[转]epoll给我们带来了什么

news/2024/7/5 6:43:02


来源:http://publish.it168.com/2005/0819/20050819022001.shtml


Q:网络服务器的瓶颈在哪? A:IO效率。

    在大家苦苦的为在线人数的增长而导致的系统资源吃紧上的问题正在发愁的时候,Linux 2.6内核中提供的System Epoll为我们提供了一套完美的解决方案。传统的select以及poll的效率会因为在线人数的线形递增而导致呈二次乃至三次方的下降,这些直接导致了网络服务器可以支持的人数有了个比较明显的限制。

    自从Linux提供了/dev/epoll的设备以及后来2.6内核中对/dev/epoll设备的访问的封装(System Epoll)之后,这种现象得到了大大的缓解,如果说几个月前,大家还对epoll不熟悉,那么现在来说的话,epoll的应用已经得到了大范围的普及。

    那么究竟如何来使用epoll呢?其实非常简单。

    通过在包含一个头文件#include 以及几个简单的API将可以大大的提高你的网络服务器的支持人数。

    首先通过create_epoll(int maxfds)来创建一个epoll的句柄,其中maxfds为你epoll所支持的最大句柄数。这个函数会返回一个新的epoll句柄,之后的所有操作将通过这个句柄来进行操作。在用完之后,记得用close()来关闭这个创建出来的epoll句柄。

    之后在你的网络主循环里面,每一帧的调用epoll_wait(int epfd, epoll_event events, int max events, int timeout)来查询所有的网络接口,看哪一个可以读,哪一个可以写了。基本的语法为: nfds = epoll_wait(kdpfd, events, maxevents, -1);

    其中kdpfd为用epoll_create创建之后的句柄,events是一个epoll_event*的指针,当epoll_wait这个函数操作成功之后,epoll_events里面将储存所有的读写事件。max_events是当前需要监听的所有socket句柄数。最后一个timeout是epoll_wait的超时,为0的时候表示马上返回,为-1的时候表示一直等下去,直到有事件范围,为任意正整数的时候表示等这么长的时间,如果一直没有事件,则范围。一般如果网络主循环是单独的线程的话,可以用-1来等,这样可以保证一些效率,如果是和主逻辑在同一个线程的话,则可以用0来保证主循环的效率。

    epoll_wait范围之后应该是一个循环,遍利所有的事件:

    for(n = 0; n < nfds; ++n)
      {
        if(events[n].data.fd == listener) { //如果是主socket的事件的话,则表示有新连接进入了,进行新连接的处理。 
       client = accept(listener, (struct sockaddr *) &local, &addrlen);
                   if(client < 0){
                       perror("accept");
                       continue;
                   }
                   setnonblocking(client); // 将新连接置于非阻塞模式
                   ev.events = EPOLLIN | EPOLLET; // 并且将新连接也加入EPOLL的监听队列。

    注意,这里的参数EPOLLIN | EPOLLET并没有设置对写socket的监听,如果有写操作的话,这个时候epoll是不会返回事件的,如果要对写操作也监听的话,应该是EPOLLIN | EPOLLOUT | EPOLLET

    ev.data.fd = client;
    if (epoll_ctl(kdpfd, EPOLL_CTL_ADD, client, &ev) < 0) {
    // 设置好event之后,将这个新的event通过epoll_ctl加入到epoll的监听队列里面,这里用EPOLL_CTL_ADD来加一个新的epoll事件,通过EPOLL_CTL_DEL来减少一个epoll事件,通过EPOLL_CTL_MOD来改变一个事件的监听方式。
        fprintf(stderr, "epoll set insertion error: fd=%d0, client);
            return -1;
                   }
               }
      else // 如果不是主socket的事件的话,则代表是一个用户socket的事件,则来处理这个用户socket的事情,比如说read(fd,xxx)之类的,或者一些其他的处理。
          do_use_fd(events[n].data.fd);
}

    对,epoll的操作就这么简单,总共不过4个API:epoll_create, epoll_ctl, epoll_wait和close。 如果您对epoll的效率还不太了解,请参考我之前关于网络游戏的网络编程等相关的文章。

    世界变了,原来担心的问题,现在已经不是问题了。

 



http://www.niftyadmin.cn/n/3652619.html

相关文章

Linux系统小白的成长之路

文章目录ShellLinux命令的分类内部命令与外部命令的区别查看内部命令Linux命令行的格式通用的命令行使用格式编辑Linux命令行编辑Linux命令行的辅助操作获取命令帮助的方法内部命令help命令的“--help”选项使用man命令阅读手册页Linux基础命令的用法查看当前的工作目录——pwd…

[转]用PHP构建一个简易监视引擎

来源: http://dev.yesky.com/web/263/2638263.shtml摘要&#xff1a;在本文中&#xff0c;让我们共同探讨基于PHP语言构建一个基本的服务器端监视引擎的诸多技巧及注意事项&#xff0c;并给出完整的源码实现。  一. 更改工作目录的问题  当你编写一个监视程序时&#xff0c…

Linux系统小白的成长之路2

文章目录统计目录及文件空间占用情况——du创建新目录——mkdir创建空文件——touch创建链接文件——ln软连接和硬链接的区别复制文件或目录——cp常用选项删除文件或目录——rm常用选项移动文件或目录——mv查找命令文件存放目录——which查找文件或目录——find常用查找条件类…

GB2312汉字拼音对照表

GB2312 汉字拼音对照表&#xff08;6727字&#xff09;来源&#xff1a;http://zh.transwiki.org/wiki/index.php/GB2312%E6%B1%89%E5%AD%97%E6%8B%BC%E9%9F%B3%E5%AF%B9%E7%85%A7%E8%A1%A8啊 a阿 a e埃 ai挨 ai哎 ai唉 ai哀 ai皑 ai癌 ai蔼 ai矮 ai艾 ai yi碍 ai爱 ai隘 ai鞍 …

Linux系统小白成长之路(3)

文章目录目录和文件管理的方法常见的子目录查看文件内容——cat&#xff08;常用于短文件&#xff09;查看文件内容——more&#xff08;常用于长文件&#xff09;查看文件内容——less查看文件内容——head、tail统计文件内容——wc检索和过滤文件内容——grep压缩命令gzip、b…

[转]通过Chroot机制让服务器安全到底

所谓"监牢"就是指通过chroot机制来更改某个进程所能看到的根目录&#xff0c;即将某进程限制在指定目录中&#xff0c;保证该进程只能对该目录及其子目录的文件有所动作&#xff0c;从而保证整个服务器的安全。 创建chroot"监牢" 以前&#xff0c;Unix/Lin…

[转]chroot Linux中的所有服务

作者&#xff1a;Mark Nielsen译者&#xff1a;蓝风原文出处&#xff1a;LinuxFocus.org 摘要&#xff1a;当某些人入侵你的系统时&#xff0c;chroot将通过限制入侵者所能造成的损失来提高系统的安全性。介绍&#xff1a;  什么是chroot呢&#xff1f;它其实是对一个程序从根…

RPM安装管理与yum的安装

文章目录应用程序与系统命令的关系典型应用程序的目录结构常见的软件包封装类型RPM管理工具rpm命令的格式查询RPM软件包信息查询未安装的RPM软件包文件中信息安装、升级、卸载RPM软件包维护RPM数据库yum安装软件包方式挂载Windows中的共享目录应用程序与系统命令的关系 角色系…