在做操作系统的实验过程中,自己安装了Ubuntu(18.04.1)64位,在这里给大家安利一个VX公众号:软件安装管家。这里真的有好多好多的软件,非常全面并且安装教程非常详细,强烈推荐!!!
在此声明,我所有代码都是基于Ubuntu(18.04.1)64位,使用vim编辑器编辑,gcc编译的。兼容性不知道如何。因为自己也是linux新人,难免有一些不太准确的地方,还希望和兄弟们交流学习。
实验应该是要验证进程之间的并发性,就是输出字符的顺序是不一定的,但是也许是由于代码太简单的缘故,导致输出顺序每次都是固定的。。很是尴尬
#include<unistd.h> #include<string.h> #include<stdlib.h> #include<stdio.h> int main() { pid_t pid1,pid2; pid1 = fork();//创建一个新process if(pid1 < 0) { printf("创建进程失败!"); exit(1); } else if(pid1 == 0) { printf("b"); } else { pid2 = fork();//创建第二个新进程 if(pid2 < 0) { printf("进程创建失败!"); exit(1); } else if(pid2 == 0) { printf("c"); } else { printf("a"); } } //getchar();//如果运行错行,再放开此句,拦住父进程,不让其结束 return 0; }
更尴尬的是,这个代码的运行结果:
a居然打印在了那个地方???小弟刚开始接触linux,人都傻了,这是因为主进程直接结束,它运行速度甚至快于终端输出??
我试着在代码尾部加了getchar()拦截一下主进程:
这下输出就舒服多了。。。但是我运行了很多遍,顺序都是这样,所以就改成for循环来打印,在每个进程执行过程中,用for循环打印数据。
#include<unistd.h> #include<string.h> #include<stdlib.h> #include<stdio.h> int main() { pid_t pid1,pid2; pid1 = fork();//创建一个新process if(pid1 < 0) { printf("创建进程失败!"); exit(1); } else if(pid1 == 0) { for(int i = 0;i<1000;i++) { printf("b 子进程1的标识符是%d",getpid()); } } else { pid2 = fork();//创建第二个新进程 if(pid2 < 0) { printf("进程创建失败!"); exit(1); } else if(pid2 == 0) { for(int i = 0;i<1000;i++) { printf("c 子进程2的标识符是%d",getpid()); } } else { for(int i = 0;i<1000;i++) { printf("a 父进程的标识符是%d",getpid()); } } } getchar();//为了拦住进程,不让进程结束 return 0; }
运行结果:
交叉打印,感觉有那味了,并发执行。
接下来又要求给进程上锁,使用lockf()函数,这个原理基本就和Windows的临界区是一个概念,申请到锁的资源才可以执行,并且在释放资源之前,不会被其他进程抢占这个资源,实现了进程间同步机制。
附上代码以及截图:
#include<unistd.h> #include<string.h> #include<stdlib.h> #include<stdio.h> int main() { pid_t pid1,pid2; pid1 = fork();//创建一个新process if(pid1 < 0) { printf("创建进程失败!"); exit(1); } else if(pid1 == 0) { lockf(1,1,0);//上锁 for(int i = 0;i<100;i++) { printf("Chile_1 子进程1标识是%d\r\n",getpid()); } lockf(1,0,0);//解锁 } else { pid2 = fork();//创建第二个新进程 if(pid2 < 0) { printf("进程创建失败!"); exit(1); } else if(pid2 == 0) { lockf(1,1,0);//上锁 for(int i = 0;i<100;i++) { printf("Child_2 子进程2标识是%d\r\n",getpid()); } lockf(1,0,0);//解锁 } else { lockf(1,1,0);//上锁 for(int i = 0;i<100;i++) { printf("FatherProcess 父进程标识是%d\r\n",getpid()); } lockf(1,0,0);//解锁 } } getchar();//为了拦住进程,不让进程结束 getchar(); return 0; }