compiler: store property parameters in a parasymtables together with property. restore those parameters for descendant properties (fixes mantis #0020421 but maybe not very optimal)

git-svn-id: trunk@19400 -
This commit is contained in:
paul 2011-10-07 05:58:58 +00:00
parent 80a615c542
commit ceb141523d
4 changed files with 40 additions and 13 deletions

View File

@ -318,6 +318,21 @@ implementation
end;
end;
procedure add_parameters(p: tpropertysym; readprocdef, writeprocdef: tprocdef);
var
i: integer;
orig, hparavs: tparavarsym;
begin
for i := 0 to p.parast.SymList.Count - 1 do
begin
orig:=tparavarsym(p.parast.SymList[i]);
hparavs:=tparavarsym.create(orig.RealName,orig.paranr,orig.varspez,orig.vardef,[]);
readprocdef.parast.insert(hparavs);
hparavs:=tparavarsym.create(orig.RealName,orig.paranr,orig.varspez,orig.vardef,[]);
writeprocdef.parast.insert(hparavs);
end;
end;
procedure add_index_parameter(var paranr: word; p: tpropertysym; readprocdef, writeprocdef: tprocdef);
var
hparavs: tparavarsym;
@ -386,7 +401,7 @@ implementation
not (m_delphi in current_settings.modeswitches) then
Message(parser_e_cant_publish_that_property);
{ create a list of the parameters }
symtablestack.push(readprocdef.parast);
symtablestack.push(p.parast);
sc:=TFPObjectList.create(false);
repeat
if try_to_consume(_VAR) then
@ -403,7 +418,7 @@ implementation
repeat
inc(paranr);
hreadparavs:=tparavarsym.create(orgpattern,10*paranr,varspez,generrordef,[]);
readprocdef.parast.insert(hreadparavs);
p.parast.insert(hreadparavs);
sc.add(hreadparavs);
consume(_ID);
until not try_to_consume(_COMMA);
@ -424,22 +439,19 @@ implementation
else
hdef:=cformaltype;
for i:=0 to sc.count-1 do
begin
hreadparavs:=tparavarsym(sc[i]);
hreadparavs.vardef:=hdef;
{ also update the writeprocdef }
hparavs:=tparavarsym.create(hreadparavs.realname,hreadparavs.paranr,vs_value,hdef,[]);
writeprocdef.parast.insert(hparavs);
end;
tparavarsym(sc[i]).vardef:=hdef;
until not try_to_consume(_SEMICOLON);
sc.free;
symtablestack.pop(readprocdef.parast);
symtablestack.pop(p.parast);
consume(_RECKKLAMMER);
{ the parser need to know if a property has parameters, the
index parameter doesn't count (PFV) }
if paranr>0 then
include(p.propoptions,ppo_hasparameters);
begin
add_parameters(p,readprocdef,writeprocdef);
include(p.propoptions,ppo_hasparameters);
end;
end;
{ overridden property ? }
{ force property interface
@ -501,6 +513,13 @@ implementation
p.index:=tpropertysym(overridden).index;
p.default:=tpropertysym(overridden).default;
p.propoptions:=tpropertysym(overridden).propoptions;
p.parast.free;
p.parast:=tpropertysym(overridden).parast.getcopy;
if ppo_hasparameters in p.propoptions then
begin
add_parameters(p,readprocdef,writeprocdef);
paranr:=p.parast.SymList.Count;
end;
if ppo_indexed in p.propoptions then
add_index_parameter(paranr,p,readprocdef,writeprocdef);
end

View File

@ -43,7 +43,7 @@ type
{$endif Test_Double_checksum}
const
CurrentPPUVersion = 137;
CurrentPPUVersion = 138;
{ buffer sizes }
maxentrysize = 1024;

View File

@ -256,6 +256,7 @@ interface
default : longint;
dispid : longint;
propaccesslist: array[tpropaccesslisttypes] of tpropaccesslist;
parast : tsymtable;
constructor create(const n : string);
destructor destroy;override;
constructor ppuload(ppufile:tcompilerppufile);
@ -944,6 +945,7 @@ implementation
default:=0;
propdef:=nil;
indexdef:=nil;
parast:=tparasymtable.create(nil,0);
for pap:=low(tpropaccesslisttypes) to high(tpropaccesslisttypes) do
propaccesslist[pap]:=tpropaccesslist.create;
end;
@ -962,6 +964,8 @@ implementation
ppufile.getderef(indexdefderef);
for pap:=low(tpropaccesslisttypes) to high(tpropaccesslisttypes) do
propaccesslist[pap]:=ppufile.getpropaccesslist;
parast:=tparasymtable.create(nil,0);
tparasymtable(parast).ppuload(ppufile);
end;
@ -971,6 +975,7 @@ implementation
begin
for pap:=low(tpropaccesslisttypes) to high(tpropaccesslisttypes) do
propaccesslist[pap].free;
parast.free;
inherited destroy;
end;
@ -984,6 +989,7 @@ implementation
indexdefderef.build(indexdef);
for pap:=low(tpropaccesslisttypes) to high(tpropaccesslisttypes) do
propaccesslist[pap].buildderef;
tparasymtable(parast).buildderef;
end;
@ -996,6 +1002,7 @@ implementation
propdef:=tdef(propdefderef.resolve);
for pap:=low(tpropaccesslisttypes) to high(tpropaccesslisttypes) do
propaccesslist[pap].resolve;
tparasymtable(parast).deref;
end;
@ -1019,6 +1026,7 @@ implementation
for pap:=low(tpropaccesslisttypes) to high(tpropaccesslisttypes) do
ppufile.putpropaccesslist(propaccesslist[pap]);
ppufile.writeentry(ibpropertysym);
tparasymtable(parast).ppuwrite(ppufile);
end;

View File

@ -1432,7 +1432,7 @@ implementation
if result then
exit;
if not(m_duplicate_names in current_settings.modeswitches) and
(defowner.typ=procdef) and
assigned(defowner) and (defowner.typ=procdef) and
assigned(tprocdef(defowner).struct) and
(tprocdef(defowner).owner.defowner=tprocdef(defowner).struct) and
(