C++ / a working model

140 / 163   ·   C11   ·   约 8 分钟

I/O 设备

先记住这句话

本章讲解操作系统如何将输入输出设备融入整体系统,涵盖层次化总线架构、设备对外接口与内部实现、基于寄存器的轮询协议,以及用中断实现计算与I/O重叠的方法。

本篇内容
  1. 层次化系统架构
  2. 典型设备的组成
  3. 轮询式交互协议
  4. 用中断降低处理器开销
  5. 运行示例
  6. 动手练习

官方章节 PDF

层次化系统架构

CPU 通过专用高速互连紧挨主存。图形卡等对延迟敏感的部件挂在通用 I/O 总线(如 PCI Express)上。磁盘、键盘、鼠标则落在更外围、更便宜的总线(SATA、USB)上。物理规律决定了越快的总线必须越短,同时高速互连的工程成本也更高,因此设计师把慢速、数量多的设备放到较远的层次,既满足性能又控制成本。

典型设备的组成

设备对外呈现一组寄存器:状态寄存器供软件查询忙闲,命令寄存器接收操作码,数据寄存器用于搬入或搬出字节。内部则是微控制器、SRAM/DRAM 以及专用电路;复杂设备甚至运行数万行固件来实现 RAID 或协议处理。操作系统只需遵守公开接口,不必知道芯片内部细节。

轮询式交互协议

软件反复读状态寄存器直到设备空闲,再把数据写入数据寄存器(由 CPU 亲自搬运,称为编程 I/O),接着把命令写入命令寄存器启动硬件,最后再次轮询直到完成。协议简单可靠,但两次忙等待会让处理器空转,尤其当设备本身很慢时浪费巨大。

用中断降低处理器开销

发出请求后操作系统立刻让发起进程睡眠并切换到其他可运行任务。设备完成后拉高硬件中断线,处理器跳进预先登记的中断服务例程,读取结果或错误码,再唤醒等待者。计算与 I/O 因此可以真正重叠,处理器不再空转。

常见误区

  • 在慢速设备上持续轮询会让 CPU 利用率接近零。
  • 命令完成后忘记检查状态寄存器中的错误位会导致静默数据损坏。
  • 大块数据仍用编程 I/O 搬运会把处理器变成搬运工,应改用 DMA。

运行一个例子

最低标准 C11 · 完整程序 · 下载 .c

#include <stdio.h>

int main(void) {
    printf("=== Simulating Canonical I/O Protocol ===\n");
    printf("Step 1: OS polls STATUS register until not BUSY\n");
    printf("  (in reality this loop wastes CPU)\n");
    printf("Step 2: OS writes data to DATA register (PIO)\n");
    printf("Step 3: OS writes command to COMMAND register\n");
    printf("Step 4: OS polls STATUS until complete\n");
    printf("I/O done. Using interrupts would overlap this wait with other computation.\n");
    return 0;
}

在本地编译

gcc -std=c11 -Wall -Wextra -Wpedantic -Werror ostep-36-io-devices.c -o example && ./example

预期结果

=== Simulating Canonical I/O Protocol ===
Step 1: OS polls STATUS register until not BUSY
  (in reality this loop wastes CPU)
Step 2: OS writes data to DATA register (PIO)
Step 3: OS writes command to COMMAND register
Step 4: OS polls STATUS until complete
I/O done. Using interrupts would overlap this wait with other computation.

CHECK YOUR UNDERSTANDING

合上答案,试着解释。

为什么系统不把所有设备直接接在高速内存总线上,而要采用层次化总线?

查看参考答案

高速互连受电气特性限制必须很短,设计成本也高。把低性能设备放到更长、更便宜的外围总线上,既能连接大量慢速部件,又不会拖累内存子系统。

继续查证

标准草案与官方章节会更新;版本标记只说明示例最低要求。

回到目录