【Linux】epoll 服务器

1. 在进行 epoll 服务器代码的编写前,我们先来认识一下需要用到的函数。

1)创建:int epoll_create(int size);

       创建一个 epoll 的句柄。自从 linux2.6.8 之后,size 参数是被忽略的。需要注意的是,当创建好 epoll 句柄后,它就是会占用一个 fd 值,在 linux 下如果查看 /proc/ 进程 id/fd/,是能够看到这个 fd 的,所以在使用完epoll后,必须调用 close() 关闭,否则可能导致 fd 被耗尽。


2)控制:int epoll_ctl(int epfd, int op, int fd, struct epoll_event *event);

       epoll 的事件注册函数,它不同于 select() 是在监听事件时告诉内核要监听什么类型的事件,而是在这里先注册要监听的事件类型。

第一个参数是 epoll_create() 的返回值。

第二个参数表示动作,用三个宏来表示:

EPOLL_CTL_ADD:注册新的 fd 到 epfd 中;

EPOLL_CTL_MOD:修改已经注册的 fd 的监听事件;

EPOLL_CTL_DEL:从 epfd 中删除一个 fd;

第三个参数是需要监听的 fd。

第四个参数是告诉内核需要监听什么事,struct epoll_event 结构如下:


events可以是以下几个宏的集合:

EPOLLIN :表示对应的文件描述符可以读(包括对端 SOCKET 正常关闭);

EPOLLOUT:表示对应的文件描述符可以写;

EPOLLPRI:表示对应的文件描述符有紧急的数据可读(这里应该表示有带外数据到来);

EPOLLERR:表示对应的文件描述符发生错误;

EPOLLHUP:表示对应的文件描述符被挂断;

EPOLLET:将 EPOLL 设为边缘触发 (Edge Triggered) 模式,这是相对于水平触发 (LevelTriggered) 来说的。

EPOLLONESHOT:只监听一次事件,当监听完这次事件之后,如果还需要继续监听这个 socket 的话,需要再次把这个 socket 加入到 EPOLL 队列里。


3. 等待:int epoll_wait(int epfd, struct epoll_event * events, int maxevents, int timeout);

       收集在 epoll 监控的事件中已经发送的事件。参数 events 是分配好的 epoll_event 结构体数组,epoll 将会把发生的事件赋值到 events 数组中(events 不可以是空指针,内核只负责把数据复制到这个 events 数组中,不会去帮助我们在用户态中分配内存)。maxevents 告之内核这个 events 有多大,这个 maxevents 的值不能大于创建 epoll_create() 时的 size,参数 timeout 是超时时间(毫秒,0 会立即返回,-1 将不确定,也有说法说是永久阻塞)。如果函数调用成功,返回对应 I/O 上已准备好的文件描述符数目,如返回 0 表示已超时。


2. 默认模式(LT)的 epoll 服务器代码

vim epoll_server.c









运行结果如下:




3. epoll 服务器的优缺点

优点:

1)支持最大数目的文件描述符(fd)

       epoll 的文件描述符支持最大的打开数目,一般来说 1G 可以存 10 万左右。

2)IO 效率不随 fd 数目增加下降 

     这个主要原因是因为 epoll 不采用轮询,采用活跃的 fd 进行调用 callback 回调机制实现的。

3)mmap实现 

     epoll 的实现中使用了 mmap (内存)映射机制,这样可以避免不必要的内存拷贝,用户空间和内核空间在同一块内存实现,避免了多余的拷贝,省掉了这些文件描述符在系统调用时复制的开销。

缺点: 

1)相对 select 来说,epoll 的跨平台性不够用,只能工作在 Linux 下,而 select 可以在 windows linux apple 上使用,还有手机端 Android iOS 之类的都可以。 android 虽然是 linux 的内核,但早期版本同样不支持 epoll 的。 

2)相对 select 来说,还是用起来还是复杂了一些,不过和 IOCP 比起来,增加了一点点的复杂度却基本上达到了 IOCP 的并发量和性能,而复杂度远远小于IOCP。 

3)相对 IOCP 来说,对多核/多线程的支持不够好,也因此在性能要求比较苛刻的情况下不如 IOCP。





  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值