Segment fault及LINUX core dump详解

时间:2022-08-29 00:28:30

源自:http://andyniu.iteye.com/blog/1965571

core dump的概念:

core dump is the recorded state of the working memory of a computer program at a specific time, generally when the program has terminated abnormally (crashed). In practice, other key pieces of program state are usually dumped at the same time, including the processor registers, which may include the program counter and stack pointer, memory management information, and other processor and operating system flags and information. The name comes from the once-standard memory technology core memory. Core dumps are often used to diagnose or debug errors in computer programs.

On many operating systems, a fatal error in a program automatically triggers a core dump, and by extension the phrase "to dump core" has come to mean, in many cases, any fatal error, regardless of whether a record of the program memory is created.

Linux平台下,设置core dump文件生成的方法:

linux coredump调试
 
1 )如何生成 coredump 文件 ?
登陆 LINUX 服务器,任意位置键入
       echo "ulimit -c 1024" >> /etc/profile
退出 LINUX 重新登陆 LINUX
键入 ulimit -c
如果显示 1024 那么说明 coredump 已经被开启。
1024 限制产生的 core 文件的大小不能超过 1024kb,可以使用参数unlimited,取消该限制
ulimit -c unlimited
2 ) . core 文件的简单介绍
在一个程序崩溃时,它一般会在指定目录下生成一个 core 文件。 core 文件仅仅是一个内存映象 ( 同时加上调试信息 ) ,主要是用来调试的。
3 ) . 开启或关闭 core 文件的生成
用以下命令来阻止系统生成 core 文件 :
ulimit -c 0
下面的命令可以检查生成 core 文件的选项是否打开 :
ulimit -a
该命令将显示所有的用户定制,其中选项 -a 代表“ all ”。
也可以修改系统文件来调整 core 选项
在 /etc/profile 通常会有这样一句话来禁止产生 core 文件,通常这种设置是合理的 :
# No core files by default
ulimit -S -c 0 > /dev/null 2>&1
但是在开发过程中有时为了调试问题,还是需要在特定的用户环境下打开 core 文件产生的设置。
在用户的 ~/.bash_profile 里加上 ulimit -c unlimited 来让特定的用户可以产生 core 文件。
如果 ulimit -c 0 则也是禁止产生 core 文件,而 ulimit -c 1024 则限制产生的 core 文件的大小不能超过 1024kb
4 ) . 设置 Core Dump 的核心转储文件目录和命名规则
/proc/sys/kernel/core_uses_pid 可以控制产生的 core 文件的文件名中是否添加 pid 作为扩展 ,如果添加则文件内容为 1 ,否则为 0
proc/sys/kernel/core_pattern 可以设置格式化的 core 文件保存位置或文件名 ,比如原来文件内容是 core-%e
可以这样修改 :
echo "/corefile/core-%e-%p-%t" > core_pattern
将会控制所产生的 core 文件会存放到 /corefile 目录下,产生的文件名为 core- 命令名 -pid- 时间戳
以下是参数列表 :
    %p - insert pid into filename 添加 pid
    %u - insert current uid into filename 添加当前 uid
    %g - insert current gid into filename 添加当前 gid
    %s - insert signal that caused the coredump into the filename 添加导致产生 core 的信号
    %t - insert UNIX time that the coredump occurred into filename 添加 core 文件生成时的 unix 时间
    %h - insert hostname where the coredump happened into filename 添加主机名
    %e - insert coredumping executable name into filename 添加命令名
6 ) . 一个小方法来测试产生 core 文件
直接输入指令 :
kill -s SIGSEGV $$

如何产生Core Dump

发生doredump一般都是在进程收到某个信号的时候,Linux上现在大概有60多个信号,可以使用 kill -l 命令全部列出来。

