在我的C程序中,我正在逐行读取文件。
FILE *file = fopen("config.txt", "r");
if (file)
{
char *line;
size_t length;
size_t read;
int test_case_number = 0;
while ((read = getline(&line, &length, file)) != -1)
{
printf("%s", line);
}
}
else
{
fputs("The provided <PATH_TO_CONFIG FILE> does not exist.\n\n");
exit(1);
}
但是,当我读取此文件时,我想防止在读取过程中任何其他过程写入config.txt
。我该怎么办?
答案 0 :(得分:1)
在Linux中,您可以使用flock()(我关注):
在打开的文件上应用或删除咨询锁。
LOCK_EX 放置独占锁。只有一个进程可以容纳 给定文件在给定时间的排他锁。
但是,您需要使用open()
而不是fopen()
打开文件。
带有抽象示例的问题:flock(): removing locked file without race condition?或选中此example。
重要提示:@JonathanLeffler评论说:“注意“咨询锁”一词-这意味着,如果写入过程未测试该锁,它将能够进行写入。在类似POSIX的系统上,您可以使用{{ 1}}或flock()
或lockf()
通过fcntl()
“锁定文件描述符。
答案 1 :(得分:1)
如果您必须“捍卫”自己的流程或“行为良好”的流程,那么您想使用flock
:
fp = fopen(fileName, fileMode);
if (fp != NULL) {
flock(fileno(fp), LOCK_EX);
...
fclose(fp); fp = NULL;
}
但是这些锁仅是 advisory ,也就是说,任何其他进程都可以选择忽略它们。还是不用费心检查。我刚刚尝试创建一个文件,将其打开并用LOCK_EX锁定,然后休眠60秒。在这段时间里,另一个过程可以自由地对文件执行任何操作(Linux,Ubuntu 18.04-LTS)。
但是如果您需要强制性锁定,则由于内核必须配合,因此并非在所有平台上都可用。 Here您将找到有关如何使用Linux中的 limited 强制性锁支持的描述和示例。
另一方面,在Windows中这是自动的:
Windows默认为自动强制性文件锁定。 UNIX默认为手动, 合作文件锁定。在这两种情况下,都可以覆盖默认值,但在两种情况下 通常情况并非如此。 (source)。
一种解决方法可以是暂时将正在处理的文件重命名为唯一的名称,可能会使用旧名称创建一个空文件,然后在完成后将其重命名;或按上述方式复制文件,并保留副本供其他程序读取。拒绝写入也可以通过更改文件权限来实现。这些解决方案需要处理一些边缘情况,例如在您将进程恢复原状之前,您的进程崩溃或机器挂起的位置。