正在链接错误的共享库

时间:2014-06-23 12:43:28

标签: c gcc linker shared-libraries

我正在尝试链接库的修改版本(LAME)。

我下载了源代码,进行了修改并构建了共享对象文件。

然后我将共享库文件复制到我想要链接到的项目的./lib文件夹中。另一个项目只是一个简单的工具来测试我的修改。我还复制了LAME ./include的相关标题。

我建立了我的安全带:

gcc -c  src/harness.c -o obj/harness.o
gcc obj/harness.o -o bin/harness -L./lib/ -libmp3lame

但令我惊讶的是:

$ ldd ./bin/harness
linux-vdso.so.1 =>  (0x00007fffbc5fe000)
libmp3lame.so.0 => /usr/lib/x86_64-linux-gnu/libmp3lame.so.0 (0x00007f10d9468000)
libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f10d90a0000)
libm.so.6 => /lib/x86_64-linux-gnu/libm.so.6 (0x00007f10d8d9b000)
/lib64/ld-linux-x86-64.so.2 (0x00007f10d9713000)

/usr/lib/...库已链接,而不是线束项目目录中./lib中的库。

然后我将自定义的libmp3lame.so的名称更改为libsomeothername.so并尝试链接..发生了同样的事情 - 安装的libmp3lame已链接而不是我自定义的。

这里发生了什么?为什么编译器不会按照它所说的去做?为什么/usr/lib/.../libmp3lame即使未使用该名称也会链接

2 个答案:

答案 0 :(得分:3)

我使用LD_DEBUG=all来查看链接器发生了什么,因为LD_LIBRARY_PATH=...应该链接到正确的库。

事实证明,链接器 在那里寻找,但期望找到libmp3lame.so.0而不是我在那里的libmp3lame.so。最后用.0重命名库来修复问题。

我现在可以跑了:

LD_LIBRARY_PATH=./lib ./bin/harness

我想要的lib是链接的。

LD_DEBUG=all似乎很有用。

答案 1 :(得分:1)

ld-linux.so库是实际控制哪个库在运行时链接的库。另一方面,GCC的-L选项仅影响库的编译时搜索路径。

手册页说:

  

在解析库依赖关系时,动态链接器首先检查   每个依赖关系字符串,以查看它是否包含斜杠(这可能会发生   如果在链接时指定了包含斜杠的库路径名)。   如果找到斜杠,则依赖关系字符串将被解释为a   (相对或绝对)路径名,并使用它加载库   路径名。

如果没有斜杠,则它会沿着预定义的搜索路径进行搜索(也在手册页中指定)。

要获得所需的行为,您有以下选择:

  1. 指定链接时库的绝对路径,或

  2. 将LD_LIBRARY_PATH设置为指向包含您的库的目录,或

  3. 链接时使用-rpath选项以在搜索路径中包含包含库的目录(注意:将链接器选项从gcc传递到链接器,使用-Wl,--rpath=/my/path