同步阻塞IO模型下,网络IO的交互流程。
- 客户端向服务器端申请建立连接
- 服务端同意建立连接
- 服务端调用accept,接受客户端连接,生成文件描述符fd
- 客户端发送消息给服务器
- 网卡接收到消息,写入连接的buffer中
- 然后调用IO中断,将消息通过IO中断写入内核中对应的fd的buffer中,完成内核态的交互
- 服务器端效用read函数,通过软中断(80中断)调用内核函数,读取fd buffer中的数据。如果fd的buffer中没有数据,将会阻塞read直到有数据进来。
同步非阻塞IO模型下,网络IO的交互流程
- 客户端向服务器端申请建立连接
- 服务端同意建立连接
- 服务端调用accept,接受客户端连接,生成文件描述符fd,储存建立连接的fd。
- 客户端发送消息给服务器
- 网卡接收到消息,写入连接的buffer中
- 然后调用IO中断,将消息通过IO中断写入内核中对应的fd的buffer中,完成内核态的交互
- 服务器端遍历建立连接的fd,调用read函数,通过软中断(80中断)调用内核函数,读取fd buffer中的数据。如果fd的buffer中没有数据,返回0,继续read下一个fd。
同步非阻塞IO模型下调用内核SELECT/POLL多路复用,网络IO的交互流程
- 服务端启动端口监听,打开一个多路复用器selector,将serversocket注册到selector中,并监听accept事件。
- 当selector.select()多路复用器中的keys大于0时,调用selector.selectedKeys()获取选中的keys,这个keys,在select和poll中是维护的数组,select一次只能查看1024个key的状态,poll没有限制,并且在内核态依然是O(N)的时间复杂度;在epoll中维护的是红黑树+链表时间复杂度是O(1)-O(lgn)。
- 客户端向服务器端申请建立连接
- 服务端获取到key,判断他是accetable的状态,获取该链接并接收,生成新的FD,将这个FD注册到多路复用器中并监听read事件。
- 客户端发送消息给服务器
- 网卡接收到消息,写入连接的buffer中
- 然后调用IO中断,将消息通过IO中断写入内核中对应的fd的buffer中,完成内核态的交互
- 多路复用器监听到fd状态变化,服务端不断轮询获取变化的fd,多路复用器一次性将所有可以触发事件的FD返回给服务端。
- 服务器端获取到fd后进行响应的accept,read,write操作。