mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-12-29 12:50:37 +01:00
* copy_value_on_stack method added for cdecl record passing
This commit is contained in:
parent
1c2eecfb9d
commit
8c82be898d
@ -772,9 +772,8 @@ implementation
|
||||
end
|
||||
else
|
||||
begin
|
||||
{ call by value open array ? }
|
||||
if (calloption in [pocall_cdecl,pocall_cppdecl]) and
|
||||
paramanager.push_addr_param(p.resulttype.def,calloption) then
|
||||
{ copy the value on the stack or use normal parameter push? }
|
||||
if paramanager.copy_value_on_stack(p.resulttype.def,calloption) then
|
||||
begin
|
||||
if not (p.location.loc in [LOC_REFERENCE,LOC_CREFERENCE]) then
|
||||
internalerror(200204241);
|
||||
@ -1876,7 +1875,10 @@ function returns in a register and the caller receives it in an other one}
|
||||
end.
|
||||
{
|
||||
$Log$
|
||||
Revision 1.63 2002-11-25 17:43:18 peter
|
||||
Revision 1.64 2002-11-27 02:33:19 peter
|
||||
* copy_value_on_stack method added for cdecl record passing
|
||||
|
||||
Revision 1.63 2002/11/25 17:43:18 peter
|
||||
* splitted defbase in defutil,symutil,defcmp
|
||||
* merged isconvertable and is_equal into compare_defs(_ext)
|
||||
* made operator search faster by walking the list only once
|
||||
|
||||
@ -54,15 +54,19 @@ unit paramgr;
|
||||
|
||||
function push_high_param(def : tdef;calloption : tproccalloption) : boolean;virtual;
|
||||
|
||||
{# Returns true if a parameter is too large to copy and only
|
||||
{ Returns true if a parameter is too large to copy and only
|
||||
the address is pushed
|
||||
}
|
||||
function push_addr_param(def : tdef;calloption : tproccalloption) : boolean;virtual;
|
||||
{# Returns a structure giving the information on
|
||||
the storage of the parameter (which must be
|
||||
an integer parameter)
|
||||
{ Returns true if a parameter needs to be copied on the stack, this
|
||||
is required for cdecl procedures
|
||||
}
|
||||
function copy_value_on_stack(def : tdef;calloption : tproccalloption) : boolean;
|
||||
{ Returns a structure giving the information on
|
||||
the storage of the parameter (which must be
|
||||
an integer parameter)
|
||||
|
||||
@param(nr Parameter number of routine, starting from 1)
|
||||
@param(nr Parameter number of routine, starting from 1)
|
||||
}
|
||||
function getintparaloc(nr : longint) : tparalocation;virtual;abstract;
|
||||
procedure create_param_loc_info(p : tabstractprocdef);virtual;abstract;
|
||||
@ -184,6 +188,42 @@ unit paramgr;
|
||||
end;
|
||||
|
||||
|
||||
{ true if a parameter is too large to copy and only the address is pushed }
|
||||
function tparamanager.copy_value_on_stack(def : tdef;calloption : tproccalloption) : boolean;
|
||||
begin
|
||||
copy_value_on_stack:=false;
|
||||
{ this is only for cdecl procedures }
|
||||
if not(calloption in [pocall_cdecl,pocall_cppdecl]) then
|
||||
exit;
|
||||
case def.deftype of
|
||||
variantdef,
|
||||
formaldef :
|
||||
copy_value_on_stack:=true;
|
||||
recorddef :
|
||||
copy_value_on_stack:=(def.size>pointer_size);
|
||||
arraydef :
|
||||
copy_value_on_stack:=(
|
||||
(tarraydef(def).highrange>=tarraydef(def).lowrange) and
|
||||
(
|
||||
not(target_info.system=system_i386_win32) or
|
||||
(def.size>pointer_size)
|
||||
)
|
||||
) or
|
||||
is_open_array(def) or
|
||||
is_array_of_const(def) or
|
||||
is_array_constructor(def);
|
||||
objectdef :
|
||||
copy_value_on_stack:=is_object(def);
|
||||
stringdef :
|
||||
copy_value_on_stack:=tstringdef(def).string_typ in [st_shortstring,st_longstring];
|
||||
procvardef :
|
||||
copy_value_on_stack:=(po_methodpointer in tprocvardef(def).procoptions);
|
||||
setdef :
|
||||
copy_value_on_stack:=(tsetdef(def).settype<>smallset);
|
||||
end;
|
||||
end;
|
||||
|
||||
|
||||
function tparamanager.getfuncretparaloc(p : tabstractprocdef) : tparalocation;
|
||||
begin
|
||||
result.loc:=LOC_REFERENCE;
|
||||
@ -339,7 +379,10 @@ end.
|
||||
|
||||
{
|
||||
$Log$
|
||||
Revision 1.24 2002-11-25 17:43:21 peter
|
||||
Revision 1.25 2002-11-27 02:33:19 peter
|
||||
* copy_value_on_stack method added for cdecl record passing
|
||||
|
||||
Revision 1.24 2002/11/25 17:43:21 peter
|
||||
* splitted defbase in defutil,symutil,defcmp
|
||||
* merged isconvertable and is_equal into compare_defs(_ext)
|
||||
* made operator search faster by walking the list only once
|
||||
|
||||
Loading…
Reference in New Issue
Block a user