如题,使用SIGCHLD信号,为子进程收尸,同时捕捉子进程的退出的状态;
实现效果:
1)回收子进程资源;
2)进程重启(当发现子进程退出后,重启该进程)
#include <stdlib.h>
#include <spawn.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <stdio.h>
#include <string.h>
#include <errno.h>
#include <unistd.h>
int ret,g_pid;
extern char **environ;
char* process_name;
void handle_exit(pid_t pid)
{
if (g_pid==pid)
{
ret = -1;
}
}
void child_end(int signum)
{
int child_status;
int pid;
pid = wait(&child_status);//返回子进程的id.
if (WIFEXITED(child_status))//正常退出
{
printf("process:%d exit normally status: %d\n",pid, child_status);
}
else
{
if (WIFSIGNALED(child_status))//异常退出
{
printf("process:%d exit abnormally status: %d,%s\n",pid, child_status,strerror(errno));
handle_exit(pid);
}
}
}
void carepid()
{
if(ret!= 0)
{
ret=posix_spawn(&g_pid,process_name,NULL,NULL,NULL,environ);
if(ret!= 0)
{
printf("process carepid():failed to start %s proc,%s\n",process_name,strerror(errno));
}else
{
printf("restart process:%s\n",process_name);
}
}
}
int main()
{
if (signal(SIGCHLD, child_end) == SIG_ERR )//回收子进程,避免僵尸进程
{
printf("can't signal(SIGCHLD, child_end)\n");
return 1;
}
process_name="test";//子进程名
ret = posix_spawn(&g_pid,process_name,NULL,NULL,NULL,environ);//启动进程
if(ret!=0)
{
printf("process:failed to start %s proc,%s\n",process_name,strerror(errno));
}
while(1)//进程守护
{
sleep(1);
carepid();
}
return 0;
}
注意: ret=posix_spawn(&g_pid,process_name,NULL,NULL,NULL,environ);
中要使用environ变量,如果置成NULL 的话,子进程和父进程同名。。。
测试结果:
第一次: kill -9 31971后,子进程重启
第二次: kill -9 32015后,子进程重启