zoukankan      html  css  js  c++  java
  • epoll 和select

    epoll 水平触发和边缘触发的区别

    EPOLLLT——水平触发
    EPOLLET——边缘触发

    epoll有EPOLLLT和EPOLLET两种触发模式,LT是默认的模式,ET是“高速”模式。LT模式下,只要这个fd还有数据可读,每次 epoll_wait都会返回它的事件,提醒用户程序去操作,而在ET(边缘触发)模式中,它只会提示一次,直到下次再有数据流入之前都不会再提示了,无 论fd中是否还有数据可读。所以在ET模式下,read一个fd的时候一定要把它的buffer读光,也就是说一直读到read的返回值小于请求值,或者 遇到EAGAIN错误。

    select 最大限制为1024解析

       Linux下,select下模型为:__FD_SETSIZE 默认最大为1024,一个int占用4个byte,也就是32个bit,所以使用了一个int数组大小为32位来表示了我们要操作的fd的数值,每个bit代表了一个handle数值,需要注意的问题是,这里的最大为1024,如果handle数值为1025是不能处理的(而且很容易导致破坏堆栈),不是说可以容纳1024个网络客户端句柄,而是最大的handle数值为1024,再算上系统本身使用的stdout,stdin, stderr默认的3个,因此最多也就是1021个,再算上程序打开的文件句柄等等,实际上使用可能要比1024少上好多。另外,ulimit对每个进程打开的句柄也有限制。当然可以通过修改内核来增大,但是原则上不推荐修改过大,这是因为过大的数目会对性能造成很大影响,所以推荐使用epoll来处理大数目handle数值。

        

        

    /* fd_set for select and pselect.  */
    
    typedef struct
    {
    /* XPG4.2 requires this member name. Otherwise avoid the name
    from the global namespace. */
    #ifdef __USE_XOPEN
    __fd_mask fds_bits[__FD_SETSIZE / __NFDBITS];
    # define __FDS_BITS(set) ((set)->fds_bits)
    #else
    __fd_mask __fds_bits[__FD_SETSIZE / __NFDBITS];
    # define __FDS_BITS(set) ((set)->__fds_bits)
    #endif
    } fd_set;

    #ifdef FD_SETSIZE
    #define __DARWIN_FD_SETSIZE FD_SETSIZE
    #else /* !FD_SETSIZE */
    #define __DARWIN_FD_SETSIZE 1024
    #endif /* FD_SETSIZE */
    #define __DARWIN_NBBY 8 /* bits in a byte */
    #define __DARWIN_NFDBITS (sizeof(__int32_t) * __DARWIN_NBBY) /* bits per mask */
    #define __DARWIN_howmany(x, y) ((((x) % (y)) == 0) ? ((x) / (y)) : (((x) / (y)) + 1)) /* # y's == x bits? */

    __BEGIN_DECLS
    typedef struct fd_set {
      __int32_t fds_bits[__DARWIN_howmany(__DARWIN_FD_SETSIZE, __DARWIN_NFDBITS)];
    } fd_set;
    __END_DECLS

     处理使用ulimit修改限制以为也可以通过函数来getrlimit和setrlimit修改:

    getrlimit和setrlimit的使用也很简单,manpage里有很清楚的描述。
    int getrlimit(int resource, struct rlimit *rlim);
    int setrlimit(int resource, const struct rlimit *rlim);
    需要注意的是你在setrlimit,需要检查是否成功来判断新值有没有超过hard limit。如下例:
    if (getrlimit(RLIMIT_CORE, &rlim)==0) {

    rlim_new.rlim_cur = rlim_new.rlim_max = RLIM_INFINITY;
    if (setrlimit(RLIMIT_CORE, &rlim_new)!=0) {
    /* failed. try raising just to the old max */
    rlim_new.rlim_cur = rlim_new.rlim_max =
    rlim.rlim_max;
    (void) setrlimit(RLIMIT_CORE, &rlim_new);
    }

    }

  • 相关阅读:
    win10通过ip连接打印机
    tarunexpectedeofinarchive
    软件工程设计阶段的几种图
    代码review checklist
    caffeine的使用
    thetrustanchorsparametermustbenonempty
    mysql explain type的详解
    scp对拷贝文件夹
    虚拟dom与diff算法
    线程池ThreadPoolExecutor的使用
  • 原文地址:https://www.cnblogs.com/fvsfvs123/p/4362562.html
Copyright © 2011-2022 走看看