diff --git a/compiler/rustc_middle/src/query/mod.rs b/compiler/rustc_middle/src/query/mod.rs index e0b4eced075e9..e1f7408cbf863 100644 --- a/compiler/rustc_middle/src/query/mod.rs +++ b/compiler/rustc_middle/src/query/mod.rs @@ -906,9 +906,10 @@ rustc_queries! { /// Checks whether all impls in the crate pass the overlap check, returning /// which impls fail it. If all impls are correct, the returned slice is empty. - query orphan_check_crate(_: ()) -> &'tcx [LocalDefId] { - desc { - "checking whether the immpl in the this crate follow the orphan rules", + query orphan_check_impl(key: LocalDefId) -> Result<(), ErrorGuaranteed> { + desc { |tcx| + "checking whether impl `{}` follows the orphan rules", + tcx.def_path_str(key.to_def_id()), } } diff --git a/compiler/rustc_trait_selection/src/traits/specialize/mod.rs b/compiler/rustc_trait_selection/src/traits/specialize/mod.rs index 95f1e224a4c7f..a1861529b5964 100644 --- a/compiler/rustc_trait_selection/src/traits/specialize/mod.rs +++ b/compiler/rustc_trait_selection/src/traits/specialize/mod.rs @@ -452,7 +452,7 @@ fn report_conflicting_impls( match used_to_be_allowed { None => { let reported = if overlap.with_impl.is_local() - || !tcx.orphan_check_crate(()).contains(&impl_def_id) + || tcx.orphan_check_impl(impl_def_id).is_ok() { let err = struct_span_err!(tcx.sess, impl_span, E0119, ""); Some(decorate( diff --git a/compiler/rustc_typeck/src/coherence/mod.rs b/compiler/rustc_typeck/src/coherence/mod.rs index 3903448a00731..447ec87f30264 100644 --- a/compiler/rustc_typeck/src/coherence/mod.rs +++ b/compiler/rustc_typeck/src/coherence/mod.rs @@ -146,7 +146,7 @@ pub fn provide(providers: &mut Providers) { use self::builtin::coerce_unsized_info; use self::inherent_impls::{crate_incoherent_impls, crate_inherent_impls, inherent_impls}; use self::inherent_impls_overlap::crate_inherent_impls_overlap_check; - use self::orphan::orphan_check_crate; + use self::orphan::orphan_check_impl; *providers = Providers { coherent_trait, @@ -155,7 +155,7 @@ pub fn provide(providers: &mut Providers) { inherent_impls, crate_inherent_impls_overlap_check, coerce_unsized_info, - orphan_check_crate, + orphan_check_impl, ..*providers }; } @@ -171,21 +171,12 @@ fn coherent_trait(tcx: TyCtxt<'_>, def_id: DefId) { check_impl(tcx, impl_def_id, trait_ref); check_object_overlap(tcx, impl_def_id, trait_ref); - } - builtin::check_trait(tcx, def_id); -} -pub fn check_coherence(tcx: TyCtxt<'_>) { - tcx.sess.time("unsafety_checking", || unsafety::check(tcx)); - tcx.ensure().orphan_check_crate(()); - - for &trait_def_id in tcx.all_local_trait_impls(()).keys() { - tcx.ensure().coherent_trait(trait_def_id); + tcx.sess.time("unsafety_checking", || unsafety::check_item(tcx, impl_def_id)); + tcx.sess.time("orphan_checking", || tcx.ensure().orphan_check_impl(impl_def_id)); } - // these queries are executed for side-effects (error reporting): - tcx.ensure().crate_inherent_impls(()); - tcx.ensure().crate_inherent_impls_overlap_check(()); + builtin::check_trait(tcx, def_id); } /// Checks whether an impl overlaps with the automatic `impl Trait for dyn Trait`. diff --git a/compiler/rustc_typeck/src/coherence/orphan.rs b/compiler/rustc_typeck/src/coherence/orphan.rs index 9ddfc8d5cc82b..f3a043a08a302 100644 --- a/compiler/rustc_typeck/src/coherence/orphan.rs +++ b/compiler/rustc_typeck/src/coherence/orphan.rs @@ -18,26 +18,29 @@ use rustc_span::Span; use rustc_trait_selection::traits; use std::ops::ControlFlow; -pub(super) fn orphan_check_crate(tcx: TyCtxt<'_>, (): ()) -> &[LocalDefId] { - let mut errors = Vec::new(); - for (&trait_def_id, impls_of_trait) in tcx.all_local_trait_impls(()) { - for &impl_of_trait in impls_of_trait { - match orphan_check_impl(tcx, impl_of_trait) { - Ok(()) => {} - Err(_) => errors.push(impl_of_trait), - } - } +#[instrument(skip(tcx), level = "debug")] +pub(crate) fn orphan_check_impl( + tcx: TyCtxt<'_>, + impl_def_id: LocalDefId, +) -> Result<(), ErrorGuaranteed> { + let trait_ref = tcx.impl_trait_ref(impl_def_id).unwrap(); + if let Some(err) = trait_ref.error_reported() { + return Err(err); + } - if tcx.trait_is_auto(trait_def_id) { - lint_auto_trait_impls(tcx, trait_def_id, impls_of_trait); - } + let ret = do_orphan_check_impl(tcx, trait_ref, impl_def_id); + if tcx.trait_is_auto(trait_ref.def_id) { + lint_auto_trait_impl(tcx, trait_ref, impl_def_id); } - tcx.arena.alloc_slice(&errors) + + ret } -#[instrument(skip(tcx), level = "debug")] -fn orphan_check_impl(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Result<(), ErrorGuaranteed> { - let trait_ref = tcx.impl_trait_ref(def_id).unwrap(); +fn do_orphan_check_impl<'tcx>( + tcx: TyCtxt<'tcx>, + trait_ref: ty::TraitRef<'tcx>, + def_id: LocalDefId, +) -> Result<(), ErrorGuaranteed> { let trait_def_id = trait_ref.def_id; let item = tcx.hir().item(hir::ItemId { def_id }); @@ -329,89 +332,82 @@ fn emit_orphan_check_error<'tcx>( /// Lint impls of auto traits if they are likely to have /// unsound or surprising effects on auto impls. -fn lint_auto_trait_impls(tcx: TyCtxt<'_>, trait_def_id: DefId, impls: &[LocalDefId]) { - let mut non_covering_impls = Vec::new(); - for &impl_def_id in impls { - let trait_ref = tcx.impl_trait_ref(impl_def_id).unwrap(); - if trait_ref.references_error() { - return; - } +fn lint_auto_trait_impl<'tcx>( + tcx: TyCtxt<'tcx>, + trait_ref: ty::TraitRef<'tcx>, + impl_def_id: LocalDefId, +) { + if tcx.impl_polarity(impl_def_id) != ImplPolarity::Positive { + return; + } - if tcx.impl_polarity(impl_def_id) != ImplPolarity::Positive { + assert_eq!(trait_ref.substs.len(), 1); + let self_ty = trait_ref.self_ty(); + let (self_type_did, substs) = match self_ty.kind() { + ty::Adt(def, substs) => (def.did(), substs), + _ => { + // FIXME: should also lint for stuff like `&i32` but + // considering that auto traits are unstable, that + // isn't too important for now as this only affects + // crates using `nightly`, and std. return; } + }; - assert_eq!(trait_ref.substs.len(), 1); - let self_ty = trait_ref.self_ty(); - let (self_type_did, substs) = match self_ty.kind() { - ty::Adt(def, substs) => (def.did(), substs), - _ => { - // FIXME: should also lint for stuff like `&i32` but - // considering that auto traits are unstable, that - // isn't too important for now as this only affects - // crates using `nightly`, and std. - continue; - } - }; + // Impls which completely cover a given root type are fine as they + // disable auto impls entirely. So only lint if the substs + // are not a permutation of the identity substs. + let Err(arg) = tcx.uses_unique_generic_params(substs, IgnoreRegions::Yes) else { + // ok + return; + }; - // Impls which completely cover a given root type are fine as they - // disable auto impls entirely. So only lint if the substs - // are not a permutation of the identity substs. - match tcx.uses_unique_generic_params(substs, IgnoreRegions::Yes) { - Ok(()) => {} // ok - Err(arg) => { - // Ideally: - // - // - compute the requirements for the auto impl candidate - // - check whether these are implied by the non covering impls - // - if not, emit the lint - // - // What we do here is a bit simpler: - // - // - badly check if an auto impl candidate definitely does not apply - // for the given simplified type - // - if so, do not lint - if fast_reject_auto_impl(tcx, trait_def_id, self_ty) { - // ok - } else { - non_covering_impls.push((impl_def_id, self_type_did, arg)); - } - } - } + // Ideally: + // + // - compute the requirements for the auto impl candidate + // - check whether these are implied by the non covering impls + // - if not, emit the lint + // + // What we do here is a bit simpler: + // + // - badly check if an auto impl candidate definitely does not apply + // for the given simplified type + // - if so, do not lint + if fast_reject_auto_impl(tcx, trait_ref.def_id, self_ty) { + // ok + return; } - for &(impl_def_id, self_type_did, arg) in &non_covering_impls { - tcx.struct_span_lint_hir( - lint::builtin::SUSPICIOUS_AUTO_TRAIT_IMPLS, - tcx.hir().local_def_id_to_hir_id(impl_def_id), - tcx.def_span(impl_def_id), - |err| { - let item_span = tcx.def_span(self_type_did); - let self_descr = tcx.def_kind(self_type_did).descr(self_type_did); - let mut err = err.build(&format!( - "cross-crate traits with a default impl, like `{}`, \ + tcx.struct_span_lint_hir( + lint::builtin::SUSPICIOUS_AUTO_TRAIT_IMPLS, + tcx.hir().local_def_id_to_hir_id(impl_def_id), + tcx.def_span(impl_def_id), + |err| { + let item_span = tcx.def_span(self_type_did); + let self_descr = tcx.def_kind(self_type_did).descr(self_type_did); + let mut err = err.build(&format!( + "cross-crate traits with a default impl, like `{}`, \ should not be specialized", - tcx.def_path_str(trait_def_id), - )); - match arg { - ty::util::NotUniqueParam::DuplicateParam(arg) => { - err.note(&format!("`{}` is mentioned multiple times", arg)); - } - ty::util::NotUniqueParam::NotParam(arg) => { - err.note(&format!("`{}` is not a generic parameter", arg)); - } + tcx.def_path_str(trait_ref.def_id), + )); + match arg { + ty::util::NotUniqueParam::DuplicateParam(arg) => { + err.note(&format!("`{}` is mentioned multiple times", arg)); } - err.span_note( - item_span, - &format!( - "try using the same sequence of generic parameters as the {} definition", - self_descr, - ), - ); - err.emit(); - }, - ); - } + ty::util::NotUniqueParam::NotParam(arg) => { + err.note(&format!("`{}` is not a generic parameter", arg)); + } + } + err.span_note( + item_span, + &format!( + "try using the same sequence of generic parameters as the {} definition", + self_descr, + ), + ); + err.emit(); + }, + ); } fn fast_reject_auto_impl<'tcx>(tcx: TyCtxt<'tcx>, trait_def_id: DefId, self_ty: Ty<'tcx>) -> bool { diff --git a/compiler/rustc_typeck/src/coherence/unsafety.rs b/compiler/rustc_typeck/src/coherence/unsafety.rs index 3cfc96ccbfd28..e45fb5fe41c02 100644 --- a/compiler/rustc_typeck/src/coherence/unsafety.rs +++ b/compiler/rustc_typeck/src/coherence/unsafety.rs @@ -6,37 +6,18 @@ use rustc_hir as hir; use rustc_hir::def::DefKind; use rustc_hir::Unsafety; use rustc_middle::ty::TyCtxt; +use rustc_span::def_id::LocalDefId; -pub fn check(tcx: TyCtxt<'_>) { - for id in tcx.hir().items() { - if matches!(tcx.def_kind(id.def_id), DefKind::Impl) { - let item = tcx.hir().item(id); - if let hir::ItemKind::Impl(ref impl_) = item.kind { - check_unsafety_coherence( - tcx, - item, - Some(&impl_.generics), - impl_.unsafety, - impl_.polarity, - ); - } - } - } -} +pub(super) fn check_item(tcx: TyCtxt<'_>, def_id: LocalDefId) { + debug_assert!(matches!(tcx.def_kind(def_id), DefKind::Impl)); + let item = tcx.hir().expect_item(def_id); + let hir::ItemKind::Impl(ref impl_) = item.kind else { bug!() }; -fn check_unsafety_coherence<'tcx>( - tcx: TyCtxt<'tcx>, - item: &hir::Item<'_>, - impl_generics: Option<&hir::Generics<'_>>, - unsafety: hir::Unsafety, - polarity: hir::ImplPolarity, -) { if let Some(trait_ref) = tcx.impl_trait_ref(item.def_id) { let trait_def = tcx.trait_def(trait_ref.def_id); - let unsafe_attr = impl_generics.and_then(|generics| { - generics.params.iter().find(|p| p.pure_wrt_drop).map(|_| "may_dangle") - }); - match (trait_def.unsafety, unsafe_attr, unsafety, polarity) { + let unsafe_attr = + impl_.generics.params.iter().find(|p| p.pure_wrt_drop).map(|_| "may_dangle"); + match (trait_def.unsafety, unsafe_attr, impl_.unsafety, impl_.polarity) { (Unsafety::Normal, None, Unsafety::Unsafe, hir::ImplPolarity::Positive) => { struct_span_err!( tcx.sess, diff --git a/compiler/rustc_typeck/src/lib.rs b/compiler/rustc_typeck/src/lib.rs index d613edf0ab0c4..a7a008bc2eb04 100644 --- a/compiler/rustc_typeck/src/lib.rs +++ b/compiler/rustc_typeck/src/lib.rs @@ -513,7 +513,15 @@ pub fn check_crate(tcx: TyCtxt<'_>) -> Result<(), ErrorGuaranteed> { })?; tcx.sess.track_errors(|| { - tcx.sess.time("coherence_checking", || coherence::check_coherence(tcx)); + tcx.sess.time("coherence_checking", || { + for &trait_def_id in tcx.all_local_trait_impls(()).keys() { + tcx.ensure().coherent_trait(trait_def_id); + } + + // these queries are executed for side-effects (error reporting): + tcx.ensure().crate_inherent_impls(()); + tcx.ensure().crate_inherent_impls_overlap_check(()); + }); })?; if tcx.features().rustc_attrs { diff --git a/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.stderr b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.stderr index 912891480790e..c364c707ff9ea 100644 --- a/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.stderr +++ b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.stderr @@ -1,3 +1,15 @@ +error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker1` + --> $DIR/coherence-impl-trait-for-marker-trait-negative.rs:15:1 + | +LL | impl !Marker1 for dyn Object + Marker2 { } + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker1` + +error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker2` + --> $DIR/coherence-impl-trait-for-marker-trait-negative.rs:17:1 + | +LL | impl !Marker2 for dyn Object + Marker2 { } + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker2` + error[E0117]: only traits defined in the current crate can be implemented for arbitrary types --> $DIR/coherence-impl-trait-for-marker-trait-negative.rs:23:1 | @@ -21,18 +33,6 @@ error[E0321]: cross-crate traits with a default impl, like `Send`, can only be i LL | impl !Send for dyn Object + Marker2 {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ can't implement cross-crate trait with a default impl for non-struct/enum type -error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker1` - --> $DIR/coherence-impl-trait-for-marker-trait-negative.rs:15:1 - | -LL | impl !Marker1 for dyn Object + Marker2 { } - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker1` - -error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker2` - --> $DIR/coherence-impl-trait-for-marker-trait-negative.rs:17:1 - | -LL | impl !Marker2 for dyn Object + Marker2 { } - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker2` - error: aborting due to 5 previous errors Some errors have detailed explanations: E0117, E0321, E0371. diff --git a/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.stderr b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.stderr index 056198374a4cc..b80429794f92c 100644 --- a/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.stderr +++ b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.stderr @@ -1,3 +1,15 @@ +error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker1` + --> $DIR/coherence-impl-trait-for-marker-trait-positive.rs:15:1 + | +LL | impl Marker1 for dyn Object + Marker2 { } + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker1` + +error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker2` + --> $DIR/coherence-impl-trait-for-marker-trait-positive.rs:17:1 + | +LL | impl Marker2 for dyn Object + Marker2 { } + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker2` + error[E0117]: only traits defined in the current crate can be implemented for arbitrary types --> $DIR/coherence-impl-trait-for-marker-trait-positive.rs:23:1 | @@ -21,18 +33,6 @@ error[E0321]: cross-crate traits with a default impl, like `Send`, can only be i LL | unsafe impl Send for dyn Object + Marker2 {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ can't implement cross-crate trait with a default impl for non-struct/enum type -error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker1` - --> $DIR/coherence-impl-trait-for-marker-trait-positive.rs:15:1 - | -LL | impl Marker1 for dyn Object + Marker2 { } - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker1` - -error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker2` - --> $DIR/coherence-impl-trait-for-marker-trait-positive.rs:17:1 - | -LL | impl Marker2 for dyn Object + Marker2 { } - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker2` - error: aborting due to 5 previous errors Some errors have detailed explanations: E0117, E0321, E0371. diff --git a/src/test/ui/coherence/coherence-impls-copy.stderr b/src/test/ui/coherence/coherence-impls-copy.stderr index b3ca354c633aa..86356af256433 100644 --- a/src/test/ui/coherence/coherence-impls-copy.stderr +++ b/src/test/ui/coherence/coherence-impls-copy.stderr @@ -9,49 +9,49 @@ LL | impl Copy for i32 {} | = note: define and implement a trait or new type instead +error[E0119]: conflicting implementations of trait `std::marker::Copy` for type `&NotSync` + --> $DIR/coherence-impls-copy.rs:28:1 + | +LL | impl Copy for &'static NotSync {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = note: conflicting implementation in crate `core`: + - impl Copy for &T + where T: ?Sized; + error[E0117]: only traits defined in the current crate can be implemented for arbitrary types - --> $DIR/coherence-impls-copy.rs:25:1 + --> $DIR/coherence-impls-copy.rs:33:1 | -LL | impl Copy for (MyType, MyType) {} - | ^^^^^^^^^^^^^^---------------- +LL | impl Copy for &'static [NotSync] {} + | ^^^^^^^^^^^^^^------------------ | | | - | | this is not defined in the current crate because tuples are always foreign + | | this is not defined in the current crate because slices are always foreign | impl doesn't use only types from inside the current crate | = note: define and implement a trait or new type instead error[E0117]: only traits defined in the current crate can be implemented for arbitrary types - --> $DIR/coherence-impls-copy.rs:30:1 + --> $DIR/coherence-impls-copy.rs:25:1 | -LL | impl Copy for [MyType] {} - | ^^^^^^^^^^^^^^-------- +LL | impl Copy for (MyType, MyType) {} + | ^^^^^^^^^^^^^^---------------- | | | - | | this is not defined in the current crate because slices are always foreign + | | this is not defined in the current crate because tuples are always foreign | impl doesn't use only types from inside the current crate | = note: define and implement a trait or new type instead error[E0117]: only traits defined in the current crate can be implemented for arbitrary types - --> $DIR/coherence-impls-copy.rs:33:1 + --> $DIR/coherence-impls-copy.rs:30:1 | -LL | impl Copy for &'static [NotSync] {} - | ^^^^^^^^^^^^^^------------------ +LL | impl Copy for [MyType] {} + | ^^^^^^^^^^^^^^-------- | | | | | this is not defined in the current crate because slices are always foreign | impl doesn't use only types from inside the current crate | = note: define and implement a trait or new type instead -error[E0119]: conflicting implementations of trait `std::marker::Copy` for type `&NotSync` - --> $DIR/coherence-impls-copy.rs:28:1 - | -LL | impl Copy for &'static NotSync {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - | - = note: conflicting implementation in crate `core`: - - impl Copy for &T - where T: ?Sized; - error[E0206]: the trait `Copy` may not be implemented for this type --> $DIR/coherence-impls-copy.rs:21:15 | diff --git a/src/test/ui/coherence/coherence-impls-send.stderr b/src/test/ui/coherence/coherence-impls-send.stderr index dd1fd1b0dce24..e1071846e146e 100644 --- a/src/test/ui/coherence/coherence-impls-send.stderr +++ b/src/test/ui/coherence/coherence-impls-send.stderr @@ -1,3 +1,14 @@ +error[E0117]: only traits defined in the current crate can be implemented for arbitrary types + --> $DIR/coherence-impls-send.rs:25:1 + | +LL | unsafe impl Send for &'static [NotSync] {} + | ^^^^^^^^^^^^^^^^^^^^^------------------ + | | | + | | this is not defined in the current crate because slices are always foreign + | impl doesn't use only types from inside the current crate + | + = note: define and implement a trait or new type instead + error[E0117]: only traits defined in the current crate can be implemented for arbitrary types --> $DIR/coherence-impls-send.rs:16:1 | @@ -26,17 +37,6 @@ LL | unsafe impl Send for [MyType] {} | = note: define and implement a trait or new type instead -error[E0117]: only traits defined in the current crate can be implemented for arbitrary types - --> $DIR/coherence-impls-send.rs:25:1 - | -LL | unsafe impl Send for &'static [NotSync] {} - | ^^^^^^^^^^^^^^^^^^^^^------------------ - | | | - | | this is not defined in the current crate because slices are always foreign - | impl doesn't use only types from inside the current crate - | - = note: define and implement a trait or new type instead - error: aborting due to 4 previous errors Some errors have detailed explanations: E0117, E0321. diff --git a/src/test/ui/coherence/coherence-impls-sized.stderr b/src/test/ui/coherence/coherence-impls-sized.stderr index e1e4acd4cd82d..17a7544521de5 100644 --- a/src/test/ui/coherence/coherence-impls-sized.stderr +++ b/src/test/ui/coherence/coherence-impls-sized.stderr @@ -1,36 +1,3 @@ -error[E0117]: only traits defined in the current crate can be implemented for arbitrary types - --> $DIR/coherence-impls-sized.rs:20:1 - | -LL | impl Sized for (MyType, MyType) {} - | ^^^^^^^^^^^^^^^---------------- - | | | - | | this is not defined in the current crate because tuples are always foreign - | impl doesn't use only types from inside the current crate - | - = note: define and implement a trait or new type instead - -error[E0117]: only traits defined in the current crate can be implemented for arbitrary types - --> $DIR/coherence-impls-sized.rs:27:1 - | -LL | impl Sized for [MyType] {} - | ^^^^^^^^^^^^^^^-------- - | | | - | | this is not defined in the current crate because slices are always foreign - | impl doesn't use only types from inside the current crate - | - = note: define and implement a trait or new type instead - -error[E0117]: only traits defined in the current crate can be implemented for arbitrary types - --> $DIR/coherence-impls-sized.rs:31:1 - | -LL | impl Sized for &'static [NotSync] {} - | ^^^^^^^^^^^^^^^------------------ - | | | - | | this is not defined in the current crate because slices are always foreign - | impl doesn't use only types from inside the current crate - | - = note: define and implement a trait or new type instead - error[E0322]: explicit impls for the `Sized` trait are not permitted --> $DIR/coherence-impls-sized.rs:14:1 | @@ -49,6 +16,17 @@ error[E0322]: explicit impls for the `Sized` trait are not permitted LL | impl Sized for (MyType, MyType) {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ impl of `Sized` not allowed +error[E0117]: only traits defined in the current crate can be implemented for arbitrary types + --> $DIR/coherence-impls-sized.rs:20:1 + | +LL | impl Sized for (MyType, MyType) {} + | ^^^^^^^^^^^^^^^---------------- + | | | + | | this is not defined in the current crate because tuples are always foreign + | impl doesn't use only types from inside the current crate + | + = note: define and implement a trait or new type instead + error[E0322]: explicit impls for the `Sized` trait are not permitted --> $DIR/coherence-impls-sized.rs:24:1 | @@ -61,12 +39,34 @@ error[E0322]: explicit impls for the `Sized` trait are not permitted LL | impl Sized for [MyType] {} | ^^^^^^^^^^^^^^^^^^^^^^^ impl of `Sized` not allowed +error[E0117]: only traits defined in the current crate can be implemented for arbitrary types + --> $DIR/coherence-impls-sized.rs:27:1 + | +LL | impl Sized for [MyType] {} + | ^^^^^^^^^^^^^^^-------- + | | | + | | this is not defined in the current crate because slices are always foreign + | impl doesn't use only types from inside the current crate + | + = note: define and implement a trait or new type instead + error[E0322]: explicit impls for the `Sized` trait are not permitted --> $DIR/coherence-impls-sized.rs:31:1 | LL | impl Sized for &'static [NotSync] {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ impl of `Sized` not allowed +error[E0117]: only traits defined in the current crate can be implemented for arbitrary types + --> $DIR/coherence-impls-sized.rs:31:1 + | +LL | impl Sized for &'static [NotSync] {} + | ^^^^^^^^^^^^^^^------------------ + | | | + | | this is not defined in the current crate because slices are always foreign + | impl doesn't use only types from inside the current crate + | + = note: define and implement a trait or new type instead + error: aborting due to 9 previous errors Some errors have detailed explanations: E0117, E0322. diff --git a/src/test/ui/coherence/coherence-with-closure.stderr b/src/test/ui/coherence/coherence-with-closure.stderr index 20b986cee6913..d2ca63fa14691 100644 --- a/src/test/ui/coherence/coherence-with-closure.stderr +++ b/src/test/ui/coherence/coherence-with-closure.stderr @@ -1,3 +1,12 @@ +error[E0119]: conflicting implementations of trait `Trait` for type `Wrapper` + --> $DIR/coherence-with-closure.rs:12:1 + | +LL | impl Trait for Wrapper {} + | ------------------------------------- first implementation here +LL | +LL | impl Trait for Wrapper {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `Wrapper` + error: cannot implement trait on type alias impl trait --> $DIR/coherence-with-closure.rs:10:24 | @@ -10,15 +19,6 @@ note: type alias impl trait defined here LL | type OpaqueClosure = impl Sized; | ^^^^^^^^^^ -error[E0119]: conflicting implementations of trait `Trait` for type `Wrapper` - --> $DIR/coherence-with-closure.rs:12:1 - | -LL | impl Trait for Wrapper {} - | ------------------------------------- first implementation here -LL | -LL | impl Trait for Wrapper {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `Wrapper` - error: aborting due to 2 previous errors For more information about this error, try `rustc --explain E0119`. diff --git a/src/test/ui/coherence/coherence-with-generator.stderr b/src/test/ui/coherence/coherence-with-generator.stderr index 249ad3cb9ec7f..804bc1c3a6dd4 100644 --- a/src/test/ui/coherence/coherence-with-generator.stderr +++ b/src/test/ui/coherence/coherence-with-generator.stderr @@ -1,3 +1,12 @@ +error[E0119]: conflicting implementations of trait `Trait` for type `Wrapper` + --> $DIR/coherence-with-generator.rs:16:1 + | +LL | impl Trait for Wrapper {} + | --------------------------------------- first implementation here +LL | +LL | impl Trait for Wrapper {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `Wrapper` + error: cannot implement trait on type alias impl trait --> $DIR/coherence-with-generator.rs:14:24 | @@ -10,15 +19,6 @@ note: type alias impl trait defined here LL | type OpaqueGenerator = impl Sized; | ^^^^^^^^^^ -error[E0119]: conflicting implementations of trait `Trait` for type `Wrapper` - --> $DIR/coherence-with-generator.rs:16:1 - | -LL | impl Trait for Wrapper {} - | --------------------------------------- first implementation here -LL | -LL | impl Trait for Wrapper {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `Wrapper` - error: aborting due to 2 previous errors For more information about this error, try `rustc --explain E0119`. diff --git a/src/test/ui/impl-trait/auto-trait.stderr b/src/test/ui/impl-trait/auto-trait.stderr index 3b360f492b70e..5e10272b0db3c 100644 --- a/src/test/ui/impl-trait/auto-trait.stderr +++ b/src/test/ui/impl-trait/auto-trait.stderr @@ -1,3 +1,12 @@ +error[E0119]: conflicting implementations of trait `AnotherTrait` for type `D` + --> $DIR/auto-trait.rs:21:1 + | +LL | impl AnotherTrait for T {} + | -------------------------------- first implementation here +... +LL | impl AnotherTrait for D { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `D` + error: cannot implement trait on type alias impl trait --> $DIR/auto-trait.rs:21:25 | @@ -10,15 +19,6 @@ note: type alias impl trait defined here LL | type OpaqueType = impl OpaqueTrait; | ^^^^^^^^^^^^^^^^ -error[E0119]: conflicting implementations of trait `AnotherTrait` for type `D` - --> $DIR/auto-trait.rs:21:1 - | -LL | impl AnotherTrait for T {} - | -------------------------------- first implementation here -... -LL | impl AnotherTrait for D { - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `D` - error: aborting due to 2 previous errors For more information about this error, try `rustc --explain E0119`. diff --git a/src/test/ui/impl-trait/negative-reasoning.stderr b/src/test/ui/impl-trait/negative-reasoning.stderr index 98f9fbd8fefb7..479b451855d55 100644 --- a/src/test/ui/impl-trait/negative-reasoning.stderr +++ b/src/test/ui/impl-trait/negative-reasoning.stderr @@ -1,3 +1,14 @@ +error[E0119]: conflicting implementations of trait `AnotherTrait` for type `D` + --> $DIR/negative-reasoning.rs:19:1 + | +LL | impl AnotherTrait for T {} + | ------------------------------------------- first implementation here +... +LL | impl AnotherTrait for D { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `D` + | + = note: upstream crates may add a new impl of trait `std::fmt::Debug` for type `OpaqueType` in future versions + error: cannot implement trait on type alias impl trait --> $DIR/negative-reasoning.rs:19:25 | @@ -10,17 +21,6 @@ note: type alias impl trait defined here LL | type OpaqueType = impl OpaqueTrait; | ^^^^^^^^^^^^^^^^ -error[E0119]: conflicting implementations of trait `AnotherTrait` for type `D` - --> $DIR/negative-reasoning.rs:19:1 - | -LL | impl AnotherTrait for T {} - | ------------------------------------------- first implementation here -... -LL | impl AnotherTrait for D { - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `D` - | - = note: upstream crates may add a new impl of trait `std::fmt::Debug` for type `OpaqueType` in future versions - error: aborting due to 2 previous errors For more information about this error, try `rustc --explain E0119`. diff --git a/src/test/ui/traits/alias/issue-83613.stderr b/src/test/ui/traits/alias/issue-83613.stderr index bbc240b6aec49..b9d93160192e9 100644 --- a/src/test/ui/traits/alias/issue-83613.stderr +++ b/src/test/ui/traits/alias/issue-83613.stderr @@ -1,3 +1,11 @@ +error[E0119]: conflicting implementations of trait `AnotherTrait` for type `OpaqueType` + --> $DIR/issue-83613.rs:10:1 + | +LL | impl AnotherTrait for T {} + | -------------------------------- first implementation here +LL | impl AnotherTrait for OpaqueType {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `OpaqueType` + error: cannot implement trait on type alias impl trait --> $DIR/issue-83613.rs:10:23 | @@ -10,14 +18,6 @@ note: type alias impl trait defined here LL | type OpaqueType = impl OpaqueTrait; | ^^^^^^^^^^^^^^^^ -error[E0119]: conflicting implementations of trait `AnotherTrait` for type `OpaqueType` - --> $DIR/issue-83613.rs:10:1 - | -LL | impl AnotherTrait for T {} - | -------------------------------- first implementation here -LL | impl AnotherTrait for OpaqueType {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `OpaqueType` - error: aborting due to 2 previous errors For more information about this error, try `rustc --explain E0119`. diff --git a/src/test/ui/traits/issue-78372.rs b/src/test/ui/traits/issue-78372.rs index 77a8c92c81c7e..92f9f4b467a97 100644 --- a/src/test/ui/traits/issue-78372.rs +++ b/src/test/ui/traits/issue-78372.rs @@ -4,7 +4,6 @@ impl DispatchFromDyn> for T {} //~ ERROR cannot find type `U` //~^ ERROR cannot find type `MISC` in this scope //~| ERROR use of unstable library feature 'dispatch_from_dyn' //~| ERROR the trait `DispatchFromDyn` may only be implemented for a coercion between structures -//~| ERROR type parameter `T` must be covered by another type when it appears before the first trait Foo: X {} trait X { fn foo(self: Smaht); diff --git a/src/test/ui/traits/issue-78372.stderr b/src/test/ui/traits/issue-78372.stderr index 49a9f47936876..7574c9107d9ac 100644 --- a/src/test/ui/traits/issue-78372.stderr +++ b/src/test/ui/traits/issue-78372.stderr @@ -50,22 +50,13 @@ LL | impl DispatchFromDyn> for T {} | = help: add `#![feature(dispatch_from_dyn)]` to the crate attributes to enable -error[E0210]: type parameter `T` must be covered by another type when it appears before the first local type (`Smaht<[type error], [type error]>`) - --> $DIR/issue-78372.rs:3:6 - | -LL | impl DispatchFromDyn> for T {} - | ^ type parameter `T` must be covered by another type when it appears before the first local type (`Smaht<[type error], [type error]>`) - | - = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local, and no uncovered type parameters appear before that first local type - = note: in this case, 'before' refers to the following order: `impl<..> ForeignTrait for T0`, where `T0` is the first and `Tn` is the last - error[E0378]: the trait `DispatchFromDyn` may only be implemented for a coercion between structures --> $DIR/issue-78372.rs:3:1 | LL | impl DispatchFromDyn> for T {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -error: aborting due to 7 previous errors +error: aborting due to 6 previous errors -Some errors have detailed explanations: E0210, E0378, E0412, E0658. -For more information about an error, try `rustc --explain E0210`. +Some errors have detailed explanations: E0378, E0412, E0658. +For more information about an error, try `rustc --explain E0378`.