Linux 如何使用readdir/inotify避免这种竞争条件?

Linux 如何使用readdir/inotify避免这种竞争条件?,linux,inotify,readdir,Linux,Inotify,Readdir,假设我想对目录中的所有文件调用某个命令,并设置一个监视以对在该目录中创建的所有文件调用该命令。如果我这样做: while( ( sdi = readdir( d )) != NULL ) { ... } closedir( d ); /* Files created here will be missed */ inotify_add_watch( ... ); 然后可能会丢失一些文件。如果我调用inotify\u add\u watch() 在readdir()之前,可以对文件执行两次操作(

假设我想对目录中的所有文件调用某个命令,并设置一个监视以对在该目录中创建的所有文件调用该命令。如果我这样做:

while( ( sdi = readdir( d )) != NULL ) { ... }
closedir( d );
/* Files created here will be missed */
inotify_add_watch( ... );
然后可能会丢失一些文件。如果我调用inotify\u add\u watch() 在readdir()之前,可以对文件执行两次操作(这需要 一个相当多的基础设施,以防止两次行动,似乎 边缘情况将难以处理)。有没有一个简单的方法可以避免 必须记录readdir循环期间处理的所有文件的名称,以及 是否将这些名称与inotify_事件结构中返回的名称进行比较?我可以 尽可能减少与以下内容的必要比较:

while( ( sdi = readdir( d )) != NULL ) { ... }
inotify_add_watch( ... );
while( ( sdi = readdir( d )) != NULL ) { /* record name */ ... }
closedir( d );

通常,第二个readdir()循环不会做任何事情,但这感觉像是一个糟糕的黑客行为。

你就是做不到。你攻击的次数越多,你得到的比赛条件就越多

最简单的实际工作解决方案是在使用
opendir()
之前设置手表,并保留已使用名称(或其哈希)的列表(集合)

但这也不是完美的。用户可以在文本编辑器中打开文件;您修复了它,用户保存了它,目录中仍然包含未修复的文件,尽管它在您的列表中


最好的方法是让程序能够通过内容实际区分使用过的文件。换句话说,您可以设置watch,在
readdir()
results上调用command,然后在inotify results上调用它,并让命令本身知道文件是否已经好了。

我实际上不记得问过这个问题,而且我还有几年的经验,我现在会回答说,你甚至不应该试图避免比赛条件。确保在循环中所做的任何事情都是幂等的,这样您就不必在意是否多次执行这些操作。