epoll_wait函数
函数简介
/* Wait for events on an epoll instance "epfd". Returns the number of
triggered events returned in "events" buffer. Or -1 in case of
error with the "errno" variable set to the specific error code. The
"events" parameter is a buffer that will contain triggered
events. The "maxevents" is the maximum number of events to be
returned ( usually size of "events" ). The "timeout" parameter
specifies the maximum wait time in milliseconds (-1 == infinite).
This function is a cancellation point and therefore not marked with
__THROW. */
extern int epoll_wait (int __epfd, struct epoll_event *__events,
int __maxevents, int __timeout)
__attr_access ((__write_only__, 2, 3)) __nonnull ((2));
epoll_wait
是 Linux 中用于轮询 I/O 事件的一个系统调用,它是 epoll
接口的一部分,用于替代传统的 select
或 poll
。epoll_wait
允许你监视多个文件描述符,以查看它们是否准备好进行读或写操作,或者是否有异常条件待处理。
函数原型:
int epoll_wait(int epfd, struct epoll_event *events, int maxevents, int timeout);
参数说明:
- epfd (epoll file descriptor):
- 这是一个由
epoll_create
或epoll_create1
创建的 epoll 实例的文件描述符。 - 通过这个描述符,你可以向 epoll 实例中添加、删除或修改要监视的文件描述符。
- events (pointer to epoll_event structure array):
- 这是一个指向
epoll_event
结构数组的指针,用于接收准备就绪的事件。 epoll_event
结构包含与事件相关的文件描述符和数据。- 在调用
epoll_wait
后,events
数组会被填充为准备就绪的文件描述符和它们关联的事件(例如读就绪、写就绪等)。
- maxevents (maximum number of events to return):
- 这个参数指定了
events
数组可以容纳的最大事件数。 epoll_wait
最多会返回这个数目的准备就绪事件。如果少于这个数目的事件准备就绪,那么实际返回的事件数会少于maxevents
。- 如果这个参数设置为 0,那么
epoll_wait
将立即返回,不等待任何事件发生。
- timeout (maximum time to wait):
- 这个参数指定了
epoll_wait
在没有事件准备就绪时应等待的最长时间(以毫秒为单位)。 - 如果设置为 -1,
epoll_wait
将无限期地等待,直到至少有一个事件准备就绪。 - 如果设置为 0,
epoll_wait
将立即返回,不等待任何事件发生。 - 如果设置为一个正整数 N,
epoll_wait
将等待最多 N 毫秒。如果在这段时间内没有事件准备就绪,它将返回一个错误。
返回值:
- 如果成功,
epoll_wait
返回准备就绪的事件数。 - 如果发生错误,它返回 -1,并设置全局变量
errno
以指示错误类型。
请注意,epoll_wait
是阻塞调用,这意味着在指定的超时时间内如果没有任何事件准备就绪,调用线程将被阻塞。如果超时时间到达并且没有事件准备就绪,epoll_wait
将返回 0。
低层实现逻辑
epoll_wait
是 Linux 下的一个函数,用于等待事件的发生。它是 epoll
接口的一部分,用于高效地处理大量文件描述符的 I/O 事件。
epoll_wait
的底层实现逻辑主要涉及以下几个方面:
-
注册文件描述符:使用
epoll_ctl
函数将需要监听的文件描述符注册到epoll
实例中,并指定感兴趣的事件。 -
等待事件:调用
epoll_wait
函数会阻塞当前线程,直到有事件发生。 -
事件处理:当有事件发生时,
epoll_wait
函数会返回发生事件的文件描述符数量,并将对应的事件存储在用户提供的数组中。通过遍历这个数组,可以获取发生事件的文件描述符和对应的事件类型。 -
高效的实现:
epoll
采用了一种基于回调的机制,不需要轮询所有的文件描述符来检测事件。它维护了一个红黑树来存储注册的文件描述符,并利用mmap
来加速事件的通知和处理。 -
支持水平触发和边缘触发:
epoll
可以配置为水平触发或边缘触发模式。水平触发模式下,只要文件描述符上有事件未处理,就会一直触发通知;而边缘触发模式下,只有在事件发生的边缘才会触发通知。 -
线程安全性:
epoll
在多线程环境下是安全的,可以在多个线程中同时使用。
epoll_wait
的底层实现利用了 Linux 内核的 epoll
机制,提供了高效的 I/O 事件通知和处理能力。它是在 Linux 上进行高性能网络编程和并发编程的重要工具。