about summary refs log tree commit diff
diff options
context:
space:
mode:
authorEsteban Küber <esteban@kuber.com.ar>2020-04-09 13:07:22 -0700
committerEsteban Küber <esteban@kuber.com.ar>2020-04-18 16:37:08 -0700
commit6bc55c701f50ccdc8605b37cdf62d02ec596b108 (patch)
treefdc555451eb61ca2504f1ff81164a84ceb55844f
parentad1c23c993dc65810b535bed8c305643c892a2a4 (diff)
downloadrust-6bc55c701f50ccdc8605b37cdf62d02ec596b108.tar.gz
rust-6bc55c701f50ccdc8605b37cdf62d02ec596b108.zip
Remove `AssocTypeBound` and propagate bound `Span`s
-rw-r--r--src/librustc_middle/traits/mod.rs9
-rw-r--r--src/librustc_middle/traits/structural_impls.rs1
-rw-r--r--src/librustc_trait_selection/traits/error_reporting/suggestions.rs9
-rw-r--r--src/librustc_trait_selection/traits/wf.rs229
-rw-r--r--src/librustc_typeck/astconv.rs2
-rw-r--r--src/test/ui/associated-type/associated-type-projection-from-multiple-supertraits.stderr4
-rw-r--r--src/test/ui/associated-types/point-at-type-on-obligation-failure-2.stderr36
-rw-r--r--src/test/ui/associated-types/point-at-type-on-obligation-failure.stderr9
-rw-r--r--src/test/ui/generic-associated-types/construct_with_other_type.stderr7
-rw-r--r--src/test/ui/generic-associated-types/iterable.stderr22
-rw-r--r--src/test/ui/issues/issue-43784-associated-type.stderr10
-rw-r--r--src/test/ui/issues/issue-65673.stderr11
-rw-r--r--src/test/ui/suggestions/missing-assoc-type-bound-restriction.stderr14
-rw-r--r--src/test/ui/traits/cycle-cache-err-60010.stderr11
-rw-r--r--src/test/ui/traits/traits-assoc-type-in-supertrait-bad.rs4
-rw-r--r--src/test/ui/traits/traits-assoc-type-in-supertrait-bad.stderr11
-rw-r--r--src/test/ui/unboxed-closures/unboxed-closure-sugar-wrong-trait.stderr4
17 files changed, 106 insertions, 287 deletions
diff --git a/src/librustc_middle/traits/mod.rs b/src/librustc_middle/traits/mod.rs
index c129b574fd3..47c8aa023f0 100644
--- a/src/librustc_middle/traits/mod.rs
+++ b/src/librustc_middle/traits/mod.rs
@@ -257,8 +257,6 @@ pub enum ObligationCauseCode<'tcx> {
 
     /// #[feature(trivial_bounds)] is not enabled
     TrivialBound,
-
-    AssocTypeBound(Box<AssocTypeBoundData>),
 }
 
 impl ObligationCauseCode<'_> {
@@ -272,13 +270,6 @@ impl ObligationCauseCode<'_> {
     }
 }
 
-#[derive(Clone, Debug, PartialEq, Eq, Hash)]
-pub struct AssocTypeBoundData {
-    pub impl_span: Option<Span>,
-    pub original: Span,
-    pub bounds: Vec<Span>,
-}
-
 // `ObligationCauseCode` is used a lot. Make sure it doesn't unintentionally get bigger.
 #[cfg(target_arch = "x86_64")]
 static_assert_size!(ObligationCauseCode<'_>, 32);
diff --git a/src/librustc_middle/traits/structural_impls.rs b/src/librustc_middle/traits/structural_impls.rs
index b1fb02a67b3..b7d0f6666bd 100644
--- a/src/librustc_middle/traits/structural_impls.rs
+++ b/src/librustc_middle/traits/structural_impls.rs
@@ -501,7 +501,6 @@ impl<'a, 'tcx> Lift<'tcx> for traits::ObligationCauseCode<'a> {
             super::MethodReceiver => Some(super::MethodReceiver),
             super::BlockTailExpression(id) => Some(super::BlockTailExpression(id)),
             super::TrivialBound => Some(super::TrivialBound),
-            super::AssocTypeBound(ref data) => Some(super::AssocTypeBound(data.clone())),
         }
     }
 }
diff --git a/src/librustc_trait_selection/traits/error_reporting/suggestions.rs b/src/librustc_trait_selection/traits/error_reporting/suggestions.rs
index 254db6cb869..52bf2e6ad49 100644
--- a/src/librustc_trait_selection/traits/error_reporting/suggestions.rs
+++ b/src/librustc_trait_selection/traits/error_reporting/suggestions.rs
@@ -1684,15 +1684,6 @@ impl<'a, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'a, 'tcx> {
                     err.help("add `#![feature(trivial_bounds)]` to the crate attributes to enable");
                 }
             }
