B站

https://www.bilibili.com/video/av6538245?from=search&seid=15415472580385966467

练习

  • 在uCore操作系统上做实验
  • http://github.com/chyyuu/mooc_os_lab

预备知识

  • 计算机结构原理
  • 数据结构
  • c和汇编语言

1.2 什么是OS

  • 用户角度上, 操作系统是一个控制软件

  • 管理应用程序

  • 为应用程序提供服务

  • 杀死应用程序

  • 资源管理

  • 管理外设, 分配资源

硬件之上,软件之下

Linux/Windows/Android的界面属于外壳(shell), 而不是内核(kernel).kernel在shell之下.


Kernel-操作系统内部组件包括:

  • CPU调度器
  • 物理内存管理
  • 虚拟内存管理
  • 文件系统管理
  • 中断处理与设备驱动

OS Kernel的特征:

  • 并发(注意和并行的区别,并行是需要多个CPU,并发是单个CPU)
  • 计算机系统中同时存在多个运行的程序,需要OS管理和调度
  • 共享
    • "同时"访问
    • 互斥共享
  • 虚拟
    • 利用多道程序设计技术, 让每个用户都觉得有一个计算机为其服务
  • 异步
    • 程序的执行并不是一贯到底的,而是走走停停,向前推进的速度不可预知
    • 但是只要运行环境相同,OS需要保证程序运行的结果也要相同

2.1 操作系统的启动

  • 启动

    • 计算机体系结构概述
    • 计算机内存和硬盘布局
    • 开机顺序
  • 中断,异常和系统调用
    • 背景
    • 中断,异常和系统调用的比较
    • 中断和异常的处理机制
    • 系统调用的概念
    • 系统调用的实现
    • 程序调用与系统调用的不同之处
    • 开销

小知识:

  1. CPU:中央处理单元(Cntral Pocessing Uit)的缩写,也叫处理器,是计算机的运算核心和控制核心。人靠大脑思考,电脑靠CPU来运算、控制。让电脑的各个部件顺利工作,起到协调和控制作用。

  2. 硬盘:存储资料和软件等数据的设备,有容量大,断电数据不丢失的特点。也被人们称之为“数据仓库”

  3. 内存: 负责硬盘等硬件上的数据与CPU之间数据交换处理; 缓存系统中的临时数据; 断电后数据丢失

  4. 一下电脑应用程序是如何执行起来的?

    当我们在电脑上打开QQ时(右键-打开或者双击QQ图标),其实是通过鼠标(输入设备)向CPU发送了一条命令,CPU接收到这条命令后,QQ程序就从硬盘里被加载到内存(加载时不通过处理器,直接从硬盘加载程序到内存里),加载完成后,CPU就开始执行QQ程序。程序执行起来后,CPU可以让QQ程序显示在我们的在显示器上。也就是你看到了QQ程序运行起来了。如果这个时候,你用QQ截取了一张屏幕的图片,那么这张图片会首先保存到内存,在没有退出截屏状态时,你可以在这张图片上写字、画线条,等你右键保存这张图片的时候,这张图片就会保存到硬盘里。

  5. 为什么要通过内存链接CPU和硬盘?

    内存存取数据的速度比硬盘的存取速度快了10倍,在某些环境里,硬盘和内存之间的速度差距可能会更大.而CPU的速度比内存不知还要快多少倍。当我们把程序从硬盘放到内存以后,CPU就直接在内存运行程序,这样比CPU直接在硬盘运行程序就要快很多.

    内存解决了一部分CPU运行过快,而硬盘数据存取太慢的问题。 提高了我们的电脑的运行速度.内存就如同一条“高速车道”一般,数据由传输速度较慢的硬盘通过这条高速车道传送至CPU进行处理.

  6. 三者之间的关系

    简单来说,硬盘用来存储我们的程序和数据,当我们运行程序的时候,CPU首先接受到我们的命令,之后CPU是告诉硬盘,我要运行你存储的程序A,你把程序A送到内存去。CPU对内存说,我让硬盘把程序A送到你这里来了,你保存一下

  • 系统调用:

    应用程序主动向操作系统发出服务请求

  • 异常(来源于不良的应用程序)

    非法指令或者其他坏的处理状态(如:内存出错)

  • 中断(来源于外设)

    来源于不同的硬件设备的计时器和网络中断

操作系统如何设计和实现中断,异常和系统调用?三者之间有什么区别和特点?

  • 三者的来源:

    • 中断:外设
    • 异常: 应用程序意想不到的行为
    • 系统调用:应用程序请求操作提供服务
  • 处理时间

    • 中断: 异步
    • 异常: 同步
    • 系统调用: 同步或者异步

    中断有两种,一种是CPU本身在执行程序的过程中产生的(也称为异常),一种是由CPU外部产生的。
    外部中断,就是通常所讲的“中断”(interrupt)。对于执行程序来说,这种“中断”的发生完全是异步的,因为不知道什么时候会发生。CPU对其的响应也完全是被动的,
    可以通过“关中断”指令关闭对其的响应。

    由软件产生的中断一般是由专设的指令,如X86中的“INT n”在程序中有意产生的,是主动的,同步的。只要CPU执行一条INT指令,在开始执行下一条指令之前一定会进入中
    断服务程序

  • 响应

    • 中断: 持续,对用户应用程序是透明的
    • 异常: 杀死或者重新执行意想不到的应用程序指令
    • 系统调用: 等待和持续’

2.2 操作系统的中断,异常和系统调用

1.中断和异常的处理机制

  • 中断是外设时间

  • 异常是内部的CPU事件

  • 中断和异常迫使CPU访问一些被中断和异常服务访问的功能

硬件响应:

  • 设置中断标记[CPU初始化]

    • 将内部,外部事件设置中断标记
    • 中断事件的ID

软件响应:

  • 保存当前状态
  • 中断服务程序处理
  • 清楚中断标记
  • 回复之前的保存的处理状态

异常:

  • 异常编号
  • 保存现场
  • 异常处理
    • 杀死产生异常的程序
    • 重新执行异常指令
  • 恢复现场

2.系统调用
程序访问主要是通过高层次的API接口而不是直接进行系统调用.

  • 用户态(运行用户程序)
  • 内核态(运行操作系统程序)

https://www.cnblogs.com/Allen-rg/p/7171105.html(用户态和内核态的一个详细介绍)

跨越操作系统边界的开销:

  • 系统调用在执行时间上的开销超过程序调用调用
  • 开销
    • 建立中断/异常/系统调用号与对应的服务例程映射关系的初始化开销
    • 建立内核堆栈
    • 验证参数
    • 内核态映射到用户态的地址空间更新页面映射权限
    • 内核独立地址空间(TLB)

3.1 计算机体系结构以及内存分层体系

https://blog.csdn.net/sinat_33363493/article/details/53647129(计算机系统组成和基本工作原理)

  • 计算机系统组成

  • 计算机硬件系统

    计算机硬件5大组成部分:运算器、控制器、存储器、输入设备和输出设备

    计算机硬件的电线结构包括:单总线结构、双总线结构和采用通道的大型系统结构

1.单总线结构:使用一组系统总线将计算机的各个部件连接起来,各部件通过总线交换信息。

一般用在小型或者微型计算机。

优点:易于扩充新I/O设备,I/O设备的寄存器和主存储器可以统一编址使CPU访问I/O更 加灵活。

缺点:限制了信息传送的吞吐率。

2.双总线结构:常见的就是在内存和CPU之间设置一组专有的高速存储总线。分为以CPU为中心的双总线和以存储器为中心的双总线。

以存储器为中心的双总线结构:

主存储器通过存储总线和CPU交换信息,同时可以通过系统总线与I/O设备交换信息。

