是首先是VM表,但是和COM相关的函数地址都废弃了,这几个VM函数具体放在哪里,还得在研究:
{ Virtual method table entries } vmtSelfPtr = -76; vmtIntfTable = -72; vmtAutoTable = -68; vmtInitTable = -64; vmtTypeInfo = -60; vmtFieldTable = -56; vmtMethodTable = -52; vmtDynamicTable = -48; vmtClassName = -44; vmtInstanceSize = -40; vmtParent = -36; vmtSafeCallException = -32 deprecated; // don't use these constants. vmtAfterConstruction = -28 deprecated; // use VMTOFFSET in asm code instead vmtBeforeDestruction = -24 deprecated; vmtDispatch = -20 deprecated; vmtDefaultHandler = -16 deprecated; vmtNewInstance = -12 deprecated; vmtFreeInstance = -8 deprecated; vmtDestroy = -4 deprecated; vmtQueryInterface = 0 deprecated; vmtAddRef = 4 deprecated; vmtRelease = 8 deprecated; vmtCreateObject = 12 deprecated;
其次是所有与COM相关的声明与定义:
type TObject = class; TClass = class of TObject; HRESULT = type Longint; { from WTYPES.H } {$EXTERNALSYM HRESULT} PGUID = ^TGUID; TGUID = packed record D1: LongWord; D2: Word; D3: Word; D4: array[0..7] of Byte; end; PInterfaceEntry = ^TInterfaceEntry; TInterfaceEntry = packed record IID: TGUID; VTable: Pointer; IOffset: Integer; ImplGetter: Integer; end; PInterfaceTable = ^TInterfaceTable; TInterfaceTable = packed record EntryCount: Integer; Entries: array[0..9999] of TInterfaceEntry; end; TMethod = record Code, Data: Pointer; end; const S_OK = 0; {$EXTERNALSYM S_OK} S_FALSE = $00000001; {$EXTERNALSYM S_FALSE} E_NOINTERFACE = HRESULT($80004002); {$EXTERNALSYM E_NOINTERFACE} E_UNEXPECTED = HRESULT($8000FFFF); {$EXTERNALSYM E_UNEXPECTED} E_NOTIMPL = HRESULT($80004001); {$EXTERNALSYM E_NOTIMPL} type IInterface = interface ['{00000000-0000-0000-C000-000000000046}'] function QueryInterface(const IID: TGUID; out Obj): HResult; stdcall; function _AddRef: Integer; stdcall; function _Release: Integer; stdcall; end; IUnknown = IInterface; {$M+} IInvokable = interface(IInterface) end; {$M-} IDispatch = interface(IUnknown) ['{00020400-0000-0000-C000-000000000046}'] function GetTypeInfoCount(out Count: Integer): HResult; stdcall; function GetTypeInfo(Index, LocaleID: Integer; out TypeInfo): HResult; stdcall; function GetIDsOfNames(const IID: TGUID; Names: Pointer; NameCount, LocaleID: Integer; DispIDs: Pointer): HResult; stdcall; function Invoke(DispID: Integer; const IID: TGUID; LocaleID: Integer; Flags: Word; var Params; VarResult, ExcepInfo, ArgErr: Pointer): HResult; stdcall; end; {$EXTERNALSYM IUnknown} {$EXTERNALSYM IDispatch} { TInterfacedObject provides a threadsafe default implementation of IInterface. You should use TInterfaceObject as the base class of objects implementing interfaces. } TInterfacedObject = class(TObject, IInterface) protected FRefCount: Integer; function QueryInterface(const IID: TGUID; out Obj): HResult; stdcall; function _AddRef: Integer; stdcall; function _Release: Integer; stdcall; public procedure AfterConstruction; override; procedure BeforeDestruction; override; class function NewInstance: TObject; override; property RefCount: Integer read FRefCount; end; TInterfacedClass = class of TInterfacedObject; { TAggregatedObject and TContainedObject are suitable base classes for interfaced objects intended to be aggregated or contained in an outer controlling object. When using the "implements" syntax on an interface property in an outer object class declaration, use these types to implement the inner object. Interfaces implemented by aggregated objects on behalf of the controller should not be distinguishable from other interfaces provided by the controller. Aggregated objects must not maintain their own reference count - they must have the same lifetime as their controller. To achieve this, aggregated objects reflect the reference count methods to the controller. TAggregatedObject simply reflects QueryInterface calls to its controller. From such an aggregated object, one can obtain any interface that the controller supports, and only interfaces that the controller supports. This is useful for implementing a controller class that uses one or more internal objects to implement the interfaces declared on the controller class. Aggregation promotes implementation sharing across the object hierarchy. TAggregatedObject is what most aggregate objects should inherit from, especially when used in conjunction with the "implements" syntax. } TAggregatedObject = class(TObject) private FController: Pointer; // weak reference to controller function GetController: IInterface; protected { IInterface } function QueryInterface(const IID: TGUID; out Obj): HResult; stdcall; function _AddRef: Integer; stdcall; function _Release: Integer; stdcall; public constructor Create(const Controller: IInterface); property Controller: IInterface read GetController; end; { TContainedObject is an aggregated object that isolates QueryInterface on the aggregate from the controller. TContainedObject will return only interfaces that the contained object itself implements, not interfaces that the controller implements. This is useful for implementing nodes that are attached to a controller and have the same lifetime as the controller, but whose interface identity is separate from the controller. You might do this if you don't want the consumers of an aggregated interface to have access to other interfaces implemented by the controller - forced encapsulation. This is a less common case than TAggregatedObject. } TContainedObject = class(TAggregatedObject, IInterface) protected { IInterface } function QueryInterface(const IID: TGUID; out Obj): HResult; virtual; stdcall; end;
里面的英文说明还得翻译如下: