fork和vfork函数

fork:

fork用于派生一个进程。如果成功,父进程返回子进程的ID,子进程中返回0,若出错则返回-1。

主要用途:

一个进程希望复制自身,从而子父进程能同时执行不同的代码段。

进程想要执行另一个程序

例如:

#include<stdio.h>
#include<sys/types.h>
#include<stdio.h>
int main()
{
        int count=0;
        pid_t pid;
        pid=fork();     // 创建一个子进程
        if(pid<0)
        {
                printf("error in fork!");
                exit(1);
        }
        else if(pid==0)
        {
                printf("I am the child process,the count is %d,my process ID %d,pid=%d\n",++count,getpid(),pid);
                exit(0);
        }
        else
                printf("I am the parent process,the count is %d,my process ID %d,pid=%d\n",count,getpid(),pid);
        return 0;
}

输出结果:

I am the parent process,the count is 0,my process ID 13981,pid=13982
I am the child process,the count is 1,my process ID 13982,pid=0

从中可以看出,两个进程中,原先就存在的那个被称为父进程,新出现的那个被称为子进程。父子进程的区别除了进程标识符(ID)不同外,变量pid的值也不同,pid存放的是fork的返回值。fork调用的一个奇妙之处就是它仅仅被调用一次,却能返回两次,它可能有三中不同的返回值

父进程中,返回新建子进程的ID

子进程中,返回0

若出错,则返回一个负值。

fork出错的原因有两种:

1. 当前的进程数已经达到系统规定的上限,

2.系统内存不足,

fork出错的可能性很小,一般为第一种情况

vfork与fork相同,父进程返回子进程的ID,子进程中返回0,若出错则返回-1。

不同的是:

fork要拷贝父进程的数据段;而vfork则不需要完全拷贝父进程的数据段,在子进程没有调用exec或exit之前,子进程与父进程共享数据段。

fork不对父子进程的执行次序进行任何限制,而在vfork调用中,子进程先运行,父进程挂起,直到子进程调用了exec或exit之后,父进程的执行次序才不再有限制。

例如:

#include<stdio.h>
#include<sys/types.h>
#include<unistd.h>
int main(void)
{
        int count=1;
        int child;
        printf("Before create son, the father‘s count is %d\n",count);
        child=vfork();  //创建了一个新的进程,此时有两个进程在运行
        if(child < 0)
        {
                printf("error in vfork!\n");
                exit(1);
        }
        if(child==0)
        {
                printf("This is son,his pid id %d and the count is %d\n",getpid(),++count);
                exit(1);
        }
        else
        {
                printf("After son, This is father,his pid is %d and the count is %d, and the child is %d\n",getpid(),count,child);
        }
        return 0;
}

运行结果:

Before create son, the father‘s count is 1
This is son,his pid id 14049 and the count is 2
After son, This is father,his pid is 14048 and the count is 2, and the child is 14049

从运行结果中,我们可以看出,在子进程中修改了count的值,但是父进程中输出了修改后的值2,而不是初始值1.说明子进程和父进程是共享count的,也就是说,由vfork创建出来的子进程与父进程之间是共享内存区的。另外,有vfork创建的子进程还会导致父进程的挂起,除非子进程执行了exit或者execve才会唤醒父进程。

时间: 2024-08-29 16:03:33

fork和vfork函数的相关文章

linux fork函数与vfork函数

man vfork: NAME vfork - create a child process and block parent SYNOPSIS #include <sys/types.h> #include <unistd.h> pid_t vfork(void); DESCRIPTION Standard description (From POSIX.1) The vfork() function has the same effect as fork(2), except

Linux系统编程——vfork() 函数详解

所需头文件: #include <sys/types.h> #include <unistd.h> pid_t vfork(void); 功能: vfork() 函数和 fork() 函数(fork()如何使用,请点此链接)一样都是在已有的进程中创建一个新的进程,但它们创建的子进程是有区别的. 参数: 无 返回值: 成功:子进程中返回 0,父进程中返回子进程 ID.pid_t,为无符号整型. 失败:返回 -1. fork() 与 vfock() 都是创建一个进程,那它们有什么区别呢

UNIX高级环境编程(9)进程控制(Process Control)- fork,vfork,僵尸进程,wait和waitpid

