Skip to content

I/O 管理概述

I/O 设备

I/O 设备管理是操作系统设计中最凌乱也最具挑战性的部分

在理解设备管理之前,应该先了解具体的 I/O 设备类型

按使用类型分类

  1. 人机交互类外部设备:用于与计算机用户之间交互的设备,如键盘等

    这类设备的数据交换速度相对较慢,通常是以字节为单位进行数据交换

  2. 存储设备:用于存储程序和数据的设备,如磁盘等

    这类设备用于数据交换,速度较快,通常以块为单位进行数据交换

  3. 网络通信设备:用于与远程设备通信的设备,如各种网络接口、调制解调器等

    速度介于前两类设备之间,网络通信设备在使用和管理上与前两类设备也有很大不同

按传输速率分类

  1. 低速设备:传输速率为每秒几字节到数百字节,如键盘、鼠标等
  2. 中速设备:传输速率为每秒数千字节至数万字节,如行式打印机、激光打印机等
  3. 高速设备:传输速率为每秒数百千字节至千兆字节,如磁带机、磁盘机、光盘机等

按信息交换的单位分类

  1. 块设备:由于信息的存取总是以数据块为单位的,如磁盘等

    属于有结构设备,传输速率较高、可寻址,即对它可随机地读/写任一块

  2. 字符设备:其传输的基本单位是字符,如键盘等

    属于无结构类型,传输速率低、不可寻址,并且在输入/输出时常采用中断驱动方式

I/O 控制方式

程序直接控制方式

