如何以编程方式在C / C ++中导致核心转储
我想强制在我的C ++应用程序的特定位置的核心转储。
我知道我可以做这样的事情:
int * crash = NULL; *crash = 1; 但是我想知道是否有更清洁的方法?
顺便说一句,我正在使用Linux。
 信号编号6( SIGABRT在Linux中)的提高是一种方法(尽pipe要记住,在所有的POSIX实现中SIGABRT不要求是6,所以如果这不是快速的,你可能想要使用SIGABRT值本身'n'dirtydebugging代码)。 
 #include <signal.h> : : : raise (SIGABRT); 
 调用abort()也会导致核心转储,甚至可以在不终止进程的情况下通过在subprocess中调用fork()和abort()来完成此任务 – 请参阅此答案以获取详细信息。 
几年前,Google发布了Coredumper库。
概观
Coredumper库可以被编译成应用程序来创build正在运行的程序的核心转储 – 无需终止。 即使内核本身不支持multithreading核心文件,它也支持单线程和multithreading核心转储。
Coredumper是根据BSD许可条款分发的。
例
这绝不是一个完整的例子。 它只是给你一个Coredumper API的样子。
#include <google/coredumper.h> ... WriteCoreDump('core.myprogram'); /* Keep going, we generated a core file, * but we didn't crash. */
这不是你要求的,但也许它更好:)
 #include <stdlib.h> // C //#include <cstdlib> // C++ void core_dump(void) { abort(); } 
如信号手册页中所列,任何具有列为“核心”动作的信号都将强制进行核心转储。 一些例子是:
 SIGQUIT 3 Core Quit from keyboard SIGILL 4 Core Illegal Instruction SIGABRT 6 Core Abort signal from abort(3) SIGFPE 8 Core Floating point exception SIGSEGV 11 Core Invalid memory reference 
确保你启用了核心转储:
 ulimit -c unlimited 
中止();
相关的,有时你会想要一个没有实际核心转储的后台跟踪,并允许程序继续运行:检查glibc backtrace()和backtrace_symbols()函数: http : //www.gnu.org/s/libc/手动/ html_node / Backtraces.html
你可以使用kill(2)发送信号。
 #include <sys/types.h> #include <signal.h> int kill(pid_t pid, int sig); 
所以,
 kill(getpid(), SIGSEGV); 
生成核心转储的另一种方法是:
 $ bash $ kill -s SIGSEGV $$ 
 只需创build一个新的bash实例,并用指定的信号杀死它。  $$是shell的PID。 否则,你正在杀死你当前的bash,将被注销,terminalclosures或断开连接。 
 $ bash $ kill -s SIGABRT $$ $ bash $ kill -s SIGFPE $$ 
有时这样做可能是适当的:
 int st = 0; pid_t p = fork(); if (!p) { signal(SIGABRT, SIG_DFL); abort(); // having the coredump of the exact copy of the calling thread } else { waitpid(p, &st, 0); // rip the zombie } // here the original process continues to live 
这种简单方法的一个问题是只有一个线程会被盗取。
 #include <assert.h> . . . assert(!"this should not happen"); 
  #include <stdio.h> #include <stdlib.h> int main() { printf("\n"); printf("Process is aborting\n"); abort(); printf("Control not reaching here\n"); return 0; } 
使用这种方法,无论你想:)