gpt4 book ai didi

c++ - 从进程外 COM 服务器返回接口(interface)指针的正确方法是什么?

转载 作者:太空狗 更新时间:2023-10-29 21:46:52 29 4
gpt4 key购买 nike

我有一个进程外 COM 服务器,它有两个 ATL COM 对象。 object1 公开一个接口(interface),该接口(interface)在内部创建 object2 并按以下方式返回指向它的接口(interface)指针:

HRESULT CObject1::CreateObject2(IObject2** pIobj2)
{
CComObject<Object2>* pObj = NULL;

HRESULT hr = CComObject<Object2>::CreateInstance(&pObj);

hr = pObj->QueryInterface(IID_IObject2,(void**)pIobj2);

//Some reason i need to store this pIobj2
(*pIobj2)->AddRef();

return hr;
}

Object1暴露了另一个接口(interface)来移除object2

HRESULT CObject1::RemoveObject2(IObject2* pIobj2)
{
pIobj2->Release(); //This to compensate QI done in CreateObject2

pIobj2->Release(); //This to compensate addref done to store in create
}

我的要求是客户端不应在 IObject1::CreateObject2() 之后的任何位置对 IObject2 指针调用 Release。要销毁 object2,它应该调用 IObject1::RemoveObject2()。当我执行客户端时,在 RemoveObject2 之后,object2 没有被销毁,但是当我在 RemoveObject2 之后在客户端的 Iobject2 指针上调用 release 时,object2被摧毁。

最佳答案

进程外 COM 对象的生命周期管理比进程内复杂得多。例如,系统必须考虑到对方可能会死亡(例如,如果客户端进程在没有 Release 的情况下死亡,服务器应该清理分配给对象的资源)。为此,Microsoft 有一个 DCOM 垃圾收集。

确实有两个 COM 对象,在客户端(代理)和服务器( stub )上。代理维护它自己的引用计数,并且您的代码混淆了这个引用计数,因为您在服务器上释放了对象 2 的引用计数 - 不会到达客户端的信息。

我强烈建议您更改架构。一方面,COM 契约是释放对象的方式是使用 Release 方法。那是契约,你的设计改变了它,这就是你对 DCOM 感到困惑的原因。

我认为更好的设计是:

  1. 在 Object2 中保留对 Object1 的引用(例如,m_pobj1)
  2. 没有 Object1::RemoveObject2。如果您需要做一些工作,请使用私有(private)(非 COM)CleanupObject2。
  3. 实现Object2::FinalRelease(Object2的清理方法),调用m_pobj1->Cleanup[Object2(this)
  4. 请记住,如果您需要在 obj1 中保留指向 obj2 的指针,请确保这些是 引用。也就是说 - 只是指针 - 没有添加引用计数。

客户端调用 Object1::CreateObject2 并获得对 obj2 的引用。当他们完成后,他们将调用 obj2->Release(),并清除引用计数,并调用 obj1->CleanupObject2 方法。

关于c++ - 从进程外 COM 服务器返回接口(interface)指针的正确方法是什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14345312/

29 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com