什么是IO

学术的说 I/O 是信息处理系统(计算机)与外界(人或信息处理系统)间的通信。如计算机,即 CPU 访问任何寄存器和 Cache 等封装以外的数据资源都可当成 I/O ,包括且不限于内存,磁盘,显卡。

软件开发中的 I/O 则常指磁盘、网络 IO

Unix 系统下,不论是标准输入还是借助套接字接受网络输入,都有两个步骤:

  • 等待数据准备好(Waiting for the data to be ready)
  • 从内核向进程复制数据(Copying the data from the kernel to the process)

Linux IO 读写方式

用户进程需要通过 系统调用 转为内核态,才能在 CPU 上运行,进而访问底层如磁盘等硬件设备。其中磁盘等 I/O 设备的控制器中有寄存器,负责与 CPU 进行通信。

那么,I/O 设备与 CPU 能用哪些方法进行通信呢?

  • 中断
  • DMA

中断

在 DMA 技术出现之前,应用程序与磁盘之间的 I/O 操作都是通过 CPU 的中断完成的。每次用户进程读取磁盘数据时,都需要 CPU 中断,然后发起 I/O 请求等待数据读取和拷贝完成,每次的 I/O 中断都导致 CPU 的上下文切换。

使用 I/O 中断方式读取数据步骤:

  1. 用户进程向 CPU 发起 read 系统调用读取数据,由用户态切换为内核态,然后一直阻塞等待数据的返回
  2. CPU 在接收到指令以后对磁盘发起 I/O 请求,将磁盘数据先放入磁盘控制器缓冲区
  3. 数据准备完成以后,磁盘向 CPU 发起 I/O 中断
  4. CPU 收到 I/O 中断以后将磁盘缓冲区中的数据拷贝到内核缓冲区,然后再从内核缓冲区拷贝到用户缓冲区
  5. 用户进程由内核态切换回用户态,解除阻塞状态,然后等待 CPU 的下一个执行时间钟

DMA

DMA(Direct Memory Access)即直接存储器存取,是指外部设备不通过 CPU 而直接与系统内存交换数据的接口技术。

要把外设的数据读入内存或把内存的数据传送到外设,一般都要通过 CPU 控制完成,如 CPU 程序查询或中断方式。

利用中断进行数据传送,可以大大提高 CPU 的利用率。但是采用中断传送有它的缺点,对于一个高速 I/O 设备以及批量交换数据的情况,如果中断 I/O 操作带来的将是性能的损耗。

对于这种类型的操作如果可以找一个第三方来执行数据拷贝而 I/O 还继续执行数据读取主流程任务是最好的。DMA 在外设与内存间直接进行数据交换,而不通过 CPU,这样数据传送的速度就取决于存储器和外设的工作速度。

DMA 机制中存在一个DMA控制器的角色,DMA控制器(DMAC),向CPU提出接管总线控制权的总线请求,CPU收到该信号后,在当前的总线周期结束后,会按DMA信号的优先级和提出DMA请求的先后顺序响应DMA信号。

DMA 控制器必须有以下功能:

  1. 能向 CPU 发出系统保持(HOLD)信号,提出总线接管请求;
  2. 当 CPU 发出允许接管信号后,负责对总线的控制,进入 DMA 方式;
  3. 能对存储器寻址及能修改地址指针,实现对内存的读写操作;
  4. 能决定本次 DMA 传送的字节数,判断 DMA 传送是否结束;
  5. 发出 DMA 结束信号,使 CPU 恢复正常工作状态。

有了DMA之后的数据读取方式:

CPU 从繁重的 I/O 操作中解脱,数据读取操作的流程如下:

  1. 用户进程向 CPU 发起 read 系统调用读取数据,由用户态切换为内核态,然后一直阻塞等待数据的返回;
  2. CPU 在接收到指令以后对 DMA 磁盘控制器发起调度指令;
  3. DMA 磁盘控制器对磁盘发起 I/O 请求,将磁盘数据先放入磁盘控制器缓冲区,CPU 全程不参与此过程;
  4. 数据读取完成后,DMA 磁盘控制器会接受到磁盘的通知,将数据从磁盘控制器缓冲区拷贝到内核缓冲区;
  5. DMA 磁盘控制器向 CPU 发出数据读完的信号,由 CPU 负责将数据从内核缓冲区拷贝到用户缓冲区;
  6. 用户进程由内核态切换回用户态,解除阻塞状态,然后等待 CPU 的下一个执行时间钟。

参考文章:

评论