Skip to content

Commit

Permalink
fix: avoid *at functions for better compatibility
Browse files Browse the repository at this point in the history
As far as I can tell, `*at` syscalls are equivalent to their
counterparts when they're called relative to the current working
directory, so this shouldn't matter. We only _need_ the `*at` syscall
for `renameat2` to pass some flags.

fixes #246
  • Loading branch information
Stebalien committed Aug 6, 2023
1 parent d258544 commit 6797401
Showing 1 changed file with 7 additions and 6 deletions.
13 changes: 7 additions & 6 deletions src/file/imp/unix.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ use crate::util;
use std::path::Path;

#[cfg(not(target_os = "redox"))]
use rustix::fs::{linkat, renameat, unlinkat, AtFlags, CWD};
use rustix::fs::{link, rename, unlink};

pub fn create_named(path: &Path, open_options: &mut OpenOptions) -> io::Result<File> {
open_options.read(true).write(true).create_new(true);
Expand Down Expand Up @@ -103,12 +103,13 @@ pub fn reopen(_file: &File, _path: &Path) -> io::Result<File> {
#[cfg(not(target_os = "redox"))]
pub fn persist(old_path: &Path, new_path: &Path, overwrite: bool) -> io::Result<()> {
if overwrite {
renameat(CWD, old_path, CWD, new_path)?;
rename(old_path, new_path)?;
} else {
// On Linux, use `renameat_with` to avoid overwriting an existing name,
// if the kernel and the filesystem support it.
#[cfg(any(target_os = "android", target_os = "linux"))]
{
use rustix::fs::CWD;
use rustix::fs::{renameat_with, RenameFlags};
use rustix::io::Errno;
use std::sync::atomic::{AtomicBool, Ordering::Relaxed};
Expand All @@ -124,12 +125,12 @@ pub fn persist(old_path: &Path, new_path: &Path, overwrite: bool) -> io::Result<
}
}

// Otherwise use `linkat` to create the new filesystem name, which
// will fail if the name already exists, and then `unlinkat` to remove
// Otherwise use `link` to create the new filesystem name, which
// will fail if the name already exists, and then `unlink` to remove
// the old name.
linkat(CWD, old_path, CWD, new_path, AtFlags::empty())?;
link(old_path, new_path)?;
// Ignore unlink errors. Can we do better?
let _ = unlinkat(CWD, old_path, AtFlags::empty());
let _ = unlink(old_path);
}
Ok(())
}
Expand Down

0 comments on commit 6797401

Please sign in to comment.