diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/auxiliary/macro-in-2021.rs b/tests/ui/rfcs/rfc-2497-if-let-chains/auxiliary/macro-in-2021.rs new file mode 100644 index 0000000000000..d2d5ae1110415 --- /dev/null +++ b/tests/ui/rfcs/rfc-2497-if-let-chains/auxiliary/macro-in-2021.rs @@ -0,0 +1,26 @@ +//@ edition: 2021 + +#[macro_export] +macro_rules! make_if { + (($($tt:tt)*) { $body:expr } { $else:expr }) => {{ + if $($tt)* { + $body + } else { + $else + } + }}; + (let ($expr:expr) { $body:expr } { $else:expr }) => {{ + if let None = $expr { + $body + } else { + $else + } + }}; + (let ($expr:expr) let ($expr2:expr) { $body:expr } { $else:expr }) => {{ + if let None = $expr && let None = $expr2 { + $body + } else { + $else + } + }}; +} diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/auxiliary/macro-in-2024.rs b/tests/ui/rfcs/rfc-2497-if-let-chains/auxiliary/macro-in-2024.rs new file mode 100644 index 0000000000000..af382c0b466ce --- /dev/null +++ b/tests/ui/rfcs/rfc-2497-if-let-chains/auxiliary/macro-in-2024.rs @@ -0,0 +1,27 @@ +//@ edition: 2024 +//@ compile-flags: -Z unstable-options + +#[macro_export] +macro_rules! make_if { + (($($tt:tt)*) { $body:expr } { $else:expr }) => {{ + if $($tt)* { + $body + } else { + $else + } + }}; + (let ($expr:expr) { $body:expr } { $else:expr }) => {{ + if let None = $expr { + $body + } else { + $else + } + }}; + (let ($expr:expr) let ($expr2:expr) { $body:expr } { $else:expr }) => {{ + if let None = $expr && let None = $expr2 { + $body + } else { + $else + } + }}; +} diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro-error.edition2021.stderr b/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro-error.edition2021.stderr new file mode 100644 index 0000000000000..23700f89f1080 --- /dev/null +++ b/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro-error.edition2021.stderr @@ -0,0 +1,65 @@ +error[E0658]: `let` expressions in this position are unstable + --> $DIR/edition-gate-macro-error.rs:19:30 + | +LL | macro_in_2021::make_if!((let Some(0) = None && let Some(0) = None) { never!() } { never!() }); + | ^^^^^^^^^^^^^^^^^^ + | + = note: see issue #53667 for more information + = help: add `#![feature(let_chains)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error[E0658]: `let` expressions in this position are unstable + --> $DIR/edition-gate-macro-error.rs:19:52 + | +LL | macro_in_2021::make_if!((let Some(0) = None && let Some(0) = None) { never!() } { never!() }); + | ^^^^^^^^^^^^^^^^^^ + | + = note: see issue #53667 for more information + = help: add `#![feature(let_chains)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error[E0658]: `let` expressions in this position are unstable + --> $DIR/edition-gate-macro-error.rs:22:5 + | +LL | macro_in_2021::make_if!(let (Some(0)) let (Some(0)) { never!() } { never!() }); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = note: see issue #53667 for more information + = help: add `#![feature(let_chains)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: this error originates in the macro `macro_in_2021::make_if` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0658]: `let` expressions in this position are unstable + --> $DIR/edition-gate-macro-error.rs:22:5 + | +LL | macro_in_2021::make_if!(let (Some(0)) let (Some(0)) { never!() } { never!() }); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = note: see issue #53667 for more information + = help: add `#![feature(let_chains)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: this error originates in the macro `macro_in_2021::make_if` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0658]: `let` expressions in this position are unstable + --> $DIR/edition-gate-macro-error.rs:26:30 + | +LL | macro_in_2024::make_if!((let Some(0) = None && let Some(0) = None) { never!() } { never!() }); + | ^^^^^^^^^^^^^^^^^^ + | + = note: see issue #53667 for more information + = help: add `#![feature(let_chains)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error[E0658]: `let` expressions in this position are unstable + --> $DIR/edition-gate-macro-error.rs:26:52 + | +LL | macro_in_2024::make_if!((let Some(0) = None && let Some(0) = None) { never!() } { never!() }); + | ^^^^^^^^^^^^^^^^^^ + | + = note: see issue #53667 for more information + = help: add `#![feature(let_chains)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error: aborting due to 6 previous errors + +For more information about this error, try `rustc --explain E0658`. diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro-error.edition2024.stderr b/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro-error.edition2024.stderr new file mode 100644 index 0000000000000..3af844f4f9665 --- /dev/null +++ b/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro-error.edition2024.stderr @@ -0,0 +1,45 @@ +error[E0658]: `let` expressions in this position are unstable + --> $DIR/edition-gate-macro-error.rs:19:30 + | +LL | macro_in_2021::make_if!((let Some(0) = None && let Some(0) = None) { never!() } { never!() }); + | ^^^^^^^^^^^^^^^^^^ + | + = note: see issue #53667 for more information + = help: add `#![feature(let_chains)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error[E0658]: `let` expressions in this position are unstable + --> $DIR/edition-gate-macro-error.rs:19:52 + | +LL | macro_in_2021::make_if!((let Some(0) = None && let Some(0) = None) { never!() } { never!() }); + | ^^^^^^^^^^^^^^^^^^ + | + = note: see issue #53667 for more information + = help: add `#![feature(let_chains)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error[E0658]: `let` expressions in this position are unstable + --> $DIR/edition-gate-macro-error.rs:22:5 + | +LL | macro_in_2021::make_if!(let (Some(0)) let (Some(0)) { never!() } { never!() }); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = note: see issue #53667 for more information + = help: add `#![feature(let_chains)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: this error originates in the macro `macro_in_2021::make_if` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0658]: `let` expressions in this position are unstable + --> $DIR/edition-gate-macro-error.rs:22:5 + | +LL | macro_in_2021::make_if!(let (Some(0)) let (Some(0)) { never!() } { never!() }); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = note: see issue #53667 for more information + = help: add `#![feature(let_chains)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: this error originates in the macro `macro_in_2021::make_if` (in Nightly builds, run with -Z macro-backtrace for more info) + +error: aborting due to 4 previous errors + +For more information about this error, try `rustc --explain E0658`. diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro-error.rs b/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro-error.rs new file mode 100644 index 0000000000000..19ea654864550 --- /dev/null +++ b/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro-error.rs @@ -0,0 +1,30 @@ +//@ revisions: edition2021 edition2024 +//@ compile-flags: -Z unstable-options -Z lint-mir -Z validate-mir +//@ [edition2021] edition: 2021 +//@ [edition2024] edition: 2024 +//@ aux-build:macro-in-2021.rs +//@ aux-build:macro-in-2024.rs + +use std::unreachable as never; + +// Compiletest doesn't specify the needed --extern flags to make `extern crate` unneccessary +extern crate macro_in_2021; +extern crate macro_in_2024; + +fn main() { + // Gated on both 2021 and 2024 if the `if` comes from a 2021 macro + // Gated only on 2021 if the `if` comes from a 2024 macro + // No gating if both the `if` and the chain are from a 2024 macro + + macro_in_2021::make_if!((let Some(0) = None && let Some(0) = None) { never!() } { never!() }); + //~^ ERROR `let` expressions in this position are unstable + //~| ERROR `let` expressions in this position are unstable + macro_in_2021::make_if!(let (Some(0)) let (Some(0)) { never!() } { never!() }); + //~^ ERROR `let` expressions in this position are unstable + //~| ERROR `let` expressions in this position are unstable + + macro_in_2024::make_if!((let Some(0) = None && let Some(0) = None) { never!() } { never!() }); + //[edition2021]~^ ERROR `let` expressions in this position are unstable + //[edition2021]~| ERROR `let` expressions in this position are unstable + macro_in_2024::make_if!(let (Some(0)) let (Some(0)) { never!() } { never!() }); +} diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro.rs b/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro.rs new file mode 100644 index 0000000000000..612aa576cf335 --- /dev/null +++ b/tests/ui/rfcs/rfc-2497-if-let-chains/edition-gate-macro.rs @@ -0,0 +1,76 @@ +//@ revisions: edition2021 edition2024 +//@ compile-flags: -Z unstable-options -Z lint-mir -Z validate-mir +//@ [edition2021] edition: 2021 +//@ [edition2024] edition: 2024 +//@ aux-build:macro-in-2021.rs +//@ aux-build:macro-in-2024.rs +//@ run-pass + +#![allow(dead_code)] + +use std::unreachable as never; +use std::cell::RefCell; +use std::convert::TryInto; + +// Compiletest doesn't specify the needed --extern flags to make `extern crate` unneccessary +extern crate macro_in_2021; +extern crate macro_in_2024; + +#[derive(Default)] +struct DropOrderCollector(RefCell>); + +struct LoudDrop<'a>(&'a DropOrderCollector, u32); + +impl Drop for LoudDrop<'_> { + fn drop(&mut self) { + println!("{}", self.1); + self.0.0.borrow_mut().push(self.1); + } +} + +impl DropOrderCollector { + fn print(&self, n: u32) { + println!("{n}"); + self.0.borrow_mut().push(n) + } + fn some_loud(&self, n: u32) -> Option { + Some(LoudDrop(self, n)) + } + + #[track_caller] + fn validate(self) { + assert!( + self.0 + .into_inner() + .into_iter() + .enumerate() + .all(|(idx, item)| idx + 1 == item.try_into().unwrap()) + ); + } + fn with_macro_2021(self) { + // Edition 2021 drop behaviour + macro_in_2021::make_if!((let None = self.some_loud(2)) { never!() } {self.print(1) }); + macro_in_2021::make_if!(let (self.some_loud(4)) { never!() } { self.print(3) }); + self.validate(); + } + fn with_macro_2024(self) { + // Edition 2024 drop behaviour + macro_in_2024::make_if!((let None = self.some_loud(1)) { never!() } { self.print(2) }); + macro_in_2024::make_if!(let (self.some_loud(3)) { never!() } { self.print(4) }); + self.validate(); + } +} + +fn main() { + // 2021 drop order if it's a 2021 macro creating the `if` + // 2024 drop order if it's a 2024 macro creating the `if` + + // Compare this with edition-gate-macro-error.rs: We want to avoid exposing 2021 drop order, + // because it can create bad MIR (issue #104843) + // This test doesn't contain any let chains at all: it should be understood + // in combination with `edition-gate-macro-error.rs` + + DropOrderCollector::default().with_macro_2021(); + DropOrderCollector::default().with_macro_2024(); + +}