【问题标题】:Duplicating epoll file descriptor复制 epoll 文件描述符
【发布时间】:2016-06-13 10:40:28
【问题描述】:
有没有办法复制使用epoll_create 创建的文件描述符,从而可以独立修改副本(使用epoll_ctl 添加/删除监视的文件描述符)。
例如我创建了一个 epoll 文件描述符 A,它等待文件 P 和 Q 上的事件。我将它复制到 epoll 文件描述符B,并使B 也等待文件R 上的事件。调用epoll_wait(A) 仍然只会等待P 和Q。
这是在A 上调用dup 时的行为,还是需要使用epoll_create 和epoll_ctl 重新创建epoll 文件描述符?
【问题讨论】:
标签:
c
linux
file-descriptor
epoll
dup
【解决方案1】:
这有点令人困惑。
当您打开一个新文件时,会创建两个实体。一个是内核中的文件句柄。另一个是文件描述符,一个引用该文件句柄的数字。
虽然我不确定 epoll fd 会发生什么,但我假设它与任何其他重复的 fd 相同,即它们是相同的文件句柄。
对于这一点的提示,epoll(2) 手册页的这段摘录可能会有所帮助:
Q6 关闭文件描述符会导致它自动从所有 epoll 集中移除吗?
A6 可以,但请注意以下几点。文件描述符是对打开文件描述的引用(请参阅open(2))。
每当通过dup(2)复制描述符时,
dup2(2)、fcntl(2) F_DUPFD 或 fork(2),创建引用相同打开文件描述的新文件描述符。一个
打开文件描述继续存在直到
所有引用它的文件描述符都已关闭。只有在所有文件之后才从 epoll 集中删除文件描述符
涉及底层的描述符
打开的文件描述已被关闭(或之前,如果使用 epoll_ctl(2) EPOLL_CTL_DEL 显式删除描述符)。
这意味着即使在一个文件之后
作为 epoll 集的一部分的描述符已关闭,如果其他文件可能会报告该文件描述符的事件
指代相同底层证券的描述符
文件描述保持打开状态。
所以,虽然我自己没有检查过,但我猜dup 不会允许你以任何方式复制 epoll 的过滤器列表。 fds 都将引用相同的文件句柄。对一个过滤器所做的任何更改都将反映在另一个过滤器中。
不幸的是,由于我知道没有 API 可以查询 epoll 的过滤器列表,这意味着你无法做你想做的事,除非从头开始跟踪。
【解决方案2】:
您可以对不同的底层文件结构(或具有不同fd的相同文件结构)独立操作重复的epfd。