优点:信息传输效率高。

缺点:增加硬件成本。

以cpu为中心的双总线结构:

优点:控制线路简单,对I/O的总线的要求低。

缺点:CPU效率低。

采用通道的大型系统结构:一台主机可以连接多个通道,一个通道可以连接一台或多台I/O设备,具有较大的扩展性。由通道控制I/O设备,减少了CPU的压力,提高了系统效率。

操作系统的四个目标:

  • 抽象

    • 逻辑地址空间
  • 保护
    • 建立地址空间
  • 共享
    • 访问相同内存
  • 虚拟化
    • 更多的地址空间

在操作系统中管理内存的不同方法

  • 程序重定位
  • 分段
  • 分页
  • 虚拟内存
  • 按需分页虚拟内存

3.2 地址空间与地址生成

  • 地址空间定义
  • 地址生成
  • 地址安全检查

地址空间:

  • 物理地址空间:硬件支持的地址空间.

    • 起始地址0, 到地址 MAXsys

逻辑地址空间:

  • 一个运行的程序所拥有的内存范围.

    • 起始地址0,直到 MAXprog



3.3 连续内存分配:内存碎片与动态分配

比较好理解的一节

  • 连续内存分配

    • 内存碎片问题
    • 内存的动态分配
      • 第一适配(比较简单, 但是容易产生外部碎片)
      • 最佳适配
      • 最差适配
    • 压缩式碎片整理
    • 交换式碎片整理

内存碎片问题:

  • 空闲内存不能被利用
  • 外部碎片
    • 在分配单元间的未使用内存
  • 内部碎片
    • 在分配单元中的未使用内存

内存的动态分配

  • 简单的内存管理方法:

    • 当一个程序准许运行在内存中时, 分配一个连续的区间
    • 分配一个连续的内存区间给运行的程序以访问数据

3.4 连续内存分配:压缩式与交换式碎片整理

压缩式碎片整理

  • 重置程序以合并孔洞
  • 要求所有程序是动态可重置的
  • 思考:
    • 何时重置?
    • 开销?

交换式碎片整理
把程序运行过程中会有等待,等待时把其占用的主存的内存空间腾出来,而暂时把该程序移植到磁盘(虚拟内存),等到等待时间结束,再重新移植回主存。这个过程称之为交换。

  • 运行程序需要更多的内存
  • 抢占等待的程序&回收他们的内存

4.1 非连续内存分配:分段

https://www.zhihu.com/question/50796850/answer/522734117(此回答可有更通俗的理解分页和分段)
https://www.jianshu.com/p/7bfe9bb44c07(对分段,分页做了详细解释)

为什么需要非连续内存分配?目的就是改善连续内存分配的缺陷

连续内存分配的缺点:

  • 分配给一个程序的物理内存是连续的
  • 内存利用率低
  • 有内、外碎片的问题

非连续内存分配的优点:

  • 一个程序的物理地址空间是非连续的
  • 更好的内存利用和管理
  • 允许共享代码和数据(共享库等。。。。。)
  • 支持动态加载和动态连接

非连续内存分配的缺点:

  • 开销的问题
  • 需要考虑如何建立虚拟地址和物理地址之间的转换
    • 软件和硬件方案
  • 如何实现?
    • 分页和分段

分段

  • 程序的分段地址空间
  • 分段寻址方案



段访问机制

  • 一个段:一个内存“块”

    • 一个逻辑地址空间
  • 程序访问内存地址需要
    • 一个2维的二元组(s, addr)
    • s–段号
    • addr–段内偏址


4.2 非连续内存分配:分页

分页的思想:固定分区会产生内部碎片,动态分区会产生外部碎片,这两种技术对内存的利用率都比较低。为尽量避免碎片的产生,引入了分页的思想:把主存空间划分为大小相等且固定的块,块相对较小,作为主存的基本单位。每个进程也以块为单位进行划分,进程在执行时,以块为单位逐个申请主存中的块空间。

分页方法与固定分区技术不同点在于:块的大小相对于分区小很多,而且进程也按照块进行划分,进程运行时,按照块申请主存可用空间并执行。与分区留在较大的内部碎片不同,分页方式只会在最后一个主存块上留下页内碎片。

现在的计算机操作系统大都使用分页机制来进行内存管理(需要好好理解)
分页

  • 分页地址空间
  • 页寻址方案

划分方案

  • 划分物理内存至固定大小的帧

    • 大小是2的幂,e.g., 512,4096,8192
  • 划分逻辑地址空间至相同大小的页
    • 大小是2的幂,e.g., 512,4096,8192
  • 建立寻址方案, 转换逻辑地址为物理地址(pages to fames)
    • 页表
    • MMU/TLB


物理内存被分割为 大小相等的帧 。帧存在帧号(frame number)与偏移(offset),相当于段中的段号与偏移。 帧号占了F这么多位,本身大小占了S这么多位。



分页存储管理的逻辑地址结构如图所示:

小知识: 在电脑当中,运行内存包括了物理内存和虚拟的内存。虚拟内存是在物理内存(真的内存条)不够的时候,占用硬盘一部分空间作为虚拟内存,虚拟内存运行比较慢。

4.3 非连续内存分配:页表-概述、TLB

为了便于在内存中找到进程的每个页面所对应的物理块,系统为每个进程建立一张页表,记录页面在内存中对应的物理块号,页表一般存放在内存中。

  • 页表

    • 页表概述
    • 转换后备缓冲区(TLB)
    • 二级/多级 页表
    • 反向页表
  • 页表结构
    • 大数组,索引是page number,内容frame number 每个运行的程序都有一个页表,属于程序运行状态,会动态变化,PTBR(页表基址寄存器)。
    • 页表项的内容
      • Flags(标志位)
      • 帧号:f
  • 通过页表进行地址转换
    • 地址变换机构的任务是将逻辑地址转换为内存中物理地址,地址变换是借助于页表实现的。转换过程中,业内偏移是固定的,需要完成由页号到块号的变换。

    • 在系统中通常设置一个页表寄存器(PTR),存放页表在内存的始址F和页表长度M。进程未执行时,页表的始址和长度存放在进程控制块中,当进程执行时,才将页表始址和长度存入页表寄存器。设页面大小为L,逻辑地址A到物理地址E的变换过程如下:

      • 计算页号P(P=A/L)和页内偏移量W (W=A%L)。
      • 比较页号P和页表长度M,若P >= M,则产生越界中断,否则继续执行。
      • 页表中页号P对应的页表项地址 = 页表起始地址F + 页号P * 页表项长度,取出该页表项内容b,即为物理块号。
      • 计算E=b*L+W,用得到的物理地址E去访问内存。

关于页表项长度的解释:
将页表始址与页号和页表项长度的乘积相加,便得到该表项在页表中的位置。
于是可从中得到该页的物理块号,将之装入物理地址寄存器中。
列出式子出来: 页表始址+页号x页表项长度
1)页表项长度是页面长度是吗?
2)如果是页面长度,那两者相乘就是整个内存的大小来,你想一想整个内存都用来存储页表可能吗?
当然是不可能了,首先内存被划分成若干个和页面大小相等的片。
每个页表项代表一个页面的地址,一般很小。
假设内存大小是2GB,页面大小(物理块)是4KB,页表项长度是4B。
则整个内存可以被划分成2GB/4KB=512K个页面。
页表的长度=页表项的长度x页面的个数=4Bx512K=2M。
内存中用2M的大小来存放页表。

  • 性能问题:

    • 时间开销:页表太大不能放到CPU中,只能放内存,每次寻址一个内存单元需要2次内存访问,获取页表项和访问数据
    • 空间开销:1页表可能非常大,64位机器,寻址空间是2的64次幂,一个页size如果只有1024 1k,要建立一个极大的页表=254,存不下。2n个程序对应n个页表,页表个数非常大。
  • 性能问题解决方案:缓存(caching)和间接(indrection)访问

    • 在cpu的MMU中,存在一个cache叫TLB translation look-aside Buffer ,缓存近期访问的页帧转换表项。首先CPU根据逻辑地址查快表TLB(key=p, value=f,由于使用关联内存(associate memory)实现,具备快速访问性能,很少超过64个表项,每个对应一个页面的相关信息。)如果命中,FRAME很快被获取,如果未命中MISS,则去查页表并更新对应的表项到TLB中。
    • TLB的缺失不会很大,32位一个页4K,访问4K次miss一次,可以接受。写程序时注意具有局部性,把频繁的访问集中在一个区域。以避免对内存的访问。另外,还需要注意,miss后,更新是硬件完成(x86),还是OS完成(现代机器,MIPS, SPARC, HP PA)。
  • 具备快表的地址变换机构

    • 若页表全部放在内存中,则存取一个数据或一条指令至少要访问两次内存:一次是访问页表,确定所存取的数据或指令的物理地址,第二次才根据该地址存取数据或指令。这种方法比通常执行指令的速度慢了一半。

    • 为加速地址变换的过程,在地址变换机构中增设了一个具有并行查找能力的高速缓冲存储器——快表,又称联想寄存器(TLB),用来存放当前访问的若干页表项。与此对应,主存中的页表也常称为慢表,配有快表的地址变换机构如图所示:

  • 在具有快表的分页机制中,地址的变换过程:

    • CPU给出逻辑地址后,由硬件进行地址转换并将页号送入高速缓存寄存器,并将此页号与快表中的所有页号进行比较。
    • 如果在快表中找到匹配的页号,则直接从中取出该页对应的页框号,与页内偏移量拼接形成物理地址。这样,存取数据仅一次访存便可实现。
    • 如果没有找到,则需要访问主存中的页表,在读出页表项后,应同时将其存入快表,以便后面可能的再次访问。但若快表已满,则必须按照一定的算法对旧的页表项进行替换。
    • 有些处理机设计为快表和慢表同时查找,如果在快表中查找成功则终止慢表的查找。一般快表的命中率可以达到90%以上,这样,分页带来的速度损失就降低到10%以下。

4.4 非连续内存分配:页表-一二级, 多级页表

二级页表将页表的10页空间也进行地址映射,建立上一级页表,用于存储页表的映射关系。上一级页表只需要1页就足够(可以存储2^10=1024个页表项)。在进程执行时,只需要将这1页的上一级页表调入内存即可,进程的页表和进程本身的页面,可以在后面的执行中再调入内存。

对二级页表再进行拓展,得到多级页表。64位计算机通常将可寻址存储空间减少为45位长度,这样可以使用三级页表结构来实现分页存储管理。

4.5 非连续内存分配:页表-反向页表

5.1 虚拟内存的起因

  • 起因
  • 覆盖技术
  • 交换技术
  • 虚存技术
    • 目标
    • 程序局部性原理
    • 基本概念
    • 基本特征
    • 虚拟页式内存管理

内存越来越不够用,理想中的存储器是更大,更快,更便宜的非易失存储器。为内存提供更大的空间

5.2 覆盖技术

https://blog.csdn.net/github_36487770/article/details/54934919

目标:

  • 是在较小的可用内存中运行较大的程序。常用于多道程序系统,与区分存储管理配合使用。
    原理:
  • 把程序按照其自身逻辑结构,划分为若干个功能上相对独立的程序模块, 那些不会同时执行的模块共享同一块内存区域,按时间先后来运行。
    • 必要部分(常用功能)的代码和数据常驻
    • 可选部分(不常用功能)在其他程序模块中实现,平时存放在外存中, 在需要用到时才装入内存
    • 不存在调用关系的模块不必同时装入到内存,从而可以相互覆盖,即这些模块共用一个分区。
      例子:A,B,C,D,E这5个函数占用空间及调用关系如左图,如B,C之间不会相互调用因此可以共用一个分区。

      还可以A占一个分区20 k,B,E,F共用一个分区50k,C,D用一个:30k,总共只用100k

缺点:
(1) 设计开销,程序员要划分模块和确定覆盖关系,编程复杂度增加了
(2) 覆盖模块从外存装入内存,实际是以时间来换空间。

5.3 交换技术

何时交换?
硬盘操作很慢, 一动系统就要等, 所以当内存空间不够时, 或者有不够的危险时换出
交换区的大小
极端下是内存中只留一个程序,其余都在交换区. 必须够大以存放所有用户进程的所有内存映像的拷贝:必须能对这些内存映像直接存取.
swap in重定位
再次换入的内存地址一定要在原来位置上吗?
不一定,可能已被占用,要正确寻址,需要动态地址映射,虚拟地址一样,物理地址不一样。

覆盖、交换的比较:
目的是一样的。
覆盖是发生在一个运行中的程序内部没有调用关系的模块之间,代价是程序员手动指定和划分逻辑覆盖结构;交换是内存中程序与管理程序或OS之间发生的,以进程作为交换的单位,需要把进程的整个地址空间都换进换出,对程序员是透明的,开销相对较大。

5.4-5 虚存技术

起因: 由于覆盖和交换技术存在缺陷
为了实现虚存,要利用程序的局部性原理(principle of locality)

虚存技术的目标:

  • 目标

    • 像覆盖技术一样,不是把所有程序的内容都放在内存当中, 因而能够运行比当前的空闲内存空间还要大的程序.但是做的更好,由操作系统自动来完成,无需程序员干涉.
    • 像交换技术那样,能够实现程序在内存与外存之间的交换,因而获得更多的空闲内存空间.但是做的更好,只对进程的那部分内容在内存和外存之间进行交换.

为了实现虚存,要利用程序的局部性原理(principle of locality), 也就是程序在执行过程的一个较短时期,所执行的指令的地址,指令的操作数地址都局限于一定区域。

  • 时间局部性:一条指令的一次执行和下次执行,一个数据的一次访问和下次访问都在较短时间内;
  • 空间局部性:当前指令和邻近的几条指令,当前访问的数据和邻近的几个数据都集中在一个较小区域内。

因此, 虚存技术可以在页式或者段式内存管理的基础上实现

  • 在装入程序时, 不必将其全部装入到内存, 而只需要将当前执行的页面或者段装入到内存,就可让程序开始执行
  • 在程序执行的过程中,如果需执行的指令或访问的数据尚未存在内存(称为缺页或者缺段), 则由处理器通知操作系统将相应到页面或者段调入到内存,然后继续执行程序.
  • 另一方面, 操作系统将内存中暂时不使用的页面或段调出保存在外存上, 从而腾出更多空闲空间存放将要装入的程序以及将要调入的页面或者段.

虚存技术基本特征:

  • 大的用户空间:内存可以小,硬盘必须足够。提供给用户的虚拟空间=物理内存+硬盘。
  • 部分交换:swap in /swap out 是对部分虚拟地址空间进行的
  • 不连续:物理内存分配的不连续,虚拟空间使用的不连续(内外存)

具体实现:多采用虚拟页式内存管理,增加了请求调页和页面置换功能

