从 64 位代码访问 32 位 DLL

Accessing 32-bit DLLs from 64-bit code(从 64 位代码访问 32 位 DLL)

本文介绍了从 64 位代码访问 32 位 DLL的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我需要迁移 32 位 dll 才能在 64 位 C#(以及 C++)应用程序中使用它.dll 是用非托管的 delphi 代码编写的.我无法重新编译 dll,唯一的方法是使用进程间通信 (IPC).我搜索了很长时间,但我发现的信息并不多.我找到的最佳指南在此链接中:从 64 位代码访问 32 位 DLL.

I need to migrate a 32bit dll in order to use it in a 64bit C# (and also C++) applications. The dll is write in unmanaged delphi code. I can't recompile the dll and the only way is to use the interprocess communication (IPC). I search for a long time but i found not many information about. The best guide i found is in this link: Accessing 32-bit DLLs from 64-bit code.

我遵循本指南来实现我的目标,因为这个论坛经常被引用.所以指南解释我必须做三个步骤:

I followed this guide for achieve my goal because very often is quoted in this forum. So the guide explain I have to make three steps:

1° STEP - 创建一个实现 COM 对象的 32 位组件,该组件加载和调用 32 位 DLL,并将 32 位 DLL 接口公开为 COM 接口.所以我做了与解释相同的事情 这里(示例取自上一个链接):

1° STEP - Create a 32-bit component implementing a COM object which loads and calls into the 32-bit DLL, and exposes the 32-bit DLL interface as a COM interface. So I made the same thing as explained here (example taken from previous link):

[ComVisible(true), GuidAttribute("137AD71F-4657-4362-B9E4-C6D734F1F530")]
[InterfaceType(ComInterfaceType.InterfaceIsDual)]
public interface IGetMyString
{
   string GetMyString();
}

[ComVisible(true), GuidAttribute("89BB4535-5A89-43a0-89C5-19A4697E5C5C")]
[ProgId("CallPDW.Class1")]
[ClassInterface(ClassInterfaceType.None)]
public class Class1 : IGetMyString
{
    string GetMyString()
    {
      ......
    }
}

然后我必须注册 .NET COM 程序集,因此我必须使用 Regasm.exe,但我创建了 Visual Studio 安装和部署项目,该项目构建一个 MSI 文件并进行与 Regasm 相同的操作.然后我控制了注册表编辑器,我找到了 HKEY,所以它可以工作.所以直到这一步一切正常或似乎没问题.

Then i have to register the .NET COM assembly so i have to use Regasm.exe, but instead I created Visual Studio Setup and Deployment project that builds an MSI file and make the same things Regasm do. Then i controlled the Registry Editor and I found the HKEYs so it works. So until this step all is ok or seems to be ok.

2° STEP - 通过创建标准 COM+ OOP 应用程序(使用 dllhost 作为代理进程)来为进程外 (OOP) 配置此 COM 组件;

2° STEP - Configure this COM components for out-of-process (OOP) by either creating a standard COM+ OOP application (using dllhost as the surrogate process);

3° STEP - 创建一个 64 位包装 DLL,它实现与原始的32位DLL,导入上面创建的COM对象的COM接口,将当前对公开接口的调用转换为对 COM 对象接口的调用,传输调用参数,接收返回值和委托他们给来电者;

3° STEP - Create a 64-bit wrapper DLL which implements the same interface as the original 32-bit DLL, imports the COM interface of the COM object created above, translates current calls to the exposed interface into calls to the COM object interface, transfers the call parameters, receives return values and delegates them to the callers;

问题在于 2° 和 3° 步骤我不知道如何实现,因为我在网络或论坛上没有找到任何关于此的内容.所以我需要帮助来实现步骤 2° 和 3°.也可以链接到其他帖子等.提前致谢.

The problem is that the 2° and the 3° STEPs I have no idea how to achieve because I don't found anything on the web or in the forum about this. So I need help to achieve step 2° and 3°. Is ok also some link to other posts etc. Thanks in advance.

其他信息(2016 年 12 月 10 日 - 晚上 11:10):此 DLL 通过两个接口将其功能暴露给 32 位本机环境:1.) 带有函数指针的 C/C++ 标头 (WINAPI*)2.) 带有 P/Invoke 的 .NET 接口

OTHER INFORMATIONS (12/10/2016 - 11:10 PM): This DLL expose its functions to the 32bit native environment through two interfaces: 1.) a C/C++ header with function pointers (WINAPI*) 2.) a .NET interface with P/Invoke

推荐答案

你在正确的轨道上.您已经创建并注册了一个 COM 可见包装 DLL,这是公开 Delphi 库的方法所必需的.

You're on the right track. You've already created and registered a COM visible wrapper DLL, which is necessary to expose the methods of your Delphi library.

由于您的 x64 进程无法调用此 x86 包装器,因此需要代理进程.但是,如果您不打算使用它的任何服务,那么将您的 DLL 转换为完整的 COM+ 服务器是没有意义的.

Since your x64 process can't call into this x86 wrapper, there's the need for a surrogate process. However, it makes little sense to transform your DLL to a full fledged COM+ server, if you're not going to use any of its services.

相反,我建议将您的包装 DLL 托管到默认的 COM 代理中.为此,请调用基于 x86 的 OLE/COM 对象查看器,它是 Windows SDK 的一部分.展开所有对象"节点并选择您的 COM 可见类.从那里,切换到实施"选项卡并选中使用代理过程".切换到注册表"选项卡并确认AppID"节点现在包含 [DllSurrogate] 条目.注意:如果您需要自动执行此步骤,您需要自己手动或通过设置过程将适当的值写入注册表.

Instead, I'd recommend hosting your wrapper DLL into the default COM surrogate. To do so, invoke the x86 based OLE/COM Object Viewer, which is part of the Windows SDK. Expand the "All Objects" node and select your COM visible class. From there, switch to the "Implementation" tab and check "Use Surrogate Process". Switch to the "Registry" tab and confirm that the "AppID" node now contains a [DllSurrogate] entry. Note: if you need to automate this step, you'll need to write the appropriate values to the registry yourself, either manually or via your setup procedure.

您现在应该能够从您的 x64 主机创建 COM 可见包装类的实例.

You should now be able to create an instance of the COM visible wrapper class from your x64 host.

这篇关于从 64 位代码访问 32 位 DLL的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持编程学习网!

本文标题为:从 64 位代码访问 32 位 DLL

基础教程推荐