Linux系统编程-父进程等待子进程退出wait,僵尸进程,孤儿进程

一.函数原型

#include <sys/types.h>

#include <sys/wait.h>

pid_t wait(int *status);

pid_t waitpid(pid_t pid, int *status, int options);

int waitid(idtype_t idtype, id_t id, siginfo_t *infop, int options);

二.返回值

如果执行成功则返回子进程识别码(PID),如果有错误发生则返回-1。失败原因存于errno 中。

三.函数说明

参数 status 是一个整形指针。如果status不是一个空指针,则终止进程的终止状态将存储在该指针所指向的内存单元中。如果不关心终止状态,可以将 status参数设置为NULL。
status 不是NULL时子进程的结束状态值会由参数 status 返回,而子进程的进程识别码作为函数返回值返回。
调用 wait 函数时,调用进程将会出现下面的情况:
· 如果其所有子进程都还在运行,则阻塞。
· 如果一个子进程已经终止,正等待父进程获取其终止状态,则获取该子进程的终止状态然后立即返回。
· 如果没有任何子进程,则立即出错返回。

四。僵尸进程

僵尸进程是当子进程比父进程先结束,而父进程又没有回收子进程,释放子进程占用的资源,此时子进程将成为一个僵尸进程。如果父进程先退出 ,子进程被init接管,子进程退出后init会回收其占用的相关资源

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

int main()
{
	pid_t pid;

	int cnt = 0;

	pid = vfork();

	if(pid > 0){//父进程没有调用wait()等待子进程
		while(1){
			printf("this is father pid, pid = %d\n",getpid());
			printf("father cnt = %d\n",cnt);
			sleep(3);
		}
	}else if(pid == 0){
		while(1){
			printf("this is child pid ,pid = %d\n",getpid());
			cnt++;
			printf("child cnt = %d\n",cnt);
			sleep(3);
			if(cnt == 5){
				exit(0);
			}
		}
	}

	return 0;
}

运行结果:
在这里插入图片描述

五.父进程等待子进程的退出,并收集其状态

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

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

int main()
{
	pid_t pid;
	int cnt = 0;
 	int status;

	pid = fork();

	if(pid > 0){
			//wait(NULL);
            wait(&status);//等待子进程
/*          wait与waitpid的区别:
			wait使调用者阻塞,waitpid有一个选项,可以使调用者不阻塞
*/   //	 		waitpid(pid,&status,WNOHANG);

  			printf("child quit,child status = %d\n",WEXITSTATUS(status));//收集子进程返回状态
		while(1){	
			printf("this is father pid, pid = %d\n",getpid());
			printf("father cnt = %d\n",cnt);
			sleep(3);
		}
	}else if(pid == 0){
		while(1){
			printf("this is child pid ,pid = %d\n",getpid());
			cnt++;
			printf("child cnt = %d\n",cnt);
			sleep(3);
			if(cnt == 5){
				exit(3);
			}
		}
	}

	return 0;
}

运行结果
在这里插入图片描述

六.孤儿进程

在类UNIX操作系统中,子进程是通过父进程创建的,子进程再创建新的进程。子进程的结束和父进程的运行是一个异步过程,即父进程永远无法预测子进程 到底什么时候结束。当一个父进程由于正常完成工作而退出或由于其他情况被终止,它的一个或多个子进程却还在运行,那么那些子进程将成为孤儿进程。为避免孤儿进程退出时无法释放所占用的资源而僵死进程号为1的init进程将会接受这些孤儿进程,这一过程也被称为“收养”。

代码展示:

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

int main()
{
	pid_t pid;
	int cnt = 0;
 	int status;

	pid = vfork();

	if(pid > 0){
			printf("this is father pid, pid = %d\n",getpid());
	}else if(pid == 0){
		while(1){
			printf("this is child pid ,pid = %d,father pid = %d\n",getpid(),getppid());
			cnt++;
			printf("child cnt = %d\n",cnt);
			sleep(3);
			if(cnt == 5){
				exit(3);

			}
		}
	}

	return 0;
}

运行结果:
在这里插入图片描述

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值