* use unique symid and defid per module

git-svn-id: trunk@5061 -
This commit is contained in:
peter 2006-10-29 13:00:22 +00:00
parent c07eac1744
commit d4d4309e44
9 changed files with 130 additions and 280 deletions

View File

@ -123,6 +123,8 @@ interface
derefmapsize : longint; { number of units in the map } derefmapsize : longint; { number of units in the map }
derefdataintflen : longint; derefdataintflen : longint;
derefdata : tdynamicarray; derefdata : tdynamicarray;
deflist,
symlist : TFPObjectList;
globalsymtable, { pointer to the global symtable of this unit } globalsymtable, { pointer to the global symtable of this unit }
localsymtable : tsymtable;{ pointer to the local symtable of this unit } localsymtable : tsymtable;{ pointer to the local symtable of this unit }
globalmacrosymtable, { pointer to the global macro symtable of this unit } globalmacrosymtable, { pointer to the global macro symtable of this unit }
@ -409,6 +411,8 @@ implementation
derefmapcnt:=0; derefmapcnt:=0;
derefdata:=TDynamicArray.Create(1024); derefdata:=TDynamicArray.Create(1024);
derefdataintflen:=0; derefdataintflen:=0;
deflist:=TFPObjectList.Create(false);
symlist:=TFPObjectList.Create(false);
globalsymtable:=nil; globalsymtable:=nil;
localsymtable:=nil; localsymtable:=nil;
globalmacrosymtable:=nil; globalmacrosymtable:=nil;
@ -510,6 +514,8 @@ implementation
d:=tmemdebug.create(modulename^+' - symtable'); d:=tmemdebug.create(modulename^+' - symtable');
{$endif} {$endif}
derefdata.free; derefdata.free;
deflist.free;
symlist.free;
if assigned(globalsymtable) then if assigned(globalsymtable) then
globalsymtable.free; globalsymtable.free;
if assigned(localsymtable) then if assigned(localsymtable) then
@ -579,6 +585,10 @@ implementation
localmacrosymtable.free; localmacrosymtable.free;
localmacrosymtable:=nil; localmacrosymtable:=nil;
end; end;
deflist.free;
deflist:=TFPObjectList.Create(false);
symlist.free;
symlist:=TFPObjectList.Create(false);
derefdata.free; derefdata.free;
derefdata:=TDynamicArray.Create(1024); derefdata:=TDynamicArray.Create(1024);
if assigned(unitmap) then if assigned(unitmap) then

View File

@ -249,6 +249,8 @@ uses
Message1(unit_u_ppu_flags,tostr(flags)); Message1(unit_u_ppu_flags,tostr(flags));
Message1(unit_u_ppu_crc,hexstr(ppufile.header.checksum,8)); Message1(unit_u_ppu_crc,hexstr(ppufile.header.checksum,8));
Message1(unit_u_ppu_crc,hexstr(ppufile.header.interface_checksum,8)+' (intfc)'); Message1(unit_u_ppu_crc,hexstr(ppufile.header.interface_checksum,8)+' (intfc)');
Comment(V_used,'Number of definitions: '+tostr(ppufile.header.deflistsize));
Comment(V_used,'Number of symbols: '+tostr(ppufile.header.symlistsize));
do_compile:=false; do_compile:=false;
openppu:=true; openppu:=true;
end; end;
@ -1106,6 +1108,8 @@ uses
ppufile.header.cpu:=word(target_cpu); ppufile.header.cpu:=word(target_cpu);
ppufile.header.target:=word(target_info.system); ppufile.header.target:=word(target_info.system);
ppufile.header.flags:=flags; ppufile.header.flags:=flags;
ppufile.header.deflistsize:=current_module.deflist.count;
ppufile.header.symlistsize:=current_module.symlist.count;
ppufile.writeheader; ppufile.writeheader;
{ save crc in current module also } { save crc in current module also }
@ -1247,6 +1251,8 @@ uses
{ ok, now load the interface of this unit } { ok, now load the interface of this unit }
if current_module<>self then if current_module<>self then
internalerror(200208187); internalerror(200208187);
deflist.count:=ppufile.header.deflistsize;
symlist.count:=ppufile.header.symlistsize;
globalsymtable:=tglobalsymtable.create(modulename^,moduleid); globalsymtable:=tglobalsymtable.create(modulename^,moduleid);
tstoredsymtable(globalsymtable).ppuload(ppufile); tstoredsymtable(globalsymtable).ppuload(ppufile);

