现代操作系统 第五章 输入/输出

现代操作系统 第五章 输入/输出

本文为读书摘要(个人认为重要的知识点)

本文只选取了 与I/O硬件编程有关的一般性背景知识(5.1~5.3)。这些内容可以看成是对1.4节介绍性材料的复习和扩充。

I/O 硬件原理

I/O设备

I/O设备大致可以分为两类:块设备(block device)和字符设备(character device)。

  • 块设备把信息存储在固定大小的块中,毎个块有自己的地址。通常块的大小在512字节至65 536字节之间。

  • 另ー类I/O设备是字符设备。字符设备以字符为单位发送或接收ー个字符流,而不考虑任何块结构。字符设备是不可寻址的,也没有任何寻道操作。

这种分类方法并不完美,有些设备就没有包括进去。例如,时钟既不是块可寻址的,也不产生或接收字符流。它所做的工作就是按照预先规定好的时间间隔产生中断。

设备控制器

I/O设备一般由机械部件和电子部件两部分组成。通常可以将这两部分分开处理,以提供更加模块化和更加通用的设计。

电子部件称作设备控制器(device controller)或适配器(adapter)。

控制器的任务是把串行的位流转换为字节块,并进行必要的错误校正工作。字节块通常首先在控制器内部的ー个缓冲区中按位进行组装,然后再对校验和进行校验并证明字节块没有错误后,再将它复制到主存中。

内存映射I/O

image-20220327141658247

每个控制器有几个寄存器用来与CPU进行通信。通过写入这些寄存器,操作系统可以命令设备发送数据、接收数据、开启或关闭,或者执行某些其他操作。通过读取这些寄存器,操作系统可以了解设备的状态,是否准备好接收ー个新的命令等。

于是,问题就出现了: CPU如何与设备的控制寄存器和数据缓冲区进行通信?

  • 在第一个方法中,每个控制寄存器被分配ー个“〇端口(DO port)号,这是ー个8位或16位的整数。所有I/O端口形成1/0端口空间(I/O port space),并且受到保护使得普通的用户程序不能对其进行访问(只有操作系统可以访问)。

    • 使用特殊的 I/O 指令进行读写
    • 内存地址空间和 I/O 地址空间是不同的,如图5-2a所示
  • 第二个方法是将所有控制寄存器映射到内存空间中,如图5-2b所示。每个控制寄存器被分配唯一的ー个内存地址,并且不会有内存被分配这一地址。这样的系统称为内存映射I/O (memory-mapped I/O)。在大多数系统中,分配给控制寄存器的地址位于或者靠近地址空间的顶端。

    • 好处

      • 对于内存映射 I/O,I/O设备驱动程序可以完全用C语言编写。如果不使用内存映射!/〇,就要用到某些汇编代码。(不需要特殊的I/O指令)
      • 第二,对于内存映射I/O,不需要特殊的保护机制来阻止用户进程执行I/O操作。
      • 第三,对于内存映射I/O,可以引用内存的每一条指令也可以引用控制寄存器。
    • 坏处

      • 对ー个设备控制寄存器进行高速缓存可能是灾难性的。

        所以对内存映射I/O,为了避免这ー情形,硬件必须能够针对每个页面有选择性地禁用高速缓存。

图5-2c所示是ー种混合的方案,这ー方案具有内存映射I/O的数据缓冲区,而控制寄存器则具有单独的 I/〇 端口。x86采用这一体系结构。

image-20220327143550049

现代个人计算机的趋势是包含专用的高速内存总线,如图5-3b所示。装备这ー总线是为了优化内存性能,而不是为了慢速的 I/O 设备而做的折中。但这也使得必须采取特殊的措施使内存映射I/O工作在具有多总线的系统上。

直接存储器存取

无论ー个CPU是否具有内存映射I/O,它都需要寻址设备控制器以便与它们交换数据。CPU可以从
I/o控制器每次请求一个字节的数据,但是这样做浪费CPU的时间,所以经常用到ー种称为直接存储器
存取(Direct Memory Access, DMA)的不同方案。

image-20220327143843305

