目录
1 IO多路复用概述
IO多路复用模型是一类IO模型的统称,在这一类模型下有不同的系统函数来帮助我们解决相应的问题有select模型,poll模型,epoll模型等等。
1.1 IO多路复用模型能为我们解决那些问题:
阻塞IO和非阻塞IO的共同问题:
应用程序不知道socket什么时候有数据了,所以当应用程序调用了read等系统函数在没有数据到来时,阻塞IO选择等待,非阻塞IO选择直接返回然后下次轮询能不能有一种方式知道socket中数据是否准备好了,准备好了再调用read等函数去读取数据,否则不发起读取数据的操作!!!
这就是IO多路复用为我们解决的问题
检测socket数据状态,有效减少无意义的系统调用。
1.2 IO多路复用模型下的IO模型分类:
IO多路复用提供了几种不同模型的不同系统调用函数可以用来检测socket的可读写状态
• select 平台一致性会好一些
• poll
• epoll 模型在linux上是比较成熟的,windows上是不行的
• kqueue (K Q)
2,select模型的调用流程
2.1 select模型调用流程 总结:
1,服务端首先创建socket套接字返回socker的标识
2,调用bind方法将我们的socket与应用程序9999端口进行绑定,表示该scoket属于9999端口的可指定
3,开启监听,一旦开启监听客户端就可以连接我们的服务端select模型为例,目前我们的socket服务端只有一个,因此我们调用select函数传入服务端的socker标识,检测该socker是否有链接进来,但是我们目前的socker 是阻塞的,
情况一,如果该socker没有任何链接进来,就说明没有任何的客户端想要跟我们建立链接,这时候我们的应用程序可以阻塞在这,因为当前应用程序现在没有任务可执行,当然我们也可以设置一个阻塞的超时时间,使用命令
查看man select查看函数文档说明得知,最后一个参数可以设置阻塞的时间
大体意思是让内核帮我们去检测,当前的socker是否可读可写可写的意思 是当我们想往一个socker中写数据时,但是该socker的内核缓冲区数据已经满了这时候就不能往该socker中写数据了,这就是检验可写的例子。
情况二:
该socker有链接进来,这时候我们就可以调用accept()函数来接收这个链接,并创建该客户端的socker接下来我们就可以继续调用select函数()把服务端的socker和客户端的socker都传过去,让select继续帮我们去检测,服务端的socker是否有新的连接过来,客户端的socker是否有数据过来如果客户端的socker有数据进来了,我们这时候调用read 函数去获取数据即可
然后继续调用select函数循环往复,这时候发现服务端的socker有新的连接进来,客户端的socker又有新的数据进来,我们就可以调用read获取客户端的数据进行处理,然后调用服务端的accept()来接收新的链接,并创建新的连接的客户端socker继续调用select函数传入服务端的socker,跟客户端1的socker和客户端2的socker继续让select函数为我们检测,循环往复。