diff --git a/src/tools/run-make-support/src/lib.rs b/src/tools/run-make-support/src/lib.rs index b920f9a07db87..6a89a75d71591 100644 --- a/src/tools/run-make-support/src/lib.rs +++ b/src/tools/run-make-support/src/lib.rs @@ -169,6 +169,38 @@ pub fn cwd() -> PathBuf { env::current_dir().unwrap() } +// FIXME(Oneirical): This will no longer be required after compiletest receives the ability +// to manipulate read-only files. See https://github.com/rust-lang/rust/issues/126334 +/// Ensure that the path P is read-only while the test runs, and restore original permissions +/// at the end so compiletest can clean up. +/// This will panic on Windows if the path is a directory (as it would otherwise do nothing) +#[track_caller] +pub fn test_while_readonly, F: FnOnce() + std::panic::UnwindSafe>( + path: P, + closure: F, +) { + let path = path.as_ref(); + if is_windows() && path.is_dir() { + eprintln!("This helper function cannot be used on Windows to make directories readonly."); + eprintln!( + "See the official documentation: + https://doc.rust-lang.org/std/fs/struct.Permissions.html#method.set_readonly" + ); + panic!("`test_while_readonly` on directory detected while on Windows."); + } + let metadata = fs_wrapper::metadata(&path); + let original_perms = metadata.permissions(); + + let mut new_perms = original_perms.clone(); + new_perms.set_readonly(true); + fs_wrapper::set_permissions(&path, new_perms); + + let success = std::panic::catch_unwind(closure); + + fs_wrapper::set_permissions(&path, original_perms); + success.unwrap(); +} + /// Use `cygpath -w` on a path to get a Windows path string back. This assumes that `cygpath` is /// available on the platform! #[track_caller] diff --git a/tests/run-make/inaccessible-temp-dir/rmake.rs b/tests/run-make/inaccessible-temp-dir/rmake.rs index 25c9d363820dc..be24e47b6decc 100644 --- a/tests/run-make/inaccessible-temp-dir/rmake.rs +++ b/tests/run-make/inaccessible-temp-dir/rmake.rs @@ -13,32 +13,26 @@ // use a directory with non-existing parent like `/does-not-exist/output`. // See https://github.com/rust-lang/rust/issues/66530 -//@ only-linux -// Reason: set_mode is only available on Unix - //@ ignore-arm // Reason: linker error on `armhf-gnu` +//@ ignore-windows +// Reason: `set_readonly` has no effect on directories +// and does not prevent modification. -use run_make_support::{fs_wrapper, rustc}; +use run_make_support::{fs_wrapper, rustc, test_while_readonly}; fn main() { // Create an inaccessible directory. fs_wrapper::create_dir("inaccessible"); - let meta = fs_wrapper::metadata("inaccessible"); - let mut perms = meta.permissions(); - perms.set_mode(0o000); // Lock down the directory. - fs_wrapper::set_permissions("inaccessible", perms); - - // Run rustc with `-Z temps-dir` set to a directory *inside* the inaccessible one, - // so that it can't create `tmp`. - rustc() - .input("program.rs") - .arg("-Ztemps-dir=inaccessible/tmp") - .run_fail() - .assert_stderr_contains( - "failed to find or create the directory specified by `--temps-dir`", - ); - - perms.set_mode(0o666); // Unlock the directory, so that compiletest can delete it. - fs_wrapper::set_permissions("inaccessible", perms); + test_while_readonly("inaccessible", || { + // Run rustc with `-Z temps-dir` set to a directory *inside* the inaccessible one, + // so that it can't create `tmp`. + rustc() + .input("program.rs") + .arg("-Ztemps-dir=inaccessible/tmp") + .run_fail() + .assert_stderr_contains( + "failed to find or create the directory specified by `--temps-dir`", + ); + }); } diff --git a/tests/run-make/output-with-hyphens/rmake.rs b/tests/run-make/output-with-hyphens/rmake.rs index 21c003c628b9e..79deb772bc5df 100644 --- a/tests/run-make/output-with-hyphens/rmake.rs +++ b/tests/run-make/output-with-hyphens/rmake.rs @@ -7,11 +7,11 @@ //@ ignore-cross-compile -use run_make_support::{path, rustc}; +use run_make_support::{bin_name, path, rust_lib_name, rustc}; fn main() { rustc().input("foo-bar.rs").crate_type("bin").run(); assert!(path(bin_name("foo-bar")).exists()); rustc().input("foo-bar.rs").crate_type("lib").run(); - assert!(path(bin_name("libfoo_bar.rlib")).exists()); + assert!(path(rust_lib_name("foo_bar")).exists()); } diff --git a/tests/run-make/parallel-rustc-no-overwrite/rmake.rs b/tests/run-make/parallel-rustc-no-overwrite/rmake.rs index 40c6ab7ed5ebf..3f032cf3762a9 100644 --- a/tests/run-make/parallel-rustc-no-overwrite/rmake.rs +++ b/tests/run-make/parallel-rustc-no-overwrite/rmake.rs @@ -10,15 +10,16 @@ use std::sync::{Arc, Barrier}; use std::thread; fn main() { + fs_wrapper::create_file("lib.rs"); let barrier = Arc::new(Barrier::new(2)); let handle = { let barrier = Arc::clone(&barrier); thread::spawn(move || { barrier.wait(); - rustc().crate_type("lib").arg("-Ztemps-dir=temp1").input("lib.rs"); + rustc().crate_type("lib").arg("-Ztemps-dir=temp1").input("lib.rs").run(); }) }; barrier.wait(); - rustc().crate_type("staticlib").arg("-Ztemps-dir=temp2").input("lib.rs"); + rustc().crate_type("staticlib").arg("-Ztemps-dir=temp2").input("lib.rs").run(); handle.join().expect("lib thread panicked"); }