【发布时间】:2017-06-03 19:58:40
【问题描述】:
我写了一个程序,故意让子进程触发SIGSEGV。但是,我希望子进程异常终止。现在我在信号处理程序中使用 exit() 。但是 exit() 调用总是会产生一个正常的终止。我应该使用哪个功能来实现这一点?另一个问题是如何让父进程知道子进程因为 SIGSEGV 而终止?
extern char etext, edata, end;
void handler() {
pid_t pid;
pid = getpid();
char buf[100];
snprintf(buf, 100, "child %d terminated by signal 11", (int)pid);
psignal(SIGSEGV, buf);
exit(-1);
}
int main(int argc, char **argv) {
if (signal(SIGSEGV, handler) == SIG_ERR) {
perror("signal error");
}
printf("First address beyond:\n");
printf(" program text segment(etext) %10p\n", &etext);
printf(" initialized data segment(edata) %10p\n", &edata);
printf(" uninitialized data segment (end) %10p\n", &end);
if (fork() == 0) {
printf("from Child before\n");
etext = 'a';
printf("from Child after\n");
} else {
pid_t pid;
int status;
if ((pid == waitpid(-1, &status, 0)) >= 0) {
printf("Handler reaped child %d\n", (int)pid);
}
printf("child WIFEXITED = %d, WEXITSTATUS = %d\n", WIFEXITED(status), WEXITSTATUS(status));
if (WEXITSTATUS(status) == -3) {
printf("Capture the exit code\n");
}
}
【问题讨论】:
-
有 _exit() 函数,它不调用 atexit() 函数,而只是(非常)立即终止。
-
使用 gcc 4.7.2 通过
cc sigsegv.c(将其保存到sigsegv.c之后)运行您的代码时,我遇到了一大堆错误。你能修复代码以便编译吗? -
我想您可以重置信号处理程序,然后自己触发分段违规? (例如通过取消引用空指针。)这将触发 SIGSEGV 并结束进程,但当然错误将发生在某个位置而不是发生原始错误的位置。
-
异常终止怎么定义?