2

インプロセス COM オブジェクトをアウトプロセス COM オブジェクトに変更しようとしています。新しいプロセスは Dispatch を以前に使用した COM オブジェクトに渡すだけなので、必要に応じてインプロセス オブジェクトに戻ることができます。これは正常に機能していますが、イベントに関する問題が発生しています。アウトプロセス サーバーは、以前に使用された COM オブジェクトのイベントをインターセプトし、これらを独自のイベント インターフェイスに渡します。このイベント インターフェイスも機能しています。しかし問題は、アウトプロセス サーバーが Windows レジストリに登録されていない場合、クライアントが DispEventAdvise を使用してこのイベント インターフェイスに接続できないことです。

サーバー IDL は次のようになります。

[
  object,
  uuid(www),
  dual,
  oleautomation,
  nonextensible,
  helpstring("IControl Interface"),
  pointer_default(unique)
]
interface IControl : IDispatch
{
  [id(1)] HRESULT CreateDispatch([out] IDispatch** ppDispatch);
};

[
  uuid(xxx),
  version(1.0),
  helpstring("Control Type Library")
]
library ControlLib
{
  importlib("stdole2.tlb");
  [
    uuid(yyy),
    helpstring("IControlEvents Interface"),
    nonextensible
  ]
  interface IControlEvents : IUnknown
  {
    [id(1)] HRESULT MyEvent(void);
  };

  [
    uuid(zzz),
    helpstring("_IControlEvents Interface")
  ]
  dispinterface _IControlEvents
  {
    interface IControlEvents;
  };

  coclass Control
  {
    [default] interface IControl;
    [default, source] dispinterface _IControlEvents;
  };
};

クライアントとサーバーに control_i.c、control_p.c、および dlldata.c を追加しました。そして、どちらも次の手順を実行してプロキシ/スタブを登録します。

PrxDllGetClassObject(IID_IControl, IID_IUnknown, (void **)&punk);
CoRegisterClassObject(IID_IControl, punk, CLSCTX_INPROC_SERVER, REGCLS_SINGLEUSE, &dwRCO);
CoRegisterPSClsid(IID_IControl, IID_IControl);
CoRegisterPSClsid(IID_IControlEvents, IID_IControl);
CoRegisterPSClsid(DIID__IControlEvents, IID_IControl);

これは、CoCreateInstance を使用して作成されるコントロールに対しては機能しますが、イベントに対しては機能しません。DispEventAdvise が CONNECT_E_CANNOTCONNECT を返し続けるため、シンクの DIID__IControlEvents の QueryInterface が E_NOINTERFACE を返します。

レジストリ内にコントロールを登録せずに、これを機能させる必要があります。また、マニフェスト ファイルと個別のプロキシ/スタブ DLL を使用して登録しようとしましたが、成功しませんでした。


4

1 に答える 1

1

スタブ クラスを正しく登録するために、ディスパッチ イベント インターフェイスのみをレジストリに登録することになりました。これで「登録」されましたが、ファイル参照はありません。そのため、サイドバイサイドのインストールを行うことができます。

于 2015-03-26T07:47:23.790 に答える