11.OS操作系统学习:进程
引入:我们可以回顾一下杨老师在课上所讲进程~
进程是一个活动的实体,具有指定下一条指令以及执行一组相关资源的程序计数器
一,冯诺依曼体系结构
注意这里的存储器是内存,
体系规定程序的运行必须加载到内存中,cpu执行的代码访问内存中的数据。
IO就是从内存的角度来说的,
比如从键盘这个输入设备到内存叫做input
从内存这个Memory Unit到屏幕这个输出设备叫做output
二,操作系统
什么是系统调用?
操作系统的职能分为四大板块
-
内存管理
-
进程管理
-
文件管理
-
驱动管理
本文讨论进程,故具体讲解进程管理模块的知识
三,进程
**课本观点:**活动的实体,具有指定下一条指令以及执行一组相关资源的程序计数器(A program counter)
PC是cpu的一个寄存器,存放着下一条要执行指令的内存地址
**内核观点:**担当分配系统资源(cpu时间,内存)的实体
进一步讲:进程应该有两个部分:
数据(例如c语言包含着二进制代码和创建修改时间等)和信息(为了方便进行管理)
1.代码与数据
stat xx//来查看文件信息
2.PCB(process control block)
ps ajx//查看进程块包含的信息
PCB包含的内容
3.practice1关于pid
前置知识:通过getpid()函数来获得当前进程的pid值(进程的唯一编号)
注意getppid()就是获得父进程
#include<stdio.h>
#include<unistd.h> //Linux中睡眠函数的头文件
#include<sys/types.h>
int main()
{
int sec = 0;
while(1)
{
printf("这是一个进程,已经运行了%d秒 当前进程的PID为:%zu\n", sec, getpid());
sleep(1); //单位是秒,睡眠一秒
sec++;
}
return 0;
}
程序运行结果:
我们使用下面这串代码查找这个进程
ps ajx | head -1 && ps ajx | grep a.out | grep -v grep
提高:可以使用makefile简化我们的过程
4.top指令查看所有的进程
top
5.fork创建子进程
这个函数有两个返回值
进程创建成功时,给父进程返回子进程的PID,给子进程返回0
创建失败时,返回 -1
int fork(void)
0.原理
1.practice1:子进程引入
#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
int main(int argc, char const *argv[])
{
//pid_t是数据类型,实际上是一个整型
//通过typedef重新定义了一个名字,用于存储进行ID
pid_t pid; //parent pid
pid_t cid; //child pid
// getpid()函数返回当前进程的ID号
printf("Before fork Process id:%d\n", getpid());
/*
fork()函数用于创建一个新的进程,该进程为当前进程的子进程,创建的方法是:
将当前进程的内存内容完整拷贝一份到内存的另一个区域,两个进程为父子关系,他们会同时(并发)执行fork()语句后面的所有语句
fork()的返回值是:
如果成功创建子进程,对于父子进程fork会返回不同的值,对于父进程它的返回值是子进程的进程id值,对于子进程它的返回值是0.
如果创建失败,返回值为-1.
*/
fork();
printf("After fork Process id:%d\n", getpid());
pause();
return 0;
}
会发现执行了两次
2.practice2:交替执行
#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
#include <sys/wait.h>
int main(int argc, char const *argv[])
{
pid_t cid; //child pid
printf("Before fork Process id:%d\n", getpid());
cid = fork();
if (cid == 0){
printf("Child process id (my parent pid is %d):%d\n", getppid(),getpid());
for(int i = 0; i < 30; i++){
printf("hello\n");
}
}else{
printf("Parent Process id: %d\n",getpid());
for(int i = 0; i < 30; i++){
printf("world\n");
}
wait(NULL);
}
return 0;
}
3.fork()函数工作原理
fork
创建子进程时,会新建一个属于 子进程
的 PCB
,然后把 父进程 PCB
的大部分数据拷贝过来使用,两者共享一份代码和数据。