为什么使用 P/Invoke 调用 dll 时,某些计算机中的 LoadLibrary 失败?

Why is LoadLibrary failing in some machines when calling a dll using P/Invoke?

本文关键字:计算机 失败 LoadLibrary Invoke dll 调用 为什么      更新时间:2023-10-16

我有一个使用 P/Invoke 调用 C++ API 的 .NET 应用程序。C++ dll 具有来自第三方 dll 的依赖项。第三方dll调用LoadLibrary来动态加载libeay32.dll,这是一个OpenSSL依赖项。

经过几次测试,我发现.NET应用程序在Windows 10中正常工作,但在使用Windows 7的某些部署中失败。失败的原因是 .NET 进程未加载 libeay32.dll。我尝试将 libeay32.dll 放在与进程相同的目录中和系统文件夹中(牢记动态加载搜索顺序),但失败仅在 Windows 7 32 位中持续存在。此外,如果我从C++控制台应用程序调用 API dll,它可以在所有平台上正常工作。为了解决这个问题,我在 .NET 应用程序中调用了LoadLibrary,然后对 C++ API 进行 P/Invoke 调用,它适用于所有目标平台(Windows 10/7 32 位和 64 位)。

为什么LoadLibrary无法在Windows 7中加载libeay32.dll而不是Windows 10,如果从使用P/Invoke调用的API的C++dll依赖项调用?

编辑评论中的一些注释:

  1. 所有已编译的程序集都面向 x86 体系结构。
  2. 在发布问题之前,我验证了没有依赖项文件 在缺少的地方,使用依赖沃克。

可能是因为 dll 依赖于缺少的某些文件。使用依赖 walker 并查看它需要哪些文件。检查两个系统。该工具将以红色显示丢失的文件。不要盲目复制文件。查看它们是什么,部署它们所需的运行时或设置,并正确部署它们。

.Net 应用程序可以使用 AnyCPU 作为目标构建,并在 64 位和 32 位模式下运行,但如果您选择 AnyCPU 作为目标,操作系统将根据其偏好选择一个。如果您有本机依赖项,这可能意味着无法加载所依赖的库,因为您以错误的位数运行。如果可以将应用程序限制为您期望的位数,则可能会更好地工作。