大部分虚拟存储系统都采用虚拟页式存储管理技术,即在页式存储管理的基础上,增加请求调页和页面置换功能

  • 基本思路

    • 当一个用户程序要调入内存运行时,不是将该程序的所有页面都装入内存,只装入部分页面即可启动程序
    • 在运行程序的过程中,如果发现要运行的程序和数据不存在即页表某项invalid,则向系统发出缺页中断请求,OS根据产生异常的地址找到对应在外存中的页面并调入内存,使得该程序能够继续运行.

  • 驻留位:为1,该页在内存,0,在外存,访问会缺页中断;
  • 保护位:是否允许某种访问,只读,可读写,可执行;
  • 修改位:在内存中是否被修改过,回收物理页面时据此决定是不是把内容写回外存;
  • 访问位:如果被访问(读、写)设1,用于页面置换算法。不常用的高可能被置换。

例子:第一个操作:把虚拟地址0读入寄存器中
最底下,2代表驻留位是1,页帧号是2,页面大小4k,物理地址2*4096=8192
第二个操作:把虚拟地址32780读入,对应第8个32k-36k,X说明缺页,抛出缺页异常

对缺页中断的处理:
(1) 如果在内存中有空闲的物理空间,则分配一个物理页帧f,然后转4,否则2
(2) 采用某种页面置换算法,选择一个被替换的物理页帧,其对应逻辑页为q,没修改过可直接释放,如果修改位是1则要写回外存
(3)把q的对应页表项驻留位设为0
(4)把需要访问的页面p装入到物理页面f中
(5)修改p对应页表项,驻留位为1,物理页帧好置为f
(6)restart
在何处保存未被映射的页?
能简单地被识别,在二级存储器中的页;交换空间(磁盘/文件):特殊格式,用于存储未被映射的页面swap file

硬盘也有多种方式存储,数据,代码,动态库—>后备存储中的前三个,动态产生的数据,是没与文件直接对应的内存内容→硬盘上专门开一个区swap file

后备存储(backing store),二级存储
数据:一个虚拟地址空间的页面可以被映射到一个二级存储中文件的某个位置;
代码段:映射到可执行二进制文件;
动态加载的共享库程序段:映射到动态调用的库文件
其他段:可能被映射到交换文件(swap file)

虚拟内存性能
为了便于理解分页开销,使用有效存储器访问时间的概念
—–effective memory access time(EAT)
EAT = 访存时间 * 页表命中几率(即1-page fault) + page fault处理时间 * page fault 几率
page fault处理时间* page fault 几率= 总的磁盘访问时间 = 单次访问磁盘时间(读/写)page fault 几率 (1 + dirty page几率)
如果有修改,还要将修改位为1的页面读出到外存

开销决定于p,所以程序必须有局部性特点

6.1 最优页面置换法

https://blog.csdn.net/github_36487770/article/details/59127556

功能目标:

  • 功能: 当缺页中断发生时,需要调入新的页面而内存已满时, 选择内存当中哪个物理页面被置换
  • 目标: 尽可能地减少页面的换进换出次数(即缺页中断的次数).具体的说,把未来不再使用的或者短期内较少使用的页面换出,通常智能在局部性原理指导下依据过去统计数据来进行预测.
  • 页面锁定: 用于描述必须常驻内存的操作系统的关键部分或时间关键的应用进程.实现方法是: 在页表中添加锁定标志位.
  1. 最优页面置换算法
  • 基本思路: 当一个缺页中断发生时, 对于保存在内存中的每一个逻辑页面.计算他的下一次访问前,还需要等待多长时间.从中选择等待时间最长的那个,作为被置换页面.
  • 这只是理想情况,因为操作系统无法知道一个页面需要等多长时间才能被访问
  • 看这个想法可以作为其他算法的一个评价指标

6.2 先进先出算法(FIFO)

  1. 先进先出算法
  • 基本思路: 选择在内存中驻留时间最长的页面并淘汰.具体来说,系统维护着一个链表,记录了所有位于内存中的逻辑页面.从链表的排列顺序来看.链首的页面驻留时间最长,链尾的驻留时间最短, 当一个缺页中断发生时,把链首页面淘汰出局, 把新的页面加入到链表.
  • 性能比较差, 调出的页面可能是要经常访问的页面,并且有bBelady现象.

6.3 最近最久未使用算法(LRU)

选择最久未使用的那个页面淘汰掉. 这是对最优置换算法的近似,以过去推测未来.根据局部性原理,如果最近一段时间内某些页面被频繁访问,那么在将来还可能被频繁访问. 反之未被访问的将来也不会被访问.

  • 缺点: 需要记录各个页面使用时间的先后顺序,开销大.
  • 两种可能实现的方法:
    • 系统维护一个页面链表,最近刚使用的页面最为首节点,最久未使用的页面作为尾节点,每次访问内存动态更新头结点。缺页中断时,淘汰末位的页面。
    • 活动页面堆栈:访问某页时,将此页号入栈,并去除栈内的重复页。淘汰栈底的页面。(栈是先进后出,只有栈顶开口,怎么push栈底?)

6.4 时钟页面置换算法(Clock)

  • Clock页面置换算法, LRU的近似, 对FIFO的一种改进
  • 基本思路
    • 需要用到页表项当中的访问位, 当一个页被装入内存时, 把该位初始化为0.然后如果这个页面被访问(读/写),则把该位置为1;
    • 把各个页面组织成环形链表(类似钟表面), 把指针指向最老的页面(最先进来的)
    • 当发生一个缺页中断时, 考察指针所指向的最老的页面.若他的访问位为0,立即淘汰; 若访问位为1, 则把该位置0, 然后指针往下移动一格. 若此下去,直到找到被淘汰的页面,然后把指针移动到他的下一格.

在内存中维持一个环形页面链表,更新并删除used bit=0的页面

6.5 二次机会法(enhance clock)

区分读和写,enhanced clock algorithm
读和写都是访问,dirty bit是写位,如果写,为1,否则是0。同时使用脏位和使用位。
修改clock算法,使它允许脏页总是在一次时钟头扫描时保留下来,以减少写回硬盘的操作(仅读的页可以直接释放)
需要替换的页,其访问位和脏位都是0,如果都是 1,则有两次机会才被淘汰。从而让更多使用频率的页有更多的机会留在内存中。
较为接近LRU算法,尽量保存dirty page,更好地减少了访问外存

6.6最不常用法(LFU)

  • 基本思路: 当一个缺页中断发生时. 选择访问次数最少的那个页, 并淘汰
  • 实现方法: 对每个页面设置一个访问计数器, 每当一个页面被访问时, 该页面的访问计数器加1, 在发生缺页中断时, 淘汰计数值最小的页面
  • LRU和LFU的区别: LRU考察的是多久未被访问,时间越短越好; 而LFU考察的是访问次数或频度, 访问次数越多越好.

6.7 Belay现象, LRU, FIFO, Clock的比较

  1. LRU和FIFO本质都是先进先出,但LRU是页面的最近访问时间而不是进入内存的时间,有动态调整,符合栈算法的特性,空间越大缺页越少。如果程序局部性,则LRU会很好。如果内存中所有页面都没有被访问过会退化为FIFO。

  2. Clock 和enhanced clock也是类似于FIFO的算法,但用了硬件的BIT来模拟了访问时间和顺序,近似了LRU,综合起来较好,但也会退化为FIFO。

  3. 都对程序的访问次序有局部性的要求,不然都会退化。

  4. 开销上,LRU开销大,FIFO开销小但BELADY,折中的是clock算法,开销较小,对内存中还未被访问的页面,效果等同LRU。对曾经被访问过的则不能记住其准确位置。

6.8 局部页替换算法的问题, 工作集模型

