Linux------进程的fork()详解

这篇具有很好参考价值的文章主要介绍了Linux------进程的fork()详解。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

目录

前言

一、fork()的使用

二、fork()的返回值

我们为什么要创建子进程?

父进程与子进程的分流

三、fork的一些难理解的问题

1.fork干了什么事情?

2.fork为什么会有两个返回值 

3.fork的两个返回值,为什么会给父进程返回子进程pid,给子进程返回0?

4.fork之后,父子进程谁先运行?

5.如何理解同一个变量,会有不同的值??


前言

在之前,我们学习了进程的概念以及命令行启动进程,今天我们来学习另一种进程创建方法:用代码创建进程。

这里我们简单回顾一下,进程 = 可执行程序+task_struct对象

创建一个进程,在系统中要申请内存,保存当前进程的可执行程序 + task_struct对象,并将 task_struct对象添加到进程列表

一、fork()的使用

我们在命令行man fork 看一下fork函数的用法与作用。 

Linux------进程的fork()详解,linux,运维,服务器

根据图片可以得到fork会创建一个子进程, 在执行fork()过后,会从一个执行流变成两个执行流,这两个执行流都会执行后续的代码。这里说起来还是有点抽象,我们直接上代码试一试。代码如下。

Linux------进程的fork()详解,linux,运维,服务器

我们发现明明我们只写了两句打印代码,却输出了三句,fork之后,打印代码执行了两遍。 还发现本身进程为21554,现在还多了一个进程为21555。

Linux------进程的fork()详解,linux,运维,服务器

我们打印更多消息看一下 

Linux------进程的fork()详解,linux,运维,服务器

执行看一看效果,这里我们发现,调用fork()后,新生成的进程是当前进程的子进程。

Linux------进程的fork()详解,linux,运维,服务器

现在我们可以总结一下结论:只有父进程执行fork之前的代码,fork之后,父子进程都要执行后面的代码

二、fork()的返回值

我们命令行  man fork 再来看一下fork的返回值。失败了返回-1,并且没有子进程被创建,如果成功,父进程返回子进程的PID,子进程返回0。这直接颠覆了我们的认知,为什么一个函数可以有两个返回值啊。

Linux------进程的fork()详解,linux,运维,服务器

我们编辑代码,打印出来看看怎么回事。

 

Linux------进程的fork()详解,linux,运维,服务器

我们发现确实如此,返回的值真的不一样 

Linux------进程的fork()详解,linux,运维,服务器

虽然现在fork我们大概什么情况,但这里还有问题。

  1. 我们为什么要创建子进程?
  2. 我们创建子进程是为了让子进程和我们父进程做一样的事情吗?

我们为什么要创建子进程?

之前,我们学习C/C++的时候,根本就没听说过什么fork父进程子进程,这是因为当时我们的任务是线性的,只需要完成一件事就行了,现在,我们想让子进程协作父进程完成一些工作,这些工作是单进程解决不了的

举个例子,我最爱迅雷边下边播这个功能,我们想让一个进程去下载,另一个进程去播放,这样才可以达到我们的目标。

我们创建子进程,就是为了让子进程和父进程做不一样的事

但是,现在问题又来了,你如何保证他们两可以执行不同的代码呢?

父进程与子进程的分流

我们可以通过fork的返回值的不同,判断出谁是子谁是父,从而让他们执行不同的代码。

Linux------进程的fork()详解,linux,运维,服务器

我们看一下结果,确实可以通过fork返回值的不同来分流。

Linux------进程的fork()详解,linux,运维,服务器

大家知道了fork的分流,但是底层逻辑我们还不清楚,这是如何分流的呀。怎么来了两个返回值呢?这些我们在下一章讲。

三、fork的一些难理解的问题

1.fork干了什么事情?

fork之后,子进程是没有自己的代码和数据的,子进程会和父进程共享代码和数据,因此他们执行的是一样的代码。