View File

@ -164,7 +164,9 @@ type
size : longint; { size of the ppufile without header } size : longint; { size of the ppufile without header }
checksum : cardinal; { checksum for this ppufile } checksum : cardinal; { checksum for this ppufile }
interface_checksum : cardinal; interface_checksum : cardinal;
future : array[0..2] of longint; deflistsize,
symlistsize : longint;
future : array[0..0] of longint;
end; end;
tppuentry=packed record tppuentry=packed record

View File

@ -63,6 +63,7 @@ interface
tdefentry = class(tsymtableentry) tdefentry = class(tsymtableentry)
deftype : tdeftype; deftype : tdeftype;
defid : longint;
end; end;
@ -72,7 +73,8 @@ interface
{ this object is the base for all symbol objects } { this object is the base for all symbol objects }
tsymentry = class(tsymtableentry) tsymentry = class(tsymtableentry)
typ : tsymtyp; typ : tsymtyp;
symid : longint;
end; end;

View File

@ -126,7 +126,9 @@ type
deref_record, deref_record,
deref_local, deref_local,
deref_para, deref_para,
deref_parent_object deref_parent_object,
deref_symid,
deref_defid
); );
{ symbol options } { symbol options }

View File

@ -912,11 +912,18 @@ implementation
fillchar(localrttilab,sizeof(localrttilab),0); fillchar(localrttilab,sizeof(localrttilab),0);
generictokenbuf:=nil; generictokenbuf:=nil;
genericdef:=nil; genericdef:=nil;
{ Register in symtable stack. { Don't register forwarddefs, they are disposed at the
Don't register forwarddefs, they are disposed at the
end of an type block } end of an type block }
if assigned(symtablestack) and if (dt=forwarddef) then
(dt<>forwarddef) then exit;
{ Register in current_module }
if assigned(current_module) then
begin
current_module.deflist.Add(self);
DefId:=current_module.deflist.Count-1;
end;
{ Register in symtable stack }
if assigned(symtablestack) then
begin begin
insertstack:=symtablestack.stack; insertstack:=symtablestack.stack;
while assigned(insertstack) and while assigned(insertstack) and
@ -951,6 +958,8 @@ implementation
{$endif} {$endif}
fillchar(localrttilab,sizeof(localrttilab),0); fillchar(localrttilab,sizeof(localrttilab),0);
{ load } { load }
DefId:=ppufile.getlongint;
current_module.deflist[DefId]:=self;
indexnr:=ppufile.getword; indexnr:=ppufile.getword;
ppufile.getderef(typesymderef); ppufile.getderef(typesymderef);
ppufile.getsmallset(defoptions); ppufile.getsmallset(defoptions);
@ -1002,6 +1011,7 @@ implementation
buf : array[0..255] of byte; buf : array[0..255] of byte;
oldintfcrc : boolean; oldintfcrc : boolean;
begin begin
ppufile.putlongint(DefId);
ppufile.putword(indexnr); ppufile.putword(indexnr);
ppufile.putderef(typesymderef); ppufile.putderef(typesymderef);
ppufile.putsmallset(defoptions); ppufile.putsmallset(defoptions);

View File

