linux内核 cpu_die,Linux内核Crash分析

结合上面的知识,看下当内核打印堆栈信息时,都打印了上面信息。下面的打印信息是工作中遇到的一种情况,打印了内核的堆栈信息,PC指针在dev_get_by_flags中,不能访问的内核虚地址为45685516,内核中一般可访问的地址都是以0xCXXXXXXX开头的地址。

Unableto handle kernel paging request atvirtualaddress45685516

pgd=c65a4000

[45685516]*pgd=00000000

Internalerror:Oops:1[#1]

lastsysfs file:/sys/devices/form/tpm/cfg_l3/l3_rule_add

Moduleslinkedin:splic mmp(P)

CPU:0Tainted:P(2.6.32.11#42)

PCisat dev_get_by_flags+0xfc/0x140

LRisat dev_get_by_flags+0xe8/0x140

pc:[]lr:[]psr:20000013

sp:c07e9c28 ip:00000000fp:c07e9c64

r10:c6bcc560 r9:c646a220 r8:c66a0000

r7:c6a00000 r6:c0204e56 r5:30687461r4:45685516

r3:00000000r2:00000010r1:c0204e56 r0:ffffffff

Flags:nzCvIRQsonFIQsonModeSVC_32 ISA ARMSegmentkernel

Control:0005397fTable:065a4000DAC:00000017

Processswapper(pid:0,stack limit=0xc07e8270)

Stack:(0xc07e9c28to0xc07ea000)

9c20:c0204e56 c6a0000045685516c69ffff0 c69ffff0 c69ffff0

9c40:c6a0000030687461c66a0000 c6a0000000000007c64b210c c07e9d24 c07e9c68

9c60:c071f764 c06bed38 c66a0000 c66a0000 c6a00000 c6a00000 c66a0000 c6a00000

9c80:c07e9cfc c07e9c90 c03350d4 c0334b2c000000340000000600000100c64b2104

9ca0:0000c4fbc0243ece c66a0000 c0beed04 c033436c c646a220 c07e9cf400000000

9cc0:c66a000000000003c0bee8e8 c0beed04 c07e9d24 c07e9ce0 c06e4f5c00004c68

9ce0:00000000faa9fea9 faa9fea90000000000000000c6bcc560 c0335138 c646a220

9d00:c66a0000 c64b2104 c085ffbc c66a0000 c0bee8e800000000c07e9d54 c07e9d28

9d20:c071f9a0 c071ebc000000000c071ebb08000000000000007c67fb460 c646a220

9d40:c0bee8c800000608c07e9d94 c07e9d58 c002a100 c071f84c c0029bb880000000

9d60:c07e9d84 c0beee0c c0335138 c66a0000 c646a22000000000c4959800 c4959800

9d80:c67fb46000000000c07e9dc4 c07e9d98 c078f0f4 c0029bc800000000c0029bb8

9da0:80000000c07e9dbc c6b8d340 c66a052000000000c646a220 c07e9dec c07e9dc8

9dc0:c078f450 c078effc00000000c67fb460 c6b8d34000000000c67fb460 c64b20f2

9de0:c07e9e24 c07e9df0 c078fb60 c078f13000000000c078f12080000000c0029a94

9e00:00000806c6b8d340 c0bee8180000000100000000c4959800 c07e9e64 c07e9e28

9e20:c002a030 c078f804 c64b207000000000c64b2078 ffc45000 c64b20c2 c085c2dc

9e40:00000000c085c2c000000000c081739800086c2ec085c2c4 c07e9e9c c07e9e68

9e60:c06c2684 c0029bc8000000010000004000000000c085c2dc c085c2c000000001

9e80:0000012c00000040c085c2d0 c0bee818 c07e9ed4 c07e9ea0 c00284e0 c06c2608

9ea0:bf00da5c00086c300000000000000001c097e7d4 c07e800000000100c08162d8

9ec0:00000002c097e7a0 c07e9f14 c07e9ed8 c00283d0 c00284785625131100023c88

9ee0:c07e9f0c00000003c08187ac000000180000000001000000c07ebc7000023cbc

9f00:5625131100023c88c07e9f24 c07e9f18 c03391e8 c0028348 c07e9f3c c07e9f28

9f20:c0028070 c03391b0 ffffffff0000001fc07e9f94 c07e9f40 c002d4d0 c0028010

9f40:0000000000000001c07e9f8860000013c07e8000 c07ebc78 c0868784 c07ebc70

9f60:00023cbc5625131100023c88c07e9f94 c07e9f98 c07e9f88 c025c3e4 c025c3f4

9f80:60000013ffffffff c07e9fb4 c07e9f98 c025c578 c025c3cc00000000c0981204

9fa0:c0025ca0 c0d01140 c07e9fc4 c07e9fb8 c0032094 c025c528 c07e9ff4 c07e9fc8

9fc0:c0008918 c0032048 c00083880000000000000000c0025ca00000000000053975

9fe0:c0868834 c00260a400000000c07e9ff800008034c00087080000000000000000

Backtrace:

[](dev_get_by_flags+0x0/0x140)from[](arp_process+0xbb4/0xc74)

r7:c64b210c r6:00000007r5:c6a00000 r4:c66a0000

(1)首先,看看这段堆栈信息是在内核中那个文件中打印出来的,在fault.c文件中,__do_kernel_fault函数,在上面的打印中Unable to handle kernel paging request at virtual address 45685516,该地址是内核空间不可访问的地址。

staticvoid__do_kernel_fault(structmm_struct*mm,unsignedlongaddr,unsignedintfsr,structpt_regs*regs)

{

/*

* Are we prepared to handle this kernel fault?

*/

if(fixup_exception(regs))

return;

/*

* No handler, we'll have to terminate things with extreme prejudice.

*/

bust_spinlocks(1);

printk(KERN_ALERT

"Unable to handle kernel %s at virtual address %08lx\n",

(addr

show_pte(mm,addr);

die("Oops",regs,fsr);

bust_spinlocks(0);

do_exit(SIGKILL);

}

(2) 对于下面的两个信息,在函数show_pte中进行了打印,下面的打印涉及到了页全局目录,页表的知识,暂时先不分析,后续补上。

pgd=c65a4000

[45685516]*pgd=00000000

voidshow_pte(structmm_struct*mm,unsignedlongaddr)

{

pgd_t*pgd;

if(!mm)

mm=&init_mm;

printk(KERN_ALERT"pgd = %p\n",mm->pgd);

pgd=pgd_offset(mm,addr);

printk(KERN_ALERT"[%08lx] *pgd=%08lx",addr,pgd_val(*pgd));

……………………

}

(3) die函数中调用在die函数中取得thread_info结构体的地址。

structthread_info*thread=current_thread_info();

staticinlinestructthread_info*current_thread_info(void){

registerunsignedlongspasm("sp");

return(structthread_info*)(sp&~(THREAD_SIZE-1));

}

Sp: 0xc07e9c28 通过current_thread_info得到 thread_info的地址

(0xc07e9c28 & 0xffffe000) = 0xC07E8000(thread_info的地址,也就是栈底的地址)

(4)下面的打印信息在__die函数中打印

Internalerror:Oops:1[#1]

lastsysfs file:/sys/devices/form/tpm/cfg_l2/l2_rule_add

Moduleslinkedin:splic mmp(P)

CPU:0Tainted:P(2.6.32.11#42)

PCisat dev_get_by_flags+0xfc/0x140

LRisat dev_get_by_flags+0xe8/0x140

pc:[]lr:[]psr:20000013

sp:c07e9c28 ip:00000000fp:c07e9c64

r10:c6bcc560 r9:c646a220 r8:c66a0000

r7:c6a00000 r6:c0204e56 r5:30687461r4:30687461

r3:00000000r2:00000010r1:c0204e56 r0:ffffffff

Flags:nzCvIRQsonFIQsonModeSVC_32 ISA ARMSegmentkernel

Control:0005397fTable:065a4000DAC:00000017

Processswapper(pid:0,stack limit=0xc07e8270)

Stack:(0xc07e9c28to0xc07ea000)

函数的调用关系:die("Oops", regs, fsr);---à __die(str, err, thread, regs);

下面是__die函数的定义:

staticvoid__die(constchar*str,interr,structthread_info*thread,structpt_regs*regs){

structtask_struct*tsk=thread->task;

staticintdie_counter;

/*Internal error: Oops: 1 [#1]*/

printk(KERN_EMERG"Internal error: %s: %x [#%d]"S_PREEMPT S_SMP"\n",

str,err,++die_counter);

/*last sysfs file: /sys/devices/form/tpm/cfg_l2/l2_rule_add*/

sysfs_printk_last_file();

/*内核中加载的模块信息Modules linked in: splic mmp(P) */

print_modules();

/*打印寄存器信息*/

__show_regs(regs);

/*Process swapper (pid: 0, stack limit = 0xc07e8270) tsk->comm task_struct结构体中的comm表示的是除去路径后的可执行文件名称,这里的swapper为idle进程,进程号为0,创建内核进程init;其中stack limit = 0xc07e8270 指向thread_info的结束地址。*/

printk(KERN_EMERG"Process %.*s (pid: %d, stack limit = 0x%p)\n",

TASK_COMM_LEN,tsk->comm,task_pid_nr(tsk),thread+1);

/* dump_mem 函数打印从栈顶到当前sp之间的内容*/

if(!user_mode(regs)||in_interrupt()){

dump_mem(KERN_EMERG,"Stack: ",regs->ARM_sp,THREAD_SIZE+(unsignedlong)task_stack_page(tsk));

dump_backtrace(regs,tsk);

dump_instr(KERN_EMERG,regs);

}

}

在上面的函数中,主要使用了thread_info,task_struct,sp之间的指向关系。task_struct结构体的成员stack是栈底,也是对应thread_info结构体的地址。堆栈数据是从栈底+8K的地方开始向下存的。SP指向的是当前的栈顶。(unsigned long)task_stack_page(tsk),

#define task_stack_page(task) ((task)->stack) ,该宏根据task_struct得到栈底,也就是thread_info地址。

#define task_thread_info(task) ((struct thread_info *)(task)->stack),该宏根据task_struct得到thread_info指针。

(5)dump_backtrace函数

该函数用于打印函数的调用关系。Fp为帧指针,用于追溯程序的方式,方向跟踪调用函数。该函数主要是fp进行检查,看看能否进行backtrace,如果可以就调用汇编的c_backtrace,在arch/arm/lib/backtrace.S函数中。

staticvoiddump_backtrace(structpt_regs*regs,structtask_struct*tsk)

{

unsignedintfp,mode;

intok=1;

printk("Backtrace: ");

if(!tsk)

tsk=current;

if(regs){

fp=regs->ARM_fp;

mode=processor_mode(regs);

}elseif(tsk!=current){

fp=thread_saved_fp(tsk);

mode=0x10;

}else{

asm("mov %0, fp":"=r"(fp)::"cc");

mode=0x10;

}

if(!fp){

printk("no frame pointer");

ok=0;

}elseif(verify_stack(fp)){

printk("invalid frame pointer 0x%08x",fp);

ok=0;

}elseif(fp

printk("frame pointer underflow");

printk("\n");

if(ok)

c_backtrace(fp,mode);

}

(6)dump_instr

根据PC指针和指令mode, 打印出当前执行的指令码

Code: 0a000008 e5944000 e2545000 0a000005 (e4153010)

9f4a8b033023d2e8b066cd807ed0a978.png

内核中函数的调用关系

Linux Kernel 的详细介绍:请点这里

Linux Kernel 的下载地址:请点这里

0b1331709591d260c1c78e86d0c51c18.png

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/408870.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

javascript设计模式--命令模式

1 <!DOCTYPE html>2 <html>3 <head>4 <title>命令模式</title>5 <meta charset"utf-8">6 </head>7 <body>8 9 <script>10 /**11 * 命令模式12 *13 * 定义&#xff1a;14 * 将一个请求封装为一个对…

linux 全球用户数量,全球Linux用户市场占有率升至2.78%

6月7日下午1点左右&#xff0c;www.w3counter.com终 于发布了今年5月份的统计数字&#xff0c;看起来&#xff0c;该网站为此次发布大概做了不少审定工作&#xff0c;相比以往&#xff0c;拖延了几天才发布。公布的统计数字如下&#xff1a;4月份 5月份XP …

[GAN学习系列] 初识GAN

本文大约 3800 字&#xff0c;阅读大约需要 8 分钟 要说最近几年在深度学习领域最火的莫过于生成对抗网络&#xff0c;即 Generative Adversarial Networks(GANs)了。它是 Ian Goodfellow 在 2014 年发表的&#xff0c;也是这四年来出现的各种 GAN 的变种的开山鼻祖了&#xff…

黑马程序员 java基础之网络编程TCP

TCP网络传输。 客户端和服务端 分别对应着两个对象。 Scoket&#xff08;客户端&#xff09;和ServerSocket&#xff08;服务端&#xff09;。 Socket(String address, int port) 创建一个流套接字并将其连接到指定 IP 地址的指定端口号。 这个客户端在一建立的情况下就去连接…

[GAN学习系列] 初始GAN

本文大约 3800 字&#xff0c;阅读大约需要 8 分钟要说最近几年在深度学习领域最火的莫过于生成对抗网络&#xff0c;即 Generative Adversarial Networks(GANs)了。它是 Ian Goodfellow 在 2014 年发表的&#xff0c;也是这四年来出现的各种 GAN 的变种的开山鼻祖了&#xff0…

linux 端口 established,ubuntu/linux上查看端口使用情况

想查看TCP或者UDP端口使用情况&#xff0c;使用netstat -anp如果有些进程看不见&#xff0c;如只显示”-”&#xff0c;可以尝试sudo netstat -anp如果想看某个端口的信息&#xff0c;使用lsof命令&#xff0c;如&#xff1a;sudo lsof -i :631-bash-3.00# netstat -tlnnetstat…

[资源分享] 吴恩达最新《机器学习训练秘籍》中文版可以免费下载了

本文大约 600 字&#xff0c; 阅读大约需要 2 分钟 吴恩达老师在上个月底宣布终于完成了他最新的书籍《Machine Learning Yearning》的最后几个章节&#xff1a; 而最近这本书也有了免费的完整中文版下载了&#xff0c;中文版的名称是《机器学习训练秘籍》&#xff0c;封面如下…

linux一g运行内存不足,在linux运行weblogic出现运行内存不足错误,求鞭挞....

该楼层疑似违规已被系统折叠 隐藏此楼查看此楼# There is insufficient memory for the Java Runtime Environment to continue.# Native memory allocation (malloc) failed to allocate 1431830528 bytes for committing reserved memory.# An error report file with more i…

Android学习笔记44:JSON数据解析

JSON&#xff08;JavaScript Object Notation&#xff09;是一种轻量级的数据交换格式&#xff0c;采用完全独立于语言的文本格式&#xff0c;为Web应用开发提供了一种理想的数据交换格式。 本文将主要介绍在Android开发中&#xff0c;如何在服务器端创建JSON数据&#xff0c;以…

[GAN学习系列2] GAN的起源

本文大约 5000 字&#xff0c;阅读大约需要 10 分钟 这是 GAN 学习系列的第二篇文章&#xff0c;这篇文章将开始介绍 GAN 的起源之作&#xff0c;鼻祖&#xff0c;也就是 Ian Goodfellow 在 2014 年发表在 ICLR 的论文–Generative Adversarial Networks”&#xff0c;当然由于…

两条路,此人如何问甲乙问题?才能走向京城

描述&#xff1a; 有甲、乙两人&#xff0c;其中&#xff0c;甲只说假话&#xff0c;而不说真话&#xff1b;乙则是只说真话&#xff0c;不说假话。但是&#xff0c;他们两个人在回答别人的问题时&#xff0c;只通过点头与摇头来表示&#xff0c;不讲话。有一天&#xff0c;一个…

[资源分享] Github上八千Star的深度学习500问教程

本文大约 600 字&#xff0c;阅读大约需要 2 分钟这周要分享的一个资源是来自 Github 上的已经有八千多 Star 的一个深度学习知识总结&#xff0c;如下图所示&#xff1a;其 Github 地址为&#xff1a;https://github.com/scutan90/DeepLearning-500-questions它目前是有 16 个…

获取android系统手机的铃声和音量

获取android系统手机的铃声和音量 通过程序 获取android系统手机的铃声和音量。设置音量的方法也很简单&#xff0c;AudioManager提供了方法&#xff1a; publicvoidsetStreamVolume(intstreamType,intIndex,intFlags)其中streamType有内置的常量&#xff0c;去文档里面就可以…

linux的xmgrace无法运行,科学网—安装xmgrace - 林绪波的博文

安装xmgrace如果不接触GROMACS我不会知道有一个类似于origin的LINUX下作图的软件――xmgrace下载地址(可自行搜索)http://plasma-gate.weizmann.ac.il/Grace/安装过程&#xff1a;# tar xvzf grace-5.1.20.tar.gz# cd grace-5.1.20.# ./configure# make# make install以上的解压…