实现Linux文件系统的监控——Inotify学习笔记
Inotify简介
Inotify是Linux中用于监控文件系统变化的API,自Linux 2.6.13开始集成到Linux内核中,并取代了以往的dnotify。该API可以实现用非轮询的方式,近似实时地监控目录或文件发生的变化。
利用Inotify可以十分方便地实现诸如文件实时同步、目录索引自动更新、配置文件自动重加载等功能。在Linux中可以通过man 7 inotify
查阅Inotify的手册。
API使用简介
Inotify API由头文件<sys/inotify.h>
提供,其中包括函数inotify_init(2)
inotify_init1(2)
inotify_add_watch(2)
inotify_rm_watch(2)
。
inotify_init(2)
和inotify_init1(2)
功能相似,若成功调用可以初始化一个inotify的实例,并返回一个用于读取文件系统事件的文件描述符,若失败则会返回-1。
不同之处在于,后者提供了一个参数。当传入0时,二者没有区别,但传入IN_NONBLOCK
IN_CLOEXEC
掩码后会对返回的文件描述符提供额外的控制功能,这两个掩码分别提供与fcntl(2)
中的O_NONBLOCK
和open(2)
中的FD_CLOEXEC
相似的功能,在此不对这两个掩码的功能作详细介绍。
在成功调用inotify_init(2)
或inotify_init1(2)
后,其返回值作为文件描述符,可在后续使用read(2)
系统调用来读取文件系统监控事件的信息,并且该读取是阻塞式的,当没有事件发生时,read(2)
将不会返回。
inotify_add_watch(2)
和inotify_rm_watch(2)
分别用于从监控列表中添加和删除目录/文件项。inotify_add_watch(2)
接受参数为inotify实例的文件描述符、需要监控的目标文件/目录路径,以及需要监控的事件掩码,成功调用后返回一个监控描述符(Watch descriptor),对应于目标路径在文件系统中的inode对象,若失败则会返回-1并设置errno。inotify_rm_watch(2)
接受参数为inotify实例的文件描述符和监控文件或目录的监控描述符,可以停止监控对应的文件或目录。
对于一个文件或目录,可以使用位或运算符合并掩码来同时监控多个事件。可监控事件列表如下:
事件掩码 | 事件描述 | 事件掩码 | 事件描述 | 事件掩码 | 事件描述 |
---|---|---|---|---|---|
IN_ACCESS | 访问文件 | IN_ATTRIB | 文件属性更改(权限、所有权等) | IN_CLOSE_WRITE | 关闭打开时设置为可写的文件 |
IN_CLOSE_NOWRITE | 关闭打开时未设置为可写的文件 | IN_CREATE | 创建文件或目录 | IN_DELETE | 删除文件或目录 |
IN_DELETE_SELF | 删除监控中的文件或目录本身 | IN_MODIFY | 修改文件 | IN_MOVE_SELF | 移动监控中的文件或目录本身 |
IN_MOVED_FROM | 移出或重命名目录中包含的文件 | IN_MOVED_TO | 移入或重命名目录中包含的文件 | IN_OPEN | 打开文件或目录 |
在设置监控成功后,通过read(2)
系统调用从inotify实例提供的文件描述符中读取文件系统监控事件的信息,该信息使用inotify_event
结构体来记录,该结构体的声明如下:
1 |
|
示例代码
1 |
|