about summary refs log tree commit diff
path: root/tests
diff options
context:
space:
mode:
Diffstat (limited to 'tests')
-rw-r--r--tests/codegen/issues/issue-115385-llvm-jump-threading.rs46
-rw-r--r--tests/codegen/sanitizer/kcfi-add-kcfi-flag.rs13
-rw-r--r--tests/coverage-map/status-quo/closure.cov-map14
-rw-r--r--tests/coverage-map/status-quo/closure_bug.cov-map148
-rw-r--r--tests/coverage-map/status-quo/closure_bug.rs44
-rw-r--r--tests/coverage-map/status-quo/closure_macro.rs2
-rw-r--r--tests/coverage-map/status-quo/closure_macro_async.rs14
-rw-r--r--tests/coverage-map/status-quo/generator.cov-map4
-rw-r--r--tests/coverage-map/status-quo/no_cov_crate.rs14
-rw-r--r--tests/debuginfo/pretty-std-collections.rs1
-rw-r--r--tests/mir-opt/const_prop/checked_add.main.ConstProp.panic-abort.diff4
-rw-r--r--tests/mir-opt/const_prop/checked_add.main.ConstProp.panic-unwind.diff4
-rw-r--r--tests/mir-opt/const_prop/indirect.main.ConstProp.panic-abort.diff4
-rw-r--r--tests/mir-opt/const_prop/indirect.main.ConstProp.panic-unwind.diff4
-rw-r--r--tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.panic-abort.diff4
-rw-r--r--tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.panic-unwind.diff4
-rw-r--r--tests/mir-opt/const_prop/issue_66971.main.ConstProp.panic-abort.diff8
-rw-r--r--tests/mir-opt/const_prop/issue_66971.main.ConstProp.panic-unwind.diff8
-rw-r--r--tests/mir-opt/const_prop/issue_67019.main.ConstProp.panic-abort.diff12
-rw-r--r--tests/mir-opt/const_prop/issue_67019.main.ConstProp.panic-unwind.diff12
-rw-r--r--tests/mir-opt/const_prop/mutable_variable_aggregate.main.ConstProp.diff8
-rw-r--r--tests/mir-opt/const_prop/mutable_variable_unprop_assign.main.ConstProp.panic-abort.diff4
-rw-r--r--tests/mir-opt/const_prop/mutable_variable_unprop_assign.main.ConstProp.panic-unwind.diff4
-rw-r--r--tests/mir-opt/const_prop/return_place.add.ConstProp.panic-abort.diff4
-rw-r--r--tests/mir-opt/const_prop/return_place.add.ConstProp.panic-unwind.diff4
-rw-r--r--tests/mir-opt/const_prop/return_place.add.PreCodegen.before.panic-abort.mir4
-rw-r--r--tests/mir-opt/const_prop/return_place.add.PreCodegen.before.panic-unwind.mir4
-rw-r--r--tests/mir-opt/const_prop/tuple_literal_propagation.main.ConstProp.panic-abort.diff12
-rw-r--r--tests/mir-opt/const_prop/tuple_literal_propagation.main.ConstProp.panic-unwind.diff12
-rw-r--r--tests/mir-opt/dataflow-const-prop/enum.constant.DataflowConstProp.32bit.diff63
-rw-r--r--tests/mir-opt/dataflow-const-prop/enum.constant.DataflowConstProp.64bit.diff63
-rw-r--r--tests/mir-opt/dataflow-const-prop/enum.multiple.DataflowConstProp.32bit.diff (renamed from tests/mir-opt/dataflow-const-prop/enum.multiple.DataflowConstProp.diff)0
-rw-r--r--tests/mir-opt/dataflow-const-prop/enum.multiple.DataflowConstProp.64bit.diff82
-rw-r--r--tests/mir-opt/dataflow-const-prop/enum.mutate_discriminant.DataflowConstProp.32bit.diff (renamed from tests/mir-opt/dataflow-const-prop/enum.mutate_discriminant.DataflowConstProp.diff)0
-rw-r--r--tests/mir-opt/dataflow-const-prop/enum.mutate_discriminant.DataflowConstProp.64bit.diff26
-rw-r--r--tests/mir-opt/dataflow-const-prop/enum.rs22
-rw-r--r--tests/mir-opt/dataflow-const-prop/enum.simple.DataflowConstProp.32bit.diff (renamed from tests/mir-opt/dataflow-const-prop/enum.simple.DataflowConstProp.diff)0
-rw-r--r--tests/mir-opt/dataflow-const-prop/enum.simple.DataflowConstProp.64bit.diff63
-rw-r--r--tests/mir-opt/dataflow-const-prop/enum.statics.DataflowConstProp.32bit.diff126
-rw-r--r--tests/mir-opt/dataflow-const-prop/enum.statics.DataflowConstProp.64bit.diff126
-rw-r--r--tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-abort.diff7
-rw-r--r--tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-unwind.diff7
-rw-r--r--tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-abort.diff7
-rw-r--r--tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-unwind.diff7
-rw-r--r--tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.32bit.diff129
-rw-r--r--tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.64bit.diff129
-rw-r--r--tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.diff51
-rw-r--r--tests/mir-opt/dataflow-const-prop/struct.rs11
-rw-r--r--tests/mir-opt/dont_inline_type_id.call.Inline.diff20
-rw-r--r--tests/mir-opt/dont_inline_type_id.rs15
-rw-r--r--tests/mir-opt/enum_opt.cand.EnumSizeOpt.32bit.diff4
-rw-r--r--tests/mir-opt/enum_opt.cand.EnumSizeOpt.64bit.diff4
-rw-r--r--tests/mir-opt/enum_opt.unin.EnumSizeOpt.32bit.diff4
-rw-r--r--tests/mir-opt/enum_opt.unin.EnumSizeOpt.64bit.diff4
-rw-r--r--tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-abort.mir6
-rw-r--r--tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-unwind.mir6
-rw-r--r--tests/mir-opt/generator_tiny.main-{closure#0}.generator_resume.0.mir6
-rw-r--r--tests/mir-opt/inline_generically_if_sized.call.Inline.diff24
-rw-r--r--tests/mir-opt/inline_generically_if_sized.rs17
-rw-r--r--tests/mir-opt/issue_99325.main.built.after.32bit.mir4
-rw-r--r--tests/mir-opt/issue_99325.main.built.after.64bit.mir4
-rw-r--r--tests/mir-opt/nll/region_subtyping_basic.main.nll.0.32bit.mir2
-rw-r--r--tests/mir-opt/nll/region_subtyping_basic.main.nll.0.64bit.mir2
-rw-r--r--tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.32bit.panic-abort.diff4
-rw-r--r--tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.32bit.panic-unwind.diff4
-rw-r--r--tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.64bit.panic-abort.diff4
-rw-r--r--tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.64bit.panic-unwind.diff4
-rw-r--r--tests/mir-opt/pre-codegen/spans.outer.PreCodegen.after.panic-abort.mir2
-rw-r--r--tests/mir-opt/pre-codegen/spans.outer.PreCodegen.after.panic-unwind.mir2
-rw-r--r--tests/pretty/tests-are-sorted.pp2
-rw-r--r--tests/run-coverage/closure.coverage14
-rw-r--r--tests/run-coverage/closure_bug.coverage53
-rw-r--r--tests/run-coverage/closure_bug.rs44
-rw-r--r--tests/run-coverage/closure_macro.coverage2
-rw-r--r--tests/run-coverage/closure_macro.rs2
-rw-r--r--tests/run-coverage/closure_macro_async.coverage14
-rw-r--r--tests/run-coverage/closure_macro_async.rs14
-rw-r--r--tests/run-coverage/no_cov_crate.coverage14
-rw-r--r--tests/run-coverage/no_cov_crate.rs14
-rw-r--r--tests/run-make-fulldeps/obtain-borrowck/driver.rs3
-rw-r--r--tests/run-make/dump-ice-to-disk/check.sh4
-rw-r--r--tests/run-make/emit-path-unhashed/Makefile8
-rw-r--r--tests/run-make/issue-88756-default-output/output-default.stdout2
-rw-r--r--tests/run-make/ls-metadata/Makefile4
-rw-r--r--tests/run-make/lto-linkage-used-attr/Makefile9
-rw-r--r--tests/run-make/lto-linkage-used-attr/lib.rs50
-rw-r--r--tests/run-make/lto-linkage-used-attr/main.rs10
-rw-r--r--tests/run-make/metadata-dep-info/Makefile13
-rw-r--r--tests/run-make/metadata-dep-info/dash-separated.rs4
-rw-r--r--tests/run-make/metadata-dep-info/dash-separated_something-extra.normalized.d5
-rw-r--r--tests/run-make/output-filename-overwrites-input/Makefile2
-rw-r--r--tests/run-make/rustdoc-themes/Makefile3
-rw-r--r--tests/rustdoc-gui/search-corrections.goml50
-rw-r--r--tests/rustdoc-gui/search-result-color.goml2
-rw-r--r--tests/rustdoc-gui/sidebar-source-code.goml2
-rw-r--r--tests/rustdoc-gui/src/theme_css/Cargo.lock7
-rw-r--r--tests/rustdoc-gui/src/theme_css/Cargo.toml7
-rw-r--r--tests/rustdoc-gui/src/theme_css/custom-theme.css99
-rw-r--r--tests/rustdoc-gui/src/theme_css/lib.rs2
-rw-r--r--tests/rustdoc-gui/theme-change.goml33
-rw-r--r--tests/rustdoc-js-std/option-type-signatures.js62
-rw-r--r--tests/rustdoc-js-std/vec-type-signatures.js22
-rw-r--r--tests/rustdoc-js/generics-match-ambiguity.js1
-rw-r--r--tests/rustdoc-js/generics-trait.js8
-rw-r--r--tests/rustdoc-js/generics-unbox.js38
-rw-r--r--tests/rustdoc-js/generics-unbox.rs36
-rw-r--r--tests/rustdoc-js/type-parameters.js87
-rw-r--r--tests/rustdoc-js/type-parameters.rs15
-rw-r--r--tests/rustdoc-ui/custom_code_classes_in_docs-warning.rs83
-rw-r--r--tests/rustdoc-ui/custom_code_classes_in_docs-warning.stderr97
-rw-r--r--tests/rustdoc-ui/custom_code_classes_in_docs-warning3.rs17
-rw-r--r--tests/rustdoc-ui/custom_code_classes_in_docs-warning3.stderr33
-rw-r--r--tests/rustdoc-ui/feature-gate-custom_code_classes_in_docs.rs15
-rw-r--r--tests/rustdoc-ui/feature-gate-custom_code_classes_in_docs.stderr14
-rw-r--r--tests/rustdoc-ui/issues/issue-91713.stdout2
-rw-r--r--tests/rustdoc/custom_code_classes.rs28
-rw-r--r--tests/rustdoc/issue-32077-type-alias-impls.rs2
-rw-r--r--tests/ui-fulldeps/pprust-expr-roundtrip.rs20
-rw-r--r--tests/ui-fulldeps/stable-mir/crate-info.rs6
-rw-r--r--tests/ui/abi/compatibility.rs75
-rw-r--r--tests/ui/abi/debug.rs1
-rw-r--r--tests/ui/abi/debug.stderr34
-rw-r--r--tests/ui/associated-consts/associated-const-array-len.stderr6
-rw-r--r--tests/ui/associated-consts/defaults-cyclic-fail.rs2
-rw-r--r--tests/ui/associated-consts/defaults-cyclic-fail.stderr14
-rw-r--r--tests/ui/associated-consts/defaults-not-assumed-fail.stderr6
-rw-r--r--tests/ui/associated-consts/issue-105330.stderr10
-rw-r--r--tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-impl.stderr12
-rw-r--r--tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-trait-default.stderr12
-rw-r--r--tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-trait.stderr12
-rw-r--r--tests/ui/associated-types/associated-types-ICE-when-projecting-out-of-err.stderr6
-rw-r--r--tests/ui/associated-types/associated-types-no-suitable-supertrait.stderr6
-rw-r--r--tests/ui/associated-types/defaults-suitability.stderr5
-rw-r--r--tests/ui/associated-types/issue-59324.stderr6
-rw-r--r--tests/ui/associated-types/issue-64855.stderr6
-rw-r--r--tests/ui/associated-types/point-at-type-on-obligation-failure-2.stderr15
-rw-r--r--tests/ui/async-await/in-trait/indirect-recursion-issue-112047.rs38
-rw-r--r--tests/ui/async-await/in-trait/indirect-recursion-issue-112047.stderr5
-rw-r--r--tests/ui/async-await/issues/issue-66695-static-refs.rs4
-rw-r--r--tests/ui/async-await/issues/issue-67611-static-mut-refs.rs4
-rw-r--r--tests/ui/async-await/missed-capture-issue-107414.rs9
-rw-r--r--tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.current.stderr8
-rw-r--r--tests/ui/binding/match-beginning-vert.rs4
-rw-r--r--tests/ui/borrowck/issue-115259-suggest-iter-mut.fixed20
-rw-r--r--tests/ui/borrowck/issue-115259-suggest-iter-mut.rs20
-rw-r--r--tests/ui/borrowck/issue-115259-suggest-iter-mut.stderr16
-rw-r--r--tests/ui/borrowck/issue-62387-suggest-iter-mut-2.fixed36
-rw-r--r--tests/ui/borrowck/issue-62387-suggest-iter-mut-2.rs36
-rw-r--r--tests/ui/borrowck/issue-62387-suggest-iter-mut-2.stderr16
-rw-r--r--tests/ui/borrowck/issue-62387-suggest-iter-mut.fixed30
-rw-r--r--tests/ui/borrowck/issue-62387-suggest-iter-mut.rs30
-rw-r--r--tests/ui/borrowck/issue-62387-suggest-iter-mut.stderr29
-rw-r--r--tests/ui/borrowck/issue-81899.stderr2
-rw-r--r--tests/ui/borrowck/issue-88434-minimal-example.stderr2
-rw-r--r--tests/ui/borrowck/issue-88434-removal-index-should-be-less.stderr2
-rw-r--r--tests/ui/c-variadic/variadic-ffi-2.rs5
-rw-r--r--tests/ui/c-variadic/variadic-ffi-2.stderr2
-rw-r--r--tests/ui/cast/cast-as-bool.rs44
-rw-r--r--tests/ui/cast/cast-as-bool.stderr80
-rw-r--r--tests/ui/cast/cast-rfc0401-2.rs2
-rw-r--r--tests/ui/cast/cast-rfc0401-2.stderr9
-rw-r--r--tests/ui/closures/2229_closure_analysis/repr_packed.rs10
-rw-r--r--tests/ui/closures/2229_closure_analysis/repr_packed.stderr19
-rw-r--r--tests/ui/codegen/subtyping-enforces-type-equality.rs48
-rw-r--r--tests/ui/codegen/subtyping-enforces-type-equality.stderr1
-rw-r--r--tests/ui/coherence/coherence-unsafe-trait-object-impl.stderr5
-rw-r--r--tests/ui/const-generics/dont-evaluate-array-len-on-err-1.stderr6
-rw-r--r--tests/ui/const-generics/early/const-param-from-outer-fn.rs2
-rw-r--r--tests/ui/const-generics/early/const-param-from-outer-fn.stderr8
-rw-r--r--tests/ui/const-generics/generic_const_exprs/issue-85848.stderr6
-rw-r--r--tests/ui/const-generics/issues/issue-86530.stderr5
-rw-r--r--tests/ui/const-generics/late-bound-vars/in_closure.rs20
-rw-r--r--tests/ui/const-generics/late-bound-vars/in_closure.stderr30
-rw-r--r--tests/ui/const-generics/late-bound-vars/late-bound-in-return-issue-77357.rs13
-rw-r--r--tests/ui/const-generics/late-bound-vars/late-bound-in-return-issue-77357.stderr8
-rw-r--r--tests/ui/const-generics/late-bound-vars/late-bound-in-where-issue-83993.rs15
-rw-r--r--tests/ui/const-generics/late-bound-vars/late-bound-in-where-issue-83993.stderr10
-rw-r--r--tests/ui/const-generics/late-bound-vars/simple.rs27
-rw-r--r--tests/ui/const-generics/late-bound-vars/simple.stderr29
-rw-r--r--tests/ui/const_prop/dont-propagate-generic-instance-2.rs26
-rw-r--r--tests/ui/const_prop/dont-propagate-generic-instance.rs24
-rw-r--r--tests/ui/consts/const-err-late.stderr6
-rw-r--r--tests/ui/consts/const-err-multi.stderr6
-rw-r--r--tests/ui/consts/const-eval/erroneous-const.stderr2
-rw-r--r--tests/ui/consts/const-eval/erroneous-const2.stderr2
-rw-r--r--tests/ui/consts/const-eval/issue-44578.stderr6
-rw-r--r--tests/ui/consts/const-eval/issue-50814-2.stderr2
-rw-r--r--tests/ui/consts/const-eval/issue-50814.stderr2
-rw-r--r--tests/ui/consts/const-eval/panic-assoc-never-type.rs2
-rw-r--r--tests/ui/consts/const-eval/panic-assoc-never-type.stderr4
-rw-r--r--tests/ui/consts/const-eval/raw-bytes.32bit.stderr6
-rw-r--r--tests/ui/consts/const-eval/raw-bytes.64bit.stderr6
-rw-r--r--tests/ui/consts/const-eval/ub-ref-ptr.stderr4
-rw-r--r--tests/ui/consts/const-eval/ub-wide-ptr.stderr6
-rw-r--r--tests/ui/consts/const-eval/union-const-eval-field.stderr4
-rw-r--r--tests/ui/consts/const-float-bits-reject-conv.stderr16
-rw-r--r--tests/ui/consts/const-len-underflow-separate-spans.next.stderr2
-rw-r--r--tests/ui/consts/const-len-underflow-separate-spans.old.stderr2
-rw-r--r--tests/ui/consts/escaping-bound-var.rs13
-rw-r--r--tests/ui/consts/escaping-bound-var.stderr20
-rw-r--r--tests/ui/consts/invalid-union.32bit.stderr4
-rw-r--r--tests/ui/consts/invalid-union.64bit.stderr4
-rw-r--r--tests/ui/consts/issue-105536-const-val-roundtrip-ptr-eq.rs31
-rw-r--r--tests/ui/consts/issue-36163.stderr14
-rw-r--r--tests/ui/consts/miri_unleashed/assoc_const.stderr4
-rw-r--r--tests/ui/consts/miri_unleashed/assoc_const_2.stderr4
-rw-r--r--tests/ui/consts/uninhabited-const-issue-61744.stderr4
-rw-r--r--tests/ui/cross/cross-fn-cache-hole.stderr5
-rw-r--r--tests/ui/deriving/deriving-all-codegen.stdout28
-rw-r--r--tests/ui/diagnostic_namespace/feature-gate-diagnostic_namespace.rs4
-rw-r--r--tests/ui/diagnostic_namespace/feature-gate-diagnostic_namespace.stderr6
-rw-r--r--tests/ui/diagnostic_namespace/non_existing_attributes_accepted.stderr2
-rw-r--r--tests/ui/diagnostic_namespace/on_unimplemented/do_not_fail_parsing_on_invalid_options_1.rs37
-rw-r--r--tests/ui/diagnostic_namespace/on_unimplemented/do_not_fail_parsing_on_invalid_options_1.stderr110
-rw-r--r--tests/ui/diagnostic_namespace/on_unimplemented/feature-gate-diagnostic_on_unimplemented.rs7
-rw-r--r--tests/ui/diagnostic_namespace/on_unimplemented/feature-gate-diagnostic_on_unimplemented.stderr12
-rw-r--r--tests/ui/diagnostic_namespace/on_unimplemented/on_unimplemented_simple.rs11
-rw-r--r--tests/ui/diagnostic_namespace/on_unimplemented/on_unimplemented_simple.stderr24
-rw-r--r--tests/ui/drop/dynamic-drop.rs18
-rw-r--r--tests/ui/dst/dst-bad-coerce1.stderr10
-rw-r--r--tests/ui/dyn-star/error.stderr6
-rw-r--r--tests/ui/error-codes/E0040.stderr10
-rw-r--r--tests/ui/error-codes/E0054.stderr9
-rw-r--r--tests/ui/error-codes/E0277.stderr5
-rw-r--r--tests/ui/error-codes/E0401.stderr22
-rw-r--r--tests/ui/error-festival.stderr9
-rw-r--r--tests/ui/explicit/explicit-call-to-dtor.stderr10
-rw-r--r--tests/ui/explicit/explicit-call-to-supertrait-dtor.stderr10
-rw-r--r--tests/ui/expr/if/bad-if-let-suggestion.rs3
-rw-r--r--tests/ui/expr/if/bad-if-let-suggestion.stderr23
-rw-r--r--tests/ui/feature-gates/feature-gate-coverage-attribute.rs14
-rw-r--r--tests/ui/feature-gates/feature-gate-coverage-attribute.stderr21
-rw-r--r--tests/ui/feature-gates/feature-gate-no_coverage.rs13
-rw-r--r--tests/ui/feature-gates/feature-gate-no_coverage.stderr12
-rw-r--r--tests/ui/fmt/raw-idents.rs17
-rw-r--r--tests/ui/fmt/raw-idents.stderr44
-rw-r--r--tests/ui/generic-associated-types/bugs/issue-88460.stderr8
-rw-r--r--tests/ui/generic-associated-types/issue-101020.stderr5
-rw-r--r--tests/ui/generics/issue-94432-garbage-ice.rs2
-rw-r--r--tests/ui/generics/issue-98432.rs2
-rw-r--r--tests/ui/generics/issue-98432.stderr8
-rw-r--r--tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-62529-3.stderr8
-rw-r--r--tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-89118.stderr15
-rw-r--r--tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-90950.stderr8
-rw-r--r--tests/ui/higher-ranked/trait-bounds/normalize-under-binder/norm-before-method-resolution.stderr5
-rw-r--r--tests/ui/impl-trait/async_scope_creep.rs15
-rw-r--r--tests/ui/impl-trait/async_scope_creep.tait.stderr9
-rw-r--r--tests/ui/impl-trait/lifetime-ambiguity-regression.rs13
-rw-r--r--tests/ui/imports/import-after-macro-expand-10.rs17
-rw-r--r--tests/ui/imports/import-after-macro-expand-11.rs21
-rw-r--r--tests/ui/imports/import-after-macro-expand-12.rs34
-rw-r--r--tests/ui/imports/import-after-macro-expand-13.rs22
-rw-r--r--tests/ui/imports/import-after-macro-expand-14.rs22
-rw-r--r--tests/ui/imports/import-after-macro-expand-2.rs4
-rw-r--r--tests/ui/imports/import-after-macro-expand-4.rs11
-rw-r--r--tests/ui/imports/import-after-macro-expand-4.stderr53
-rw-r--r--tests/ui/imports/import-after-macro-expand-6.rs4
-rw-r--r--tests/ui/imports/import-after-macro-expand-9.rs17
-rw-r--r--tests/ui/inner-static-type-parameter.rs2
-rw-r--r--tests/ui/inner-static-type-parameter.stderr6
-rw-r--r--tests/ui/issues/issue-17252.stderr11
-rw-r--r--tests/ui/issues/issue-18611.stderr6
-rw-r--r--tests/ui/issues/issue-21763.stderr3
-rw-r--r--tests/ui/issues/issue-23302-1.stderr9
-rw-r--r--tests/ui/issues/issue-23302-2.stderr9
-rw-r--r--tests/ui/issues/issue-23302-3.stderr14
-rw-r--r--tests/ui/issues/issue-25076.stderr5
-rw-r--r--tests/ui/issues/issue-3214.rs2
-rw-r--r--tests/ui/issues/issue-3214.stderr8
-rw-r--r--tests/ui/issues/issue-35570.stderr6
-rw-r--r--tests/ui/issues/issue-5997-enum.rs2
-rw-r--r--tests/ui/issues/issue-5997-enum.stderr8
-rw-r--r--tests/ui/issues/issue-5997-struct.rs2
-rw-r--r--tests/ui/issues/issue-5997-struct.stderr8
-rw-r--r--tests/ui/issues/issue-60218.stderr5
-rw-r--r--tests/ui/issues/issue-66353.stderr12
-rw-r--r--tests/ui/issues/issue-69602-type-err-during-codegen-ice.stderr2
-rw-r--r--tests/ui/layout/homogeneous-aggr-transparent.rs44
-rw-r--r--tests/ui/layout/homogeneous-aggr-transparent.stderr32
-rw-r--r--tests/ui/lifetimes/anonymize-unnamed-bound-vars-in-binders.rs27
-rw-r--r--tests/ui/lifetimes/lifetime-elision-return-type-trait.stderr6
-rw-r--r--tests/ui/limits/issue-55878.stderr8
-rw-r--r--tests/ui/limits/issue-56762.rs6
-rw-r--r--tests/ui/limits/issue-56762.stderr10
-rw-r--r--tests/ui/lint/expr-field.rs15
-rw-r--r--tests/ui/lint/lint-ctypes-option-nonnull-unsized.rs8
-rw-r--r--tests/ui/lint/lint-ctypes-option-nonnull-unsized.stderr16
-rw-r--r--tests/ui/lint/no-coverage.rs40
-rw-r--r--tests/ui/lint/no-coverage.stderr72
-rw-r--r--tests/ui/lint/ptr_null_checks.rs14
-rw-r--r--tests/ui/lint/ptr_null_checks.stderr38
-rw-r--r--tests/ui/match/issue-115681.rs32
-rw-r--r--tests/ui/mir/issue-92893.rs4
-rw-r--r--tests/ui/mir/issue-92893.stderr18
-rw-r--r--tests/ui/mismatched_types/cast-rfc0401.stderr11
-rw-r--r--tests/ui/namespace/namespace-mix.stderr220
-rw-r--r--tests/ui/nested-ty-params.rs2
-rw-r--r--tests/ui/nested-ty-params.stderr16
-rw-r--r--tests/ui/never_type/feature-gate-never_type_fallback.stderr5
-rw-r--r--tests/ui/never_type/impl_trait_fallback3.stderr6
-rw-r--r--tests/ui/never_type/impl_trait_fallback4.stderr6
-rw-r--r--tests/ui/on-unimplemented/on-trait.stderr10
-rw-r--r--tests/ui/on-unimplemented/parent-label.stderr20
-rw-r--r--tests/ui/parser/issues/issue-115780-pat-lt-bracket-in-macro-call.rs21
-rw-r--r--tests/ui/pattern/issue-114896.rs7
-rw-r--r--tests/ui/pattern/issue-114896.stderr11
-rw-r--r--tests/ui/proc-macro/bad-projection.stderr6
-rw-r--r--tests/ui/range/range-1.stderr2
-rw-r--r--tests/ui/repr/repr-transparent-non-exhaustive.rs40
-rw-r--r--tests/ui/repr/repr-transparent-non-exhaustive.stderr42
-rw-r--r--tests/ui/repr/repr-transparent.rs23
-rw-r--r--tests/ui/repr/repr-transparent.stderr82
-rw-r--r--tests/ui/resolve/bad-type-env-capture.stderr8
-rw-r--r--tests/ui/resolve/generic-params-from-outer-item-in-const-item.default.stderr28
-rw-r--r--tests/ui/resolve/generic-params-from-outer-item-in-const-item.generic_const_items.stderr34
-rw-r--r--tests/ui/resolve/generic-params-from-outer-item-in-const-item.rs39
-rw-r--r--tests/ui/resolve/issue-12796.rs2
-rw-r--r--tests/ui/resolve/issue-12796.stderr4
-rw-r--r--tests/ui/resolve/issue-3021-c.rs4
-rw-r--r--tests/ui/resolve/issue-3021-c.stderr16
-rw-r--r--tests/ui/resolve/issue-65025-extern-static-parent-generics.rs2
-rw-r--r--tests/ui/resolve/issue-65025-extern-static-parent-generics.stderr6
-rw-r--r--tests/ui/resolve/issue-65035-static-with-parent-generics.rs10
-rw-r--r--tests/ui/resolve/issue-65035-static-with-parent-generics.stderr30
-rw-r--r--tests/ui/resolve/resolve-type-param-in-item-in-trait.rs8
-rw-r--r--tests/ui/resolve/resolve-type-param-in-item-in-trait.stderr32
-rw-r--r--tests/ui/resolve/use-self-in-inner-fn.rs6
-rw-r--r--tests/ui/resolve/use-self-in-inner-fn.stderr6
-rw-r--r--tests/ui/rfcs/rfc-2294-if-let-guard/const-expr.rs26
-rw-r--r--tests/ui/rfcs/rfc-2294-if-let-guard/feature-gate.rs36
-rw-r--r--tests/ui/rfcs/rfc-2294-if-let-guard/feature-gate.stderr285
-rw-r--r--tests/ui/rfcs/rfc-2294-if-let-guard/macro-expanded.stderr1
-rw-r--r--tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let-chain.rs97
-rw-r--r--tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let-chain.stderr67
-rw-r--r--tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let.rs41
-rw-r--r--tests/ui/rfcs/rfc-2294-if-let-guard/parens.rs2
-rw-r--r--tests/ui/rfcs/rfc-2294-if-let-guard/parens.stderr34
-rw-r--r--tests/ui/rfcs/rfc-2294-if-let-guard/type-inference.rs16
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/ast-validate-guards.rs2
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/ast-validate-guards.stderr2
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/avoid-invalid-mir.rs14
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/avoid-invalid-mir.stderr10
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions-without-feature-gate.rs340
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions-without-feature-gate.stderr1021
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions.rs261
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions.stderr1462
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/ensure-that-let-else-does-not-interact-with-let-chains.rs1
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/ensure-that-let-else-does-not-interact-with-let-chains.stderr30
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/feature-gate.rs6
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/feature-gate.stderr30
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/invalid-let-in-a-valid-let-context.rs2
-rw-r--r--tests/ui/rfcs/rfc-2497-if-let-chains/invalid-let-in-a-valid-let-context.stderr36
-rw-r--r--tests/ui/rfcs/rfc-2632-const-trait-impl/effects/fallback.rs16
-rw-r--r--tests/ui/sanitize/cfg.rs21
-rw-r--r--tests/ui/span/issue-29595.stderr6
-rw-r--r--tests/ui/span/send-is-not-static-std-sync.rs2
-rw-r--r--tests/ui/span/send-is-not-static-std-sync.stderr8
-rw-r--r--tests/ui/specialization/issue-38091.stderr5
-rw-r--r--tests/ui/suggestions/issue-89333.stderr5
-rw-r--r--tests/ui/thir-print/thir-flat-const-variant.stdout96
-rw-r--r--tests/ui/thir-print/thir-tree-match.stdout20
-rw-r--r--tests/ui/trait-bounds/issue-82038.stderr6
-rw-r--r--tests/ui/traits/bound/on-structs-and-enums-in-fns.stderr10
-rw-r--r--tests/ui/traits/bound/on-structs-and-enums-in-impls.stderr5
-rw-r--r--tests/ui/traits/bound/on-structs-and-enums-locals.stderr10
-rw-r--r--tests/ui/traits/bound/on-structs-and-enums-static.stderr5
-rw-r--r--tests/ui/traits/bound/on-structs-and-enums.stderr20
-rw-r--r--tests/ui/traits/deny-builtin-object-impl.current.stderr5
-rw-r--r--tests/ui/traits/deny-builtin-object-impl.next.stderr5
-rw-r--r--tests/ui/traits/dont-autoderef-ty-with-escaping-var.stderr5
-rw-r--r--tests/ui/traits/impl-bounds-checking.stderr5
-rw-r--r--tests/ui/traits/new-solver/canonicalize-effect-var.rs22
-rw-r--r--tests/ui/traits/new-solver/projection-discr-kind.stderr5
-rw-r--r--tests/ui/traits/non_lifetime_binders/capture-late-ct-in-anon.rs2
-rw-r--r--tests/ui/traits/non_lifetime_binders/capture-late-ct-in-anon.stderr2
-rw-r--r--tests/ui/traits/non_lifetime_binders/fail.stderr5
-rw-r--r--tests/ui/traits/non_lifetime_binders/late-bound-in-anon-ct.rs2
-rw-r--r--tests/ui/traits/non_lifetime_binders/late-bound-in-anon-ct.stderr2
-rw-r--r--tests/ui/traits/object-does-not-impl-trait.stderr5
-rw-r--r--tests/ui/traits/vtable-res-trait-param.stderr5
-rw-r--r--tests/ui/trivial-bounds/trivial-bounds-leak.stderr11
-rw-r--r--tests/ui/type-alias-impl-trait/escaping-bound-var.rs22
-rw-r--r--tests/ui/type-alias-impl-trait/escaping-bound-var.stderr8
-rw-r--r--tests/ui/type-alias-impl-trait/indirect-recursion-issue-112047.rs29
-rw-r--r--tests/ui/type-alias-impl-trait/indirect-recursion-issue-112047.stderr5
-rw-r--r--tests/ui/type-alias-impl-trait/mututally-recursive-overflow.rs40
-rw-r--r--tests/ui/type-alias-impl-trait/mututally-recursive-overflow.stderr5
-rw-r--r--tests/ui/type-alias-impl-trait/nested-tait-hrtb.rs2
-rw-r--r--tests/ui/type-alias-impl-trait/nested-tait-hrtb.stderr14
-rw-r--r--tests/ui/type-alias-impl-trait/rpit_tait_equality_in_canonical_query.rs25
-rw-r--r--tests/ui/type-alias-impl-trait/variance.rs30
-rw-r--r--tests/ui/type-alias-impl-trait/variance.stderr62
-rw-r--r--tests/ui/type/type-arg-out-of-scope.rs2
-rw-r--r--tests/ui/type/type-arg-out-of-scope.stderr16
-rw-r--r--tests/ui/union/projection-as-union-type-error-2.stderr5
-rw-r--r--tests/ui/union/projection-as-union-type-error.stderr6
-rw-r--r--tests/ui/unreachable-code.rs15
-rw-r--r--tests/ui/unsafe/edition-2024-unsafe_op_in_unsafe_fn.rs17
-rw-r--r--tests/ui/unsafe/edition-2024-unsafe_op_in_unsafe_fn.stderr16
-rw-r--r--tests/ui/unsized/issue-115809.rs13
-rw-r--r--tests/ui/unsized/issue-115809.stderr19
-rw-r--r--tests/ui/unsized/issue-75707.stderr5
-rw-r--r--tests/ui/wf/hir-wf-canonicalized.stderr12
-rw-r--r--tests/ui/wf/issue-95665.stderr5
-rw-r--r--tests/ui/wf/wf-complex-assoc-type.stderr5
-rw-r--r--tests/ui/wf/wf-foreign-fn-decl-ret.stderr11
-rw-r--r--tests/ui/wf/wf-packed-on-proj-of-type-as-unimpl-trait.stderr6
-rw-r--r--tests/ui/where-clauses/higher-ranked-fn-type.quiet.stderr5
-rw-r--r--tests/ui/where-clauses/higher-ranked-fn-type.verbose.stderr5
-rw-r--r--tests/ui/where-clauses/where-clause-method-substituion.stderr5
410 files changed, 7673 insertions, 2683 deletions
diff --git a/tests/codegen/issues/issue-115385-llvm-jump-threading.rs b/tests/codegen/issues/issue-115385-llvm-jump-threading.rs
new file mode 100644
index 00000000000..142e3596d96
--- /dev/null
+++ b/tests/codegen/issues/issue-115385-llvm-jump-threading.rs
@@ -0,0 +1,46 @@
+// compile-flags: -O -Ccodegen-units=1
+
+#![crate_type = "lib"]
+
+#[repr(i64)]
+pub enum Boolean {
+    False = 0,
+    True = 1,
+}
+
+impl Clone for Boolean {
+    fn clone(&self) -> Self {
+        *self
+    }
+}
+
+impl Copy for Boolean {}
+
+extern "C" {
+    fn set_value(foo: *mut i64);
+    fn bar();
+}
+
+pub fn foo(x: bool) {
+    let mut foo = core::mem::MaybeUninit::<i64>::uninit();
+    unsafe {
+        set_value(foo.as_mut_ptr());
+    }
+
+    if x {
+        let l1 = unsafe { *foo.as_mut_ptr().cast::<Boolean>() };
+        if matches!(l1, Boolean::False) {
+            unsafe {
+                *foo.as_mut_ptr() = 0;
+            }
+        }
+    }
+
+    let l2 = unsafe { *foo.as_mut_ptr() };
+    if l2 == 2 {
+        // CHECK: call void @bar
+        unsafe {
+            bar();
+        }
+    }
+}
diff --git a/tests/codegen/sanitizer/kcfi-add-kcfi-flag.rs b/tests/codegen/sanitizer/kcfi-add-kcfi-flag.rs
index c2eb852aec3..6d466b93c40 100644
--- a/tests/codegen/sanitizer/kcfi-add-kcfi-flag.rs
+++ b/tests/codegen/sanitizer/kcfi-add-kcfi-flag.rs
@@ -1,9 +1,20 @@
 // Verifies that "kcfi" module flag is added.
 //
-// needs-sanitizer-kcfi
+// revisions: aarch64 x86_64
+// [aarch64] compile-flags: --target aarch64-unknown-none
+// [aarch64] needs-llvm-components: aarch64
+// [x86_64] compile-flags: --target x86_64-unknown-none
+// [x86_64] needs-llvm-components: x86
 // compile-flags: -Ctarget-feature=-crt-static -Zsanitizer=kcfi
 
+#![feature(no_core, lang_items)]
 #![crate_type="lib"]
+#![no_core]
+
+#[lang="sized"]
+trait Sized { }
+#[lang="copy"]
+trait Copy { }
 
 pub fn foo() {
 }
diff --git a/tests/coverage-map/status-quo/closure.cov-map b/tests/coverage-map/status-quo/closure.cov-map
index f3a32f091a9..7dbf6ec834d 100644
--- a/tests/coverage-map/status-quo/closure.cov-map
+++ b/tests/coverage-map/status-quo/closure.cov-map
@@ -1,5 +1,5 @@
 Function name: closure::main
-Raw bytes (170): 0x[01, 01, 17, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 05, 05, 5a, 01, 05, 18, 01, 08, 01, 0f, 0d, 03, 16, 0e, 06, 0a, 07, 10, 05, 13, 0d, 0b, 1a, 0e, 08, 09, 0f, 10, 05, 0e, 09, 13, 16, 05, 0d, 18, 17, 19, 09, 01, 21, 1b, 04, 09, 00, 29, 1f, 01, 09, 00, 2d, 23, 01, 09, 00, 24, 27, 05, 09, 00, 24, 2b, 02, 09, 00, 21, 2f, 04, 09, 00, 21, 33, 04, 09, 00, 28, 37, 09, 09, 00, 32, 3b, 04, 09, 00, 33, 3f, 07, 09, 00, 4b, 43, 08, 09, 01, 09, 47, 0a, 09, 01, 09, 4b, 08, 09, 01, 09, 4f, 0a, 08, 00, 10, 05, 00, 11, 04, 06, 5a, 04, 06, 00, 07, 57, 01, 05, 03, 02]
+Raw bytes (170): 0x[01, 01, 17, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 00, 01, 05, 05, 5a, 01, 05, 18, 01, 08, 01, 0f, 0d, 03, 16, 0e, 06, 0a, 07, 10, 05, 13, 0d, 0b, 1a, 0e, 06, 0a, 0f, 10, 05, 0c, 16, 13, 16, 05, 0d, 18, 17, 19, 09, 01, 1e, 1b, 04, 09, 00, 29, 1f, 01, 09, 00, 2d, 23, 01, 09, 00, 24, 27, 05, 09, 00, 24, 2b, 02, 09, 00, 21, 2f, 04, 09, 00, 21, 33, 04, 09, 00, 28, 37, 09, 09, 00, 32, 3b, 04, 09, 00, 33, 3f, 07, 09, 00, 4b, 43, 08, 09, 00, 48, 47, 0a, 09, 00, 47, 4b, 08, 09, 00, 44, 4f, 0a, 08, 00, 10, 05, 00, 11, 04, 06, 5a, 04, 06, 00, 07, 57, 01, 05, 03, 02]
 Number of files: 1
 - file 0 => global file 1
 Number of expressions: 23
@@ -32,13 +32,13 @@ Number of file 0 mappings: 24
     = (c0 + Zero)
 - Code(Expression(1, Add)) at (prev + 16, 5) to (start + 19, 13)
     = (c0 + Zero)
-- Code(Expression(2, Add)) at (prev + 26, 14) to (start + 8, 9)
+- Code(Expression(2, Add)) at (prev + 26, 14) to (start + 6, 10)
     = (c0 + Zero)
-- Code(Expression(3, Add)) at (prev + 16, 5) to (start + 14, 9)
+- Code(Expression(3, Add)) at (prev + 16, 5) to (start + 12, 22)
     = (c0 + Zero)
 - Code(Expression(4, Add)) at (prev + 22, 5) to (start + 13, 24)
     = (c0 + Zero)
-- Code(Expression(5, Add)) at (prev + 25, 9) to (start + 1, 33)
+- Code(Expression(5, Add)) at (prev + 25, 9) to (start + 1, 30)
     = (c0 + Zero)
 - Code(Expression(6, Add)) at (prev + 4, 9) to (start + 0, 41)
     = (c0 + Zero)
@@ -60,11 +60,11 @@ Number of file 0 mappings: 24
     = (c0 + Zero)
 - Code(Expression(15, Add)) at (prev + 7, 9) to (start + 0, 75)
     = (c0 + Zero)
-- Code(Expression(16, Add)) at (prev + 8, 9) to (start + 1, 9)
+- Code(Expression(16, Add)) at (prev + 8, 9) to (start + 0, 72)
     = (c0 + Zero)
-- Code(Expression(17, Add)) at (prev + 10, 9) to (start + 1, 9)
+- Code(Expression(17, Add)) at (prev + 10, 9) to (start + 0, 71)
     = (c0 + Zero)
-- Code(Expression(18, Add)) at (prev + 8, 9) to (start + 1, 9)
+- Code(Expression(18, Add)) at (prev + 8, 9) to (start + 0, 68)
     = (c0 + Zero)
 - Code(Expression(19, Add)) at (prev + 10, 8) to (start + 0, 16)
     = (c0 + Zero)
diff --git a/tests/coverage-map/status-quo/closure_bug.cov-map b/tests/coverage-map/status-quo/closure_bug.cov-map
new file mode 100644
index 00000000000..4fe2e5ad243
--- /dev/null
+++ b/tests/coverage-map/status-quo/closure_bug.cov-map
@@ -0,0 +1,148 @@
+Function name: closure_bug::main
+Raw bytes (241): 0x[01, 01, 34, 01, 00, 01, 05, 05, ce, 01, 01, 05, cb, 01, 00, 05, ce, 01, 01, 05, cb, 01, 09, 05, ce, 01, 01, 05, 09, c6, 01, cb, 01, 09, 05, ce, 01, 01, 05, c3, 01, 00, 09, c6, 01, cb, 01, 09, 05, ce, 01, 01, 05, c3, 01, 0d, 09, c6, 01, cb, 01, 09, 05, ce, 01, 01, 05, 0d, be, 01, c3, 01, 0d, 09, c6, 01, cb, 01, 09, 05, ce, 01, 01, 05, bb, 01, 00, 0d, be, 01, c3, 01, 0d, 09, c6, 01, cb, 01, 09, 05, ce, 01, 01, 05, bb, 01, 11, 0d, be, 01, c3, 01, 0d, 09, c6, 01, cb, 01, 09, 05, ce, 01, 01, 05, 11, b6, 01, bb, 01, 11, 0d, be, 01, c3, 01, 0d, 09, c6, 01, cb, 01, 09, 05, ce, 01, 01, 05, 11, 01, 06, 01, 03, 0a, 03, 09, 05, 01, 0e, 05, 01, 0f, 00, 17, ce, 01, 00, 17, 00, 18, cb, 01, 02, 09, 00, 0a, 13, 06, 05, 01, 0e, 09, 01, 0f, 00, 17, c6, 01, 00, 17, 00, 18, c3, 01, 02, 09, 00, 0a, 3b, 06, 05, 01, 0e, 0d, 01, 0f, 00, 17, be, 01, 00, 17, 00, 18, bb, 01, 02, 09, 00, 0a, 7b, 06, 05, 01, 0e, 11, 01, 0f, 00, 17, b6, 01, 00, 17, 00, 18, b3, 01, 01, 01, 00, 02]
+Number of files: 1
+- file 0 => global file 1
+Number of expressions: 52
+- expression 0 operands: lhs = Counter(0), rhs = Zero
+- expression 1 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 2 operands: lhs = Counter(1), rhs = Expression(51, Sub)
+- expression 3 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 4 operands: lhs = Expression(50, Add), rhs = Zero
+- expression 5 operands: lhs = Counter(1), rhs = Expression(51, Sub)
+- expression 6 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 7 operands: lhs = Expression(50, Add), rhs = Counter(2)
+- expression 8 operands: lhs = Counter(1), rhs = Expression(51, Sub)
+- expression 9 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 10 operands: lhs = Counter(2), rhs = Expression(49, Sub)
+- expression 11 operands: lhs = Expression(50, Add), rhs = Counter(2)
+- expression 12 operands: lhs = Counter(1), rhs = Expression(51, Sub)
+- expression 13 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 14 operands: lhs = Expression(48, Add), rhs = Zero
+- expression 15 operands: lhs = Counter(2), rhs = Expression(49, Sub)
+- expression 16 operands: lhs = Expression(50, Add), rhs = Counter(2)
+- expression 17 operands: lhs = Counter(1), rhs = Expression(51, Sub)
+- expression 18 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 19 operands: lhs = Expression(48, Add), rhs = Counter(3)
+- expression 20 operands: lhs = Counter(2), rhs = Expression(49, Sub)
+- expression 21 operands: lhs = Expression(50, Add), rhs = Counter(2)
+- expression 22 operands: lhs = Counter(1), rhs = Expression(51, Sub)
+- expression 23 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 24 operands: lhs = Counter(3), rhs = Expression(47, Sub)
+- expression 25 operands: lhs = Expression(48, Add), rhs = Counter(3)
+- expression 26 operands: lhs = Counter(2), rhs = Expression(49, Sub)
+- expression 27 operands: lhs = Expression(50, Add), rhs = Counter(2)
+- expression 28 operands: lhs = Counter(1), rhs = Expression(51, Sub)
+- expression 29 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 30 operands: lhs = Expression(46, Add), rhs = Zero
+- expression 31 operands: lhs = Counter(3), rhs = Expression(47, Sub)
+- expression 32 operands: lhs = Expression(48, Add), rhs = Counter(3)
+- expression 33 operands: lhs = Counter(2), rhs = Expression(49, Sub)
+- expression 34 operands: lhs = Expression(50, Add), rhs = Counter(2)
+- expression 35 operands: lhs = Counter(1), rhs = Expression(51, Sub)
+- expression 36 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 37 operands: lhs = Expression(46, Add), rhs = Counter(4)
+- expression 38 operands: lhs = Counter(3), rhs = Expression(47, Sub)
+- expression 39 operands: lhs = Expression(48, Add), rhs = Counter(3)
+- expression 40 operands: lhs = Counter(2), rhs = Expression(49, Sub)
+- expression 41 operands: lhs = Expression(50, Add), rhs = Counter(2)
+- expression 42 operands: lhs = Counter(1), rhs = Expression(51, Sub)
+- expression 43 operands: lhs = Counter(0), rhs = Counter(1)
+- expression 44 operands: lhs = Counter(4), rhs = Expression(45, Sub)
+- expression 45 operands: lhs = Expression(46, Add), rhs = Counter(4)
+- expression 46 operands: lhs = Counter(3), rhs = Expression(47, Sub)
+- expression 47 operands: lhs = Expression(48, Add), rhs = Counter(3)
+- expression 48 operands: lhs = Counter(2), rhs = Expression(49, Sub)
+- expression 49 operands: lhs = Expression(50, Add), rhs = Counter(2)
+- expression 50 operands: lhs = Counter(1), rhs = Expression(51, Sub)
+- expression 51 operands: lhs = Counter(0), rhs = Counter(1)
+Number of file 0 mappings: 17
+- Code(Counter(0)) at (prev + 6, 1) to (start + 3, 10)
+- Code(Expression(0, Add)) at (prev + 9, 5) to (start + 1, 14)
+    = (c0 + Zero)
+- Code(Counter(1)) at (prev + 1, 15) to (start + 0, 23)
+- Code(Expression(51, Sub)) at (prev + 0, 23) to (start + 0, 24)
+    = (c0 - c1)
+- Code(Expression(50, Add)) at (prev + 2, 9) to (start + 0, 10)
+    = (c1 + (c0 - c1))
+- Code(Expression(4, Add)) at (prev + 6, 5) to (start + 1, 14)
+    = ((c1 + (c0 - c1)) + Zero)
+- Code(Counter(2)) at (prev + 1, 15) to (start + 0, 23)
+- Code(Expression(49, Sub)) at (prev + 0, 23) to (start + 0, 24)
+    = ((c1 + (c0 - c1)) - c2)
+- Code(Expression(48, Add)) at (prev + 2, 9) to (start + 0, 10)
+    = (c2 + ((c1 + (c0 - c1)) - c2))
+- Code(Expression(14, Add)) at (prev + 6, 5) to (start + 1, 14)
+    = ((c2 + ((c1 + (c0 - c1)) - c2)) + Zero)
+- Code(Counter(3)) at (prev + 1, 15) to (start + 0, 23)
+- Code(Expression(47, Sub)) at (prev + 0, 23) to (start + 0, 24)
+    = ((c2 + ((c1 + (c0 - c1)) - c2)) - c3)
+- Code(Expression(46, Add)) at (prev + 2, 9) to (start + 0, 10)
+    = (c3 + ((c2 + ((c1 + (c0 - c1)) - c2)) - c3))
+- Code(Expression(30, Add)) at (prev + 6, 5) to (start + 1, 14)
+    = ((c3 + ((c2 + ((c1 + (c0 - c1)) - c2)) - c3)) + Zero)
+- Code(Counter(4)) at (prev + 1, 15) to (start + 0, 23)
+- Code(Expression(45, Sub)) at (prev + 0, 23) to (start + 0, 24)
+    = ((c3 + ((c2 + ((c1 + (c0 - c1)) - c2)) - c3)) - c4)
+- Code(Expression(44, Add)) at (prev + 1, 1) to (start + 0, 2)
+    = (c4 + ((c3 + ((c2 + ((c1 + (c0 - c1)) - c2)) - c3)) - c4))
+
+Function name: closure_bug::main::{closure#0}
+Raw bytes (28): 0x[01, 01, 02, 01, 05, 05, 02, 04, 01, 0d, 09, 00, 12, 05, 00, 15, 00, 19, 02, 00, 23, 00, 28, 07, 00, 29, 00, 2a]
+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: 4
+- Code(Counter(0)) at (prev + 13, 9) to (start + 0, 18)
+- Code(Counter(1)) at (prev + 0, 21) to (start + 0, 25)
+- Code(Expression(0, Sub)) at (prev + 0, 35) to (start + 0, 40)
+    = (c0 - c1)
+- Code(Expression(1, Add)) at (prev + 0, 41) to (start + 0, 42)
+    = (c1 + (c0 - c1))
+
+Function name: closure_bug::main::{closure#1}
+Raw bytes (28): 0x[01, 01, 02, 01, 05, 05, 02, 04, 01, 16, 09, 00, 12, 05, 00, 15, 00, 19, 02, 00, 23, 00, 28, 07, 00, 29, 00, 2a]
+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: 4
+- Code(Counter(0)) at (prev + 22, 9) to (start + 0, 18)
+- Code(Counter(1)) at (prev + 0, 21) to (start + 0, 25)
+- Code(Expression(0, Sub)) at (prev + 0, 35) to (start + 0, 40)
+    = (c0 - c1)
+- Code(Expression(1, Add)) at (prev + 0, 41) to (start + 0, 42)
+    = (c1 + (c0 - c1))
+
+Function name: closure_bug::main::{closure#2}
+Raw bytes (28): 0x[01, 01, 02, 01, 05, 05, 02, 04, 01, 1f, 09, 00, 12, 05, 00, 15, 00, 19, 02, 00, 23, 00, 28, 07, 00, 29, 00, 2a]
+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: 4
+- Code(Counter(0)) at (prev + 31, 9) to (start + 0, 18)
+- Code(Counter(1)) at (prev + 0, 21) to (start + 0, 25)
+- Code(Expression(0, Sub)) at (prev + 0, 35) to (start + 0, 40)
+    = (c0 - c1)
+- Code(Expression(1, Add)) at (prev + 0, 41) to (start + 0, 42)
+    = (c1 + (c0 - c1))
+
+Function name: closure_bug::main::{closure#3}
+Raw bytes (28): 0x[01, 01, 02, 01, 05, 05, 02, 04, 01, 28, 09, 00, 12, 05, 00, 15, 00, 19, 02, 00, 23, 00, 28, 07, 00, 29, 00, 2a]
+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: 4
+- Code(Counter(0)) at (prev + 40, 9) to (start + 0, 18)
+- Code(Counter(1)) at (prev + 0, 21) to (start + 0, 25)
+- Code(Expression(0, Sub)) at (prev + 0, 35) to (start + 0, 40)
+    = (c0 - c1)
+- Code(Expression(1, Add)) at (prev + 0, 41) to (start + 0, 42)
+    = (c1 + (c0 - c1))
+
diff --git a/tests/coverage-map/status-quo/closure_bug.rs b/tests/coverage-map/status-quo/closure_bug.rs
new file mode 100644
index 00000000000..739bc5f0b51
--- /dev/null
+++ b/tests/coverage-map/status-quo/closure_bug.rs
@@ -0,0 +1,44 @@
+// Regression test for #115930.
+// All of these closures are identical, and should produce identical output in
+// the coverage report. However, an unstable sort was causing them to be treated
+// inconsistently when preparing coverage spans.
+
+fn main() {
+    let truthy = std::env::args().len() == 1;
+
+    let a
+        =
+        |
+        |
+        if truthy { true } else { false };
+
+    a();
+    if truthy { a(); }
+
+    let b
+        =
+        |
+        |
+        if truthy { true } else { false };
+
+    b();
+    if truthy { b(); }
+
+    let c
+        =
+        |
+        |
+        if truthy { true } else { false };
+
+    c();
+    if truthy { c(); }
+
+    let d
+        =
+        |
+        |
+        if truthy { true } else { false };
+
+    d();
+    if truthy { d(); }
+}
diff --git a/tests/coverage-map/status-quo/closure_macro.rs b/tests/coverage-map/status-quo/closure_macro.rs
index 5e3b00d1ef5..9b289141c2e 100644
--- a/tests/coverage-map/status-quo/closure_macro.rs
+++ b/tests/coverage-map/status-quo/closure_macro.rs
@@ -1,5 +1,5 @@
 // compile-flags: --edition=2018
-#![feature(no_coverage)]
+#![feature(coverage_attribute)]
 
 macro_rules! bail {
     ($msg:literal $(,)?) => {
diff --git a/tests/coverage-map/status-quo/closure_macro_async.rs b/tests/coverage-map/status-quo/closure_macro_async.rs
index 3d6bdb38a2a..b4275599e59 100644
--- a/tests/coverage-map/status-quo/closure_macro_async.rs
+++ b/tests/coverage-map/status-quo/closure_macro_async.rs
@@ -1,5 +1,5 @@
 // compile-flags: --edition=2018
-#![feature(no_coverage)]
+#![feature(coverage_attribute)]
 
 macro_rules! bail {
     ($msg:literal $(,)?) => {
@@ -39,7 +39,7 @@ pub async fn test() -> Result<(), String> {
     Ok(())
 }
 
-#[no_coverage]
+#[coverage(off)]
 fn main() {
     executor::block_on(test()).unwrap();
 }
@@ -51,18 +51,18 @@ mod executor {
         task::{Context, Poll, RawWaker, RawWakerVTable, Waker},
     };
 
-    #[no_coverage]
+    #[coverage(off)]
     pub fn block_on<F: Future>(mut future: F) -> F::Output {
         let mut future = unsafe { Pin::new_unchecked(&mut future) };
         use std::hint::unreachable_unchecked;
         static VTABLE: RawWakerVTable = RawWakerVTable::new(
-            #[no_coverage]
+            #[coverage(off)]
             |_| unsafe { unreachable_unchecked() }, // clone
-            #[no_coverage]
+            #[coverage(off)]
             |_| unsafe { unreachable_unchecked() }, // wake
-            #[no_coverage]
+            #[coverage(off)]
             |_| unsafe { unreachable_unchecked() }, // wake_by_ref
-            #[no_coverage]
+            #[coverage(off)]
             |_| (),
         );
         let waker = unsafe { Waker::from_raw(RawWaker::new(core::ptr::null(), &VTABLE)) };
diff --git a/tests/coverage-map/status-quo/generator.cov-map b/tests/coverage-map/status-quo/generator.cov-map
index 6e10b58a941..a66c1af30f9 100644
--- a/tests/coverage-map/status-quo/generator.cov-map
+++ b/tests/coverage-map/status-quo/generator.cov-map
@@ -14,7 +14,7 @@ Number of file 0 mappings: 4
     = (c1 + (c0 - c1))
 
 Function name: generator::main
-Raw bytes (71): 0x[01, 01, 0b, 01, 00, 05, 0b, 09, 0d, 11, 00, 11, 15, 2a, 19, 11, 15, 15, 19, 26, 00, 2a, 19, 11, 15, 09, 01, 0f, 01, 02, 19, 03, 07, 0b, 00, 2e, 11, 01, 2b, 00, 2d, 07, 01, 0e, 00, 35, 0f, 02, 0b, 00, 2e, 2a, 01, 22, 00, 27, 26, 00, 2c, 00, 2e, 1f, 01, 0e, 00, 35, 23, 02, 01, 00, 02]
+Raw bytes (71): 0x[01, 01, 0b, 01, 00, 05, 0b, 09, 0d, 11, 00, 11, 15, 2a, 19, 11, 15, 15, 19, 26, 00, 2a, 19, 11, 15, 09, 01, 0f, 01, 02, 16, 03, 07, 0b, 00, 2e, 11, 01, 2b, 00, 2d, 07, 01, 0e, 00, 35, 0f, 02, 0b, 00, 2e, 2a, 01, 22, 00, 27, 26, 00, 2c, 00, 2e, 1f, 01, 0e, 00, 35, 23, 02, 01, 00, 02]
 Number of files: 1
 - file 0 => global file 1
 Number of expressions: 11
@@ -30,7 +30,7 @@ Number of expressions: 11
 - expression 9 operands: lhs = Expression(10, Sub), rhs = Counter(6)
 - expression 10 operands: lhs = Counter(4), rhs = Counter(5)
 Number of file 0 mappings: 9
-- Code(Counter(0)) at (prev + 15, 1) to (start + 2, 25)
+- Code(Counter(0)) at (prev + 15, 1) to (start + 2, 22)
 - Code(Expression(0, Add)) at (prev + 7, 11) to (start + 0, 46)
     = (c0 + Zero)
 - Code(Counter(4)) at (prev + 1, 43) to (start + 0, 45)
diff --git a/tests/coverage-map/status-quo/no_cov_crate.rs b/tests/coverage-map/status-quo/no_cov_crate.rs
index 5b748aeefb7..e12e4bc55e3 100644
--- a/tests/coverage-map/status-quo/no_cov_crate.rs
+++ b/tests/coverage-map/status-quo/no_cov_crate.rs
@@ -1,17 +1,17 @@
-// Enables `no_coverage` on the entire crate
-#![feature(no_coverage)]
+// Enables `coverage(off)` on the entire crate
+#![feature(coverage_attribute)]
 
-#[no_coverage]
+#[coverage(off)]
 fn do_not_add_coverage_1() {
     println!("called but not covered");
 }
 
 fn do_not_add_coverage_2() {
-    #![no_coverage]
+    #![coverage(off)]
     println!("called but not covered");
 }
 
-#[no_coverage]
+#[coverage(off)]
 #[allow(dead_code)]
 fn do_not_add_coverage_not_called() {
     println!("not called and not covered");
@@ -33,7 +33,7 @@ fn add_coverage_not_called() {
 // FIXME: These test-cases illustrate confusing results of nested functions.
 // See https://github.com/rust-lang/rust/issues/93319
 mod nested_fns {
-    #[no_coverage]
+    #[coverage(off)]
     pub fn outer_not_covered(is_true: bool) {
         fn inner(is_true: bool) {
             if is_true {
@@ -50,7 +50,7 @@ mod nested_fns {
         println!("called and covered");
         inner_not_covered(is_true);
 
-        #[no_coverage]
+        #[coverage(off)]
         fn inner_not_covered(is_true: bool) {
             if is_true {
                 println!("called but not covered");
diff --git a/tests/debuginfo/pretty-std-collections.rs b/tests/debuginfo/pretty-std-collections.rs
index 93597aa7e23..93a0dff6848 100644
--- a/tests/debuginfo/pretty-std-collections.rs
+++ b/tests/debuginfo/pretty-std-collections.rs
@@ -1,7 +1,6 @@
 // ignore-windows failing on win32 bot
 // ignore-freebsd: gdb package too new
 // ignore-android: FIXME(#10381)
-// ignore-macos: FIXME(#78665)
 // compile-flags:-g
 
 // The pretty printers being tested here require the patch from
diff --git a/tests/mir-opt/const_prop/checked_add.main.ConstProp.panic-abort.diff b/tests/mir-opt/const_prop/checked_add.main.ConstProp.panic-abort.diff
index 6daef87dd2c..c2fd7f65f5e 100644
--- a/tests/mir-opt/const_prop/checked_add.main.ConstProp.panic-abort.diff
+++ b/tests/mir-opt/const_prop/checked_add.main.ConstProp.panic-abort.diff
@@ -24,5 +24,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc3 (size: 8, align: 4) {
++     02 00 00 00 00 __ __ __                         │ .....░░░
   }
   
diff --git a/tests/mir-opt/const_prop/checked_add.main.ConstProp.panic-unwind.diff b/tests/mir-opt/const_prop/checked_add.main.ConstProp.panic-unwind.diff
index 125407bf285..21a31f9aba3 100644
--- a/tests/mir-opt/const_prop/checked_add.main.ConstProp.panic-unwind.diff
+++ b/tests/mir-opt/const_prop/checked_add.main.ConstProp.panic-unwind.diff
@@ -24,5 +24,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc3 (size: 8, align: 4) {
++     02 00 00 00 00 __ __ __                         │ .....░░░
   }
   
diff --git a/tests/mir-opt/const_prop/indirect.main.ConstProp.panic-abort.diff b/tests/mir-opt/const_prop/indirect.main.ConstProp.panic-abort.diff
index ca0ce2888cd..c0efc873029 100644
--- a/tests/mir-opt/const_prop/indirect.main.ConstProp.panic-abort.diff
+++ b/tests/mir-opt/const_prop/indirect.main.ConstProp.panic-abort.diff
@@ -29,5 +29,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc3 (size: 2, align: 1) {
++     03 00                                           │ ..
   }
   
diff --git a/tests/mir-opt/const_prop/indirect.main.ConstProp.panic-unwind.diff b/tests/mir-opt/const_prop/indirect.main.ConstProp.panic-unwind.diff
index d63fb9255a3..2aee6f164ae 100644
--- a/tests/mir-opt/const_prop/indirect.main.ConstProp.panic-unwind.diff
+++ b/tests/mir-opt/const_prop/indirect.main.ConstProp.panic-unwind.diff
@@ -29,5 +29,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc3 (size: 2, align: 1) {
++     03 00                                           │ ..
   }
   
diff --git a/tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.panic-abort.diff b/tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.panic-abort.diff
index 51e17cf690a..7ba51ccdbf6 100644
--- a/tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.panic-abort.diff
+++ b/tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.panic-abort.diff
@@ -35,5 +35,9 @@
           _0 = const ();
           return;
       }
++ }
++ 
++ alloc3 (size: 2, align: 1) {
++     00 01                                           │ ..
   }
   
diff --git a/tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.panic-unwind.diff b/tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.panic-unwind.diff
index 5ef201497fb..545b7f22f6e 100644
--- a/tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.panic-unwind.diff
+++ b/tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.panic-unwind.diff
@@ -35,5 +35,9 @@
           _0 = const ();
           return;
       }
++ }
++ 
++ alloc3 (size: 2, align: 1) {
++     00 01                                           │ ..
   }
   
diff --git a/tests/mir-opt/const_prop/issue_66971.main.ConstProp.panic-abort.diff b/tests/mir-opt/const_prop/issue_66971.main.ConstProp.panic-abort.diff
index 170c019782d..18341ba7db9 100644
--- a/tests/mir-opt/const_prop/issue_66971.main.ConstProp.panic-abort.diff
+++ b/tests/mir-opt/const_prop/issue_66971.main.ConstProp.panic-abort.diff
@@ -18,5 +18,13 @@
           StorageDead(_2);
           return;
       }
++ }
++ 
++ alloc8 (size: 2, align: 1) {
++     00 00                                           │ ..
++ }
++ 
++ alloc7 (size: 2, align: 1) {
++     00 00                                           │ ..
   }
   
diff --git a/tests/mir-opt/const_prop/issue_66971.main.ConstProp.panic-unwind.diff b/tests/mir-opt/const_prop/issue_66971.main.ConstProp.panic-unwind.diff
index 64227dfd78c..50763c10f0c 100644
--- a/tests/mir-opt/const_prop/issue_66971.main.ConstProp.panic-unwind.diff
+++ b/tests/mir-opt/const_prop/issue_66971.main.ConstProp.panic-unwind.diff
@@ -18,5 +18,13 @@
           StorageDead(_2);
           return;
       }
++ }
++ 
++ alloc8 (size: 2, align: 1) {
++     00 00                                           │ ..
++ }
++ 
++ alloc7 (size: 2, align: 1) {
++     00 00                                           │ ..
   }
   
diff --git a/tests/mir-opt/const_prop/issue_67019.main.ConstProp.panic-abort.diff b/tests/mir-opt/const_prop/issue_67019.main.ConstProp.panic-abort.diff
index e1f3f37b370..015180db896 100644
--- a/tests/mir-opt/const_prop/issue_67019.main.ConstProp.panic-abort.diff
+++ b/tests/mir-opt/const_prop/issue_67019.main.ConstProp.panic-abort.diff
@@ -23,5 +23,17 @@
           StorageDead(_2);
           return;
       }
++ }
++ 
++ alloc12 (size: 2, align: 1) {
++     01 02                                           │ ..
++ }
++ 
++ alloc11 (size: 2, align: 1) {
++     01 02                                           │ ..
++ }
++ 
++ alloc8 (size: 2, align: 1) {
++     01 02                                           │ ..
   }
   
diff --git a/tests/mir-opt/const_prop/issue_67019.main.ConstProp.panic-unwind.diff b/tests/mir-opt/const_prop/issue_67019.main.ConstProp.panic-unwind.diff
index aaa376a95cf..8e41705c1af 100644
--- a/tests/mir-opt/const_prop/issue_67019.main.ConstProp.panic-unwind.diff
+++ b/tests/mir-opt/const_prop/issue_67019.main.ConstProp.panic-unwind.diff
@@ -23,5 +23,17 @@
           StorageDead(_2);
           return;
       }
++ }
++ 
++ alloc12 (size: 2, align: 1) {
++     01 02                                           │ ..
++ }
++ 
++ alloc11 (size: 2, align: 1) {
++     01 02                                           │ ..
++ }
++ 
++ alloc8 (size: 2, align: 1) {
++     01 02                                           │ ..
   }
   
diff --git a/tests/mir-opt/const_prop/mutable_variable_aggregate.main.ConstProp.diff b/tests/mir-opt/const_prop/mutable_variable_aggregate.main.ConstProp.diff
index 0f118c7f59f..56a127ae31e 100644
--- a/tests/mir-opt/const_prop/mutable_variable_aggregate.main.ConstProp.diff
+++ b/tests/mir-opt/const_prop/mutable_variable_aggregate.main.ConstProp.diff
@@ -25,5 +25,13 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc7 (size: 8, align: 4) {
++     2a 00 00 00 63 00 00 00                         │ *...c...
++ }
++ 
++ alloc5 (size: 8, align: 4) {
++     2a 00 00 00 2b 00 00 00                         │ *...+...
   }
   
diff --git a/tests/mir-opt/const_prop/mutable_variable_unprop_assign.main.ConstProp.panic-abort.diff b/tests/mir-opt/const_prop/mutable_variable_unprop_assign.main.ConstProp.panic-abort.diff
index a85dcf9c7ed..a1b433716c8 100644
--- a/tests/mir-opt/const_prop/mutable_variable_unprop_assign.main.ConstProp.panic-abort.diff
+++ b/tests/mir-opt/const_prop/mutable_variable_unprop_assign.main.ConstProp.panic-abort.diff
@@ -46,5 +46,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc7 (size: 8, align: 4) {
++     01 00 00 00 02 00 00 00                         │ ........
   }
   
diff --git a/tests/mir-opt/const_prop/mutable_variable_unprop_assign.main.ConstProp.panic-unwind.diff b/tests/mir-opt/const_prop/mutable_variable_unprop_assign.main.ConstProp.panic-unwind.diff
index 15ef0fa4dff..2dc514194bc 100644
--- a/tests/mir-opt/const_prop/mutable_variable_unprop_assign.main.ConstProp.panic-unwind.diff
+++ b/tests/mir-opt/const_prop/mutable_variable_unprop_assign.main.ConstProp.panic-unwind.diff
@@ -46,5 +46,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc7 (size: 8, align: 4) {
++     01 00 00 00 02 00 00 00                         │ ........
   }
   
diff --git a/tests/mir-opt/const_prop/return_place.add.ConstProp.panic-abort.diff b/tests/mir-opt/const_prop/return_place.add.ConstProp.panic-abort.diff
index f3b30e0dcde..6c9de476465 100644
--- a/tests/mir-opt/const_prop/return_place.add.ConstProp.panic-abort.diff
+++ b/tests/mir-opt/const_prop/return_place.add.ConstProp.panic-abort.diff
@@ -17,5 +17,9 @@
 +         _0 = const 4_u32;
           return;
       }
++ }
++ 
++ alloc5 (size: 8, align: 4) {
++     04 00 00 00 00 __ __ __                         │ .....░░░
   }
   
diff --git a/tests/mir-opt/const_prop/return_place.add.ConstProp.panic-unwind.diff b/tests/mir-opt/const_prop/return_place.add.ConstProp.panic-unwind.diff
index 79f85fcef11..0f079278c43 100644
--- a/tests/mir-opt/const_prop/return_place.add.ConstProp.panic-unwind.diff
+++ b/tests/mir-opt/const_prop/return_place.add.ConstProp.panic-unwind.diff
@@ -17,5 +17,9 @@
 +         _0 = const 4_u32;
           return;
       }
++ }
++ 
++ alloc5 (size: 8, align: 4) {
++     04 00 00 00 00 __ __ __                         │ .....░░░
   }
   
diff --git a/tests/mir-opt/const_prop/return_place.add.PreCodegen.before.panic-abort.mir b/tests/mir-opt/const_prop/return_place.add.PreCodegen.before.panic-abort.mir
index c8f3f641a6d..c2488f3944c 100644
--- a/tests/mir-opt/const_prop/return_place.add.PreCodegen.before.panic-abort.mir
+++ b/tests/mir-opt/const_prop/return_place.add.PreCodegen.before.panic-abort.mir
@@ -14,3 +14,7 @@ fn add() -> u32 {
         return;
     }
 }
+
+alloc5 (size: 8, align: 4) {
+    04 00 00 00 00 __ __ __                         │ .....░░░
+}
diff --git a/tests/mir-opt/const_prop/return_place.add.PreCodegen.before.panic-unwind.mir b/tests/mir-opt/const_prop/return_place.add.PreCodegen.before.panic-unwind.mir
index 9a064697463..fa0b9c77eaf 100644
--- a/tests/mir-opt/const_prop/return_place.add.PreCodegen.before.panic-unwind.mir
+++ b/tests/mir-opt/const_prop/return_place.add.PreCodegen.before.panic-unwind.mir
@@ -14,3 +14,7 @@ fn add() -> u32 {
         return;
     }
 }
+
+alloc5 (size: 8, align: 4) {
+    04 00 00 00 00 __ __ __                         │ .....░░░
+}
diff --git a/tests/mir-opt/const_prop/tuple_literal_propagation.main.ConstProp.panic-abort.diff b/tests/mir-opt/const_prop/tuple_literal_propagation.main.ConstProp.panic-abort.diff
index 9e705695ac0..988ef7dd225 100644
--- a/tests/mir-opt/const_prop/tuple_literal_propagation.main.ConstProp.panic-abort.diff
+++ b/tests/mir-opt/const_prop/tuple_literal_propagation.main.ConstProp.panic-abort.diff
@@ -29,5 +29,17 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc9 (size: 8, align: 4) {
++     01 00 00 00 02 00 00 00                         │ ........
++ }
++ 
++ alloc8 (size: 8, align: 4) {
++     01 00 00 00 02 00 00 00                         │ ........
++ }
++ 
++ alloc6 (size: 8, align: 4) {
++     01 00 00 00 02 00 00 00                         │ ........
   }
   
diff --git a/tests/mir-opt/const_prop/tuple_literal_propagation.main.ConstProp.panic-unwind.diff b/tests/mir-opt/const_prop/tuple_literal_propagation.main.ConstProp.panic-unwind.diff
index 882dd97cc16..29844619720 100644
--- a/tests/mir-opt/const_prop/tuple_literal_propagation.main.ConstProp.panic-unwind.diff
+++ b/tests/mir-opt/const_prop/tuple_literal_propagation.main.ConstProp.panic-unwind.diff
@@ -29,5 +29,17 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc9 (size: 8, align: 4) {
++     01 00 00 00 02 00 00 00                         │ ........
++ }
++ 
++ alloc8 (size: 8, align: 4) {
++     01 00 00 00 02 00 00 00                         │ ........
++ }
++ 
++ alloc6 (size: 8, align: 4) {
++     01 00 00 00 02 00 00 00                         │ ........
   }
   
diff --git a/tests/mir-opt/dataflow-const-prop/enum.constant.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/enum.constant.DataflowConstProp.32bit.diff
new file mode 100644
index 00000000000..07ac5b72e24
--- /dev/null
+++ b/tests/mir-opt/dataflow-const-prop/enum.constant.DataflowConstProp.32bit.diff
@@ -0,0 +1,63 @@
+- // MIR for `constant` before DataflowConstProp
++ // MIR for `constant` after DataflowConstProp
+  
+  fn constant() -> () {
+      let mut _0: ();
+      let _1: E;
+      let mut _3: isize;
+      scope 1 {
+          debug e => _1;
+          let _2: i32;
+          let _4: i32;
+          let _5: i32;
+          scope 2 {
+              debug x => _2;
+          }
+          scope 3 {
+              debug x => _4;
+          }
+          scope 4 {
+              debug x => _5;
+          }
+      }
+  
+      bb0: {
+          StorageLive(_1);
+          _1 = const _;
+          StorageLive(_2);
+-         _3 = discriminant(_1);
+-         switchInt(move _3) -> [0: bb3, 1: bb1, otherwise: bb2];
++         _3 = const 0_isize;
++         switchInt(const 0_isize) -> [0: bb3, 1: bb1, otherwise: bb2];
+      }
+  
+      bb1: {
+          StorageLive(_5);
+          _5 = ((_1 as V2).0: i32);
+          _2 = _5;
+          StorageDead(_5);
+          goto -> bb4;
+      }
+  
+      bb2: {
+          unreachable;
+      }
+  
+      bb3: {
+          StorageLive(_4);
+-         _4 = ((_1 as V1).0: i32);
+-         _2 = _4;
++         _4 = const 0_i32;
++         _2 = const 0_i32;
+          StorageDead(_4);
+          goto -> bb4;
+      }
+  
+      bb4: {
+          _0 = const ();
+          StorageDead(_2);
+          StorageDead(_1);
+          return;
+      }
+  }
+  
diff --git a/tests/mir-opt/dataflow-const-prop/enum.constant.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/enum.constant.DataflowConstProp.64bit.diff
new file mode 100644
index 00000000000..07ac5b72e24
--- /dev/null
+++ b/tests/mir-opt/dataflow-const-prop/enum.constant.DataflowConstProp.64bit.diff
@@ -0,0 +1,63 @@
+- // MIR for `constant` before DataflowConstProp
++ // MIR for `constant` after DataflowConstProp
+  
+  fn constant() -> () {
+      let mut _0: ();
+      let _1: E;
+      let mut _3: isize;
+      scope 1 {
+          debug e => _1;
+          let _2: i32;
+          let _4: i32;
+          let _5: i32;
+          scope 2 {
+              debug x => _2;
+          }
+          scope 3 {
+              debug x => _4;
+          }
+          scope 4 {
+              debug x => _5;
+          }
+      }
+  
+      bb0: {
+          StorageLive(_1);
+          _1 = const _;
+          StorageLive(_2);
+-         _3 = discriminant(_1);
+-         switchInt(move _3) -> [0: bb3, 1: bb1, otherwise: bb2];
++         _3 = const 0_isize;
++         switchInt(const 0_isize) -> [0: bb3, 1: bb1, otherwise: bb2];
+      }
+  
+      bb1: {
+          StorageLive(_5);
+          _5 = ((_1 as V2).0: i32);
+          _2 = _5;
+          StorageDead(_5);
+          goto -> bb4;
+      }
+  
+      bb2: {
+          unreachable;
+      }
+  
+      bb3: {
+          StorageLive(_4);
+-         _4 = ((_1 as V1).0: i32);
+-         _2 = _4;
++         _4 = const 0_i32;
++         _2 = const 0_i32;
+          StorageDead(_4);
+          goto -> bb4;
+      }
+  
+      bb4: {
+          _0 = const ();
+          StorageDead(_2);
+          StorageDead(_1);
+          return;
+      }
+  }
+  
diff --git a/tests/mir-opt/dataflow-const-prop/enum.multiple.DataflowConstProp.diff b/tests/mir-opt/dataflow-const-prop/enum.multiple.DataflowConstProp.32bit.diff
index 775325c4d06..775325c4d06 100644
--- a/tests/mir-opt/dataflow-const-prop/enum.multiple.DataflowConstProp.diff
+++ b/tests/mir-opt/dataflow-const-prop/enum.multiple.DataflowConstProp.32bit.diff
diff --git a/tests/mir-opt/dataflow-const-prop/enum.multiple.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/enum.multiple.DataflowConstProp.64bit.diff
new file mode 100644
index 00000000000..775325c4d06
--- /dev/null
+++ b/tests/mir-opt/dataflow-const-prop/enum.multiple.DataflowConstProp.64bit.diff
@@ -0,0 +1,82 @@
+- // MIR for `multiple` before DataflowConstProp
++ // MIR for `multiple` after DataflowConstProp
+  
+  fn multiple(_1: bool, _2: u8) -> () {
+      debug x => _1;
+      debug i => _2;
+      let mut _0: ();
+      let _3: std::option::Option<u8>;
+      let mut _4: bool;
+      let mut _5: u8;
+      let mut _7: isize;
+      scope 1 {
+          debug e => _3;
+          let _6: u8;
+          let _8: u8;
+          scope 2 {
+              debug x => _6;
+              let _9: u8;
+              scope 4 {
+                  debug y => _9;
+              }
+          }
+          scope 3 {
+              debug i => _8;
+          }
+      }
+  
+      bb0: {
+          StorageLive(_3);
+          StorageLive(_4);
+          _4 = _1;
+          switchInt(move _4) -> [0: bb2, otherwise: bb1];
+      }
+  
+      bb1: {
+          StorageLive(_5);
+          _5 = _2;
+          _3 = Option::<u8>::Some(move _5);
+          StorageDead(_5);
+          goto -> bb3;
+      }
+  
+      bb2: {
+          _3 = Option::<u8>::None;
+          goto -> bb3;
+      }
+  
+      bb3: {
+          StorageDead(_4);
+          StorageLive(_6);
+          _7 = discriminant(_3);
+          switchInt(move _7) -> [0: bb4, 1: bb6, otherwise: bb5];
+      }
+  
+      bb4: {
+          _6 = const 0_u8;
+          goto -> bb7;
+      }
+  
+      bb5: {
+          unreachable;
+      }
+  
+      bb6: {
+          StorageLive(_8);
+          _8 = ((_3 as Some).0: u8);
+          _6 = _8;
+          StorageDead(_8);
+          goto -> bb7;
+      }
+  
+      bb7: {
+          StorageLive(_9);
+          _9 = _6;
+          _0 = const ();
+          StorageDead(_9);
+          StorageDead(_6);
+          StorageDead(_3);
+          return;
+      }
+  }
+  
diff --git a/tests/mir-opt/dataflow-const-prop/enum.mutate_discriminant.DataflowConstProp.diff b/tests/mir-opt/dataflow-const-prop/enum.mutate_discriminant.DataflowConstProp.32bit.diff
index 960e69ee916..960e69ee916 100644
--- a/tests/mir-opt/dataflow-const-prop/enum.mutate_discriminant.DataflowConstProp.diff
+++ b/tests/mir-opt/dataflow-const-prop/enum.mutate_discriminant.DataflowConstProp.32bit.diff
diff --git a/tests/mir-opt/dataflow-const-prop/enum.mutate_discriminant.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/enum.mutate_discriminant.DataflowConstProp.64bit.diff
new file mode 100644
index 00000000000..960e69ee916
--- /dev/null
+++ b/tests/mir-opt/dataflow-const-prop/enum.mutate_discriminant.DataflowConstProp.64bit.diff
@@ -0,0 +1,26 @@
+- // MIR for `mutate_discriminant` before DataflowConstProp
++ // MIR for `mutate_discriminant` after DataflowConstProp
+  
+  fn mutate_discriminant() -> u8 {
+      let mut _0: u8;
+      let mut _1: std::option::Option<NonZeroUsize>;
+      let mut _2: isize;
+  
+      bb0: {
+          discriminant(_1) = 1;
+          (((_1 as variant#1).0: NonZeroUsize).0: usize) = const 0_usize;
+          _2 = discriminant(_1);
+          switchInt(_2) -> [0: bb1, otherwise: bb2];
+      }
+  
+      bb1: {
+          _0 = const 1_u8;
+          return;
+      }
+  
+      bb2: {
+          _0 = const 2_u8;
+          unreachable;
+      }
+  }
+  
diff --git a/tests/mir-opt/dataflow-const-prop/enum.rs b/tests/mir-opt/dataflow-const-prop/enum.rs
index 79a20d7ef45..5a10e9e883d 100644
--- a/tests/mir-opt/dataflow-const-prop/enum.rs
+++ b/tests/mir-opt/dataflow-const-prop/enum.rs
@@ -1,9 +1,11 @@
 // unit-test: DataflowConstProp
+// EMIT_MIR_FOR_EACH_BIT_WIDTH
 
 #![feature(custom_mir, core_intrinsics, rustc_attrs)]
 
 use std::intrinsics::mir::*;
 
+#[derive(Copy, Clone)]
 enum E {
     V1(i32),
     V2(i32)
@@ -15,6 +17,24 @@ fn simple() {
     let x = match e { E::V1(x) => x, E::V2(x) => x };
 }
 
+// EMIT_MIR enum.constant.DataflowConstProp.diff
+fn constant() {
+    const C: E = E::V1(0);
+    let e = C;
+    let x = match e { E::V1(x) => x, E::V2(x) => x };
+}
+
+// EMIT_MIR enum.statics.DataflowConstProp.diff
+fn statics() {
+    static C: E = E::V1(0);
+    let e = C;
+    let x = match e { E::V1(x) => x, E::V2(x) => x };
+
+    static RC: &E = &E::V2(4);
+    let e = RC;
+    let x = match e { E::V1(x) => x, E::V2(x) => x };
+}
+
 #[rustc_layout_scalar_valid_range_start(1)]
 #[rustc_nonnull_optimization_guaranteed]
 struct NonZeroUsize(usize);
@@ -63,6 +83,8 @@ fn multiple(x: bool, i: u8) {
 
 fn main() {
     simple();
+    constant();
+    statics();
     mutate_discriminant();
     multiple(false, 5);
 }
diff --git a/tests/mir-opt/dataflow-const-prop/enum.simple.DataflowConstProp.diff b/tests/mir-opt/dataflow-const-prop/enum.simple.DataflowConstProp.32bit.diff
index 3946e7c7d96..3946e7c7d96 100644
--- a/tests/mir-opt/dataflow-const-prop/enum.simple.DataflowConstProp.diff
+++ b/tests/mir-opt/dataflow-const-prop/enum.simple.DataflowConstProp.32bit.diff
diff --git a/tests/mir-opt/dataflow-const-prop/enum.simple.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/enum.simple.DataflowConstProp.64bit.diff
new file mode 100644
index 00000000000..3946e7c7d96
--- /dev/null
+++ b/tests/mir-opt/dataflow-const-prop/enum.simple.DataflowConstProp.64bit.diff
@@ -0,0 +1,63 @@
+- // MIR for `simple` before DataflowConstProp
++ // MIR for `simple` after DataflowConstProp
+  
+  fn simple() -> () {
+      let mut _0: ();
+      let _1: E;
+      let mut _3: isize;
+      scope 1 {
+          debug e => _1;
+          let _2: i32;
+          let _4: i32;
+          let _5: i32;
+          scope 2 {
+              debug x => _2;
+          }
+          scope 3 {
+              debug x => _4;
+          }
+          scope 4 {
+              debug x => _5;
+          }
+      }
+  
+      bb0: {
+          StorageLive(_1);
+          _1 = E::V1(const 0_i32);
+          StorageLive(_2);
+-         _3 = discriminant(_1);
+-         switchInt(move _3) -> [0: bb3, 1: bb1, otherwise: bb2];
++         _3 = const 0_isize;
++         switchInt(const 0_isize) -> [0: bb3, 1: bb1, otherwise: bb2];
+      }
+  
+      bb1: {
+          StorageLive(_5);
+          _5 = ((_1 as V2).0: i32);
+          _2 = _5;
+          StorageDead(_5);
+          goto -> bb4;
+      }
+  
+      bb2: {
+          unreachable;
+      }
+  
+      bb3: {
+          StorageLive(_4);
+-         _4 = ((_1 as V1).0: i32);
+-         _2 = _4;
++         _4 = const 0_i32;
++         _2 = const 0_i32;
+          StorageDead(_4);
+          goto -> bb4;
+      }
+  
+      bb4: {
+          _0 = const ();
+          StorageDead(_2);
+          StorageDead(_1);
+          return;
+      }
+  }
+  
diff --git a/tests/mir-opt/dataflow-const-prop/enum.statics.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/enum.statics.DataflowConstProp.32bit.diff
new file mode 100644
index 00000000000..ae8b44c953e
--- /dev/null
+++ b/tests/mir-opt/dataflow-const-prop/enum.statics.DataflowConstProp.32bit.diff
@@ -0,0 +1,126 @@
+- // MIR for `statics` before DataflowConstProp
++ // MIR for `statics` after DataflowConstProp
+  
+  fn statics() -> () {
+      let mut _0: ();
+      let _1: E;
+      let mut _2: &E;
+      let mut _4: isize;
+      let mut _8: &&E;
+      let mut _10: isize;
+      scope 1 {
+          debug e => _1;
+          let _3: i32;
+          let _5: i32;
+          let _6: i32;
+          scope 2 {
+              debug x => _3;
+              let _7: &E;
+              scope 5 {
+                  debug e => _7;
+                  let _9: &i32;
+                  let _11: &i32;
+                  let _12: &i32;
+                  scope 6 {
+                      debug x => _9;
+                  }
+                  scope 7 {
+                      debug x => _11;
+                  }
+                  scope 8 {
+                      debug x => _12;
+                  }
+              }
+          }
+          scope 3 {
+              debug x => _5;
+          }
+          scope 4 {
+              debug x => _6;
+          }
+      }
+  
+      bb0: {
+          StorageLive(_1);
+          StorageLive(_2);
+          _2 = const {alloc1: &E};
+          _1 = (*_2);
+          StorageDead(_2);
+          StorageLive(_3);
+-         _4 = discriminant(_1);
+-         switchInt(move _4) -> [0: bb3, 1: bb1, otherwise: bb2];
++         _4 = const 0_isize;
++         switchInt(const 0_isize) -> [0: bb3, 1: bb1, otherwise: bb2];
+      }
+  
+      bb1: {
+          StorageLive(_6);
+          _6 = ((_1 as V2).0: i32);
+          _3 = _6;
+          StorageDead(_6);
+          goto -> bb4;
+      }
+  
+      bb2: {
+          unreachable;
+      }
+  
+      bb3: {
+          StorageLive(_5);
+-         _5 = ((_1 as V1).0: i32);
+-         _3 = _5;
++         _5 = const 0_i32;
++         _3 = const 0_i32;
+          StorageDead(_5);
+          goto -> bb4;
+      }
+  
+      bb4: {
+          StorageLive(_7);
+          StorageLive(_8);
+          _8 = const {alloc2: &&E};
+          _7 = (*_8);
+          StorageDead(_8);
+          StorageLive(_9);
+          _10 = discriminant((*_7));
+          switchInt(move _10) -> [0: bb6, 1: bb5, otherwise: bb2];
+      }
+  
+      bb5: {
+          StorageLive(_12);
+          _12 = &(((*_7) as V2).0: i32);
+          _9 = &(*_12);
+          StorageDead(_12);
+          goto -> bb7;
+      }
+  
+      bb6: {
+          StorageLive(_11);
+          _11 = &(((*_7) as V1).0: i32);
+          _9 = _11;
+          StorageDead(_11);
+          goto -> bb7;
+      }
+  
+      bb7: {
+          _0 = const ();
+          StorageDead(_9);
+          StorageDead(_7);
+          StorageDead(_3);
+          StorageDead(_1);
+          return;
+      }
+  }
+  
+  alloc2 (static: RC, size: 4, align: 4) {
+      ╾─alloc14─╼                                     │ ╾──╼
+  }
+  
+  alloc14 (size: 8, align: 4) {
+      01 00 00 00 04 00 00 00                         │ ........
+  }
+  
+  alloc1 (static: statics::C, size: 8, align: 4) {
+      00 00 00 00 00 00 00 00                         │ ........
+  }
+  
diff --git a/tests/mir-opt/dataflow-const-prop/enum.statics.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/enum.statics.DataflowConstProp.64bit.diff
new file mode 100644
index 00000000000..63799b3bac3
--- /dev/null
+++ b/tests/mir-opt/dataflow-const-prop/enum.statics.DataflowConstProp.64bit.diff
@@ -0,0 +1,126 @@
+- // MIR for `statics` before DataflowConstProp
++ // MIR for `statics` after DataflowConstProp
+  
+  fn statics() -> () {
+      let mut _0: ();
+      let _1: E;
+      let mut _2: &E;
+      let mut _4: isize;
+      let mut _8: &&E;
+      let mut _10: isize;
+      scope 1 {
+          debug e => _1;
+          let _3: i32;
+          let _5: i32;
+          let _6: i32;
+          scope 2 {
+              debug x => _3;
+              let _7: &E;
+              scope 5 {
+                  debug e => _7;
+                  let _9: &i32;
+                  let _11: &i32;
+                  let _12: &i32;
+                  scope 6 {
+                      debug x => _9;
+                  }
+                  scope 7 {
+                      debug x => _11;
+                  }
+                  scope 8 {
+                      debug x => _12;
+                  }
+              }
+          }
+          scope 3 {
+              debug x => _5;
+          }
+          scope 4 {
+              debug x => _6;
+          }
+      }
+  
+      bb0: {
+          StorageLive(_1);
+          StorageLive(_2);
+          _2 = const {alloc1: &E};
+          _1 = (*_2);
+          StorageDead(_2);
+          StorageLive(_3);
+-         _4 = discriminant(_1);
+-         switchInt(move _4) -> [0: bb3, 1: bb1, otherwise: bb2];
++         _4 = const 0_isize;
++         switchInt(const 0_isize) -> [0: bb3, 1: bb1, otherwise: bb2];
+      }
+  
+      bb1: {
+          StorageLive(_6);
+          _6 = ((_1 as V2).0: i32);
+          _3 = _6;
+          StorageDead(_6);
+          goto -> bb4;
+      }
+  
+      bb2: {
+          unreachable;
+      }
+  
+      bb3: {
+          StorageLive(_5);
+-         _5 = ((_1 as V1).0: i32);
+-         _3 = _5;
++         _5 = const 0_i32;
++         _3 = const 0_i32;
+          StorageDead(_5);
+          goto -> bb4;
+      }
+  
+      bb4: {
+          StorageLive(_7);
+          StorageLive(_8);
+          _8 = const {alloc2: &&E};
+          _7 = (*_8);
+          StorageDead(_8);
+          StorageLive(_9);
+          _10 = discriminant((*_7));
+          switchInt(move _10) -> [0: bb6, 1: bb5, otherwise: bb2];
+      }
+  
+      bb5: {
+          StorageLive(_12);
+          _12 = &(((*_7) as V2).0: i32);
+          _9 = &(*_12);
+          StorageDead(_12);
+          goto -> bb7;
+      }
+  
+      bb6: {
+          StorageLive(_11);
+          _11 = &(((*_7) as V1).0: i32);
+          _9 = _11;
+          StorageDead(_11);
+          goto -> bb7;
+      }
+  
+      bb7: {
+          _0 = const ();
+          StorageDead(_9);
+          StorageDead(_7);
+          StorageDead(_3);
+          StorageDead(_1);
+          return;
+      }
+  }
+  
+  alloc2 (static: RC, size: 8, align: 8) {
+      ╾───────alloc14───────╼                         │ ╾──────╼
+  }
+  
+  alloc14 (size: 8, align: 4) {
+      01 00 00 00 04 00 00 00                         │ ........
+  }
+  
+  alloc1 (static: statics::C, size: 8, align: 4) {
+      00 00 00 00 00 00 00 00                         │ ........
+  }
+  
diff --git a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-abort.diff
index be55d259dcf..e99b413f708 100644
--- a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-abort.diff
+++ b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-abort.diff
@@ -55,11 +55,12 @@
           _10 = const _;
           StorageLive(_11);
           _11 = const 1_usize;
-          _12 = Len((*_10));
+-         _12 = Len((*_10));
 -         _13 = Lt(_11, _12);
 -         assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, _11) -> [success: bb2, unwind unreachable];
-+         _13 = Lt(const 1_usize, _12);
-+         assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, const 1_usize) -> [success: bb2, unwind unreachable];
++         _12 = const 3_usize;
++         _13 = const true;
++         assert(const true, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 1_usize) -> [success: bb2, unwind unreachable];
       }
   
       bb2: {
diff --git a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-unwind.diff
index f9a6c509ac8..759a793fbf3 100644
--- a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-unwind.diff
+++ b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-unwind.diff
@@ -55,11 +55,12 @@
           _10 = const _;
           StorageLive(_11);
           _11 = const 1_usize;
-          _12 = Len((*_10));
+-         _12 = Len((*_10));
 -         _13 = Lt(_11, _12);
 -         assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, _11) -> [success: bb2, unwind continue];
-+         _13 = Lt(const 1_usize, _12);
-+         assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, const 1_usize) -> [success: bb2, unwind continue];
++         _12 = const 3_usize;
++         _13 = const true;
++         assert(const true, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 1_usize) -> [success: bb2, unwind continue];
       }
   
       bb2: {
diff --git a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-abort.diff
index be55d259dcf..e99b413f708 100644
--- a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-abort.diff
+++ b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-abort.diff
@@ -55,11 +55,12 @@
           _10 = const _;
           StorageLive(_11);
           _11 = const 1_usize;
-          _12 = Len((*_10));
+-         _12 = Len((*_10));
 -         _13 = Lt(_11, _12);
 -         assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, _11) -> [success: bb2, unwind unreachable];
-+         _13 = Lt(const 1_usize, _12);
-+         assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, const 1_usize) -> [success: bb2, unwind unreachable];
++         _12 = const 3_usize;
++         _13 = const true;
++         assert(const true, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 1_usize) -> [success: bb2, unwind unreachable];
       }
   
       bb2: {
diff --git a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-unwind.diff
index f9a6c509ac8..759a793fbf3 100644
--- a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-unwind.diff
+++ b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-unwind.diff
@@ -55,11 +55,12 @@
           _10 = const _;
           StorageLive(_11);
           _11 = const 1_usize;
-          _12 = Len((*_10));
+-         _12 = Len((*_10));
 -         _13 = Lt(_11, _12);
 -         assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, _11) -> [success: bb2, unwind continue];
-+         _13 = Lt(const 1_usize, _12);
-+         assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, const 1_usize) -> [success: bb2, unwind continue];
++         _12 = const 3_usize;
++         _13 = const true;
++         assert(const true, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 1_usize) -> [success: bb2, unwind continue];
       }
   
       bb2: {
diff --git a/tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.32bit.diff
new file mode 100644
index 00000000000..2de6ba307d5
--- /dev/null
+++ b/tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.32bit.diff
@@ -0,0 +1,129 @@
+- // MIR for `main` before DataflowConstProp
++ // MIR for `main` after DataflowConstProp
+  
+  fn main() -> () {
+      let mut _0: ();
+      let mut _1: S;
+      let mut _3: i32;
+      let mut _5: i32;
+      let mut _6: i32;
+      let mut _11: BigStruct;
+      let mut _16: &&BigStruct;
+      let mut _17: &BigStruct;
+      let mut _18: &BigStruct;
+      let mut _19: &BigStruct;
+      let mut _20: &BigStruct;
+      let mut _21: &BigStruct;
+      scope 1 {
+          debug s => _1;
+          let _2: i32;
+          scope 2 {
+              debug a => _2;
+              let _4: i32;
+              scope 3 {
+                  debug b => _4;
+                  let _7: S;
+                  let _8: u8;
+                  let _9: f32;
+                  let _10: S;
+                  scope 4 {
+                      debug a => _7;
+                      debug b => _8;
+                      debug c => _9;
+                      debug d => _10;
+                      let _12: S;
+                      let _13: u8;
+                      let _14: f32;
+                      let _15: S;
+                      scope 5 {
+                          debug a => _12;
+                          debug b => _13;
+                          debug c => _14;
+                          debug d => _15;
+                      }
+                  }
+              }
+          }
+      }
+  
+      bb0: {
+          StorageLive(_1);
+          _1 = S(const 1_i32);
+          StorageLive(_2);
+          StorageLive(_3);
+-         _3 = (_1.0: i32);
+-         _2 = Add(move _3, const 2_i32);
++         _3 = const 1_i32;
++         _2 = const 3_i32;
+          StorageDead(_3);
+          (_1.0: i32) = const 3_i32;
+          StorageLive(_4);
+          StorageLive(_5);
+-         _5 = _2;
++         _5 = const 3_i32;
+          StorageLive(_6);
+-         _6 = (_1.0: i32);
+-         _4 = Add(move _5, move _6);
++         _6 = const 3_i32;
++         _4 = const 6_i32;
+          StorageDead(_6);
+          StorageDead(_5);
+          StorageLive(_11);
+          _11 = const _;
+          StorageLive(_7);
+-         _7 = (_11.0: S);
++         _7 = const S(1_i32);
+          StorageLive(_8);
+-         _8 = (_11.1: u8);
++         _8 = const 5_u8;
+          StorageLive(_9);
+-         _9 = (_11.2: f32);
++         _9 = const 7f32;
+          StorageLive(_10);
+-         _10 = (_11.3: S);
++         _10 = const S(13_i32);
+          StorageDead(_11);
+          StorageLive(_16);
+          _16 = const {alloc1: &&BigStruct};
+          _17 = deref_copy (*_16);
+          StorageLive(_12);
+          _18 = deref_copy (*_16);
+-         _12 = ((*_18).0: S);
++         _12 = const S(1_i32);
+          StorageLive(_13);
+          _19 = deref_copy (*_16);
+-         _13 = ((*_19).1: u8);
++         _13 = const 5_u8;
+          StorageLive(_14);
+          _20 = deref_copy (*_16);
+-         _14 = ((*_20).2: f32);
++         _14 = const 7f32;
+          StorageLive(_15);
+          _21 = deref_copy (*_16);
+-         _15 = ((*_21).3: S);
++         _15 = const S(13_i32);
+          StorageDead(_16);
+          _0 = const ();
+          StorageDead(_15);
+          StorageDead(_14);
+          StorageDead(_13);
+          StorageDead(_12);
+          StorageDead(_10);
+          StorageDead(_9);
+          StorageDead(_8);
+          StorageDead(_7);
+          StorageDead(_4);
+          StorageDead(_2);
+          StorageDead(_1);
+          return;
+      }
+  }
+  
+  alloc1 (static: STAT, size: 4, align: 4) {
+      ╾─alloc15─╼                                     │ ╾──╼
+  }
+  
+  alloc15 (size: 16, align: 4) {
+      01 00 00 00 00 00 e0 40 0d 00 00 00 05 __ __ __ │ .......@.....░░░
+  }
+  
diff --git a/tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.64bit.diff
new file mode 100644
index 00000000000..71a28f2165b
--- /dev/null
+++ b/tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.64bit.diff
@@ -0,0 +1,129 @@
+- // MIR for `main` before DataflowConstProp
++ // MIR for `main` after DataflowConstProp
+  
+  fn main() -> () {
+      let mut _0: ();
+      let mut _1: S;
+      let mut _3: i32;
+      let mut _5: i32;
+      let mut _6: i32;
+      let mut _11: BigStruct;
+      let mut _16: &&BigStruct;
+      let mut _17: &BigStruct;
+      let mut _18: &BigStruct;
+      let mut _19: &BigStruct;
+      let mut _20: &BigStruct;
+      let mut _21: &BigStruct;
+      scope 1 {
+          debug s => _1;
+          let _2: i32;
+          scope 2 {
+              debug a => _2;
+              let _4: i32;
+              scope 3 {
+                  debug b => _4;
+                  let _7: S;
+                  let _8: u8;
+                  let _9: f32;
+                  let _10: S;
+                  scope 4 {
+                      debug a => _7;
+                      debug b => _8;
+                      debug c => _9;
+                      debug d => _10;
+                      let _12: S;
+                      let _13: u8;
+                      let _14: f32;
+                      let _15: S;
+                      scope 5 {
+                          debug a => _12;
+                          debug b => _13;
+                          debug c => _14;
+                          debug d => _15;
+                      }
+                  }
+              }
+          }
+      }
+  
+      bb0: {
+          StorageLive(_1);
+          _1 = S(const 1_i32);
+          StorageLive(_2);
+          StorageLive(_3);
+-         _3 = (_1.0: i32);
+-         _2 = Add(move _3, const 2_i32);
++         _3 = const 1_i32;
++         _2 = const 3_i32;
+          StorageDead(_3);
+          (_1.0: i32) = const 3_i32;
+          StorageLive(_4);
+          StorageLive(_5);
+-         _5 = _2;
++         _5 = const 3_i32;
+          StorageLive(_6);
+-         _6 = (_1.0: i32);
+-         _4 = Add(move _5, move _6);
++         _6 = const 3_i32;
++         _4 = const 6_i32;
+          StorageDead(_6);
+          StorageDead(_5);
+          StorageLive(_11);
+          _11 = const _;
+          StorageLive(_7);
+-         _7 = (_11.0: S);
++         _7 = const S(1_i32);
+          StorageLive(_8);
+-         _8 = (_11.1: u8);
++         _8 = const 5_u8;
+          StorageLive(_9);
+-         _9 = (_11.2: f32);
++         _9 = const 7f32;
+          StorageLive(_10);
+-         _10 = (_11.3: S);
++         _10 = const S(13_i32);
+          StorageDead(_11);
+          StorageLive(_16);
+          _16 = const {alloc1: &&BigStruct};
+          _17 = deref_copy (*_16);
+          StorageLive(_12);
+          _18 = deref_copy (*_16);
+-         _12 = ((*_18).0: S);
++         _12 = const S(1_i32);
+          StorageLive(_13);
+          _19 = deref_copy (*_16);
+-         _13 = ((*_19).1: u8);
++         _13 = const 5_u8;
+          StorageLive(_14);
+          _20 = deref_copy (*_16);
+-         _14 = ((*_20).2: f32);
++         _14 = const 7f32;
+          StorageLive(_15);
+          _21 = deref_copy (*_16);
+-         _15 = ((*_21).3: S);
++         _15 = const S(13_i32);
+          StorageDead(_16);
+          _0 = const ();
+          StorageDead(_15);
+          StorageDead(_14);
+          StorageDead(_13);
+          StorageDead(_12);
+          StorageDead(_10);
+          StorageDead(_9);
+          StorageDead(_8);
+          StorageDead(_7);
+          StorageDead(_4);
+          StorageDead(_2);
+          StorageDead(_1);
+          return;
+      }
+  }
+  
+  alloc1 (static: STAT, size: 8, align: 8) {
+      ╾───────alloc15───────╼                         │ ╾──────╼
+  }
+  
+  alloc15 (size: 16, align: 4) {
+      01 00 00 00 00 00 e0 40 0d 00 00 00 05 __ __ __ │ .......@.....░░░
+  }
+  
diff --git a/tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.diff b/tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.diff
deleted file mode 100644
index 914bc8ac47e..00000000000
--- a/tests/mir-opt/dataflow-const-prop/struct.main.DataflowConstProp.diff
+++ /dev/null
@@ -1,51 +0,0 @@
-- // MIR for `main` before DataflowConstProp
-+ // MIR for `main` after DataflowConstProp
-  
-  fn main() -> () {
-      let mut _0: ();
-      let mut _1: S;
-      let mut _3: i32;
-      let mut _5: i32;
-      let mut _6: i32;
-      scope 1 {
-          debug s => _1;
-          let _2: i32;
-          scope 2 {
-              debug a => _2;
-              let _4: i32;
-              scope 3 {
-                  debug b => _4;
-              }
-          }
-      }
-  
-      bb0: {
-          StorageLive(_1);
-          _1 = S(const 1_i32);
-          StorageLive(_2);
-          StorageLive(_3);
--         _3 = (_1.0: i32);
--         _2 = Add(move _3, const 2_i32);
-+         _3 = const 1_i32;
-+         _2 = const 3_i32;
-          StorageDead(_3);
-          (_1.0: i32) = const 3_i32;
-          StorageLive(_4);
-          StorageLive(_5);
--         _5 = _2;
-+         _5 = const 3_i32;
-          StorageLive(_6);
--         _6 = (_1.0: i32);
--         _4 = Add(move _5, move _6);
-+         _6 = const 3_i32;
-+         _4 = const 6_i32;
-          StorageDead(_6);
-          StorageDead(_5);
-          _0 = const ();
-          StorageDead(_4);
-          StorageDead(_2);
-          StorageDead(_1);
-          return;
-      }
-  }
-  
diff --git a/tests/mir-opt/dataflow-const-prop/struct.rs b/tests/mir-opt/dataflow-const-prop/struct.rs
index 841b279e03e..e92a1676d3f 100644
--- a/tests/mir-opt/dataflow-const-prop/struct.rs
+++ b/tests/mir-opt/dataflow-const-prop/struct.rs
@@ -1,11 +1,22 @@
 // unit-test: DataflowConstProp
+// EMIT_MIR_FOR_EACH_BIT_WIDTH
 
+#[derive(Copy, Clone)]
 struct S(i32);
 
+#[derive(Copy, Clone)]
+struct BigStruct(S, u8, f32, S);
+
 // EMIT_MIR struct.main.DataflowConstProp.diff
 fn main() {
     let mut s = S(1);
     let a = s.0 + 2;
     s.0 = 3;
     let b = a + s.0;
+
+    const VAL: BigStruct = BigStruct(S(1), 5, 7., S(13));
+    let BigStruct(a, b, c, d) = VAL;
+
+    static STAT: &BigStruct = &BigStruct(S(1), 5, 7., S(13));
+    let BigStruct(a, b, c, d) = *STAT;
 }
diff --git a/tests/mir-opt/dont_inline_type_id.call.Inline.diff b/tests/mir-opt/dont_inline_type_id.call.Inline.diff
new file mode 100644
index 00000000000..80cfe07b0cb
--- /dev/null
+++ b/tests/mir-opt/dont_inline_type_id.call.Inline.diff
@@ -0,0 +1,20 @@
+- // MIR for `call` before Inline
++ // MIR for `call` after Inline
+  
+  fn call(_1: &T) -> TypeId {
+      debug s => _1;
+      let mut _0: std::any::TypeId;
+      let mut _2: &T;
+  
+      bb0: {
+          StorageLive(_2);
+          _2 = &(*_1);
+          _0 = <T as Any>::type_id(move _2) -> [return: bb1, unwind unreachable];
+      }
+  
+      bb1: {
+          StorageDead(_2);
+          return;
+      }
+  }
+  
diff --git a/tests/mir-opt/dont_inline_type_id.rs b/tests/mir-opt/dont_inline_type_id.rs
new file mode 100644
index 00000000000..d8a56636094
--- /dev/null
+++ b/tests/mir-opt/dont_inline_type_id.rs
@@ -0,0 +1,15 @@
+// unit-test: Inline
+// compile-flags: --crate-type=lib -C panic=abort
+
+use std::any::Any;
+use std::any::TypeId;
+
+struct A<T: ?Sized + 'static> {
+    a: i32,
+    b: T,
+}
+
+// EMIT_MIR dont_inline_type_id.call.Inline.diff
+pub fn call<T: ?Sized + 'static>(s: &T) -> TypeId {
+    s.type_id()
+}
diff --git a/tests/mir-opt/enum_opt.cand.EnumSizeOpt.32bit.diff b/tests/mir-opt/enum_opt.cand.EnumSizeOpt.32bit.diff
index 9d9a7a1e485..ec5f5c1f1fc 100644
--- a/tests/mir-opt/enum_opt.cand.EnumSizeOpt.32bit.diff
+++ b/tests/mir-opt/enum_opt.cand.EnumSizeOpt.32bit.diff
@@ -64,5 +64,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc15 (size: 8, align: 4) {
++     02 00 00 00 05 20 00 00                         │ ..... ..
   }
   
diff --git a/tests/mir-opt/enum_opt.cand.EnumSizeOpt.64bit.diff b/tests/mir-opt/enum_opt.cand.EnumSizeOpt.64bit.diff
index 9d9a7a1e485..9bf8637ec76 100644
--- a/tests/mir-opt/enum_opt.cand.EnumSizeOpt.64bit.diff
+++ b/tests/mir-opt/enum_opt.cand.EnumSizeOpt.64bit.diff
@@ -64,5 +64,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc15 (size: 16, align: 8) {
++     02 00 00 00 00 00 00 00 05 20 00 00 00 00 00 00 │ ......... ......
   }
   
diff --git a/tests/mir-opt/enum_opt.unin.EnumSizeOpt.32bit.diff b/tests/mir-opt/enum_opt.unin.EnumSizeOpt.32bit.diff
index 4306f38b82a..7dc6d21a907 100644
--- a/tests/mir-opt/enum_opt.unin.EnumSizeOpt.32bit.diff
+++ b/tests/mir-opt/enum_opt.unin.EnumSizeOpt.32bit.diff
@@ -64,5 +64,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc14 (size: 8, align: 4) {
++     05 20 00 00 01 00 00 00                         │ . ......
   }
   
diff --git a/tests/mir-opt/enum_opt.unin.EnumSizeOpt.64bit.diff b/tests/mir-opt/enum_opt.unin.EnumSizeOpt.64bit.diff
index 4306f38b82a..0b000876a86 100644
--- a/tests/mir-opt/enum_opt.unin.EnumSizeOpt.64bit.diff
+++ b/tests/mir-opt/enum_opt.unin.EnumSizeOpt.64bit.diff
@@ -64,5 +64,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc14 (size: 16, align: 8) {
++     05 20 00 00 00 00 00 00 01 00 00 00 00 00 00 00 │ . ..............
   }
   
diff --git a/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-abort.mir b/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-abort.mir
index acbb7904985..958078b9706 100644
--- a/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-abort.mir
+++ b/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-abort.mir
@@ -2,11 +2,7 @@
 /* generator_layout = GeneratorLayout {
     field_tys: {
         _0: GeneratorSavedTy {
-            ty: Adt(
-                std::string::String,
-                [
-                ],
-            ),
+            ty: std::string::String,
             source_info: SourceInfo {
                 span: $DIR/generator_drop_cleanup.rs:11:13: 11:15 (#0),
                 scope: scope[0],
diff --git a/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-unwind.mir b/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-unwind.mir
index c17d4421542..7e050e585b1 100644
--- a/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-unwind.mir
+++ b/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-unwind.mir
@@ -2,11 +2,7 @@
 /* generator_layout = GeneratorLayout {
     field_tys: {
         _0: GeneratorSavedTy {
-            ty: Adt(
-                std::string::String,
-                [
-                ],
-            ),
+            ty: std::string::String,
             source_info: SourceInfo {
                 span: $DIR/generator_drop_cleanup.rs:11:13: 11:15 (#0),
                 scope: scope[0],
diff --git a/tests/mir-opt/generator_tiny.main-{closure#0}.generator_resume.0.mir b/tests/mir-opt/generator_tiny.main-{closure#0}.generator_resume.0.mir
index e33f5f59de1..13d703b908c 100644
--- a/tests/mir-opt/generator_tiny.main-{closure#0}.generator_resume.0.mir
+++ b/tests/mir-opt/generator_tiny.main-{closure#0}.generator_resume.0.mir
@@ -2,11 +2,7 @@
 /* generator_layout = GeneratorLayout {
     field_tys: {
         _0: GeneratorSavedTy {
-            ty: Adt(
-                HasDrop,
-                [
-                ],
-            ),
+            ty: HasDrop,
             source_info: SourceInfo {
                 span: $DIR/generator_tiny.rs:20:13: 20:15 (#0),
                 scope: scope[0],
diff --git a/tests/mir-opt/inline_generically_if_sized.call.Inline.diff b/tests/mir-opt/inline_generically_if_sized.call.Inline.diff
new file mode 100644
index 00000000000..0cf4565dc99
--- /dev/null
+++ b/tests/mir-opt/inline_generically_if_sized.call.Inline.diff
@@ -0,0 +1,24 @@
+- // MIR for `call` before Inline
++ // MIR for `call` after Inline
+  
+  fn call(_1: &T) -> i32 {
+      debug s => _1;
+      let mut _0: i32;
+      let mut _2: &T;
++     scope 1 (inlined <T as Foo>::bar) {
++         debug self => _2;
++     }
+  
+      bb0: {
+          StorageLive(_2);
+          _2 = &(*_1);
+-         _0 = <T as Foo>::bar(move _2) -> [return: bb1, unwind unreachable];
+-     }
+- 
+-     bb1: {
++         _0 = const 0_i32;
+          StorageDead(_2);
+          return;
+      }
+  }
+  
diff --git a/tests/mir-opt/inline_generically_if_sized.rs b/tests/mir-opt/inline_generically_if_sized.rs
new file mode 100644
index 00000000000..1acfff7a56b
--- /dev/null
+++ b/tests/mir-opt/inline_generically_if_sized.rs
@@ -0,0 +1,17 @@
+// unit-test: Inline
+// compile-flags: --crate-type=lib -C panic=abort
+
+trait Foo {
+    fn bar(&self) -> i32;
+}
+
+impl<T> Foo for T {
+    fn bar(&self) -> i32 {
+        0
+    }
+}
+
+// EMIT_MIR inline_generically_if_sized.call.Inline.diff
+pub fn call<T>(s: &T) -> i32 {
+    s.bar()
+}
diff --git a/tests/mir-opt/issue_99325.main.built.after.32bit.mir b/tests/mir-opt/issue_99325.main.built.after.32bit.mir
index b6a673b6355..132b713356e 100644
--- a/tests/mir-opt/issue_99325.main.built.after.32bit.mir
+++ b/tests/mir-opt/issue_99325.main.built.after.32bit.mir
@@ -1,8 +1,8 @@
 // MIR for `main` after built
 
 | User Type Annotations
-| 0: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [Const { ty: &ReStatic [u8; Const { ty: usize, kind: Leaf(0x00000004) }], kind: Branch([Leaf(0x41), Leaf(0x41), Leaf(0x41), Leaf(0x41)]) }], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:12:16: 12:46, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">}
-| 1: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [Const { ty: &ReStatic [u8; Const { ty: usize, kind: Leaf(0x00000004) }], kind: UnevaluatedConst { def: DefId(0:8 ~ issue_99325[22bb]::main::{constant#1}), args: [] } }], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:13:16: 13:68, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">}
+| 0: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [&*b"AAAA"], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:12:16: 12:46, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">}
+| 1: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [UnevaluatedConst { def: DefId(0:8 ~ issue_99325[22bb]::main::{constant#1}), args: [] }: &ReStatic [u8; 4_usize]], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:13:16: 13:68, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">}
 |
 fn main() -> () {
     let mut _0: ();
diff --git a/tests/mir-opt/issue_99325.main.built.after.64bit.mir b/tests/mir-opt/issue_99325.main.built.after.64bit.mir
index 9d112cfa20a..132b713356e 100644
--- a/tests/mir-opt/issue_99325.main.built.after.64bit.mir
+++ b/tests/mir-opt/issue_99325.main.built.after.64bit.mir
@@ -1,8 +1,8 @@
 // MIR for `main` after built
 
 | User Type Annotations
-| 0: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [Const { ty: &ReStatic [u8; Const { ty: usize, kind: Leaf(0x0000000000000004) }], kind: Branch([Leaf(0x41), Leaf(0x41), Leaf(0x41), Leaf(0x41)]) }], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:12:16: 12:46, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">}
-| 1: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [Const { ty: &ReStatic [u8; Const { ty: usize, kind: Leaf(0x0000000000000004) }], kind: UnevaluatedConst { def: DefId(0:8 ~ issue_99325[22bb]::main::{constant#1}), args: [] } }], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:13:16: 13:68, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">}
+| 0: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [&*b"AAAA"], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:12:16: 12:46, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">}
+| 1: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [UnevaluatedConst { def: DefId(0:8 ~ issue_99325[22bb]::main::{constant#1}), args: [] }: &ReStatic [u8; 4_usize]], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:13:16: 13:68, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">}
 |
 fn main() -> () {
     let mut _0: ();
diff --git a/tests/mir-opt/nll/region_subtyping_basic.main.nll.0.32bit.mir b/tests/mir-opt/nll/region_subtyping_basic.main.nll.0.32bit.mir
index 56b0f816573..c581d0f8471 100644
--- a/tests/mir-opt/nll/region_subtyping_basic.main.nll.0.32bit.mir
+++ b/tests/mir-opt/nll/region_subtyping_basic.main.nll.0.32bit.mir
@@ -22,7 +22,7 @@
 |
 fn main() -> () {
     let mut _0: ();
-    let mut _1: [usize; Const { ty: usize, kind: Leaf(0x00000003) }];
+    let mut _1: [usize; ValTree(Leaf(0x00000003): usize)];
     let _3: usize;
     let mut _4: usize;
     let mut _5: bool;
diff --git a/tests/mir-opt/nll/region_subtyping_basic.main.nll.0.64bit.mir b/tests/mir-opt/nll/region_subtyping_basic.main.nll.0.64bit.mir
index 83b851eed74..48243e34d08 100644
--- a/tests/mir-opt/nll/region_subtyping_basic.main.nll.0.64bit.mir
+++ b/tests/mir-opt/nll/region_subtyping_basic.main.nll.0.64bit.mir
@@ -22,7 +22,7 @@
 |
 fn main() -> () {
     let mut _0: ();
-    let mut _1: [usize; Const { ty: usize, kind: Leaf(0x0000000000000003) }];
+    let mut _1: [usize; ValTree(Leaf(0x0000000000000003): usize)];
     let _3: usize;
     let mut _4: usize;
     let mut _5: bool;
diff --git a/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.32bit.panic-abort.diff b/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.32bit.panic-abort.diff
index 2c607b4c055..681e9666e0f 100644
--- a/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.32bit.panic-abort.diff
+++ b/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.32bit.panic-abort.diff
@@ -55,5 +55,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc5 (size: 8, align: 4) {
++     04 00 00 00 00 __ __ __                         │ .....░░░
   }
   
diff --git a/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.32bit.panic-unwind.diff b/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.32bit.panic-unwind.diff
index b6929f3f93c..db16b8d82d2 100644
--- a/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.32bit.panic-unwind.diff
+++ b/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.32bit.panic-unwind.diff
@@ -55,5 +55,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc5 (size: 8, align: 4) {
++     04 00 00 00 00 __ __ __                         │ .....░░░
   }
   
diff --git a/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.64bit.panic-abort.diff b/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.64bit.panic-abort.diff
index 2c607b4c055..681e9666e0f 100644
--- a/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.64bit.panic-abort.diff
+++ b/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.64bit.panic-abort.diff
@@ -55,5 +55,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc5 (size: 8, align: 4) {
++     04 00 00 00 00 __ __ __                         │ .....░░░
   }
   
diff --git a/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.64bit.panic-unwind.diff b/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.64bit.panic-unwind.diff
index b6929f3f93c..db16b8d82d2 100644
--- a/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.64bit.panic-unwind.diff
+++ b/tests/mir-opt/pre-codegen/optimizes_into_variable.main.ConstProp.64bit.panic-unwind.diff
@@ -55,5 +55,9 @@
           StorageDead(_1);
           return;
       }
++ }
++ 
++ alloc5 (size: 8, align: 4) {
++     04 00 00 00 00 __ __ __                         │ .....░░░
   }
   
diff --git a/tests/mir-opt/pre-codegen/spans.outer.PreCodegen.after.panic-abort.mir b/tests/mir-opt/pre-codegen/spans.outer.PreCodegen.after.panic-abort.mir
index 1d3405a9afe..18a663d9f9e 100644
--- a/tests/mir-opt/pre-codegen/spans.outer.PreCodegen.after.panic-abort.mir
+++ b/tests/mir-opt/pre-codegen/spans.outer.PreCodegen.after.panic-abort.mir
@@ -11,7 +11,7 @@ fn outer(_1: u8) -> u8 {
         _0 = inner(move _2) -> [return: bb1, unwind unreachable]; // scope 0 at $DIR/spans.rs:10:5: 10:14
                                          // mir::Constant
                                          // + span: $DIR/spans.rs:10:5: 10:10
-                                         // + literal: Const { ty: for<'a> fn(&'a u8) -> u8 {inner}, val: Value(<ZST>) }
+                                         // + literal: Const { ty: for<'a> fn(&'a u8) -> u8 {inner}, val: Value(inner) }
     }
 
     bb1: {
diff --git a/tests/mir-opt/pre-codegen/spans.outer.PreCodegen.after.panic-unwind.mir b/tests/mir-opt/pre-codegen/spans.outer.PreCodegen.after.panic-unwind.mir
index 285b6e41314..1c02fb72bcd 100644
--- a/tests/mir-opt/pre-codegen/spans.outer.PreCodegen.after.panic-unwind.mir
+++ b/tests/mir-opt/pre-codegen/spans.outer.PreCodegen.after.panic-unwind.mir
@@ -11,7 +11,7 @@ fn outer(_1: u8) -> u8 {
         _0 = inner(move _2) -> [return: bb1, unwind continue]; // scope 0 at $DIR/spans.rs:10:5: 10:14
                                          // mir::Constant
                                          // + span: $DIR/spans.rs:10:5: 10:10
-                                         // + literal: Const { ty: for<'a> fn(&'a u8) -> u8 {inner}, val: Value(<ZST>) }
+                                         // + literal: Const { ty: for<'a> fn(&'a u8) -> u8 {inner}, val: Value(inner) }
     }
 
     bb1: {
diff --git a/tests/pretty/tests-are-sorted.pp b/tests/pretty/tests-are-sorted.pp
index 7d7f682130d..fd9386be8f3 100644
--- a/tests/pretty/tests-are-sorted.pp
+++ b/tests/pretty/tests-are-sorted.pp
@@ -79,7 +79,7 @@ pub const a_test: test::TestDescAndFn =
     };
 fn a_test() {}
 #[rustc_main]
-#[no_coverage]
+#[coverage(off)]
 pub fn main() -> () {
     extern crate test;
     test::test_main_static(&[&a_test, &m_test, &z_test])
diff --git a/tests/run-coverage/closure.coverage b/tests/run-coverage/closure.coverage
index 930348dc431..67014f792c8 100644
--- a/tests/run-coverage/closure.coverage
+++ b/tests/run-coverage/closure.coverage
@@ -76,8 +76,8 @@
    LL|      1|    some_string = None;
    LL|      1|    let
    LL|      1|        a
-   LL|      1|    =
-   LL|      1|        ||
+   LL|       |    =
+   LL|       |        ||
    LL|      1|    {
    LL|      1|        let mut countdown = 0;
    LL|      1|        if is_false {
@@ -98,8 +98,8 @@
    LL|      1|
    LL|      1|    let
    LL|      1|        quote_closure
-   LL|      1|    =
-   LL|      1|        |val|
+   LL|       |    =
+   LL|       |        |val|
    LL|      5|    {
    LL|      5|        let mut countdown = 0;
    LL|      5|        if is_false {
@@ -186,7 +186,7 @@
    LL|       |    ;
    LL|       |
    LL|      1|    let short_used_not_covered_closure_line_break_block_embedded_branch =
-   LL|      1|        | _unused_arg: u8 |
+   LL|       |        | _unused_arg: u8 |
    LL|      0|        {
    LL|      0|            println!(
    LL|      0|                "not called: {}",
@@ -196,7 +196,7 @@
    LL|       |    ;
    LL|       |
    LL|      1|    let short_used_covered_closure_line_break_no_block_embedded_branch =
-   LL|      1|        | _unused_arg: u8 |
+   LL|       |        | _unused_arg: u8 |
    LL|      1|            println!(
    LL|      1|                "not called: {}",
    LL|      1|                if is_true { "check" } else { "me" }
@@ -205,7 +205,7 @@
    LL|       |    ;
    LL|       |
    LL|      1|    let short_used_covered_closure_line_break_block_embedded_branch =
-   LL|      1|        | _unused_arg: u8 |
+   LL|       |        | _unused_arg: u8 |
    LL|      1|        {
    LL|      1|            println!(
    LL|      1|                "not called: {}",
diff --git a/tests/run-coverage/closure_bug.coverage b/tests/run-coverage/closure_bug.coverage
new file mode 100644
index 00000000000..f3299834bce
--- /dev/null
+++ b/tests/run-coverage/closure_bug.coverage
@@ -0,0 +1,53 @@
+   LL|       |// Regression test for #115930.
+   LL|       |// All of these closures are identical, and should produce identical output in
+   LL|       |// the coverage report. However, an unstable sort was causing them to be treated
+   LL|       |// inconsistently when preparing coverage spans.
+   LL|       |
+   LL|      1|fn main() {
+   LL|      1|    let truthy = std::env::args().len() == 1;
+   LL|      1|
+   LL|      1|    let a
+   LL|       |        =
+   LL|       |        |
+   LL|       |        |
+   LL|      2|        if truthy { true } else { false };
+                                                ^0
+   LL|       |
+   LL|      1|    a();
+   LL|      1|    if truthy { a(); }
+                                    ^0
+   LL|       |
+   LL|      1|    let b
+   LL|       |        =
+   LL|       |        |
+   LL|       |        |
+   LL|      2|        if truthy { true } else { false };
+                                                ^0
+   LL|       |
+   LL|      1|    b();
+   LL|      1|    if truthy { b(); }
+                                    ^0
+   LL|       |
+   LL|      1|    let c
+   LL|       |        =
+   LL|       |        |
+   LL|       |        |
+   LL|      2|        if truthy { true } else { false };
+                                                ^0
+   LL|       |
+   LL|      1|    c();
+   LL|      1|    if truthy { c(); }
+                                    ^0
+   LL|       |
+   LL|      1|    let d
+   LL|       |        =
+   LL|       |        |
+   LL|       |        |
+   LL|      2|        if truthy { true } else { false };
+                                                ^0
+   LL|       |
+   LL|      1|    d();
+   LL|      1|    if truthy { d(); }
+                                    ^0
+   LL|      1|}
+
diff --git a/tests/run-coverage/closure_bug.rs b/tests/run-coverage/closure_bug.rs
new file mode 100644
index 00000000000..739bc5f0b51
--- /dev/null
+++ b/tests/run-coverage/closure_bug.rs
@@ -0,0 +1,44 @@
+// Regression test for #115930.
+// All of these closures are identical, and should produce identical output in
+// the coverage report. However, an unstable sort was causing them to be treated
+// inconsistently when preparing coverage spans.
+
+fn main() {
+    let truthy = std::env::args().len() == 1;
+
+    let a
+        =
+        |
+        |
+        if truthy { true } else { false };
+
+    a();
+    if truthy { a(); }
+
+    let b
+        =
+        |
+        |
+        if truthy { true } else { false };
+
+    b();
+    if truthy { b(); }
+
+    let c
+        =
+        |
+        |
+        if truthy { true } else { false };
+
+    c();
+    if truthy { c(); }
+
+    let d
+        =
+        |
+        |
+        if truthy { true } else { false };
+
+    d();
+    if truthy { d(); }
+}
diff --git a/tests/run-coverage/closure_macro.coverage b/tests/run-coverage/closure_macro.coverage
index 1bfd2013da8..0f2c917e090 100644
--- a/tests/run-coverage/closure_macro.coverage
+++ b/tests/run-coverage/closure_macro.coverage
@@ -1,5 +1,5 @@
    LL|       |// compile-flags: --edition=2018
-   LL|       |#![feature(no_coverage)]
+   LL|       |#![feature(coverage_attribute)]
    LL|       |
    LL|       |macro_rules! bail {
    LL|       |    ($msg:literal $(,)?) => {
diff --git a/tests/run-coverage/closure_macro.rs b/tests/run-coverage/closure_macro.rs
index 5e3b00d1ef5..9b289141c2e 100644
--- a/tests/run-coverage/closure_macro.rs
+++ b/tests/run-coverage/closure_macro.rs
@@ -1,5 +1,5 @@
 // compile-flags: --edition=2018
-#![feature(no_coverage)]
+#![feature(coverage_attribute)]
 
 macro_rules! bail {
     ($msg:literal $(,)?) => {
diff --git a/tests/run-coverage/closure_macro_async.coverage b/tests/run-coverage/closure_macro_async.coverage
index 018e3160e4f..74247f1bc6f 100644
--- a/tests/run-coverage/closure_macro_async.coverage
+++ b/tests/run-coverage/closure_macro_async.coverage
@@ -1,5 +1,5 @@
    LL|       |// compile-flags: --edition=2018
-   LL|       |#![feature(no_coverage)]
+   LL|       |#![feature(coverage_attribute)]
    LL|       |
    LL|       |macro_rules! bail {
    LL|       |    ($msg:literal $(,)?) => {
@@ -40,7 +40,7 @@
    LL|      1|    Ok(())
    LL|      1|}
    LL|       |
-   LL|       |#[no_coverage]
+   LL|       |#[coverage(off)]
    LL|       |fn main() {
    LL|       |    executor::block_on(test()).unwrap();
    LL|       |}
@@ -52,18 +52,18 @@
    LL|       |        task::{Context, Poll, RawWaker, RawWakerVTable, Waker},
    LL|       |    };
    LL|       |
-   LL|       |    #[no_coverage]
+   LL|       |    #[coverage(off)]
    LL|       |    pub fn block_on<F: Future>(mut future: F) -> F::Output {
    LL|       |        let mut future = unsafe { Pin::new_unchecked(&mut future) };
    LL|       |        use std::hint::unreachable_unchecked;
    LL|       |        static VTABLE: RawWakerVTable = RawWakerVTable::new(
-   LL|       |            #[no_coverage]
+   LL|       |            #[coverage(off)]
    LL|       |            |_| unsafe { unreachable_unchecked() }, // clone
-   LL|       |            #[no_coverage]
+   LL|       |            #[coverage(off)]
    LL|       |            |_| unsafe { unreachable_unchecked() }, // wake
-   LL|       |            #[no_coverage]
+   LL|       |            #[coverage(off)]
    LL|       |            |_| unsafe { unreachable_unchecked() }, // wake_by_ref
-   LL|       |            #[no_coverage]
+   LL|       |            #[coverage(off)]
    LL|       |            |_| (),
    LL|       |        );
    LL|       |        let waker = unsafe { Waker::from_raw(RawWaker::new(core::ptr::null(), &VTABLE)) };
diff --git a/tests/run-coverage/closure_macro_async.rs b/tests/run-coverage/closure_macro_async.rs
index 3d6bdb38a2a..b4275599e59 100644
--- a/tests/run-coverage/closure_macro_async.rs
+++ b/tests/run-coverage/closure_macro_async.rs
@@ -1,5 +1,5 @@
 // compile-flags: --edition=2018
-#![feature(no_coverage)]
+#![feature(coverage_attribute)]
 
 macro_rules! bail {
     ($msg:literal $(,)?) => {
@@ -39,7 +39,7 @@ pub async fn test() -> Result<(), String> {
     Ok(())
 }
 
-#[no_coverage]
+#[coverage(off)]
 fn main() {
     executor::block_on(test()).unwrap();
 }
@@ -51,18 +51,18 @@ mod executor {
         task::{Context, Poll, RawWaker, RawWakerVTable, Waker},
     };
 
-    #[no_coverage]
+    #[coverage(off)]
     pub fn block_on<F: Future>(mut future: F) -> F::Output {
         let mut future = unsafe { Pin::new_unchecked(&mut future) };
         use std::hint::unreachable_unchecked;
         static VTABLE: RawWakerVTable = RawWakerVTable::new(
-            #[no_coverage]
+            #[coverage(off)]
             |_| unsafe { unreachable_unchecked() }, // clone
-            #[no_coverage]
+            #[coverage(off)]
             |_| unsafe { unreachable_unchecked() }, // wake
-            #[no_coverage]
+            #[coverage(off)]
             |_| unsafe { unreachable_unchecked() }, // wake_by_ref
-            #[no_coverage]
+            #[coverage(off)]
             |_| (),
         );
         let waker = unsafe { Waker::from_raw(RawWaker::new(core::ptr::null(), &VTABLE)) };
diff --git a/tests/run-coverage/no_cov_crate.coverage b/tests/run-coverage/no_cov_crate.coverage
index 73f6fbd0c2b..f5a0322bf3e 100644
--- a/tests/run-coverage/no_cov_crate.coverage
+++ b/tests/run-coverage/no_cov_crate.coverage
@@ -1,17 +1,17 @@
-   LL|       |// Enables `no_coverage` on the entire crate
-   LL|       |#![feature(no_coverage)]
+   LL|       |// Enables `coverage(off)` on the entire crate
+   LL|       |#![feature(coverage_attribute)]
    LL|       |
-   LL|       |#[no_coverage]
+   LL|       |#[coverage(off)]
    LL|       |fn do_not_add_coverage_1() {
    LL|       |    println!("called but not covered");
    LL|       |}
    LL|       |
    LL|       |fn do_not_add_coverage_2() {
-   LL|       |    #![no_coverage]
+   LL|       |    #![coverage(off)]
    LL|       |    println!("called but not covered");
    LL|       |}
    LL|       |
-   LL|       |#[no_coverage]
+   LL|       |#[coverage(off)]
    LL|       |#[allow(dead_code)]
    LL|       |fn do_not_add_coverage_not_called() {
    LL|       |    println!("not called and not covered");
@@ -33,7 +33,7 @@
    LL|       |// FIXME: These test-cases illustrate confusing results of nested functions.
    LL|       |// See https://github.com/rust-lang/rust/issues/93319
    LL|       |mod nested_fns {
-   LL|       |    #[no_coverage]
+   LL|       |    #[coverage(off)]
    LL|       |    pub fn outer_not_covered(is_true: bool) {
    LL|      1|        fn inner(is_true: bool) {
    LL|      1|            if is_true {
@@ -50,7 +50,7 @@
    LL|      1|        println!("called and covered");
    LL|      1|        inner_not_covered(is_true);
    LL|      1|
-   LL|      1|        #[no_coverage]
+   LL|      1|        #[coverage(off)]
    LL|      1|        fn inner_not_covered(is_true: bool) {
    LL|      1|            if is_true {
    LL|      1|                println!("called but not covered");
diff --git a/tests/run-coverage/no_cov_crate.rs b/tests/run-coverage/no_cov_crate.rs
index 5b748aeefb7..e12e4bc55e3 100644
--- a/tests/run-coverage/no_cov_crate.rs
+++ b/tests/run-coverage/no_cov_crate.rs
@@ -1,17 +1,17 @@
-// Enables `no_coverage` on the entire crate
-#![feature(no_coverage)]
+// Enables `coverage(off)` on the entire crate
+#![feature(coverage_attribute)]
 
-#[no_coverage]
+#[coverage(off)]
 fn do_not_add_coverage_1() {
     println!("called but not covered");
 }
 
 fn do_not_add_coverage_2() {
-    #![no_coverage]
+    #![coverage(off)]
     println!("called but not covered");
 }
 
-#[no_coverage]
+#[coverage(off)]
 #[allow(dead_code)]
 fn do_not_add_coverage_not_called() {
     println!("not called and not covered");
@@ -33,7 +33,7 @@ fn add_coverage_not_called() {
 // FIXME: These test-cases illustrate confusing results of nested functions.
 // See https://github.com/rust-lang/rust/issues/93319
 mod nested_fns {
-    #[no_coverage]
+    #[coverage(off)]
     pub fn outer_not_covered(is_true: bool) {
         fn inner(is_true: bool) {
             if is_true {
@@ -50,7 +50,7 @@ mod nested_fns {
         println!("called and covered");
         inner_not_covered(is_true);
 
-        #[no_coverage]
+        #[coverage(off)]
         fn inner_not_covered(is_true: bool) {
             if is_true {
                 println!("called but not covered");
diff --git a/tests/run-make-fulldeps/obtain-borrowck/driver.rs b/tests/run-make-fulldeps/obtain-borrowck/driver.rs
index 04c551cf4bb..b59a65a713f 100644
--- a/tests/run-make-fulldeps/obtain-borrowck/driver.rs
+++ b/tests/run-make-fulldeps/obtain-borrowck/driver.rs
@@ -27,7 +27,7 @@ use rustc_interface::{Config, Queries};
 use rustc_middle::query::queries::mir_borrowck::ProvidedValue;
 use rustc_middle::query::{ExternProviders, Providers};
 use rustc_middle::ty::TyCtxt;
-use rustc_session::{Session, EarlyErrorHandler};
+use rustc_session::Session;
 use std::cell::RefCell;
 use std::collections::HashMap;
 use std::thread_local;
@@ -58,7 +58,6 @@ impl rustc_driver::Callbacks for CompilerCalls {
     // the result.
     fn after_analysis<'tcx>(
         &mut self,
-        _handler: &EarlyErrorHandler,
         compiler: &Compiler,
         queries: &'tcx Queries<'tcx>,
     ) -> Compilation {
diff --git a/tests/run-make/dump-ice-to-disk/check.sh b/tests/run-make/dump-ice-to-disk/check.sh
index 91109596a45..ab6f9ab6018 100644
--- a/tests/run-make/dump-ice-to-disk/check.sh
+++ b/tests/run-make/dump-ice-to-disk/check.sh
@@ -22,8 +22,8 @@ rm $TMPDIR/rustc-ice-*.txt
 # Explicitly disabling ICE dump
 export RUSTC_ICE=0
 $RUSTC src/lib.rs -Z treat-err-as-bug=1 1>$TMPDIR/rust-test-disabled.log 2>&1
-should_be_empty_tmp=$(ls -l $TMPDIR/rustc-ice-*.txt | wc -l)
-should_be_empty_dot=$(ls -l ./rustc-ice-*.txt | wc -l)
+should_be_empty_tmp=$(ls -l $TMPDIR/rustc-ice-*.txt 2>/dev/null | wc -l)
+should_be_empty_dot=$(ls -l ./rustc-ice-*.txt 2>/dev/null | wc -l)
 
 echo "#### ICE Dump content:"
 echo $content
diff --git a/tests/run-make/emit-path-unhashed/Makefile b/tests/run-make/emit-path-unhashed/Makefile
index 74047fe5f86..611f8578140 100644
--- a/tests/run-make/emit-path-unhashed/Makefile
+++ b/tests/run-make/emit-path-unhashed/Makefile
@@ -5,10 +5,10 @@ OUT=$(TMPDIR)/emit
 # --emit KIND=PATH should not affect crate hash vs --emit KIND
 all: $(OUT)/a/libfoo.rlib $(OUT)/b/libfoo.rlib $(OUT)/c/libfoo.rlib \
 		$(TMPDIR)/libfoo.rlib
-	$(RUSTC) -Zls $(TMPDIR)/libfoo.rlib > $(TMPDIR)/base.txt
-	$(RUSTC) -Zls $(OUT)/a/libfoo.rlib > $(TMPDIR)/a.txt
-	$(RUSTC) -Zls $(OUT)/b/libfoo.rlib > $(TMPDIR)/b.txt
-	$(RUSTC) -Zls $(OUT)/c/libfoo.rlib > $(TMPDIR)/c.txt
+	$(RUSTC) -Zls=root $(TMPDIR)/libfoo.rlib > $(TMPDIR)/base.txt
+	$(RUSTC) -Zls=root $(OUT)/a/libfoo.rlib > $(TMPDIR)/a.txt
+	$(RUSTC) -Zls=root $(OUT)/b/libfoo.rlib > $(TMPDIR)/b.txt
+	$(RUSTC) -Zls=root $(OUT)/c/libfoo.rlib > $(TMPDIR)/c.txt
 
 	diff $(TMPDIR)/base.txt $(TMPDIR)/a.txt
 	diff $(TMPDIR)/base.txt $(TMPDIR)/b.txt
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 de8ff0e5f89..f5981045b03 100644
--- a/tests/run-make/issue-88756-default-output/output-default.stdout
+++ b/tests/run-make/issue-88756-default-output/output-default.stdout
@@ -100,7 +100,7 @@ Options:
                         check if given theme is valid
         --resource-suffix PATH
                         suffix to add to CSS and JavaScript files, e.g.,
-                        "light.css" will become "light-suffix.css"
+                        "search-index.js" will become "search-index-suffix.js"
         --edition EDITION
                         edition to use when compiling rust code (default:
                         2015)
diff --git a/tests/run-make/ls-metadata/Makefile b/tests/run-make/ls-metadata/Makefile
index 123dd64e15c..f03569baef7 100644
--- a/tests/run-make/ls-metadata/Makefile
+++ b/tests/run-make/ls-metadata/Makefile
@@ -3,6 +3,6 @@ include ../tools.mk
 
 all:
 	$(RUSTC) foo.rs
-	$(RUSTC) -Z ls $(TMPDIR)/foo
+	$(RUSTC) -Z ls=root $(TMPDIR)/foo
 	touch $(TMPDIR)/bar
-	$(RUSTC) -Z ls $(TMPDIR)/bar
+	$(RUSTC) -Z ls=root $(TMPDIR)/bar
diff --git a/tests/run-make/lto-linkage-used-attr/Makefile b/tests/run-make/lto-linkage-used-attr/Makefile
new file mode 100644
index 00000000000..e78b83890ed
--- /dev/null
+++ b/tests/run-make/lto-linkage-used-attr/Makefile
@@ -0,0 +1,9 @@
+include ../tools.mk
+
+# Verify that the impl_* symbols are preserved. #108030
+# only-x86_64-unknown-linux-gnu
+# min-llvm-version: 17
+
+all:
+	$(RUSTC) -Cdebuginfo=0 -Copt-level=3 lib.rs
+	$(RUSTC) -Clto=fat -Cdebuginfo=0 -Copt-level=3 main.rs
diff --git a/tests/run-make/lto-linkage-used-attr/lib.rs b/tests/run-make/lto-linkage-used-attr/lib.rs
new file mode 100644
index 00000000000..0a92ea9cd22
--- /dev/null
+++ b/tests/run-make/lto-linkage-used-attr/lib.rs
@@ -0,0 +1,50 @@
+#![crate_type = "rlib"]
+#![crate_type = "cdylib"]
+
+#[macro_export]
+macro_rules! asm_func {
+    ($name:expr, $body:expr $(, $($args:tt)*)?) => {
+        core::arch::global_asm!(
+            concat!(
+                ".p2align 4\n",
+                ".hidden ", $name, "\n",
+                ".global ", $name, "\n",
+                ".type ", $name, ",@function\n",
+                $name, ":\n",
+                $body,
+                ".size ", $name, ",.-", $name,
+            )
+            $(, $($args)*)?
+        );
+    };
+}
+
+macro_rules! libcall_trampoline {
+    ($libcall:ident ; $libcall_impl:ident) => {
+        asm_func!(
+            stringify!($libcall),
+            concat!(
+                "
+                   .cfi_startproc simple
+                   .cfi_def_cfa_offset 0
+                    jmp {}
+                    .cfi_endproc
+                ",
+            ),
+            sym $libcall_impl
+        );
+    };
+}
+
+pub mod trampolines {
+    extern "C" {
+        pub fn table_fill_funcref();
+        pub fn table_fill_externref();
+    }
+
+    unsafe extern "C" fn impl_table_fill_funcref() {}
+    unsafe extern "C" fn impl_table_fill_externref() {}
+
+    libcall_trampoline!(table_fill_funcref ; impl_table_fill_funcref);
+    libcall_trampoline!(table_fill_externref ; impl_table_fill_externref);
+}
diff --git a/tests/run-make/lto-linkage-used-attr/main.rs b/tests/run-make/lto-linkage-used-attr/main.rs
new file mode 100644
index 00000000000..256b02e5b0b
--- /dev/null
+++ b/tests/run-make/lto-linkage-used-attr/main.rs
@@ -0,0 +1,10 @@
+extern crate lib;
+
+use lib::trampolines::*;
+
+fn main() {
+    unsafe {
+        table_fill_externref();
+        table_fill_funcref();
+    }
+}
diff --git a/tests/run-make/metadata-dep-info/Makefile b/tests/run-make/metadata-dep-info/Makefile
new file mode 100644
index 00000000000..f9043f21433
--- /dev/null
+++ b/tests/run-make/metadata-dep-info/Makefile
@@ -0,0 +1,13 @@
+include ../tools.mk
+
+ifdef RUSTC_BLESS_TEST
+    RUSTC_TEST_OP = cp
+else
+    RUSTC_TEST_OP = $(DIFF)
+endif
+
+all:
+	$(RUSTC) --emit=metadata,dep-info --crate-type lib dash-separated.rs -C extra-filename=_something-extra
+	# Strip TMPDIR since it is a machine specific absolute path
+	sed "s%.*[/\\]%%" "$(TMPDIR)"/dash-separated_something-extra.d > "$(TMPDIR)"/dash-separated_something-extra.normalized.d
+	$(RUSTC_TEST_OP) "$(TMPDIR)"/dash-separated_something-extra.normalized.d dash-separated_something-extra.normalized.d
diff --git a/tests/run-make/metadata-dep-info/dash-separated.rs b/tests/run-make/metadata-dep-info/dash-separated.rs
new file mode 100644
index 00000000000..4202afd3d08
--- /dev/null
+++ b/tests/run-make/metadata-dep-info/dash-separated.rs
@@ -0,0 +1,4 @@
+//! It is important that this file has at least one `-` in the file name since
+//! we want to test that it becomes a `_` when appropriate.
+
+pub struct Foo;
diff --git a/tests/run-make/metadata-dep-info/dash-separated_something-extra.normalized.d b/tests/run-make/metadata-dep-info/dash-separated_something-extra.normalized.d
new file mode 100644
index 00000000000..497d76b4ea1
--- /dev/null
+++ b/tests/run-make/metadata-dep-info/dash-separated_something-extra.normalized.d
@@ -0,0 +1,5 @@
+libdash_separated_something-extra.rmeta: dash-separated.rs
+
+dash-separated_something-extra.d: dash-separated.rs
+
+dash-separated.rs:
diff --git a/tests/run-make/output-filename-overwrites-input/Makefile b/tests/run-make/output-filename-overwrites-input/Makefile
index 605b86b253e..fe5d231382d 100644
--- a/tests/run-make/output-filename-overwrites-input/Makefile
+++ b/tests/run-make/output-filename-overwrites-input/Makefile
@@ -8,7 +8,7 @@ all:
 	cp bar.rs $(TMPDIR)/bar.rlib
 	$(RUSTC) $(TMPDIR)/bar.rlib -o $(TMPDIR)/bar.rlib 2>&1 \
 		| $(CGREP) -e "the input file \".*bar.rlib\" would be overwritten by the generated executable"
-	$(RUSTC) foo.rs 2>&1 && $(RUSTC) -Z ls $(TMPDIR)/foo 2>&1
+	$(RUSTC) foo.rs 2>&1 && $(RUSTC) -Z ls=root $(TMPDIR)/foo 2>&1
 	cp foo.rs $(TMPDIR)/foo.rs
 	$(RUSTC) $(TMPDIR)/foo.rs -o $(TMPDIR)/foo.rs 2>&1 \
 		| $(CGREP) -e "the input file \".*foo.rs\" would be overwritten by the generated executable"
diff --git a/tests/run-make/rustdoc-themes/Makefile b/tests/run-make/rustdoc-themes/Makefile
index a6d9a43addf..a4980eb0b3e 100644
--- a/tests/run-make/rustdoc-themes/Makefile
+++ b/tests/run-make/rustdoc-themes/Makefile
@@ -5,6 +5,7 @@ include ../tools.mk
 OUTPUT_DIR := "$(TMPDIR)/rustdoc-themes"
 
 all:
-	cp $(S)/src/librustdoc/html/static/css/themes/light.css $(TMPDIR)/test.css
+	awk '/Begin theme: light/ {in_theme=1;next} /End theme:/ {in_theme=0} { if (in_theme) print }' \
+		< '$(S)/src/librustdoc/html/static/css/noscript.css' > '$(TMPDIR)/test.css'
 	$(RUSTDOC) -o $(OUTPUT_DIR) foo.rs --theme $(TMPDIR)/test.css
 	$(HTMLDOCCK) $(OUTPUT_DIR) foo.rs
diff --git a/tests/rustdoc-gui/search-corrections.goml b/tests/rustdoc-gui/search-corrections.goml
index 5d1b83b35c5..aeb3c9b31a3 100644
--- a/tests/rustdoc-gui/search-corrections.goml
+++ b/tests/rustdoc-gui/search-corrections.goml
@@ -54,3 +54,53 @@ assert-text: (
     ".search-corrections",
     "Type \"notablestructwithlongnamr\" not found. Showing results for closest type name \"notablestructwithlongname\" instead."
 )
+
+// Now, generic correction
+go-to: "file://" + |DOC_PATH| + "/test_docs/index.html"
+// Intentionally wrong spelling of "NotableStructWithLongName"
+write: (".search-input", "NotableStructWithLongNamr, NotableStructWithLongNamr")
+// To be SURE that the search will be run.
+press-key: 'Enter'
+// Waiting for the search results to appear...
+wait-for: "#search-tabs"
+
+assert-css: (".search-corrections", {
+    "display": "block"
+})
+assert-text: (
+    ".search-corrections",
+    "Type \"notablestructwithlongnamr\" not found and used as generic parameter. Consider searching for \"notablestructwithlongname\" instead."
+)
+
+// Now, generic correction plus error
+go-to: "file://" + |DOC_PATH| + "/test_docs/index.html"
+// Intentionally wrong spelling of "NotableStructWithLongName"
+write: (".search-input", "Foo<NotableStructWithLongNamr>,y")
+// To be SURE that the search will be run.
+press-key: 'Enter'
+// Waiting for the search results to appear...
+wait-for: "#search-tabs"
+
+assert-css: (".search-corrections", {
+    "display": "block"
+})
+assert-text: (
+    ".search-corrections",
+    "Type \"notablestructwithlongnamr\" not found and used as generic parameter. Consider searching for \"notablestructwithlongname\" instead."
+)
+
+go-to: "file://" + |DOC_PATH| + "/test_docs/index.html"
+// Intentionally wrong spelling of "NotableStructWithLongName"
+write: (".search-input", "generic:NotableStructWithLongNamr<x>,y")
+// To be SURE that the search will be run.
+press-key: 'Enter'
+// Waiting for the search results to appear...
+wait-for: "#search-tabs"
+
+assert-css: (".error", {
+    "display": "block"
+})
+assert-text: (
+    ".error",
+    "Query parser error: \"Generic type parameter notablestructwithlongnamr does not accept generic parameters\"."
+)
diff --git a/tests/rustdoc-gui/search-result-color.goml b/tests/rustdoc-gui/search-result-color.goml
index f9f81c5ba04..44677dfbfef 100644
--- a/tests/rustdoc-gui/search-result-color.goml
+++ b/tests/rustdoc-gui/search-result-color.goml
@@ -151,7 +151,7 @@ assert-css: (
 )
 assert-css: (
     "//*[@class='result-name']//*[text()='test_docs::']/ancestor::a",
-    {"color": "#fff", "background-color": "rgb(60, 60, 60)"},
+    {"color": "#fff", "background-color": "#3c3c3c"},
 )
 
 // Dark theme
diff --git a/tests/rustdoc-gui/sidebar-source-code.goml b/tests/rustdoc-gui/sidebar-source-code.goml
index 69c589741cb..92b9045b734 100644
--- a/tests/rustdoc-gui/sidebar-source-code.goml
+++ b/tests/rustdoc-gui/sidebar-source-code.goml
@@ -73,7 +73,7 @@ assert: "//*[@class='dir-entry' and @open]/*[text()='sub_mod']"
 // Only "another_folder" should be "open" in "lib2".
 assert: "//*[@class='dir-entry' and not(@open)]/*[text()='another_mod']"
 // All other trees should be collapsed.
-assert-count: ("//*[@id='src-sidebar']/details[not(text()='lib2') and not(@open)]", 9)
+assert-count: ("//*[@id='src-sidebar']/details[not(text()='lib2') and not(@open)]", 10)
 
 // We now switch to mobile mode.
 set-window-size: (600, 600)
diff --git a/tests/rustdoc-gui/src/theme_css/Cargo.lock b/tests/rustdoc-gui/src/theme_css/Cargo.lock
new file mode 100644
index 00000000000..7ad6737a4d0
--- /dev/null
+++ b/tests/rustdoc-gui/src/theme_css/Cargo.lock
@@ -0,0 +1,7 @@
+# This file is automatically @generated by Cargo.
+# It is not intended for manual editing.
+version = 3
+
+[[package]]
+name = "theme_css"
+version = "0.1.0"
diff --git a/tests/rustdoc-gui/src/theme_css/Cargo.toml b/tests/rustdoc-gui/src/theme_css/Cargo.toml
new file mode 100644
index 00000000000..798e64f9309
--- /dev/null
+++ b/tests/rustdoc-gui/src/theme_css/Cargo.toml
@@ -0,0 +1,7 @@
+[package]
+name = "theme_css"
+version = "0.1.0"
+edition = "2018"
+
+[lib]
+path = "lib.rs"
diff --git a/tests/rustdoc-gui/src/theme_css/custom-theme.css b/tests/rustdoc-gui/src/theme_css/custom-theme.css
new file mode 100644
index 00000000000..260ef87f6ea
--- /dev/null
+++ b/tests/rustdoc-gui/src/theme_css/custom-theme.css
@@ -0,0 +1,99 @@
+:root {
+	--main-background-color: red;
+	--main-color: black;
+	--settings-input-color: #2196f3;
+	--settings-input-border-color: #717171;
+	--settings-button-color: #000;
+	--settings-button-border-focus: #717171;
+	--sidebar-background-color: #f5f5f5;
+	--sidebar-background-color-hover: #e0e0e0;
+	--code-block-background-color: #f5f5f5;
+	--scrollbar-track-background-color: #dcdcdc;
+	--scrollbar-thumb-background-color: rgba(36, 37, 39, 0.6);
+	--scrollbar-color: rgba(36, 37, 39, 0.6) #d9d9d9;
+	--headings-border-bottom-color: #ddd;
+	--border-color: #e0e0e0;
+	--button-background-color: #fff;
+	--right-side-color: grey;
+	--code-attribute-color: #999;
+	--toggles-color: #999;
+	--toggle-filter: none;
+	--search-input-focused-border-color: #66afe9;
+	--copy-path-button-color: #999;
+	--copy-path-img-filter: invert(50%);
+	--copy-path-img-hover-filter: invert(35%);
+	--codeblock-error-hover-color: rgb(255, 0, 0);
+	--codeblock-error-color: rgba(255, 0, 0, .5);
+	--codeblock-ignore-hover-color: rgb(255, 142, 0);
+	--codeblock-ignore-color: rgba(255, 142, 0, .6);
+	--warning-border-color: #ff8e00;
+	--type-link-color: #ad378a;
+	--trait-link-color: #6e4fc9;
+	--assoc-item-link-color: #3873ad;
+	--function-link-color: #ad7c37;
+	--macro-link-color: #068000;
+	--keyword-link-color: #3873ad;
+	--mod-link-color: #3873ad;
+	--link-color: #3873ad;
+	--sidebar-link-color: #356da4;
+	--sidebar-current-link-background-color: #fff;
+	--search-result-link-focus-background-color: #ccc;
+	--search-result-border-color: #aaa3;
+	--search-color: #000;
+	--search-error-code-background-color: #d0cccc;
+	--search-results-alias-color: #000;
+	--search-results-grey-color: #999;
+	--search-tab-title-count-color: #888;
+	--search-tab-button-not-selected-border-top-color: #e6e6e6;
+	--search-tab-button-not-selected-background: #e6e6e6;
+	--search-tab-button-selected-border-top-color: #0089ff;
+	--search-tab-button-selected-background: #fff;
+	--stab-background-color: #fff5d6;
+	--stab-code-color: #000;
+	--code-highlight-kw-color: #8959a8;
+	--code-highlight-kw-2-color: #4271ae;
+	--code-highlight-lifetime-color: #b76514;
+	--code-highlight-prelude-color: #4271ae;
+	--code-highlight-prelude-val-color: #c82829;
+	--code-highlight-number-color: #718c00;
+	--code-highlight-string-color: #718c00;
+	--code-highlight-literal-color: #c82829;
+	--code-highlight-attribute-color: #c82829;
+	--code-highlight-self-color: #c82829;
+	--code-highlight-macro-color: #3e999f;
+	--code-highlight-question-mark-color: #ff9011;
+	--code-highlight-comment-color: #8e908c;
+	--code-highlight-doc-comment-color: #4d4d4c;
+	--src-line-numbers-span-color: #c67e2d;
+	--src-line-number-highlighted-background-color: #fdffd3;
+	--test-arrow-color: #f5f5f5;
+	--test-arrow-background-color: rgba(78, 139, 202, 0.2);
+	--test-arrow-hover-color: #f5f5f5;
+	--test-arrow-hover-background-color: rgb(78, 139, 202);
+	--target-background-color: #fdffd3;
+	--target-border-color: #ad7c37;
+	--kbd-color: #000;
+	--kbd-background: #fafbfc;
+	--kbd-box-shadow-color: #c6cbd1;
+	--rust-logo-filter: initial;
+	/* match border-color; uses https://codepen.io/sosuke/pen/Pjoqqp */
+	--crate-search-div-filter: invert(100%) sepia(0%) saturate(4223%) hue-rotate(289deg)
+		brightness(114%) contrast(76%);
+	--crate-search-div-hover-filter: invert(44%) sepia(18%) saturate(23%) hue-rotate(317deg)
+		brightness(96%) contrast(93%);
+	--crate-search-hover-border: #717171;
+	--src-sidebar-background-selected: #fff;
+	--src-sidebar-background-hover: #e0e0e0;
+	--table-alt-row-background-color: #f5f5f5;
+	--codeblock-link-background: #eee;
+	--scrape-example-toggle-line-background: #ccc;
+	--scrape-example-toggle-line-hover-background: #999;
+	--scrape-example-code-line-highlight: #fcffd6;
+	--scrape-example-code-line-highlight-focus: #f6fdb0;
+	--scrape-example-help-border-color: #555;
+	--scrape-example-help-color: #333;
+	--scrape-example-help-hover-border-color: #000;
+	--scrape-example-help-hover-color: #000;
+	--scrape-example-code-wrapper-background-start: rgba(255, 255, 255, 1);
+	--scrape-example-code-wrapper-background-end: rgba(255, 255, 255, 0);
+}
diff --git a/tests/rustdoc-gui/src/theme_css/lib.rs b/tests/rustdoc-gui/src/theme_css/lib.rs
new file mode 100644
index 00000000000..e9f3265fa6b
--- /dev/null
+++ b/tests/rustdoc-gui/src/theme_css/lib.rs
@@ -0,0 +1,2 @@
+// compile-flags: --theme custom-theme.css
+//! <div class="custom-text">custom text</div>
diff --git a/tests/rustdoc-gui/theme-change.goml b/tests/rustdoc-gui/theme-change.goml
index e4b031b735e..fdaf9d6289a 100644
--- a/tests/rustdoc-gui/theme-change.goml
+++ b/tests/rustdoc-gui/theme-change.goml
@@ -65,3 +65,36 @@ assert-local-storage: { "rustdoc-theme": "light" }
 reload:
 wait-for: "#settings"
 assert: "#preferred-light-theme.setting-line.hidden"
+
+// Ensures that the custom theme feature is working as expected.
+go-to: "file://" + |DOC_PATH| + "/theme_css/index.html"
+set-local-storage: {"rustdoc-use-system-theme": "false", "rustdoc-theme": "dark"}
+reload:
+
+store-value: (background_light, "white")
+store-value: (background_dark, "#353535")
+store-value: (background_ayu, "#0f1419")
+store-value: (background_custom_theme, "red")
+
+click: "#settings-menu"
+wait-for: "#theme-ayu"
+click: "#theme-ayu"
+// should be the ayu theme so let's check the color.
+wait-for-css: ("body", { "background-color": |background_ayu| })
+assert-local-storage: { "rustdoc-theme": "ayu" }
+assert-text: (".custom-text", "custom text")
+click: "#theme-light"
+// should be the light theme so let's check the color.
+wait-for-css: ("body", { "background-color": |background_light| })
+assert-local-storage: { "rustdoc-theme": "light" }
+assert-text: (".custom-text", "custom text")
+click: "#theme-dark"
+// Should be the dark theme so let's check the color.
+wait-for-css: ("body", { "background-color": |background_dark| })
+assert-local-storage: { "rustdoc-theme": "dark" }
+assert-text: (".custom-text", "custom text")
+click: "#theme-custom-theme"
+// Should be the custom theme so let's check the color.
+wait-for-css: ("body", { "background-color": |background_custom_theme| })
+assert-local-storage: { "rustdoc-theme": "custom-theme" }
+assert-text: (".custom-text", "custom text")
diff --git a/tests/rustdoc-js-std/option-type-signatures.js b/tests/rustdoc-js-std/option-type-signatures.js
index 25997850661..e154fa707ab 100644
--- a/tests/rustdoc-js-std/option-type-signatures.js
+++ b/tests/rustdoc-js-std/option-type-signatures.js
@@ -1,3 +1,7 @@
+// ignore-order
+
+const FILTER_CRATE = "std";
+
 const EXPECTED = [
     {
         'query': 'option, fnonce -> option',
@@ -19,4 +23,62 @@ const EXPECTED = [
             { 'path': 'std::option::Option', 'name': 'as_mut_slice' },
         ],
     },
+    {
+        'query': 'option<t>, option<t> -> option<t>',
+        'others': [
+            { 'path': 'std::option::Option', 'name': 'or' },
+            { 'path': 'std::option::Option', 'name': 'xor' },
+        ],
+    },
+    {
+        'query': 'option<t>, option<u> -> option<u>',
+        'others': [
+            { 'path': 'std::option::Option', 'name': 'and' },
+            { 'path': 'std::option::Option', 'name': 'zip' },
+        ],
+    },
+    {
+        'query': 'option<t>, option<u> -> option<t>',
+        'others': [
+            { 'path': 'std::option::Option', 'name': 'and' },
+            { 'path': 'std::option::Option', 'name': 'zip' },
+        ],
+    },
+    {
+        'query': 'option<t>, option<u> -> option<t, u>',
+        'others': [
+            { 'path': 'std::option::Option', 'name': 'zip' },
+        ],
+    },
+    {
+        'query': 'option<t>, e -> result<t, e>',
+        'others': [
+            { 'path': 'std::option::Option', 'name': 'ok_or' },
+            { 'path': 'std::result::Result', 'name': 'transpose' },
+        ],
+    },
+    {
+        'query': 'result<option<t>, e> -> option<result<t, e>>',
+        'others': [
+            { 'path': 'std::result::Result', 'name': 'transpose' },
+        ],
+    },
+    {
+        'query': 'option<t>, option<t> -> bool',
+        'others': [
+            { 'path': 'std::option::Option', 'name': 'eq' },
+        ],
+    },
+    {
+        'query': 'option<option<t>> -> option<t>',
+        'others': [
+            { 'path': 'std::option::Option', 'name': 'flatten' },
+        ],
+    },
+    {
+        'query': 'option<t>',
+        'returned': [
+            { 'path': 'std::result::Result', 'name': 'ok' },
+        ],
+    },
 ];
diff --git a/tests/rustdoc-js-std/vec-type-signatures.js b/tests/rustdoc-js-std/vec-type-signatures.js
new file mode 100644
index 00000000000..18cf9d6efd0
--- /dev/null
+++ b/tests/rustdoc-js-std/vec-type-signatures.js
@@ -0,0 +1,22 @@
+// ignore-order
+
+const FILTER_CRATE = "std";
+
+const EXPECTED = [
+    {
+        'query': 'vec::intoiter<T> -> [T]',
+        'others': [
+            { 'path': 'std::vec::IntoIter', 'name': 'as_slice' },
+            { 'path': 'std::vec::IntoIter', 'name': 'as_mut_slice' },
+            { 'path': 'std::vec::IntoIter', 'name': 'next_chunk' },
+        ],
+    },
+    {
+        'query': 'vec::intoiter<T> -> []',
+        'others': [
+            { 'path': 'std::vec::IntoIter', 'name': 'as_slice' },
+            { 'path': 'std::vec::IntoIter', 'name': 'as_mut_slice' },
+            { 'path': 'std::vec::IntoIter', 'name': 'next_chunk' },
+        ],
+    },
+];
diff --git a/tests/rustdoc-js/generics-match-ambiguity.js b/tests/rustdoc-js/generics-match-ambiguity.js
index a9932a16ca3..edce4268c5a 100644
--- a/tests/rustdoc-js/generics-match-ambiguity.js
+++ b/tests/rustdoc-js/generics-match-ambiguity.js
@@ -79,6 +79,7 @@ const EXPECTED = [
             { 'path': 'generics_match_ambiguity', 'name': 'baac' },
             { 'path': 'generics_match_ambiguity', 'name': 'baaf' },
             { 'path': 'generics_match_ambiguity', 'name': 'baag' },
+            { 'path': 'generics_match_ambiguity', 'name': 'baah' },
         ],
     },
     {
diff --git a/tests/rustdoc-js/generics-trait.js b/tests/rustdoc-js/generics-trait.js
index 4ccfb8f4e4d..a71393b5e05 100644
--- a/tests/rustdoc-js/generics-trait.js
+++ b/tests/rustdoc-js/generics-trait.js
@@ -12,12 +12,16 @@ const EXPECTED = [
         ],
     },
     {
-        'query': 'Result<SomeTraiz>',
-        'correction': null,
+        'query': 'Resulx<SomeTrait>',
         'in_args': [],
         'returned': [],
     },
     {
+        'query': 'Result<SomeTraiz>',
+        'proposeCorrectionFrom': 'SomeTraiz',
+        'proposeCorrectionTo': 'SomeTrait',
+    },
+    {
         'query': 'OtherThingxxxxxxxx',
         'correction': null,
         'in_args': [
diff --git a/tests/rustdoc-js/generics-unbox.js b/tests/rustdoc-js/generics-unbox.js
new file mode 100644
index 00000000000..9cdfc7ac8b6
--- /dev/null
+++ b/tests/rustdoc-js/generics-unbox.js
@@ -0,0 +1,38 @@
+// exact-check
+
+const EXPECTED = [
+    {
+        'query': 'Inside<T> -> Out1<T>',
+        'others': [
+            { 'path': 'generics_unbox', 'name': 'alpha' },
+        ],
+    },
+    {
+        'query': 'Inside<T> -> Out3<T>',
+        'others': [
+            { 'path': 'generics_unbox', 'name': 'beta' },
+            { 'path': 'generics_unbox', 'name': 'gamma' },
+        ],
+    },
+    {
+        'query': 'Inside<T> -> Out4<T>',
+        'others': [
+            { 'path': 'generics_unbox', 'name': 'beta' },
+            { 'path': 'generics_unbox', 'name': 'gamma' },
+        ],
+    },
+    {
+        'query': 'Inside<T> -> Out3<U, T>',
+        'others': [
+            { 'path': 'generics_unbox', 'name': 'beta' },
+            { 'path': 'generics_unbox', 'name': 'gamma' },
+        ],
+    },
+    {
+        'query': 'Inside<T> -> Out4<U, T>',
+        'others': [
+            { 'path': 'generics_unbox', 'name': 'beta' },
+            { 'path': 'generics_unbox', 'name': 'gamma' },
+        ],
+    },
+];
diff --git a/tests/rustdoc-js/generics-unbox.rs b/tests/rustdoc-js/generics-unbox.rs
new file mode 100644
index 00000000000..bef34f891e9
--- /dev/null
+++ b/tests/rustdoc-js/generics-unbox.rs
@@ -0,0 +1,36 @@
+pub struct Out<A, B = ()> {
+    a: A,
+    b: B,
+}
+
+pub struct Out1<A, const N: usize> {
+    a: [A; N],
+}
+
+pub struct Out2<A, const N: usize> {
+    a: [A; N],
+}
+
+pub struct Out3<A, B> {
+    a: A,
+    b: B,
+}
+
+pub struct Out4<A, B> {
+    a: A,
+    b: B,
+}
+
+pub struct Inside<T>(T);
+
+pub fn alpha<const N: usize, T>(_: Inside<T>) -> Out<Out1<T, N>, Out2<T, N>> {
+    loop {}
+}
+
+pub fn beta<T, U>(_: Inside<T>) -> Out<Out3<T, U>, Out4<U, T>> {
+    loop {}
+}
+
+pub fn gamma<T, U>(_: Inside<T>) -> Out<Out3<U, T>, Out4<T, U>> {
+    loop {}
+}
diff --git a/tests/rustdoc-js/type-parameters.js b/tests/rustdoc-js/type-parameters.js
new file mode 100644
index 00000000000..e695f189bb6
--- /dev/null
+++ b/tests/rustdoc-js/type-parameters.js
@@ -0,0 +1,87 @@
+// exact-check
+// ignore-order
+
+const EXPECTED = [
+    {
+        query: '-> trait:Some',
+        others: [
+            { path: 'foo', name: 'alef' },
+            { path: 'foo', name: 'alpha' },
+        ],
+    },
+    {
+        query: '-> generic:T',
+        others: [
+            { path: 'foo', name: 'bet' },
+            { path: 'foo', name: 'alef' },
+            { path: 'foo', name: 'beta' },
+        ],
+    },
+    {
+        query: 'A -> B',
+        others: [
+            { path: 'foo', name: 'bet' },
+        ],
+    },
+    {
+        query: 'A -> A',
+        others: [
+            { path: 'foo', name: 'beta' },
+        ],
+    },
+    {
+        query: 'A, A',
+        others: [
+            { path: 'foo', name: 'alternate' },
+        ],
+    },
+    {
+        query: 'A, B',
+        others: [
+            { path: 'foo', name: 'other' },
+        ],
+    },
+    {
+        query: 'Other, Other',
+        others: [
+            { path: 'foo', name: 'other' },
+            { path: 'foo', name: 'alternate' },
+        ],
+    },
+    {
+        query: 'generic:T',
+        in_args: [
+            { path: 'foo', name: 'bet' },
+            { path: 'foo', name: 'beta' },
+            { path: 'foo', name: 'other' },
+            { path: 'foo', name: 'alternate' },
+        ],
+    },
+    {
+        query: 'generic:Other',
+        in_args: [
+            { path: 'foo', name: 'bet' },
+            { path: 'foo', name: 'beta' },
+            { path: 'foo', name: 'other' },
+            { path: 'foo', name: 'alternate' },
+        ],
+    },
+    {
+        query: 'trait:Other',
+        in_args: [
+            { path: 'foo', name: 'other' },
+            { path: 'foo', name: 'alternate' },
+        ],
+    },
+    {
+        query: 'Other',
+        in_args: [
+            { path: 'foo', name: 'other' },
+            { path: 'foo', name: 'alternate' },
+        ],
+    },
+    {
+        query: 'trait:T',
+        in_args: [],
+    },
+];
diff --git a/tests/rustdoc-js/type-parameters.rs b/tests/rustdoc-js/type-parameters.rs
new file mode 100644
index 00000000000..cda5e26171f
--- /dev/null
+++ b/tests/rustdoc-js/type-parameters.rs
@@ -0,0 +1,15 @@
+#![crate_name="foo"]
+
+pub trait Some {}
+impl Some for () {}
+pub trait Other {}
+impl Other for () {}
+
+pub fn alef<T: Some>() -> T { loop {} }
+pub fn alpha() -> impl Some { }
+
+pub fn bet<T, U>(t: T) -> U { loop {} }
+pub fn beta<T>(t: T) -> T {}
+
+pub fn other<T: Other, U: Other>(t: T, u: U) { loop {} }
+pub fn alternate<T: Other>(t: T, u: T) { loop {} }
diff --git a/tests/rustdoc-ui/custom_code_classes_in_docs-warning.rs b/tests/rustdoc-ui/custom_code_classes_in_docs-warning.rs
new file mode 100644
index 00000000000..5398d5833c7
--- /dev/null
+++ b/tests/rustdoc-ui/custom_code_classes_in_docs-warning.rs
@@ -0,0 +1,83 @@
+// This test ensures that warnings are working as expected for "custom_code_classes_in_docs"
+// feature.
+
+#![feature(custom_code_classes_in_docs)]
+#![deny(warnings)]
+#![feature(no_core)]
+#![no_core]
+
+/// ```{. }
+/// main;
+/// ```
+//~^^^ ERROR unexpected ` ` character after `.`
+pub fn foo() {}
+
+/// ```{class= a}
+/// main;
+/// ```
+//~^^^ ERROR unexpected ` ` character after `=`
+pub fn foo2() {}
+
+/// ```{#id}
+/// main;
+/// ```
+//~^^^ ERROR unexpected character `#`
+pub fn foo3() {}
+
+/// ```{{
+/// main;
+/// ```
+//~^^^ ERROR unexpected character `{`
+pub fn foo4() {}
+
+/// ```}
+/// main;
+/// ```
+//~^^^ ERROR unexpected character `}`
+pub fn foo5() {}
+
+/// ```)
+/// main;
+/// ```
+//~^^^ ERROR unexpected character `)`
+pub fn foo6() {}
+
+/// ```{class=}
+/// main;
+/// ```
+//~^^^ ERROR unexpected `}` character after `=`
+pub fn foo7() {}
+
+/// ```(
+/// main;
+/// ```
+//~^^^ ERROR unclosed comment: missing `)` at the end
+pub fn foo8() {}
+
+/// ```{class=one=two}
+/// main;
+/// ```
+//~^^^ ERROR unexpected `=` character
+pub fn foo9() {}
+
+/// ```{.one.two}
+/// main;
+/// ```
+pub fn foo10() {}
+
+/// ```{class=(one}
+/// main;
+/// ```
+//~^^^ ERROR unexpected `(` character after `=`
+pub fn foo11() {}
+
+/// ```{class=one.two}
+/// main;
+/// ```
+pub fn foo12() {}
+
+/// ```{(comment)}
+/// main;
+/// ```
+//~^^^ ERROR unexpected character `(`
+pub fn foo13() {}
diff --git a/tests/rustdoc-ui/custom_code_classes_in_docs-warning.stderr b/tests/rustdoc-ui/custom_code_classes_in_docs-warning.stderr
new file mode 100644
index 00000000000..14b4b3bab3f
--- /dev/null
+++ b/tests/rustdoc-ui/custom_code_classes_in_docs-warning.stderr
@@ -0,0 +1,97 @@
+error: unexpected ` ` character after `.`
+  --> $DIR/custom_code_classes_in_docs-warning.rs:9:1
+   |
+LL | / /// ```{. }
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+   |
+note: the lint level is defined here
+  --> $DIR/custom_code_classes_in_docs-warning.rs:5:9
+   |
+LL | #![deny(warnings)]
+   |         ^^^^^^^^
+   = note: `#[deny(rustdoc::invalid_codeblock_attributes)]` implied by `#[deny(warnings)]`
+
+error: unexpected ` ` character after `=`
+  --> $DIR/custom_code_classes_in_docs-warning.rs:15:1
+   |
+LL | / /// ```{class= a}
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+
+error: unexpected character `#`
+  --> $DIR/custom_code_classes_in_docs-warning.rs:21:1
+   |
+LL | / /// ```{#id}
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+
+error: unexpected character `{`
+  --> $DIR/custom_code_classes_in_docs-warning.rs:27:1
+   |
+LL | / /// ```{{
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+
+error: unexpected character `}`
+  --> $DIR/custom_code_classes_in_docs-warning.rs:33:1
+   |
+LL | / /// ```}
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+
+error: unexpected character `)`
+  --> $DIR/custom_code_classes_in_docs-warning.rs:39:1
+   |
+LL | / /// ```)
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+
+error: unexpected `}` character after `=`
+  --> $DIR/custom_code_classes_in_docs-warning.rs:45:1
+   |
+LL | / /// ```{class=}
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+
+error: unclosed comment: missing `)` at the end
+  --> $DIR/custom_code_classes_in_docs-warning.rs:51:1
+   |
+LL | / /// ```(
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+
+error: unexpected `=` character
+  --> $DIR/custom_code_classes_in_docs-warning.rs:57:1
+   |
+LL | / /// ```{class=one=two}
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+
+error: unexpected `(` character after `=`
+  --> $DIR/custom_code_classes_in_docs-warning.rs:68:1
+   |
+LL | / /// ```{class=(one}
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+
+error: unexpected character `(`
+  --> $DIR/custom_code_classes_in_docs-warning.rs:79:1
+   |
+LL | / /// ```{(comment)}
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+
+error: aborting due to 11 previous errors
+
diff --git a/tests/rustdoc-ui/custom_code_classes_in_docs-warning3.rs b/tests/rustdoc-ui/custom_code_classes_in_docs-warning3.rs
new file mode 100644
index 00000000000..57d9038cb0c
--- /dev/null
+++ b/tests/rustdoc-ui/custom_code_classes_in_docs-warning3.rs
@@ -0,0 +1,17 @@
+// This test ensures that warnings are working as expected for "custom_code_classes_in_docs"
+// feature.
+
+#![feature(custom_code_classes_in_docs)]
+#![deny(warnings)]
+#![feature(no_core)]
+#![no_core]
+
+/// ```{class="}
+/// main;
+/// ```
+//~^^^ ERROR unclosed quote string
+//~| ERROR unclosed quote string
+/// ```"
+/// main;
+/// ```
+pub fn foo() {}
diff --git a/tests/rustdoc-ui/custom_code_classes_in_docs-warning3.stderr b/tests/rustdoc-ui/custom_code_classes_in_docs-warning3.stderr
new file mode 100644
index 00000000000..4f2ded78c29
--- /dev/null
+++ b/tests/rustdoc-ui/custom_code_classes_in_docs-warning3.stderr
@@ -0,0 +1,33 @@
+error: unclosed quote string `"`
+  --> $DIR/custom_code_classes_in_docs-warning3.rs:9:1
+   |
+LL | / /// ```{class="}
+LL | | /// main;
+LL | | /// ```
+LL | |
+...  |
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+   |
+note: the lint level is defined here
+  --> $DIR/custom_code_classes_in_docs-warning3.rs:5:9
+   |
+LL | #![deny(warnings)]
+   |         ^^^^^^^^
+   = note: `#[deny(rustdoc::invalid_codeblock_attributes)]` implied by `#[deny(warnings)]`
+
+error: unclosed quote string `"`
+  --> $DIR/custom_code_classes_in_docs-warning3.rs:9:1
+   |
+LL | / /// ```{class="}
+LL | | /// main;
+LL | | /// ```
+LL | |
+...  |
+LL | | /// main;
+LL | | /// ```
+   | |_______^
+
+error: aborting due to 2 previous errors
+
diff --git a/tests/rustdoc-ui/feature-gate-custom_code_classes_in_docs.rs b/tests/rustdoc-ui/feature-gate-custom_code_classes_in_docs.rs
new file mode 100644
index 00000000000..99263a944f8
--- /dev/null
+++ b/tests/rustdoc-ui/feature-gate-custom_code_classes_in_docs.rs
@@ -0,0 +1,15 @@
+// check-pass
+
+/// ```{class=language-c}
+/// int main(void) { return 0; }
+/// ```
+//~^^^ WARNING custom classes in code blocks will change behaviour
+//~| NOTE found these custom classes: class=language-c
+//~| NOTE see issue #79483 <https://github.com/rust-lang/rust/issues/79483>
+//~| HELP add `#![feature(custom_code_classes_in_docs)]` to the crate attributes to enable
+pub struct Bar;
+
+/// ```ASN.1
+/// int main(void) { return 0; }
+/// ```
+pub struct Bar2;
diff --git a/tests/rustdoc-ui/feature-gate-custom_code_classes_in_docs.stderr b/tests/rustdoc-ui/feature-gate-custom_code_classes_in_docs.stderr
new file mode 100644
index 00000000000..1a2360d9b30
--- /dev/null
+++ b/tests/rustdoc-ui/feature-gate-custom_code_classes_in_docs.stderr
@@ -0,0 +1,14 @@
+warning: custom classes in code blocks will change behaviour
+  --> $DIR/feature-gate-custom_code_classes_in_docs.rs:3:1
+   |
+LL | / /// ```{class=language-c}
+LL | | /// int main(void) { return 0; }
+LL | | /// ```
+   | |_______^
+   |
+   = note: see issue #79483 <https://github.com/rust-lang/rust/issues/79483> for more information
+   = help: add `#![feature(custom_code_classes_in_docs)]` to the crate attributes to enable
+   = note: found these custom classes: class=language-c
+
+warning: 1 warning emitted
+
diff --git a/tests/rustdoc-ui/issues/issue-91713.stdout b/tests/rustdoc-ui/issues/issue-91713.stdout
index 16783524363..bbea7e5c212 100644
--- a/tests/rustdoc-ui/issues/issue-91713.stdout
+++ b/tests/rustdoc-ui/issues/issue-91713.stdout
@@ -1,4 +1,5 @@
 Available passes for running rustdoc:
+check-custom-code-classes - check for custom code classes without the feature-gate enabled
 check_doc_test_visibility - run various visibility-related lints on doctests
         strip-hidden - strips all `#[doc(hidden)]` items from the output
        strip-private - strips all private items from a crate which cannot be seen externally, implies strip-priv-imports
@@ -10,6 +11,7 @@ calculate-doc-coverage - counts the number of items with and without documentati
            run-lints - runs some of rustdoc's lints
 
 Default passes for rustdoc:
+check-custom-code-classes
  collect-trait-impls
 check_doc_test_visibility
         strip-hidden  (when not --document-hidden-items)
diff --git a/tests/rustdoc/custom_code_classes.rs b/tests/rustdoc/custom_code_classes.rs
new file mode 100644
index 00000000000..cd20d8b7d6c
--- /dev/null
+++ b/tests/rustdoc/custom_code_classes.rs
@@ -0,0 +1,28 @@
+// Test for `custom_code_classes_in_docs` feature.
+
+#![feature(custom_code_classes_in_docs)]
+#![crate_name = "foo"]
+#![feature(no_core)]
+#![no_core]
+
+// @has 'foo/struct.Bar.html'
+// @has - '//*[@id="main-content"]//pre[@class="language-whatever hoho-c"]' 'main;'
+// @has - '//*[@id="main-content"]//pre[@class="language-whatever2 haha-c"]' 'main;'
+// @has - '//*[@id="main-content"]//pre[@class="language-whatever4 huhu-c"]' 'main;'
+
+/// ```{class=hoho-c},whatever
+/// main;
+/// ```
+///
+/// Testing multiple kinds of orders.
+///
+/// ```whatever2 {class=haha-c}
+/// main;
+/// ```
+///
+/// Testing with multiple "unknown". Only the first should be used.
+///
+/// ```whatever4,{.huhu-c} whatever5
+/// main;
+/// ```
+pub struct Bar;
diff --git a/tests/rustdoc/issue-32077-type-alias-impls.rs b/tests/rustdoc/issue-32077-type-alias-impls.rs
index 26778c67c24..ac486c36ad0 100644
--- a/tests/rustdoc/issue-32077-type-alias-impls.rs
+++ b/tests/rustdoc/issue-32077-type-alias-impls.rs
@@ -19,6 +19,8 @@ impl<T> Foo for GenericStruct<T> {}
 impl Bar for GenericStruct<u32> {}
 
 // @has 'foo/type.TypedefStruct.html'
+// We check that "Aliased type" is also present as a title in the sidebar.
+// @has - '//*[@class="sidebar-elems"]//h3/a[@href="#aliased-type"]' 'Aliased type'
 // We check that we have the implementation of the type alias itself.
 // @has - '//*[@id="impl-TypedefStruct"]/h3' 'impl TypedefStruct'
 // @has - '//*[@id="method.on_alias"]/h4' 'pub fn on_alias()'
diff --git a/tests/ui-fulldeps/pprust-expr-roundtrip.rs b/tests/ui-fulldeps/pprust-expr-roundtrip.rs
index ae375dfab90..541be7ebbc0 100644
--- a/tests/ui-fulldeps/pprust-expr-roundtrip.rs
+++ b/tests/ui-fulldeps/pprust-expr-roundtrip.rs
@@ -80,14 +80,20 @@ fn iter_exprs(depth: usize, f: &mut dyn FnMut(P<Expr>)) {
                 let seg = PathSegment::from_ident(Ident::from_str("x"));
                 iter_exprs(depth - 1, &mut |e| {
                     g(ExprKind::MethodCall(Box::new(MethodCall {
-                        seg: seg.clone(), receiver: e, args: thin_vec![make_x()], span: DUMMY_SP
-                    }))
-                )});
+                        seg: seg.clone(),
+                        receiver: e,
+                        args: thin_vec![make_x()],
+                        span: DUMMY_SP,
+                    })))
+                });
                 iter_exprs(depth - 1, &mut |e| {
                     g(ExprKind::MethodCall(Box::new(MethodCall {
-                        seg: seg.clone(), receiver: make_x(), args: thin_vec![e], span: DUMMY_SP
-                    }))
-                )});
+                        seg: seg.clone(),
+                        receiver: make_x(),
+                        args: thin_vec![e],
+                        span: DUMMY_SP,
+                    })))
+                });
             }
             2..=7 => {
                 let op = Spanned {
@@ -174,7 +180,7 @@ fn iter_exprs(depth: usize, f: &mut dyn FnMut(P<Expr>)) {
             18 => {
                 let pat =
                     P(Pat { id: DUMMY_NODE_ID, kind: PatKind::Wild, span: DUMMY_SP, tokens: None });
-                iter_exprs(depth - 1, &mut |e| g(ExprKind::Let(pat.clone(), e, DUMMY_SP)))
+                iter_exprs(depth - 1, &mut |e| g(ExprKind::Let(pat.clone(), e, DUMMY_SP, None)))
             }
             _ => panic!("bad counter value in iter_exprs"),
         }
diff --git a/tests/ui-fulldeps/stable-mir/crate-info.rs b/tests/ui-fulldeps/stable-mir/crate-info.rs
index d55eae86f07..a11720c4b55 100644
--- a/tests/ui-fulldeps/stable-mir/crate-info.rs
+++ b/tests/ui-fulldeps/stable-mir/crate-info.rs
@@ -154,6 +154,10 @@ fn test_stable_mir(tcx: TyCtxt<'_>) -> ControlFlow<()> {
         }
     }
 
+    let foo_const = get_item(tcx, &items, (DefKind::Const, "FOO")).unwrap();
+    // Ensure we don't panic trying to get the body of a constant.
+    foo_const.body();
+
     ControlFlow::Continue(())
 }
 
@@ -191,6 +195,8 @@ fn generate_input(path: &str) -> std::io::Result<()> {
     write!(
         file,
         r#"
+    pub const FOO: u32 = 1 + 2;
+
     fn generic<T, const U: usize>(t: T) -> [(); U] {{
         _ = t;
         [(); U]
diff --git a/tests/ui/abi/compatibility.rs b/tests/ui/abi/compatibility.rs
index 86fb365507a..d4f42cdda97 100644
--- a/tests/ui/abi/compatibility.rs
+++ b/tests/ui/abi/compatibility.rs
@@ -1,15 +1,23 @@
 // check-pass
-#![feature(rustc_attrs, transparent_unions)]
-#![allow(unused, improper_ctypes_definitions)]
+#![feature(rustc_attrs, unsized_fn_params, transparent_unions)]
+#![allow(unused, improper_ctypes_definitions, internal_features)]
 use std::marker::PhantomData;
 use std::mem::ManuallyDrop;
 use std::num::NonZeroI32;
 use std::ptr::NonNull;
 
+// FIXME: a bunch of targets are broken in various ways.
+// Hence there are `cfg` throughout this test to disable parts of it on those targets.
+// sparc64: https://github.com/rust-lang/rust/issues/115336
+// mips64: https://github.com/rust-lang/rust/issues/115404
+// loongarch64: https://github.com/rust-lang/rust/issues/115509
+
 macro_rules! assert_abi_compatible {
     ($name:ident, $t1:ty, $t2:ty) => {
         mod $name {
             use super::*;
+            // Declaring a `type` doesn't even check well-formedness, so we also declare a function.
+            fn check_wf(_x: $t1, _y: $t2) {}
             // Test argument and return value, `Rust` and `C` ABIs.
             #[rustc_abi(assert_eq)]
             type TestRust = (fn($t1) -> $t1, fn($t2) -> $t2);
@@ -23,7 +31,7 @@ macro_rules! assert_abi_compatible {
 struct Zst;
 
 #[repr(C)]
-struct ReprC1<T>(T);
+struct ReprC1<T: ?Sized>(T);
 #[repr(C)]
 struct ReprC2Int<T>(i32, T);
 #[repr(C)]
@@ -72,14 +80,20 @@ test_abi_compatible!(fn_fn, fn(), fn(i32) -> i32);
 
 // Some further guarantees we will likely (have to) make.
 test_abi_compatible!(zst_unit, Zst, ());
+#[cfg(not(any(target_arch = "sparc64")))]
 test_abi_compatible!(zst_array, Zst, [u8; 0]);
 test_abi_compatible!(nonzero_int, NonZeroI32, i32);
 
+// `DispatchFromDyn` relies on ABI compatibility.
+// This is interesting since these types are not `repr(transparent)`.
+test_abi_compatible!(rc, std::rc::Rc<i32>, *mut i32);
+test_abi_compatible!(arc, std::sync::Arc<i32>, *mut i32);
+
 // `repr(transparent)` compatibility.
 #[repr(transparent)]
-struct Wrapper1<T>(T);
+struct Wrapper1<T: ?Sized>(T);
 #[repr(transparent)]
-struct Wrapper2<T>((), Zst, T);
+struct Wrapper2<T: ?Sized>((), Zst, T);
 #[repr(transparent)]
 struct Wrapper3<T>(T, [u8; 0], PhantomData<u64>);
 #[repr(transparent)]
@@ -95,6 +109,7 @@ macro_rules! test_transparent {
             test_abi_compatible!(wrap1, $t, Wrapper1<$t>);
             test_abi_compatible!(wrap2, $t, Wrapper2<$t>);
             test_abi_compatible!(wrap3, $t, Wrapper3<$t>);
+            #[cfg(not(target_arch = "loongarch64"))]
             test_abi_compatible!(wrap4, $t, WrapperUnion<$t>);
         }
     };
@@ -104,22 +119,50 @@ test_transparent!(simple, i32);
 test_transparent!(reference, &'static i32);
 test_transparent!(zst, Zst);
 test_transparent!(unit, ());
-test_transparent!(pair, (i32, f32)); // mixing in some floats since they often get special treatment
-test_transparent!(triple, (i8, i16, f32)); // chosen to fit into 64bit
-test_transparent!(tuple, (i32, f32, i64, f64));
-test_transparent!(empty_array, [u32; 0]);
-test_transparent!(empty_1zst_array, [u8; 0]);
-test_transparent!(small_array, [i32; 2]); // chosen to fit into 64bit
-test_transparent!(large_array, [i32; 16]);
 test_transparent!(enum_, Option<i32>);
 test_transparent!(enum_niched, Option<&'static i32>);
-// Pure-float types that are not ScalarPair seem to be tricky.
-// FIXME: <https://github.com/rust-lang/rust/issues/115664>
-#[cfg(not(any(target_arch = "arm", target_arch = "aarch64")))]
-mod tricky {
+#[cfg(not(any(target_arch = "mips64", target_arch = "sparc64")))]
+mod tuples {
     use super::*;
+    // mixing in some floats since they often get special treatment
+    test_transparent!(pair, (i32, f32));
+    // chosen to fit into 64bit
+    test_transparent!(triple, (i8, i16, f32));
+    // Pure-float types that are not ScalarPair seem to be tricky.
     test_transparent!(triple_f32, (f32, f32, f32));
     test_transparent!(triple_f64, (f64, f64, f64));
+    // and also something that's larger than 2 pointers
+    test_transparent!(tuple, (i32, f32, i64, f64));
+}
+// Some targets have special rules for arrays.
+#[cfg(not(any(target_arch = "mips64", target_arch = "sparc64")))]
+mod arrays {
+    use super::*;
+    test_transparent!(empty_array, [u32; 0]);
+    test_transparent!(empty_1zst_array, [u8; 0]);
+    test_transparent!(small_array, [i32; 2]); // chosen to fit into 64bit
+    test_transparent!(large_array, [i32; 16]);
+}
+
+// Some tests with unsized types (not all wrappers are compatible with that).
+macro_rules! test_transparent_unsized {
+    ($name:ident, $t:ty) => {
+        mod $name {
+            use super::*;
+            assert_abi_compatible!(wrap1, $t, Wrapper1<$t>);
+            assert_abi_compatible!(wrap1_reprc, ReprC1<$t>, ReprC1<Wrapper1<$t>>);
+            assert_abi_compatible!(wrap2, $t, Wrapper2<$t>);
+            assert_abi_compatible!(wrap2_reprc, ReprC1<$t>, ReprC1<Wrapper2<$t>>);
+        }
+    };
+}
+
+#[cfg(not(any(target_arch = "mips64", target_arch = "sparc64")))]
+mod unsized_ {
+    use super::*;
+    test_transparent_unsized!(str_, str);
+    test_transparent_unsized!(slice, [u8]);
+    test_transparent_unsized!(dyn_trait, dyn std::any::Any);
 }
 
 // RFC 3391 <https://rust-lang.github.io/rfcs/3391-result_ffi_guarantees.html>.
diff --git a/tests/ui/abi/debug.rs b/tests/ui/abi/debug.rs
index ac37d7b6bff..77715ee4023 100644
--- a/tests/ui/abi/debug.rs
+++ b/tests/ui/abi/debug.rs
@@ -4,7 +4,6 @@
 // normalize-stderr-test "(valid_range): 0\.\.=(4294967295|18446744073709551615)" -> "$1: $$FULL"
 // This pattern is prepared for when we account for alignment in the niche.
 // normalize-stderr-test "(valid_range): [1-9]\.\.=(429496729[0-9]|1844674407370955161[0-9])" -> "$1: $$NON_NULL"
-// normalize-stderr-test "Leaf\(0x0*20\)" -> "Leaf(0x0...20)"
 // Some attributes are only computed for release builds:
 // compile-flags: -O
 #![feature(rustc_attrs)]
diff --git a/tests/ui/abi/debug.stderr b/tests/ui/abi/debug.stderr
index f56f5c525ab..00fc7d1ece1 100644
--- a/tests/ui/abi/debug.stderr
+++ b/tests/ui/abi/debug.stderr
@@ -87,7 +87,7 @@ error: fn_abi_of(test) = FnAbi {
            conv: Rust,
            can_unwind: $SOME_BOOL,
        }
-  --> $DIR/debug.rs:16:1
+  --> $DIR/debug.rs:15:1
    |
 LL | fn test(_x: u8) -> bool { true }
    | ^^^^^^^^^^^^^^^^^^^^^^^
@@ -181,7 +181,7 @@ error: fn_abi_of(TestFnPtr) = FnAbi {
            conv: Rust,
            can_unwind: $SOME_BOOL,
        }
-  --> $DIR/debug.rs:19:1
+  --> $DIR/debug.rs:18:1
    |
 LL | type TestFnPtr = fn(bool) -> u8;
    | ^^^^^^^^^^^^^^
@@ -190,7 +190,7 @@ error: fn_abi_of(test_generic) = FnAbi {
            args: [
                ArgAbi {
                    layout: TyAndLayout {
-                       ty: *const T/#0,
+                       ty: *const T,
                        layout: Layout {
                            size: $SOME_SIZE,
                            align: AbiAndPrefAlign {
@@ -257,13 +257,13 @@ error: fn_abi_of(test_generic) = FnAbi {
            conv: Rust,
            can_unwind: $SOME_BOOL,
        }
-  --> $DIR/debug.rs:22:1
+  --> $DIR/debug.rs:21:1
    |
 LL | fn test_generic<T>(_x: *const T) { }
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: `#[rustc_abi]` can only be applied to function items, type aliases, and associated functions
-  --> $DIR/debug.rs:25:1
+  --> $DIR/debug.rs:24:1
    |
 LL | const C: () = ();
    | ^^^^^^^^^^^
@@ -409,7 +409,7 @@ error: ABIs are not compatible
            conv: Rust,
            can_unwind: $SOME_BOOL,
        }
-  --> $DIR/debug.rs:41:1
+  --> $DIR/debug.rs:40:1
    |
 LL | type TestAbiNe = (fn(u8), fn(u32));
    | ^^^^^^^^^^^^^^
@@ -419,7 +419,7 @@ error: ABIs are not compatible
            args: [
                ArgAbi {
                    layout: TyAndLayout {
-                       ty: [u8; Const { ty: usize, kind: Leaf(0x0...20) }],
+                       ty: [u8; 32],
                        layout: Layout {
                            size: Size(32 bytes),
                            align: AbiAndPrefAlign {
@@ -450,7 +450,7 @@ error: ABIs are not compatible
                                Align(1 bytes),
                            ),
                        },
-                       extra_attrs: None,
+                       meta_attrs: None,
                        on_stack: false,
                    },
                },
@@ -490,7 +490,7 @@ error: ABIs are not compatible
            args: [
                ArgAbi {
                    layout: TyAndLayout {
-                       ty: [u32; Const { ty: usize, kind: Leaf(0x0...20) }],
+                       ty: [u32; 32],
                        layout: Layout {
                            size: Size(128 bytes),
                            align: AbiAndPrefAlign {
@@ -521,7 +521,7 @@ error: ABIs are not compatible
                                Align(4 bytes),
                            ),
                        },
-                       extra_attrs: None,
+                       meta_attrs: None,
                        on_stack: false,
                    },
                },
@@ -557,7 +557,7 @@ error: ABIs are not compatible
            conv: Rust,
            can_unwind: $SOME_BOOL,
        }
-  --> $DIR/debug.rs:44:1
+  --> $DIR/debug.rs:43:1
    |
 LL | type TestAbiNeLarger = (fn([u8; 32]), fn([u32; 32]));
    | ^^^^^^^^^^^^^^^^^^^^
@@ -700,7 +700,7 @@ error: ABIs are not compatible
            conv: Rust,
            can_unwind: $SOME_BOOL,
        }
-  --> $DIR/debug.rs:47:1
+  --> $DIR/debug.rs:46:1
    |
 LL | type TestAbiNeFloat = (fn(f32), fn(u32));
    | ^^^^^^^^^^^^^^^^^^^
@@ -846,13 +846,13 @@ error: ABIs are not compatible
            conv: Rust,
            can_unwind: $SOME_BOOL,
        }
-  --> $DIR/debug.rs:51:1
+  --> $DIR/debug.rs:50:1
    |
 LL | type TestAbiNeSign = (fn(i32), fn(u32));
    | ^^^^^^^^^^^^^^^^^^
 
 error[E0277]: the size for values of type `str` cannot be known at compilation time
-  --> $DIR/debug.rs:54:46
+  --> $DIR/debug.rs:53:46
    |
 LL | type TestAbiEqNonsense = (fn((str, str)), fn((str, str)));
    |                                              ^^^^^^^^^^ doesn't have a size known at compile-time
@@ -861,7 +861,7 @@ LL | type TestAbiEqNonsense = (fn((str, str)), fn((str, str)));
    = note: only the last element of a tuple may have a dynamically sized type
 
 error: `#[rustc_abi]` can only be applied to function items, type aliases, and associated functions
-  --> $DIR/debug.rs:29:5
+  --> $DIR/debug.rs:28:5
    |
 LL |     const C: () = ();
    |     ^^^^^^^^^^^
@@ -870,7 +870,7 @@ error: fn_abi_of(assoc_test) = FnAbi {
            args: [
                ArgAbi {
                    layout: TyAndLayout {
-                       ty: &ReErased Adt(S, []),
+                       ty: &S,
                        layout: Layout {
                            size: $SOME_SIZE,
                            align: AbiAndPrefAlign {
@@ -949,7 +949,7 @@ error: fn_abi_of(assoc_test) = FnAbi {
            conv: Rust,
            can_unwind: $SOME_BOOL,
        }
-  --> $DIR/debug.rs:34:5
+  --> $DIR/debug.rs:33:5
    |
 LL |     fn assoc_test(&self) { }
    |     ^^^^^^^^^^^^^^^^^^^^
diff --git a/tests/ui/associated-consts/associated-const-array-len.stderr b/tests/ui/associated-consts/associated-const-array-len.stderr
index 0e0dec35b53..e3db45810fd 100644
--- a/tests/ui/associated-consts/associated-const-array-len.stderr
+++ b/tests/ui/associated-consts/associated-const-array-len.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `i32: Foo` is not satisfied
    |
 LL | const X: [i32; <i32 as Foo>::ID] = [0, 1, 2];
    |                 ^^^ the trait `Foo` is not implemented for `i32`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/associated-const-array-len.rs:1:1
+   |
+LL | trait Foo {
+   | ^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/associated-consts/defaults-cyclic-fail.rs b/tests/ui/associated-consts/defaults-cyclic-fail.rs
index a1c6840a0f1..9ef0003da17 100644
--- a/tests/ui/associated-consts/defaults-cyclic-fail.rs
+++ b/tests/ui/associated-consts/defaults-cyclic-fail.rs
@@ -3,7 +3,7 @@
 // Cyclic assoc. const defaults don't error unless *used*
 trait Tr {
     const A: u8 = Self::B;
-    //~^ cycle detected when const-evaluating + checking `Tr::A`
+    //~^ cycle detected
 
     const B: u8 = Self::A;
 }
diff --git a/tests/ui/associated-consts/defaults-cyclic-fail.stderr b/tests/ui/associated-consts/defaults-cyclic-fail.stderr
index ebdb76e4286..e29c32f5dfd 100644
--- a/tests/ui/associated-consts/defaults-cyclic-fail.stderr
+++ b/tests/ui/associated-consts/defaults-cyclic-fail.stderr
@@ -1,15 +1,25 @@
-error[E0391]: cycle detected when const-evaluating + checking `Tr::A`
+error[E0391]: cycle detected when simplifying constant for the type system `Tr::A`
+  --> $DIR/defaults-cyclic-fail.rs:5:5
+   |
+LL |     const A: u8 = Self::B;
+   |     ^^^^^^^^^^^
+   |
+note: ...which requires const-evaluating + checking `Tr::A`...
   --> $DIR/defaults-cyclic-fail.rs:5:19
    |
 LL |     const A: u8 = Self::B;
    |                   ^^^^^^^
+note: ...which requires simplifying constant for the type system `Tr::B`...
+  --> $DIR/defaults-cyclic-fail.rs:8:5
    |
+LL |     const B: u8 = Self::A;
+   |     ^^^^^^^^^^^
 note: ...which requires const-evaluating + checking `Tr::B`...
   --> $DIR/defaults-cyclic-fail.rs:8:19
    |
 LL |     const B: u8 = Self::A;
    |                   ^^^^^^^
-   = note: ...which again requires const-evaluating + checking `Tr::A`, completing the cycle
+   = note: ...which again requires simplifying constant for the type system `Tr::A`, completing the cycle
 note: cycle used when const-evaluating + checking `main::promoted[1]`
   --> $DIR/defaults-cyclic-fail.rs:16:16
    |
diff --git a/tests/ui/associated-consts/defaults-not-assumed-fail.stderr b/tests/ui/associated-consts/defaults-not-assumed-fail.stderr
index 9b761b00691..d659912341a 100644
--- a/tests/ui/associated-consts/defaults-not-assumed-fail.stderr
+++ b/tests/ui/associated-consts/defaults-not-assumed-fail.stderr
@@ -4,13 +4,13 @@ error[E0080]: evaluation of `<() as Tr>::B` failed
 LL |     const B: u8 = Self::A + 1;
    |                   ^^^^^^^^^^^ attempt to compute `u8::MAX + 1_u8`, which would overflow
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/defaults-not-assumed-fail.rs:33:16
    |
 LL |     assert_eq!(<() as Tr>::B, 0);    // causes the error above
    |                ^^^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/defaults-not-assumed-fail.rs:33:5
    |
 LL |     assert_eq!(<() as Tr>::B, 0);    // causes the error above
@@ -18,7 +18,7 @@ LL |     assert_eq!(<() as Tr>::B, 0);    // causes the error above
    |
    = note: this note originates in the macro `assert_eq` (in Nightly builds, run with -Z macro-backtrace for more info)
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/defaults-not-assumed-fail.rs:33:5
    |
 LL |     assert_eq!(<() as Tr>::B, 0);    // causes the error above
diff --git a/tests/ui/associated-consts/issue-105330.stderr b/tests/ui/associated-consts/issue-105330.stderr
index e9fe3a5e514..927422fa8dc 100644
--- a/tests/ui/associated-consts/issue-105330.stderr
+++ b/tests/ui/associated-consts/issue-105330.stderr
@@ -51,6 +51,11 @@ error[E0277]: the trait bound `Demo: TraitWAssocConst` is not satisfied
 LL |     foo::<Demo>()();
    |           ^^^^ the trait `TraitWAssocConst` is not implemented for `Demo`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-105330.rs:1:1
+   |
+LL | pub trait TraitWAssocConst {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^
 note: required by a bound in `foo`
   --> $DIR/issue-105330.rs:11:11
    |
@@ -87,6 +92,11 @@ error[E0277]: the trait bound `Demo: TraitWAssocConst` is not satisfied
 LL |     foo::<Demo>();
    |           ^^^^ the trait `TraitWAssocConst` is not implemented for `Demo`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-105330.rs:1:1
+   |
+LL | pub trait TraitWAssocConst {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^
 note: required by a bound in `foo`
   --> $DIR/issue-105330.rs:11:11
    |
diff --git a/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-impl.stderr b/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-impl.stderr
index 51bf0cb5e5c..4418fb7556b 100644
--- a/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-impl.stderr
+++ b/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-impl.stderr
@@ -4,7 +4,12 @@ error[E0391]: cycle detected when elaborating drops for `<impl at $DIR/issue-249
 LL |     const BAR: u32 = IMPL_REF_BAR;
    |                      ^^^^^^^^^^^^
    |
-note: ...which requires const-evaluating + checking `IMPL_REF_BAR`...
+note: ...which requires simplifying constant for the type system `IMPL_REF_BAR`...
+  --> $DIR/issue-24949-assoc-const-static-recursion-impl.rs:7:1
+   |
+LL | const IMPL_REF_BAR: u32 = GlobalImplRef::BAR;
+   | ^^^^^^^^^^^^^^^^^^^^^^^
+note: ...which requires simplifying constant for the type system `IMPL_REF_BAR`...
   --> $DIR/issue-24949-assoc-const-static-recursion-impl.rs:7:1
    |
 LL | const IMPL_REF_BAR: u32 = GlobalImplRef::BAR;
@@ -14,6 +19,11 @@ note: ...which requires const-evaluating + checking `IMPL_REF_BAR`...
    |
 LL | const IMPL_REF_BAR: u32 = GlobalImplRef::BAR;
    |                           ^^^^^^^^^^^^^^^^^^
+note: ...which requires simplifying constant for the type system `<impl at $DIR/issue-24949-assoc-const-static-recursion-impl.rs:11:1: 11:19>::BAR`...
+  --> $DIR/issue-24949-assoc-const-static-recursion-impl.rs:12:5
+   |
+LL |     const BAR: u32 = IMPL_REF_BAR;
+   |     ^^^^^^^^^^^^^^
 note: ...which requires const-evaluating + checking `<impl at $DIR/issue-24949-assoc-const-static-recursion-impl.rs:11:1: 11:19>::BAR`...
   --> $DIR/issue-24949-assoc-const-static-recursion-impl.rs:12:5
    |
diff --git a/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-trait-default.stderr b/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-trait-default.stderr
index 8277d41a1c9..392cd5e3443 100644
--- a/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-trait-default.stderr
+++ b/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-trait-default.stderr
@@ -4,7 +4,12 @@ error[E0391]: cycle detected when elaborating drops for `FooDefault::BAR`
 LL |     const BAR: u32 = DEFAULT_REF_BAR;
    |                      ^^^^^^^^^^^^^^^
    |
-note: ...which requires const-evaluating + checking `DEFAULT_REF_BAR`...
+note: ...which requires simplifying constant for the type system `DEFAULT_REF_BAR`...
+  --> $DIR/issue-24949-assoc-const-static-recursion-trait-default.rs:11:1
+   |
+LL | const DEFAULT_REF_BAR: u32 = <GlobalDefaultRef>::BAR;
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^
+note: ...which requires simplifying constant for the type system `DEFAULT_REF_BAR`...
   --> $DIR/issue-24949-assoc-const-static-recursion-trait-default.rs:11:1
    |
 LL | const DEFAULT_REF_BAR: u32 = <GlobalDefaultRef>::BAR;
@@ -14,6 +19,11 @@ note: ...which requires const-evaluating + checking `DEFAULT_REF_BAR`...
    |
 LL | const DEFAULT_REF_BAR: u32 = <GlobalDefaultRef>::BAR;
    |                              ^^^^^^^^^^^^^^^^^^^^^^^
+note: ...which requires simplifying constant for the type system `FooDefault::BAR`...
+  --> $DIR/issue-24949-assoc-const-static-recursion-trait-default.rs:8:5
+   |
+LL |     const BAR: u32 = DEFAULT_REF_BAR;
+   |     ^^^^^^^^^^^^^^
 note: ...which requires const-evaluating + checking `FooDefault::BAR`...
   --> $DIR/issue-24949-assoc-const-static-recursion-trait-default.rs:8:5
    |
diff --git a/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-trait.stderr b/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-trait.stderr
index 9983ba794cd..6cbddca9c62 100644
--- a/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-trait.stderr
+++ b/tests/ui/associated-consts/issue-24949-assoc-const-static-recursion-trait.stderr
@@ -4,7 +4,12 @@ error[E0391]: cycle detected when elaborating drops for `<impl at $DIR/issue-249
 LL |     const BAR: u32 = TRAIT_REF_BAR;
    |                      ^^^^^^^^^^^^^
    |
-note: ...which requires const-evaluating + checking `TRAIT_REF_BAR`...
+note: ...which requires simplifying constant for the type system `TRAIT_REF_BAR`...
+  --> $DIR/issue-24949-assoc-const-static-recursion-trait.rs:7:1
+   |
+LL | const TRAIT_REF_BAR: u32 = <GlobalTraitRef>::BAR;
+   | ^^^^^^^^^^^^^^^^^^^^^^^^
+note: ...which requires simplifying constant for the type system `TRAIT_REF_BAR`...
   --> $DIR/issue-24949-assoc-const-static-recursion-trait.rs:7:1
    |
 LL | const TRAIT_REF_BAR: u32 = <GlobalTraitRef>::BAR;
@@ -14,6 +19,11 @@ note: ...which requires const-evaluating + checking `TRAIT_REF_BAR`...
    |
 LL | const TRAIT_REF_BAR: u32 = <GlobalTraitRef>::BAR;
    |                            ^^^^^^^^^^^^^^^^^^^^^
+note: ...which requires simplifying constant for the type system `<impl at $DIR/issue-24949-assoc-const-static-recursion-trait.rs:11:1: 11:28>::BAR`...
+  --> $DIR/issue-24949-assoc-const-static-recursion-trait.rs:12:5
+   |
+LL |     const BAR: u32 = TRAIT_REF_BAR;
+   |     ^^^^^^^^^^^^^^
 note: ...which requires const-evaluating + checking `<impl at $DIR/issue-24949-assoc-const-static-recursion-trait.rs:11:1: 11:28>::BAR`...
   --> $DIR/issue-24949-assoc-const-static-recursion-trait.rs:12:5
    |
diff --git a/tests/ui/associated-types/associated-types-ICE-when-projecting-out-of-err.stderr b/tests/ui/associated-types/associated-types-ICE-when-projecting-out-of-err.stderr
index 8c3463a2832..fbc4ccd4cf4 100644
--- a/tests/ui/associated-types/associated-types-ICE-when-projecting-out-of-err.stderr
+++ b/tests/ui/associated-types/associated-types-ICE-when-projecting-out-of-err.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): Add<A>` is not satisfied
    |
 LL |     r = r + a;
    |           ^ the trait `Add<A>` is not implemented for `()`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/associated-types-ICE-when-projecting-out-of-err.rs:15:1
+   |
+LL | trait Add<RHS=Self> {
+   | ^^^^^^^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/associated-types/associated-types-no-suitable-supertrait.stderr b/tests/ui/associated-types/associated-types-no-suitable-supertrait.stderr
index bd3ee2abd2c..b3f2e16ba0d 100644
--- a/tests/ui/associated-types/associated-types-no-suitable-supertrait.stderr
+++ b/tests/ui/associated-types/associated-types-no-suitable-supertrait.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `(T, U): Get` is not satisfied
    |
 LL |     fn uhoh<U:Get>(&self, foo: U, bar: <(T, U) as Get>::Value) {}
    |                                        ^^^^^^^^^^^^^^^^^^^^^^ the trait `Get` is not implemented for `(T, U)`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/associated-types-no-suitable-supertrait.rs:12:1
+   |
+LL | trait Get {
+   | ^^^^^^^^^
 
 error[E0277]: the trait bound `Self: Get` is not satisfied
   --> $DIR/associated-types-no-suitable-supertrait.rs:17:40
diff --git a/tests/ui/associated-types/defaults-suitability.stderr b/tests/ui/associated-types/defaults-suitability.stderr
index 4b2094691f8..0a8ad0f89e2 100644
--- a/tests/ui/associated-types/defaults-suitability.stderr
+++ b/tests/ui/associated-types/defaults-suitability.stderr
@@ -58,6 +58,11 @@ error[E0277]: the trait bound `(): Foo<Self>` is not satisfied
 LL |     type Assoc: Foo<Self> = ();
    |                             ^^ the trait `Foo<Self>` is not implemented for `()`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/defaults-suitability.rs:27:1
+   |
+LL | trait Foo<T> {
+   | ^^^^^^^^^^^^
 note: required by a bound in `Bar::Assoc`
   --> $DIR/defaults-suitability.rs:34:17
    |
diff --git a/tests/ui/associated-types/issue-59324.stderr b/tests/ui/associated-types/issue-59324.stderr
index a84b599b52b..266e22d4726 100644
--- a/tests/ui/associated-types/issue-59324.stderr
+++ b/tests/ui/associated-types/issue-59324.stderr
@@ -48,6 +48,12 @@ error[E0277]: the trait bound `(): Foo` is not satisfied
    |
 LL | fn with_factory<H>(factory: dyn ThriftService<()>) {}
    |                             ^^^^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `()`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-59324.rs:3:1
+   |
+LL | pub trait Foo: NotFoo {
+   | ^^^^^^^^^^^^^^^^^^^^^
 
 error[E0277]: the trait bound `Bug: Foo` is not satisfied
   --> $DIR/issue-59324.rs:19:10
diff --git a/tests/ui/associated-types/issue-64855.stderr b/tests/ui/associated-types/issue-64855.stderr
index 6ad795c1117..f1016f0e3a1 100644
--- a/tests/ui/associated-types/issue-64855.stderr
+++ b/tests/ui/associated-types/issue-64855.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `Bar<T>: Foo` is not satisfied
    |
 LL | pub struct Bar<T>(<Self as Foo>::Type) where Self: ;
    |                   ^^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `Bar<T>`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-64855.rs:1:1
+   |
+LL | pub trait Foo {
+   | ^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/associated-types/point-at-type-on-obligation-failure-2.stderr b/tests/ui/associated-types/point-at-type-on-obligation-failure-2.stderr
index 3b4689e08cc..056d9201b4a 100644
--- a/tests/ui/associated-types/point-at-type-on-obligation-failure-2.stderr
+++ b/tests/ui/associated-types/point-at-type-on-obligation-failure-2.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `bool: Bar` is not satisfied
 LL |     type Assoc = bool;
    |                  ^^^^ the trait `Bar` is not implemented for `bool`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/point-at-type-on-obligation-failure-2.rs:1:1
+   |
+LL | trait Bar {}
+   | ^^^^^^^^^
 note: required by a bound in `Foo::Assoc`
   --> $DIR/point-at-type-on-obligation-failure-2.rs:4:17
    |
@@ -16,6 +21,11 @@ error[E0277]: the trait bound `bool: Bar` is not satisfied
 LL |     type Assoc = bool;
    |                  ^^^^ the trait `Bar` is not implemented for `bool`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/point-at-type-on-obligation-failure-2.rs:1:1
+   |
+LL | trait Bar {}
+   | ^^^^^^^^^
 note: required by a bound in `Baz::Assoc`
   --> $DIR/point-at-type-on-obligation-failure-2.rs:13:18
    |
@@ -31,6 +41,11 @@ error[E0277]: the trait bound `bool: Bar` is not satisfied
 LL |     type Assoc = bool;
    |                  ^^^^ the trait `Bar` is not implemented for `bool`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/point-at-type-on-obligation-failure-2.rs:1:1
+   |
+LL | trait Bar {}
+   | ^^^^^^^^^
 note: required by a bound in `Bat::Assoc`
   --> $DIR/point-at-type-on-obligation-failure-2.rs:24:27
    |
diff --git a/tests/ui/async-await/in-trait/indirect-recursion-issue-112047.rs b/tests/ui/async-await/in-trait/indirect-recursion-issue-112047.rs
new file mode 100644
index 00000000000..85d17ddff94
--- /dev/null
+++ b/tests/ui/async-await/in-trait/indirect-recursion-issue-112047.rs
@@ -0,0 +1,38 @@
+// edition: 2021
+// build-fail
+//~^^ ERROR overflow evaluating the requirement `<A as Second>::{opaque#0} == _`
+
+#![feature(async_fn_in_trait)]
+
+fn main() {
+    let _ = async {
+        A.first().await.second().await;
+    };
+}
+
+pub trait First {
+    type Second: Second;
+    async fn first(self) -> Self::Second;
+}
+
+struct A;
+
+impl First for A {
+    type Second = A;
+    async fn first(self) -> Self::Second {
+        A
+    }
+}
+
+pub trait Second {
+    async fn second(self);
+}
+
+impl<C> Second for C
+where
+    C: First,
+{
+    async fn second(self) {
+        self.first().await.second().await;
+    }
+}
diff --git a/tests/ui/async-await/in-trait/indirect-recursion-issue-112047.stderr b/tests/ui/async-await/in-trait/indirect-recursion-issue-112047.stderr
new file mode 100644
index 00000000000..3f487a6e5fe
--- /dev/null
+++ b/tests/ui/async-await/in-trait/indirect-recursion-issue-112047.stderr
@@ -0,0 +1,5 @@
+error[E0275]: overflow evaluating the requirement `<A as Second>::{opaque#0} == _`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0275`.
diff --git a/tests/ui/async-await/issues/issue-66695-static-refs.rs b/tests/ui/async-await/issues/issue-66695-static-refs.rs
index f0609713b4d..1b0e1c6c9e7 100644
--- a/tests/ui/async-await/issues/issue-66695-static-refs.rs
+++ b/tests/ui/async-await/issues/issue-66695-static-refs.rs
@@ -1,12 +1,15 @@
 // build-pass
 // edition:2018
 
+#![feature(if_let_guard)]
+
 static A: [i32; 5] = [1, 2, 3, 4, 5];
 
 async fn fun() {
     let u = A[async { 1 }.await];
     match A {
         i if async { true }.await => (),
+        i if let Some(1) = async { Some(1) }.await => (),
         _ => (),
     }
 }
@@ -18,6 +21,7 @@ fn main() {
     async {
         match A {
             i if async { true }.await => (),
+            i if let Some(2) = async { Some(2) }.await => (),
             _ => (),
         }
     };
diff --git a/tests/ui/async-await/issues/issue-67611-static-mut-refs.rs b/tests/ui/async-await/issues/issue-67611-static-mut-refs.rs
index c4f8f607d25..80d824d3b2e 100644
--- a/tests/ui/async-await/issues/issue-67611-static-mut-refs.rs
+++ b/tests/ui/async-await/issues/issue-67611-static-mut-refs.rs
@@ -5,6 +5,8 @@
 // [drop_tracking] compile-flags: -Zdrop-tracking
 // [drop_tracking_mir] compile-flags: -Zdrop-tracking-mir
 
+#![feature(if_let_guard)]
+
 static mut A: [i32; 5] = [1, 2, 3, 4, 5];
 
 fn is_send_sync<T: Send + Sync>(_: T) {}
@@ -14,6 +16,7 @@ async fn fun() {
     unsafe {
         match A {
             i if async { true }.await => (),
+            i if let Some(1) = async { Some(1) }.await => (),
             _ => (),
         }
     }
@@ -27,6 +30,7 @@ fn main() {
         unsafe {
             match A {
                 i if async { true }.await => (),
+                i if let Some(2) = async { Some(2) }.await => (),
                 _ => (),
             }
         }
diff --git a/tests/ui/async-await/missed-capture-issue-107414.rs b/tests/ui/async-await/missed-capture-issue-107414.rs
index 0ab4f5ade98..bb14eb74b3a 100644
--- a/tests/ui/async-await/missed-capture-issue-107414.rs
+++ b/tests/ui/async-await/missed-capture-issue-107414.rs
@@ -1,6 +1,8 @@
 // check-pass
 // edition:2018
 
+#![feature(if_let_guard)]
+
 fn main() {}
 
 struct StructA {}
@@ -22,3 +24,10 @@ async fn ice() {
         _ => {}
     }
 }
+
+async fn if_let() {
+    match Some(StructB {}) {
+        Some(struct_b) if let true = get_struct_a_async().await.fn_taking_struct_b(&struct_b) => {}
+        _ => {}
+    }
+}
diff --git a/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.current.stderr b/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.current.stderr
index 3b63ec45804..8f45902035e 100644
--- a/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.current.stderr
+++ b/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.current.stderr
@@ -16,6 +16,14 @@ LL |     build(Bar);
    |     required by a bound introduced by this call
    |
    = help: the trait `for<'a> Send` is not implemented for `impl Future<Output = ()> { <_ as Foo>::bar() }`
+note: this is a known limitation of the trait solver that will be lifted in the future
+  --> $DIR/normalizing-self-auto-trait-issue-109924.rs:23:11
+   |
+LL |     build(Bar);
+   |     ------^^^-
+   |     |     |
+   |     |     the trait solver is unable to infer the generic types that should be inferred from this argument
+   |     add turbofish arguments to this call to specify the types manually, even if it's redundant
 note: required by a bound in `build`
   --> $DIR/normalizing-self-auto-trait-issue-109924.rs:20:39
    |
diff --git a/tests/ui/binding/match-beginning-vert.rs b/tests/ui/binding/match-beginning-vert.rs
index 79267400b28..93c08f0b710 100644
--- a/tests/ui/binding/match-beginning-vert.rs
+++ b/tests/ui/binding/match-beginning-vert.rs
@@ -1,4 +1,7 @@
 // run-pass
+
+#![feature(if_let_guard)]
+
 enum Foo {
     A,
     B,
@@ -13,6 +16,7 @@ fn main() {
         match *foo {
             | A => println!("A"),
             | B | C if 1 < 2 => println!("BC!"),
+            | D if let 1 = 1 => println!("D!"),
             | _ => {},
         }
     }
diff --git a/tests/ui/borrowck/issue-115259-suggest-iter-mut.fixed b/tests/ui/borrowck/issue-115259-suggest-iter-mut.fixed
new file mode 100644
index 00000000000..4653fe7375d
--- /dev/null
+++ b/tests/ui/borrowck/issue-115259-suggest-iter-mut.fixed
@@ -0,0 +1,20 @@
+// run-rustfix
+#![allow(unused_mut)]
+#![allow(dead_code)]
+
+pub trait Layer {
+    fn process(&mut self) -> u32;
+}
+
+pub struct State {
+    layers: Vec<Box<dyn Layer>>,
+}
+
+impl State {
+    pub fn process(&mut self) -> u32 {
+        self.layers.iter_mut().fold(0, |result, mut layer| result + layer.process())
+        //~^ ERROR cannot borrow `**layer` as mutable, as it is behind a `&` reference
+    }
+}
+
+fn main() {}
diff --git a/tests/ui/borrowck/issue-115259-suggest-iter-mut.rs b/tests/ui/borrowck/issue-115259-suggest-iter-mut.rs
new file mode 100644
index 00000000000..e0f6ab1321f
--- /dev/null
+++ b/tests/ui/borrowck/issue-115259-suggest-iter-mut.rs
@@ -0,0 +1,20 @@
+// run-rustfix
+#![allow(unused_mut)]
+#![allow(dead_code)]
+
+pub trait Layer {
+    fn process(&mut self) -> u32;
+}
+
+pub struct State {
+    layers: Vec<Box<dyn Layer>>,
+}
+
+impl State {
+    pub fn process(&mut self) -> u32 {
+        self.layers.iter().fold(0, |result, mut layer| result + layer.process())
+        //~^ ERROR cannot borrow `**layer` as mutable, as it is behind a `&` reference
+    }
+}
+
+fn main() {}
diff --git a/tests/ui/borrowck/issue-115259-suggest-iter-mut.stderr b/tests/ui/borrowck/issue-115259-suggest-iter-mut.stderr
new file mode 100644
index 00000000000..7e0fc2cf298
--- /dev/null
+++ b/tests/ui/borrowck/issue-115259-suggest-iter-mut.stderr
@@ -0,0 +1,16 @@
+error[E0596]: cannot borrow `**layer` as mutable, as it is behind a `&` reference
+  --> $DIR/issue-115259-suggest-iter-mut.rs:15:65
+   |
+LL |         self.layers.iter().fold(0, |result, mut layer| result + layer.process())
+   |                                             ---------           ^^^^^ `layer` is a `&` reference, so the data it refers to cannot be borrowed as mutable
+   |                                             |
+   |                                             consider changing this binding's type to be: `&mut Box<dyn Layer>`
+   |
+help: you may want to use `iter_mut` here
+   |
+LL |         self.layers.iter_mut().fold(0, |result, mut layer| result + layer.process())
+   |                     ~~~~~~~~
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0596`.
diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.fixed b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.fixed
new file mode 100644
index 00000000000..f02374d8e11
--- /dev/null
+++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.fixed
@@ -0,0 +1,36 @@
+// run-rustfix
+#![allow(unused_mut)]
+#![allow(dead_code)]
+use std::path::PathBuf;
+
+#[derive(Clone)]
+struct Container {
+    things: Vec<PathBuf>,
+}
+
+impl Container {
+    fn things(&mut self) -> &[PathBuf] {
+        &self.things
+    }
+}
+
+// contains containers
+struct ContainerContainer {
+    contained: Vec<Container>,
+}
+
+impl ContainerContainer {
+    fn contained(&self) -> &[Container] {
+        &self.contained
+    }
+
+    fn all_the_things(&mut self) -> &[PathBuf] {
+        let mut vec = self.contained.clone();
+        let _a =
+            vec.iter_mut().flat_map(|container| container.things()).cloned().collect::<Vec<PathBuf>>();
+        //~^ ERROR cannot borrow `*container` as mutable, as it is behind a `&` reference
+        unimplemented!();
+    }
+}
+
+fn main() {}
diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.rs b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.rs
new file mode 100644
index 00000000000..2d0b837a946
--- /dev/null
+++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.rs
@@ -0,0 +1,36 @@
+// run-rustfix
+#![allow(unused_mut)]
+#![allow(dead_code)]
+use std::path::PathBuf;
+
+#[derive(Clone)]
+struct Container {
+    things: Vec<PathBuf>,
+}
+
+impl Container {
+    fn things(&mut self) -> &[PathBuf] {
+        &self.things
+    }
+}
+
+// contains containers
+struct ContainerContainer {
+    contained: Vec<Container>,
+}
+
+impl ContainerContainer {
+    fn contained(&self) -> &[Container] {
+        &self.contained
+    }
+
+    fn all_the_things(&mut self) -> &[PathBuf] {
+        let mut vec = self.contained.clone();
+        let _a =
+            vec.iter().flat_map(|container| container.things()).cloned().collect::<Vec<PathBuf>>();
+        //~^ ERROR cannot borrow `*container` as mutable, as it is behind a `&` reference
+        unimplemented!();
+    }
+}
+
+fn main() {}
diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.stderr b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.stderr
new file mode 100644
index 00000000000..19f194100a1
--- /dev/null
+++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.stderr
@@ -0,0 +1,16 @@
+error[E0596]: cannot borrow `*container` as mutable, as it is behind a `&` reference
+  --> $DIR/issue-62387-suggest-iter-mut-2.rs:30:45
+   |
+LL |             vec.iter().flat_map(|container| container.things()).cloned().collect::<Vec<PathBuf>>();
+   |                                  ---------  ^^^^^^^^^ `container` is a `&` reference, so the data it refers to cannot be borrowed as mutable
+   |                                  |
+   |                                  consider changing this binding's type to be: `&mut Container`
+   |
+help: you may want to use `iter_mut` here
+   |
+LL |             vec.iter_mut().flat_map(|container| container.things()).cloned().collect::<Vec<PathBuf>>();
+   |                 ~~~~~~~~
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0596`.
diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut.fixed b/tests/ui/borrowck/issue-62387-suggest-iter-mut.fixed
new file mode 100644
index 00000000000..8bf2625de6d
--- /dev/null
+++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut.fixed
@@ -0,0 +1,30 @@
+// run-rustfix
+#![allow(unused_mut)]
+#![allow(dead_code)]
+
+#[derive(Debug)]
+struct A {
+    a: i32,
+}
+
+impl A {
+    fn double(&mut self) {
+        self.a += self.a
+    }
+}
+
+fn baz() {
+    let mut v = [A { a: 4 }];
+    v.iter_mut().for_each(|a| a.double());
+    //~^ ERROR cannot borrow `*a` as mutable, as it is behind a `&` reference
+    println!("{:?}", v);
+}
+
+fn bar() {
+    let mut v = [A { a: 4 }];
+    v.iter_mut().rev().rev().for_each(|a| a.double());
+    //~^ ERROR cannot borrow `*a` as mutable, as it is behind a `&` reference
+    println!("{:?}", v);
+}
+
+fn main() {}
diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut.rs b/tests/ui/borrowck/issue-62387-suggest-iter-mut.rs
new file mode 100644
index 00000000000..39bc30bf294
--- /dev/null
+++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut.rs
@@ -0,0 +1,30 @@
+// run-rustfix
+#![allow(unused_mut)]
+#![allow(dead_code)]
+
+#[derive(Debug)]
+struct A {
+    a: i32,
+}
+
+impl A {
+    fn double(&mut self) {
+        self.a += self.a
+    }
+}
+
+fn baz() {
+    let mut v = [A { a: 4 }];
+    v.iter().for_each(|a| a.double());
+    //~^ ERROR cannot borrow `*a` as mutable, as it is behind a `&` reference
+    println!("{:?}", v);
+}
+
+fn bar() {
+    let mut v = [A { a: 4 }];
+    v.iter().rev().rev().for_each(|a| a.double());
+    //~^ ERROR cannot borrow `*a` as mutable, as it is behind a `&` reference
+    println!("{:?}", v);
+}
+
+fn main() {}
diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut.stderr b/tests/ui/borrowck/issue-62387-suggest-iter-mut.stderr
new file mode 100644
index 00000000000..fd58e433020
--- /dev/null
+++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut.stderr
@@ -0,0 +1,29 @@
+error[E0596]: cannot borrow `*a` as mutable, as it is behind a `&` reference
+  --> $DIR/issue-62387-suggest-iter-mut.rs:18:27
+   |
+LL |     v.iter().for_each(|a| a.double());
+   |                        -  ^ `a` is a `&` reference, so the data it refers to cannot be borrowed as mutable
+   |                        |
+   |                        consider changing this binding's type to be: `&mut A`
+   |
+help: you may want to use `iter_mut` here
+   |
+LL |     v.iter_mut().for_each(|a| a.double());
+   |       ~~~~~~~~
+
+error[E0596]: cannot borrow `*a` as mutable, as it is behind a `&` reference
+  --> $DIR/issue-62387-suggest-iter-mut.rs:25:39
+   |
+LL |     v.iter().rev().rev().for_each(|a| a.double());
+   |                                    -  ^ `a` is a `&` reference, so the data it refers to cannot be borrowed as mutable
+   |                                    |
+   |                                    consider changing this binding's type to be: `&mut A`
+   |
+help: you may want to use `iter_mut` here
+   |
+LL |     v.iter_mut().rev().rev().for_each(|a| a.double());
+   |       ~~~~~~~~
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0596`.
diff --git a/tests/ui/borrowck/issue-81899.stderr b/tests/ui/borrowck/issue-81899.stderr
index 1b03bc3af9c..63e817239c6 100644
--- a/tests/ui/borrowck/issue-81899.stderr
+++ b/tests/ui/borrowck/issue-81899.stderr
@@ -16,7 +16,7 @@ LL | const _CONST: &[u8] = &f(&[], |_| {});
    |                        ^^^^^^^^^^^^^^
    = 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 used
+note: erroneous constant encountered
   --> $DIR/issue-81899.rs:4:23
    |
 LL | const _CONST: &[u8] = &f(&[], |_| {});
diff --git a/tests/ui/borrowck/issue-88434-minimal-example.stderr b/tests/ui/borrowck/issue-88434-minimal-example.stderr
index a5a571c6d4d..4c887b2ad42 100644
--- a/tests/ui/borrowck/issue-88434-minimal-example.stderr
+++ b/tests/ui/borrowck/issue-88434-minimal-example.stderr
@@ -16,7 +16,7 @@ LL | const _CONST: &() = &f(&|_| {});
    |                      ^^^^^^^^^^
    = 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 used
+note: erroneous constant encountered
   --> $DIR/issue-88434-minimal-example.rs:3:21
    |
 LL | const _CONST: &() = &f(&|_| {});
diff --git a/tests/ui/borrowck/issue-88434-removal-index-should-be-less.stderr b/tests/ui/borrowck/issue-88434-removal-index-should-be-less.stderr
index 00023c459a8..f7257817a8b 100644
--- a/tests/ui/borrowck/issue-88434-removal-index-should-be-less.stderr
+++ b/tests/ui/borrowck/issue-88434-removal-index-should-be-less.stderr
@@ -16,7 +16,7 @@ LL | const _CONST: &[u8] = &f(&[], |_| {});
    |                        ^^^^^^^^^^^^^^
    = 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 used
+note: erroneous constant encountered
   --> $DIR/issue-88434-removal-index-should-be-less.rs:3:23
    |
 LL | const _CONST: &[u8] = &f(&[], |_| {});
diff --git a/tests/ui/c-variadic/variadic-ffi-2.rs b/tests/ui/c-variadic/variadic-ffi-2.rs
index c34b7e55f6a..67a0a9a1dec 100644
--- a/tests/ui/c-variadic/variadic-ffi-2.rs
+++ b/tests/ui/c-variadic/variadic-ffi-2.rs
@@ -3,10 +3,13 @@
 
 fn baz(f: extern "stdcall" fn(usize, ...)) {
     //~^ ERROR: C-variadic function must have a compatible calling convention,
-    // like C, cdecl, win64, sysv64 or efiapi
+    // like C, cdecl, aapcs, win64, sysv64 or efiapi
     f(22, 44);
 }
 
+fn aapcs(f: extern "aapcs" fn(usize, ...)) {
+    f(22, 44);
+}
 fn sysv(f: extern "sysv64" fn(usize, ...)) {
     f(22, 44);
 }
diff --git a/tests/ui/c-variadic/variadic-ffi-2.stderr b/tests/ui/c-variadic/variadic-ffi-2.stderr
index e21001ecaf8..8884fc6fb2a 100644
--- a/tests/ui/c-variadic/variadic-ffi-2.stderr
+++ b/tests/ui/c-variadic/variadic-ffi-2.stderr
@@ -1,4 +1,4 @@
-error[E0045]: C-variadic function must have a compatible calling convention, like `C`, `cdecl`, `win64`, `sysv64` or `efiapi`
+error[E0045]: C-variadic function must have a compatible calling convention, like `C`, `cdecl`, `aapcs`, `win64`, `sysv64` or `efiapi`
   --> $DIR/variadic-ffi-2.rs:4:11
    |
 LL | fn baz(f: extern "stdcall" fn(usize, ...)) {
diff --git a/tests/ui/cast/cast-as-bool.rs b/tests/ui/cast/cast-as-bool.rs
index fbebc80d91c..511a02718fe 100644
--- a/tests/ui/cast/cast-as-bool.rs
+++ b/tests/ui/cast/cast-as-bool.rs
@@ -1,11 +1,47 @@
 fn main() {
-    let u = 5 as bool; //~ ERROR cannot cast as `bool`
+    let u = 5 as bool; //~ ERROR cannot cast `i32` as `bool`
                        //~| HELP compare with zero instead
-                       //~| SUGGESTION 5 != 0
+                       //~| SUGGESTION != 0
 
-    let t = (1 + 2) as bool; //~ ERROR cannot cast as `bool`
+    let t = (1 + 2) as bool; //~ ERROR cannot cast `i32` as `bool`
                              //~| HELP compare with zero instead
-                             //~| SUGGESTION (1 + 2) != 0
+                             //~| SUGGESTION != 0
+
+    let _ = 5_u32 as bool; //~ ERROR cannot cast `u32` as `bool`
+                           //~| HELP compare with zero instead
+
+    let _ = 64.0_f64 as bool; //~ ERROR cannot cast `f64` as `bool`
+                              //~| HELP compare with zero instead
+
+    // Enums that can normally be cast to integers can't be cast to `bool`, just like integers.
+    // Note that enums that cannot be cast to integers can't be cast to anything at *all*
+    // so that's not tested here.
+    enum IntEnum {
+        Zero,
+        One,
+        Two
+    }
+    let _ = IntEnum::One as bool; //~ ERROR cannot cast `IntEnum` as `bool`
+
+    fn uwu(_: u8) -> String {
+        todo!()
+    }
+
+    unsafe fn owo() {}
+
+    // fn item to bool
+    let _ = uwu as bool; //~ ERROR cannot cast `fn(u8) -> String {uwu}` as `bool`
+    // unsafe fn item
+    let _ = owo as bool; //~ ERROR cannot cast `unsafe fn() {owo}` as `bool`
+
+    // fn ptr to bool
+    let _ = uwu as fn(u8) -> String as bool; //~ ERROR cannot cast `fn(u8) -> String` as `bool`
+
+    let _ = 'x' as bool; //~ ERROR cannot cast `char` as `bool`
+
+    let ptr = 1 as *const ();
+
+    let _ = ptr as bool; //~ ERROR cannot cast `*const ()` as `bool`
 
     let v = "hello" as bool;
     //~^ ERROR casting `&'static str` as `bool` is invalid
diff --git a/tests/ui/cast/cast-as-bool.stderr b/tests/ui/cast/cast-as-bool.stderr
index 19ac8f10fec..4ff56a95e49 100644
--- a/tests/ui/cast/cast-as-bool.stderr
+++ b/tests/ui/cast/cast-as-bool.stderr
@@ -1,18 +1,86 @@
-error[E0054]: cannot cast as `bool`
+error[E0054]: cannot cast `i32` as `bool`
   --> $DIR/cast-as-bool.rs:2:13
    |
 LL |     let u = 5 as bool;
-   |             ^^^^^^^^^ help: compare with zero instead: `5 != 0`
+   |             ^^^^^^^^^
+   |
+help: compare with zero instead
+   |
+LL |     let u = 5 != 0;
+   |               ~~~~
 
-error[E0054]: cannot cast as `bool`
+error[E0054]: cannot cast `i32` as `bool`
   --> $DIR/cast-as-bool.rs:6:13
    |
 LL |     let t = (1 + 2) as bool;
-   |             ^^^^^^^^^^^^^^^ help: compare with zero instead: `(1 + 2) != 0`
+   |             ^^^^^^^^^^^^^^^
+   |
+help: compare with zero instead
+   |
+LL |     let t = (1 + 2) != 0;
+   |                     ~~~~
 
-error[E0606]: casting `&'static str` as `bool` is invalid
+error[E0054]: cannot cast `u32` as `bool`
   --> $DIR/cast-as-bool.rs:10:13
    |
+LL |     let _ = 5_u32 as bool;
+   |             ^^^^^^^^^^^^^
+   |
+help: compare with zero instead
+   |
+LL |     let _ = 5_u32 != 0;
+   |                   ~~~~
+
+error[E0054]: cannot cast `f64` as `bool`
+  --> $DIR/cast-as-bool.rs:13:13
+   |
+LL |     let _ = 64.0_f64 as bool;
+   |             ^^^^^^^^^^^^^^^^
+   |
+help: compare with zero instead
+   |
+LL |     let _ = 64.0_f64 != 0;
+   |                      ~~~~
+
+error[E0054]: cannot cast `IntEnum` as `bool`
+  --> $DIR/cast-as-bool.rs:24:13
+   |
+LL |     let _ = IntEnum::One as bool;
+   |             ^^^^^^^^^^^^^^^^^^^^ unsupported cast
+
+error[E0054]: cannot cast `fn(u8) -> String {uwu}` as `bool`
+  --> $DIR/cast-as-bool.rs:33:13
+   |
+LL |     let _ = uwu as bool;
+   |             ^^^^^^^^^^^ unsupported cast
+
+error[E0054]: cannot cast `unsafe fn() {owo}` as `bool`
+  --> $DIR/cast-as-bool.rs:35:13
+   |
+LL |     let _ = owo as bool;
+   |             ^^^^^^^^^^^ unsupported cast
+
+error[E0054]: cannot cast `fn(u8) -> String` as `bool`
+  --> $DIR/cast-as-bool.rs:38:13
+   |
+LL |     let _ = uwu as fn(u8) -> String as bool;
+   |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ unsupported cast
+
+error[E0054]: cannot cast `char` as `bool`
+  --> $DIR/cast-as-bool.rs:40:13
+   |
+LL |     let _ = 'x' as bool;
+   |             ^^^^^^^^^^^ unsupported cast
+
+error[E0054]: cannot cast `*const ()` as `bool`
+  --> $DIR/cast-as-bool.rs:44:13
+   |
+LL |     let _ = ptr as bool;
+   |             ^^^^^^^^^^^ unsupported cast
+
+error[E0606]: casting `&'static str` as `bool` is invalid
+  --> $DIR/cast-as-bool.rs:46:13
+   |
 LL |     let v = "hello" as bool;
    |             ^^^^^^^^^^^^^^^
    |
@@ -21,7 +89,7 @@ help: consider using the `is_empty` method on `&'static str` to determine if it
 LL |     let v = !"hello".is_empty();
    |             +       ~~~~~~~~~~~
 
-error: aborting due to 3 previous errors
+error: aborting due to 11 previous errors
 
 Some errors have detailed explanations: E0054, E0606.
 For more information about an error, try `rustc --explain E0054`.
diff --git a/tests/ui/cast/cast-rfc0401-2.rs b/tests/ui/cast/cast-rfc0401-2.rs
index 7709aa34104..70604a587ea 100644
--- a/tests/ui/cast/cast-rfc0401-2.rs
+++ b/tests/ui/cast/cast-rfc0401-2.rs
@@ -4,5 +4,5 @@
 
 fn main() {
     let _ = 3 as bool;
-    //~^ ERROR cannot cast as `bool`
+    //~^ ERROR cannot cast `i32` as `bool`
 }
diff --git a/tests/ui/cast/cast-rfc0401-2.stderr b/tests/ui/cast/cast-rfc0401-2.stderr
index 52f6af78a9b..dd90c3a9723 100644
--- a/tests/ui/cast/cast-rfc0401-2.stderr
+++ b/tests/ui/cast/cast-rfc0401-2.stderr
@@ -1,8 +1,13 @@
-error[E0054]: cannot cast as `bool`
+error[E0054]: cannot cast `i32` as `bool`
   --> $DIR/cast-rfc0401-2.rs:6:13
    |
 LL |     let _ = 3 as bool;
-   |             ^^^^^^^^^ help: compare with zero instead: `3 != 0`
+   |             ^^^^^^^^^
+   |
+help: compare with zero instead
+   |
+LL |     let _ = 3 != 0;
+   |               ~~~~
 
 error: aborting due to previous error
 
diff --git a/tests/ui/closures/2229_closure_analysis/repr_packed.rs b/tests/ui/closures/2229_closure_analysis/repr_packed.rs
index f23670f63ac..8c23454fae9 100644
--- a/tests/ui/closures/2229_closure_analysis/repr_packed.rs
+++ b/tests/ui/closures/2229_closure_analysis/repr_packed.rs
@@ -3,7 +3,8 @@
 #![feature(rustc_attrs)]
 
 // `u8` aligned at a byte and are unaffected by repr(packed).
-// Therefore we can precisely (and safely) capture references to both the fields.
+// Therefore we *could* precisely (and safely) capture references to both the fields,
+// but we don't, since we don't want capturing to change when field types change alignment.
 fn test_alignment_not_affected() {
     #[repr(packed)]
     struct Foo { x: u8, y: u8 }
@@ -17,11 +18,10 @@ fn test_alignment_not_affected() {
     //~^ ERROR: First Pass analysis includes:
     //~| ERROR: Min Capture analysis includes:
         let z1: &u8 = &foo.x;
-        //~^ NOTE: Capturing foo[(0, 0)] -> ImmBorrow
-        //~| NOTE: Min Capture foo[(0, 0)] -> ImmBorrow
+        //~^ NOTE: Capturing foo[] -> ImmBorrow
         let z2: &mut u8 = &mut foo.y;
-        //~^ NOTE: Capturing foo[(1, 0)] -> MutBorrow
-        //~| NOTE: Min Capture foo[(1, 0)] -> MutBorrow
+        //~^ NOTE: Capturing foo[] -> MutBorrow
+        //~| NOTE: Min Capture foo[] -> MutBorrow
 
         *z2 = 42;
 
diff --git a/tests/ui/closures/2229_closure_analysis/repr_packed.stderr b/tests/ui/closures/2229_closure_analysis/repr_packed.stderr
index 580061ebc6e..32b3d844c6e 100644
--- a/tests/ui/closures/2229_closure_analysis/repr_packed.stderr
+++ b/tests/ui/closures/2229_closure_analysis/repr_packed.stderr
@@ -1,5 +1,5 @@
 error[E0658]: attributes on expressions are experimental
-  --> $DIR/repr_packed.rs:13:17
+  --> $DIR/repr_packed.rs:14:17
    |
 LL |     let mut c = #[rustc_capture_analysis]
    |                 ^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -26,7 +26,7 @@ LL |     let c = #[rustc_capture_analysis]
    = help: add `#![feature(stmt_expr_attributes)]` to the crate attributes to enable
 
 error: First Pass analysis includes:
-  --> $DIR/repr_packed.rs:16:5
+  --> $DIR/repr_packed.rs:17:5
    |
 LL | /     || {
 LL | |
@@ -37,19 +37,19 @@ LL | |         println!("({}, {})", z1, z2);
 LL | |     };
    | |_____^
    |
-note: Capturing foo[(0, 0)] -> ImmBorrow
-  --> $DIR/repr_packed.rs:19:24
+note: Capturing foo[] -> ImmBorrow
+  --> $DIR/repr_packed.rs:20:24
    |
 LL |         let z1: &u8 = &foo.x;
    |                        ^^^^^
-note: Capturing foo[(1, 0)] -> MutBorrow
+note: Capturing foo[] -> MutBorrow
   --> $DIR/repr_packed.rs:22:32
    |
 LL |         let z2: &mut u8 = &mut foo.y;
    |                                ^^^^^
 
 error: Min Capture analysis includes:
-  --> $DIR/repr_packed.rs:16:5
+  --> $DIR/repr_packed.rs:17:5
    |
 LL | /     || {
 LL | |
@@ -60,12 +60,7 @@ LL | |         println!("({}, {})", z1, z2);
 LL | |     };
    | |_____^
    |
-note: Min Capture foo[(0, 0)] -> ImmBorrow
-  --> $DIR/repr_packed.rs:19:24
-   |
-LL |         let z1: &u8 = &foo.x;
-   |                        ^^^^^
-note: Min Capture foo[(1, 0)] -> MutBorrow
+note: Min Capture foo[] -> MutBorrow
   --> $DIR/repr_packed.rs:22:32
    |
 LL |         let z2: &mut u8 = &mut foo.y;
diff --git a/tests/ui/codegen/subtyping-enforces-type-equality.rs b/tests/ui/codegen/subtyping-enforces-type-equality.rs
new file mode 100644
index 00000000000..a5ffcb3f854
--- /dev/null
+++ b/tests/ui/codegen/subtyping-enforces-type-equality.rs
@@ -0,0 +1,48 @@
+// ignore-pass
+// build-pass
+// edition:2021
+use std::future::Future;
+use std::pin::Pin;
+
+type BoxFuture<T> = Pin<Box<dyn Future<Output = T>>>;
+
+fn main() {
+    let _ = wrapper_call(handler);
+}
+
+async fn wrapper_call(handler: impl Handler) {
+    handler.call().await;
+}
+async fn handler() {
+    f(&()).await;
+}
+async fn f<'a>(db: impl Acquire<'a>) {
+    db.acquire().await;
+}
+
+trait Handler {
+    type Future: Future;
+    fn call(self) -> Self::Future;
+}
+
+impl<Fut, F> Handler for F
+where
+    F: Fn() -> Fut,
+    Fut: Future,
+{
+    type Future = Fut;
+    fn call(self) -> Self::Future {
+        loop {}
+    }
+}
+
+trait Acquire<'a> {
+    type Connection;
+    fn acquire(self) -> BoxFuture<Self::Connection>;
+}
+impl<'a> Acquire<'a> for &'a () {
+    type Connection = Self;
+    fn acquire(self) -> BoxFuture<Self> {
+        loop {}
+    }
+}
diff --git a/tests/ui/codegen/subtyping-enforces-type-equality.stderr b/tests/ui/codegen/subtyping-enforces-type-equality.stderr
new file mode 100644
index 00000000000..870ca0f839f
--- /dev/null
+++ b/tests/ui/codegen/subtyping-enforces-type-equality.stderr
@@ -0,0 +1 @@
+WARN rustc_codegen_ssa::mir::locals Unexpected initial operand type. See the issues/114858
diff --git a/tests/ui/coherence/coherence-unsafe-trait-object-impl.stderr b/tests/ui/coherence/coherence-unsafe-trait-object-impl.stderr
index 2e2dac288a1..a3a37fd2775 100644
--- a/tests/ui/coherence/coherence-unsafe-trait-object-impl.stderr
+++ b/tests/ui/coherence/coherence-unsafe-trait-object-impl.stderr
@@ -6,6 +6,11 @@ LL |     takes_t(t);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/coherence-unsafe-trait-object-impl.rs:6:1
+   |
+LL | trait Trait: Sized {
+   | ^^^^^^^^^^^^^^^^^^
 note: required by a bound in `takes_t`
   --> $DIR/coherence-unsafe-trait-object-impl.rs:10:15
    |
diff --git a/tests/ui/const-generics/dont-evaluate-array-len-on-err-1.stderr b/tests/ui/const-generics/dont-evaluate-array-len-on-err-1.stderr
index cb51d9b1ea5..b3a27566026 100644
--- a/tests/ui/const-generics/dont-evaluate-array-len-on-err-1.stderr
+++ b/tests/ui/const-generics/dont-evaluate-array-len-on-err-1.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `[Adt; std::mem::size_of::<Self::Assoc>()]: Foo` i
    |
 LL |         <[Adt; std::mem::size_of::<Self::Assoc>()] as Foo>::bar()
    |          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `[Adt; std::mem::size_of::<Self::Assoc>()]`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/dont-evaluate-array-len-on-err-1.rs:9:1
+   |
+LL | trait Foo {
+   | ^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/const-generics/early/const-param-from-outer-fn.rs b/tests/ui/const-generics/early/const-param-from-outer-fn.rs
index c3b418ee3f8..ee57f3c4fc3 100644
--- a/tests/ui/const-generics/early/const-param-from-outer-fn.rs
+++ b/tests/ui/const-generics/early/const-param-from-outer-fn.rs
@@ -1,6 +1,6 @@
 fn foo<const X: u32>() {
     fn bar() -> u32 {
-        X //~ ERROR can't use generic parameters from outer function
+        X //~ ERROR can't use generic parameters from outer item
     }
 }
 
diff --git a/tests/ui/const-generics/early/const-param-from-outer-fn.stderr b/tests/ui/const-generics/early/const-param-from-outer-fn.stderr
index e3bf38b702e..826f2657905 100644
--- a/tests/ui/const-generics/early/const-param-from-outer-fn.stderr
+++ b/tests/ui/const-generics/early/const-param-from-outer-fn.stderr
@@ -1,12 +1,12 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/const-param-from-outer-fn.rs:3:9
    |
 LL | fn foo<const X: u32>() {
-   |              - const parameter from outer function
+   |              - const parameter from outer item
 LL |     fn bar() -> u32 {
-   |           - help: try using a local generic parameter instead: `<X>`
+   |           - help: try introducing a local generic parameter here: `<X>`
 LL |         X
-   |         ^ use of generic parameter from outer function
+   |         ^ use of generic parameter from outer item
 
 error: aborting due to previous error
 
diff --git a/tests/ui/const-generics/generic_const_exprs/issue-85848.stderr b/tests/ui/const-generics/generic_const_exprs/issue-85848.stderr
index e50ac671eca..9391b1c1a17 100644
--- a/tests/ui/const-generics/generic_const_exprs/issue-85848.stderr
+++ b/tests/ui/const-generics/generic_const_exprs/issue-85848.stderr
@@ -6,7 +6,11 @@ LL |     writes_to_specific_path(&cap);
    |     |
    |     required by a bound introduced by this call
    |
-   = help: the trait `Delegates<U>` is implemented for `T`
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-85848.rs:4:1
+   |
+LL | trait _Contains<T> {
+   | ^^^^^^^^^^^^^^^^^^
 note: required for `&C` to implement `Contains<(), true>`
   --> $DIR/issue-85848.rs:21:12
    |
diff --git a/tests/ui/const-generics/issues/issue-86530.stderr b/tests/ui/const-generics/issues/issue-86530.stderr
index 620ed4f0fb2..d02808f7c56 100644
--- a/tests/ui/const-generics/issues/issue-86530.stderr
+++ b/tests/ui/const-generics/issues/issue-86530.stderr
@@ -6,6 +6,11 @@ LL |     z(" ");
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-86530.rs:4:1
+   |
+LL | pub trait X {
+   | ^^^^^^^^^^^
 note: required by a bound in `z`
   --> $DIR/issue-86530.rs:10:8
    |
diff --git a/tests/ui/const-generics/late-bound-vars/in_closure.rs b/tests/ui/const-generics/late-bound-vars/in_closure.rs
index 6549cad629b..443c755c601 100644
--- a/tests/ui/const-generics/late-bound-vars/in_closure.rs
+++ b/tests/ui/const-generics/late-bound-vars/in_closure.rs
@@ -1,23 +1,5 @@
-// failure-status: 1
 // known-bug: unknown
-// error-pattern:internal compiler error
-// normalize-stderr-test "internal compiler error.*" -> ""
-// normalize-stderr-test "DefId\([^)]*\)" -> "..."
-// normalize-stderr-test "\nerror: internal compiler error.*\n\n" -> ""
-// normalize-stderr-test "note:.*unexpectedly panicked.*\n\n" -> ""
-// normalize-stderr-test "note: we would appreciate a bug report.*\n\n" -> ""
-// normalize-stderr-test "note: compiler flags.*\n\n" -> ""
-// normalize-stderr-test "note: rustc.*running on.*\n\n" -> ""
-// normalize-stderr-test "thread.*panicked.*:\n.*\n" -> ""
-// normalize-stderr-test "stack backtrace:\n" -> ""
-// normalize-stderr-test "\s\d{1,}: .*\n" -> ""
-// normalize-stderr-test "\s at .*\n" -> ""
-// normalize-stderr-test ".*note: Some details.*\n" -> ""
-// normalize-stderr-test "\n[ ]*\n" -> ""
-// normalize-stderr-test "compiler/.*: projection" -> "projection"
-// normalize-stderr-test ".*omitted \d{1,} frame.*\n" -> ""
-// normalize-stderr-test "error: [\s\n]*query stack during panic:\n" -> ""
-// this should run-pass
+// see comment on `tests/ui/const-generics/late-bound-vars/simple.rs`
 
 #![feature(generic_const_exprs)]
 #![allow(incomplete_features)]
diff --git a/tests/ui/const-generics/late-bound-vars/in_closure.stderr b/tests/ui/const-generics/late-bound-vars/in_closure.stderr
index ac406bf2bb1..e15496454a0 100644
--- a/tests/ui/const-generics/late-bound-vars/in_closure.stderr
+++ b/tests/ui/const-generics/late-bound-vars/in_closure.stderr
@@ -1,10 +1,20 @@
-#0 [mir_borrowck] borrow-checking `test::{closure#0}::{constant#1}`
-#1 [mir_drops_elaborated_and_const_checked] elaborating drops for `test::{closure#0}::{constant#1}`
-#2 [mir_for_ctfe] caching mir of `test::{closure#0}::{constant#1}` for CTFE
-#3 [eval_to_allocation_raw] const-evaluating + checking `test::{closure#0}::{constant#1}`
-#4 [eval_to_allocation_raw] const-evaluating + checking `test::{closure#0}::{constant#1}`
-#5 [eval_to_valtree] evaluating type-level constant
-#6 [typeck] type-checking `test`
-#7 [analysis] running analysis passes on this crate
-end of query stack
-error: aborting due to previous error
\ No newline at end of file
+error: cannot capture late-bound lifetime in constant
+  --> $DIR/in_closure.rs:16:29
+   |
+LL | fn test<'a>() {
+   |         -- lifetime defined here
+LL |     let _ = || {
+LL |         let _: [u8; inner::<'a>()];
+   |                             ^^
+
+error: cannot capture late-bound lifetime in constant
+  --> $DIR/in_closure.rs:17:29
+   |
+LL | fn test<'a>() {
+   |         -- lifetime defined here
+...
+LL |         let _ = [0; inner::<'a>()];
+   |                             ^^
+
+error: aborting due to 2 previous errors
+
diff --git a/tests/ui/const-generics/late-bound-vars/late-bound-in-return-issue-77357.rs b/tests/ui/const-generics/late-bound-vars/late-bound-in-return-issue-77357.rs
new file mode 100644
index 00000000000..b81aa50d9a9
--- /dev/null
+++ b/tests/ui/const-generics/late-bound-vars/late-bound-in-return-issue-77357.rs
@@ -0,0 +1,13 @@
+// known-bug: unknown
+// see comment on `tests/ui/const-generics/late-bound-vars/simple.rs`
+
+#![feature(generic_const_exprs)]
+#![allow(incomplete_features)]
+
+trait MyTrait<T> {}
+
+fn bug<'a, T>() -> &'static dyn MyTrait<[(); { |x: &'a u32| { x }; 4 }]> {
+    todo!()
+}
+
+fn main() {}
diff --git a/tests/ui/const-generics/late-bound-vars/late-bound-in-return-issue-77357.stderr b/tests/ui/const-generics/late-bound-vars/late-bound-in-return-issue-77357.stderr
new file mode 100644
index 00000000000..21c8fe6865c
--- /dev/null
+++ b/tests/ui/const-generics/late-bound-vars/late-bound-in-return-issue-77357.stderr
@@ -0,0 +1,8 @@
+error: cannot capture late-bound lifetime in constant
+  --> $DIR/late-bound-in-return-issue-77357.rs:9:53
+   |
+LL | fn bug<'a, T>() -> &'static dyn MyTrait<[(); { |x: &'a u32| { x }; 4 }]> {
+   |        -- lifetime defined here                     ^^
+
+error: aborting due to previous error
+
diff --git a/tests/ui/const-generics/late-bound-vars/late-bound-in-where-issue-83993.rs b/tests/ui/const-generics/late-bound-vars/late-bound-in-where-issue-83993.rs
new file mode 100644
index 00000000000..89f01748fc9
--- /dev/null
+++ b/tests/ui/const-generics/late-bound-vars/late-bound-in-where-issue-83993.rs
@@ -0,0 +1,15 @@
+// known-bug: unknown
+// see comment on `tests/ui/const-generics/late-bound-vars/simple.rs`
+
+#![feature(generic_const_exprs)]
+#![allow(incomplete_features)]
+
+fn bug<'a>()
+where
+    for<'b> [(); {
+        let x: &'b ();
+        0
+    }]:
+{}
+
+fn main() {}
diff --git a/tests/ui/const-generics/late-bound-vars/late-bound-in-where-issue-83993.stderr b/tests/ui/const-generics/late-bound-vars/late-bound-in-where-issue-83993.stderr
new file mode 100644
index 00000000000..a66dc8db914
--- /dev/null
+++ b/tests/ui/const-generics/late-bound-vars/late-bound-in-where-issue-83993.stderr
@@ -0,0 +1,10 @@
+error: cannot capture late-bound lifetime in constant
+  --> $DIR/late-bound-in-where-issue-83993.rs:10:17
+   |
+LL |     for<'b> [(); {
+   |         -- lifetime defined here
+LL |         let x: &'b ();
+   |                 ^^
+
+error: aborting due to previous error
+
diff --git a/tests/ui/const-generics/late-bound-vars/simple.rs b/tests/ui/const-generics/late-bound-vars/simple.rs
index 544073b5a56..a562bd8cb41 100644
--- a/tests/ui/const-generics/late-bound-vars/simple.rs
+++ b/tests/ui/const-generics/late-bound-vars/simple.rs
@@ -1,22 +1,13 @@
-// failure-status: 101
 // known-bug: unknown
-// error-pattern:internal compiler error
-// normalize-stderr-test "internal compiler error.*" -> ""
-// normalize-stderr-test "DefId\([^)]*\)" -> "..."
-// normalize-stderr-test "\nerror: internal compiler error.*\n\n" -> ""
-// normalize-stderr-test "note:.*unexpectedly panicked.*\n\n" -> ""
-// normalize-stderr-test "note: we would appreciate a bug report.*\n\n" -> ""
-// normalize-stderr-test "note: compiler flags.*\n\n" -> ""
-// normalize-stderr-test "note: rustc.*running on.*\n\n" -> ""
-// normalize-stderr-test "thread.*panicked.*:\n.*\n" -> ""
-// normalize-stderr-test "stack backtrace:\n" -> ""
-// normalize-stderr-test "\s\d{1,}: .*\n" -> ""
-// normalize-stderr-test "\s at .*\n" -> ""
-// normalize-stderr-test ".*note: Some details.*\n" -> ""
-// normalize-stderr-test "\n\n[ ]*\n" -> ""
-// normalize-stderr-test "compiler/.*: projection" -> "projection"
-// normalize-stderr-test ".*omitted \d{1,} frame.*\n" -> ""
-// normalize-stderr-test "error: [\s\n]*query stack" -> "error: query stack"
+
+// If we want this to compile, then we'd need to do something like RPITs do,
+// where nested associated constants have early-bound versions of their captured
+// late-bound vars inserted into their generics. This gives us substitutable
+// lifetimes to actually use when borrow-checking the associated const, which is
+// lowered as a totally separate body from its parent. Since this doesn't exist,
+// we should just error rather than resolving this late-bound var with no
+// binder to actually attach it to, or worse, as a free region that can't even be
+// substituted correctly, and ICEing. - @compiler-errors
 
 #![feature(generic_const_exprs)]
 #![allow(incomplete_features)]
diff --git a/tests/ui/const-generics/late-bound-vars/simple.stderr b/tests/ui/const-generics/late-bound-vars/simple.stderr
index c9f2164b635..e72e373630d 100644
--- a/tests/ui/const-generics/late-bound-vars/simple.stderr
+++ b/tests/ui/const-generics/late-bound-vars/simple.stderr
@@ -1,12 +1,19 @@
-error: query stack during panic:
-#0 [mir_borrowck] borrow-checking `test::{constant#1}`
-#1 [mir_drops_elaborated_and_const_checked] elaborating drops for `test::{constant#1}`
-#2 [mir_for_ctfe] caching mir of `test::{constant#1}` for CTFE
-#3 [eval_to_allocation_raw] const-evaluating + checking `test::{constant#1}`
-#4 [eval_to_allocation_raw] const-evaluating + checking `test::{constant#1}`
-#5 [eval_to_valtree] evaluating type-level constant
-#6 [typeck] type-checking `test`
-#7 [analysis] running analysis passes on this crate
-end of query stack
-error: aborting due to previous error
+error: cannot capture late-bound lifetime in constant
+  --> $DIR/simple.rs:20:25
+   |
+LL | fn test<'a>() {
+   |         -- lifetime defined here
+LL |     let _: [u8; inner::<'a>()];
+   |                         ^^
+
+error: cannot capture late-bound lifetime in constant
+  --> $DIR/simple.rs:21:25
+   |
+LL | fn test<'a>() {
+   |         -- lifetime defined here
+LL |     let _: [u8; inner::<'a>()];
+LL |     let _ = [0; inner::<'a>()];
+   |                         ^^
+
+error: aborting due to 2 previous errors
 
diff --git a/tests/ui/const_prop/dont-propagate-generic-instance-2.rs b/tests/ui/const_prop/dont-propagate-generic-instance-2.rs
new file mode 100644
index 00000000000..e5525af23f0
--- /dev/null
+++ b/tests/ui/const_prop/dont-propagate-generic-instance-2.rs
@@ -0,0 +1,26 @@
+// run-pass
+
+#![feature(inline_const)]
+
+// Makes sure we don't propagate generic instances of `Self: ?Sized` blanket impls.
+// This is relevant when we have an overlapping impl and builtin dyn instance.
+// See <https://github.com/rust-lang/rust/pull/114941> for more context.
+
+trait Trait {
+    fn foo(&self) -> &'static str;
+}
+
+impl<T: ?Sized> Trait for T {
+    fn foo(&self) -> &'static str {
+        std::any::type_name::<T>()
+    }
+}
+
+fn bar<T: ?Sized>() -> fn(&T) -> &'static str {
+    const { Trait::foo as fn(&T) -> &'static str }
+    // If const prop were to propagate the instance
+}
+
+fn main() {
+    assert_eq!("i32", bar::<dyn Trait>()(&1i32));
+}
diff --git a/tests/ui/const_prop/dont-propagate-generic-instance.rs b/tests/ui/const_prop/dont-propagate-generic-instance.rs
new file mode 100644
index 00000000000..5994961b887
--- /dev/null
+++ b/tests/ui/const_prop/dont-propagate-generic-instance.rs
@@ -0,0 +1,24 @@
+// run-pass
+
+// Makes sure we don't propagate generic instances of `Self: ?Sized` blanket impls.
+// This is relevant when we have an overlapping impl and builtin dyn instance.
+// See <https://github.com/rust-lang/rust/pull/114941> for more context.
+
+trait Trait {
+    fn foo(&self) -> &'static str;
+}
+
+impl<T: ?Sized> Trait for T {
+    fn foo(&self) -> &'static str {
+        std::any::type_name::<T>()
+    }
+}
+
+const fn bar<T: ?Sized>() -> fn(&T) -> &'static str {
+    Trait::foo
+    // If const prop were to propagate the instance
+}
+
+fn main() {
+    assert_eq!("i32", bar::<dyn Trait>()(&1i32));
+}
diff --git a/tests/ui/consts/const-err-late.stderr b/tests/ui/consts/const-err-late.stderr
index 149d3b5236b..85bc56baed8 100644
--- a/tests/ui/consts/const-err-late.stderr
+++ b/tests/ui/consts/const-err-late.stderr
@@ -4,7 +4,7 @@ error[E0080]: evaluation of `S::<i32>::FOO` failed
 LL |     const FOO: u8 = [5u8][1];
    |                     ^^^^^^^^ index out of bounds: the length is 1 but the index is 1
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-err-late.rs:19:16
    |
 LL |     black_box((S::<i32>::FOO, S::<u32>::FOO));
@@ -16,13 +16,13 @@ error[E0080]: evaluation of `S::<u32>::FOO` failed
 LL |     const FOO: u8 = [5u8][1];
    |                     ^^^^^^^^ index out of bounds: the length is 1 but the index is 1
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-err-late.rs:19:31
    |
 LL |     black_box((S::<i32>::FOO, S::<u32>::FOO));
    |                               ^^^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-err-late.rs:19:16
    |
 LL |     black_box((S::<i32>::FOO, S::<u32>::FOO));
diff --git a/tests/ui/consts/const-err-multi.stderr b/tests/ui/consts/const-err-multi.stderr
index 28af8e5eb09..1ad504b3a80 100644
--- a/tests/ui/consts/const-err-multi.stderr
+++ b/tests/ui/consts/const-err-multi.stderr
@@ -4,19 +4,19 @@ error[E0080]: evaluation of constant value failed
 LL | pub const A: i8 = -i8::MIN;
    |                   ^^^^^^^^ attempt to negate `i8::MIN`, which would overflow
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-err-multi.rs:3:19
    |
 LL | pub const B: i8 = A;
    |                   ^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-err-multi.rs:5:19
    |
 LL | pub const C: u8 = A as u8;
    |                   ^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-err-multi.rs:7:24
    |
 LL | pub const D: i8 = 50 - A;
diff --git a/tests/ui/consts/const-eval/erroneous-const.stderr b/tests/ui/consts/const-eval/erroneous-const.stderr
index 770f95062ab..0e31520fdbb 100644
--- a/tests/ui/consts/const-eval/erroneous-const.stderr
+++ b/tests/ui/consts/const-eval/erroneous-const.stderr
@@ -4,7 +4,7 @@ error[E0080]: evaluation of `PrintName::<i32>::VOID` failed
 LL |     const VOID: () = [()][2];
    |                      ^^^^^^^ index out of bounds: the length is 1 but the index is 2
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/erroneous-const.rs:13:13
    |
 LL |             PrintName::<T>::VOID;
diff --git a/tests/ui/consts/const-eval/erroneous-const2.stderr b/tests/ui/consts/const-eval/erroneous-const2.stderr
index 082c2876575..4ca44694cd7 100644
--- a/tests/ui/consts/const-eval/erroneous-const2.stderr
+++ b/tests/ui/consts/const-eval/erroneous-const2.stderr
@@ -4,7 +4,7 @@ error[E0080]: evaluation of `PrintName::<i32>::VOID` failed
 LL |     const VOID: () = [()][2];
    |                      ^^^^^^^ index out of bounds: the length is 1 but the index is 2
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/erroneous-const2.rs:13:9
    |
 LL |         PrintName::<i32>::VOID;
diff --git a/tests/ui/consts/const-eval/issue-44578.stderr b/tests/ui/consts/const-eval/issue-44578.stderr
index f3952809e4b..c7aaee94271 100644
--- a/tests/ui/consts/const-eval/issue-44578.stderr
+++ b/tests/ui/consts/const-eval/issue-44578.stderr
@@ -4,13 +4,13 @@ error[E0080]: evaluation of `<Bar<u16, u8> as Foo>::AMT` failed
 LL |     const AMT: usize = [A::AMT][(A::AMT > B::AMT) as usize];
    |                        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ index out of bounds: the length is 1 but the index is 1
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/issue-44578.rs:25:20
    |
 LL |     println!("{}", <Bar<u16, u8> as Foo>::AMT);
    |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/issue-44578.rs:25:20
    |
 LL |     println!("{}", <Bar<u16, u8> as Foo>::AMT);
@@ -18,7 +18,7 @@ LL |     println!("{}", <Bar<u16, u8> as Foo>::AMT);
    |
    = note: this note originates in the macro `$crate::format_args_nl` which comes from the expansion of the macro `println` (in Nightly builds, run with -Z macro-backtrace for more info)
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/issue-44578.rs:25:20
    |
 LL |     println!("{}", <Bar<u16, u8> as Foo>::AMT);
diff --git a/tests/ui/consts/const-eval/issue-50814-2.stderr b/tests/ui/consts/const-eval/issue-50814-2.stderr
index 956f7aec9da..450fb002373 100644
--- a/tests/ui/consts/const-eval/issue-50814-2.stderr
+++ b/tests/ui/consts/const-eval/issue-50814-2.stderr
@@ -4,7 +4,7 @@ error[E0080]: evaluation of `<A<()> as Foo<()>>::BAR` failed
 LL |     const BAR: usize = [5, 6, 7][T::BOO];
    |                        ^^^^^^^^^^^^^^^^^ index out of bounds: the length is 3 but the index is 42
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/issue-50814-2.rs:18:6
    |
 LL |     &<A<T> as Foo<T>>::BAR
diff --git a/tests/ui/consts/const-eval/issue-50814.stderr b/tests/ui/consts/const-eval/issue-50814.stderr
index 05b6271f4e4..48a20d0bbd0 100644
--- a/tests/ui/consts/const-eval/issue-50814.stderr
+++ b/tests/ui/consts/const-eval/issue-50814.stderr
@@ -4,7 +4,7 @@ error[E0080]: evaluation of `<Sum<U8, U8> as Unsigned>::MAX` failed
 LL |     const MAX: u8 = A::MAX + B::MAX;
    |                     ^^^^^^^^^^^^^^^ attempt to compute `u8::MAX + u8::MAX`, which would overflow
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/issue-50814.rs:20:6
    |
 LL |     &Sum::<U8, U8>::MAX
diff --git a/tests/ui/consts/const-eval/panic-assoc-never-type.rs b/tests/ui/consts/const-eval/panic-assoc-never-type.rs
index 1abe708d19e..88ce5b0d895 100644
--- a/tests/ui/consts/const-eval/panic-assoc-never-type.rs
+++ b/tests/ui/consts/const-eval/panic-assoc-never-type.rs
@@ -11,5 +11,5 @@ impl PrintName {
 }
 
 fn main() {
-    let _ = PrintName::VOID; //~ erroneous constant used
+    let _ = PrintName::VOID; //~ erroneous constant encountered
 }
diff --git a/tests/ui/consts/const-eval/panic-assoc-never-type.stderr b/tests/ui/consts/const-eval/panic-assoc-never-type.stderr
index 7c36a3a426e..4706497dbc4 100644
--- a/tests/ui/consts/const-eval/panic-assoc-never-type.stderr
+++ b/tests/ui/consts/const-eval/panic-assoc-never-type.stderr
@@ -6,13 +6,13 @@ LL |     const VOID: ! = 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 used
+note: erroneous constant encountered
   --> $DIR/panic-assoc-never-type.rs:14:13
    |
 LL |     let _ = PrintName::VOID;
    |             ^^^^^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/panic-assoc-never-type.rs:14:13
    |
 LL |     let _ = PrintName::VOID;
diff --git a/tests/ui/consts/const-eval/raw-bytes.32bit.stderr b/tests/ui/consts/const-eval/raw-bytes.32bit.stderr
index e087a0ebec7..042e7eeb31e 100644
--- a/tests/ui/consts/const-eval/raw-bytes.32bit.stderr
+++ b/tests/ui/consts/const-eval/raw-bytes.32bit.stderr
@@ -341,7 +341,7 @@ LL | const SLICE_CONTENT_INVALID: &[bool] = &[unsafe { mem::transmute(3u8) }];
                ╾ALLOC_ID╼                                     │ ╾──╼
            }
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/raw-bytes.rs:160:40
    |
 LL | const SLICE_CONTENT_INVALID: &[bool] = &[unsafe { mem::transmute(3u8) }];
@@ -358,7 +358,7 @@ LL | const MYSLICE_PREFIX_BAD: &MySliceBool = &MySlice(unsafe { mem::transmute(3
                ╾ALLOC_ID╼                                     │ ╾──╼
            }
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/raw-bytes.rs:166:42
    |
 LL | const MYSLICE_PREFIX_BAD: &MySliceBool = &MySlice(unsafe { mem::transmute(3u8) }, [false]);
@@ -375,7 +375,7 @@ LL | const MYSLICE_SUFFIX_BAD: &MySliceBool = &MySlice(true, [unsafe { mem::tran
                ╾ALLOC_ID╼                                     │ ╾──╼
            }
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/raw-bytes.rs:170:42
    |
 LL | const MYSLICE_SUFFIX_BAD: &MySliceBool = &MySlice(true, [unsafe { mem::transmute(3u8) }]);
diff --git a/tests/ui/consts/const-eval/raw-bytes.64bit.stderr b/tests/ui/consts/const-eval/raw-bytes.64bit.stderr
index 4c655161f79..8426a95055c 100644
--- a/tests/ui/consts/const-eval/raw-bytes.64bit.stderr
+++ b/tests/ui/consts/const-eval/raw-bytes.64bit.stderr
@@ -341,7 +341,7 @@ LL | const SLICE_CONTENT_INVALID: &[bool] = &[unsafe { mem::transmute(3u8) }];
                ╾ALLOC_ID╼                         │ ╾──────╼
            }
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/raw-bytes.rs:160:40
    |
 LL | const SLICE_CONTENT_INVALID: &[bool] = &[unsafe { mem::transmute(3u8) }];
@@ -358,7 +358,7 @@ LL | const MYSLICE_PREFIX_BAD: &MySliceBool = &MySlice(unsafe { mem::transmute(3
                ╾ALLOC_ID╼                         │ ╾──────╼
            }
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/raw-bytes.rs:166:42
    |
 LL | const MYSLICE_PREFIX_BAD: &MySliceBool = &MySlice(unsafe { mem::transmute(3u8) }, [false]);
@@ -375,7 +375,7 @@ LL | const MYSLICE_SUFFIX_BAD: &MySliceBool = &MySlice(true, [unsafe { mem::tran
                ╾ALLOC_ID╼                         │ ╾──────╼
            }
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/raw-bytes.rs:170:42
    |
 LL | const MYSLICE_SUFFIX_BAD: &MySliceBool = &MySlice(true, [unsafe { mem::transmute(3u8) }]);
diff --git a/tests/ui/consts/const-eval/ub-ref-ptr.stderr b/tests/ui/consts/const-eval/ub-ref-ptr.stderr
index 0ee1e60877f..6d5c36cea7d 100644
--- a/tests/ui/consts/const-eval/ub-ref-ptr.stderr
+++ b/tests/ui/consts/const-eval/ub-ref-ptr.stderr
@@ -60,7 +60,7 @@ LL | const REF_AS_USIZE_SLICE: &[usize] = &[unsafe { mem::transmute(&0) }];
    = help: this code performed an operation that depends on the underlying bytes representing a pointer
    = help: the absolute address of a pointer is not known at compile-time, so such operations are not supported
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/ub-ref-ptr.rs:36:38
    |
 LL | const REF_AS_USIZE_SLICE: &[usize] = &[unsafe { mem::transmute(&0) }];
@@ -75,7 +75,7 @@ LL | const REF_AS_USIZE_BOX_SLICE: Box<[usize]> = unsafe { mem::transmute::<&[us
    = help: this code performed an operation that depends on the underlying bytes representing a pointer
    = help: the absolute address of a pointer is not known at compile-time, so such operations are not supported
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/ub-ref-ptr.rs:39:85
    |
 LL | const REF_AS_USIZE_BOX_SLICE: Box<[usize]> = unsafe { mem::transmute::<&[usize], _>(&[mem::transmute(&0)]) };
diff --git a/tests/ui/consts/const-eval/ub-wide-ptr.stderr b/tests/ui/consts/const-eval/ub-wide-ptr.stderr
index 02bbbf50435..d8add67fac1 100644
--- a/tests/ui/consts/const-eval/ub-wide-ptr.stderr
+++ b/tests/ui/consts/const-eval/ub-wide-ptr.stderr
@@ -139,7 +139,7 @@ LL | const SLICE_CONTENT_INVALID: &[bool] = &[unsafe { mem::transmute(3u8) }];
                HEX_DUMP
            }
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/ub-wide-ptr.rs:85:40
    |
 LL | const SLICE_CONTENT_INVALID: &[bool] = &[unsafe { mem::transmute(3u8) }];
@@ -156,7 +156,7 @@ LL | const MYSLICE_PREFIX_BAD: &MySliceBool = &MySlice(unsafe { mem::transmute(3
                HEX_DUMP
            }
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/ub-wide-ptr.rs:92:42
    |
 LL | const MYSLICE_PREFIX_BAD: &MySliceBool = &MySlice(unsafe { mem::transmute(3u8) }, [false]);
@@ -173,7 +173,7 @@ LL | const MYSLICE_SUFFIX_BAD: &MySliceBool = &MySlice(true, [unsafe { mem::tran
                HEX_DUMP
            }
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/ub-wide-ptr.rs:96:42
    |
 LL | const MYSLICE_SUFFIX_BAD: &MySliceBool = &MySlice(true, [unsafe { mem::transmute(3u8) }]);
diff --git a/tests/ui/consts/const-eval/union-const-eval-field.stderr b/tests/ui/consts/const-eval/union-const-eval-field.stderr
index 9899c56c0ec..ce260300fc8 100644
--- a/tests/ui/consts/const-eval/union-const-eval-field.stderr
+++ b/tests/ui/consts/const-eval/union-const-eval-field.stderr
@@ -4,13 +4,13 @@ error[E0080]: evaluation of constant value failed
 LL |     const FIELD3: Field3 = unsafe { UNION.field3 };
    |                                     ^^^^^^^^^^^^ using uninitialized data, but this operation requires initialized memory
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/union-const-eval-field.rs:31:5
    |
 LL |     FIELD3
    |     ^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/union-const-eval-field.rs:31:5
    |
 LL |     FIELD3
diff --git a/tests/ui/consts/const-float-bits-reject-conv.stderr b/tests/ui/consts/const-float-bits-reject-conv.stderr
index 7ad02252094..1511dab12b0 100644
--- a/tests/ui/consts/const-float-bits-reject-conv.stderr
+++ b/tests/ui/consts/const-float-bits-reject-conv.stderr
@@ -30,25 +30,25 @@ LL |     const MASKED_NAN2: u32 = f32::NAN.to_bits() ^ 0x0055_5555;
    |                              ^^^^^^^^^^^^^^^^^^
    = note: this error originates in the macro `$crate::panic::panic_2021` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-float-bits-reject-conv.rs:35:34
    |
 LL |     const_assert!(f32::from_bits(MASKED_NAN1).is_nan());
    |                                  ^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-float-bits-reject-conv.rs:36:34
    |
 LL |     const_assert!(f32::from_bits(MASKED_NAN1).is_nan());
    |                                  ^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-float-bits-reject-conv.rs:42:34
    |
 LL |     const_assert!(f32::from_bits(MASKED_NAN1).to_bits(), MASKED_NAN1);
    |                                  ^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-float-bits-reject-conv.rs:43:34
    |
 LL |     const_assert!(f32::from_bits(MASKED_NAN2).to_bits(), MASKED_NAN2);
@@ -86,25 +86,25 @@ LL |     const MASKED_NAN2: u64 = f64::NAN.to_bits() ^ 0x0005_5555_5555_5555;
    |                              ^^^^^^^^^^^^^^^^^^
    = note: this error originates in the macro `$crate::panic::panic_2021` which comes from the expansion of the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-float-bits-reject-conv.rs:57:34
    |
 LL |     const_assert!(f64::from_bits(MASKED_NAN1).is_nan());
    |                                  ^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-float-bits-reject-conv.rs:58:34
    |
 LL |     const_assert!(f64::from_bits(MASKED_NAN1).is_nan());
    |                                  ^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-float-bits-reject-conv.rs:61:34
    |
 LL |     const_assert!(f64::from_bits(MASKED_NAN1).to_bits(), MASKED_NAN1);
    |                                  ^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-float-bits-reject-conv.rs:62:34
    |
 LL |     const_assert!(f64::from_bits(MASKED_NAN2).to_bits(), MASKED_NAN2);
diff --git a/tests/ui/consts/const-len-underflow-separate-spans.next.stderr b/tests/ui/consts/const-len-underflow-separate-spans.next.stderr
index d9208d0706a..b7b5b648c12 100644
--- a/tests/ui/consts/const-len-underflow-separate-spans.next.stderr
+++ b/tests/ui/consts/const-len-underflow-separate-spans.next.stderr
@@ -4,7 +4,7 @@ error[E0080]: evaluation of constant value failed
 LL | const LEN: usize = ONE - TWO;
    |                    ^^^^^^^^^ attempt to compute `1_usize - 2_usize`, which would overflow
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-len-underflow-separate-spans.rs:14:17
    |
 LL |     let a: [i8; LEN] = unimplemented!();
diff --git a/tests/ui/consts/const-len-underflow-separate-spans.old.stderr b/tests/ui/consts/const-len-underflow-separate-spans.old.stderr
index d9208d0706a..b7b5b648c12 100644
--- a/tests/ui/consts/const-len-underflow-separate-spans.old.stderr
+++ b/tests/ui/consts/const-len-underflow-separate-spans.old.stderr
@@ -4,7 +4,7 @@ error[E0080]: evaluation of constant value failed
 LL | const LEN: usize = ONE - TWO;
    |                    ^^^^^^^^^ attempt to compute `1_usize - 2_usize`, which would overflow
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/const-len-underflow-separate-spans.rs:14:17
    |
 LL |     let a: [i8; LEN] = unimplemented!();
diff --git a/tests/ui/consts/escaping-bound-var.rs b/tests/ui/consts/escaping-bound-var.rs
new file mode 100644
index 00000000000..7c1fbd24f55
--- /dev/null
+++ b/tests/ui/consts/escaping-bound-var.rs
@@ -0,0 +1,13 @@
+#![feature(generic_const_exprs)]
+//~^ WARN the feature `generic_const_exprs` is incomplete
+
+fn test<'a>(
+    _: &'a (),
+) -> [(); {
+    let x: &'a ();
+    //~^ ERROR cannot capture late-bound lifetime in constant
+    1
+}] {
+}
+
+fn main() {}
diff --git a/tests/ui/consts/escaping-bound-var.stderr b/tests/ui/consts/escaping-bound-var.stderr
new file mode 100644
index 00000000000..d26ae2cee1c
--- /dev/null
+++ b/tests/ui/consts/escaping-bound-var.stderr
@@ -0,0 +1,20 @@
+warning: the feature `generic_const_exprs` is incomplete and may not be safe to use and/or cause compiler crashes
+  --> $DIR/escaping-bound-var.rs:1:12
+   |
+LL | #![feature(generic_const_exprs)]
+   |            ^^^^^^^^^^^^^^^^^^^
+   |
+   = note: see issue #76560 <https://github.com/rust-lang/rust/issues/76560> for more information
+   = note: `#[warn(incomplete_features)]` on by default
+
+error: cannot capture late-bound lifetime in constant
+  --> $DIR/escaping-bound-var.rs:7:13
+   |
+LL | fn test<'a>(
+   |         -- lifetime defined here
+...
+LL |     let x: &'a ();
+   |             ^^
+
+error: aborting due to previous error; 1 warning emitted
+
diff --git a/tests/ui/consts/invalid-union.32bit.stderr b/tests/ui/consts/invalid-union.32bit.stderr
index 0dd18a55786..b6cf060e5ae 100644
--- a/tests/ui/consts/invalid-union.32bit.stderr
+++ b/tests/ui/consts/invalid-union.32bit.stderr
@@ -9,13 +9,13 @@ LL | fn main() {
                ╾─alloc7──╼                                     │ ╾──╼
            }
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/invalid-union.rs:43:25
    |
 LL |     let _: &'static _ = &C;
    |                         ^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/invalid-union.rs:43:25
    |
 LL |     let _: &'static _ = &C;
diff --git a/tests/ui/consts/invalid-union.64bit.stderr b/tests/ui/consts/invalid-union.64bit.stderr
index 07f36ee2832..e3a3ef62c4a 100644
--- a/tests/ui/consts/invalid-union.64bit.stderr
+++ b/tests/ui/consts/invalid-union.64bit.stderr
@@ -9,13 +9,13 @@ LL | fn main() {
                ╾───────alloc7────────╼                         │ ╾──────╼
            }
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/invalid-union.rs:43:25
    |
 LL |     let _: &'static _ = &C;
    |                         ^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/invalid-union.rs:43:25
    |
 LL |     let _: &'static _ = &C;
diff --git a/tests/ui/consts/issue-105536-const-val-roundtrip-ptr-eq.rs b/tests/ui/consts/issue-105536-const-val-roundtrip-ptr-eq.rs
new file mode 100644
index 00000000000..1615399be32
--- /dev/null
+++ b/tests/ui/consts/issue-105536-const-val-roundtrip-ptr-eq.rs
@@ -0,0 +1,31 @@
+// run-pass
+
+// This does not reflect a stable guarantee (we guarantee very little for equality of pointers
+// around `const`), but it would be good to understand what is happening if these assertions ever
+// fail.
+use std::ptr::NonNull;
+use std::slice::from_raw_parts;
+
+const PTR_U8: *const u8 = NonNull::dangling().as_ptr();
+const CONST_U8_REF: &[u8] = unsafe { from_raw_parts(PTR_U8, 0) };
+const CONST_U8_PTR: *const u8 = unsafe { from_raw_parts(PTR_U8, 0).as_ptr() };
+static STATIC_U8_REF: &[u8] = unsafe { from_raw_parts(PTR_U8, 0) };
+
+const PTR_U16: *const u16 = NonNull::dangling().as_ptr();
+const CONST_U16_REF: &[u16] = unsafe { from_raw_parts(PTR_U16, 0) };
+
+const fn const_u8_fn() -> &'static [u8] {
+    unsafe { from_raw_parts(PTR_U8, 0) }
+}
+
+fn main() {
+    let ptr_u8 = unsafe { from_raw_parts(PTR_U8, 0) }.as_ptr();
+    let ptr_u16 = unsafe { from_raw_parts(PTR_U16, 0) }.as_ptr();
+
+    assert_eq!(ptr_u8, PTR_U8);
+    assert_eq!(ptr_u8, CONST_U8_PTR);
+    assert_eq!(ptr_u8, const_u8_fn().as_ptr());
+    assert_eq!(ptr_u8, STATIC_U8_REF.as_ptr());
+    assert_eq!(ptr_u16, CONST_U16_REF.as_ptr());
+    assert_eq!(ptr_u8, CONST_U8_REF.as_ptr());
+}
diff --git a/tests/ui/consts/issue-36163.stderr b/tests/ui/consts/issue-36163.stderr
index 190b41062f8..6fcfe3ed28c 100644
--- a/tests/ui/consts/issue-36163.stderr
+++ b/tests/ui/consts/issue-36163.stderr
@@ -1,15 +1,25 @@
-error[E0391]: cycle detected when const-evaluating + checking `Foo::B::{constant#0}`
+error[E0391]: cycle detected when simplifying constant for the type system `Foo::B::{constant#0}`
   --> $DIR/issue-36163.rs:4:9
    |
 LL |     B = A,
    |         ^
    |
+note: ...which requires const-evaluating + checking `Foo::B::{constant#0}`...
+  --> $DIR/issue-36163.rs:4:9
+   |
+LL |     B = A,
+   |         ^
+note: ...which requires simplifying constant for the type system `A`...
+  --> $DIR/issue-36163.rs:1:1
+   |
+LL | const A: isize = Foo::B as isize;
+   | ^^^^^^^^^^^^^^
 note: ...which requires const-evaluating + checking `A`...
   --> $DIR/issue-36163.rs:1:18
    |
 LL | const A: isize = Foo::B as isize;
    |                  ^^^^^^^^^^^^^^^
-   = note: ...which again requires const-evaluating + checking `Foo::B::{constant#0}`, completing the cycle
+   = note: ...which again requires simplifying constant for the type system `Foo::B::{constant#0}`, completing the cycle
 note: cycle used when simplifying constant for the type system `Foo::B::{constant#0}`
   --> $DIR/issue-36163.rs:4:9
    |
diff --git a/tests/ui/consts/miri_unleashed/assoc_const.stderr b/tests/ui/consts/miri_unleashed/assoc_const.stderr
index d97097d352a..274b1de7e7d 100644
--- a/tests/ui/consts/miri_unleashed/assoc_const.stderr
+++ b/tests/ui/consts/miri_unleashed/assoc_const.stderr
@@ -13,13 +13,13 @@ note: inside `<String as Bar<Vec<u32>, String>>::F`
 LL |     const F: u32 = (U::X, 42).1;
    |                               ^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/assoc_const.rs:29:13
    |
 LL |     let y = <String as Bar<Vec<u32>, String>>::F;
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/assoc_const.rs:29:13
    |
 LL |     let y = <String as Bar<Vec<u32>, String>>::F;
diff --git a/tests/ui/consts/miri_unleashed/assoc_const_2.stderr b/tests/ui/consts/miri_unleashed/assoc_const_2.stderr
index ae7b03fc9dd..c8e4cab4e71 100644
--- a/tests/ui/consts/miri_unleashed/assoc_const_2.stderr
+++ b/tests/ui/consts/miri_unleashed/assoc_const_2.stderr
@@ -4,13 +4,13 @@ error[E0080]: evaluation of `<std::string::String as Bar<std::string::String>>::
 LL |     const F: u32 = 100 / U::X;
    |                    ^^^^^^^^^^ attempt to divide `100_u32` by zero
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/assoc_const_2.rs:27:13
    |
 LL |     let y = <String as Bar<String>>::F;
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/assoc_const_2.rs:27:13
    |
 LL |     let y = <String as Bar<String>>::F;
diff --git a/tests/ui/consts/uninhabited-const-issue-61744.stderr b/tests/ui/consts/uninhabited-const-issue-61744.stderr
index adefbf336c2..f48e6c4ce51 100644
--- a/tests/ui/consts/uninhabited-const-issue-61744.stderr
+++ b/tests/ui/consts/uninhabited-const-issue-61744.stderr
@@ -645,13 +645,13 @@ note: inside `<i32 as Const>::CONSTANT`
 LL |     const CONSTANT: i32 = unsafe { fake_type() };
    |                                    ^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/uninhabited-const-issue-61744.rs:18:10
    |
 LL |     dbg!(i32::CONSTANT);
    |          ^^^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/uninhabited-const-issue-61744.rs:18:10
    |
 LL |     dbg!(i32::CONSTANT);
diff --git a/tests/ui/cross/cross-fn-cache-hole.stderr b/tests/ui/cross/cross-fn-cache-hole.stderr
index 7e15562b081..79d1713934b 100644
--- a/tests/ui/cross/cross-fn-cache-hole.stderr
+++ b/tests/ui/cross/cross-fn-cache-hole.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `i32: Bar<u32>` is not satisfied
 LL |     where i32: Foo<u32, A>
    |           ^^^^^^^^^^^^^^^^ the trait `Bar<u32>` is not implemented for `i32`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/cross-fn-cache-hole.rs:11:1
+   |
+LL | trait Bar<X> { }
+   | ^^^^^^^^^^^^
    = help: see issue #48214
    = help: add `#![feature(trivial_bounds)]` to the crate attributes to enable
 
diff --git a/tests/ui/deriving/deriving-all-codegen.stdout b/tests/ui/deriving/deriving-all-codegen.stdout
index 6bfc859bfe8..3d9f8129d93 100644
--- a/tests/ui/deriving/deriving-all-codegen.stdout
+++ b/tests/ui/deriving/deriving-all-codegen.stdout
@@ -60,7 +60,7 @@ impl ::core::marker::StructuralEq for Empty { }
 impl ::core::cmp::Eq for Empty {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {}
 }
 #[automatically_derived]
@@ -135,7 +135,7 @@ impl ::core::marker::StructuralEq for Point { }
 impl ::core::cmp::Eq for Point {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {
         let _: ::core::cmp::AssertParamIsEq<u32>;
     }
@@ -221,7 +221,7 @@ impl ::core::marker::StructuralEq for PackedPoint { }
 impl ::core::cmp::Eq for PackedPoint {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {
         let _: ::core::cmp::AssertParamIsEq<u32>;
     }
@@ -334,7 +334,7 @@ impl ::core::marker::StructuralEq for Big { }
 impl ::core::cmp::Eq for Big {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {
         let _: ::core::cmp::AssertParamIsEq<u32>;
     }
@@ -500,7 +500,7 @@ impl ::core::marker::StructuralEq for Unsized { }
 impl ::core::cmp::Eq for Unsized {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {
         let _: ::core::cmp::AssertParamIsEq<[u32]>;
     }
@@ -615,7 +615,7 @@ impl<T: ::core::cmp::Eq + Trait, U: ::core::cmp::Eq> ::core::cmp::Eq for
     Generic<T, U> where T::A: ::core::cmp::Eq {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {
         let _: ::core::cmp::AssertParamIsEq<T>;
         let _: ::core::cmp::AssertParamIsEq<T::A>;
@@ -738,7 +738,7 @@ impl<T: ::core::cmp::Eq + ::core::marker::Copy + Trait, U: ::core::cmp::Eq +
     T::A: ::core::cmp::Eq + ::core::marker::Copy {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {
         let _: ::core::cmp::AssertParamIsEq<T>;
         let _: ::core::cmp::AssertParamIsEq<T::A>;
@@ -821,7 +821,7 @@ impl ::core::marker::StructuralEq for Enum0 { }
 impl ::core::cmp::Eq for Enum0 {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {}
 }
 #[automatically_derived]
@@ -892,7 +892,7 @@ impl ::core::marker::StructuralEq for Enum1 { }
 impl ::core::cmp::Eq for Enum1 {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {
         let _: ::core::cmp::AssertParamIsEq<u32>;
     }
@@ -959,7 +959,7 @@ impl ::core::marker::StructuralEq for Fieldless1 { }
 impl ::core::cmp::Eq for Fieldless1 {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {}
 }
 #[automatically_derived]
@@ -1034,7 +1034,7 @@ impl ::core::marker::StructuralEq for Fieldless { }
 impl ::core::cmp::Eq for Fieldless {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {}
 }
 #[automatically_derived]
@@ -1142,7 +1142,7 @@ impl ::core::marker::StructuralEq for Mixed { }
 impl ::core::cmp::Eq for Mixed {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {
         let _: ::core::cmp::AssertParamIsEq<u32>;
         let _: ::core::cmp::AssertParamIsEq<Option<u32>>;
@@ -1270,7 +1270,7 @@ impl ::core::marker::StructuralEq for Fielded { }
 impl ::core::cmp::Eq for Fielded {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {
         let _: ::core::cmp::AssertParamIsEq<u32>;
         let _: ::core::cmp::AssertParamIsEq<bool>;
@@ -1393,7 +1393,7 @@ impl<T: ::core::cmp::Eq, U: ::core::cmp::Eq> ::core::cmp::Eq for
     EnumGeneric<T, U> {
     #[inline]
     #[doc(hidden)]
-    #[no_coverage]
+    #[coverage(off)]
     fn assert_receiver_is_total_eq(&self) -> () {
         let _: ::core::cmp::AssertParamIsEq<T>;
         let _: ::core::cmp::AssertParamIsEq<U>;
diff --git a/tests/ui/diagnostic_namespace/feature-gate-diagnostic_namespace.rs b/tests/ui/diagnostic_namespace/feature-gate-diagnostic_namespace.rs
index a686ed9c84e..b08e291621f 100644
--- a/tests/ui/diagnostic_namespace/feature-gate-diagnostic_namespace.rs
+++ b/tests/ui/diagnostic_namespace/feature-gate-diagnostic_namespace.rs
@@ -1,12 +1,12 @@
 #[diagnostic::non_existing_attribute]
 //~^ERROR `#[diagnostic]` attribute name space is experimental [E0658]
-//~|WARNING unknown diagnostic attribute [unknown_diagnostic_attributes]
+//~|WARNING unknown diagnostic attribute [unknown_or_malformed_diagnostic_attributes]
 pub trait Bar {
 }
 
 #[diagnostic::non_existing_attribute(with_option = "foo")]
 //~^ERROR `#[diagnostic]` attribute name space is experimental [E0658]
-//~|WARNING unknown diagnostic attribute [unknown_diagnostic_attributes]
+//~|WARNING unknown diagnostic attribute [unknown_or_malformed_diagnostic_attributes]
 struct Foo;
 
 fn main() {
diff --git a/tests/ui/diagnostic_namespace/feature-gate-diagnostic_namespace.stderr b/tests/ui/diagnostic_namespace/feature-gate-diagnostic_namespace.stderr
index 45c95cbb3c7..017d00e2c8e 100644
--- a/tests/ui/diagnostic_namespace/feature-gate-diagnostic_namespace.stderr
+++ b/tests/ui/diagnostic_namespace/feature-gate-diagnostic_namespace.stderr
@@ -4,7 +4,7 @@ error[E0658]: `#[diagnostic]` attribute name space is experimental
 LL | #[diagnostic::non_existing_attribute]
    |   ^^^^^^^^^^
    |
-   = note: see issue #94785 <https://github.com/rust-lang/rust/issues/94785> for more information
+   = note: see issue #111996 <https://github.com/rust-lang/rust/issues/111996> for more information
    = help: add `#![feature(diagnostic_namespace)]` to the crate attributes to enable
 
 error[E0658]: `#[diagnostic]` attribute name space is experimental
@@ -13,7 +13,7 @@ error[E0658]: `#[diagnostic]` attribute name space is experimental
 LL | #[diagnostic::non_existing_attribute(with_option = "foo")]
    |   ^^^^^^^^^^
    |
-   = note: see issue #94785 <https://github.com/rust-lang/rust/issues/94785> for more information
+   = note: see issue #111996 <https://github.com/rust-lang/rust/issues/111996> for more information
    = help: add `#![feature(diagnostic_namespace)]` to the crate attributes to enable
 
 warning: unknown diagnostic attribute
@@ -22,7 +22,7 @@ warning: unknown diagnostic attribute
 LL | #[diagnostic::non_existing_attribute]
    |               ^^^^^^^^^^^^^^^^^^^^^^
    |
-   = note: `#[warn(unknown_diagnostic_attributes)]` on by default
+   = note: `#[warn(unknown_or_malformed_diagnostic_attributes)]` on by default
 
 warning: unknown diagnostic attribute
   --> $DIR/feature-gate-diagnostic_namespace.rs:7:15
diff --git a/tests/ui/diagnostic_namespace/non_existing_attributes_accepted.stderr b/tests/ui/diagnostic_namespace/non_existing_attributes_accepted.stderr
index 4f9b7ba2bcf..753077b365e 100644
--- a/tests/ui/diagnostic_namespace/non_existing_attributes_accepted.stderr
+++ b/tests/ui/diagnostic_namespace/non_existing_attributes_accepted.stderr
@@ -4,7 +4,7 @@ warning: unknown diagnostic attribute
 LL | #[diagnostic::non_existing_attribute]
    |               ^^^^^^^^^^^^^^^^^^^^^^
    |
-   = note: `#[warn(unknown_diagnostic_attributes)]` on by default
+   = note: `#[warn(unknown_or_malformed_diagnostic_attributes)]` on by default
 
 warning: unknown diagnostic attribute
   --> $DIR/non_existing_attributes_accepted.rs:8:15
diff --git a/tests/ui/diagnostic_namespace/on_unimplemented/do_not_fail_parsing_on_invalid_options_1.rs b/tests/ui/diagnostic_namespace/on_unimplemented/do_not_fail_parsing_on_invalid_options_1.rs
new file mode 100644
index 00000000000..00fb59d14d7
--- /dev/null
+++ b/tests/ui/diagnostic_namespace/on_unimplemented/do_not_fail_parsing_on_invalid_options_1.rs
@@ -0,0 +1,37 @@
+#![feature(diagnostic_namespace)]
+
+#[diagnostic::on_unimplemented(unsupported = "foo")]
+//~^WARN malformed `on_unimplemented` attribute
+//~|WARN malformed `on_unimplemented` attribute
+trait Foo {}
+
+#[diagnostic::on_unimplemented(message = "Baz")]
+//~^WARN `#[diagnostic::on_unimplemented]` can only be applied to trait definitions
+struct Bar {}
+
+#[diagnostic::on_unimplemented(message = "Boom", unsupported = "Bar")]
+//~^WARN malformed `on_unimplemented` attribute
+//~|WARN malformed `on_unimplemented` attribute
+trait Baz {}
+
+#[diagnostic::on_unimplemented(message = "Boom", on(_Self = "i32", message = "whatever"))]
+//~^WARN malformed `on_unimplemented` attribute
+//~|WARN malformed `on_unimplemented` attribute
+trait Boom {}
+
+#[diagnostic::on_unimplemented = "boom"]
+//~^WARN malformed `on_unimplemented` attribute
+trait Doom {}
+
+fn take_foo(_: impl Foo) {}
+fn take_baz(_: impl Baz) {}
+fn take_boom(_: impl Boom) {}
+
+fn main() {
+    take_foo(1_i32);
+    //~^ERROR the trait bound `i32: Foo` is not satisfied
+    take_baz(1_i32);
+    //~^ERROR Boom
+    take_boom(1_i32);
+    //~^ERROR Boom
+}
diff --git a/tests/ui/diagnostic_namespace/on_unimplemented/do_not_fail_parsing_on_invalid_options_1.stderr b/tests/ui/diagnostic_namespace/on_unimplemented/do_not_fail_parsing_on_invalid_options_1.stderr
new file mode 100644
index 00000000000..bb1b29ef248
--- /dev/null
+++ b/tests/ui/diagnostic_namespace/on_unimplemented/do_not_fail_parsing_on_invalid_options_1.stderr
@@ -0,0 +1,110 @@
+warning: `#[diagnostic::on_unimplemented]` can only be applied to trait definitions
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:8:1
+   |
+LL | #[diagnostic::on_unimplemented(message = "Baz")]
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: `#[warn(unknown_or_malformed_diagnostic_attributes)]` on by default
+
+warning: malformed `on_unimplemented` attribute
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:3:32
+   |
+LL | #[diagnostic::on_unimplemented(unsupported = "foo")]
+   |                                ^^^^^^^^^^^^^^^^^^^
+
+warning: malformed `on_unimplemented` attribute
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:12:50
+   |
+LL | #[diagnostic::on_unimplemented(message = "Boom", unsupported = "Bar")]
+   |                                                  ^^^^^^^^^^^^^^^^^^^
+
+warning: malformed `on_unimplemented` attribute
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:17:50
+   |
+LL | #[diagnostic::on_unimplemented(message = "Boom", on(_Self = "i32", message = "whatever"))]
+   |                                                  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+warning: malformed `on_unimplemented` attribute
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:22:1
+   |
+LL | #[diagnostic::on_unimplemented = "boom"]
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+warning: malformed `on_unimplemented` attribute
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:3:32
+   |
+LL | #[diagnostic::on_unimplemented(unsupported = "foo")]
+   |                                ^^^^^^^^^^^^^^^^^^^
+
+error[E0277]: the trait bound `i32: Foo` is not satisfied
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:31:14
+   |
+LL |     take_foo(1_i32);
+   |     -------- ^^^^^ the trait `Foo` is not implemented for `i32`
+   |     |
+   |     required by a bound introduced by this call
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:6:1
+   |
+LL | trait Foo {}
+   | ^^^^^^^^^
+note: required by a bound in `take_foo`
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:26:21
+   |
+LL | fn take_foo(_: impl Foo) {}
+   |                     ^^^ required by this bound in `take_foo`
+
+warning: malformed `on_unimplemented` attribute
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:12:50
+   |
+LL | #[diagnostic::on_unimplemented(message = "Boom", unsupported = "Bar")]
+   |                                                  ^^^^^^^^^^^^^^^^^^^
+
+error[E0277]: Boom
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:33:14
+   |
+LL |     take_baz(1_i32);
+   |     -------- ^^^^^ the trait `Baz` is not implemented for `i32`
+   |     |
+   |     required by a bound introduced by this call
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:15:1
+   |
+LL | trait Baz {}
+   | ^^^^^^^^^
+note: required by a bound in `take_baz`
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:27:21
+   |
+LL | fn take_baz(_: impl Baz) {}
+   |                     ^^^ required by this bound in `take_baz`
+
+warning: malformed `on_unimplemented` attribute
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:17:50
+   |
+LL | #[diagnostic::on_unimplemented(message = "Boom", on(_Self = "i32", message = "whatever"))]
+   |                                                  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error[E0277]: Boom
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:35:15
+   |
+LL |     take_boom(1_i32);
+   |     --------- ^^^^^ the trait `Boom` is not implemented for `i32`
+   |     |
+   |     required by a bound introduced by this call
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:20:1
+   |
+LL | trait Boom {}
+   | ^^^^^^^^^^
+note: required by a bound in `take_boom`
+  --> $DIR/do_not_fail_parsing_on_invalid_options_1.rs:28:22
+   |
+LL | fn take_boom(_: impl Boom) {}
+   |                      ^^^^ required by this bound in `take_boom`
+
+error: aborting due to 3 previous errors; 8 warnings emitted
+
+For more information about this error, try `rustc --explain E0277`.
diff --git a/tests/ui/diagnostic_namespace/on_unimplemented/feature-gate-diagnostic_on_unimplemented.rs b/tests/ui/diagnostic_namespace/on_unimplemented/feature-gate-diagnostic_on_unimplemented.rs
new file mode 100644
index 00000000000..609a840c118
--- /dev/null
+++ b/tests/ui/diagnostic_namespace/on_unimplemented/feature-gate-diagnostic_on_unimplemented.rs
@@ -0,0 +1,7 @@
+#[diagnostic::on_unimplemented(message = "Foo")]
+//~^ERROR `#[diagnostic]` attribute name space is experimental [E0658]
+pub trait Bar {
+}
+
+fn main() {
+}
diff --git a/tests/ui/diagnostic_namespace/on_unimplemented/feature-gate-diagnostic_on_unimplemented.stderr b/tests/ui/diagnostic_namespace/on_unimplemented/feature-gate-diagnostic_on_unimplemented.stderr
new file mode 100644
index 00000000000..21f02e3a73b
--- /dev/null
+++ b/tests/ui/diagnostic_namespace/on_unimplemented/feature-gate-diagnostic_on_unimplemented.stderr
@@ -0,0 +1,12 @@
+error[E0658]: `#[diagnostic]` attribute name space is experimental
+  --> $DIR/feature-gate-diagnostic_on_unimplemented.rs:1:3
+   |
+LL | #[diagnostic::on_unimplemented(message = "Foo")]
+   |   ^^^^^^^^^^
+   |
+   = note: see issue #111996 <https://github.com/rust-lang/rust/issues/111996> for more information
+   = help: add `#![feature(diagnostic_namespace)]` to the crate attributes to enable
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0658`.
diff --git a/tests/ui/diagnostic_namespace/on_unimplemented/on_unimplemented_simple.rs b/tests/ui/diagnostic_namespace/on_unimplemented/on_unimplemented_simple.rs
new file mode 100644
index 00000000000..797edbc9ec5
--- /dev/null
+++ b/tests/ui/diagnostic_namespace/on_unimplemented/on_unimplemented_simple.rs
@@ -0,0 +1,11 @@
+#![feature(diagnostic_namespace)]
+
+#[diagnostic::on_unimplemented(message = "Foo", label = "Bar", note = "Baz")]
+trait Foo {}
+
+fn takes_foo(_: impl Foo) {}
+
+fn main() {
+    takes_foo(());
+    //~^ERROR Foo
+}
diff --git a/tests/ui/diagnostic_namespace/on_unimplemented/on_unimplemented_simple.stderr b/tests/ui/diagnostic_namespace/on_unimplemented/on_unimplemented_simple.stderr
new file mode 100644
index 00000000000..549c7caa720
--- /dev/null
+++ b/tests/ui/diagnostic_namespace/on_unimplemented/on_unimplemented_simple.stderr
@@ -0,0 +1,24 @@
+error[E0277]: Foo
+  --> $DIR/on_unimplemented_simple.rs:9:15
+   |
+LL |     takes_foo(());
+   |     --------- ^^ Bar
+   |     |
+   |     required by a bound introduced by this call
+   |
+   = help: the trait `Foo` is not implemented for `()`
+   = note: Baz
+help: this trait has no implementations, consider adding one
+  --> $DIR/on_unimplemented_simple.rs:4:1
+   |
+LL | trait Foo {}
+   | ^^^^^^^^^
+note: required by a bound in `takes_foo`
+  --> $DIR/on_unimplemented_simple.rs:6:22
+   |
+LL | fn takes_foo(_: impl Foo) {}
+   |                      ^^^ required by this bound in `takes_foo`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0277`.
diff --git a/tests/ui/drop/dynamic-drop.rs b/tests/ui/drop/dynamic-drop.rs
index 9e51d3adaaa..caef6358ea7 100644
--- a/tests/ui/drop/dynamic-drop.rs
+++ b/tests/ui/drop/dynamic-drop.rs
@@ -2,6 +2,7 @@
 // needs-unwind
 
 #![feature(generators, generator_trait)]
+#![feature(if_let_guard)]
 
 #![allow(unused_assignments)]
 #![allow(unused_variables)]
@@ -332,6 +333,16 @@ fn move_ref_pattern(a: &Allocator) {
     let (ref _a, ref mut _b, _c, mut _d) = tup;
 }
 
+fn if_let_guard(a: &Allocator, c: bool, d: i32) {
+    let foo = if c { Some(a.alloc()) } else { None };
+
+    match d == 0 {
+        false if let Some(a) = foo => { let b = a; }
+        true if let true = { drop(foo.unwrap_or_else(|| a.alloc())); d == 1 } => {}
+        _ => {}
+    }
+}
+
 fn panic_after_return(a: &Allocator) -> Ptr<'_> {
     // Panic in the drop of `p` or `q` can leak
     let exceptions = vec![8, 9];
@@ -497,6 +508,13 @@ fn main() {
 
     run_test(|a| move_ref_pattern(a));
 
+    run_test(|a| if_let_guard(a, true, 0));
+    run_test(|a| if_let_guard(a, true, 1));
+    run_test(|a| if_let_guard(a, true, 2));
+    run_test(|a| if_let_guard(a, false, 0));
+    run_test(|a| if_let_guard(a, false, 1));
+    run_test(|a| if_let_guard(a, false, 2));
+
     run_test(|a| {
         panic_after_return(a);
     });
diff --git a/tests/ui/dst/dst-bad-coerce1.stderr b/tests/ui/dst/dst-bad-coerce1.stderr
index 2c75518c298..455d15e935f 100644
--- a/tests/ui/dst/dst-bad-coerce1.stderr
+++ b/tests/ui/dst/dst-bad-coerce1.stderr
@@ -15,6 +15,11 @@ error[E0277]: the trait bound `Foo: Bar` is not satisfied
 LL |     let f3: &Fat<dyn Bar> = f2;
    |                             ^^ the trait `Bar` is not implemented for `Foo`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/dst-bad-coerce1.rs:10:1
+   |
+LL | trait Bar { fn bar(&self) {} }
+   | ^^^^^^^^^
    = note: required for the cast from `&Fat<Foo>` to `&Fat<dyn Bar>`
 
 error[E0308]: mismatched types
@@ -34,6 +39,11 @@ error[E0277]: the trait bound `Foo: Bar` is not satisfied
 LL |     let f3: &(dyn Bar,) = f2;
    |                           ^^ the trait `Bar` is not implemented for `Foo`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/dst-bad-coerce1.rs:10:1
+   |
+LL | trait Bar { fn bar(&self) {} }
+   | ^^^^^^^^^
    = note: required for the cast from `&(Foo,)` to `&(dyn Bar,)`
 
 error: aborting due to 4 previous errors
diff --git a/tests/ui/dyn-star/error.stderr b/tests/ui/dyn-star/error.stderr
index ae54b9ca707..e039bb6f1c8 100644
--- a/tests/ui/dyn-star/error.stderr
+++ b/tests/ui/dyn-star/error.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `{integer}: Foo` is not satisfied
    |
 LL |     let dyn_i: dyn* Foo = i;
    |                           ^ the trait `Foo` is not implemented for `{integer}`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/error.rs:6:1
+   |
+LL | trait Foo {}
+   | ^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/error-codes/E0040.stderr b/tests/ui/error-codes/E0040.stderr
index 9fcda1a9385..839be79d28d 100644
--- a/tests/ui/error-codes/E0040.stderr
+++ b/tests/ui/error-codes/E0040.stderr
@@ -2,10 +2,12 @@ error[E0040]: explicit use of destructor method
   --> $DIR/E0040.rs:16:7
    |
 LL |     x.drop();
-   |     --^^^^--
-   |     | |
-   |     | explicit destructor calls not allowed
-   |     help: consider using `drop` function: `drop(x)`
+   |       ^^^^ explicit destructor calls not allowed
+   |
+help: consider using `drop` function
+   |
+LL |     drop(x);
+   |     +++++ ~
 
 error: aborting due to previous error
 
diff --git a/tests/ui/error-codes/E0054.stderr b/tests/ui/error-codes/E0054.stderr
index 6b1092760fb..0a4adabbaf6 100644
--- a/tests/ui/error-codes/E0054.stderr
+++ b/tests/ui/error-codes/E0054.stderr
@@ -1,8 +1,13 @@
-error[E0054]: cannot cast as `bool`
+error[E0054]: cannot cast `i32` as `bool`
   --> $DIR/E0054.rs:3:24
    |
 LL |     let x_is_nonzero = x as bool;
-   |                        ^^^^^^^^^ help: compare with zero instead: `x != 0`
+   |                        ^^^^^^^^^
+   |
+help: compare with zero instead
+   |
+LL |     let x_is_nonzero = x != 0;
+   |                          ~~~~
 
 error: aborting due to previous error
 
diff --git a/tests/ui/error-codes/E0277.stderr b/tests/ui/error-codes/E0277.stderr
index 440e43dff81..0b0d2b09720 100644
--- a/tests/ui/error-codes/E0277.stderr
+++ b/tests/ui/error-codes/E0277.stderr
@@ -21,6 +21,11 @@ LL |     some_func(5i32);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/E0277.rs:3:1
+   |
+LL | trait Foo {
+   | ^^^^^^^^^
 note: required by a bound in `some_func`
   --> $DIR/E0277.rs:7:17
    |
diff --git a/tests/ui/error-codes/E0401.stderr b/tests/ui/error-codes/E0401.stderr
index fa4b91cacef..928c8d11d20 100644
--- a/tests/ui/error-codes/E0401.stderr
+++ b/tests/ui/error-codes/E0401.stderr
@@ -1,26 +1,26 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/E0401.rs:4:39
    |
 LL | fn foo<T>(x: T) {
-   |        - type parameter from outer function
+   |        - type parameter from outer item
 LL |     fn bfnr<U, V: Baz<U>, W: Fn()>(y: T) {
-   |             -                         ^ use of generic parameter from outer function
+   |             -                         ^ use of generic parameter from outer item
    |             |
-   |             help: try using a local generic parameter instead: `T,`
+   |             help: try introducing a local generic parameter here: `T,`
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/E0401.rs:9:16
    |
 LL | fn foo<T>(x: T) {
-   |        - type parameter from outer function
+   |        - type parameter from outer item
 ...
 LL |     fn baz<U,
-   |            - help: try using a local generic parameter instead: `T,`
+   |            - help: try introducing a local generic parameter here: `T,`
 ...
 LL |            (y: T) {
-   |                ^ use of generic parameter from outer function
+   |                ^ use of generic parameter from outer item
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/E0401.rs:24:25
    |
 LL | impl<T> Iterator for A<T> {
@@ -29,8 +29,8 @@ LL | impl<T> Iterator for A<T> {
 LL |         fn helper(sel: &Self) -> u8 {
    |                         ^^^^
    |                         |
-   |                         use of generic parameter from outer function
-   |                         use a type here instead
+   |                         use of generic parameter from outer item
+   |                         refer to the type directly here instead
 
 error[E0282]: type annotations needed
   --> $DIR/E0401.rs:11:5
diff --git a/tests/ui/error-festival.stderr b/tests/ui/error-festival.stderr
index e8ee1d96942..9d75671c4e6 100644
--- a/tests/ui/error-festival.stderr
+++ b/tests/ui/error-festival.stderr
@@ -59,11 +59,16 @@ error[E0605]: non-primitive cast: `u8` as `Vec<u8>`
 LL |     x as Vec<u8>;
    |     ^^^^^^^^^^^^ an `as` expression can only be used to convert between primitive types or to coerce to a specific trait object
 
-error[E0054]: cannot cast as `bool`
+error[E0054]: cannot cast `{integer}` as `bool`
   --> $DIR/error-festival.rs:33:24
    |
 LL |     let x_is_nonzero = x as bool;
-   |                        ^^^^^^^^^ help: compare with zero instead: `x != 0`
+   |                        ^^^^^^^^^
+   |
+help: compare with zero instead
+   |
+LL |     let x_is_nonzero = x != 0;
+   |                          ~~~~
 
 error[E0606]: casting `&u8` as `u32` is invalid
   --> $DIR/error-festival.rs:37:18
diff --git a/tests/ui/explicit/explicit-call-to-dtor.stderr b/tests/ui/explicit/explicit-call-to-dtor.stderr
index f3c9bf6cccd..f2e0b73b6c5 100644
--- a/tests/ui/explicit/explicit-call-to-dtor.stderr
+++ b/tests/ui/explicit/explicit-call-to-dtor.stderr
@@ -2,10 +2,12 @@ error[E0040]: explicit use of destructor method
   --> $DIR/explicit-call-to-dtor.rs:15:7
    |
 LL |     x.drop();
-   |     --^^^^--
-   |     | |
-   |     | explicit destructor calls not allowed
-   |     help: consider using `drop` function: `drop(x)`
+   |       ^^^^ explicit destructor calls not allowed
+   |
+help: consider using `drop` function
+   |
+LL |     drop(x);
+   |     +++++ ~
 
 error: aborting due to previous error
 
diff --git a/tests/ui/explicit/explicit-call-to-supertrait-dtor.stderr b/tests/ui/explicit/explicit-call-to-supertrait-dtor.stderr
index c7067117349..5fa42fcf191 100644
--- a/tests/ui/explicit/explicit-call-to-supertrait-dtor.stderr
+++ b/tests/ui/explicit/explicit-call-to-supertrait-dtor.stderr
@@ -2,10 +2,12 @@ error[E0040]: explicit use of destructor method
   --> $DIR/explicit-call-to-supertrait-dtor.rs:22:14
    |
 LL |         self.drop();
-   |         -----^^^^--
-   |         |    |
-   |         |    explicit destructor calls not allowed
-   |         help: consider using `drop` function: `drop(self)`
+   |              ^^^^ explicit destructor calls not allowed
+   |
+help: consider using `drop` function
+   |
+LL |         drop(self);
+   |         +++++    ~
 
 error: aborting due to previous error
 
diff --git a/tests/ui/expr/if/bad-if-let-suggestion.rs b/tests/ui/expr/if/bad-if-let-suggestion.rs
index a8b2a283039..99d584ac7a5 100644
--- a/tests/ui/expr/if/bad-if-let-suggestion.rs
+++ b/tests/ui/expr/if/bad-if-let-suggestion.rs
@@ -4,9 +4,8 @@
 fn a() {
     if let x = 1 && i = 2 {}
     //~^ ERROR cannot find value `i` in this scope
-    //~| ERROR `let` expressions in this position are unstable
     //~| ERROR mismatched types
-    //~| ERROR `let` expressions are not supported here
+    //~| ERROR expected expression, found `let` statement
 }
 
 fn b() {
diff --git a/tests/ui/expr/if/bad-if-let-suggestion.stderr b/tests/ui/expr/if/bad-if-let-suggestion.stderr
index 3a53a20b453..20ac9ca76ba 100644
--- a/tests/ui/expr/if/bad-if-let-suggestion.stderr
+++ b/tests/ui/expr/if/bad-if-let-suggestion.stderr
@@ -1,4 +1,4 @@
-error: `let` expressions are not supported here
+error: expected expression, found `let` statement
   --> $DIR/bad-if-let-suggestion.rs:5:8
    |
 LL |     if let x = 1 && i = 2 {}
@@ -13,7 +13,7 @@ LL |     if let x = 1 && i = 2 {}
    |                     ^ not found in this scope
 
 error[E0425]: cannot find value `i` in this scope
-  --> $DIR/bad-if-let-suggestion.rs:13:9
+  --> $DIR/bad-if-let-suggestion.rs:12:9
    |
 LL | fn a() {
    | ------ similarly named function `a` defined here
@@ -22,7 +22,7 @@ LL |     if (i + j) = i {}
    |         ^ help: a function with a similar name exists: `a`
 
 error[E0425]: cannot find value `j` in this scope
-  --> $DIR/bad-if-let-suggestion.rs:13:13
+  --> $DIR/bad-if-let-suggestion.rs:12:13
    |
 LL | fn a() {
    | ------ similarly named function `a` defined here
@@ -31,7 +31,7 @@ LL |     if (i + j) = i {}
    |             ^ help: a function with a similar name exists: `a`
 
 error[E0425]: cannot find value `i` in this scope
-  --> $DIR/bad-if-let-suggestion.rs:13:18
+  --> $DIR/bad-if-let-suggestion.rs:12:18
    |
 LL | fn a() {
    | ------ similarly named function `a` defined here
@@ -40,7 +40,7 @@ LL |     if (i + j) = i {}
    |                  ^ help: a function with a similar name exists: `a`
 
 error[E0425]: cannot find value `x` in this scope
-  --> $DIR/bad-if-let-suggestion.rs:20:8
+  --> $DIR/bad-if-let-suggestion.rs:19:8
    |
 LL | fn a() {
    | ------ similarly named function `a` defined here
@@ -48,15 +48,6 @@ LL | fn a() {
 LL |     if x[0] = 1 {}
    |        ^ help: a function with a similar name exists: `a`
 
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/bad-if-let-suggestion.rs:5:8
-   |
-LL |     if let x = 1 && i = 2 {}
-   |        ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
 error[E0308]: mismatched types
   --> $DIR/bad-if-let-suggestion.rs:5:8
    |
@@ -68,7 +59,7 @@ help: you might have meant to compare for equality
 LL |     if let x = 1 && i == 2 {}
    |                        +
 
-error: aborting due to 8 previous errors
+error: aborting due to 7 previous errors
 
-Some errors have detailed explanations: E0308, E0425, E0658.
+Some errors have detailed explanations: E0308, E0425.
 For more information about an error, try `rustc --explain E0308`.
diff --git a/tests/ui/feature-gates/feature-gate-coverage-attribute.rs b/tests/ui/feature-gates/feature-gate-coverage-attribute.rs
new file mode 100644
index 00000000000..0a463755f13
--- /dev/null
+++ b/tests/ui/feature-gates/feature-gate-coverage-attribute.rs
@@ -0,0 +1,14 @@
+#![crate_type = "lib"]
+#![feature(no_coverage)] //~ ERROR feature has been removed [E0557]
+
+#[derive(PartialEq, Eq)] // ensure deriving `Eq` does not enable `feature(coverage)`
+struct Foo {
+    a: u8,
+    b: u32,
+}
+
+#[coverage(off)] //~ ERROR the `#[coverage]` attribute is an experimental feature
+fn requires_feature_coverage() -> bool {
+    let bar = Foo { a: 0, b: 0 };
+    bar == Foo { a: 0, b: 0 }
+}
diff --git a/tests/ui/feature-gates/feature-gate-coverage-attribute.stderr b/tests/ui/feature-gates/feature-gate-coverage-attribute.stderr
new file mode 100644
index 00000000000..0131a19a39d
--- /dev/null
+++ b/tests/ui/feature-gates/feature-gate-coverage-attribute.stderr
@@ -0,0 +1,21 @@
+error[E0557]: feature has been removed
+  --> $DIR/feature-gate-coverage-attribute.rs:2:12
+   |
+LL | #![feature(no_coverage)]
+   |            ^^^^^^^^^^^ feature has been removed
+   |
+   = note: renamed to `coverage_attribute`
+
+error[E0658]: the `#[coverage]` attribute is an experimental feature
+  --> $DIR/feature-gate-coverage-attribute.rs:10:1
+   |
+LL | #[coverage(off)]
+   | ^^^^^^^^^^^^^^^^
+   |
+   = note: see issue #84605 <https://github.com/rust-lang/rust/issues/84605> for more information
+   = help: add `#![feature(coverage_attribute)]` to the crate attributes to enable
+
+error: aborting due to 2 previous errors
+
+Some errors have detailed explanations: E0557, E0658.
+For more information about an error, try `rustc --explain E0557`.
diff --git a/tests/ui/feature-gates/feature-gate-no_coverage.rs b/tests/ui/feature-gates/feature-gate-no_coverage.rs
deleted file mode 100644
index fd4c6f76059..00000000000
--- a/tests/ui/feature-gates/feature-gate-no_coverage.rs
+++ /dev/null
@@ -1,13 +0,0 @@
-#![crate_type = "lib"]
-
-#[derive(PartialEq, Eq)] // ensure deriving `Eq` does not enable `feature(no_coverage)`
-struct Foo {
-    a: u8,
-    b: u32,
-}
-
-#[no_coverage] //~ ERROR the `#[no_coverage]` attribute is an experimental feature
-fn requires_feature_no_coverage() -> bool {
-    let bar = Foo { a: 0, b: 0 };
-    bar == Foo { a: 0, b: 0 }
-}
diff --git a/tests/ui/feature-gates/feature-gate-no_coverage.stderr b/tests/ui/feature-gates/feature-gate-no_coverage.stderr
deleted file mode 100644
index f7167e0b771..00000000000
--- a/tests/ui/feature-gates/feature-gate-no_coverage.stderr
+++ /dev/null
@@ -1,12 +0,0 @@
-error[E0658]: the `#[no_coverage]` attribute is an experimental feature
-  --> $DIR/feature-gate-no_coverage.rs:9:1
-   |
-LL | #[no_coverage]
-   | ^^^^^^^^^^^^^^
-   |
-   = note: see issue #84605 <https://github.com/rust-lang/rust/issues/84605> for more information
-   = help: add `#![feature(no_coverage)]` to the crate attributes to enable
-
-error: aborting due to previous error
-
-For more information about this error, try `rustc --explain E0658`.
diff --git a/tests/ui/fmt/raw-idents.rs b/tests/ui/fmt/raw-idents.rs
new file mode 100644
index 00000000000..29a74c55a4a
--- /dev/null
+++ b/tests/ui/fmt/raw-idents.rs
@@ -0,0 +1,17 @@
+// Regression test for https://github.com/rust-lang/rust/issues/115466
+
+// The "identifier" in format strings is parsed as an IDENTIFIER_OR_KEYWORD, not an IDENTIFIER.
+// Test that there is an actionable diagnostic if a RAW_IDENTIFIER is used instead.
+
+fn main() {
+    let r#type = "foobar";
+    println!("It is {r#type}"); //~ ERROR: invalid format string: raw identifiers are not supported
+    println!(r##"It still is {r#type}"##); //~ ERROR: invalid format string: raw identifiers are not supported
+    println!(concat!("{r#", "type}")); //~ ERROR: invalid format string: raw identifiers are not supported
+    println!("{\x72\x23type:?}"); //~ ERROR: invalid format string: raw identifiers are not supported
+
+    // OK
+    println!("{type}");
+    println!("{let}", let = r#type);
+    println!("{let}", r#let = r#type);
+}
diff --git a/tests/ui/fmt/raw-idents.stderr b/tests/ui/fmt/raw-idents.stderr
new file mode 100644
index 00000000000..2ddc114d286
--- /dev/null
+++ b/tests/ui/fmt/raw-idents.stderr
@@ -0,0 +1,44 @@
+error: invalid format string: raw identifiers are not supported
+  --> $DIR/raw-idents.rs:8:22
+   |
+LL |     println!("It is {r#type}");
+   |                      --^^^^
+   |                      |
+   |                      raw identifier used here in format string
+   |                      help: remove the `r#`
+   |
+   = note: identifiers in format strings can be keywords and don't need to be prefixed with `r#`
+
+error: invalid format string: raw identifiers are not supported
+  --> $DIR/raw-idents.rs:9:31
+   |
+LL |     println!(r##"It still is {r#type}"##);
+   |                               --^^^^
+   |                               |
+   |                               raw identifier used here in format string
+   |                               help: remove the `r#`
+   |
+   = note: identifiers in format strings can be keywords and don't need to be prefixed with `r#`
+
+error: invalid format string: raw identifiers are not supported
+  --> $DIR/raw-idents.rs:10:14
+   |
+LL |     println!(concat!("{r#", "type}"));
+   |              ^^^^^^^^^^^^^^^^^^^^^^^ raw identifier used here in format string
+   |
+   = note: identifiers in format strings can be keywords and don't need to be prefixed with `r#`
+   = note: this error originates in the macro `concat` (in Nightly builds, run with -Z macro-backtrace for more info)
+
+error: invalid format string: raw identifiers are not supported
+  --> $DIR/raw-idents.rs:11:16
+   |
+LL |     println!("{\x72\x23type:?}");
+   |                --------^^^^
+   |                |
+   |                raw identifier used here in format string
+   |                help: remove the `r#`
+   |
+   = note: identifiers in format strings can be keywords and don't need to be prefixed with `r#`
+
+error: aborting due to 4 previous errors
+
diff --git a/tests/ui/generic-associated-types/bugs/issue-88460.stderr b/tests/ui/generic-associated-types/bugs/issue-88460.stderr
index a2047f103d4..b9e2c4186c1 100644
--- a/tests/ui/generic-associated-types/bugs/issue-88460.stderr
+++ b/tests/ui/generic-associated-types/bugs/issue-88460.stderr
@@ -7,6 +7,14 @@ LL |     test(Foo);
    |     required by a bound introduced by this call
    |
    = help: the trait `Marker` is implemented for `()`
+note: this is a known limitation of the trait solver that will be lifted in the future
+  --> $DIR/issue-88460.rs:28:10
+   |
+LL |     test(Foo);
+   |     -----^^^-
+   |     |    |
+   |     |    the trait solver is unable to infer the generic types that should be inferred from this argument
+   |     add turbofish arguments to this call to specify the types manually, even if it's redundant
 note: required by a bound in `test`
   --> $DIR/issue-88460.rs:15:27
    |
diff --git a/tests/ui/generic-associated-types/issue-101020.stderr b/tests/ui/generic-associated-types/issue-101020.stderr
index 5c8db617c17..91967fb8509 100644
--- a/tests/ui/generic-associated-types/issue-101020.stderr
+++ b/tests/ui/generic-associated-types/issue-101020.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `for<'a> &'a mut (): Foo<&'a mut ()>` is not satis
 LL |     (&mut EmptyIter).consume(());
    |                      ^^^^^^^ the trait `for<'a> Foo<&'a mut ()>` is not implemented for `&'a mut ()`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-101020.rs:28:1
+   |
+LL | trait Foo<T> {}
+   | ^^^^^^^^^^^^
 note: required for `&'a mut ()` to implement `for<'a> FuncInput<'a, &'a mut ()>`
   --> $DIR/issue-101020.rs:27:20
    |
diff --git a/tests/ui/generics/issue-94432-garbage-ice.rs b/tests/ui/generics/issue-94432-garbage-ice.rs
index d0709e2d2a4..4ddb3a7e9f8 100644
--- a/tests/ui/generics/issue-94432-garbage-ice.rs
+++ b/tests/ui/generics/issue-94432-garbage-ice.rs
@@ -4,7 +4,7 @@
 
 fn�a<e>(){fn�p(){e}} //~ ERROR unknown start of token: \u{fffd}
 //~^ ERROR unknown start of token: \u{fffd}
-//~^^ ERROR can't use generic parameters from outer function [E0401]
+//~^^ ERROR can't use generic parameters from outer item [E0401]
 //~^^^ WARN type parameter `e` should have an upper camel case name
 
 fn main(){}
diff --git a/tests/ui/generics/issue-98432.rs b/tests/ui/generics/issue-98432.rs
index 780c50d6ffa..c31dea76c09 100644
--- a/tests/ui/generics/issue-98432.rs
+++ b/tests/ui/generics/issue-98432.rs
@@ -2,7 +2,7 @@ struct Struct<T>(T);
 
 impl<T> Struct<T> {
     const CONST: fn() = || {
-        struct _Obligation where T:; //~ ERROR can't use generic parameters from outer function
+        struct _Obligation where T:; //~ ERROR can't use generic parameters from outer item
     };
 }
 
diff --git a/tests/ui/generics/issue-98432.stderr b/tests/ui/generics/issue-98432.stderr
index c7b5c33618d..0736d94106e 100644
--- a/tests/ui/generics/issue-98432.stderr
+++ b/tests/ui/generics/issue-98432.stderr
@@ -1,13 +1,13 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-98432.rs:5:34
    |
 LL | impl<T> Struct<T> {
-   |      - type parameter from outer function
+   |      - type parameter from outer item
 LL |     const CONST: fn() = || {
 LL |         struct _Obligation where T:;
-   |                           -      ^ use of generic parameter from outer function
+   |                           -      ^ use of generic parameter from outer item
    |                           |
-   |                           help: try using a local generic parameter instead: `<T>`
+   |                           help: try introducing a local generic parameter here: `<T>`
 
 error: aborting due to previous error
 
diff --git a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-62529-3.stderr b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-62529-3.stderr
index b30dd36d2ad..2cc2bb2bbc3 100644
--- a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-62529-3.stderr
+++ b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-62529-3.stderr
@@ -8,6 +8,14 @@ LL |         call(f, ());
    |
    = note: expected a closure with arguments `((),)`
               found a closure with arguments `(<_ as ATC<'a>>::Type,)`
+note: this is a known limitation of the trait solver that will be lifted in the future
+  --> $DIR/issue-62529-3.rs:25:14
+   |
+LL |         call(f, ());
+   |         -----^-----
+   |         |    |
+   |         |    the trait solver is unable to infer the generic types that should be inferred from this argument
+   |         add turbofish arguments to this call to specify the types manually, even if it's redundant
 note: required by a bound in `call`
   --> $DIR/issue-62529-3.rs:9:36
    |
diff --git a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-89118.stderr b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-89118.stderr
index edef6ccd34e..7fe803550bd 100644
--- a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-89118.stderr
+++ b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-89118.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `for<'a> &'a (): BufferMut` is not satisfied
 LL |     C: StackContext,
    |        ^^^^^^^^^^^^ the trait `for<'a> BufferMut` is not implemented for `&'a ()`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-89118.rs:1:1
+   |
+LL | trait BufferMut {}
+   | ^^^^^^^^^^^^^^^
 note: required for `Ctx<()>` to implement `for<'a> BufferUdpStateContext<&'a ()>`
   --> $DIR/issue-89118.rs:5:23
    |
@@ -26,6 +31,11 @@ error[E0277]: the trait bound `for<'a> &'a (): BufferMut` is not satisfied
 LL | impl<C> EthernetWorker<C> {}
    |         ^^^^^^^^^^^^^^^^^ the trait `for<'a> BufferMut` is not implemented for `&'a ()`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-89118.rs:1:1
+   |
+LL | trait BufferMut {}
+   | ^^^^^^^^^^^^^^^
 note: required for `Ctx<()>` to implement `for<'a> BufferUdpStateContext<&'a ()>`
   --> $DIR/issue-89118.rs:5:23
    |
@@ -48,6 +58,11 @@ error[E0277]: the trait bound `for<'a> &'a (): BufferMut` is not satisfied
 LL |     type Handler = Ctx<C::Dispatcher>;
    |                    ^^^^^^^^^^^^^^^^^^ the trait `for<'a> BufferMut` is not implemented for `&'a ()`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-89118.rs:1:1
+   |
+LL | trait BufferMut {}
+   | ^^^^^^^^^^^^^^^
 note: required for `Ctx<()>` to implement `for<'a> BufferUdpStateContext<&'a ()>`
   --> $DIR/issue-89118.rs:5:23
    |
diff --git a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-90950.stderr b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-90950.stderr
index 5be33bccdc3..55eaef78634 100644
--- a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-90950.stderr
+++ b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-90950.stderr
@@ -7,6 +7,14 @@ LL |     upcast(y)
    |     required by a bound introduced by this call
    |
    = help: the trait `IsCovariant<'a>` is implemented for `std::borrow::Cow<'a, T>`
+note: this is a known limitation of the trait solver that will be lifted in the future
+  --> $DIR/issue-90950.rs:50:12
+   |
+LL |     upcast(y)
+   |     -------^-
+   |     |      |
+   |     |      the trait solver is unable to infer the generic types that should be inferred from this argument
+   |     add turbofish arguments to this call to specify the types manually, even if it's redundant
 note: required by a bound in `upcast`
   --> $DIR/issue-90950.rs:27:42
    |
diff --git a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/norm-before-method-resolution.stderr b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/norm-before-method-resolution.stderr
index 73388a72574..081dbb67df8 100644
--- a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/norm-before-method-resolution.stderr
+++ b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/norm-before-method-resolution.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `for<'a> <_ as Trait<'a>>::Out: Copy` is not satis
 LL |     let _: () = weird_bound();
    |                 ^^^^^^^^^^^ the trait `for<'a> Copy` is not implemented for `<_ as Trait<'a>>::Out`
    |
+note: this is a known limitation of the trait solver that will be lifted in the future
+  --> $DIR/norm-before-method-resolution.rs:22:17
+   |
+LL |     let _: () = weird_bound();
+   |                 ^^^^^^^^^^^ try adding turbofish arguments to this expression to specify the types manually, even if it's redundant
 note: required by a bound in `weird_bound`
   --> $DIR/norm-before-method-resolution.rs:18:40
    |
diff --git a/tests/ui/impl-trait/async_scope_creep.rs b/tests/ui/impl-trait/async_scope_creep.rs
index 7a9d64d339f..9a8831a299e 100644
--- a/tests/ui/impl-trait/async_scope_creep.rs
+++ b/tests/ui/impl-trait/async_scope_creep.rs
@@ -1,6 +1,7 @@
 #![feature(type_alias_impl_trait)]
 // edition:2021
-// check-pass
+//[rpit] check-pass
+// revisions: tait rpit
 
 struct Pending {}
 
@@ -12,15 +13,23 @@ impl AsyncRead for i32 {}
 
 type PendingReader<'a> = impl AsyncRead + 'a;
 
-type OpeningReadFuture<'a> =
-    impl std::future::Future<Output = Result<PendingReader<'a>, CantOpen>>;
+#[cfg(tait)]
+type OpeningReadFuture<'a> = impl std::future::Future<Output = Result<PendingReader<'a>, CantOpen>>;
 
 impl Pending {
     async fn read(&mut self) -> Result<impl AsyncRead + '_, CantOpen> {
         Ok(42)
     }
 
+    #[cfg(tait)]
     fn read_fut(&mut self) -> OpeningReadFuture<'_> {
+        self.read() //[tait]~ ERROR: cannot satisfy `impl AsyncRead + 'a == PendingReader<'a>`
+    }
+
+    #[cfg(rpit)]
+    fn read_fut(
+        &mut self,
+    ) -> impl std::future::Future<Output = Result<PendingReader<'_>, CantOpen>> {
         self.read()
     }
 }
diff --git a/tests/ui/impl-trait/async_scope_creep.tait.stderr b/tests/ui/impl-trait/async_scope_creep.tait.stderr
new file mode 100644
index 00000000000..165096a0574
--- /dev/null
+++ b/tests/ui/impl-trait/async_scope_creep.tait.stderr
@@ -0,0 +1,9 @@
+error[E0284]: type annotations needed: cannot satisfy `impl AsyncRead + 'a == PendingReader<'a>`
+  --> $DIR/async_scope_creep.rs:26:9
+   |
+LL |         self.read()
+   |         ^^^^^^^^^^^ cannot satisfy `impl AsyncRead + 'a == PendingReader<'a>`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0284`.
diff --git a/tests/ui/impl-trait/lifetime-ambiguity-regression.rs b/tests/ui/impl-trait/lifetime-ambiguity-regression.rs
new file mode 100644
index 00000000000..ce6ae3786e1
--- /dev/null
+++ b/tests/ui/impl-trait/lifetime-ambiguity-regression.rs
@@ -0,0 +1,13 @@
+//! This test shows a situation where through subtle compiler changes we can
+//! suddenly infer a different lifetime in the hidden type, and thus not meet
+//! the opaque type bounds anymore. In this case `'a` and `'b` are equal, so
+//! picking either is fine, but then we'll fail an identity check of the hidden
+//! type and the expected hidden type.
+
+// check-pass
+
+fn test<'a: 'b, 'b: 'a>() -> impl IntoIterator<Item = (&'a u8, impl Into<(&'b u8, &'a u8)>)> {
+    None::<(_, (_, _))>
+}
+
+fn main() {}
diff --git a/tests/ui/imports/import-after-macro-expand-10.rs b/tests/ui/imports/import-after-macro-expand-10.rs
new file mode 100644
index 00000000000..b3520c42dfc
--- /dev/null
+++ b/tests/ui/imports/import-after-macro-expand-10.rs
@@ -0,0 +1,17 @@
+// check-pass
+
+mod b {
+    pub mod http {
+        pub struct HeaderMap;
+    }
+
+    pub use self::http::*;
+    #[derive(Debug)]
+    pub struct HeaderMap;
+}
+
+use crate::b::*;
+
+fn main() {
+    let h: crate::b::HeaderMap = HeaderMap;
+}
diff --git a/tests/ui/imports/import-after-macro-expand-11.rs b/tests/ui/imports/import-after-macro-expand-11.rs
new file mode 100644
index 00000000000..2b81dfc236a
--- /dev/null
+++ b/tests/ui/imports/import-after-macro-expand-11.rs
@@ -0,0 +1,21 @@
+// check-pass
+
+#[derive(Debug)]
+struct H;
+
+mod p {
+    use super::*;
+
+    #[derive(Clone)]
+    struct H;
+
+    mod t {
+        use super::*;
+
+        fn f() {
+           let h: crate::p::H = H;
+        }
+    }
+}
+
+fn main() {}
diff --git a/tests/ui/imports/import-after-macro-expand-12.rs b/tests/ui/imports/import-after-macro-expand-12.rs
new file mode 100644
index 00000000000..f92e8c12fca
--- /dev/null
+++ b/tests/ui/imports/import-after-macro-expand-12.rs
@@ -0,0 +1,34 @@
+// check-pass
+// https://github.com/rust-lang/rust/issues/115377
+
+use module::*;
+
+mod module {
+    pub enum B {}
+    impl B {
+        pub const ASSOC: u8 = 0;
+    }
+}
+
+#[derive()]
+pub enum B {}
+impl B {
+    pub const ASSOC: u16 = 0;
+}
+
+macro_rules! m {
+    ($right:expr) => {
+        $right
+    };
+}
+
+fn main() {
+    let a: u16 = {
+        use self::*;
+        B::ASSOC
+    };
+    let b: u16 = m!({
+        use self::*;
+        B::ASSOC
+    });
+}
diff --git a/tests/ui/imports/import-after-macro-expand-13.rs b/tests/ui/imports/import-after-macro-expand-13.rs
new file mode 100644
index 00000000000..fd640002c3e
--- /dev/null
+++ b/tests/ui/imports/import-after-macro-expand-13.rs
@@ -0,0 +1,22 @@
+// check-pass
+// similar as `import-after-macro-expand-6.rs`
+
+use crate::a::HeaderMap;
+
+mod b {
+    pub mod http {
+        pub struct HeaderMap;
+    }
+
+    pub use self::http::*;
+    #[derive(Debug)]
+    pub struct HeaderMap;
+}
+
+mod a {
+    pub use crate::b::*;
+}
+
+fn main() {
+    let h: crate::b::HeaderMap = HeaderMap;
+}
diff --git a/tests/ui/imports/import-after-macro-expand-14.rs b/tests/ui/imports/import-after-macro-expand-14.rs
new file mode 100644
index 00000000000..4d461a0e20c
--- /dev/null
+++ b/tests/ui/imports/import-after-macro-expand-14.rs
@@ -0,0 +1,22 @@
+// check-pass
+
+use crate::a::HeaderMap;
+
+mod b {
+    pub mod http {
+        #[derive(Clone)]
+        pub struct HeaderMap;
+    }
+
+    pub use self::http::*;
+    #[derive(Debug)]
+    pub struct HeaderMap;
+}
+
+mod a {
+    pub use crate::b::*;
+}
+
+fn main() {
+    let h: crate::b::HeaderMap = HeaderMap;
+}
diff --git a/tests/ui/imports/import-after-macro-expand-2.rs b/tests/ui/imports/import-after-macro-expand-2.rs
index b3996d48840..ff773fc8272 100644
--- a/tests/ui/imports/import-after-macro-expand-2.rs
+++ b/tests/ui/imports/import-after-macro-expand-2.rs
@@ -12,9 +12,7 @@ mod tests {
     use super::*;
 
     fn test_thing() {
-        let thing: crate::thing::Thing = Thing::Bar;
-        // FIXME: `thing` should refer to `crate::Thing`,
-        // FIXME: but doesn't currently refer to it due to backward compatibility
+        let thing: crate::Thing = Thing::Foo;
     }
 }
 
diff --git a/tests/ui/imports/import-after-macro-expand-4.rs b/tests/ui/imports/import-after-macro-expand-4.rs
index 02cc3f01af9..fc0a232a93c 100644
--- a/tests/ui/imports/import-after-macro-expand-4.rs
+++ b/tests/ui/imports/import-after-macro-expand-4.rs
@@ -1,3 +1,4 @@
+// check-pass
 // https://github.com/rust-lang/rust/pull/113242#issuecomment-1616034904
 // similar with `import-after-macro-expand-2.rs`
 
@@ -10,16 +11,6 @@ pub use a::*;
 mod c {
     use crate::*;
     pub struct S(Vec<P>);
-    //~^ ERROR the size for values of type
-    //~| WARNING trait objects without an explicit
-    //~| WARNING this is accepted in the current edition
-    //~| WARNING trait objects without an explicit
-    //~| WARNING this is accepted in the current edition
-    //~| WARNING trait objects without an explicit
-    //~| WARNING this is accepted in the current edition
-
-    // FIXME: should works, but doesn't currently refer
-    // to it due to backward compatibility
 }
 
 #[derive(Clone)]
diff --git a/tests/ui/imports/import-after-macro-expand-4.stderr b/tests/ui/imports/import-after-macro-expand-4.stderr
deleted file mode 100644
index 01f70cfc5bf..00000000000
--- a/tests/ui/imports/import-after-macro-expand-4.stderr
+++ /dev/null
@@ -1,53 +0,0 @@
-warning: trait objects without an explicit `dyn` are deprecated
-  --> $DIR/import-after-macro-expand-4.rs:12:22
-   |
-LL |     pub struct S(Vec<P>);
-   |                      ^
-   |
-   = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021!
-   = note: for more information, see <https://doc.rust-lang.org/nightly/edition-guide/rust-2021/warnings-promoted-to-error.html>
-   = note: `#[warn(bare_trait_objects)]` on by default
-help: use `dyn`
-   |
-LL |     pub struct S(Vec<dyn P>);
-   |                      +++
-
-warning: trait objects without an explicit `dyn` are deprecated
-  --> $DIR/import-after-macro-expand-4.rs:12:22
-   |
-LL |     pub struct S(Vec<P>);
-   |                      ^
-   |
-   = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021!
-   = note: for more information, see <https://doc.rust-lang.org/nightly/edition-guide/rust-2021/warnings-promoted-to-error.html>
-help: use `dyn`
-   |
-LL |     pub struct S(Vec<dyn P>);
-   |                      +++
-
-warning: trait objects without an explicit `dyn` are deprecated
-  --> $DIR/import-after-macro-expand-4.rs:12:22
-   |
-LL |     pub struct S(Vec<P>);
-   |                      ^
-   |
-   = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021!
-   = note: for more information, see <https://doc.rust-lang.org/nightly/edition-guide/rust-2021/warnings-promoted-to-error.html>
-help: use `dyn`
-   |
-LL |     pub struct S(Vec<dyn P>);
-   |                      +++
-
-error[E0277]: the size for values of type `(dyn a::P + 'static)` cannot be known at compilation time
-  --> $DIR/import-after-macro-expand-4.rs:12:18
-   |
-LL |     pub struct S(Vec<P>);
-   |                  ^^^^^^ doesn't have a size known at compile-time
-   |
-   = help: the trait `Sized` is not implemented for `(dyn a::P + 'static)`
-note: required by a bound in `Vec`
-  --> $SRC_DIR/alloc/src/vec/mod.rs:LL:COL
-
-error: aborting due to previous error; 3 warnings emitted
-
-For more information about this error, try `rustc --explain E0277`.
diff --git a/tests/ui/imports/import-after-macro-expand-6.rs b/tests/ui/imports/import-after-macro-expand-6.rs
index ab5bb37a175..bff8efebca6 100644
--- a/tests/ui/imports/import-after-macro-expand-6.rs
+++ b/tests/ui/imports/import-after-macro-expand-6.rs
@@ -18,7 +18,5 @@ mod b {
 use crate::a::HeaderMap;
 
 fn main() {
-    let h: crate::b::http::HeaderMap = HeaderMap;
-    // FIXME: should refer to `crate::b::HeaderMap`,
-    // FIXME: but doesn't currently refer to it due to backward compatibility
+    let h: crate::b::HeaderMap = HeaderMap;
 }
diff --git a/tests/ui/imports/import-after-macro-expand-9.rs b/tests/ui/imports/import-after-macro-expand-9.rs
new file mode 100644
index 00000000000..deee42c3b84
--- /dev/null
+++ b/tests/ui/imports/import-after-macro-expand-9.rs
@@ -0,0 +1,17 @@
+// check-pass
+
+use crate::b::*;
+
+mod b {
+    pub mod http {
+        pub struct HeaderMap;
+    }
+
+    pub use self::http::*;
+    #[derive(Debug)]
+    pub struct HeaderMap;
+}
+
+fn main() {
+    let h: crate::b::HeaderMap = HeaderMap;
+}
diff --git a/tests/ui/inner-static-type-parameter.rs b/tests/ui/inner-static-type-parameter.rs
index c08ccd29d80..a1994e7529c 100644
--- a/tests/ui/inner-static-type-parameter.rs
+++ b/tests/ui/inner-static-type-parameter.rs
@@ -4,7 +4,7 @@ enum Bar<T> { What } //~ ERROR parameter `T` is never used
 
 fn foo<T>() {
     static a: Bar<T> = Bar::What;
-//~^ ERROR can't use generic parameters from outer function
+//~^ ERROR can't use generic parameters from outer item
 }
 
 fn main() {
diff --git a/tests/ui/inner-static-type-parameter.stderr b/tests/ui/inner-static-type-parameter.stderr
index e4e449e4159..ff6558e494b 100644
--- a/tests/ui/inner-static-type-parameter.stderr
+++ b/tests/ui/inner-static-type-parameter.stderr
@@ -1,10 +1,10 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/inner-static-type-parameter.rs:6:19
    |
 LL | fn foo<T>() {
-   |        - type parameter from outer function
+   |        - type parameter from outer item
 LL |     static a: Bar<T> = Bar::What;
-   |                   ^ use of generic parameter from outer function
+   |                   ^ use of generic parameter from outer item
 
 error[E0392]: parameter `T` is never used
   --> $DIR/inner-static-type-parameter.rs:3:10
diff --git a/tests/ui/issues/issue-17252.stderr b/tests/ui/issues/issue-17252.stderr
index daaf82e80ad..32e20d77465 100644
--- a/tests/ui/issues/issue-17252.stderr
+++ b/tests/ui/issues/issue-17252.stderr
@@ -1,10 +1,15 @@
-error[E0391]: cycle detected when const-evaluating + checking `FOO`
+error[E0391]: cycle detected when simplifying constant for the type system `FOO`
+  --> $DIR/issue-17252.rs:1:1
+   |
+LL | const FOO: usize = FOO;
+   | ^^^^^^^^^^^^^^^^
+   |
+note: ...which requires const-evaluating + checking `FOO`...
   --> $DIR/issue-17252.rs:1:20
    |
 LL | const FOO: usize = FOO;
    |                    ^^^
-   |
-   = note: ...which immediately requires const-evaluating + checking `FOO` again
+   = note: ...which again requires simplifying constant for the type system `FOO`, completing the cycle
 note: cycle used when const-evaluating + checking `main::{constant#0}`
   --> $DIR/issue-17252.rs:4:18
    |
diff --git a/tests/ui/issues/issue-18611.stderr b/tests/ui/issues/issue-18611.stderr
index bd18d46223e..784b9b984e9 100644
--- a/tests/ui/issues/issue-18611.stderr
+++ b/tests/ui/issues/issue-18611.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `isize: HasState` is not satisfied
    |
 LL | fn add_state(op: <isize as HasState>::State) {
    |                  ^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `HasState` is not implemented for `isize`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-18611.rs:5:1
+   |
+LL | trait HasState {
+   | ^^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/issues/issue-21763.stderr b/tests/ui/issues/issue-21763.stderr
index df50118ac47..a887635d354 100644
--- a/tests/ui/issues/issue-21763.stderr
+++ b/tests/ui/issues/issue-21763.stderr
@@ -9,9 +9,6 @@ LL |     foo::<HashMap<Rc<()>, Rc<()>>>();
    = note: required for `hashbrown::raw::RawTable<(Rc<()>, Rc<()>)>` to implement `Send`
 note: required because it appears within the type `HashMap<Rc<()>, Rc<()>, RandomState>`
   --> $HASHBROWN_SRC_LOCATION
-   |
-LL | pub struct HashMap<K, V, S = DefaultHashBuilder, A: Allocator + Clone = Global> {
-   |            ^^^^^^^
 note: required because it appears within the type `HashMap<Rc<()>, Rc<()>>`
   --> $SRC_DIR/std/src/collections/hash/map.rs:LL:COL
 note: required by a bound in `foo`
diff --git a/tests/ui/issues/issue-23302-1.stderr b/tests/ui/issues/issue-23302-1.stderr
index d807e24403e..d753bdeb9f7 100644
--- a/tests/ui/issues/issue-23302-1.stderr
+++ b/tests/ui/issues/issue-23302-1.stderr
@@ -1,10 +1,15 @@
-error[E0391]: cycle detected when const-evaluating + checking `X::A::{constant#0}`
+error[E0391]: cycle detected when simplifying constant for the type system `X::A::{constant#0}`
   --> $DIR/issue-23302-1.rs:4:9
    |
 LL |     A = X::A as isize,
    |         ^^^^^^^^^^^^^
    |
-   = note: ...which immediately requires const-evaluating + checking `X::A::{constant#0}` again
+note: ...which requires const-evaluating + checking `X::A::{constant#0}`...
+  --> $DIR/issue-23302-1.rs:4:9
+   |
+LL |     A = X::A as isize,
+   |         ^^^^^^^^^^^^^
+   = note: ...which again requires simplifying constant for the type system `X::A::{constant#0}`, completing the cycle
 note: cycle used when simplifying constant for the type system `X::A::{constant#0}`
   --> $DIR/issue-23302-1.rs:4:9
    |
diff --git a/tests/ui/issues/issue-23302-2.stderr b/tests/ui/issues/issue-23302-2.stderr
index 91b39dba1ba..b756ee1d5e2 100644
--- a/tests/ui/issues/issue-23302-2.stderr
+++ b/tests/ui/issues/issue-23302-2.stderr
@@ -1,10 +1,15 @@
-error[E0391]: cycle detected when const-evaluating + checking `Y::A::{constant#0}`
+error[E0391]: cycle detected when simplifying constant for the type system `Y::A::{constant#0}`
   --> $DIR/issue-23302-2.rs:4:9
    |
 LL |     A = Y::B as isize,
    |         ^^^^^^^^^^^^^
    |
-   = note: ...which immediately requires const-evaluating + checking `Y::A::{constant#0}` again
+note: ...which requires const-evaluating + checking `Y::A::{constant#0}`...
+  --> $DIR/issue-23302-2.rs:4:9
+   |
+LL |     A = Y::B as isize,
+   |         ^^^^^^^^^^^^^
+   = note: ...which again requires simplifying constant for the type system `Y::A::{constant#0}`, completing the cycle
 note: cycle used when simplifying constant for the type system `Y::A::{constant#0}`
   --> $DIR/issue-23302-2.rs:4:9
    |
diff --git a/tests/ui/issues/issue-23302-3.stderr b/tests/ui/issues/issue-23302-3.stderr
index 6b708d81f73..6cdc94551fe 100644
--- a/tests/ui/issues/issue-23302-3.stderr
+++ b/tests/ui/issues/issue-23302-3.stderr
@@ -1,15 +1,25 @@
-error[E0391]: cycle detected when const-evaluating + checking `A`
+error[E0391]: cycle detected when simplifying constant for the type system `A`
+  --> $DIR/issue-23302-3.rs:1:1
+   |
+LL | const A: i32 = B;
+   | ^^^^^^^^^^^^
+   |
+note: ...which requires const-evaluating + checking `A`...
   --> $DIR/issue-23302-3.rs:1:16
    |
 LL | const A: i32 = B;
    |                ^
+note: ...which requires simplifying constant for the type system `B`...
+  --> $DIR/issue-23302-3.rs:3:1
    |
+LL | const B: i32 = A;
+   | ^^^^^^^^^^^^
 note: ...which requires const-evaluating + checking `B`...
   --> $DIR/issue-23302-3.rs:3:16
    |
 LL | const B: i32 = A;
    |                ^
-   = note: ...which again requires const-evaluating + checking `A`, completing the cycle
+   = note: ...which again requires simplifying constant for the type system `A`, completing the cycle
 note: cycle used when simplifying constant for the type system `A`
   --> $DIR/issue-23302-3.rs:1:1
    |
diff --git a/tests/ui/issues/issue-25076.stderr b/tests/ui/issues/issue-25076.stderr
index 159cc484c5d..065bf7def42 100644
--- a/tests/ui/issues/issue-25076.stderr
+++ b/tests/ui/issues/issue-25076.stderr
@@ -6,6 +6,11 @@ LL |     do_fold(bot(), ());
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-25076.rs:3:1
+   |
+LL | trait InOut<T> { type Out; }
+   | ^^^^^^^^^^^^^^
 note: required by a bound in `do_fold`
   --> $DIR/issue-25076.rs:5:18
    |
diff --git a/tests/ui/issues/issue-3214.rs b/tests/ui/issues/issue-3214.rs
index e3c07bb3f72..b2c27f5be95 100644
--- a/tests/ui/issues/issue-3214.rs
+++ b/tests/ui/issues/issue-3214.rs
@@ -1,6 +1,6 @@
 fn foo<T>() {
     struct Foo {
-        x: T, //~ ERROR can't use generic parameters from outer function
+        x: T, //~ ERROR can't use generic parameters from outer item
     }
 
     impl<T> Drop for Foo<T> {
diff --git a/tests/ui/issues/issue-3214.stderr b/tests/ui/issues/issue-3214.stderr
index 7a2d772f0a1..5b57c1baf90 100644
--- a/tests/ui/issues/issue-3214.stderr
+++ b/tests/ui/issues/issue-3214.stderr
@@ -1,12 +1,12 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-3214.rs:3:12
    |
 LL | fn foo<T>() {
-   |        - type parameter from outer function
+   |        - type parameter from outer item
 LL |     struct Foo {
-   |               - help: try using a local generic parameter instead: `<T>`
+   |               - help: try introducing a local generic parameter here: `<T>`
 LL |         x: T,
-   |            ^ use of generic parameter from outer function
+   |            ^ use of generic parameter from outer item
 
 error[E0107]: struct takes 0 generic arguments but 1 generic argument was supplied
   --> $DIR/issue-3214.rs:6:22
diff --git a/tests/ui/issues/issue-35570.stderr b/tests/ui/issues/issue-35570.stderr
index 2697d46bdb2..197e80ac097 100644
--- a/tests/ui/issues/issue-35570.stderr
+++ b/tests/ui/issues/issue-35570.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `for<'a> (): Trait2<'a>` is not satisfied
    |
 LL | fn _ice(param: Box<dyn for <'a> Trait1<<() as Trait2<'a>>::Ty>>) {
    |                                        ^^^^^^^^^^^^^^^^^^^^^^ the trait `for<'a> Trait2<'a>` is not implemented for `()`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-35570.rs:4:1
+   |
+LL | trait Trait2<'a> {
+   | ^^^^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/issues/issue-5997-enum.rs b/tests/ui/issues/issue-5997-enum.rs
index 3ff4e036c60..0b1857ae3df 100644
--- a/tests/ui/issues/issue-5997-enum.rs
+++ b/tests/ui/issues/issue-5997-enum.rs
@@ -1,6 +1,6 @@
 fn f<Z>() -> bool {
     enum E { V(Z) }
-    //~^ ERROR can't use generic parameters from outer function
+    //~^ ERROR can't use generic parameters from outer item
     true
 }
 
diff --git a/tests/ui/issues/issue-5997-enum.stderr b/tests/ui/issues/issue-5997-enum.stderr
index 3a79215d3ae..d07258ea7a2 100644
--- a/tests/ui/issues/issue-5997-enum.stderr
+++ b/tests/ui/issues/issue-5997-enum.stderr
@@ -1,12 +1,12 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-5997-enum.rs:2:16
    |
 LL | fn f<Z>() -> bool {
-   |      - type parameter from outer function
+   |      - type parameter from outer item
 LL |     enum E { V(Z) }
-   |           -    ^ use of generic parameter from outer function
+   |           -    ^ use of generic parameter from outer item
    |           |
-   |           help: try using a local generic parameter instead: `<Z>`
+   |           help: try introducing a local generic parameter here: `<Z>`
 
 error: aborting due to previous error
 
diff --git a/tests/ui/issues/issue-5997-struct.rs b/tests/ui/issues/issue-5997-struct.rs
index 6cf510b0a9d..19d994b0dfb 100644
--- a/tests/ui/issues/issue-5997-struct.rs
+++ b/tests/ui/issues/issue-5997-struct.rs
@@ -1,5 +1,5 @@
 fn f<T>() -> bool {
-    struct S(T); //~ ERROR can't use generic parameters from outer function
+    struct S(T); //~ ERROR can't use generic parameters from outer item
 
     true
 }
diff --git a/tests/ui/issues/issue-5997-struct.stderr b/tests/ui/issues/issue-5997-struct.stderr
index d2e97f76771..83229e02c6c 100644
--- a/tests/ui/issues/issue-5997-struct.stderr
+++ b/tests/ui/issues/issue-5997-struct.stderr
@@ -1,12 +1,12 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-5997-struct.rs:2:14
    |
 LL | fn f<T>() -> bool {
-   |      - type parameter from outer function
+   |      - type parameter from outer item
 LL |     struct S(T);
-   |             -^ use of generic parameter from outer function
+   |             -^ use of generic parameter from outer item
    |             |
-   |             help: try using a local generic parameter instead: `<T>`
+   |             help: try introducing a local generic parameter here: `<T>`
 
 error: aborting due to previous error
 
diff --git a/tests/ui/issues/issue-60218.stderr b/tests/ui/issues/issue-60218.stderr
index 563690c9a5d..ae3c4d12025 100644
--- a/tests/ui/issues/issue-60218.stderr
+++ b/tests/ui/issues/issue-60218.stderr
@@ -6,6 +6,11 @@ LL |     trigger_error(vec![], |x: &u32| x)
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-60218.rs:7:1
+   |
+LL | pub trait Foo {}
+   | ^^^^^^^^^^^^^
 note: required by a bound in `trigger_error`
   --> $DIR/issue-60218.rs:13:72
    |
diff --git a/tests/ui/issues/issue-66353.stderr b/tests/ui/issues/issue-66353.stderr
index 71530f58220..7ab7547b42d 100644
--- a/tests/ui/issues/issue-66353.stderr
+++ b/tests/ui/issues/issue-66353.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): _A` is not satisfied
    |
 LL |     _Func::< <() as _A>::AssocT >::func(());
    |               ^^ the trait `_A` is not implemented for `()`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-66353.rs:7:1
+   |
+LL | trait _A {
+   | ^^^^^^^^
 
 error[E0277]: the trait bound `(): _Func<_>` is not satisfied
   --> $DIR/issue-66353.rs:12:41
@@ -11,6 +17,12 @@ LL |     _Func::< <() as _A>::AssocT >::func(());
    |     ----------------------------------- ^^ the trait `_Func<_>` is not implemented for `()`
    |     |
    |     required by a bound introduced by this call
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-66353.rs:3:1
+   |
+LL | trait _Func<T> {
+   | ^^^^^^^^^^^^^^
 
 error: aborting due to 2 previous errors
 
diff --git a/tests/ui/issues/issue-69602-type-err-during-codegen-ice.stderr b/tests/ui/issues/issue-69602-type-err-during-codegen-ice.stderr
index ba385d887fb..6f9302bc4a5 100644
--- a/tests/ui/issues/issue-69602-type-err-during-codegen-ice.stderr
+++ b/tests/ui/issues/issue-69602-type-err-during-codegen-ice.stderr
@@ -13,7 +13,7 @@ LL |     type MyA: TraitA;
 LL | impl TraitB for B {
    | ^^^^^^^^^^^^^^^^^ missing `MyA` in implementation
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/issue-69602-type-err-during-codegen-ice.rs:21:17
    |
 LL |     let _ = [0; B::VALUE];
diff --git a/tests/ui/layout/homogeneous-aggr-transparent.rs b/tests/ui/layout/homogeneous-aggr-transparent.rs
new file mode 100644
index 00000000000..9703d2bf294
--- /dev/null
+++ b/tests/ui/layout/homogeneous-aggr-transparent.rs
@@ -0,0 +1,44 @@
+#![feature(rustc_attrs)]
+#![feature(transparent_unions)]
+use std::marker::PhantomData;
+
+// Regression test for #115664. We want to ensure that `repr(transparent)` wrappers do not affect
+// the result of `homogeneous_aggregate`.
+
+type Tuple = (f32, f32, f32);
+
+struct Zst;
+
+#[repr(transparent)]
+struct Wrapper1<T>(T);
+#[repr(transparent)]
+struct Wrapper2<T>((), Zst, T);
+#[repr(transparent)]
+struct Wrapper3<T>(T, [u8; 0], PhantomData<u64>);
+#[repr(transparent)]
+union WrapperUnion<T: Copy> {
+    nothing: (),
+    something: T,
+}
+
+#[rustc_layout(homogeneous_aggregate)]
+pub type Test0 = Tuple;
+//~^ ERROR homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) }))
+
+#[rustc_layout(homogeneous_aggregate)]
+pub type Test1 = Wrapper1<Tuple>;
+//~^ ERROR homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) }))
+
+#[rustc_layout(homogeneous_aggregate)]
+pub type Test2 = Wrapper2<Tuple>;
+//~^ ERROR homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) }))
+
+#[rustc_layout(homogeneous_aggregate)]
+pub type Test3 = Wrapper3<Tuple>;
+//~^ ERROR homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) }))
+
+#[rustc_layout(homogeneous_aggregate)]
+pub type Test4 = WrapperUnion<Tuple>;
+//~^ ERROR homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) }))
+
+fn main() {}
diff --git a/tests/ui/layout/homogeneous-aggr-transparent.stderr b/tests/ui/layout/homogeneous-aggr-transparent.stderr
new file mode 100644
index 00000000000..99eb703ac82
--- /dev/null
+++ b/tests/ui/layout/homogeneous-aggr-transparent.stderr
@@ -0,0 +1,32 @@
+error: homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) }))
+  --> $DIR/homogeneous-aggr-transparent.rs:25:1
+   |
+LL | pub type Test0 = Tuple;
+   | ^^^^^^^^^^^^^^
+
+error: homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) }))
+  --> $DIR/homogeneous-aggr-transparent.rs:29:1
+   |
+LL | pub type Test1 = Wrapper1<Tuple>;
+   | ^^^^^^^^^^^^^^
+
+error: homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) }))
+  --> $DIR/homogeneous-aggr-transparent.rs:33:1
+   |
+LL | pub type Test2 = Wrapper2<Tuple>;
+   | ^^^^^^^^^^^^^^
+
+error: homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) }))
+  --> $DIR/homogeneous-aggr-transparent.rs:37:1
+   |
+LL | pub type Test3 = Wrapper3<Tuple>;
+   | ^^^^^^^^^^^^^^
+
+error: homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) }))
+  --> $DIR/homogeneous-aggr-transparent.rs:41:1
+   |
+LL | pub type Test4 = WrapperUnion<Tuple>;
+   | ^^^^^^^^^^^^^^
+
+error: aborting due to 5 previous errors
+
diff --git a/tests/ui/lifetimes/anonymize-unnamed-bound-vars-in-binders.rs b/tests/ui/lifetimes/anonymize-unnamed-bound-vars-in-binders.rs
new file mode 100644
index 00000000000..05e3763e9d1
--- /dev/null
+++ b/tests/ui/lifetimes/anonymize-unnamed-bound-vars-in-binders.rs
@@ -0,0 +1,27 @@
+// build-pass
+// issue: #115807
+
+trait Chip: for<'a> TraitWithLifetime<'a> + SomeMarker {
+    fn compute(&self);
+}
+
+trait SomeMarker {}
+
+trait TraitWithLifetime<'a>: SomeMarker {}
+
+trait Machine {
+    fn run();
+}
+
+struct BasicMachine;
+
+impl Machine for BasicMachine {
+    fn run() {
+        let chips: [&dyn Chip; 0] = [];
+        let _ = chips.map(|chip| chip.compute());
+    }
+}
+
+fn main() {
+    BasicMachine::run();
+}
diff --git a/tests/ui/lifetimes/lifetime-elision-return-type-trait.stderr b/tests/ui/lifetimes/lifetime-elision-return-type-trait.stderr
index ef1127c59ac..421ab3fcf4e 100644
--- a/tests/ui/lifetimes/lifetime-elision-return-type-trait.stderr
+++ b/tests/ui/lifetimes/lifetime-elision-return-type-trait.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `Result<(), _>: Future` is not satisfied
    |
 LL | fn foo() -> impl Future<Item=(), Error=Box<dyn Error>> {
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Future` is not implemented for `Result<(), _>`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/lifetime-elision-return-type-trait.rs:1:1
+   |
+LL | trait Future {
+   | ^^^^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/limits/issue-55878.stderr b/tests/ui/limits/issue-55878.stderr
index 510b36edd8f..93716c0b347 100644
--- a/tests/ui/limits/issue-55878.stderr
+++ b/tests/ui/limits/issue-55878.stderr
@@ -1,6 +1,8 @@
-error[E0080]: values of the type `[u8; usize::MAX]` are too big for the current architecture
+error[E0080]: evaluation of constant value failed
   --> $SRC_DIR/core/src/mem/mod.rs:LL:COL
    |
+   = note: values of the type `[u8; usize::MAX]` are too big for the current architecture
+   |
 note: inside `std::mem::size_of::<[u8; usize::MAX]>`
   --> $SRC_DIR/core/src/mem/mod.rs:LL:COL
 note: inside `main`
@@ -9,7 +11,7 @@ note: inside `main`
 LL |     println!("Size: {}", std::mem::size_of::<[u8; u64::MAX as usize]>());
    |                          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/issue-55878.rs:7:26
    |
 LL |     println!("Size: {}", std::mem::size_of::<[u8; u64::MAX as usize]>());
@@ -17,7 +19,7 @@ LL |     println!("Size: {}", std::mem::size_of::<[u8; u64::MAX as usize]>());
    |
    = note: this note originates in the macro `$crate::format_args_nl` which comes from the expansion of the macro `println` (in Nightly builds, run with -Z macro-backtrace for more info)
 
-note: erroneous constant used
+note: erroneous constant encountered
   --> $DIR/issue-55878.rs:7:26
    |
 LL |     println!("Size: {}", std::mem::size_of::<[u8; u64::MAX as usize]>());
diff --git a/tests/ui/limits/issue-56762.rs b/tests/ui/limits/issue-56762.rs
index ed7ee4da85d..1c7facb045d 100644
--- a/tests/ui/limits/issue-56762.rs
+++ b/tests/ui/limits/issue-56762.rs
@@ -14,8 +14,10 @@ impl TooBigArray {
 }
 
 static MY_TOO_BIG_ARRAY_1: TooBigArray = TooBigArray::new();
-//~^ ERROR values of the type `[u8; 2305843009213693951]` are too big
+//~^ ERROR could not evaluate static initializer
+//~| too big
 static MY_TOO_BIG_ARRAY_2: [u8; HUGE_SIZE] = [0x00; HUGE_SIZE];
-//~^ ERROR values of the type `[u8; 2305843009213693951]` are too big
+//~^ ERROR could not evaluate static initializer
+//~| too big
 
 fn main() { }
diff --git a/tests/ui/limits/issue-56762.stderr b/tests/ui/limits/issue-56762.stderr
index 29f2a8859ee..3a6c3559ac1 100644
--- a/tests/ui/limits/issue-56762.stderr
+++ b/tests/ui/limits/issue-56762.stderr
@@ -1,14 +1,14 @@
-error[E0080]: values of the type `[u8; 2305843009213693951]` are too big for the current architecture
+error[E0080]: could not evaluate static initializer
   --> $DIR/issue-56762.rs:16:1
    |
 LL | static MY_TOO_BIG_ARRAY_1: TooBigArray = TooBigArray::new();
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ values of the type `[u8; 2305843009213693951]` are too big for the current architecture
 
-error[E0080]: values of the type `[u8; 2305843009213693951]` are too big for the current architecture
-  --> $DIR/issue-56762.rs:18:1
+error[E0080]: could not evaluate static initializer
+  --> $DIR/issue-56762.rs:19:1
    |
 LL | static MY_TOO_BIG_ARRAY_2: [u8; HUGE_SIZE] = [0x00; HUGE_SIZE];
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ values of the type `[u8; 2305843009213693951]` are too big for the current architecture
 
 error: aborting due to 2 previous errors
 
diff --git a/tests/ui/lint/expr-field.rs b/tests/ui/lint/expr-field.rs
new file mode 100644
index 00000000000..638fbf521c4
--- /dev/null
+++ b/tests/ui/lint/expr-field.rs
@@ -0,0 +1,15 @@
+// check-pass
+
+pub struct A {
+    pub x: u32,
+}
+
+#[deny(unused_comparisons)]
+pub fn foo(y: u32) -> A {
+    A {
+        #[allow(unused_comparisons)]
+        x: if y < 0 { 1 } else { 2 },
+    }
+}
+
+fn main() {}
diff --git a/tests/ui/lint/lint-ctypes-option-nonnull-unsized.rs b/tests/ui/lint/lint-ctypes-option-nonnull-unsized.rs
new file mode 100644
index 00000000000..ca08eb23a57
--- /dev/null
+++ b/tests/ui/lint/lint-ctypes-option-nonnull-unsized.rs
@@ -0,0 +1,8 @@
+#![deny(improper_ctypes_definitions)]
+
+extern "C" fn foo<T: ?Sized + 'static>() -> Option<&'static T> {
+    //~^ ERROR `extern` fn uses type `Option<&T>`, which is not FFI-safe
+    None
+}
+
+fn main() {}
diff --git a/tests/ui/lint/lint-ctypes-option-nonnull-unsized.stderr b/tests/ui/lint/lint-ctypes-option-nonnull-unsized.stderr
new file mode 100644
index 00000000000..f59fb3cc750
--- /dev/null
+++ b/tests/ui/lint/lint-ctypes-option-nonnull-unsized.stderr
@@ -0,0 +1,16 @@
+error: `extern` fn uses type `Option<&T>`, which is not FFI-safe
+  --> $DIR/lint-ctypes-option-nonnull-unsized.rs:3:45
+   |
+LL | extern "C" fn foo<T: ?Sized + 'static>() -> Option<&'static T> {
+   |                                             ^^^^^^^^^^^^^^^^^^ not FFI-safe
+   |
+   = help: consider adding a `#[repr(C)]`, `#[repr(transparent)]`, or integer `#[repr(...)]` attribute to this enum
+   = note: enum has no representation hint
+note: the lint level is defined here
+  --> $DIR/lint-ctypes-option-nonnull-unsized.rs:1:9
+   |
+LL | #![deny(improper_ctypes_definitions)]
+   |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to previous error
+
diff --git a/tests/ui/lint/no-coverage.rs b/tests/ui/lint/no-coverage.rs
index 07906a43472..907d25d333e 100644
--- a/tests/ui/lint/no-coverage.rs
+++ b/tests/ui/lint/no-coverage.rs
@@ -1,55 +1,55 @@
 #![feature(extern_types)]
-#![feature(no_coverage)]
+#![feature(coverage_attribute)]
 #![feature(impl_trait_in_assoc_type)]
 #![warn(unused_attributes)]
-#![no_coverage]
-//~^ WARN: `#[no_coverage]` does not propagate into items and must be applied to the contained functions directly
+#![coverage(off)]
+//~^ WARN: `#[coverage]` does not propagate into items and must be applied to the contained functions directly
 
-#[no_coverage]
-//~^ WARN: `#[no_coverage]` does not propagate into items and must be applied to the contained functions directly
+#[coverage(off)]
+//~^ WARN: `#[coverage]` does not propagate into items and must be applied to the contained functions directly
 trait Trait {
-    #[no_coverage] //~ ERROR `#[no_coverage]` must be applied to coverable code
+    #[coverage(off)] //~ ERROR `#[coverage]` must be applied to coverable code
     const X: u32;
 
-    #[no_coverage] //~ ERROR `#[no_coverage]` must be applied to coverable code
+    #[coverage(off)] //~ ERROR `#[coverage]` must be applied to coverable code
     type T;
 
     type U;
 }
 
-#[no_coverage]
-//~^ WARN: `#[no_coverage]` does not propagate into items and must be applied to the contained functions directly
+#[coverage(off)]
+//~^ WARN: `#[coverage]` does not propagate into items and must be applied to the contained functions directly
 impl Trait for () {
     const X: u32 = 0;
 
-    #[no_coverage] //~ ERROR `#[no_coverage]` must be applied to coverable code
+    #[coverage(off)] //~ ERROR `#[coverage]` must be applied to coverable code
     type T = Self;
 
-    #[no_coverage] //~ ERROR `#[no_coverage]` must be applied to coverable code
+    #[coverage(off)] //~ ERROR `#[coverage]` must be applied to coverable code
     type U = impl Trait; //~ ERROR unconstrained opaque type
 }
 
 extern "C" {
-    #[no_coverage] //~ ERROR `#[no_coverage]` must be applied to coverable code
+    #[coverage(off)] //~ ERROR `#[coverage]` must be applied to coverable code
     static X: u32;
 
-    #[no_coverage] //~ ERROR `#[no_coverage]` must be applied to coverable code
+    #[coverage(off)] //~ ERROR `#[coverage]` must be applied to coverable code
     type T;
 }
 
-#[no_coverage]
+#[coverage(off)]
 fn main() {
-    #[no_coverage]
-    //~^ WARN `#[no_coverage]` may only be applied to function definitions
+    #[coverage(off)]
+    //~^ WARN `#[coverage]` may only be applied to function definitions
     let _ = ();
 
     match () {
-        #[no_coverage]
-        //~^ WARN `#[no_coverage]` may only be applied to function definitions
+        #[coverage(off)]
+        //~^ WARN `#[coverage]` may only be applied to function definitions
         () => (),
     }
 
-    #[no_coverage]
-    //~^ WARN `#[no_coverage]` may only be applied to function definitions
+    #[coverage(off)]
+    //~^ WARN `#[coverage]` may only be applied to function definitions
     return ();
 }
diff --git a/tests/ui/lint/no-coverage.stderr b/tests/ui/lint/no-coverage.stderr
index 404efbeac1e..a87b0fb49f0 100644
--- a/tests/ui/lint/no-coverage.stderr
+++ b/tests/ui/lint/no-coverage.stderr
@@ -1,8 +1,8 @@
-warning: `#[no_coverage]` does not propagate into items and must be applied to the contained functions directly
+warning: `#[coverage]` does not propagate into items and must be applied to the contained functions directly
   --> $DIR/no-coverage.rs:8:1
    |
-LL | #[no_coverage]
-   | ^^^^^^^^^^^^^^
+LL | #[coverage(off)]
+   | ^^^^^^^^^^^^^^^^
    |
 note: the lint level is defined here
   --> $DIR/no-coverage.rs:4:9
@@ -10,83 +10,83 @@ note: the lint level is defined here
 LL | #![warn(unused_attributes)]
    |         ^^^^^^^^^^^^^^^^^
 
-warning: `#[no_coverage]` does not propagate into items and must be applied to the contained functions directly
+warning: `#[coverage]` does not propagate into items and must be applied to the contained functions directly
   --> $DIR/no-coverage.rs:20:1
    |
-LL | #[no_coverage]
-   | ^^^^^^^^^^^^^^
+LL | #[coverage(off)]
+   | ^^^^^^^^^^^^^^^^
 
-warning: `#[no_coverage]` may only be applied to function definitions
+warning: `#[coverage]` may only be applied to function definitions
   --> $DIR/no-coverage.rs:42:5
    |
-LL |     #[no_coverage]
-   |     ^^^^^^^^^^^^^^
+LL |     #[coverage(off)]
+   |     ^^^^^^^^^^^^^^^^
 
-warning: `#[no_coverage]` may only be applied to function definitions
+warning: `#[coverage]` may only be applied to function definitions
   --> $DIR/no-coverage.rs:47:9
    |
-LL |         #[no_coverage]
-   |         ^^^^^^^^^^^^^^
+LL |         #[coverage(off)]
+   |         ^^^^^^^^^^^^^^^^
 
-warning: `#[no_coverage]` may only be applied to function definitions
+warning: `#[coverage]` may only be applied to function definitions
   --> $DIR/no-coverage.rs:52:5
    |
-LL |     #[no_coverage]
-   |     ^^^^^^^^^^^^^^
+LL |     #[coverage(off)]
+   |     ^^^^^^^^^^^^^^^^
 
-error[E0788]: `#[no_coverage]` must be applied to coverable code
+error[E0788]: `#[coverage]` must be applied to coverable code
   --> $DIR/no-coverage.rs:11:5
    |
-LL |     #[no_coverage]
-   |     ^^^^^^^^^^^^^^
+LL |     #[coverage(off)]
+   |     ^^^^^^^^^^^^^^^^
 LL |     const X: u32;
    |     ------------- not coverable code
 
-error[E0788]: `#[no_coverage]` must be applied to coverable code
+error[E0788]: `#[coverage]` must be applied to coverable code
   --> $DIR/no-coverage.rs:14:5
    |
-LL |     #[no_coverage]
-   |     ^^^^^^^^^^^^^^
+LL |     #[coverage(off)]
+   |     ^^^^^^^^^^^^^^^^
 LL |     type T;
    |     ------- not coverable code
 
-error[E0788]: `#[no_coverage]` must be applied to coverable code
+error[E0788]: `#[coverage]` must be applied to coverable code
   --> $DIR/no-coverage.rs:25:5
    |
-LL |     #[no_coverage]
-   |     ^^^^^^^^^^^^^^
+LL |     #[coverage(off)]
+   |     ^^^^^^^^^^^^^^^^
 LL |     type T = Self;
    |     -------------- not coverable code
 
-error[E0788]: `#[no_coverage]` must be applied to coverable code
+error[E0788]: `#[coverage]` must be applied to coverable code
   --> $DIR/no-coverage.rs:28:5
    |
-LL |     #[no_coverage]
-   |     ^^^^^^^^^^^^^^
+LL |     #[coverage(off)]
+   |     ^^^^^^^^^^^^^^^^
 LL |     type U = impl Trait;
    |     -------------------- not coverable code
 
-error[E0788]: `#[no_coverage]` must be applied to coverable code
+error[E0788]: `#[coverage]` must be applied to coverable code
   --> $DIR/no-coverage.rs:33:5
    |
-LL |     #[no_coverage]
-   |     ^^^^^^^^^^^^^^
+LL |     #[coverage(off)]
+   |     ^^^^^^^^^^^^^^^^
 LL |     static X: u32;
    |     -------------- not coverable code
 
-error[E0788]: `#[no_coverage]` must be applied to coverable code
+error[E0788]: `#[coverage]` must be applied to coverable code
   --> $DIR/no-coverage.rs:36:5
    |
-LL |     #[no_coverage]
-   |     ^^^^^^^^^^^^^^
+LL |     #[coverage(off)]
+   |     ^^^^^^^^^^^^^^^^
 LL |     type T;
    |     ------- not coverable code
 
-warning: `#[no_coverage]` does not propagate into items and must be applied to the contained functions directly
+warning: `#[coverage]` does not propagate into items and must be applied to the contained functions directly
   --> $DIR/no-coverage.rs:5:1
    |
-LL | #![no_coverage]
-   | ^^^^^^^^^^^^^^^
+LL | #![coverage(off)]
+   | ^^^^^^^^^^^^^^^^^
 
 error: unconstrained opaque type
   --> $DIR/no-coverage.rs:29:14
diff --git a/tests/ui/lint/ptr_null_checks.rs b/tests/ui/lint/ptr_null_checks.rs
index e677ea3094d..3028084e962 100644
--- a/tests/ui/lint/ptr_null_checks.rs
+++ b/tests/ui/lint/ptr_null_checks.rs
@@ -38,15 +38,15 @@ fn main() {
     if (&mut 8 as *mut i32).is_null() {}
     //~^ WARN references are not nullable
     if ptr::from_mut(&mut 8).is_null() {}
-    //~^ WARN references are not nullable
+    //~^ WARN call is never null
     if (&8 as *const i32).is_null() {}
     //~^ WARN references are not nullable
     if ptr::from_ref(&8).is_null() {}
-    //~^ WARN references are not nullable
+    //~^ WARN call is never null
     if ptr::from_ref(&8).cast_mut().is_null() {}
-    //~^ WARN references are not nullable
+    //~^ WARN call is never null
     if (ptr::from_ref(&8).cast_mut() as *mut i32).is_null() {}
-    //~^ WARN references are not nullable
+    //~^ WARN call is never null
     if (&8 as *const i32) == std::ptr::null() {}
     //~^ WARN references are not nullable
     let ref_num = &8;
@@ -65,6 +65,12 @@ fn main() {
     if (&*{ static_i32() } as *const i32).is_null() {}
     //~^ WARN references are not nullable
 
+    // ---------------- Functions -------------------
+    if ptr::NonNull::new(&mut 8).unwrap().as_ptr().is_null() {}
+    //~^ WARN call is never null
+    if ptr::NonNull::<u8>::dangling().as_ptr().is_null() {}
+    //~^ WARN call is never null
+
     // ----------------------------------------------
     const ZPTR: *const () = 0 as *const _;
     const NOT_ZPTR: *const () = 1 as *const _;
diff --git a/tests/ui/lint/ptr_null_checks.stderr b/tests/ui/lint/ptr_null_checks.stderr
index 3cee1804b62..0edc1b86536 100644
--- a/tests/ui/lint/ptr_null_checks.stderr
+++ b/tests/ui/lint/ptr_null_checks.stderr
@@ -117,13 +117,11 @@ LL |     if (&mut 8 as *mut i32).is_null() {}
    |         |
    |         expression has type `&mut i32`
 
-warning: references are not nullable, so checking them for null will always return false
+warning: returned pointer of `from_mut` call is never null, so checking it for null will always return false
   --> $DIR/ptr_null_checks.rs:40:8
    |
 LL |     if ptr::from_mut(&mut 8).is_null() {}
-   |        ^^^^^^^^^^^^^^------^^^^^^^^^^^
-   |                      |
-   |                      expression has type `&mut i32`
+   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 warning: references are not nullable, so checking them for null will always return false
   --> $DIR/ptr_null_checks.rs:42:8
@@ -133,29 +131,23 @@ LL |     if (&8 as *const i32).is_null() {}
    |         |
    |         expression has type `&i32`
 
-warning: references are not nullable, so checking them for null will always return false
+warning: returned pointer of `from_ref` call is never null, so checking it for null will always return false
   --> $DIR/ptr_null_checks.rs:44:8
    |
 LL |     if ptr::from_ref(&8).is_null() {}
-   |        ^^^^^^^^^^^^^^--^^^^^^^^^^^
-   |                      |
-   |                      expression has type `&i32`
+   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-warning: references are not nullable, so checking them for null will always return false
+warning: returned pointer of `from_ref` call is never null, so checking it for null will always return false
   --> $DIR/ptr_null_checks.rs:46:8
    |
 LL |     if ptr::from_ref(&8).cast_mut().is_null() {}
-   |        ^^^^^^^^^^^^^^--^^^^^^^^^^^^^^^^^^^^^^
-   |                      |
-   |                      expression has type `&i32`
+   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-warning: references are not nullable, so checking them for null will always return false
+warning: returned pointer of `from_ref` call is never null, so checking it for null will always return false
   --> $DIR/ptr_null_checks.rs:48:8
    |
 LL |     if (ptr::from_ref(&8).cast_mut() as *mut i32).is_null() {}
-   |        ^^^^^^^^^^^^^^^--^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-   |                       |
-   |                       expression has type `&i32`
+   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 warning: references are not nullable, so checking them for null will always return false
   --> $DIR/ptr_null_checks.rs:50:8
@@ -221,5 +213,17 @@ LL |     if (&*{ static_i32() } as *const i32).is_null() {}
    |         |
    |         expression has type `&i32`
 
-warning: 25 warnings emitted
+warning: returned pointer of `as_ptr` call is never null, so checking it for null will always return false
+  --> $DIR/ptr_null_checks.rs:69:8
+   |
+LL |     if ptr::NonNull::new(&mut 8).unwrap().as_ptr().is_null() {}
+   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+warning: returned pointer of `as_ptr` call is never null, so checking it for null will always return false
+  --> $DIR/ptr_null_checks.rs:71:8
+   |
+LL |     if ptr::NonNull::<u8>::dangling().as_ptr().is_null() {}
+   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+warning: 27 warnings emitted
 
diff --git a/tests/ui/match/issue-115681.rs b/tests/ui/match/issue-115681.rs
new file mode 100644
index 00000000000..c41e808e170
--- /dev/null
+++ b/tests/ui/match/issue-115681.rs
@@ -0,0 +1,32 @@
+// run-pass
+// compile-flags: -C opt-level=1
+
+// Make sure LLVM does not miscompile this match.
+fn main() {
+    enum Bits {
+        None = 0x00,
+        Low = 0x40,
+        High = 0x80,
+        Both = 0xC0,
+    }
+
+    let value = Box::new(0x40u8);
+    let mut out = Box::new(0u8);
+
+    let bits = match *value {
+        0x00 => Bits::None,
+        0x40 => Bits::Low,
+        0x80 => Bits::High,
+        0xC0 => Bits::Both,
+        _ => return,
+    };
+
+    match bits {
+        Bits::None | Bits::Low => {
+            *out = 1;
+        }
+        _ => (),
+    }
+
+    assert_eq!(*out, 1);
+}
diff --git a/tests/ui/mir/issue-92893.rs b/tests/ui/mir/issue-92893.rs
index 635050f376c..6127d267ebc 100644
--- a/tests/ui/mir/issue-92893.rs
+++ b/tests/ui/mir/issue-92893.rs
@@ -1,7 +1,5 @@
 struct Bug<A = [(); (let a = (), 1).1]> {
-    //~^ `let` expressions are not supported here
-    //~| `let` expressions in this position are unstable [E0658]
-    //~| expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     a: A
 }
 
diff --git a/tests/ui/mir/issue-92893.stderr b/tests/ui/mir/issue-92893.stderr
index 4a0fcce31d7..6c1a9dc0317 100644
--- a/tests/ui/mir/issue-92893.stderr
+++ b/tests/ui/mir/issue-92893.stderr
@@ -3,24 +3,8 @@ error: expected expression, found `let` statement
    |
 LL | struct Bug<A = [(); (let a = (), 1).1]> {
    |                      ^^^
-
-error: `let` expressions are not supported here
-  --> $DIR/issue-92893.rs:1:22
-   |
-LL | struct Bug<A = [(); (let a = (), 1).1]> {
-   |                      ^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/issue-92893.rs:1:22
-   |
-LL | struct Bug<A = [(); (let a = (), 1).1]> {
-   |                      ^^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error: aborting due to 3 previous errors
+error: aborting due to previous error
 
-For more information about this error, try `rustc --explain E0658`.
diff --git a/tests/ui/mismatched_types/cast-rfc0401.stderr b/tests/ui/mismatched_types/cast-rfc0401.stderr
index 6b9ac3c5852..d63cec48917 100644
--- a/tests/ui/mismatched_types/cast-rfc0401.stderr
+++ b/tests/ui/mismatched_types/cast-rfc0401.stderr
@@ -82,13 +82,18 @@ error[E0606]: casting `f32` as `*const u8` is invalid
 LL |     let _ = f as *const u8;
    |             ^^^^^^^^^^^^^^
 
-error[E0054]: cannot cast as `bool`
+error[E0054]: cannot cast `i32` as `bool`
   --> $DIR/cast-rfc0401.rs:39:13
    |
 LL |     let _ = 3_i32 as bool;
-   |             ^^^^^^^^^^^^^ help: compare with zero instead: `3_i32 != 0`
+   |             ^^^^^^^^^^^^^
+   |
+help: compare with zero instead
+   |
+LL |     let _ = 3_i32 != 0;
+   |                   ~~~~
 
-error[E0054]: cannot cast as `bool`
+error[E0054]: cannot cast `E` as `bool`
   --> $DIR/cast-rfc0401.rs:40:13
    |
 LL |     let _ = E::A as bool;
diff --git a/tests/ui/namespace/namespace-mix.stderr b/tests/ui/namespace/namespace-mix.stderr
index 3ac5e96c574..4eff08ead42 100644
--- a/tests/ui/namespace/namespace-mix.stderr
+++ b/tests/ui/namespace/namespace-mix.stderr
@@ -114,6 +114,11 @@ LL |     check(m1::S{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -128,6 +133,11 @@ LL |     check(m2::S{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -142,6 +152,11 @@ LL |     check(m2::S);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -156,6 +171,11 @@ LL |     check(xm1::S{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -170,6 +190,11 @@ LL |     check(xm2::S{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -184,6 +209,11 @@ LL |     check(xm2::S);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -198,6 +228,11 @@ LL |     check(m3::TS{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -212,6 +247,11 @@ LL |     check(m3::TS);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -226,6 +266,11 @@ LL |     check(m4::TS{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -240,6 +285,11 @@ LL |     check(m4::TS);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -254,6 +304,11 @@ LL |     check(xm3::TS{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -268,6 +323,11 @@ LL |     check(xm3::TS);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -282,6 +342,11 @@ LL |     check(xm4::TS{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -296,6 +361,11 @@ LL |     check(xm4::TS);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -310,6 +380,11 @@ LL |     check(m5::US{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -324,6 +399,11 @@ LL |     check(m5::US);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -338,6 +418,11 @@ LL |     check(m6::US{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -352,6 +437,11 @@ LL |     check(m6::US);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -366,6 +456,11 @@ LL |     check(xm5::US{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -380,6 +475,11 @@ LL |     check(xm5::US);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -394,6 +494,11 @@ LL |     check(xm6::US{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -408,6 +513,11 @@ LL |     check(xm6::US);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -422,6 +532,11 @@ LL |     check(m7::V{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -436,6 +551,11 @@ LL |     check(m8::V{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -450,6 +570,11 @@ LL |     check(m8::V);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -464,6 +589,11 @@ LL |     check(xm7::V{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -478,6 +608,11 @@ LL |     check(xm8::V{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -492,6 +627,11 @@ LL |     check(xm8::V);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -506,6 +646,11 @@ LL |     check(m9::TV{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -520,6 +665,11 @@ LL |     check(m9::TV);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -534,6 +684,11 @@ LL |     check(mA::TV{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -548,6 +703,11 @@ LL |     check(mA::TV);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -562,6 +722,11 @@ LL |     check(xm9::TV{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -576,6 +741,11 @@ LL |     check(xm9::TV);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -590,6 +760,11 @@ LL |     check(xmA::TV{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -604,6 +779,11 @@ LL |     check(xmA::TV);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -618,6 +798,11 @@ LL |     check(mB::UV{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -632,6 +817,11 @@ LL |     check(mB::UV);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -646,6 +836,11 @@ LL |     check(mC::UV{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -660,6 +855,11 @@ LL |     check(mC::UV);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -674,6 +874,11 @@ LL |     check(xmB::UV{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -688,6 +893,11 @@ LL |     check(xmB::UV);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -702,6 +912,11 @@ LL |     check(xmC::UV{});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
@@ -716,6 +931,11 @@ LL |     check(xmC::UV);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/namespace-mix.rs:20:1
+   |
+LL | trait Impossible {}
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `check`
   --> $DIR/namespace-mix.rs:21:13
    |
diff --git a/tests/ui/nested-ty-params.rs b/tests/ui/nested-ty-params.rs
index 85413acdb14..25bac1ba24b 100644
--- a/tests/ui/nested-ty-params.rs
+++ b/tests/ui/nested-ty-params.rs
@@ -1,4 +1,4 @@
-// error-pattern:can't use generic parameters from outer function
+// error-pattern:can't use generic parameters from outer item
 fn hd<U>(v: Vec<U> ) -> U {
     fn hd1(w: [U]) -> U { return w[0]; }
 
diff --git a/tests/ui/nested-ty-params.stderr b/tests/ui/nested-ty-params.stderr
index 8f4746f5ec3..a9cdec66719 100644
--- a/tests/ui/nested-ty-params.stderr
+++ b/tests/ui/nested-ty-params.stderr
@@ -1,22 +1,22 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/nested-ty-params.rs:3:16
    |
 LL | fn hd<U>(v: Vec<U> ) -> U {
-   |       - type parameter from outer function
+   |       - type parameter from outer item
 LL |     fn hd1(w: [U]) -> U { return w[0]; }
-   |           -    ^ use of generic parameter from outer function
+   |           -    ^ use of generic parameter from outer item
    |           |
-   |           help: try using a local generic parameter instead: `<U>`
+   |           help: try introducing a local generic parameter here: `<U>`
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/nested-ty-params.rs:3:23
    |
 LL | fn hd<U>(v: Vec<U> ) -> U {
-   |       - type parameter from outer function
+   |       - type parameter from outer item
 LL |     fn hd1(w: [U]) -> U { return w[0]; }
-   |           -           ^ use of generic parameter from outer function
+   |           -           ^ use of generic parameter from outer item
    |           |
-   |           help: try using a local generic parameter instead: `<U>`
+   |           help: try introducing a local generic parameter here: `<U>`
 
 error: aborting due to 2 previous errors
 
diff --git a/tests/ui/never_type/feature-gate-never_type_fallback.stderr b/tests/ui/never_type/feature-gate-never_type_fallback.stderr
index 2db1cc4b776..56aafbb4ce8 100644
--- a/tests/ui/never_type/feature-gate-never_type_fallback.stderr
+++ b/tests/ui/never_type/feature-gate-never_type_fallback.stderr
@@ -8,6 +8,11 @@ LL |     foo(panic!())
    |     |   this tail expression is of type `()`
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/feature-gate-never_type_fallback.rs:7:1
+   |
+LL | trait T {}
+   | ^^^^^^^
 note: required by a bound in `foo`
   --> $DIR/feature-gate-never_type_fallback.rs:13:16
    |
diff --git a/tests/ui/never_type/impl_trait_fallback3.stderr b/tests/ui/never_type/impl_trait_fallback3.stderr
index 5d5d216fb9b..821d141569e 100644
--- a/tests/ui/never_type/impl_trait_fallback3.stderr
+++ b/tests/ui/never_type/impl_trait_fallback3.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): T` is not satisfied
    |
 LL | fn a() -> Foo {
    |           ^^^ the trait `T` is not implemented for `()`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/impl_trait_fallback3.rs:5:1
+   |
+LL | trait T {
+   | ^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/never_type/impl_trait_fallback4.stderr b/tests/ui/never_type/impl_trait_fallback4.stderr
index f2e216e9044..67421ba8da7 100644
--- a/tests/ui/never_type/impl_trait_fallback4.stderr
+++ b/tests/ui/never_type/impl_trait_fallback4.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): T` is not satisfied
    |
 LL | fn foo() -> impl T {
    |             ^^^^^^ the trait `T` is not implemented for `()`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/impl_trait_fallback4.rs:3:1
+   |
+LL | trait T {
+   | ^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/on-unimplemented/on-trait.stderr b/tests/ui/on-unimplemented/on-trait.stderr
index 4b040f1ac5a..4847a1a5a61 100644
--- a/tests/ui/on-unimplemented/on-trait.stderr
+++ b/tests/ui/on-unimplemented/on-trait.stderr
@@ -5,6 +5,11 @@ LL |     let y: Option<Vec<u8>> = collect(x.iter()); // this should give approxi
    |                              ^^^^^^^ a collection of type `Option<Vec<u8>>` cannot be built from an iterator over elements of type `&u8`
    |
    = help: the trait `MyFromIterator<&u8>` is not implemented for `Option<Vec<u8>>`
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-trait.rs:17:1
+   |
+LL | trait MyFromIterator<A> {
+   | ^^^^^^^^^^^^^^^^^^^^^^^
 note: required by a bound in `collect`
   --> $DIR/on-trait.rs:22:39
    |
@@ -18,6 +23,11 @@ LL |     let x: String = foobar();
    |                     ^^^^^^ test error `String` with `u8` `_` `u32` in `Foo`
    |
    = help: the trait `Foo<u8, _, u32>` is not implemented for `String`
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-trait.rs:7:3
+   |
+LL |   pub trait Foo<Bar, Baz, Quux> {}
+   |   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 note: required by a bound in `foobar`
   --> $DIR/on-trait.rs:12:24
    |
diff --git a/tests/ui/on-unimplemented/parent-label.stderr b/tests/ui/on-unimplemented/parent-label.stderr
index 8cd7412fd9d..101a41512d2 100644
--- a/tests/ui/on-unimplemented/parent-label.stderr
+++ b/tests/ui/on-unimplemented/parent-label.stderr
@@ -8,6 +8,11 @@ LL |         f(Foo {});
    |         |
    |         required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/parent-label.rs:6:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `f`
   --> $DIR/parent-label.rs:10:9
    |
@@ -24,6 +29,11 @@ LL |             f(Foo {});
    |             |
    |             required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/parent-label.rs:6:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `f`
   --> $DIR/parent-label.rs:10:9
    |
@@ -41,6 +51,11 @@ LL |             f(Foo {});
    |             |
    |             required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/parent-label.rs:6:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `f`
   --> $DIR/parent-label.rs:10:9
    |
@@ -58,6 +73,11 @@ LL |     f(Foo {});
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/parent-label.rs:6:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `f`
   --> $DIR/parent-label.rs:10:9
    |
diff --git a/tests/ui/parser/issues/issue-115780-pat-lt-bracket-in-macro-call.rs b/tests/ui/parser/issues/issue-115780-pat-lt-bracket-in-macro-call.rs
new file mode 100644
index 00000000000..3421333b8a0
--- /dev/null
+++ b/tests/ui/parser/issues/issue-115780-pat-lt-bracket-in-macro-call.rs
@@ -0,0 +1,21 @@
+// Regression test for issue #115780.
+// Ensure that we don't emit a parse error for the token sequence `Ident "<" Ty` in pattern position
+// if we are inside a macro call since it can be valid input for a subsequent macro rule.
+// See also #103534.
+
+// check-pass
+
+macro_rules! mdo {
+    ($p: pat =<< $e: expr ; $( $t: tt )*) => {
+        $e.and_then(|$p| mdo! { $( $t )* })
+    };
+    (ret<$ty: ty> $e: expr;) => { Some::<$ty>($e) };
+}
+
+fn main() {
+    mdo! {
+        x_val =<< Some(0);
+        y_val =<< Some(1);
+        ret<(i32, i32)> (x_val, y_val);
+    };
+}
diff --git a/tests/ui/pattern/issue-114896.rs b/tests/ui/pattern/issue-114896.rs
new file mode 100644
index 00000000000..cde37f658d6
--- /dev/null
+++ b/tests/ui/pattern/issue-114896.rs
@@ -0,0 +1,7 @@
+fn main() {
+    fn x(a: &char) {
+        let &b = a;
+        b.make_ascii_uppercase();
+//~^ cannot borrow `b` as mutable, as it is not declared as mutable
+    }
+}
diff --git a/tests/ui/pattern/issue-114896.stderr b/tests/ui/pattern/issue-114896.stderr
new file mode 100644
index 00000000000..ffeb7bc1365
--- /dev/null
+++ b/tests/ui/pattern/issue-114896.stderr
@@ -0,0 +1,11 @@
+error[E0596]: cannot borrow `b` as mutable, as it is not declared as mutable
+  --> $DIR/issue-114896.rs:4:9
+   |
+LL |         let &b = a;
+   |             -- help: consider changing this to be mutable: `&(mut b)`
+LL |         b.make_ascii_uppercase();
+   |         ^ cannot borrow as mutable
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0596`.
diff --git a/tests/ui/proc-macro/bad-projection.stderr b/tests/ui/proc-macro/bad-projection.stderr
index 8a8246376fe..8716defa17a 100644
--- a/tests/ui/proc-macro/bad-projection.stderr
+++ b/tests/ui/proc-macro/bad-projection.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): Project` is not satisfied
    |
 LL | pub fn uwu() -> <() as Project>::Assoc {}
    |                 ^^^^^^^^^^^^^^^^^^^^^^ the trait `Project` is not implemented for `()`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/bad-projection.rs:9:1
+   |
+LL | trait Project {
+   | ^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/range/range-1.stderr b/tests/ui/range/range-1.stderr
index ecfc56961ee..96c1ffb2f7e 100644
--- a/tests/ui/range/range-1.stderr
+++ b/tests/ui/range/range-1.stderr
@@ -19,7 +19,7 @@ LL |     for i in false..true {}
              i64
              i128
              usize
-           and 6 others
+           and 8 others
    = note: required for `std::ops::Range<bool>` to implement `Iterator`
    = note: required for `std::ops::Range<bool>` to implement `IntoIterator`
 
diff --git a/tests/ui/repr/repr-transparent-non-exhaustive.rs b/tests/ui/repr/repr-transparent-non-exhaustive.rs
index 506f1dcf3fc..84dd3f49239 100644
--- a/tests/ui/repr/repr-transparent-non-exhaustive.rs
+++ b/tests/ui/repr/repr-transparent-non-exhaustive.rs
@@ -93,4 +93,44 @@ pub struct T16(Sized, ExternalIndirection<NonExhaustiveVariant>);
 //~^ ERROR zero-sized fields in `repr(transparent)` cannot contain external non-exhaustive types
 //~| WARN this was previously accepted by the compiler
 
+#[repr(transparent)]
+pub struct T17(NonExhaustive, Sized);
+//~^ ERROR zero-sized fields in `repr(transparent)` cannot contain external non-exhaustive types
+//~| WARN this was previously accepted by the compiler
+
+#[repr(transparent)]
+pub struct T18(NonExhaustive, NonExhaustive);
+//~^ ERROR zero-sized fields in `repr(transparent)` cannot contain external non-exhaustive types
+//~| WARN this was previously accepted by the compiler
+
+#[repr(transparent)]
+pub struct T19(NonExhaustive, Private);
+//~^ ERROR zero-sized fields in `repr(transparent)` cannot contain external non-exhaustive types
+//~| WARN this was previously accepted by the compiler
+
+#[repr(transparent)]
+pub struct T19Flipped(Private, NonExhaustive);
+//~^ ERROR zero-sized fields in `repr(transparent)` cannot contain external non-exhaustive types
+//~| WARN this was previously accepted by the compiler
+
+#[repr(transparent)]
+pub struct T20(NonExhaustive);
+// Okay, since it's the only field.
+
+#[repr(transparent)]
+pub struct T21(NonExhaustive, InternalNonExhaustive);
+// Okay, since there's only 1 foreign non-exhaustive type.
+
+#[repr(transparent)]
+pub struct T21Flipped(InternalNonExhaustive, NonExhaustive);
+// Okay, since there's only 1 foreign non-exhaustive type.
+
+#[repr(transparent)]
+pub struct T22(NonExhaustive, InternalPrivate);
+// Okay, since there's only 1 foreign non-exhaustive type.
+
+#[repr(transparent)]
+pub struct T22Flipped(InternalPrivate, NonExhaustive);
+// Okay, since there's only 1 foreign non-exhaustive type.
+
 fn main() {}
diff --git a/tests/ui/repr/repr-transparent-non-exhaustive.stderr b/tests/ui/repr/repr-transparent-non-exhaustive.stderr
index 16edf59c7cc..808b9bc986d 100644
--- a/tests/ui/repr/repr-transparent-non-exhaustive.stderr
+++ b/tests/ui/repr/repr-transparent-non-exhaustive.stderr
@@ -123,5 +123,45 @@ LL | pub struct T16(Sized, ExternalIndirection<NonExhaustiveVariant>);
    = note: for more information, see issue #78586 <https://github.com/rust-lang/rust/issues/78586>
    = note: this enum contains `NonExhaustiveVariant`, which is marked with `#[non_exhaustive]`, and makes it not a breaking change to become non-zero-sized in the future.
 
-error: aborting due to 12 previous errors
+error: zero-sized fields in `repr(transparent)` cannot contain external non-exhaustive types
+  --> $DIR/repr-transparent-non-exhaustive.rs:97:16
+   |
+LL | pub struct T17(NonExhaustive, Sized);
+   |                ^^^^^^^^^^^^^
+   |
+   = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
+   = note: for more information, see issue #78586 <https://github.com/rust-lang/rust/issues/78586>
+   = note: this struct contains `NonExhaustive`, which is marked with `#[non_exhaustive]`, and makes it not a breaking change to become non-zero-sized in the future.
+
+error: zero-sized fields in `repr(transparent)` cannot contain external non-exhaustive types
+  --> $DIR/repr-transparent-non-exhaustive.rs:102:31
+   |
+LL | pub struct T18(NonExhaustive, NonExhaustive);
+   |                               ^^^^^^^^^^^^^
+   |
+   = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
+   = note: for more information, see issue #78586 <https://github.com/rust-lang/rust/issues/78586>
+   = note: this struct contains `NonExhaustive`, which is marked with `#[non_exhaustive]`, and makes it not a breaking change to become non-zero-sized in the future.
+
+error: zero-sized fields in `repr(transparent)` cannot contain external non-exhaustive types
+  --> $DIR/repr-transparent-non-exhaustive.rs:107:31
+   |
+LL | pub struct T19(NonExhaustive, Private);
+   |                               ^^^^^^^
+   |
+   = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
+   = note: for more information, see issue #78586 <https://github.com/rust-lang/rust/issues/78586>
+   = note: this struct contains `Private`, which contains private fields, and makes it not a breaking change to become non-zero-sized in the future.
+
+error: zero-sized fields in `repr(transparent)` cannot contain external non-exhaustive types
+  --> $DIR/repr-transparent-non-exhaustive.rs:112:32
+   |
+LL | pub struct T19Flipped(Private, NonExhaustive);
+   |                                ^^^^^^^^^^^^^
+   |
+   = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
+   = note: for more information, see issue #78586 <https://github.com/rust-lang/rust/issues/78586>
+   = note: this struct contains `NonExhaustive`, which is marked with `#[non_exhaustive]`, and makes it not a breaking change to become non-zero-sized in the future.
+
+error: aborting due to 16 previous errors
 
diff --git a/tests/ui/repr/repr-transparent.rs b/tests/ui/repr/repr-transparent.rs
index 8c9d1639c0a..87cf59ce9af 100644
--- a/tests/ui/repr/repr-transparent.rs
+++ b/tests/ui/repr/repr-transparent.rs
@@ -23,23 +23,26 @@ struct ContainsMultipleZst(PhantomData<*const i32>, NoFields);
 struct ContainsZstAndNonZst((), [i32; 2]);
 
 #[repr(transparent)]
-struct MultipleNonZst(u8, u8); //~ ERROR needs at most one non-zero-sized field
+struct MultipleNonZst(u8, u8); //~ ERROR needs at most one field with non-trivial size or alignment
 
 trait Mirror { type It: ?Sized; }
 impl<T: ?Sized> Mirror for T { type It = Self; }
 
 #[repr(transparent)]
 pub struct StructWithProjection(f32, <f32 as Mirror>::It);
-//~^ ERROR needs at most one non-zero-sized field
+//~^ ERROR needs at most one field with non-trivial size or alignment
 
 #[repr(transparent)]
-struct NontrivialAlignZst(u32, [u16; 0]); //~ ERROR alignment larger than 1
+struct NontrivialAlignZst(u32, [u16; 0]); //~ ERROR needs at most one field with non-trivial size or alignment
 
 #[repr(align(32))]
 struct ZstAlign32<T>(PhantomData<T>);
 
 #[repr(transparent)]
-struct GenericAlign<T>(ZstAlign32<T>, u32); //~ ERROR alignment larger than 1
+struct GenericAlign<T>(ZstAlign32<T>, u32); //~ ERROR needs at most one field with non-trivial size or alignment
+
+#[repr(transparent)]
+struct WrapsZstWithAlignment([i32; 0]);
 
 #[repr(transparent)] //~ ERROR unsupported representation for zero-variant enum
 enum Void {} //~ ERROR transparent enum needs exactly one variant, but has 0
@@ -58,7 +61,7 @@ enum UnitFieldEnum {
 enum TooManyFieldsEnum {
     Foo(u32, String),
 }
-//~^^^ ERROR transparent enum needs at most one non-zero-sized field, but has 2
+//~^^^ ERROR transparent enum needs at most one field with non-trivial size or alignment, but has 2
 
 #[repr(transparent)]
 enum MultipleVariants { //~ ERROR transparent enum needs exactly one variant, but has 2
@@ -67,13 +70,13 @@ enum MultipleVariants { //~ ERROR transparent enum needs exactly one variant, bu
 }
 
 #[repr(transparent)]
-enum NontrivialAlignZstEnum {
-    Foo(u32, [u16; 0]), //~ ERROR alignment larger than 1
+enum NontrivialAlignZstEnum { //~ ERROR needs at most one field with non-trivial size or alignment
+    Foo(u32, [u16; 0]),
 }
 
 #[repr(transparent)]
-enum GenericAlignEnum<T> {
-    Foo { bar: ZstAlign32<T>, baz: u32 } //~ ERROR alignment larger than 1
+enum GenericAlignEnum<T> { //~ ERROR needs at most one field with non-trivial size or alignment
+    Foo { bar: ZstAlign32<T>, baz: u32 }
 }
 
 #[repr(transparent)]
@@ -82,7 +85,7 @@ union UnitUnion {
 }
 
 #[repr(transparent)]
-union TooManyFields { //~ ERROR transparent union needs at most one non-zero-sized field, but has 2
+union TooManyFields { //~ ERROR transparent union needs at most one field with non-trivial size or alignment, but has 2
     u: u32,
     s: i32
 }
diff --git a/tests/ui/repr/repr-transparent.stderr b/tests/ui/repr/repr-transparent.stderr
index 028fc25db46..d0c78a8418a 100644
--- a/tests/ui/repr/repr-transparent.stderr
+++ b/tests/ui/repr/repr-transparent.stderr
@@ -1,35 +1,41 @@
-error[E0690]: transparent struct needs at most one non-zero-sized field, but has 2
+error[E0690]: transparent struct needs at most one field with non-trivial size or alignment, but has 2
   --> $DIR/repr-transparent.rs:26:1
    |
 LL | struct MultipleNonZst(u8, u8);
-   | ^^^^^^^^^^^^^^^^^^^^^ --  -- this field is non-zero-sized
+   | ^^^^^^^^^^^^^^^^^^^^^ --  -- this field has non-zero size or requires alignment
    | |                     |
-   | |                     this field is non-zero-sized
-   | needs at most one non-zero-sized field, but has 2
+   | |                     this field has non-zero size or requires alignment
+   | needs at most one field with non-trivial size or alignment, but has 2
 
-error[E0690]: transparent struct needs at most one non-zero-sized field, but has 2
+error[E0690]: transparent struct needs at most one field with non-trivial size or alignment, but has 2
   --> $DIR/repr-transparent.rs:32:1
    |
 LL | pub struct StructWithProjection(f32, <f32 as Mirror>::It);
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ---  ------------------- this field is non-zero-sized
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ---  ------------------- this field has non-zero size or requires alignment
    | |                               |
-   | |                               this field is non-zero-sized
-   | needs at most one non-zero-sized field, but has 2
+   | |                               this field has non-zero size or requires alignment
+   | needs at most one field with non-trivial size or alignment, but has 2
 
-error[E0691]: zero-sized field in transparent struct has alignment larger than 1
-  --> $DIR/repr-transparent.rs:36:32
+error[E0690]: transparent struct needs at most one field with non-trivial size or alignment, but has 2
+  --> $DIR/repr-transparent.rs:36:1
    |
 LL | struct NontrivialAlignZst(u32, [u16; 0]);
-   |                                ^^^^^^^^ has alignment of 2, which is larger than 1
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^ ---  -------- this field has non-zero size or requires alignment
+   | |                         |
+   | |                         this field has non-zero size or requires alignment
+   | needs at most one field with non-trivial size or alignment, but has 2
 
-error[E0691]: zero-sized field in transparent struct has alignment larger than 1
-  --> $DIR/repr-transparent.rs:42:24
+error[E0690]: transparent struct needs at most one field with non-trivial size or alignment, but has 2
+  --> $DIR/repr-transparent.rs:42:1
    |
 LL | struct GenericAlign<T>(ZstAlign32<T>, u32);
-   |                        ^^^^^^^^^^^^^ has alignment of 32, which is larger than 1
+   | ^^^^^^^^^^^^^^^^^^^^^^ -------------  --- this field has non-zero size or requires alignment
+   | |                      |
+   | |                      this field has non-zero size or requires alignment
+   | needs at most one field with non-trivial size or alignment, but has 2
 
 error[E0084]: unsupported representation for zero-variant enum
-  --> $DIR/repr-transparent.rs:44:1
+  --> $DIR/repr-transparent.rs:47:1
    |
 LL | #[repr(transparent)]
    | ^^^^^^^^^^^^^^^^^^^^
@@ -37,23 +43,23 @@ LL | enum Void {}
    | --------- zero-variant enum
 
 error[E0731]: transparent enum needs exactly one variant, but has 0
-  --> $DIR/repr-transparent.rs:45:1
+  --> $DIR/repr-transparent.rs:48:1
    |
 LL | enum Void {}
    | ^^^^^^^^^ needs exactly one variant, but has 0
 
-error[E0690]: the variant of a transparent enum needs at most one non-zero-sized field, but has 2
-  --> $DIR/repr-transparent.rs:58:1
+error[E0690]: the variant of a transparent enum needs at most one field with non-trivial size or alignment, but has 2
+  --> $DIR/repr-transparent.rs:61:1
    |
 LL | enum TooManyFieldsEnum {
-   | ^^^^^^^^^^^^^^^^^^^^^^ needs at most one non-zero-sized field, but has 2
+   | ^^^^^^^^^^^^^^^^^^^^^^ needs at most one field with non-trivial size or alignment, but has 2
 LL |     Foo(u32, String),
-   |         ---  ------ this field is non-zero-sized
+   |         ---  ------ this field has non-zero size or requires alignment
    |         |
-   |         this field is non-zero-sized
+   |         this field has non-zero size or requires alignment
 
 error[E0731]: transparent enum needs exactly one variant, but has 2
-  --> $DIR/repr-transparent.rs:64:1
+  --> $DIR/repr-transparent.rs:67:1
    |
 LL | enum MultipleVariants {
    | ^^^^^^^^^^^^^^^^^^^^^ needs exactly one variant, but has 2
@@ -62,29 +68,37 @@ LL |     Foo(String),
 LL |     Bar,
    |     --- too many variants in `MultipleVariants`
 
-error[E0691]: zero-sized field in transparent enum has alignment larger than 1
-  --> $DIR/repr-transparent.rs:71:14
+error[E0690]: the variant of a transparent enum needs at most one field with non-trivial size or alignment, but has 2
+  --> $DIR/repr-transparent.rs:73:1
    |
+LL | enum NontrivialAlignZstEnum {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ needs at most one field with non-trivial size or alignment, but has 2
 LL |     Foo(u32, [u16; 0]),
-   |              ^^^^^^^^ has alignment of 2, which is larger than 1
+   |         ---  -------- this field has non-zero size or requires alignment
+   |         |
+   |         this field has non-zero size or requires alignment
 
-error[E0691]: zero-sized field in transparent enum has alignment larger than 1
-  --> $DIR/repr-transparent.rs:76:11
+error[E0690]: the variant of a transparent enum needs at most one field with non-trivial size or alignment, but has 2
+  --> $DIR/repr-transparent.rs:78:1
    |
+LL | enum GenericAlignEnum<T> {
+   | ^^^^^^^^^^^^^^^^^^^^^^^^ needs at most one field with non-trivial size or alignment, but has 2
 LL |     Foo { bar: ZstAlign32<T>, baz: u32 }
-   |           ^^^^^^^^^^^^^^^^^^ has alignment of 32, which is larger than 1
+   |           ------------------  -------- this field has non-zero size or requires alignment
+   |           |
+   |           this field has non-zero size or requires alignment
 
-error[E0690]: transparent union needs at most one non-zero-sized field, but has 2
-  --> $DIR/repr-transparent.rs:85:1
+error[E0690]: transparent union needs at most one field with non-trivial size or alignment, but has 2
+  --> $DIR/repr-transparent.rs:88:1
    |
 LL | union TooManyFields {
-   | ^^^^^^^^^^^^^^^^^^^ needs at most one non-zero-sized field, but has 2
+   | ^^^^^^^^^^^^^^^^^^^ needs at most one field with non-trivial size or alignment, but has 2
 LL |     u: u32,
-   |     ------ this field is non-zero-sized
+   |     ------ this field has non-zero size or requires alignment
 LL |     s: i32
-   |     ------ this field is non-zero-sized
+   |     ------ this field has non-zero size or requires alignment
 
 error: aborting due to 11 previous errors
 
-Some errors have detailed explanations: E0084, E0690, E0691, E0731.
+Some errors have detailed explanations: E0084, E0690, E0731.
 For more information about an error, try `rustc --explain E0084`.
diff --git a/tests/ui/resolve/bad-type-env-capture.stderr b/tests/ui/resolve/bad-type-env-capture.stderr
index b6282c2d070..941b6b7a68c 100644
--- a/tests/ui/resolve/bad-type-env-capture.stderr
+++ b/tests/ui/resolve/bad-type-env-capture.stderr
@@ -1,12 +1,12 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/bad-type-env-capture.rs:2:15
    |
 LL | fn foo<T>() {
-   |        - type parameter from outer function
+   |        - type parameter from outer item
 LL |     fn bar(b: T) { }
-   |           -   ^ use of generic parameter from outer function
+   |           -   ^ use of generic parameter from outer item
    |           |
-   |           help: try using a local generic parameter instead: `<T>`
+   |           help: try introducing a local generic parameter here: `<T>`
 
 error: aborting due to previous error
 
diff --git a/tests/ui/resolve/generic-params-from-outer-item-in-const-item.default.stderr b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.default.stderr
new file mode 100644
index 00000000000..4f853829279
--- /dev/null
+++ b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.default.stderr
@@ -0,0 +1,28 @@
+error[E0401]: can't use generic parameters from outer item
+  --> $DIR/generic-params-from-outer-item-in-const-item.rs:12:20
+   |
+LL | fn outer<T: Tr>() { // outer function
+   |          - type parameter from outer item
+LL |     const K: u32 = T::C;
+   |                    ^^^^ use of generic parameter from outer item
+
+error[E0401]: can't use generic parameters from outer item
+  --> $DIR/generic-params-from-outer-item-in-const-item.rs:19:24
+   |
+LL | impl<T> Tr for T { // outer impl block
+   |      - type parameter from outer item
+LL |     const C: u32 = {
+LL |         const I: u32 = T::C;
+   |                        ^^^^ use of generic parameter from outer item
+
+error[E0401]: can't use generic parameters from outer item
+  --> $DIR/generic-params-from-outer-item-in-const-item.rs:27:20
+   |
+LL | struct S<T: Tr>(U32<{ // outer struct
+   |          - type parameter from outer item
+LL |     const _: u32 = T::C;
+   |                    ^^^^ use of generic parameter from outer item
+
+error: aborting due to 3 previous errors
+
+For more information about this error, try `rustc --explain E0401`.
diff --git a/tests/ui/resolve/generic-params-from-outer-item-in-const-item.generic_const_items.stderr b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.generic_const_items.stderr
new file mode 100644
index 00000000000..1cb55842bc6
--- /dev/null
+++ b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.generic_const_items.stderr
@@ -0,0 +1,34 @@
+error[E0401]: can't use generic parameters from outer item
+  --> $DIR/generic-params-from-outer-item-in-const-item.rs:12:20
+   |
+LL | fn outer<T: Tr>() { // outer function
+   |          - type parameter from outer item
+LL |     const K: u32 = T::C;
+   |            -       ^^^^ use of generic parameter from outer item
+   |            |
+   |            help: try introducing a local generic parameter here: `<T>`
+
+error[E0401]: can't use generic parameters from outer item
+  --> $DIR/generic-params-from-outer-item-in-const-item.rs:19:24
+   |
+LL | impl<T> Tr for T { // outer impl block
+   |      - type parameter from outer item
+LL |     const C: u32 = {
+LL |         const I: u32 = T::C;
+   |                -       ^^^^ use of generic parameter from outer item
+   |                |
+   |                help: try introducing a local generic parameter here: `<T>`
+
+error[E0401]: can't use generic parameters from outer item
+  --> $DIR/generic-params-from-outer-item-in-const-item.rs:27:20
+   |
+LL | struct S<T: Tr>(U32<{ // outer struct
+   |          - type parameter from outer item
+LL |     const _: u32 = T::C;
+   |            -       ^^^^ use of generic parameter from outer item
+   |            |
+   |            help: try introducing a local generic parameter here: `<T>`
+
+error: aborting due to 3 previous errors
+
+For more information about this error, try `rustc --explain E0401`.
diff --git a/tests/ui/resolve/generic-params-from-outer-item-in-const-item.rs b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.rs
new file mode 100644
index 00000000000..e5647d72cba
--- /dev/null
+++ b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.rs
@@ -0,0 +1,39 @@
+// Regression test for issue #115720.
+// If a const item contains generic params from an outer items, only suggest
+// turning the const item generic if the feature `generic_const_items` is enabled.
+
+// revisions: default generic_const_items
+
+#![cfg_attr(generic_const_items, feature(generic_const_items))]
+#![feature(generic_const_exprs)] // only used for the test case "outer struct"
+#![allow(incomplete_features)]
+
+fn outer<T: Tr>() { // outer function
+    const K: u32 = T::C;
+    //~^ ERROR can't use generic parameters from outer item
+    //[generic_const_items]~| HELP try introducing a local generic parameter here
+}
+
+impl<T> Tr for T { // outer impl block
+    const C: u32 = {
+        const I: u32 = T::C;
+        //~^ ERROR can't use generic parameters from outer item
+        //[generic_const_items]~| HELP try introducing a local generic parameter here
+        I
+    };
+}
+
+struct S<T: Tr>(U32<{ // outer struct
+    const _: u32 = T::C;
+    //~^ ERROR can't use generic parameters from outer item
+    //[generic_const_items]~| HELP try introducing a local generic parameter here
+    0
+}>);
+
+trait Tr {
+    const C: u32;
+}
+
+struct U32<const N: u32>;
+
+fn main() {}
diff --git a/tests/ui/resolve/issue-12796.rs b/tests/ui/resolve/issue-12796.rs
index 942d6b9a568..de3e73437f0 100644
--- a/tests/ui/resolve/issue-12796.rs
+++ b/tests/ui/resolve/issue-12796.rs
@@ -1,7 +1,7 @@
 trait Trait {
     fn outer(&self) {
         fn inner(_: &Self) {
-            //~^ ERROR can't use generic parameters from outer function
+            //~^ ERROR can't use generic parameters from outer item
         }
     }
 }
diff --git a/tests/ui/resolve/issue-12796.stderr b/tests/ui/resolve/issue-12796.stderr
index a01fd2d6542..ef59d00360b 100644
--- a/tests/ui/resolve/issue-12796.stderr
+++ b/tests/ui/resolve/issue-12796.stderr
@@ -1,10 +1,10 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-12796.rs:3:22
    |
 LL |         fn inner(_: &Self) {
    |                      ^^^^
    |                      |
-   |                      use of generic parameter from outer function
+   |                      use of generic parameter from outer item
    |                      can't use `Self` here
 
 error: aborting due to previous error
diff --git a/tests/ui/resolve/issue-3021-c.rs b/tests/ui/resolve/issue-3021-c.rs
index 94ed1fdf781..bd21d124423 100644
--- a/tests/ui/resolve/issue-3021-c.rs
+++ b/tests/ui/resolve/issue-3021-c.rs
@@ -1,8 +1,8 @@
 fn siphash<T>() {
 
     trait U {
-        fn g(&self, x: T) -> T;  //~ ERROR can't use generic parameters from outer function
-        //~^ ERROR can't use generic parameters from outer function
+        fn g(&self, x: T) -> T;  //~ ERROR can't use generic parameters from outer item
+        //~^ ERROR can't use generic parameters from outer item
     }
 }
 
diff --git a/tests/ui/resolve/issue-3021-c.stderr b/tests/ui/resolve/issue-3021-c.stderr
index 5176efc3a6b..537bbaf7b6a 100644
--- a/tests/ui/resolve/issue-3021-c.stderr
+++ b/tests/ui/resolve/issue-3021-c.stderr
@@ -1,24 +1,24 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-3021-c.rs:4:24
    |
 LL | fn siphash<T>() {
-   |            - type parameter from outer function
+   |            - type parameter from outer item
 LL |
 LL |     trait U {
-   |            - help: try using a local generic parameter instead: `<T>`
+   |            - help: try introducing a local generic parameter here: `<T>`
 LL |         fn g(&self, x: T) -> T;
-   |                        ^ use of generic parameter from outer function
+   |                        ^ use of generic parameter from outer item
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-3021-c.rs:4:30
    |
 LL | fn siphash<T>() {
-   |            - type parameter from outer function
+   |            - type parameter from outer item
 LL |
 LL |     trait U {
-   |            - help: try using a local generic parameter instead: `<T>`
+   |            - help: try introducing a local generic parameter here: `<T>`
 LL |         fn g(&self, x: T) -> T;
-   |                              ^ use of generic parameter from outer function
+   |                              ^ use of generic parameter from outer item
 
 error: aborting due to 2 previous errors
 
diff --git a/tests/ui/resolve/issue-65025-extern-static-parent-generics.rs b/tests/ui/resolve/issue-65025-extern-static-parent-generics.rs
index ce45f630e48..4fa3f12d024 100644
--- a/tests/ui/resolve/issue-65025-extern-static-parent-generics.rs
+++ b/tests/ui/resolve/issue-65025-extern-static-parent-generics.rs
@@ -1,7 +1,7 @@
 unsafe fn foo<A>() {
     extern "C" {
         static baz: *const A;
-        //~^ ERROR can't use generic parameters from outer function
+        //~^ ERROR can't use generic parameters from outer item
     }
 
     let bar: *const u64 = core::mem::transmute(&baz);
diff --git a/tests/ui/resolve/issue-65025-extern-static-parent-generics.stderr b/tests/ui/resolve/issue-65025-extern-static-parent-generics.stderr
index 6bbf76dd1fb..3e9c3fd11b7 100644
--- a/tests/ui/resolve/issue-65025-extern-static-parent-generics.stderr
+++ b/tests/ui/resolve/issue-65025-extern-static-parent-generics.stderr
@@ -1,11 +1,11 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-65025-extern-static-parent-generics.rs:3:28
    |
 LL | unsafe fn foo<A>() {
-   |               - type parameter from outer function
+   |               - type parameter from outer item
 LL |     extern "C" {
 LL |         static baz: *const A;
-   |                            ^ use of generic parameter from outer function
+   |                            ^ use of generic parameter from outer item
 
 error: aborting due to previous error
 
diff --git a/tests/ui/resolve/issue-65035-static-with-parent-generics.rs b/tests/ui/resolve/issue-65035-static-with-parent-generics.rs
index f96c04841dd..bc99584a8d2 100644
--- a/tests/ui/resolve/issue-65035-static-with-parent-generics.rs
+++ b/tests/ui/resolve/issue-65035-static-with-parent-generics.rs
@@ -1,26 +1,26 @@
 fn f<T>() {
     extern "C" {
         static a: *const T;
-        //~^ ERROR can't use generic parameters from outer function
+        //~^ ERROR can't use generic parameters from outer item
     }
 }
 
 fn g<T: Default>() {
     static a: *const T = Default::default();
-    //~^ ERROR can't use generic parameters from outer function
+    //~^ ERROR can't use generic parameters from outer item
 }
 
 fn h<const N: usize>() {
     extern "C" {
         static a: [u8; N];
-        //~^ ERROR can't use generic parameters from outer function
+        //~^ ERROR can't use generic parameters from outer item
     }
 }
 
 fn i<const N: usize>() {
     static a: [u8; N] = [0; N];
-    //~^ ERROR can't use generic parameters from outer function
-    //~| ERROR can't use generic parameters from outer function
+    //~^ ERROR can't use generic parameters from outer item
+    //~| ERROR can't use generic parameters from outer item
 }
 
 fn main() {}
diff --git a/tests/ui/resolve/issue-65035-static-with-parent-generics.stderr b/tests/ui/resolve/issue-65035-static-with-parent-generics.stderr
index 7ed572f80b8..f1fe1a6002c 100644
--- a/tests/ui/resolve/issue-65035-static-with-parent-generics.stderr
+++ b/tests/ui/resolve/issue-65035-static-with-parent-generics.stderr
@@ -1,44 +1,44 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-65035-static-with-parent-generics.rs:3:26
    |
 LL | fn f<T>() {
-   |      - type parameter from outer function
+   |      - type parameter from outer item
 LL |     extern "C" {
 LL |         static a: *const T;
-   |                          ^ use of generic parameter from outer function
+   |                          ^ use of generic parameter from outer item
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-65035-static-with-parent-generics.rs:9:22
    |
 LL | fn g<T: Default>() {
-   |      - type parameter from outer function
+   |      - type parameter from outer item
 LL |     static a: *const T = Default::default();
-   |                      ^ use of generic parameter from outer function
+   |                      ^ use of generic parameter from outer item
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-65035-static-with-parent-generics.rs:15:24
    |
 LL | fn h<const N: usize>() {
-   |            - const parameter from outer function
+   |            - const parameter from outer item
 LL |     extern "C" {
 LL |         static a: [u8; N];
-   |                        ^ use of generic parameter from outer function
+   |                        ^ use of generic parameter from outer item
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-65035-static-with-parent-generics.rs:21:20
    |
 LL | fn i<const N: usize>() {
-   |            - const parameter from outer function
+   |            - const parameter from outer item
 LL |     static a: [u8; N] = [0; N];
-   |                    ^ use of generic parameter from outer function
+   |                    ^ use of generic parameter from outer item
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/issue-65035-static-with-parent-generics.rs:21:29
    |
 LL | fn i<const N: usize>() {
-   |            - const parameter from outer function
+   |            - const parameter from outer item
 LL |     static a: [u8; N] = [0; N];
-   |                             ^ use of generic parameter from outer function
+   |                             ^ use of generic parameter from outer item
 
 error: aborting due to 5 previous errors
 
diff --git a/tests/ui/resolve/resolve-type-param-in-item-in-trait.rs b/tests/ui/resolve/resolve-type-param-in-item-in-trait.rs
index c77a66524f7..2d5f34c62a6 100644
--- a/tests/ui/resolve/resolve-type-param-in-item-in-trait.rs
+++ b/tests/ui/resolve/resolve-type-param-in-item-in-trait.rs
@@ -6,7 +6,7 @@ trait TraitA<A> {
     fn outer(&self) {
         enum Foo<B> {
             Variance(A)
-                //~^ ERROR can't use generic parameters from outer function
+                //~^ ERROR can't use generic parameters from outer item
         }
     }
 }
@@ -14,21 +14,21 @@ trait TraitA<A> {
 trait TraitB<A> {
     fn outer(&self) {
         struct Foo<B>(A);
-                //~^ ERROR can't use generic parameters from outer function
+                //~^ ERROR can't use generic parameters from outer item
     }
 }
 
 trait TraitC<A> {
     fn outer(&self) {
         struct Foo<B> { a: A }
-                //~^ ERROR can't use generic parameters from outer function
+                //~^ ERROR can't use generic parameters from outer item
     }
 }
 
 trait TraitD<A> {
     fn outer(&self) {
         fn foo<B>(a: A) { }
-                //~^ ERROR can't use generic parameters from outer function
+                //~^ ERROR can't use generic parameters from outer item
     }
 }
 
diff --git a/tests/ui/resolve/resolve-type-param-in-item-in-trait.stderr b/tests/ui/resolve/resolve-type-param-in-item-in-trait.stderr
index 0a6d1cc3bcd..1ab56fdc504 100644
--- a/tests/ui/resolve/resolve-type-param-in-item-in-trait.stderr
+++ b/tests/ui/resolve/resolve-type-param-in-item-in-trait.stderr
@@ -1,46 +1,46 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/resolve-type-param-in-item-in-trait.rs:8:22
    |
 LL | trait TraitA<A> {
-   |              - type parameter from outer function
+   |              - type parameter from outer item
 LL |     fn outer(&self) {
 LL |         enum Foo<B> {
-   |                  - help: try using a local generic parameter instead: `A,`
+   |                  - help: try introducing a local generic parameter here: `A,`
 LL |             Variance(A)
-   |                      ^ use of generic parameter from outer function
+   |                      ^ use of generic parameter from outer item
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/resolve-type-param-in-item-in-trait.rs:16:23
    |
 LL | trait TraitB<A> {
-   |              - type parameter from outer function
+   |              - type parameter from outer item
 LL |     fn outer(&self) {
 LL |         struct Foo<B>(A);
-   |                    -  ^ use of generic parameter from outer function
+   |                    -  ^ use of generic parameter from outer item
    |                    |
-   |                    help: try using a local generic parameter instead: `A,`
+   |                    help: try introducing a local generic parameter here: `A,`
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/resolve-type-param-in-item-in-trait.rs:23:28
    |
 LL | trait TraitC<A> {
-   |              - type parameter from outer function
+   |              - type parameter from outer item
 LL |     fn outer(&self) {
 LL |         struct Foo<B> { a: A }
-   |                    -       ^ use of generic parameter from outer function
+   |                    -       ^ use of generic parameter from outer item
    |                    |
-   |                    help: try using a local generic parameter instead: `A,`
+   |                    help: try introducing a local generic parameter here: `A,`
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/resolve-type-param-in-item-in-trait.rs:30:22
    |
 LL | trait TraitD<A> {
-   |              - type parameter from outer function
+   |              - type parameter from outer item
 LL |     fn outer(&self) {
 LL |         fn foo<B>(a: A) { }
-   |                -     ^ use of generic parameter from outer function
+   |                -     ^ use of generic parameter from outer item
    |                |
-   |                help: try using a local generic parameter instead: `A,`
+   |                help: try introducing a local generic parameter here: `A,`
 
 error: aborting due to 4 previous errors
 
diff --git a/tests/ui/resolve/use-self-in-inner-fn.rs b/tests/ui/resolve/use-self-in-inner-fn.rs
index eccb315feb1..f4dfa4c40ab 100644
--- a/tests/ui/resolve/use-self-in-inner-fn.rs
+++ b/tests/ui/resolve/use-self-in-inner-fn.rs
@@ -4,9 +4,9 @@ impl A {
 //~^ NOTE `Self` type implicitly declared here, by this `impl`
     fn banana(&mut self) {
         fn peach(this: &Self) {
-        //~^ ERROR can't use generic parameters from outer function
-        //~| NOTE use of generic parameter from outer function
-        //~| NOTE use a type here instead
+        //~^ ERROR can't use generic parameters from outer item
+        //~| NOTE use of generic parameter from outer item
+        //~| NOTE refer to the type directly here instead
         }
     }
 }
diff --git a/tests/ui/resolve/use-self-in-inner-fn.stderr b/tests/ui/resolve/use-self-in-inner-fn.stderr
index 96609349924..832aaacaf49 100644
--- a/tests/ui/resolve/use-self-in-inner-fn.stderr
+++ b/tests/ui/resolve/use-self-in-inner-fn.stderr
@@ -1,4 +1,4 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/use-self-in-inner-fn.rs:6:25
    |
 LL | impl A {
@@ -7,8 +7,8 @@ LL | impl A {
 LL |         fn peach(this: &Self) {
    |                         ^^^^
    |                         |
-   |                         use of generic parameter from outer function
-   |                         use a type here instead
+   |                         use of generic parameter from outer item
+   |                         refer to the type directly here instead
 
 error: aborting due to previous error
 
diff --git a/tests/ui/rfcs/rfc-2294-if-let-guard/const-expr.rs b/tests/ui/rfcs/rfc-2294-if-let-guard/const-expr.rs
new file mode 100644
index 00000000000..5c42c0d8bec
--- /dev/null
+++ b/tests/ui/rfcs/rfc-2294-if-let-guard/const-expr.rs
@@ -0,0 +1,26 @@
+// Ensure if let guards can be used in constant expressions.
+// build-pass
+
+#![feature(if_let_guard)]
+
+const fn match_if_let(x: Option<i32>, y: Option<i32>) -> i32 {
+    match x {
+        None if let Some(a @ 5) = y => a,
+        Some(z) if let (Some(_), 12) = (y, z) => 2,
+        _ => 3,
+    }
+}
+
+const ASSERTS: usize = {
+    assert!(match_if_let(None, Some(5)) == 5);
+    assert!(match_if_let(Some(12), Some(3)) == 2);
+    assert!(match_if_let(None, Some(4)) == 3);
+    assert!(match_if_let(Some(11), Some(3)) == 3);
+    assert!(match_if_let(Some(12), None) == 3);
+    assert!(match_if_let(None, None) == 3);
+    0
+};
+
+fn main() {
+    let _: [(); ASSERTS];
+}
diff --git a/tests/ui/rfcs/rfc-2294-if-let-guard/feature-gate.rs b/tests/ui/rfcs/rfc-2294-if-let-guard/feature-gate.rs
index 3beb20f0a37..b8c0eb3e6d6 100644
--- a/tests/ui/rfcs/rfc-2294-if-let-guard/feature-gate.rs
+++ b/tests/ui/rfcs/rfc-2294-if-let-guard/feature-gate.rs
@@ -8,14 +8,10 @@ fn _if_let_guard() {
         //~^ ERROR `if let` guards are experimental
 
         () if (let 0 = 1) => {}
-        //~^ ERROR `let` expressions in this position are unstable
-        //~| ERROR expected expression, found `let` statement
-        //~| ERROR `let` expressions are not supported here
+        //~^ ERROR expected expression, found `let` statement
 
         () if (((let 0 = 1))) => {}
-        //~^ ERROR `let` expressions in this position are unstable
-        //~| ERROR expected expression, found `let` statement
-        //~| ERROR `let` expressions are not supported here
+        //~^ ERROR expected expression, found `let` statement
 
         () if true && let 0 = 1 => {}
         //~^ ERROR `if let` guards are experimental
@@ -26,36 +22,22 @@ fn _if_let_guard() {
         //~| ERROR `let` expressions in this position are unstable
 
         () if (let 0 = 1) && true => {}
-        //~^ ERROR `let` expressions in this position are unstable
-        //~| ERROR expected expression, found `let` statement
-        //~| ERROR `let` expressions are not supported here
+        //~^ ERROR expected expression, found `let` statement
 
         () if true && (let 0 = 1) => {}
-        //~^ ERROR `let` expressions in this position are unstable
-        //~| ERROR expected expression, found `let` statement
-        //~| ERROR `let` expressions are not supported here
+        //~^ ERROR expected expression, found `let` statement
 
         () if (let 0 = 1) && (let 0 = 1) => {}
-        //~^ ERROR `let` expressions in this position are unstable
-        //~| ERROR `let` expressions in this position are unstable
+        //~^ ERROR expected expression, found `let` statement
         //~| ERROR expected expression, found `let` statement
-        //~| ERROR expected expression, found `let` statement
-        //~| ERROR `let` expressions are not supported here
-        //~| ERROR `let` expressions are not supported here
 
         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
         //~^ ERROR `if let` guards are experimental
         //~| ERROR `let` expressions in this position are unstable
         //~| ERROR `let` expressions in this position are unstable
-        //~| ERROR `let` expressions in this position are unstable
-        //~| ERROR `let` expressions in this position are unstable
-        //~| ERROR `let` expressions in this position are unstable
         //~| ERROR expected expression, found `let` statement
         //~| ERROR expected expression, found `let` statement
         //~| ERROR expected expression, found `let` statement
-        //~| ERROR `let` expressions are not supported here
-        //~| ERROR `let` expressions are not supported here
-        //~| ERROR `let` expressions are not supported here
 
 
         () if let Range { start: _, end: _ } = (true..true) && false => {}
@@ -76,13 +58,9 @@ fn _macros() {
         }
     }
     use_expr!((let 0 = 1 && 0 == 0));
-    //~^ ERROR `let` expressions in this position are unstable
-    //~| ERROR expected expression, found `let` statement
-    //~| ERROR `let` expressions are not supported here
+    //~^ ERROR expected expression, found `let` statement
     use_expr!((let 0 = 1));
-    //~^ ERROR `let` expressions in this position are unstable
-    //~| ERROR expected expression, found `let` statement
-    //~| ERROR `let` expressions are not supported here
+    //~^ ERROR expected expression, found `let` statement
     match () {
         #[cfg(FALSE)]
         () if let 0 = 1 => {}
diff --git a/tests/ui/rfcs/rfc-2294-if-let-guard/feature-gate.stderr b/tests/ui/rfcs/rfc-2294-if-let-guard/feature-gate.stderr
index dc182ce464a..62534b555b2 100644
--- a/tests/ui/rfcs/rfc-2294-if-let-guard/feature-gate.stderr
+++ b/tests/ui/rfcs/rfc-2294-if-let-guard/feature-gate.stderr
@@ -2,87 +2,6 @@ error: expected expression, found `let` statement
   --> $DIR/feature-gate.rs:10:16
    |
 LL |         () if (let 0 = 1) => {}
-   |                ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/feature-gate.rs:15:18
-   |
-LL |         () if (((let 0 = 1))) => {}
-   |                  ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/feature-gate.rs:28:16
-   |
-LL |         () if (let 0 = 1) && true => {}
-   |                ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/feature-gate.rs:33:24
-   |
-LL |         () if true && (let 0 = 1) => {}
-   |                        ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/feature-gate.rs:38:16
-   |
-LL |         () if (let 0 = 1) && (let 0 = 1) => {}
-   |                ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/feature-gate.rs:38:31
-   |
-LL |         () if (let 0 = 1) && (let 0 = 1) => {}
-   |                               ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/feature-gate.rs:46:42
-   |
-LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
-   |                                          ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/feature-gate.rs:46:55
-   |
-LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
-   |                                                       ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/feature-gate.rs:46:68
-   |
-LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
-   |                                                                    ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/feature-gate.rs:78:16
-   |
-LL |     use_expr!((let 0 = 1 && 0 == 0));
-   |                ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/feature-gate.rs:82:16
-   |
-LL |     use_expr!((let 0 = 1));
-   |                ^^^
-
-error: no rules expected the token `let`
-  --> $DIR/feature-gate.rs:92:15
-   |
-LL |     macro_rules! use_expr {
-   |     --------------------- when calling this macro
-...
-LL |     use_expr!(let 0 = 1);
-   |               ^^^ no rules expected this token in macro call
-   |
-note: while trying to match meta-variable `$e:expr`
-  --> $DIR/feature-gate.rs:71:10
-   |
-LL |         ($e:expr) => {
-   |          ^^^^^^^
-
-error: `let` expressions are not supported here
-  --> $DIR/feature-gate.rs:10:16
-   |
-LL |         () if (let 0 = 1) => {}
    |                ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
@@ -92,135 +11,140 @@ note: `let`s wrapped in parentheses are not supported in a context with let chai
 LL |         () if (let 0 = 1) => {}
    |                ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/feature-gate.rs:15:18
+error: expected expression, found `let` statement
+  --> $DIR/feature-gate.rs:13:18
    |
 LL |         () if (((let 0 = 1))) => {}
    |                  ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/feature-gate.rs:15:18
+  --> $DIR/feature-gate.rs:13:18
    |
 LL |         () if (((let 0 = 1))) => {}
    |                  ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/feature-gate.rs:28:16
+error: expected expression, found `let` statement
+  --> $DIR/feature-gate.rs:24:16
    |
 LL |         () if (let 0 = 1) && true => {}
    |                ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/feature-gate.rs:28:16
+  --> $DIR/feature-gate.rs:24:16
    |
 LL |         () if (let 0 = 1) && true => {}
    |                ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/feature-gate.rs:33:24
+error: expected expression, found `let` statement
+  --> $DIR/feature-gate.rs:27:24
    |
 LL |         () if true && (let 0 = 1) => {}
    |                        ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/feature-gate.rs:33:24
+  --> $DIR/feature-gate.rs:27:24
    |
 LL |         () if true && (let 0 = 1) => {}
    |                        ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/feature-gate.rs:38:16
+error: expected expression, found `let` statement
+  --> $DIR/feature-gate.rs:30:16
    |
 LL |         () if (let 0 = 1) && (let 0 = 1) => {}
    |                ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/feature-gate.rs:38:16
+  --> $DIR/feature-gate.rs:30:16
    |
 LL |         () if (let 0 = 1) && (let 0 = 1) => {}
    |                ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/feature-gate.rs:38:31
+error: expected expression, found `let` statement
+  --> $DIR/feature-gate.rs:30:31
    |
 LL |         () if (let 0 = 1) && (let 0 = 1) => {}
    |                               ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/feature-gate.rs:38:31
+  --> $DIR/feature-gate.rs:30:31
    |
 LL |         () if (let 0 = 1) && (let 0 = 1) => {}
    |                               ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/feature-gate.rs:46:42
+error: expected expression, found `let` statement
+  --> $DIR/feature-gate.rs:34:42
    |
 LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
    |                                          ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/feature-gate.rs:46:42
+  --> $DIR/feature-gate.rs:34:42
    |
 LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
    |                                          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/feature-gate.rs:46:55
+error: expected expression, found `let` statement
+  --> $DIR/feature-gate.rs:34:55
    |
 LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
    |                                                       ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/feature-gate.rs:46:42
+  --> $DIR/feature-gate.rs:34:42
    |
 LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
    |                                          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/feature-gate.rs:46:68
+error: expected expression, found `let` statement
+  --> $DIR/feature-gate.rs:34:68
    |
 LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
    |                                                                    ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/feature-gate.rs:46:42
+  --> $DIR/feature-gate.rs:34:42
    |
 LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
    |                                          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/feature-gate.rs:78:16
+error: expected expression, found `let` statement
+  --> $DIR/feature-gate.rs:60:16
    |
 LL |     use_expr!((let 0 = 1 && 0 == 0));
-   |                ^^^^^^^^^
+   |                ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/feature-gate.rs:78:16
-   |
-LL |     use_expr!((let 0 = 1 && 0 == 0));
-   |                ^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/feature-gate.rs:82:16
+error: expected expression, found `let` statement
+  --> $DIR/feature-gate.rs:62:16
    |
 LL |     use_expr!((let 0 = 1));
-   |                ^^^^^^^^^
+   |                ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/feature-gate.rs:82:16
+
+error: no rules expected the token `let`
+  --> $DIR/feature-gate.rs:70:15
    |
-LL |     use_expr!((let 0 = 1));
-   |                ^^^^^^^^^
+LL |     macro_rules! use_expr {
+   |     --------------------- when calling this macro
+...
+LL |     use_expr!(let 0 = 1);
+   |               ^^^ no rules expected this token in macro call
+   |
+note: while trying to match meta-variable `$e:expr`
+  --> $DIR/feature-gate.rs:53:10
+   |
+LL |         ($e:expr) => {
+   |          ^^^^^^^
 
 error[E0658]: `if let` guards are experimental
   --> $DIR/feature-gate.rs:7:12
@@ -233,7 +157,7 @@ LL |         () if let 0 = 1 => {}
    = help: you can write `if matches!(<expr>, <pattern>)` instead of `if let <pattern> = <expr>`
 
 error[E0658]: `if let` guards are experimental
-  --> $DIR/feature-gate.rs:20:12
+  --> $DIR/feature-gate.rs:16:12
    |
 LL |         () if true && let 0 = 1 => {}
    |            ^^^^^^^^^^^^^^^^^^^^
@@ -243,7 +167,7 @@ LL |         () if true && let 0 = 1 => {}
    = help: you can write `if matches!(<expr>, <pattern>)` instead of `if let <pattern> = <expr>`
 
 error[E0658]: `if let` guards are experimental
-  --> $DIR/feature-gate.rs:24:12
+  --> $DIR/feature-gate.rs:20:12
    |
 LL |         () if let 0 = 1 && true => {}
    |            ^^^^^^^^^^^^^^^^^^^^
@@ -253,7 +177,7 @@ LL |         () if let 0 = 1 && true => {}
    = help: you can write `if matches!(<expr>, <pattern>)` instead of `if let <pattern> = <expr>`
 
 error[E0658]: `if let` guards are experimental
-  --> $DIR/feature-gate.rs:46:12
+  --> $DIR/feature-gate.rs:34:12
    |
 LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
    |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -263,7 +187,7 @@ LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 =
    = help: you can write `if matches!(<expr>, <pattern>)` instead of `if let <pattern> = <expr>`
 
 error[E0658]: `if let` guards are experimental
-  --> $DIR/feature-gate.rs:61:12
+  --> $DIR/feature-gate.rs:43:12
    |
 LL |         () if let Range { start: _, end: _ } = (true..true) && false => {}
    |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -273,7 +197,7 @@ LL |         () if let Range { start: _, end: _ } = (true..true) && false => {}
    = help: you can write `if matches!(<expr>, <pattern>)` instead of `if let <pattern> = <expr>`
 
 error[E0658]: `if let` guards are experimental
-  --> $DIR/feature-gate.rs:88:12
+  --> $DIR/feature-gate.rs:66:12
    |
 LL |         () if let 0 = 1 => {}
    |            ^^^^^^^^^^^^
@@ -283,25 +207,7 @@ LL |         () if let 0 = 1 => {}
    = help: you can write `if matches!(<expr>, <pattern>)` instead of `if let <pattern> = <expr>`
 
 error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:10:16
-   |
-LL |         () if (let 0 = 1) => {}
-   |                ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:15:18
-   |
-LL |         () if (((let 0 = 1))) => {}
-   |                  ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:20:23
+  --> $DIR/feature-gate.rs:16:23
    |
 LL |         () if true && let 0 = 1 => {}
    |                       ^^^^^^^^^
@@ -310,7 +216,7 @@ LL |         () if true && let 0 = 1 => {}
    = help: add `#![feature(let_chains)]` to the crate attributes to enable
 
 error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:24:15
+  --> $DIR/feature-gate.rs:20:15
    |
 LL |         () if let 0 = 1 && true => {}
    |               ^^^^^^^^^
@@ -319,43 +225,7 @@ LL |         () if let 0 = 1 && true => {}
    = help: add `#![feature(let_chains)]` to the crate attributes to enable
 
 error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:28:16
-   |
-LL |         () if (let 0 = 1) && true => {}
-   |                ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:33:24
-   |
-LL |         () if true && (let 0 = 1) => {}
-   |                        ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:38:16
-   |
-LL |         () if (let 0 = 1) && (let 0 = 1) => {}
-   |                ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:38:31
-   |
-LL |         () if (let 0 = 1) && (let 0 = 1) => {}
-   |                               ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:46:15
+  --> $DIR/feature-gate.rs:34:15
    |
 LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
    |               ^^^^^^^^^
@@ -364,7 +234,7 @@ LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 =
    = help: add `#![feature(let_chains)]` to the crate attributes to enable
 
 error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:46:28
+  --> $DIR/feature-gate.rs:34:28
    |
 LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
    |                            ^^^^^^^^^
@@ -373,34 +243,7 @@ LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 =
    = help: add `#![feature(let_chains)]` to the crate attributes to enable
 
 error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:46:42
-   |
-LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
-   |                                          ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:46:55
-   |
-LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
-   |                                                       ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:46:68
-   |
-LL |         () if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) => {}
-   |                                                                    ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:61:15
+  --> $DIR/feature-gate.rs:43:15
    |
 LL |         () if let Range { start: _, end: _ } = (true..true) && false => {}
    |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -408,24 +251,6 @@ LL |         () if let Range { start: _, end: _ } = (true..true) && false => {}
    = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
    = help: add `#![feature(let_chains)]` to the crate attributes to enable
 
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:78:16
-   |
-LL |     use_expr!((let 0 = 1 && 0 == 0));
-   |                ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:82:16
-   |
-LL |     use_expr!((let 0 = 1));
-   |                ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error: aborting due to 45 previous errors
+error: aborting due to 23 previous errors
 
 For more information about this error, try `rustc --explain E0658`.
diff --git a/tests/ui/rfcs/rfc-2294-if-let-guard/macro-expanded.stderr b/tests/ui/rfcs/rfc-2294-if-let-guard/macro-expanded.stderr
index 41a20bf8ae1..00c1c303d2b 100644
--- a/tests/ui/rfcs/rfc-2294-if-let-guard/macro-expanded.stderr
+++ b/tests/ui/rfcs/rfc-2294-if-let-guard/macro-expanded.stderr
@@ -7,6 +7,7 @@ LL |     ($e:expr) => { let Some(x) = $e }
 LL |         () if m!(Some(5)) => {}
    |               ----------- in this macro invocation
    |
+   = note: only supported directly in conditions of `if` and `while` expressions
    = note: this error originates in the macro `m` (in Nightly builds, run with -Z macro-backtrace for more info)
 
 error: aborting due to previous error
diff --git a/tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let-chain.rs b/tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let-chain.rs
new file mode 100644
index 00000000000..5c333cd7795
--- /dev/null
+++ b/tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let-chain.rs
@@ -0,0 +1,97 @@
+#![feature(if_let_guard)]
+#![feature(let_chains)]
+#![allow(irrefutable_let_patterns)]
+
+fn same_pattern(c: bool) {
+    let x: Box<_> = Box::new(1);
+
+    let v = (1, 2);
+
+    match v {
+        (1, 2) if let y = x && c => (),
+        (1, 2) if let z = x => (), //~ ERROR use of moved value: `x`
+        _ => (),
+    }
+}
+
+fn same_pattern_ok(c: bool) {
+    let x: Box<_> = Box::new(1);
+
+    let v = (1, 2);
+
+    match v {
+        (1, 2) if c && let y = x => (),
+        (1, 2) if let z = x => (),
+        _ => (),
+    }
+}
+
+fn different_patterns(c: bool) {
+    let x: Box<_> = Box::new(1);
+
+    let v = (1, 2);
+
+    match v {
+        (1, _) if let y = x && c => (),
+        (_, 2) if let z = x => (), //~ ERROR use of moved value: `x`
+        _ => (),
+    }
+}
+
+fn different_patterns_ok(c: bool) {
+    let x: Box<_> = Box::new(1);
+
+    let v = (1, 2);
+
+    match v {
+        (1, _) if c && let y = x => (),
+        (_, 2) if let z = x => (),
+        _ => (),
+    }
+}
+
+fn or_pattern(c: bool) {
+    let x: Box<_> = Box::new(1);
+
+    let v = (1, 2);
+
+    match v {
+        (1, _) | (_, 2) if let y = x && c => (), //~ ERROR use of moved value: `x`
+        _ => (),
+    }
+}
+
+fn or_pattern_ok(c: bool) {
+    let x: Box<_> = Box::new(1);
+
+    let v = (1, 2);
+
+    match v {
+        (1, _) | (_, 2) if c && let y = x => (),
+        _ => (),
+    }
+}
+
+fn use_in_arm(c: bool) {
+    let x: Box<_> = Box::new(1);
+
+    let v = (1, 2);
+
+    match v {
+        (1, 2) if let y = x && c => false,
+        _ => { *x == 1 }, //~ ERROR use of moved value: `x`
+    };
+}
+
+fn use_in_arm_ok(c: bool) {
+    let x: Box<_> = Box::new(1);
+
+    let v = (1, 2);
+
+    match v {
+        (1, 2) if c && let y = x => false,
+        _ => { *x == 1 },
+    };
+}
+
+fn main() {}
diff --git a/tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let-chain.stderr b/tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let-chain.stderr
new file mode 100644
index 00000000000..d27fde58244
--- /dev/null
+++ b/tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let-chain.stderr
@@ -0,0 +1,67 @@
+error[E0382]: use of moved value: `x`
+  --> $DIR/move-guard-if-let-chain.rs:12:27
+   |
+LL |     let x: Box<_> = Box::new(1);
+   |         - move occurs because `x` has type `Box<i32>`, which does not implement the `Copy` trait
+...
+LL |         (1, 2) if let y = x && c => (),
+   |                       - value moved here
+LL |         (1, 2) if let z = x => (),
+   |                           ^ value used here after move
+   |
+help: borrow this binding in the pattern to avoid moving the value
+   |
+LL |         (1, 2) if let ref y = x && c => (),
+   |                       +++
+
+error[E0382]: use of moved value: `x`
+  --> $DIR/move-guard-if-let-chain.rs:36:27
+   |
+LL |     let x: Box<_> = Box::new(1);
+   |         - move occurs because `x` has type `Box<i32>`, which does not implement the `Copy` trait
+...
+LL |         (1, _) if let y = x && c => (),
+   |                       - value moved here
+LL |         (_, 2) if let z = x => (),
+   |                           ^ value used here after move
+   |
+help: borrow this binding in the pattern to avoid moving the value
+   |
+LL |         (1, _) if let ref y = x && c => (),
+   |                       +++
+
+error[E0382]: use of moved value: `x`
+  --> $DIR/move-guard-if-let-chain.rs:59:36
+   |
+LL |     let x: Box<_> = Box::new(1);
+   |         - move occurs because `x` has type `Box<i32>`, which does not implement the `Copy` trait
+...
+LL |         (1, _) | (_, 2) if let y = x && c => (),
+   |                                -   ^ value used here after move
+   |                                |
+   |                                value moved here
+   |
+help: borrow this binding in the pattern to avoid moving the value
+   |
+LL |         (1, _) | (_, 2) if let ref y = x && c => (),
+   |                                +++
+
+error[E0382]: use of moved value: `x`
+  --> $DIR/move-guard-if-let-chain.rs:82:16
+   |
+LL |     let x: Box<_> = Box::new(1);
+   |         - move occurs because `x` has type `Box<i32>`, which does not implement the `Copy` trait
+...
+LL |         (1, 2) if let y = x && c => false,
+   |                       - value moved here
+LL |         _ => { *x == 1 },
+   |                ^^ value used here after move
+   |
+help: borrow this binding in the pattern to avoid moving the value
+   |
+LL |         (1, 2) if let ref y = x && c => false,
+   |                       +++
+
+error: aborting due to 4 previous errors
+
+For more information about this error, try `rustc --explain E0382`.
diff --git a/tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let.rs b/tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let.rs
new file mode 100644
index 00000000000..071b86e2e14
--- /dev/null
+++ b/tests/ui/rfcs/rfc-2294-if-let-guard/move-guard-if-let.rs
@@ -0,0 +1,41 @@
+// Check that borrowck knows that moves in the pattern for if-let guards
+// only happen when the pattern is matched.
+
+// build-pass
+
+#![feature(if_let_guard)]
+#![allow(irrefutable_let_patterns)]
+
+fn same_pattern() {
+    let x: Box<_> = Box::new(1);
+
+    let v = (1, 2);
+
+    match v {
+        (1, 2) if let y = x => (),
+        (1, 2) if let z = x => (),
+        _ => (),
+    }
+}
+
+fn or_pattern() {
+    let x: Box<_> = Box::new(1);
+
+    let v = (1, 2);
+
+    match v {
+        (1, _) | (_, 2) if let y = x => (),
+        _ => (),
+    }
+}
+
+fn main() {
+    let x: Box<_> = Box::new(1);
+
+    let v = (1, 2);
+
+    match v {
+        (1, 2) if let y = x => false,
+        _ => { *x == 1 },
+    };
+}
diff --git a/tests/ui/rfcs/rfc-2294-if-let-guard/parens.rs b/tests/ui/rfcs/rfc-2294-if-let-guard/parens.rs
index 9cb27c73b14..f12824db9c0 100644
--- a/tests/ui/rfcs/rfc-2294-if-let-guard/parens.rs
+++ b/tests/ui/rfcs/rfc-2294-if-let-guard/parens.rs
@@ -19,9 +19,7 @@ fn main() {
         () if let 0 = 1 => {}
         () if (let 0 = 1) => {}
         //~^ ERROR expected expression, found `let` statement
-        //~| ERROR `let` expressions are not supported here
         () if (((let 0 = 1))) => {}
         //~^ ERROR expected expression, found `let` statement
-        //~| ERROR `let` expressions are not supported here
     }
 }
diff --git a/tests/ui/rfcs/rfc-2294-if-let-guard/parens.stderr b/tests/ui/rfcs/rfc-2294-if-let-guard/parens.stderr
index 85df360daab..0c16d9c5442 100644
--- a/tests/ui/rfcs/rfc-2294-if-let-guard/parens.stderr
+++ b/tests/ui/rfcs/rfc-2294-if-let-guard/parens.stderr
@@ -2,27 +2,29 @@ error: expected expression, found `let` statement
   --> $DIR/parens.rs:10:16
    |
 LL |         () if (let 0 = 1) => {}
-   |                ^^^
+   |                ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/parens.rs:10:16
+   |
+LL |         () if (let 0 = 1) => {}
+   |                ^^^^^^^^^
 
 error: expected expression, found `let` statement
   --> $DIR/parens.rs:12:18
    |
 LL |         () if (((let 0 = 1))) => {}
-   |                  ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/parens.rs:20:16
+   |                  ^^^^^^^^^
    |
-LL |         () if (let 0 = 1) => {}
-   |                ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/parens.rs:23:18
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/parens.rs:12:18
    |
 LL |         () if (((let 0 = 1))) => {}
-   |                  ^^^
+   |                  ^^^^^^^^^
 
-error: `let` expressions are not supported here
+error: expected expression, found `let` statement
   --> $DIR/parens.rs:20:16
    |
 LL |         () if (let 0 = 1) => {}
@@ -35,18 +37,18 @@ note: `let`s wrapped in parentheses are not supported in a context with let chai
 LL |         () if (let 0 = 1) => {}
    |                ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/parens.rs:23:18
+error: expected expression, found `let` statement
+  --> $DIR/parens.rs:22:18
    |
 LL |         () if (((let 0 = 1))) => {}
    |                  ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/parens.rs:23:18
+  --> $DIR/parens.rs:22:18
    |
 LL |         () if (((let 0 = 1))) => {}
    |                  ^^^^^^^^^
 
-error: aborting due to 6 previous errors
+error: aborting due to 4 previous errors
 
diff --git a/tests/ui/rfcs/rfc-2294-if-let-guard/type-inference.rs b/tests/ui/rfcs/rfc-2294-if-let-guard/type-inference.rs
new file mode 100644
index 00000000000..ef7a772e6c5
--- /dev/null
+++ b/tests/ui/rfcs/rfc-2294-if-let-guard/type-inference.rs
@@ -0,0 +1,16 @@
+// check-pass
+
+#![feature(if_let_guard)]
+
+struct S;
+
+fn get<T>() -> Option<T> {
+    None
+}
+
+fn main() {
+    match get() {
+        x if let Some(S) = x => {}
+        _ => {}
+    }
+}
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/ast-validate-guards.rs b/tests/ui/rfcs/rfc-2497-if-let-chains/ast-validate-guards.rs
index e6dee2a1d06..cb3be59bee0 100644
--- a/tests/ui/rfcs/rfc-2497-if-let-chains/ast-validate-guards.rs
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/ast-validate-guards.rs
@@ -3,7 +3,7 @@
 fn let_or_guard(x: Result<Option<i32>, ()>) {
     match x {
         Ok(opt) if let Some(4) = opt || false  => {}
-        //~^ ERROR `let` expressions are not supported here
+        //~^ ERROR expected expression, found `let` statement
         _ => {}
     }
 }
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/ast-validate-guards.stderr b/tests/ui/rfcs/rfc-2497-if-let-chains/ast-validate-guards.stderr
index 26850998cc4..4b85fdd5050 100644
--- a/tests/ui/rfcs/rfc-2497-if-let-chains/ast-validate-guards.stderr
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/ast-validate-guards.stderr
@@ -1,4 +1,4 @@
-error: `let` expressions are not supported here
+error: expected expression, found `let` statement
   --> $DIR/ast-validate-guards.rs:5:20
    |
 LL |         Ok(opt) if let Some(4) = opt || false  => {}
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/avoid-invalid-mir.rs b/tests/ui/rfcs/rfc-2497-if-let-chains/avoid-invalid-mir.rs
new file mode 100644
index 00000000000..530458064b2
--- /dev/null
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/avoid-invalid-mir.rs
@@ -0,0 +1,14 @@
+// Regression test for #104172
+
+const N: usize = {
+    struct U;
+    !let y = 42;
+    //~^ ERROR expected expression, found `let` statement
+    3
+};
+
+struct S {
+    x: [(); N]
+}
+
+fn main() {}
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/avoid-invalid-mir.stderr b/tests/ui/rfcs/rfc-2497-if-let-chains/avoid-invalid-mir.stderr
new file mode 100644
index 00000000000..3eaccde3b74
--- /dev/null
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/avoid-invalid-mir.stderr
@@ -0,0 +1,10 @@
+error: expected expression, found `let` statement
+  --> $DIR/avoid-invalid-mir.rs:5:6
+   |
+LL |     !let y = 42;
+   |      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: aborting due to previous error
+
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions-without-feature-gate.rs b/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions-without-feature-gate.rs
new file mode 100644
index 00000000000..096036bb133
--- /dev/null
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions-without-feature-gate.rs
@@ -0,0 +1,340 @@
+// Check that we don't suggest enabling a feature for code that's
+// not accepted even with that feature.
+
+#![allow(irrefutable_let_patterns)]
+
+use std::ops::Range;
+
+fn main() {}
+
+fn _if() {
+    if (let 0 = 1) {}
+    //~^ ERROR expected expression, found `let` statement
+
+    if (((let 0 = 1))) {}
+    //~^ ERROR expected expression, found `let` statement
+
+    if (let 0 = 1) && true {}
+    //~^ ERROR expected expression, found `let` statement
+
+    if true && (let 0 = 1) {}
+    //~^ ERROR expected expression, found `let` statement
+
+    if (let 0 = 1) && (let 0 = 1) {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR expected expression, found `let` statement
+
+    if (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR expected expression, found `let` statement
+    //~| ERROR expected expression, found `let` statement
+}
+
+fn _while() {
+    while (let 0 = 1) {}
+    //~^ ERROR expected expression, found `let` statement
+
+    while (((let 0 = 1))) {}
+    //~^ ERROR expected expression, found `let` statement
+
+    while (let 0 = 1) && true {}
+    //~^ ERROR expected expression, found `let` statement
+
+    while true && (let 0 = 1) {}
+    //~^ ERROR expected expression, found `let` statement
+
+    while (let 0 = 1) && (let 0 = 1) {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR expected expression, found `let` statement
+
+    while (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR expected expression, found `let` statement
+    //~| ERROR expected expression, found `let` statement
+}
+
+fn _macros() {
+    macro_rules! use_expr {
+        ($e:expr) => {
+            if $e {}
+            while $e {}
+        }
+    }
+    use_expr!((let 0 = 1 && 0 == 0));
+    //~^ ERROR expected expression, found `let` statement
+    use_expr!((let 0 = 1));
+    //~^ ERROR expected expression, found `let` statement
+}
+
+fn nested_within_if_expr() {
+    if &let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+
+    if !let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+    if *let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+    if -let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+
+    fn _check_try_binds_tighter() -> Result<(), ()> {
+        if let 0 = 0? {}
+        //~^ ERROR the `?` operator can only be applied to values that implement `Try`
+        Ok(())
+    }
+    if (let 0 = 0)? {}
+    //~^ ERROR expected expression, found `let` statement
+
+    if true || let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+    if (true || let 0 = 0) {}
+    //~^ ERROR expected expression, found `let` statement
+    if true && (true || let 0 = 0) {}
+    //~^ ERROR expected expression, found `let` statement
+    if true || (true && let 0 = 0) {}
+    //~^ ERROR expected expression, found `let` statement
+
+    let mut x = true;
+    if x = let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+
+    if true..(let 0 = 0) {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR mismatched types
+    if ..(let 0 = 0) {}
+    //~^ ERROR expected expression, found `let` statement
+    if (let 0 = 0).. {}
+    //~^ ERROR expected expression, found `let` statement
+
+    // Binds as `(let ... = true)..true &&/|| false`.
+    if let Range { start: _, end: _ } = true..true && false {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR mismatched types
+    if let Range { start: _, end: _ } = true..true || false {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR mismatched types
+
+    // Binds as `(let Range { start: F, end } = F)..(|| true)`.
+    const F: fn() -> bool = || true;
+    if let Range { start: F, end } = F..|| true {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR mismatched types
+
+    // Binds as `(let Range { start: true, end } = t)..(&&false)`.
+    let t = &&true;
+    if let Range { start: true, end } = t..&&false {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR mismatched types
+
+    if let true = let true = true {}
+    //~^ ERROR expected expression, found `let` statement
+}
+
+fn nested_within_while_expr() {
+    while &let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+
+    while !let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+    while *let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+    while -let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+
+    fn _check_try_binds_tighter() -> Result<(), ()> {
+        while let 0 = 0? {}
+        //~^ ERROR the `?` operator can only be applied to values that implement `Try`
+        Ok(())
+    }
+    while (let 0 = 0)? {}
+    //~^ ERROR expected expression, found `let` statement
+
+    while true || let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+    while (true || let 0 = 0) {}
+    //~^ ERROR expected expression, found `let` statement
+    while true && (true || let 0 = 0) {}
+    //~^ ERROR expected expression, found `let` statement
+    while true || (true && let 0 = 0) {}
+    //~^ ERROR expected expression, found `let` statement
+
+    let mut x = true;
+    while x = let 0 = 0 {}
+    //~^ ERROR expected expression, found `let` statement
+
+    while true..(let 0 = 0) {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR mismatched types
+    while ..(let 0 = 0) {}
+    //~^ ERROR expected expression, found `let` statement
+    while (let 0 = 0).. {}
+    //~^ ERROR expected expression, found `let` statement
+
+    // Binds as `(let ... = true)..true &&/|| false`.
+    while let Range { start: _, end: _ } = true..true && false {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR mismatched types
+    while let Range { start: _, end: _ } = true..true || false {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR mismatched types
+
+    // Binds as `(let Range { start: F, end } = F)..(|| true)`.
+    const F: fn() -> bool = || true;
+    while let Range { start: F, end } = F..|| true {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR mismatched types
+
+    // Binds as `(let Range { start: true, end } = t)..(&&false)`.
+    let t = &&true;
+    while let Range { start: true, end } = t..&&false {}
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR mismatched types
+
+    while let true = let true = true {}
+    //~^ ERROR expected expression, found `let` statement
+}
+
+fn not_error_because_clarified_intent() {
+    if let Range { start: _, end: _ } = (true..true || false) { }
+
+    if let Range { start: _, end: _ } = (true..true && false) { }
+
+    while let Range { start: _, end: _ } = (true..true || false) { }
+
+    while let Range { start: _, end: _ } = (true..true && false) { }
+}
+
+fn outside_if_and_while_expr() {
+    &let 0 = 0;
+    //~^ ERROR expected expression, found `let` statement
+
+    !let 0 = 0;
+    //~^ ERROR expected expression, found `let` statement
+    *let 0 = 0;
+    //~^ ERROR expected expression, found `let` statement
+    -let 0 = 0;
+    //~^ ERROR expected expression, found `let` statement
+    let _ = let _ = 3;
+    //~^ ERROR expected expression, found `let` statement
+
+    fn _check_try_binds_tighter() -> Result<(), ()> {
+        let 0 = 0?;
+        //~^ ERROR the `?` operator can only be applied to values that implement `Try`
+        Ok(())
+    }
+    (let 0 = 0)?;
+    //~^ ERROR expected expression, found `let` statement
+
+    true || let 0 = 0;
+    //~^ ERROR expected expression, found `let` statement
+    (true || let 0 = 0);
+    //~^ ERROR expected expression, found `let` statement
+    true && (true || let 0 = 0);
+    //~^ ERROR expected expression, found `let` statement
+
+    let mut x = true;
+    x = let 0 = 0;
+    //~^ ERROR expected expression, found `let` statement
+
+    true..(let 0 = 0);
+    //~^ ERROR expected expression, found `let` statement
+    ..(let 0 = 0);
+    //~^ ERROR expected expression, found `let` statement
+    (let 0 = 0)..;
+    //~^ ERROR expected expression, found `let` statement
+
+    (let Range { start: _, end: _ } = true..true || false);
+    //~^ ERROR mismatched types
+    //~| ERROR expected expression, found `let` statement
+
+    (let true = let true = true);
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR expected expression, found `let` statement
+
+    {
+        #[cfg(FALSE)]
+        let x = true && let y = 1;
+        //~^ ERROR expected expression, found `let` statement
+    }
+
+    #[cfg(FALSE)]
+    {
+        [1, 2, 3][let _ = ()]
+        //~^ ERROR expected expression, found `let` statement
+    }
+
+    // Check function tail position.
+    &let 0 = 0
+    //~^ ERROR expected expression, found `let` statement
+}
+
+// Let's make sure that `let` inside const generic arguments are considered.
+fn inside_const_generic_arguments() {
+    struct A<const B: bool>;
+    impl<const B: bool> A<{B}> { const O: u32 = 5; }
+
+    if let A::<{
+        true && let 1 = 1
+        //~^ ERROR expected expression, found `let` statement
+    }>::O = 5 {}
+
+    while let A::<{
+        true && let 1 = 1
+        //~^ ERROR expected expression, found `let` statement
+    }>::O = 5 {}
+
+    if A::<{
+        true && let 1 = 1
+        //~^ ERROR expected expression, found `let` statement
+    }>::O == 5 {}
+
+    // In the cases above we have `ExprKind::Block` to help us out.
+    // Below however, we would not have a block and so an implementation might go
+    // from visiting expressions to types without banning `let` expressions down the tree.
+    // This tests ensures that we are not caught by surprise should the parser
+    // admit non-IDENT expressions in const generic arguments.
+
+    if A::<
+        true && let 1 = 1
+        //~^ ERROR expressions must be enclosed in braces
+        //~| ERROR expected expression, found `let` statement
+    >::O == 5 {}
+}
+
+fn with_parenthesis() {
+    let opt = Some(Some(1i32));
+
+    if (let Some(a) = opt && true) {
+    //~^ ERROR expected expression, found `let` statement
+    }
+
+    if (let Some(a) = opt) && true {
+    //~^ ERROR expected expression, found `let` statement
+    }
+    if (let Some(a) = opt) && (let Some(b) = a) {
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR expected expression, found `let` statement
+    }
+
+    if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR expected expression, found `let` statement
+    }
+    if (let Some(a) = opt && (let Some(b) = a)) && true {
+    //~^ ERROR expected expression, found `let` statement
+    //~| ERROR expected expression, found `let` statement
+    }
+    if (let Some(a) = opt && (true)) && true {
+    //~^ ERROR expected expression, found `let` statement
+    }
+
+    #[cfg(FALSE)]
+    let x = (true && let y = 1);
+    //~^ ERROR expected expression, found `let` statement
+
+    #[cfg(FALSE)]
+    {
+        ([1, 2, 3][let _ = ()])
+        //~^ ERROR expected expression, found `let` statement
+    }
+}
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions-without-feature-gate.stderr b/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions-without-feature-gate.stderr
new file mode 100644
index 00000000000..31f389512ed
--- /dev/null
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions-without-feature-gate.stderr
@@ -0,0 +1,1021 @@
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:11:9
+   |
+LL |     if (let 0 = 1) {}
+   |         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:11:9
+   |
+LL |     if (let 0 = 1) {}
+   |         ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:14:11
+   |
+LL |     if (((let 0 = 1))) {}
+   |           ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:14:11
+   |
+LL |     if (((let 0 = 1))) {}
+   |           ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:17:9
+   |
+LL |     if (let 0 = 1) && true {}
+   |         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:17:9
+   |
+LL |     if (let 0 = 1) && true {}
+   |         ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:20:17
+   |
+LL |     if true && (let 0 = 1) {}
+   |                 ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:20:17
+   |
+LL |     if true && (let 0 = 1) {}
+   |                 ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:23:9
+   |
+LL |     if (let 0 = 1) && (let 0 = 1) {}
+   |         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:23:9
+   |
+LL |     if (let 0 = 1) && (let 0 = 1) {}
+   |         ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:23:24
+   |
+LL |     if (let 0 = 1) && (let 0 = 1) {}
+   |                        ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:23:24
+   |
+LL |     if (let 0 = 1) && (let 0 = 1) {}
+   |                        ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:27:9
+   |
+LL |     if (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:27:9
+   |
+LL |     if (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:27:22
+   |
+LL |     if (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |                      ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:27:9
+   |
+LL |     if (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:27:35
+   |
+LL |     if (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |                                   ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:27:9
+   |
+LL |     if (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:34:12
+   |
+LL |     while (let 0 = 1) {}
+   |            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:34:12
+   |
+LL |     while (let 0 = 1) {}
+   |            ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:37:14
+   |
+LL |     while (((let 0 = 1))) {}
+   |              ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:37:14
+   |
+LL |     while (((let 0 = 1))) {}
+   |              ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:40:12
+   |
+LL |     while (let 0 = 1) && true {}
+   |            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:40:12
+   |
+LL |     while (let 0 = 1) && true {}
+   |            ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:43:20
+   |
+LL |     while true && (let 0 = 1) {}
+   |                    ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:43:20
+   |
+LL |     while true && (let 0 = 1) {}
+   |                    ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:46:12
+   |
+LL |     while (let 0 = 1) && (let 0 = 1) {}
+   |            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:46:12
+   |
+LL |     while (let 0 = 1) && (let 0 = 1) {}
+   |            ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:46:27
+   |
+LL |     while (let 0 = 1) && (let 0 = 1) {}
+   |                           ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:46:27
+   |
+LL |     while (let 0 = 1) && (let 0 = 1) {}
+   |                           ^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:50:12
+   |
+LL |     while (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:50:12
+   |
+LL |     while (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:50:25
+   |
+LL |     while (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |                         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:50:12
+   |
+LL |     while (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:50:38
+   |
+LL |     while (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |                                      ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:50:12
+   |
+LL |     while (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
+   |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:70:9
+   |
+LL |     if &let 0 = 0 {}
+   |         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:73:9
+   |
+LL |     if !let 0 = 0 {}
+   |         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:75:9
+   |
+LL |     if *let 0 = 0 {}
+   |         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:77:9
+   |
+LL |     if -let 0 = 0 {}
+   |         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:85:9
+   |
+LL |     if (let 0 = 0)? {}
+   |         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:88:16
+   |
+LL |     if true || let 0 = 0 {}
+   |                ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `||` operators are not supported in let chain expressions
+  --> $DIR/disallowed-positions-without-feature-gate.rs:88:13
+   |
+LL |     if true || let 0 = 0 {}
+   |             ^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:90:17
+   |
+LL |     if (true || let 0 = 0) {}
+   |                 ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:92:25
+   |
+LL |     if true && (true || let 0 = 0) {}
+   |                         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:94:25
+   |
+LL |     if true || (true && let 0 = 0) {}
+   |                         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:98:12
+   |
+LL |     if x = let 0 = 0 {}
+   |            ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:101:15
+   |
+LL |     if true..(let 0 = 0) {}
+   |               ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:104:11
+   |
+LL |     if ..(let 0 = 0) {}
+   |           ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:106:9
+   |
+LL |     if (let 0 = 0).. {}
+   |         ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:110:8
+   |
+LL |     if let Range { start: _, end: _ } = true..true && false {}
+   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:113:8
+   |
+LL |     if let Range { start: _, end: _ } = true..true || false {}
+   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:119:8
+   |
+LL |     if let Range { start: F, end } = F..|| true {}
+   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:125:8
+   |
+LL |     if let Range { start: true, end } = t..&&false {}
+   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:129:19
+   |
+LL |     if let true = let true = true {}
+   |                   ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:134:12
+   |
+LL |     while &let 0 = 0 {}
+   |            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:137:12
+   |
+LL |     while !let 0 = 0 {}
+   |            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:139:12
+   |
+LL |     while *let 0 = 0 {}
+   |            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:141:12
+   |
+LL |     while -let 0 = 0 {}
+   |            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:149:12
+   |
+LL |     while (let 0 = 0)? {}
+   |            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:152:19
+   |
+LL |     while true || let 0 = 0 {}
+   |                   ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `||` operators are not supported in let chain expressions
+  --> $DIR/disallowed-positions-without-feature-gate.rs:152:16
+   |
+LL |     while true || let 0 = 0 {}
+   |                ^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:154:20
+   |
+LL |     while (true || let 0 = 0) {}
+   |                    ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:156:28
+   |
+LL |     while true && (true || let 0 = 0) {}
+   |                            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:158:28
+   |
+LL |     while true || (true && let 0 = 0) {}
+   |                            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:162:15
+   |
+LL |     while x = let 0 = 0 {}
+   |               ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:165:18
+   |
+LL |     while true..(let 0 = 0) {}
+   |                  ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:168:14
+   |
+LL |     while ..(let 0 = 0) {}
+   |              ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:170:12
+   |
+LL |     while (let 0 = 0).. {}
+   |            ^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:174:11
+   |
+LL |     while let Range { start: _, end: _ } = true..true && false {}
+   |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:177:11
+   |
+LL |     while let Range { start: _, end: _ } = true..true || false {}
+   |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:183:11
+   |
+LL |     while let Range { start: F, end } = F..|| true {}
+   |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:189:11
+   |
+LL |     while let Range { start: true, end } = t..&&false {}
+   |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:193:22
+   |
+LL |     while let true = let true = true {}
+   |                      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:208:6
+   |
+LL |     &let 0 = 0;
+   |      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:211:6
+   |
+LL |     !let 0 = 0;
+   |      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:213:6
+   |
+LL |     *let 0 = 0;
+   |      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:215:6
+   |
+LL |     -let 0 = 0;
+   |      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:217:13
+   |
+LL |     let _ = let _ = 3;
+   |             ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:225:6
+   |
+LL |     (let 0 = 0)?;
+   |      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:228:13
+   |
+LL |     true || let 0 = 0;
+   |             ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:230:14
+   |
+LL |     (true || let 0 = 0);
+   |              ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:232:22
+   |
+LL |     true && (true || let 0 = 0);
+   |                      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:236:9
+   |
+LL |     x = let 0 = 0;
+   |         ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:239:12
+   |
+LL |     true..(let 0 = 0);
+   |            ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:241:8
+   |
+LL |     ..(let 0 = 0);
+   |        ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:243:6
+   |
+LL |     (let 0 = 0)..;
+   |      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:246:6
+   |
+LL |     (let Range { start: _, end: _ } = true..true || false);
+   |      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:250:6
+   |
+LL |     (let true = let true = true);
+   |      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:250:17
+   |
+LL |     (let true = let true = true);
+   |                 ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:256:25
+   |
+LL |         let x = true && let y = 1;
+   |                         ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:262:19
+   |
+LL |         [1, 2, 3][let _ = ()]
+   |                   ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:267:6
+   |
+LL |     &let 0 = 0
+   |      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:277:17
+   |
+LL |         true && let 1 = 1
+   |                 ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:282:17
+   |
+LL |         true && let 1 = 1
+   |                 ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:287:17
+   |
+LL |         true && let 1 = 1
+   |                 ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:298:17
+   |
+LL |         true && let 1 = 1
+   |                 ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expressions must be enclosed in braces to be used as const generic arguments
+  --> $DIR/disallowed-positions-without-feature-gate.rs:298:9
+   |
+LL |         true && let 1 = 1
+   |         ^^^^^^^^^^^^^^^^^
+   |
+help: enclose the `const` expression in braces
+   |
+LL |         { true && let 1 = 1 }
+   |         +                   +
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:307:9
+   |
+LL |     if (let Some(a) = opt && true) {
+   |         ^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:307:9
+   |
+LL |     if (let Some(a) = opt && true) {
+   |         ^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:311:9
+   |
+LL |     if (let Some(a) = opt) && true {
+   |         ^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:311:9
+   |
+LL |     if (let Some(a) = opt) && true {
+   |         ^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:314:9
+   |
+LL |     if (let Some(a) = opt) && (let Some(b) = a) {
+   |         ^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:314:9
+   |
+LL |     if (let Some(a) = opt) && (let Some(b) = a) {
+   |         ^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:314:32
+   |
+LL |     if (let Some(a) = opt) && (let Some(b) = a) {
+   |                                ^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:314:32
+   |
+LL |     if (let Some(a) = opt) && (let Some(b) = a) {
+   |                                ^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:319:9
+   |
+LL |     if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
+   |         ^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:319:9
+   |
+LL |     if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
+   |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:319:31
+   |
+LL |     if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
+   |                               ^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:319:31
+   |
+LL |     if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
+   |                               ^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:323:9
+   |
+LL |     if (let Some(a) = opt && (let Some(b) = a)) && true {
+   |         ^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:323:9
+   |
+LL |     if (let Some(a) = opt && (let Some(b) = a)) && true {
+   |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:323:31
+   |
+LL |     if (let Some(a) = opt && (let Some(b) = a)) && true {
+   |                               ^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:323:31
+   |
+LL |     if (let Some(a) = opt && (let Some(b) = a)) && true {
+   |                               ^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:327:9
+   |
+LL |     if (let Some(a) = opt && (true)) && true {
+   |         ^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+note: `let`s wrapped in parentheses are not supported in a context with let chains
+  --> $DIR/disallowed-positions-without-feature-gate.rs:327:9
+   |
+LL |     if (let Some(a) = opt && (true)) && true {
+   |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:332:22
+   |
+LL |     let x = (true && let y = 1);
+   |                      ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:337:20
+   |
+LL |         ([1, 2, 3][let _ = ()])
+   |                    ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:63:16
+   |
+LL |     use_expr!((let 0 = 1 && 0 == 0));
+   |                ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions-without-feature-gate.rs:65:16
+   |
+LL |     use_expr!((let 0 = 1));
+   |                ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error[E0308]: mismatched types
+  --> $DIR/disallowed-positions-without-feature-gate.rs:101:8
+   |
+LL |     if true..(let 0 = 0) {}
+   |        ^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
+   |
+   = note: expected type `bool`
+            found struct `std::ops::Range<bool>`
+
+error[E0308]: mismatched types
+  --> $DIR/disallowed-positions-without-feature-gate.rs:110:12
+   |
+LL |     if let Range { start: _, end: _ } = true..true && false {}
+   |            ^^^^^^^^^^^^^^^^^^^^^^^^^^   ---- this expression has type `bool`
+   |            |
+   |            expected `bool`, found `Range<_>`
+   |
+   = note: expected type `bool`
+            found struct `std::ops::Range<_>`
+
+error[E0308]: mismatched types
+  --> $DIR/disallowed-positions-without-feature-gate.rs:113:12
+   |
+LL |     if let Range { start: _, end: _ } = true..true || false {}
+   |            ^^^^^^^^^^^^^^^^^^^^^^^^^^   ---- this expression has type `bool`
+   |            |
+   |            expected `bool`, found `Range<_>`
+   |
+   = note: expected type `bool`
+            found struct `std::ops::Range<_>`
+
+error[E0308]: mismatched types
+  --> $DIR/disallowed-positions-without-feature-gate.rs:119:12
+   |
+LL |     if let Range { start: F, end } = F..|| true {}
+   |            ^^^^^^^^^^^^^^^^^^^^^^^   - this expression has type `fn() -> bool`
+   |            |
+   |            expected fn pointer, found `Range<_>`
+   |
+   = note: expected fn pointer `fn() -> bool`
+                  found struct `std::ops::Range<_>`
+
+error[E0308]: mismatched types
+  --> $DIR/disallowed-positions-without-feature-gate.rs:125:12
+   |
+LL |     if let Range { start: true, end } = t..&&false {}
+   |            ^^^^^^^^^^^^^^^^^^^^^^^^^^   - this expression has type `&&bool`
+   |            |
+   |            expected `bool`, found `Range<_>`
+   |
+   = note: expected type `bool`
+            found struct `std::ops::Range<_>`
+
+error[E0277]: the `?` operator can only be applied to values that implement `Try`
+  --> $DIR/disallowed-positions-without-feature-gate.rs:81:20
+   |
+LL |         if let 0 = 0? {}
+   |                    ^^ the `?` operator cannot be applied to type `{integer}`
+   |
+   = help: the trait `Try` is not implemented for `{integer}`
+
+error[E0308]: mismatched types
+  --> $DIR/disallowed-positions-without-feature-gate.rs:165:11
+   |
+LL |     while true..(let 0 = 0) {}
+   |           ^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
+   |
+   = note: expected type `bool`
+            found struct `std::ops::Range<bool>`
+
+error[E0308]: mismatched types
+  --> $DIR/disallowed-positions-without-feature-gate.rs:174:15
+   |
+LL |     while let Range { start: _, end: _ } = true..true && false {}
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^   ---- this expression has type `bool`
+   |               |
+   |               expected `bool`, found `Range<_>`
+   |
+   = note: expected type `bool`
+            found struct `std::ops::Range<_>`
+
+error[E0308]: mismatched types
+  --> $DIR/disallowed-positions-without-feature-gate.rs:177:15
+   |
+LL |     while let Range { start: _, end: _ } = true..true || false {}
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^   ---- this expression has type `bool`
+   |               |
+   |               expected `bool`, found `Range<_>`
+   |
+   = note: expected type `bool`
+            found struct `std::ops::Range<_>`
+
+error[E0308]: mismatched types
+  --> $DIR/disallowed-positions-without-feature-gate.rs:183:15
+   |
+LL |     while let Range { start: F, end } = F..|| true {}
+   |               ^^^^^^^^^^^^^^^^^^^^^^^   - this expression has type `fn() -> bool`
+   |               |
+   |               expected fn pointer, found `Range<_>`
+   |
+   = note: expected fn pointer `fn() -> bool`
+                  found struct `std::ops::Range<_>`
+
+error[E0308]: mismatched types
+  --> $DIR/disallowed-positions-without-feature-gate.rs:189:15
+   |
+LL |     while let Range { start: true, end } = t..&&false {}
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^   - this expression has type `&&bool`
+   |               |
+   |               expected `bool`, found `Range<_>`
+   |
+   = note: expected type `bool`
+            found struct `std::ops::Range<_>`
+
+error[E0277]: the `?` operator can only be applied to values that implement `Try`
+  --> $DIR/disallowed-positions-without-feature-gate.rs:145:23
+   |
+LL |         while let 0 = 0? {}
+   |                       ^^ the `?` operator cannot be applied to type `{integer}`
+   |
+   = help: the trait `Try` is not implemented for `{integer}`
+
+error[E0308]: mismatched types
+  --> $DIR/disallowed-positions-without-feature-gate.rs:246:10
+   |
+LL |     (let Range { start: _, end: _ } = true..true || false);
+   |          ^^^^^^^^^^^^^^^^^^^^^^^^^^   ---- this expression has type `bool`
+   |          |
+   |          expected `bool`, found `Range<_>`
+   |
+   = note: expected type `bool`
+            found struct `std::ops::Range<_>`
+
+error[E0277]: the `?` operator can only be applied to values that implement `Try`
+  --> $DIR/disallowed-positions-without-feature-gate.rs:221:17
+   |
+LL |         let 0 = 0?;
+   |                 ^^ the `?` operator cannot be applied to type `{integer}`
+   |
+   = help: the trait `Try` is not implemented for `{integer}`
+
+error: aborting due to 105 previous errors
+
+Some errors have detailed explanations: E0277, E0308.
+For more information about an error, try `rustc --explain E0277`.
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions.rs b/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions.rs
index 2a9a5472b2e..4ac3ea53a08 100644
--- a/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions.rs
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions.rs
@@ -27,64 +27,46 @@ fn main() {}
 
 fn _if() {
     if (let 0 = 1) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     if (((let 0 = 1))) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     if (let 0 = 1) && true {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     if true && (let 0 = 1) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     if (let 0 = 1) && (let 0 = 1) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR expected expression, found `let` statement
 
     if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR `let` expressions are not supported here
-    //~| ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR expected expression, found `let` statement
     //~| ERROR expected expression, found `let` statement
 }
 
 fn _while() {
     while (let 0 = 1) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     while (((let 0 = 1))) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     while (let 0 = 1) && true {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     while true && (let 0 = 1) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     while (let 0 = 1) && (let 0 = 1) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR expected expression, found `let` statement
 
     while let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR `let` expressions are not supported here
-    //~| ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR expected expression, found `let` statement
     //~| ERROR expected expression, found `let` statement
 }
@@ -97,32 +79,21 @@ fn _macros() {
         }
     }
     use_expr!((let 0 = 1 && 0 == 0));
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     use_expr!((let 0 = 1));
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 }
 
 fn nested_within_if_expr() {
     if &let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     if !let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     if *let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR type `bool` cannot be dereferenced
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     if -let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR cannot apply unary operator `-` to type `bool`
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     fn _check_try_binds_tighter() -> Result<(), ()> {
         if let 0 = 0? {}
@@ -130,91 +101,63 @@ fn nested_within_if_expr() {
         Ok(())
     }
     if (let 0 = 0)? {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR the `?` operator can only be applied to values that implement `Try`
-    //~| ERROR the `?` operator can only be used in a function that returns `Result`
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     if true || let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     if (true || let 0 = 0) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     if true && (true || let 0 = 0) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     if true || (true && let 0 = 0) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     let mut x = true;
     if x = let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     if true..(let 0 = 0) {}
-    //~^ ERROR `let` expressions are not supported here
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR mismatched types
-    //~| ERROR expected expression, found `let` statement
     if ..(let 0 = 0) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     if (let 0 = 0).. {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     // Binds as `(let ... = true)..true &&/|| false`.
     if let Range { start: _, end: _ } = true..true && false {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR mismatched types
     if let Range { start: _, end: _ } = true..true || false {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR mismatched types
 
     // Binds as `(let Range { start: F, end } = F)..(|| true)`.
     const F: fn() -> bool = || true;
     if let Range { start: F, end } = F..|| true {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR mismatched types
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR mismatched types
 
     // Binds as `(let Range { start: true, end } = t)..(&&false)`.
     let t = &&true;
     if let Range { start: true, end } = t..&&false {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR mismatched types
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR mismatched types
 
     if let true = let true = true {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 }
 
 fn nested_within_while_expr() {
     while &let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     while !let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     while *let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR type `bool` cannot be dereferenced
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     while -let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR cannot apply unary operator `-` to type `bool`
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     fn _check_try_binds_tighter() -> Result<(), ()> {
         while let 0 = 0? {}
@@ -222,72 +165,51 @@ fn nested_within_while_expr() {
         Ok(())
     }
     while (let 0 = 0)? {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR the `?` operator can only be applied to values that implement `Try`
-    //~| ERROR the `?` operator can only be used in a function that returns `Result`
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     while true || let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     while (true || let 0 = 0) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     while true && (true || let 0 = 0) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     while true || (true && let 0 = 0) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     let mut x = true;
     while x = let 0 = 0 {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     while true..(let 0 = 0) {}
-    //~^ ERROR `let` expressions are not supported here
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR mismatched types
-    //~| ERROR expected expression, found `let` statement
     while ..(let 0 = 0) {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     while (let 0 = 0).. {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     // Binds as `(let ... = true)..true &&/|| false`.
     while let Range { start: _, end: _ } = true..true && false {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR mismatched types
     while let Range { start: _, end: _ } = true..true || false {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR mismatched types
 
     // Binds as `(let Range { start: F, end } = F)..(|| true)`.
     const F: fn() -> bool = || true;
     while let Range { start: F, end } = F..|| true {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR mismatched types
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR mismatched types
 
     // Binds as `(let Range { start: true, end } = t)..(&&false)`.
     let t = &&true;
     while let Range { start: true, end } = t..&&false {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR mismatched types
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR mismatched types
 
     while let true = let true = true {}
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 }
 
 fn not_error_because_clarified_intent() {
@@ -302,20 +224,14 @@ fn not_error_because_clarified_intent() {
 
 fn outside_if_and_while_expr() {
     &let 0 = 0;
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     !let 0 = 0;
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     *let 0 = 0;
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR type `bool` cannot be dereferenced
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     -let 0 = 0;
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR cannot apply unary operator `-` to type `bool`
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     fn _check_try_binds_tighter() -> Result<(), ()> {
         let 0 = 0?;
@@ -323,44 +239,32 @@ fn outside_if_and_while_expr() {
         Ok(())
     }
     (let 0 = 0)?;
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR the `?` operator can only be used in a function that returns `Result`
-    //~| ERROR the `?` operator can only be applied to values that implement `Try`
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     true || let 0 = 0;
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     (true || let 0 = 0);
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     true && (true || let 0 = 0);
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     let mut x = true;
     x = let 0 = 0;
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     true..(let 0 = 0);
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     ..(let 0 = 0);
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     (let 0 = 0)..;
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     (let Range { start: _, end: _ } = true..true || false);
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
+    //~^ ERROR mismatched types
     //~| ERROR expected expression, found `let` statement
 
     (let true = let true = true);
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR expected expression, found `let` statement
 
     {
@@ -377,9 +281,7 @@ fn outside_if_and_while_expr() {
 
     // Check function tail position.
     &let 0 = 0
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR mismatched types
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 }
 
 // Let's make sure that `let` inside const generic arguments are considered.
@@ -389,20 +291,17 @@ fn inside_const_generic_arguments() {
 
     if let A::<{
         true && let 1 = 1
-        //~^ ERROR `let` expressions are not supported here
-        //~| ERROR expected expression, found `let` statement
+        //~^ ERROR expected expression, found `let` statement
     }>::O = 5 {}
 
     while let A::<{
         true && let 1 = 1
-        //~^ ERROR `let` expressions are not supported here
-        //~| ERROR expected expression, found `let` statement
+        //~^ ERROR expected expression, found `let` statement
     }>::O = 5 {}
 
     if A::<{
         true && let 1 = 1
-        //~^ ERROR `let` expressions are not supported here
-        //~| ERROR expected expression, found `let` statement
+        //~^ ERROR expected expression, found `let` statement
     }>::O == 5 {}
 
     // In the cases above we have `ExprKind::Block` to help us out.
@@ -413,8 +312,7 @@ fn inside_const_generic_arguments() {
 
     if A::<
         true && let 1 = 1
-        //~^ ERROR `let` expressions are not supported here
-        //~| ERROR expressions must be enclosed in braces
+        //~^ ERROR expressions must be enclosed in braces
         //~| ERROR expected expression, found `let` statement
     >::O == 5 {}
 }
@@ -423,38 +321,29 @@ fn with_parenthesis() {
     let opt = Some(Some(1i32));
 
     if (let Some(a) = opt && true) {
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     }
 
     if (let Some(a) = opt) && true {
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     }
     if (let Some(a) = opt) && (let Some(b) = a) {
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR expected expression, found `let` statement
     }
     if let Some(a) = opt && (true && true) {
     }
 
     if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR expected expression, found `let` statement
     }
     if (let Some(a) = opt && (let Some(b) = a)) && true {
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     //~| ERROR expected expression, found `let` statement
     }
     if (let Some(a) = opt && (true)) && true {
-    //~^ ERROR `let` expressions are not supported here
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     }
 
     if (true && (true)) && let Some(a) = opt {
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions.stderr b/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions.stderr
index 81933173c25..ab58abf4d46 100644
--- a/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions.stderr
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/disallowed-positions.stderr
@@ -2,503 +2,6 @@ error: expected expression, found `let` statement
   --> $DIR/disallowed-positions.rs:29:9
    |
 LL |     if (let 0 = 1) {}
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:33:11
-   |
-LL |     if (((let 0 = 1))) {}
-   |           ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:37:9
-   |
-LL |     if (let 0 = 1) && true {}
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:41:17
-   |
-LL |     if true && (let 0 = 1) {}
-   |                 ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:45:9
-   |
-LL |     if (let 0 = 1) && (let 0 = 1) {}
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:45:24
-   |
-LL |     if (let 0 = 1) && (let 0 = 1) {}
-   |                        ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:51:35
-   |
-LL |     if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
-   |                                   ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:51:48
-   |
-LL |     if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
-   |                                                ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:51:61
-   |
-LL |     if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
-   |                                                             ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:61:12
-   |
-LL |     while (let 0 = 1) {}
-   |            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:65:14
-   |
-LL |     while (((let 0 = 1))) {}
-   |              ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:69:12
-   |
-LL |     while (let 0 = 1) && true {}
-   |            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:73:20
-   |
-LL |     while true && (let 0 = 1) {}
-   |                    ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:77:12
-   |
-LL |     while (let 0 = 1) && (let 0 = 1) {}
-   |            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:77:27
-   |
-LL |     while (let 0 = 1) && (let 0 = 1) {}
-   |                           ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:83:38
-   |
-LL |     while let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
-   |                                      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:83:51
-   |
-LL |     while let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
-   |                                                   ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:83:64
-   |
-LL |     while let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
-   |                                                                ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:110:9
-   |
-LL |     if &let 0 = 0 {}
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:115:9
-   |
-LL |     if !let 0 = 0 {}
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:118:9
-   |
-LL |     if *let 0 = 0 {}
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:122:9
-   |
-LL |     if -let 0 = 0 {}
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:132:9
-   |
-LL |     if (let 0 = 0)? {}
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:138:16
-   |
-LL |     if true || let 0 = 0 {}
-   |                ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:141:17
-   |
-LL |     if (true || let 0 = 0) {}
-   |                 ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:144:25
-   |
-LL |     if true && (true || let 0 = 0) {}
-   |                         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:147:25
-   |
-LL |     if true || (true && let 0 = 0) {}
-   |                         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:152:12
-   |
-LL |     if x = let 0 = 0 {}
-   |            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:157:15
-   |
-LL |     if true..(let 0 = 0) {}
-   |               ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:161:11
-   |
-LL |     if ..(let 0 = 0) {}
-   |           ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:165:9
-   |
-LL |     if (let 0 = 0).. {}
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:196:19
-   |
-LL |     if let true = let true = true {}
-   |                   ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:202:12
-   |
-LL |     while &let 0 = 0 {}
-   |            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:207:12
-   |
-LL |     while !let 0 = 0 {}
-   |            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:210:12
-   |
-LL |     while *let 0 = 0 {}
-   |            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:214:12
-   |
-LL |     while -let 0 = 0 {}
-   |            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:224:12
-   |
-LL |     while (let 0 = 0)? {}
-   |            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:230:19
-   |
-LL |     while true || let 0 = 0 {}
-   |                   ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:233:20
-   |
-LL |     while (true || let 0 = 0) {}
-   |                    ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:236:28
-   |
-LL |     while true && (true || let 0 = 0) {}
-   |                            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:239:28
-   |
-LL |     while true || (true && let 0 = 0) {}
-   |                            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:244:15
-   |
-LL |     while x = let 0 = 0 {}
-   |               ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:249:18
-   |
-LL |     while true..(let 0 = 0) {}
-   |                  ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:253:14
-   |
-LL |     while ..(let 0 = 0) {}
-   |              ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:257:12
-   |
-LL |     while (let 0 = 0).. {}
-   |            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:288:22
-   |
-LL |     while let true = let true = true {}
-   |                      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:304:6
-   |
-LL |     &let 0 = 0;
-   |      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:308:6
-   |
-LL |     !let 0 = 0;
-   |      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:311:6
-   |
-LL |     *let 0 = 0;
-   |      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:315:6
-   |
-LL |     -let 0 = 0;
-   |      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:325:6
-   |
-LL |     (let 0 = 0)?;
-   |      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:331:13
-   |
-LL |     true || let 0 = 0;
-   |             ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:334:14
-   |
-LL |     (true || let 0 = 0);
-   |              ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:337:22
-   |
-LL |     true && (true || let 0 = 0);
-   |                      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:342:9
-   |
-LL |     x = let 0 = 0;
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:346:12
-   |
-LL |     true..(let 0 = 0);
-   |            ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:349:8
-   |
-LL |     ..(let 0 = 0);
-   |        ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:352:6
-   |
-LL |     (let 0 = 0)..;
-   |      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:356:6
-   |
-LL |     (let Range { start: _, end: _ } = true..true || false);
-   |      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:361:6
-   |
-LL |     (let true = let true = true);
-   |      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:361:17
-   |
-LL |     (let true = let true = true);
-   |                 ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:368:25
-   |
-LL |         let x = true && let y = 1;
-   |                         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:374:19
-   |
-LL |         [1, 2, 3][let _ = ()]
-   |                   ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:379:6
-   |
-LL |     &let 0 = 0
-   |      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:391:17
-   |
-LL |         true && let 1 = 1
-   |                 ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:397:17
-   |
-LL |         true && let 1 = 1
-   |                 ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:403:17
-   |
-LL |         true && let 1 = 1
-   |                 ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:415:17
-   |
-LL |         true && let 1 = 1
-   |                 ^^^
-
-error: expressions must be enclosed in braces to be used as const generic arguments
-  --> $DIR/disallowed-positions.rs:415:9
-   |
-LL |         true && let 1 = 1
-   |         ^^^^^^^^^^^^^^^^^
-   |
-help: enclose the `const` expression in braces
-   |
-LL |         { true && let 1 = 1 }
-   |         +                   +
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:425:9
-   |
-LL |     if (let Some(a) = opt && true) {
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:430:9
-   |
-LL |     if (let Some(a) = opt) && true {
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:434:9
-   |
-LL |     if (let Some(a) = opt) && (let Some(b) = a) {
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:434:32
-   |
-LL |     if (let Some(a) = opt) && (let Some(b) = a) {
-   |                                ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:443:9
-   |
-LL |     if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:443:31
-   |
-LL |     if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
-   |                               ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:449:9
-   |
-LL |     if (let Some(a) = opt && (let Some(b) = a)) && true {
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:449:31
-   |
-LL |     if (let Some(a) = opt && (let Some(b) = a)) && true {
-   |                               ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:455:9
-   |
-LL |     if (let Some(a) = opt && (true)) && true {
-   |         ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:472:22
-   |
-LL |     let x = (true && let y = 1);
-   |                      ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:477:20
-   |
-LL |         ([1, 2, 3][let _ = ()])
-   |                    ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:99:16
-   |
-LL |     use_expr!((let 0 = 1 && 0 == 0));
-   |                ^^^
-
-error: expected expression, found `let` statement
-  --> $DIR/disallowed-positions.rs:103:16
-   |
-LL |     use_expr!((let 0 = 1));
-   |                ^^^
-
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:29:9
-   |
-LL |     if (let 0 = 1) {}
    |         ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
@@ -508,1012 +11,863 @@ note: `let`s wrapped in parentheses are not supported in a context with let chai
 LL |     if (let 0 = 1) {}
    |         ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:33:11
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:32:11
    |
 LL |     if (((let 0 = 1))) {}
    |           ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:33:11
+  --> $DIR/disallowed-positions.rs:32:11
    |
 LL |     if (((let 0 = 1))) {}
    |           ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:37:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:35:9
    |
 LL |     if (let 0 = 1) && true {}
    |         ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:37:9
+  --> $DIR/disallowed-positions.rs:35:9
    |
 LL |     if (let 0 = 1) && true {}
    |         ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:41:17
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:38:17
    |
 LL |     if true && (let 0 = 1) {}
    |                 ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:41:17
+  --> $DIR/disallowed-positions.rs:38:17
    |
 LL |     if true && (let 0 = 1) {}
    |                 ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:45:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:41:9
    |
 LL |     if (let 0 = 1) && (let 0 = 1) {}
    |         ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:45:9
+  --> $DIR/disallowed-positions.rs:41:9
    |
 LL |     if (let 0 = 1) && (let 0 = 1) {}
    |         ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:45:24
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:41:24
    |
 LL |     if (let 0 = 1) && (let 0 = 1) {}
    |                        ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:45:24
+  --> $DIR/disallowed-positions.rs:41:24
    |
 LL |     if (let 0 = 1) && (let 0 = 1) {}
    |                        ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:51:35
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:45:35
    |
 LL |     if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                   ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:51:35
+  --> $DIR/disallowed-positions.rs:45:35
    |
 LL |     if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:51:48
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:45:48
    |
 LL |     if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                                ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:51:35
+  --> $DIR/disallowed-positions.rs:45:35
    |
 LL |     if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:51:61
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:45:61
    |
 LL |     if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                                             ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:51:35
+  --> $DIR/disallowed-positions.rs:45:35
    |
 LL |     if let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:61:12
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:52:12
    |
 LL |     while (let 0 = 1) {}
    |            ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:61:12
+  --> $DIR/disallowed-positions.rs:52:12
    |
 LL |     while (let 0 = 1) {}
    |            ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:65:14
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:55:14
    |
 LL |     while (((let 0 = 1))) {}
    |              ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:65:14
+  --> $DIR/disallowed-positions.rs:55:14
    |
 LL |     while (((let 0 = 1))) {}
    |              ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:69:12
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:58:12
    |
 LL |     while (let 0 = 1) && true {}
    |            ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:69:12
+  --> $DIR/disallowed-positions.rs:58:12
    |
 LL |     while (let 0 = 1) && true {}
    |            ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:73:20
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:61:20
    |
 LL |     while true && (let 0 = 1) {}
    |                    ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:73:20
+  --> $DIR/disallowed-positions.rs:61:20
    |
 LL |     while true && (let 0 = 1) {}
    |                    ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:77:12
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:64:12
    |
 LL |     while (let 0 = 1) && (let 0 = 1) {}
    |            ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:77:12
+  --> $DIR/disallowed-positions.rs:64:12
    |
 LL |     while (let 0 = 1) && (let 0 = 1) {}
    |            ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:77:27
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:64:27
    |
 LL |     while (let 0 = 1) && (let 0 = 1) {}
    |                           ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:77:27
+  --> $DIR/disallowed-positions.rs:64:27
    |
 LL |     while (let 0 = 1) && (let 0 = 1) {}
    |                           ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:83:38
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:68:38
    |
 LL |     while let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                      ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:83:38
+  --> $DIR/disallowed-positions.rs:68:38
    |
 LL |     while let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:83:51
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:68:51
    |
 LL |     while let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                                   ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:83:38
+  --> $DIR/disallowed-positions.rs:68:38
    |
 LL |     while let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:83:64
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:68:64
    |
 LL |     while let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                                                ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:83:38
+  --> $DIR/disallowed-positions.rs:68:38
    |
 LL |     while let 0 = 1 && let 1 = 2 && (let 2 = 3 && let 3 = 4 && let 4 = 5) {}
    |                                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:99:16
-   |
-LL |     use_expr!((let 0 = 1 && 0 == 0));
-   |                ^^^^^^^^^
-   |
-   = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:99:16
-   |
-LL |     use_expr!((let 0 = 1 && 0 == 0));
-   |                ^^^^^^^^^^^^^^^^^^^
-
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:99:16
-   |
-LL |     use_expr!((let 0 = 1 && 0 == 0));
-   |                ^^^^^^^^^
-   |
-   = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:99:16
-   |
-LL |     use_expr!((let 0 = 1 && 0 == 0));
-   |                ^^^^^^^^^^^^^^^^^^^
-
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:103:16
-   |
-LL |     use_expr!((let 0 = 1));
-   |                ^^^^^^^^^
-   |
-   = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:103:16
-   |
-LL |     use_expr!((let 0 = 1));
-   |                ^^^^^^^^^
-
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:103:16
-   |
-LL |     use_expr!((let 0 = 1));
-   |                ^^^^^^^^^
-   |
-   = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:103:16
-   |
-LL |     use_expr!((let 0 = 1));
-   |                ^^^^^^^^^
-
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:110:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:88:9
    |
 LL |     if &let 0 = 0 {}
    |         ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:115:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:91:9
    |
 LL |     if !let 0 = 0 {}
    |         ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:118:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:93:9
    |
 LL |     if *let 0 = 0 {}
    |         ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:122:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:95:9
    |
 LL |     if -let 0 = 0 {}
    |         ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:132:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:103:9
    |
 LL |     if (let 0 = 0)? {}
    |         ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:132:9
-   |
-LL |     if (let 0 = 0)? {}
-   |         ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:138:16
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:106:16
    |
 LL |     if true || let 0 = 0 {}
    |                ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `||` operators are not supported in let chain expressions
-  --> $DIR/disallowed-positions.rs:138:13
+  --> $DIR/disallowed-positions.rs:106:13
    |
 LL |     if true || let 0 = 0 {}
    |             ^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:141:17
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:108:17
    |
 LL |     if (true || let 0 = 0) {}
    |                 ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `||` operators are not supported in let chain expressions
-  --> $DIR/disallowed-positions.rs:141:14
-   |
-LL |     if (true || let 0 = 0) {}
-   |              ^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:144:25
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:110:25
    |
 LL |     if true && (true || let 0 = 0) {}
    |                         ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `||` operators are not supported in let chain expressions
-  --> $DIR/disallowed-positions.rs:144:22
-   |
-LL |     if true && (true || let 0 = 0) {}
-   |                      ^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:147:25
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:112:25
    |
 LL |     if true || (true && let 0 = 0) {}
    |                         ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:147:17
-   |
-LL |     if true || (true && let 0 = 0) {}
-   |                 ^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:152:12
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:116:12
    |
 LL |     if x = let 0 = 0 {}
-   |            ^^^^^^^^^
+   |            ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:157:15
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:119:15
    |
 LL |     if true..(let 0 = 0) {}
    |               ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:157:15
-   |
-LL |     if true..(let 0 = 0) {}
-   |               ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:161:11
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:122:11
    |
 LL |     if ..(let 0 = 0) {}
    |           ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:161:11
-   |
-LL |     if ..(let 0 = 0) {}
-   |           ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:165:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:124:9
    |
 LL |     if (let 0 = 0).. {}
    |         ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:165:9
-   |
-LL |     if (let 0 = 0).. {}
-   |         ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:171:8
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:128:8
    |
 LL |     if let Range { start: _, end: _ } = true..true && false {}
    |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:175:8
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:131:8
    |
 LL |     if let Range { start: _, end: _ } = true..true || false {}
    |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:182:8
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:137:8
    |
 LL |     if let Range { start: F, end } = F..|| true {}
    |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:190:8
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:143:8
    |
 LL |     if let Range { start: true, end } = t..&&false {}
    |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:196:19
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:147:19
    |
 LL |     if let true = let true = true {}
-   |                   ^^^^^^^^^^^^^^^
+   |                   ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:202:12
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:152:12
    |
 LL |     while &let 0 = 0 {}
    |            ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:207:12
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:155:12
    |
 LL |     while !let 0 = 0 {}
    |            ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:210:12
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:157:12
    |
 LL |     while *let 0 = 0 {}
    |            ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:214:12
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:159:12
    |
 LL |     while -let 0 = 0 {}
    |            ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:224:12
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:167:12
    |
 LL |     while (let 0 = 0)? {}
    |            ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:224:12
-   |
-LL |     while (let 0 = 0)? {}
-   |            ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:230:19
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:170:19
    |
 LL |     while true || let 0 = 0 {}
    |                   ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `||` operators are not supported in let chain expressions
-  --> $DIR/disallowed-positions.rs:230:16
+  --> $DIR/disallowed-positions.rs:170:16
    |
 LL |     while true || let 0 = 0 {}
    |                ^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:233:20
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:172:20
    |
 LL |     while (true || let 0 = 0) {}
    |                    ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `||` operators are not supported in let chain expressions
-  --> $DIR/disallowed-positions.rs:233:17
-   |
-LL |     while (true || let 0 = 0) {}
-   |                 ^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:236:28
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:174:28
    |
 LL |     while true && (true || let 0 = 0) {}
    |                            ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `||` operators are not supported in let chain expressions
-  --> $DIR/disallowed-positions.rs:236:25
-   |
-LL |     while true && (true || let 0 = 0) {}
-   |                         ^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:239:28
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:176:28
    |
 LL |     while true || (true && let 0 = 0) {}
    |                            ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:239:20
-   |
-LL |     while true || (true && let 0 = 0) {}
-   |                    ^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:244:15
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:180:15
    |
 LL |     while x = let 0 = 0 {}
-   |               ^^^^^^^^^
+   |               ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:249:18
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:183:18
    |
 LL |     while true..(let 0 = 0) {}
    |                  ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:249:18
-   |
-LL |     while true..(let 0 = 0) {}
-   |                  ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:253:14
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:186:14
    |
 LL |     while ..(let 0 = 0) {}
    |              ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:253:14
-   |
-LL |     while ..(let 0 = 0) {}
-   |              ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:257:12
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:188:12
    |
 LL |     while (let 0 = 0).. {}
    |            ^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:257:12
-   |
-LL |     while (let 0 = 0).. {}
-   |            ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:263:11
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:192:11
    |
 LL |     while let Range { start: _, end: _ } = true..true && false {}
    |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:267:11
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:195:11
    |
 LL |     while let Range { start: _, end: _ } = true..true || false {}
    |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:274:11
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:201:11
    |
 LL |     while let Range { start: F, end } = F..|| true {}
    |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:282:11
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:207:11
    |
 LL |     while let Range { start: true, end } = t..&&false {}
    |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:288:22
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:211:22
    |
 LL |     while let true = let true = true {}
-   |                      ^^^^^^^^^^^^^^^
+   |                      ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:304:6
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:226:6
    |
 LL |     &let 0 = 0;
-   |      ^^^^^^^^^
+   |      ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:308:6
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:229:6
    |
 LL |     !let 0 = 0;
-   |      ^^^^^^^^^
+   |      ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:311:6
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:231:6
    |
 LL |     *let 0 = 0;
-   |      ^^^^^^^^^
+   |      ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:315:6
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:233:6
    |
 LL |     -let 0 = 0;
-   |      ^^^^^^^^^
+   |      ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:325:6
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:241:6
    |
 LL |     (let 0 = 0)?;
-   |      ^^^^^^^^^
+   |      ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:325:6
-   |
-LL |     (let 0 = 0)?;
-   |      ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:331:13
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:244:13
    |
 LL |     true || let 0 = 0;
-   |             ^^^^^^^^^
+   |             ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `||` operators are not supported in let chain expressions
-  --> $DIR/disallowed-positions.rs:331:10
-   |
-LL |     true || let 0 = 0;
-   |          ^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:334:14
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:246:14
    |
 LL |     (true || let 0 = 0);
-   |              ^^^^^^^^^
+   |              ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `||` operators are not supported in let chain expressions
-  --> $DIR/disallowed-positions.rs:334:11
-   |
-LL |     (true || let 0 = 0);
-   |           ^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:337:22
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:248:22
    |
 LL |     true && (true || let 0 = 0);
-   |                      ^^^^^^^^^
+   |                      ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `||` operators are not supported in let chain expressions
-  --> $DIR/disallowed-positions.rs:337:19
-   |
-LL |     true && (true || let 0 = 0);
-   |                   ^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:342:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:252:9
    |
 LL |     x = let 0 = 0;
-   |         ^^^^^^^^^
+   |         ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:346:12
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:255:12
    |
 LL |     true..(let 0 = 0);
-   |            ^^^^^^^^^
+   |            ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:346:12
-   |
-LL |     true..(let 0 = 0);
-   |            ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:349:8
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:257:8
    |
 LL |     ..(let 0 = 0);
-   |        ^^^^^^^^^
+   |        ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:349:8
-   |
-LL |     ..(let 0 = 0);
-   |        ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:352:6
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:259:6
    |
 LL |     (let 0 = 0)..;
-   |      ^^^^^^^^^
+   |      ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:352:6
-   |
-LL |     (let 0 = 0)..;
-   |      ^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:356:6
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:262:6
    |
 LL |     (let Range { start: _, end: _ } = true..true || false);
-   |      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |      ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:361:6
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:266:6
    |
 LL |     (let true = let true = true);
-   |      ^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |      ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
-note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:361:6
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:266:17
    |
 LL |     (let true = let true = true);
-   |      ^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |                 ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:272:25
+   |
+LL |         let x = true && let y = 1;
+   |                         ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:278:19
+   |
+LL |         [1, 2, 3][let _ = ()]
+   |                   ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:379:6
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:283:6
    |
 LL |     &let 0 = 0
-   |      ^^^^^^^^^
+   |      ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:391:17
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:293:17
    |
 LL |         true && let 1 = 1
-   |                 ^^^^^^^^^
+   |                 ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:397:17
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:298:17
    |
 LL |         true && let 1 = 1
-   |                 ^^^^^^^^^
+   |                 ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:403:17
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:303:17
    |
 LL |         true && let 1 = 1
-   |                 ^^^^^^^^^
+   |                 ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:415:17
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:314:17
    |
 LL |         true && let 1 = 1
-   |                 ^^^^^^^^^
+   |                 ^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:425:9
+error: expressions must be enclosed in braces to be used as const generic arguments
+  --> $DIR/disallowed-positions.rs:314:9
+   |
+LL |         true && let 1 = 1
+   |         ^^^^^^^^^^^^^^^^^
+   |
+help: enclose the `const` expression in braces
+   |
+LL |         { true && let 1 = 1 }
+   |         +                   +
+
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:323:9
    |
 LL |     if (let Some(a) = opt && true) {
    |         ^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:425:9
+  --> $DIR/disallowed-positions.rs:323:9
    |
 LL |     if (let Some(a) = opt && true) {
    |         ^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:430:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:327:9
    |
 LL |     if (let Some(a) = opt) && true {
    |         ^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:430:9
+  --> $DIR/disallowed-positions.rs:327:9
    |
 LL |     if (let Some(a) = opt) && true {
    |         ^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:434:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:330:9
    |
 LL |     if (let Some(a) = opt) && (let Some(b) = a) {
    |         ^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:434:9
+  --> $DIR/disallowed-positions.rs:330:9
    |
 LL |     if (let Some(a) = opt) && (let Some(b) = a) {
    |         ^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:434:32
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:330:32
    |
 LL |     if (let Some(a) = opt) && (let Some(b) = a) {
    |                                ^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:434:32
+  --> $DIR/disallowed-positions.rs:330:32
    |
 LL |     if (let Some(a) = opt) && (let Some(b) = a) {
    |                                ^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:443:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:337:9
    |
 LL |     if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
    |         ^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:443:9
+  --> $DIR/disallowed-positions.rs:337:9
    |
 LL |     if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
    |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:443:31
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:337:31
    |
 LL |     if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
    |                               ^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:443:31
+  --> $DIR/disallowed-positions.rs:337:31
    |
 LL |     if (let Some(a) = opt && (let Some(b) = a)) && b == 1 {
    |                               ^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:449:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:341:9
    |
 LL |     if (let Some(a) = opt && (let Some(b) = a)) && true {
    |         ^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:449:9
+  --> $DIR/disallowed-positions.rs:341:9
    |
 LL |     if (let Some(a) = opt && (let Some(b) = a)) && true {
    |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:449:31
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:341:31
    |
 LL |     if (let Some(a) = opt && (let Some(b) = a)) && true {
    |                               ^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:449:31
+  --> $DIR/disallowed-positions.rs:341:31
    |
 LL |     if (let Some(a) = opt && (let Some(b) = a)) && true {
    |                               ^^^^^^^^^^^^^^^
 
-error: `let` expressions are not supported here
-  --> $DIR/disallowed-positions.rs:455:9
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:345:9
    |
 LL |     if (let Some(a) = opt && (true)) && true {
    |         ^^^^^^^^^^^^^^^^^
    |
    = note: only supported directly in conditions of `if` and `while` expressions
 note: `let`s wrapped in parentheses are not supported in a context with let chains
-  --> $DIR/disallowed-positions.rs:455:9
+  --> $DIR/disallowed-positions.rs:345:9
    |
 LL |     if (let Some(a) = opt && (true)) && true {
    |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:110:8
-   |
-LL |     if &let 0 = 0 {}
-   |        ^^^^^^^^^^ expected `bool`, found `&bool`
-   |
-help: consider removing the borrow
-   |
-LL -     if &let 0 = 0 {}
-LL +     if let 0 = 0 {}
-   |
-
-error[E0614]: type `bool` cannot be dereferenced
-  --> $DIR/disallowed-positions.rs:118:8
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:361:22
    |
-LL |     if *let 0 = 0 {}
-   |        ^^^^^^^^^^
-
-error[E0600]: cannot apply unary operator `-` to type `bool`
-  --> $DIR/disallowed-positions.rs:122:8
+LL |     let x = (true && let y = 1);
+   |                      ^^^
    |
-LL |     if -let 0 = 0 {}
-   |        ^^^^^^^^^^ cannot apply unary operator `-`
+   = note: only supported directly in conditions of `if` and `while` expressions
 
-error[E0277]: the `?` operator can only be applied to values that implement `Try`
-  --> $DIR/disallowed-positions.rs:132:8
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:366:20
    |
-LL |     if (let 0 = 0)? {}
-   |        ^^^^^^^^^^^^ the `?` operator cannot be applied to type `bool`
+LL |         ([1, 2, 3][let _ = ()])
+   |                    ^^^
    |
-   = help: the trait `Try` is not implemented for `bool`
+   = note: only supported directly in conditions of `if` and `while` expressions
 
-error[E0277]: the `?` operator can only be used in a function that returns `Result` or `Option` (or another type that implements `FromResidual`)
-  --> $DIR/disallowed-positions.rs:132:19
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:81:16
    |
-LL | fn nested_within_if_expr() {
-   | -------------------------- this function should return `Result` or `Option` to accept `?`
-...
-LL |     if (let 0 = 0)? {}
-   |                   ^ cannot use the `?` operator in a function that returns `()`
+LL |     use_expr!((let 0 = 1 && 0 == 0));
+   |                ^^^
    |
-   = help: the trait `FromResidual<_>` is not implemented for `()`
+   = note: only supported directly in conditions of `if` and `while` expressions
 
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:152:8
-   |
-LL |     if x = let 0 = 0 {}
-   |        ^^^^^^^^^^^^^ expected `bool`, found `()`
+error: expected expression, found `let` statement
+  --> $DIR/disallowed-positions.rs:83:16
    |
-help: you might have meant to compare for equality
+LL |     use_expr!((let 0 = 1));
+   |                ^^^
    |
-LL |     if x == let 0 = 0 {}
-   |           +
+   = note: only supported directly in conditions of `if` and `while` expressions
 
 error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:157:8
+  --> $DIR/disallowed-positions.rs:119:8
    |
 LL |     if true..(let 0 = 0) {}
    |        ^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
@@ -1522,25 +876,7 @@ LL |     if true..(let 0 = 0) {}
             found struct `std::ops::Range<bool>`
 
 error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:161:8
-   |
-LL |     if ..(let 0 = 0) {}
-   |        ^^^^^^^^^^^^^ expected `bool`, found `RangeTo<bool>`
-   |
-   = note: expected type `bool`
-            found struct `RangeTo<bool>`
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:165:8
-   |
-LL |     if (let 0 = 0).. {}
-   |        ^^^^^^^^^^^^^ expected `bool`, found `RangeFrom<bool>`
-   |
-   = note: expected type `bool`
-            found struct `RangeFrom<bool>`
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:171:12
+  --> $DIR/disallowed-positions.rs:128:12
    |
 LL |     if let Range { start: _, end: _ } = true..true && false {}
    |            ^^^^^^^^^^^^^^^^^^^^^^^^^^   ---- this expression has type `bool`
@@ -1551,16 +887,7 @@ LL |     if let Range { start: _, end: _ } = true..true && false {}
             found struct `std::ops::Range<_>`
 
 error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:171:8
-   |
-LL |     if let Range { start: _, end: _ } = true..true && false {}
-   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
-   |
-   = note: expected type `bool`
-            found struct `std::ops::Range<bool>`
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:175:12
+  --> $DIR/disallowed-positions.rs:131:12
    |
 LL |     if let Range { start: _, end: _ } = true..true || false {}
    |            ^^^^^^^^^^^^^^^^^^^^^^^^^^   ---- this expression has type `bool`
@@ -1571,16 +898,7 @@ LL |     if let Range { start: _, end: _ } = true..true || false {}
             found struct `std::ops::Range<_>`
 
 error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:175:8
-   |
-LL |     if let Range { start: _, end: _ } = true..true || false {}
-   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
-   |
-   = note: expected type `bool`
-            found struct `std::ops::Range<bool>`
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:182:12
+  --> $DIR/disallowed-positions.rs:137:12
    |
 LL |     if let Range { start: F, end } = F..|| true {}
    |            ^^^^^^^^^^^^^^^^^^^^^^^   - this expression has type `fn() -> bool`
@@ -1591,29 +909,7 @@ LL |     if let Range { start: F, end } = F..|| true {}
                   found struct `std::ops::Range<_>`
 
 error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:182:41
-   |
-LL |     if let Range { start: F, end } = F..|| true {}
-   |                                         ^^^^^^^ expected `bool`, found closure
-   |
-   = note: expected type `bool`
-           found closure `[closure@$DIR/disallowed-positions.rs:182:41: 182:43]`
-help: use parentheses to call this closure
-   |
-LL |     if let Range { start: F, end } = F..(|| true)() {}
-   |                                         +       +++
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:182:8
-   |
-LL |     if let Range { start: F, end } = F..|| true {}
-   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
-   |
-   = note: expected type `bool`
-            found struct `std::ops::Range<bool>`
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:190:12
+  --> $DIR/disallowed-positions.rs:143:12
    |
 LL |     if let Range { start: true, end } = t..&&false {}
    |            ^^^^^^^^^^^^^^^^^^^^^^^^^^   - this expression has type `&&bool`
@@ -1623,29 +919,8 @@ LL |     if let Range { start: true, end } = t..&&false {}
    = note: expected type `bool`
             found struct `std::ops::Range<_>`
 
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:190:44
-   |
-LL |     if let Range { start: true, end } = t..&&false {}
-   |                                            ^^^^^^^ expected `bool`, found `&&bool`
-   |
-help: consider removing the `&&`
-   |
-LL -     if let Range { start: true, end } = t..&&false {}
-LL +     if let Range { start: true, end } = t..false {}
-   |
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:190:8
-   |
-LL |     if let Range { start: true, end } = t..&&false {}
-   |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
-   |
-   = note: expected type `bool`
-            found struct `std::ops::Range<bool>`
-
 error[E0277]: the `?` operator can only be applied to values that implement `Try`
-  --> $DIR/disallowed-positions.rs:128:20
+  --> $DIR/disallowed-positions.rs:99:20
    |
 LL |         if let 0 = 0? {}
    |                    ^^ the `?` operator cannot be applied to type `{integer}`
@@ -1653,61 +928,7 @@ LL |         if let 0 = 0? {}
    = help: the trait `Try` is not implemented for `{integer}`
 
 error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:202:11
-   |
-LL |     while &let 0 = 0 {}
-   |           ^^^^^^^^^^ expected `bool`, found `&bool`
-   |
-help: consider removing the borrow
-   |
-LL -     while &let 0 = 0 {}
-LL +     while let 0 = 0 {}
-   |
-
-error[E0614]: type `bool` cannot be dereferenced
-  --> $DIR/disallowed-positions.rs:210:11
-   |
-LL |     while *let 0 = 0 {}
-   |           ^^^^^^^^^^
-
-error[E0600]: cannot apply unary operator `-` to type `bool`
-  --> $DIR/disallowed-positions.rs:214:11
-   |
-LL |     while -let 0 = 0 {}
-   |           ^^^^^^^^^^ cannot apply unary operator `-`
-
-error[E0277]: the `?` operator can only be applied to values that implement `Try`
-  --> $DIR/disallowed-positions.rs:224:11
-   |
-LL |     while (let 0 = 0)? {}
-   |           ^^^^^^^^^^^^ the `?` operator cannot be applied to type `bool`
-   |
-   = help: the trait `Try` is not implemented for `bool`
-
-error[E0277]: the `?` operator can only be used in a function that returns `Result` or `Option` (or another type that implements `FromResidual`)
-  --> $DIR/disallowed-positions.rs:224:22
-   |
-LL | fn nested_within_while_expr() {
-   | ----------------------------- this function should return `Result` or `Option` to accept `?`
-...
-LL |     while (let 0 = 0)? {}
-   |                      ^ cannot use the `?` operator in a function that returns `()`
-   |
-   = help: the trait `FromResidual<_>` is not implemented for `()`
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:244:11
-   |
-LL |     while x = let 0 = 0 {}
-   |           ^^^^^^^^^^^^^ expected `bool`, found `()`
-   |
-help: you might have meant to compare for equality
-   |
-LL |     while x == let 0 = 0 {}
-   |              +
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:249:11
+  --> $DIR/disallowed-positions.rs:183:11
    |
 LL |     while true..(let 0 = 0) {}
    |           ^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
@@ -1716,25 +937,7 @@ LL |     while true..(let 0 = 0) {}
             found struct `std::ops::Range<bool>`
 
 error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:253:11
-   |
-LL |     while ..(let 0 = 0) {}
-   |           ^^^^^^^^^^^^^ expected `bool`, found `RangeTo<bool>`
-   |
-   = note: expected type `bool`
-            found struct `RangeTo<bool>`
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:257:11
-   |
-LL |     while (let 0 = 0).. {}
-   |           ^^^^^^^^^^^^^ expected `bool`, found `RangeFrom<bool>`
-   |
-   = note: expected type `bool`
-            found struct `RangeFrom<bool>`
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:263:15
+  --> $DIR/disallowed-positions.rs:192:15
    |
 LL |     while let Range { start: _, end: _ } = true..true && false {}
    |               ^^^^^^^^^^^^^^^^^^^^^^^^^^   ---- this expression has type `bool`
@@ -1745,16 +948,7 @@ LL |     while let Range { start: _, end: _ } = true..true && false {}
             found struct `std::ops::Range<_>`
 
 error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:263:11
-   |
-LL |     while let Range { start: _, end: _ } = true..true && false {}
-   |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
-   |
-   = note: expected type `bool`
-            found struct `std::ops::Range<bool>`
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:267:15
+  --> $DIR/disallowed-positions.rs:195:15
    |
 LL |     while let Range { start: _, end: _ } = true..true || false {}
    |               ^^^^^^^^^^^^^^^^^^^^^^^^^^   ---- this expression has type `bool`
@@ -1765,16 +959,7 @@ LL |     while let Range { start: _, end: _ } = true..true || false {}
             found struct `std::ops::Range<_>`
 
 error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:267:11
-   |
-LL |     while let Range { start: _, end: _ } = true..true || false {}
-   |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
-   |
-   = note: expected type `bool`
-            found struct `std::ops::Range<bool>`
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:274:15
+  --> $DIR/disallowed-positions.rs:201:15
    |
 LL |     while let Range { start: F, end } = F..|| true {}
    |               ^^^^^^^^^^^^^^^^^^^^^^^   - this expression has type `fn() -> bool`
@@ -1785,29 +970,7 @@ LL |     while let Range { start: F, end } = F..|| true {}
                   found struct `std::ops::Range<_>`
 
 error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:274:44
-   |
-LL |     while let Range { start: F, end } = F..|| true {}
-   |                                            ^^^^^^^ expected `bool`, found closure
-   |
-   = note: expected type `bool`
-           found closure `[closure@$DIR/disallowed-positions.rs:274:44: 274:46]`
-help: use parentheses to call this closure
-   |
-LL |     while let Range { start: F, end } = F..(|| true)() {}
-   |                                            +       +++
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:274:11
-   |
-LL |     while let Range { start: F, end } = F..|| true {}
-   |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
-   |
-   = note: expected type `bool`
-            found struct `std::ops::Range<bool>`
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:282:15
+  --> $DIR/disallowed-positions.rs:207:15
    |
 LL |     while let Range { start: true, end } = t..&&false {}
    |               ^^^^^^^^^^^^^^^^^^^^^^^^^^   - this expression has type `&&bool`
@@ -1817,68 +980,16 @@ LL |     while let Range { start: true, end } = t..&&false {}
    = note: expected type `bool`
             found struct `std::ops::Range<_>`
 
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:282:47
-   |
-LL |     while let Range { start: true, end } = t..&&false {}
-   |                                               ^^^^^^^ expected `bool`, found `&&bool`
-   |
-help: consider removing the `&&`
-   |
-LL -     while let Range { start: true, end } = t..&&false {}
-LL +     while let Range { start: true, end } = t..false {}
-   |
-
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:282:11
-   |
-LL |     while let Range { start: true, end } = t..&&false {}
-   |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `bool`, found `Range<bool>`
-   |
-   = note: expected type `bool`
-            found struct `std::ops::Range<bool>`
-
 error[E0277]: the `?` operator can only be applied to values that implement `Try`
-  --> $DIR/disallowed-positions.rs:220:23
+  --> $DIR/disallowed-positions.rs:163:23
    |
 LL |         while let 0 = 0? {}
    |                       ^^ the `?` operator cannot be applied to type `{integer}`
    |
    = help: the trait `Try` is not implemented for `{integer}`
 
-error[E0614]: type `bool` cannot be dereferenced
-  --> $DIR/disallowed-positions.rs:311:5
-   |
-LL |     *let 0 = 0;
-   |     ^^^^^^^^^^
-
-error[E0600]: cannot apply unary operator `-` to type `bool`
-  --> $DIR/disallowed-positions.rs:315:5
-   |
-LL |     -let 0 = 0;
-   |     ^^^^^^^^^^ cannot apply unary operator `-`
-
-error[E0277]: the `?` operator can only be applied to values that implement `Try`
-  --> $DIR/disallowed-positions.rs:325:5
-   |
-LL |     (let 0 = 0)?;
-   |     ^^^^^^^^^^^^ the `?` operator cannot be applied to type `bool`
-   |
-   = help: the trait `Try` is not implemented for `bool`
-
-error[E0277]: the `?` operator can only be used in a function that returns `Result` or `Option` (or another type that implements `FromResidual`)
-  --> $DIR/disallowed-positions.rs:325:16
-   |
-LL | fn outside_if_and_while_expr() {
-   | ------------------------------ this function should return `Result` or `Option` to accept `?`
-...
-LL |     (let 0 = 0)?;
-   |                ^ cannot use the `?` operator in a function that returns `()`
-   |
-   = help: the trait `FromResidual<_>` is not implemented for `()`
-
 error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:356:10
+  --> $DIR/disallowed-positions.rs:262:10
    |
 LL |     (let Range { start: _, end: _ } = true..true || false);
    |          ^^^^^^^^^^^^^^^^^^^^^^^^^^   ---- this expression has type `bool`
@@ -1888,24 +999,15 @@ LL |     (let Range { start: _, end: _ } = true..true || false);
    = note: expected type `bool`
             found struct `std::ops::Range<_>`
 
-error[E0308]: mismatched types
-  --> $DIR/disallowed-positions.rs:379:5
-   |
-LL | fn outside_if_and_while_expr() {
-   |                                - help: try adding a return type: `-> &bool`
-...
-LL |     &let 0 = 0
-   |     ^^^^^^^^^^ expected `()`, found `&bool`
-
 error[E0277]: the `?` operator can only be applied to values that implement `Try`
-  --> $DIR/disallowed-positions.rs:321:17
+  --> $DIR/disallowed-positions.rs:237:17
    |
 LL |         let 0 = 0?;
    |                 ^^ the `?` operator cannot be applied to type `{integer}`
    |
    = help: the trait `Try` is not implemented for `{integer}`
 
-error: aborting due to 215 previous errors
+error: aborting due to 104 previous errors
 
-Some errors have detailed explanations: E0277, E0308, E0600, E0614.
+Some errors have detailed explanations: E0277, E0308.
 For more information about an error, try `rustc --explain E0277`.
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/ensure-that-let-else-does-not-interact-with-let-chains.rs b/tests/ui/rfcs/rfc-2497-if-let-chains/ensure-that-let-else-does-not-interact-with-let-chains.rs
index 2a6c144350a..3c572054e3f 100644
--- a/tests/ui/rfcs/rfc-2497-if-let-chains/ensure-that-let-else-does-not-interact-with-let-chains.rs
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/ensure-that-let-else-does-not-interact-with-let-chains.rs
@@ -14,7 +14,6 @@ fn main() {
     };
     let Some(n) = opt && let another = n else {
     //~^ ERROR a `&&` expression cannot be directly assigned in `let...else`
-    //~| ERROR `let` expressions are not supported here
     //~| ERROR mismatched types
     //~| ERROR mismatched types
     //~| ERROR expected expression, found `let` statement
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/ensure-that-let-else-does-not-interact-with-let-chains.stderr b/tests/ui/rfcs/rfc-2497-if-let-chains/ensure-that-let-else-does-not-interact-with-let-chains.stderr
index 9bc3e754126..0442f1218b1 100644
--- a/tests/ui/rfcs/rfc-2497-if-let-chains/ensure-that-let-else-does-not-interact-with-let-chains.stderr
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/ensure-that-let-else-does-not-interact-with-let-chains.stderr
@@ -14,6 +14,8 @@ error: expected expression, found `let` statement
    |
 LL |     let Some(n) = opt && let another = n else {
    |                          ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
 
 error: a `&&` expression cannot be directly assigned in `let...else`
   --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:15:19
@@ -27,13 +29,13 @@ LL |     let Some(n) = (opt && let another = n) else {
    |                   +                      +
 
 error: this `if` expression is missing a block after the condition
-  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:24:5
+  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:23:5
    |
 LL |     if let Some(n) = opt else {
    |     ^^
    |
 help: add a block here
-  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:24:25
+  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:23:25
    |
 LL |     if let Some(n) = opt else {
    |                         ^
@@ -44,31 +46,31 @@ LL +     let Some(n) = opt else {
    |
 
 error: this `if` expression is missing a block after the condition
-  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:28:5
+  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:27:5
    |
 LL |     if let Some(n) = opt && n == 1 else {
    |     ^^
    |
 help: add a block here
-  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:28:35
+  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:27:35
    |
 LL |     if let Some(n) = opt && n == 1 else {
    |                                   ^
 
 error: this `if` expression is missing a block after the condition
-  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:32:5
+  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:31:5
    |
 LL |     if let Some(n) = opt && let another = n else {
    |     ^^
    |
 help: add a block here
-  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:32:44
+  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:31:44
    |
 LL |     if let Some(n) = opt && let another = n else {
    |                                            ^
 
 error: expected `{`, found keyword `else`
-  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:38:33
+  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:37:33
    |
 LL |         while let Some(n) = opt else {
    |         ----- ----------------- ^^^^ expected `{`
@@ -77,7 +79,7 @@ LL |         while let Some(n) = opt else {
    |         while parsing the body of this `while` expression
 
 error: expected `{`, found keyword `else`
-  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:44:43
+  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:43:43
    |
 LL |         while let Some(n) = opt && n == 1 else {
    |         ----- --------------------------- ^^^^ expected `{`
@@ -86,7 +88,7 @@ LL |         while let Some(n) = opt && n == 1 else {
    |         while parsing the body of this `while` expression
 
 error: expected `{`, found keyword `else`
-  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:50:52
+  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:49:52
    |
 LL |         while let Some(n) = opt && let another = n else {
    |         ----- ------------------------------------ ^^^^ expected `{`
@@ -94,14 +96,6 @@ LL |         while let Some(n) = opt && let another = n else {
    |         |     this `while` condition successfully parsed
    |         while parsing the body of this `while` expression
 
-error: `let` expressions are not supported here
-  --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:15:26
-   |
-LL |     let Some(n) = opt && let another = n else {
-   |                          ^^^^^^^^^^^^^^^
-   |
-   = note: only supported directly in conditions of `if` and `while` expressions
-
 error[E0308]: mismatched types
   --> $DIR/ensure-that-let-else-does-not-interact-with-let-chains.rs:9:19
    |
@@ -142,6 +136,6 @@ LL |     let Some(n) = opt && let another = n else {
    = note: expected type `bool`
               found enum `Option<_>`
 
-error: aborting due to 14 previous errors
+error: aborting due to 13 previous errors
 
 For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/feature-gate.rs b/tests/ui/rfcs/rfc-2497-if-let-chains/feature-gate.rs
index 2b407ef510c..bca7564efd8 100644
--- a/tests/ui/rfcs/rfc-2497-if-let-chains/feature-gate.rs
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/feature-gate.rs
@@ -43,8 +43,7 @@ fn _macros() {
     macro_rules! noop_expr { ($e:expr) => {}; }
 
     noop_expr!((let 0 = 1));
-    //~^ ERROR `let` expressions in this position are unstable [E0658]
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
 
     macro_rules! use_expr {
         ($e:expr) => {
@@ -53,8 +52,7 @@ fn _macros() {
         }
     }
     #[cfg(FALSE)] (let 0 = 1);
-    //~^ ERROR `let` expressions in this position are unstable [E0658]
-    //~| ERROR expected expression, found `let` statement
+    //~^ ERROR expected expression, found `let` statement
     use_expr!(let 0 = 1);
     //~^ ERROR no rules expected the token `let`
 }
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/feature-gate.stderr b/tests/ui/rfcs/rfc-2497-if-let-chains/feature-gate.stderr
index 7a43b71fc8b..6f74736755e 100644
--- a/tests/ui/rfcs/rfc-2497-if-let-chains/feature-gate.stderr
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/feature-gate.stderr
@@ -1,17 +1,21 @@
 error: expected expression, found `let` statement
-  --> $DIR/feature-gate.rs:55:20
+  --> $DIR/feature-gate.rs:54:20
    |
 LL |     #[cfg(FALSE)] (let 0 = 1);
    |                    ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
 
 error: expected expression, found `let` statement
   --> $DIR/feature-gate.rs:45:17
    |
 LL |     noop_expr!((let 0 = 1));
    |                 ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
 
 error: no rules expected the token `let`
-  --> $DIR/feature-gate.rs:58:15
+  --> $DIR/feature-gate.rs:56:15
    |
 LL |     macro_rules! use_expr {
    |     --------------------- when calling this macro
@@ -20,7 +24,7 @@ LL |     use_expr!(let 0 = 1);
    |               ^^^ no rules expected this token in macro call
    |
 note: while trying to match meta-variable `$e:expr`
-  --> $DIR/feature-gate.rs:50:10
+  --> $DIR/feature-gate.rs:49:10
    |
 LL |         ($e:expr) => {
    |          ^^^^^^^
@@ -97,24 +101,6 @@ LL |     while let Range { start: _, end: _ } = (true..true) && false {}
    = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
    = help: add `#![feature(let_chains)]` to the crate attributes to enable
 
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:55:20
-   |
-LL |     #[cfg(FALSE)] (let 0 = 1);
-   |                    ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error[E0658]: `let` expressions in this position are unstable
-  --> $DIR/feature-gate.rs:45:17
-   |
-LL |     noop_expr!((let 0 = 1));
-   |                 ^^^^^^^^^
-   |
-   = note: see issue #53667 <https://github.com/rust-lang/rust/issues/53667> for more information
-   = help: add `#![feature(let_chains)]` to the crate attributes to enable
-
-error: aborting due to 13 previous errors
+error: aborting due to 11 previous errors
 
 For more information about this error, try `rustc --explain E0658`.
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/invalid-let-in-a-valid-let-context.rs b/tests/ui/rfcs/rfc-2497-if-let-chains/invalid-let-in-a-valid-let-context.rs
index a942d1f4caf..dce1c19ff33 100644
--- a/tests/ui/rfcs/rfc-2497-if-let-chains/invalid-let-in-a-valid-let-context.rs
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/invalid-let-in-a-valid-let-context.rs
@@ -13,6 +13,7 @@ fn main() {
         if let Some(elem) = _opt && [1, 2, 3][let _ = &&let Some(x) = Some(42)] = 1 {
         //~^ ERROR expected expression, found `let` statement
         //~| ERROR expected expression, found `let` statement
+        //~| ERROR expected expression, found `let` statement
             true
         }
     }
@@ -31,6 +32,7 @@ fn main() {
     {
         if let Some(elem) = _opt && [1, 2, 3][let _ = ()] = 1 {
         //~^ ERROR expected expression, found `let` statement
+        //~| ERROR expected expression, found `let` statement
             true
         }
     }
diff --git a/tests/ui/rfcs/rfc-2497-if-let-chains/invalid-let-in-a-valid-let-context.stderr b/tests/ui/rfcs/rfc-2497-if-let-chains/invalid-let-in-a-valid-let-context.stderr
index d1ce83c7233..247fad2e992 100644
--- a/tests/ui/rfcs/rfc-2497-if-let-chains/invalid-let-in-a-valid-let-context.stderr
+++ b/tests/ui/rfcs/rfc-2497-if-let-chains/invalid-let-in-a-valid-let-context.stderr
@@ -3,36 +3,64 @@ error: expected expression, found `let` statement
    |
 LL |         let _ = &&let Some(x) = Some(42);
    |                   ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
 
 error: expected expression, found `let` statement
   --> $DIR/invalid-let-in-a-valid-let-context.rs:13:47
    |
 LL |         if let Some(elem) = _opt && [1, 2, 3][let _ = &&let Some(x) = Some(42)] = 1 {
    |                                               ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
 
 error: expected expression, found `let` statement
   --> $DIR/invalid-let-in-a-valid-let-context.rs:13:57
    |
 LL |         if let Some(elem) = _opt && [1, 2, 3][let _ = &&let Some(x) = Some(42)] = 1 {
    |                                                         ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/invalid-let-in-a-valid-let-context.rs:13:12
+   |
+LL |         if let Some(elem) = _opt && [1, 2, 3][let _ = &&let Some(x) = Some(42)] = 1 {
+   |            ^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
 
 error: expected expression, found `let` statement
-  --> $DIR/invalid-let-in-a-valid-let-context.rs:23:23
+  --> $DIR/invalid-let-in-a-valid-let-context.rs:24:23
    |
 LL |             [1, 2, 3][let _ = ()];
    |                       ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
 
 error: expected expression, found `let` statement
-  --> $DIR/invalid-let-in-a-valid-let-context.rs:32:47
+  --> $DIR/invalid-let-in-a-valid-let-context.rs:33:47
    |
 LL |         if let Some(elem) = _opt && [1, 2, 3][let _ = ()] = 1 {
    |                                               ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
+
+error: expected expression, found `let` statement
+  --> $DIR/invalid-let-in-a-valid-let-context.rs:33:12
+   |
+LL |         if let Some(elem) = _opt && [1, 2, 3][let _ = ()] = 1 {
+   |            ^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
 
 error: expected expression, found `let` statement
-  --> $DIR/invalid-let-in-a-valid-let-context.rs:40:21
+  --> $DIR/invalid-let-in-a-valid-let-context.rs:42:21
    |
 LL |             let x = let y = 1;
    |                     ^^^
+   |
+   = note: only supported directly in conditions of `if` and `while` expressions
 
-error: aborting due to 6 previous errors
+error: aborting due to 8 previous errors
 
diff --git a/tests/ui/rfcs/rfc-2632-const-trait-impl/effects/fallback.rs b/tests/ui/rfcs/rfc-2632-const-trait-impl/effects/fallback.rs
new file mode 100644
index 00000000000..da2778f6101
--- /dev/null
+++ b/tests/ui/rfcs/rfc-2632-const-trait-impl/effects/fallback.rs
@@ -0,0 +1,16 @@
+// check-pass
+
+#![feature(effects)]
+
+pub const fn owo() {}
+
+fn main() {
+    // make sure falling back ty/int vars doesn't cause const fallback to be skipped...
+    // See issue: 115791.
+    let _ = 1;
+    if false {
+        let x = panic!();
+    }
+
+    let _ = owo;
+}
diff --git a/tests/ui/sanitize/cfg.rs b/tests/ui/sanitize/cfg.rs
index 523de1ceaee..f8ccf3b042d 100644
--- a/tests/ui/sanitize/cfg.rs
+++ b/tests/ui/sanitize/cfg.rs
@@ -1,15 +1,15 @@
 // Verifies that when compiling with -Zsanitizer=option,
 // the `#[cfg(sanitize = "option")]` attribute is configured.
 
-// needs-sanitizer-support
 // check-pass
 // revisions: address cfi kcfi leak memory thread
 //[address]needs-sanitizer-address
 //[address]compile-flags: -Zsanitizer=address --cfg address
 //[cfi]needs-sanitizer-cfi
-//[cfi]compile-flags:     -Zsanitizer=cfi     --cfg cfi -Clto
-//[kcfi]needs-sanitizer-kcfi
-//[kcfi]compile-flags:    -Zsanitizer=kcfi    --cfg kcfi
+//[cfi]compile-flags:     -Zsanitizer=cfi     --cfg cfi
+//[cfi]compile-flags:     -Clto -Ccodegen-units=1 -Ctarget-feature=-crt-static
+//[kcfi]needs-llvm-components: x86
+//[kcfi]compile-flags:    -Zsanitizer=kcfi    --cfg kcfi --target x86_64-unknown-none
 //[leak]needs-sanitizer-leak
 //[leak]compile-flags:    -Zsanitizer=leak    --cfg leak
 //[memory]needs-sanitizer-memory
@@ -17,7 +17,14 @@
 //[thread]needs-sanitizer-thread
 //[thread]compile-flags:  -Zsanitizer=thread  --cfg thread
 
-#![feature(cfg_sanitize)]
+#![feature(cfg_sanitize, no_core, lang_items)]
+#![crate_type="lib"]
+#![no_core]
+
+#[lang="sized"]
+trait Sized { }
+#[lang="copy"]
+trait Copy { }
 
 #[cfg(all(sanitize = "address", address))]
 fn main() {}
@@ -36,3 +43,7 @@ fn main() {}
 
 #[cfg(all(sanitize = "thread", thread))]
 fn main() {}
+
+pub fn check() {
+    main();
+}
diff --git a/tests/ui/span/issue-29595.stderr b/tests/ui/span/issue-29595.stderr
index 92445e40731..7d603cdbfe5 100644
--- a/tests/ui/span/issue-29595.stderr
+++ b/tests/ui/span/issue-29595.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `u8: Tr` is not satisfied
    |
 LL |     let a: u8 = Tr::C;
    |                 ^^^^^ the trait `Tr` is not implemented for `u8`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-29595.rs:1:1
+   |
+LL | trait Tr {
+   | ^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/span/send-is-not-static-std-sync.rs b/tests/ui/span/send-is-not-static-std-sync.rs
index f8ab5243c22..9c1ee287154 100644
--- a/tests/ui/span/send-is-not-static-std-sync.rs
+++ b/tests/ui/span/send-is-not-static-std-sync.rs
@@ -46,7 +46,7 @@ fn channel() {
         tx.send(&z).unwrap();
     }
     //~^^ ERROR `z` does not live long enough
-    // (channels lack #[may_dangle], thus their dtors are implicit uses of `z`)
+    tx.use_ref(); // (channel drop glue does not use `z` => needs explicit use)
 }
 
 fn main() {}
diff --git a/tests/ui/span/send-is-not-static-std-sync.stderr b/tests/ui/span/send-is-not-static-std-sync.stderr
index eaba415adaa..46534b39168 100644
--- a/tests/ui/span/send-is-not-static-std-sync.stderr
+++ b/tests/ui/span/send-is-not-static-std-sync.stderr
@@ -75,11 +75,9 @@ LL |         tx.send(&z).unwrap();
    |                 ^^ borrowed value does not live long enough
 LL |     }
    |     - `z` dropped here while still borrowed
-...
-LL | }
-   | - borrow might be used here, when `tx` is dropped and runs the `Drop` code for type `Sender`
-   |
-   = note: values in a scope are dropped in the opposite order they are defined
+LL |
+LL |     tx.use_ref(); // (channel drop glue does not use `z` => needs explicit use)
+   |     -- borrow later used here
 
 error: aborting due to 6 previous errors
 
diff --git a/tests/ui/specialization/issue-38091.stderr b/tests/ui/specialization/issue-38091.stderr
index f2210a40719..4d840482b46 100644
--- a/tests/ui/specialization/issue-38091.stderr
+++ b/tests/ui/specialization/issue-38091.stderr
@@ -14,6 +14,11 @@ error[E0277]: the trait bound `(): Valid` is not satisfied
 LL |     default type Ty = ();
    |                       ^^ the trait `Valid` is not implemented for `()`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-38091.rs:20:1
+   |
+LL | trait Valid {}
+   | ^^^^^^^^^^^
 note: required by a bound in `Iterate::Ty`
   --> $DIR/issue-38091.rs:5:14
    |
diff --git a/tests/ui/suggestions/issue-89333.stderr b/tests/ui/suggestions/issue-89333.stderr
index f73f1147d5d..4739f11ddad 100644
--- a/tests/ui/suggestions/issue-89333.stderr
+++ b/tests/ui/suggestions/issue-89333.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `for<'a> &'a _: Trait` is not satisfied
 LL |     test(&|| 0);
    |     ^^^^ the trait `for<'a> Trait` is not implemented for `&'a _`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-89333.rs:9:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `test`
   --> $DIR/issue-89333.rs:11:55
    |
diff --git a/tests/ui/thir-print/thir-flat-const-variant.stdout b/tests/ui/thir-print/thir-flat-const-variant.stdout
index af7f2b67152..7bddc925996 100644
--- a/tests/ui/thir-print/thir-flat-const-variant.stdout
+++ b/tests/ui/thir-print/thir-flat-const-variant.stdout
@@ -1,11 +1,7 @@
 DefId(0:8 ~ thir_flat_const_variant[1f54]::{impl#0}::BAR1):
 Thir {
     body_type: Const(
-        Adt(
-            Foo,
-            [
-            ],
-        ),
+        Foo,
     ),
     arms: [],
     blocks: [],
@@ -50,11 +46,7 @@ Thir {
                     base: None,
                 },
             ),
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
@@ -68,11 +60,7 @@ Thir {
                 ),
                 value: e2,
             },
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
@@ -84,11 +72,7 @@ Thir {
                 lint_level: Inherited,
                 value: e3,
             },
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
@@ -102,11 +86,7 @@ Thir {
 DefId(0:9 ~ thir_flat_const_variant[1f54]::{impl#0}::BAR2):
 Thir {
     body_type: Const(
-        Adt(
-            Foo,
-            [
-            ],
-        ),
+        Foo,
     ),
     arms: [],
     blocks: [],
@@ -151,11 +131,7 @@ Thir {
                     base: None,
                 },
             ),
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
@@ -169,11 +145,7 @@ Thir {
                 ),
                 value: e2,
             },
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
@@ -185,11 +157,7 @@ Thir {
                 lint_level: Inherited,
                 value: e3,
             },
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
@@ -203,11 +171,7 @@ Thir {
 DefId(0:10 ~ thir_flat_const_variant[1f54]::{impl#0}::BAR3):
 Thir {
     body_type: Const(
-        Adt(
-            Foo,
-            [
-            ],
-        ),
+        Foo,
     ),
     arms: [],
     blocks: [],
@@ -252,11 +216,7 @@ Thir {
                     base: None,
                 },
             ),
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
@@ -270,11 +230,7 @@ Thir {
                 ),
                 value: e2,
             },
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
@@ -286,11 +242,7 @@ Thir {
                 lint_level: Inherited,
                 value: e3,
             },
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
@@ -304,11 +256,7 @@ Thir {
 DefId(0:11 ~ thir_flat_const_variant[1f54]::{impl#0}::BAR4):
 Thir {
     body_type: Const(
-        Adt(
-            Foo,
-            [
-            ],
-        ),
+        Foo,
     ),
     arms: [],
     blocks: [],
@@ -353,11 +301,7 @@ Thir {
                     base: None,
                 },
             ),
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
@@ -371,11 +315,7 @@ Thir {
                 ),
                 value: e2,
             },
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
@@ -387,11 +327,7 @@ Thir {
                 lint_level: Inherited,
                 value: e3,
             },
-            ty: Adt(
-                Foo,
-                [
-                ],
-            ),
+            ty: Foo,
             temp_lifetime: Some(
                 Node(3),
             ),
diff --git a/tests/ui/thir-print/thir-tree-match.stdout b/tests/ui/thir-print/thir-tree-match.stdout
index 0e21b98307b..3fc130f0176 100644
--- a/tests/ui/thir-print/thir-tree-match.stdout
+++ b/tests/ui/thir-print/thir-tree-match.stdout
@@ -1,13 +1,13 @@
 DefId(0:16 ~ thir_tree_match[fcf8]::has_match):
 params: [
     Param {
-        ty: Adt(Foo, [])
+        ty: Foo
         ty_span: Some($DIR/thir-tree-match.rs:15:19: 15:22 (#0))
         self_kind: None
         hir_id: Some(HirId(DefId(0:16 ~ thir_tree_match[fcf8]::has_match).1))
         param: Some( 
             Pat: {
-                ty: Adt(Foo, [])
+                ty: Foo
                 span: $DIR/thir-tree-match.rs:15:14: 15:17 (#0)
                 kind: PatKind {
                     Binding {
@@ -15,7 +15,7 @@ params: [
                         name: "foo"
                         mode: ByValue
                         var: LocalVarId(HirId(DefId(0:16 ~ thir_tree_match[fcf8]::has_match).2))
-                        ty: Adt(Foo, [])
+                        ty: Foo
                         is_primary: true
                         subpattern: None
                     }
@@ -73,7 +73,7 @@ body:
                                                                             Match {
                                                                                 scrutinee:
                                                                                     Expr {
-                                                                                        ty: Adt(Foo, [])
+                                                                                        ty: Foo
                                                                                         temp_lifetime: Some(Node(26))
                                                                                         span: $DIR/thir-tree-match.rs:16:11: 16:14 (#0)
                                                                                         kind: 
@@ -82,7 +82,7 @@ body:
                                                                                                 lint_level: Explicit(HirId(DefId(0:16 ~ thir_tree_match[fcf8]::has_match).4))
                                                                                                 value:
                                                                                                     Expr {
-                                                                                                        ty: Adt(Foo, [])
+                                                                                                        ty: Foo
                                                                                                         temp_lifetime: Some(Node(26))
                                                                                                         span: $DIR/thir-tree-match.rs:16:11: 16:14 (#0)
                                                                                                         kind: 
@@ -96,7 +96,7 @@ body:
                                                                                     Arm {
                                                                                         pattern: 
                                                                                             Pat: {
-                                                                                                ty: Adt(Foo, [])
+                                                                                                ty: Foo
                                                                                                 span: $DIR/thir-tree-match.rs:17:9: 17:32 (#0)
                                                                                                 kind: PatKind {
                                                                                                     Variant {
@@ -110,7 +110,7 @@ body:
                                                                                                         variant_index: 0
                                                                                                         subpatterns: [
                                                                                                             Pat: {
-                                                                                                                ty: Adt(Bar, [])
+                                                                                                                ty: Bar
                                                                                                                 span: $DIR/thir-tree-match.rs:17:21: 17:31 (#0)
                                                                                                                 kind: PatKind {
                                                                                                                     Variant {
@@ -169,7 +169,7 @@ body:
                                                                                     Arm {
                                                                                         pattern: 
                                                                                             Pat: {
-                                                                                                ty: Adt(Foo, [])
+                                                                                                ty: Foo
                                                                                                 span: $DIR/thir-tree-match.rs:18:9: 18:23 (#0)
                                                                                                 kind: PatKind {
                                                                                                     Variant {
@@ -183,7 +183,7 @@ body:
                                                                                                         variant_index: 0
                                                                                                         subpatterns: [
                                                                                                             Pat: {
-                                                                                                                ty: Adt(Bar, [])
+                                                                                                                ty: Bar
                                                                                                                 span: $DIR/thir-tree-match.rs:18:21: 18:22 (#0)
                                                                                                                 kind: PatKind {
                                                                                                                     Wild
@@ -232,7 +232,7 @@ body:
                                                                                     Arm {
                                                                                         pattern: 
                                                                                             Pat: {
-                                                                                                ty: Adt(Foo, [])
+                                                                                                ty: Foo
                                                                                                 span: $DIR/thir-tree-match.rs:19:9: 19:20 (#0)
                                                                                                 kind: PatKind {
                                                                                                     Variant {
diff --git a/tests/ui/trait-bounds/issue-82038.stderr b/tests/ui/trait-bounds/issue-82038.stderr
index f37e3286f4b..30bb4a0a850 100644
--- a/tests/ui/trait-bounds/issue-82038.stderr
+++ b/tests/ui/trait-bounds/issue-82038.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `bool: Foo` is not satisfied
    |
 LL |     <bool as Foo>::my_method();
    |      ^^^^ the trait `Foo` is not implemented for `bool`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-82038.rs:3:1
+   |
+LL | trait Foo {
+   | ^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/traits/bound/on-structs-and-enums-in-fns.stderr b/tests/ui/traits/bound/on-structs-and-enums-in-fns.stderr
index 61237a63e32..530264b344a 100644
--- a/tests/ui/traits/bound/on-structs-and-enums-in-fns.stderr
+++ b/tests/ui/traits/bound/on-structs-and-enums-in-fns.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `u32: Trait` is not satisfied
 LL | fn explode(x: Foo<u32>) {}
    |               ^^^^^^^^ the trait `Trait` is not implemented for `u32`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-structs-and-enums-in-fns.rs:1:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `Foo`
   --> $DIR/on-structs-and-enums-in-fns.rs:3:14
    |
@@ -16,6 +21,11 @@ error[E0277]: the trait bound `f32: Trait` is not satisfied
 LL | fn kaboom(y: Bar<f32>) {}
    |              ^^^^^^^^ the trait `Trait` is not implemented for `f32`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-structs-and-enums-in-fns.rs:1:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `Bar`
   --> $DIR/on-structs-and-enums-in-fns.rs:7:12
    |
diff --git a/tests/ui/traits/bound/on-structs-and-enums-in-impls.stderr b/tests/ui/traits/bound/on-structs-and-enums-in-impls.stderr
index 8a43742260b..372bbabbd86 100644
--- a/tests/ui/traits/bound/on-structs-and-enums-in-impls.stderr
+++ b/tests/ui/traits/bound/on-structs-and-enums-in-impls.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `u16: Trait` is not satisfied
 LL | impl PolyTrait<Foo<u16>> for Struct {
    |      ^^^^^^^^^^^^^^^^^^^ the trait `Trait` is not implemented for `u16`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-structs-and-enums-in-impls.rs:1:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `Foo`
   --> $DIR/on-structs-and-enums-in-impls.rs:3:14
    |
diff --git a/tests/ui/traits/bound/on-structs-and-enums-locals.stderr b/tests/ui/traits/bound/on-structs-and-enums-locals.stderr
index 20bbe69c059..01cf76c62d5 100644
--- a/tests/ui/traits/bound/on-structs-and-enums-locals.stderr
+++ b/tests/ui/traits/bound/on-structs-and-enums-locals.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `usize: Trait` is not satisfied
 LL |     let baz: Foo<usize> = loop { };
    |              ^^^^^^^^^^ the trait `Trait` is not implemented for `usize`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-structs-and-enums-locals.rs:1:1
+   |
+LL | trait Trait {
+   | ^^^^^^^^^^^
 note: required by a bound in `Foo`
   --> $DIR/on-structs-and-enums-locals.rs:5:14
    |
@@ -16,6 +21,11 @@ error[E0277]: the trait bound `{integer}: Trait` is not satisfied
 LL |         x: 3
    |            ^ the trait `Trait` is not implemented for `{integer}`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-structs-and-enums-locals.rs:1:1
+   |
+LL | trait Trait {
+   | ^^^^^^^^^^^
 note: required by a bound in `Foo`
   --> $DIR/on-structs-and-enums-locals.rs:5:14
    |
diff --git a/tests/ui/traits/bound/on-structs-and-enums-static.stderr b/tests/ui/traits/bound/on-structs-and-enums-static.stderr
index fda734e8571..fa14aff684d 100644
--- a/tests/ui/traits/bound/on-structs-and-enums-static.stderr
+++ b/tests/ui/traits/bound/on-structs-and-enums-static.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `usize: Trait` is not satisfied
 LL | static X: Foo<usize> = Foo {
    |           ^^^^^^^^^^ the trait `Trait` is not implemented for `usize`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-structs-and-enums-static.rs:1:1
+   |
+LL | trait Trait {
+   | ^^^^^^^^^^^
 note: required by a bound in `Foo`
   --> $DIR/on-structs-and-enums-static.rs:5:14
    |
diff --git a/tests/ui/traits/bound/on-structs-and-enums.stderr b/tests/ui/traits/bound/on-structs-and-enums.stderr
index fe05b86344b..606f764852f 100644
--- a/tests/ui/traits/bound/on-structs-and-enums.stderr
+++ b/tests/ui/traits/bound/on-structs-and-enums.stderr
@@ -20,6 +20,11 @@ error[E0277]: the trait bound `isize: Trait` is not satisfied
 LL |     a: Foo<isize>,
    |        ^^^^^^^^^^ the trait `Trait` is not implemented for `isize`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-structs-and-enums.rs:1:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `Foo`
   --> $DIR/on-structs-and-enums.rs:3:14
    |
@@ -32,6 +37,11 @@ error[E0277]: the trait bound `usize: Trait` is not satisfied
 LL |     Quux(Bar<usize>),
    |          ^^^^^^^^^^ the trait `Trait` is not implemented for `usize`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-structs-and-enums.rs:1:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `Bar`
   --> $DIR/on-structs-and-enums.rs:7:12
    |
@@ -76,6 +86,11 @@ error[E0277]: the trait bound `i32: Trait` is not satisfied
 LL |     Foo<i32>,
    |     ^^^^^^^^ the trait `Trait` is not implemented for `i32`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-structs-and-enums.rs:1:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `Foo`
   --> $DIR/on-structs-and-enums.rs:3:14
    |
@@ -88,6 +103,11 @@ error[E0277]: the trait bound `u8: Trait` is not satisfied
 LL |     DictionaryLike { field: Bar<u8> },
    |                             ^^^^^^^ the trait `Trait` is not implemented for `u8`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/on-structs-and-enums.rs:1:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `Bar`
   --> $DIR/on-structs-and-enums.rs:7:12
    |
diff --git a/tests/ui/traits/deny-builtin-object-impl.current.stderr b/tests/ui/traits/deny-builtin-object-impl.current.stderr
index 5c1987426f7..8ca3d3a057f 100644
--- a/tests/ui/traits/deny-builtin-object-impl.current.stderr
+++ b/tests/ui/traits/deny-builtin-object-impl.current.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `dyn NotObject: NotObject` is not satisfied
 LL |     test_not_object::<dyn NotObject>();
    |                       ^^^^^^^^^^^^^ the trait `NotObject` is not implemented for `dyn NotObject`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/deny-builtin-object-impl.rs:10:1
+   |
+LL | trait NotObject {}
+   | ^^^^^^^^^^^^^^^
 note: required by a bound in `test_not_object`
   --> $DIR/deny-builtin-object-impl.rs:14:23
    |
diff --git a/tests/ui/traits/deny-builtin-object-impl.next.stderr b/tests/ui/traits/deny-builtin-object-impl.next.stderr
index 5c1987426f7..8ca3d3a057f 100644
--- a/tests/ui/traits/deny-builtin-object-impl.next.stderr
+++ b/tests/ui/traits/deny-builtin-object-impl.next.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `dyn NotObject: NotObject` is not satisfied
 LL |     test_not_object::<dyn NotObject>();
    |                       ^^^^^^^^^^^^^ the trait `NotObject` is not implemented for `dyn NotObject`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/deny-builtin-object-impl.rs:10:1
+   |
+LL | trait NotObject {}
+   | ^^^^^^^^^^^^^^^
 note: required by a bound in `test_not_object`
   --> $DIR/deny-builtin-object-impl.rs:14:23
    |
diff --git a/tests/ui/traits/dont-autoderef-ty-with-escaping-var.stderr b/tests/ui/traits/dont-autoderef-ty-with-escaping-var.stderr
index 263c59ee327..a5d0e6ab095 100644
--- a/tests/ui/traits/dont-autoderef-ty-with-escaping-var.stderr
+++ b/tests/ui/traits/dont-autoderef-ty-with-escaping-var.stderr
@@ -10,6 +10,11 @@ error[E0277]: the trait bound `for<'a> &'a mut Vec<&'a u32>: Foo<'static, i32>`
 LL |     <i32 as RefFoo<i32>>::ref_foo(unknown);
    |      ^^^ the trait `for<'a> Foo<'static, i32>` is not implemented for `&'a mut Vec<&'a u32>`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/dont-autoderef-ty-with-escaping-var.rs:3:1
+   |
+LL | trait Foo<'x, T> {}
+   | ^^^^^^^^^^^^^^^^
 note: required for `i32` to implement `RefFoo<i32>`
   --> $DIR/dont-autoderef-ty-with-escaping-var.rs:9:9
    |
diff --git a/tests/ui/traits/impl-bounds-checking.stderr b/tests/ui/traits/impl-bounds-checking.stderr
index 1f969efe114..bfa8213abe7 100644
--- a/tests/ui/traits/impl-bounds-checking.stderr
+++ b/tests/ui/traits/impl-bounds-checking.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `isize: Clone2` is not satisfied
 LL | impl Getter<isize> for isize {
    |                        ^^^^^ the trait `Clone2` is not implemented for `isize`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/impl-bounds-checking.rs:1:1
+   |
+LL | pub trait Clone2 {
+   | ^^^^^^^^^^^^^^^^
 note: required by a bound in `Getter`
   --> $DIR/impl-bounds-checking.rs:6:17
    |
diff --git a/tests/ui/traits/new-solver/canonicalize-effect-var.rs b/tests/ui/traits/new-solver/canonicalize-effect-var.rs
new file mode 100644
index 00000000000..35b69ed1a6b
--- /dev/null
+++ b/tests/ui/traits/new-solver/canonicalize-effect-var.rs
@@ -0,0 +1,22 @@
+// compile-flags: -Ztrait-solver=next
+// check-pass
+
+#![feature(effects)]
+#![feature(const_trait_impl)]
+
+#[const_trait]
+trait Foo {
+    fn foo();
+}
+
+trait Bar {}
+
+impl const Foo for i32 {
+    fn foo() {}
+}
+
+impl<T> const Foo for T where T: Bar {
+    fn foo() {}
+}
+
+fn main() {}
diff --git a/tests/ui/traits/new-solver/projection-discr-kind.stderr b/tests/ui/traits/new-solver/projection-discr-kind.stderr
index 03e28f993e2..e14953f19ff 100644
--- a/tests/ui/traits/new-solver/projection-discr-kind.stderr
+++ b/tests/ui/traits/new-solver/projection-discr-kind.stderr
@@ -6,6 +6,11 @@ LL |     needs_bar(std::mem::discriminant(&x));
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/projection-discr-kind.rs:10:1
+   |
+LL | trait Bar {}
+   | ^^^^^^^^^
 note: required by a bound in `needs_bar`
   --> $DIR/projection-discr-kind.rs:11:22
    |
diff --git a/tests/ui/traits/non_lifetime_binders/capture-late-ct-in-anon.rs b/tests/ui/traits/non_lifetime_binders/capture-late-ct-in-anon.rs
index 91c6dfb8e0a..bbae67f0bad 100644
--- a/tests/ui/traits/non_lifetime_binders/capture-late-ct-in-anon.rs
+++ b/tests/ui/traits/non_lifetime_binders/capture-late-ct-in-anon.rs
@@ -4,7 +4,7 @@
 fn b()
 where
     for<const C: usize> [(); C]: Copy,
-    //~^ ERROR cannot capture late-bound const parameter in a constant
+    //~^ ERROR cannot capture late-bound const parameter in constant
 {
 }
 
diff --git a/tests/ui/traits/non_lifetime_binders/capture-late-ct-in-anon.stderr b/tests/ui/traits/non_lifetime_binders/capture-late-ct-in-anon.stderr
index 69bb605bf41..d65892ec6df 100644
--- a/tests/ui/traits/non_lifetime_binders/capture-late-ct-in-anon.stderr
+++ b/tests/ui/traits/non_lifetime_binders/capture-late-ct-in-anon.stderr
@@ -7,7 +7,7 @@ LL | #![feature(non_lifetime_binders)]
    = note: see issue #108185 <https://github.com/rust-lang/rust/issues/108185> for more information
    = note: `#[warn(incomplete_features)]` on by default
 
-error: cannot capture late-bound const parameter in a constant
+error: cannot capture late-bound const parameter in constant
   --> $DIR/capture-late-ct-in-anon.rs:6:30
    |
 LL |     for<const C: usize> [(); C]: Copy,
diff --git a/tests/ui/traits/non_lifetime_binders/fail.stderr b/tests/ui/traits/non_lifetime_binders/fail.stderr
index 7bd02550fb3..240bcef7df5 100644
--- a/tests/ui/traits/non_lifetime_binders/fail.stderr
+++ b/tests/ui/traits/non_lifetime_binders/fail.stderr
@@ -13,6 +13,11 @@ error[E0277]: the trait bound `T: Trait` is not satisfied
 LL |     fail();
    |     ^^^^ the trait `Trait` is not implemented for `T`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/fail.rs:6:1
+   |
+LL | trait Trait {}
+   | ^^^^^^^^^^^
 note: required by a bound in `fail`
   --> $DIR/fail.rs:10:15
    |
diff --git a/tests/ui/traits/non_lifetime_binders/late-bound-in-anon-ct.rs b/tests/ui/traits/non_lifetime_binders/late-bound-in-anon-ct.rs
index 3903bfe9bcf..64f09f823fc 100644
--- a/tests/ui/traits/non_lifetime_binders/late-bound-in-anon-ct.rs
+++ b/tests/ui/traits/non_lifetime_binders/late-bound-in-anon-ct.rs
@@ -5,7 +5,7 @@
 fn foo() -> usize
 where
     for<T> [i32; { let _: T = todo!(); 0 }]:,
-    //~^ ERROR cannot capture late-bound type parameter in a constant
+    //~^ ERROR cannot capture late-bound type parameter in constant
 {}
 
 fn main() {}
diff --git a/tests/ui/traits/non_lifetime_binders/late-bound-in-anon-ct.stderr b/tests/ui/traits/non_lifetime_binders/late-bound-in-anon-ct.stderr
index fafff02dea6..dc54e1acc39 100644
--- a/tests/ui/traits/non_lifetime_binders/late-bound-in-anon-ct.stderr
+++ b/tests/ui/traits/non_lifetime_binders/late-bound-in-anon-ct.stderr
@@ -15,7 +15,7 @@ LL | #![feature(non_lifetime_binders, generic_const_exprs)]
    |
    = note: see issue #76560 <https://github.com/rust-lang/rust/issues/76560> for more information
 
-error: cannot capture late-bound type parameter in a constant
+error: cannot capture late-bound type parameter in constant
   --> $DIR/late-bound-in-anon-ct.rs:7:27
    |
 LL |     for<T> [i32; { let _: T = todo!(); 0 }]:,
diff --git a/tests/ui/traits/object-does-not-impl-trait.stderr b/tests/ui/traits/object-does-not-impl-trait.stderr
index f1dd508a467..81d67255a0b 100644
--- a/tests/ui/traits/object-does-not-impl-trait.stderr
+++ b/tests/ui/traits/object-does-not-impl-trait.stderr
@@ -6,6 +6,11 @@ LL | fn take_object(f: Box<dyn Foo>) { take_foo(f); }
    |                                   |
    |                                   required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/object-does-not-impl-trait.rs:4:1
+   |
+LL | trait Foo {}
+   | ^^^^^^^^^
 note: required by a bound in `take_foo`
   --> $DIR/object-does-not-impl-trait.rs:5:15
    |
diff --git a/tests/ui/traits/vtable-res-trait-param.stderr b/tests/ui/traits/vtable-res-trait-param.stderr
index 2b3e3de9b1a..4cfceefb24c 100644
--- a/tests/ui/traits/vtable-res-trait-param.stderr
+++ b/tests/ui/traits/vtable-res-trait-param.stderr
@@ -6,6 +6,11 @@ LL |     b.gimme_an_a(y)
    |       |
    |       required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/vtable-res-trait-param.rs:1:1
+   |
+LL | trait TraitA {
+   | ^^^^^^^^^^^^
 note: required by a bound in `TraitB::gimme_an_a`
   --> $DIR/vtable-res-trait-param.rs:6:21
    |
diff --git a/tests/ui/trivial-bounds/trivial-bounds-leak.stderr b/tests/ui/trivial-bounds/trivial-bounds-leak.stderr
index 02c5d5d2484..be472a50769 100644
--- a/tests/ui/trivial-bounds/trivial-bounds-leak.stderr
+++ b/tests/ui/trivial-bounds/trivial-bounds-leak.stderr
@@ -27,6 +27,12 @@ LL |     Foo::test(&4i32);
    |     --------- ^^^^^ the trait `Foo` is not implemented for `i32`
    |     |
    |     required by a bound introduced by this call
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/trivial-bounds-leak.rs:4:1
+   |
+LL | pub trait Foo {
+   | ^^^^^^^^^^^^^
 
 error[E0277]: the trait bound `i32: Foo` is not satisfied
   --> $DIR/trivial-bounds-leak.rs:26:22
@@ -36,6 +42,11 @@ LL |     generic_function(5i32);
    |     |
    |     required by a bound introduced by this call
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/trivial-bounds-leak.rs:4:1
+   |
+LL | pub trait Foo {
+   | ^^^^^^^^^^^^^
 note: required by a bound in `generic_function`
   --> $DIR/trivial-bounds-leak.rs:29:24
    |
diff --git a/tests/ui/type-alias-impl-trait/escaping-bound-var.rs b/tests/ui/type-alias-impl-trait/escaping-bound-var.rs
new file mode 100644
index 00000000000..bf27e76db2b
--- /dev/null
+++ b/tests/ui/type-alias-impl-trait/escaping-bound-var.rs
@@ -0,0 +1,22 @@
+#![feature(type_alias_impl_trait)]
+
+pub trait Trait<'a> {
+    type Assoc;
+}
+
+trait Test<'a> {}
+
+pub type Foo = impl for<'a> Trait<'a, Assoc = impl Test<'a>>;
+//~^ ERROR cannot capture late-bound lifetime in type alias impl trait
+
+impl Trait<'_> for () {
+    type Assoc = ();
+}
+
+impl Test<'_> for () {}
+
+fn constrain() -> Foo {
+    ()
+}
+
+fn main() {}
diff --git a/tests/ui/type-alias-impl-trait/escaping-bound-var.stderr b/tests/ui/type-alias-impl-trait/escaping-bound-var.stderr
new file mode 100644
index 00000000000..8205a60ccdd
--- /dev/null
+++ b/tests/ui/type-alias-impl-trait/escaping-bound-var.stderr
@@ -0,0 +1,8 @@
+error: cannot capture late-bound lifetime in type alias impl trait
+  --> $DIR/escaping-bound-var.rs:9:57
+   |
+LL | pub type Foo = impl for<'a> Trait<'a, Assoc = impl Test<'a>>;
+   |                         -- lifetime defined here        ^^
+
+error: aborting due to previous error
+
diff --git a/tests/ui/type-alias-impl-trait/indirect-recursion-issue-112047.rs b/tests/ui/type-alias-impl-trait/indirect-recursion-issue-112047.rs
new file mode 100644
index 00000000000..baa22e1ce18
--- /dev/null
+++ b/tests/ui/type-alias-impl-trait/indirect-recursion-issue-112047.rs
@@ -0,0 +1,29 @@
+// edition: 2021
+// build-fail
+//~^^ ERROR overflow evaluating the requirement `<() as Recur>::Recur == _`
+
+#![feature(impl_trait_in_assoc_type)]
+
+use core::future::Future;
+
+trait Recur {
+    type Recur: Future<Output = ()>;
+
+    fn recur(self) -> Self::Recur;
+}
+
+async fn recur(t: impl Recur) {
+    t.recur().await;
+}
+
+impl Recur for () {
+    type Recur = impl Future<Output = ()>;
+
+    fn recur(self) -> Self::Recur {
+        async move { recur(self).await; }
+    }
+}
+
+fn main() {
+    recur(());
+}
diff --git a/tests/ui/type-alias-impl-trait/indirect-recursion-issue-112047.stderr b/tests/ui/type-alias-impl-trait/indirect-recursion-issue-112047.stderr
new file mode 100644
index 00000000000..0238694c24d
--- /dev/null
+++ b/tests/ui/type-alias-impl-trait/indirect-recursion-issue-112047.stderr
@@ -0,0 +1,5 @@
+error[E0275]: overflow evaluating the requirement `<() as Recur>::Recur == _`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0275`.
diff --git a/tests/ui/type-alias-impl-trait/mututally-recursive-overflow.rs b/tests/ui/type-alias-impl-trait/mututally-recursive-overflow.rs
new file mode 100644
index 00000000000..1ccd1b0cbad
--- /dev/null
+++ b/tests/ui/type-alias-impl-trait/mututally-recursive-overflow.rs
@@ -0,0 +1,40 @@
+// edition: 2021
+// build-fail
+//~^^ ERROR overflow evaluating the requirement `<() as B>::Assoc == _`
+
+#![feature(rustc_attrs)]
+#![feature(impl_trait_in_assoc_type)]
+
+#[rustc_coinductive]
+trait A {
+    type Assoc;
+
+    fn test() -> Self::Assoc;
+}
+
+#[rustc_coinductive]
+trait B {
+    type Assoc;
+
+    fn test() -> Self::Assoc;
+}
+
+impl<T: A> B for T {
+    type Assoc = impl Sized;
+
+    fn test() -> <Self as B>::Assoc {
+        <T as A>::test()
+    }
+}
+
+fn main() {
+    <() as A>::test();
+}
+
+impl<T: B> A for T {
+    type Assoc = impl Sized;
+
+    fn test() -> <Self as A>::Assoc {
+        <T as B>::test()
+    }
+}
diff --git a/tests/ui/type-alias-impl-trait/mututally-recursive-overflow.stderr b/tests/ui/type-alias-impl-trait/mututally-recursive-overflow.stderr
new file mode 100644
index 00000000000..49c59f7eb37
--- /dev/null
+++ b/tests/ui/type-alias-impl-trait/mututally-recursive-overflow.stderr
@@ -0,0 +1,5 @@
+error[E0275]: overflow evaluating the requirement `<() as B>::Assoc == _`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0275`.
diff --git a/tests/ui/type-alias-impl-trait/nested-tait-hrtb.rs b/tests/ui/type-alias-impl-trait/nested-tait-hrtb.rs
index 4a9631a7208..ba705d6f85a 100644
--- a/tests/ui/type-alias-impl-trait/nested-tait-hrtb.rs
+++ b/tests/ui/type-alias-impl-trait/nested-tait-hrtb.rs
@@ -8,7 +8,7 @@ fn without_lt() -> impl for<'a> Trait<'a, Assoc = WithoutLt> {}
 //~^ ERROR captures lifetime that does not appear in bounds
 
 type WithLt<'a> = impl Sized + 'a;
-//~^ ERROR concrete type differs from previous defining opaque type use
+
 fn with_lt() -> impl for<'a> Trait<'a, Assoc = WithLt<'a>> {}
 //~^ ERROR expected generic lifetime parameter, found `'a`
 
diff --git a/tests/ui/type-alias-impl-trait/nested-tait-hrtb.stderr b/tests/ui/type-alias-impl-trait/nested-tait-hrtb.stderr
index 9a783a6d92a..f208730552d 100644
--- a/tests/ui/type-alias-impl-trait/nested-tait-hrtb.stderr
+++ b/tests/ui/type-alias-impl-trait/nested-tait-hrtb.stderr
@@ -17,19 +17,7 @@ LL |
 LL | fn with_lt() -> impl for<'a> Trait<'a, Assoc = WithLt<'a>> {}
    |                                                            ^^
 
-error: concrete type differs from previous defining opaque type use
-  --> $DIR/nested-tait-hrtb.rs:10:19
-   |
-LL | type WithLt<'a> = impl Sized + 'a;
-   |                   ^^^^^^^^^^^^^^^ expected `&'a str`, got `{type error}`
-   |
-note: previous use here
-  --> $DIR/nested-tait-hrtb.rs:12:17
-   |
-LL | fn with_lt() -> impl for<'a> Trait<'a, Assoc = WithLt<'a>> {}
-   |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-
-error: aborting due to 3 previous errors
+error: aborting due to 2 previous errors
 
 Some errors have detailed explanations: E0700, E0792.
 For more information about an error, try `rustc --explain E0700`.
diff --git a/tests/ui/type-alias-impl-trait/rpit_tait_equality_in_canonical_query.rs b/tests/ui/type-alias-impl-trait/rpit_tait_equality_in_canonical_query.rs
new file mode 100644
index 00000000000..eefe333da45
--- /dev/null
+++ b/tests/ui/type-alias-impl-trait/rpit_tait_equality_in_canonical_query.rs
@@ -0,0 +1,25 @@
+//! This tries to prove the APIT's bounds in a canonical query,
+//! which doesn't know anything about the defining scope of either
+//! opaque type and thus makes a random choice as to which opaque type
+//! becomes the hidden type of the other. When we leave the canonical
+//! query, we attempt to actually check the defining anchor, but now we
+//! have a situation where the RPIT gets constrained outside its anchor.
+
+// revisions: current next
+//[next] compile-flags: -Ztrait-solver=next
+// check-pass
+
+#![feature(type_alias_impl_trait)]
+
+type Opaque = impl Sized;
+
+fn get_rpit() -> impl Clone {}
+
+fn query(_: impl FnOnce() -> Opaque) {}
+
+fn test() -> Opaque {
+    query(get_rpit);
+    get_rpit()
+}
+
+fn main() {}
diff --git a/tests/ui/type-alias-impl-trait/variance.rs b/tests/ui/type-alias-impl-trait/variance.rs
index eba4816003b..e92cf2513e7 100644
--- a/tests/ui/type-alias-impl-trait/variance.rs
+++ b/tests/ui/type-alias-impl-trait/variance.rs
@@ -9,42 +9,36 @@ type NotCapturedEarly<'a> = impl Sized; //~ [o]
 
 type CapturedEarly<'a> = impl Sized + Captures<'a>; //~ [o]
 
+// TAIT does *not* capture `'b`
 type NotCapturedLate<'a> = dyn for<'b> Iterator<Item = impl Sized>; //~ [o]
 
-type CapturedLate<'a> = dyn for<'b> Iterator<Item = impl Sized + Captures<'b>>; //~ [o]
-
-type Captured<'a> = dyn for<'b> Iterator<Item = impl Sized + Captures<'a> + Captures<'b>>; //~ [o]
+// TAIT does *not* capture `'b`
+type Captured<'a> = dyn for<'b> Iterator<Item = impl Sized + Captures<'a>>; //~ [o]
 
 type Bar<'a, 'b: 'b, T> = impl Sized; //~ ERROR [o, o, o]
 
 trait Foo<'i> {
-    type ImplicitCapturedEarly<'a>;
-
-    type ExplicitCaptureEarly<'a>;
+    type ImplicitCapture<'a>;
 
-    type ImplicitCaptureLate<'a>;
+    type ExplicitCaptureFromHeader<'a>;
 
-    type ExplicitCaptureLate<'a>;
+    type ExplicitCaptureFromGat<'a>;
 }
 
 impl<'i> Foo<'i> for &'i () {
-    type ImplicitCapturedEarly<'a> = impl Sized; //~ [o, o]
+    type ImplicitCapture<'a> = impl Sized; //~ [o, o]
 
-    type ExplicitCaptureEarly<'a> = impl Sized + Captures<'i>; //~ [o, o]
+    type ExplicitCaptureFromHeader<'a> = impl Sized + Captures<'i>; //~ [o, o]
 
-    type ImplicitCaptureLate<'a> = impl Sized; //~ [o, o]
-
-    type ExplicitCaptureLate<'a> = impl Sized + Captures<'a>; //~ [o, o]
+    type ExplicitCaptureFromGat<'a> = impl Sized + Captures<'a>; //~ [o, o]
 }
 
 impl<'i> Foo<'i> for () {
-    type ImplicitCapturedEarly<'a> = impl Sized; //~ [o, o]
-
-    type ExplicitCaptureEarly<'a> = impl Sized + Captures<'i>; //~ [o, o]
+    type ImplicitCapture<'a> = impl Sized; //~ [o, o]
 
-    type ImplicitCaptureLate<'a> = impl Sized; //~ [o, o]
+    type ExplicitCaptureFromHeader<'a> = impl Sized + Captures<'i>; //~ [o, o]
 
-    type ExplicitCaptureLate<'a> = impl Sized + Captures<'a>; //~ [o, o]
+    type ExplicitCaptureFromGat<'a> = impl Sized + Captures<'a>; //~ [o, o]
 }
 
 fn main() {}
diff --git a/tests/ui/type-alias-impl-trait/variance.stderr b/tests/ui/type-alias-impl-trait/variance.stderr
index f73cf617a4c..1794447c89a 100644
--- a/tests/ui/type-alias-impl-trait/variance.stderr
+++ b/tests/ui/type-alias-impl-trait/variance.stderr
@@ -11,22 +11,16 @@ LL | type CapturedEarly<'a> = impl Sized + Captures<'a>;
    |                          ^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: [o]
-  --> $DIR/variance.rs:12:56
+  --> $DIR/variance.rs:13:56
    |
 LL | type NotCapturedLate<'a> = dyn for<'b> Iterator<Item = impl Sized>;
    |                                                        ^^^^^^^^^^
 
 error: [o]
-  --> $DIR/variance.rs:14:53
-   |
-LL | type CapturedLate<'a> = dyn for<'b> Iterator<Item = impl Sized + Captures<'b>>;
-   |                                                     ^^^^^^^^^^^^^^^^^^^^^^^^^
-
-error: [o]
   --> $DIR/variance.rs:16:49
    |
-LL | type Captured<'a> = dyn for<'b> Iterator<Item = impl Sized + Captures<'a> + Captures<'b>>;
-   |                                                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | type Captured<'a> = dyn for<'b> Iterator<Item = impl Sized + Captures<'a>>;
+   |                                                 ^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: [o, o, o]
   --> $DIR/variance.rs:18:27
@@ -35,52 +29,40 @@ LL | type Bar<'a, 'b: 'b, T> = impl Sized;
    |                           ^^^^^^^^^^
 
 error: [o, o]
-  --> $DIR/variance.rs:31:38
-   |
-LL |     type ImplicitCapturedEarly<'a> = impl Sized;
-   |                                      ^^^^^^^^^^
-
-error: [o, o]
-  --> $DIR/variance.rs:33:37
-   |
-LL |     type ExplicitCaptureEarly<'a> = impl Sized + Captures<'i>;
-   |                                     ^^^^^^^^^^^^^^^^^^^^^^^^^
-
-error: [o, o]
-  --> $DIR/variance.rs:35:36
+  --> $DIR/variance.rs:29:32
    |
-LL |     type ImplicitCaptureLate<'a> = impl Sized;
-   |                                    ^^^^^^^^^^
+LL |     type ImplicitCapture<'a> = impl Sized;
+   |                                ^^^^^^^^^^
 
 error: [o, o]
-  --> $DIR/variance.rs:37:36
+  --> $DIR/variance.rs:31:42
    |
-LL |     type ExplicitCaptureLate<'a> = impl Sized + Captures<'a>;
-   |                                    ^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     type ExplicitCaptureFromHeader<'a> = impl Sized + Captures<'i>;
+   |                                          ^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: [o, o]
-  --> $DIR/variance.rs:41:38
+  --> $DIR/variance.rs:33:39
    |
-LL |     type ImplicitCapturedEarly<'a> = impl Sized;
-   |                                      ^^^^^^^^^^
+LL |     type ExplicitCaptureFromGat<'a> = impl Sized + Captures<'a>;
+   |                                       ^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: [o, o]
-  --> $DIR/variance.rs:43:37
+  --> $DIR/variance.rs:37:32
    |
-LL |     type ExplicitCaptureEarly<'a> = impl Sized + Captures<'i>;
-   |                                     ^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     type ImplicitCapture<'a> = impl Sized;
+   |                                ^^^^^^^^^^
 
 error: [o, o]
-  --> $DIR/variance.rs:45:36
+  --> $DIR/variance.rs:39:42
    |
-LL |     type ImplicitCaptureLate<'a> = impl Sized;
-   |                                    ^^^^^^^^^^
+LL |     type ExplicitCaptureFromHeader<'a> = impl Sized + Captures<'i>;
+   |                                          ^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: [o, o]
-  --> $DIR/variance.rs:47:36
+  --> $DIR/variance.rs:41:39
    |
-LL |     type ExplicitCaptureLate<'a> = impl Sized + Captures<'a>;
-   |                                    ^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     type ExplicitCaptureFromGat<'a> = impl Sized + Captures<'a>;
+   |                                       ^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: aborting due to 14 previous errors
+error: aborting due to 11 previous errors
 
diff --git a/tests/ui/type/type-arg-out-of-scope.rs b/tests/ui/type/type-arg-out-of-scope.rs
index 02aad007707..c36f9904e5d 100644
--- a/tests/ui/type/type-arg-out-of-scope.rs
+++ b/tests/ui/type/type-arg-out-of-scope.rs
@@ -1,4 +1,4 @@
-// error-pattern:can't use generic parameters from outer function
+// error-pattern:can't use generic parameters from outer item
 fn foo<T>(x: T) {
     fn bar(f: Box<dyn FnMut(T) -> T>) { }
 }
diff --git a/tests/ui/type/type-arg-out-of-scope.stderr b/tests/ui/type/type-arg-out-of-scope.stderr
index 7f18b4510f4..8665001e243 100644
--- a/tests/ui/type/type-arg-out-of-scope.stderr
+++ b/tests/ui/type/type-arg-out-of-scope.stderr
@@ -1,22 +1,22 @@
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/type-arg-out-of-scope.rs:3:29
    |
 LL | fn foo<T>(x: T) {
-   |        - type parameter from outer function
+   |        - type parameter from outer item
 LL |     fn bar(f: Box<dyn FnMut(T) -> T>) { }
-   |           -                 ^ use of generic parameter from outer function
+   |           -                 ^ use of generic parameter from outer item
    |           |
-   |           help: try using a local generic parameter instead: `<T>`
+   |           help: try introducing a local generic parameter here: `<T>`
 
-error[E0401]: can't use generic parameters from outer function
+error[E0401]: can't use generic parameters from outer item
   --> $DIR/type-arg-out-of-scope.rs:3:35
    |
 LL | fn foo<T>(x: T) {
-   |        - type parameter from outer function
+   |        - type parameter from outer item
 LL |     fn bar(f: Box<dyn FnMut(T) -> T>) { }
-   |           -                       ^ use of generic parameter from outer function
+   |           -                       ^ use of generic parameter from outer item
    |           |
-   |           help: try using a local generic parameter instead: `<T>`
+   |           help: try introducing a local generic parameter here: `<T>`
 
 error: aborting due to 2 previous errors
 
diff --git a/tests/ui/union/projection-as-union-type-error-2.stderr b/tests/ui/union/projection-as-union-type-error-2.stderr
index bab226f271d..21f4ea103ad 100644
--- a/tests/ui/union/projection-as-union-type-error-2.stderr
+++ b/tests/ui/union/projection-as-union-type-error-2.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `u8: NotImplemented` is not satisfied
 LL |     a: <Foo as Identity>::Identity,
    |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `NotImplemented` is not implemented for `u8`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/projection-as-union-type-error-2.rs:9:1
+   |
+LL | trait NotImplemented {}
+   | ^^^^^^^^^^^^^^^^^^^^
 note: required for `u8` to implement `Identity`
   --> $DIR/projection-as-union-type-error-2.rs:11:25
    |
diff --git a/tests/ui/union/projection-as-union-type-error.stderr b/tests/ui/union/projection-as-union-type-error.stderr
index e4fbe9603ad..2b0241caf98 100644
--- a/tests/ui/union/projection-as-union-type-error.stderr
+++ b/tests/ui/union/projection-as-union-type-error.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `u8: Identity` is not satisfied
    |
 LL |     a:  <Foo as Identity>::Identity,
    |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Identity` is not implemented for `u8`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/projection-as-union-type-error.rs:6:1
+   |
+LL | pub trait Identity {
+   | ^^^^^^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/unreachable-code.rs b/tests/ui/unreachable-code.rs
index 28b938edc63..64174db7afb 100644
--- a/tests/ui/unreachable-code.rs
+++ b/tests/ui/unreachable-code.rs
@@ -2,25 +2,32 @@
 
 #![allow(unused_must_use)]
 #![allow(dead_code)]
-
 #![allow(path_statements)]
 #![allow(unreachable_code)]
 #![allow(unused_variables)]
+#![feature(if_let_guard)]
 
-fn id(x: bool) -> bool { x }
+fn id(x: bool) -> bool {
+    x
+}
 
 fn call_id() {
     let c = panic!();
     id(c);
 }
 
-fn call_id_2() { id(true) && id(return); }
+fn call_id_2() {
+    id(true) && id(return);
+}
 
-fn call_id_3() { id(return) && id(return); }
+fn call_id_3() {
+    id(return) && id(return);
+}
 
 fn ret_guard() {
     match 2 {
       x if (return) => { x; }
+      x if let true = return => { x; }
       _ => {}
     }
 }
diff --git a/tests/ui/unsafe/edition-2024-unsafe_op_in_unsafe_fn.rs b/tests/ui/unsafe/edition-2024-unsafe_op_in_unsafe_fn.rs
new file mode 100644
index 00000000000..a192f3445f7
--- /dev/null
+++ b/tests/ui/unsafe/edition-2024-unsafe_op_in_unsafe_fn.rs
@@ -0,0 +1,17 @@
+// edition: 2024
+// compile-flags: -Zunstable-options
+// check-pass
+
+#![crate_type = "lib"]
+
+#![deny(unused_unsafe)]
+
+unsafe fn unsf() {}
+
+unsafe fn foo() {
+    unsf();
+    //~^ WARN call to unsafe function is unsafe and requires unsafe block
+
+    // no unused_unsafe
+    unsafe { unsf(); }
+}
diff --git a/tests/ui/unsafe/edition-2024-unsafe_op_in_unsafe_fn.stderr b/tests/ui/unsafe/edition-2024-unsafe_op_in_unsafe_fn.stderr
new file mode 100644
index 00000000000..fbc621f4d0e
--- /dev/null
+++ b/tests/ui/unsafe/edition-2024-unsafe_op_in_unsafe_fn.stderr
@@ -0,0 +1,16 @@
+warning: call to unsafe function is unsafe and requires unsafe block (error E0133)
+  --> $DIR/edition-2024-unsafe_op_in_unsafe_fn.rs:12:5
+   |
+LL |     unsf();
+   |     ^^^^^^ call to unsafe function
+   |
+   = note: consult the function's documentation for information on how to avoid undefined behavior
+note: an unsafe function restricts its caller, but its body is safe by default
+  --> $DIR/edition-2024-unsafe_op_in_unsafe_fn.rs:11:1
+   |
+LL | unsafe fn foo() {
+   | ^^^^^^^^^^^^^^^
+   = note: `#[warn(unsafe_op_in_unsafe_fn)]` on by default
+
+warning: 1 warning emitted
+
diff --git a/tests/ui/unsized/issue-115809.rs b/tests/ui/unsized/issue-115809.rs
new file mode 100644
index 00000000000..ff25365ea50
--- /dev/null
+++ b/tests/ui/unsized/issue-115809.rs
@@ -0,0 +1,13 @@
+// compile-flags: --emit=link -Zmir-opt-level=2 -Zpolymorphize=on
+
+fn foo<T>() {
+    let a: [i32; 0] = [];
+    match [a[..]] {
+        //~^ ERROR cannot move a value of type `[i32]
+        //~| ERROR cannot move out of type `[i32]`, a non-copy slice
+        [[x]] => {}
+        _ => (),
+    }
+}
+
+fn main() {}
diff --git a/tests/ui/unsized/issue-115809.stderr b/tests/ui/unsized/issue-115809.stderr
new file mode 100644
index 00000000000..a92554b79b9
--- /dev/null
+++ b/tests/ui/unsized/issue-115809.stderr
@@ -0,0 +1,19 @@
+error[E0161]: cannot move a value of type `[i32]`
+  --> $DIR/issue-115809.rs:5:12
+   |
+LL |     match [a[..]] {
+   |            ^^^^^ the size of `[i32]` cannot be statically determined
+
+error[E0508]: cannot move out of type `[i32]`, a non-copy slice
+  --> $DIR/issue-115809.rs:5:12
+   |
+LL |     match [a[..]] {
+   |            ^^^^^
+   |            |
+   |            cannot move out of here
+   |            move occurs because value has type `[i32]`, which does not implement the `Copy` trait
+
+error: aborting due to 2 previous errors
+
+Some errors have detailed explanations: E0161, E0508.
+For more information about an error, try `rustc --explain E0161`.
diff --git a/tests/ui/unsized/issue-75707.stderr b/tests/ui/unsized/issue-75707.stderr
index 97618ed05ed..aa7f9c78fa8 100644
--- a/tests/ui/unsized/issue-75707.stderr
+++ b/tests/ui/unsized/issue-75707.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `MyCall: Callback` is not satisfied
 LL |     f::<dyn Processing<Call = MyCall>>();
    |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Callback` is not implemented for `MyCall`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-75707.rs:1:1
+   |
+LL | pub trait Callback {
+   | ^^^^^^^^^^^^^^^^^^
 note: required by a bound in `f`
   --> $DIR/issue-75707.rs:9:9
    |
diff --git a/tests/ui/wf/hir-wf-canonicalized.stderr b/tests/ui/wf/hir-wf-canonicalized.stderr
index 9fd0f9c81eb..21122e37da5 100644
--- a/tests/ui/wf/hir-wf-canonicalized.stderr
+++ b/tests/ui/wf/hir-wf-canonicalized.stderr
@@ -3,12 +3,24 @@ error[E0277]: the trait bound `Bar<'a, T>: Foo` is not satisfied
    |
 LL |     callback: Box<dyn Callback<dyn Callback<Bar<'a, T>>>>,
    |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `Bar<'a, T>`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/hir-wf-canonicalized.rs:3:1
+   |
+LL | trait Foo {
+   | ^^^^^^^^^
 
 error[E0277]: the trait bound `(dyn Callback<Bar<'a, T>, for<'b, 'c, 'd> Output = ()> + 'static): Foo` is not satisfied
   --> $DIR/hir-wf-canonicalized.rs:10:15
    |
 LL |     callback: Box<dyn Callback<dyn Callback<Bar<'a, T>>>>,
    |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `(dyn Callback<Bar<'a, T>, for<'b, 'c, 'd> Output = ()> + 'static)`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/hir-wf-canonicalized.rs:3:1
+   |
+LL | trait Foo {
+   | ^^^^^^^^^
 
 error[E0277]: the size for values of type `(dyn Callback<Bar<'a, T>, for<'b, 'c, 'd> Output = ()> + 'static)` cannot be known at compilation time
   --> $DIR/hir-wf-canonicalized.rs:10:15
diff --git a/tests/ui/wf/issue-95665.stderr b/tests/ui/wf/issue-95665.stderr
index b1cda59a916..f80cd41a4c2 100644
--- a/tests/ui/wf/issue-95665.stderr
+++ b/tests/ui/wf/issue-95665.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `u8: Trait` is not satisfied
 LL |     static VAR: Struct<u8>;
    |                 ^^^^^^^^^^ the trait `Trait` is not implemented for `u8`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/issue-95665.rs:4:1
+   |
+LL | pub trait Trait: {}
+   | ^^^^^^^^^^^^^^^
 note: required by a bound in `Struct`
   --> $DIR/issue-95665.rs:6:22
    |
diff --git a/tests/ui/wf/wf-complex-assoc-type.stderr b/tests/ui/wf/wf-complex-assoc-type.stderr
index ef613e3132d..6a623bec815 100644
--- a/tests/ui/wf/wf-complex-assoc-type.stderr
+++ b/tests/ui/wf/wf-complex-assoc-type.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `bool: MyTrait` is not satisfied
 LL |     type MyItem = Option<((AssertMyTrait<bool>, u8))>;
    |                            ^^^^^^^^^^^^^^^^^^^ the trait `MyTrait` is not implemented for `bool`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/wf-complex-assoc-type.rs:1:1
+   |
+LL | trait MyTrait {}
+   | ^^^^^^^^^^^^^
 note: required by a bound in `AssertMyTrait`
   --> $DIR/wf-complex-assoc-type.rs:2:25
    |
diff --git a/tests/ui/wf/wf-foreign-fn-decl-ret.stderr b/tests/ui/wf/wf-foreign-fn-decl-ret.stderr
index b03023b5fd1..0e93601043a 100644
--- a/tests/ui/wf/wf-foreign-fn-decl-ret.stderr
+++ b/tests/ui/wf/wf-foreign-fn-decl-ret.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): Foo` is not satisfied
    |
 LL |     pub fn lint_me() -> <() as Foo>::Assoc;
    |                         ^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `()`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/wf-foreign-fn-decl-ret.rs:6:1
+   |
+LL | pub trait Foo {
+   | ^^^^^^^^^^^^^
 
 error[E0277]: the trait bound `u32: Unsatisfied` is not satisfied
   --> $DIR/wf-foreign-fn-decl-ret.rs:14:32
@@ -10,6 +16,11 @@ error[E0277]: the trait bound `u32: Unsatisfied` is not satisfied
 LL |     pub fn lint_me_aswell() -> Bar<u32>;
    |                                ^^^^^^^^ the trait `Unsatisfied` is not implemented for `u32`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/wf-foreign-fn-decl-ret.rs:1:1
+   |
+LL | pub trait Unsatisfied {}
+   | ^^^^^^^^^^^^^^^^^^^^^
 note: required by a bound in `Bar`
   --> $DIR/wf-foreign-fn-decl-ret.rs:4:19
    |
diff --git a/tests/ui/wf/wf-packed-on-proj-of-type-as-unimpl-trait.stderr b/tests/ui/wf/wf-packed-on-proj-of-type-as-unimpl-trait.stderr
index e460cdcd3f3..52f46562c37 100644
--- a/tests/ui/wf/wf-packed-on-proj-of-type-as-unimpl-trait.stderr
+++ b/tests/ui/wf/wf-packed-on-proj-of-type-as-unimpl-trait.stderr
@@ -3,6 +3,12 @@ error[E0277]: the trait bound `DefaultAllocator: Allocator` is not satisfied
    |
 LL | struct Foo(Matrix<<DefaultAllocator as Allocator>::Buffer>);
    |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Allocator` is not implemented for `DefaultAllocator`
+   |
+help: this trait has no implementations, consider adding one
+  --> $DIR/wf-packed-on-proj-of-type-as-unimpl-trait.rs:23:1
+   |
+LL | pub trait Allocator { type Buffer; }
+   | ^^^^^^^^^^^^^^^^^^^
 
 error: aborting due to previous error
 
diff --git a/tests/ui/where-clauses/higher-ranked-fn-type.quiet.stderr b/tests/ui/where-clauses/higher-ranked-fn-type.quiet.stderr
index 191a8ca8ebc..29b36f44a4d 100644
--- a/tests/ui/where-clauses/higher-ranked-fn-type.quiet.stderr
+++ b/tests/ui/where-clauses/higher-ranked-fn-type.quiet.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `for<'b> fn(&'b ()): Foo` is not satisfied
 LL |     called()
    |     ^^^^^^ the trait `for<'b> Foo` is not implemented for `fn(&'b ())`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/higher-ranked-fn-type.rs:6:1
+   |
+LL | trait Foo {
+   | ^^^^^^^^^
 note: required by a bound in `called`
   --> $DIR/higher-ranked-fn-type.rs:12:25
    |
diff --git a/tests/ui/where-clauses/higher-ranked-fn-type.verbose.stderr b/tests/ui/where-clauses/higher-ranked-fn-type.verbose.stderr
index ce409f627be..54afeaa7eda 100644
--- a/tests/ui/where-clauses/higher-ranked-fn-type.verbose.stderr
+++ b/tests/ui/where-clauses/higher-ranked-fn-type.verbose.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `for<Region(BrNamed(DefId(0:6 ~ higher_ranked_fn_t
 LL |     called()
    |     ^^^^^^ the trait `for<Region(BrNamed(DefId(0:6 ~ higher_ranked_fn_type[9e51]::called::'b), 'b))> Foo` is not implemented for `fn(&ReLateBound(DebruijnIndex(1), BoundRegion { var: 0, kind: BrNamed(DefId(0:6 ~ higher_ranked_fn_type[9e51]::called::'b), 'b) }) ())`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/higher-ranked-fn-type.rs:6:1
+   |
+LL | trait Foo {
+   | ^^^^^^^^^
 note: required by a bound in `called`
   --> $DIR/higher-ranked-fn-type.rs:12:25
    |
diff --git a/tests/ui/where-clauses/where-clause-method-substituion.stderr b/tests/ui/where-clauses/where-clause-method-substituion.stderr
index 8c47ed6d431..2f3b615a13b 100644
--- a/tests/ui/where-clauses/where-clause-method-substituion.stderr
+++ b/tests/ui/where-clauses/where-clause-method-substituion.stderr
@@ -4,6 +4,11 @@ error[E0277]: the trait bound `X: Foo<X>` is not satisfied
 LL |     1.method::<X>();
    |                ^ the trait `Foo<X>` is not implemented for `X`
    |
+help: this trait has no implementations, consider adding one
+  --> $DIR/where-clause-method-substituion.rs:1:1
+   |
+LL | trait Foo<T> {
+   | ^^^^^^^^^^^^
 note: required by a bound in `Bar::method`
   --> $DIR/where-clause-method-substituion.rs:6:34
    |