阻塞IO 非阻塞IO IO多路复用 异步IO 区别

Linux中五种IO模型:阻塞IO模型、非阻塞IO模型、IO复用模型、信号驱动IO模型、异步IO模型

linux的内核将所有外部设备都看作一个文件来操作,针对一个文件的读写会调用内核提供的系统命令,返回一个file description(df,文件描述符)。图片截取自《Netty权威指南》

UNIX提供了5种IO模型:

         ​1、阻塞式IO:以socket套接字为例,在进程空间中调用recvfrom,其系统调用直到数据包到达且被复制到应用进程的缓冲区中或发生错误时才返回,在此期间一直会等待,进程从调用recvfrom开始到返回的整段时间内都是被阻塞的。

         ​2、非阻塞IO:recvfrom从应用层到内核的时候,如果该缓冲区没有数据的话,就直接返回一个ewouldblock错误,一般都对非阻塞IO进行轮询检查这个状态,看内核是不是有数据到来。

         ​3、IO复用:linux提供了select/poll,进程通过将一个或多个fd传递给select或poll系统调用,阻塞在select上,这样select/poll可以帮助我们侦测多个fd是否处于就绪状态。select/poll是顺序扫描fd是否就绪,而且支持的fd数量有限,因此它的使用受到了一些制约。linux还提供了一个epoll系统调用,epoll使用基于事件驱动的方式代替顺序扫描,因此性能更高。当有fd就绪时,立即回调函数rollback。

        ​4、信号驱动IO:首先开启套接字信号驱动IO功能,并通过系统调用sigaction执行一个信号处理函数(此系统调用立即返回,进程继续工作,它是非阻塞的)。当数据准备就绪时,就为该进程生成一个sigio信号,通过信号回调通知应用程序调用recvfrom来读取数据,并通知主循环函数处理函数。

        ​5、异步IO:告知内核启动某个操作,并让内核在整个操作完成后(包括将数据从内核复制到用户自己的缓冲区)通知我们。这种模型与信号驱动模型的主要区别是:信号驱动模型由内核通知我们何时可以开始一个IO操作;异步IO模型由内核通知我们IO操作何时已经完成。 ​ ​ ​ ​

 

​其实我个人理解整个io的过程可以大概分为两个阶段: ​

1、阶段一是内核态对数据报的准备阶段。 ​

2、阶段二是将数据从内核态拷贝到用户空间。

​ ​阻塞io在两个阶段都阻塞。

​ ​非阻塞io在阶段一通过进程反复调用revfrom等待返回成功指令,第二阶段为阻塞。

​ ​io复用通过select/poll epoll,将传递过来的df文件描述符的状态进行检测,其是否为就绪状态。 ​select为O(n)的轮询复杂度,有最大连接数限制。 ​poll也是O(n)复杂度,但因为它基于链表的实现,没有最大连接数限制。epoll将每个流发生的io事件对我们进行通知。实际上是事件驱动,每个事件关联fd。使复杂度降低到O(n)。 ​

信号驱动io的第一阶段建立sigio的信号处理程序,以及sigio的回传,第二阶段为阻塞。

​ ​异步io在第一阶段和第二阶段的工作都完成后,由内核向应用进程进行通知。 ​

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值