DMA能够独立于CPU而访问系统总线,如图5-4所示。它包含若干个可以被CPU读写的寄存器,其中包括ー个内存地址寄存器、ー个字节计数寄存器和一个或多个控制寄存器。控制寄存器指定要使用的 I/O 端口、传送方向(从 I/O 设备读或写到 I/O 设备)、传送单位 (毎次一个字节或每次一个字)以及在一次突发传送中要传送的字节数。

DMA读磁盘的步骤

  1. CPU通过设置DMA控制器的寄存器对它进行编程(DMA知道做什么)
    DMA控制器还要向磁盘控制器发出ー个命令,通知它从磁盘读数据到其内部的缓冲区中,并且对校验和进行检验。
  2. DMA控制器通过在总线上发出ー个读请求到磁盘控制器而发起DMA传送。
  3. 写到内存是另ー个标准总线周期。
  4. 当写操作完成时,磁盘控制器在总线上发出ー个应答信号到DMA控制器。
  5. DMA控制器将中断CPU以便让CPU知道传送现在已经完成了。

为什么控制器从磁盘读取字节后不立即将其存储在主存中?

  • 首先,通过进行内部缓冲,磁盘控制器可以在开始传送之前检验校验和。如果校验和是错误的,那么将发出一个表明错误的信号并且不会进行传送。

  • 第二个原因是,一旦磁盘传送开始工作,从磁盘读出的数据就是以固定速率到达的,而不论控制器是否准备好接收数据。如果控制器要将数据直接写到内存,则它必须为要传送的每个字取得系统总线的控制权。此时,若由于其他设备使用总线而导致总线忙(例如在突发模式中),则控制器只能等待。(需要做对意外情况做大量额外工作)

重温中断

硬件层面,中断的工作如下所述。当ー个シ。设备完成交给它的工作时,它就
产生一个中断(假设操作系统已经开放中断),它是通过在分配给它的一条总线信号线上置起信号而产
生中断的。该信号被主板上的中断控制器芯片检测到,由中断控制器芯片决定做什么。

image-20220327144912374

中断信号导致CPU停止当前正在做的工作并且开始做其他的事情。地址线上的数字被用做指向ー个称为中断向量(interrupt vector)的表格的索引,以便读取ー个新的程序计数器。这ー程序计数器指向相应的中断服务过程的开始。

一般情况下,陷阱和中断从这一点上看使用相同的机制,并且常常共享相同的中断向量。

一般使用内核堆栈保存中断服务程序的信息(如程序计数器)

精确中断和不精确中断

将机器留在ー个明确状态的中断称为精确中断(precise interrupti Walker和Cragon, 1995)。精确中断具有4个特性:

1)PC(程序计数器)保存在ー个已知的地方。
2) PC 所指向的指令之前的所有指令已经完全执行d
3) PC 所指向的指令之后的所有指令都没有执行。
4) PC 所指向的指令的执行状态是已知的。

I/O软件原理

I/O软件的目标

  • 在设计I/O软件时一个关键的概念是设备独立性(device independence)。它的意思是应该能够编写出这样的程序:它可以访问任意I/O设备而无需事先指定设备。

程序控制I/O

  • 程序控制 I/O 十分简单但是有缺点,即直到全部I/o完成之前要占用CPU的全部时间。如果“打印”一个字符的时间非常短(因为打印机所做的全部事情就是将新的字符复制到ー个内部缓冲区中),那么忙等待还是不错的。此外,在嵌入式系统中,CPU没有其他事情要做,忙等待也是合理的。然而,在更加复杂的系统中,CPU有其他工作要做,忙等待将是低效的,需要更好的 I/O 方法。

中断驱动I/O

  • 这种允许CPU在等待打印机变为就绪的同时做某些其他事情的方式就是使用中断。当打印字符串的系统调用被发出时,如我们前面所介绍的,字符串缓冲区被复制到内核空间,并且一旦打印机准备好接收ー个字符时就将第一个字符复制到打印机中。
    这时,CPU要调用调度程序,并且某个其他进程将运行。 请求打印字符串的进程将被阻塞,直到整个字符串打印完。

