网络IO的阻塞&非阻塞&同步&异步,五种IO模型

网络IO接口调用分为两个阶段–数据准备和数据读写

1.数据准备 (操作系统方面)
ssize recv(int sockfd,void *buf,size_t len,int flags)\

//flags默认为0

当文件描述符为非阻塞时,recv的返回值 size:

-1&&errno == EAGAIN 如果只是-1,那么是系统发生错误,或者链接异常断开等。如果再继续errno==EAGAIN,则为文件描述符为非阻塞并且没有数据到来

0 网络对端关闭了链接

size>0 数据的字节

阻塞:调用IO方法的线程进入阻塞状态

非阻塞:不会改变线程状态,通过返回值判断

2.数据读写 (应用程序方面)

数据读写分同步和异步

PS:平时我们说的同步异步一般都是指网络IO方面的同步异步,和几个同事几件合作的同步异步是不一样的。

同步

自己定义一个buf,应用程序不断从操作系统的TCP接收缓冲区搬运数据,期间不可以进行其它操作(如果文件描述符为堵塞状态,则一直卡着)

异步

应用程序将sockfd,buf,以及通知方式(一般是回调函数或者信号sigio)告诉操作系统,让操作系统帮忙搬运,等操作系统完成后,操作系统再用应用程序提供的通知方式,来通知应用程序。在搬运期间,应用程序可以做自己的事情

linux提供的异步函数:

aio_read

aio_write

epoll_wait是同步方式

PS:陈硕大神的原话:在处理IO的时候,阻塞和非阻塞都是同步IO,只有使用了特殊的API才是异步IO。

作为面试者,如何阐述阻塞,非阻塞,同步,异步

PS:在将理论时,尽量也往实际上靠

一次网络IO接口调用包含两个阶段:数据准备和数据读写阶段。数据准备阶段,根据系统IO操作的就绪状态,即内核相应的sockfd对应的TCP接收缓冲区是否有数据可读,如果IO工作在阻塞模式下,那么调用例如recv函数时,recv会阻塞当前这个线程;如果IO工作在非阻塞模式下,调用recv会立刻返回,根据返回值来判断非阻塞的状态,如果单纯为-1则是链接异常中断等原因,如果同时errno等于ENGAIN,则表示当前IO工作于非阻塞模式,并且TCP接收缓冲区无数据。当数据就绪后,进入数据读写阶段。如果是同步,则应用程序调用函数去搬运操作系统的TCP接收缓冲区的数据,花费的是应用程序的时间。如果是异步,应用程序将sockfd,以及数据搬运的目的地buf,还有通知方式,一般是回调或者信号,告诉操作系统,让操作系统帮忙搬运,期间应用程序可以进行其它操作。等操作程序搬运完后,再通知应用程序。项目开发时,也会说到业务层面的并发的同步和异步。此时同步就比如说,A对B的业务感兴趣,A会等待B完成业务。异步则是,A告诉B我对你的业务感兴趣,并且把通知方式告诉你,等你完成业务后,再用我告诉你的通知方式来通知我。

五种IO模型

阻塞 blocking

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-R5rB09Yn-1642561042350)(C:\Users\chenzhengchang\AppData\Roaming\Typora\typora-user-images\image-20220118171509523.png)]

非阻塞 non-blocking

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-VoCnpXiR-1642560964685)(C:\Users\chenzhengchang\AppData\Roaming\Typora\typora-user-images\image-20220118171519954.png)]

IO复用 IO multiplexing

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-J8U5dGba-1642560964686)(C:\Users\chenzhengchang\AppData\Roaming\Typora\typora-user-images\image-20220118171534811.png)]

信号驱动 signal-driven

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-o1NTsulP-1642560964686)(C:\Users\chenzhengchang\AppData\Roaming\Typora\typora-user-images\image-20220118171552686.png)]

异步 asynchronous

在这里插入图片描述

说明:
  • IO复用,使得不用不断创建进程就可以处理多个连接,可以一个进程处理多个服务。

  • 信号驱动,内核在第一个阶段是异步,在第二个阶段是同步;与非阻塞IO的区别在于它提供了消息通知机制,不需 要用户进程不断的轮询检查,减少了系统API的调用次数,提高了效率。

  • 异步,第一和第二步(数据拷贝就是在第二步)都是异步,应用程序将任务交给操作系统去完成,完成后再通知应用程序。

典型的异步非阻塞状态,Node.js采用的网络IO模型。

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值