-            ObligationCauseCode::AssocTypeBound(ref data) => {
-                err.span_label(data.original, "associated type defined here");
-                if let Some(sp) = data.impl_span {
-                    err.span_label(sp, "in this `impl` item");
-                }
-                for sp in &data.bounds {
-                    err.span_label(*sp, "restricted in this bound");
-                }
-            }
         }
     }
 
diff --git a/src/librustc_trait_selection/traits/wf.rs b/src/librustc_trait_selection/traits/wf.rs
index d341909ef7f..0cda92b7dc8 100644
--- a/src/librustc_trait_selection/traits/wf.rs
+++ b/src/librustc_trait_selection/traits/wf.rs
@@ -1,12 +1,11 @@
 use crate::infer::InferCtxt;
 use crate::opaque_types::required_region_bounds;
-use crate::traits::{self, AssocTypeBoundData};
+use crate::traits;
 use rustc_hir as hir;
 use rustc_hir::def_id::DefId;
 use rustc_hir::lang_items;
 use rustc_middle::ty::subst::{GenericArgKind, SubstsRef};
 use rustc_middle::ty::{self, ToPredicate, Ty, TyCtxt, TypeFoldable, WithConstness};
-use rustc_span::symbol::{kw, Ident};
 use rustc_span::Span;
 use std::rc::Rc;
 
