分析共享库是否存在重复代码链接

Analyzing shared libraries for duplicate code linkage

本文关键字:代码 链接 存在 是否 共享      更新时间:2023-10-16

我们有一个大型代码库,其中包含>40个项目(VS术语),创建了多个DLL/SO(~15)和一个EXE。

有一些实用工具项目以静态链接方式创建 EXE,并且也被大多数 DLL 使用。理想情况下,我们希望这些实用工具项目也是 DLL,这样代码就不会在依赖于它们的每个 DLL 中重复。

是否有任何工具可以对 DLL 进行二进制分析以查看存在多少重复(代码 + 数据)?对此进行估计会有所帮助。

没有工具,只有你耳朵之间的工具。 您希望专注于链接静态库的项目,请查找多次使用同一静态库的项目。 这是假设一个函数可以多次链接的起点。

然后,您可以使用链接器的/VERBOSE 选项,它显示哪些函数正在从静态库中链接。 该选项有很多输出,但它简短且易于解析。

或者,请考虑使用链接器的/MAP 选项生成 .map 文件。 它详细显示了哪些函数被链接到最终可执行文件中。 让相同的函数在不同的 .map 文件中多次出现是您的线索,将其放在 DLL 中可能会有所帮助。 用您喜欢的脚本语言编写一个小程序来处理/VERBOSE 输出或 .map 文件并查找匹配项是可行的。

好吧,在Unix/Linux/OSX系统上,你会做类似的事情

for eachfile in *.exe *.dll ; do
    nm $eachfile | sort | uniq > $eachfile.symbols.txt
done
cat *.symbols.txt | sort | uniq -c > count-duplicate-symbols.txt
sort -r count-duplicate-symbols.txt | less

前三行说"从每个.exe中转储符号,并在当前目录中.dll文件;将每个转储存储在单独的文件中。顺便说一下,如果同一行在单个文件中多次出现,只需存储一次即可。

cat 开头的行表示"计算每行在我们刚刚生成的所有文件中出现的次数。编写一个名为 count-duplicate-symbols.txt 的新文件,其中包含重复的行及其计数。

最后一行说"按重复项数(按递增顺序)对该文件进行排序,并将其通过管道传输到终端,以便我可以读取它。

如果您想查看哪些源文件包含有问题的重复符号,您可以使用grep

请注意,此方法可能不适用于static符号(函数和变量),并且可能会对应该随处可见的内联函数之类的内容产生误报。您可以过滤掉出现在linkonce部分中的符号,使用c++filt等美化输出。

其中一些工具绝对可用于Windows。我不知道他们是否都是。