为什么 "符号查找错误","未定义符号",而该符号却存在

问题描述 投票:1回答:1

这原本是 PySide2错误,但在经过一番调试后,如下所示 本回答我认为这可能是一个普遍的c++问题,不管应用程序和未定义符号到底是什么。

当我运行 /home/me/.local/lib/python3.8/site-packages/PySide2/designer 并关闭它,它就会崩溃

/home/me/.local/lib/python3.8/site-packages/PySide2/designer:
  symbol lookup error: /home/me/.local/lib/python3.8/site-packages/PySide2/designer:
  undefined symbol: _ZdlPvm, version Qt_5

但这是不应该发生的。首先,系统libstdc++确实被加载了。

$ LD_DEBUG=libs pyside2-designer 2>&1 |grep libstdc++
   1926528: find library=libstdc++.so.6 [0]; searching
   1926528:   trying file=/home/me/.local/lib/python3.8/site-packages/shiboken2/libstdc++.so.6
   1926528:   trying file=/usr/lib/libstdc++.so.6
   1926528: calling init: /usr/lib/libstdc++.so.6
   1926533: find library=libstdc++.so.6 [0]; searching
   1926533:   trying file=/usr/lib/libstdc++.so.6
   1926533: calling init: /usr/lib/libstdc++.so.6
   1926528: calling fini: /usr/lib/libstdc++.so.6 [0]

第二, 符号"_ZdlPvm "确实被定义在... /usr/lib/libstdc++.so.6:

$ nm -D /usr/lib/libstdc++.so.6 |grep _ZdlPvm
00000000000a1ca0 T _ZdlPvm
00000000000a3c30 T _ZdlPvmSt11align_val_t

除非这两个事实不能保证符号 _ZdlPvm 是找到并使用的,那么我想知道如何保证,动态加载到底是如何工作的。

先谢谢大家了。

c++ linker shared-libraries
1个回答
1
投票

完整的错误信息是

{...}/lib/python3.6/site-packages/PySide2/designer: relocation error: 
     {...}/lib/python3.6/site-packages/PySide2/designer: symbol 
     _ZdlPvm version Qt_5 not defined in file libQt5Core.so.5 with
      link time reference

您的包是与 它自己的本地副本 的Qt库,但是你并没有使用这些库(你没有将相关目录添加到你的 LD_LIBRARY_PATH). 让我们来看看。

$ nm -D {...}/lib/python3.6/site-packages/PySide2/Qt/lib/libQt5Core.so.5 | grep _ZdlPvm
00000000003b95e0 T _ZdlPvm

$ nm -D /usr/lib64/libQt5Core.so.5 | grep _ZdlPvm
                 U _ZdlPvm

为什么它关心的地方 _ZdlPvm 的定义?嗯,因为符号不仅仅是名字。还有符号版本。请看这个小 version Qt_5 信息的一部分?

$ nm --with-symbol-versions -D /usr/lib/gcc/x86_64-pc-linux-gnu/9.3.0/libstdc++.so.6 | grep _ZdlPvm
00000000000d0060 T _ZdlPvm@@CXXABI_1.3.9
00000000000d1ed0 T _ZdlPvmSt11align_val_t@@CXXABI_1.3.11

$ nm --with-symbol-versions -D {...}/lib/python3.6/site-packages/PySide2/Qt/lib/libQt5Core.so.5 | grep _ZdlPvm
00000000003b95e0 T _ZdlPvm@@Qt_5

所以,你们当地的符号 libQt5Core.so.5 的定义实际上与 libstdc++.so.6 的定义。

我试着将Qt的本地副本添加到了 LD_LIBRARY_PATH但结果是找不到 Kerberos 库。我的系统不使用 Kerberos,所以它们不存在。如果您使用的是像 Ubuntu 这样的标准 Linux 发行版, 您可能会有更好的运气。

总结一下,有 包中的一个错误。如果它需要使用它自己的Qt拷贝,它应该想出一种方法来实际使用它,而不需要用户去跳槽。这不是C++或其他语言的问题。它是一个更普遍的问题的表现,被称为 "DLL地狱"。

© www.soinside.com 2019 - 2024. All rights reserved.