本章包含内容有: 创建新进程 程序执行(program execution) 进程终止(process termination) 进程的各种ID ? 1 进程标识符(Process Identifiers) 每个进程都有一个唯一的标识符,进程ID(process ID). 进程的ID是可重用的,如果一个进程被终止,那么它的进程ID会被系统回收,但是会延迟使用,防止该进程ID标识的新进程被误认为是以前的进程. 三个特殊ID的进程: Process ID 0:调度者进程,内核进程. Process

fork和vfork,return和exit的理解

fork和vfork的差别: 1.fork是创建一个子进程,并把父进程的内存数据copy到子进程中. vfork是创建一个子进程,并和父进程的内存数据share一起. 2.vfork是这样的工作的: (1).保证子进程先执行. (2).当子进程调用exit()或exec()后,父进程往下执行. 3.fork后来采用的优化技术,这样,对于fork后并不是马上拷贝内存,而是只有你在需要改变的时候,才会从父进程中拷贝到子进程中,这样fork后立马执行exec的成本就非常小了.而vfork因为共享内存所

进程控制fork与vfork

1. 进程标识符 在前面进程描述一章节里已经介绍过进程的两个基本标识符pid和ppid,现在将详细介绍进程的其他标识符. 每个进程都有非负的整形表示唯一的进程ID.一个进程终止后,其进程ID就可以再次使用了.如下是一个典型进程的ID及其类型和功能. 进程名:swapper (交换进程),进程ID:0,类型:系统进程,作用:它是内核的一部分,不执行磁盘上的程序,是调度进程. 进程名:init(init进程),进程ID:1,类型:用户进程 ,作用:永远不会终止,启动系统,读取系统初始化的文件. 进程

fork()函数 —— 父子进程资源问

fork()函数功能--创建新进程 1.父子进程有独立的数据段.堆.栈,共享代码段 Linux中每个进程都有4G的虚拟地址空间(独立的3G用户空间和共享的1G内核空间),fork()创建的子进程也不例外.子进程资源的由来: 1.1G内核空间既然是所有进程共享,因此fork()创建的子进程自然也将拥有: 2.3G的用户空间是从父进程进程而来. fork()创建子进程时继承了父进程的数据段.代码段.栈段.堆,注意从父进程继承来的是虚拟地址空间,同时也复制了页表(没有复制物理块).因此,此时父子进程拥

Linux之fork与vfork区别

创建一个新进程的方法只有由某个已存在的进程调用fork()或vfork() 1.fork()函数 返回值:成功:父进程:返回子进程的PID 子进程:返回0 失败:父进程返回-1 子进程是父进程的一个拷贝.即子进程从父进程得到数据段和堆.栈段的拷贝,这些需要分配新的内存(不是与父进程共享,而是单独分配内存):而对于只读的代码段,通常使用共享内存的方式访问. fork返回后,子进程和父进程都从调用fork函数的下一条语句开始执行. 由于子进程与父进程的运行是无关的,所以,父进程可先于子进程运行,子进

小程序分析(fork()和vfork())

分析下述程序,i<4时,最终创建了多少个进程. fork()是创建一个子进程. 分析:i=0时,父进程1创建了一个子进程1.(此时共2个进程) i=1时,父进程1继续创建子进程2,将子进程1又当成父进程,创建子进程3.(此时共6个进程) i=2时,将子进程当成父进程继续创建子进程.之前的父进程继续创建子进程.(此时共14个进程) i=3时,将子进程继续当成父进程继续创建子进程.之前的父进程继续创建子进程.(此时共30个进程) 注:可先计算由父进程创建的进程数,最后乘2即为总进程数. 扩展:当i<

小何讲进程: Linux进程控制编程 (fork、vfork)

所谓进程控制,就是系统使用一些具有特定功能的程序段来创建进程.撤消进程以及完成进程在各种状态之间的转换, 从而达到多进程高效率并发执行和协调资源共享的目的.进程控制是进程管理和处理机管理的一个重要任务. 1. fork()创建进程 在Linux系统中,除了系统启动之后的第一个进程(根进程)由系统来创建外, 其余所有进程都必须由已存在的进程来创建新创建的进程叫子进程,而创建子进程的进程叫父进程, 具有相同父进程的进程叫兄弟进程. 在Linux中创建一个新进程的方法是使用fork()函数. fork