fork之前的代码,子进程也可以看见,但是fork之后,eip(是寄存器,用来存储CPU要读取指令的地址,CPU通过EIP寄存器读取即将要执行的指令)指向的fork后续的代码,eip也会被子进程继承,因此子进程只会执行fork之后的代码。

Linux------进程的fork()详解,linux,运维,服务器

2.fork为什么会有两个返回值 

fork是系统接口,本质上就是一个函数,在fork里面进行创建子进程,将子进程放入调度队列中。我们现在知道,fork之后,代码共享,这里指的在fork内部,代码就已经被共享了,也就是子进程已经被创建出来了,最后需要return返回。

父进程需要return,子进程也需要return,因此fork会有两个返回值。

Linux------进程的fork()详解,linux,运维,服务器

3.fork的两个返回值,为什么会给父进程返回子进程pid,给子进程返回0?

在现实中,你生了五个儿女,你叫他们不能统一的叫儿子或者女儿,因为这样儿女不知道你叫的是哪个儿子哪个女儿,因此你需要叫他们大儿子,二儿子,大女儿来区分他们。而他们叫你爸爸,正常情况下爸爸只有一个,不需要做额外区分。

计算机也要标识出到底是哪一个儿子,由于父只有一个,而子进程可以有很多个,因此父进程返回子进程的pid,来标识你创建好的子进程pid是多少。子进程返回0,因为子进程只有一个父亲,不需要额外标识出来。

4.fork之后,父子进程谁先运行?

首先,fork创建完成子进程,这仅仅是一个开始,创建完成后,系统的其他进程,还有当前的父进程和子进程,是要被CPU调度执行的

当父子进程的PCB都被创建并在运行队列中排队的时候,哪一个进程先被CPU调度,哪一个进程就先运行,因此我们不确定这是由各自PCB的调度信息(时间片,优先级等)+调度算法自助决定。

5.如何理解同一个变量,会有不同的值??

要理解这个问题,我们得先知道父子进程是具有独立性的

比如之前我们提到的边下边播,你由于断网问题,下载停止了,但是只要你当前观看内容片段已经下载,播放就不会停止。

同理,如果我们fork之后,有了父子进程,父进程被杀掉,子进程也应该还在啊,或者子进程被杀掉,父进程应该也还在。如下。

杀死父进程,子进程仍在运行

Linux------进程的fork()详解,linux,运维,服务器

杀死子进程,父进程仍在运行 

Linux------进程的fork()详解,linux,运维,服务器

现在我们可以得知, 进程在运行的时候,无论什么关系,进程之间都具有独立性

这个独立性是如何做到的呢?

进程的独立性,首先表现在有各自的PCB。但是我们之前提到fork之后,子进程是没有代码和数据的,他和父进程共享代码和数据。代码本身是只读的,不会影响。但是数据是会修改的。因此父子进程代码共享,数据各自必须想办法私有一份。

这运用到了写时拷贝,如果数据值是一样的,那我就不做处理,如果数据不一样,那我子进程要想办法深拷贝一份数据,当子进程的值覆盖上去,这就完成了父子进程数据各自一份。

正是由于返回的时候发生了写时拷贝,因此同一个变量会有不同的值。 文章来源地址https://www.toymoban.com/news/detail-799594.html