@ -366,6 +366,7 @@ implementation
systems, systems,
{ symtable } { symtable }
defutil,symtable, defutil,symtable,
fmodule,
{ tree } { tree }
node, node,
{ aasm } { aasm }
@ -386,6 +387,12 @@ implementation
constructor tstoredsym.create(st:tsymtyp;const n : string); constructor tstoredsym.create(st:tsymtyp;const n : string);
begin begin
inherited create(st,n); inherited create(st,n);
{ Register in current_module }
if assigned(current_module) then
begin
current_module.symlist.Add(self);
SymId:=current_module.symlist.Count-1;
end;
end; end;
@ -394,6 +401,8 @@ implementation
nr : word; nr : word;
s : string; s : string;
begin begin
SymId:=ppufile.getlongint;
current_module.symlist[SymId]:=self;
nr:=ppufile.getword; nr:=ppufile.getword;
s:=ppufile.getstring; s:=ppufile.getstring;
if s[1]='$' then if s[1]='$' then
@ -417,6 +426,7 @@ implementation
procedure tstoredsym.ppuwrite(ppufile:tcompilerppufile); procedure tstoredsym.ppuwrite(ppufile:tcompilerppufile);
begin begin
ppufile.putlongint(SymId);
ppufile.putword(indexnr); ppufile.putword(indexnr);
ppufile.putstring(_realname^); ppufile.putstring(_realname^);
ppufile.putposinfo(fileinfo); ppufile.putposinfo(fileinfo);

View File

