通过/ proc/mounts监视安装点更改

sho*_*ban 10 c linux filesystems mount procfs

根据proc手册,可以通过打开"/ proc/mounts"监视linux系统中的挂载点更改,并添加文件描述符以读fd_set入select()调用.

以下代码适用于Ubuntu 9.04,而不适用于Ubuntu 10.04(2.6.32 linux内核):

int mfd = open("/proc/mounts", O_RDONLY, 0);

fd_set rfds;
struct timeval tv;
int rv;

FD_ZERO(&rfds);
FD_SET(mfd, &rfds);
tv.tv_sec = 5;
tv.tv_usec = 0;

int changes = 0;
while ((rv = select(mfd+1, &rfds, NULL, NULL, &tv)) >= 0) {
    if (FD_ISSET(mfd, &rfds)) {
        fprintf(stdout, "Mount points changed. %d.\n", changes++);
    }

    FD_ZERO(&rfds);
    FD_SET(mfd, &rfds);
    tv.tv_sec = 5;
    tv.tv_usec = 0;

    if (changes > 10) {
        exit(EXIT_FAILURE);
    }
}
Run Code Online (Sandbox Code Playgroud)

可编辑的代码段.

文件描述符总是在一台机器上可读,因此它会在select调用中不断弹出.即使坐骑没有变化.

我在这里错过了什么吗?

在此先感谢您的帮助!

男人5 proc:

/ proc/[pid]/mounts(自Linux 2.4.19起)

这是当前安装在进程的mount命名空间中的所有文件系统的列表.fstab(5)中记录了该文件的格式.从内核版本2.6.15开始,此文件是可轮询的:打开文件进行读取后,此文件中的更改(即文件系统挂载或卸载)会导致select(2)将文件描述符标记为可读,并轮询( 2)和epoll_wait(2)将文件标记为具有错误条件.

Dan*_*nin 13

linux内核中有一个描述该行为的错误修正:

SUSv3表示"常规文件应始终轮询TRUE以进行读写".见 http://www.opengroup.org/onlinepubs/009695399/functions/poll.html

所以,你必须使用POLLPRI |进行民意调查 POLLERR标志.像这样的东西:


     int mfd = open("/proc/mounts", O_RDONLY, 0);
     struct pollfd pfd;
     int rv;

     int changes = 0;
     pfd.fd = mfd;
     pfd.events = POLLERR | POLLPRI;
     pfd.revents = 0;
     while ((rv = poll(&pfd, 1, 5)) >= 0) {
          if (pfd.revents & POLLERR) {
               fprintf(stdout, "Mount points changed. %d.\n", changes++);
          }

          pfd.revents = 0;
          if (changes > 10) {
               exit(EXIT_FAILURE);
          }
     }