工作集模型:
如果局部性原理不成立,那各种算法都没啥区别,比如是单调递增,那不管哪种都会缺页中断。如果局部性原理成立, 那么如何来证明他的存在, 如何对它进行定量的分析?这就是工作集模型!
工作集: 一个进程当前正在使用的逻辑页面的集合,可以用一个二元函数W(t,Δ)W(t, \Delta)W(t,Δ)来表示:

  • t是当前的执行时刻
  • Δ\DeltaΔ称为工作集窗口, 即一个定长的页面访问时间窗口
  • W(t,Δ)W(t, \Delta)W(t,Δ)=在当前时刻t之前的Δ\DeltaΔ时间窗口当中的所有页面所组成的集合(随着t的变化, 该集合也在不断的变化);
  • |W(t,Δ)W(t, \Delta)W(t,Δ)|指工作集的大小, 即页面数目

常驻集是指当前时刻, 进程中实际驻留与内存中的页面集合

  • 工作集是固有性质,常驻集取决于系统分配给进程的物理页面数目和所采用的置换算法。如果一个进程的常驻集与工作集尽量重叠,则不会造成太多缺页中断。当常驻集大小达到某个数目后,再分配物理页帧也不会有明显下降的缺页率——可以把多出来的物理页帧分给其他程序了。

6.9 两个全局页面置换算法

6.10 抖动问题

7.1 进程定义

https://blog.csdn.net/github_36487770/article/details/60144610

7.2 进程的组成

https://blog.csdn.net/github_36487770/article/details/60144610

包含了正在运行的一个程序的所有状态信息

  • 程序的代码
  • 程序处理的数据
  • 要知道现在执行哪条指令,程序计数器中的值指示将运行的指令。
  • CPU寄存器会动态变化,一组通用寄存器的当前值,堆,栈等;
  • 各种系统资源,内存,外存,网络

进程与程序的联系
程序是进程的基础,代码控制操作,可以多次执行程序,每次构成不同的进程;进程是程序功能的体现;多次执行——某一个程序对应多个进程;调用关系——某一个进程包括多个程序
多对多的映射关系

进程与程序的区别

  • 程序静态,有序代码的集合;
  • 进程动态,执行中可以是核心态/用户态,写的代码都是用户态,但有些操作比如读写文件只能由OS完成,
  • OS代表进程在内核中执行,此时为核心态;
  • 进程是暂时的,是状态变化的过程,程序永久;
  • 组成不同,进程包括程序,数据(可能变化),进程控制块(进程状态信息)

7.3 进程的特点

  • 动态性;
  • 并发性(在一段时间内有多个程序在执行,不同于并行,是一个时间点有多个在跑,需多个CPU即多核,进程可以被独立调度并占用处理机运行):
  • 独立性,正确性不受影响(通过OS给不同的进程分配不同页表);
  • 制约性,因访问共享数据/资源或进程间同步产生制约,要同步互斥;


描述进程的数据结构:进程控制块,PROCESS control block PCB
OS给每个进程都维护了一个PCB,保存与之有关的所有状态信息。

7.4 进程控制结构

PCB(进程控制块):进程存在的唯一标识,操作系统管理控制进程运行所用的信息集合,描述进程的基本情况和运行变化的过程.
用PCB的生成,回收,组织管理来完成进程的创建、终止和管理。
PCB含有三大类信息:

  • 进程标识,哪个程序在执行,执行了几次(本进程的标识),产生者标识(父进程标识),用户标识
  • 处理机状态信息保存区,主要就是寄存器,保存进程的运行现场信息:
    • 用户可见寄存器,程序使用的数据,地址
    • 控制和状态寄存器,程序计数器pc,程序状态字PSW
    • 栈指针,过程调用/系统调用/中断处理和返回时需要用到
  • 进程控制信息
    • 调度和状态信息,用于操作系统调度进程并占用处理机使用。运行状态?等待?进程当前的执行现状
    • 进程间通信信息,各种标识、信号、信件等
    • 进程本身的存储管理信息,即指向本进程映像存储空间的数据结构,内存信息,占了多少?要不要回收?
    • 进程所用资源,打开使用的系统资源,如文件
    • 有关数据结构连接信息,父进程,子进程,构成一个链,进程可以连接到一个进程队列,或链接到其他进程的PCB

PCB的组织方式:

  • 链表(便于插删,用于通用的OS):同一状态的进程PCB为一链表,多个状态对应更多个不同的链表,就绪链表,阻塞链表 ,
  • 索引表(数组,不利于插删,使用于固定数目的进程,相对创建更快捷):同一状态的归入一个index表(每一个index指向PCB),就绪/阻塞索引表

7.5 进程的生命周期

进程生命期管理:创建—>运行—>等待—>唤醒—>结束
创建:
引起进程创建的3个主要时间:系统初始化时,创建INIT进程,INIT再负责创建其他进程;

运行
运行:内核选择一个就绪的进程,让它占用处理机(cpu)并执行.

等待:
以下三种情况,进程等待(阻塞)

  • 请求并等待系统服务, 无法马上完成
  • 启动某种操作,无法马上完成
  • 需要的数据没有到达

进程只能自己阻塞自己,因为只有进程自身才知道何时需要等待某件事情的发生.
唤醒:

  • 需要的资源可被满足,
  • 等待的事件到达,
  • 都意味着可将该进程的PCB插入到就绪队列
    进程只能被别的进程或操作系统唤醒

结束:

  • 自愿(正常退出,错误退出),
  • 强制性的(致命错误,被其他进程所杀)

7.6 进程状态变化模型

进程结束前的处于且仅处于的三种状态之一:

  • 运行态(running),
  • 就绪态(ready 获得除CPU即处理机之外的一切资源,一旦得到CPU就可以运行),
  • 等待状态(阻塞态,blocked):一个进程正在等待某一事件而暂停运行时.如等待某资源,等待输入/输出完成.

进程状态变化模型

状态变化图

可能的状态变化如下:

  • NULL ->New: 一个新的进程被产生出来执行一个程序
  • New->Ready: 当进程被创建完成并初始化后,一切就绪准备运行时,变为就绪态.是否会持续很久?
  • Ready->Runing: 处于就绪态的进程被进程调度程序选中后,就分配到处理机上来运行
  • Runing->Exit: 当进程表示它已经完成或者因为出错,当前运行进程会由操作系统做结束处理.
  • Runing->Ready: 分的时间片到了,就让出处理机给另外一个程序. 这个过程由OS结合时钟完成。
  • Runing->Blocked: 当进程请求某样东西且必须等待时.
  • Blocked->Ready: 当进程要等待某事件到来时, 他从阻塞状态变换到就绪状态

创建态(new) 已创建还没就绪
结束态(exit) 正在从OS中消失,PCB还存在

7.7 进程挂起

使用进程挂起的目的是为了合理利用资源。但是不同于进程阻塞。挂起时没有占用该内存空间,而是映像在磁盘上。类似虚存中,有的程序段被放到了硬盘上。

两种挂起状态:

  • 阻塞挂起(blocked suspend): 进程在外存等事件
  • 就绪挂起(ready suspend): 进程在外存,但进了内存就能执行

状态转换:
1.在内存中被挂起:

  • blocked to blocked suspend: 没有进程ready或ready进程要求更多内存时挂起,以提交新进程或运行就绪进程
  • ready to ready suspend: 多个就绪进程挂优先级低的,有高优先级阻塞(OS认为会很快就绪)进程和低优先ready进程时,挂低优先的就绪进程
  • running to ready blocked: 抢先式分时系统,空间不够或高优先级阻塞挂起进程进入就绪挂起时,正在运行的进程被就绪挂起

