.NET COM Callable Wrapper如何生成IID?

时间:2011-07-03 15:20:20

标签: .net c++-cli ccw

通过OLE / COM对象查看器查看由CCW创建的生成的TLB文件显示IID保持不变,除非我更改了界面的设计(这是正确的行为),我担心的是如果我编译同样的代码另一台机器将生成一个完全不同的IID,尽管接口没有改变,因此破坏了现有的COM客户端。

  1. COM Callable Wrapper如何生成COM接口ID?
  2. CCW如何知道界面是否已更改并需要生成新的IID?
  3. 在源文件中生成自己的并声明是否更安全?

1 个答案:

答案 0 :(得分:5)

类型的guid不是特定于COM互操作,所有.NET类型都有一个guid。您可以从Type.GUID属性获取它。生成它的CLR中的代码可从SSCLI20发行版中获得。您可以通过查看clr / scr / vm / methodtable.cpp,MethodTable :: GetGuid()方法中的代码来查看算法。

总结算法:

  • 如果类型具有[Guid]属性,则返回
  • 如果类型是接口类型,则生成接口类型定义的字符串化版本。这是由interoputil.cpp中的GetStringizedItfDef()完成的。它以完全限定的类型名称开头,并附加每个成员定义的字符串版本。
  • 对于所有其他类型,生成该类的字符串化版本。它以完全限定的类型名称开头,附加类名并附加完全限定的程序集名称。
  • 然后通过辅助函数CorGuidFromNameW()将生成的字符串散列到Guid中。

这足以回答您的问题:

  

COM Callable Wrapper如何生成COM接口ID?

它使用由上述算法生成的Type.GUID。算法中的所有元素都不是特定于它所执行的机器,因此您不必担心在不同的构建机器上获得不同的IID和CLSID。

  

CCW如何知道接口是否已更改并需要生成新的IID?

没有。它纯粹依赖于为不同的接口定义生成不同GUID的算法。

  

在源文件中生成自己的并声明是否更安全?

不是真的。此算法没有记录的故障模式。使用您自己的[Guid]属性会显着增加您在必要时忘记更改它的几率。这是经常采用的快捷方式,也是DLL Hell的主要来源。令人讨厌的那种,使客户端崩溃几乎不可能诊断硬件异常。与E_NOINTERFACE仍然很难但不是不可能的那种相反。依靠自动生成的Guid,我只能想到两个缺点:当您在重建它们之前忘记取消注册程序集时,它往往会导致您的开发计算机上的注册表污染。当你对COM错误进行故障排除时,它会让你慢下来,因为你不知道guid。无可否认,注册表污染对我来说是足够的理由。