解析fork函数与vfork函数

一、fork函数与vfork函数的简介

(1)fork函数

在Linux下fork函数很重要,它的作用是创建子进程,即在当前进程中创建一个新的进程,新进程为子进程,原来的进程为父进程。

我们来看一下这个函数的返回值和类型

#include 
pid_t fork(void);

我们可以看到这个函数的返回值是一个pid_t的类型,它的返回类型分别为:

  • 子进程返回0
  • 父进程返回子进程的ID
  • 出错返回-1

当我们调用fork函数后控制转移到内核的fork的代码中,内核需要做一系列的动作然后就产生了两个二进制代码相同的进程,它们都运行到同一个地方,它在创建子进程的时候返回父进程的下一个语句,即返回到父进程执行fork函数的下一句。这个时候每个进程都有各自的旅行。

此时我们需要注意的是:fork之后谁先执行完全由调度器来决定。

fork的子进程与父进程贡献一段存储空间,但是子进程不需要把父进程的4G内存空间全部全部拷贝,太浪费了,在《UNIX环境高级编程》一书中有详细介绍什么拷贝什么不拷贝,例如代码段不需要共享,但是数据段在父进程更改的时候子进程也更改,这个技术叫做写时拷贝。

fork函数的常规用法

  • 一个父进程希望子进程复制自己,使父子进程同时执行不同的代码段。例如:父进程等待客户端的请求,生成子进程来处理请求。
  • 一个进程要执行一个不同的程序。例如:子进程从fork返回后调用exec函数。

fork函数失败的原因

  • 每个操作系统都设置的有进程的上限数字,一旦我们用户的进程数目超过了这个值,那么此时就会创建子进程失败。
  • 一旦当系统有太多的进程,那么此时也可能会创建进程失败。

(2)vfork函数

由于fork函数创建的子进程有一段自己的地址空间,但是我们有时候并不希望这样,所以此时便有了vfork函数。

#include 
#include 

pid_t vfork(void);

vfork的函数返回值和fork函数的返回值是一样的。

vfork函数也是用来创建子进程的,它不会拷贝4G进程空间,它保证了子进程先运行,但是它与fork创建的子进程有如下的区别:

  • vfork创建的子进程和父进程共享地址空间,fork的子进程有独立地址空间
  • vfork保证子进程先运行,在子进程调用exec或者exit函数之后父进程才会被调度运行。fork函数则没有这样。

缺点:

vfork的底层实现有点问题,所以一般我们不建议使用(因为可能会出现段错误),但是如果我们在最后使用exit函数进行退出即可保证程序正确。

二、fork函数与vfork函数的区别与总结

  • 1、fork出来的父子进程交替运行,vfork出来的进程是父进程阻塞,直到子进程结束。
  • 2、fork实现了写时拷贝,vfork就算是写,也不拷贝。
  • 3、vfork必须使用exit或者exec后父进程才会运行。
  • 4、我们就算是把fork实现了写时拷贝,它的性能也没有vfork高。
  • 5、每个系统是的vfork都有问题,不建议使用。

你可能感兴趣的:(Linux,fork,fork函数,vfork)