@ -232,7 +232,7 @@ implementation
uses uses
verbose, verbose,
fmodule fmodule,symtable
; ;
@ -373,6 +373,7 @@ implementation
function tsym.mangledname : string; function tsym.mangledname : string;
begin begin
internalerror(200204171); internalerror(200204171);
result:='';
end; end;
@ -774,209 +775,57 @@ implementation
dataidx:=-1; dataidx:=-1;
end; end;
procedure tderef.build(s:tsymtableentry); procedure tderef.build(s:tsymtableentry);
var var
len : byte; len : byte;
st : tsymtable;
data : array[0..255] of byte; data : array[0..255] of byte;
idx : word;
function is_child(currdef,ownerdef:tdef):boolean;
begin
while assigned(currdef) and
(currdef<>ownerdef) do
currdef:=currdef.getparentdef;
result:=assigned(currdef);
end;
procedure addowner(s:tsymtableentry);
var
idx : longint;
begin
if not assigned(s.owner) then
internalerror(200306063);
case s.owner.symtabletype of
globalsymtable :
begin
if s.owner.iscurrentunit then
begin
data[len]:=ord(deref_aktglobal);
inc(len);
end
else
begin
{ register that the unit is needed for resolving }
idx:=current_module.derefidx_unit(s.owner.moduleid);
data[len]:=ord(deref_unit);
data[len+1]:=idx shr 8;
data[len+2]:=idx and $ff;
inc(len,3);
end;
end;
staticsymtable :
begin
{ only references to the current static symtable are allowed }
if not s.owner.iscurrentunit then
internalerror(200306233);
data[len]:=ord(deref_aktstatic);
inc(len);
end;
localsymtable :
begin
addowner(s.owner.defowner);
data[len]:=ord(deref_def);
data[len+1]:=s.owner.defowner.indexnr shr 8;
data[len+2]:=s.owner.defowner.indexnr and $ff;
data[len+3]:=ord(deref_local);
inc(len,4);
end;
parasymtable :
begin
addowner(s.owner.defowner);
data[len]:=ord(deref_def);
data[len+1]:=s.owner.defowner.indexnr shr 8;
data[len+2]:=s.owner.defowner.indexnr and $ff;
data[len+3]:=ord(deref_para);
inc(len,4);
end;
objectsymtable,
recordsymtable :
begin
addowner(s.owner.defowner);
data[len]:=ord(deref_def);
data[len+1]:=s.owner.defowner.indexnr shr 8;
data[len+2]:=s.owner.defowner.indexnr and $ff;
data[len+3]:=ord(deref_record);
inc(len,4);
end;
else
internalerror(200306065);
end;
if len>252 then
internalerror(200306062);
end;
procedure addparentobject(currdef,ownerdef:tdef);
var
nextdef : tdef;
begin
if not assigned(currdef) then
internalerror(200306185);
{ Already handled by derefaktrecordindex }
if currdef=ownerdef then
internalerror(200306188);
{ Generate a direct reference to the top parent
class available in the current unit, this is required because
the parent class is maybe not resolved yet and therefor
has the childof value not available yet }
while (currdef<>ownerdef) do
begin
nextdef:=currdef.getparentdef;
{ objects are only allowed in globalsymtable,staticsymtable }
if not(nextdef.owner.symtabletype in [globalsymtable,staticsymtable]) then
internalerror(200306187);
{ Next parent is in a different unit, then stop }
if not(nextdef.owner.iscurrentunit) then
break;
currdef:=nextdef;
end;
{ Add reference where to start the parent lookup }
if currdef=aktrecordsymtable.defowner then
begin
data[len]:=ord(deref_aktrecord);
inc(len);
end
else
begin
if currdef.owner.symtabletype=globalsymtable then
data[len]:=ord(deref_aktglobal)
else
data[len]:=ord(deref_aktstatic);
data[len+1]:=ord(deref_def);
data[len+2]:=currdef.indexnr shr 8;
data[len+3]:=currdef.indexnr and $ff;
data[len+4]:=ord(deref_record);
inc(len,5);
end;
{ When the current found parent in this module is not the owner we
add derefs for the parent classes not available in this unit }
while (currdef<>ownerdef) do
begin
data[len]:=ord(deref_parent_object);
inc(len);
currdef:=currdef.getparentdef;
{ It should be valid as it is checked by is_child }
if not assigned(currdef) then
internalerror(200306186);
end;
end;
begin begin
{ skip length byte } { skip length byte }
len:=1; len:=1;
if assigned(s) then if assigned(s) then
begin begin
{ Static symtable of current unit ? } st:=findunitsymtable(s.owner);
if (s.owner.symtabletype=staticsymtable) and if not st.iscurrentunit then
s.owner.iscurrentunit then begin
begin { register that the unit is needed for resolving }
data[len]:=ord(deref_aktstatic); data[len]:=ord(deref_unit);
inc(len); idx:=current_module.derefidx_unit(st.moduleid);
end data[len+1]:=idx shr 8 and $ff;
{ Global symtable of current unit ? } data[len+2]:=idx and $ff;
else if (s.owner.symtabletype=globalsymtable) and inc(len,3);
s.owner.iscurrentunit then end;
begin
data[len]:=ord(deref_aktglobal);
inc(len);
end
{ Current record/object symtable ? }
else if (s.owner=aktrecordsymtable) then
begin
data[len]:=ord(deref_aktrecord);
inc(len);
end
{ Current local symtable ? }
else if (s.owner=aktlocalsymtable) then
begin
data[len]:=ord(deref_aktlocal);
inc(len);
end
{ Current para symtable ? }
else if (s.owner=aktparasymtable) then
begin
data[len]:=ord(deref_aktpara);
inc(len);
end
{ Parent class? }
else if assigned(aktrecordsymtable) and
(aktrecordsymtable.symtabletype=objectsymtable) and
(s.owner.symtabletype=objectsymtable) and
is_child(tdef(aktrecordsymtable.defowner),tdef(s.owner.defowner)) then
begin
addparentobject(tdef(aktrecordsymtable.defowner),tdef(s.owner.defowner));
end
else
{ Default, start by building from unit symtable }
begin
addowner(s);
end;
{ Add index of the symbol/def }
if s is tsym then if s is tsym then
data[len]:=ord(deref_sym) begin
data[len]:=ord(deref_symid);
data[len+1]:=tsym(s).symid shr 24 and $ff;
data[len+2]:=tsym(s).symid shr 16 and $ff;
data[len+3]:=tsym(s).symid shr 8 and $ff;
data[len+4]:=tsym(s).symid and $ff;
inc(len,5);
end
else else
data[len]:=ord(deref_def); begin
data[len+1]:=s.indexnr shr 8; data[len]:=ord(deref_defid);
data[len+2]:=s.indexnr and $ff; data[len+1]:=tdef(s).defid shr 24 and $ff;
inc(len,3); data[len+2]:=tdef(s).defid shr 16 and $ff;
data[len+3]:=tdef(s).defid shr 8 and $ff;
data[len+4]:=tdef(s).defid and $ff;
inc(len,5);
end;
end end
else else
begin begin
{ nil pointer } { nil pointer }
data[len]:=0; data[len]:=ord(deref_nil);
inc(len); inc(len);
end; end;
{ store data length in first byte } { store data length in first byte }
data[0]:=len-1; data[0]:=len-1;
{ store index and write to derefdata } { store index and write to derefdata }
dataidx:=current_module.derefdata.size; dataidx:=current_module.derefdata.size;
current_module.derefdata.write(data,len); current_module.derefdata.write(data,len);
@ -985,10 +834,8 @@ implementation
function tderef.resolve:tsymtableentry; function tderef.resolve:tsymtableentry;
var var
pd : tdef;
pm : tmodule; pm : tmodule;
typ : tdereftype; typ : tdereftype;
st : tsymtable;
idx : word; idx : word;
i : aint; i : aint;
len : byte; len : byte;
@ -1008,13 +855,31 @@ implementation
internalerror(200310222); internalerror(200310222);
end; end;
{ process data } { process data }
st:=nil; pm:=current_module;
i:=0; i:=0;
while (i<len) do while (i<len) do
begin begin
typ:=tdereftype(data[i]); typ:=tdereftype(data[i]);
inc(i); inc(i);
case typ of case typ of
deref_unit :
begin
idx:=(data[i] shl 8) or data[i+1];
inc(i,2);
pm:=current_module.resolve_unit(idx);
end;
deref_defid :
begin
idx:=(data[i] shl 24) or (data[i+1] shl 16) or (data[i+2] shl 8) or data[i+3];
inc(i,4);
result:=tdef(pm.deflist[idx]);
end;
deref_symid :
begin
idx:=(data[i] shl 24) or (data[i+1] shl 16) or (data[i+2] shl 8) or data[i+3];
inc(i,4);
result:=tsym(pm.symlist[idx]);
end;
deref_nil : deref_nil :
begin begin
result:=nil; result:=nil;
@ -1022,91 +887,13 @@ implementation
if len<>1 then if len<>1 then
internalerror(200306232); internalerror(200306232);
end; end;
deref_sym :
begin
if not assigned(st) then
internalerror(200309141);
idx:=(data[i] shl 8) or data[i+1];
inc(i,2);
result:=st.getsymnr(idx);
end;
deref_def :
begin
if not assigned(st) then
internalerror(200309142);
idx:=(data[i] shl 8) or data[i+1];
inc(i,2);
result:=st.getdefnr(idx);
end;
deref_aktrecord :
st:=aktrecordsymtable;
deref_aktstatic :
st:=current_module.localsymtable;
deref_aktglobal :
st:=current_module.globalsymtable;
deref_aktlocal :
st:=aktlocalsymtable;
deref_aktpara :
st:=aktparasymtable;
deref_unit :
begin
idx:=(data[i] shl 8) or data[i+1];
inc(i,2);
pm:=current_module.resolve_unit(idx);
st:=pm.globalsymtable;
end;
deref_local :
begin
if not assigned(result) then
internalerror(200306069);
st:=tdef(result).getsymtable(gs_local);
result:=nil;
if not assigned(st) then
internalerror(200212275);
end;
deref_para :
begin
if not assigned(result) then
internalerror(2003060610);
st:=tdef(result).getsymtable(gs_para);
result:=nil;
if not assigned(st) then
internalerror(200212276);
end;
deref_record :
begin
if not assigned(result) then
internalerror(200306068);
st:=tdef(result).getsymtable(gs_record);
result:=nil;
if not assigned(st) then
internalerror(200212274);
end;
deref_parent_object :
begin
{ load current object symtable if no
symtable is available yet }
if st=nil then
begin
st:=aktrecordsymtable;
if not assigned(st) then
internalerror(200306068);
end;
if st.symtabletype<>objectsymtable then
internalerror(200306189);
pd:=tdef(st.defowner).getparentdef;
if not assigned(pd) then
internalerror(200306184);
st:=pd.getsymtable(gs_record);
if not assigned(st) then
internalerror(200212274);
end;
else else
internalerror(200212277); internalerror(200212277);
end; end;
end; end;
end; end;
{***************************************************************************** {*****************************************************************************
TCompilerPPUFile TCompilerPPUFile
*****************************************************************************} *****************************************************************************}

