(Linux2.6内核)进程调度队列与切换

简介: (Linux2.6内核)进程调度队列与切换

个人主页:Lei宝啊

愿所有美好如期而遇


我们首先来了解几个概念

1. 进程在CPU上运行的时候,一定要运行完才行吗?答案是否定的,我们大部分的操作系统,主流就是分时操作系统,即基于时间片进程轮转执行的。

时间片是什么呢?

就是进程有一个执行时间,这个时间到了就算没执行完,也不会继续执行,而是会执行下一个进程,每个进程都有自己的时间片,时间片到了就下一个进程。

2. 竞争性:系统进程很多,但是CPU只有少数,我们大部分人用的只有一个,为了更高效完成任务,需要合理竞争相关资源,于是就有了优先级。

 独立性:进程相互之间是独立的,多进程同时运行相互之间不会影响。

    并行:多个进程在多个CPU下分别,同时运行。

    并发:多个进程在一个CPU下通过进程切换的方式,在一段时间内,让多个进程同时推进,称之为并发。

进程的切换

       我们要先知道CPU里有很多的寄存器,这些寄存器用来计算进程的代码和数据,寄存器也可以存储数据,eip这个寄存器存储将要执行的下一行代码的地址,CPU执行到哪一行,那行的代码和数据就会输入寄存器,寄存器计算后会返回一个结果,同时在寄存器内产生大量临时数据,这个临时数据我们叫做进程的硬件上下文。

       在一个进程时间片结束时,会将CPU寄存器中的临时数据保存在task_struct中,下一次执行时,将数据覆盖在寄存器上,继续上一次的执行,如果是首次执行的寄存器,会从头开始执行,每个进程的数据都是私有的,寄存器中上一个进程留下的临时数据不会被下一个进程读取,下一个进程会将自己的数据在寄存器上进行覆盖。

所有的保存是为了最终数据的恢复,所有的恢复都是为了继续上次的运行。

进程的调度

我们说,一个程序本质就是二进制文件,是文件就保存在磁盘中,而想要运行这个程序,就要先将其加载到内存中,而加载到内存中,就要被操作系统所管理,于是操作系统建立了他的PCB,也就是task_struct,然后将程序加载到内存中,描述了这个程序之后,将其连入数据结构中进管理,于是这个可执行程序的代码和数据+内核数据结构就构成了进程,而进程要想被CPU运行,就要先进入CPU的运行队列进行排队,而排队的进程也有优先级,Linux实现进程调度的算法,既要考虑优先级,还要考虑饥饿问题,以及效率。

上图就是Linux2.6内核中进程队列的数据结构。

首先,queue[140]这个数组中的每个元素都是task_struct*类型,也就是指向进程的进程控制块,这个数组我们只会用到下标100~139,40个下标对应了我们40个优先级,下标越靠前,优先级越高。

CPU在执行进程时,就会去遍历这个数组,如果不为NULL,就说明这个优先级有队列,就会开始执行这个队列的进程,这个队列的进程执行完或者时间片结束,就会离开这个队列,于是活跃队列中的进程越来越少,直到全部为NULL。

我们定义一个 struct q这样的结构体,再用这样一个结构体定义一个数组,我们的active以及expired都是struct q*类型,分别指向这个数组的元素,active指向的活跃队列,expire指向过期队列,CPU执行活跃队列里的进程时,当有优先级高的进程就绪时,不会进入活跃队列,而是进入过期队列中对应下标中,当活跃队列中的进程时间片结束,但是没有执行完,也会按照优先级进入过期队列相应的下标中,当活跃队列全部为空时,执行swap(&active,&expired),交换指针,过期队列也就变成了活跃队列,活跃队列变成过期队列,CPU不会直接去访问这个数组中的结构体,而是通过这两个指针去访问队列。

再一个,CPU不会去遍历queue,而是通过其他算法,也就是通过我们的bitmap数组,32*5共160个字节,我们使用其中140个bit位,对应queue中的每个下标,如果下标为空,那么对应在bitmap中的那个bit位就是0,不为空就是1,因为bitmap有5个字节,我们会通看这个数组的每一个元素是否为0,为0,直接下一个元素,省去了遍历32个位,不为0,我们就通过位运算去取到bit位为1的位置,然后CPU去执行!这样就再次提高了效率,Linux进程调度的算法以及其结构非常优秀!

目录
相关文章
|
8天前
|
Linux Shell
6-9|linux查询现在运行的进程
6-9|linux查询现在运行的进程
|
17天前
|
算法 调度 Python
探索操作系统的内核——一个简单的进程调度示例
【9月更文挑战第17天】在这篇文章中,我们将深入探讨操作系统的核心组件之一——进程调度。通过一个简化版的代码示例,我们将了解进程调度的基本概念、目的和实现方式。无论你是初学者还是有一定基础的学习者,这篇文章都将帮助你更好地理解操作系统中进程调度的原理和实践。
|
23天前
|
存储 安全 Linux
探索Linux操作系统的心脏:内核
在这篇文章中,我们将深入探讨Linux操作系统的核心—内核。通过简单易懂的语言和比喻,我们会发现内核是如何像心脏一样为系统提供动力,处理数据,并保持一切顺畅运行。从文件系统的管理到进程调度,再到设备驱动,我们将一探究竟,看看内核是怎样支撑起整个操作系统的大厦。无论你是计算机新手还是资深用户,这篇文章都将带你领略Linux内核的魅力,让你对这台复杂机器的内部运作有一个清晰的认识。
52 3
|
1月前
|
缓存 安全 Unix
Linux 内核黑客不可靠指南【ChatGPT】
Linux 内核黑客不可靠指南【ChatGPT】
|
1月前
|
Linux 开发者
Linux内核贡献成熟度模型 【ChatGPT】
Linux内核贡献成熟度模型 【ChatGPT】
|
1月前
|
网络协议 Ubuntu Linux
用Qemu模拟vexpress-a9 (三)--- 实现用u-boot引导Linux内核
用Qemu模拟vexpress-a9 (三)--- 实现用u-boot引导Linux内核
|
1月前
|
Linux
用clang编译Linux内核
用clang编译Linux内核
|
21天前
|
存储 监控 安全
探究Linux操作系统的进程管理机制及其优化策略
本文旨在深入探讨Linux操作系统中的进程管理机制,包括进程调度、内存管理以及I/O管理等核心内容。通过对这些关键组件的分析,我们将揭示它们如何共同工作以提供稳定、高效的计算环境,并讨论可能的优化策略。
22 0
|
1月前
|
Linux API 调度
关于在Linux内核中使用不同延迟/休眠机制 【ChatGPT】
关于在Linux内核中使用不同延迟/休眠机制 【ChatGPT】
|
网络协议 NoSQL Linux
阿里云 Linux 内核优化实战(sysctl.conf 和 ulimits )
一、sysctl.conf优化Linux系统内核参数的配置文件为 /etc/sysctl.conf 和 /etc/sysctl.d/ 目录。其读取顺序为: /etc/sysctl.d/ 下面的文件按照字母排序;然后读取 /etc/sysctl.conf 。
8425 1
下一篇
无影云桌面