裸机场景下,如何查看GCC静态链接的库及程序依赖的外部库?
问题描述
我有一个希望在裸机(SystemC模型中)运行的C程序,这意味着无法依赖操作系统或任何共享库。我已自行编写适配裸机的文件输入输出例程,并采用静态链接编译:
gcc -static my_app.c -o my_app
但运行程序时,它进入.iplt段后似乎陷入无限循环,我怀疑它试图跳转到未正确加载至内存的函数表(因无操作系统进行管理)。我的问题是:编译完成后,如何判断哪些库已成功静态链接(属于二进制文件本身),以及程序依赖操作系统提供的哪些外部库?是否存在链接器生成的可查看报告?
解决方法
一、检查静态链接内容与外部依赖
可以通过以下工具直接分析生成的二进制文件:
readelf工具:- 查看所有符号状态:执行
readelf -s my_app,输出中标记为UND的是未定义的外部符号(即依赖外部系统/库的部分),其余非UND的符号均已被静态链接到二进制文件中。 - 检查动态依赖:执行
readelf -d my_app,如果是完全静态编译的程序,输出中不应包含Dynamic section相关内容;若存在,则说明仍有未处理的动态依赖。
- 查看所有符号状态:执行
nm工具:
执行nm my_app,同样通过UND标记识别未定义的外部依赖,其他符号均为已静态嵌入的内容。
二、生成链接器详细报告
编译时添加链接器参数-Wl,--verbose,即可输出完整的链接过程日志,包括:
- 链接器搜索的静态库路径
- 实际链接的静态库文件
- 每个符号的来源库
- 未解决的外部符号(即需要外部提供的依赖)
修改后的编译命令为:
gcc -static -Wl,--verbose my_app.c -o my_app
三、关于.iplt段的额外说明
静态编译的程序理论上不应存在.iplt(动态链接过程链接表)段,出现该段说明仍有动态依赖残留。可能的解决方向:
- 确保编译时添加
-static-libgcc(针对gcc内部辅助函数)或-static-libstdc++(若使用C++),强制静态链接所有依赖库。 - 检查代码中是否隐式调用了标准libc的IO或其他系统相关函数,需确保完全用自定义裸机例程替代这些函数。
内容的提问来源于stack exchange,提问作者jkang
相关产品推荐
相关产品推荐

