在Linux上编译一个共享库来定位所有发行版

我们想要创build一个共享库(.so)来定位所有的发行版,包括旧发行版。 代码是用C ++编写的,使用C ++ 11的特性,所以编译器必须至less是gcc 4.7。 我们注意到,如果我们在安装了gcc 4.7.2的Linux机器上编译我们的代码(例如,Ubuntu 12.10),那么.so生成的版本为“版本1(GNU / Linux)”,而在旧的操作系统上(例如CentOS 5.6)版本是“版本1(SYSV)” – GNU / Linux较新版本的库不能在旧的操作系统上使用。

所以我们尝试了在CentOS 5.6机器上安装gcc 4.7的方法,用这个编译器编译我们的代码,并且用libstdc ++(-static-libstdc ++)静态链接 – 这样就产生了一个.so,在我们发现的每个linux上都可以使用。

这对32位工作正常。 但是,当我们在64位操作系统(CentOS)上遵循相同的方法时,这个失败的错误是我们试图链接的现有libstdc ++。a编译时没有使用-fPIC。

所以我们试着用“-with-pic”选项来编译gcc 4.7.2源代码,但是我们不能链接到新的libstdc ++。a – 错误是:

/opt/centos/devtoolset-1.1/root/usr/libexec/gcc/x86_64-CentOS-linux/4.7.2/ld:/usr/local/lib/libFoo.so:版本节点找不到符号_ZNSs7_M_copyEPcPKcm @ GLIBCXX_3。 4 /opt/centos/devtoolset-1.1/root/usr/libexec/gcc/x86_64-CentOS-linux/4.7.2/ld:未设置dynamic区段大小:错误值collect2:错误:ld返回1退出状态

我们search了编译libstdc ++与-fPIC可能会有问题,但为什么它适用于32位而不是64位的操作系统? 是否有另一种build议的方式来创build一个.so所有的Linux发行版?

我在https://gcc.gnu.org/ml/libstdc++/2014-05/msg00107.html回答了这个问题

这看起来像https://gcc.gnu.org/bugzilla/show_bug.cgi?id=54482所以可能会在GCC 4.7.3中修复(但我不确定)

对于x86和x86_64,PIC的实现方式是不同的,因为64位模式已经内置了对它的支持。

静态链接到libc / libstdc ++不应该完成,即使它工作! 这是相当危险的,因为很多安全方面需要更新libc。 如果静态链接没有更新可以填补空白。

我不能相信有一个“通用”的libc存在于所有的Linux平台上。 libc是安装系统的界面,这是很大的差异。 一个lib如何适合所有?

虽然链接,你可以尝试

 -static-libstdc++ -static-libgcc 

作为ld的选项。 也许这有帮助。 但我永远不会这样做!