如何持久地重命名POSIX中的文件? [英] How to durably rename a file in POSIX?

查看:273
本文介绍了如何持久地重命名POSIX中的文件?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在POSIX文件系统中持久地重命名文件的方法是什么?特别想知道目录上的fsync。 (如果这取决于OS / FS,我在问Linux和ext3 / ext4)。

What's the correct way to durably rename a file in a POSIX file system? Specifically wondering about fsyncs on the directories. (If this depends on the OS/FS, I'm asking about Linux and ext3/ext4).

注意:还有其他问题在StackOverflow上关于持久性重命名,但是AFAICT他们没有解决fsync-ing目录(这对我来说很重要 - 我甚至不修改文件数据)。

Note: there are other questions on StackOverflow about durable renames, but AFAICT they don't address fsync-ing the directories (which is what matters to me - I'm not even modifying file data).

我目前有(在Python中):

I currently have (in Python):

dstdirfd = open(dstdirpath, O_DIRECTORY|O_RDONLY)
rename(srcdirpath + '/' + filename, dstdirpath + '/' + filename)
fsync(dstdirfd)

具体问题


  • 这是否也隐含地将fsync的源目录?或者我可能会在电源循环后最终显示在两个目录中的文件(意味着我必须检查硬链接计数并手动执行恢复),即不可能保证持久的原子移动操作?

  • 如果我fsync源目录而不是目标目录,那么还会隐含地fsync目标目录?

  • 是否有任何有用的相关的测试/调试/学习工具(故障注入器,内省工具,模拟文件系统等)?

  • Does this also implicitly fsync the source directory? Or might I end up with the file showing up in both directories after a power cycle (meaning I'd have to check the hard link count and manually perform recovery), i.e. it's impossible to guarantee a durably atomic move operation?
  • If I fsync the source directory instead of the destination directory, will that also implicitly fsync the destination directory?
  • Are there any useful related testing/debugging/learning tools (fault injectors, introspection tools, mock filesystems, etc.)?

提前感谢。 p>

Thanks in advance.

推荐答案

POSIX定义重命名功能必须是原子:

POSIX defines that the rename function must be atomic:


http://pubs.opengroup.org/onlinepubs/009695399/函数/ rename.html

所以如果你重命名(A,B),在任何情况下你都不会看到状态该文件位于两个目录或两个目录中。总是会有一个,无论你使用fsync()或系统是否崩溃。

So if you rename(A, B), under no circumstances should you ever see a state with the file in both directories or neither directory. There will always be exactly one, no matter what you do with fsync() or whether the system crashes.

但是这并不能解决确保重命名的问题()操作是耐用的。 POSIX回答这个问题:

But that doesn't solve the problem of making sure the rename() operation is durable. POSIX answers this question:


如果定义了_POSIX_SYNCHRONIZED_IO,fsync()函数将强制与文件相关联的所有当前排队的I / O操作由文件描述符fildes指示为同步的I / O完成状态。所有I / O操作应按照同步I / O文件完整性完成定义完成。

If _POSIX_SYNCHRONIZED_IO is defined, the fsync() function shall force all currently queued I/O operations associated with the file indicated by file descriptor fildes to the synchronized I/O completion state. All I/O operations shall be completed as defined for synchronized I/O file integrity completion.

(从 http: //pubs.opengroup.org/onlinepubs/009695399/functions/fsync.html

所以如果你fsync )一个目录,等待重命名操作必须在返回的时候传输到磁盘。任何一个目录的fsync()都应该是足够的,因为重命名()操作的原子性将要求两个目录的更改都是原子地相同的。

So if you fsync() a directory, pending rename operations must be transferred to disk by the time this returns. fsync() of either directory should be sufficient because atomicity of the rename() operation would require that both directories' changes be syncked atomically.

最后,与索赔相反在另一个答案中提到的博客文章中,其理由解释如下:

Finally, in contrast to the claim in the blog post mentioned in another answer, the rationale for this explains the following:


fsync()函数旨在强制实体从缓冲区高速缓存写入数据,并确保在系统崩溃或其他故障之后将所有数据直到fsync()调用时都记录在磁盘上。由于这里没有定义缓冲区缓存,系统崩溃,物理写入和非易失性存储的概念,所以措辞必须更抽象。

The fsync() function is intended to force a physical write of data from the buffer cache, and to assure that after a system crash or other failure that all data up to the time of the fsync() call is recorded on the disk. Since the concepts of "buffer cache", "system crash", "physical write", and "non-volatile storage" are not defined here, the wording has to be more abstract.

声称符合POSIX的系统,并认为它是正确的行为(即不是错误或硬件故障)来完成fsync(),并且不会在系统崩溃中持续这些更改

A system that claimed to be POSIX compliant and that considered it correct behavior (i.e. not a bug or hardware failure) to complete an fsync() and not persist those changes across a system crash would have to be deliberately misrepresenting itself with respect to the spec.

(使用附加信息更新:Linux特定与便携式行为)

(updated with additional info re: Linux-specific vs. portable behavior)

这篇关于如何持久地重命名POSIX中的文件?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