上篇文章【ARM 嵌入式 编译系列 3.4 – 查看所依赖库文件的路径 详细介绍】一直在提链接参数,那么链接参数有哪些,它们又有什么作用呢?
如前一篇文章中的的链接参数到底是什么意思呢?
$(TARGET): $(OBJS)
@echo Building target: $@
$(LD) -L /usr/lib/gcc/arm-none-eabi/10.4.2/thumb/v8-m.main+fp/hard/ \
-L /usr/lib/gcc/../thumb/v8-m.main+fp/hard/ \
-T ../script/fsp.ld --gc-sections \
-u _printf_float \
-o $@ $(OBJS) \
-lc -lm -lgcc
-L
: 指定了 链接库的路径。-T fsp.ld
:指定了链接脚本。--gc-sections
:这是一个链接器选项,用于在链接时移除未使用的代码和数据节(sections)。这能够减少生成的程序的大小,特别是在嵌入式系统中非常有用。与编译器选项 -ffunction-sections
和 -fdata-sections
结合使用时,可以实现针对未使用函数和数据的优化。-u _printf_float
: 强制链接器包含处理浮点数 printf 支持的代码。-o $@
:指定了输出文件名,$@
是 Makefile 中的变量,代表目标文件名, 也就是 $(TARGET)
。$(objs)
:是链接的对象文件列表,这也是一个 Makefile 变量,包含了所有要链接的对象文件,简单理解就是各个.c
文件编译生成的 .o
文件。-lc -lm -lgcc
: 显式地链接 C 标准库、数学库以及 GCC 的支持库。需要它们以满足程序可能依赖的函数--start-group
和 --end-group
:--start-group
和 --end-group
是链接器选项,用于解决循环依赖问题。当链接器处理库文件时,它通常按照给定的顺序一次处理一个库。如果在库 A 中存在对库 B 的引用,而库 B 又引用了库 A 的话,这就产生了循环依赖。使用 --start-group
和 --end-group
会告诉链接器循环扫描这组库直到解决所有未解决的符号或者没有进一步的符号可以被解决为止。-l
:这是一个链接器选项,用于指定要链接的库。它后面通常跟着库的名称,不包括前缀 lib
和后缀(比如 .a
或 .so
)。