diff options
| author | Matthias Krüger <matthias.krueger@famsik.de> | 2024-10-16 19:18:30 +0200 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2024-10-16 19:18:30 +0200 |
| commit | c1ed1f133e4e07b5cb03ce44cb9ed6881d7ae6ca (patch) | |
| tree | 3dbe45433fedba0c113535df6c3b480470c9bb6b /tests/ui/pattern | |
| parent | 1817de609b0ffaab0cf32de6baae5944f6f6e7d6 (diff) | |
| parent | 2ef0a8fdfd5142e8a524f4dc9fff8c65d0bd7cc2 (diff) | |
| download | rust-c1ed1f133e4e07b5cb03ce44cb9ed6881d7ae6ca.tar.gz rust-c1ed1f133e4e07b5cb03ce44cb9ed6881d7ae6ca.zip | |
Rollup merge of #131381 - Nadrieril:min-match-ergonomics, r=pnkfelix
Implement edition 2024 match ergonomics restrictions This implements the minimalest version of [match ergonomics for edition 2024](https://rust-lang.github.io/rfcs/3627-match-ergonomics-2024.html). This minimal version makes it an error to ever reset the default binding mode. The implemented proposal is described precisely [here](https://hackmd.io/zUqs2ISNQ0Wrnxsa9nhD0Q#RFC-3627-nano), where it is called "RFC 3627-nano". Rules: - Rule 1C: When the DBM (default binding mode) is not `move` (whether or not behind a reference), writing `mut`, `ref`, or `ref mut` on a binding is an error. - Rule 2C: Reference patterns can only match against references in the scrutinee when the DBM is `move`. This minimal version is forward-compatible with the main proposals for match ergonomics 2024: [RFC3627](https://rust-lang.github.io/rfcs/3627-match-ergonomics-2024.html) itself, the alternative [rule 4-early variant](https://rust-lang.github.io/rfcs/3627-match-ergonomics-2024.html), and [others](https://hackmd.io/zUqs2ISNQ0Wrnxsa9nhD0Q). The idea is to give us more time to iron out a final proposal. This includes a migration lint that desugars any offending pattern into one that doesn't make use of match ergonomics. Such patterns have identical meaning across editions. This PR insta-stabilizes the proposed behavior onto edition 2024. r? `@ghost` Tracking: - https://github.com/rust-lang/rust/issues/123076
Diffstat (limited to 'tests/ui/pattern')
| -rw-r--r-- | tests/ui/pattern/match_ergonomics_2024.fixed | 57 | ||||
| -rw-r--r-- | tests/ui/pattern/match_ergonomics_2024.rs | 57 | ||||
| -rw-r--r-- | tests/ui/pattern/match_ergonomics_2024.stderr | 97 | ||||
| -rw-r--r-- | tests/ui/pattern/rfc-3627-match-ergonomics-2024/auxiliary/migration_lint_macros.rs (renamed from tests/ui/pattern/auxiliary/match_ergonomics_2024_macros.rs) | 0 | ||||
| -rw-r--r-- | tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.fixed | 144 | ||||
| -rw-r--r-- | tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.rs | 144 | ||||
| -rw-r--r-- | tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.stderr | 188 | ||||
| -rw-r--r-- | tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.rs | 46 | ||||
| -rw-r--r-- | tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.stderr | 160 | ||||
| -rw-r--r-- | tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_success.rs | 17 |
10 files changed, 699 insertions, 211 deletions
diff --git a/tests/ui/pattern/match_ergonomics_2024.fixed b/tests/ui/pattern/match_ergonomics_2024.fixed deleted file mode 100644 index 1ec2b5a214b..00000000000 --- a/tests/ui/pattern/match_ergonomics_2024.fixed +++ /dev/null @@ -1,57 +0,0 @@ -//@ edition: 2021 -//@ run-rustfix -//@ rustfix-only-machine-applicable -//@ aux-build:match_ergonomics_2024_macros.rs -#![feature(mut_ref, ref_pat_eat_one_layer_2024)] -#![allow(incomplete_features, unused)] -#![deny(rust_2024_incompatible_pat)] - -extern crate match_ergonomics_2024_macros; - -struct Foo(u8); - -fn main() { - let &Foo(mut a) = &Foo(0); - //~^ ERROR: the semantics of this pattern will change in edition 2024 - a = 42; - - let &mut Foo(mut a) = &mut Foo(0); - //~^ ERROR: the semantics of this pattern will change in edition 2024 - a = 42; - - if let &&&&&Some(&_) = &&&&&Some(&0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let &&&&&Some(&mut _) = &&&&&Some(&mut 0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let &&&&&mut Some(&_) = &&&&&mut Some(&0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let &mut Some(&mut Some(&mut Some(_))) = &mut Some(&mut Some(&mut Some(0u8))) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let &mut Some(&mut Some(&mut Some(ref mut _a))) = &mut Some(&mut Some(&mut Some(0u8))) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - struct Struct { - a: u32, - b: u32, - c: u32, - } - let s = Struct { a: 0, b: 0, c: 0 }; - let &Struct { ref a, mut b, ref c } = &s; - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - #[warn(rust_2024_incompatible_pat)] - match &(Some(0), Some(0)) { - // The two patterns are the same syntactically, but because they're defined in different - // editions they don't mean the same thing. - (Some(mut _x), match_ergonomics_2024_macros::mixed_edition_pat!(_y)) => { - //~^ WARN: the semantics of this pattern will change in edition 2024 - _x = 4; - _y = &7; - } - _ => {} - } -} diff --git a/tests/ui/pattern/match_ergonomics_2024.rs b/tests/ui/pattern/match_ergonomics_2024.rs deleted file mode 100644 index c9f992c12d4..00000000000 --- a/tests/ui/pattern/match_ergonomics_2024.rs +++ /dev/null @@ -1,57 +0,0 @@ -//@ edition: 2021 -//@ run-rustfix -//@ rustfix-only-machine-applicable -//@ aux-build:match_ergonomics_2024_macros.rs -#![feature(mut_ref, ref_pat_eat_one_layer_2024)] -#![allow(incomplete_features, unused)] -#![deny(rust_2024_incompatible_pat)] - -extern crate match_ergonomics_2024_macros; - -struct Foo(u8); - -fn main() { - let Foo(mut a) = &Foo(0); - //~^ ERROR: the semantics of this pattern will change in edition 2024 - a = 42; - - let Foo(mut a) = &mut Foo(0); - //~^ ERROR: the semantics of this pattern will change in edition 2024 - a = 42; - - if let Some(&_) = &&&&&Some(&0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let Some(&mut _) = &&&&&Some(&mut 0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let Some(&_) = &&&&&mut Some(&0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let Some(&mut Some(Some(_))) = &mut Some(&mut Some(&mut Some(0u8))) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let Some(&mut Some(Some(_a))) = &mut Some(&mut Some(&mut Some(0u8))) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - struct Struct { - a: u32, - b: u32, - c: u32, - } - let s = Struct { a: 0, b: 0, c: 0 }; - let Struct { a, mut b, c } = &s; - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - #[warn(rust_2024_incompatible_pat)] - match &(Some(0), Some(0)) { - // The two patterns are the same syntactically, but because they're defined in different - // editions they don't mean the same thing. - (Some(mut _x), match_ergonomics_2024_macros::mixed_edition_pat!(_y)) => { - //~^ WARN: the semantics of this pattern will change in edition 2024 - _x = 4; - _y = &7; - } - _ => {} - } -} diff --git a/tests/ui/pattern/match_ergonomics_2024.stderr b/tests/ui/pattern/match_ergonomics_2024.stderr deleted file mode 100644 index 11844434ad2..00000000000 --- a/tests/ui/pattern/match_ergonomics_2024.stderr +++ /dev/null @@ -1,97 +0,0 @@ -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:14:9 - | -LL | let Foo(mut a) = &Foo(0); - | -^^^^^^^^^ - | | - | help: desugar the match ergonomics: `&` - | -note: the lint level is defined here - --> $DIR/match_ergonomics_2024.rs:7:9 - | -LL | #![deny(rust_2024_incompatible_pat)] - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:18:9 - | -LL | let Foo(mut a) = &mut Foo(0); - | -^^^^^^^^^ - | | - | help: desugar the match ergonomics: `&mut` - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:22:12 - | -LL | if let Some(&_) = &&&&&Some(&0u8) {} - | -^^^^^^^ - | | - | help: desugar the match ergonomics: `&&&&&` - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:25:12 - | -LL | if let Some(&mut _) = &&&&&Some(&mut 0u8) {} - | -^^^^^^^^^^^ - | | - | help: desugar the match ergonomics: `&&&&&` - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:28:12 - | -LL | if let Some(&_) = &&&&&mut Some(&0u8) {} - | -^^^^^^^ - | | - | help: desugar the match ergonomics: `&&&&&mut` - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:31:12 - | -LL | if let Some(&mut Some(Some(_))) = &mut Some(&mut Some(&mut Some(0u8))) {} - | ^^^^^^^^^^^^^^^^^^^^^^^^ - | -help: desugar the match ergonomics - | -LL | if let &mut Some(&mut Some(&mut Some(_))) = &mut Some(&mut Some(&mut Some(0u8))) {} - | ++++ ++++ - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:34:12 - | -LL | if let Some(&mut Some(Some(_a))) = &mut Some(&mut Some(&mut Some(0u8))) {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ - | -help: desugar the match ergonomics - | -LL | if let &mut Some(&mut Some(&mut Some(ref mut _a))) = &mut Some(&mut Some(&mut Some(0u8))) {} - | ++++ ++++ +++++++ - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:43:9 - | -LL | let Struct { a, mut b, c } = &s; - | ^^^^^^^^^^^^^^^^^^^^^^ - | -help: desugar the match ergonomics - | -LL | let &Struct { ref a, mut b, ref c } = &s; - | + +++ +++ - -warning: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:50:9 - | -LL | (Some(mut _x), match_ergonomics_2024_macros::mixed_edition_pat!(_y)) => { - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - | -note: the lint level is defined here - --> $DIR/match_ergonomics_2024.rs:46:12 - | -LL | #[warn(rust_2024_incompatible_pat)] - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ -help: desugar the match ergonomics - | -LL | &(Some(mut _x), match_ergonomics_2024_macros::mixed_edition_pat!(ref _y)) => { - | + +++ - -error: aborting due to 8 previous errors; 1 warning emitted - diff --git a/tests/ui/pattern/auxiliary/match_ergonomics_2024_macros.rs b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/auxiliary/migration_lint_macros.rs index 0b70e4404ab..0b70e4404ab 100644 --- a/tests/ui/pattern/auxiliary/match_ergonomics_2024_macros.rs +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/auxiliary/migration_lint_macros.rs diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.fixed b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.fixed new file mode 100644 index 00000000000..086671e69cb --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.fixed @@ -0,0 +1,144 @@ +//@ edition: 2021 +//@ run-rustfix +//@ rustfix-only-machine-applicable +//@ aux-build:migration_lint_macros.rs +#![feature(mut_ref)] +#![allow(incomplete_features, unused)] +#![deny(rust_2024_incompatible_pat)] + +extern crate migration_lint_macros; + +struct Foo<T>(T); + +// Tests type equality in a way that avoids coercing `&&T` to `&T`. +trait Eq<T> {} +impl<T> Eq<T> for T {} +fn assert_type_eq<T, U: Eq<T>>(_: T, _: U) {} + +fn main() { + let Foo(x) = &Foo(0); + assert_type_eq(x, &0u8); + + let Foo(x) = &mut Foo(0); + assert_type_eq(x, &mut 0u8); + + let &Foo(mut x) = &Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let &mut Foo(mut x) = &mut Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let &Foo(ref x) = &Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &0u8); + + let &mut Foo(ref x) = &mut Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &0u8); + + let &Foo(x) = &Foo(0); + assert_type_eq(x, 0u8); + + let &mut Foo(x) = &mut Foo(0); + assert_type_eq(x, 0u8); + + let &Foo(x) = &Foo(&0); + assert_type_eq(x, &0u8); + + let &mut Foo(x) = &mut Foo(&0); + assert_type_eq(x, &0u8); + + let &Foo(&x) = &Foo(&0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let &Foo(&mut x) = &Foo(&mut 0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let &mut Foo(&x) = &mut Foo(&0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let &mut Foo(&mut x) = &mut Foo(&mut 0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + if let Some(x) = &&&&&Some(&0u8) { + assert_type_eq(x, &&0u8); + } + + if let &&&&&Some(&x) = &&&&&Some(&0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let &&&&&Some(&mut x) = &&&&&Some(&mut 0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let &&&&&mut Some(&x) = &&&&&mut Some(&0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let &mut Some(&mut Some(&mut Some(ref mut x))) = &mut Some(&mut Some(&mut Some(0u8))) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &mut 0u8); + } + + struct Struct<A, B, C> { + a: A, + b: B, + c: C, + } + + let &Struct { ref a, mut b, ref c } = &Struct { a: 0, b: 0, c: 0 }; + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(a, &0u32); + assert_type_eq(b, 0u32); + + let &Struct { a: &a, ref b, ref c } = &Struct { a: &0, b: &0, c: &0 }; + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(a, 0u32); + assert_type_eq(b, &&0u32); + assert_type_eq(c, &&0u32); + + if let &Struct { a: &Some(a), b: &Some(&b), c: &Some(ref c) } = + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + &(Struct { a: &Some(&0), b: &Some(&0), c: &Some(&0) }) + { + assert_type_eq(a, &0u32); + assert_type_eq(b, 0u32); + assert_type_eq(c, &&0u32); + } + + match &(Some(0), Some(0)) { + // The two patterns are the same syntactically, but because they're defined in different + // editions they don't mean the same thing. + &(Some(mut x), migration_lint_macros::mixed_edition_pat!(y)) => { + //~^ ERROR: patterns are not allowed to reset the default binding mode + assert_type_eq(x, 0u32); + assert_type_eq(y, 0u32); + } + _ => {} + } +} diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.rs b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.rs new file mode 100644 index 00000000000..acceafdb7ec --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.rs @@ -0,0 +1,144 @@ +//@ edition: 2021 +//@ run-rustfix +//@ rustfix-only-machine-applicable +//@ aux-build:migration_lint_macros.rs +#![feature(mut_ref)] +#![allow(incomplete_features, unused)] +#![deny(rust_2024_incompatible_pat)] + +extern crate migration_lint_macros; + +struct Foo<T>(T); + +// Tests type equality in a way that avoids coercing `&&T` to `&T`. +trait Eq<T> {} +impl<T> Eq<T> for T {} +fn assert_type_eq<T, U: Eq<T>>(_: T, _: U) {} + +fn main() { + let Foo(x) = &Foo(0); + assert_type_eq(x, &0u8); + + let Foo(x) = &mut Foo(0); + assert_type_eq(x, &mut 0u8); + + let Foo(mut x) = &Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let Foo(mut x) = &mut Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let Foo(ref x) = &Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &0u8); + + let Foo(ref x) = &mut Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &0u8); + + let &Foo(x) = &Foo(0); + assert_type_eq(x, 0u8); + + let &mut Foo(x) = &mut Foo(0); + assert_type_eq(x, 0u8); + + let &Foo(x) = &Foo(&0); + assert_type_eq(x, &0u8); + + let &mut Foo(x) = &mut Foo(&0); + assert_type_eq(x, &0u8); + + let Foo(&x) = &Foo(&0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let Foo(&mut x) = &Foo(&mut 0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let Foo(&x) = &mut Foo(&0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let Foo(&mut x) = &mut Foo(&mut 0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + if let Some(x) = &&&&&Some(&0u8) { + assert_type_eq(x, &&0u8); + } + + if let Some(&x) = &&&&&Some(&0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let Some(&mut x) = &&&&&Some(&mut 0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let Some(&x) = &&&&&mut Some(&0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let Some(&mut Some(Some(x))) = &mut Some(&mut Some(&mut Some(0u8))) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &mut 0u8); + } + + struct Struct<A, B, C> { + a: A, + b: B, + c: C, + } + + let Struct { a, mut b, c } = &Struct { a: 0, b: 0, c: 0 }; + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(a, &0u32); + assert_type_eq(b, 0u32); + + let Struct { a: &a, b, ref c } = &Struct { a: &0, b: &0, c: &0 }; + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(a, 0u32); + assert_type_eq(b, &&0u32); + assert_type_eq(c, &&0u32); + + if let Struct { a: &Some(a), b: Some(&b), c: Some(c) } = + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + &(Struct { a: &Some(&0), b: &Some(&0), c: &Some(&0) }) + { + assert_type_eq(a, &0u32); + assert_type_eq(b, 0u32); + assert_type_eq(c, &&0u32); + } + + match &(Some(0), Some(0)) { + // The two patterns are the same syntactically, but because they're defined in different + // editions they don't mean the same thing. + (Some(mut x), migration_lint_macros::mixed_edition_pat!(y)) => { + //~^ ERROR: patterns are not allowed to reset the default binding mode + assert_type_eq(x, 0u32); + assert_type_eq(y, 0u32); + } + _ => {} + } +} diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.stderr b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.stderr new file mode 100644 index 00000000000..1c9a469e6ee --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.stderr @@ -0,0 +1,188 @@ +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:25:9 + | +LL | let Foo(mut x) = &Foo(0); + | -^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 +note: the lint level is defined here + --> $DIR/migration_lint.rs:7:9 + | +LL | #![deny(rust_2024_incompatible_pat)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:30:9 + | +LL | let Foo(mut x) = &mut Foo(0); + | -^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&mut` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:35:9 + | +LL | let Foo(ref x) = &Foo(0); + | -^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:40:9 + | +LL | let Foo(ref x) = &mut Foo(0); + | -^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&mut` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:57:9 + | +LL | let Foo(&x) = &Foo(&0); + | -^^^^^^ + | | + | help: desugar the match ergonomics: `&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:62:9 + | +LL | let Foo(&mut x) = &Foo(&mut 0); + | -^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:67:9 + | +LL | let Foo(&x) = &mut Foo(&0); + | -^^^^^^ + | | + | help: desugar the match ergonomics: `&mut` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:72:9 + | +LL | let Foo(&mut x) = &mut Foo(&mut 0); + | -^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&mut` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:81:12 + | +LL | if let Some(&x) = &&&&&Some(&0u8) { + | -^^^^^^^ + | | + | help: desugar the match ergonomics: `&&&&&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:87:12 + | +LL | if let Some(&mut x) = &&&&&Some(&mut 0u8) { + | -^^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&&&&&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:93:12 + | +LL | if let Some(&x) = &&&&&mut Some(&0u8) { + | -^^^^^^^ + | | + | help: desugar the match ergonomics: `&&&&&mut` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:99:12 + | +LL | if let Some(&mut Some(Some(x))) = &mut Some(&mut Some(&mut Some(0u8))) { + | ^^^^^^^^^^^^^^^^^^^^^^^^ + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 +help: desugar the match ergonomics + | +LL | if let &mut Some(&mut Some(&mut Some(ref mut x))) = &mut Some(&mut Some(&mut Some(0u8))) { + | ++++ ++++ +++++++ + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:111:9 + | +LL | let Struct { a, mut b, c } = &Struct { a: 0, b: 0, c: 0 }; + | ^^^^^^^^^^^^^^^^^^^^^^ + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 +help: desugar the match ergonomics + | +LL | let &Struct { ref a, mut b, ref c } = &Struct { a: 0, b: 0, c: 0 }; + | + +++ +++ + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:117:9 + | +LL | let Struct { a: &a, b, ref c } = &Struct { a: &0, b: &0, c: &0 }; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 +help: desugar the match ergonomics + | +LL | let &Struct { a: &a, ref b, ref c } = &Struct { a: &0, b: &0, c: &0 }; + | + +++ + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:124:12 + | +LL | if let Struct { a: &Some(a), b: Some(&b), c: Some(c) } = + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 +help: desugar the match ergonomics + | +LL | if let &Struct { a: &Some(a), b: &Some(&b), c: &Some(ref c) } = + | + + + +++ + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:137:9 + | +LL | (Some(mut x), migration_lint_macros::mixed_edition_pat!(y)) => { + | -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: aborting due to 16 previous errors + diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.rs b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.rs new file mode 100644 index 00000000000..a822c90ab6e --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.rs @@ -0,0 +1,46 @@ +//@ check-fail +//@ edition: 2024 +//@ compile-flags: -Zunstable-options +#![deny(rust_2024_incompatible_pat)] + +fn main() {} + +#[derive(Copy, Clone)] +struct T; + +struct Foo { + f: &'static (u8,), +} + +macro_rules! test_pat_on_type { + ($($tt:tt)*) => { + const _: () = { + // Define a new function to ensure all cases are tested independently. + fn foo($($tt)*) {} + }; + }; +} + +test_pat_on_type![(&x,): &(T,)]; //~ ERROR mismatched types +test_pat_on_type![(&x,): &(&T,)]; //~ ERROR patterns are not allowed to reset the default binding mode +test_pat_on_type![(&x,): &(&mut T,)]; //~ ERROR mismatched types +test_pat_on_type![(&mut x,): &(&T,)]; //~ ERROR mismatched types +test_pat_on_type![(&mut x,): &(&mut T,)]; //~ ERROR patterns are not allowed to reset the default binding mode +test_pat_on_type![(&x,): &&mut &(T,)]; //~ ERROR mismatched types +test_pat_on_type![Foo { f: (&x,) }: Foo]; //~ ERROR mismatched types +test_pat_on_type![Foo { f: (&x,) }: &mut Foo]; //~ ERROR mismatched types +test_pat_on_type![Foo { f: &(x,) }: &Foo]; //~ ERROR patterns are not allowed to reset the default binding mode +test_pat_on_type![(mut x,): &(T,)]; //~ ERROR patterns are not allowed to reset the default binding mode +test_pat_on_type![(ref x,): &(T,)]; //~ ERROR patterns are not allowed to reset the default binding mode +test_pat_on_type![(ref mut x,): &mut (T,)]; //~ ERROR patterns are not allowed to reset the default binding mode + +fn get<X>() -> X { + unimplemented!() +} + +// Make sure this works even when the underlying type is inferred. This test passes on rust stable. +fn infer<X: Copy>() -> X { + match &get() { + (&x,) => x, //~ ERROR patterns are not allowed to reset the default binding mode + } +} diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.stderr b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.stderr new file mode 100644 index 00000000000..33e4f0021b7 --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.stderr @@ -0,0 +1,160 @@ +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:24:20 + | +LL | test_pat_on_type![(&x,): &(T,)]; + | ^^ ----- expected due to this + | | + | expected `T`, found `&_` + | + = note: expected struct `T` + found reference `&_` +help: consider removing `&` from the pattern + | +LL - test_pat_on_type![(&x,): &(T,)]; +LL + test_pat_on_type![(x,): &(T,)]; + | + +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:26:20 + | +LL | test_pat_on_type![(&x,): &(&mut T,)]; + | ^^ ---------- expected due to this + | | + | types differ in mutability + | + = note: expected mutable reference `&mut T` + found reference `&_` +help: consider removing `&` from the pattern + | +LL - test_pat_on_type![(&x,): &(&mut T,)]; +LL + test_pat_on_type![(x,): &(&mut T,)]; + | + +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:27:20 + | +LL | test_pat_on_type![(&mut x,): &(&T,)]; + | ^^^^^^ ------ expected due to this + | | + | types differ in mutability + | + = note: expected reference `&T` + found mutable reference `&mut _` +note: to declare a mutable binding use: `mut x` + --> $DIR/min_match_ergonomics_fail.rs:27:20 + | +LL | test_pat_on_type![(&mut x,): &(&T,)]; + | ^^^^^^ +help: consider removing `&mut` from the pattern + | +LL - test_pat_on_type![(&mut x,): &(&T,)]; +LL + test_pat_on_type![(x,): &(&T,)]; + | + +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:29:20 + | +LL | test_pat_on_type![(&x,): &&mut &(T,)]; + | ^^ ----------- expected due to this + | | + | expected `T`, found `&_` + | + = note: expected struct `T` + found reference `&_` +help: consider removing `&` from the pattern + | +LL - test_pat_on_type![(&x,): &&mut &(T,)]; +LL + test_pat_on_type![(x,): &&mut &(T,)]; + | + +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:30:29 + | +LL | test_pat_on_type![Foo { f: (&x,) }: Foo]; + | ^^ --- expected due to this + | | + | expected `u8`, found `&_` + | + = note: expected type `u8` + found reference `&_` +help: consider removing `&` from the pattern + | +LL - test_pat_on_type![Foo { f: (&x,) }: Foo]; +LL + test_pat_on_type![Foo { f: (x,) }: Foo]; + | + +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:31:29 + | +LL | test_pat_on_type![Foo { f: (&x,) }: &mut Foo]; + | ^^ -------- expected due to this + | | + | expected `u8`, found `&_` + | + = note: expected type `u8` + found reference `&_` +help: consider removing `&` from the pattern + | +LL - test_pat_on_type![Foo { f: (&x,) }: &mut Foo]; +LL + test_pat_on_type![Foo { f: (x,) }: &mut Foo]; + | + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:25:19 + | +LL | test_pat_on_type![(&x,): &(&T,)]; + | -^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:28:19 + | +LL | test_pat_on_type![(&mut x,): &(&mut T,)]; + | -^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:32:19 + | +LL | test_pat_on_type![Foo { f: &(x,) }: &Foo]; + | -^^^^^^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:33:19 + | +LL | test_pat_on_type![(mut x,): &(T,)]; + | -^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:34:19 + | +LL | test_pat_on_type![(ref x,): &(T,)]; + | -^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:35:19 + | +LL | test_pat_on_type![(ref mut x,): &mut (T,)]; + | -^^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&mut` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:44:9 + | +LL | (&x,) => x, + | -^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: aborting due to 13 previous errors + +For more information about this error, try `rustc --explain E0308`. diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_success.rs b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_success.rs new file mode 100644 index 00000000000..0fb448afca9 --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_success.rs @@ -0,0 +1,17 @@ +//@ check-pass +#![allow(incomplete_features)] + +fn main() {} + +// Tests type equality in a way that avoids coercing `&&T` to `&T`. +trait Eq<T> {} +impl<T> Eq<T> for T {} +fn assert_type_eq<T, U: Eq<T>>(_: T, _: U) {} + +#[derive(Copy, Clone)] +struct T; + +fn test() { + let (x,) = &(&T,); + assert_type_eq(x, &&T); +} |