对 I/O 设备发出命令后就一直检查外设的状态,直到确定该字已经在 I/O 控制器的数据寄存器中(每次读一个字

image-20211121202511286

由于 CPU 的高速性和 I/O 设备的低速性,使得 CPU 浪费时间在等待上,造成了 CPU 资源的极大浪费

优点:简单且易于实现;缺点:CPU 和 I/O 设备只能串行工作,CPU 利用率相当低

中断驱动方式

对 I/O 设备发出命令后 CPU 就去做其他事情,当 I/O 设备完后使用中断通知 CPU,CPU 处理中断(每次读一个字)

image-20211121202548700

优点:比程序直接控制方式 CPU 占用率更低;缺点:传送数据仍需要 CPU,消耗较多的 CPU 时间

DMA 方式

DMA 方式在 I/O 设备和内存之间开辟直接的数据交换通路,彻底解放 CPU

DMA 方式的特点如下:

  1. 基本单位是数据块
  2. 所传送的数据,是从设备直接送入内存的,或者相反
  3. 整块数据的传送是在 DMA 控制器的控制下完成的
  4. 仅在传送一个或多个数据块的开始和结束时,才需 CPU 干预

要在主机与控制器之间实现成块数据的直接交换,则需在 DMA 控制器中设置:

  1. 命令/状态寄存器 CR:接受 CPU 发来的 I/O 命令或有关控制信息,或设备的状态
  2. 内存地址寄存器 MAR:输入时把设备的数据读入内存;输出时把内存的数据写入设备
  3. 数据寄存器 DR:用于暂存从设备到内存或从内存到设备的数据
  4. 数据计数器 DC:存放本次要传送的字(节)数

image-20211121192900425

需要传送数据时 DMA 向 CPU 发送请求,响应后开始传送数据,整个数据块传送完成后,向 CPU 发送中断信号

image-20211121202620710

DMA 控制方式与中断驱动方式的主要区别:

  1. 中断驱动方式:每字传输都要中断 CPU;DMA 控制方式:传送完一批数据后才需要中断 CPU
  2. 中断驱动方式:中断处理时由 CPU 传输数据;DMA 控制方式:在 DMA 控制器的控制下传输数据

通道控制方式

I/O 通道是指专门负责输入/输出的处理机,是 DMA 方式的发展,它可以进一步减少 CPU 的干预,基本单位是一组数据块

当 CPU 要完成一组相关的读/写操作及有关控制时,向 I/O 通道发送一条 I/O 指令(通道程序的首地址和 I/O 设备号),通道接到该指令后,执行通道程序传送数据,数据传送结束时向 CPU 发中断请求

I/O 通道与一般处理机的区别是:通道指令的类型单一,没有自己的内存,通道所执行的通道程序是放在内存中

I/O 通道与 DMA 方式的区别是:

  • DMA 方式需要 CPU 来控制传输的数据块大小、传输的内存位置;通道方式中这些信息是由通道控制的
  • 每个 DMA 控制器对应一台设备与内存传递数据;一个通道可以控制多台设备与内存的数据交换

思考:CPU 要进行 I/O 时可能在内存写好通道程序,然后发送命令给 I/O 通道运行这些程序,运行完后发送中断

I/O 子系统的层次结构

I/O 软件层次结构

I/O 软件涉及的面非常广,即与硬件有着密切的联系,又与用户直接交互,它与进程管理、存储器管理、文件管理等都有联系

在 I/O 软件中普遍采用了层次式结构,每层都利用其下层提供的服务,完成输入/输出功能中的某些子功能,向高层提供服务

只要层次间的接口不变,对某一层次中的软件的修改都不会引起其下层或高层代码的变更,仅最低层才涉及硬件的具体特性

image-20211121212900285

整个 I/O 系统可以视为具有 4 个层次的系统结构,各层次及其功能如下:

用户层 I/O 软件

实现与用户交互的接口,用户可直接调用在用户层提供的、与 I/O 操作有关的库函数,对设备进行操作

大部分 I/O 软件在 OS 内部,小部分在用户层,包括与用户程序链接在一起的库函数,和完全运行于内核之外的一些程序

用户层软件必须通过一组系统调用来获取操作系统服务

设备独立性软件

为了实现设备独立性,必须再在驱动程序之上设置一层设备独立性软件

设备独立性也称设备无关性,使应用程序独立于具体使用的物理设备,通过引入了逻辑设备和物理设备来实现

  • 在应用程序中,使用逻辑设备名来请求使用某类设备
  • 在系统实际执行时,必须将逻辑设备名映射成物理设备名使用

使用逻辑设备名的好处是:

  1. 增加设备分配的灵活性
  2. 易于实现 I/O 重定向,即用于 I/O 操作的设备可以更换,而不必改变应用程序

设备独立性软件的主要功能可分为以下两个方面:

  1. 执行所有设备的公有操作
    • 对设备的分配与回收
    • 将逻辑设备名映射为物理设备名
    • 对设备进行保护,禁止用户直接访问设备
    • 缓冲管理
    • 差错控制
    • 提供缓冲区,屏蔽设备之间信息交换单位大小和传输速率的差异
  2. 向用户层(或文件层)提供统一接口:无论何种设备,它们向用户所提供的接口应是相同的

设备驱动程序

与硬件直接相关,负责具体实现系统对设备发出的操作指令,驱动 I/O 设备工作的驱动程序

每类设备配置一个设备驱动程序,它是 I/O 进程与设备控制器之间的通信程序,常以进程形式存在

设备驱动程序向上层用户程序提供一组标准接口,设备具体的差别被设备驱动程序所封装,从而隐藏设备控制器之间的差异

把上层的命令转换为具体要求后,发送给设备控制器,控制 I/O 设备工作;设备控制器发来的信号也传送给上层软件

中断处理程序

保存被中断进程的 CPU 环境,转入相应的中断处理程序进行处理,处理完并恢复被中断进程的现场后,返回到被中断进程

中断处理层的主要任务有:进行进程上下文的切换,对处理中断信号源进行测试,读取设备状态和修改进程状态等

由于中断处理与硬件紧密相关,对用户而言,应尽量加以屏蔽,因此应放在操作系统的底层

硬件设备

I/O 设备通常包括一个机械部件和一个电子部件

  • 电子部件,设备控制器(适配器),通常是一块插入主板扩充槽的印刷电路板
  • 机械部件:设备本身

思考:用户想要读某设备时,调用用户层的 read 命令,由设备独立性软件分配设备,由设备驱动程序解析成硬件使用的指令,由中断处理程序中断当前进程,让硬件运行读命令

*I/O 控制器

设备控制器通过内部的寄存器与 CPU 通信

  • 内存映像 I/O:这些寄存器占用内存地址的一部分
  • 寄存器独立编址:采用 I/O 专用地址

设备控制器的工作方式:

  1. OS 向控制器的寄存器写命令字
  2. 控制器收到一条命令后,完成具体的 I/O 操作
  3. 命令执行完毕后,控制器发出一个中断信号
  4. OS 检查执行结果,从状态寄存器中读取设备的状态

设备控制器的主要功能如下:

  1. 接收和识别 CPU 或通道发来的命令
  2. 实现数据交换,包括设备和控制器之间的数据传输以及控制器和主存之间的数据传输
  3. 发现和记录设备及自身的状态信息,供 CPU 处理使用
  4. 设备地址识别

为实现上述功能,设备控制器包含以下组成部分:

  1. 设备控制器与 CPU 的接口:该接口有数据线、地址线、控制线

    数据线:修改或读取数据寄存器和控制/状态寄存器的内容

  2. 设备控制器与设备的接口:

    设备控制器连接设备需要相应数量的接口,一个接口连接一台设备

    每个接口中都存在数据、控制和状态三种类型的信号

  3. I/O 控制逻辑:用于实现对设备的控制

    它通过一组控制线与 CPU 交互,对从 CPU 收到的 I/O 命令进行译码

image-20211121212940417

思考:由于设备控制器链接多个设备,有多个设备同时使用的情况,所以数据寄存器和控制/状态寄存器应有多个

注意:以机组的为准

I/O 核心子系统

I/O 子系统概述

由于 I/O 设备种类繁多,功能和传输速率差异巨大,因此需要多种方法来进行设备控制

这些方法共同组成了操作系统内核的 I/O 子系统,它将内核的其他方面从繁重的 I/O 设备管理中解放出来

I/O 核心子系统提供的服务主要有 I/O 调度、缓冲与高速缓存、设备分配与回收、假脱机、设备保护和差错处理等

I/O 调度概念

I/O 调度就是确定一个好的顺序来执行这些 I/O 请求,从而改善系统整体性能,使进程之间公平地共享设备访问

操作系统为每个设备维护一个请求队列,调度就是从中选择一个请求来运行,如磁盘调度算法

高速缓存与缓冲区

磁盘高速缓存 Disk Cache

磁盘高速缓存技术指利用内存中的存储空间来暂存从磁盘中读出的一系列盘块中的信息,对内存访问更快

磁盘高速缓存逻辑上属于磁盘,物理上则是驻留在内存中的盘块

高速缓存在内存中分为两种形式:

  1. 在内存中开辟一个单独的存储空间作为磁盘高速缓存,大小固定
  2. 未利用的内存空间作为一个缓冲池,供请求分页系统和磁盘 I/O 时共享

额外:预读是从磁盘读数据额外预读数据,滞后写是等多一点数据再写,都可以概述磁盘 I/O 性能

缓冲区 Buffer

在设备管理子系统中,引入缓冲区的目的主要如下:

  1. 缓和 CPU 与 I/O 设备间速度不匹配的矛盾
  2. 减少对 CPU 的中断频率,放宽对 CPU 中断响应时间的限制
  3. 解决基本数据单元大小不匹配的问题
  4. 提高 CPU 和 I/O 设备之间的并行性

其实现方法如下:

  1. 采用硬件缓冲器,但由于成本太高,只用于关键部位
  2. 采用缓冲区,位于内存区域

缓冲区有以下特点:

  • 当缓冲区的数据非空时,只能从缓冲区把数据传出
  • 当缓冲区为空时,可以往缓冲区冲入数据
  • 必须把缓冲区充满后,才能从缓冲区把数据传出

选择题:单缓冲、双缓冲、循环缓冲属于专用缓冲;缓冲池是系统的共用资源,可共享

选择题:缓冲区管理着重要考虑的问题是实现进程访问缓冲区的同步

根据系统设置缓冲器的个数,缓冲技术可以分为如下几种:

单缓冲

在设备和处理机之间设置一个缓冲区,被交换数据先写入缓冲区,然后被需要数据的设备或处理机取走

假设设备输入一块数据仅缓冲区的时间为 T,缓冲区中传送到用户区的时间为 M,数据处理的时间为 C

计算处理一块数据所需的时间:假设一种初始状态,计算下一次到达相同状态时所需的时间

设初始状态为:工作区是满的,缓冲区是空的,一般认为缓冲区的大小和工作区的大小相等:

  • 假设 T > C:在 T 时间后写入缓冲区和处理数据都完成,M 时间传送到用户区后,回到初始状态,用时 M + T
  • 假设 T < C:在 C 时间后写入缓冲区和处理数据都完成,M 时间传送到用户区后,回到初始状态,用时 M + C

所以单缓冲区处理每块数据的用时为 max(C, T) + M

注意:缓冲区中传送到用户区和数据处理都是 CPU 在做,所以不能并行,但都可以和设备输入数据并行

image-20211122213548458

双缓冲

I/O 设备输入数据时先装填到缓冲区 1,在缓冲区 1 填满后才开始装填缓冲区 2,同时可以从缓冲区 1 中取出数据

双缓冲机制提高了处理机和输入设备的并行操作的程度

设初始状态为:工作区是空的,一个缓冲区是满的,另一个缓冲区是空的;不妨假设 1 满 2 空

  • 假设 T > C + M:当 T 时间后回到初始状态
  • 假设 T < C + M:当 C + M 时间后回到初始状态(每次进行一个数据块的处理必定需要 C + M 的时间)

双缓冲区处理一块数据的用时为 max(C + M, T)

image-20211122213644612

若 M + C < T,则可使块设备连续输入;若 C + M > T,则可使 CPU 不必等待设备输入

单双缓冲对比

对于字符设备,若采用行输入方式:

  • 双缓冲:用户在输入第一行后,在 CPU 执行第一行中的命令的同时,用户可继续向第二缓冲区输入下一行数据
  • 单缓冲:必须等待一行数据被提取完毕才可输入下一行的数据

两台机器之间通信:

  • 单缓冲:它们在任意时刻都只能实现单方向的数据传输,而绝不允许双方同时向对方发送数据
  • 双缓冲:一个用作发送缓冲区,另一个用作接收缓冲区,实现双向数据传输

image-20211122213851387

循环缓冲

包含多个大小相等的缓冲区,这些缓冲区以循环链表的方式链接在一起,形成一个环形

循环缓冲用于输入/输出时,还需要有两个指针 in 和 out:

  • 输入:从 in 拿到第一个空缓冲区,从设备接收数据到缓冲区中,放满后 in 指向下一个
  • 输出:从 out 取第一个满缓冲区,从此缓冲区中提取数据,取空后 out 指向下一个

缓冲池

多个系统公用的缓冲区组成,缓冲区按其使用状况可以形成三个队列:

空缓冲队列、装满输入数据的缓冲队列(输入队列)和装满输出数据的缓冲队列(输出队列

还应具有 4 种缓冲区:

  1. 用于收容输入数据的工作缓冲区
  2. 用于提取输入数据的工作缓冲区
  3. 用于收容输出数据的工作缓冲区
  4. 用于提取输出数据的工作缓冲区

进程与缓冲区的交互

  • 输入进程输入数据:从空缓冲队列队首取一个空缓冲区,作为 1,输入数据后挂在输入队列队尾
  • 计算进程接受数据:从输入队列队首取一个缓冲区,作为 2,提取数据使用完后挂在空缓冲队列
  • 计算进程输出数据:从空缓冲队列队首取一个空缓冲区,作为 3,输入数据后挂在输出队列队尾
  • 输出进程接受数据:从输出队列队首取一个缓冲区,作为 4,提取数据使用完后挂在空缓冲队列

image-20211122214009700

高速缓存与缓冲区的对比

image-20211122214108952

设备分配与回收

设备分配概述

设备分配是指根据用户的 I/O 请求分配所需的设备

分配的总原则:①充分发挥设备的使用效率,尽可能地让设备忙碌;②避免造成进程死锁

从设备的特性来看,有以下使用设备的方式:

  1. 独占式使用设备:申请设备时,若设备空闲,则将其独占,直到该设备被释放才允许其他进程申请使用
  2. 分时式共享使用设备:当设备没有独占使用的要求时,可以通过分时共享使用提高利用率
  3. 以 SPOOLing 方式使用外部设备:在批处理操作系统时代引入,用于对设备的操作,实质上就是对 I/O 操作进行批处理,是以空间换时间的技术

设备分配的数据结构

设备分配依据的主要数据结构有设备控制表 DCT、控制器控制表 COCT、通道控制表 CHCT、系统设备表 SDT

由于在多道程序系统中,进程数多于资源数,会引起资源的竞争,因此要有一套合理的分配原则

主要考虑的因素:I/O 设备的固有属性、I/O 设备的分配算法、I/O 设备分配的安全性、I/O 设备的独立性

思考:一个通道对应多个设备控制器,一个设备控制器对应多个设备

设备控制表

一个设备控制表就表征一个设备,而这个控制表中的表项就是设备的各个属性

image-20211122214442221

  • 设备标识符:物理设备名,系统中的每个设备的物理设备名唯一
  • 指向控制器表的指针:每个设备由一个控制器控制,该指针可找到相应控制器的信息
  • 重复执行次数或时间:当重复执行多次 I/O 操作后仍不成功,才认为此次 I/O 失败
  • 设备队列的队首指针:指向正在等待该设备的进程队列,由进程 PCB 组成队列

控制器控制表

image-20211123194240617

  • 控制器标识符:各个控制器的唯一 ID
  • 与控制器连接的通道表指针:每个控制器由一个通道控制,该指针可找到相应通道的信息
  • 控制器队列的队首/尾指针:指向正在等待该控制器的进程队列,由进程 PCB 组成队列

通道控制表

通道方式显然要比其他几种方式更加优越,因此现代操作系统的 I/O 控制采用的都是通道控制

image-20211123194348027

  • 通道标识符:各个通道的唯一 ID
  • 与通道连接的控制器表首址:可通过该指针找到该通道管理的所有控制器相关信息
  • 通道队列的队首/尾指针:指向正在等待该通道的进程队列,由进程 PCB 组成队列

系统设备表

系统设备表 SDT:整个系统只有一张 SDT,它记录已连接到系统中的所有物理设备的情况,每个物理设备占一个表目

image-20211123194414242

  • 设备类:记录设备的类型,逻辑设备名就是这个
  • 设备标识符:物理设备名

设备的分配步骤

  1. 根据进程请求的逻辑设备名查找 SDT,用户编程时提供的逻辑设备名是设备类型

  2. 查找 SDT,找到指定类型的、并且空闲的设备,将其分配给该进程,操作系统在逻辑设备表 LUT 中新增一个表项

    若没有空闲的设备,则将进程 PCB 挂到该类设备的等待队列上

  3. 根据 DCT 找到 COCT,若控制器忙碌则将进程 PCB 挂到控制器等待队列中,不忙碌则将控制器分配给进程

  4. 根据 COCT 找到 CHCT,若通道忙碌则将进程 PCB 挂到通道等待队列中,不忙碌则将通道分配给进程

    若设备控制器连接了多个通道,则在通道忙时检查下一个通道的状态

要成功分配一个设备必须要:设备可用、控制器可用、通道可用

设备分配的策略

  1. 设备分配原则:设备分配应根据设备特性、用户要求、系统配置情况

    分配的总原则是:充分发挥设备的使用效率;避免造成进程死锁;将用户程序和具体设备隔离开

  2. 设备分配方式:

    • 静态分配:主要用于对独占设备的分配

      在用户作业开始执行前,由系统一次性分配该作业所要求的全部设备、控制器,直到该作业被撤销

      静态分配方式不会出现死锁,但设备的使用效率低,不符合分配的总原则

    • 动态分配:在进程执行过程中根据执行需要进行

      当进程需要设备时,由系统给进程分配所需要的设备、I/O控制器,一旦用完,便立即释放

      动态分配方式有利于提高设备的利用率,但若分配算法使用不当,则有可能造成进程死锁

  3. 设备分配算法:

    常用的动态设备分配算法先请求先分配、优先级高者优先

    独占设备:既可以采用动态分配方式,又可以采用静态分配方式,但往往采用静态分配方式

    共享设备:可被多个进程所共享,一般采用动态分配方式

设备分配的安全性

设备分配的安全性是指设备分配中应防止发生进程死锁

  1. 安全分配方式:每当进程发出 I/O 请求后便进入阻塞态,直到 I/O 操作完成时才被唤醒

    因为被阻塞到 I/O 完成,所以它运行时不占资源,阻塞时占一个资源,不会死锁

    优点:设备分配安全;缺点:CPU 和 I/O 设备是串行工作

  2. 不安全分配方式:进程在发出 I/O 请求后继续运行,可以继续发 I/O 请求

    仅当进程所请求的设备已被另一进程占用时,才进入阻塞态

    优点:可同时占多个设备,以迅速推进进程;缺点:这种设备分配有可能产生死锁

逻辑设备名到物理设备名的映射

设备独立性:应用程序独立于具体使用的物理设备,用于提高设备分配的灵活性和设备的利用率,方便实现 I/O 重定向

逻辑设备表 LUT:用于将逻辑设备名映射为物理设备名,以实现设备独立性

LUT 表项包括逻辑设备名、物理设备名、设备驱动程序入口地址

  • 当进程用逻辑设备名来请求分配设备时,系统为它分配相应的物理设备,并在 LUT 中建立一个表项
  • 以后进程再利用逻辑设备名请求 I/O 操作时,系统通过查找 LUT 来寻找相应的物理设备和驱动程序

在系统中可采取两种方式建立逻辑设备表:

  1. 整个系统中只设置一张 LUT:这样不允许有相同的逻辑设备名,主要适用于单用户系统
  2. 每个用户设置一张 LUT:当用户登录时,OS 为用户建立一个进程和一张 LUT,并把该表放入进程的 PCB

SPOOLing 技术

脱机输入/输出技术:缓和 CPU 的高速性与 I/O 设备低速性之间的矛盾

  • 处理器只与高速的磁盘交换数据,而不与低速 I/O 设备交换
  • 利用专门的外围控制机,让低速 I/O 设备与高速磁盘进行输入输出

SPOOLing 又称假脱机输入/输出操作,是操作系统中采用的一项将独占设备改造成共享设备的技术,下面是它的组成:

image-20211122214853891

选择题:SPOOLing 系统由预输入程序、井管理程序、缓输出程序组成

输入井和输出井

输入井和输出井是指在磁盘上开辟出的两个存储区域:

  • 输入井模拟脱机输入时的磁盘,用于收容 I/O 设备输入的数据
  • 输出井模拟脱机输出时的磁盘,用于收容用户程序的输出数据

思考:输入井和输出井与用户程序直接连接,发送数据时写到输出井;接受数据时从输入井拿

输入缓冲区和输出缓冲区

输入缓冲区和输出缓冲区是在内存中开辟的两个缓冲区:

  • 输入缓冲区:用于暂存由输入设备送来的数据,以后再传送到输入井
  • 输出缓冲区:用于暂存从输出井送来的数据,以后再传送到输出设备

思考:这部分对用户程序透明,由于 I/O 设备是与内存交互的,所以数据要经过内存

输入进程和输出进程

输入进程和输出进程就是模拟脱机输入和脱机输出时的外围控制机

  • 输入进程:将数据从 I/O 设备通过输入缓冲区再送到输入井,用户需要数据时直接从输入井拿

  • 输出进程:用户需要发送数据时放入输出井,对应的 I/O 设备空闲时,从输出井拿出数据经过输出缓冲区送到 I/O 设备

共享打印机是使用 SPOOLing 技术的一个实例,这项技术已被广泛地用于多用户系统和局域网络

当用户进程请求打印输出时,SPOOLing 系统同意为它打印输出并为它做两件事:

  1. 输出进程在输出井中为之申请一个空闲磁盘块区,并将要打印的数据送入其中
  2. 输出进程申请一张空白的用户请求打印表,写入用户打印要求,挂到请求打印队列上

SPOOLing 系统的主要特点有:提高了 I/O 的速度;将独占设备改造为共享设备;实现了虚拟设备功能

思考:提高了 I/O 速度是对于用户程序而言的,它只需要对磁盘进行 I/O 相比于 I/O 设备来说快了很多

注意:用户对井的操作是通过 SPOOLing 软件来进行的,而不是直接访问井


📝 个人补充与原笔记精华

IMPORTANT

程序直接控制方式:CPU 需要不断轮询检查设备状态,导致 CPU 长期处于“忙等”状态,利用率极低。数据传送以 为单位。

IMPORTANT

中断驱动方式:允许 I/O 设备主动请求服务。CPU 发出命令后可切换到其他进程,直到设备发出中断信号。相比程序直接控制,大大提高了 CPU 利用率,但由于每个字仍需 CPU 中转,频繁中断仍有一定开销。

Released under the MIT License.