From 5765819226ac8d4433dd8c99ba1dabd58e427485 Mon Sep 17 00:00:00 2001 From: David Tolnay Date: Tue, 26 Apr 2022 15:00:36 -0700 Subject: [PATCH 01/14] Add test of temporaries inside format_args of core/std macros --- src/test/ui/macros/format-args-temporaries.rs | 70 +++++++++++++++++++ 1 file changed, 70 insertions(+) create mode 100644 src/test/ui/macros/format-args-temporaries.rs diff --git a/src/test/ui/macros/format-args-temporaries.rs b/src/test/ui/macros/format-args-temporaries.rs new file mode 100644 index 0000000000000..ddd4c9754bfa4 --- /dev/null +++ b/src/test/ui/macros/format-args-temporaries.rs @@ -0,0 +1,70 @@ +// check-pass + +use std::fmt::{self, Display}; + +struct Mutex; + +impl Mutex { + fn lock(&self) -> MutexGuard { + MutexGuard(self) + } +} + +struct MutexGuard<'a>(&'a Mutex); + +impl<'a> Drop for MutexGuard<'a> { + fn drop(&mut self) { + // Empty but this is a necessary part of the repro. Otherwise borrow + // checker is fine with 'a dangling at the time that MutexGuard goes out + // of scope. + } +} + +impl<'a> MutexGuard<'a> { + fn write_fmt(&self, _args: fmt::Arguments) {} +} + +impl<'a> Display for MutexGuard<'a> { + fn fmt(&self, _formatter: &mut fmt::Formatter) -> fmt::Result { + Ok(()) + } +} + +fn main() { + let _write = { + let out = Mutex; + let mutex = Mutex; + write!(out.lock(), "{}", mutex.lock()) /* no semicolon */ + }; + + let _writeln = { + let out = Mutex; + let mutex = Mutex; + writeln!(out.lock(), "{}", mutex.lock()) /* no semicolon */ + }; + + let _print = { + let mutex = Mutex; + print!("{}", mutex.lock()) /* no semicolon */ + }; + + let _println = { + let mutex = Mutex; + println!("{}", mutex.lock()) /* no semicolon */ + }; + + let _eprint = { + let mutex = Mutex; + eprint!("{}", mutex.lock()) /* no semicolon */ + }; + + let _eprintln = { + let mutex = Mutex; + eprintln!("{}", mutex.lock()) /* no semicolon */ + }; + + let _panic = { + let mutex = Mutex; + panic!("{}", mutex.lock()) /* no semicolon */ + }; +} From 6f10c0ac1a17130a454d65362c9cd59239c71812 Mon Sep 17 00:00:00 2001 From: David Tolnay Date: Tue, 26 Apr 2022 15:16:23 -0700 Subject: [PATCH 02/14] Make write/print macros eagerly drop temporaries --- library/core/src/macros/mod.rs | 14 ++++++++------ library/std/src/macros.rs | 24 ++++++++++++------------ 2 files changed, 20 insertions(+), 18 deletions(-) diff --git a/library/core/src/macros/mod.rs b/library/core/src/macros/mod.rs index 83f33ca007af1..88f225747d946 100644 --- a/library/core/src/macros/mod.rs +++ b/library/core/src/macros/mod.rs @@ -496,9 +496,10 @@ macro_rules! r#try { #[stable(feature = "rust1", since = "1.0.0")] #[cfg_attr(not(test), rustc_diagnostic_item = "write_macro")] macro_rules! write { - ($dst:expr, $($arg:tt)*) => { - $dst.write_fmt($crate::format_args!($($arg)*)) - }; + ($dst:expr, $($arg:tt)*) => {{ + let result = $dst.write_fmt($crate::format_args!($($arg)*)); + result + }}; } /// Write formatted data into a buffer, with a newline appended. @@ -553,9 +554,10 @@ macro_rules! writeln { ($dst:expr $(,)?) => { $crate::write!($dst, "\n") }; - ($dst:expr, $($arg:tt)*) => { - $dst.write_fmt($crate::format_args_nl!($($arg)*)) - }; + ($dst:expr, $($arg:tt)*) => {{ + let result = $dst.write_fmt($crate::format_args_nl!($($arg)*)); + result + }}; } /// Indicates unreachable code. diff --git a/library/std/src/macros.rs b/library/std/src/macros.rs index c597fb5df45d2..1495dfc1409e2 100644 --- a/library/std/src/macros.rs +++ b/library/std/src/macros.rs @@ -60,9 +60,9 @@ macro_rules! panic { #[cfg_attr(not(test), rustc_diagnostic_item = "print_macro")] #[allow_internal_unstable(print_internals)] macro_rules! print { - ($($arg:tt)*) => { - $crate::io::_print($crate::format_args!($($arg)*)) - }; + ($($arg:tt)*) => {{ + $crate::io::_print($crate::format_args!($($arg)*)); + }}; } /// Prints to the standard output, with a newline. @@ -99,9 +99,9 @@ macro_rules! println { () => { $crate::print!("\n") }; - ($($arg:tt)*) => { - $crate::io::_print($crate::format_args_nl!($($arg)*)) - }; + ($($arg:tt)*) => {{ + $crate::io::_print($crate::format_args_nl!($($arg)*)); + }}; } /// Prints to the standard error. @@ -130,9 +130,9 @@ macro_rules! println { #[cfg_attr(not(test), rustc_diagnostic_item = "eprint_macro")] #[allow_internal_unstable(print_internals)] macro_rules! eprint { - ($($arg:tt)*) => { - $crate::io::_eprint($crate::format_args!($($arg)*)) - }; + ($($arg:tt)*) => {{ + $crate::io::_eprint($crate::format_args!($($arg)*)); + }}; } /// Prints to the standard error, with a newline. @@ -164,9 +164,9 @@ macro_rules! eprintln { () => { $crate::eprint!("\n") }; - ($($arg:tt)*) => { - $crate::io::_eprint($crate::format_args_nl!($($arg)*)) - }; + ($($arg:tt)*) => {{ + $crate::io::_eprint($crate::format_args_nl!($($arg)*)); + }}; } /// Prints and returns the value of a given expression for quick and dirty From a03f15a276b407197b78c4cf304801405f6d5e33 Mon Sep 17 00:00:00 2001 From: David Tolnay Date: Tue, 26 Apr 2022 15:44:39 -0700 Subject: [PATCH 03/14] Bless tests following write/print macros change --- src/test/pretty/dollar-crate.pp | 2 +- src/test/ui/macros/trace-macro.stderr | 2 +- .../ui/pattern/usefulness/tuple-struct-nonexhaustive.stderr | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/test/pretty/dollar-crate.pp b/src/test/pretty/dollar-crate.pp index 0c96fb593e659..3af37955f2380 100644 --- a/src/test/pretty/dollar-crate.pp +++ b/src/test/pretty/dollar-crate.pp @@ -9,5 +9,5 @@ // pp-exact:dollar-crate.pp fn main() { - ::std::io::_print(::core::fmt::Arguments::new_v1(&["rust\n"], &[])); + { ::std::io::_print(::core::fmt::Arguments::new_v1(&["rust\n"], &[])); }; } diff --git a/src/test/ui/macros/trace-macro.stderr b/src/test/ui/macros/trace-macro.stderr index c8a0fd684304e..43272248c280e 100644 --- a/src/test/ui/macros/trace-macro.stderr +++ b/src/test/ui/macros/trace-macro.stderr @@ -5,5 +5,5 @@ LL | println!("Hello, World!"); | ^^^^^^^^^^^^^^^^^^^^^^^^^ | = note: expanding `println! { "Hello, World!" }` - = note: to `$crate :: io :: _print($crate :: format_args_nl! ("Hello, World!"))` + = note: to `{ $crate :: io :: _print($crate :: format_args_nl! ("Hello, World!")) ; }` diff --git a/src/test/ui/pattern/usefulness/tuple-struct-nonexhaustive.stderr b/src/test/ui/pattern/usefulness/tuple-struct-nonexhaustive.stderr index e2a65ff852404..fc0430d06fa1c 100644 --- a/src/test/ui/pattern/usefulness/tuple-struct-nonexhaustive.stderr +++ b/src/test/ui/pattern/usefulness/tuple-struct-nonexhaustive.stderr @@ -12,7 +12,7 @@ LL | struct Foo(isize, isize); = note: the matched value is of type `Foo` help: ensure that all possible cases are being handled by adding a match arm with a wildcard pattern or an explicit pattern as shown | -LL ~ Foo(2, b) => println!("{}", b), +LL ~ Foo(2, b) => println!("{}", b) LL + Foo(_, _) => todo!() | From b2316c1a88b09dfebe7cabf889af9ceab8fef5f9 Mon Sep 17 00:00:00 2001 From: Collin Baker Date: Wed, 27 Apr 2022 17:11:14 -0400 Subject: [PATCH 04/14] Add test skip support libtest already supports a "--skip SUBSTRING" arg which excludes any test names matching SUBSTRING. This adds a "--skip" argument to compiletest and bootstrap which is forwarded to libtest. --- src/bootstrap/builder/tests.rs | 2 ++ src/bootstrap/flags.rs | 21 +++++++++++++++++++-- src/tools/compiletest/src/common.rs | 4 ++++ src/tools/compiletest/src/main.rs | 6 +++++- 4 files changed, 30 insertions(+), 3 deletions(-) diff --git a/src/bootstrap/builder/tests.rs b/src/bootstrap/builder/tests.rs index 3b6cd7564f08a..b3ccba2e48d6d 100644 --- a/src/bootstrap/builder/tests.rs +++ b/src/bootstrap/builder/tests.rs @@ -495,6 +495,7 @@ mod dist { config.stage = 0; config.cmd = Subcommand::Test { paths: vec!["library/std".into()], + skip: vec![], test_args: vec![], rustc_args: vec![], fail_fast: true, @@ -565,6 +566,7 @@ mod dist { let mut config = configure(&["A"], &["A"]); config.cmd = Subcommand::Test { paths: vec![], + skip: vec![], test_args: vec![], rustc_args: vec![], fail_fast: true, diff --git a/src/bootstrap/flags.rs b/src/bootstrap/flags.rs index 58571ea129c19..4cd835ade6421 100644 --- a/src/bootstrap/flags.rs +++ b/src/bootstrap/flags.rs @@ -111,6 +111,7 @@ pub enum Subcommand { compare_mode: Option, pass: Option, run: Option, + skip: Vec, test_args: Vec, rustc_args: Vec, fail_fast: bool, @@ -261,6 +262,7 @@ To learn more about a subcommand, run `./x.py -h`", match subcommand { Kind::Test => { opts.optflag("", "no-fail-fast", "Run all tests regardless of failure"); + opts.optmulti("", "skip", "skips tests matching SUBSTRING, if supported by test tool. May be passed multiple times", "SUBSTRING"); opts.optmulti( "", "test-args", @@ -545,6 +547,7 @@ Arguments: compare_mode: matches.opt_str("compare-mode"), pass: matches.opt_str("pass"), run: matches.opt_str("run"), + skip: matches.opt_strs("skip"), test_args: matches.opt_strs("test-args"), rustc_args: matches.opt_strs("rustc-args"), fail_fast: !matches.opt_present("no-fail-fast"), @@ -689,12 +692,26 @@ impl Subcommand { } pub fn test_args(&self) -> Vec<&str> { + let mut args = vec![]; + + match *self { + Subcommand::Test { ref skip, .. } => { + for s in skip { + args.push("--skip"); + args.push(s.as_str()); + } + } + _ => (), + }; + match *self { Subcommand::Test { ref test_args, .. } | Subcommand::Bench { ref test_args, .. } => { - test_args.iter().flat_map(|s| s.split_whitespace()).collect() + args.extend(test_args.iter().flat_map(|s| s.split_whitespace())) } - _ => Vec::new(), + _ => (), } + + args } pub fn rustc_args(&self) -> Vec<&str> { diff --git a/src/tools/compiletest/src/common.rs b/src/tools/compiletest/src/common.rs index 2cb368c688188..ea13ae13208ad 100644 --- a/src/tools/compiletest/src/common.rs +++ b/src/tools/compiletest/src/common.rs @@ -246,6 +246,10 @@ pub struct Config { /// Only run tests that match these filters pub filters: Vec, + /// Skip tests tests matching these substrings. Corresponds to + /// `test::TestOpts::skip`. `filter_exact` does not apply to these flags. + pub skip: Vec, + /// Exactly match the filter, rather than a substring pub filter_exact: bool, diff --git a/src/tools/compiletest/src/main.rs b/src/tools/compiletest/src/main.rs index 3d11ea21acf9f..e23cccf6cd129 100644 --- a/src/tools/compiletest/src/main.rs +++ b/src/tools/compiletest/src/main.rs @@ -91,6 +91,7 @@ pub fn parse_config(args: Vec) -> Config { ) .optopt("", "run", "whether to execute run-* tests", "auto | always | never") .optflag("", "ignored", "run tests marked as ignored") + .optmulti("", "skip", "skip tests matching SUBSTRING. Can be passed multiple times", "SUBSTRING") .optflag("", "exact", "filters match exactly") .optopt( "", @@ -236,6 +237,7 @@ pub fn parse_config(args: Vec) -> Config { debugger: None, run_ignored, filters: matches.free.clone(), + skip: matches.opt_strs("skip"), filter_exact: matches.opt_present("exact"), force_pass_mode: matches.opt_str("pass").map(|mode| { mode.parse::() @@ -312,6 +314,7 @@ pub fn log_config(config: &Config) { logv(c, format!("mode: {}", config.mode)); logv(c, format!("run_ignored: {}", config.run_ignored)); logv(c, format!("filters: {:?}", config.filters)); + logv(c, format!("skip: {:?}", config.skip)); logv(c, format!("filter_exact: {}", config.filter_exact)); logv( c, @@ -506,7 +509,7 @@ pub fn test_opts(config: &Config) -> test::TestOpts { shuffle: false, shuffle_seed: None, test_threads: None, - skip: vec![], + skip: config.skip.clone(), list: false, options: test::Options::new(), time_options: None, @@ -595,6 +598,7 @@ fn collect_tests_from_dir( debug!("found test file: {:?}", file_path.display()); let paths = TestPaths { file: file_path, relative_dir: relative_dir_path.to_path_buf() }; + tests.extend(make_test(config, &paths, inputs)) } else if file_path.is_dir() { let relative_file_path = relative_dir_path.join(file.file_name()); From 4ce68c13bfbd88df8d93da676e8424544c27321e Mon Sep 17 00:00:00 2001 From: Dan Gohman Date: Tue, 10 May 2022 21:20:34 -0700 Subject: [PATCH 05/14] Clarify what values `BorrowedHandle`, `OwnedHandle` etc. can hold. Clarify that when `BorrowedHandle`, `OwnedHandle`, or `HandleOrNull` hold the value `-1`, it always means the current process handle, and not `INVALID_HANDLE_VALUE`. --- library/std/src/os/windows/io/handle.rs | 29 +++++++++++++++---------- 1 file changed, 17 insertions(+), 12 deletions(-) diff --git a/library/std/src/os/windows/io/handle.rs b/library/std/src/os/windows/io/handle.rs index 290b7f0d08a72..b80ea0ac5eeb3 100644 --- a/library/std/src/os/windows/io/handle.rs +++ b/library/std/src/os/windows/io/handle.rs @@ -22,8 +22,9 @@ use crate::sys_common::{AsInner, FromInner, IntoInner}; /// so it can be used in FFI in places where a handle is passed as an argument, /// it is not captured or consumed. /// -/// Note that it *may* have the value `INVALID_HANDLE_VALUE` (-1), which is -/// sometimes a valid handle value. See [here] for the full story. +/// Note that it *may* have the value `-1`, which in `BorrowedFd` always +/// represents the current process handle, and not `INVALID_HANDLE_VALUE`, +/// despite the two having the same value. See [here] for the full story. /// /// And, it *may* have the value `NULL` (0), which can occur when consoles are /// detached from processes, or when `windows_subsystem` is used. @@ -45,8 +46,9 @@ pub struct BorrowedHandle<'handle> { /// /// This closes the handle on drop. /// -/// Note that it *may* have the value `INVALID_HANDLE_VALUE` (-1), which is -/// sometimes a valid handle value. See [here] for the full story. +/// Note that it *may* have the value `-1`, which in `OwnedFd` always +/// represents the current process handle, and not `INVALID_HANDLE_VALUE`, +/// despite the two having the same value. See [here] for the full story. /// /// And, it *may* have the value `NULL` (0), which can occur when consoles are /// detached from processes, or when `windows_subsystem` is used. @@ -75,11 +77,11 @@ pub struct OwnedHandle { /// `NULL`. This ensures that such FFI calls cannot start using the handle without /// checking for `NULL` first. /// -/// This type considers any value other than `NULL` to be valid, including `INVALID_HANDLE_VALUE`. -/// This is because APIs that use `NULL` as their sentry value don't treat `INVALID_HANDLE_VALUE` -/// as special. +/// This type may hold any handle value that [`OwnedFd`] may hold, except `NULL`. It may +/// hold `-1`, even though `-1` has the same value as `INVALID_HANDLE_VALUE`, because in +/// `HandleOrNull`, `-1` is interpreted to mean the current process handle. /// -/// If this holds a valid handle, it will close the handle on drop. +/// If this holds a non-null handle, it will close the handle on drop. #[repr(transparent)] #[unstable(feature = "io_safety", issue = "87074")] #[derive(Debug)] @@ -95,11 +97,14 @@ pub struct HandleOrNull(OwnedHandle); /// `INVALID_HANDLE_VALUE`. This ensures that such FFI calls cannot start using the handle without /// checking for `INVALID_HANDLE_VALUE` first. /// -/// This type considers any value other than `INVALID_HANDLE_VALUE` to be valid, including `NULL`. -/// This is because APIs that use `INVALID_HANDLE_VALUE` as their sentry value may return `NULL` -/// under `windows_subsystem = "windows"` or other situations where I/O devices are detached. +/// This type may hold any handle value that [`OwnedFd`] may hold, except `-1`. It must not +/// hold `-1`, because `-1` in `HandleOrInvalid` is interpreted to mean `INVALID_HANDLE_VALUE`. /// -/// If this holds a valid handle, it will close the handle on drop. +/// This type may hold `NULL`, because APIs that use `INVALID_HANDLE_VALUE` as their sentry value +/// may return `NULL` under `windows_subsystem = "windows"` or other situations where I/O devices +/// are detached. +/// +/// If holds a handle other than `INVALID_HANDLE_VALUE`, it will close the handle on drop. #[repr(transparent)] #[unstable(feature = "io_safety", issue = "87074")] #[derive(Debug)] From 2bb7fdb8e16788367ea4a3403ac405b8bc614cc6 Mon Sep 17 00:00:00 2001 From: Dan Gohman Date: Tue, 10 May 2022 21:42:30 -0700 Subject: [PATCH 06/14] Also document that `as_raw_handle` may return NULL. --- library/std/src/os/windows/io/raw.rs | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/library/std/src/os/windows/io/raw.rs b/library/std/src/os/windows/io/raw.rs index 68fa8918a56a0..49e4f304f5dba 100644 --- a/library/std/src/os/windows/io/raw.rs +++ b/library/std/src/os/windows/io/raw.rs @@ -32,8 +32,15 @@ pub trait AsRawHandle { /// raw handle to the caller, and the handle is only guaranteed /// to be valid while the original object has not yet been destroyed. /// + /// This function may return null, such as when called on [`Stdin`], + /// [`Stdout`], or [`Stderr`] when the console is detached. + /// /// However, borrowing is not strictly required. See [`AsHandle::as_handle`] /// for an API which strictly borrows a handle. + /// + /// [`Stdin`]: io::Stdin + /// [`Stdout`]: io::Stdout + /// [`Stderr`]: io::Stderr #[stable(feature = "rust1", since = "1.0.0")] fn as_raw_handle(&self) -> RawHandle; } From 0a39e5ad36419c2b257a91705ac1337f18a5e08f Mon Sep 17 00:00:00 2001 From: Dan Gohman Date: Tue, 10 May 2022 21:56:51 -0700 Subject: [PATCH 07/14] Fix incorrect mentions of `OwnedFd` and `BorrowedFd` in Windows docs. --- library/std/src/os/windows/io/handle.rs | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/library/std/src/os/windows/io/handle.rs b/library/std/src/os/windows/io/handle.rs index b80ea0ac5eeb3..ef2ef10e05fea 100644 --- a/library/std/src/os/windows/io/handle.rs +++ b/library/std/src/os/windows/io/handle.rs @@ -22,7 +22,7 @@ use crate::sys_common::{AsInner, FromInner, IntoInner}; /// so it can be used in FFI in places where a handle is passed as an argument, /// it is not captured or consumed. /// -/// Note that it *may* have the value `-1`, which in `BorrowedFd` always +/// Note that it *may* have the value `-1`, which in `BorrowedHandle` always /// represents the current process handle, and not `INVALID_HANDLE_VALUE`, /// despite the two having the same value. See [here] for the full story. /// @@ -46,7 +46,7 @@ pub struct BorrowedHandle<'handle> { /// /// This closes the handle on drop. /// -/// Note that it *may* have the value `-1`, which in `OwnedFd` always +/// Note that it *may* have the value `-1`, which in `OwnedHandle` always /// represents the current process handle, and not `INVALID_HANDLE_VALUE`, /// despite the two having the same value. See [here] for the full story. /// @@ -77,7 +77,7 @@ pub struct OwnedHandle { /// `NULL`. This ensures that such FFI calls cannot start using the handle without /// checking for `NULL` first. /// -/// This type may hold any handle value that [`OwnedFd`] may hold, except `NULL`. It may +/// This type may hold any handle value that [`OwnedHandle`] may hold, except `NULL`. It may /// hold `-1`, even though `-1` has the same value as `INVALID_HANDLE_VALUE`, because in /// `HandleOrNull`, `-1` is interpreted to mean the current process handle. /// @@ -97,7 +97,7 @@ pub struct HandleOrNull(OwnedHandle); /// `INVALID_HANDLE_VALUE`. This ensures that such FFI calls cannot start using the handle without /// checking for `INVALID_HANDLE_VALUE` first. /// -/// This type may hold any handle value that [`OwnedFd`] may hold, except `-1`. It must not +/// This type may hold any handle value that [`OwnedHandle`] may hold, except `-1`. It must not /// hold `-1`, because `-1` in `HandleOrInvalid` is interpreted to mean `INVALID_HANDLE_VALUE`. /// /// This type may hold `NULL`, because APIs that use `INVALID_HANDLE_VALUE` as their sentry value From 2f75b4aaa64fb8bfb9635a879c1af52a5d68f662 Mon Sep 17 00:00:00 2001 From: Dan Gohman Date: Wed, 11 May 2022 06:36:54 -0700 Subject: [PATCH 08/14] HandleOrNull can hold null, and HandleOrInvalid can hold INVALID_HANDLE_VALUE. --- library/std/src/os/windows/io/handle.rs | 14 +++++--------- 1 file changed, 5 insertions(+), 9 deletions(-) diff --git a/library/std/src/os/windows/io/handle.rs b/library/std/src/os/windows/io/handle.rs index ef2ef10e05fea..81ae1539acb65 100644 --- a/library/std/src/os/windows/io/handle.rs +++ b/library/std/src/os/windows/io/handle.rs @@ -77,9 +77,9 @@ pub struct OwnedHandle { /// `NULL`. This ensures that such FFI calls cannot start using the handle without /// checking for `NULL` first. /// -/// This type may hold any handle value that [`OwnedHandle`] may hold, except `NULL`. It may -/// hold `-1`, even though `-1` has the same value as `INVALID_HANDLE_VALUE`, because in -/// `HandleOrNull`, `-1` is interpreted to mean the current process handle. +/// This type may hold any handle value that [`OwnedHandle`] may hold. As with `OwnedHandle`, when +/// it holds `-1`, that value is interpreted as the current process handle, and not +/// `INVALID_HANDLE_VALUE`. /// /// If this holds a non-null handle, it will close the handle on drop. #[repr(transparent)] @@ -97,12 +97,8 @@ pub struct HandleOrNull(OwnedHandle); /// `INVALID_HANDLE_VALUE`. This ensures that such FFI calls cannot start using the handle without /// checking for `INVALID_HANDLE_VALUE` first. /// -/// This type may hold any handle value that [`OwnedHandle`] may hold, except `-1`. It must not -/// hold `-1`, because `-1` in `HandleOrInvalid` is interpreted to mean `INVALID_HANDLE_VALUE`. -/// -/// This type may hold `NULL`, because APIs that use `INVALID_HANDLE_VALUE` as their sentry value -/// may return `NULL` under `windows_subsystem = "windows"` or other situations where I/O devices -/// are detached. +/// This type may hold any handle value that [`OwnedHandle`] may hold, except that when it holds +/// `-1`, that value is interpreted to mean `INVALID_HANDLE_VALUE`. /// /// If holds a handle other than `INVALID_HANDLE_VALUE`, it will close the handle on drop. #[repr(transparent)] From cdbfd3e01136948e2ca7947c6eb37914b296cb2d Mon Sep 17 00:00:00 2001 From: ludfo774 <79518686+ludfo774@users.noreply.github.com> Date: Wed, 11 May 2022 16:42:16 +0200 Subject: [PATCH 09/14] Add test of matches macro for trailing commas --- src/test/ui/macros/macro-comma-support-rpass.rs | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/test/ui/macros/macro-comma-support-rpass.rs b/src/test/ui/macros/macro-comma-support-rpass.rs index f6c4f896d67c1..25b8c3cc62e16 100644 --- a/src/test/ui/macros/macro-comma-support-rpass.rs +++ b/src/test/ui/macros/macro-comma-support-rpass.rs @@ -192,6 +192,12 @@ fn line() { let _ = line!(); } +#[test] +fn matches() { + let _ = matches!(1, x if x > 0); + let _ = matches!(1, x if x > 0,); +} + #[test] fn module_path() { let _ = module_path!(); From c586bc3d760c4cb158aba5c59ca15809a6957142 Mon Sep 17 00:00:00 2001 From: Gary Guo Date: Wed, 11 May 2022 23:08:02 +0100 Subject: [PATCH 10/14] Prevent unwinding when `-C panic=abort` is used regardless declared ABI --- compiler/rustc_middle/src/ty/layout.rs | 8 ++++++++ src/test/codegen/unwind-abis/c-unwind-abi-panic-abort.rs | 6 +++--- 2 files changed, 11 insertions(+), 3 deletions(-) diff --git a/compiler/rustc_middle/src/ty/layout.rs b/compiler/rustc_middle/src/ty/layout.rs index c8055100d3096..630a89cc7cbfc 100644 --- a/compiler/rustc_middle/src/ty/layout.rs +++ b/compiler/rustc_middle/src/ty/layout.rs @@ -2888,6 +2888,14 @@ pub fn fn_can_unwind<'tcx>(tcx: TyCtxt<'tcx>, fn_def_id: Option, abi: Spe return false; } + // With `-C panic=abort`, all non-FFI functions are required to not unwind. + // + // Note that this is true regardless ABI specified on the function -- a `extern "C-unwind"` + // function defined in Rust is also required to abort. + if tcx.sess.panic_strategy() == PanicStrategy::Abort && !tcx.is_foreign_item(did) { + return false; + } + // With -Z panic-in-drop=abort, drop_in_place never unwinds. // // This is not part of `codegen_fn_attrs` as it can differ between crates diff --git a/src/test/codegen/unwind-abis/c-unwind-abi-panic-abort.rs b/src/test/codegen/unwind-abis/c-unwind-abi-panic-abort.rs index 398937a04c923..5334a1c004dbb 100644 --- a/src/test/codegen/unwind-abis/c-unwind-abi-panic-abort.rs +++ b/src/test/codegen/unwind-abis/c-unwind-abi-panic-abort.rs @@ -1,7 +1,7 @@ // compile-flags: -C panic=abort -// Test that `nounwind` atributes are not applied to `C-unwind` extern functions -// even when the code is compiled with `panic=abort`. +// Test that `nounwind` atributes are also applied to extern `C-unwind` Rust functions +// when the code is compiled with `panic=abort`. #![crate_type = "lib"] #![feature(c_unwind)] @@ -19,4 +19,4 @@ pub unsafe extern "C-unwind" fn rust_item_that_can_unwind() { // Now, make sure that the LLVM attributes for this functions are correct. First, make // sure that the first item is correctly marked with the `nounwind` attribute: // -// CHECK-NOT: attributes #0 = { {{.*}}nounwind{{.*}} } +// CHECK: attributes #0 = { {{.*}}nounwind{{.*}} } From 516a7fa6934c561e9fc1b357a57eb5f0adb89739 Mon Sep 17 00:00:00 2001 From: Dan Gohman Date: Wed, 11 May 2022 20:50:07 -0700 Subject: [PATCH 11/14] Relax the wording about the meaning of -1. --- library/std/src/os/windows/io/handle.rs | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/library/std/src/os/windows/io/handle.rs b/library/std/src/os/windows/io/handle.rs index 81ae1539acb65..e473fac351825 100644 --- a/library/std/src/os/windows/io/handle.rs +++ b/library/std/src/os/windows/io/handle.rs @@ -23,8 +23,9 @@ use crate::sys_common::{AsInner, FromInner, IntoInner}; /// it is not captured or consumed. /// /// Note that it *may* have the value `-1`, which in `BorrowedHandle` always -/// represents the current process handle, and not `INVALID_HANDLE_VALUE`, -/// despite the two having the same value. See [here] for the full story. +/// represents a valid handle value, such as [the current process handle], and +/// not `INVALID_HANDLE_VALUE`, despite the two having the same value. See +/// [here] for the full story. /// /// And, it *may* have the value `NULL` (0), which can occur when consoles are /// detached from processes, or when `windows_subsystem` is used. @@ -34,6 +35,7 @@ use crate::sys_common::{AsInner, FromInner, IntoInner}; /// handle, which is then borrowed under the same lifetime. /// /// [here]: https://devblogs.microsoft.com/oldnewthing/20040302-00/?p=40443 +/// [the current process handle]: https://docs.microsoft.com/en-us/windows/win32/api/processthreadsapi/nf-processthreadsapi-getcurrentprocess#remarks #[derive(Copy, Clone)] #[repr(transparent)] #[unstable(feature = "io_safety", issue = "87074")] @@ -47,8 +49,9 @@ pub struct BorrowedHandle<'handle> { /// This closes the handle on drop. /// /// Note that it *may* have the value `-1`, which in `OwnedHandle` always -/// represents the current process handle, and not `INVALID_HANDLE_VALUE`, -/// despite the two having the same value. See [here] for the full story. +/// represents a valid handle value, such as [the current process handle], and +/// not `INVALID_HANDLE_VALUE`, despite the two having the same value. See +/// [here] for the full story. /// /// And, it *may* have the value `NULL` (0), which can occur when consoles are /// detached from processes, or when `windows_subsystem` is used. @@ -61,6 +64,7 @@ pub struct BorrowedHandle<'handle> { /// [`RegCloseKey`]: https://docs.microsoft.com/en-us/windows/win32/api/winreg/nf-winreg-regclosekey /// /// [here]: https://devblogs.microsoft.com/oldnewthing/20040302-00/?p=40443 +/// [the current process handle]: https://docs.microsoft.com/en-us/windows/win32/api/processthreadsapi/nf-processthreadsapi-getcurrentprocess#remarks #[repr(transparent)] #[unstable(feature = "io_safety", issue = "87074")] pub struct OwnedHandle { @@ -78,10 +82,11 @@ pub struct OwnedHandle { /// checking for `NULL` first. /// /// This type may hold any handle value that [`OwnedHandle`] may hold. As with `OwnedHandle`, when -/// it holds `-1`, that value is interpreted as the current process handle, and not -/// `INVALID_HANDLE_VALUE`. +/// it holds `-1`, that value is interpreted as a valid handle value, such as +/// [the current process handle], and not `INVALID_HANDLE_VALUE`. /// /// If this holds a non-null handle, it will close the handle on drop. +/// [the current process handle]: https://docs.microsoft.com/en-us/windows/win32/api/processthreadsapi/nf-processthreadsapi-getcurrentprocess#remarks #[repr(transparent)] #[unstable(feature = "io_safety", issue = "87074")] #[derive(Debug)] From 275812ad2cb0a5a9a8de88151438d1319a6f0704 Mon Sep 17 00:00:00 2001 From: Dan Gohman Date: Wed, 11 May 2022 21:11:49 -0700 Subject: [PATCH 12/14] Fix comment syntax. --- library/std/src/os/windows/io/handle.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/library/std/src/os/windows/io/handle.rs b/library/std/src/os/windows/io/handle.rs index e473fac351825..f27970eaaf122 100644 --- a/library/std/src/os/windows/io/handle.rs +++ b/library/std/src/os/windows/io/handle.rs @@ -86,6 +86,7 @@ pub struct OwnedHandle { /// [the current process handle], and not `INVALID_HANDLE_VALUE`. /// /// If this holds a non-null handle, it will close the handle on drop. +/// /// [the current process handle]: https://docs.microsoft.com/en-us/windows/win32/api/processthreadsapi/nf-processthreadsapi-getcurrentprocess#remarks #[repr(transparent)] #[unstable(feature = "io_safety", issue = "87074")] From a315bb444678a31de0effcb3071c6a9c57d25219 Mon Sep 17 00:00:00 2001 From: Gary Guo Date: Thu, 12 May 2022 14:20:13 +0100 Subject: [PATCH 13/14] Expand c-unwind-abi-panic-abort test --- .../codegen/unwind-abis/c-unwind-abi-panic-abort.rs | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/src/test/codegen/unwind-abis/c-unwind-abi-panic-abort.rs b/src/test/codegen/unwind-abis/c-unwind-abi-panic-abort.rs index 5334a1c004dbb..af6879880ae3b 100644 --- a/src/test/codegen/unwind-abis/c-unwind-abi-panic-abort.rs +++ b/src/test/codegen/unwind-abis/c-unwind-abi-panic-abort.rs @@ -6,17 +6,22 @@ #![crate_type = "lib"] #![feature(c_unwind)] -extern "C-unwind" { - fn may_unwind(); -} - // CHECK: @rust_item_that_can_unwind() unnamed_addr #0 #[no_mangle] pub unsafe extern "C-unwind" fn rust_item_that_can_unwind() { + // CHECK: call void @_ZN4core9panicking15panic_no_unwind may_unwind(); } +extern "C-unwind" { + // CHECK: @may_unwind() unnamed_addr #1 + fn may_unwind(); +} + // Now, make sure that the LLVM attributes for this functions are correct. First, make // sure that the first item is correctly marked with the `nounwind` attribute: // // CHECK: attributes #0 = { {{.*}}nounwind{{.*}} } +// +// Now, check that foreign item is correctly marked without the `nounwind` attribute. +// CHECK-NOT: attributes #1 = { {{.*}}nounwind{{.*}} } From d3fd6bfd308f1cca010086e30e75daaee984beab Mon Sep 17 00:00:00 2001 From: Michael Howell Date: Thu, 12 May 2022 14:15:31 -0700 Subject: [PATCH 14/14] rustdoc: fix GUI crash when searching for magic JS property values --- src/librustdoc/html/static/js/search.js | 4 ++-- src/test/rustdoc-js/prototype.js | 16 ++++++++++++++++ src/test/rustdoc-js/prototype.rs | 4 ++++ 3 files changed, 22 insertions(+), 2 deletions(-) create mode 100644 src/test/rustdoc-js/prototype.js create mode 100644 src/test/rustdoc-js/prototype.rs diff --git a/src/librustdoc/html/static/js/search.js b/src/librustdoc/html/static/js/search.js index 7754d626e209e..b596adf32c6fd 100644 --- a/src/librustdoc/html/static/js/search.js +++ b/src/librustdoc/html/static/js/search.js @@ -119,7 +119,7 @@ window.initSearch = rawSearchIndex => { */ let searchIndex; let currentResults; - const ALIASES = {}; + const ALIASES = Object.create(null); const params = searchState.getQueryStringParams(); // Populate search bar with query string search term when provided, @@ -1953,7 +1953,7 @@ window.initSearch = rawSearchIndex => { } if (aliases) { - ALIASES[crate] = {}; + ALIASES[crate] = Object.create(null); for (const alias_name in aliases) { if (!hasOwnPropertyRustdoc(aliases, alias_name)) { continue; diff --git a/src/test/rustdoc-js/prototype.js b/src/test/rustdoc-js/prototype.js new file mode 100644 index 0000000000000..2f1d841c3be19 --- /dev/null +++ b/src/test/rustdoc-js/prototype.js @@ -0,0 +1,16 @@ +// exact-check + +const QUERY = ['constructor', '__proto__']; + +const EXPECTED = [ + { + 'others': [], + 'returned': [], + 'in_args': [], + }, + { + 'others': [], + 'returned': [], + 'in_args': [], + }, +]; diff --git a/src/test/rustdoc-js/prototype.rs b/src/test/rustdoc-js/prototype.rs new file mode 100644 index 0000000000000..5f6d73cc19626 --- /dev/null +++ b/src/test/rustdoc-js/prototype.rs @@ -0,0 +1,4 @@ +// The alias needed to be there to reproduce the bug +// that used to be here. +#[doc(alias="other_alias")] +pub fn something_else() {}