mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-04-23 02:29:34 +02:00
* Mantis #27044: copy Variant to temp if it cannot be passed by reference to fpc_dispinvoke_variant helper. This provides behavior consistent to implicit 'self' parameter of objects/records.
git-svn-id: trunk@29093 -
This commit is contained in:
parent
d844025ddf
commit
64af966eaa
@ -336,6 +336,8 @@ implementation
|
||||
pvardatadef : tdef;
|
||||
useresult: boolean;
|
||||
restype: byte;
|
||||
selftemp: ttempcreatenode;
|
||||
selfpara: tnode;
|
||||
|
||||
names : ansistring;
|
||||
variantdispatch : boolean;
|
||||
@ -369,7 +371,7 @@ implementation
|
||||
if is_interfacecom_or_dispinterface(sourcedef) then
|
||||
begin
|
||||
{ distinct IDispatch and IUnknown interfaces }
|
||||
if def_is_related(tobjectdef(sourcedef),tobjectdef(search_system_type('IDISPATCH').typedef)) then
|
||||
if def_is_related(tobjectdef(sourcedef),interface_idispatch) then
|
||||
result:=vardispatch
|
||||
else
|
||||
result:=varunknown;
|
||||
@ -382,6 +384,8 @@ implementation
|
||||
variantdispatch:=selfnode.resultdef.typ=variantdef;
|
||||
result:=internalstatements(statements);
|
||||
result_data:=nil;
|
||||
selftemp:=nil;
|
||||
selfpara:=nil;
|
||||
|
||||
useresult := assigned(resultdef) and not is_void(resultdef);
|
||||
if useresult then
|
||||
@ -527,13 +531,27 @@ implementation
|
||||
{ actual call }
|
||||
vardatadef:=trecorddef(search_system_type('TVARDATA').typedef);
|
||||
|
||||
{ the Variant should behave similar to hidden 'self' parameter of objects/records,
|
||||
see issues #26773 and #27044 }
|
||||
if not valid_for_var(selfnode,false) then
|
||||
begin
|
||||
selftemp:=ctempcreatenode.create(selfnode.resultdef,selfnode.resultdef.size,tt_persistent,false);
|
||||
addstatement(statements,selftemp);
|
||||
addstatement(statements,cassignmentnode.create(ctemprefnode.create(selftemp),selfnode));
|
||||
selfpara:=ctemprefnode.create(selftemp);
|
||||
end
|
||||
else
|
||||
selfpara:=selfnode;
|
||||
|
||||
addstatement(statements,ccallnode.createintern('fpc_dispinvoke_variant',
|
||||
{ parameters are passed always reverted, i.e. the last comes first }
|
||||
ccallparanode.create(caddrnode.create(ctemprefnode.create(params)),
|
||||
ccallparanode.create(caddrnode.create(calldescnode),
|
||||
ccallparanode.create(ctypeconvnode.create_internal(selfnode,vardatadef),
|
||||
ccallparanode.create(ctypeconvnode.create_internal(selfpara,vardatadef),
|
||||
ccallparanode.create(ctypeconvnode.create_internal(resultvalue,pvardatadef),nil)))))
|
||||
);
|
||||
if assigned(selftemp) then
|
||||
addstatement(statements,ctempdeletenode.create(selftemp));
|
||||
end
|
||||
else
|
||||
begin
|
||||
|
Loading…
Reference in New Issue
Block a user