about summary refs log tree commit diff
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2025-02-06 06:45:07 +0000
committerbors <bors@rust-lang.org>2025-02-06 06:45:07 +0000
commit59588250ad973ce69bd15879314c9769e65f36b3 (patch)
tree25e49a356546f6a242f6ea26a94071b3f1a96ad1
parentc753cb9b42e530950204dd0367525cce12811cdd (diff)
parentc549268a4a64c0a2c2288c6eee74173cdd7ad37e (diff)
downloadrust-59588250ad973ce69bd15879314c9769e65f36b3.tar.gz
rust-59588250ad973ce69bd15879314c9769e65f36b3.zip
Auto merge of #136613 - workingjubilee:rollup-ry6rw0m, r=workingjubilee
Rollup of 13 pull requests

Successful merges:

 - #133932 (Avoid using make_direct_deprecated() in extern "ptx-kernel")
 - #136269 (Pass spans around new solver)
 - #136550 (Fix `rustc_hidden_type_of_opaques` for RPITITs with no default body)
 - #136558 (Document minimum supported host tooling on macOS)
 - #136563 (Clean up `Trivial*Impls` macros)
 - #136566 (Fix link in from_fn.rs)
 - #136573 (Document why some "type mismatches" exist)
 - #136583 (Only highlight unmatchable parameters at the definition site)
 - #136587 (Update browser-ui-test version to `0.20.2`)
 - #136590 (Implement RustcInternal for RawPtrKind)
 - #136591 (Add `rustc_hir_pretty::expr_to_string` function)
 - #136595 (Fix `unreachable_pub` lint for hermit target)
 - #136611 (cg_llvm: Remove the `mod llvm_` hack, which should no longer be necessary)

Failed merges:

 - #136565 (compiler: Clean up weird `rustc_abi` reexports)

r? `@ghost`
`@rustbot` modify labels: rollup
-rw-r--r--compiler/rustc_codegen_llvm/src/lib.rs11
-rw-r--r--compiler/rustc_codegen_llvm/src/llvm/mod.rs4
-rw-r--r--compiler/rustc_hir_analysis/src/collect/dump.rs9
-rw-r--r--compiler/rustc_hir_pretty/src/lib.rs4
-rw-r--r--compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs319
-rw-r--r--compiler/rustc_infer/src/infer/at.rs23
-rw-r--r--compiler/rustc_infer/src/infer/context.rs14
-rw-r--r--compiler/rustc_middle/src/infer/canonical.rs4
-rw-r--r--compiler/rustc_middle/src/mir/basic_blocks.rs1
-rw-r--r--compiler/rustc_middle/src/mir/interpret/error.rs2
-rw-r--r--compiler/rustc_middle/src/mir/mod.rs4
-rw-r--r--compiler/rustc_middle/src/mir/type_foldable.rs67
-rw-r--r--compiler/rustc_middle/src/traits/mod.rs4
-rw-r--r--compiler/rustc_middle/src/traits/select.rs2
-rw-r--r--compiler/rustc_middle/src/ty/abstract_const.rs2
-rw-r--r--compiler/rustc_middle/src/ty/context.rs44
-rw-r--r--compiler/rustc_middle/src/ty/structural_impls.rs146
-rw-r--r--compiler/rustc_next_trait_solver/src/delegate.rs10
-rw-r--r--compiler/rustc_next_trait_solver/src/solve/eval_ctxt/canonical.rs27
-rw-r--r--compiler/rustc_next_trait_solver/src/solve/eval_ctxt/mod.rs46
-rw-r--r--compiler/rustc_next_trait_solver/src/solve/eval_ctxt/probe.rs1
-rw-r--r--compiler/rustc_smir/src/rustc_internal/internal.rs14
-rw-r--r--compiler/rustc_target/src/callconv/nvptx64.rs44
-rw-r--r--compiler/rustc_trait_selection/src/solve/delegate.rs17
-rw-r--r--compiler/rustc_trait_selection/src/solve/fulfill.rs4
-rw-r--r--compiler/rustc_trait_selection/src/solve/fulfill/derive_errors.rs6
-rw-r--r--compiler/rustc_trait_selection/src/solve/inspect/analyse.rs9
-rw-r--r--compiler/rustc_ty_utils/src/abi.rs11
-rw-r--r--compiler/rustc_type_ir/src/infer_ctxt.rs3
-rw-r--r--compiler/rustc_type_ir/src/macros.rs11
-rw-r--r--compiler/rustc_type_ir/src/relate/solver_relating.rs24
-rw-r--r--library/core/src/iter/sources/from_fn.rs2
-rw-r--r--library/panic_unwind/src/hermit.rs4
-rw-r--r--src/ci/docker/host-x86_64/x86_64-gnu-tools/browser-ui-test.version2
-rw-r--r--src/doc/rustc/src/platform-support/apple-darwin.md12
-rw-r--r--src/tools/rustdoc-gui/tester.js1
-rw-r--r--tests/assembly/nvptx-kernel-abi/nvptx-kernel-args-abi-v7.rs18
-rw-r--r--tests/ui/argument-suggestions/basic.stderr4
-rw-r--r--tests/ui/argument-suggestions/complex.stderr2
-rw-r--r--tests/ui/argument-suggestions/extra_arguments.stderr34
-rw-r--r--tests/ui/argument-suggestions/invalid_arguments.stderr12
-rw-r--r--tests/ui/argument-suggestions/issue-100478.stderr8
-rw-r--r--tests/ui/argument-suggestions/issue-101097.stderr56
-rw-r--r--tests/ui/argument-suggestions/issue-109425.stderr12
-rw-r--r--tests/ui/argument-suggestions/issue-109831.stderr2
-rw-r--r--tests/ui/argument-suggestions/issue-96638.stderr2
-rw-r--r--tests/ui/argument-suggestions/issue-97197.stderr2
-rw-r--r--tests/ui/argument-suggestions/issue-97484.stderr2
-rw-r--r--tests/ui/argument-suggestions/missing_arguments.stderr26
-rw-r--r--tests/ui/argument-suggestions/mixed_cases.stderr12
-rw-r--r--tests/ui/argument-suggestions/permuted_arguments.stderr4
-rw-r--r--tests/ui/argument-suggestions/suggest-better-removing-issue-126246.stderr12
-rw-r--r--tests/ui/argument-suggestions/swapped_arguments.stderr10
-rw-r--r--tests/ui/error-codes/E0061.stderr2
-rw-r--r--tests/ui/impl-trait/in-trait/dump.rs15
-rw-r--r--tests/ui/impl-trait/in-trait/dump.stderr8
-rw-r--r--tests/ui/issues/issue-4935.stderr2
-rw-r--r--tests/ui/methods/method-call-err-msg.stderr2
-rw-r--r--tests/ui/mismatched_types/generic-mismatch-reporting-issue-116615.stderr10
-rw-r--r--tests/ui/not-enough-arguments.stderr9
-rw-r--r--tests/ui/span/issue-34264.stderr4
-rw-r--r--tests/ui/span/missing-unit-argument.stderr2
-rw-r--r--tests/ui/traits/next-solver/diagnostics/coerce-in-may-coerce.stderr2
-rw-r--r--tests/ui/traits/next-solver/specialization-transmute.rs2
-rw-r--r--tests/ui/traits/next-solver/specialization-transmute.stderr8
-rw-r--r--tests/ui/traits/next-solver/unsound-region-obligation.rs2
-rw-r--r--tests/ui/traits/next-solver/unsound-region-obligation.stderr4
-rw-r--r--tests/ui/type/type-check/point-at-inference-4.rs1
-rw-r--r--tests/ui/type/type-check/point-at-inference-4.stderr6
-rw-r--r--tests/ui/typeck/remove-extra-argument.stderr2
70 files changed, 613 insertions, 594 deletions
diff --git a/compiler/rustc_codegen_llvm/src/lib.rs b/compiler/rustc_codegen_llvm/src/lib.rs
index 4a84fd29e44..14346795fda 100644
--- a/compiler/rustc_codegen_llvm/src/lib.rs
+++ b/compiler/rustc_codegen_llvm/src/lib.rs
@@ -71,14 +71,9 @@ mod debuginfo;
 mod declare;
 mod errors;
 mod intrinsic;
-
-// The following is a workaround that replaces `pub mod llvm;` and that fixes issue 53912.
-#[path = "llvm/mod.rs"]
-mod llvm_;
-pub mod llvm {
-    pub use super::llvm_::*;
-}
-
+// FIXME(Zalathar): Fix all the unreachable-pub warnings that would occur if
+// this isn't pub, then make it not pub.
+pub mod llvm;
 mod llvm_util;
 mod mono_item;
 mod type_;
diff --git a/compiler/rustc_codegen_llvm/src/llvm/mod.rs b/compiler/rustc_codegen_llvm/src/llvm/mod.rs
index 2592a7df95c..707aeba22cc 100644
--- a/compiler/rustc_codegen_llvm/src/llvm/mod.rs
+++ b/compiler/rustc_codegen_llvm/src/llvm/mod.rs
@@ -10,13 +10,9 @@ use libc::c_uint;
 use rustc_abi::{Align, Size, WrappingRange};
 use rustc_llvm::RustString;
 
-pub use self::AtomicRmwBinOp::*;
 pub use self::CallConv::*;
 pub use self::CodeGenOptSize::*;
-pub use self::IntPredicate::*;
-pub use self::Linkage::*;
 pub use self::MetadataType::*;
-pub use self::RealPredicate::*;
 pub use self::ffi::*;
 use crate::common::AsCCharPtr;
 
