ncgld.pas 58 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416
  1. {
  2. $Id$
  3. Copyright (c) 1998-2002 by Florian Klaempfl
  4. Generate assembler for nodes that handle loads and assignments which
  5. are the same for all (most) processors
  6. This program is free software; you can redistribute it and/or modify
  7. it under the terms of the GNU General Public License as published by
  8. the Free Software Foundation; either version 2 of the License, or
  9. (at your option) any later version.
  10. This program is distributed in the hope that it will be useful,
  11. but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. GNU General Public License for more details.
  14. You should have received a copy of the GNU General Public License
  15. along with this program; if not, write to the Free Software
  16. Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  17. ****************************************************************************
  18. }
  19. unit ncgld;
  20. {$i fpcdefs.inc}
  21. interface
  22. uses
  23. node,nld;
  24. type
  25. tcgloadnode = class(tloadnode)
  26. procedure pass_2;override;
  27. procedure generate_picvaraccess;virtual;
  28. end;
  29. tcgassignmentnode = class(tassignmentnode)
  30. procedure pass_2;override;
  31. end;
  32. tcgarrayconstructornode = class(tarrayconstructornode)
  33. procedure pass_2;override;
  34. end;
  35. implementation
  36. uses
  37. cutils,
  38. systems,
  39. verbose,globtype,globals,
  40. symconst,symtype,symdef,symsym,defutil,paramgr,
  41. ncnv,ncon,nmem,nbas,
  42. aasmbase,aasmtai,aasmcpu,
  43. cgbase,pass_2,
  44. procinfo,
  45. cpubase,cpuinfo,
  46. tgobj,ncgutil,
  47. cgutils,cgobj,
  48. ncgbas;
  49. {*****************************************************************************
  50. SecondLoad
  51. *****************************************************************************}
  52. procedure tcgloadnode.generate_picvaraccess;
  53. begin
  54. location.reference.base:=current_procinfo.got;
  55. location.reference.symbol:=objectlibrary.newasmsymbol(tvarsym(symtableentry).mangledname+'@GOT',AB_EXTERNAL,AT_DATA);
  56. end;
  57. procedure tcgloadnode.pass_2;
  58. var
  59. hregister : tregister;
  60. symtabletype : tsymtabletype;
  61. href : treference;
  62. newsize : tcgsize;
  63. endrelocatelab,
  64. norelocatelab : tasmlabel;
  65. paraloc1 : tparalocation;
  66. begin
  67. { we don't know the size of all arrays }
  68. newsize:=def_cgsize(resulttype.def);
  69. location_reset(location,LOC_REFERENCE,newsize);
  70. case symtableentry.typ of
  71. absolutesym :
  72. begin
  73. { this is only for toasm and toaddr }
  74. case tabsolutesym(symtableentry).abstyp of
  75. toaddr :
  76. begin
  77. {$ifdef i386}
  78. if tabsolutesym(symtableentry).absseg then
  79. location.reference.segment:=NR_FS;
  80. {$endif i386}
  81. location.reference.offset:=tabsolutesym(symtableentry).fieldoffset;
  82. end;
  83. toasm :
  84. location.reference.symbol:=objectlibrary.newasmsymbol(tabsolutesym(symtableentry).mangledname,AB_EXTERNAL,AT_DATA);
  85. else
  86. internalerror(200310283);
  87. end;
  88. end;
  89. constsym:
  90. begin
  91. if tconstsym(symtableentry).consttyp=constresourcestring then
  92. begin
  93. location_reset(location,LOC_CREFERENCE,OS_ADDR);
  94. location.reference.symbol:=objectlibrary.newasmsymbol(make_mangledname('RESOURCESTRINGLIST',tconstsym(symtableentry).owner,''),AB_EXTERNAL,AT_DATA);
  95. location.reference.offset:=tconstsym(symtableentry).resstrindex*16+8;
  96. end
  97. else
  98. internalerror(22798);
  99. end;
  100. varsym :
  101. begin
  102. if (tvarsym(symtableentry).varspez=vs_const) then
  103. location_reset(location,LOC_CREFERENCE,newsize);
  104. symtabletype:=symtable.symtabletype;
  105. hregister:=NR_NO;
  106. { C variable }
  107. if (vo_is_C_var in tvarsym(symtableentry).varoptions) then
  108. begin
  109. location.reference.symbol:=objectlibrary.newasmsymbol(tvarsym(symtableentry).mangledname,AB_EXTERNAL,AT_DATA);
  110. end
  111. { DLL variable }
  112. else if (vo_is_dll_var in tvarsym(symtableentry).varoptions) then
  113. begin
  114. if target_info.system=system_powerpc_darwin then
  115. begin
  116. generate_picvaraccess;
  117. if not(pi_needs_got in current_procinfo.flags) then
  118. internalerror(200403022);
  119. end
  120. else
  121. begin
  122. hregister:=cg.getaddressregister(exprasmlist);
  123. location.reference.symbol:=objectlibrary.newasmsymbol(tvarsym(symtableentry).mangledname,AB_EXTERNAL,AT_DATA);
  124. cg.a_load_ref_reg(exprasmlist,OS_ADDR,OS_ADDR,location.reference,hregister);
  125. reference_reset_base(location.reference,hregister,0);
  126. end;
  127. end
  128. { external variable }
  129. else if (vo_is_external in tvarsym(symtableentry).varoptions) then
  130. begin
  131. location.reference.symbol:=objectlibrary.newasmsymbol(tvarsym(symtableentry).mangledname,AB_EXTERNAL,AT_DATA);
  132. end
  133. { thread variable }
  134. else if (vo_is_thread_var in tvarsym(symtableentry).varoptions) then
  135. begin
  136. {
  137. Thread var loading is optimized to first check if
  138. a relocate function is available. When the function
  139. is available it is called to retrieve the address.
  140. Otherwise the address is loaded with the symbol
  141. The code needs to be in the order to first handle the
  142. call and then the address load to be sure that the
  143. register that is used for returning is the same (PFV)
  144. }
  145. objectlibrary.getlabel(norelocatelab);
  146. objectlibrary.getlabel(endrelocatelab);
  147. { make sure hregister can't allocate the register necessary for the parameter }
  148. paraloc1:=paramanager.getintparaloc(pocall_default,1);
  149. hregister:=cg.getaddressregister(exprasmlist);
  150. reference_reset_symbol(href,objectlibrary.newasmsymbol('FPC_THREADVAR_RELOCATE',AB_EXTERNAL,AT_DATA),0);
  151. cg.a_load_ref_reg(exprasmlist,OS_ADDR,OS_ADDR,href,hregister);
  152. cg.ungetregister(exprasmlist,hregister);
  153. cg.a_cmp_const_reg_label(exprasmlist,OS_ADDR,OC_EQ,0,hregister,norelocatelab);
  154. { don't save the allocated register else the result will be destroyed later }
  155. reference_reset_symbol(href,objectlibrary.newasmsymbol(tvarsym(symtableentry).mangledname,AB_EXTERNAL,AT_DATA),0);
  156. paramanager.allocparaloc(exprasmlist,paraloc1);
  157. cg.a_param_ref(exprasmlist,OS_ADDR,href,paraloc1);
  158. paramanager.freeparaloc(exprasmlist,paraloc1);
  159. cg.allocexplicitregisters(exprasmlist,R_INTREGISTER,paramanager.get_volatile_registers_int(pocall_default));
  160. cg.a_call_reg(exprasmlist,hregister);
  161. cg.deallocexplicitregisters(exprasmlist,R_INTREGISTER,paramanager.get_volatile_registers_int(pocall_default));
  162. cg.getexplicitregister(exprasmlist,NR_FUNCTION_RESULT_REG);
  163. cg.ungetregister(exprasmlist,NR_FUNCTION_RESULT_REG);
  164. hregister:=cg.getaddressregister(exprasmlist);
  165. cg.a_load_reg_reg(exprasmlist,OS_INT,OS_ADDR,NR_FUNCTION_RESULT_REG,hregister);
  166. cg.a_jmp_always(exprasmlist,endrelocatelab);
  167. cg.a_label(exprasmlist,norelocatelab);
  168. { no relocation needed, load the address of the variable only, the
  169. layout of a threadvar is (4 bytes pointer):
  170. 0 - Threadvar index
  171. 4 - Threadvar value in single threading }
  172. reference_reset_symbol(href,objectlibrary.newasmsymbol(tvarsym(symtableentry).mangledname,AB_EXTERNAL,AT_DATA),POINTER_SIZE);
  173. cg.a_loadaddr_ref_reg(exprasmlist,href,hregister);
  174. cg.a_label(exprasmlist,endrelocatelab);
  175. location.reference.base:=hregister;
  176. end
  177. { nested variable }
  178. else if assigned(left) then
  179. begin
  180. if not(symtabletype in [localsymtable,parasymtable]) then
  181. internalerror(200309285);
  182. secondpass(left);
  183. if left.location.loc<>LOC_REGISTER then
  184. internalerror(200309286);
  185. hregister:=left.location.register;
  186. location.reference.base:=hregister;
  187. location.reference.offset:=tvarsym(symtableentry).localloc.reference.offset;
  188. end
  189. { normal variable }
  190. else
  191. begin
  192. { in case it is a register variable: }
  193. if tvarsym(symtableentry).localloc.loc in [LOC_REGISTER,LOC_FPUREGISTER] then
  194. begin
  195. case getregtype(tvarsym(symtableentry).localloc.register) of
  196. R_FPUREGISTER :
  197. begin
  198. location_reset(location,LOC_CFPUREGISTER,def_cgsize(resulttype.def));
  199. location.register:=tvarsym(symtableentry).localloc.register;
  200. end;
  201. R_INTREGISTER :
  202. begin
  203. location_reset(location,LOC_CREGISTER,def_cgsize(resulttype.def));
  204. location.register:=tvarsym(symtableentry).localloc.register;
  205. hregister := location.register;
  206. end;
  207. else
  208. internalerror(200301172);
  209. end;
  210. end
  211. else
  212. begin
  213. case symtabletype of
  214. localsymtable,
  215. parasymtable :
  216. begin
  217. if tvarsym(symtableentry).localloc.loc<>LOC_REFERENCE then
  218. internalerror(2003091816);
  219. location.reference.base:=tvarsym(symtableentry).localloc.reference.index;
  220. location.reference.offset:=tvarsym(symtableentry).localloc.reference.offset;
  221. end;
  222. globalsymtable,
  223. staticsymtable :
  224. begin
  225. if cs_create_pic in aktmoduleswitches then
  226. begin
  227. generate_picvaraccess;
  228. if not(pi_needs_got in current_procinfo.flags) then
  229. internalerror(200403023);
  230. end
  231. else
  232. location.reference.symbol:=objectlibrary.newasmsymbol(tvarsym(symtableentry).mangledname,AB_EXTERNAL,AT_DATA);
  233. end;
  234. stt_exceptsymtable:
  235. begin
  236. if tvarsym(symtableentry).localloc.loc<>LOC_REFERENCE then
  237. internalerror(2003091817);
  238. location.reference.base:=tvarsym(symtableentry).localloc.reference.index;
  239. location.reference.offset:=tvarsym(symtableentry).localloc.reference.offset;
  240. end;
  241. else
  242. internalerror(200305102);
  243. end;
  244. end;
  245. end;
  246. { handle call by reference variables when they are not
  247. alreayd copied to local copies. Also ignore the reference
  248. when we need to load the self pointer for objects }
  249. if (symtabletype=parasymtable) and
  250. not(vo_has_local_copy in tvarsym(symtableentry).varoptions) and
  251. not(nf_load_self_pointer in flags) and
  252. paramanager.push_addr_param(tvarsym(symtableentry).varspez,tvarsym(symtableentry).vartype.def,tprocdef(symtable.defowner).proccalloption) then
  253. begin
  254. if hregister=NR_NO then
  255. hregister:=cg.getaddressregister(exprasmlist);
  256. { we need to load only an address }
  257. location.size:=OS_ADDR;
  258. cg.a_load_loc_reg(exprasmlist,location.size,location,hregister);
  259. if tvarsym(symtableentry).varspez=vs_const then
  260. location_reset(location,LOC_CREFERENCE,newsize)
  261. else
  262. location_reset(location,LOC_REFERENCE,newsize);
  263. location.reference.base:=hregister;
  264. end;
  265. end;
  266. procsym:
  267. begin
  268. if not assigned(procdef) then
  269. internalerror(200312011);
  270. if assigned(left) then
  271. begin
  272. {
  273. THIS IS A TERRIBLE HACK!!!!!! WHICH WILL NOT WORK
  274. ON 64-BIT SYSTEMS: SINCE PROCSYM FOR METHODS
  275. CONSISTS OF TWO OS_ADDR, so you cannot set it
  276. to OS_64 - how to solve?? Carl
  277. Solved. Florian
  278. }
  279. if (sizeof(aword) = 4) then
  280. location_reset(location,LOC_CREFERENCE,OS_64)
  281. else if (sizeof(aword) = 8) then
  282. location_reset(location,LOC_CREFERENCE,OS_128)
  283. else
  284. internalerror(20020520);
  285. tg.GetTemp(exprasmlist,2*POINTER_SIZE,tt_normal,location.reference);
  286. secondpass(left);
  287. { load class instance address }
  288. case left.location.loc of
  289. LOC_CREGISTER,
  290. LOC_REGISTER:
  291. begin
  292. { this is not possible for objects }
  293. if is_object(left.resulttype.def) then
  294. internalerror(200304234);
  295. hregister:=left.location.register;
  296. end;
  297. LOC_CREFERENCE,
  298. LOC_REFERENCE:
  299. begin
  300. location_release(exprasmlist,left.location);
  301. hregister:=cg.getaddressregister(exprasmlist);
  302. if is_class_or_interface(left.resulttype.def) then
  303. cg.a_load_ref_reg(exprasmlist,OS_ADDR,OS_ADDR,left.location.reference,hregister)
  304. else
  305. cg.a_loadaddr_ref_reg(exprasmlist,left.location.reference,hregister);
  306. location_freetemp(exprasmlist,left.location);
  307. end;
  308. else
  309. internalerror(26019);
  310. end;
  311. { store the class instance address }
  312. href:=location.reference;
  313. inc(href.offset,POINTER_SIZE);
  314. cg.a_load_reg_ref(exprasmlist,OS_ADDR,OS_ADDR,hregister,href);
  315. { virtual method ? }
  316. if (po_virtualmethod in procdef.procoptions) then
  317. begin
  318. { load vmt pointer }
  319. reference_reset_base(href,hregister,0);
  320. reference_release(exprasmlist,href);
  321. hregister:=cg.getaddressregister(exprasmlist);
  322. cg.a_load_ref_reg(exprasmlist,OS_ADDR,OS_ADDR,href,hregister);
  323. reference_reset_base(href,hregister,
  324. procdef._class.vmtmethodoffset(procdef.extnumber));
  325. reference_release(exprasmlist,href);
  326. { load method address }
  327. hregister:=cg.getaddressregister(exprasmlist);
  328. cg.a_load_ref_reg(exprasmlist,OS_ADDR,OS_ADDR,href,hregister);
  329. { ... and store it }
  330. cg.a_load_reg_ref(exprasmlist,OS_ADDR,OS_ADDR,hregister,location.reference);
  331. cg.ungetregister(exprasmlist,hregister);
  332. end
  333. else
  334. begin
  335. { we don't use the hregister }
  336. cg.ungetregister(exprasmlist,hregister);
  337. { load address of the function }
  338. reference_reset_symbol(href,objectlibrary.newasmsymbol(procdef.mangledname,AB_EXTERNAL,AT_FUNCTION),0);
  339. hregister:=cg.getaddressregister(exprasmlist);
  340. cg.a_loadaddr_ref_reg(exprasmlist,href,hregister);
  341. cg.a_load_reg_ref(exprasmlist,OS_ADDR,OS_ADDR,hregister,location.reference);
  342. cg.ungetregister(exprasmlist,hregister);
  343. end;
  344. end
  345. else
  346. begin
  347. {!!!!! Be aware, work on virtual methods too }
  348. location.reference.symbol:=objectlibrary.newasmsymbol(procdef.mangledname,AB_EXTERNAL,AT_FUNCTION);
  349. end;
  350. end;
  351. typedconstsym :
  352. begin
  353. location.reference.symbol:=objectlibrary.newasmsymbol(ttypedconstsym(symtableentry).mangledname,AB_EXTERNAL,AT_DATA);
  354. end;
  355. else internalerror(4);
  356. end;
  357. end;
  358. {*****************************************************************************
  359. SecondAssignment
  360. *****************************************************************************}
  361. procedure tcgassignmentnode.pass_2;
  362. var
  363. otlabel,hlabel,oflabel : tasmlabel;
  364. fputyp : tfloattype;
  365. href : treference;
  366. old_allow_multi_pass2,
  367. releaseright : boolean;
  368. cgsize : tcgsize;
  369. r:Tregister;
  370. begin
  371. location_reset(location,LOC_VOID,OS_NO);
  372. otlabel:=truelabel;
  373. oflabel:=falselabel;
  374. objectlibrary.getlabel(truelabel);
  375. objectlibrary.getlabel(falselabel);
  376. {
  377. in most cases we can process first the right node which contains
  378. the most complex code. But not when the result is in the flags, then
  379. loading the left node afterwards can destroy the flags.
  380. when the right node returns as LOC_JUMP then we will generate
  381. the following code:
  382. rightnode
  383. true:
  384. leftnode
  385. assign 1
  386. false:
  387. leftnode
  388. assign 0
  389. }
  390. { Try to determine which side to calculate first, }
  391. if (right.expectloc<>LOC_FLAGS) and
  392. ((right.expectloc=LOC_JUMP) or
  393. (right.nodetype=calln) or
  394. (right.registersint>=left.registersint)) then
  395. begin
  396. secondpass(right);
  397. { increment source reference counter, this is
  398. useless for string constants}
  399. if (right.resulttype.def.needs_inittable) and
  400. (right.nodetype<>stringconstn) then
  401. cg.g_incrrefcount(exprasmlist,right.resulttype.def,right.location.reference,false);
  402. if codegenerror then
  403. exit;
  404. { We skip the generation of the left node when it's a jump, see
  405. explanation above }
  406. if (right.location.loc<>LOC_JUMP) and
  407. not(nf_concat_string in flags) then
  408. begin
  409. { left can't be never a 64 bit LOC_REGISTER, so the 3. arg }
  410. { can be false }
  411. secondpass(left);
  412. { decrement destination reference counter }
  413. if (left.resulttype.def.needs_inittable) then
  414. cg.g_decrrefcount(exprasmlist,left.resulttype.def,left.location.reference,false);
  415. if codegenerror then
  416. exit;
  417. end;
  418. end
  419. else
  420. begin
  421. { calculate left sides }
  422. { don't do it yet if it's a crgister (JM) }
  423. if not(nf_concat_string in flags) then
  424. begin
  425. secondpass(left);
  426. { decrement destination reference counter }
  427. if (left.resulttype.def.needs_inittable) then
  428. cg.g_decrrefcount(exprasmlist,left.resulttype.def,left.location.reference,false);
  429. if codegenerror then
  430. exit;
  431. end;
  432. { left can't be never a 64 bit LOC_REGISTER, so the 3. arg }
  433. { can be false }
  434. secondpass(right);
  435. { increment source reference counter, this is
  436. useless for string constants}
  437. if (right.resulttype.def.needs_inittable) and
  438. (right.nodetype<>stringconstn) then
  439. cg.g_incrrefcount(exprasmlist,right.resulttype.def,right.location.reference,false);
  440. if codegenerror then
  441. exit;
  442. end;
  443. releaseright:=true;
  444. { optimize temp to temp copies }
  445. if (left.nodetype = temprefn) and
  446. { we may store certain temps in registers in the future, then this }
  447. { optimization will have to be adapted }
  448. (left.location.loc = LOC_REFERENCE) and
  449. (right.location.loc = LOC_REFERENCE) and
  450. tg.istemp(right.location.reference) and
  451. (tg.sizeoftemp(exprasmlist,right.location.reference) = tg.sizeoftemp(exprasmlist,left.location.reference)) then
  452. begin
  453. { in theory, we should also make sure the left temp type is }
  454. { already more or less of the same kind (ie. we must not }
  455. { assign an ansistring to a normaltemp). In practice, the }
  456. { assignment node will have already taken care of this for us }
  457. tcgtemprefnode(left).changelocation(right.location.reference);
  458. end
  459. { shortstring assignments are handled separately }
  460. else if is_shortstring(left.resulttype.def) then
  461. begin
  462. {
  463. we can get here only in the following situations
  464. for the right node:
  465. - empty constant string
  466. - char
  467. }
  468. { empty constant string }
  469. if (right.nodetype=stringconstn) and
  470. (tstringconstnode(right).len=0) then
  471. begin
  472. cg.a_load_const_ref(exprasmlist,OS_8,0,left.location.reference);
  473. end
  474. { char loading }
  475. else if is_char(right.resulttype.def) then
  476. begin
  477. if right.nodetype=ordconstn then
  478. begin
  479. if (target_info.endian = endian_little) then
  480. cg.a_load_const_ref(exprasmlist,OS_16,(tordconstnode(right).value shl 8) or 1,
  481. left.location.reference)
  482. else
  483. cg.a_load_const_ref(exprasmlist,OS_16,tordconstnode(right).value or (1 shl 8),
  484. left.location.reference);
  485. end
  486. else
  487. begin
  488. href:=left.location.reference;
  489. cg.a_load_const_ref(exprasmlist,OS_8,1,href);
  490. inc(href.offset,1);
  491. case right.location.loc of
  492. LOC_REGISTER,
  493. LOC_CREGISTER :
  494. begin
  495. r:=cg.makeregsize(exprasmlist,right.location.register,OS_8);
  496. cg.a_load_reg_ref(exprasmlist,OS_8,OS_8,r,href);
  497. end;
  498. LOC_REFERENCE,
  499. LOC_CREFERENCE :
  500. cg.a_load_ref_ref(exprasmlist,OS_8,OS_8,right.location.reference,href);
  501. else
  502. internalerror(200205111);
  503. end;
  504. end;
  505. end
  506. else
  507. internalerror(200204249);
  508. end
  509. else
  510. begin
  511. case right.location.loc of
  512. LOC_CONSTANT :
  513. begin
  514. if right.location.size in [OS_64,OS_S64] then
  515. cg64.a_load64_const_loc(exprasmlist,
  516. right.location.valueqword,left.location)
  517. else
  518. cg.a_load_const_loc(exprasmlist,right.location.value,left.location);
  519. end;
  520. LOC_REFERENCE,
  521. LOC_CREFERENCE :
  522. begin
  523. case left.location.loc of
  524. LOC_CREGISTER :
  525. begin
  526. cgsize:=def_cgsize(left.resulttype.def);
  527. if cgsize in [OS_64,OS_S64] then
  528. begin
  529. cg64.a_load64_ref_reg(exprasmlist,
  530. right.location.reference,left.location.register64);
  531. location_release(exprasmlist,right.location);
  532. end
  533. else
  534. begin
  535. location_release(exprasmlist,right.location);
  536. cg.a_load_ref_reg(exprasmlist,cgsize,cgsize,
  537. right.location.reference,left.location.register);
  538. end;
  539. end;
  540. LOC_CFPUREGISTER :
  541. begin
  542. cg.a_loadfpu_ref_reg(exprasmlist,
  543. def_cgsize(right.resulttype.def),
  544. right.location.reference,
  545. left.location.register);
  546. end;
  547. LOC_REFERENCE,
  548. LOC_CREFERENCE :
  549. begin
  550. cg.g_concatcopy(exprasmlist,right.location.reference,
  551. left.location.reference,left.resulttype.def.size,true,false);
  552. { right.location is already released by concatcopy }
  553. releaseright:=false;
  554. end;
  555. else
  556. internalerror(200203284);
  557. end;
  558. end;
  559. {$ifdef SUPPORT_MMX}
  560. LOC_CMMXREGISTER,
  561. LOC_MMXREGISTER:
  562. begin
  563. if left.location.loc=LOC_CMMXREGISTER then
  564. cg.a_loadmm_reg_reg(exprasmlist,right.location.register,left.location.register)
  565. else
  566. cg.a_loadmm_reg_ref(exprasmlist,right.location.register,left.location.reference);
  567. end;
  568. {$endif SUPPORT_MMX}
  569. LOC_MMREGISTER,
  570. LOC_CMMREGISTER:
  571. begin
  572. if left.resulttype.def.deftype=arraydef then
  573. begin
  574. end
  575. else
  576. begin
  577. cgsize:=def_cgsize(left.resulttype.def);
  578. if left.location.loc=LOC_CMMREGISTER then
  579. cg.a_loadmm_reg_reg(exprasmlist,right.location.size,left.location.size,right.location.register,left.location.register,mms_movescalar)
  580. else
  581. cg.a_loadmm_reg_ref(exprasmlist,right.location.size,left.location.size,right.location.register,left.location.reference,mms_movescalar);
  582. end;
  583. end;
  584. LOC_REGISTER,
  585. LOC_CREGISTER :
  586. begin
  587. cgsize:=def_cgsize(left.resulttype.def);
  588. if cgsize in [OS_64,OS_S64] then
  589. cg64.a_load64_reg_loc(exprasmlist,
  590. right.location.register64,left.location)
  591. else
  592. cg.a_load_reg_loc(exprasmlist,right.location.size,right.location.register,left.location);
  593. end;
  594. LOC_FPUREGISTER,LOC_CFPUREGISTER :
  595. begin
  596. if (left.resulttype.def.deftype=floatdef) then
  597. fputyp:=tfloatdef(left.resulttype.def).typ
  598. else
  599. if (right.resulttype.def.deftype=floatdef) then
  600. fputyp:=tfloatdef(right.resulttype.def).typ
  601. else
  602. if (right.nodetype=typeconvn) and
  603. (ttypeconvnode(right).left.resulttype.def.deftype=floatdef) then
  604. fputyp:=tfloatdef(ttypeconvnode(right).left.resulttype.def).typ
  605. else
  606. fputyp:=s32real;
  607. cg.a_loadfpu_reg_loc(exprasmlist,
  608. tfloat2tcgsize[fputyp],
  609. right.location.register,left.location);
  610. end;
  611. LOC_JUMP :
  612. begin
  613. cgsize:=def_cgsize(left.resulttype.def);
  614. objectlibrary.getlabel(hlabel);
  615. { generate the leftnode for the true case, and
  616. release the location }
  617. cg.a_label(exprasmlist,truelabel);
  618. secondpass(left);
  619. if codegenerror then
  620. exit;
  621. cg.a_load_const_loc(exprasmlist,1,left.location);
  622. location_release(exprasmlist,left.location);
  623. cg.a_jmp_always(exprasmlist,hlabel);
  624. { generate the leftnode for the false case }
  625. cg.a_label(exprasmlist,falselabel);
  626. old_allow_multi_pass2:=allow_multi_pass2;
  627. allow_multi_pass2:=true;
  628. secondpass(left);
  629. allow_multi_pass2:=old_allow_multi_pass2;
  630. if codegenerror then
  631. exit;
  632. cg.a_load_const_loc(exprasmlist,0,left.location);
  633. cg.a_label(exprasmlist,hlabel);
  634. end;
  635. {$ifdef cpuflags}
  636. LOC_FLAGS :
  637. begin
  638. {This can be a wordbool or longbool too, no?}
  639. if left.location.loc=LOC_CREGISTER then
  640. cg.g_flags2reg(exprasmlist,def_cgsize(left.resulttype.def),right.location.resflags,left.location.register)
  641. else
  642. begin
  643. if not(left.location.loc = LOC_REFERENCE) then
  644. internalerror(200203273);
  645. cg.g_flags2ref(exprasmlist,def_cgsize(left.resulttype.def),right.location.resflags,left.location.reference);
  646. end;
  647. end;
  648. {$endif cpuflags}
  649. end;
  650. end;
  651. if releaseright then
  652. location_release(exprasmlist,right.location);
  653. location_release(exprasmlist,left.location);
  654. truelabel:=otlabel;
  655. falselabel:=oflabel;
  656. end;
  657. {*****************************************************************************
  658. SecondArrayConstruct
  659. *****************************************************************************}
  660. const
  661. vtInteger = 0;
  662. vtBoolean = 1;
  663. vtChar = 2;
  664. vtExtended = 3;
  665. vtString = 4;
  666. vtPointer = 5;
  667. vtPChar = 6;
  668. vtObject = 7;
  669. vtClass = 8;
  670. vtWideChar = 9;
  671. vtPWideChar = 10;
  672. vtAnsiString32 = 11;
  673. vtCurrency = 12;
  674. vtVariant = 13;
  675. vtInterface = 14;
  676. vtWideString = 15;
  677. vtInt64 = 16;
  678. vtQWord = 17;
  679. vtAnsiString16 = 18;
  680. vtAnsiString64 = 19;
  681. procedure tcgarrayconstructornode.pass_2;
  682. var
  683. hp : tarrayconstructornode;
  684. href : treference;
  685. lt : tdef;
  686. vaddr : boolean;
  687. vtype : longint;
  688. freetemp,
  689. dovariant : boolean;
  690. elesize : longint;
  691. tmpreg : tregister;
  692. paraloc : tparalocation;
  693. begin
  694. dovariant:=(nf_forcevaria in flags) or tarraydef(resulttype.def).isvariant;
  695. if dovariant then
  696. elesize:=8
  697. else
  698. elesize:=tarraydef(resulttype.def).elesize;
  699. location_reset(location,LOC_CREFERENCE,OS_NO);
  700. fillchar(paraloc,sizeof(paraloc),0);
  701. { Allocate always a temp, also if no elements are required, to
  702. be sure that location is valid (PFV) }
  703. if tarraydef(resulttype.def).highrange=-1 then
  704. tg.GetTemp(exprasmlist,elesize,tt_normal,location.reference)
  705. else
  706. tg.GetTemp(exprasmlist,(tarraydef(resulttype.def).highrange+1)*elesize,tt_normal,location.reference);
  707. href:=location.reference;
  708. { Process nodes in array constructor }
  709. hp:=self;
  710. while assigned(hp) do
  711. begin
  712. if assigned(hp.left) then
  713. begin
  714. freetemp:=true;
  715. secondpass(hp.left);
  716. if codegenerror then
  717. exit;
  718. { Move flags and jump in register }
  719. if hp.left.location.loc in [LOC_FLAGS,LOC_JUMP] then
  720. location_force_reg(exprasmlist,hp.left.location,def_cgsize(hp.left.resulttype.def),false);
  721. if dovariant then
  722. begin
  723. { find the correct vtype value }
  724. vtype:=$ff;
  725. vaddr:=false;
  726. lt:=hp.left.resulttype.def;
  727. case lt.deftype of
  728. enumdef,
  729. orddef :
  730. begin
  731. if is_64bit(lt) then
  732. begin
  733. case torddef(lt).typ of
  734. s64bit:
  735. vtype:=vtInt64;
  736. u64bit:
  737. vtype:=vtQWord;
  738. end;
  739. freetemp:=false;
  740. vaddr:=true;
  741. end
  742. else if (lt.deftype=enumdef) or
  743. is_integer(lt) then
  744. vtype:=vtInteger
  745. else
  746. if is_boolean(lt) then
  747. vtype:=vtBoolean
  748. else
  749. if (lt.deftype=orddef) then
  750. begin
  751. case torddef(lt).typ of
  752. uchar:
  753. vtype:=vtChar;
  754. uwidechar:
  755. vtype:=vtWideChar;
  756. end;
  757. end;
  758. end;
  759. floatdef :
  760. begin
  761. vtype:=vtExtended;
  762. freetemp:=false;
  763. vaddr:=true;
  764. end;
  765. procvardef,
  766. pointerdef :
  767. begin
  768. if is_pchar(lt) then
  769. vtype:=vtPChar
  770. else
  771. vtype:=vtPointer;
  772. end;
  773. variantdef :
  774. begin
  775. vtype:=vtVariant;
  776. vaddr:=true;
  777. freetemp:=false;
  778. end;
  779. classrefdef :
  780. vtype:=vtClass;
  781. objectdef :
  782. vtype:=vtObject;
  783. stringdef :
  784. begin
  785. if is_shortstring(lt) then
  786. begin
  787. vtype:=vtString;
  788. vaddr:=true;
  789. freetemp:=false;
  790. end
  791. else
  792. if is_ansistring(lt) then
  793. {$ifdef ansistring_bits}
  794. begin
  795. case Tstringdef(lt).string_typ of
  796. st_ansistring16:
  797. vtype:=vtAnsiString16;
  798. st_ansistring32:
  799. vtype:=vtAnsiString32;
  800. st_ansistring64:
  801. vtype:=vtAnsiString64;
  802. end;
  803. freetemp:=false;
  804. end
  805. {$else}
  806. begin
  807. vtype:=vtAnsiString;
  808. freetemp:=false;
  809. end
  810. {$endif}
  811. else
  812. if is_widestring(lt) then
  813. begin
  814. vtype:=vtWideString;
  815. freetemp:=false;
  816. end;
  817. end;
  818. end;
  819. if vtype=$ff then
  820. internalerror(14357);
  821. { write changing field update href to the next element }
  822. inc(href.offset,4);
  823. if vaddr then
  824. begin
  825. location_force_mem(exprasmlist,hp.left.location);
  826. location_release(exprasmlist,hp.left.location);
  827. tmpreg:=cg.getaddressregister(exprasmlist);
  828. cg.a_loadaddr_ref_reg(exprasmlist,hp.left.location.reference,tmpreg);
  829. cg.ungetregister(exprasmlist,tmpreg);
  830. cg.a_load_reg_ref(exprasmlist,OS_ADDR,OS_ADDR,tmpreg,href);
  831. if freetemp then
  832. location_freetemp(exprasmlist,hp.left.location);
  833. end
  834. else
  835. begin
  836. location_release(exprasmlist,hp.left.location);
  837. cg.a_load_loc_ref(exprasmlist,OS_ADDR,hp.left.location,href);
  838. end;
  839. { update href to the vtype field and write it }
  840. dec(href.offset,4);
  841. cg.a_load_const_ref(exprasmlist, OS_INT,vtype,href);
  842. { goto next array element }
  843. inc(href.offset,8);
  844. end
  845. else
  846. { normal array constructor of the same type }
  847. begin
  848. if is_ansistring(left.resulttype.def) or
  849. is_widestring(left.resulttype.def) or
  850. (left.resulttype.def.deftype=variantdef) then
  851. freetemp:=false;
  852. case hp.left.location.loc of
  853. LOC_FPUREGISTER,
  854. LOC_CFPUREGISTER :
  855. begin
  856. location_release(exprasmlist,hp.left.location);
  857. cg.a_loadfpu_reg_ref(exprasmlist,hp.left.location.size,hp.left.location.register,href);
  858. end;
  859. LOC_REFERENCE,
  860. LOC_CREFERENCE :
  861. begin
  862. location_release(exprasmlist,hp.left.location);
  863. if is_shortstring(hp.left.resulttype.def) then
  864. cg.g_copyshortstring(exprasmlist,hp.left.location.reference,href,
  865. Tstringdef(hp.left.resulttype.def).len,freetemp,false)
  866. else
  867. cg.g_concatcopy(exprasmlist,hp.left.location.reference,href,elesize,freetemp,false);
  868. end;
  869. else
  870. begin
  871. if hp.left.location.size in [OS_64,OS_S64] then
  872. begin
  873. cg64.a_load64_loc_ref(exprasmlist,hp.left.location,href);
  874. location_release(exprasmlist,hp.left.location);
  875. end
  876. else
  877. begin
  878. location_release(exprasmlist,hp.left.location);
  879. cg.a_load_loc_ref(exprasmlist,hp.left.location.size,hp.left.location,href);
  880. end;
  881. end;
  882. end;
  883. inc(href.offset,elesize);
  884. end;
  885. end;
  886. { load next entry }
  887. hp:=tarrayconstructornode(hp.right);
  888. end;
  889. end;
  890. begin
  891. cloadnode:=tcgloadnode;
  892. cassignmentnode:=tcgassignmentnode;
  893. carrayconstructornode:=tcgarrayconstructornode;
  894. end.
  895. {
  896. $Log$
  897. Revision 1.116 2004-05-22 23:34:28 peter
  898. tai_regalloc.allocation changed to ratype to notify rgobj of register size changes
  899. Revision 1.115 2004/04/29 19:56:37 daniel
  900. * Prepare compiler infrastructure for multiple ansistring types
  901. Revision 1.114 2004/03/02 17:32:12 florian
  902. * make cycle fixed
  903. + pic support for darwin
  904. + support of importing vars from shared libs on darwin implemented
  905. Revision 1.113 2004/03/02 00:36:33 olle
  906. * big transformation of Tai_[const_]Symbol.Create[data]name*
  907. Revision 1.112 2004/02/27 10:21:05 florian
  908. * top_symbol killed
  909. + refaddr to treference added
  910. + refsymbol to treference added
  911. * top_local stuff moved to an extra record to save memory
  912. + aint introduced
  913. * tppufile.get/putint64/aint implemented
  914. Revision 1.111 2004/02/22 16:48:09 florian
  915. * x86_64 uses generic concatcopy_valueopenarray for now
  916. Revision 1.110 2004/02/22 16:30:37 florian
  917. * fixed
  918. + second_cmpfloatsse
  919. Revision 1.109 2004/02/20 19:49:21 daniel
  920. * Message system uses open arrays internally
  921. * Bugfix for string handling in array constructor node
  922. * Micro code reductions in pdecl.pas
  923. Revision 1.108 2004/02/08 17:45:53 jonas
  924. * fixed regvars
  925. Revision 1.107 2004/02/05 01:24:08 florian
  926. * several fixes to compile x86-64 system
  927. Revision 1.106 2004/02/03 22:32:54 peter
  928. * renamed xNNbittype to xNNinttype
  929. * renamed registers32 to registersint
  930. * replace some s32bit,u32bit with torddef([su]inttype).def.typ
  931. Revision 1.105 2004/02/02 20:41:59 florian
  932. + added prefetch(const mem) support
  933. Revision 1.104 2003/12/25 01:07:09 florian
  934. + $fputype directive support
  935. + single data type operations with sse unit
  936. * fixed more x86-64 stuff
  937. Revision 1.103 2003/12/24 00:10:02 florian
  938. - delete parameter in cg64 methods removed
  939. Revision 1.102 2003/12/06 01:15:22 florian
  940. * reverted Peter's alloctemp patch; hopefully properly
  941. Revision 1.101 2003/12/03 23:13:20 peter
  942. * delayed paraloc allocation, a_param_*() gets extra parameter
  943. if it needs to allocate temp or real paralocation
  944. * optimized/simplified int-real loading
  945. Revision 1.100 2003/12/01 18:44:15 peter
  946. * fixed some crashes
  947. * fixed varargs and register calling probs
  948. Revision 1.99 2003/11/23 17:39:33 peter
  949. * removed obsolete nf_cargs flag
  950. Revision 1.98 2003/10/29 19:48:50 peter
  951. * renamed mangeldname_prefix to make_mangledname and made it more
  952. generic
  953. * make_mangledname is now also used for internal threadvar/resstring
  954. lists
  955. * Add P$ in front of program modulename to prevent duplicated symbols
  956. at assembler level, because the main program can have the same name
  957. as a unit, see webtbs/tw1251b
  958. Revision 1.97 2003/10/28 15:36:01 peter
  959. * absolute to object field supported, fixes tb0458
  960. Revision 1.96 2003/10/17 14:38:32 peter
  961. * 64k registers supported
  962. * fixed some memory leaks
  963. Revision 1.95 2003/10/14 00:30:48 florian
  964. + some code for PIC support added
  965. Revision 1.94 2003/10/11 16:06:42 florian
  966. * fixed some MMX<->SSE
  967. * started to fix ppc, needs an overhaul
  968. + stabs info improve for spilling, not sure if it works correctly/completly
  969. - MMX_SUPPORT removed from Makefile.fpc
  970. Revision 1.93 2003/10/10 17:48:13 peter
  971. * old trgobj moved to x86/rgcpu and renamed to trgx86fpu
  972. * tregisteralloctor renamed to trgobj
  973. * removed rgobj from a lot of units
  974. * moved location_* and reference_* to cgobj
  975. * first things for mmx register allocation
  976. Revision 1.92 2003/10/09 21:31:37 daniel
  977. * Register allocator splitted, ans abstract now
  978. Revision 1.91 2003/10/07 15:17:07 peter
  979. * inline supported again, LOC_REFERENCEs are used to pass the
  980. parameters
  981. * inlineparasymtable,inlinelocalsymtable removed
  982. * exitlabel inserting fixed
  983. Revision 1.90 2003/10/05 21:21:52 peter
  984. * c style array of const generates callparanodes
  985. * varargs paraloc fixes
  986. Revision 1.89 2003/10/01 20:34:48 peter
  987. * procinfo unit contains tprocinfo
  988. * cginfo renamed to cgbase
  989. * moved cgmessage to verbose
  990. * fixed ppc and sparc compiles
  991. Revision 1.88 2003/09/29 20:58:56 peter
  992. * optimized releasing of registers
  993. Revision 1.87 2003/09/28 21:46:18 peter
  994. * fix allocation of threadvar parameter
  995. Revision 1.86 2003/09/28 17:55:03 peter
  996. * parent framepointer changed to hidden parameter
  997. * tloadparentfpnode added
  998. Revision 1.85 2003/09/28 13:39:38 peter
  999. * optimized releasing of registers
  1000. Revision 1.84 2003/09/25 21:27:31 peter
  1001. * rearranged threadvar code so the result register is the same
  1002. for the relocated and address loaded variables
  1003. Revision 1.83 2003/09/23 17:56:05 peter
  1004. * locals and paras are allocated in the code generation
  1005. * tvarsym.localloc contains the location of para/local when
  1006. generating code for the current procedure
  1007. Revision 1.82 2003/09/16 16:17:01 peter
  1008. * varspez in calls to push_addr_param
  1009. Revision 1.81 2003/09/14 12:57:10 peter
  1010. * save destroyed registers when calling threadvar helper
  1011. Revision 1.80 2003/09/10 08:31:47 marco
  1012. * Patch from Peter for paraloc
  1013. Revision 1.79 2003/09/03 15:55:00 peter
  1014. * NEWRA branch merged
  1015. Revision 1.78 2003/09/03 11:18:37 florian
  1016. * fixed arm concatcopy
  1017. + arm support in the common compiler sources added
  1018. * moved some generic cg code around
  1019. + tfputype added
  1020. * ...
  1021. Revision 1.77.2.2 2003/08/31 15:46:26 peter
  1022. * more updates for tregister
  1023. Revision 1.77.2.1 2003/08/29 17:28:59 peter
  1024. * next batch of updates
  1025. Revision 1.77 2003/08/20 20:13:08 daniel
  1026. * Fixed the fixed trouble
  1027. Revision 1.76 2003/08/20 20:11:24 daniel
  1028. * Fixed some R_NO trouble
  1029. Revision 1.75 2003/07/20 16:26:43 jonas
  1030. * fix for threadvars with -dnewra
  1031. Revision 1.74 2003/07/06 17:58:22 peter
  1032. * framepointer fixes for sparc
  1033. * parent framepointer code more generic
  1034. Revision 1.73 2003/07/06 15:25:54 jonas
  1035. * newra fix for threadvars
  1036. Revision 1.72 2003/06/15 15:13:12 jonas
  1037. * fixed register allocation for threadvar loads with newra
  1038. Revision 1.71 2003/06/13 21:19:30 peter
  1039. * current_procdef removed, use current_procinfo.procdef instead
  1040. Revision 1.70 2003/06/12 16:43:07 peter
  1041. * newra compiles for sparc
  1042. Revision 1.69 2003/06/09 16:41:52 jonas
  1043. * fixed regvar optimization for call_by_reference parameters (no need
  1044. to load address in another register)
  1045. Revision 1.68 2003/06/08 18:27:15 jonas
  1046. + ability to change the location of a ttempref node with changelocation()
  1047. method. Useful to use instead of copying the contents from one temp to
  1048. another
  1049. + some shortstring optimizations in tassignmentnode that avoid some
  1050. copying (required some shortstring optimizations to be moved from
  1051. resulttype to firstpass, because they work on callnodes and string
  1052. addnodes are only changed to callnodes in the firstpass)
  1053. * allow setting/changing the funcretnode of callnodes after the
  1054. resulttypepass has been done, funcretnode is now a property
  1055. (all of the above should have a quite big effect on callparatemp)
  1056. Revision 1.67 2003/06/07 18:57:04 jonas
  1057. + added freeintparaloc
  1058. * ppc get/freeintparaloc now check whether the parameter regs are
  1059. properly allocated/deallocated (and get an extra list para)
  1060. * ppc a_call_* now internalerrors if pi_do_call is not yet set
  1061. * fixed lot of missing pi_do_call's
  1062. Revision 1.66 2003/06/03 21:11:09 peter
  1063. * cg.a_load_* get a from and to size specifier
  1064. * makeregsize only accepts newregister
  1065. * i386 uses generic tcgnotnode,tcgunaryminus
  1066. Revision 1.65 2003/06/03 13:01:59 daniel
  1067. * Register allocator finished
  1068. Revision 1.64 2003/05/30 23:57:08 peter
  1069. * more sparc cleanup
  1070. * accumulator removed, splitted in function_return_reg (called) and
  1071. function_result_reg (caller)
  1072. Revision 1.63 2003/05/30 23:54:08 jonas
  1073. * forgot to commit, a_load_loc_reg change
  1074. Revision 1.62 2003/05/26 19:38:28 peter
  1075. * generic fpc_shorstr_concat
  1076. + fpc_shortstr_append_shortstr optimization
  1077. Revision 1.61 2003/05/24 11:47:27 jonas
  1078. * fixed framepointer storage: it's now always stored at r1+12, which is
  1079. a place in the link area reserved for compiler use.
  1080. Revision 1.60 2003/05/23 14:27:35 peter
  1081. * remove some unit dependencies
  1082. * current_procinfo changes to store more info
  1083. Revision 1.59 2003/05/15 18:58:53 peter
  1084. * removed selfpointer_offset, vmtpointer_offset
  1085. * tvarsym.adjusted_address
  1086. * address in localsymtable is now in the real direction
  1087. * removed some obsolete globals
  1088. Revision 1.58 2003/05/12 17:22:00 jonas
  1089. * fixed (last?) remaining -tvarsym(X).address to
  1090. tg.direction*tvarsym(X).address...
  1091. Revision 1.57 2003/05/11 21:37:03 peter
  1092. * moved implicit exception frame from ncgutil to psub
  1093. * constructor/destructor helpers moved from cobj/ncgutil to psub
  1094. Revision 1.56 2003/05/11 14:45:12 peter
  1095. * tloadnode does not support objectsymtable,withsymtable anymore
  1096. * withnode cleanup
  1097. * direct with rewritten to use temprefnode
  1098. Revision 1.55 2003/04/29 07:29:14 michael
  1099. + Patch from peter to fix wrong pushing of ansistring function results in open array
  1100. Revision 1.54 2003/04/27 11:21:33 peter
  1101. * aktprocdef renamed to current_procinfo.procdef
  1102. * procinfo renamed to current_procinfo
  1103. * procinfo will now be stored in current_module so it can be
  1104. cleaned up properly
  1105. * gen_main_procsym changed to create_main_proc and release_main_proc
  1106. to also generate a tprocinfo structure
  1107. * fixed unit implicit initfinal
  1108. Revision 1.53 2003/04/27 07:29:50 peter
  1109. * current_procinfo.procdef cleanup, current_procdef is now always nil when parsing
  1110. a new procdef declaration
  1111. * aktprocsym removed
  1112. * lexlevel removed, use symtable.symtablelevel instead
  1113. * implicit init/final code uses the normal genentry/genexit
  1114. * funcret state checking updated for new funcret handling
  1115. Revision 1.52 2003/04/25 20:59:33 peter
  1116. * removed funcretn,funcretsym, function result is now in varsym
  1117. and aliases for result and function name are added using absolutesym
  1118. * vs_hidden parameter for funcret passed in parameter
  1119. * vs_hidden fixes
  1120. * writenode changed to printnode and released from extdebug
  1121. * -vp option added to generate a tree.log with the nodetree
  1122. * nicer printnode for statements, callnode
  1123. Revision 1.51 2003/04/23 20:16:04 peter
  1124. + added currency support based on int64
  1125. + is_64bit for use in cg units instead of is_64bitint
  1126. * removed cgmessage from n386add, replace with internalerrors
  1127. Revision 1.50 2003/04/23 10:12:14 peter
  1128. * allow multi pass2 changed to global boolean instead of node flag
  1129. Revision 1.49 2003/04/22 23:50:22 peter
  1130. * firstpass uses expectloc
  1131. * checks if there are differences between the expectloc and
  1132. location.loc from secondpass in EXTDEBUG
  1133. Revision 1.48 2003/04/22 10:09:35 daniel
  1134. + Implemented the actual register allocator
  1135. + Scratch registers unavailable when new register allocator used
  1136. + maybe_save/maybe_restore unavailable when new register allocator used
  1137. Revision 1.47 2003/04/06 21:11:23 olle
  1138. * changed newasmsymbol to newasmsymboldata for data symbols
  1139. Revision 1.46 2003/03/28 19:16:56 peter
  1140. * generic constructor working for i386
  1141. * remove fixed self register
  1142. * esi added as address register for i386
  1143. Revision 1.45 2003/02/19 22:00:14 daniel
  1144. * Code generator converted to new register notation
  1145. - Horribily outdated todo.txt removed
  1146. Revision 1.44 2003/01/08 18:43:56 daniel
  1147. * Tregister changed into a record
  1148. Revision 1.43 2003/01/05 22:44:14 peter
  1149. * remove a lot of code to support typen in loadn-procsym
  1150. Revision 1.42 2002/12/20 18:13:46 peter
  1151. * fixes for fpu values in arrayconstructor
  1152. Revision 1.41 2002/11/27 20:04:39 peter
  1153. * cdecl array of const fixes
  1154. Revision 1.40 2002/11/25 17:43:18 peter
  1155. * splitted defbase in defutil,symutil,defcmp
  1156. * merged isconvertable and is_equal into compare_defs(_ext)
  1157. * made operator search faster by walking the list only once
  1158. Revision 1.39 2002/11/22 16:22:45 jonas
  1159. * fixed error in my previous commit (the size of the location of the
  1160. funcretnode must be based on the current resulttype of the node and not
  1161. the resulttype defined by the function; these can be different in case
  1162. of "absolute" declarations)
  1163. Revision 1.38 2002/11/18 17:31:54 peter
  1164. * pass proccalloption to ret_in_xxx and push_xxx functions
  1165. Revision 1.37 2002/11/15 21:16:39 jonas
  1166. * proper fix for tw2110, also fixes tb0416 (funcretnode of parent
  1167. function was handled wrong inside nested functions/procedures)
  1168. Revision 1.36 2002/11/15 01:58:51 peter
  1169. * merged changes from 1.0.7 up to 04-11
  1170. - -V option for generating bug report tracing
  1171. - more tracing for option parsing
  1172. - errors for cdecl and high()
  1173. - win32 import stabs
  1174. - win32 records<=8 are returned in eax:edx (turned off by default)
  1175. - heaptrc update
  1176. - more info for temp management in .s file with EXTDEBUG
  1177. Revision 1.35 2002/10/14 19:44:13 peter
  1178. * (hacked) new threadvar relocate code
  1179. Revision 1.34 2002/10/13 11:22:06 florian
  1180. * fixed threadvars
  1181. Revision 1.33 2002/10/03 21:32:02 carl
  1182. * bugfix for 2110 (without -Or), wrong checking was done in returntype
  1183. Revision 1.32 2002/09/30 07:00:46 florian
  1184. * fixes to common code to get the alpha compiler compiled applied
  1185. Revision 1.31 2002/09/26 15:02:05 florian
  1186. + support of passing variants to "array of const"
  1187. Revision 1.30 2002/09/17 18:54:02 jonas
  1188. * a_load_reg_reg() now has two size parameters: source and dest. This
  1189. allows some optimizations on architectures that don't encode the
  1190. register size in the register name.
  1191. Revision 1.29 2002/09/07 15:25:03 peter
  1192. * old logs removed and tabs fixed
  1193. Revision 1.28 2002/09/01 19:26:32 peter
  1194. * fixed register variable loading from parasymtable, the call by
  1195. reference code was moved wrong
  1196. Revision 1.27 2002/09/01 12:15:40 peter
  1197. * fixed loading of procvar of object when the object is initialized
  1198. with 0
  1199. Revision 1.26 2002/08/25 19:25:18 peter
  1200. * sym.insert_in_data removed
  1201. * symtable.insertvardata/insertconstdata added
  1202. * removed insert_in_data call from symtable.insert, it needs to be
  1203. called separatly. This allows to deref the address calculation
  1204. * procedures now calculate the parast addresses after the procedure
  1205. directives are parsed. This fixes the cdecl parast problem
  1206. * push_addr_param has an extra argument that specifies if cdecl is used
  1207. or not
  1208. Revision 1.25 2002/08/23 16:14:48 peter
  1209. * tempgen cleanup
  1210. * tt_noreuse temp type added that will be used in genentrycode
  1211. Revision 1.24 2002/08/17 09:23:35 florian
  1212. * first part of procinfo rewrite
  1213. Revision 1.23 2002/08/14 18:13:28 jonas
  1214. * adapted previous fix to Peter's asmsymbol patch
  1215. Revision 1.22 2002/08/14 18:00:42 jonas
  1216. * fixed tb0403
  1217. Revision 1.21 2002/08/13 21:40:56 florian
  1218. * more fixes for ppc calling conventions
  1219. Revision 1.20 2002/08/11 14:32:26 peter
  1220. * renamed current_library to objectlibrary
  1221. Revision 1.19 2002/08/11 13:24:12 peter
  1222. * saving of asmsymbols in ppu supported
  1223. * asmsymbollist global is removed and moved into a new class
  1224. tasmlibrarydata that will hold the info of a .a file which
  1225. corresponds with a single module. Added librarydata to tmodule
  1226. to keep the library info stored for the module. In the future the
  1227. objectfiles will also be stored to the tasmlibrarydata class
  1228. * all getlabel/newasmsymbol and friends are moved to the new class
  1229. Revision 1.18 2002/08/06 20:55:21 florian
  1230. * first part of ppc calling conventions fix
  1231. Revision 1.17 2002/07/28 09:25:37 carl
  1232. + correct size of parameter (64-bit portability)
  1233. Revision 1.16 2002/07/27 19:53:51 jonas
  1234. + generic implementation of tcg.g_flags2ref()
  1235. * tcg.flags2xxx() now also needs a size parameter
  1236. Revision 1.15 2002/07/20 11:57:54 florian
  1237. * types.pas renamed to defbase.pas because D6 contains a types
  1238. unit so this would conflicts if D6 programms are compiled
  1239. + Willamette/SSE2 instructions to assembler added
  1240. Revision 1.14 2002/07/16 09:17:44 florian
  1241. * threadvar relocation result wasn't handled properly, it could cause
  1242. a crash
  1243. Revision 1.13 2002/07/11 14:41:28 florian
  1244. * start of the new generic parameter handling
  1245. Revision 1.12 2002/07/07 09:52:32 florian
  1246. * powerpc target fixed, very simple units can be compiled
  1247. * some basic stuff for better callparanode handling, far from being finished
  1248. Revision 1.11 2002/07/01 18:46:23 peter
  1249. * internal linker
  1250. * reorganized aasm layer
  1251. Revision 1.10 2002/07/01 16:23:53 peter
  1252. * cg64 patch
  1253. * basics for currency
  1254. * asnode updates for class and interface (not finished)
  1255. Revision 1.9 2002/05/20 13:30:40 carl
  1256. * bugfix of hdisponen (base must be set, not index)
  1257. * more portability fixes
  1258. }