GDB调试打印链表
先看数据结构
// 标准头结点
struct list_head {
struct list_head *next, *prev;
};
// 自定义内容结点
struct blist_reason_node {
struct list_head elem;
u32 id;
char desc[BLIST_LEN];
char cn_desc[BLIST_LEN];
};
// 部分代码段如下
// node是内存中的节点
list_for_each_entry(node, head, elem) {
if (id < 12) {
id++;
continue;
}
// printf("node id:%d, desc:%s.\n", node->id, node->desc);
id++;
}
当GDB断点到达你所需要的位置时,先打印出其中的某一个结点(随便哪一个,只要他存在)。目的是为了获取链表的一个节点地址,当然也可以直接找到链表的头。
# 这里我们先进入list_for_each_entry循环中打印出node
(gdb) p *(struct blist_reason_node *)node
$1 = {elem = {next = 0x80000000542cca90, prev = 0x80000000542cc790}, id = 2, desc ="test blist", '\000' <repeats 116 times>,
cn_desc = "IP\346\211\253\346\217\217\351\230\262\346\212\244", '\000' <repeats 113 times>}
# 设置一个变量用来保存下一个节点指针
(gdb) set $a=(struct blist_reason_node *)0x80000000542cca90
# 书写循环打印语句
(gdb) while 1
>p *($a)
# 前面加(struct blist_reason_node *) 是为了 p 直接按照结构打印
>set $a=(struct blist_reason_node *)((struct blist_reason_node *)$a)->elem.next
>end
$47 = {elem = {next = 0x80000000542ccc10, prev = 0x80000000542cc910}, id = 3,
desc = "test blist 2", '\000' <repeats 124 times>,
cn_desc = "\262\346\232\264\345", '\000' <repeats 124 times>}
$48 = {elem = {next = 0x80000000542ccd90, prev = 0x80000000542cca90}, id = 4,
desc = "test blist 3", '\000' <repeats 124 times>,
cn_desc = "\351\230\262\346\232\264\345\212\233\347\240\264\350\247\243", '\000' <repeats 112 times>}
....
(gdb)
就这啦!
需要注意的是,指向下一个节点的指针赋值不写错问题就不大。