Liunx操作-Record17—子进程回收相关的函数(”wait“及”waitpid“)

目录

回收子进程:"pid_t wait(int *status);"

回收子进程:"pid_t waitpid(pid_t pid, int *status, int options);"


回收子进程:"pid_t wait(int *status);"

  • status 传出参数
  • 返回值成功:返回 终止的子进程ID;失败: 返回 -1

用来知道子进程的死亡原因,作用:

  • 阻塞等待(如果子进程没死的话)
  • 回收子进程资源(如果子进程死的话)
  • 查看死亡原因(如果子进程死的话)

死亡原因:

  • 正常死亡 WIFEXITED
    • 如果WIFEXITED为真,使用 WEXITSTATUS 得到退出状态
  • 非正常死亡 WIFSIGNALED
    • 如果WIFSIGNALED 为真,使用WTERMSIG 得到信号

下面创建一个僵尸进程,那么看wait函数如何处理:

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <stdlib.h>

int main()
{
    pid_t pid = fork();
    if(pid == 0){
        printf("I am child,will die!\n");
        sleep(2);
    }
    else if(pid > 0){
        printf("I am parent,wait for child die!\n");
        pid_t wpid = wait(NULL);
        printf("wait ok,wpid=%d,pid=%d\n",wpid,pid);
        while(1){
            sleep(1);
        }
    }
    return 0;
}

运行如下: 

可以看出,这个wait可以回收僵尸进程。 

下面用wait来显示下成为僵尸进程的死亡原因:

int main()
{
    pid_t pid = fork();
    if(pid == 0){
        printf("I am child,will die!\n");
        sleep(2);
        while(1){
            printf("I am child,guo lai da wo!\n");
            sleep(1);
        }
        //return 101;
        exit(102);
    }
    else if(pid > 0){
        printf("I am parent,wait for child die!\n");
        int status;

        pid_t wpid = wait(&status);
        printf("wait ok,wpid=%d,pid=%d\n",wpid,pid);
        if(WIFEXITED(status)){
            printf("child exit with %d\n",WEXITSTATUS(status));
        }
        if(WIFSIGNALED(status)){
            printf("child killed by %d\n",WTERMSIG(status));
        }

        while(1){
            sleep(1);
        }
    }
    return 0;
}

可以根据死亡原因进行输出:

 回收子进程:"pid_t waitpid(pid_t pid, int *status, int options);"

  • pid
    • < -1  -组id
    • -1   回收任意
    • 0    回收和调用进程组id相同组内的子进程
    • >0  回收指定的pid
  • options
    • 0 与wait相同,也会阻塞
    • WNOHANG 如果当前没有子进程退出的,会立刻返回
  • 返回值
    • 如果设置了WNOHANG,那么如果没有子进程退出,返回0
      • 如果有子进程退出,返回退出的子进程pid
    • 失败返回-1(没有子进程)

比wait函数更强大,其中,WNOHANG,保证了如果子进程没有死亡的话,其会立刻进行返回(而wait函数的处理方式是阻塞等待),相当于不阻塞了就。如果将"option"项填入"0",那这个函数就相当于wait函数了就。

很明显waitpid比wait函数用的就麻烦一些,

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/wait.h>

int main()
{
    pid_t pid = fork();

    if(pid == 0){
        printf("I am child,pid=%d\n",getpid());
        sleep(2);
    }
    else if(pid > 0){
        printf("I am parent,pid=%d\n",getpid());

        int ret ;
        while((ret= waitpid(-1,NULL,WNOHANG) ) == 0 ){
            sleep(1);
        }
        printf("ret = %d\n",ret);
        ret = waitpid(-1,NULL,WNOHANG);
        if(ret < 0){
            perror("wait err");
        }
        while(1){
            sleep(1);
        }
    }
    return 0;
}

运行如下:

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值