剥离Windows DLL调试信息?

时间:2008-10-09 18:44:28

标签: windows dll

我通常不参与Windows开发,并且完全不熟悉工具链和构建系统。我的嵌入式产品包括来自其文件系统中第三方的一些Windows DLL(由安装文件系统的Windows机器使用)。

我遇到了一个问题:与以前的版本相比,这些DLL的最新版本大小增加了三倍,并且它们不再适合文件系统。 DLL的功能没有太多变化,所以我怀疑开发人员只是忘了在这个drop中删除调试符号。我会问他们,但由于时区和语言的不同,得到答案通常需要几天时间。

有人可以使用简单的步骤向不熟悉VisualC的人解释如何确定DLL是否仍包含调试信息以及如何将其删除?

5 个答案:

答案 0 :(得分:5)

通常,调试信息本身是作为单独的*.pdb文件(Program DataBase)构建的,而不是像在unix中一样附加到二进制文件中。如果开发人员确实构建了库的调试版本,则更严重的问题可能是依赖关系。如果二进制文件的发布版本链接到MSVCRT.DLL,则调试版本将链接到MSVCRTD.DLL(其他运行时库类似地用D后缀命名)。要查找特定二进制文件的依赖项,请尝试:

dumpbin /imports whatever.dll

这将显示库whatever.dll的所有运行时依赖项(请注意,列出了这些库中的库名称和符号)。如果您没有看到预期的依赖项列表,则可能只有通过让原始开发人员以正确的构建模式重建库来解决问题。

答案 1 :(得分:5)

Rebase是微软工具集的一部分。除了设置dll的基址之外,它还可以将任何附加的调试信息删除到单独的.dbg文件中。

rebase -i 0x10000000 -a -x。\ -p

理论上,您应该尝试确定dll是否已构建到唯一的基址并使用它。或者,选择一个基址来最小化与应用程序使用的任何其他dll发生冲突的可能性,以便Windows在加载时不必修补dll。在一个装载程序通常将模块的加载地址随机化为安全功能的时代,我不确定它是否值得特别设置基址的麻烦。

答案 2 :(得分:3)

您希望从开发人员那里获得发布版本,即使这很痛苦,因为调试版本默认情况下编译时禁用了代码优化。因此,即使您以某种方式删除了调试信息,您也会留下尽可能无效的代码。 (更不用说那里的调试陷阱和消息了。)

至于确定您拥有哪种DLL,您可以使用Dependency Walker来查看您的DLL是否链接到VC运行时库的调试版或发行版(假设这些库没有静态链接。 )

答案 3 :(得分:2)

Dependency walker确实显示了依赖关系,但没有显示调试信息是否已被剥离。使用PeStudio查看两者。

答案 4 :(得分:0)

暂时忽略其他建议,例如获取发布版本,这是有效的。开发人员正在寻找的工具实际上是来自Visual Studio(或SDK或WDK)的link.exe

如果他们希望您能够将调试器与其代码一起使用,则可以为您创建公共PDB文件。他们想要使用的选项是:

  /PDB:filename
  /PDBSTRIPPED:filename

然而,我担心你自己不能做很多事情。 PDB文件本身是单独的文件,调试信息通常不会包含在现代MS编译器的二进制文件中(尽管可能包含一些RTTI内容,更不用说{{1}的文件名和字符串了。和类似的宏和“函数” - 这是对感知臃肿的最可能的解释。)

注意:来自WDK的ASSERT提供与上述标志相同的功能,但有一些更复杂的(虽然适合WDK构建过程)语法。