仅将ATL exe服务器限制为一个进程(实例)

时间:2011-02-13 20:02:33

标签: visual-studio-2010 com process atl single-instance

我有一个用C ++编写的ATL exe服务器(Visual Studio 2010,合并了proxy-stud dll)。可执行文件是针对Windows 7 x86& 64。两种体系结构都发生以下情况:

ATL exe服务器应该作为“服务器进程”运行,即每台机器应该存在一个进程(MyATLServer.exe,只有一个!),并且许多客户端(让它保持简单:在同一台机器上)正在消耗来自它的COM对象。服务器通过使用服务器公开的COM对象来保存应用程序状态(在内存中),并且所有客户端都应“共享”此状态。

exe服务器通常在系统启动时启动,因为它由COM调用调用以创建其中一个托管对象。该调用源自spoolsv.exe进程(打印后台处理程序服务)。这会导致服务器进程在“SYSTEM”用户下运行(我猜是因为spoolsv.exe以'SYSTEM'运行)。

当其中一个客户端从ATL服务器创建COM对象时,另一个进程(MyATLServer.exe再次)被实例化(在登录到Windows的用户下运行),因此,它无法与“原始”共享应用程序状态“一个(在'SYSTEM'下运行)。第二个客户端将连接到登录用户实例化的客户端(“第二个”)。

在网上搜索了无数的论坛后,我得到了以下结论:

1)我的ATL服务器使用默认(由VS2010自动生成)ATL-Module,它继承自ATL :: CAtlExeModuleT<>。深入研究ATL标题我肯定这个模块使用正确的标志调用AtlComModuleRegisterClassObjects进行这种使用(dwClsContext = CLSCTX_LOCAL_SERVER,flags = REGCLS_MULTIPLEUSE | REGCLS_SUSPENDED)。所以它统治了这个。

2)使用start - >跑 - > dcomcnfg - > DCOM配置 - > MyATLServer - >属性我在“身份”选项卡下设置了“此用户”选项(使用本地管理员用户)。在“位置”选项卡中,未选中“在此计算机上运行应用程序”选项并显示为灰色。这导致我再次搜索,我来到这里:http://social.technet.microsoft.com/Forums/en-US/w7itprosecurity/thread/4f63ee11-e472-40f9-85db-a6b235d7579c。 该链接解释了dcomcnfg实用程序的x64版本是错误的,并且应该在x64 Windows上使用它的32位版本(start-> run->'mmc comexp.msc / 32')。在两个系统(每个系统中的一个)上检查后,我发现“在此计算机上运行应用程序”选项显示为灰色,而且两者都未选中。

从这一点开始,我完全迷失了(试图压抑挫折...... :-))。 我在正确的道路上吗?有没有人这样做过?

或原始意图 - 如何使我的ATL exe服务器“单独处理”?

谢谢!

欧米

1 个答案:

答案 0 :(得分:2)

好的......所以最后我要回答自己: - )

我已经找到了一些时间来尝试再次解决这个问题(并再次......)。 设置了2个不同的新开发机器(Win7x86和Win7x64)并仅使用32位版本的dcomcnfg - 一台机器正常工作,32位机器(Win7x86)!

深入研究“非工作”机器,我发现我遇到了GUID地狱!在x64 dev机器上,COM对象使用与代码文件中的值(生成代码)不同的GUID进行注册。为了使它变得更加困难,我使用了连接点,这些连接点也注册了无效的GUID。我的意思是 - 注册表中的GUID值不正确!到目前为止,我不知道为什么会发生这种情况,但我100%确定VS2010中的COM向导是错误的(生成部分代码,如果有的话......),这些向导生成的代码可能会导致注册问题。 / p>

要解决此问题,我手动删除了ATL服务器的所有相关注册表项,取消了VS项目中的自动COM注册并自行注册了EXE(在x64上使用%WINDIR%\ SysWOW64 \ cmd.exe控制台,而不是本机x64)。

手动注册服务器后,所有工作正常(正如预期的那样,单个进程,在多个客户端之间共享)并且dcomcnfg配置实用程序中没有灰色复选框。

我确信这个解决方案有很多无法解释的差距,但它对我有用(现在......)。

干杯; - )