From 6679e2c2f2f5e123b845db4554a1cc8c9a6abd79 Mon Sep 17 00:00:00 2001 From: Oli Scherer Date: Thu, 11 Jan 2024 20:33:52 +0000 Subject: [PATCH] Register even erroneous impls Otherwise the specialization graph fails to pick it up, even though other code assumes that all impl blocks have an entry in the specialization graph. --- compiler/rustc_middle/src/ty/fast_reject.rs | 4 +- compiler/rustc_middle/src/ty/trait_def.rs | 4 - .../unknown-lifetime-ice-119827.rs | 16 +++ .../unknown-lifetime-ice-119827.stderr | 119 ++++++++++++++++++ 4 files changed, 138 insertions(+), 5 deletions(-) create mode 100644 tests/ui/generic-associated-types/unknown-lifetime-ice-119827.rs create mode 100644 tests/ui/generic-associated-types/unknown-lifetime-ice-119827.stderr diff --git a/compiler/rustc_middle/src/ty/fast_reject.rs b/compiler/rustc_middle/src/ty/fast_reject.rs index 6ed68f90eb3..b71919adc58 100644 --- a/compiler/rustc_middle/src/ty/fast_reject.rs +++ b/compiler/rustc_middle/src/ty/fast_reject.rs @@ -32,6 +32,7 @@ pub enum SimplifiedType { CoroutineWitness(DefId), Function(usize), Placeholder, + Error, } /// Generic parameters are pretty much just bound variables, e.g. @@ -153,7 +154,8 @@ pub fn simplify_type<'tcx>( TreatParams::ForLookup | TreatParams::AsCandidateKey => None, }, ty::Foreign(def_id) => Some(SimplifiedType::Foreign(def_id)), - ty::Bound(..) | ty::Infer(_) | ty::Error(_) => None, + ty::Error(_) => Some(SimplifiedType::Error), + ty::Bound(..) | ty::Infer(_) => None, } } diff --git a/compiler/rustc_middle/src/ty/trait_def.rs b/compiler/rustc_middle/src/ty/trait_def.rs index bf9b244936f..227a0753d04 100644 --- a/compiler/rustc_middle/src/ty/trait_def.rs +++ b/compiler/rustc_middle/src/ty/trait_def.rs @@ -1,6 +1,5 @@ use crate::traits::specialization_graph; use crate::ty::fast_reject::{self, SimplifiedType, TreatParams, TreatProjections}; -use crate::ty::visit::TypeVisitableExt; use crate::ty::{Ident, Ty, TyCtxt}; use hir::def_id::LOCAL_CRATE; use rustc_hir as hir; @@ -241,9 +240,6 @@ pub(super) fn trait_impls_of_provider(tcx: TyCtxt<'_>, trait_id: DefId) -> Trait let impl_def_id = impl_def_id.to_def_id(); let impl_self_ty = tcx.type_of(impl_def_id).instantiate_identity(); - if impl_self_ty.references_error() { - continue; - } if let Some(simplified_self_ty) = fast_reject::simplify_type(tcx, impl_self_ty, TreatParams::AsCandidateKey) diff --git a/tests/ui/generic-associated-types/unknown-lifetime-ice-119827.rs b/tests/ui/generic-associated-types/unknown-lifetime-ice-119827.rs new file mode 100644 index 00000000000..cd3acf9bc41 --- /dev/null +++ b/tests/ui/generic-associated-types/unknown-lifetime-ice-119827.rs @@ -0,0 +1,16 @@ +trait Foo { + type Context<'c> + where + Self: 'c; +} + +impl Foo for Box {} +//~^ ERROR `Foo` cannot be made into an object +//~| ERROR `Foo` cannot be made into an object +//~| ERROR cycle detected +//~| ERROR cycle detected +//~| ERROR cycle detected +//~| ERROR the trait bound `Box<(dyn Foo + 'static)>: Foo` is not satisfied +//~| ERROR not all trait items implemented + +fn main() {} diff --git a/tests/ui/generic-associated-types/unknown-lifetime-ice-119827.stderr b/tests/ui/generic-associated-types/unknown-lifetime-ice-119827.stderr new file mode 100644 index 00000000000..8e6b69f7461 --- /dev/null +++ b/tests/ui/generic-associated-types/unknown-lifetime-ice-119827.stderr @@ -0,0 +1,119 @@ +error[E0391]: cycle detected when computing type of `` + --> $DIR/unknown-lifetime-ice-119827.rs:7:1 + | +LL | impl Foo for Box {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^ + | +note: ...which requires finding trait impls of `Foo`... + --> $DIR/unknown-lifetime-ice-119827.rs:1:1 + | +LL | trait Foo { + | ^^^^^^^^^ + = note: ...which again requires computing type of ``, completing the cycle +note: cycle used when collecting item types in top-level module + --> $DIR/unknown-lifetime-ice-119827.rs:1:1 + | +LL | / trait Foo { +LL | | type Context<'c> +LL | | where +LL | | Self: 'c; +... | +LL | | +LL | | fn main() {} + | |____________^ + = note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information + +error[E0391]: cycle detected when computing type of `` + --> $DIR/unknown-lifetime-ice-119827.rs:7:1 + | +LL | impl Foo for Box {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = note: ...which immediately requires computing type of `` again +note: cycle used when collecting item types in top-level module + --> $DIR/unknown-lifetime-ice-119827.rs:1:1 + | +LL | / trait Foo { +LL | | type Context<'c> +LL | | where +LL | | Self: 'c; +... | +LL | | +LL | | fn main() {} + | |____________^ + = note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information + +error[E0391]: cycle detected when computing type of `` + --> $DIR/unknown-lifetime-ice-119827.rs:7:1 + | +LL | impl Foo for Box {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = note: ...which immediately requires computing type of `` again +note: cycle used when collecting item types in top-level module + --> $DIR/unknown-lifetime-ice-119827.rs:1:1 + | +LL | / trait Foo { +LL | | type Context<'c> +LL | | where +LL | | Self: 'c; +... | +LL | | +LL | | fn main() {} + | |____________^ + = note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` + +error[E0038]: the trait `Foo` cannot be made into an object + --> $DIR/unknown-lifetime-ice-119827.rs:7:22 + | +LL | impl Foo for Box {} + | ^^^ `Foo` cannot be made into an object + | +note: for a trait to be "object safe" it needs to allow building a vtable to allow the call to be resolvable dynamically; for more information visit + --> $DIR/unknown-lifetime-ice-119827.rs:2:10 + | +LL | trait Foo { + | --- this trait cannot be made into an object... +LL | type Context<'c> + | ^^^^^^^ ...because it contains the generic associated type `Context` + = help: consider moving `Context` to another trait + = help: only type `{type error}` implements the trait, consider using it directly instead + +error[E0277]: the trait bound `Box<(dyn Foo + 'static)>: Foo` is not satisfied + --> $DIR/unknown-lifetime-ice-119827.rs:7:14 + | +LL | impl Foo for Box {} + | ^^^^^^^^^^^^ the trait `Foo` is not implemented for `Box<(dyn Foo + 'static)>` + | + = help: the trait `Foo` is implemented for `Box<(dyn Foo + 'static)>` + +error[E0038]: the trait `Foo` cannot be made into an object + --> $DIR/unknown-lifetime-ice-119827.rs:7:14 + | +LL | impl Foo for Box {} + | ^^^^^^^^^^^^ `Foo` cannot be made into an object + | +note: for a trait to be "object safe" it needs to allow building a vtable to allow the call to be resolvable dynamically; for more information visit + --> $DIR/unknown-lifetime-ice-119827.rs:2:10 + | +LL | trait Foo { + | --- this trait cannot be made into an object... +LL | type Context<'c> + | ^^^^^^^ ...because it contains the generic associated type `Context` + = help: consider moving `Context` to another trait + = help: only type `std::boxed::Box<(dyn Foo + 'static)>` implements the trait, consider using it directly instead + +error[E0046]: not all trait items implemented, missing: `Context` + --> $DIR/unknown-lifetime-ice-119827.rs:7:1 + | +LL | type Context<'c> + | ---------------- `Context` from trait +... +LL | impl Foo for Box {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^ missing `Context` in implementation + +error: aborting due to 7 previous errors + +Some errors have detailed explanations: E0038, E0046, E0277, E0391. +For more information about an error, try `rustc --explain E0038`.