mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-08-21 12:29:46 +02:00
* changed getprocaddressprocvar() into a tprocvardef.getreusableprocaddr()
class method git-svn-id: trunk@31148 -
This commit is contained in:
parent
f40ea04540
commit
508828958c
@ -1274,7 +1274,7 @@ implementation
|
|||||||
|
|
||||||
procedure ttai_typedconstbuilder.emit_procdef_const(pd: tprocdef);
|
procedure ttai_typedconstbuilder.emit_procdef_const(pd: tprocdef);
|
||||||
begin
|
begin
|
||||||
emit_tai(Tai_const.Createname(pd.mangledname,AT_FUNCTION,0),getprocaddressprocvar(pd));
|
emit_tai(Tai_const.Createname(pd.mangledname,AT_FUNCTION,0),cprocvardef.getreusableprocaddr(pd));
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
|
||||||
|
@ -319,7 +319,7 @@ implementation
|
|||||||
begin
|
begin
|
||||||
if (pd.typ=procdef) or
|
if (pd.typ=procdef) or
|
||||||
not pd.is_addressonly then
|
not pd.is_addressonly then
|
||||||
result:=getprocaddressprocvar(pd)
|
result:=cprocvardef.getreusableprocaddr(pd)
|
||||||
else
|
else
|
||||||
result:=pd
|
result:=pd
|
||||||
end;
|
end;
|
||||||
@ -420,7 +420,7 @@ implementation
|
|||||||
{ if this is a complex procvar, get the non-tmethod-like equivalent }
|
{ if this is a complex procvar, get the non-tmethod-like equivalent }
|
||||||
if (pd.typ=procvardef) and
|
if (pd.typ=procvardef) and
|
||||||
not pd.is_addressonly then
|
not pd.is_addressonly then
|
||||||
pd:=tprocvardef(getprocaddressprocvar(pd));
|
pd:=tprocvardef(cprocvardef.getreusableprocaddr(pd));
|
||||||
{ if the function returns a function pointer type or is varargs, we
|
{ if the function returns a function pointer type or is varargs, we
|
||||||
must specify the full function signature, otherwise we can only
|
must specify the full function signature, otherwise we can only
|
||||||
specify the return type }
|
specify the return type }
|
||||||
|
@ -236,7 +236,7 @@ implementation
|
|||||||
procedure tllvmtai_typedconstbuilder.emit_tai_procvar2procdef(p: tai; pvdef: tprocvardef);
|
procedure tllvmtai_typedconstbuilder.emit_tai_procvar2procdef(p: tai; pvdef: tprocvardef);
|
||||||
begin
|
begin
|
||||||
if not pvdef.is_addressonly then
|
if not pvdef.is_addressonly then
|
||||||
pvdef:=getprocaddressprocvar(pvdef);
|
pvdef:=cprocvardef.getreusableprocaddr(pvdef);
|
||||||
emit_tai(p,pvdef);
|
emit_tai(p,pvdef);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -444,7 +444,7 @@ implementation
|
|||||||
the procdef }
|
the procdef }
|
||||||
if (fromdef.typ=procdef) and
|
if (fromdef.typ=procdef) and
|
||||||
(todef.typ<>procdef) then
|
(todef.typ<>procdef) then
|
||||||
fromdef:=getprocaddressprocvar(tprocdef(fromdef));
|
fromdef:=cprocvardef.getreusableprocaddr(tprocdef(fromdef));
|
||||||
op:=llvmconvop(fromdef,todef);
|
op:=llvmconvop(fromdef,todef);
|
||||||
case op of
|
case op of
|
||||||
la_ptrtoint_to_x,
|
la_ptrtoint_to_x,
|
||||||
|
@ -820,7 +820,7 @@ implementation
|
|||||||
of far calls where the procvardef was defined does not matter,
|
of far calls where the procvardef was defined does not matter,
|
||||||
even though the procvardef constructor called by getcopyas looks at
|
even though the procvardef constructor called by getcopyas looks at
|
||||||
it) }
|
it) }
|
||||||
codeprocdef:=getprocaddressprocvar(procdefinition);
|
codeprocdef:=cprocvardef.getreusableprocaddr(procdefinition);
|
||||||
result:=hlcg.getaddressregister(current_asmdata.CurrAsmList,codeprocdef);
|
result:=hlcg.getaddressregister(current_asmdata.CurrAsmList,codeprocdef);
|
||||||
{ in case we have a method pointer on a big endian target in registers,
|
{ in case we have a method pointer on a big endian target in registers,
|
||||||
the method address is stored in registerhi (it's the first field
|
the method address is stored in registerhi (it's the first field
|
||||||
|
@ -722,7 +722,7 @@ implementation
|
|||||||
hs:=make_mangledname('WRPR',_class.owner,_class.objname^+'_$_'+AImplIntf.IntfDef.objname^+'_$_'+
|
hs:=make_mangledname('WRPR',_class.owner,_class.objname^+'_$_'+AImplIntf.IntfDef.objname^+'_$_'+
|
||||||
tostr(i)+'_$_'+pd.mangledname);
|
tostr(i)+'_$_'+pd.mangledname);
|
||||||
{ create reference }
|
{ create reference }
|
||||||
datatcb.emit_tai(Tai_const.Createname(hs,AT_FUNCTION,0),getprocaddressprocvar(pd));
|
datatcb.emit_tai(Tai_const.Createname(hs,AT_FUNCTION,0),cprocvardef.getreusableprocaddr(pd));
|
||||||
end;
|
end;
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
@ -1015,7 +1015,7 @@ implementation
|
|||||||
procname:='FPC_EMPTYMETHOD'
|
procname:='FPC_EMPTYMETHOD'
|
||||||
else if not wpoinfomanager.optimized_name_for_vmt(_class,vmtpd,procname) then
|
else if not wpoinfomanager.optimized_name_for_vmt(_class,vmtpd,procname) then
|
||||||
procname:=vmtpd.mangledname;
|
procname:=vmtpd.mangledname;
|
||||||
tcb.emit_tai(Tai_const.Createname(procname,AT_FUNCTION,0),getprocaddressprocvar(vmtpd));
|
tcb.emit_tai(Tai_const.Createname(procname,AT_FUNCTION,0),cprocvardef.getreusableprocaddr(vmtpd));
|
||||||
{$ifdef vtentry}
|
{$ifdef vtentry}
|
||||||
hs:='VTENTRY'+'_'+_class.vmt_mangledname+'$$'+tostr(_class.vmtmethodoffset(i) div sizeof(pint));
|
hs:='VTENTRY'+'_'+_class.vmt_mangledname+'$$'+tostr(_class.vmtmethodoffset(i) div sizeof(pint));
|
||||||
current_asmdata.asmlists[al_globals].concat(tai_symbol.CreateName(hs,AT_DATA,0));
|
current_asmdata.asmlists[al_globals].concat(tai_symbol.CreateName(hs,AT_DATA,0));
|
||||||
|
@ -864,7 +864,7 @@ implementation
|
|||||||
{ now add the methods }
|
{ now add the methods }
|
||||||
for i:=0 to _class.vmtentries.count-1 do
|
for i:=0 to _class.vmtentries.count-1 do
|
||||||
vmtdef.add_field_by_def(
|
vmtdef.add_field_by_def(
|
||||||
getprocaddressprocvar(pvmtentry(_class.vmtentries[i])^.procdef)
|
cprocvardef.getreusableprocaddr(pvmtentry(_class.vmtentries[i])^.procdef)
|
||||||
);
|
);
|
||||||
{ the VMT ends with a nil pointer }
|
{ the VMT ends with a nil pointer }
|
||||||
vmtdef.add_field_by_def(voidcodepointertype);
|
vmtdef.add_field_by_def(voidcodepointertype);
|
||||||
|
@ -608,6 +608,8 @@ interface
|
|||||||
|
|
||||||
tprocvardef = class(tabstractprocdef)
|
tprocvardef = class(tabstractprocdef)
|
||||||
constructor create(level:byte);virtual;
|
constructor create(level:byte);virtual;
|
||||||
|
{ returns a procvardef that represents the address of a proc(var)def }
|
||||||
|
class function getreusableprocaddr(def: tabstractprocdef): tprocvardef; virtual;
|
||||||
constructor ppuload(ppufile:tcompilerppufile);
|
constructor ppuload(ppufile:tcompilerppufile);
|
||||||
function getcopy : tstoreddef;override;
|
function getcopy : tstoreddef;override;
|
||||||
{ do not override this routine in platform-specific subclasses,
|
{ do not override this routine in platform-specific subclasses,
|
||||||
@ -1126,9 +1128,6 @@ interface
|
|||||||
|
|
||||||
function use_vectorfpu(def : tdef) : boolean;
|
function use_vectorfpu(def : tdef) : boolean;
|
||||||
|
|
||||||
{ returns a procvardef that represents the address of a procdef }
|
|
||||||
function getprocaddressprocvar(def: tabstractprocdef): tprocvardef;
|
|
||||||
|
|
||||||
function getansistringcodepage:tstringencoding; inline;
|
function getansistringcodepage:tstringencoding; inline;
|
||||||
function getansistringdef:tstringdef;
|
function getansistringdef:tstringdef;
|
||||||
function getparaencoding(def:tdef):tstringencoding; inline;
|
function getparaencoding(def:tdef):tstringencoding; inline;
|
||||||
@ -5900,6 +5899,33 @@ implementation
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
|
|
||||||
|
class function tprocvardef.getreusableprocaddr(def: tabstractprocdef): tprocvardef;
|
||||||
|
var
|
||||||
|
res: PHashSetItem;
|
||||||
|
oldsymtablestack: tsymtablestack;
|
||||||
|
begin
|
||||||
|
if not assigned(current_module) then
|
||||||
|
internalerror(2011081301);
|
||||||
|
res:=current_module.procaddrdefs.FindOrAdd(@def,sizeof(def));
|
||||||
|
if not assigned(res^.Data) then
|
||||||
|
begin
|
||||||
|
{ since these pointerdefs can be reused anywhere in the current
|
||||||
|
unit, add them to the global/staticsymtable }
|
||||||
|
oldsymtablestack:=symtablestack;
|
||||||
|
{ do not simply push/pop current_module.localsymtable, because
|
||||||
|
that can have side-effects (e.g., it removes helpers) }
|
||||||
|
symtablestack:=nil;
|
||||||
|
res^.Data:=def.getcopyas(procvardef,pc_address_only);
|
||||||
|
if assigned(current_module.localsymtable) then
|
||||||
|
current_module.localsymtable.insertdef(tdef(res^.Data))
|
||||||
|
else
|
||||||
|
current_module.globalsymtable.insertdef(tdef(res^.Data));
|
||||||
|
symtablestack:=oldsymtablestack;
|
||||||
|
end;
|
||||||
|
result:=tprocvardef(res^.Data);
|
||||||
|
end;
|
||||||
|
|
||||||
|
|
||||||
constructor tprocvardef.ppuload(ppufile:tcompilerppufile);
|
constructor tprocvardef.ppuload(ppufile:tcompilerppufile);
|
||||||
begin
|
begin
|
||||||
inherited ppuload(procvardef,ppufile);
|
inherited ppuload(procvardef,ppufile);
|
||||||
@ -7661,30 +7687,4 @@ implementation
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
|
|
||||||
function getprocaddressprocvar(def: tabstractprocdef): tprocvardef;
|
|
||||||
var
|
|
||||||
res: PHashSetItem;
|
|
||||||
oldsymtablestack: tsymtablestack;
|
|
||||||
begin
|
|
||||||
if not assigned(current_module) then
|
|
||||||
internalerror(2011081301);
|
|
||||||
res:=current_module.procaddrdefs.FindOrAdd(@def,sizeof(def));
|
|
||||||
if not assigned(res^.Data) then
|
|
||||||
begin
|
|
||||||
{ since these pointerdefs can be reused anywhere in the current
|
|
||||||
unit, add them to the global/staticsymtable }
|
|
||||||
oldsymtablestack:=symtablestack;
|
|
||||||
{ do not simply push/pop current_module.localsymtable, because
|
|
||||||
that can have side-effects (e.g., it removes helpers) }
|
|
||||||
symtablestack:=nil;
|
|
||||||
res^.Data:=def.getcopyas(procvardef,pc_address_only);
|
|
||||||
if assigned(current_module.localsymtable) then
|
|
||||||
current_module.localsymtable.insertdef(tdef(res^.Data))
|
|
||||||
else
|
|
||||||
current_module.globalsymtable.insertdef(tdef(res^.Data));
|
|
||||||
symtablestack:=oldsymtablestack;
|
|
||||||
end;
|
|
||||||
result:=tprocvardef(res^.Data);
|
|
||||||
end;
|
|
||||||
|
|
||||||
end.
|
end.
|
||||||
|
Loading…
Reference in New Issue
Block a user