.NET Framework(v 4.0)从Win32 C ++应用程序

时间:2016-10-11 16:33:40

标签: c# c++ com registration-free-com

我需要在.Net Framework c#中创建一个免注册的COM对象。 我跟着msdn演练https://msdn.microsoft.com/en-us/library/ms973915.aspx。我要处理它,因为,或者它不够清楚,或者它不正确,但这是一个旧帖子,我在Windows 10上使用Visual Studio 2015,所以可能有些东西被改变了。 下面是我为使其发挥作用而采取的步骤

  1. 编译COM C#dll SideBySide.dll(Target Framework 2.0)当然 我没有用regasm注册它

  2. 我没有使用教程中描述的方法,似乎对我不起作用。我在这里通过mt.exe创建SideBySide.Manifest命令

    mt -outputresource:“” - 显示“”

  3. 我手动修改了生成的清单,删除了所有无用的标签,并在下面的修改后的清单中添加了强制标签

      <assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">
    <assemblyIdentity
        name="SideBySide"
        version="1.0.0.0"
        type="win32" />
        <clrClass
                  clsid="{4B72FC46-C543-4101-80DB-7777848D1357}"
                  progid="SideBySide.SideBySideClass"
                  threadingModel="Both"
                  name="SideBySide.SideBySideClass"
                  runtimeVersion="v2.0.50727">
        </clrClass>
        <file name="SideBySide.dll">
     </file>
    

  4. 我已使用命令

  5. 向SideBySide.dll添加了清单

    mt -outputresource:“” - 显示“SideBySide.manifest”

    1. 我使用tlbexp从SideBySide .Net dll导出了tlb

    2. 我在配置属性中设置了 - &gt;清单工具 - &gt;嵌入c ++客户端的清单

    3. 我编译了client.exe,然后我将更改应用于che client.exe.manifest文件。以下是修改过的清单

      <assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0"> <assemblyIdentity type = "win32" name = "client" version = "1.0.0.0" /> <dependency> <dependentAssembly> <assemblyIdentity type="win32" name="SideBySide" version="1.0.0.0" /> </dependentAssembly> </dependency> </assembly>

    4. 它运行良好,似乎我可以从本机c ++应用程序中使用.Net Framework COM接口。然而,有一个问题,然后当我调用CreateInstance

      时,我尝试使用.Net Framework 4.0或更新版本编译SideBySide
      ISideBySideClassPtr ptr;
      HRESULT hr = ptr.CreateInstance(__uuidof(SideBySideClass));
      

      发生此错误: 0x8013101b:此程序集由比当前加载的运行时更新的运行时构建,无法加载。当然我已经尝试执行上面列出的所有步骤,我还尝试在dll的清单中指定运行时版本,但它没有用。我还看过这篇文章https://blogs.msdn.microsoft.com/dsnotes/2012/08/10/error-0x8013101b-when-doing-a-registration-free-com-activation/ 问题是一样的但是解决方案在我看来不适合我,因为我需要从本地客户端调用c#COM。

      有一些解决方法可以应用,或者我需要另一种方法解决我的问题

2 个答案:

答案 0 :(得分:1)

我很晚才感激这一点,但对于遇到这个问题的其他人来说......

我今天早些时候遇到过这个问题。我的注册免费COM库是用.Net 4.5.2构建的,我的解决方案是使用“runtimeVersion”属性,如下所示

<clrClass 
   clsid="{...}" 
   progid="Library.Name" 
   threadingModel="Both" 
   name="Library.Name.Class"
   runtimeVersion="v4.0.30319">

或者,您可以省略runtimeVersion属性(或指定v2.0.50272)并为.Net 3.5编译库。这两种解决方案似乎都可以解决问题。

答案 1 :(得分:0)

我只是在猜测,但你说清单文件中的运行时版本是2.0.50727,但是你在使用4进行编译时遇到了问题?您的清单和工具的版本不匹配。

我只是使用清单工具在我的程序集中创建和存储信息(在PostBuild步骤中):

"$(PathToYourTools)\mt.exe" -managedassemblyname:$(TargetPath) -nodependency -outputresource:$(TargetPath);#2

它的另一个好处是不需要为.NET程序集生成类型库。