mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-04-22 06:49:27 +02:00
* use temp-reference nodes rather than addrnodes to create references to
complex parameters passed to inlined routines on the JVM target, because it is not possible to take the address of any kind of node on the JVM target (temp-reference nodes work for any kind of LOC_(C)REFERENCE, but are currently only implemented for the JVM platform) git-svn-id: branches/jvmbackend@18905 -
This commit is contained in:
parent
49817c9a0e
commit
6a7ff1cf75
@ -28,7 +28,7 @@ interface
|
||||
uses
|
||||
cgbase,
|
||||
symtype,symdef,
|
||||
node,ncgcal;
|
||||
node,ncal,ncgcal;
|
||||
|
||||
type
|
||||
tjvmcallparanode = class(tcgcallparanode)
|
||||
@ -43,6 +43,7 @@ interface
|
||||
|
||||
tjvmcallnode = class(tcgcallnode)
|
||||
protected
|
||||
procedure wrapcomplexinlinepara(para: tcallparanode); override;
|
||||
procedure extra_pre_call_code; override;
|
||||
procedure set_result_location(realresdef: tstoreddef); override;
|
||||
procedure do_release_unused_return_value;override;
|
||||
@ -59,7 +60,6 @@ implementation
|
||||
uses
|
||||
verbose,globtype,constexp,cutils,
|
||||
symconst,symtable,symsym,defutil,
|
||||
ncal,
|
||||
cgutils,tgobj,procinfo,htypechk,
|
||||
cpubase,aasmdata,aasmcpu,
|
||||
hlcgobj,hlcgcpu,
|
||||
@ -311,6 +311,26 @@ implementation
|
||||
TJVMCALLNODE
|
||||
*****************************************************************************}
|
||||
|
||||
procedure tjvmcallnode.wrapcomplexinlinepara(para: tcallparanode);
|
||||
var
|
||||
tempnode: ttempcreatenode;
|
||||
begin
|
||||
{ don't use caddrnodes for the JVM target, because we can't take the
|
||||
address of every kind of type (e.g., of ansistrings). A temp-reference
|
||||
node does work for any kind of memory reference (and the expectloc
|
||||
is LOC_(C)REFERENCE when this routine is called), but is not (yet)
|
||||
supported for other targets }
|
||||
tempnode:=ctempcreatenode.create_reference(para.parasym.vardef,para.parasym.vardef.size,
|
||||
tt_persistent,tparavarsym(para.parasym).is_regvar(false),para.left,false);
|
||||
addstatement(inlineinitstatement,tempnode);
|
||||
addstatement(inlinecleanupstatement,ctempdeletenode.create(tempnode));
|
||||
para.left:=ctemprefnode.create(tempnode);
|
||||
{ inherit addr_taken flag }
|
||||
if (tabstractvarsym(para.parasym).addr_taken) then
|
||||
include(tempnode.tempinfo^.flags,ti_addr_taken);
|
||||
end;
|
||||
|
||||
|
||||
procedure tjvmcallnode.extra_pre_call_code;
|
||||
begin
|
||||
{ when calling a constructor, first create a new instance, except
|
||||
|
@ -80,12 +80,13 @@ interface
|
||||
protected
|
||||
procedure objc_convert_to_message_send;virtual;
|
||||
|
||||
private
|
||||
protected
|
||||
{ inlining support }
|
||||
inlinelocals : TFPObjectList;
|
||||
inlineinitstatement,
|
||||
inlinecleanupstatement : tstatementnode;
|
||||
procedure createinlineparas;
|
||||
procedure wrapcomplexinlinepara(para: tcallparanode); virtual;
|
||||
function replaceparaload(var n: tnode; arg: pointer): foreachnoderesult;
|
||||
procedure createlocaltemps(p:TObject;arg:pointer);
|
||||
function optimize_funcret_assignment(inlineblock: tblocknode): tnode;
|
||||
@ -3667,8 +3668,6 @@ implementation
|
||||
para: tcallparanode;
|
||||
tempnode: ttempcreatenode;
|
||||
n: tnode;
|
||||
paraaddr: taddrnode;
|
||||
ptrtype: tpointerdef;
|
||||
paracomplexity: longint;
|
||||
pushconstaddr: boolean;
|
||||
begin
|
||||
@ -3802,18 +3801,7 @@ implementation
|
||||
{ temp }
|
||||
else if (paracomplexity > 1) then
|
||||
begin
|
||||
ptrtype:=getpointerdef(para.left.resultdef);
|
||||
tempnode := ctempcreatenode.create(ptrtype,ptrtype.size,tt_persistent,tparavarsym(para.parasym).is_regvar(true));
|
||||
addstatement(inlineinitstatement,tempnode);
|
||||
addstatement(inlinecleanupstatement,ctempdeletenode.create(tempnode));
|
||||
{ inherit addr_taken flag }
|
||||
if (tabstractvarsym(para.parasym).addr_taken) then
|
||||
include(tempnode.tempinfo^.flags,ti_addr_taken);
|
||||
paraaddr:=caddrnode.create_internal(para.left);
|
||||
include(paraaddr.flags,nf_typedaddr);
|
||||
addstatement(inlineinitstatement,cassignmentnode.create(ctemprefnode.create(tempnode),
|
||||
paraaddr));
|
||||
para.left:=cderefnode.create(ctemprefnode.create(tempnode));
|
||||
wrapcomplexinlinepara(para);
|
||||
end;
|
||||
end;
|
||||
para := tcallparanode(para.right);
|
||||
@ -3827,6 +3815,27 @@ implementation
|
||||
end;
|
||||
|
||||
|
||||
procedure tcallnode.wrapcomplexinlinepara(para: tcallparanode);
|
||||
var
|
||||
ptrtype: tdef;
|
||||
tempnode: ttempcreatenode;
|
||||
paraaddr: taddrnode;
|
||||
begin
|
||||
ptrtype:=getpointerdef(para.left.resultdef);
|
||||
tempnode := ctempcreatenode.create(ptrtype,ptrtype.size,tt_persistent,tparavarsym(para.parasym).is_regvar(true));
|
||||
addstatement(inlineinitstatement,tempnode);
|
||||
addstatement(inlinecleanupstatement,ctempdeletenode.create(tempnode));
|
||||
{ inherit addr_taken flag }
|
||||
if (tabstractvarsym(para.parasym).addr_taken) then
|
||||
include(tempnode.tempinfo^.flags,ti_addr_taken);
|
||||
paraaddr:=caddrnode.create_internal(para.left);
|
||||
include(paraaddr.flags,nf_typedaddr);
|
||||
addstatement(inlineinitstatement,cassignmentnode.create(ctemprefnode.create(tempnode),
|
||||
paraaddr));
|
||||
para.left:=cderefnode.create(ctemprefnode.create(tempnode));
|
||||
end;
|
||||
|
||||
|
||||
function tcallnode.optimize_funcret_assignment(inlineblock: tblocknode): tnode;
|
||||
var
|
||||
hp : tstatementnode;
|
||||
|
Loading…
Reference in New Issue
Block a user