项目接入层用的模型是,主线程创建listenfd,传入6个子线程,每个子线程一个事件循环,epoll_wait这个listenfd。

如果是listenfd,则epoll_wait返回调用accept,其它fd则另外处理。

这里有个epoll_wait的惊群现象:

当一个新连接到达(connect),所有等待在此listenfd上的线程均会被唤醒,进入到事件处理循环中去,但只有一个循环中的accept()会返回,其它线程均返回-1,并置EAGAIN (11)的errno;

Linux在内核层解决了accept的惊群问题,即accept在同一listenfd上的多个线程,事件到达时只有一个会被唤醒。

但Linux为什么不在内核解决epoll_wait的惊群问题呢?

因为对于listenfd,有确切的语义,只会调用accept。但epoll_wait可以等待listenfd和socketfd及其它多种事件,像socketfd可能存在由多个线程同时去读的情景(只是举例,一般网络编程也无这种场景应用);Linux内核无法加以区分。

————

如何解决epoll_wait的惊群问题?

参考Nginx的方案,使用一个accept_mutex锁,同一时刻listenfd只会加入到其中一个线程的事件循环中监听;当前进程处理的连接达到一定规模后,释放掉mutex,即不再处理新的连接请求。这样其它低负载的线程会拿到锁,去监听;这样也达到一个负载均衡的效果;

————

惊群带来的效率损失,主要在频繁的唤起epoll_wait,带来的系统调用开销。我们目前的处理方式为:

大量TCP长连接,不存在惊群引入的效率问题,因此未处理;只在accept返回-1,errno == 11时,作continue处理;

epoll_wait惊群问题的更多相关文章

  1. accept与epoll惊群 转载

    今天打开 OneNote,发现里面躺着一篇很久以前写的笔记,现在将它贴出来. 1. 什么叫惊群现象 首先,我们看看维基百科对惊群的定义: The thundering herd problem occ ...

  2. “惊群”,看看nginx是怎么解决它的

    在说nginx前,先来看看什么是“惊群”?简单说来,多线程/多进程(linux下线程进程也没多大区别)等待同一个socket事件,当这个事件发生时,这些线程/进程被同时唤醒,就是惊群.可以想见,效率很 ...

  3. Linux网络编程“惊群”问题总结

    1.前言 我从事Linux系统下网络开发将近4年了,经常还是遇到一些问题,只是知其然而不知其所以然,有时候和其他人交流,搞得非常尴尬.如今计算机都是多核了,网络编程框架也逐步丰富多了,我所知道的有多进 ...

  4. epoll 惊群处理

    #include <sys/types.h> #include <sys/socket.h> #include <sys/epoll.h> #include < ...

  5. Linux惊群效应详解

    Linux惊群效应详解(最详细的了吧)   linux惊群效应 详细的介绍什么是惊群,惊群在线程和进程中的具体表现,惊群的系统消耗和惊群的处理方法. 1.惊群效应是什么?        惊群效应也有人 ...

  6. redis惊群

    本文链接:http://www.cnblogs.com/zhenghongxin/p/8681168.html 什么是惊群 首先,我们使用缓存的主要目的就是为了高并发情况下的高可用,换句话说,在使用了 ...

  7. Nginx学习之一-惊群现象

    惊群问题(thundering herd)的产生 在建立连接的时候,Nginx处于充分发挥多核CPU架构性能的考虑,使用了多个worker子进程监听相同端口的设计,这样多个子进程在accept建立新连 ...

  8. Nginx惊群处理

    惊群:是指在多线程/多进程中,当有一个客户端发生链接请求时,多线程/多进程都被唤醒,然后只仅仅有一个进程/线程处理成功,其他进程/线程还是回到睡眠状态,这种现象就是惊群. 惊群是经常发生现在serve ...

  9. 【转载】“惊群”,看看nginx是怎么解决它的

    原文:http://blog.csdn.net/russell_tao/article/details/7204260 在说nginx前,先来看看什么是“惊群”?简单说来,多线程/多进程(linux下 ...

随机推荐

  1. Linux中环境变量文件

    一.环境变量文件介绍 转自:http://blog.csdn.net/cscmaker/article/details/7261921 Linux中环境变量包括系统级和用户级,系统级的环境变量是每个登 ...

  2. Redis php常用操作

    $redis = new redis(); //连接 $redis->connect('127.0.0.1',6379); // //设置值 $result = $redis->set(' ...

  3. vue2.0 transition 手风琴

    <div class="food"> <button @click="show=!show">show</button> & ...

  4. Linux升级内核教程(CentOS7)

    1.查看当前内核版本 uname -r 2.通过yum升级内核 通过yum升级内核是最保险的升级方式,因为安装的是操作系统发行厂商验证过兼容性的rpm包,升级风险一般很小. yum install - ...

  5. 交互式shell编程

    FQ #!/usr/bin/env shxfce4-terminal -x sudo python ./local/proxy.py 连续执行 gnome-terminal -x bash -c &q ...

  6. map的key 为指针

    STL中map的key能否用char *呢?当然可以! 在程序中需要用到一个map,本来是这样写的,map<string, int> mapStr; 为了追求效率,把string改成了ch ...

  7. CString 转换为 wchar_t *

    1.将CString转换为const char* CString str = _T("231222"); std::string strDp = CStringA(str);  / ...

  8. ajax参数传递之[HttpGet]/[HttpPost]/[HttpPut]/[HttpDelete]请求

    $.ajax({ type: "get", url: "http://localhost:27221/api/Charging/GetByModel", con ...

  9. 银联接口C#

    银联支付: ChinaPay的会员商户接入支付平台,以方便商户开展网上支付交易. 持卡人从商户网站中生成订单信息,通过公共支付交易平台中的支付网关子系统进行支付的过程,其交易流程包括订单确认.支付处理 ...

  10. 深入理解Connector

    上一篇主要是从各个容器的生命周期的角度讲了一下整个tomcat的运行流程,说明了各个容器之间的调用关系.但并没有太过详细的说明每一个组件并区分他们. 下面从功能的角度上详细的分析一下connector ...