我的编程空间,编程开发者的网络收藏夹
学习永远不晚

Unix/Linux fork隐藏的开销

短信预约 信息系统项目管理师 报名、考试、查分时间动态提醒
省份

北京

  • 北京
  • 上海
  • 天津
  • 重庆
  • 河北
  • 山东
  • 辽宁
  • 黑龙江
  • 吉林
  • 甘肃
  • 青海
  • 河南
  • 江苏
  • 湖北
  • 湖南
  • 江西
  • 浙江
  • 广东
  • 云南
  • 福建
  • 海南
  • 山西
  • 四川
  • 陕西
  • 贵州
  • 安徽
  • 广西
  • 内蒙
  • 西藏
  • 新疆
  • 宁夏
  • 兵团
手机号立即预约

请填写图片验证码后获取短信验证码

看不清楚,换张图片

免费获取短信验证码

Unix/Linux fork隐藏的开销

目录
  • 一、fork的由来
  • 二、早期UNIX的覆盖(overlaying)技术
  • 三、fork引入UNIX前的表象
    • 1、UNIX fork的诞生
    • 2、UNIX fork-exec
    • 3、UNIX fork/exec/exit/wait

一、fork的由来

fork的思想在UNIX出现几年前就出现了,时间大概是1963年,这比UNIX在PDP-7上的第一个版本早了6年。
1963年,计算机科学家Melvin Conway(以Conway's Law闻名于世)写下一篇论文,正式提出了fork思想,
fork的思想最初是Conway作为一种 多处理器并行 的方案提出来的,这个想法非常有意思。简而言之,fork思想来源于流程图。

我们看一个普通的流程图:

你看,流程图的分枝处,fork-叉子,多么形象!

一个流程图上的分支点分裂出来的分支显然是逻辑独立的,这便是可并行的前提,于是它们便可以表现为不同的 处理进程(process) 的形式,当时的表达还只是“process”这个术语,它还不是现代操作系统意义上的“进程”的概念。

join同步点表现为多个并行处理的进程由于某种原因不得不同步的点,也就是多个并行流程汇合的点,直到现在,在多线程编程中,这个点依然叫join。比如Java Thread的join方法以及pthread库的pthread_join函数。

广义来讲,join也表示诸如临界区等必须串行通过的点, 减少join点的数量将会提高并行的效率。

我们来看看Conway论文中关于fork的原始图示:

Conway在论文中的另一个创举是,他将处理进程(也就是后来操作系统中的process的概念)以及执行该进程的处理器(即CPU核)分离了开来,抽象出了schedule层。

大意是说、“只要满足系统中的活动处理器数量是总处理器数量和并行处理进程的最小值即可。” 这意味着调度程序可以将多处理器系统的所有处理器和系统所有处理进程分别看作是统一的资源池和消费者,执行统一调度:

在UNIX引入fork之后,这种多处理器并行的设计思想就深入到了UNIX的核心。这个思想最终也影响了UNIX以及后来的Linux,直到现在。
关于这个设计思想为什么可以影响UNIX这么久,我想和Conway本人的“Conway's law”不无关系,在这个law中,他提到:Any organization that designs a system (defined broadly) will produce a design whose structure is a copy of the organization's communication structure.

二、早期UNIX的覆盖(overlaying)技术

接下来看UNIX fork的另一个脉络,1969年最初的UNIX用一种在现在看来非常奇怪的方式运行。

一般的资料都是从UNIX v6版本开始讲起,那个版本已经是比较 “现代” 的版本了,所以很少有人能看到最初的UNIX是什么样子的。即便是能查阅到的1970年的PDP-7上运行的UNIX源码,也是引入fork之后的版本,在那之前的最原始版本几乎找不到了(你可能会说,那时的UNIX不叫UNIX,but who cares…)。

最初的UNIX是一个分时系统,它只有两个shell进程,分别属于两个终端:

分时系统最初并不是基于进程分时的,那时根本还没有完整的进程的概念,分时系统是针对终端分时的,而操作员坐在终端前,为了让每个操作员在操作过程中感觉上是在独占机器资源,每个终端享受一段时间的时间片,在该时间片内,该终端前的操作员完全享受机器,但是为了公平,超过了时间片,时间片就要给另一个终端。

就是这样,最初的UNIX为了体现分时特性,实现了最少的两个终端。注意,最初的UNIX没有fork,没有exec,甚至没有多进程的概念,为了实现分时,系统中仅有两个朴素的shell进程。

事实上,最初的UNIX用只有两个元素的表来容纳所有进程(显然,这看起来好笑…),当然,这里的 “表” 的概念也是抽象的朴素概念,因为当时的系统是用PDP-7的汇编写的,还没有后来C语言数据结构。

我们现在考虑其中一个终端的shell进程如何工作。马上问题就来了, 这个shell进程如何执行别的命令程序??

如果说系统中最多只能容纳两个进程,一个终端只有一个shell进程的话,当该终端的shell进程执行其它命令程序时,它自己怎么办?这个问题得思考一会儿…

注意:不要用现代的眼光去评价1969年的初版UNIX,按照现代的眼光,执行一个程序必然要生成一个新的进程,显然这在初版UNIX中并不正确。

答案是根本不用产生新的进程,直接将命令程序的代码载入内存并 覆盖 掉shell进程的代码即可!当命令执行完后,再用shell的代码覆盖掉命令程序的代码,针对单独的终端,系统其实一直在执行下面的覆盖循环(摘自论文的Process control 章节):

然而,在fork被引入UNIX之前,事实就是这样。一个终端上一直都是那一个进程,一会儿它执行shell的代码,一会儿它执行具体命令程序的代码,以下是一个覆盖程序的结构(图片来自《FreeBSD操作系统设计与实现》一书):

然而,当时毕竟还没有将这个逻辑封装成exec系统调用,这些都是每一个进程显式完成的:

  • 对于shell执行命令程序而言,shell自己执行disk IO来载入命令程序覆盖掉自身;
  • 对于命令程序执行结束时,exit调用内部执行disk IO载入shell程序。

exec逻辑是shell程序的一部分,由于它会被所有的命令程序所使用,该逻辑也被封装到了exit调用中。

三、fork引入UNIX前的表象

1963年Melvin Conway提出了fork思想,作为在多处理器中并行执行进程的一个手段。

1969年汤普森版UNIX仅有两个shell进程,使用覆盖(overlaying)技术执行命令。

截止目前,我们看到的表象是:

汤普森版UNIX没有fork,没有exec,没有wait,仅有的库函数般的exit也和现在的exit系统调用大相径庭,显然汤普森版UNIX并非一个多进程系统,而只是一个可以跑的简陋的两终端分时系统!

1、UNIX fork的诞生

fork是如何引入UNIX的呢?

这还要从采用覆盖技术的汤普森版UNIX所固有的问题说起,还是看论文原文:

若要解决这些问题,很简单的方案汤普森都想到了:

  • 保持shell进程的驻留而不是销毁。命令执行时,将其交换到磁盘便是了

很显然,命令程序是不能覆盖掉shell进程了。解决方案是使用 “交换” 技术。

交换技术和覆盖技术其实都是解决有限内存的多进程使用问题的,不同点在于方向不同:

  • 覆盖技术指的是用不同的进程磁盘映像覆盖当前的进程内存映像。
  • 交换技术指的是用将进程的内存映像交换到磁盘,载入一个别的进程磁盘映像。

使用交换技术解决覆盖的问题,意味着要创建新的进程:

  • 在新的进程中执行命令程序。

UNIX需要进行改动,两个配额的进程表显然不够用了。当然,解决方案也并不麻烦:

要讲效率,创造不如抄袭,创建新进程的最直接的就是copy当前shell进程,在copy的新进程中执行覆盖,命令程序覆盖copy的新进程,而当前的终端shell进程则被交换到磁盘保得全身。

覆盖和交换相结合了,UNIX离现代化更近了一步!

确定了copy当前进程的方案后,进一步的问题是如何来copy进程。

现在要说回fork了。

Conway提出fork思想后,马上就有了fork的实现原型(正如Conway自己所说,他只是提出了一个可能造就存在的想法,并没有实现它),Project Genie算是实现fork比较完善的系统之一了。

Project Genie系统的fork不仅仅是盲目地copy进程,它对fork的过程拥有精细的控制权,比如分配多大的内存空间,copy哪些必要的资源等等。显然,Project Genie的fork是冲着Conway的多处理器并行逻辑去的。

还是那句话,创造不如抄袭,UNIX若想实现进程copy,有一个现成的模版就是Project Genie,但是Project Genie的fork对于UNIX太过复杂,太过精细化了,UNIX显然用不到这些精细的控制, UNIX仅仅是想让fork出来的新进程被覆盖,而不是让它去执行什么多处理器上的并行逻辑。

换句话说,UNIX只是借用了fork的copy逻辑的实现,来完成一件别的事。

于是,UNIX非常粗暴的实现了fork!即完全copy父进程,这就是直到现在我们依然在使用的fork系统调用:

投机取巧:

  • fork本来就不是让你用来覆盖新进程的,不然为何多此一举。fork是让你来分解程序流程得以并行处理的。

UNIX fork就此诞生!

我们再次回顾一下UNIX fork诞生之前的景象:

再来看看fork诞生之后的景象:

于是UNIX正式迈开了现代化建设的步伐,一直走到了今天。

2、UNIX fork-exec

关于exec,故事没什么好讲的,它事实上就是关于上述覆盖逻辑的封装,此后程序员不必自己写覆盖逻辑了,直接调用exec系统调用即可。

于是经典的UNIX fork-exec序列便形成了。

3、UNIX fork/exec/exit/wait

值得一提的是,fork被引入UNIX后,exit的语义发生了巨大的改变。

在原始的1969年汤普森版UNIX中,由于每一个终端有且仅有一个进程,这意味着覆盖永远是在shell程序和某个命令程序之间进行的:

  • shell执行命令A:命令程序A覆盖内存中的shell代码。
  • 命令A执行结束:shell覆盖结束的命令A的内存代码。

然而,在fork被引入后,虽然shell执行某个命令依然是特定的命令程序覆盖fork出来的shell子进程,但是当命令执行完毕后,exit逻辑却不能再让shell覆盖当前命令程序了,因为shell从来就没有结束过,它作为父进程只是被交换到了磁盘而已(后来内存到了,可以容纳多个进程时,连交换都不需要了)。

那么exit将让谁来覆盖当前进程呢?

答案是不用覆盖,按照exit的字面意思,它只要结束自己就可以了。

本着 自己的资源自己管理的责任原则 exit只需要清理掉自己分配的资源即可。比如清理掉自己的内存空间以及一些其它的数据结构。

对于子进程本身而言,由于它是父进程生成的,所以它便由父进程来管理释放。于是经典的UNIX进程管理四件套正式形成:

到此这篇关于Unix/Linux fork隐藏的开销的文章就介绍到这了,更多相关Unix/Linux fork内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!,希望大家以后多多支持编程网!

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

Unix/Linux fork隐藏的开销

下载Word文档到电脑,方便收藏和打印~

下载Word文档

猜你喜欢

Unix/Linux fork隐藏的开销

目录一、fork的由来二、早期UNIX的覆盖(overlaying)技术三、fork引入UNIX前的表象1、UNIX fork的诞生2、UNIX fork-exec3、UNIX fork/exec/exit/wait一、fork的由来 fo
2022-06-03

揭秘CMS中隐藏的电子商务宝藏:点亮您的在线销售之路

: 电子商务已成为现代商业的主要力量,而内容管理系统 (CMS) 已成为构建电子商务网站的首选工具。通过了解 CMS 中隐藏的电子商务宝藏,企业可以轻松实现在线销售,扩大业务规模。
揭秘CMS中隐藏的电子商务宝藏:点亮您的在线销售之路
2024-02-02

揭秘 Java Git 的隐藏宝藏,提升开发效率

Java Git 可以通过利用隐藏的功能和特性显著提升开发效率。本文将深入探索 Java Git 的宝藏,揭示如何使用别名、钩子、提示和远程源来优化开发流程。
揭秘 Java Git 的隐藏宝藏,提升开发效率
2024-03-04

收藏28个Unix/Linux的命令行神器

dstat & sar iostat, vmstat, ifstat 三合一的工具,用来查看系统性能。 官方网站:http://dag.wieers.com/rpm/packages/dstat/ 你可以这样使用:alias dstat='
2022-06-04

Android实现第三方登录的上拉展开,下拉隐藏,下拉隐藏示例

Android的UI和交互是很重要的一部分,直接影响到用户对软件的体验。随着项目经验的积累,发现Android中动画的运用越来越重要。本篇文章抽出了项目登录界面中实现的第三方登录,用户可以上拉展开,下拉隐藏第三方登录这么一个效果,提高用户和
2023-05-31

Win8中隐藏Administrator账户的开启方法

Win8开启隐藏Administrator账户的方法如下:1、将鼠标放到右下角。2、点击搜索。3、搜索cmd,然后点击应用。4、在搜索出来程序上右键,选择以管理员身份运行。5、用户帐户控制中选择“是”。6、输入命令:
2022-06-04

建议收藏:好用的 Unix/Linux 命令技巧

1、删除一个大文件 我在生产服务器上有一个很大的200GB的日志文件需要删除。我的rm和ls命令已经崩溃,我担心这是由于巨大的磁盘IO造成的,要删除这个大文件,输入:> /path/to/file.log # 或使用如下格式 :
2022-06-04

探索 ASP 网站部署的未知领域:揭开隐藏的宝藏

ASP 网站部署是一个奥秘的世界,充满着隐藏的宝藏和未探索的领域。通过揭开这些秘密,您可以释放网站的全部潜力,为用户提供无与伦比的体验。踏上这场探索之旅,揭开 ASP 网站部署的未知领域。
探索 ASP 网站部署的未知领域:揭开隐藏的宝藏
2024-03-07

Linux操作系统下隐藏文件的方法

这篇文章主要讲解了“Linux操作系统下隐藏文件的方法”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“Linux操作系统下隐藏文件的方法”吧!一. 概述 目前通用的隐藏文件方法还是hooksy
2023-06-17

Java 多态:揭开隐藏在代码中的魔力

Java 多态性是一种强大的编程概念,让对象能够以不同方式响应相同的方法调用,从而提高代码的可扩展性和可重用性。本文将深入剖析多态性原理,并通过示例代码详细讲解其用法。
Java 多态:揭开隐藏在代码中的魔力
2024-02-06

如何使用Linux释放你Chromebook的隐藏潜能

这篇文章主要介绍如何使用Linux释放你Chromebook的隐藏潜能,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!什么是Linux系统Linux是一种免费使用和自由传播的类UNIX操作系统,是一个基于POSIX的多
2023-06-07

Android开发之完全隐藏软键盘的方法

隐藏软键盘一直是我头痛的事情,没有找到一种真正能隐藏的方法。点击EditText的时候总是弹出软键盘。-----杯具杯具(一):InputMethodManager im =(InputMethodManager) mEdit getCo
2022-06-06

WinXP系统如何隐藏最近打开的文件

大家知道,我们在使用电脑的过程中,浏览一些文件会被电脑记录下来,放在了最近看过的文档列表里面去了,那么我们的一些小隐私就被泄漏了,如何去掉这些痕迹呢?今天教大家一些方法:要改变某些任务栏属性,右击蓝色的任务栏和一个小菜单,出现如下图
2023-05-30

linux 下隐藏进程的一种方法及遇到的坑

前言 1.本文所用到的工具在 https://github.com/gianlucaborello/libprocesshider 可以下载 2.思路就是利用 LD_PRELOAD 来实现系统函数的劫持 LD_PRELOAD是什么: LD_
2022-06-04

编程热搜

目录