我们有一个应用程序依赖于许多第三方DLL组。 不幸的是,这些第三方DLL的编写者没有一个非常一致地命名它们,所以很难看出哪个DLL是什么组的一部分。
为了尝试和pipe理这个,我们希望将第三方DLL组放在应用程序文件夹的一个文件夹中,而不是像这样在应用程序旁边。
--> Application Folder --> Application.exe --> MyDLL1.dll --> MyDLL2.dll --> Third Party 1 DLL folder --> Third Party 1 DLL 1.dll --> Third Party 1 DLL 2.dll --> Third Party 1 DLL 3.dll --> Third Party 2 DLL folder --> Third Party 2 DLL 1.dll --> Third Party 2 DLL 2.dll --> Third Party 2 DLL 3.dll
我的问题是如何让dynamic链接器find它们并加载它们?
我们可以使用LoadLibrary()和GetProcAddress()来手动完成这个工作,但是这非常繁琐。 看起来我们可以用manifest和“probing”来做到这一点,但是这似乎只是Windows 7(我们需要在XP及更高版本上工作)。
更新
我们最后使用了清单来做这件事(谢谢@Chris) – 有一些其他的箍我们不得不跳过,以防有人在寻找解决scheme!
首先,我们的“汇编”实际上有几个DLL,我们链接到那个链接到其他链接。 所有这些DLL将需要程序集依赖项添加到它们的清单(您可以使用mt.exe来执行此操作,而无需访问这些DLL的源代码)。
其次,程序集需要与DLL并行,而不是与EXE一起 – 我们的DLL实际上是一个已经在应用程序的子文件夹中的插件。
这是我们的最终布局:
--> Application Folder --> Application.exe --> Plugins folder --> MyDLL1.dll --> Third Party 1 --> Third Party 1.manifest --> A.dll --> B.dll --> C.dll
如果MyDLL1.dll是链接到A.dll的插件,并且A.dll链接到B.dll和C.dll,则:
对我来说,(3)有点刺激。 你会认为链接器会在程序集中寻找依赖的DLL。
您可以在没有探测的情况下使用清单来完成。 通过定义包含dll的.manifests来创建“假”程序集。 (在这个dll中没有改变)因为程序集支持被添加到NT 5.1(Windows XP),Windows加载程序首先通过扫描带有程序集名称的文件夹来查找程序集。
因此,例如,如果您需要为您的应用程序分发Visual C 2008的Microsoft Visual C运行库,则可以创建如下所示的文件夹结构:
--> Application Folder --> Application.exe --> MyDll1.dll --> MyDll2.dll --> Microsoft.VC90.CRT --> Microsoft.VC90.CRT.manifest --> msvcr90.dll --> msvcp90.dll --> msvcm90.dll
这个相同的方案将适用于你的第三方DLL。 所有你需要做的就是将“假”程序集作为依赖程序集添加到应用程序的清单中(如果你的dll有清单,(他们访问第三方dll),那么清单也必须有条目。
描述程序集的清单文件需要一个assemblyIdentity和每个dll的文件节点:
<assembly manifestVersion="1.0"> <assemblyIdentity type="Win32" name="Assembly Name" version="1.0.0.0" processorArchitecture="x86" /> <file name="dll1.dll" /> <file name="dll2.dll" /> </assembly>
而你的应用程序和DLL是用MS Visual Studio 2005或更高版本构建的,下面的编译指示会让你的应用程序在程序集中查找dll:
#pragma comment(linker, "/manifestDependency:\"name='Assembly Name' processorArchitecture='*' version='1.0.0.0' type='win32' \"")
您可以使用SetDLLDirectory函数为您的DLL指定路径。 或者阅读有关使用应用程序特定路径的信息 。