5

在 C 编程中,我认为目标文件可以与 .so 文件成功链接,只要 .so 文件提供已在头文件中声明的所有符号。

假设我有 foo.c、bar.h 和两个库 libbar.so.1 和 libbar.so.2。libbar.so.1 和 libbar.so.2 的实现是完全不同的,但我认为只要它们都提供在 bar.h 中声明的函数就可以了。

我将 foo.o 与 libbar.so.1 链接并生成了一个可执行文件:foo.bin。当 libbar.so.1 在 LD_LIBRARY_PATH 中时,此可执行文件有效。(当然,符号链接是作为 libbar.so 建立的)但是,当我将符号链接更改为 libbar.so.2 时,foo.bin 无法运行并抱怨这个:

 undefined symbol: _ZSt4cerr

libbar.so.1 是 c++ 构建的库,而 libbar.so.2 是 ac 构建的库。我不明白为什么 foo.bin 需要那些仅在 libbar.so.1 本身中有意义的 c++ 相关符号,因为 foo.bin 是建立在纯 c 代码 foo.c 之上的。

4

4 回答 4

3

_ZSt4cerr 显然是一个错位的 C++ 名称。您可能需要检查您是否使用了正确的编译器(gcc/g++,我知道这听起来很愚蠢,但我碰巧遇到了这样的困惑;)),以及 bar.h 文件中是否有任何宏可能有参考cerr。

于 2010-03-03T08:58:23.873 回答
2

您必须在搜索之前对 c++ 名称进行 demangle。对于 gcc,有一个 c++filt 实用程序:

$ c++filt
_ZSt4cerr
std::cerr

它只是标准错误文件流。

于 2010-03-03T08:59:08.280 回答
0

您可能只是忘记将整个程序与 C++ 标准库链接。

于 2010-03-03T09:01:58.087 回答
0

问题中的陈述是错误的。你说,“头文件”。没有“ (唯一的)头文件”之类的东西。如果您的意思是“声明某个 C++ 类的头文件”,那么该类可能继承自其他类。或者它可能会使用异常。或 RTTI。在这种情况下,默认情况下,包含随附代码的 .so 将包含“悬挂未定义符号”。默认情况下,“主”程序是 C++ 的,它链接到 C++ 运行时。

可以创建一个独立.so,但您必须做额外的工作才能创建它。您可能需要使用-Bsymbolic,或在链接时指定一些 -l 库,或两者兼而有之。这个区域没有很好的记录,通常需要一些考古学。

于 2010-03-14T23:53:11.047 回答