@sagi-laptop:~$ -l
) SIGHUP ) SIGINT ) SIGQUIT ) SIGILL ) SIGTRAP
) SIGABRT ) SIGBUS ) SIGFPE ) SIGKILL ) SIGUSR1
) SIGSEGV ) SIGUSR2 ) SIGPIPE ) SIGALRM ) SIGTERM
) SIGSTKFLT ) SIGCHLD ) SIGCONT ) SIGSTOP ) SIGTSTP
) SIGTTIN ) SIGTTOU ) SIGURG ) SIGXCPU ) SIGXFSZ
) SIGVTALRM ) SIGPROF ) SIGWINCH ) SIGIO ) SIGPWR
) SIGSYS ) SIGRTMIN ) SIGRTMIN+362 ) SIGRTMIN+384 ) SIGRTMIN+406 ) SIGRTMIN+428
) SIGRTMIN+4410 ) SIGRTMIN+4612 ) SIGRTMIN+4814 ) SIGRTMIN+5014 ) SIGRTMAX-5212
) SIGRTMAX-5410 ) SIGRTMAX-568 ) SIGRTMAX-586 ) SIGRTMAX-604 ) SIGRTMAX-622
) SIGRTMAX-64
)SIGQUIT   )SIGILL    )SIGABRT   )SIGFPE    )SIGSEGV    )SIGBUS    )SIGSYS
)SIGTRAP )SIGXCPU )SIGXFSZ )SIGIOT

我们看到SIGSEGV在其中,一般数组越界或是访问空指针都会产生这个信号。另外虽然默认是这样的,但是你也可以写自己的信号处理函数改变默认行为,更多信号相关可以看参考链接33

上述内容只是产生coredump的必要条件,而非充分条件。要产生core文件还依赖于程序运行的shell,可以通过ulimit -a命令查看,输出内容大致如下:

