diff options
| author | Oli Scherer <git-spam-no-reply9815368754983@oli-obk.de> | 2022-02-10 14:53:50 +0000 |
|---|---|---|
| committer | Oli Scherer <git-spam-no-reply9815368754983@oli-obk.de> | 2022-03-28 16:29:54 +0000 |
| commit | 1c5bfb17703975ff9952243c24c46cf54fe0d49c (patch) | |
| tree | 97957c637ce3e87550fe69caf11dad04134fd9eb | |
| parent | f42a6793ce3d32a8d414519b8ec82141f7996479 (diff) | |
| download | rust-1c5bfb17703975ff9952243c24c46cf54fe0d49c.tar.gz rust-1c5bfb17703975ff9952243c24c46cf54fe0d49c.zip | |
Don't bind hidden types when searching for matching impls
7 files changed, 74 insertions, 39 deletions
diff --git a/compiler/rustc_trait_selection/src/traits/select/mod.rs b/compiler/rustc_trait_selection/src/traits/select/mod.rs index 9b8a49e512b..76526df6461 100644 --- a/compiler/rustc_trait_selection/src/traits/select/mod.rs +++ b/compiler/rustc_trait_selection/src/traits/select/mod.rs @@ -2163,6 +2163,7 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> { let InferOk { obligations, .. } = self .infcx .at(&cause, obligation.param_env) + .define_opaque_types(false) .eq(placeholder_obligation_trait_ref, impl_trait_ref) .map_err(|e| debug!("match_impl: failed eq_trait_refs due to `{}`", e))?; nested_obligations.extend(obligations); diff --git a/src/test/ui/impl-trait/nested_impl_trait.rs b/src/test/ui/impl-trait/nested_impl_trait.rs index ec2d49d9367..85c6f8c462c 100644 --- a/src/test/ui/impl-trait/nested_impl_trait.rs +++ b/src/test/ui/impl-trait/nested_impl_trait.rs @@ -4,7 +4,7 @@ fn fine(x: impl Into<u32>) -> impl Into<u32> { x } fn bad_in_ret_position(x: impl Into<u32>) -> impl Into<impl Debug> { x } //~^ ERROR nested `impl Trait` is not allowed -//~| ERROR `impl Into<u32>` doesn't implement `Debug` +//~| ERROR the trait bound `impl Debug: From<impl Into<u32>>` is not satisfied fn bad_in_fn_syntax(x: fn() -> impl Into<impl Debug>) {} //~^ ERROR nested `impl Trait` is not allowed @@ -17,7 +17,7 @@ struct X; impl X { fn bad(x: impl Into<u32>) -> impl Into<impl Debug> { x } //~^ ERROR nested `impl Trait` is not allowed - //~| ERROR `impl Into<u32>` doesn't implement `Debug` + //~| ERROR the trait bound `impl Debug: From<impl Into<u32>>` is not satisfied } fn allowed_in_assoc_type() -> impl Iterator<Item=impl Fn()> { diff --git a/src/test/ui/impl-trait/nested_impl_trait.stderr b/src/test/ui/impl-trait/nested_impl_trait.stderr index 248d1254ef7..a10e4ec3182 100644 --- a/src/test/ui/impl-trait/nested_impl_trait.stderr +++ b/src/test/ui/impl-trait/nested_impl_trait.stderr @@ -46,27 +46,21 @@ error[E0562]: `impl Trait` only allowed in function and inherent method return t LL | fn allowed_in_ret_type() -> impl Fn() -> impl Into<u32> { | ^^^^^^^^^^^^^^ -error[E0277]: `impl Into<u32>` doesn't implement `Debug` +error[E0277]: the trait bound `impl Debug: From<impl Into<u32>>` is not satisfied --> $DIR/nested_impl_trait.rs:5:70 | LL | fn bad_in_ret_position(x: impl Into<u32>) -> impl Into<impl Debug> { x } - | ^ `impl Into<u32>` cannot be formatted using `{:?}` because it doesn't implement `Debug` + | ^ the trait `From<impl Into<u32>>` is not implemented for `impl Debug` | -help: consider further restricting this bound - | -LL | fn bad_in_ret_position(x: impl Into<u32> + std::fmt::Debug) -> impl Into<impl Debug> { x } - | +++++++++++++++++ + = note: required because of the requirements on the impl of `Into<impl Debug>` for `impl Into<u32>` -error[E0277]: `impl Into<u32>` doesn't implement `Debug` +error[E0277]: the trait bound `impl Debug: From<impl Into<u32>>` is not satisfied --> $DIR/nested_impl_trait.rs:18:58 | LL | fn bad(x: impl Into<u32>) -> impl Into<impl Debug> { x } - | ^ `impl Into<u32>` cannot be formatted using `{:?}` because it doesn't implement `Debug` - | -help: consider further restricting this bound + | ^ the trait `From<impl Into<u32>>` is not implemented for `impl Debug` | -LL | fn bad(x: impl Into<u32> + std::fmt::Debug) -> impl Into<impl Debug> { x } - | +++++++++++++++++ + = note: required because of the requirements on the impl of `Into<impl Debug>` for `impl Into<u32>` error: aborting due to 8 previous errors diff --git a/src/test/ui/impl-trait/recursive-type-alias-impl-trait-declaration-too-subtle-2.rs b/src/test/ui/impl-trait/recursive-type-alias-impl-trait-declaration-too-subtle-2.rs new file mode 100644 index 00000000000..6b200d7e3a8 --- /dev/null +++ b/src/test/ui/impl-trait/recursive-type-alias-impl-trait-declaration-too-subtle-2.rs @@ -0,0 +1,17 @@ +#![feature(type_alias_impl_trait)] + +type Foo = impl PartialEq<(Foo, i32)>; + +struct Bar; + +impl PartialEq<(Foo, i32)> for Bar { + fn eq(&self, _other: &(Foo, i32)) -> bool { + true + } +} + +fn foo() -> Foo { + Bar //~ ERROR can't compare `Bar` with `(Bar, i32)` +} + +fn main() {} diff --git a/src/test/ui/impl-trait/recursive-type-alias-impl-trait-declaration-too-subtle-2.stderr b/src/test/ui/impl-trait/recursive-type-alias-impl-trait-declaration-too-subtle-2.stderr new file mode 100644 index 00000000000..5476bf9d277 --- /dev/null +++ b/src/test/ui/impl-trait/recursive-type-alias-impl-trait-declaration-too-subtle-2.stderr @@ -0,0 +1,11 @@ +error[E0277]: can't compare `Bar` with `(Bar, i32)` + --> $DIR/recursive-type-alias-impl-trait-declaration-too-subtle-2.rs:14:5 + | +LL | Bar + | ^^^ no implementation for `Bar == (Bar, i32)` + | + = help: the trait `PartialEq<(Bar, i32)>` is not implemented for `Bar` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0277`. diff --git a/src/test/ui/impl-trait/recursive-type-alias-impl-trait-declaration.rs b/src/test/ui/impl-trait/recursive-type-alias-impl-trait-declaration.rs index bdabc13c36a..ad0a003e879 100644 --- a/src/test/ui/impl-trait/recursive-type-alias-impl-trait-declaration.rs +++ b/src/test/ui/impl-trait/recursive-type-alias-impl-trait-declaration.rs @@ -2,36 +2,18 @@ #![feature(type_alias_impl_trait)] -mod direct { - type Foo = impl PartialEq<(Foo, i32)>; +type Foo = impl PartialEq<(Foo, i32)>; - struct Bar; +struct Bar; - impl PartialEq<(Foo, i32)> for Bar { - fn eq(&self, _other: &(Foo, i32)) -> bool { - true - } - } - - fn foo() -> Foo { - Bar +impl PartialEq<(Bar, i32)> for Bar { + fn eq(&self, _other: &(Bar, i32)) -> bool { + true } } -mod indirect { - type Foo = impl PartialEq<(Foo, i32)>; - - struct Bar; - - impl PartialEq<(Bar, i32)> for Bar { - fn eq(&self, _other: &(Bar, i32)) -> bool { - true - } - } - - fn foo() -> Foo { - Bar - } +fn foo() -> Foo { + Bar } fn main() {} diff --git a/src/test/ui/impl-trait/trait_resolution.rs b/src/test/ui/impl-trait/trait_resolution.rs new file mode 100644 index 00000000000..8dcbbfd6e64 --- /dev/null +++ b/src/test/ui/impl-trait/trait_resolution.rs @@ -0,0 +1,30 @@ +// check-pass + +use std::fmt::Debug; + +pub struct EventStream<S> { + stream: S, +} + +impl<S: Debug> EventStream<S> { + fn into_stream(self) -> impl Debug { + unimplemented!() + } + + pub fn into_reader(self) -> impl Debug { + ReaderStream::from(self.into_stream()) + } +} + +#[derive(Debug)] +pub struct ReaderStream<S> { + stream: S, +} + +impl<S> From<S> for ReaderStream<S> { + fn from(stream: S) -> Self { + ReaderStream { stream } + } +} + +fn main() {} |
