diff --git a/compiler/rustc_builtin_macros/src/test.rs b/compiler/rustc_builtin_macros/src/test.rs index e658631d090..0c2d20b8f2d 100644 --- a/compiler/rustc_builtin_macros/src/test.rs +++ b/compiler/rustc_builtin_macros/src/test.rs @@ -105,14 +105,18 @@ pub fn expand_test_or_bench( // Note: non-associated fn items are already handled by `expand_test_or_bench` if !matches!(item.kind, ast::ItemKind::Fn(_)) { - cx.sess - .parse_sess - .span_diagnostic - .struct_span_err( - attr_sp, - "the `#[test]` attribute may only be used on a non-associated function", - ) - .note("the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions") + let diag = &cx.sess.parse_sess.span_diagnostic; + let msg = "the `#[test]` attribute may only be used on a non-associated function"; + let mut err = match item.kind { + // These were a warning before #92959 and need to continue being that to avoid breaking + // stable user code (#94508). + ast::ItemKind::MacCall(_) => diag.struct_span_warn(attr_sp, msg), + // `.forget_guarantee()` needed to get these two arms to match types. Because of how + // locally close the `.emit()` call is I'm comfortable with it, but if it can be + // reworked in the future to not need it, it'd be nice. + _ => diag.struct_span_err(attr_sp, msg).forget_guarantee(), + }; + err.span_label(attr_sp, "the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions") .span_label(item.span, format!("expected a non-associated function, found {} {}", item.kind.article(), item.kind.descr())) .span_suggestion(attr_sp, "replace with conditional compilation to make the item only exist when tests are being run", String::from("#[cfg(test)]"), Applicability::MaybeIncorrect) .emit(); diff --git a/src/test/ui/test-attrs/test-on-not-fn.rs b/src/test/ui/test-attrs/test-on-not-fn.rs index b2f681c01d1..a460480afb1 100644 --- a/src/test/ui/test-attrs/test-on-not-fn.rs +++ b/src/test/ui/test-attrs/test-on-not-fn.rs @@ -58,7 +58,7 @@ macro_rules! foo { () => {}; } -#[test] //~ ERROR: the `#[test]` attribute may only be used on a non-associated function +#[test] //~ WARN: the `#[test]` attribute may only be used on a non-associated function foo!(); // make sure it doesn't erroneously trigger on a real test diff --git a/src/test/ui/test-attrs/test-on-not-fn.stderr b/src/test/ui/test-attrs/test-on-not-fn.stderr index dd693cf316d..23efd5bc0d9 100644 --- a/src/test/ui/test-attrs/test-on-not-fn.stderr +++ b/src/test/ui/test-attrs/test-on-not-fn.stderr @@ -2,11 +2,10 @@ error: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:3:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | mod test {} | ----------- expected a non-associated function, found a module | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] @@ -16,7 +15,7 @@ error: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:6:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | / mod loooooooooooooong_teeeeeeeeeest { LL | | /* LL | | this is a comment @@ -26,7 +25,6 @@ LL | | */ LL | | } | |_- expected a non-associated function, found a module | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] @@ -36,11 +34,10 @@ error: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:20:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | extern "C" {} | ------------- expected a non-associated function, found an extern block | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] @@ -50,11 +47,10 @@ error: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:23:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | trait Foo {} | ------------ expected a non-associated function, found a trait | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] @@ -64,11 +60,10 @@ error: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:26:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | impl Foo for i32 {} | ------------------- expected a non-associated function, found an implementation | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] @@ -78,11 +73,10 @@ error: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:29:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | const FOO: i32 = -1_i32; | ------------------------ expected a non-associated function, found a constant item | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] @@ -92,11 +86,10 @@ error: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:32:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | static BAR: u64 = 10_000_u64; | ----------------------------- expected a non-associated function, found a static item | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] @@ -106,13 +99,12 @@ error: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:35:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | / enum MyUnit { LL | | Unit, LL | | } | |_- expected a non-associated function, found an enum | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] @@ -122,11 +114,10 @@ error: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:40:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | struct NewI32(i32); | ------------------- expected a non-associated function, found a struct | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] @@ -136,14 +127,13 @@ error: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:43:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | / union Spooky { LL | | x: i32, LL | | y: u32, LL | | } | |_- expected a non-associated function, found a union | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] @@ -153,7 +143,7 @@ error: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:50:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | #[derive(Copy, Clone, Debug)] LL | / struct MoreAttrs { LL | | a: i32, @@ -161,25 +151,23 @@ LL | | b: u64, LL | | } | |_- expected a non-associated function, found a struct | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] | ~~~~~~~~~~~~ -error: the `#[test]` attribute may only be used on a non-associated function +warning: the `#[test]` attribute may only be used on a non-associated function --> $DIR/test-on-not-fn.rs:61:1 | LL | #[test] - | ^^^^^^^ + | ^^^^^^^ the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions LL | foo!(); | ------- expected a non-associated function, found an item macro invocation | - = note: the `#[test]` macro causes a a function to be run on a test and has no effect on non-functions help: replace with conditional compilation to make the item only exist when tests are being run | LL | #[cfg(test)] | ~~~~~~~~~~~~ -error: aborting due to 12 previous errors +error: aborting due to 11 previous errors; 1 warning emitted