options.pas 188 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904190519061907190819091910191119121913191419151916191719181919192019211922192319241925192619271928192919301931193219331934193519361937193819391940194119421943194419451946194719481949195019511952195319541955195619571958195919601961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030203120322033203420352036203720382039204020412042204320442045204620472048204920502051205220532054205520562057205820592060206120622063206420652066206720682069207020712072207320742075207620772078207920802081208220832084208520862087208820892090209120922093209420952096209720982099210021012102210321042105210621072108210921102111211221132114211521162117211821192120212121222123212421252126212721282129213021312132213321342135213621372138213921402141214221432144214521462147214821492150215121522153215421552156215721582159216021612162216321642165216621672168216921702171217221732174217521762177217821792180218121822183218421852186218721882189219021912192219321942195219621972198219922002201220222032204220522062207220822092210221122122213221422152216221722182219222022212222222322242225222622272228222922302231223222332234223522362237223822392240224122422243224422452246224722482249225022512252225322542255225622572258225922602261226222632264226522662267226822692270227122722273227422752276227722782279228022812282228322842285228622872288228922902291229222932294229522962297229822992300230123022303230423052306230723082309231023112312231323142315231623172318231923202321232223232324232523262327232823292330233123322333233423352336233723382339234023412342234323442345234623472348234923502351235223532354235523562357235823592360236123622363236423652366236723682369237023712372237323742375237623772378237923802381238223832384238523862387238823892390239123922393239423952396239723982399240024012402240324042405240624072408240924102411241224132414241524162417241824192420242124222423242424252426242724282429243024312432243324342435243624372438243924402441244224432444244524462447244824492450245124522453245424552456245724582459246024612462246324642465246624672468246924702471247224732474247524762477247824792480248124822483248424852486248724882489249024912492249324942495249624972498249925002501250225032504250525062507250825092510251125122513251425152516251725182519252025212522252325242525252625272528252925302531253225332534253525362537253825392540254125422543254425452546254725482549255025512552255325542555255625572558255925602561256225632564256525662567256825692570257125722573257425752576257725782579258025812582258325842585258625872588258925902591259225932594259525962597259825992600260126022603260426052606260726082609261026112612261326142615261626172618261926202621262226232624262526262627262826292630263126322633263426352636263726382639264026412642264326442645264626472648264926502651265226532654265526562657265826592660266126622663266426652666266726682669267026712672267326742675267626772678267926802681268226832684268526862687268826892690269126922693269426952696269726982699270027012702270327042705270627072708270927102711271227132714271527162717271827192720272127222723272427252726272727282729273027312732273327342735273627372738273927402741274227432744274527462747274827492750275127522753275427552756275727582759276027612762276327642765276627672768276927702771277227732774277527762777277827792780278127822783278427852786278727882789279027912792279327942795279627972798279928002801280228032804280528062807280828092810281128122813281428152816281728182819282028212822282328242825282628272828282928302831283228332834283528362837283828392840284128422843284428452846284728482849285028512852285328542855285628572858285928602861286228632864286528662867286828692870287128722873287428752876287728782879288028812882288328842885288628872888288928902891289228932894289528962897289828992900290129022903290429052906290729082909291029112912291329142915291629172918291929202921292229232924292529262927292829292930293129322933293429352936293729382939294029412942294329442945294629472948294929502951295229532954295529562957295829592960296129622963296429652966296729682969297029712972297329742975297629772978297929802981298229832984298529862987298829892990299129922993299429952996299729982999300030013002300330043005300630073008300930103011301230133014301530163017301830193020302130223023302430253026302730283029303030313032303330343035303630373038303930403041304230433044304530463047304830493050305130523053305430553056305730583059306030613062306330643065306630673068306930703071307230733074307530763077307830793080308130823083308430853086308730883089309030913092309330943095309630973098309931003101310231033104310531063107310831093110311131123113311431153116311731183119312031213122312331243125312631273128312931303131313231333134313531363137313831393140314131423143314431453146314731483149315031513152315331543155315631573158315931603161316231633164316531663167316831693170317131723173317431753176317731783179318031813182318331843185318631873188318931903191319231933194319531963197319831993200320132023203320432053206320732083209321032113212321332143215321632173218321932203221322232233224322532263227322832293230323132323233323432353236323732383239324032413242324332443245324632473248324932503251325232533254325532563257325832593260326132623263326432653266326732683269327032713272327332743275327632773278327932803281328232833284328532863287328832893290329132923293329432953296329732983299330033013302330333043305330633073308330933103311331233133314331533163317331833193320332133223323332433253326332733283329333033313332333333343335333633373338333933403341334233433344334533463347334833493350335133523353335433553356335733583359336033613362336333643365336633673368336933703371337233733374337533763377337833793380338133823383338433853386338733883389339033913392339333943395339633973398339934003401340234033404340534063407340834093410341134123413341434153416341734183419342034213422342334243425342634273428342934303431343234333434343534363437343834393440344134423443344434453446344734483449345034513452345334543455345634573458345934603461346234633464346534663467346834693470347134723473347434753476347734783479348034813482348334843485348634873488348934903491349234933494349534963497349834993500350135023503350435053506350735083509351035113512351335143515351635173518351935203521352235233524352535263527352835293530353135323533353435353536353735383539354035413542354335443545354635473548354935503551355235533554355535563557355835593560356135623563356435653566356735683569357035713572357335743575357635773578357935803581358235833584358535863587358835893590359135923593359435953596359735983599360036013602360336043605360636073608360936103611361236133614361536163617361836193620362136223623362436253626362736283629363036313632363336343635363636373638363936403641364236433644364536463647364836493650365136523653365436553656365736583659366036613662366336643665366636673668366936703671367236733674367536763677367836793680368136823683368436853686368736883689369036913692369336943695369636973698369937003701370237033704370537063707370837093710371137123713371437153716371737183719372037213722372337243725372637273728372937303731373237333734373537363737373837393740374137423743374437453746374737483749375037513752375337543755375637573758375937603761376237633764376537663767376837693770377137723773377437753776377737783779378037813782378337843785378637873788378937903791379237933794379537963797379837993800380138023803380438053806380738083809381038113812381338143815381638173818381938203821382238233824382538263827382838293830383138323833383438353836383738383839384038413842384338443845384638473848384938503851385238533854385538563857385838593860386138623863386438653866386738683869387038713872387338743875387638773878387938803881388238833884388538863887388838893890389138923893389438953896389738983899390039013902390339043905390639073908390939103911391239133914391539163917391839193920392139223923392439253926392739283929393039313932393339343935393639373938393939403941394239433944394539463947394839493950395139523953395439553956395739583959396039613962396339643965396639673968396939703971397239733974397539763977397839793980398139823983398439853986398739883989399039913992399339943995399639973998399940004001400240034004400540064007400840094010401140124013401440154016401740184019402040214022402340244025402640274028402940304031403240334034403540364037403840394040404140424043404440454046404740484049405040514052405340544055405640574058405940604061406240634064406540664067406840694070407140724073407440754076407740784079408040814082408340844085408640874088408940904091409240934094409540964097409840994100410141024103410441054106410741084109411041114112411341144115411641174118411941204121412241234124412541264127412841294130413141324133413441354136413741384139414041414142414341444145414641474148414941504151415241534154415541564157415841594160416141624163416441654166416741684169417041714172417341744175417641774178417941804181418241834184418541864187418841894190419141924193419441954196419741984199420042014202420342044205420642074208420942104211421242134214421542164217421842194220422142224223422442254226422742284229423042314232423342344235423642374238423942404241424242434244424542464247424842494250425142524253425442554256425742584259426042614262426342644265426642674268426942704271427242734274427542764277427842794280428142824283428442854286428742884289429042914292429342944295429642974298429943004301430243034304430543064307430843094310431143124313431443154316431743184319432043214322432343244325432643274328432943304331433243334334433543364337433843394340434143424343434443454346434743484349435043514352435343544355435643574358435943604361436243634364436543664367436843694370437143724373437443754376437743784379438043814382438343844385438643874388438943904391439243934394439543964397439843994400440144024403440444054406440744084409441044114412441344144415441644174418441944204421442244234424442544264427442844294430443144324433443444354436443744384439444044414442444344444445444644474448444944504451445244534454445544564457445844594460446144624463446444654466446744684469447044714472447344744475447644774478447944804481448244834484448544864487448844894490449144924493449444954496449744984499450045014502450345044505450645074508450945104511451245134514451545164517451845194520452145224523452445254526452745284529453045314532453345344535453645374538453945404541454245434544454545464547454845494550455145524553455445554556455745584559456045614562456345644565456645674568456945704571457245734574457545764577457845794580458145824583458445854586458745884589459045914592459345944595459645974598459946004601460246034604460546064607460846094610461146124613461446154616461746184619462046214622462346244625462646274628462946304631463246334634463546364637463846394640464146424643464446454646464746484649465046514652465346544655465646574658465946604661466246634664466546664667466846694670467146724673467446754676467746784679468046814682468346844685468646874688468946904691469246934694469546964697469846994700470147024703470447054706470747084709471047114712471347144715471647174718471947204721472247234724472547264727472847294730473147324733473447354736473747384739474047414742474347444745474647474748474947504751475247534754475547564757475847594760476147624763476447654766476747684769477047714772477347744775477647774778477947804781478247834784478547864787478847894790479147924793479447954796479747984799480048014802480348044805480648074808480948104811481248134814481548164817481848194820482148224823482448254826482748284829483048314832483348344835483648374838483948404841484248434844484548464847484848494850485148524853485448554856485748584859486048614862486348644865486648674868486948704871487248734874487548764877487848794880488148824883488448854886488748884889489048914892489348944895489648974898489949004901490249034904490549064907490849094910491149124913491449154916491749184919492049214922492349244925492649274928492949304931493249334934493549364937493849394940494149424943494449454946494749484949495049514952495349544955495649574958495949604961496249634964496549664967496849694970497149724973497449754976497749784979498049814982498349844985498649874988498949904991499249934994499549964997499849995000500150025003500450055006500750085009501050115012501350145015501650175018501950205021502250235024502550265027502850295030503150325033503450355036503750385039504050415042504350445045504650475048504950505051505250535054505550565057505850595060506150625063506450655066506750685069507050715072507350745075507650775078507950805081508250835084508550865087508850895090509150925093509450955096509750985099510051015102510351045105510651075108510951105111511251135114511551165117511851195120512151225123512451255126512751285129513051315132513351345135513651375138513951405141514251435144514551465147514851495150515151525153515451555156515751585159516051615162516351645165516651675168516951705171517251735174517551765177517851795180518151825183518451855186518751885189519051915192519351945195519651975198519952005201520252035204520552065207520852095210521152125213521452155216521752185219522052215222522352245225522652275228522952305231523252335234523552365237523852395240524152425243524452455246524752485249525052515252525352545255525652575258525952605261526252635264526552665267526852695270527152725273527452755276527752785279528052815282528352845285528652875288528952905291529252935294529552965297529852995300530153025303530453055306530753085309531053115312531353145315531653175318531953205321532253235324532553265327532853295330533153325333533453355336533753385339534053415342534353445345534653475348534953505351535253535354535553565357535853595360536153625363536453655366536753685369537053715372537353745375537653775378537953805381538253835384538553865387538853895390539153925393539453955396539753985399540054015402540354045405540654075408540954105411541254135414541554165417541854195420542154225423542454255426542754285429543054315432543354345435543654375438543954405441544254435444544554465447544854495450545154525453545454555456545754585459546054615462546354645465546654675468546954705471547254735474547554765477547854795480548154825483548454855486548754885489549054915492549354945495549654975498549955005501550255035504550555065507550855095510551155125513551455155516551755185519552055215522552355245525552655275528552955305531
  1. {
  2. Copyright (c) 1998-2008 by Florian Klaempfl and Peter Vreman
  3. Reads command line options and config files
  4. This program is free software; you can redistribute it and/or modify
  5. it under the terms of the GNU General Public License as published by
  6. the Free Software Foundation; either version 2 of the License, or
  7. (at your option) any later version.
  8. This program is distributed in the hope that it will be useful,
  9. but WITHOUT ANY WARRANTY; without even the implied warranty of
  10. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  11. GNU General Public License for more details.
  12. You should have received a copy of the GNU General Public License
  13. along with this program; if not, write to the Free Software
  14. Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  15. ****************************************************************************
  16. }
  17. unit options;
  18. {$i fpcdefs.inc}
  19. interface
  20. uses
  21. cfileutl,cclasses,versioncmp,
  22. globtype,globals,verbose,systems,cpuinfo,comprsrc;
  23. Type
  24. TOption=class
  25. FirstPass,
  26. ParaLogo,
  27. NoPressEnter,
  28. FPCHelpLines,
  29. LogoWritten,
  30. ABISetExplicitly,
  31. FPUSetExplicitly,
  32. CPUSetExplicitly,
  33. OptCPUSetExplicitly: boolean;
  34. FileLevel : longint;
  35. QuickInfo : string;
  36. FPCBinaryPath: string;
  37. ParaIncludeCfgPath,
  38. ParaIncludePath,
  39. ParaUnitPath,
  40. ParaObjectPath,
  41. ParaLibraryPath,
  42. ParaFrameworkPath,
  43. parapackagepath : TSearchPathList;
  44. paranamespaces : TCmdStrList;
  45. ParaAlignment : TAlignmentInfo;
  46. parapackages : tfphashobjectlist;
  47. paratarget : tsystem;
  48. paratargetasm : tasm;
  49. paratargetdbg : tdbg;
  50. parasubtarget : string;
  51. LinkTypeSetExplicitly : boolean;
  52. LinkerSetExplicitly : boolean;
  53. Constructor Create;
  54. Destructor Destroy;override;
  55. procedure WriteLogo;
  56. procedure WriteInfo (More: string);
  57. procedure WriteHelpPages;
  58. procedure WriteQuickInfo;
  59. procedure IllegalPara(const opt:TCmdStr);
  60. procedure UnsupportedPara(const opt:TCmdStr);
  61. procedure IgnoredPara(const opt:TCmdStr);
  62. function Unsetbool(var Opts:TCmdStr; Pos: Longint; const FullPara: TCmdStr; RequireBoolPara: Boolean):boolean;
  63. procedure interpret_option(const opt :TCmdStr;ispara:boolean);
  64. procedure Interpret_envvar(const envname : TCmdStr);
  65. procedure Interpret_file(const filename : TPathStr);
  66. procedure Read_Parameters;
  67. procedure parsecmd(cmd:TCmdStr);
  68. procedure TargetOptions(def:boolean);
  69. procedure CheckOptionsCompatibility;
  70. procedure ForceStaticLinking;
  71. protected
  72. MacVersionSet: boolean;
  73. IdfVersionSet: boolean;
  74. processorstr: TCmdStr;
  75. function ParseMacVersionMin(out minversion, invalidateversion: tversion; const compvarname, value: string; ios: boolean): boolean;
  76. procedure MaybeSetDefaultMacVersionMacro;
  77. {$ifdef XTENSA}
  78. function ParseVersionStr(out ver: longint; const compvarname, value: string): boolean;
  79. procedure MaybeSetIdfVersionMacro;
  80. {$endif}
  81. {$ifdef llvm}
  82. procedure LLVMEnableSanitizers(sanitizers: TCmdStr);
  83. {$endif llvm}
  84. procedure VerifyTargetProcessor;
  85. end;
  86. TOptionClass=class of toption;
  87. var
  88. coption : TOptionClass;
  89. procedure read_arguments(cmd:TCmdStr);
  90. implementation
  91. uses
  92. widestr,
  93. charset,
  94. SysUtils,
  95. version,
  96. cutils,cmsgs,
  97. comphook,
  98. symtable,scanner,rabase,
  99. symconst,
  100. {$ifdef llvm}
  101. { override supported optimizer transformations at the compiler level }
  102. llvminfo,
  103. {$endif llvm}
  104. dirparse,
  105. pkgutil;
  106. const
  107. page_size = 24;
  108. page_width = 80;
  109. var
  110. option : toption;
  111. read_subfile, { read subtarget config file, set when a cfgfile is found }
  112. read_configfile, { read config file, set when a cfgfile is found }
  113. disable_configfile : boolean;
  114. subcfg,
  115. fpcdir,
  116. ppccfg,
  117. param_file : string; { file to compile specified on the commandline }
  118. {****************************************************************************
  119. Options not supported on all platforms
  120. ****************************************************************************}
  121. const
  122. { gprof (requires implementation of g_profilecode in the code generator) }
  123. supported_targets_pg = [system_i386_linux,system_x86_64_linux,system_mipseb_linux,system_mipsel_linux,system_arm_linux]
  124. + [system_i386_win32]
  125. + [system_powerpc_darwin,system_x86_64_darwin]
  126. + [system_i386_GO32V2]
  127. + [system_i386_freebsd]
  128. + [system_i386_netbsd]
  129. + [system_i386_wdosx]
  130. + [system_riscv32_linux,system_riscv64_linux]
  131. + [system_aarch64_linux];
  132. suppported_targets_x_smallr = systems_linux + systems_solaris + systems_android
  133. + systems_openbsd
  134. + [system_i386_haiku,system_x86_64_haiku]
  135. + [system_i386_beos]
  136. + [system_m68k_amiga];
  137. {****************************************************************************
  138. Defines
  139. ****************************************************************************}
  140. procedure set_default_link_type;
  141. begin
  142. undef_system_macro('FPC_LINK_SMART');
  143. def_system_macro('FPC_LINK_STATIC');
  144. undef_system_macro('FPC_LINK_DYNAMIC');
  145. init_settings.globalswitches:=init_settings.globalswitches+[cs_link_static];
  146. init_settings.globalswitches:=init_settings.globalswitches-[cs_link_shared,cs_link_smart];
  147. {$ifdef AIX}
  148. init_settings.globalswitches:=init_settings.globalswitches+[cs_link_native];
  149. {$endif}
  150. end;
  151. procedure set_endianess_macros;
  152. begin
  153. { endian define }
  154. case target_info.endian of
  155. endian_little :
  156. begin
  157. def_system_macro('ENDIAN_LITTLE');
  158. def_system_macro('FPC_LITTLE_ENDIAN');
  159. undef_system_macro('ENDIAN_BIG');
  160. undef_system_macro('FPC_BIG_ENDIAN');
  161. end;
  162. endian_big :
  163. begin
  164. def_system_macro('ENDIAN_BIG');
  165. def_system_macro('FPC_BIG_ENDIAN');
  166. undef_system_macro('ENDIAN_LITTLE');
  167. undef_system_macro('FPC_LITTLE_ENDIAN');
  168. end;
  169. end;
  170. end;
  171. {****************************************************************************
  172. Toption
  173. ****************************************************************************}
  174. procedure StopOptions(err:longint);
  175. begin
  176. if assigned(Option) then
  177. begin
  178. Option.free;
  179. Option:=nil;
  180. end;
  181. raise ECompilerAbortSilent.Create;
  182. end;
  183. function is_identifier(const s: TCmdStr): boolean;
  184. var
  185. i: longint;
  186. begin
  187. result:=false;
  188. if (s='') or not (s[1] in ['A'..'Z','a'..'z','_']) then
  189. exit;
  190. for i:=2 to length(s) do
  191. if not (s[I] in ['A'..'Z','a'..'z','0'..'9','_']) then
  192. exit;
  193. result:=true;
  194. end;
  195. procedure Toption.WriteLogo;
  196. var
  197. msg : TMsgStr;
  198. p : pchar;
  199. begin
  200. if not LogoWritten then
  201. begin
  202. msg:=MessageStr(option_logo);
  203. p:=pchar(msg);
  204. while assigned(p) do
  205. Comment(V_Normal,GetMsgLine(p));
  206. LogoWritten:= true;
  207. end;
  208. end;
  209. procedure Toption.WriteInfo (More: string);
  210. var
  211. msg_str: TMsgStr;
  212. p : pchar;
  213. hs,hs1,hs3,s : TCmdStr;
  214. J: longint;
  215. xmloutput: Text;
  216. const
  217. NewLineStr = '$\n';
  218. OSTargetsPlaceholder = '$OSTARGETS';
  219. CPUListPlaceholder = '$INSTRUCTIONSETS';
  220. FPUListPlaceholder = '$FPUINSTRUCTIONSETS';
  221. ABIListPlaceholder = '$ABITARGETS';
  222. OptListPlaceholder = '$OPTIMIZATIONS';
  223. WPOListPlaceholder = '$WPOPTIMIZATIONS';
  224. AsmModeListPlaceholder = '$ASMMODES';
  225. ControllerListPlaceholder = '$CONTROLLERTYPES';
  226. FeatureListPlaceholder = '$FEATURELIST';
  227. ModeSwitchListPlaceholder = '$MODESWITCHES';
  228. CodeGenerationBackendPlaceholder = '$CODEGENERATIONBACKEND';
  229. LLVMVersionPlaceholder = '$LLVMVERSIONS';
  230. procedure SplitLine (var OrigString: TCmdStr; const Placeholder: TCmdStr;
  231. out RemainderString: TCmdStr);
  232. var
  233. I: longint;
  234. HS2: TCmdStr;
  235. begin
  236. RemainderString := '';
  237. if OrigString = '' then
  238. Exit;
  239. repeat
  240. I := Pos (NewLineStr, OrigString);
  241. if I > 0 then
  242. begin
  243. HS2 := Copy (OrigString, 1, Pred (I));
  244. { Stop if this line contains the placeholder for list replacement }
  245. if Pos (Placeholder, HS2) > 0 then
  246. begin
  247. RemainderString := Copy (OrigString, I + Length (NewLineStr),
  248. Length (OrigString) - I - Length (NewLineStr));
  249. { Special case - NewLineStr at the end of the line }
  250. if RemainderString = '' then
  251. RemainderString := NewLineStr;
  252. OrigString := HS2;
  253. Exit;
  254. end;
  255. Comment (V_Normal, HS2);
  256. Delete (OrigString, 1, Pred (I) + Length (NewLineStr));
  257. end;
  258. until I = 0;
  259. if (OrigString <> '') and (Pos (Placeholder, OrigString) = 0) then
  260. Comment (V_Normal, OrigString);
  261. end;
  262. procedure ListOSTargets (OrigString: TCmdStr);
  263. var
  264. target : tsystem;
  265. begin
  266. SplitLine (OrigString, OSTargetsPlaceholder, HS3);
  267. for target:=low(tsystem) to high(tsystem) do
  268. if assigned(targetinfos[target]) then
  269. begin
  270. hs1:=targetinfos[target]^.shortname;
  271. if OrigString = '' then
  272. Comment (V_Normal, hs1)
  273. else
  274. begin
  275. hs := OrigString;
  276. hs1:=hs1 + ': ' + targetinfos[target]^.name;
  277. if tf_under_development in targetinfos[target]^.flags then
  278. hs1:=hs1+' {*}';
  279. Replace(hs,OSTargetsPlaceholder,hs1);
  280. Comment(V_Normal,hs);
  281. end;
  282. end;
  283. end;
  284. procedure ListOSTargetsXML;
  285. var
  286. target : tsystem;
  287. begin
  288. WriteLn(xmloutput,' <ostargets>');
  289. for target:=low(tsystem) to high(tsystem) do
  290. if assigned(targetinfos[target]) then
  291. begin
  292. Write(xmloutput,' <ostarget shortname="',targetinfos[target]^.shortname,'" name="',targetinfos[target]^.name,'"');
  293. if tf_under_development in targetinfos[target]^.flags then
  294. Write(' experimental="1"');
  295. WriteLn('/>');
  296. end;
  297. WriteLn(xmloutput,' </ostargets>');
  298. end;
  299. procedure ListCPUInstructionSets (OrigString: TCmdStr);
  300. var
  301. cpu : tcputype;
  302. begin
  303. SplitLine (OrigString, CPUListPlaceholder, HS3);
  304. hs1:='';
  305. for cpu:=low(tcputype) to high(tcputype) do
  306. begin
  307. if (OrigString = '') then
  308. begin
  309. if CPUTypeStr [CPU] <> '' then
  310. Comment (V_Normal, CPUTypeStr [CPU]);
  311. end
  312. else
  313. begin
  314. if length(hs1+cputypestr[cpu])>70 then
  315. begin
  316. hs:=OrigString;
  317. HS1 := HS1 + ',';
  318. Replace(hs,CPUListPlaceholder,hs1);
  319. Comment(V_Normal,hs);
  320. hs1:=''
  321. end
  322. else if hs1<>'' then
  323. hs1:=hs1+',';
  324. if cputypestr[cpu]<>'' then
  325. hs1:=hs1+cputypestr[cpu];
  326. end;
  327. end;
  328. if (OrigString <> '') and (hs1 <> '') then
  329. begin
  330. hs:=OrigString;
  331. Replace(hs,CPUListPlaceholder,hs1);
  332. Comment(V_Normal,hs);
  333. hs1:=''
  334. end;
  335. end;
  336. procedure ListCPUInstructionSetsXML;
  337. var
  338. cpu : tcputype;
  339. begin
  340. WriteLn(xmloutput,' <cpuinstructionsets>');
  341. for cpu:=low(tcputype) to high(tcputype) do
  342. if CPUTypeStr [CPU] <> '' then
  343. WriteLn(xmloutput,' <cpuinstructionset name="',CPUTypeStr [CPU], '"/>');
  344. WriteLn(xmloutput,' </cpuinstructionsets>');
  345. end;
  346. procedure ListFPUInstructionSets (OrigString: TCmdStr);
  347. var
  348. fpu : tfputype;
  349. begin
  350. SplitLine (OrigString, FPUListPlaceholder, HS3);
  351. hs1:='';
  352. for fpu:=low(tfputype) to high(tfputype) do
  353. begin
  354. if (OrigString = '') then
  355. begin
  356. if FPUTypeStr [FPU] <> '' then
  357. Comment (V_Normal, FPUTypeStr [FPU]);
  358. end
  359. else
  360. begin
  361. if length(hs1+fputypestr[fpu])>70 then
  362. begin
  363. hs:=OrigString;
  364. HS1 := HS1 + ',';
  365. Replace(hs,FPUListPlaceholder,hs1);
  366. Comment(V_Normal,hs);
  367. hs1:=''
  368. end
  369. else if hs1<>'' then
  370. hs1:=hs1+',';
  371. if fputypestr[fpu]<>'' then
  372. hs1:=hs1+fputypestr[fpu];
  373. end;
  374. end;
  375. if (OrigString <> '') and (hs1 <> '') then
  376. begin
  377. hs:=OrigString;
  378. Replace(hs,FPUListPlaceholder,hs1);
  379. Comment(V_Normal,hs);
  380. hs1:=''
  381. end;
  382. end;
  383. procedure ListFPUInstructionSetsXML;
  384. var
  385. fpu : tfputype;
  386. begin
  387. WriteLn(xmloutput,' <fpuinstructionsets>');
  388. for fpu:=low(tfputype) to high(tfputype) do
  389. if FPUTypeStr [fpu] <> '' then
  390. WriteLn(xmloutput,' <cpuinstructionset name="',FPUTypeStr [fpu], '"/>');
  391. WriteLn(xmloutput,' </fpuinstructionsets>');
  392. end;
  393. procedure ListABITargets (OrigString: TCmdStr);
  394. var
  395. abi : tabi;
  396. begin
  397. SplitLine (OrigString, ABIListPlaceholder, HS3);
  398. for abi:=low(abi) to high(abi) do
  399. begin
  400. if not abiinfo[abi].supported then
  401. continue;
  402. hs1:=abiinfo[abi].name;
  403. if hs1<>'' then
  404. begin
  405. if OrigString = '' then
  406. Comment (V_Normal, HS1)
  407. else
  408. begin
  409. hs:=OrigString;
  410. Replace(hs,ABIListPlaceholder,hs1);
  411. Comment(V_Normal,hs);
  412. end;
  413. end;
  414. end;
  415. end;
  416. procedure ListABITargetsXML;
  417. var
  418. abi : tabi;
  419. begin
  420. WriteLn(xmloutput,' <abis>');
  421. for abi:=low(abi) to high(abi) do
  422. begin
  423. if not abiinfo[abi].supported then
  424. continue;
  425. if abiinfo[abi].name<>'' then;
  426. WriteLn(xmloutput,' <abi name="',abiinfo[abi].name, '"/>');
  427. end;
  428. WriteLn(xmloutput,' </abis>');
  429. end;
  430. procedure ListOptimizations (OrigString: TCmdStr);
  431. var
  432. opt : toptimizerswitch;
  433. begin
  434. SplitLine (OrigString, OptListPlaceholder, HS3);
  435. for opt:=low(toptimizerswitch) to high(toptimizerswitch) do
  436. begin
  437. if opt in supported_optimizerswitches then
  438. begin
  439. hs1:=OptimizerSwitchStr[opt];
  440. if hs1<>'' then
  441. begin
  442. if OrigString = '' then
  443. Comment (V_Normal, hs1)
  444. else
  445. begin
  446. hs:=OrigString;
  447. Replace(hs,OptListPlaceholder,hs1);
  448. Comment(V_Normal,hs);
  449. end;
  450. end;
  451. end;
  452. end;
  453. end;
  454. procedure ListOptimizationsXML;
  455. var
  456. opt: toptimizerswitch;
  457. begin
  458. WriteLn(xmloutput,' <optimizations>');
  459. for opt:=low(toptimizerswitch) to high(toptimizerswitch) do
  460. if OptimizerSwitchStr[opt]<>'' then
  461. WriteLn(xmloutput,' <optimization name="',OptimizerSwitchStr[opt],'"/>');
  462. WriteLn(xmloutput,' </optimizations>');
  463. end;
  464. procedure ListWPOptimizations (OrigString: TCmdStr);
  465. var
  466. wpopt: twpoptimizerswitch;
  467. begin
  468. SplitLine (OrigString, WPOListPlaceholder, HS3);
  469. for wpopt:=low(twpoptimizerswitch) to high(twpoptimizerswitch) do
  470. begin
  471. { currently all whole program optimizations are platform-independent
  472. if opt in supported_wpoptimizerswitches then
  473. }
  474. begin
  475. hs1:=WPOptimizerSwitchStr[wpopt];
  476. if hs1<>'' then
  477. begin
  478. if OrigString = '' then
  479. Comment (V_Normal, hs1)
  480. else
  481. begin
  482. hs:=OrigString;
  483. Replace(hs,WPOListPlaceholder,hs1);
  484. Comment(V_Normal,hs);
  485. end;
  486. end;
  487. end;
  488. end;
  489. end;
  490. procedure ListWPOptimizationsXML;
  491. var
  492. wpopt: twpoptimizerswitch;
  493. begin
  494. WriteLn(xmloutput,' <wpoptimizations>');
  495. for wpopt:=low(twpoptimizerswitch) to high(twpoptimizerswitch) do
  496. if WPOptimizerSwitchStr[wpopt]<>'' then
  497. WriteLn(xmloutput,' <wpoptimization name="',WPOptimizerSwitchStr[wpopt],'"/>');
  498. WriteLn(xmloutput,' </wpoptimizations>');
  499. end;
  500. procedure ListAsmModes (OrigString: TCmdStr);
  501. var
  502. asmmode : tasmmode;
  503. begin
  504. SplitLine (OrigString, AsmModeListPlaceholder, HS3);
  505. for asmmode:=low(tasmmode) to high(tasmmode) do
  506. if assigned(asmmodeinfos[asmmode]) then
  507. begin
  508. hs1:=asmmodeinfos[asmmode]^.idtxt;
  509. if hs1<>'' then
  510. begin
  511. if OrigString = '' then
  512. Comment (V_Normal, hs1)
  513. else
  514. begin
  515. hs:=OrigString;
  516. Replace(hs,AsmModeListPlaceholder,hs1);
  517. Comment(V_Normal,hs);
  518. end;
  519. end;
  520. end;
  521. end;
  522. procedure ListAsmModesXML;
  523. var
  524. asmmode : tasmmode;
  525. begin
  526. WriteLn(xmloutput,' <asmmodes>');
  527. for asmmode:=low(tasmmode) to high(tasmmode) do
  528. if assigned(asmmodeinfos[asmmode]) then
  529. WriteLn(xmloutput,' <asmmode name="',asmmodeinfos[asmmode]^.idtxt,'"/>');
  530. WriteLn(xmloutput,' </asmmodes>');
  531. end;
  532. procedure ListControllerTypes (OrigString: TCmdStr);
  533. var
  534. controllertype : tcontrollertype;
  535. begin
  536. {$PUSH}
  537. {$WARN 6018 OFF} (* Unreachable code due to compile time evaluation *)
  538. if (ControllerSupport) then
  539. begin
  540. SplitLine (OrigString, ControllerListPlaceholder, HS3);
  541. hs1:='';
  542. for controllertype:=low(tcontrollertype) to high(tcontrollertype) do
  543. begin
  544. if (OrigString = '') then
  545. begin
  546. if Embedded_Controllers [ControllerType].ControllerTypeStr <> '' then
  547. Comment (V_Normal, Embedded_Controllers [ControllerType].ControllerTypeStr);
  548. end
  549. else
  550. begin
  551. if length(hs1+embedded_controllers[controllertype].ControllerTypeStr)
  552. >70 then
  553. begin
  554. hs:=OrigString;
  555. HS1 := HS1 + ',';
  556. Replace(hs,ControllerListPlaceholder,hs1);
  557. Comment(V_Normal,hs);
  558. hs1:=''
  559. end
  560. else if hs1<>'' then
  561. hs1:=hs1+',';
  562. if embedded_controllers[controllertype].ControllerTypeStr<>'' then
  563. hs1:=hs1+embedded_controllers[controllertype].ControllerTypeStr;
  564. end;
  565. end;
  566. if (OrigString <> '') and (hs1<>'') then
  567. begin
  568. hs:=OrigString;
  569. Replace(hs,ControllerListPlaceholder,hs1);
  570. Comment(V_Normal,hs);
  571. hs1:=''
  572. end;
  573. end;
  574. {$POP}
  575. end;
  576. procedure ListControllerTypesXML;
  577. var
  578. controllertype : tcontrollertype;
  579. begin
  580. {$PUSH}
  581. {$WARN 6018 OFF} (* Unreachable code due to compile time evaluation *)
  582. if (ControllerSupport) then
  583. begin
  584. WriteLn(xmloutput,' <controllertypes>');
  585. for controllertype:=low(tcontrollertype) to high(tcontrollertype) do
  586. if embedded_controllers[controllertype].ControllerTypeStr<>'' then
  587. WriteLn(xmloutput,' <controllertype name="',embedded_controllers[controllertype].ControllerTypeStr,
  588. '" controllerunit="',embedded_controllers[controllertype].controllerunitstr, '"/>');
  589. WriteLn(xmloutput,' </controllertypes>');
  590. end;
  591. {$POP}
  592. end;
  593. procedure ListFeatures (OrigString: TCmdStr);
  594. var
  595. Feature: TFeature;
  596. begin
  597. SplitLine (OrigString, FeatureListPlaceholder, HS3);
  598. HS1 := '';
  599. for Feature := Low (TFeature) to High (TFeature) do
  600. begin
  601. if (OrigString = '') then
  602. begin
  603. if FeatureStr [Feature] <> '' then
  604. Comment (V_Normal, FeatureStr [Feature]);
  605. end
  606. else
  607. begin
  608. if Length (HS1 + FeatureStr [Feature]) > 70 then
  609. begin
  610. HS := OrigString;
  611. HS1 := HS1 + ',';
  612. Replace (HS, FeatureListPlaceholder, HS1);
  613. Comment (V_Normal, HS);
  614. HS1 := ''
  615. end
  616. else if HS1 <> '' then
  617. HS1 := HS1 + ',';
  618. if FeatureStr [Feature] <> '' then
  619. HS1 := HS1 + FeatureStr [Feature];
  620. end;
  621. end;
  622. if (OrigString <> '') and (HS1 <> '') then
  623. begin
  624. HS := OrigString;
  625. Replace (HS, FeatureListPlaceholder, HS1);
  626. Comment (V_Normal, HS);
  627. HS1 := ''
  628. end;
  629. end;
  630. procedure ListFeaturesXML;
  631. var
  632. Feature: TFeature;
  633. begin
  634. WriteLn(xmloutput,' <features>');
  635. for Feature := Low (TFeature) to High (TFeature) do
  636. if FeatureStr [Feature] <> '' then
  637. WriteLn(xmloutput,' <feature name="',FeatureStr [Feature],'"/>');
  638. WriteLn(xmloutput,' </features>');
  639. end;
  640. procedure ListModeswitches (OrigString: TCmdStr);
  641. var
  642. Modeswitch: TModeswitch;
  643. begin
  644. SplitLine (OrigString, ModeswitchListPlaceholder, HS3);
  645. HS1 := '';
  646. for Modeswitch := Low (TModeswitch) to High (TModeswitch) do
  647. begin
  648. if (OrigString = '') then
  649. begin
  650. if ModeswitchStr [Modeswitch] <> '' then
  651. Comment (V_Normal, ModeswitchStr [Modeswitch]);
  652. end
  653. else
  654. begin
  655. if Length (HS1 + ModeswitchStr [Modeswitch]) > 60 then
  656. begin
  657. HS := OrigString;
  658. HS1 := HS1 + ',';
  659. Replace (HS, ModeswitchListPlaceholder, HS1);
  660. Comment (V_Normal, HS);
  661. HS1 := ''
  662. end
  663. else if HS1 <> '' then
  664. HS1 := HS1 + ',';
  665. if ModeswitchStr [Modeswitch] <> '' then
  666. HS1 := HS1 + ModeswitchStr [Modeswitch];
  667. end;
  668. end;
  669. if (OrigString <> '') and (HS1 <> '') then
  670. begin
  671. HS := OrigString;
  672. Replace (HS, ModeswitchListPlaceholder, HS1);
  673. Comment (V_Normal, HS);
  674. HS1 := ''
  675. end;
  676. end;
  677. procedure ListModeswitchesXML;
  678. var
  679. Modeswitch: TModeswitch;
  680. begin
  681. WriteLn(xmloutput,' <modeswitches>');
  682. for Modeswitch:=Low(TModeswitch) to High(TModeswitch) do
  683. if ModeswitchStr [Modeswitch]<>'' then
  684. WriteLn(xmloutput,' <modeswitch name="',ModeswitchStr [Modeswitch],'"/>');
  685. WriteLn(xmloutput,' </modeswitches>');
  686. end;
  687. procedure ListCodeGenerationBackend (OrigString: TCmdStr);
  688. begin
  689. SplitLine (OrigString, CodeGenerationBackendPlaceholder, HS3);
  690. hs1:=cgbackend2str[cgbackend];
  691. if OrigString = '' then
  692. Comment (V_Normal, hs1)
  693. else
  694. begin
  695. hs:=OrigString;
  696. Replace(hs,CodeGenerationBackendPlaceholder,hs1);
  697. Comment(V_Normal,hs);
  698. end;
  699. end;
  700. procedure ListCodeGenerationBackendXML;
  701. begin
  702. WriteLn(xmloutput,' <codegeneratorbackend>',cgbackend2str[cgbackend],'</codegeneratorbackend>');
  703. end;
  704. procedure ListLLVMVersions (OrigString: TCmdStr);
  705. {$ifdef LLVM}
  706. var
  707. llvmversion : tllvmversion;
  708. {$endif LLVM}
  709. begin
  710. {$ifdef LLVM}
  711. SplitLine (OrigString, LLVMVersionPlaceholder, HS3);
  712. for llvmversion:=low(llvmversion) to high(llvmversion) do
  713. begin
  714. hs1:=llvmversionstr[llvmversion];
  715. if hs1<>'' then
  716. begin
  717. if OrigString = '' then
  718. Comment (V_Normal, hs1)
  719. else
  720. begin
  721. hs:=OrigString;
  722. Replace(hs,LLVMVersionPlaceholder,hs1);
  723. Comment(V_Normal,hs);
  724. end;
  725. end;
  726. end;
  727. {$else LLVM}
  728. Comment (V_Normal, '')
  729. {$endif LLVM}
  730. end;
  731. procedure ListLLVMVersionsXML;
  732. {$ifdef LLVM}
  733. var
  734. llvmversion : tllvmversion;
  735. {$endif LLVM}
  736. begin
  737. {$ifdef LLVM}
  738. WriteLn(xmloutput,' <llvmversions>');
  739. for llvmversion:=Low(tllvmversion) to High(tllvmversion) do
  740. if llvmversionstr[llvmversion]<>'' then
  741. WriteLn(xmloutput,' <llvmversion name="',llvmversionstr[llvmversion],'"/>');
  742. WriteLn(xmloutput,' </llvmversions>');
  743. {$endif LLVM}
  744. end;
  745. begin
  746. if More = '' then
  747. begin
  748. msg_str:=MessageStr(option_info);
  749. p:=pchar(msg_str);
  750. while assigned(p) do
  751. begin
  752. s:=GetMsgLine(p);
  753. { list permitted values for certain options }
  754. if pos(OSTargetsPlaceholder,s)>0 then
  755. ListOSTargets (S)
  756. else if pos(CPUListPlaceholder,s)>0 then
  757. ListCPUInstructionSets (S)
  758. else if pos(FPUListPlaceholder,s)>0 then
  759. ListFPUInstructionSets (S)
  760. else if pos(ABIListPlaceholder,s)>0 then
  761. ListABITargets (S)
  762. else if pos(OptListPlaceholder,s)>0 then
  763. ListOptimizations (S)
  764. else if pos(WPOListPlaceholder,s)>0 then
  765. ListWPOptimizations (S)
  766. else if Pos (ModeswitchListPlaceholder, S) > 0 then
  767. ListModeswitches (S)
  768. else if pos(AsmModeListPlaceholder,s)>0 then
  769. ListAsmModes (S)
  770. else if pos(ControllerListPlaceholder,s)>0 then
  771. ListControllerTypes (S)
  772. else if pos(FeatureListPlaceholder,s)>0 then
  773. ListFeatures (S)
  774. else if pos(CodeGenerationBackendPlaceholder,s)>0 then
  775. ListCodeGenerationBackend (S)
  776. else if pos(LLVMVersionPlaceholder,s)>0 then
  777. ListLLVMVersions (s)
  778. else
  779. Comment(V_Normal,s);
  780. end;
  781. end
  782. else if Copy(More,1,1) = 'x' then
  783. begin
  784. Assign(xmloutput,Copy(More,2,length(More)-1));
  785. Rewrite(xmloutput);
  786. WriteLn(xmloutput,'<?xml version="1.0" encoding="utf-8"?>');
  787. WriteLn(xmloutput,'<fpcoutput>');
  788. WriteLn(xmloutput,' <info>');
  789. ListOSTargetsXML;
  790. ListCPUInstructionSetsXML;
  791. ListFPUInstructionSetsXML;
  792. ListABITargetsXML;
  793. ListOptimizationsXML;
  794. ListWPOptimizationsXML;
  795. ListModeswitchesXML;
  796. ListAsmModesXML;
  797. ListControllerTypesXML;
  798. ListFeaturesXML;
  799. ListCodeGenerationBackendXML;
  800. ListLLVMVersionsXML;
  801. WriteLn(xmloutput,' </info>');
  802. WriteLn(xmloutput,'</fpcoutput>');
  803. Close(xmloutput);
  804. end
  805. else
  806. begin
  807. J := 1;
  808. while J <= Length (More) do
  809. begin
  810. if J > 1 then
  811. Comment(V_Normal,''); (* Put empty line between multiple sections *)
  812. case More [J] of
  813. 'a': ListABITargets ('');
  814. 'b': Comment(V_Normal, cgbackend2str[cgbackend]);
  815. 'c': ListCPUInstructionSets ('');
  816. 'f': ListFPUInstructionSets ('');
  817. 'i': ListAsmModes ('');
  818. {$ifdef LLVM}
  819. 'l': ListLLVMVersions ('');
  820. {$endif LLVM}
  821. 'm': ListModeswitches ('');
  822. 'o': ListOptimizations ('');
  823. 'r': ListFeatures ('');
  824. 't': ListOSTargets ('');
  825. 'u': ListControllerTypes ('');
  826. 'w': ListWPOptimizations ('');
  827. else
  828. IllegalPara ('-i' + More);
  829. end;
  830. Inc (J);
  831. end;
  832. end;
  833. StopOptions(0);
  834. end;
  835. procedure Toption.WriteHelpPages;
  836. function PadEnd(s:string;i:longint):string;
  837. begin
  838. if length(s) >= i then
  839. S := S + ' '
  840. else
  841. while (length(s)<i) do
  842. s:=s+' ';
  843. PadEnd:=s;
  844. end;
  845. var
  846. lastident,
  847. j,outline,
  848. ident,
  849. HelpLineHeight,
  850. lines : longint;
  851. show : boolean;
  852. opt : string[32];
  853. input,
  854. HelpLine,
  855. s : string;
  856. p : pchar;
  857. msg_str: TMsgStr;
  858. begin
  859. WriteLogo;
  860. Lines:=4;
  861. if FPCHelpLines then
  862. Message1(option_usage,FixFileName(FPCBinaryPath))
  863. else
  864. Message1(option_usage,FixFileName(system.paramstr(0)));
  865. lastident:=0;
  866. msg_str:=MessageStr(option_help_pages);
  867. p:=pchar(msg_str);
  868. while assigned(p) do
  869. begin
  870. { get a line and reset }
  871. s:=GetMsgLine(p);
  872. ident:=0;
  873. show:=false;
  874. { parse options }
  875. case s[1] of
  876. 'F': if FPCHelpLines then
  877. Show := true;
  878. {$ifdef UNITALIASES}
  879. 'a',
  880. {$endif}
  881. {$ifdef EXTDEBUG}
  882. 'e',
  883. {$endif EXTDEBUG}
  884. {$ifdef i386}
  885. '3',
  886. {$endif}
  887. {$ifdef x86_64}
  888. '4',
  889. {$endif}
  890. {$ifdef m68k}
  891. '6',
  892. {$endif}
  893. {$ifdef i8086}
  894. '8',
  895. {$endif}
  896. {$ifdef aarch64}
  897. 'a',
  898. {$endif}
  899. {$ifdef arm}
  900. 'A',
  901. {$endif}
  902. {$ifdef mipsel}
  903. 'm',
  904. {$endif}
  905. {$ifdef mipseb}
  906. 'M',
  907. {$endif}
  908. {$ifdef powerpc}
  909. 'P',
  910. {$endif}
  911. {$ifdef powerpc64}
  912. 'p',
  913. {$endif}
  914. {$ifdef sparc}
  915. 'S',
  916. {$endif}
  917. {$ifdef sparc64}
  918. 's',
  919. {$endif}
  920. {$ifdef riscv32}
  921. 'R',
  922. {$endif}
  923. {$ifdef riscv64}
  924. 'r',
  925. {$endif}
  926. {$ifdef avr}
  927. 'V',
  928. {$endif}
  929. {$ifdef jvm}
  930. 'J',
  931. {$endif}
  932. {$ifdef llvm}
  933. 'L',
  934. {$endif}
  935. {$ifdef xtensa}
  936. 'x',
  937. {$endif}
  938. {$ifdef z80}
  939. 'Z',
  940. {$endif}
  941. {$ifdef wasm32}
  942. 'W',
  943. {$endif}
  944. {$ifdef loongarch64}
  945. 'l',
  946. {$endif}
  947. '*' : show:=true;
  948. end;
  949. if show then
  950. begin
  951. case s[2] of
  952. 'g',
  953. {$ifdef Unix}
  954. 'L',
  955. {$endif}
  956. {$ifdef os2}
  957. 'O',
  958. {$endif}
  959. '*' : show:=true;
  960. else
  961. show:=false;
  962. end;
  963. end;
  964. { now we may show the message or not }
  965. if show then
  966. begin
  967. case s[3] of
  968. '0' : begin
  969. ident:=0;
  970. outline:=0;
  971. end;
  972. '1' : begin
  973. ident:=2;
  974. outline:=7;
  975. end;
  976. '2' : begin
  977. ident:=6;
  978. outline:=11;
  979. end;
  980. '3' : begin
  981. ident:=9;
  982. outline:=11;
  983. end;
  984. else
  985. internalerror(2013112906);
  986. end;
  987. j:=pos('_',s);
  988. opt:=Copy(s,4,j-4);
  989. if opt='*' then
  990. opt:=''
  991. else
  992. if (opt=' ') or (opt[1]='@') then
  993. opt:=PadEnd(opt,outline)
  994. else
  995. opt:=PadEnd('-'+opt,outline);
  996. if (ident=0) and (lastident<>0) then
  997. begin
  998. Comment(V_Normal,'');
  999. inc(Lines);
  1000. end;
  1001. HelpLine := PadEnd('',ident)+opt+Copy(s,j+1,255);
  1002. if HelpLine = '' then
  1003. HelpLineHeight := 1
  1004. else
  1005. HelpLineHeight := Succ (CharLength (HelpLine) div Page_Width);
  1006. { page full ? }
  1007. if (lines + HelpLineHeight >= page_size - 1) then
  1008. begin
  1009. if not NoPressEnter then
  1010. begin
  1011. Message(option_help_press_enter);
  1012. readln(input);
  1013. if upper(input)='Q' then
  1014. StopOptions(0);
  1015. end;
  1016. lines:=0;
  1017. end;
  1018. Comment(V_Normal,HelpLine);
  1019. LastIdent:=Ident;
  1020. Inc (Lines, HelpLineHeight);
  1021. end;
  1022. end;
  1023. StopOptions(0);
  1024. end;
  1025. procedure Toption.IllegalPara(const opt:TCmdStr);
  1026. begin
  1027. Message1(option_illegal_para,opt);
  1028. Message(option_help_pages_para);
  1029. StopOptions(1);
  1030. end;
  1031. procedure toption.UnsupportedPara(const opt: TCmdStr);
  1032. begin
  1033. Message1(option_unsupported_target,opt);
  1034. StopOptions(1);
  1035. end;
  1036. procedure toption.IgnoredPara(const opt: TCmdStr);
  1037. begin
  1038. Message1(option_ignored_target,opt);
  1039. end;
  1040. procedure toption.ForceStaticLinking;
  1041. begin
  1042. def_system_macro('FPC_LINK_STATIC');
  1043. undef_system_macro('FPC_LINK_SMART');
  1044. undef_system_macro('FPC_LINK_DYNAMIC');
  1045. include(init_settings.globalswitches,cs_link_static);
  1046. exclude(init_settings.globalswitches,cs_link_smart);
  1047. exclude(init_settings.globalswitches,cs_link_shared);
  1048. LinkTypeSetExplicitly:=true;
  1049. end;
  1050. function toption.ParseMacVersionMin(out minversion, invalidateversion: tversion; const compvarname, value: string; ios: boolean): boolean;
  1051. function subval(start,maxlen: longint; out stop: longint): string;
  1052. var
  1053. i: longint;
  1054. begin
  1055. result:='';
  1056. i:=start;
  1057. while (i<=length(value)) and
  1058. (value[i] in ['0'..'9']) do
  1059. inc(i);
  1060. { sufficient amount of digits? }
  1061. if (i=start) or
  1062. (i-start>maxlen) then
  1063. exit;
  1064. result:=copy(value,start,i-start);
  1065. stop:=i;
  1066. end;
  1067. var
  1068. temp,
  1069. compvarvalue,
  1070. versionstr: string[15];
  1071. major, minor, patch: cardinal;
  1072. i, err: longint;
  1073. osx_minor_two_digits: boolean;
  1074. begin
  1075. invalidateversion.invalidate;
  1076. versionstr:=value;
  1077. MacVersionSet:=false;
  1078. { check whether the value is a valid version number }
  1079. if value='' then
  1080. begin
  1081. undef_system_macro(compvarname);
  1082. exit(true);
  1083. end;
  1084. { major version number }
  1085. compvarvalue:=subval(1,2,i);
  1086. { not enough digits -> invalid }
  1087. if compvarvalue='' then
  1088. exit(false);
  1089. { already end of string -> invalid }
  1090. if (i>=length(value)) or
  1091. (value[i]<>'.') then
  1092. exit(false);
  1093. val(compvarvalue,major,err);
  1094. if err<>0 then
  1095. exit(false);
  1096. { minor version number }
  1097. temp:=subval(i+1,2,i);
  1098. if temp='' then
  1099. exit(false);
  1100. val(temp,minor,err);
  1101. if err<>0 then
  1102. exit(false);
  1103. { on Mac OS X, the minor version number was originally limited to 1 digit;
  1104. with 10.10 the format changed and two digits were also supported; on iOS,
  1105. the minor version number always takes up two digits }
  1106. osx_minor_two_digits:=false;
  1107. if not ios then
  1108. begin
  1109. { if the minor version number is two digits on OS X (the case since
  1110. OS X 10.10), we also have to add two digits for the patch level}
  1111. if length(temp)=2 then
  1112. osx_minor_two_digits:=true;
  1113. end
  1114. { the minor version number always takes up two digits on iOS }
  1115. else if length(temp)=1 then
  1116. temp:='0'+temp;
  1117. compvarvalue:=compvarvalue+temp;
  1118. { optional patch level }
  1119. patch:=0;
  1120. if i<=length(value) then
  1121. begin
  1122. if value[i]<>'.' then
  1123. exit(false);
  1124. temp:=subval(i+1,2,i);
  1125. if temp='' then
  1126. exit(false);
  1127. { there's only room for a single digit patch level in the version macro
  1128. for Mac OS X. gcc sets it to zero if there are more digits, but that
  1129. seems worse than clamping to 9 (don't declare as invalid like with
  1130. minor version number, because there is a precedent like 10.4.11).
  1131. As of OS X 10.10 there are two digits for the patch level
  1132. }
  1133. if not ios and
  1134. not osx_minor_two_digits then
  1135. begin
  1136. if length(temp)<>1 then
  1137. temp:='9';
  1138. end
  1139. else
  1140. begin
  1141. { on iOS, the patch level is always two digits }
  1142. if length(temp)=1 then
  1143. temp:='0'+temp;
  1144. end;
  1145. compvarvalue:=compvarvalue+temp;
  1146. { must be the end }
  1147. if i<=length(value) then
  1148. exit(false);
  1149. val(temp,patch,err);
  1150. if err<>0 then
  1151. exit(false);
  1152. end
  1153. else if not ios and
  1154. not osx_minor_two_digits then
  1155. begin
  1156. compvarvalue:=compvarvalue+'0';
  1157. versionstr:=versionstr+'.0'
  1158. end
  1159. else
  1160. begin
  1161. compvarvalue:=compvarvalue+'00';
  1162. { command line versions still only use one 0 though }
  1163. versionstr:=versionstr+'.0'
  1164. end;
  1165. minversion.init(versionstr,major,minor,patch);
  1166. set_system_compvar(compvarname,compvarvalue);
  1167. MacVersionSet:=true;
  1168. result:=true;
  1169. end;
  1170. {$ifdef XTENSA}
  1171. function TOption.ParseVersionStr(out ver: longint;
  1172. const compvarname, value: string): boolean;
  1173. function subval(start,maxlen: longint; out stop: longint): string;
  1174. var
  1175. i: longint;
  1176. begin
  1177. result:='';
  1178. i:=start;
  1179. while (i<=length(value)) and
  1180. (value[i] in ['0'..'9']) do
  1181. inc(i);
  1182. { sufficient amount of digits? }
  1183. if (i=start) or
  1184. (i-start>maxlen) then
  1185. exit;
  1186. result:=copy(value,start,i-start);
  1187. stop:=i;
  1188. end;
  1189. var
  1190. temp,
  1191. compvarvalue: string[15];
  1192. i: longint;
  1193. begin
  1194. Result:=false;
  1195. IdfVersionSet:=false;
  1196. emptystr:='';
  1197. { check whether the value is a valid version number }
  1198. if value='' then
  1199. begin
  1200. undef_system_macro(compvarname);
  1201. exit(true);
  1202. end;
  1203. { major version number }
  1204. compvarvalue:=subval(1,2,i);
  1205. { not enough digits -> invalid }
  1206. if compvarvalue='' then
  1207. exit(false);
  1208. { already end of string -> invalid }
  1209. if (i>=length(value)) or
  1210. (value[i]<>'.') then
  1211. exit(false);
  1212. { minor version number }
  1213. temp:=subval(i+1,2,i);
  1214. if temp='' then
  1215. exit(false);
  1216. if length(temp)=1 then
  1217. temp:='0'+temp;
  1218. compvarvalue:=compvarvalue+temp;
  1219. { patch level }
  1220. if i<=length(value) then
  1221. begin
  1222. if value[i]<>'.' then
  1223. exit(false);
  1224. temp:=subval(i+1,2,i);
  1225. if temp='' then
  1226. exit(false);
  1227. if length(temp)=1 then
  1228. temp:='0'+temp;
  1229. compvarvalue:=compvarvalue+temp;
  1230. { must be the end }
  1231. if i<=length(value) then
  1232. exit(false);
  1233. end
  1234. else
  1235. begin
  1236. compvarvalue:=compvarvalue+'00';
  1237. end;
  1238. val(compvarvalue,idf_version,i);
  1239. if i=0 then
  1240. begin
  1241. set_system_compvar(compvarname,compvarvalue);
  1242. IdfVersionSet:=true;
  1243. result:=true;
  1244. end;
  1245. end;
  1246. {$endif XTENSA}
  1247. procedure TOption.MaybeSetDefaultMacVersionMacro;
  1248. var
  1249. envstr: ansistring;
  1250. begin
  1251. if not(target_info.system in systems_darwin) then
  1252. exit;
  1253. if MacVersionSet then
  1254. exit;
  1255. { check for deployment target set via environment variable }
  1256. if not(target_info.system in [system_i386_iphonesim,system_arm_ios,system_aarch64_ios,system_x86_64_iphonesim,system_aarch64_iphonesim]) then
  1257. begin
  1258. envstr:=GetEnvironmentVariable('MACOSX_DEPLOYMENT_TARGET');
  1259. if envstr<>'' then
  1260. if not ParseMacVersionMin(MacOSXVersionMin,iPhoneOSVersionMin,'MAC_OS_X_VERSION_MIN_REQUIRED',envstr,false) then
  1261. Message1(option_invalid_macosx_deployment_target,envstr)
  1262. else
  1263. begin
  1264. {$ifdef llvm}
  1265. { We only support libunwind as part of libsystem, which happened in Mac OS X 10.6 }
  1266. if MacOSXVersionMin.relationto(10,6,0)<0 then
  1267. Message1(option_invalid_macosx_deployment_target,envstr);
  1268. {$endif}
  1269. exit;
  1270. end;
  1271. end
  1272. else
  1273. begin
  1274. envstr:=GetEnvironmentVariable('IPHONEOS_DEPLOYMENT_TARGET');
  1275. if envstr<>'' then
  1276. if not ParseMacVersionMin(iPhoneOSVersionMin,MacOSXVersionMin,'IPHONE_OS_VERSION_MIN_REQUIRED',envstr,true) then
  1277. Message1(option_invalid_iphoneos_deployment_target,envstr)
  1278. else
  1279. exit;
  1280. end;
  1281. { nothing specified -> defaults }
  1282. case target_info.system of
  1283. system_powerpc_darwin:
  1284. begin
  1285. if not ParseMacVersionMin(MacOSXVersionMin,iPhoneOSVersionMin,'MAC_OS_X_VERSION_MIN_REQUIRED','10.3.0',false) then
  1286. internalerror(2022090910);
  1287. end;
  1288. system_powerpc64_darwin:
  1289. begin
  1290. if not ParseMacVersionMin(MacOSXVersionMin,iPhoneOSVersionMin,'MAC_OS_X_VERSION_MIN_REQUIRED','10.4.0',false) then
  1291. internalerror(2022090911);
  1292. end;
  1293. system_i386_darwin,
  1294. system_x86_64_darwin:
  1295. begin
  1296. if not ParseMacVersionMin(MacOSXVersionMin,iPhoneOSVersionMin,'MAC_OS_X_VERSION_MIN_REQUIRED','10.8.0',false) then
  1297. internalerror(2022090912);
  1298. end;
  1299. system_arm_ios,
  1300. system_i386_iphonesim:
  1301. begin
  1302. if not ParseMacVersionMin(iPhoneOSVersionMin,MacOSXVersionMin,'IPHONE_OS_VERSION_MIN_REQUIRED','9.0.0',false) then
  1303. internalerror(2022090913);
  1304. end;
  1305. system_aarch64_ios,
  1306. system_x86_64_iphonesim:
  1307. begin
  1308. if not ParseMacVersionMin(iPhoneOSVersionMin,MacOSXVersionMin,'IPHONE_OS_VERSION_MIN_REQUIRED','9.0.0',false) then
  1309. internalerror(2022090914);
  1310. end;
  1311. system_aarch64_iphonesim:
  1312. begin
  1313. if not ParseMacVersionMin(iPhoneOSVersionMin,MacOSXVersionMin,'IPHONE_OS_VERSION_MIN_REQUIRED','14.0.0',false) then
  1314. internalerror(2023032201);
  1315. end;
  1316. system_aarch64_darwin:
  1317. begin
  1318. if not ParseMacVersionMin(MacOSXVersionMin,iPhoneOSVersionMin,'MAC_OS_X_VERSION_MIN_REQUIRED','11.0.0',false) then
  1319. internalerror(2022090915);
  1320. end
  1321. else
  1322. internalerror(2012031001);
  1323. end;
  1324. end;
  1325. {$ifdef llvm}
  1326. procedure TOption.LLVMEnableSanitizers(sanitizers: TCmdStr);
  1327. var
  1328. sanitizer: TCMdStr;
  1329. begin
  1330. sanitizer:=GetToken(sanitizers,',');
  1331. repeat
  1332. case sanitizer of
  1333. 'address':
  1334. include(init_settings.moduleswitches,cs_sanitize_address);
  1335. else
  1336. IllegalPara(sanitizer);
  1337. end;
  1338. sanitizer:=GetToken(sanitizers,',');
  1339. until sanitizer='';
  1340. end;
  1341. {$endif}
  1342. {$ifdef XTENSA}
  1343. procedure TOption.MaybeSetIdfVersionMacro;
  1344. begin
  1345. if not(target_info.system=system_xtensa_freertos) then
  1346. exit;
  1347. if IdfVersionSet then
  1348. exit;
  1349. { nothing specified -> defaults }
  1350. case current_settings.controllertype of
  1351. ct_esp8266:
  1352. begin
  1353. set_system_compvar('IDF_VERSION','30300');
  1354. idf_version:=30300;
  1355. end;
  1356. ct_esp32:
  1357. begin
  1358. set_system_compvar('IDF_VERSION','40200');
  1359. idf_version:=40200;
  1360. end;
  1361. else
  1362. begin
  1363. set_system_compvar('IDF_VERSION','00000');
  1364. idf_version:=0;
  1365. end;
  1366. end;
  1367. end;
  1368. {$endif XTENSA}
  1369. procedure TOption.VerifyTargetProcessor;
  1370. begin
  1371. { no custom target processor specified -> ok }
  1372. if processorstr='' then
  1373. exit;
  1374. { custom target processor specified -> verify it's the one we support }
  1375. if upcase(processorstr)<>upcase(target_cpu_string) then
  1376. Message1(option_invalid_target_architecture,processorstr);
  1377. end;
  1378. function Toption.Unsetbool(var Opts:TCmdStr; Pos: Longint; const FullPara: TCmdStr; RequireBoolPara: boolean):boolean;
  1379. { checks if the character after pos in Opts is a + or a - and returns resp.
  1380. false or true. If it is another character (or none), it also returns false }
  1381. begin
  1382. UnsetBool := false;
  1383. if Length(Opts)>Pos then
  1384. begin
  1385. inc(Pos);
  1386. UnsetBool := Opts[Pos] = '-';
  1387. if Opts[Pos] in ['-','+']then
  1388. delete(Opts,Pos,1)
  1389. else if RequireBoolPara then
  1390. IllegalPara(FullPara);
  1391. end;
  1392. end;
  1393. procedure TOption.interpret_option(const opt:TCmdStr;ispara:boolean);
  1394. var
  1395. code : integer;
  1396. c : char;
  1397. {$ifdef cpucapabilities}
  1398. cf : tcpuflags;
  1399. cpuflagsstr,
  1400. extrasettings,
  1401. {$endif cpucapabilities}
  1402. more : TCmdStr;
  1403. major,minor : longint;
  1404. error : integer;
  1405. j,l , deletepos: longint;
  1406. d,s : TCmdStr;
  1407. hs : TCmdStr;
  1408. unicodemapping : punicodemap;
  1409. includecapability: Boolean;
  1410. {$ifdef llvm}
  1411. disable: boolean;
  1412. {$endif}
  1413. begin
  1414. if opt='' then
  1415. exit;
  1416. { only parse define,undef,target,verbosity,link etc options the firsttime
  1417. -Us must now also be first-passed to avoid rejection of -Sf options
  1418. earlier in command line }
  1419. if firstpass and
  1420. not(
  1421. (opt[1]='-') and
  1422. (
  1423. ((length(opt)>1) and (opt[2] in ['i','d','v','T','t','u','n','x','X','l','U'])) or
  1424. ((length(opt)>3) and (opt[2]='F') and (opt[3]='e')) or
  1425. ((length(opt)>2) and (opt[2]='C') and (opt[3] in ['a','b','f','p'])) or
  1426. ((length(opt)>3) and (opt[2]='W') and (opt[3] in ['m','p']))
  1427. )
  1428. ) then
  1429. exit;
  1430. Message1(option_handling_option,opt);
  1431. case opt[1] of
  1432. '-' :
  1433. begin
  1434. more:=Copy(opt,3,2147483647);
  1435. if firstpass then
  1436. Message1(option_interpreting_firstpass_option,opt)
  1437. else
  1438. Message1(option_interpreting_option,opt);
  1439. case opt[2] of
  1440. '?' :
  1441. begin
  1442. if (More <> '') and (More [1] = 'F') then
  1443. begin
  1444. FPCHelpLines := true;
  1445. Delete (More, 1, 1);
  1446. FPCBinaryPath := More;
  1447. end;
  1448. WriteHelpPages;
  1449. end;
  1450. 'a' :
  1451. begin
  1452. include(init_settings.globalswitches,cs_asm_leave);
  1453. j:=1;
  1454. while j<=length(more) do
  1455. begin
  1456. case more[j] of
  1457. '5' :
  1458. if (target_info.system in systems_all_windows+systems_nativent-[system_i8086_win16])
  1459. or (target_info.cpu in [cpu_mipseb, cpu_mipsel]) then
  1460. begin
  1461. if UnsetBool(More, j, opt, false) then
  1462. exclude(init_settings.globalswitches,cs_asm_pre_binutils_2_25)
  1463. else
  1464. include(init_settings.globalswitches,cs_asm_pre_binutils_2_25);
  1465. end
  1466. else
  1467. IllegalPara(opt);
  1468. 'l' :
  1469. include(init_settings.globalswitches,cs_asm_source);
  1470. 'r' :
  1471. include(init_settings.globalswitches,cs_asm_regalloc);
  1472. 'R' :
  1473. include(init_settings.globalswitches,cs_asm_rtti_source);
  1474. 't' :
  1475. include(init_settings.globalswitches,cs_asm_tempalloc);
  1476. 'n' :
  1477. include(init_settings.globalswitches,cs_asm_nodes);
  1478. { -ao option must be the last, everything behind it is passed directly to
  1479. external assembler, it is ignored if internal assembler is used. }
  1480. 'o' :
  1481. begin
  1482. asmextraopt:=copy(more,j+1,length(more)-j);
  1483. break;
  1484. end;
  1485. 'p' :
  1486. begin
  1487. exclude(init_settings.globalswitches,cs_asm_leave);
  1488. if UnsetBool(More, 0, opt, false) then
  1489. exclude(init_settings.globalswitches,cs_asm_pipe)
  1490. else
  1491. include(init_settings.globalswitches,cs_asm_pipe);
  1492. end;
  1493. '-' :
  1494. init_settings.globalswitches:=init_settings.globalswitches -
  1495. [cs_asm_leave, cs_asm_source,cs_asm_regalloc, cs_asm_tempalloc,
  1496. cs_asm_nodes, cs_asm_pipe];
  1497. else
  1498. IllegalPara(opt);
  1499. end;
  1500. inc(j);
  1501. end;
  1502. end;
  1503. 'A' :
  1504. begin
  1505. if CompareText(More,'DEFAULT') = 0 then
  1506. paratargetasm:=as_default
  1507. else
  1508. paratargetasm:=find_asm_by_string(More);
  1509. if paratargetasm=as_none then
  1510. IllegalPara(opt);
  1511. end;
  1512. 'b' :
  1513. begin
  1514. // Message1(option_obsolete_switch,'-b');
  1515. if UnsetBool(More,0,opt,false) then
  1516. begin
  1517. init_settings.moduleswitches:=init_settings.moduleswitches-[cs_browser];
  1518. init_settings.moduleswitches:=init_settings.moduleswitches-[cs_local_browser];
  1519. end
  1520. else
  1521. begin
  1522. init_settings.moduleswitches:=init_settings.moduleswitches+[cs_browser];
  1523. end;
  1524. if More<>'' then
  1525. if (More='l') or (More='l+') then
  1526. init_settings.moduleswitches:=init_settings.moduleswitches+[cs_local_browser]
  1527. else if More='l-' then
  1528. init_settings.moduleswitches:=init_settings.moduleswitches-[cs_local_browser]
  1529. else
  1530. IllegalPara(opt);
  1531. end;
  1532. 'B' :
  1533. do_build:=not UnSetBool(more,0,opt,true);
  1534. 'C' :
  1535. begin
  1536. j:=1;
  1537. while j<=length(more) do
  1538. begin
  1539. case more[j] of
  1540. '3' :
  1541. If UnsetBool(More, j, opt, false) then
  1542. exclude(init_settings.localswitches,cs_ieee_errors)
  1543. Else
  1544. include(init_settings.localswitches,cs_ieee_errors);
  1545. 'a' :
  1546. begin
  1547. s:=upper(copy(more,j+1,length(more)-j));
  1548. if not(SetAbiType(s,target_info.abi)) then
  1549. IllegalPara(opt);
  1550. ABISetExplicitly:=true;
  1551. break;
  1552. end;
  1553. 'b' :
  1554. begin
  1555. if UnsetBool(More, j, opt, false) then
  1556. target_info.endian:=endian_little
  1557. else
  1558. target_info.endian:=endian_big;
  1559. set_endianess_macros;
  1560. end;
  1561. 'c' :
  1562. begin
  1563. if not SetAktProcCall(upper(copy(more,j+1,length(more)-j)),init_settings.defproccall) then
  1564. IllegalPara(opt);
  1565. break;
  1566. end;
  1567. {$ifdef cpufpemu}
  1568. 'e' :
  1569. begin
  1570. If UnsetBool(More, j, opt, false) then
  1571. exclude(init_settings.moduleswitches,cs_fp_emulation)
  1572. Else
  1573. include(init_settings.moduleswitches,cs_fp_emulation);
  1574. end;
  1575. {$endif cpufpemu}
  1576. 'E' :
  1577. If UnsetBool(More, j, opt, false) then
  1578. exclude(init_settings.localswitches,cs_check_fpu_exceptions)
  1579. Else
  1580. include(init_settings.localswitches,cs_check_fpu_exceptions);
  1581. 'f' :
  1582. begin
  1583. s:=upper(copy(more,j+1,length(more)-j));
  1584. if not(SetFpuType(s,init_settings.fputype)) then
  1585. IllegalPara(opt);
  1586. FPUSetExplicitly:=True;
  1587. break;
  1588. end;
  1589. 'F' :
  1590. begin
  1591. if not SetMinFPConstPrec(copy(more,j+1,length(more)-j),init_settings.minfpconstprec) then
  1592. IllegalPara(opt);
  1593. break;
  1594. end;
  1595. 'g' :
  1596. begin
  1597. if tf_no_pic_supported in target_info.flags then
  1598. begin
  1599. { consume a possible '-' coming after it }
  1600. UnsetBool(More, j, opt, false);
  1601. message(scan_w_pic_ignored);
  1602. end
  1603. else if UnsetBool(More, j, opt, false) then
  1604. exclude(init_settings.moduleswitches,cs_create_pic)
  1605. else
  1606. include(init_settings.moduleswitches,cs_create_pic);
  1607. end;
  1608. 'h' :
  1609. begin
  1610. l:=pos(',',copy(more,j+1,length(more)-j));
  1611. if l=0 then
  1612. l:=length(more)-j+1;
  1613. val(copy(more,j+1,l-1),heapsize,code);
  1614. if (code<>0)
  1615. {$ifdef AVR}
  1616. or (heapsize<32)
  1617. {$else AVR}
  1618. or (heapsize<1024)
  1619. {$endif AVR}
  1620. then
  1621. IllegalPara(opt)
  1622. else if l<=length(more)-j then
  1623. begin
  1624. val(copy(more,j+l+1,length(more)),maxheapsize,code);
  1625. if code<>0 then
  1626. IllegalPara(opt)
  1627. else if (maxheapsize<heapsize) then
  1628. begin
  1629. message(scan_w_heapmax_lessthan_heapmin);
  1630. maxheapsize:=heapsize;
  1631. end;
  1632. end;
  1633. break;
  1634. end;
  1635. 'i' :
  1636. If UnsetBool(More, j, opt, false) then
  1637. exclude(init_settings.localswitches,cs_check_io)
  1638. else
  1639. include(init_settings.localswitches,cs_check_io);
  1640. {$ifdef arm}
  1641. 'I' :
  1642. begin
  1643. if (upper(copy(more,j+1,length(more)-j))='THUMB') and
  1644. { does selected CPU really understand thumb? }
  1645. (init_settings.cputype in cpu_has_thumb) then
  1646. init_settings.instructionset:=is_thumb
  1647. else if upper(copy(more,j+1,length(more)-j))='ARM' then
  1648. init_settings.instructionset:=is_arm
  1649. else
  1650. IllegalPara(opt);
  1651. break;
  1652. end;
  1653. {$endif arm}
  1654. {$ifdef llvm}
  1655. 'l':
  1656. begin
  1657. l:=j+1;
  1658. while l<=length(More) do
  1659. begin
  1660. case More[l] of
  1661. 'f':
  1662. begin
  1663. delete(More,1,l);
  1664. disable:=Unsetbool(More,length(More)-1,opt,false);
  1665. case More of
  1666. 'lto':
  1667. begin
  1668. if not disable then
  1669. begin
  1670. include(init_settings.moduleswitches,cs_lto);
  1671. LTOExt:='.bc';
  1672. end
  1673. else
  1674. exclude(init_settings.moduleswitches,cs_lto);
  1675. end;
  1676. 'ltonosystem':
  1677. begin
  1678. if not disable then
  1679. begin
  1680. include(init_settings.globalswitches,cs_lto_nosystem);
  1681. end
  1682. else
  1683. exclude(init_settings.globalswitches,cs_lto_nosystem);
  1684. end;
  1685. else if More.StartsWith('sanitize=') then
  1686. begin
  1687. delete(More,1,length('sanitize='));
  1688. LLVMEnableSanitizers(more);
  1689. end
  1690. else
  1691. begin
  1692. IllegalPara(opt);
  1693. end;
  1694. end;
  1695. l:=length(more)+1;
  1696. end;
  1697. 'v':
  1698. begin
  1699. init_settings.llvmversion:=llvmversion2enum(copy(More,l+1,length(More)));
  1700. if init_settings.llvmversion=llvmver_invalid then
  1701. begin
  1702. IllegalPara(opt);
  1703. end;
  1704. l:=length(More)+1;
  1705. end
  1706. else
  1707. begin
  1708. IllegalPara(opt);
  1709. end;
  1710. end;
  1711. end;
  1712. j:=l;
  1713. end;
  1714. {$endif llvm}
  1715. 'n' :
  1716. If UnsetBool(More, j, opt, false) then
  1717. exclude(init_settings.globalswitches,cs_link_nolink)
  1718. Else
  1719. include(init_settings.globalswitches,cs_link_nolink);
  1720. 'N' :
  1721. If UnsetBool(More, j, opt, false) then
  1722. exclude(init_settings.localswitches,cs_check_low_addr_load)
  1723. Else
  1724. include(init_settings.localswitches,cs_check_low_addr_load);
  1725. 'o' :
  1726. If UnsetBool(More, j, opt, false) then
  1727. exclude(init_settings.localswitches,cs_check_overflow)
  1728. Else
  1729. include(init_settings.localswitches,cs_check_overflow);
  1730. 'O' :
  1731. If UnsetBool(More, j, opt, false) then
  1732. exclude(init_settings.localswitches,cs_check_ordinal_size)
  1733. Else
  1734. include(init_settings.localswitches,cs_check_ordinal_size);
  1735. 'p' :
  1736. begin
  1737. s:=upper(copy(more,j+1,length(more)-j));
  1738. {$ifdef cpucapabilities}
  1739. { find first occurrence of + or - }
  1740. deletepos:=PosCharset(['+','-'],s);
  1741. if deletepos<>0 then
  1742. begin
  1743. extrasettings:=Copy(s,deletepos,Length(s));
  1744. Delete(s,deletepos,Length(s));
  1745. end
  1746. else
  1747. extrasettings:='';
  1748. {$endif cpucapabilities}
  1749. if not(Setcputype(s,init_settings)) then
  1750. IllegalPara(opt);
  1751. {$ifdef cpucapabilities}
  1752. while extrasettings<>'' do
  1753. begin
  1754. Delete(extrasettings,1,1);
  1755. includecapability:=true;
  1756. deletepos:=PosCharset(['+','-'],extrasettings);
  1757. if deletepos<>0 then
  1758. begin
  1759. includecapability:=extrasettings[deletepos]='+';
  1760. s:=Copy(extrasettings,1,deletepos-1);
  1761. Delete(extrasettings,1,deletepos-1);
  1762. end
  1763. else
  1764. begin
  1765. s:=extrasettings;
  1766. extrasettings:='';
  1767. end;
  1768. for cf in tcpuflags do
  1769. begin
  1770. Str(cf,cpuflagsstr);
  1771. { expect that the cpuflagsstr i.e. the enum as well contains _HAS_ }
  1772. if Pos('_HAS_',cpuflagsstr)<>0 then
  1773. { get rid of prefix including _HAS_ }
  1774. Delete(cpuflagsstr,1,Pos('_HAS_',cpuflagsstr)+4)
  1775. else
  1776. Internalerror(2021110601);
  1777. if s=cpuflagsstr then
  1778. begin
  1779. if includecapability then
  1780. Include(cpu_capabilities[init_settings.cputype],cf)
  1781. else
  1782. Exclude(cpu_capabilities[init_settings.cputype],cf);
  1783. s:='';
  1784. break;
  1785. end;
  1786. end;
  1787. if s<>'' then
  1788. IllegalPara(opt);
  1789. end;
  1790. {$endif cpucapabilities}
  1791. CPUSetExplicitly:=true;
  1792. break;
  1793. end;
  1794. 'P':
  1795. begin
  1796. delete(more,1,1);
  1797. case upper(copy(more,1,pos('=',more)-1)) of
  1798. 'PACKSET':
  1799. begin
  1800. delete(more,1,pos('=',more));
  1801. case more of
  1802. '0','DEFAULT','NORMAL':
  1803. init_settings.setalloc:=0;
  1804. '1','2','4','8':
  1805. init_settings.setalloc:=StrToInt(more);
  1806. else
  1807. IllegalPara(opt);
  1808. end
  1809. end;
  1810. 'PACKENUM':
  1811. begin
  1812. delete(more,1,pos('=',more));
  1813. case more of
  1814. '0','DEFAULT','NORMAL':
  1815. init_settings.packenum:=4;
  1816. '1','2','4':
  1817. init_settings.packenum:=StrToInt(more);
  1818. else
  1819. IllegalPara(opt);
  1820. end;
  1821. end;
  1822. 'PACKRECORD':
  1823. begin
  1824. delete(more,1,pos('=',more));
  1825. case more of
  1826. '0','DEFAULT','NORMAL':
  1827. init_settings.packrecords:=default_settings.packrecords;
  1828. '1','2','4','8','16','32':
  1829. init_settings.packrecords:=StrToInt(more);
  1830. else
  1831. IllegalPara(opt);
  1832. end;
  1833. end
  1834. else
  1835. IllegalPara(opt);
  1836. end;
  1837. end;
  1838. 'r' :
  1839. If UnsetBool(More, j, opt, false) then
  1840. exclude(init_settings.localswitches,cs_check_range)
  1841. Else
  1842. include(init_settings.localswitches,cs_check_range);
  1843. 'R' :
  1844. If UnsetBool(More, j, opt, false) then
  1845. begin
  1846. exclude(init_settings.localswitches,cs_check_range);
  1847. exclude(init_settings.localswitches,cs_check_object);
  1848. end
  1849. Else
  1850. begin
  1851. include(init_settings.localswitches,cs_check_range);
  1852. include(init_settings.localswitches,cs_check_object);
  1853. end;
  1854. 's' :
  1855. begin
  1856. val(copy(more,j+1,length(more)-j),stacksize,code);
  1857. if (code<>0)
  1858. {$ifdef cpu16bitaddr}
  1859. or (stacksize>=65521)
  1860. {$else cpu16bitaddr}
  1861. or (stacksize>=67107840)
  1862. {$endif cpu16bitaddr}
  1863. or (stacksize<1024) then
  1864. IllegalPara(opt);
  1865. break;
  1866. end;
  1867. 't' :
  1868. If UnsetBool(More, j, opt, false) then
  1869. exclude(init_settings.localswitches,cs_check_stack)
  1870. Else
  1871. include(init_settings.localswitches,cs_check_stack);
  1872. 'D' :
  1873. If UnsetBool(More, j, opt, false) then
  1874. exclude(init_settings.moduleswitches,cs_create_dynamic)
  1875. Else
  1876. include(init_settings.moduleswitches,cs_create_dynamic);
  1877. 'X' :
  1878. If UnsetBool(More, j, opt, false) then
  1879. exclude(init_settings.moduleswitches,cs_create_smart)
  1880. Else
  1881. include(init_settings.moduleswitches,cs_create_smart);
  1882. 'T' :
  1883. begin
  1884. if not UpdateTargetSwitchStr(copy(more,j+1,length(more)),init_settings.targetswitches,true) then
  1885. IllegalPara(opt);
  1886. break;
  1887. end;
  1888. 'v' :
  1889. If target_info.system in systems_jvm then
  1890. If UnsetBool(More, j, opt, false) then
  1891. exclude(init_settings.localswitches,cs_check_var_copyout)
  1892. Else
  1893. include(init_settings.localswitches,cs_check_var_copyout)
  1894. else
  1895. IllegalPara(opt);
  1896. 'V':
  1897. begin
  1898. s:=upper(copy(more,j+1,length(more)-j));
  1899. if s='GLOBAL-DYNAMIC' then
  1900. init_settings.tlsmodel:=tlsm_global_dynamic
  1901. else if s='LOCAL-EXEC' then
  1902. init_settings.tlsmodel:=tlsm_local_exec
  1903. else
  1904. IllegalPara(opt);
  1905. break;
  1906. end;
  1907. else
  1908. IllegalPara(opt);
  1909. end;
  1910. inc(j);
  1911. end;
  1912. end;
  1913. 'd' :
  1914. begin
  1915. l:=Pos(':=',more);
  1916. DefaultReplacements(more);
  1917. if l>0 then
  1918. hs:=copy(more,1,l-1)
  1919. else
  1920. hs:=more;
  1921. if (not is_identifier(hs)) then
  1922. begin
  1923. if hs='' then
  1924. Message1(option_missing_arg,'-d')
  1925. else
  1926. Message1(option_malformed_para,opt);
  1927. StopOptions(1);
  1928. end;
  1929. if l>0 then
  1930. begin
  1931. if cs_support_macro in init_settings.moduleswitches then
  1932. set_system_macro(hs,Copy(more,l+2,255))
  1933. else
  1934. set_system_compvar(hs,Copy(more,l+2,255));
  1935. end
  1936. else
  1937. def_system_macro(hs);
  1938. end;
  1939. 'D' :
  1940. begin
  1941. j:=1;
  1942. while j<=length(more) do
  1943. begin
  1944. case more[j] of
  1945. 'd' :
  1946. begin
  1947. include(init_settings.globalswitches,cs_link_deffile);
  1948. description:=Copy(more,j+1,255);
  1949. break;
  1950. end;
  1951. 'D' :
  1952. begin
  1953. datestr:=Copy(more,j+1,255);
  1954. break;
  1955. end;
  1956. 'T' :
  1957. begin
  1958. timestr:=Copy(more,j+1,255);
  1959. break;
  1960. end;
  1961. 'v' :
  1962. begin
  1963. include(init_settings.globalswitches,cs_link_deffile);
  1964. dllversion:=Copy(more,j+1,255);
  1965. l:=pos('.',dllversion);
  1966. dllminor:=0;
  1967. error:=0;
  1968. if l>0 then
  1969. begin
  1970. val(copy(dllversion,l+1,255),minor,error);
  1971. if (error=0) and
  1972. (minor>=0) and (minor<=$ffff) then
  1973. dllminor:=minor
  1974. else
  1975. if error=0 then
  1976. error:=1;
  1977. end;
  1978. if l=0 then
  1979. l:=256;
  1980. dllmajor:=1;
  1981. major:=0;
  1982. if error=0 then
  1983. val(copy(dllversion,1,l-1),major,error);
  1984. if (error=0) and (major>=0) and (major<=$ffff) then
  1985. dllmajor:=major
  1986. else
  1987. if error=0 then
  1988. error:=1;
  1989. if error<>0 then
  1990. Message1(scan_w_wrong_version_ignored,dllversion);
  1991. break;
  1992. end;
  1993. 'w' :
  1994. begin
  1995. include(init_settings.globalswitches,cs_link_deffile);
  1996. usewindowapi:=true;
  1997. end;
  1998. '-' :
  1999. begin
  2000. exclude(init_settings.globalswitches,cs_link_deffile);
  2001. usewindowapi:=false;
  2002. end;
  2003. else
  2004. IllegalPara(opt);
  2005. end;
  2006. inc(j);
  2007. end;
  2008. end;
  2009. 'e' :
  2010. exepath:=FixPath(More,true);
  2011. 'E' :
  2012. begin
  2013. if UnsetBool(More, 0, opt, true) then
  2014. exclude(init_settings.globalswitches,cs_link_nolink)
  2015. else
  2016. include(init_settings.globalswitches,cs_link_nolink);
  2017. end;
  2018. 'f' :
  2019. begin
  2020. if more='PIC' then
  2021. begin
  2022. if tf_no_pic_supported in target_info.flags then
  2023. message(scan_w_pic_ignored)
  2024. else
  2025. include(init_settings.moduleswitches,cs_create_pic)
  2026. end
  2027. else
  2028. IllegalPara(opt);
  2029. end;
  2030. 'F' :
  2031. begin
  2032. if more='' then
  2033. IllegalPara(opt);
  2034. c:=more[1];
  2035. Delete(more,1,1);
  2036. DefaultReplacements(More);
  2037. case c of
  2038. 'a' :
  2039. autoloadunits:=more;
  2040. 'c' :
  2041. begin
  2042. { if we first specify that the system code page should be
  2043. used and then explicitly specify a code page, unset the
  2044. flag that we're using the system code page again }
  2045. SetCompileModeSwitch('SYSTEMCODEPAGE-',true);
  2046. if (upper(more)='UTF8') or (upper(more)='UTF-8') then
  2047. init_settings.sourcecodepage:=CP_UTF8
  2048. else if not(cpavailable(more)) then
  2049. Message1(option_code_page_not_available,more)
  2050. else
  2051. init_settings.sourcecodepage:=codepagebyname(more);
  2052. include(init_settings.moduleswitches,cs_explicit_codepage);
  2053. end;
  2054. 'C' :
  2055. RCCompiler:=More;
  2056. 'd' :
  2057. if UnsetBool(more, 0, opt, true) then
  2058. init_settings.disabledircache:=false
  2059. else
  2060. init_settings.disabledircache:=true;
  2061. 'D' :
  2062. utilsdirectory:=FixPath(More,true);
  2063. 'e' :
  2064. SetRedirectFile(More);
  2065. 'E' :
  2066. OutputExeDir:=FixPath(More,true);
  2067. 'f' :
  2068. if (target_info.system in systems_darwin) then
  2069. if ispara then
  2070. ParaFrameworkPath.AddPath(More,false)
  2071. else
  2072. frameworksearchpath.AddPath(More,true)
  2073. {$if defined(XTENSA) or defined(RISCV32)}
  2074. else if (target_info.system=system_xtensa_freertos) then
  2075. idfpath:=FixPath(More,true)
  2076. {$endif defined(XTENSA) or defined(RISCV32)}
  2077. else
  2078. IllegalPara(opt);
  2079. 'F' :
  2080. RCForceFPCRes:=true;
  2081. 'i' :
  2082. begin
  2083. if ispara then
  2084. ParaIncludePath.AddPath(More,false)
  2085. else
  2086. includesearchpath.AddPath(More,true);
  2087. end;
  2088. 'm' :
  2089. begin
  2090. s:=ExtractFileDir(more);
  2091. if TryStrToInt(ExtractFileName(more),j) then
  2092. begin
  2093. unicodemapping:=loadunicodemapping(More,More+'.txt',j);
  2094. if assigned(unicodemapping) then
  2095. registermapping(unicodemapping)
  2096. else
  2097. IllegalPara(opt);
  2098. end
  2099. else
  2100. IllegalPara(opt);
  2101. end;
  2102. 'M' :
  2103. unicodepath:=FixPath(More,true);
  2104. 'g' :
  2105. Message2(option_obsolete_switch_use_new,'-Fg','-Fl');
  2106. 'l' :
  2107. begin
  2108. if ispara then
  2109. ParaLibraryPath.AddLibraryPath(sysrootpath,More,false)
  2110. else
  2111. LibrarySearchPath.AddLibraryPath(sysrootpath,More,true)
  2112. end;
  2113. 'L' :
  2114. begin
  2115. if More<>'' then
  2116. ParaDynamicLinker:=More
  2117. else
  2118. IllegalPara(opt);
  2119. end;
  2120. 'N' :
  2121. begin
  2122. if more<>'' then
  2123. paranamespaces.insert(more)
  2124. else
  2125. illegalpara(opt);
  2126. end;
  2127. 'o' :
  2128. begin
  2129. if ispara then
  2130. ParaObjectPath.AddPath(More,false)
  2131. else
  2132. ObjectSearchPath.AddPath(More,true);
  2133. end;
  2134. 'P' :
  2135. begin
  2136. if ispara then
  2137. parapackages.add(more,nil)
  2138. else
  2139. add_package(more,true,true);
  2140. end;
  2141. 'p' :
  2142. begin
  2143. if ispara then
  2144. parapackagepath.AddPath(More,false)
  2145. else
  2146. packagesearchpath.AddPath(More,true);
  2147. end;
  2148. 'r' :
  2149. Msgfilename:=More;
  2150. 'R' :
  2151. ResCompiler:=More;
  2152. 'u' :
  2153. begin
  2154. if ispara then
  2155. ParaUnitPath.AddPath(More,false)
  2156. else
  2157. unitsearchpath.AddPath(More,true);
  2158. end;
  2159. 'U' :
  2160. OutputUnitDir:=FixPath(More,true);
  2161. 'W',
  2162. 'w':
  2163. begin
  2164. if More<>'' then
  2165. begin
  2166. DefaultReplacements(More);
  2167. D:=ExtractFilePath(More);
  2168. if (D<>'') then
  2169. D:=FixPath(D,True);
  2170. D:=D+ExtractFileName(More);
  2171. if (c='W') then
  2172. WpoFeedbackOutput:=D
  2173. else
  2174. WpoFeedbackInput:=D;
  2175. end
  2176. else
  2177. IllegalPara(opt);
  2178. end;
  2179. else
  2180. IllegalPara(opt);
  2181. end;
  2182. end;
  2183. 'g' :
  2184. begin
  2185. if UnsetBool(More, 0, opt, false) then
  2186. begin
  2187. exclude(init_settings.moduleswitches,cs_debuginfo);
  2188. exclude(init_settings.globalswitches,cs_use_heaptrc);
  2189. exclude(init_settings.globalswitches,cs_use_lineinfo);
  2190. exclude(init_settings.localswitches,cs_checkpointer);
  2191. paratargetdbg:=dbg_none;
  2192. localvartrashing := -1;
  2193. end
  2194. else
  2195. begin
  2196. include(init_settings.moduleswitches,cs_debuginfo);
  2197. if paratargetdbg=dbg_none then
  2198. paratargetdbg:=target_info.dbg;
  2199. end;
  2200. if not RelocSectionSetExplicitly then
  2201. RelocSection:=false;
  2202. j:=1;
  2203. while j<=length(more) do
  2204. begin
  2205. case more[j] of
  2206. 'c' :
  2207. begin
  2208. if UnsetBool(More, j, opt, false) then
  2209. exclude(init_settings.localswitches,cs_checkpointer)
  2210. else if (target_info.system in systems_support_checkpointer) then
  2211. begin
  2212. if do_release then
  2213. Message(option_gc_incompatible_with_release_flag)
  2214. else
  2215. include(init_settings.localswitches,cs_checkpointer);
  2216. end
  2217. else
  2218. UnsupportedPara('-gc');
  2219. end;
  2220. 'h' :
  2221. begin
  2222. if UnsetBool(More, j, opt, false) then
  2223. exclude(init_settings.globalswitches,cs_use_heaptrc)
  2224. else
  2225. begin
  2226. if cs_gdb_valgrind in init_settings.globalswitches then
  2227. Message2(option_valgrind_heaptrc_mismatch,'-gh', '-gv');
  2228. include(init_settings.globalswitches,cs_use_heaptrc);
  2229. end;
  2230. end;
  2231. 'l' :
  2232. begin
  2233. if UnsetBool(More, j, opt, false) then
  2234. exclude(init_settings.globalswitches,cs_use_lineinfo)
  2235. else
  2236. include(init_settings.globalswitches,cs_use_lineinfo);
  2237. end;
  2238. 'm' :
  2239. begin
  2240. paratargetdbg:=dbg_codeview;
  2241. end;
  2242. 'o' :
  2243. begin
  2244. if not UpdateDebugStr(copy(more,j+1,length(more)),init_settings.debugswitches) then
  2245. IllegalPara(opt);
  2246. break;
  2247. end;
  2248. 'p' :
  2249. begin
  2250. if UnsetBool(More, j, opt, false) then
  2251. exclude(init_settings.globalswitches,cs_stabs_preservecase)
  2252. else
  2253. include(init_settings.globalswitches,cs_stabs_preservecase);
  2254. end;
  2255. 's' :
  2256. begin
  2257. paratargetdbg:=dbg_stabs;
  2258. end;
  2259. 't' :
  2260. begin
  2261. if UnsetBool(More, j, opt, false) then
  2262. localvartrashing := -1
  2263. else
  2264. localvartrashing := (localvartrashing + 1) mod nroftrashvalues;
  2265. end;
  2266. 'v' :
  2267. begin
  2268. if UnsetBool(More, j, opt, false) then
  2269. exclude(init_settings.globalswitches,cs_gdb_valgrind)
  2270. else
  2271. begin
  2272. if cs_use_heaptrc in init_settings.globalswitches then
  2273. Message2(option_valgrind_heaptrc_mismatch,'-gh', '-gv');
  2274. include(init_settings.globalswitches,cs_gdb_valgrind);
  2275. end;
  2276. end;
  2277. 'w' :
  2278. begin
  2279. if (j<length(more)) and (more[j+1] in ['2','3','4']) then
  2280. begin
  2281. case more[j+1] of
  2282. '2': paratargetdbg:=dbg_dwarf2;
  2283. '3': paratargetdbg:=dbg_dwarf3;
  2284. '4': paratargetdbg:=dbg_dwarf4;
  2285. end;
  2286. inc(j);
  2287. end
  2288. else
  2289. paratargetdbg:=dbg_dwarf2;
  2290. end;
  2291. else
  2292. IllegalPara(opt);
  2293. end;
  2294. inc(j);
  2295. end;
  2296. end;
  2297. 'h' :
  2298. begin
  2299. NoPressEnter:=true;
  2300. if (More <> '') and (More [1] = 'F') then
  2301. begin
  2302. FPCHelpLines := true;
  2303. Delete (More, 1, 1);
  2304. FPCBinaryPath := More;
  2305. end;
  2306. WriteHelpPages;
  2307. end;
  2308. 'i' :
  2309. begin
  2310. if (More='') or
  2311. (More [1] in ['a', 'b', 'c', 'f', 'i', {$ifdef LLVM}'l',{$endif} 'm', 'o', 'r', 't', 'u', 'w', 'x']) then
  2312. WriteInfo (More)
  2313. else
  2314. QuickInfo:=QuickInfo+More;
  2315. end;
  2316. 'I' :
  2317. begin
  2318. if ispara then
  2319. ParaIncludePath.AddPath(More,false)
  2320. else
  2321. includesearchpath.AddPath(More,false);
  2322. end;
  2323. 'k' :
  2324. begin
  2325. if more<>'' then
  2326. ParaLinkOptions:=ParaLinkOptions+' '+More
  2327. else
  2328. IllegalPara(opt);
  2329. end;
  2330. 'l' :
  2331. ParaLogo:=not UnSetBool(more,0,opt,true);
  2332. {$ifdef PREPROCWRITE}
  2333. 'm' :
  2334. parapreprocess:=not UnSetBool(more,0,opt,true);
  2335. {$endif PREPROCWRITE}
  2336. 'M' :
  2337. begin
  2338. more:=Upper(more);
  2339. if not SetCompileMode(more, true) then
  2340. if not SetCompileModeSwitch(more, true) then
  2341. IllegalPara(opt);
  2342. end;
  2343. 'n' :
  2344. begin
  2345. if More='' then
  2346. disable_configfile:=true
  2347. else
  2348. IllegalPara(opt);
  2349. end;
  2350. 'o' :
  2351. begin
  2352. if More<>'' then
  2353. begin
  2354. DefaultReplacements(More);
  2355. D:=ExtractFilePath(More);
  2356. if (D<>'') then
  2357. OutputExeDir:=FixPath(D,True);
  2358. OutputFileName:=ExtractFileName(More);
  2359. end
  2360. else
  2361. IllegalPara(opt);
  2362. end;
  2363. 'O' :
  2364. begin
  2365. j:=1;
  2366. while j<=length(more) do
  2367. begin
  2368. case more[j] of
  2369. '1' :
  2370. init_settings.optimizerswitches:=init_settings.optimizerswitches+level1optimizerswitches;
  2371. '2' :
  2372. init_settings.optimizerswitches:=init_settings.optimizerswitches+level2optimizerswitches;
  2373. '3' :
  2374. init_settings.optimizerswitches:=init_settings.optimizerswitches+level3optimizerswitches;
  2375. '4' :
  2376. init_settings.optimizerswitches:=init_settings.optimizerswitches+level4optimizerswitches;
  2377. 'a' :
  2378. begin
  2379. if not(UpdateAlignmentStr(Copy(Opt,j+3,255),ParaAlignment)) then
  2380. IllegalPara(opt);
  2381. break;
  2382. end;
  2383. 's' :
  2384. include(init_settings.optimizerswitches,cs_opt_size);
  2385. 'p' :
  2386. begin
  2387. if not Setoptimizecputype(copy(more,j+1,length(more)),init_settings.optimizecputype) then
  2388. begin
  2389. OptCPUSetExplicitly:=true;
  2390. { Give warning for old i386 switches }
  2391. if (Length(More)-j=1) and
  2392. (More[j+1]>='1') and (More[j+1]<='5')then
  2393. Message2(option_obsolete_switch_use_new,'-Op<nr>','-Op<name>')
  2394. else
  2395. IllegalPara(opt);
  2396. end;
  2397. break;
  2398. end;
  2399. 'o' :
  2400. begin
  2401. if not UpdateOptimizerStr(copy(more,j+1,length(more)),init_settings.optimizerswitches) then
  2402. IllegalPara(opt);
  2403. break;
  2404. end;
  2405. '-' :
  2406. begin
  2407. init_settings.optimizerswitches:=[];
  2408. FillChar(ParaAlignment,sizeof(ParaAlignment),0);
  2409. end;
  2410. { Obsolete switches }
  2411. 'g' :
  2412. Message2(option_obsolete_switch_use_new,'-Og','-Os');
  2413. 'G' :
  2414. Message1(option_obsolete_switch,'-OG');
  2415. 'r' :
  2416. Message2(option_obsolete_switch_use_new,'-Or','-O2 or -Ooregvar');
  2417. 'u' :
  2418. Message2(option_obsolete_switch_use_new,'-Ou','-Oouncertain');
  2419. 'w' :
  2420. begin
  2421. if not UpdateWpoStr(copy(more,j+1,length(more)),init_settings.dowpoptimizerswitches) then
  2422. IllegalPara(opt);
  2423. break;
  2424. end;
  2425. 'W' :
  2426. begin
  2427. if not UpdateWpoStr(copy(more,j+1,length(more)),init_settings.genwpoptimizerswitches) then
  2428. IllegalPara(opt);
  2429. break;
  2430. end;
  2431. else
  2432. IllegalPara(opt);
  2433. end;
  2434. inc(j);
  2435. end;
  2436. end;
  2437. 'p' :
  2438. begin
  2439. if UnsetBool(More, 0, opt, false) then
  2440. begin
  2441. init_settings.moduleswitches:=init_settings.moduleswitches-[cs_profile];
  2442. undef_system_macro('FPC_PROFILE');
  2443. end
  2444. else
  2445. if Length(More)=0 then
  2446. IllegalPara(opt)
  2447. else
  2448. case more[1] of
  2449. 'g' : if UnsetBool(more, 1, opt, false) then
  2450. begin
  2451. exclude(init_settings.moduleswitches,cs_profile);
  2452. undef_system_macro('FPC_PROFILE');
  2453. end
  2454. else if (target_info.system in supported_targets_pg) then
  2455. begin
  2456. include(init_settings.moduleswitches,cs_profile);
  2457. def_system_macro('FPC_PROFILE');
  2458. end
  2459. else
  2460. UnsupportedPara('-pg');
  2461. else
  2462. IllegalPara(opt);
  2463. end;
  2464. end;
  2465. 'P' :
  2466. begin
  2467. { used to select the target processor with the "fpc" binary;
  2468. give an error if it's not the target architecture supported by
  2469. this compiler binary (will be verified after the target_info
  2470. is set) }
  2471. processorstr:=More;
  2472. end;
  2473. 'R' :
  2474. begin
  2475. if not SetAsmReadMode(More,init_settings.asmmode) then
  2476. IllegalPara(opt);
  2477. end;
  2478. 's' :
  2479. begin
  2480. if UnsetBool(More, 0, opt, false) then
  2481. begin
  2482. init_settings.globalswitches:=init_settings.globalswitches-[cs_asm_extern,cs_link_extern,cs_link_nolink];
  2483. if more<>'' then
  2484. IllegalPara(opt);
  2485. end
  2486. else
  2487. begin
  2488. init_settings.globalswitches:=init_settings.globalswitches+[cs_asm_extern,cs_link_extern,cs_link_nolink];
  2489. if more='h' then
  2490. init_settings.globalswitches:=init_settings.globalswitches-[cs_link_on_target,cs_assemble_on_target]
  2491. else if more='t' then
  2492. init_settings.globalswitches:=init_settings.globalswitches+[cs_link_on_target,cs_assemble_on_target]
  2493. else if more='T' then
  2494. init_settings.globalswitches:=init_settings.globalswitches+[cs_link_on_target]-[cs_asm_extern]
  2495. else if more='r' then
  2496. init_settings.globalswitches:=init_settings.globalswitches+[cs_asm_leave,cs_no_regalloc]
  2497. else if more<>'' then
  2498. IllegalPara(opt);
  2499. end;
  2500. end;
  2501. 'S' :
  2502. begin
  2503. if more='' then
  2504. IllegalPara(opt);
  2505. if more[1]='I' then
  2506. begin
  2507. {$ifdef jvm}
  2508. UnsupportedPara('-SI');
  2509. {$endif}
  2510. if upper(more)='ICOM' then
  2511. init_settings.interfacetype:=it_interfacecom
  2512. else if upper(more)='ICORBA' then
  2513. init_settings.interfacetype:=it_interfacecorba
  2514. else
  2515. IllegalPara(opt);
  2516. end
  2517. else
  2518. begin
  2519. j:=1;
  2520. while j<=length(more) do
  2521. begin
  2522. case more[j] of
  2523. '2' : //an alternative to -Mobjfpc
  2524. SetCompileMode('OBJFPC',true);
  2525. 'a' :
  2526. If UnsetBool(More, j, opt, false) then
  2527. exclude(init_settings.localswitches,cs_do_assertion)
  2528. else
  2529. include(init_settings.localswitches,cs_do_assertion);
  2530. 'c' :
  2531. If UnsetBool(More, j, opt, false) then
  2532. exclude(init_settings.moduleswitches,cs_support_c_operators)
  2533. else
  2534. include(init_settings.moduleswitches,cs_support_c_operators);
  2535. 'C':
  2536. If UnsetBool(More, j, opt, false) then
  2537. exclude(init_settings.localswitches,cs_check_all_case_coverage)
  2538. else
  2539. include(init_settings.localswitches,cs_check_all_case_coverage);
  2540. 'd' : //an alternative to -Mdelphi
  2541. SetCompileMode('DELPHI',true);
  2542. 'e' :
  2543. begin
  2544. SetErrorFlags(copy(more,j+1,length(more)));
  2545. break;
  2546. end;
  2547. 'f' :
  2548. begin
  2549. if not(cs_compilesystem in init_settings.moduleswitches) then
  2550. Message(option_features_only_for_system_unit);
  2551. inc(j);
  2552. if more[j]='-' then
  2553. begin
  2554. if length(more)>j then
  2555. IllegalPara(opt)
  2556. else
  2557. features:=[];
  2558. end
  2559. else
  2560. begin
  2561. if (HandleFeature(upper(copy(more,j,length(more)-j+1)))) then
  2562. j:=length(more)
  2563. else
  2564. IllegalPara(opt);
  2565. end;
  2566. end;
  2567. 'g' :
  2568. If UnsetBool(More, j, opt, false) then
  2569. exclude(init_settings.moduleswitches,cs_support_goto)
  2570. else
  2571. include(init_settings.moduleswitches,cs_support_goto);
  2572. 'h' :
  2573. If UnsetBool(More, j, opt, false) then
  2574. exclude(init_settings.localswitches,cs_refcountedstrings)
  2575. else
  2576. include(init_settings.localswitches,cs_refcountedstrings);
  2577. 'i' :
  2578. If UnsetBool(More, j, opt, false) then
  2579. exclude(init_settings.localswitches,cs_do_inline)
  2580. else
  2581. include(init_settings.localswitches,cs_do_inline);
  2582. 'j' :
  2583. If UnsetBool(More, j, opt, false) then
  2584. exclude(init_settings.localswitches,cs_typed_const_writable)
  2585. else
  2586. include(init_settings.localswitches,cs_typed_const_writable);
  2587. 'k' :
  2588. If UnsetBool(More, j, opt, false) then
  2589. exclude(init_settings.globalswitches,cs_load_fpcylix_unit)
  2590. else
  2591. include(init_settings.globalswitches,cs_load_fpcylix_unit);
  2592. 'm' :
  2593. If UnsetBool(More, j, opt, false) then
  2594. exclude(init_settings.moduleswitches,cs_support_macro)
  2595. else
  2596. include(init_settings.moduleswitches,cs_support_macro);
  2597. 'o' : //an alternative to -Mtp
  2598. SetCompileMode('TP',true);
  2599. 'r' :
  2600. If UnsetBool(More, j, opt, false) then
  2601. exclude(init_settings.globalswitches,cs_transparent_file_names)
  2602. else
  2603. include(init_settings.globalswitches,cs_transparent_file_names);
  2604. {$ifdef gpc_mode}
  2605. 'p' : //an alternative to -Mgpc
  2606. SetCompileMode('GPC',true);
  2607. {$endif}
  2608. 's' :
  2609. If UnsetBool(More, j, opt, false) then
  2610. exclude(init_settings.globalswitches,cs_constructor_name)
  2611. else
  2612. include(init_settings.globalswitches,cs_constructor_name);
  2613. 't' :
  2614. Message1(option_obsolete_switch,'-St');
  2615. 'v' :
  2616. If UnsetBool(More, j, opt, false) then
  2617. exclude(init_settings.globalswitches,cs_support_vectors)
  2618. else
  2619. include(init_settings.globalswitches,cs_support_vectors);
  2620. 'x' :
  2621. If UnsetBool(More, j, opt, false) then
  2622. SetCompileModeSwitch('EXCEPTIONS-',true)
  2623. else
  2624. SetCompileModeSwitch('EXCEPTIONS',true);
  2625. 'y' :
  2626. If UnsetBool(More, j, opt, false) then
  2627. exclude(init_settings.localswitches,cs_typed_addresses)
  2628. else
  2629. include(init_settings.localswitches,cs_typed_addresses);
  2630. '-' :
  2631. begin
  2632. init_settings.globalswitches:=init_settings.globalswitches - [cs_constructor_name,cs_support_exceptions,
  2633. cs_support_vectors,cs_load_fpcylix_unit];
  2634. init_settings.localswitches:=init_settings.localswitches - [cs_do_assertion,cs_do_inline, cs_refcountedstrings,
  2635. cs_typed_addresses];
  2636. init_settings.moduleswitches:=init_settings.moduleswitches - [cs_support_c_operators, cs_support_goto,
  2637. cs_support_macro];
  2638. end;
  2639. else
  2640. IllegalPara(opt);
  2641. end;
  2642. inc(j);
  2643. end;
  2644. end;
  2645. end;
  2646. 'T' :
  2647. begin
  2648. more:=Upper(More);
  2649. if paratarget=system_none then
  2650. begin
  2651. { remove old target define }
  2652. TargetOptions(false);
  2653. { load new target }
  2654. paratarget:=find_system_by_string(More);
  2655. if paratarget<>system_none then
  2656. set_target(paratarget)
  2657. else
  2658. IllegalPara(opt);
  2659. { set new define }
  2660. TargetOptions(true);
  2661. end
  2662. else
  2663. if More<>upper(target_info.shortname) then
  2664. Message1(option_target_is_already_set,target_info.shortname);
  2665. end;
  2666. 't' :
  2667. begin
  2668. more:=Upper(More);
  2669. if (more='') then
  2670. Message1(option_missing_arg,'-t')
  2671. else
  2672. begin
  2673. if (self.parasubtarget<>'') and (More<>upper(self.parasubtarget)) then
  2674. Message1(option_subtarget_is_already_set,self.parasubtarget)
  2675. else
  2676. begin
  2677. self.parasubtarget:=more;
  2678. end;
  2679. end;
  2680. end;
  2681. 'u' :
  2682. if is_identifier(more) then
  2683. undef_system_macro(more)
  2684. else
  2685. begin
  2686. if (more='') then
  2687. Message1(option_missing_arg,'-u')
  2688. else
  2689. Message1(option_malformed_para,opt);
  2690. StopOptions(1);
  2691. end;
  2692. 'U' :
  2693. begin
  2694. j:=1;
  2695. while j<=length(more) do
  2696. begin
  2697. case more[j] of
  2698. {$ifdef UNITALIASES}
  2699. 'a' :
  2700. begin
  2701. AddUnitAlias(Copy(More,j+1,255));
  2702. break;
  2703. end;
  2704. {$endif UNITALIASES}
  2705. 'n' :
  2706. exclude(init_settings.globalswitches,cs_check_unit_name);
  2707. 'p' :
  2708. begin
  2709. Message2(option_obsolete_switch_use_new,'-Up','-Fu');
  2710. break;
  2711. end;
  2712. 'r' :
  2713. begin
  2714. do_release:=true;
  2715. if (cs_checkpointer in init_settings.localswitches) then
  2716. begin
  2717. Message(option_gc_incompatible_with_release_flag);
  2718. exclude(init_settings.localswitches,cs_checkpointer);
  2719. end;
  2720. end;
  2721. 's' :
  2722. include(init_settings.moduleswitches,cs_compilesystem);
  2723. '-' :
  2724. begin
  2725. exclude(init_settings.moduleswitches,cs_compilesystem);
  2726. exclude(init_settings.globalswitches,cs_check_unit_name);
  2727. end;
  2728. else
  2729. IllegalPara(opt);
  2730. end;
  2731. inc(j);
  2732. end;
  2733. end;
  2734. 'v' :
  2735. begin
  2736. if not setverbosity(More) then
  2737. IllegalPara(opt);
  2738. end;
  2739. 'V' : ; { Ignore used by fpc }
  2740. 'W' :
  2741. begin
  2742. j:=1;
  2743. while j<=length(More) do
  2744. begin
  2745. case More[j] of
  2746. 'A':
  2747. begin
  2748. if target_info.system in systems_all_windows then
  2749. begin
  2750. if UnsetBool(More, j, opt, false) then
  2751. SetApptype(app_cui)
  2752. else
  2753. SetApptype(app_native);
  2754. end
  2755. else
  2756. IllegalPara(opt);
  2757. end;
  2758. 'b':
  2759. begin
  2760. if target_info.system in systems_darwin then
  2761. begin
  2762. if UnsetBool(More, j, opt, false) then
  2763. SetApptype(app_cui)
  2764. else
  2765. SetApptype(app_bundle)
  2766. end
  2767. else
  2768. IllegalPara(opt);
  2769. end;
  2770. 'B':
  2771. begin
  2772. if target_info.system in systems_all_windows+systems_symbian+[system_z80_zxspectrum] then
  2773. begin
  2774. { -WB200000 means set trefered base address
  2775. to $200000, but does not change relocsection boolean
  2776. this way we can create both relocatble and
  2777. non relocatable DLL at a specific base address PM }
  2778. if (length(More)>j) then
  2779. begin
  2780. val('$'+Copy(More,j+1,255),imagebase,code);
  2781. if code<>0 then
  2782. IllegalPara(opt);
  2783. ImageBaseSetExplicity:=true;
  2784. end
  2785. else
  2786. begin
  2787. RelocSection:=true;
  2788. RelocSectionSetExplicitly:=true;
  2789. end;
  2790. break;
  2791. end
  2792. else
  2793. IllegalPara(opt);
  2794. end;
  2795. 'C':
  2796. begin
  2797. if target_info.system in systems_all_windows+systems_os2+systems_macos then
  2798. begin
  2799. if UnsetBool(More, j, opt, false) then
  2800. SetApptype(app_gui)
  2801. else
  2802. SetApptype(app_cui);
  2803. end
  2804. else
  2805. IllegalPara(opt);
  2806. end;
  2807. 'D':
  2808. begin
  2809. if target_info.system in systems_all_windows then
  2810. begin
  2811. UseDeffileForExports:=not UnsetBool(More, j, opt, false);
  2812. UseDeffileForExportsSetExplicitly:=true;
  2813. end
  2814. else
  2815. IllegalPara(opt);
  2816. end;
  2817. 'e':
  2818. begin
  2819. if (target_info.system in systems_darwin) then
  2820. begin
  2821. set_target_res(res_ext);
  2822. target_info.resobjext:='.fpcres';
  2823. end
  2824. else
  2825. IllegalPara(opt);
  2826. end;
  2827. 'F':
  2828. begin
  2829. {$if defined(m68k)}
  2830. if target_info.system in [system_m68k_atari] then
  2831. begin
  2832. if (length(More)>j) then
  2833. begin
  2834. val(Copy(More,j+1,255),ataritos_exe_flags,code);
  2835. if code<>0 then
  2836. IllegalPara(opt);
  2837. end
  2838. else
  2839. IllegalPara(opt);
  2840. break;
  2841. end;
  2842. {$endif defined(m68k)}
  2843. if target_info.system in systems_os2 then
  2844. begin
  2845. if UnsetBool(More, j, opt, false) then
  2846. SetApptype(app_cui)
  2847. else
  2848. SetApptype(app_fs);
  2849. end
  2850. else
  2851. IllegalPara(opt);
  2852. end;
  2853. 'G':
  2854. begin
  2855. if target_info.system in systems_all_windows+systems_os2+systems_macos then
  2856. begin
  2857. if UnsetBool(More, j, opt, false) then
  2858. SetApptype(app_cui)
  2859. else
  2860. SetApptype(app_gui);
  2861. end
  2862. else
  2863. IllegalPara(opt);
  2864. end;
  2865. {$if defined(i8086)}
  2866. 'h':
  2867. begin
  2868. if UnsetBool(More, j, opt, false) then
  2869. exclude(init_settings.moduleswitches,cs_huge_code)
  2870. else
  2871. include(init_settings.moduleswitches,cs_huge_code);
  2872. end;
  2873. {$endif defined(i8086)}
  2874. 'I':
  2875. begin
  2876. if target_info.system in systems_all_windows then
  2877. begin
  2878. GenerateImportSection:=not UnsetBool(More,j,opt,false);
  2879. GenerateImportSectionSetExplicitly:=true;
  2880. end
  2881. else
  2882. IllegalPara(opt);
  2883. end;
  2884. 'i':
  2885. begin
  2886. if (target_info.system in systems_darwin) then
  2887. begin
  2888. set_target_res(res_macho);
  2889. target_info.resobjext:=
  2890. targetinfos[target_info.system]^.resobjext;
  2891. end
  2892. else
  2893. IllegalPara(opt);
  2894. end;
  2895. 'm':
  2896. begin
  2897. {$if defined(i8086)}
  2898. if (target_info.system in [system_i8086_msdos,system_i8086_win16,system_i8086_embedded]) then
  2899. begin
  2900. case Upper(Copy(More,j+1,255)) of
  2901. 'TINY': init_settings.x86memorymodel:=mm_tiny;
  2902. 'SMALL': init_settings.x86memorymodel:=mm_small;
  2903. 'MEDIUM': init_settings.x86memorymodel:=mm_medium;
  2904. 'COMPACT': init_settings.x86memorymodel:=mm_compact;
  2905. 'LARGE': init_settings.x86memorymodel:=mm_large;
  2906. 'HUGE': init_settings.x86memorymodel:=mm_huge;
  2907. else
  2908. IllegalPara(opt);
  2909. end;
  2910. break;
  2911. end
  2912. else
  2913. {$endif defined(i8086)}
  2914. IllegalPara(opt);
  2915. end;
  2916. 'M':
  2917. begin
  2918. if (target_info.system in (systems_darwin-[system_i386_iphonesim,system_arm_ios,system_aarch64_ios,system_x86_64_iphonesim,system_aarch64_iphonesim])) and
  2919. ParseMacVersionMin(MacOSXVersionMin,iPhoneOSVersionMin,'MAC_OS_X_VERSION_MIN_REQUIRED',copy(More,2,255),false) then
  2920. begin
  2921. break;
  2922. end
  2923. else
  2924. IllegalPara(opt);
  2925. end;
  2926. 'N':
  2927. begin
  2928. if target_info.system in systems_all_windows then
  2929. begin
  2930. RelocSection:=UnsetBool(More,j,opt,false);
  2931. RelocSectionSetExplicitly:=true;
  2932. end
  2933. else
  2934. IllegalPara(opt);
  2935. end;
  2936. 'p':
  2937. begin
  2938. {$push}
  2939. {$warn 6018 off} { Unreachable code due to compile time evaluation }
  2940. if ((target_info.system in systems_embedded) or (target_info.system in systems_freertos)) and
  2941. ControllerSupport then
  2942. begin
  2943. s:=upper(copy(more,j+1,length(more)-j));
  2944. if not(SetControllerType(s,init_settings.controllertype)) then
  2945. IllegalPara(opt)
  2946. else
  2947. begin
  2948. if init_settings.cputype<>embedded_controllers[init_settings.controllertype].cputype then
  2949. begin
  2950. Message(scan_n_changecputype);
  2951. init_settings.cputype:=embedded_controllers[init_settings.controllertype].cputype;
  2952. end;
  2953. end;
  2954. break;
  2955. end
  2956. else
  2957. IllegalPara(opt);
  2958. {$pop}
  2959. end;
  2960. 'P':
  2961. begin
  2962. if (target_info.system in [system_i386_iphonesim,system_arm_ios,system_aarch64_ios,system_x86_64_iphonesim,system_aarch64_iphonesim]) and
  2963. ParseMacVersionMin(iPhoneOSVersionMin,MacOSXVersionMin,'IPHONE_OS_VERSION_MIN_REQUIRED',copy(More,2,255),true) then
  2964. begin
  2965. break;
  2966. end
  2967. {$ifdef XTENSA}
  2968. else if (target_info.system in [system_xtensa_freertos]) and
  2969. ParseVersionStr(idf_version,'IDF_VERSION',copy(More,2,255)) then
  2970. begin
  2971. break;
  2972. end
  2973. {$endif XTENSA}
  2974. else
  2975. IllegalPara(opt);
  2976. end;
  2977. {$if defined(m68k)}
  2978. 'L':
  2979. begin
  2980. if (target_info.system in [system_m68k_sinclairql]) then
  2981. sinclairql_vlink_experimental:=false
  2982. else
  2983. IllegalPara(opt);
  2984. end;
  2985. 'Q':
  2986. begin
  2987. if (target_info.system in [system_m68k_sinclairql]) then
  2988. begin
  2989. sinclairql_metadata_format:=Upper(Copy(More,j+1,255));
  2990. case sinclairql_metadata_format of
  2991. 'QHDR', 'XTCC': ; { allowed formats }
  2992. else
  2993. IllegalPara(opt);
  2994. end;
  2995. break;
  2996. end
  2997. else
  2998. IllegalPara(opt);
  2999. end;
  3000. {$endif defined(m68k)}
  3001. 'R':
  3002. begin
  3003. if target_info.system in systems_all_windows then
  3004. begin
  3005. { support -WR+ / -WR- as synonyms to -WR / -WN }
  3006. RelocSection:=not UnsetBool(More,j,opt,false);
  3007. RelocSectionSetExplicitly:=true;
  3008. end
  3009. else
  3010. IllegalPara(opt);
  3011. end;
  3012. 't':
  3013. begin
  3014. {$if defined(i8086)}
  3015. if (target_info.system in [system_i8086_msdos,system_i8086_embedded]) then
  3016. begin
  3017. case Upper(Copy(More,j+1,255)) of
  3018. 'EXE': SetAppType(app_cui);
  3019. 'COM': SetAppType(app_com);
  3020. else
  3021. IllegalPara(opt);
  3022. end;
  3023. break;
  3024. end
  3025. else
  3026. {$endif defined(i8086)}
  3027. {$if defined(m68k)}
  3028. if (target_info.system in [system_m68k_atari]) then
  3029. begin
  3030. case Upper(Copy(More,j+1,255)) of
  3031. 'TOS': ataritos_exe_format := 'ataritos';
  3032. 'MINT': ataritos_exe_format := 'aoutmint';
  3033. else
  3034. IllegalPara(opt);
  3035. end;
  3036. break;
  3037. end
  3038. else
  3039. {$endif defined(m68k)}
  3040. IllegalPara(opt);
  3041. end;
  3042. 'T':
  3043. begin
  3044. if target_info.system in systems_macos then
  3045. begin
  3046. if UnsetBool(More, j, opt, false) then
  3047. SetApptype(app_cui)
  3048. else
  3049. SetApptype(app_tool);
  3050. end
  3051. else
  3052. IllegalPara(opt);
  3053. end;
  3054. 'X':
  3055. begin
  3056. if (target_info.system in systems_linux) then
  3057. begin
  3058. if UnsetBool(More, j, opt, false) then
  3059. exclude(init_settings.moduleswitches,cs_executable_stack)
  3060. else
  3061. include(init_settings.moduleswitches,cs_executable_stack)
  3062. end
  3063. else
  3064. IllegalPara(opt);
  3065. end;
  3066. else
  3067. IllegalPara(opt);
  3068. end;
  3069. inc(j);
  3070. end;
  3071. end;
  3072. 'x' :
  3073. message1(option_x_ignored,more);
  3074. 'X' :
  3075. begin
  3076. j:=1;
  3077. while j<=length(more) do
  3078. begin
  3079. case More[j] of
  3080. '9' :
  3081. begin
  3082. if target_info.system in systems_linux then
  3083. begin
  3084. if UnsetBool(More, j, opt, false) then
  3085. exclude(init_settings.globalswitches,cs_link_pre_binutils_2_19)
  3086. else
  3087. include(init_settings.globalswitches,cs_link_pre_binutils_2_19);
  3088. end
  3089. else
  3090. IllegalPara(opt);
  3091. end;
  3092. 'a' :
  3093. begin
  3094. If UnsetBool(More, j, opt, false) then
  3095. exclude(init_settings.globalswitches,cs_large)
  3096. else
  3097. include(init_settings.globalswitches,cs_large);
  3098. end;
  3099. 'c' : Cshared:=TRUE;
  3100. 'd' : Dontlinkstdlibpath:=TRUE;
  3101. 'e' :
  3102. begin
  3103. If UnsetBool(More, j, opt, false) then
  3104. exclude(init_settings.globalswitches,cs_link_extern)
  3105. else
  3106. include(init_settings.globalswitches,cs_link_extern);
  3107. end;
  3108. 'f' :
  3109. include(init_settings.globalswitches,cs_link_pthread);
  3110. 'g' :
  3111. begin
  3112. If UnsetBool(More, j, opt, false) then
  3113. exclude(init_settings.globalswitches,cs_link_separate_dbg_file)
  3114. else
  3115. include(init_settings.globalswitches,cs_link_separate_dbg_file);
  3116. end;
  3117. 'i' :
  3118. begin
  3119. If UnsetBool(More, j, opt, false) then
  3120. include(init_settings.globalswitches,cs_link_extern)
  3121. else
  3122. exclude(init_settings.globalswitches,cs_link_extern);
  3123. end;
  3124. 'n' :
  3125. begin
  3126. If UnsetBool(More, j, opt, false) then
  3127. exclude(init_settings.globalswitches,cs_link_native)
  3128. else
  3129. include(init_settings.globalswitches,cs_link_native);
  3130. end;
  3131. {$ifdef llvm}
  3132. 'l' :
  3133. begin
  3134. if j=length(more) then
  3135. IllegalPara(opt)
  3136. else
  3137. begin
  3138. case more[j+1] of
  3139. 'S':
  3140. begin
  3141. llvmutilssuffix:=copy(more,j+2,length(more));
  3142. j:=length(more);
  3143. end
  3144. else
  3145. IllegalPara(opt);
  3146. end;
  3147. end;
  3148. end;
  3149. {$endif}
  3150. 'm' :
  3151. begin
  3152. If UnsetBool(More, j, opt, false) then
  3153. exclude(init_settings.globalswitches,cs_link_map)
  3154. else
  3155. include(init_settings.globalswitches,cs_link_map);
  3156. end;
  3157. 'p' : ; { Ignore used by fpc.pp }
  3158. 'r' :
  3159. begin
  3160. if (target_info.system in suppported_targets_x_smallr) then
  3161. begin
  3162. rlinkpath:=Copy(more,2,length(More)-1);
  3163. DefaultReplacements(rlinkpath);
  3164. end
  3165. else
  3166. IgnoredPara('-Xr');
  3167. more:='';
  3168. end;
  3169. 'R' :
  3170. begin
  3171. sysrootpath:=copy(more,2,length(more)-1);
  3172. defaultreplacements(sysrootpath);
  3173. more:='';
  3174. end;
  3175. 's' :
  3176. begin
  3177. If UnsetBool(More, j, opt, false) then
  3178. exclude(init_settings.globalswitches,cs_link_strip)
  3179. else
  3180. include(init_settings.globalswitches,cs_link_strip);
  3181. end;
  3182. 't' :
  3183. include(init_settings.globalswitches,cs_link_staticflag);
  3184. 'u' :
  3185. begin
  3186. if target_info.system in systems_support_uf2 then
  3187. begin
  3188. if UnsetBool(More, j, opt, false) then
  3189. exclude(init_settings.globalswitches,cs_generate_uf2)
  3190. else
  3191. include(init_settings.globalswitches,cs_generate_uf2);
  3192. end
  3193. else
  3194. IgnoredPara('-Xu');
  3195. end;
  3196. 'v' :
  3197. begin
  3198. If UnsetBool(More, j, opt, false) then
  3199. exclude(init_settings.globalswitches,cs_link_opt_vtable)
  3200. else
  3201. include(init_settings.globalswitches,cs_link_opt_vtable);
  3202. end;
  3203. 'D' :
  3204. begin
  3205. def_system_macro('FPC_LINK_DYNAMIC');
  3206. undef_system_macro('FPC_LINK_SMART');
  3207. undef_system_macro('FPC_LINK_STATIC');
  3208. exclude(init_settings.globalswitches,cs_link_static);
  3209. exclude(init_settings.globalswitches,cs_link_smart);
  3210. include(init_settings.globalswitches,cs_link_shared);
  3211. LinkTypeSetExplicitly:=true;
  3212. end;
  3213. 'M' :
  3214. begin
  3215. mainaliasname:=Copy(more,2,length(More)-1);
  3216. More:='';
  3217. end;
  3218. 'P' :
  3219. begin
  3220. utilsprefix:=Copy(more,2,length(More)-1);
  3221. DefaultReplacements(utilsprefix);
  3222. More:='';
  3223. end;
  3224. 'L' : begin // -XLO is link order -XLA is link alias. -XLD avoids load defaults.
  3225. // these are not aggregable.
  3226. if (j=length(more)) or not (more[j+1] in ['O','A','D']) then
  3227. IllegalPara(opt)
  3228. else
  3229. begin
  3230. case more[j+1] of
  3231. 'A' : begin
  3232. s:=Copy(more,3,length(More)-2);
  3233. if not LinkLibraryAliases.AddDep(s) Then
  3234. IllegalPara(opt);
  3235. end;
  3236. 'O' : begin
  3237. s:=Copy(more,3,length(More)-2);
  3238. if not LinkLibraryOrder.AddWeight(s) Then
  3239. IllegalPara(opt);
  3240. end;
  3241. 'D' : include(init_settings.globalswitches,cs_link_no_default_lib_order)
  3242. else
  3243. IllegalPara(opt);
  3244. end; {case}
  3245. j:=length(more);
  3246. end; {else begin}
  3247. end;
  3248. 'S' :
  3249. begin
  3250. ForceStaticLinking;
  3251. end;
  3252. 'V' :
  3253. begin
  3254. if UnsetBool(More, j, opt, false) then
  3255. exclude(init_settings.globalswitches,cs_link_vlink)
  3256. else
  3257. begin
  3258. include(init_settings.globalswitches,cs_link_vlink);
  3259. include(init_settings.globalswitches,cs_link_extern);
  3260. end;
  3261. LinkerSetExplicitly:=true;
  3262. end;
  3263. 'X' :
  3264. begin
  3265. def_system_macro('FPC_LINK_SMART');
  3266. undef_system_macro('FPC_LINK_STATIC');
  3267. undef_system_macro('FPC_LINK_DYNAMIC');
  3268. exclude(init_settings.globalswitches,cs_link_static);
  3269. include(init_settings.globalswitches,cs_link_smart);
  3270. exclude(init_settings.globalswitches,cs_link_shared);
  3271. LinkTypeSetExplicitly:=true;
  3272. end;
  3273. '-' :
  3274. begin
  3275. exclude(init_settings.globalswitches,cs_link_staticflag);
  3276. exclude(init_settings.globalswitches,cs_link_strip);
  3277. exclude(init_settings.globalswitches,cs_link_map);
  3278. set_default_link_type;
  3279. end;
  3280. else
  3281. IllegalPara(opt);
  3282. end;
  3283. inc(j);
  3284. end;
  3285. end;
  3286. else
  3287. IllegalPara(opt);
  3288. end;
  3289. end;
  3290. '@' :
  3291. begin
  3292. Message(option_no_nested_response_file);
  3293. StopOptions(1);
  3294. end;
  3295. else
  3296. begin
  3297. if (length(param_file)<>0) then
  3298. Message2(option_only_one_source_support,param_file,opt);
  3299. param_file:=opt;
  3300. Message1(option_found_file,opt);
  3301. end;
  3302. end;
  3303. end;
  3304. procedure Toption.Interpret_file(const filename : TPathStr);
  3305. procedure RemoveSep(var fn:TPathStr);
  3306. var
  3307. i : longint;
  3308. begin
  3309. i:=0;
  3310. while (i<length(fn)) and (fn[i+1] in [',',' ',#9]) do
  3311. inc(i);
  3312. Delete(fn,1,i);
  3313. i:=length(fn);
  3314. while (i>0) and (fn[i] in [',',' ',#9]) do
  3315. dec(i);
  3316. fn:=copy(fn,1,i);
  3317. end;
  3318. function GetName(var fn:TPathStr):TPathStr;
  3319. var
  3320. i : longint;
  3321. begin
  3322. i:=0;
  3323. while (i<length(fn)) and (fn[i+1] in ['a'..'z','A'..'Z','0'..'9','_','-']) do
  3324. inc(i);
  3325. GetName:=Copy(fn,1,i);
  3326. Delete(fn,1,i);
  3327. end;
  3328. const
  3329. maxlevel = 15;
  3330. var
  3331. f : text;
  3332. s, tmp,
  3333. opts : TCmdStr;
  3334. skip : array[0..maxlevel] of boolean;
  3335. line,
  3336. level : longint;
  3337. option_read : boolean;
  3338. oldfilemode : byte;
  3339. ConfigFile: TPathStr;
  3340. begin
  3341. { avoid infinite loop }
  3342. Inc(FileLevel);
  3343. Option_read:=false;
  3344. If FileLevel>MaxLevel then
  3345. Message(option_too_many_cfg_files);
  3346. if not ParaIncludeCfgPath.FindFile(fileName,true,ConfigFile) then
  3347. ConfigFile := ExpandFileName(filename);
  3348. { Maybe It's Directory ?} //Jaro Change:
  3349. if PathExists(ConfigFile,false) then
  3350. begin
  3351. Message1(option_config_is_dir,filename);
  3352. exit;
  3353. end;
  3354. { open file }
  3355. Message1(option_using_file,filename);
  3356. oldfilemode:=filemode;
  3357. filemode:=0;
  3358. assign(f,ConfigFile);
  3359. {$push}{$I-}
  3360. reset(f);
  3361. {$pop}
  3362. filemode:=oldfilemode;
  3363. if ioresult<>0 then
  3364. begin
  3365. Message1(option_unable_open_file,filename);
  3366. exit;
  3367. end;
  3368. Message1(option_start_reading_configfile,filename);
  3369. fillchar(skip,sizeof(skip),0);
  3370. level:=0;
  3371. line:=0;
  3372. while not eof(f) do
  3373. begin
  3374. readln(f,opts);
  3375. inc(line);
  3376. RemoveSep(opts);
  3377. if (opts<>'') and (opts[1]<>';') then
  3378. begin
  3379. if opts[1]='#' then
  3380. begin
  3381. Message1(option_interpreting_file_option,opts);
  3382. Delete(opts,1,1);
  3383. s:=upper(GetName(opts));
  3384. if (s='SECTION') then
  3385. begin
  3386. RemoveSep(opts);
  3387. s:=upper(GetName(opts));
  3388. if level=0 then
  3389. skip[level]:=not defined_macro(s) or (s='COMMON');
  3390. end
  3391. else
  3392. if (s='IFDEF') then
  3393. begin
  3394. RemoveSep(opts);
  3395. if Level>=maxlevel then
  3396. begin
  3397. Message2(option_too_many_ifdef,filename,tostr(line));
  3398. stopOptions(1);
  3399. end;
  3400. inc(Level);
  3401. { environment variable? }
  3402. if (opts[1]='$') and (opts[length(opts)]='$') then
  3403. skip[level]:=skip[level-1] or (GetEnvironmentVariable(copy(opts,2,length(opts)-2))='')
  3404. else
  3405. skip[level]:=(skip[level-1] or not defined_macro(upper(GetName(opts))));
  3406. end
  3407. else
  3408. if (s='IFNDEF') then
  3409. begin
  3410. RemoveSep(opts);
  3411. if Level>=maxlevel then
  3412. begin
  3413. Message2(option_too_many_ifdef,filename,tostr(line));
  3414. stopOptions(1);
  3415. end;
  3416. inc(Level);
  3417. { environment variable? }
  3418. if (opts[1]='$') and (opts[length(opts)]='$') then
  3419. skip[level]:=skip[level-1] or (GetEnvironmentVariable(copy(opts,2,length(opts)-2))<>'')
  3420. else
  3421. skip[level]:=skip[level-1] or defined_macro(upper(GetName(opts)));
  3422. end
  3423. else
  3424. if (s='ELSE') then
  3425. begin
  3426. if Level=0 then
  3427. begin
  3428. Message2(option_else_without_if,filename,tostr(line));
  3429. stopOptions(1);
  3430. end
  3431. else
  3432. skip[level]:=skip[level-1] or (not skip[level])
  3433. end
  3434. else
  3435. if (s='ENDIF') then
  3436. begin
  3437. skip[level]:=false;
  3438. if Level=0 then
  3439. begin
  3440. Message2(option_too_many_endif,filename,tostr(line));
  3441. stopOptions(1);
  3442. end;
  3443. dec(level);
  3444. end
  3445. else
  3446. if (not skip[level]) then
  3447. begin
  3448. if (s='DEFINE') then
  3449. begin
  3450. RemoveSep(opts);
  3451. tmp:= GetName(opts);
  3452. if tmp <> '' then
  3453. def_system_macro(tmp);
  3454. Option_read:=true;
  3455. end
  3456. else
  3457. if (s='UNDEF') then
  3458. begin
  3459. RemoveSep(opts);
  3460. tmp:= GetName(opts);
  3461. if tmp <> '' then
  3462. undef_system_macro(tmp);
  3463. Option_read:=true;
  3464. end
  3465. else
  3466. if (s='WRITE') then
  3467. begin
  3468. Delete(opts,1,1);
  3469. DefaultReplacements(opts);
  3470. WriteLn(opts);
  3471. Option_read:=true;
  3472. end
  3473. else
  3474. if (s='INCLUDE') then
  3475. begin
  3476. Delete(opts,1,1);
  3477. DefaultReplacements(opts);
  3478. Interpret_file(opts);
  3479. Option_read:=true;
  3480. end
  3481. else
  3482. if (s='CFGDIR') then
  3483. begin
  3484. Delete(opts,1,1);
  3485. DefaultReplacements(opts);
  3486. ParaIncludeCfgPath.AddPath(opts,false);
  3487. Option_read:=true;
  3488. end;
  3489. end;
  3490. end
  3491. else
  3492. begin
  3493. if (opts[1]='-') or (opts[1]='@') then
  3494. begin
  3495. if (not skip[level]) then
  3496. interpret_option(opts,false);
  3497. Option_read:=true;
  3498. end
  3499. else
  3500. Message1(option_illegal_para,opts);
  3501. end;
  3502. end;
  3503. end;
  3504. if Level>0 then
  3505. Message(option_too_less_endif);
  3506. if Not Option_read then
  3507. Message1(option_no_option_found,filename)
  3508. else
  3509. Message1(option_end_reading_configfile,filename);
  3510. Close(f);
  3511. Dec(FileLevel);
  3512. end;
  3513. procedure Toption.Interpret_envvar(const envname : TCmdStr);
  3514. var
  3515. argstart,
  3516. env,
  3517. pc : pchar;
  3518. arglen : longint;
  3519. quote : set of char;
  3520. hs : TCmdStr;
  3521. begin
  3522. Message1(option_using_env,envname);
  3523. env:=GetEnvPChar(envname);
  3524. pc:=env;
  3525. hs:='';
  3526. if assigned(pc) then
  3527. begin
  3528. repeat
  3529. { skip leading spaces }
  3530. while pc^ in [' ',#9,#13] do
  3531. inc(pc);
  3532. case pc^ of
  3533. #0 :
  3534. break;
  3535. '"' :
  3536. begin
  3537. quote:=['"'];
  3538. inc(pc);
  3539. end;
  3540. '''' :
  3541. begin
  3542. quote:=[''''];
  3543. inc(pc);
  3544. end;
  3545. else
  3546. quote:=[' ',#9,#13];
  3547. end;
  3548. { scan until the end of the argument }
  3549. argstart:=pc;
  3550. while (pc^<>#0) and not(pc^ in quote) do
  3551. inc(pc);
  3552. { create argument }
  3553. arglen:=pc-argstart;
  3554. { TODO: FIXME: silent truncation of environment parameters }
  3555. if (arglen > 255) then
  3556. arglen := 255;
  3557. setlength(hs,arglen);
  3558. move(argstart^,hs[1],arglen);
  3559. interpret_option(hs,true);
  3560. { skip quote }
  3561. if pc^ in quote then
  3562. inc(pc);
  3563. until false;
  3564. end
  3565. else
  3566. Message1(option_no_option_found,'(env) '+envname);
  3567. FreeEnvPChar(env);
  3568. end;
  3569. procedure toption.read_parameters;
  3570. var
  3571. opts : TCmdStr;
  3572. paramindex : longint;
  3573. begin
  3574. paramindex:=0;
  3575. while paramindex<paramcount do
  3576. begin
  3577. inc(paramindex);
  3578. opts:=objpas.paramstr(paramindex);
  3579. if length(opts)>0 then
  3580. case opts[1] of
  3581. '@' :
  3582. if not firstpass then
  3583. begin
  3584. Delete(opts,1,1);
  3585. Message1(option_reading_further_from,opts);
  3586. interpret_file(opts);
  3587. end;
  3588. '!' :
  3589. if not firstpass then
  3590. begin
  3591. Delete(opts,1,1);
  3592. Message1(option_reading_further_from,'(env) '+opts);
  3593. interpret_envvar(opts);
  3594. end;
  3595. else
  3596. interpret_option(opts,true);
  3597. end;
  3598. end;
  3599. end;
  3600. procedure toption.parsecmd(cmd:TCmdStr);
  3601. var
  3602. i,ps : longint;
  3603. opts : TCmdStr;
  3604. begin
  3605. while (cmd<>'') do
  3606. begin
  3607. while cmd[1]=' ' do
  3608. delete(cmd,1,1);
  3609. i:=pos(' ',cmd);
  3610. if i=0 then
  3611. i:=2147483647;
  3612. opts:=Copy(cmd,1,i-1);
  3613. Delete(cmd,1,i);
  3614. case opts[1] of
  3615. '@' :
  3616. if not firstpass then
  3617. begin
  3618. Delete(opts,1,1);
  3619. Message1(option_reading_further_from,opts);
  3620. interpret_file(opts);
  3621. end;
  3622. '!' :
  3623. if not firstpass then
  3624. begin
  3625. Delete(opts,1,1);
  3626. Message1(option_reading_further_from,'(env) '+opts);
  3627. interpret_envvar(opts);
  3628. end;
  3629. '"' :
  3630. begin
  3631. Delete(opts,1,1);
  3632. ps:=pos('"',cmd);
  3633. if (i<>256) and (ps>0) then
  3634. begin
  3635. opts:=opts + ' '+ copy(cmd,1,ps-1);
  3636. cmd:=copy(cmd,ps+1,255);
  3637. end;
  3638. interpret_option(opts,true);
  3639. end;
  3640. else
  3641. interpret_option(opts,true);
  3642. end;
  3643. end;
  3644. end;
  3645. procedure toption.writequickinfo;
  3646. var
  3647. s : string;
  3648. i : longint;
  3649. emptyOK : Boolean;
  3650. procedure addinfo(const hs:string);
  3651. begin
  3652. if s<>'' then
  3653. s:=s+' '+hs
  3654. else
  3655. s:=hs;
  3656. end;
  3657. begin
  3658. emptyOK:=False;
  3659. s:='';
  3660. i:=0;
  3661. while (i<length(quickinfo)) do
  3662. begin
  3663. inc(i);
  3664. case quickinfo[i] of
  3665. 'S' :
  3666. begin
  3667. inc(i);
  3668. case quickinfo[i] of
  3669. 'O' :
  3670. addinfo(lower(source_info.shortname));
  3671. 'P' :
  3672. addinfo(source_cpu_string);
  3673. else
  3674. IllegalPara('-i'+QuickInfo);
  3675. end;
  3676. end;
  3677. 'T' :
  3678. begin
  3679. inc(i);
  3680. case quickinfo[i] of
  3681. 'O' :
  3682. addinfo(lower(target_info.shortname));
  3683. 'P' :
  3684. AddInfo(target_cpu_string);
  3685. 'T' :
  3686. begin
  3687. addinfo(lower(self.parasubtarget));
  3688. emptyOK:=True;
  3689. end
  3690. else
  3691. IllegalPara('-i'+QuickInfo);
  3692. end;
  3693. end;
  3694. 'V' :
  3695. AddInfo(version_string);
  3696. 'W' :
  3697. AddInfo(full_version_string);
  3698. 'D' :
  3699. AddInfo(date_string);
  3700. '_' :
  3701. ;
  3702. else
  3703. IllegalPara('-i'+QuickInfo);
  3704. end;
  3705. end;
  3706. if (s<>'') or EmptyOK then
  3707. begin
  3708. writeln(s);
  3709. stopoptions(0);
  3710. end;
  3711. end;
  3712. procedure TOption.TargetOptions(def:boolean);
  3713. var
  3714. s : string;
  3715. i : integer;
  3716. target_unsup_features : tfeatures;
  3717. begin
  3718. if def then
  3719. def_system_macro(target_info.shortname)
  3720. else
  3721. undef_system_macro(target_info.shortname);
  3722. s:=target_info.extradefines;
  3723. while (s<>'') do
  3724. begin
  3725. i:=pos(';',s);
  3726. if i=0 then
  3727. i:=length(s)+1;
  3728. if def then
  3729. def_system_macro(Copy(s,1,i-1))
  3730. else
  3731. undef_system_macro(Copy(s,1,i-1));
  3732. delete(s,1,i);
  3733. end;
  3734. if (tf_winlikewidestring in target_info.flags) then
  3735. if def then
  3736. def_system_macro('FPC_WINLIKEWIDESTRING')
  3737. else
  3738. undef_system_macro('FPC_WINLIKEWIDESTRING');
  3739. if (tf_requires_proper_alignment in target_info.flags) then
  3740. if def then
  3741. def_system_macro('FPC_REQUIRES_PROPER_ALIGNMENT')
  3742. else
  3743. undef_system_macro('FPC_REQUIRES_PROPER_ALIGNMENT');
  3744. if (tf_init_final_units_by_calls in target_info.flags) then
  3745. if def then
  3746. def_system_macro('FPC_INIT_FINAL_UNITS_BY_CALLS')
  3747. else
  3748. undef_system_macro('FPC_INIT_FINAL_UNITS_BY_CALLS');
  3749. if source_info.system<>target_info.system then
  3750. if def then
  3751. def_system_macro('FPC_CROSSCOMPILING')
  3752. else
  3753. undef_system_macro('FPC_CROSSCOMPILING');
  3754. if source_info.cpu<>target_info.cpu then
  3755. if def then
  3756. def_system_macro('FPC_CPUCROSSCOMPILING')
  3757. else
  3758. def_system_macro('FPC_CPUCROSSCOMPILING');
  3759. if (tf_no_generic_stackcheck in target_info.flags) then
  3760. if def then
  3761. def_system_macro('FPC_NO_GENERIC_STACK_CHECK')
  3762. else
  3763. undef_system_macro('FPC_NO_GENERIC_STACK_CHECK');
  3764. if (tf_section_threadvars in target_info.flags) then
  3765. if def then
  3766. def_system_macro('FPC_SECTION_THREADVARS')
  3767. else
  3768. undef_system_macro('FPC_SECTION_THREADVARS');
  3769. if (tf_use_psabieh in target_info.flags) then
  3770. if def then
  3771. def_system_macro('FPC_USE_PSABIEH')
  3772. else
  3773. undef_system_macro('FPC_USE_PSABIEH');
  3774. { Code generation flags }
  3775. if (tf_pic_default in target_info.flags) then
  3776. if def then
  3777. include(init_settings.moduleswitches,cs_create_pic)
  3778. else
  3779. exclude(init_settings.moduleswitches,cs_create_pic);
  3780. { Resources support }
  3781. if (tf_has_winlike_resources in target_info.flags) then
  3782. if def then
  3783. def_system_macro('FPC_HAS_WINLIKERESOURCES')
  3784. else
  3785. undef_system_macro('FPC_HAS_WINLIKERESOURCES');
  3786. { Features }
  3787. case target_info.system of
  3788. system_arm_gba:
  3789. target_unsup_features:=[f_dynlibs];
  3790. system_arm_nds:
  3791. target_unsup_features:=[f_threading,f_commandargs,f_fileio,f_textio,f_consoleio,f_dynlibs];
  3792. system_i386_nativent:
  3793. // until these features are implemented, they are disabled in the compiler
  3794. target_unsup_features:=[f_stackcheck];
  3795. system_i8086_msdos:
  3796. target_unsup_features:=[f_threading,f_dynlibs];
  3797. system_i8086_win16:
  3798. target_unsup_features:=[f_threading];
  3799. system_jvm_java32,
  3800. system_jvm_android32:
  3801. target_unsup_features:=[f_heap,f_textio,f_consoleio,f_fileio,
  3802. f_variants,f_objects,f_commandargs,
  3803. f_processes,f_stackcheck,f_dynlibs,f_softfpu,f_objectivec1,f_resources];
  3804. system_arm_palmos,
  3805. system_m68k_palmos:
  3806. target_unsup_features:=[f_threading];
  3807. system_m68k_atari:
  3808. target_unsup_features:=[f_threading];
  3809. { classic amiga has dynamic libraries, but they cannot be integrated in the
  3810. normal dynlibs infrastructure due to architectural differences, so therefore
  3811. lets disable the feature. }
  3812. system_m68k_amiga:
  3813. target_unsup_features:=[f_dynlibs];
  3814. system_m68k_sinclairql:
  3815. target_unsup_features:=[f_threading,f_dynlibs];
  3816. system_z80_zxspectrum:
  3817. target_unsup_features:=[f_threading,f_dynlibs{,f_fileio,f_textio},f_commandargs,f_exitcode];
  3818. system_z80_msxdos:
  3819. target_unsup_features:=[f_threading,f_dynlibs];
  3820. else
  3821. target_unsup_features:=[];
  3822. end;
  3823. if def then
  3824. features:=features-target_unsup_features
  3825. else
  3826. features:=features+target_unsup_features;
  3827. {$if defined(hasamiga)}
  3828. { enable vlink as default linker on Amiga but not for cross compilers (for now) }
  3829. if (target_info.system in [system_m68k_amiga,system_powerpc_amiga]) and
  3830. not LinkerSetExplicitly then
  3831. include(init_settings.globalswitches,cs_link_vlink);
  3832. {$endif}
  3833. {$ifdef m68k}
  3834. { always enable vlink as default linker for the Sinclair QL and Atari }
  3835. if (target_info.system in [system_m68k_sinclairql,system_m68k_atari]) and
  3836. not LinkerSetExplicitly then
  3837. include(init_settings.globalswitches,cs_link_vlink);
  3838. {$endif m68k}
  3839. end;
  3840. procedure TOption.checkoptionscompatibility;
  3841. begin
  3842. {$ifdef wasm}
  3843. if (Ord(ts_wasm_no_exceptions in init_settings.targetswitches)+
  3844. Ord(ts_wasm_js_exceptions in init_settings.targetswitches)+
  3845. Ord(ts_wasm_native_exceptions in init_settings.targetswitches)+
  3846. Ord(ts_wasm_bf_exceptions in init_settings.targetswitches))>1 then
  3847. begin
  3848. Message(option_too_many_exception_modes);
  3849. StopOptions(1);
  3850. end;
  3851. {$endif}
  3852. {$ifdef i8086}
  3853. if (apptype=app_com) and (init_settings.x86memorymodel<>mm_tiny) then
  3854. begin
  3855. Message(option_com_files_require_tiny_model);
  3856. StopOptions(1);
  3857. end;
  3858. {$endif i8086}
  3859. {$ifndef i8086_link_intern_debuginfo}
  3860. if (cs_debuginfo in init_settings.moduleswitches) and
  3861. (target_info.system in [system_i8086_msdos,system_i8086_win16,system_i8086_embedded]) and
  3862. not (cs_link_extern in init_settings.globalswitches) then
  3863. begin
  3864. Message(option_debug_info_requires_external_linker);
  3865. include(init_settings.globalswitches,cs_link_extern);
  3866. end;
  3867. {$endif i8086_link_intern_debuginfo}
  3868. if (paratargetdbg in [dbg_dwarf2,dbg_dwarf3,dbg_dwarf4]) and
  3869. not(target_info.system in (systems_darwin+[system_i8086_msdos,system_i8086_embedded])) then
  3870. begin
  3871. { smartlink creation does not yet work with DWARF
  3872. debug info on most targets, but it works in internal assembler }
  3873. if (cs_create_smart in init_settings.moduleswitches) and
  3874. not (af_outputbinary in target_asm.flags) then
  3875. begin
  3876. Message(option_dwarf_smartlink_creation);
  3877. exclude(init_settings.moduleswitches,cs_create_smart);
  3878. end;
  3879. { smart linking does not yet work with DWARF debug info on most targets }
  3880. if (cs_link_smart in init_settings.globalswitches) then
  3881. begin
  3882. Message(option_dwarf_smart_linking);
  3883. ForceStaticLinking;
  3884. end;
  3885. end;
  3886. { external debug info is only supported for DWARF on darwin }
  3887. if (target_info.system in systems_darwin) and
  3888. (cs_link_separate_dbg_file in init_settings.globalswitches) and
  3889. not(paratargetdbg in [dbg_dwarf2,dbg_dwarf3,dbg_dwarf4]) then
  3890. begin
  3891. Message(option_debug_external_unsupported);
  3892. exclude(init_settings.globalswitches,cs_link_separate_dbg_file);
  3893. end;
  3894. { Also create a smartlinked version, on an assembler that
  3895. does not support smartlink sections like nasm?
  3896. This is not compatible with using internal linker. }
  3897. if ((cs_link_smart in init_settings.globalswitches) or
  3898. (cs_create_smart in init_settings.moduleswitches)) and
  3899. (af_needar in target_asm.flags) and
  3900. not (af_smartlink_sections in target_asm.flags) and
  3901. not (cs_link_extern in init_settings.globalswitches) and
  3902. (target_info.link<>ld_none) and
  3903. not (cs_link_nolink in init_settings.globalswitches) then
  3904. begin
  3905. Message(option_smart_link_requires_external_linker);
  3906. include(init_settings.globalswitches,cs_link_extern);
  3907. end;
  3908. end;
  3909. constructor TOption.create;
  3910. begin
  3911. LogoWritten:=false;
  3912. NoPressEnter:=false;
  3913. FirstPass:=false;
  3914. ABISetExplicitly:=false;
  3915. FPUSetExplicitly:=false;
  3916. CPUSetExplicitly:=false;
  3917. OptCPUSetExplicitly:=false;
  3918. FileLevel:=0;
  3919. Quickinfo:='';
  3920. ParaIncludeCfgPath:=TSearchPathList.Create;
  3921. ParaIncludePath:=TSearchPathList.Create;
  3922. ParaObjectPath:=TSearchPathList.Create;
  3923. ParaUnitPath:=TSearchPathList.Create;
  3924. ParaLibraryPath:=TSearchPathList.Create;
  3925. ParaFrameworkPath:=TSearchPathList.Create;
  3926. parapackagepath:=TSearchPathList.Create;
  3927. parapackages:=TFPHashObjectList.Create;
  3928. paranamespaces:=TCmdStrList.Create;
  3929. FillChar(ParaAlignment,sizeof(ParaAlignment),0);
  3930. MacVersionSet:=false;
  3931. paratarget:=system_none;
  3932. paratargetasm:=as_none;
  3933. paratargetdbg:=dbg_none;
  3934. LinkTypeSetExplicitly:=false;
  3935. LinkerSetExplicitly:=false;
  3936. end;
  3937. destructor TOption.destroy;
  3938. begin
  3939. ParaIncludeCfgPath.Free;
  3940. ParaIncludePath.Free;
  3941. ParaObjectPath.Free;
  3942. ParaUnitPath.Free;
  3943. ParaLibraryPath.Free;
  3944. ParaFrameworkPath.Free;
  3945. parapackagepath.Free;
  3946. ParaPackages.Free;
  3947. paranamespaces.free;
  3948. end;
  3949. {****************************************************************************
  3950. Callable Routines
  3951. ****************************************************************************}
  3952. function check_configfile(fn:string; var foundfn:string):boolean;
  3953. function CfgFileExists(const fn:string):boolean;
  3954. begin
  3955. Comment(V_Tried,'Configfile search: '+fn);
  3956. CfgFileExists:=FileExists(fn);
  3957. end;
  3958. var
  3959. {$ifdef Unix}
  3960. hs,
  3961. {$endif Unix}
  3962. configpath : string;
  3963. begin
  3964. foundfn:=fn;
  3965. check_configfile:=true;
  3966. { retrieve configpath }
  3967. configpath:=FixPath(GetEnvironmentVariable('PPC_CONFIG_PATH'),false);
  3968. {$ifdef Unix}
  3969. if configpath='' then
  3970. configpath:=ExpandFileName(FixPath(exepath+'../etc/',false));
  3971. {$endif}
  3972. {
  3973. Order to read configuration file :
  3974. try reading fpc.cfg in :
  3975. 1 - current dir
  3976. 2 - configpath
  3977. 3 - compiler path
  3978. }
  3979. if not FileExists(fn) then
  3980. begin
  3981. {$ifdef Unix}
  3982. hs:=GetEnvironmentVariable('HOME');
  3983. if (hs<>'') and CfgFileExists(FixPath(hs,false)+'.'+fn) then
  3984. foundfn:=FixPath(hs,false)+'.'+fn
  3985. else
  3986. {$endif}
  3987. if CfgFileExists(configpath+fn) then
  3988. foundfn:=configpath+fn
  3989. else
  3990. {$ifdef WINDOWS}
  3991. if (GetEnvironmentVariable('USERPROFILE')<>'') and CfgFileExists(FixPath(GetEnvironmentVariable('USERPROFILE'),false)+fn) then
  3992. foundfn:=FixPath(GetEnvironmentVariable('USERPROFILE'),false)+fn
  3993. else
  3994. if (GetEnvironmentVariable('ALLUSERSPROFILE')<>'') and CfgFileExists(FixPath(GetEnvironmentVariable('ALLUSERSPROFILE'),false)+fn) then
  3995. foundfn:=FixPath(GetEnvironmentVariable('ALLUSERSPROFILE'),false)+fn
  3996. else
  3997. {$endif WINDOWS}
  3998. {$ifndef Unix}
  3999. if CfgFileExists(exepath+fn) then
  4000. foundfn:=exepath+fn
  4001. else
  4002. {$else}
  4003. if CfgFileExists('/etc/'+fn) then
  4004. foundfn:='/etc/'+fn
  4005. else
  4006. {$endif}
  4007. check_configfile:=false;
  4008. end;
  4009. end;
  4010. procedure read_arguments(cmd:TCmdStr);
  4011. procedure def_cpu_macros;
  4012. var
  4013. abi : tabi;
  4014. fputype : tfputype;
  4015. cputype : tcputype;
  4016. controller: tcontrollertype;
  4017. s: string;
  4018. begin
  4019. {$ifdef llvm}
  4020. def_system_macro('CPULLVM');
  4021. {$endif}
  4022. for cputype:=low(tcputype) to high(tcputype) do
  4023. undef_system_macro('CPU'+Cputypestr[cputype]);
  4024. def_system_macro('CPU'+Cputypestr[init_settings.cputype]);
  4025. for fputype:=low(tfputype) to high(tfputype) do
  4026. undef_system_macro('FPU'+fputypestr[fputype]);
  4027. def_system_macro('FPU'+fputypestr[init_settings.fputype]);
  4028. {$PUSH}
  4029. {$WARN 6018 OFF} { Unreachable code due to compile time evaluation }
  4030. if ControllerSupport then
  4031. begin
  4032. for controller:=low(tcontrollertype) to high(tcontrollertype) do
  4033. begin
  4034. s:=embedded_controllers[controller].controllertypestr;
  4035. if s<>'' then
  4036. undef_system_macro('FPC_MCU_'+s);
  4037. end;
  4038. s:=embedded_controllers[init_settings.controllertype].controllertypestr;
  4039. if s<>'' then
  4040. def_system_macro('FPC_MCU_'+s);
  4041. end;
  4042. {$POP}
  4043. { define abi }
  4044. for abi:=low(tabi) to high(tabi) do
  4045. undef_system_macro('FPC_ABI_'+abiinfo[abi].name);
  4046. def_system_macro('FPC_ABI_'+abiinfo[target_info.abi].name);
  4047. { Define FPC_ABI_EABI in addition to FPC_ABI_EABIHF on EABI VFP hardfloat
  4048. systems since most code needs to behave the same on both}
  4049. if target_info.abi = abi_eabihf then
  4050. def_system_macro('FPC_ABI_EABI');
  4051. { using a case is pretty useless here (FK) }
  4052. { some stuff for TP compatibility }
  4053. {$ifdef i386}
  4054. def_system_macro('CPU86');
  4055. def_system_macro('CPU87');
  4056. def_system_macro('CPU386');
  4057. {$endif}
  4058. { new processor stuff }
  4059. {$ifdef i386}
  4060. def_system_macro('CPUI386');
  4061. def_system_macro('CPU32');
  4062. def_system_macro('CPUX86');
  4063. def_system_macro('FPC_HAS_TYPE_EXTENDED');
  4064. def_system_macro('FPC_HAS_TYPE_DOUBLE');
  4065. def_system_macro('FPC_HAS_TYPE_SINGLE');
  4066. {$endif}
  4067. {$ifdef m68k}
  4068. def_system_macro('CPU68');
  4069. def_system_macro('CPU68K');
  4070. def_system_macro('CPUM68K');
  4071. def_system_macro('CPU32');
  4072. def_system_macro('FPC_CURRENCY_IS_INT64');
  4073. def_system_macro('FPC_COMP_IS_INT64');
  4074. {$endif}
  4075. {$ifdef powerpc}
  4076. def_system_macro('CPUPOWERPC');
  4077. def_system_macro('CPUPOWERPC32');
  4078. def_system_macro('CPU32');
  4079. def_system_macro('FPC_CURRENCY_IS_INT64');
  4080. def_system_macro('FPC_COMP_IS_INT64');
  4081. {$endif}
  4082. {$ifdef POWERPC64}
  4083. def_system_macro('CPUPOWERPC');
  4084. def_system_macro('CPUPOWERPC64');
  4085. def_system_macro('CPU64');
  4086. def_system_macro('FPC_CURRENCY_IS_INT64');
  4087. def_system_macro('FPC_COMP_IS_INT64');
  4088. {$endif}
  4089. {$ifdef x86_64}
  4090. def_system_macro('CPUX86_64');
  4091. def_system_macro('CPUAMD64');
  4092. def_system_macro('CPU64');
  4093. def_system_macro('CPUX64');
  4094. { not supported for now, afaik (FK)
  4095. def_system_macro('FPC_HAS_TYPE_FLOAT128'); }
  4096. {$ifndef FPC_SUPPORT_X87_TYPES_ON_WIN64}
  4097. { normally, win64 doesn't support the legacy fpu }
  4098. if target_info.system=system_x86_64_win64 then
  4099. begin
  4100. def_system_macro('FPC_CURRENCY_IS_INT64');
  4101. def_system_macro('FPC_COMP_IS_INT64');
  4102. end;
  4103. {$endif FPC_SUPPORT_X87_TYPES_ON_WIN64}
  4104. {$endif}
  4105. {$ifdef sparc}
  4106. def_system_macro('CPUSPARCGEN');
  4107. def_system_macro('CPUSPARC');
  4108. def_system_macro('CPUSPARC32');
  4109. def_system_macro('CPU32');
  4110. def_system_macro('FPC_CURRENCY_IS_INT64');
  4111. def_system_macro('FPC_COMP_IS_INT64');
  4112. {$endif}
  4113. {$ifdef sparc64}
  4114. def_system_macro('CPUSPARCGEN');
  4115. def_system_macro('CPUSPARC64');
  4116. def_system_macro('CPU64');
  4117. def_system_macro('FPC_CURRENCY_IS_INT64');
  4118. def_system_macro('FPC_COMP_IS_INT64');
  4119. {$endif}
  4120. {$ifdef arm}
  4121. def_system_macro('CPUARM');
  4122. def_system_macro('CPU32');
  4123. def_system_macro('FPC_CURRENCY_IS_INT64');
  4124. def_system_macro('FPC_COMP_IS_INT64');
  4125. {$endif arm}
  4126. {$ifdef avr}
  4127. def_system_macro('CPUAVR');
  4128. def_system_macro('CPU16');
  4129. def_system_macro('FPC_CURRENCY_IS_INT64');
  4130. def_system_macro('FPC_COMP_IS_INT64');
  4131. {$endif avr}
  4132. {$ifdef jvm}
  4133. def_system_macro('CPUJVM');
  4134. def_system_macro('CPU32');
  4135. def_system_macro('FPC_CURRENCY_IS_INT64');
  4136. def_system_macro('FPC_COMP_IS_INT64');
  4137. {$endif jvm}
  4138. {$ifdef mipsel}
  4139. def_system_macro('CPUMIPS');
  4140. def_system_macro('CPUMIPSEL');
  4141. def_system_macro('CPUMIPS32');
  4142. def_system_macro('CPUMIPSEL32');
  4143. def_system_macro('CPU32');
  4144. def_system_macro('FPC_HAS_TYPE_DOUBLE');
  4145. def_system_macro('FPC_HAS_TYPE_SINGLE');
  4146. def_system_macro('FPC_INCLUDE_SOFTWARE_INT64_TO_DOUBLE');
  4147. def_system_macro('FPC_CURRENCY_IS_INT64');
  4148. def_system_macro('FPC_COMP_IS_INT64');
  4149. def_system_macro('FPC_REQUIRES_PROPER_ALIGNMENT');
  4150. { On most systems, locals are accessed relative to base pointer,
  4151. but for MIPS cpu, they are accessed relative to stack pointer.
  4152. This needs adaptation for so low level routines,
  4153. like MethodPointerLocal and related objects unit functions. }
  4154. def_system_macro('FPC_LOCALS_ARE_STACK_REG_RELATIVE');
  4155. {$endif mipsel}
  4156. {$ifdef mipseb}
  4157. def_system_macro('CPUMIPS');
  4158. def_system_macro('CPUMIPSEB');
  4159. def_system_macro('CPUMIPS32');
  4160. def_system_macro('CPUMIPSEB32');
  4161. def_system_macro('CPU32');
  4162. def_system_macro('FPC_HAS_TYPE_DOUBLE');
  4163. def_system_macro('FPC_HAS_TYPE_SINGLE');
  4164. def_system_macro('FPC_INCLUDE_SOFTWARE_INT64_TO_DOUBLE');
  4165. def_system_macro('FPC_CURRENCY_IS_INT64');
  4166. def_system_macro('FPC_COMP_IS_INT64');
  4167. def_system_macro('FPC_REQUIRES_PROPER_ALIGNMENT');
  4168. { See comment above for mipsel }
  4169. def_system_macro('FPC_LOCALS_ARE_STACK_REG_RELATIVE');
  4170. {$endif mipseb}
  4171. {$ifdef mips64eb}
  4172. def_system_macro('CPUMIPS');
  4173. def_system_macro('CPUMIPS64');
  4174. def_system_macro('CPUMIPSEB64');
  4175. def_system_macro('CPUMIPS64EB');
  4176. def_system_macro('CPU64');
  4177. def_system_macro('FPC_INCLUDE_SOFTWARE_INT64_TO_DOUBLE');
  4178. def_system_macro('FPC_CURRENCY_IS_INT64');
  4179. def_system_macro('FPC_COMP_IS_INT64');
  4180. def_system_macro('FPC_REQUIRES_PROPER_ALIGNMENT');
  4181. { See comment above for mipsel }
  4182. def_system_macro('FPC_LOCALS_ARE_STACK_REG_RELATIVE');
  4183. {$endif mips64eb}
  4184. {$ifdef mips64el}
  4185. def_system_macro('CPUMIPS');
  4186. def_system_macro('CPUMIPS64');
  4187. def_system_macro('CPUMIPSEL64');
  4188. def_system_macro('CPUMIPS64EL');
  4189. def_system_macro('CPU64');
  4190. def_system_macro('FPC_HAS_TYPE_DOUBLE');
  4191. def_system_macro('FPC_HAS_TYPE_SINGLE');
  4192. def_system_macro('FPC_INCLUDE_SOFTWARE_INT64_TO_DOUBLE');
  4193. def_system_macro('FPC_CURRENCY_IS_INT64');
  4194. def_system_macro('FPC_COMP_IS_INT64');
  4195. def_system_macro('FPC_REQUIRES_PROPER_ALIGNMENT');
  4196. { On most systems, locals are accessed relative to base pointer,
  4197. but for MIPS cpu, they are accessed relative to stack pointer.
  4198. This needs adaptation for so low level routines,
  4199. like MethodPointerLocal and related objects unit functions. }
  4200. def_system_macro('FPC_LOCALS_ARE_STACK_REG_RELATIVE');
  4201. {$endif mips64el}
  4202. {$ifdef i8086}
  4203. def_system_macro('CPU86'); { Borland compatibility }
  4204. def_system_macro('CPU87'); { Borland compatibility }
  4205. def_system_macro('CPUI8086');
  4206. def_system_macro('CPU16');
  4207. def_system_macro('FPC_HAS_TYPE_EXTENDED');
  4208. def_system_macro('FPC_HAS_TYPE_DOUBLE');
  4209. def_system_macro('FPC_HAS_TYPE_SINGLE');
  4210. case init_settings.x86memorymodel of
  4211. mm_tiny: def_system_macro('FPC_MM_TINY');
  4212. mm_small: def_system_macro('FPC_MM_SMALL');
  4213. mm_medium: def_system_macro('FPC_MM_MEDIUM');
  4214. mm_compact: def_system_macro('FPC_MM_COMPACT');
  4215. mm_large: def_system_macro('FPC_MM_LARGE');
  4216. mm_huge: def_system_macro('FPC_MM_HUGE');
  4217. end;
  4218. {$endif i8086}
  4219. {$ifdef aarch64}
  4220. def_system_macro('CPUAARCH64');
  4221. def_system_macro('CPU64');
  4222. def_system_macro('FPC_CURRENCY_IS_INT64');
  4223. def_system_macro('FPC_COMP_IS_INT64');
  4224. {$endif aarch64}
  4225. {$ifdef riscv32}
  4226. def_system_macro('CPURISCV');
  4227. def_system_macro('CPURISCV32');
  4228. def_system_macro('CPU32');
  4229. def_system_macro('FPC_CURRENCY_IS_INT64');
  4230. def_system_macro('FPC_COMP_IS_INT64');
  4231. def_system_macro('FPC_REQUIRES_PROPER_ALIGNMENT');
  4232. {$endif riscv32}
  4233. {$ifdef riscv64}
  4234. def_system_macro('CPURISCV');
  4235. def_system_macro('CPURISCV64');
  4236. def_system_macro('CPU64');
  4237. def_system_macro('FPC_CURRENCY_IS_INT64');
  4238. def_system_macro('FPC_COMP_IS_INT64');
  4239. def_system_macro('FPC_REQUIRES_PROPER_ALIGNMENT');
  4240. {$endif riscv64}
  4241. {$ifdef xtensa}
  4242. def_system_macro('CPUXTENSA');
  4243. def_system_macro('CPU32');
  4244. def_system_macro('FPC_CURRENCY_IS_INT64');
  4245. def_system_macro('FPC_COMP_IS_INT64');
  4246. def_system_macro('FPC_REQUIRES_PROPER_ALIGNMENT');
  4247. {$endif xtensa}
  4248. {$ifdef z80}
  4249. def_system_macro('CPUZ80');
  4250. def_system_macro('CPU16');
  4251. def_system_macro('FPC_CURRENCY_IS_INT64');
  4252. def_system_macro('FPC_COMP_IS_INT64');
  4253. {$endif z80}
  4254. {$ifdef wasm32}
  4255. def_system_macro('CPUWASM');
  4256. def_system_macro('CPUWASM32');
  4257. def_system_macro('CPU32');
  4258. def_system_macro('FPC_CURRENCY_IS_INT64');
  4259. def_system_macro('FPC_COMP_IS_INT64');
  4260. {$endif wasm32}
  4261. {$ifdef loongarch64}
  4262. def_system_macro('CPULOONGARCH');
  4263. def_system_macro('CPULOONGARCH64');
  4264. def_system_macro('CPU64');
  4265. def_system_macro('FPC_CURRENCY_IS_INT64');
  4266. def_system_macro('FPC_COMP_IS_INT64');
  4267. def_system_macro('FPC_REQUIRES_PROPER_ALIGNMENT');
  4268. def_system_macro('FPC_LOCALS_ARE_STACK_REG_RELATIVE');
  4269. {$endif loongarch64}
  4270. {$if defined(cpu8bitalu)}
  4271. def_system_macro('CPUINT8');
  4272. {$elseif defined(cpu16bitalu)}
  4273. def_system_macro('CPUINT16');
  4274. {$elseif defined(cpu32bitalu)}
  4275. def_system_macro('CPUINT32');
  4276. {$elseif defined(cpu64bitalu)}
  4277. def_system_macro('CPUINT64');
  4278. {$endif defined(cpu64bitalu)}
  4279. {$if defined(avr)}
  4280. def_system_macro('FPC_HAS_INTERNAL_ABS_SHORTINT');
  4281. {$endif}
  4282. {$if defined(i8086) or defined(avr)}
  4283. def_system_macro('FPC_HAS_INTERNAL_ABS_SMALLINT');
  4284. {$endif i8086 or avr}
  4285. { abs(long) is handled internally on all CPUs }
  4286. def_system_macro('FPC_HAS_INTERNAL_ABS_LONG');
  4287. {$if defined(i8086) or defined(i386) or defined(x86_64) or defined(powerpc64) or defined(aarch64)}
  4288. def_system_macro('FPC_HAS_INTERNAL_ABS_INT64');
  4289. {$endif i8086 or i386 or x86_64 or powerpc64 or aarch64}
  4290. def_system_macro('FPC_HAS_UNICODESTRING');
  4291. def_system_macro('FPC_RTTI_PACKSET1');
  4292. def_system_macro('FPC_HAS_CPSTRING');
  4293. {$ifdef x86_64}
  4294. def_system_macro('FPC_HAS_RIP_RELATIVE');
  4295. {$endif x86_64}
  4296. def_system_macro('FPC_HAS_CEXTENDED');
  4297. def_system_macro('FPC_HAS_RESSTRINITS');
  4298. { these cpus have an inline rol/ror implementaion }
  4299. {$ifdef cpurox}
  4300. {$ifdef m68k}
  4301. if CPUM68K_HAS_ROLROR in cpu_capabilities[init_settings.cputype] then
  4302. def_system_macro('FPC_HAS_INTERNAL_ROX');
  4303. {$else}
  4304. def_system_macro('FPC_HAS_INTERNAL_ROX');
  4305. {$endif}
  4306. {$endif}
  4307. {$ifdef powerpc64}
  4308. def_system_macro('FPC_HAS_LWSYNC');
  4309. {$endif}
  4310. { currently, all supported CPUs have an internal sar implementation }
  4311. def_system_macro('FPC_HAS_INTERNAL_SAR');
  4312. {$ifdef SUPPORT_GET_FRAME}
  4313. def_system_macro('INTERNAL_BACKTRACE');
  4314. {$endif SUPPORT_GET_FRAME}
  4315. def_system_macro('STR_CONCAT_PROCS');
  4316. {$warnings off}
  4317. if pocall_default = pocall_register then
  4318. def_system_macro('REGCALL');
  4319. {$warnings on}
  4320. end;
  4321. var
  4322. env: ansistring;
  4323. i : tfeature;
  4324. j : longint;
  4325. tmplist : TCmdStrList;
  4326. cmditem,
  4327. tmpcmditem : TCmdStrListItem;
  4328. cmdstr : TCmdStr;
  4329. {$if defined(cpucapabilities)}
  4330. cpuflag : tcpuflags;
  4331. {$endif defined(cpucapabilities)}
  4332. {$if defined(fpucapabilities)}
  4333. fpuflag : tfpuflags;
  4334. {$endif defined(fpucapabilities)}
  4335. {$if defined(cpucapabilities) or defined(fpucapabilities)}
  4336. hs : string;
  4337. {$endif defined(cpucapabilities) or defined(fpucapabilities)}
  4338. begin
  4339. option:=coption.create;
  4340. disable_configfile:=false;
  4341. { Non-core target defines }
  4342. Option.TargetOptions(true);
  4343. { get default messagefile }
  4344. msgfilename:=GetEnvironmentVariable('PPC_ERROR_FILE');
  4345. { default configfile can be specified on the commandline,
  4346. remove it first }
  4347. if (cmd<>'') and (cmd[1]='[') then
  4348. begin
  4349. ppccfg:=Copy(cmd,2,pos(']',cmd)-2);
  4350. Delete(cmd,1,pos(']',cmd));
  4351. end
  4352. else
  4353. ppccfg:='fpc.cfg';
  4354. { first pass reading of parameters, only -i -v -T etc.}
  4355. option.firstpass:=true;
  4356. if cmd<>'' then
  4357. option.parsecmd(cmd)
  4358. else
  4359. begin
  4360. option.read_parameters;
  4361. { Write only quickinfo }
  4362. if option.quickinfo<>'' then
  4363. option.writequickinfo;
  4364. end;
  4365. option.firstpass:=false;
  4366. { redefine target options so all defines are written even if no -Txxx is passed on the command line }
  4367. Option.TargetOptions(true);
  4368. { target is set here, for wince the default app type is gui }
  4369. if target_info.system in systems_wince then
  4370. SetApptype(app_gui)
  4371. else
  4372. SetApptype(apptype);
  4373. { default defines }
  4374. def_system_macro(target_info.shortname);
  4375. def_system_macro('FPC');
  4376. def_system_macro('VER'+version_nr);
  4377. def_system_macro('VER'+version_nr+'_'+release_nr);
  4378. def_system_macro('VER'+version_nr+'_'+release_nr+'_'+patch_nr);
  4379. { Temporary defines, until things settle down }
  4380. def_system_macro('FPC_HAS_OPERATOR_ENUMERATOR');
  4381. def_system_macro('FPC_HAS_CONSTREF');
  4382. def_system_macro('FPC_STATICRIPFIXED');
  4383. def_system_macro('FPC_VARIANTCOPY_FIXED');
  4384. def_system_macro('FPC_DYNARRAYCOPY_FIXED');
  4385. def_system_macro('FPC_HAS_MEMBAR');
  4386. def_system_macro('FPC_SETBASE_USED');
  4387. def_system_macro('FPC_ALIGNED_THREADVARTABLES');
  4388. { don't remove this, it's also for fpdoc necessary (FK) }
  4389. def_system_macro('FPC_HAS_FEATURE_SUPPORT');
  4390. if (Option.parasubtarget<>'') then
  4391. begin
  4392. def_system_macro('FPC_SUBTARGET_'+Option.parasubtarget);
  4393. if cs_support_macro in init_settings.moduleswitches then
  4394. set_system_macro('FPC_SUBTARGET',Option.parasubtarget)
  4395. else
  4396. set_system_compvar('FPC_SUBTARGET',Option.parasubtarget);
  4397. // So it can be used in macro substitution.
  4398. globals.subtarget:=Option.parasubtarget;
  4399. end;
  4400. { make cpu makros available when reading the config files the second time }
  4401. def_cpu_macros;
  4402. set_endianess_macros;
  4403. if tf_cld in target_info.flags then
  4404. if not UpdateTargetSwitchStr('CLD', init_settings.targetswitches, true) then
  4405. InternalError(2013092801);
  4406. if tf_x86_far_procs_push_odd_bp in target_info.flags then
  4407. if not UpdateTargetSwitchStr('FARPROCSPUSHODDBP', init_settings.targetswitches, true) then
  4408. InternalError(2013092802);
  4409. { Use standard Android NDK prefixes when cross-compiling }
  4410. if (source_info.system<>target_info.system) and (target_info.system in systems_android) then
  4411. case target_info.system of
  4412. system_arm_android:
  4413. utilsprefix:='arm-linux-androideabi-';
  4414. system_i386_android:
  4415. utilsprefix:='i686-linux-android-';
  4416. else
  4417. utilsprefix:=target_cpu_string + '-linux-android-';
  4418. end;
  4419. { Set up default value for the heap on Amiga-likes (values only apply if the OSHeap allocator is used) }
  4420. if target_info.system in systems_amigalike then
  4421. begin
  4422. case target_info.system of
  4423. system_m68k_amiga:
  4424. heapsize:=256*1024;
  4425. system_powerpc_amiga,
  4426. system_powerpc_morphos,
  4427. system_arm_aros,
  4428. system_i386_aros,
  4429. system_x86_64_aros:
  4430. heapsize:=1024*1024;
  4431. else
  4432. heapsize:=256*1024;
  4433. end;
  4434. end;
  4435. if target_info.system in (systems_embedded+systems_freertos+[system_z80_zxspectrum,system_z80_msxdos]) then
  4436. begin
  4437. case target_info.system of
  4438. {$ifdef AVR}
  4439. system_avr_embedded:
  4440. if init_settings.controllertype=ct_avrsim then
  4441. heapsize:=8192
  4442. else
  4443. heapsize:=128;
  4444. {$endif AVR}
  4445. system_arm_freertos:
  4446. heapsize:=8192;
  4447. system_xtensa_freertos:
  4448. { keep default value }
  4449. ;
  4450. system_arm_embedded:
  4451. heapsize:=256;
  4452. system_mipsel_embedded:
  4453. heapsize:=256;
  4454. else
  4455. heapsize:=256;
  4456. end;
  4457. end;
  4458. { read configuration file }
  4459. if (not disable_configfile) and
  4460. (ppccfg<>'') then
  4461. read_configfile:=check_configfile(ppccfg,ppccfg)
  4462. else
  4463. read_configfile := false;
  4464. if (option.parasubtarget<>'') then
  4465. begin
  4466. subcfg:='fpc-'+lower(option.parasubtarget)+'.cfg';
  4467. read_subfile:=check_configfile(subcfg,subcfg);
  4468. // Warn if we didn't find an architecture-specific file
  4469. if not read_subfile then
  4470. message2(option_subtarget_config_not_found,option.parasubtarget,subcfg);
  4471. end;
  4472. { Read commandline and configfile }
  4473. param_file:='';
  4474. { read configfile }
  4475. if read_configfile then
  4476. option.interpret_file(ppccfg);
  4477. if read_subfile then
  4478. option.interpret_file(subcfg);
  4479. { read parameters again to override config file }
  4480. if cmd<>'' then
  4481. option.parsecmd(cmd)
  4482. else
  4483. begin
  4484. { Write help pages if no parameters are passed }
  4485. if (paramcount=0) then
  4486. Option.WriteHelpPages;
  4487. option.read_parameters;
  4488. { Write only quickinfo }
  4489. if option.quickinfo<>'' then
  4490. option.writequickinfo;
  4491. end;
  4492. { check the compatibility of different options and adjust them if necessary
  4493. (and print possible errors)
  4494. }
  4495. option.checkoptionscompatibility;
  4496. { uses the CPUXXX-defines and target_info to determine whether the selected
  4497. target processor, if any, is supported }
  4498. Option.VerifyTargetProcessor;
  4499. { Stop if errors in options }
  4500. if ErrorCount>0 then
  4501. StopOptions(1);
  4502. { Write logo }
  4503. if option.ParaLogo then
  4504. option.writelogo;
  4505. { Check file to compile }
  4506. if param_file='' then
  4507. begin
  4508. Message(option_no_source_found);
  4509. StopOptions(1);
  4510. end;
  4511. {$ifndef Unix}
  4512. param_file:=FixFileName(param_file);
  4513. {$endif not unix}
  4514. inputfilepath:=ExtractFilePath(param_file);
  4515. inputfilename:=ExtractFileName(param_file);
  4516. if ExtractFileExt(inputfilename)='' then
  4517. begin
  4518. if FileExists(inputfilepath+ChangeFileExt(inputfilename,sourceext)) then
  4519. inputfilename:=ChangeFileExt(inputfilename,sourceext)
  4520. else if FileExists(inputfilepath+ChangeFileExt(inputfilename,pasext)) then
  4521. inputfilename:=ChangeFileExt(inputfilename,pasext)
  4522. else if ((m_mac in current_settings.modeswitches) or
  4523. (tf_p_ext_support in target_info.flags))
  4524. and FileExists(inputfilepath+ChangeFileExt(inputfilename,pext)) then
  4525. inputfilename:=ChangeFileExt(inputfilename,pext);
  4526. end;
  4527. { Check output dir }
  4528. if (OutputExeDir<>'') and
  4529. not PathExists(OutputExeDir,false) then
  4530. begin
  4531. Message1(general_e_path_does_not_exist,OutputExeDir);
  4532. StopOptions(1);
  4533. end;
  4534. { Add paths specified with parameters to the searchpaths }
  4535. UnitSearchPath.AddList(option.ParaUnitPath,true);
  4536. ObjectSearchPath.AddList(option.ParaObjectPath,true);
  4537. IncludeSearchPath.AddList(option.ParaIncludePath,true);
  4538. LibrarySearchPath.AddList(option.ParaLibraryPath,true);
  4539. FrameworkSearchPath.AddList(option.ParaFrameworkPath,true);
  4540. packagesearchpath.addlist(option.parapackagepath,true);
  4541. for j:=0 to option.parapackages.count-1 do
  4542. add_package(option.parapackages.NameOfIndex(j),true,true);
  4543. { add default namespaces }
  4544. tmplist:=TCmdStrList.Create;
  4545. cmditem:=TCmdStrListItem(option.paranamespaces.First);
  4546. while assigned(cmditem) do
  4547. begin
  4548. { use a temporary list cause if ";" are involved we need to reverse the
  4549. order due to how TCmdStrList behaves }
  4550. cmdstr:=cmditem.str;
  4551. repeat
  4552. j:=Pos(';',cmdstr);
  4553. if j>0 then
  4554. begin
  4555. tmplist.insert(copy(cmdstr,1,j-1));
  4556. delete(cmdstr,1,j);
  4557. end
  4558. else
  4559. tmplist.insert(cmdstr);
  4560. until j=0;
  4561. tmpcmditem:=TCmdStrListItem(tmplist.First);
  4562. while assigned(tmpcmditem) do
  4563. begin
  4564. namespacelist.insert(tmpcmditem.Str);
  4565. tmpcmditem:=TCmdStrListItem(tmpcmditem.Next);
  4566. end;
  4567. tmplist.clear;
  4568. cmditem:=TCmdStrListItem(cmditem.Next);
  4569. end;
  4570. tmplist.Free;
  4571. { add unit environment and exepath to the unit search path }
  4572. if inputfilepath<>'' then
  4573. Unitsearchpath.AddPath(inputfilepath,true);
  4574. if not disable_configfile then
  4575. begin
  4576. env:=GetEnvironmentVariable(target_info.unit_env);
  4577. if env<>'' then
  4578. UnitSearchPath.AddPath(GetEnvironmentVariable(target_info.unit_env),false);
  4579. end;
  4580. {$ifdef Unix}
  4581. fpcdir:=FixPath(GetEnvironmentVariable('FPCDIR'),false);
  4582. if fpcdir='' then
  4583. begin
  4584. if PathExists('/usr/local/lib/fpc/'+version_string,true) then
  4585. fpcdir:='/usr/local/lib/fpc/'+version_string+'/'
  4586. else
  4587. fpcdir:='/usr/lib/fpc/'+version_string+'/';
  4588. end;
  4589. {$else unix}
  4590. fpcdir:=FixPath(GetEnvironmentVariable('FPCDIR'),false);
  4591. if fpcdir='' then
  4592. begin
  4593. fpcdir:=ExePath+'../';
  4594. if not(PathExists(fpcdir+'units',true)) and
  4595. not(PathExists(fpcdir+'rtl',true)) then
  4596. fpcdir:=fpcdir+'../';
  4597. end;
  4598. {$endif unix}
  4599. { first try development RTL, else use the default installation path }
  4600. if not disable_configfile then
  4601. begin
  4602. if PathExists(FpcDir+'rtl',true) then
  4603. if (tf_use_8_3 in Source_Info.Flags) or
  4604. (tf_use_8_3 in Target_Info.Flags) then
  4605. UnitSearchPath.AddPath(FpcDir+'rtl/'+target_os_string,false)
  4606. else
  4607. UnitSearchPath.AddPath(FpcDir+'rtl/'+target_full_string,false)
  4608. else
  4609. if (tf_use_8_3 in Source_Info.Flags) or
  4610. (tf_use_8_3 in Target_Info.Flags) then
  4611. UnitSearchPath.AddPath(FpcDir+'units/'+target_os_string+'/rtl',false)
  4612. else
  4613. UnitSearchPath.AddPath(FpcDir+'units/'+target_full_string+'/rtl',false);
  4614. end;
  4615. { Add exepath if the exe is not in the current dir, because that is always searched already.
  4616. Do not add it when linking on the target because then we can maybe already find
  4617. .o files that are not for the target }
  4618. if (ExePath<>cfileutl.GetCurrentDir) and
  4619. not(cs_link_on_target in init_settings.globalswitches) then
  4620. UnitSearchPath.AddPath(ExePath,false);
  4621. { Add unit dir to the object and library path }
  4622. objectsearchpath.AddList(unitsearchpath,false);
  4623. librarysearchpath.AddList(unitsearchpath,false);
  4624. {$ifdef llvm}
  4625. { default to clang }
  4626. if (option.paratargetasm=as_none) then
  4627. begin
  4628. if not(target_info.system in systems_darwin) then
  4629. option.paratargetasm:=as_clang_llvm
  4630. else
  4631. option.paratargetasm:=as_clang_llvm_darwin;
  4632. end;
  4633. {$endif llvm}
  4634. { maybe override assembler }
  4635. if (option.paratargetasm<>as_none) then
  4636. begin
  4637. if (option.paratargetasm=as_default) then
  4638. begin
  4639. option.paratargetasm:=target_info.assem;
  4640. end;
  4641. if not set_target_asm(option.paratargetasm) then
  4642. begin
  4643. if assigned(asminfos[option.paratargetasm]) then
  4644. Message2(option_incompatible_asm,asminfos[option.paratargetasm]^.idtxt,target_info.name)
  4645. else
  4646. Message2(option_incompatible_asm,'<invalid assembler>',target_info.name);
  4647. set_target_asm(target_info.assemextern);
  4648. Message1(option_asm_forced,target_asm.idtxt);
  4649. end;
  4650. if (af_no_debug in asminfos[option.paratargetasm]^.flags) and
  4651. (option.paratargetdbg<>dbg_none) then
  4652. begin
  4653. Message1(option_confict_asm_debug,
  4654. asminfos[option.paratargetasm]^.idtxt);
  4655. option.paratargetdbg:=dbg_none;
  4656. exclude(init_settings.moduleswitches,cs_debuginfo);
  4657. end;
  4658. { Some assemblers, like clang, do not support
  4659. stabs debugging format, switch to dwardé in that case }
  4660. if (af_no_stabs in asminfos[option.paratargetasm]^.flags) and
  4661. (option.paratargetdbg=dbg_stabs) then
  4662. begin
  4663. option.paratargetdbg:=dbg_dwarf2;
  4664. end;
  4665. end;
  4666. {TOptionheck a second time as we might have changed assembler just above }
  4667. option.checkoptionscompatibility;
  4668. { maybe override debug info format }
  4669. if (option.paratargetdbg<>dbg_none) then
  4670. if not set_target_dbg(option.paratargetdbg) then
  4671. Message(option_w_unsupported_debug_format);
  4672. { switch assembler if it's binary and we got -a on the cmdline }
  4673. if (af_outputbinary in target_asm.flags) and
  4674. ((cs_asm_leave in init_settings.globalswitches) or
  4675. { if -s is passed, we shouldn't call the internal assembler }
  4676. (cs_asm_extern in init_settings.globalswitches)) then
  4677. begin
  4678. Message(option_switch_bin_to_src_assembler);
  4679. {$ifdef llvm}
  4680. if not(target_info.system in systems_darwin) then
  4681. set_target_asm(as_clang_llvm)
  4682. else
  4683. set_target_asm(as_clang_llvm_darwin);
  4684. {$else}
  4685. set_target_asm(target_info.assemextern);
  4686. {$endif}
  4687. { At least i8086 needs that for nasm and -CX
  4688. which is incompatible with internal linker }
  4689. option.checkoptionscompatibility;
  4690. end;
  4691. { Force use of external linker if there is no
  4692. internal linker or the linking is skipped }
  4693. if not(cs_link_extern in init_settings.globalswitches) and
  4694. ((target_info.link=ld_none) or
  4695. (cs_link_nolink in init_settings.globalswitches)) then
  4696. begin
  4697. include(init_settings.globalswitches,cs_link_extern);
  4698. end;
  4699. { turn off stripping if compiling with debuginfo or profile }
  4700. if (
  4701. (cs_debuginfo in init_settings.moduleswitches) or
  4702. (cs_profile in init_settings.moduleswitches)
  4703. ) and
  4704. not(cs_link_separate_dbg_file in init_settings.globalswitches) then
  4705. exclude(init_settings.globalswitches,cs_link_strip);
  4706. { choose a reasonable tls model }
  4707. if (tf_section_threadvars in target_info.flags) and (init_settings.tlsmodel=tlsm_none) then
  4708. begin
  4709. if cs_create_pic in init_settings.moduleswitches then
  4710. init_settings.tlsmodel:=tlsm_global_dynamic
  4711. else
  4712. init_settings.tlsmodel:=tlsm_local_exec;
  4713. end;
  4714. { set Mac OS X version default macros if not specified explicitly }
  4715. option.MaybeSetDefaultMacVersionMacro;
  4716. {$ifdef XTENSA}
  4717. { set ESP32 or ESP8266 default SDK versions }
  4718. option.MaybeSetIdfVersionMacro;
  4719. {$endif XTENSA}
  4720. {$ifdef cpufpemu}
  4721. { force fpu emulation on arm/wince, arm/gba, arm/embedded and arm/nds etc.
  4722. if fpu type not explicitly set }
  4723. if not(option.FPUSetExplicitly) and
  4724. ((target_info.system in [system_arm_wince,system_arm_gba,
  4725. system_m68k_amiga,system_m68k_atari,
  4726. system_arm_nds,system_arm_embedded,system_arm_freertos,
  4727. system_riscv32_embedded,system_riscv64_embedded,system_xtensa_linux,
  4728. system_z80_embedded,system_z80_zxspectrum,system_riscv32_freertos])
  4729. {$ifdef arm}
  4730. or (target_info.abi=abi_eabi)
  4731. {$endif arm}
  4732. )
  4733. or (init_settings.fputype=fpu_soft)
  4734. then
  4735. begin
  4736. include(init_settings.moduleswitches,cs_fp_emulation);
  4737. { cs_fp_emulation and fpu_soft are equal on arm and m68k }
  4738. init_settings.fputype:=fpu_soft;
  4739. end;
  4740. {$endif cpufpemu}
  4741. {$ifdef i386}
  4742. if target_info.system in systems_i386_default_486 then
  4743. begin
  4744. { Avoid use of MMX/CMOVcc instructions on older systems.
  4745. Some systems might not handle these instructions correctly,
  4746. Used emulators might also be problematic. PM }
  4747. if not option.CPUSetExplicitly then
  4748. init_settings.cputype:=cpu_486;
  4749. end;
  4750. case target_info.system of
  4751. system_i386_android:
  4752. begin
  4753. { set default cpu type to PentiumM for Android unless specified otherwise }
  4754. if not option.CPUSetExplicitly then
  4755. init_settings.cputype:=cpu_PentiumM;
  4756. if not option.OptCPUSetExplicitly then
  4757. init_settings.optimizecputype:=cpu_PentiumM;
  4758. { set default fpu type to SSSE3 for Android unless specified otherwise }
  4759. if not option.FPUSetExplicitly then
  4760. init_settings.fputype:=fpu_ssse3;
  4761. end;
  4762. else
  4763. ;
  4764. end;
  4765. {$endif i386}
  4766. {$ifdef xtensa}
  4767. { xtensa-linux target does not support controller setting option -Wp }
  4768. if not(option.FPUSetExplicitly) and not(target_info.system = system_xtensa_linux) then
  4769. begin
  4770. init_settings.fputype:=embedded_controllers[init_settings.controllertype].fputype;
  4771. if (init_settings.fputype=fpu_soft) then
  4772. include(init_settings.moduleswitches,cs_fp_emulation);
  4773. end;
  4774. if not(option.CPUSetExplicitly) and (target_info.system=system_xtensa_linux) then
  4775. init_settings.cputype:=cpu_lx6;
  4776. if (target_info.system in [system_xtensa_embedded,system_xtensa_freertos]) and not(option.ABISetExplicitly) then
  4777. begin
  4778. if CPUXTENSA_REGWINDOW in cpu_capabilities[init_settings.cputype] then
  4779. target_info.abi:=abi_xtensa_windowed
  4780. else
  4781. target_info.abi:=abi_xtensa_call0;
  4782. end;
  4783. {$endif xtensa}
  4784. {$ifdef arm}
  4785. case target_info.system of
  4786. system_arm_ios:
  4787. begin
  4788. { set default cpu type to ARMv7 for Darwin unless specified otherwise, and fpu
  4789. to VFPv3 (that's what all 32 bit ARM iOS devices use nowadays)
  4790. }
  4791. if not option.CPUSetExplicitly then
  4792. init_settings.cputype:=cpu_armv7;
  4793. if not option.OptCPUSetExplicitly then
  4794. init_settings.optimizecputype:=cpu_armv7;
  4795. if not option.FPUSetExplicitly then
  4796. init_settings.fputype:=fpu_vfpv3;
  4797. end;
  4798. system_arm_android:
  4799. begin
  4800. { set default cpu type to ARMv5T for Android unless specified otherwise }
  4801. if not option.CPUSetExplicitly then
  4802. init_settings.cputype:=cpu_armv5t;
  4803. if not option.OptCPUSetExplicitly then
  4804. init_settings.optimizecputype:=cpu_armv5t;
  4805. end;
  4806. else
  4807. ;
  4808. end;
  4809. { set ABI defaults }
  4810. case target_info.abi of
  4811. abi_eabihf:
  4812. { set default cpu type to ARMv7a for ARMHF unless specified otherwise }
  4813. begin
  4814. {$ifdef CPUARMV6}
  4815. { if the compiler is built for armv6, then
  4816. inherit this setting, e.g. Raspian is armhf but
  4817. only armv6, this makes rebuilds of the compiler
  4818. easier }
  4819. if not option.CPUSetExplicitly then
  4820. init_settings.cputype:=cpu_armv6;
  4821. if not option.OptCPUSetExplicitly then
  4822. init_settings.optimizecputype:=cpu_armv6;
  4823. {$else CPUARMV6}
  4824. if not option.CPUSetExplicitly then
  4825. init_settings.cputype:=cpu_armv7a;
  4826. if not option.OptCPUSetExplicitly then
  4827. init_settings.optimizecputype:=cpu_armv7a;
  4828. {$endif CPUARMV6}
  4829. { Set FPU type }
  4830. if not(option.FPUSetExplicitly) then
  4831. begin
  4832. if init_settings.cputype < cpu_armv7 then
  4833. init_settings.fputype:=fpu_vfpv2
  4834. else
  4835. init_settings.fputype:=fpu_vfpv3_d16;
  4836. end
  4837. else
  4838. begin
  4839. if (not(FPUARM_HAS_VFP_EXTENSION in fpu_capabilities[init_settings.fputype]))
  4840. or (target_info.system = system_arm_ios) then
  4841. begin
  4842. Message(option_illegal_fpu_eabihf);
  4843. StopOptions(1);
  4844. end;
  4845. end;
  4846. end;
  4847. abi_eabi:
  4848. begin
  4849. if target_info.system=system_arm_linux then
  4850. begin
  4851. { this is what Debian uses }
  4852. if not option.CPUSetExplicitly then
  4853. init_settings.cputype:=cpu_armv4t;
  4854. if not option.OptCPUSetExplicitly then
  4855. init_settings.optimizecputype:=cpu_armv4t;
  4856. if not(option.FPUSetExplicitly) then
  4857. init_settings.fputype:=fpu_soft;
  4858. end;
  4859. end;
  4860. else
  4861. ;
  4862. end;
  4863. if (init_settings.instructionset=is_thumb) and not(CPUARM_HAS_THUMB2 in cpu_capabilities[init_settings.cputype]) then
  4864. begin
  4865. def_system_macro('CPUTHUMB');
  4866. if not option.FPUSetExplicitly then
  4867. init_settings.fputype:=fpu_soft;
  4868. if not(init_settings.fputype in [fpu_none,fpu_soft,fpu_libgcc]) then
  4869. Message2(option_unsupported_fpu,fputypestr[init_settings.fputype],'Thumb');
  4870. {$if defined(FPC_ARMEL) or defined(FPC_ARMHF)}
  4871. target_info.llvmdatalayout:='e-p:32:32:32-i1:8:32-i8:8:32-i16:16:32-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:64:128-a0:0:32-n32-S64';
  4872. {$else FPC_ARMAL or FPC_ARMHF}
  4873. if target_info.endian=endian_little then
  4874. target_info.llvmdatalayout:='e-p:32:32:32-i1:8:32-i8:8:32-i16:16:32-i32:32:32-i64:32:64-f32:32:32-f64:32:64-v64:32:64-v128:32:128-a0:0:32-n32-S32';
  4875. {$endif FPC_ARMAL or FPC_ARMHF}
  4876. end;
  4877. if (init_settings.instructionset=is_thumb) and (CPUARM_HAS_THUMB2 in cpu_capabilities[init_settings.cputype]) then
  4878. def_system_macro('CPUTHUMB2');
  4879. {$endif arm}
  4880. {$ifdef aarch64}
  4881. case target_info.system of
  4882. system_aarch64_darwin:
  4883. begin
  4884. if not option.CPUSetExplicitly then
  4885. init_settings.cputype:=cpu_armv84a;
  4886. if not option.OptCPUSetExplicitly then
  4887. init_settings.optimizecputype:=cpu_armv84a;
  4888. end;
  4889. else
  4890. ;
  4891. end;
  4892. {$endif aarch64}
  4893. {$if defined(riscv32) or defined(riscv64)}
  4894. { RISC-V defaults }
  4895. if (target_info.abi = abi_riscv_hf) then
  4896. begin
  4897. {$ifdef riscv32}
  4898. if not option.CPUSetExplicitly then
  4899. init_settings.cputype:=cpu_rv32ima;
  4900. if not option.OptCPUSetExplicitly then
  4901. init_settings.optimizecputype:=cpu_rv32ima;
  4902. {$else}
  4903. if not option.CPUSetExplicitly then
  4904. init_settings.cputype:=cpu_rv64imac;
  4905. if not option.OptCPUSetExplicitly then
  4906. init_settings.optimizecputype:=cpu_rv64imac;
  4907. {$endif}
  4908. { Set FPU type }
  4909. if not(option.FPUSetExplicitly) then
  4910. init_settings.fputype:=fpu_fd
  4911. else
  4912. begin
  4913. if not (init_settings.fputype in [fpu_fd]) then
  4914. begin
  4915. Message(option_illegal_fpu_eabihf);
  4916. StopOptions(1);
  4917. end;
  4918. end;
  4919. end;
  4920. {$endif defined(riscv32) or defined(riscv64)}
  4921. {$ifdef jvm}
  4922. { set default CPU type to Dalvik when targeting Android }
  4923. if target_info.system=system_jvm_android32 then
  4924. begin
  4925. if not option.CPUSetExplicitly then
  4926. init_settings.cputype:=cpu_dalvik;
  4927. end;
  4928. {$endif jvm}
  4929. {$ifdef llvm}
  4930. { standard extension for llvm bitcode files }
  4931. target_info.asmext:='.ll';
  4932. { don't generate dwarf cfi, llvm will do that }
  4933. exclude(target_info.flags,tf_needs_dwarf_cfi);
  4934. {$endif llvm}
  4935. {$ifdef mipsel}
  4936. case target_info.system of
  4937. system_mipsel_android:
  4938. begin
  4939. { set default cpu type to MIPS32 rev. 1 and hard float for MIPS-Android unless specified otherwise }
  4940. if not option.CPUSetExplicitly then
  4941. init_settings.cputype:=cpu_mips32;
  4942. if not option.OptCPUSetExplicitly then
  4943. init_settings.optimizecputype:=cpu_mips32;
  4944. if not option.FPUSetExplicitly then
  4945. init_settings.fputype:=fpu_mips2;
  4946. end;
  4947. system_mipsel_embedded:
  4948. begin
  4949. { set default cpu type to PIC32MX and softfloat for MIPSEL-EMBEDDED target unless specified otherwise }
  4950. if not option.CPUSetExplicitly then
  4951. init_settings.cputype:=cpu_pic32mx;
  4952. if not option.OptCPUSetExplicitly then
  4953. init_settings.optimizecputype:=cpu_pic32mx;
  4954. if not option.FPUSetExplicitly then
  4955. init_settings.fputype:=fpu_soft;
  4956. end;
  4957. else
  4958. ;
  4959. end;
  4960. {$endif mipsel}
  4961. {$ifdef m68k}
  4962. if init_settings.cputype in cpu_coldfire then
  4963. def_system_macro('CPUCOLDFIRE');
  4964. case target_info.system of
  4965. system_m68k_linux,
  4966. system_m68k_netbsd:
  4967. begin
  4968. if not (option.FPUSetExplicitly) and
  4969. not (init_settings.cputype in cpu_coldfire) then
  4970. begin
  4971. { enable HW FPU for UNIX by default, but only for
  4972. original 68k, not Coldfire }
  4973. exclude(init_settings.moduleswitches,cs_fp_emulation);
  4974. init_settings.fputype:=fpu_68881;
  4975. end;
  4976. end;
  4977. system_m68k_atari,
  4978. system_m68k_sinclairql:
  4979. begin
  4980. if not option.CPUSetExplicitly then
  4981. init_settings.cputype:=cpu_mc68000;
  4982. end;
  4983. system_m68k_palmos:
  4984. begin
  4985. if not option.CPUSetExplicitly then
  4986. init_settings.cputype:=cpu_mc68000;
  4987. if not (option.FPUSetExplicitly) then
  4988. begin
  4989. { No FPU for PalmOS by default }
  4990. exclude(init_settings.moduleswitches,cs_fp_emulation);
  4991. init_settings.fputype:=fpu_none;
  4992. end;
  4993. end;
  4994. else
  4995. ;
  4996. end;
  4997. {$endif m68k}
  4998. {$ifdef wasm}
  4999. { if no explicit exception handling mode is set for WebAssembly, assume no exceptions }
  5000. if init_settings.targetswitches*[ts_wasm_no_exceptions,ts_wasm_js_exceptions,ts_wasm_native_exceptions,ts_wasm_bf_exceptions]=[] then
  5001. begin
  5002. def_system_macro(TargetSwitchStr[ts_wasm_no_exceptions].define);
  5003. include(init_settings.targetswitches,ts_wasm_no_exceptions);
  5004. end;
  5005. {$endif wasm}
  5006. {$if defined(loongarch64)}
  5007. { LoongArch defaults }
  5008. if (target_info.abi = abi_riscv_hf) then
  5009. begin
  5010. init_settings.cputype:=cpu_3a;
  5011. init_settings.fputype:=fpu_fd;
  5012. end;
  5013. {$endif defined(loongarch64)}
  5014. { now we can define cpu and fpu type }
  5015. def_cpu_macros;
  5016. set_endianess_macros;
  5017. { Use init_settings cpu type for asm cpu type,
  5018. if asmcputype is cpu_none,
  5019. at least as long as there is no explicit
  5020. option to set it on command line PM }
  5021. if init_settings.asmcputype = cpu_none then
  5022. init_settings.asmcputype:=init_settings.cputype;
  5023. {$ifdef llvm}
  5024. def_system_macro('CPULLVM');
  5025. {$endif llvm}
  5026. {$if defined(cpucapabilities)}
  5027. for cpuflag:=low(cpuflag) to high(cpuflag) do
  5028. begin
  5029. str(cpuflag,hs);
  5030. if cpuflag in cpu_capabilities[init_settings.cputype] then
  5031. def_system_macro(hs)
  5032. else
  5033. undef_system_macro(hs);
  5034. end;
  5035. {$endif defined(cpucapabilities)}
  5036. {$if defined(fpucapabilities)}
  5037. for fpuflag:=low(fpuflag) to high(fpuflag) do
  5038. begin
  5039. str(fpuflag,hs);
  5040. if fpuflag in fpu_capabilities[init_settings.fputype] then
  5041. def_system_macro(hs)
  5042. else
  5043. undef_system_macro(hs);
  5044. end;
  5045. {$endif defined(fpucapabilities)}
  5046. if init_settings.fputype<>fpu_none then
  5047. begin
  5048. {$if defined(i386) or defined(i8086)}
  5049. def_system_macro('FPC_HAS_TYPE_EXTENDED');
  5050. {$endif}
  5051. def_system_macro('FPC_HAS_TYPE_SINGLE');
  5052. def_system_macro('FPC_HAS_TYPE_DOUBLE');
  5053. {$if not defined(i386) and not defined(x86_64) and not defined(i8086) and not defined(aarch64)}
  5054. def_system_macro('FPC_INCLUDE_SOFTWARE_INT64_TO_DOUBLE');
  5055. {$endif}
  5056. {$if defined(m68k)}
  5057. def_system_macro('FPC_INCLUDE_SOFTWARE_LONGWORD_TO_DOUBLE');
  5058. {$endif}
  5059. {$ifdef x86_64}
  5060. {$ifndef FPC_SUPPORT_X87_TYPES_ON_WIN64}
  5061. { normally, win64 doesn't support the legacy fpu }
  5062. if target_info.system=system_x86_64_win64 then
  5063. undef_system_macro('FPC_HAS_TYPE_EXTENDED')
  5064. else
  5065. {$endif FPC_SUPPORT_X87_TYPES_ON_WIN64}
  5066. def_system_macro('FPC_HAS_TYPE_EXTENDED');
  5067. {$endif}
  5068. end;
  5069. { Enable now for testing }
  5070. {$ifndef DISABLE_TLS_DIRECTORY}
  5071. if target_info.system in systems_windows then
  5072. def_system_macro('FPC_USE_TLS_DIRECTORY');
  5073. {$endif not DISABLE_TLS_DIRECTORY}
  5074. {$ifndef DISABLE_WIN64_SEH}
  5075. if target_info.system=system_x86_64_win64 then
  5076. def_system_macro('FPC_USE_WIN64_SEH');
  5077. {$endif DISABLE_WIN64_SEH}
  5078. {$ifndef DISABLE_WIN32_SEH}
  5079. if target_info.system=system_i386_win32 then
  5080. def_system_macro('FPC_USE_WIN32_SEH');
  5081. {$endif not DISABLE_WIN32_SEH}
  5082. {$ifdef ARM}
  5083. { define FPC_DOUBLE_HILO_SWAPPED if needed to properly handle doubles in RTL }
  5084. if (init_settings.fputype in [fpu_fpa,fpu_fpa10,fpu_fpa11]) and
  5085. not(cs_fp_emulation in init_settings.moduleswitches) then
  5086. def_system_macro('FPC_DOUBLE_HILO_SWAPPED');
  5087. {$endif ARM}
  5088. { inline bsf/bsr implementation }
  5089. {$if defined(i386) or defined(x86_64) or defined(aarch64) or defined(powerpc) or defined(powerpc64)}
  5090. def_system_macro('FPC_HAS_INTERNAL_BSF');
  5091. def_system_macro('FPC_HAS_INTERNAL_BSR');
  5092. {$endif}
  5093. { hardware FMA support }
  5094. {$if defined(i386) or defined(x86_64)}
  5095. if (fpu_capabilities[current_settings.fputype]*[FPUX86_HAS_FMA,FPUX86_HAS_FMA4])<>[] then
  5096. begin
  5097. def_system_macro('FPC_HAS_FAST_FMA_SINGLE');
  5098. def_system_macro('FPC_HAS_FAST_FMA_DOUBLE');
  5099. end;
  5100. {$endif defined(i386) or defined(x86_64)}
  5101. {$if defined(arm)}
  5102. { it is determined during system unit compilation if clz is used for bsf or not,
  5103. this is not perfect but the current implementation bsf/bsr does not allow another
  5104. solution }
  5105. if (CPUARM_HAS_CLZ in cpu_capabilities[init_settings.cputype]) and
  5106. ((init_settings.instructionset=is_arm) or
  5107. (CPUARM_HAS_THUMB2 in cpu_capabilities[init_settings.cputype])) then
  5108. begin
  5109. def_system_macro('FPC_HAS_INTERNAL_BSR');
  5110. if CPUARM_HAS_RBIT in cpu_capabilities[init_settings.cputype] then
  5111. def_system_macro('FPC_HAS_INTERNAL_BSF');
  5112. end;
  5113. {$endif}
  5114. {$if defined(xtensa)}
  5115. { it is determined during system unit compilation if nsau is used for bsr or not,
  5116. this is not perfect but the current implementation bsf/bsr does not allow another
  5117. solution }
  5118. if CPUXTENSA_HAS_NSAx in cpu_capabilities[init_settings.cputype] then
  5119. begin
  5120. def_system_macro('FPC_HAS_INTERNAL_BSR');
  5121. end;
  5122. {$endif}
  5123. {$if defined(powerpc64)}
  5124. { on sysv targets, default to elfv2 for little endian and to elfv1 for
  5125. big endian (unless specified otherwise). As the gcc man page says:
  5126. "Overriding the default ABI requires special system support and is
  5127. likely to fail in spectacular ways" }
  5128. if not option.ABISetExplicitly then
  5129. begin
  5130. if (target_info.abi=abi_powerpc_sysv) and
  5131. (target_info.endian=endian_little) then
  5132. target_info.abi:=abi_powerpc_elfv2
  5133. else
  5134. if (target_info.abi=abi_powerpc_elfv2) and
  5135. (target_info.endian=endian_big) then
  5136. target_info.abi:=abi_powerpc_sysv
  5137. end;
  5138. {$endif}
  5139. {$if defined(powerpc) or defined(powerpc64)}
  5140. { define _CALL_ELF symbol like gcc }
  5141. case target_info.abi of
  5142. abi_powerpc_sysv:
  5143. set_system_compvar('_CALL_ELF','1');
  5144. abi_powerpc_elfv2:
  5145. set_system_compvar('_CALL_ELF','2');
  5146. else
  5147. ;
  5148. end;
  5149. {$endif}
  5150. { Section smartlinking conflicts with import sections on Windows }
  5151. if GenerateImportSection and
  5152. (target_info.system in [system_i386_win32,system_x86_64_win64,system_aarch64_win64]) then
  5153. exclude(target_info.flags,tf_smartlink_sections);
  5154. if not option.LinkTypeSetExplicitly then
  5155. set_default_link_type;
  5156. { Default alignment settings,
  5157. 1. load the defaults for the target
  5158. 2. adapt defaults specifically for the target
  5159. 3. override with generic optimizer setting (little size)
  5160. 4. override with the user specified -Oa }
  5161. UpdateAlignment(init_settings.alignment,target_info.alignment);
  5162. {$ifdef arm}
  5163. if (init_settings.instructionset=is_thumb) and not(CPUARM_HAS_THUMB2 in cpu_capabilities[init_settings.cputype]) then
  5164. begin
  5165. init_settings.alignment.procalign:=2;
  5166. init_settings.alignment.jumpalign:=2;
  5167. init_settings.alignment.coalescealign:=2;
  5168. init_settings.alignment.loopalign:=2;
  5169. end;
  5170. {$endif arm}
  5171. if (cs_opt_size in init_settings.optimizerswitches) then
  5172. begin
  5173. init_settings.alignment.procalign:=1;
  5174. init_settings.alignment.jumpalign:=1;
  5175. init_settings.alignment.coalescealign:=1;
  5176. init_settings.alignment.loopalign:=1;
  5177. {$ifdef x86}
  5178. { constalignmax=1 keeps the executable and thus the memory foot print small but
  5179. all processors except x86 are really hurt by this or might even crash }
  5180. init_settings.alignment.constalignmax:=1;
  5181. {$endif x86}
  5182. end;
  5183. UpdateAlignment(init_settings.alignment,option.paraalignment);
  5184. set_system_macro('FPC_VERSION',version_nr);
  5185. set_system_macro('FPC_RELEASE',release_nr);
  5186. set_system_macro('FPC_PATCH',patch_nr);
  5187. set_system_macro('FPC_FULLVERSION',Format('%d%.02d%.02d',[StrToInt(version_nr),StrToInt(release_nr),StrToInt(patch_nr)]));
  5188. if target_info.system in systems_indirect_entry_information then
  5189. def_system_macro('FPC_HAS_INDIRECT_ENTRY_INFORMATION');
  5190. if not (tf_winlikewidestring in target_info.flags) then
  5191. def_system_macro('FPC_WIDESTRING_EQUAL_UNICODESTRING');
  5192. if tf_supports_packages in target_info.flags then
  5193. def_system_macro('FPC_HAS_DYNAMIC_PACKAGES');
  5194. if target_info.system in systems_indirect_var_imports then
  5195. def_system_macro('FPC_HAS_INDIRECT_VAR_ACCESS');
  5196. if cs_compilesystem in init_settings.moduleswitches then
  5197. for i:=low(tfeature) to high(tfeature) do
  5198. if i in features then
  5199. def_system_macro('FPC_HAS_FEATURE_'+featurestr[i]);
  5200. {$push}
  5201. {$warn 6018 off} { Unreachable code due to compile time evaluation }
  5202. if ControllerSupport and (target_info.system in (systems_embedded+systems_freertos)) and
  5203. (init_settings.controllertype<>ct_none) then
  5204. begin
  5205. with embedded_controllers[init_settings.controllertype] do
  5206. begin
  5207. set_system_macro('FPC_FLASHBASE',tostr(flashbase));
  5208. set_system_macro('FPC_FLASHSIZE',tostr(flashsize));
  5209. set_system_macro('FPC_SRAMBASE',tostr(srambase));
  5210. set_system_macro('FPC_SRAMSIZE',tostr(sramsize));
  5211. set_system_macro('FPC_EEPROMBASE',tostr(eeprombase));
  5212. set_system_macro('FPC_EEPROMSIZE',tostr(eepromsize));
  5213. set_system_macro('FPC_BOOTBASE',tostr(bootbase));
  5214. set_system_macro('FPC_BOOTSIZE',tostr(bootsize));
  5215. end;
  5216. end;
  5217. {$pop}
  5218. { as stackalign is not part of the alignment record, we do not need to define the others alignments for symmetry yet }
  5219. set_system_macro('FPC_STACKALIGNMENT',tostr(target_info.stackalign));
  5220. option.free;
  5221. Option:=nil;
  5222. clearstack_pocalls := [pocall_cdecl,pocall_cppdecl,pocall_syscall,pocall_mwpascal,pocall_sysv_abi_cdecl,pocall_ms_abi_cdecl{$ifdef z80},pocall_stdcall{$endif}];
  5223. cdecl_pocalls := [pocall_cdecl, pocall_cppdecl, pocall_mwpascal, pocall_sysv_abi_cdecl, pocall_ms_abi_cdecl];
  5224. if (tf_safecall_clearstack in target_info.flags) then
  5225. begin
  5226. include (cdecl_pocalls, pocall_safecall);
  5227. include (clearstack_pocalls, pocall_safecall)
  5228. end;
  5229. end;
  5230. initialization
  5231. coption:=toption;
  5232. finalization
  5233. if assigned(option) then
  5234. option.free;
  5235. end.