【Linux】(二)Putty、 fork() 、 wait() 、waitpid()、僵尸进程、孤儿进程、进程树

Putty

putty远程链接虚拟机内的Linux可以黏贴代码(和win10一样 右键) ,
使用方法:

在这里插入图片描述
下载putty,在1处输入虚拟机ip地址,若长期使用则在2处保存。IP地址可打开虚拟机的terminal从此处看
在这里插入图片描述
两个都试一下能连上就行
有时会弹出这个提示框在这里插入图片描述
这是提示你putty不能确定这个ip是不是你想链接的IP,一般用于远程链接,我们只连局域网的虚拟机就不用管了,能连上就肯定是,点击accept将其接受,如果虚拟机的Ip地址经常变的不想保存可以点击ConnectOnce.

fork( )

创建一个新进程。
系统调用格式: pid=fork( )
参数定义: int fork( )
fork( )返回值意义如下:若子进程创建失败,则调用进程获得返回值-1。若创建成功,在子进程中,fork( )返回值为 0,表示当前进程是子进程;在父进程中,fork( )返回值为子进程的 id 值(>0)。如果 fork( )调用成功,它向父进程返回子进程的 PID,并向子进程返回 0,即 fork( )调用一次,但在不同进程返回不同的值。

运行情况返回值
创建失败-1
创建成功 子进程中0
创建成功 父进程中子进程ID(id>0)

此时 OS 在内存中建立一个新进程,所建的新进程是调用 fork( )父进程(parent process)的副本,称为子进程(child process)。子进程继承了父进程的许多特性,并具有与父进程完全相同的用户级上下文。父进程与子进程并发执行。
在这里插入图片描述

核心为 fork( )完成以下操作:
(1)为新进程分配一进程表项和进程标识符
进入 fork( )后,核心检查系统是否有足够的资源来建立一个新进程。若资源不足,则fork( )系统调用失败;否则,核心为新进程分配一进程表项和唯一的进程标识符。
(2)检查同时运行的进程数目
超过预先规定的最大数目时,fork( )系统调用失败。
(3)拷贝进程表项中的数据
将父进程的当前目录和所有已打开的数据拷贝到子进程表项中,并置进程的状态为“创建”状态。
(4)子进程继承父进程的所有文件
对父进程当前目录和所有已打开的文件表项中的引用计数加 1。
(5)为子进程创建进程上、下文
进程创建结束,设子进程状态为“内存中就绪”并返回子进程的标识符。
(6)子进程执行
虽然父进程与子进程程序完全相同,但每个进程都有自己的程序计数器PC(注意子进程的 PC 开始位置),然后根据 pid 变量保存的 fork( )返回值的不同,执行了不同的分支语句

wait()

#include <sys/types.h>
#include <sys/wait.h>
pid_t wait(int *wstatus);

等待一个子进程状态改变(大部分时候是结束)。如果子进程没有完成状态改变,父进程一直等待。wait( )将调用进程挂起,直至其子进程因暂停或终止而发来软中断信号为止。如果在wait( )前已有子进程暂停或终止,则调用进程做适当处理后便返回。
其中,status 是用户空间的地址。它的低 8 位反映子进程退出状态,为 0 表示子进程正常结束,非 0 则表示出现了各种各样的问题;高 8 位则带回了exit( )的返回值。exit( )返回值由系统给出。wait 的返回值为结束子进程的PID。
核心对 wait( )作以下处理:
(1)首先查找调用进程是否有子进程,若无,则返回出错码;
(2)若找到一处于“僵死状态”的子进程,则将子进程的执行时间加到父进程的执行时间上,并释放子进程的进程表项;
(3)若未找到处于“僵死状态”的子进程,则调用进程便在可被中断的优先级上睡眠,等待其子进程发来软中断信号时被唤醒。

waitpid

#include <sys/types.h>
#include <sys/wait.h>
pid_t waitpid(pid_t pid, int *wstatus, int options);

阻塞等待直到pid的子进程的状态改变
与wait相似,以下两个代码功能相同

 waitpid(-1, &wstatus, 0);
 wait(&wstatus);

默认情况下,waitpid只等待子进程被终结(terminated ),但可以通过第三个参数option改变此行为。
pid可以为

pid表示
> 0等待PID与pid相同的子进程
0等待组id与调用进程组id相同的子进程
-1等待任何子进程
< -1表示任何一个组id与 abs(pid)值相同组的子进程

第三个参数options 可以为

options表示
WNOHANG不阻塞,如果当前进程没有该指定的子进程,或者函数执行错误,waitpid()返回值为-1,如果该子进程没有结束,则返回0;如果该子进程已经结束,则返回该pid;

僵尸进程

子进程结束,而父进程没有调用wait(或waitpid)回收该子进程,则子进程成为“僵尸进程“ 。 内核维护了关于该僵尸进程的有关信息(pid、终结状态、资源使用信息)使得之后父进程可以wait(),这占用了内核的一个进程表的项,(it will consume a slot in the kernel process table),而当该表满时,无法创建新进程,所以需要避免僵尸进程的出现。
当父进程终结,若有僵尸子进程,进程被init(1)收养,init(1)自动wait来清理僵尸进程。

孤儿进程

父进程结束,子进程没结束。
孤儿进程会自动被init进程收养。init 进程会循环地 wait() 它的已经退出的子进程。
孤儿进程无害。

进程

在这里插入图片描述

进程空间4g,其中,用户空间会在进程结束时自动清理,而内核空间(PCB等)需要父进程清理,所以需要父进程调用wait等待子进程退出并清理。

getpid( ),getppid( )

getpid( ) 获得当前进程的进程 id
getppid( ) 获得当前父进程的进程 id

进程树

在 UNIX 系统中,只有 0 进程是在系统引导时被创建的,在系统初启时由 0 进程创建1 进程,以后 0 进程变成对换进程,1 进程成为系统中的始祖进程。UNIX 利用 fork( )为每个终端创建一个子进程为用户服务,如等待用户登录、执行 SHELL 命令解释程序等,每个终端进程又可利用 fork( )来创建其子进程,从而形成一棵进程树。可以说,系统中除 0进程外的所有进程都是用 fork( )创建的。

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值