-
Notifications
You must be signed in to change notification settings - Fork 13.9k
Win: Use POSIX rename semantics for std::fs::rename if available
#131072
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Win: Use POSIX rename semantics for std::fs::rename if available
#131072
Conversation
…available Windows 10 1601 introduced `FileRenameInfoEx` as well as `FILE_RENAME_FLAG_POSIX_SEMANTICS`, allowing for atomic renaming. If it isn't supported, we fall back to `FileRenameInfo`. This commit also replicates `MoveFileExW`'s behavior of checking whether the source file is a mount point and moving the mount point instead of resolving the target path.
… opened and for renaming over a non-empty directory
|
r? @ChrisDenton rustbot has assigned @ChrisDenton. Use |
|
This looks good to me.
Yes, I'd prefer if we just did that. Doing so doesn't appear to require anything special and the less the |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this is looking good. Just a couple of nits.
|
Thanks! @bors r+ |
Windows 10 1601 introduced
FileRenameInfoExas well asFILE_RENAME_FLAG_POSIX_SEMANTICS, allowing for atomic renaming and renaming if the target file is has already been opened withFILE_SHARE_DELETE, in which case the file gets renamed on disk while the open file handle still refers to the old file, just like in POSIX. This resolves #123985, where atomic renaming proved difficult to impossible due to race conditions.If
FileRenameInfoExisn't available due to missing support from the underlying filesystem or missing OS support, the renaming is retried withFileRenameInfo, which matches the behavior ofMoveFileEx.This PR also manually replicates parts of
MoveFileEx's internal logic, as reverse-engineered from the disassembly: If the source file is a reparse point and said reparse point is a mount point, the mount point itself gets renamed; otherwise the reparse point is resolved and the result renamed.Notes:
win7target doesn't bother withFileRenameInfoExat all; it's probably desirable to remove that special casing and tryFileRenameInfoExanyway if it doesn't exist, in case the binary is run on newer OS versions.Fixes #123985