一起来解coredump

1.什么是coredump

一般的coredump文件为ELF格式,coredmp包含了程序运行时的内存,寄存器状态,堆栈指针,内存管理信息等。许多程序和操作系统出错时会自动生成一个core文件。coredump可以用在很多场合,使用Linux系统在跑一些压力测试或者系统负载一大的话,系统就hang住了或者干脆system panic。这时唯一能帮助你分析和解决问题的就是coredump了。通常进程或者内核收到

通常情况下coredmp包含了程序运行时的内存,寄存器状态,堆栈指针,内存管理信息等。可以理解为把程序工作的当前状态存储成一个文件。许多程序和操作系统出错时会自动生成一个core文件。signal 11(abort)

2.如何产生和控制Coredump

开启core dump可以使用命令ulimit开启,也可以在程序中通过setrlimit系统调用开启。

打开coredump功能,

1.在终端中输入ulimit -c ,输出结果为0,说明默认结果是关闭coredump的。

2.ulimit -c unlimited 开启coredump功能,并且不限制coredump文件的大小;如果要限制大小,将unlimited修改为数值即可。

3.上述方法只有对当前终端环境有效,想要永久生效,可以修改文件/etc/security/limits.conf.

# /etc/security/limits.conf
#
# each line describe a limit for a user in the form 
#
# <domain> <type> <item> <value>
    *        soft    core unlimited 

4.修改coredump文件保存路径

默认生成的coredump文件保存在可执行文件啊所在目录下,文件名就叫core

通过修改/proc/sys/kernel/core_user_id,生成的core文件名将会变成core.pid.

echo 1> /proc/sys/kernel/core_user_pid

还可以通过修改/proc/sys/kernel/core_pattern,来控制生成core文件保存的位置及文件名格式。

echo "/tem/corefile-%e-%p-%t" > /proc/sys/kernel/core_pattern
//生成的coredump文件保存/tem/corefile目录下,文件格式为“core-文件名-pid-时间戳”

可以通过sysctl或者/proc中来设置core文件的文件名以及生成的路径等。

实际程序中可以通过cat /proc/pid/limits查看进程的资源限制,Max core file size中soft limit为coredump文件支持最大值,0则表示不会生成coredump文件

开启之后还可以设置coredump文件的格式化名字以及生成的路径,/proc/sys/kernel/core_uses_pid支持文件名中带有pid, /proc/sys/kernel/core_pattern可以设置格式化的core文件保存位置或文件名,例如如下示例说明echo "/corefile/core-%e-%p-%t" > core_pattern将会控制所产生的core文件会存放到/corefile目录下,产生的文件名为core-命令名-pid-时间戳

3.读取coredump的命令

gdb exec_file  core_file

使用GDB,先从可执行文件中读取符号表信息,然后读取Core文件。因为Core文件中没有符号表信息,需要加载相应的库文件,无法进行调试。

4.gdb调试

bt(backtrace)/info stack函数调用栈

info args 查看当前参数

info r(resgister)当前寄存器的值

info source 查看当前源程序

info frame 详细的当前栈层的信息

info threads 显示当前可调试的所有线程,前面有*的是当前调试的线程。

Thread + thread ID切换线程

f列出当前的函数

l(list)列出函数的实体

list num 列出当前文件的某行为中心的代码

l文件名或者文件名:行数 显示另外的源文件

连续的l(list) 接着上一次继续向下显示

l - 显示之前的代码

x(examine)检查内存值 x /NFU 地址

注:<N 显示个数,F显示格式(x,d,u,f),U显示的数据单位(b,h,w,g)>

p(print)打印变量的值

pt可以打印出变量的数据结构,而后p可以查看感兴趣的变量

layout:用于分割窗口,可以一边查看代码,一边测试:

layout src:显示源代码窗口

layout asm:显示反汇编窗口

layout regs:显示源代码/反汇编和CPU寄存器窗口

layout split:显示源代码和反汇编窗口

可以使用ctrl + x 然后ctrl +a进行窗口的切换。

Forward-search  字串 向前搜索源码

Reverse-search  字串  全部搜索

成功获取core文件,并将拷贝的core文件放入对应的process的程序工程目录下同一目录下且工程目录有process生成bin文件,cd到process的目录

XXX-XXX-XX-gdb bin core

进入gdb模式,调试中可能有一些库要用到,所以还要设置gdb中调用库的库文件的绝对路径,一般linux嵌入式一般是生成的文件系统作为调用路径

initially, you will see a lot of error messages. They can be ignored.  Now on the gdb prompt, type:

(gdb) set solib-absolute-prefix SRCPATH/targets/PROFILE/fs.install

(gdb) bt

bt之后可以看见打印的堆栈信息。

造成程序coredump的原因

1 内存访问越界

2.多线程程序使用了线程不安全的函数。

3.多线程读写的数据未加锁保护。对于会被多个线程同时访问的全局数据,应该注意加锁保护,否则很容易造成core dump

4.非法指针

5.堆栈溢出

5.demo

gcc -g *.c -o *

./*

gdb ./* core_dump

时间紧就不传了,有需要的可以评论。

参考链接

http://www.cnblogs.com/hazir/p/linxu_core_dump.html

http://www.cnblogs.com/niocai/archive/2012/04/01/2428128.html

http://baidutech.blog.51cto.com/4114344/904419/

猜你喜欢

转载自blog.csdn.net/u012516571/article/details/82345311