epoll的EPOLLIN和EPOLLOU为什么不能同时关联 http://laokaddk.blog.51cto.com/368606/791945
epoll使用总结 http://laokaddk.blog.51cto.com/368606/617497
epoll学习:思考一种高性能的服务器处理框架 http://laokaddk.blog.51cto.com/368606/607231
epoll学习笔记 http://laokaddk.blog.51cto.com/368606/607017
简单学习了一下epoll,之前也用过,这次又看了看,收获如下:
两种实现模式(在http://laokaddk.blog.51cto.com/368606/791945中都有提到):同一个线程 和 不同线程;
顺便了解了一下惊群现象,如果用accept阻塞的方式就不存在惊群现象了,在不同线程中通过epoll_wait来出发accept行为的nginx的解决方法是通过进程里原子的修改寄存器a来做到进程间互斥的。
在不同线程模式下:listenfd需设置为非阻塞,注册EPOLLIN就可以了,触发时调用accept,有没有连接都会立刻返回;
在同一个线程模式下:listenfd为阻塞模式,不注册epoll,阻塞while调用accept即可;
ET触发只支持非阻塞模式,这里针对的fd是accept接收到的然后epoll_add了的那些fds,原因是:因为ET触发需要处理函数一直处理完所有in/out数据,比如read数据,如果read到的字节数小于预先准备读入的字节数,那么就可以认为读完了;如果是非阻塞模式,那么read会一直阻塞在那里。
epollfd不需要设置阻塞、非阻塞。
一般都用LT触发,不论哪种实现模式,EPOLLIN和EPOLLOUT都不同时设定,都是不断切换来做的。
客户端close掉socket时,会唤醒服务端epoll_wait;
对于epoll_wait而言,针对一个fd只存在唤醒与被唤醒,至于是EPOLLIN还是EPOLLOUT,取决于你当初epoll_add时的设定,因此如果你epoll_add时设定了EPOLLIN|EPOLLOUT,那么当EPOLLIN发生时(内核里当然是可以区分EPOLLIN和EPOLLOUT的),你收到的fd上的事件依然是EPOLLIN|EPOLLOUT。
http://my.oschina.net/costaxu/blog/127394
http://blog.csdn.net/guomsh/article/details/8484222
http://blog.csdn.net/guomsh/article/details/8478209
http://blog.csdn.net/ctthuangcheng/article/details/8596818
http://blog.yunn.io/archives/114/