【问题标题】:How can I specify the rpath in a dylib?如何在 dylib 中指定 rpath?
【发布时间】:2013-06-16 15:23:24
【问题描述】:

我有一个库:libfoo.dylib。命令中说明了问题:

$ install_name_tool -id "@rpath/libfoo.dylib" libfoo.dylib
$ install_name_tool -add_rpath "@executable_path/" libfoo.dylib
$ gcc -o foo foo.c -lfoo
$ ./foo #

如何实现不必在可执行编译时指定库在哪里的目标?

【问题讨论】:

  • 认为您需要编译并链接libfoo.dylib-headerpad_max_install_names,以确保有足够的空间容纳您尝试添加的名称。一旦libfoo.dylib 有了它的安装名称,那么foo 将能够链接到它,而不管程序的位置如何。

标签: macos ld dylib dyld


【解决方案1】:

我必须承认,我对你想要达到的目标有点困惑。使用运行路径搜索路径的全部意义在于加载库的图像定义了加载库时要使用的搜索路径。您要求的是库定义可执行文件应该在哪里找到它。这可以在不使用运行路径搜索路径的情况下完成,只需将 dylib 的安装名称设置为适当的值即可。根据您的特定示例,听起来您想将安装名称设置为 @loader_path/libfoo.dylib 之类的名称。考虑以下内容,与您的示例相同:

$ cat a.c 
int a(void)
{
    return 1;
}
$ cc -install_name "@loader_path/liba.dylib" -dynamiclib -o liba.dylib a.c 
$ cat main.c
#include <stdio.h>

extern int a(void);

int main(int argc, char **argv)
{
    fprintf(stderr, "A: %d\n", a());
    return 0;
}
$ cc -L. -la -o main main.c
$ ./main
A: 1
$ 

该库通过设置其安装名称告诉与之链接的可执行文件如何找到它,并且在链接可执行文件以使其在运行时找到该库时不需要做任何特殊的事情。

【讨论】:

  • 是的,您的示例可以满足我的要求(将库设置在应该找到的位置,而不是可执行文件)。唯一的问题(以及我想使用 rpath 的原因)是我想指定 3 个要搜索的位置:/usr/lib../Framework/,以及您展示的可执行路径。根据我的阅读,仅使用 install_name 是不可能的,对吧?
  • 对,如果要指定多个位置,则需要使用运行路径搜索路径,因此可执行文件将指定在何处查找库。请注意,如果在加载命令引用的位置找不到库,则默认搜索/usr/lib,因此可能不需要显式引用该位置。
【解决方案2】:

您唯一需要做的就是告诉链接器在您的二进制文件中添加 rpath。实际上,您告诉gcc 以以下方式告诉链接器:

$ gcc -o foo foo.c -lfoo -Wl,-rpath=/some/path

现在,如果您使用 objdump 来查看其中的内容:

$ objdump -x ./foo | less

你会在Dynamic Section 下看到类似RPATH /some/path 的东西。

如果必须输入相同的-Wl,-rpath=... 太麻烦,ld 接受@file 选项(我不知道dyld,但我想它也是):

$ echo "-rpath=/some/path" > ./ld-options
$ gcc ./foo.c -o foo -Wl,@ld-options

【讨论】:

  • 我想我应该进一步解释一下,但问题是我有很多可执行文件正在编译,而只有一个库。我想将构建可执行文件的命令保留在 1 行的范围内,以便很容易看到警告。在每个可执行的编译命令中添加rpath=... 会使命令非常长并且超过 1 行标记。与其说是必要,不如说是方便。
  • 没有用,所以我尝试了原来的方式:ld: unknown option: -rpath=@executable_path/
  • 这些说明似乎是针对 GCC 和 GNU binutils 而不是 OS X 工具链的。这就是为什么像 -Wl,-rpath=/foogcc 这样的选项会引发错误。
猜你喜欢
  • 2011-10-02
  • 2017-12-12
  • 2014-09-06
  • 1970-01-01
  • 2018-03-11
  • 2019-06-23
  • 2018-10-20
  • 2017-06-18
  • 2016-02-04
相关资源
最近更新 更多