From d084f7a0777b2479ee76dc7cd1b5f2a83be9471a Mon Sep 17 00:00:00 2001 From: Thibault Saunier Date: Thu, 2 May 2024 07:56:35 -0400 Subject: [PATCH] Workaround copying file returning EAGAIN on ZFS on mac OS Falling back to hard_link when that happens, retrying can lead to very long wait before copying works (up to 4secs in my tests) while hard_linking works straight away. Looks related to https://github.com/openzfsonosx/zfs/issues/809 Closes #13838 --- crates/cargo-util/Cargo.toml | 4 ++-- crates/cargo-util/src/paths.rs | 18 +++++++++++++++++- 2 files changed, 19 insertions(+), 3 deletions(-) diff --git a/crates/cargo-util/Cargo.toml b/crates/cargo-util/Cargo.toml index 28877eedaf76..43a6b0969d58 100644 --- a/crates/cargo-util/Cargo.toml +++ b/crates/cargo-util/Cargo.toml @@ -1,7 +1,7 @@ [package] name = "cargo-util" -version = "0.2.12" -rust-version = "1.77" # MSRV:1 +version = "0.2.13" +rust-version = "1.77" # MSRV:1 edition.workspace = true license.workspace = true homepage.workspace = true diff --git a/crates/cargo-util/src/paths.rs b/crates/cargo-util/src/paths.rs index 1172b002885d..f890390b0e08 100644 --- a/crates/cargo-util/src/paths.rs +++ b/crates/cargo-util/src/paths.rs @@ -585,7 +585,23 @@ fn _link_or_copy(src: &Path, dst: &Path) -> Result<()> { // Note that: fs::copy on macos is using CopyOnWrite (syscall fclonefileat) which should be // as fast as hardlinking. // See https://github.com/rust-lang/cargo/issues/10060 for the details - fs::copy(src, dst).map(|_| ()) + fs::copy(src, dst).map_or_else( + |e| { + if e.raw_os_error() + .map_or(false, |os_err| os_err == 35 /* libc::EAGAIN */) + { + tracing::info!("copy failed {e:?}. falling back to fs::hard_link"); + + // Working around an issue copying too fast with zfs (probably related to + // https://github.com/openzfsonosx/zfs/issues/809) + // See https://github.com/rust-lang/cargo/issues/13838 + fs::hard_link(src, dst) + } else { + Err(e) + } + }, + |_| Ok(()), + ) } else { fs::hard_link(src, dst) }