Chinaunix首页 | 论坛 | 博客
  • 博客访问: 471823
  • 博文数量: 135
  • 博客积分: 1860
  • 博客等级: 上尉
  • 技术积分: 1441
  • 用 户 组: 普通用户
  • 注册时间: 2008-01-05 20:39
文章分类
文章存档

2012年(2)

2011年(130)

2009年(2)

2008年(1)

我的朋友

分类:

2011-08-11 14:58:41

 

简述EPOLL

2008-08-07 12:54

1,epoll为啥高效

TCP协议栈发现一个socket有事件发生时,它就会唤醒阻塞中的进程(调用select、poll、epoll_wait而睡眠的应用程序)。区别在于,select和poll的内核实现中,协议栈仅仅是唤醒应用程序,没有其他后续操作,所以select内部醒来后还得自己轮询所有的socket;当socket的数量很大时,这里的效率就有了瓶颈。

epoll不同,在内核支持epoll后,唤醒应用程序的操作中,可以挂载回调函数,所以epoll实现的回调函数就把发生事件的socket信息记录到一个就绪队列中了。当epoll_wait醒来的时候,它当然不需要轮询,直接就从就绪队列中就可以取出所有发生了事件的套接字。

这里面,显然有计算机中中断和轮询的思想在。

2,ET和LT

简单地说,LT的套接字从就绪队列中取出后,如果该套接字上确实是有事件,那么内核还会将它再入放入就绪队列,下次epoll_wait还会返回该套接字。ET就不一样,从就绪队列中取出来后就不会再放进去了,除非TCP协议栈再次因为有了新事件再次将其放入队列。

这样导致的差别是LT的套接字不会发生“饿死”的现象,比如说LT的套接字收到了10000个字节的数据,那么你每次read 100个字节后继续epoll_wait,该套接字的事件依然会被返回(因为每次epoll_wait时,内核发现数据没有读完,依然会让该套接字保持在就绪队列中),不管有没有新的数据到达。ET就不一样,如果你读了100字节后就继续epoll_wait,只要没有新数据(或事件)到达,那么就永远不会监听到该套接字的事件了。所以ET的套接字常常设置为非阻塞的,在epoll_wait返回后一次性读完,直到返回EAGAIN为止。LT的套接字当然最好也设置为非阻塞的。

3,结论

写技术文章是件很麻烦的事,不知道说明白没有,EPOLL的关键是在内核里设置了一个“就绪队列”以及回调函数机制

 

Pasted from <http://hi.baidu.com/nanpo/blog/item/20b702241b73a92dd5074277.html>

 

阅读(615) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~