epoll是linux特有的IO复用函数。
把用户关心的文件描述符上的事件放在内核里的一个事件表里,从而无须像select和poll
那样每次调用都要重复传入文件描述符或事件集。
#include<sys/epoll.h>
int epoll_create(int size).
size参数现在并不起作用,只是给内核一个提示:告诉它事件表需要多大。
该函数返回的文件描述符将用作其他所有epoll系统调用的第一个参数
以指定要访问的内核事件表。
#include<sys/epoll.h>
int epoll_ctl(int epfd,int op,int fd,struct epoll_event* event)
epoll支持的事件类型和poll基本相同,表示epoll的事件类型的宏是在poll对应的宏前加上E,
但是epoll有两个额外的事件类型EPOLLET和EPOLLONESHOT,
这个函数成功时返回0.失败时返回-1并且设置errno
int epoll_wait(int epfd,struct epoll_event* events, int maxevents, int timeout)
这个函数成功时返回就绪的文件描述符的个数,失败则返回-1并且设置errno
maxevents指定最多监听多少个事件,必须大于0
timeout参数同poll参数的timeout参数
epoll_wait函数如果检测到事件,就将所有就绪的事件从内核表中复制到第二个参数指向的数组中,
epoll对文件描述符有两种模式LT电平触发和ET边沿触发 默认是LT模式 ,
当往epoll内核事件表中注册EPOLLET事件时会以ET模式来操作该文件描述符。
即使我们使用边沿触发,仍然可能多次触发事件,
在某些特定情况下,可能会需要用到EPOLLONESHOT 这个事件。
对于注册了这个事件的文件描述符,操作系统最多触发其上注册的一个可读,可写,或者异常事件,
且只触发一次,所以在不需要继续使用这个socket的情况下,需要重置这个socket,否则永远不会再接收
到这个socket的有关事件。
~~~epoll的工作原理
内核监测到就绪的文件描述符时,将触发回调函数,回调函数就将该文件描述符上对应的事件插入内核就绪事件队列,内核最后在适当的时机将该就绪事件队列中的内容拷贝到用户空间。