Rust 设备 I/O
本章主要讲:
- Linux 的设备 I/O 基础
- 带缓冲的读写
- 使用标准输入输出
- 函数式编程: 链式和迭代式 I/O
- 错误处理和返回值
- 编写一个程序获取已连接 USB 设备的信息
理解设备 I/O
操作系统除了管理 CPU 和内存外, 还需要负责对系统中其他硬件的管理, 比如键盘鼠标, 硬盘, 显卡声卡网卡, 其他的 USB 设备等.
操作系统通过设备驱动来进行设备 I/O, 通过设备驱动来和设备进行交互.
什么是设备驱动?
设备驱动是一些加载到内核的共享库, 包含用于控制底层硬件的相关功能. 它们利用总线或其他的通信渠道和连接到系统中的硬件进行通信. 设备驱动根据设备的不同, 设备类型的不同以及操作系统的不同都各有不同.
设备驱动将硬件有关的细节都抽象出去了, 从而方便上层软件使用硬件. 比如磁盘驱动可能会将读写请求中的 block number 转换为磁道/扇区进行读写, 并控制设备的初始化, 判断设备是否正在被使用, 处理设备中断信号, 实现硬件协议等.
操作系统(特指内核)从用户空间的程序收到设备控制或访问的系统调用, 然后使用特定的设备驱动对设备进行物理层面的访问和控制.
Rust 程序使用标准库的图示如下:
在 Unix 系统中有"万物皆文件"的理念, 放到设备 I/O 这里也适用. 即外部设备的访问也会通过 open
, close
, read
和 write
这些系统调用去访问, 设备被抽象为块设备, 字符设备等. 由于存在操作系统和设备驱动提供的抽象, 意味着用户空间中的开发者可以在"设备文件"这个抽象层上对设备进行访问. 并且 Rust 标准库还提供了一层设备无关的软件抽象层, 更便于开发了.