2.外存中:

  • blocked suspend to ready suspend: 相关事件出现时,转变为ready suspend但还在硬盘上。
    解挂/激活 activate:外存到内存,需要运行该进程时
  • ready suspend to ready: 没有就绪进程或挂起就绪优先进程优先级高于当前就绪进程时
  • blocked suspend to blocked:当一个进程释放了足够内存时,OS把高优先级阻塞挂起(认为很快出现等待的事件)转换为阻塞进程


OS怎么通过PCB和定义的进程状态来管理?
以进程为基本结构的OS,底层为CPU调度程序(执行哪个?中断处理等),上面是各种进程。
OS要维护一组状态队列(重要的数据结构),表示系统中所有进程的当前状态。
就绪队列,各种类型的阻塞队列,挂起队列
PCB根据状态排入相应队列,状态变化加入和脱离队列

7.8 为什么使用线程

7.9 什么是线程

线程(thread): 进程中的一条执行流程。
重新理解进程
进程由两部分构成:
(1)资源管理,包括地址空间(代码段,数据段),打开的文件等的资源平台(环境)等
(2)从运行的角度,线程,即代码在这个资源平台上的一条执行流程。一个进程所拥有的线程共用进程的资源平台。利于通信。


线程有自己的TCB(thread control block)只负责这条流程的信息,包括PC程序计数器,SP堆栈,State状态,和寄存器。有不同的控制流,需要不同的寄存器来表示控制流的执行状态,每个线程有独立的这些信息,但共享一个资源。

线程=进程-共享资源
线程是控制流,一个进程中可以同时存在多个线程,各个线程并发执行,共享地址空间和文件等资源。

多线程: 在进程空间内有多个控制流且执行流程不一样,有各自独立的寄存器和堆栈,但共享代码段,数据段,资源。

线程与进程的比较:

  • 进程是资源分配单元(内存,打开的文件,访问的网络),线程是CPU调度单位,CPU也是一种特殊的资源,要执行控制流需要的相关信息
  • 进程拥有一个完整资源平台,而线程只独享必不可少的资源如寄存器和栈
  • 线程同样具有就绪,阻塞和执行三种基本状态和转换关系线程能减少并发执行的时空开销:
    • 线程的创建时间、终止时间、同一进程内线程的切换时间都更短,因为进程要创建一些对内存和打开的文件的管理信息,而线程可以直接用所属的进程的信息,因为同一进程内的线程有同一个地址空间,同一个页表,所有信息可以重用,无失效处理。而进程要切页表,开销大,访问的地址空间不一样,cache,TLB等硬件信息的访问开销大。另外线程的数据传递不用通过内核,直接通过内存地址可以访问到,效率很高。

7.10 线程的实现

https://blog.csdn.net/u013007900/article/details/79620082

三种实现方式

  • 用户线程,在用户空间实现,OS看不到,由应用程序的用户线程库来管理;POSIX Pthreads, Mach C-threads
  • 内核线程,在内核中实现,OS管理的;Windows
  • 轻量级进程lightweight process:内核中实现,支持用户线程。Solaris, Linux

7.11 上下文切换

什么是上下文切换?
进程共享CPU,停止当前进程,并调度其他进程的切换叫做上下文切换。

上下文切换的要求:

  • 切换前必须存储上下文;
  • 能够在切换后恢复他们, 所以进程不能显示他曾被暂停过;
  • 必须快速(上下文切换频繁)

要存储什么上下文?

  • 寄存器(pc,sp,…),CPU状态等
  • 一些时候可能会比较费时, 所以应该尽量避免

进程执行中要关注寄存器,PC(进程执行到了什么地方),栈指针(调用关系,相应的局部变量位置)等。这些信息要被保存到PCB中,进程挂起时要把PCB的这些值重置,恢复到寄存器中去,使接下来进程可以继续在CPU上执行。

上下文切换的开销越小越好,且所有信息都与硬件紧密相连。

7.12-14进程控制

本节知识点来源于http://c.biancheng.net/cpp/html/2590.html

创建、加载、执行、等待和结束进程

进程控制的主要功能是对系统中的所有进程实施有效的管理,它具有创建新进程、撤销已有进程、实现进程状态转换等功能。在操作系统中,一般把进程控制用的程序段称为原语,原语的特点是执行期间不允许中断,它是一个不可分割的基本单位。

进程创建

允许一个进程创建另一个进程。此时创建者称为父进程,被创建的进程称为子进程。子进程可以继承父进程所拥有的资源。当子进程被撤销时,应将其从父进程那里获得的资源归还给父进程。此外,在撤销父进程时,也必须同时撤销其所有的子进程。

在操作系统中,终端用户登录系统、作业调度、系统提供服务、用户程序的应用请求等都会引起进程的创建。操作系统创建一个新进程的过程如下(创建原语):

  1. 为新进程分配一个唯一的进程标识号,并申请一个空白的PCB(PCB是有限的)。若PCB申请失败则创建失败。
  2. 为进程分配资源,为新进程的程序和数据、以及用户栈分配必要的内存空间(在PCB 中体现)。注意:这里如果资源不足(比如内存空间),并不是创建失败,而是处于”等待状态“,或称为“阻塞状态”,等待的是内存这个资源。
  3. 初始化PCB,主要包括初始化标志信息、初始化处理机状态信息和初始化处理机控制信息,以及设置进程的优先级等。
  4. 如果进程就绪队列能够接纳新进程,就将新进程插入到就绪队列,等待被调度运行。

进程终止
引起进程终止的事件主要有:正常结束,表示进程的任务已经完成和准备退出运行。异常结束是指进程在运行时,发生了某种异常事件,使程序无法继续运行,如存储区越界、保护错、非法指令、特权指令错、I/O故障等。外界干预是指进程应外界的请求而终止运行,如操作员或操作系统干预、父进程请求和父进程终止。
操作系统终止进程的过程如下(撤销原语):

  1. 根据被终止进程的标识符,检索PCB,从中读出该进程的状态。
  2. 若被终止进程处于执行状态,立即终止该进程的执行,将处理机资源分配给其他进程。
  3. 若该进程还有子进程,则应将其所有子进程终止。
  4. 将该进程所拥有的全部资源,或归还给其父进程或归还给操作系统。
  5. 将该PCB从所在队列(链表)中删除。

进程的阻塞和唤醒
正在执行的进程,由于期待的某些事件未发生,如请求系统资源失败、等待某种操作的完成、新数据尚未到达或无新工作做等,则由系统自动执行阻塞原语(Block),使自己由运行状态变为阻塞状态。可见,进程的阻塞是进程自身的一种主动行为,也因此只有处于运行态的进程(获得CPU),才可能将其转为阻塞状态。

阻塞原语的执行过程是:

  1. 找到将要被阻塞进程的标识号对应的PCB。
  2. 若该进程为运行状态,则保护其现场,将其状态转为阻塞状态,停止运行。
  3. 把该PCB插入到相应事件的等待队列中去。

当被阻塞进程所期待的事件出现时,如它所启动的I/O操作已完成或其所期待的数据已到达,则由有关进程(比如,提供数据的进程)调用唤醒原语(Wakeup),将等待该事件的进程唤醒。

唤醒原语的执行过程是:

  1. 在该事件的等待队列中找到相应进程的PCB。
  2. 将其从等待队列中移出,并置其状态为就绪状态。
  3. 把该PCB插入就绪队列中,等待调度程序调度。

需要注意的是,Block原语和Wakeup原语是一对作用刚好相反的原语,必须成对使用。 Block原语是由被阻塞进程自我调用实现的,而Wakeup原语则是由一个与被唤醒进程相合作或被其他相关的进程调用实现的。

进程切换
对于通常的进程,其创建、撤销以及要求由系统设备完成的I/O操作都是利用系统调用而进入内核,再由内核中相应处理程序予以完成的。进程切换同样是在内核的支持下实现的,因此可以说,任何进程都是在操作系统内核的支持下运行的,是与内核紧密相关的。

