核心句子
子进程在终止时会给父进程发SIGCHLD信号,该信号的默认处理动作是忽略,父进程可以自 定义SIGCHLD信号的处理函数。
僵尸进程的产生:
#include "head.h"
#include <unistd.h>
#include <signal.h>
int main()
{
key_t key = ftok(".",1);
pid_t pid = fork();
if( pid > 0)
{
while(1)
{
printf("I am father\n");
sleep(1);
}
}
else if(pid == 0)
printf("I am child\n");
else
perror("fork()");
}
优先选择#ps -lA | grep a.out
SIGCHLD建立信号处理程序
当SIGCHLD信号正在处理一个终止的子进程时,如果有两个子进程同时终止,那么就产生了两个SIGCHLD信号,父进程只可以捕获一个。
结果是父进程的SIGCHLD信号处理程序每次只调用一次wait()。这样就一定会产生僵尸进程
使用for循环产生10个子进程,十个子进程都是僵尸进程
#include "head.h"
#include <unistd.h>
#include <signal.h>
int handler(int s)
{
wait();
}
int main()
{
key_t key = ftok(".",1);
signal(SIGCHLD,handler);
int i ;
for(i = 0;i<10;i++)
{
pid_t pid = fork();
if (pid == 0)
{
printf("i am child\n");
sleep(1);
exit(0);
}
else if(pid < 0)
perror("fork():");
}
while(1)
{
printf("让程序在这里死循环,然后观察后台进程\n");
sleep(1);
}
}
处理方案
int handler(int s)
{
while(waitpid(-1,NULL,WNOHANG) > 0)
{
continue;
}
}
关于waitpid () 和 wait()的解释请看下一篇博客