View File

@ -418,7 +418,7 @@ Procedure ReadDerefmap;
var var
i,mapsize : longint; i,mapsize : longint;
begin begin
mapsize:=ppufile.getword; mapsize:=ppufile.getlongint;
writeln('DerefMapsize: ',mapsize); writeln('DerefMapsize: ',mapsize);
for i:=0 to mapsize-1 do for i:=0 to mapsize-1 do
writeln('DerefMap[',i,'] = ',ppufile.getstring); writeln('DerefMap[',i,'] = ',ppufile.getstring);
@ -570,11 +570,14 @@ type
deref_record, deref_record,
deref_local, deref_local,
deref_para, deref_para,
deref_parent_object deref_parent_object,
deref_symid,
deref_defid
); );
var var
b : tdereftype; b : tdereftype;
first : boolean; first : boolean;
unitid : word;
idx : longint; idx : longint;
i,n : byte; i,n : byte;
pdata : pbyte; pdata : pbyte;
@ -609,6 +612,18 @@ begin
case b of case b of
deref_nil : deref_nil :
write('Nil'); write('Nil');
deref_symid :
begin
idx:=pdata[i] shl 24 or pdata[i+1] shl 16 or pdata[i+2] shl 8 or pdata[i+3];
inc(i,4);
write('SymId ',idx);
end;
deref_defid :
begin
idx:=pdata[i] shl 24 or pdata[i+1] shl 16 or pdata[i+2] shl 8 or pdata[i+3];
inc(i,4);
write('DefId ',idx);
end;
deref_def : deref_def :
begin begin
idx:=pdata[i] shl 8; idx:=pdata[i] shl 8;
@ -635,8 +650,7 @@ begin
write('AktPara'); write('AktPara');
deref_unit : deref_unit :
begin begin
idx:=pdata[i] shl 8; idx:=pdata[i] shl 8 or pdata[i+1];
idx:=idx or pdata[i+1];
inc(i,2); inc(i,2);
write('Unit ',idx); write('Unit ',idx);
end; end;
@ -760,8 +774,11 @@ end;
procedure readcommonsym(const s:string); procedure readcommonsym(const s:string);
var
symid : longint;
begin begin
writeln(space,'** Symbol Nr. ',ppufile.getword,' **'); symid:=ppufile.getlongint;
writeln(space,'** Symbol Nr. ',ppufile.getword,' (',symid,') ',' **');
writeln(space,s,ppufile.getstring); writeln(space,s,ppufile.getstring);
write(space,' File Pos : '); write(space,' File Pos : ');
readposinfo; readposinfo;
@ -807,8 +824,10 @@ var
first : boolean; first : boolean;
tokenbufsize : longint; tokenbufsize : longint;
tokenbuf : pointer; tokenbuf : pointer;
defid : longint;
begin begin
writeln(space,'** Definition Nr. ',ppufile.getword,' **'); defid:=ppufile.getlongint;
writeln(space,'** Definition Nr. ',ppufile.getword,' (',defid,') ',' **');
writeln(space,s); writeln(space,s);
write (space,' Type symbol : '); write (space,' Type symbol : ');
readderef; readderef;
@ -2193,6 +2212,8 @@ begin
Writeln('FileSize (w/o header) : ',size); Writeln('FileSize (w/o header) : ',size);
Writeln('Checksum : ',hexstr(checksum,8)); Writeln('Checksum : ',hexstr(checksum,8));
Writeln('Interface Checksum : ',hexstr(interface_checksum,8)); Writeln('Interface Checksum : ',hexstr(interface_checksum,8));
Writeln('Definitions stored : ',tostr(deflistsize));
Writeln('Symbols stored : ',tostr(symlistsize));
end; end;
end; end;
{read the general stuff} {read the general stuff}