1

您好我正在尝试创建某种调试器来查看系统调用以检测它们,但从可用性的角度来看,我希望能够获取检测到错误的源代码名称和行号。我一直在使用名为 libunwind 的库,但它给了我函数名、函数偏移量以及可执行文件地址空间中的程序计数器。但是,如果您查看 valgrind 或 gdb,它会在使用 -g 标志编译时为您提供行号和源代码名称。我该怎么做?

4

2 回答 2

2

不幸的是,libunwind 只擅长从调用堆栈中获取地址。您要查找的库是Ian Lance Taylor 的 libbacktrace

它解析 DWARF 调试信息。因此,它能够生成带有内联函数名称、源文件名和行号的回溯。

编辑:另一个选项是back-cpp。不过,我没有这方面的经验,但我可以证明 libbacktrace 非常棒!

于 2021-01-18T11:07:07.117 回答
1

对于交互式查看,您可以使用addr2line命令行实用程序。它采用可执行名称和地址(程序计数器),并输出源文件和行。如果您创建了一个程序化解析器,您可以使用它来检查自己。

为了将地址解析为程序中的一行,您必须解析可执行文件中的 DWARF 信息,特别是行号部分。粗略地看一下libunwindAPI,它似乎不支持检索那种信息。还有另一个libdwarf支持通用 DWARF 解析的库。不过,这将是一个相当复杂的项目,行号存储在 DWARF 中的方式并不简单。

如果您不想一直使用libdwarf,可以使用readelf --debug-dump=decodedline命令行将行号部分转换为(相对)易于解析的文本文件,并从 C 程序中解析/解释它。它将为您提供程序计数器值(范围)和源代码行号之间的对应关系。

从命令行转储行信息的另一种方法是dwarfdump -l. 那是更底层的IIRC。

请记住内联函数。相同的 PC 值可能对应多个源行。

要以交互方式查看可执行文件中的 DWARF 信息,您可以使用DWARF Explorer GUI 工具(完全公开:我编写了 GUI)。行号将在源文件的顶部项目下,在stmt_list. 该工具背后的 DWARF 解析器是 Python解析器,而不是 C 解析器。

于 2020-06-18T01:51:01.273 回答