我的构建环境是CentOS 5 我有一个名为libcunit的第三方库。 我用autotools安装它,它生成libcunit.alibcunit.so 我有自己的应用程序链接到一堆共享库。 libcunit.a位于当前目录中, libcunit.so和其他共享库位于/usr/local/lib/ 当我编译时:

gcc -o test test.c -L. libcunit.a -L/usr/local/lib -labc -lyz

我收到一个链接错误:

libcunit.a(Util.o): In function `CU_trim_left':
Util.c:(.text+0x346): undefined reference to `__ctype_b'
libcunit.a(Util.o): In function `CU_trim_right':
Util.c:(.text+0x3fd): undefined reference to `__ctype_b'

但是当我使用.so编译时:

gcc -o test test.c -L/usr/local/lib -lcunit -labc -lyz

编译很好,运行也很好。

为什么在与libcunit.a静态链接时会libcunit.a

===============>>#1 票数:6

为什么在与libcunit.a静态链接时会libcunit.a

问题是你的libcunit.a是建立在一个古老的Linux系统上的,并且取决于从libc 删除的符号(这些符号在glibc-2.2 ,并且在10年前从glibc-2.3中删除)。 更准确地说,这些符号已被hidden 它们可用于动态链接到旧二进制文件(例如libcunit.so ),但没有新代码可以静态链接到它们(您无法创建引用它们的新可执行文件或共享库)。

您可以这样观察:

readelf -Ws /lib/x86_64-linux-gnu/libc.so.6 | egrep '\W__ctype_b\W'
   769: 00000000003b9130     8 OBJECT  GLOBAL DEFAULT   31 __ctype_b@GLIBC_2.2.5

readelf -Ws /usr/lib/x86_64-linux-gnu/libc.a | egrep '\W__ctype_b\W'
# no output

===============>>#2 票数:3

没有注意到libcunit.a实际上是在你的情况下找到的,而linakge的问题则在CUnit库中。 雇用俄语是绝对正确的,他不是在谈论预编译的二进制文件。 我们知道您自己构建了它。 然而,CUinit本身似乎依赖于来自glibc的符号,该符号不再用于静态链接。 因此,您只有2个选项:

  1. 向CUnit的开发者提交一份报告,并要求他们修复它;
  2. 使用动态链接。

不过,我对你的静态连接方式的建议仍然适用。 -L. 总的来说是不好的做法 CUnit是第三方库,不应放在包含项目源文件的目录中。 它应该以与动态版本相同的方式安装,就像你在/usr/local/liblibcunit.so一样。 如果您在CUnit的配置阶段为Autotools提供prefix ,那么Autotools将正确安装所有内容。 因此,如果要静态链接CUnit,请考虑以下面的形式进行:

gcc -o test test.c -L/usr/local/lib -Wl,-Bstatic -lcunit -Wl,-Bdynamic -labc -lyz

  ask by bala1486 translate from so

未解决问题?本站智能推荐: