在C / C ++应用程序中分析过多代码大小的一些技术或工具是什么?
我有一个C ++库,可以生成更大的代码,我真的希望它能做什么。 从少于50K行的源代码中,我得到几乎4MB的共享对象和9个静态存档。这是有问题的,因为库的二进制文件非常大,而且更糟糕的是,甚至连接它的简单应用程序通常也会增加500到1000 KB代码大小。 用像-Os这样的标志来编译这个库会有所帮助,但并不是非常有用。
我也尝试过使用GCC的-frepo命令(尽管我看过的所有文档都表明,在Linux上collect2会合并重复的模板),并且模板上的显式模板实例化看起来“很可能”被重复了很多,但没有在任何情况下都有实际效果 当然,我会说“可能”,因为就像任何类型的分析一样,这样的盲目猜测几乎总是错误的。
是否有一些工具可以轻松分析代码大小,或者我可以找出占用这么多空间的东西,或者更一般地说,我应该尝试其他任何东西? 在Linux下工作的东西将是理想的,但我会尽我所能。
如果你想知道你的可执行文件是什么,那么问问你的工具。 打开ld链接器的--print-map(或-M)选项以生成一个映射文件,其中显示了它在内存中的位置以及位置。 为静态链接的例子做这些可能会提供更多的信息。
如果你不是直接调用ld,而只是通过gcc命令行,那么你可以通过在-Wl,
前面加上ld来从gcc命令行传递ld特定的选项。
在Linux上,链接器当然会合并多个模板实例。
确保你没有测量调试二进制文件(调试信息可能占用最终二进制大小的75%以上)。
以减少最终的二进制大小的一种方法是用编译-ffunction-sections
和-fdata-sections
,然后用链接-Wl,--gc-sections
。
如果您使用[gold][1]
开发版本(新的仅ELF链接器,binutils的一部分),并且与-Wl,--icf
链接,则可能会有更大的缩减(我们已经看到25%)。
另一个有用的技术是通过__attribute__((visibility(...)))
或使用链接器脚本来减少由共享库“导出”的一组符号(所有内容都默认导出)。 详细信息在这里(见“出口控制”)。
一种非常粗糙但非常快速的方法是查看目标文件的大小。 并非所有对象文件中的代码都将被编译为最终的二进制文件,因此可能会有一些误报,但它可以给出关于热点位置的良好印象。 一旦找到最大的目标文件,就可以使用objdump
和nm
等工具深入研究它们。
上一篇: What are some techniques or tools for profiling excessive code size in C/C++ applications?
下一篇: What are some best practices for reducing memory usage in C?