我可以 link 一个现有的 .so 到另一个 .so 以便 ldd 显示它们的关联吗?

Can I link an existing .so to another .so so that ldd will show their association?

我有两个现有的 .so 文件:

ldd 报告说他们都不了解对方,但是 a.so 依赖于 b.so 中的一个函数,在这个人为的例子中:

# ldd -r a.so
    linux-vdso.so.1 =>  (0x00007ffe8e7bb000)
    libc.so.6 => /lib64/libc.so.6 (0x00007f3d8830c000)
undefined symbol: b_test_func   (./a.so)

# ldd -r b.so
    linux-vdso.so.1 =>  (0x00007ffe8e7bb000)
    libc.so.6 => /lib64/libc.so.6 (0x00007f3d8830c000)

# objdump -T b.so
0000000000fac7a0 g    DF .text  0000000000000f80 b_test_func

由于 a.so 不是针对 b.so 编译的,linker 留下了未解析的符号 b_test_func,因此 ldd 没有列出 b.so 作为依赖项,否则您会在 ldd a.so 输出中看到类似 b.so => /foo/b.so 的内容。

我需要 dlmopen(LM_ID_NEWLM) a.so 进入一个新的命名空间,因此 a.so 必须依赖于 b.so 因为 RTLD_GLOBAL 不受支持dlmopen() 因为 this bug。 (请注意 dlopen(RTLD_GLOBAL) 确实有效)。

因此我们需要 glibc 动态 linker 通过使 a.so 表明它需要 b.so 来解析 linkage 本身,以便它们可以在相同的环境中运行命名空间和 dlmopen() 将自动解决依赖关系。如果没有 ldd 显示的 link,它们将不会使用彼此的共享符号,因此 dlsym() 将无法解析。

问题:

Is there a way to modify a.so so that ldd a.so will try to resolve b.so ?

在大多数 UNIX 系统上,.so最终 link 产品,无法进一步修改。

您也许可以使用 patchelf --add-needed b.so a.so,但只需 dlmopening b.so 然后 dlmopen a.so(正如 Lorinczy Zsigmond 所建议的)可能是一个更简单的解决方案。