聊聊fork的那些事

参加了一场面试 学会了一个知识点 

fork之后发生了 什么 ,我很正常的做出了回答,对父进程的内存进行了复制。

fork之后 ,在早期的unix的系统是通过复制的 

为系统分配 内存页

初始化内存页

将父进程的内存内容分配到子进程当中

这造成了什么?这造成了cpu和内存的浪费,如果一个父进程1个g占用,那么子进程是否也就占用了一个G呢?

当我读书unix高级环境编程,被一端内容所误解,却没有理解书中后面的内容,这段内容是,子进程是父进程的副本,父子进程不共享这些存储空间,但是共享正文段。读到这里完全被误解了!!!没有看到书后面的写时复制(cow)

书中后面说道,由于许多人在fork之后直接调用的exec,所以会造成严重的内存浪费,所以开始使用了 写时复制cow,那么什么是cow呢?

我们先要明白一个进程他的c程序存储空间,一个unix进程的c程序存储空间是怎么样的?

unix高阶环境编程里面写到,一个进程的c存储空间是由,堆、栈、数据区(未初始化数据,初始化数据)、正文段 这几部分程序组成。

写时复制是父子进程共享一个存储空间,而且都是只读的,父子进程任何一个要做修改都会复制出一块内存页。fork之后子进程的数据段和堆栈都是指向父进程的物理空间的 也就是说父子进程的虚拟内存是不同的,当父子进程发生修改的时候再为子进程分配内存页。

 

那我们继续来说一下 vfork这个函数,vfork也是创建一个新的进程,但是vfork函数的目的是为了执行exec,但是他不会把将父进程的地址空间完全复制到子进程地址空间中(意味着 数据区域 和 堆栈区域 都不会被复制到子进程的虚拟内存中),因为子进程会调用exec不会访问父进程的地址空间,另一个区别是vfork一定是确保子进程先运行的。

 

fork函数,子进程是在调用父进程调用fork函数之后生成的。上面说明了子进程将其终止状态返回给父进程,但是如果父进程在子进程终止之前终止会出现什么状况呢?对于父进程已经终止的所有进程,他们的父进程变为init进程,我们称这些进程由init进程领养。其操作过程如下:在一个进程终止的时候,内核会逐个检查所有活动的进程,以判断是否是要正要终止的子进程,如果是则将这个进程的父进程更改为pid为1.这种方法保证了每一个子进程都有一个父进程.(注意在ubuntu上父进程死掉之后领养的进程不是init 是 systemd!!!!)

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值