@@ -143,137 +142,57 @@ fn extend_cause_with_original_assoc_item_obligation<'tcx>(
     pred: &ty::Predicate<'_>,
     mut trait_assoc_items: impl Iterator<Item = ty::AssocItem>,
 ) {
-    let trait_item =
-        tcx.hir().as_local_hir_id(trait_ref.def_id).and_then(|trait_id| tcx.hir().find(trait_id));
-    let (trait_name, trait_generics) = match trait_item {
-        Some(hir::Node::Item(hir::Item {
-            ident,
-            kind: hir::ItemKind::Trait(.., generics, _, _),
-            ..
-        }))
-        | Some(hir::Node::Item(hir::Item {
-            ident,
-            kind: hir::ItemKind::TraitAlias(generics, _),
-            ..
-        })) => (Some(ident), Some(generics)),
-        _ => (None, None),
+    debug!(
+        "extended_cause_with_original_assoc_item_obligation {:?} {:?} {:?} {:?}",
+        trait_ref, item, cause, pred
+    );
+    let items = match item {
+        Some(hir::Item { kind: hir::ItemKind::Impl { items, .. }, .. }) => items,
+        _ => return,
     };
-
-    let item_span = item.map(|i| tcx.sess.source_map().guess_head_span(i.span));
+    let fix_span =
+        |impl_item_ref: &hir::ImplItemRef<'_>| match tcx.hir().impl_item(impl_item_ref.id).kind {
+            hir::ImplItemKind::Const(ty, _) | hir::ImplItemKind::TyAlias(ty) => ty.span,
+            _ => impl_item_ref.span,
+        };
     match pred {
         ty::Predicate::Projection(proj) => {
             // The obligation comes not from the current `impl` nor the `trait` being
             // implemented, but rather from a "second order" obligation, like in
-            // `src/test/ui/associated-types/point-at-type-on-obligation-failure.rs`:
-            //
-            //   error[E0271]: type mismatch resolving `<Foo2 as Bar2>::Ok == ()`
-            //     --> $DIR/point-at-type-on-obligation-failure.rs:13:5
-            //      |
-            //   LL |     type Ok;
-            //      |          -- associated type defined here
-            //   ...
-            //   LL | impl Bar for Foo {
-            //      | ---------------- in this `impl` item
-            //   LL |     type Ok = ();
-            //      |     ^^^^^^^^^^^^^ expected `u32`, found `()`
-            //      |
-            //      = note: expected type `u32`
-            //                 found type `()`
-            //
-            // FIXME: we would want to point a span to all places that contributed to this
-            // obligation. In the case above, it should be closer to:
-            //
-            //   error[E0271]: type mismatch resolving `<Foo2 as Bar2>::Ok == ()`
-            //     --> $DIR/point-at-type-on-obligation-failure.rs:13:5
-            //      |
-            //   LL |     type Ok;
-            //      |          -- associated type defined here
-            //   LL |     type Sibling: Bar2<Ok=Self::Ok>;
-            //      |     -------------------------------- obligation set here
-            //   ...
-            //   LL | impl Bar for Foo {
-            //      | ---------------- in this `impl` item
-            //   LL |     type Ok = ();
-            //      |     ^^^^^^^^^^^^^ expected `u32`, found `()`
-            //   ...
-            //   LL | impl Bar2 for Foo2 {
-            //      | ---------------- in this `impl` item
-            //   LL |     type Ok = u32;
-            //      |     -------------- obligation set here
-            //      |
-            //      = note: expected type `u32`
-            //                 found type `()`
-            if let Some(hir::ItemKind::Impl { items, .. }) = item.map(|i| &i.kind) {
-                let trait_assoc_item = tcx.associated_item(proj.projection_def_id());
-                if let Some(impl_item) =
-                    items.iter().find(|item| item.ident == trait_assoc_item.ident)
-                {
-                    cause.span = impl_item.span;
-                    cause.code = traits::AssocTypeBound(Box::new(AssocTypeBoundData {
-                        impl_span: item_span,
-                        original: trait_assoc_item.ident.span,
-                        bounds: vec![],
-                    }));
+            // `src/test/ui/associated-types/point-at-type-on-obligation-failure.rs`.
+            let trait_assoc_item = tcx.associated_item(proj.projection_def_id());
+            if let Some(impl_item_span) =
+                items.iter().find(|item| item.ident == trait_assoc_item.ident).map(fix_span)
+            {
+                cause.span = impl_item_span;
+            } else {
+                let kind = &proj.ty().skip_binder().kind;
+                if let ty::Projection(projection_ty) = kind {
+                    // This happens when an associated type has a projection coming from another
+                    // associated type. See `traits-assoc-type-in-supertrait-bad.rs`.
+                    let trait_assoc_item = tcx.associated_item(projection_ty.item_def_id);
+                    if let Some(impl_item_span) =
+                        items.iter().find(|item| item.ident == trait_assoc_item.ident).map(fix_span)
+                    {
+                        cause.span = impl_item_span;
+                    }
                 }
             }
         }
-        ty::Predicate::Trait(proj, _) => {
-            // An associated item obligation born out of the `trait` failed to be met.
-            // Point at the `impl` that failed the obligation, the associated item that
-            // needed to meet the obligation, and the definition of that associated item,
-            // which should hold the obligation in most cases. An example can be seen in
-            // `src/test/ui/associated-types/point-at-type-on-obligation-failure-2.rs`:
-            //
-            //   error[E0277]: the trait bound `bool: Bar` is not satisfied
-            //     --> $DIR/point-at-type-on-obligation-failure-2.rs:8:5
-            //      |
-            //   LL |     type Assoc: Bar;
-            //      |          ----- associated type defined here
-            //   ...
-            //   LL | impl Foo for () {
-            //      | --------------- in this `impl` item
-            //   LL |     type Assoc = bool;
-            //      |     ^^^^^^^^^^^^^^^^^^ the trait `Bar` is not implemented for `bool`
-            //
-            // If the obligation comes from the where clause in the `trait`, we point at it:
-            //
-            //   error[E0277]: the trait bound `bool: Bar` is not satisfied
-            //     --> $DIR/point-at-type-on-obligation-failure-2.rs:8:5
-            //      |
-            //      | trait Foo where <Self as Foo>>::Assoc: Bar {
-            //      |                 -------------------------- restricted in this bound
-            //   LL |     type Assoc;
-            //      |          ----- associated type defined here
-            //   ...
-            //   LL | impl Foo for () {
-            //      | --------------- in this `impl` item
-            //   LL |     type Assoc = bool;
-            //      |     ^^^^^^^^^^^^^^^^^^ the trait `Bar` is not implemented for `bool`
-            if let (
-                ty::Projection(ty::ProjectionTy { item_def_id, .. }),
-                Some(hir::ItemKind::Impl { items, .. }),
-            ) = (&proj.skip_binder().self_ty().kind, item.map(|i| &i.kind))
+        ty::Predicate::Trait(pred, _) => {
+            // An associated item obligation born out of the `trait` failed to be met. An example
+            // can be seen in `ui/associated-types/point-at-type-on-obligation-failure-2.rs`.
+            debug!("extended_cause_with_original_assoc_item_obligation trait proj {:?}", pred);
+            if let ty::Projection(ty::ProjectionTy { item_def_id, .. }) =
+                &pred.skip_binder().self_ty().kind
             {
-                if let Some((impl_item, trait_assoc_item)) = trait_assoc_items
+                if let Some(impl_item_span) = trait_assoc_items
                     .find(|i| i.def_id == *item_def_id)
                     .and_then(|trait_assoc_item| {
-                        items
-                            .iter()
-                            .find(|i| i.ident == trait_assoc_item.ident)
-                            .map(|impl_item| (impl_item, trait_assoc_item))
+                        items.iter().find(|i| i.ident == trait_assoc_item.ident).map(fix_span)
                     })
                 {
-                    let bounds = trait_generics
-                        .map(|generics| {
-                            get_generic_bound_spans(&generics, trait_name, trait_assoc_item.ident)
-                        })
-                        .unwrap_or_else(Vec::new);
-                    cause.span = impl_item.span;
-                    cause.code = traits::AssocTypeBound(Box::new(AssocTypeBoundData {
-                        impl_span: item_span,
-                        original: trait_assoc_item.ident.span,
-                        bounds,
-                    }));
+                    cause.span = impl_item_span;
                 }
             }
         }
@@ -307,6 +226,7 @@ impl<'a, 'tcx> WfPredicates<'a, 'tcx> {
         let tcx = self.infcx.tcx;
         let obligations = self.nominal_obligations(trait_ref.def_id, trait_ref.substs);
 
+        debug!("compute_trait_ref obligations {:?}", obligations);
         let cause = self.cause(traits::MiscObligation);
         let param_env = self.param_env;
 
@@ -315,16 +235,16 @@ impl<'a, 'tcx> WfPredicates<'a, 'tcx> {
         if let Elaborate::All = elaborate {
             let implied_obligations = traits::util::elaborate_obligations(tcx, obligations.clone());
             let implied_obligations = implied_obligations.map(|obligation| {
+                debug!("compute_trait_ref implied_obligation {:?}", obligation);
+                debug!("compute_trait_ref implied_obligation cause {:?}", obligation.cause);
                 let mut cause = cause.clone();
-                let parent_trait_ref = obligation
-                    .predicate
-                    .to_opt_poly_trait_ref()
-                    .unwrap_or_else(|| ty::Binder::dummy(*trait_ref));
-                let derived_cause = traits::DerivedObligationCause {
-                    parent_trait_ref,
-                    parent_code: Rc::new(obligation.cause.code.clone()),
-                };
-                cause.code = traits::ObligationCauseCode::ImplDerivedObligation(derived_cause);
+                if let Some(parent_trait_ref) = obligation.predicate.to_opt_poly_trait_ref() {
+                    let derived_cause = traits::DerivedObligationCause {
+                        parent_trait_ref,
+                        parent_code: Rc::new(obligation.cause.code.clone()),
+                    };
+                    cause.code = traits::ObligationCauseCode::ImplDerivedObligation(derived_cause);
+                }
                 extend_cause_with_original_assoc_item_obligation(
                     tcx,
                     trait_ref,
@@ -333,6 +253,7 @@ impl<'a, 'tcx> WfPredicates<'a, 'tcx> {
                     &obligation.predicate,
                     tcx.associated_items(trait_ref.def_id).in_definition_order().copied(),
                 );
+                debug!("compute_trait_ref new cause {:?}", cause);
                 traits::Obligation::new(cause, param_env, obligation.predicate)
             });
             self.out.extend(implied_obligations);
@@ -719,53 +640,3 @@ pub fn object_region_bounds<'tcx>(
 
     required_region_bounds(tcx, open_ty, predicates)
 }
-
-/// Find the span of a generic bound affecting an associated type.
-fn get_generic_bound_spans(
-    generics: &hir::Generics<'_>,
-    trait_name: Option<&Ident>,
-    assoc_item_name: Ident,
-) -> Vec<Span> {
-    let mut bounds = vec![];
-    for clause in generics.where_clause.predicates.iter() {
-        if let hir::WherePredicate::BoundPredicate(pred) = clause {
-            match &pred.bounded_ty.kind {
-                hir::TyKind::Path(hir::QPath::Resolved(Some(ty), path)) => {
-                    let mut s = path.segments.iter();
-                    if let (a, Some(b), None) = (s.next(), s.next(), s.next()) {
-                        if a.map(|s| &s.ident) == trait_name
-                            && b.ident == assoc_item_name
-                            && is_self_path(&ty.kind)
-                        {
-                            // `<Self as Foo>::Bar`
-                            bounds.push(pred.span);
-                        }
-                    }
-                }
-                hir::TyKind::Path(hir::QPath::TypeRelative(ty, segment)) => {
-                    if segment.ident == assoc_item_name {
-                        if is_self_path(&ty.kind) {
-                            // `Self::Bar`
-                            bounds.push(pred.span);
-                        }
-                    }
-                }
-                _ => {}
-            }
-        }
-    }
-    bounds
-}
-
-fn is_self_path(kind: &hir::TyKind<'_>) -> bool {
-    if let hir::TyKind::Path(hir::QPath::Resolved(None, path)) = kind {
-        let mut s = path.segments.iter();
-        if let (Some(segment), None) = (s.next(), s.next()) {
-            if segment.ident.name == kw::SelfUpper {
-                // `type(Self)`
-                return true;
-            }
-        }
-    }
-    false
-}
diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs
index 4a8cd9e91e2..3aaa84da752 100644
--- a/src/librustc_typeck/astconv.rs
+++ b/src/librustc_typeck/astconv.rs
@@ -1045,7 +1045,7 @@ impl<'o, 'tcx> dyn AstConv<'tcx> + 'o {
                 bounds,
                 speculative,
                 &mut dup_bindings,
-                span,
+                binding.span,
             );
             // Okay to ignore `Err` because of `ErrorReported` (see above).
         }
diff --git a/src/test/ui/associated-type/associated-type-projection-from-multiple-supertraits.stderr b/src/test/ui/associated-type/associated-type-projection-from-multiple-supertraits.stderr
index 8d0cd57fad4..b6a88179c1f 100644
--- a/src/test/ui/associated-type/associated-type-projection-from-multiple-supertraits.stderr
+++ b/src/test/ui/associated-type/associated-type-projection-from-multiple-supertraits.stderr
@@ -28,7 +28,7 @@ LL | fn dent<C:BoxCar>(c: C, color: <C as Vehicle>::Color) {
    |                                ^^^^^^^^^^^^^^^^^^^^^
 
 error[E0222]: ambiguous associated type `Color` in bounds of `BoxCar`
-  --> $DIR/associated-type-projection-from-multiple-supertraits.rs:23:30
+  --> $DIR/associated-type-projection-from-multiple-supertraits.rs:23:37
    |
 LL |     type Color;
    |     ----------- ambiguous `Color` from `Vehicle`
@@ -37,7 +37,7 @@ LL |     type Color;
    |     ----------- ambiguous `Color` from `Box`
 ...
 LL | fn dent_object<COLOR>(c: dyn BoxCar<Color=COLOR>) {
-   |                              ^^^^^^^^^^^^^^^^^^^ ambiguous associated type `Color`
+   |                                     ^^^^^^^^^^^ ambiguous associated type `Color`
    |
    = help: consider introducing a new type parameter `T` and adding `where` constraints:
                where
diff --git a/src/test/ui/associated-types/point-at-type-on-obligation-failure-2.stderr b/src/test/ui/associated-types/point-at-type-on-obligation-failure-2.stderr
index 072e9dad062..cdc9559cd95 100644
--- a/src/test/ui/associated-types/point-at-type-on-obligation-failure-2.stderr
+++ b/src/test/ui/associated-types/point-at-type-on-obligation-failure-2.stderr
@@ -1,39 +1,37 @@
 error[E0277]: the trait bound `bool: Bar` is not satisfied
-  --> $DIR/point-at-type-on-obligation-failure-2.rs:8:5
+  --> $DIR/point-at-type-on-obligation-failure-2.rs:8:18
    |
+LL | trait Foo {
+   |       ---
 LL |     type Assoc: Bar;
-   |          ----- associated type defined here
+   |                 --- required by this bound in `Foo`
 ...
-LL | impl Foo for () {
-   | --------------- in this `impl` item
 LL |     type Assoc = bool;
-   |     ^^^^^^^^^^^^^^^^^^ the trait `Bar` is not implemented for `bool`
+   |                  ^^^^ the trait `Bar` is not implemented for `bool`
+   |
+   = note: required because of the requirements on the impl of `Bar` for `<() as Foo>::Assoc`
 
 error[E0277]: the trait bound `bool: Bar` is not satisfied
-  --> $DIR/point-at-type-on-obligation-failure-2.rs:16:5
+  --> $DIR/point-at-type-on-obligation-failure-2.rs:16:18
    |
 LL | trait Baz where Self::Assoc: Bar {
-   |                 ---------------- restricted in this bound
-LL |     type Assoc;
-   |          ----- associated type defined here
+   |                              --- required by this bound in `Baz`
 ...
-LL | impl Baz for () {
-   | --------------- in this `impl` item
 LL |     type Assoc = bool;
-   |     ^^^^^^^^^^^^^^^^^^ the trait `Bar` is not implemented for `bool`
+   |                  ^^^^ the trait `Bar` is not implemented for `bool`
+   |
+   = note: required because of the requirements on the impl of `Bar` for `<() as Baz>::Assoc`
 
 error[E0277]: the trait bound `bool: Bar` is not satisfied
-  --> $DIR/point-at-type-on-obligation-failure-2.rs:24:5
+  --> $DIR/point-at-type-on-obligation-failure-2.rs:24:18
    |
 LL | trait Bat where <Self as Bat>::Assoc: Bar {
-   |                 ------------------------- restricted in this bound
-LL |     type Assoc;
-   |          ----- associated type defined here
+   |                                       --- required by this bound in `Bat`
 ...
-LL | impl Bat for () {
-   | --------------- in this `impl` item
 LL |     type Assoc = bool;
-   |     ^^^^^^^^^^^^^^^^^^ the trait `Bar` is not implemented for `bool`
+   |                  ^^^^ the trait `Bar` is not implemented for `bool`
+   |
+   = note: required because of the requirements on the impl of `Bar` for `<() as Bat>::Assoc`
 
 error: aborting due to 3 previous errors
 
diff --git a/src/test/ui/associated-types/point-at-type-on-obligation-failure.stderr b/src/test/ui/associated-types/point-at-type-on-obligation-failure.stderr
index e86b460f818..818702b7afe 100644
--- a/src/test/ui/associated-types/point-at-type-on-obligation-failure.stderr
+++ b/src/test/ui/associated-types/point-at-type-on-obligation-failure.stderr
@@ -1,13 +1,8 @@
 error[E0271]: type mismatch resolving `<Foo2 as Bar2>::Ok == ()`
-  --> $DIR/point-at-type-on-obligation-failure.rs:13:5
+  --> $DIR/point-at-type-on-obligation-failure.rs:13:15
    |
-LL |     type Ok;
-   |          -- associated type defined here
-...
-LL | impl Bar for Foo {
-   | ---------------- in this `impl` item
 LL |     type Ok = ();
-   |     ^^^^^^^^^^^^^ expected `u32`, found `()`
+   |               ^^ expected `u32`, found `()`
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/generic-associated-types/construct_with_other_type.stderr b/src/test/ui/generic-associated-types/construct_with_other_type.stderr
index f27bc4d68d4..bad746f7ef1 100644
--- a/src/test/ui/generic-associated-types/construct_with_other_type.stderr
+++ b/src/test/ui/generic-associated-types/construct_with_other_type.stderr
@@ -1,19 +1,12 @@
 error[E0271]: type mismatch resolving `for<'a> <<T as Baz>::Baa<'a> as std::ops::Deref>::Target == <<T as Baz>::Quux<'a> as Foo>::Bar<'a, 'static>`
   --> $DIR/construct_with_other_type.rs:19:9
    |
-LL | trait Baz {
-   |       ---
-...
-LL |     type Baa<'a>: Deref<Target = <Self::Quux<'a> as Foo>::Bar<'a, 'static>>  where Self: 'a;
-   |                         -------------------------------------------------- required by this bound in `Baz`
-...
 LL | impl<T> Baz for T where T: Foo {
    |         ^^^ expected type parameter `T`, found associated type
    |
    = note: expected associated type `<T as Foo>::Bar<'_, 'static>`
               found associated type `<<T as Baz>::Quux<'_> as Foo>::Bar<'_, 'static>`
    = note: you might be missing a type parameter or trait bound
-   = note: required because of the requirements on the impl of `Baz` for `T`
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/generic-associated-types/iterable.stderr b/src/test/ui/generic-associated-types/iterable.stderr
index dc62ee53c06..6bc5a2319a9 100644
--- a/src/test/ui/generic-associated-types/iterable.stderr
+++ b/src/test/ui/generic-associated-types/iterable.stderr
@@ -1,15 +1,8 @@
 error[E0271]: type mismatch resolving `for<'a> <<std::vec::Vec<T> as Iterable>::Iter<'a> as std::iter::Iterator>::Item == <std::vec::Vec<T> as Iterable>::Item<'a>`
-  --> $DIR/iterable.rs:15:5
+  --> $DIR/iterable.rs:15:33
    |
-LL | impl<T> Iterable for Vec<T> {
-   | --------------------------- in this `impl` item
 LL |     type Item<'a> where T: 'a = <std::slice::Iter<'a, T> as Iterator>::Item;
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected reference, found associated type
-   | 
-  ::: $SRC_DIR/libcore/iter/traits/iterator.rs:LL:COL
-   |
-LL |     type Item;
-   |          ---- associated type defined here
+   |                                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected reference, found associated type
    |
    = note:    expected reference `&T`
            found associated type `<std::vec::Vec<T> as Iterable>::Item<'_>`
@@ -17,17 +10,10 @@ LL |     type Item;
    = note: for more information, visit https://doc.rust-lang.org/book/ch19-03-advanced-traits.html
 
 error[E0271]: type mismatch resolving `for<'a> <<[T] as Iterable>::Iter<'a> as std::iter::Iterator>::Item == <[T] as Iterable>::Item<'a>`
-  --> $DIR/iterable.rs:27:5
+  --> $DIR/iterable.rs:27:33
    |
-LL | impl<T> Iterable for [T] {
-   | ------------------------ in this `impl` item
 LL |     type Item<'a> where T: 'a = <std::slice::Iter<'a, T> as Iterator>::Item;
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected reference, found associated type
-   | 
-  ::: $SRC_DIR/libcore/iter/traits/iterator.rs:LL:COL
-   |
-LL |     type Item;
-   |          ---- associated type defined here
+   |                                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected reference, found associated type
    |
    = note:    expected reference `&T`
            found associated type `<[T] as Iterable>::Item<'_>`
diff --git a/src/test/ui/issues/issue-43784-associated-type.stderr b/src/test/ui/issues/issue-43784-associated-type.stderr
index 21cd39d01fa..fa835f5543d 100644
--- a/src/test/ui/issues/issue-43784-associated-type.stderr
+++ b/src/test/ui/issues/issue-43784-associated-type.stderr
@@ -1,14 +1,10 @@
 error[E0277]: the trait bound `T: std::marker::Copy` is not satisfied
-  --> $DIR/issue-43784-associated-type.rs:14:5
+  --> $DIR/issue-43784-associated-type.rs:14:18
    |
-LL |     type Assoc: Partial<Self>;
-   |          ----- associated type defined here
-...
-LL | impl<T> Complete for T {
-   | ---------------------- in this `impl` item
 LL |     type Assoc = T;
-   |     ^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `T`
+   |                  ^ the trait `std::marker::Copy` is not implemented for `T`
    |
+   = note: required because of the requirements on the impl of `std::marker::Copy` for `<T as Complete>::Assoc`
 help: consider restricting type parameter `T`
    |
 LL | impl<T: std::marker::Copy> Complete for T {
diff --git a/src/test/ui/issues/issue-65673.stderr b/src/test/ui/issues/issue-65673.stderr
index a556e35b6a9..d1a490eb565 100644
--- a/src/test/ui/issues/issue-65673.stderr
+++ b/src/test/ui/issues/issue-65673.stderr
@@ -1,16 +1,17 @@
 error[E0277]: the size for values of type `(dyn Trait + 'static)` cannot be known at compilation time
-  --> $DIR/issue-65673.rs:9:5
+  --> $DIR/issue-65673.rs:9:16
    |
+LL | trait WithType {
+   |       --------
 LL |     type Ctx;
-   |          --- associated type defined here
+   |     --------- required by this bound in `WithType`
 ...
-LL | impl<T> WithType for T {
-   | ---------------------- in this `impl` item
 LL |     type Ctx = dyn Alias<T>;
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
+   |                ^^^^^^^^^^^^ doesn't have a size known at compile-time
    |
    = help: the trait `std::marker::Sized` is not implemented for `(dyn Trait + 'static)`
    = note: to learn more, visit <https://doc.rust-lang.org/book/ch19-04-advanced-types.html#dynamically-sized-types-and-the-sized-trait>
+   = note: required because of the requirements on the impl of `std::marker::Sized` for `<T as WithType>::Ctx`
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/suggestions/missing-assoc-type-bound-restriction.stderr b/src/test/ui/suggestions/missing-assoc-type-bound-restriction.stderr
index 6b985edae9e..2091e30f115 100644
--- a/src/test/ui/suggestions/missing-assoc-type-bound-restriction.stderr
+++ b/src/test/ui/suggestions/missing-assoc-type-bound-restriction.stderr
@@ -13,20 +13,22 @@ LL | impl<A, T: Parent<Ty = A>> Parent for ParentWrapper<T> {
    |                   the trait `Child<A>` is not implemented for `<T as Parent>::Assoc`
 
 error[E0277]: the trait bound `<T as Parent>::Assoc: Child<A>` is not satisfied
-  --> $DIR/missing-assoc-type-bound-restriction.rs:20:5
+  --> $DIR/missing-assoc-type-bound-restriction.rs:20:18
    |
+LL | trait Parent {
+   |       ------
+LL |     type Ty;
 LL |     type Assoc: Child<Self::Ty>;
-   |          ----- associated type defined here
+   |                 --------------- required by this bound in `Parent`
 ...
 LL | impl<A, T: Parent<Ty = A>> Parent for ParentWrapper<T> {
-   | ------------------------------------------------------- help: consider further restricting the associated type: `where <T as Parent>::Assoc: Child<A>`
-   | |
-   | in this `impl` item
+   |                                                       - help: consider further restricting the associated type: `where <T as Parent>::Assoc: Child<A>`
 ...
 LL |     type Assoc = ChildWrapper<T::Assoc>;
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Child<A>` is not implemented for `<T as Parent>::Assoc`
+   |                  ^^^^^^^^^^^^^^^^^^^^^^ the trait `Child<A>` is not implemented for `<T as Parent>::Assoc`
    |
    = note: required because of the requirements on the impl of `Child<A>` for `ChildWrapper<<T as Parent>::Assoc>`
+   = note: required because of the requirements on the impl of `Child<<ParentWrapper<T> as Parent>::Ty>` for `<ParentWrapper<T> as Parent>::Assoc`
 
 error[E0277]: the trait bound `<T as Parent>::Assoc: Child<A>` is not satisfied
   --> $DIR/missing-assoc-type-bound-restriction.rs:20:5
diff --git a/src/test/ui/traits/cycle-cache-err-60010.stderr b/src/test/ui/traits/cycle-cache-err-60010.stderr
index 295845b1146..9e2e5568ba2 100644
--- a/src/test/ui/traits/cycle-cache-err-60010.stderr
+++ b/src/test/ui/traits/cycle-cache-err-60010.stderr
@@ -7,20 +7,21 @@ LL |     _parse: <ParseQuery as Query<RootDatabase>>::Data,
    = note: required because of the requirements on the impl of `Query<RootDatabase>` for `ParseQuery`
 
 error[E0275]: overflow evaluating the requirement `Runtime<RootDatabase>: std::panic::RefUnwindSafe`
-  --> $DIR/cycle-cache-err-60010.rs:31:5
+  --> $DIR/cycle-cache-err-60010.rs:31:20
    |
+LL | trait Database {
+   |       --------
 LL |     type Storage;
-   |          ------- associated type defined here
+   |     ------------- required by this bound in `Database`
 ...
-LL | impl Database for RootDatabase {
-   | ------------------------------ in this `impl` item
 LL |     type Storage = SalsaStorage;
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |                    ^^^^^^^^^^^^
    |
    = note: required because it appears within the type `RootDatabase`
    = note: required because of the requirements on the impl of `SourceDatabase` for `RootDatabase`
    = note: required because of the requirements on the impl of `Query<RootDatabase>` for `ParseQuery`
    = note: required because it appears within the type `SalsaStorage`
+   = note: required because of the requirements on the impl of `std::marker::Sized` for `<RootDatabase as Database>::Storage`
 
 error: aborting due to 2 previous errors
 
diff --git a/src/test/ui/traits/traits-assoc-type-in-supertrait-bad.rs b/src/test/ui/traits/traits-assoc-type-in-supertrait-bad.rs
index 47d7075ac35..579ce7cf706 100644
--- a/src/test/ui/traits/traits-assoc-type-in-supertrait-bad.rs
+++ b/src/test/ui/traits/traits-assoc-type-in-supertrait-bad.rs
@@ -8,8 +8,8 @@ pub trait Foo: Iterator<Item=<Self as Foo>::Key> {
     type Key;
 }
 
-impl Foo for IntoIter<i32> { //~ ERROR type mismatch
-    type Key = u32;
+impl Foo for IntoIter<i32> {
+    type Key = u32; //~ ERROR type mismatch
 }
 
 fn main() {
diff --git a/src/test/ui/traits/traits-assoc-type-in-supertrait-bad.stderr b/src/test/ui/traits/traits-assoc-type-in-supertrait-bad.stderr
index 441fa9f2792..604763f8e35 100644
--- a/src/test/ui/traits/traits-assoc-type-in-supertrait-bad.stderr
+++ b/src/test/ui/traits/traits-assoc-type-in-supertrait-bad.stderr
@@ -1,13 +1,8 @@
 error[E0271]: type mismatch resolving `<std::vec::IntoIter<i32> as std::iter::Iterator>::Item == u32`
-  --> $DIR/traits-assoc-type-in-supertrait-bad.rs:11:6
+  --> $DIR/traits-assoc-type-in-supertrait-bad.rs:12:16
    |
-LL | pub trait Foo: Iterator<Item=<Self as Foo>::Key> {
-   |                         ----------------------- required by this bound in `Foo`
-...
-LL | impl Foo for IntoIter<i32> {
-   |      ^^^ expected `i32`, found `u32`
-   |
-   = note: required because of the requirements on the impl of `Foo` for `std::vec::IntoIter<i32>`
+LL |     type Key = u32;
+   |                ^^^ expected `i32`, found `u32`
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/unboxed-closures/unboxed-closure-sugar-wrong-trait.stderr b/src/test/ui/unboxed-closures/unboxed-closure-sugar-wrong-trait.stderr
index ff65fd968c5..c81402a3dcc 100644
--- a/src/test/ui/unboxed-closures/unboxed-closure-sugar-wrong-trait.stderr
+++ b/src/test/ui/unboxed-closures/unboxed-closure-sugar-wrong-trait.stderr
@@ -5,10 +5,10 @@ LL | fn f<F:Trait(isize) -> isize>(x: F) {}
    |        ^^^^^^^^^^^^ unexpected type argument
 
 error[E0220]: associated type `Output` not found for `Trait`
-  --> $DIR/unboxed-closure-sugar-wrong-trait.rs:5:8
+  --> $DIR/unboxed-closure-sugar-wrong-trait.rs:5:24
    |
 LL | fn f<F:Trait(isize) -> isize>(x: F) {}
-   |        ^^^^^^^^^^^^^^^^^^^^^ associated type `Output` not found
+   |                        ^^^^^ associated type `Output` not found
 
 error: aborting due to 2 previous errors