微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

如何在所有模板函数实例化中的标签上设置 gdb 断点

如何解决如何在所有模板函数实例化中的标签上设置 gdb 断点

假设我有以下 C++:

template <int I> int bar(int i) {
  ++i;
label1:
  return I * i;
}
int main(int argc,char **) { return bar<2>(argc); }

是否可以在 label1 上为 bar 的 all 实例设置一个 gdb 断点?在上面,很简单——只有一个实例化。在我的实际用例中,代码库中分布着大量数据。

换句话说,在我的 gdb 命令文件中,有没有办法避免需要先验了解 bar 的每个模板实例化?在我的实际用例中,我的目标是在标签处发出一些有关程序状态的信息(不用担心,goto 不会损害任何程序)。

我知道我可以在标签上为 bar 的特定实例设置断点,如下所示:

break -function bar<2> -label label1

我也知道 rbreak 可用于中断所有模板函数的入口,但显然没有 -label 选项。我不想打破入口点——只是标签。我还想看看是否可以将 rbreakuntil label1 结合使用,但没有用。

我考虑过的另外两种方法是:

  1. grep 用于标签(或者甚至可以只是特殊形成的注释),发出行号并使用此信息来填充/生成带有源文件和行号断点的 gdb 命令文件。这肯定会起作用,但有点希望避免“生成”我的命令文件的需要。
  2. 由于我打算实现一些 gdb Python 漂亮的打印机,也许我可以从 python 中解析源代码获取行号并随后设置断点。我只是在学习 Python API,如何从 gdb python 包中获取等效的 list 并不是很明显。

有什么建议吗?

解决方法

This answer 展示了如何迭代程序中的所有全局符号。

对于您的测试程序,它会产生:

bar<2>(int) True
main(int,char**) True

从这里,您可以轻松找到 bar<>() 的所有实例,并使用 Python breakpoints API 在它们上设置断点。

(gdb) py
>gdb.Breakpoint(function='bar<2>(int)',label='label1')
Breakpoint 1 at 0x1158: file t.cc,line 3.

使用 function='bar<2>' 也有效。

,

根据 suggestion from Employed Russian,我想出了以下 gdb python 脚本:

import re


class Custombreakpoint(gdb.Breakpoint):
    def __init__(self,function,label):
        super().__init__(function=function,label=label,internal=True)

    def stop(self):
        I = gdb.parse_and_eval("I")
        i = gdb.parse_and_eval("i")
        print(f"I = {I},i = {i}")
        return False

pattern = re.compile('.*foo.*')
for sym in gdb.lookup_global_symbol('main').symtab.global_block():
    if sym.is_function:
        match = pattern.search(sym.name)
        if match:
            Custombreakpoint(function=match.string,label='label1')

gdb.execute('run')
gdb.execute('quit')

产生以下输出:

$ g++ -g ./test.cc && gdb --command=test.py ./a.out                                                                                                                                      
Reading symbols from ./a.out...                                                                                                                                                                                      
I = 2,i = 2                                                                                                                                                                                                         
I = 3,i = 2                                                                                                                                                                                                         
[Inferior 1 (process 17224) exited with code 012]

这将使我能够在实际用例中完全按照自己的意愿去做。感谢您的帮助!

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其他元素将获得点击?
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。)
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbcDriver发生异常。为什么?
这是用Java进行XML解析的最佳库。
Java的PriorityQueue的内置迭代器不会以任何特定顺序遍历数据结构。为什么?
如何在Java中聆听按键时移动图像。
Java“Program to an interface”。这是什么意思?