进程
进程的组成
程序的代码
程序处理的数据
要知道现在执行哪条指令,程序计数器中的值指示将运行的指令。
CPU寄存器会动态变化,一组通用寄存器的当前值,堆,栈等;
各种系统资源,内存,外存,网络
进程与程序的联系(多对多)
程序是进程的基础,进程是程序功能的体现。
多次执行——某一个程序对应多个进程
调用关系——某一个进程包括多个程序
进程与程序的区别
程序静态,进程动态,进程执行中可以是核心态/用户态,写的代码都是用户态, 但有些操作只能由OS完成。
进程是暂时的,是状态变化的过程,程序永久;
组成不同,进程包括程序,数据(可能变化),进程控制块(进程状态信息)
进程的特点
动态
并发
独立:独立运行,正确性不受影响
制约:共享资源,相互制约,同一时刻一个资源(文件、cpu)只能被一个进程占用。
进程控制块PCB
系统所需的所有进程信息
进程标识:执行了几次(本进程的标识),产生者标识(父进程标识),用户标识
处理机状态信息保存区:用户可用寄存器,程序计数器pc,程序状态字PSW,栈指针
进程控制信息
调度和状态信息,进程当前的执行现状,运行?等待?
进程间通信信息,各种标识、信号、信件等
进程本身的存储管理信息,内存信息,占了多少?要不要回收?
进程所用资源,打开使用的系统资源,如文件
进程间关联信息,父进程,子进程,构成一个链
存储结构
链表:同一状态的进程PCB为一链表,如就绪链表,阻塞链表
索引表(数组):同一状态的归入一个index表,就绪/阻塞索引表
进程状态
创建、就绪、运行、等待、退出
就绪:在等待CPU资源
运行:占用CPU资源
等待:等待除CPU以的资源
挂起(进程在外存,解决内存不足问题)
等待挂起:仍然为等待态,当内存足够时激活,但即使内存不足可以从等待挂起变 为就绪挂起
就绪挂起:仍然为就绪态,当内存足够时激活(当需要运行时可挂起其他进程)
线程
概述
实现进程内部的并发
进程是资源分配单位,线程是CPU调度单位
进程拥有一个完整的资源平台,线程只有指令流执行的必要资源,如寄存器和栈
线程能减少并发执行的时间和空间开销
同一进程的各线程间共享内存和文件资源,可不通过内核进行直接通信
每个线程都有自己的TCB(thread control block),包括PC程序计数器,SP 堆栈,State状态,和寄存器。
线程实现
用户线程
即在进程内部实现多任务调度(快,简单;但会有线程阻塞)
内核线程
任务的切换由内核管理
轻权线程(实际效果不理想)
一个进程有一个或多个轻量级进程,每个轻量级进程由一个单独的内核线程来支持。
进程控制
进程切换
要求快速切换,汇编实现
保存被切进程信息,恢复切换进程信息,包括寄存器,CPU,以及小部分内存地址空间
进程创建与加载
windows API:CreateProcess(filename)
Unix:fork/exec
fork()把进程复制为两个进程,子进程产生新的ID
复制父进程的所有变量和内存,所有的CPU寄存器,内核复制出一个一样的PCB,但PID不同
返回值,父进程返回进程子进程的PID,子进程返回0,(可利用这一条件,实现程序加载)
getpid()可获取自己的pid
exec()重写当前进程,PID没有发生改变
加载新程序从main(_start)开始执行,可指定启动参数
代码段、堆栈和堆等完全重写
进程等待和退出
wait():父进程等待子进程结束
子进程结束时用过exit()向父进程返回一个值
父进程通过wait()接收并处理返回值
wait()与exit()的执行顺序
先wait后exit:父进程等待子进程返回结果
子进程调用exit(),唤醒父进程,将exit的返回值作为父进程中wait的返回值
先exit后wait:父进程不处于等待状态,需要父进程主动执行wait
- 子进程调用exit(),未获得父进程响应,进入僵尸状态,
- 父进程执行一次wait响应一个僵尸子进程的结束请求
- 没有需要处理的子进程,wait立即返回。
exit():结束进程
- 释放内存,释放相关数据结构
- 进入僵尸状态,唤醒父进程,若无父,则被收养。
- 清理所有僵尸子进程(孤儿进程被收养,被wait)
其他系统调用
(1)nice()指定进程的初始优先级
(2)ptrace()允许一个进程控制另一个进程的执行
(3)sleep()让进程在定时器的等待队列中等待指定
进程状态与其系统调用的关系
其中exec属于运行的一部分。