【问题标题】:why is gcc linking dynamically when -l is used?为什么使用 -l 时 gcc 会动态链接?
【发布时间】:2018-09-11 18:59:42
【问题描述】:

我使用 pthread 库做了一个“Hello World”程序。 我用这种简单的方式编译它:

$ gcc main.c -lpthread

根据 gcc 文档(“链接选项”部分):

-llibrary [...] 链接器在标准目录列表中搜索该库,该库实际上是一个名为 liblibrary.a 的文件。链接器 然后使用此文件,就好像它已按名称精确指定。 [...]

所以,我的理解是:gcc 正在寻找 libpthread.a 。给定 .a 结尾,这应该是一个静态库。

但是,这是动态链接的:

$ ldd a.out
        linux-vdso.so.1 =>  (0x00007fffde3c3000)
        libpthread.so.0 => /lib/x86_64-linux-gnu/libpthread.so.0 (0x00007fb345820000)
        libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007fb345456000)
        /lib64/ld-linux-x86-64.so.2 (0x00007fb345a3d000)

我错过了什么?

【问题讨论】:

    标签: gcc linker shared-libraries static-libraries


    【解决方案1】:

    GCC 手册中-l|--library 选项的文档具有误导性, 因为它没有指定选项在支持的系统上的行为 共享库,或警告我们它不这样做。

    -l 选项被传递给链接器,通常是 GNU ld(或替代方案)。 ld manual 中的选项文档 是优越的,并清楚地表明共享库将满足 -l 选项 优先于静态库。

    -l 名称规范

    --library=namespec

    将 namespec 指定的存档或目标文件添加到要链接的文件列表中。 此选项可以使用任意次数。如果 namespec 的格式为 :filename, ld 将在库路径中搜索名为 filename 的文件,否则将搜索 > 名为 libnamespec.a 的文件的库路径。

    在支持共享库的系统上,ld 也可以搜索 libnamespec.a 以外的文件。 具体来说,在 ELF 和 SunOS 系统上,ld 将在目录中搜索名为 libnamespec.so 的库,然后再搜索名为 libnamespec.a 的库。 (按照惯例,.so 扩展名表示共享库。) 请注意,此行为不适用于 :filename,它始终指定一个名为 filename 的文件。

    链接器只会在命令行中指定的位置搜索存档一次。 如果档案定义了一个符号,该符号在档案之前出现的某个对象中未定义 在命令行上,链接器将包含存档中的适当文件。 但是,稍后在命令行中出现的对象中的未定义符号将 不会导致链接器再次搜索存档。

    ...

    (我的重点)

    【讨论】:

      猜你喜欢
      • 2012-12-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-11-13
      • 1970-01-01
      相关资源
      最近更新 更多