面试冲刺:44---fork()与vfork()有哪些特点?区别是什么?写时复制是什么?

一、fork

  • 详情还可以参阅:https://blog.csdn.net/qq_41453285/article/details/103743246

接口语法

  • 用来创造一个子进程
  • 在子进程中,成功的fork调用会返回 0。在父进程中fork返回子进程的 pid。如果出现错误,fork返回一个负值
  • 成功调用fork会创建一个新的进程,它几乎与调用fork的进程一模一样,这两 个进程都会继续运行
  • 最常见的fork用法是创建一个新的进程,然后使用exec载入二进制映像,替换当前进程的映像。这种情况下,派生(fork)了新的进程,而这个子进程会执行一个 新的二进制可执行文件的映像。这种“派生加执行”的方式是很常见的

Linux的写时复制机制

  • 当调用 fork 时,内核会把所有的内部数据结构复制一份,复制进程的页表项,然后把父进程的地址空间中的内容逐页的复制到子进程的地址空间中。但从内核角度来说,逐页的复制方式是十分耗时的
  • 只有在需要写入的时候(父进程写或者子进程写),数据才会被复制从而使各个进程拥有各自的拷贝。也就是说,资源的复制只有在需要写入的时候才进行,在此之前,只是以只读方式共享。这种技术使地址空间上的页的拷贝被推迟到实际发生写入的时候才进行。在页根本不会被写入的情况下(举例来说,fork()后立即调用exec())它们就无须复制了

二、vfork

  • 详情还可以参阅:https://blog.csdn.net/qq_41453285/article/details/103743246

特点

  • 对vfork的成功调用所产生的结果和fork是一样的。vfork会挂起父进程直到子进程终止或者运行了一个新的可执行文件的映像(exec)
  • 通过这样的方式,vfork避免了地址空间的按页复制。在这个过程中,父进程和子进程共享相同的地址空间和页表 项。实际上 vfork( )只完成了一件事:复制内部的内核数据结构。因此,子进程也就 不能修改地址空间中的任何内存
  • 需要注意的是,即使增加了写时复制,vfork也要比fork快,因为它没有进行页表项的复制

三、fork与vfork的对比

  • fork的子进程拷贝父进程的数据段和代码段;vfork的子进程与父进程共享数据段
  • fork的父子进程的执行次序不确定vfork保证子进程先运行,在调用exec或exit之前与父进程数据是共享的,在它调用exec或 exit 之后父进程才可能被调度运行
  • vfork保证子进程先运行,在它调用exec或exit之后父进程才可能被调度运行。如果在调用这两个函数之前子进程依赖于父进程的进一步动作,则会导致死锁
  • 当需要改变共享数据段中变量的值,则拷贝父进程

你可能感兴趣的:(面试冲刺)