21

我想知道在使用某个文件中的函数时是否有任何方法可以停止程序。理想情况下,我正在寻找的是:

GDB Stop when use a function from file foo.cpp

这样做的原因是因为我正在调试一个不属于我的代码,并且我不确切知道哪些函数被调用,哪些函数没有被调用。GDB 中是否有一个函数可以做我正在寻找的事情,或者有任何其他推荐的方法来做类似的事情?

谢谢

4

6 回答 6

22

第 1 步:构建foo.cpp
我能想到的最简单方法中定义的所有函数的列表(假设你有binutilsGNU grep):

nm a.out | grep ' T ' | addr2line  -fe a.out |
  grep -B1 'foo\.cpp' | grep -v 'foo\.cpp' > funclist

第 2 步:构建一个 GDB 脚本,它将在上述每个函数上设置一个断点:

sed 's/^/break /' funclist > stop-in-foo.gdb

[显然,步骤 1 和 2 可以合并;-]

第三步:实际设置断点:

gdb a.out
(gdb) source stop-in-foo.gdb

看看这个答案,一个更简单的方法(如果你在 Fedora Linux 上)找出调用了哪些 foo.cpp 函数:

ftrace -sym='foo.cpp#*' ./a.out

太糟糕了ftrace手册页说这还没有实现。

于 2009-01-25T17:53:44.323 回答
12

rbreak regex

在与正则表达式 regex 匹配的所有函数上设置断点。此命令在所有匹配项上设置一个无条件断点,打印它设置的所有断点的列表。一旦设置了这些断点,它们将被视为使用 break 命令设置的断点。您可以删除它们、禁用它们或使它们像任何其他断点一样有条件。

正则表达式的语法是与“grep”等工具一起使用的标准语法。请注意,这与 shell 使用的语法不同,因此例如 foo* 匹配所有包含 fo 后跟零个或多个 os 的函数。您提供的正则表达式有一个隐含的 .* 前导和尾随,因此要仅匹配以 foo 开头的函数,请使用 ^foo。

在调试 C++ 程序时,rbreak 对于在不是任何特殊类成员的重载函数上设置断点很有用。

于 2010-07-29T13:25:57.043 回答
7

rbreak foo.cpp:.

这里.匹配任何东西,因此会破坏 file 的所有功能foo.cpp

于 2017-06-14T08:03:19.783 回答
2

Employed Russian 的回答看起来很好,但既然你说:

我不确切知道调用了哪些函数,没有调用哪些函数。

由代码覆盖工具(如gcov或涉及Valgrind的工具)生成的哪些函数被命中的报告会是解决您问题的好方法吗?

于 2009-01-25T19:40:04.217 回答
1

您可以使用命令:

break foo.cpp:function-name
于 2009-01-25T19:48:37.337 回答
0

gdb 断点有几种语法...请参见此处。

它不会破坏文件中的任何功能......

编辑:你可以做一些愚蠢的事情,比如让所有函数调用一个虚拟函数 void foo(void),并在里面设置断点。至少你会破坏文件内部,并且应该很容易找到文件 X 侧的哪个函数被调用。

于 2009-01-24T01:32:30.133 回答