IO 多路复用 select vs pool vs epool

2020-07-02  本文已影响0人  三石_5f43

IO 多路复用 select vs pool vs epool

前言

IO多路复用(IO Multiplexing )出现的背景

io 多路复用应运而生。

IO Multiplexing 模式的支持

实现思想是: 采用内核机制来轮询一组文件描述符,在linux 中有以下三种支持。

它们的实现思路一样,都是创建一组标志读(read) 写(write)的文件描述符,并告知内核,并用一个线程阻塞一个函数调用,直到一个文件描述符的操作(read/write)可用。

select() 系统调用

select () 指令

int select(int nfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds, struct timeval *timeout);

对一个select 指令的调用会被阻塞,直到给定的文件描述符执行IO 操作,或则在指定的过期时间内失效,被监视的文件描述符分为三组。

select 没有监察到上述事件就会返回null。成功返回则修改每个集合。使其仅包含已经准备就绪的文件描述符。

因为需要告知 select() 最大的文件描述符编号,这是fd_sets 的内部实现。

【在fd_set 中 一个fd(file description) 文件描述占用 1bit, fd_set 是length 为32 的整数数组,(32 x 4byte x 8bit = 1024bit) ,假设存在 8个文件描述符,最大的文件描述符值为1000, 那么将会在0 ~ 1000 中找到监视的文件描述符】

这也是一个弊端,因为需要在每次轮询迭代时重新构建文件描述符集。

select () 总结

pool() 系统调用

int poll (struct pollfd *fds, unsigned int nfds, int timeout);

与select () 采用3个 基于标记位的文件描述符集不同,pool 采用一个pollfd 结构,原型更简单。

struct pollfd {
      int fd;
      short events; 
      short revents;
};

为每一个文件描述符构建一个 pollfd 类型的兑对象,并填充请求(request)事件,然后轮询返回响应,检查返回事件(revents)字段。

与selelct() 类似,需要检测每一个pollfd 对象去看它的文件描述符是否已准备好,,但是不需要在每次轮询时重新构建文件描述符集。

epool() 系统调用

pool() ,select() 工作时,我们需要在用户空间管理任何事情,在每次调用发送 文件描述符集时陷入阻塞等待。添加另外的socket , 我们需要把它加入到 集合中并再一次调用 pool() select()。

epool() 帮助我们在内核中创建和管理上下文,可以分为以下三步:

pool() vs select()

epool vs pool vs select

上一篇下一篇

猜你喜欢

热点阅读