diff --git a/compiler/rustc_hir_analysis/src/collect/dump.rs b/compiler/rustc_hir_analysis/src/collect/dump.rs
index 4a508fc0cf6..41f8465ae91 100644
--- a/compiler/rustc_hir_analysis/src/collect/dump.rs
+++ b/compiler/rustc_hir_analysis/src/collect/dump.rs
@@ -11,6 +11,15 @@ pub(crate) fn opaque_hidden_types(tcx: TyCtxt<'_>) {
     }
 
     for id in tcx.hir_crate_items(()).opaques() {
+        if let hir::OpaqueTyOrigin::FnReturn { parent: fn_def_id, .. }
+        | hir::OpaqueTyOrigin::AsyncFn { parent: fn_def_id, .. } =
+            tcx.hir().expect_opaque_ty(id).origin
+            && let hir::Node::TraitItem(trait_item) = tcx.hir_node_by_def_id(fn_def_id)
+            && let (_, hir::TraitFn::Required(..)) = trait_item.expect_fn()
+        {
+            continue;
+        }
+
         let ty = tcx.type_of(id).instantiate_identity();
         let span = tcx.def_span(id);
         tcx.dcx().emit_err(crate::errors::TypeOf { span, ty });
diff --git a/compiler/rustc_hir_pretty/src/lib.rs b/compiler/rustc_hir_pretty/src/lib.rs
index 3b163d0bc20..8efef0c612b 100644
--- a/compiler/rustc_hir_pretty/src/lib.rs
+++ b/compiler/rustc_hir_pretty/src/lib.rs
@@ -321,6 +321,10 @@ pub fn pat_to_string(ann: &dyn PpAnn, pat: &hir::Pat<'_>) -> String {
     to_string(ann, |s| s.print_pat(pat))
 }
 
+pub fn expr_to_string(ann: &dyn PpAnn, pat: &hir::Expr<'_>) -> String {
+    to_string(ann, |s| s.print_expr(pat))
+}
+
 impl<'a> State<'a> {
     fn bclose_maybe_open(&mut self, span: rustc_span::Span, close_box: bool) {
         self.maybe_print_comment(span.hi());
diff --git a/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs b/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs
index e90474cabb4..5ce9e0556b4 100644
--- a/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs
+++ b/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs
@@ -1,4 +1,4 @@
-use std::{iter, mem};
+use std::{fmt, iter, mem};
 
 use itertools::Itertools;
 use rustc_data_structures::fx::FxIndexSet;
@@ -13,7 +13,7 @@ use rustc_hir::{ExprKind, HirId, Node, QPath};
 use rustc_hir_analysis::check::intrinsicck::InlineAsmCtxt;
 use rustc_hir_analysis::check::potentially_plural_count;
 use rustc_hir_analysis::hir_ty_lowering::HirTyLowerer;
-use rustc_index::{Idx, IndexVec};
+use rustc_index::IndexVec;
 use rustc_infer::infer::{DefineOpaqueTypes, InferOk, TypeTrace};
 use rustc_middle::ty::adjustment::AllowTwoPhase;
 use rustc_middle::ty::error::TypeError;
@@ -25,6 +25,7 @@ use rustc_span::{DUMMY_SP, Ident, Span, Symbol, kw, sym};
 use rustc_trait_selection::error_reporting::infer::{FailureCode, ObligationCauseExt};
 use rustc_trait_selection::infer::InferCtxtExt;
 use rustc_trait_selection::traits::{self, ObligationCauseCode, ObligationCtxt, SelectionContext};
+use smallvec::SmallVec;
 use tracing::debug;
 use {rustc_ast as ast, rustc_hir as hir};
 
@@ -44,6 +45,12 @@ use crate::{
     struct_span_code_err,
 };
 
+rustc_index::newtype_index! {
+    #[orderable]
+    #[debug_format = "GenericIdx({})"]
+    pub(crate) struct GenericIdx {}
+}
+
 #[derive(Clone, Copy, Default)]
 pub(crate) enum DivergingBlockBehavior {
     /// This is the current stable behavior:
@@ -1619,6 +1626,9 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
             ast::LitKind::Int(_, ast::LitIntType::Unsuffixed) => {
                 let opt_ty = expected.to_option(self).and_then(|ty| match ty.kind() {
                     ty::Int(_) | ty::Uint(_) => Some(ty),
+                    // These exist to direct casts like `0x61 as char` to use
+                    // the right integer type to cast from, instead of falling back to
+                    // i32 due to no further constraints.
                     ty::Char => Some(tcx.types.u8),
                     ty::RawPtr(..) => Some(tcx.types.usize),
                     ty::FnDef(..) | ty::FnPtr(..) => Some(tcx.types.usize),
@@ -2288,7 +2298,9 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
         // If we're calling a method of a Fn/FnMut/FnOnce trait object implicitly
         // (eg invoking a closure) we want to point at the underlying callable,
         // not the method implicitly invoked (eg call_once).
-        if let Some(assoc_item) = self.tcx.opt_associated_item(def_id)
+        // TupleArguments is set only when this is an implicit call (my_closure(...)) rather than explicit (my_closure.call(...))
+        if tuple_arguments == TupleArguments
+            && let Some(assoc_item) = self.tcx.opt_associated_item(def_id)
             // Since this is an associated item, it might point at either an impl or a trait item.
             // We want it to always point to the trait item.
             // If we're pointing at an inherent function, we don't need to do anything,
@@ -2298,8 +2310,6 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
             // Just an easy way to check "trait_def_id == Fn/FnMut/FnOnce"
             && let Some(call_kind) = self.tcx.fn_trait_kind_from_def_id(maybe_trait_def_id)
             && let Some(callee_ty) = callee_ty
-            // TupleArguments is set only when this is an implicit call (my_closure(...)) rather than explicit (my_closure.call(...))
-            && tuple_arguments == TupleArguments
         {
             let callee_ty = callee_ty.peel_refs();
             match *callee_ty.kind() {
@@ -2368,174 +2378,136 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
             && !def_span.is_dummy()
         {
             let mut spans: MultiSpan = def_span.into();
-
-            if let Some(params_with_generics) = self.get_hir_params_with_generics(def_id, is_method)
+            if let Some((params_with_generics, hir_generics)) =
+                self.get_hir_param_info(def_id, is_method)
             {
-                debug_assert_eq!(params_with_generics.len(), matched_inputs.len());
-
-                let mut generics_with_unmatched_params = Vec::new();
-
-                let check_for_matched_generics = || {
-                    if matched_inputs.iter().any(|x| x.is_some())
-                        && params_with_generics.iter().any(|(x, _)| x.is_some())
-                    {
-                        for (idx, (generic, _)) in params_with_generics.iter_enumerated() {
-                            // Param has to have a generic and be matched to be relevant
-                            if matched_inputs[idx].is_none() {
-                                continue;
-                            }
-
-                            let Some(generic) = generic else {
-                                continue;
-                            };
+                struct MismatchedParam<'a> {
+                    idx: ExpectedIdx,
+                    generic: GenericIdx,
+                    param: &'a FnParam<'a>,
+                    deps: SmallVec<[ExpectedIdx; 4]>,
+                }
 
-                            for unmatching_idx in
-                                idx.plus(1)..ExpectedIdx::from_usize(params_with_generics.len())
-                            {
-                                if matched_inputs[unmatching_idx].is_none()
-                                    && let Some(unmatched_idx_param_generic) =
-                                        params_with_generics[unmatching_idx].0
-                                    && unmatched_idx_param_generic.name.ident()
-                                        == generic.name.ident()
-                                {
-                                    // We found a parameter that didn't match that needed to
-                                    return true;
-                                }
-                            }
-                        }
+                debug_assert_eq!(params_with_generics.len(), matched_inputs.len());
+                // Gather all mismatched parameters with generics.
+                let mut mismatched_params = Vec::<MismatchedParam<'_>>::new();
+                if let Some(expected_idx) = expected_idx {
+                    let expected_idx = ExpectedIdx::from_usize(expected_idx);
+                    let &(expected_generic, ref expected_param) =
+                        &params_with_generics[expected_idx];
+                    if let Some(expected_generic) = expected_generic {
+                        mismatched_params.push(MismatchedParam {
+                            idx: expected_idx,
+                            generic: expected_generic,
+                            param: expected_param,
+                            deps: SmallVec::new(),
+                        });
+                    } else {
+                        // Still mark the mismatched parameter
+                        spans.push_span_label(expected_param.span(), "");
                     }
-                    false
-                };
-
-                let check_for_matched_generics = check_for_matched_generics();
-
-                for (idx, &(generic_param, param)) in
-                    params_with_generics.iter_enumerated().filter(|&(idx, _)| {
-                        check_for_matched_generics
-                            || expected_idx
-                                .is_none_or(|expected_idx| expected_idx == idx.as_usize())
-                    })
-                {
-                    let Some(generic_param) = generic_param else {
-                        spans.push_span_label(param.span(), "");
-                        continue;
-                    };
-
-                    let other_params_matched: Vec<(ExpectedIdx, FnParam<'_>)> =
-                        params_with_generics
-                            .iter_enumerated()
-                            .filter(|&(other_idx, &(other_generic_param, _))| {
-                                if other_idx == idx {
-                                    return false;
-                                }
-                                let Some(other_generic_param) = other_generic_param else {
-                                    return false;
-                                };
-                                if matched_inputs[idx].is_none()
-                                    && matched_inputs[other_idx].is_none()
-                                {
-                                    return false;
-                                }
-                                if matched_inputs[idx].is_some()
-                                    && matched_inputs[other_idx].is_some()
-                                {
-                                    return false;
-                                }
-                                other_generic_param.name.ident() == generic_param.name.ident()
-                            })
-                            .map(|(other_idx, &(_, other_param))| (other_idx, other_param))
-                            .collect();
-
-                    if !other_params_matched.is_empty() {
-                        let other_param_matched_names: Vec<String> = other_params_matched
-                            .iter()
-                            .map(|(idx, other_param)| {
-                                if let Some(name) = other_param.name() {
-                                    format!("`{name}`")
+                } else {
+                    mismatched_params.extend(
+                        params_with_generics.iter_enumerated().zip(matched_inputs).filter_map(
+                            |((idx, &(generic, ref param)), matched_idx)| {
+                                if matched_idx.is_some() {
+                                    None
+                                } else if let Some(generic) = generic {
+                                    Some(MismatchedParam {
+                                        idx,
+                                        generic,
+                                        param,
+                                        deps: SmallVec::new(),
+                                    })
                                 } else {
-                                    format!("parameter #{}", idx.as_u32() + 1)
+                                    // Still mark mismatched parameters
+                                    spans.push_span_label(param.span(), "");
+                                    None
                                 }
-                            })
-                            .collect();
+                            },
+                        ),
+                    );
+                }
 
-                        let matched_ty = self
-                            .resolve_vars_if_possible(formal_and_expected_inputs[idx].1)
-                            .sort_string(self.tcx);
+                if !mismatched_params.is_empty() {
+                    // For each mismatched paramter, create a two-way link to each matched parameter
+                    // of the same type.
+                    let mut dependants = IndexVec::<ExpectedIdx, _>::from_fn_n(
+                        |_| SmallVec::<[u32; 4]>::new(),
+                        params_with_generics.len(),
+                    );
+                    let mut generic_uses = IndexVec::<GenericIdx, _>::from_fn_n(
+                        |_| SmallVec::<[ExpectedIdx; 4]>::new(),
+                        hir_generics.params.len(),
+                    );
+                    for (idx, param) in mismatched_params.iter_mut().enumerate() {
+                        for ((other_idx, &(other_generic, _)), &other_matched_idx) in
+                            params_with_generics.iter_enumerated().zip(matched_inputs)
+                        {
+                            if other_generic == Some(param.generic) && other_matched_idx.is_some() {
+                                generic_uses[param.generic].extend([param.idx, other_idx]);
+                                dependants[other_idx].push(idx as u32);
+                                param.deps.push(other_idx);
+                            }
+                        }
+                    }
 
-                        if matched_inputs[idx].is_some() {
+                    // Highlight each mismatched type along with a note about which other parameters
+                    // the type depends on (if any).
+                    for param in &mismatched_params {
+                        if let Some(deps_list) = listify(&param.deps, |&dep| {
+                            params_with_generics[dep].1.display(dep.as_usize()).to_string()
+                        }) {
                             spans.push_span_label(
-                                param.span(),
+                                param.param.span(),
                                 format!(
-                                    "{} need{} to match the {} type of this parameter",
-                                    listify(&other_param_matched_names, |n| n.to_string())
-                                        .unwrap_or_default(),
-                                    pluralize!(if other_param_matched_names.len() == 1 {
-                                        0
-                                    } else {
-                                        1
-                                    }),
-                                    matched_ty,
+                                    "this parameter needs to match the {} type of {deps_list}",
+                                    self.resolve_vars_if_possible(
+                                        formal_and_expected_inputs[param.deps[0]].1
+                                    )
+                                    .sort_string(self.tcx),
                                 ),
                             );
                         } else {
+                            // Still mark mismatched parameters
+                            spans.push_span_label(param.param.span(), "");
+                        }
+                    }
+                    // Highligh each parameter being depended on for a generic type.
+                    for ((&(_, param), deps), &(_, expected_ty)) in
+                        params_with_generics.iter().zip(&dependants).zip(formal_and_expected_inputs)
+                    {
+                        if let Some(deps_list) = listify(deps, |&dep| {
+                            let param = &mismatched_params[dep as usize];
+                            param.param.display(param.idx.as_usize()).to_string()
+                        }) {
                             spans.push_span_label(
                                 param.span(),
                                 format!(
-                                    "this parameter needs to match the {} type of {}",
-                                    matched_ty,
-                                    listify(&other_param_matched_names, |n| n.to_string())
-                                        .unwrap_or_default(),
+                                    "{deps_list} need{} to match the {} type of this parameter",
+                                    pluralize!((deps.len() != 1) as u32),
+                                    self.resolve_vars_if_possible(expected_ty)
+                                        .sort_string(self.tcx),
                                 ),
                             );
                         }
-                        generics_with_unmatched_params.push(generic_param);
-                    } else {
-                        spans.push_span_label(param.span(), "");
                     }
-                }
-
-                for generic_param in self
-                    .tcx
-                    .hir()
-                    .get_if_local(def_id)
-                    .and_then(|node| node.generics())
-                    .into_iter()
-                    .flat_map(|x| x.params)
-                    .filter(|x| {
-                        generics_with_unmatched_params
-                            .iter()
-                            .any(|y| x.name.ident() == y.name.ident())
-                    })
-                {
-                    let param_idents_matching: Vec<String> = params_with_generics
-                        .iter_enumerated()
-                        .filter(|&(_, &(generic, _))| {
-                            if let Some(generic) = generic {
-                                generic.name.ident() == generic_param.name.ident()
-                            } else {
-                                false
-                            }
-                        })
-                        .map(|(idx, &(_, param))| {
-                            if let Some(name) = param.name() {
-                                format!("`{name}`")
-                            } else {
-                                format!("parameter #{}", idx.as_u32() + 1)
-                            }
-                        })
-                        .collect();
-
-                    if !param_idents_matching.is_empty() {
-                        spans.push_span_label(
-                            generic_param.span,
-                            format!(
-                                "{} {} reference this parameter `{}`",
-                                listify(&param_idents_matching, |n| n.to_string())
-                                    .unwrap_or_default(),
-                                if param_idents_matching.len() == 2 { "both" } else { "all" },
-                                generic_param.name.ident().name,
-                            ),
-                        );
+                    // Highlight each generic parameter in use.
+                    for (param, uses) in hir_generics.params.iter().zip(&mut generic_uses) {
+                        uses.sort();
+                        uses.dedup();
+                        if let Some(param_list) = listify(uses, |&idx| {
+                            params_with_generics[idx].1.display(idx.as_usize()).to_string()
+                        }) {
+                            spans.push_span_label(
+                                param.span,
+                                format!(
+                                    "{param_list} {} reference this parameter `{}`",
+                                    if uses.len() == 2 { "both" } else { "all" },
+                                    param.name.ident().name,
+                                ),
+                            );
+                        }
                     }
                 }
             }
@@ -2611,7 +2583,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
             return;
         };
 
-        if let Some(params_with_generics) = self.get_hir_params_with_generics(def_id, is_method) {
+        if let Some((params_with_generics, _)) = self.get_hir_param_info(def_id, is_method) {
             debug_assert_eq!(params_with_generics.len(), matched_inputs.len());
             for (idx, (generic_param, _)) in params_with_generics.iter_enumerated() {
                 if matched_inputs[idx].is_none() {
@@ -2639,7 +2611,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
                         if matched_inputs[other_idx].is_some() {
                             return false;
                         }
-                        other_generic_param.name.ident() == generic_param.name.ident()
+                        other_generic_param == generic_param
                     })
                     .count();
 
@@ -2671,11 +2643,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
     /// Returns the parameters of a function, with their generic parameters if those are the full
     /// type of that parameter. Returns `None` if the function has no generics or the body is
     /// unavailable (eg is an instrinsic).
-    fn get_hir_params_with_generics(
+    fn get_hir_param_info(
         &self,
         def_id: DefId,
         is_method: bool,
-    ) -> Option<IndexVec<ExpectedIdx, (Option<&hir::GenericParam<'_>>, FnParam<'_>)>> {
+    ) -> Option<(IndexVec<ExpectedIdx, (Option<GenericIdx>, FnParam<'_>)>, &hir::Generics<'_>)>
+    {
         let (sig, generics, body_id, param_names) = match self.tcx.hir().get_if_local(def_id)? {
             hir::Node::TraitItem(&hir::TraitItem {
                 generics,
@@ -2705,7 +2678,11 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
                 &hir::Path { res: Res::Def(_, res_def_id), .. },
             )) = param.kind
             {
-                generics.params.iter().find(|param| param.def_id.to_def_id() == res_def_id)
+                generics
+                    .params
+                    .iter()
+                    .position(|param| param.def_id.to_def_id() == res_def_id)
+                    .map(GenericIdx::from_usize)
             } else {
                 None
             }
@@ -2717,12 +2694,18 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
                 let params =
                     params.get(is_method as usize..params.len() - sig.decl.c_variadic as usize)?;
                 debug_assert_eq!(params.len(), fn_inputs.len());
-                Some(fn_inputs.zip(params.iter().map(|param| FnParam::Param(param))).collect())
+                Some((
+                    fn_inputs.zip(params.iter().map(|param| FnParam::Param(param))).collect(),
+                    generics,
+                ))
             }
             (None, Some(params)) => {
                 let params = params.get(is_method as usize..)?;
                 debug_assert_eq!(params.len(), fn_inputs.len());
-                Some(fn_inputs.zip(params.iter().map(|param| FnParam::Name(param))).collect())
+                Some((
+                    fn_inputs.zip(params.iter().map(|param| FnParam::Name(param))).collect(),
+                    generics,
+                ))
             }
         }
     }
@@ -2770,4 +2753,18 @@ impl FnParam<'_> {
             _ => None,
         }
     }
+
+    fn display(&self, idx: usize) -> impl '_ + fmt::Display {
+        struct D<'a>(FnParam<'a>, usize);
+        impl fmt::Display for D<'_> {
+            fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+                if let Some(name) = self.0.name() {
+                    write!(f, "`{name}`")
+                } else {
+                    write!(f, "parameter #{}", self.1 + 1)
+                }
+            }
+        }
+        D(*self, idx)
+    }
 }
diff --git a/compiler/rustc_infer/src/infer/at.rs b/compiler/rustc_infer/src/infer/at.rs
index ad15b764bcc..2cd67cc4da2 100644
--- a/compiler/rustc_infer/src/infer/at.rs
+++ b/compiler/rustc_infer/src/infer/at.rs
@@ -137,6 +137,7 @@ impl<'a, 'tcx> At<'a, 'tcx> {
                 expected,
                 ty::Contravariant,
                 actual,
+                self.cause.span,
             )
             .map(|goals| self.goals_to_obligations(goals))
         } else {
@@ -163,8 +164,15 @@ impl<'a, 'tcx> At<'a, 'tcx> {
         T: ToTrace<'tcx>,
     {
         if self.infcx.next_trait_solver {
-            NextSolverRelate::relate(self.infcx, self.param_env, expected, ty::Covariant, actual)
-                .map(|goals| self.goals_to_obligations(goals))
+            NextSolverRelate::relate(
+                self.infcx,
+                self.param_env,
+                expected,
+                ty::Covariant,
+                actual,
+                self.cause.span,
+            )
+            .map(|goals| self.goals_to_obligations(goals))
         } else {
             let mut op = TypeRelating::new(
                 self.infcx,
@@ -208,8 +216,15 @@ impl<'a, 'tcx> At<'a, 'tcx> {
         T: Relate<TyCtxt<'tcx>>,
     {
         if self.infcx.next_trait_solver {
-            NextSolverRelate::relate(self.infcx, self.param_env, expected, ty::Invariant, actual)
-                .map(|goals| self.goals_to_obligations(goals))
+            NextSolverRelate::relate(
+                self.infcx,
+                self.param_env,
+                expected,
+                ty::Invariant,
+                actual,
+                self.cause.span,
+            )
+            .map(|goals| self.goals_to_obligations(goals))
         } else {
             let mut op = TypeRelating::new(
                 self.infcx,
diff --git a/compiler/rustc_infer/src/infer/context.rs b/compiler/rustc_infer/src/infer/context.rs
index 69ab0e69e21..eae69ec3e0f 100644
--- a/compiler/rustc_infer/src/infer/context.rs
+++ b/compiler/rustc_infer/src/infer/context.rs
@@ -5,7 +5,7 @@ use rustc_middle::ty::fold::TypeFoldable;
 use rustc_middle::ty::relate::RelateResult;
 use rustc_middle::ty::relate::combine::PredicateEmittingRelation;
 use rustc_middle::ty::{self, Ty, TyCtxt};
-use rustc_span::{DUMMY_SP, ErrorGuaranteed};
+use rustc_span::{DUMMY_SP, ErrorGuaranteed, Span};
 
 use super::{BoundRegionConversionTime, InferCtxt, RegionVariableOrigin, SubregionOrigin};
 
@@ -203,23 +203,23 @@ impl<'tcx> rustc_type_ir::InferCtxtLike for InferCtxt<'tcx> {
         self.probe(|_| probe())
     }
 
-    fn sub_regions(&self, sub: ty::Region<'tcx>, sup: ty::Region<'tcx>) {
+    fn sub_regions(&self, sub: ty::Region<'tcx>, sup: ty::Region<'tcx>, span: Span) {
         self.inner.borrow_mut().unwrap_region_constraints().make_subregion(
-            SubregionOrigin::RelateRegionParamBound(DUMMY_SP, None),
+            SubregionOrigin::RelateRegionParamBound(span, None),
             sub,
             sup,
         );
     }
 
-    fn equate_regions(&self, a: ty::Region<'tcx>, b: ty::Region<'tcx>) {
+    fn equate_regions(&self, a: ty::Region<'tcx>, b: ty::Region<'tcx>, span: Span) {
         self.inner.borrow_mut().unwrap_region_constraints().make_eqregion(
-            SubregionOrigin::RelateRegionParamBound(DUMMY_SP, None),
+            SubregionOrigin::RelateRegionParamBound(span, None),
             a,
             b,
         );
     }
 
-    fn register_ty_outlives(&self, ty: Ty<'tcx>, r: ty::Region<'tcx>) {
-        self.register_region_obligation_with_cause(ty, r, &ObligationCause::dummy());
+    fn register_ty_outlives(&self, ty: Ty<'tcx>, r: ty::Region<'tcx>, span: Span) {
+        self.register_region_obligation_with_cause(ty, r, &ObligationCause::dummy_with_span(span));
     }
 }
diff --git a/compiler/rustc_middle/src/infer/canonical.rs b/compiler/rustc_middle/src/infer/canonical.rs
index 0f408375e05..3cd148cd442 100644
--- a/compiler/rustc_middle/src/infer/canonical.rs
+++ b/compiler/rustc_middle/src/infer/canonical.rs
@@ -142,10 +142,6 @@ impl<'tcx, R> QueryResponse<'tcx, R> {
 pub type QueryOutlivesConstraint<'tcx> =
     (ty::OutlivesPredicate<'tcx, GenericArg<'tcx>>, ConstraintCategory<'tcx>);
 
-TrivialTypeTraversalImpls! {
-    crate::infer::canonical::Certainty,
-}
-
 #[derive(Default)]
 pub struct CanonicalParamEnvCache<'tcx> {
     map: Lock<
diff --git a/compiler/rustc_middle/src/mir/basic_blocks.rs b/compiler/rustc_middle/src/mir/basic_blocks.rs
index 3eb563d7d6e..c32cf5f8253 100644
--- a/compiler/rustc_middle/src/mir/basic_blocks.rs
+++ b/compiler/rustc_middle/src/mir/basic_blocks.rs
@@ -163,6 +163,7 @@ impl<'tcx> graph::Predecessors for BasicBlocks<'tcx> {
     }
 }
 
+// Done here instead of in `structural_impls.rs` because `Cache` is private, as is `basic_blocks`.
 TrivialTypeTraversalImpls! { Cache }
 
 impl<S: Encoder> Encodable<S> for Cache {
diff --git a/compiler/rustc_middle/src/mir/interpret/error.rs b/compiler/rustc_middle/src/mir/interpret/error.rs
index 8c085fa310a..1222ba052cc 100644
--- a/compiler/rustc_middle/src/mir/interpret/error.rs
+++ b/compiler/rustc_middle/src/mir/interpret/error.rs
@@ -95,8 +95,6 @@ impl From<ReportedErrorInfo> for ErrorGuaranteed {
     }
 }
 
-TrivialTypeTraversalImpls! { ErrorHandled }
-
 pub type EvalToAllocationRawResult<'tcx> = Result<ConstAlloc<'tcx>, ErrorHandled>;
 pub type EvalStaticInitializerRawResult<'tcx> = Result<ConstAllocation<'tcx>, ErrorHandled>;
 pub type EvalToConstValueResult<'tcx> = Result<ConstValue<'tcx>, ErrorHandled>;
diff --git a/compiler/rustc_middle/src/mir/mod.rs b/compiler/rustc_middle/src/mir/mod.rs
index cfb78e5dddf..68d5e5f4dd2 100644
--- a/compiler/rustc_middle/src/mir/mod.rs
+++ b/compiler/rustc_middle/src/mir/mod.rs
@@ -34,7 +34,6 @@ use self::visit::TyContext;
 use crate::mir::interpret::{AllocRange, Scalar};
 use crate::mir::visit::MirVisitable;
 use crate::ty::codec::{TyDecoder, TyEncoder};
-use crate::ty::fold::{FallibleTypeFolder, TypeFoldable};
 use crate::ty::print::{FmtPrinter, Printer, pretty_print_const, with_no_trimmed_paths};
 use crate::ty::visit::TypeVisitableExt;
 use crate::ty::{
@@ -59,7 +58,6 @@ pub mod tcx;
 mod terminator;
 
 pub mod traversal;
-mod type_foldable;
 pub mod visit;
 
 pub use consts::*;
@@ -927,8 +925,6 @@ pub enum BindingForm<'tcx> {
     RefForGuard,
 }
 
-TrivialTypeTraversalImpls! { BindingForm<'tcx> }
-
 mod binding_form_impl {
     use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
     use rustc_query_system::ich::StableHashingContext;
diff --git a/compiler/rustc_middle/src/mir/type_foldable.rs b/compiler/rustc_middle/src/mir/type_foldable.rs
deleted file mode 100644
index 9893dd0484c..00000000000
--- a/compiler/rustc_middle/src/mir/type_foldable.rs
+++ /dev/null
@@ -1,67 +0,0 @@
-//! `TypeFoldable` implementations for MIR types
-
-use rustc_ast::InlineAsmTemplatePiece;
-use rustc_hir::UnsafeBinderCastKind;
-use rustc_hir::def_id::LocalDefId;
-
-use super::*;
-
-TrivialTypeTraversalImpls! {
-    BlockTailInfo,
-    MirPhase,
-    SourceInfo,
-    FakeReadCause,
-    RetagKind,
-    SourceScope,
-    SourceScopeLocalData,
-    UserTypeAnnotationIndex,
-    BorrowKind,
-    RawPtrKind,
-    CastKind,
-    BasicBlock,
-    SwitchTargets,
-    CoroutineKind,
-    CoroutineSavedLocal,
-    UnsafeBinderCastKind,
-}
-
-TrivialTypeTraversalImpls! {
-    ConstValue<'tcx>,
-    NullOp<'tcx>,
-}
-
-impl<'tcx> TypeFoldable<TyCtxt<'tcx>> for &'tcx [InlineAsmTemplatePiece] {
-    fn try_fold_with<F: FallibleTypeFolder<TyCtxt<'tcx>>>(
-        self,
-        _folder: &mut F,
-    ) -> Result<Self, F::Error> {
-        Ok(self)
-    }
-}
-
-impl<'tcx> TypeFoldable<TyCtxt<'tcx>> for &'tcx [Span] {
-    fn try_fold_with<F: FallibleTypeFolder<TyCtxt<'tcx>>>(
-        self,
-        _folder: &mut F,
-    ) -> Result<Self, F::Error> {
-        Ok(self)
-    }
-}
-
-impl<'tcx> TypeFoldable<TyCtxt<'tcx>> for &'tcx ty::List<LocalDefId> {
-    fn try_fold_with<F: FallibleTypeFolder<TyCtxt<'tcx>>>(
-        self,
-        _folder: &mut F,
-    ) -> Result<Self, F::Error> {
-        Ok(self)
-    }
-}
-
-impl<'tcx> TypeFoldable<TyCtxt<'tcx>> for &'tcx ty::List<PlaceElem<'tcx>> {
-    fn try_fold_with<F: FallibleTypeFolder<TyCtxt<'tcx>>>(
-        self,
-        folder: &mut F,
-    ) -> Result<Self, F::Error> {
-        ty::util::fold_list(self, folder, |tcx, v| tcx.mk_place_elems(v))
-    }
-}
diff --git a/compiler/rustc_middle/src/traits/mod.rs b/compiler/rustc_middle/src/traits/mod.rs
index d0ce4e6242e..1314a235610 100644
--- a/compiler/rustc_middle/src/traits/mod.rs
+++ b/compiler/rustc_middle/src/traits/mod.rs
@@ -427,10 +427,6 @@ pub enum IsConstable {
     Ctor,
 }
 
-TrivialTypeTraversalAndLiftImpls! {
-    IsConstable,
-}
-
 /// The 'location' at which we try to perform HIR-based wf checking.
 /// This information is used to obtain an `hir::Ty`, which
 /// we can walk in order to obtain precise spans for any
diff --git a/compiler/rustc_middle/src/traits/select.rs b/compiler/rustc_middle/src/traits/select.rs
index 094fc62afbb..b7cd545d02d 100644
--- a/compiler/rustc_middle/src/traits/select.rs
+++ b/compiler/rustc_middle/src/traits/select.rs
@@ -260,8 +260,6 @@ impl From<ErrorGuaranteed> for OverflowError {
     }
 }
 
-TrivialTypeTraversalImpls! { OverflowError }
-
 impl<'tcx> From<OverflowError> for SelectionError<'tcx> {
     fn from(overflow_error: OverflowError) -> SelectionError<'tcx> {
         match overflow_error {
diff --git a/compiler/rustc_middle/src/ty/abstract_const.rs b/compiler/rustc_middle/src/ty/abstract_const.rs
index 002d3819621..c9b9ec771b3 100644
--- a/compiler/rustc_middle/src/ty/abstract_const.rs
+++ b/compiler/rustc_middle/src/ty/abstract_const.rs
@@ -30,8 +30,6 @@ impl From<ErrorGuaranteed> for NotConstEvaluatable {
     }
 }
 
-TrivialTypeTraversalImpls! { NotConstEvaluatable }
-
 pub type BoundAbstractConst<'tcx> =
     Result<Option<EarlyBinder<'tcx, ty::Const<'tcx>>>, ErrorGuaranteed>;
 
diff --git a/compiler/rustc_middle/src/ty/context.rs b/compiler/rustc_middle/src/ty/context.rs
index 86248b495cd..1a98db54581 100644
--- a/compiler/rustc_middle/src/ty/context.rs
+++ b/compiler/rustc_middle/src/ty/context.rs
@@ -76,11 +76,11 @@ use crate::traits::solve::{
 };
 use crate::ty::predicate::ExistentialPredicateStableCmpExt as _;
 use crate::ty::{
-    self, AdtDef, AdtDefData, AdtKind, Binder, BoundConstness, Clause, Clauses, Const, GenericArg,
-    GenericArgs, GenericArgsRef, GenericParamDefKind, ImplPolarity, List, ListWithCachedTypeInfo,
-    ParamConst, ParamTy, Pattern, PatternKind, PolyExistentialPredicate, PolyFnSig, Predicate,
-    PredicateKind, PredicatePolarity, Region, RegionKind, ReprOptions, TraitObjectVisitor, Ty,
-    TyKind, TyVid, Visibility,
+    self, AdtDef, AdtDefData, AdtKind, Binder, Clause, Clauses, Const, GenericArg, GenericArgs,
+    GenericArgsRef, GenericParamDefKind, List, ListWithCachedTypeInfo, ParamConst, ParamTy,
+    Pattern, PatternKind, PolyExistentialPredicate, PolyFnSig, Predicate, PredicateKind,
+    PredicatePolarity, Region, RegionKind, ReprOptions, TraitObjectVisitor, Ty, TyKind, TyVid,
+    Visibility,
 };
 
 #[allow(rustc::usage_of_ty_tykind)]
@@ -2243,21 +2243,23 @@ macro_rules! nop_list_lift {
     };
 }
 
-nop_lift! {type_; Ty<'a> => Ty<'tcx>}
-nop_lift! {region; Region<'a> => Region<'tcx>}
-nop_lift! {const_; Const<'a> => Const<'tcx>}
-nop_lift! {pat; Pattern<'a> => Pattern<'tcx>}
-nop_lift! {const_allocation; ConstAllocation<'a> => ConstAllocation<'tcx>}
-nop_lift! {predicate; Predicate<'a> => Predicate<'tcx>}
-nop_lift! {predicate; Clause<'a> => Clause<'tcx>}
-nop_lift! {layout; Layout<'a> => Layout<'tcx>}
-
-nop_list_lift! {type_lists; Ty<'a> => Ty<'tcx>}
-nop_list_lift! {poly_existential_predicates; PolyExistentialPredicate<'a> => PolyExistentialPredicate<'tcx>}
-nop_list_lift! {bound_variable_kinds; ty::BoundVariableKind => ty::BoundVariableKind}
+nop_lift! { type_; Ty<'a> => Ty<'tcx> }
+nop_lift! { region; Region<'a> => Region<'tcx> }
+nop_lift! { const_; Const<'a> => Const<'tcx> }
+nop_lift! { pat; Pattern<'a> => Pattern<'tcx> }
+nop_lift! { const_allocation; ConstAllocation<'a> => ConstAllocation<'tcx> }
+nop_lift! { predicate; Predicate<'a> => Predicate<'tcx> }
+nop_lift! { predicate; Clause<'a> => Clause<'tcx> }
+nop_lift! { layout; Layout<'a> => Layout<'tcx> }
+
+nop_list_lift! { type_lists; Ty<'a> => Ty<'tcx> }
+nop_list_lift! {
+    poly_existential_predicates; PolyExistentialPredicate<'a> => PolyExistentialPredicate<'tcx>
+}
+nop_list_lift! { bound_variable_kinds; ty::BoundVariableKind => ty::BoundVariableKind }
 
 // This is the impl for `&'a GenericArgs<'a>`.
-nop_list_lift! {args; GenericArg<'a> => GenericArg<'tcx>}
+nop_list_lift! { args; GenericArg<'a> => GenericArg<'tcx> }
 
 macro_rules! nop_slice_lift {
     ($ty:ty => $lifted:ty) => {
@@ -2277,11 +2279,7 @@ macro_rules! nop_slice_lift {
     };
 }
 
-nop_slice_lift! {ty::ValTree<'a> => ty::ValTree<'tcx>}
-
-TrivialLiftImpls! {
-    ImplPolarity, PredicatePolarity, Promoted, BoundConstness,
-}
+nop_slice_lift! { ty::ValTree<'a> => ty::ValTree<'tcx> }
 
 macro_rules! sty_debug_print {
     ($fmt: expr, $ctxt: expr, $($variant: ident),*) => {{
diff --git a/compiler/rustc_middle/src/ty/structural_impls.rs b/compiler/rustc_middle/src/ty/structural_impls.rs
index 03b26b44538..c33f952fc86 100644
--- a/compiler/rustc_middle/src/ty/structural_impls.rs
+++ b/compiler/rustc_middle/src/ty/structural_impls.rs
@@ -6,15 +6,18 @@
 use std::fmt::{self, Debug};
 
 use rustc_abi::TyAndLayout;
+use rustc_ast::InlineAsmTemplatePiece;
 use rustc_ast_ir::try_visit;
 use rustc_ast_ir::visit::VisitorResult;
 use rustc_hir::def::Namespace;
+use rustc_hir::def_id::LocalDefId;
+use rustc_span::Span;
 use rustc_span::source_map::Spanned;
 use rustc_type_ir::ConstKind;
 
 use super::print::PrettyPrinter;
 use super::{GenericArg, GenericArgKind, Pattern, Region};
-use crate::mir::interpret;
+use crate::mir::PlaceElem;
 use crate::ty::fold::{FallibleTypeFolder, TypeFoldable, TypeSuperFoldable};
 use crate::ty::print::{FmtPrinter, Printer, with_no_trimmed_paths};
 use crate::ty::visit::{TypeSuperVisitable, TypeVisitable, TypeVisitor};
@@ -221,76 +224,89 @@ impl<'tcx> fmt::Debug for Region<'tcx> {
 // copy...), just add them to one of these lists as appropriate.
 
 // For things for which the type library provides traversal implementations
-// for all Interners, we only need to provide a Lift implementation:
+// for all Interners, we only need to provide a Lift implementation.
 TrivialLiftImpls! {
-     (),
-     bool,
-     usize,
-     u64,
+    (),
+    bool,
+    usize,
+    u64,
+    // tidy-alphabetical-start
+    crate::mir::interpret::AllocId,
+    crate::mir::interpret::Scalar,
+    crate::mir::Promoted,
+    rustc_abi::ExternAbi,
+    rustc_abi::Size,
+    rustc_hir::Safety,
+    rustc_type_ir::BoundConstness,
+    rustc_type_ir::PredicatePolarity,
+    // tidy-alphabetical-end
 }
 
 // For some things about which the type library does not know, or does not
 // provide any traversal implementations, we need to provide a traversal
 // implementation (only for TyCtxt<'_> interners).
 TrivialTypeTraversalImpls! {
-    ::rustc_abi::FieldIdx,
-    ::rustc_abi::VariantIdx,
-    crate::middle::region::Scope,
-    ::rustc_ast::InlineAsmOptions,
-    ::rustc_ast::InlineAsmTemplatePiece,
-    ::rustc_ast::NodeId,
-    ::rustc_hir::def::Res,
-    ::rustc_hir::def_id::LocalDefId,
-    ::rustc_hir::ByRef,
-    ::rustc_hir::HirId,
-    ::rustc_hir::MatchSource,
-    ::rustc_target::asm::InlineAsmRegOrRegClass,
-    crate::mir::coverage::BlockMarkerId,
-    crate::mir::coverage::CounterId,
-    crate::mir::coverage::ExpressionId,
-    crate::mir::coverage::ConditionId,
+    // tidy-alphabetical-start
+    crate::infer::canonical::Certainty,
+    crate::mir::BasicBlock,
+    crate::mir::BindingForm<'tcx>,
+    crate::mir::BlockTailInfo,
+    crate::mir::BorrowKind,
+    crate::mir::CastKind,
+    crate::mir::ConstValue<'tcx>,
+    crate::mir::CoroutineSavedLocal,
+    crate::mir::FakeReadCause,
     crate::mir::Local,
+    crate::mir::MirPhase,
+    crate::mir::NullOp<'tcx>,
     crate::mir::Promoted,
+    crate::mir::RawPtrKind,
+    crate::mir::RetagKind,
+    crate::mir::SourceInfo,
+    crate::mir::SourceScope,
+    crate::mir::SourceScopeLocalData,
+    crate::mir::SwitchTargets,
+    crate::traits::IsConstable,
+    crate::traits::OverflowError,
+    crate::ty::abstract_const::NotConstEvaluatable,
     crate::ty::adjustment::AutoBorrowMutability,
+    crate::ty::adjustment::PointerCoercion,
     crate::ty::AdtKind,
-    crate::ty::BoundRegion,
-    // Including `BoundRegionKind` is a *bit* dubious, but direct
-    // references to bound region appear in `ty::Error`, and aren't
-    // really meant to be folded. In general, we can only fold a fully
-    // general `Region`.
-    crate::ty::BoundRegionKind,
     crate::ty::AssocItem,
     crate::ty::AssocKind,
+    crate::ty::BoundRegion,
+    crate::ty::BoundVar,
     crate::ty::Placeholder<crate::ty::BoundRegion>,
     crate::ty::Placeholder<crate::ty::BoundTy>,
     crate::ty::Placeholder<ty::BoundVar>,
-    crate::ty::LateParamRegion,
-    crate::ty::adjustment::PointerCoercion,
-    ::rustc_span::Ident,
-    ::rustc_span::Span,
-    ::rustc_span::Symbol,
-    ty::BoundVar,
-    ty::ValTree<'tcx>,
+    crate::ty::UserTypeAnnotationIndex,
+    crate::ty::ValTree<'tcx>,
+    rustc_abi::FieldIdx,
+    rustc_abi::VariantIdx,
+    rustc_ast::InlineAsmOptions,
+    rustc_ast::InlineAsmTemplatePiece,
+    rustc_hir::CoroutineKind,
+    rustc_hir::def_id::LocalDefId,
+    rustc_hir::HirId,
+    rustc_hir::MatchSource,
+    rustc_span::Ident,
+    rustc_span::Span,
+    rustc_span::Symbol,
+    rustc_target::asm::InlineAsmRegOrRegClass,
+    // tidy-alphabetical-end
 }
+
 // For some things about which the type library does not know, or does not
 // provide any traversal implementations, we need to provide a traversal
 // implementation and a lift implementation (the former only for TyCtxt<'_>
 // interners).
 TrivialTypeTraversalAndLiftImpls! {
-    ::rustc_hir::def_id::DefId,
-    crate::ty::ClosureKind,
+    // tidy-alphabetical-start
+    crate::ty::instance::ReifyReason,
     crate::ty::ParamConst,
     crate::ty::ParamTy,
-    crate::ty::instance::ReifyReason,
-    interpret::AllocId,
-    interpret::CtfeProvenance,
-    interpret::Scalar,
-    rustc_abi::Size,
-}
-
-TrivialLiftImpls! {
-    ::rustc_hir::Safety,
-    ::rustc_abi::ExternAbi,
+    rustc_hir::def_id::DefId,
+    // tidy-alphabetical-end
 }
 
 ///////////////////////////////////////////////////////////////////////////
@@ -672,3 +688,39 @@ impl<'tcx, T: TypeFoldable<TyCtxt<'tcx>> + Debug + Clone> TypeFoldable<TyCtxt<'t
         })
     }
 }
+
+impl<'tcx> TypeFoldable<TyCtxt<'tcx>> for &'tcx [InlineAsmTemplatePiece] {
+    fn try_fold_with<F: FallibleTypeFolder<TyCtxt<'tcx>>>(
+        self,
+        _folder: &mut F,
+    ) -> Result<Self, F::Error> {
+        Ok(self)
+    }
+}
+
+impl<'tcx> TypeFoldable<TyCtxt<'tcx>> for &'tcx [Span] {
+    fn try_fold_with<F: FallibleTypeFolder<TyCtxt<'tcx>>>(
+        self,
+        _folder: &mut F,
+    ) -> Result<Self, F::Error> {
+        Ok(self)
+    }
+}
+
+impl<'tcx> TypeFoldable<TyCtxt<'tcx>> for &'tcx ty::List<LocalDefId> {
+    fn try_fold_with<F: FallibleTypeFolder<TyCtxt<'tcx>>>(
+        self,
+        _folder: &mut F,
+    ) -> Result<Self, F::Error> {
+        Ok(self)
+    }
+}
+
+impl<'tcx> TypeFoldable<TyCtxt<'tcx>> for &'tcx ty::List<PlaceElem<'tcx>> {
+    fn try_fold_with<F: FallibleTypeFolder<TyCtxt<'tcx>>>(
+        self,
+        folder: &mut F,
+    ) -> Result<Self, F::Error> {
+        ty::util::fold_list(self, folder, |tcx, v| tcx.mk_place_elems(v))
+    }
+}
diff --git a/compiler/rustc_next_trait_solver/src/delegate.rs b/compiler/rustc_next_trait_solver/src/delegate.rs
index 2d2d50e62f9..a64941cce3a 100644
--- a/compiler/rustc_next_trait_solver/src/delegate.rs
+++ b/compiler/rustc_next_trait_solver/src/delegate.rs
@@ -4,15 +4,13 @@ use rustc_type_ir::fold::TypeFoldable;
 use rustc_type_ir::solve::{Certainty, Goal, NoSolution};
 use rustc_type_ir::{self as ty, InferCtxtLike, Interner};
 
-pub trait SolverDelegate: Deref<Target = <Self as SolverDelegate>::Infcx> + Sized {
-    type Infcx: InferCtxtLike<Interner = <Self as SolverDelegate>::Interner>;
+pub trait SolverDelegate: Deref<Target = Self::Infcx> + Sized {
+    type Infcx: InferCtxtLike<Interner = Self::Interner>;
     type Interner: Interner;
     fn cx(&self) -> Self::Interner {
         (**self).cx()
     }
 
-    type Span: Copy;
-
     fn build_with_canonical<V>(
         cx: Self::Interner,
         canonical: &ty::CanonicalQueryInput<Self::Interner, V>,
@@ -23,7 +21,7 @@ pub trait SolverDelegate: Deref<Target = <Self as SolverDelegate>::Infcx> + Size
     fn fresh_var_for_kind_with_span(
         &self,
         arg: <Self::Interner as Interner>::GenericArg,
-        span: Self::Span,
+        span: <Self::Interner as Interner>::Span,
     ) -> <Self::Interner as Interner>::GenericArg;
 
     // FIXME: Uplift the leak check into this crate.
@@ -61,6 +59,7 @@ pub trait SolverDelegate: Deref<Target = <Self as SolverDelegate>::Infcx> + Size
     fn instantiate_canonical_var_with_infer(
         &self,
         cv_info: ty::CanonicalVarInfo<Self::Interner>,
+        span: <Self::Interner as Interner>::Span,
         universe_map: impl Fn(ty::UniverseIndex) -> ty::UniverseIndex,
     ) -> <Self::Interner as Interner>::GenericArg;
 
@@ -86,6 +85,7 @@ pub trait SolverDelegate: Deref<Target = <Self as SolverDelegate>::Infcx> + Size
         &self,
         key: ty::OpaqueTypeKey<Self::Interner>,
         hidden_ty: <Self::Interner as Interner>::Ty,
+        span: <Self::Interner as Interner>::Span,
     );
 
     fn reset_opaque_types(&self);
diff --git a/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/canonical.rs b/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/canonical.rs
index e99cd3d2727..39e365806cb 100644
--- a/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/canonical.rs
+++ b/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/canonical.rs
@@ -255,20 +255,29 @@ where
             self.delegate,
             &original_values,
             &response,
+            self.origin_span,
         );
 
         let Response { var_values, external_constraints, certainty } =
             self.delegate.instantiate_canonical(response, instantiation);
 
-        Self::unify_query_var_values(self.delegate, param_env, &original_values, var_values);
+        Self::unify_query_var_values(
+            self.delegate,
+            param_env,
+            &original_values,
+            var_values,
+            self.origin_span,
+        );
 
         let ExternalConstraintsData {
             region_constraints,
             opaque_types,
             normalization_nested_goals,
         } = &*external_constraints;
+
         self.register_region_constraints(region_constraints);
         self.register_new_opaque_types(opaque_types);
+
         (normalization_nested_goals.clone(), certainty)
     }
 
@@ -279,6 +288,7 @@ where
         delegate: &D,
         original_values: &[I::GenericArg],
         response: &Canonical<I, T>,
+        span: I::Span,
     ) -> CanonicalVarValues<I> {
         // FIXME: Longterm canonical queries should deal with all placeholders
         // created inside of the query directly instead of returning them to the
@@ -331,7 +341,7 @@ where
                     // A variable from inside a binder of the query. While ideally these shouldn't
                     // exist at all (see the FIXME at the start of this method), we have to deal with
                     // them for now.
-                    delegate.instantiate_canonical_var_with_infer(info, |idx| {
+                    delegate.instantiate_canonical_var_with_infer(info, span, |idx| {
                         ty::UniverseIndex::from(prev_universe.index() + idx.index())
                     })
                 } else if info.is_existential() {
@@ -345,7 +355,7 @@ where
                     if let Some(v) = opt_values[ty::BoundVar::from_usize(index)] {
                         v
                     } else {
-                        delegate.instantiate_canonical_var_with_infer(info, |_| prev_universe)
+                        delegate.instantiate_canonical_var_with_infer(info, span, |_| prev_universe)
                     }
                 } else {
                     // For placeholders which were already part of the input, we simply map this
@@ -376,12 +386,13 @@ where
         param_env: I::ParamEnv,
         original_values: &[I::GenericArg],
         var_values: CanonicalVarValues<I>,
+        span: I::Span,
     ) {
         assert_eq!(original_values.len(), var_values.len());
 
         for (&orig, response) in iter::zip(original_values, var_values.var_values.iter()) {
             let goals =
-                delegate.eq_structurally_relating_aliases(param_env, orig, response).unwrap();
+                delegate.eq_structurally_relating_aliases(param_env, orig, response, span).unwrap();
             assert!(goals.is_empty());
         }
     }
@@ -401,7 +412,7 @@ where
 
     fn register_new_opaque_types(&mut self, opaque_types: &[(ty::OpaqueTypeKey<I>, I::Ty)]) {
         for &(key, ty) in opaque_types {
-            self.delegate.inject_new_hidden_type_unchecked(key, ty);
+            self.delegate.inject_new_hidden_type_unchecked(key, ty, self.origin_span);
         }
     }
 }
@@ -431,7 +442,7 @@ where
 // `rustc_trait_selection::solve::inspect::analyse`.
 pub fn instantiate_canonical_state<D, I, T: TypeFoldable<I>>(
     delegate: &D,
-    span: D::Span,
+    span: I::Span,
     param_env: I::ParamEnv,
     orig_values: &mut Vec<I::GenericArg>,
     state: inspect::CanonicalState<I, T>,
@@ -451,10 +462,10 @@ where
     }
 
     let instantiation =
-        EvalCtxt::compute_query_response_instantiation_values(delegate, orig_values, &state);
+        EvalCtxt::compute_query_response_instantiation_values(delegate, orig_values, &state, span);
 
     let inspect::State { var_values, data } = delegate.instantiate_canonical(state, instantiation);
 
-    EvalCtxt::unify_query_var_values(delegate, param_env, orig_values, var_values);
+    EvalCtxt::unify_query_var_values(delegate, param_env, orig_values, var_values, span);
     data
 }
diff --git a/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/mod.rs b/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/mod.rs
index 91ad24bff67..48a05488148 100644
--- a/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/mod.rs
+++ b/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/mod.rs
@@ -78,6 +78,8 @@ where
 
     nested_goals: NestedGoals<I>,
 
+    pub(super) origin_span: I::Span,
+
     // Has this `EvalCtxt` errored out with `NoSolution` in `try_evaluate_added_goals`?
     //
     // If so, then it can no longer be used to make a canonical query response,
@@ -134,6 +136,7 @@ pub trait SolverDelegateEvalExt: SolverDelegate {
         &self,
         goal: Goal<Self::Interner, <Self::Interner as Interner>::Predicate>,
         generate_proof_tree: GenerateProofTree,
+        span: <Self::Interner as Interner>::Span,
     ) -> (
         Result<(HasChanged, Certainty), NoSolution>,
         Option<inspect::GoalEvaluation<Self::Interner>>,
@@ -174,8 +177,9 @@ where
         &self,
         goal: Goal<I, I::Predicate>,
         generate_proof_tree: GenerateProofTree,
+        span: I::Span,
     ) -> (Result<(HasChanged, Certainty), NoSolution>, Option<inspect::GoalEvaluation<I>>) {
-        EvalCtxt::enter_root(self, self.cx().recursion_limit(), generate_proof_tree, |ecx| {
+        EvalCtxt::enter_root(self, self.cx().recursion_limit(), generate_proof_tree, span, |ecx| {
             ecx.evaluate_goal(GoalEvaluationKind::Root, GoalSource::Misc, goal)
         })
     }
@@ -186,7 +190,7 @@ where
         goal: Goal<Self::Interner, <Self::Interner as Interner>::Predicate>,
     ) -> bool {
         self.probe(|| {
-            EvalCtxt::enter_root(self, root_depth, GenerateProofTree::No, |ecx| {
+            EvalCtxt::enter_root(self, root_depth, GenerateProofTree::No, I::Span::dummy(), |ecx| {
                 ecx.evaluate_goal(GoalEvaluationKind::Root, GoalSource::Misc, goal)
             })
             .0
@@ -203,9 +207,13 @@ where
         Result<(NestedNormalizationGoals<I>, HasChanged, Certainty), NoSolution>,
         Option<inspect::GoalEvaluation<I>>,
     ) {
-        EvalCtxt::enter_root(self, self.cx().recursion_limit(), generate_proof_tree, |ecx| {
-            ecx.evaluate_goal_raw(GoalEvaluationKind::Root, GoalSource::Misc, goal)
-        })
+        EvalCtxt::enter_root(
+            self,
+            self.cx().recursion_limit(),
+            generate_proof_tree,
+            I::Span::dummy(),
+            |ecx| ecx.evaluate_goal_raw(GoalEvaluationKind::Root, GoalSource::Misc, goal),
+        )
     }
 }
 
@@ -229,6 +237,7 @@ where
         delegate: &D,
         root_depth: usize,
         generate_proof_tree: GenerateProofTree,
+        origin_span: I::Span,
         f: impl FnOnce(&mut EvalCtxt<'_, D>) -> R,
     ) -> (R, Option<inspect::GoalEvaluation<I>>) {
         let mut search_graph = SearchGraph::new(root_depth);
@@ -248,6 +257,7 @@ where
             variables: Default::default(),
             var_values: CanonicalVarValues::dummy(),
             is_normalizes_to_goal: false,
+            origin_span,
             tainted: Ok(()),
         };
         let result = f(&mut ecx);
@@ -289,12 +299,13 @@ where
             max_input_universe: canonical_input.canonical.max_universe,
             search_graph,
             nested_goals: NestedGoals::new(),
+            origin_span: I::Span::dummy(),
             tainted: Ok(()),
             inspect: canonical_goal_evaluation.new_goal_evaluation_step(var_values),
         };
 
         for &(key, ty) in &input.predefined_opaques_in_body.opaque_types {
-            ecx.delegate.inject_new_hidden_type_unchecked(key, ty);
+            ecx.delegate.inject_new_hidden_type_unchecked(key, ty, ecx.origin_span);
         }
 
         if !ecx.nested_goals.is_empty() {
@@ -822,8 +833,12 @@ where
             let identity_args = self.fresh_args_for_item(alias.def_id);
             let rigid_ctor = ty::AliasTerm::new_from_args(cx, alias.def_id, identity_args);
             let ctor_term = rigid_ctor.to_term(cx);
-            let obligations =
-                self.delegate.eq_structurally_relating_aliases(param_env, term, ctor_term)?;
+            let obligations = self.delegate.eq_structurally_relating_aliases(
+                param_env,
+                term,
+                ctor_term,
+                self.origin_span,
+            )?;
             debug_assert!(obligations.is_empty());
             self.relate(param_env, alias, variance, rigid_ctor)
         } else {
@@ -841,7 +856,12 @@ where
         lhs: T,
         rhs: T,
     ) -> Result<(), NoSolution> {
-        let result = self.delegate.eq_structurally_relating_aliases(param_env, lhs, rhs)?;
+        let result = self.delegate.eq_structurally_relating_aliases(
+            param_env,
+            lhs,
+            rhs,
+            self.origin_span,
+        )?;
         assert_eq!(result, vec![]);
         Ok(())
     }
@@ -864,7 +884,7 @@ where
         variance: ty::Variance,
         rhs: T,
     ) -> Result<(), NoSolution> {
-        let goals = self.delegate.relate(param_env, lhs, variance, rhs)?;
+        let goals = self.delegate.relate(param_env, lhs, variance, rhs, self.origin_span)?;
         self.add_goals(GoalSource::Misc, goals);
         Ok(())
     }
@@ -881,7 +901,7 @@ where
         lhs: T,
         rhs: T,
     ) -> Result<Vec<Goal<I, I::Predicate>>, NoSolution> {
-        Ok(self.delegate.relate(param_env, lhs, ty::Variance::Invariant, rhs)?)
+        Ok(self.delegate.relate(param_env, lhs, ty::Variance::Invariant, rhs, self.origin_span)?)
     }
 
     pub(super) fn instantiate_binder_with_infer<T: TypeFoldable<I> + Copy>(
@@ -917,12 +937,12 @@ where
     }
 
     pub(super) fn register_ty_outlives(&self, ty: I::Ty, lt: I::Region) {
-        self.delegate.register_ty_outlives(ty, lt);
+        self.delegate.register_ty_outlives(ty, lt, self.origin_span);
     }
 
     pub(super) fn register_region_outlives(&self, a: I::Region, b: I::Region) {
         // `b : a` ==> `a <= b`
-        self.delegate.sub_regions(b, a);
+        self.delegate.sub_regions(b, a, self.origin_span);
     }
 
     /// Computes the list of goals required for `arg` to be well-formed
diff --git a/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/probe.rs b/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/probe.rs
index be69a6e84ea..add96a1fdf7 100644
--- a/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/probe.rs
+++ b/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/probe.rs
@@ -39,6 +39,7 @@ where
             max_input_universe,
             search_graph: outer_ecx.search_graph,
             nested_goals: outer_ecx.nested_goals.clone(),
+            origin_span: outer_ecx.origin_span,
             tainted: outer_ecx.tainted,
             inspect: outer_ecx.inspect.take_and_enter_probe(),
         };
diff --git a/compiler/rustc_smir/src/rustc_internal/internal.rs b/compiler/rustc_smir/src/rustc_internal/internal.rs
index 3bc896dd7ef..50cf605ba2a 100644
--- a/compiler/rustc_smir/src/rustc_internal/internal.rs
+++ b/compiler/rustc_smir/src/rustc_internal/internal.rs
@@ -10,7 +10,7 @@ use rustc_span::Symbol;
 use stable_mir::abi::Layout;
 use stable_mir::mir::alloc::AllocId;
 use stable_mir::mir::mono::{Instance, MonoItem, StaticDef};
-use stable_mir::mir::{BinOp, Mutability, Place, ProjectionElem, Safety, UnOp};
+use stable_mir::mir::{BinOp, Mutability, Place, ProjectionElem, RawPtrKind, Safety, UnOp};
 use stable_mir::ty::{
     Abi, AdtDef, Binder, BoundRegionKind, BoundTyKind, BoundVariableKind, ClosureKind, DynKind,
     ExistentialPredicate, ExistentialProjection, ExistentialTraitRef, FloatTy, FnSig,
@@ -226,6 +226,18 @@ impl RustcInternal for Movability {
     }
 }
 
+impl RustcInternal for RawPtrKind {
+    type T<'tcx> = rustc_middle::mir::RawPtrKind;
+
+    fn internal<'tcx>(&self, _tables: &mut Tables<'_>, _tcx: TyCtxt<'tcx>) -> Self::T<'tcx> {
+        match self {
+            RawPtrKind::Mut => rustc_middle::mir::RawPtrKind::Mut,
+            RawPtrKind::Const => rustc_middle::mir::RawPtrKind::Const,
+            RawPtrKind::FakeForPtrMetadata => rustc_middle::mir::RawPtrKind::FakeForPtrMetadata,
+        }
+    }
+}
+
 impl RustcInternal for FnSig {
     type T<'tcx> = rustc_ty::FnSig<'tcx>;
 
diff --git a/compiler/rustc_target/src/callconv/nvptx64.rs b/compiler/rustc_target/src/callconv/nvptx64.rs
index 2e8b16d3a93..c64164372a1 100644
--- a/compiler/rustc_target/src/callconv/nvptx64.rs
+++ b/compiler/rustc_target/src/callconv/nvptx64.rs
@@ -1,5 +1,5 @@
 use super::{ArgAttribute, ArgAttributes, ArgExtension, CastTarget};
-use crate::abi::call::{ArgAbi, FnAbi, PassMode, Reg, Size, Uniform};
+use crate::abi::call::{ArgAbi, FnAbi, Reg, Size, Uniform};
 use crate::abi::{HasDataLayout, TyAbiInterface};
 
 fn classify_ret<Ty>(ret: &mut ArgAbi<'_, Ty>) {
@@ -53,21 +53,37 @@ where
     Ty: TyAbiInterface<'a, C> + Copy,
     C: HasDataLayout,
 {
-    if matches!(arg.mode, PassMode::Pair(..)) && (arg.layout.is_adt() || arg.layout.is_tuple()) {
-        let align_bytes = arg.layout.align.abi.bytes();
+    match arg.mode {
+        super::PassMode::Ignore | super::PassMode::Direct(_) => return,
+        super::PassMode::Pair(_, _) => {}
+        super::PassMode::Cast { .. } => unreachable!(),
+        super::PassMode::Indirect { .. } => {}
+    }
+
+    // FIXME only allow structs and wide pointers here
+    // panic!(
+    //     "`extern \"ptx-kernel\"` doesn't allow passing types other than primitives and structs"
+    // );
+
+    let align_bytes = arg.layout.align.abi.bytes();
 
-        let unit = match align_bytes {
-            1 => Reg::i8(),
-            2 => Reg::i16(),
-            4 => Reg::i32(),
-            8 => Reg::i64(),
-            16 => Reg::i128(),
-            _ => unreachable!("Align is given as power of 2 no larger than 16 bytes"),
-        };
-        arg.cast_to(Uniform::new(unit, Size::from_bytes(2 * align_bytes)));
+    let unit = match align_bytes {
+        1 => Reg::i8(),
+        2 => Reg::i16(),
+        4 => Reg::i32(),
+        8 => Reg::i64(),
+        16 => Reg::i128(),
+        _ => unreachable!("Align is given as power of 2 no larger than 16 bytes"),
+    };
+    if arg.layout.size.bytes() / align_bytes == 1 {
+        // Make sure we pass the struct as array at the LLVM IR level and not as a single integer.
+        arg.cast_to(CastTarget {
+            prefix: [Some(unit), None, None, None, None, None, None, None],
+            rest: Uniform::new(unit, Size::ZERO),
+            attrs: ArgAttributes::new(),
+        });
     } else {
-        // FIXME: find a better way to do this. See https://github.com/rust-lang/rust/issues/117271.
-        arg.make_direct_deprecated();
+        arg.cast_to(Uniform::new(unit, arg.layout.size));
     }
 }
 
diff --git a/compiler/rustc_trait_selection/src/solve/delegate.rs b/compiler/rustc_trait_selection/src/solve/delegate.rs
index abb79493432..58d8a3a6254 100644
--- a/compiler/rustc_trait_selection/src/solve/delegate.rs
+++ b/compiler/rustc_trait_selection/src/solve/delegate.rs
@@ -43,8 +43,6 @@ impl<'tcx> rustc_next_trait_solver::delegate::SolverDelegate for SolverDelegate<
         self.0.tcx
     }
 
-    type Span = Span;
-
     fn build_with_canonical<V>(
         interner: TyCtxt<'tcx>,
         canonical: &CanonicalQueryInput<'tcx, V>,
@@ -147,9 +145,10 @@ impl<'tcx> rustc_next_trait_solver::delegate::SolverDelegate for SolverDelegate<
     fn instantiate_canonical_var_with_infer(
         &self,
         cv_info: CanonicalVarInfo<'tcx>,
+        span: Span,
         universe_map: impl Fn(ty::UniverseIndex) -> ty::UniverseIndex,
     ) -> ty::GenericArg<'tcx> {
-        self.0.instantiate_canonical_var(DUMMY_SP, cv_info, universe_map)
+        self.0.instantiate_canonical_var(span, cv_info, universe_map)
     }
 
     fn insert_hidden_type(
@@ -175,11 +174,13 @@ impl<'tcx> rustc_next_trait_solver::delegate::SolverDelegate for SolverDelegate<
         self.0.add_item_bounds_for_hidden_type(def_id, args, param_env, hidden_ty, goals);
     }
 
-    fn inject_new_hidden_type_unchecked(&self, key: ty::OpaqueTypeKey<'tcx>, hidden_ty: Ty<'tcx>) {
-        self.0.inject_new_hidden_type_unchecked(key, ty::OpaqueHiddenType {
-            ty: hidden_ty,
-            span: DUMMY_SP,
-        })
+    fn inject_new_hidden_type_unchecked(
+        &self,
+        key: ty::OpaqueTypeKey<'tcx>,
+        hidden_ty: Ty<'tcx>,
+        span: Span,
+    ) {
+        self.0.inject_new_hidden_type_unchecked(key, ty::OpaqueHiddenType { ty: hidden_ty, span })
     }
 
     fn reset_opaque_types(&self) {
diff --git a/compiler/rustc_trait_selection/src/solve/fulfill.rs b/compiler/rustc_trait_selection/src/solve/fulfill.rs
index 0db44eda847..c238e708ab8 100644
--- a/compiler/rustc_trait_selection/src/solve/fulfill.rs
+++ b/compiler/rustc_trait_selection/src/solve/fulfill.rs
@@ -82,7 +82,7 @@ impl<'tcx> ObligationStorage<'tcx> {
             self.overflowed.extend(ExtractIf::new(&mut self.pending, |o| {
                 let goal = o.clone().into();
                 let result = <&SolverDelegate<'tcx>>::from(infcx)
-                    .evaluate_root_goal(goal, GenerateProofTree::No)
+                    .evaluate_root_goal(goal, GenerateProofTree::No, o.cause.span)
                     .0;
                 matches!(result, Ok((HasChanged::Yes, _)))
             }));
@@ -163,7 +163,7 @@ where
             for obligation in self.obligations.unstalled_for_select() {
                 let goal = obligation.clone().into();
                 let result = <&SolverDelegate<'tcx>>::from(infcx)
-                    .evaluate_root_goal(goal, GenerateProofTree::No)
+                    .evaluate_root_goal(goal, GenerateProofTree::No, obligation.cause.span)
                     .0;
                 self.inspect_evaluated_obligation(infcx, &obligation, &result);
                 let (changed, certainty) = match result {
diff --git a/compiler/rustc_trait_selection/src/solve/fulfill/derive_errors.rs b/compiler/rustc_trait_selection/src/solve/fulfill/derive_errors.rs
index c64bc19835b..8edd623e5d0 100644
--- a/compiler/rustc_trait_selection/src/solve/fulfill/derive_errors.rs
+++ b/compiler/rustc_trait_selection/src/solve/fulfill/derive_errors.rs
@@ -88,7 +88,11 @@ pub(super) fn fulfillment_error_for_stalled<'tcx>(
 ) -> FulfillmentError<'tcx> {
     let (code, refine_obligation) = infcx.probe(|_| {
         match <&SolverDelegate<'tcx>>::from(infcx)
-            .evaluate_root_goal(root_obligation.clone().into(), GenerateProofTree::No)
+            .evaluate_root_goal(
+                root_obligation.clone().into(),
+                GenerateProofTree::No,
+                root_obligation.cause.span,
+            )
             .0
         {
             Ok((_, Certainty::Maybe(MaybeCause::Ambiguity))) => {
diff --git a/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs b/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs
index 9ba48cd588f..9f4ee54bd4c 100644
--- a/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs
+++ b/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs
@@ -238,7 +238,7 @@ impl<'a, 'tcx> InspectCandidate<'a, 'tcx> {
                 // constraints, we get an ICE if we already applied the constraints
                 // from the chosen candidate.
                 let proof_tree = infcx
-                    .probe(|_| infcx.evaluate_root_goal(goal, GenerateProofTree::Yes).1)
+                    .probe(|_| infcx.evaluate_root_goal(goal, GenerateProofTree::Yes, span).1)
                     .unwrap();
                 InspectGoal::new(infcx, self.goal.depth + 1, proof_tree, None, source)
             }
@@ -440,8 +440,11 @@ impl<'tcx> InferCtxt<'tcx> {
         depth: usize,
         visitor: &mut V,
     ) -> V::Result {
-        let (_, proof_tree) =
-            <&SolverDelegate<'tcx>>::from(self).evaluate_root_goal(goal, GenerateProofTree::Yes);
+        let (_, proof_tree) = <&SolverDelegate<'tcx>>::from(self).evaluate_root_goal(
+            goal,
+            GenerateProofTree::Yes,
+            visitor.span(),
+        );
         let proof_tree = proof_tree.unwrap();
         visitor.visit_goal(&InspectGoal::new(self, depth, proof_tree, None, GoalSource::Misc))
     }
diff --git a/compiler/rustc_ty_utils/src/abi.rs b/compiler/rustc_ty_utils/src/abi.rs
index c528179ae0e..169f3a78c26 100644
--- a/compiler/rustc_ty_utils/src/abi.rs
+++ b/compiler/rustc_ty_utils/src/abi.rs
@@ -489,21 +489,16 @@ fn fn_abi_sanity_check<'tcx>(
                         // have to allow it -- but we absolutely shouldn't let any more targets do
                         // that. (Also see <https://github.com/rust-lang/rust/issues/115666>.)
                         //
-                        // The unstable abi `PtxKernel` also uses Direct for now.
-                        // It needs to switch to something else before stabilization can happen.
-                        // (See issue: https://github.com/rust-lang/rust/issues/117271)
-                        //
-                        // And finally the unadjusted ABI is ill specified and uses Direct for all
-                        // args, but unfortunately we need it for calling certain LLVM intrinsics.
+                        // The unadjusted ABI also uses Direct for all args and is ill-specified,
+                        // but unfortunately we need it for calling certain LLVM intrinsics.
 
                         match spec_abi {
                             ExternAbi::Unadjusted => {}
-                            ExternAbi::PtxKernel => {}
                             ExternAbi::C { unwind: _ }
                                 if matches!(&*tcx.sess.target.arch, "wasm32" | "wasm64") => {}
                             _ => {
                                 panic!(
-                                    "`PassMode::Direct` for aggregates only allowed for \"unadjusted\" and \"ptx-kernel\" functions and on wasm\n\
+                                    "`PassMode::Direct` for aggregates only allowed for \"unadjusted\" functions and on wasm\n\
                                       Problematic type: {:#?}",
                                     arg.layout,
                                 );
diff --git a/compiler/rustc_type_ir/src/infer_ctxt.rs b/compiler/rustc_type_ir/src/infer_ctxt.rs
index a892b88c2c6..c9b636132f8 100644
--- a/compiler/rustc_type_ir/src/infer_ctxt.rs
+++ b/compiler/rustc_type_ir/src/infer_ctxt.rs
@@ -201,17 +201,20 @@ pub trait InferCtxtLike: Sized {
         &self,
         sub: <Self::Interner as Interner>::Region,
         sup: <Self::Interner as Interner>::Region,
+        span: <Self::Interner as Interner>::Span,
     );
 
     fn equate_regions(
         &self,
         a: <Self::Interner as Interner>::Region,
         b: <Self::Interner as Interner>::Region,
+        span: <Self::Interner as Interner>::Span,
     );
 
     fn register_ty_outlives(
         &self,
         ty: <Self::Interner as Interner>::Ty,
         r: <Self::Interner as Interner>::Region,
+        span: <Self::Interner as Interner>::Span,
     );
 }
diff --git a/compiler/rustc_type_ir/src/macros.rs b/compiler/rustc_type_ir/src/macros.rs
index aae5aeb5fb3..fab1a11304d 100644
--- a/compiler/rustc_type_ir/src/macros.rs
+++ b/compiler/rustc_type_ir/src/macros.rs
@@ -47,23 +47,16 @@ TrivialTypeTraversalImpls! {
     u16,
     u32,
     u64,
-    String,
+    // tidy-alphabetical-start
     crate::AliasRelationDirection,
-    crate::AliasTyKind,
     crate::BoundConstness,
     crate::DebruijnIndex,
-    crate::FloatTy,
-    crate::InferTy,
-    crate::IntVarValue,
     crate::PredicatePolarity,
-    crate::RegionVid,
     crate::solve::BuiltinImplSource,
     crate::solve::Certainty,
     crate::solve::GoalSource,
-    crate::solve::MaybeCause,
-    crate::solve::NoSolution,
     crate::UniverseIndex,
     crate::Variance,
-    rustc_ast_ir::Movability,
     rustc_ast_ir::Mutability,
+    // tidy-alphabetical-end
 }
diff --git a/compiler/rustc_type_ir/src/relate/solver_relating.rs b/compiler/rustc_type_ir/src/relate/solver_relating.rs
index ad10ad5af9c..dc2312b2da3 100644
--- a/compiler/rustc_type_ir/src/relate/solver_relating.rs
+++ b/compiler/rustc_type_ir/src/relate/solver_relating.rs
@@ -13,6 +13,7 @@ pub trait RelateExt: InferCtxtLike {
         lhs: T,
         variance: ty::Variance,
         rhs: T,
+        span: <Self::Interner as Interner>::Span,
     ) -> Result<
         Vec<Goal<Self::Interner, <Self::Interner as Interner>::Predicate>>,
         TypeError<Self::Interner>,
@@ -23,6 +24,7 @@ pub trait RelateExt: InferCtxtLike {
         param_env: <Self::Interner as Interner>::ParamEnv,
         lhs: T,
         rhs: T,
+        span: <Self::Interner as Interner>::Span,
     ) -> Result<
         Vec<Goal<Self::Interner, <Self::Interner as Interner>::Predicate>>,
         TypeError<Self::Interner>,
@@ -36,12 +38,13 @@ impl<Infcx: InferCtxtLike> RelateExt for Infcx {
         lhs: T,
         variance: ty::Variance,
         rhs: T,
+        span: <Self::Interner as Interner>::Span,
     ) -> Result<
         Vec<Goal<Self::Interner, <Self::Interner as Interner>::Predicate>>,
         TypeError<Self::Interner>,
     > {
         let mut relate =
-            SolverRelating::new(self, StructurallyRelateAliases::No, variance, param_env);
+            SolverRelating::new(self, StructurallyRelateAliases::No, variance, param_env, span);
         relate.relate(lhs, rhs)?;
         Ok(relate.goals)
     }
@@ -51,12 +54,18 @@ impl<Infcx: InferCtxtLike> RelateExt for Infcx {
         param_env: <Self::Interner as Interner>::ParamEnv,
         lhs: T,
         rhs: T,
+        span: <Self::Interner as Interner>::Span,
     ) -> Result<
         Vec<Goal<Self::Interner, <Self::Interner as Interner>::Predicate>>,
         TypeError<Self::Interner>,
     > {
-        let mut relate =
-            SolverRelating::new(self, StructurallyRelateAliases::Yes, ty::Invariant, param_env);
+        let mut relate = SolverRelating::new(
+            self,
+            StructurallyRelateAliases::Yes,
+            ty::Invariant,
+            param_env,
+            span,
+        );
         relate.relate(lhs, rhs)?;
         Ok(relate.goals)
     }
@@ -68,6 +77,7 @@ pub struct SolverRelating<'infcx, Infcx, I: Interner> {
     // Immutable fields.
     structurally_relate_aliases: StructurallyRelateAliases,
     param_env: I::ParamEnv,
+    span: I::Span,
     // Mutable fields.
     ambient_variance: ty::Variance,
     goals: Vec<Goal<I, I::Predicate>>,
@@ -106,10 +116,12 @@ where
         structurally_relate_aliases: StructurallyRelateAliases,
         ambient_variance: ty::Variance,
         param_env: I::ParamEnv,
+        span: I::Span,
     ) -> Self {
         SolverRelating {
             infcx,
             structurally_relate_aliases,
+            span,
             ambient_variance,
             param_env,
             goals: vec![],
@@ -241,10 +253,10 @@ where
     fn regions(&mut self, a: I::Region, b: I::Region) -> RelateResult<I, I::Region> {
         match self.ambient_variance {
             // Subtype(&'a u8, &'b u8) => Outlives('a: 'b) => SubRegion('b, 'a)
-            ty::Covariant => self.infcx.sub_regions(b, a),
+            ty::Covariant => self.infcx.sub_regions(b, a, self.span),
             // Suptype(&'a u8, &'b u8) => Outlives('b: 'a) => SubRegion('a, 'b)
-            ty::Contravariant => self.infcx.sub_regions(a, b),
-            ty::Invariant => self.infcx.equate_regions(a, b),
+            ty::Contravariant => self.infcx.sub_regions(a, b, self.span),
+            ty::Invariant => self.infcx.equate_regions(a, b, self.span),
             ty::Bivariant => {
                 unreachable!("Expected bivariance to be handled in relate_with_variance")
             }
diff --git a/library/core/src/iter/sources/from_fn.rs b/library/core/src/iter/sources/from_fn.rs
index 75cc0ffe3c7..1c7e1b30a2f 100644
--- a/library/core/src/iter/sources/from_fn.rs
+++ b/library/core/src/iter/sources/from_fn.rs
@@ -1,7 +1,7 @@
 use crate::fmt;
 
 /// Creates an iterator with the provided closure
-/// `F: FnMut() -> Option<T>` as its `[next](Iterator::next)` method.
+/// `F: FnMut() -> Option<T>` as its [`next`](Iterator::next) method.
 ///
 /// The iterator will yield the `T`s returned from the closure.
 ///
diff --git a/library/panic_unwind/src/hermit.rs b/library/panic_unwind/src/hermit.rs
index 8ac827dd9cc..7e08ad66577 100644
--- a/library/panic_unwind/src/hermit.rs
+++ b/library/panic_unwind/src/hermit.rs
@@ -7,14 +7,14 @@ use core::any::Any;
 
 pub(crate) unsafe fn cleanup(_ptr: *mut u8) -> Box<dyn Any + Send> {
     extern "C" {
-        pub fn __rust_abort() -> !;
+        fn __rust_abort() -> !;
     }
     __rust_abort();
 }
 
 pub(crate) unsafe fn panic(_data: Box<dyn Any + Send>) -> u32 {
     extern "C" {
-        pub fn __rust_abort() -> !;
+        fn __rust_abort() -> !;
     }
     __rust_abort();
 }
diff --git a/src/ci/docker/host-x86_64/x86_64-gnu-tools/browser-ui-test.version b/src/ci/docker/host-x86_64/x86_64-gnu-tools/browser-ui-test.version
index 7211b157c69..a158e5b6253 100644
--- a/src/ci/docker/host-x86_64/x86_64-gnu-tools/browser-ui-test.version
+++ b/src/ci/docker/host-x86_64/x86_64-gnu-tools/browser-ui-test.version
@@ -1 +1 @@
-0.18.2
\ No newline at end of file
+0.20.2
\ No newline at end of file
diff --git a/src/doc/rustc/src/platform-support/apple-darwin.md b/src/doc/rustc/src/platform-support/apple-darwin.md
index 17ea225805b..dba2c4b2aaf 100644
--- a/src/doc/rustc/src/platform-support/apple-darwin.md
+++ b/src/doc/rustc/src/platform-support/apple-darwin.md
@@ -30,6 +30,18 @@ The current default deployment target for `rustc` can be retrieved with
 [deployment target]: https://developer.apple.com/library/archive/documentation/DeveloperTools/Conceptual/cross_development/Configuring/configuring.html
 [rustc-print]: ../command-line-arguments.md#option-print
 
+### Host tooling
+
+The minimum supported OS versions for the host tooling (`rustc`, `cargo`,
+etc.) are currently the same as for applications, namely 10.12 on x86 and 11.0
+on ARM64.
+The minimum supported Xcode version is 9.2.
+
+Building from source likely requires that you can build LLVM from source too,
+which [currently][llvm-os] requires Xcode 10.0 and macOS 10.13 (for LLVM 19).
+
+[llvm-os]: https://releases.llvm.org/19.1.0/docs/GettingStarted.html#host-c-toolchain-both-compiler-and-standard-library
+
 ### Binary format
 
 The default binary format is Mach-O, the executable format used on Apple's
diff --git a/src/tools/rustdoc-gui/tester.js b/src/tools/rustdoc-gui/tester.js
index c5874b4ee02..ff87b76aa45 100644
--- a/src/tools/rustdoc-gui/tester.js
+++ b/src/tools/rustdoc-gui/tester.js
@@ -197,7 +197,6 @@ async function main(argv) {
         const args = [
             "--variable", "DOC_PATH", opts["doc_folder"].split("\\").join("/"),
             "--enable-fail-on-js-error", "--allow-file-access-from-files",
-            "--no-sandbox",
         ];
         if (opts["debug"]) {
             debug = true;
diff --git a/tests/assembly/nvptx-kernel-abi/nvptx-kernel-args-abi-v7.rs b/tests/assembly/nvptx-kernel-abi/nvptx-kernel-args-abi-v7.rs
index fb3a325a41f..b3bfc66a5a5 100644
--- a/tests/assembly/nvptx-kernel-abi/nvptx-kernel-args-abi-v7.rs
+++ b/tests/assembly/nvptx-kernel-abi/nvptx-kernel-args-abi-v7.rs
@@ -242,22 +242,6 @@ pub unsafe extern "ptx-kernel" fn f_float_array_arg(_a: [f32; 5]) {}
 //pub unsafe extern "ptx-kernel" fn f_u128_array_arg(_a: [u128; 5]) {}
 
 // CHECK: .visible .entry f_u32_slice_arg(
-// CHECK: .param .u64 f_u32_slice_arg_param_0
-// CHECK: .param .u64 f_u32_slice_arg_param_1
+// CHECK: .param .align 8 .b8 f_u32_slice_arg_param_0[16]
 #[no_mangle]
 pub unsafe extern "ptx-kernel" fn f_u32_slice_arg(_a: &[u32]) {}
-
-// CHECK: .visible .entry f_tuple_u8_u8_arg(
-// CHECK: .param .align 1 .b8 f_tuple_u8_u8_arg_param_0[2]
-#[no_mangle]
-pub unsafe extern "ptx-kernel" fn f_tuple_u8_u8_arg(_a: (u8, u8)) {}
-
-// CHECK: .visible .entry f_tuple_u32_u32_arg(
-// CHECK: .param .align 4 .b8 f_tuple_u32_u32_arg_param_0[8]
-#[no_mangle]
-pub unsafe extern "ptx-kernel" fn f_tuple_u32_u32_arg(_a: (u32, u32)) {}
-
-// CHECK: .visible .entry f_tuple_u8_u8_u32_arg(
-// CHECK: .param .align 4 .b8 f_tuple_u8_u8_u32_arg_param_0[8]
-#[no_mangle]
-pub unsafe extern "ptx-kernel" fn f_tuple_u8_u8_u32_arg(_a: (u8, u8, u32)) {}
diff --git a/tests/ui/argument-suggestions/basic.stderr b/tests/ui/argument-suggestions/basic.stderr
index 2d52df21233..83f0f630fe8 100644
--- a/tests/ui/argument-suggestions/basic.stderr
+++ b/tests/ui/argument-suggestions/basic.stderr
@@ -57,7 +57,7 @@ note: function defined here
   --> $DIR/basic.rs:16:4
    |
 LL | fn swapped(_i: u32, _s: &str) {}
-   |    ^^^^^^^ -------  --------
+   |    ^^^^^^^
 help: swap these arguments
    |
 LL |     swapped(1, "");
@@ -76,7 +76,7 @@ note: function defined here
   --> $DIR/basic.rs:17:4
    |
 LL | fn permuted(_x: X, _y: Y, _z: Z) {}
-   |    ^^^^^^^^ -----  -----  -----
+   |    ^^^^^^^^
 help: reorder these arguments
    |
 LL |     permuted(X {}, Y {}, Z {});
diff --git a/tests/ui/argument-suggestions/complex.stderr b/tests/ui/argument-suggestions/complex.stderr
index bb3817421df..20c7c2fd7a5 100644
--- a/tests/ui/argument-suggestions/complex.stderr
+++ b/tests/ui/argument-suggestions/complex.stderr
@@ -8,7 +8,7 @@ note: function defined here
   --> $DIR/complex.rs:11:4
    |
 LL | fn complex(_i: u32, _s: &str, _e: E, _f: F, _g: G, _x: X, _y: Y, _z: Z ) {}
-   |    ^^^^^^^ -------  --------  -----  -----  -----  -----  -----  -----
+   |    ^^^^^^^ -------            -----
 help: did you mean
    |
 LL |   complex(/* u32 */, &"", /* E */, F::X2, G{}, X {}, Y {}, Z {});
diff --git a/tests/ui/argument-suggestions/extra_arguments.stderr b/tests/ui/argument-suggestions/extra_arguments.stderr
index 8c95cc86a27..5ed42a9ddd2 100644
--- a/tests/ui/argument-suggestions/extra_arguments.stderr
+++ b/tests/ui/argument-suggestions/extra_arguments.stderr
@@ -44,7 +44,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:2:4
    |
 LL | fn one_arg<T>(_a: T) {}
-   |    ^^^^^^^    -----
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -   one_arg(1, 1);
@@ -61,7 +61,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:2:4
    |
 LL | fn one_arg<T>(_a: T) {}
-   |    ^^^^^^^    -----
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -   one_arg(1, "");
@@ -80,7 +80,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:2:4
    |
 LL | fn one_arg<T>(_a: T) {}
-   |    ^^^^^^^    -----
+   |    ^^^^^^^
 help: remove the extra arguments
    |
 LL -   one_arg(1, "", 1.0);
@@ -97,7 +97,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:3:4
    |
 LL | fn two_arg_same(_a: i32, _b: i32) {}
-   |    ^^^^^^^^^^^^ -------  -------
+   |    ^^^^^^^^^^^^
 help: remove the extra argument
    |
 LL -   two_arg_same(1, 1, 1);
@@ -114,7 +114,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:3:4
    |
 LL | fn two_arg_same(_a: i32, _b: i32) {}
-   |    ^^^^^^^^^^^^ -------  -------
+   |    ^^^^^^^^^^^^
 help: remove the extra argument
    |
 LL -   two_arg_same(1, 1, 1.0);
@@ -131,7 +131,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:4:4
    |
 LL | fn two_arg_diff(_a: i32, _b: &str) {}
-   |    ^^^^^^^^^^^^ -------  --------
+   |    ^^^^^^^^^^^^
 help: remove the extra argument
    |
 LL -   two_arg_diff(1, 1, "");
@@ -148,7 +148,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:4:4
    |
 LL | fn two_arg_diff(_a: i32, _b: &str) {}
-   |    ^^^^^^^^^^^^ -------  --------
+   |    ^^^^^^^^^^^^
 help: remove the extra argument
    |
 LL -   two_arg_diff(1, "", "");
@@ -167,7 +167,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:4:4
    |
 LL | fn two_arg_diff(_a: i32, _b: &str) {}
-   |    ^^^^^^^^^^^^ -------  --------
+   |    ^^^^^^^^^^^^
 help: remove the extra arguments
    |
 LL -   two_arg_diff(1, 1, "", "");
@@ -186,7 +186,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:4:4
    |
 LL | fn two_arg_diff(_a: i32, _b: &str) {}
-   |    ^^^^^^^^^^^^ -------  --------
+   |    ^^^^^^^^^^^^
 help: remove the extra arguments
    |
 LL -   two_arg_diff(1, "", 1, "");
@@ -203,7 +203,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:3:4
    |
 LL | fn two_arg_same(_a: i32, _b: i32) {}
-   |    ^^^^^^^^^^^^ -------  -------
+   |    ^^^^^^^^^^^^
 help: remove the extra argument
    |
 LL -   two_arg_same(1, 1,     "");
@@ -220,7 +220,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:4:4
    |
 LL | fn two_arg_diff(_a: i32, _b: &str) {}
-   |    ^^^^^^^^^^^^ -------  --------
+   |    ^^^^^^^^^^^^
 help: remove the extra argument
    |
 LL -   two_arg_diff(1, 1,     "");
@@ -240,7 +240,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:3:4
    |
 LL | fn two_arg_same(_a: i32, _b: i32) {}
-   |    ^^^^^^^^^^^^ -------  -------
+   |    ^^^^^^^^^^^^
 help: remove the extra argument
    |
 LL -     1,
@@ -261,7 +261,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:4:4
    |
 LL | fn two_arg_diff(_a: i32, _b: &str) {}
-   |    ^^^^^^^^^^^^ -------  --------
+   |    ^^^^^^^^^^^^
 help: remove the extra argument
    |
 LL -     1,
@@ -335,7 +335,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:2:4
    |
 LL | fn one_arg<T>(_a: T) {}
-   |    ^^^^^^^    -----
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -   one_arg(1, panic!());
@@ -352,7 +352,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:2:4
    |
 LL | fn one_arg<T>(_a: T) {}
-   |    ^^^^^^^    -----
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -   one_arg(panic!(), 1);
@@ -369,7 +369,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:2:4
    |
 LL | fn one_arg<T>(_a: T) {}
-   |    ^^^^^^^    -----
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -   one_arg(stringify!($e), 1);
@@ -386,7 +386,7 @@ note: function defined here
   --> $DIR/extra_arguments.rs:2:4
    |
 LL | fn one_arg<T>(_a: T) {}
-   |    ^^^^^^^    -----
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -   one_arg(for _ in 1.. {}, 1);
diff --git a/tests/ui/argument-suggestions/invalid_arguments.stderr b/tests/ui/argument-suggestions/invalid_arguments.stderr
index d26f33d098b..a50058149b8 100644
--- a/tests/ui/argument-suggestions/invalid_arguments.stderr
+++ b/tests/ui/argument-suggestions/invalid_arguments.stderr
@@ -150,7 +150,7 @@ note: function defined here
   --> $DIR/invalid_arguments.rs:8:4
    |
 LL | fn three_arg_diff(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^^^^^ -------  -------
 
 error[E0308]: arguments to this function are incorrect
   --> $DIR/invalid_arguments.rs:29:3
@@ -164,7 +164,7 @@ note: function defined here
   --> $DIR/invalid_arguments.rs:8:4
    |
 LL | fn three_arg_diff(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^^^^^ -------           --------
 
 error[E0308]: arguments to this function are incorrect
   --> $DIR/invalid_arguments.rs:30:3
@@ -178,7 +178,7 @@ note: function defined here
   --> $DIR/invalid_arguments.rs:8:4
    |
 LL | fn three_arg_diff(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^^^^^          -------  --------
 
 error[E0308]: arguments to this function are incorrect
   --> $DIR/invalid_arguments.rs:32:3
@@ -249,7 +249,7 @@ note: function defined here
   --> $DIR/invalid_arguments.rs:9:4
    |
 LL | fn three_arg_repeat(_a: i32, _b: i32, _c: &str) {}
-   |    ^^^^^^^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^^^^^^^ -------  -------
 
 error[E0308]: arguments to this function are incorrect
   --> $DIR/invalid_arguments.rs:39:3
@@ -263,7 +263,7 @@ note: function defined here
   --> $DIR/invalid_arguments.rs:9:4
    |
 LL | fn three_arg_repeat(_a: i32, _b: i32, _c: &str) {}
-   |    ^^^^^^^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^^^^^^^ -------           --------
 
 error[E0308]: arguments to this function are incorrect
   --> $DIR/invalid_arguments.rs:40:3
@@ -277,7 +277,7 @@ note: function defined here
   --> $DIR/invalid_arguments.rs:9:4
    |
 LL | fn three_arg_repeat(_a: i32, _b: i32, _c: &str) {}
-   |    ^^^^^^^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^^^^^^^          -------  --------
 
 error[E0308]: arguments to this function are incorrect
   --> $DIR/invalid_arguments.rs:42:3
diff --git a/tests/ui/argument-suggestions/issue-100478.stderr b/tests/ui/argument-suggestions/issue-100478.stderr
index 94709f0ebc6..6299571d998 100644
--- a/tests/ui/argument-suggestions/issue-100478.stderr
+++ b/tests/ui/argument-suggestions/issue-100478.stderr
@@ -11,7 +11,7 @@ note: function defined here
   --> $DIR/issue-100478.rs:30:4
    |
 LL | fn three_diff(_a: T1, _b: T2, _c: T3) {}
-   |    ^^^^^^^^^^ ------  ------  ------
+   |    ^^^^^^^^^^ ------          ------
 help: provide the arguments
    |
 LL |     three_diff(/* T1 */, T2::new(0), /* T3 */);
@@ -31,7 +31,7 @@ note: function defined here
   --> $DIR/issue-100478.rs:31:4
    |
 LL | fn four_shuffle(_a: T1, _b: T2, _c: T3, _d: T4) {}
-   |    ^^^^^^^^^^^^ ------  ------  ------  ------
+   |    ^^^^^^^^^^^^
 help: did you mean
    |
 LL |     four_shuffle(T1::default(), T2::default(), T3::default(), T4::default());
@@ -50,7 +50,7 @@ note: function defined here
   --> $DIR/issue-100478.rs:31:4
    |
 LL | fn four_shuffle(_a: T1, _b: T2, _c: T3, _d: T4) {}
-   |    ^^^^^^^^^^^^ ------  ------  ------  ------
+   |    ^^^^^^^^^^^^                         ------
 help: swap these arguments
    |
 LL |     four_shuffle(T1::default(), T2::default(), T3::default(), /* T4 */);
@@ -69,7 +69,7 @@ note: function defined here
   --> $DIR/issue-100478.rs:29:4
    |
 LL | fn foo(p1: T1, p2: Arc<T2>, p3: T3, p4: Arc<T4>, p5: T5, p6: T6, p7: T7, p8: Arc<T8>) {}
-   |    ^^^ ------  -----------  ------  -----------  ------  ------  ------  -----------
+   |    ^^^         -----------
 help: provide the argument
    |
 LL |     foo(p1, /* Arc<T2> */, p3, p4, p5, p6, p7, p8);
diff --git a/tests/ui/argument-suggestions/issue-101097.stderr b/tests/ui/argument-suggestions/issue-101097.stderr
index 6e21f19ab4f..45aa2dba5d5 100644
--- a/tests/ui/argument-suggestions/issue-101097.stderr
+++ b/tests/ui/argument-suggestions/issue-101097.stderr
@@ -13,18 +13,6 @@ note: function defined here
    |
 LL | fn f(
    |    ^
-LL |     a1: A,
-   |     -----
-LL |     a2: A,
-   |     -----
-LL |     b1: B,
-   |     -----
-LL |     b2: B,
-   |     -----
-LL |     c1: C,
-   |     -----
-LL |     c2: C,
-   |     -----
 help: did you mean
    |
 LL |     f(A, A, B, B, C, C);
@@ -41,18 +29,6 @@ note: function defined here
    |
 LL | fn f(
    |    ^
-LL |     a1: A,
-   |     -----
-LL |     a2: A,
-   |     -----
-LL |     b1: B,
-   |     -----
-LL |     b2: B,
-   |     -----
-LL |     c1: C,
-   |     -----
-LL |     c2: C,
-   |     -----
 help: did you mean
    |
 LL |     f(A, A, B, B, C, C);
@@ -72,14 +48,7 @@ note: function defined here
    |
 LL | fn f(
    |    ^
-LL |     a1: A,
-   |     -----
-LL |     a2: A,
-   |     -----
-LL |     b1: B,
-   |     -----
-LL |     b2: B,
-   |     -----
+...
 LL |     c1: C,
    |     -----
 LL |     c2: C,
@@ -104,18 +73,6 @@ note: function defined here
    |
 LL | fn f(
    |    ^
-LL |     a1: A,
-   |     -----
-LL |     a2: A,
-   |     -----
-LL |     b1: B,
-   |     -----
-LL |     b2: B,
-   |     -----
-LL |     c1: C,
-   |     -----
-LL |     c2: C,
-   |     -----
 help: did you mean
    |
 LL |     f(A, A, B, B, C, C);
@@ -137,18 +94,9 @@ note: function defined here
    |
 LL | fn f(
    |    ^
-LL |     a1: A,
-   |     -----
-LL |     a2: A,
-   |     -----
+...
 LL |     b1: B,
    |     -----
-LL |     b2: B,
-   |     -----
-LL |     c1: C,
-   |     -----
-LL |     c2: C,
-   |     -----
 help: did you mean
    |
 LL |     f(A, A, /* B */, B, C, C);
diff --git a/tests/ui/argument-suggestions/issue-109425.stderr b/tests/ui/argument-suggestions/issue-109425.stderr
index 2cd53ed528e..232dc0183c8 100644
--- a/tests/ui/argument-suggestions/issue-109425.stderr
+++ b/tests/ui/argument-suggestions/issue-109425.stderr
@@ -29,7 +29,7 @@ note: function defined here
   --> $DIR/issue-109425.rs:4:4
    |
 LL | fn i(_: u32) {}
-   |    ^ ------
+   |    ^
 help: remove the extra arguments
    |
 LL -     i(0, 1, 2,);     // i(0,)
@@ -48,7 +48,7 @@ note: function defined here
   --> $DIR/issue-109425.rs:4:4
    |
 LL | fn i(_: u32) {}
-   |    ^ ------
+   |    ^
 help: remove the extra arguments
    |
 LL -     i(0, 1, 2);      // i(0)
@@ -67,7 +67,7 @@ note: function defined here
   --> $DIR/issue-109425.rs:5:4
    |
 LL | fn is(_: u32, _: &str) {}
-   |    ^^ ------  -------
+   |    ^^
 help: remove the extra arguments
    |
 LL -     is(0, 1, 2, ""); // is(0, "")
@@ -86,7 +86,7 @@ note: function defined here
   --> $DIR/issue-109425.rs:5:4
    |
 LL | fn is(_: u32, _: &str) {}
-   |    ^^ ------  -------
+   |    ^^
 help: remove the extra arguments
    |
 LL -     is((), 1, "", ());
@@ -105,7 +105,7 @@ note: function defined here
   --> $DIR/issue-109425.rs:5:4
    |
 LL | fn is(_: u32, _: &str) {}
-   |    ^^ ------  -------
+   |    ^^
 help: remove the extra arguments
    |
 LL -     is(1, (), "", ());
@@ -124,7 +124,7 @@ note: function defined here
   --> $DIR/issue-109425.rs:6:4
    |
 LL | fn s(_: &str) {}
-   |    ^ -------
+   |    ^
 help: remove the extra arguments
    |
 LL -     s(0, 1, "");     // s("")
diff --git a/tests/ui/argument-suggestions/issue-109831.stderr b/tests/ui/argument-suggestions/issue-109831.stderr
index 12be0887121..cee87223866 100644
--- a/tests/ui/argument-suggestions/issue-109831.stderr
+++ b/tests/ui/argument-suggestions/issue-109831.stderr
@@ -38,7 +38,7 @@ note: function defined here
   --> $DIR/issue-109831.rs:4:4
    |
 LL | fn f(b1: B, b2: B, a2: C) {}
-   |    ^ -----  -----  -----
+   |    ^ -----  -----
 help: remove the extra argument
    |
 LL -     f(A, A, B, C);
diff --git a/tests/ui/argument-suggestions/issue-96638.stderr b/tests/ui/argument-suggestions/issue-96638.stderr
index 6492acbad94..509b2a157de 100644
--- a/tests/ui/argument-suggestions/issue-96638.stderr
+++ b/tests/ui/argument-suggestions/issue-96638.stderr
@@ -10,7 +10,7 @@ note: function defined here
   --> $DIR/issue-96638.rs:1:4
    |
 LL | fn f(_: usize, _: &usize, _: usize) {}
-   |    ^ --------  ---------  --------
+   |    ^ --------             --------
 help: provide the argument
    |
 LL |     f(/* usize */, &x, /* usize */);
diff --git a/tests/ui/argument-suggestions/issue-97197.stderr b/tests/ui/argument-suggestions/issue-97197.stderr
index 3768367a5e6..1cf19fc1bc8 100644
--- a/tests/ui/argument-suggestions/issue-97197.stderr
+++ b/tests/ui/argument-suggestions/issue-97197.stderr
@@ -8,7 +8,7 @@ note: function defined here
   --> $DIR/issue-97197.rs:6:8
    |
 LL | pub fn g(a1: (), a2: bool, a3: bool, a4: bool, a5: bool, a6: ()) -> () {}
-   |        ^ ------  --------  --------  --------  --------  ------
+   |        ^         --------  --------  --------  --------
 help: provide the arguments
    |
 LL |     g((), /* bool */, /* bool */, /* bool */, /* bool */, ());
diff --git a/tests/ui/argument-suggestions/issue-97484.stderr b/tests/ui/argument-suggestions/issue-97484.stderr
index a7708f6e0d7..e09d1928f74 100644
--- a/tests/ui/argument-suggestions/issue-97484.stderr
+++ b/tests/ui/argument-suggestions/issue-97484.stderr
@@ -12,7 +12,7 @@ note: function defined here
   --> $DIR/issue-97484.rs:9:4
    |
 LL | fn foo(a: &A, d: D, e: &E, g: G) {}
-   |    ^^^ -----  ----  -----  ----
+   |    ^^^              -----
 help: consider borrowing here
    |
 LL |     foo(&&A, B, C, D, &E, F, G);
diff --git a/tests/ui/argument-suggestions/missing_arguments.stderr b/tests/ui/argument-suggestions/missing_arguments.stderr
index 3a27a51d032..fc219b9ce2c 100644
--- a/tests/ui/argument-suggestions/missing_arguments.stderr
+++ b/tests/ui/argument-suggestions/missing_arguments.stderr
@@ -40,7 +40,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:2:4
    |
 LL | fn two_same(_a: i32, _b: i32) {}
-   |    ^^^^^^^^ -------  -------
+   |    ^^^^^^^^          -------
 help: provide the argument
    |
 LL |   two_same(1, /* i32 */);
@@ -72,7 +72,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:3:4
    |
 LL | fn two_diff(_a: i32, _b: f32) {}
-   |    ^^^^^^^^ -------  -------
+   |    ^^^^^^^^          -------
 help: provide the argument
    |
 LL |   two_diff(1, /* f32 */);
@@ -88,7 +88,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:3:4
    |
 LL | fn two_diff(_a: i32, _b: f32) {}
-   |    ^^^^^^^^ -------  -------
+   |    ^^^^^^^^ -------
 help: provide the argument
    |
 LL |   two_diff(/* i32 */, 1.0);
@@ -120,7 +120,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:4:4
    |
 LL | fn three_same(_a: i32, _b: i32, _c: i32) {}
-   |    ^^^^^^^^^^ -------  -------  -------
+   |    ^^^^^^^^^^          -------  -------
 help: provide the arguments
    |
 LL |   three_same(1, /* i32 */, /* i32 */);
@@ -136,7 +136,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:4:4
    |
 LL | fn three_same(_a: i32, _b: i32, _c: i32) {}
-   |    ^^^^^^^^^^ -------  -------  -------
+   |    ^^^^^^^^^^                   -------
 help: provide the argument
    |
 LL |   three_same(1, 1, /* i32 */);
@@ -152,7 +152,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:5:4
    |
 LL | fn three_diff(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^ -------
 help: provide the argument
    |
 LL |   three_diff(/* i32 */, 1.0, "");
@@ -168,7 +168,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:5:4
    |
 LL | fn three_diff(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^          -------
 help: provide the argument
    |
 LL |   three_diff(1, /* f32 */, "");
@@ -184,7 +184,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:5:4
    |
 LL | fn three_diff(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^                   --------
 help: provide the argument
    |
 LL |   three_diff(1, 1.0, /* &str */);
@@ -200,7 +200,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:5:4
    |
 LL | fn three_diff(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^ -------  -------
 help: provide the arguments
    |
 LL |   three_diff(/* i32 */, /* f32 */, "");
@@ -219,7 +219,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:5:4
    |
 LL | fn three_diff(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^ -------           --------
 help: provide the arguments
    |
 LL |   three_diff(/* i32 */, 1.0, /* &str */);
@@ -235,7 +235,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:5:4
    |
 LL | fn three_diff(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^          -------  --------
 help: provide the arguments
    |
 LL |   three_diff(1, /* f32 */, /* &str */);
@@ -267,7 +267,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:6:4
    |
 LL | fn four_repeated(_a: i32, _b: f32, _c: f32, _d: &str) {}
-   |    ^^^^^^^^^^^^^ -------  -------  -------  --------
+   |    ^^^^^^^^^^^^^          -------  -------
 help: provide the arguments
    |
 LL |   four_repeated(1, /* f32 */, /* f32 */, "");
@@ -299,7 +299,7 @@ note: function defined here
   --> $DIR/missing_arguments.rs:7:4
    |
 LL | fn complex(_a: i32, _b: f32, _c: i32, _d: f32, _e: &str) {}
-   |    ^^^^^^^ -------  -------  -------  -------  --------
+   |    ^^^^^^^          -------  -------  -------
 help: provide the arguments
    |
 LL |   complex(1, /* f32 */, /* i32 */, /* f32 */, "");
diff --git a/tests/ui/argument-suggestions/mixed_cases.stderr b/tests/ui/argument-suggestions/mixed_cases.stderr
index bec5d4dc16b..c19cd68c771 100644
--- a/tests/ui/argument-suggestions/mixed_cases.stderr
+++ b/tests/ui/argument-suggestions/mixed_cases.stderr
@@ -10,7 +10,7 @@ note: function defined here
   --> $DIR/mixed_cases.rs:5:4
    |
 LL | fn two_args(_a: i32, _b: f32) {}
-   |    ^^^^^^^^ -------  -------
+   |    ^^^^^^^^          -------
 help: remove the extra argument
    |
 LL -   two_args(1, "", X {});
@@ -30,7 +30,7 @@ note: function defined here
   --> $DIR/mixed_cases.rs:6:4
    |
 LL | fn three_args(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^          -------
 help: did you mean
    |
 LL |   three_args(1, /* f32 */, "");
@@ -49,7 +49,7 @@ note: function defined here
   --> $DIR/mixed_cases.rs:6:4
    |
 LL | fn three_args(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^          -------  --------
 help: provide the argument
    |
 LL |   three_args(1, /* f32 */, /* &str */);
@@ -67,7 +67,7 @@ note: function defined here
   --> $DIR/mixed_cases.rs:6:4
    |
 LL | fn three_args(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^          -------
 help: did you mean
    |
 LL |   three_args(1, /* f32 */, "");
@@ -86,7 +86,7 @@ note: function defined here
   --> $DIR/mixed_cases.rs:6:4
    |
 LL | fn three_args(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^          -------
 help: swap these arguments
    |
 LL |   three_args(1, /* f32 */, "");
@@ -106,7 +106,7 @@ note: function defined here
   --> $DIR/mixed_cases.rs:6:4
    |
 LL | fn three_args(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^          -------
 help: did you mean
    |
 LL |   three_args(1, /* f32 */, "");
diff --git a/tests/ui/argument-suggestions/permuted_arguments.stderr b/tests/ui/argument-suggestions/permuted_arguments.stderr
index 655807a7f38..f6bec520984 100644
--- a/tests/ui/argument-suggestions/permuted_arguments.stderr
+++ b/tests/ui/argument-suggestions/permuted_arguments.stderr
@@ -11,7 +11,7 @@ note: function defined here
   --> $DIR/permuted_arguments.rs:5:4
    |
 LL | fn three_args(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^
 help: reorder these arguments
    |
 LL |   three_args(1, 1.0, "");
@@ -32,7 +32,7 @@ note: function defined here
   --> $DIR/permuted_arguments.rs:6:4
    |
 LL | fn many_args(_a: i32, _b: f32, _c: &str, _d: X, _e: Y) {}
-   |    ^^^^^^^^^ -------  -------  --------  -----  -----
+   |    ^^^^^^^^^
 help: reorder these arguments
    |
 LL |   many_args(1, 1.0, "", X {}, Y {});
diff --git a/tests/ui/argument-suggestions/suggest-better-removing-issue-126246.stderr b/tests/ui/argument-suggestions/suggest-better-removing-issue-126246.stderr
index 730f20cfb88..48c647764df 100644
--- a/tests/ui/argument-suggestions/suggest-better-removing-issue-126246.stderr
+++ b/tests/ui/argument-suggestions/suggest-better-removing-issue-126246.stderr
@@ -38,7 +38,7 @@ note: function defined here
   --> $DIR/suggest-better-removing-issue-126246.rs:1:4
    |
 LL | fn add_one(x: i32) -> i32 {
-   |    ^^^^^^^ ------
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -     add_one(2, 2);
@@ -55,7 +55,7 @@ note: function defined here
   --> $DIR/suggest-better-removing-issue-126246.rs:1:4
    |
 LL | fn add_one(x: i32) -> i32 {
-   |    ^^^^^^^ ------
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -     add_one(no_such_local, 10);
@@ -72,7 +72,7 @@ note: function defined here
   --> $DIR/suggest-better-removing-issue-126246.rs:1:4
    |
 LL | fn add_one(x: i32) -> i32 {
-   |    ^^^^^^^ ------
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -     add_one(10, no_such_local);
@@ -89,7 +89,7 @@ note: function defined here
   --> $DIR/suggest-better-removing-issue-126246.rs:5:4
    |
 LL | fn add_two(x: i32, y: i32) -> i32 {
-   |    ^^^^^^^ ------  ------
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -     add_two(10, no_such_local, 10);
@@ -106,7 +106,7 @@ note: function defined here
   --> $DIR/suggest-better-removing-issue-126246.rs:5:4
    |
 LL | fn add_two(x: i32, y: i32) -> i32 {
-   |    ^^^^^^^ ------  ------
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -     add_two(no_such_local, 10, 10);
@@ -123,7 +123,7 @@ note: function defined here
   --> $DIR/suggest-better-removing-issue-126246.rs:5:4
    |
 LL | fn add_two(x: i32, y: i32) -> i32 {
-   |    ^^^^^^^ ------  ------
+   |    ^^^^^^^
 help: remove the extra argument
    |
 LL -     add_two(10, 10, no_such_local);
diff --git a/tests/ui/argument-suggestions/swapped_arguments.stderr b/tests/ui/argument-suggestions/swapped_arguments.stderr
index dabf5e952b2..22db77b3b93 100644
--- a/tests/ui/argument-suggestions/swapped_arguments.stderr
+++ b/tests/ui/argument-suggestions/swapped_arguments.stderr
@@ -10,7 +10,7 @@ note: function defined here
   --> $DIR/swapped_arguments.rs:3:4
    |
 LL | fn two_args(_a: i32, _b: f32) {}
-   |    ^^^^^^^^ -------  -------
+   |    ^^^^^^^^
 help: swap these arguments
    |
 LL |   two_args(1, 1.0);
@@ -28,7 +28,7 @@ note: function defined here
   --> $DIR/swapped_arguments.rs:4:4
    |
 LL | fn three_args(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^
 help: swap these arguments
    |
 LL |   three_args(1, 1.0, "");
@@ -46,7 +46,7 @@ note: function defined here
   --> $DIR/swapped_arguments.rs:4:4
    |
 LL | fn three_args(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^
 help: swap these arguments
    |
 LL |   three_args(1, 1.0, "");
@@ -64,7 +64,7 @@ note: function defined here
   --> $DIR/swapped_arguments.rs:4:4
    |
 LL | fn three_args(_a: i32, _b: f32, _c: &str) {}
-   |    ^^^^^^^^^^ -------  -------  --------
+   |    ^^^^^^^^^^
 help: swap these arguments
    |
 LL |   three_args(1, 1.0, "");
@@ -84,7 +84,7 @@ note: function defined here
   --> $DIR/swapped_arguments.rs:5:4
    |
 LL | fn four_args(_a: i32, _b: f32, _c: &str, _d: X) {}
-   |    ^^^^^^^^^ -------  -------  --------  -----
+   |    ^^^^^^^^^
 help: did you mean
    |
 LL |   four_args(1, 1.0, "", X {});
diff --git a/tests/ui/error-codes/E0061.stderr b/tests/ui/error-codes/E0061.stderr
index 7b180c07120..4a420cd118a 100644
--- a/tests/ui/error-codes/E0061.stderr
+++ b/tests/ui/error-codes/E0061.stderr
@@ -8,7 +8,7 @@ note: function defined here
   --> $DIR/E0061.rs:1:4
    |
 LL | fn f(a: u16, b: &str) {}
-   |    ^ ------  -------
+   |    ^         -------
 help: provide the argument
    |
 LL |     f(0, /* &str */);
diff --git a/tests/ui/impl-trait/in-trait/dump.rs b/tests/ui/impl-trait/in-trait/dump.rs
new file mode 100644
index 00000000000..47198d51150
--- /dev/null
+++ b/tests/ui/impl-trait/in-trait/dump.rs
@@ -0,0 +1,15 @@
+//@ compile-flags: -Zverbose-internals
+
+#![feature(precise_capturing_in_traits, rustc_attrs)]
+#![rustc_hidden_type_of_opaques]
+
+trait Foo {
+    fn hello(&self) -> impl Sized;
+}
+
+fn hello<'s, T: Foo>(x: &'s T) -> impl Sized + use<'s, T> {
+//~^ ERROR <T as Foo>::{synthetic#0}<'s/#1>
+    x.hello()
+}
+
+fn main() {}
diff --git a/tests/ui/impl-trait/in-trait/dump.stderr b/tests/ui/impl-trait/in-trait/dump.stderr
new file mode 100644
index 00000000000..95805840385
--- /dev/null
+++ b/tests/ui/impl-trait/in-trait/dump.stderr
@@ -0,0 +1,8 @@
+error: <T as Foo>::{synthetic#0}<'s/#1>
+  --> $DIR/dump.rs:10:35
+   |
+LL | fn hello<'s, T: Foo>(x: &'s T) -> impl Sized + use<'s, T> {
+   |                                   ^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
diff --git a/tests/ui/issues/issue-4935.stderr b/tests/ui/issues/issue-4935.stderr
index 7ee895d91c7..918f74256c0 100644
--- a/tests/ui/issues/issue-4935.stderr
+++ b/tests/ui/issues/issue-4935.stderr
@@ -8,7 +8,7 @@ note: function defined here
   --> $DIR/issue-4935.rs:3:4
    |
 LL | fn foo(a: usize) {}
-   |    ^^^ --------
+   |    ^^^
 help: remove the extra argument
    |
 LL - fn main() { foo(5, 6) }
diff --git a/tests/ui/methods/method-call-err-msg.stderr b/tests/ui/methods/method-call-err-msg.stderr
index 84005119a87..c17c4a23a3a 100644
--- a/tests/ui/methods/method-call-err-msg.stderr
+++ b/tests/ui/methods/method-call-err-msg.stderr
@@ -41,7 +41,7 @@ note: method defined here
   --> $DIR/method-call-err-msg.rs:7:8
    |
 LL |     fn two(self, _: isize, _: isize) -> Foo { self }
-   |        ^^^       --------  --------
+   |        ^^^                 --------
 help: provide the argument
    |
 LL |      .two(0, /* isize */);
diff --git a/tests/ui/mismatched_types/generic-mismatch-reporting-issue-116615.stderr b/tests/ui/mismatched_types/generic-mismatch-reporting-issue-116615.stderr
index 0a86f884e70..9fc3a914447 100644
--- a/tests/ui/mismatched_types/generic-mismatch-reporting-issue-116615.stderr
+++ b/tests/ui/mismatched_types/generic-mismatch-reporting-issue-116615.stderr
@@ -31,9 +31,8 @@ note: function defined here
   --> $DIR/generic-mismatch-reporting-issue-116615.rs:2:4
    |
 LL | fn foo_multi_same<T>(a: T, b: T, c: T, d: T, e: T, f: i32) {}
-   |    ^^^^^^^^^^^^^^ -  ----  ----  ----  ----  ----  ------
-   |                   |  |     |     |     |     |
-   |                   |  |     |     |     |     this parameter needs to match the `&str` type of `a` and `b`
+   |    ^^^^^^^^^^^^^^ -  ----  ----  ----  ----  ---- this parameter needs to match the `&str` type of `a` and `b`
+   |                   |  |     |     |     |
    |                   |  |     |     |     this parameter needs to match the `&str` type of `a` and `b`
    |                   |  |     |     this parameter needs to match the `&str` type of `a` and `b`
    |                   |  |     `c`, `d` and `e` need to match the `&str` type of this parameter
@@ -83,9 +82,8 @@ note: function defined here
   --> $DIR/generic-mismatch-reporting-issue-116615.rs:2:4
    |
 LL | fn foo_multi_same<T>(a: T, b: T, c: T, d: T, e: T, f: i32) {}
-   |    ^^^^^^^^^^^^^^ -  ----  ----  ----  ----  ----  ------
-   |                   |  |     |     |     |     |
-   |                   |  |     |     |     |     `b` and `c` need to match the `&str` type of this parameter
+   |    ^^^^^^^^^^^^^^ -  ----  ----  ----  ----  ---- `b` and `c` need to match the `&str` type of this parameter
+   |                   |  |     |     |     |
    |                   |  |     |     |     `b` and `c` need to match the `&str` type of this parameter
    |                   |  |     |     this parameter needs to match the `&str` type of `a`, `d` and `e`
    |                   |  |     this parameter needs to match the `&str` type of `a`, `d` and `e`
diff --git a/tests/ui/not-enough-arguments.stderr b/tests/ui/not-enough-arguments.stderr
index 89e98866667..66c96ba43c8 100644
--- a/tests/ui/not-enough-arguments.stderr
+++ b/tests/ui/not-enough-arguments.stderr
@@ -8,7 +8,7 @@ note: function defined here
   --> $DIR/not-enough-arguments.rs:5:4
    |
 LL | fn foo(a: isize, b: isize, c: isize, d:isize) {
-   |    ^^^ --------  --------  --------  -------
+   |    ^^^                               -------
 help: provide the argument
    |
 LL |   foo(1, 2, 3, /* isize */);
@@ -25,12 +25,7 @@ note: function defined here
    |
 LL | fn bar(
    |    ^^^
-LL |     a: i32,
-   |     ------
-LL |     b: i32,
-   |     ------
-LL |     c: i32,
-   |     ------
+...
 LL |     d: i32,
    |     ------
 LL |     e: i32,
diff --git a/tests/ui/span/issue-34264.stderr b/tests/ui/span/issue-34264.stderr
index b581cdd0be2..c8046a1bddf 100644
--- a/tests/ui/span/issue-34264.stderr
+++ b/tests/ui/span/issue-34264.stderr
@@ -60,7 +60,7 @@ note: function defined here
   --> $DIR/issue-34264.rs:1:4
    |
 LL | fn foo(Option<i32>, String) {}
-   |    ^^^ -----------  ------
+   |    ^^^
 help: remove the extra argument
    |
 LL -     foo(Some(42), 2, "");
@@ -91,7 +91,7 @@ note: function defined here
   --> $DIR/issue-34264.rs:3:4
    |
 LL | fn bar(x, y: usize) {}
-   |    ^^^ -  --------
+   |    ^^^
 help: remove the extra argument
    |
 LL -     bar(1, 2, 3);
diff --git a/tests/ui/span/missing-unit-argument.stderr b/tests/ui/span/missing-unit-argument.stderr
index 79980f48ab6..6261831b752 100644
--- a/tests/ui/span/missing-unit-argument.stderr
+++ b/tests/ui/span/missing-unit-argument.stderr
@@ -37,7 +37,7 @@ note: function defined here
   --> $DIR/missing-unit-argument.rs:1:4
    |
 LL | fn foo(():(), ():()) {}
-   |    ^^^ -----  -----
+   |    ^^^        -----
 help: provide the argument
    |
 LL |     foo((), ());
diff --git a/tests/ui/traits/next-solver/diagnostics/coerce-in-may-coerce.stderr b/tests/ui/traits/next-solver/diagnostics/coerce-in-may-coerce.stderr
index 1938b3375a5..9c28f7b0792 100644
--- a/tests/ui/traits/next-solver/diagnostics/coerce-in-may-coerce.stderr
+++ b/tests/ui/traits/next-solver/diagnostics/coerce-in-may-coerce.stderr
@@ -10,7 +10,7 @@ note: function defined here
   --> $DIR/coerce-in-may-coerce.rs:12:4
    |
 LL | fn arg_error(x: <fn() as Mirror>::Assoc, y: ()) { todo!() }
-   |    ^^^^^^^^^ --------------------------  -----
+   |    ^^^^^^^^^
 help: swap these arguments
    |
 LL |     arg_error(|| (), ());
diff --git a/tests/ui/traits/next-solver/specialization-transmute.rs b/tests/ui/traits/next-solver/specialization-transmute.rs
index 9e31fed9b18..376fa22ae19 100644
--- a/tests/ui/traits/next-solver/specialization-transmute.rs
+++ b/tests/ui/traits/next-solver/specialization-transmute.rs
@@ -1,5 +1,4 @@
 //@ compile-flags: -Znext-solver
-//~^ ERROR cannot normalize `<T as Default>::Id: '_`
 #![feature(specialization)]
 //~^ WARN the feature `specialization` is incomplete
 
@@ -14,6 +13,7 @@ impl<T> Default for T {
     // This will be fixed by #111994
     fn intu(&self) -> &Self::Id {
         //~^ ERROR type annotations needed
+        //~| ERROR cannot normalize `<T as Default>::Id: '_`
         self //~ ERROR cannot satisfy
     }
 }
diff --git a/tests/ui/traits/next-solver/specialization-transmute.stderr b/tests/ui/traits/next-solver/specialization-transmute.stderr
index 2d0c503bc95..eeb101911c4 100644
--- a/tests/ui/traits/next-solver/specialization-transmute.stderr
+++ b/tests/ui/traits/next-solver/specialization-transmute.stderr
@@ -1,5 +1,5 @@
 warning: the feature `specialization` is incomplete and may not be safe to use and/or cause compiler crashes
-  --> $DIR/specialization-transmute.rs:3:12
+  --> $DIR/specialization-transmute.rs:2:12
    |
 LL | #![feature(specialization)]
    |            ^^^^^^^^^^^^^^
@@ -9,9 +9,13 @@ LL | #![feature(specialization)]
    = note: `#[warn(incomplete_features)]` on by default
 
 error: cannot normalize `<T as Default>::Id: '_`
+  --> $DIR/specialization-transmute.rs:14:5
+   |
+LL |     fn intu(&self) -> &Self::Id {
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0282]: type annotations needed
-  --> $DIR/specialization-transmute.rs:15:23
+  --> $DIR/specialization-transmute.rs:14:23
    |
 LL |     fn intu(&self) -> &Self::Id {
    |                       ^^^^^^^^^ cannot infer type for reference `&<T as Default>::Id`
diff --git a/tests/ui/traits/next-solver/unsound-region-obligation.rs b/tests/ui/traits/next-solver/unsound-region-obligation.rs
index 733be204354..e7fa60a2e3f 100644
--- a/tests/ui/traits/next-solver/unsound-region-obligation.rs
+++ b/tests/ui/traits/next-solver/unsound-region-obligation.rs
@@ -1,4 +1,3 @@
-//~ ERROR the type `&'a ()` does not fulfill the required lifetime
 //@ compile-flags: -Znext-solver
 // Regression test for rust-lang/trait-system-refactor-initiative#59
 
@@ -8,6 +7,7 @@ trait StaticTy {
 
 impl StaticTy for () {
     type Item<'a> = &'a ();
+    //~^ ERROR the type `&'a ()` does not fulfill the required lifetime
 }
 
 fn main() {}
diff --git a/tests/ui/traits/next-solver/unsound-region-obligation.stderr b/tests/ui/traits/next-solver/unsound-region-obligation.stderr
index fe96a184f43..dea3b62334c 100644
--- a/tests/ui/traits/next-solver/unsound-region-obligation.stderr
+++ b/tests/ui/traits/next-solver/unsound-region-obligation.stderr
@@ -1,4 +1,8 @@
 error[E0477]: the type `&'a ()` does not fulfill the required lifetime
+  --> $DIR/unsound-region-obligation.rs:9:21
+   |
+LL |     type Item<'a> = &'a ();
+   |                     ^^^^^^
    |
    = note: type must satisfy the static lifetime
 
diff --git a/tests/ui/type/type-check/point-at-inference-4.rs b/tests/ui/type/type-check/point-at-inference-4.rs
index 5745b738532..258374f299e 100644
--- a/tests/ui/type/type-check/point-at-inference-4.rs
+++ b/tests/ui/type/type-check/point-at-inference-4.rs
@@ -4,7 +4,6 @@ impl<A, B> S<A, B> {
     fn infer(&self, a: A, b: B) {}
     //~^ NOTE method defined here
     //~| NOTE
-    //~| NOTE
 }
 
 fn main() {
diff --git a/tests/ui/type/type-check/point-at-inference-4.stderr b/tests/ui/type/type-check/point-at-inference-4.stderr
index a953ca70ea2..544c25934ec 100644
--- a/tests/ui/type/type-check/point-at-inference-4.stderr
+++ b/tests/ui/type/type-check/point-at-inference-4.stderr
@@ -1,5 +1,5 @@
 error[E0061]: this method takes 2 arguments but 1 argument was supplied
-  --> $DIR/point-at-inference-4.rs:12:7
+  --> $DIR/point-at-inference-4.rs:11:7
    |
 LL |     s.infer(0i32);
    |       ^^^^^------ argument #2 is missing
@@ -8,14 +8,14 @@ note: method defined here
   --> $DIR/point-at-inference-4.rs:4:8
    |
 LL |     fn infer(&self, a: A, b: B) {}
-   |        ^^^^^        ----  ----
+   |        ^^^^^              ----
 help: provide the argument
    |
 LL |     s.infer(0i32, /* b */);
    |            ~~~~~~~~~~~~~~~
 
 error[E0308]: mismatched types
-  --> $DIR/point-at-inference-4.rs:19:24
+  --> $DIR/point-at-inference-4.rs:18:24
    |
 LL |     s.infer(0i32);
    |     -       ---- this argument has type `i32`...
diff --git a/tests/ui/typeck/remove-extra-argument.stderr b/tests/ui/typeck/remove-extra-argument.stderr
index d4e0dcb50ae..17e1b613cd9 100644
--- a/tests/ui/typeck/remove-extra-argument.stderr
+++ b/tests/ui/typeck/remove-extra-argument.stderr
@@ -8,7 +8,7 @@ note: function defined here
   --> $DIR/remove-extra-argument.rs:3:4
    |
 LL | fn l(_a: Vec<u8>) {}
-   |    ^ -----------
+   |    ^
 help: remove the extra argument
    |
 LL -     l(vec![], vec![])