options.pas 53 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696
  1. {
  2. $Id$
  3. Copyright (c) 1998-2000 by Florian Klaempfl and Peter Vreman
  4. Reads command line options and config files
  5. This program is free software; you can redistribute it and/or modify
  6. it under the terms of the GNU General Public License as published by
  7. the Free Software Foundation; either version 2 of the License, or
  8. (at your option) any later version.
  9. This program is distributed in the hope that it will be useful,
  10. but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. GNU General Public License for more details.
  13. You should have received a copy of the GNU General Public License
  14. along with this program; if not, write to the Free Software
  15. Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  16. ****************************************************************************
  17. }
  18. unit options;
  19. {$i defines.inc}
  20. interface
  21. uses
  22. globtype,globals,verbose;
  23. type
  24. TOption=class
  25. FirstPass,
  26. NoPressEnter,
  27. DoWriteLogo : boolean;
  28. FileLevel : longint;
  29. QuickInfo : string;
  30. ParaIncludePath,
  31. ParaUnitPath,
  32. ParaObjectPath,
  33. ParaLibraryPath : TSearchPathList;
  34. Constructor Create;
  35. Destructor Destroy;override;
  36. procedure WriteLogo;
  37. procedure WriteInfo;
  38. procedure WriteHelpPages;
  39. procedure WriteQuickInfo;
  40. procedure IllegalPara(const opt:string);
  41. function Unsetbool(var Opts:string; Pos: Longint):boolean;
  42. procedure interpret_proc_specific_options(const opt:string);virtual;
  43. procedure interpret_option(const opt :string;ispara:boolean);
  44. procedure Interpret_envvar(const envname : string);
  45. procedure Interpret_file(const filename : string);
  46. procedure Read_Parameters;
  47. procedure parsecmd(cmd:string);
  48. end;
  49. TOptionClass=class of toption;
  50. var
  51. coption : TOptionClass;
  52. procedure read_arguments(cmd:string);
  53. implementation
  54. uses
  55. {$ifdef Delphi}
  56. dmisc,
  57. {$else Delphi}
  58. dos,
  59. {$endif Delphi}
  60. version,systems,
  61. cutils,messages
  62. {$ifdef BrowserLog}
  63. ,browlog
  64. {$endif BrowserLog}
  65. ;
  66. const
  67. page_size = 24;
  68. var
  69. option : toption;
  70. read_configfile, { read config file, set when a cfgfile is found }
  71. disable_configfile,
  72. target_is_set : boolean; { do not allow contradictory target settings }
  73. asm_is_set : boolean; { -T also change initoutputformat if not set idrectly }
  74. fpcdir,
  75. ppccfg,
  76. param_file : string; { file to compile specified on the commandline }
  77. {****************************************************************************
  78. Defines
  79. ****************************************************************************}
  80. procedure def_symbol(const s : string);
  81. begin
  82. if s='' then
  83. exit;
  84. initdefines.insert(upper(s));
  85. end;
  86. procedure undef_symbol(const s : string);
  87. begin
  88. if s='' then
  89. exit;
  90. InitDefines.Remove(s);
  91. end;
  92. function check_symbol(const s:string):boolean;
  93. begin
  94. check_symbol:=(initdefines.find(s)<>nil);
  95. end;
  96. procedure set_default_link_type;
  97. begin
  98. if (target_info.target=target_i386_win32) then
  99. begin
  100. def_symbol('FPC_LINK_SMART');
  101. undef_symbol('FPC_LINK_STATIC');
  102. undef_symbol('FPC_LINK_DYNAMIC');
  103. initglobalswitches:=initglobalswitches+[cs_link_smart];
  104. initglobalswitches:=initglobalswitches-[cs_link_shared,cs_link_static];
  105. end
  106. else
  107. begin
  108. undef_symbol('FPC_LINK_SMART');
  109. def_symbol('FPC_LINK_STATIC');
  110. undef_symbol('FPC_LINK_DYNAMIC');
  111. initglobalswitches:=initglobalswitches+[cs_link_static];
  112. initglobalswitches:=initglobalswitches-[cs_link_shared,cs_link_smart];
  113. end;
  114. end;
  115. {****************************************************************************
  116. Toption
  117. ****************************************************************************}
  118. procedure StopOptions;
  119. begin
  120. if assigned(Option) then
  121. begin
  122. Option.free;
  123. Option:=nil;
  124. end;
  125. DoneVerbose;
  126. Stop;
  127. end;
  128. procedure Toption.WriteLogo;
  129. var
  130. p : pchar;
  131. begin
  132. p:=MessagePchar(option_logo);
  133. while assigned(p) do
  134. Comment(V_Normal,GetMsgLine(p));
  135. end;
  136. procedure Toption.WriteInfo;
  137. var
  138. p : pchar;
  139. begin
  140. p:=MessagePchar(option_info);
  141. while assigned(p) do
  142. Comment(V_Normal,GetMsgLine(p));
  143. StopOptions;
  144. end;
  145. procedure Toption.WriteHelpPages;
  146. function PadEnd(s:string;i:longint):string;
  147. begin
  148. while (length(s)<i) do
  149. s:=s+' ';
  150. PadEnd:=s;
  151. end;
  152. var
  153. lastident,
  154. j,outline,
  155. ident,
  156. lines : longint;
  157. show : boolean;
  158. opt : string[32];
  159. input,
  160. s : string;
  161. p : pchar;
  162. begin
  163. WriteLogo;
  164. Lines:=4;
  165. Message1(option_usage,system.paramstr(0));
  166. lastident:=0;
  167. p:=MessagePChar(option_help_pages);
  168. while assigned(p) do
  169. begin
  170. { get a line and reset }
  171. s:=GetMsgLine(p);
  172. ident:=0;
  173. show:=false;
  174. { parse options }
  175. case s[1] of
  176. {$ifdef UNITALIASES}
  177. 'a',
  178. {$endif}
  179. {$ifdef EXTDEBUG}
  180. 'e',
  181. {$endif EXTDEBUG}
  182. {$ifdef i386}
  183. '3',
  184. {$endif}
  185. {$ifdef m68k}
  186. '6',
  187. {$endif}
  188. '*' : show:=true;
  189. end;
  190. if show then
  191. begin
  192. case s[2] of
  193. {$ifdef GDB}
  194. 'g',
  195. {$endif}
  196. {$ifdef Unix}
  197. 'L',
  198. {$endif}
  199. {$ifdef os2}
  200. 'O',
  201. {$endif}
  202. '*' : show:=true;
  203. else
  204. show:=false;
  205. end;
  206. end;
  207. { now we may show the message or not }
  208. if show then
  209. begin
  210. case s[3] of
  211. '0' : begin
  212. ident:=0;
  213. outline:=0;
  214. end;
  215. '1' : begin
  216. ident:=2;
  217. outline:=7;
  218. end;
  219. '2' : begin
  220. ident:=6;
  221. outline:=11;
  222. end;
  223. '3' : begin
  224. ident:=9;
  225. outline:=6;
  226. end;
  227. end;
  228. j:=pos('_',s);
  229. opt:=Copy(s,4,j-4);
  230. if opt='*' then
  231. opt:=''
  232. else
  233. if opt=' ' then
  234. opt:=PadEnd(opt,outline)
  235. else
  236. opt:=PadEnd('-'+opt,outline);
  237. if (ident=0) and (lastident<>0) then
  238. begin
  239. Comment(V_Normal,'');
  240. inc(Lines);
  241. end;
  242. { page full ? }
  243. if (lines >= page_size - 1) then
  244. begin
  245. if not NoPressEnter then
  246. begin
  247. Message(option_help_press_enter);
  248. readln(input);
  249. if upper(input)='Q' then
  250. StopOptions;
  251. end;
  252. lines:=0;
  253. end;
  254. Comment(V_Normal,PadEnd('',ident)+opt+Copy(s,j+1,255));
  255. LastIdent:=Ident;
  256. inc(Lines);
  257. end;
  258. end;
  259. StopOptions;
  260. end;
  261. procedure Toption.IllegalPara(const opt:string);
  262. begin
  263. Message1(option_illegal_para,opt);
  264. Message(option_help_pages_para);
  265. StopOptions;
  266. end;
  267. function Toption.Unsetbool(var Opts:string; Pos: Longint):boolean;
  268. { checks if the character after pos in Opts is a + or a - and returns resp.
  269. false or true. If it is another character (or none), it also returns false }
  270. begin
  271. UnsetBool := false;
  272. if Length(Opts)>Pos then
  273. begin
  274. inc(Pos);
  275. UnsetBool := Opts[Pos] = '-';
  276. if Opts[Pos] in ['-','+']then
  277. delete(Opts,Pos,1);
  278. end;
  279. end;
  280. procedure TOption.interpret_proc_specific_options(const opt:string);
  281. begin
  282. end;
  283. procedure TOption.interpret_option(const opt:string;ispara:boolean);
  284. var
  285. code : integer;
  286. c : char;
  287. more : string;
  288. major,minor : longint;
  289. error : integer;
  290. j,l : longint;
  291. d : DirStr;
  292. e : ExtStr;
  293. forceasm : tasm;
  294. begin
  295. if opt='' then
  296. exit;
  297. { only parse define,undef,target,verbosity and link options the firsttime }
  298. if firstpass and
  299. not((opt[1]='-') and (opt[2] in ['i','d','v','T','u','n','X'])) then
  300. exit;
  301. Message1(option_handling_option,opt);
  302. case opt[1] of
  303. '-' : begin
  304. more:=Copy(opt,3,255);
  305. case opt[2] of
  306. '!' : initlocalswitches:=initlocalswitches+[cs_ansistrings];
  307. '?' : WriteHelpPages;
  308. 'a' : begin
  309. initglobalswitches:=initglobalswitches+[cs_asm_leave];
  310. for j:=1 to length(more) do
  311. case more[j] of
  312. 'l' : initglobalswitches:=initglobalswitches+[cs_asm_source];
  313. 'r' : initglobalswitches:=initglobalswitches+[cs_asm_regalloc];
  314. 't' : initglobalswitches:=initglobalswitches+[cs_asm_tempalloc];
  315. '-' : initglobalswitches:=initglobalswitches-
  316. [cs_asm_leave, cs_asm_source,cs_asm_regalloc, cs_asm_tempalloc];
  317. else
  318. IllegalPara(opt);
  319. end;
  320. end;
  321. 'A' : begin
  322. if set_target_asm_by_string(More) then
  323. asm_is_set:=true
  324. else
  325. IllegalPara(opt);
  326. end;
  327. 'b' : begin
  328. {$ifdef BrowserLog}
  329. initglobalswitches:=initglobalswitches+[cs_browser_log];
  330. {$endif}
  331. if More<>'' then
  332. if More='l' then
  333. initmoduleswitches:=initmoduleswitches+[cs_local_browser]
  334. else if More='-' then
  335. begin
  336. initmoduleswitches:=initmoduleswitches-[cs_browser,cs_local_browser];
  337. {$ifdef BrowserLog}
  338. initglobalswitches:=initglobalswitches-[cs_browser_log];
  339. {$endif}
  340. end
  341. else if More<>'+' then
  342. {$ifdef BrowserLog}
  343. browserlog.elements_to_list.insert(more);
  344. {$else}
  345. IllegalPara(opt);
  346. {$endif}
  347. end;
  348. 'B' : if UnSetBool(more,0) then
  349. do_build:=false
  350. else
  351. do_build:=true;
  352. 'C' : begin
  353. j := 1;
  354. while j <= length(more) Do
  355. Begin
  356. case more[j] of
  357. 'a' : Message2(option_obsolete_switch_use_new,'-Ca','-Or');
  358. 'h' :
  359. begin
  360. val(copy(more,j+1,length(more)-j),heapsize,code);
  361. if (code<>0) or (heapsize>=67107840) or (heapsize<1024) then
  362. IllegalPara(opt);
  363. break;
  364. end;
  365. 'i' : If UnsetBool(More, j) then
  366. initlocalswitches:=initlocalswitches-[cs_check_io]
  367. else initlocalswitches:=initlocalswitches+[cs_check_io];
  368. 'n' : If UnsetBool(More, j) then
  369. initglobalswitches:=initglobalswitches-[cs_link_extern]
  370. Else initglobalswitches:=initglobalswitches+[cs_link_extern];
  371. 'o' :
  372. If UnsetBool(More, j) then
  373. initlocalswitches:=initlocalswitches-[cs_check_overflow]
  374. Else
  375. initlocalswitches:=initlocalswitches+[cs_check_overflow];
  376. 'r' :
  377. If UnsetBool(More, j) then
  378. initlocalswitches:=initlocalswitches-[cs_check_range]
  379. Else
  380. initlocalswitches:=initlocalswitches+[cs_check_range];
  381. 'R' :
  382. If UnsetBool(More, j) then
  383. initlocalswitches:=initlocalswitches-[cs_check_object_ext]
  384. Else
  385. initlocalswitches:=initlocalswitches+[cs_check_object_ext];
  386. 's' :
  387. begin
  388. val(copy(more,j+1,length(more)-j),stacksize,code);
  389. if (code<>0) or (stacksize>=67107840) or (stacksize<1024) then
  390. IllegalPara(opt);
  391. break;
  392. end;
  393. 't' :
  394. If UnsetBool(More, j) then
  395. initlocalswitches:=initlocalswitches-[cs_check_stack]
  396. Else
  397. initlocalswitches:=initlocalswitches+[cs_check_stack];
  398. 'D' :
  399. If UnsetBool(More, j) then
  400. initmoduleswitches:=initmoduleswitches-[cs_create_dynamic]
  401. Else
  402. initmoduleswitches:=initmoduleswitches+[cs_create_dynamic];
  403. 'X' :
  404. If UnsetBool(More, j) then
  405. initmoduleswitches:=initmoduleswitches-[cs_create_smart]
  406. Else
  407. initmoduleswitches:=initmoduleswitches+[cs_create_smart];
  408. else
  409. IllegalPara(opt);
  410. end;
  411. inc(j);
  412. end;
  413. end;
  414. 'd' : def_symbol(more);
  415. 'D' : begin
  416. initglobalswitches:=initglobalswitches+[cs_link_deffile];
  417. for j:=1 to length(more) do
  418. case more[j] of
  419. 'd' : begin
  420. description:=Copy(more,j+1,255);
  421. break;
  422. end;
  423. 'v' : begin
  424. dllversion:=Copy(more,j+1,255);
  425. l:=pos('.',dllversion);
  426. dllminor:=0;
  427. error:=0;
  428. if l>0 then
  429. begin
  430. valint(copy(dllversion,l+1,255),minor,error);
  431. if (error=0) and
  432. (minor>=0) and (minor<=$ffff) then
  433. dllminor:=minor
  434. else if error=0 then
  435. error:=1;
  436. end;
  437. if l=0 then l:=256;
  438. dllmajor:=1;
  439. if error=0 then
  440. valint(copy(dllversion,1,l-1),major,error);
  441. if (error=0) and (major>=0) and (major<=$ffff) then
  442. dllmajor:=major
  443. else if error=0 then
  444. error:=1;
  445. if error<>0 then
  446. Message1(scan_w_wrong_version_ignored,dllversion);
  447. break;
  448. end;
  449. 'w' : usewindowapi:=true;
  450. '-' : begin
  451. initglobalswitches:=initglobalswitches-
  452. [cs_link_deffile];
  453. usewindowapi:=false;
  454. end;
  455. else
  456. IllegalPara(opt);
  457. end;
  458. end;
  459. 'e' : exepath:=FixPath(More,true);
  460. { Just used by RHIDE }
  461. 'E' : if (length(more)=0) or (UnsetBool(More, 0)) then
  462. initglobalswitches:=initglobalswitches+[cs_link_extern]
  463. else
  464. initglobalswitches:=initglobalswitches-[cs_link_extern];
  465. 'F' : begin
  466. c:=more[1];
  467. Delete(more,1,1);
  468. DefaultReplacements(More);
  469. case c of
  470. 'D' : utilsdirectory:=FixPath(More,true);
  471. 'e' : SetRedirectFile(More);
  472. 'E' : OutputExeDir:=FixPath(More,true);
  473. 'i' : if ispara then
  474. ParaIncludePath.AddPath(More,false)
  475. else
  476. includesearchpath.AddPath(More,true);
  477. 'g' : Message2(option_obsolete_switch_use_new,'-Fg','-Fl');
  478. 'l' : if ispara then
  479. ParaLibraryPath.AddPath(More,false)
  480. else
  481. LibrarySearchPath.AddPath(More,true);
  482. 'L' : if More<>'' then
  483. ParaDynamicLinker:=More
  484. else
  485. IllegalPara(opt);
  486. 'o' : if ispara then
  487. ParaObjectPath.AddPath(More,false)
  488. else
  489. ObjectSearchPath.AddPath(More,true);
  490. 'r' : Msgfilename:=More;
  491. 'u' : if ispara then
  492. ParaUnitPath.AddPath(More,false)
  493. else
  494. unitsearchpath.AddPath(More,true);
  495. 'U' : OutputUnitDir:=FixPath(More,true);
  496. else
  497. IllegalPara(opt);
  498. end;
  499. end;
  500. 'g' : begin
  501. if UnsetBool(More, 0) then
  502. begin
  503. initmoduleswitches:=initmoduleswitches-[cs_debuginfo];
  504. if (length(More)>1) and (More[2]='l') then
  505. initglobalswitches:=initglobalswitches+[cs_gdb_lineinfo];
  506. end
  507. else
  508. begin
  509. {$ifdef GDB}
  510. initmoduleswitches:=initmoduleswitches+[cs_debuginfo];
  511. if not RelocSectionSetExplicitly then
  512. RelocSection:=false;
  513. for j:=1 to length(more) do
  514. case more[j] of
  515. 'd' : initglobalswitches:=initglobalswitches+[cs_gdb_dbx];
  516. 'g' : initglobalswitches:=initglobalswitches+[cs_gdb_gsym];
  517. 'h' : initglobalswitches:=initglobalswitches+[cs_gdb_heaptrc];
  518. 'l' : initglobalswitches:=initglobalswitches+[cs_gdb_lineinfo];
  519. 'c' : initglobalswitches:=initglobalswitches+[cs_checkpointer];
  520. {$ifdef EXTDEBUG}
  521. 'p' : only_one_pass:=true;
  522. {$endif EXTDEBUG}
  523. else
  524. IllegalPara(opt);
  525. end;
  526. {$else GDB}
  527. Message(option_no_debug_support);
  528. Message(option_no_debug_support_recompile_fpc);
  529. {$endif GDB}
  530. end;
  531. end;
  532. 'h' : begin
  533. NoPressEnter:=true;
  534. WriteHelpPages;
  535. end;
  536. 'i' : if More='' then
  537. WriteInfo
  538. else
  539. QuickInfo:=QuickInfo+More;
  540. 'I' : if ispara then
  541. ParaIncludePath.AddPath(More,false)
  542. else
  543. includesearchpath.AddPath(More,false);
  544. 'k' : if more<>'' then
  545. ParaLinkOptions:=ParaLinkOptions+' '+More
  546. else
  547. IllegalPara(opt);
  548. 'l' : if UnSetBool(more,0) then
  549. DoWriteLogo:=false
  550. else
  551. DoWriteLogo:=true;
  552. 'm' : if UnSetBool(more,0) then
  553. parapreprocess:=false
  554. else
  555. parapreprocess:=true;
  556. 'n' : if More='' then
  557. begin
  558. read_configfile:=false;
  559. disable_configfile:=true;
  560. end
  561. else
  562. IllegalPara(opt);
  563. 'o' : if More<>'' then
  564. Fsplit(More,d,OutputFile,e)
  565. else
  566. IllegalPara(opt);
  567. 'p' : begin
  568. if UnsetBool(More, 0) then
  569. begin
  570. initmoduleswitches:=initmoduleswitches-[cs_profile];
  571. undef_symbol('FPC_PROFILE');
  572. end
  573. else
  574. case more[1] of
  575. 'g' : if (length(opt)=3) and UnsetBool(more, 1) then
  576. begin
  577. initmoduleswitches:=initmoduleswitches-[cs_profile];
  578. undef_symbol('FPC_PROFILE');
  579. end
  580. else
  581. begin
  582. initmoduleswitches:=initmoduleswitches+[cs_profile];
  583. def_symbol('FPC_PROFILE');
  584. end;
  585. else
  586. IllegalPara(opt);
  587. end;
  588. end;
  589. {$ifdef Unix}
  590. 'P' : if UnsetBool(More, 0) then
  591. initglobalswitches:=initglobalswitches-[cs_asm_pipe]
  592. else
  593. initglobalswitches:=initglobalswitches+[cs_asm_pipe];
  594. {$endif Unix}
  595. 's' : if UnsetBool(More, 0) then
  596. initglobalswitches:=initglobalswitches-[cs_asm_extern,cs_link_extern]
  597. else
  598. initglobalswitches:=initglobalswitches+[cs_asm_extern,cs_link_extern];
  599. 'S' : begin
  600. if more[1]='I' then
  601. begin
  602. if upper(more)='ICOM' then
  603. initinterfacetype:=it_interfacecom
  604. else if upper(more)='ICORBA' then
  605. initinterfacetype:=it_interfacecorba
  606. else
  607. IllegalPara(opt);
  608. end
  609. else
  610. for j:=1 to length(more) do
  611. case more[j] of
  612. '2' : SetCompileMode('OBJFPC',true);
  613. 'a' : initlocalswitches:=InitLocalswitches+[cs_do_assertion];
  614. 'c' : initmoduleswitches:=initmoduleswitches+[cs_support_c_operators];
  615. 'd' : SetCompileMode('DELPHI',true);
  616. 'e' : begin
  617. SetErrorFlags(copy(more,j+1,length(more)));
  618. break;
  619. end;
  620. 'g' : initmoduleswitches:=initmoduleswitches+[cs_support_goto];
  621. 'h' : initlocalswitches:=initlocalswitches+[cs_ansistrings];
  622. 'i' : initmoduleswitches:=initmoduleswitches+[cs_support_inline];
  623. 'm' : initmoduleswitches:=initmoduleswitches+[cs_support_macro];
  624. 'o' : SetCompileMode('TP',true);
  625. 'p' : SetCompileMode('GPC',true);
  626. 's' : initglobalswitches:=initglobalswitches+[cs_constructor_name];
  627. 't' : initmoduleswitches:=initmoduleswitches+[cs_static_keyword];
  628. '-' : begin
  629. initglobalswitches:=initglobalswitches -
  630. [cs_constructor_name];
  631. initlocalswitches:=InitLocalswitches -
  632. [cs_do_assertion, cs_ansistrings];
  633. initmoduleswitches:=initmoduleswitches -
  634. [cs_support_c_operators, cs_support_goto,
  635. cs_support_inline, cs_support_macro,
  636. cs_static_keyword];
  637. end;
  638. else
  639. IllegalPara(opt);
  640. end;
  641. end;
  642. 'T' : begin
  643. more:=Upper(More);
  644. if not target_is_set then
  645. begin
  646. { remove old target define }
  647. undef_symbol(upper(target_info.shortname));
  648. { Save assembler if set }
  649. if asm_is_set then
  650. forceasm:=target_asm.id;
  651. { load new target }
  652. if not(set_target_by_string(More)) then
  653. IllegalPara(opt);
  654. { also initialize assembler if not explicitly set }
  655. if asm_is_set then
  656. set_target_asm(forceasm);
  657. { set new define }
  658. def_symbol(upper(target_info.shortname));
  659. target_is_set:=true;
  660. end
  661. else
  662. if More<>upper(target_info.shortname) then
  663. Message1(option_target_is_already_set,target_info.shortname);
  664. end;
  665. 'u' : undef_symbol(upper(More));
  666. 'U' : begin
  667. for j:=1 to length(more) do
  668. case more[j] of
  669. {$ifdef UNITALIASES}
  670. 'a' : begin
  671. AddUnitAlias(Copy(More,j+1,255));
  672. break;
  673. end;
  674. {$endif UNITALIASES}
  675. 'n' : initglobalswitches:=initglobalswitches-[cs_check_unit_name];
  676. 'p' : begin
  677. Message2(option_obsolete_switch_use_new,'-Up','-Fu');
  678. break;
  679. end;
  680. 'r' : do_release:=true;
  681. 's' : initmoduleswitches:=initmoduleswitches+[cs_compilesystem];
  682. '-' : begin
  683. initmoduleswitches:=initmoduleswitches
  684. - [cs_compilesystem];
  685. initglobalswitches:=initglobalswitches
  686. + [cs_check_unit_name];
  687. end;
  688. else
  689. IllegalPara(opt);
  690. end;
  691. end;
  692. 'v' : if not setverbosity(More) then
  693. IllegalPara(opt);
  694. 'W' : begin
  695. j:=0;
  696. while j<length(More) do
  697. begin
  698. inc(j);
  699. case More[j] of
  700. 'B': {bind_win32_dll:=true}
  701. begin
  702. { -WB200000 means set trefered base address
  703. to $200000, but does not change relocsection boolean
  704. this way we can create both relocatble and
  705. non relocatable DLL at a specific base address PM }
  706. if (length(More)>j) then
  707. begin
  708. if DLLImageBase=nil then
  709. DLLImageBase:=StringDup(Copy(More,j+1,255));
  710. end
  711. else
  712. begin
  713. RelocSection:=true;
  714. RelocSectionSetExplicitly:=true;
  715. end;
  716. break;
  717. end;
  718. 'C': apptype:=app_cui;
  719. 'D': ForceDeffileForExport:=not UnsetBool(More, j);
  720. 'F': apptype:=app_fs;
  721. 'G': apptype:=app_gui;
  722. 'N': begin
  723. RelocSection:=false;
  724. RelocSectionSetExplicitly:=true;
  725. end;
  726. 'R': begin
  727. { support -WR+ / -WR- as synonims to -WR / -WN }
  728. RelocSection:=not UnsetBool(More,j);
  729. RelocSectionSetExplicitly:=true;
  730. end;
  731. else
  732. IllegalPara(opt);
  733. end;
  734. end; {of while}
  735. end;
  736. 'X' : begin
  737. for j:=1 to length(More) do
  738. case More[j] of
  739. 'c' : initglobalswitches:=initglobalswitches+[cs_link_toc];
  740. 's' : initglobalswitches:=initglobalswitches+[cs_link_strip];
  741. 't' : initglobalswitches:=initglobalswitches+[cs_link_staticflag];
  742. 'D' : begin
  743. def_symbol('FPC_LINK_DYNAMIC');
  744. undef_symbol('FPC_LINK_SMART');
  745. undef_symbol('FPC_LINK_STATIC');
  746. initglobalswitches:=initglobalswitches+[cs_link_shared];
  747. initglobalswitches:=initglobalswitches-[cs_link_static,cs_link_smart];
  748. LinkTypeSetExplicitly:=true;
  749. end;
  750. 'S' : begin
  751. def_symbol('FPC_LINK_STATIC');
  752. undef_symbol('FPC_LINK_SMART');
  753. undef_symbol('FPC_LINK_DYNAMIC');
  754. initglobalswitches:=initglobalswitches+[cs_link_static];
  755. initglobalswitches:=initglobalswitches-[cs_link_shared,cs_link_smart];
  756. LinkTypeSetExplicitly:=true;
  757. end;
  758. 'X' : begin
  759. def_symbol('FPC_LINK_SMART');
  760. undef_symbol('FPC_LINK_STATIC');
  761. undef_symbol('FPC_LINK_DYNAMIC');
  762. initglobalswitches:=initglobalswitches+[cs_link_smart];
  763. initglobalswitches:=initglobalswitches-[cs_link_shared,cs_link_static];
  764. LinkTypeSetExplicitly:=true;
  765. end;
  766. '-' : begin
  767. initglobalswitches:=initglobalswitches-[cs_link_toc, cs_link_strip, cs_link_staticflag];
  768. set_default_link_type;
  769. end;
  770. else
  771. IllegalPara(opt);
  772. end;
  773. end;
  774. { give processor specific options a chance }
  775. else
  776. interpret_proc_specific_options(opt);
  777. end;
  778. end;
  779. '@' : begin
  780. Message(option_no_nested_response_file);
  781. StopOptions;
  782. end;
  783. else
  784. begin
  785. if (length(param_file)<>0) then
  786. Message(option_only_one_source_support);
  787. param_file:=opt;
  788. end;
  789. end;
  790. end;
  791. procedure Toption.Interpret_file(const filename : string);
  792. procedure RemoveSep(var fn:string);
  793. var
  794. i : longint;
  795. begin
  796. i:=0;
  797. while (i<length(fn)) and (fn[i+1] in [',',' ',#9]) do
  798. inc(i);
  799. Delete(fn,1,i);
  800. i:=length(fn);
  801. while (i>0) and (fn[i] in [',',' ',#9]) do
  802. dec(i);
  803. fn:=copy(fn,1,i);
  804. end;
  805. function GetName(var fn:string):string;
  806. var
  807. i : longint;
  808. begin
  809. i:=0;
  810. while (i<length(fn)) and (fn[i+1] in ['a'..'z','A'..'Z','0'..'9','_','-']) do
  811. inc(i);
  812. GetName:=Copy(fn,1,i);
  813. Delete(fn,1,i);
  814. end;
  815. const
  816. maxlevel=16;
  817. var
  818. f : text;
  819. s,
  820. opts : string;
  821. skip : array[0..maxlevel-1] of boolean;
  822. level : longint;
  823. option_read : boolean;
  824. begin
  825. { avoid infinite loop }
  826. Inc(FileLevel);
  827. Option_read:=false;
  828. If FileLevel>MaxLevel then
  829. Message(option_too_many_cfg_files);
  830. { open file }
  831. Message1(option_using_file,filename);
  832. assign(f,filename);
  833. {$I-}
  834. reset(f);
  835. {$I+}
  836. if ioresult<>0 then
  837. begin
  838. Message1(option_unable_open_file,filename);
  839. exit;
  840. end;
  841. fillchar(skip,sizeof(skip),0);
  842. level:=0;
  843. while not eof(f) do
  844. begin
  845. readln(f,opts);
  846. RemoveSep(opts);
  847. if (opts<>'') and (opts[1]<>';') then
  848. begin
  849. if opts[1]='#' then
  850. begin
  851. Delete(opts,1,1);
  852. s:=upper(GetName(opts));
  853. if (s='SECTION') then
  854. begin
  855. RemoveSep(opts);
  856. s:=upper(GetName(opts));
  857. if level=0 then
  858. skip[level]:=not (check_symbol(s) or (s='COMMON'));
  859. end
  860. else
  861. if (s='IFDEF') then
  862. begin
  863. RemoveSep(opts);
  864. if Level>=maxlevel then
  865. begin
  866. Message(option_too_many_ifdef);
  867. stopOptions;
  868. end;
  869. inc(Level);
  870. skip[level]:=(skip[level-1] or (not check_symbol(upper(GetName(opts)))));
  871. end
  872. else
  873. if (s='IFNDEF') then
  874. begin
  875. RemoveSep(opts);
  876. if Level>=maxlevel then
  877. begin
  878. Message(option_too_many_ifdef);
  879. stopOptions;
  880. end;
  881. inc(Level);
  882. skip[level]:=(skip[level-1] or (check_symbol(upper(GetName(opts)))));
  883. end
  884. else
  885. if (s='ELSE') then
  886. skip[level]:=skip[level-1] or (not skip[level])
  887. else
  888. if (s='ENDIF') then
  889. begin
  890. skip[level]:=false;
  891. if Level=0 then
  892. begin
  893. Message(option_too_many_endif);
  894. stopOptions;
  895. end;
  896. dec(level);
  897. end
  898. else
  899. if (not skip[level]) then
  900. begin
  901. if (s='DEFINE') then
  902. begin
  903. RemoveSep(opts);
  904. def_symbol(upper(GetName(opts)));
  905. end
  906. else
  907. if (s='UNDEF') then
  908. begin
  909. RemoveSep(opts);
  910. undef_symbol(upper(GetName(opts)));
  911. end
  912. else
  913. if (s='WRITE') then
  914. begin
  915. Delete(opts,1,1);
  916. WriteLn(opts);
  917. end
  918. else
  919. if (s='INCLUDE') then
  920. begin
  921. Delete(opts,1,1);
  922. Interpret_file(opts);
  923. end;
  924. end;
  925. end
  926. else
  927. begin
  928. if (opts[1]='-') or (opts[1]='@') then
  929. begin
  930. if (not skip[level]) then
  931. interpret_option(opts,false);
  932. Option_read:=true;
  933. end
  934. else
  935. Message1(option_illegal_para,opts);
  936. end;
  937. end;
  938. end;
  939. if Level>0 then
  940. Message(option_too_less_endif);
  941. if Not Option_read then
  942. Message1(option_no_option_found,filename);
  943. Close(f);
  944. Dec(FileLevel);
  945. end;
  946. procedure Toption.Interpret_envvar(const envname : string);
  947. var
  948. argstart,
  949. env,
  950. pc : pchar;
  951. arglen : longint;
  952. quote : set of char;
  953. hs : string;
  954. begin
  955. Message1(option_using_env,envname);
  956. env:=GetEnvPChar(envname);
  957. pc:=env;
  958. if assigned(pc) then
  959. begin
  960. repeat
  961. { skip leading spaces }
  962. while pc^ in [' ',#9,#13] do
  963. inc(pc);
  964. case pc^ of
  965. #0 :
  966. break;
  967. '"' :
  968. begin
  969. quote:=['"'];
  970. inc(pc);
  971. end;
  972. '''' :
  973. begin
  974. quote:=[''''];
  975. inc(pc);
  976. end;
  977. else
  978. quote:=[' ',#9,#13];
  979. end;
  980. { scan until the end of the argument }
  981. argstart:=pc;
  982. while (pc^<>#0) and not(pc^ in quote) do
  983. inc(pc);
  984. { create argument }
  985. arglen:=pc-argstart;
  986. hs[0]:=chr(arglen);
  987. move(argstart^,hs[1],arglen);
  988. interpret_option(hs,true);
  989. { skip quote }
  990. if pc^ in quote then
  991. inc(pc);
  992. until false;
  993. end
  994. else
  995. Message1(option_no_option_found,'(env) '+envname);
  996. FreeEnvPChar(env);
  997. end;
  998. procedure toption.read_parameters;
  999. var
  1000. opts : string;
  1001. paramindex : longint;
  1002. begin
  1003. paramindex:=0;
  1004. while paramindex<paramcount do
  1005. begin
  1006. inc(paramindex);
  1007. opts:=system.paramstr(paramindex);
  1008. case opts[1] of
  1009. '@' :
  1010. if not firstpass then
  1011. begin
  1012. Delete(opts,1,1);
  1013. Message1(option_reading_further_from,opts);
  1014. interpret_file(opts);
  1015. end;
  1016. '!' :
  1017. if not firstpass then
  1018. begin
  1019. Delete(opts,1,1);
  1020. Message1(option_reading_further_from,'(env) '+opts);
  1021. interpret_envvar(opts);
  1022. end;
  1023. else
  1024. interpret_option(opts,true);
  1025. end;
  1026. end;
  1027. end;
  1028. procedure toption.parsecmd(cmd:string);
  1029. var
  1030. i,ps : longint;
  1031. opts : string;
  1032. begin
  1033. while (cmd<>'') do
  1034. begin
  1035. while cmd[1]=' ' do
  1036. delete(cmd,1,1);
  1037. i:=pos(' ',cmd);
  1038. if i=0 then
  1039. i:=256;
  1040. opts:=Copy(cmd,1,i-1);
  1041. Delete(cmd,1,i);
  1042. case opts[1] of
  1043. '@' :
  1044. if not firstpass then
  1045. begin
  1046. Delete(opts,1,1);
  1047. Message1(option_reading_further_from,opts);
  1048. interpret_file(opts);
  1049. end;
  1050. '!' :
  1051. if not firstpass then
  1052. begin
  1053. Delete(opts,1,1);
  1054. Message1(option_reading_further_from,'(env) '+opts);
  1055. interpret_envvar(opts);
  1056. end;
  1057. '"' :
  1058. begin
  1059. Delete(opts,1,1);
  1060. ps:=pos('"',cmd);
  1061. if (i<>256) and (ps>0) then
  1062. begin
  1063. opts:=opts + ' '+ copy(cmd,1,ps-1);
  1064. cmd:=copy(cmd,ps+1,255);
  1065. end;
  1066. interpret_option(opts,true);
  1067. end;
  1068. else
  1069. interpret_option(opts,true);
  1070. end;
  1071. end;
  1072. end;
  1073. procedure toption.writequickinfo;
  1074. var
  1075. s : string;
  1076. i : longint;
  1077. procedure addinfo(const hs:string);
  1078. begin
  1079. if s<>'' then
  1080. s:=s+' '+hs
  1081. else
  1082. s:=hs;
  1083. end;
  1084. begin
  1085. s:='';
  1086. i:=0;
  1087. while (i<length(quickinfo)) do
  1088. begin
  1089. inc(i);
  1090. case quickinfo[i] of
  1091. 'S' :
  1092. begin
  1093. inc(i);
  1094. case quickinfo[i] of
  1095. 'O' :
  1096. addinfo(lower(source_info.shortname));
  1097. {$ifdef Delphi}
  1098. 'P' :
  1099. addinfo('i386');
  1100. {$else Delphi}
  1101. 'P' :
  1102. addinfo(source_cpu_string);
  1103. {$endif Delphi}
  1104. else
  1105. IllegalPara('-iS'+QuickInfo);
  1106. end;
  1107. end;
  1108. 'T' :
  1109. begin
  1110. inc(i);
  1111. case quickinfo[i] of
  1112. 'O' :
  1113. addinfo(lower(target_info.shortname));
  1114. 'P' :
  1115. AddInfo(target_cpu_string);
  1116. else
  1117. IllegalPara('-iT'+QuickInfo);
  1118. end;
  1119. end;
  1120. 'V' :
  1121. AddInfo(version_string);
  1122. 'D' :
  1123. AddInfo(date_string);
  1124. '_' :
  1125. ;
  1126. else
  1127. IllegalPara('-i'+QuickInfo);
  1128. end;
  1129. end;
  1130. if s<>'' then
  1131. begin
  1132. writeln(s);
  1133. stopoptions;
  1134. end;
  1135. end;
  1136. constructor TOption.create;
  1137. begin
  1138. DoWriteLogo:=false;
  1139. NoPressEnter:=false;
  1140. FirstPass:=false;
  1141. FileLevel:=0;
  1142. Quickinfo:='';
  1143. ParaIncludePath:=TSearchPathList.Create;
  1144. ParaObjectPath:=TSearchPathList.Create;
  1145. ParaUnitPath:=TSearchPathList.Create;
  1146. ParaLibraryPath:=TSearchPathList.Create;
  1147. end;
  1148. destructor TOption.destroy;
  1149. begin
  1150. ParaIncludePath.Free;
  1151. ParaObjectPath.Free;
  1152. ParaUnitPath.Free;
  1153. ParaLibraryPath.Free;
  1154. end;
  1155. {****************************************************************************
  1156. Callable Routines
  1157. ****************************************************************************}
  1158. procedure read_arguments(cmd:string);
  1159. var
  1160. configpath : pathstr;
  1161. s : string;
  1162. i : integer;
  1163. begin
  1164. option:=coption.create;
  1165. disable_configfile:=false;
  1166. { default defines }
  1167. def_symbol(upper(target_info.shortname));
  1168. def_symbol('FPC');
  1169. def_symbol('VER'+version_nr);
  1170. def_symbol('VER'+version_nr+'_'+release_nr);
  1171. def_symbol('VER'+version_nr+'_'+release_nr+'_'+patch_nr);
  1172. {$ifdef newcg}
  1173. def_symbol('WITHNEWCG');
  1174. {$endif}
  1175. { Temporary defines, until things settle down }
  1176. {$ifdef SUPPORT_FIXED}
  1177. def_symbol('HASFIXED');
  1178. {$endif SUPPORT_FIXED}
  1179. def_symbol('HASWIDECHAR');
  1180. def_symbol('HASOUT');
  1181. def_symbol('HASINTF');
  1182. def_symbol('HASVARIANT');
  1183. def_symbol('INTERNSETLENGTH');
  1184. def_symbol('INT64FUNCRESOK');
  1185. def_symbol('PACKENUMFIXED');
  1186. def_symbol('HAS_ADDR_STACK_ON_STACK');
  1187. def_symbol('NOBOUNDCHECK');
  1188. { some stuff for TP compatibility }
  1189. {$ifdef i386}
  1190. def_symbol('CPU86');
  1191. def_symbol('CPU87');
  1192. {$endif}
  1193. {$ifdef m68k}
  1194. def_symbol('CPU68');
  1195. {$endif}
  1196. { new processor stuff }
  1197. {$ifdef i386}
  1198. def_symbol('CPUI386');
  1199. {$endif}
  1200. {$ifdef m68k}
  1201. def_symbol('CPU68K');
  1202. {$endif}
  1203. {$ifdef ALPHA}
  1204. def_symbol('CPUALPHA');
  1205. {$endif}
  1206. {$ifdef powerpc}
  1207. def_symbol('CPUPOWERPC');
  1208. {$endif}
  1209. { get default messagefile }
  1210. {$ifdef Delphi}
  1211. msgfilename:=dmisc.getenv('PPC_ERROR_FILE');
  1212. {$else Delphi}
  1213. msgfilename:=dos.getenv('PPC_ERROR_FILE');
  1214. {$endif Delphi}
  1215. { default configfile }
  1216. if (cmd<>'') and (cmd[1]='[') then
  1217. begin
  1218. ppccfg:=Copy(cmd,2,pos(']',cmd)-2);
  1219. Delete(cmd,1,pos(']',cmd));
  1220. end
  1221. else
  1222. begin
  1223. {$ifdef i386}
  1224. ppccfg:='ppc386.cfg';
  1225. {$endif i386}
  1226. {$ifdef ia64}
  1227. ppccfg:='ppcia64.cfg';
  1228. {$endif ia64}
  1229. {$ifdef m68k}
  1230. ppccfg:='ppc68k.cfg';
  1231. {$endif}
  1232. {$ifdef alpha}
  1233. ppccfg:='ppcalpha.cfg';
  1234. {$endif}
  1235. {$ifdef powerpc}
  1236. ppccfg:='ppcppc.cfg';
  1237. {$endif}
  1238. end;
  1239. { Order to read ppc386.cfg:
  1240. 1 - current dir
  1241. 2 - configpath
  1242. 3 - compiler path }
  1243. {$ifdef Delphi}
  1244. configpath:=FixPath(dmisc.getenv('PPC_CONFIG_PATH'),false);
  1245. {$else Delphi}
  1246. configpath:=FixPath(dos.getenv('PPC_CONFIG_PATH'),false);
  1247. {$endif Delphi}
  1248. {$ifdef Unix}
  1249. if configpath='' then
  1250. configpath:='/etc/';
  1251. {$endif}
  1252. if ppccfg<>'' then
  1253. begin
  1254. read_configfile:=true;
  1255. if not FileExists(ppccfg) then
  1256. begin
  1257. {$ifdef Unix}
  1258. if (dos.getenv('HOME')<>'') and FileExists(FixPath(dos.getenv('HOME'),false)+'.'+ppccfg) then
  1259. ppccfg:=FixPath(dos.getenv('HOME'),false)+'.'+ppccfg
  1260. else
  1261. {$endif}
  1262. if FileExists(configpath+ppccfg) then
  1263. ppccfg:=configpath+ppccfg
  1264. else
  1265. {$ifndef Unix}
  1266. if FileExists(exepath+ppccfg) then
  1267. ppccfg:=exepath+ppccfg
  1268. else
  1269. {$endif}
  1270. read_configfile:=false;
  1271. end;
  1272. end
  1273. else
  1274. read_configfile:=false;
  1275. { Read commandline and configfile }
  1276. target_is_set:=false;
  1277. asm_is_set:=false;
  1278. param_file:='';
  1279. if read_configfile then
  1280. begin
  1281. { read the parameters quick, only -i -v -T }
  1282. option.firstpass:=true;
  1283. if cmd<>'' then
  1284. option.parsecmd(cmd)
  1285. else
  1286. begin
  1287. option.read_parameters;
  1288. { Write only quickinfo }
  1289. if option.quickinfo<>'' then
  1290. option.writequickinfo;
  1291. end;
  1292. { Read the configfile }
  1293. option.firstpass:=false;
  1294. if read_configfile then
  1295. option.interpret_file(ppccfg);
  1296. end;
  1297. if cmd<>'' then
  1298. option.parsecmd(cmd)
  1299. else
  1300. begin
  1301. option.read_parameters;
  1302. { Write only quickinfo }
  1303. if option.quickinfo<>'' then
  1304. option.writequickinfo;
  1305. end;
  1306. { Write help pages }
  1307. if (cmd='') and (paramcount=0) then
  1308. Option.WriteHelpPages;
  1309. { Stop if errors in options }
  1310. if ErrorCount>0 then
  1311. StopOptions;
  1312. { Non-core target defines }
  1313. s:=target_info.extradefines;
  1314. while (s<>'') do
  1315. begin
  1316. i:=pos(';',s);
  1317. if i=0 then
  1318. i:=length(s)+1;
  1319. def_symbol(Copy(s,1,i-1));
  1320. delete(s,1,i);
  1321. end;
  1322. { endian define }
  1323. case target_info.endian of
  1324. endian_little :
  1325. def_symbol('ENDIAN_LITTLE');
  1326. endian_big :
  1327. def_symbol('ENDIAN_BIG');
  1328. end;
  1329. { write logo if set }
  1330. if option.DoWriteLogo then
  1331. option.WriteLogo;
  1332. { Check file to compile }
  1333. if param_file='' then
  1334. begin
  1335. Message(option_no_source_found);
  1336. StopOptions;
  1337. end;
  1338. {$ifndef Unix}
  1339. param_file:=FixFileName(param_file);
  1340. {$endif}
  1341. fsplit(param_file,inputdir,inputfile,inputextension);
  1342. if inputextension='' then
  1343. begin
  1344. if FileExists(inputdir+inputfile+target_info.sourceext) then
  1345. inputextension:=target_info.sourceext
  1346. else
  1347. if FileExists(inputdir+inputfile+target_info.pasext) then
  1348. inputextension:=target_info.pasext;
  1349. end;
  1350. { Add paths specified with parameters to the searchpaths }
  1351. UnitSearchPath.AddList(option.ParaUnitPath,true);
  1352. ObjectSearchPath.AddList(option.ParaObjectPath,true);
  1353. IncludeSearchPath.AddList(option.ParaIncludePath,true);
  1354. LibrarySearchPath.AddList(option.ParaLibraryPath,true);
  1355. { add unit environment and exepath to the unit search path }
  1356. if inputdir<>'' then
  1357. Unitsearchpath.AddPath(inputdir,true);
  1358. if not disable_configfile then
  1359. {$ifdef Delphi}
  1360. UnitSearchPath.AddPath(dmisc.getenv(target_info.unit_env),false);
  1361. {$else}
  1362. UnitSearchPath.AddPath(dos.getenv(target_info.unit_env),false);
  1363. {$endif Delphi}
  1364. {$ifdef Unix}
  1365. fpcdir:=FixPath(getenv('FPCDIR'),false);
  1366. if fpcdir='' then
  1367. begin
  1368. if PathExists('/usr/local/lib/fpc/'+version_string) then
  1369. fpcdir:='/usr/local/lib/fpc/'+version_string+'/'
  1370. else
  1371. fpcdir:='/usr/lib/fpc/'+version_string+'/';
  1372. end;
  1373. {$else}
  1374. fpcdir:=FixPath(getenv('FPCDIR'),false);
  1375. if fpcdir='' then
  1376. begin
  1377. fpcdir:=ExePath+'../';
  1378. if not(PathExists(fpcdir+'/units')) and
  1379. not(PathExists(fpcdir+'/rtl')) then
  1380. fpcdir:=fpcdir+'../';
  1381. end;
  1382. {$endif}
  1383. { first try development RTL, else use the default installation path }
  1384. if not disable_configfile then
  1385. begin
  1386. if PathExists(FpcDir+'rtl/'+lower(target_info.shortname)) then
  1387. UnitSearchPath.AddPath(FpcDir+'rtl/'+lower(target_info.shortname),false)
  1388. else
  1389. begin
  1390. UnitSearchPath.AddPath(FpcDir+'units/'+lower(target_info.shortname),false);
  1391. UnitSearchPath.AddPath(FpcDir+'units/'+lower(target_info.shortname)+'/rtl',false);
  1392. end;
  1393. end;
  1394. { Add exepath if the exe is not in the current dir, because that is always searched already }
  1395. if ExePath<>GetCurrentDir then
  1396. UnitSearchPath.AddPath(ExePath,false);
  1397. { Add unit dir to the object and library path }
  1398. objectsearchpath.AddList(unitsearchpath,false);
  1399. librarysearchpath.AddList(unitsearchpath,false);
  1400. { switch assembler if it's binary and we got -a on the cmdline }
  1401. if (cs_asm_leave in initglobalswitches) and
  1402. (target_asm.outputbinary) then
  1403. begin
  1404. Message(option_switch_bin_to_src_assembler);
  1405. set_target_asm(target_info.assemextern);
  1406. end;
  1407. if (target_asm.supported_target <> target_any) and
  1408. (target_asm.supported_target <> target_info.target) then
  1409. begin
  1410. Message2(option_incompatible_asm,target_asm.idtxt,target_info.name);
  1411. set_target_asm(target_info.assemextern);
  1412. Message1(option_asm_forced,target_asm.idtxt);
  1413. end;
  1414. { turn off stripping if compiling with debuginfo or profile }
  1415. if (cs_debuginfo in initmoduleswitches) or
  1416. (cs_profile in initmoduleswitches) then
  1417. initglobalswitches:=initglobalswitches-[cs_link_strip];
  1418. if not LinkTypeSetExplicitly then
  1419. set_default_link_type;
  1420. { Set defines depending on the target }
  1421. if (target_info.target in [target_i386_GO32V1,target_i386_GO32V2]) then
  1422. def_symbol('DPMI'); { MSDOS is not defined in BP when target is DPMI }
  1423. option.free;
  1424. Option:=nil;
  1425. end;
  1426. initialization
  1427. coption:=toption;
  1428. finalization
  1429. if assigned(option) then
  1430. option.free;
  1431. end.
  1432. {
  1433. $Log$
  1434. Revision 1.46 2001-06-29 19:41:54 peter
  1435. * patch from Pavel Ozerski to support +/- better
  1436. Revision 1.45 2001/06/19 14:55:45 jonas
  1437. * fixed typo in NOBOUNDCHECK define
  1438. Revision 1.44 2001/06/18 20:36:24 peter
  1439. * -Ur switch (merged)
  1440. * masm fixes (merged)
  1441. * quoted filenames for go32v2 and win32
  1442. Revision 1.43 2001/06/02 19:21:45 peter
  1443. * extradefines field added to target_info, so that targets don't
  1444. need to put code in options.pas for it
  1445. Revision 1.42 2001/05/18 22:28:59 peter
  1446. * endian define
  1447. Revision 1.41 2001/05/12 12:11:31 peter
  1448. * simplify_ppu is now the default, a recompile of the compiler now
  1449. only compiles pp.pas
  1450. Revision 1.40 2001/04/18 22:01:54 peter
  1451. * registration of targets and assemblers
  1452. Revision 1.39 2001/04/13 01:22:10 peter
  1453. * symtable change to classes
  1454. * range check generation and errors fixed, make cycle DEBUG=1 works
  1455. * memory leaks fixed
  1456. Revision 1.38 2001/03/25 12:27:31 peter
  1457. * fixed -Se (merged)
  1458. Revision 1.37 2001/03/23 00:16:07 florian
  1459. + some stuff to compile FreeCLX added
  1460. Revision 1.36 2001/03/13 20:59:56 peter
  1461. * message loading fixes from Sergey (merged)
  1462. Revision 1.35 2001/03/10 13:19:10 peter
  1463. * don't check messagefile for numbers, this allows the usage of
  1464. 1.1 msgfiles with a 1.0.x compiler
  1465. Revision 1.34 2001/03/05 21:50:29 peter
  1466. * press enter moved to errore.msg
  1467. Revision 1.33 2001/03/03 12:41:22 jonas
  1468. * simplified and optimized range checking code, FPC_BOUNDCHECK is no longer necessary
  1469. Revision 1.32 2001/02/26 19:44:53 peter
  1470. * merged generic m68k updates from fixes branch
  1471. Revision 1.31 2001/02/26 12:47:46 jonas
  1472. * fixed bug in type checking for compatibility of set elements (merged)
  1473. * released fix in options.pas from Carl also for FPC (merged)
  1474. Revision 1.30 2001/02/26 08:08:39 michael
  1475. * option_help_pages:
  1476. allow to omit an option (use one space char insteed an option)
  1477. but to indent a continuation line as if option is present. For lines:
  1478. 3*2CX_first line
  1479. 3*2 _second line
  1480. 3*2*_third line
  1481. we could get:
  1482. -CX first line
  1483. second line
  1484. third line
  1485. Revision 1.29 2001/02/26 07:49:50 michael
  1486. Support replacements for all -F<x> options
  1487. Revision 1.28 2001/02/05 21:26:36 peter
  1488. * applied patches from Sergey Korshunoff
  1489. Revision 1.27 2001/01/20 18:36:51 hajny
  1490. + APPTYPE support under OS/2, app_fs, GetEnvPChar for OS/2
  1491. Revision 1.26 2001/01/12 19:21:09 peter
  1492. * fixed writing of quickinfo when no ppc386.cfg is available
  1493. Revision 1.25 2001/01/05 17:36:57 florian
  1494. * the info about exception frames is stored now on the stack
  1495. instead on the heap
  1496. Revision 1.24 2000/12/25 00:07:26 peter
  1497. + new tlinkedlist class (merge of old tstringqueue,tcontainer and
  1498. tlinkedlist objects)
  1499. Revision 1.23 2000/12/24 12:21:41 peter
  1500. * use system.paramstr()
  1501. Revision 1.22 2000/12/23 19:46:49 peter
  1502. * object to class conversion
  1503. * more verbosity for -vt and -vd
  1504. * -i options can be put after eachother so the Makefiles only need
  1505. to call fpc once for all info (will be twice as the first one will
  1506. be to check the version if fpc supports multiple info)
  1507. Revision 1.21 2000/12/16 15:56:19 jonas
  1508. - removed all ifdef cardinalmulfix code
  1509. Revision 1.20 2000/12/15 13:26:01 jonas
  1510. * only return int64's from functions if it int64funcresok is defined
  1511. + added int64funcresok define to options.pas
  1512. Revision 1.19 2000/11/30 22:48:23 florian
  1513. * opts386 renamed
  1514. Revision 1.18 2000/11/29 00:30:34 florian
  1515. * unused units removed from uses clause
  1516. * some changes for widestrings
  1517. Revision 1.17 2000/11/13 15:26:12 marco
  1518. * Renamefest
  1519. Revision 1.16 2000/11/12 22:20:37 peter
  1520. * create generic toutputsection for binary writers
  1521. Revision 1.15 2000/11/07 15:09:27 marco
  1522. * Define UNIX for FreeBSD and Linux. Checked crosscompile thingy.
  1523. Revision 1.14 2000/11/07 14:25:08 marco
  1524. * FreeBSD defines (FreeBSD,Linux,BSD,Unix) Linux defines (Linux,Unix)
  1525. Revision 1.13 2000/11/06 20:30:54 peter
  1526. * more fixes to get make cycle working
  1527. Revision 1.12 2000/11/04 14:25:20 florian
  1528. + merged Attila's changes for interfaces, not tested yet
  1529. Revision 1.11 2000/09/26 10:50:41 jonas
  1530. * initmodeswitches is changed is you change the compiler mode from the
  1531. command line (the -S<x> switches didn't work anymore for changing the
  1532. compiler mode) (merged from fixes branch)
  1533. Revision 1.10 2000/09/24 21:33:47 peter
  1534. * message updates merges
  1535. Revision 1.9 2000/09/24 15:06:20 peter
  1536. * use defines.inc
  1537. Revision 1.8 2000/09/18 12:28:41 marco
  1538. * Definition of multiple FreeBSD target defines moved to after error check
  1539. commandline parsing
  1540. Revision 1.7 2000/09/16 12:22:52 peter
  1541. * freebsd support merged
  1542. Revision 1.6 2000/08/27 16:11:51 peter
  1543. * moved some util functions from globals,cobjects to cutils
  1544. * splitted files into finput,fmodule
  1545. Revision 1.5 2000/08/07 11:31:04 jonas
  1546. * fixed bug in type conversions between enum subranges (it didn't take
  1547. the packenum directive into account)
  1548. + define PACKENUMFIXED symbol in options.pas
  1549. (merged from fixes branch)
  1550. Revision 1.4 2000/07/14 05:11:48 michael
  1551. + Patch to 1.1
  1552. Revision 1.3 2000/07/13 12:08:26 michael
  1553. + patched to 1.1.0 with former 1.09patch from peter
  1554. Revision 1.2 2000/07/13 11:32:44 michael
  1555. + removed logs
  1556. }