设置观察点以在GDB中输出十六进制列表

时间:2014-07-10 14:58:24

标签: c debugging gdb

我正在使用GDB调试C程序,并且我在变量uint8_t msg_bin_tst[64];上设置了一个观察点。当触发观察点时,GDB输出如下内容:

Watchpoint 4: msg_bin_tst
Old value = "@\001\000\067\335\002\033a32c85ba9dda45823be416246cf8b433baa068d7\000\000\000\000\000\000\000\000\000\017\000\000\000(\000\000"
New value = "@\001\000\067\335\002\033a32c85ba9dda45823be416246cf6cf8b433baa068d7\000\000\000\000\000\000\017\000\000\000(\000\000"

这有点难以理解,是否有办法将输出格式设置为print/x,即:

msg_bin_tst = {0x40, 0x1, 0x0, 0x37, 0xdd, 0x2, 0x1b, 0x61, 0x33, 0x32, 0x63, 0x38, 0x35, 0x62, 0x61, 0x39, 0x64, 0x64, 0x61, 0x34, 0x35, 0x38, 0x32, 0x33, 0x62, 0x65, 0x34, 0x31, 0x36, 0x32, 0x34, 0x36, 0x63, 0x66, 0x38, 0x62, 0x34, 0x33, 0x33, 0x62, 0x61, 0x61, 0x30, 0x36, 0x38, 0x64, 0x37, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xf, 0x0, 0x0, 0x0, 0x28, 0x0, 0x0, 0x0}

2 个答案:

答案 0 :(得分:1)

gdb根据uint8_t [64]的默认格式打印您的值。但是gdb也允许您更改打印特定类型的方式。这称为Python Pretty-Printers。你可以在这里阅读它们:

我没有c ++ 11,为了演示一个例子我使用unsigned char作为一种类型。您的类型的打印机可能如下所示:

$ cat my_priner.py
class CustomPrinter(object):
    def __init__(self, val):
        self.val = val

    def to_string(self):
        res = "{"
        for m in xrange(64):
          res += hex(int(self.val[m]))
          if m != 63:
            res += ", "
        res += " }"
        return res

def lookup_type (val):
    if str(val.type) == 'unsigned char [64]':
        return CustomPrinter(val)
    return None

gdb.pretty_printers.append (lookup_type)

这是适用于我的变量unsigned char m[64];的打印机:

$ gdb  -q -x my_priner.py  -ex "set pagination off" -ex "start" -ex "watch m" -ex "c"  ./main
Reading symbols from /home/main...done.
Temporary breakpoint 1 at 0x400590: file main.cpp, line 7.
Starting program: /home/main

Temporary breakpoint 1, main () at main.cpp:7
7         memcpy(m, "He",2);
Watchpoint 2: m
Continuing.
Watchpoint 2: m

Old value = {0x48, 0x65, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 }
New value = {0x48, 0x65, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 }
0x0000003c41288ac4 in memcpy () from /lib64/libc.so.6
(gdb)

答案 1 :(得分:1)

使用commands在命中观察点时设置命令,例如:

(gdb) commands 2
Type commands for breakpoint(s) 2, one per line.
End with a line saying just "end".
>print /x msg_bin_tst
>end

2是观察点的数量。然后,当点击观察点时,阵列将自动转储。

您可以参考gab手册:https://sourceware.org/gdb/onlinedocs/gdb/Break-Commands.html