实验二. 进程的创建
1. 进程的基本概念
1.1 进程的定义
1.1.1 进程的定义
- 进程是操作系统进行资源分配和调度的一个独立单位。
- 它由程序的代码、数据和进程控制块组成。
- 进程是程序在计算机上的一次执行过程,是系统进行资源分配和调度的独立单位。
1.1.2 进程的特点
- 动态性:进程是程序的一次执行过程,具有动态性。
- 并发性:多个进程可以同时运行,提高了计算机的利用率。
- 独立性:进程之间相互独立,互不影响。
- 结构性:进程由程序的代码、数据和进程控制块组成。
1.2 进程的状态
1.2.1 进程的五种基本状态
- 创建状态:进程尚未被创建,仅存在于程序中。
- 就绪状态:进程已创建,等待CPU调度。
- 运行状态:进程正在CPU上执行。
- 阻塞状态:进程因等待某种资源或事件而暂停执行。
- 终止状态:进程执行完毕,释放所占资源。
1.2.2 进程的状态转换
- 创建状态→就绪状态:程序被加载到内存,进程控制块(PCB)被创建。
- 就绪状态→运行状态:进程被CPU调度执行。
- 运行状态→就绪状态:进程因时间片到期或其他原因被中断。
- 运行状态→阻塞状态:进程因等待资源或事件而暂停执行。
- 阻塞状态→就绪状态:等待的资源或事件到来,进程重新进入就绪状态。
- 阻塞状态→终止状态:进程因等待时间过长而终止。
- 运行状态→终止状态:进程执行完毕,释放所占资源。
1.3 进程控制块(PCB)
1.3.1 进程控制块的概念
- 进程控制块(PCB)是操作系统中用于描述进程的内部数据结构。
- PCB包含了进程的运行状态、程序计数器、寄存器集合、打开文件表等信息。
1.3.2 PCB的作用
- 描述进程的当前状态,为操作系统提供进程管理的基础。
- 作为进程调度和资源分配的依据。
- 记录进程的运行历史,为进程的恢复和终止提供信息。
2. 进程的创建
2.1 进程创建的过程
2.1.1 进程创建的基本步骤
- 进程控制块(PCB)的创建:为新建进程分配PCB,记录进程的基本信息。
- 分配内存空间:为新建进程分配内存空间,包括代码段、数据段和堆栈段。
- 初始化进程状态:将新建进程的状态设置为就绪状态。
- 设置进程优先级:根据进程的性质和需求,为新建进程设置优先级。
2.1.2 进程创建的时机
- 用户请求:用户通过命令或图形界面请求执行一个程序。
- 系统调度:操作系统根据进程的优先级和资源需求,自动创建进程。
- 系统初始化:操作系统在启动时,自动创建初始进程(如init进程)。
2.2 进程创建的实现方式
2.2.1 系统调用
- 系统调用是用户进程与操作系统之间的接口。
- 通过系统调用,用户进程可以请求操作系统创建新的进程。
2.2.2 进程控制块(PCB)的管理
- 操作系统维护一个进程控制块表,用于存储所有进程的PCB。
- 当创建新进程时,操作系统从PCB表中分配一个PCB,并为新进程设置相关信息。
2.2.3 内存分配
- 操作系统根据新进程的需求,为其分配内存空间。
- 内存分配可以采用连续分配、分页分配或分段分配等策略。
2.3 进程创建的优化
2.3.1 进程优先级调度
- 根据进程的优先级,优先调度高优先级的进程。
- 提高系统资源的利用率,保证关键进程的执行。
2.3.2 进程调度算法
- 操作系统采用不同的进程调度算法,如FCFS、SJF、轮转法等。
- 优化进程调度,提高系统性能。
2.3.3 进程同步与互斥
- 采用进程同步机制,避免进程间的冲突。
- 实现进程间的互斥访问,确保共享资源的正确使用。
2.4 进程创建的示例
2.4.1 用户请求创建进程
- 用户通过命令行或图形界面请求执行一个程序。
- 操作系统根据请求,创建新进程并为其分配资源。
2.4.2 系统自动创建进程
- 操作系统在启动时,自动创建初始进程(如init进程)。
- 初始进程负责创建其他进程,如shell进程、守护进程等。
2.4.3 进程创建的代码示例
c #include <stdio.h> #include <unistd.h> #include <sys/types.h> #include <sys/wait.h>
int main() { pid_t pid; pid = fork();
if (pid < 0) { perror("fork failed"); return 1; } else if (pid == 0) { printf("Child process ID: %ld\n", (long)getpid()); } else { printf("Parent process ID: %ld\n", (long)getpid()); wait(NULL); }
return 0; }
以上代码展示了使用fork系统调用来创建进程的基本过程。当运行该程序时,会创建一个子进程,父进程和子进程分别打印出自己的进程ID。子进程执行完毕后,父进程会等待子进程结束。




