* fixed LLVM para loading for byval paralocs that are preceded by other

paralocs

git-svn-id: branches/debug_eh@41217 -
This commit is contained in:
Jonas Maebe 2019-02-03 21:10:18 +00:00
parent af098474f4
commit a0831b058a
3 changed files with 24 additions and 14 deletions

View File

@ -314,7 +314,7 @@ implementation
newrefsize: tdef;
reg: tregister;
begin
newrefsize:=llvmgetcgparadef(para,true);
newrefsize:=llvmgetcgparadef(para,true,callerside);
if (refsize<>newrefsize) and
(initialref.refaddr<>addr_full) then
begin
@ -532,7 +532,7 @@ implementation
hlretdef:=forceresdef;
{ llvm will always expect the original return def }
if not paramanager.ret_in_param(hlretdef, pd) then
llvmretdef:=llvmgetcgparadef(pd.funcretloc[callerside], true)
llvmretdef:=llvmgetcgparadef(pd.funcretloc[callerside], true, callerside)
else
llvmretdef:=voidtype;
if not is_void(llvmretdef) then
@ -1416,7 +1416,7 @@ implementation
LOC_MMREGISTER:
begin
if not llvmaggregatetype(resdef) then
list.concat(taillvm.op_reg_size_undef(la_bitcast,resloc.location^.register,llvmgetcgparadef(resloc,true)))
list.concat(taillvm.op_reg_size_undef(la_bitcast,resloc.location^.register,llvmgetcgparadef(resloc,true,calleeside)))
else
{ bitcast doesn't work for aggregates -> just load from the
(uninitialised) function result memory location }
@ -1634,7 +1634,7 @@ implementation
end;
{ get the LLVM representation of the function result (e.g. a
struct with two i64 fields for a record with 4 i32 fields) }
result.def:=llvmgetcgparadef(result,true);
result.def:=llvmgetcgparadef(result,true,callerside);
if assigned(result.location^.next) then
begin
{ unify the result into a sinlge location; unlike for parameters,
@ -1722,7 +1722,7 @@ implementation
{ get the equivalent llvm def used to pass the parameter (e.g. a record
with two int64 fields for passing a record consisiting of 8 bytes on
x86-64) }
llvmparadef:=llvmgetcgparadef(para,true);
llvmparadef:=llvmgetcgparadef(para,true,calleeside);
userecord:=
(llvmparadef<>para.def) and
assigned(para.location^.next);

View File

@ -30,7 +30,7 @@ interface
cclasses,globtype,
aasmbase,
parabase,
symbase,symtype,symdef,
symconst,symbase,symtype,symdef,
llvmbase;
type
@ -76,7 +76,7 @@ interface
such parameters to be zero/sign extended. The second parameter can be used
to get the type before zero/sign extension, as e.g. required to generate
function declarations. }
function llvmgetcgparadef(const cgpara: tcgpara; beforevalueext: boolean): tdef;
function llvmgetcgparadef(const cgpara: tcgpara; beforevalueext: boolean; callercallee: tcallercallee): tdef;
{ can be used to extract the value extension info from acgpara. Pass in
the def of the cgpara as first parameter and a local variable holding
@ -116,7 +116,7 @@ implementation
globals,cutils,constexp,
verbose,systems,
fmodule,
symtable,symconst,symsym,
symtable,symsym,
llvmsym,hlcgobj,
defutil,blockutl,cgbase,paramgr;
@ -817,7 +817,7 @@ implementation
{ function result (return-by-ref is handled explicitly) }
if not paramanager.ret_in_param(def.returndef,def) then
begin
usedef:=llvmgetcgparadef(def.funcretloc[useside],false);
usedef:=llvmgetcgparadef(def.funcretloc[useside],false,useside);
llvmextractvalueextinfo(def.returndef,usedef,signext);
{ specifying result sign extention information for an alias causes
an error for some reason }
@ -924,7 +924,7 @@ implementation
end;
function llvmgetcgparadef(const cgpara: tcgpara; beforevalueext: boolean): tdef;
function llvmgetcgparadef(const cgpara: tcgpara; beforevalueext: boolean; callercallee: tcallercallee): tdef;
var
retdeflist: array[0..9] of tdef;
retloc: pcgparalocation;
@ -968,6 +968,16 @@ implementation
retdeflist[i]:=retloc^.def;
dec(sizeleft,retloc^.def.size);
end
{ on the callerside, "byval" parameter locations have the implicit
pointer in their type -> remove if we wish to create a record
containing all actual parameter data }
else if (callercallee=callerside) and
not retloc^.llvmvalueloc then
begin
if retloc^.def.typ<>pointerdef then
internalerror(2019020201);
retdeflist[i]:=tpointerdef(retloc^.def).pointeddef
end
else if retloc^.def.size<>sizeleft then
begin
case sizeleft of

View File

@ -501,8 +501,8 @@ implementation
if (tprocdef(def).has_paraloc_info=callnoside) then
tprocdef(def).init_paraloc_info(callerside);
for i:=0 to tprocdef(def).paras.count-1 do
record_def(llvmgetcgparadef(tparavarsym(tprocdef(def).paras[i]).paraloc[callerside],true));
record_def(llvmgetcgparadef(tprocdef(def).funcretloc[callerside],true));
record_def(llvmgetcgparadef(tparavarsym(tprocdef(def).paras[i]).paraloc[callerside],true,calleeside));
record_def(llvmgetcgparadef(tprocdef(def).funcretloc[callerside],true,calleeside));
end;
end;
end;
@ -586,8 +586,8 @@ implementation
types that are then casted to the real type when they are used }
def.init_paraloc_info(callerside);
for i:=0 to def.paras.count-1 do
appenddef(list,llvmgetcgparadef(tparavarsym(def.paras[i]).paraloc[callerside],true));
appenddef(list,llvmgetcgparadef(def.funcretloc[callerside],true));
appenddef(list,llvmgetcgparadef(tparavarsym(def.paras[i]).paraloc[callerside],true,calleeside));
appenddef(list,llvmgetcgparadef(def.funcretloc[callerside],true,calleeside));
if assigned(def.typesym) and
not def.is_addressonly then
list.concat(taillvm.op_size(LA_TYPE,record_def(def)));