剖析epoll机制

  • Linux epoll机制;
  • 写这篇文章的原因是, 上次百度面试被问到一个事件怎么添加到epoll的双向链表中的; 这个问题比较深入, 涉及到内核的实现问题, 今天就来理解一下;
  • epoll和select/poll完全不同, epoll通过在Linux内核中申请一个简易的文件系统(文件系统一般用什么实现? B+树);
    • B+树, 相当于一个2-3的扩展, 一个节点可以有多个数据项, B+树而且它的叶子结点才有真正的数据, 并用一个单链表链接起来的;
  • epoll调用分成3个部分:
    • 调用epoll_create()建立一个epoll对象(在epoll文件系统中为这个句柄对象分配资源);
    • 调用epoll_ctl向epoll对象中添加或删除一些套接字;
    • 调用epoll_wait收集发生的事件的连接;
      • epoll_wait的调用非常高, 因为调用epoll_wait时, 并没有向操作系统复制连接的句柄数据, 内核不需要遍历全部的连接;
  • epoll_create会创建一个eventpoll结构体, 这个结构体中有两个成员与epoll的使用方式密切相关;
    • struct rb_root rbr; //红黑树的根节点, 这棵树中存储着所有添加到epoll中的需要监控的事件
    • epoll机制通过红黑树保存需要监控的事件;
    • struct list_head rdlist; // 双链表中存放着将要通过epoll_wait返回给用户的满足条件的活跃事件;
    • epoll机制通过一个双链表来保存活跃的事件;
  • 每一个epoll对象都有一个独立的eventpoll结构体, 用于存放通过epoll_ctl方法向epoll向epoll对象中添加进来的事件;
    • 这些事件都会被挂载在红黑树中, 重复添加的事件就可以通过红黑树而高效的识别出来(红黑树的插入时间效率是lgn, 其中n为树的高度);
    • 而所有添加到epoll中的事件都会与设备(网卡)驱动程序建立回调关系, 也就是说, 当相对应的事件发生时会调用这个回调方法;
    • 这个回调方法在内核中叫ep_poll_callback, 它将发生的事件添加到rdlist双链表中;
  • 在epoll中, 对于每一个事件, 都会建立一个epitem结构体;
    struct epitem{
struct rb_node rbn; //红黑树节点
struct list_head rdllink; //双向链表节点
struct epoll_filefd ffd; //事件句柄信息
struct eventpoll *ep; //指向其所属的eventpoll对象
struct epoll_event event; //期待发生的事件类型
}
  • 当调用epoll_wait检查是否有事件发生时, 只需要检查eventpoll对象中的rdlist双向链表中是否有epitem元素即可;

    • 如果红黑树不为空, 则把发生的事件复制到用户态, 同时把事件的数量返回给用户;
    • 双向链表的每个节点都是基于epitem结构中的rdlink成员;
    • 红黑树中的每个节点都是基于eptiem结构体中的rbn成员;
  • 通过红黑树和双向链表数据结构, 并结合回调机制, 照就了epoll的高效;
  • 怎么把事件添加到双向链表中?
    • 在调用epoll_ctl时, 如果增加socket句柄, 则检查在红黑树中是否存在, 如果存在则立即返回, 不存在则添加到树干上, 然后向内核注册回调函数, 回调函数用于当中断事件来临时向准备就绪链表中插入数据;
    • 那意思是中断函数会自动调用回调函数, 然后向准备就绪的双向链表中插入数据, 把就绪的事件加入到双向链表中;
  • nginx的epoll;

