如果你用GCC编译一个共享库并传递"-z defs"标志(我认为它只是盲目地传递给ld)那么你得到一个很好的报告,没有定义什么符号,并且ld失败(没有.so文件)被建造).另一方面,如果你没有指定"-z defs"或明确指定"-z nodefs"(默认值),那么即使缺少符号也会生成.so,但是你没有得到什么符号的报告如果有的话会失踪.
我想要两个!我想要创建.so,但我也想要报告任何缺少的符号.到目前为止,我知道这样做的唯一方法是运行两次,一次使用"-z defs",一次不使用.这意味着潜在的长链接阶段会完成两次,这将使编译/测试周期更加糟糕.
如果您想知道我的最终目标 - 在编译库时,本地目标文件中的未定义符号表示未指定应该在我的构建环境中的依赖项,而如果库中缺少某个符号,那么'链接不是一个错误(-l标志只给出了立即依赖,而不是依赖的依赖,在这个系统下).我需要列出"在文件中引用"的部分的报告,以便我可以看到符号是由本地对象引用还是被链接的库引用.--allow-shlib-undefined选项几乎修复了这个问题,但在链接静态库时它不起作用.
优先考虑适用于GNU和Solaris链接器的解决方案.
您可以在生成的.so文件中使用nm,而不是在链接期间使ld报告未定义的符号.例如:
nm --dynamic --undefined-only foo.so
Run Code Online (Sandbox Code Playgroud)
编辑:虽然我想这不会给你使用符号的源文件.抱歉,我错过了你的那部分问题.
您仍然可以使用nm作为近似解决方案,以及grep:
for sym in `nm --dynamic --undefined-only foo.so |cut -d' ' -f11 |c++filt -p` ; do
grep -o -e "\\<$sym\\>" *.cpp *.c *.h
done
Run Code Online (Sandbox Code Playgroud)
这可能与同名的本地符号等有问题.
来自GNU ld 2.15 NEWS文件: