我正在使用引用非托管 dll 的托管 DLL。我在/External/foo/ 目录下添加了非托管 dll ,并将“复制到输出目录”更改为始终。
问题是 dll 被复制到outputDir/External/foo目录,当运行时试图找到它时,它失败并出现以下错误:“无法加载 dll:找不到模块”
当我将它直接复制到输出目录时,一切正常。
如何设置项目运行时在输出目录的子目录中搜索?
谢谢!
我正在使用引用非托管 dll 的托管 DLL。我在/External/foo/ 目录下添加了非托管 dll ,并将“复制到输出目录”更改为始终。
问题是 dll 被复制到outputDir/External/foo目录,当运行时试图找到它时,它失败并出现以下错误:“无法加载 dll:找不到模块”
当我将它直接复制到输出目录时,一切正常。
如何设置项目运行时在输出目录的子目录中搜索?
谢谢!
您不想这样做,DLL Search Hell 是您想要避免的。Windows 在查找 DLL 的位置方面非常不灵活。理所当然,DLL Hell 没什么好惹的。非托管 DLL 的唯一好地方是与您的 EXE 在同一目录中。如果您不想将 DLL 存储在项目目录中,因此复制它们非常容易,那么您将需要一个使用 xcopy.exe 将 DLL 复制到输出目录的构建后事件。
替代品并不漂亮。如果此 DLL 是隐式加载的,那么唯一的选择是使用安装程序将目录添加到系统的 PATH 环境变量中。这是一个非常糟糕的主意,太容易让您的程序崩溃。如果使用 LoadLibrary 或 pinvoke 声明显式加载它,那么您有更有吸引力的选择,因为您可以在需要 DLL 之前更改 Main() 方法中的搜索路径。使用 Environment.SetEnvironmentVariable() 或 pinvoke SetDllDirectory() 将路径附加到 PATH 环境变量的本地副本。请注意,您也有部署问题,有人将不得不创建此子目录并将 DLL 复制到用户计算机上。不这样做的所有重要理由。
这是我们在上一个项目中所做的事情。编写一个批处理文件,将此非托管 dll 复制到输出目录。每次程序编译时调用批处理文件。您也可以使用配置键控制批处理文件的调用。所以它基于配置键值 true/false 运行。我希望这有帮助