Linux环境C语言创建僵尸进程并获取子进程退出状态求助
实现思路与调试指引
现有代码问题说明
你当前编写的代码本身已经具备生成僵尸进程的能力,没有观测到预期效果的核心原因有两个:
- 父进程只sleep 5秒,观测窗口太短,还没来得及执行ps命令查看进程状态,父进程就已经退出,子进程会被系统init进程自动回收,僵尸状态就消失了
- 缺少获取子进程退出状态的相关逻辑,也没有对子进程的退出状态做打印输出
优化后可直接运行的代码
#include <unistd.h> #include <stdlib.h> #include <stdio.h> #include <sys/types.h> #include <sys/wait.h> int main() { pid_t pid = fork(); if (pid == -1) { perror("fork创建子进程失败"); exit(1); } else if (pid == 0) { printf("子进程pid:%d\n", getpid()); printf("对应父进程pid:%d\n", getppid()); // 子进程直接退出,传入自定义退出码123,方便后续验证状态 exit(123); } else { // 延长sleep时间到30秒,预留足够的观测窗口 sleep(30); int wstatus; // 回收指定子进程,获取退出状态 waitpid(pid, &wstatus, 0); printf("当前父进程pid:%d\n",getpid()); if (WIFEXITED(wstatus)) { printf("子进程正常退出,退出状态码:%d\n", WEXITSTATUS(wstatus)); } } return 0; }
调试观测步骤
- 编译代码:执行命令
gcc 代码文件名.c -o zombie_test - 运行程序:执行命令
./zombie_test,程序启动后会先打印子进程的pid信息,之后进入30秒等待 - 观测僵尸进程:在30秒等待期间,新开一个终端窗口,执行命令
ps -ef | grep Z或者ps aux | grep defunct,就能看到状态标记为Z的僵尸进程,进程id和刚才打印的子进程pid一致 - 验证回收逻辑:30秒结束后,父进程会打印自身pid和子进程的退出状态码,此时再执行ps命令查询,僵尸进程已经被父进程回收,不再显示
核心逻辑说明
- 僵尸进程产生条件:子进程先于父进程退出,且父进程没有调用
wait()/waitpid()回收子进程的进程控制块资源,此时子进程就会进入Z(僵尸)状态 - 退出状态获取规则:
waitpid()第二个参数会存储子进程的退出状态信息,需要先用WIFEXITED宏判断子进程是否为正常退出,再用WEXITSTATUS宏解析得到子进程调用exit()时传入的退出码 - 注意事项:不要把
wait()/waitpid()的调用放在sleep()之前,否则父进程会直接阻塞等待子进程退出,第一时间回收子进程资源,就没有窗口可以观测到僵尸进程了
内容的提问来源于stack exchange,提问作者Marco
相关产品推荐
相关产品推荐