到了这里,关于Linux------进程的fork()详解的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 【运维】Linux 跨服务器复制文件文件夹

    如果是云服务 建议用内网ip scp是secure copy的简写,用于在Linux下进行远程拷贝文件的命令,和它类似的命令有cp,不过cp只是在本机进行拷贝不能跨服务器,而且scp传输是加密的。可能会稍微影响一下速度。当你服务器硬盘变为只读 read only system时,用scp可以帮你把文件移出来

    2024年02月08日
    浏览(46)
  • linux并发服务器 —— 多进程并发(四)

    程序是包含一系列信息的文件,描述了如何在运行时创建一个进程; 进程是正在运行的程序的实例,可以用一个程序来创建多个进程; 用户内存空间包含程序代码以及代码所使用的变量,内核数据结构用于维护进程状态信息; 进程控制块(PCB):维护进程相关的信息,tas

    2024年02月11日
    浏览(40)
  • Linux服务器上查询进程 ps aux

    在Linux服务器上查询进程,有以下几种方法: 使用ps命令。这个命令用于报告当前系统的进程状态。可以用以下方式使用ps命令来查看进程信息: ps aux:显示系统中所有进程的信息。 ps -e:显示所有进程的信息。 ps -f:显示进程的所有信息。 ps -l:以长格式显示进程信息。

    2024年02月05日
    浏览(44)
  • 【Linux运维】shell脚本检查服务器内存和CPU利用率

    在管理服务器时候写了一个 shell脚本,在服务上实现每天凌晨3点查系统的指定文件夹下的容量大小,如果超过10G就要删除3天前的内容,还要时刻查询内存和cpu利用率,如果超过80%就要提示用户出现过载 将以上代码保存为一个.sh文件,然后通过crontab在每天凌晨3点运行即可:

    2024年02月09日
    浏览(48)
  • Linux服务器中查看进程的四种方法

    1. 使用 ps aux 命令来查看,能以简单列表的形式显示出进程信息 ps aux 用于报告当前系统的进程状态。可以搭配kill指令随时中断、删除不必要的程序. ps 命令是最基本同时也是非常强大的进程查看命令,使用该命令可以确定有哪些进程正在运行和运行的状态、进程是否结束、进

    2024年02月02日
    浏览(30)
  • Linux网络编程:多进程 多线程_并发服务器

    文章目录: 一:wrap常用函数封装 wrap.h  wrap.c server.c封装实现 client.c封装实现 二:多进程process并发服务器 server.c服务器 实现思路 代码逻辑  client.c客户端 三:多线程thread并发服务器 server.c服务器 实现思路 代码逻辑  client.c客户端 ​​​​   read 函数的返回值 wrap.h  wrap

    2024年02月12日
    浏览(44)
  • Linux本地部署1Panel服务器运维管理面板并实现公网访问

    1Panel 是一个现代化、开源的 Linux 服务器运维管理面板。高效管理,通过 Web 端轻松管理 Linux 服务器,包括主机监控、文件管理、数据库管理、容器管理等 下面我们介绍在Linux 本地安装1Panel 并结合cpolar 内网穿透工具实现远程访问1Panel 管理界面 执行如下命令一键安装 1Panel: 安

    2024年02月04日
    浏览(58)
  • Linux服务器常见运维性能测试(1)综合跑分unixbench、superbench

    最近需要测试一批服务器的相关硬件性能,以及在常规环境下的硬件运行稳定情况,需要持续拷机测试稳定性。所以找了一些测试用例。本次测试包括在服务器的高低温下性能记录及压力测试,高低电压下性能记录及压力测试,常规环境下CPU满载稳定运行的功率记录。 这个系

    2024年02月04日
    浏览(55)
  • 蓝易云:Linux系统sshd命令 – openssh服务器守护进程

    sshd是Linux系统中的一个守护进程,它提供了远程登录服务和安全的文件传输功能。以下是sshd的详细教程。 1. 安装openssh-server 在Debian/Ubuntu上安装openssh-server命令如下: sudo apt-get update sudo apt-get install openssh-server 在CentOS/RHEL上安装openssh-server命令如下: sudo yum update sudo yum install

    2024年02月16日
    浏览(36)
  • 基于linux下的高并发服务器开发(第二章)- 2.7 进程退出、孤儿进程、僵尸进程

    ◼ 父进程运行结束,但子进程还在运行(未运行结束),这样的子进程就称为孤儿进程 (Orphan Process)。 ◼ 每当出现一个孤儿进程的时候,内核就把孤儿进程的父进程设置为 init ,而 init 进程会循环地 wait() 它的已经退出的子进程。这样,当一个孤儿进程凄凉地结束 了其生

    2024年02月16日
    浏览(40)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包