网站开发工程师的经验,广州建筑设计公司有哪些,电子商务网站建设与管理目录,手机ui设计#x1f30e;进程的调度与切换 文章目录#xff1a;
进程的调度与切换 进程切换 进程调度 活动状态进程队列 位图判断 过期队列 总结 前言#xff1a; 在Linux操作系统中#xff0c;进程的调度与切换是操作系统核心功能之一#xff…进程的调度与切换 文章目录
进程的调度与切换 进程切换 进程调度 活动状态进程队列 位图判断 过期队列 总结 前言 在Linux操作系统中进程的调度与切换是操作系统核心功能之一它直接影响着系统的性能和响应速度。那么话不多说开启我们今天的话题 进程切换 CPU中存在众多寄存器不同的寄存器有不同的功能这些寄存器都在CPU中保存着每一个都能装一定的数据。 运行队列控制着PCB排队执行每执行到一个进程的时候内存里的eip指针会逐条追踪下一条指令。 我们要知道所有的保存都是为了恢复保存在CPU寄存器里的数据是当前进程时间片用完之前所执行的进度而 所有的恢复都是为了从上次的运行位置继续运行。 并且CPU内的所有临时数据我们称之为进程的 硬件上下文 硬件上下文由我们的 进程进行保存得以保护上下文。 当进程在进行第二次及第N次调度进程的时候进程被放到CPU上开始运行将曾经保存的硬件上下文进行恢复。 所以进程切换最重要的就是 进程上下文的保存和恢复。 我们可以看一下内核中的一些寄存器 注意 CPU中的寄存器只有一套而寄存器保存的数据可以有多套。虽然寄存器数据放在了共享的CPU设备内但是 所有的数据都是被进程私有的 进程调度
✈️活动状态进程队列 我们上次说过Linux实现进程调度的算法需要考虑 优先级考虑进程饥饿以及效率。那么CPU是如何实现进程调度的呢 我们来看一下Linux下CPU的运行队列的各项属性 我们首先看蓝色框内的内容有一个叫做 queue[140] 的数组这里的 queue数组表示活动状态进程的进程队列。 其中在queue数组中索引0~99号下标我们是不用的这是因为0-99号下标对应的是 实时进程的优先级实时进程是内核里更加重要的进程放 在前100位由操作系统控制避免系统抢占的情况。 所以我们只剩下 100-139 这个范围可操控其实这也就和我们优先级的可控范围大小相同正好对应队列的四十个空位而OS通过 某种映射关系将可控优先级映射到数组 100-139的下标。 ✈️位图判断 我们看蓝色框内还有一项 bitmap数组类型为int这个数组用来干嘛呢只能存储5个整形变量。 数组的名字叫做bitmap已经很明显了就是位图5个整形元素有 32 * 5 160 个比特位比特位的位置表示哪一个队列。比特位的内容表示该队列为不为空。 比如0000 … 0000 如果最左侧0对应queue[100]的位置那么如果该比特位为0表示在该下标映射的优先级下该队列为空否则不为空。 有人会问为什么要用位图不得不说这是个愚蠢的问题遍历整个队列的时间开销要远大于查找位图。 所以bitmap是用来检测队列中是否有进程检测对应的比特位是否为1 而蓝色框内还有一个元素nr_active在Linux中nr_active 是运行队列中用于表示活跃进程数量的计数器。nr_active 的值可以告诉内核有多少进程正在等待执行从而帮助内核进行进程调度和资源分配。 ✈️过期队列 在红色框中的三项属性与蓝色框中的三项属性完全相同也就是另外一个队列被称为——过期队列。 活跃队列表示当前CPU正在执行的运行队列而 正在执行的运行队列也就是活跃队列是不可以增加新的进程的。 所以操作系统设置了一个 和活跃队列相同属性的过期队列当活跃队列正在执行时如果有进程需要添加进运行队列那么就会添加至过期队列当中也就是说 活跃队列的进程一直在减少而过期队列中的进程一直在增多 当活跃队列的进程执行完毕后就会和过期队列进行交换它们交换的方式是通过两个结构体指针 就是 active 和 expired 结构体指针它们分别指向活跃队列和过期队列而活跃队列与过期队列由于属性完全相同于是被放在了一个叫做 prio_arry_t[2] 的数组里prio_arry_t[0]指向活跃队列prio_arry_t[1]指向过期队列
struct q{//q是我随意取的名字int nr_active;int bitmap[5];task_struct queue[140];
}struct q *active;//活跃队列
struct q *expired;//过期队列struct q *active prio_array_t[0];
struct q *expired prio_array_t[1];当活跃队列被CPU执行完毕后我们 只需要交换两个指针的内容即可这样仅仅是指向的内容变了活跃队列变为过期队列过期队列变活跃队列并且时间复杂度为 O(1)
swap(active, expried);//直接交换两个指针的内容新增进程在过期队列里插入此时正在执行的是活跃队列所以这个时候在过期队列里就有时间处理竞争饥饿的问题了。 这样我们竞争饥饿优先级以及进程效率都解决了。 ✏️总结 进程切换最重要的部分就是 进程上下文的保护和恢复。 进程调度的优先级问题由 活跃进程数组的下标与进程优先级形成一种映射关系 解决。 进程调度的时间复杂度问题由 位图和两个结构体指针 解决时间复杂度控制在了O(1)。 进程调度的进程饥饿问题由 活跃队列和过期队列 解决。 创作不易如果这篇文章对你有帮助的话还望三连支持博主呀~~