C 为什么我的IUnknown释放函数会阻止我的子线程?

C 为什么我的IUnknown释放函数会阻止我的子线程?,c,com,ole,iunknown,C,Com,Ole,Iunknown,在我的C应用程序中,我有一个子线程,它在生命开始时检索IUnknown接口: static struct IUnknown* punk = NULL; void DispatcherStart(){ CoInitialize(NULL); CheckHRESULT(GetActiveObject(&MY_CLSID,NULL,&punk)); } 一切都很好,它被用来调用一些activeX函数,它可以工作!但是,当我的程序结束时,它会要求线程终止,因此我的线程

在我的C应用程序中,我有一个子线程,它在生命开始时检索IUnknown接口:

static struct IUnknown* punk = NULL;

void DispatcherStart(){
    CoInitialize(NULL);
    CheckHRESULT(GetActiveObject(&MY_CLSID,NULL,&punk));
}
一切都很好,它被用来调用一些activeX函数,它可以工作!但是,当我的程序结束时,它会要求线程终止,因此我的线程调用是结束函数的:

void DispatcherStop(){
    if(punk) (punk)->lpVtbl->Release(punk); // BLOCK here
    punk = NULL;
    CoUninitialize();
}
我的thead永远不会回来,因为IUnknow ptr上的释放会阻止它。(如果我删除了释放,那么conInitialize()块也会被删除)


我做错了什么?(朋克初始化无法在主线程中完成)

如果没有消息泵,执行
协同初始化的线程将失败。所以使用
coinitializex(NULL,COINIT\u多线程)如果线程没有自己的线程。
但后一种情况仅适用于mta com。
这并不意味着您只需将
CoInitialize
更改为
coinitializex..


mta com应该有自己的基础。你应该提供它。就像我在那里做的那样

没有太多的信息可供参考。根据我的经验,GetActiveObject()通常是为进程外对象调用的。对于进程外对象,我认为您的Release()将被阻止,直到超时…可能是30秒。超时后,它将返回。我注意到GetActiveObject()是在oleauto.h中声明的。一般来说,CoInitialize()和OleInitialize()之间没有太大区别,但可能有一些区别。我可能会尝试使用OLE函数OleInitialize(NULL)和Oleunizaize()而不是“Co”版本。@JosephWillcoxson感谢您的帮助,OLE和Co版本之间没有区别。两者都阻止我的线程,我必须设置一个超时来正确关闭我的应用程序。@JosephWillcoxson确实没有太多信息。目前我的代码非常简单。我的线程通过oleInit/CoInit初始化OLE,然后直接初始化。为了提供更多的上下文,我正在编写一个基本代码,该代码初始化ActiveX服务器,然后启动连接到此ActiveX服务器的子线程。当它结束时,我的线程在释放activeX serveur之前被释放。如果我尝试从主线程初始化我的IUnknown ptr,那么一些activeX函数什么都不做(所有在GUI上工作的activeX函数)和一些工作。某些操作(如剪贴板、拖放等)需要使用release和OleUninit,并且不阻塞Oleunialize。您的案例中似乎不需要这些操作。像您这样的STA线程(由CoInitialize启动)必须泵送一个消息循环。您的释放呼叫会将消息发送到一个消息循环,而该消息循环(似乎)不会传递消息。