Linux——进程(1)
在Linux中,创建一个新进程的命令是使用fork()
系统调用:
int fork();
我们把调用fork()
的进程称为父进程,把创建的新进程称为子进程。子进程将拥有父进程的程序代码,地址空间、数据和堆栈段的一份拷贝,以及对所有打开的文件描述符(在内核中)的访问权。它们有各自的虚拟机,在各自独立的地址空间中并发从fork()
之后的同一执行点开始执行——在此刻父进程与子进程仿佛两个完全相同的平行宇宙;
不同在于:父进程中的fork()
函数将返回子进程的PID;子进程中则返回0
值;基于此,一般地,可以使用条件判断,让父进程与子进程产生不同行为:
childpid = fork();
if( childpid == 0 ){
//子进程将会从这里开始执行
...
exit(0);
}
//父进程将会从这里开始执行
...
这仿佛是两个平行宇宙同时对薛定谔的猫进行观察——其中一个宇宙的猫是死掉的而另外一个宇宙的猫是活着,从此两个平行宇宙可以开始有完全不同的行为
《薛定谔的猫》的一种解释为在观察的瞬间,宇宙才发生分裂,形成两个平行宇宙——其各自观察结果为其中一个猫还活着,另一个猫已经死掉。
另外子进程和父进程不能通过引用存储在相同地址上的变量进行通信,唯一可以共享引用的是打开的文件——Linux利用这种方式来作为进程间接通信机制。
测试代码
//fork.c
#include<stdio.h>
#include<stdlib.h>
#include <unistd.h>
void main(){
int childpid, parentpid;
parentpid = getpid();
childpid = fork();
if( childpid == 0 ){
childpid = getpid();
printf("I'm child my pid:%d,my parent pid:%d\n",childpid,parentpid);
exit(0);
}
printf("I'm parent my pid:%d,my child pid:%d\n",parentpid,childpid);
exit(0);
}
运行
$ cc fork.c
$ ./a.out
I'm parent my pid:45173,my child pid:45174
I'm child my pid:45174,my parent pid 45173