使用 DMA的I/O

  • DMA重大的成功是将中断的次数从打印每个字符一次减少到打印毎个缓冲区一次。如果有许多字符并且中断十分缓慢,那么采用DMA可能是重要的改进。
  • 另ー方面,DMA控制器通常比主CPU要慢很多。如果DMA控制器不能以全速驱动设备,或者CPU在等待DMA中断的同时没有其他事情要做,那么采用中断驱动I/O甚至采用程序控制I/O也许更好。

I/O软件层次

image-20220327145914124

中断处理程序

当中断发生时,中断处理程序 将做它必须要做的全部工作以便对中断进行处理。然后,它可以将启动中断的驱动程序解除阻塞。

对ー个中断进行处理并不只是简单地捕获中断,在某个信号量上执行up操作,然后执行一条IRET指令从中断返回到先前的进程。对操作系统而言,还涉及更多的工作。我们将按一系列步骤给出这ー工作的轮廓,这些步骤是硬件中断完成之后必须在软件中执行的。应该注意
的是,细节是非常依赖于系统的,所以下面列出的某些步骤在ー个特定的机器上可能是不必要的,而没有列出的步骤可能是必需的。

1)保存没有被中断硬件保存的所有寄存器(包括PSW)。
2)为中断服务过程设置上下文,可能包括设置TLB、MMU和页表。
3)为中断服务过程设置堆栈。
4)应答中断控制器,如果不存在集中的中断控制器,则再次开放中断。
5)将寄存器从它们被保存的地方(可能是某个堆栈)复制到进程表中“
6)运行中断服务过程,从发出中断的设备控制器的寄存器中提取信息。
7)选择下一次运行哪个进程,如果中断导致某个被阻塞的高优先级进程变为就绪,则可能选择它现 在就运行。
8)为下一次要运行的进程设置MMU上下文,也许还需要设置某个TLB。
9)装入新进程的寄存器,包括其PSW。
10)开始运行新进程。

设备驱动程序

每个连接到计算机上的I/O设备都需要某些设备特定的代码来对其进行控制。这样的代码称为设备驱动程序(device driver),它一般由设备的制造商编写并随同设备ー起交付。

与设备无关的 I/O 软件

image-20220327150429492

设备驱动程序的统一接口

image-20220327150646082

这种设计的工作方式如下。对于每ー种设备类型,例如磁盘或打印机,操作系统定义ー组驱动程序
必须支持的函数。对于磁盘而言,这些函数自然地包含读和写,除此之外还包含开启和关闭电源、格式
化以及其他与磁盘有关的事情。驱动程序通常包含ー张表格,这张表格具有针对这些函数指向驱动程序
自身的指针。当驱动程序装载时,操作系统记录下这张函数指针表的地址,所以当操作系统需要调用ー
个函数时,它可以通过这张表格发出间接调用。

缓冲!

