将 32 位 dll 转换为 64 位

Converting 32 bit dll to 64 bit

我不得不切换到 Office 64 位(2019,Professional Plus)。我有大量 VBA 脚本,其中大部分调用用普通 C 语言编写并使用非常旧的 Developer Studio 97 编译的旧 32 位 dll。我设法用 Visual Studio 重新编译它2019 作为 64 位 C++ dll,我遇到了 2 个问题:函数 MessageBox(和 MessageBoxA)被标记为“未定义”。解决方法:我暂时将它们替换为 OutputDebugStringA,DLL 编译正常。

从VBA调用函数,加载失败。感谢 ProcessorMonitor,我发现我的 dll 试图加载 VCRUNTIME140D.dll 和 UCRBASED.dll。我从互联网上下载了它们,我发现我必须将它们放在 C:\Program Files\Microsoft Office\root\Office16 中。但这还不够! VCRUNTIME140D.dll 也必须放在C:\WINDOWS\SYSTEM32!

那时,我的 DLL 作为 64 位 dll 可以正常工作。

接下来惊喜的是,重启后,由于缺少VCRUNTIME140_APP.dll,再次加载失败(请注意“140”后没有“D”)!下载并放置在 C:\Program Files\Microsoft Office\root\Office16 中,DLL 工作正常。

我试图将其编译为“静态”('Code Generation' -> 'runtime library' -> 'multithreaded' 而不是 'multithreaded dll')但我得到了错误: MSB8024 不支持使用静态版本的 C++ 运行时库。

我在某处读到 VCRUNTIME140 与 Visual Studio 2014 相关...很奇怪,但可能我也错过了那个版本的一些 .obj 以便静态 link?为什么我需要来自旧系统的元素?

回到 MessageBox 问题,我尝试了一个简单的 c++ 64 位控制台应用程序,完全相同的功能被接受并按预期工作,所以我猜是 header 文件中的一些 #ifdef 排除了dll中的声明。在我的 header 文件中移动了 MessageBox 声明,编译成功,但是(正如我猜测的那样)出现了 MessageBox 的 linker “未解析的外部”。

至此,我的问题是: - 是否可以创建 64 位 static .dll? - 是不是正常我必须从网上下载上面的3个dll,然后将它们复制到一些目录中? - 是否可以在 64 位 dll 中使用普通 MessageBox(句柄、文本、标题、按钮)?

谢谢。

最后,多亏了rustyx的直觉,我发现我用的是适合“app”开发的“Solution”。 (调用的 dll 名称中的字符串 _APP 表明了这一点!)我设法切换到“桌面”解决方案,现在加载的 dll 没有 _APP 后缀。 MessageBox 功能运行良好,无需在库中进行任何特定设置。

VCRUNTIME140D.DLL(调试版)和 VCRUNTIME140.DLL(发行版)存在于我安装的安装中,而它们 Visual Studio 的一部分2019 年(以及 2015 年和 2017 年)。

最后,现在可以在这种情况下生成静态 dll,VCRUNTIME140.DLL(以及更多)不会在运行时加载,但相同的代码是静态链接的。 Dumpbin 显示它。 动态链接: USER32.dll VCRUNTIME140.dll api-ms-win-crt-filesystem-l1-1-0.dll api-ms-win-crt-stdio-l1-1-0.dll api-ms-win-crt-heap-l1-1-0.dll api-ms-win-crt-string-l1-1-0.dll api-ms-win-crt-runtime-l1-1-0.dll KERNEL32.dll 静态链接: USER32.dll KERNEL32.dll

所有问题都解决了!