jam*_*dge 6 c c++ linux filesystems inotify
我正在使用类似下面的代码来检查文件是否在继续之前已经创建了,事情是文件在文件浏览器中显示的内容很多,然后才被stat检测到...这样做有问题吗?
//... do something
struct stat buf;
while(stat("myfile.txt", &buf))
sleep(1);
//... do something else
Run Code Online (Sandbox Code Playgroud)
或者有更好的方法来检查文件是否存在?
小智 4
“stat”系统调用正在收集有关文件的不同信息,例如指向该文件的硬链接数量或其“inode”号。您可能想查看“access”系统调用,您可以使用它仅通过在“mode”中指定“F_OK”标志来执行存在检查。
但是,您的代码有一个小问题。每次检查尚不存在的文件时,它都会使进程休眠一秒钟。为了避免这种情况,您必须按照 Jerry Coffin 的建议使用inotify API,以便在您等待的文件存在时得到内核通知。请记住,如果文件已经存在,inotify 不会通知您,因此实际上您需要同时使用“access”和“inotify”以避免在文件创建后开始监视文件时出现竞争情况。
没有更好或更快的方法来检查文件是否存在。如果您的文件浏览器显示文件的速度仍然比该程序检测到的速度稍快,则 Greg Hewgill 关于重命名的想法可能正在发生。
下面是一个 C++ 代码示例,它设置一个 inotify 监视,检查文件是否已存在并等待它,否则:
#include <cstdio>
#include <cstring>
#include <string>
#include <unistd.h>
#include <sys/inotify.h>
int
main ()
{
const std::string directory = "/tmp";
const std::string filename = "test.txt";
const std::string fullpath = directory + "/" + filename;
int fd = inotify_init ();
int watch = inotify_add_watch (fd, directory.c_str (),
IN_MODIFY | IN_CREATE | IN_MOVED_TO);
if (access (fullpath.c_str (), F_OK) == 0)
{
printf ("File %s exists.\n", fullpath.c_str ());
return 0;
}
char buf [1024 * (sizeof (inotify_event) + 16)];
ssize_t length;
bool isCreated = false;
while (!isCreated)
{
length = read (fd, buf, sizeof (buf));
if (length < 0)
break;
inotify_event *event;
for (size_t i = 0; i < static_cast<size_t> (length);
i += sizeof (inotify_event) + event->len)
{
event = reinterpret_cast<inotify_event *> (&buf[i]);
if (event->len > 0 && filename == event->name)
{
printf ("The file %s was created.\n", event->name);
isCreated = true;
break;
}
}
}
inotify_rm_watch (fd, watch);
close (fd);
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
5514 次 |
| 最近记录: |