[英]automatic debugging with gdb
I am dealing with a large code base with tons of globals.我正在处理一个包含大量全局变量的大型代码库。 Under some peculiar set of data it produces the wrong result.
在某些特殊的数据集下,它会产生错误的结果。 I wanted to automatically run few scenarios with gdb in automatic step-by-step execution and periodical dumping of some values and recording the tracing in some file.
我想用 gdb 自动运行几个场景,自动逐步执行和定期转储一些值并在一些文件中记录跟踪。 Doing it manually will ruin my sight and my brain.
手动操作会毁了我的视力和大脑。 I speculate that there is some globals mess-up.
我推测有一些全局混乱。 How to do this automatically?
如何自动执行此操作? Use some scripting.
使用一些脚本。 All this is in RH linux.
所有这些都在 RH linux 中。 Thanks in advance.
提前致谢。
tried to do this manually using conditional breaks, but gave up after a while尝试使用条件中断手动执行此操作,但一段时间后放弃了
I wanted to automatically run few scenarios with gdb in automatic step-by-step execution and periodical dumping of some values and recording the tracing in some file.
我想用 gdb 自动运行几个场景,自动逐步执行和定期转储一些值并在一些文件中记录跟踪。
It may be significantly more effective to run the program under reverse debugger (such as rr ), and trace the wrong result back to its source.在反向调试器(例如rr )下运行程序可能会更有效,并将错误的结果追溯到其源。
How to do this automatically?
如何自动执行此操作?
You can't do automatically what you can't express as an algorithm, and you haven't described an algorithm you want to use.你不能自动地做你不能用算法表达的事情,你还没有描述你想要使用的算法。 If it's something like "stop every 100 times
foo
is called and print the values of these 500 globals", than that's trivially automatable with GDB.如果它类似于“每调用 100 次
foo
就停止并打印这 500 个全局变量的值”,那么使用 GDB 可以轻松实现自动化。
More complicated algorithms are possible with the use of embedded Python.使用嵌入式 Python 可以实现更复杂的算法。
In the .gdbinit
file in your home folder add在主文件夹中的
.gdbinit
文件中添加
add-auto-load-safe-path /path_to_the_folder_containing_your_executable/
Now you can create another .gdbinit
file in the same folder where your executable is that will be loaded when you start gdb from there (the .gdbinit
file in your home that is also read - useful if you have nice stuff there such as loading pretty printers).现在,您可以在您的可执行文件所在的同一文件夹中创建另一个
.gdbinit
文件,当您从那里启动 gdb 时将加载该文件(您家中的.gdbinit
文件也已读取 - 如果您有不错的东西,例如加载漂亮的打印机)。
In this .gdbinit
file, add the code below在这个
.gdbinit
文件中,添加以下代码
file your_executable_name
start
# Optional
set args "<any command line parameters you program might need>"
# xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
# Add gdb commands below to set breakpoints, print variable values, etc
# xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
run
Gdb is very powerful and I'll list a few things that might help this automation. Gdb 非常强大,我将列出一些可能有助于实现自动化的东西。
b filename.ext:line_number
or b function_name
b filename.ext:line_number
或b function_name
设置断点commands breakpoint_number
(see here ) and then list commands that should be run after this breakpoint is hit.commands breakpoint_number
(请参见此处),然后列出在命中此断点后应运行的命令。 Use end
to finish the commandsend
完成命令
start
will count as a breakpoint and thus the first one you add will be breakpoint 2)start
将计为断点,因此您添加的第一个断点将是断点 2)One idea is that you can save the address of the important global variables (if they are not always accessible) using convenience variables.一种想法是,您可以使用便利变量保存重要的全局变量的地址(如果它们不总是可访问的)。 For instance, add a breakpoint where this global variable is and then add to this breakpoint the command to save the address of this variable to a convenience variable followed by
continue
(with continue
you will not see gdb stopping there).例如,在此全局变量所在的位置添加一个断点,然后在此断点中添加命令以将此变量的地址保存到一个便利变量,然后再
continue
(使用continue
您将不会看到 gdb 停在那里)。
set $var1 = &myglobal
continue
You might want to also delete this breakpoint with delete breakpoint_number
before continue
to avoid stopping at this breakpoint again.您可能还想在
continue
避免再次在此断点处停止之前使用delete breakpoint_number
删除此断点。
Then as long is the object exists you can inspect it using p $var1
or p $var1->something
when the program is stopped at a different breakpoint where myglobal
might not be directly accessible.然后只要 object 存在,当程序在
myglobal
可能无法直接访问的不同断点处停止时,您可以使用p $var1
或p $var1->something
检查它。
In the commands that you add to be run when a breakpoint is hit you can do things such as echo message explaining where you are
, p some_var
to see the values of variables or even python some_complicated_python_code
.在遇到断点时添加的命令中,您可以执行诸如
echo message explaining where you are
、 p some_var
以查看变量值甚至python some_complicated_python_code
的操作。
In the case you want to use python for more power it is worth reading the section about it in the manual.如果您想使用 python 获得更多功率,则值得阅读手册中有关它的部分。 Let-me give you one example.
让我举一个例子。 Suppose one of your global variables was stored in a convenience variable called "$myvar".
假设您的一个全局变量存储在一个名为“$myvar”的便利变量中。 Then you can pass it to the python interpreter with
然后你可以将它传递给 python 解释器
python myvar = gdb.parse_and_eval("$myvar")
You can also pass any variable in the current scope to parse_and_eval
.您还可以将当前 scope 中的任何变量传递给
parse_and_eval
。 Now, suppose this global variable stores an object of a class with a "n_elem" attribute you want to check.现在,假设这个全局变量存储一个 class 的 object,您要检查一个“n_elem”属性。 You can print it with
你可以打印它
python print(myvar["n_elem"])
You can also create a python file in the same folder and use您还可以在同一文件夹中创建 python 文件并使用
python from my_python_file import *
to import functions defined there.导入那里定义的函数。
With these gdb features you can pretty much automate whatever you might need.借助这些 gdb 功能,您几乎可以自动化您可能需要的任何内容。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.