我在VS 2005中为本机Win32 /非托管C ++创建了一个DLL项目,称之为myProj.dll。这取决于第三方商业DLL,而后者依赖于msvcr90.dll(我假设它是从VS 2008项目构建的)。我将其称为thirdParty.dll。
我的DLL项目在VS2005中构建得很好。我已经构建了一个链接到myProj.lib的测试应用程序(同样,VS 2005 Win32 C ++)。 (顺便说一句,根据.lib的小尺寸来判断,并且在运行时,应用程序必须找到myProj.dll,我猜测.lib只是一个调用的包装器。 loadLibrary()加载实际的DLL;是关闭吗?)
我的问题是,在运行时,测试应用程序无法找到msvcr90.dll(也不是msvcp90.dll),其依赖源于thirdParty.dll。
我已经安装了Microsoft的redist包,所以在c:\ WINDOWS \ WinSxS \ x86_Microsoft.VC90.CRT _...中安装了所有std(9.0)C ++库。更重要的是,如果我将依赖性walker指向thirdParty.dll,它会愉快地解析对该位置的引用。
但是,如果我将depends.exe指向我的测试应用程序(.exe)或myProj.dll,则找不到msvcr90.dll和msvcp90.dll。
我猜我需要在VS2005中配置一些东西,以便.exe或myProj.dll知道std C ++库的9.0版本的位置(大概是redist包在C:中安装它们的位置) WINDOWS \ WinSxS),但我似乎无法弄清楚它是什么。我是在正确的轨道上吗?
我注意到,如果我只是将msvc * 90.dll文件复制到我的app目录,那么依赖项就解决了,但是我得到了关于std c ++ DLL等的不正确加载的运行时错误。
非常感谢。
答案 0 :(得分:6)
这看起来像是一个“并排组件”问题。
据我所知,微软试图阻止过去几年的 DLL Hell 问题,引入了“并排组件”的概念。
在坚果外壳中,这意味着您的应用需要告诉 Windows 它设计用于哪种版本的 CRT 。安装应用程序时,Windows将确保您的应用程序获得这些DLL文件的私有副本。
要完成所有工作,您需要将应用程序的DLL依赖项嵌入到应用程序 Manifest 文件中,并使用清单工具将其附加到项目中,输入应用程序项目设置的输出部分。
这里的示例是我用于Zeus for Windows IDE的清单:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">
<assemblyIdentity
name="Xidicone.Windows.Zeus for Windows"
version="3.9.6.69"
processorArchitecture="X86"
type="win32" />
<description>Zeus for Windows</description>
<dependency>
<dependentAssembly>
<assemblyIdentity
type="win32"
name="Microsoft.VC80.CRT"
version="8.0.50608.0"
processorArchitecture="x86"
publicKeyToken="1fc8b3b9a1e18e3b" />
</dependentAssembly>
</dependency>
<dependency>
<dependentAssembly>
<assemblyIdentity
type="win32"
name="Microsoft.Windows.Common-Controls"
version="6.0.0.0"
processorArchitecture="X86"
publicKeyToken="6595b64144ccf1df"
language="*" />
</dependentAssembly>
</dependency>
</assembly>
最后,如果您计划制作安装程序,则需要将这些DLL文件的相同版本添加到应用程序安装程序,或者让安装程序运行Microsoft CRT可再发行组件安装程序。
FWIW当用户报告由于缺少MSVCRT运行时DLL文件而导致Zeus不再在Windows XP上运行时,我才发现这一点,但Zeus已经正常工作超过10年没有曾经不得不附带一个MSVCRT运行时DLL文件。
答案 1 :(得分:2)
您是否安装了msvc 2008 redist的SP1 version?
如果depends.exe无法找到msvcr90.dll,则不会出现问题,如果您使用的是Microsoft软件安装程序,它会自动安装在正确的位置,如果您的应用程序运行,则会找到它。如果您不创建清单,则将dll复制到应用程序目录中无效。
但是你能说出你得到的确切错误信息吗?
答案 2 :(得分:1)
我会问第三方dll人这个问题。
答案 3 :(得分:0)
前几天我遇到了同样的问题。 myProj.dll依赖于使用msvcr90的thirdParty.dll。如果我直接使用myProj.dll构建一个test.exe,那就可以了。但是如果我在test.exe中使用loadLibrary(myProj.dll),则调用将失败。如果我在Java程序中尝试loadLibrary(myProj.dll),也会发生同样的情况。
经过对互联网的一些调查和研究,以下步骤解决了我的问题。
确保PATH上没有msvcr90。 您可以使用进程资源管理器(SystemInternals的procexp.exe)来查找当前在您的环境中加载的所有msvcr90。事实上,从VC 2005开始,C运行时库只应安装在全局程序集缓存(\ winsxs ....)中,甚至不应安装在windows或windows \ system32下。
将dll清单嵌入myProj.dll中。 在cl.exe和link.exe生成myProj.dll之后,还会生成相应的清单。 然后使用mt.exe -inputresource myProj.dll.manifest -out myProj.dll; 2
以上解决了我的问题,希望它对你有任何帮助。 顺便说一句,我在Windows 2008 R下使用VC 2008