我对Microsoft COM技术并不熟悉。简而言之,我在可执行文件foo.exe
中实现了Microsoft Out-of-process COM Server。环境是C ++和Microsoft基础类框架(MFC)。
有一个客户端bar.exe
,它使用foo.exe中的功能而不是Microsoft COM技术。在foo.exe中,涉及一些动态链接库,它还使用COM服务器foo.exe提供的功能(例如fooBar.dll
)。
到目前为止一切顺利。我正在寻找一种方法来确定COM服务器foo.exe的客户端是否在其他进程中,或者甚至在与foo.exe相同的进程中,例如上面示例中的fooBar.dll。有谁知道这样的方式?
修改
换句话说:显然COM服务器foo.exe
可以充当进程内或进程外的COM服务器。添加Hans Passant的评论和Joe Willcoxson的答案,他建议通过GetModuleHandle
来解决调用DLL,以确定COM服务器当前是否作为进程内服务器,以防我得到句柄如果我没有得到作为进程外服务器的句柄。因此,当COM服务器知道在同一进程中使用来自该服务器的功能的众所周知的DLL时,我们可以说COM服务器此时作为进程内服务器而在其他情况下作为外部服务器。 -process Server。我是否误解了某些事情或者这些考虑是否正确?
我目前的调查没有提及,所以我希望社区中有一位知道手推车如何运行的Microsoft COM专家。
非常感谢您的帮助!
答案 0 :(得分:1)
我不确定一旦你有一个COM指针你会怎么做。但是,有一种方法可以在创建对象时使用。
CoCreateInstance()
函数带有标记CLSCTX_INPROC_SERVER, CLSCTX_INPROC_HANDLER, CLSCTX_LOCAL_SERVER, CLSCTX_REMOTE_SERVER
。
当你使用ATL这样的东西时,通常默认的参数是组合标志,它只返回可用的东西。您可以单独尝试标记,看看是否使用特定标志创建了对象,而不是这样做。
我应该补充说,如果对象实际上是一个OLE对象/服务器,那就有一种方法。如果是这种情况,那么您可以查询IViewObject。如果它正在进行中,它就不会拥有该界面。如果它不在进程中,那么它将具有接口。
另一件事,如果对象实现了IRunnableObject并且你没有做任何事情来专门将它置于运行状态,那么进程内对象很可能处于运行状态,而进程外对象将不会在运行状态。
一个非常简单的黑客可能是使用DLL的名称调用GetModuleHandle()
。如果它返回一个句柄,那么它就在进程中。它不是通用解决方案,它要求您事先知道DLL的名称。
答案 1 :(得分:0)
在COM服务器foo.exe
中,您可以执行以下操作。
CTheApp::InitInstance()
{
[...]
bool runAsOutOfProcessServer = false;
CCommandLineInfo commandInfo;
ParseCommandLine(commandInfo);
if(commandInfo.m_bRunEmbedded || commandInfo.m_bRunAutomated)
{
runAsOutOfProcessServer = true;
}
[...]
if(runAsOUtOfProcessServer)
AfxMessageBox("Out of Process Invocation");
}
很明显CCommandLineInfo中有两个成员表示该进程是作为OLE自动化服务器启动的,或者是为了编辑嵌入式OLE项而启动的。使用ParseCommandLine,您可以通过引用本地变量commandInfo
来获取调用信息。然后,您可以检查是否设置了成员m_bRunEmbedded
或m_bRunAutomated
以确定foo.exe
中的COM服务器是否已启动。然后,只有当局部变量runAsOutOfProcessServer
为真时,您才能弹出消息框。