进程切换是指处理机从一个进程的运行转到另一个进程上运行,这个过程中,进程的运行环境产生了实质性的变化

进程切换的过程如下:

  1. 保存处理机上下文,包括程序计数器和其他寄存器。
  2. 更新PCB信息。
  3. 把进程的PCB移入相应的队列,如就绪、在某事件阻塞等队列。
  4. 选择另一个进程执行,并更新其PCB。
  5. 更新内存管理的数据结构。
  6. 恢复处理机上下文

注意,进程切换与处理机模式切换是不同的,模式切换时,处理机逻辑上可能还在同一进程中运行。如果进程因中断或异常进入到核心态运行,执行完后又回到用户态刚被中断的程序运行,则操作系统只需恢复进程进入内核时所保存的CPU现场,无需改变当前进程的环境信息。但若要切换进程,当前运行进程改变了,则当前进程的环境信息也需要改变。

8.1 算法背景

上下文切换:切换CPU的当前任务,从一个进程/线程到另一个,保存当前在PCB/TCB中的执行上下文,读取下一个的上下文
CPU调度:从就绪队列中挑选一个进程/线程作为CPU将要运行的下一个线程/进程
调度程序:挑选进程/线程的内核函数(通过一切调度策略)使得效率最高,满足用户需求

1.在进程/线程的生命周期中的什么时候进行调度?
从一个状态变为另一个状态,特别是和运行(running)相关的状态。

2.内核运行调度程序的条件:进程从运行状态切换到等待状态;一个进程被终结了.(这两者满足一个就可以)
3.不可抢占调度:调度必须等待事件/进程结束(早期OS)。
4.可以抢占:调度程序在中断被响应后执行;当前的进程从运行切换到就绪,或者一个进程从等待切换到就绪;当前运行的进程被换出(OS决定在何时打断进程).

可以抢占针对的是用户态的进程。 进程在内核中通过系统调用执行,因为系统调用返回时是到发起这个调用的进程继续执行,所以内核中不会切换,抢占。只要进程在系统调用时不存在从运行态到阻塞态的变化,OS可以确保返回正常。 如果在内核中也允许这种抢占,系统调用返回时不是原来的进程而是另一个优先级更高的进程,就是内核中的抢占。

os早期是完全不可抢占,后来用户态进程允许抢占,现在内核态进程也可以抢占。

8.2 调度原则

CPU的占用率是波状,CPU大量运算是高峰,而读写I/O时是平稳的低值。每个调度决定都是关于下一个CPU突发时将哪个工作交给CPU,在时间分片下,线程可能在结束当前CPU突发前被迫放弃CPU。
程序在CPU突发和I/O中交替,CPU占用率高说明是在充分地使用CPU。

选择调度方法的评价指标:

  • CPU使用率:CPU处于忙状态的时间百分比
  • 吞吐量:单位时间内完成的进程数量
  • 周转时间:一个进程从初始化到结束包括(所有等待时间)- - 所花费的时间,周转时间=等待时间+服务时间
  • 等待时间:进程在就绪队列中的总时间,进程从就绪态到运行态的时间。
  • 响应时间:一个请求被提交到第一次响应所花费的总时间

用户要求:

  • 高带宽:吞吐量高
  • 低延迟:响应时间快

用量化的方法来看调度算法:

  • 减少响应时间
  • 减少平均响应时间的波动,交互系统中,可预测性比高差异低平均更重要
  • 增加吞吐量
    减少开销(操作系统开销,上下文切换)
    系统资源的高效利用(CPU,I/O设备)
  • 减少等待时间

8.3-4 调度算法

  • 一般性的调度算法
  • 针对嵌入式系统的特殊调度算法
  • 多CPU多内核的调度算法

1、先到先服务调度算法(FCFS)
  根据就绪队列的到达时间来服务,此时就绪队列是一个FIFO队列,先到先服务,后到的线程不能抢占前面正在服务的线程。这种算法的优点是实现简单,缺点也很明显,就是CPU进程区间变化很大时,平均等待时间会变化很大。

2、最短作业优先调度(SJF)
  顾名思义,就是CPU进程区间最短的先执行,如果两个进程区间具有同样的长度,那么按照FCFS来调度。

SJF可以是抢占的,也可以是不抢占的。它的平均等待时间优于FCFS。

3、优先级调度(HRRN)
  其实上面的SJF算法就是一种特殊的优先级调度,只不过这里的优先级定义更加广泛一些,SJF算法的优先级是按照CPU进程区间长短来定义的,这里的优先级可以是其他的一些定义。

优先级调度可以是抢占的,也可以是非抢占的。

优先级调度的一个主要问题是无穷阻塞(也称为饥饿),如果一个线程的优先级很低,可能需要等待很长的时间才能到这个线程执行,甚至永远不执行,一种解决方法是老化(随着时间的增长,增加线程的优先级)

4、轮转法调度(RR)
  轮转法调度专门是为分时系统设计的。它类似于FCFS,但是增加了抢占为了切换线程。定义一个较小的时间单元,称为时间片,通常为10-100ms。为了实现RR算法,将就绪队列保存为FIFO队列,新进程增加到就绪队列队尾,CPU调度程序从就绪队列选择第一个进程,设置定时器在一个时间片之后再中断,再分派这个进程。

如果该进程的CPU区间小于时间片,进程本身就会释放CPU,调度程序继续处理下一个进程,如果当前进程的CPU区间比时间片长,定时器会产生CPU中断,实行上下文切换,然后将此进程放到就绪队列队尾,继续调度就绪队列第一个进程。

5、多级队列调度:
  这里对进程进行分组,在组内使用FCFS和SJF算法,在组间实行优先级调度或者轮转法调度。但是不允许进程在组间切换。

6、多级反馈队列调度
  允许进程在组间切换,主要思想是根据不同区间的特点区分进程,如果CPU进程占用过多CPU时间,那么它会被转移到更低优先级队列。这种形式老化阻止饥饿。

各个调度算法的详细解释:

1、FCFS first come first served先来先服务
如果前面的进程运行的时间长,后面的进程就只能等着,导致周转时间慢。如果进程阻塞了,队列中的下一个会得到CPU

优点:简单
缺点:平均等待时间波动大;花费时间少的可能反而排在后面;可能导致CPU和I/O之间的重叠处理,没考虑抢占,CPU密集的进程导致I/O闲置时,I/O密集型进程也在等。

2、SPN/SJF/SRT shortest process next/shortest JOB first/shortest remaining time 短剩余时间,短进程优先

不可抢占: SJF SPN
可抢占: ready queue中的第一个进程正在运行时,来了一个比它的预测完成时间还短的进程,SRT

优点:最小的平均等待时间和周转时间
缺点:可能导致长任务饥饿,不能保证公平;需要预知未来下一个进程的时间,比如询问用户,如果用户欺骗就杀死进程。

可以根据进程执行历史看将来某个进程CPU突发的持续时间,递归展开

预测和实际情况可能会有差距,但是趋势是一致的。

3、HRRN 最高相应比优先

  • 在SPN调度的基础上进行改进
  • 不可抢占
  • 关注进程等待了多长时间
  • 防止无限期推迟(饥饿)

R=(w+s)/sR=(w+s)/sR=(w+s)/s
w: waiting time 等待时间
s: service time 服务时间
选取R值最高的进程作为高优先级进程。

优点:交互性,响应性更好
缺点:对抢占性的支持不够,也需要预知service time

4、Round Robin 轮循
用时间切片和抢占来轮流执行,强调了公平

  • 在量子切片/时间切片的离散单元中分配处理器;
  • 时间片结束时切换到下一个准备好的进程

