在编译我的程序时,出现了未解决符号错误,指控无法找到__dso_handle
。通常这个函数在哪个库中定义?
nm on libstdc++.so.6
的以下结果是否意味着它包含该函数?
我尝试链接它,但错误仍然发生。
nm libstdc++.so.6 | grep dso
00000000002fc480 d __dso_handle
__dso_handle
是一个“保护程序”,用于在全局销毁期间标识动态共享对象。
实际上,你应该停止阅读。如果你试图通过操纵 __dso_handle
来破坏对象识别,那么很可能出现问题。
然而,既然你问它的定义在哪里:答案比较复杂。想要查看其定义位置(对于GCC),在C++文件中使用,并在此之后执行extern int __dso_handle;
。由于类型冲突,这应该会显示声明的位置(有关来源,请参见此论坛帖子)。
有时,它可以 手动定义。
有时候,它由编译器安装的“运行时”定义/提供(实际上,CRT通常只是一堆二进制头文件/入口点管理代码和一些退出保护/处理程序)。在GCC中(不确定其他编译器是否支持此功能;如果支持,则会在它们的源代码中): 通常,它在stdlib中定义:更多阅读:
我遇到了这个问题。以下是似乎会可靠地生成问题的条件:
-nostdlib
连接 g++ 时没有使用 C/C++ 标准库(典型的小型嵌入式场景)。std::vector
。以前,静态分配的 std::array
没有任何问题。显然,并非所有的 std::
静态分配对象都会引起这个问题。如果您的情况是这样,那么只需在您的编译/链接命令行中添加命令行选项:-fno-use-cxa-atexit
这里有一个非常好的链接 __dso_handle 的使用作为“动态共享对象句柄”。
该页面中似乎存在一个拼写错误,但我不知道应该联系谁来确认:
在调用对象的构造函数析构函数之后,GCC 自动调用该函数……
我认为这应该是“一旦所有析构函数都被调用后,GCC 调用该函数”……
确认的一种方法是按照提到的实现 __cxa_atexit
函数,然后单步运行程序并查看它在哪里被调用。我以后会试试,但现在不行。
在@natersoz的回答基础上-
对我来说,使用-Wabi-tag -D_GLIBCXX_USE_CXX11_ABI=0
与-fno-use-cxa-atexit
一起编译一个旧的库有所帮助。如果错误消息中的C++函数包含std::__cxx11
,则说明由于ABI更改而发生了变化。