linuxファイルシステム変化通知メカニズム-inotify
概要
inotify — a powerful yet simple file change notification system. inotifyはlinuxカーネル2.6.13以降にサポートされる特性で、ファイルシステムの変化を監視し、ファイルシステムの変化を監視した後、対応するアプリケーションに変化イベントを送信する機能です.inotifyはファイルシステムの変化通知メカニズムであり、ファイルの増加、削除などのイベントはすぐにユーザーに知らせることができ、このメカニズムは有名なデスクトップ検索エンジンプロジェクトbeagleが導入したものである.
イベントのモニタリング
ヘッダファイル:#include
Supported events suitable for MASK parameter of inotify_add_watch.
Events sent by the kernel.
Special flags.
All events which a program can wait on.
API関数
inotifyは主に以下のAPIを提供する.
(1)inotifyエンティティの作成
inotify_Init()カーネルにエンティティを作成する:inotify_デバイスを返し、ファイル記述子を返します.使用:int fd=inotify_init();
(2)モニタの作成
inotify_add_watch inotify_デバイス内のモニタリスト追加モニタ:inotify_watch. モニタを作成するには、(1)inotifyインスタンスinotify_デバイスのファイル記述子:fd(2)監視ターゲットパス:name(3)監視イベントリスト:maskが成功した場合、モニタ記述子wdを返します.そうでなければ-1を返します.
(3)モニタの削除
inotifyからデバイスのモニタリストからモニタを削除します.
イベントの読み込み
どのファイルシステムイベントが発生したかを決定するには、readシステム呼び出しでinotify_を読み込む必要があります.Init()が返すファイル記述子.read()は1つ以上のinotifyを返します.event.
inotify_eventはファイルシステムイベントです.ここでwdは監視対象のwatch記述子であり、maskはイベントマスクであり、nameは監視対象のパス名であり、lenはnameの長さである.各notify_eventの構造体サイズはsizeof(struct inotify_event)+lenです.inotifyでeventは次のことを示します.
(1)ターゲットの監視(ファイル/ディレクトリ)—>name,len(2)モニタ—>wd(3)ターゲットのイベントの監視—>mask
read()により、提供されるbufが十分大きい限り、複数のイベントを一度に取得することができる.size_t len = read(fd, buf , MAX_BUF_SIZE); lenは、実際に得られたイベントセットの合計長です.関数inotify()で返されるファイル記述子fdにselect()またはpoll()、epoll()を使用してもよいし、fdにioctlコマンドFIONREADを使用して現在のキューの長さを取得してもよい.close(fd)は、fdに追加されたwatchをすべて削除し、必要なクリーンアップを行います.
カーネル実装の概要
ディレクトリでもファイルでも、カーネルにはinode構造が1つ対応しており、inotifyシステムの再inode構造には2つのフィールドが追加されています:#ifdef CONFIG_INOTIFY struct list_head inotify_watches;/* watches on this inode */ struct semaphore inotify_sem;/* protects the watches list */#endif
Reference
1. documentation\filesystems\inotify.txt 2. include\linux\inotify.h 3. http://www.ibm.com/developerworks/cn/linux/l-inotifynew/4. http://tianyapiaozi.blogbus.com/logs/61783047.html
inotify — a powerful yet simple file change notification system. inotifyはlinuxカーネル2.6.13以降にサポートされる特性で、ファイルシステムの変化を監視し、ファイルシステムの変化を監視した後、対応するアプリケーションに変化イベントを送信する機能です.inotifyはファイルシステムの変化通知メカニズムであり、ファイルの増加、削除などのイベントはすぐにユーザーに知らせることができ、このメカニズムは有名なデスクトップ検索エンジンプロジェクトbeagleが導入したものである.
イベントのモニタリング
ヘッダファイル:#include
Supported events suitable for MASK parameter of inotify_add_watch.
/* File was accessed. 。*/
#define IN_ACCESS 0x00000001
/* FIle was modified. 。*/
#define IN_MODIFY 0x00000002
/* Metadata changed. , chmod、chown、touch 。*/
#define IN_ATTRIB 0x00000004
/* Writtable file was closed. 。*/
#define IN_CLOSE_WRITE 0x00000008
/* Unwrittable file closed. 。*/
#define IN_CLOSE_NOWRITE 0x00000010
/* 。*/
#define IN_CLOSE (IN_CLOSE_WRITE | IN_CLOSE_NOWRITE)
/* File was opened. 。*/
#define IN_OPEN 0x00000020
/* File was moved from X. , mv。*/
#define IN_MOVED_FROM 0x00000040
/* File was moved to Y. , mv、cp。*/
#define IN_MOVED_TO 0x00000080
/* Moves. 。*/
#define IN_MOVED (IN_MOVED_FROM | IN_MOVED_TO)
/* Subfile was created. 。*/
#define IN_CREATE 0x00000100
/* Subfile was deleted. , rm。*/
#define IN_DELETE 0x00000200
/* Self was deleted. , 。*/
#define IN_DELETE_SELF 0x00000400
/* Self was moved. , 。*/
#define IN_MOVE_SELF 0x00000800
Events sent by the kernel.
/* Backing fs was unmounted. unmount。*/
#define IN_UNMOUNT 0x00002000
/* Event queued overflowed. ,
* inotify_device max_events。*/
#define IN_Q_OVERFLOW 0x00004000
/* File was ignored. watch inotify
* , !*/
#define IN_IGNORED 0x00008000
Special flags.
/* Only watch the path if it is a directory. */
#define IN_ONLYDIR 0x01000000
/* Do not follow a sym link. */
#define IN_DONT_FOLLOW 0x02000000
/* Add to the mask of an already existing watch. */
#define IN_MASK_ADD 0x20000000
/* Event occurred against dir. */
#define IN_ISDIR 0x40000000
/* Only send event once. */
#define IN_ONESHOT 0x80000000
All events which a program can wait on.
#define IN_ALL_EVENTS (IN_ACCESS | IN_MODIFY | IN_ATTRIB | IN_CLOSE_WRITE \
| IN_CLOSE_NOWRITE | IN_OPEN | IN_MOVED_FROM | IN_MOVED_TO \
| IN_CREATE | IN_DELETE | IN_DELETE_SELF | IN_MOVE_SELF)
API関数
inotifyは主に以下のAPIを提供する.
(1)inotifyエンティティの作成
/* Create and initialize inotify instance. */
extern int inotify_init (void) __THROW;
inotify_Init()カーネルにエンティティを作成する:inotify_デバイスを返し、ファイル記述子を返します.使用:int fd=inotify_init();
(2)モニタの作成
/* Add watch of object NAME to inotify instance FD. Notify about events
* specified by MASK.
*/
extern int inotify_add_watch (int __fd, const char * __name, uint32_t __mask)
__THROW;
inotify_add_watch inotify_デバイス内のモニタリスト追加モニタ:inotify_watch. モニタを作成するには、(1)inotifyインスタンスinotify_デバイスのファイル記述子:fd(2)監視ターゲットパス:name(3)監視イベントリスト:maskが成功した場合、モニタ記述子wdを返します.そうでなければ-1を返します.
(3)モニタの削除
/* Remove the watch specified by WD from the inotify instance FD. */
extern int inotify_rm_watch (int __fd, uint32_t __wd) __THROW;
inotifyからデバイスのモニタリストからモニタを削除します.
イベントの読み込み
どのファイルシステムイベントが発生したかを決定するには、readシステム呼び出しでinotify_を読み込む必要があります.Init()が返すファイル記述子.read()は1つ以上のinotifyを返します.event.
/* Structure describing an inotify event. */
struct inotify_event
{
int wd; /* Watch descriptor. */
unit32_t mask; /* Watch mask */
unit32_t cookie; /* Cookie to synchronize two events. */
unit32_t len; /* Length (including NULLs) of name. */
char name __flexarr; /* Name. */
};
inotify_eventはファイルシステムイベントです.ここでwdは監視対象のwatch記述子であり、maskはイベントマスクであり、nameは監視対象のパス名であり、lenはnameの長さである.各notify_eventの構造体サイズはsizeof(struct inotify_event)+lenです.inotifyでeventは次のことを示します.
(1)ターゲットの監視(ファイル/ディレクトリ)—>name,len(2)モニタ—>wd(3)ターゲットのイベントの監視—>mask
read()により、提供されるbufが十分大きい限り、複数のイベントを一度に取得することができる.size_t len = read(fd, buf , MAX_BUF_SIZE); lenは、実際に得られたイベントセットの合計長です.関数inotify()で返されるファイル記述子fdにselect()またはpoll()、epoll()を使用してもよいし、fdにioctlコマンドFIONREADを使用して現在のキューの長さを取得してもよい.close(fd)は、fdに追加されたwatchをすべて削除し、必要なクリーンアップを行います.
カーネル実装の概要
Each inotify instance is represented by an inotify_handle structure.
Inotify's userspace consumers also have an inotify_device which is
associated with the inotify_handle, and on which events are queued.
Each watch is associated with an inotify_watch structure. Watches are chained
off of each associated inotify_handle and each associated inode.
See fs/notify/inotify/inotify_fsnotify.c and fs/notify/inotify/inotify_user.c for
the locking and lifetime rules.
ディレクトリでもファイルでも、カーネルにはinode構造が1つ対応しており、inotifyシステムの再inode構造には2つのフィールドが追加されています:#ifdef CONFIG_INOTIFY struct list_head inotify_watches;/* watches on this inode */ struct semaphore inotify_sem;/* protects the watches list */#endif
Reference
1. documentation\filesystems\inotify.txt 2. include\linux\inotify.h 3. http://www.ibm.com/developerworks/cn/linux/l-inotifynew/4. http://tianyapiaozi.blogbus.com/logs/61783047.html