我在VS2005中继承了一个相当大的C ++项目,它编译成一个大约5MB的DLL。我想减少库的大小,以便通过网络加速,以便从慢速网络共享中使用它的客户端。
我知道如何通过分析代码,包含和项目设置来做到这一点,但我想知道是否有任何可用的工具可以更容易地确定代码的哪些部分消耗最多的空间。有没有办法生成DLL布局的“配置文件”?关于库图像中消耗空间的内容和报告的数量的报告?
答案 0 :(得分:6)
构建DLL时,可以将/MAP传递给链接器,使其生成包含结果图像中所有符号地址的映射文件。您可能需要编写一些脚本来计算每个符号的大小。
使用"strings" utility扫描您的DLL可能会显示意外或未使用的可打印字符串(例如资源,RCS ID,__FILE__
宏,调试消息,断言等。)。
此外,如果您尚未使用/Os进行编译,则值得一试。
答案 1 :(得分:4)
如果您的最终目标只是调整DLL的大小,那么在调整编译器设置后,您可能会通过UPX运行DLL来获得最快的结果。 UPX是DLL和EXE的优秀压缩实用程序;它也是开源的,具有非病毒许可证,因此可以在商业/闭源产品中使用。
我只是在最高压缩设置(蛮力选项)上发出了病毒警告,所以如果你使用的设置低于此值,你可能会没问题。
答案 2 :(得分:3)
虽然我不知道任何二进制大小分析器,但您可以选择查找最大的目标文件(.obj) - 这至少可以让您了解问题点的位置。
当然,这需要一个足够模块化的项目。
答案 3 :(得分:1)
您也可以尝试静态链接而不是使用dll。实际上,当库静态链接时,链接器会从最终的exe中删除所有未使用的函数。有时最终的exe只会稍微大一点,而你没有任何dll。
答案 4 :(得分:1)
如果你的DLL很大,因为它导出的C ++函数具有特别长的错位名称,另一种方法是使用.DEF
文件按顺序导出函数,不带名称(使用NONAME
.DEF文件)。有点脆,但它减少了DLL大小,EXE大小和加载时间。
参见例如http://home.hiwaay.net/~georgech/WhitePapers/Exporting/Exp.htm
答案 5 :(得分:1)
假设您的所有.obj文件大小相同,假设您使用的是预编译头文件,请尝试创建一个空的obj文件并查看其大小。这将使您了解由于PCH编译而导致的每个.obj的比例。顺便说一句,链接器将能够删除那里的所有重复项。或者,您可以尝试禁用PCH,以便obj文件可以更好地指示主要罪魁祸首。
答案 6 :(得分:1)
所有好建议。我所做的是获取地图文件,然后只是眼球。我过去发现的那种事情是,大部分空间是由一个或多个类库引入的,因为某个变量在某处被声明为具有类似于它可以节省一些编码的类型努力,但并非真的有必要。
就像在MFC中一样(记得吗?),他们有一个包装类来绕过Win32提供的控件,字体等所有东西。那些占用大量空间而你并不总是需要它们。
另一件可能占用大量空间的东西是你可以管理的集合类。另一个是您不使用的cout I / O例程。
答案 7 :(得分:0)
我会推荐以下其中一项:
覆盖率 - 您可以运行一个覆盖工具,希望能够检测到一些死代码
缓存 - 在初始激活时缓存客户端的dll
拆分 - 将dll分成几个较小的dll,使用bootstrap dll启动应用程序并在应用程序启动后下载其他dll
编译和关联 - 使用较小的运行时库,使用大小优化进行编译等。有关更多建议,请参阅此link。
压缩 - 如果dll中有数据或大量资源,则只能在下载后或运行时压缩它们并解压缩。