image-20220327150723212

  • 无缓冲输入 (基本没有这种)

    • 对于每个到来的字符,都必须启动用户进程。对于短暂的数据流量让ー个进程运行许多次效率会很低,所以这不是一个良好的设计。
  • 用户空间中的缓冲

    • 此处,用户进程在用户空间中提供了一个包含n个字符的缓冲区,并且执行读入n个字符的读操作。中断服务过程负责将到来的字符放入该缓冲区中直到缓冲区填满,然后喚醒用户进程。
    • 这ー方案比前ー种方案的效率要高很多
    • 但是它也有一个缺点:当一个字符到来时,如果缓冲区被分页而调出了内存会出现什么问题呢?
      • 解决方法是将缓冲区锁定在内存中,但是如果许多进程都在内存中锁定页面,那么可用页面池就会收缩并且系统性能将下降。
  • 内核缓冲空间中的缓冲复制到用户空间

    • 在内核空间中创建一个缓冲区并且让中断处理程序将字符放到这个缓冲区中,如图5∙15c所示。当该缓冲区被填满的时候,将包含用户缓冲区的页面调入内存(如果需要的话),并且在一次操作中将内核缓冲区的内容复制到用户缓冲区中。这一方法的效率要高很多。
  • 内核空间中的双缓冲

    • 然而,即使这种改进的方案也面临ー个问题:正当包含用户缓冲区的页面从磁盘调入内存的时候有新的字符到来,这样会发生什么事情?因为缓冲区已满,所以没有地方放置这些新来的字符。
    • ー种解决问题的方法是使用第二个内核缓冲区。第一个缓冲区填满之后,在它被清空之前,使用第二个缓冲区,如图5∙15d所示。当第二个缓冲区填满时,就可以将它复制给用户(假设用户已经请求它)。当第二个缓冲区正在复制到用户空间的时候,第一个缓冲区可以用来接收新的字符。以这样的方法,两个缓冲区轮流使用:当ー个缓冲区正在被复制到用户空间的时候,另ー个缓冲区正在收集新的输入。像这样的缓冲模式称为双缓冲(double buffering)。
  • 缓冲的另ー种常用形式是循环缓冲区(circular buffer)。

    • 它由一个内存区域和两个指针组成。**ー个指针指向下一个空闲的字,新的数据可以放置到此处。另ー个指针指向缓冲区中数据的第一个字,该字尚未被取走。**在许多情况下,当添加新的数据时(例如刚刚从网络到来),硬件将推进第一个指针,而操作系统在取走并处理数据时推进第二个指针。两个指针都是环绕的,当它们到达顶部时将回到底部。

缓冲是ー种广泛采用的技术,但是它也有不利的方面。如果数据被缓冲太多次,性能就会降低。例如,考虑图5-16中的网络。其中,一
个用户执行了一个系统调用向网络写数据。内核将数据包复制到ー个内核缓冲区中,从而立即使用户进程得以继续进行(第1步)。在此刻,用户程序可以重用缓冲区。

image-20220327153443360

用户空间的I/O软件

并非所有的用户层i/o软件都是由库过程组成的。另ー个重要的类别是假脱机系统。假脱机(spooling)是多道程序设计系统中处理独占I/O设备的ー种方法。考虑ー种典型的假脱机设备:打印机。 尽管在技术上可以十分容易地让任何用户进程打开表示该打印机的字符特殊文件,但是假如一个进程打开它,然后很长时间不使用,则其他进程都无法打印。

**ー种方法是创建一个特殊进程,称为守护进程(daemon),以及ー个特殊目录,称为假脱机目录(spooling directory)。 ー个进程要打印ー个文件时,首先生成要打印的整个文件,并且将其放在假脱机目录下。由守护进程打印该目录下的文件,该进程是允许使用打印机特殊文件的唯一进程。**通过保护特殊文件来防止用户直接使用,可以解决某些进程不必要地长期空占打印机的问题。

假脱机不仅仅用于打印机,还可以在其他情况下使用。例如,通过网络传输文件常常使用ー个网络守护进程。要发送ー个文件到某个地方,用户可以将该文件放在ー个网络假脱机目录下。稍后,由网络守护进程将其取出并且发送出去。

总结

图5 - 17对I/O系统进行了总结,给出了所有层次以及每ー层的主要功能。从底部开始,这些层是硬件、中断处理程序、设备驱动程序、与设
备无关的软件,最后是用户进程。

图5 - 17中的箭头表明了控制流。例如, 当ー个用户程序试图从ー个文件中读一个请求块时,操作系统被调用以实现这ー请求。与设备无关的软件在缓冲区高速缓存中査 找有无要读的块。如果需要的块不在其中,则调用设备驱动程序,向硬件发出ー个请求,让它从磁盘中获取该块。然后,进程被阻塞直到磁盘操作完成并且数据在调用者的缓冲区中安全可用。

当磁盘操作完成时,硬件产生一个中断。中断处理程序就会运行,它要查明发生了什么事情,也就是说此刻需要关注哪个设备。然后,中断处理程序从设备提取状态信息,喚醒休眠的进程以结束此次I/O请求,并且让用户进程继续运行。

image-20220327153710771

  • 2
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值