gcc - 静态链接Linux中共享对象的依赖关系

标签 gcc shared-libraries static-libraries static-linking dynamic-linking

我正在尝试创建一个共享对象,该对象具有静态链接的自己的依赖项。

这是一个例子:

/* File: add.c */
#include <stdio.h>

int add(int a, int b) {
  printf("Adding: %d %d\n", a, b);
  return a + b;
}

当我尝试编译时出现以下错误:

$ gcc -g -shared -fPIC -o libadd.so add.c -Wl,-Bstatic -lc -Wl,-Bdynamic
/usr/bin/ld: /usr/lib/gcc/x86_64-linux-gnu/7/../../../x86_64-linux-gnu/libc.a(malloc.o): relocation R_X86_64_TPOFF32 against `tcache' can not be used when making a shared object; recompile with -fPIC
/usr/bin/ld: /usr/lib/gcc/x86_64-linux-gnu/7/../../../x86_64-linux-gnu/libc.a(libc_fatal.o): relocation R_X86_64_PC32 against symbol `_dl_pagesize' can not be used when making a shared object; recompile with -fPIC
/usr/bin/ld: final link failed: Bad value
collect2: error: ld returned 1 exit status

Ubuntu 18.04.4 LTS 上运行,使用 gcc (Ubuntu 7.5.0-3ubuntu1~18.04) 7.5.0GNU ld (GNU Binutils for Ubuntu) )2.30

我的问题:

  1. 如何才能实现上述工作?
  2. 如果同时运行 2 个 libc(一个静态链接在我的共享对象中,另一个来自将链接到我的共享对象和 libc 的假设可执行文件),会出现问题吗?

我还找到了这篇文章here突出显示类似的问题,但没有解决方案。

最佳答案

How can I make the above work?

libc.a 的正常构建没有 -fPIC。在 i386 上,您实际上可以将非 PIC 目标文件链接到 .so,但结果将是需要文本重定位的 .so (此类 .so.text 不能在进程之间共享)。

但是在 x86_64 上你不能(在介质内存模型中重定位只有 4 个字节,并且你需要将 .text 重定位超过 +/- 2GiB)。

因此,要实现此功能,您必须使用 -fPIC 重建 libc.a

Would it be an issue if 2 libcs run simultaneously (one statically linked in my shared object and one from a hypothetical executable that will link against my shared object and libc)?

大多数事情都会起作用,但 TLS 可能会导致复杂性。

关于gcc - 静态链接Linux中共享对象的依赖关系,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62877978/

相关文章:

c++ - 使用 Waf 编译时无法正确链接库

linux - 如何使 apache 在执行 cgi 时跳过特定的 stdout 行或停止共享库打印到 stdout

c++ - 是否可以在静态库中编写COM代码,然后将其链接到DLL?

c++ - std::unordered_map::emplace 问题与私有(private)/删除的复制构造函数

c++ - gcc 原子内置函数这么慢是正常的吗?

c++ - gcc 和 MSFT CL 之间的位域结构大小不同

c - 我可以使某些符号仅对其他图书馆成员可见吗?

使用 gettext 时 gcc 可以检查 printf 格式吗?

android - native 库可以作为依赖项包含在 Android Studio 项目中吗?

shared-libraries - 来自动态/静态库的可执行文件的大小