IO
IO:数据的读取或写入操作。
通过完整的IO分两个阶段: 用户进程空间到内核空间的转换; 内核空间到设备空间的转换。因为在Linux系统下,进程无法直接操作IO设备,必须通过内核协助。除此之外内核为每个IO设备提供缓冲区,以提高IO效率。
任何的IO都分为两个步骤:等和数据拷贝。即等待用户进程请求数据到达内核空间,从内核空间将数据拷贝到用户进程空间。
五种IO模型:
同步IO:
- 阻塞IO
- 非阻塞IO
- 信号驱动IO
- IO多路转接
异步IO
同步IO:用户进程需要从设备取数据,发送IO调用后,经过内核缓冲区同步,待数据准备好后,从内核空间复制数据到用户进程空间。而在拷贝数据期间,进程是阻塞的,直到IO操作完成。
异步IO:用户发出IO调用后,内核在数据准备好后直接将其复制到进程空间,此过程进程不会阻塞。
所以同步与异步区别就是:调用者在数据到来时,是否处于阻塞等待状态。
阻塞IO
在内核数据准备好之前,系统调用会一直阻塞。
特征:
- 进程阻塞挂起不消耗CPU资源,及时响应每个操作;
- 实现简单
- 适用于并发量小且及时处理的应用开发。由于每次为每个请求分配一个进程去处理,增加系统开销,所以适合并发量小的。
非阻塞IO
若内核中请求数据未准备好,系统调用直接返回,并返回EWOULDBLOCK错误码。
特征:
- 进程轮询调用,消耗CPU;
- 实现难度较低;
- 适用于并发量小且不需要及时响应的应用开发。
信号驱动IO
内核将数据准备好时,会通过SIGIO信号通知应用程序进行IO。
特点:回调机制,实现难度大。
IO多路转接
其过程类似于阻塞IO,但它能同时等待多个文件描述符就绪状态。
特征:
- 可以处理多个进程IO阻塞问题,性能好;
- 适用于高并发的应用开发:一个进程响应多个请求。
异步IO
有内核在数据拷贝完成时,通知应用进程
与信号驱动不同的是:信号驱动是通知进程可以开始拷贝数据。而异步IO是内核将整个IO处理完后,通知进程结果,若IO成功则进程直接获取数据。
特点:
- 不阻塞,数据直接交给进程;
- 实现难度大;
- 适合高性能高并发应用开发。