剖析epoll机制的更多相关文章

  1. 【Unix环境编程】select、poll、epoll机制的联系与区别

    在linux设计并发网络程序,主要有如下几种模型:Apache模型(Process Per Connection, PPC).TPC(Thread Per Connection)模型,select机制 ...

  2. epoll机制详解

    epoll机制详解 大牛的详解 epoll详解 什么是epoll? epoll是为处理大批量句柄而作了改进的poll, 是性能最好的多路I/O就绪通知方法; 只有三个系统调用: epoll_creat ...

  3. linux epoll机制对TCP 客户端和服务端的监听C代码通用框架实现

    1 TCP简介 tcp是一种基于流的应用层协议,其“可靠的数据传输”实现的原理就是,“拥塞控制”的滑动窗口机制,该机制包含的算法主要有“慢启动”,“拥塞避免”,“快速重传”. 2 TCP socket ...

  4. 从select机制谈到epoll机制

    目录 为什么要用select机制 等待队列 唤醒操作 什么是select机制 关于fd_set select使用 poll函数 为什么select效率较低 什么是epoll epoll机制实现思路 e ...

  5. select、poll和epoll机制

    一.参考网址 1.select函数及fd_set介绍 2.linux select 函数和 fd_set 用法 2.select.poll和epoll的区别 3.利用select实现IO多路复用TCP ...

  6. epoll机制

    一.参考网址 1.epoll机制:epoll_create.epoll_ctl.epoll_wait.close 2.Linux网络编程 使用epoll实现一个高性能TCP Echo服务器 3.用C写 ...

  7. 对epoll机制的学习理解v1

    epoll机制 wrk用非阻塞多路复用IO技术创造出大量的连接,从而达到很好的压力测试效果.epoll就是实现IO多路复用的关键. 本节是对epoll的本质的学习总结,进一步的参考资料为: <深 ...

  8. linux下select/poll/epoll机制的比较

    select.poll.epoll简介 epoll跟select都能提供多路I/O复用的解决方案.在现在的Linux内核里有都能够支持,其中epoll是Linux所特有,而select则应该是POSI ...

  9. Linux epoll机制

    epoll_create.epoll_ctl.epoll_wait.close 在linux的网络编程中,很长的时间都在使用select来做事件触发.在linux新的内核中,有了一种替换它的机制,就是 ...

随机推荐

  1. Redis之RDB与AOF 笔记

    AOF定义:以日志的形式记录每个操作,将Redis执行过的所有指令全部记录下来(读操作不记录),只许追加文件但不可以修改文件,Redis启动时会读取AOF配置文件重构数据 换句话说,就是Redis重启 ...

  2. C#设计模式(0)——设计原则

    设计原则 使用设计模式的根本原因是适应变化,提高代码复用率,使软件更具有可维护性和可扩展性.在进行设计的时候,我们需要遵循以下几个原则:单一职责原则.开闭原则.里氏替代原则.依赖倒置原则.接口隔离原则 ...

  3. Windows netstat 查看端口、进程占用 查看进程路径

    1.查看端口.进程占用 运行->进入cmd->netstat -ano 2.查看进程路径 运行->WMIC->process 3.查看进程PID和占用内存情况 运行->进 ...

  4. poi读取写入word【未完,待续】

    , [项目实战]Java POI之Word导出经典案例一 Java POI 读取word文件 POI-对于WORD的操作(一)

  5. javascript中var、let和const的区别

    在javascript中,var.let和const都可以用来声明变量,那么三者有什么区别呢?要回答这个问题,我们可以从先想想:三种不同的声明会影响变量的哪些方面?这些方面也就是变量的特性,那么变量有 ...

  6. C#中转换函数Convert、Parse、TryParse、(int) 的区别

    Convert.Parse.TryParse.(int) 三个函数都是将值转换成整数,但是四者之间各有异同,开发人员可以根据情况选用最合适的.以下解释均经过高人验证,希望对大家有所帮助. 1 (int ...

  7. 【游记】THUWC2018踹线记

    Day1. 早上九点多报道,然后就是试机.一开始有一些懵,没看清门外的通知,操作起来各种懵逼.不过提前适应过了在Linux下面编程,所以问题不大.调了gedit的界面,试了一下对拍,敲了一道试机题,然 ...

  8. webpack中resolve用法

    如果想在页面中使用 bootstrap 的样式,一般会在入口文件中引入 import 'bootstrap' 但是这样引入的 bootstrap 默认引入的是JS文件,所以页面的样式是不会生效的,下面 ...

  9. jmeter负载机运行/添加压力机/分布式

    • 我们在压测的时候,可能并发比较大, 一台机子已经启动不了那么多并发了,这个时候我们就要使用多台机子一起来发压力,就要添加压力机,添加压力机怎么添加呢,首先要在做压力机的机子上启动jmeter的代理 ...

  10. lua 协程的理解

    参考链接: http://www.cnblogs.com/zrtqsk/p/4374360.html 对例子的自我理解: -- 协程的理解 -- co 是协程的内容,类似函数内容, 通过yield 将 ...