我如何列出从一个.so文件导出的符号?如果可能的话,我还想知道它们的来源(例如,如果它们是从静态库中提取的)。
我使用的是gcc 4.0.2,如果有区别的话。
我如何列出从一个.so文件导出的符号?如果可能的话,我还想知道它们的来源(例如,如果它们是从静态库中提取的)。
我使用的是gcc 4.0.2,如果有区别的话。
当前回答
如果你只是想知道是否有符号存在,你可以使用
objdump -h /path/to/object
或者列出调试信息
objdump -g /path/to/object
其他回答
我一直在想为什么-fvisibility=hidden和#pragma GCC可见性似乎没有任何影响,因为所有的符号都是用nm可见的-直到我发现这篇文章指向readelf和objdump,这让我意识到似乎实际上有两个符号表:
你可以用nm列出来 你可以用readelf和objdump列出
我认为前者包含可以用strip或-s开关剥离的调试符号,可以给链接器或安装命令。即使nm不再列出任何东西,导出的符号仍然会被导出,因为它们在ELF“动态符号表”中,也就是后者。
objdump -TC /usr/lib/libexample.so
对于Android .so文件,NDK工具链附带了其他答案中提到的所需工具:readelf, objdump和nm。
Nm -g列出了extern变量,这不是必要的导出符号。 任何非静态文件作用域变量(在C语言中)都是extern变量。
nm -D将在动态表中列出该符号,您可以通过dlsym找到它的地址。
nm -版本
GNU nm 2.17.50.0.6-12.el5 20061020
如果你的.so文件是elf格式的,你可以使用readelf程序从二进制文件中提取符号信息。这个命令会给你一个符号表:
readelf -Ws /usr/lib/libexample.so
你应该只提取在这个.so文件中定义的,而不是在它引用的库中。在本例中,第七列应该包含一个数字。你可以使用一个简单的正则表达式来提取它:
readelf -Ws /usr/lib/libstdc++.so.6 | grep '^\([[:space:]]\+[^[:space:]]\+\)\{6\}[[:space:]]\+[[:digit:]]\+'
或者如卡斯平所提议的:
readelf -Ws /usr/lib/libstdc++.so.6 | awk '{print $8}';