这里写自定义目录标题
一、core dump(核心转储)
core dump即”核心转储“程序崩溃时操作系统自动生成的内存快照文件(通常命名为core或core.PID),包含崩溃瞬间的进程内存、寄存器状态、堆栈信息等。用于事后调试定位崩溃原因,常用于C++程序员调试程序。
| core错误 | 错误原因 |
|---|---|
| 段错误(Segmentation fault) | 程序访问了无效的内存地址,比如试图访问未分配的内存或者已经释放的内存 |
| 空指针引用(Null pointer dereference) | 程序试图使用空指针(null pointer)访问内存中的数据时,会导致空指针引用错误 |
| 内存访问越界(Out of bounds memory access) | 程序试图访问数组或者其他数据结构超出其边界范围的内存,就会发生内存访问越界错误 |
| 使用已释放的内存(Use after free) | 程序试图在已经释放的内存地址上进行读取或写入操作时,就会发生使用已释放的内存错误 |
| 栈溢出(Stack overflow): | 程序递归调用层数过深或者在栈上分配了过多的内存时,会导致栈溢出错误 |
| 无效的指令或操作码(Invalid instruction or opcode) | 执行了不存在或无效的机器指令或操作码,会导致无效指令错误 |
二、使用gdb分析Core Dump文件
gdb /path/to/program /path/to/core_file # 加载程序与core文件
常用命令如下
| 命令 | 作用 | 示例 |
|---|---|---|
| bt | 打印崩溃时的堆栈回溯 | (gdb) bt |
| frame N | 切换到指定栈帧 | (gdb) frame 1 |
| info registers | 查看寄存器状态 | (gdb) info registers |
| p variable | 查看变量值 | (gdb) p *ptr |
| list | 显示崩溃位置附近源码 | (gdb) list |
三、可能遇到的问题
1 找不到core
一般而言可能遇到的问题就是找不到生成的core文件。在默认的情况下,core文件一般会生成在工作目录中,但是也有的时候不一定。这时,可以按照如下方法调试
- 查看系统是否开启了核心转储
输入指令
ulimit -a
可以看到core file size为0,即意味着生成的core文件大小限制为0,那么当然是找不到core文件的。
real-time non-blocking time (microseconds, -R) unlimited
core file size (blocks, -c) 0
data seg size (kbytes, -d) unlimited
scheduling priority (-e) 0
file size (blocks, -f) unlimited
pending signals (-i) 31254
max locked memory (kbytes, -l) 1010508
max memory size (kbytes, -m) unlimited
open files (-n) 1024
pipe size (512 bytes, -p) 8
POSIX message queues (bytes, -q) 819200
real-time priority (-r) 0
stack size (kbytes, -s) 8192
cpu time (seconds, -t) unlimited
max user processes (-u) 31254
virtual memory (kbytes, -v) unlimited
file locks (-x) unlimited
可以输出命令ulimit -c unlimited,开启核心转储,仅对该终端有效,下次重启终端则失效了。
这时我们再去运行程序,在程序终止运行的时候,就会爆出错误xxxxx(core dump),类似的字样,再去该文件夹下寻找core文件用gdb调试即可。
2. 但是,有的时候core文件确实是生成了,它却不在工作目录中。接着我们可以输入命令cat /proc/sys/kernel/core_pattern查看core文件保存的位置。这时候会有两种情况:
-
若返回路径
(如 /path/core.%e.%p),那就存在path中,去相应位置找到core文件即可。 -
如果返回管道命令
(如 |/usr/lib/systemd/systemd-coredump),文件由 systemd-coredump 管理,路径为/var/lib/systemd/coredump/。可以输入命令查看core文件信息,包括进程、时间等信息。coredumpctl list然后通过
coredumpctl -o 自定义文件名 dump <Pid>取出core文件来调试。
2 永久开启核心转储
- 只需要把刚刚的命令
ulimit -c unlimited追加到/etc/profile或者~/bashrc中。
echo "ulimit -c unlimited" >> ~/.bashrc
这种方法仅对交互式shell有效,但是对守护进程无效
2. 也可以修改全局配置文件 /etc/security/limits.conf
sudo vim /etc/security/limits.conf
添加或者修改以下内容
* soft core unlimited # 所有用户生效(软限制)
* hard core unlimited # 所有用户生效(硬限制)
三、修改core文件生成位置
# 修改内核参数(临时生效)
echo "/tmp/coredump/core.%e.%p.%t" | sudo tee /proc/sys/kernel/core_pattern
# 永久生效:编辑/etc/sysctl.conf
echo "kernel.core_pattern=/tmp/coredump/core.%e.%p.%t" | sudo tee -a /etc/sysctl.conf
sudo sysctl -p # 应用配置
要注意指定的位置/tmp/cordump文件夹是否有权限,如果没有权限应chmod给权限,否则不能core dump。
上述指令参数含义如下
%p 出Core进程的PID
%u 出Core进程的UID
%s 造成Core的signal号
%t 出Core的时间,从1970-01-0100:00:00开始的秒数
%e 出Core进程对应的可执行文件名
四、调试正在运行中的进程
ps -ef | grep 程序名 # 获取程序的进程编号
gdb 程序名 -p 进程编号

1万+

被折叠的 条评论
为什么被折叠?