@sagi-laptop:~$ -a core size ) size ) unlimited scheduling priority ) file (blocks, -f(-i16382 max locked memory ) size ) unlimited open files ) size 512 bytes, -p8 POSIX message queues ) (-r0 stack (kbytes, -s8192 cpu (seconds, -t(-u(kbytes, -vfile locks ) unlimited

看到第一行了吧,core file size,这个值用来限制产生的core文件大小,超过这个值就不会保存了。我这里输出是0,也就是不会保存core文件,即使产生了,也保存不下来==! 要改变这个设置,可以使用ulimit -c unlimited。

OK, 现在万事具备,只缺一个能产生Core的程序了,介个对C程序员来说太容易了。

"margin:0px; padding:0px; border:0px currentColor; color:rgb(51,153,51); vertical-align:baseline; background-color:transparent">#include <stdio.h>;</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(51,153,51); vertical-align:baseline; background-color:transparent">#include <stdlib.h>;</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(153,51,51); vertical-align:baseline; background-color:transparent">int</span> crash<span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">(</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">)</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">{</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(153,51,51); vertical-align:baseline; background-color:transparent">char</span> <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(51,153,51); vertical-align:baseline; background-color:transparent">*</span>xxx <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(51,153,51); vertical-align:baseline; background-color:transparent">=</span> <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(255,0,0); vertical-align:baseline; background-color:transparent">"crash!!"</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(51,153,51); vertical-align:baseline; background-color:transparent">;</span>
  • xxx<span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">[</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,0,221); vertical-align:baseline; background-color:transparent">1</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">]</span> <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(51,153,51); vertical-align:baseline; background-color:transparent">=</span> <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(255,0,0); vertical-align:baseline; background-color:transparent">'D'</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(51,153,51); vertical-align:baseline; background-color:transparent">;</span> <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(102,102,102); font-style:italic; vertical-align:baseline; background-color:transparent">// 写只读存储区!</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(177,177,0); vertical-align:baseline; background-color:transparent">return</span> <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,0,221); vertical-align:baseline; background-color:transparent">2</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(51,153,51); vertical-align:baseline; background-color:transparent">;</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">}</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(153,51,51); vertical-align:baseline; background-color:transparent">int</span> foo<span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">(</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">)</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">{</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(177,177,0); vertical-align:baseline; background-color:transparent">return</span> crash<span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">(</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">)</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(51,153,51); vertical-align:baseline; background-color:transparent">;</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">}</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(153,51,51); vertical-align:baseline; background-color:transparent">int</span> main<span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">(</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">)</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">{</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(177,177,0); vertical-align:baseline; background-color:transparent">return</span> foo<span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">(</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">)</span><span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(51,153,51); vertical-align:baseline; background-color:transparent">;</span>
  • <span style="margin:0px; padding:0px; border:0px currentColor; color:rgb(0,153,0); vertical-align:baseline; background-color:transparent">}</span>

上手调试

?
2
4
6
8
10
12
#include <stdio.h>
 
{
*p = 0;
 
{
func(NULL);
return
0;
}
 
生成可执行文件并运行
gcc -o main a.c
root@ubuntu:~# ./main
Segmentation fault (core dumped) 
<-----这里出现段错误并生成core文件了。
在/tmp目录下发现文件core-main-10815 
 
如何查看进程挂在哪里了?
我们可以用
gdb main /tmp/core-main-10815 
查看信息,发现能定位到函数了
Program terminated with signal 11, Segmentation fault.
#0  0x080483ba in func ()
 

如何定位到行?

在编译的时候开启-g调试开关就可以了
gcc -o main -g a.c
gdb
main /tmp/core-main-10815 
最终看到的结果如下,好棒。
Program terminated with signal 11, Segmentation fault.
#0  0x080483ba in func (p=0x0) at a.c:5
5          *p = 0;
 
总结一下,需要定位进程挂在哪一行我们只需要4个操作,
ulimit
-c unlimited
/proc/sys/kernel/core_pattern
gcc -o main -g a.c
gdb main /tmp/core-main-10815 
就可以啦。

上边的程序编译的时候有一点需要注意,需要带上参数-g, 这样生成的可执行程序中会带上足够的调试信息。编译运行之后你就应该能看见期待已久的“Segment Fault(core dumped)”或是“段错误 (核心已转储)”之类的字眼了。看看当前目录下是不是有个core或是core.xxx的文件。祭出linux下经典的调试器GDB,首先带着core文件载入程序:gdb exefile core,这里需要注意的这个core文件必须是exefile产生的,否则符号表会对不上。载入之后大概是这个样子的:

@sagi-laptop:~$ /coredump';
(gdb)

我们看到已经能直接定位到出core的地方了,在第8行写了一个只读的内存区域导致触发Segment Fault信号。在载入core的时候有个小技巧,如果你事先不知道这个core文件是由哪个程序产生的,你可以先随便找个代替一下,比如/usr/bin/w就是不错的选择。比如我们采用这种方法载入上边产生的core,gdb会有类似的输出:

@sagi-laptop:~$ /usr//coredump
启动程序:run
  • 打印堆栈信息:bt

Segment fault及LINUX core dump详解的更多相关文章

  1. Segment fault及LINUX core dump详解 (zz&rpar;

    C 程序在进行中发生segment fault(core dump)错误,通常与内存操作不当有关,主要有以下几种情况: (1)数组越界. (2)修改了只读内存. (3)scanf("%d&q ...

  2. 【转】段错误调试神器 - Core Dump详解

    from:http://www.embeddedlinux.org.cn/html/jishuzixun/201307/08-2594.html 段错误调试神器 - Core Dump详解 来源:互联 ...

  3. 段错误调试神器 - Core Dump详解

    一.前言: 有的程序可以通过编译, 但在运行时会出现Segment fault(段错误). 这通常都是指针错误引起的. 但这不像编译错误一样会提示到文件某一行, 而是没有任何信息, 使得我们的调试变得 ...

  4. 造成segment fault,产生core dump的可能原因

    1.内存访问越界 a) 由于使用错误的下标,导致数组访问越界 b) 搜索字符串时,依靠字符串结束符来判断字符串是否结束,但是字符串没有正常的使用结束符 c) 使用strcpy, strcat, spr ...

  5. 【转】 Linux Core Dump 介绍

    ===============================================================  Linux core dump的祥细介绍和使用 =========== ...

  6. linux core dump 文件 gdb分析

    core dump又叫核心转储, 当程序运行过程中发生异常, 程序异常退出时, 由操作系统把程序当前的内存状况存储在一个core文件中, 叫core dump. (linux中如果内存越界会收到SIG ...

  7. Linux core dump file详解

    Linux core dump file详解 http://www.cnblogs.com/langqi250/archive/2013/03/05/2944931.html

  8. 红帽Linux故障定位技术详解与实例&lpar;2&rpar;

    红帽Linux故障定位技术详解与实例(2) 2011-09-28 14:26 圈儿 BEAREYES.COM 我要评论(0) 字号:T | T 在线故障定位就是在故障发生时, 故障所处的操作系统环境仍 ...

  9. linux进程地址空间详解(转载)

    linux进程地址空间详解(转载) 在前面的<对一个程序在内存中的分析 >中很好的描述了程序在内存中的布局,这里对这个结果做些总结和实验验证.下面以Linux为例(实验结果显示window ...

随机推荐

  1. 10&period;Pattern 和 Matcher

    Pattern:正则表达式的模式类 获取对象的函数Pattern pattern=Pattern.compiler(regex); 功能函数: 1.pattern.split(String targe ...

  2. WIN10 CMD 启动虚拟WIFI

    1.以管理员身份运行命令提示符: 快捷键win+R→输入cmd→回车 2.启用并设定虚拟WiFi网卡: 运行命令:netsh wlan set hostednetwork mode=allow ssi ...

  3. IOS框架和服务

    在iOS中框架是一个目录,包含了共享资源库,用于访问该资源库中储存的代码的头文件,以及图像.声音文件等其他资源.共享资源库定义应用程序可以调用的函数和方法. iOS为应用程序开发提供了许多可使用的框架 ...

  4. chroot directory

    给 /A/B/C的C目录做chroot,要对C能读写,所以C目录不能做ROOT目录,对B做chroot. 设置C目录所有者为sftp 账户a,组也改为sftp组(这里a和sftp组都是之前建立好的sf ...

  5. poj 1067 取石子游戏(威佐夫博奕(Wythoff Game))

    这里不在详细介绍威佐夫博弈论 简单提一下 要先提出一个名词“奇异局势”,如果你面对奇异局势则必输 奇异局势前几项(0,0).(1,2).(3,5).(4,7).(6,10).(8,13).(9,15) ...

  6. 在VC&plus;&plus;中使用Tab Control控件

    系统环境:Windows 7软件环境:Visual Studio 2008 SP1本次目的:在模态或非模态对话框中使用Tab Control控件,及引申在单/多文档中使用 查阅MSDN文档,对于创建T ...

  7. LANMP On CentOS 6

    摘要 --在CentOS6.2-x86_64上安装Apache,Nginx,MySQL,Php 环境:最小化安装系统 yum install lrzsz mlocate.x86_64 wget lso ...

  8. 关于NPOI导入的时候有时出现乱码解决办法

    手上这个项目之前客户说过导入的时候回出现乱码问题,一直没用重视,现在自己做做一个功能,乱码经常出现,开始以为是代码的问题,最后百度了试了很多方法猜找到解决办法: 乱码页面如下: 解决办法: 打开IIS ...

  9. Ionic常用命令

    安装ionic npm install -g ionic 更新www/lib/ionic 目录的文件,如有项目中有bower,此命令会运行bower update ionic, 否则则会从CDN上下载 ...

  10. Django-website 程序案例系列-10 cookie 和 session的应用

    cookie:  现在所有网站基本都要开启cookie 客户端浏览器上的一个文件 例如:   {‘key’: 'sefwefqefwefw'} 是一个键值对 简单实现cookie认证: user_in ...