• select\poll\epoll的区别


    select

    1. select 最多只能监听1024个文件描述符,且这1024个文件描述符的最大值不能超过1023,这是因为selset使用的fd_set结构体。fd_set结构体内容如下:
      
      __fd_mask fds_bits[__FD_SETSIZE / __NFDBITS];
      
      typedef long int __fd_mask;
      #define	__FD_SETSIZE		1024
      #define __NFDBITS	(8 * (int) sizeof (__fd_mask))
      
      //实际上就是
      long int fds_bits[1024 / sizeof(long int)]
      
      • 1
      • 2
      • 3
      • 4
      • 5
      • 6
      • 7
      • 8
      • 9

    fd_set直接看成一个数组,以32位机为例,就相当于一个长度为(1024 / 32)的long int数组,里面使用一位监听一个文件描述符,故其最多只可监听1024个文件描述符,且最大文件描述符为1023。

    1. select每次监听前都要为想要构造想要监听的fd_set,因为select是通过你所传递进去的文件fd_set返回的,在内核中会修改fd_set表中的内容。这是因为在内核中会先将用户空间定义的fd_set拷贝到内核空间,在内核空间会对文件描述符进行监听,在数据没有准备好的时候,进程会放弃cpu进入到休眠态,当被唤醒后会再次遍历拷贝到内核中的fd_set,找到对应的就绪文件描述符,将对应位置一,最后再将将内核中的fd_set拷贝到用户空间,用户拿到的fd_set是已经就绪的文件描述符表,不一定是原来的表,因此每次在监听前都要重新构造fd_set,所以效率低。
    2. 当select对应的进程休眠时,如果对应的文件描述符准备好了,还要再次遍历整个文件描述符的表,将对应的位置一,不能直接返回准备好的文件描述符表,因此效率低。

    poll

    1. poll监听的文件描述符没有个数限制,因为poll使用的是结构体指针,因此没有描述符的个数限制。
      struct pollfd {
        int   fd;         /* 文件描述符  设置成-1 内核就不再监视这一位了*/
        short events;     /* 要监视的事件 */
        short revents;    /* 返回的事件 */
      };
      
      • 1
      • 2
      • 3
      • 4
      • 5
    2. poll表不会被清空,不需要反复构造,效率高。
    3. 当poll对应的进程休眠的时候,如果有文件描述符的数据准备好了,还需要再次遍历文件描述符,效率低。

    epoll

    1. epoll监听的文件描述符没有个数限制,epoll使用的是红黑树。
    2. epoll表不会被清空,不需要反复构造,效率高。
    3. 当epoll对应的进程休眠的时候,如果有文件描述符的数据准备好了,不需要遍历文件描述符,它可以直接拿到准备好的文件描述符。效率高。

    注意:

    select、poll和epoll在驱动中使用的都是.poll,它们的不同都在VFS中。

  • 相关阅读:
    SpringBoot集成ElasticSearch,实现模糊查询,批量CRUD,排序,分页,高亮
    asp.net core系列 77 webapi响应压缩
    智囊AI-基于 ChatGPT 的 AI 工具产品 你的私人AI助手
    Python科学计算与可视化 C1
    【直播】-DRM和TZC400的介绍-2022/11/26
    OpenGL之着色器
    《算法笔记》图专题
    网络安全(黑客)自学
    1796. 字符串中第二大的数字
    ADB环境搭建和抓取Crash日志实践总结
  • 原文地址:https://blog.csdn.net/qq_41555003/article/details/127989927