Linux五种I/O模型

I/O阶段

典型的一次I/O分为两个阶段:数据就绪数据读写

  1. 数据就绪:根据系统I/O操作的就绪状态
  • 阻塞
  • 非阻塞

区别在于:进程发起系统调用后,是会被挂起直到收到数据后再返回,还是立即返回成功或错误。

  1. 数据读写:根据应用程序和内核的交互方式
  • 同步
  • 异步

区别在于:将数据从内核复制到用户空间时,用户进程是否会阻塞(需要用户进程来完成)

Linux五种I/O模型

阻塞I/O (blocking)

调用者调用了某个函数,等待这个函数返回,期间什么也不做,不停的去检查这个函数有无返回,必须有返回后才能进行下一步动作

非阻塞I/O (NIO)

非阻塞等待,每隔一段时间就去检测IO事件是否就绪。没有就绪就可以做其它事。非阻塞I/O执行系统调用总是立即返回,不管事件是否已经发生,若事件没有发生,则返回-1,此时可以根据errno区分这两种情况,对于accept,recv和send,事件未发生时,errno通常被设置成EAGAIN。

I/O复用 (IO multiplexing)

Linux用select/poll/epoll函数实现IO复用模型,这些函数也会使进程阻塞,但和阻塞IO所不同的是这些函数可以同时阻塞多个IO操作。而且可以同时对多个读操作,写操作的IO函数进行检测,直到有数据可读或可写时,才真正调用IO操作函数。

信号驱动I/O (signal-driven)

Linux用套接口进行信号驱动I/O,安装一个信号处理程序,进程继续运行并不阻塞,当I/O事件就绪,进程收到SIGIO信号,然后处理IO事件。

异步I/O (asynchronous)

Linux中,可以调用aio_read()函数告诉内核该描述符缓冲区指针和缓冲区的大小,文件偏移及通知的方式,然后立即返回该函数调用状态(函数调用成功与否)。当内核将数据拷贝到缓冲区后,再通知应用程序。

五种I/O模型的对比

  • 同步I/O模型要求用户代码自行执行I/O操作(将数据从内核缓冲区读入用户缓冲区,或将数据从用户缓冲区写入内核缓冲区);
  • 异步I/O机制则由内核来执行I/O操作(数据在内核缓冲区和用户缓冲区之间的移动是由内核在”后台完成的”)。
  • 同步I/O向应用程序通知的是I/O就绪事件
  • 异步I/O向应用程序通知的是I/O完成事件
posted @ 2022-11-11 16:29  yytarget  阅读(28)  评论(0编辑  收藏  举报