简述:
file_operations的poll是驱动提供给应用程序探测设备文件是否有数据可读接口。

应用程序探测文件的接口:
select,poll,epoll三个接口都是应用程序探测设备文件是否有数据可读的接口,没有数据进程阻塞,有数据时唤醒。select和poll差不多,epoll是select、poll的增强版,性能上会更好。

select头文件:

#include <sys/select.h>

poll头文件:

#include <sys/poll.h>

epoll头文件:

#include <sys/epoll.h>

如是ubuntu系统,select.h、poll.h、epoll.h都可以在/usr/include/sys/目录下查看。

三个函数详细说明用法,参考如下博客:
Linux IO模式及 select、poll、epoll详解
linux poll函数
Linux内核中select, poll和epoll的区别

驱动层实现file_operations的poll:

先直接看一个例子:

static DECLARE_WAIT_QUEUE_HEAD(my_waitq);  //休眠要挂的等待队列
static unsigned drv_poll(struct file *file, poll_table *wait)
{
    unsigned int mask = 0;
    poll_wait(file, &my_waitq, wait); // 不会立即休眠
    if (有数据)//判断是否有数据
    mask |= POLLIN | POLLRDNORM;
    return mask;
}

poll_wait:看得出,我们只是提供了一个waitqueue,没有数据时进程会阻塞在这个waitqueue上。驱动poll里面基本上都要用这个函数,定义在头文件:

#include <linux/poll.h>

例子中,进程不会在drv_poll里面阻塞,当mask为0返回时,进程阻塞,什么时候唤醒,需要驱动根据情况去wake up我们定义的waitqueue(my_waitq)。如有数据时,需要告诉系统数据情况,如例子中的mask |= POLLIN | POLLRDNORM,mask不为0不阻塞,根据mask值做出操作。

POLLIN、POLLRDNORM宏定义在include/uapi/asm-generic/poll.h中,说明如下:
POLLIN: 有数据可读。
POLLRDNORM: 有普通数据可读。
POLLRDBAND:有优先数据可读。
POLLPRI:有紧迫数据可读。
POLLOUT:写数据不会导致阻塞。表示有空间可写。
POLLWRNORM:写普通数据不会导致阻塞。表示有空间可写。
POLLWRBAND:写优先数据不会导致阻塞。表示有空间可写。
POLLMSG:SIGPOLL 消息可用。
POLLER:指定的文件描述符发生错误。
POLLHUP:指定的文件描述符挂起事件。
POLLNVAL:指定的文件描述符非法。

总结:驱动接口poll不会阻塞进程,只是返回后,系统会根据返回值是否阻塞进程,如阻塞,需求驱动去唤醒(有数据时wake up)。

poll代码跟踪分析,参考如下博客:
linux的poll机制

GitHub 加速计划 / li / linux-dash
10.39 K
1.2 K
下载
A beautiful web dashboard for Linux
最近提交(Master分支:2 个月前 )
186a802e added ecosystem file for PM2 4 年前
5def40a3 Add host customization support for the NodeJS version 4 年前
Logo

旨在为数千万中国开发者提供一个无缝且高效的云端环境,以支持学习、使用和贡献开源项目。

更多推荐