diff --git a/tests/ui/coercion/coerce-issue-49593-box-never.e2021.stderr b/tests/ui/coercion/coerce-issue-49593-box-never.e2021.stderr new file mode 100644 index 000000000000..214c37febc06 --- /dev/null +++ b/tests/ui/coercion/coerce-issue-49593-box-never.e2021.stderr @@ -0,0 +1,19 @@ +error[E0277]: the trait bound `(): std::error::Error` is not satisfied + --> $DIR/coerce-issue-49593-box-never.rs:28:5 + | +LL | Box::new(x) + | ^^^^^^^^^^^ the trait `std::error::Error` is not implemented for `()` + | + = note: required for the cast from `Box<()>` to `Box<(dyn std::error::Error + 'static)>` + +error[E0277]: the trait bound `(): std::error::Error` is not satisfied + --> $DIR/coerce-issue-49593-box-never.rs:33:5 + | +LL | raw_ptr(x) + | ^^^^^^^^^^ the trait `std::error::Error` is not implemented for `()` + | + = note: required for the cast from `*mut ()` to `*mut (dyn std::error::Error + 'static)` + +error: aborting due to 2 previous errors + +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/coercion/coerce-issue-49593-box-never.rs b/tests/ui/coercion/coerce-issue-49593-box-never.rs index 6706d07e1f76..751450a7fb43 100644 --- a/tests/ui/coercion/coerce-issue-49593-box-never.rs +++ b/tests/ui/coercion/coerce-issue-49593-box-never.rs @@ -1,57 +1,37 @@ -//@ revisions: nofallback fallback -//@[fallback] edition: 2024 -//@[fallback] check-pass +// Regression test for . +// +// This checks that we can construct `Box` by calling `Box::new` +// with a value of the never type. And similarly for raw pointers. +// +// This used to fail because we tried to coerce `! -> dyn Error`, which then +// failed because we were trying to pass an unsized value by value, etc. +// +// On edition <= 2021 this currently fails because of never type fallback to +// unit. +// +//@ revisions: e2021 e2024 +//@[e2021] edition: 2021 +//@[e2024] edition: 2024 +// +//@[e2024] check-pass #![feature(never_type)] use std::error::Error; use std::mem; -fn raw_ptr_box(t: T) -> *mut T { +fn raw_ptr(t: T) -> *mut T { panic!() } fn foo(x: !) -> Box { - // Method resolution will generate new inference vars and relate them. - // Thus fallback will not fall back to `!`, but `()` instead. - Box::<_ /* ! */>::new(x) - //[nofallback]~^ ERROR trait bound `(): std::error::Error` is not satisfied + Box::new(x) + //[e2021]~^ ERROR trait bound `(): std::error::Error` is not satisfied } fn foo_raw_ptr(x: !) -> *mut dyn Error { - /* *mut $0 is coerced to *mut Error here */ - raw_ptr_box::<_ /* ! */>(x) - //[nofallback]~^ ERROR trait bound `(): std::error::Error` is not satisfied -} - -fn no_coercion(d: *mut dyn Error) -> *mut dyn Error { - /* an unsize coercion won't compile here, and it is indeed not used - because there is nothing requiring the _ to be Sized */ - d as *mut _ -} - -trait Xyz {} -struct S; -struct T; -impl Xyz for S {} -impl Xyz for T {} - -fn foo_no_never() { - let mut x /* : Option */ = None; - let mut first_iter = false; - loop { - if !first_iter { - let y: Box - = /* Box<$0> is coerced to Box here */ Box::new(x.unwrap()); - } - - x = Some(S); - first_iter = true; - } - - let mut y: Option = None; - // assert types are equal - mem::swap(&mut x, &mut y); + raw_ptr(x) + //[e2021]~^ ERROR trait bound `(): std::error::Error` is not satisfied } fn main() {}