当链接到静态库时,GCC链接选项真的是必要的吗?

neekobn8  于 2022-11-13  发布在  其他
关注(0)|答案(1)|浏览(214)

我最近一直在玩GCC,并且一直在试验链接选项。我有点困惑为什么链接选项-l在静态链接到一个存档文件时是必需的。看起来你可以把.a文件当作一个普通的对象文件来丢弃。
例如,以下面的make文件为例:

test1 : main.c libfunc.a
    gcc main.c -L. -lfunc -o main.out

test2 : main.c libfunc.a
    gcc main.c libfunc.a -o main.out

libfunc.a : func1.c func2.c
    gcc func1.c -c
    gcc func2.c -c
    ar cr libfunc.a func1.o func2.o

Make target test1使用GCC的链接选项来链接到存档文件。Target test2则直接包含存档文件。构建和运行每个输出似乎都产生相同的可执行文件。

ubof19bj

ubof19bj1#

有几种方法可以告诉gcc什么文件(s)。-lname的参数(或两个参数`-l `name)表示“搜索名为name的库“。根据GCC文档,此参数传递给链接器链接器查找名称类似于libname.extension的文件,其中extension``是已知库文件扩展名之一,如.a.so,并在它拥有的库目录列表中查找具有这些名称的文件。
当连接器找到程式库时,它会使用它,就像您已经指定路径一样,因此无论您是以-l或其路径指定程式库,最终结果都是相同的。
通过使用路径,可以指定不在已知库目录中的库或具有不寻常名称的库。
请注意,链接器处理库的方式与处理目标文件的方式不同。当链接器处理目标文件时,它会将目标文件中的所有内容合并到正在构造的输出文件中。当链接器处理库文件时,它只会合并库中的那些模块,这些模块为前一个模块引用的符号提供符号定义,但尚未解析。例如,如果你写了一个使用sqrt但不使用sin的程序,那么,当链接器在阅读你的目标模块后处理libm.a时,它将从库中获取sqrt模块,而不是sin模块。

相关问题