about summary refs log tree commit diff
path: root/tests
diff options
context:
space:
mode:
Diffstat (limited to 'tests')
-rw-r--r--tests/codegen/align-byval-alignment-mismatch.rs126
-rw-r--r--tests/coverage/branch_generics.cov-map54
-rw-r--r--tests/coverage/branch_generics.coverage62
-rw-r--r--tests/coverage/branch_generics.rs19
-rw-r--r--tests/coverage/branch_guard.cov-map32
-rw-r--r--tests/coverage/branch_guard.coverage45
-rw-r--r--tests/coverage/branch_guard.rs37
-rw-r--r--tests/coverage/branch_if.cov-map188
-rw-r--r--tests/coverage/branch_if.coverage115
-rw-r--r--tests/coverage/branch_if.rs81
-rw-r--r--tests/coverage/branch_while.cov-map98
-rw-r--r--tests/coverage/branch_while.coverage74
-rw-r--r--tests/coverage/branch_while.rs58
-rw-r--r--tests/run-make/issue-88756-default-output/output-default.stdout2
-rw-r--r--tests/run-make/pdb-alt-path/Makefile20
-rw-r--r--tests/run-make/pdb-alt-path/main.rs24
-rw-r--r--tests/rustdoc-js-std/parser-errors.js19
-rw-r--r--tests/rustdoc-js-std/parser-hof.js712
-rw-r--r--tests/rustdoc-js-std/parser-weird-queries.js9
-rw-r--r--tests/rustdoc-js/auxiliary/interner.rs245
-rw-r--r--tests/rustdoc-js/hof.js176
-rw-r--r--tests/rustdoc-js/hof.rs12
-rw-r--r--tests/rustdoc-js/looks-like-rustc-interner.js9
-rw-r--r--tests/rustdoc-js/looks-like-rustc-interner.rs5
-rw-r--r--tests/rustdoc/display-hidden-items.rs12
-rw-r--r--tests/ui-fulldeps/stable-mir/check_transform.rs147
-rw-r--r--tests/ui/associated-type-bounds/dedup-normalized-1.rs24
-rw-r--r--tests/ui/associated-type-bounds/dedup-normalized-2-higher-ranked.rs27
-rw-r--r--tests/ui/associated-type-bounds/dedup-normalized-2-higher-ranked.stderr20
-rw-r--r--tests/ui/async-await/in-trait/hir-hash.rs11
-rw-r--r--tests/ui/async-await/return-type-notation/issue-110963-early.stderr27
-rw-r--r--tests/ui/borrowck/clone-on-ref.fixed32
-rw-r--r--tests/ui/borrowck/clone-on-ref.rs31
-rw-r--r--tests/ui/borrowck/clone-on-ref.stderr64
-rw-r--r--tests/ui/closures/multiple-fn-bounds.stderr2
-rw-r--r--tests/ui/consts/assoc_const_generic_impl.stderr6
-rw-r--r--tests/ui/consts/const-eval/erroneous-const.stderr15
-rw-r--r--tests/ui/consts/const-eval/erroneous-const2.rs19
-rw-r--r--tests/ui/consts/const-eval/erroneous-const2.stderr15
-rw-r--r--tests/ui/consts/const-eval/index-out-of-bounds-never-type.stderr6
-rw-r--r--tests/ui/consts/const-eval/issue-50814-2.mir-opt.stderr46
-rw-r--r--tests/ui/consts/const-eval/issue-50814-2.normal.stderr14
-rw-r--r--tests/ui/consts/const-eval/issue-50814.stderr14
-rw-r--r--tests/ui/consts/const-eval/issue-85155.stderr8
-rw-r--r--tests/ui/consts/const-eval/unused-broken-const-late.stderr11
-rw-r--r--tests/ui/consts/required-consts/collect-in-called-fn.noopt.stderr23
-rw-r--r--tests/ui/consts/required-consts/collect-in-called-fn.opt.stderr23
-rw-r--r--tests/ui/consts/required-consts/collect-in-called-fn.rs (renamed from tests/ui/consts/const-eval/unused-broken-const-late.rs)18
-rw-r--r--tests/ui/consts/required-consts/collect-in-dead-drop.noopt.stderr20
-rw-r--r--tests/ui/consts/required-consts/collect-in-dead-drop.rs33
-rw-r--r--tests/ui/consts/required-consts/collect-in-dead-fn.noopt.stderr23
-rw-r--r--tests/ui/consts/required-consts/collect-in-dead-fn.rs35
-rw-r--r--tests/ui/consts/required-consts/collect-in-dead-forget.rs32
-rw-r--r--tests/ui/consts/required-consts/collect-in-dead-move.noopt.stderr20
-rw-r--r--tests/ui/consts/required-consts/collect-in-dead-move.rs33
-rw-r--r--tests/ui/consts/required-consts/collect-in-dead-vtable.noopt.stderr23
-rw-r--r--tests/ui/consts/required-consts/collect-in-dead-vtable.rs41
-rw-r--r--tests/ui/consts/required-consts/interpret-in-const-called-fn.noopt.stderr17
-rw-r--r--tests/ui/consts/required-consts/interpret-in-const-called-fn.opt.stderr17
-rw-r--r--tests/ui/consts/required-consts/interpret-in-const-called-fn.rs (renamed from tests/ui/consts/const-eval/erroneous-const.rs)13
-rw-r--r--tests/ui/consts/required-consts/interpret-in-promoted.noopt.stderr27
-rw-r--r--tests/ui/consts/required-consts/interpret-in-promoted.opt.stderr27
-rw-r--r--tests/ui/consts/required-consts/interpret-in-promoted.rs15
-rw-r--r--tests/ui/consts/required-consts/interpret-in-static.noopt.stderr17
-rw-r--r--tests/ui/consts/required-consts/interpret-in-static.opt.stderr17
-rw-r--r--tests/ui/consts/required-consts/interpret-in-static.rs21
-rw-r--r--tests/ui/coroutine/resume-arg-late-bound.rs2
-rw-r--r--tests/ui/coroutine/resume-arg-late-bound.stderr14
-rw-r--r--tests/ui/diagnostic_namespace/deny_malformed_attribute.rs7
-rw-r--r--tests/ui/diagnostic_namespace/deny_malformed_attribute.stderr14
-rw-r--r--tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.next.stderr48
-rw-r--r--tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.old.stderr20
-rw-r--r--tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.rs22
-rw-r--r--tests/ui/generic-associated-types/bugs/issue-88382.stderr29
-rw-r--r--tests/ui/generic-associated-types/rigid-hr-projection-issue-93340.rs (renamed from tests/ui/generic-associated-types/issue-93340.rs)4
-rw-r--r--tests/ui/generics/post_monomorphization_error_backtrace.rs3
-rw-r--r--tests/ui/generics/post_monomorphization_error_backtrace.stderr18
-rw-r--r--tests/ui/half-open-range-patterns/half-open-range-pats-exhaustive-fail.stderr16
-rw-r--r--tests/ui/higher-ranked/higher-ranked-lifetime-error.rs2
-rw-r--r--tests/ui/higher-ranked/higher-ranked-lifetime-error.stderr9
-rw-r--r--tests/ui/higher-ranked/trait-bounds/issue-59311.rs8
-rw-r--r--tests/ui/higher-ranked/trait-bounds/issue-59311.stderr14
-rw-r--r--tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-71955.rs8
-rw-r--r--tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-71955.stderr75
-rw-r--r--tests/ui/impl-trait/in-trait/ensure-rpitits-are-created-before-freezing.rs13
-rw-r--r--tests/ui/impl-trait/in-trait/ensure-rpitits-are-created-before-freezing.stderr9
-rw-r--r--tests/ui/impl-trait/in-trait/return-dont-satisfy-bounds.rs1
-rw-r--r--tests/ui/impl-trait/in-trait/return-dont-satisfy-bounds.stderr18
-rw-r--r--tests/ui/impl-trait/stranded-opaque.rs13
-rw-r--r--tests/ui/impl-trait/stranded-opaque.stderr9
-rw-r--r--tests/ui/implied-bounds/gluon_salsa.rs13
-rw-r--r--tests/ui/inline-const/const-expr-generic-err.stderr20
-rw-r--r--tests/ui/inline-const/required-const.stderr6
-rw-r--r--tests/ui/lifetimes/issue-105675.rs12
-rw-r--r--tests/ui/lifetimes/issue-105675.stderr89
-rw-r--r--tests/ui/lifetimes/issue-76168-hr-outlives-3.rs1
-rw-r--r--tests/ui/lifetimes/issue-76168-hr-outlives-3.stderr23
-rw-r--r--tests/ui/lifetimes/issue-79187-2.rs2
-rw-r--r--tests/ui/lifetimes/issue-79187-2.stderr22
-rw-r--r--tests/ui/lifetimes/issue-79187.rs4
-rw-r--r--tests/ui/lifetimes/issue-79187.stderr24
-rw-r--r--tests/ui/lifetimes/lifetime-errors/issue_74400.rs2
-rw-r--r--tests/ui/lifetimes/lifetime-errors/issue_74400.stderr16
-rw-r--r--tests/ui/lint/lint-qualification.fixed7
-rw-r--r--tests/ui/lint/lint-qualification.rs5
-rw-r--r--tests/ui/lint/lint-qualification.stderr30
-rw-r--r--tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.fixed50
-rw-r--r--tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.rs50
-rw-r--r--tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.stderr31
-rw-r--r--tests/ui/mismatched_types/closure-arg-type-mismatch-issue-45727.stderr2
-rw-r--r--tests/ui/mismatched_types/closure-arg-type-mismatch.rs2
-rw-r--r--tests/ui/mismatched_types/closure-arg-type-mismatch.stderr19
-rw-r--r--tests/ui/mismatched_types/closure-mismatch.rs4
-rw-r--r--tests/ui/mismatched_types/closure-mismatch.stderr45
-rw-r--r--tests/ui/mismatched_types/fn-variance-1.stderr4
-rw-r--r--tests/ui/mismatched_types/issue-36053-2.stderr2
-rw-r--r--tests/ui/mismatched_types/suggest-option-asderef-inference-var.stderr2
-rw-r--r--tests/ui/mismatched_types/suggest-option-asderef-unfixable.stderr4
-rw-r--r--tests/ui/mismatched_types/suggest-option-asderef.stderr8
-rw-r--r--tests/ui/nll/missing-universe-cause-issue-114907.rs4
-rw-r--r--tests/ui/nll/missing-universe-cause-issue-114907.stderr47
-rw-r--r--tests/ui/pattern/bindings-after-at/bind-by-move-neither-can-live-while-the-other-survives-1.stderr4
-rw-r--r--tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse-promotion.stderr2
-rw-r--r--tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse.stderr50
-rw-r--r--tests/ui/pattern/bindings-after-at/borrowck-pat-ref-mut-twice.stderr8
-rw-r--r--tests/ui/pattern/bindings-after-at/default-binding-modes-both-sides-independent.stderr2
-rw-r--r--tests/ui/pattern/usefulness/integer-ranges/exhaustiveness.stderr8
-rw-r--r--tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.fixed11
-rw-r--r--tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.rs11
-rw-r--r--tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.stderr2
-rw-r--r--tests/ui/resolve/unused-qualifications-suggestion.fixed2
-rw-r--r--tests/ui/resolve/unused-qualifications-suggestion.rs2
-rw-r--r--tests/ui/resolve/unused-qualifications-suggestion.stderr2
-rw-r--r--tests/ui/rfcs/rfc-1623-static/rfc1623-2.rs4
-rw-r--r--tests/ui/rfcs/rfc-1623-static/rfc1623-2.stderr18
-rw-r--r--tests/ui/simd/const-err-trumps-simd-err.rs24
-rw-r--r--tests/ui/simd/const-err-trumps-simd-err.stderr23
-rw-r--r--tests/ui/stats/hir-stats.stderr6
-rw-r--r--tests/ui/suggestions/clone-bounds-121524.rs19
-rw-r--r--tests/ui/suggestions/clone-bounds-121524.stderr19
-rw-r--r--tests/ui/suggestions/late-bound-in-borrow-closure-sugg.stderr2
-rw-r--r--tests/ui/suggestions/ref-pattern-binding.stderr4
-rw-r--r--tests/ui/traits/non_lifetime_binders/type-match-with-late-bound.stderr23
-rw-r--r--tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.current.stderr22
-rw-r--r--tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.next.stderr14
-rw-r--r--tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.rs19
-rw-r--r--tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.current.stderr22
-rw-r--r--tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.next.stderr14
-rw-r--r--tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.rs37
-rw-r--r--tests/ui/transmutability/alignment/align-fail.stderr2
-rw-r--r--tests/ui/transmutability/arrays/should_require_well_defined_layout.stderr12
-rw-r--r--tests/ui/transmutability/enums/repr/primitive_reprs_should_have_correct_length.stderr40
-rw-r--r--tests/ui/transmutability/enums/repr/should_require_well_defined_layout.stderr12
-rw-r--r--tests/ui/transmutability/enums/should_pad_variants.stderr2
-rw-r--r--tests/ui/transmutability/enums/should_respect_endianness.stderr2
-rw-r--r--tests/ui/transmutability/primitives/bool-mut.stderr2
-rw-r--r--tests/ui/transmutability/primitives/bool.current.stderr2
-rw-r--r--tests/ui/transmutability/primitives/bool.next.stderr2
-rw-r--r--tests/ui/transmutability/primitives/numbers.current.stderr114
-rw-r--r--tests/ui/transmutability/primitives/numbers.next.stderr114
-rw-r--r--tests/ui/transmutability/primitives/unit.current.stderr2
-rw-r--r--tests/ui/transmutability/primitives/unit.next.stderr2
-rw-r--r--tests/ui/transmutability/references/recursive-wrapper-types-bit-incompatible.stderr2
-rw-r--r--tests/ui/transmutability/references/reject_extension.rs49
-rw-r--r--tests/ui/transmutability/references/reject_extension.stderr25
-rw-r--r--tests/ui/transmutability/references/unit-to-u8.stderr4
-rw-r--r--tests/ui/transmutability/region-infer.stderr2
-rw-r--r--tests/ui/transmutability/structs/repr/should_require_well_defined_layout.stderr24
-rw-r--r--tests/ui/transmutability/transmute-padding-ice.stderr2
-rw-r--r--tests/ui/transmutability/unions/repr/should_require_well_defined_layout.stderr4
-rw-r--r--tests/ui/transmutability/unions/should_pad_variants.stderr2
-rw-r--r--tests/ui/transmutability/unions/should_reject_contraction.stderr2
-rw-r--r--tests/ui/transmutability/unions/should_reject_disjoint.stderr4
-rw-r--r--tests/ui/transmutability/unions/should_reject_intersecting.stderr4
-rw-r--r--tests/ui/type-alias-impl-trait/in-where-clause.rs2
-rw-r--r--tests/ui/typeck/ice-self-mismatch-const-generics.rs25
-rw-r--r--tests/ui/typeck/ice-self-mismatch-const-generics.stderr37
-rw-r--r--tests/ui/typeck/mismatched-map-under-self.stderr2
-rw-r--r--tests/ui/unop-move-semantics.stderr4
179 files changed, 4347 insertions, 723 deletions
diff --git a/tests/codegen/align-byval-alignment-mismatch.rs b/tests/codegen/align-byval-alignment-mismatch.rs
new file mode 100644
index 00000000000..306e3ce1358
--- /dev/null
+++ b/tests/codegen/align-byval-alignment-mismatch.rs
@@ -0,0 +1,126 @@
+// ignore-tidy-linelength
+//@ revisions:i686-linux x86_64-linux
+
+//@[i686-linux] compile-flags: --target i686-unknown-linux-gnu
+//@[i686-linux] needs-llvm-components: x86
+//@[x86_64-linux] compile-flags: --target x86_64-unknown-linux-gnu
+//@[x86_64-linux] needs-llvm-components: x86
+
+// Tests that we correctly copy arguments into allocas when the alignment of the byval argument
+// is different from the alignment of the Rust type.
+
+// For the following test cases:
+// All of the `*_decreases_alignment` functions should codegen to a direct call, since the
+// alignment is already sufficient.
+// All off the `*_increases_alignment` functions should copy the argument to an alloca
+// on i686-unknown-linux-gnu, since the alignment needs to be increased, and should codegen
+// to a direct call on x86_64-unknown-linux-gnu, where byval alignment matches Rust alignment.
+
+#![feature(no_core, lang_items)]
+#![crate_type = "lib"]
+#![no_std]
+#![no_core]
+#![allow(non_camel_case_types)]
+
+#[lang = "sized"]
+trait Sized {}
+#[lang = "freeze"]
+trait Freeze {}
+#[lang = "copy"]
+trait Copy {}
+
+// This type has align 1 in Rust, but as a byval argument on i686-linux, it will have align 4.
+#[repr(C)]
+#[repr(packed)]
+struct Align1 {
+    x: u128,
+    y: u128,
+    z: u128,
+}
+
+// This type has align 16 in Rust, but as a byval argument on i686-linux, it will have align 4.
+#[repr(C)]
+#[repr(align(16))]
+struct Align16 {
+    x: u128,
+    y: u128,
+    z: u128,
+}
+
+extern "C" {
+    fn extern_c_align1(x: Align1);
+    fn extern_c_align16(x: Align16);
+}
+
+// CHECK-LABEL: @rust_to_c_increases_alignment
+#[no_mangle]
+pub unsafe fn rust_to_c_increases_alignment(x: Align1) {
+    // i686-linux: start:
+    // i686-linux-NEXT: [[ALLOCA:%[0-9a-z]+]] = alloca %Align1, align 4
+    // i686-linux-NEXT: call void @llvm.memcpy.{{.+}}(ptr {{.*}}align 4 {{.*}}[[ALLOCA]], ptr {{.*}}align 1 {{.*}}%x
+    // i686-linux-NEXT: call void @extern_c_align1({{.+}} [[ALLOCA]])
+
+    // x86_64-linux: start:
+    // x86_64-linux-NEXT: call void @extern_c_align1
+    extern_c_align1(x);
+}
+
+// CHECK-LABEL: @rust_to_c_decreases_alignment
+#[no_mangle]
+pub unsafe fn rust_to_c_decreases_alignment(x: Align16) {
+    // CHECK: start:
+    // CHECK-NEXT: call void @extern_c_align16
+    extern_c_align16(x);
+}
+
+extern "Rust" {
+    fn extern_rust_align1(x: Align1);
+    fn extern_rust_align16(x: Align16);
+}
+
+// CHECK-LABEL: @c_to_rust_decreases_alignment
+#[no_mangle]
+pub unsafe extern "C" fn c_to_rust_decreases_alignment(x: Align1) {
+    // CHECK: start:
+    // CHECK-NEXT: call void @extern_rust_align1
+    extern_rust_align1(x);
+}
+
+// CHECK-LABEL: @c_to_rust_increases_alignment
+#[no_mangle]
+pub unsafe extern "C" fn c_to_rust_increases_alignment(x: Align16) {
+    // i686-linux: start:
+    // i686-linux-NEXT: [[ALLOCA:%[0-9a-z]+]] = alloca %Align16, align 16
+    // i686-linux-NEXT: call void @llvm.memcpy.{{.+}}(ptr {{.*}}align 16 {{.*}}[[ALLOCA]], ptr {{.*}}align 4 {{.*}}%0
+    // i686-linux-NEXT: call void @extern_rust_align16({{.+}} [[ALLOCA]])
+
+    // x86_64-linux: start:
+    // x86_64-linux-NEXT: call void @extern_rust_align16
+    extern_rust_align16(x);
+}
+
+extern "Rust" {
+    fn extern_rust_ref_align1(x: &Align1);
+    fn extern_rust_ref_align16(x: &Align16);
+}
+
+// CHECK-LABEL: @c_to_rust_ref_decreases_alignment
+#[no_mangle]
+pub unsafe extern "C" fn c_to_rust_ref_decreases_alignment(x: Align1) {
+    // CHECK: start:
+    // CHECK-NEXT: call void @extern_rust_ref_align1
+    extern_rust_ref_align1(&x);
+}
+
+// CHECK-LABEL: @c_to_rust_ref_increases_alignment
+#[no_mangle]
+pub unsafe extern "C" fn c_to_rust_ref_increases_alignment(x: Align16) {
+    // i686-linux: start:
+    // i686-linux-NEXT: [[ALLOCA:%[0-9a-z]+]] = alloca %Align16, align 16
+    // i686-linux-NEXT: call void @llvm.memcpy.{{.+}}(ptr {{.*}}align 16 {{.*}}[[ALLOCA]], ptr {{.*}}align 4 {{.*}}%0
+    // i686-linux-NEXT: call void @extern_rust_ref_align16({{.+}} [[ALLOCA]])
+
+    // x86_64-linux: start:
+    // x86_64-linux-NEXT: call void @extern_rust_ref_align16
+    extern_rust_ref_align16(&x);
+}
diff --git a/tests/coverage/branch_generics.cov-map b/tests/coverage/branch_generics.cov-map
new file mode 100644
index 00000000000..719e97efad4
--- /dev/null
+++ b/tests/coverage/branch_generics.cov-map
@@ -0,0 +1,54 @@
+Function name: branch_generics::print_size::<()>
+Raw bytes (35): 0x[01, 01, 02, 01, 05, 05, 02, 05, 01, 06, 01, 01, 24, 20, 05, 02, 01, 08, 00, 24, 05, 00, 25, 02, 06, 02, 02, 0c, 02, 06, 07, 03, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 2
+- expression 0 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 1 operands: lhs = Counter(1), rhs = Expression(0, Sub)
+Number of file 0 mappings: 5
+- Code(Counter(0)) at (prev + 6, 1) to (start + 1, 36)
+- Branch { true: Counter(1), false: Expression(0, Sub) } at (prev + 1, 8) to (start + 0, 36)
+    true  = c1
+    false = (c0 - c1)
+- Code(Counter(1)) at (prev + 0, 37) to (start + 2, 6)
+- Code(Expression(0, Sub)) at (prev + 2, 12) to (start + 2, 6)
+    = (c0 - c1)
+- Code(Expression(1, Add)) at (prev + 3, 1) to (start + 0, 2)
+    = (c1 + (c0 - c1))
+
+Function name: branch_generics::print_size::<u32>
+Raw bytes (35): 0x[01, 01, 02, 01, 05, 05, 02, 05, 01, 06, 01, 01, 24, 20, 05, 02, 01, 08, 00, 24, 05, 00, 25, 02, 06, 02, 02, 0c, 02, 06, 07, 03, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 2
+- expression 0 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 1 operands: lhs = Counter(1), rhs = Expression(0, Sub)
+Number of file 0 mappings: 5
+- Code(Counter(0)) at (prev + 6, 1) to (start + 1, 36)
+- Branch { true: Counter(1), false: Expression(0, Sub) } at (prev + 1, 8) to (start + 0, 36)
+    true  = c1
+    false = (c0 - c1)
+- Code(Counter(1)) at (prev + 0, 37) to (start + 2, 6)
+- Code(Expression(0, Sub)) at (prev + 2, 12) to (start + 2, 6)
+    = (c0 - c1)
+- Code(Expression(1, Add)) at (prev + 3, 1) to (start + 0, 2)
+    = (c1 + (c0 - c1))
+
+Function name: branch_generics::print_size::<u64>
+Raw bytes (35): 0x[01, 01, 02, 01, 05, 05, 02, 05, 01, 06, 01, 01, 24, 20, 05, 02, 01, 08, 00, 24, 05, 00, 25, 02, 06, 02, 02, 0c, 02, 06, 07, 03, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 2
+- expression 0 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 1 operands: lhs = Counter(1), rhs = Expression(0, Sub)
+Number of file 0 mappings: 5
+- Code(Counter(0)) at (prev + 6, 1) to (start + 1, 36)
+- Branch { true: Counter(1), false: Expression(0, Sub) } at (prev + 1, 8) to (start + 0, 36)
+    true  = c1
+    false = (c0 - c1)
+- Code(Counter(1)) at (prev + 0, 37) to (start + 2, 6)
+- Code(Expression(0, Sub)) at (prev + 2, 12) to (start + 2, 6)
+    = (c0 - c1)
+- Code(Expression(1, Add)) at (prev + 3, 1) to (start + 0, 2)
+    = (c1 + (c0 - c1))
+
diff --git a/tests/coverage/branch_generics.coverage b/tests/coverage/branch_generics.coverage
new file mode 100644
index 00000000000..e7cec151ce6
--- /dev/null
+++ b/tests/coverage/branch_generics.coverage
@@ -0,0 +1,62 @@
+   LL|       |#![feature(coverage_attribute)]
+   LL|       |//@ edition: 2021
+   LL|       |//@ compile-flags: -Zcoverage-options=branch
+   LL|       |//@ llvm-cov-flags: --show-branches=count
+   LL|       |
+   LL|      3|fn print_size<T>() {
+   LL|      3|    if std::mem::size_of::<T>() > 4 {
+  ------------------
+  |  Branch (LL:8): [True: 0, False: 1]
+  |  Branch (LL:8): [True: 0, False: 1]
+  |  Branch (LL:8): [True: 1, False: 0]
+  ------------------
+   LL|      1|        println!("size > 4");
+   LL|      2|    } else {
+   LL|      2|        println!("size <= 4");
+   LL|      2|    }
+   LL|      3|}
+  ------------------
+  | branch_generics::print_size::<()>:
+  |   LL|      1|fn print_size<T>() {
+  |   LL|      1|    if std::mem::size_of::<T>() > 4 {
+  |  ------------------
+  |  |  Branch (LL:8): [True: 0, False: 1]
+  |  ------------------
+  |   LL|      0|        println!("size > 4");
+  |   LL|      1|    } else {
+  |   LL|      1|        println!("size <= 4");
+  |   LL|      1|    }
+  |   LL|      1|}
+  ------------------
+  | branch_generics::print_size::<u32>:
+  |   LL|      1|fn print_size<T>() {
+  |   LL|      1|    if std::mem::size_of::<T>() > 4 {
+  |  ------------------
+  |  |  Branch (LL:8): [True: 0, False: 1]
+  |  ------------------
+  |   LL|      0|        println!("size > 4");
+  |   LL|      1|    } else {
+  |   LL|      1|        println!("size <= 4");
+  |   LL|      1|    }
+  |   LL|      1|}
+  ------------------
+  | branch_generics::print_size::<u64>:
+  |   LL|      1|fn print_size<T>() {
+  |   LL|      1|    if std::mem::size_of::<T>() > 4 {
+  |  ------------------
+  |  |  Branch (LL:8): [True: 1, False: 0]
+  |  ------------------
+  |   LL|      1|        println!("size > 4");
+  |   LL|      1|    } else {
+  |   LL|      0|        println!("size <= 4");
+  |   LL|      0|    }
+  |   LL|      1|}
+  ------------------
+   LL|       |
+   LL|       |#[coverage(off)]
+   LL|       |fn main() {
+   LL|       |    print_size::<()>();
+   LL|       |    print_size::<u32>();
+   LL|       |    print_size::<u64>();
+   LL|       |}
+
diff --git a/tests/coverage/branch_generics.rs b/tests/coverage/branch_generics.rs
new file mode 100644
index 00000000000..d870ace7006
--- /dev/null
+++ b/tests/coverage/branch_generics.rs
@@ -0,0 +1,19 @@
+#![feature(coverage_attribute)]
+//@ edition: 2021
+//@ compile-flags: -Zcoverage-options=branch
+//@ llvm-cov-flags: --show-branches=count
+
+fn print_size<T>() {
+    if std::mem::size_of::<T>() > 4 {
+        println!("size > 4");
+    } else {
+        println!("size <= 4");
+    }
+}
+
+#[coverage(off)]
+fn main() {
+    print_size::<()>();
+    print_size::<u32>();
+    print_size::<u64>();
+}
diff --git a/tests/coverage/branch_guard.cov-map b/tests/coverage/branch_guard.cov-map
new file mode 100644
index 00000000000..0b3622f6347
--- /dev/null
+++ b/tests/coverage/branch_guard.cov-map
@@ -0,0 +1,32 @@
+Function name: branch_guard::branch_match_guard
+Raw bytes (85): 0x[01, 01, 06, 19, 0d, 05, 09, 0f, 15, 13, 11, 17, 0d, 05, 09, 0d, 01, 0c, 01, 01, 10, 1d, 03, 0b, 00, 0c, 15, 01, 14, 02, 0a, 0d, 03, 0e, 00, 0f, 19, 00, 14, 00, 19, 20, 0d, 02, 00, 14, 00, 1e, 0d, 00, 1d, 02, 0a, 11, 03, 0e, 00, 0f, 1d, 00, 14, 00, 19, 20, 11, 09, 00, 14, 00, 1e, 11, 00, 1d, 02, 0a, 17, 03, 0e, 02, 0a, 0b, 04, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 6
+- expression 0 operands: lhs = Counter(6), rhs = Counter(3)
+- expression 1 operands: lhs = Counter(1), rhs = Counter(2)
+- expression 2 operands: lhs = Expression(3, Add), rhs = Counter(5)
+- expression 3 operands: lhs = Expression(4, Add), rhs = Counter(4)
+- expression 4 operands: lhs = Expression(5, Add), rhs = Counter(3)
+- expression 5 operands: lhs = Counter(1), rhs = Counter(2)
+Number of file 0 mappings: 13
+- Code(Counter(0)) at (prev + 12, 1) to (start + 1, 16)
+- Code(Counter(7)) at (prev + 3, 11) to (start + 0, 12)
+- Code(Counter(5)) at (prev + 1, 20) to (start + 2, 10)
+- Code(Counter(3)) at (prev + 3, 14) to (start + 0, 15)
+- Code(Counter(6)) at (prev + 0, 20) to (start + 0, 25)
+- Branch { true: Counter(3), false: Expression(0, Sub) } at (prev + 0, 20) to (start + 0, 30)
+    true  = c3
+    false = (c6 - c3)
+- Code(Counter(3)) at (prev + 0, 29) to (start + 2, 10)
+- Code(Counter(4)) at (prev + 3, 14) to (start + 0, 15)
+- Code(Counter(7)) at (prev + 0, 20) to (start + 0, 25)
+- Branch { true: Counter(4), false: Counter(2) } at (prev + 0, 20) to (start + 0, 30)
+    true  = c4
+    false = c2
+- Code(Counter(4)) at (prev + 0, 29) to (start + 2, 10)
+- Code(Expression(5, Add)) at (prev + 3, 14) to (start + 2, 10)
+    = (c1 + c2)
+- Code(Expression(2, Add)) at (prev + 4, 1) to (start + 0, 2)
+    = ((((c1 + c2) + c3) + c4) + c5)
+
diff --git a/tests/coverage/branch_guard.coverage b/tests/coverage/branch_guard.coverage
new file mode 100644
index 00000000000..f89b965b5d0
--- /dev/null
+++ b/tests/coverage/branch_guard.coverage
@@ -0,0 +1,45 @@
+   LL|       |#![feature(coverage_attribute)]
+   LL|       |//@ edition: 2021
+   LL|       |//@ compile-flags: -Zcoverage-options=branch
+   LL|       |//@ llvm-cov-flags: --show-branches=count
+   LL|       |
+   LL|       |macro_rules! no_merge {
+   LL|       |    () => {
+   LL|       |        for _ in 0..1 {}
+   LL|       |    };
+   LL|       |}
+   LL|       |
+   LL|      4|fn branch_match_guard(x: Option<u32>) {
+   LL|      4|    no_merge!();
+   LL|       |
+   LL|      1|    match x {
+   LL|      1|        Some(0) => {
+   LL|      1|            println!("zero");
+   LL|      1|        }
+   LL|      3|        Some(x) if x % 2 == 0 => {
+                           ^2
+  ------------------
+  |  Branch (LL:20): [True: 2, False: 1]
+  ------------------
+   LL|      2|            println!("is nonzero and even");
+   LL|      2|        }
+   LL|      1|        Some(x) if x % 3 == 0 => {
+  ------------------
+  |  Branch (LL:20): [True: 1, False: 0]
+  ------------------
+   LL|      1|            println!("is nonzero and odd, but divisible by 3");
+   LL|      1|        }
+   LL|      0|        _ => {
+   LL|      0|            println!("something else");
+   LL|      0|        }
+   LL|       |    }
+   LL|      4|}
+   LL|       |
+   LL|       |#[coverage(off)]
+   LL|       |fn main() {
+   LL|       |    branch_match_guard(Some(0));
+   LL|       |    branch_match_guard(Some(2));
+   LL|       |    branch_match_guard(Some(6));
+   LL|       |    branch_match_guard(Some(3));
+   LL|       |}
+
diff --git a/tests/coverage/branch_guard.rs b/tests/coverage/branch_guard.rs
new file mode 100644
index 00000000000..fa049e6206d
--- /dev/null
+++ b/tests/coverage/branch_guard.rs
@@ -0,0 +1,37 @@
+#![feature(coverage_attribute)]
+//@ edition: 2021
+//@ compile-flags: -Zcoverage-options=branch
+//@ llvm-cov-flags: --show-branches=count
+
+macro_rules! no_merge {
+    () => {
+        for _ in 0..1 {}
+    };
+}
+
+fn branch_match_guard(x: Option<u32>) {
+    no_merge!();
+
+    match x {
+        Some(0) => {
+            println!("zero");
+        }
+        Some(x) if x % 2 == 0 => {
+            println!("is nonzero and even");
+        }
+        Some(x) if x % 3 == 0 => {
+            println!("is nonzero and odd, but divisible by 3");
+        }
+        _ => {
+            println!("something else");
+        }
+    }
+}
+
+#[coverage(off)]
+fn main() {
+    branch_match_guard(Some(0));
+    branch_match_guard(Some(2));
+    branch_match_guard(Some(6));
+    branch_match_guard(Some(3));
+}
diff --git a/tests/coverage/branch_if.cov-map b/tests/coverage/branch_if.cov-map
new file mode 100644
index 00000000000..0dbfd92541b
--- /dev/null
+++ b/tests/coverage/branch_if.cov-map
@@ -0,0 +1,188 @@
+Function name: branch_if::branch_and
+Raw bytes (56): 0x[01, 01, 04, 05, 09, 0d, 02, 11, 0f, 0d, 02, 08, 01, 2b, 01, 01, 10, 05, 03, 08, 00, 09, 20, 09, 02, 00, 08, 00, 09, 09, 00, 0d, 00, 0e, 20, 11, 0d, 00, 0d, 00, 0e, 11, 00, 0f, 02, 06, 0f, 02, 0c, 02, 06, 0b, 03, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 4
+- expression 0 operands: lhs = Counter(1), rhs = Counter(2)
+- expression 1 operands: lhs = Counter(3), rhs = Expression(0, Sub)
+- expression 2 operands: lhs = Counter(4), rhs = Expression(3, Add)
+- expression 3 operands: lhs = Counter(3), rhs = Expression(0, Sub)
+Number of file 0 mappings: 8
+- Code(Counter(0)) at (prev + 43, 1) to (start + 1, 16)
+- Code(Counter(1)) at (prev + 3, 8) to (start + 0, 9)
+- Branch { true: Counter(2), false: Expression(0, Sub) } at (prev + 0, 8) to (start + 0, 9)
+    true  = c2
+    false = (c1 - c2)
+- Code(Counter(2)) at (prev + 0, 13) to (start + 0, 14)
+- Branch { true: Counter(4), false: Counter(3) } at (prev + 0, 13) to (start + 0, 14)
+    true  = c4
+    false = c3
+- Code(Counter(4)) at (prev + 0, 15) to (start + 2, 6)
+- Code(Expression(3, Add)) at (prev + 2, 12) to (start + 2, 6)
+    = (c3 + (c1 - c2))
+- Code(Expression(2, Add)) at (prev + 3, 1) to (start + 0, 2)
+    = (c4 + (c3 + (c1 - c2)))
+
+Function name: branch_if::branch_not
+Raw bytes (224): 0x[01, 01, 29, 05, 09, 09, 02, a3, 01, 0d, 09, 02, a3, 01, 0d, 09, 02, 0d, 9e, 01, a3, 01, 0d, 09, 02, 9b, 01, 11, 0d, 9e, 01, a3, 01, 0d, 09, 02, 9b, 01, 11, 0d, 9e, 01, a3, 01, 0d, 09, 02, 11, 96, 01, 9b, 01, 11, 0d, 9e, 01, a3, 01, 0d, 09, 02, 93, 01, 15, 11, 96, 01, 9b, 01, 11, 0d, 9e, 01, a3, 01, 0d, 09, 02, 93, 01, 15, 11, 96, 01, 9b, 01, 11, 0d, 9e, 01, a3, 01, 0d, 09, 02, 15, 8e, 01, 93, 01, 15, 11, 96, 01, 9b, 01, 11, 0d, 9e, 01, a3, 01, 0d, 09, 02, 12, 01, 0c, 01, 01, 10, 05, 03, 08, 00, 09, 20, 09, 02, 00, 08, 00, 09, 09, 01, 09, 00, 11, 02, 01, 06, 00, 07, a3, 01, 01, 08, 00, 0a, 20, 9e, 01, 0d, 00, 08, 00, 0a, 9e, 01, 00, 0b, 02, 06, 0d, 02, 06, 00, 07, 9b, 01, 01, 08, 00, 0b, 20, 11, 96, 01, 00, 08, 00, 0b, 11, 00, 0c, 02, 06, 96, 01, 02, 06, 00, 07, 93, 01, 01, 08, 00, 0c, 20, 8e, 01, 15, 00, 08, 00, 0c, 8e, 01, 00, 0d, 02, 06, 15, 02, 06, 00, 07, 8b, 01, 01, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 41
+- expression 0 operands: lhs = Counter(1), rhs = Counter(2)
+- expression 1 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 2 operands: lhs = Expression(40, Add), rhs = Counter(3)
+- expression 3 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 4 operands: lhs = Expression(40, Add), rhs = Counter(3)
+- expression 5 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 6 operands: lhs = Counter(3), rhs = Expression(39, Sub)
+- expression 7 operands: lhs = Expression(40, Add), rhs = Counter(3)
+- expression 8 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 9 operands: lhs = Expression(38, Add), rhs = Counter(4)
+- expression 10 operands: lhs = Counter(3), rhs = Expression(39, Sub)
+- expression 11 operands: lhs = Expression(40, Add), rhs = Counter(3)
+- expression 12 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 13 operands: lhs = Expression(38, Add), rhs = Counter(4)
+- expression 14 operands: lhs = Counter(3), rhs = Expression(39, Sub)
+- expression 15 operands: lhs = Expression(40, Add), rhs = Counter(3)
+- expression 16 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 17 operands: lhs = Counter(4), rhs = Expression(37, Sub)
+- expression 18 operands: lhs = Expression(38, Add), rhs = Counter(4)
+- expression 19 operands: lhs = Counter(3), rhs = Expression(39, Sub)
+- expression 20 operands: lhs = Expression(40, Add), rhs = Counter(3)
+- expression 21 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 22 operands: lhs = Expression(36, Add), rhs = Counter(5)
+- expression 23 operands: lhs = Counter(4), rhs = Expression(37, Sub)
+- expression 24 operands: lhs = Expression(38, Add), rhs = Counter(4)
+- expression 25 operands: lhs = Counter(3), rhs = Expression(39, Sub)
+- expression 26 operands: lhs = Expression(40, Add), rhs = Counter(3)
+- expression 27 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 28 operands: lhs = Expression(36, Add), rhs = Counter(5)
+- expression 29 operands: lhs = Counter(4), rhs = Expression(37, Sub)
+- expression 30 operands: lhs = Expression(38, Add), rhs = Counter(4)
+- expression 31 operands: lhs = Counter(3), rhs = Expression(39, Sub)
+- expression 32 operands: lhs = Expression(40, Add), rhs = Counter(3)
+- expression 33 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 34 operands: lhs = Counter(5), rhs = Expression(35, Sub)
+- expression 35 operands: lhs = Expression(36, Add), rhs = Counter(5)
+- expression 36 operands: lhs = Counter(4), rhs = Expression(37, Sub)
+- expression 37 operands: lhs = Expression(38, Add), rhs = Counter(4)
+- expression 38 operands: lhs = Counter(3), rhs = Expression(39, Sub)
+- expression 39 operands: lhs = Expression(40, Add), rhs = Counter(3)
+- expression 40 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+Number of file 0 mappings: 18
+- Code(Counter(0)) at (prev + 12, 1) to (start + 1, 16)
+- Code(Counter(1)) at (prev + 3, 8) to (start + 0, 9)
+- Branch { true: Counter(2), false: Expression(0, Sub) } at (prev + 0, 8) to (start + 0, 9)
+    true  = c2
+    false = (c1 - c2)
+- Code(Counter(2)) at (prev + 1, 9) to (start + 0, 17)
+- Code(Expression(0, Sub)) at (prev + 1, 6) to (start + 0, 7)
+    = (c1 - c2)
+- Code(Expression(40, Add)) at (prev + 1, 8) to (start + 0, 10)
+    = (c2 + (c1 - c2))
+- Branch { true: Expression(39, Sub), false: Counter(3) } at (prev + 0, 8) to (start + 0, 10)
+    true  = ((c2 + (c1 - c2)) - c3)
+    false = c3
+- Code(Expression(39, Sub)) at (prev + 0, 11) to (start + 2, 6)
+    = ((c2 + (c1 - c2)) - c3)
+- Code(Counter(3)) at (prev + 2, 6) to (start + 0, 7)
+- Code(Expression(38, Add)) at (prev + 1, 8) to (start + 0, 11)
+    = (c3 + ((c2 + (c1 - c2)) - c3))
+- Branch { true: Counter(4), false: Expression(37, Sub) } at (prev + 0, 8) to (start + 0, 11)
+    true  = c4
+    false = ((c3 + ((c2 + (c1 - c2)) - c3)) - c4)
+- Code(Counter(4)) at (prev + 0, 12) to (start + 2, 6)
+- Code(Expression(37, Sub)) at (prev + 2, 6) to (start + 0, 7)
+    = ((c3 + ((c2 + (c1 - c2)) - c3)) - c4)
+- Code(Expression(36, Add)) at (prev + 1, 8) to (start + 0, 12)
+    = (c4 + ((c3 + ((c2 + (c1 - c2)) - c3)) - c4))
+- Branch { true: Expression(35, Sub), false: Counter(5) } at (prev + 0, 8) to (start + 0, 12)
+    true  = ((c4 + ((c3 + ((c2 + (c1 - c2)) - c3)) - c4)) - c5)
+    false = c5
+- Code(Expression(35, Sub)) at (prev + 0, 13) to (start + 2, 6)
+    = ((c4 + ((c3 + ((c2 + (c1 - c2)) - c3)) - c4)) - c5)
+- Code(Counter(5)) at (prev + 2, 6) to (start + 0, 7)
+- Code(Expression(34, Add)) at (prev + 1, 1) to (start + 0, 2)
+    = (c5 + ((c4 + ((c3 + ((c2 + (c1 - c2)) - c3)) - c4)) - c5))
+
+Function name: branch_if::branch_not_as
+Raw bytes (124): 0x[01, 01, 16, 05, 09, 09, 02, 57, 0d, 09, 02, 57, 0d, 09, 02, 0d, 52, 57, 0d, 09, 02, 4f, 11, 0d, 52, 57, 0d, 09, 02, 4f, 11, 0d, 52, 57, 0d, 09, 02, 11, 4a, 4f, 11, 0d, 52, 57, 0d, 09, 02, 0e, 01, 1d, 01, 01, 10, 05, 03, 08, 00, 14, 20, 02, 09, 00, 08, 00, 14, 02, 00, 15, 02, 06, 09, 02, 06, 00, 07, 57, 01, 08, 00, 15, 20, 0d, 52, 00, 08, 00, 15, 0d, 00, 16, 02, 06, 52, 02, 06, 00, 07, 4f, 01, 08, 00, 16, 20, 4a, 11, 00, 08, 00, 16, 4a, 00, 17, 02, 06, 11, 02, 06, 00, 07, 47, 01, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 22
+- expression 0 operands: lhs = Counter(1), rhs = Counter(2)
+- expression 1 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 2 operands: lhs = Expression(21, Add), rhs = Counter(3)
+- expression 3 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 4 operands: lhs = Expression(21, Add), rhs = Counter(3)
+- expression 5 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 6 operands: lhs = Counter(3), rhs = Expression(20, Sub)
+- expression 7 operands: lhs = Expression(21, Add), rhs = Counter(3)
+- expression 8 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 9 operands: lhs = Expression(19, Add), rhs = Counter(4)
+- expression 10 operands: lhs = Counter(3), rhs = Expression(20, Sub)
+- expression 11 operands: lhs = Expression(21, Add), rhs = Counter(3)
+- expression 12 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 13 operands: lhs = Expression(19, Add), rhs = Counter(4)
+- expression 14 operands: lhs = Counter(3), rhs = Expression(20, Sub)
+- expression 15 operands: lhs = Expression(21, Add), rhs = Counter(3)
+- expression 16 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+- expression 17 operands: lhs = Counter(4), rhs = Expression(18, Sub)
+- expression 18 operands: lhs = Expression(19, Add), rhs = Counter(4)
+- expression 19 operands: lhs = Counter(3), rhs = Expression(20, Sub)
+- expression 20 operands: lhs = Expression(21, Add), rhs = Counter(3)
+- expression 21 operands: lhs = Counter(2), rhs = Expression(0, Sub)
+Number of file 0 mappings: 14
+- Code(Counter(0)) at (prev + 29, 1) to (start + 1, 16)
+- Code(Counter(1)) at (prev + 3, 8) to (start + 0, 20)
+- Branch { true: Expression(0, Sub), false: Counter(2) } at (prev + 0, 8) to (start + 0, 20)
+    true  = (c1 - c2)
+    false = c2
+- Code(Expression(0, Sub)) at (prev + 0, 21) to (start + 2, 6)
+    = (c1 - c2)
+- Code(Counter(2)) at (prev + 2, 6) to (start + 0, 7)
+- Code(Expression(21, Add)) at (prev + 1, 8) to (start + 0, 21)
+    = (c2 + (c1 - c2))
+- Branch { true: Counter(3), false: Expression(20, Sub) } at (prev + 0, 8) to (start + 0, 21)
+    true  = c3
+    false = ((c2 + (c1 - c2)) - c3)
+- Code(Counter(3)) at (prev + 0, 22) to (start + 2, 6)
+- Code(Expression(20, Sub)) at (prev + 2, 6) to (start + 0, 7)
+    = ((c2 + (c1 - c2)) - c3)
+- Code(Expression(19, Add)) at (prev + 1, 8) to (start + 0, 22)
+    = (c3 + ((c2 + (c1 - c2)) - c3))
+- Branch { true: Expression(18, Sub), false: Counter(4) } at (prev + 0, 8) to (start + 0, 22)
+    true  = ((c3 + ((c2 + (c1 - c2)) - c3)) - c4)
+    false = c4
+- Code(Expression(18, Sub)) at (prev + 0, 23) to (start + 2, 6)
+    = ((c3 + ((c2 + (c1 - c2)) - c3)) - c4)
+- Code(Counter(4)) at (prev + 2, 6) to (start + 0, 7)
+- Code(Expression(17, Add)) at (prev + 1, 1) to (start + 0, 2)
+    = (c4 + ((c3 + ((c2 + (c1 - c2)) - c3)) - c4))
+
+Function name: branch_if::branch_or
+Raw bytes (56): 0x[01, 01, 04, 05, 09, 09, 0d, 0f, 11, 09, 0d, 08, 01, 35, 01, 01, 10, 05, 03, 08, 00, 09, 20, 09, 02, 00, 08, 00, 09, 02, 00, 0d, 00, 0e, 20, 0d, 11, 00, 0d, 00, 0e, 0f, 00, 0f, 02, 06, 11, 02, 0c, 02, 06, 0b, 03, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 4
+- expression 0 operands: lhs = Counter(1), rhs = Counter(2)
+- expression 1 operands: lhs = Counter(2), rhs = Counter(3)
+- expression 2 operands: lhs = Expression(3, Add), rhs = Counter(4)
+- expression 3 operands: lhs = Counter(2), rhs = Counter(3)
+Number of file 0 mappings: 8
+- Code(Counter(0)) at (prev + 53, 1) to (start + 1, 16)
+- Code(Counter(1)) at (prev + 3, 8) to (start + 0, 9)
+- Branch { true: Counter(2), false: Expression(0, Sub) } at (prev + 0, 8) to (start + 0, 9)
+    true  = c2
+    false = (c1 - c2)
+- Code(Expression(0, Sub)) at (prev + 0, 13) to (start + 0, 14)
+    = (c1 - c2)
+- Branch { true: Counter(3), false: Counter(4) } at (prev + 0, 13) to (start + 0, 14)
+    true  = c3
+    false = c4
+- Code(Expression(3, Add)) at (prev + 0, 15) to (start + 2, 6)
+    = (c2 + c3)
+- Code(Counter(4)) at (prev + 2, 12) to (start + 2, 6)
+- Code(Expression(2, Add)) at (prev + 3, 1) to (start + 0, 2)
+    = ((c2 + c3) + c4)
+
diff --git a/tests/coverage/branch_if.coverage b/tests/coverage/branch_if.coverage
new file mode 100644
index 00000000000..2a9a408b16a
--- /dev/null
+++ b/tests/coverage/branch_if.coverage
@@ -0,0 +1,115 @@
+   LL|       |#![feature(coverage_attribute)]
+   LL|       |//@ edition: 2021
+   LL|       |//@ compile-flags: -Zcoverage-options=branch
+   LL|       |//@ llvm-cov-flags: --show-branches=count
+   LL|       |
+   LL|       |macro_rules! no_merge {
+   LL|       |    () => {
+   LL|       |        for _ in 0..1 {}
+   LL|       |    };
+   LL|       |}
+   LL|       |
+   LL|      3|fn branch_not(a: bool) {
+   LL|      3|    no_merge!();
+   LL|       |
+   LL|      3|    if a {
+  ------------------
+  |  Branch (LL:8): [True: 2, False: 1]
+  ------------------
+   LL|      2|        say("a")
+   LL|      1|    }
+   LL|      3|    if !a {
+  ------------------
+  |  Branch (LL:8): [True: 1, False: 2]
+  ------------------
+   LL|      1|        say("not a");
+   LL|      2|    }
+   LL|      3|    if !!a {
+  ------------------
+  |  Branch (LL:8): [True: 2, False: 1]
+  ------------------
+   LL|      2|        say("not not a");
+   LL|      2|    }
+                   ^1
+   LL|      3|    if !!!a {
+  ------------------
+  |  Branch (LL:8): [True: 1, False: 2]
+  ------------------
+   LL|      1|        say("not not not a");
+   LL|      2|    }
+   LL|      3|}
+   LL|       |
+   LL|      3|fn branch_not_as(a: bool) {
+   LL|      3|    no_merge!();
+   LL|       |
+   LL|      3|    if !(a as bool) {
+  ------------------
+  |  Branch (LL:8): [True: 1, False: 2]
+  ------------------
+   LL|      1|        say("not (a as bool)");
+   LL|      2|    }
+   LL|      3|    if !!(a as bool) {
+  ------------------
+  |  Branch (LL:8): [True: 2, False: 1]
+  ------------------
+   LL|      2|        say("not not (a as bool)");
+   LL|      2|    }
+                   ^1
+   LL|      3|    if !!!(a as bool) {
+  ------------------
+  |  Branch (LL:8): [True: 1, False: 2]
+  ------------------
+   LL|      1|        say("not not (a as bool)");
+   LL|      2|    }
+   LL|      3|}
+   LL|       |
+   LL|     15|fn branch_and(a: bool, b: bool) {
+   LL|     15|    no_merge!();
+   LL|       |
+   LL|     15|    if a && b {
+                          ^12
+  ------------------
+  |  Branch (LL:8): [True: 12, False: 3]
+  |  Branch (LL:13): [True: 8, False: 4]
+  ------------------
+   LL|      8|        say("both");
+   LL|      8|    } else {
+   LL|      7|        say("not both");
+   LL|      7|    }
+   LL|     15|}
+   LL|       |
+   LL|     15|fn branch_or(a: bool, b: bool) {
+   LL|     15|    no_merge!();
+   LL|       |
+   LL|     15|    if a || b {
+                          ^3
+  ------------------
+  |  Branch (LL:8): [True: 12, False: 3]
+  |  Branch (LL:13): [True: 2, False: 1]
+  ------------------
+   LL|     14|        say("either");
+   LL|     14|    } else {
+   LL|      1|        say("neither");
+   LL|      1|    }
+   LL|     15|}
+   LL|       |
+   LL|       |#[coverage(off)]
+   LL|       |fn say(message: &str) {
+   LL|       |    core::hint::black_box(message);
+   LL|       |}
+   LL|       |
+   LL|       |#[coverage(off)]
+   LL|       |fn main() {
+   LL|       |    for a in [false, true, true] {
+   LL|       |        branch_not(a);
+   LL|       |        branch_not_as(a);
+   LL|       |    }
+   LL|       |
+   LL|       |    for a in [false, true, true, true, true] {
+   LL|       |        for b in [false, true, true] {
+   LL|       |            branch_and(a, b);
+   LL|       |            branch_or(a, b);
+   LL|       |        }
+   LL|       |    }
+   LL|       |}
+
diff --git a/tests/coverage/branch_if.rs b/tests/coverage/branch_if.rs
new file mode 100644
index 00000000000..151eede75bb
--- /dev/null
+++ b/tests/coverage/branch_if.rs
@@ -0,0 +1,81 @@
+#![feature(coverage_attribute)]
+//@ edition: 2021
+//@ compile-flags: -Zcoverage-options=branch
+//@ llvm-cov-flags: --show-branches=count
+
+macro_rules! no_merge {
+    () => {
+        for _ in 0..1 {}
+    };
+}
+
+fn branch_not(a: bool) {
+    no_merge!();
+
+    if a {
+        say("a")
+    }
+    if !a {
+        say("not a");
+    }
+    if !!a {
+        say("not not a");
+    }
+    if !!!a {
+        say("not not not a");
+    }
+}
+
+fn branch_not_as(a: bool) {
+    no_merge!();
+
+    if !(a as bool) {
+        say("not (a as bool)");
+    }
+    if !!(a as bool) {
+        say("not not (a as bool)");
+    }
+    if !!!(a as bool) {
+        say("not not (a as bool)");
+    }
+}
+
+fn branch_and(a: bool, b: bool) {
+    no_merge!();
+
+    if a && b {
+        say("both");
+    } else {
+        say("not both");
+    }
+}
+
+fn branch_or(a: bool, b: bool) {
+    no_merge!();
+
+    if a || b {
+        say("either");
+    } else {
+        say("neither");
+    }
+}
+
+#[coverage(off)]
+fn say(message: &str) {
+    core::hint::black_box(message);
+}
+
+#[coverage(off)]
+fn main() {
+    for a in [false, true, true] {
+        branch_not(a);
+        branch_not_as(a);
+    }
+
+    for a in [false, true, true, true, true] {
+        for b in [false, true, true] {
+            branch_and(a, b);
+            branch_or(a, b);
+        }
+    }
+}
diff --git a/tests/coverage/branch_while.cov-map b/tests/coverage/branch_while.cov-map
new file mode 100644
index 00000000000..d5f54f1abea
--- /dev/null
+++ b/tests/coverage/branch_while.cov-map
@@ -0,0 +1,98 @@
+Function name: branch_while::while_cond
+Raw bytes (42): 0x[01, 01, 03, 05, 09, 03, 09, 03, 09, 06, 01, 0c, 01, 01, 10, 05, 03, 09, 00, 12, 03, 01, 0b, 00, 10, 20, 09, 0a, 00, 0b, 00, 10, 09, 00, 11, 02, 06, 0a, 03, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 3
+- expression 0 operands: lhs = Counter(1), rhs = Counter(2)
+- expression 1 operands: lhs = Expression(0, Add), rhs = Counter(2)
+- expression 2 operands: lhs = Expression(0, Add), rhs = Counter(2)
+Number of file 0 mappings: 6
+- Code(Counter(0)) at (prev + 12, 1) to (start + 1, 16)
+- Code(Counter(1)) at (prev + 3, 9) to (start + 0, 18)
+- Code(Expression(0, Add)) at (prev + 1, 11) to (start + 0, 16)
+    = (c1 + c2)
+- Branch { true: Counter(2), false: Expression(2, Sub) } at (prev + 0, 11) to (start + 0, 16)
+    true  = c2
+    false = ((c1 + c2) - c2)
+- Code(Counter(2)) at (prev + 0, 17) to (start + 2, 6)
+- Code(Expression(2, Sub)) at (prev + 3, 1) to (start + 0, 2)
+    = ((c1 + c2) - c2)
+
+Function name: branch_while::while_cond_not
+Raw bytes (42): 0x[01, 01, 03, 05, 09, 03, 09, 03, 09, 06, 01, 15, 01, 01, 10, 05, 03, 09, 00, 12, 03, 01, 0b, 00, 14, 20, 09, 0a, 00, 0b, 00, 14, 09, 00, 15, 02, 06, 0a, 03, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 3
+- expression 0 operands: lhs = Counter(1), rhs = Counter(2)
+- expression 1 operands: lhs = Expression(0, Add), rhs = Counter(2)
+- expression 2 operands: lhs = Expression(0, Add), rhs = Counter(2)
+Number of file 0 mappings: 6
+- Code(Counter(0)) at (prev + 21, 1) to (start + 1, 16)
+- Code(Counter(1)) at (prev + 3, 9) to (start + 0, 18)
+- Code(Expression(0, Add)) at (prev + 1, 11) to (start + 0, 20)
+    = (c1 + c2)
+- Branch { true: Counter(2), false: Expression(2, Sub) } at (prev + 0, 11) to (start + 0, 20)
+    true  = c2
+    false = ((c1 + c2) - c2)
+- Code(Counter(2)) at (prev + 0, 21) to (start + 2, 6)
+- Code(Expression(2, Sub)) at (prev + 3, 1) to (start + 0, 2)
+    = ((c1 + c2) - c2)
+
+Function name: branch_while::while_op_and
+Raw bytes (56): 0x[01, 01, 04, 05, 09, 03, 0d, 03, 0d, 11, 0d, 08, 01, 1e, 01, 01, 10, 05, 03, 09, 01, 12, 03, 02, 0b, 00, 10, 20, 0a, 0d, 00, 0b, 00, 10, 0a, 00, 14, 00, 19, 20, 09, 11, 00, 14, 00, 19, 09, 00, 1a, 03, 06, 0f, 04, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 4
+- expression 0 operands: lhs = Counter(1), rhs = Counter(2)
+- expression 1 operands: lhs = Expression(0, Add), rhs = Counter(3)
+- expression 2 operands: lhs = Expression(0, Add), rhs = Counter(3)
+- expression 3 operands: lhs = Counter(4), rhs = Counter(3)
+Number of file 0 mappings: 8
+- Code(Counter(0)) at (prev + 30, 1) to (start + 1, 16)
+- Code(Counter(1)) at (prev + 3, 9) to (start + 1, 18)
+- Code(Expression(0, Add)) at (prev + 2, 11) to (start + 0, 16)
+    = (c1 + c2)
+- Branch { true: Expression(2, Sub), false: Counter(3) } at (prev + 0, 11) to (start + 0, 16)
+    true  = ((c1 + c2) - c3)
+    false = c3
+- Code(Expression(2, Sub)) at (prev + 0, 20) to (start + 0, 25)
+    = ((c1 + c2) - c3)
+- Branch { true: Counter(2), false: Counter(4) } at (prev + 0, 20) to (start + 0, 25)
+    true  = c2
+    false = c4
+- Code(Counter(2)) at (prev + 0, 26) to (start + 3, 6)
+- Code(Expression(3, Add)) at (prev + 4, 1) to (start + 0, 2)
+    = (c4 + c3)
+
+Function name: branch_while::while_op_or
+Raw bytes (66): 0x[01, 01, 09, 05, 1b, 09, 0d, 03, 09, 03, 09, 22, 0d, 03, 09, 09, 0d, 22, 0d, 03, 09, 08, 01, 29, 01, 01, 10, 05, 03, 09, 01, 12, 03, 02, 0b, 00, 10, 20, 09, 22, 00, 0b, 00, 10, 22, 00, 14, 00, 19, 20, 0d, 1e, 00, 14, 00, 19, 1b, 00, 1a, 03, 06, 1e, 04, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 9
+- expression 0 operands: lhs = Counter(1), rhs = Expression(6, Add)
+- expression 1 operands: lhs = Counter(2), rhs = Counter(3)
+- expression 2 operands: lhs = Expression(0, Add), rhs = Counter(2)
+- expression 3 operands: lhs = Expression(0, Add), rhs = Counter(2)
+- expression 4 operands: lhs = Expression(8, Sub), rhs = Counter(3)
+- expression 5 operands: lhs = Expression(0, Add), rhs = Counter(2)
+- expression 6 operands: lhs = Counter(2), rhs = Counter(3)
+- expression 7 operands: lhs = Expression(8, Sub), rhs = Counter(3)
+- expression 8 operands: lhs = Expression(0, Add), rhs = Counter(2)
+Number of file 0 mappings: 8
+- Code(Counter(0)) at (prev + 41, 1) to (start + 1, 16)
+- Code(Counter(1)) at (prev + 3, 9) to (start + 1, 18)
+- Code(Expression(0, Add)) at (prev + 2, 11) to (start + 0, 16)
+    = (c1 + (c2 + c3))
+- Branch { true: Counter(2), false: Expression(8, Sub) } at (prev + 0, 11) to (start + 0, 16)
+    true  = c2
+    false = ((c1 + (c2 + c3)) - c2)
+- Code(Expression(8, Sub)) at (prev + 0, 20) to (start + 0, 25)
+    = ((c1 + (c2 + c3)) - c2)
+- Branch { true: Counter(3), false: Expression(7, Sub) } at (prev + 0, 20) to (start + 0, 25)
+    true  = c3
+    false = (((c1 + (c2 + c3)) - c2) - c3)
+- Code(Expression(6, Add)) at (prev + 0, 26) to (start + 3, 6)
+    = (c2 + c3)
+- Code(Expression(7, Sub)) at (prev + 4, 1) to (start + 0, 2)
+    = (((c1 + (c2 + c3)) - c2) - c3)
+
diff --git a/tests/coverage/branch_while.coverage b/tests/coverage/branch_while.coverage
new file mode 100644
index 00000000000..8d9a6c3bc68
--- /dev/null
+++ b/tests/coverage/branch_while.coverage
@@ -0,0 +1,74 @@
+   LL|       |#![feature(coverage_attribute)]
+   LL|       |//@ edition: 2021
+   LL|       |//@ compile-flags: -Zcoverage-options=branch
+   LL|       |//@ llvm-cov-flags: --show-branches=count
+   LL|       |
+   LL|       |macro_rules! no_merge {
+   LL|       |    () => {
+   LL|       |        for _ in 0..1 {}
+   LL|       |    };
+   LL|       |}
+   LL|       |
+   LL|      1|fn while_cond() {
+   LL|      1|    no_merge!();
+   LL|       |
+   LL|      1|    let mut a = 8;
+   LL|      9|    while a > 0 {
+  ------------------
+  |  Branch (LL:11): [True: 8, False: 1]
+  ------------------
+   LL|      8|        a -= 1;
+   LL|      8|    }
+   LL|      1|}
+   LL|       |
+   LL|      1|fn while_cond_not() {
+   LL|      1|    no_merge!();
+   LL|       |
+   LL|      1|    let mut a = 8;
+   LL|      9|    while !(a == 0) {
+  ------------------
+  |  Branch (LL:11): [True: 8, False: 1]
+  ------------------
+   LL|      8|        a -= 1;
+   LL|      8|    }
+   LL|      1|}
+   LL|       |
+   LL|      1|fn while_op_and() {
+   LL|      1|    no_merge!();
+   LL|       |
+   LL|      1|    let mut a = 8;
+   LL|      1|    let mut b = 4;
+   LL|      5|    while a > 0 && b > 0 {
+  ------------------
+  |  Branch (LL:11): [True: 5, False: 0]
+  |  Branch (LL:20): [True: 4, False: 1]
+  ------------------
+   LL|      4|        a -= 1;
+   LL|      4|        b -= 1;
+   LL|      4|    }
+   LL|      1|}
+   LL|       |
+   LL|      1|fn while_op_or() {
+   LL|      1|    no_merge!();
+   LL|       |
+   LL|      1|    let mut a = 4;
+   LL|      1|    let mut b = 8;
+   LL|      9|    while a > 0 || b > 0 {
+                                 ^5
+  ------------------
+  |  Branch (LL:11): [True: 4, False: 5]
+  |  Branch (LL:20): [True: 4, False: 1]
+  ------------------
+   LL|      8|        a -= 1;
+   LL|      8|        b -= 1;
+   LL|      8|    }
+   LL|      1|}
+   LL|       |
+   LL|       |#[coverage(off)]
+   LL|       |fn main() {
+   LL|       |    while_cond();
+   LL|       |    while_cond_not();
+   LL|       |    while_op_and();
+   LL|       |    while_op_or();
+   LL|       |}
+
diff --git a/tests/coverage/branch_while.rs b/tests/coverage/branch_while.rs
new file mode 100644
index 00000000000..507815fbecb
--- /dev/null
+++ b/tests/coverage/branch_while.rs
@@ -0,0 +1,58 @@
+#![feature(coverage_attribute)]
+//@ edition: 2021
+//@ compile-flags: -Zcoverage-options=branch
+//@ llvm-cov-flags: --show-branches=count
+
+macro_rules! no_merge {
+    () => {
+        for _ in 0..1 {}
+    };
+}
+
+fn while_cond() {
+    no_merge!();
+
+    let mut a = 8;
+    while a > 0 {
+        a -= 1;
+    }
+}
+
+fn while_cond_not() {
+    no_merge!();
+
+    let mut a = 8;
+    while !(a == 0) {
+        a -= 1;
+    }
+}
+
+fn while_op_and() {
+    no_merge!();
+
+    let mut a = 8;
+    let mut b = 4;
+    while a > 0 && b > 0 {
+        a -= 1;
+        b -= 1;
+    }
+}
+
+fn while_op_or() {
+    no_merge!();
+
+    let mut a = 4;
+    let mut b = 8;
+    while a > 0 || b > 0 {
+        a -= 1;
+        b -= 1;
+    }
+}
+
+#[coverage(off)]
+fn main() {
+    while_cond();
+    while_cond_not();
+    while_op_and();
+    while_op_or();
+}
diff --git a/tests/run-make/issue-88756-default-output/output-default.stdout b/tests/run-make/issue-88756-default-output/output-default.stdout
index 38a3965f0c5..12c1b389fb3 100644
--- a/tests/run-make/issue-88756-default-output/output-default.stdout
+++ b/tests/run-make/issue-88756-default-output/output-default.stdout
@@ -147,6 +147,8 @@ Options:
                         
         --test-builder PATH
                         The rustc-like binary to use as the test builder
+        --test-builder-wrapper PATH
+                        Wrapper program to pass test-builder and arguments
         --check         Run rustdoc checks
         --generate-redirect-map 
                         Generate JSON file at the top level instead of
diff --git a/tests/run-make/pdb-alt-path/Makefile b/tests/run-make/pdb-alt-path/Makefile
new file mode 100644
index 00000000000..7a0ae3bf2ef
--- /dev/null
+++ b/tests/run-make/pdb-alt-path/Makefile
@@ -0,0 +1,20 @@
+include ../tools.mk
+
+# only-windows-msvc
+
+all:
+	# Test that we don't have the full path to the PDB file in the binary
+	$(RUSTC) main.rs -g --crate-name my_crate_name --crate-type bin -Cforce-frame-pointers
+	$(CGREP) "my_crate_name.pdb" < $(TMPDIR)/my_crate_name.exe
+	$(CGREP) -v "\\my_crate_name.pdb" < $(TMPDIR)/my_crate_name.exe
+
+	# Test that backtraces still can find debuginfo by checking that they contain symbol names and
+	# source locations.
+	$(TMPDIR)/my_crate_name.exe &> $(TMPDIR)/backtrace.txt
+	$(CGREP) "my_crate_name::fn_in_backtrace" < $(TMPDIR)/backtrace.txt
+	$(CGREP) "main.rs:15" < $(TMPDIR)/backtrace.txt
+
+	# Test that explicitly passed `-Clink-arg=/PDBALTPATH:...` is respected
+	$(RUSTC) main.rs -g --crate-name my_crate_name --crate-type bin -Clink-arg=/PDBALTPATH:abcdefg.pdb -Cforce-frame-pointers
+	$(CGREP) "abcdefg.pdb" < $(TMPDIR)/my_crate_name.exe
+	$(CGREP) -v "my_crate_name.pdb" < $(TMPDIR)/my_crate_name.exe
diff --git a/tests/run-make/pdb-alt-path/main.rs b/tests/run-make/pdb-alt-path/main.rs
new file mode 100644
index 00000000000..d38d540fbc2
--- /dev/null
+++ b/tests/run-make/pdb-alt-path/main.rs
@@ -0,0 +1,24 @@
+// The various #[inline(never)] annotations and std::hint::black_box calls are
+// an attempt to make unwinding as non-flaky as possible on i686-pc-windows-msvc.
+
+#[inline(never)]
+fn generate_backtrace(x: &u32) {
+    std::hint::black_box(x);
+    let bt = std::backtrace::Backtrace::force_capture();
+    println!("{}", bt);
+    std::hint::black_box(x);
+}
+
+#[inline(never)]
+fn fn_in_backtrace(x: &u32) {
+    std::hint::black_box(x);
+    generate_backtrace(x);
+    std::hint::black_box(x);
+}
+
+fn main() {
+    let x = &41;
+    std::hint::black_box(x);
+    fn_in_backtrace(x);
+    std::hint::black_box(x);
+}
diff --git a/tests/rustdoc-js-std/parser-errors.js b/tests/rustdoc-js-std/parser-errors.js
index 16d171260da..ffd169812b6 100644
--- a/tests/rustdoc-js-std/parser-errors.js
+++ b/tests/rustdoc-js-std/parser-errors.js
@@ -114,7 +114,7 @@ const PARSED = [
         original: "(p -> p",
         returned: [],
         userQuery: "(p -> p",
-        error: "Unexpected `-` after `(`",
+        error: "Unclosed `(`",
     },
     {
         query: "::a::b",
@@ -195,7 +195,7 @@ const PARSED = [
         original: "a (b:",
         returned: [],
         userQuery: "a (b:",
-        error: "Expected `,`, `:` or `->`, found `(`",
+        error: "Unclosed `(`",
     },
     {
         query: "_:",
@@ -330,7 +330,7 @@ const PARSED = [
         original: 'a<->',
         returned: [],
         userQuery: 'a<->',
-        error: 'Unexpected `-` after `<`',
+        error: 'Unclosed `<`',
     },
     {
         query: "a<a>:",
@@ -357,7 +357,16 @@ const PARSED = [
         original: "a,:",
         returned: [],
         userQuery: "a,:",
-        error: 'Unexpected `,` in type filter (before `:`)',
+        error: 'Expected type filter before `:`',
+    },
+    {
+        query: "a!:",
+        elems: [],
+        foundElems: 0,
+        original: "a!:",
+        returned: [],
+        userQuery: "a!:",
+        error: 'Unexpected `!` in type filter (before `:`)',
     },
     {
         query: "  a<>  :",
@@ -366,7 +375,7 @@ const PARSED = [
         original: "a<>  :",
         returned: [],
         userQuery: "a<>  :",
-        error: 'Unexpected `<` in type filter (before `:`)',
+        error: 'Expected `,`, `:` or `->` after `>`, found `:`',
     },
     {
         query: "mod : :",
diff --git a/tests/rustdoc-js-std/parser-hof.js b/tests/rustdoc-js-std/parser-hof.js
new file mode 100644
index 00000000000..0b99c45b7a9
--- /dev/null
+++ b/tests/rustdoc-js-std/parser-hof.js
@@ -0,0 +1,712 @@
+const PARSED = [
+    // ML-style HOF
+    {
+        query: "(-> F<P>)",
+        elems: [{
+            name: "->",
+            fullPath: ["->"],
+            pathWithoutLast: [],
+            pathLast: "->",
+            generics: [],
+            bindings: [
+                [
+                    "output",
+                    [{
+                        name: "f",
+                        fullPath: ["f"],
+                        pathWithoutLast: [],
+                        pathLast: "f",
+                        generics: [
+                            {
+                                name: "p",
+                                fullPath: ["p"],
+                                pathWithoutLast: [],
+                                pathLast: "p",
+                                generics: [],
+                            },
+                        ],
+                        typeFilter: -1,
+                    }],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "(-> F<P>)",
+        returned: [],
+        userQuery: "(-> f<p>)",
+        error: null,
+    },
+    {
+        query: "(-> P)",
+        elems: [{
+            name: "->",
+            fullPath: ["->"],
+            pathWithoutLast: [],
+            pathLast: "->",
+            generics: [],
+            bindings: [
+                [
+                    "output",
+                    [{
+                        name: "p",
+                        fullPath: ["p"],
+                        pathWithoutLast: [],
+                        pathLast: "p",
+                        generics: [],
+                        typeFilter: -1,
+                    }],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "(-> P)",
+        returned: [],
+        userQuery: "(-> p)",
+        error: null,
+    },
+    {
+        query: "(->,a)",
+        elems: [{
+            name: "->",
+            fullPath: ["->"],
+            pathWithoutLast: [],
+            pathLast: "->",
+            generics: [],
+            bindings: [
+                [
+                    "output",
+                    [{
+                        name: "a",
+                        fullPath: ["a"],
+                        pathWithoutLast: [],
+                        pathLast: "a",
+                        generics: [],
+                        typeFilter: -1,
+                    }],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "(->,a)",
+        returned: [],
+        userQuery: "(->,a)",
+        error: null,
+    },
+    {
+        query: "(F<P> ->)",
+        elems: [{
+            name: "->",
+            fullPath: ["->"],
+            pathWithoutLast: [],
+            pathLast: "->",
+            generics: [{
+                name: "f",
+                fullPath: ["f"],
+                pathWithoutLast: [],
+                pathLast: "f",
+                generics: [
+                    {
+                        name: "p",
+                        fullPath: ["p"],
+                        pathWithoutLast: [],
+                        pathLast: "p",
+                        generics: [],
+                    },
+                ],
+                typeFilter: -1,
+            }],
+            bindings: [
+                [
+                    "output",
+                    [],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "(F<P> ->)",
+        returned: [],
+        userQuery: "(f<p> ->)",
+        error: null,
+    },
+    {
+        query: "(P ->)",
+        elems: [{
+            name: "->",
+            fullPath: ["->"],
+            pathWithoutLast: [],
+            pathLast: "->",
+            generics: [{
+                name: "p",
+                fullPath: ["p"],
+                pathWithoutLast: [],
+                pathLast: "p",
+                generics: [],
+                typeFilter: -1,
+            }],
+            bindings: [
+                [
+                    "output",
+                    [],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "(P ->)",
+        returned: [],
+        userQuery: "(p ->)",
+        error: null,
+    },
+    {
+        query: "(,a->)",
+        elems: [{
+            name: "->",
+            fullPath: ["->"],
+            pathWithoutLast: [],
+            pathLast: "->",
+            generics: [{
+                name: "a",
+                fullPath: ["a"],
+                pathWithoutLast: [],
+                pathLast: "a",
+                generics: [],
+                typeFilter: -1,
+            }],
+            bindings: [
+                [
+                    "output",
+                    [],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "(,a->)",
+        returned: [],
+        userQuery: "(,a->)",
+        error: null,
+    },
+    {
+        query: "(aaaaa->a)",
+        elems: [{
+            name: "->",
+            fullPath: ["->"],
+            pathWithoutLast: [],
+            pathLast: "->",
+            generics: [{
+                name: "aaaaa",
+                fullPath: ["aaaaa"],
+                pathWithoutLast: [],
+                pathLast: "aaaaa",
+                generics: [],
+                typeFilter: -1,
+            }],
+            bindings: [
+                [
+                    "output",
+                    [{
+                        name: "a",
+                        fullPath: ["a"],
+                        pathWithoutLast: [],
+                        pathLast: "a",
+                        generics: [],
+                        typeFilter: -1,
+                    }],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "(aaaaa->a)",
+        returned: [],
+        userQuery: "(aaaaa->a)",
+        error: null,
+    },
+    {
+        query: "(aaaaa, b -> a)",
+        elems: [{
+            name: "->",
+            fullPath: ["->"],
+            pathWithoutLast: [],
+            pathLast: "->",
+            generics: [
+                {
+                    name: "aaaaa",
+                    fullPath: ["aaaaa"],
+                    pathWithoutLast: [],
+                    pathLast: "aaaaa",
+                    generics: [],
+                    typeFilter: -1,
+                },
+                {
+                    name: "b",
+                    fullPath: ["b"],
+                    pathWithoutLast: [],
+                    pathLast: "b",
+                    generics: [],
+                    typeFilter: -1,
+                },
+            ],
+            bindings: [
+                [
+                    "output",
+                    [{
+                        name: "a",
+                        fullPath: ["a"],
+                        pathWithoutLast: [],
+                        pathLast: "a",
+                        generics: [],
+                        typeFilter: -1,
+                    }],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "(aaaaa, b -> a)",
+        returned: [],
+        userQuery: "(aaaaa, b -> a)",
+        error: null,
+    },
+    {
+        query: "primitive:(aaaaa, b -> a)",
+        elems: [{
+            name: "->",
+            fullPath: ["->"],
+            pathWithoutLast: [],
+            pathLast: "->",
+            generics: [
+                {
+                    name: "aaaaa",
+                    fullPath: ["aaaaa"],
+                    pathWithoutLast: [],
+                    pathLast: "aaaaa",
+                    generics: [],
+                    typeFilter: -1,
+                },
+                {
+                    name: "b",
+                    fullPath: ["b"],
+                    pathWithoutLast: [],
+                    pathLast: "b",
+                    generics: [],
+                    typeFilter: -1,
+                },
+            ],
+            bindings: [
+                [
+                    "output",
+                    [{
+                        name: "a",
+                        fullPath: ["a"],
+                        pathWithoutLast: [],
+                        pathLast: "a",
+                        generics: [],
+                        typeFilter: -1,
+                    }],
+                ],
+            ],
+            typeFilter: 1,
+        }],
+        foundElems: 1,
+        original: "primitive:(aaaaa, b -> a)",
+        returned: [],
+        userQuery: "primitive:(aaaaa, b -> a)",
+        error: null,
+    },
+    {
+        query: "x, trait:(aaaaa, b -> a)",
+        elems: [
+            {
+                name: "x",
+                fullPath: ["x"],
+                pathWithoutLast: [],
+                pathLast: "x",
+                generics: [],
+                typeFilter: -1,
+            },
+            {
+                name: "->",
+                fullPath: ["->"],
+                pathWithoutLast: [],
+                pathLast: "->",
+                generics: [
+                    {
+                        name: "aaaaa",
+                        fullPath: ["aaaaa"],
+                        pathWithoutLast: [],
+                        pathLast: "aaaaa",
+                        generics: [],
+                        typeFilter: -1,
+                    },
+                    {
+                        name: "b",
+                        fullPath: ["b"],
+                        pathWithoutLast: [],
+                        pathLast: "b",
+                        generics: [],
+                        typeFilter: -1,
+                    },
+                ],
+                bindings: [
+                    [
+                        "output",
+                        [{
+                            name: "a",
+                            fullPath: ["a"],
+                            pathWithoutLast: [],
+                            pathLast: "a",
+                            generics: [],
+                            typeFilter: -1,
+                        }],
+                    ],
+                ],
+                typeFilter: 10,
+            }
+        ],
+        foundElems: 2,
+        original: "x, trait:(aaaaa, b -> a)",
+        returned: [],
+        userQuery: "x, trait:(aaaaa, b -> a)",
+        error: null,
+    },
+    // Rust-style HOF
+    {
+        query: "Fn () -> F<P>",
+        elems: [{
+            name: "fn",
+            fullPath: ["fn"],
+            pathWithoutLast: [],
+            pathLast: "fn",
+            generics: [],
+            bindings: [
+                [
+                    "output",
+                    [{
+                        name: "f",
+                        fullPath: ["f"],
+                        pathWithoutLast: [],
+                        pathLast: "f",
+                        generics: [
+                            {
+                                name: "p",
+                                fullPath: ["p"],
+                                pathWithoutLast: [],
+                                pathLast: "p",
+                                generics: [],
+                            },
+                        ],
+                        typeFilter: -1,
+                    }],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "Fn () -> F<P>",
+        returned: [],
+        userQuery: "fn () -> f<p>",
+        error: null,
+    },
+    {
+        query: "FnMut() -> P",
+        elems: [{
+            name: "fnmut",
+            fullPath: ["fnmut"],
+            pathWithoutLast: [],
+            pathLast: "fnmut",
+            generics: [],
+            bindings: [
+                [
+                    "output",
+                    [{
+                        name: "p",
+                        fullPath: ["p"],
+                        pathWithoutLast: [],
+                        pathLast: "p",
+                        generics: [],
+                        typeFilter: -1,
+                    }],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "FnMut() -> P",
+        returned: [],
+        userQuery: "fnmut() -> p",
+        error: null,
+    },
+    {
+        query: "(FnMut() -> P)",
+        elems: [{
+            name: "fnmut",
+            fullPath: ["fnmut"],
+            pathWithoutLast: [],
+            pathLast: "fnmut",
+            generics: [],
+            bindings: [
+                [
+                    "output",
+                    [{
+                        name: "p",
+                        fullPath: ["p"],
+                        pathWithoutLast: [],
+                        pathLast: "p",
+                        generics: [],
+                        typeFilter: -1,
+                    }],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "(FnMut() -> P)",
+        returned: [],
+        userQuery: "(fnmut() -> p)",
+        error: null,
+    },
+    {
+        query: "Fn(F<P>)",
+        elems: [{
+            name: "fn",
+            fullPath: ["fn"],
+            pathWithoutLast: [],
+            pathLast: "fn",
+            generics: [{
+                name: "f",
+                fullPath: ["f"],
+                pathWithoutLast: [],
+                pathLast: "f",
+                generics: [
+                    {
+                        name: "p",
+                        fullPath: ["p"],
+                        pathWithoutLast: [],
+                        pathLast: "p",
+                        generics: [],
+                    },
+                ],
+                typeFilter: -1,
+            }],
+            bindings: [
+                [
+                    "output",
+                    [],
+                ],
+            ],
+            typeFilter: -1,
+        }],
+        foundElems: 1,
+        original: "Fn(F<P>)",
+        returned: [],
+        userQuery: "fn(f<p>)",
+        error: null,
+    },
+    {
+        query: "primitive:fnonce(aaaaa, b) -> a",
+        elems: [{
+            name: "fnonce",
+            fullPath: ["fnonce"],
+            pathWithoutLast: [],
+            pathLast: "fnonce",
+            generics: [
+                {
+                    name: "aaaaa",
+                    fullPath: ["aaaaa"],
+                    pathWithoutLast: [],
+                    pathLast: "aaaaa",
+                    generics: [],
+                    typeFilter: -1,
+                },
+                {
+                    name: "b",
+                    fullPath: ["b"],
+                    pathWithoutLast: [],
+                    pathLast: "b",
+                    generics: [],
+                    typeFilter: -1,
+                },
+            ],
+            bindings: [
+                [
+                    "output",
+                    [{
+                        name: "a",
+                        fullPath: ["a"],
+                        pathWithoutLast: [],
+                        pathLast: "a",
+                        generics: [],
+                        typeFilter: -1,
+                    }],
+                ],
+            ],
+            typeFilter: 1,
+        }],
+        foundElems: 1,
+        original: "primitive:fnonce(aaaaa, b) -> a",
+        returned: [],
+        userQuery: "primitive:fnonce(aaaaa, b) -> a",
+        error: null,
+    },
+    {
+        query: "primitive:fnonce(aaaaa, keyword:b) -> trait:a",
+        elems: [{
+            name: "fnonce",
+            fullPath: ["fnonce"],
+            pathWithoutLast: [],
+            pathLast: "fnonce",
+            generics: [
+                {
+                    name: "aaaaa",
+                    fullPath: ["aaaaa"],
+                    pathWithoutLast: [],
+                    pathLast: "aaaaa",
+                    generics: [],
+                    typeFilter: -1,
+                },
+                {
+                    name: "b",
+                    fullPath: ["b"],
+                    pathWithoutLast: [],
+                    pathLast: "b",
+                    generics: [],
+                    typeFilter: 0,
+                },
+            ],
+            bindings: [
+                [
+                    "output",
+                    [{
+                        name: "a",
+                        fullPath: ["a"],
+                        pathWithoutLast: [],
+                        pathLast: "a",
+                        generics: [],
+                        typeFilter: 10,
+                    }],
+                ],
+            ],
+            typeFilter: 1,
+        }],
+        foundElems: 1,
+        original: "primitive:fnonce(aaaaa, keyword:b) -> trait:a",
+        returned: [],
+        userQuery: "primitive:fnonce(aaaaa, keyword:b) -> trait:a",
+        error: null,
+    },
+    {
+        query: "x, trait:fn(aaaaa, b -> a)",
+        elems: [
+            {
+                name: "x",
+                fullPath: ["x"],
+                pathWithoutLast: [],
+                pathLast: "x",
+                generics: [],
+                typeFilter: -1,
+            },
+            {
+                name: "fn",
+                fullPath: ["fn"],
+                pathWithoutLast: [],
+                pathLast: "fn",
+                generics: [
+                    {
+                        name: "->",
+                        fullPath: ["->"],
+                        pathWithoutLast: [],
+                        pathLast: "->",
+                        generics: [
+                            {
+                                name: "aaaaa",
+                                fullPath: ["aaaaa"],
+                                pathWithoutLast: [],
+                                pathLast: "aaaaa",
+                                generics: [],
+                                typeFilter: -1,
+                            },
+                            {
+                                name: "b",
+                                fullPath: ["b"],
+                                pathWithoutLast: [],
+                                pathLast: "b",
+                                generics: [],
+                                typeFilter: -1,
+                            },
+                        ],
+                        bindings: [
+                            [
+                                "output",
+                                [{
+                                    name: "a",
+                                    fullPath: ["a"],
+                                    pathWithoutLast: [],
+                                    pathLast: "a",
+                                    generics: [],
+                                    typeFilter: -1,
+                                }],
+                            ],
+                        ],
+                        typeFilter: -1,
+                    },
+                ],
+                bindings: [
+                    [
+                        "output",
+                        [],
+                    ]
+                ],
+                typeFilter: 10,
+            }
+        ],
+        foundElems: 2,
+        original: "x, trait:fn(aaaaa, b -> a)",
+        returned: [],
+        userQuery: "x, trait:fn(aaaaa, b -> a)",
+        error: null,
+    },
+    {
+        query: 'a,b(c)',
+        elems: [
+            {
+                name: "a",
+                fullPath: ["a"],
+                pathWithoutLast: [],
+                pathLast: "a",
+                generics: [],
+                typeFilter: -1,
+            },
+            {
+                name: "b",
+                fullPath: ["b"],
+                pathWithoutLast: [],
+                pathLast: "b",
+                generics: [{
+                    name: "c",
+                    fullPath: ["c"],
+                    pathWithoutLast: [],
+                    pathLast: "c",
+                    generics: [],
+                    typeFilter: -1,
+                }],
+                bindings: [
+                    [
+                        "output",
+                        [],
+                    ]
+                ],
+                typeFilter: -1,
+            }
+        ],
+        foundElems: 2,
+        original: "a,b(c)",
+        returned: [],
+        userQuery: "a,b(c)",
+        error: null,
+    },
+];
diff --git a/tests/rustdoc-js-std/parser-weird-queries.js b/tests/rustdoc-js-std/parser-weird-queries.js
index 26b8c32d680..499b82a3469 100644
--- a/tests/rustdoc-js-std/parser-weird-queries.js
+++ b/tests/rustdoc-js-std/parser-weird-queries.js
@@ -38,15 +38,6 @@ const PARSED = [
         error: null,
     },
     {
-        query: 'a,b(c)',
-        elems: [],
-        foundElems: 0,
-        original: "a,b(c)",
-        returned: [],
-        userQuery: "a,b(c)",
-        error: "Expected `,`, `:` or `->`, found `(`",
-    },
-    {
         query: 'aaa,a',
         elems: [
             {
diff --git a/tests/rustdoc-js/auxiliary/interner.rs b/tests/rustdoc-js/auxiliary/interner.rs
new file mode 100644
index 00000000000..c95029be9f0
--- /dev/null
+++ b/tests/rustdoc-js/auxiliary/interner.rs
@@ -0,0 +1,245 @@
+#![feature(associated_type_defaults)]
+
+use std::cmp::Ord;
+use std::fmt::{Debug, Formatter};
+use std::hash::Hash;
+use std::ops::ControlFlow;
+
+pub trait Interner: Sized {
+    type DefId: Copy + Debug + Hash + Ord;
+    type AdtDef: Copy + Debug + Hash + Ord;
+    type GenericArgs: Copy
+        + DebugWithInfcx<Self>
+        + Hash
+        + Ord
+        + IntoIterator<Item = Self::GenericArg>;
+    type GenericArg: Copy + DebugWithInfcx<Self> + Hash + Ord;
+    type Term: Copy + Debug + Hash + Ord;
+    type Binder<T: TypeVisitable<Self>>: BoundVars<Self> + TypeSuperVisitable<Self>;
+    type BoundVars: IntoIterator<Item = Self::BoundVar>;
+    type BoundVar;
+    type CanonicalVars: Copy + Debug + Hash + Eq + IntoIterator<Item = CanonicalVarInfo<Self>>;
+    type Ty: Copy
+        + DebugWithInfcx<Self>
+        + Hash
+        + Ord
+        + Into<Self::GenericArg>
+        + IntoKind<Kind = TyKind<Self>>
+        + TypeSuperVisitable<Self>
+        + Flags
+        + Ty<Self>;
+    type Tys: Copy + Debug + Hash + Ord + IntoIterator<Item = Self::Ty>;
+    type AliasTy: Copy + DebugWithInfcx<Self> + Hash + Ord;
+    type ParamTy: Copy + Debug + Hash + Ord;
+    type BoundTy: Copy + Debug + Hash + Ord;
+    type PlaceholderTy: Copy + Debug + Hash + Ord + PlaceholderLike;
+    type ErrorGuaranteed: Copy + Debug + Hash + Ord;
+    type BoundExistentialPredicates: Copy + DebugWithInfcx<Self> + Hash + Ord;
+    type PolyFnSig: Copy + DebugWithInfcx<Self> + Hash + Ord;
+    type AllocId: Copy + Debug + Hash + Ord;
+    type Const: Copy
+        + DebugWithInfcx<Self>
+        + Hash
+        + Ord
+        + Into<Self::GenericArg>
+        + IntoKind<Kind = ConstKind<Self>>
+        + ConstTy<Self>
+        + TypeSuperVisitable<Self>
+        + Flags
+        + Const<Self>;
+    type AliasConst: Copy + DebugWithInfcx<Self> + Hash + Ord;
+    type PlaceholderConst: Copy + Debug + Hash + Ord + PlaceholderLike;
+    type ParamConst: Copy + Debug + Hash + Ord;
+    type BoundConst: Copy + Debug + Hash + Ord;
+    type ValueConst: Copy + Debug + Hash + Ord;
+    type ExprConst: Copy + DebugWithInfcx<Self> + Hash + Ord;
+    type Region: Copy
+        + DebugWithInfcx<Self>
+        + Hash
+        + Ord
+        + Into<Self::GenericArg>
+        + IntoKind<Kind = RegionKind<Self>>
+        + Flags
+        + Region<Self>;
+    type EarlyParamRegion: Copy + Debug + Hash + Ord;
+    type LateParamRegion: Copy + Debug + Hash + Ord;
+    type BoundRegion: Copy + Debug + Hash + Ord;
+    type InferRegion: Copy + DebugWithInfcx<Self> + Hash + Ord;
+    type PlaceholderRegion: Copy + Debug + Hash + Ord + PlaceholderLike;
+    type Predicate: Copy + Debug + Hash + Eq + TypeSuperVisitable<Self> + Flags;
+    type TraitPredicate: Copy + Debug + Hash + Eq;
+    type RegionOutlivesPredicate: Copy + Debug + Hash + Eq;
+    type TypeOutlivesPredicate: Copy + Debug + Hash + Eq;
+    type ProjectionPredicate: Copy + Debug + Hash + Eq;
+    type NormalizesTo: Copy + Debug + Hash + Eq;
+    type SubtypePredicate: Copy + Debug + Hash + Eq;
+    type CoercePredicate: Copy + Debug + Hash + Eq;
+    type ClosureKind: Copy + Debug + Hash + Eq;
+
+    // Required method
+    fn mk_canonical_var_infos(
+        self,
+        infos: &[CanonicalVarInfo<Self>]
+    ) -> Self::CanonicalVars;
+}
+
+pub trait DebugWithInfcx<I: Interner>: Debug {
+    // Required method
+    fn fmt<Infcx: InferCtxtLike<Interner = I>>(
+        this: WithInfcx<'_, Infcx, &Self>,
+        f: &mut Formatter<'_>
+    ) -> std::fmt::Result;
+}
+
+pub trait TypeVisitable<I: Interner>: Debug + Clone {
+    // Required method
+    fn visit_with<V: TypeVisitor<I>>(&self, visitor: &mut V) -> V::Result;
+}
+
+pub trait BoundVars<I: Interner> {
+    // Required methods
+    fn bound_vars(&self) -> I::BoundVars;
+    fn has_no_bound_vars(&self) -> bool;
+}
+
+pub trait TypeSuperVisitable<I: Interner>: TypeVisitable<I> {
+    // Required method
+    fn super_visit_with<V: TypeVisitor<I>>(&self, visitor: &mut V) -> V::Result;
+}
+
+pub struct CanonicalVarInfo<I: Interner> {
+    pub kind: CanonicalVarKind<I>,
+}
+
+pub struct CanonicalVarKind<I>(std::marker::PhantomData<I>);
+
+pub struct TyKind<I>(std::marker::PhantomData<I>);
+
+pub trait IntoKind {
+    type Kind;
+
+    // Required method
+    fn kind(self) -> Self::Kind;
+}
+pub trait Flags {
+    // Required methods
+    fn flags(&self) -> TypeFlags;
+    fn outer_exclusive_binder(&self) -> DebruijnIndex;
+}
+pub struct TypeFlags;
+
+pub trait Ty<I: Interner<Ty = Self>> {
+    // Required method
+    fn new_anon_bound(
+        interner: I,
+        debruijn: DebruijnIndex,
+        var: BoundVar
+    ) -> Self;
+}
+
+pub trait PlaceholderLike {
+    // Required methods
+    fn universe(self) -> UniverseIndex;
+    fn var(self) -> BoundVar;
+    fn with_updated_universe(self, ui: UniverseIndex) -> Self;
+    fn new(ui: UniverseIndex, var: BoundVar) -> Self;
+}
+
+pub struct UniverseIndex;
+
+pub struct BoundVar;
+
+pub struct ConstKind<I>(std::marker::PhantomData<I>);
+pub trait Const<I: Interner<Const = Self>> {
+    // Required method
+    fn new_anon_bound(
+        interner: I,
+        debruijn: DebruijnIndex,
+        var: BoundVar,
+        ty: I::Ty
+    ) -> Self;
+}
+
+pub trait ConstTy<I: Interner> {
+    // Required method
+    fn ty(self) -> I::Ty;
+}
+
+pub struct DebruijnIndex;
+
+pub struct RegionKind<I>(std::marker::PhantomData<I>);
+pub trait Region<I: Interner<Region = Self>> {
+    // Required method
+    fn new_anon_bound(
+        interner: I,
+        debruijn: DebruijnIndex,
+        var: BoundVar
+    ) -> Self;
+}
+
+pub trait TypeVisitor<I: Interner>: Sized {
+    type Result: VisitorResult = ();
+
+    // Provided methods
+    fn visit_binder<T: TypeVisitable<I>>(
+        &mut self,
+        t: &I::Binder<T>
+    ) -> Self::Result { unimplemented!() }
+    fn visit_ty(&mut self, t: I::Ty) -> Self::Result { unimplemented!() }
+    fn visit_region(&mut self, _r: I::Region) -> Self::Result { unimplemented!() }
+    fn visit_const(&mut self, c: I::Const) -> Self::Result { unimplemented!() }
+    fn visit_predicate(&mut self, p: I::Predicate) -> Self::Result { unimplemented!() }
+}
+
+pub trait VisitorResult {
+    type Residual;
+
+    // Required methods
+    fn output() -> Self;
+    fn from_residual(residual: Self::Residual) -> Self;
+    fn from_branch(b: ControlFlow<Self::Residual>) -> Self;
+    fn branch(self) -> ControlFlow<Self::Residual>;
+}
+
+impl VisitorResult for () {
+    type Residual = ();
+    fn output() -> Self {}
+    fn from_residual(_: Self::Residual) -> Self {}
+    fn from_branch(_: ControlFlow<Self::Residual>) -> Self {}
+    fn branch(self) -> ControlFlow<Self::Residual> { ControlFlow::Continue(()) }
+}
+
+pub struct WithInfcx<'a, Infcx: InferCtxtLike, T> {
+    pub data: T,
+    pub infcx: &'a Infcx,
+}
+
+pub trait InferCtxtLike {
+    type Interner: Interner;
+
+    // Required methods
+    fn interner(&self) -> Self::Interner;
+    fn universe_of_ty(&self, ty: TyVid) -> Option<UniverseIndex>;
+    fn root_ty_var(&self, vid: TyVid) -> TyVid;
+    fn probe_ty_var(
+        &self,
+        vid: TyVid
+    ) -> Option<<Self::Interner as Interner>::Ty>;
+    fn universe_of_lt(
+        &self,
+        lt: <Self::Interner as Interner>::InferRegion
+    ) -> Option<UniverseIndex>;
+    fn opportunistic_resolve_lt_var(
+        &self,
+        vid: <Self::Interner as Interner>::InferRegion
+    ) -> Option<<Self::Interner as Interner>::Region>;
+    fn universe_of_ct(&self, ct: ConstVid) -> Option<UniverseIndex>;
+    fn root_ct_var(&self, vid: ConstVid) -> ConstVid;
+    fn probe_ct_var(
+        &self,
+        vid: ConstVid
+    ) -> Option<<Self::Interner as Interner>::Const>;
+}
+
+pub struct TyVid;
+pub struct ConstVid;
diff --git a/tests/rustdoc-js/hof.js b/tests/rustdoc-js/hof.js
new file mode 100644
index 00000000000..5e6c9d83c7c
--- /dev/null
+++ b/tests/rustdoc-js/hof.js
@@ -0,0 +1,176 @@
+// exact-check
+
+const EXPECTED = [
+    // not a HOF query
+    {
+        'query': 'u32 -> !',
+        'others': [],
+    },
+
+    // ML-style higher-order function notation
+    {
+        'query': 'bool, (u32 -> !) -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_ptr"},
+        ],
+    },
+    {
+        'query': 'u8, (u32 -> !) -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_once"},
+        ],
+    },
+    {
+        'query': 'i8, (u32 -> !) -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_mut"},
+        ],
+    },
+    {
+        'query': 'char, (u32 -> !) -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_"},
+        ],
+    },
+    {
+        'query': '(first<u32> -> !) -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_ptr"},
+        ],
+    },
+    {
+        'query': '(second<u32> -> !) -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_once"},
+        ],
+    },
+    {
+        'query': '(third<u32> -> !) -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_mut"},
+        ],
+    },
+    {
+        'query': '(u32 -> !) -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_"},
+            {"path": "hof", "name": "fn_ptr"},
+            {"path": "hof", "name": "fn_mut"},
+            {"path": "hof", "name": "fn_once"},
+        ],
+    },
+    {
+        'query': '(str, str -> i8) -> ()',
+        'others': [
+            {"path": "hof", "name": "multiple"},
+        ],
+    },
+    {
+        'query': '(str ->) -> ()',
+        'others': [
+            {"path": "hof", "name": "multiple"},
+        ],
+    },
+    {
+        'query': '(-> i8) -> ()',
+        'others': [
+            {"path": "hof", "name": "multiple"},
+        ],
+    },
+    {
+        'query': '(str -> str) -> ()',
+        // params and return are not the same
+        'others': [],
+    },
+    {
+        'query': '(i8 ->) -> ()',
+        // params and return are not the same
+        'others': [],
+    },
+    {
+        'query': '(-> str) -> ()',
+        // params and return are not the same
+        'others': [],
+    },
+
+    // Rust-style higher-order function notation
+    {
+        'query': 'bool, fn(u32) -> ! -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_ptr"},
+        ],
+    },
+    {
+        'query': 'u8, fnonce(u32) -> ! -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_once"},
+        ],
+    },
+    {
+        'query': 'u8, fn(u32) -> ! -> ()',
+        // fnonce != fn
+        'others': [],
+    },
+    {
+        'query': 'i8, fnmut(u32) -> ! -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_mut"},
+        ],
+    },
+    {
+        'query': 'i8, fn(u32) -> ! -> ()',
+        // fnmut != fn
+        'others': [],
+    },
+    {
+        'query': 'char, fn(u32) -> ! -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_"},
+        ],
+    },
+    {
+        'query': 'char, fnmut(u32) -> ! -> ()',
+        // fn != fnmut
+        'others': [],
+    },
+    {
+        'query': 'fn(first<u32>) -> ! -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_ptr"},
+        ],
+    },
+    {
+        'query': 'fnonce(second<u32>) -> ! -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_once"},
+        ],
+    },
+    {
+        'query': 'fnmut(third<u32>) -> ! -> ()',
+        'others': [
+            {"path": "hof", "name": "fn_mut"},
+        ],
+    },
+    {
+        'query': 'fn(u32) -> ! -> ()',
+        'others': [
+            // fn matches primitive:fn and trait:Fn
+            {"path": "hof", "name": "fn_"},
+            {"path": "hof", "name": "fn_ptr"},
+        ],
+    },
+    {
+        'query': 'trait:fn(u32) -> ! -> ()',
+        'others': [
+            // fn matches primitive:fn and trait:Fn
+            {"path": "hof", "name": "fn_"},
+        ],
+    },
+    {
+        'query': 'primitive:fn(u32) -> ! -> ()',
+        'others': [
+            // fn matches primitive:fn and trait:Fn
+            {"path": "hof", "name": "fn_ptr"},
+        ],
+    },
+];
diff --git a/tests/rustdoc-js/hof.rs b/tests/rustdoc-js/hof.rs
new file mode 100644
index 00000000000..4d2c6e331ca
--- /dev/null
+++ b/tests/rustdoc-js/hof.rs
@@ -0,0 +1,12 @@
+#![feature(never_type)]
+
+pub struct First<T>(T);
+pub struct Second<T>(T);
+pub struct Third<T>(T);
+
+pub fn fn_ptr(_: fn (First<u32>) -> !, _: bool) {}
+pub fn fn_once(_: impl FnOnce (Second<u32>) -> !, _: u8) {}
+pub fn fn_mut(_: impl FnMut (Third<u32>) -> !, _: i8) {}
+pub fn fn_(_: impl Fn (u32) -> !, _: char) {}
+
+pub fn multiple(_: impl Fn(&'static str, &'static str) -> i8) {}
diff --git a/tests/rustdoc-js/looks-like-rustc-interner.js b/tests/rustdoc-js/looks-like-rustc-interner.js
new file mode 100644
index 00000000000..a4806d23499
--- /dev/null
+++ b/tests/rustdoc-js/looks-like-rustc-interner.js
@@ -0,0 +1,9 @@
+// https://github.com/rust-lang/rust/pull/122247
+// exact-check
+
+const EXPECTED = {
+    'query': 'canonicalvarinfo, intoiterator -> intoiterator',
+    'others': [
+        { 'path': 'looks_like_rustc_interner::Interner', 'name': 'mk_canonical_var_infos' },
+    ],
+};
diff --git a/tests/rustdoc-js/looks-like-rustc-interner.rs b/tests/rustdoc-js/looks-like-rustc-interner.rs
new file mode 100644
index 00000000000..f304e28d952
--- /dev/null
+++ b/tests/rustdoc-js/looks-like-rustc-interner.rs
@@ -0,0 +1,5 @@
+//@ aux-crate:interner=interner.rs
+// https://github.com/rust-lang/rust/pull/122247
+extern crate interner;
+#[doc(inline)]
+pub use interner::*;
diff --git a/tests/rustdoc/display-hidden-items.rs b/tests/rustdoc/display-hidden-items.rs
index 76124554767..901ca17d4d2 100644
--- a/tests/rustdoc/display-hidden-items.rs
+++ b/tests/rustdoc/display-hidden-items.rs
@@ -5,19 +5,22 @@
 #![crate_name = "foo"]
 
 // @has 'foo/index.html'
-// @has - '//*[@id="reexport.hidden_reexport"]/code' 'pub use hidden::inside_hidden as hidden_reexport;'
+// @has - '//*[@class="item-name"]/span[@title="Hidden item"]' '👻'
+
+// @has - '//*[@id="reexport.hidden_reexport"]/code' '#[doc(hidden)] pub use hidden::inside_hidden as hidden_reexport;'
 #[doc(hidden)]
 pub use hidden::inside_hidden as hidden_reexport;
 
 // @has - '//*[@class="item-name"]/a[@class="trait"]' 'TraitHidden'
 // @has 'foo/trait.TraitHidden.html'
+// @has - '//code' '#[doc(hidden)] pub trait TraitHidden'
 #[doc(hidden)]
 pub trait TraitHidden {}
 
 // @has 'foo/index.html' '//*[@class="item-name"]/a[@class="trait"]' 'Trait'
 pub trait Trait {
     // @has 'foo/trait.Trait.html'
-    // @has - '//*[@id="associatedconstant.BAR"]/*[@class="code-header"]' 'const BAR: u32 = 0u32'
+    // @has - '//*[@id="associatedconstant.BAR"]/*[@class="code-header"]' '#[doc(hidden)] const BAR: u32 = 0u32'
     #[doc(hidden)]
     const BAR: u32 = 0;
 
@@ -41,14 +44,15 @@ impl Struct {
 }
 
 impl Trait for Struct {
-    // @has - '//*[@id="associatedconstant.BAR"]/*[@class="code-header"]' 'const BAR: u32 = 0u32'
-    // @has - '//*[@id="method.foo"]/*[@class="code-header"]' 'fn foo()'
+    // @has - '//*[@id="associatedconstant.BAR"]/*[@class="code-header"]' '#[doc(hidden)] const BAR: u32 = 0u32'
+    // @has - '//*[@id="method.foo"]/*[@class="code-header"]' '#[doc(hidden)] fn foo()'
 }
 // @has - '//*[@id="impl-TraitHidden-for-Struct"]/*[@class="code-header"]' 'impl TraitHidden for Struct'
 impl TraitHidden for Struct {}
 
 // @has 'foo/index.html' '//*[@class="item-name"]/a[@class="enum"]' 'HiddenEnum'
 // @has 'foo/enum.HiddenEnum.html'
+// @has - '//code' '#[doc(hidden)] pub enum HiddenEnum'
 #[doc(hidden)]
 pub enum HiddenEnum {
     A,
diff --git a/tests/ui-fulldeps/stable-mir/check_transform.rs b/tests/ui-fulldeps/stable-mir/check_transform.rs
new file mode 100644
index 00000000000..e7d852a27df
--- /dev/null
+++ b/tests/ui-fulldeps/stable-mir/check_transform.rs
@@ -0,0 +1,147 @@
+//@ run-pass
+//! Test a few methods to transform StableMIR.
+
+//@ ignore-stage1
+//@ ignore-cross-compile
+//@ ignore-remote
+//@ ignore-windows-gnu mingw has troubles with linking https://github.com/rust-lang/rust/pull/116837
+
+#![feature(rustc_private)]
+#![feature(assert_matches)]
+#![feature(control_flow_enum)]
+#![feature(ascii_char, ascii_char_variants)]
+
+extern crate rustc_hir;
+#[macro_use]
+extern crate rustc_smir;
+extern crate rustc_driver;
+extern crate rustc_interface;
+extern crate stable_mir;
+
+use rustc_smir::rustc_internal;
+use stable_mir::mir::alloc::GlobalAlloc;
+use stable_mir::mir::mono::Instance;
+use stable_mir::mir::{Body, Constant, Operand, Rvalue, StatementKind, TerminatorKind};
+use stable_mir::ty::{Const, ConstantKind};
+use stable_mir::{CrateDef, CrateItems, ItemKind};
+use std::convert::TryFrom;
+use std::io::Write;
+use std::ops::ControlFlow;
+
+const CRATE_NAME: &str = "input";
+
+/// This function uses the Stable MIR APIs to transform the MIR.
+fn test_transform() -> ControlFlow<()> {
+    // Find items in the local crate.
+    let items = stable_mir::all_local_items();
+
+    // Test fn_abi
+    let target_fn = *get_item(&items, (ItemKind::Fn, "dummy")).unwrap();
+    let instance = Instance::try_from(target_fn).unwrap();
+    let body = instance.body().unwrap();
+    check_msg(&body, "oops");
+
+    let new_msg = "new panic message";
+    let new_body = change_panic_msg(body, new_msg);
+    check_msg(&new_body, new_msg);
+
+    ControlFlow::Continue(())
+}
+
+/// Check that the body panic message matches the given message.
+fn check_msg(body: &Body, expected: &str) {
+    let msg = body
+        .blocks
+        .iter()
+        .find_map(|bb| match &bb.terminator.kind {
+            TerminatorKind::Call { args, .. } => {
+                assert_eq!(args.len(), 1, "Expected panic message, but found {args:?}");
+                let msg_const = match &args[0] {
+                    Operand::Constant(msg_const) => msg_const,
+                    Operand::Copy(place) | Operand::Move(place) => {
+                        assert!(place.projection.is_empty());
+                        bb.statements
+                            .iter()
+                            .find_map(|stmt| match &stmt.kind {
+                                StatementKind::Assign(
+                                    destination,
+                                    Rvalue::Use(Operand::Constant(msg_const)),
+                                ) if destination == place => Some(msg_const),
+                                _ => None,
+                            })
+                            .unwrap()
+                    }
+                };
+                let ConstantKind::Allocated(alloc) = msg_const.literal.kind() else {
+                    unreachable!()
+                };
+                assert_eq!(alloc.provenance.ptrs.len(), 1);
+
+                let alloc_prov_id = alloc.provenance.ptrs[0].1 .0;
+                let GlobalAlloc::Memory(val) = GlobalAlloc::from(alloc_prov_id) else {
+                    unreachable!()
+                };
+                let bytes = val.raw_bytes().unwrap();
+                Some(std::str::from_utf8(&bytes).unwrap().to_string())
+            }
+            _ => None,
+        })
+        .expect("Failed to find panic message");
+    assert_eq!(&msg, expected);
+}
+
+/// Modify body to use a different panic message.
+fn change_panic_msg(mut body: Body, new_msg: &str) -> Body {
+    for bb in &mut body.blocks {
+        match &mut bb.terminator.kind {
+            TerminatorKind::Call { args, .. } => {
+                let new_const = Const::from_str(new_msg);
+                args[0] = Operand::Constant(Constant {
+                    literal: new_const,
+                    span: bb.terminator.span,
+                    user_ty: None,
+                });
+            }
+            _ => {}
+        }
+    }
+    body
+}
+
+fn get_item<'a>(
+    items: &'a CrateItems,
+    item: (ItemKind, &str),
+) -> Option<&'a stable_mir::CrateItem> {
+    items.iter().find(|crate_item| (item.0 == crate_item.kind()) && crate_item.name() == item.1)
+}
+
+/// This test will generate and analyze a dummy crate using the stable mir.
+/// For that, it will first write the dummy crate into a file.
+/// Then it will create a `StableMir` using custom arguments and then
+/// it will run the compiler.
+fn main() {
+    let path = "transform_input.rs";
+    generate_input(&path).unwrap();
+    let args = vec![
+        "rustc".to_string(),
+        "--crate-type=lib".to_string(),
+        "--crate-name".to_string(),
+        CRATE_NAME.to_string(),
+        path.to_string(),
+    ];
+    run!(args, test_transform).unwrap();
+}
+
+fn generate_input(path: &str) -> std::io::Result<()> {
+    let mut file = std::fs::File::create(path)?;
+    write!(
+        file,
+        r#"
+        #![feature(panic_internals)]
+        pub fn dummy() {{
+            core::panicking::panic_str("oops");
+        }}
+        "#
+    )?;
+    Ok(())
+}
diff --git a/tests/ui/associated-type-bounds/dedup-normalized-1.rs b/tests/ui/associated-type-bounds/dedup-normalized-1.rs
new file mode 100644
index 00000000000..5329018e79f
--- /dev/null
+++ b/tests/ui/associated-type-bounds/dedup-normalized-1.rs
@@ -0,0 +1,24 @@
+//@ check-pass
+
+// We try to prove `T::Rigid: Into<?0>` and have 2 candidates from where-clauses:
+//
+// - `Into<String>`
+// - `Into<<T::Rigid as Elaborate>::Assoc>`
+//
+// This causes ambiguity unless we normalize the alias in the second candidate
+// to detect that they actually result in the same constraints.
+trait Trait {
+    type Rigid: Elaborate<Assoc = String> + Into<String>;
+}
+
+trait Elaborate: Into<Self::Assoc> {
+    type Assoc;
+}
+
+fn impls<T: Into<U>, U>(_: T) {}
+
+fn test<P: Trait>(rigid: P::Rigid) {
+    impls(rigid);
+}
+
+fn main() {}
diff --git a/tests/ui/associated-type-bounds/dedup-normalized-2-higher-ranked.rs b/tests/ui/associated-type-bounds/dedup-normalized-2-higher-ranked.rs
new file mode 100644
index 00000000000..9224d47d30f
--- /dev/null
+++ b/tests/ui/associated-type-bounds/dedup-normalized-2-higher-ranked.rs
@@ -0,0 +1,27 @@
+// We try to prove `for<'b> T::Rigid: Bound<'b, ?0>` and have 2 candidates from where-clauses:
+//
+// - `for<'a> Bound<'a, String>`
+// - `for<'a> Bound<'a, <T::Rigid as Elaborate>::Assoc>`
+//
+// This causes ambiguity unless we normalize the alias in the second candidate
+// to detect that they actually result in the same constraints. We currently
+// fail to detect that the constraints from these bounds are equal and error
+// with ambiguity.
+trait Bound<'a, U> {}
+
+trait Trait {
+    type Rigid: Elaborate<Assoc = String> + for<'a> Bound<'a, String>;
+}
+
+trait Elaborate: for<'a> Bound<'a, Self::Assoc> {
+    type Assoc;
+}
+
+fn impls<T: for<'b> Bound<'b, U>, U>(_: T) {}
+
+fn test<P: Trait>(rigid: P::Rigid) {
+    impls(rigid);
+    //~^ ERROR type annotations needed
+}
+
+fn main() {}
diff --git a/tests/ui/associated-type-bounds/dedup-normalized-2-higher-ranked.stderr b/tests/ui/associated-type-bounds/dedup-normalized-2-higher-ranked.stderr
new file mode 100644
index 00000000000..372d379de5a
--- /dev/null
+++ b/tests/ui/associated-type-bounds/dedup-normalized-2-higher-ranked.stderr
@@ -0,0 +1,20 @@
+error[E0283]: type annotations needed
+  --> $DIR/dedup-normalized-2-higher-ranked.rs:23:5
+   |
+LL |     impls(rigid);
+   |     ^^^^^ cannot infer type of the type parameter `U` declared on the function `impls`
+   |
+   = note: cannot satisfy `for<'b> <P as Trait>::Rigid: Bound<'b, _>`
+note: required by a bound in `impls`
+  --> $DIR/dedup-normalized-2-higher-ranked.rs:20:13
+   |
+LL | fn impls<T: for<'b> Bound<'b, U>, U>(_: T) {}
+   |             ^^^^^^^^^^^^^^^^^^^^ required by this bound in `impls`
+help: consider specifying the generic arguments
+   |
+LL |     impls::<<P as Trait>::Rigid, U>(rigid);
+   |          ++++++++++++++++++++++++++
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0283`.
diff --git a/tests/ui/async-await/in-trait/hir-hash.rs b/tests/ui/async-await/in-trait/hir-hash.rs
new file mode 100644
index 00000000000..8324fec8282
--- /dev/null
+++ b/tests/ui/async-await/in-trait/hir-hash.rs
@@ -0,0 +1,11 @@
+// Issue #122508
+
+//@ check-pass
+//@ incremental
+//@ edition:2021
+
+trait MyTrait {
+    async fn bar(&self) -> i32;
+}
+
+fn main() {}
diff --git a/tests/ui/async-await/return-type-notation/issue-110963-early.stderr b/tests/ui/async-await/return-type-notation/issue-110963-early.stderr
index feae2698e8f..23ede089b5a 100644
--- a/tests/ui/async-await/return-type-notation/issue-110963-early.stderr
+++ b/tests/ui/async-await/return-type-notation/issue-110963-early.stderr
@@ -7,7 +7,7 @@ LL | #![feature(return_type_notation)]
    = note: see issue #109417 <https://github.com/rust-lang/rust/issues/109417> for more information
    = note: `#[warn(incomplete_features)]` on by default
 
-error[E0308]: mismatched types
+error: implementation of `Send` is not general enough
   --> $DIR/issue-110963-early.rs:14:5
    |
 LL | /     spawn(async move {
@@ -16,17 +16,12 @@ LL | |         if !hc.check().await {
 LL | |             log_health_check_failure().await;
 LL | |         }
 LL | |     });
-   | |______^ one type is more general than the other
+   | |______^ implementation of `Send` is not general enough
    |
-   = note: expected trait `Send`
-              found trait `for<'a> Send`
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-110963-early.rs:34:17
-   |
-LL |     F: Future + Send + 'static,
-   |                 ^^^^
+   = note: `Send` would have to be implemented for the type `impl Future<Output = bool> { <HC as HealthCheck>::check<'0>() }`, for any two lifetimes `'0` and `'1`...
+   = note: ...but `Send` is actually implemented for the type `impl Future<Output = bool> { <HC as HealthCheck>::check<'2>() }`, for some specific lifetime `'2`
 
-error[E0308]: mismatched types
+error: implementation of `Send` is not general enough
   --> $DIR/issue-110963-early.rs:14:5
    |
 LL | /     spawn(async move {
@@ -35,17 +30,11 @@ LL | |         if !hc.check().await {
 LL | |             log_health_check_failure().await;
 LL | |         }
 LL | |     });
-   | |______^ one type is more general than the other
-   |
-   = note: expected trait `Send`
-              found trait `for<'a> Send`
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-110963-early.rs:34:17
+   | |______^ implementation of `Send` is not general enough
    |
-LL |     F: Future + Send + 'static,
-   |                 ^^^^
+   = note: `Send` would have to be implemented for the type `impl Future<Output = bool> { <HC as HealthCheck>::check<'0>() }`, for any two lifetimes `'0` and `'1`...
+   = note: ...but `Send` is actually implemented for the type `impl Future<Output = bool> { <HC as HealthCheck>::check<'2>() }`, for some specific lifetime `'2`
    = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
 error: aborting due to 2 previous errors; 1 warning emitted
 
-For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/borrowck/clone-on-ref.fixed b/tests/ui/borrowck/clone-on-ref.fixed
new file mode 100644
index 00000000000..b6927ba590e
--- /dev/null
+++ b/tests/ui/borrowck/clone-on-ref.fixed
@@ -0,0 +1,32 @@
+//@ run-rustfix
+fn foo<T: Default + Clone>(list: &mut Vec<T>) {
+    let mut cloned_items = Vec::new();
+    for v in list.iter() {
+        cloned_items.push(v.clone())
+    }
+    list.push(T::default());
+    //~^ ERROR cannot borrow `*list` as mutable because it is also borrowed as immutable
+    drop(cloned_items);
+}
+fn bar<T: std::fmt::Display + Clone>(x: T) {
+    let a = &x;
+    let b = a.clone();
+    drop(x);
+    //~^ ERROR cannot move out of `x` because it is borrowed
+    println!("{b}");
+}
+#[derive(Debug)]
+#[derive(Clone)]
+struct A;
+fn qux(x: A) {
+    let a = &x;
+    let b = a.clone();
+    drop(x);
+    //~^ ERROR cannot move out of `x` because it is borrowed
+    println!("{b:?}");
+}
+fn main() {
+    foo(&mut vec![1, 2, 3]);
+    bar("");
+    qux(A);
+}
diff --git a/tests/ui/borrowck/clone-on-ref.rs b/tests/ui/borrowck/clone-on-ref.rs
new file mode 100644
index 00000000000..f8c94d3cce3
--- /dev/null
+++ b/tests/ui/borrowck/clone-on-ref.rs
@@ -0,0 +1,31 @@
+//@ run-rustfix
+fn foo<T: Default>(list: &mut Vec<T>) {
+    let mut cloned_items = Vec::new();
+    for v in list.iter() {
+        cloned_items.push(v.clone())
+    }
+    list.push(T::default());
+    //~^ ERROR cannot borrow `*list` as mutable because it is also borrowed as immutable
+    drop(cloned_items);
+}
+fn bar<T: std::fmt::Display>(x: T) {
+    let a = &x;
+    let b = a.clone();
+    drop(x);
+    //~^ ERROR cannot move out of `x` because it is borrowed
+    println!("{b}");
+}
+#[derive(Debug)]
+struct A;
+fn qux(x: A) {
+    let a = &x;
+    let b = a.clone();
+    drop(x);
+    //~^ ERROR cannot move out of `x` because it is borrowed
+    println!("{b:?}");
+}
+fn main() {
+    foo(&mut vec![1, 2, 3]);
+    bar("");
+    qux(A);
+}
diff --git a/tests/ui/borrowck/clone-on-ref.stderr b/tests/ui/borrowck/clone-on-ref.stderr
new file mode 100644
index 00000000000..ee4fcadf55a
--- /dev/null
+++ b/tests/ui/borrowck/clone-on-ref.stderr
@@ -0,0 +1,64 @@
+error[E0502]: cannot borrow `*list` as mutable because it is also borrowed as immutable
+  --> $DIR/clone-on-ref.rs:7:5
+   |
+LL |     for v in list.iter() {
+   |              ---- immutable borrow occurs here
+LL |         cloned_items.push(v.clone())
+   |                             ------- this call doesn't do anything, the result is still `&T` because `T` doesn't implement `Clone`
+LL |     }
+LL |     list.push(T::default());
+   |     ^^^^^^^^^^^^^^^^^^^^^^^ mutable borrow occurs here
+LL |
+LL |     drop(cloned_items);
+   |          ------------ immutable borrow later used here
+   |
+help: consider further restricting this bound
+   |
+LL | fn foo<T: Default + Clone>(list: &mut Vec<T>) {
+   |                   +++++++
+
+error[E0505]: cannot move out of `x` because it is borrowed
+  --> $DIR/clone-on-ref.rs:14:10
+   |
+LL | fn bar<T: std::fmt::Display>(x: T) {
+   |                              - binding `x` declared here
+LL |     let a = &x;
+   |             -- borrow of `x` occurs here
+LL |     let b = a.clone();
+   |               ------- this call doesn't do anything, the result is still `&T` because `T` doesn't implement `Clone`
+LL |     drop(x);
+   |          ^ move out of `x` occurs here
+LL |
+LL |     println!("{b}");
+   |               --- borrow later used here
+   |
+help: consider further restricting this bound
+   |
+LL | fn bar<T: std::fmt::Display + Clone>(x: T) {
+   |                             +++++++
+
+error[E0505]: cannot move out of `x` because it is borrowed
+  --> $DIR/clone-on-ref.rs:23:10
+   |
+LL | fn qux(x: A) {
+   |        - binding `x` declared here
+LL |     let a = &x;
+   |             -- borrow of `x` occurs here
+LL |     let b = a.clone();
+   |               ------- this call doesn't do anything, the result is still `&A` because `A` doesn't implement `Clone`
+LL |     drop(x);
+   |          ^ move out of `x` occurs here
+LL |
+LL |     println!("{b:?}");
+   |               ----- borrow later used here
+   |
+help: consider annotating `A` with `#[derive(Clone)]`
+   |
+LL + #[derive(Clone)]
+LL | struct A;
+   |
+
+error: aborting due to 3 previous errors
+
+Some errors have detailed explanations: E0502, E0505.
+For more information about an error, try `rustc --explain E0502`.
diff --git a/tests/ui/closures/multiple-fn-bounds.stderr b/tests/ui/closures/multiple-fn-bounds.stderr
index 9a49fc99ac3..861b39b4d07 100644
--- a/tests/ui/closures/multiple-fn-bounds.stderr
+++ b/tests/ui/closures/multiple-fn-bounds.stderr
@@ -8,7 +8,7 @@ LL |     foo(move |x| v);
    |     expected due to this
    |
    = note: expected closure signature `fn(_) -> _`
-              found closure signature `for<'a> fn(&'a _) -> _`
+              found closure signature `fn(&_) -> _`
 note: closure inferred to have a different signature due to this bound
   --> $DIR/multiple-fn-bounds.rs:1:11
    |
diff --git a/tests/ui/consts/assoc_const_generic_impl.stderr b/tests/ui/consts/assoc_const_generic_impl.stderr
index d826972ce9f..45219508396 100644
--- a/tests/ui/consts/assoc_const_generic_impl.stderr
+++ b/tests/ui/consts/assoc_const_generic_impl.stderr
@@ -4,6 +4,12 @@ error[E0080]: evaluation of `<u32 as ZeroSized>::I_AM_ZERO_SIZED` failed
 LL |     const I_AM_ZERO_SIZED: ()  = [()][std::mem::size_of::<Self>()];
    |                                  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ index out of bounds: the length is 1 but the index is 4
 
+note: erroneous constant encountered
+  --> $DIR/assoc_const_generic_impl.rs:11:9
+   |
+LL |         Self::I_AM_ZERO_SIZED;
+   |         ^^^^^^^^^^^^^^^^^^^^^
+
 note: the above error was encountered while instantiating `fn <u32 as ZeroSized>::requires_zero_size`
   --> $DIR/assoc_const_generic_impl.rs:18:5
    |
diff --git a/tests/ui/consts/const-eval/erroneous-const.stderr b/tests/ui/consts/const-eval/erroneous-const.stderr
deleted file mode 100644
index bd25e96c2cf..00000000000
--- a/tests/ui/consts/const-eval/erroneous-const.stderr
+++ /dev/null
@@ -1,15 +0,0 @@
-error[E0080]: evaluation of `PrintName::<i32>::VOID` failed
-  --> $DIR/erroneous-const.rs:6:22
-   |
-LL |     const VOID: () = [()][2];
-   |                      ^^^^^^^ index out of bounds: the length is 1 but the index is 2
-
-note: erroneous constant encountered
-  --> $DIR/erroneous-const.rs:13:13
-   |
-LL |             PrintName::<T>::VOID;
-   |             ^^^^^^^^^^^^^^^^^^^^
-
-error: aborting due to 1 previous error
-
-For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/const-eval/erroneous-const2.rs b/tests/ui/consts/const-eval/erroneous-const2.rs
deleted file mode 100644
index 61f2955f2d8..00000000000
--- a/tests/ui/consts/const-eval/erroneous-const2.rs
+++ /dev/null
@@ -1,19 +0,0 @@
-//! Make sure we error on erroneous consts even if they are unused.
-#![allow(unconditional_panic)]
-
-struct PrintName<T>(T);
-impl<T> PrintName<T> {
-    const VOID: () = [()][2]; //~ERROR evaluation of `PrintName::<i32>::VOID` failed
-}
-
-pub static FOO: () = {
-    if false {
-        // This bad constant is only used in dead code in a static initializer... and yet we still
-        // must make sure that the build fails.
-        PrintName::<i32>::VOID; //~ constant
-    }
-};
-
-fn main() {
-    FOO
-}
diff --git a/tests/ui/consts/const-eval/erroneous-const2.stderr b/tests/ui/consts/const-eval/erroneous-const2.stderr
deleted file mode 100644
index 6a5839e3dfb..00000000000
--- a/tests/ui/consts/const-eval/erroneous-const2.stderr
+++ /dev/null
@@ -1,15 +0,0 @@
-error[E0080]: evaluation of `PrintName::<i32>::VOID` failed
-  --> $DIR/erroneous-const2.rs:6:22
-   |
-LL |     const VOID: () = [()][2];
-   |                      ^^^^^^^ index out of bounds: the length is 1 but the index is 2
-
-note: erroneous constant encountered
-  --> $DIR/erroneous-const2.rs:13:9
-   |
-LL |         PrintName::<i32>::VOID;
-   |         ^^^^^^^^^^^^^^^^^^^^^^
-
-error: aborting due to 1 previous error
-
-For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/const-eval/index-out-of-bounds-never-type.stderr b/tests/ui/consts/const-eval/index-out-of-bounds-never-type.stderr
index 4e7ef52f674..7facb2d1a5c 100644
--- a/tests/ui/consts/const-eval/index-out-of-bounds-never-type.stderr
+++ b/tests/ui/consts/const-eval/index-out-of-bounds-never-type.stderr
@@ -4,6 +4,12 @@ error[E0080]: evaluation of `PrintName::<()>::VOID` failed
 LL |     const VOID: ! = { let x = 0 * std::mem::size_of::<T>(); [][x] };
    |                                                             ^^^^^ index out of bounds: the length is 0 but the index is 0
 
+note: erroneous constant encountered
+  --> $DIR/index-out-of-bounds-never-type.rs:16:13
+   |
+LL |     let _ = PrintName::<T>::VOID;
+   |             ^^^^^^^^^^^^^^^^^^^^
+
 note: the above error was encountered while instantiating `fn f::<()>`
   --> $DIR/index-out-of-bounds-never-type.rs:20:5
    |
diff --git a/tests/ui/consts/const-eval/issue-50814-2.mir-opt.stderr b/tests/ui/consts/const-eval/issue-50814-2.mir-opt.stderr
index 7e764ca7239..2de68d3fee9 100644
--- a/tests/ui/consts/const-eval/issue-50814-2.mir-opt.stderr
+++ b/tests/ui/consts/const-eval/issue-50814-2.mir-opt.stderr
@@ -10,6 +10,52 @@ note: erroneous constant encountered
 LL |     &<A<T> as Foo<T>>::BAR
    |      ^^^^^^^^^^^^^^^^^^^^^
 
+note: erroneous constant encountered
+  --> $DIR/issue-50814-2.rs:20:5
+   |
+LL |     &<A<T> as Foo<T>>::BAR
+   |     ^^^^^^^^^^^^^^^^^^^^^^
+
+note: erroneous constant encountered
+  --> $DIR/issue-50814-2.rs:20:5
+   |
+LL |     &<A<T> as Foo<T>>::BAR
+   |     ^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
+note: erroneous constant encountered
+  --> $DIR/issue-50814-2.rs:20:5
+   |
+LL |     &<A<T> as Foo<T>>::BAR
+   |     ^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
+note: erroneous constant encountered
+  --> $DIR/issue-50814-2.rs:20:5
+   |
+LL |     &<A<T> as Foo<T>>::BAR
+   |     ^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
+note: erroneous constant encountered
+  --> $DIR/issue-50814-2.rs:20:6
+   |
+LL |     &<A<T> as Foo<T>>::BAR
+   |      ^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
+note: erroneous constant encountered
+  --> $DIR/issue-50814-2.rs:20:6
+   |
+LL |     &<A<T> as Foo<T>>::BAR
+   |      ^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
 error: aborting due to 1 previous error
 
 For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/const-eval/issue-50814-2.normal.stderr b/tests/ui/consts/const-eval/issue-50814-2.normal.stderr
index f552c8fde5b..4a7dfb19304 100644
--- a/tests/ui/consts/const-eval/issue-50814-2.normal.stderr
+++ b/tests/ui/consts/const-eval/issue-50814-2.normal.stderr
@@ -10,6 +10,20 @@ note: erroneous constant encountered
 LL |     &<A<T> as Foo<T>>::BAR
    |      ^^^^^^^^^^^^^^^^^^^^^
 
+note: erroneous constant encountered
+  --> $DIR/issue-50814-2.rs:20:5
+   |
+LL |     &<A<T> as Foo<T>>::BAR
+   |     ^^^^^^^^^^^^^^^^^^^^^^
+
+note: erroneous constant encountered
+  --> $DIR/issue-50814-2.rs:20:6
+   |
+LL |     &<A<T> as Foo<T>>::BAR
+   |      ^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
 note: the above error was encountered while instantiating `fn foo::<()>`
   --> $DIR/issue-50814-2.rs:32:22
    |
diff --git a/tests/ui/consts/const-eval/issue-50814.stderr b/tests/ui/consts/const-eval/issue-50814.stderr
index 8d018161401..fe0e25b820f 100644
--- a/tests/ui/consts/const-eval/issue-50814.stderr
+++ b/tests/ui/consts/const-eval/issue-50814.stderr
@@ -26,6 +26,20 @@ LL |     &Sum::<U8, U8>::MAX
    |
    = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
+note: erroneous constant encountered
+  --> $DIR/issue-50814.rs:21:5
+   |
+LL |     &Sum::<U8, U8>::MAX
+   |     ^^^^^^^^^^^^^^^^^^^
+
+note: erroneous constant encountered
+  --> $DIR/issue-50814.rs:21:6
+   |
+LL |     &Sum::<U8, U8>::MAX
+   |      ^^^^^^^^^^^^^^^^^^
+   |
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
 note: the above error was encountered while instantiating `fn foo::<i32>`
   --> $DIR/issue-50814.rs:26:5
    |
diff --git a/tests/ui/consts/const-eval/issue-85155.stderr b/tests/ui/consts/const-eval/issue-85155.stderr
index a88e959a8a6..99836a3fac6 100644
--- a/tests/ui/consts/const-eval/issue-85155.stderr
+++ b/tests/ui/consts/const-eval/issue-85155.stderr
@@ -4,6 +4,14 @@ error[E0080]: evaluation of `post_monomorphization_error::ValidateConstImm::<2,
 LL |         let _ = 1 / ((IMM >= MIN && IMM <= MAX) as usize);
    |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ attempt to divide `1_usize` by zero
 
+note: erroneous constant encountered
+  --> $DIR/auxiliary/post_monomorphization_error.rs:19:5
+   |
+LL |     static_assert_imm1!(IMM1);
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: this note originates in the macro `static_assert_imm1` (in Nightly builds, run with -Z macro-backtrace for more info)
+
 note: the above error was encountered while instantiating `fn post_monomorphization_error::stdarch_intrinsic::<2>`
   --> $DIR/issue-85155.rs:19:5
    |
diff --git a/tests/ui/consts/const-eval/unused-broken-const-late.stderr b/tests/ui/consts/const-eval/unused-broken-const-late.stderr
deleted file mode 100644
index c2cf2f3813c..00000000000
--- a/tests/ui/consts/const-eval/unused-broken-const-late.stderr
+++ /dev/null
@@ -1,11 +0,0 @@
-error[E0080]: evaluation of `PrintName::<i32>::VOID` failed
-  --> $DIR/unused-broken-const-late.rs:8:22
-   |
-LL |     const VOID: () = panic!();
-   |                      ^^^^^^^^ the evaluated program panicked at 'explicit panic', $DIR/unused-broken-const-late.rs:8:22
-   |
-   = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
-
-error: aborting due to 1 previous error
-
-For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/required-consts/collect-in-called-fn.noopt.stderr b/tests/ui/consts/required-consts/collect-in-called-fn.noopt.stderr
new file mode 100644
index 00000000000..14a4cb0217f
--- /dev/null
+++ b/tests/ui/consts/required-consts/collect-in-called-fn.noopt.stderr
@@ -0,0 +1,23 @@
+error[E0080]: evaluation of `Fail::<i32>::C` failed
+  --> $DIR/collect-in-called-fn.rs:9:19
+   |
+LL |     const C: () = panic!();
+   |                   ^^^^^^^^ the evaluated program panicked at 'explicit panic', $DIR/collect-in-called-fn.rs:9:19
+   |
+   = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+note: erroneous constant encountered
+  --> $DIR/collect-in-called-fn.rs:18:17
+   |
+LL |         let _ = Fail::<T>::C;
+   |                 ^^^^^^^^^^^^
+
+note: the above error was encountered while instantiating `fn called::<i32>`
+  --> $DIR/collect-in-called-fn.rs:23:5
+   |
+LL |     called::<i32>();
+   |     ^^^^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/required-consts/collect-in-called-fn.opt.stderr b/tests/ui/consts/required-consts/collect-in-called-fn.opt.stderr
new file mode 100644
index 00000000000..14a4cb0217f
--- /dev/null
+++ b/tests/ui/consts/required-consts/collect-in-called-fn.opt.stderr
@@ -0,0 +1,23 @@
+error[E0080]: evaluation of `Fail::<i32>::C` failed
+  --> $DIR/collect-in-called-fn.rs:9:19
+   |
+LL |     const C: () = panic!();
+   |                   ^^^^^^^^ the evaluated program panicked at 'explicit panic', $DIR/collect-in-called-fn.rs:9:19
+   |
+   = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+note: erroneous constant encountered
+  --> $DIR/collect-in-called-fn.rs:18:17
+   |
+LL |         let _ = Fail::<T>::C;
+   |                 ^^^^^^^^^^^^
+
+note: the above error was encountered while instantiating `fn called::<i32>`
+  --> $DIR/collect-in-called-fn.rs:23:5
+   |
+LL |     called::<i32>();
+   |     ^^^^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/const-eval/unused-broken-const-late.rs b/tests/ui/consts/required-consts/collect-in-called-fn.rs
index c4916061f9e..55133a10cd9 100644
--- a/tests/ui/consts/const-eval/unused-broken-const-late.rs
+++ b/tests/ui/consts/required-consts/collect-in-called-fn.rs
@@ -1,20 +1,24 @@
+//@revisions: noopt opt
 //@ build-fail
-//@ compile-flags: -O
+//@[opt] compile-flags: -O
 //! Make sure we detect erroneous constants post-monomorphization even when they are unused. This is
 //! crucial, people rely on it for soundness. (https://github.com/rust-lang/rust/issues/112090)
 
-struct PrintName<T>(T);
-impl<T> PrintName<T> {
-    const VOID: () = panic!(); //~ERROR evaluation of `PrintName::<i32>::VOID` failed
+struct Fail<T>(T);
+impl<T> Fail<T> {
+    const C: () = panic!(); //~ERROR evaluation of `Fail::<i32>::C` failed
 }
 
-fn no_codegen<T>() {
+#[inline(never)]
+fn called<T>() {
     // Any function that is called is guaranteed to have all consts that syntactically
     // appear in its body evaluated, even if they only appear in dead code.
+    // This relies on mono-item collection checking `required_consts` in collected functions.
     if false {
-        let _ = PrintName::<T>::VOID;
+        let _ = Fail::<T>::C;
     }
 }
+
 pub fn main() {
-    no_codegen::<i32>();
+    called::<i32>();
 }
diff --git a/tests/ui/consts/required-consts/collect-in-dead-drop.noopt.stderr b/tests/ui/consts/required-consts/collect-in-dead-drop.noopt.stderr
new file mode 100644
index 00000000000..0bf231d09f1
--- /dev/null
+++ b/tests/ui/consts/required-consts/collect-in-dead-drop.noopt.stderr
@@ -0,0 +1,20 @@
+error[E0080]: evaluation of `Fail::<i32>::C` failed
+  --> $DIR/collect-in-dead-drop.rs:12:19
+   |
+LL |     const C: () = panic!();
+   |                   ^^^^^^^^ the evaluated program panicked at 'explicit panic', $DIR/collect-in-dead-drop.rs:12:19
+   |
+   = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+note: erroneous constant encountered
+  --> $DIR/collect-in-dead-drop.rs:19:17
+   |
+LL |         let _ = Fail::<T>::C;
+   |                 ^^^^^^^^^^^^
+
+note: the above error was encountered while instantiating `fn <Fail<i32> as std::ops::Drop>::drop`
+  --> $SRC_DIR/core/src/ptr/mod.rs:LL:COL
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/required-consts/collect-in-dead-drop.rs b/tests/ui/consts/required-consts/collect-in-dead-drop.rs
new file mode 100644
index 00000000000..c9ffcec6903
--- /dev/null
+++ b/tests/ui/consts/required-consts/collect-in-dead-drop.rs
@@ -0,0 +1,33 @@
+//@revisions: noopt opt
+//@[noopt] build-fail
+//@[opt] compile-flags: -O
+//FIXME: `opt` revision currently does not stop with an error due to
+//<https://github.com/rust-lang/rust/issues/107503>.
+//@[opt] build-pass
+//! Make sure we detect erroneous constants post-monomorphization even when they are unused. This is
+//! crucial, people rely on it for soundness. (https://github.com/rust-lang/rust/issues/112090)
+
+struct Fail<T>(T);
+impl<T> Fail<T> {
+    const C: () = panic!(); //[noopt]~ERROR evaluation of `Fail::<i32>::C` failed
+}
+
+// This function is not actually called, but is mentioned implicitly as destructor in dead code in a
+// function that is called. Make sure we still find this error.
+impl<T> Drop for Fail<T> {
+    fn drop(&mut self) {
+        let _ = Fail::<T>::C;
+    }
+}
+
+#[inline(never)]
+fn called<T>(x: T) {
+    if false {
+        let v = Fail(x);
+        // Now it gest dropped implicitly, at the end of this scope.
+    }
+}
+
+pub fn main() {
+    called::<i32>(0);
+}
diff --git a/tests/ui/consts/required-consts/collect-in-dead-fn.noopt.stderr b/tests/ui/consts/required-consts/collect-in-dead-fn.noopt.stderr
new file mode 100644
index 00000000000..8bb99efe8e4
--- /dev/null
+++ b/tests/ui/consts/required-consts/collect-in-dead-fn.noopt.stderr
@@ -0,0 +1,23 @@
+error[E0080]: evaluation of `Fail::<i32>::C` failed
+  --> $DIR/collect-in-dead-fn.rs:12:19
+   |
+LL |     const C: () = panic!();
+   |                   ^^^^^^^^ the evaluated program panicked at 'explicit panic', $DIR/collect-in-dead-fn.rs:12:19
+   |
+   = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+note: erroneous constant encountered
+  --> $DIR/collect-in-dead-fn.rs:22:17
+   |
+LL |         let _ = Fail::<T>::C;
+   |                 ^^^^^^^^^^^^
+
+note: the above error was encountered while instantiating `fn not_called::<i32>`
+  --> $DIR/collect-in-dead-fn.rs:29:9
+   |
+LL |         not_called::<T>();
+   |         ^^^^^^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/required-consts/collect-in-dead-fn.rs b/tests/ui/consts/required-consts/collect-in-dead-fn.rs
new file mode 100644
index 00000000000..9e6b1519153
--- /dev/null
+++ b/tests/ui/consts/required-consts/collect-in-dead-fn.rs
@@ -0,0 +1,35 @@
+//@revisions: noopt opt
+//@[noopt] build-fail
+//@[opt] compile-flags: -O
+//FIXME: `opt` revision currently does not stop with an error due to
+//<https://github.com/rust-lang/rust/issues/107503>.
+//@[opt] build-pass
+//! Make sure we detect erroneous constants post-monomorphization even when they are unused. This is
+//! crucial, people rely on it for soundness. (https://github.com/rust-lang/rust/issues/112090)
+
+struct Fail<T>(T);
+impl<T> Fail<T> {
+    const C: () = panic!(); //[noopt]~ERROR evaluation of `Fail::<i32>::C` failed
+}
+
+// This function is not actually called, but it is mentioned in dead code in a function that is
+// called. Make sure we still find this error.
+// This relies on mono-item collection checking `required_consts` in functions that syntactically
+// are called in collected functions (even inside dead code).
+#[inline(never)]
+fn not_called<T>() {
+    if false {
+        let _ = Fail::<T>::C;
+    }
+}
+
+#[inline(never)]
+fn called<T>() {
+    if false {
+        not_called::<T>();
+    }
+}
+
+pub fn main() {
+    called::<i32>();
+}
diff --git a/tests/ui/consts/required-consts/collect-in-dead-forget.rs b/tests/ui/consts/required-consts/collect-in-dead-forget.rs
new file mode 100644
index 00000000000..720b7a499f7
--- /dev/null
+++ b/tests/ui/consts/required-consts/collect-in-dead-forget.rs
@@ -0,0 +1,32 @@
+//@revisions: noopt opt
+//@build-pass
+//@[opt] compile-flags: -O
+//! Make sure we detect erroneous constants post-monomorphization even when they are unused. This is
+//! crucial, people rely on it for soundness. (https://github.com/rust-lang/rust/issues/112090)
+
+struct Fail<T>(T);
+impl<T> Fail<T> {
+    const C: () = panic!();
+}
+
+// This function is not actually called, but is mentioned implicitly as destructor in dead code in a
+// function that is called. Make sure we still find this error.
+impl<T> Drop for Fail<T> {
+    fn drop(&mut self) {
+        let _ = Fail::<T>::C;
+    }
+}
+
+#[inline(never)]
+fn called<T>(x: T) {
+    if false {
+        let v = Fail(x);
+        std::mem::forget(v);
+        // Now the destructor never gets "mentioned" so this build should *not* fail.
+        // IOW, this demonstrates that we are using a post-drop-elab notion of "mentioned".
+    }
+}
+
+pub fn main() {
+    called::<i32>(0);
+}
diff --git a/tests/ui/consts/required-consts/collect-in-dead-move.noopt.stderr b/tests/ui/consts/required-consts/collect-in-dead-move.noopt.stderr
new file mode 100644
index 00000000000..5b1df78b232
--- /dev/null
+++ b/tests/ui/consts/required-consts/collect-in-dead-move.noopt.stderr
@@ -0,0 +1,20 @@
+error[E0080]: evaluation of `Fail::<i32>::C` failed
+  --> $DIR/collect-in-dead-move.rs:12:19
+   |
+LL |     const C: () = panic!();
+   |                   ^^^^^^^^ the evaluated program panicked at 'explicit panic', $DIR/collect-in-dead-move.rs:12:19
+   |
+   = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+note: erroneous constant encountered
+  --> $DIR/collect-in-dead-move.rs:19:17
+   |
+LL |         let _ = Fail::<T>::C;
+   |                 ^^^^^^^^^^^^
+
+note: the above error was encountered while instantiating `fn <Fail<i32> as std::ops::Drop>::drop`
+  --> $SRC_DIR/core/src/ptr/mod.rs:LL:COL
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/required-consts/collect-in-dead-move.rs b/tests/ui/consts/required-consts/collect-in-dead-move.rs
new file mode 100644
index 00000000000..f3a6ba8a657
--- /dev/null
+++ b/tests/ui/consts/required-consts/collect-in-dead-move.rs
@@ -0,0 +1,33 @@
+//@revisions: noopt opt
+//@[noopt] build-fail
+//@[opt] compile-flags: -O
+//FIXME: `opt` revision currently does not stop with an error due to
+//<https://github.com/rust-lang/rust/issues/107503>.
+//@[opt] build-pass
+//! Make sure we detect erroneous constants post-monomorphization even when they are unused. This is
+//! crucial, people rely on it for soundness. (https://github.com/rust-lang/rust/issues/112090)
+
+struct Fail<T>(T);
+impl<T> Fail<T> {
+    const C: () = panic!(); //[noopt]~ERROR evaluation of `Fail::<i32>::C` failed
+}
+
+// This function is not actually called, but is mentioned implicitly as destructor in dead code in a
+// function that is called. Make sure we still find this error.
+impl<T> Drop for Fail<T> {
+    fn drop(&mut self) {
+        let _ = Fail::<T>::C;
+    }
+}
+
+#[inline(never)]
+fn called<T>(x: T) {
+    if false {
+        let v = Fail(x);
+        drop(v); // move `v` away (and it then gets dropped there so build still fails)
+    }
+}
+
+pub fn main() {
+    called::<i32>(0);
+}
diff --git a/tests/ui/consts/required-consts/collect-in-dead-vtable.noopt.stderr b/tests/ui/consts/required-consts/collect-in-dead-vtable.noopt.stderr
new file mode 100644
index 00000000000..56b6989b441
--- /dev/null
+++ b/tests/ui/consts/required-consts/collect-in-dead-vtable.noopt.stderr
@@ -0,0 +1,23 @@
+error[E0080]: evaluation of `Fail::<i32>::C` failed
+  --> $DIR/collect-in-dead-vtable.rs:12:19
+   |
+LL |     const C: () = panic!();
+   |                   ^^^^^^^^ the evaluated program panicked at 'explicit panic', $DIR/collect-in-dead-vtable.rs:12:19
+   |
+   = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+note: erroneous constant encountered
+  --> $DIR/collect-in-dead-vtable.rs:26:21
+   |
+LL |             let _ = Fail::<T>::C;
+   |                     ^^^^^^^^^^^^
+
+note: the above error was encountered while instantiating `fn <std::vec::Vec<i32> as MyTrait>::not_called`
+  --> $DIR/collect-in-dead-vtable.rs:35:40
+   |
+LL |         let gen_vtable: &dyn MyTrait = &v; // vtable "appears" here
+   |                                        ^^
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/required-consts/collect-in-dead-vtable.rs b/tests/ui/consts/required-consts/collect-in-dead-vtable.rs
new file mode 100644
index 00000000000..f21a1cc1fc2
--- /dev/null
+++ b/tests/ui/consts/required-consts/collect-in-dead-vtable.rs
@@ -0,0 +1,41 @@
+//@revisions: noopt opt
+//@[noopt] build-fail
+//@[opt] compile-flags: -O
+//FIXME: `opt` revision currently does not stop with an error due to
+//<https://github.com/rust-lang/rust/issues/107503>.
+//@[opt] build-pass
+//! Make sure we detect erroneous constants post-monomorphization even when they are unused. This is
+//! crucial, people rely on it for soundness. (https://github.com/rust-lang/rust/issues/112090)
+
+struct Fail<T>(T);
+impl<T> Fail<T> {
+    const C: () = panic!(); //[noopt]~ERROR evaluation of `Fail::<i32>::C` failed
+}
+
+trait MyTrait {
+    fn not_called(&self);
+}
+
+// This function is not actually called, but it is mentioned in a vtable in a function that is
+// called. Make sure we still find this error.
+// This relies on mono-item collection checking `required_consts` in functions that are referenced
+// in vtables that syntactically appear in collected functions (even inside dead code).
+impl<T> MyTrait for Vec<T> {
+    fn not_called(&self) {
+        if false {
+            let _ = Fail::<T>::C;
+        }
+    }
+}
+
+#[inline(never)]
+fn called<T>() {
+    if false {
+        let v: Vec<T> = Vec::new();
+        let gen_vtable: &dyn MyTrait = &v; // vtable "appears" here
+    }
+}
+
+pub fn main() {
+    called::<i32>();
+}
diff --git a/tests/ui/consts/required-consts/interpret-in-const-called-fn.noopt.stderr b/tests/ui/consts/required-consts/interpret-in-const-called-fn.noopt.stderr
new file mode 100644
index 00000000000..75304591b9f
--- /dev/null
+++ b/tests/ui/consts/required-consts/interpret-in-const-called-fn.noopt.stderr
@@ -0,0 +1,17 @@
+error[E0080]: evaluation of `Fail::<i32>::C` failed
+  --> $DIR/interpret-in-const-called-fn.rs:7:19
+   |
+LL |     const C: () = panic!();
+   |                   ^^^^^^^^ the evaluated program panicked at 'explicit panic', $DIR/interpret-in-const-called-fn.rs:7:19
+   |
+   = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+note: erroneous constant encountered
+  --> $DIR/interpret-in-const-called-fn.rs:16:9
+   |
+LL |         Fail::<T>::C;
+   |         ^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/required-consts/interpret-in-const-called-fn.opt.stderr b/tests/ui/consts/required-consts/interpret-in-const-called-fn.opt.stderr
new file mode 100644
index 00000000000..75304591b9f
--- /dev/null
+++ b/tests/ui/consts/required-consts/interpret-in-const-called-fn.opt.stderr
@@ -0,0 +1,17 @@
+error[E0080]: evaluation of `Fail::<i32>::C` failed
+  --> $DIR/interpret-in-const-called-fn.rs:7:19
+   |
+LL |     const C: () = panic!();
+   |                   ^^^^^^^^ the evaluated program panicked at 'explicit panic', $DIR/interpret-in-const-called-fn.rs:7:19
+   |
+   = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+note: erroneous constant encountered
+  --> $DIR/interpret-in-const-called-fn.rs:16:9
+   |
+LL |         Fail::<T>::C;
+   |         ^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/const-eval/erroneous-const.rs b/tests/ui/consts/required-consts/interpret-in-const-called-fn.rs
index 74d44c5259a..c409fae0bb9 100644
--- a/tests/ui/consts/const-eval/erroneous-const.rs
+++ b/tests/ui/consts/required-consts/interpret-in-const-called-fn.rs
@@ -1,16 +1,19 @@
+//@revisions: noopt opt
+//@[opt] compile-flags: -O
 //! Make sure we error on erroneous consts even if they are unused.
-#![allow(unconditional_panic)]
 
-struct PrintName<T>(T);
-impl<T> PrintName<T> {
-    const VOID: () = [()][2]; //~ERROR evaluation of `PrintName::<i32>::VOID` failed
+struct Fail<T>(T);
+impl<T> Fail<T> {
+    const C: () = panic!(); //~ERROR evaluation of `Fail::<i32>::C` failed
 }
 
+#[inline(never)]
 const fn no_codegen<T>() {
     if false {
         // This bad constant is only used in dead code in a no-codegen function... and yet we still
         // must make sure that the build fails.
-            PrintName::<T>::VOID; //~ constant
+        // This relies on const-eval evaluating all `required_consts` of `const fn`.
+        Fail::<T>::C; //~ constant
     }
 }
 
diff --git a/tests/ui/consts/required-consts/interpret-in-promoted.noopt.stderr b/tests/ui/consts/required-consts/interpret-in-promoted.noopt.stderr
new file mode 100644
index 00000000000..491131daf8d
--- /dev/null
+++ b/tests/ui/consts/required-consts/interpret-in-promoted.noopt.stderr
@@ -0,0 +1,27 @@
+error[E0080]: evaluation of constant value failed
+  --> $SRC_DIR/core/src/hint.rs:LL:COL
+   |
+   = note: entering unreachable code
+   |
+note: inside `unreachable_unchecked`
+  --> $SRC_DIR/core/src/hint.rs:LL:COL
+note: inside `ub`
+  --> $DIR/interpret-in-promoted.rs:6:5
+   |
+LL |     std::hint::unreachable_unchecked();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+note: inside `FOO`
+  --> $DIR/interpret-in-promoted.rs:12:28
+   |
+LL |     let _x: &'static () = &ub();
+   |                            ^^^^
+
+note: erroneous constant encountered
+  --> $DIR/interpret-in-promoted.rs:12:27
+   |
+LL |     let _x: &'static () = &ub();
+   |                           ^^^^^
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/required-consts/interpret-in-promoted.opt.stderr b/tests/ui/consts/required-consts/interpret-in-promoted.opt.stderr
new file mode 100644
index 00000000000..491131daf8d
--- /dev/null
+++ b/tests/ui/consts/required-consts/interpret-in-promoted.opt.stderr
@@ -0,0 +1,27 @@
+error[E0080]: evaluation of constant value failed
+  --> $SRC_DIR/core/src/hint.rs:LL:COL
+   |
+   = note: entering unreachable code
+   |
+note: inside `unreachable_unchecked`
+  --> $SRC_DIR/core/src/hint.rs:LL:COL
+note: inside `ub`
+  --> $DIR/interpret-in-promoted.rs:6:5
+   |
+LL |     std::hint::unreachable_unchecked();
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+note: inside `FOO`
+  --> $DIR/interpret-in-promoted.rs:12:28
+   |
+LL |     let _x: &'static () = &ub();
+   |                            ^^^^
+
+note: erroneous constant encountered
+  --> $DIR/interpret-in-promoted.rs:12:27
+   |
+LL |     let _x: &'static () = &ub();
+   |                           ^^^^^
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/required-consts/interpret-in-promoted.rs b/tests/ui/consts/required-consts/interpret-in-promoted.rs
new file mode 100644
index 00000000000..9c2cf4e70d3
--- /dev/null
+++ b/tests/ui/consts/required-consts/interpret-in-promoted.rs
@@ -0,0 +1,15 @@
+//@revisions: noopt opt
+//@[opt] compile-flags: -O
+//! Make sure we error on erroneous consts even if they are unused.
+
+const unsafe fn ub() {
+    std::hint::unreachable_unchecked();
+}
+
+pub const FOO: () = unsafe {
+    // Make sure that this gets promoted and then fails to evaluate, and we deal with that
+    // correctly.
+    let _x: &'static () = &ub(); //~ erroneous constant
+};
+
+fn main() {}
diff --git a/tests/ui/consts/required-consts/interpret-in-static.noopt.stderr b/tests/ui/consts/required-consts/interpret-in-static.noopt.stderr
new file mode 100644
index 00000000000..159c9449fc0
--- /dev/null
+++ b/tests/ui/consts/required-consts/interpret-in-static.noopt.stderr
@@ -0,0 +1,17 @@
+error[E0080]: evaluation of `Fail::<i32>::C` failed
+  --> $DIR/interpret-in-static.rs:7:19
+   |
+LL |     const C: () = panic!();
+   |                   ^^^^^^^^ the evaluated program panicked at 'explicit panic', $DIR/interpret-in-static.rs:7:19
+   |
+   = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+note: erroneous constant encountered
+  --> $DIR/interpret-in-static.rs:15:9
+   |
+LL |         Fail::<i32>::C;
+   |         ^^^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/required-consts/interpret-in-static.opt.stderr b/tests/ui/consts/required-consts/interpret-in-static.opt.stderr
new file mode 100644
index 00000000000..159c9449fc0
--- /dev/null
+++ b/tests/ui/consts/required-consts/interpret-in-static.opt.stderr
@@ -0,0 +1,17 @@
+error[E0080]: evaluation of `Fail::<i32>::C` failed
+  --> $DIR/interpret-in-static.rs:7:19
+   |
+LL |     const C: () = panic!();
+   |                   ^^^^^^^^ the evaluated program panicked at 'explicit panic', $DIR/interpret-in-static.rs:7:19
+   |
+   = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+note: erroneous constant encountered
+  --> $DIR/interpret-in-static.rs:15:9
+   |
+LL |         Fail::<i32>::C;
+   |         ^^^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/required-consts/interpret-in-static.rs b/tests/ui/consts/required-consts/interpret-in-static.rs
new file mode 100644
index 00000000000..559e281b2b0
--- /dev/null
+++ b/tests/ui/consts/required-consts/interpret-in-static.rs
@@ -0,0 +1,21 @@
+//@revisions: noopt opt
+//@[opt] compile-flags: -O
+//! Make sure we error on erroneous consts even if they are unused.
+
+struct Fail<T>(T);
+impl<T> Fail<T> {
+    const C: () = panic!(); //~ERROR evaluation of `Fail::<i32>::C` failed
+}
+
+pub static FOO: () = {
+    if false {
+        // This bad constant is only used in dead code in a static initializer... and yet we still
+        // must make sure that the build fails.
+        // This relies on const-eval evaluating all `required_consts` of the `static` MIR body.
+        Fail::<i32>::C; //~ constant
+    }
+};
+
+fn main() {
+    FOO
+}
diff --git a/tests/ui/coroutine/resume-arg-late-bound.rs b/tests/ui/coroutine/resume-arg-late-bound.rs
index dd6d318afbc..3c2ab41047e 100644
--- a/tests/ui/coroutine/resume-arg-late-bound.rs
+++ b/tests/ui/coroutine/resume-arg-late-bound.rs
@@ -13,5 +13,5 @@ fn main() {
         *arg = true;
     };
     test(gen);
-    //~^ ERROR mismatched types
+    //~^ ERROR implementation of `Coroutine` is not general enough
 }
diff --git a/tests/ui/coroutine/resume-arg-late-bound.stderr b/tests/ui/coroutine/resume-arg-late-bound.stderr
index a97cc6190fd..4a4ee08c529 100644
--- a/tests/ui/coroutine/resume-arg-late-bound.stderr
+++ b/tests/ui/coroutine/resume-arg-late-bound.stderr
@@ -1,17 +1,11 @@
-error[E0308]: mismatched types
+error: implementation of `Coroutine` is not general enough
   --> $DIR/resume-arg-late-bound.rs:15:5
    |
 LL |     test(gen);
-   |     ^^^^^^^^^ one type is more general than the other
+   |     ^^^^^^^^^ implementation of `Coroutine` is not general enough
    |
-   = note: expected trait `for<'a> Coroutine<&'a mut bool>`
-              found trait `Coroutine<&mut bool>`
-note: the lifetime requirement is introduced here
-  --> $DIR/resume-arg-late-bound.rs:8:17
-   |
-LL | fn test(a: impl for<'a> Coroutine<&'a mut bool>) {}
-   |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   = note: `{coroutine@$DIR/resume-arg-late-bound.rs:11:15: 11:31}` must implement `Coroutine<&'1 mut bool>`, for any lifetime `'1`...
+   = note: ...but it actually implements `Coroutine<&'2 mut bool>`, for some specific lifetime `'2`
 
 error: aborting due to 1 previous error
 
-For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/diagnostic_namespace/deny_malformed_attribute.rs b/tests/ui/diagnostic_namespace/deny_malformed_attribute.rs
new file mode 100644
index 00000000000..1d946a14aff
--- /dev/null
+++ b/tests/ui/diagnostic_namespace/deny_malformed_attribute.rs
@@ -0,0 +1,7 @@
+#![deny(unknown_or_malformed_diagnostic_attributes)]
+
+#[diagnostic::unknown_attribute]
+//~^ERROR unknown diagnostic attribute
+struct Foo;
+
+fn main() {}
diff --git a/tests/ui/diagnostic_namespace/deny_malformed_attribute.stderr b/tests/ui/diagnostic_namespace/deny_malformed_attribute.stderr
new file mode 100644
index 00000000000..a646d3613de
--- /dev/null
+++ b/tests/ui/diagnostic_namespace/deny_malformed_attribute.stderr
@@ -0,0 +1,14 @@
+error: unknown diagnostic attribute
+  --> $DIR/deny_malformed_attribute.rs:3:15
+   |
+LL | #[diagnostic::unknown_attribute]
+   |               ^^^^^^^^^^^^^^^^^
+   |
+note: the lint level is defined here
+  --> $DIR/deny_malformed_attribute.rs:1:9
+   |
+LL | #![deny(unknown_or_malformed_diagnostic_attributes)]
+   |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
diff --git a/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.next.stderr b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.next.stderr
new file mode 100644
index 00000000000..06ffff057f9
--- /dev/null
+++ b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.next.stderr
@@ -0,0 +1,48 @@
+error[E0283]: type annotations needed
+  --> $DIR/ambig-hr-projection-issue-93340.rs:16:5
+   |
+LL |     cmp_eq
+   |     ^^^^^^ cannot infer type of the type parameter `A` declared on the function `cmp_eq`
+   |
+   = note: cannot satisfy `_: Scalar`
+note: required by a bound in `cmp_eq`
+  --> $DIR/ambig-hr-projection-issue-93340.rs:9:22
+   |
+LL | fn cmp_eq<'a, 'b, A: Scalar, B: Scalar, O: Scalar>(a: A::RefType<'a>, b: B::RefType<'b>) -> O {
+   |                      ^^^^^^ required by this bound in `cmp_eq`
+help: consider specifying the generic arguments
+   |
+LL |     cmp_eq::<A, B, O>
+   |           +++++++++++
+
+error[E0275]: overflow evaluating the requirement `impl for<'a, 'b> Fn(<A as Scalar>::RefType<'a>, <B as Scalar>::RefType<'b>) -> O == for<'a, 'b> fn(..., ...) -> ... {cmp_eq::<..., ..., ...>}`
+  --> $DIR/ambig-hr-projection-issue-93340.rs:16:5
+   |
+LL |     cmp_eq
+   |     ^^^^^^
+
+error[E0275]: overflow evaluating the requirement `impl for<'a, 'b> Fn(<A as Scalar>::RefType<'a>, <B as Scalar>::RefType<'b>) -> O == for<'a, 'b> fn(..., ...) -> ... {cmp_eq::<..., ..., ...>}`
+  --> $DIR/ambig-hr-projection-issue-93340.rs:16:5
+   |
+LL |     cmp_eq
+   |     ^^^^^^
+   |
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
+error[E0275]: overflow evaluating the requirement `for<'a, 'b> fn(<O as Scalar>::RefType<'a>, <_ as Scalar>::RefType<'b>) -> _ {cmp_eq::<O, ..., ...>} <: ...`
+  --> $DIR/ambig-hr-projection-issue-93340.rs:14:51
+   |
+LL |   ) -> impl Fn(A::RefType<'_>, B::RefType<'_>) -> O {
+   |  ___________________________________________________^
+LL | |
+LL | |     cmp_eq
+LL | |
+LL | |
+LL | |
+LL | | }
+   | |_^
+
+error: aborting due to 4 previous errors
+
+Some errors have detailed explanations: E0275, E0283.
+For more information about an error, try `rustc --explain E0275`.
diff --git a/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.old.stderr b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.old.stderr
new file mode 100644
index 00000000000..df2ec4ab182
--- /dev/null
+++ b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.old.stderr
@@ -0,0 +1,20 @@
+error[E0283]: type annotations needed
+  --> $DIR/ambig-hr-projection-issue-93340.rs:16:5
+   |
+LL |     cmp_eq
+   |     ^^^^^^ cannot infer type of the type parameter `A` declared on the function `cmp_eq`
+   |
+   = note: cannot satisfy `_: Scalar`
+note: required by a bound in `cmp_eq`
+  --> $DIR/ambig-hr-projection-issue-93340.rs:9:22
+   |
+LL | fn cmp_eq<'a, 'b, A: Scalar, B: Scalar, O: Scalar>(a: A::RefType<'a>, b: B::RefType<'b>) -> O {
+   |                      ^^^^^^ required by this bound in `cmp_eq`
+help: consider specifying the generic arguments
+   |
+LL |     cmp_eq::<A, B, O>
+   |           +++++++++++
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0283`.
diff --git a/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.rs b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.rs
new file mode 100644
index 00000000000..4d8ea9d8d48
--- /dev/null
+++ b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.rs
@@ -0,0 +1,22 @@
+//@ revisions: old next
+//@[next] compile-flags: -Znext-solver
+pub trait Scalar: 'static {
+    type RefType<'a>: ScalarRef<'a>;
+}
+
+pub trait ScalarRef<'a>: 'a {}
+
+fn cmp_eq<'a, 'b, A: Scalar, B: Scalar, O: Scalar>(a: A::RefType<'a>, b: B::RefType<'b>) -> O {
+    todo!()
+}
+
+fn build_expression<A: Scalar, B: Scalar, O: Scalar>(
+) -> impl Fn(A::RefType<'_>, B::RefType<'_>) -> O {
+    //[next]~^ ERROR overflow evaluating the requirement
+    cmp_eq
+    //~^ ERROR type annotations needed
+    //[next]~| ERROR overflow evaluating the requirement
+    //[next]~| ERROR overflow evaluating the requirement
+}
+
+fn main() {}
diff --git a/tests/ui/generic-associated-types/bugs/issue-88382.stderr b/tests/ui/generic-associated-types/bugs/issue-88382.stderr
index 9b061528e3b..0f5e394ab61 100644
--- a/tests/ui/generic-associated-types/bugs/issue-88382.stderr
+++ b/tests/ui/generic-associated-types/bugs/issue-88382.stderr
@@ -1,26 +1,21 @@
-error[E0631]: type mismatch in function arguments
+error[E0283]: type annotations needed
   --> $DIR/issue-88382.rs:26:40
    |
 LL |     do_something(SomeImplementation(), test);
-   |     ------------                       ^^^^ expected due to this
-   |     |
-   |     required by a bound introduced by this call
-...
-LL | fn test<'a, I: Iterable>(_: &mut I::Iterator<'a>) {}
-   | ------------------------------------------------- found signature defined here
+   |                                        ^^^^ cannot infer type of the type parameter `I` declared on the function `test`
    |
-   = note: expected function signature `for<'a> fn(&'a mut std::iter::Empty<usize>) -> _`
-              found function signature `for<'a, 'b> fn(&'b mut <_ as Iterable>::Iterator<'a>) -> _`
-note: required by a bound in `do_something`
-  --> $DIR/issue-88382.rs:20:48
+   = note: cannot satisfy `_: Iterable`
+   = help: the trait `Iterable` is implemented for `SomeImplementation`
+note: required by a bound in `test`
+  --> $DIR/issue-88382.rs:29:16
    |
-LL | fn do_something<I: Iterable>(i: I, mut f: impl for<'a> Fn(&mut I::Iterator<'a>)) {
-   |                                                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `do_something`
-help: consider wrapping the function in a closure
+LL | fn test<'a, I: Iterable>(_: &mut I::Iterator<'a>) {}
+   |                ^^^^^^^^ required by this bound in `test`
+help: consider specifying the generic argument
    |
-LL |     do_something(SomeImplementation(), |arg0: &mut std::iter::Empty<usize>| test(/* &mut <_ as Iterable>::Iterator<'_> */));
-   |                                        ++++++++++++++++++++++++++++++++++++     ++++++++++++++++++++++++++++++++++++++++++
+LL |     do_something(SomeImplementation(), test::<I>);
+   |                                            +++++
 
 error: aborting due to 1 previous error
 
-For more information about this error, try `rustc --explain E0631`.
+For more information about this error, try `rustc --explain E0283`.
diff --git a/tests/ui/generic-associated-types/issue-93340.rs b/tests/ui/generic-associated-types/rigid-hr-projection-issue-93340.rs
index 783f8c06ebf..b55ca845cd3 100644
--- a/tests/ui/generic-associated-types/issue-93340.rs
+++ b/tests/ui/generic-associated-types/rigid-hr-projection-issue-93340.rs
@@ -1,3 +1,5 @@
+//@ revisions: old next
+//@[next] compile-flags: -Znext-solver
 //@ check-pass
 
 pub trait Scalar: 'static {
@@ -12,7 +14,7 @@ fn cmp_eq<'a, 'b, A: Scalar, B: Scalar, O: Scalar>(a: A::RefType<'a>, b: B::RefT
 
 fn build_expression<A: Scalar, B: Scalar, O: Scalar>(
 ) -> impl Fn(A::RefType<'_>, B::RefType<'_>) -> O {
-    cmp_eq
+    cmp_eq::<A, B, O>
 }
 
 fn main() {}
diff --git a/tests/ui/generics/post_monomorphization_error_backtrace.rs b/tests/ui/generics/post_monomorphization_error_backtrace.rs
index 56155ae2bd5..2c18f2b233a 100644
--- a/tests/ui/generics/post_monomorphization_error_backtrace.rs
+++ b/tests/ui/generics/post_monomorphization_error_backtrace.rs
@@ -12,6 +12,9 @@ fn assert_zst<T>() {
         //~| NOTE: the evaluated program panicked
     }
     F::<T>::V;
+    //~^NOTE: erroneous constant
+    //~|NOTE: erroneous constant
+    //~|NOTE: duplicate
 }
 
 fn foo<U>() {
diff --git a/tests/ui/generics/post_monomorphization_error_backtrace.stderr b/tests/ui/generics/post_monomorphization_error_backtrace.stderr
index 0d707d83d26..8a57979bca7 100644
--- a/tests/ui/generics/post_monomorphization_error_backtrace.stderr
+++ b/tests/ui/generics/post_monomorphization_error_backtrace.stderr
@@ -6,8 +6,14 @@ LL |         const V: () = assert!(std::mem::size_of::<T>() == 0);
    |
    = note: this error originates in the macro `assert` (in Nightly builds, run with -Z macro-backtrace for more info)
 
+note: erroneous constant encountered
+  --> $DIR/post_monomorphization_error_backtrace.rs:14:5
+   |
+LL |     F::<T>::V;
+   |     ^^^^^^^^^
+
 note: the above error was encountered while instantiating `fn assert_zst::<u32>`
-  --> $DIR/post_monomorphization_error_backtrace.rs:18:5
+  --> $DIR/post_monomorphization_error_backtrace.rs:21:5
    |
 LL |     assert_zst::<U>()
    |     ^^^^^^^^^^^^^^^^^
@@ -20,8 +26,16 @@ LL |         const V: () = assert!(std::mem::size_of::<T>() == 0);
    |
    = note: this error originates in the macro `assert` (in Nightly builds, run with -Z macro-backtrace for more info)
 
+note: erroneous constant encountered
+  --> $DIR/post_monomorphization_error_backtrace.rs:14:5
+   |
+LL |     F::<T>::V;
+   |     ^^^^^^^^^
+   |
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
 note: the above error was encountered while instantiating `fn assert_zst::<i32>`
-  --> $DIR/post_monomorphization_error_backtrace.rs:18:5
+  --> $DIR/post_monomorphization_error_backtrace.rs:21:5
    |
 LL |     assert_zst::<U>()
    |     ^^^^^^^^^^^^^^^^^
diff --git a/tests/ui/half-open-range-patterns/half-open-range-pats-exhaustive-fail.stderr b/tests/ui/half-open-range-patterns/half-open-range-pats-exhaustive-fail.stderr
index 6b20a820b73..bb4c2a4c523 100644
--- a/tests/ui/half-open-range-patterns/half-open-range-pats-exhaustive-fail.stderr
+++ b/tests/ui/half-open-range-patterns/half-open-range-pats-exhaustive-fail.stderr
@@ -394,17 +394,17 @@ help: ensure that all possible cases are being handled by adding a match arm wit
 LL |         match $s { $($t)+ => {}, u128::MAX => todo!() }
    |                                ++++++++++++++++++++++
 
-error[E0004]: non-exhaustive patterns: `340282366920938463463374607431768211454_u128..=u128::MAX` not covered
+error[E0004]: non-exhaustive patterns: `340282366920938463463374607431768211454_u128..` not covered
   --> $DIR/half-open-range-pats-exhaustive-fail.rs:93:12
    |
 LL |         m!(0, ..ALMOST_MAX);
-   |            ^ pattern `340282366920938463463374607431768211454_u128..=u128::MAX` not covered
+   |            ^ pattern `340282366920938463463374607431768211454_u128..` not covered
    |
    = note: the matched value is of type `u128`
 help: ensure that all possible cases are being handled by adding a match arm with a wildcard pattern or an explicit pattern as shown
    |
-LL |         match $s { $($t)+ => {}, 340282366920938463463374607431768211454_u128..=u128::MAX => todo!() }
-   |                                +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+LL |         match $s { $($t)+ => {}, 340282366920938463463374607431768211454_u128.. => todo!() }
+   |                                +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 
 error[E0004]: non-exhaustive patterns: `0_u128` not covered
   --> $DIR/half-open-range-pats-exhaustive-fail.rs:94:12
@@ -754,17 +754,17 @@ help: ensure that all possible cases are being handled by adding a match arm wit
 LL |         match $s { $($t)+ => {}, i128::MAX => todo!() }
    |                                ++++++++++++++++++++++
 
-error[E0004]: non-exhaustive patterns: `170141183460469231731687303715884105726_i128..=i128::MAX` not covered
+error[E0004]: non-exhaustive patterns: `170141183460469231731687303715884105726_i128..` not covered
   --> $DIR/half-open-range-pats-exhaustive-fail.rs:161:12
    |
 LL |         m!(0, ..ALMOST_MAX);
-   |            ^ pattern `170141183460469231731687303715884105726_i128..=i128::MAX` not covered
+   |            ^ pattern `170141183460469231731687303715884105726_i128..` not covered
    |
    = note: the matched value is of type `i128`
 help: ensure that all possible cases are being handled by adding a match arm with a wildcard pattern or an explicit pattern as shown
    |
-LL |         match $s { $($t)+ => {}, 170141183460469231731687303715884105726_i128..=i128::MAX => todo!() }
-   |                                +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+LL |         match $s { $($t)+ => {}, 170141183460469231731687303715884105726_i128.. => todo!() }
+   |                                +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 
 error[E0004]: non-exhaustive patterns: `i128::MIN` not covered
   --> $DIR/half-open-range-pats-exhaustive-fail.rs:162:12
diff --git a/tests/ui/higher-ranked/higher-ranked-lifetime-error.rs b/tests/ui/higher-ranked/higher-ranked-lifetime-error.rs
index aee5db83669..f89a37c8512 100644
--- a/tests/ui/higher-ranked/higher-ranked-lifetime-error.rs
+++ b/tests/ui/higher-ranked/higher-ranked-lifetime-error.rs
@@ -10,5 +10,5 @@ fn id(x: &String) -> &String {
 
 fn main() {
     assert_all::<_, &String>(id);
-    //~^ mismatched types
+    //~^ ERROR implementation of `FnMut` is not general enough
 }
diff --git a/tests/ui/higher-ranked/higher-ranked-lifetime-error.stderr b/tests/ui/higher-ranked/higher-ranked-lifetime-error.stderr
index c25e731d962..d7add865aa0 100644
--- a/tests/ui/higher-ranked/higher-ranked-lifetime-error.stderr
+++ b/tests/ui/higher-ranked/higher-ranked-lifetime-error.stderr
@@ -1,12 +1,11 @@
-error[E0308]: mismatched types
+error: implementation of `FnMut` is not general enough
   --> $DIR/higher-ranked-lifetime-error.rs:12:5
    |
 LL |     assert_all::<_, &String>(id);
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^ one type is more general than the other
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^ implementation of `FnMut` is not general enough
    |
-   = note: expected trait `for<'a> <for<'a> fn(&'a String) -> &'a String {id} as FnMut<(&'a String,)>>`
-              found trait `for<'a> <for<'a> fn(&'a String) -> &'a String {id} as FnMut<(&'a String,)>>`
+   = note: `for<'a> fn(&'a String) -> &'a String {id}` must implement `FnMut<(&String,)>`
+   = note: ...but it actually implements `FnMut<(&'0 String,)>`, for some specific lifetime `'0`
 
 error: aborting due to 1 previous error
 
-For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/higher-ranked/trait-bounds/issue-59311.rs b/tests/ui/higher-ranked/trait-bounds/issue-59311.rs
index 387c78a802a..4e722dc0e80 100644
--- a/tests/ui/higher-ranked/trait-bounds/issue-59311.rs
+++ b/tests/ui/higher-ranked/trait-bounds/issue-59311.rs
@@ -6,17 +6,17 @@
 // an error, but the regression test is here to ensure
 // that it does not ICE. See discussion on #74889 for details.
 
-pub trait T {
+pub trait Trait {
     fn t<F: Fn()>(&self, _: F) {}
 }
 
 pub fn crash<V>(v: &V)
 where
-    for<'a> &'a V: T + 'static,
+    for<'a> &'a V: Trait + 'static,
 {
     v.t(|| {});
-    //~^ ERROR: higher-ranked lifetime error
-    //~| ERROR: higher-ranked lifetime error
+    //~^ ERROR: implementation of `Trait` is not general enough
+    //~| ERROR: implementation of `Trait` is not general enough
     //~| ERROR: higher-ranked lifetime error
 }
 
diff --git a/tests/ui/higher-ranked/trait-bounds/issue-59311.stderr b/tests/ui/higher-ranked/trait-bounds/issue-59311.stderr
index 3053a299802..f8bed86ccf5 100644
--- a/tests/ui/higher-ranked/trait-bounds/issue-59311.stderr
+++ b/tests/ui/higher-ranked/trait-bounds/issue-59311.stderr
@@ -1,18 +1,20 @@
-error: higher-ranked lifetime error
+error: implementation of `Trait` is not general enough
   --> $DIR/issue-59311.rs:17:5
    |
 LL |     v.t(|| {});
-   |     ^^^^^^^^^^
+   |     ^^^^^^^^^^ implementation of `Trait` is not general enough
    |
-   = note: could not prove `{closure@$DIR/issue-59311.rs:17:9: 17:11} well-formed`
+   = note: `Trait` would have to be implemented for the type `&'a V`
+   = note: ...but `Trait` is actually implemented for the type `&'0 V`, for some specific lifetime `'0`
 
-error: higher-ranked lifetime error
+error: implementation of `Trait` is not general enough
   --> $DIR/issue-59311.rs:17:5
    |
 LL |     v.t(|| {});
-   |     ^^^^^^^^^^
+   |     ^^^^^^^^^^ implementation of `Trait` is not general enough
    |
-   = note: could not prove `{closure@$DIR/issue-59311.rs:17:9: 17:11} well-formed`
+   = note: `Trait` would have to be implemented for the type `&'a V`
+   = note: ...but `Trait` is actually implemented for the type `&'0 V`, for some specific lifetime `'0`
    = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
 error: higher-ranked lifetime error
diff --git a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-71955.rs b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-71955.rs
index 4bd3b96e475..a44ed9e5ef5 100644
--- a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-71955.rs
+++ b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-71955.rs
@@ -43,9 +43,9 @@ fn main() {
     }
 
     foo(bar, "string", |s| s.len() == 5);
-    //~^ ERROR mismatched types
-    //~| ERROR mismatched types
+    //~^ ERROR implementation of `FnOnce` is not general enough
+    //~| ERROR implementation of `FnOnce` is not general enough
     foo(baz, "string", |s| s.0.len() == 5);
-    //~^ ERROR mismatched types
-    //~| ERROR mismatched types
+    //~^ ERROR implementation of `FnOnce` is not general enough
+    //~| ERROR implementation of `FnOnce` is not general enough
 }
diff --git a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-71955.stderr b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-71955.stderr
index 1cf364aa9f6..b2bb417a8f0 100644
--- a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-71955.stderr
+++ b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-71955.stderr
@@ -1,79 +1,40 @@
-error[E0308]: mismatched types
+error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-71955.rs:45:5
    |
 LL |     foo(bar, "string", |s| s.len() == 5);
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ one type is more general than the other
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ implementation of `FnOnce` is not general enough
    |
-   = note: expected trait `for<'a, 'b> FnOnce(&'a &'b str)`
-              found trait `for<'a> FnOnce(&'a &str)`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/issue-71955.rs:45:24
-   |
-LL |     foo(bar, "string", |s| s.len() == 5);
-   |                        ^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-71955.rs:25:9
-   |
-LL |     F2: FnOnce(&<F1 as Parser>::Output) -> bool
-   |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   = note: closure with signature `for<'a> fn(&'a &'2 str) -> bool` must implement `FnOnce<(&&'1 str,)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `FnOnce<(&&'2 str,)>`, for some specific lifetime `'2`
 
-error[E0308]: mismatched types
+error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-71955.rs:45:5
    |
 LL |     foo(bar, "string", |s| s.len() == 5);
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ one type is more general than the other
-   |
-   = note: expected trait `for<'a, 'b> FnOnce(&'a &'b str)`
-              found trait `for<'a> FnOnce(&'a &str)`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/issue-71955.rs:45:24
-   |
-LL |     foo(bar, "string", |s| s.len() == 5);
-   |                        ^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-71955.rs:25:44
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ implementation of `FnOnce` is not general enough
    |
-LL |     F2: FnOnce(&<F1 as Parser>::Output) -> bool
-   |                                            ^^^^
+   = note: closure with signature `for<'a> fn(&'a &'2 str) -> bool` must implement `FnOnce<(&&'1 str,)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `FnOnce<(&&'2 str,)>`, for some specific lifetime `'2`
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
-error[E0308]: mismatched types
+error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-71955.rs:48:5
    |
 LL |     foo(baz, "string", |s| s.0.len() == 5);
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ one type is more general than the other
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ implementation of `FnOnce` is not general enough
    |
-   = note: expected trait `for<'a, 'b> FnOnce(&'a Wrapper<'b>)`
-              found trait `for<'a> FnOnce(&'a Wrapper<'_>)`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/issue-71955.rs:48:24
-   |
-LL |     foo(baz, "string", |s| s.0.len() == 5);
-   |                        ^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-71955.rs:25:9
-   |
-LL |     F2: FnOnce(&<F1 as Parser>::Output) -> bool
-   |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   = note: closure with signature `for<'a> fn(&'a Wrapper<'2>) -> bool` must implement `FnOnce<(&Wrapper<'1>,)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `FnOnce<(&Wrapper<'2>,)>`, for some specific lifetime `'2`
 
-error[E0308]: mismatched types
+error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-71955.rs:48:5
    |
 LL |     foo(baz, "string", |s| s.0.len() == 5);
-   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ one type is more general than the other
-   |
-   = note: expected trait `for<'a, 'b> FnOnce(&'a Wrapper<'b>)`
-              found trait `for<'a> FnOnce(&'a Wrapper<'_>)`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/issue-71955.rs:48:24
-   |
-LL |     foo(baz, "string", |s| s.0.len() == 5);
-   |                        ^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-71955.rs:25:44
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ implementation of `FnOnce` is not general enough
    |
-LL |     F2: FnOnce(&<F1 as Parser>::Output) -> bool
-   |                                            ^^^^
+   = note: closure with signature `for<'a> fn(&'a Wrapper<'2>) -> bool` must implement `FnOnce<(&Wrapper<'1>,)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `FnOnce<(&Wrapper<'2>,)>`, for some specific lifetime `'2`
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
 error: aborting due to 4 previous errors
 
-For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/impl-trait/in-trait/ensure-rpitits-are-created-before-freezing.rs b/tests/ui/impl-trait/in-trait/ensure-rpitits-are-created-before-freezing.rs
new file mode 100644
index 00000000000..35a6acca52c
--- /dev/null
+++ b/tests/ui/impl-trait/in-trait/ensure-rpitits-are-created-before-freezing.rs
@@ -0,0 +1,13 @@
+trait Iterable {
+    type Item;
+    fn iter(&self) -> impl Sized;
+}
+
+// `ty::Error` in a trait ref will silence any missing item errors, but will also
+// prevent the `associated_items` query from being called before def ids are frozen.
+impl Iterable for Missing {
+//~^ ERROR cannot find type `Missing` in this scope
+    fn iter(&self) -> Self::Item {}
+}
+
+fn main() {}
diff --git a/tests/ui/impl-trait/in-trait/ensure-rpitits-are-created-before-freezing.stderr b/tests/ui/impl-trait/in-trait/ensure-rpitits-are-created-before-freezing.stderr
new file mode 100644
index 00000000000..c172787e6ef
--- /dev/null
+++ b/tests/ui/impl-trait/in-trait/ensure-rpitits-are-created-before-freezing.stderr
@@ -0,0 +1,9 @@
+error[E0412]: cannot find type `Missing` in this scope
+  --> $DIR/ensure-rpitits-are-created-before-freezing.rs:8:19
+   |
+LL | impl Iterable for Missing {
+   |                   ^^^^^^^ not found in this scope
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0412`.
diff --git a/tests/ui/impl-trait/in-trait/return-dont-satisfy-bounds.rs b/tests/ui/impl-trait/in-trait/return-dont-satisfy-bounds.rs
index ff265e576b9..84bc39d9263 100644
--- a/tests/ui/impl-trait/in-trait/return-dont-satisfy-bounds.rs
+++ b/tests/ui/impl-trait/in-trait/return-dont-satisfy-bounds.rs
@@ -9,6 +9,7 @@ impl Foo<char> for Bar {
         //~^ ERROR: the trait bound `impl Foo<u8>: Foo<char>` is not satisfied [E0277]
         //~| ERROR: the trait bound `Bar: Foo<u8>` is not satisfied [E0277]
         //~| ERROR: impl has stricter requirements than trait
+        //~| ERROR: the trait bound `F2: Foo<u8>` is not satisfied
         self
     }
 }
diff --git a/tests/ui/impl-trait/in-trait/return-dont-satisfy-bounds.stderr b/tests/ui/impl-trait/in-trait/return-dont-satisfy-bounds.stderr
index 12725c3456f..fbf82a24b50 100644
--- a/tests/ui/impl-trait/in-trait/return-dont-satisfy-bounds.stderr
+++ b/tests/ui/impl-trait/in-trait/return-dont-satisfy-bounds.stderr
@@ -11,6 +11,22 @@ note: required by a bound in `Foo::{synthetic#0}`
 LL |     fn foo<F2>(self) -> impl Foo<T>;
    |                              ^^^^^^ required by this bound in `Foo::{synthetic#0}`
 
+error[E0277]: the trait bound `F2: Foo<u8>` is not satisfied
+  --> $DIR/return-dont-satisfy-bounds.rs:8:34
+   |
+LL |     fn foo<F2: Foo<u8>>(self) -> impl Foo<u8> {
+   |                                  ^^^^^^^^^^^^ the trait `Foo<u8>` is not implemented for `F2`
+   |
+note: required by a bound in `<Bar as Foo<char>>::foo`
+  --> $DIR/return-dont-satisfy-bounds.rs:8:16
+   |
+LL |     fn foo<F2: Foo<u8>>(self) -> impl Foo<u8> {
+   |                ^^^^^^^ required by this bound in `<Bar as Foo<char>>::foo`
+help: consider further restricting this bound
+   |
+LL |     fn foo<F2: Foo<u8> + Foo<u8>>(self) -> impl Foo<u8> {
+   |                        +++++++++
+
 error[E0276]: impl has stricter requirements than trait
   --> $DIR/return-dont-satisfy-bounds.rs:8:16
    |
@@ -32,7 +48,7 @@ LL |         self
    = help: the trait `Foo<char>` is implemented for `Bar`
    = help: for that trait implementation, expected `char`, found `u8`
 
-error: aborting due to 3 previous errors
+error: aborting due to 4 previous errors
 
 Some errors have detailed explanations: E0276, E0277.
 For more information about an error, try `rustc --explain E0276`.
diff --git a/tests/ui/impl-trait/stranded-opaque.rs b/tests/ui/impl-trait/stranded-opaque.rs
new file mode 100644
index 00000000000..c7ab390e1fd
--- /dev/null
+++ b/tests/ui/impl-trait/stranded-opaque.rs
@@ -0,0 +1,13 @@
+trait Trait {}
+
+impl Trait for i32 {}
+
+// Since `Assoc` doesn't actually exist, it's "stranded", and won't show up in
+// the list of opaques that may be defined by the function. Make sure we don't
+// ICE in this case.
+fn produce<T>() -> impl Trait<Assoc = impl Trait> {
+    //~^ ERROR associated type `Assoc` not found for `Trait`
+    16
+}
+
+fn main () {}
diff --git a/tests/ui/impl-trait/stranded-opaque.stderr b/tests/ui/impl-trait/stranded-opaque.stderr
new file mode 100644
index 00000000000..75f5480bc8b
--- /dev/null
+++ b/tests/ui/impl-trait/stranded-opaque.stderr
@@ -0,0 +1,9 @@
+error[E0220]: associated type `Assoc` not found for `Trait`
+  --> $DIR/stranded-opaque.rs:8:31
+   |
+LL | fn produce<T>() -> impl Trait<Assoc = impl Trait> {
+   |                               ^^^^^ associated type `Assoc` not found
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0220`.
diff --git a/tests/ui/implied-bounds/gluon_salsa.rs b/tests/ui/implied-bounds/gluon_salsa.rs
index 368fb197909..cc6352c4a32 100644
--- a/tests/ui/implied-bounds/gluon_salsa.rs
+++ b/tests/ui/implied-bounds/gluon_salsa.rs
@@ -1,5 +1,6 @@
 //@ check-pass
-// Found in a crater run on #118553
+// Related to Bevy regression #115559, found in
+// a crater run on #118553.
 
 pub trait QueryBase {
     type Db;
@@ -17,11 +18,17 @@ pub struct QueryTable<'me, Q, DB> {
     _marker: Option<&'me ()>,
 }
 
-impl<'me, Q> QueryTable<'me, Q, <Q as QueryBase>::Db> // projection is important
-//   ^^^ removing 'me (and in QueryTable) gives a different error
+impl<'me, Q> QueryTable<'me, Q, <Q as QueryBase>::Db>
 where
     Q: for<'f> AsyncQueryFunction<'f>,
 {
+    // When borrowchechking this function we normalize `<Q as QueryBase>::Db` in the
+    // function signature to `<Self as QueryFunction<'?x>>::SendDb`, where `'?x` is an
+    // unconstrained region variable. We then addd `<Self as QueryFunction<'?x>>::SendDb: 'a`
+    // as an implied bound. We currently a structural equality to decide whether this bound
+    // should be used to prove the bound  `<Self as QueryFunction<'?x>>::SendDb: 'a`. For this
+    // to work we may have to structurally resolve regions as the actually used vars may
+    // otherwise be semantically equal but structurally different.
     pub fn get_async<'a>(&'a mut self) {
         panic!();
     }
diff --git a/tests/ui/inline-const/const-expr-generic-err.stderr b/tests/ui/inline-const/const-expr-generic-err.stderr
index fc0b6cc4451..7331c7f18e9 100644
--- a/tests/ui/inline-const/const-expr-generic-err.stderr
+++ b/tests/ui/inline-const/const-expr-generic-err.stderr
@@ -6,6 +6,12 @@ LL |     const { assert!(std::mem::size_of::<T>() == 0); }
    |
    = note: this error originates in the macro `assert` (in Nightly builds, run with -Z macro-backtrace for more info)
 
+note: erroneous constant encountered
+  --> $DIR/const-expr-generic-err.rs:5:5
+   |
+LL |     const { assert!(std::mem::size_of::<T>() == 0); }
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
 note: the above error was encountered while instantiating `fn foo::<i32>`
   --> $DIR/const-expr-generic-err.rs:13:5
    |
@@ -18,6 +24,20 @@ error[E0080]: evaluation of `bar::<0>::{constant#0}` failed
 LL |     const { N - 1 }
    |             ^^^^^ attempt to compute `0_usize - 1_usize`, which would overflow
 
+note: erroneous constant encountered
+  --> $DIR/const-expr-generic-err.rs:9:5
+   |
+LL |     const { N - 1 }
+   |     ^^^^^^^^^^^^^^^
+
+note: erroneous constant encountered
+  --> $DIR/const-expr-generic-err.rs:9:5
+   |
+LL |     const { N - 1 }
+   |     ^^^^^^^^^^^^^^^
+   |
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
 note: the above error was encountered while instantiating `fn bar::<0>`
   --> $DIR/const-expr-generic-err.rs:14:5
    |
diff --git a/tests/ui/inline-const/required-const.stderr b/tests/ui/inline-const/required-const.stderr
index cd86020184d..2a13d18547c 100644
--- a/tests/ui/inline-const/required-const.stderr
+++ b/tests/ui/inline-const/required-const.stderr
@@ -6,6 +6,12 @@ LL |         const { panic!() }
    |
    = note: this error originates in the macro `$crate::panic::panic_2015` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
 
+note: erroneous constant encountered
+  --> $DIR/required-const.rs:7:9
+   |
+LL |         const { panic!() }
+   |         ^^^^^^^^^^^^^^^^^^
+
 error: aborting due to 1 previous error
 
 For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/lifetimes/issue-105675.rs b/tests/ui/lifetimes/issue-105675.rs
index 58d8be8b65f..2e2eaca0d33 100644
--- a/tests/ui/lifetimes/issue-105675.rs
+++ b/tests/ui/lifetimes/issue-105675.rs
@@ -3,12 +3,12 @@ fn thing(x: impl FnOnce(&u32, &u32, u32)) {}
 fn main() {
     let f = | _ , y: &u32 , z | ();
     thing(f);
-    //~^ ERROR mismatched types
-    //~^^ ERROR mismatched types
+    //~^ ERROR implementation of `FnOnce` is not general enough
+    //~^^ ERROR implementation of `FnOnce` is not general enough
     let f = | x, y: _  , z: u32 | ();
     thing(f);
-    //~^ ERROR mismatched types
-    //~^^ ERROR mismatched types
-    //~^^^ ERROR implementation of `FnOnce` is not general enough
-    //~^^^^ ERROR implementation of `FnOnce` is not general enough
+    //~^ ERROR implementation of `FnOnce` is not general enough
+    //~| ERROR implementation of `FnOnce` is not general enough
+    //~| ERROR implementation of `FnOnce` is not general enough
+    //~| ERROR implementation of `FnOnce` is not general enough
 }
diff --git a/tests/ui/lifetimes/issue-105675.stderr b/tests/ui/lifetimes/issue-105675.stderr
index f1fa5a59860..4b3d0e8ac5e 100644
--- a/tests/ui/lifetimes/issue-105675.stderr
+++ b/tests/ui/lifetimes/issue-105675.stderr
@@ -1,91 +1,39 @@
-error[E0308]: mismatched types
+error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-105675.rs:5:5
    |
 LL |     thing(f);
-   |     ^^^^^^^^ one type is more general than the other
-   |
-   = note: expected trait `for<'a, 'b> FnOnce(&'a u32, &'b u32, u32)`
-              found trait `for<'a> FnOnce(&u32, &'a u32, u32)`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/issue-105675.rs:4:13
-   |
-LL |     let f = | _ , y: &u32 , z | ();
-   |             ^^^^^^^^^^^^^^^^^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-105675.rs:1:18
-   |
-LL | fn thing(x: impl FnOnce(&u32, &u32, u32)) {}
-   |                  ^^^^^^^^^^^^^^^^^^^^^^^
-help: consider specifying the type of the closure parameters
+   |     ^^^^^^^^ implementation of `FnOnce` is not general enough
    |
-LL |     let f = |_: &_, y: &u32, z| ();
-   |             ~~~~~~~~~~~~~~~~~~~
+   = note: closure with signature `for<'a> fn(&'2 u32, &'a u32, u32)` must implement `FnOnce<(&'1 u32, &u32, u32)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `FnOnce<(&'2 u32, &u32, u32)>`, for some specific lifetime `'2`
 
-error[E0308]: mismatched types
+error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-105675.rs:5:5
    |
 LL |     thing(f);
-   |     ^^^^^^^^ one type is more general than the other
-   |
-   = note: expected trait `for<'a, 'b> FnOnce(&'a u32, &'b u32, u32)`
-              found trait `for<'a> FnOnce(&u32, &'a u32, u32)`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/issue-105675.rs:4:13
-   |
-LL |     let f = | _ , y: &u32 , z | ();
-   |             ^^^^^^^^^^^^^^^^^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-105675.rs:1:18
+   |     ^^^^^^^^ implementation of `FnOnce` is not general enough
    |
-LL | fn thing(x: impl FnOnce(&u32, &u32, u32)) {}
-   |                  ^^^^^^^^^^^^^^^^^^^^^^^
+   = note: closure with signature `for<'a> fn(&'2 u32, &'a u32, u32)` must implement `FnOnce<(&'1 u32, &u32, u32)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `FnOnce<(&'2 u32, &u32, u32)>`, for some specific lifetime `'2`
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
-error[E0308]: mismatched types
+error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-105675.rs:9:5
    |
 LL |     thing(f);
-   |     ^^^^^^^^ one type is more general than the other
-   |
-   = note: expected trait `for<'a, 'b> FnOnce(&'a u32, &'b u32, u32)`
-              found trait `FnOnce(&u32, &u32, u32)`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/issue-105675.rs:8:13
-   |
-LL |     let f = | x, y: _  , z: u32 | ();
-   |             ^^^^^^^^^^^^^^^^^^^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-105675.rs:1:18
-   |
-LL | fn thing(x: impl FnOnce(&u32, &u32, u32)) {}
-   |                  ^^^^^^^^^^^^^^^^^^^^^^^
-help: consider specifying the type of the closure parameters
+   |     ^^^^^^^^ implementation of `FnOnce` is not general enough
    |
-LL |     let f = |x: &_, y: &_, z: u32| ();
-   |             ~~~~~~~~~~~~~~~~~~~~~~
+   = note: closure with signature `fn(&'2 u32, &u32, u32)` must implement `FnOnce<(&'1 u32, &u32, u32)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `FnOnce<(&'2 u32, &u32, u32)>`, for some specific lifetime `'2`
 
-error[E0308]: mismatched types
+error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-105675.rs:9:5
    |
 LL |     thing(f);
-   |     ^^^^^^^^ one type is more general than the other
-   |
-   = note: expected trait `for<'a, 'b> FnOnce(&'a u32, &'b u32, u32)`
-              found trait `FnOnce(&u32, &u32, u32)`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/issue-105675.rs:8:13
-   |
-LL |     let f = | x, y: _  , z: u32 | ();
-   |             ^^^^^^^^^^^^^^^^^^^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-105675.rs:1:18
-   |
-LL | fn thing(x: impl FnOnce(&u32, &u32, u32)) {}
-   |                  ^^^^^^^^^^^^^^^^^^^^^^^
-   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
-help: consider specifying the type of the closure parameters
+   |     ^^^^^^^^ implementation of `FnOnce` is not general enough
    |
-LL |     let f = |x: &_, y: &_, z: u32| ();
-   |             ~~~~~~~~~~~~~~~~~~~~~~
+   = note: closure with signature `fn(&u32, &'2 u32, u32)` must implement `FnOnce<(&u32, &'1 u32, u32)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `FnOnce<(&u32, &'2 u32, u32)>`, for some specific lifetime `'2`
 
 error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-105675.rs:9:5
@@ -95,6 +43,7 @@ LL |     thing(f);
    |
    = note: closure with signature `fn(&'2 u32, &u32, u32)` must implement `FnOnce<(&'1 u32, &u32, u32)>`, for any lifetime `'1`...
    = note: ...but it actually implements `FnOnce<(&'2 u32, &u32, u32)>`, for some specific lifetime `'2`
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
 error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-105675.rs:9:5
@@ -104,7 +53,7 @@ LL |     thing(f);
    |
    = note: closure with signature `fn(&u32, &'2 u32, u32)` must implement `FnOnce<(&u32, &'1 u32, u32)>`, for any lifetime `'1`...
    = note: ...but it actually implements `FnOnce<(&u32, &'2 u32, u32)>`, for some specific lifetime `'2`
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
 error: aborting due to 6 previous errors
 
-For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/lifetimes/issue-76168-hr-outlives-3.rs b/tests/ui/lifetimes/issue-76168-hr-outlives-3.rs
index 85eeb5d4c90..eab436fa341 100644
--- a/tests/ui/lifetimes/issue-76168-hr-outlives-3.rs
+++ b/tests/ui/lifetimes/issue-76168-hr-outlives-3.rs
@@ -7,6 +7,7 @@ async fn wrapper<F>(f: F)
 //~^ ERROR: expected a `FnOnce(&'a mut i32)` closure, found `i32`
 //~| ERROR: expected a `FnOnce(&'a mut i32)` closure, found `i32`
 //~| ERROR: expected a `FnOnce(&'a mut i32)` closure, found `i32`
+//~| ERROR: expected a `FnOnce(&'a mut i32)` closure, found `i32`
 where
 F:,
 for<'a> <i32 as FnOnce<(&'a mut i32,)>>::Output: Future<Output = ()> + 'a,
diff --git a/tests/ui/lifetimes/issue-76168-hr-outlives-3.stderr b/tests/ui/lifetimes/issue-76168-hr-outlives-3.stderr
index 578ba149baf..e9f97d1d93b 100644
--- a/tests/ui/lifetimes/issue-76168-hr-outlives-3.stderr
+++ b/tests/ui/lifetimes/issue-76168-hr-outlives-3.stderr
@@ -5,7 +5,7 @@ LL | / async fn wrapper<F>(f: F)
 LL | |
 LL | |
 LL | |
-LL | | where
+...  |
 LL | | F:,
 LL | | for<'a> <i32 as FnOnce<(&'a mut i32,)>>::Output: Future<Output = ()> + 'a,
    | |__________________________________________________________________________^ expected an `FnOnce(&'a mut i32)` closure, found `i32`
@@ -27,7 +27,7 @@ LL | / async fn wrapper<F>(f: F)
 LL | |
 LL | |
 LL | |
-LL | | where
+...  |
 LL | | F:,
 LL | | for<'a> <i32 as FnOnce<(&'a mut i32,)>>::Output: Future<Output = ()> + 'a,
    | |__________________________________________________________________________^ expected an `FnOnce(&'a mut i32)` closure, found `i32`
@@ -35,7 +35,22 @@ LL | | for<'a> <i32 as FnOnce<(&'a mut i32,)>>::Output: Future<Output = ()> + 'a
    = help: the trait `for<'a> FnOnce<(&'a mut i32,)>` is not implemented for `i32`
 
 error[E0277]: expected a `FnOnce(&'a mut i32)` closure, found `i32`
-  --> $DIR/issue-76168-hr-outlives-3.rs:13:1
+  --> $DIR/issue-76168-hr-outlives-3.rs:6:1
+   |
+LL | / async fn wrapper<F>(f: F)
+LL | |
+LL | |
+LL | |
+...  |
+LL | | F:,
+LL | | for<'a> <i32 as FnOnce<(&'a mut i32,)>>::Output: Future<Output = ()> + 'a,
+   | |__________________________________________________________________________^ expected an `FnOnce(&'a mut i32)` closure, found `i32`
+   |
+   = help: the trait `for<'a> FnOnce<(&'a mut i32,)>` is not implemented for `i32`
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
+error[E0277]: expected a `FnOnce(&'a mut i32)` closure, found `i32`
+  --> $DIR/issue-76168-hr-outlives-3.rs:14:1
    |
 LL | / {
 LL | |
@@ -46,6 +61,6 @@ LL | | }
    |
    = help: the trait `for<'a> FnOnce<(&'a mut i32,)>` is not implemented for `i32`
 
-error: aborting due to 4 previous errors
+error: aborting due to 5 previous errors
 
 For more information about this error, try `rustc --explain E0277`.
diff --git a/tests/ui/lifetimes/issue-79187-2.rs b/tests/ui/lifetimes/issue-79187-2.rs
index fff92c30b37..9d7f17e7f23 100644
--- a/tests/ui/lifetimes/issue-79187-2.rs
+++ b/tests/ui/lifetimes/issue-79187-2.rs
@@ -7,7 +7,7 @@ fn take_foo(_: impl Foo) {}
 fn main() {
     take_foo(|a| a);
     //~^ ERROR implementation of `FnOnce` is not general enough
-    //~| ERROR mismatched types
+    //~| ERROR implementation of `Fn` is not general enough
     take_foo(|a: &i32| a);
     //~^ ERROR lifetime may not live long enough
     //~| ERROR mismatched types
diff --git a/tests/ui/lifetimes/issue-79187-2.stderr b/tests/ui/lifetimes/issue-79187-2.stderr
index e8115bb6b06..78f6ce882df 100644
--- a/tests/ui/lifetimes/issue-79187-2.stderr
+++ b/tests/ui/lifetimes/issue-79187-2.stderr
@@ -25,28 +25,14 @@ LL |     take_foo(|a| a);
    = note: closure with signature `fn(&'2 i32) -> &i32` must implement `FnOnce<(&'1 i32,)>`, for any lifetime `'1`...
    = note: ...but it actually implements `FnOnce<(&'2 i32,)>`, for some specific lifetime `'2`
 
-error[E0308]: mismatched types
+error: implementation of `Fn` is not general enough
   --> $DIR/issue-79187-2.rs:8:5
    |
 LL |     take_foo(|a| a);
-   |     ^^^^^^^^^^^^^^^ one type is more general than the other
-   |
-   = note: expected trait `for<'a> Fn(&'a i32)`
-              found trait `Fn(&i32)`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/issue-79187-2.rs:8:14
-   |
-LL |     take_foo(|a| a);
-   |              ^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-79187-2.rs:5:21
-   |
-LL | fn take_foo(_: impl Foo) {}
-   |                     ^^^
-help: consider specifying the type of the closure parameters
+   |     ^^^^^^^^^^^^^^^ implementation of `Fn` is not general enough
    |
-LL |     take_foo(|a: &_| a);
-   |              ~~~~~~~
+   = note: closure with signature `fn(&'2 i32) -> &i32` must implement `Fn<(&'1 i32,)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `Fn<(&'2 i32,)>`, for some specific lifetime `'2`
 
 error[E0308]: mismatched types
   --> $DIR/issue-79187-2.rs:11:5
diff --git a/tests/ui/lifetimes/issue-79187.rs b/tests/ui/lifetimes/issue-79187.rs
index 8e13045623b..a8829bd4e49 100644
--- a/tests/ui/lifetimes/issue-79187.rs
+++ b/tests/ui/lifetimes/issue-79187.rs
@@ -3,6 +3,6 @@ fn thing(x: impl FnOnce(&u32)) {}
 fn main() {
     let f = |_| ();
     thing(f);
-    //~^ ERROR mismatched types
-    //~^^ ERROR implementation of `FnOnce` is not general enough
+    //~^ ERROR implementation of `FnOnce` is not general enough
+    //~| ERROR implementation of `FnOnce` is not general enough
 }
diff --git a/tests/ui/lifetimes/issue-79187.stderr b/tests/ui/lifetimes/issue-79187.stderr
index 14bdfe75c08..8adde8d6dfb 100644
--- a/tests/ui/lifetimes/issue-79187.stderr
+++ b/tests/ui/lifetimes/issue-79187.stderr
@@ -1,25 +1,11 @@
-error[E0308]: mismatched types
+error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-79187.rs:5:5
    |
 LL |     thing(f);
-   |     ^^^^^^^^ one type is more general than the other
-   |
-   = note: expected trait `for<'a> FnOnce(&'a u32)`
-              found trait `FnOnce(&u32)`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/issue-79187.rs:4:13
-   |
-LL |     let f = |_| ();
-   |             ^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/issue-79187.rs:1:18
-   |
-LL | fn thing(x: impl FnOnce(&u32)) {}
-   |                  ^^^^^^^^^^^^
-help: consider specifying the type of the closure parameters
+   |     ^^^^^^^^ implementation of `FnOnce` is not general enough
    |
-LL |     let f = |_: &_| ();
-   |             ~~~~~~~
+   = note: closure with signature `fn(&'2 u32)` must implement `FnOnce<(&'1 u32,)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `FnOnce<(&'2 u32,)>`, for some specific lifetime `'2`
 
 error: implementation of `FnOnce` is not general enough
   --> $DIR/issue-79187.rs:5:5
@@ -29,7 +15,7 @@ LL |     thing(f);
    |
    = note: closure with signature `fn(&'2 u32)` must implement `FnOnce<(&'1 u32,)>`, for any lifetime `'1`...
    = note: ...but it actually implements `FnOnce<(&'2 u32,)>`, for some specific lifetime `'2`
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
 error: aborting due to 2 previous errors
 
-For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/lifetimes/lifetime-errors/issue_74400.rs b/tests/ui/lifetimes/lifetime-errors/issue_74400.rs
index f17e0a678c9..b02e38bec3b 100644
--- a/tests/ui/lifetimes/lifetime-errors/issue_74400.rs
+++ b/tests/ui/lifetimes/lifetime-errors/issue_74400.rs
@@ -13,6 +13,6 @@ fn g<T>(data: &[T]) {
     //~^ ERROR the parameter type
     //~| ERROR the parameter type
     //~| ERROR the parameter type
-    //~| ERROR mismatched types
     //~| ERROR implementation of `FnOnce` is not general
+    //~| ERROR implementation of `Fn` is not general enough
 }
diff --git a/tests/ui/lifetimes/lifetime-errors/issue_74400.stderr b/tests/ui/lifetimes/lifetime-errors/issue_74400.stderr
index beb838d2ff8..4dada6ff014 100644
--- a/tests/ui/lifetimes/lifetime-errors/issue_74400.stderr
+++ b/tests/ui/lifetimes/lifetime-errors/issue_74400.stderr
@@ -42,19 +42,14 @@ help: consider adding an explicit lifetime bound
 LL | fn g<T: 'static>(data: &[T]) {
    |       +++++++++
 
-error[E0308]: mismatched types
+error: implementation of `Fn` is not general enough
   --> $DIR/issue_74400.rs:12:5
    |
 LL |     f(data, identity)
-   |     ^^^^^^^^^^^^^^^^^ one type is more general than the other
+   |     ^^^^^^^^^^^^^^^^^ implementation of `Fn` is not general enough
    |
-   = note: expected trait `for<'a> Fn(&'a T)`
-              found trait `Fn(&T)`
-note: the lifetime requirement is introduced here
-  --> $DIR/issue_74400.rs:8:34
-   |
-LL | fn f<T, S>(data: &[T], key: impl Fn(&T) -> S) {
-   |                                  ^^^^^^^^^^^
+   = note: `fn(&'2 T) -> &'2 T {identity::<&'2 T>}` must implement `Fn<(&'1 T,)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `Fn<(&'2 T,)>`, for some specific lifetime `'2`
 
 error: implementation of `FnOnce` is not general enough
   --> $DIR/issue_74400.rs:12:5
@@ -67,5 +62,4 @@ LL |     f(data, identity)
 
 error: aborting due to 5 previous errors
 
-Some errors have detailed explanations: E0308, E0310.
-For more information about an error, try `rustc --explain E0308`.
+For more information about this error, try `rustc --explain E0310`.
diff --git a/tests/ui/lint/lint-qualification.fixed b/tests/ui/lint/lint-qualification.fixed
index 2b1f8b59175..6fe6ba2792f 100644
--- a/tests/ui/lint/lint-qualification.fixed
+++ b/tests/ui/lint/lint-qualification.fixed
@@ -1,5 +1,6 @@
 //@ run-rustfix
 #![deny(unused_qualifications)]
+#![deny(unused_imports)]
 #![allow(deprecated, dead_code)]
 
 mod foo {
@@ -21,8 +22,10 @@ fn main() {
     //~^ ERROR: unnecessary qualification
     //~| ERROR: unnecessary qualification
 
-    use std::fmt;
-    let _: fmt::Result = Ok(()); //~ ERROR: unnecessary qualification
+    
+    //~^ ERROR: unused import: `std::fmt`
+    let _: std::fmt::Result = Ok(());
+    // don't report unnecessary qualification because fix(#122373) for issue #121331
 
     let _ = <bool as Default>::default(); // issue #121999
     //~^ ERROR: unnecessary qualification
diff --git a/tests/ui/lint/lint-qualification.rs b/tests/ui/lint/lint-qualification.rs
index 002fdbf7724..19d339b006c 100644
--- a/tests/ui/lint/lint-qualification.rs
+++ b/tests/ui/lint/lint-qualification.rs
@@ -1,5 +1,6 @@
 //@ run-rustfix
 #![deny(unused_qualifications)]
+#![deny(unused_imports)]
 #![allow(deprecated, dead_code)]
 
 mod foo {
@@ -22,7 +23,9 @@ fn main() {
     //~| ERROR: unnecessary qualification
 
     use std::fmt;
-    let _: std::fmt::Result = Ok(()); //~ ERROR: unnecessary qualification
+    //~^ ERROR: unused import: `std::fmt`
+    let _: std::fmt::Result = Ok(());
+    // don't report unnecessary qualification because fix(#122373) for issue #121331
 
     let _ = <bool as ::std::default::Default>::default(); // issue #121999
     //~^ ERROR: unnecessary qualification
diff --git a/tests/ui/lint/lint-qualification.stderr b/tests/ui/lint/lint-qualification.stderr
index 8dddcf23f75..9e5c9b2df13 100644
--- a/tests/ui/lint/lint-qualification.stderr
+++ b/tests/ui/lint/lint-qualification.stderr
@@ -1,5 +1,5 @@
 error: unnecessary qualification
-  --> $DIR/lint-qualification.rs:11:5
+  --> $DIR/lint-qualification.rs:12:5
    |
 LL |     foo::bar();
    |     ^^^^^^^^
@@ -16,7 +16,7 @@ LL +     bar();
    |
 
 error: unnecessary qualification
-  --> $DIR/lint-qualification.rs:12:5
+  --> $DIR/lint-qualification.rs:13:5
    |
 LL |     crate::foo::bar();
    |     ^^^^^^^^^^^^^^^
@@ -28,7 +28,7 @@ LL +     bar();
    |
 
 error: unnecessary qualification
-  --> $DIR/lint-qualification.rs:17:13
+  --> $DIR/lint-qualification.rs:18:13
    |
 LL |     let _ = std::string::String::new();
    |             ^^^^^^^^^^^^^^^^^^^^^^^^
@@ -40,7 +40,7 @@ LL +     let _ = String::new();
    |
 
 error: unnecessary qualification
-  --> $DIR/lint-qualification.rs:18:13
+  --> $DIR/lint-qualification.rs:19:13
    |
 LL |     let _ = ::std::env::current_dir();
    |             ^^^^^^^^^^^^^^^^^^^^^^^
@@ -52,7 +52,7 @@ LL +     let _ = std::env::current_dir();
    |
 
 error: unnecessary qualification
-  --> $DIR/lint-qualification.rs:20:12
+  --> $DIR/lint-qualification.rs:21:12
    |
 LL |     let _: std::vec::Vec<String> = std::vec::Vec::<String>::new();
    |            ^^^^^^^^^^^^^^^^^^^^^
@@ -64,7 +64,7 @@ LL +     let _: Vec<String> = std::vec::Vec::<String>::new();
    |
 
 error: unnecessary qualification
-  --> $DIR/lint-qualification.rs:20:36
+  --> $DIR/lint-qualification.rs:21:36
    |
 LL |     let _: std::vec::Vec<String> = std::vec::Vec::<String>::new();
    |                                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -75,20 +75,20 @@ LL -     let _: std::vec::Vec<String> = std::vec::Vec::<String>::new();
 LL +     let _: std::vec::Vec<String> = Vec::<String>::new();
    |
 
-error: unnecessary qualification
-  --> $DIR/lint-qualification.rs:25:12
-   |
-LL |     let _: std::fmt::Result = Ok(());
-   |            ^^^^^^^^^^^^^^^^
+error: unused import: `std::fmt`
+  --> $DIR/lint-qualification.rs:25:9
    |
-help: remove the unnecessary path segments
+LL |     use std::fmt;
+   |         ^^^^^^^^
    |
-LL -     let _: std::fmt::Result = Ok(());
-LL +     let _: fmt::Result = Ok(());
+note: the lint level is defined here
+  --> $DIR/lint-qualification.rs:3:9
    |
+LL | #![deny(unused_imports)]
+   |         ^^^^^^^^^^^^^^
 
 error: unnecessary qualification
-  --> $DIR/lint-qualification.rs:27:13
+  --> $DIR/lint-qualification.rs:30:13
    |
 LL |     let _ = <bool as ::std::default::Default>::default(); // issue #121999
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
diff --git a/tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.fixed b/tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.fixed
new file mode 100644
index 00000000000..d554bbfcc98
--- /dev/null
+++ b/tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.fixed
@@ -0,0 +1,50 @@
+//@ run-rustfix
+//@ edition:2021
+#![deny(unused_qualifications)]
+#![deny(unused_imports)]
+#![feature(coroutines, coroutine_trait)]
+
+use std::ops::{
+    Coroutine,
+    CoroutineState::{self},
+    //~^ ERROR unused import: `*`
+};
+use std::pin::Pin;
+
+#[allow(dead_code)]
+fn finish<T>(mut amt: usize, mut t: T) -> T::Return
+    where T: Coroutine<(), Yield = ()> + Unpin,
+{
+    loop {
+        match Pin::new(&mut t).resume(()) {
+            CoroutineState::Yielded(()) => amt = amt.checked_sub(1).unwrap(),
+            CoroutineState::Complete(ret) => {
+                assert_eq!(amt, 0);
+                return ret
+            }
+        }
+    }
+}
+
+
+mod foo {
+    pub fn bar() {}
+}
+
+pub fn main() {
+
+    use foo::bar;
+    bar();
+    //~^ ERROR unnecessary qualification
+    bar();
+
+    // The item `use std::string::String` is imported redundantly.
+    // Suppress `unused_imports` reporting, otherwise the fixed file will report an error
+    #[allow(unused_imports)]
+    use std::string::String;
+    let s = String::new();
+    let y = std::string::String::new();
+    // unnecessary qualification
+    println!("{} {}", s, y);
+
+}
diff --git a/tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.rs b/tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.rs
new file mode 100644
index 00000000000..4d79f5ab745
--- /dev/null
+++ b/tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.rs
@@ -0,0 +1,50 @@
+//@ run-rustfix
+//@ edition:2021
+#![deny(unused_qualifications)]
+#![deny(unused_imports)]
+#![feature(coroutines, coroutine_trait)]
+
+use std::ops::{
+    Coroutine,
+    CoroutineState::{self, *},
+    //~^ ERROR unused import: `*`
+};
+use std::pin::Pin;
+
+#[allow(dead_code)]
+fn finish<T>(mut amt: usize, mut t: T) -> T::Return
+    where T: Coroutine<(), Yield = ()> + Unpin,
+{
+    loop {
+        match Pin::new(&mut t).resume(()) {
+            CoroutineState::Yielded(()) => amt = amt.checked_sub(1).unwrap(),
+            CoroutineState::Complete(ret) => {
+                assert_eq!(amt, 0);
+                return ret
+            }
+        }
+    }
+}
+
+
+mod foo {
+    pub fn bar() {}
+}
+
+pub fn main() {
+
+    use foo::bar;
+    foo::bar();
+    //~^ ERROR unnecessary qualification
+    bar();
+
+    // The item `use std::string::String` is imported redundantly.
+    // Suppress `unused_imports` reporting, otherwise the fixed file will report an error
+    #[allow(unused_imports)]
+    use std::string::String;
+    let s = String::new();
+    let y = std::string::String::new();
+    // unnecessary qualification
+    println!("{} {}", s, y);
+
+}
diff --git a/tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.stderr b/tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.stderr
new file mode 100644
index 00000000000..52ed13ea150
--- /dev/null
+++ b/tests/ui/lint/unnecessary-qualification/lint-unnecessary-qualification-issue-121331.stderr
@@ -0,0 +1,31 @@
+error: unused import: `*`
+  --> $DIR/lint-unnecessary-qualification-issue-121331.rs:9:28
+   |
+LL |     CoroutineState::{self, *},
+   |                            ^
+   |
+note: the lint level is defined here
+  --> $DIR/lint-unnecessary-qualification-issue-121331.rs:4:9
+   |
+LL | #![deny(unused_imports)]
+   |         ^^^^^^^^^^^^^^
+
+error: unnecessary qualification
+  --> $DIR/lint-unnecessary-qualification-issue-121331.rs:37:5
+   |
+LL |     foo::bar();
+   |     ^^^^^^^^
+   |
+note: the lint level is defined here
+  --> $DIR/lint-unnecessary-qualification-issue-121331.rs:3:9
+   |
+LL | #![deny(unused_qualifications)]
+   |         ^^^^^^^^^^^^^^^^^^^^^
+help: remove the unnecessary path segments
+   |
+LL -     foo::bar();
+LL +     bar();
+   |
+
+error: aborting due to 2 previous errors
+
diff --git a/tests/ui/mismatched_types/closure-arg-type-mismatch-issue-45727.stderr b/tests/ui/mismatched_types/closure-arg-type-mismatch-issue-45727.stderr
index 452cba6b4de..e52e095e9f7 100644
--- a/tests/ui/mismatched_types/closure-arg-type-mismatch-issue-45727.stderr
+++ b/tests/ui/mismatched_types/closure-arg-type-mismatch-issue-45727.stderr
@@ -24,7 +24,7 @@ LL |     let _ = (-10..=10).find(|x: &&&i32| x.signum() == 0);
    |                        expected due to this
    |
    = note: expected closure signature `for<'a> fn(&'a {integer}) -> _`
-              found closure signature `for<'a, 'b, 'c> fn(&'a &'b &'c i32) -> _`
+              found closure signature `fn(&&&i32) -> _`
 note: required by a bound in `find`
   --> $SRC_DIR/core/src/iter/traits/iterator.rs:LL:COL
 help: consider adjusting the signature so it does not borrow its argument
diff --git a/tests/ui/mismatched_types/closure-arg-type-mismatch.rs b/tests/ui/mismatched_types/closure-arg-type-mismatch.rs
index e73a33dfded..55a4a0b5707 100644
--- a/tests/ui/mismatched_types/closure-arg-type-mismatch.rs
+++ b/tests/ui/mismatched_types/closure-arg-type-mismatch.rs
@@ -8,7 +8,7 @@ fn main() {
 fn baz<F: Fn(*mut &u32)>(_: F) {}
 fn _test<'a>(f: fn(*mut &'a u32)) {
     baz(f);
-    //~^ ERROR: mismatched types
+    //~^ ERROR: implementation of `FnOnce` is not general enough
     //~| ERROR: borrowed data escapes
     //~| ERROR: not general enough
 }
diff --git a/tests/ui/mismatched_types/closure-arg-type-mismatch.stderr b/tests/ui/mismatched_types/closure-arg-type-mismatch.stderr
index e63d3f6a075..abc5d150a3f 100644
--- a/tests/ui/mismatched_types/closure-arg-type-mismatch.stderr
+++ b/tests/ui/mismatched_types/closure-arg-type-mismatch.stderr
@@ -24,7 +24,7 @@ LL |     a.iter().map(|_: &(u16, u16)| 45);
    |              expected due to this
    |
    = note: expected closure signature `fn(&(u32, u32)) -> _`
-              found closure signature `for<'a> fn(&'a (u16, u16)) -> _`
+              found closure signature `fn(&(u16, u16)) -> _`
 note: required by a bound in `map`
   --> $SRC_DIR/core/src/iter/traits/iterator.rs:LL:COL
 
@@ -63,19 +63,14 @@ note: due to current limitations in the borrow checker, this implies a `'static`
 LL | fn baz<F: Fn(*mut &u32)>(_: F) {}
    |           ^^^^^^^^^^^^^
 
-error[E0308]: mismatched types
+error: implementation of `Fn` is not general enough
   --> $DIR/closure-arg-type-mismatch.rs:10:5
    |
 LL |     baz(f);
-   |     ^^^^^^ one type is more general than the other
+   |     ^^^^^^ implementation of `Fn` is not general enough
    |
-   = note: expected trait `for<'a> Fn(*mut &'a u32)`
-              found trait `Fn(*mut &u32)`
-note: the lifetime requirement is introduced here
-  --> $DIR/closure-arg-type-mismatch.rs:8:11
-   |
-LL | fn baz<F: Fn(*mut &u32)>(_: F) {}
-   |           ^^^^^^^^^^^^^
+   = note: `fn(*mut &'2 u32)` must implement `Fn<(*mut &'1 u32,)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `Fn<(*mut &'2 u32,)>`, for some specific lifetime `'2`
 
 error: implementation of `FnOnce` is not general enough
   --> $DIR/closure-arg-type-mismatch.rs:10:5
@@ -88,5 +83,5 @@ LL |     baz(f);
 
 error: aborting due to 6 previous errors
 
-Some errors have detailed explanations: E0308, E0521, E0631.
-For more information about an error, try `rustc --explain E0308`.
+Some errors have detailed explanations: E0521, E0631.
+For more information about an error, try `rustc --explain E0521`.
diff --git a/tests/ui/mismatched_types/closure-mismatch.rs b/tests/ui/mismatched_types/closure-mismatch.rs
index 4eb33497c39..efaed4dc1b9 100644
--- a/tests/ui/mismatched_types/closure-mismatch.rs
+++ b/tests/ui/mismatched_types/closure-mismatch.rs
@@ -7,8 +7,8 @@ fn baz<T: Foo>(_: T) {}
 fn main() {
     baz(|_| ());
     //~^ ERROR implementation of `FnOnce` is not general enough
-    //~| ERROR mismatched types
+    //~| ERROR implementation of `Fn` is not general enough
     baz(|x| ());
     //~^ ERROR implementation of `FnOnce` is not general enough
-    //~| ERROR mismatched types
+    //~| ERROR implementation of `Fn` is not general enough
 }
diff --git a/tests/ui/mismatched_types/closure-mismatch.stderr b/tests/ui/mismatched_types/closure-mismatch.stderr
index 74033c18573..802110c6511 100644
--- a/tests/ui/mismatched_types/closure-mismatch.stderr
+++ b/tests/ui/mismatched_types/closure-mismatch.stderr
@@ -7,28 +7,14 @@ LL |     baz(|_| ());
    = note: closure with signature `fn(&'2 ())` must implement `FnOnce<(&'1 (),)>`, for any lifetime `'1`...
    = note: ...but it actually implements `FnOnce<(&'2 (),)>`, for some specific lifetime `'2`
 
-error[E0308]: mismatched types
+error: implementation of `Fn` is not general enough
   --> $DIR/closure-mismatch.rs:8:5
    |
 LL |     baz(|_| ());
-   |     ^^^^^^^^^^^ one type is more general than the other
+   |     ^^^^^^^^^^^ implementation of `Fn` is not general enough
    |
-   = note: expected trait `for<'a> Fn(&'a ())`
-              found trait `Fn(&())`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/closure-mismatch.rs:8:9
-   |
-LL |     baz(|_| ());
-   |         ^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/closure-mismatch.rs:5:11
-   |
-LL | fn baz<T: Foo>(_: T) {}
-   |           ^^^
-help: consider specifying the type of the closure parameters
-   |
-LL |     baz(|_: &_| ());
-   |         ~~~~~~~
+   = note: closure with signature `fn(&'2 ())` must implement `Fn<(&'1 (),)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `Fn<(&'2 (),)>`, for some specific lifetime `'2`
 
 error: implementation of `FnOnce` is not general enough
   --> $DIR/closure-mismatch.rs:11:5
@@ -39,29 +25,14 @@ LL |     baz(|x| ());
    = note: closure with signature `fn(&'2 ())` must implement `FnOnce<(&'1 (),)>`, for any lifetime `'1`...
    = note: ...but it actually implements `FnOnce<(&'2 (),)>`, for some specific lifetime `'2`
 
-error[E0308]: mismatched types
+error: implementation of `Fn` is not general enough
   --> $DIR/closure-mismatch.rs:11:5
    |
 LL |     baz(|x| ());
-   |     ^^^^^^^^^^^ one type is more general than the other
-   |
-   = note: expected trait `for<'a> Fn(&'a ())`
-              found trait `Fn(&())`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/closure-mismatch.rs:11:9
-   |
-LL |     baz(|x| ());
-   |         ^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/closure-mismatch.rs:5:11
-   |
-LL | fn baz<T: Foo>(_: T) {}
-   |           ^^^
-help: consider specifying the type of the closure parameters
+   |     ^^^^^^^^^^^ implementation of `Fn` is not general enough
    |
-LL |     baz(|x: &_| ());
-   |         ~~~~~~~
+   = note: closure with signature `fn(&'2 ())` must implement `Fn<(&'1 (),)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `Fn<(&'2 (),)>`, for some specific lifetime `'2`
 
 error: aborting due to 4 previous errors
 
-For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/mismatched_types/fn-variance-1.stderr b/tests/ui/mismatched_types/fn-variance-1.stderr
index fdb2e6f0097..ed450d8d81c 100644
--- a/tests/ui/mismatched_types/fn-variance-1.stderr
+++ b/tests/ui/mismatched_types/fn-variance-1.stderr
@@ -10,7 +10,7 @@ LL |     apply(&3, takes_mut);
    |     required by a bound introduced by this call
    |
    = note: expected function signature `fn(&{integer}) -> _`
-              found function signature `for<'a> fn(&'a mut isize) -> _`
+              found function signature `fn(&mut isize) -> _`
 note: required by a bound in `apply`
   --> $DIR/fn-variance-1.rs:5:37
    |
@@ -33,7 +33,7 @@ LL |     apply(&mut 3, takes_imm);
    |     required by a bound introduced by this call
    |
    = note: expected function signature `fn(&mut {integer}) -> _`
-              found function signature `for<'a> fn(&'a isize) -> _`
+              found function signature `fn(&isize) -> _`
 note: required by a bound in `apply`
   --> $DIR/fn-variance-1.rs:5:37
    |
diff --git a/tests/ui/mismatched_types/issue-36053-2.stderr b/tests/ui/mismatched_types/issue-36053-2.stderr
index 6d23319ca7e..ffaa276b62e 100644
--- a/tests/ui/mismatched_types/issue-36053-2.stderr
+++ b/tests/ui/mismatched_types/issue-36053-2.stderr
@@ -7,7 +7,7 @@ LL |     once::<&str>("str").fuse().filter(|a: &str| true).count();
    |                                expected due to this
    |
    = note: expected closure signature `for<'a> fn(&'a &_) -> _`
-              found closure signature `for<'a> fn(&'a _) -> _`
+              found closure signature `fn(&_) -> _`
 note: required by a bound in `filter`
   --> $SRC_DIR/core/src/iter/traits/iterator.rs:LL:COL
 help: consider adjusting the signature so it borrows its argument
diff --git a/tests/ui/mismatched_types/suggest-option-asderef-inference-var.stderr b/tests/ui/mismatched_types/suggest-option-asderef-inference-var.stderr
index 0ed57466e9c..0b8943898f5 100644
--- a/tests/ui/mismatched_types/suggest-option-asderef-inference-var.stderr
+++ b/tests/ui/mismatched_types/suggest-option-asderef-inference-var.stderr
@@ -10,7 +10,7 @@ LL |     let _has_inference_vars: Option<i32> = Some(0).map(deref_int);
    |                                                    required by a bound introduced by this call
    |
    = note: expected function signature `fn({integer}) -> _`
-              found function signature `for<'a> fn(&'a i32) -> _`
+              found function signature `fn(&i32) -> _`
 note: required by a bound in `Option::<T>::map`
   --> $SRC_DIR/core/src/option.rs:LL:COL
 help: consider wrapping the function in a closure
diff --git a/tests/ui/mismatched_types/suggest-option-asderef-unfixable.stderr b/tests/ui/mismatched_types/suggest-option-asderef-unfixable.stderr
index 1ac057a5f38..99c9028ae1e 100644
--- a/tests/ui/mismatched_types/suggest-option-asderef-unfixable.stderr
+++ b/tests/ui/mismatched_types/suggest-option-asderef-unfixable.stderr
@@ -10,7 +10,7 @@ LL |     let _ = produces_string().and_then(takes_str_but_too_many_refs);
    |                               required by a bound introduced by this call
    |
    = note: expected function signature `fn(String) -> _`
-              found function signature `for<'a, 'b> fn(&'a &'b str) -> _`
+              found function signature `fn(&&str) -> _`
 note: required by a bound in `Option::<T>::and_then`
   --> $SRC_DIR/core/src/option.rs:LL:COL
 help: consider wrapping the function in a closure
@@ -69,7 +69,7 @@ LL |     let _ = Some(TypeWithoutDeref).and_then(takes_str_but_too_many_refs);
    |                                    required by a bound introduced by this call
    |
    = note: expected function signature `fn(TypeWithoutDeref) -> _`
-              found function signature `for<'a, 'b> fn(&'a &'b str) -> _`
+              found function signature `fn(&&str) -> _`
 note: required by a bound in `Option::<T>::and_then`
   --> $SRC_DIR/core/src/option.rs:LL:COL
 help: consider wrapping the function in a closure
diff --git a/tests/ui/mismatched_types/suggest-option-asderef.stderr b/tests/ui/mismatched_types/suggest-option-asderef.stderr
index 1702a7f1dec..306c412e9d2 100644
--- a/tests/ui/mismatched_types/suggest-option-asderef.stderr
+++ b/tests/ui/mismatched_types/suggest-option-asderef.stderr
@@ -10,7 +10,7 @@ LL |     let _: Option<()> = produces_string().and_then(takes_str);
    |                                           required by a bound introduced by this call
    |
    = note: expected function signature `fn(String) -> _`
-              found function signature `for<'a> fn(&'a str) -> _`
+              found function signature `fn(&str) -> _`
 note: required by a bound in `Option::<T>::and_then`
   --> $SRC_DIR/core/src/option.rs:LL:COL
 help: consider wrapping the function in a closure
@@ -34,7 +34,7 @@ LL |     let _: Option<Option<()>> = produces_string().map(takes_str);
    |                                                   required by a bound introduced by this call
    |
    = note: expected function signature `fn(String) -> _`
-              found function signature `for<'a> fn(&'a str) -> _`
+              found function signature `fn(&str) -> _`
 note: required by a bound in `Option::<T>::map`
   --> $SRC_DIR/core/src/option.rs:LL:COL
 help: consider wrapping the function in a closure
@@ -58,7 +58,7 @@ LL |     let _: Option<Option<()>> = produces_string().map(takes_str_mut);
    |                                                   required by a bound introduced by this call
    |
    = note: expected function signature `fn(String) -> _`
-              found function signature `for<'a> fn(&'a mut str) -> _`
+              found function signature `fn(&mut str) -> _`
 note: required by a bound in `Option::<T>::map`
   --> $SRC_DIR/core/src/option.rs:LL:COL
 help: consider wrapping the function in a closure
@@ -82,7 +82,7 @@ LL |     let _ = produces_string().and_then(generic_ref);
    |                               required by a bound introduced by this call
    |
    = note: expected function signature `fn(String) -> _`
-              found function signature `for<'a> fn(&'a _) -> _`
+              found function signature `fn(&_) -> _`
 note: required by a bound in `Option::<T>::and_then`
   --> $SRC_DIR/core/src/option.rs:LL:COL
 help: consider wrapping the function in a closure
diff --git a/tests/ui/nll/missing-universe-cause-issue-114907.rs b/tests/ui/nll/missing-universe-cause-issue-114907.rs
index 9c69c6bdc36..a3eb5fceea9 100644
--- a/tests/ui/nll/missing-universe-cause-issue-114907.rs
+++ b/tests/ui/nll/missing-universe-cause-issue-114907.rs
@@ -31,8 +31,8 @@ fn accept<C: FnOnce(&())>(_: C) -> Handshake<HandshakeCallback<C>> {
 fn main() {
     let callback = |_| {};
     accept(callback);
-    //~^ ERROR mismatched types
-    //~| ERROR mismatched types
+    //~^ ERROR implementation of `FnOnce` is not general enough
+    //~| ERROR implementation of `FnOnce` is not general enough
     //~| ERROR implementation of `FnOnce` is not general enough
     //~| ERROR implementation of `FnOnce` is not general enough
     //~| ERROR higher-ranked subtype error
diff --git a/tests/ui/nll/missing-universe-cause-issue-114907.stderr b/tests/ui/nll/missing-universe-cause-issue-114907.stderr
index a616d29c4fe..26ad1efec05 100644
--- a/tests/ui/nll/missing-universe-cause-issue-114907.stderr
+++ b/tests/ui/nll/missing-universe-cause-issue-114907.stderr
@@ -1,25 +1,11 @@
-error[E0308]: mismatched types
+error: implementation of `FnOnce` is not general enough
   --> $DIR/missing-universe-cause-issue-114907.rs:33:5
    |
 LL |     accept(callback);
-   |     ^^^^^^^^^^^^^^^^ one type is more general than the other
-   |
-   = note: expected trait `for<'a> FnOnce(&'a ())`
-              found trait `FnOnce(&())`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/missing-universe-cause-issue-114907.rs:32:20
-   |
-LL |     let callback = |_| {};
-   |                    ^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/missing-universe-cause-issue-114907.rs:27:14
-   |
-LL | fn accept<C: FnOnce(&())>(_: C) -> Handshake<HandshakeCallback<C>> {
-   |              ^^^^^^^^^^^
-help: consider specifying the type of the closure parameters
+   |     ^^^^^^^^^^^^^^^^ implementation of `FnOnce` is not general enough
    |
-LL |     let callback = |_: &_| {};
-   |                    ~~~~~~~
+   = note: closure with signature `fn(&'2 ())` must implement `FnOnce<(&'1 (),)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `FnOnce<(&'2 (),)>`, for some specific lifetime `'2`
 
 error: implementation of `FnOnce` is not general enough
   --> $DIR/missing-universe-cause-issue-114907.rs:33:5
@@ -29,6 +15,7 @@ LL |     accept(callback);
    |
    = note: closure with signature `fn(&'2 ())` must implement `FnOnce<(&'1 (),)>`, for any lifetime `'1`...
    = note: ...but it actually implements `FnOnce<(&'2 (),)>`, for some specific lifetime `'2`
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
 error: implementation of `FnOnce` is not general enough
   --> $DIR/missing-universe-cause-issue-114907.rs:33:5
@@ -40,28 +27,15 @@ LL |     accept(callback);
    = note: ...but it actually implements `FnOnce<(&'2 (),)>`, for some specific lifetime `'2`
    = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
-error[E0308]: mismatched types
+error: implementation of `FnOnce` is not general enough
   --> $DIR/missing-universe-cause-issue-114907.rs:33:5
    |
 LL |     accept(callback);
-   |     ^^^^^^^^^^^^^^^^ one type is more general than the other
-   |
-   = note: expected trait `for<'a> FnOnce(&'a ())`
-              found trait `FnOnce(&())`
-note: this closure does not fulfill the lifetime requirements
-  --> $DIR/missing-universe-cause-issue-114907.rs:32:20
-   |
-LL |     let callback = |_| {};
-   |                    ^^^
-note: the lifetime requirement is introduced here
-  --> $DIR/missing-universe-cause-issue-114907.rs:20:21
-   |
-LL | struct Handshake<R: Role> {
-   |                     ^^^^
-help: consider specifying the type of the closure parameters
+   |     ^^^^^^^^^^^^^^^^ implementation of `FnOnce` is not general enough
    |
-LL |     let callback = |_: &_| {};
-   |                    ~~~~~~~
+   = note: closure with signature `fn(&'2 ())` must implement `FnOnce<(&'1 (),)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `FnOnce<(&'2 (),)>`, for some specific lifetime `'2`
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
 error: higher-ranked subtype error
   --> $DIR/missing-universe-cause-issue-114907.rs:33:21
@@ -79,4 +53,3 @@ LL |     accept(callback);
 
 error: aborting due to 6 previous errors
 
-For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/pattern/bindings-after-at/bind-by-move-neither-can-live-while-the-other-survives-1.stderr b/tests/ui/pattern/bindings-after-at/bind-by-move-neither-can-live-while-the-other-survives-1.stderr
index 25838fbf0ab..16a93a0d47d 100644
--- a/tests/ui/pattern/bindings-after-at/bind-by-move-neither-can-live-while-the-other-survives-1.stderr
+++ b/tests/ui/pattern/bindings-after-at/bind-by-move-neither-can-live-while-the-other-survives-1.stderr
@@ -13,7 +13,7 @@ LL |         Some(_z @ ref _y) => {}
    |              ^^   ------ value borrowed here after move
    |              |
    |              value moved into `_z` here
-   |              move occurs because `_z` has type `X` which does not implement the `Copy` trait
+   |              move occurs because `_z` has type `X`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -35,7 +35,7 @@ LL |         Some(_z @ ref mut _y) => {}
    |              ^^   ---------- value borrowed here after move
    |              |
    |              value moved into `_z` here
-   |              move occurs because `_z` has type `X` which does not implement the `Copy` trait
+   |              move occurs because `_z` has type `X`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
diff --git a/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse-promotion.stderr b/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse-promotion.stderr
index 815a4ade995..ea04d4bc055 100644
--- a/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse-promotion.stderr
+++ b/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse-promotion.stderr
@@ -5,7 +5,7 @@ LL |     let a @ ref b = U;
    |         ^   ----- value borrowed here after move
    |         |
    |         value moved into `a` here
-   |         move occurs because `a` has type `U` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
diff --git a/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse.stderr b/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse.stderr
index fd7a51388bc..25c940a3200 100644
--- a/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse.stderr
+++ b/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse.stderr
@@ -5,7 +5,7 @@ LL |     let a @ ref b = U;
    |         ^   ----- value borrowed here after move
    |         |
    |         value moved into `a` here
-   |         move occurs because `a` has type `U` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -20,7 +20,7 @@ LL |     let a @ (mut b @ ref mut c, d @ ref e) = (U, U);
    |         |            |
    |         |            value borrowed here after move
    |         value moved into `a` here
-   |         move occurs because `a` has type `(U, U)` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `(U, U)`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -34,7 +34,7 @@ LL |     let a @ (mut b @ ref mut c, d @ ref e) = (U, U);
    |              ^^^^^   --------- value borrowed here after move
    |              |
    |              value moved into `b` here
-   |              move occurs because `b` has type `U` which does not implement the `Copy` trait
+   |              move occurs because `b` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -48,7 +48,7 @@ LL |     let a @ (mut b @ ref mut c, d @ ref e) = (U, U);
    |                                 ^   ----- value borrowed here after move
    |                                 |
    |                                 value moved into `d` here
-   |                                 move occurs because `d` has type `U` which does not implement the `Copy` trait
+   |                                 move occurs because `d` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -63,7 +63,7 @@ LL |     let a @ [ref mut b, ref c] = [U, U];
    |         |    |
    |         |    value borrowed here after move
    |         value moved into `a` here
-   |         move occurs because `a` has type `[U; 2]` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `[U; 2]`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -77,7 +77,7 @@ LL |     let a @ ref b = u();
    |         ^   ----- value borrowed here after move
    |         |
    |         value moved into `a` here
-   |         move occurs because `a` has type `U` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -92,7 +92,7 @@ LL |     let a @ (mut b @ ref mut c, d @ ref e) = (u(), u());
    |         |            |
    |         |            value borrowed here after move
    |         value moved into `a` here
-   |         move occurs because `a` has type `(U, U)` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `(U, U)`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -106,7 +106,7 @@ LL |     let a @ (mut b @ ref mut c, d @ ref e) = (u(), u());
    |              ^^^^^   --------- value borrowed here after move
    |              |
    |              value moved into `b` here
-   |              move occurs because `b` has type `U` which does not implement the `Copy` trait
+   |              move occurs because `b` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -120,7 +120,7 @@ LL |     let a @ (mut b @ ref mut c, d @ ref e) = (u(), u());
    |                                 ^   ----- value borrowed here after move
    |                                 |
    |                                 value moved into `d` here
-   |                                 move occurs because `d` has type `U` which does not implement the `Copy` trait
+   |                                 move occurs because `d` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -135,7 +135,7 @@ LL |     let a @ [ref mut b, ref c] = [u(), u()];
    |         |    |
    |         |    value borrowed here after move
    |         value moved into `a` here
-   |         move occurs because `a` has type `[U; 2]` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `[U; 2]`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -149,7 +149,7 @@ LL |         a @ Some(ref b) => {}
    |         ^        ----- value borrowed here after move
    |         |
    |         value moved into `a` here
-   |         move occurs because `a` has type `Option<U>` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `Option<U>`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -164,7 +164,7 @@ LL |         a @ Some((mut b @ ref mut c, d @ ref e)) => {}
    |         |                 |
    |         |                 value borrowed here after move
    |         value moved into `a` here
-   |         move occurs because `a` has type `Option<(U, U)>` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `Option<(U, U)>`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -178,7 +178,7 @@ LL |         a @ Some((mut b @ ref mut c, d @ ref e)) => {}
    |                   ^^^^^   --------- value borrowed here after move
    |                   |
    |                   value moved into `b` here
-   |                   move occurs because `b` has type `U` which does not implement the `Copy` trait
+   |                   move occurs because `b` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -192,7 +192,7 @@ LL |         a @ Some((mut b @ ref mut c, d @ ref e)) => {}
    |                                      ^   ----- value borrowed here after move
    |                                      |
    |                                      value moved into `d` here
-   |                                      move occurs because `d` has type `U` which does not implement the `Copy` trait
+   |                                      move occurs because `d` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -207,7 +207,7 @@ LL |         mut a @ Some([ref b, ref mut c]) => {}
    |         |             |
    |         |             value borrowed here after move
    |         value moved into `a` here
-   |         move occurs because `a` has type `Option<[U; 2]>` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `Option<[U; 2]>`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -221,7 +221,7 @@ LL |         a @ Some(ref b) => {}
    |         ^        ----- value borrowed here after move
    |         |
    |         value moved into `a` here
-   |         move occurs because `a` has type `Option<U>` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `Option<U>`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -236,7 +236,7 @@ LL |         a @ Some((mut b @ ref mut c, d @ ref e)) => {}
    |         |                 |
    |         |                 value borrowed here after move
    |         value moved into `a` here
-   |         move occurs because `a` has type `Option<(U, U)>` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `Option<(U, U)>`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -250,7 +250,7 @@ LL |         a @ Some((mut b @ ref mut c, d @ ref e)) => {}
    |                   ^^^^^   --------- value borrowed here after move
    |                   |
    |                   value moved into `b` here
-   |                   move occurs because `b` has type `U` which does not implement the `Copy` trait
+   |                   move occurs because `b` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -264,7 +264,7 @@ LL |         a @ Some((mut b @ ref mut c, d @ ref e)) => {}
    |                                      ^   ----- value borrowed here after move
    |                                      |
    |                                      value moved into `d` here
-   |                                      move occurs because `d` has type `U` which does not implement the `Copy` trait
+   |                                      move occurs because `d` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -279,7 +279,7 @@ LL |         mut a @ Some([ref b, ref mut c]) => {}
    |         |             |
    |         |             value borrowed here after move
    |         value moved into `a` here
-   |         move occurs because `a` has type `Option<[U; 2]>` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `Option<[U; 2]>`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -349,7 +349,7 @@ LL |     fn f1(a @ ref b: U) {}
    |           ^   ----- value borrowed here after move
    |           |
    |           value moved into `a` here
-   |           move occurs because `a` has type `U` which does not implement the `Copy` trait
+   |           move occurs because `a` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -364,7 +364,7 @@ LL |     fn f2(mut a @ (b @ ref c, mut d @ ref e): (U, U)) {}
    |           |            |
    |           |            value borrowed here after move
    |           value moved into `a` here
-   |           move occurs because `a` has type `(U, U)` which does not implement the `Copy` trait
+   |           move occurs because `a` has type `(U, U)`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -378,7 +378,7 @@ LL |     fn f2(mut a @ (b @ ref c, mut d @ ref e): (U, U)) {}
    |                    ^   ----- value borrowed here after move
    |                    |
    |                    value moved into `b` here
-   |                    move occurs because `b` has type `U` which does not implement the `Copy` trait
+   |                    move occurs because `b` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -392,7 +392,7 @@ LL |     fn f2(mut a @ (b @ ref c, mut d @ ref e): (U, U)) {}
    |                               ^^^^^   ----- value borrowed here after move
    |                               |
    |                               value moved into `d` here
-   |                               move occurs because `d` has type `U` which does not implement the `Copy` trait
+   |                               move occurs because `d` has type `U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -417,7 +417,7 @@ LL |     fn f3(a @ [ref mut b, ref c]: [U; 2]) {}
    |           |    |
    |           |    value borrowed here after move
    |           value moved into `a` here
-   |           move occurs because `a` has type `[U; 2]` which does not implement the `Copy` trait
+   |           move occurs because `a` has type `[U; 2]`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
diff --git a/tests/ui/pattern/bindings-after-at/borrowck-pat-ref-mut-twice.stderr b/tests/ui/pattern/bindings-after-at/borrowck-pat-ref-mut-twice.stderr
index 3446148d2b1..76085f897ff 100644
--- a/tests/ui/pattern/bindings-after-at/borrowck-pat-ref-mut-twice.stderr
+++ b/tests/ui/pattern/bindings-after-at/borrowck-pat-ref-mut-twice.stderr
@@ -78,7 +78,7 @@ LL |     let a @ (ref mut b, ref mut c) = (U, U);
    |         |    |
    |         |    value borrowed here after move
    |         value moved into `a` here
-   |         move occurs because `a` has type `(U, U)` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `(U, U)`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -94,7 +94,7 @@ LL |     let a @ (b, [c, d]) = &mut val; // Same as ^--
    |         |    |   value borrowed here after move
    |         |    value borrowed here after move
    |         value moved into `a` here
-   |         move occurs because `a` has type `&mut (U, [U; 2])` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `&mut (U, [U; 2])`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -108,7 +108,7 @@ LL |     let a @ &mut ref mut b = &mut U;
    |         ^        --------- value borrowed here after move
    |         |
    |         value moved into `a` here
-   |         move occurs because `a` has type `&mut U` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `&mut U`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -123,7 +123,7 @@ LL |     let a @ &mut (ref mut b, ref mut c) = &mut (U, U);
    |         |         |
    |         |         value borrowed here after move
    |         value moved into `a` here
-   |         move occurs because `a` has type `&mut (U, U)` which does not implement the `Copy` trait
+   |         move occurs because `a` has type `&mut (U, U)`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
diff --git a/tests/ui/pattern/bindings-after-at/default-binding-modes-both-sides-independent.stderr b/tests/ui/pattern/bindings-after-at/default-binding-modes-both-sides-independent.stderr
index 36515c1a29b..a0a43e83a6a 100644
--- a/tests/ui/pattern/bindings-after-at/default-binding-modes-both-sides-independent.stderr
+++ b/tests/ui/pattern/bindings-after-at/default-binding-modes-both-sides-independent.stderr
@@ -29,7 +29,7 @@ LL |         Ok(ref a @ b) | Err(b @ ref a) => {
    |                             ^   ----- value borrowed here after move
    |                             |
    |                             value moved into `b` here
-   |                             move occurs because `b` has type `NotCopy` which does not implement the `Copy` trait
+   |                             move occurs because `b` has type `NotCopy`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
diff --git a/tests/ui/pattern/usefulness/integer-ranges/exhaustiveness.stderr b/tests/ui/pattern/usefulness/integer-ranges/exhaustiveness.stderr
index 90d0fd7483a..68976c1b057 100644
--- a/tests/ui/pattern/usefulness/integer-ranges/exhaustiveness.stderr
+++ b/tests/ui/pattern/usefulness/integer-ranges/exhaustiveness.stderr
@@ -107,17 +107,17 @@ help: ensure that all possible cases are being handled by adding a match arm wit
 LL |         match $s { $($t)+ => {}, u128::MAX => todo!() }
    |                                ++++++++++++++++++++++
 
-error[E0004]: non-exhaustive patterns: `5_u128..=u128::MAX` not covered
+error[E0004]: non-exhaustive patterns: `5_u128..` not covered
   --> $DIR/exhaustiveness.rs:61:8
    |
 LL |     m!(0u128, 0..=4);
-   |        ^^^^^ pattern `5_u128..=u128::MAX` not covered
+   |        ^^^^^ pattern `5_u128..` not covered
    |
    = note: the matched value is of type `u128`
 help: ensure that all possible cases are being handled by adding a match arm with a wildcard pattern or an explicit pattern as shown
    |
-LL |         match $s { $($t)+ => {}, 5_u128..=u128::MAX => todo!() }
-   |                                +++++++++++++++++++++++++++++++
+LL |         match $s { $($t)+ => {}, 5_u128.. => todo!() }
+   |                                +++++++++++++++++++++
 
 error[E0004]: non-exhaustive patterns: `0_u128` not covered
   --> $DIR/exhaustiveness.rs:62:8
diff --git a/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.fixed b/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.fixed
index 8a67b20eec1..d95faef8ac4 100644
--- a/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.fixed
+++ b/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.fixed
@@ -18,6 +18,16 @@ impl Index<str> for A {
     }
 }
 
+// This is used to make `use std::ops::Index;` not unused_import.
+// details in fix(#122373) for issue #121331
+pub struct C;
+impl Index<str> for C {
+    type Output = ();
+    fn index(&self, _: str) -> &Self::Output {
+        &()
+    }
+}
+
 mod inner {
     pub trait Trait<T> {}
 }
@@ -29,4 +39,5 @@ use inner::Trait;
 impl Trait<u8> for () {}
 //~^ ERROR unnecessary qualification
 
+impl Trait<A> for A {}
 fn main() {}
diff --git a/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.rs b/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.rs
index 528edb331cf..0eee8f71ad4 100644
--- a/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.rs
+++ b/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.rs
@@ -18,6 +18,16 @@ impl ops::Index<str> for A {
     }
 }
 
+// This is used to make `use std::ops::Index;` not unused_import.
+// details in fix(#122373) for issue #121331
+pub struct C;
+impl Index<str> for C {
+    type Output = ();
+    fn index(&self, _: str) -> &Self::Output {
+        &()
+    }
+}
+
 mod inner {
     pub trait Trait<T> {}
 }
@@ -29,4 +39,5 @@ use inner::Trait;
 impl inner::Trait<u8> for () {}
 //~^ ERROR unnecessary qualification
 
+impl Trait<A> for A {}
 fn main() {}
diff --git a/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.stderr b/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.stderr
index bcda7210712..e105b754b71 100644
--- a/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.stderr
+++ b/tests/ui/resolve/issue-113808-invalid-unused-qualifications-suggestion.stderr
@@ -16,7 +16,7 @@ LL + impl Index<str> for A {
    |
 
 error: unnecessary qualification
-  --> $DIR/issue-113808-invalid-unused-qualifications-suggestion.rs:29:6
+  --> $DIR/issue-113808-invalid-unused-qualifications-suggestion.rs:39:6
    |
 LL | impl inner::Trait<u8> for () {}
    |      ^^^^^^^^^^^^^^^^
diff --git a/tests/ui/resolve/unused-qualifications-suggestion.fixed b/tests/ui/resolve/unused-qualifications-suggestion.fixed
index 6935f611b36..22e0daea467 100644
--- a/tests/ui/resolve/unused-qualifications-suggestion.fixed
+++ b/tests/ui/resolve/unused-qualifications-suggestion.fixed
@@ -16,8 +16,10 @@ fn main() {
     use foo::bar;
     bar();
     //~^ ERROR unnecessary qualification
+    bar();
 
     use baz::qux::quux;
     quux();
     //~^ ERROR unnecessary qualification
+    quux();
 }
diff --git a/tests/ui/resolve/unused-qualifications-suggestion.rs b/tests/ui/resolve/unused-qualifications-suggestion.rs
index b3fe04ff0ea..89516c1344a 100644
--- a/tests/ui/resolve/unused-qualifications-suggestion.rs
+++ b/tests/ui/resolve/unused-qualifications-suggestion.rs
@@ -16,8 +16,10 @@ fn main() {
     use foo::bar;
     foo::bar();
     //~^ ERROR unnecessary qualification
+    bar();
 
     use baz::qux::quux;
     baz::qux::quux();
     //~^ ERROR unnecessary qualification
+    quux();
 }
diff --git a/tests/ui/resolve/unused-qualifications-suggestion.stderr b/tests/ui/resolve/unused-qualifications-suggestion.stderr
index e3dac37fc6e..5b71ba9e222 100644
--- a/tests/ui/resolve/unused-qualifications-suggestion.stderr
+++ b/tests/ui/resolve/unused-qualifications-suggestion.stderr
@@ -16,7 +16,7 @@ LL +     bar();
    |
 
 error: unnecessary qualification
-  --> $DIR/unused-qualifications-suggestion.rs:21:5
+  --> $DIR/unused-qualifications-suggestion.rs:22:5
    |
 LL |     baz::qux::quux();
    |     ^^^^^^^^^^^^^^
diff --git a/tests/ui/rfcs/rfc-1623-static/rfc1623-2.rs b/tests/ui/rfcs/rfc-1623-static/rfc1623-2.rs
index c0e13a5f5f0..5d11941414f 100644
--- a/tests/ui/rfcs/rfc-1623-static/rfc1623-2.rs
+++ b/tests/ui/rfcs/rfc-1623-static/rfc1623-2.rs
@@ -26,8 +26,8 @@ static SOME_STRUCT: &SomeStruct = &SomeStruct {
     foo: &Foo { bools: &[false, true] },
     bar: &Bar { bools: &[true, true] },
     f: &id,
-    //~^ ERROR mismatched types
-    //~| ERROR mismatched types
+    //~^ ERROR implementation of `Fn` is not general enough
+    //~| ERROR implementation of `Fn` is not general enough
     //~| ERROR implementation of `FnOnce` is not general enough
     //~| ERROR implementation of `FnOnce` is not general enough
 };
diff --git a/tests/ui/rfcs/rfc-1623-static/rfc1623-2.stderr b/tests/ui/rfcs/rfc-1623-static/rfc1623-2.stderr
index 52c700c326e..5c98a9d4fb4 100644
--- a/tests/ui/rfcs/rfc-1623-static/rfc1623-2.stderr
+++ b/tests/ui/rfcs/rfc-1623-static/rfc1623-2.stderr
@@ -1,21 +1,20 @@
-error[E0308]: mismatched types
+error: implementation of `Fn` is not general enough
   --> $DIR/rfc1623-2.rs:28:8
    |
 LL |     f: &id,
-   |        ^^^ one type is more general than the other
+   |        ^^^ implementation of `Fn` is not general enough
    |
-   = note: expected trait `for<'a, 'b> Fn(&'a Foo<'b>)`
-              found trait `Fn(&Foo<'_>)`
+   = note: `fn(&'2 Foo<'_>) -> &'2 Foo<'_> {id::<&'2 Foo<'_>>}` must implement `Fn<(&'1 Foo<'b>,)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `Fn<(&'2 Foo<'_>,)>`, for some specific lifetime `'2`
 
-error[E0308]: mismatched types
+error: implementation of `Fn` is not general enough
   --> $DIR/rfc1623-2.rs:28:8
    |
 LL |     f: &id,
-   |        ^^^ one type is more general than the other
+   |        ^^^ implementation of `Fn` is not general enough
    |
-   = note: expected trait `for<'a, 'b> Fn(&'a Foo<'b>)`
-              found trait `Fn(&Foo<'_>)`
-   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+   = note: `fn(&Foo<'2>) -> &Foo<'2> {id::<&Foo<'2>>}` must implement `Fn<(&'a Foo<'1>,)>`, for any lifetime `'1`...
+   = note: ...but it actually implements `Fn<(&Foo<'2>,)>`, for some specific lifetime `'2`
 
 error: implementation of `FnOnce` is not general enough
   --> $DIR/rfc1623-2.rs:28:8
@@ -37,4 +36,3 @@ LL |     f: &id,
 
 error: aborting due to 4 previous errors
 
-For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/simd/const-err-trumps-simd-err.rs b/tests/ui/simd/const-err-trumps-simd-err.rs
new file mode 100644
index 00000000000..06a747273ab
--- /dev/null
+++ b/tests/ui/simd/const-err-trumps-simd-err.rs
@@ -0,0 +1,24 @@
+//@build-fail
+//! Make sure that monomorphization-time const errors from `static_assert` take priority over the
+//! error from simd_extract. Basically this checks that if a const fails to evaluate in some
+//! function, we don't bother codegen'ing the function.
+#![feature(generic_arg_infer)]
+#![feature(core_intrinsics)]
+#![feature(repr_simd)]
+#![feature(inline_const)]
+use std::intrinsics::simd::*;
+
+#[repr(simd)]
+#[allow(non_camel_case_types)]
+struct int8x4_t(u8,u8,u8,u8);
+
+fn get_elem<const LANE: u32>(a: int8x4_t) -> u8 {
+    const { assert!(LANE < 4); } // the error should be here...
+    //~^ ERROR failed
+    //~| assertion failed
+    unsafe { simd_extract(a, LANE) } // ...not here
+}
+
+fn main() {
+    get_elem::<4>(int8x4_t(0,0,0,0));
+}
diff --git a/tests/ui/simd/const-err-trumps-simd-err.stderr b/tests/ui/simd/const-err-trumps-simd-err.stderr
new file mode 100644
index 00000000000..1e46667cf4e
--- /dev/null
+++ b/tests/ui/simd/const-err-trumps-simd-err.stderr
@@ -0,0 +1,23 @@
+error[E0080]: evaluation of `get_elem::<4>::{constant#0}` failed
+  --> $DIR/const-err-trumps-simd-err.rs:16:13
+   |
+LL |     const { assert!(LANE < 4); } // the error should be here...
+   |             ^^^^^^^^^^^^^^^^^ the evaluated program panicked at 'assertion failed: LANE < 4', $DIR/const-err-trumps-simd-err.rs:16:13
+   |
+   = note: this error originates in the macro `assert` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+note: erroneous constant encountered
+  --> $DIR/const-err-trumps-simd-err.rs:16:5
+   |
+LL |     const { assert!(LANE < 4); } // the error should be here...
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+note: the above error was encountered while instantiating `fn get_elem::<4>`
+  --> $DIR/const-err-trumps-simd-err.rs:23:5
+   |
+LL |     get_elem::<4>(int8x4_t(0,0,0,0));
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/stats/hir-stats.stderr b/tests/ui/stats/hir-stats.stderr
index 579a5d5180e..dc24833c267 100644
--- a/tests/ui/stats/hir-stats.stderr
+++ b/tests/ui/stats/hir-stats.stderr
@@ -17,7 +17,7 @@ ast-stats-1 - Fn                        96 ( 1.4%)             1
 ast-stats-1 FnDecl                   120 ( 1.8%)             5            24
 ast-stats-1 FieldDef                 160 ( 2.4%)             2            80
 ast-stats-1 Stmt                     160 ( 2.4%)             5            32
-ast-stats-1 - Local                     32 ( 0.5%)             1
+ast-stats-1 - Let                       32 ( 0.5%)             1
 ast-stats-1 - MacCall                   32 ( 0.5%)             1
 ast-stats-1 - Expr                      96 ( 1.4%)             3
 ast-stats-1 Param                    160 ( 2.4%)             4            40
@@ -75,7 +75,7 @@ ast-stats-2 - DocComment                32 ( 0.4%)             1
 ast-stats-2 - Normal                    96 ( 1.3%)             3
 ast-stats-2 FieldDef                 160 ( 2.2%)             2            80
 ast-stats-2 Stmt                     160 ( 2.2%)             5            32
-ast-stats-2 - Local                     32 ( 0.4%)             1
+ast-stats-2 - Let                       32 ( 0.4%)             1
 ast-stats-2 - Semi                      32 ( 0.4%)             1
 ast-stats-2 - Expr                      96 ( 1.3%)             3
 ast-stats-2 Param                    160 ( 2.2%)             4            40
@@ -131,7 +131,7 @@ hir-stats ImplItemRef               72 ( 0.8%)             2            36
 hir-stats Arm                       80 ( 0.9%)             2            40
 hir-stats FieldDef                  96 ( 1.1%)             2            48
 hir-stats Stmt                      96 ( 1.1%)             3            32
-hir-stats - Local                     32 ( 0.4%)             1
+hir-stats - Let                       32 ( 0.4%)             1
 hir-stats - Semi                      32 ( 0.4%)             1
 hir-stats - Expr                      32 ( 0.4%)             1
 hir-stats FnDecl                   120 ( 1.3%)             3            40
diff --git a/tests/ui/suggestions/clone-bounds-121524.rs b/tests/ui/suggestions/clone-bounds-121524.rs
new file mode 100644
index 00000000000..8cd60b452de
--- /dev/null
+++ b/tests/ui/suggestions/clone-bounds-121524.rs
@@ -0,0 +1,19 @@
+#[derive(Clone)]
+struct ThingThatDoesAThing;
+
+trait DoesAThing {}
+
+impl DoesAThing for ThingThatDoesAThing {}
+
+fn clones_impl_ref_inline(thing: &impl DoesAThing) {
+    //~^ HELP consider further restricting this bound
+    drops_impl_owned(thing.clone()); //~ ERROR E0277
+    //~^ NOTE copies the reference
+    //~| NOTE the trait `DoesAThing` is not implemented for `&impl DoesAThing`
+}
+
+fn drops_impl_owned(_thing: impl DoesAThing) { }
+
+fn main() {
+    clones_impl_ref_inline(&ThingThatDoesAThing);
+}
diff --git a/tests/ui/suggestions/clone-bounds-121524.stderr b/tests/ui/suggestions/clone-bounds-121524.stderr
new file mode 100644
index 00000000000..6d60508a4a1
--- /dev/null
+++ b/tests/ui/suggestions/clone-bounds-121524.stderr
@@ -0,0 +1,19 @@
+error[E0277]: the trait bound `&impl DoesAThing: DoesAThing` is not satisfied
+  --> $DIR/clone-bounds-121524.rs:10:22
+   |
+LL |     drops_impl_owned(thing.clone());
+   |                      ^^^^^^^^^^^^^ the trait `DoesAThing` is not implemented for `&impl DoesAThing`
+   |
+note: this `clone()` copies the reference, which does not do anything, because `impl DoesAThing` does not implement `Clone`
+  --> $DIR/clone-bounds-121524.rs:10:28
+   |
+LL |     drops_impl_owned(thing.clone());
+   |                            ^^^^^
+help: consider further restricting this bound
+   |
+LL | fn clones_impl_ref_inline(thing: &impl DoesAThing + Clone) {
+   |                                                   +++++++
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0277`.
diff --git a/tests/ui/suggestions/late-bound-in-borrow-closure-sugg.stderr b/tests/ui/suggestions/late-bound-in-borrow-closure-sugg.stderr
index ee924522564..f0acf1dbb96 100644
--- a/tests/ui/suggestions/late-bound-in-borrow-closure-sugg.stderr
+++ b/tests/ui/suggestions/late-bound-in-borrow-closure-sugg.stderr
@@ -10,7 +10,7 @@ LL |     trader.set_closure(closure);
    |            required by a bound introduced by this call
    |
    = note: expected closure signature `for<'a, 'b> fn(&'a mut Trader<'b>) -> _`
-              found closure signature `for<'a> fn(Trader<'a>) -> _`
+              found closure signature `fn(Trader<'_>) -> _`
 note: required by a bound in `Trader::<'a>::set_closure`
   --> $DIR/late-bound-in-borrow-closure-sugg.rs:15:50
    |
diff --git a/tests/ui/suggestions/ref-pattern-binding.stderr b/tests/ui/suggestions/ref-pattern-binding.stderr
index 69ce5d440af..af21c6aef70 100644
--- a/tests/ui/suggestions/ref-pattern-binding.stderr
+++ b/tests/ui/suggestions/ref-pattern-binding.stderr
@@ -5,7 +5,7 @@ LL |     let _moved @ ref _from = String::from("foo");
    |         ^^^^^^   --------- value borrowed here after move
    |         |
    |         value moved into `_moved` here
-   |         move occurs because `_moved` has type `String` which does not implement the `Copy` trait
+   |         move occurs because `_moved` has type `String`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
@@ -35,7 +35,7 @@ LL |     let _moved @ S { ref f } = S { f: String::from("foo") };
    |         ^^^^^^       ----- value borrowed here after move
    |         |
    |         value moved into `_moved` here
-   |         move occurs because `_moved` has type `S` which does not implement the `Copy` trait
+   |         move occurs because `_moved` has type `S`, which does not implement the `Copy` trait
    |
 help: borrow this binding in the pattern to avoid moving the value
    |
diff --git a/tests/ui/traits/non_lifetime_binders/type-match-with-late-bound.stderr b/tests/ui/traits/non_lifetime_binders/type-match-with-late-bound.stderr
index 6c259621466..40e16dde6e4 100644
--- a/tests/ui/traits/non_lifetime_binders/type-match-with-late-bound.stderr
+++ b/tests/ui/traits/non_lifetime_binders/type-match-with-late-bound.stderr
@@ -8,6 +8,27 @@ LL | #![feature(non_lifetime_binders)]
    = note: `#[warn(incomplete_features)]` on by default
 
 error[E0309]: the placeholder type `!1_"F"` may not live long enough
+  --> $DIR/type-match-with-late-bound.rs:8:1
+   |
+LL |   async fn walk2<'a, T: 'a>(_: T)
+   |   ^              -- the placeholder type `!1_"F"` must be valid for the lifetime `'a` as defined here...
+   |  _|
+   | |
+LL | | where
+LL | |     for<F> F: 'a,
+   | |_________________^ ...so that the type `F` will meet its required lifetime bounds...
+   |
+note: ...that is required by this bound
+  --> $DIR/type-match-with-late-bound.rs:10:15
+   |
+LL |     for<F> F: 'a,
+   |               ^^
+help: consider adding an explicit lifetime bound
+   |
+LL |     for<F> F: 'a, !1_"F": 'a
+   |                 ~~~~~~~~~~~~
+
+error[E0309]: the placeholder type `!1_"F"` may not live long enough
   --> $DIR/type-match-with-late-bound.rs:11:1
    |
 LL | async fn walk2<'a, T: 'a>(_: T)
@@ -35,6 +56,6 @@ help: consider adding an explicit lifetime bound
 LL |     for<F> F: 'a, !2_"F": 'a
    |                 ~~~~~~~~~~~~
 
-error: aborting due to 2 previous errors; 1 warning emitted
+error: aborting due to 3 previous errors; 1 warning emitted
 
 For more information about this error, try `rustc --explain E0309`.
diff --git a/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.current.stderr b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.current.stderr
new file mode 100644
index 00000000000..098ab71e946
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.current.stderr
@@ -0,0 +1,22 @@
+error[E0308]: mismatched types
+  --> $DIR/higher-ranked-upcasting-ok.rs:17:5
+   |
+LL |     x
+   |     ^ one type is more general than the other
+   |
+   = note: expected existential trait ref `for<'a, 'b> Supertrait<'a, 'b>`
+              found existential trait ref `for<'a> Supertrait<'a, 'a>`
+
+error[E0308]: mismatched types
+  --> $DIR/higher-ranked-upcasting-ok.rs:17:5
+   |
+LL |     x
+   |     ^ one type is more general than the other
+   |
+   = note: expected existential trait ref `for<'a, 'b> Supertrait<'a, 'b>`
+              found existential trait ref `for<'a> Supertrait<'a, 'a>`
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.next.stderr b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.next.stderr
new file mode 100644
index 00000000000..ac516fd6975
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.next.stderr
@@ -0,0 +1,14 @@
+error[E0308]: mismatched types
+  --> $DIR/higher-ranked-upcasting-ok.rs:17:5
+   |
+LL | fn ok(x: &dyn for<'a, 'b> Subtrait<'a, 'b>) -> &dyn for<'a> Supertrait<'a, 'a> {
+   |                                                ------------------------------- expected `&dyn for<'a> Supertrait<'a, 'a>` because of return type
+LL |     x
+   |     ^ expected trait `Supertrait`, found trait `Subtrait`
+   |
+   = note: expected reference `&dyn for<'a> Supertrait<'a, 'a>`
+              found reference `&dyn for<'a, 'b> Subtrait<'a, 'b>`
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.rs b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.rs
new file mode 100644
index 00000000000..00743203179
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ok.rs
@@ -0,0 +1,19 @@
+//@ revisions: current next
+//@ ignore-compare-mode-next-solver (explicit revisions)
+//@[next] compile-flags: -Znext-solver
+
+// We should be able to instantiate a binder during trait upcasting.
+// This test could be `check-pass`, but we should make sure that we
+// do so in both trait solvers.
+#![feature(trait_upcasting)]
+#![crate_type = "rlib"]
+trait Supertrait<'a, 'b> {}
+
+trait Subtrait<'a, 'b>: Supertrait<'a, 'b> {}
+
+impl<'a> Supertrait<'a, 'a> for () {}
+impl<'a> Subtrait<'a, 'a> for () {}
+fn ok(x: &dyn for<'a, 'b> Subtrait<'a, 'b>) -> &dyn for<'a> Supertrait<'a, 'a> {
+    x //~ ERROR mismatched types
+    //[current]~^ ERROR mismatched types
+}
diff --git a/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.current.stderr b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.current.stderr
new file mode 100644
index 00000000000..bac82983268
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.current.stderr
@@ -0,0 +1,22 @@
+error[E0308]: mismatched types
+  --> $DIR/higher-ranked-upcasting-ub.rs:22:5
+   |
+LL |     x
+   |     ^ one type is more general than the other
+   |
+   = note: expected existential trait ref `for<'a> Supertrait<'a, 'a>`
+              found existential trait ref `for<'a, 'b> Supertrait<'a, 'b>`
+
+error[E0308]: mismatched types
+  --> $DIR/higher-ranked-upcasting-ub.rs:22:5
+   |
+LL |     x
+   |     ^ one type is more general than the other
+   |
+   = note: expected existential trait ref `for<'a> Supertrait<'a, 'a>`
+              found existential trait ref `for<'a, 'b> Supertrait<'a, 'b>`
+   = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.next.stderr b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.next.stderr
new file mode 100644
index 00000000000..b82f1eef42b
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.next.stderr
@@ -0,0 +1,14 @@
+error[E0308]: mismatched types
+  --> $DIR/higher-ranked-upcasting-ub.rs:22:5
+   |
+LL | fn unsound(x: &dyn for<'a> Subtrait<'a, 'a>) -> &dyn for<'a, 'b> Supertrait<'a, 'b> {
+   |                                                 ----------------------------------- expected `&dyn for<'a, 'b> Supertrait<'a, 'b>` because of return type
+LL |     x
+   |     ^ expected trait `Supertrait`, found trait `Subtrait`
+   |
+   = note: expected reference `&dyn for<'a, 'b> Supertrait<'a, 'b>`
+              found reference `&dyn for<'a> Subtrait<'a, 'a>`
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.rs b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.rs
new file mode 100644
index 00000000000..2cf6fc75e77
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/higher-ranked-upcasting-ub.rs
@@ -0,0 +1,37 @@
+//@ revisions: current next
+//@ ignore-compare-mode-next-solver (explicit revisions)
+//@[next] compile-flags: -Znext-solver
+
+// We previously wrongly instantiated binders during trait upcasting,
+// allowing the super trait to be more generic than the sub trait.
+// This was unsound.
+#![feature(trait_upcasting)]
+trait Supertrait<'a, 'b> {
+    fn cast(&self, x: &'a str) -> &'b str;
+}
+
+trait Subtrait<'a, 'b>: Supertrait<'a, 'b> {}
+
+impl<'a> Supertrait<'a, 'a> for () {
+    fn cast(&self, x: &'a str) -> &'a str {
+        x
+    }
+}
+impl<'a> Subtrait<'a, 'a> for () {}
+fn unsound(x: &dyn for<'a> Subtrait<'a, 'a>) -> &dyn for<'a, 'b> Supertrait<'a, 'b> {
+    x //~ ERROR mismatched types
+    //[current]~^ ERROR mismatched types
+}
+
+fn transmute<'a, 'b>(x: &'a str) -> &'b str {
+    unsound(&()).cast(x)
+}
+
+fn main() {
+    let x;
+    {
+        let mut temp = String::from("hello there");
+        x = transmute(temp.as_str());
+    }
+    println!("{x}");
+}
diff --git a/tests/ui/transmutability/alignment/align-fail.stderr b/tests/ui/transmutability/alignment/align-fail.stderr
index c92c3d841f2..f05e55fb024 100644
--- a/tests/ui/transmutability/alignment/align-fail.stderr
+++ b/tests/ui/transmutability/alignment/align-fail.stderr
@@ -2,7 +2,7 @@ error[E0277]: `&[u8; 0]` cannot be safely transmuted into `&[u16; 0]`
   --> $DIR/align-fail.rs:21:55
    |
 LL | ...tatic [u8; 0], &'static [u16; 0]>();
-   |                   ^^^^^^^^^^^^^^^^^ The minimum alignment of `&[u8; 0]` (1) should be greater than that of `&[u16; 0]` (2)
+   |                   ^^^^^^^^^^^^^^^^^ the minimum alignment of `&[u8; 0]` (1) should be greater than that of `&[u16; 0]` (2)
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/align-fail.rs:9:14
diff --git a/tests/ui/transmutability/arrays/should_require_well_defined_layout.stderr b/tests/ui/transmutability/arrays/should_require_well_defined_layout.stderr
index fd21ac34183..e486928a445 100644
--- a/tests/ui/transmutability/arrays/should_require_well_defined_layout.stderr
+++ b/tests/ui/transmutability/arrays/should_require_well_defined_layout.stderr
@@ -2,7 +2,7 @@ error[E0277]: `[String; 0]` cannot be safely transmuted into `()`
   --> $DIR/should_require_well_defined_layout.rs:25:52
    |
 LL |         assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                    ^^ `[String; 0]` does not have a well-specified layout
+   |                                                    ^^ analyzing the transmutability of `[String; 0]` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -23,7 +23,7 @@ error[E0277]: `u128` cannot be safely transmuted into `[String; 0]`
   --> $DIR/should_require_well_defined_layout.rs:26:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                               ^^^^^^^^^ `[String; 0]` does not have a well-specified layout
+   |                                               ^^^^^^^^^ analyzing the transmutability of `[String; 0]` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -44,7 +44,7 @@ error[E0277]: `[String; 1]` cannot be safely transmuted into `()`
   --> $DIR/should_require_well_defined_layout.rs:31:52
    |
 LL |         assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                    ^^ `[String; 1]` does not have a well-specified layout
+   |                                                    ^^ analyzing the transmutability of `[String; 1]` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -65,7 +65,7 @@ error[E0277]: `u128` cannot be safely transmuted into `[String; 1]`
   --> $DIR/should_require_well_defined_layout.rs:32:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                               ^^^^^^^^^ `[String; 1]` does not have a well-specified layout
+   |                                               ^^^^^^^^^ analyzing the transmutability of `[String; 1]` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -86,7 +86,7 @@ error[E0277]: `[String; 2]` cannot be safely transmuted into `()`
   --> $DIR/should_require_well_defined_layout.rs:37:52
    |
 LL |         assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                    ^^ `[String; 2]` does not have a well-specified layout
+   |                                                    ^^ analyzing the transmutability of `[String; 2]` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -107,7 +107,7 @@ error[E0277]: `u128` cannot be safely transmuted into `[String; 2]`
   --> $DIR/should_require_well_defined_layout.rs:38:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                               ^^^^^^^^^ `[String; 2]` does not have a well-specified layout
+   |                                               ^^^^^^^^^ analyzing the transmutability of `[String; 2]` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
diff --git a/tests/ui/transmutability/enums/repr/primitive_reprs_should_have_correct_length.stderr b/tests/ui/transmutability/enums/repr/primitive_reprs_should_have_correct_length.stderr
index b2ff04eeed9..6c88bf4ff96 100644
--- a/tests/ui/transmutability/enums/repr/primitive_reprs_should_have_correct_length.stderr
+++ b/tests/ui/transmutability/enums/repr/primitive_reprs_should_have_correct_length.stderr
@@ -2,7 +2,7 @@ error[E0277]: `Zst` cannot be safely transmuted into `V0i8`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:46:44
    |
 LL |         assert::is_transmutable::<Smaller, Current>();
-   |                                            ^^^^^^^ The size of `Zst` is smaller than the size of `V0i8`
+   |                                            ^^^^^^^ the size of `Zst` is smaller than the size of `V0i8`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -24,7 +24,7 @@ error[E0277]: `V0i8` cannot be safely transmuted into `u16`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:48:44
    |
 LL |         assert::is_transmutable::<Current, Larger>();
-   |                                            ^^^^^^ The size of `V0i8` is smaller than the size of `u16`
+   |                                            ^^^^^^ the size of `V0i8` is smaller than the size of `u16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -46,7 +46,7 @@ error[E0277]: `Zst` cannot be safely transmuted into `V0u8`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:54:44
    |
 LL |         assert::is_transmutable::<Smaller, Current>();
-   |                                            ^^^^^^^ The size of `Zst` is smaller than the size of `V0u8`
+   |                                            ^^^^^^^ the size of `Zst` is smaller than the size of `V0u8`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -68,7 +68,7 @@ error[E0277]: `V0u8` cannot be safely transmuted into `u16`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:56:44
    |
 LL |         assert::is_transmutable::<Current, Larger>();
-   |                                            ^^^^^^ The size of `V0u8` is smaller than the size of `u16`
+   |                                            ^^^^^^ the size of `V0u8` is smaller than the size of `u16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -90,7 +90,7 @@ error[E0277]: `u8` cannot be safely transmuted into `V0i16`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:68:44
    |
 LL |         assert::is_transmutable::<Smaller, Current>();
-   |                                            ^^^^^^^ The size of `u8` is smaller than the size of `V0i16`
+   |                                            ^^^^^^^ the size of `u8` is smaller than the size of `V0i16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -112,7 +112,7 @@ error[E0277]: `V0i16` cannot be safely transmuted into `u32`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:70:44
    |
 LL |         assert::is_transmutable::<Current, Larger>();
-   |                                            ^^^^^^ The size of `V0i16` is smaller than the size of `u32`
+   |                                            ^^^^^^ the size of `V0i16` is smaller than the size of `u32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -134,7 +134,7 @@ error[E0277]: `u8` cannot be safely transmuted into `V0u16`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:76:44
    |
 LL |         assert::is_transmutable::<Smaller, Current>();
-   |                                            ^^^^^^^ The size of `u8` is smaller than the size of `V0u16`
+   |                                            ^^^^^^^ the size of `u8` is smaller than the size of `V0u16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -156,7 +156,7 @@ error[E0277]: `V0u16` cannot be safely transmuted into `u32`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:78:44
    |
 LL |         assert::is_transmutable::<Current, Larger>();
-   |                                            ^^^^^^ The size of `V0u16` is smaller than the size of `u32`
+   |                                            ^^^^^^ the size of `V0u16` is smaller than the size of `u32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -178,7 +178,7 @@ error[E0277]: `u16` cannot be safely transmuted into `V0i32`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:90:44
    |
 LL |         assert::is_transmutable::<Smaller, Current>();
-   |                                            ^^^^^^^ The size of `u16` is smaller than the size of `V0i32`
+   |                                            ^^^^^^^ the size of `u16` is smaller than the size of `V0i32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -200,7 +200,7 @@ error[E0277]: `V0i32` cannot be safely transmuted into `u64`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:92:44
    |
 LL |         assert::is_transmutable::<Current, Larger>();
-   |                                            ^^^^^^ The size of `V0i32` is smaller than the size of `u64`
+   |                                            ^^^^^^ the size of `V0i32` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -222,7 +222,7 @@ error[E0277]: `u16` cannot be safely transmuted into `V0u32`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:98:44
    |
 LL |         assert::is_transmutable::<Smaller, Current>();
-   |                                            ^^^^^^^ The size of `u16` is smaller than the size of `V0u32`
+   |                                            ^^^^^^^ the size of `u16` is smaller than the size of `V0u32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -244,7 +244,7 @@ error[E0277]: `V0u32` cannot be safely transmuted into `u64`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:100:44
    |
 LL |         assert::is_transmutable::<Current, Larger>();
-   |                                            ^^^^^^ The size of `V0u32` is smaller than the size of `u64`
+   |                                            ^^^^^^ the size of `V0u32` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -266,7 +266,7 @@ error[E0277]: `u32` cannot be safely transmuted into `V0i64`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:112:44
    |
 LL |         assert::is_transmutable::<Smaller, Current>();
-   |                                            ^^^^^^^ The size of `u32` is smaller than the size of `V0i64`
+   |                                            ^^^^^^^ the size of `u32` is smaller than the size of `V0i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -288,7 +288,7 @@ error[E0277]: `V0i64` cannot be safely transmuted into `u128`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:114:44
    |
 LL |         assert::is_transmutable::<Current, Larger>();
-   |                                            ^^^^^^ The size of `V0i64` is smaller than the size of `u128`
+   |                                            ^^^^^^ the size of `V0i64` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -310,7 +310,7 @@ error[E0277]: `u32` cannot be safely transmuted into `V0u64`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:120:44
    |
 LL |         assert::is_transmutable::<Smaller, Current>();
-   |                                            ^^^^^^^ The size of `u32` is smaller than the size of `V0u64`
+   |                                            ^^^^^^^ the size of `u32` is smaller than the size of `V0u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -332,7 +332,7 @@ error[E0277]: `V0u64` cannot be safely transmuted into `u128`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:122:44
    |
 LL |         assert::is_transmutable::<Current, Larger>();
-   |                                            ^^^^^^ The size of `V0u64` is smaller than the size of `u128`
+   |                                            ^^^^^^ the size of `V0u64` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -354,7 +354,7 @@ error[E0277]: `u8` cannot be safely transmuted into `V0isize`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:134:44
    |
 LL |         assert::is_transmutable::<Smaller, Current>();
-   |                                            ^^^^^^^ The size of `u8` is smaller than the size of `V0isize`
+   |                                            ^^^^^^^ the size of `u8` is smaller than the size of `V0isize`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -376,7 +376,7 @@ error[E0277]: `V0isize` cannot be safely transmuted into `[usize; 2]`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:136:44
    |
 LL |         assert::is_transmutable::<Current, Larger>();
-   |                                            ^^^^^^ The size of `V0isize` is smaller than the size of `[usize; 2]`
+   |                                            ^^^^^^ the size of `V0isize` is smaller than the size of `[usize; 2]`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -398,7 +398,7 @@ error[E0277]: `u8` cannot be safely transmuted into `V0usize`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:142:44
    |
 LL |         assert::is_transmutable::<Smaller, Current>();
-   |                                            ^^^^^^^ The size of `u8` is smaller than the size of `V0usize`
+   |                                            ^^^^^^^ the size of `u8` is smaller than the size of `V0usize`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
@@ -420,7 +420,7 @@ error[E0277]: `V0usize` cannot be safely transmuted into `[usize; 2]`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:144:44
    |
 LL |         assert::is_transmutable::<Current, Larger>();
-   |                                            ^^^^^^ The size of `V0usize` is smaller than the size of `[usize; 2]`
+   |                                            ^^^^^^ the size of `V0usize` is smaller than the size of `[usize; 2]`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14
diff --git a/tests/ui/transmutability/enums/repr/should_require_well_defined_layout.stderr b/tests/ui/transmutability/enums/repr/should_require_well_defined_layout.stderr
index 24730935047..2a683de6a65 100644
--- a/tests/ui/transmutability/enums/repr/should_require_well_defined_layout.stderr
+++ b/tests/ui/transmutability/enums/repr/should_require_well_defined_layout.stderr
@@ -2,7 +2,7 @@ error[E0277]: `void::repr_rust` cannot be safely transmuted into `()`
   --> $DIR/should_require_well_defined_layout.rs:27:52
    |
 LL |         assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                    ^^ `void::repr_rust` does not have a well-specified layout
+   |                                                    ^^ analyzing the transmutability of `void::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:13:14
@@ -24,7 +24,7 @@ error[E0277]: `u128` cannot be safely transmuted into `void::repr_rust`
   --> $DIR/should_require_well_defined_layout.rs:28:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                               ^^^^^^^^^ `void::repr_rust` does not have a well-specified layout
+   |                                               ^^^^^^^^^ analyzing the transmutability of `void::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:13:14
@@ -46,7 +46,7 @@ error[E0277]: `singleton::repr_rust` cannot be safely transmuted into `()`
   --> $DIR/should_require_well_defined_layout.rs:33:52
    |
 LL |         assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                    ^^ `singleton::repr_rust` does not have a well-specified layout
+   |                                                    ^^ analyzing the transmutability of `singleton::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:13:14
@@ -68,7 +68,7 @@ error[E0277]: `u128` cannot be safely transmuted into `singleton::repr_rust`
   --> $DIR/should_require_well_defined_layout.rs:34:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                               ^^^^^^^^^ `singleton::repr_rust` does not have a well-specified layout
+   |                                               ^^^^^^^^^ analyzing the transmutability of `singleton::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:13:14
@@ -90,7 +90,7 @@ error[E0277]: `duplex::repr_rust` cannot be safely transmuted into `()`
   --> $DIR/should_require_well_defined_layout.rs:39:52
    |
 LL |         assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                    ^^ `duplex::repr_rust` does not have a well-specified layout
+   |                                                    ^^ analyzing the transmutability of `duplex::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:13:14
@@ -112,7 +112,7 @@ error[E0277]: `u128` cannot be safely transmuted into `duplex::repr_rust`
   --> $DIR/should_require_well_defined_layout.rs:40:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                               ^^^^^^^^^ `duplex::repr_rust` does not have a well-specified layout
+   |                                               ^^^^^^^^^ analyzing the transmutability of `duplex::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:13:14
diff --git a/tests/ui/transmutability/enums/should_pad_variants.stderr b/tests/ui/transmutability/enums/should_pad_variants.stderr
index 13b4c8053ad..da4294bdbce 100644
--- a/tests/ui/transmutability/enums/should_pad_variants.stderr
+++ b/tests/ui/transmutability/enums/should_pad_variants.stderr
@@ -2,7 +2,7 @@ error[E0277]: `Src` cannot be safely transmuted into `Dst`
   --> $DIR/should_pad_variants.rs:43:36
    |
 LL |     assert::is_transmutable::<Src, Dst>();
-   |                                    ^^^ The size of `Src` is smaller than the size of `Dst`
+   |                                    ^^^ the size of `Src` is smaller than the size of `Dst`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/should_pad_variants.rs:13:14
diff --git a/tests/ui/transmutability/enums/should_respect_endianness.stderr b/tests/ui/transmutability/enums/should_respect_endianness.stderr
index c2a2eb53458..9f88bb06813 100644
--- a/tests/ui/transmutability/enums/should_respect_endianness.stderr
+++ b/tests/ui/transmutability/enums/should_respect_endianness.stderr
@@ -2,7 +2,7 @@ error[E0277]: `Src` cannot be safely transmuted into `Unexpected`
   --> $DIR/should_respect_endianness.rs:35:36
    |
 LL |     assert::is_transmutable::<Src, Unexpected>();
-   |                                    ^^^^^^^^^^ At least one value of `Src` isn't a bit-valid value of `Unexpected`
+   |                                    ^^^^^^^^^^ at least one value of `Src` isn't a bit-valid value of `Unexpected`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/should_respect_endianness.rs:13:14
diff --git a/tests/ui/transmutability/primitives/bool-mut.stderr b/tests/ui/transmutability/primitives/bool-mut.stderr
index c4f295fc70a..464c2755e11 100644
--- a/tests/ui/transmutability/primitives/bool-mut.stderr
+++ b/tests/ui/transmutability/primitives/bool-mut.stderr
@@ -2,7 +2,7 @@ error[E0277]: `u8` cannot be safely transmuted into `bool`
   --> $DIR/bool-mut.rs:15:50
    |
 LL |     assert::is_transmutable::<&'static mut bool, &'static mut u8>()
-   |                                                  ^^^^^^^^^^^^^^^ At least one value of `u8` isn't a bit-valid value of `bool`
+   |                                                  ^^^^^^^^^^^^^^^ at least one value of `u8` isn't a bit-valid value of `bool`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/bool-mut.rs:10:14
diff --git a/tests/ui/transmutability/primitives/bool.current.stderr b/tests/ui/transmutability/primitives/bool.current.stderr
index 98e4a1029c9..da6a4a44e95 100644
--- a/tests/ui/transmutability/primitives/bool.current.stderr
+++ b/tests/ui/transmutability/primitives/bool.current.stderr
@@ -2,7 +2,7 @@ error[E0277]: `u8` cannot be safely transmuted into `bool`
   --> $DIR/bool.rs:21:35
    |
 LL |     assert::is_transmutable::<u8, bool>();
-   |                                   ^^^^ At least one value of `u8` isn't a bit-valid value of `bool`
+   |                                   ^^^^ at least one value of `u8` isn't a bit-valid value of `bool`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/bool.rs:11:14
diff --git a/tests/ui/transmutability/primitives/bool.next.stderr b/tests/ui/transmutability/primitives/bool.next.stderr
index 98e4a1029c9..da6a4a44e95 100644
--- a/tests/ui/transmutability/primitives/bool.next.stderr
+++ b/tests/ui/transmutability/primitives/bool.next.stderr
@@ -2,7 +2,7 @@ error[E0277]: `u8` cannot be safely transmuted into `bool`
   --> $DIR/bool.rs:21:35
    |
 LL |     assert::is_transmutable::<u8, bool>();
-   |                                   ^^^^ At least one value of `u8` isn't a bit-valid value of `bool`
+   |                                   ^^^^ at least one value of `u8` isn't a bit-valid value of `bool`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/bool.rs:11:14
diff --git a/tests/ui/transmutability/primitives/numbers.current.stderr b/tests/ui/transmutability/primitives/numbers.current.stderr
index 7a80e444149..0a9b9d182f8 100644
--- a/tests/ui/transmutability/primitives/numbers.current.stderr
+++ b/tests/ui/transmutability/primitives/numbers.current.stderr
@@ -2,7 +2,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i16`
   --> $DIR/numbers.rs:64:40
    |
 LL |     assert::is_transmutable::<   i8,   i16>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `i16`
+   |                                        ^^^ the size of `i8` is smaller than the size of `i16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -17,7 +17,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u16`
   --> $DIR/numbers.rs:65:40
    |
 LL |     assert::is_transmutable::<   i8,   u16>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `u16`
+   |                                        ^^^ the size of `i8` is smaller than the size of `u16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -32,7 +32,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i32`
   --> $DIR/numbers.rs:66:40
    |
 LL |     assert::is_transmutable::<   i8,   i32>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `i32`
+   |                                        ^^^ the size of `i8` is smaller than the size of `i32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -47,7 +47,7 @@ error[E0277]: `i8` cannot be safely transmuted into `f32`
   --> $DIR/numbers.rs:67:40
    |
 LL |     assert::is_transmutable::<   i8,   f32>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `f32`
+   |                                        ^^^ the size of `i8` is smaller than the size of `f32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -62,7 +62,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u32`
   --> $DIR/numbers.rs:68:40
    |
 LL |     assert::is_transmutable::<   i8,   u32>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `u32`
+   |                                        ^^^ the size of `i8` is smaller than the size of `u32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -77,7 +77,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:69:40
    |
 LL |     assert::is_transmutable::<   i8,   u64>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `u64`
+   |                                        ^^^ the size of `i8` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -92,7 +92,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:70:40
    |
 LL |     assert::is_transmutable::<   i8,   i64>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `i64`
+   |                                        ^^^ the size of `i8` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -107,7 +107,7 @@ error[E0277]: `i8` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:71:40
    |
 LL |     assert::is_transmutable::<   i8,   f64>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `f64`
+   |                                        ^^^ the size of `i8` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -122,7 +122,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:72:39
    |
 LL |     assert::is_transmutable::<   i8,  u128>();
-   |                                       ^^^^ The size of `i8` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `i8` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -137,7 +137,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:73:39
    |
 LL |     assert::is_transmutable::<   i8,  i128>();
-   |                                       ^^^^ The size of `i8` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `i8` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -152,7 +152,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i16`
   --> $DIR/numbers.rs:75:40
    |
 LL |     assert::is_transmutable::<   u8,   i16>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `i16`
+   |                                        ^^^ the size of `u8` is smaller than the size of `i16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -167,7 +167,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u16`
   --> $DIR/numbers.rs:76:40
    |
 LL |     assert::is_transmutable::<   u8,   u16>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `u16`
+   |                                        ^^^ the size of `u8` is smaller than the size of `u16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -182,7 +182,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i32`
   --> $DIR/numbers.rs:77:40
    |
 LL |     assert::is_transmutable::<   u8,   i32>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `i32`
+   |                                        ^^^ the size of `u8` is smaller than the size of `i32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -197,7 +197,7 @@ error[E0277]: `u8` cannot be safely transmuted into `f32`
   --> $DIR/numbers.rs:78:40
    |
 LL |     assert::is_transmutable::<   u8,   f32>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `f32`
+   |                                        ^^^ the size of `u8` is smaller than the size of `f32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -212,7 +212,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u32`
   --> $DIR/numbers.rs:79:40
    |
 LL |     assert::is_transmutable::<   u8,   u32>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `u32`
+   |                                        ^^^ the size of `u8` is smaller than the size of `u32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -227,7 +227,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:80:40
    |
 LL |     assert::is_transmutable::<   u8,   u64>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `u64`
+   |                                        ^^^ the size of `u8` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -242,7 +242,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:81:40
    |
 LL |     assert::is_transmutable::<   u8,   i64>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `i64`
+   |                                        ^^^ the size of `u8` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -257,7 +257,7 @@ error[E0277]: `u8` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:82:40
    |
 LL |     assert::is_transmutable::<   u8,   f64>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `f64`
+   |                                        ^^^ the size of `u8` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -272,7 +272,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:83:39
    |
 LL |     assert::is_transmutable::<   u8,  u128>();
-   |                                       ^^^^ The size of `u8` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `u8` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -287,7 +287,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:84:39
    |
 LL |     assert::is_transmutable::<   u8,  i128>();
-   |                                       ^^^^ The size of `u8` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `u8` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -302,7 +302,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i32`
   --> $DIR/numbers.rs:86:40
    |
 LL |     assert::is_transmutable::<  i16,   i32>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `i32`
+   |                                        ^^^ the size of `i16` is smaller than the size of `i32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -317,7 +317,7 @@ error[E0277]: `i16` cannot be safely transmuted into `f32`
   --> $DIR/numbers.rs:87:40
    |
 LL |     assert::is_transmutable::<  i16,   f32>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `f32`
+   |                                        ^^^ the size of `i16` is smaller than the size of `f32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -332,7 +332,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u32`
   --> $DIR/numbers.rs:88:40
    |
 LL |     assert::is_transmutable::<  i16,   u32>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `u32`
+   |                                        ^^^ the size of `i16` is smaller than the size of `u32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -347,7 +347,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:89:40
    |
 LL |     assert::is_transmutable::<  i16,   u64>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `u64`
+   |                                        ^^^ the size of `i16` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -362,7 +362,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:90:40
    |
 LL |     assert::is_transmutable::<  i16,   i64>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `i64`
+   |                                        ^^^ the size of `i16` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -377,7 +377,7 @@ error[E0277]: `i16` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:91:40
    |
 LL |     assert::is_transmutable::<  i16,   f64>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `f64`
+   |                                        ^^^ the size of `i16` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -392,7 +392,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:92:39
    |
 LL |     assert::is_transmutable::<  i16,  u128>();
-   |                                       ^^^^ The size of `i16` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `i16` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -407,7 +407,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:93:39
    |
 LL |     assert::is_transmutable::<  i16,  i128>();
-   |                                       ^^^^ The size of `i16` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `i16` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -422,7 +422,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i32`
   --> $DIR/numbers.rs:95:40
    |
 LL |     assert::is_transmutable::<  u16,   i32>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `i32`
+   |                                        ^^^ the size of `u16` is smaller than the size of `i32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -437,7 +437,7 @@ error[E0277]: `u16` cannot be safely transmuted into `f32`
   --> $DIR/numbers.rs:96:40
    |
 LL |     assert::is_transmutable::<  u16,   f32>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `f32`
+   |                                        ^^^ the size of `u16` is smaller than the size of `f32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -452,7 +452,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u32`
   --> $DIR/numbers.rs:97:40
    |
 LL |     assert::is_transmutable::<  u16,   u32>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `u32`
+   |                                        ^^^ the size of `u16` is smaller than the size of `u32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -467,7 +467,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:98:40
    |
 LL |     assert::is_transmutable::<  u16,   u64>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `u64`
+   |                                        ^^^ the size of `u16` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -482,7 +482,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:99:40
    |
 LL |     assert::is_transmutable::<  u16,   i64>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `i64`
+   |                                        ^^^ the size of `u16` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -497,7 +497,7 @@ error[E0277]: `u16` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:100:40
    |
 LL |     assert::is_transmutable::<  u16,   f64>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `f64`
+   |                                        ^^^ the size of `u16` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -512,7 +512,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:101:39
    |
 LL |     assert::is_transmutable::<  u16,  u128>();
-   |                                       ^^^^ The size of `u16` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `u16` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -527,7 +527,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:102:39
    |
 LL |     assert::is_transmutable::<  u16,  i128>();
-   |                                       ^^^^ The size of `u16` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `u16` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -542,7 +542,7 @@ error[E0277]: `i32` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:104:40
    |
 LL |     assert::is_transmutable::<  i32,   u64>();
-   |                                        ^^^ The size of `i32` is smaller than the size of `u64`
+   |                                        ^^^ the size of `i32` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -557,7 +557,7 @@ error[E0277]: `i32` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:105:40
    |
 LL |     assert::is_transmutable::<  i32,   i64>();
-   |                                        ^^^ The size of `i32` is smaller than the size of `i64`
+   |                                        ^^^ the size of `i32` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -572,7 +572,7 @@ error[E0277]: `i32` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:106:40
    |
 LL |     assert::is_transmutable::<  i32,   f64>();
-   |                                        ^^^ The size of `i32` is smaller than the size of `f64`
+   |                                        ^^^ the size of `i32` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -587,7 +587,7 @@ error[E0277]: `i32` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:107:39
    |
 LL |     assert::is_transmutable::<  i32,  u128>();
-   |                                       ^^^^ The size of `i32` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `i32` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -602,7 +602,7 @@ error[E0277]: `i32` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:108:39
    |
 LL |     assert::is_transmutable::<  i32,  i128>();
-   |                                       ^^^^ The size of `i32` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `i32` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -617,7 +617,7 @@ error[E0277]: `f32` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:110:40
    |
 LL |     assert::is_transmutable::<  f32,   u64>();
-   |                                        ^^^ The size of `f32` is smaller than the size of `u64`
+   |                                        ^^^ the size of `f32` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -632,7 +632,7 @@ error[E0277]: `f32` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:111:40
    |
 LL |     assert::is_transmutable::<  f32,   i64>();
-   |                                        ^^^ The size of `f32` is smaller than the size of `i64`
+   |                                        ^^^ the size of `f32` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -647,7 +647,7 @@ error[E0277]: `f32` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:112:40
    |
 LL |     assert::is_transmutable::<  f32,   f64>();
-   |                                        ^^^ The size of `f32` is smaller than the size of `f64`
+   |                                        ^^^ the size of `f32` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -662,7 +662,7 @@ error[E0277]: `f32` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:113:39
    |
 LL |     assert::is_transmutable::<  f32,  u128>();
-   |                                       ^^^^ The size of `f32` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `f32` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -677,7 +677,7 @@ error[E0277]: `f32` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:114:39
    |
 LL |     assert::is_transmutable::<  f32,  i128>();
-   |                                       ^^^^ The size of `f32` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `f32` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -692,7 +692,7 @@ error[E0277]: `u32` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:116:40
    |
 LL |     assert::is_transmutable::<  u32,   u64>();
-   |                                        ^^^ The size of `u32` is smaller than the size of `u64`
+   |                                        ^^^ the size of `u32` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -707,7 +707,7 @@ error[E0277]: `u32` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:117:40
    |
 LL |     assert::is_transmutable::<  u32,   i64>();
-   |                                        ^^^ The size of `u32` is smaller than the size of `i64`
+   |                                        ^^^ the size of `u32` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -722,7 +722,7 @@ error[E0277]: `u32` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:118:40
    |
 LL |     assert::is_transmutable::<  u32,   f64>();
-   |                                        ^^^ The size of `u32` is smaller than the size of `f64`
+   |                                        ^^^ the size of `u32` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -737,7 +737,7 @@ error[E0277]: `u32` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:119:39
    |
 LL |     assert::is_transmutable::<  u32,  u128>();
-   |                                       ^^^^ The size of `u32` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `u32` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -752,7 +752,7 @@ error[E0277]: `u32` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:120:39
    |
 LL |     assert::is_transmutable::<  u32,  i128>();
-   |                                       ^^^^ The size of `u32` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `u32` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -767,7 +767,7 @@ error[E0277]: `u64` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:122:39
    |
 LL |     assert::is_transmutable::<  u64,  u128>();
-   |                                       ^^^^ The size of `u64` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `u64` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -782,7 +782,7 @@ error[E0277]: `u64` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:123:39
    |
 LL |     assert::is_transmutable::<  u64,  i128>();
-   |                                       ^^^^ The size of `u64` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `u64` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -797,7 +797,7 @@ error[E0277]: `i64` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:125:39
    |
 LL |     assert::is_transmutable::<  i64,  u128>();
-   |                                       ^^^^ The size of `i64` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `i64` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -812,7 +812,7 @@ error[E0277]: `i64` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:126:39
    |
 LL |     assert::is_transmutable::<  i64,  i128>();
-   |                                       ^^^^ The size of `i64` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `i64` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -827,7 +827,7 @@ error[E0277]: `f64` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:128:39
    |
 LL |     assert::is_transmutable::<  f64,  u128>();
-   |                                       ^^^^ The size of `f64` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `f64` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -842,7 +842,7 @@ error[E0277]: `f64` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:129:39
    |
 LL |     assert::is_transmutable::<  f64,  i128>();
-   |                                       ^^^^ The size of `f64` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `f64` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
diff --git a/tests/ui/transmutability/primitives/numbers.next.stderr b/tests/ui/transmutability/primitives/numbers.next.stderr
index 7a80e444149..0a9b9d182f8 100644
--- a/tests/ui/transmutability/primitives/numbers.next.stderr
+++ b/tests/ui/transmutability/primitives/numbers.next.stderr
@@ -2,7 +2,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i16`
   --> $DIR/numbers.rs:64:40
    |
 LL |     assert::is_transmutable::<   i8,   i16>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `i16`
+   |                                        ^^^ the size of `i8` is smaller than the size of `i16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -17,7 +17,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u16`
   --> $DIR/numbers.rs:65:40
    |
 LL |     assert::is_transmutable::<   i8,   u16>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `u16`
+   |                                        ^^^ the size of `i8` is smaller than the size of `u16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -32,7 +32,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i32`
   --> $DIR/numbers.rs:66:40
    |
 LL |     assert::is_transmutable::<   i8,   i32>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `i32`
+   |                                        ^^^ the size of `i8` is smaller than the size of `i32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -47,7 +47,7 @@ error[E0277]: `i8` cannot be safely transmuted into `f32`
   --> $DIR/numbers.rs:67:40
    |
 LL |     assert::is_transmutable::<   i8,   f32>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `f32`
+   |                                        ^^^ the size of `i8` is smaller than the size of `f32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -62,7 +62,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u32`
   --> $DIR/numbers.rs:68:40
    |
 LL |     assert::is_transmutable::<   i8,   u32>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `u32`
+   |                                        ^^^ the size of `i8` is smaller than the size of `u32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -77,7 +77,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:69:40
    |
 LL |     assert::is_transmutable::<   i8,   u64>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `u64`
+   |                                        ^^^ the size of `i8` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -92,7 +92,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:70:40
    |
 LL |     assert::is_transmutable::<   i8,   i64>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `i64`
+   |                                        ^^^ the size of `i8` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -107,7 +107,7 @@ error[E0277]: `i8` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:71:40
    |
 LL |     assert::is_transmutable::<   i8,   f64>();
-   |                                        ^^^ The size of `i8` is smaller than the size of `f64`
+   |                                        ^^^ the size of `i8` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -122,7 +122,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:72:39
    |
 LL |     assert::is_transmutable::<   i8,  u128>();
-   |                                       ^^^^ The size of `i8` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `i8` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -137,7 +137,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:73:39
    |
 LL |     assert::is_transmutable::<   i8,  i128>();
-   |                                       ^^^^ The size of `i8` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `i8` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -152,7 +152,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i16`
   --> $DIR/numbers.rs:75:40
    |
 LL |     assert::is_transmutable::<   u8,   i16>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `i16`
+   |                                        ^^^ the size of `u8` is smaller than the size of `i16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -167,7 +167,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u16`
   --> $DIR/numbers.rs:76:40
    |
 LL |     assert::is_transmutable::<   u8,   u16>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `u16`
+   |                                        ^^^ the size of `u8` is smaller than the size of `u16`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -182,7 +182,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i32`
   --> $DIR/numbers.rs:77:40
    |
 LL |     assert::is_transmutable::<   u8,   i32>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `i32`
+   |                                        ^^^ the size of `u8` is smaller than the size of `i32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -197,7 +197,7 @@ error[E0277]: `u8` cannot be safely transmuted into `f32`
   --> $DIR/numbers.rs:78:40
    |
 LL |     assert::is_transmutable::<   u8,   f32>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `f32`
+   |                                        ^^^ the size of `u8` is smaller than the size of `f32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -212,7 +212,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u32`
   --> $DIR/numbers.rs:79:40
    |
 LL |     assert::is_transmutable::<   u8,   u32>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `u32`
+   |                                        ^^^ the size of `u8` is smaller than the size of `u32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -227,7 +227,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:80:40
    |
 LL |     assert::is_transmutable::<   u8,   u64>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `u64`
+   |                                        ^^^ the size of `u8` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -242,7 +242,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:81:40
    |
 LL |     assert::is_transmutable::<   u8,   i64>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `i64`
+   |                                        ^^^ the size of `u8` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -257,7 +257,7 @@ error[E0277]: `u8` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:82:40
    |
 LL |     assert::is_transmutable::<   u8,   f64>();
-   |                                        ^^^ The size of `u8` is smaller than the size of `f64`
+   |                                        ^^^ the size of `u8` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -272,7 +272,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:83:39
    |
 LL |     assert::is_transmutable::<   u8,  u128>();
-   |                                       ^^^^ The size of `u8` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `u8` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -287,7 +287,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:84:39
    |
 LL |     assert::is_transmutable::<   u8,  i128>();
-   |                                       ^^^^ The size of `u8` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `u8` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -302,7 +302,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i32`
   --> $DIR/numbers.rs:86:40
    |
 LL |     assert::is_transmutable::<  i16,   i32>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `i32`
+   |                                        ^^^ the size of `i16` is smaller than the size of `i32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -317,7 +317,7 @@ error[E0277]: `i16` cannot be safely transmuted into `f32`
   --> $DIR/numbers.rs:87:40
    |
 LL |     assert::is_transmutable::<  i16,   f32>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `f32`
+   |                                        ^^^ the size of `i16` is smaller than the size of `f32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -332,7 +332,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u32`
   --> $DIR/numbers.rs:88:40
    |
 LL |     assert::is_transmutable::<  i16,   u32>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `u32`
+   |                                        ^^^ the size of `i16` is smaller than the size of `u32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -347,7 +347,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:89:40
    |
 LL |     assert::is_transmutable::<  i16,   u64>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `u64`
+   |                                        ^^^ the size of `i16` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -362,7 +362,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:90:40
    |
 LL |     assert::is_transmutable::<  i16,   i64>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `i64`
+   |                                        ^^^ the size of `i16` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -377,7 +377,7 @@ error[E0277]: `i16` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:91:40
    |
 LL |     assert::is_transmutable::<  i16,   f64>();
-   |                                        ^^^ The size of `i16` is smaller than the size of `f64`
+   |                                        ^^^ the size of `i16` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -392,7 +392,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:92:39
    |
 LL |     assert::is_transmutable::<  i16,  u128>();
-   |                                       ^^^^ The size of `i16` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `i16` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -407,7 +407,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:93:39
    |
 LL |     assert::is_transmutable::<  i16,  i128>();
-   |                                       ^^^^ The size of `i16` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `i16` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -422,7 +422,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i32`
   --> $DIR/numbers.rs:95:40
    |
 LL |     assert::is_transmutable::<  u16,   i32>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `i32`
+   |                                        ^^^ the size of `u16` is smaller than the size of `i32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -437,7 +437,7 @@ error[E0277]: `u16` cannot be safely transmuted into `f32`
   --> $DIR/numbers.rs:96:40
    |
 LL |     assert::is_transmutable::<  u16,   f32>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `f32`
+   |                                        ^^^ the size of `u16` is smaller than the size of `f32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -452,7 +452,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u32`
   --> $DIR/numbers.rs:97:40
    |
 LL |     assert::is_transmutable::<  u16,   u32>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `u32`
+   |                                        ^^^ the size of `u16` is smaller than the size of `u32`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -467,7 +467,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:98:40
    |
 LL |     assert::is_transmutable::<  u16,   u64>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `u64`
+   |                                        ^^^ the size of `u16` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -482,7 +482,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:99:40
    |
 LL |     assert::is_transmutable::<  u16,   i64>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `i64`
+   |                                        ^^^ the size of `u16` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -497,7 +497,7 @@ error[E0277]: `u16` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:100:40
    |
 LL |     assert::is_transmutable::<  u16,   f64>();
-   |                                        ^^^ The size of `u16` is smaller than the size of `f64`
+   |                                        ^^^ the size of `u16` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -512,7 +512,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:101:39
    |
 LL |     assert::is_transmutable::<  u16,  u128>();
-   |                                       ^^^^ The size of `u16` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `u16` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -527,7 +527,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:102:39
    |
 LL |     assert::is_transmutable::<  u16,  i128>();
-   |                                       ^^^^ The size of `u16` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `u16` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -542,7 +542,7 @@ error[E0277]: `i32` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:104:40
    |
 LL |     assert::is_transmutable::<  i32,   u64>();
-   |                                        ^^^ The size of `i32` is smaller than the size of `u64`
+   |                                        ^^^ the size of `i32` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -557,7 +557,7 @@ error[E0277]: `i32` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:105:40
    |
 LL |     assert::is_transmutable::<  i32,   i64>();
-   |                                        ^^^ The size of `i32` is smaller than the size of `i64`
+   |                                        ^^^ the size of `i32` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -572,7 +572,7 @@ error[E0277]: `i32` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:106:40
    |
 LL |     assert::is_transmutable::<  i32,   f64>();
-   |                                        ^^^ The size of `i32` is smaller than the size of `f64`
+   |                                        ^^^ the size of `i32` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -587,7 +587,7 @@ error[E0277]: `i32` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:107:39
    |
 LL |     assert::is_transmutable::<  i32,  u128>();
-   |                                       ^^^^ The size of `i32` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `i32` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -602,7 +602,7 @@ error[E0277]: `i32` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:108:39
    |
 LL |     assert::is_transmutable::<  i32,  i128>();
-   |                                       ^^^^ The size of `i32` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `i32` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -617,7 +617,7 @@ error[E0277]: `f32` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:110:40
    |
 LL |     assert::is_transmutable::<  f32,   u64>();
-   |                                        ^^^ The size of `f32` is smaller than the size of `u64`
+   |                                        ^^^ the size of `f32` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -632,7 +632,7 @@ error[E0277]: `f32` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:111:40
    |
 LL |     assert::is_transmutable::<  f32,   i64>();
-   |                                        ^^^ The size of `f32` is smaller than the size of `i64`
+   |                                        ^^^ the size of `f32` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -647,7 +647,7 @@ error[E0277]: `f32` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:112:40
    |
 LL |     assert::is_transmutable::<  f32,   f64>();
-   |                                        ^^^ The size of `f32` is smaller than the size of `f64`
+   |                                        ^^^ the size of `f32` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -662,7 +662,7 @@ error[E0277]: `f32` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:113:39
    |
 LL |     assert::is_transmutable::<  f32,  u128>();
-   |                                       ^^^^ The size of `f32` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `f32` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -677,7 +677,7 @@ error[E0277]: `f32` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:114:39
    |
 LL |     assert::is_transmutable::<  f32,  i128>();
-   |                                       ^^^^ The size of `f32` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `f32` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -692,7 +692,7 @@ error[E0277]: `u32` cannot be safely transmuted into `u64`
   --> $DIR/numbers.rs:116:40
    |
 LL |     assert::is_transmutable::<  u32,   u64>();
-   |                                        ^^^ The size of `u32` is smaller than the size of `u64`
+   |                                        ^^^ the size of `u32` is smaller than the size of `u64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -707,7 +707,7 @@ error[E0277]: `u32` cannot be safely transmuted into `i64`
   --> $DIR/numbers.rs:117:40
    |
 LL |     assert::is_transmutable::<  u32,   i64>();
-   |                                        ^^^ The size of `u32` is smaller than the size of `i64`
+   |                                        ^^^ the size of `u32` is smaller than the size of `i64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -722,7 +722,7 @@ error[E0277]: `u32` cannot be safely transmuted into `f64`
   --> $DIR/numbers.rs:118:40
    |
 LL |     assert::is_transmutable::<  u32,   f64>();
-   |                                        ^^^ The size of `u32` is smaller than the size of `f64`
+   |                                        ^^^ the size of `u32` is smaller than the size of `f64`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -737,7 +737,7 @@ error[E0277]: `u32` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:119:39
    |
 LL |     assert::is_transmutable::<  u32,  u128>();
-   |                                       ^^^^ The size of `u32` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `u32` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -752,7 +752,7 @@ error[E0277]: `u32` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:120:39
    |
 LL |     assert::is_transmutable::<  u32,  i128>();
-   |                                       ^^^^ The size of `u32` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `u32` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -767,7 +767,7 @@ error[E0277]: `u64` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:122:39
    |
 LL |     assert::is_transmutable::<  u64,  u128>();
-   |                                       ^^^^ The size of `u64` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `u64` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -782,7 +782,7 @@ error[E0277]: `u64` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:123:39
    |
 LL |     assert::is_transmutable::<  u64,  i128>();
-   |                                       ^^^^ The size of `u64` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `u64` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -797,7 +797,7 @@ error[E0277]: `i64` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:125:39
    |
 LL |     assert::is_transmutable::<  i64,  u128>();
-   |                                       ^^^^ The size of `i64` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `i64` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -812,7 +812,7 @@ error[E0277]: `i64` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:126:39
    |
 LL |     assert::is_transmutable::<  i64,  i128>();
-   |                                       ^^^^ The size of `i64` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `i64` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -827,7 +827,7 @@ error[E0277]: `f64` cannot be safely transmuted into `u128`
   --> $DIR/numbers.rs:128:39
    |
 LL |     assert::is_transmutable::<  f64,  u128>();
-   |                                       ^^^^ The size of `f64` is smaller than the size of `u128`
+   |                                       ^^^^ the size of `f64` is smaller than the size of `u128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
@@ -842,7 +842,7 @@ error[E0277]: `f64` cannot be safely transmuted into `i128`
   --> $DIR/numbers.rs:129:39
    |
 LL |     assert::is_transmutable::<  f64,  i128>();
-   |                                       ^^^^ The size of `f64` is smaller than the size of `i128`
+   |                                       ^^^^ the size of `f64` is smaller than the size of `i128`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/numbers.rs:14:14
diff --git a/tests/ui/transmutability/primitives/unit.current.stderr b/tests/ui/transmutability/primitives/unit.current.stderr
index b2831dbf842..52b708d680e 100644
--- a/tests/ui/transmutability/primitives/unit.current.stderr
+++ b/tests/ui/transmutability/primitives/unit.current.stderr
@@ -2,7 +2,7 @@ error[E0277]: `()` cannot be safely transmuted into `u8`
   --> $DIR/unit.rs:31:35
    |
 LL |     assert::is_transmutable::<(), u8>();
-   |                                   ^^ The size of `()` is smaller than the size of `u8`
+   |                                   ^^ the size of `()` is smaller than the size of `u8`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/unit.rs:16:14
diff --git a/tests/ui/transmutability/primitives/unit.next.stderr b/tests/ui/transmutability/primitives/unit.next.stderr
index b2831dbf842..52b708d680e 100644
--- a/tests/ui/transmutability/primitives/unit.next.stderr
+++ b/tests/ui/transmutability/primitives/unit.next.stderr
@@ -2,7 +2,7 @@ error[E0277]: `()` cannot be safely transmuted into `u8`
   --> $DIR/unit.rs:31:35
    |
 LL |     assert::is_transmutable::<(), u8>();
-   |                                   ^^ The size of `()` is smaller than the size of `u8`
+   |                                   ^^ the size of `()` is smaller than the size of `u8`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/unit.rs:16:14
diff --git a/tests/ui/transmutability/references/recursive-wrapper-types-bit-incompatible.stderr b/tests/ui/transmutability/references/recursive-wrapper-types-bit-incompatible.stderr
index 305fca30939..2b7cab1660d 100644
--- a/tests/ui/transmutability/references/recursive-wrapper-types-bit-incompatible.stderr
+++ b/tests/ui/transmutability/references/recursive-wrapper-types-bit-incompatible.stderr
@@ -2,7 +2,7 @@ error[E0277]: `B` cannot be safely transmuted into `A`
   --> $DIR/recursive-wrapper-types-bit-incompatible.rs:23:49
    |
 LL |     assert::is_maybe_transmutable::<&'static B, &'static A>();
-   |                                                 ^^^^^^^^^^ At least one value of `B` isn't a bit-valid value of `A`
+   |                                                 ^^^^^^^^^^ at least one value of `B` isn't a bit-valid value of `A`
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/recursive-wrapper-types-bit-incompatible.rs:9:14
diff --git a/tests/ui/transmutability/references/reject_extension.rs b/tests/ui/transmutability/references/reject_extension.rs
new file mode 100644
index 00000000000..161da5772e8
--- /dev/null
+++ b/tests/ui/transmutability/references/reject_extension.rs
@@ -0,0 +1,49 @@
+//@ check-fail
+
+//! Reject extensions behind references.
+
+#![crate_type = "lib"]
+#![feature(transmutability)]
+
+mod assert {
+    use std::mem::{Assume, BikeshedIntrinsicFrom};
+
+    pub fn is_transmutable<Src, Dst>()
+    where
+        Dst: BikeshedIntrinsicFrom<
+            Src,
+            {
+                Assume {
+                    alignment: true,
+                    lifetimes: true,
+                    safety: true,
+                    validity: true,
+                }
+            },
+        >,
+    {
+    }
+}
+
+#[repr(C, packed)]
+struct Packed<T>(T);
+
+fn reject_extension() {
+    #[repr(C, align(2))]
+    struct Two(u8);
+
+    #[repr(C, align(4))]
+    struct Four(u8);
+
+    // These two types differ in the number of trailing padding bytes they have.
+    type Src = Packed<Two>;
+    type Dst = Packed<Four>;
+
+    const _: () = {
+        use std::mem::size_of;
+        assert!(size_of::<Src>() == 2);
+        assert!(size_of::<Dst>() == 4);
+    };
+
+    assert::is_transmutable::<&Src, &Dst>(); //~ ERROR cannot be safely transmuted
+}
diff --git a/tests/ui/transmutability/references/reject_extension.stderr b/tests/ui/transmutability/references/reject_extension.stderr
new file mode 100644
index 00000000000..88dd0313e3c
--- /dev/null
+++ b/tests/ui/transmutability/references/reject_extension.stderr
@@ -0,0 +1,25 @@
+error[E0277]: `&Packed<Two>` cannot be safely transmuted into `&Packed<Four>`
+  --> $DIR/reject_extension.rs:48:37
+   |
+LL |     assert::is_transmutable::<&Src, &Dst>();
+   |                                     ^^^^ the referent size of `&Packed<Two>` (2 bytes) is smaller than that of `&Packed<Four>` (4 bytes)
+   |
+note: required by a bound in `is_transmutable`
+  --> $DIR/reject_extension.rs:13:14
+   |
+LL |       pub fn is_transmutable<Src, Dst>()
+   |              --------------- required by a bound in this function
+LL |       where
+LL |           Dst: BikeshedIntrinsicFrom<
+   |  ______________^
+LL | |             Src,
+LL | |             {
+LL | |                 Assume {
+...  |
+LL | |             },
+LL | |         >,
+   | |_________^ required by this bound in `is_transmutable`
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0277`.
diff --git a/tests/ui/transmutability/references/unit-to-u8.stderr b/tests/ui/transmutability/references/unit-to-u8.stderr
index e2eb50442ca..5d73dfdc8eb 100644
--- a/tests/ui/transmutability/references/unit-to-u8.stderr
+++ b/tests/ui/transmutability/references/unit-to-u8.stderr
@@ -1,8 +1,8 @@
-error[E0277]: `Unit` cannot be safely transmuted into `u8`
+error[E0277]: `&Unit` cannot be safely transmuted into `&u8`
   --> $DIR/unit-to-u8.rs:22:52
    |
 LL |     assert::is_maybe_transmutable::<&'static Unit, &'static u8>();
-   |                                                    ^^^^^^^^^^^ The size of `Unit` is smaller than the size of `u8`
+   |                                                    ^^^^^^^^^^^ the referent size of `&Unit` (0 bytes) is smaller than that of `&u8` (1 bytes)
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/unit-to-u8.rs:9:14
diff --git a/tests/ui/transmutability/region-infer.stderr b/tests/ui/transmutability/region-infer.stderr
index 5497af2429e..03c46823838 100644
--- a/tests/ui/transmutability/region-infer.stderr
+++ b/tests/ui/transmutability/region-infer.stderr
@@ -2,7 +2,7 @@ error[E0277]: `()` cannot be safely transmuted into `W<'_>`
   --> $DIR/region-infer.rs:18:5
    |
 LL |     test();
-   |     ^^^^^^ The size of `()` is smaller than the size of `W<'_>`
+   |     ^^^^^^ the size of `()` is smaller than the size of `W<'_>`
    |
 note: required by a bound in `test`
   --> $DIR/region-infer.rs:10:12
diff --git a/tests/ui/transmutability/structs/repr/should_require_well_defined_layout.stderr b/tests/ui/transmutability/structs/repr/should_require_well_defined_layout.stderr
index 924422de538..77788f72c21 100644
--- a/tests/ui/transmutability/structs/repr/should_require_well_defined_layout.stderr
+++ b/tests/ui/transmutability/structs/repr/should_require_well_defined_layout.stderr
@@ -2,7 +2,7 @@ error[E0277]: `should_reject_repr_rust::unit::repr_rust` cannot be safely transm
   --> $DIR/should_require_well_defined_layout.rs:27:52
    |
 LL |         assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                    ^^ `should_reject_repr_rust::unit::repr_rust` does not have a well-specified layout
+   |                                                    ^^ analyzing the transmutability of `should_reject_repr_rust::unit::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -24,7 +24,7 @@ error[E0277]: `u128` cannot be safely transmuted into `should_reject_repr_rust::
   --> $DIR/should_require_well_defined_layout.rs:28:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                               ^^^^^^^^^ `should_reject_repr_rust::unit::repr_rust` does not have a well-specified layout
+   |                                               ^^^^^^^^^ analyzing the transmutability of `should_reject_repr_rust::unit::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -46,7 +46,7 @@ error[E0277]: `should_reject_repr_rust::tuple::repr_rust` cannot be safely trans
   --> $DIR/should_require_well_defined_layout.rs:33:52
    |
 LL |         assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                    ^^ `should_reject_repr_rust::tuple::repr_rust` does not have a well-specified layout
+   |                                                    ^^ analyzing the transmutability of `should_reject_repr_rust::tuple::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -68,7 +68,7 @@ error[E0277]: `u128` cannot be safely transmuted into `should_reject_repr_rust::
   --> $DIR/should_require_well_defined_layout.rs:34:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                               ^^^^^^^^^ `should_reject_repr_rust::tuple::repr_rust` does not have a well-specified layout
+   |                                               ^^^^^^^^^ analyzing the transmutability of `should_reject_repr_rust::tuple::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -90,7 +90,7 @@ error[E0277]: `should_reject_repr_rust::braces::repr_rust` cannot be safely tran
   --> $DIR/should_require_well_defined_layout.rs:39:52
    |
 LL |         assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                    ^^ `should_reject_repr_rust::braces::repr_rust` does not have a well-specified layout
+   |                                                    ^^ analyzing the transmutability of `should_reject_repr_rust::braces::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -112,7 +112,7 @@ error[E0277]: `u128` cannot be safely transmuted into `should_reject_repr_rust::
   --> $DIR/should_require_well_defined_layout.rs:40:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                               ^^^^^^^^^ `should_reject_repr_rust::braces::repr_rust` does not have a well-specified layout
+   |                                               ^^^^^^^^^ analyzing the transmutability of `should_reject_repr_rust::braces::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -134,7 +134,7 @@ error[E0277]: `aligned::repr_rust` cannot be safely transmuted into `()`
   --> $DIR/should_require_well_defined_layout.rs:45:52
    |
 LL |         assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                    ^^ `aligned::repr_rust` does not have a well-specified layout
+   |                                                    ^^ analyzing the transmutability of `aligned::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -156,7 +156,7 @@ error[E0277]: `u128` cannot be safely transmuted into `aligned::repr_rust`
   --> $DIR/should_require_well_defined_layout.rs:46:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                               ^^^^^^^^^ `aligned::repr_rust` does not have a well-specified layout
+   |                                               ^^^^^^^^^ analyzing the transmutability of `aligned::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -178,7 +178,7 @@ error[E0277]: `packed::repr_rust` cannot be safely transmuted into `()`
   --> $DIR/should_require_well_defined_layout.rs:51:52
    |
 LL |         assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                    ^^ `packed::repr_rust` does not have a well-specified layout
+   |                                                    ^^ analyzing the transmutability of `packed::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -200,7 +200,7 @@ error[E0277]: `u128` cannot be safely transmuted into `packed::repr_rust`
   --> $DIR/should_require_well_defined_layout.rs:52:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                               ^^^^^^^^^ `packed::repr_rust` does not have a well-specified layout
+   |                                               ^^^^^^^^^ analyzing the transmutability of `packed::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -222,7 +222,7 @@ error[E0277]: `nested::repr_c` cannot be safely transmuted into `()`
   --> $DIR/should_require_well_defined_layout.rs:58:49
    |
 LL |         assert::is_maybe_transmutable::<repr_c, ()>();
-   |                                                 ^^ `nested::repr_c` does not have a well-specified layout
+   |                                                 ^^ analyzing the transmutability of `nested::repr_c` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -244,7 +244,7 @@ error[E0277]: `u128` cannot be safely transmuted into `nested::repr_c`
   --> $DIR/should_require_well_defined_layout.rs:59:47
    |
 LL |         assert::is_maybe_transmutable::<u128, repr_c>();
-   |                                               ^^^^^^ `nested::repr_c` does not have a well-specified layout
+   |                                               ^^^^^^ analyzing the transmutability of `nested::repr_c` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
diff --git a/tests/ui/transmutability/transmute-padding-ice.stderr b/tests/ui/transmutability/transmute-padding-ice.stderr
index c48a5cd80ce..4c121d463c6 100644
--- a/tests/ui/transmutability/transmute-padding-ice.stderr
+++ b/tests/ui/transmutability/transmute-padding-ice.stderr
@@ -2,7 +2,7 @@ error[E0277]: `B` cannot be safely transmuted into `A`
   --> $DIR/transmute-padding-ice.rs:25:40
    |
 LL |     assert::is_maybe_transmutable::<B, A>();
-   |                                        ^ The size of `B` is smaller than the size of `A`
+   |                                        ^ the size of `B` is smaller than the size of `A`
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/transmute-padding-ice.rs:10:14
diff --git a/tests/ui/transmutability/unions/repr/should_require_well_defined_layout.stderr b/tests/ui/transmutability/unions/repr/should_require_well_defined_layout.stderr
index ee0e8a66434..bec07f13103 100644
--- a/tests/ui/transmutability/unions/repr/should_require_well_defined_layout.stderr
+++ b/tests/ui/transmutability/unions/repr/should_require_well_defined_layout.stderr
@@ -2,7 +2,7 @@ error[E0277]: `should_reject_repr_rust::repr_rust` cannot be safely transmuted i
   --> $DIR/should_require_well_defined_layout.rs:29:48
    |
 LL |     assert::is_maybe_transmutable::<repr_rust, ()>();
-   |                                                ^^ `should_reject_repr_rust::repr_rust` does not have a well-specified layout
+   |                                                ^^ analyzing the transmutability of `should_reject_repr_rust::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
@@ -24,7 +24,7 @@ error[E0277]: `u128` cannot be safely transmuted into `should_reject_repr_rust::
   --> $DIR/should_require_well_defined_layout.rs:30:43
    |
 LL |     assert::is_maybe_transmutable::<u128, repr_rust>();
-   |                                           ^^^^^^^^^ `should_reject_repr_rust::repr_rust` does not have a well-specified layout
+   |                                           ^^^^^^^^^ analyzing the transmutability of `should_reject_repr_rust::repr_rust` is not yet supported.
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_require_well_defined_layout.rs:12:14
diff --git a/tests/ui/transmutability/unions/should_pad_variants.stderr b/tests/ui/transmutability/unions/should_pad_variants.stderr
index 13b4c8053ad..da4294bdbce 100644
--- a/tests/ui/transmutability/unions/should_pad_variants.stderr
+++ b/tests/ui/transmutability/unions/should_pad_variants.stderr
@@ -2,7 +2,7 @@ error[E0277]: `Src` cannot be safely transmuted into `Dst`
   --> $DIR/should_pad_variants.rs:43:36
    |
 LL |     assert::is_transmutable::<Src, Dst>();
-   |                                    ^^^ The size of `Src` is smaller than the size of `Dst`
+   |                                    ^^^ the size of `Src` is smaller than the size of `Dst`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/should_pad_variants.rs:13:14
diff --git a/tests/ui/transmutability/unions/should_reject_contraction.stderr b/tests/ui/transmutability/unions/should_reject_contraction.stderr
index a3e387a0f84..20eaa3a6b09 100644
--- a/tests/ui/transmutability/unions/should_reject_contraction.stderr
+++ b/tests/ui/transmutability/unions/should_reject_contraction.stderr
@@ -2,7 +2,7 @@ error[E0277]: `Superset` cannot be safely transmuted into `Subset`
   --> $DIR/should_reject_contraction.rs:34:41
    |
 LL |     assert::is_transmutable::<Superset, Subset>();
-   |                                         ^^^^^^ At least one value of `Superset` isn't a bit-valid value of `Subset`
+   |                                         ^^^^^^ at least one value of `Superset` isn't a bit-valid value of `Subset`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/should_reject_contraction.rs:12:14
diff --git a/tests/ui/transmutability/unions/should_reject_disjoint.stderr b/tests/ui/transmutability/unions/should_reject_disjoint.stderr
index 447ab6d9de7..ea47797c970 100644
--- a/tests/ui/transmutability/unions/should_reject_disjoint.stderr
+++ b/tests/ui/transmutability/unions/should_reject_disjoint.stderr
@@ -2,7 +2,7 @@ error[E0277]: `A` cannot be safely transmuted into `B`
   --> $DIR/should_reject_disjoint.rs:32:40
    |
 LL |     assert::is_maybe_transmutable::<A, B>();
-   |                                        ^ At least one value of `A` isn't a bit-valid value of `B`
+   |                                        ^ at least one value of `A` isn't a bit-valid value of `B`
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_reject_disjoint.rs:12:14
@@ -17,7 +17,7 @@ error[E0277]: `B` cannot be safely transmuted into `A`
   --> $DIR/should_reject_disjoint.rs:33:40
    |
 LL |     assert::is_maybe_transmutable::<B, A>();
-   |                                        ^ At least one value of `B` isn't a bit-valid value of `A`
+   |                                        ^ at least one value of `B` isn't a bit-valid value of `A`
    |
 note: required by a bound in `is_maybe_transmutable`
   --> $DIR/should_reject_disjoint.rs:12:14
diff --git a/tests/ui/transmutability/unions/should_reject_intersecting.stderr b/tests/ui/transmutability/unions/should_reject_intersecting.stderr
index f0763bc8be7..79dec659d9d 100644
--- a/tests/ui/transmutability/unions/should_reject_intersecting.stderr
+++ b/tests/ui/transmutability/unions/should_reject_intersecting.stderr
@@ -2,7 +2,7 @@ error[E0277]: `A` cannot be safely transmuted into `B`
   --> $DIR/should_reject_intersecting.rs:35:34
    |
 LL |     assert::is_transmutable::<A, B>();
-   |                                  ^ At least one value of `A` isn't a bit-valid value of `B`
+   |                                  ^ at least one value of `A` isn't a bit-valid value of `B`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/should_reject_intersecting.rs:13:14
@@ -17,7 +17,7 @@ error[E0277]: `B` cannot be safely transmuted into `A`
   --> $DIR/should_reject_intersecting.rs:36:34
    |
 LL |     assert::is_transmutable::<B, A>();
-   |                                  ^ At least one value of `B` isn't a bit-valid value of `A`
+   |                                  ^ at least one value of `B` isn't a bit-valid value of `A`
    |
 note: required by a bound in `is_transmutable`
   --> $DIR/should_reject_intersecting.rs:13:14
diff --git a/tests/ui/type-alias-impl-trait/in-where-clause.rs b/tests/ui/type-alias-impl-trait/in-where-clause.rs
index 0ad6e7a6f60..7c0de39c7c9 100644
--- a/tests/ui/type-alias-impl-trait/in-where-clause.rs
+++ b/tests/ui/type-alias-impl-trait/in-where-clause.rs
@@ -1,5 +1,5 @@
 //! We evaluate `1 + 2` with `Reveal::All` during typeck, causing
-//! us to to get the concrete type of `Bar` while computing it.
+//! us to get the concrete type of `Bar` while computing it.
 //! This again requires type checking `foo`.
 #![feature(type_alias_impl_trait)]
 type Bar = impl Sized;
diff --git a/tests/ui/typeck/ice-self-mismatch-const-generics.rs b/tests/ui/typeck/ice-self-mismatch-const-generics.rs
new file mode 100644
index 00000000000..43f435ba4cf
--- /dev/null
+++ b/tests/ui/typeck/ice-self-mismatch-const-generics.rs
@@ -0,0 +1,25 @@
+// Checks that the following does not ICE when constructing type mismatch diagnostic involving
+// `Self` and const generics.
+// Issue: <https://github.com/rust-lang/rust/issues/122467>
+
+pub struct GenericStruct<const N: usize, T> {
+    thing: T,
+}
+
+impl<T> GenericStruct<0, T> {
+    pub fn new(thing: T) -> GenericStruct<1, T> {
+        Self { thing }
+        //~^ ERROR mismatched types
+    }
+}
+
+pub struct GenericStruct2<const M: usize, T>(T);
+
+impl<T> GenericStruct2<0, T> {
+    pub fn new(thing: T) -> GenericStruct2<1, T> {
+        Self { 0: thing }
+        //~^ ERROR mismatched types
+    }
+}
+
+fn main() {}
diff --git a/tests/ui/typeck/ice-self-mismatch-const-generics.stderr b/tests/ui/typeck/ice-self-mismatch-const-generics.stderr
new file mode 100644
index 00000000000..c502ea4565f
--- /dev/null
+++ b/tests/ui/typeck/ice-self-mismatch-const-generics.stderr
@@ -0,0 +1,37 @@
+error[E0308]: mismatched types
+  --> $DIR/ice-self-mismatch-const-generics.rs:11:9
+   |
+LL | impl<T> GenericStruct<0, T> {
+   |         ------------------- this is the type of the `Self` literal
+LL |     pub fn new(thing: T) -> GenericStruct<1, T> {
+   |                             ------------------- expected `GenericStruct<1, T>` because of return type
+LL |         Self { thing }
+   |         ^^^^^^^^^^^^^^ expected `1`, found `0`
+   |
+   = note: expected struct `GenericStruct<_, 1>`
+              found struct `GenericStruct<_, 0>`
+help: use the type name directly
+   |
+LL |         GenericStruct::<1, T> { thing }
+   |         ~~~~~~~~~~~~~~~~~~~~~
+
+error[E0308]: mismatched types
+  --> $DIR/ice-self-mismatch-const-generics.rs:20:9
+   |
+LL | impl<T> GenericStruct2<0, T> {
+   |         -------------------- this is the type of the `Self` literal
+LL |     pub fn new(thing: T) -> GenericStruct2<1, T> {
+   |                             -------------------- expected `GenericStruct2<1, T>` because of return type
+LL |         Self { 0: thing }
+   |         ^^^^^^^^^^^^^^^^^ expected `1`, found `0`
+   |
+   = note: expected struct `GenericStruct2<_, 1>`
+              found struct `GenericStruct2<_, 0>`
+help: use the type name directly
+   |
+LL |         GenericStruct2::<1, T> { 0: thing }
+   |         ~~~~~~~~~~~~~~~~~~~~~~
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/typeck/mismatched-map-under-self.stderr b/tests/ui/typeck/mismatched-map-under-self.stderr
index 13678b4b827..322bf349f92 100644
--- a/tests/ui/typeck/mismatched-map-under-self.stderr
+++ b/tests/ui/typeck/mismatched-map-under-self.stderr
@@ -27,7 +27,7 @@ LL |         self.map(Insertable::values).unwrap_or_default()
    |              required by a bound introduced by this call
    |
    = note: expected function signature `fn(T) -> _`
-              found function signature `for<'a> fn(&'a _) -> _`
+              found function signature `fn(&_) -> _`
 note: required by a bound in `Option::<T>::map`
   --> $SRC_DIR/core/src/option.rs:LL:COL
 help: consider wrapping the function in a closure
diff --git a/tests/ui/unop-move-semantics.stderr b/tests/ui/unop-move-semantics.stderr
index b6de7976ac9..187dd66b2fe 100644
--- a/tests/ui/unop-move-semantics.stderr
+++ b/tests/ui/unop-move-semantics.stderr
@@ -9,7 +9,7 @@ LL |
 LL |     x.clone();
    |     ^ value borrowed here after move
    |
-note: calling this operator moves the left-hand side
+note: calling this operator moves the value
   --> $SRC_DIR/core/src/ops/bit.rs:LL:COL
 help: consider cloning the value if the performance cost is acceptable
    |
@@ -57,7 +57,7 @@ LL |     !*m;
    |     |move occurs because `*m` has type `T`, which does not implement the `Copy` trait
    |     `*m` moved due to usage in operator
    |
-note: calling this operator moves the left-hand side
+note: calling this operator moves the value
   --> $SRC_DIR/core/src/ops/bit.rs:LL:COL
 
 error[E0507]: cannot move out of `*n` which is behind a shared reference