有点:公平,相对稳定;
缺点:但平均等待时间较长
开销:额外的上下文切换;
时间量子的选择:

  • 太大,则等待时间过长会退化成FCFS;
  • 太小,反应迅速但吞吐量由于大量的上下文切换开销受影响

目标:选择一个合适的时间量子,经验是维持上下文切换开销处于1%以内,现在LINUX是千分之一秒

Multilevel Queues→ multilevel Feedback Queues
多级队列:
就绪队列分为相对独立的队列,前台交互,RR,后台/底层批处理,FCFS,调度在队列间进行

  • 固定优先级:先前台,再处理后台,可能导致饥饿
  • 时间切片:每个队列都得到一个确定的,调度其进程的CPU总时间,如80%给前台,20%给后台

进程和队列都在动态变化,能否动态调整?
多级反馈队列 优先级队列中的轮循 有动态调整:
一个进程可以在不同队列中移动,N级优先级
在所有队列中优先级调度,每个级别内部RR轮循
时间量子大小随优先级增加而增加,若当前时间量子中没有完成就给当前任务则降到下一个优先级

Fair share scheduling cpu的等待时间和执行时间公平共享在用户级别实现公平共享
FFS控制用户对系统资源的访问

  • 一些用户组比其他组更重要,
  • 保证不重要的组无法垄断资源,
  • 未使用的资源按照每个组所分配的资源的比例来分配,
  • 没有达到资源使用率目标的组获得更高的优先级

8.5 实时调度

调度火车,工厂,需要确保任务在规定时间内完成的
1、定义: 正确依赖于其时间功能两个方面的一种操作系统。
2、性能指标:

  • 时间约束的即使性
  • 速度和平均性能相对重要

3、主要特性

  • 时间约束的可预测性

4、类别

  • 硬实时系统/强实时系统:如果某个任务没完成有严重后果
  • 软实时系统/弱实时系统:重要的进程优先级更高,要尽量完成,如看视频,帧数没控制好会掉帧。

5、任务/工作单元job:一次计算,一次文件读取,一次信息传递等等
6、属性:取得进展所需要的资源和实时参数

  • release time 进程处于就绪态的时间
  • relative deadline: 任务是间隔时间段完成,每个任务有个特定的时间,要在特定的时间段内完成
  • absolute deadline:最终的结束时间

8.6多处理器调度与优先级反转

阅读笔记--操作系统(清华大学公开课)相关推荐

  1. 计算机体系结构 公开课,清华大学公开课:操作系统

    操作系统是控制软件,管理应用程序,为应用程序提供服务,杀死应用程序,分配资源,管理外设.(网易公开课编辑整理) 操作系统是控制软件,管理应用程序,为应用程序提供服务,杀死应用程序,分配资源,管理外设. ...

  2. 清华大学公开课线性代数2——第8讲:图和网络

    此博客停止更新迁移至SnailDove's Blog,查看本文点击此处 目录 目录 简介 欧姆定律Ohms law的向量形式 图与矩阵 关联矩阵incidence matrix 邻接矩阵adjacen ...

  3. 清华大学公开课线性代数2——第7讲:工程中的矩阵

    此博客停止更新迁移至SnailDove's Blog,查看本文点击此处 笔记源自:清华大学公开课:线性代数2--第7讲:工程中的矩阵 提示:如果文中图片看不清文字,请右键单击鼠标,选择在新窗口打开图片 ...

  4. 清华大学公开课线性代数2——第9讲:马尔科夫矩阵和正矩阵

    此博客停止更新迁移至SnailDove's Blog,查看本文点击此处 笔记源自:清华大学公开课:线性代数2--第9讲:马尔科夫矩阵和正矩阵 提示:如果文中图片看不清文字,请右键单击鼠标,选择在新窗口 ...

  5. 清华大学公开课线性代数2——第6讲:伪逆

    此博客停止更新,迁移至SnailDove's blog,查看本文请点击此处,清华大学线性代数2笔记汇总:线性代数总结 笔记源自:清华大学公开课:线性代数2--第6讲:伪逆 **提示:**如果文中图片看 ...

  6. 清华大学公开课线性代数2——第1讲:正定矩阵

    此博客停止更新迁移至SnailDove's Blog,查看本文点击 此处 清华大学线性代数2笔记汇总:线性代数总结 笔记源自:清华大学公开课:线性代数2--第1讲:正定矩阵,涉及:正定矩阵.二次型.合 ...

  7. 清华大学公开课线性代数2——第10讲:傅里叶级数

    此博客停止更新迁移至SnailDove's Blog,查看本文点击此处 笔记源自:清华大学公开课:线性代数2--第10讲:傅里叶级数 **提示:**如果文中图片看不清文字,请右键单击鼠标,选择在新窗口 ...

  8. 清华大学公开课线性代数2——第3讲:奇异值分解

    此博客停止更新迁移至SnailDove's Blog,查看本文点击此处 笔记源自:清华大学公开课:线性代数2--第3讲:奇异值分解 提示:如果文中图片看不清文字,请右键单击鼠标,选择在新窗口打开图片, ...

  9. 清华大学公开课线性代数2——第4讲:线性变换1

    此博客停止更新迁移至SnailDove's Blog,查看本文点击此处 笔记源自:清华大学公开课:线性代数2--第4讲:线性变换1 目录 目录 前言 线性变换的定义性质运算 向量空间的定义 线性变换的 ...

最新文章

  1. 【Kubernetes】Kubernetes的Service外部访问方式:NodePort和LoadBalancer
  2. Bootstrap 与 Jquery validate 结合使用——简单实现
  3. javascript中的事件处理
  4. 【若依(ruoyi)】表格实现tooltip
  5. react js 按条数 展开/折叠
  6. pandas series取值_【小学生级】pandas入门到精通备查表——AI未来系列3
  7. Java工作笔记-JPA查询达梦7数据库(Spring Boot + ORM)
  8. 请阐述调用Activity有哪几种方法,并写出相关的Java代码
  9. 利用memoize缓存到Redis出现多个参数同一个结果
  10. [通信] ITU-T G.729 8kb/s CS—ACELP简介
  11. 华硕ASUS acrh17 PandoraBox固件
  12. spyder python下载_Spyder Python软件-Spyder Python下载-最火手机站
  13. 世界500强面试题----反应能力
  14. 利用python、selenium和超级鹰 实现B站自动登录
  15. 淘宝联盟饿了么推广 API取链转链 永久有效
  16. iredmail mysql_iRedmail配置手册
  17. 7款最好用的图片无损,视频无损压缩软件
  18. WinServer 2012 R2 安装python3.6时出现错误:0x80240017 导致安装失败
  19. Huawei RH2288 V3 风扇噪音大的解决方案
  20. ios:新浪微博iphone客户端

热门文章

  1. Thinkphp 模型与表名定义
  2. 自定义用户和认证 中间件 文件上传/oss 图片验证码
  3. 手机移动端web总结
  4. ips细胞最新发现:科学家开发出了一套评估干细胞的全能性的新标准
  5. mysql架设手游_手游长生诀手工架设完整服务端文件+安卓客户端+架设教程
  6. SAP中带用内部订单控制的成本中心发料的成本对象确定
  7. 解决异常Error creating bean with name ‘xxxxxController‘: Unsatisfied dependency expressed through field
  8. IDEA运行Java Applet程序
  9. 程旭/王蒙岑/袁梦婷/李建刚/熊武客座主编Frontiers根际微生物组专刊征稿(IF6)
  10. 微信小程序云开发实现收藏及收藏页面(带样式布局)