免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
12下一页
最近访问板块 发新帖
查看: 25850 | 回复: 17
打印 上一主题 下一主题

CPU 0 Unable to handle kernel paging request at virtual address 00000000000000a0 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2012-02-16 13:33 |只看该作者 |倒序浏览
系统在启动时,遇到一些错误。
CPU 0 Unable to handle kernel paging request at virtual address 00000000000000a0
, epc == c00000000005d6c0, ra == c0000000000610f4
Oops[#1]:
Cpu 0
$ 0   : 0000000000000000 0000000000070000 0000000000000000 0000000000000001
$ 4   : 000000000000ffff 0000000000000000 980000009f507ac0 ffffffffbfd00000
$ 8   : ffffffffbfe00134 0000000000000000 0000000000000000 0000000000000000
$12   : 000000001000c4e0 000000001000001f 0000000000000000 00000000000007b1
$16   : 0000000000000000 000000000000ffff 0000000000000000 0000000000000000
$20   : 0000000000000014 980000009f507ac0 980000009f507ca0 0000000000000000
$24   : 0000000000000004 980000009e4df6b4
$28   : 980000009f504000 980000009f5079b0 0000000000000034 c0000000000610f4
Hi    : 0000000000000000
Lo    : 0000000000000780
epc   : c00000000005d6c0 $L95+0x20/0x1a8 [pcan]     Not tainted
ra    : c0000000000610f4 $L130+0x0/0x40 [pcan]
Status: 1000c4e3    KX SX UX KERNEL EXL IE
Cause : 10003808
BadVA : 00000000000000a0
PrId  : 00006303
Modules linked in: pcan
Process klogd (pid: 2138, threadinfo=980000009f504000, task=980000009f331f3
Stack : 0000000000000000 000000000000ffff c0000000000610f4 0000000000000000
        980000009c12df00 0000000000000001 0000000000000014 980000009f507ac0
        0000000000000080 0000000000000001 ffffffff80278594 ffffffff80278594
        ffffffff807ec780 0000000000000014 980000009fcc4980 980000009f507ac0
        fffffffffffbffff 000000000000000a ffffffff802787ac 00000000000007b1
        980000009f507ac0 0000000000000010 0000000000007000 0000000000000004
        0000000000000001 ffffffff802017bc 7fffffffffffffff 0000000000000034
        980000009fbf63a0 980000009e4df680 980000009e38bf00 980000009fbf6120
        ffffffff80202d00 ffffffff806ae6d4 0000000000000000 ffffffffcfffffff
        0000000000000000 0000000000000000 980000009fbf6428 7fffffffffffffff
        ...
Call Trace:
[<c00000000005d6c0>] $L95+0x20/0x1a8 [pcan]
[<c0000000000610f4>] $L130+0x0/0x40 [pcan]
Code: dca59350  000a58f8  0165102d <dc4300a0> 8c640114  8c62010c  00041800  0002
1000  3048ffff
Kernel panic - not syncing: Fatal exception in interrupt

这个是在安装我们自己设计FPGA驱动的时候出现的。
这个错误在我们这出现的次数不多,重复开关机,半天会出现一次。但是在客户那里经常出现。
请问一般是什么原因造成的这种错误?
在此先谢谢各位的帮助了

论坛徽章:
6
金牛座
日期:2013-10-08 10:19:10技术图书徽章
日期:2013-10-14 16:24:09CU十二周年纪念徽章
日期:2013-10-24 15:41:34狮子座
日期:2013-11-24 19:26:19未羊
日期:2014-01-23 15:50:002015年亚洲杯之阿联酋
日期:2015-05-09 14:36:15
2 [报告]
发表于 2012-02-16 14:10 |只看该作者
回复 1# Blaider
从panic的信息可以找到出错的那行代码,把那行出处的代码贴出来看看

   

论坛徽章:
0
3 [报告]
发表于 2012-02-16 18:39 |只看该作者
回复 2# 瀚海书香

1、Kernel panic - not syncing: Fatal exception in interrupt
从这句话好像也找不到什么出错信息吧,而且现在还无法定位具体是在哪行代码出现的错误,里面调用的东西太多了。

2、  从“CPU 0 Unable to handle kernel paging request at virtual address 00000000000000a0”这句话来看,是不是一般是内存有问题?或者是非法操作地址造成的?
3、epc   : c00000000005d6c0 $L95+0x20/0x1a8 [pcan]     Not tainted
在这句话中,$L95是不是代表某个模块?怎么知道具体是哪个模块?怎么才能让它找到自己的符号表?解析的时候把函数名也显示出来?因为我在其它的错误里发现这个位置会是出错时函数名,但是这里只是显示了$L95。那么模块函数名称后面的+0x20/0x1a8 又代表什么意思?

论坛徽章:
22
丑牛
日期:2014-08-15 14:32:0015-16赛季CBA联赛之同曦
日期:2017-12-14 15:28:14黑曼巴
日期:2017-08-10 08:14:342017金鸡报晓
日期:2017-02-08 10:39:42黑曼巴
日期:2016-11-15 15:48:38CU十四周年纪念徽章
日期:2016-11-09 13:19:1015-16赛季CBA联赛之同曦
日期:2016-04-08 18:00:03平安夜徽章
日期:2015-12-26 00:06:30程序设计版块每日发帖之星
日期:2015-12-03 06:20:002015七夕节徽章
日期:2015-08-21 11:06:17IT运维版块每日发帖之星
日期:2015-08-09 06:20:002015亚冠之吉达阿赫利
日期:2015-07-03 08:39:42
4 [报告]
发表于 2012-02-16 22:52 |只看该作者
这个错误的原因是访问了不对的指针,LZ可以用objdump -S vmlinux 然后用你的PC值看附近的汇编。乃至去看C源码

论坛徽章:
0
5 [报告]
发表于 2012-02-17 00:26 |只看该作者
回复 4# amarant


    咱们的论坛里有没有哪个帖子是讲如何反汇编程序,并根据反汇编代码调试程序的?如果有的话请发一个地址吧,我想好好学学反汇编调试方法。现在发现汇编也是好东西啊

论坛徽章:
0
6 [报告]
发表于 2012-02-17 00:30 |只看该作者
回复 4# amarant


    mips汇编的objdump 教程……

论坛徽章:
6
金牛座
日期:2013-10-08 10:19:10技术图书徽章
日期:2013-10-14 16:24:09CU十二周年纪念徽章
日期:2013-10-24 15:41:34狮子座
日期:2013-11-24 19:26:19未羊
日期:2014-01-23 15:50:002015年亚洲杯之阿联酋
日期:2015-05-09 14:36:15
7 [报告]
发表于 2012-02-17 08:57 |只看该作者
回复 3# Blaider
下面是我自己存档的一段定位oops代码的资料,希望对你有帮助

定位oops的具体代码行
来自Linus Torvalds的讨论:
https://groups.google.com/group/ ... 41/ed9c0a0cfcd31111
例如这样的一个Oops:
Oops: 0000 [#1] PREEMPT SMP
Modules linked in: capidrv kernelcapi isdn slhc ipv6 loop dm_multipath snd_ens1371 gameport snd_rawmidi snd_ac97_codec ac97_bus s nd_seq_dummy snd_seq_oss snd_seq_midi_event snd_seq snd_seq_device snd_pcm_oss snd_mixer_oss snd_pcm snd_timer snd parport_pc floppy parport pcnet32 soundcore mii pcspkr snd_page_alloc ac i2c_piix4 i2c_core button power_supply sr_mod sg cdrom ata_piix libata dm_snapshot dm_zero dm_mirror dm_mod BusLogic sd_mod scsi_mod ext3 jbd mbcache uhci_hcd ohci_hcd ehci_hcd
Pid: 1726, comm: kstopmachine Not tainted (2.6.24-rc3-module #2)
EIP: 0060:[] EFLAGS: 00010092 CPU: 0
EIP is at list_del+0xa/0x61
EAX: e0c3cc04 EBX: 00000020 ECX: 0000000e EDX: dec62000
ESI: df6e8f08 EDI: 000006bf EBP: dec62fb4 ESP: dec62fa4
DS: 007b ES: 007b FS: 00d8 GS: 0000 SS: 0068
Process kstopmachine (pid: 1726, ti=dec62000 task=df8d2d40 task.ti=dec62000)
Stack: 000006bf dec62fb4 c04276c7 00000020 dec62fbc c044ab4c dec62fd0 c045336c
df6e8f08 c04532b4 00000000 dec62fe0 c043deb0 c043de75 00000000 00000000
c0405cdf df6e8eb4 00000000 00000000 00000000 00000000 00000000
Call Trace:
[] show_trace_log_lvl+0x1a/0x2f
[] show_stack_log_lvl+0x9b/0xa3
[] show_registers+0xa3/0x1df
[] die+0x11f/0x200
[] do_page_fault+0x533/0x61a
[] error_code+0x72/0x78
[] __unlink_module+0xb/0xf
[] do_stop+0xb8/0x108
[] kthread+0x3b/0x63
[] kernel_thread_helper+0x7/0x10
=======================
Code: 6b c0 e8 2e 7e f6 ff e8 d1 16 f2 ff b8 01 00 00 00 e8 aa 1c f4 ff 89 d8 83 c4 10 5b 5d c3 90 90 90 55 89 e5 53 83 ec 0c 8b 48 04 11 39 c2 74 18 89 54 24 08 89 44 24 04 c7 04 24 be 32 6b c0
EIP: [] list_del+0xa/0x61 SS:ESP 0068:dec62fa4
note: kstopmachine[1726] exited with preempt_count 1
1, 有自己编译的vmlinux: 使用gdb
编译时打开complie with debug info选项。
注意这行:
EIP is at list_del+0xa/0x61
这告诉我们,list_del函数有0x61这么大,而Oops发生在0xa处。 那么我们先看一下list_del从哪里开始:
# grep list_del /boot/System.map-2.6.24-rc3-module
c10e5234 T plist_del
c10e53cc T list_del
c120feb6 T klist_del
c12d6d34 r __ksymtab_list_del
c12dadfc r __ksymtab_klist_del
c12e1abd r __kstrtab_list_del
c12e9d03 r __kstrtab_klist_del
于是我们知道,发生Oops时的EIP值是:
c10e53cc + 0xa == c10e53d6
然后用gdb查看:
# gdb /home/arc/build/linux-2.6/vmlinux
(gdb) b *0xc10e53d6
Breakpoint 1 at 0xc10e53d6: file /usr/src/linux-2.6.24-rc3/lib/list_debug.c, line 64.
看,gdb直接就告诉你在哪个文件、哪一行了。
gdb中还可以这样:
# gdb Sources/linux-2.6.24/vmlinux
(gdb) l *do_fork+0x1f
0xc102b7ac is in do_fork (kernel/fork.c:1385).
1380
1381 static int fork_traceflag(unsigned clone_flags)
1382 {
1383 if (clone_flags & CLONE_UNTRACED)
1384 return 0;
1385 else if (clone_flags & CLONE_VFORK) {
1386 if (current->ptrace & PT_TRACE_VFORK)
1387 return PTRACE_EVENT_VFORK;
1388 } else if ((clone_flags & CSIGNAL) != SIGCHLD) {
1389 if (current->ptrace & PT_TRACE_CLONE)
(gdb)
也可以直接知道line number。
或者:
(gdb) l *(0xffffffff8023eaf0 + 0xff) /* 出错函数的地址加上偏移 */
2, 没有自己编译的vmlinux: TIPS
如果在lkml或bugzilla上看到一个Oops,而自己不能重现,那就只能反汇编以"Code:"开始的行。 这样可以尝试定位到
源代码中。
注意,Oops中的Code:行,会把导致Oops的第一条指令,也就是EIP的值的第一个字节, 用尖括号括起来。 但是,有些
体系结构(例如常见的x86)指令是不等长的(不一样的指令可能有不一样的长度),所以要不断的尝试(trial-and-error)。
Linus通常使用一个小程序,类似这样:
const char array[] = "\xnn\xnn\xnn...";
int main(int argc, char *argv[])
{
printf("%p\n", array);
*(int *)0 = 0;
}
e.g. /*{{{*/ /* 注意, array一共有从array[0]到array[64]这65个元素, 其中出错的那个操作码 == arry[43] */
#include
#include
const char array[] ="\x6b\xc0\xe8\x2e\x7e\xf6\xff\xe8\xd1\x16\xf2\xff\xb8\x01\x00\x00\x00\xe8\xaa\x1c\xf4\xff\x89\xd8\x83\xc4\x10\x5b\x5d\xc3\x90\x90\x90\x55\x89\xe5\x53\x83\xec\x0c\x8b\x48\x04\x8b\x11\x39\xc2\x74\x18\x89\x54\x24\x08\x89\x44\x24\x04\xc7\x04\x24\xbe\x32\x6b\xc0";
int main(int argc, char *argv[])
{
printf("%p\n", array);
*(int *)0 = 0;
}
/*}}}*/
用gcc -g编译,在gdb里运行它:
[arc@dhcp-cbjs05-218-251 ~]$ gdb hello
GNU gdb Fedora (6.8-1.fc9)
Copyright (C) 2008 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law. Type "show copying"
and "show warranty" for details.
This GDB was configured as "x86_64-redhat-linux-gnu"...
(no debugging symbols found)
(gdb) r
Starting program: /home/arc/hello
0x80484e0
Program received signal SIGSEGV, Segmentation fault.
注意,这时候就可以反汇编0x80484e0这个地址:
(gdb) disassemble 0x80484e0
Dump of assembler code for function array:
0x080484e0 : imul $0xffffffe8,%eax,%eax
0x080484e3 : jle,pn 0x80484dc
0x080484e6 : ljmp *
0x080484e8 : rcll (%esi)
0x080484ea : repnz (bad)
0x080484ec : mov $0x1,%eax
0x080484f1 : call 0x7f8a1a0
0x080484f6 : mov %ebx,%eax
0x080484f8 : add $0x10,%esp
0x080484fb : pop %ebx
0x080484fc : pop %ebp
0x080484fd : ret
0x080484fe : nop
0x080484ff : nop
0x08048500 : nop
0x08048501 : push %ebp
0x08048502 : mov %esp,%ebp
0x08048504 : push %ebx
0x08048505 : sub $0xc,%esp
0x08048508 : mov 0x4(%eax),%ecx
0x0804850b : mov (%ecx),%edx
0x0804850d : cmp %eax,%edx
0x0804850f : je 0x8048529
0x08048511 : mov %edx,0x8(%esp)
0x08048515 : mov %eax,0x4(%esp)
0x08048519 : movl $0xc06b32be,(%esp)
0x08048520 : add %ah,0xa70
End of assembler dump.
(gdb)
OK, 现在你知道出错的那条指令是array[43],也就是mov (%ecx),%edx,也就是说,(%ecx)指向了一个错误内存地址。
补充:
为了使汇编代码和C代码更好的对应起来, Linux内核的Kbuild子系统提供了这样一个功能: 任何一个C文件都可以单独编译成汇编文件,例如:
make path/to/the/sourcefile.s
例如我想把kernel/sched.c编译成汇编,那么:
make kernel/sched.s V=1
或者:
make kernel/sched.lst V=1
编译出*.s文件

有时侯需要对*.s文件进行分析,以确定BUG所在的位置。 对任何一个内核build目录下的*.c文件,都可以
直接编译出*.s文件。
# make drivers/net/e100.s V=1

而对于自己写的module,就需要在Makefile中有一个灵活的target写法:

# cat Makefile
obj-m := usb-skel.o
KDIR := /lib/modules/`uname -r`/build
traget := modules
default:
make -C $(KDIR) M=$(shell pwd) $(target)
clean:
rm -f *.o *.ko .*.cmd *.symvers *.mod.c
rm -rf .tmp_versions
# make target=usb-skel.s V=1

这样,kbuild系统才知道你要make的目标不是modules,而是usb-skel.s。
另外, 内核源代码目录的./scripts/decodecode文件是用来解码Oops的:
./scripts/decodecode


   

论坛徽章:
0
8 [报告]
发表于 2012-02-17 22:07 |只看该作者
回复 7# 瀚海书香


    谢谢,很受用
经过排查发现是自己的驱动中使用了未初始化的变量引起的……

论坛徽章:
0
9 [报告]
发表于 2012-02-19 00:30 |只看该作者
瀚海书香 发表于 2012-02-17 08:57
回复 3# Blaider
下面是我自己存档的一段定位oops代码的资料,希望对你有帮助


===================================
这贴不错,对内核中的错误定位很有帮助。 MARK!

论坛徽章:
0
10 [报告]
发表于 2013-02-26 10:19 |只看该作者
帖子很好,很受用!
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP