.so 中缺少一个符号是否表示构建错误或损坏?

Does a single missing symbol from a .so indicate a bad build or corruption?

我有一些代码崩溃并产生了核心转储。在 GDB

中打印时,它的顶部看起来像这样(名称已更改)
#0  0x00007f66be37d428 in __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:54
#1  0x00007f66be37f02a in __GI_abort () at abort.c:89
#2  0x00007f66be9b784d in __gnu_cxx::__verbose_terminate_handler() () from /usr/lib/x86_64-linux-gnu/libstdc++.so.6
#3  0x00007f66be9b56b6 in ?? () from /usr/lib/x86_64-linux-gnu/libstdc++.so.6
#4  0x00007f66be9b5701 in std::terminate() () from /usr/lib/x86_64-linux-gnu/libstdc++.so.6
#5  0x00007f66be9b5919 in __cxa_throw () from /usr/lib/x86_64-linux-gnu/libstdc++.so.6
#6  0x00007f66be9de14f in std::__throw_logic_error(char const*) () from /usr/lib/x86_64-linux-gnu/libstdc++.so.6
#7  0x00007f66bf9798e4 in ?? () from /path/to/my/libname.so
#8  0x00007f66bf979c69 in MyNamespace::MyClass::function_3() () from /path/to/my/libname.so
#9  0x00007f66bf86020a in MyNamespace::MyClass::function_2() () from /path/to/my/libname.so
#10 0x00007f66bf855c0f in MyNamespace::MyClass::function_1() () from /path/to/my/libname.so

第 6 行的异常是

what():  basic_string::_M_construct null not valid

但是 - 第 7 行的元素缺少符号 - 这让我觉得我正在查看一个损坏问题,或者这个库以某种方式构建得很糟糕。我无法解释为什么我们在失败之前一直都有符号。

是否存在核心转储中省略某个符号而其他符号没有的合理情况?

这个库是用带有 CMAKE_BUILD_TYPE=Release 的 CMake 构建的,所以没有调试符号 - 但 AFAIK 应该不会阻止生成和使用实际函数名称的符号(比如 libstdc++ 符号在异常处理中)——尽管诚然那里也缺少一个符号

However - the element at row 7 lacks symbols - this has gotten me thinking that I am looking at a corruption issue or that somehow this lib was built badly somehow.

你猜错了。

libstdc++.so.6 完全 剥离(以保存 space)。唯一保留的符号信息是 从库中导出 的符号(构成其 API 的符号),同时所有内部符号都被删除。

你可以用 nm /usr/lib/x86_64-linux-gnu/libstdc++.so.6nm -D /usr/lib/x86_64-linux-gnu/libstdc++.so.6 来验证——前者应该产生 "no symbols",而后者会列出很多符号。

解决方法很简单:安装 libstdc++6-dbg 包。一旦你这样做,GDB 应该给你一个堆栈(使用相同的 core 文件)没有丢失的函数名称(以及文件和行信息来引导)。