symtype.pas 41 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506
  1. {
  2. $Id$
  3. Copyright (c) 1998-2002 by Florian Klaempfl, Pierre Muller
  4. This unit handles the symbol tables
  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 symtype;
  19. {$i fpcdefs.inc}
  20. interface
  21. uses
  22. { common }
  23. cutils,
  24. {$ifdef MEMDEBUG}
  25. cclasses,
  26. {$endif MEMDEBUG}
  27. { global }
  28. globtype,globals,
  29. { symtable }
  30. symconst,symbase,
  31. { aasm }
  32. aasmbase,ppu,cpuinfo
  33. ;
  34. type
  35. {************************************************
  36. Required Forwards
  37. ************************************************}
  38. tsym = class;
  39. Tcompilerppufile=class;
  40. {************************************************
  41. TRef
  42. ************************************************}
  43. tref = class
  44. nextref : tref;
  45. posinfo : tfileposinfo;
  46. moduleindex : longint;
  47. is_written : boolean;
  48. constructor create(ref:tref;pos:pfileposinfo);
  49. procedure freechain;
  50. destructor destroy;override;
  51. end;
  52. {************************************************
  53. TDef
  54. ************************************************}
  55. tgetsymtable = (gs_none,gs_record,gs_local,gs_para);
  56. tdef = class(tdefentry)
  57. typesym : tsym; { which type the definition was generated this def }
  58. defoptions : tdefoptions;
  59. constructor create;
  60. procedure buildderef;virtual;abstract;
  61. procedure buildderefimpl;virtual;abstract;
  62. procedure deref;virtual;abstract;
  63. procedure derefimpl;virtual;abstract;
  64. function typename:string;
  65. function gettypename:string;virtual;
  66. function mangledparaname:string;
  67. function getmangledparaname:string;virtual;
  68. function size:aint;virtual;abstract;
  69. function alignment:longint;virtual;abstract;
  70. function getparentdef:tdef;virtual;
  71. function getsymtable(t:tgetsymtable):tsymtable;virtual;
  72. function is_publishable:boolean;virtual;abstract;
  73. function needs_inittable:boolean;virtual;abstract;
  74. end;
  75. {************************************************
  76. TSym
  77. ************************************************}
  78. { this object is the base for all symbol objects }
  79. tsym = class(tsymentry)
  80. protected
  81. public
  82. _realname : pstring;
  83. fileinfo : tfileposinfo;
  84. symoptions : tsymoptions;
  85. refs : longint;
  86. lastref,
  87. defref,
  88. lastwritten : tref;
  89. refcount : longint;
  90. {$ifdef GDB}
  91. isstabwritten : boolean;
  92. function get_var_value(const s:string):string;
  93. function stabstr_evaluate(const s:string;vars:array of string):Pchar;
  94. function stabstring : pchar;virtual;
  95. {$endif GDB}
  96. constructor create(const n : string);
  97. destructor destroy;override;
  98. function realname:string;
  99. procedure buildderef;virtual;
  100. procedure deref;virtual;
  101. function gettypedef:tdef;virtual;
  102. procedure load_references(ppufile:tcompilerppufile;locals:boolean);virtual;
  103. function write_references(ppufile:tcompilerppufile;locals:boolean):boolean;virtual;
  104. function is_visible_for_object(currobjdef:Tdef):boolean;virtual;
  105. end;
  106. tsymarr = array[0..maxlongint div sizeof(pointer)-1] of tsym;
  107. psymarr = ^tsymarr;
  108. {************************************************
  109. TDeref
  110. ************************************************}
  111. tderef = object
  112. dataidx : longint;
  113. procedure reset;
  114. procedure build(s:tsymtableentry);
  115. function resolve:tsymtableentry;
  116. end;
  117. {************************************************
  118. TType
  119. ************************************************}
  120. ttype = object
  121. def : tdef;
  122. sym : tsym;
  123. deref : tderef;
  124. procedure reset;
  125. procedure setdef(p:tdef);
  126. procedure setsym(p:tsym);
  127. procedure resolve;
  128. procedure buildderef;
  129. end;
  130. {************************************************
  131. TSymList
  132. ************************************************}
  133. psymlistitem = ^tsymlistitem;
  134. tsymlistitem = record
  135. sltype : tsltype;
  136. next : psymlistitem;
  137. case byte of
  138. 0 : (sym : tsym; symderef : tderef);
  139. 1 : (value : TConstExprInt);
  140. 2 : (tt : ttype);
  141. end;
  142. tsymlist = class
  143. procdef : tdef;
  144. procdefderef : tderef;
  145. firstsym,
  146. lastsym : psymlistitem;
  147. constructor create;
  148. destructor destroy;override;
  149. function empty:boolean;
  150. procedure addsym(slt:tsltype;p:tsym);
  151. procedure addsymderef(slt:tsltype;const d:tderef);
  152. procedure addconst(slt:tsltype;v:TConstExprInt);
  153. procedure addtype(slt:tsltype;const tt:ttype);
  154. procedure clear;
  155. function getcopy:tsymlist;
  156. procedure resolve;
  157. procedure buildderef;
  158. end;
  159. {************************************************
  160. Tcompilerppufile
  161. ************************************************}
  162. tcompilerppufile=class(tppufile)
  163. public
  164. procedure checkerror;
  165. procedure getguid(var g: tguid);
  166. function getexprint:tconstexprint;
  167. function getptruint:TConstPtrUInt;
  168. procedure getposinfo(var p:tfileposinfo);
  169. procedure getderef(var d:tderef);
  170. function getsymlist:tsymlist;
  171. procedure gettype(var t:ttype);
  172. function getasmsymbol:tasmsymbol;
  173. procedure putguid(const g: tguid);
  174. procedure putexprint(v:tconstexprint);
  175. procedure PutPtrUInt(v:TConstPtrUInt);
  176. procedure putposinfo(const p:tfileposinfo);
  177. procedure putderef(const d:tderef);
  178. procedure putsymlist(p:tsymlist);
  179. procedure puttype(const t:ttype);
  180. procedure putasmsymbol(s:tasmsymbol);
  181. end;
  182. {$ifdef MEMDEBUG}
  183. var
  184. membrowser,
  185. memrealnames,
  186. memmanglednames,
  187. memprocpara,
  188. memprocparast,
  189. memproclocalst,
  190. memprocnodetree : tmemdebug;
  191. {$endif MEMDEBUG}
  192. const
  193. current_object_option : tsymoptions = [sp_public];
  194. implementation
  195. uses
  196. verbose,
  197. fmodule
  198. // symdef
  199. {$ifdef GDB}
  200. ,gdb
  201. {$endif GDB}
  202. ;
  203. {****************************************************************************
  204. Tdef
  205. ****************************************************************************}
  206. constructor tdef.create;
  207. begin
  208. inherited create;
  209. deftype:=abstractdef;
  210. owner := nil;
  211. typesym := nil;
  212. defoptions:=[];
  213. end;
  214. function tdef.typename:string;
  215. begin
  216. if assigned(typesym) and
  217. not(deftype in [procvardef,procdef]) and
  218. assigned(typesym._realname) and
  219. (typesym._realname^[1]<>'$') then
  220. typename:=typesym._realname^
  221. else
  222. typename:=gettypename;
  223. end;
  224. function tdef.gettypename : string;
  225. begin
  226. gettypename:='<unknown type>'
  227. end;
  228. function tdef.mangledparaname:string;
  229. begin
  230. if assigned(typesym) then
  231. mangledparaname:=typesym.name
  232. else
  233. mangledparaname:=getmangledparaname;
  234. end;
  235. function tdef.getmangledparaname:string;
  236. begin
  237. result:='<unknown type>';
  238. end;
  239. function tdef.getparentdef:tdef;
  240. begin
  241. result:=nil;
  242. end;
  243. function tdef.getsymtable(t:tgetsymtable):tsymtable;
  244. begin
  245. getsymtable:=nil;
  246. end;
  247. {****************************************************************************
  248. TSYM (base for all symtypes)
  249. ****************************************************************************}
  250. constructor tsym.create(const n : string);
  251. begin
  252. if n[1]='$' then
  253. inherited createname(copy(n,2,255))
  254. else
  255. inherited createname(upper(n));
  256. _realname:=stringdup(n);
  257. typ:=abstractsym;
  258. symoptions:=[];
  259. defref:=nil;
  260. refs:=0;
  261. lastwritten:=nil;
  262. refcount:=0;
  263. fileinfo:=akttokenpos;
  264. if (cs_browser in aktmoduleswitches) and make_ref then
  265. begin
  266. defref:=tref.create(defref,@akttokenpos);
  267. inc(refcount);
  268. end;
  269. lastref:=defref;
  270. {$ifdef GDB}
  271. isstabwritten := false;
  272. {$endif GDB}
  273. symoptions:=current_object_option;
  274. end;
  275. destructor tsym.destroy;
  276. begin
  277. {$ifdef MEMDEBUG}
  278. memrealnames.start;
  279. {$endif MEMDEBUG}
  280. stringdispose(_realname);
  281. {$ifdef MEMDEBUG}
  282. memrealnames.stop;
  283. {$endif MEMDEBUG}
  284. inherited destroy;
  285. end;
  286. procedure Tsym.buildderef;
  287. begin
  288. end;
  289. procedure Tsym.deref;
  290. begin
  291. end;
  292. {$ifdef GDB}
  293. function Tsym.get_var_value(const s:string):string;
  294. begin
  295. if s='name' then
  296. get_var_value:=name
  297. else if s='ownername' then
  298. get_var_value:=owner.name^
  299. else if s='line' then
  300. get_var_value:=tostr(fileinfo.line)
  301. else if s='N_LSYM' then
  302. get_var_value:=tostr(N_LSYM)
  303. else if s='N_LCSYM' then
  304. get_var_value:=tostr(N_LCSYM)
  305. else if s='N_RSYM' then
  306. get_var_value:=tostr(N_RSYM)
  307. else if s='N_TSYM' then
  308. get_var_value:=tostr(N_TSYM)
  309. else if s='N_STSYM' then
  310. get_var_value:=tostr(N_STSYM)
  311. else if s='N_FUNCTION' then
  312. get_var_value:=tostr(N_FUNCTION)
  313. else
  314. internalerror(200401152);
  315. end;
  316. function Tsym.stabstr_evaluate(const s:string;vars:array of string):Pchar;
  317. begin
  318. stabstr_evaluate:=string_evaluate(s,@get_var_value,vars);
  319. end;
  320. function Tsym.stabstring : pchar;
  321. begin
  322. stabstring:=nil;
  323. end;
  324. {$endif GDB}
  325. function tsym.realname : string;
  326. begin
  327. if assigned(_realname) then
  328. realname:=_realname^
  329. else
  330. realname:=name;
  331. end;
  332. function tsym.gettypedef:tdef;
  333. begin
  334. gettypedef:=nil;
  335. end;
  336. procedure Tsym.load_references(ppufile:tcompilerppufile;locals:boolean);
  337. var
  338. pos : tfileposinfo;
  339. move_last : boolean;
  340. begin
  341. move_last:=lastwritten=lastref;
  342. while (not ppufile.endofentry) do
  343. begin
  344. ppufile.getposinfo(pos);
  345. inc(refcount);
  346. lastref:=tref.create(lastref,@pos);
  347. lastref.is_written:=true;
  348. if refcount=1 then
  349. defref:=lastref;
  350. end;
  351. if move_last then
  352. lastwritten:=lastref;
  353. end;
  354. { big problem here :
  355. wrong refs were written because of
  356. interface parsing of other units PM
  357. moduleindex must be checked !! }
  358. function Tsym.write_references(ppufile:tcompilerppufile;locals:boolean):boolean;
  359. var
  360. d : tderef;
  361. ref : tref;
  362. symref_written,move_last : boolean;
  363. begin
  364. write_references:=false;
  365. if lastwritten=lastref then
  366. exit;
  367. { should we update lastref }
  368. move_last:=true;
  369. symref_written:=false;
  370. { write symbol refs }
  371. d.reset;
  372. if assigned(lastwritten) then
  373. ref:=lastwritten
  374. else
  375. ref:=defref;
  376. while assigned(ref) do
  377. begin
  378. if ref.moduleindex=current_module.unit_index then
  379. begin
  380. { write address to this symbol }
  381. if not symref_written then
  382. begin
  383. d.build(self);
  384. ppufile.putderef(d);
  385. symref_written:=true;
  386. end;
  387. ppufile.putposinfo(ref.posinfo);
  388. ref.is_written:=true;
  389. if move_last then
  390. lastwritten:=ref;
  391. end
  392. else if not ref.is_written then
  393. move_last:=false
  394. else if move_last then
  395. lastwritten:=ref;
  396. ref:=ref.nextref;
  397. end;
  398. if symref_written then
  399. ppufile.writeentry(ibsymref);
  400. write_references:=symref_written;
  401. end;
  402. function Tsym.is_visible_for_object(currobjdef:Tdef):boolean;
  403. begin
  404. is_visible_for_object:=false;
  405. { private symbols are allowed when we are in the same
  406. module as they are defined }
  407. if (sp_private in symoptions) and
  408. assigned(owner.defowner) and
  409. (owner.defowner.owner.symtabletype in [globalsymtable,staticsymtable]) and
  410. (owner.defowner.owner.unitid<>0) then
  411. exit;
  412. { protected symbols are vissible in the module that defines them and
  413. also visible to related objects }
  414. if (sp_protected in symoptions) and
  415. (
  416. (
  417. assigned(owner.defowner) and
  418. (owner.defowner.owner.symtabletype in [globalsymtable,staticsymtable]) and
  419. (owner.defowner.owner.unitid<>0)
  420. ) and
  421. not(
  422. assigned(currobjdef) {and
  423. Tobjectdef(currobjdef).is_related(tobjectdef(owner.defowner))}
  424. )
  425. ) then
  426. exit;
  427. is_visible_for_object:=true;
  428. end;
  429. {****************************************************************************
  430. TRef
  431. ****************************************************************************}
  432. constructor tref.create(ref :tref;pos : pfileposinfo);
  433. begin
  434. nextref:=nil;
  435. if pos<>nil then
  436. posinfo:=pos^;
  437. if assigned(current_module) then
  438. moduleindex:=current_module.unit_index;
  439. if assigned(ref) then
  440. ref.nextref:=self;
  441. is_written:=false;
  442. end;
  443. procedure tref.freechain;
  444. var
  445. p,q : tref;
  446. begin
  447. p:=nextref;
  448. nextref:=nil;
  449. while assigned(p) do
  450. begin
  451. q:=p.nextref;
  452. p.free;
  453. p:=q;
  454. end;
  455. end;
  456. destructor tref.destroy;
  457. begin
  458. nextref:=nil;
  459. end;
  460. {****************************************************************************
  461. TType
  462. ****************************************************************************}
  463. procedure ttype.reset;
  464. begin
  465. def:=nil;
  466. sym:=nil;
  467. end;
  468. procedure ttype.setdef(p:tdef);
  469. begin
  470. def:=p;
  471. sym:=nil;
  472. end;
  473. procedure ttype.setsym(p:tsym);
  474. begin
  475. sym:=p;
  476. def:=p.gettypedef;
  477. if not assigned(def) then
  478. internalerror(1234005);
  479. end;
  480. procedure ttype.resolve;
  481. var
  482. p : tsymtableentry;
  483. begin
  484. p:=deref.resolve;
  485. if assigned(p) then
  486. begin
  487. if p is tsym then
  488. begin
  489. setsym(tsym(p));
  490. if not assigned(def) then
  491. internalerror(200212272);
  492. end
  493. else
  494. begin
  495. setdef(tdef(p));
  496. end;
  497. end
  498. else
  499. reset;
  500. end;
  501. procedure ttype.buildderef;
  502. begin
  503. { Write symbol references when the symbol is a redefine,
  504. but don't write symbol references for the current unit
  505. and for the system unit }
  506. if assigned(sym) and
  507. (
  508. (sym<>def.typesym) or
  509. ((sym.owner.unitid<>0) and
  510. (sym.owner.unitid<>1))
  511. ) then
  512. deref.build(sym)
  513. else
  514. deref.build(def);
  515. end;
  516. {****************************************************************************
  517. TSymList
  518. ****************************************************************************}
  519. constructor tsymlist.create;
  520. begin
  521. procdef:=nil; { needed for procedures }
  522. firstsym:=nil;
  523. lastsym:=nil;
  524. end;
  525. destructor tsymlist.destroy;
  526. begin
  527. clear;
  528. end;
  529. function tsymlist.empty:boolean;
  530. begin
  531. empty:=(firstsym=nil);
  532. end;
  533. procedure tsymlist.clear;
  534. var
  535. hp : psymlistitem;
  536. begin
  537. while assigned(firstsym) do
  538. begin
  539. hp:=firstsym;
  540. firstsym:=firstsym^.next;
  541. dispose(hp);
  542. end;
  543. firstsym:=nil;
  544. lastsym:=nil;
  545. procdef:=nil;
  546. end;
  547. procedure tsymlist.addsym(slt:tsltype;p:tsym);
  548. var
  549. hp : psymlistitem;
  550. begin
  551. if not assigned(p) then
  552. internalerror(200110203);
  553. new(hp);
  554. fillchar(hp^,sizeof(tsymlistitem),0);
  555. hp^.sltype:=slt;
  556. hp^.sym:=p;
  557. hp^.symderef.reset;
  558. if assigned(lastsym) then
  559. lastsym^.next:=hp
  560. else
  561. firstsym:=hp;
  562. lastsym:=hp;
  563. end;
  564. procedure tsymlist.addsymderef(slt:tsltype;const d:tderef);
  565. var
  566. hp : psymlistitem;
  567. begin
  568. new(hp);
  569. fillchar(hp^,sizeof(tsymlistitem),0);
  570. hp^.sltype:=slt;
  571. hp^.symderef:=d;
  572. if assigned(lastsym) then
  573. lastsym^.next:=hp
  574. else
  575. firstsym:=hp;
  576. lastsym:=hp;
  577. end;
  578. procedure tsymlist.addconst(slt:tsltype;v:TConstExprInt);
  579. var
  580. hp : psymlistitem;
  581. begin
  582. new(hp);
  583. fillchar(hp^,sizeof(tsymlistitem),0);
  584. hp^.sltype:=slt;
  585. hp^.value:=v;
  586. if assigned(lastsym) then
  587. lastsym^.next:=hp
  588. else
  589. firstsym:=hp;
  590. lastsym:=hp;
  591. end;
  592. procedure tsymlist.addtype(slt:tsltype;const tt:ttype);
  593. var
  594. hp : psymlistitem;
  595. begin
  596. new(hp);
  597. fillchar(hp^,sizeof(tsymlistitem),0);
  598. hp^.sltype:=slt;
  599. hp^.tt:=tt;
  600. if assigned(lastsym) then
  601. lastsym^.next:=hp
  602. else
  603. firstsym:=hp;
  604. lastsym:=hp;
  605. end;
  606. function tsymlist.getcopy:tsymlist;
  607. var
  608. hp : tsymlist;
  609. hp2 : psymlistitem;
  610. hpn : psymlistitem;
  611. begin
  612. hp:=tsymlist.create;
  613. hp.procdef:=procdef;
  614. hp2:=firstsym;
  615. while assigned(hp2) do
  616. begin
  617. new(hpn);
  618. hpn^:=hp2^;
  619. hpn^.next:=nil;
  620. if assigned(hp.lastsym) then
  621. hp.lastsym^.next:=hpn
  622. else
  623. hp.firstsym:=hpn;
  624. hp.lastsym:=hpn;
  625. hp2:=hp2^.next;
  626. end;
  627. getcopy:=hp;
  628. end;
  629. procedure tsymlist.resolve;
  630. var
  631. hp : psymlistitem;
  632. begin
  633. procdef:=tdef(procdefderef.resolve);
  634. hp:=firstsym;
  635. while assigned(hp) do
  636. begin
  637. case hp^.sltype of
  638. sl_call,
  639. sl_load,
  640. sl_subscript :
  641. hp^.sym:=tsym(hp^.symderef.resolve);
  642. sl_typeconv :
  643. hp^.tt.resolve;
  644. sl_vec :
  645. ;
  646. else
  647. internalerror(200110205);
  648. end;
  649. hp:=hp^.next;
  650. end;
  651. end;
  652. procedure tsymlist.buildderef;
  653. var
  654. hp : psymlistitem;
  655. begin
  656. procdefderef.build(procdef);
  657. hp:=firstsym;
  658. while assigned(hp) do
  659. begin
  660. case hp^.sltype of
  661. sl_call,
  662. sl_load,
  663. sl_subscript :
  664. hp^.symderef.build(hp^.sym);
  665. sl_typeconv :
  666. hp^.tt.buildderef;
  667. sl_vec :
  668. ;
  669. else
  670. internalerror(200110205);
  671. end;
  672. hp:=hp^.next;
  673. end;
  674. end;
  675. {****************************************************************************
  676. Tderef
  677. ****************************************************************************}
  678. procedure tderef.reset;
  679. begin
  680. dataidx:=-1;
  681. end;
  682. procedure tderef.build(s:tsymtableentry);
  683. var
  684. len : byte;
  685. data : array[0..255] of byte;
  686. function is_child(currdef,ownerdef:tdef):boolean;
  687. begin
  688. while assigned(currdef) and
  689. (currdef<>ownerdef) do
  690. currdef:=currdef.getparentdef;
  691. result:=assigned(currdef);
  692. end;
  693. procedure addowner(s:tsymtableentry);
  694. begin
  695. if not assigned(s.owner) then
  696. internalerror(200306063);
  697. case s.owner.symtabletype of
  698. globalsymtable :
  699. begin
  700. if s.owner.unitid=0 then
  701. begin
  702. data[len]:=ord(deref_aktglobal);
  703. inc(len);
  704. end
  705. else
  706. begin
  707. { check if the unit is available in the uses
  708. clause, else it's an error }
  709. if s.owner.unitid=$ffff then
  710. internalerror(200306063);
  711. data[len]:=ord(deref_unit);
  712. data[len+1]:=s.owner.unitid shr 8;
  713. data[len+2]:=s.owner.unitid and $ff;
  714. inc(len,3);
  715. end;
  716. end;
  717. staticsymtable :
  718. begin
  719. { only references to the current static symtable are allowed }
  720. if s.owner<>current_module.localsymtable then
  721. internalerror(200306233);
  722. data[len]:=ord(deref_aktstatic);
  723. inc(len);
  724. end;
  725. localsymtable :
  726. begin
  727. addowner(s.owner.defowner);
  728. data[len]:=ord(deref_def);
  729. data[len+1]:=s.owner.defowner.indexnr shr 8;
  730. data[len+2]:=s.owner.defowner.indexnr and $ff;
  731. data[len+3]:=ord(deref_local);
  732. inc(len,4);
  733. end;
  734. parasymtable :
  735. begin
  736. addowner(s.owner.defowner);
  737. data[len]:=ord(deref_def);
  738. data[len+1]:=s.owner.defowner.indexnr shr 8;
  739. data[len+2]:=s.owner.defowner.indexnr and $ff;
  740. data[len+3]:=ord(deref_para);
  741. inc(len,4);
  742. end;
  743. objectsymtable,
  744. recordsymtable :
  745. begin
  746. addowner(s.owner.defowner);
  747. data[len]:=ord(deref_def);
  748. data[len+1]:=s.owner.defowner.indexnr shr 8;
  749. data[len+2]:=s.owner.defowner.indexnr and $ff;
  750. data[len+3]:=ord(deref_record);
  751. inc(len,4);
  752. end;
  753. else
  754. internalerror(200306065);
  755. end;
  756. if len>252 then
  757. internalerror(200306062);
  758. end;
  759. procedure addparentobject(currdef,ownerdef:tdef);
  760. var
  761. nextdef : tdef;
  762. begin
  763. if not assigned(currdef) then
  764. internalerror(200306185);
  765. { Already handled by derefaktrecordindex }
  766. if currdef=ownerdef then
  767. internalerror(200306188);
  768. { Generate a direct reference to the top parent
  769. class available in the current unit, this is required because
  770. the parent class is maybe not resolved yet and therefor
  771. has the childof value not available yet }
  772. while (currdef<>ownerdef) do
  773. begin
  774. nextdef:=currdef.getparentdef;
  775. { objects are only allowed in globalsymtable,staticsymtable this check is
  776. needed because we need the unitid }
  777. if not(nextdef.owner.symtabletype in [globalsymtable,staticsymtable]) then
  778. internalerror(200306187);
  779. { Next parent is in a different unit, then stop }
  780. if nextdef.owner.unitid<>0 then
  781. break;
  782. currdef:=nextdef;
  783. end;
  784. { Add reference where to start the parent lookup }
  785. if currdef=aktrecordsymtable.defowner then
  786. begin
  787. data[len]:=ord(deref_aktrecord);
  788. inc(len);
  789. end
  790. else
  791. begin
  792. if currdef.owner.symtabletype=globalsymtable then
  793. data[len]:=ord(deref_aktglobal)
  794. else
  795. data[len]:=ord(deref_aktstatic);
  796. data[len+1]:=ord(deref_def);
  797. data[len+2]:=currdef.indexnr shr 8;
  798. data[len+3]:=currdef.indexnr and $ff;
  799. data[len+4]:=ord(deref_record);
  800. inc(len,5);
  801. end;
  802. { When the current found parent in this module is not the owner we
  803. add derefs for the parent classes not available in this unit }
  804. while (currdef<>ownerdef) do
  805. begin
  806. data[len]:=ord(deref_parent_object);
  807. inc(len);
  808. currdef:=currdef.getparentdef;
  809. { It should be valid as it is checked by is_child }
  810. if not assigned(currdef) then
  811. internalerror(200306186);
  812. end;
  813. end;
  814. begin
  815. { skip length byte }
  816. len:=1;
  817. if assigned(s) then
  818. begin
  819. { Static symtable of current unit ? }
  820. if (s.owner.symtabletype=staticsymtable) and
  821. (s.owner.unitid=0) then
  822. begin
  823. data[len]:=ord(deref_aktstatic);
  824. inc(len);
  825. end
  826. { Global symtable of current unit ? }
  827. else if (s.owner.symtabletype=globalsymtable) and
  828. (s.owner.unitid=0) then
  829. begin
  830. data[len]:=ord(deref_aktglobal);
  831. inc(len);
  832. end
  833. { Current record/object symtable ? }
  834. else if (s.owner=aktrecordsymtable) then
  835. begin
  836. data[len]:=ord(deref_aktrecord);
  837. inc(len);
  838. end
  839. { Current local symtable ? }
  840. else if (s.owner=aktlocalsymtable) then
  841. begin
  842. data[len]:=ord(deref_aktlocal);
  843. inc(len);
  844. end
  845. { Current para symtable ? }
  846. else if (s.owner=aktparasymtable) then
  847. begin
  848. data[len]:=ord(deref_aktpara);
  849. inc(len);
  850. end
  851. { Parent class? }
  852. else if assigned(aktrecordsymtable) and
  853. (aktrecordsymtable.symtabletype=objectsymtable) and
  854. (s.owner.symtabletype=objectsymtable) and
  855. is_child(tdef(aktrecordsymtable.defowner),tdef(s.owner.defowner)) then
  856. begin
  857. addparentobject(tdef(aktrecordsymtable.defowner),tdef(s.owner.defowner));
  858. end
  859. else
  860. { Default, start by building from unit symtable }
  861. begin
  862. addowner(s);
  863. end;
  864. { Add index of the symbol/def }
  865. if s is tsym then
  866. data[len]:=ord(deref_sym)
  867. else
  868. data[len]:=ord(deref_def);
  869. data[len+1]:=s.indexnr shr 8;
  870. data[len+2]:=s.indexnr and $ff;
  871. inc(len,3);
  872. end
  873. else
  874. begin
  875. { nil pointer }
  876. data[len]:=0;
  877. inc(len);
  878. end;
  879. { store data length in first byte }
  880. data[0]:=len-1;
  881. { store index and write to derefdata }
  882. dataidx:=current_module.derefdata.size;
  883. current_module.derefdata.write(data,len);
  884. end;
  885. function tderef.resolve:tsymtableentry;
  886. var
  887. pd : tdef;
  888. pm : tmodule;
  889. typ : tdereftype;
  890. st : tsymtable;
  891. idx : word;
  892. i : aint;
  893. len : byte;
  894. data : array[0..255] of byte;
  895. begin
  896. result:=nil;
  897. { not initialized or error }
  898. if dataidx<0 then
  899. internalerror(200306067);
  900. { read data }
  901. current_module.derefdata.seek(dataidx);
  902. if current_module.derefdata.read(len,1)<>1 then
  903. internalerror(200310221);
  904. if len>0 then
  905. begin
  906. if current_module.derefdata.read(data,len)<>len then
  907. internalerror(200310222);
  908. end;
  909. { process data }
  910. st:=nil;
  911. i:=0;
  912. while (i<len) do
  913. begin
  914. typ:=tdereftype(data[i]);
  915. inc(i);
  916. case typ of
  917. deref_nil :
  918. begin
  919. result:=nil;
  920. { Only allowed when no other deref is available }
  921. if len<>1 then
  922. internalerror(200306232);
  923. end;
  924. deref_sym :
  925. begin
  926. if not assigned(st) then
  927. internalerror(200309141);
  928. idx:=(data[i] shl 8) or data[i+1];
  929. inc(i,2);
  930. result:=st.getsymnr(idx);
  931. end;
  932. deref_def :
  933. begin
  934. if not assigned(st) then
  935. internalerror(200309142);
  936. idx:=(data[i] shl 8) or data[i+1];
  937. inc(i,2);
  938. result:=st.getdefnr(idx);
  939. end;
  940. deref_aktrecord :
  941. st:=aktrecordsymtable;
  942. deref_aktstatic :
  943. st:=current_module.localsymtable;
  944. deref_aktglobal :
  945. st:=current_module.globalsymtable;
  946. deref_aktlocal :
  947. st:=aktlocalsymtable;
  948. deref_aktpara :
  949. st:=aktparasymtable;
  950. deref_unit :
  951. begin
  952. idx:=(data[i] shl 8) or data[i+1];
  953. inc(i,2);
  954. if idx>current_module.mapsize then
  955. internalerror(200306231);
  956. pm:=current_module.map[idx].u;
  957. if not assigned(pm) then
  958. internalerror(200212273);
  959. st:=pm.globalsymtable;
  960. end;
  961. deref_local :
  962. begin
  963. if not assigned(result) then
  964. internalerror(200306069);
  965. st:=tdef(result).getsymtable(gs_local);
  966. result:=nil;
  967. if not assigned(st) then
  968. internalerror(200212275);
  969. end;
  970. deref_para :
  971. begin
  972. if not assigned(result) then
  973. internalerror(2003060610);
  974. st:=tdef(result).getsymtable(gs_para);
  975. result:=nil;
  976. if not assigned(st) then
  977. internalerror(200212276);
  978. end;
  979. deref_record :
  980. begin
  981. if not assigned(result) then
  982. internalerror(200306068);
  983. st:=tdef(result).getsymtable(gs_record);
  984. result:=nil;
  985. if not assigned(st) then
  986. internalerror(200212274);
  987. end;
  988. deref_parent_object :
  989. begin
  990. { load current object symtable if no
  991. symtable is available yet }
  992. if st=nil then
  993. begin
  994. st:=aktrecordsymtable;
  995. if not assigned(st) then
  996. internalerror(200306068);
  997. end;
  998. if st.symtabletype<>objectsymtable then
  999. internalerror(200306189);
  1000. pd:=tdef(st.defowner).getparentdef;
  1001. if not assigned(pd) then
  1002. internalerror(200306184);
  1003. st:=pd.getsymtable(gs_record);
  1004. if not assigned(st) then
  1005. internalerror(200212274);
  1006. end;
  1007. else
  1008. internalerror(200212277);
  1009. end;
  1010. end;
  1011. end;
  1012. {*****************************************************************************
  1013. TCompilerPPUFile
  1014. *****************************************************************************}
  1015. procedure tcompilerppufile.checkerror;
  1016. begin
  1017. if error then
  1018. Message(unit_f_ppu_read_error);
  1019. end;
  1020. procedure tcompilerppufile.getguid(var g: tguid);
  1021. begin
  1022. getdata(g,sizeof(g));
  1023. end;
  1024. function tcompilerppufile.getexprint:tconstexprint;
  1025. begin
  1026. if sizeof(tconstexprint)=8 then
  1027. result:=tconstexprint(getint64)
  1028. else
  1029. result:=tconstexprint(getlongint);
  1030. end;
  1031. function tcompilerppufile.getPtrUInt:TConstPtrUInt;
  1032. begin
  1033. if sizeof(TConstPtrUInt)=8 then
  1034. result:=tconstptruint(getint64)
  1035. else
  1036. result:=TConstPtrUInt(getlongint);
  1037. end;
  1038. procedure tcompilerppufile.getposinfo(var p:tfileposinfo);
  1039. var
  1040. info : byte;
  1041. begin
  1042. {
  1043. info byte layout in bits:
  1044. 0-1 - amount of bytes for fileindex
  1045. 2-3 - amount of bytes for line
  1046. 4-5 - amount of bytes for column
  1047. }
  1048. info:=getbyte;
  1049. case (info and $03) of
  1050. 0 : p.fileindex:=getbyte;
  1051. 1 : p.fileindex:=getword;
  1052. 2 : p.fileindex:=(getbyte shl 16) or getword;
  1053. 3 : p.fileindex:=getlongint;
  1054. end;
  1055. case ((info shr 2) and $03) of
  1056. 0 : p.line:=getbyte;
  1057. 1 : p.line:=getword;
  1058. 2 : p.line:=(getbyte shl 16) or getword;
  1059. 3 : p.line:=getlongint;
  1060. end;
  1061. case ((info shr 4) and $03) of
  1062. 0 : p.column:=getbyte;
  1063. 1 : p.column:=getword;
  1064. 2 : p.column:=(getbyte shl 16) or getword;
  1065. 3 : p.column:=getlongint;
  1066. end;
  1067. end;
  1068. procedure tcompilerppufile.getderef(var d:tderef);
  1069. begin
  1070. d.dataidx:=getlongint;
  1071. end;
  1072. function tcompilerppufile.getsymlist:tsymlist;
  1073. var
  1074. symderef : tderef;
  1075. tt : ttype;
  1076. slt : tsltype;
  1077. idx : longint;
  1078. p : tsymlist;
  1079. begin
  1080. p:=tsymlist.create;
  1081. getderef(p.procdefderef);
  1082. repeat
  1083. slt:=tsltype(getbyte);
  1084. case slt of
  1085. sl_none :
  1086. break;
  1087. sl_call,
  1088. sl_load,
  1089. sl_subscript :
  1090. begin
  1091. getderef(symderef);
  1092. p.addsymderef(slt,symderef);
  1093. end;
  1094. sl_typeconv :
  1095. begin
  1096. gettype(tt);
  1097. p.addtype(slt,tt);
  1098. end;
  1099. sl_vec :
  1100. begin
  1101. idx:=getlongint;
  1102. p.addconst(slt,idx);
  1103. end;
  1104. else
  1105. internalerror(200110204);
  1106. end;
  1107. until false;
  1108. getsymlist:=tsymlist(p);
  1109. end;
  1110. procedure tcompilerppufile.gettype(var t:ttype);
  1111. begin
  1112. getderef(t.deref);
  1113. t.def:=nil;
  1114. t.sym:=nil;
  1115. end;
  1116. function tcompilerppufile.getasmsymbol:tasmsymbol;
  1117. begin
  1118. getasmsymbol:=tasmsymbol(pointer(ptrint(getlongint)));
  1119. end;
  1120. procedure tcompilerppufile.putposinfo(const p:tfileposinfo);
  1121. var
  1122. oldcrc : boolean;
  1123. info : byte;
  1124. begin
  1125. { posinfo is not relevant for changes in PPU }
  1126. oldcrc:=do_crc;
  1127. do_crc:=false;
  1128. {
  1129. info byte layout in bits:
  1130. 0-1 - amount of bytes for fileindex
  1131. 2-3 - amount of bytes for line
  1132. 4-5 - amount of bytes for column
  1133. }
  1134. info:=0;
  1135. { calculate info byte }
  1136. if (p.fileindex>$ff) then
  1137. begin
  1138. if (p.fileindex<=$ffff) then
  1139. info:=info or $1
  1140. else
  1141. if (p.fileindex<=$ffffff) then
  1142. info:=info or $2
  1143. else
  1144. info:=info or $3;
  1145. end;
  1146. if (p.line>$ff) then
  1147. begin
  1148. if (p.line<=$ffff) then
  1149. info:=info or $4
  1150. else
  1151. if (p.line<=$ffffff) then
  1152. info:=info or $8
  1153. else
  1154. info:=info or $c;
  1155. end;
  1156. if (p.column>$ff) then
  1157. begin
  1158. if (p.column<=$ffff) then
  1159. info:=info or $10
  1160. else
  1161. if (p.column<=$ffffff) then
  1162. info:=info or $20
  1163. else
  1164. info:=info or $30;
  1165. end;
  1166. { write data }
  1167. putbyte(info);
  1168. case (info and $03) of
  1169. 0 : putbyte(p.fileindex);
  1170. 1 : putword(p.fileindex);
  1171. 2 : begin
  1172. putbyte(p.fileindex shr 16);
  1173. putword(p.fileindex and $ffff);
  1174. end;
  1175. 3 : putlongint(p.fileindex);
  1176. end;
  1177. case ((info shr 2) and $03) of
  1178. 0 : putbyte(p.line);
  1179. 1 : putword(p.line);
  1180. 2 : begin
  1181. putbyte(p.line shr 16);
  1182. putword(p.line and $ffff);
  1183. end;
  1184. 3 : putlongint(p.line);
  1185. end;
  1186. case ((info shr 4) and $03) of
  1187. 0 : putbyte(p.column);
  1188. 1 : putword(p.column);
  1189. 2 : begin
  1190. putbyte(p.column shr 16);
  1191. putword(p.column and $ffff);
  1192. end;
  1193. 3 : putlongint(p.column);
  1194. end;
  1195. do_crc:=oldcrc;
  1196. end;
  1197. procedure tcompilerppufile.putguid(const g: tguid);
  1198. begin
  1199. putdata(g,sizeof(g));
  1200. end;
  1201. procedure tcompilerppufile.putexprint(v:tconstexprint);
  1202. begin
  1203. if sizeof(TConstExprInt)=8 then
  1204. putint64(int64(v))
  1205. else if sizeof(TConstExprInt)=4 then
  1206. putlongint(longint(v))
  1207. else
  1208. internalerror(2002082601);
  1209. end;
  1210. procedure tcompilerppufile.PutPtrUInt(v:TConstPtrUInt);
  1211. begin
  1212. if sizeof(TConstPtrUInt)=8 then
  1213. putint64(int64(v))
  1214. else if sizeof(TConstPtrUInt)=4 then
  1215. putlongint(longint(v))
  1216. else
  1217. internalerror(2002082601);
  1218. end;
  1219. procedure tcompilerppufile.putderef(const d:tderef);
  1220. var
  1221. oldcrc : boolean;
  1222. begin
  1223. oldcrc:=do_crc;
  1224. do_crc:=false;
  1225. putlongint(d.dataidx);
  1226. do_crc:=oldcrc;
  1227. end;
  1228. procedure tcompilerppufile.putsymlist(p:tsymlist);
  1229. var
  1230. hp : psymlistitem;
  1231. begin
  1232. putderef(p.procdefderef);
  1233. hp:=p.firstsym;
  1234. while assigned(hp) do
  1235. begin
  1236. putbyte(byte(hp^.sltype));
  1237. case hp^.sltype of
  1238. sl_call,
  1239. sl_load,
  1240. sl_subscript :
  1241. putderef(hp^.symderef);
  1242. sl_typeconv :
  1243. puttype(hp^.tt);
  1244. sl_vec :
  1245. putlongint(hp^.value);
  1246. else
  1247. internalerror(200110205);
  1248. end;
  1249. hp:=hp^.next;
  1250. end;
  1251. putbyte(byte(sl_none));
  1252. end;
  1253. procedure tcompilerppufile.puttype(const t:ttype);
  1254. begin
  1255. putderef(t.deref);
  1256. end;
  1257. procedure tcompilerppufile.putasmsymbol(s:tasmsymbol);
  1258. begin
  1259. if assigned(s) then
  1260. begin
  1261. if s.ppuidx=-1 then
  1262. begin
  1263. inc(objectlibrary.asmsymbolppuidx);
  1264. s.ppuidx:=objectlibrary.asmsymbolppuidx;
  1265. end;
  1266. putlongint(s.ppuidx);
  1267. end
  1268. else
  1269. putlongint(0);
  1270. end;
  1271. {$ifdef MEMDEBUG}
  1272. initialization
  1273. membrowser:=TMemDebug.create('BrowserRefs');
  1274. membrowser.stop;
  1275. memrealnames:=TMemDebug.create('Realnames');
  1276. memrealnames.stop;
  1277. memmanglednames:=TMemDebug.create('Manglednames');
  1278. memmanglednames.stop;
  1279. memprocpara:=TMemDebug.create('ProcPara');
  1280. memprocpara.stop;
  1281. memprocparast:=TMemDebug.create('ProcParaSt');
  1282. memprocparast.stop;
  1283. memproclocalst:=TMemDebug.create('ProcLocalSt');
  1284. memproclocalst.stop;
  1285. memprocnodetree:=TMemDebug.create('ProcNodeTree');
  1286. memprocnodetree.stop;
  1287. finalization
  1288. membrowser.free;
  1289. memrealnames.free;
  1290. memmanglednames.free;
  1291. memprocpara.free;
  1292. memprocparast.free;
  1293. memproclocalst.free;
  1294. memprocnodetree.free;
  1295. {$endif MEMDEBUG}
  1296. end.
  1297. {
  1298. $Log$
  1299. Revision 1.49 2004-12-15 21:09:06 peter
  1300. * 64bit typecast
  1301. Revision 1.48 2004/11/15 23:35:31 peter
  1302. * tparaitem removed, use tparavarsym instead
  1303. * parameter order is now calculated from paranr value in tparavarsym
  1304. Revision 1.47 2004/11/08 22:09:59 peter
  1305. * tvarsym splitted
  1306. Revision 1.46 2004/11/01 23:30:11 peter
  1307. * support > 32bit accesses for x86_64
  1308. * rewrote array size checking to support 64bit
  1309. Revision 1.45 2004/10/12 14:34:49 peter
  1310. * fixed visibility for procsyms
  1311. * fixed override check when there was no entry yet
  1312. Revision 1.44 2004/07/09 22:17:32 peter
  1313. * revert has_localst patch
  1314. * replace aktstaticsymtable/aktglobalsymtable with current_module
  1315. Revision 1.43 2004/06/20 08:55:30 florian
  1316. * logs truncated
  1317. Revision 1.42 2004/06/16 20:07:10 florian
  1318. * dwarf branch merged
  1319. Revision 1.41 2004/05/23 15:23:30 peter
  1320. * fixed qword(longint) that removed sign from the number
  1321. * removed code in the compiler that relied on wrong qword(longint)
  1322. code generation
  1323. Revision 1.40.2.1 2004/04/12 14:45:11 peter
  1324. * tai_const_symbol and tai_const merged
  1325. Revision 1.40 2004/02/27 13:04:22 daniel
  1326. * Removed unused concatstabto
  1327. Revision 1.39 2004/02/11 19:59:06 peter
  1328. * fix compilation without GDB
  1329. }
  1330. end.