[fpc-devel] {$Interfaces Corba} and TInterfacedObject

Thorsten Engler thorsten.engler at gmx.net
Thu Nov 29 14:27:55 CET 2007


> > AObject as ICorbaInterface ?
> 
> And how does the underlying code do the lookup in the 
> interfaces table?

There is no "lookup" required for this. An "as" cast from object to
interface is only allowed (at least in Delphi) if the compiler can
statically at compiletime determine that the type of the AObject variable
implements that interface. Objects implement interfaces by having a pointer
to the VMT of for the implemented interface in their instance data. So the
above cast should get compiled into somethinge like:

If Aobject = nil then
  Intf := nil
Else
  Intf := ICorbaInterface(IntPtr(Aobject) + OffsetOfICorbaInterface);

There is no need for a GUID in this case. (And in Delphi, using an "as" cast
like this is the way how you get a reference to an interface that has no
GUID.)

It's important to mention here that:

Intf := AObject as ISomeInterface;
and
Supports(Aobject, ISomeInterface, Intf);

Do very different things.

The first one resolves the offset that needs to be applied to AObject to get
to ISomeInterface at compiletime based on the type of the variable (not the
type of the actual instance which is only known at runtime). The 2nd one
uses a call to Aobject.GetInterface, passing in the GUID of Iinterface and
then calls QueryInterface with the GUID of ISomeInterface on that.

That can lead to interesting effects:

Type
  TObjectA = class(TInterfacedObject, ISomeInterface)
    procedure SomeMethod; //not virtual!
  end;  

  TObjectB = class(TObjectA, ISomeInterface)
    procedure SomeMethod;
  end;

Var
  Obj   : TObjectA;
  IntfA : ISomeInterface;
  IntfB : ISomeInterface;
Begin
  Obj := TObjectB.Create;
  IntfA := Obj as ISomeInterface;
  Supports(Obj, ISomeInterface, IntfB); 
  IntfA.SomeMethod; //calls TObjectA.SomeMethod
  IntfB.SomeMethod; //calls TObjectB.SomeMethod
End;

Most of the above assumes you are working with COM style interfaces (the
only type of interface supported by Delphi/Kylix which doesn't have any
support at compiler level for "CORBA" interfaces).

For "CORBA" interfaces in FPC the only thing that should/can work is casting
from an object variable to an interface type using "as" if the compiler can
statically at compiletime determine the correct offset to apply to the
object pointer to get to the interface VMT and maybe support casting an
interface to one of it's parent interfaces. There is no way how "is", "as"
or "Supports" could be implemented for such interfacces.




More information about the fpc-devel mailing list