使用fork创建父子进程:通过信号实现子进程按输入异常终止并让父进程识别终止状态的技术方案
解决父子进程终止状态判断与异常通知的问题
嘿,我来帮你把这个逻辑理清楚,顺便把代码补全!你现在的问题主要聚焦在两个点:子进程如何通过信号实现异常终止,以及父进程怎么正确识别子进程的终止状态,咱们一步步拆解:
先修正几个基础小问题
fork是函数,调用时必须加括号:fork()scanf("%d\n",&ans);里的\n会导致输入后需要额外回车才能触发读取,改成scanf("%d", &ans);就正常了- 惯例上
exit(0)表示正常终止,exit(非0)一般用于正常退出但带错误状态的场景,咱们调整下更符合规范
子进程异常终止的实现
如果输入不是5,子进程可以通过raise()函数给自己发送一个终止信号(比如SIGABRT,这是专门用于标记异常终止的信号),这样父进程就能通过状态判断出子进程是被信号强制终止的。
父进程的状态判断逻辑
父进程必须先调用wait()或waitpid()来获取子进程的终止状态(你之前的代码漏掉了这关键一步!),然后用以下系统宏来判断:
WIFEXITED(status):若子进程通过exit()或_exit()正常终止,该宏返回真WIFSIGNALED(status):若子进程被信号终止,该宏返回真WTERMSIG(status):如果是被信号终止,这个宏能返回导致终止的信号编号
完整代码示例
#include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <sys/wait.h> #include <signal.h> int main() { int ans; pid_t pid = fork(); // 调用fork并保存进程ID if (pid == 0) { // 子进程逻辑 printf("请输入一个整数:"); scanf("%d", &ans); // 修正scanf格式问题 if (ans == 5) { printf("子进程:输入正确,正常终止\n"); exit(0); // 正常终止用exit(0)更符合惯例 } else { printf("子进程:输入不符合要求,触发异常终止\n"); raise(SIGABRT); // 给自己发送异常终止信号,通知父进程 } } else if (pid > 0) { // 父进程逻辑 int status; wait(&status); // 阻塞等待子进程终止,并获取其终止状态 if (WIFEXITED(status)) { // 子进程正常终止分支 printf("父进程:子进程正常终止,退出码:%d\n", WEXITSTATUS(status)); } else if (WIFSIGNALED(status)) { // 子进程被信号终止分支 printf("父进程:子进程异常终止,终止信号编号:%d\n", WTERMSIG(status)); } } else { // fork调用失败的异常处理 perror("fork调用失败"); exit(1); } return 0; }
代码逻辑解释
- 子进程部分:输入5时用
exit(0)正常退出;输入其他值时调用raise(SIGABRT),这个信号会直接终止子进程,同时让父进程能捕获到异常终止的事件。 - 父进程部分:通过
wait(&status)阻塞等待子进程结束,之后用WIFEXITED判断是否为正常终止,用WIFSIGNALED判断是否为信号终止,还可以通过WEXITSTATUS获取正常终止的退出码,WTERMSIG获取终止信号的具体编号。
这样就能完美实现你想要的逻辑啦!
内容的提问来源于stack exchange,提问作者kateTs
相关产品推荐
相关产品推荐

