crash中使用list遍历结构体
Posted 程序猿Ricky的日常干货
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了crash中使用list遍历结构体相关的知识,希望对你有一定的参考价值。
list [[-o] offset][-e end][-[s|S] struct[.member[,member] [-l offset]] -[x|d]] [-r|-h|-H] start
如下介绍只列举常用的和容易混淆的参数:
- [-o] offset:用于指定next地址指针,可以不用加-o,它支持两种offset格式,一种为structure.member,另一种为一个数字当使用这个offset参数后,最后跟的start地址应该是这个结构体地址,而不是list_head地址。
- -s struct:用于打印结构体中的成员的,当一个结构体很大,而我们只想关注其中的个别结构体成员,那么可以使用这个参数,多个成员之间可以使用逗号分开。
- -l offset:参数格式和-o一样,但是它代表的含义不同,当传入的start地址并非结构体地址,而是嵌入在结构体中的list_head地址时,需要使用-l表示这个list_head相对于结构体的偏移量。
start:它有两种含义,首先它可以表示一个结构体的地址,其次当与-l和-s使用时,它表示一个list_head地址。 - -H start:当结构体中嵌入list_head使用时,使用这个参数表示start为单独的list_head头地址,用于表示链表的起始,这个头并不包含数据。
- -h start:当结构体中嵌入list_head使用时,使用这个参数表示start为一个结构体地址,而非单独的list_head头。
举例说明:
当打印系统中所有的task结构体数据时,list后需要跟offset参数用于表示next地址在哪里,需要使用-h指定某一个task_struct的地址。
crash> struct -o task_struct.tasks
struct task_struct
[1072] struct list_head tasks;
使用如下方法进行list遍历:
list task_struct.tasks -s task_struct.comm -h ffff88083cc5d080
或者使用:
list 1072 -s task_struct.comm -h ffff88083cc5d080
输出如下所示,其中输出的地址为结构体地址:
ffff88083cc5d080
comm = "agent\\000\\000\\000\\000"
ffff88102ac7a280
comm = "test\\000r\\000"
ffffffff81951440
comm = "swapper/0\\000\\000\\000\\000\\000\\000"
ffff881053cf0000
comm = "systemd\\000\\060\\000\\000\\000\\000\\000\\000"
ffff881053cf0b80
comm = "kthreadd\\000\\000\\000\\000\\000\\000\\000"
ffff880854448000
假如我们只知道一个task_struct中的一个tasks(list_head)地址,想通过这个list_head来遍历所有task_struct结构体,那么此时就需要使用-l选项了:
list 0xffff88102ac7a6b0 -l task_struct.tasks -s task_struct.comm
输出如下所示,和上面不同的是,输出的地址为嵌入的list_head结构体成员tasks的地址:
crash> list -h 0xffff88102ac7a6b0 -l task_struct.tasks -s task_struct.comm
ffff88102ac7a6b0
comm = "test\\000r\\000"
ffffffff81951870
comm = "swapper/0\\000\\000\\000\\000\\000\\000"
ffff881053cf0430
comm = "systemd\\000\\060\\000\\000\\000\\000\\000\\000"
ffff881053cf0fb0
comm = "kthreadd\\000\\000\\000\\000\\000\\000\\000"
ffff880854448430
以上是关于crash中使用list遍历结构体的主要内容,如果未能解决你的问题,请参考以下文章