缺少整个程序中库的调试符号的行号,但不是单独的

时间:2011-07-21 01:27:30

标签: gdb debug-symbols libtool dwarf

我在尝试使用gdb为使用libtool构建的软件包调试测试程序时遇到了一个奇怪的问题。如果我运行libtool --mode=execute gdb .libs/libfoo.so并要求它列出某个函数list Bar::Baz的源代码,我会按预期获得源代码。如果我运行libtool --mode=execute gdb binary,我可以进入Bar::Baz(),并在堆栈跟踪中查看其参数,但我没有得到源文件或行号,如下所示:

#7  0x018348e5 in Bar::Baz(Qux*, Quux*) () from /path/to/libfoo.so
                           ^^^^^^^^^^^ <--- debug symbols are present!

同样,如果我在调试可执行文件时尝试list Bar::Baz,我会得到

No line number known for 'Bar::Baz'.

我已确认二进制文件与-g链接,我可以列出其main函数,因此我知道存在一些调试信息。

当我说info sources时,我会得到一个完整的文件列表,其中包含正确的绝对路径。当我说info shared时,我会在目标文件中找到正确的路径,Yes列中有Syms

任何进一步的想法可能出错,以及如何解决它?


编辑1:不小心,我在有问题的库上运行了objdump -g,得到了以下输出:

/path/to/foo.so.0.0.0: file format elf32-i386
objdump: /path/to/foo.so.0.0.0: no recognized debugging information

这是令人惊讶的,因为objdump -h(我试图运行的)列出了一堆.debug_*部分。 objdump手册也提示readelf -w,这似乎打印了大量信息。不过,我需要仔细研究它实际提供的内容。


编辑2:所以,readelf -w已经产生了一些启示。无论出于何种原因,共享对象文件似乎不包含来自的绝大多数 任何链接到其中的对象的调试信息。基于Makefile,实际上将对象收集到共享库中的命令可能不会传递-g,因此信息传播不正确。有趣的是,这对我们所有其他配置都有效(包含完整的调试信息),包括x86_64上的相同编译器版本(与现在的x86相比)。


编辑3:实际上在LDFLAGS上添加了-g时使用修改后的Makefile进行了完全重建,但没有任何区别。现在我很好,真的很困惑。

3 个答案:

答案 0 :(得分:5)

这是一个老问题的答案,但你的问题与我的问题相符,但没有一个解决方案有效。这对我有用。

将CFLAGS -g更改为“-g -gstabs”。

objdump没有认识到矮人风格的调试信息。 -gstabs将此格式更改为与objdump -g和objdump -S以及我的调试器一起使用的格式。

希望它有所帮助。

注意:对我来说,我正在构建一个Linux内核。这个更改是在linux内核的Makefile中生成的。

答案 1 :(得分:2)

您的第一个困惑点:Bar::Baz(Qux*, Quux*) 暗示调试符号存在(实际上暗示它们存在)。

调试器只是对函数名称进行解码。如果调试符号实际存在,您会看到Bar::Baz(Qux* qux = 0x12..., Quux* quux = 0x234...)

至于真正的问题,我怀疑该符号是在某些其他库中定义的,

  • 出现在libfoo.so之前的二进制文件的链接行,
  • 是在没有调试符号的情况下构建的

(运行时加载器会将对Bar::Baz()的引用绑定到它看到的第一个定义。)

如果您在第7帧中打印ip,然后执行info symbol <value-just-printed>,我怀疑您会有“啊哈!”时刻。

编辑:您的更新使您的问题自我不一致。 AFAICT,

    执行
    时,
  1. gdb可以看到调试符号 libtool --mode=execute gdb .libs/libfoo.so
  2. 但不执行libtool --mode=execute gdb binary
  3. 您已经验证了符号定义来自于 完全相同.libs/libfoo.o
  4. readelf -w.libs/libfoo.o
  5. 中看不到调试符号

    上述陈述中至少有一项可能是错误的。

    如果它们都是真的,那么你可能有一个奇怪的GDB readelf错误(一个错误可能存在,两者同时存在错误)。

    另请注意,将-g添加到LDFLAGS通常是错误的要做的事情。您的意思是将其添加到CXXFLAGS吗?

答案 2 :(得分:0)

有些东西让我想知道当你遇到show language时的输出是什么 问题。如果不是c++,可能需要set language c++吗?