]> git.lizzy.rs Git - rust.git/commitdiff
Rollup merge of #100814 - gabrielBusta:port_trait_selection_diagnostics, r=davidtwco
authorMatthias Krüger <matthias.krueger@famsik.de>
Fri, 2 Sep 2022 16:22:00 +0000 (18:22 +0200)
committerGitHub <noreply@github.com>
Fri, 2 Sep 2022 16:22:00 +0000 (18:22 +0200)
 Porting 'compiler/rustc_trait_selection' to translatable diagnostics - Part 1

``@rustbot`` label +A-translation

r? rust-lang/diagnostics
cc #100717

310 files changed:
.gitignore
Cargo.lock
compiler/rustc_ast/src/lib.rs
compiler/rustc_ast/src/util/literal.rs
compiler/rustc_ast_lowering/src/index.rs
compiler/rustc_ast_lowering/src/lib.rs
compiler/rustc_ast_lowering/src/path.rs
compiler/rustc_ast_passes/src/feature_gate.rs
compiler/rustc_ast_passes/src/lib.rs
compiler/rustc_borrowck/src/diagnostics/outlives_suggestion.rs
compiler/rustc_borrowck/src/diagnostics/region_errors.rs
compiler/rustc_borrowck/src/diagnostics/region_name.rs
compiler/rustc_borrowck/src/region_infer/mod.rs
compiler/rustc_borrowck/src/region_infer/opaque_types.rs
compiler/rustc_borrowck/src/universal_regions.rs
compiler/rustc_builtin_macros/src/lib.rs
compiler/rustc_builtin_macros/src/test.rs
compiler/rustc_builtin_macros/src/test_harness.rs
compiler/rustc_codegen_llvm/src/asm.rs
compiler/rustc_codegen_llvm/src/back/archive.rs
compiler/rustc_codegen_llvm/src/back/lto.rs
compiler/rustc_codegen_llvm/src/back/write.rs
compiler/rustc_codegen_llvm/src/builder.rs
compiler/rustc_codegen_llvm/src/callee.rs
compiler/rustc_codegen_llvm/src/common.rs
compiler/rustc_codegen_llvm/src/consts.rs
compiler/rustc_codegen_llvm/src/coverageinfo/mapgen.rs
compiler/rustc_codegen_llvm/src/coverageinfo/mod.rs
compiler/rustc_codegen_llvm/src/debuginfo/metadata.rs
compiler/rustc_codegen_llvm/src/debuginfo/mod.rs
compiler/rustc_codegen_llvm/src/debuginfo/utils.rs
compiler/rustc_codegen_llvm/src/declare.rs
compiler/rustc_codegen_llvm/src/lib.rs
compiler/rustc_codegen_llvm/src/llvm_util.rs
compiler/rustc_codegen_llvm/src/mono_item.rs
compiler/rustc_codegen_llvm/src/type_of.rs
compiler/rustc_codegen_ssa/src/back/link.rs
compiler/rustc_codegen_ssa/src/back/linker.rs
compiler/rustc_const_eval/src/const_eval/eval_queries.rs
compiler/rustc_const_eval/src/const_eval/valtrees.rs
compiler/rustc_const_eval/src/interpret/intern.rs
compiler/rustc_const_eval/src/transform/validate.rs
compiler/rustc_driver/Cargo.toml
compiler/rustc_error_messages/locales/en-US/privacy.ftl
compiler/rustc_error_messages/src/lib.rs
compiler/rustc_errors/src/diagnostic_builder.rs
compiler/rustc_errors/src/emitter.rs
compiler/rustc_expand/src/lib.rs
compiler/rustc_expand/src/mbe/macro_rules.rs
compiler/rustc_feature/src/builtin_attrs.rs
compiler/rustc_hir/src/definitions.rs
compiler/rustc_hir/src/lib.rs
compiler/rustc_infer/src/infer/combine.rs
compiler/rustc_infer/src/infer/error_reporting/mod.rs
compiler/rustc_infer/src/infer/higher_ranked/mod.rs
compiler/rustc_infer/src/infer/lexical_region_resolve/mod.rs
compiler/rustc_infer/src/infer/nll_relate/mod.rs
compiler/rustc_infer/src/infer/opaque_types.rs
compiler/rustc_infer/src/infer/opaque_types/table.rs
compiler/rustc_infer/src/infer/outlives/mod.rs
compiler/rustc_infer/src/infer/outlives/obligations.rs
compiler/rustc_infer/src/infer/outlives/test_type_match.rs
compiler/rustc_interface/src/interface.rs
compiler/rustc_interface/src/lib.rs
compiler/rustc_interface/src/passes.rs
compiler/rustc_interface/src/queries.rs
compiler/rustc_interface/src/tests.rs
compiler/rustc_interface/src/util.rs
compiler/rustc_lint/src/builtin.rs
compiler/rustc_lint/src/context.rs
compiler/rustc_lint/src/early.rs
compiler/rustc_lint/src/internal.rs
compiler/rustc_lint/src/late.rs
compiler/rustc_lint/src/let_underscore.rs [new file with mode: 0644]
compiler/rustc_lint/src/levels.rs
compiler/rustc_lint/src/lib.rs
compiler/rustc_lint/src/types.rs
compiler/rustc_macros/src/diagnostics/subdiagnostic.rs
compiler/rustc_metadata/src/creader.rs
compiler/rustc_metadata/src/dependency_format.rs
compiler/rustc_metadata/src/lib.rs
compiler/rustc_metadata/src/locator.rs
compiler/rustc_metadata/src/rmeta/decoder.rs
compiler/rustc_metadata/src/rmeta/decoder/cstore_impl.rs
compiler/rustc_metadata/src/rmeta/encoder.rs
compiler/rustc_metadata/src/rmeta/mod.rs
compiler/rustc_metadata/src/rmeta/table.rs
compiler/rustc_middle/src/arena.rs
compiler/rustc_middle/src/dep_graph/dep_node.rs
compiler/rustc_middle/src/mir/mod.rs
compiler/rustc_middle/src/ty/consts.rs
compiler/rustc_middle/src/ty/context.rs
compiler/rustc_middle/src/ty/fold.rs
compiler/rustc_middle/src/ty/normalize_erasing_regions.rs
compiler/rustc_middle/src/ty/parameterized.rs
compiler/rustc_middle/src/ty/trait_def.rs
compiler/rustc_middle/src/ty/util.rs
compiler/rustc_middle/src/ty/visit.rs
compiler/rustc_mir_build/src/build/matches/mod.rs
compiler/rustc_mir_build/src/thir/cx/expr.rs
compiler/rustc_mir_build/src/thir/cx/mod.rs
compiler/rustc_mir_build/src/thir/pattern/const_to_pat.rs
compiler/rustc_mir_build/src/thir/pattern/usefulness.rs
compiler/rustc_monomorphize/src/collector.rs
compiler/rustc_monomorphize/src/polymorphize.rs
compiler/rustc_parse/src/lexer/mod.rs
compiler/rustc_parse/src/lexer/unescape_error_reporting.rs
compiler/rustc_parse/src/parser/attr.rs
compiler/rustc_parse/src/parser/diagnostics.rs
compiler/rustc_parse/src/parser/item.rs
compiler/rustc_parse/src/parser/mod.rs
compiler/rustc_parse/src/parser/path.rs
compiler/rustc_passes/src/liveness.rs
compiler/rustc_privacy/src/errors.rs
compiler/rustc_privacy/src/lib.rs
compiler/rustc_query_impl/src/plumbing.rs
compiler/rustc_query_system/src/query/config.rs
compiler/rustc_resolve/src/access_levels.rs
compiler/rustc_resolve/src/build_reduced_graph.rs
compiler/rustc_resolve/src/def_collector.rs
compiler/rustc_resolve/src/diagnostics.rs
compiler/rustc_resolve/src/ident.rs
compiler/rustc_resolve/src/imports.rs
compiler/rustc_resolve/src/late.rs
compiler/rustc_resolve/src/late/diagnostics.rs
compiler/rustc_resolve/src/late/lifetimes.rs
compiler/rustc_resolve/src/lib.rs
compiler/rustc_save_analysis/src/dump_visitor.rs
compiler/rustc_save_analysis/src/lib.rs
compiler/rustc_session/src/cgu_reuse_tracker.rs
compiler/rustc_session/src/config.rs
compiler/rustc_session/src/filesearch.rs
compiler/rustc_session/src/lib.rs
compiler/rustc_session/src/options.rs
compiler/rustc_span/src/hygiene.rs
compiler/rustc_span/src/lib.rs
compiler/rustc_span/src/source_map.rs
compiler/rustc_span/src/symbol.rs
compiler/rustc_symbol_mangling/src/legacy.rs
compiler/rustc_symbol_mangling/src/lib.rs
compiler/rustc_target/src/spec/asmjs_unknown_emscripten.rs
compiler/rustc_target/src/spec/bpf_base.rs
compiler/rustc_target/src/spec/l4re_base.rs
compiler/rustc_target/src/spec/mod.rs
compiler/rustc_target/src/spec/nvptx64_nvidia_cuda.rs
compiler/rustc_target/src/spec/tests/tests_impl.rs
compiler/rustc_target/src/spec/wasm32_unknown_emscripten.rs
compiler/rustc_trait_selection/src/traits/codegen.rs
compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs
compiler/rustc_trait_selection/src/traits/fulfill.rs
compiler/rustc_trait_selection/src/traits/project.rs
compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs
compiler/rustc_trait_selection/src/traits/select/mod.rs
compiler/rustc_trait_selection/src/traits/wf.rs
compiler/rustc_transmute/src/layout/tree.rs
compiler/rustc_transmute/src/maybe_transmutable/mod.rs
compiler/rustc_transmute/src/maybe_transmutable/query_context.rs
compiler/rustc_ty_utils/src/instance.rs
compiler/rustc_ty_utils/src/ty.rs
compiler/rustc_typeck/src/astconv/mod.rs
compiler/rustc_typeck/src/check/_match.rs
compiler/rustc_typeck/src/check/closure.rs
compiler/rustc_typeck/src/check/compare_method.rs
compiler/rustc_typeck/src/check/demand.rs
compiler/rustc_typeck/src/check/fn_ctxt/_impl.rs
compiler/rustc_typeck/src/check/generator_interior.rs
compiler/rustc_typeck/src/check/method/mod.rs
compiler/rustc_typeck/src/check/method/probe.rs
compiler/rustc_typeck/src/check/mod.rs
compiler/rustc_typeck/src/check/wfcheck.rs
compiler/rustc_typeck/src/collect/type_of.rs
config.toml.example
library/core/src/any.rs
library/core/src/num/nonzero.rs
library/core/tests/any.rs
library/std/src/io/stdio.rs
library/std/src/sync/mutex.rs
library/std/src/sync/rwlock.rs
src/bootstrap/bootstrap.py
src/bootstrap/compile.rs
src/bootstrap/config.rs
src/bootstrap/dist.rs
src/bootstrap/doc.rs
src/bootstrap/lib.rs
src/ci/docker/host-x86_64/arm-android/Dockerfile
src/ci/docker/host-x86_64/dist-android/Dockerfile
src/ci/docker/scripts/android-base-apt-get.sh
src/doc/rustc/src/platform-support/armv4t-none-eabi.md [new file with mode: 0644]
src/doc/rustc/src/platform-support/armv4t_none_eabi.md [deleted file]
src/doc/rustc/src/platform-support/fuchsia.md
src/librustdoc/html/format.rs
src/librustdoc/html/render/mod.rs
src/librustdoc/html/static/css/rustdoc.css
src/librustdoc/passes/collect_intra_doc_links.rs
src/librustdoc/passes/propagate_doc_cfg.rs
src/librustdoc/passes/stripper.rs
src/test/mir-opt/early_otherwise_branch_68867.rs
src/test/mir-opt/early_otherwise_branch_68867.try_sum.EarlyOtherwiseBranch.before-SimplifyConstCondition-final.after.diff [deleted file]
src/test/mir-opt/early_otherwise_branch_68867.try_sum.EarlyOtherwiseBranch.diff
src/test/mir-opt/issue-73223.rs
src/test/mir-opt/issue_73223.main.PreCodegen.32bit.diff [deleted file]
src/test/mir-opt/issue_73223.main.PreCodegen.64bit.diff [deleted file]
src/test/mir-opt/lower_array_len.array_bound.InstCombine.diff [deleted file]
src/test/mir-opt/lower_array_len.array_bound.SimplifyLocals.diff [deleted file]
src/test/mir-opt/lower_array_len.array_bound_mut.InstCombine.diff [deleted file]
src/test/mir-opt/lower_array_len.array_bound_mut.SimplifyLocals.diff [deleted file]
src/test/mir-opt/lower_array_len.array_len.InstCombine.diff [deleted file]
src/test/mir-opt/lower_array_len.array_len.SimplifyLocals.diff [deleted file]
src/test/mir-opt/lower_array_len.array_len_by_value.InstCombine.diff [deleted file]
src/test/mir-opt/lower_array_len.array_len_by_value.SimplifyLocals.diff [deleted file]
src/test/mir-opt/lower_array_len.rs
src/test/mir-opt/lower_array_len_e2e.array_bound.PreCodegen.after.mir [new file with mode: 0644]
src/test/mir-opt/lower_array_len_e2e.array_bound_mut.PreCodegen.after.mir [new file with mode: 0644]
src/test/mir-opt/lower_array_len_e2e.array_len.PreCodegen.after.mir [new file with mode: 0644]
src/test/mir-opt/lower_array_len_e2e.array_len_by_value.PreCodegen.after.mir [new file with mode: 0644]
src/test/mir-opt/lower_array_len_e2e.rs [new file with mode: 0644]
src/test/mir-opt/lower_intrinsics.align_of.LowerIntrinsics.diff
src/test/mir-opt/lower_intrinsics.discriminant.LowerIntrinsics.diff
src/test/mir-opt/lower_intrinsics.f_u64.PreCodegen.before.mir [deleted file]
src/test/mir-opt/lower_intrinsics.f_unit.PreCodegen.before.mir [deleted file]
src/test/mir-opt/lower_intrinsics.forget.LowerIntrinsics.diff
src/test/mir-opt/lower_intrinsics.non_const.LowerIntrinsics.diff
src/test/mir-opt/lower_intrinsics.rs
src/test/mir-opt/lower_intrinsics.size_of.LowerIntrinsics.diff
src/test/mir-opt/lower_intrinsics.unreachable.LowerIntrinsics.diff
src/test/mir-opt/lower_intrinsics.wrapping.LowerIntrinsics.diff
src/test/mir-opt/lower_intrinsics_e2e.f_u64.PreCodegen.after.mir [new file with mode: 0644]
src/test/mir-opt/lower_intrinsics_e2e.f_unit.PreCodegen.after.mir [new file with mode: 0644]
src/test/mir-opt/lower_intrinsics_e2e.rs [new file with mode: 0644]
src/test/mir-opt/matches_reduce_branches.bar.MatchBranchSimplification.32bit.diff
src/test/mir-opt/matches_reduce_branches.bar.MatchBranchSimplification.64bit.diff
src/test/mir-opt/matches_reduce_branches.foo.MatchBranchSimplification.32bit.diff
src/test/mir-opt/matches_reduce_branches.foo.MatchBranchSimplification.64bit.diff
src/test/mir-opt/matches_reduce_branches.foo.PreCodegen.before.32bit.mir [deleted file]
src/test/mir-opt/matches_reduce_branches.foo.PreCodegen.before.64bit.mir [deleted file]
src/test/mir-opt/matches_reduce_branches.match_nested_if.MatchBranchSimplification.32bit.diff
src/test/mir-opt/matches_reduce_branches.match_nested_if.MatchBranchSimplification.64bit.diff
src/test/mir-opt/matches_reduce_branches.rs
src/test/mir-opt/matches_u8.rs
src/test/mir-opt/separate_const_switch.identity.SeparateConstSwitch.diff
src/test/mir-opt/separate_const_switch.rs
src/test/mir-opt/simplify-arm-identity.rs
src/test/mir-opt/simplify-arm.rs
src/test/mir-opt/simplify-locals-removes-unused-discriminant-reads.rs
src/test/mir-opt/simplify_arm.id.SimplifyArmIdentity.diff [deleted file]
src/test/mir-opt/simplify_arm.id.SimplifyBranchSame.diff [deleted file]
src/test/mir-opt/simplify_arm.id_result.SimplifyArmIdentity.diff [deleted file]
src/test/mir-opt/simplify_arm.id_result.SimplifyBranchSame.diff [deleted file]
src/test/mir-opt/simplify_arm_identity.main.SimplifyArmIdentity.32bit.diff [deleted file]
src/test/mir-opt/simplify_arm_identity.main.SimplifyArmIdentity.64bit.diff [deleted file]
src/test/mir-opt/simplify_locals_removes_unused_discriminant_reads.map.SimplifyLocals.32bit.diff
src/test/mir-opt/simplify_locals_removes_unused_discriminant_reads.map.SimplifyLocals.64bit.diff
src/test/mir-opt/simplify_try.rs [deleted file]
src/test/mir-opt/try_identity_e2e.new.PreCodegen.after.mir [new file with mode: 0644]
src/test/mir-opt/try_identity_e2e.old.PreCodegen.after.mir [new file with mode: 0644]
src/test/mir-opt/try_identity_e2e.rs [new file with mode: 0644]
src/test/rustdoc-gui/src/lib2/lib.rs
src/test/rustdoc-gui/where-whitespace.goml [new file with mode: 0644]
src/test/rustdoc/const-generics/const-generics-docs.rs
src/test/rustdoc/doc_auto_cfg_nested_impl.rs [new file with mode: 0644]
src/test/rustdoc/generic-associated-types/gats.rs
src/test/rustdoc/higher-ranked-trait-bounds.rs
src/test/rustdoc/impl-parts.rs
src/test/rustdoc/issue-20727-4.rs
src/test/rustdoc/issue-21801.rs
src/test/rustdoc/issue-29503.rs
src/test/rustdoc/issue-34928.rs
src/test/rustdoc/issue-50159.rs
src/test/rustdoc/issue-51236.rs
src/test/rustdoc/issue-54705.rs
src/test/rustdoc/issue-98697.rs
src/test/rustdoc/primitive-slice-auto-trait.rs
src/test/rustdoc/synthetic_auto/basic.rs
src/test/rustdoc/synthetic_auto/complex.rs
src/test/rustdoc/synthetic_auto/lifetimes.rs
src/test/rustdoc/synthetic_auto/manual.rs
src/test/rustdoc/synthetic_auto/nested.rs
src/test/rustdoc/synthetic_auto/no-redundancy.rs
src/test/rustdoc/synthetic_auto/project.rs
src/test/rustdoc/synthetic_auto/self-referential.rs
src/test/rustdoc/synthetic_auto/static-region.rs
src/test/rustdoc/where-clause-order.rs
src/test/rustdoc/where.rs
src/test/ui-fulldeps/session-diagnostic/diagnostic-derive.rs
src/test/ui-fulldeps/session-diagnostic/diagnostic-derive.stderr
src/test/ui-fulldeps/session-diagnostic/subdiagnostic-derive.rs
src/test/ui-fulldeps/session-diagnostic/subdiagnostic-derive.stderr
src/test/ui/borrowck/do-not-suggest-adding-move-when-closure-is-already-marked-as-move.rs [new file with mode: 0644]
src/test/ui/borrowck/do-not-suggest-adding-move-when-closure-is-already-marked-as-move.stderr [new file with mode: 0644]
src/test/ui/lint/let_underscore/let_underscore_drop.rs [new file with mode: 0644]
src/test/ui/lint/let_underscore/let_underscore_drop.stderr [new file with mode: 0644]
src/test/ui/lint/let_underscore/let_underscore_lock.rs [new file with mode: 0644]
src/test/ui/lint/let_underscore/let_underscore_lock.stderr [new file with mode: 0644]
src/test/ui/mir/issue-99866.rs [new file with mode: 0644]
src/test/ui/modules/auxiliary/dummy_lib.rs [new file with mode: 0644]
src/test/ui/modules/special_module_name.rs [new file with mode: 0644]
src/test/ui/modules/special_module_name.stderr [new file with mode: 0644]
src/test/ui/modules/special_module_name_ignore.rs [new file with mode: 0644]
src/test/ui/privacy/access_levels.rs [new file with mode: 0644]
src/test/ui/privacy/access_levels.stderr [new file with mode: 0644]
src/tools/error_index_generator/Cargo.toml
src/tools/error_index_generator/book_config.toml [new file with mode: 0644]
src/tools/error_index_generator/error-index.css [new file with mode: 0644]
src/tools/error_index_generator/error-index.js [new file with mode: 0644]
src/tools/error_index_generator/main.rs
src/tools/error_index_generator/redirect.js [new file with mode: 0644]
src/tools/lint-docs/src/groups.rs
src/tools/lld-wrapper/src/main.rs
src/tools/miri
triagebot.toml

index b16fb6341c2e50a2f37f04e563017a588365a4d7..37972532b361429f281f8d52f34ea4d1ca621540 100644 (file)
@@ -46,6 +46,7 @@ no_llvm_build
 /dist/
 /unicode-downloads
 /target
+/src/bootstrap/target
 /src/tools/x/target
 # Created by default with `src/ci/docker/run.sh`
 /obj/
index f83678f0ca67100de1f50a2e5387e0ae25d918be..97a64feca1b7b84101854163ca7b2a0996c3953f 100644 (file)
@@ -1036,16 +1036,6 @@ dependencies = [
  "quote",
 ]
 
-[[package]]
-name = "ctor"
-version = "0.1.22"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "f877be4f7c9f246b183111634f75baa039715e3f46ce860677d3b19a69fb229c"
-dependencies = [
- "quote",
- "syn",
-]
-
 [[package]]
 name = "curl"
 version = "0.4.43"
@@ -1269,7 +1259,7 @@ dependencies = [
 name = "error_index_generator"
 version = "0.0.0"
 dependencies = [
- "rustdoc",
+ "mdbook",
 ]
 
 [[package]]
@@ -2294,6 +2284,7 @@ dependencies = [
  "getrandom 0.2.0",
  "lazy_static",
  "libc",
+ "libloading",
  "log",
  "measureme",
  "rand 0.8.5",
@@ -2472,15 +2463,6 @@ version = "6.0.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "8e22443d1643a904602595ba1cd8f7d896afe56d26712531c5ff73a15b2fbf64"
 
-[[package]]
-name = "output_vt100"
-version = "0.1.3"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "628223faebab4e3e40667ee0b2336d34a5b960ff60ea743ddfdbcf7770bcfb66"
-dependencies = [
- "winapi",
-]
-
 [[package]]
 name = "owo-colors"
 version = "3.4.0"
@@ -2721,18 +2703,6 @@ version = "0.1.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "925383efa346730478fb4838dbe9137d2a47675ad789c546d150a6e1dd4ab31c"
 
-[[package]]
-name = "pretty_assertions"
-version = "1.2.1"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "c89f989ac94207d048d92db058e4f6ec7342b0971fc58d1271ca148b799b3563"
-dependencies = [
- "ansi_term",
- "ctor",
- "diff",
- "output_vt100",
-]
-
 [[package]]
 name = "pretty_env_logger"
 version = "0.4.0"
@@ -5135,14 +5105,16 @@ checksum = "56dee185309b50d1f11bfedef0fe6d036842e3fb77413abef29f8f8d1c5d4c1c"
 
 [[package]]
 name = "ui_test"
-version = "0.1.0"
+version = "0.3.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "7d1f546a5883ae78da735bba529ec1116661e2f73582f23920d994dc97da3a22"
 dependencies = [
  "cargo_metadata 0.15.0",
  "color-eyre",
  "colored",
  "crossbeam",
+ "diff",
  "lazy_static",
- "pretty_assertions",
  "regex",
  "rustc_version",
  "serde",
index 27061f300a2b20191e5906ed47ac7a683cfd8aa8..e5435e3a3d4fad4037927e7eaae246f1d8652f7e 100644 (file)
@@ -26,6 +26,9 @@
 #[macro_use]
 extern crate rustc_macros;
 
+#[macro_use]
+extern crate tracing;
+
 pub mod util {
     pub mod classify;
     pub mod comments;
index 69a78d165ef5895ad654b51103bd6efa21f5d016..6a1578498e6894468552c4729ecb0cf2c4b9531e 100644 (file)
@@ -9,7 +9,6 @@
 use rustc_span::Span;
 
 use std::ascii;
-use tracing::debug;
 
 pub enum LitError {
     NotLiteral,
index 2b7431f0990570a004902099db789a36f65cd989..219e1b81d1ea64d3226d9eb93787b1ed2d98fe4d 100644 (file)
@@ -11,8 +11,6 @@
 use rustc_span::source_map::SourceMap;
 use rustc_span::{Span, DUMMY_SP};
 
-use tracing::debug;
-
 /// A visitor that walks over the HIR and collects `Node`s into a HIR map.
 pub(super) struct NodeCollector<'a, 'hir> {
     /// Source map
@@ -31,7 +29,7 @@ pub(super) struct NodeCollector<'a, 'hir> {
     definitions: &'a definitions::Definitions,
 }
 
-#[tracing::instrument(level = "debug", skip(sess, definitions, bodies))]
+#[instrument(level = "debug", skip(sess, definitions, bodies))]
 pub(super) fn index_hir<'hir>(
     sess: &Session,
     definitions: &definitions::Definitions,
@@ -67,7 +65,7 @@ pub(super) fn index_hir<'hir>(
 }
 
 impl<'a, 'hir> NodeCollector<'a, 'hir> {
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn insert(&mut self, span: Span, hir_id: HirId, node: Node<'hir>) {
         debug_assert_eq!(self.owner, hir_id.owner);
         debug_assert_ne!(hir_id.local_id.as_u32(), 0);
@@ -142,7 +140,7 @@ fn visit_param(&mut self, param: &'hir Param<'hir>) {
         });
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn visit_item(&mut self, i: &'hir Item<'hir>) {
         debug_assert_eq!(i.def_id, self.owner);
         self.with_parent(i.hir_id(), |this| {
@@ -156,7 +154,7 @@ fn visit_item(&mut self, i: &'hir Item<'hir>) {
         });
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn visit_foreign_item(&mut self, fi: &'hir ForeignItem<'hir>) {
         debug_assert_eq!(fi.def_id, self.owner);
         self.with_parent(fi.hir_id(), |this| {
@@ -175,7 +173,7 @@ fn visit_const_param_default(&mut self, param: HirId, ct: &'hir AnonConst) {
         })
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn visit_trait_item(&mut self, ti: &'hir TraitItem<'hir>) {
         debug_assert_eq!(ti.def_id, self.owner);
         self.with_parent(ti.hir_id(), |this| {
@@ -183,7 +181,7 @@ fn visit_trait_item(&mut self, ti: &'hir TraitItem<'hir>) {
         });
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn visit_impl_item(&mut self, ii: &'hir ImplItem<'hir>) {
         debug_assert_eq!(ii.def_id, self.owner);
         self.with_parent(ii.hir_id(), |this| {
index a5957e2df2e5f56bdbaa89d4d0504ba1410ad409..9a960356a85f4066f628ea59a101e29c4b6dc306 100644 (file)
@@ -220,7 +220,7 @@ fn decl_macro_kind(&self, def_id: LocalDefId) -> MacroKind {
     /// Panics if no map has been pushed.
     /// Remapping is used when creating lowering `-> impl Trait` return
     /// types to create the resulting opaque type.
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn record_def_id_remap(&mut self, from: LocalDefId, to: LocalDefId) {
         self.generics_def_id_map.last_mut().expect("no map pushed").insert(from, to);
     }
@@ -771,7 +771,7 @@ fn lower_ident(&self, ident: Ident) -> Ident {
     }
 
     /// Converts a lifetime into a new generic parameter.
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn lifetime_res_to_generic_param(
         &mut self,
         ident: Ident,
@@ -815,7 +815,7 @@ fn lifetime_res_to_generic_param(
     /// name resolver owing to lifetime elision; this also populates the resolver's node-id->def-id
     /// map, so that later calls to `opt_node_id_to_def_id` that refer to these extra lifetime
     /// parameters will be successful.
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     #[inline]
     fn lower_lifetime_binder(
         &mut self,
@@ -1385,7 +1385,7 @@ fn lower_ty_direct(&mut self, t: &Ty, itctx: ImplTraitContext) -> hir::Ty<'hir>
     /// added explicitly in the HIR). But this includes all the lifetimes, and we only want to
     /// capture the lifetimes that are referenced in the bounds. Therefore, we add *extra* lifetime parameters
     /// for the lifetimes that get captured (`'x`, in our example above) and reference those.
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn lower_opaque_impl_trait(
         &mut self,
         span: Span,
@@ -1621,7 +1621,7 @@ fn lower_fn_params_to_names(&mut self, decl: &FnDecl) -> &'hir [Ident] {
     // `make_ret_async`: if `Some`, converts `-> T` into `-> impl Future<Output = T>` in the
     //      return type. This is used for `async fn` declarations. The `NodeId` is the ID of the
     //      return type `impl Trait` item.
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn lower_fn_decl(
         &mut self,
         decl: &FnDecl,
@@ -1730,7 +1730,7 @@ fn lower_fn_decl(
     // `output`: unlowered output type (`T` in `-> T`)
     // `fn_def_id`: `DefId` of the parent function (used to create child impl trait definition)
     // `opaque_ty_node_id`: `NodeId` of the opaque `impl Trait` type that should be created
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn lower_async_fn_ret_ty(
         &mut self,
         output: &FnRetTy,
@@ -2013,7 +2013,7 @@ fn lower_lifetime(&mut self, l: &Lifetime) -> hir::Lifetime {
         self.new_named_lifetime(l.id, l.id, span, ident)
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn new_named_lifetime_with_res(
         &mut self,
         id: NodeId,
@@ -2044,7 +2044,7 @@ fn new_named_lifetime_with_res(
         hir::Lifetime { hir_id: self.lower_node_id(id), span: self.lower_span(span), name }
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn new_named_lifetime(
         &mut self,
         id: NodeId,
@@ -2132,7 +2132,7 @@ fn lower_trait_ref(&mut self, p: &TraitRef, itctx: ImplTraitContext) -> hir::Tra
         hir::TraitRef { path, hir_ref_id: self.lower_node_id(p.ref_id) }
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn lower_poly_trait_ref(
         &mut self,
         p: &PolyTraitRef,
index 5874d08a94fe06bac55a516e8abef538f386aa58..897c7215805e0753e784601eb16518b94e9556bc 100644 (file)
@@ -13,7 +13,6 @@
 use rustc_span::{BytePos, Span, DUMMY_SP};
 
 use smallvec::smallvec;
-use tracing::debug;
 
 impl<'a, 'hir> LoweringContext<'a, 'hir> {
     #[instrument(level = "trace", skip(self))]
index 6f7e88eb86f195e074a38cab814758c0f57d54d0..ca5b7a64155157f80c250cd9e8c8e07b9897ebbe 100644 (file)
@@ -11,8 +11,6 @@
 use rustc_span::symbol::sym;
 use rustc_span::Span;
 
-use tracing::debug;
-
 macro_rules! gate_feature_fn {
     ($visitor: expr, $has_feature: expr, $span: expr, $name: expr, $explain: expr, $help: expr) => {{
         let (visitor, has_feature, span, name, explain, help) =
index f282ff251bda181ca8c7f97c961382c1cd1c1b95..af25982e2887bb33656b99017083f8c460d7a619 100644 (file)
@@ -12,6 +12,9 @@
 #![feature(let_else)]
 #![recursion_limit = "256"]
 
+#[macro_use]
+extern crate tracing;
+
 pub mod ast_validation;
 mod errors;
 pub mod feature_gate;
index d359d7efb626801905958a91c983f866105a1fce..35c3df768995a0d2907db1cb174122666596a9cc 100644 (file)
@@ -6,7 +6,6 @@
 use rustc_middle::ty::RegionVid;
 use smallvec::SmallVec;
 use std::collections::BTreeMap;
-use tracing::debug;
 
 use crate::MirBorrowckCtxt;
 
index 00fdf331ca60ce8c270a3ce98ec6a41d35baafa6..082dd86902354843822df54b8cee1b6dd56b63a3 100644 (file)
@@ -902,7 +902,11 @@ fn suggest_move_on_borrowing_closure(&self, diag: &mut Diagnostic) {
             hir::ExprKind::MethodCall(.., args, _) => {
                 // only the first closre parameter of the method. args[0] is MethodCall PathSegment
                 for i in 1..args.len() {
-                    if let hir::ExprKind::Closure(..) = args[i].kind {
+                    if let hir::ExprKind::Closure(hir::Closure {
+                        capture_clause: hir::CaptureBy::Ref,
+                        ..
+                    }) = args[i].kind
+                    {
                         closure_span = Some(args[i].span.shrink_to_lo());
                         break;
                     }
@@ -911,7 +915,11 @@ fn suggest_move_on_borrowing_closure(&self, diag: &mut Diagnostic) {
             hir::ExprKind::Block(blk, _) => {
                 if let Some(ref expr) = blk.expr {
                     // only when the block is a closure
-                    if let hir::ExprKind::Closure(..) = expr.kind {
+                    if let hir::ExprKind::Closure(hir::Closure {
+                        capture_clause: hir::CaptureBy::Ref,
+                        ..
+                    }) = expr.kind
+                    {
                         closure_span = Some(expr.span.shrink_to_lo());
                     }
                 }
@@ -921,7 +929,7 @@ fn suggest_move_on_borrowing_closure(&self, diag: &mut Diagnostic) {
         if let Some(closure_span) = closure_span {
             diag.span_suggestion_verbose(
                 closure_span,
-                format!("consider adding 'move' keyword before the nested closure"),
+                "consider adding 'move' keyword before the nested closure",
                 "move ",
                 Applicability::MaybeIncorrect,
             );
index a87e8bd5ba16fc276183bc1366a121107141dd94..75fde53b6cdecd24452e0293db2118ad598f9620 100644 (file)
@@ -265,7 +265,7 @@ pub(crate) fn give_region_a_name(&self, fr: RegionVid) -> Option<RegionName> {
     /// *user* has a name for. In that case, we'll be able to map
     /// `fr` to a `Region<'tcx>`, and that region will be one of
     /// named variants.
-    #[tracing::instrument(level = "trace", skip(self))]
+    #[instrument(level = "trace", skip(self))]
     fn give_name_from_error_region(&self, fr: RegionVid) -> Option<RegionName> {
         let error_region = self.to_error_region(fr)?;
 
@@ -373,7 +373,7 @@ fn give_name_from_error_region(&self, fr: RegionVid) -> Option<RegionName> {
     ///  | fn foo(x: &u32) { .. }
     ///           ------- fully elaborated type of `x` is `&'1 u32`
     /// ```
-    #[tracing::instrument(level = "trace", skip(self))]
+    #[instrument(level = "trace", skip(self))]
     fn give_name_if_anonymous_region_appears_in_arguments(
         &self,
         fr: RegionVid,
@@ -662,7 +662,7 @@ fn try_match_adt_and_generic_args<'hir>(
     ///  | let x = Some(&22);
     ///        - fully elaborated type of `x` is `Option<&'1 u32>`
     /// ```
-    #[tracing::instrument(level = "trace", skip(self))]
+    #[instrument(level = "trace", skip(self))]
     fn give_name_if_anonymous_region_appears_in_upvars(&self, fr: RegionVid) -> Option<RegionName> {
         let upvar_index = self.regioncx.get_upvar_index_for_region(self.infcx.tcx, fr)?;
         let (upvar_name, upvar_span) = self.regioncx.get_upvar_name_and_span_for_region(
@@ -682,7 +682,7 @@ fn give_name_if_anonymous_region_appears_in_upvars(&self, fr: RegionVid) -> Opti
     /// must be a closure since, in a free fn, such an argument would
     /// have to either also appear in an argument (if using elision)
     /// or be early bound (named, not in argument).
-    #[tracing::instrument(level = "trace", skip(self))]
+    #[instrument(level = "trace", skip(self))]
     fn give_name_if_anonymous_region_appears_in_output(&self, fr: RegionVid) -> Option<RegionName> {
         let tcx = self.infcx.tcx;
         let hir = tcx.hir();
@@ -814,7 +814,7 @@ fn get_future_inner_return_ty(&self, hir_ty: &'tcx hir::Ty<'tcx>) -> &'tcx hir::
         }
     }
 
-    #[tracing::instrument(level = "trace", skip(self))]
+    #[instrument(level = "trace", skip(self))]
     fn give_name_if_anonymous_region_appears_in_yield_ty(
         &self,
         fr: RegionVid,
index f5bd5cd3beaed0ab0006c2ba688a5fc8009f743a..8dc9368a0b994d197943ea914fa19b6578b554dc 100644 (file)
@@ -1139,7 +1139,7 @@ fn non_local_universal_upper_bound(&self, r: RegionVid) -> RegionVid {
     ///   include the CFG anyhow.
     /// - For each `end('x)` element in `'r`, compute the mutual LUB, yielding
     ///   a result `'y`.
-    #[instrument(skip(self), level = "debug")]
+    #[instrument(skip(self), level = "debug", ret)]
     pub(crate) fn universal_upper_bound(&self, r: RegionVid) -> RegionVid {
         debug!(r = %self.region_value_str(r));
 
@@ -1151,8 +1151,6 @@ pub(crate) fn universal_upper_bound(&self, r: RegionVid) -> RegionVid {
             lub = self.universal_region_relations.postdom_upper_bound(lub, ur);
         }
 
-        debug!(?lub);
-
         lub
     }
 
@@ -1333,15 +1331,15 @@ fn eval_equal(&self, r1: RegionVid, r2: RegionVid) -> bool {
     }
 
     // Evaluate whether `sup_region: sub_region`.
-    #[instrument(skip(self), level = "debug")]
+    #[instrument(skip(self), level = "debug", ret)]
     fn eval_outlives(&self, sup_region: RegionVid, sub_region: RegionVid) -> bool {
         debug!(
-            "eval_outlives: sup_region's value = {:?} universal={:?}",
+            "sup_region's value = {:?} universal={:?}",
             self.region_value_str(sup_region),
             self.universal_regions.is_universal_region(sup_region),
         );
         debug!(
-            "eval_outlives: sub_region's value = {:?} universal={:?}",
+            "sub_region's value = {:?} universal={:?}",
             self.region_value_str(sub_region),
             self.universal_regions.is_universal_region(sub_region),
         );
@@ -1354,7 +1352,7 @@ fn eval_outlives(&self, sup_region: RegionVid, sub_region: RegionVid) -> bool {
         // true if `'sup` outlives static.
         if !self.universe_compatible(sub_region_scc, sup_region_scc) {
             debug!(
-                "eval_outlives: sub universe `{sub_region_scc:?}` is not nameable \
+                "sub universe `{sub_region_scc:?}` is not nameable \
                 by super `{sup_region_scc:?}`, promoting to static",
             );
 
@@ -1375,9 +1373,7 @@ fn eval_outlives(&self, sup_region: RegionVid, sub_region: RegionVid) -> bool {
             });
 
         if !universal_outlives {
-            debug!(
-                "eval_outlives: returning false because sub region contains a universal region not present in super"
-            );
+            debug!("sub region contains a universal region not present in super");
             return false;
         }
 
@@ -1386,15 +1382,13 @@ fn eval_outlives(&self, sup_region: RegionVid, sub_region: RegionVid) -> bool {
 
         if self.universal_regions.is_universal_region(sup_region) {
             // Micro-opt: universal regions contain all points.
-            debug!(
-                "eval_outlives: returning true because super is universal and hence contains all points"
-            );
+            debug!("super is universal and hence contains all points");
             return true;
         }
 
-        let result = self.scc_values.contains_points(sup_region_scc, sub_region_scc);
-        debug!("returning {} because of comparison between points in sup/sub", result);
-        result
+        debug!("comparison between points in sup/sub");
+
+        self.scc_values.contains_points(sup_region_scc, sub_region_scc)
     }
 
     /// Once regions have been propagated, this method is used to see
@@ -1971,7 +1965,7 @@ pub(crate) fn find_constraint_paths_between_regions(
     }
 
     /// Finds some region R such that `fr1: R` and `R` is live at `elem`.
-    #[instrument(skip(self), level = "trace")]
+    #[instrument(skip(self), level = "trace", ret)]
     pub(crate) fn find_sub_region_live_at(&self, fr1: RegionVid, elem: Location) -> RegionVid {
         trace!(scc = ?self.constraint_sccs.scc(fr1));
         trace!(universe = ?self.scc_universes[self.constraint_sccs.scc(fr1)]);
index 127cb4e408372e800e9ef7380f04c8ee59cf9e8d..0392367288c40544cad175913f68626a3ca9684d 100644 (file)
@@ -60,7 +60,7 @@ impl<'tcx> RegionInferenceContext<'tcx> {
     /// Calling `universal_upper_bound` for such a region gives `fr_fn_body`,
     /// which has no `external_name` in which case we use `'empty` as the
     /// region to pass to `infer_opaque_definition_from_instantiation`.
-    #[instrument(level = "debug", skip(self, infcx))]
+    #[instrument(level = "debug", skip(self, infcx), ret)]
     pub(crate) fn infer_opaque_types(
         &self,
         infcx: &InferCtxt<'_, 'tcx>,
index 2a7713bc4df3b6d1e8be939ef07799a5c412f820..b9b181681ec4b7495cf63f925799d205cdaff281 100644 (file)
@@ -768,10 +768,9 @@ fn replace_late_bound_regions_with_nll_infer_vars(
         mir_def_id: LocalDefId,
         indices: &mut UniversalRegionIndices<'tcx>,
     ) {
-        debug!("replace_late_bound_regions_with_nll_infer_vars(mir_def_id={:?})", mir_def_id);
         let typeck_root_def_id = self.tcx.typeck_root_def_id(mir_def_id.to_def_id());
         for_each_late_bound_region_defined_on(self.tcx, typeck_root_def_id, |r| {
-            debug!("replace_late_bound_regions_with_nll_infer_vars: r={:?}", r);
+            debug!(?r);
             if !indices.indices.contains_key(&r) {
                 let region_vid = self.next_nll_region_var(FR);
                 debug!(?region_vid);
index 11565ba72d7555f1fb157468fd4c83b957eb873e..280fa70451141f85f821c2f2b02e0f87f82d5a83 100644 (file)
@@ -16,6 +16,9 @@
 
 extern crate proc_macro;
 
+#[macro_use]
+extern crate tracing;
+
 use crate::deriving::*;
 
 use rustc_expand::base::{MacroExpanderFn, ResolverExpand, SyntaxExtensionKind};
index 7eee80733666cf56e1657c6612ce31495032b9b4..7efb6cc61eecbb2325525c4696b5b5b7c9040c8a 100644 (file)
@@ -335,7 +335,7 @@ pub fn expand_test_or_bench(
     // extern crate test
     let test_extern = cx.item(sp, test_id, ast::AttrVec::new(), ast::ItemKind::ExternCrate(None));
 
-    tracing::debug!("synthetic test item:\n{}\n", pprust::item_to_string(&test_const));
+    debug!("synthetic test item:\n{}\n", pprust::item_to_string(&test_const));
 
     if is_stmt {
         vec![
index 89b0d2cc9be2eed8df75ae903645553f5dfcf1b2..079c6ff37cfb53222caeaf79014ebda64fa65716 100644 (file)
@@ -15,7 +15,6 @@
 use rustc_target::spec::PanicStrategy;
 use smallvec::{smallvec, SmallVec};
 use thin_vec::thin_vec;
-use tracing::debug;
 
 use std::{iter, mem};
 
index 2a6612eb86f12c62b41f516b41dfe18c5cd40806..5202ac697e9496f4551bb265de5732ed542fed72 100644 (file)
@@ -19,7 +19,6 @@
 
 use libc::{c_char, c_uint};
 use smallvec::SmallVec;
-use tracing::debug;
 
 impl<'ll, 'tcx> AsmBuilderMethods<'tcx> for Builder<'_, 'll, 'tcx> {
     fn codegen_inline_asm(
index 2e614e5dd88e7fc18068974f22e1e7a3a8a34df7..38a366095b41da97c9fe8906b8ab626be71935e5 100644 (file)
@@ -190,10 +190,10 @@ fn create_dll_import_lib(
 
             let output_path_z = rustc_fs_util::path_to_c_string(&output_path);
 
-            tracing::trace!("invoking LLVMRustWriteImportLibrary");
-            tracing::trace!("  dll_name {:#?}", dll_name_z);
-            tracing::trace!("  output_path {}", output_path.display());
-            tracing::trace!(
+            trace!("invoking LLVMRustWriteImportLibrary");
+            trace!("  dll_name {:#?}", dll_name_z);
+            trace!("  output_path {}", output_path.display());
+            trace!(
                 "  import names: {}",
                 dll_imports
                     .iter()
index e4af6269abc5305870515a832baf27da3111b677..a89df00e248e30e385fe2bc35202e4879d866780 100644 (file)
@@ -18,7 +18,6 @@
 use rustc_middle::middle::exported_symbols::{SymbolExportInfo, SymbolExportLevel};
 use rustc_session::cgu_reuse_tracker::CguReuse;
 use rustc_session::config::{self, CrateType, Lto};
-use tracing::{debug, info};
 
 use std::ffi::{CStr, CString};
 use std::fs::File;
index 740a68d0772c1632ba54061cc8bb783591eecfd6..a695df8409bb4621326aa87929be8851337a418a 100644 (file)
@@ -28,7 +28,6 @@
 use rustc_span::symbol::sym;
 use rustc_span::InnerSpan;
 use rustc_target::spec::{CodeModel, RelocModel, SanitizerSet, SplitDebuginfo};
-use tracing::debug;
 
 use libc::{c_char, c_int, c_uint, c_void, size_t};
 use std::ffi::CString;
index e7e373bf45d11043f9e3ba32bd18d09f10313322..63b63c6a1fab5d42d89c48ca7dea9dfc90ddd69e 100644 (file)
@@ -27,7 +27,6 @@
 use std::iter;
 use std::ops::Deref;
 use std::ptr;
-use tracing::{debug, instrument};
 
 // All Builders must have an llfn associated with them
 #[must_use]
index d55f995b933a6f6ec4935c8bf712247a0fcd9762..b83c1e8f08f3182ee2178faa1a03b98862d3985c 100644 (file)
@@ -11,7 +11,6 @@
 use crate::llvm;
 use crate::value::Value;
 use rustc_codegen_ssa::traits::*;
-use tracing::debug;
 
 use rustc_middle::ty::layout::{FnAbiOf, HasTyCtxt};
 use rustc_middle::ty::{self, Instance, TypeVisitable};
index 63d3bb40a3fe0c448463f9d32253b984b7476424..13e437cfbf7fb1b52d06589eb20c068ad140a131 100644 (file)
@@ -21,7 +21,6 @@
 
 use libc::{c_char, c_uint};
 use std::fmt::Write;
-use tracing::debug;
 
 /*
 * A note on nomenclature of linking: "extern", "foreign", and "upcall".
index d3e33da27993c6b3286765128fd0b7ca6ce04952..a559f7f3d57035a58da56542d948fdad98a9274a 100644 (file)
@@ -23,7 +23,6 @@
     AddressSpace, Align, HasDataLayout, Primitive, Scalar, Size, WrappingRange,
 };
 use std::ops::Range;
-use tracing::debug;
 
 pub fn const_alloc_to_llvm<'ll>(cx: &CodegenCx<'ll, '_>, alloc: ConstAllocation<'_>) -> &'ll Value {
     let alloc = alloc.inner();
index 58f391692c49c109bb59b7011109403a09625943..0d1df6fb1acd99e437c9fbcf3d4bc59b984b4578 100644 (file)
@@ -16,8 +16,6 @@
 
 use std::ffi::CString;
 
-use tracing::debug;
-
 /// Generates and exports the Coverage Map.
 ///
 /// Rust Coverage Map generation supports LLVM Coverage Mapping Format versions
index 98ba38356a4c30c8cafcd806115ebff394581817..964a632b6eeddc77a68711eed82bc4eef8c20e73 100644 (file)
@@ -28,7 +28,6 @@
 use std::ffi::CString;
 
 use std::iter;
-use tracing::debug;
 
 pub mod mapgen;
 
index d0a6f216858b61575238b6101f2a34fd151d8bd0..163ccd9460c54b58c9f1326fd3d186ae60496d9f 100644 (file)
@@ -42,7 +42,6 @@
 use rustc_symbol_mangling::typeid_for_trait_ref;
 use rustc_target::abi::{Align, Size};
 use smallvec::smallvec;
-use tracing::debug;
 
 use libc::{c_char, c_longlong, c_uint};
 use std::borrow::Cow;
@@ -51,7 +50,6 @@
 use std::iter;
 use std::path::{Path, PathBuf};
 use std::ptr;
-use tracing::instrument;
 
 impl PartialEq for llvm::Metadata {
     fn eq(&self, other: &Self) -> bool {
index cf591295b84680b57c660219f07e891a0c09a821..b23fe3fc9d5575ae8971c6dbb4b61cd1905512aa 100644 (file)
@@ -39,7 +39,6 @@
 use std::cell::OnceCell;
 use std::cell::RefCell;
 use std::iter;
-use tracing::debug;
 
 mod create_scope_map;
 pub mod gdb;
index 8f24367390775e1a8b43cac1024b7d093b17e4d3..a40cfc8b23fb32217f5b6b0897bea0e4f9e27373 100644 (file)
@@ -6,7 +6,7 @@
 use rustc_hir::def_id::DefId;
 use rustc_middle::ty::layout::{HasParamEnv, LayoutOf};
 use rustc_middle::ty::{self, DefIdTree, Ty};
-use tracing::trace;
+use trace;
 
 use crate::common::CodegenCx;
 use crate::llvm;
index fa0ecd18fc895bcd7908250d6b970a0834677243..0f663a26732bba8abf5094a095a859784f6f9012 100644 (file)
@@ -22,7 +22,6 @@
 use rustc_middle::ty::Ty;
 use rustc_symbol_mangling::typeid::typeid_for_fnabi;
 use smallvec::SmallVec;
-use tracing::debug;
 
 /// Declare a function.
 ///
index 636d689a34b5a900ef1ad0ae41484ac5147b4729..334425ae55b43300c1f3f7e06463b235a5ad3a28 100644 (file)
@@ -16,6 +16,8 @@
 
 #[macro_use]
 extern crate rustc_macros;
+#[macro_use]
+extern crate tracing;
 
 use back::write::{create_informational_target_machine, create_target_machine};
 
index f5d676c44e3428b83677bd237daf7e5ad9ca2782..1b049dfe9790444e300423cbbef45ccb27370168 100644 (file)
@@ -15,7 +15,6 @@
 use rustc_target::spec::{MergeFunctions, PanicStrategy};
 use smallvec::{smallvec, SmallVec};
 use std::ffi::{CStr, CString};
-use tracing::debug;
 
 use std::mem;
 use std::path::Path;
index 6e94284852f357970663599fbf08766576eef75c..1eceb7f5c87beb362760851e5ce31ae40a66c75f 100644 (file)
@@ -11,7 +11,6 @@
 use rustc_middle::ty::{self, Instance, TypeVisitable};
 use rustc_session::config::CrateType;
 use rustc_target::spec::RelocModel;
-use tracing::debug;
 
 impl<'tcx> PreDefineMethods<'tcx> for CodegenCx<'_, 'tcx> {
     fn predefine_static(
index 9f0e6c80b19a7f0108620d5fa07275f7dd90aaee..dc1165835e7ca271b38986619f20801fb8c5a71e 100644 (file)
@@ -11,7 +11,6 @@
 use rustc_target::abi::{Int, Pointer, F32, F64};
 use rustc_target::abi::{PointeeInfo, Scalar, Size, TyAbiInterface, Variants};
 use smallvec::{smallvec, SmallVec};
-use tracing::debug;
 
 use std::fmt::Write;
 
index d2f2c7bf7988ad84ea14ffd0563c5961fb631c7c..e9171823c242c7c1be928306c1b50d76025066a4 100644 (file)
@@ -1173,13 +1173,6 @@ fn infer_from(
             // only the linker flavor is known; use the default linker for the selected flavor
             (None, Some(flavor)) => Some((
                 PathBuf::from(match flavor {
-                    LinkerFlavor::Em => {
-                        if cfg!(windows) {
-                            "emcc.bat"
-                        } else {
-                            "emcc"
-                        }
-                    }
                     LinkerFlavor::Gcc => {
                         if cfg!(any(target_os = "solaris", target_os = "illumos")) {
                             // On historical Solaris systems, "cc" may have
@@ -1194,11 +1187,17 @@ fn infer_from(
                         }
                     }
                     LinkerFlavor::Ld => "ld",
-                    LinkerFlavor::Msvc => "link.exe",
                     LinkerFlavor::Lld(_) => "lld",
-                    LinkerFlavor::PtxLinker => "rust-ptx-linker",
-                    LinkerFlavor::BpfLinker => "bpf-linker",
-                    LinkerFlavor::L4Bender => "l4-bender",
+                    LinkerFlavor::Msvc => "link.exe",
+                    LinkerFlavor::EmCc => {
+                        if cfg!(windows) {
+                            "emcc.bat"
+                        } else {
+                            "emcc"
+                        }
+                    }
+                    LinkerFlavor::Bpf => "bpf-linker",
+                    LinkerFlavor::Ptx => "rust-ptx-linker",
                 }),
                 flavor,
             )),
@@ -1208,7 +1207,7 @@ fn infer_from(
                 });
 
                 let flavor = if stem == "emcc" {
-                    LinkerFlavor::Em
+                    LinkerFlavor::EmCc
                 } else if stem == "gcc"
                     || stem.ends_with("-gcc")
                     || stem == "clang"
@@ -1236,7 +1235,8 @@ fn infer_from(
 
     // linker and linker flavor specified via command line have precedence over what the target
     // specification specifies
-    if let Some(ret) = infer_from(sess, sess.opts.cg.linker.clone(), sess.opts.cg.linker_flavor) {
+    let linker_flavor = sess.opts.cg.linker_flavor.map(LinkerFlavor::from_cli);
+    if let Some(ret) = infer_from(sess, sess.opts.cg.linker.clone(), linker_flavor) {
         return ret;
     }
 
@@ -2113,11 +2113,11 @@ fn add_order_independent_options(
         });
     }
 
-    if flavor == LinkerFlavor::PtxLinker {
+    if flavor == LinkerFlavor::Ptx {
         // Provide the linker with fallback to internal `target-cpu`.
         cmd.arg("--fallback-arch");
         cmd.arg(&codegen_results.crate_info.target_cpu);
-    } else if flavor == LinkerFlavor::BpfLinker {
+    } else if flavor == LinkerFlavor::Bpf {
         cmd.arg("--cpu");
         cmd.arg(&codegen_results.crate_info.target_cpu);
         cmd.arg("--cpu-features");
@@ -2797,20 +2797,24 @@ fn add_gcc_ld_path(cmd: &mut dyn Linker, sess: &Session, flavor: LinkerFlavor) {
         if let LinkerFlavor::Gcc = flavor {
             match ld_impl {
                 LdImpl::Lld => {
-                    let tools_path = sess.get_tools_search_paths(false);
-                    let gcc_ld_dir = tools_path
-                        .into_iter()
-                        .map(|p| p.join("gcc-ld"))
-                        .find(|p| {
-                            p.join(if sess.host.is_like_windows { "ld.exe" } else { "ld" }).exists()
-                        })
-                        .unwrap_or_else(|| sess.fatal("rust-lld (as ld) not found"));
-                    cmd.arg({
-                        let mut arg = OsString::from("-B");
-                        arg.push(gcc_ld_dir);
-                        arg
-                    });
-                    cmd.arg(format!("-Wl,-rustc-lld-flavor={}", sess.target.lld_flavor.as_str()));
+                    // Implement the "self-contained" part of -Zgcc-ld
+                    // by adding rustc distribution directories to the tool search path.
+                    for path in sess.get_tools_search_paths(false) {
+                        cmd.arg({
+                            let mut arg = OsString::from("-B");
+                            arg.push(path.join("gcc-ld"));
+                            arg
+                        });
+                    }
+                    // Implement the "linker flavor" part of -Zgcc-ld
+                    // by asking cc to use some kind of lld.
+                    cmd.arg("-fuse-ld=lld");
+                    if sess.target.lld_flavor != LldFlavor::Ld {
+                        // Tell clang to use a non-default LLD flavor.
+                        // Gcc doesn't understand the target option, but we currently assume
+                        // that gcc is not used for Apple and Wasm targets (#97402).
+                        cmd.arg(format!("--target={}", sess.target.llvm_target));
+                    }
                 }
             }
         } else {
index ce51b2e9531fcedbe1520bb18736badb692a4de9..8c6f526b054bc5ec213eddf5fac9d8505029d9d5 100644 (file)
@@ -126,29 +126,26 @@ pub fn get_linker<'a>(
     // to the linker args construction.
     assert!(cmd.get_args().is_empty() || sess.target.vendor == "uwp");
     match flavor {
-        LinkerFlavor::Lld(LldFlavor::Link) | LinkerFlavor::Msvc => {
-            Box::new(MsvcLinker { cmd, sess }) as Box<dyn Linker>
-        }
-        LinkerFlavor::Em => Box::new(EmLinker { cmd, sess }) as Box<dyn Linker>,
         LinkerFlavor::Gcc => {
             Box::new(GccLinker { cmd, sess, target_cpu, hinted_static: false, is_ld: false })
                 as Box<dyn Linker>
         }
-
+        LinkerFlavor::Ld if sess.target.os == "l4re" => {
+            Box::new(L4Bender::new(cmd, sess)) as Box<dyn Linker>
+        }
         LinkerFlavor::Lld(LldFlavor::Ld)
         | LinkerFlavor::Lld(LldFlavor::Ld64)
         | LinkerFlavor::Ld => {
             Box::new(GccLinker { cmd, sess, target_cpu, hinted_static: false, is_ld: true })
                 as Box<dyn Linker>
         }
-
+        LinkerFlavor::Lld(LldFlavor::Link) | LinkerFlavor::Msvc => {
+            Box::new(MsvcLinker { cmd, sess }) as Box<dyn Linker>
+        }
         LinkerFlavor::Lld(LldFlavor::Wasm) => Box::new(WasmLd::new(cmd, sess)) as Box<dyn Linker>,
-
-        LinkerFlavor::PtxLinker => Box::new(PtxLinker { cmd, sess }) as Box<dyn Linker>,
-
-        LinkerFlavor::BpfLinker => Box::new(BpfLinker { cmd, sess }) as Box<dyn Linker>,
-
-        LinkerFlavor::L4Bender => Box::new(L4Bender::new(cmd, sess)) as Box<dyn Linker>,
+        LinkerFlavor::EmCc => Box::new(EmLinker { cmd, sess }) as Box<dyn Linker>,
+        LinkerFlavor::Bpf => Box::new(BpfLinker { cmd, sess }) as Box<dyn Linker>,
+        LinkerFlavor::Ptx => Box::new(PtxLinker { cmd, sess }) as Box<dyn Linker>,
     }
 }
 
index b46f71fc78a3b9164919ce9c3e2097e7764875d9..a2f14e753aebe7ca5cb6bf7b049123f7c746ff5d 100644 (file)
@@ -197,7 +197,7 @@ pub(super) fn op_to_const<'tcx>(
     }
 }
 
-#[instrument(skip(tcx), level = "debug")]
+#[instrument(skip(tcx), level = "debug", ret)]
 pub(crate) fn turn_into_const_value<'tcx>(
     tcx: TyCtxt<'tcx>,
     constant: ConstAlloc<'tcx>,
@@ -224,10 +224,7 @@ pub(crate) fn turn_into_const_value<'tcx>(
     );
 
     // Turn this into a proper constant.
-    let const_val = op_to_const(&ecx, &mplace.into());
-    debug!(?const_val);
-
-    const_val
+    op_to_const(&ecx, &mplace.into())
 }
 
 #[instrument(skip(tcx), level = "debug")]
index 373b139c86e424d941b779aaddbe7e5912db6301..8b7c3cf3377cc9108bc7a9e9f1f7f4763b35cdf8 100644 (file)
@@ -204,7 +204,7 @@ fn get_info_on_unsized_field<'tcx>(
     (unsized_inner_ty, num_elems)
 }
 
-#[instrument(skip(ecx), level = "debug")]
+#[instrument(skip(ecx), level = "debug", ret)]
 fn create_pointee_place<'tcx>(
     ecx: &mut CompileTimeEvalContext<'tcx, 'tcx>,
     ty: Ty<'tcx>,
@@ -237,14 +237,11 @@ fn create_pointee_place<'tcx>(
         let ptr = ecx.allocate_ptr(size, align, MemoryKind::Stack).unwrap();
         debug!(?ptr);
 
-        let place = MPlaceTy::from_aligned_ptr_with_meta(
+        MPlaceTy::from_aligned_ptr_with_meta(
             ptr.into(),
             layout,
             MemPlaceMeta::Meta(Scalar::from_machine_usize(num_elems as u64, &tcx)),
-        );
-        debug!(?place);
-
-        place
+        )
     } else {
         create_mplace_from_layout(ecx, ty)
     }
@@ -253,7 +250,7 @@ fn create_pointee_place<'tcx>(
 /// Converts a `ValTree` to a `ConstValue`, which is needed after mir
 /// construction has finished.
 // FIXME Merge `valtree_to_const_value` and `valtree_into_mplace` into one function
-#[instrument(skip(tcx), level = "debug")]
+#[instrument(skip(tcx), level = "debug", ret)]
 pub fn valtree_to_const_value<'tcx>(
     tcx: TyCtxt<'tcx>,
     param_env_ty: ty::ParamEnvAnd<'tcx, Ty<'tcx>>,
@@ -294,7 +291,7 @@ pub fn valtree_to_const_value<'tcx>(
             dump_place(&ecx, place.into());
             intern_const_alloc_recursive(&mut ecx, InternKind::Constant, &place).unwrap();
 
-            let const_val = match ty.kind() {
+            match ty.kind() {
                 ty::Ref(_, _, _) => {
                     let ref_place = place.to_ref(&tcx);
                     let imm =
@@ -303,10 +300,7 @@ pub fn valtree_to_const_value<'tcx>(
                     op_to_const(&ecx, &imm.into())
                 }
                 _ => op_to_const(&ecx, &place.into()),
-            };
-            debug!(?const_val);
-
-            const_val
+            }
         }
         ty::Never
         | ty::Error(_)
index 66ab3f15716f2e5d7eb93782df478f32bf5f50e2..24dbc769529c3665a6e30da12c750226a21ffd19 100644 (file)
@@ -334,7 +334,7 @@ pub enum InternKind {
 /// tracks where in the value we are and thus can show much better error messages.
 /// Any errors here would anyway be turned into `const_err` lints, whereas validation failures
 /// are hard errors.
-#[tracing::instrument(level = "debug", skip(ecx))]
+#[instrument(level = "debug", skip(ecx))]
 pub fn intern_const_alloc_recursive<
     'mir,
     'tcx: 'mir,
index b662513e70fbe6ee0d57ec27d50c651bd691c5c1..b798862583952eb5d1604a56750c14850ac8c6ab 100644 (file)
@@ -181,16 +181,23 @@ fn mir_assign_valid_types(&self, src: Ty<'tcx>, dest: Ty<'tcx>) -> bool {
         if (src, dest).has_opaque_types() {
             return true;
         }
-        // Normalize projections and things like that.
-        let param_env = self.param_env.with_reveal_all_normalized(self.tcx);
-        let src = self.tcx.normalize_erasing_regions(param_env, src);
-        let dest = self.tcx.normalize_erasing_regions(param_env, dest);
 
+        // Normalize projections and things like that.
         // Type-changing assignments can happen when subtyping is used. While
         // all normal lifetimes are erased, higher-ranked types with their
         // late-bound lifetimes are still around and can lead to type
         // differences. So we compare ignoring lifetimes.
-        equal_up_to_regions(self.tcx, param_env, src, dest)
+
+        // First, try with reveal_all. This might not work in some cases, as the predicates
+        // can be cleared in reveal_all mode. We try the reveal first anyways as it is used
+        // by some other passes like inlining as well.
+        let param_env = self.param_env.with_reveal_all_normalized(self.tcx);
+        if equal_up_to_regions(self.tcx, param_env, src, dest) {
+            return true;
+        }
+
+        // If this fails, we can try it without the reveal.
+        equal_up_to_regions(self.tcx, self.param_env, src, dest)
     }
 }
 
index 4570c1448337eec7b661868deb0d81d64f219916..d1d02ed73f9595a3847d38d96eb8665fc56badbc 100644 (file)
@@ -7,7 +7,7 @@ edition = "2021"
 crate-type = ["dylib"]
 
 [dependencies]
-tracing = { version = "0.1.28" }
+tracing = { version = "0.1.35" }
 serde_json = "1.0.59"
 rustc_log = { path = "../rustc_log" }
 rustc_middle = { path = "../rustc_middle" }
index 223092a74bd97cf00d62ed229dcbae3493e985c4..da987152ff66030dcdbba447d15dce67950c45b9 100644 (file)
@@ -11,6 +11,8 @@ privacy_in_public_interface = {$vis_descr} {$kind} `{$descr}` in public interfac
     .label = can't leak {$vis_descr} {$kind}
     .visibility_label = `{$descr}` declared as {$vis_descr}
 
+privacy_report_access_level = {$descr}
+
 privacy_from_private_dep_in_public_interface =
     {$kind} `{$descr}` from private dependency '{$krate}' in public interface
 
index 5fe107fbc530ae59319b38210979eed6d6ea5df7..05d0a2ba82cee984758cc5f498edbb5b2b23c148 100644 (file)
@@ -5,6 +5,9 @@
 #![deny(rustc::untranslatable_diagnostic)]
 #![deny(rustc::diagnostic_outside_of_impl)]
 
+#[macro_use]
+extern crate tracing;
+
 use fluent_bundle::FluentResource;
 use fluent_syntax::parser::ParserError;
 use rustc_data_structures::sync::Lrc;
@@ -16,7 +19,6 @@
 use std::fs;
 use std::io;
 use std::path::{Path, PathBuf};
-use tracing::{instrument, trace};
 
 #[cfg(not(parallel_compiler))]
 use std::cell::LazyCell as Lazy;
index 61d767a1cc6b4f97d806c45b8a0d3a127ec2d59a..7e29dc207accecca9a86275ec477cb9426c2b087 100644 (file)
@@ -12,7 +12,6 @@
 use std::marker::PhantomData;
 use std::ops::{Deref, DerefMut};
 use std::thread::panicking;
-use tracing::debug;
 
 /// Used for emitting structured error messages and other diagnostic information.
 ///
index 6c1bfcb9919eb9df89a3124f90bf16a655da2645..e79ce11a6fc075a8bdf162f7b63256b066c89a29 100644 (file)
@@ -34,7 +34,6 @@
 use std::path::Path;
 use termcolor::{Ansi, BufferWriter, ColorChoice, ColorSpec, StandardStream};
 use termcolor::{Buffer, Color, WriteColor};
-use tracing::*;
 
 /// Default column width, used in tests and when terminal dimensions cannot be determined.
 const DEFAULT_COLUMN_WIDTH: usize = 140;
index 75dcbd69674d652c5897b8db9c596fc74307eabc..ac0e200b1b73ee783e22affe3e6b48ab2b4a435f 100644 (file)
@@ -15,6 +15,9 @@
 #[macro_use]
 extern crate rustc_macros;
 
+#[macro_use]
+extern crate tracing;
+
 extern crate proc_macro as pm;
 
 mod placeholders;
index 86dbd33a221f81c08b9d9ff6072814c411c69e90..7764ffd246e323d205c992bd61627c9652ce3b05 100644 (file)
@@ -32,7 +32,6 @@
 use std::borrow::Cow;
 use std::collections::hash_map::Entry;
 use std::{mem, slice};
-use tracing::debug;
 
 pub(crate) struct ParserAnyMacro<'a> {
     parser: Parser<'a>,
index 0487270b52a9aaad0e0dce49ac753a2c8ba84b98..0c88379d498994845bee2bc7e019617e471a096b 100644 (file)
@@ -758,6 +758,7 @@ pub struct BuiltinAttribute {
     // Internal attributes, Testing:
     // ==========================================================================
 
+    rustc_attr!(TEST, rustc_access_level, Normal, template!(Word), WarnFollowing),
     rustc_attr!(TEST, rustc_outlives, Normal, template!(Word), WarnFollowing),
     rustc_attr!(TEST, rustc_capture_analysis, Normal, template!(Word), WarnFollowing),
     rustc_attr!(TEST, rustc_insignificant_dtor, Normal, template!(Word), WarnFollowing),
index c2c551e78a41105af9ee32fe96fbabbd750a3b7e..d85ac960f9b2f10b415cb0a43d2eaa7de8bfc102 100644 (file)
@@ -15,7 +15,6 @@
 
 use std::fmt::{self, Write};
 use std::hash::Hash;
-use tracing::debug;
 
 /// The `DefPathTable` maps `DefIndex`es to `DefKey`s and vice versa.
 /// Internally the `DefPathTable` holds a tree of `DefKey`s, where each `DefKey`
index 092029ef09ec80e6cab087b6b63838e94ed25f4e..1b33cb9c2da9cbcebbe4be41ca0bd6d1d7665e08 100644 (file)
@@ -17,6 +17,9 @@
 #[macro_use]
 extern crate rustc_macros;
 
+#[macro_use]
+extern crate tracing;
+
 #[macro_use]
 extern crate rustc_data_structures;
 
index 8bf1de34a9b5cace73b66a13e3f888ebafc6fbb9..d4350aa5734dee4aefe5583a5f1e6233d0cf2303 100644 (file)
@@ -391,7 +391,7 @@ pub fn instantiate(
     /// Preconditions:
     ///
     /// - `for_vid` is a "root vid"
-    #[instrument(skip(self), level = "trace")]
+    #[instrument(skip(self), level = "trace", ret)]
     fn generalize(
         &self,
         ty: Ty<'tcx>,
@@ -435,15 +435,8 @@ fn generalize(
             cache: SsoHashMap::new(),
         };
 
-        let ty = match generalize.relate(ty, ty) {
-            Ok(ty) => ty,
-            Err(e) => {
-                debug!(?e, "failure");
-                return Err(e);
-            }
-        };
+        let ty = generalize.relate(ty, ty)?;
         let needs_wf = generalize.needs_wf;
-        trace!(?ty, ?needs_wf, "success");
         Ok(Generalization { ty, needs_wf })
     }
 
@@ -499,6 +492,7 @@ struct Generalizer<'cx, 'tcx> {
 /// Result from a generalization operation. This includes
 /// not only the generalized type, but also a bool flag
 /// indicating whether further WF checks are needed.
+#[derive(Debug)]
 struct Generalization<'tcx> {
     ty: Ty<'tcx>,
 
@@ -856,10 +850,9 @@ fn binders<T>(
         Ok(a.rebind(self.relate(a.skip_binder(), b.skip_binder())?))
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self), ret)]
     fn tys(&mut self, t: Ty<'tcx>, _t: Ty<'tcx>) -> RelateResult<'tcx, Ty<'tcx>> {
         debug_assert_eq!(t, _t);
-        debug!("ConstInferUnifier: t={:?}", t);
 
         match t.kind() {
             &ty::Infer(ty::TyVar(vid)) => {
@@ -883,12 +876,7 @@ fn tys(&mut self, t: Ty<'tcx>, _t: Ty<'tcx>) -> RelateResult<'tcx, Ty<'tcx>> {
                             .borrow_mut()
                             .type_variables()
                             .new_var(self.for_universe, origin);
-                        let u = self.tcx().mk_ty_var(new_var_id);
-                        debug!(
-                            "ConstInferUnifier: replacing original vid={:?} with new={:?}",
-                            vid, u
-                        );
-                        Ok(u)
+                        Ok(self.tcx().mk_ty_var(new_var_id))
                     }
                 }
             }
@@ -932,14 +920,13 @@ fn regions(
         }
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn consts(
         &mut self,
         c: ty::Const<'tcx>,
         _c: ty::Const<'tcx>,
     ) -> RelateResult<'tcx, ty::Const<'tcx>> {
         debug_assert_eq!(c, _c);
-        debug!("ConstInferUnifier: c={:?}", c);
 
         match c.kind() {
             ty::ConstKind::Infer(InferConst::Var(vid)) => {
index 3a6119a627368fb18da0c9e7f4638546ce339428..6dad9873d613404a124bac052236be887ecdb7f0 100644 (file)
@@ -1434,7 +1434,7 @@ fn lifetime_display(lifetime: Region<'_>) -> String {
     /// the message in `secondary_span` as the primary label, and apply the message that would
     /// otherwise be used for the primary label on the `secondary_span` `Span`. This applies on
     /// E0271, like `src/test/ui/issues/issue-39970.stderr`.
-    #[tracing::instrument(
+    #[instrument(
         level = "debug",
         skip(self, diag, secondary_span, swap_secondary_and_primary, prefer_label)
     )]
index d0d9efe152cc04109799f78aa8df246f6db4a191..67426fcf0feda6c5a7664772c7dfffd8cd941ae1 100644 (file)
@@ -69,7 +69,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
     /// For more details visit the relevant sections of the [rustc dev guide].
     ///
     /// [rustc dev guide]: https://rustc-dev-guide.rust-lang.org/traits/hrtb.html
-    #[instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self), ret)]
     pub fn replace_bound_vars_with_placeholders<T>(&self, binder: ty::Binder<'tcx, T>) -> T
     where
         T: TypeFoldable<'tcx> + Copy,
@@ -104,9 +104,8 @@ pub fn replace_bound_vars_with_placeholders<T>(&self, binder: ty::Binder<'tcx, T
             },
         };
 
-        let result = self.tcx.replace_bound_vars_uncached(binder, delegate);
-        debug!(?next_universe, ?result);
-        result
+        debug!(?next_universe);
+        self.tcx.replace_bound_vars_uncached(binder, delegate)
     }
 
     /// See [RegionConstraintCollector::leak_check][1].
index 3783cfb4cc5c85c85aaf53e674bdfb7916a95ba8..13b7e8eb9643611e0a5678f9b936250e347ac216 100644 (file)
@@ -333,9 +333,9 @@ fn sub_concrete_regions(&self, a: Region<'tcx>, b: Region<'tcx>) -> bool {
     ///
     /// Neither `a` nor `b` may be an inference variable (hence the
     /// term "concrete regions").
-    #[instrument(level = "trace", skip(self))]
+    #[instrument(level = "trace", skip(self), ret)]
     fn lub_concrete_regions(&self, a: Region<'tcx>, b: Region<'tcx>) -> Region<'tcx> {
-        let r = match (*a, *b) {
+        match (*a, *b) {
             (ReLateBound(..), _) | (_, ReLateBound(..)) | (ReErased, _) | (_, ReErased) => {
                 bug!("cannot relate region: LUB({:?}, {:?})", a, b);
             }
@@ -399,11 +399,7 @@ fn lub_concrete_regions(&self, a: Region<'tcx>, b: Region<'tcx>) -> Region<'tcx>
                     self.tcx().lifetimes.re_static
                 }
             }
-        };
-
-        debug!("lub_concrete_regions({:?}, {:?}) = {:?}", a, b, r);
-
-        r
+        }
     }
 
     /// After expansion is complete, go and check upper bounds (i.e.,
index e7e93116a66d146c9d3b74ad4bb5cd79324cc06b..bb6f6ae60e26ac27c05ad3e59c889122e90d6ef3 100644 (file)
@@ -542,7 +542,7 @@ fn a_is_expected(&self) -> bool {
         true
     }
 
-    #[instrument(skip(self, info), level = "trace")]
+    #[instrument(skip(self, info), level = "trace", ret)]
     fn relate_with_variance<T: Relate<'tcx>>(
         &mut self,
         variance: ty::Variance,
@@ -560,8 +560,6 @@ fn relate_with_variance<T: Relate<'tcx>>(
 
         self.ambient_variance = old_ambient_variance;
 
-        debug!(?r);
-
         Ok(r)
     }
 
index 233a5004a3931f53444eaf75538edc8f89d65e6a..d45adf43abfcc0040f0feeb235604eff4cc422a9 100644 (file)
@@ -390,7 +390,7 @@ pub fn register_member_constraints(
         });
     }
 
-    #[instrument(skip(self), level = "trace")]
+    #[instrument(skip(self), level = "trace", ret)]
     pub fn opaque_type_origin(&self, def_id: LocalDefId, span: Span) -> Option<OpaqueTyOrigin> {
         let opaque_hir_id = self.tcx.hir().local_def_id_to_hir_id(def_id);
         let parent_def_id = match self.defining_use_anchor {
@@ -421,16 +421,14 @@ pub fn opaque_type_origin(&self, def_id: LocalDefId, span: Span) -> Option<Opaqu
         in_definition_scope.then_some(*origin)
     }
 
-    #[instrument(skip(self), level = "trace")]
+    #[instrument(skip(self), level = "trace", ret)]
     fn opaque_ty_origin_unchecked(&self, def_id: LocalDefId, span: Span) -> OpaqueTyOrigin {
-        let origin = match self.tcx.hir().expect_item(def_id).kind {
+        match self.tcx.hir().expect_item(def_id).kind {
             hir::ItemKind::OpaqueTy(hir::OpaqueTy { origin, .. }) => origin,
             ref itemkind => {
                 span_bug!(span, "weird opaque type: {:?}, {:#?}", def_id, itemkind)
             }
-        };
-        trace!(?origin);
-        origin
+        }
     }
 }
 
index fb12da0cc13f0aeb3661ff34d8c7781d92058d9f..4d124554afb94d3bb119275e9c415932dbc8131b 100644 (file)
@@ -29,7 +29,7 @@ pub(crate) fn remove(&mut self, key: OpaqueTypeKey<'tcx>, idx: Option<OpaqueHidd
         }
     }
 
-    #[instrument(level = "debug")]
+    #[instrument(level = "debug", ret)]
     pub fn take_opaque_types(&mut self) -> OpaqueTypeMap<'tcx> {
         std::mem::take(&mut self.opaque_types)
     }
index 2a085288fb7c069c8d58d8a776b9e758d0b4078c..2d19d1823fdfc2b04816cde419dd59aa3361009b 100644 (file)
@@ -9,7 +9,7 @@
 use rustc_middle::traits::query::OutlivesBound;
 use rustc_middle::ty;
 
-#[instrument(level = "debug", skip(param_env))]
+#[instrument(level = "debug", skip(param_env), ret)]
 pub fn explicit_outlives_bounds<'tcx>(
     param_env: ty::ParamEnv<'tcx>,
 ) -> impl Iterator<Item = OutlivesBound<'tcx>> + 'tcx {
index fe78890ff6ed7648b309d0b095b284b25c0dd4b3..74c8bd88d275dbfb79589c41d21eab3bd91d169b 100644 (file)
@@ -313,7 +313,7 @@ fn param_ty_must_outlive(
         self.delegate.push_verify(origin, generic, region, verify_bound);
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn projection_must_outlive(
         &mut self,
         origin: infer::SubregionOrigin<'tcx>,
index be03c8b5bae98a507cec3b8581bd874cea47338c..a5c21f0fb9b50eadf775aac2a6840500f388a00d 100644 (file)
@@ -34,7 +34,7 @@
 /// like are used. This is a particular challenge since this function is invoked
 /// very late in inference and hence cannot make use of the normal inference
 /// machinery.
-#[tracing::instrument(level = "debug", skip(tcx, param_env))]
+#[instrument(level = "debug", skip(tcx, param_env))]
 pub fn extract_verify_if_eq<'tcx>(
     tcx: TyCtxt<'tcx>,
     param_env: ty::ParamEnv<'tcx>,
@@ -71,7 +71,7 @@ pub fn extract_verify_if_eq<'tcx>(
 }
 
 /// True if a (potentially higher-ranked) outlives
-#[tracing::instrument(level = "debug", skip(tcx, param_env))]
+#[instrument(level = "debug", skip(tcx, param_env))]
 pub(super) fn can_match_erased_ty<'tcx>(
     tcx: TyCtxt<'tcx>,
     param_env: ty::ParamEnv<'tcx>,
@@ -110,7 +110,7 @@ fn no_match<T>(&self) -> RelateResult<'tcx, T> {
 
     /// Binds the pattern variable `br` to `value`; returns an `Err` if the pattern
     /// is already bound to a different value.
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn bind(
         &mut self,
         br: ty::BoundRegion,
index 1c6243c275c01daed80196d81a77c072ec4af099..949bd02ad6839a8f1535e453efc2d08d1a704dcf 100644 (file)
@@ -332,7 +332,7 @@ pub fn create_compiler_and_run<R>(config: Config, f: impl FnOnce(&Compiler) -> R
 // JUSTIFICATION: before session exists, only config
 #[allow(rustc::bad_opt_access)]
 pub fn run_compiler<R: Send>(config: Config, f: impl FnOnce(&Compiler) -> R + Send) -> R {
-    tracing::trace!("run_compiler");
+    trace!("run_compiler");
     util::run_in_thread_pool_with_globals(
         config.opts.edition,
         config.opts.unstable_opts.threads,
index 258e38c3bdb9e09197fc006865defaa66903149a..1a8d619fafb6212483b49ab045f40f6e07af901f 100644 (file)
@@ -8,6 +8,9 @@
 #![deny(rustc::untranslatable_diagnostic)]
 #![deny(rustc::diagnostic_outside_of_impl)]
 
+#[macro_use]
+extern crate tracing;
+
 mod callbacks;
 mod errors;
 pub mod interface;
index 66c6a229b89e4564b4e9130f3191eded516adcf7..f8b40949e2ed993ab2b2c2917d251bd94c824ba7 100644 (file)
@@ -38,7 +38,6 @@
 use rustc_span::FileName;
 use rustc_trait_selection::traits;
 use rustc_typeck as typeck;
-use tracing::{info, warn};
 
 use std::any::Any;
 use std::cell::RefCell;
@@ -165,7 +164,7 @@ pub fn create_resolver(
     krate: &ast::Crate,
     crate_name: &str,
 ) -> BoxedResolver {
-    tracing::trace!("create_resolver");
+    trace!("create_resolver");
     BoxedResolver::new(sess, move |sess, resolver_arenas| {
         Resolver::new(sess, krate, crate_name, metadata_loader, resolver_arenas)
     })
@@ -279,7 +278,7 @@ pub fn configure_and_expand(
     crate_name: &str,
     resolver: &mut Resolver<'_>,
 ) -> Result<ast::Crate> {
-    tracing::trace!("configure_and_expand");
+    trace!("configure_and_expand");
     pre_expansion_lint(sess, lint_store, resolver.registered_tools(), &krate, crate_name);
     rustc_builtin_macros::register_builtin_macros(resolver);
 
index 65fa8d7495a4bf16cc76277a97bf5593e3e29fd9..6c725a01b53151ccfb9325f876442a22920facbf 100644 (file)
@@ -166,7 +166,7 @@ pub fn crate_name(&self) -> Result<&Query<String>> {
     pub fn expansion(
         &self,
     ) -> Result<&Query<(Lrc<ast::Crate>, Rc<RefCell<BoxedResolver>>, Lrc<LintStore>)>> {
-        tracing::trace!("expansion");
+        trace!("expansion");
         self.expansion.compute(|| {
             let crate_name = self.crate_name()?.peek().clone();
             let (krate, lint_store) = self.register_plugins()?.take();
index 9207a0488623c94e9ef3aa5fd89280f20942666d..5df5ab3ddc032eb19ec354e3f1bcb012b8b32345 100644 (file)
 use rustc_span::edition::{Edition, DEFAULT_EDITION};
 use rustc_span::symbol::sym;
 use rustc_span::SourceFileHashAlgorithm;
-use rustc_target::spec::{CodeModel, LinkerFlavor, MergeFunctions, PanicStrategy};
-use rustc_target::spec::{
-    RelocModel, RelroLevel, SanitizerSet, SplitDebuginfo, StackProtector, TlsModel,
-};
+use rustc_target::spec::{CodeModel, LinkerFlavorCli, MergeFunctions, PanicStrategy, RelocModel};
+use rustc_target::spec::{RelroLevel, SanitizerSet, SplitDebuginfo, StackProtector, TlsModel};
 
 use std::collections::{BTreeMap, BTreeSet};
 use std::iter::FromIterator;
@@ -552,7 +550,7 @@ macro_rules! untracked {
     untracked!(link_args, vec![String::from("abc"), String::from("def")]);
     untracked!(link_self_contained, Some(true));
     untracked!(linker, Some(PathBuf::from("linker")));
-    untracked!(linker_flavor, Some(LinkerFlavor::Gcc));
+    untracked!(linker_flavor, Some(LinkerFlavorCli::Gcc));
     untracked!(no_stack_check, true);
     untracked!(remark, Passes::Some(vec![String::from("pass1"), String::from("pass2")]));
     untracked!(rpath, true);
index e74978485a21c818e780d1d3a923593a73de7b8c..f7e70d355cf86e6ff3ad519311676536ed3a6e24 100644 (file)
@@ -1,3 +1,4 @@
+use info;
 use libloading::Library;
 use rustc_ast as ast;
 use rustc_codegen_ssa::traits::CodegenBackend;
@@ -31,7 +32,6 @@
 use std::sync::atomic::{AtomicBool, Ordering};
 use std::sync::OnceLock;
 use std::thread;
-use tracing::info;
 
 /// Function pointer type that constructs a new CodegenBackend.
 pub type MakeBackendFn = fn() -> Box<dyn CodegenBackend>;
index 868555a72b0d1284f94982c90cc8dcd600a9f486..4e9c209a58400aa176d13cf336cf7c01e1cc4a86 100644 (file)
@@ -59,7 +59,6 @@
 use crate::nonstandard_style::{method_context, MethodLateContext};
 
 use std::fmt::Write;
-use tracing::{debug, trace};
 
 // hardwired lints from librustc_middle
 pub use rustc_session::lint::builtin::*;
@@ -3173,3 +3172,81 @@ fn check_expr(&mut self, cx: &LateContext<'tcx>, expr: &'tcx hir::Expr<'tcx>) {
         }
     }
 }
+
+declare_lint! {
+    /// The `special_module_name` lint detects module
+    /// declarations for files that have a special meaning.
+    ///
+    /// ### Example
+    ///
+    /// ```rust,compile_fail
+    /// mod lib;
+    ///
+    /// fn main() {
+    ///     lib::run();
+    /// }
+    /// ```
+    ///
+    /// {{produces}}
+    ///
+    /// ### Explanation
+    ///
+    /// Cargo recognizes `lib.rs` and `main.rs` as the root of a
+    /// library or binary crate, so declaring them as modules
+    /// will lead to miscompilation of the crate unless configured
+    /// explicitly.
+    ///
+    /// To access a library from a binary target within the same crate,
+    /// use `your_crate_name::` as the path path instead of `lib::`:
+    ///
+    /// ```rust,compile_fail
+    /// // bar/src/lib.rs
+    /// fn run() {
+    ///     // ...
+    /// }
+    ///
+    /// // bar/src/main.rs
+    /// fn main() {
+    ///     bar::run();
+    /// }
+    /// ```
+    ///
+    /// Binary targets cannot be used as libraries and so declaring
+    /// one as a module is not allowed.
+    pub SPECIAL_MODULE_NAME,
+    Warn,
+    "module declarations for files with a special meaning",
+}
+
+declare_lint_pass!(SpecialModuleName => [SPECIAL_MODULE_NAME]);
+
+impl EarlyLintPass for SpecialModuleName {
+    fn check_crate(&mut self, cx: &EarlyContext<'_>, krate: &ast::Crate) {
+        for item in &krate.items {
+            if let ast::ItemKind::Mod(
+                _,
+                ast::ModKind::Unloaded | ast::ModKind::Loaded(_, ast::Inline::No, _),
+            ) = item.kind
+            {
+                if item.attrs.iter().any(|a| a.has_name(sym::path)) {
+                    continue;
+                }
+
+                match item.ident.name.as_str() {
+                    "lib" => cx.struct_span_lint(SPECIAL_MODULE_NAME, item.span, |lint| {
+                        lint.build("found module declaration for lib.rs")
+                            .note("lib.rs is the root of this crate's library target")
+                            .help("to refer to it from other targets, use the library's name as the path")
+                            .emit()
+                    }),
+                    "main" => cx.struct_span_lint(SPECIAL_MODULE_NAME, item.span, |lint| {
+                        lint.build("found module declaration for main.rs")
+                            .note("a binary crate cannot be used as library")
+                            .emit()
+                    }),
+                    _ => continue
+                }
+            }
+        }
+    }
+}
index 002bba4759be820ace8e656cd52a36f9fe52edca..e3b6c0159870072522a93ce2b2a1477e8dd12198 100644 (file)
@@ -45,7 +45,6 @@
 use rustc_span::symbol::{sym, Ident, Symbol};
 use rustc_span::{BytePos, Span};
 use rustc_target::abi;
-use tracing::debug;
 
 use std::cell::Cell;
 use std::iter;
@@ -417,7 +416,7 @@ pub fn check_lint_name(
                     None => {
                         // 1. The tool is currently running, so this lint really doesn't exist.
                         // FIXME: should this handle tools that never register a lint, like rustfmt?
-                        tracing::debug!("lints={:?}", self.by_name.keys().collect::<Vec<_>>());
+                        debug!("lints={:?}", self.by_name.keys().collect::<Vec<_>>());
                         let tool_prefix = format!("{}::", tool_name);
                         return if self.by_name.keys().any(|lint| lint.starts_with(&tool_prefix)) {
                             self.no_lint_suggestion(&complete_name)
@@ -510,7 +509,7 @@ fn check_tool_name_for_backwards_compat(
                 CheckLintNameResult::Tool(Err((Some(slice::from_ref(id)), complete_name)))
             }
             Some(other) => {
-                tracing::debug!("got renamed lint {:?}", other);
+                debug!("got renamed lint {:?}", other);
                 CheckLintNameResult::NoLint(None)
             }
         }
index cdb5b3c4284a8d37afc0dd2f6bb7b4f8c3006937..27d173ebde82a506d7c1f8493352b137b3fee634 100644 (file)
@@ -26,7 +26,6 @@
 use rustc_span::Span;
 
 use std::slice;
-use tracing::debug;
 
 macro_rules! run_early_pass { ($cx:expr, $f:ident, $($args:expr),*) => ({
     $cx.pass.$f(&$cx.context, $($args),*);
index 6d451f3090acb22c499aad8bd51c2eaab2eaa542..16b7d2cbbaea73ac489f4b4730f76c4eca98a96c 100644 (file)
@@ -12,7 +12,6 @@
 use rustc_span::hygiene::{ExpnKind, MacroKind};
 use rustc_span::symbol::{kw, sym, Symbol};
 use rustc_span::Span;
-use tracing::debug;
 
 declare_tool_lint! {
     pub rustc::DEFAULT_HASH_TYPES,
index 5188ac633d3928b9bcf56cc63bcab58bd76ab4da..8a336844dc2fac73f02f7c0fb003ae23ac77181c 100644 (file)
@@ -29,7 +29,6 @@
 use std::any::Any;
 use std::cell::Cell;
 use std::slice;
-use tracing::debug;
 
 /// Extract the `LintStore` from the query context.
 /// This function exists because we've erased `LintStore` as `dyn Any` in the context.
diff --git a/compiler/rustc_lint/src/let_underscore.rs b/compiler/rustc_lint/src/let_underscore.rs
new file mode 100644 (file)
index 0000000..7e885e6
--- /dev/null
@@ -0,0 +1,175 @@
+use crate::{LateContext, LateLintPass, LintContext};
+use rustc_errors::{Applicability, LintDiagnosticBuilder, MultiSpan};
+use rustc_hir as hir;
+use rustc_middle::ty;
+use rustc_span::Symbol;
+
+declare_lint! {
+    /// The `let_underscore_drop` lint checks for statements which don't bind
+    /// an expression which has a non-trivial Drop implementation to anything,
+    /// causing the expression to be dropped immediately instead of at end of
+    /// scope.
+    ///
+    /// ### Example
+    /// ```
+    /// struct SomeStruct;
+    /// impl Drop for SomeStruct {
+    ///     fn drop(&mut self) {
+    ///         println!("Dropping SomeStruct");
+    ///     }
+    /// }
+    ///
+    /// fn main() {
+    ///    #[warn(let_underscore_drop)]
+    ///     // SomeStuct is dropped immediately instead of at end of scope,
+    ///     // so "Dropping SomeStruct" is printed before "end of main".
+    ///     // The order of prints would be reversed if SomeStruct was bound to
+    ///     // a name (such as "_foo").
+    ///     let _ = SomeStruct;
+    ///     println!("end of main");
+    /// }
+    /// ```
+    ///
+    /// {{produces}}
+    ///
+    /// ### Explanation
+    ///
+    /// Statements which assign an expression to an underscore causes the
+    /// expression to immediately drop instead of extending the expression's
+    /// lifetime to the end of the scope. This is usually unintended,
+    /// especially for types like `MutexGuard`, which are typically used to
+    /// lock a mutex for the duration of an entire scope.
+    ///
+    /// If you want to extend the expression's lifetime to the end of the scope,
+    /// assign an underscore-prefixed name (such as `_foo`) to the expression.
+    /// If you do actually want to drop the expression immediately, then
+    /// calling `std::mem::drop` on the expression is clearer and helps convey
+    /// intent.
+    pub LET_UNDERSCORE_DROP,
+    Allow,
+    "non-binding let on a type that implements `Drop`"
+}
+
+declare_lint! {
+    /// The `let_underscore_lock` lint checks for statements which don't bind
+    /// a mutex to anything, causing the lock to be released immediately instead
+    /// of at end of scope, which is typically incorrect.
+    ///
+    /// ### Example
+    /// ```compile_fail
+    /// use std::sync::{Arc, Mutex};
+    /// use std::thread;
+    /// let data = Arc::new(Mutex::new(0));
+    ///
+    /// thread::spawn(move || {
+    ///     // The lock is immediately released instead of at the end of the
+    ///     // scope, which is probably not intended.
+    ///     let _ = data.lock().unwrap();
+    ///     println!("doing some work");
+    ///     let mut lock = data.lock().unwrap();
+    ///     *lock += 1;
+    /// });
+    /// ```
+    ///
+    /// {{produces}}
+    ///
+    /// ### Explanation
+    ///
+    /// Statements which assign an expression to an underscore causes the
+    /// expression to immediately drop instead of extending the expression's
+    /// lifetime to the end of the scope. This is usually unintended,
+    /// especially for types like `MutexGuard`, which are typically used to
+    /// lock a mutex for the duration of an entire scope.
+    ///
+    /// If you want to extend the expression's lifetime to the end of the scope,
+    /// assign an underscore-prefixed name (such as `_foo`) to the expression.
+    /// If you do actually want to drop the expression immediately, then
+    /// calling `std::mem::drop` on the expression is clearer and helps convey
+    /// intent.
+    pub LET_UNDERSCORE_LOCK,
+    Deny,
+    "non-binding let on a synchronization lock"
+}
+
+declare_lint_pass!(LetUnderscore => [LET_UNDERSCORE_DROP, LET_UNDERSCORE_LOCK]);
+
+const SYNC_GUARD_SYMBOLS: [Symbol; 3] = [
+    rustc_span::sym::MutexGuard,
+    rustc_span::sym::RwLockReadGuard,
+    rustc_span::sym::RwLockWriteGuard,
+];
+
+impl<'tcx> LateLintPass<'tcx> for LetUnderscore {
+    fn check_local(&mut self, cx: &LateContext<'_>, local: &hir::Local<'_>) {
+        if !matches!(local.pat.kind, hir::PatKind::Wild) {
+            return;
+        }
+        if let Some(init) = local.init {
+            let init_ty = cx.typeck_results().expr_ty(init);
+            // If the type has a trivial Drop implementation, then it doesn't
+            // matter that we drop the value immediately.
+            if !init_ty.needs_drop(cx.tcx, cx.param_env) {
+                return;
+            }
+            let is_sync_lock = match init_ty.kind() {
+                ty::Adt(adt, _) => SYNC_GUARD_SYMBOLS
+                    .iter()
+                    .any(|guard_symbol| cx.tcx.is_diagnostic_item(*guard_symbol, adt.did())),
+                _ => false,
+            };
+
+            if is_sync_lock {
+                let mut span = MultiSpan::from_spans(vec![local.pat.span, init.span]);
+                span.push_span_label(
+                    local.pat.span,
+                    "this lock is not assigned to a binding and is immediately dropped".to_string(),
+                );
+                span.push_span_label(
+                    init.span,
+                    "this binding will immediately drop the value assigned to it".to_string(),
+                );
+                cx.struct_span_lint(LET_UNDERSCORE_LOCK, span, |lint| {
+                    build_and_emit_lint(
+                        lint,
+                        local,
+                        init.span,
+                        "non-binding let on a synchronization lock",
+                    )
+                })
+            } else {
+                cx.struct_span_lint(LET_UNDERSCORE_DROP, local.span, |lint| {
+                    build_and_emit_lint(
+                        lint,
+                        local,
+                        init.span,
+                        "non-binding let on a type that implements `Drop`",
+                    );
+                })
+            }
+        }
+    }
+}
+
+fn build_and_emit_lint(
+    lint: LintDiagnosticBuilder<'_, ()>,
+    local: &hir::Local<'_>,
+    init_span: rustc_span::Span,
+    msg: &str,
+) {
+    lint.build(msg)
+        .span_suggestion_verbose(
+            local.pat.span,
+            "consider binding to an unused variable to avoid immediately dropping the value",
+            "_unused",
+            Applicability::MachineApplicable,
+        )
+        .multipart_suggestion(
+            "consider immediately dropping the value",
+            vec![
+                (local.span.until(init_span), "drop(".to_string()),
+                (init_span.shrink_to_hi(), ")".to_string()),
+            ],
+            Applicability::MachineApplicable,
+        )
+        .emit();
+}
index 89409b58f88b90af3d5762e537c33ac986f7c131..f1d8ef2e47d31cb74d2f37a3056d1af66766f1e8 100644 (file)
@@ -21,7 +21,6 @@
 use rustc_session::Session;
 use rustc_span::symbol::{sym, Symbol};
 use rustc_span::{Span, DUMMY_SP};
-use tracing::debug;
 
 use crate::errors::{
     MalformedAttribute, MalformedAttributeSub, OverruledAttribute, OverruledAttributeSub,
index c3065e4a2d9383c13d7bb147f2540c5b6d3efef4..8cbfc82c0f0b6eb8a018c41509e97c4b4597595a 100644 (file)
@@ -42,6 +42,8 @@
 extern crate rustc_middle;
 #[macro_use]
 extern crate rustc_session;
+#[macro_use]
+extern crate tracing;
 
 mod array_into_iter;
 pub mod builtin;
@@ -53,6 +55,7 @@
 pub mod hidden_unicode_codepoints;
 mod internal;
 mod late;
+mod let_underscore;
 mod levels;
 mod methods;
 mod non_ascii_idents;
@@ -84,6 +87,7 @@
 use enum_intrinsics_non_enums::EnumIntrinsicsNonEnums;
 use hidden_unicode_codepoints::*;
 use internal::*;
+use let_underscore::*;
 use methods::*;
 use non_ascii_idents::*;
 use non_fmt_panic::NonPanicFmt;
@@ -131,6 +135,7 @@ macro_rules! early_lint_passes {
                 UnusedBraces: UnusedBraces,
                 UnusedImportBraces: UnusedImportBraces,
                 UnsafeCode: UnsafeCode,
+                SpecialModuleName: SpecialModuleName,
                 AnonymousParameters: AnonymousParameters,
                 EllipsisInclusiveRangePatterns: EllipsisInclusiveRangePatterns::default(),
                 NonCamelCaseTypes: NonCamelCaseTypes,
@@ -186,6 +191,7 @@ macro_rules! late_lint_mod_passes {
                 VariantSizeDifferences: VariantSizeDifferences,
                 BoxPointers: BoxPointers,
                 PathStatements: PathStatements,
+                LetUnderscore: LetUnderscore,
                 // Depends on referenced function signatures in expressions
                 UnusedResults: UnusedResults,
                 NonUpperCaseGlobals: NonUpperCaseGlobals,
@@ -312,6 +318,8 @@ macro_rules! register_passes {
         REDUNDANT_SEMICOLONS
     );
 
+    add_lint_group!("let_underscore", LET_UNDERSCORE_DROP, LET_UNDERSCORE_LOCK);
+
     add_lint_group!(
         "rust_2018_idioms",
         BARE_TRAIT_OBJECTS,
index 484e541afc5879c477a6fefc674ba50bd642e08a..0316651998129037219b6bc7c9e2ac9d4e6adaf2 100644 (file)
@@ -19,7 +19,6 @@
 use std::cmp;
 use std::iter;
 use std::ops::ControlFlow;
-use tracing::debug;
 
 declare_lint! {
     /// The `unused_comparisons` lint detects comparisons made useless by
index c1b82abc1e064a8da1b8dd62e3610232f7722393..dce5d3cfb84ff05b87aeceb2f47148e9bb55eed1 100644 (file)
@@ -12,7 +12,7 @@
 use std::collections::HashMap;
 use std::fmt;
 use std::str::FromStr;
-use syn::{spanned::Spanned, Meta, MetaList, MetaNameValue, NestedMeta, Path};
+use syn::{spanned::Spanned, Attribute, Meta, MetaList, MetaNameValue, NestedMeta, Path};
 use synstructure::{BindingInfo, Structure, VariantInfo};
 
 /// Which kind of suggestion is being created?
@@ -28,8 +28,41 @@ enum SubdiagnosticSuggestionKind {
     Verbose,
 }
 
+impl FromStr for SubdiagnosticSuggestionKind {
+    type Err = ();
+
+    fn from_str(s: &str) -> Result<Self, Self::Err> {
+        match s {
+            "" => Ok(SubdiagnosticSuggestionKind::Normal),
+            "_short" => Ok(SubdiagnosticSuggestionKind::Short),
+            "_hidden" => Ok(SubdiagnosticSuggestionKind::Hidden),
+            "_verbose" => Ok(SubdiagnosticSuggestionKind::Verbose),
+            _ => Err(()),
+        }
+    }
+}
+
+impl SubdiagnosticSuggestionKind {
+    pub fn to_suggestion_style(&self) -> TokenStream {
+        match self {
+            SubdiagnosticSuggestionKind::Normal => {
+                quote! { rustc_errors::SuggestionStyle::ShowCode }
+            }
+            SubdiagnosticSuggestionKind::Short => {
+                quote! { rustc_errors::SuggestionStyle::HideCodeInline }
+            }
+            SubdiagnosticSuggestionKind::Hidden => {
+                quote! { rustc_errors::SuggestionStyle::HideCodeAlways }
+            }
+            SubdiagnosticSuggestionKind::Verbose => {
+                quote! { rustc_errors::SuggestionStyle::ShowAlways }
+            }
+        }
+    }
+}
+
 /// Which kind of subdiagnostic is being created from a variant?
-#[derive(Clone, Copy)]
+#[derive(Clone)]
 enum SubdiagnosticKind {
     /// `#[label(...)]`
     Label,
@@ -40,31 +73,9 @@ enum SubdiagnosticKind {
     /// `#[warning(...)]`
     Warn,
     /// `#[suggestion{,_short,_hidden,_verbose}]`
-    Suggestion(SubdiagnosticSuggestionKind),
-}
-
-impl FromStr for SubdiagnosticKind {
-    type Err = ();
-
-    fn from_str(s: &str) -> Result<Self, Self::Err> {
-        match s {
-            "label" => Ok(SubdiagnosticKind::Label),
-            "note" => Ok(SubdiagnosticKind::Note),
-            "help" => Ok(SubdiagnosticKind::Help),
-            "warning" => Ok(SubdiagnosticKind::Warn),
-            "suggestion" => Ok(SubdiagnosticKind::Suggestion(SubdiagnosticSuggestionKind::Normal)),
-            "suggestion_short" => {
-                Ok(SubdiagnosticKind::Suggestion(SubdiagnosticSuggestionKind::Short))
-            }
-            "suggestion_hidden" => {
-                Ok(SubdiagnosticKind::Suggestion(SubdiagnosticSuggestionKind::Hidden))
-            }
-            "suggestion_verbose" => {
-                Ok(SubdiagnosticKind::Suggestion(SubdiagnosticSuggestionKind::Verbose))
-            }
-            _ => Err(()),
-        }
-    }
+    Suggestion { suggestion_kind: SubdiagnosticSuggestionKind, code: TokenStream },
+    /// `#[multipart_suggestion{,_short,_hidden,_verbose}]`
+    MultipartSuggestion { suggestion_kind: SubdiagnosticSuggestionKind },
 }
 
 impl quote::IdentFragment for SubdiagnosticKind {
@@ -74,17 +85,9 @@ fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
             SubdiagnosticKind::Note => write!(f, "note"),
             SubdiagnosticKind::Help => write!(f, "help"),
             SubdiagnosticKind::Warn => write!(f, "warn"),
-            SubdiagnosticKind::Suggestion(SubdiagnosticSuggestionKind::Normal) => {
-                write!(f, "suggestion")
-            }
-            SubdiagnosticKind::Suggestion(SubdiagnosticSuggestionKind::Short) => {
-                write!(f, "suggestion_short")
-            }
-            SubdiagnosticKind::Suggestion(SubdiagnosticSuggestionKind::Hidden) => {
-                write!(f, "suggestion_hidden")
-            }
-            SubdiagnosticKind::Suggestion(SubdiagnosticSuggestionKind::Verbose) => {
-                write!(f, "suggestion_verbose")
+            SubdiagnosticKind::Suggestion { .. } => write!(f, "suggestion_with_style"),
+            SubdiagnosticKind::MultipartSuggestion { .. } => {
+                write!(f, "multipart_suggestion_with_style")
             }
         }
     }
@@ -148,11 +151,9 @@ pub(crate) fn into_tokens(self) -> TokenStream {
                     variant,
                     span,
                     fields: fields_map,
-                    kinds: Vec::new(),
-                    slugs: Vec::new(),
-                    code: None,
                     span_field: None,
                     applicability: None,
+                    has_suggestion_parts: false,
                 };
                 builder.into_tokens().unwrap_or_else(|v| v.to_compile_error())
             });
@@ -193,21 +194,15 @@ struct SessionSubdiagnosticDeriveBuilder<'a> {
     /// derive builder.
     fields: HashMap<String, TokenStream>,
 
-    /// Subdiagnostic kind of the type/variant.
-    kinds: Vec<(SubdiagnosticKind, proc_macro::Span)>,
-
-    /// Slugs of the subdiagnostic - corresponds to the Fluent identifier for the message - from the
-    /// `#[kind(slug)]` attribute on the type or variant.
-    slugs: Vec<(Path, proc_macro::Span)>,
-    /// If a suggestion, the code to suggest as a replacement - from the `#[kind(code = "...")]`
-    /// attribute on the type or variant.
-    code: Option<(TokenStream, proc_macro::Span)>,
-
     /// Identifier for the binding to the `#[primary_span]` field.
     span_field: Option<(proc_macro2::Ident, proc_macro::Span)>,
     /// If a suggestion, the identifier for the binding to the `#[applicability]` field or a
     /// `rustc_errors::Applicability::*` variant directly.
     applicability: Option<(TokenStream, proc_macro::Span)>,
+
+    /// Set to true when a `#[suggestion_part]` field is encountered, used to generate an error
+    /// during finalization if still `false`.
+    has_suggestion_parts: bool,
 }
 
 impl<'a> HasFieldMap for SessionSubdiagnosticDeriveBuilder<'a> {
@@ -216,125 +211,162 @@ fn get_field_binding(&self, field: &String) -> Option<&TokenStream> {
     }
 }
 
+/// Provides frequently-needed information about the diagnostic kinds being derived for this type.
+#[derive(Clone, Copy, Debug)]
+struct KindsStatistics {
+    has_multipart_suggestion: bool,
+    all_multipart_suggestions: bool,
+    has_normal_suggestion: bool,
+}
+
+impl<'a> FromIterator<&'a SubdiagnosticKind> for KindsStatistics {
+    fn from_iter<T: IntoIterator<Item = &'a SubdiagnosticKind>>(kinds: T) -> Self {
+        let mut ret = Self {
+            has_multipart_suggestion: false,
+            all_multipart_suggestions: true,
+            has_normal_suggestion: false,
+        };
+        for kind in kinds {
+            if let SubdiagnosticKind::MultipartSuggestion { .. } = kind {
+                ret.has_multipart_suggestion = true;
+            } else {
+                ret.all_multipart_suggestions = false;
+            }
+
+            if let SubdiagnosticKind::Suggestion { .. } = kind {
+                ret.has_normal_suggestion = true;
+            }
+        }
+        ret
+    }
+}
+
 impl<'a> SessionSubdiagnosticDeriveBuilder<'a> {
-    fn identify_kind(&mut self) -> Result<(), DiagnosticDeriveError> {
-        for (i, attr) in self.variant.ast().attrs.iter().enumerate() {
+    fn identify_kind(&mut self) -> Result<Vec<(SubdiagnosticKind, Path)>, DiagnosticDeriveError> {
+        let mut kind_slugs = vec![];
+
+        for attr in self.variant.ast().attrs {
             let span = attr.span().unwrap();
 
             let name = attr.path.segments.last().unwrap().ident.to_string();
             let name = name.as_str();
 
             let meta = attr.parse_meta()?;
-            let kind = match meta {
-                Meta::List(MetaList { ref nested, .. }) => {
-                    let mut nested_iter = nested.into_iter();
-                    if let Some(nested_attr) = nested_iter.next() {
-                        match nested_attr {
-                            NestedMeta::Meta(Meta::Path(path)) => {
-                                self.slugs.push((path.clone(), span));
-                            }
-                            NestedMeta::Meta(meta @ Meta::NameValue(_))
-                                if matches!(
-                                    meta.path().segments.last().unwrap().ident.to_string().as_str(),
-                                    "code" | "applicability"
-                                ) =>
-                            {
-                                // don't error for valid follow-up attributes
-                            }
-                            nested_attr => {
-                                throw_invalid_nested_attr!(attr, &nested_attr, |diag| {
-                                    diag.help(
-                                        "first argument of the attribute should be the diagnostic \
-                                         slug",
-                                    )
-                                })
-                            }
-                        };
-                    }
+            let Meta::List(MetaList { ref nested, .. }) = meta else {
+                throw_invalid_attr!(attr, &meta);
+            };
 
-                    for nested_attr in nested_iter {
-                        let meta = match nested_attr {
-                            NestedMeta::Meta(ref meta) => meta,
-                            _ => throw_invalid_nested_attr!(attr, &nested_attr),
-                        };
-
-                        let span = meta.span().unwrap();
-                        let nested_name = meta.path().segments.last().unwrap().ident.to_string();
-                        let nested_name = nested_name.as_str();
-
-                        match meta {
-                            Meta::NameValue(MetaNameValue { lit: syn::Lit::Str(s), .. }) => {
-                                match nested_name {
-                                    "code" => {
-                                        let formatted_str = self.build_format(&s.value(), s.span());
-                                        self.code.set_once((formatted_str, span));
-                                    }
-                                    "applicability" => {
-                                        let value = match Applicability::from_str(&s.value()) {
-                                            Ok(v) => v,
-                                            Err(()) => {
-                                                span_err(span, "invalid applicability").emit();
-                                                Applicability::Unspecified
-                                            }
-                                        };
-                                        self.applicability.set_once((quote! { #value }, span));
-                                    }
-                                    _ => throw_invalid_nested_attr!(attr, &nested_attr, |diag| {
-                                        diag.help(
-                                            "only `code` and `applicability` are valid nested \
-                                             attributes",
-                                        )
-                                    }),
-                                }
-                            }
-                            _ => throw_invalid_nested_attr!(attr, &nested_attr, |diag| {
-                                if matches!(meta, Meta::Path(_)) {
-                                    diag.help(
-                                        "a diagnostic slug must be the first argument to the \
-                                         attribute",
-                                    )
-                                } else {
-                                    diag
-                                }
-                            }),
-                        }
+            let mut kind = match name {
+                "label" => SubdiagnosticKind::Label,
+                "note" => SubdiagnosticKind::Note,
+                "help" => SubdiagnosticKind::Help,
+                "warning" => SubdiagnosticKind::Warn,
+                _ => {
+                    if let Some(suggestion_kind) =
+                        name.strip_prefix("suggestion").and_then(|s| s.parse().ok())
+                    {
+                        SubdiagnosticKind::Suggestion { suggestion_kind, code: TokenStream::new() }
+                    } else if let Some(suggestion_kind) =
+                        name.strip_prefix("multipart_suggestion").and_then(|s| s.parse().ok())
+                    {
+                        SubdiagnosticKind::MultipartSuggestion { suggestion_kind }
+                    } else {
+                        throw_invalid_attr!(attr, &meta);
                     }
-
-                    let Ok(kind) = SubdiagnosticKind::from_str(name) else {
-                        throw_invalid_attr!(attr, &meta)
-                    };
-
-                    kind
                 }
-                _ => throw_invalid_attr!(attr, &meta),
             };
 
-            if matches!(
-                kind,
-                SubdiagnosticKind::Label | SubdiagnosticKind::Help | SubdiagnosticKind::Note
-            ) && self.code.is_some()
-            {
-                throw_span_err!(
-                    span,
-                    &format!("`code` is not a valid nested attribute of a `{}` attribute", name)
-                );
+            let mut slug = None;
+            let mut code = None;
+
+            let mut nested_iter = nested.into_iter();
+            if let Some(nested_attr) = nested_iter.next() {
+                match nested_attr {
+                    NestedMeta::Meta(Meta::Path(path)) => {
+                        slug.set_once((path.clone(), span));
+                    }
+                    NestedMeta::Meta(meta @ Meta::NameValue(_))
+                        if matches!(
+                            meta.path().segments.last().unwrap().ident.to_string().as_str(),
+                            "code" | "applicability"
+                        ) =>
+                    {
+                        // Don't error for valid follow-up attributes.
+                    }
+                    nested_attr => {
+                        throw_invalid_nested_attr!(attr, &nested_attr, |diag| {
+                            diag.help(
+                                "first argument of the attribute should be the diagnostic \
+                                 slug",
+                            )
+                        })
+                    }
+                };
             }
 
-            if matches!(
-                kind,
-                SubdiagnosticKind::Label | SubdiagnosticKind::Help | SubdiagnosticKind::Note
-            ) && self.applicability.is_some()
-            {
-                throw_span_err!(
-                    span,
-                    &format!(
-                        "`applicability` is not a valid nested attribute of a `{}` attribute",
-                        name
-                    )
-                );
+            for nested_attr in nested_iter {
+                let meta = match nested_attr {
+                    NestedMeta::Meta(ref meta) => meta,
+                    _ => throw_invalid_nested_attr!(attr, &nested_attr),
+                };
+
+                let span = meta.span().unwrap();
+                let nested_name = meta.path().segments.last().unwrap().ident.to_string();
+                let nested_name = nested_name.as_str();
+
+                let value = match meta {
+                    Meta::NameValue(MetaNameValue { lit: syn::Lit::Str(value), .. }) => value,
+                    Meta::Path(_) => throw_invalid_nested_attr!(attr, &nested_attr, |diag| {
+                        diag.help("a diagnostic slug must be the first argument to the attribute")
+                    }),
+                    _ => throw_invalid_nested_attr!(attr, &nested_attr),
+                };
+
+                match nested_name {
+                    "code" => {
+                        if matches!(kind, SubdiagnosticKind::Suggestion { .. }) {
+                            let formatted_str = self.build_format(&value.value(), value.span());
+                            code.set_once((formatted_str, span));
+                        } else {
+                            span_err(
+                                span,
+                                &format!(
+                                    "`code` is not a valid nested attribute of a `{}` attribute",
+                                    name
+                                ),
+                            )
+                            .emit();
+                        }
+                    }
+                    "applicability" => {
+                        if matches!(
+                            kind,
+                            SubdiagnosticKind::Suggestion { .. }
+                                | SubdiagnosticKind::MultipartSuggestion { .. }
+                        ) {
+                            let value =
+                                Applicability::from_str(&value.value()).unwrap_or_else(|()| {
+                                    span_err(span, "invalid applicability").emit();
+                                    Applicability::Unspecified
+                                });
+                            self.applicability.set_once((quote! { #value }, span));
+                        } else {
+                            span_err(
+                                span,
+                                &format!(
+                                    "`applicability` is not a valid nested attribute of a `{}` attribute",
+                                    name
+                                )
+                            ).emit();
+                        }
+                    }
+                    _ => throw_invalid_nested_attr!(attr, &nested_attr, |diag| {
+                        diag.help("only `code` and `applicability` are valid nested attributes")
+                    }),
+                }
             }
 
-            if self.slugs.len() != i + 1 {
+            let Some((slug, _)) = slug else {
                 throw_span_err!(
                     span,
                     &format!(
@@ -342,146 +374,334 @@ fn identify_kind(&mut self) -> Result<(), DiagnosticDeriveError> {
                         name
                     )
                 );
+            };
+
+            match kind {
+                SubdiagnosticKind::Suggestion { code: ref mut code_field, .. } => {
+                    let Some((code, _)) = code else {
+                        throw_span_err!(span, "suggestion without `code = \"...\"`");
+                    };
+                    *code_field = code;
+                }
+                SubdiagnosticKind::Label
+                | SubdiagnosticKind::Note
+                | SubdiagnosticKind::Help
+                | SubdiagnosticKind::Warn
+                | SubdiagnosticKind::MultipartSuggestion { .. } => {}
             }
 
-            self.kinds.push((kind, span));
+            kind_slugs.push((kind, slug))
         }
 
-        Ok(())
+        Ok(kind_slugs)
     }
 
-    fn generate_field_code(
+    /// Generates the code for a field with no attributes.
+    fn generate_field_set_arg(&mut self, binding: &BindingInfo<'_>) -> TokenStream {
+        let ast = binding.ast();
+        assert_eq!(ast.attrs.len(), 0, "field with attribute used as diagnostic arg");
+
+        let diag = &self.diag;
+        let ident = ast.ident.as_ref().unwrap();
+        quote! {
+            #diag.set_arg(
+                stringify!(#ident),
+                #binding
+            );
+        }
+    }
+
+    /// Generates the necessary code for all attributes on a field.
+    fn generate_field_attr_code(
         &mut self,
         binding: &BindingInfo<'_>,
-        have_suggestion: bool,
-    ) -> Result<TokenStream, DiagnosticDeriveError> {
+        kind_stats: KindsStatistics,
+    ) -> TokenStream {
         let ast = binding.ast();
+        assert!(ast.attrs.len() > 0, "field without attributes generating attr code");
 
+        // Abstract over `Vec<T>` and `Option<T>` fields using `FieldInnerTy`, which will
+        // apply the generated code on each element in the `Vec` or `Option`.
         let inner_ty = FieldInnerTy::from_type(&ast.ty);
-        let info = FieldInfo {
-            binding: binding,
-            ty: inner_ty.inner_type().unwrap_or(&ast.ty),
-            span: &ast.span(),
-        };
+        ast.attrs
+            .iter()
+            .map(|attr| {
+                let info = FieldInfo {
+                    binding,
+                    ty: inner_ty.inner_type().unwrap_or(&ast.ty),
+                    span: &ast.span(),
+                };
 
-        for attr in &ast.attrs {
-            let name = attr.path.segments.last().unwrap().ident.to_string();
-            let name = name.as_str();
-            let span = attr.span().unwrap();
+                let generated = self
+                    .generate_field_code_inner(kind_stats, attr, info)
+                    .unwrap_or_else(|v| v.to_compile_error());
 
-            let meta = attr.parse_meta()?;
-            match meta {
-                Meta::Path(_) => match name {
-                    "primary_span" => {
-                        report_error_if_not_applied_to_span(attr, &info)?;
-                        self.span_field.set_once((binding.binding.clone(), span));
-                        return Ok(quote! {});
-                    }
-                    "applicability" if have_suggestion => {
-                        report_error_if_not_applied_to_applicability(attr, &info)?;
-                        let binding = binding.binding.clone();
-                        self.applicability.set_once((quote! { #binding }, span));
-                        return Ok(quote! {});
-                    }
-                    "applicability" => {
-                        span_err(span, "`#[applicability]` is only valid on suggestions").emit();
-                        return Ok(quote! {});
-                    }
-                    "skip_arg" => {
-                        return Ok(quote! {});
-                    }
-                    _ => throw_invalid_attr!(attr, &meta, |diag| {
+                inner_ty.with(binding, generated)
+            })
+            .collect()
+    }
+
+    fn generate_field_code_inner(
+        &mut self,
+        kind_stats: KindsStatistics,
+        attr: &Attribute,
+        info: FieldInfo<'_>,
+    ) -> Result<TokenStream, DiagnosticDeriveError> {
+        let meta = attr.parse_meta()?;
+        match meta {
+            Meta::Path(path) => self.generate_field_code_inner_path(kind_stats, attr, info, path),
+            Meta::List(list @ MetaList { .. }) => {
+                self.generate_field_code_inner_list(kind_stats, attr, info, list)
+            }
+            _ => throw_invalid_attr!(attr, &meta),
+        }
+    }
+
+    /// Generates the code for a `[Meta::Path]`-like attribute on a field (e.g. `#[primary_span]`).
+    fn generate_field_code_inner_path(
+        &mut self,
+        kind_stats: KindsStatistics,
+        attr: &Attribute,
+        info: FieldInfo<'_>,
+        path: Path,
+    ) -> Result<TokenStream, DiagnosticDeriveError> {
+        let span = attr.span().unwrap();
+        let ident = &path.segments.last().unwrap().ident;
+        let name = ident.to_string();
+        let name = name.as_str();
+
+        match name {
+            "skip_arg" => Ok(quote! {}),
+            "primary_span" => {
+                if kind_stats.has_multipart_suggestion {
+                    throw_invalid_attr!(attr, &Meta::Path(path), |diag| {
                         diag.help(
-                            "only `primary_span`, `applicability` and `skip_arg` are valid field \
-                             attributes",
+                            "multipart suggestions use one or more `#[suggestion_part]`s rather \
+                            than one `#[primary_span]`",
                         )
-                    }),
-                },
-                _ => throw_invalid_attr!(attr, &meta),
+                    })
+                }
+
+                report_error_if_not_applied_to_span(attr, &info)?;
+
+                let binding = info.binding.binding.clone();
+                self.span_field.set_once((binding, span));
+
+                Ok(quote! {})
             }
+            "suggestion_part" => {
+                self.has_suggestion_parts = true;
+
+                if kind_stats.has_multipart_suggestion {
+                    span_err(span, "`#[suggestion_part(...)]` attribute without `code = \"...\"`")
+                        .emit();
+                    Ok(quote! {})
+                } else {
+                    throw_invalid_attr!(attr, &Meta::Path(path), |diag| {
+                        diag.help(
+                                "`#[suggestion_part(...)]` is only valid in multipart suggestions, use `#[primary_span]` instead",
+                            )
+                    });
+                }
+            }
+            "applicability" => {
+                if kind_stats.has_multipart_suggestion || kind_stats.has_normal_suggestion {
+                    report_error_if_not_applied_to_applicability(attr, &info)?;
+
+                    let binding = info.binding.binding.clone();
+                    self.applicability.set_once((quote! { #binding }, span));
+                } else {
+                    span_err(span, "`#[applicability]` is only valid on suggestions").emit();
+                }
+
+                Ok(quote! {})
+            }
+            _ => throw_invalid_attr!(attr, &Meta::Path(path), |diag| {
+                let mut span_attrs = vec![];
+                if kind_stats.has_multipart_suggestion {
+                    span_attrs.push("suggestion_part");
+                }
+                if !kind_stats.all_multipart_suggestions {
+                    span_attrs.push("primary_span")
+                }
+                diag.help(format!(
+                    "only `{}`, `applicability` and `skip_arg` are valid field attributes",
+                    span_attrs.join(", ")
+                ))
+            }),
         }
+    }
 
-        let ident = ast.ident.as_ref().unwrap();
+    /// Generates the code for a `[Meta::List]`-like attribute on a field (e.g.
+    /// `#[suggestion_part(code = "...")]`).
+    fn generate_field_code_inner_list(
+        &mut self,
+        kind_stats: KindsStatistics,
+        attr: &Attribute,
+        info: FieldInfo<'_>,
+        list: MetaList,
+    ) -> Result<TokenStream, DiagnosticDeriveError> {
+        let span = attr.span().unwrap();
+        let ident = &list.path.segments.last().unwrap().ident;
+        let name = ident.to_string();
+        let name = name.as_str();
+
+        match name {
+            "suggestion_part" => {
+                if !kind_stats.has_multipart_suggestion {
+                    throw_invalid_attr!(attr, &Meta::List(list), |diag| {
+                        diag.help(
+                            "`#[suggestion_part(...)]` is only valid in multipart suggestions",
+                        )
+                    })
+                }
 
-        let diag = &self.diag;
-        let generated = quote! {
-            #diag.set_arg(
-                stringify!(#ident),
-                #binding
-            );
-        };
+                self.has_suggestion_parts = true;
+
+                report_error_if_not_applied_to_span(attr, &info)?;
+
+                let mut code = None;
+                for nested_attr in list.nested.iter() {
+                    let NestedMeta::Meta(ref meta) = nested_attr else {
+                        throw_invalid_nested_attr!(attr, &nested_attr);
+                    };
+
+                    let span = meta.span().unwrap();
+                    let nested_name = meta.path().segments.last().unwrap().ident.to_string();
+                    let nested_name = nested_name.as_str();
 
-        Ok(inner_ty.with(binding, generated))
+                    let Meta::NameValue(MetaNameValue { lit: syn::Lit::Str(value), .. }) = meta else {
+                        throw_invalid_nested_attr!(attr, &nested_attr);
+                    };
+
+                    match nested_name {
+                        "code" => {
+                            let formatted_str = self.build_format(&value.value(), value.span());
+                            code.set_once((formatted_str, span));
+                        }
+                        _ => throw_invalid_nested_attr!(attr, &nested_attr, |diag| {
+                            diag.help("`code` is the only valid nested attribute")
+                        }),
+                    }
+                }
+
+                let Some((code, _)) = code else {
+                    span_err(span, "`#[suggestion_part(...)]` attribute without `code = \"...\"`")
+                        .emit();
+                    return Ok(quote! {});
+                };
+                let binding = info.binding;
+
+                Ok(quote! { suggestions.push((#binding, #code)); })
+            }
+            _ => throw_invalid_attr!(attr, &Meta::List(list), |diag| {
+                let mut span_attrs = vec![];
+                if kind_stats.has_multipart_suggestion {
+                    span_attrs.push("suggestion_part");
+                }
+                if !kind_stats.all_multipart_suggestions {
+                    span_attrs.push("primary_span")
+                }
+                diag.help(format!(
+                    "only `{}`, `applicability` and `skip_arg` are valid field attributes",
+                    span_attrs.join(", ")
+                ))
+            }),
+        }
     }
 
-    fn into_tokens(&mut self) -> Result<TokenStream, DiagnosticDeriveError> {
-        self.identify_kind()?;
-        if self.kinds.is_empty() {
+    pub fn into_tokens(&mut self) -> Result<TokenStream, DiagnosticDeriveError> {
+        let kind_slugs = self.identify_kind()?;
+        if kind_slugs.is_empty() {
             throw_span_err!(
                 self.variant.ast().ident.span().unwrap(),
                 "subdiagnostic kind not specified"
             );
         };
-        let have_suggestion =
-            self.kinds.iter().any(|(k, _)| matches!(k, SubdiagnosticKind::Suggestion(_)));
-        let mut args = TokenStream::new();
-        for binding in self.variant.bindings() {
-            let arg = self
-                .generate_field_code(binding, have_suggestion)
-                .unwrap_or_else(|v| v.to_compile_error());
-            args.extend(arg);
-        }
-        let mut tokens = TokenStream::new();
-        for ((kind, _), (slug, _)) in self.kinds.iter().zip(&self.slugs) {
-            let code = match self.code.as_ref() {
-                Some((code, _)) => Some(quote! { #code }),
-                None if have_suggestion => {
-                    span_err(self.span, "suggestion without `code = \"...\"`").emit();
-                    Some(quote! { /* macro error */ "..." })
-                }
-                None => None,
-            };
 
-            let span_field = self.span_field.as_ref().map(|(span, _)| span);
-            let applicability = match self.applicability.clone() {
-                Some((applicability, _)) => Some(applicability),
-                None if have_suggestion => {
-                    span_err(self.span, "suggestion without `applicability`").emit();
-                    Some(quote! { rustc_errors::Applicability::Unspecified })
-                }
-                None => None,
-            };
+        let kind_stats: KindsStatistics = kind_slugs.iter().map(|(kind, _slug)| kind).collect();
+
+        let init = if kind_stats.has_multipart_suggestion {
+            quote! { let mut suggestions = Vec::new(); }
+        } else {
+            quote! {}
+        };
+
+        let attr_args: TokenStream = self
+            .variant
+            .bindings()
+            .iter()
+            .filter(|binding| !binding.ast().attrs.is_empty())
+            .map(|binding| self.generate_field_attr_code(binding, kind_stats))
+            .collect();
+
+        let span_field = self.span_field.as_ref().map(|(span, _)| span);
+        let applicability = self.applicability.take().map_or_else(
+            || quote! { rustc_errors::Applicability::Unspecified },
+            |(applicability, _)| applicability,
+        );
 
-            let diag = &self.diag;
+        let diag = &self.diag;
+        let mut calls = TokenStream::new();
+        for (kind, slug) in kind_slugs {
             let name = format_ident!("{}{}", if span_field.is_some() { "span_" } else { "" }, kind);
             let message = quote! { rustc_errors::fluent::#slug };
-            let call = if matches!(kind, SubdiagnosticKind::Suggestion(..)) {
-                if let Some(span) = span_field {
-                    quote! { #diag.#name(#span, #message, #code, #applicability); }
-                } else {
-                    span_err(self.span, "suggestion without `#[primary_span]` field").emit();
-                    quote! { unreachable!(); }
+            let call = match kind {
+                SubdiagnosticKind::Suggestion { suggestion_kind, code } => {
+                    if let Some(span) = span_field {
+                        let style = suggestion_kind.to_suggestion_style();
+
+                        quote! { #diag.#name(#span, #message, #code, #applicability, #style); }
+                    } else {
+                        span_err(self.span, "suggestion without `#[primary_span]` field").emit();
+                        quote! { unreachable!(); }
+                    }
                 }
-            } else if matches!(kind, SubdiagnosticKind::Label) {
-                if let Some(span) = span_field {
-                    quote! { #diag.#name(#span, #message); }
-                } else {
-                    span_err(self.span, "label without `#[primary_span]` field").emit();
-                    quote! { unreachable!(); }
+                SubdiagnosticKind::MultipartSuggestion { suggestion_kind } => {
+                    if !self.has_suggestion_parts {
+                        span_err(
+                            self.span,
+                            "multipart suggestion without any `#[suggestion_part(...)]` fields",
+                        )
+                        .emit();
+                    }
+
+                    let style = suggestion_kind.to_suggestion_style();
+
+                    quote! { #diag.#name(#message, suggestions, #applicability, #style); }
                 }
-            } else {
-                if let Some(span) = span_field {
-                    quote! { #diag.#name(#span, #message); }
-                } else {
-                    quote! { #diag.#name(#message); }
+                SubdiagnosticKind::Label => {
+                    if let Some(span) = span_field {
+                        quote! { #diag.#name(#span, #message); }
+                    } else {
+                        span_err(self.span, "label without `#[primary_span]` field").emit();
+                        quote! { unreachable!(); }
+                    }
+                }
+                _ => {
+                    if let Some(span) = span_field {
+                        quote! { #diag.#name(#span, #message); }
+                    } else {
+                        quote! { #diag.#name(#message); }
+                    }
                 }
             };
-            tokens.extend(quote! {
-                #call
-                #args
-            });
+            calls.extend(call);
         }
 
-        Ok(tokens)
+        let plain_args: TokenStream = self
+            .variant
+            .bindings()
+            .iter()
+            .filter(|binding| binding.ast().attrs.is_empty())
+            .map(|binding| self.generate_field_set_arg(binding))
+            .collect();
+
+        Ok(quote! {
+            #init
+            #attr_args
+            #calls
+            #plain_args
+        })
     }
 }
index 708d0b1fd8a301818b8b667233975772cfffe0ea..6a5716600b3b34379b3257fcf93121b347a3ead0 100644 (file)
@@ -29,7 +29,6 @@
 use std::ops::Fn;
 use std::path::Path;
 use std::{cmp, env};
-use tracing::{debug, info};
 
 #[derive(Clone)]
 pub struct CStore {
@@ -263,7 +262,7 @@ pub fn into_cstore(self) -> CStore {
     fn existing_match(&self, name: Symbol, hash: Option<Svh>, kind: PathKind) -> Option<CrateNum> {
         for (cnum, data) in self.cstore.iter_crate_data() {
             if data.name() != name {
-                tracing::trace!("{} did not match {}", data.name(), name);
+                trace!("{} did not match {}", data.name(), name);
                 continue;
             }
 
index b765c34f8e364d2d4ec15846bd5d4daa5718a9a9..1a25e987d3a62c5369e772bf5592938838b137a7 100644 (file)
@@ -158,11 +158,11 @@ fn calculate_type(tcx: TyCtxt<'_>, ty: CrateType) -> DependencyList {
         let name = tcx.crate_name(cnum);
         let src = tcx.used_crate_source(cnum);
         if src.dylib.is_some() {
-            tracing::info!("adding dylib: {}", name);
+            info!("adding dylib: {}", name);
             add_library(tcx, cnum, RequireDynamic, &mut formats);
             let deps = tcx.dylib_dependency_formats(cnum);
             for &(depnum, style) in deps.iter() {
-                tracing::info!("adding {:?}: {}", style, tcx.crate_name(depnum));
+                info!("adding {:?}: {}", style, tcx.crate_name(depnum));
                 add_library(tcx, depnum, style, &mut formats);
             }
         }
@@ -190,7 +190,7 @@ fn calculate_type(tcx: TyCtxt<'_>, ty: CrateType) -> DependencyList {
             && tcx.dep_kind(cnum) == CrateDepKind::Explicit
         {
             assert!(src.rlib.is_some() || src.rmeta.is_some());
-            tracing::info!("adding staticlib: {}", tcx.crate_name(cnum));
+            info!("adding staticlib: {}", tcx.crate_name(cnum));
             add_library(tcx, cnum, RequireStatic, &mut formats);
             ret[cnum.as_usize() - 1] = Linkage::Static;
         }
index 6440f3e390cf1fde772fe34a0b50f79eef8faf20..337d3cca2aed7fb3acab33145400fca40561ba3a 100644 (file)
@@ -26,6 +26,9 @@
 #[macro_use]
 extern crate rustc_data_structures;
 
+#[macro_use]
+extern crate tracing;
+
 pub use rmeta::{provide, provide_extern};
 
 mod dependency_format;
index 2c1c84b0be26a874d7d9e6657f6a05f105381460..5b7d0c8581ab214217dc49f520d3044fafbfcbfa 100644 (file)
 use std::io::{Read, Result as IoResult, Write};
 use std::path::{Path, PathBuf};
 use std::{cmp, fmt, fs};
-use tracing::{debug, info};
 
 #[derive(Clone)]
 pub(crate) struct CrateLocator<'a> {
index d0e0aa91480c917eb56c5243795c9c5ef5c3c1f3..6f026678170b7af312fbde3ba26f97d40ebf3982 100644 (file)
@@ -4,7 +4,6 @@
 use crate::rmeta::*;
 
 use rustc_ast as ast;
-use rustc_ast::ptr::P;
 use rustc_data_structures::captures::Captures;
 use rustc_data_structures::fx::FxHashMap;
 use rustc_data_structures::svh::Svh;
@@ -33,7 +32,7 @@
 use rustc_session::Session;
 use rustc_span::hygiene::{ExpnIndex, MacroKind};
 use rustc_span::source_map::{respan, Spanned};
-use rustc_span::symbol::{sym, Ident, Symbol};
+use rustc_span::symbol::{kw, sym, Ident, Symbol};
 use rustc_span::{self, BytePos, ExpnId, Pos, Span, SyntaxContext, DUMMY_SP};
 
 use proc_macro::bridge::client::ProcMacro;
@@ -42,7 +41,6 @@
 use std::mem;
 use std::num::NonZeroUsize;
 use std::path::Path;
-use tracing::debug;
 
 pub(super) use cstore_impl::provide;
 pub use cstore_impl::provide_extern;
@@ -786,26 +784,11 @@ fn item_ident(self, item_index: DefIndex, sess: &Session) -> Ident {
         self.opt_item_ident(item_index, sess).expect("no encoded ident for item")
     }
 
-    fn maybe_kind(self, item_id: DefIndex) -> Option<EntryKind> {
-        self.root.tables.kind.get(self, item_id).map(|k| k.decode(self))
-    }
-
     #[inline]
     pub(super) fn map_encoded_cnum_to_current(self, cnum: CrateNum) -> CrateNum {
         if cnum == LOCAL_CRATE { self.cnum } else { self.cnum_map[cnum] }
     }
 
-    fn kind(self, item_id: DefIndex) -> EntryKind {
-        self.maybe_kind(item_id).unwrap_or_else(|| {
-            bug!(
-                "CrateMetadata::kind({:?}): id not found, in crate {:?} with number {}",
-                item_id,
-                self.root.name,
-                self.cnum,
-            )
-        })
-    }
-
     fn def_kind(self, item_id: DefIndex) -> DefKind {
         self.root.tables.opt_def_kind.get(self, item_id).unwrap_or_else(|| {
             bug!(
@@ -857,21 +840,16 @@ fn load_proc_macro(self, id: DefIndex, sess: &Session) -> SyntaxExtension {
         )
     }
 
-    fn get_variant(self, kind: &EntryKind, index: DefIndex, parent_did: DefId) -> ty::VariantDef {
-        let data = match kind {
-            EntryKind::Variant(data) | EntryKind::Struct(data) | EntryKind::Union(data) => {
-                data.decode(self)
-            }
-            _ => bug!(),
-        };
-
+    fn get_variant(self, kind: &DefKind, index: DefIndex, parent_did: DefId) -> ty::VariantDef {
         let adt_kind = match kind {
-            EntryKind::Variant(_) => ty::AdtKind::Enum,
-            EntryKind::Struct(..) => ty::AdtKind::Struct,
-            EntryKind::Union(..) => ty::AdtKind::Union,
+            DefKind::Variant => ty::AdtKind::Enum,
+            DefKind::Struct => ty::AdtKind::Struct,
+            DefKind::Union => ty::AdtKind::Union,
             _ => bug!(),
         };
 
+        let data = self.root.tables.variant_data.get(self, index).unwrap().decode(self);
+
         let variant_did =
             if adt_kind == ty::AdtKind::Enum { Some(self.local_def_id(index)) } else { None };
         let ctor_did = data.ctor.map(|index| self.local_def_id(index));
@@ -902,13 +880,13 @@ fn get_variant(self, kind: &EntryKind, index: DefIndex, parent_did: DefId) -> ty
     }
 
     fn get_adt_def(self, item_id: DefIndex, tcx: TyCtxt<'tcx>) -> ty::AdtDef<'tcx> {
-        let kind = self.kind(item_id);
+        let kind = self.def_kind(item_id);
         let did = self.local_def_id(item_id);
 
         let adt_kind = match kind {
-            EntryKind::Enum => ty::AdtKind::Enum,
-            EntryKind::Struct(_) => ty::AdtKind::Struct,
-            EntryKind::Union(_) => ty::AdtKind::Union,
+            DefKind::Enum => ty::AdtKind::Enum,
+            DefKind::Struct => ty::AdtKind::Struct,
+            DefKind::Union => ty::AdtKind::Union,
             _ => bug!("get_adt_def called on a non-ADT {:?}", did),
         };
         let repr = self.root.tables.repr_options.get(self, item_id).unwrap().decode(self);
@@ -920,7 +898,7 @@ fn get_adt_def(self, item_id: DefIndex, tcx: TyCtxt<'tcx>) -> ty::AdtDef<'tcx> {
                 .get(self, item_id)
                 .unwrap_or_else(LazyArray::empty)
                 .decode(self)
-                .map(|index| self.get_variant(&self.kind(index), index, did))
+                .map(|index| self.get_variant(&self.def_kind(index), index, did))
                 .collect()
         } else {
             std::iter::once(self.get_variant(&kind, item_id, did)).collect()
@@ -1030,10 +1008,9 @@ fn for_each_module_child(
                 let vis = self.get_visibility(child_index);
                 let span = self.get_span(child_index, sess);
                 let macro_rules = match kind {
-                    DefKind::Macro(..) => match self.kind(child_index) {
-                        EntryKind::MacroDef(_, macro_rules) => macro_rules,
-                        _ => unreachable!(),
-                    },
+                    DefKind::Macro(..) => {
+                        self.root.tables.macro_rules.get(self, child_index).is_some()
+                    }
                     _ => false,
                 };
 
@@ -1087,14 +1064,10 @@ fn for_each_module_child(
             }
         }
 
-        match self.kind(id) {
-            EntryKind::Mod(exports) => {
-                for exp in exports.decode((self, sess)) {
-                    callback(exp);
-                }
+        if let Some(exports) = self.root.tables.module_reexports.get(self, id) {
+            for exp in exports.decode((self, sess)) {
+                callback(exp);
             }
-            EntryKind::Enum | EntryKind::Trait => {}
-            _ => bug!("`for_each_module_child` is called on a non-module: {:?}", self.def_kind(id)),
         }
     }
 
@@ -1107,19 +1080,21 @@ fn is_item_mir_available(self, id: DefIndex) -> bool {
     }
 
     fn module_expansion(self, id: DefIndex, sess: &Session) -> ExpnId {
-        match self.kind(id) {
-            EntryKind::Mod(_) | EntryKind::Enum | EntryKind::Trait => {
-                self.get_expn_that_defined(id, sess)
-            }
+        match self.def_kind(id) {
+            DefKind::Mod | DefKind::Enum | DefKind::Trait => self.get_expn_that_defined(id, sess),
             _ => panic!("Expected module, found {:?}", self.local_def_id(id)),
         }
     }
 
-    fn get_fn_has_self_parameter(self, id: DefIndex) -> bool {
-        match self.kind(id) {
-            EntryKind::AssocFn { has_self, .. } => has_self,
-            _ => false,
-        }
+    fn get_fn_has_self_parameter(self, id: DefIndex, sess: &'a Session) -> bool {
+        self.root
+            .tables
+            .fn_arg_names
+            .get(self, id)
+            .unwrap_or_else(LazyArray::empty)
+            .decode((self, sess))
+            .nth(0)
+            .map_or(false, |ident| ident.name == kw::SelfLower)
     }
 
     fn get_associated_item_def_ids(
@@ -1136,15 +1111,17 @@ fn get_associated_item_def_ids(
             .map(move |child_index| self.local_def_id(child_index))
     }
 
-    fn get_associated_item(self, id: DefIndex) -> ty::AssocItem {
+    fn get_associated_item(self, id: DefIndex, sess: &'a Session) -> ty::AssocItem {
         let name = self.item_name(id);
 
-        let (kind, container, has_self) = match self.kind(id) {
-            EntryKind::AssocConst(container) => (ty::AssocKind::Const, container, false),
-            EntryKind::AssocFn { container, has_self } => (ty::AssocKind::Fn, container, has_self),
-            EntryKind::AssocType(container) => (ty::AssocKind::Type, container, false),
-            _ => bug!("cannot get associated-item of `{:?}`", id),
+        let kind = match self.def_kind(id) {
+            DefKind::AssocConst => ty::AssocKind::Const,
+            DefKind::AssocFn => ty::AssocKind::Fn,
+            DefKind::AssocTy => ty::AssocKind::Type,
+            _ => bug!("cannot get associated-item of `{:?}`", self.def_key(id)),
         };
+        let has_self = self.get_fn_has_self_parameter(id, sess);
+        let container = self.root.tables.assoc_container.get(self, id).unwrap();
 
         ty::AssocItem {
             name,
@@ -1157,9 +1134,9 @@ fn get_associated_item(self, id: DefIndex) -> ty::AssocItem {
     }
 
     fn get_ctor_def_id_and_kind(self, node_id: DefIndex) -> Option<(DefId, CtorKind)> {
-        match self.kind(node_id) {
-            EntryKind::Struct(data) | EntryKind::Variant(data) => {
-                let vdata = data.decode(self);
+        match self.def_kind(node_id) {
+            DefKind::Struct | DefKind::Variant => {
+                let vdata = self.root.tables.variant_data.get(self, node_id).unwrap().decode(self);
                 vdata.ctor.map(|index| (self.local_def_id(index), vdata.ctor_kind))
             }
             _ => None,
@@ -1347,18 +1324,22 @@ fn exported_symbols(
     }
 
     fn get_macro(self, id: DefIndex, sess: &Session) -> ast::MacroDef {
-        match self.kind(id) {
-            EntryKind::MacroDef(mac_args, macro_rules) => {
-                ast::MacroDef { body: P(mac_args.decode((self, sess))), macro_rules }
+        match self.def_kind(id) {
+            DefKind::Macro(_) => {
+                let macro_rules = self.root.tables.macro_rules.get(self, id).is_some();
+                let body =
+                    self.root.tables.macro_definition.get(self, id).unwrap().decode((self, sess));
+                ast::MacroDef { macro_rules, body: ast::ptr::P(body) }
             }
             _ => bug!(),
         }
     }
 
     fn is_foreign_item(self, id: DefIndex) -> bool {
-        match self.kind(id) {
-            EntryKind::ForeignStatic | EntryKind::ForeignFn => true,
-            _ => false,
+        if let Some(parent) = self.def_key(id).parent {
+            matches!(self.def_kind(parent), DefKind::ForeignMod)
+        } else {
+            false
         }
     }
 
index 9d201a0c799928174f80efd1f93135013ed01733..6b447ebd99910ae21f348d34728e24b00095168f 100644 (file)
@@ -233,7 +233,7 @@ fn into_args(self) -> (DefId, SimplifiedType) {
     associated_item_def_ids => {
         tcx.arena.alloc_from_iter(cdata.get_associated_item_def_ids(def_id.index, tcx.sess))
     }
-    associated_item => { cdata.get_associated_item(def_id.index) }
+    associated_item => { cdata.get_associated_item(def_id.index, tcx.sess) }
     inherent_impls => { cdata.get_inherent_implementations_for_type(tcx, def_id.index) }
     is_foreign_item => { cdata.is_foreign_item(def_id.index) }
     item_attrs => { tcx.arena.alloc_from_iter(cdata.get_item_attrs(def_id.index, tcx.sess)) }
@@ -535,8 +535,8 @@ pub fn load_macro_untracked(&self, id: DefId, sess: &Session) -> LoadedMacro {
         )
     }
 
-    pub fn fn_has_self_parameter_untracked(&self, def: DefId) -> bool {
-        self.get_crate_data(def.krate).get_fn_has_self_parameter(def.index)
+    pub fn fn_has_self_parameter_untracked(&self, def: DefId, sess: &Session) -> bool {
+        self.get_crate_data(def.krate).get_fn_has_self_parameter(def.index, sess)
     }
 
     pub fn crate_source_untracked(&self, cnum: CrateNum) -> Lrc<CrateSource> {
index 3482d9f04514e561b08c458639af28b7dde76292..4be4d4b7872aeeaa7d745d034cf2daf247ac3e4e 100644 (file)
@@ -16,7 +16,6 @@
 use rustc_hir::definitions::DefPathData;
 use rustc_hir::intravisit::{self, Visitor};
 use rustc_hir::lang_items;
-use rustc_hir::{AnonConst, GenericParamKind};
 use rustc_middle::hir::nested_filter;
 use rustc_middle::middle::dependency_format::Linkage;
 use rustc_middle::middle::exported_symbols::{
@@ -44,7 +43,6 @@
 use std::iter;
 use std::num::NonZeroUsize;
 use std::path::{Path, PathBuf};
-use tracing::{debug, trace};
 
 pub(super) struct EncodeContext<'a, 'tcx> {
     opaque: opaque::FileEncoder,
@@ -1020,6 +1018,89 @@ fn should_encode_generics(def_kind: DefKind) -> bool {
     }
 }
 
+fn should_encode_type(tcx: TyCtxt<'_>, def_id: LocalDefId, def_kind: DefKind) -> bool {
+    match def_kind {
+        DefKind::Struct
+        | DefKind::Union
+        | DefKind::Enum
+        | DefKind::Variant
+        | DefKind::Ctor(..)
+        | DefKind::Field
+        | DefKind::Fn
+        | DefKind::Const
+        | DefKind::Static(..)
+        | DefKind::TyAlias
+        | DefKind::OpaqueTy
+        | DefKind::ForeignTy
+        | DefKind::Impl
+        | DefKind::AssocFn
+        | DefKind::AssocConst
+        | DefKind::Closure
+        | DefKind::Generator
+        | DefKind::ConstParam
+        | DefKind::AnonConst
+        | DefKind::InlineConst => true,
+
+        DefKind::AssocTy => {
+            let assoc_item = tcx.associated_item(def_id);
+            match assoc_item.container {
+                ty::AssocItemContainer::ImplContainer => true,
+                ty::AssocItemContainer::TraitContainer => assoc_item.defaultness(tcx).has_value(),
+            }
+        }
+        DefKind::TyParam => {
+            let hir::Node::GenericParam(param) = tcx.hir().get_by_def_id(def_id) else { bug!() };
+            let hir::GenericParamKind::Type { default, .. } = param.kind else { bug!() };
+            default.is_some()
+        }
+
+        DefKind::Trait
+        | DefKind::TraitAlias
+        | DefKind::Mod
+        | DefKind::ForeignMod
+        | DefKind::Macro(..)
+        | DefKind::Use
+        | DefKind::LifetimeParam
+        | DefKind::GlobalAsm
+        | DefKind::ExternCrate => false,
+    }
+}
+
+fn should_encode_const(def_kind: DefKind) -> bool {
+    match def_kind {
+        DefKind::Const | DefKind::AssocConst | DefKind::AnonConst => true,
+
+        DefKind::Struct
+        | DefKind::Union
+        | DefKind::Enum
+        | DefKind::Variant
+        | DefKind::Ctor(..)
+        | DefKind::Field
+        | DefKind::Fn
+        | DefKind::Static(..)
+        | DefKind::TyAlias
+        | DefKind::OpaqueTy
+        | DefKind::ForeignTy
+        | DefKind::Impl
+        | DefKind::AssocFn
+        | DefKind::Closure
+        | DefKind::Generator
+        | DefKind::ConstParam
+        | DefKind::InlineConst
+        | DefKind::AssocTy
+        | DefKind::TyParam
+        | DefKind::Trait
+        | DefKind::TraitAlias
+        | DefKind::Mod
+        | DefKind::ForeignMod
+        | DefKind::Macro(..)
+        | DefKind::Use
+        | DefKind::LifetimeParam
+        | DefKind::GlobalAsm
+        | DefKind::ExternCrate => false,
+    }
+}
+
 impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
     fn encode_attrs(&mut self, def_id: LocalDefId) {
         let mut attrs = self
@@ -1045,7 +1126,8 @@ fn encode_def_ids(&mut self) {
             let def_kind = tcx.opt_def_kind(local_id);
             let Some(def_kind) = def_kind else { continue };
             self.tables.opt_def_kind.set(def_id.index, def_kind);
-            record!(self.tables.def_span[def_id] <- tcx.def_span(def_id));
+            let def_span = tcx.def_span(local_id);
+            record!(self.tables.def_span[def_id] <- def_span);
             self.encode_attrs(local_id);
             record!(self.tables.expn_that_defined[def_id] <- self.tcx.expn_that_defined(def_id));
             if let Some(ident_span) = tcx.def_ident_span(def_id) {
@@ -1076,6 +1158,9 @@ fn encode_def_ids(&mut self) {
                     record_array!(self.tables.inferred_outlives_of[def_id] <- inferred_outlives);
                 }
             }
+            if should_encode_type(tcx, local_id, def_kind) {
+                record!(self.tables.type_of[def_id] <- self.tcx.type_of(def_id));
+            }
             if let DefKind::TyParam | DefKind::ConstParam = def_kind {
                 if let Some(default) = self.tcx.object_lifetime_default(def_id) {
                     record!(self.tables.object_lifetime_default[def_id] <- default);
@@ -1097,11 +1182,6 @@ fn encode_def_ids(&mut self) {
         }
     }
 
-    fn encode_item_type(&mut self, def_id: DefId) {
-        debug!("EncodeContext::encode_item_type({:?})", def_id);
-        record!(self.tables.type_of[def_id] <- self.tcx.type_of(def_id));
-    }
-
     fn encode_enum_variant_info(&mut self, def: ty::AdtDef<'tcx>, index: VariantIdx) {
         let tcx = self.tcx;
         let variant = &def.variant(index);
@@ -1115,13 +1195,12 @@ fn encode_enum_variant_info(&mut self, def: ty::AdtDef<'tcx>, index: VariantIdx)
             is_non_exhaustive: variant.is_field_list_non_exhaustive(),
         };
 
-        record!(self.tables.kind[def_id] <- EntryKind::Variant(self.lazy(data)));
+        record!(self.tables.variant_data[def_id] <- data);
         self.tables.constness.set(def_id.index, hir::Constness::Const);
         record_array!(self.tables.children[def_id] <- variant.fields.iter().map(|f| {
             assert!(f.did.is_local());
             f.did.index
         }));
-        self.encode_item_type(def_id);
         if variant.ctor_kind == CtorKind::Fn {
             // FIXME(eddyb) encode signature only in `encode_enum_variant_ctor`.
             if let Some(ctor_def_id) = variant.ctor_def_id {
@@ -1144,9 +1223,8 @@ fn encode_enum_variant_ctor(&mut self, def: ty::AdtDef<'tcx>, index: VariantIdx)
             is_non_exhaustive: variant.is_field_list_non_exhaustive(),
         };
 
-        record!(self.tables.kind[def_id] <- EntryKind::Variant(self.lazy(data)));
+        record!(self.tables.variant_data[def_id] <- data);
         self.tables.constness.set(def_id.index, hir::Constness::Const);
-        self.encode_item_type(def_id);
         if variant.ctor_kind == CtorKind::Fn {
             record!(self.tables.fn_sig[def_id] <- tcx.fn_sig(def_id));
         }
@@ -1163,15 +1241,12 @@ fn encode_info_for_mod(&mut self, local_def_id: LocalDefId, md: &hir::Mod<'_>) {
         // code uses it). However, we skip encoding anything relating to child
         // items - we encode information about proc-macros later on.
         let reexports = if !self.is_proc_macro {
-            match tcx.module_reexports(local_def_id) {
-                Some(exports) => self.lazy_array(exports),
-                _ => LazyArray::empty(),
-            }
+            tcx.module_reexports(local_def_id).unwrap_or(&[])
         } else {
-            LazyArray::empty()
+            &[]
         };
 
-        record!(self.tables.kind[def_id] <- EntryKind::Mod(reexports));
+        record_array!(self.tables.module_reexports[def_id] <- reexports);
         if self.is_proc_macro {
             // Encode this here because we don't do it in encode_def_ids.
             record!(self.tables.expn_that_defined[def_id] <- tcx.expn_that_defined(local_def_id));
@@ -1199,22 +1274,6 @@ fn encode_info_for_mod(&mut self, local_def_id: LocalDefId, md: &hir::Mod<'_>) {
         }
     }
 
-    fn encode_field(
-        &mut self,
-        adt_def: ty::AdtDef<'tcx>,
-        variant_index: VariantIdx,
-        field_index: usize,
-    ) {
-        let variant = &adt_def.variant(variant_index);
-        let field = &variant.fields[field_index];
-
-        let def_id = field.did;
-        debug!("EncodeContext::encode_field({:?})", def_id);
-
-        record!(self.tables.kind[def_id] <- EntryKind::Field);
-        self.encode_item_type(def_id);
-    }
-
     fn encode_struct_ctor(&mut self, adt_def: ty::AdtDef<'tcx>, def_id: DefId) {
         debug!("EncodeContext::encode_struct_ctor({:?})", def_id);
         let tcx = self.tcx;
@@ -1228,9 +1287,8 @@ fn encode_struct_ctor(&mut self, adt_def: ty::AdtDef<'tcx>, def_id: DefId) {
         };
 
         record!(self.tables.repr_options[def_id] <- adt_def.repr());
+        record!(self.tables.variant_data[def_id] <- data);
         self.tables.constness.set(def_id.index, hir::Constness::Const);
-        record!(self.tables.kind[def_id] <- EntryKind::Struct(self.lazy(data)));
-        self.encode_item_type(def_id);
         if variant.ctor_kind == CtorKind::Fn {
             record!(self.tables.fn_sig[def_id] <- tcx.fn_sig(def_id));
         }
@@ -1251,18 +1309,10 @@ fn encode_info_for_trait_item(&mut self, def_id: DefId) {
         let ast_item = tcx.hir().expect_trait_item(def_id.expect_local());
         self.tables.impl_defaultness.set(def_id.index, ast_item.defaultness);
         let trait_item = tcx.associated_item(def_id);
+        self.tables.assoc_container.set(def_id.index, trait_item.container);
 
         match trait_item.kind {
-            ty::AssocKind::Const => {
-                let rendered = rustc_hir_pretty::to_string(
-                    &(&self.tcx.hir() as &dyn intravisit::Map<'_>),
-                    |s| s.print_trait_item(ast_item),
-                );
-
-                record!(self.tables.kind[def_id] <- EntryKind::AssocConst(ty::AssocItemContainer::TraitContainer));
-                record!(self.tables.mir_const_qualif[def_id] <- mir::ConstQualifs::default());
-                record!(self.tables.rendered_const[def_id] <- rendered);
-            }
+            ty::AssocKind::Const => {}
             ty::AssocKind::Fn => {
                 let hir::TraitItemKind::Fn(m_sig, m) = &ast_item.kind else { bug!() };
                 match *m {
@@ -1275,24 +1325,9 @@ fn encode_info_for_trait_item(&mut self, def_id: DefId) {
                 };
                 self.tables.asyncness.set(def_id.index, m_sig.header.asyncness);
                 self.tables.constness.set(def_id.index, hir::Constness::NotConst);
-                record!(self.tables.kind[def_id] <- EntryKind::AssocFn {
-                    container: ty::AssocItemContainer::TraitContainer,
-                    has_self: trait_item.fn_has_self_parameter,
-                });
             }
             ty::AssocKind::Type => {
                 self.encode_explicit_item_bounds(def_id);
-                record!(self.tables.kind[def_id] <- EntryKind::AssocType(ty::AssocItemContainer::TraitContainer));
-            }
-        }
-        match trait_item.kind {
-            ty::AssocKind::Const | ty::AssocKind::Fn => {
-                self.encode_item_type(def_id);
-            }
-            ty::AssocKind::Type => {
-                if ast_item.defaultness.has_value() {
-                    self.encode_item_type(def_id);
-                }
             }
         }
         if trait_item.kind == ty::AssocKind::Fn {
@@ -1307,20 +1342,9 @@ fn encode_info_for_impl_item(&mut self, def_id: DefId) {
         let ast_item = self.tcx.hir().expect_impl_item(def_id.expect_local());
         self.tables.impl_defaultness.set(def_id.index, ast_item.defaultness);
         let impl_item = self.tcx.associated_item(def_id);
+        self.tables.assoc_container.set(def_id.index, impl_item.container);
 
         match impl_item.kind {
-            ty::AssocKind::Const => {
-                if let hir::ImplItemKind::Const(_, body_id) = ast_item.kind {
-                    let qualifs = self.tcx.at(ast_item.span).mir_const_qualif(def_id);
-                    let const_data = self.encode_rendered_const_for_body(body_id);
-
-                    record!(self.tables.kind[def_id] <- EntryKind::AssocConst(ty::AssocItemContainer::ImplContainer));
-                    record!(self.tables.mir_const_qualif[def_id] <- qualifs);
-                    record!(self.tables.rendered_const[def_id] <- const_data);
-                } else {
-                    bug!()
-                }
-            }
             ty::AssocKind::Fn => {
                 let hir::ImplItemKind::Fn(ref sig, body) = ast_item.kind else { bug!() };
                 self.tables.asyncness.set(def_id.index, sig.header.asyncness);
@@ -1332,16 +1356,9 @@ fn encode_info_for_impl_item(&mut self, def_id: DefId) {
                     hir::Constness::NotConst
                 };
                 self.tables.constness.set(def_id.index, constness);
-                record!(self.tables.kind[def_id] <- EntryKind::AssocFn {
-                    container: ty::AssocItemContainer::ImplContainer,
-                    has_self: impl_item.fn_has_self_parameter,
-                });
-            }
-            ty::AssocKind::Type => {
-                record!(self.tables.kind[def_id] <- EntryKind::AssocType(ty::AssocItemContainer::ImplContainer));
             }
+            ty::AssocKind::Const | ty::AssocKind::Type => {}
         }
-        self.encode_item_type(def_id);
         if let Some(trait_item_def_id) = impl_item.trait_item_def_id {
             self.tables.trait_item_def_id.set(def_id.index, trait_item_def_id.into());
         }
@@ -1358,12 +1375,13 @@ fn encode_mir(&mut self) {
             return;
         }
 
-        let keys_and_jobs = self
-            .tcx
+        let tcx = self.tcx;
+
+        let keys_and_jobs = tcx
             .mir_keys(())
             .iter()
             .filter_map(|&def_id| {
-                let (encode_const, encode_opt) = should_encode_mir(self.tcx, def_id);
+                let (encode_const, encode_opt) = should_encode_mir(tcx, def_id);
                 if encode_const || encode_opt {
                     Some((def_id, encode_const, encode_opt))
                 } else {
@@ -1376,22 +1394,32 @@ fn encode_mir(&mut self) {
 
             debug!("EntryBuilder::encode_mir({:?})", def_id);
             if encode_opt {
-                record!(self.tables.optimized_mir[def_id.to_def_id()] <- self.tcx.optimized_mir(def_id));
+                record!(self.tables.optimized_mir[def_id.to_def_id()] <- tcx.optimized_mir(def_id));
             }
             if encode_const {
-                record!(self.tables.mir_for_ctfe[def_id.to_def_id()] <- self.tcx.mir_for_ctfe(def_id));
+                record!(self.tables.mir_for_ctfe[def_id.to_def_id()] <- tcx.mir_for_ctfe(def_id));
 
                 // FIXME(generic_const_exprs): this feels wrong to have in `encode_mir`
-                let abstract_const = self.tcx.thir_abstract_const(def_id);
+                let abstract_const = tcx.thir_abstract_const(def_id);
                 if let Ok(Some(abstract_const)) = abstract_const {
                     record!(self.tables.thir_abstract_const[def_id.to_def_id()] <- abstract_const);
                 }
+
+                if should_encode_const(tcx.def_kind(def_id)) {
+                    let qualifs = tcx.mir_const_qualif(def_id);
+                    record!(self.tables.mir_const_qualif[def_id.to_def_id()] <- qualifs);
+                    let body_id = tcx.hir().maybe_body_owned_by(def_id);
+                    if let Some(body_id) = body_id {
+                        let const_data = self.encode_rendered_const_for_body(body_id);
+                        record!(self.tables.rendered_const[def_id.to_def_id()] <- const_data);
+                    }
+                }
             }
-            record!(self.tables.promoted_mir[def_id.to_def_id()] <- self.tcx.promoted_mir(def_id));
+            record!(self.tables.promoted_mir[def_id.to_def_id()] <- tcx.promoted_mir(def_id));
 
             let instance =
                 ty::InstanceDef::Item(ty::WithOptConstParam::unknown(def_id.to_def_id()));
-            let unused = self.tcx.unused_generic_params(instance);
+            let unused = tcx.unused_generic_params(instance);
             if !unused.is_empty() {
                 record!(self.tables.unused_generic_params[def_id.to_def_id()] <- unused);
             }
@@ -1454,38 +1482,27 @@ fn encode_info_for_item(&mut self, def_id: DefId, item: &'tcx hir::Item<'tcx>) {
 
         debug!("EncodeContext::encode_info_for_item({:?})", def_id);
 
-        let entry_kind = match item.kind {
-            hir::ItemKind::Static(..) => EntryKind::Static,
-            hir::ItemKind::Const(_, body_id) => {
-                let qualifs = self.tcx.at(item.span).mir_const_qualif(def_id);
-                let const_data = self.encode_rendered_const_for_body(body_id);
-                record!(self.tables.mir_const_qualif[def_id] <- qualifs);
-                record!(self.tables.rendered_const[def_id] <- const_data);
-                EntryKind::Const
-            }
+        match item.kind {
             hir::ItemKind::Fn(ref sig, .., body) => {
                 self.tables.asyncness.set(def_id.index, sig.header.asyncness);
                 record_array!(self.tables.fn_arg_names[def_id] <- self.tcx.hir().body_param_names(body));
                 self.tables.constness.set(def_id.index, sig.header.constness);
-                EntryKind::Fn
             }
             hir::ItemKind::Macro(ref macro_def, _) => {
-                EntryKind::MacroDef(self.lazy(&*macro_def.body), macro_def.macro_rules)
+                if macro_def.macro_rules {
+                    self.tables.macro_rules.set(def_id.index, ());
+                }
+                record!(self.tables.macro_definition[def_id] <- &*macro_def.body);
             }
             hir::ItemKind::Mod(ref m) => {
                 return self.encode_info_for_mod(item.def_id, m);
             }
-            hir::ItemKind::ForeignMod { .. } => EntryKind::ForeignMod,
-            hir::ItemKind::GlobalAsm(..) => EntryKind::GlobalAsm,
-            hir::ItemKind::TyAlias(..) => EntryKind::Type,
             hir::ItemKind::OpaqueTy(..) => {
                 self.encode_explicit_item_bounds(def_id);
-                EntryKind::OpaqueTy
             }
             hir::ItemKind::Enum(..) => {
                 let adt_def = self.tcx.adt_def(def_id);
                 record!(self.tables.repr_options[def_id] <- adt_def.repr());
-                EntryKind::Enum
             }
             hir::ItemKind::Struct(ref struct_def, _) => {
                 let adt_def = self.tcx.adt_def(def_id);
@@ -1500,24 +1517,24 @@ fn encode_info_for_item(&mut self, def_id: DefId, item: &'tcx hir::Item<'tcx>) {
                     .map(|ctor_hir_id| self.tcx.hir().local_def_id(ctor_hir_id).local_def_index);
 
                 let variant = adt_def.non_enum_variant();
-                EntryKind::Struct(self.lazy(VariantData {
+                record!(self.tables.variant_data[def_id] <- VariantData {
                     ctor_kind: variant.ctor_kind,
                     discr: variant.discr,
                     ctor,
                     is_non_exhaustive: variant.is_field_list_non_exhaustive(),
-                }))
+                });
             }
             hir::ItemKind::Union(..) => {
                 let adt_def = self.tcx.adt_def(def_id);
                 record!(self.tables.repr_options[def_id] <- adt_def.repr());
 
                 let variant = adt_def.non_enum_variant();
-                EntryKind::Union(self.lazy(VariantData {
+                record!(self.tables.variant_data[def_id] <- VariantData {
                     ctor_kind: variant.ctor_kind,
                     discr: variant.discr,
                     ctor: None,
                     is_non_exhaustive: variant.is_field_list_non_exhaustive(),
-                }))
+                });
             }
             hir::ItemKind::Impl(hir::Impl { defaultness, constness, .. }) => {
                 self.tables.impl_defaultness.set(def_id.index, *defaultness);
@@ -1543,26 +1560,24 @@ fn encode_info_for_item(&mut self, def_id: DefId, item: &'tcx hir::Item<'tcx>) {
 
                 let polarity = self.tcx.impl_polarity(def_id);
                 self.tables.impl_polarity.set(def_id.index, polarity);
-
-                EntryKind::Impl
             }
             hir::ItemKind::Trait(..) => {
                 let trait_def = self.tcx.trait_def(def_id);
                 record!(self.tables.trait_def[def_id] <- trait_def);
-
-                EntryKind::Trait
             }
             hir::ItemKind::TraitAlias(..) => {
                 let trait_def = self.tcx.trait_def(def_id);
                 record!(self.tables.trait_def[def_id] <- trait_def);
-
-                EntryKind::TraitAlias
             }
             hir::ItemKind::ExternCrate(_) | hir::ItemKind::Use(..) => {
                 bug!("cannot encode info for item {:?}", item)
             }
+            hir::ItemKind::Static(..)
+            | hir::ItemKind::Const(..)
+            | hir::ItemKind::ForeignMod { .. }
+            | hir::ItemKind::GlobalAsm(..)
+            | hir::ItemKind::TyAlias(..) => {}
         };
-        record!(self.tables.kind[def_id] <- entry_kind);
         // FIXME(eddyb) there should be a nicer way to do this.
         match item.kind {
             hir::ItemKind::Enum(..) => record_array!(self.tables.children[def_id] <-
@@ -1590,18 +1605,6 @@ fn encode_info_for_item(&mut self, def_id: DefId, item: &'tcx hir::Item<'tcx>) {
             }
             _ => {}
         }
-        match item.kind {
-            hir::ItemKind::Static(..)
-            | hir::ItemKind::Const(..)
-            | hir::ItemKind::Fn(..)
-            | hir::ItemKind::TyAlias(..)
-            | hir::ItemKind::OpaqueTy(..)
-            | hir::ItemKind::Enum(..)
-            | hir::ItemKind::Struct(..)
-            | hir::ItemKind::Union(..)
-            | hir::ItemKind::Impl { .. } => self.encode_item_type(def_id),
-            _ => {}
-        }
         if let hir::ItemKind::Fn(..) = item.kind {
             record!(self.tables.fn_sig[def_id] <- tcx.fn_sig(def_id));
             if tcx.is_intrinsic(def_id) {
@@ -1613,12 +1616,43 @@ fn encode_info_for_item(&mut self, def_id: DefId, item: &'tcx hir::Item<'tcx>) {
                 record!(self.tables.impl_trait_ref[def_id] <- trait_ref);
             }
         }
-    }
+        // In some cases, along with the item itself, we also
+        // encode some sub-items. Usually we want some info from the item
+        // so it's easier to do that here then to wait until we would encounter
+        // normally in the visitor walk.
+        match item.kind {
+            hir::ItemKind::Enum(..) => {
+                let def = self.tcx.adt_def(item.def_id.to_def_id());
+                for (i, variant) in def.variants().iter_enumerated() {
+                    self.encode_enum_variant_info(def, i);
 
-    fn encode_info_for_generic_param(&mut self, def_id: DefId, kind: EntryKind, encode_type: bool) {
-        record!(self.tables.kind[def_id] <- kind);
-        if encode_type {
-            self.encode_item_type(def_id);
+                    if let Some(_ctor_def_id) = variant.ctor_def_id {
+                        self.encode_enum_variant_ctor(def, i);
+                    }
+                }
+            }
+            hir::ItemKind::Struct(ref struct_def, _) => {
+                let def = self.tcx.adt_def(item.def_id.to_def_id());
+                // If the struct has a constructor, encode it.
+                if let Some(ctor_hir_id) = struct_def.ctor_hir_id() {
+                    let ctor_def_id = self.tcx.hir().local_def_id(ctor_hir_id);
+                    self.encode_struct_ctor(def, ctor_def_id.to_def_id());
+                }
+            }
+            hir::ItemKind::Impl { .. } => {
+                for &trait_item_def_id in
+                    self.tcx.associated_item_def_ids(item.def_id.to_def_id()).iter()
+                {
+                    self.encode_info_for_impl_item(trait_item_def_id);
+                }
+            }
+            hir::ItemKind::Trait(..) => {
+                for &item_def_id in self.tcx.associated_item_def_ids(item.def_id.to_def_id()).iter()
+                {
+                    self.encode_info_for_trait_item(item_def_id);
+                }
+            }
+            _ => {}
         }
     }
 
@@ -1633,34 +1667,16 @@ fn encode_info_for_closure(&mut self, hir_id: hir::HirId) {
             ty::Generator(..) => {
                 let data = self.tcx.generator_kind(def_id).unwrap();
                 let generator_diagnostic_data = typeck_result.get_generator_diagnostic_data();
-                record!(self.tables.kind[def_id.to_def_id()] <- EntryKind::Generator);
                 record!(self.tables.generator_kind[def_id.to_def_id()] <- data);
                 record!(self.tables.generator_diagnostic_data[def_id.to_def_id()]  <- generator_diagnostic_data);
             }
 
-            ty::Closure(..) => {
-                record!(self.tables.kind[def_id.to_def_id()] <- EntryKind::Closure);
+            ty::Closure(_, substs) => {
+                record!(self.tables.fn_sig[def_id.to_def_id()] <- substs.as_closure().sig());
             }
 
             _ => bug!("closure that is neither generator nor closure"),
         }
-        self.encode_item_type(def_id.to_def_id());
-        if let ty::Closure(def_id, substs) = *ty.kind() {
-            record!(self.tables.fn_sig[def_id] <- substs.as_closure().sig());
-        }
-    }
-
-    fn encode_info_for_anon_const(&mut self, id: hir::HirId) {
-        let def_id = self.tcx.hir().local_def_id(id);
-        debug!("EncodeContext::encode_info_for_anon_const({:?})", def_id);
-        let body_id = self.tcx.hir().body_owned_by(def_id);
-        let const_data = self.encode_rendered_const_for_body(body_id);
-        let qualifs = self.tcx.mir_const_qualif(def_id);
-
-        record!(self.tables.kind[def_id.to_def_id()] <- EntryKind::AnonConst);
-        record!(self.tables.mir_const_qualif[def_id.to_def_id()] <- qualifs);
-        record!(self.tables.rendered_const[def_id.to_def_id()] <- const_data);
-        self.encode_item_type(def_id.to_def_id());
     }
 
     fn encode_native_libraries(&mut self) -> LazyArray<NativeLib> {
@@ -1758,7 +1774,7 @@ fn encode_proc_macros(&mut self) -> Option<ProcMacroData> {
 
                 let def_id = id.to_def_id();
                 self.tables.opt_def_kind.set(def_id.index, DefKind::Macro(macro_kind));
-                record!(self.tables.kind[def_id] <- EntryKind::ProcMacro(macro_kind));
+                self.tables.proc_macro.set(def_id.index, macro_kind);
                 self.encode_attrs(id);
                 record!(self.tables.def_keys[def_id] <- def_key);
                 record!(self.tables.def_ident_span[def_id] <- span);
@@ -1996,18 +2012,11 @@ fn encode_info_for_foreign_item(&mut self, def_id: DefId, nitem: &hir::ForeignIt
                     hir::Constness::NotConst
                 };
                 self.tables.constness.set(def_id.index, constness);
-                record!(self.tables.kind[def_id] <- EntryKind::ForeignFn);
-            }
-            hir::ForeignItemKind::Static(..) => {
-                record!(self.tables.kind[def_id] <- EntryKind::ForeignStatic);
-            }
-            hir::ForeignItemKind::Type => {
-                record!(self.tables.kind[def_id] <- EntryKind::ForeignType);
+                record!(self.tables.fn_sig[def_id] <- tcx.fn_sig(def_id));
             }
+            hir::ForeignItemKind::Static(..) | hir::ForeignItemKind::Type => {}
         }
-        self.encode_item_type(def_id);
         if let hir::ForeignItemKind::Fn(..) = nitem.kind {
-            record!(self.tables.fn_sig[def_id] <- tcx.fn_sig(def_id));
             if tcx.is_intrinsic(def_id) {
                 self.tables.is_intrinsic.set(def_id.index, ());
             }
@@ -2026,17 +2035,12 @@ fn visit_expr(&mut self, ex: &'tcx hir::Expr<'tcx>) {
         intravisit::walk_expr(self, ex);
         self.encode_info_for_expr(ex);
     }
-    fn visit_anon_const(&mut self, c: &'tcx AnonConst) {
-        intravisit::walk_anon_const(self, c);
-        self.encode_info_for_anon_const(c.hir_id);
-    }
     fn visit_item(&mut self, item: &'tcx hir::Item<'tcx>) {
         intravisit::walk_item(self, item);
         match item.kind {
             hir::ItemKind::ExternCrate(_) | hir::ItemKind::Use(..) => {} // ignore these
             _ => self.encode_info_for_item(item.def_id.to_def_id(), item),
         }
-        self.encode_addl_info_for_item(item);
     }
     fn visit_foreign_item(&mut self, ni: &'tcx hir::ForeignItem<'tcx>) {
         intravisit::walk_foreign_item(self, ni);
@@ -2049,29 +2053,13 @@ fn visit_generics(&mut self, generics: &'tcx hir::Generics<'tcx>) {
 }
 
 impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
-    fn encode_fields(&mut self, adt_def: ty::AdtDef<'tcx>) {
-        for (variant_index, variant) in adt_def.variants().iter_enumerated() {
-            for (field_index, _field) in variant.fields.iter().enumerate() {
-                self.encode_field(adt_def, variant_index, field_index);
-            }
-        }
-    }
-
     fn encode_info_for_generics(&mut self, generics: &hir::Generics<'tcx>) {
         for param in generics.params {
             let def_id = self.tcx.hir().local_def_id(param.hir_id);
             match param.kind {
-                GenericParamKind::Lifetime { .. } => continue,
-                GenericParamKind::Type { default, .. } => {
-                    self.encode_info_for_generic_param(
-                        def_id.to_def_id(),
-                        EntryKind::TypeParam,
-                        default.is_some(),
-                    );
-                }
-                GenericParamKind::Const { ref default, .. } => {
+                hir::GenericParamKind::Lifetime { .. } | hir::GenericParamKind::Type { .. } => {}
+                hir::GenericParamKind::Const { ref default, .. } => {
                     let def_id = def_id.to_def_id();
-                    self.encode_info_for_generic_param(def_id, EntryKind::ConstParam, true);
                     if default.is_some() {
                         record!(self.tables.const_param_default[def_id] <- self.tcx.const_param_default(def_id))
                     }
@@ -2085,68 +2073,6 @@ fn encode_info_for_expr(&mut self, expr: &hir::Expr<'_>) {
             self.encode_info_for_closure(expr.hir_id);
         }
     }
-
-    /// In some cases, along with the item itself, we also
-    /// encode some sub-items. Usually we want some info from the item
-    /// so it's easier to do that here then to wait until we would encounter
-    /// normally in the visitor walk.
-    fn encode_addl_info_for_item(&mut self, item: &hir::Item<'_>) {
-        match item.kind {
-            hir::ItemKind::Static(..)
-            | hir::ItemKind::Const(..)
-            | hir::ItemKind::Fn(..)
-            | hir::ItemKind::Macro(..)
-            | hir::ItemKind::Mod(..)
-            | hir::ItemKind::ForeignMod { .. }
-            | hir::ItemKind::GlobalAsm(..)
-            | hir::ItemKind::ExternCrate(..)
-            | hir::ItemKind::Use(..)
-            | hir::ItemKind::TyAlias(..)
-            | hir::ItemKind::OpaqueTy(..)
-            | hir::ItemKind::TraitAlias(..) => {
-                // no sub-item recording needed in these cases
-            }
-            hir::ItemKind::Enum(..) => {
-                let def = self.tcx.adt_def(item.def_id.to_def_id());
-                self.encode_fields(def);
-
-                for (i, variant) in def.variants().iter_enumerated() {
-                    self.encode_enum_variant_info(def, i);
-
-                    if let Some(_ctor_def_id) = variant.ctor_def_id {
-                        self.encode_enum_variant_ctor(def, i);
-                    }
-                }
-            }
-            hir::ItemKind::Struct(ref struct_def, _) => {
-                let def = self.tcx.adt_def(item.def_id.to_def_id());
-                self.encode_fields(def);
-
-                // If the struct has a constructor, encode it.
-                if let Some(ctor_hir_id) = struct_def.ctor_hir_id() {
-                    let ctor_def_id = self.tcx.hir().local_def_id(ctor_hir_id);
-                    self.encode_struct_ctor(def, ctor_def_id.to_def_id());
-                }
-            }
-            hir::ItemKind::Union(..) => {
-                let def = self.tcx.adt_def(item.def_id.to_def_id());
-                self.encode_fields(def);
-            }
-            hir::ItemKind::Impl { .. } => {
-                for &trait_item_def_id in
-                    self.tcx.associated_item_def_ids(item.def_id.to_def_id()).iter()
-                {
-                    self.encode_info_for_impl_item(trait_item_def_id);
-                }
-            }
-            hir::ItemKind::Trait(..) => {
-                for &item_def_id in self.tcx.associated_item_def_ids(item.def_id.to_def_id()).iter()
-                {
-                    self.encode_info_for_trait_item(item_def_id);
-                }
-            }
-        }
-    }
 }
 
 /// Used to prefetch queries which will be needed later by metadata encoding.
index aeffc85b507556648ed956d50937c91435949a48..6f849a58580e679550216f06ff690d75e11a8a8f 100644 (file)
@@ -334,7 +334,6 @@ fn encode(&self, buf: &mut FileEncoder) -> LazyTables {
 }
 
 define_tables! {
-    kind: Table<DefIndex, LazyValue<EntryKind>>,
     attributes: Table<DefIndex, LazyArray<ast::Attribute>>,
     children: Table<DefIndex, LazyArray<DefIndex>>,
 
@@ -393,39 +392,13 @@ fn encode(&self, buf: &mut FileEncoder) -> LazyTables {
     proc_macro_quoted_spans: Table<usize, LazyValue<Span>>,
     generator_diagnostic_data: Table<DefIndex, LazyValue<GeneratorDiagnosticData<'static>>>,
     may_have_doc_links: Table<DefIndex, ()>,
-}
-
-#[derive(Copy, Clone, MetadataEncodable, MetadataDecodable)]
-enum EntryKind {
-    AnonConst,
-    Const,
-    Static,
-    ForeignStatic,
-    ForeignMod,
-    ForeignType,
-    GlobalAsm,
-    Type,
-    TypeParam,
-    ConstParam,
-    OpaqueTy,
-    Enum,
-    Field,
-    Variant(LazyValue<VariantData>),
-    Struct(LazyValue<VariantData>),
-    Union(LazyValue<VariantData>),
-    Fn,
-    ForeignFn,
-    Mod(LazyArray<ModChild>),
-    MacroDef(LazyValue<ast::MacArgs>, /*macro_rules*/ bool),
-    ProcMacro(MacroKind),
-    Closure,
-    Generator,
-    Trait,
-    Impl,
-    AssocFn { container: ty::AssocItemContainer, has_self: bool },
-    AssocType(ty::AssocItemContainer),
-    AssocConst(ty::AssocItemContainer),
-    TraitAlias,
+    variant_data: Table<DefIndex, LazyValue<VariantData>>,
+    assoc_container: Table<DefIndex, ty::AssocItemContainer>,
+    // Slot is full when macro is macro_rules.
+    macro_rules: Table<DefIndex, ()>,
+    macro_definition: Table<DefIndex, LazyValue<ast::MacArgs>>,
+    proc_macro: Table<DefIndex, MacroKind>,
+    module_reexports: Table<DefIndex, LazyArray<ModChild>>,
 }
 
 #[derive(TyEncodable, TyDecodable)]
@@ -459,7 +432,6 @@ pub fn provide(providers: &mut Providers) {
 
 trivially_parameterized_over_tcx! {
     VariantData,
-    EntryKind,
     RawDefId,
     TraitImpls,
     IncoherentImpls,
index 21841ae2532a7b913f1da7b901c1417ae091cc84..d5f151f0ed8e50a4116de32d27be14044bf589eb 100644 (file)
@@ -10,7 +10,6 @@
 use std::convert::TryInto;
 use std::marker::PhantomData;
 use std::num::NonZeroUsize;
-use tracing::debug;
 
 /// Helper trait, for encoding to, and decoding from, a fixed number of bytes.
 /// Used mainly for Lazy positions and lengths.
@@ -51,7 +50,7 @@ impl FixedSizeEncoding for Option<$ty> {
                 }
                 match b[0] - 1 {
                     $(${index()} => Some($($pat)*),)*
-                    _ => panic!("Unexpected ImplPolarity code: {:?}", b[0]),
+                    _ => panic!("Unexpected {} code: {:?}", stringify!($ty), b[0]),
                 }
             }
 
@@ -141,6 +140,21 @@ impl FixedSizeEncoding for Option<$ty> {
     }
 }
 
+fixed_size_enum! {
+    ty::AssocItemContainer {
+        ( TraitContainer )
+        ( ImplContainer  )
+    }
+}
+
+fixed_size_enum! {
+    MacroKind {
+        ( Attr   )
+        ( Bang   )
+        ( Derive )
+    }
+}
+
 // We directly encode `DefPathHash` because a `LazyValue` would incur a 25% cost.
 impl FixedSizeEncoding for Option<DefPathHash> {
     type ByteArray = [u8; 16];
index b94de537dc81e5525e5c5b14889c496315eee470..65d5f755f72482173aafada909ce89241ff9ebaf 100644 (file)
@@ -100,7 +100,7 @@ macro_rules! arena_types {
             [decode] is_late_bound_map: rustc_data_structures::fx::FxIndexSet<rustc_hir::def_id::LocalDefId>,
             [decode] impl_source: rustc_middle::traits::ImplSource<'tcx, ()>,
 
-            [] dep_kind: rustc_middle::dep_graph::DepKindStruct,
+            [] dep_kind: rustc_middle::dep_graph::DepKindStruct<'tcx>,
         ]);
     )
 }
index 65fc8a2e9cf5a4413e309a96726c9ea85126aae2..7718906ac4ee7976aad733815b6d6637e66ce014 100644 (file)
@@ -74,7 +74,7 @@
 /// Information is retrieved by indexing the `DEP_KINDS` array using the integer value
 /// of the `DepKind`. Overall, this allows to implement `DepContext` using this manual
 /// jump table instead of large matches.
-pub struct DepKindStruct {
+pub struct DepKindStruct<'tcx> {
     /// Anonymous queries cannot be replayed from one compiler invocation to the next.
     /// When their result is needed, it is recomputed. They are useful for fine-grained
     /// dependency tracking, and caching within one compiler invocation.
@@ -124,10 +124,10 @@ pub struct DepKindStruct {
     /// with kind `MirValidated`, we know that the GUID/fingerprint of the `DepNode`
     /// is actually a `DefPathHash`, and can therefore just look up the corresponding
     /// `DefId` in `tcx.def_path_hash_to_def_id`.
-    pub force_from_dep_node: Option<fn(tcx: TyCtxt<'_>, dep_node: DepNode) -> bool>,
+    pub force_from_dep_node: Option<fn(tcx: TyCtxt<'tcx>, dep_node: DepNode) -> bool>,
 
     /// Invoke a query to put the on-disk cached value in memory.
-    pub try_load_from_on_disk_cache: Option<fn(TyCtxt<'_>, DepNode)>,
+    pub try_load_from_on_disk_cache: Option<fn(TyCtxt<'tcx>, DepNode)>,
 }
 
 impl DepKind {
index 560d9fde0492af646e4146f9960196049789d27a..f3676604bb0e64b34b6d6d6e38eea52be4768683 100644 (file)
@@ -2267,7 +2267,7 @@ pub fn from_anon_const(
         Self::from_opt_const_arg_anon_const(tcx, ty::WithOptConstParam::unknown(def_id), param_env)
     }
 
-    #[instrument(skip(tcx), level = "debug")]
+    #[instrument(skip(tcx), level = "debug", ret)]
     pub fn from_inline_const(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Self {
         let hir_id = tcx.hir().local_def_id_to_hir_id(def_id);
         let body_id = match tcx.hir().get(hir_id) {
@@ -2305,21 +2305,18 @@ pub fn from_inline_const(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Self {
         let substs =
             ty::InlineConstSubsts::new(tcx, ty::InlineConstSubstsParts { parent_substs, ty })
                 .substs;
-        let uneval_const = tcx.mk_const(ty::ConstS {
+        debug_assert!(!substs.has_free_regions());
+        Self::Ty(tcx.mk_const(ty::ConstS {
             kind: ty::ConstKind::Unevaluated(ty::Unevaluated {
                 def: ty::WithOptConstParam::unknown(def_id).to_global(),
                 substs,
                 promoted: None,
             }),
             ty,
-        });
-        debug!(?uneval_const);
-        debug_assert!(!uneval_const.has_free_regions());
-
-        Self::Ty(uneval_const)
+        }))
     }
 
-    #[instrument(skip(tcx), level = "debug")]
+    #[instrument(skip(tcx), level = "debug", ret)]
     fn from_opt_const_arg_anon_const(
         tcx: TyCtxt<'tcx>,
         def: ty::WithOptConstParam<LocalDefId>,
@@ -2402,24 +2399,21 @@ fn from_opt_const_arg_anon_const(
 
         match tcx.const_eval_resolve(param_env, uneval, Some(span)) {
             Ok(val) => {
-                debug!("evaluated const value: {:?}", val);
+                debug!("evaluated const value");
                 Self::Val(val, ty)
             }
             Err(_) => {
                 debug!("error encountered during evaluation");
                 // Error was handled in `const_eval_resolve`. Here we just create a
                 // new unevaluated const and error hard later in codegen
-                let ty_const = tcx.mk_const(ty::ConstS {
+                Self::Ty(tcx.mk_const(ty::ConstS {
                     kind: ty::ConstKind::Unevaluated(ty::Unevaluated {
                         def: def.to_global(),
                         substs: InternalSubsts::identity_for_item(tcx, def.did.to_def_id()),
                         promoted: None,
                     }),
                     ty,
-                });
-                debug!(?ty_const);
-
-                Self::Ty(ty_const)
+                }))
             }
         }
     }
index f8792edc017b2d8d3a5da6affae1e10302511dce..2eb5cffa6bc44360a25dc9cb7f578ac7addc31ff 100644 (file)
@@ -65,8 +65,6 @@ pub fn from_opt_const_arg_anon_const(
         tcx: TyCtxt<'tcx>,
         def: ty::WithOptConstParam<LocalDefId>,
     ) -> Self {
-        debug!("Const::from_anon_const(def={:?})", def);
-
         let body_id = match tcx.hir().get_by_def_id(def.did) {
             hir::Node::AnonConst(ac) => ac.body,
             _ => span_bug!(
index 052bb1263c98f8d022e4577b4c26d275f1bd4afa..7a990773ab87577e375a0c9d79f8c13dee3cc320 100644 (file)
@@ -1089,7 +1089,7 @@ pub struct GlobalCtxt<'tcx> {
 
     pub queries: &'tcx dyn query::QueryEngine<'tcx>,
     pub query_caches: query::QueryCaches<'tcx>,
-    query_kinds: &'tcx [DepKindStruct],
+    query_kinds: &'tcx [DepKindStruct<'tcx>],
 
     // Internal caches for metadata decoding. No need to track deps on this.
     pub ty_rcache: Lock<FxHashMap<ty::CReaderCacheKey, Ty<'tcx>>>,
@@ -1246,7 +1246,7 @@ pub fn create_global_ctxt(
         dep_graph: DepGraph,
         on_disk_cache: Option<&'tcx dyn OnDiskCache<'tcx>>,
         queries: &'tcx dyn query::QueryEngine<'tcx>,
-        query_kinds: &'tcx [DepKindStruct],
+        query_kinds: &'tcx [DepKindStruct<'tcx>],
         crate_name: &str,
         output_filenames: OutputFilenames,
     ) -> GlobalCtxt<'tcx> {
@@ -1296,7 +1296,7 @@ pub fn create_global_ctxt(
         }
     }
 
-    pub(crate) fn query_kind(self, k: DepKind) -> &'tcx DepKindStruct {
+    pub(crate) fn query_kind(self, k: DepKind) -> &'tcx DepKindStruct<'tcx> {
         &self.query_kinds[k as usize]
     }
 
index 5e96e278b9cad5f76008b2878a8bdfbe9c89b9af..cb46a9dba579fd6d40a75e0b835cba021d2a7661 100644 (file)
@@ -353,7 +353,7 @@ fn fold_binder<T: TypeFoldable<'tcx>>(
         t
     }
 
-    #[instrument(skip(self), level = "debug")]
+    #[instrument(skip(self), level = "debug", ret)]
     fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> {
         match *r {
             ty::ReLateBound(debruijn, _) if debruijn < self.current_index => {
index 9d8a811659433f6b36b4b2043f714a228d24545d..cac8560ce1c320229dfe789a27695b039160ab26 100644 (file)
@@ -188,13 +188,11 @@ struct NormalizeAfterErasingRegionsFolder<'tcx> {
 }
 
 impl<'tcx> NormalizeAfterErasingRegionsFolder<'tcx> {
-    #[instrument(skip(self), level = "debug")]
     fn normalize_generic_arg_after_erasing_regions(
         &self,
         arg: ty::GenericArg<'tcx>,
     ) -> ty::GenericArg<'tcx> {
         let arg = self.param_env.and(arg);
-        debug!(?arg);
 
         self.tcx.try_normalize_generic_arg_after_erasing_regions(arg).unwrap_or_else(|_| bug!(
                 "Failed to normalize {:?}, maybe try to call `try_normalize_erasing_regions` instead",
index 19b8f27bc95caae910d164128766cbefb533a254..ca24c0d1ce386fc5801be18526395b68e3589677 100644 (file)
@@ -55,6 +55,7 @@ impl $crate::ty::ParameterizedOverTcx for $ty {
     crate::middle::exported_symbols::SymbolExportInfo,
     crate::middle::resolve_lifetime::ObjectLifetimeDefault,
     crate::mir::ConstQualifs,
+    ty::AssocItemContainer,
     ty::Generics,
     ty::ImplPolarity,
     ty::ReprOptions,
index 541dace5cc2bb5f31964d42799e792ebdab6af2d..ac79949fca5cc40d7ed5391e8e96557ff459e36d 100644 (file)
@@ -256,7 +256,6 @@ pub(super) fn trait_impls_of_provider(tcx: TyCtxt<'_>, trait_id: DefId) -> Trait
 }
 
 // Query provider for `incoherent_impls`.
-#[instrument(level = "debug", skip(tcx))]
 pub(super) fn incoherent_impls_provider(tcx: TyCtxt<'_>, simp: SimplifiedType) -> &[DefId] {
     let mut impls = Vec::new();
 
index 591bb7831b5b6375ab98b17f28ecfb389dc26e5a..a3837512bce2652c1155ca2672e06bcb1cd07bdb 100644 (file)
@@ -627,7 +627,7 @@ pub fn static_ptr_ty(self, def_id: DefId) -> Ty<'tcx> {
     }
 
     /// Expands the given impl trait type, stopping if the type is recursive.
-    #[instrument(skip(self), level = "debug")]
+    #[instrument(skip(self), level = "debug", ret)]
     pub fn try_expand_impl_trait_type(
         self,
         def_id: DefId,
@@ -644,7 +644,6 @@ pub fn try_expand_impl_trait_type(
         };
 
         let expanded_type = visitor.expand_opaque_ty(def_id, substs).unwrap();
-        trace!(?expanded_type);
         if visitor.found_recursion { Err(expanded_type) } else { Ok(expanded_type) }
     }
 
index 5365067209af98042864cd0a8410a0a20170e722..5e042c3acfce25897621b4b4215df93554a266ed 100644 (file)
@@ -84,7 +84,7 @@ fn has_escaping_bound_vars(&self) -> bool {
         self.has_vars_bound_at_or_above(ty::INNERMOST)
     }
 
-    #[instrument(level = "trace")]
+    #[instrument(level = "trace", ret)]
     fn has_type_flags(&self, flags: TypeFlags) -> bool {
         self.visit_with(&mut HasTypeFlagsVisitor { flags }).break_value() == Some(FoundFlags)
     }
@@ -560,7 +560,7 @@ impl<'tcx> TypeVisitor<'tcx> for HasTypeFlagsVisitor {
     type BreakTy = FoundFlags;
 
     #[inline]
-    #[instrument(skip(self), level = "trace")]
+    #[instrument(skip(self), level = "trace", ret)]
     fn visit_ty(&mut self, t: Ty<'tcx>) -> ControlFlow<Self::BreakTy> {
         let flags = t.flags();
         trace!(t.flags=?t.flags());
@@ -572,7 +572,7 @@ fn visit_ty(&mut self, t: Ty<'tcx>) -> ControlFlow<Self::BreakTy> {
     }
 
     #[inline]
-    #[instrument(skip(self), level = "trace")]
+    #[instrument(skip(self), level = "trace", ret)]
     fn visit_region(&mut self, r: ty::Region<'tcx>) -> ControlFlow<Self::BreakTy> {
         let flags = r.type_flags();
         trace!(r.flags=?flags);
@@ -584,7 +584,7 @@ fn visit_region(&mut self, r: ty::Region<'tcx>) -> ControlFlow<Self::BreakTy> {
     }
 
     #[inline]
-    #[instrument(level = "trace")]
+    #[instrument(level = "trace", ret)]
     fn visit_const(&mut self, c: ty::Const<'tcx>) -> ControlFlow<Self::BreakTy> {
         let flags = FlagComputation::for_const(c);
         trace!(r.flags=?flags);
@@ -596,7 +596,7 @@ fn visit_const(&mut self, c: ty::Const<'tcx>) -> ControlFlow<Self::BreakTy> {
     }
 
     #[inline]
-    #[instrument(level = "trace")]
+    #[instrument(level = "trace", ret)]
     fn visit_unevaluated(&mut self, uv: ty::Unevaluated<'tcx>) -> ControlFlow<Self::BreakTy> {
         let flags = FlagComputation::for_unevaluated_const(uv);
         trace!(r.flags=?flags);
@@ -608,7 +608,7 @@ fn visit_unevaluated(&mut self, uv: ty::Unevaluated<'tcx>) -> ControlFlow<Self::
     }
 
     #[inline]
-    #[instrument(level = "trace")]
+    #[instrument(level = "trace", ret)]
     fn visit_predicate(&mut self, predicate: ty::Predicate<'tcx>) -> ControlFlow<Self::BreakTy> {
         debug!(
             "HasTypeFlagsVisitor: predicate={:?} predicate.flags={:?} self.flags={:?}",
index 2ca6d7628466229c1ea5db3c678d47397d98aa45..0e5cd6199ac9fb69ec7d3ecd7e23c42c3c483669 100644 (file)
@@ -155,7 +155,7 @@ pub(crate) fn then_else_break(
     ///
     /// * From each pre-binding block to the next pre-binding block.
     /// * From each otherwise block to the next pre-binding block.
-    #[tracing::instrument(level = "debug", skip(self, arms))]
+    #[instrument(level = "debug", skip(self, arms))]
     pub(crate) fn match_expr(
         &mut self,
         destination: Place<'tcx>,
index 0c2b117453fe9ed5785a444d4ee0deff4186f34b..9ed1c064d2b7f3ea651eb303c9e7824dbbdba8ec 100644 (file)
@@ -268,7 +268,7 @@ fn make_mirror_unadjusted(&mut self, expr: &'tcx hir::Expr<'tcx>) -> Expr<'tcx>
                 // the overall method call for better diagnostics. args[0]
                 // is guaranteed to exist, since a method call always has a receiver.
                 let old_adjustment_span = self.adjustment_span.replace((args[0].hir_id, expr_span));
-                tracing::info!("Using method span: {:?}", expr.span);
+                info!("Using method span: {:?}", expr.span);
                 let args = self.mirror_exprs(args);
                 self.adjustment_span = old_adjustment_span;
                 ExprKind::Call {
index f7351a4caa9545250d59dcbf5c21a146724fcc27..b84a84976c7d9371339158086d26d4c3d472a92b 100644 (file)
@@ -77,7 +77,7 @@ fn new(tcx: TyCtxt<'tcx>, def: ty::WithOptConstParam<LocalDefId>) -> Cx<'tcx> {
         }
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     pub(crate) fn pattern_from_hir(&mut self, p: &hir::Pat<'_>) -> Pat<'tcx> {
         let p = match self.tcx.hir().get(p.hir_id) {
             Node::Pat(p) => p,
index f2045ac19cac42920293ecc3b71d865cf5cb29a9..210d77c66e7002ff4928a9f26e45af4fee5117c8 100644 (file)
@@ -19,7 +19,7 @@ impl<'a, 'tcx> PatCtxt<'a, 'tcx> {
     /// Converts an evaluated constant to a pattern (if possible).
     /// This means aggregate values (like structs and enums) are converted
     /// to a pattern that matches the value (as if you'd compared via structural equality).
-    #[instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self), ret)]
     pub(super) fn const_to_pat(
         &self,
         cv: mir::ConstantKind<'tcx>,
@@ -27,13 +27,10 @@ pub(super) fn const_to_pat(
         span: Span,
         mir_structural_match_violation: bool,
     ) -> Pat<'tcx> {
-        let pat = self.tcx.infer_ctxt().enter(|infcx| {
+        self.tcx.infer_ctxt().enter(|infcx| {
             let mut convert = ConstToPat::new(self, id, span, infcx);
             convert.to_pat(cv, mir_structural_match_violation)
-        });
-
-        debug!(?pat);
-        pat
+        })
     }
 }
 
index 443626d14b9f67c636bed05f1a7483d9366ce79d..319183eb9b33fc7e0a81f15cedd6f87cd641ad88 100644 (file)
@@ -791,7 +791,7 @@ fn lint_non_exhaustive_omitted_patterns<'p, 'tcx>(
 /// `is_under_guard` is used to inform if the pattern has a guard. If it
 /// has one it must not be inserted into the matrix. This shouldn't be
 /// relied on for soundness.
-#[instrument(level = "debug", skip(cx, matrix, hir_id))]
+#[instrument(level = "debug", skip(cx, matrix, hir_id), ret)]
 fn is_useful<'p, 'tcx>(
     cx: &MatchCheckCtxt<'p, 'tcx>,
     matrix: &Matrix<'p, 'tcx>,
@@ -917,7 +917,6 @@ fn is_useful<'p, 'tcx>(
         v.head().set_reachable();
     }
 
-    debug!(?ret);
     ret
 }
 
index 170616d4b42ce76e62a6f12021907822b351e32c..6ec5e9e113d1b4b85f6134c36fc1e4e75c89e529 100644 (file)
@@ -419,7 +419,6 @@ fn collect_items_rec<'tcx>(
         // We've been here already, no need to search again.
         return;
     }
-    debug!("BEGIN collect_items_rec({})", starting_point.node);
 
     let mut neighbors = MonoItems { compute_inlining: true, tcx, items: Vec::new() };
     let recursion_depth_reset;
@@ -545,8 +544,6 @@ fn collect_items_rec<'tcx>(
     if let Some((def_id, depth)) = recursion_depth_reset {
         recursion_depths.insert(def_id, depth);
     }
-
-    debug!("END collect_items_rec({})", starting_point.node);
 }
 
 /// Format instance name that is already known to be too long for rustc.
@@ -1148,23 +1145,18 @@ fn find_vtable_types_for_unsizing<'tcx>(
     }
 }
 
-#[instrument(skip(tcx), level = "debug")]
+#[instrument(skip(tcx), level = "debug", ret)]
 fn create_fn_mono_item<'tcx>(
     tcx: TyCtxt<'tcx>,
     instance: Instance<'tcx>,
     source: Span,
 ) -> Spanned<MonoItem<'tcx>> {
-    debug!("create_fn_mono_item(instance={})", instance);
-
     let def_id = instance.def_id();
     if tcx.sess.opts.unstable_opts.profile_closures && def_id.is_local() && tcx.is_closure(def_id) {
         crate::util::dump_closure_profile(tcx, instance);
     }
 
-    let respanned = respan(source, MonoItem::Fn(instance.polymorphize(tcx)));
-    debug!(?respanned);
-
-    respanned
+    respan(source, MonoItem::Fn(instance.polymorphize(tcx)))
 }
 
 /// Creates a `MonoItem` for each method that is referenced by the vtable for
@@ -1309,7 +1301,7 @@ fn is_root(&self, def_id: LocalDefId) -> bool {
     #[instrument(skip(self), level = "debug")]
     fn push_if_root(&mut self, def_id: LocalDefId) {
         if self.is_root(def_id) {
-            debug!("RootCollector::push_if_root: found root def_id={:?}", def_id);
+            debug!("found root");
 
             let instance = Instance::mono(self.tcx, def_id.to_def_id());
             self.output.push(create_fn_mono_item(self.tcx, instance, DUMMY_SP));
index 6e4ab2a35c3375e0c43b274ae285bf7fbd22f28d..af4b35db3bace8bbaefb9b7808e01bd05aaf75ed 100644 (file)
@@ -33,7 +33,6 @@ pub fn provide(providers: &mut Providers) {
 ///
 /// Returns a bitset where bits representing unused parameters are set (`is_empty` indicates all
 /// parameters are used).
-#[instrument(level = "debug", skip(tcx))]
 fn unused_generic_params<'tcx>(
     tcx: TyCtxt<'tcx>,
     instance: ty::InstanceDef<'tcx>,
index 848e142e59ce9b4dcc47b41a37fb4d46b073d330..63819a2f98df57b17a49a426500e48111befcfa4 100644 (file)
@@ -14,8 +14,6 @@
 use rustc_span::symbol::{sym, Symbol};
 use rustc_span::{edition::Edition, BytePos, Pos, Span};
 
-use tracing::debug;
-
 mod tokentrees;
 mod unescape_error_reporting;
 mod unicode_chars;
index 273827864f1a405295e2f7f0499d605c82f290f0..77c4fadab45eacc9f61d5fd4cb4d361cedc62666 100644 (file)
@@ -20,13 +20,9 @@ pub(crate) fn emit_unescape_error(
     range: Range<usize>,
     error: EscapeError,
 ) {
-    tracing::debug!(
+    debug!(
         "emit_unescape_error: {:?}, {:?}, {:?}, {:?}, {:?}",
-        lit,
-        span_with_quotes,
-        mode,
-        range,
-        error
+        lit, span_with_quotes, mode, range, error
     );
     let last_char = || {
         let c = lit[range.clone()].chars().rev().next().unwrap();
index 72ab96b5ca67032aa9e4c83509e42a5b4ced6613..77a6bde1c164e43ac43c73d6a36e50929da3a671 100644 (file)
@@ -7,8 +7,6 @@
 use rustc_span::{sym, BytePos, Span};
 use std::convert::TryInto;
 
-use tracing::debug;
-
 // Public for rustfmt usage
 #[derive(Debug)]
 pub enum InnerAttrPolicy<'a> {
index f0ea1dfe297f2fb5c99da39460a21b693bc9c980..dd806e2130e9b062f62a58603524534328ab3298 100644 (file)
@@ -29,7 +29,6 @@
 use std::mem::take;
 
 use crate::parser;
-use tracing::{debug, trace};
 
 const TURBOFISH_SUGGESTION_STR: &str =
     "use `::<...>` instead of `<...>` to specify lifetime, type, or const arguments";
index b743162a7e4d0809a234454ccea601335bb9cc2a..5b75d1d5f221daa69dbaf0d34fc1a0462ec756ba 100644 (file)
@@ -22,7 +22,6 @@
 
 use std::convert::TryFrom;
 use std::mem;
-use tracing::debug;
 
 impl<'a> Parser<'a> {
     /// Parses a source module as a crate. This is the main entry point for the parser.
index 5e79308464f6408bb22b6278c22aaef8f80ca42b..5c8f374255c7fc91635b88391161d743150ecced 100644 (file)
@@ -37,7 +37,6 @@
 use rustc_session::parse::ParseSess;
 use rustc_span::source_map::{Span, DUMMY_SP};
 use rustc_span::symbol::{kw, sym, Ident, Symbol};
-use tracing::debug;
 
 use std::ops::Range;
 use std::{cmp, mem, slice};
index fc7fb866f110f5dd91e85fa1f0a0d79ea8a47cef..fdc1af27f82e4206e3e7d95eec13f6ffb59a4a92 100644 (file)
@@ -13,7 +13,6 @@
 use rustc_span::symbol::{kw, sym, Ident};
 
 use std::mem;
-use tracing::debug;
 
 /// Specifies how to parse a path.
 #[derive(Copy, Clone, PartialEq)]
index 5b79dd3d3ef25d3a14e0760bcb2587773e14dacd..2a6889af7c2c92aab88860e449ae341e8e07917f 100644 (file)
@@ -1573,7 +1573,7 @@ fn check_unused_vars_in_pat(
         }
     }
 
-    #[tracing::instrument(skip(self), level = "INFO")]
+    #[instrument(skip(self), level = "INFO")]
     fn report_unused(
         &self,
         hir_ids_and_spans: Vec<(HirId, Span, Span)>,
index 1e423ddb7102cb753ae0bf8aefcc1d54664afc11..63f83f8965ec52c8a56e15123549eea3369dfef0 100644 (file)
@@ -75,6 +75,14 @@ pub struct InPublicInterface<'a> {
     pub vis_span: Span,
 }
 
+#[derive(SessionDiagnostic)]
+#[diag(privacy::report_access_level)]
+pub struct ReportAccessLevel {
+    #[primary_span]
+    pub span: Span,
+    pub descr: String,
+}
+
 #[derive(LintDiagnostic)]
 #[diag(privacy::from_private_dep_in_public_interface)]
 pub struct FromPrivateDependencyInPublicInterface<'a> {
index 5d562f18a815814785602fff35961933b7b32d0a..ba69bc23118b2527921188cdf8f7a595a97bef8b 100644 (file)
@@ -8,6 +8,9 @@
 #![deny(rustc::untranslatable_diagnostic)]
 #![deny(rustc::diagnostic_outside_of_impl)]
 
+#[macro_use]
+extern crate tracing;
+
 mod errors;
 
 use rustc_ast::MacroDef;
@@ -30,7 +33,7 @@
 use rustc_middle::ty::{TraitRef, Ty, TyCtxt, TypeSuperVisitable, TypeVisitable, TypeVisitor};
 use rustc_session::lint;
 use rustc_span::hygiene::Transparency;
-use rustc_span::symbol::{kw, Ident};
+use rustc_span::symbol::{kw, sym, Ident};
 use rustc_span::Span;
 
 use std::marker::PhantomData;
@@ -39,7 +42,8 @@
 
 use errors::{
     FieldIsPrivate, FieldIsPrivateLabel, FromPrivateDependencyInPublicInterface, InPublicInterface,
-    InPublicInterfaceTraits, ItemIsPrivate, PrivateInPublicLint, UnnamedItemIsPrivate,
+    InPublicInterfaceTraits, ItemIsPrivate, PrivateInPublicLint, ReportAccessLevel,
+    UnnamedItemIsPrivate,
 };
 
 ////////////////////////////////////////////////////////////////////////////////
@@ -904,6 +908,60 @@ fn visit_def_id(
     }
 }
 
+////////////////////////////////////////////////////////////////////////////////
+/// Visitor, used for AccessLevels table checking
+////////////////////////////////////////////////////////////////////////////////
+pub struct TestReachabilityVisitor<'tcx, 'a> {
+    tcx: TyCtxt<'tcx>,
+    access_levels: &'a AccessLevels,
+}
+
+impl<'tcx, 'a> TestReachabilityVisitor<'tcx, 'a> {
+    fn access_level_diagnostic(&mut self, def_id: LocalDefId) {
+        if self.tcx.has_attr(def_id.to_def_id(), sym::rustc_access_level) {
+            let access_level = format!("{:?}", self.access_levels.map.get(&def_id));
+            let span = self.tcx.def_span(def_id.to_def_id());
+            self.tcx.sess.emit_err(ReportAccessLevel { span, descr: access_level });
+        }
+    }
+}
+
+impl<'tcx, 'a> Visitor<'tcx> for TestReachabilityVisitor<'tcx, 'a> {
+    fn visit_item(&mut self, item: &'tcx hir::Item<'tcx>) {
+        self.access_level_diagnostic(item.def_id);
+
+        match item.kind {
+            hir::ItemKind::Enum(ref def, _) => {
+                for variant in def.variants.iter() {
+                    let variant_id = self.tcx.hir().local_def_id(variant.id);
+                    self.access_level_diagnostic(variant_id);
+                    for field in variant.data.fields() {
+                        let def_id = self.tcx.hir().local_def_id(field.hir_id);
+                        self.access_level_diagnostic(def_id);
+                    }
+                }
+            }
+            hir::ItemKind::Struct(ref def, _) | hir::ItemKind::Union(ref def, _) => {
+                for field in def.fields() {
+                    let def_id = self.tcx.hir().local_def_id(field.hir_id);
+                    self.access_level_diagnostic(def_id);
+                }
+            }
+            _ => {}
+        }
+    }
+
+    fn visit_trait_item(&mut self, item: &'tcx hir::TraitItem<'tcx>) {
+        self.access_level_diagnostic(item.def_id);
+    }
+    fn visit_impl_item(&mut self, item: &'tcx hir::ImplItem<'tcx>) {
+        self.access_level_diagnostic(item.def_id);
+    }
+    fn visit_foreign_item(&mut self, item: &'tcx hir::ForeignItem<'tcx>) {
+        self.access_level_diagnostic(item.def_id);
+    }
+}
+
 //////////////////////////////////////////////////////////////////////////////////////
 /// Name privacy visitor, checks privacy and reports violations.
 /// Most of name privacy checks are performed during the main resolution phase,
@@ -1784,7 +1842,7 @@ fn check_def_id(&mut self, def_id: DefId, kind: &str, descr: &dyn fmt::Display)
     fn leaks_private_dep(&self, item_id: DefId) -> bool {
         let ret = self.required_visibility.is_public() && self.tcx.is_private_dep(item_id.krate);
 
-        tracing::debug!("leaks_private_dep(item_id={:?})={}", item_id, ret);
+        debug!("leaks_private_dep(item_id={:?})={}", item_id, ret);
         ret
     }
 }
@@ -2042,6 +2100,9 @@ fn privacy_access_levels(tcx: TyCtxt<'_>, (): ()) -> &AccessLevels {
         }
     }
 
+    let mut check_visitor = TestReachabilityVisitor { tcx, access_levels: &visitor.access_levels };
+    tcx.hir().visit_all_item_likes_in_crate(&mut check_visitor);
+
     tcx.arena.alloc(visitor.access_levels)
 }
 
index f38f29e14afd4c4fba99299f62117620e6805906..274df5b5e5e9415679ffd389b9ab3ee5626c9e18 100644 (file)
@@ -7,13 +7,16 @@
 use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
 use rustc_data_structures::sync::Lock;
 use rustc_errors::{Diagnostic, Handler};
-use rustc_middle::dep_graph::{self, DepKind, DepNodeIndex, SerializedDepNodeIndex};
+use rustc_middle::dep_graph::{
+    self, DepKind, DepKindStruct, DepNode, DepNodeIndex, SerializedDepNodeIndex,
+};
 use rustc_middle::ty::tls::{self, ImplicitCtxt};
 use rustc_middle::ty::{self, TyCtxt};
-use rustc_query_system::dep_graph::HasDepContext;
+use rustc_query_system::dep_graph::{DepNodeParams, HasDepContext};
 use rustc_query_system::ich::StableHashingContext;
 use rustc_query_system::query::{
-    QueryContext, QueryJobId, QueryMap, QuerySideEffects, QueryStackFrame,
+    force_query, QueryConfig, QueryContext, QueryDescription, QueryJobId, QueryMap,
+    QuerySideEffects, QueryStackFrame,
 };
 use std::any::Any;
 use std::num::NonZeroU64;
@@ -298,6 +301,66 @@ pub(crate) fn create_query_frame<
     QueryStackFrame::new(name, description, span, def_kind, hash)
 }
 
+fn try_load_from_on_disk_cache<'tcx, Q>(tcx: TyCtxt<'tcx>, dep_node: DepNode)
+where
+    Q: QueryDescription<QueryCtxt<'tcx>>,
+    Q::Key: DepNodeParams<TyCtxt<'tcx>>,
+{
+    debug_assert!(tcx.dep_graph.is_green(&dep_node));
+
+    let key = Q::Key::recover(tcx, &dep_node).unwrap_or_else(|| {
+        panic!("Failed to recover key for {:?} with hash {}", dep_node, dep_node.hash)
+    });
+    if Q::cache_on_disk(tcx, &key) {
+        let _ = Q::execute_query(tcx, key);
+    }
+}
+
+fn force_from_dep_node<'tcx, Q>(tcx: TyCtxt<'tcx>, dep_node: DepNode) -> bool
+where
+    Q: QueryDescription<QueryCtxt<'tcx>>,
+    Q::Key: DepNodeParams<TyCtxt<'tcx>>,
+{
+    if let Some(key) = Q::Key::recover(tcx, &dep_node) {
+        #[cfg(debug_assertions)]
+        let _guard = tracing::span!(tracing::Level::TRACE, stringify!($name), ?key).entered();
+        let tcx = QueryCtxt::from_tcx(tcx);
+        force_query::<Q, _>(tcx, key, dep_node);
+        true
+    } else {
+        false
+    }
+}
+
+pub(crate) fn query_callback<'tcx, Q: QueryConfig>(
+    is_anon: bool,
+    is_eval_always: bool,
+) -> DepKindStruct<'tcx>
+where
+    Q: QueryDescription<QueryCtxt<'tcx>>,
+    Q::Key: DepNodeParams<TyCtxt<'tcx>>,
+{
+    let fingerprint_style = Q::Key::fingerprint_style();
+
+    if is_anon || !fingerprint_style.reconstructible() {
+        return DepKindStruct {
+            is_anon,
+            is_eval_always,
+            fingerprint_style,
+            force_from_dep_node: None,
+            try_load_from_on_disk_cache: None,
+        };
+    }
+
+    DepKindStruct {
+        is_anon,
+        is_eval_always,
+        fingerprint_style,
+        force_from_dep_node: Some(force_from_dep_node::<Q>),
+        try_load_from_on_disk_cache: Some(try_load_from_on_disk_cache::<Q>),
+    }
+}
+
 // NOTE: `$V` isn't used here, but we still need to match on it so it can be passed to other macros
 // invoked by `rustc_query_append`.
 macro_rules! define_queries {
@@ -308,18 +371,6 @@ macro_rules! define_queries {
             input: ($(([$($modifiers)*] [$($attr)*] [$name]))*)
         }
 
-        mod make_query {
-            use super::*;
-
-            // Create an eponymous constructor for each query.
-            $(#[allow(nonstandard_style)] $(#[$attr])*
-            pub fn $name<'tcx>(tcx: QueryCtxt<'tcx>, key: <queries::$name<'tcx> as QueryConfig>::Key) -> QueryStackFrame {
-                let kind = dep_graph::DepKind::$name;
-                let name = stringify!($name);
-                $crate::plumbing::create_query_frame(tcx, queries::$name::describe, key, kind, name)
-            })*
-        }
-
         #[allow(nonstandard_style)]
         mod queries {
             use std::marker::PhantomData;
@@ -373,18 +424,19 @@ fn make_vtable(tcx: QueryCtxt<'tcx>, key: &Self::Key) ->
                     try_load_from_disk: Self::TRY_LOAD_FROM_DISK,
                 }
             }
+
+            fn execute_query(tcx: TyCtxt<'tcx>, k: Self::Key) -> Self::Stored {
+                tcx.$name(k)
+            }
         })*
 
         #[allow(nonstandard_style)]
         mod query_callbacks {
             use super::*;
-            use rustc_middle::dep_graph::DepNode;
-            use rustc_query_system::dep_graph::DepNodeParams;
-            use rustc_query_system::query::{force_query, QueryDescription};
             use rustc_query_system::dep_graph::FingerprintStyle;
 
             // We use this for most things when incr. comp. is turned off.
-            pub fn Null() -> DepKindStruct {
+            pub fn Null<'tcx>() -> DepKindStruct<'tcx> {
                 DepKindStruct {
                     is_anon: false,
                     is_eval_always: false,
@@ -395,7 +447,7 @@ pub fn Null() -> DepKindStruct {
             }
 
             // We use this for the forever-red node.
-            pub fn Red() -> DepKindStruct {
+            pub fn Red<'tcx>() -> DepKindStruct<'tcx> {
                 DepKindStruct {
                     is_anon: false,
                     is_eval_always: false,
@@ -405,7 +457,7 @@ pub fn Red() -> DepKindStruct {
                 }
             }
 
-            pub fn TraitSelect() -> DepKindStruct {
+            pub fn TraitSelect<'tcx>() -> DepKindStruct<'tcx> {
                 DepKindStruct {
                     is_anon: true,
                     is_eval_always: false,
@@ -415,7 +467,7 @@ pub fn TraitSelect() -> DepKindStruct {
                 }
             }
 
-            pub fn CompileCodegenUnit() -> DepKindStruct {
+            pub fn CompileCodegenUnit<'tcx>() -> DepKindStruct<'tcx> {
                 DepKindStruct {
                     is_anon: false,
                     is_eval_always: false,
@@ -425,7 +477,7 @@ pub fn CompileCodegenUnit() -> DepKindStruct {
                 }
             }
 
-            pub fn CompileMonoItem() -> DepKindStruct {
+            pub fn CompileMonoItem<'tcx>() -> DepKindStruct<'tcx> {
                 DepKindStruct {
                     is_anon: false,
                     is_eval_always: false,
@@ -435,60 +487,15 @@ pub fn CompileMonoItem() -> DepKindStruct {
                 }
             }
 
-            $(pub(crate) fn $name()-> DepKindStruct {
-                let is_anon = is_anon!([$($modifiers)*]);
-                let is_eval_always = is_eval_always!([$($modifiers)*]);
-
-                let fingerprint_style =
-                    <<queries::$name<'_> as QueryConfig>::Key as DepNodeParams<TyCtxt<'_>>>::fingerprint_style();
-
-                if is_anon || !fingerprint_style.reconstructible() {
-                    return DepKindStruct {
-                        is_anon,
-                        is_eval_always,
-                        fingerprint_style,
-                        force_from_dep_node: None,
-                        try_load_from_on_disk_cache: None,
-                    }
-                }
-
-                #[inline(always)]
-                fn recover<'tcx>(tcx: TyCtxt<'tcx>, dep_node: DepNode) -> Option<<queries::$name<'tcx> as QueryConfig>::Key> {
-                    <<queries::$name<'_> as QueryConfig>::Key as DepNodeParams<TyCtxt<'_>>>::recover(tcx, &dep_node)
-                }
-
-                fn force_from_dep_node(tcx: TyCtxt<'_>, dep_node: DepNode) -> bool {
-                    if let Some(key) = recover(tcx, dep_node) {
-                        #[cfg(debug_assertions)]
-                        let _guard = tracing::span!(tracing::Level::TRACE, stringify!($name), ?key).entered();
-                        let tcx = QueryCtxt::from_tcx(tcx);
-                        force_query::<queries::$name<'_>, _>(tcx, key, dep_node);
-                        true
-                    } else {
-                        false
-                    }
-                }
-
-                fn try_load_from_on_disk_cache(tcx: TyCtxt<'_>, dep_node: DepNode) {
-                    debug_assert!(tcx.dep_graph.is_green(&dep_node));
-
-                    let key = recover(tcx, dep_node).unwrap_or_else(|| panic!("Failed to recover key for {:?} with hash {}", dep_node, dep_node.hash));
-                    if queries::$name::cache_on_disk(tcx, &key) {
-                        let _ = tcx.$name(key);
-                    }
-                }
-
-                DepKindStruct {
-                    is_anon,
-                    is_eval_always,
-                    fingerprint_style,
-                    force_from_dep_node: Some(force_from_dep_node),
-                    try_load_from_on_disk_cache: Some(try_load_from_on_disk_cache),
-                }
+            $(pub(crate) fn $name<'tcx>()-> DepKindStruct<'tcx> {
+                $crate::plumbing::query_callback::<queries::$name<'tcx>>(
+                    is_anon!([$($modifiers)*]),
+                    is_eval_always!([$($modifiers)*]),
+                )
             })*
         }
 
-        pub fn query_callbacks<'tcx>(arena: &'tcx Arena<'tcx>) -> &'tcx [DepKindStruct] {
+        pub fn query_callbacks<'tcx>(arena: &'tcx Arena<'tcx>) -> &'tcx [DepKindStruct<'tcx>] {
             arena.alloc_from_iter(make_dep_kind_array!(query_callbacks))
         }
     }
@@ -531,9 +538,14 @@ pub(crate) fn try_collect_active_jobs(
                 let mut jobs = QueryMap::default();
 
                 $(
+                    let make_query = |tcx, key| {
+                        let kind = dep_graph::DepKind::$name;
+                        let name = stringify!($name);
+                        $crate::plumbing::create_query_frame(tcx, queries::$name::describe, key, kind, name)
+                    };
                     self.$name.try_collect_active_jobs(
                         tcx,
-                        make_query::$name,
+                        make_query,
                         &mut jobs,
                     )?;
                 )*
@@ -555,7 +567,7 @@ fn try_mark_green(&'tcx self, tcx: TyCtxt<'tcx>, dep_node: &dep_graph::DepNode)
 
             $($(#[$attr])*
             #[inline(always)]
-            #[tracing::instrument(level = "trace", skip(self, tcx))]
+            #[tracing::instrument(level = "trace", skip(self, tcx), ret)]
             fn $name(
                 &'tcx self,
                 tcx: TyCtxt<'tcx>,
index bd0fd7ac3503a16ede69e8faa1f30a5f8140916d..ea38df836cbf1e4a0f9b98b8cad319644a4ad8b6 100644 (file)
@@ -73,4 +73,7 @@ fn query_cache<'a>(tcx: CTX) -> &'a Self::Cache
     fn make_vtable(tcx: CTX, key: &Self::Key) -> QueryVTable<CTX, Self::Key, Self::Value>;
 
     fn cache_on_disk(tcx: CTX::DepContext, key: &Self::Key) -> bool;
+
+    // Don't use this method to compute query results, instead use the methods on TyCtxt
+    fn execute_query(tcx: CTX::DepContext, k: Self::Key) -> Self::Stored;
 }
index 3fba923d9fdf425c443300fb15eed97ba6ffdfd8..0a3add2e0f5328a7e7ff90ff20630d12408484e1 100644 (file)
@@ -1,25 +1,21 @@
+use crate::imports::ImportKind;
+use crate::NameBinding;
+use crate::NameBindingKind;
+use crate::Resolver;
 use rustc_ast::ast;
 use rustc_ast::visit;
 use rustc_ast::visit::Visitor;
 use rustc_ast::Crate;
 use rustc_ast::EnumDef;
-use rustc_ast::ForeignMod;
 use rustc_ast::NodeId;
 use rustc_hir::def_id::LocalDefId;
 use rustc_hir::def_id::CRATE_DEF_ID;
 use rustc_middle::middle::privacy::AccessLevel;
-use rustc_middle::ty::Visibility;
+use rustc_middle::ty::DefIdTree;
 use rustc_span::sym;
 
-use crate::imports::ImportKind;
-use crate::BindingKey;
-use crate::NameBinding;
-use crate::NameBindingKind;
-use crate::Resolver;
-
 pub struct AccessLevelsVisitor<'r, 'a> {
     r: &'r mut Resolver<'a>,
-    prev_level: Option<AccessLevel>,
     changed: bool,
 }
 
@@ -28,31 +24,32 @@ impl<'r, 'a> AccessLevelsVisitor<'r, 'a> {
     /// For now, this doesn't resolve macros (FIXME) and cannot resolve Impl, as we
     /// need access to a TyCtxt for that.
     pub fn compute_access_levels<'c>(r: &'r mut Resolver<'a>, krate: &'c Crate) {
-        let mut visitor =
-            AccessLevelsVisitor { r, changed: false, prev_level: Some(AccessLevel::Public) };
+        let mut visitor = AccessLevelsVisitor { r, changed: false };
 
         visitor.set_access_level_def_id(CRATE_DEF_ID, Some(AccessLevel::Public));
-        visitor.set_exports_access_level(CRATE_DEF_ID);
+        visitor.set_bindings_access_level(CRATE_DEF_ID);
 
         while visitor.changed {
             visitor.reset();
             visit::walk_crate(&mut visitor, krate);
         }
 
-        tracing::info!("resolve::access_levels: {:#?}", r.access_levels);
+        info!("resolve::access_levels: {:#?}", r.access_levels);
     }
 
     fn reset(&mut self) {
         self.changed = false;
-        self.prev_level = Some(AccessLevel::Public);
     }
 
-    /// Update the access level of the exports of the given module accordingly. The module access
+    /// Update the access level of the bindings in the given module accordingly. The module access
     /// level has to be Exported or Public.
     /// This will also follow `use` chains (see PrivacyVisitor::set_import_binding_access_level).
-    fn set_exports_access_level(&mut self, module_id: LocalDefId) {
+    fn set_bindings_access_level(&mut self, module_id: LocalDefId) {
         assert!(self.r.module_map.contains_key(&&module_id.to_def_id()));
-
+        let module_level = self.r.access_levels.map.get(&module_id).copied();
+        if !module_level.is_some() {
+            return;
+        }
         // Set the given binding access level to `AccessLevel::Public` and
         // sets the rest of the `use` chain to `AccessLevel::Exported` until
         // we hit the actual exported item.
@@ -72,28 +69,20 @@ fn set_exports_access_level(&mut self, module_id: LocalDefId) {
                 }
             };
 
-        let module_level = self.r.access_levels.map.get(&module_id).copied();
-        assert!(module_level >= Some(AccessLevel::Exported));
-
-        if let Some(exports) = self.r.reexport_map.get(&module_id) {
-            let pub_exports = exports
-                .iter()
-                .filter(|ex| ex.vis == Visibility::Public)
-                .cloned()
-                .collect::<Vec<_>>();
-
-            let module = self.r.get_module(module_id.to_def_id()).unwrap();
-            for export in pub_exports.into_iter() {
-                if let Some(export_def_id) = export.res.opt_def_id().and_then(|id| id.as_local()) {
-                    self.set_access_level_def_id(export_def_id, Some(AccessLevel::Exported));
-                }
-
-                if let Some(ns) = export.res.ns() {
-                    let key = BindingKey { ident: export.ident, ns, disambiguator: 0 };
-                    let name_res = self.r.resolution(module, key);
-                    if let Some(binding) = name_res.borrow().binding() {
-                        set_import_binding_access_level(self, binding, module_level)
-                    }
+        let module = self.r.get_module(module_id.to_def_id()).unwrap();
+        let resolutions = self.r.resolutions(module);
+
+        for (.., name_resolution) in resolutions.borrow().iter() {
+            if let Some(binding) = name_resolution.borrow().binding() && binding.vis.is_public() && !binding.is_ambiguity() {
+                let access_level = match binding.is_import() {
+                    true => {
+                        set_import_binding_access_level(self, binding, module_level);
+                        Some(AccessLevel::Exported)
+                    },
+                    false => module_level,
+                };
+                if let Some(def_id) = binding.res().opt_def_id().and_then(|id| id.as_local()) {
+                    self.set_access_level_def_id(def_id, access_level);
                 }
             }
         }
@@ -127,97 +116,59 @@ fn set_access_level_def_id(
 
 impl<'r, 'ast> Visitor<'ast> for AccessLevelsVisitor<'ast, 'r> {
     fn visit_item(&mut self, item: &'ast ast::Item) {
-        let inherited_item_level = match item.kind {
+        let def_id = self.r.local_def_id(item.id);
+        // Set access level of nested items.
+        // If it's a mod, also make the visitor walk all of its items
+        match item.kind {
             // Resolved in rustc_privacy when types are available
             ast::ItemKind::Impl(..) => return,
 
-            // Only exported `macro_rules!` items are public, but they always are
-            ast::ItemKind::MacroDef(ref macro_def) if macro_def.macro_rules => {
-                let is_macro_export =
-                    item.attrs.iter().any(|attr| attr.has_name(sym::macro_export));
-                if is_macro_export { Some(AccessLevel::Public) } else { None }
-            }
-
-            // Foreign modules inherit level from parents.
-            ast::ItemKind::ForeignMod(..) => self.prev_level,
-
-            // Other `pub` items inherit levels from parents.
-            ast::ItemKind::ExternCrate(..)
-            | ast::ItemKind::Use(..)
-            | ast::ItemKind::Static(..)
-            | ast::ItemKind::Const(..)
-            | ast::ItemKind::Fn(..)
-            | ast::ItemKind::Mod(..)
-            | ast::ItemKind::GlobalAsm(..)
-            | ast::ItemKind::TyAlias(..)
-            | ast::ItemKind::Enum(..)
-            | ast::ItemKind::Struct(..)
-            | ast::ItemKind::Union(..)
-            | ast::ItemKind::Trait(..)
-            | ast::ItemKind::TraitAlias(..)
-            | ast::ItemKind::MacroDef(..) => {
-                if item.vis.kind.is_pub() {
-                    self.prev_level
-                } else {
-                    None
-                }
-            }
-
             // Should be unreachable at this stage
             ast::ItemKind::MacCall(..) => panic!(
                 "ast::ItemKind::MacCall encountered, this should not anymore appear at this stage"
             ),
-        };
 
-        let access_level = self.set_access_level(item.id, inherited_item_level);
+            // Foreign modules inherit level from parents.
+            ast::ItemKind::ForeignMod(..) => {
+                let parent_level =
+                    self.r.access_levels.map.get(&self.r.local_parent(def_id)).copied();
+                self.set_access_level(item.id, parent_level);
+            }
 
-        // Set access level of nested items.
-        // If it's a mod, also make the visitor walk all of its items
-        match item.kind {
-            ast::ItemKind::Mod(..) => {
-                if access_level.is_some() {
-                    self.set_exports_access_level(self.r.local_def_id(item.id));
+            // Only exported `macro_rules!` items are public, but they always are
+            ast::ItemKind::MacroDef(ref macro_def) if macro_def.macro_rules => {
+                if item.attrs.iter().any(|attr| attr.has_name(sym::macro_export)) {
+                    self.set_access_level(item.id, Some(AccessLevel::Public));
                 }
+            }
 
-                let orig_level = std::mem::replace(&mut self.prev_level, access_level);
+            ast::ItemKind::Mod(..) => {
+                self.set_bindings_access_level(def_id);
                 visit::walk_item(self, item);
-                self.prev_level = orig_level;
             }
 
-            ast::ItemKind::ForeignMod(ForeignMod { ref items, .. }) => {
-                for nested in items {
-                    if nested.vis.kind.is_pub() {
-                        self.set_access_level(nested.id, access_level);
-                    }
-                }
-            }
             ast::ItemKind::Enum(EnumDef { ref variants }, _) => {
+                self.set_bindings_access_level(def_id);
                 for variant in variants {
-                    let variant_level = self.set_access_level(variant.id, access_level);
-                    if let Some(ctor_id) = variant.data.ctor_id() {
-                        self.set_access_level(ctor_id, access_level);
-                    }
-
+                    let variant_def_id = self.r.local_def_id(variant.id);
+                    let variant_level = self.r.access_levels.map.get(&variant_def_id).copied();
                     for field in variant.data.fields() {
                         self.set_access_level(field.id, variant_level);
                     }
                 }
             }
-            ast::ItemKind::Struct(ref def, _) | ast::ItemKind::Union(ref def, _) => {
-                if let Some(ctor_id) = def.ctor_id() {
-                    self.set_access_level(ctor_id, access_level);
-                }
 
+            ast::ItemKind::Struct(ref def, _) | ast::ItemKind::Union(ref def, _) => {
+                let inherited_level = self.r.access_levels.map.get(&def_id).copied();
                 for field in def.fields() {
                     if field.vis.kind.is_pub() {
-                        self.set_access_level(field.id, access_level);
+                        self.set_access_level(field.id, inherited_level);
                     }
                 }
             }
-            ast::ItemKind::Trait(ref trait_kind) => {
-                for nested in trait_kind.items.iter() {
-                    self.set_access_level(nested.id, access_level);
-                }
+
+            ast::ItemKind::Trait(..) => {
+                self.set_bindings_access_level(def_id);
             }
 
             ast::ItemKind::ExternCrate(..)
@@ -229,9 +180,6 @@ fn visit_item(&mut self, item: &'ast ast::Item) {
             | ast::ItemKind::TraitAlias(..)
             | ast::ItemKind::MacroDef(..)
             | ast::ItemKind::Fn(..) => return,
-
-            // Unreachable kinds
-            ast::ItemKind::Impl(..) | ast::ItemKind::MacCall(..) => unreachable!(),
         }
     }
 }
index 8f3b6009bd6ef8a5f31fa6387c5badaceb443faf..51e8c24b9c25a51066088753bf4ec5b00a261798 100644 (file)
@@ -36,7 +36,6 @@
 
 use std::cell::Cell;
 use std::ptr;
-use tracing::debug;
 
 type Res = def::Res<NodeId>;
 
@@ -1030,7 +1029,7 @@ fn build_reduced_graph_for_external_crate_res(&mut self, child: ModChild) {
                 self.insert_field_names(def_id, field_names);
             }
             Res::Def(DefKind::AssocFn, def_id) => {
-                if cstore.fn_has_self_parameter_untracked(def_id) {
+                if cstore.fn_has_self_parameter_untracked(def_id, self.r.session) {
                     self.r.has_self.insert(def_id);
                 }
             }
index 66641fb2cb248dc15446f722b0bb88f6f530a536..5955d8df16ee1edfa34f6edf2af8fca6c3cfc69c 100644 (file)
@@ -8,7 +8,6 @@
 use rustc_span::hygiene::LocalExpnId;
 use rustc_span::symbol::sym;
 use rustc_span::Span;
-use tracing::debug;
 
 pub(crate) fn collect_definitions(
     resolver: &mut Resolver<'_>,
index 2d15b1b0a1b94fbb23740e9248407b6732a2d570..4fd6fe4e36c69093babe14a7b3b2e8c214fa83d4 100644 (file)
@@ -25,7 +25,6 @@
 use rustc_span::source_map::SourceMap;
 use rustc_span::symbol::{kw, sym, Ident, Symbol};
 use rustc_span::{BytePos, Span};
-use tracing::debug;
 
 use crate::imports::{Import, ImportKind, ImportResolver};
 use crate::late::{PatternSource, Rib};
index 2afba94d793af192258f03affa50a5c65e63093c..b84a610833ddf6a8faa398d6e070d0ef93b25136 100644 (file)
@@ -273,7 +273,7 @@ fn hygienic_lexical_parent(
     ///
     /// Invariant: This must only be called during main resolution, not during
     /// import resolution.
-    #[tracing::instrument(level = "debug", skip(self, ribs))]
+    #[instrument(level = "debug", skip(self, ribs))]
     pub(crate) fn resolve_ident_in_lexical_scope(
         &mut self,
         mut ident: Ident,
@@ -367,7 +367,7 @@ pub(crate) fn resolve_ident_in_lexical_scope(
     /// expansion and import resolution (perhaps they can be merged in the future).
     /// The function is used for resolving initial segments of macro paths (e.g., `foo` in
     /// `foo::bar!(); or `foo!();`) and also for import paths on 2018 edition.
-    #[tracing::instrument(level = "debug", skip(self, scope_set))]
+    #[instrument(level = "debug", skip(self, scope_set))]
     pub(crate) fn early_resolve_ident_in_lexical_scope(
         &mut self,
         orig_ident: Ident,
@@ -708,7 +708,7 @@ struct Flags: u8 {
         Err(Determinacy::determined(determinacy == Determinacy::Determined || force))
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     pub(crate) fn maybe_resolve_ident_in_module(
         &mut self,
         module: ModuleOrUniformRoot<'a>,
@@ -720,7 +720,7 @@ pub(crate) fn maybe_resolve_ident_in_module(
             .map_err(|(determinacy, _)| determinacy)
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     pub(crate) fn resolve_ident_in_module(
         &mut self,
         module: ModuleOrUniformRoot<'a>,
@@ -734,7 +734,7 @@ pub(crate) fn resolve_ident_in_module(
             .map_err(|(determinacy, _)| determinacy)
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn resolve_ident_in_module_ext(
         &mut self,
         module: ModuleOrUniformRoot<'a>,
@@ -772,7 +772,7 @@ fn resolve_ident_in_module_ext(
         )
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn resolve_ident_in_module_unadjusted(
         &mut self,
         module: ModuleOrUniformRoot<'a>,
@@ -796,7 +796,7 @@ fn resolve_ident_in_module_unadjusted(
 
     /// Attempts to resolve `ident` in namespaces `ns` of `module`.
     /// Invariant: if `finalize` is `Some`, expansion and import resolution must be complete.
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn resolve_ident_in_module_unadjusted_ext(
         &mut self,
         module: ModuleOrUniformRoot<'a>,
@@ -1059,7 +1059,7 @@ fn resolve_ident_in_module_unadjusted_ext(
     }
 
     /// Validate a local resolution (from ribs).
-    #[tracing::instrument(level = "debug", skip(self, all_ribs))]
+    #[instrument(level = "debug", skip(self, all_ribs))]
     fn validate_res_from_ribs(
         &mut self,
         rib_index: usize,
@@ -1294,7 +1294,7 @@ fn validate_res_from_ribs(
         res
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     pub(crate) fn maybe_resolve_path(
         &mut self,
         path: &[Segment],
@@ -1304,7 +1304,7 @@ pub(crate) fn maybe_resolve_path(
         self.resolve_path_with_ribs(path, opt_ns, parent_scope, None, None, None)
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     pub(crate) fn resolve_path(
         &mut self,
         path: &[Segment],
index c2491c6ebdec08892d03f255f2f991b4484b902a..27745cee52df7f3243630d103984205ecbb9db78 100644 (file)
@@ -23,8 +23,6 @@
 use rustc_span::symbol::{kw, Ident, Symbol};
 use rustc_span::Span;
 
-use tracing::*;
-
 use std::cell::Cell;
 use std::{mem, ptr};
 
@@ -1135,24 +1133,15 @@ fn finalize_resolutions_in(&mut self, module: Module<'b>) {
         if let Some(def_id) = module.opt_def_id() {
             let mut reexports = Vec::new();
 
-            module.for_each_child(self.r, |_, ident, _, binding| {
-                // FIXME: Consider changing the binding inserted by `#[macro_export] macro_rules`
-                // into the crate root to actual `NameBindingKind::Import`.
-                if binding.is_import()
-                    || matches!(binding.kind, NameBindingKind::Res(_, _is_macro_export @ true))
-                {
-                    let res = binding.res().expect_non_local();
-                    // Ambiguous imports are treated as errors at this point and are
-                    // not exposed to other crates (see #36837 for more details).
-                    if res != def::Res::Err && !binding.is_ambiguity() {
-                        reexports.push(ModChild {
-                            ident,
-                            res,
-                            vis: binding.vis,
-                            span: binding.span,
-                            macro_rules: false,
-                        });
-                    }
+            module.for_each_child(self.r, |this, ident, _, binding| {
+                if let Some(res) = this.is_reexport(binding) {
+                    reexports.push(ModChild {
+                        ident,
+                        res,
+                        vis: binding.vis,
+                        span: binding.span,
+                        macro_rules: false,
+                    });
                 }
             });
 
index 693ec86616ee431e3ff70e2bbeeef37228ba70f2..dbe4d691f04cdf1a465dc3d1598498294f27b784 100644 (file)
@@ -32,7 +32,6 @@
 use rustc_span::source_map::{respan, Spanned};
 use std::collections::{hash_map::Entry, BTreeSet};
 use std::mem::{replace, take};
-use tracing::debug;
 
 mod diagnostics;
 pub(crate) mod lifetimes;
@@ -1390,7 +1389,7 @@ fn visit_generic_params(&mut self, params: &'ast [GenericParam], add_self_upper:
         })
     }
 
-    #[tracing::instrument(level = "debug", skip(self, work))]
+    #[instrument(level = "debug", skip(self, work))]
     fn with_lifetime_rib<T>(
         &mut self,
         kind: LifetimeRibKind,
@@ -1404,7 +1403,7 @@ fn with_lifetime_rib<T>(
         ret
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn resolve_lifetime(&mut self, lifetime: &'ast Lifetime, use_ctxt: visit::LifetimeCtxt) {
         let ident = lifetime.ident;
 
@@ -1508,7 +1507,7 @@ fn resolve_lifetime(&mut self, lifetime: &'ast Lifetime, use_ctxt: visit::Lifeti
         self.record_lifetime_res(lifetime.id, LifetimeRes::Error, LifetimeElisionCandidate::Named);
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn resolve_anonymous_lifetime(&mut self, lifetime: &Lifetime, elided: bool) {
         debug_assert_eq!(lifetime.ident.name, kw::UnderscoreLifetime);
 
@@ -1573,7 +1572,7 @@ fn resolve_anonymous_lifetime(&mut self, lifetime: &Lifetime, elided: bool) {
         self.report_missing_lifetime_specifiers(vec![missing_lifetime], None);
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn resolve_elided_lifetime(&mut self, anchor_id: NodeId, span: Span) {
         let id = self.r.next_node_id();
         let lt = Lifetime { id, ident: Ident::new(kw::UnderscoreLifetime, span) };
@@ -1586,7 +1585,7 @@ fn resolve_elided_lifetime(&mut self, anchor_id: NodeId, span: Span) {
         self.resolve_anonymous_lifetime(&lt, true);
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn create_fresh_lifetime(&mut self, id: NodeId, ident: Ident, binder: NodeId) -> LifetimeRes {
         debug_assert_eq!(ident.name, kw::UnderscoreLifetime);
         debug!(?ident.span);
@@ -1604,7 +1603,7 @@ fn create_fresh_lifetime(&mut self, id: NodeId, ident: Ident, binder: NodeId) ->
         res
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn resolve_elided_lifetimes_in_path(
         &mut self,
         path_id: NodeId,
@@ -1804,7 +1803,7 @@ fn resolve_elided_lifetimes_in_path(
         }
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn record_lifetime_res(
         &mut self,
         id: NodeId,
@@ -1827,7 +1826,7 @@ fn record_lifetime_res(
         }
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn record_lifetime_param(&mut self, id: NodeId, res: LifetimeRes) {
         if let Some(prev_res) = self.r.lifetimes_res_map.insert(id, res) {
             panic!(
@@ -1838,7 +1837,7 @@ fn record_lifetime_param(&mut self, id: NodeId, res: LifetimeRes) {
     }
 
     /// Perform resolution of a function signature, accounting for lifetime elision.
-    #[tracing::instrument(level = "debug", skip(self, inputs))]
+    #[instrument(level = "debug", skip(self, inputs))]
     fn resolve_fn_signature(
         &mut self,
         fn_id: NodeId,
@@ -3268,11 +3267,9 @@ fn smart_resolve_path_fragment(
         source: PathSource<'ast>,
         finalize: Finalize,
     ) -> PartialRes {
-        tracing::debug!(
+        debug!(
             "smart_resolve_path_fragment(qself={:?}, path={:?}, finalize={:?})",
-            qself,
-            path,
-            finalize,
+            qself, path, finalize,
         );
         let ns = source.namespace();
 
index 9fc637ddbbffae4cc939405cb4702105e8f59585..99d13acbae1b9aa5fd9afecc36f18949557bbc8b 100644 (file)
@@ -33,8 +33,6 @@
 use std::iter;
 use std::ops::Deref;
 
-use tracing::debug;
-
 type Res = def::Res<ast::NodeId>;
 
 /// A field or associated item from self type suggested in case of resolution failure.
index 661aadea94443022dbfc2f1a25368b4d4fcf1fa3..c16eab222f625d8495bcf99e62d8fed42aef951e 100644 (file)
@@ -278,7 +278,7 @@ pub fn provide(providers: &mut ty::query::Providers) {
 /// lifetimes into a single binder.) This requires us to resolve the
 /// *trait definition* of `Sub`; basically just enough lifetime information
 /// to look at the supertraits.
-#[tracing::instrument(level = "debug", skip(tcx))]
+#[instrument(level = "debug", skip(tcx))]
 fn resolve_lifetimes_trait_definition(
     tcx: TyCtxt<'_>,
     local_def_id: LocalDefId,
@@ -289,7 +289,7 @@ fn resolve_lifetimes_trait_definition(
 /// Computes the `ResolveLifetimes` map that contains data for an entire `Item`.
 /// You should not read the result of this query directly, but rather use
 /// `named_region_map`, `is_late_bound_map`, etc.
-#[tracing::instrument(level = "debug", skip(tcx))]
+#[instrument(level = "debug", skip(tcx))]
 fn resolve_lifetimes(tcx: TyCtxt<'_>, local_def_id: LocalDefId) -> ResolveLifetimes {
     convert_named_region_map(do_resolve(tcx, local_def_id, false))
 }
@@ -647,7 +647,7 @@ fn visit_foreign_item(&mut self, item: &'tcx hir::ForeignItem<'tcx>) {
         }
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn visit_ty(&mut self, ty: &'tcx hir::Ty<'tcx>) {
         match ty.kind {
             hir::TyKind::BareFn(ref c) => {
@@ -930,7 +930,7 @@ fn visit_impl_item(&mut self, impl_item: &'tcx hir::ImplItem<'tcx>) {
         }
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn visit_lifetime(&mut self, lifetime_ref: &'tcx hir::Lifetime) {
         match lifetime_ref.name {
             hir::LifetimeName::Static => self.insert_lifetime(lifetime_ref, Region::Static),
@@ -1212,7 +1212,7 @@ fn with<F>(&mut self, wrap_scope: Scope<'_>, f: F)
             scope: &wrap_scope,
             trait_definition_only: self.trait_definition_only,
         };
-        let span = tracing::debug_span!("scope", scope = ?TruncatedScopeDebug(&this.scope));
+        let span = debug_span!("scope", scope = ?TruncatedScopeDebug(&this.scope));
         {
             let _enter = span.enter();
             f(&mut this);
@@ -1287,7 +1287,7 @@ fn visit_early_late<F>(
         self.with(scope, walk);
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn resolve_lifetime_ref(
         &mut self,
         region_def_id: LocalDefId,
@@ -1409,7 +1409,7 @@ fn resolve_lifetime_ref(
         );
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn visit_segment_args(
         &mut self,
         res: Res,
@@ -1659,7 +1659,7 @@ fn supertrait_hrtb_lifetimes(
         }
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn visit_fn_like_elision(
         &mut self,
         inputs: &'tcx [hir::Ty<'tcx>],
@@ -1707,7 +1707,7 @@ fn resolve_object_lifetime_default(&mut self, lifetime_ref: &'tcx hir::Lifetime)
         self.insert_lifetime(lifetime_ref, lifetime.shifted(late_depth));
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self))]
     fn insert_lifetime(&mut self, lifetime_ref: &'tcx hir::Lifetime, def: Region) {
         debug!(
             node = ?self.tcx.hir().node_to_string(lifetime_ref.hir_id),
index 5c33cb694a7655356cef6ca54838423891e8fc04..a15a0c298a9522940402fda5716bbe39fdeb0933 100644 (file)
@@ -58,7 +58,6 @@
 use std::cell::{Cell, RefCell};
 use std::collections::BTreeSet;
 use std::{cmp, fmt, ptr};
-use tracing::debug;
 
 use diagnostics::{ImportSuggestion, LabelSuggestion, Suggestion};
 use imports::{Import, ImportKind, ImportResolver, NameResolution};
@@ -2021,6 +2020,24 @@ fn resolve_main(&mut self) {
         }
         self.main_def = Some(MainDefinition { res, is_import, span });
     }
+
+    // Items that go to reexport table encoded to metadata and visible through it to other crates.
+    fn is_reexport(&self, binding: &NameBinding<'a>) -> Option<def::Res<!>> {
+        // FIXME: Consider changing the binding inserted by `#[macro_export] macro_rules`
+        // into the crate root to actual `NameBindingKind::Import`.
+        if binding.is_import()
+            || matches!(binding.kind, NameBindingKind::Res(_, _is_macro_export @ true))
+        {
+            let res = binding.res().expect_non_local();
+            // Ambiguous imports are treated as errors at this point and are
+            // not exposed to other crates (see #36837 for more details).
+            if res != def::Res::Err && !binding.is_ambiguity() {
+                return Some(res);
+            }
+        }
+
+        return None;
+    }
 }
 
 fn names_to_string(names: &[Symbol]) -> String {
index e2e0e1f5b300ad345ef4bf9837bab4eb49c8b29a..ac6c3663b63762d134e8bb21a6567724a08dd022 100644 (file)
@@ -44,8 +44,6 @@
     RefKind, Relation, RelationKind, SpanData,
 };
 
-use tracing::{debug, error};
-
 #[rustfmt::skip] // https://github.com/rust-lang/rustfmt/issues/5213
 macro_rules! down_cast_data {
     ($id:ident, $kind:ident, $sp:expr) => {
index 619e083d89ad398b1991ecbf49e808e37409321a..16af53385104646aab85c1876aaf6e4f07b3c1ee 100644 (file)
@@ -7,6 +7,9 @@
 #![deny(rustc::untranslatable_diagnostic)]
 #![deny(rustc::diagnostic_outside_of_impl)]
 
+#[macro_use]
+extern crate tracing;
+
 mod dump_visitor;
 mod dumper;
 #[macro_use]
@@ -49,8 +52,6 @@
     RefKind, Relation, RelationKind, SpanData,
 };
 
-use tracing::{debug, error, info};
-
 pub struct SaveContext<'tcx> {
     tcx: TyCtxt<'tcx>,
     maybe_typeck_results: Option<&'tcx ty::TypeckResults<'tcx>>,
index 2a4a772f61085dfe13dfba1a48d4944cd39e0f56..2336d99363fd3d8ed639b61d96d9891dcb293439 100644 (file)
@@ -10,7 +10,6 @@
 use std::borrow::Cow;
 use std::fmt::{self};
 use std::sync::{Arc, Mutex};
-use tracing::debug;
 
 #[derive(Copy, Clone, Debug, PartialEq, PartialOrd)]
 pub enum CguReuse {
index 162fc9aa0a6ea622e3202fb47a2fe2f967777ebe..d4d29288f7f28147c647886c1672674adfbcd605 100644 (file)
@@ -12,8 +12,8 @@
 
 use rustc_data_structures::stable_hasher::ToStableHashKey;
 use rustc_target::abi::{Align, TargetDataLayout};
-use rustc_target::spec::{LinkerFlavor, SplitDebuginfo, Target, TargetTriple, TargetWarnings};
-use rustc_target::spec::{PanicStrategy, SanitizerSet, TARGETS};
+use rustc_target::spec::{PanicStrategy, SanitizerSet, SplitDebuginfo};
+use rustc_target::spec::{Target, TargetTriple, TargetWarnings, TARGETS};
 
 use crate::parse::{CrateCheckConfig, CrateConfig};
 use rustc_feature::UnstableFeatures;
@@ -2379,16 +2379,6 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
         }
     }
 
-    if cg.linker_flavor == Some(LinkerFlavor::L4Bender)
-        && !nightly_options::is_unstable_enabled(matches)
-    {
-        early_error(
-            error_format,
-            "`l4-bender` linker flavor is unstable, `-Z unstable-options` \
-             flag must also be passed to explicitly use it",
-        );
-    }
-
     let prints = collect_print_requests(&mut cg, &mut unstable_opts, matches, error_format);
 
     let cg = cg;
@@ -2530,7 +2520,7 @@ fn parse_pretty(unstable_opts: &UnstableOptions, efmt: ErrorOutputType) -> Optio
             ),
         ),
     };
-    tracing::debug!("got unpretty option: {first:?}");
+    debug!("got unpretty option: {first:?}");
     Some(first)
 }
 
index c973e3140cef97b596545cdfb3d536fa6bd6eef1..e8edb38f5038ea1f4c55d949a5dc3558050efbbe 100644 (file)
@@ -7,7 +7,6 @@
 
 use crate::search_paths::{PathKind, SearchPath};
 use rustc_fs_util::fix_windows_verbatim_for_gcc;
-use tracing::debug;
 
 #[derive(Copy, Clone)]
 pub enum FileMatch {
index 429475c573c8e8d01202e46d7ed7a1c8957ffd97..02d5d33c8d5ba24727b27fec54a3a42bbd511fe4 100644 (file)
@@ -14,6 +14,9 @@
 extern crate rustc_macros;
 pub mod errors;
 
+#[macro_use]
+extern crate tracing;
+
 pub mod cgu_reuse_tracker;
 pub mod utils;
 pub use lint::{declare_lint, declare_lint_pass, declare_tool_lint, impl_lint_pass};
index 46bba02537dc7b830f20d03450c307b964c0c301..9f07394b61ab8fc0808ee5397d4bfd7e20b5deec 100644 (file)
@@ -5,7 +5,7 @@
 use crate::search_paths::SearchPath;
 use crate::utils::NativeLib;
 use rustc_errors::LanguageIdentifier;
-use rustc_target::spec::{CodeModel, LinkerFlavor, MergeFunctions, PanicStrategy, SanitizerSet};
+use rustc_target::spec::{CodeModel, LinkerFlavorCli, MergeFunctions, PanicStrategy, SanitizerSet};
 use rustc_target::spec::{
     RelocModel, RelroLevel, SplitDebuginfo, StackProtector, TargetTriple, TlsModel,
 };
@@ -382,7 +382,7 @@ mod desc {
         "either a boolean (`yes`, `no`, `on`, `off`, etc), `checks`, or `nochecks`";
     pub const parse_cfprotection: &str = "`none`|`no`|`n` (default), `branch`, `return`, or `full`|`yes`|`y` (equivalent to `branch` and `return`)";
     pub const parse_strip: &str = "either `none`, `debuginfo`, or `symbols`";
-    pub const parse_linker_flavor: &str = ::rustc_target::spec::LinkerFlavor::one_of();
+    pub const parse_linker_flavor: &str = ::rustc_target::spec::LinkerFlavorCli::one_of();
     pub const parse_optimization_fuel: &str = "crate=integer";
     pub const parse_mir_spanview: &str = "`statement` (default), `terminator`, or `block`";
     pub const parse_instrument_coverage: &str =
@@ -763,8 +763,8 @@ pub(crate) fn parse_cfprotection(slot: &mut CFProtection, v: Option<&str>) -> bo
         true
     }
 
-    pub(crate) fn parse_linker_flavor(slot: &mut Option<LinkerFlavor>, v: Option<&str>) -> bool {
-        match v.and_then(LinkerFlavor::from_str) {
+    pub(crate) fn parse_linker_flavor(slot: &mut Option<LinkerFlavorCli>, v: Option<&str>) -> bool {
+        match v.and_then(LinkerFlavorCli::from_str) {
             Some(lf) => *slot = Some(lf),
             _ => return false,
         }
@@ -1139,7 +1139,7 @@ pub(crate) fn parse_proc_macro_execution_strategy(
         on C toolchain installed in the system"),
     linker: Option<PathBuf> = (None, parse_opt_pathbuf, [UNTRACKED],
         "system linker to link outputs with"),
-    linker_flavor: Option<LinkerFlavor> = (None, parse_linker_flavor, [UNTRACKED],
+    linker_flavor: Option<LinkerFlavorCli> = (None, parse_linker_flavor, [UNTRACKED],
         "linker flavor"),
     linker_plugin_lto: LinkerPluginLto = (LinkerPluginLto::Disabled,
         parse_linker_plugin_lto, [TRACKED],
index e169d3c7cfb7c2553d583f7686c30a9e73383798..e8ddb4ed17a3e6da5af4e922736fa11dbe4c029f 100644 (file)
@@ -41,7 +41,6 @@
 use rustc_serialize::{Decodable, Decoder, Encodable, Encoder};
 use std::fmt;
 use std::hash::Hash;
-use tracing::*;
 
 /// A `SyntaxContext` represents a chain of pairs `(ExpnId, Transparency)` named "marks".
 #[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
index 860af7fe93a077959f1377c70d642af5e8709a9e..34e2e92bdfce1efa6fc203f15245ac5d76104a04 100644 (file)
@@ -76,8 +76,6 @@
 use sha1::Sha1;
 use sha2::Sha256;
 
-use tracing::debug;
-
 #[cfg(test)]
 mod tests;
 
index a32cabab4c407281a0190e9dba473a863086b8bf..4d94c92d3f2b182ce8521d059210527bf784d62d 100644 (file)
@@ -23,7 +23,6 @@
 
 use std::fs;
 use std::io;
-use tracing::debug;
 
 #[cfg(test)]
 mod tests;
@@ -1060,13 +1059,13 @@ pub fn map_prefix(&self, path: PathBuf) -> (PathBuf, bool) {
 
         return remap_path_prefix(&self.mapping, path);
 
-        #[instrument(level = "debug", skip(mapping))]
+        #[instrument(level = "debug", skip(mapping), ret)]
         fn remap_path_prefix(mapping: &[(PathBuf, PathBuf)], path: PathBuf) -> (PathBuf, bool) {
             // NOTE: We are iterating over the mapping entries from last to first
             //       because entries specified later on the command line should
             //       take precedence.
             for &(ref from, ref to) in mapping.iter().rev() {
-                debug!("Trying to apply {:?} => {:?}", from, to);
+                debug!("Trying to apply {from:?} => {to:?}");
 
                 if let Ok(rest) = path.strip_prefix(from) {
                     let remapped = if rest.as_os_str().is_empty() {
@@ -1080,15 +1079,15 @@ fn remap_path_prefix(mapping: &[(PathBuf, PathBuf)], path: PathBuf) -> (PathBuf,
                     } else {
                         to.join(rest)
                     };
-                    debug!("Match - remapped {:?} => {:?}", path, remapped);
+                    debug!("Match - remapped");
 
                     return (remapped, true);
                 } else {
-                    debug!("No match - prefix {:?} does not match {:?}", from, path);
+                    debug!("No match - prefix {from:?} does not match");
                 }
             }
 
-            debug!("Path {:?} was not remapped", path);
+            debug!("not remapped");
             (path, false)
         }
     }
index 6eca7dc52b26ac7d47d5fb83c6676ea9665a7b93..be954334313494da2be6a62ebc78faba2d63cec1 100644 (file)
         LinkedList,
         LintPass,
         Mutex,
+        MutexGuard,
         N,
         NonZeroI128,
         NonZeroI16,
         Rust,
         RustcDecodable,
         RustcEncodable,
+        RwLockReadGuard,
+        RwLockWriteGuard,
         Send,
         SeqCst,
         SessionDiagnostic,
         rust_eh_unregister_frames,
         rust_oom,
         rustc,
+        rustc_access_level,
         rustc_allocator,
         rustc_allocator_nounwind,
         rustc_allocator_zeroed,
index 9241fd82c745fde4a857c5598faaba111c2edd34..46c5fe78ffbf65697085e5bcd7874ed70e50595a 100644 (file)
@@ -6,8 +6,6 @@
 use rustc_middle::ty::{self, Instance, Ty, TyCtxt, TypeVisitable};
 use rustc_middle::util::common::record_time;
 
-use tracing::debug;
-
 use std::fmt::{self, Write};
 use std::mem::{self, discriminant};
 
index 0c6489acb34835085ceb32cd02f2223c5d05f8cf..62f44a48032efd93301b704bf538bdea53813c8f 100644 (file)
@@ -97,6 +97,9 @@
 #[macro_use]
 extern crate rustc_middle;
 
+#[macro_use]
+extern crate tracing;
+
 use rustc_hir::def::DefKind;
 use rustc_hir::def_id::{CrateNum, LOCAL_CRATE};
 use rustc_middle::middle::codegen_fn_attrs::CodegenFnAttrFlags;
 use rustc_middle::ty::{self, Instance, TyCtxt};
 use rustc_session::config::SymbolManglingVersion;
 
-use tracing::debug;
-
 mod legacy;
 mod v0;
 
index b4cf2c5ee229496f71f65ba2eebb2af13b208913..f492c3451a4182dcb18dbf991980f5089cd27a39 100644 (file)
@@ -2,6 +2,6 @@
 
 pub fn target() -> Target {
     let mut target = wasm32_unknown_emscripten::target();
-    target.add_post_link_args(LinkerFlavor::Em, &["-sWASM=0", "--memory-init-file", "0"]);
+    target.add_post_link_args(LinkerFlavor::EmCc, &["-sWASM=0", "--memory-init-file", "0"]);
     target
 }
index 3c4da6f883d9dab420e3520d582ff68ff12a1ede..baf36587147a690d4ecbeba0066468e4f5af6c2f 100644 (file)
@@ -5,7 +5,7 @@ pub fn opts(endian: Endian) -> TargetOptions {
     TargetOptions {
         allow_asm: true,
         endian,
-        linker_flavor: LinkerFlavor::BpfLinker,
+        linker_flavor: LinkerFlavor::Bpf,
         atomic_cas: false,
         dynamic_linking: true,
         no_builtins: true,
index cab4dd333d43dbc5edb34d0f634616d7af6597bb..b7bc1072bf3280c0b496ce057c09dabef754f47f 100644 (file)
@@ -4,7 +4,7 @@ pub fn opts() -> TargetOptions {
     TargetOptions {
         os: "l4re".into(),
         env: "uclibc".into(),
-        linker_flavor: LinkerFlavor::L4Bender,
+        linker_flavor: LinkerFlavor::Ld,
         panic_strategy: PanicStrategy::Abort,
         linker: Some("l4-bender".into()),
         linker_is_gnu: false,
index 2459b0280cd66df3e2f5ca94a8193f4b9364f7f1..47eb5fc6a1dcbc6d5beac04d65a6fae9d2709b49 100644 (file)
 
 #[derive(Clone, Copy, Debug, Eq, Ord, PartialEq, PartialOrd)]
 pub enum LinkerFlavor {
-    Em,
     Gcc,
-    L4Bender,
     Ld,
+    Lld(LldFlavor),
     Msvc,
+    EmCc,
+    Bpf,
+    Ptx,
+}
+
+#[derive(Clone, Copy, Debug, Eq, Ord, PartialEq, PartialOrd)]
+pub enum LinkerFlavorCli {
+    Gcc,
+    Ld,
     Lld(LldFlavor),
-    PtxLinker,
+    Msvc,
+    Em,
     BpfLinker,
+    PtxLinker,
 }
 
 #[derive(Clone, Copy, Debug, Eq, Ord, PartialEq, PartialOrd)]
@@ -137,19 +147,40 @@ fn to_json(&self) -> Json {
     }
 }
 
-impl ToJson for LinkerFlavor {
-    fn to_json(&self) -> Json {
-        self.desc().to_json()
+impl LinkerFlavor {
+    pub fn from_cli(cli: LinkerFlavorCli) -> LinkerFlavor {
+        match cli {
+            LinkerFlavorCli::Gcc => LinkerFlavor::Gcc,
+            LinkerFlavorCli::Ld => LinkerFlavor::Ld,
+            LinkerFlavorCli::Lld(lld_flavor) => LinkerFlavor::Lld(lld_flavor),
+            LinkerFlavorCli::Msvc => LinkerFlavor::Msvc,
+            LinkerFlavorCli::Em => LinkerFlavor::EmCc,
+            LinkerFlavorCli::BpfLinker => LinkerFlavor::Bpf,
+            LinkerFlavorCli::PtxLinker => LinkerFlavor::Ptx,
+        }
+    }
+
+    fn to_cli(self) -> LinkerFlavorCli {
+        match self {
+            LinkerFlavor::Gcc => LinkerFlavorCli::Gcc,
+            LinkerFlavor::Ld => LinkerFlavorCli::Ld,
+            LinkerFlavor::Lld(lld_flavor) => LinkerFlavorCli::Lld(lld_flavor),
+            LinkerFlavor::Msvc => LinkerFlavorCli::Msvc,
+            LinkerFlavor::EmCc => LinkerFlavorCli::Em,
+            LinkerFlavor::Bpf => LinkerFlavorCli::BpfLinker,
+            LinkerFlavor::Ptx => LinkerFlavorCli::PtxLinker,
+        }
     }
 }
-macro_rules! flavor_mappings {
-    ($((($($flavor:tt)*), $string:expr),)*) => (
-        impl LinkerFlavor {
+
+macro_rules! linker_flavor_cli_impls {
+    ($(($($flavor:tt)*) $string:literal)*) => (
+        impl LinkerFlavorCli {
             pub const fn one_of() -> &'static str {
                 concat!("one of: ", $($string, " ",)*)
             }
 
-            pub fn from_str(s: &str) -> Option<Self> {
+            pub fn from_str(s: &str) -> Option<LinkerFlavorCli> {
                 Some(match s {
                     $($string => $($flavor)*,)*
                     _ => return None,
@@ -165,18 +196,23 @@ pub fn desc(&self) -> &str {
     )
 }
 
-flavor_mappings! {
-    ((LinkerFlavor::Em), "em"),
-    ((LinkerFlavor::Gcc), "gcc"),
-    ((LinkerFlavor::L4Bender), "l4-bender"),
-    ((LinkerFlavor::Ld), "ld"),
-    ((LinkerFlavor::Msvc), "msvc"),
-    ((LinkerFlavor::PtxLinker), "ptx-linker"),
-    ((LinkerFlavor::BpfLinker), "bpf-linker"),
-    ((LinkerFlavor::Lld(LldFlavor::Wasm)), "wasm-ld"),
-    ((LinkerFlavor::Lld(LldFlavor::Ld64)), "ld64.lld"),
-    ((LinkerFlavor::Lld(LldFlavor::Ld)), "ld.lld"),
-    ((LinkerFlavor::Lld(LldFlavor::Link)), "lld-link"),
+linker_flavor_cli_impls! {
+    (LinkerFlavorCli::Gcc) "gcc"
+    (LinkerFlavorCli::Ld) "ld"
+    (LinkerFlavorCli::Lld(LldFlavor::Ld)) "ld.lld"
+    (LinkerFlavorCli::Lld(LldFlavor::Ld64)) "ld64.lld"
+    (LinkerFlavorCli::Lld(LldFlavor::Link)) "lld-link"
+    (LinkerFlavorCli::Lld(LldFlavor::Wasm)) "wasm-ld"
+    (LinkerFlavorCli::Msvc) "msvc"
+    (LinkerFlavorCli::Em) "em"
+    (LinkerFlavorCli::BpfLinker) "bpf-linker"
+    (LinkerFlavorCli::PtxLinker) "ptx-linker"
+}
+
+impl ToJson for LinkerFlavorCli {
+    fn to_json(&self) -> Json {
+        self.desc().to_json()
+    }
 }
 
 #[derive(Clone, Copy, Debug, PartialEq, Hash, Encodable, Decodable, HashStable_Generic)]
@@ -467,6 +503,7 @@ fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
 }
 
 pub type LinkArgs = BTreeMap<LinkerFlavor, Vec<StaticCow<str>>>;
+pub type LinkArgsCli = BTreeMap<LinkerFlavorCli, Vec<StaticCow<str>>>;
 
 /// Which kind of debuginfo does the target use?
 ///
@@ -1210,19 +1247,21 @@ pub struct TargetOptions {
     pub abi: StaticCow<str>,
     /// Vendor name to use for conditional compilation (`target_vendor`). Defaults to "unknown".
     pub vendor: StaticCow<str>,
-    /// Default linker flavor used if `-C linker-flavor` or `-C linker` are not passed
-    /// on the command line. Defaults to `LinkerFlavor::Gcc`.
-    pub linker_flavor: LinkerFlavor,
 
     /// Linker to invoke
     pub linker: Option<StaticCow<str>>,
-
+    /// Default linker flavor used if `-C linker-flavor` or `-C linker` are not passed
+    /// on the command line. Defaults to `LinkerFlavor::Gcc`.
+    pub linker_flavor: LinkerFlavor,
+    linker_flavor_json: LinkerFlavorCli,
     /// LLD flavor used if `lld` (or `rust-lld`) is specified as a linker
     /// without clarifying its flavor in any way.
+    /// FIXME: Merge this into `LinkerFlavor`.
     pub lld_flavor: LldFlavor,
+    /// Whether the linker support GNU-like arguments such as -O. Defaults to true.
+    /// FIXME: Merge this into `LinkerFlavor`.
+    pub linker_is_gnu: bool,
 
-    /// Linker arguments that are passed *before* any user-defined libraries.
-    pub pre_link_args: LinkArgs,
     /// Objects to link before and after all other object code.
     pub pre_link_objects: CrtObjects,
     pub post_link_objects: CrtObjects,
@@ -1231,24 +1270,31 @@ pub struct TargetOptions {
     pub post_link_objects_self_contained: CrtObjects,
     pub link_self_contained: LinkSelfContainedDefault,
 
+    /// Linker arguments that are passed *before* any user-defined libraries.
+    pub pre_link_args: LinkArgs,
+    pre_link_args_json: LinkArgsCli,
     /// Linker arguments that are unconditionally passed after any
     /// user-defined but before post-link objects. Standard platform
     /// libraries that should be always be linked to, usually go here.
     pub late_link_args: LinkArgs,
+    late_link_args_json: LinkArgsCli,
     /// Linker arguments used in addition to `late_link_args` if at least one
     /// Rust dependency is dynamically linked.
     pub late_link_args_dynamic: LinkArgs,
+    late_link_args_dynamic_json: LinkArgsCli,
     /// Linker arguments used in addition to `late_link_args` if all Rust
     /// dependencies are statically linked.
     pub late_link_args_static: LinkArgs,
+    late_link_args_static_json: LinkArgsCli,
     /// Linker arguments that are unconditionally passed *after* any
     /// user-defined libraries.
     pub post_link_args: LinkArgs,
+    post_link_args_json: LinkArgsCli,
+
     /// Optional link script applied to `dylib` and `executable` crate types.
     /// This is a string containing the script, not a path. Can only be applied
     /// to linkers where `linker_is_gnu` is true.
     pub link_script: Option<StaticCow<str>>,
-
     /// Environment variables to be set for the linker invocation.
     pub link_env: StaticCow<[(StaticCow<str>, StaticCow<str>)]>,
     /// Environment variables to be removed for the linker invocation.
@@ -1333,8 +1379,6 @@ pub struct TargetOptions {
     /// Default supported version of DWARF on this platform.
     /// Useful because some platforms (osx, bsd) only want up to DWARF2.
     pub default_dwarf_version: u32,
-    /// Whether the linker support GNU-like arguments such as -O. Defaults to true.
-    pub linker_is_gnu: bool,
     /// The MinGW toolchain has a known issue that prevents it from correctly
     /// handling COFF object files with more than 2<sup>15</sup> sections. Since each weak
     /// symbol needs its own COMDAT section, weak linkage implies a large
@@ -1532,11 +1576,7 @@ fn add_link_args(link_args: &mut LinkArgs, flavor: LinkerFlavor, args: &[&'stati
         LinkerFlavor::Lld(lld_flavor) => {
             panic!("add_link_args: use non-LLD flavor for {:?}", lld_flavor)
         }
-        LinkerFlavor::Gcc
-        | LinkerFlavor::Em
-        | LinkerFlavor::L4Bender
-        | LinkerFlavor::BpfLinker
-        | LinkerFlavor::PtxLinker => {}
+        LinkerFlavor::Gcc | LinkerFlavor::EmCc | LinkerFlavor::Bpf | LinkerFlavor::Ptx => {}
     }
 }
 
@@ -1554,6 +1594,36 @@ fn add_pre_link_args(&mut self, flavor: LinkerFlavor, args: &[&'static str]) {
     fn add_post_link_args(&mut self, flavor: LinkerFlavor, args: &[&'static str]) {
         add_link_args(&mut self.post_link_args, flavor, args);
     }
+
+    fn update_from_cli(&mut self) {
+        self.linker_flavor = LinkerFlavor::from_cli(self.linker_flavor_json);
+        for (args, args_json) in [
+            (&mut self.pre_link_args, &self.pre_link_args_json),
+            (&mut self.late_link_args, &self.late_link_args_json),
+            (&mut self.late_link_args_dynamic, &self.late_link_args_dynamic_json),
+            (&mut self.late_link_args_static, &self.late_link_args_static_json),
+            (&mut self.post_link_args, &self.post_link_args_json),
+        ] {
+            *args = args_json
+                .iter()
+                .map(|(flavor, args)| (LinkerFlavor::from_cli(*flavor), args.clone()))
+                .collect();
+        }
+    }
+
+    fn update_to_cli(&mut self) {
+        self.linker_flavor_json = self.linker_flavor.to_cli();
+        for (args, args_json) in [
+            (&self.pre_link_args, &mut self.pre_link_args_json),
+            (&self.late_link_args, &mut self.late_link_args_json),
+            (&self.late_link_args_dynamic, &mut self.late_link_args_dynamic_json),
+            (&self.late_link_args_static, &mut self.late_link_args_static_json),
+            (&self.post_link_args, &mut self.post_link_args_json),
+        ] {
+            *args_json =
+                args.iter().map(|(flavor, args)| (flavor.to_cli(), args.clone())).collect();
+        }
+    }
 }
 
 impl Default for TargetOptions {
@@ -1568,11 +1638,11 @@ fn default() -> TargetOptions {
             env: "".into(),
             abi: "".into(),
             vendor: "unknown".into(),
-            linker_flavor: LinkerFlavor::Gcc,
             linker: option_env!("CFG_DEFAULT_LINKER").map(|s| s.into()),
+            linker_flavor: LinkerFlavor::Gcc,
+            linker_flavor_json: LinkerFlavorCli::Gcc,
             lld_flavor: LldFlavor::Ld,
-            pre_link_args: LinkArgs::new(),
-            post_link_args: LinkArgs::new(),
+            linker_is_gnu: true,
             link_script: None,
             asm_args: cvs![],
             cpu: "generic".into(),
@@ -1599,7 +1669,6 @@ fn default() -> TargetOptions {
             is_like_msvc: false,
             is_like_wasm: false,
             default_dwarf_version: 4,
-            linker_is_gnu: true,
             allows_weak_linkage: true,
             has_rpath: false,
             no_default_libraries: true,
@@ -1612,9 +1681,16 @@ fn default() -> TargetOptions {
             pre_link_objects_self_contained: Default::default(),
             post_link_objects_self_contained: Default::default(),
             link_self_contained: LinkSelfContainedDefault::False,
+            pre_link_args: LinkArgs::new(),
+            pre_link_args_json: LinkArgsCli::new(),
             late_link_args: LinkArgs::new(),
+            late_link_args_json: LinkArgsCli::new(),
             late_link_args_dynamic: LinkArgs::new(),
+            late_link_args_dynamic_json: LinkArgsCli::new(),
             late_link_args_static: LinkArgs::new(),
+            late_link_args_static_json: LinkArgsCli::new(),
+            post_link_args: LinkArgs::new(),
+            post_link_args_json: LinkArgsCli::new(),
             link_env: cvs![],
             link_env_remove: cvs![],
             archive_format: "gnu".into(),
@@ -2019,13 +2095,13 @@ macro_rules! key {
                     Some(Ok(()))
                 })).unwrap_or(Ok(()))
             } );
-            ($key_name:ident, LinkerFlavor) => ( {
-                let name = (stringify!($key_name)).replace("_", "-");
-                obj.remove(&name).and_then(|o| o.as_str().and_then(|s| {
-                    match LinkerFlavor::from_str(s) {
+            ($key_name:ident = $json_name:expr, LinkerFlavor) => ( {
+                let name = $json_name;
+                obj.remove(name).and_then(|o| o.as_str().and_then(|s| {
+                    match LinkerFlavorCli::from_str(s) {
                         Some(linker_flavor) => base.$key_name = linker_flavor,
                         _ => return Some(Err(format!("'{}' is not a valid value for linker-flavor. \
-                                                      Use {}", s, LinkerFlavor::one_of()))),
+                                                      Use {}", s, LinkerFlavorCli::one_of()))),
                     }
                     Some(Ok(()))
                 })).unwrap_or(Ok(()))
@@ -2106,14 +2182,14 @@ macro_rules! key {
                     base.$key_name = args;
                 }
             } );
-            ($key_name:ident, link_args) => ( {
-                let name = (stringify!($key_name)).replace("_", "-");
-                if let Some(val) = obj.remove(&name) {
+            ($key_name:ident = $json_name:expr, link_args) => ( {
+                let name = $json_name;
+                if let Some(val) = obj.remove(name) {
                     let obj = val.as_object().ok_or_else(|| format!("{}: expected a \
                         JSON object with fields per linker-flavor.", name))?;
-                    let mut args = LinkArgs::new();
+                    let mut args = LinkArgsCli::new();
                     for (k, v) in obj {
-                        let flavor = LinkerFlavor::from_str(&k).ok_or_else(|| {
+                        let flavor = LinkerFlavorCli::from_str(&k).ok_or_else(|| {
                             format!("{}: '{}' is not a valid value for linker-flavor. \
                                      Use 'em', 'gcc', 'ld' or 'msvc'", name, k)
                         })?;
@@ -2199,19 +2275,20 @@ macro_rules! key {
         key!(env);
         key!(abi);
         key!(vendor);
-        key!(linker_flavor, LinkerFlavor)?;
         key!(linker, optional);
+        key!(linker_flavor_json = "linker-flavor", LinkerFlavor)?;
         key!(lld_flavor, LldFlavor)?;
+        key!(linker_is_gnu, bool);
         key!(pre_link_objects = "pre-link-objects", link_objects);
         key!(post_link_objects = "post-link-objects", link_objects);
         key!(pre_link_objects_self_contained = "pre-link-objects-fallback", link_objects);
         key!(post_link_objects_self_contained = "post-link-objects-fallback", link_objects);
         key!(link_self_contained = "crt-objects-fallback", link_self_contained)?;
-        key!(pre_link_args, link_args);
-        key!(late_link_args, link_args);
-        key!(late_link_args_dynamic, link_args);
-        key!(late_link_args_static, link_args);
-        key!(post_link_args, link_args);
+        key!(pre_link_args_json = "pre-link-args", link_args);
+        key!(late_link_args_json = "late-link-args", link_args);
+        key!(late_link_args_dynamic_json = "late-link-args-dynamic", link_args);
+        key!(late_link_args_static_json = "late-link-args-static", link_args);
+        key!(post_link_args_json = "post-link-args", link_args);
         key!(link_script, optional);
         key!(link_env, env);
         key!(link_env_remove, list);
@@ -2239,7 +2316,6 @@ macro_rules! key {
         key!(is_like_msvc, bool);
         key!(is_like_wasm, bool);
         key!(default_dwarf_version, u32);
-        key!(linker_is_gnu, bool);
         key!(allows_weak_linkage, bool);
         key!(has_rpath, bool);
         key!(no_default_libraries, bool);
@@ -2296,6 +2372,8 @@ macro_rules! key {
             // This can cause unfortunate ICEs later down the line.
             return Err("may not set is_builtin for targets not built-in".into());
         }
+        base.update_from_cli();
+
         // Each field should have been read using `Json::remove` so any keys remaining are unused.
         let remaining_keys = obj.keys();
         Ok((
@@ -2387,42 +2465,44 @@ impl ToJson for Target {
     fn to_json(&self) -> Json {
         let mut d = serde_json::Map::new();
         let default: TargetOptions = Default::default();
+        let mut target = self.clone();
+        target.update_to_cli();
 
         macro_rules! target_val {
             ($attr:ident) => {{
                 let name = (stringify!($attr)).replace("_", "-");
-                d.insert(name, self.$attr.to_json());
+                d.insert(name, target.$attr.to_json());
             }};
         }
 
         macro_rules! target_option_val {
             ($attr:ident) => {{
                 let name = (stringify!($attr)).replace("_", "-");
-                if default.$attr != self.$attr {
-                    d.insert(name, self.$attr.to_json());
+                if default.$attr != target.$attr {
+                    d.insert(name, target.$attr.to_json());
                 }
             }};
-            ($attr:ident, $key_name:expr) => {{
-                let name = $key_name;
-                if default.$attr != self.$attr {
-                    d.insert(name.into(), self.$attr.to_json());
+            ($attr:ident, $json_name:expr) => {{
+                let name = $json_name;
+                if default.$attr != target.$attr {
+                    d.insert(name.into(), target.$attr.to_json());
                 }
             }};
-            (link_args - $attr:ident) => {{
-                let name = (stringify!($attr)).replace("_", "-");
-                if default.$attr != self.$attr {
-                    let obj = self
+            (link_args - $attr:ident, $json_name:expr) => {{
+                let name = $json_name;
+                if default.$attr != target.$attr {
+                    let obj = target
                         .$attr
                         .iter()
                         .map(|(k, v)| (k.desc().to_string(), v.clone()))
                         .collect::<BTreeMap<_, _>>();
-                    d.insert(name, obj.to_json());
+                    d.insert(name.to_string(), obj.to_json());
                 }
             }};
             (env - $attr:ident) => {{
                 let name = (stringify!($attr)).replace("_", "-");
-                if default.$attr != self.$attr {
-                    let obj = self
+                if default.$attr != target.$attr {
+                    let obj = target
                         .$attr
                         .iter()
                         .map(|&(ref k, ref v)| format!("{k}={v}"))
@@ -2444,19 +2524,20 @@ macro_rules! target_option_val {
         target_option_val!(env);
         target_option_val!(abi);
         target_option_val!(vendor);
-        target_option_val!(linker_flavor);
         target_option_val!(linker);
+        target_option_val!(linker_flavor_json, "linker-flavor");
         target_option_val!(lld_flavor);
+        target_option_val!(linker_is_gnu);
         target_option_val!(pre_link_objects);
         target_option_val!(post_link_objects);
         target_option_val!(pre_link_objects_self_contained, "pre-link-objects-fallback");
         target_option_val!(post_link_objects_self_contained, "post-link-objects-fallback");
         target_option_val!(link_self_contained, "crt-objects-fallback");
-        target_option_val!(link_args - pre_link_args);
-        target_option_val!(link_args - late_link_args);
-        target_option_val!(link_args - late_link_args_dynamic);
-        target_option_val!(link_args - late_link_args_static);
-        target_option_val!(link_args - post_link_args);
+        target_option_val!(link_args - pre_link_args_json, "pre-link-args");
+        target_option_val!(link_args - late_link_args_json, "late-link-args");
+        target_option_val!(link_args - late_link_args_dynamic_json, "late-link-args-dynamic");
+        target_option_val!(link_args - late_link_args_static_json, "late-link-args-static");
+        target_option_val!(link_args - post_link_args_json, "post-link-args");
         target_option_val!(link_script);
         target_option_val!(env - link_env);
         target_option_val!(link_env_remove);
@@ -2485,7 +2566,6 @@ macro_rules! target_option_val {
         target_option_val!(is_like_msvc);
         target_option_val!(is_like_wasm);
         target_option_val!(default_dwarf_version);
-        target_option_val!(linker_is_gnu);
         target_option_val!(allows_weak_linkage);
         target_option_val!(has_rpath);
         target_option_val!(no_default_libraries);
index 1c5b68001b957b00cc0b927c014022f3b1c25c95..6ab3a8b7eb5a06f688bc5505f1f0ddb9e6301bb8 100644 (file)
@@ -10,7 +10,7 @@ pub fn target() -> Target {
         options: TargetOptions {
             os: "cuda".into(),
             vendor: "nvidia".into(),
-            linker_flavor: LinkerFlavor::PtxLinker,
+            linker_flavor: LinkerFlavor::Ptx,
             // The linker can be installed from `crates.io`.
             linker: Some("rust-ptx-linker".into()),
             linker_is_gnu: false,
index 4a53b9c173d1ff43b492e886e3313ab410c23530..d03f959076de0c0ab5fe7691c1f70daf5756d2ab 100644 (file)
@@ -2,9 +2,11 @@
 use std::assert_matches::assert_matches;
 
 // Test target self-consistency and JSON encoding/decoding roundtrip.
-pub(super) fn test_target(target: Target, triple: &str) {
+pub(super) fn test_target(mut target: Target, triple: &str) {
+    let recycled_target = Target::from_json(target.to_json()).map(|(j, _)| j);
+    target.update_to_cli();
     target.check_consistency(triple);
-    assert_eq!(Target::from_json(target.to_json()).map(|(j, _)| j), Ok(target));
+    assert_eq!(recycled_target, Ok(target));
 }
 
 impl Target {
@@ -22,10 +24,9 @@ fn check_consistency(&self, triple: &str) {
         assert_eq!(self.is_like_osx, matches!(self.lld_flavor, LldFlavor::Ld64));
         assert_eq!(self.is_like_msvc, matches!(self.lld_flavor, LldFlavor::Link));
         assert_eq!(self.is_like_wasm, matches!(self.lld_flavor, LldFlavor::Wasm));
-        assert_eq!(self.os == "l4re", matches!(self.linker_flavor, LinkerFlavor::L4Bender));
-        assert_eq!(self.os == "emscripten", matches!(self.linker_flavor, LinkerFlavor::Em));
-        assert_eq!(self.arch == "bpf", matches!(self.linker_flavor, LinkerFlavor::BpfLinker));
-        assert_eq!(self.arch == "nvptx64", matches!(self.linker_flavor, LinkerFlavor::PtxLinker));
+        assert_eq!(self.os == "emscripten", matches!(self.linker_flavor, LinkerFlavor::EmCc));
+        assert_eq!(self.arch == "bpf", matches!(self.linker_flavor, LinkerFlavor::Bpf));
+        assert_eq!(self.arch == "nvptx64", matches!(self.linker_flavor, LinkerFlavor::Ptx));
 
         for args in [
             &self.pre_link_args,
@@ -65,17 +66,14 @@ fn check_consistency(&self, triple: &str) {
                             LinkerFlavor::Lld(LldFlavor::Wasm) | LinkerFlavor::Gcc
                         )
                     }
-                    (LinkerFlavor::L4Bender, LldFlavor::Ld) => {
-                        assert_matches!(flavor, LinkerFlavor::L4Bender)
+                    (LinkerFlavor::EmCc, LldFlavor::Wasm) => {
+                        assert_matches!(flavor, LinkerFlavor::EmCc)
                     }
-                    (LinkerFlavor::Em, LldFlavor::Wasm) => {
-                        assert_matches!(flavor, LinkerFlavor::Em)
+                    (LinkerFlavor::Bpf, LldFlavor::Ld) => {
+                        assert_matches!(flavor, LinkerFlavor::Bpf)
                     }
-                    (LinkerFlavor::BpfLinker, LldFlavor::Ld) => {
-                        assert_matches!(flavor, LinkerFlavor::BpfLinker)
-                    }
-                    (LinkerFlavor::PtxLinker, LldFlavor::Ld) => {
-                        assert_matches!(flavor, LinkerFlavor::PtxLinker)
+                    (LinkerFlavor::Ptx, LldFlavor::Ld) => {
+                        assert_matches!(flavor, LinkerFlavor::Ptx)
                     }
                     flavors => unreachable!("unexpected flavor combination: {:?}", flavors),
                 }
index c7e7d22108656ffab3264bc5263cb0a2575e9f12..6f77ef98c015df8c38dc5629d23fa5c496982be8 100644 (file)
@@ -5,13 +5,13 @@ pub fn target() -> Target {
     // Reset flags for non-Em flavors back to empty to satisfy sanity checking tests.
     let pre_link_args = LinkArgs::new();
     let post_link_args = TargetOptions::link_args(
-        LinkerFlavor::Em,
+        LinkerFlavor::EmCc,
         &["-sABORTING_MALLOC=0", "-Wl,--fatal-warnings"],
     );
 
     let opts = TargetOptions {
         os: "emscripten".into(),
-        linker_flavor: LinkerFlavor::Em,
+        linker_flavor: LinkerFlavor::EmCc,
         // emcc emits two files - a .js file to instantiate the wasm and supply platform
         // functionality, and a .wasm file.
         exe_suffix: ".js".into(),
index c0700748c79f9d7df78b0bf21458e92ebd509974..26f8e7d34c6eac056f1b06a4563b0e7c33497906 100644 (file)
@@ -18,7 +18,6 @@
 /// obligations *could be* resolved if we wanted to.
 ///
 /// This also expects that `trait_ref` is fully normalized.
-#[instrument(level = "debug", skip(tcx))]
 pub fn codegen_fulfill_obligation<'tcx>(
     tcx: TyCtxt<'tcx>,
     (param_env, trait_ref): (ty::ParamEnv<'tcx>, ty::PolyTraitRef<'tcx>),
@@ -74,7 +73,6 @@ pub fn codegen_fulfill_obligation<'tcx>(
         // (ouz-a) This is required for `type-alias-impl-trait/assoc-projection-ice.rs` to pass
         let _ = infcx.inner.borrow_mut().opaque_type_storage.take_opaque_types();
 
-        debug!("Cache miss: {trait_ref:?} => {impl_source:?}");
         Ok(&*tcx.arena.alloc(impl_source))
     })
 }
index e4af7022239b83fa2492b0754ea1688096a76854..99046bd126f937f74d557cb582c8db8d17457305 100644 (file)
@@ -2014,7 +2014,7 @@ fn maybe_report_ambiguity(
         let predicate = self.resolve_vars_if_possible(obligation.predicate);
         let span = obligation.cause.span;
 
-        debug!(?predicate, obligation.cause.code = tracing::field::debug(&obligation.cause.code()));
+        debug!(?predicate, obligation.cause.code = ?obligation.cause.code());
 
         // Ambiguity errors are often caused as fallout from earlier errors.
         // We ignore them if this `infcx` is tainted in some cases below.
index d840677f1ca8b0d4c5e52d694a231789915a13b4..3763a98c488b766c11fc1e863a17e29f1c5c23d2 100644 (file)
@@ -135,7 +135,7 @@ impl<'tcx> TraitEngine<'tcx> for FulfillmentContext<'tcx> {
     /// `SomeTrait` or a where-clause that lets us unify `$0` with
     /// something concrete. If this fails, we'll unify `$0` with
     /// `projection_ty` again.
-    #[tracing::instrument(level = "debug", skip(self, infcx, param_env, cause))]
+    #[instrument(level = "debug", skip(self, infcx, param_env, cause))]
     fn normalize_projection_type(
         &mut self,
         infcx: &InferCtxt<'_, 'tcx>,
index 444ca6471e2e4d51696f25da4abfd4a1881e4c76..398635674abcfd19a69c7de02f88af6787e209f9 100644 (file)
@@ -231,7 +231,7 @@ pub(super) fn poly_project_and_unify_type<'cx, 'tcx>(
 /// If successful, this may result in additional obligations.
 ///
 /// See [poly_project_and_unify_type] for an explanation of the return value.
-#[tracing::instrument(level = "debug", skip(selcx))]
+#[instrument(level = "debug", skip(selcx))]
 fn project_and_unify_type<'cx, 'tcx>(
     selcx: &mut SelectionContext<'cx, 'tcx>,
     obligation: &ProjectionObligation<'tcx>,
@@ -1206,7 +1206,7 @@ fn with_addl_obligations(mut self, mut obligations: Vec<PredicateObligation<'tcx
 ///
 /// IMPORTANT:
 /// - `obligation` must be fully normalized
-#[tracing::instrument(level = "info", skip(selcx))]
+#[instrument(level = "info", skip(selcx))]
 fn project<'cx, 'tcx>(
     selcx: &mut SelectionContext<'cx, 'tcx>,
     obligation: &ProjectionTyObligation<'tcx>,
@@ -1368,7 +1368,7 @@ fn assemble_candidates_from_object_ty<'cx, 'tcx>(
     );
 }
 
-#[tracing::instrument(
+#[instrument(
     level = "debug",
     skip(selcx, candidate_set, ctor, env_predicates, potentially_unnormalized_candidates)
 )]
@@ -1419,7 +1419,7 @@ fn assemble_candidates_from_predicates<'cx, 'tcx>(
     }
 }
 
-#[tracing::instrument(level = "debug", skip(selcx, obligation, candidate_set))]
+#[instrument(level = "debug", skip(selcx, obligation, candidate_set))]
 fn assemble_candidates_from_impls<'cx, 'tcx>(
     selcx: &mut SelectionContext<'cx, 'tcx>,
     obligation: &ProjectionTyObligation<'tcx>,
index d67bd6292b434534556ea19f1896f3597294e377..e84c462ca816195e39badb321ed16c0a2135404b 100644 (file)
@@ -28,7 +28,7 @@
 use super::{EvaluatedCandidate, SelectionCandidateSet, SelectionContext, TraitObligationStack};
 
 impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
-    #[instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self), ret)]
     pub(super) fn candidate_from_obligation<'o>(
         &mut self,
         stack: &TraitObligationStack<'o, 'tcx>,
@@ -48,7 +48,7 @@ pub(super) fn candidate_from_obligation<'o>(
         if let Some(c) =
             self.check_candidate_cache(stack.obligation.param_env, cache_fresh_trait_pred)
         {
-            debug!(candidate = ?c, "CACHE HIT");
+            debug!("CACHE HIT");
             return c;
         }
 
@@ -61,7 +61,7 @@ pub(super) fn candidate_from_obligation<'o>(
         let (candidate, dep_node) =
             self.in_task(|this| this.candidate_from_obligation_no_cache(stack));
 
-        debug!(?candidate, "CACHE MISS");
+        debug!("CACHE MISS");
         self.insert_candidate_cache(
             stack.obligation.param_env,
             cache_fresh_trait_pred,
@@ -337,7 +337,7 @@ pub(super) fn assemble_candidates<'o>(
         Ok(candidates)
     }
 
-    #[tracing::instrument(level = "debug", skip(self, candidates))]
+    #[instrument(level = "debug", skip(self, candidates))]
     fn assemble_candidates_from_projected_tys(
         &mut self,
         obligation: &TraitObligation<'tcx>,
@@ -367,7 +367,7 @@ fn assemble_candidates_from_projected_tys(
     /// supplied to find out whether it is listed among them.
     ///
     /// Never affects the inference environment.
-    #[tracing::instrument(level = "debug", skip(self, stack, candidates))]
+    #[instrument(level = "debug", skip(self, stack, candidates))]
     fn assemble_candidates_from_caller_bounds<'o>(
         &mut self,
         stack: &TraitObligationStack<'o, 'tcx>,
@@ -880,7 +880,7 @@ fn assemble_candidates_for_unsizing(
         };
     }
 
-    #[tracing::instrument(level = "debug", skip(self, obligation, candidates))]
+    #[instrument(level = "debug", skip(self, obligation, candidates))]
     fn assemble_candidates_for_transmutability(
         &mut self,
         obligation: &TraitObligation<'tcx>,
@@ -898,7 +898,7 @@ fn assemble_candidates_for_transmutability(
         candidates.vec.push(TransmutabilityCandidate);
     }
 
-    #[tracing::instrument(level = "debug", skip(self, obligation, candidates))]
+    #[instrument(level = "debug", skip(self, obligation, candidates))]
     fn assemble_candidates_for_trait_alias(
         &mut self,
         obligation: &TraitObligation<'tcx>,
@@ -917,7 +917,7 @@ fn assemble_candidates_for_trait_alias(
 
     /// Assembles the trait which are built-in to the language itself:
     /// `Copy`, `Clone` and `Sized`.
-    #[tracing::instrument(level = "debug", skip(self, candidates))]
+    #[instrument(level = "debug", skip(self, candidates))]
     fn assemble_builtin_bound_candidates(
         &mut self,
         conditions: BuiltinImplConditions<'tcx>,
index 46b50dd92f1ef7a3ed17fa20b66ccaf9b7b7657b..5da8cfab0b13b77102197cf235c3503b1cef9533 100644 (file)
@@ -295,7 +295,7 @@ pub fn is_intercrate(&self) -> bool {
 
     /// Attempts to satisfy the obligation. If successful, this will affect the surrounding
     /// type environment by performing unification.
-    #[instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self), ret)]
     pub fn select(
         &mut self,
         obligation: &TraitObligation<'tcx>,
@@ -325,10 +325,7 @@ pub fn select(
                 Err(SelectionError::Overflow(OverflowError::Canonical))
             }
             Err(e) => Err(e),
-            Ok(candidate) => {
-                debug!(?candidate, "confirmed");
-                Ok(Some(candidate))
-            }
+            Ok(candidate) => Ok(Some(candidate)),
         }
     }
 
@@ -435,6 +432,7 @@ fn evaluate_predicates_recursively<'o, I>(
         level = "debug",
         skip(self, previous_stack),
         fields(previous_stack = ?previous_stack.head())
+        ret,
     )]
     fn evaluate_predicate_recursively<'o>(
         &mut self,
@@ -450,7 +448,7 @@ fn evaluate_predicate_recursively<'o>(
             None => self.check_recursion_limit(&obligation, &obligation)?,
         }
 
-        let result = ensure_sufficient_stack(|| {
+        ensure_sufficient_stack(|| {
             let bound_predicate = obligation.predicate.kind();
             match bound_predicate.skip_binder() {
                 ty::PredicateKind::Trait(t) => {
@@ -760,14 +758,10 @@ fn evaluate_predicate_recursively<'o>(
                     bug!("TypeWellFormedFromEnv is only used for chalk")
                 }
             }
-        });
-
-        debug!("finished: {:?} from {:?}", result, obligation);
-
-        result
+        })
     }
 
-    #[instrument(skip(self, previous_stack), level = "debug")]
+    #[instrument(skip(self, previous_stack), level = "debug", ret)]
     fn evaluate_trait_predicate_recursively<'o>(
         &mut self,
         previous_stack: TraitObligationStackList<'o, 'tcx>,
@@ -798,12 +792,12 @@ fn evaluate_trait_predicate_recursively<'o>(
         // If a trait predicate is in the (local or global) evaluation cache,
         // then we know it holds without cycles.
         if let Some(result) = self.check_evaluation_cache(param_env, fresh_trait_pred) {
-            debug!(?result, "CACHE HIT");
+            debug!("CACHE HIT");
             return Ok(result);
         }
 
         if let Some(result) = stack.cache().get_provisional(fresh_trait_pred) {
-            debug!(?result, "PROVISIONAL CACHE HIT");
+            debug!("PROVISIONAL CACHE HIT");
             stack.update_reached_depth(result.reached_depth);
             return Ok(result.result);
         }
@@ -826,11 +820,11 @@ fn evaluate_trait_predicate_recursively<'o>(
 
         let reached_depth = stack.reached_depth.get();
         if reached_depth >= stack.depth {
-            debug!(?result, "CACHE MISS");
+            debug!("CACHE MISS");
             self.insert_evaluation_cache(param_env, fresh_trait_pred, dep_node, result);
             stack.cache().on_completion(stack.dfn);
         } else {
-            debug!(?result, "PROVISIONAL");
+            debug!("PROVISIONAL");
             debug!(
                 "caching provisionally because {:?} \
                  is a cycle participant (at depth {}, reached depth {})",
@@ -1023,7 +1017,8 @@ fn coinductive_predicate(&self, predicate: ty::Predicate<'tcx>) -> bool {
     #[instrument(
         level = "debug",
         skip(self, stack),
-        fields(depth = stack.obligation.recursion_depth)
+        fields(depth = stack.obligation.recursion_depth),
+        ret
     )]
     fn evaluate_candidate<'o>(
         &mut self,
@@ -1056,7 +1051,6 @@ fn evaluate_candidate<'o>(
             result = result.max(EvaluatedToOkModuloRegions);
         }
 
-        debug!(?result);
         Ok(result)
     }
 
@@ -1405,7 +1399,7 @@ fn insert_candidate_cache(
     /// a projection, look at the bounds of `T::Bar`, see if we can find a
     /// `Baz` bound. We return indexes into the list returned by
     /// `tcx.item_bounds` for any applicable bounds.
-    #[instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self), ret)]
     fn match_projection_obligation_against_definition_bounds(
         &mut self,
         obligation: &TraitObligation<'tcx>,
@@ -1435,7 +1429,7 @@ fn match_projection_obligation_against_definition_bounds(
         // unnecessary ambiguity.
         let mut distinct_normalized_bounds = FxHashSet::default();
 
-        let matching_bounds = bounds
+        bounds
             .iter()
             .enumerate()
             .filter_map(|(idx, bound)| {
@@ -1462,10 +1456,7 @@ fn match_projection_obligation_against_definition_bounds(
                 }
                 None
             })
-            .collect();
-
-        debug!(?matching_bounds);
-        matching_bounds
+            .collect()
     }
 
     /// Equates the trait in `obligation` with trait bound. If the two traits
@@ -2153,7 +2144,7 @@ fn rematch_impl(
         }
     }
 
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self), ret)]
     fn match_impl(
         &mut self,
         impl_def_id: DefId,
@@ -2194,17 +2185,16 @@ fn match_impl(
             .at(&cause, obligation.param_env)
             .define_opaque_types(false)
             .eq(placeholder_obligation_trait_ref, impl_trait_ref)
-            .map_err(|e| debug!("match_impl: failed eq_trait_refs due to `{}`", e))?;
+            .map_err(|e| debug!("match_impl: failed eq_trait_refs due to `{e}`"))?;
         nested_obligations.extend(obligations);
 
         if !self.intercrate
             && self.tcx().impl_polarity(impl_def_id) == ty::ImplPolarity::Reservation
         {
-            debug!("match_impl: reservation impls only apply in intercrate mode");
+            debug!("reservation impls only apply in intercrate mode");
             return Err(());
         }
 
-        debug!(?impl_substs, ?nested_obligations, "match_impl: success");
         Ok(Normalized { value: impl_substs, obligations: nested_obligations })
     }
 
@@ -2335,7 +2325,7 @@ fn generator_trait_ref_unnormalized(
     /// impl or trait. The obligations are substituted and fully
     /// normalized. This is used when confirming an impl or default
     /// impl.
-    #[tracing::instrument(level = "debug", skip(self, cause, param_env))]
+    #[instrument(level = "debug", skip(self, cause, param_env))]
     fn impl_or_trait_obligations(
         &mut self,
         cause: &ObligationCause<'tcx>,
index 4bd179d23913143dd663bd7c7899677264f5c3ba..bb6009cb22a37b2df733bb9019e164eae8d5288b 100644 (file)
@@ -841,7 +841,7 @@ pub fn object_region_bounds<'tcx>(
 ///
 /// Requires that trait definitions have been processed so that we can
 /// elaborate predicates and walk supertraits.
-#[instrument(skip(tcx, predicates), level = "debug")]
+#[instrument(skip(tcx, predicates), level = "debug", ret)]
 pub(crate) fn required_region_bounds<'tcx>(
     tcx: TyCtxt<'tcx>,
     erased_self_ty: Ty<'tcx>,
index 4ab6d3737c5959c31c39d1b5bd272ea662672ce2..211c813b8001c8ae626bc5f783213c3c83fc2010 100644 (file)
@@ -317,7 +317,7 @@ pub fn from_ty(ty: Ty<'tcx>, tcx: TyCtxt<'tcx>) -> Result<Self, Err> {
                             tcx,
                         )?,
                         AdtKind::Enum => {
-                            tracing::trace!(?adt_def, "treeifying enum");
+                            trace!(?adt_def, "treeifying enum");
                             let mut tree = Tree::uninhabited();
 
                             for (idx, discr) in adt_def.discriminants(tcx) {
@@ -381,7 +381,7 @@ fn from_repr_c_variant(
             let clamp =
                 |align: Align| align.clamp(min_align, max_align).bytes().try_into().unwrap();
 
-            let variant_span = tracing::trace_span!(
+            let variant_span = trace_span!(
                 "treeifying variant",
                 min_align = ?min_align,
                 max_align = ?max_align,
@@ -396,22 +396,22 @@ fn from_repr_c_variant(
 
             // The layout of the variant is prefixed by the discriminant, if any.
             if let Some(discr) = discr {
-                tracing::trace!(?discr, "treeifying discriminant");
+                trace!(?discr, "treeifying discriminant");
                 let discr_layout = alloc::Layout::from_size_align(
                     layout_summary.discriminant_size,
                     clamp(layout_summary.discriminant_align),
                 )
                 .unwrap();
-                tracing::trace!(?discr_layout, "computed discriminant layout");
+                trace!(?discr_layout, "computed discriminant layout");
                 variant_layout = variant_layout.extend(discr_layout).unwrap().0;
                 tree = tree.then(Self::from_disr(discr, tcx, layout_summary.discriminant_size));
             }
 
             // Next come fields.
-            let fields_span = tracing::trace_span!("treeifying fields").entered();
+            let fields_span = trace_span!("treeifying fields").entered();
             for field_def in variant_def.fields.iter() {
                 let field_ty = field_def.ty(tcx, substs_ref);
-                let _span = tracing::trace_span!("treeifying field", field = ?field_ty).entered();
+                let _span = trace_span!("treeifying field", field = ?field_ty).entered();
 
                 // begin with the field's visibility
                 tree = tree.then(Self::def(Def::Field(field_def)));
@@ -434,7 +434,7 @@ fn from_repr_c_variant(
             drop(fields_span);
 
             // finally: padding
-            let padding_span = tracing::trace_span!("adding trailing padding").entered();
+            let padding_span = trace_span!("adding trailing padding").entered();
             let padding_needed = layout_summary.total_size - variant_layout.size();
             if padding_needed > 0 {
                 tree = tree.then(Self::padding(padding_needed));
@@ -467,7 +467,7 @@ fn layout_of<'tcx>(
             layout.align().abi.bytes().try_into().unwrap(),
         )
         .unwrap();
-        tracing::trace!(?ty, ?layout, "computed layout for type");
+        trace!(?ty, ?layout, "computed layout for type");
         Ok(layout)
     }
 }
index 076d922d1b72b4157a47dd296dc15a3007252d8b..248ff1ec24164c9209c84bdd98b009de8e2679d7 100644 (file)
@@ -110,7 +110,7 @@ pub(crate) fn answer(self) -> Answer<<C as QueryContext>::Ref> {
             // Remove all `Def` nodes from `src`, without checking their visibility.
             let src = src.prune(&|def| true);
 
-            tracing::trace!(?src, "pruned src");
+            trace!(?src, "pruned src");
 
             // Remove all `Def` nodes from `dst`, additionally...
             let dst = if assume_visibility {
@@ -121,7 +121,7 @@ pub(crate) fn answer(self) -> Answer<<C as QueryContext>::Ref> {
                 dst.prune(&|def| context.is_accessible_from(def, scope))
             };
 
-            tracing::trace!(?dst, "pruned dst");
+            trace!(?dst, "pruned dst");
 
             // Convert `src` from a tree-based representation to an NFA-based representation.
             // If the conversion fails because `src` is uninhabited, conclude that the transmutation
index 9c2cf4c9a92384821dc5c356372d351982213b83..adab343ac98aaa4b225a4b2bcb790d3000f3c2ea 100644 (file)
@@ -82,7 +82,7 @@ fn is_accessible_from(&self, def: Self::Def, scope: Self::Scope) -> bool {
                 false
             };
 
-            tracing::trace!(?ret, "ret");
+            trace!(?ret, "ret");
             ret
         }
 
index bd1d568cd9a051079bae294ec74562a557c371ce..661e413fc5b8170defb0d06724fc0b62710b4573 100644 (file)
@@ -15,8 +15,6 @@
 use std::collections::BTreeMap;
 use std::ops::ControlFlow;
 
-use tracing::debug;
-
 // FIXME(#86795): `BoundVarsCollector` here should **NOT** be used
 // outside of `resolve_associated_item`. It's just to address #64494,
 // #83765, and #85848 which are creating bound types/regions that lose
index acfeefb4d12d535d9d7a03477a90049cde370ac6..9d640672cf92c8cd3bc2f7cc861c931a71b3edb7 100644 (file)
@@ -104,7 +104,6 @@ fn adt_sized_constraint(tcx: TyCtxt<'_>, def_id: DefId) -> ty::AdtSizedConstrain
 }
 
 /// See `ParamEnv` struct definition for details.
-#[instrument(level = "debug", skip(tcx))]
 fn param_env(tcx: TyCtxt<'_>, def_id: DefId) -> ty::ParamEnv<'_> {
     // The param_env of an impl Trait type is its defining function's param_env
     if let Some(parent) = ty::is_impl_trait_defn(tcx, def_id) {
@@ -410,7 +409,6 @@ fn asyncness(tcx: TyCtxt<'_>, def_id: DefId) -> hir::IsAsync {
 }
 
 /// Don't call this directly: use ``tcx.conservative_is_privately_uninhabited`` instead.
-#[instrument(level = "debug", skip(tcx))]
 pub fn conservative_is_privately_uninhabited_raw<'tcx>(
     tcx: TyCtxt<'tcx>,
     param_env_and: ty::ParamEnvAnd<'tcx, Ty<'tcx>>,
index 5c96f1c4623a6c9010633d79951b1af3023c96c4..ef927058df4eef0781c1c7a512921844d540b2c9 100644 (file)
@@ -144,7 +144,7 @@ enum ConvertedBindingKind<'a, 'tcx> {
 /// instantiated with some generic arguments providing `'a` explicitly,
 /// we taint those arguments with `ExplicitLateBound::Yes` so that we
 /// can provide an appropriate diagnostic later.
-#[derive(Copy, Clone, PartialEq)]
+#[derive(Copy, Clone, PartialEq, Debug)]
 pub enum ExplicitLateBound {
     Yes,
     No,
@@ -167,7 +167,7 @@ pub(crate) enum GenericArgPosition {
 
 /// A marker denoting that the generic arguments that were
 /// provided did not match the respective generic parameters.
-#[derive(Clone, Default)]
+#[derive(Clone, Default, Debug)]
 pub struct GenericArgCountMismatch {
     /// Indicates whether a fatal error was reported (`Some`), or just a lint (`None`).
     pub reported: Option<ErrorGuaranteed>,
@@ -177,7 +177,7 @@ pub struct GenericArgCountMismatch {
 
 /// Decorates the result of a generic argument count mismatch
 /// check with whether explicit late bounds were provided.
-#[derive(Clone)]
+#[derive(Clone, Debug)]
 pub struct GenericArgCountResult {
     pub explicit_late_bound: ExplicitLateBound,
     pub correct: Result<(), GenericArgCountMismatch>,
@@ -201,7 +201,7 @@ fn inferred_kind(
 }
 
 impl<'o, 'tcx> dyn AstConv<'tcx> + 'o {
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self), ret)]
     pub fn ast_region_to_region(
         &self,
         lifetime: &hir::Lifetime,
@@ -210,7 +210,7 @@ pub fn ast_region_to_region(
         let tcx = self.tcx();
         let lifetime_name = |def_id| tcx.hir().name(tcx.hir().local_def_id_to_hir_id(def_id));
 
-        let r = match tcx.named_region(lifetime.hir_id) {
+        match tcx.named_region(lifetime.hir_id) {
             Some(rl::Region::Static) => tcx.lifetimes.re_static,
 
             Some(rl::Region::LateBound(debruijn, index, def_id)) => {
@@ -255,9 +255,7 @@ pub fn ast_region_to_region(
                     tcx.lifetimes.re_static
                 })
             }
-        };
-        debug!("ast_region_to_region(lifetime={:?}) yields {:?}", lifetime, r);
-        r
+        }
     }
 
     /// Given a path `path` that refers to an item `I` with the declared generics `decl_generics`,
@@ -317,7 +315,7 @@ pub fn ast_path_substs_for_ty(
     /// `[Vec<u8>, u8]` and `generic_args` are the arguments for the associated
     /// type itself: `['a]`. The returned `SubstsRef` concatenates these two
     /// lists: `[Vec<u8>, u8, 'a]`.
-    #[tracing::instrument(level = "debug", skip(self, span))]
+    #[instrument(level = "debug", skip(self, span), ret)]
     fn create_substs_for_ast_path<'a>(
         &self,
         span: Span,
@@ -537,11 +535,6 @@ fn inferred_kind(
             &mut substs_ctx,
         );
 
-        debug!(
-            "create_substs_for_ast_path(generic_params={:?}, self_ty={:?}) -> {:?}",
-            generics, self_ty, substs
-        );
-
         (substs, arg_count)
     }
 
@@ -716,7 +709,7 @@ fn instantiate_poly_trait_ref_inner(
     /// where `'a` is a bound region at depth 0. Similarly, the `poly_trait_ref` would be
     /// `Bar<'a>`. The returned poly-trait-ref will have this binder instantiated explicitly,
     /// however.
-    #[tracing::instrument(level = "debug", skip(self, span, constness, bounds, speculative))]
+    #[instrument(level = "debug", skip(self, span, constness, bounds, speculative))]
     pub(crate) fn instantiate_poly_trait_ref(
         &self,
         trait_ref: &hir::TraitRef<'_>,
@@ -808,7 +801,7 @@ fn ast_path_to_mono_trait_ref(
         ty::TraitRef::new(trait_def_id, substs)
     }
 
-    #[tracing::instrument(level = "debug", skip(self, span))]
+    #[instrument(level = "debug", skip(self, span))]
     fn create_substs_for_ast_trait_ref<'a>(
         &self,
         span: Span,
@@ -922,7 +915,7 @@ pub(crate) fn add_implicitly_sized<'hir>(
     /// **A note on binders:** there is an implied binder around
     /// `param_ty` and `ast_bounds`. See `instantiate_poly_trait_ref`
     /// for more details.
-    #[tracing::instrument(level = "debug", skip(self, ast_bounds, bounds))]
+    #[instrument(level = "debug", skip(self, ast_bounds, bounds))]
     pub(crate) fn add_bounds<'hir, I: Iterator<Item = &'hir hir::GenericBound<'hir>>>(
         &self,
         param_ty: Ty<'tcx>,
@@ -1028,10 +1021,7 @@ fn compute_bounds_inner(
     /// **A note on binders:** given something like `T: for<'a> Iterator<Item = &'a u32>`, the
     /// `trait_ref` here will be `for<'a> T: Iterator`. The `binding` data however is from *inside*
     /// the binder (e.g., `&'a u32`) and hence may reference bound regions.
-    #[tracing::instrument(
-        level = "debug",
-        skip(self, bounds, speculative, dup_bindings, path_span)
-    )]
+    #[instrument(level = "debug", skip(self, bounds, speculative, dup_bindings, path_span))]
     fn add_predicates_for_ast_type_binding(
         &self,
         hir_ref_id: hir::HirId,
@@ -2599,7 +2589,7 @@ pub fn ast_ty_to_ty_in_path(&self, ast_ty: &hir::Ty<'_>) -> Ty<'tcx> {
 
     /// Turns a `hir::Ty` into a `Ty`. For diagnostics' purposes we keep track of whether trait
     /// objects are borrowed like `&dyn Trait` to avoid emitting redundant errors.
-    #[tracing::instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self), ret)]
     fn ast_ty_to_ty_inner(&self, ast_ty: &hir::Ty<'_>, borrowed: bool, in_path: bool) -> Ty<'tcx> {
         let tcx = self.tcx();
 
@@ -2703,8 +2693,6 @@ fn ast_ty_to_ty_inner(&self, ast_ty: &hir::Ty<'_>, borrowed: bool, in_path: bool
             hir::TyKind::Err => tcx.ty_error(),
         };
 
-        debug!(?result_ty);
-
         self.record_ty(ast_ty.hir_id, result_ty, ast_ty.span);
         result_ty
     }
index 2d50412007d909b493571c7d774bc4c82b729dd0..25bafdfe859b882af75dee0a021595a9db8f7670 100644 (file)
@@ -12,7 +12,7 @@
 };
 
 impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
-    #[instrument(skip(self), level = "debug")]
+    #[instrument(skip(self), level = "debug", ret)]
     pub fn check_match(
         &self,
         expr: &'tcx hir::Expr<'tcx>,
@@ -212,9 +212,7 @@ pub fn check_match(
         // We won't diverge unless the scrutinee or all arms diverge.
         self.diverges.set(scrut_diverges | all_arms_diverge);
 
-        let match_ty = coercion.complete(self);
-        debug!(?match_ty);
-        match_ty
+        coercion.complete(self)
     }
 
     /// When the previously checked expression (the scrutinee) diverges,
index fee872155f5b2d1fa86c3ca4958a8c5d0384ce3a..bc3fec6e7d66a371dc57dfb0fd8a0039a30838fa 100644 (file)
@@ -58,7 +58,7 @@ pub fn check_expr_closure(
         self.check_closure(expr, expected_kind, decl, body, gen, expected_sig)
     }
 
-    #[instrument(skip(self, expr, body, decl), level = "debug")]
+    #[instrument(skip(self, expr, body, decl), level = "debug", ret)]
     fn check_closure(
         &self,
         expr: &hir::Expr<'_>,
@@ -158,11 +158,7 @@ fn check_closure(
             },
         );
 
-        let closure_type = self.tcx.mk_closure(expr_def_id.to_def_id(), closure_substs.substs);
-
-        debug!(?expr.hir_id, ?closure_type);
-
-        closure_type
+        self.tcx.mk_closure(expr_def_id.to_def_id(), closure_substs.substs)
     }
 
     /// Given the expected type, figures out what it can about this closure we
@@ -262,7 +258,7 @@ fn deduce_expectations_from_obligations(
     /// The `cause_span` should be the span that caused us to
     /// have this expected signature, or `None` if we can't readily
     /// know that.
-    #[instrument(level = "debug", skip(self, cause_span))]
+    #[instrument(level = "debug", skip(self, cause_span), ret)]
     fn deduce_sig_from_projection(
         &self,
         cause_span: Option<Span>,
@@ -317,7 +313,6 @@ fn deduce_sig_from_projection(
             hir::Unsafety::Normal,
             Abi::Rust,
         ));
-        debug!(?sig);
 
         Some(ExpectedSig { cause_span, sig })
     }
@@ -576,7 +571,7 @@ fn check_supplied_sig_against_expectation(
     /// types that the user gave into a signature.
     ///
     /// Also, record this closure signature for later.
-    #[instrument(skip(self, decl, body), level = "debug")]
+    #[instrument(skip(self, decl, body), level = "debug", ret)]
     fn supplied_sig_of_closure(
         &self,
         hir_id: hir::HirId,
@@ -629,8 +624,6 @@ fn supplied_sig_of_closure(
             bound_vars,
         );
 
-        debug!(?result);
-
         let c_result = self.inh.infcx.canonicalize_response(result);
         self.typeck_results.borrow_mut().user_provided_sigs.insert(expr_def_id, c_result);
 
@@ -643,7 +636,7 @@ fn supplied_sig_of_closure(
     /// user specified. The "desugared" return type is an `impl
     /// Future<Output = T>`, so we do this by searching through the
     /// obligations to extract the `T`.
-    #[instrument(skip(self), level = "debug")]
+    #[instrument(skip(self), level = "debug", ret)]
     fn deduce_future_output_from_obligations(
         &self,
         expr_def_id: DefId,
@@ -704,7 +697,6 @@ fn deduce_future_output_from_obligations(
             );
         self.register_predicates(obligations);
 
-        debug!("deduce_future_output_from_obligations: output_ty={:?}", output_ty);
         Some(output_ty)
     }
 
index 804306814a24127b2c352a21ec17364e31c0a077..b6bc244d2b14447a5c3d4a96c942a87f8ca0f58a 100644 (file)
@@ -1308,7 +1308,7 @@ fn compare_type_predicate_entailment<'tcx>(
 /// For default associated types the normalization is not possible (the value
 /// from the impl could be overridden). We also can't normalize generic
 /// associated types (yet) because they contain bound parameters.
-#[tracing::instrument(level = "debug", skip(tcx))]
+#[instrument(level = "debug", skip(tcx))]
 pub fn check_type_bounds<'tcx>(
     tcx: TyCtxt<'tcx>,
     trait_ty: &ty::AssocItem,
index 07046f3f0326b119185f836728bd3bf49df39873..b9054898a2e579174a748a275146d570d0074449 100644 (file)
@@ -130,7 +130,7 @@ pub fn demand_coerce(
     ///
     /// N.B., this code relies on `self.diverges` to be accurate. In particular, assignments to `!`
     /// will be permitted if the diverges flag is currently "always".
-    #[tracing::instrument(level = "debug", skip(self, expr, expected_ty_expr, allow_two_phase))]
+    #[instrument(level = "debug", skip(self, expr, expected_ty_expr, allow_two_phase))]
     pub fn demand_coerce_diag(
         &self,
         expr: &hir::Expr<'tcx>,
index 20d25d508d224e9749e631f3e8a4cfb5905cbe1e..66b737a493058861a7b36928ba4295eeb1b2ff8a 100644 (file)
@@ -83,7 +83,7 @@ pub(in super::super) fn resolve_vars_with_obligations(&self, ty: Ty<'tcx>) -> Ty
         self.resolve_vars_with_obligations_and_mutate_fulfillment(ty, |_| {})
     }
 
-    #[instrument(skip(self, mutate_fulfillment_errors), level = "debug")]
+    #[instrument(skip(self, mutate_fulfillment_errors), level = "debug", ret)]
     pub(in super::super) fn resolve_vars_with_obligations_and_mutate_fulfillment(
         &self,
         mut ty: Ty<'tcx>,
@@ -107,10 +107,7 @@ pub(in super::super) fn resolve_vars_with_obligations_and_mutate_fulfillment(
         // indirect dependencies that don't seem worth tracking
         // precisely.
         self.select_obligations_where_possible(false, mutate_fulfillment_errors);
-        ty = self.resolve_vars_if_possible(ty);
-
-        debug!(?ty);
-        ty
+        self.resolve_vars_if_possible(ty)
     }
 
     pub(in super::super) fn record_deferred_call_resolution(
@@ -1405,7 +1402,7 @@ pub(crate) fn add_required_obligations_for_hir(
         })
     }
 
-    #[tracing::instrument(level = "debug", skip(self, code, span, def_id, substs))]
+    #[instrument(level = "debug", skip(self, code, span, def_id, substs))]
     fn add_required_obligations_with_code(
         &self,
         span: Span,
index 85a0d4e44990602e6a6bcdb7172bf0057d0f685f..2a8c460bb11830921c4e48fdc715d9d3e0980ae2 100644 (file)
@@ -17,7 +17,6 @@
 use rustc_middle::ty::{self, RvalueScopes, Ty, TyCtxt, TypeVisitable};
 use rustc_span::symbol::sym;
 use rustc_span::Span;
-use tracing::debug;
 
 mod drop_ranges;
 
index de26a9e56e2d6b57275d2060fb475c540677eda0..a9071cd1fd949efe57c2bfd122425fb0b5277dd7 100644 (file)
@@ -168,7 +168,7 @@ pub(crate) fn suggest_method_call(
     /// * `call_expr`:             the complete method call: (`foo.bar::<T1,...Tn>(...)`)
     /// * `self_expr`:             the self expression (`foo`)
     /// * `args`:                  the expressions of the arguments (`a, b + 1, ...`)
-    #[instrument(level = "debug", skip(self, call_expr, self_expr))]
+    #[instrument(level = "debug", skip(self))]
     pub fn lookup_method(
         &self,
         self_ty: Ty<'tcx>,
@@ -178,11 +178,6 @@ pub fn lookup_method(
         self_expr: &'tcx hir::Expr<'tcx>,
         args: &'tcx [hir::Expr<'tcx>],
     ) -> Result<MethodCallee<'tcx>, MethodError<'tcx>> {
-        debug!(
-            "lookup(method_name={}, self_ty={:?}, call_expr={:?}, self_expr={:?})",
-            segment.ident, self_ty, call_expr, self_expr
-        );
-
         let pick =
             self.lookup_probe(span, segment.ident, self_ty, call_expr, ProbeScope::TraitsInScope)?;
 
@@ -383,7 +378,7 @@ pub(super) fn obligation_for_op_method(
     /// In particular, it doesn't really do any probing: it simply constructs
     /// an obligation for a particular trait with the given self type and checks
     /// whether that trait is implemented.
-    #[instrument(level = "debug", skip(self, span, opt_input_types))]
+    #[instrument(level = "debug", skip(self, span))]
     pub(super) fn lookup_method_in_trait(
         &self,
         span: Span,
@@ -392,11 +387,6 @@ pub(super) fn lookup_method_in_trait(
         self_ty: Ty<'tcx>,
         opt_input_types: Option<&[Ty<'tcx>]>,
     ) -> Option<InferOk<'tcx, MethodCallee<'tcx>>> {
-        debug!(
-            "lookup_in_trait_adjusted(self_ty={:?}, m_name={}, trait_def_id={:?}, opt_input_types={:?})",
-            self_ty, m_name, trait_def_id, opt_input_types
-        );
-
         let (obligation, substs) =
             self.obligation_for_method(span, trait_def_id, self_ty, opt_input_types);
         self.construct_obligation_for_trait(
@@ -576,7 +566,7 @@ fn construct_obligation_for_trait(
     /// * `self_ty`:               the type to search within (`Foo`)
     /// * `self_ty_span`           the span for the type being searched within (span of `Foo`)
     /// * `expr_id`:               the [`hir::HirId`] of the expression composing the entire call
-    #[instrument(level = "debug", skip(self))]
+    #[instrument(level = "debug", skip(self), ret)]
     pub fn resolve_fully_qualified_call(
         &self,
         span: Span,
@@ -585,11 +575,6 @@ pub fn resolve_fully_qualified_call(
         self_ty_span: Span,
         expr_id: hir::HirId,
     ) -> Result<(DefKind, DefId), MethodError<'tcx>> {
-        debug!(
-            "resolve_fully_qualified_call: method_name={:?} self_ty={:?} expr_id={:?}",
-            method_name, self_ty, expr_id,
-        );
-
         let tcx = self.tcx;
 
         // Check if we have an enum variant.
@@ -633,21 +618,17 @@ pub fn resolve_fully_qualified_call(
             &pick,
         );
 
-        debug!("resolve_fully_qualified_call: pick={:?}", pick);
+        debug!(?pick);
         {
             let mut typeck_results = self.typeck_results.borrow_mut();
             let used_trait_imports = Lrc::get_mut(&mut typeck_results.used_trait_imports).unwrap();
             for import_id in pick.import_ids {
-                debug!("resolve_fully_qualified_call: used_trait_import: {:?}", import_id);
+                debug!(used_trait_import=?import_id);
                 used_trait_imports.insert(import_id);
             }
         }
 
         let def_kind = pick.item.kind.as_def_kind();
-        debug!(
-            "resolve_fully_qualified_call: def_kind={:?}, def_id={:?}",
-            def_kind, pick.item.def_id
-        );
         tcx.check_stability(pick.item.def_id, Some(expr_id), span, Some(method_name.span));
         Ok((def_kind, pick.item.def_id))
     }
index d9870060a40bbb974922ac85bce1f00c9d21f838..e9f55ab3406f5df2ea9bc49c8e34985b479c36df 100644 (file)
@@ -253,7 +253,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
     /// would result in an error (basically, the same criteria we
     /// would use to decide if a method is a plausible fit for
     /// ambiguity purposes).
-    #[instrument(level = "debug", skip(self, scope_expr_id))]
+    #[instrument(level = "debug", skip(self))]
     pub fn probe_for_return_type(
         &self,
         span: Span,
@@ -262,10 +262,6 @@ pub fn probe_for_return_type(
         self_ty: Ty<'tcx>,
         scope_expr_id: hir::HirId,
     ) -> Vec<ty::AssocItem> {
-        debug!(
-            "probe(self_ty={:?}, return_type={}, scope_expr_id={})",
-            self_ty, return_type, scope_expr_id
-        );
         let method_names = self
             .probe_op(
                 span,
@@ -299,7 +295,7 @@ pub fn probe_for_return_type(
             .collect()
     }
 
-    #[instrument(level = "debug", skip(self, scope_expr_id))]
+    #[instrument(level = "debug", skip(self))]
     pub fn probe_for_name(
         &self,
         span: Span,
@@ -310,10 +306,6 @@ pub fn probe_for_name(
         scope_expr_id: hir::HirId,
         scope: ProbeScope,
     ) -> PickResult<'tcx> {
-        debug!(
-            "probe(self_ty={:?}, item_name={}, scope_expr_id={})",
-            self_ty, item_name, scope_expr_id
-        );
         self.probe_op(
             span,
             mode,
index 3281dd8298bc3000526cc5bb55fdd577e9235933..66281448d40e88e6c5c45217b5d0183501de1281 100644 (file)
@@ -341,7 +341,6 @@ fn diagnostic_only_typeck<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> &ty::T
     typeck_with_fallback(tcx, def_id, fallback)
 }
 
-#[instrument(skip(tcx, fallback))]
 fn typeck_with_fallback<'tcx>(
     tcx: TyCtxt<'tcx>,
     def_id: LocalDefId,
index ba42453bd60e920286239085eeb96203479087a8..86cf12d224047a664cef7b1942e4da58b09f64fd 100644 (file)
@@ -972,7 +972,7 @@ fn check_param_wf(tcx: TyCtxt<'_>, param: &hir::GenericParam<'_>) {
     }
 }
 
-#[tracing::instrument(level = "debug", skip(tcx, span, sig_if_method))]
+#[instrument(level = "debug", skip(tcx, span, sig_if_method))]
 fn check_associated_item(
     tcx: TyCtxt<'_>,
     item_id: LocalDefId,
@@ -1225,7 +1225,7 @@ fn check_item_type(tcx: TyCtxt<'_>, item_id: LocalDefId, ty_span: Span, allow_fo
     });
 }
 
-#[tracing::instrument(level = "debug", skip(tcx, ast_self_ty, ast_trait_ref))]
+#[instrument(level = "debug", skip(tcx, ast_self_ty, ast_trait_ref))]
 fn check_impl<'tcx>(
     tcx: TyCtxt<'tcx>,
     item: &'tcx hir::Item<'tcx>,
@@ -1472,7 +1472,7 @@ fn visit_const(&mut self, c: ty::Const<'tcx>) -> ControlFlow<Self::BreakTy> {
     wfcx.register_obligations(obligations);
 }
 
-#[tracing::instrument(level = "debug", skip(wfcx, span, hir_decl))]
+#[instrument(level = "debug", skip(wfcx, span, hir_decl))]
 fn check_fn_or_method<'tcx>(
     wfcx: &WfCheckingCtxt<'_, 'tcx>,
     span: Span,
@@ -1536,7 +1536,7 @@ fn check_fn_or_method<'tcx>(
      `self: Rc<Self>`, `self: Arc<Self>`, or `self: Pin<P>` (where P is one \
      of the previous types except `Self`)";
 
-#[tracing::instrument(level = "debug", skip(wfcx))]
+#[instrument(level = "debug", skip(wfcx))]
 fn check_method_receiver<'tcx>(
     wfcx: &WfCheckingCtxt<'_, 'tcx>,
     fn_sig: &hir::FnSig<'_>,
index f1dbe64f13abbb33e3cb4a323abb015be0288489..9f931de6fdedb674b11b6fff3724a49c5b4a361a 100644 (file)
@@ -19,7 +19,6 @@
 /// Computes the relevant generic parameter for a potential generic const argument.
 ///
 /// This should be called using the query `tcx.opt_const_param_of`.
-#[instrument(level = "debug", skip(tcx))]
 pub(super) fn opt_const_param_of(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Option<DefId> {
     use hir::*;
     let hir_id = tcx.hir().local_def_id_to_hir_id(def_id);
index b320cdcc109ddc061fec4a33b2fea4b379ed89e3..a967d881b029b7facb6af929d2d18c3fc6bc6d93 100644 (file)
@@ -666,6 +666,10 @@ changelog-seen = 2
 # target.
 #llvm-config = <none> (path)
 
+# Override detection of whether this is a Rust-patched LLVM. This would be used
+# in conjunction with either an llvm-config or build.submodules = false.
+#llvm-has-rust-patches = if llvm-config { false } else { true }
+
 # Normally the build system can find LLVM's FileCheck utility, but if
 # not, you can specify an explicit file name for it.
 #llvm-filecheck = "/path/to/llvm-version/bin/FileCheck"
index e54f6c912d5945eacdc096a27c4b5b52222a6575..1a379ecc11c01d7ae8cdfde75d8a591425eaa2ca 100644 (file)
@@ -796,7 +796,7 @@ pub trait Provider {
     /// impl Provider for SomeConcreteType {
     ///     fn provide<'a>(&'a self, demand: &mut Demand<'a>) {
     ///         demand.provide_ref::<str>(&self.field)
-    ///             .provide_value::<i32>(|| self.num_field);
+    ///             .provide_value::<i32>(self.num_field);
     ///     }
     /// }
     /// ```
@@ -881,28 +881,55 @@ fn new<'b>(erased: &'b mut (dyn Erased<'a> + 'a)) -> &'b mut Demand<'a> {
     ///
     /// # Examples
     ///
+    /// Provides an `u8`.
+    ///
+    /// ```rust
+    /// #![feature(provide_any)]
+    ///
+    /// use std::any::{Provider, Demand};
+    /// # struct SomeConcreteType { field: u8 }
+    ///
+    /// impl Provider for SomeConcreteType {
+    ///     fn provide<'a>(&'a self, demand: &mut Demand<'a>) {
+    ///         demand.provide_value::<u8>(self.field);
+    ///     }
+    /// }
+    /// ```
+    #[unstable(feature = "provide_any", issue = "96024")]
+    pub fn provide_value<T>(&mut self, value: T) -> &mut Self
+    where
+        T: 'static,
+    {
+        self.provide::<tags::Value<T>>(value)
+    }
+
+    /// Provide a value or other type with only static lifetimes computed using a closure.
+    ///
+    /// # Examples
+    ///
     /// Provides a `String` by cloning.
     ///
     /// ```rust
-    /// # #![feature(provide_any)]
+    /// #![feature(provide_any)]
+    ///
     /// use std::any::{Provider, Demand};
     /// # struct SomeConcreteType { field: String }
     ///
     /// impl Provider for SomeConcreteType {
     ///     fn provide<'a>(&'a self, demand: &mut Demand<'a>) {
-    ///         demand.provide_value::<String>(|| self.field.clone());
+    ///         demand.provide_value_with::<String>(|| self.field.clone());
     ///     }
     /// }
     /// ```
     #[unstable(feature = "provide_any", issue = "96024")]
-    pub fn provide_value<T>(&mut self, fulfil: impl FnOnce() -> T) -> &mut Self
+    pub fn provide_value_with<T>(&mut self, fulfil: impl FnOnce() -> T) -> &mut Self
     where
         T: 'static,
     {
         self.provide_with::<tags::Value<T>>(fulfil)
     }
 
-    /// Provide a reference, note that the referee type must be bounded by `'static`,
+    /// Provide a reference. The referee type must be bounded by `'static`,
     /// but may be unsized.
     ///
     /// # Examples
@@ -910,7 +937,8 @@ pub fn provide_value<T>(&mut self, fulfil: impl FnOnce() -> T) -> &mut Self
     /// Provides a reference to a field as a `&str`.
     ///
     /// ```rust
-    /// # #![feature(provide_any)]
+    /// #![feature(provide_any)]
+    ///
     /// use std::any::{Provider, Demand};
     /// # struct SomeConcreteType { field: String }
     ///
@@ -925,6 +953,40 @@ pub fn provide_ref<T: ?Sized + 'static>(&mut self, value: &'a T) -> &mut Self {
         self.provide::<tags::Ref<tags::MaybeSizedValue<T>>>(value)
     }
 
+    /// Provide a reference computed using a closure. The referee type
+    /// must be bounded by `'static`, but may be unsized.
+    ///
+    /// # Examples
+    ///
+    /// Provides a reference to a field as a `&str`.
+    ///
+    /// ```rust
+    /// #![feature(provide_any)]
+    ///
+    /// use std::any::{Provider, Demand};
+    /// # struct SomeConcreteType { business: String, party: String }
+    /// # fn today_is_a_weekday() -> bool { true }
+    ///
+    /// impl Provider for SomeConcreteType {
+    ///     fn provide<'a>(&'a self, demand: &mut Demand<'a>) {
+    ///         demand.provide_ref_with::<str>(|| {
+    ///             if today_is_a_weekday() {
+    ///                 &self.business
+    ///             } else {
+    ///                 &self.party
+    ///             }
+    ///         });
+    ///     }
+    /// }
+    /// ```
+    #[unstable(feature = "provide_any", issue = "96024")]
+    pub fn provide_ref_with<T: ?Sized + 'static>(
+        &mut self,
+        fulfil: impl FnOnce() -> &'a T,
+    ) -> &mut Self {
+        self.provide_with::<tags::Ref<tags::MaybeSizedValue<T>>>(fulfil)
+    }
+
     /// Provide a value with the given `Type` tag.
     fn provide<I>(&mut self, value: I::Reified) -> &mut Self
     where
@@ -946,6 +1008,156 @@ fn provide_with<I>(&mut self, fulfil: impl FnOnce() -> I::Reified) -> &mut Self
         }
         self
     }
+
+    /// Check if the `Demand` would be satisfied if provided with a
+    /// value of the specified type. If the type does not match or has
+    /// already been provided, returns false.
+    ///
+    /// # Examples
+    ///
+    /// Check if an `u8` still needs to be provided and then provides
+    /// it.
+    ///
+    /// ```rust
+    /// #![feature(provide_any)]
+    ///
+    /// use std::any::{Provider, Demand};
+    ///
+    /// struct Parent(Option<u8>);
+    ///
+    /// impl Provider for Parent {
+    ///     fn provide<'a>(&'a self, demand: &mut Demand<'a>) {
+    ///         if let Some(v) = self.0 {
+    ///             demand.provide_value::<u8>(v);
+    ///         }
+    ///     }
+    /// }
+    ///
+    /// struct Child {
+    ///     parent: Parent,
+    /// }
+    ///
+    /// impl Child {
+    ///     // Pretend that this takes a lot of resources to evaluate.
+    ///     fn an_expensive_computation(&self) -> Option<u8> {
+    ///         Some(99)
+    ///     }
+    /// }
+    ///
+    /// impl Provider for Child {
+    ///     fn provide<'a>(&'a self, demand: &mut Demand<'a>) {
+    ///         // In general, we don't know if this call will provide
+    ///         // an `u8` value or not...
+    ///         self.parent.provide(demand);
+    ///
+    ///         // ...so we check to see if the `u8` is needed before
+    ///         // we run our expensive computation.
+    ///         if demand.would_be_satisfied_by_value_of::<u8>() {
+    ///             if let Some(v) = self.an_expensive_computation() {
+    ///                 demand.provide_value::<u8>(v);
+    ///             }
+    ///         }
+    ///
+    ///         // The demand will be satisfied now, regardless of if
+    ///         // the parent provided the value or we did.
+    ///         assert!(!demand.would_be_satisfied_by_value_of::<u8>());
+    ///     }
+    /// }
+    ///
+    /// let parent = Parent(Some(42));
+    /// let child = Child { parent };
+    /// assert_eq!(Some(42), std::any::request_value::<u8>(&child));
+    ///
+    /// let parent = Parent(None);
+    /// let child = Child { parent };
+    /// assert_eq!(Some(99), std::any::request_value::<u8>(&child));
+    /// ```
+    #[unstable(feature = "provide_any", issue = "96024")]
+    pub fn would_be_satisfied_by_value_of<T>(&self) -> bool
+    where
+        T: 'static,
+    {
+        self.would_be_satisfied_by::<tags::Value<T>>()
+    }
+
+    /// Check if the `Demand` would be satisfied if provided with a
+    /// reference to a value of the specified type. If the type does
+    /// not match or has already been provided, returns false.
+    ///
+    /// # Examples
+    ///
+    /// Check if a `&str` still needs to be provided and then provides
+    /// it.
+    ///
+    /// ```rust
+    /// #![feature(provide_any)]
+    ///
+    /// use std::any::{Provider, Demand};
+    ///
+    /// struct Parent(Option<String>);
+    ///
+    /// impl Provider for Parent {
+    ///     fn provide<'a>(&'a self, demand: &mut Demand<'a>) {
+    ///         if let Some(v) = &self.0 {
+    ///             demand.provide_ref::<str>(v);
+    ///         }
+    ///     }
+    /// }
+    ///
+    /// struct Child {
+    ///     parent: Parent,
+    ///     name: String,
+    /// }
+    ///
+    /// impl Child {
+    ///     // Pretend that this takes a lot of resources to evaluate.
+    ///     fn an_expensive_computation(&self) -> Option<&str> {
+    ///         Some(&self.name)
+    ///     }
+    /// }
+    ///
+    /// impl Provider for Child {
+    ///     fn provide<'a>(&'a self, demand: &mut Demand<'a>) {
+    ///         // In general, we don't know if this call will provide
+    ///         // a `str` reference or not...
+    ///         self.parent.provide(demand);
+    ///
+    ///         // ...so we check to see if the `&str` is needed before
+    ///         // we run our expensive computation.
+    ///         if demand.would_be_satisfied_by_ref_of::<str>() {
+    ///             if let Some(v) = self.an_expensive_computation() {
+    ///                 demand.provide_ref::<str>(v);
+    ///             }
+    ///         }
+    ///
+    ///         // The demand will be satisfied now, regardless of if
+    ///         // the parent provided the reference or we did.
+    ///         assert!(!demand.would_be_satisfied_by_ref_of::<str>());
+    ///     }
+    /// }
+    ///
+    /// let parent = Parent(Some("parent".into()));
+    /// let child = Child { parent, name: "child".into() };
+    /// assert_eq!(Some("parent"), std::any::request_ref::<str>(&child));
+    ///
+    /// let parent = Parent(None);
+    /// let child = Child { parent, name: "child".into() };
+    /// assert_eq!(Some("child"), std::any::request_ref::<str>(&child));
+    /// ```
+    #[unstable(feature = "provide_any", issue = "96024")]
+    pub fn would_be_satisfied_by_ref_of<T>(&self) -> bool
+    where
+        T: ?Sized + 'static,
+    {
+        self.would_be_satisfied_by::<tags::Ref<tags::MaybeSizedValue<T>>>()
+    }
+
+    fn would_be_satisfied_by<I>(&self) -> bool
+    where
+        I: tags::Type<'a>,
+    {
+        matches!(self.0.downcast::<I>(), Some(TaggedOption(None)))
+    }
 }
 
 #[unstable(feature = "provide_any", issue = "96024")]
@@ -1050,6 +1262,21 @@ impl<'a> dyn Erased<'a> + 'a {
     /// Returns some reference to the dynamic value if it is tagged with `I`,
     /// or `None` otherwise.
     #[inline]
+    fn downcast<I>(&self) -> Option<&TaggedOption<'a, I>>
+    where
+        I: tags::Type<'a>,
+    {
+        if self.tag_id() == TypeId::of::<I>() {
+            // SAFETY: Just checked whether we're pointing to an I.
+            Some(unsafe { &*(self as *const Self).cast::<TaggedOption<'a, I>>() })
+        } else {
+            None
+        }
+    }
+
+    /// Returns some mutable reference to the dynamic value if it is tagged with `I`,
+    /// or `None` otherwise.
+    #[inline]
     fn downcast_mut<I>(&mut self) -> Option<&mut TaggedOption<'a, I>>
     where
         I: tags::Type<'a>,
index 6196c4da4e32928670529a82433ff98baaea50ba..1cf306f2103b4ff02ca0dfdeee6918725054fdf1 100644 (file)
@@ -309,8 +309,8 @@ macro_rules! nonzero_unsigned_operations {
     ( $( $Ty: ident($Int: ident); )+ ) => {
         $(
             impl $Ty {
-                /// Add an unsigned integer to a non-zero value.
-                /// Check for overflow and return [`None`] on overflow
+                /// Adds an unsigned integer to a non-zero value.
+                /// Checks for overflow and returns [`None`] on overflow.
                 /// As a consequence, the result cannot wrap to zero.
                 ///
                 ///
@@ -346,7 +346,7 @@ pub const fn checked_add(self, other: $Int) -> Option<$Ty> {
                     }
                 }
 
-                /// Add an unsigned integer to a non-zero value.
+                /// Adds an unsigned integer to a non-zero value.
                 #[doc = concat!("Return [`", stringify!($Int), "::MAX`] on overflow.")]
                 ///
                 /// # Examples
@@ -377,7 +377,7 @@ pub const fn saturating_add(self, other: $Int) -> $Ty {
                     unsafe { $Ty::new_unchecked(self.get().saturating_add(other)) }
                 }
 
-                /// Add an unsigned integer to a non-zero value,
+                /// Adds an unsigned integer to a non-zero value,
                 /// assuming overflow cannot occur.
                 /// Overflow is unchecked, and it is undefined behaviour to overflow
                 /// *even if the result would wrap to a non-zero value*.
@@ -409,7 +409,7 @@ pub const fn saturating_add(self, other: $Int) -> $Ty {
                 }
 
                 /// Returns the smallest power of two greater than or equal to n.
-                /// Check for overflow and return [`None`]
+                /// Checks for overflow and returns [`None`]
                 /// if the next power of two is greater than the type’s maximum value.
                 /// As a consequence, the result cannot wrap to zero.
                 ///
@@ -545,7 +545,7 @@ pub const fn abs(self) -> $Ty {
                 }
 
                 /// Checked absolute value.
-                /// Check for overflow and returns [`None`] if
+                /// Checks for overflow and returns [`None`] if
                 #[doc = concat!("`self == ", stringify!($Int), "::MIN`.")]
                 /// The result cannot be zero.
                 ///
@@ -740,8 +740,8 @@ macro_rules! nonzero_unsigned_signed_operations {
     ( $( $signedness:ident $Ty: ident($Int: ty); )+ ) => {
         $(
             impl $Ty {
-                /// Multiply two non-zero integers together.
-                /// Check for overflow and return [`None`] on overflow.
+                /// Multiplies two non-zero integers together.
+                /// Checks for overflow and returns [`None`] on overflow.
                 /// As a consequence, the result cannot wrap to zero.
                 ///
                 /// # Examples
@@ -777,7 +777,7 @@ pub const fn checked_mul(self, other: $Ty) -> Option<$Ty> {
                     }
                 }
 
-                /// Multiply two non-zero integers together.
+                /// Multiplies two non-zero integers together.
                 #[doc = concat!("Return [`", stringify!($Int), "::MAX`] on overflow.")]
                 ///
                 /// # Examples
@@ -809,7 +809,7 @@ pub const fn saturating_mul(self, other: $Ty) -> $Ty {
                     unsafe { $Ty::new_unchecked(self.get().saturating_mul(other.get())) }
                 }
 
-                /// Multiply two non-zero integers together,
+                /// Multiplies two non-zero integers together,
                 /// assuming overflow cannot occur.
                 /// Overflow is unchecked, and it is undefined behaviour to overflow
                 /// *even if the result would wrap to a non-zero value*.
@@ -849,8 +849,8 @@ pub const fn saturating_mul(self, other: $Ty) -> $Ty {
                     unsafe { $Ty::new_unchecked(self.get().unchecked_mul(other.get())) }
                 }
 
-                /// Raise non-zero value to an integer power.
-                /// Check for overflow and return [`None`] on overflow.
+                /// Raises non-zero value to an integer power.
+                /// Checks for overflow and returns [`None`] on overflow.
                 /// As a consequence, the result cannot wrap to zero.
                 ///
                 /// # Examples
index 8ed0c88808fe27fc47d36b4734dae75a0401e11b..9538b81394957be74e188531cb1d9e9b9f4fa9ad 100644 (file)
@@ -142,7 +142,7 @@ fn provide<'a>(&'a self, demand: &mut Demand<'a>) {
         demand
             .provide_ref::<String>(&self.some_string)
             .provide_ref::<str>(&self.some_string)
-            .provide_value::<String>(|| "bye".to_owned());
+            .provide_value_with::<String>(|| "bye".to_owned());
     }
 }
 
index 4d3736f79146c8df36976ba06397e108ef532af7..07239746258d109adb6130bd10b95cafe5d3190b 100644 (file)
@@ -986,10 +986,10 @@ pub fn set_output_capture(sink: Option<LocalStream>) -> Option<LocalStream> {
 /// otherwise. `label` identifies the stream in a panic message.
 ///
 /// This function is used to print error messages, so it takes extra
-/// care to avoid causing a panic when `local_s` is unusable.
-/// For instance, if the TLS key for the local stream is
-/// already destroyed, or if the local stream is locked by another
-/// thread, it will just fall back to the global stream.
+/// care to avoid causing a panic when `OUTPUT_CAPTURE` is unusable.
+/// For instance, if the TLS key for output capturing is already destroyed, or
+/// if the local stream is in use by another thread, it will just fall back to
+/// the global stream.
 ///
 /// However, if the actual I/O causes an error, this function does panic.
 fn print_to<T>(args: fmt::Arguments<'_>, global_s: fn() -> T, label: &str)
index e0d13cd648c64ceeb003da18d1401e02104bccf2..de851c8fbbed51743776477b338dda1677fd925a 100644 (file)
@@ -192,6 +192,7 @@ unsafe impl<T: ?Sized + Send> Sync for Mutex<T> {}
                       and cause Futures to not implement `Send`"]
 #[stable(feature = "rust1", since = "1.0.0")]
 #[clippy::has_significant_drop]
+#[cfg_attr(not(test), rustc_diagnostic_item = "MutexGuard")]
 pub struct MutexGuard<'a, T: ?Sized + 'a> {
     lock: &'a Mutex<T>,
     poison: poison::Guard,
index 6e4a2cfc82afd07b80b1efd0d3a2e6a47ce2d35a..9ab781561e9b1280460d858bd36d737bfe5aa7e1 100644 (file)
@@ -101,6 +101,7 @@ unsafe impl<T: ?Sized + Send + Sync> Sync for RwLock<T> {}
                       and cause Futures to not implement `Send`"]
 #[stable(feature = "rust1", since = "1.0.0")]
 #[clippy::has_significant_drop]
+#[cfg_attr(not(test), rustc_diagnostic_item = "RwLockReadGuard")]
 pub struct RwLockReadGuard<'a, T: ?Sized + 'a> {
     // NB: we use a pointer instead of `&'a T` to avoid `noalias` violations, because a
     // `Ref` argument doesn't hold immutability for its whole scope, only until it drops.
@@ -130,6 +131,7 @@ unsafe impl<T: ?Sized + Sync> Sync for RwLockReadGuard<'_, T> {}
                       and cause Future's to not implement `Send`"]
 #[stable(feature = "rust1", since = "1.0.0")]
 #[clippy::has_significant_drop]
+#[cfg_attr(not(test), rustc_diagnostic_item = "RwLockWriteGuard")]
 pub struct RwLockWriteGuard<'a, T: ?Sized + 'a> {
     lock: &'a RwLock<T>,
     poison: poison::Guard,
index fe1b00a90fce25d229dfb62b76bc694ada48a86d..cc08ae5f99f0e80d03c36998ad02df043dcf10d0 100644 (file)
@@ -793,6 +793,8 @@ class RustBuild(object):
 
     def check_vendored_status(self):
         """Check that vendoring is configured properly"""
+        # keep this consistent with the equivalent check in rustbuild:
+        # https://github.com/rust-lang/rust/blob/a8a33cf27166d3eabaffc58ed3799e054af3b0c6/src/bootstrap/lib.rs#L399-L405
         if 'SUDO_USER' in os.environ and not self.use_vendored_sources:
             if os.getuid() == 0:
                 self.use_vendored_sources = True
index c3aabb16a9b9af131c70095d4ecc6e667efe5a07..c13e83f6c86126c82563b80f224f6252bf6dfc2e 100644 (file)
@@ -1281,7 +1281,9 @@ fn run(self, builder: &Builder<'_>) -> Compiler {
                 compiler: build_compiler,
                 target: target_compiler.host,
             });
-            builder.copy(&lld_wrapper_exe, &gcc_ld_dir.join(exe("ld", target_compiler.host)));
+            for name in crate::LLD_FILE_NAMES {
+                builder.copy(&lld_wrapper_exe, &gcc_ld_dir.join(exe(name, target_compiler.host)));
+            }
         }
 
         if builder.config.rust_codegen_backends.contains(&INTERNER.intern_str("llvm")) {
index 13e3049f2c81ff001a9bfbbce5efb075c676772c..7c062460c4f16e8eb21475c0e5da443bbc015f64 100644 (file)
@@ -388,6 +388,7 @@ fn eq(&self, other: &&str) -> bool {
 pub struct Target {
     /// Some(path to llvm-config) if using an external LLVM.
     pub llvm_config: Option<PathBuf>,
+    pub llvm_has_rust_patches: Option<bool>,
     /// Some(path to FileCheck) if one was specified.
     pub llvm_filecheck: Option<PathBuf>,
     pub llvm_libunwind: Option<LlvmLibunwind>,
@@ -733,6 +734,7 @@ struct TomlTarget {
         default_linker: Option<PathBuf> = "default-linker",
         linker: Option<String> = "linker",
         llvm_config: Option<String> = "llvm-config",
+        llvm_has_rust_patches: Option<bool> = "llvm-has-rust-patches",
         llvm_filecheck: Option<String> = "llvm-filecheck",
         llvm_libunwind: Option<String> = "llvm-libunwind",
         android_ndk: Option<String> = "android-ndk",
@@ -1109,6 +1111,7 @@ pub fn parse(args: &[String]) -> Config {
                 if let Some(ref s) = cfg.llvm_config {
                     target.llvm_config = Some(config.src.join(s));
                 }
+                target.llvm_has_rust_patches = cfg.llvm_has_rust_patches;
                 if let Some(ref s) = cfg.llvm_filecheck {
                     target.llvm_filecheck = Some(config.src.join(s));
                 }
index c01afa1fd3b75c3fbc07f38f4fcac5c158846e35..1a59b3958f1060844999fa0dac6ab6e7f30c3807 100644 (file)
@@ -423,8 +423,11 @@ fn prepare_image(builder: &Builder<'_>, compiler: Compiler, image: &Path) {
                 let gcc_lld_src_dir = src_dir.join("gcc-ld");
                 let gcc_lld_dst_dir = dst_dir.join("gcc-ld");
                 t!(fs::create_dir(&gcc_lld_dst_dir));
-                let exe_name = exe("ld", compiler.host);
-                builder.copy(&gcc_lld_src_dir.join(&exe_name), &gcc_lld_dst_dir.join(&exe_name));
+                for name in crate::LLD_FILE_NAMES {
+                    let exe_name = exe(name, compiler.host);
+                    builder
+                        .copy(&gcc_lld_src_dir.join(&exe_name), &gcc_lld_dst_dir.join(&exe_name));
+                }
             }
 
             // Man pages
index 2852442d0be6fbb7986a84f211a84a6494cde744..f909ecc0ab858404403aaa3edb7df83d6043df97 100644 (file)
@@ -793,7 +793,7 @@ fn run(self, builder: &Builder<'_>) {
         t!(fs::create_dir_all(&out));
         let mut index = tool::ErrorIndex::command(builder);
         index.arg("html");
-        index.arg(out.join("error-index.html"));
+        index.arg(out);
         index.arg(&builder.version);
 
         builder.run(&mut index);
index d111d945d6f2f5b439dd3c76aaf71d16e655b7d5..cc0cf12bd187a7fc48ed6c06bfa09a9af5e064b0 100644 (file)
 use std::process::Command;
 use std::str;
 
+use config::Target;
 use filetime::FileTime;
 use once_cell::sync::OnceCell;
 
@@ -186,6 +187,9 @@ pub unsafe fn setup(_build: &mut crate::Build) {}
     "opt",           // used to optimize LLVM bytecode
 ];
 
+/// LLD file names for all flavors.
+const LLD_FILE_NAMES: &[&str] = &["ld.lld", "ld64.lld", "lld-link", "wasm-ld"];
+
 pub const VERSION: usize = 2;
 
 /// Extra --check-cfg to add when building
@@ -395,13 +399,18 @@ pub fn new(config: Config) -> Build {
         let src = config.src.clone();
         let out = config.out.clone();
 
+        #[cfg(unix)]
+        // keep this consistent with the equivalent check in x.py:
+        // https://github.com/rust-lang/rust/blob/a8a33cf27166d3eabaffc58ed3799e054af3b0c6/src/bootstrap/bootstrap.py#L796-L797
         let is_sudo = match env::var_os("SUDO_USER") {
-            Some(sudo_user) => match env::var_os("USER") {
-                Some(user) => user != sudo_user,
-                None => false,
-            },
+            Some(_sudo_user) => {
+                let uid = unsafe { libc::getuid() };
+                uid == 0
+            }
             None => false,
         };
+        #[cfg(not(unix))]
+        let is_sudo = false;
 
         let ignore_git = config.ignore_git;
         let rust_info = channel::GitInfo::new(ignore_git, &src);
@@ -834,12 +843,13 @@ fn md_doc_out(&self, target: TargetSelection) -> Interned<PathBuf> {
     ///
     /// If no custom `llvm-config` was specified then Rust's llvm will be used.
     fn is_rust_llvm(&self, target: TargetSelection) -> bool {
-        if self.config.llvm_from_ci && target == self.config.build {
-            return true;
-        }
-
         match self.config.target_config.get(&target) {
-            Some(ref c) => c.llvm_config.is_none(),
+            Some(Target { llvm_has_rust_patches: Some(patched), .. }) => *patched,
+            Some(Target { llvm_config, .. }) => {
+                // If the user set llvm-config we assume Rust is not patched,
+                // but first check to see if it was configured by llvm-from-ci.
+                (self.config.llvm_from_ci && target == self.config.build) || llvm_config.is_none()
+            }
             None => true,
         }
     }
index d0d367b39b493850cfce53e8095f2f05f7127905..7a875c960e13312d77d11983c0f4bab304b4c554 100644 (file)
@@ -1,5 +1,6 @@
-FROM ubuntu:16.04
+FROM ubuntu:22.04
 
+ARG DEBIAN_FRONTEND=noninteractive
 COPY scripts/android-base-apt-get.sh /scripts/
 RUN sh /scripts/android-base-apt-get.sh
 
@@ -13,7 +14,7 @@ RUN dpkg --add-architecture i386 && \
   libgl1-mesa-glx \
   libpulse0 \
   libstdc++6:i386 \
-  openjdk-9-jre-headless \
+  openjdk-8-jre-headless \
   tzdata \
   wget \
   python3
@@ -29,20 +30,12 @@ ENV PATH=$PATH:/android/sdk/platform-tools
 
 ENV TARGETS=arm-linux-androideabi
 
-# We are intentionally allowing an old toolchain on this builder (and that's
-# incompatible with LLVM downloads today).
-ENV NO_DOWNLOAD_CI_LLVM 1
-
-ENV RUST_CONFIGURE_ARGS --arm-linux-androideabi-ndk=/android/ndk/arm-14 \
-    --set llvm.allow-old-toolchain
+ENV RUST_CONFIGURE_ARGS --arm-linux-androideabi-ndk=/android/ndk/arm-14
 
 ENV SCRIPT python3 ../x.py --stage 2 test --host='' --target $TARGETS
 
 COPY scripts/sccache.sh /scripts/
 RUN sh /scripts/sccache.sh
 
-COPY scripts/cmake.sh /scripts/
-RUN /scripts/cmake.sh
-
 COPY scripts/android-start-emulator.sh /scripts/
 ENTRYPOINT ["/scripts/android-start-emulator.sh"]
index c98fa496d4861d22c274e17d3f38c2ca12fc7ccf..2328db4ab8b1d126dd774a67a744afb990bde1e0 100644 (file)
@@ -1,4 +1,4 @@
-FROM ubuntu:16.04
+FROM ubuntu:22.04
 
 COPY scripts/android-base-apt-get.sh /scripts/
 RUN sh /scripts/android-base-apt-get.sh
@@ -32,13 +32,9 @@ ENV RUST_CONFIGURE_ARGS \
       --i686-linux-android-ndk=/android/ndk/x86-14 \
       --aarch64-linux-android-ndk=/android/ndk/arm64-21 \
       --x86_64-linux-android-ndk=/android/ndk/x86_64-21 \
-      --disable-docs \
-      --set llvm.allow-old-toolchain
+      --disable-docs
 
 ENV SCRIPT python3 ../x.py dist --host='' --target $TARGETS
 
 COPY scripts/sccache.sh /scripts/
 RUN sh /scripts/sccache.sh
-
-COPY scripts/cmake.sh /scripts/
-RUN /scripts/cmake.sh
index f1761f80643ba32321af88365051aac4c49b6c52..22e2e243e430a0d7a9d103b3bcdb63ed697c2691 100644 (file)
@@ -10,6 +10,7 @@ apt-get install -y --no-install-recommends \
   g++ \
   git \
   libssl-dev \
+  libncurses5 \
   make \
   ninja-build \
   pkg-config \
diff --git a/src/doc/rustc/src/platform-support/armv4t-none-eabi.md b/src/doc/rustc/src/platform-support/armv4t-none-eabi.md
new file mode 100644 (file)
index 0000000..cf831e1
--- /dev/null
@@ -0,0 +1,70 @@
+# armv4t-none-eabi
+
+Tier 3
+
+Bare-metal target for any cpu in the ARMv4T architecture family, supporting
+ARM/Thumb code interworking (aka `a32`/`t32`), with ARM code as the default code
+generation.
+
+In particular this supports the Gameboy Advance (GBA), but there's nothing GBA
+specific with this target, so any ARMv4T device should work fine.
+
+## Target Maintainers
+
+* [@Lokathor](https://github.com/lokathor)
+
+## Requirements
+
+The target is cross-compiled, and uses static linking.
+
+The linker that comes with rustc cannot link for this platform (the platform is
+too old). You will need the `arm-none-eabi-ld` linker from a GNU Binutils
+targeting ARM. This can be obtained for Windows/Mac/Linux from the [ARM
+Developer Website][arm-dev], or possibly from your OS's package manager.
+
+[arm-dev]: https://developer.arm.com/Tools%20and%20Software/GNU%20Toolchain
+
+This target doesn't provide a linker script, you'll need to bring your own
+according to the specific device you want to target. Pass
+`-Clink-arg=-Tyour_script.ld` as a rustc argument to make the linker use
+`your_script.ld` during linking.
+
+## Building Rust Programs
+
+Because it is Tier 3, rust does not yet ship pre-compiled artifacts for this target.
+
+Just use the `build-std` nightly cargo feature to build the `core` library. You
+can pass this as a command line argument to cargo, or your `.cargo/config.toml`
+file might include the following lines:
+
+```toml
+[unstable]
+build-std = ["core"]
+```
+
+Most of `core` should work as expected, with the following notes:
+* the target is "soft float", so `f32` and `f64` operations are emulated in
+  software.
+* integer division is also emulated in software.
+* the target is old enough that it doesn't have atomic instructions.
+
+Rust programs are output as ELF files.
+
+For running on hardware, you'll generally need to extract the "raw" program code
+out of the ELF and into a file of its own. The `objcopy` program provided as
+part of the GNU Binutils can do this:
+
+```shell
+arm-none-eabi-objcopy --output-target binary [in_file] [out_file]
+```
+
+## Testing
+
+This is a cross-compiled target that you will need to emulate during testing.
+
+Because this is a device-agnostic target, and the exact emulator that you'll
+need depends on the specific device you want to run your code on.
+
+For example, when programming for the Gameboy Advance, the
+[mgba-test-runner](https://github.com/agbrs/agb) program could be used to make a
+normal set of rust tests be run within the `mgba` emulator.
diff --git a/src/doc/rustc/src/platform-support/armv4t_none_eabi.md b/src/doc/rustc/src/platform-support/armv4t_none_eabi.md
deleted file mode 100644 (file)
index cf831e1..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-# armv4t-none-eabi
-
-Tier 3
-
-Bare-metal target for any cpu in the ARMv4T architecture family, supporting
-ARM/Thumb code interworking (aka `a32`/`t32`), with ARM code as the default code
-generation.
-
-In particular this supports the Gameboy Advance (GBA), but there's nothing GBA
-specific with this target, so any ARMv4T device should work fine.
-
-## Target Maintainers
-
-* [@Lokathor](https://github.com/lokathor)
-
-## Requirements
-
-The target is cross-compiled, and uses static linking.
-
-The linker that comes with rustc cannot link for this platform (the platform is
-too old). You will need the `arm-none-eabi-ld` linker from a GNU Binutils
-targeting ARM. This can be obtained for Windows/Mac/Linux from the [ARM
-Developer Website][arm-dev], or possibly from your OS's package manager.
-
-[arm-dev]: https://developer.arm.com/Tools%20and%20Software/GNU%20Toolchain
-
-This target doesn't provide a linker script, you'll need to bring your own
-according to the specific device you want to target. Pass
-`-Clink-arg=-Tyour_script.ld` as a rustc argument to make the linker use
-`your_script.ld` during linking.
-
-## Building Rust Programs
-
-Because it is Tier 3, rust does not yet ship pre-compiled artifacts for this target.
-
-Just use the `build-std` nightly cargo feature to build the `core` library. You
-can pass this as a command line argument to cargo, or your `.cargo/config.toml`
-file might include the following lines:
-
-```toml
-[unstable]
-build-std = ["core"]
-```
-
-Most of `core` should work as expected, with the following notes:
-* the target is "soft float", so `f32` and `f64` operations are emulated in
-  software.
-* integer division is also emulated in software.
-* the target is old enough that it doesn't have atomic instructions.
-
-Rust programs are output as ELF files.
-
-For running on hardware, you'll generally need to extract the "raw" program code
-out of the ELF and into a file of its own. The `objcopy` program provided as
-part of the GNU Binutils can do this:
-
-```shell
-arm-none-eabi-objcopy --output-target binary [in_file] [out_file]
-```
-
-## Testing
-
-This is a cross-compiled target that you will need to emulate during testing.
-
-Because this is a device-agnostic target, and the exact emulator that you'll
-need depends on the specific device you want to run your code on.
-
-For example, when programming for the Gameboy Advance, the
-[mgba-test-runner](https://github.com/agbrs/agb) program could be used to make a
-normal set of rust tests be run within the `mgba` emulator.
index c2a1613f288c5c8a7db18addef22bb474d17209b..53a510f080ece9cd899052107f28de1fad2a15ba 100644 (file)
@@ -79,7 +79,7 @@ the following commands:
 
 ```sh
 rustup target add x86_64-fuchsia
-rustup target add aarch_64-fuchsia
+rustup target add aarch64-fuchsia
 ```
 
 After installing our Fuchsia targets, we can now compile a Rust binary that targets
@@ -125,13 +125,20 @@ during compilation:
 [target.x86_64-fuchsia]
 
 rustflags = [
-    "-Lnative", "<SDK_PATH>/arch/x64/sysroot/lib",
-    "-Lnative", "<SDK_PATH>/arch/x64/lib"
+    "-Lnative=<SDK_PATH>/arch/x64/lib",
+    "-Lnative=<SDK_PATH>/arch/x64/sysroot/lib"
 ]
 ```
 
 *Note: Make sure to fill out `<SDK_PATH>` with the path to the downloaded [Fuchsia SDK].*
 
+These options configure the following:
+
+* `-Lnative=${SDK_PATH}/arch/${ARCH}/lib`: Link against Fuchsia libraries from
+  the SDK
+* `-Lnative=${SDK_PATH}/arch/${ARCH}/sysroot/lib`: Link against Fuchsia kernel
+  libraries from the SDK
+
 In total, our new project will look like:
 
 **Current directory structure**
@@ -368,6 +375,7 @@ language called CML. The Fuchsia devsite contains an [overview of CML] and a
 }
 ```
 
+**Current directory structure**
 ```txt
 hello_fuchsia/
 ┗━ pkg/
@@ -386,6 +394,9 @@ ${SDK_PATH}/tools/${ARCH}/cmc compile \
     -o pkg/meta/hello_fuchsia.cm
 ```
 
+*Note: `--includepath` tells the compiler where to look for `include`s from our CML.
+In our case, we're only using `syslog/client.shard.cml`.*
+
 **Current directory structure**
 ```txt
 hello_fuchsia/
@@ -397,19 +408,16 @@ hello_fuchsia/
    ┗━ hello_fuchsia.cml
 ```
 
-*Note: `--includepath` tells the compiler where to look for `include`s from our CML.
-In our case, we're only using `syslog/client.shard.cml`.*
-
 ### Building a Fuchsia package
 
 Next, we'll build a package manifest as defined by our manifest:
 
 ```sh
 ${SDK_PATH}/tools/${ARCH}/pm \
-    -o hello_fuchsia_manifest \
+    -o pkg/hello_fuchsia_manifest \
     -m pkg/hello_fuchsia.manifest \
     build \
-    -output-package-manifest hello_fuchsia_package_manifest
+    -output-package-manifest pkg/hello_fuchsia_package_manifest
 ```
 
 This will produce `pkg/hello_fuchsia_manifest/` which is a package manifest we can
@@ -469,15 +477,15 @@ We can publish our new package to that repository with:
 
 ```sh
 ${SDK_PATH}/tools/${ARCH}/pm publish \
-    -repo repo \
-    -lp -f <(echo "hello_fuchsia_package_manifest")
+    -repo pkg/repo \
+    -lp -f <(echo "pkg/hello_fuchsia_package_manifest")
 ```
 
 Then we can add the repository to `ffx`'s package server as `hello-fuchsia` using:
 
 ```sh
 ${SDK_PATH}/tools/${ARCH}/ffx repository add-from-pm \
-    repo \
+    pkg/repo \
     -r hello-fuchsia
 ```
 
index 6f49f00f93e5eb98abd62017ee1adaf0c7ca62c3..be10a5c101f7ffa3e5ad5c9aa028f40201a07d45 100644 (file)
@@ -349,8 +349,7 @@ pub(crate) fn print_where_clause<'a, 'tcx: 'a>(
         let where_preds = comma_sep(where_predicates, false);
         let clause = if f.alternate() {
             if ending == Ending::Newline {
-                // add a space so stripping <br> tags and breaking spaces still renders properly
-                format!(" where{where_preds}, ")
+                format!(" where{where_preds},")
             } else {
                 format!(" where{where_preds}")
             }
@@ -364,20 +363,16 @@ pub(crate) fn print_where_clause<'a, 'tcx: 'a>(
 
             if ending == Ending::Newline {
                 let mut clause = "&nbsp;".repeat(indent.saturating_sub(1));
-                // add a space so stripping <br> tags and breaking spaces still renders properly
-                write!(
-                    clause,
-                    " <span class=\"where fmt-newline\">where{where_preds},&nbsp;</span>"
-                )?;
+                write!(clause, "<span class=\"where fmt-newline\">where{where_preds},</span>")?;
                 clause
             } else {
                 // insert a <br> tag after a single space but before multiple spaces at the start
                 if indent == 0 {
-                    format!(" <br><span class=\"where\">where{where_preds}</span>")
+                    format!("<br><span class=\"where\">where{where_preds}</span>")
                 } else {
                     let mut clause = br_with_padding;
                     clause.truncate(clause.len() - 5 * "&nbsp;".len());
-                    write!(clause, " <span class=\"where\">where{where_preds}</span>")?;
+                    write!(clause, "<span class=\"where\">where{where_preds}</span>")?;
                     clause
                 }
             }
index eff34047e3c8fb93ac5bfa1b2f72351ecfc892cc..7577c71962388ebc2617ebebd3b722d0ff55af10 100644 (file)
@@ -1737,8 +1737,8 @@ pub(crate) fn render_impl_summary(
     // in documentation pages for trait with automatic implementations like "Send" and "Sync".
     aliases: &[String],
 ) {
-    let id =
-        cx.derive_id(get_id_for_impl(&i.inner_impl().for_, i.inner_impl().trait_.as_ref(), cx));
+    let inner_impl = i.inner_impl();
+    let id = cx.derive_id(get_id_for_impl(&inner_impl.for_, inner_impl.trait_.as_ref(), cx));
     let aliases = if aliases.is_empty() {
         String::new()
     } else {
@@ -1750,9 +1750,9 @@ pub(crate) fn render_impl_summary(
     write!(w, "<h3 class=\"code-header in-band\">");
 
     if let Some(use_absolute) = use_absolute {
-        write!(w, "{}", i.inner_impl().print(use_absolute, cx));
+        write!(w, "{}", inner_impl.print(use_absolute, cx));
         if show_def_docs {
-            for it in &i.inner_impl().items {
+            for it in &inner_impl.items {
                 if let clean::AssocTypeItem(ref tydef, ref _bounds) = *it.kind {
                     w.write_str("<span class=\"where fmt-newline\">  ");
                     assoc_type(
@@ -1770,11 +1770,11 @@ pub(crate) fn render_impl_summary(
             }
         }
     } else {
-        write!(w, "{}", i.inner_impl().print(false, cx));
+        write!(w, "{}", inner_impl.print(false, cx));
     }
     write!(w, "</h3>");
 
-    let is_trait = i.inner_impl().trait_.is_some();
+    let is_trait = inner_impl.trait_.is_some();
     if is_trait {
         if let Some(portability) = portability(&i.impl_item, Some(parent)) {
             write!(w, "<span class=\"item-info\">{}</span>", portability);
index c117e3ac40dab57e22db93ab76b4e1046ce43edb..c7a9f247e208421a42c982aa8b47f6fa8ed11390 100644 (file)
@@ -207,7 +207,6 @@ h1, h2, h3, h4, h5, h6,
 a.source,
 .search-input,
 .search-results .result-name,
-.content table td:first-child > a,
 .item-left > a,
 .out-of-band,
 span.since,
@@ -216,7 +215,6 @@ details.rustdoc-toggle > summary::before,
 div.impl-items > div:not(.docblock):not(.item-info),
 .content ul.crate a.crate,
 a.srclink,
-#main-content > .since,
 #help-button > button,
 details.rustdoc-toggle.top-doc > summary,
 details.rustdoc-toggle.top-doc > summary::before,
@@ -759,14 +757,6 @@ pre, .rustdoc.source .example-wrap {
        margin-bottom: 15px;
 }
 
-.content .docblock > .impl-items {
-       margin-left: 20px;
-       margin-top: -34px;
-}
-.content .docblock >.impl-items table td {
-       padding: 0;
-}
-
 .item-info {
        display: block;
 }
index 39d3b43cf32e2aa1c5e5d083a1c04b83fb709a3a..c27f0ce18c1414d027453b4e8d2799105c980cfa 100644 (file)
@@ -750,7 +750,7 @@ fn resolve_associated_trait_item<'a>(
 ///
 /// This is just a wrapper around [`TyCtxt::impl_item_implementor_ids()`] and
 /// [`TyCtxt::associated_item()`] (with some helpful logging added).
-#[instrument(level = "debug", skip(tcx))]
+#[instrument(level = "debug", skip(tcx), ret)]
 fn trait_assoc_to_impl_assoc_item<'tcx>(
     tcx: TyCtxt<'tcx>,
     impl_id: DefId,
@@ -760,9 +760,7 @@ fn trait_assoc_to_impl_assoc_item<'tcx>(
     debug!(?trait_to_impl_assoc_map);
     let impl_assoc_id = *trait_to_impl_assoc_map.get(&trait_assoc_id)?;
     debug!(?impl_assoc_id);
-    let impl_assoc = tcx.associated_item(impl_assoc_id);
-    debug!(?impl_assoc);
-    Some(impl_assoc)
+    Some(tcx.associated_item(impl_assoc_id))
 }
 
 /// Given a type, return all trait impls in scope in `module` for that type.
index 2b12d118bca0e3968e0598e68a2a7a008fcb2599..765f7c61bd392dc433d5e2e5aa2c55ea95828992 100644 (file)
@@ -3,7 +3,7 @@
 
 use crate::clean::cfg::Cfg;
 use crate::clean::inline::{load_attrs, merge_attrs};
-use crate::clean::{Crate, Item};
+use crate::clean::{Crate, Item, ItemKind};
 use crate::core::DocContext;
 use crate::fold::DocFolder;
 use crate::passes::Pass;
@@ -26,30 +26,50 @@ struct CfgPropagator<'a, 'tcx> {
     cx: &'a mut DocContext<'tcx>,
 }
 
-impl<'a, 'tcx> DocFolder for CfgPropagator<'a, 'tcx> {
-    fn fold_item(&mut self, mut item: Item) -> Option<Item> {
-        let old_parent_cfg = self.parent_cfg.clone();
+impl<'a, 'tcx> CfgPropagator<'a, 'tcx> {
+    // Some items need to merge their attributes with their parents' otherwise a few of them
+    // (mostly `cfg` ones) will be missing.
+    fn merge_with_parent_attributes(&mut self, item: &mut Item) {
+        let check_parent = match &*item.kind {
+            // impl blocks can be in different modules with different cfg and we need to get them
+            // as well.
+            ItemKind::ImplItem(_) => false,
+            kind if kind.is_non_assoc() => true,
+            _ => return,
+        };
 
-        if item.kind.is_non_assoc() &&
-            let Some(def_id) = item.item_id.as_def_id().and_then(|def_id| def_id.as_local()) {
-            let hir = self.cx.tcx.hir();
-            let hir_id = hir.local_def_id_to_hir_id(def_id);
+        let Some(def_id) = item.item_id.as_def_id().and_then(|def_id| def_id.as_local())
+            else { return };
+
+        let hir = self.cx.tcx.hir();
+        let hir_id = hir.local_def_id_to_hir_id(def_id);
+
+        if check_parent {
             let expected_parent = hir.get_parent_item(hir_id);
+            // If parents are different, it means that `item` is a reexport and we need
+            // to compute the actual `cfg` by iterating through its "real" parents.
+            if self.parent == Some(expected_parent) {
+                return;
+            }
+        }
 
-            // If parents are different, it means that `item` is a reexport and we need to compute
-            // the actual `cfg` by iterating through its "real" parents.
-            if self.parent != Some(expected_parent) {
-                let mut attrs = Vec::new();
-                for (parent_hir_id, _) in hir.parent_iter(hir_id) {
-                    if let Some(def_id) = hir.opt_local_def_id(parent_hir_id) {
-                        attrs.extend_from_slice(load_attrs(self.cx, def_id.to_def_id()));
-                    }
-                }
-                let (_, cfg) =
-                    merge_attrs(self.cx, None, item.attrs.other_attrs.as_slice(), Some(&attrs));
-                item.cfg = cfg;
+        let mut attrs = Vec::new();
+        for (parent_hir_id, _) in hir.parent_iter(hir_id) {
+            if let Some(def_id) = hir.opt_local_def_id(parent_hir_id) {
+                attrs.extend_from_slice(load_attrs(self.cx, def_id.to_def_id()));
             }
         }
+        let (_, cfg) = merge_attrs(self.cx, None, item.attrs.other_attrs.as_slice(), Some(&attrs));
+        item.cfg = cfg;
+    }
+}
+
+impl<'a, 'tcx> DocFolder for CfgPropagator<'a, 'tcx> {
+    fn fold_item(&mut self, mut item: Item) -> Option<Item> {
+        let old_parent_cfg = self.parent_cfg.clone();
+
+        self.merge_with_parent_attributes(&mut item);
+
         let new_cfg = match (self.parent_cfg.take(), item.cfg.take()) {
             (None, None) => None,
             (Some(rc), None) | (None, Some(rc)) => Some(rc),
index 83ed3752a824cd541aa608be7c46fb97b1d234c3..a9d768f0149d6280d561806d47bb3d038f50e414 100644 (file)
@@ -91,7 +91,7 @@ fn fold_item(&mut self, i: Item) -> Option<Item> {
             clean::ExternCrateItem { .. } => {}
             clean::ImportItem(ref imp) => {
                 // Because json doesn't inline imports from private modules, we need to mark
-                // the imported item as retained so it's impls won't be stripped.i
+                // the imported item as retained so it's impls won't be stripped.
                 //
                 // FIXME: Is it necessary to check for json output here: See
                 // https://github.com/rust-lang/rust/pull/100325#discussion_r941495215
index ca298e9211d4864400aa0116975c4c86ad5c9f04..a6a56f3a95d18b302869fac8672cd620e0b68829 100644 (file)
@@ -1,4 +1,6 @@
-// compile-flags: -Z mir-opt-level=4 -Zunsound-mir-opts
+// unit-test: EarlyOtherwiseBranch
+
+// FIXME: This test was broken by the derefer change.
 
 // example from #68867
 type CSSFloat = f32;
@@ -11,7 +13,6 @@ pub enum ViewportPercentageLength {
 }
 
 // EMIT_MIR early_otherwise_branch_68867.try_sum.EarlyOtherwiseBranch.diff
-// EMIT_MIR early_otherwise_branch_68867.try_sum EarlyOtherwiseBranch.before SimplifyConstCondition-final.after
 #[no_mangle]
 pub extern "C" fn try_sum(
     x: &ViewportPercentageLength,
diff --git a/src/test/mir-opt/early_otherwise_branch_68867.try_sum.EarlyOtherwiseBranch.before-SimplifyConstCondition-final.after.diff b/src/test/mir-opt/early_otherwise_branch_68867.try_sum.EarlyOtherwiseBranch.before-SimplifyConstCondition-final.after.diff
deleted file mode 100644 (file)
index 8b37fb7..0000000
+++ /dev/null
@@ -1,322 +0,0 @@
-- // MIR for `try_sum` before EarlyOtherwiseBranch
-+ // MIR for `try_sum` after SimplifyConstCondition-final
-  
-  fn try_sum(_1: &ViewportPercentageLength, _2: &ViewportPercentageLength) -> Result<ViewportPercentageLength, ()> {
-      debug x => _1;                       // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+1:5: +1:6
-      debug other => _2;                   // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+2:5: +2:10
-      let mut _0: std::result::Result<ViewportPercentageLength, ()>; // return place in scope 0 at $DIR/early_otherwise_branch_68867.rs:+3:6: +3:42
-      let mut _3: ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:8: +11:6
-      let mut _4: (&ViewportPercentageLength, &ViewportPercentageLength); // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _5: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:15: +5:16
-      let mut _6: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:18: +5:23
-      let mut _7: isize;                   // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:21: +6:30
-      let mut _8: isize;                   // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:21: +7:30
-      let mut _9: isize;                   // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:23: +8:34
-      let mut _10: isize;                  // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:23: +9:34
-      let mut _11: isize;                  // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:11: +6:18
-      let _12: f32;                        // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:14: +6:17
-      let _13: f32;                        // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:24: +6:29
-      let mut _14: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:38: +6:49
-      let mut _15: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:38: +6:41
-      let mut _16: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:44: +6:49
-      let _17: f32;                        // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:14: +7:17
-      let _18: f32;                        // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:24: +7:29
-      let mut _19: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:38: +7:49
-      let mut _20: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:38: +7:41
-      let mut _21: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:44: +7:49
-      let _22: f32;                        // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:16: +8:19
-      let _23: f32;                        // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:28: +8:33
-      let mut _24: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:44: +8:55
-      let mut _25: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:44: +8:47
-      let mut _26: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:50: +8:55
-      let _27: f32;                        // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:16: +9:19
-      let _28: f32;                        // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:28: +9:33
-      let mut _29: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:44: +9:55
-      let mut _30: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:44: +9:47
-      let mut _31: f32;                    // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:50: +9:55
-      let mut _32: !;                      // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:14: +10:28
-      let mut _33: ();                     // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:25: +10:27
-      let mut _34: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _35: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _36: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _37: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _38: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _39: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _40: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _41: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _42: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _43: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _44: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _45: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      let mut _46: &ViewportPercentageLength; // in scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-      scope 1 {
--         debug one => _12;                // in scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:14: +6:17
--         debug other => _13;              // in scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:24: +6:29
-+         debug one => _15;                // in scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:14: +6:17
-+         debug other => _16;              // in scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:24: +6:29
-      }
-      scope 2 {
--         debug one => _17;                // in scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:14: +7:17
--         debug other => _18;              // in scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:24: +7:29
-+         debug one => _20;                // in scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:14: +7:17
-+         debug other => _21;              // in scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:24: +7:29
-      }
-      scope 3 {
--         debug one => _22;                // in scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:16: +8:19
--         debug other => _23;              // in scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:28: +8:33
-+         debug one => _25;                // in scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:16: +8:19
-+         debug other => _26;              // in scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:28: +8:33
-      }
-      scope 4 {
--         debug one => _27;                // in scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:16: +9:19
--         debug other => _28;              // in scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:28: +9:33
-+         debug one => _30;                // in scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:16: +9:19
-+         debug other => _31;              // in scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:28: +9:33
-      }
-  
-      bb0: {
--         StorageLive(_3);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:8: +11:6
--         StorageLive(_4);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
--         StorageLive(_5);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:15: +5:16
--         _5 = _1;                         // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:15: +5:16
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:8: +11:6
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:15: +5:16
-+         (_4.0: &ViewportPercentageLength) = _1; // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:15: +5:16
-          StorageLive(_6);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:18: +5:23
-          _6 = _2;                         // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:18: +5:23
-          Deinit(_4);                      // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
--         (_4.0: &ViewportPercentageLength) = move _5; // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          (_4.1: &ViewportPercentageLength) = move _6; // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          StorageDead(_6);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:23: +5:24
--         StorageDead(_5);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:23: +5:24
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:23: +5:24
-          _34 = deref_copy (_4.0: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          _11 = discriminant((*_34));      // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          switchInt(move _11) -> [0_isize: bb1, 1_isize: bb3, 2_isize: bb4, 3_isize: bb5, otherwise: bb11]; // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:8: +5:24
-      }
-  
-      bb1: {
-          _35 = deref_copy (_4.1: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          _7 = discriminant((*_35));       // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          switchInt(move _7) -> [0_isize: bb6, otherwise: bb2]; // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:8: +5:24
-      }
-  
-      bb2: {
-          StorageLive(_33);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:25: +10:27
-          nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:25: +10:27
-          Deinit(_0);                      // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:21: +10:28
-          nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:21: +10:28
-          discriminant(_0) = 1;            // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:21: +10:28
-          StorageDead(_33);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:27: +10:28
--         StorageDead(_3);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+11:6: +11:7
--         StorageDead(_4);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:1: +12:2
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+11:6: +11:7
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:1: +12:2
-          return;                          // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:2: +12:2
-      }
-  
-      bb3: {
-          _36 = deref_copy (_4.1: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          _8 = discriminant((*_36));       // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          switchInt(move _8) -> [1_isize: bb7, otherwise: bb2]; // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:8: +5:24
-      }
-  
-      bb4: {
-          _37 = deref_copy (_4.1: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          _9 = discriminant((*_37));       // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          switchInt(move _9) -> [2_isize: bb8, otherwise: bb2]; // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:8: +5:24
-      }
-  
-      bb5: {
-          _38 = deref_copy (_4.1: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          _10 = discriminant((*_38));      // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          switchInt(move _10) -> [3_isize: bb9, otherwise: bb2]; // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:8: +5:24
-      }
-  
-      bb6: {
--         StorageLive(_12);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:14: +6:17
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:14: +6:17
-          _39 = deref_copy (_4.0: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:14: +6:17
--         _12 = (((*_39) as Vw).0: f32);   // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:14: +6:17
--         StorageLive(_13);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:24: +6:29
-+         _15 = (((*_39) as Vw).0: f32);   // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:14: +6:17
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:24: +6:29
-          _40 = deref_copy (_4.1: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:24: +6:29
--         _13 = (((*_40) as Vw).0: f32);   // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:24: +6:29
--         StorageLive(_14);                // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:38: +6:49
--         StorageLive(_15);                // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:38: +6:41
--         _15 = _12;                       // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:38: +6:41
--         StorageLive(_16);                // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:44: +6:49
--         _16 = _13;                       // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:44: +6:49
--         _14 = Add(move _15, move _16);   // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:38: +6:49
--         StorageDead(_16);                // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:48: +6:49
--         StorageDead(_15);                // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:48: +6:49
--         Deinit(_3);                      // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:35: +6:50
--         ((_3 as Vw).0: f32) = move _14;  // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:35: +6:50
--         discriminant(_3) = 0;            // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:35: +6:50
--         StorageDead(_14);                // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:49: +6:50
--         StorageDead(_13);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:49: +6:50
--         StorageDead(_12);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:49: +6:50
-+         _16 = (((*_40) as Vw).0: f32);   // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:24: +6:29
-+         nop;                             // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:38: +6:49
-+         nop;                             // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:38: +6:41
-+         nop;                             // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:38: +6:41
-+         nop;                             // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:44: +6:49
-+         nop;                             // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:44: +6:49
-+         ((((_0 as Ok).0: ViewportPercentageLength) as Vw).0: f32) = Add(move _15, move _16); // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:38: +6:49
-+         nop;                             // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:48: +6:49
-+         nop;                             // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:48: +6:49
-+         Deinit(((_0 as Ok).0: ViewportPercentageLength)); // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:35: +6:50
-+         nop;                             // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:35: +6:50
-+         discriminant(((_0 as Ok).0: ViewportPercentageLength)) = 0; // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:35: +6:50
-+         nop;                             // scope 1 at $DIR/early_otherwise_branch_68867.rs:+6:49: +6:50
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:49: +6:50
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:49: +6:50
-          goto -> bb10;                    // scope 0 at $DIR/early_otherwise_branch_68867.rs:+6:49: +6:50
-      }
-  
-      bb7: {
--         StorageLive(_17);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:14: +7:17
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:14: +7:17
-          _41 = deref_copy (_4.0: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:14: +7:17
--         _17 = (((*_41) as Vh).0: f32);   // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:14: +7:17
--         StorageLive(_18);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:24: +7:29
-+         _20 = (((*_41) as Vh).0: f32);   // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:14: +7:17
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:24: +7:29
-          _42 = deref_copy (_4.1: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:24: +7:29
--         _18 = (((*_42) as Vh).0: f32);   // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:24: +7:29
--         StorageLive(_19);                // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:38: +7:49
--         StorageLive(_20);                // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:38: +7:41
--         _20 = _17;                       // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:38: +7:41
--         StorageLive(_21);                // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:44: +7:49
--         _21 = _18;                       // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:44: +7:49
--         _19 = Add(move _20, move _21);   // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:38: +7:49
--         StorageDead(_21);                // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:48: +7:49
--         StorageDead(_20);                // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:48: +7:49
--         Deinit(_3);                      // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:35: +7:50
--         ((_3 as Vh).0: f32) = move _19;  // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:35: +7:50
--         discriminant(_3) = 1;            // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:35: +7:50
--         StorageDead(_19);                // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:49: +7:50
--         StorageDead(_18);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:49: +7:50
--         StorageDead(_17);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:49: +7:50
-+         _21 = (((*_42) as Vh).0: f32);   // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:24: +7:29
-+         nop;                             // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:38: +7:49
-+         nop;                             // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:38: +7:41
-+         nop;                             // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:38: +7:41
-+         nop;                             // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:44: +7:49
-+         nop;                             // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:44: +7:49
-+         ((((_0 as Ok).0: ViewportPercentageLength) as Vh).0: f32) = Add(move _20, move _21); // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:38: +7:49
-+         nop;                             // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:48: +7:49
-+         nop;                             // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:48: +7:49
-+         Deinit(((_0 as Ok).0: ViewportPercentageLength)); // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:35: +7:50
-+         nop;                             // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:35: +7:50
-+         discriminant(((_0 as Ok).0: ViewportPercentageLength)) = 1; // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:35: +7:50
-+         nop;                             // scope 2 at $DIR/early_otherwise_branch_68867.rs:+7:49: +7:50
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:49: +7:50
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:49: +7:50
-          goto -> bb10;                    // scope 0 at $DIR/early_otherwise_branch_68867.rs:+7:49: +7:50
-      }
-  
-      bb8: {
--         StorageLive(_22);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:16: +8:19
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:16: +8:19
-          _43 = deref_copy (_4.0: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:16: +8:19
--         _22 = (((*_43) as Vmin).0: f32); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:16: +8:19
--         StorageLive(_23);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:28: +8:33
-+         _25 = (((*_43) as Vmin).0: f32); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:16: +8:19
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:28: +8:33
-          _44 = deref_copy (_4.1: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:28: +8:33
--         _23 = (((*_44) as Vmin).0: f32); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:28: +8:33
--         StorageLive(_24);                // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:44: +8:55
--         StorageLive(_25);                // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:44: +8:47
--         _25 = _22;                       // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:44: +8:47
--         StorageLive(_26);                // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:50: +8:55
--         _26 = _23;                       // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:50: +8:55
--         _24 = Add(move _25, move _26);   // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:44: +8:55
--         StorageDead(_26);                // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:54: +8:55
--         StorageDead(_25);                // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:54: +8:55
--         Deinit(_3);                      // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:39: +8:56
--         ((_3 as Vmin).0: f32) = move _24; // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:39: +8:56
--         discriminant(_3) = 2;            // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:39: +8:56
--         StorageDead(_24);                // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:55: +8:56
--         StorageDead(_23);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:55: +8:56
--         StorageDead(_22);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:55: +8:56
-+         _26 = (((*_44) as Vmin).0: f32); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:28: +8:33
-+         nop;                             // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:44: +8:55
-+         nop;                             // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:44: +8:47
-+         nop;                             // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:44: +8:47
-+         nop;                             // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:50: +8:55
-+         nop;                             // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:50: +8:55
-+         ((((_0 as Ok).0: ViewportPercentageLength) as Vmin).0: f32) = Add(move _25, move _26); // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:44: +8:55
-+         nop;                             // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:54: +8:55
-+         nop;                             // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:54: +8:55
-+         Deinit(((_0 as Ok).0: ViewportPercentageLength)); // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:39: +8:56
-+         nop;                             // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:39: +8:56
-+         discriminant(((_0 as Ok).0: ViewportPercentageLength)) = 2; // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:39: +8:56
-+         nop;                             // scope 3 at $DIR/early_otherwise_branch_68867.rs:+8:55: +8:56
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:55: +8:56
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:55: +8:56
-          goto -> bb10;                    // scope 0 at $DIR/early_otherwise_branch_68867.rs:+8:55: +8:56
-      }
-  
-      bb9: {
--         StorageLive(_27);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:16: +9:19
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:16: +9:19
-          _45 = deref_copy (_4.0: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:16: +9:19
--         _27 = (((*_45) as Vmax).0: f32); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:16: +9:19
--         StorageLive(_28);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:28: +9:33
-+         _30 = (((*_45) as Vmax).0: f32); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:16: +9:19
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:28: +9:33
-          _46 = deref_copy (_4.1: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:28: +9:33
--         _28 = (((*_46) as Vmax).0: f32); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:28: +9:33
--         StorageLive(_29);                // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:44: +9:55
--         StorageLive(_30);                // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:44: +9:47
--         _30 = _27;                       // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:44: +9:47
--         StorageLive(_31);                // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:50: +9:55
--         _31 = _28;                       // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:50: +9:55
--         _29 = Add(move _30, move _31);   // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:44: +9:55
--         StorageDead(_31);                // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:54: +9:55
--         StorageDead(_30);                // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:54: +9:55
--         Deinit(_3);                      // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:39: +9:56
--         ((_3 as Vmax).0: f32) = move _29; // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:39: +9:56
--         discriminant(_3) = 3;            // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:39: +9:56
--         StorageDead(_29);                // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:55: +9:56
--         StorageDead(_28);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:55: +9:56
--         StorageDead(_27);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:55: +9:56
-+         _31 = (((*_46) as Vmax).0: f32); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:28: +9:33
-+         nop;                             // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:44: +9:55
-+         nop;                             // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:44: +9:47
-+         nop;                             // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:44: +9:47
-+         nop;                             // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:50: +9:55
-+         nop;                             // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:50: +9:55
-+         ((((_0 as Ok).0: ViewportPercentageLength) as Vmax).0: f32) = Add(move _30, move _31); // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:44: +9:55
-+         nop;                             // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:54: +9:55
-+         nop;                             // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:54: +9:55
-+         Deinit(((_0 as Ok).0: ViewportPercentageLength)); // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:39: +9:56
-+         nop;                             // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:39: +9:56
-+         discriminant(((_0 as Ok).0: ViewportPercentageLength)) = 3; // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:39: +9:56
-+         nop;                             // scope 4 at $DIR/early_otherwise_branch_68867.rs:+9:55: +9:56
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:55: +9:56
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:55: +9:56
-          goto -> bb10;                    // scope 0 at $DIR/early_otherwise_branch_68867.rs:+9:55: +9:56
-      }
-  
-      bb10: {
-          Deinit(_0);                      // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:5: +11:7
--         ((_0 as Ok).0: ViewportPercentageLength) = move _3; // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:5: +11:7
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:5: +11:7
-          discriminant(_0) = 0;            // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:5: +11:7
--         StorageDead(_3);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+11:6: +11:7
--         StorageDead(_4);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:1: +12:2
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+11:6: +11:7
-+         nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:1: +12:2
-          return;                          // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:2: +12:2
-      }
-  
-      bb11: {
-          unreachable;                     // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:2: +12:2
-      }
-  }
-  
index 50a58d4792a8d19ed25fafc1a2da11e30eac2592..6bc025bb5b204897dc703bc1ddfa995e634377de 100644 (file)
@@ -80,7 +80,7 @@
           StorageDead(_5);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:23: +5:24
           _34 = deref_copy (_4.0: &ViewportPercentageLength); // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
           _11 = discriminant((*_34));      // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:14: +5:24
-          switchInt(move _11) -> [0_isize: bb1, 1_isize: bb3, 2_isize: bb4, 3_isize: bb5, otherwise: bb11]; // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:8: +5:24
+          switchInt(move _11) -> [0_isize: bb1, 1_isize: bb3, 2_isize: bb4, 3_isize: bb5, otherwise: bb2]; // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:8: +5:24
       }
   
       bb1: {
   
       bb2: {
           StorageLive(_33);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:25: +10:27
-          nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:25: +10:27
+          Deinit(_33);                     // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:25: +10:27
           Deinit(_0);                      // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:21: +10:28
-          nop;                             // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:21: +10:28
+          ((_0 as Err).0: ()) = move _33;  // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:21: +10:28
           discriminant(_0) = 1;            // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:21: +10:28
           StorageDead(_33);                // scope 0 at $DIR/early_otherwise_branch_68867.rs:+10:27: +10:28
           StorageDead(_3);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+11:6: +11:7
           StorageDead(_4);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:1: +12:2
-          return;                          // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:2: +12:2
+          goto -> bb11;                    // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:2: +12:2
       }
   
       bb3: {
           discriminant(_0) = 0;            // scope 0 at $DIR/early_otherwise_branch_68867.rs:+5:5: +11:7
           StorageDead(_3);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+11:6: +11:7
           StorageDead(_4);                 // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:1: +12:2
-          return;                          // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:2: +12:2
+          goto -> bb11;                    // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:2: +12:2
       }
   
       bb11: {
-          unreachable;                     // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:2: +12:2
+          return;                          // scope 0 at $DIR/early_otherwise_branch_68867.rs:+12:2: +12:2
       }
   }
   
index 703b876123133a2f01e82f08d2096e6382ad6b8b..9e731c40908790c8a9c30440333ca8bc7c8bbca9 100644 (file)
@@ -10,4 +10,3 @@ fn main() {
 
 // EMIT_MIR_FOR_EACH_BIT_WIDTH
 // EMIT_MIR issue_73223.main.SimplifyArmIdentity.diff
-// EMIT_MIR issue_73223.main.PreCodegen.diff
diff --git a/src/test/mir-opt/issue_73223.main.PreCodegen.32bit.diff b/src/test/mir-opt/issue_73223.main.PreCodegen.32bit.diff
deleted file mode 100644 (file)
index be8e86a..0000000
+++ /dev/null
@@ -1,117 +0,0 @@
-- // MIR for `main` before PreCodegen
-+ // MIR for `main` after PreCodegen
-  
-  fn main() -> () {
-      let mut _0: ();                      // return place in scope 0 at $DIR/issue-73223.rs:+0:11: +0:11
-      let _1: i32;                         // in scope 0 at $DIR/issue-73223.rs:+1:9: +1:14
-      let mut _2: std::option::Option<i32>; // in scope 0 at $DIR/issue-73223.rs:+1:23: +1:30
-      let _3: i32;                         // in scope 0 at $DIR/issue-73223.rs:+2:14: +2:15
-      let mut _5: (&i32, &i32);            // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _6: &i32;                    // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _7: &i32;                    // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _10: bool;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _11: bool;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _12: i32;                    // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let _14: !;                          // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _15: &i32;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let _16: &i32;                       // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _17: &i32;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let _18: &i32;                       // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _19: std::option::Option<std::fmt::Arguments>; // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      scope 1 {
-          debug split => _1;               // in scope 1 at $DIR/issue-73223.rs:+1:9: +1:14
-          let _4: std::option::Option<i32>; // in scope 1 at $DIR/issue-73223.rs:+6:9: +6:14
-          scope 3 {
-              debug _prev => _4;           // in scope 3 at $DIR/issue-73223.rs:+6:9: +6:14
-              let _8: &i32;                // in scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-              let _9: &i32;                // in scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-              let mut _20: &i32;           // in scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-              scope 4 {
-                  debug left_val => _8;    // in scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                  debug right_val => _9;   // in scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                  let _13: core::panicking::AssertKind; // in scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                  scope 5 {
-                      debug kind => _13;   // in scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                  }
-              }
-          }
-      }
-      scope 2 {
-          debug v => _3;                   // in scope 2 at $DIR/issue-73223.rs:+2:14: +2:15
-      }
-  
-      bb0: {
-          StorageLive(_1);                 // scope 0 at $DIR/issue-73223.rs:+1:9: +1:14
-          StorageLive(_2);                 // scope 0 at $DIR/issue-73223.rs:+1:23: +1:30
-          Deinit(_2);                      // scope 0 at $DIR/issue-73223.rs:+1:23: +1:30
-          ((_2 as Some).0: i32) = const 1_i32; // scope 0 at $DIR/issue-73223.rs:+1:23: +1:30
-          discriminant(_2) = 1;            // scope 0 at $DIR/issue-73223.rs:+1:23: +1:30
-          StorageLive(_3);                 // scope 0 at $DIR/issue-73223.rs:+2:14: +2:15
-          _3 = ((_2 as Some).0: i32);      // scope 0 at $DIR/issue-73223.rs:+2:14: +2:15
-          _1 = _3;                         // scope 2 at $DIR/issue-73223.rs:+2:20: +2:21
-          StorageDead(_3);                 // scope 0 at $DIR/issue-73223.rs:+2:20: +2:21
-          StorageDead(_2);                 // scope 0 at $DIR/issue-73223.rs:+4:6: +4:7
-          StorageLive(_4);                 // scope 1 at $DIR/issue-73223.rs:+6:9: +6:14
-          StorageLive(_5);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_6);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _6 = &_1;                        // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_7);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _20 = const main::promoted[0];   // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                                           // mir::Constant
-                                           // + span: $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                                           // + literal: Const { ty: &i32, val: Unevaluated(main, [], Some(promoted[0])) }
-          _7 = _20;                        // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          Deinit(_5);                      // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          (_5.0: &i32) = move _6;          // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          (_5.1: &i32) = move _7;          // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_7);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_6);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_8);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _8 = (_5.0: &i32);               // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_9);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _9 = (_5.1: &i32);               // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_10);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_11);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_12);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _12 = (*_8);                     // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _11 = Eq(move _12, const 1_i32); // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_12);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _10 = Not(move _11);             // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_11);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          switchInt(move _10) -> [false: bb2, otherwise: bb1]; // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      }
-  
-      bb1: {
-          StorageLive(_13);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_14);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_15);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_16);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _16 = _8;                        // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _15 = _16;                       // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_17);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_18);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _18 = _9;                        // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _17 = _18;                       // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_19);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          Deinit(_19);                     // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          discriminant(_19) = 0;           // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _14 = core::panicking::assert_failed::<i32, i32>(const core::panicking::AssertKind::Eq, move _15, move _17, move _19); // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                                           // mir::Constant
-                                           // + span: $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                                           // + literal: Const { ty: for<'r, 's, 't0> fn(core::panicking::AssertKind, &'r i32, &'s i32, Option<Arguments<'t0>>) -> ! {core::panicking::assert_failed::<i32, i32>}, val: Value(<ZST>) }
-                                           // mir::Constant
-                                           // + span: $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                                           // + literal: Const { ty: core::panicking::AssertKind, val: Value(Scalar(0x00)) }
-      }
-  
-      bb2: {
-          StorageDead(_10);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_9);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_8);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_5);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_4);                 // scope 1 at $DIR/issue-73223.rs:+8:1: +8:2
-          StorageDead(_1);                 // scope 0 at $DIR/issue-73223.rs:+8:1: +8:2
-          return;                          // scope 0 at $DIR/issue-73223.rs:+8:2: +8:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/issue_73223.main.PreCodegen.64bit.diff b/src/test/mir-opt/issue_73223.main.PreCodegen.64bit.diff
deleted file mode 100644 (file)
index be8e86a..0000000
+++ /dev/null
@@ -1,117 +0,0 @@
-- // MIR for `main` before PreCodegen
-+ // MIR for `main` after PreCodegen
-  
-  fn main() -> () {
-      let mut _0: ();                      // return place in scope 0 at $DIR/issue-73223.rs:+0:11: +0:11
-      let _1: i32;                         // in scope 0 at $DIR/issue-73223.rs:+1:9: +1:14
-      let mut _2: std::option::Option<i32>; // in scope 0 at $DIR/issue-73223.rs:+1:23: +1:30
-      let _3: i32;                         // in scope 0 at $DIR/issue-73223.rs:+2:14: +2:15
-      let mut _5: (&i32, &i32);            // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _6: &i32;                    // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _7: &i32;                    // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _10: bool;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _11: bool;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _12: i32;                    // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let _14: !;                          // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _15: &i32;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let _16: &i32;                       // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _17: &i32;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let _18: &i32;                       // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      let mut _19: std::option::Option<std::fmt::Arguments>; // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      scope 1 {
-          debug split => _1;               // in scope 1 at $DIR/issue-73223.rs:+1:9: +1:14
-          let _4: std::option::Option<i32>; // in scope 1 at $DIR/issue-73223.rs:+6:9: +6:14
-          scope 3 {
-              debug _prev => _4;           // in scope 3 at $DIR/issue-73223.rs:+6:9: +6:14
-              let _8: &i32;                // in scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-              let _9: &i32;                // in scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-              let mut _20: &i32;           // in scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-              scope 4 {
-                  debug left_val => _8;    // in scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                  debug right_val => _9;   // in scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                  let _13: core::panicking::AssertKind; // in scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                  scope 5 {
-                      debug kind => _13;   // in scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                  }
-              }
-          }
-      }
-      scope 2 {
-          debug v => _3;                   // in scope 2 at $DIR/issue-73223.rs:+2:14: +2:15
-      }
-  
-      bb0: {
-          StorageLive(_1);                 // scope 0 at $DIR/issue-73223.rs:+1:9: +1:14
-          StorageLive(_2);                 // scope 0 at $DIR/issue-73223.rs:+1:23: +1:30
-          Deinit(_2);                      // scope 0 at $DIR/issue-73223.rs:+1:23: +1:30
-          ((_2 as Some).0: i32) = const 1_i32; // scope 0 at $DIR/issue-73223.rs:+1:23: +1:30
-          discriminant(_2) = 1;            // scope 0 at $DIR/issue-73223.rs:+1:23: +1:30
-          StorageLive(_3);                 // scope 0 at $DIR/issue-73223.rs:+2:14: +2:15
-          _3 = ((_2 as Some).0: i32);      // scope 0 at $DIR/issue-73223.rs:+2:14: +2:15
-          _1 = _3;                         // scope 2 at $DIR/issue-73223.rs:+2:20: +2:21
-          StorageDead(_3);                 // scope 0 at $DIR/issue-73223.rs:+2:20: +2:21
-          StorageDead(_2);                 // scope 0 at $DIR/issue-73223.rs:+4:6: +4:7
-          StorageLive(_4);                 // scope 1 at $DIR/issue-73223.rs:+6:9: +6:14
-          StorageLive(_5);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_6);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _6 = &_1;                        // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_7);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _20 = const main::promoted[0];   // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                                           // mir::Constant
-                                           // + span: $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                                           // + literal: Const { ty: &i32, val: Unevaluated(main, [], Some(promoted[0])) }
-          _7 = _20;                        // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          Deinit(_5);                      // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          (_5.0: &i32) = move _6;          // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          (_5.1: &i32) = move _7;          // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_7);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_6);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_8);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _8 = (_5.0: &i32);               // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_9);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _9 = (_5.1: &i32);               // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_10);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_11);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_12);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _12 = (*_8);                     // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _11 = Eq(move _12, const 1_i32); // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_12);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _10 = Not(move _11);             // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_11);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          switchInt(move _10) -> [false: bb2, otherwise: bb1]; // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-      }
-  
-      bb1: {
-          StorageLive(_13);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_14);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_15);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_16);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _16 = _8;                        // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _15 = _16;                       // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_17);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_18);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _18 = _9;                        // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _17 = _18;                       // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageLive(_19);                // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          Deinit(_19);                     // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          discriminant(_19) = 0;           // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          _14 = core::panicking::assert_failed::<i32, i32>(const core::panicking::AssertKind::Eq, move _15, move _17, move _19); // scope 5 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                                           // mir::Constant
-                                           // + span: $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                                           // + literal: Const { ty: for<'r, 's, 't0> fn(core::panicking::AssertKind, &'r i32, &'s i32, Option<Arguments<'t0>>) -> ! {core::panicking::assert_failed::<i32, i32>}, val: Value(<ZST>) }
-                                           // mir::Constant
-                                           // + span: $SRC_DIR/core/src/macros/mod.rs:LL:COL
-                                           // + literal: Const { ty: core::panicking::AssertKind, val: Value(Scalar(0x00)) }
-      }
-  
-      bb2: {
-          StorageDead(_10);                // scope 4 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_9);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_8);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_5);                 // scope 3 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-          StorageDead(_4);                 // scope 1 at $DIR/issue-73223.rs:+8:1: +8:2
-          StorageDead(_1);                 // scope 0 at $DIR/issue-73223.rs:+8:1: +8:2
-          return;                          // scope 0 at $DIR/issue-73223.rs:+8:2: +8:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/lower_array_len.array_bound.InstCombine.diff b/src/test/mir-opt/lower_array_len.array_bound.InstCombine.diff
deleted file mode 100644 (file)
index 2589c9f..0000000
+++ /dev/null
@@ -1,66 +0,0 @@
-- // MIR for `array_bound` before InstCombine
-+ // MIR for `array_bound` after InstCombine
-  
-  fn array_bound(_1: usize, _2: &[u8; N]) -> u8 {
-      debug index => _1;                   // in scope 0 at $DIR/lower_array_len.rs:+0:36: +0:41
-      debug slice => _2;                   // in scope 0 at $DIR/lower_array_len.rs:+0:50: +0:55
-      let mut _0: u8;                      // return place in scope 0 at $DIR/lower_array_len.rs:+0:70: +0:72
-      let mut _3: bool;                    // in scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-      let mut _4: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-      let mut _5: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-      let mut _6: &[u8];                   // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-      let mut _7: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-      let _8: usize;                       // in scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
-      let mut _9: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-      let mut _10: bool;                   // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-      let mut _11: &[u8; N];               // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-  
-      bb0: {
-          StorageLive(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-          StorageLive(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-          _4 = _1;                         // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-          StorageLive(_5);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageLive(_6);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageLive(_7);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         _7 = &(*_2);                     // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-+         _7 = _2;                         // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageLive(_11);                // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          _11 = _7;                        // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          _6 = move _7 as &[u8] (Pointer(Unsize)); // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageDead(_7);                 // scope 0 at $DIR/lower_array_len.rs:+1:20: +1:21
--         _5 = Len((*_11));                // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-+         _5 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageDead(_11);                // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageDead(_6);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          _3 = Lt(move _4, move _5);       // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-          StorageDead(_5);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          StorageDead(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          switchInt(move _3) -> [false: bb3, otherwise: bb1]; // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-      }
-  
-      bb1: {
-          StorageLive(_8);                 // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
-          _8 = _1;                         // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
--         _9 = Len((*_2));                 // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+         _9 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-          _10 = Lt(_8, _9);                // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-          assert(move _10, "index out of bounds: the length is {} but the index is {}", move _9, _8) -> bb2; // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-      }
-  
-      bb2: {
-          _0 = (*_2)[_8];                  // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-          StorageDead(_8);                 // scope 0 at $DIR/lower_array_len.rs:+3:5: +3:6
-          goto -> bb4;                     // scope 0 at $DIR/lower_array_len.rs:+1:5: +5:6
-      }
-  
-      bb3: {
-          _0 = const 42_u8;                // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:11
-          goto -> bb4;                     // scope 0 at $DIR/lower_array_len.rs:+1:5: +5:6
-      }
-  
-      bb4: {
-          StorageDead(_3);                 // scope 0 at $DIR/lower_array_len.rs:+5:5: +5:6
-          return;                          // scope 0 at $DIR/lower_array_len.rs:+6:2: +6:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/lower_array_len.array_bound.SimplifyLocals.diff b/src/test/mir-opt/lower_array_len.array_bound.SimplifyLocals.diff
deleted file mode 100644 (file)
index 8312db6..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-- // MIR for `array_bound` before SimplifyLocals
-+ // MIR for `array_bound` after SimplifyLocals
-  
-  fn array_bound(_1: usize, _2: &[u8; N]) -> u8 {
-      debug index => _1;                   // in scope 0 at $DIR/lower_array_len.rs:+0:36: +0:41
-      debug slice => _2;                   // in scope 0 at $DIR/lower_array_len.rs:+0:50: +0:55
-      let mut _0: u8;                      // return place in scope 0 at $DIR/lower_array_len.rs:+0:70: +0:72
-      let mut _3: bool;                    // in scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-      let mut _4: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-      let mut _5: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--     let mut _6: &[u8];                   // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--     let mut _7: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--     let _8: usize;                       // in scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
--     let mut _9: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
--     let mut _10: bool;                   // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
--     let mut _11: &[u8; N];               // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-+     let _6: usize;                       // in scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
-+     let mut _7: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+     let mut _8: bool;                    // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-  
-      bb0: {
-          StorageLive(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-          StorageLive(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-          _4 = _1;                         // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-          StorageLive(_5);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageLive(_6);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageLive(_7);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageLive(_11);                // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageDead(_7);                 // scope 0 at $DIR/lower_array_len.rs:+1:20: +1:21
-          _5 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageDead(_11);                // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageDead(_6);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          _3 = Lt(move _4, move _5);       // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-          StorageDead(_5);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          StorageDead(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          switchInt(move _3) -> [false: bb3, otherwise: bb1]; // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-      }
-  
-      bb1: {
--         StorageLive(_8);                 // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
--         _8 = _1;                         // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
--         _9 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
--         _10 = Lt(_8, _9);                // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
--         assert(move _10, "index out of bounds: the length is {} but the index is {}", move _9, _8) -> bb2; // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+         StorageLive(_6);                 // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
-+         _6 = _1;                         // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
-+         _7 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+         _8 = Lt(_6, _7);                 // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+         assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> bb2; // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-      }
-  
-      bb2: {
--         _0 = (*_2)[_8];                  // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
--         StorageDead(_8);                 // scope 0 at $DIR/lower_array_len.rs:+3:5: +3:6
-+         _0 = (*_2)[_6];                  // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+         StorageDead(_6);                 // scope 0 at $DIR/lower_array_len.rs:+3:5: +3:6
-          goto -> bb4;                     // scope 0 at $DIR/lower_array_len.rs:+1:5: +5:6
-      }
-  
-      bb3: {
-          _0 = const 42_u8;                // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:11
-          goto -> bb4;                     // scope 0 at $DIR/lower_array_len.rs:+1:5: +5:6
-      }
-  
-      bb4: {
-          StorageDead(_3);                 // scope 0 at $DIR/lower_array_len.rs:+5:5: +5:6
-          return;                          // scope 0 at $DIR/lower_array_len.rs:+6:2: +6:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/lower_array_len.array_bound_mut.InstCombine.diff b/src/test/mir-opt/lower_array_len.array_bound_mut.InstCombine.diff
deleted file mode 100644 (file)
index 401d4ba..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-- // MIR for `array_bound_mut` before InstCombine
-+ // MIR for `array_bound_mut` after InstCombine
-  
-  fn array_bound_mut(_1: usize, _2: &mut [u8; N]) -> u8 {
-      debug index => _1;                   // in scope 0 at $DIR/lower_array_len.rs:+0:40: +0:45
-      debug slice => _2;                   // in scope 0 at $DIR/lower_array_len.rs:+0:54: +0:59
-      let mut _0: u8;                      // return place in scope 0 at $DIR/lower_array_len.rs:+0:78: +0:80
-      let mut _3: bool;                    // in scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-      let mut _4: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-      let mut _5: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-      let mut _6: &[u8];                   // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-      let mut _7: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-      let _8: usize;                       // in scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
-      let mut _9: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-      let mut _10: bool;                   // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-      let _11: usize;                      // in scope 0 at $DIR/lower_array_len.rs:+4:15: +4:16
-      let mut _12: usize;                  // in scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-      let mut _13: bool;                   // in scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-      let mut _14: &[u8; N];               // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-  
-      bb0: {
-          StorageLive(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-          StorageLive(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-          _4 = _1;                         // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-          StorageLive(_5);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageLive(_6);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageLive(_7);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          _7 = &(*_2);                     // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageLive(_14);                // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          _14 = _7;                        // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          _6 = move _7 as &[u8] (Pointer(Unsize)); // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageDead(_7);                 // scope 0 at $DIR/lower_array_len.rs:+1:20: +1:21
--         _5 = Len((*_14));                // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-+         _5 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageDead(_14);                // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-          StorageDead(_6);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          _3 = Lt(move _4, move _5);       // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-          StorageDead(_5);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          StorageDead(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          switchInt(move _3) -> [false: bb3, otherwise: bb1]; // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-      }
-  
-      bb1: {
-          StorageLive(_8);                 // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
-          _8 = _1;                         // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
--         _9 = Len((*_2));                 // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+         _9 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-          _10 = Lt(_8, _9);                // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-          assert(move _10, "index out of bounds: the length is {} but the index is {}", move _9, _8) -> bb2; // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-      }
-  
-      bb2: {
-          _0 = (*_2)[_8];                  // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-          StorageDead(_8);                 // scope 0 at $DIR/lower_array_len.rs:+3:5: +3:6
-          goto -> bb5;                     // scope 0 at $DIR/lower_array_len.rs:+1:5: +7:6
-      }
-  
-      bb3: {
-          StorageLive(_11);                // scope 0 at $DIR/lower_array_len.rs:+4:15: +4:16
-          _11 = const 0_usize;             // scope 0 at $DIR/lower_array_len.rs:+4:15: +4:16
--         _12 = Len((*_2));                // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-+         _12 = const N;                   // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-          _13 = Lt(_11, _12);              // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-          assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, _11) -> bb4; // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-      }
-  
-      bb4: {
-          (*_2)[_11] = const 42_u8;        // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:22
-          StorageDead(_11);                // scope 0 at $DIR/lower_array_len.rs:+4:22: +4:23
-          _0 = const 42_u8;                // scope 0 at $DIR/lower_array_len.rs:+6:9: +6:11
-          goto -> bb5;                     // scope 0 at $DIR/lower_array_len.rs:+1:5: +7:6
-      }
-  
-      bb5: {
-          StorageDead(_3);                 // scope 0 at $DIR/lower_array_len.rs:+7:5: +7:6
-          return;                          // scope 0 at $DIR/lower_array_len.rs:+8:2: +8:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/lower_array_len.array_bound_mut.SimplifyLocals.diff b/src/test/mir-opt/lower_array_len.array_bound_mut.SimplifyLocals.diff
deleted file mode 100644 (file)
index 4f241d7..0000000
+++ /dev/null
@@ -1,93 +0,0 @@
-- // MIR for `array_bound_mut` before SimplifyLocals
-+ // MIR for `array_bound_mut` after SimplifyLocals
-  
-  fn array_bound_mut(_1: usize, _2: &mut [u8; N]) -> u8 {
-      debug index => _1;                   // in scope 0 at $DIR/lower_array_len.rs:+0:40: +0:45
-      debug slice => _2;                   // in scope 0 at $DIR/lower_array_len.rs:+0:54: +0:59
-      let mut _0: u8;                      // return place in scope 0 at $DIR/lower_array_len.rs:+0:78: +0:80
-      let mut _3: bool;                    // in scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-      let mut _4: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-      let mut _5: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--     let mut _6: &[u8];                   // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--     let mut _7: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--     let _8: usize;                       // in scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
--     let mut _9: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
--     let mut _10: bool;                   // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
--     let _11: usize;                      // in scope 0 at $DIR/lower_array_len.rs:+4:15: +4:16
--     let mut _12: usize;                  // in scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
--     let mut _13: bool;                   // in scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
--     let mut _14: &[u8; N];               // in scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
-+     let _6: usize;                       // in scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
-+     let mut _7: usize;                   // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+     let mut _8: bool;                    // in scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+     let _9: usize;                       // in scope 0 at $DIR/lower_array_len.rs:+4:15: +4:16
-+     let mut _10: usize;                  // in scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-+     let mut _11: bool;                   // in scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-  
-      bb0: {
-          StorageLive(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-          StorageLive(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-          _4 = _1;                         // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:13
-          StorageLive(_5);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageLive(_6);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageLive(_7);                 // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageLive(_14);                // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageDead(_7);                 // scope 0 at $DIR/lower_array_len.rs:+1:20: +1:21
-          _5 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageDead(_14);                // scope 0 at $DIR/lower_array_len.rs:+1:16: +1:27
--         StorageDead(_6);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          _3 = Lt(move _4, move _5);       // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-          StorageDead(_5);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          StorageDead(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:26: +1:27
-          switchInt(move _3) -> [false: bb3, otherwise: bb1]; // scope 0 at $DIR/lower_array_len.rs:+1:8: +1:27
-      }
-  
-      bb1: {
--         StorageLive(_8);                 // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
--         _8 = _1;                         // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
--         _9 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
--         _10 = Lt(_8, _9);                // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
--         assert(move _10, "index out of bounds: the length is {} but the index is {}", move _9, _8) -> bb2; // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+         StorageLive(_6);                 // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
-+         _6 = _1;                         // scope 0 at $DIR/lower_array_len.rs:+2:15: +2:20
-+         _7 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+         _8 = Lt(_6, _7);                 // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+         assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> bb2; // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-      }
-  
-      bb2: {
--         _0 = (*_2)[_8];                  // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
--         StorageDead(_8);                 // scope 0 at $DIR/lower_array_len.rs:+3:5: +3:6
-+         _0 = (*_2)[_6];                  // scope 0 at $DIR/lower_array_len.rs:+2:9: +2:21
-+         StorageDead(_6);                 // scope 0 at $DIR/lower_array_len.rs:+3:5: +3:6
-          goto -> bb5;                     // scope 0 at $DIR/lower_array_len.rs:+1:5: +7:6
-      }
-  
-      bb3: {
--         StorageLive(_11);                // scope 0 at $DIR/lower_array_len.rs:+4:15: +4:16
--         _11 = const 0_usize;             // scope 0 at $DIR/lower_array_len.rs:+4:15: +4:16
--         _12 = const N;                   // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
--         _13 = Lt(const 0_usize, _12);    // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
--         assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, const 0_usize) -> bb4; // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-+         StorageLive(_9);                 // scope 0 at $DIR/lower_array_len.rs:+4:15: +4:16
-+         _9 = const 0_usize;              // scope 0 at $DIR/lower_array_len.rs:+4:15: +4:16
-+         _10 = const N;                   // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-+         _11 = Lt(const 0_usize, _10);    // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-+         assert(move _11, "index out of bounds: the length is {} but the index is {}", move _10, const 0_usize) -> bb4; // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:17
-      }
-  
-      bb4: {
--         (*_2)[_11] = const 42_u8;        // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:22
--         StorageDead(_11);                // scope 0 at $DIR/lower_array_len.rs:+4:22: +4:23
-+         (*_2)[_9] = const 42_u8;         // scope 0 at $DIR/lower_array_len.rs:+4:9: +4:22
-+         StorageDead(_9);                 // scope 0 at $DIR/lower_array_len.rs:+4:22: +4:23
-          _0 = const 42_u8;                // scope 0 at $DIR/lower_array_len.rs:+6:9: +6:11
-          goto -> bb5;                     // scope 0 at $DIR/lower_array_len.rs:+1:5: +7:6
-      }
-  
-      bb5: {
-          StorageDead(_3);                 // scope 0 at $DIR/lower_array_len.rs:+7:5: +7:6
-          return;                          // scope 0 at $DIR/lower_array_len.rs:+8:2: +8:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/lower_array_len.array_len.InstCombine.diff b/src/test/mir-opt/lower_array_len.array_len.InstCombine.diff
deleted file mode 100644 (file)
index 26f45be..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-- // MIR for `array_len` before InstCombine
-+ // MIR for `array_len` after InstCombine
-  
-  fn array_len(_1: &[u8; N]) -> usize {
-      debug arr => _1;                     // in scope 0 at $DIR/lower_array_len.rs:+0:34: +0:37
-      let mut _0: usize;                   // return place in scope 0 at $DIR/lower_array_len.rs:+0:52: +0:57
-      let mut _2: &[u8];                   // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-      let mut _3: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-      let mut _4: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-  
-      bb0: {
-          StorageLive(_2);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          StorageLive(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--         _3 = &(*_1);                     // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-+         _3 = _1;                         // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          StorageLive(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          _4 = _3;                         // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          _2 = move _3 as &[u8] (Pointer(Unsize)); // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          StorageDead(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:7: +1:8
--         _0 = Len((*_4));                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-+         _0 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          StorageDead(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          StorageDead(_2);                 // scope 0 at $DIR/lower_array_len.rs:+1:13: +1:14
-          return;                          // scope 0 at $DIR/lower_array_len.rs:+2:2: +2:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/lower_array_len.array_len.SimplifyLocals.diff b/src/test/mir-opt/lower_array_len.array_len.SimplifyLocals.diff
deleted file mode 100644 (file)
index 09d571d..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-- // MIR for `array_len` before SimplifyLocals
-+ // MIR for `array_len` after SimplifyLocals
-  
-  fn array_len(_1: &[u8; N]) -> usize {
-      debug arr => _1;                     // in scope 0 at $DIR/lower_array_len.rs:+0:34: +0:37
-      let mut _0: usize;                   // return place in scope 0 at $DIR/lower_array_len.rs:+0:52: +0:57
--     let mut _2: &[u8];                   // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--     let mut _3: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--     let mut _4: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-  
-      bb0: {
--         StorageLive(_2);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--         StorageLive(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--         StorageLive(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--         StorageDead(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:7: +1:8
-          _0 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--         StorageDead(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--         StorageDead(_2);                 // scope 0 at $DIR/lower_array_len.rs:+1:13: +1:14
-          return;                          // scope 0 at $DIR/lower_array_len.rs:+2:2: +2:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/lower_array_len.array_len_by_value.InstCombine.diff b/src/test/mir-opt/lower_array_len.array_len_by_value.InstCombine.diff
deleted file mode 100644 (file)
index 843da75..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-- // MIR for `array_len_by_value` before InstCombine
-+ // MIR for `array_len_by_value` after InstCombine
-  
-  fn array_len_by_value(_1: [u8; N]) -> usize {
-      debug arr => _1;                     // in scope 0 at $DIR/lower_array_len.rs:+0:43: +0:46
-      let mut _0: usize;                   // return place in scope 0 at $DIR/lower_array_len.rs:+0:60: +0:65
-      let mut _2: &[u8];                   // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-      let mut _3: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-      let mut _4: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-  
-      bb0: {
-          StorageLive(_2);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          StorageLive(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          _3 = &_1;                        // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          StorageLive(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          _4 = _3;                         // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          _2 = move _3 as &[u8] (Pointer(Unsize)); // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          StorageDead(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:7: +1:8
--         _0 = Len((*_4));                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-+         _0 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          StorageDead(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-          StorageDead(_2);                 // scope 0 at $DIR/lower_array_len.rs:+1:13: +1:14
-          return;                          // scope 0 at $DIR/lower_array_len.rs:+2:2: +2:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/lower_array_len.array_len_by_value.SimplifyLocals.diff b/src/test/mir-opt/lower_array_len.array_len_by_value.SimplifyLocals.diff
deleted file mode 100644 (file)
index dc1c00b..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-- // MIR for `array_len_by_value` before SimplifyLocals
-+ // MIR for `array_len_by_value` after SimplifyLocals
-  
-  fn array_len_by_value(_1: [u8; N]) -> usize {
-      debug arr => _1;                     // in scope 0 at $DIR/lower_array_len.rs:+0:43: +0:46
-      let mut _0: usize;                   // return place in scope 0 at $DIR/lower_array_len.rs:+0:60: +0:65
--     let mut _2: &[u8];                   // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--     let mut _3: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--     let mut _4: &[u8; N];                // in scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
-  
-      bb0: {
--         StorageLive(_2);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--         StorageLive(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--         StorageLive(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--         StorageDead(_3);                 // scope 0 at $DIR/lower_array_len.rs:+1:7: +1:8
-          _0 = const N;                    // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--         StorageDead(_4);                 // scope 0 at $DIR/lower_array_len.rs:+1:5: +1:14
--         StorageDead(_2);                 // scope 0 at $DIR/lower_array_len.rs:+1:13: +1:14
-          return;                          // scope 0 at $DIR/lower_array_len.rs:+2:2: +2:2
-      }
-  }
-  
index fc12ee75fcfcd233bccd82626f2e907bfa06ca5d..ea0224b21d72d769972aef5f75c3c0876ae8b495 100644 (file)
@@ -1,8 +1,7 @@
-// compile-flags: -Z mir-opt-level=4
+// unit-test: NormalizeArrayLen
+// compile-flags: -Zmir-enable-passes=+LowerSliceLenCalls
 
 // EMIT_MIR lower_array_len.array_bound.NormalizeArrayLen.diff
-// EMIT_MIR lower_array_len.array_bound.SimplifyLocals.diff
-// EMIT_MIR lower_array_len.array_bound.InstCombine.diff
 pub fn array_bound<const N: usize>(index: usize, slice: &[u8; N]) -> u8 {
     if index < slice.len() {
         slice[index]
@@ -12,8 +11,6 @@
 }
 
 // EMIT_MIR lower_array_len.array_bound_mut.NormalizeArrayLen.diff
-// EMIT_MIR lower_array_len.array_bound_mut.SimplifyLocals.diff
-// EMIT_MIR lower_array_len.array_bound_mut.InstCombine.diff
 pub fn array_bound_mut<const N: usize>(index: usize, slice: &mut [u8; N]) -> u8 {
     if index < slice.len() {
         slice[index]
 }
 
 // EMIT_MIR lower_array_len.array_len.NormalizeArrayLen.diff
-// EMIT_MIR lower_array_len.array_len.SimplifyLocals.diff
-// EMIT_MIR lower_array_len.array_len.InstCombine.diff
 pub fn array_len<const N: usize>(arr: &[u8; N]) -> usize {
     arr.len()
 }
 
 // EMIT_MIR lower_array_len.array_len_by_value.NormalizeArrayLen.diff
-// EMIT_MIR lower_array_len.array_len_by_value.SimplifyLocals.diff
-// EMIT_MIR lower_array_len.array_len_by_value.InstCombine.diff
 pub fn array_len_by_value<const N: usize>(arr: [u8; N]) -> usize {
     arr.len()
 }
diff --git a/src/test/mir-opt/lower_array_len_e2e.array_bound.PreCodegen.after.mir b/src/test/mir-opt/lower_array_len_e2e.array_bound.PreCodegen.after.mir
new file mode 100644 (file)
index 0000000..2c6c93c
--- /dev/null
@@ -0,0 +1,49 @@
+// MIR for `array_bound` after PreCodegen
+
+fn array_bound(_1: usize, _2: &[u8; N]) -> u8 {
+    debug index => _1;                   // in scope 0 at $DIR/lower_array_len_e2e.rs:+0:36: +0:41
+    debug slice => _2;                   // in scope 0 at $DIR/lower_array_len_e2e.rs:+0:50: +0:55
+    let mut _0: u8;                      // return place in scope 0 at $DIR/lower_array_len_e2e.rs:+0:70: +0:72
+    let mut _3: bool;                    // in scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:27
+    let mut _4: usize;                   // in scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:13
+    let mut _5: usize;                   // in scope 0 at $DIR/lower_array_len_e2e.rs:+1:16: +1:27
+    let _6: usize;                       // in scope 0 at $DIR/lower_array_len_e2e.rs:+2:15: +2:20
+    let mut _7: usize;                   // in scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+    let mut _8: bool;                    // in scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+
+    bb0: {
+        StorageLive(_3);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:27
+        StorageLive(_4);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:13
+        _4 = _1;                         // scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:13
+        StorageLive(_5);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+1:16: +1:27
+        _5 = const N;                    // scope 0 at $DIR/lower_array_len_e2e.rs:+1:16: +1:27
+        _3 = Lt(move _4, move _5);       // scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:27
+        StorageDead(_5);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+1:26: +1:27
+        StorageDead(_4);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+1:26: +1:27
+        switchInt(move _3) -> [false: bb3, otherwise: bb1]; // scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:27
+    }
+
+    bb1: {
+        StorageLive(_6);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+2:15: +2:20
+        _6 = _1;                         // scope 0 at $DIR/lower_array_len_e2e.rs:+2:15: +2:20
+        _7 = const N;                    // scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+        _8 = Lt(_6, _7);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+        assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> bb2; // scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+    }
+
+    bb2: {
+        _0 = (*_2)[_6];                  // scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+        StorageDead(_6);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+3:5: +3:6
+        goto -> bb4;                     // scope 0 at $DIR/lower_array_len_e2e.rs:+1:5: +5:6
+    }
+
+    bb3: {
+        _0 = const 42_u8;                // scope 0 at $DIR/lower_array_len_e2e.rs:+4:9: +4:11
+        goto -> bb4;                     // scope 0 at $DIR/lower_array_len_e2e.rs:+1:5: +5:6
+    }
+
+    bb4: {
+        StorageDead(_3);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+5:5: +5:6
+        return;                          // scope 0 at $DIR/lower_array_len_e2e.rs:+6:2: +6:2
+    }
+}
diff --git a/src/test/mir-opt/lower_array_len_e2e.array_bound_mut.PreCodegen.after.mir b/src/test/mir-opt/lower_array_len_e2e.array_bound_mut.PreCodegen.after.mir
new file mode 100644 (file)
index 0000000..aee3a82
--- /dev/null
@@ -0,0 +1,62 @@
+// MIR for `array_bound_mut` after PreCodegen
+
+fn array_bound_mut(_1: usize, _2: &mut [u8; N]) -> u8 {
+    debug index => _1;                   // in scope 0 at $DIR/lower_array_len_e2e.rs:+0:40: +0:45
+    debug slice => _2;                   // in scope 0 at $DIR/lower_array_len_e2e.rs:+0:54: +0:59
+    let mut _0: u8;                      // return place in scope 0 at $DIR/lower_array_len_e2e.rs:+0:78: +0:80
+    let mut _3: bool;                    // in scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:27
+    let mut _4: usize;                   // in scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:13
+    let mut _5: usize;                   // in scope 0 at $DIR/lower_array_len_e2e.rs:+1:16: +1:27
+    let _6: usize;                       // in scope 0 at $DIR/lower_array_len_e2e.rs:+2:15: +2:20
+    let mut _7: usize;                   // in scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+    let mut _8: bool;                    // in scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+    let _9: usize;                       // in scope 0 at $DIR/lower_array_len_e2e.rs:+4:15: +4:16
+    let mut _10: usize;                  // in scope 0 at $DIR/lower_array_len_e2e.rs:+4:9: +4:17
+    let mut _11: bool;                   // in scope 0 at $DIR/lower_array_len_e2e.rs:+4:9: +4:17
+
+    bb0: {
+        StorageLive(_3);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:27
+        StorageLive(_4);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:13
+        _4 = _1;                         // scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:13
+        StorageLive(_5);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+1:16: +1:27
+        _5 = const N;                    // scope 0 at $DIR/lower_array_len_e2e.rs:+1:16: +1:27
+        _3 = Lt(move _4, move _5);       // scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:27
+        StorageDead(_5);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+1:26: +1:27
+        StorageDead(_4);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+1:26: +1:27
+        switchInt(move _3) -> [false: bb3, otherwise: bb1]; // scope 0 at $DIR/lower_array_len_e2e.rs:+1:8: +1:27
+    }
+
+    bb1: {
+        StorageLive(_6);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+2:15: +2:20
+        _6 = _1;                         // scope 0 at $DIR/lower_array_len_e2e.rs:+2:15: +2:20
+        _7 = const N;                    // scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+        _8 = Lt(_6, _7);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+        assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> bb2; // scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+    }
+
+    bb2: {
+        _0 = (*_2)[_6];                  // scope 0 at $DIR/lower_array_len_e2e.rs:+2:9: +2:21
+        StorageDead(_6);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+3:5: +3:6
+        goto -> bb5;                     // scope 0 at $DIR/lower_array_len_e2e.rs:+1:5: +7:6
+    }
+
+    bb3: {
+        StorageLive(_9);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+4:15: +4:16
+        _9 = const 0_usize;              // scope 0 at $DIR/lower_array_len_e2e.rs:+4:15: +4:16
+        _10 = const N;                   // scope 0 at $DIR/lower_array_len_e2e.rs:+4:9: +4:17
+        _11 = Lt(const 0_usize, _10);    // scope 0 at $DIR/lower_array_len_e2e.rs:+4:9: +4:17
+        assert(move _11, "index out of bounds: the length is {} but the index is {}", move _10, const 0_usize) -> bb4; // scope 0 at $DIR/lower_array_len_e2e.rs:+4:9: +4:17
+    }
+
+    bb4: {
+        (*_2)[_9] = const 42_u8;         // scope 0 at $DIR/lower_array_len_e2e.rs:+4:9: +4:22
+        StorageDead(_9);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+4:22: +4:23
+        _0 = const 42_u8;                // scope 0 at $DIR/lower_array_len_e2e.rs:+6:9: +6:11
+        goto -> bb5;                     // scope 0 at $DIR/lower_array_len_e2e.rs:+1:5: +7:6
+    }
+
+    bb5: {
+        StorageDead(_3);                 // scope 0 at $DIR/lower_array_len_e2e.rs:+7:5: +7:6
+        return;                          // scope 0 at $DIR/lower_array_len_e2e.rs:+8:2: +8:2
+    }
+}
diff --git a/src/test/mir-opt/lower_array_len_e2e.array_len.PreCodegen.after.mir b/src/test/mir-opt/lower_array_len_e2e.array_len.PreCodegen.after.mir
new file mode 100644 (file)
index 0000000..4b19f67
--- /dev/null
@@ -0,0 +1,11 @@
+// MIR for `array_len` after PreCodegen
+
+fn array_len(_1: &[u8; N]) -> usize {
+    debug arr => _1;                     // in scope 0 at $DIR/lower_array_len_e2e.rs:+0:34: +0:37
+    let mut _0: usize;                   // return place in scope 0 at $DIR/lower_array_len_e2e.rs:+0:52: +0:57
+
+    bb0: {
+        _0 = const N;                    // scope 0 at $DIR/lower_array_len_e2e.rs:+1:5: +1:14
+        return;                          // scope 0 at $DIR/lower_array_len_e2e.rs:+2:2: +2:2
+    }
+}
diff --git a/src/test/mir-opt/lower_array_len_e2e.array_len_by_value.PreCodegen.after.mir b/src/test/mir-opt/lower_array_len_e2e.array_len_by_value.PreCodegen.after.mir
new file mode 100644 (file)
index 0000000..4dc0ba9
--- /dev/null
@@ -0,0 +1,11 @@
+// MIR for `array_len_by_value` after PreCodegen
+
+fn array_len_by_value(_1: [u8; N]) -> usize {
+    debug arr => _1;                     // in scope 0 at $DIR/lower_array_len_e2e.rs:+0:43: +0:46
+    let mut _0: usize;                   // return place in scope 0 at $DIR/lower_array_len_e2e.rs:+0:60: +0:65
+
+    bb0: {
+        _0 = const N;                    // scope 0 at $DIR/lower_array_len_e2e.rs:+1:5: +1:14
+        return;                          // scope 0 at $DIR/lower_array_len_e2e.rs:+2:2: +2:2
+    }
+}
diff --git a/src/test/mir-opt/lower_array_len_e2e.rs b/src/test/mir-opt/lower_array_len_e2e.rs
new file mode 100644 (file)
index 0000000..49b35d5
--- /dev/null
@@ -0,0 +1,39 @@
+// compile-flags: -Z mir-opt-level=4
+
+// EMIT_MIR lower_array_len_e2e.array_bound.PreCodegen.after.mir
+pub fn array_bound<const N: usize>(index: usize, slice: &[u8; N]) -> u8 {
+    if index < slice.len() {
+        slice[index]
+    } else {
+        42
+    }
+}
+
+// EMIT_MIR lower_array_len_e2e.array_bound_mut.PreCodegen.after.mir
+pub fn array_bound_mut<const N: usize>(index: usize, slice: &mut [u8; N]) -> u8 {
+    if index < slice.len() {
+        slice[index]
+    } else {
+        slice[0] = 42;
+
+        42
+    }
+}
+
+// EMIT_MIR lower_array_len_e2e.array_len.PreCodegen.after.mir
+pub fn array_len<const N: usize>(arr: &[u8; N]) -> usize {
+    arr.len()
+}
+
+// EMIT_MIR lower_array_len_e2e.array_len_by_value.PreCodegen.after.mir
+pub fn array_len_by_value<const N: usize>(arr: [u8; N]) -> usize {
+    arr.len()
+}
+
+fn main() {
+    let _ = array_bound(3, &[0, 1, 2, 3]);
+    let mut tmp = [0, 1, 2, 3, 4];
+    let _ = array_bound_mut(3, &mut [0, 1, 2, 3]);
+    let _ = array_len(&[0]);
+    let _ = array_len_by_value([0, 2]);
+}
index 5c635e2220ed707ce1de3fa180afae64e08f1413..3389db733b992a3a0576e83bae9c2d04a0490348 100644 (file)
@@ -7,7 +7,7 @@
       bb0: {
 -         _0 = std::intrinsics::min_align_of::<T>() -> bb1; // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:42
 -                                          // mir::Constant
--                                          // + span: $DIR/lower_intrinsics.rs:19:5: 19:40
+-                                          // + span: $DIR/lower_intrinsics.rs:21:5: 21:40
 -                                          // + literal: Const { ty: extern "rust-intrinsic" fn() -> usize {std::intrinsics::min_align_of::<T>}, val: Value(<ZST>) }
 +         _0 = AlignOf(T);                 // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:42
 +         goto -> bb1;                     // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:42
index 8a80de32f3ae36d4c7916cc1849c93b4abed061a..f92ff9faf979686efb80d8edd3b0ba4def816b80 100644 (file)
@@ -31,7 +31,7 @@
           _3 = &(*_4);                     // scope 0 at $DIR/lower_intrinsics.rs:+1:42: +1:44
 -         _2 = discriminant_value::<T>(move _3) -> bb1; // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:45
 -                                          // mir::Constant
--                                          // + span: $DIR/lower_intrinsics.rs:74:5: 74:41
+-                                          // + span: $DIR/lower_intrinsics.rs:49:5: 49:41
 -                                          // + literal: Const { ty: for<'r> extern "rust-intrinsic" fn(&'r T) -> <T as DiscriminantKind>::Discriminant {discriminant_value::<T>}, val: Value(<ZST>) }
 +         _2 = discriminant((*_3));        // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:45
 +         goto -> bb1;                     // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:45
           StorageLive(_7);                 // scope 0 at $DIR/lower_intrinsics.rs:+2:42: +2:44
           _19 = const discriminant::<T>::promoted[2]; // scope 0 at $DIR/lower_intrinsics.rs:+2:42: +2:44
                                            // mir::Constant
-                                           // + span: $DIR/lower_intrinsics.rs:75:42: 75:44
+                                           // + span: $DIR/lower_intrinsics.rs:50:42: 50:44
                                            // + literal: Const { ty: &i32, val: Unevaluated(discriminant, [T], Some(promoted[2])) }
           _7 = &(*_19);                    // scope 0 at $DIR/lower_intrinsics.rs:+2:42: +2:44
           _6 = &(*_7);                     // scope 0 at $DIR/lower_intrinsics.rs:+2:42: +2:44
 -         _5 = discriminant_value::<i32>(move _6) -> bb2; // scope 0 at $DIR/lower_intrinsics.rs:+2:5: +2:45
 -                                          // mir::Constant
--                                          // + span: $DIR/lower_intrinsics.rs:75:5: 75:41
+-                                          // + span: $DIR/lower_intrinsics.rs:50:5: 50:41
 -                                          // + literal: Const { ty: for<'r> extern "rust-intrinsic" fn(&'r i32) -> <i32 as DiscriminantKind>::Discriminant {discriminant_value::<i32>}, val: Value(<ZST>) }
 +         _5 = discriminant((*_6));        // scope 0 at $DIR/lower_intrinsics.rs:+2:5: +2:45
 +         goto -> bb2;                     // scope 0 at $DIR/lower_intrinsics.rs:+2:5: +2:45
           StorageLive(_11);                // scope 0 at $DIR/lower_intrinsics.rs:+3:42: +3:45
           _18 = const discriminant::<T>::promoted[1]; // scope 0 at $DIR/lower_intrinsics.rs:+3:42: +3:45
                                            // mir::Constant
-                                           // + span: $DIR/lower_intrinsics.rs:76:42: 76:45
+                                           // + span: $DIR/lower_intrinsics.rs:51:42: 51:45
                                            // + literal: Const { ty: &(), val: Unevaluated(discriminant, [T], Some(promoted[1])) }
           _11 = &(*_18);                   // scope 0 at $DIR/lower_intrinsics.rs:+3:42: +3:45
           _10 = &(*_11);                   // scope 0 at $DIR/lower_intrinsics.rs:+3:42: +3:45
 -         _9 = discriminant_value::<()>(move _10) -> bb3; // scope 0 at $DIR/lower_intrinsics.rs:+3:5: +3:46
 -                                          // mir::Constant
--                                          // + span: $DIR/lower_intrinsics.rs:76:5: 76:41
+-                                          // + span: $DIR/lower_intrinsics.rs:51:5: 51:41
 -                                          // + literal: Const { ty: for<'r> extern "rust-intrinsic" fn(&'r ()) -> <() as DiscriminantKind>::Discriminant {discriminant_value::<()>}, val: Value(<ZST>) }
 +         _9 = discriminant((*_10));       // scope 0 at $DIR/lower_intrinsics.rs:+3:5: +3:46
 +         goto -> bb3;                     // scope 0 at $DIR/lower_intrinsics.rs:+3:5: +3:46
           StorageLive(_15);                // scope 0 at $DIR/lower_intrinsics.rs:+4:42: +4:47
           _17 = const discriminant::<T>::promoted[0]; // scope 0 at $DIR/lower_intrinsics.rs:+4:42: +4:47
                                            // mir::Constant
-                                           // + span: $DIR/lower_intrinsics.rs:77:42: 77:47
+                                           // + span: $DIR/lower_intrinsics.rs:52:42: 52:47
                                            // + literal: Const { ty: &E, val: Unevaluated(discriminant, [T], Some(promoted[0])) }
           _15 = &(*_17);                   // scope 0 at $DIR/lower_intrinsics.rs:+4:42: +4:47
           _14 = &(*_15);                   // scope 0 at $DIR/lower_intrinsics.rs:+4:42: +4:47
 -         _13 = discriminant_value::<E>(move _14) -> bb4; // scope 0 at $DIR/lower_intrinsics.rs:+4:5: +4:48
 -                                          // mir::Constant
--                                          // + span: $DIR/lower_intrinsics.rs:77:5: 77:41
+-                                          // + span: $DIR/lower_intrinsics.rs:52:5: 52:41
 -                                          // + literal: Const { ty: for<'r> extern "rust-intrinsic" fn(&'r E) -> <E as DiscriminantKind>::Discriminant {discriminant_value::<E>}, val: Value(<ZST>) }
 +         _13 = discriminant((*_14));      // scope 0 at $DIR/lower_intrinsics.rs:+4:5: +4:48
 +         goto -> bb4;                     // scope 0 at $DIR/lower_intrinsics.rs:+4:5: +4:48
           StorageDead(_15);                // scope 0 at $DIR/lower_intrinsics.rs:+4:48: +4:49
           StorageDead(_13);                // scope 0 at $DIR/lower_intrinsics.rs:+4:48: +4:49
           _0 = const ();                   // scope 0 at $DIR/lower_intrinsics.rs:+0:30: +5:2
-          drop(_1) -> bb5;                 // scope 0 at $DIR/lower_intrinsics.rs:+5:1: +5:2
+          drop(_1) -> [return: bb5, unwind: bb6]; // scope 0 at $DIR/lower_intrinsics.rs:+5:1: +5:2
       }
   
       bb5: {
           return;                          // scope 0 at $DIR/lower_intrinsics.rs:+5:2: +5:2
       }
+  
+      bb6 (cleanup): {
+          resume;                          // scope 0 at $DIR/lower_intrinsics.rs:+0:1: +5:2
+      }
   }
   
diff --git a/src/test/mir-opt/lower_intrinsics.f_u64.PreCodegen.before.mir b/src/test/mir-opt/lower_intrinsics.f_u64.PreCodegen.before.mir
deleted file mode 100644 (file)
index 2a9a099..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-// MIR for `f_u64` before PreCodegen
-
-fn f_u64() -> () {
-    let mut _0: ();                      // return place in scope 0 at $DIR/lower_intrinsics.rs:+0:16: +0:16
-    let mut _1: u64;                     // in scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:21
-    scope 1 (inlined f_dispatch::<u64>) { // at $DIR/lower_intrinsics.rs:40:5: 40:21
-        debug t => _1;                   // in scope 1 at $DIR/lower_intrinsics.rs:44:22: 44:23
-        let _2: ();                      // in scope 1 at $DIR/lower_intrinsics.rs:48:9: 48:21
-        let mut _3: u64;                 // in scope 1 at $DIR/lower_intrinsics.rs:48:19: 48:20
-        scope 2 (inlined std::mem::size_of::<u64>) { // at $DIR/lower_intrinsics.rs:45:8: 45:32
-        }
-    }
-
-    bb0: {
-        StorageLive(_1);                 // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:21
-        _1 = const 0_u64;                // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:21
-        StorageLive(_2);                 // scope 1 at $DIR/lower_intrinsics.rs:48:9: 48:21
-        StorageLive(_3);                 // scope 1 at $DIR/lower_intrinsics.rs:48:19: 48:20
-        _3 = move _1;                    // scope 1 at $DIR/lower_intrinsics.rs:48:19: 48:20
-        _2 = f_non_zst::<u64>(move _3) -> bb1; // scope 1 at $DIR/lower_intrinsics.rs:48:9: 48:21
-                                         // mir::Constant
-                                         // + span: $DIR/lower_intrinsics.rs:48:9: 48:18
-                                         // + literal: Const { ty: fn(u64) {f_non_zst::<u64>}, val: Value(<ZST>) }
-    }
-
-    bb1: {
-        StorageDead(_3);                 // scope 1 at $DIR/lower_intrinsics.rs:48:20: 48:21
-        StorageDead(_2);                 // scope 1 at $DIR/lower_intrinsics.rs:48:21: 48:22
-        StorageDead(_1);                 // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:21
-        return;                          // scope 0 at $DIR/lower_intrinsics.rs:+2:2: +2:2
-    }
-}
diff --git a/src/test/mir-opt/lower_intrinsics.f_unit.PreCodegen.before.mir b/src/test/mir-opt/lower_intrinsics.f_unit.PreCodegen.before.mir
deleted file mode 100644 (file)
index 5783822..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-// MIR for `f_unit` before PreCodegen
-
-fn f_unit() -> () {
-    let mut _0: ();                      // return place in scope 0 at $DIR/lower_intrinsics.rs:+0:17: +0:17
-    let mut _1: ();                      // in scope 0 at $DIR/lower_intrinsics.rs:+1:16: +1:18
-    scope 1 (inlined f_dispatch::<()>) { // at $DIR/lower_intrinsics.rs:34:5: 34:19
-        debug t => _1;                   // in scope 1 at $DIR/lower_intrinsics.rs:44:22: 44:23
-        let _2: ();                      // in scope 1 at $DIR/lower_intrinsics.rs:46:9: 46:17
-        let mut _3: ();                  // in scope 1 at $DIR/lower_intrinsics.rs:46:15: 46:16
-        scope 2 (inlined std::mem::size_of::<()>) { // at $DIR/lower_intrinsics.rs:45:8: 45:32
-        }
-    }
-
-    bb0: {
-        StorageLive(_1);                 // scope 0 at $DIR/lower_intrinsics.rs:+1:16: +1:18
-        StorageLive(_2);                 // scope 1 at $DIR/lower_intrinsics.rs:46:9: 46:17
-        StorageLive(_3);                 // scope 1 at $DIR/lower_intrinsics.rs:46:15: 46:16
-        _2 = f_zst::<()>(move _3) -> bb1; // scope 1 at $DIR/lower_intrinsics.rs:46:9: 46:17
-                                         // mir::Constant
-                                         // + span: $DIR/lower_intrinsics.rs:46:9: 46:14
-                                         // + literal: Const { ty: fn(()) {f_zst::<()>}, val: Value(<ZST>) }
-    }
-
-    bb1: {
-        StorageDead(_3);                 // scope 1 at $DIR/lower_intrinsics.rs:46:16: 46:17
-        StorageDead(_2);                 // scope 1 at $DIR/lower_intrinsics.rs:46:17: 46:18
-        StorageDead(_1);                 // scope 0 at $DIR/lower_intrinsics.rs:+1:18: +1:19
-        return;                          // scope 0 at $DIR/lower_intrinsics.rs:+2:2: +2:2
-    }
-}
index e6a2f6512f55af51df45fa5cc4b7a7ae8ece4190..4cbbc02c94333514a9091517956216b63945092f 100644 (file)
@@ -11,7 +11,7 @@
           _2 = move _1;                    // scope 0 at $DIR/lower_intrinsics.rs:+1:30: +1:31
 -         _0 = std::intrinsics::forget::<T>(move _2) -> bb1; // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:32
 -                                          // mir::Constant
--                                          // + span: $DIR/lower_intrinsics.rs:24:5: 24:29
+-                                          // + span: $DIR/lower_intrinsics.rs:26:5: 26:29
 -                                          // + literal: Const { ty: extern "rust-intrinsic" fn(T) {std::intrinsics::forget::<T>}, val: Value(<ZST>) }
 +         _0 = const ();                   // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:32
 +         goto -> bb1;                     // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:32
index 1ab2f2a0a046828c32577c7ce3721661dfa879bd..d8cd5f59a3532fa0bcf496c6502ecae349ddbaa6 100644 (file)
@@ -13,7 +13,7 @@
           StorageLive(_1);                 // scope 0 at $DIR/lower_intrinsics.rs:+2:9: +2:18
           _1 = std::intrinsics::size_of::<T>; // scope 0 at $DIR/lower_intrinsics.rs:+2:21: +2:51
                                            // mir::Constant
-                                           // + span: $DIR/lower_intrinsics.rs:62:21: 62:51
+                                           // + span: $DIR/lower_intrinsics.rs:37:21: 37:51
                                            // + literal: Const { ty: extern "rust-intrinsic" fn() -> usize {std::intrinsics::size_of::<T>}, val: Value(<ZST>) }
           StorageLive(_2);                 // scope 1 at $DIR/lower_intrinsics.rs:+3:5: +3:14
           _2 = _1;                         // scope 1 at $DIR/lower_intrinsics.rs:+3:5: +3:14
index eab51b65f1a19a6e868dbe6b4c24221a5d7b917e..195543d42bb5ba157b8a46c5d2b5fed5c1a96a13 100644 (file)
@@ -1,4 +1,6 @@
-// compile-flags: -Cpanic=abort
+// unit-test: LowerIntrinsics
+// ignore-wasm32 compiled with panic=abort by default
+
 #![feature(core_intrinsics)]
 #![crate_type = "lib"]
 
@@ -29,33 +31,6 @@ pub fn unreachable() -> ! {
     unsafe { core::intrinsics::unreachable() };
 }
 
-// EMIT_MIR lower_intrinsics.f_unit.PreCodegen.before.mir
-pub fn f_unit() {
-    f_dispatch(());
-}
-
-
-// EMIT_MIR lower_intrinsics.f_u64.PreCodegen.before.mir
-pub fn f_u64() {
-    f_dispatch(0u64);
-}
-
-#[inline(always)]
-pub fn f_dispatch<T>(t: T) {
-    if std::mem::size_of::<T>() == 0 {
-        f_zst(t);
-    } else {
-        f_non_zst(t);
-    }
-}
-
-#[inline(never)]
-pub fn f_zst<T>(_t: T) {
-}
-
-#[inline(never)]
-pub fn f_non_zst<T>(_t: T) {}
-
 // EMIT_MIR lower_intrinsics.non_const.LowerIntrinsics.diff
 pub fn non_const<T>() -> usize {
     // Check that lowering works with non-const operand as a func.
index 11b27976b551c9f171e11cbe7f9b0a0edb3ce07f..cf0ab73a5d4b1786b0eceb29f70859da81eef00d 100644 (file)
@@ -7,7 +7,7 @@
       bb0: {
 -         _0 = std::intrinsics::size_of::<T>() -> bb1; // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:37
 -                                          // mir::Constant
--                                          // + span: $DIR/lower_intrinsics.rs:14:5: 14:35
+-                                          // + span: $DIR/lower_intrinsics.rs:16:5: 16:35
 -                                          // + literal: Const { ty: extern "rust-intrinsic" fn() -> usize {std::intrinsics::size_of::<T>}, val: Value(<ZST>) }
 +         _0 = SizeOf(T);                  // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:37
 +         goto -> bb1;                     // scope 0 at $DIR/lower_intrinsics.rs:+1:5: +1:37
index ac077e85b04f357a3ed5eab40a6182c2ec3e63b9..6f17d44516de194475d6f93250ee6b42443a22d5 100644 (file)
@@ -14,7 +14,7 @@
           StorageLive(_3);                 // scope 1 at $DIR/lower_intrinsics.rs:+1:14: +1:45
 -         _3 = std::intrinsics::unreachable(); // scope 1 at $DIR/lower_intrinsics.rs:+1:14: +1:45
 -                                          // mir::Constant
--                                          // + span: $DIR/lower_intrinsics.rs:29:14: 29:43
+-                                          // + span: $DIR/lower_intrinsics.rs:31:14: 31:43
 -                                          // + literal: Const { ty: unsafe extern "rust-intrinsic" fn() -> ! {std::intrinsics::unreachable}, val: Value(<ZST>) }
 +         unreachable;                     // scope 1 at $DIR/lower_intrinsics.rs:+1:14: +1:45
       }
index e0a5416b22b5fbe431578dadf506d8c7fab940c9..22ef75fd8046089c57c566a5705ac77d91166ac9 100644 (file)
@@ -32,7 +32,7 @@
           _5 = _2;                         // scope 0 at $DIR/lower_intrinsics.rs:+1:48: +1:49
 -         _3 = wrapping_add::<i32>(move _4, move _5) -> bb1; // scope 0 at $DIR/lower_intrinsics.rs:+1:14: +1:50
 -                                          // mir::Constant
--                                          // + span: $DIR/lower_intrinsics.rs:7:14: 7:44
+-                                          // + span: $DIR/lower_intrinsics.rs:9:14: 9:44
 -                                          // + literal: Const { ty: extern "rust-intrinsic" fn(i32, i32) -> i32 {wrapping_add::<i32>}, val: Value(<ZST>) }
 +         _3 = Add(move _4, move _5);      // scope 0 at $DIR/lower_intrinsics.rs:+1:14: +1:50
 +         goto -> bb1;                     // scope 0 at $DIR/lower_intrinsics.rs:+1:14: +1:50
@@ -48,7 +48,7 @@
           _8 = _2;                         // scope 1 at $DIR/lower_intrinsics.rs:+2:48: +2:49
 -         _6 = wrapping_sub::<i32>(move _7, move _8) -> bb2; // scope 1 at $DIR/lower_intrinsics.rs:+2:14: +2:50
 -                                          // mir::Constant
--                                          // + span: $DIR/lower_intrinsics.rs:8:14: 8:44
+-                                          // + span: $DIR/lower_intrinsics.rs:10:14: 10:44
 -                                          // + literal: Const { ty: extern "rust-intrinsic" fn(i32, i32) -> i32 {wrapping_sub::<i32>}, val: Value(<ZST>) }
 +         _6 = Sub(move _7, move _8);      // scope 1 at $DIR/lower_intrinsics.rs:+2:14: +2:50
 +         goto -> bb2;                     // scope 1 at $DIR/lower_intrinsics.rs:+2:14: +2:50
@@ -64,7 +64,7 @@
           _11 = _2;                        // scope 2 at $DIR/lower_intrinsics.rs:+3:48: +3:49
 -         _9 = wrapping_mul::<i32>(move _10, move _11) -> bb3; // scope 2 at $DIR/lower_intrinsics.rs:+3:14: +3:50
 -                                          // mir::Constant
--                                          // + span: $DIR/lower_intrinsics.rs:9:14: 9:44
+-                                          // + span: $DIR/lower_intrinsics.rs:11:14: 11:44
 -                                          // + literal: Const { ty: extern "rust-intrinsic" fn(i32, i32) -> i32 {wrapping_mul::<i32>}, val: Value(<ZST>) }
 +         _9 = Mul(move _10, move _11);    // scope 2 at $DIR/lower_intrinsics.rs:+3:14: +3:50
 +         goto -> bb3;                     // scope 2 at $DIR/lower_intrinsics.rs:+3:14: +3:50
diff --git a/src/test/mir-opt/lower_intrinsics_e2e.f_u64.PreCodegen.after.mir b/src/test/mir-opt/lower_intrinsics_e2e.f_u64.PreCodegen.after.mir
new file mode 100644 (file)
index 0000000..8e18532
--- /dev/null
@@ -0,0 +1,32 @@
+// MIR for `f_u64` after PreCodegen
+
+fn f_u64() -> () {
+    let mut _0: ();                      // return place in scope 0 at $DIR/lower_intrinsics_e2e.rs:+0:16: +0:16
+    let mut _1: u64;                     // in scope 0 at $DIR/lower_intrinsics_e2e.rs:+1:5: +1:21
+    scope 1 (inlined f_dispatch::<u64>) { // at $DIR/lower_intrinsics_e2e.rs:15:5: 15:21
+        debug t => _1;                   // in scope 1 at $DIR/lower_intrinsics_e2e.rs:19:22: 19:23
+        let _2: ();                      // in scope 1 at $DIR/lower_intrinsics_e2e.rs:23:9: 23:21
+        let mut _3: u64;                 // in scope 1 at $DIR/lower_intrinsics_e2e.rs:23:19: 23:20
+        scope 2 (inlined std::mem::size_of::<u64>) { // at $DIR/lower_intrinsics_e2e.rs:20:8: 20:32
+        }
+    }
+
+    bb0: {
+        StorageLive(_1);                 // scope 0 at $DIR/lower_intrinsics_e2e.rs:+1:5: +1:21
+        _1 = const 0_u64;                // scope 0 at $DIR/lower_intrinsics_e2e.rs:+1:5: +1:21
+        StorageLive(_2);                 // scope 1 at $DIR/lower_intrinsics_e2e.rs:23:9: 23:21
+        StorageLive(_3);                 // scope 1 at $DIR/lower_intrinsics_e2e.rs:23:19: 23:20
+        _3 = move _1;                    // scope 1 at $DIR/lower_intrinsics_e2e.rs:23:19: 23:20
+        _2 = f_non_zst::<u64>(move _3) -> bb1; // scope 1 at $DIR/lower_intrinsics_e2e.rs:23:9: 23:21
+                                         // mir::Constant
+                                         // + span: $DIR/lower_intrinsics_e2e.rs:23:9: 23:18
+                                         // + literal: Const { ty: fn(u64) {f_non_zst::<u64>}, val: Value(<ZST>) }
+    }
+
+    bb1: {
+        StorageDead(_3);                 // scope 1 at $DIR/lower_intrinsics_e2e.rs:23:20: 23:21
+        StorageDead(_2);                 // scope 1 at $DIR/lower_intrinsics_e2e.rs:23:21: 23:22
+        StorageDead(_1);                 // scope 0 at $DIR/lower_intrinsics_e2e.rs:+1:5: +1:21
+        return;                          // scope 0 at $DIR/lower_intrinsics_e2e.rs:+2:2: +2:2
+    }
+}
diff --git a/src/test/mir-opt/lower_intrinsics_e2e.f_unit.PreCodegen.after.mir b/src/test/mir-opt/lower_intrinsics_e2e.f_unit.PreCodegen.after.mir
new file mode 100644 (file)
index 0000000..a5b396c
--- /dev/null
@@ -0,0 +1,30 @@
+// MIR for `f_unit` after PreCodegen
+
+fn f_unit() -> () {
+    let mut _0: ();                      // return place in scope 0 at $DIR/lower_intrinsics_e2e.rs:+0:17: +0:17
+    let mut _1: ();                      // in scope 0 at $DIR/lower_intrinsics_e2e.rs:+1:16: +1:18
+    scope 1 (inlined f_dispatch::<()>) { // at $DIR/lower_intrinsics_e2e.rs:9:5: 9:19
+        debug t => _1;                   // in scope 1 at $DIR/lower_intrinsics_e2e.rs:19:22: 19:23
+        let _2: ();                      // in scope 1 at $DIR/lower_intrinsics_e2e.rs:21:9: 21:17
+        let mut _3: ();                  // in scope 1 at $DIR/lower_intrinsics_e2e.rs:21:15: 21:16
+        scope 2 (inlined std::mem::size_of::<()>) { // at $DIR/lower_intrinsics_e2e.rs:20:8: 20:32
+        }
+    }
+
+    bb0: {
+        StorageLive(_1);                 // scope 0 at $DIR/lower_intrinsics_e2e.rs:+1:16: +1:18
+        StorageLive(_2);                 // scope 1 at $DIR/lower_intrinsics_e2e.rs:21:9: 21:17
+        StorageLive(_3);                 // scope 1 at $DIR/lower_intrinsics_e2e.rs:21:15: 21:16
+        _2 = f_zst::<()>(move _3) -> bb1; // scope 1 at $DIR/lower_intrinsics_e2e.rs:21:9: 21:17
+                                         // mir::Constant
+                                         // + span: $DIR/lower_intrinsics_e2e.rs:21:9: 21:14
+                                         // + literal: Const { ty: fn(()) {f_zst::<()>}, val: Value(<ZST>) }
+    }
+
+    bb1: {
+        StorageDead(_3);                 // scope 1 at $DIR/lower_intrinsics_e2e.rs:21:16: 21:17
+        StorageDead(_2);                 // scope 1 at $DIR/lower_intrinsics_e2e.rs:21:17: 21:18
+        StorageDead(_1);                 // scope 0 at $DIR/lower_intrinsics_e2e.rs:+1:18: +1:19
+        return;                          // scope 0 at $DIR/lower_intrinsics_e2e.rs:+2:2: +2:2
+    }
+}
diff --git a/src/test/mir-opt/lower_intrinsics_e2e.rs b/src/test/mir-opt/lower_intrinsics_e2e.rs
new file mode 100644 (file)
index 0000000..872ef59
--- /dev/null
@@ -0,0 +1,32 @@
+// Checks that we do not have any branches in the MIR for the two tested functions.
+
+// compile-flags: -Cpanic=abort
+#![feature(core_intrinsics)]
+#![crate_type = "lib"]
+
+// EMIT_MIR lower_intrinsics_e2e.f_unit.PreCodegen.after.mir
+pub fn f_unit() {
+    f_dispatch(());
+}
+
+
+// EMIT_MIR lower_intrinsics_e2e.f_u64.PreCodegen.after.mir
+pub fn f_u64() {
+    f_dispatch(0u64);
+}
+
+#[inline(always)]
+pub fn f_dispatch<T>(t: T) {
+    if std::mem::size_of::<T>() == 0 {
+        f_zst(t);
+    } else {
+        f_non_zst(t);
+    }
+}
+
+#[inline(never)]
+pub fn f_zst<T>(_t: T) {
+}
+
+#[inline(never)]
+pub fn f_non_zst<T>(_t: T) {}
index 2005c10efa93bf6700cae844553ddd21159e9fef..f9eeb1ea5b96095be840b3afd1c193409cdb55ba 100644 (file)
@@ -41,7 +41,7 @@
 -         _3 = const false;                // scope 4 at $DIR/matches_reduce_branches.rs:+16:13: +16:22
 -         _4 = const false;                // scope 4 at $DIR/matches_reduce_branches.rs:+17:13: +17:22
 -         _5 = const true;                 // scope 4 at $DIR/matches_reduce_branches.rs:+18:13: +18:21
--         nop;                             // scope 4 at $DIR/matches_reduce_branches.rs:+19:13: +19:15
+-         Deinit(_6);                      // scope 4 at $DIR/matches_reduce_branches.rs:+19:13: +19:15
 -         goto -> bb3;                     // scope 4 at $DIR/matches_reduce_branches.rs:+19:13: +19:15
 -     }
 - 
@@ -54,7 +54,7 @@
 +         _3 = Eq(_11, const 7_i32);       // scope 4 at $DIR/matches_reduce_branches.rs:+9:13: +9:21
           _4 = const false;                // scope 4 at $DIR/matches_reduce_branches.rs:+10:13: +10:22
           _5 = const true;                 // scope 4 at $DIR/matches_reduce_branches.rs:+11:13: +11:21
--         nop;                             // scope 4 at $DIR/matches_reduce_branches.rs:+12:13: +12:15
+          Deinit(_6);                      // scope 4 at $DIR/matches_reduce_branches.rs:+12:13: +12:15
 -         goto -> bb3;                     // scope 4 at $DIR/matches_reduce_branches.rs:+12:13: +12:15
 -     }
 - 
index 2005c10efa93bf6700cae844553ddd21159e9fef..f9eeb1ea5b96095be840b3afd1c193409cdb55ba 100644 (file)
@@ -41,7 +41,7 @@
 -         _3 = const false;                // scope 4 at $DIR/matches_reduce_branches.rs:+16:13: +16:22
 -         _4 = const false;                // scope 4 at $DIR/matches_reduce_branches.rs:+17:13: +17:22
 -         _5 = const true;                 // scope 4 at $DIR/matches_reduce_branches.rs:+18:13: +18:21
--         nop;                             // scope 4 at $DIR/matches_reduce_branches.rs:+19:13: +19:15
+-         Deinit(_6);                      // scope 4 at $DIR/matches_reduce_branches.rs:+19:13: +19:15
 -         goto -> bb3;                     // scope 4 at $DIR/matches_reduce_branches.rs:+19:13: +19:15
 -     }
 - 
@@ -54,7 +54,7 @@
 +         _3 = Eq(_11, const 7_i32);       // scope 4 at $DIR/matches_reduce_branches.rs:+9:13: +9:21
           _4 = const false;                // scope 4 at $DIR/matches_reduce_branches.rs:+10:13: +10:22
           _5 = const true;                 // scope 4 at $DIR/matches_reduce_branches.rs:+11:13: +11:21
--         nop;                             // scope 4 at $DIR/matches_reduce_branches.rs:+12:13: +12:15
+          Deinit(_6);                      // scope 4 at $DIR/matches_reduce_branches.rs:+12:13: +12:15
 -         goto -> bb3;                     // scope 4 at $DIR/matches_reduce_branches.rs:+12:13: +12:15
 -     }
 - 
index b7862e5678f23598d3ba2afb8b144d73309b0cdb..0b40b3be8bdd41efd5e773ab32228a05b64f394c 100644 (file)
@@ -4,26 +4,51 @@
   fn foo(_1: Option<()>) -> () {
       debug bar => _1;                     // in scope 0 at $DIR/matches_reduce_branches.rs:+0:8: +0:11
       let mut _0: ();                      // return place in scope 0 at $DIR/matches_reduce_branches.rs:+0:25: +0:25
-      let mut _2: isize;                   // in scope 0 at $DIR/matches_reduce_branches.rs:+1:22: +1:26
-+     let mut _3: isize;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+      let mut _2: bool;                    // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+      let mut _3: isize;                   // in scope 0 at $DIR/matches_reduce_branches.rs:+1:22: +1:26
++     let mut _4: isize;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
   
       bb0: {
-          _2 = discriminant(_1);           // scope 0 at $DIR/matches_reduce_branches.rs:+1:17: +1:20
--         switchInt(move _2) -> [0_isize: bb2, otherwise: bb1]; // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
--     }
-- 
--     bb1: {
+          StorageLive(_2);                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+          _3 = discriminant(_1);           // scope 0 at $DIR/matches_reduce_branches.rs:+1:17: +1:20
+-         switchInt(move _3) -> [0_isize: bb2, otherwise: bb1]; // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
++         StorageLive(_4);                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
++         _4 = move _3;                    // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
++         _2 = Eq(_4, const 0_isize);      // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
++         StorageDead(_4);                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
++         switchInt(move _2) -> [false: bb2, otherwise: bb1]; // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+      }
+  
+      bb1: {
+-         _2 = const false;                // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
 -         goto -> bb3;                     // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
 -     }
 - 
 -     bb2: {
+-         _2 = const true;                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
 -         goto -> bb3;                     // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
 -     }
 - 
 -     bb3: {
-+         StorageLive(_3);                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-+         _3 = move _2;                    // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-+         StorageDead(_3);                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+-         switchInt(move _2) -> [false: bb5, otherwise: bb4]; // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+-     }
+- 
+-     bb4: {
+          Deinit(_0);                      // scope 0 at $DIR/matches_reduce_branches.rs:+2:9: +2:11
+-         goto -> bb6;                     // scope 0 at $DIR/matches_reduce_branches.rs:+1:5: +3:6
++         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+1:5: +3:6
+      }
+  
+-     bb5: {
++     bb2: {
+          _0 = const ();                   // scope 0 at $DIR/matches_reduce_branches.rs:+3:6: +3:6
+-         goto -> bb6;                     // scope 0 at $DIR/matches_reduce_branches.rs:+1:5: +3:6
++         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+1:5: +3:6
+      }
+  
+-     bb6: {
++     bb3: {
+          StorageDead(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+3:5: +3:6
           return;                          // scope 0 at $DIR/matches_reduce_branches.rs:+4:2: +4:2
       }
   }
index b7862e5678f23598d3ba2afb8b144d73309b0cdb..0b40b3be8bdd41efd5e773ab32228a05b64f394c 100644 (file)
@@ -4,26 +4,51 @@
   fn foo(_1: Option<()>) -> () {
       debug bar => _1;                     // in scope 0 at $DIR/matches_reduce_branches.rs:+0:8: +0:11
       let mut _0: ();                      // return place in scope 0 at $DIR/matches_reduce_branches.rs:+0:25: +0:25
-      let mut _2: isize;                   // in scope 0 at $DIR/matches_reduce_branches.rs:+1:22: +1:26
-+     let mut _3: isize;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+      let mut _2: bool;                    // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+      let mut _3: isize;                   // in scope 0 at $DIR/matches_reduce_branches.rs:+1:22: +1:26
++     let mut _4: isize;                   // in scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
   
       bb0: {
-          _2 = discriminant(_1);           // scope 0 at $DIR/matches_reduce_branches.rs:+1:17: +1:20
--         switchInt(move _2) -> [0_isize: bb2, otherwise: bb1]; // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
--     }
-- 
--     bb1: {
+          StorageLive(_2);                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+          _3 = discriminant(_1);           // scope 0 at $DIR/matches_reduce_branches.rs:+1:17: +1:20
+-         switchInt(move _3) -> [0_isize: bb2, otherwise: bb1]; // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
++         StorageLive(_4);                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
++         _4 = move _3;                    // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
++         _2 = Eq(_4, const 0_isize);      // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
++         StorageDead(_4);                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
++         switchInt(move _2) -> [false: bb2, otherwise: bb1]; // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+      }
+  
+      bb1: {
+-         _2 = const false;                // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
 -         goto -> bb3;                     // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
 -     }
 - 
 -     bb2: {
+-         _2 = const true;                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
 -         goto -> bb3;                     // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
 -     }
 - 
 -     bb3: {
-+         StorageLive(_3);                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-+         _3 = move _2;                    // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
-+         StorageDead(_3);                 // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+-         switchInt(move _2) -> [false: bb5, otherwise: bb4]; // scope 0 at $SRC_DIR/core/src/macros/mod.rs:LL:COL
+-     }
+- 
+-     bb4: {
+          Deinit(_0);                      // scope 0 at $DIR/matches_reduce_branches.rs:+2:9: +2:11
+-         goto -> bb6;                     // scope 0 at $DIR/matches_reduce_branches.rs:+1:5: +3:6
++         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+1:5: +3:6
+      }
+  
+-     bb5: {
++     bb2: {
+          _0 = const ();                   // scope 0 at $DIR/matches_reduce_branches.rs:+3:6: +3:6
+-         goto -> bb6;                     // scope 0 at $DIR/matches_reduce_branches.rs:+1:5: +3:6
++         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+1:5: +3:6
+      }
+  
+-     bb6: {
++     bb3: {
+          StorageDead(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+3:5: +3:6
           return;                          // scope 0 at $DIR/matches_reduce_branches.rs:+4:2: +4:2
       }
   }
diff --git a/src/test/mir-opt/matches_reduce_branches.foo.PreCodegen.before.32bit.mir b/src/test/mir-opt/matches_reduce_branches.foo.PreCodegen.before.32bit.mir
deleted file mode 100644 (file)
index a36ec8d..0000000
+++ /dev/null
@@ -1,10 +0,0 @@
-// MIR for `foo` before PreCodegen
-
-fn foo(_1: Option<()>) -> () {
-    debug bar => _1;                     // in scope 0 at $DIR/matches_reduce_branches.rs:+0:8: +0:11
-    let mut _0: ();                      // return place in scope 0 at $DIR/matches_reduce_branches.rs:+0:25: +0:25
-
-    bb0: {
-        return;                          // scope 0 at $DIR/matches_reduce_branches.rs:+4:2: +4:2
-    }
-}
diff --git a/src/test/mir-opt/matches_reduce_branches.foo.PreCodegen.before.64bit.mir b/src/test/mir-opt/matches_reduce_branches.foo.PreCodegen.before.64bit.mir
deleted file mode 100644 (file)
index a36ec8d..0000000
+++ /dev/null
@@ -1,10 +0,0 @@
-// MIR for `foo` before PreCodegen
-
-fn foo(_1: Option<()>) -> () {
-    debug bar => _1;                     // in scope 0 at $DIR/matches_reduce_branches.rs:+0:8: +0:11
-    let mut _0: ();                      // return place in scope 0 at $DIR/matches_reduce_branches.rs:+0:25: +0:25
-
-    bb0: {
-        return;                          // scope 0 at $DIR/matches_reduce_branches.rs:+4:2: +4:2
-    }
-}
index 672c6b34e94b612b6c2c5d9f1d933aa56855df17..b8c7722cd3713c905b31331b98b0cc2623594660 100644 (file)
   fn match_nested_if() -> bool {
       let mut _0: bool;                    // return place in scope 0 at $DIR/matches_reduce_branches.rs:+0:25: +0:29
       let _1: bool;                        // in scope 0 at $DIR/matches_reduce_branches.rs:+1:9: +1:12
-      let mut _2: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
-+     let mut _3: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
+      let mut _2: ();                      // in scope 0 at $DIR/matches_reduce_branches.rs:+1:21: +1:23
+      let mut _3: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+      let mut _4: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
+      let mut _5: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
+      let mut _6: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
++     let mut _7: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
++     let mut _8: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
++     let mut _9: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
++     let mut _10: bool;                   // in scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
       scope 1 {
           debug val => _1;                 // in scope 1 at $DIR/matches_reduce_branches.rs:+1:9: +1:12
       }
   
       bb0: {
           StorageLive(_1);                 // scope 0 at $DIR/matches_reduce_branches.rs:+1:9: +1:12
-          StorageLive(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
-          _2 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
--         switchInt(move _2) -> [false: bb2, otherwise: bb1]; // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
+          StorageLive(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+1:21: +1:23
+          Deinit(_2);                      // scope 0 at $DIR/matches_reduce_branches.rs:+1:21: +1:23
+          StorageLive(_3);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+          StorageLive(_4);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
+          StorageLive(_5);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
+          StorageLive(_6);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
+          _6 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
+-         switchInt(move _6) -> [false: bb2, otherwise: bb1]; // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
 -     }
 - 
 -     bb1: {
-+         StorageLive(_3);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
-+         _3 = move _2;                    // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
-          StorageDead(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:51: +2:52
--         _1 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+8:13: +8:17
--         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+8:13: +8:17
+-         _5 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:31: +2:35
+-         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
 -     }
 - 
 -     bb2: {
--         StorageDead(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:51: +2:52
--         _1 = const false;                // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
--         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
+-         _5 = const false;                // scope 0 at $DIR/matches_reduce_branches.rs:+2:45: +2:50
+-         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
 -     }
 - 
 -     bb3: {
-+         _1 = Ne(_3, const false);        // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
-+         StorageDead(_3);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
++         StorageLive(_7);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
++         _7 = move _6;                    // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
++         _5 = Ne(_7, const false);        // scope 0 at $DIR/matches_reduce_branches.rs:+2:45: +2:50
++         StorageDead(_7);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
+          StorageDead(_6);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:51: +2:52
+-         switchInt(move _5) -> [false: bb5, otherwise: bb4]; // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
+-     }
+- 
+-     bb4: {
+-         _4 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:55: +2:59
+-         goto -> bb6;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
+-     }
+- 
+-     bb5: {
+-         _4 = const false;                // scope 0 at $DIR/matches_reduce_branches.rs:+2:69: +2:74
+-         goto -> bb6;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
+-     }
+- 
+-     bb6: {
++         StorageLive(_8);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
++         _8 = move _5;                    // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
++         _4 = Ne(_8, const false);        // scope 0 at $DIR/matches_reduce_branches.rs:+2:69: +2:74
++         StorageDead(_8);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
+          StorageDead(_5);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:75: +2:76
+-         switchInt(move _4) -> [false: bb8, otherwise: bb7]; // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
+-     }
+- 
+-     bb7: {
+-         _3 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+3:13: +3:17
+-         goto -> bb9;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+-     }
+- 
+-     bb8: {
+-         _3 = const false;                // scope 0 at $DIR/matches_reduce_branches.rs:+5:13: +5:18
+-         goto -> bb9;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+-     }
+- 
+-     bb9: {
+-         switchInt(move _3) -> [false: bb11, otherwise: bb10]; // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+-     }
+- 
+-     bb10: {
++         StorageLive(_9);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
++         _9 = move _4;                    // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
++         _3 = Ne(_9, const false);        // scope 0 at $DIR/matches_reduce_branches.rs:+5:13: +5:18
++         StorageDead(_9);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
++         StorageLive(_10);                // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
++         _10 = move _3;                   // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+          StorageDead(_4);                 // scope 0 at $DIR/matches_reduce_branches.rs:+6:9: +6:10
+          StorageDead(_3);                 // scope 0 at $DIR/matches_reduce_branches.rs:+6:9: +6:10
+-         _1 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+8:13: +8:17
+-         goto -> bb12;                    // scope 0 at $DIR/matches_reduce_branches.rs:+8:13: +8:17
+-     }
+- 
+-     bb11: {
+-         StorageDead(_4);                 // scope 0 at $DIR/matches_reduce_branches.rs:+6:9: +6:10
+-         StorageDead(_3);                 // scope 0 at $DIR/matches_reduce_branches.rs:+6:9: +6:10
+-         _1 = const false;                // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
+-         goto -> bb12;                    // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
+-     }
+- 
+-     bb12: {
++         _1 = Ne(_10, const false);       // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
++         StorageDead(_10);                // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+          StorageDead(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+11:6: +11:7
           _0 = _1;                         // scope 1 at $DIR/matches_reduce_branches.rs:+12:5: +12:8
           StorageDead(_1);                 // scope 0 at $DIR/matches_reduce_branches.rs:+13:1: +13:2
           return;                          // scope 0 at $DIR/matches_reduce_branches.rs:+13:2: +13:2
index 672c6b34e94b612b6c2c5d9f1d933aa56855df17..b8c7722cd3713c905b31331b98b0cc2623594660 100644 (file)
   fn match_nested_if() -> bool {
       let mut _0: bool;                    // return place in scope 0 at $DIR/matches_reduce_branches.rs:+0:25: +0:29
       let _1: bool;                        // in scope 0 at $DIR/matches_reduce_branches.rs:+1:9: +1:12
-      let mut _2: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
-+     let mut _3: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
+      let mut _2: ();                      // in scope 0 at $DIR/matches_reduce_branches.rs:+1:21: +1:23
+      let mut _3: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+      let mut _4: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
+      let mut _5: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
+      let mut _6: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
++     let mut _7: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
++     let mut _8: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
++     let mut _9: bool;                    // in scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
++     let mut _10: bool;                   // in scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
       scope 1 {
           debug val => _1;                 // in scope 1 at $DIR/matches_reduce_branches.rs:+1:9: +1:12
       }
   
       bb0: {
           StorageLive(_1);                 // scope 0 at $DIR/matches_reduce_branches.rs:+1:9: +1:12
-          StorageLive(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
-          _2 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
--         switchInt(move _2) -> [false: bb2, otherwise: bb1]; // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
+          StorageLive(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+1:21: +1:23
+          Deinit(_2);                      // scope 0 at $DIR/matches_reduce_branches.rs:+1:21: +1:23
+          StorageLive(_3);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+          StorageLive(_4);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
+          StorageLive(_5);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
+          StorageLive(_6);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
+          _6 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
+-         switchInt(move _6) -> [false: bb2, otherwise: bb1]; // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
 -     }
 - 
 -     bb1: {
-+         StorageLive(_3);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
-+         _3 = move _2;                    // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
-          StorageDead(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:51: +2:52
--         _1 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+8:13: +8:17
--         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+8:13: +8:17
+-         _5 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:31: +2:35
+-         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
 -     }
 - 
 -     bb2: {
--         StorageDead(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:51: +2:52
--         _1 = const false;                // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
--         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
+-         _5 = const false;                // scope 0 at $DIR/matches_reduce_branches.rs:+2:45: +2:50
+-         goto -> bb3;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
 -     }
 - 
 -     bb3: {
-+         _1 = Ne(_3, const false);        // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
-+         StorageDead(_3);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
++         StorageLive(_7);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
++         _7 = move _6;                    // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
++         _5 = Ne(_7, const false);        // scope 0 at $DIR/matches_reduce_branches.rs:+2:45: +2:50
++         StorageDead(_7);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:24: +2:28
+          StorageDead(_6);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:51: +2:52
+-         switchInt(move _5) -> [false: bb5, otherwise: bb4]; // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
+-     }
+- 
+-     bb4: {
+-         _4 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:55: +2:59
+-         goto -> bb6;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
+-     }
+- 
+-     bb5: {
+-         _4 = const false;                // scope 0 at $DIR/matches_reduce_branches.rs:+2:69: +2:74
+-         goto -> bb6;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
+-     }
+- 
+-     bb6: {
++         StorageLive(_8);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
++         _8 = move _5;                    // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
++         _4 = Ne(_8, const false);        // scope 0 at $DIR/matches_reduce_branches.rs:+2:69: +2:74
++         StorageDead(_8);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:21: +2:52
+          StorageDead(_5);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:75: +2:76
+-         switchInt(move _4) -> [false: bb8, otherwise: bb7]; // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
+-     }
+- 
+-     bb7: {
+-         _3 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+3:13: +3:17
+-         goto -> bb9;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+-     }
+- 
+-     bb8: {
+-         _3 = const false;                // scope 0 at $DIR/matches_reduce_branches.rs:+5:13: +5:18
+-         goto -> bb9;                     // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+-     }
+- 
+-     bb9: {
+-         switchInt(move _3) -> [false: bb11, otherwise: bb10]; // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+-     }
+- 
+-     bb10: {
++         StorageLive(_9);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
++         _9 = move _4;                    // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
++         _3 = Ne(_9, const false);        // scope 0 at $DIR/matches_reduce_branches.rs:+5:13: +5:18
++         StorageDead(_9);                 // scope 0 at $DIR/matches_reduce_branches.rs:+2:18: +2:76
++         StorageLive(_10);                // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
++         _10 = move _3;                   // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+          StorageDead(_4);                 // scope 0 at $DIR/matches_reduce_branches.rs:+6:9: +6:10
+          StorageDead(_3);                 // scope 0 at $DIR/matches_reduce_branches.rs:+6:9: +6:10
+-         _1 = const true;                 // scope 0 at $DIR/matches_reduce_branches.rs:+8:13: +8:17
+-         goto -> bb12;                    // scope 0 at $DIR/matches_reduce_branches.rs:+8:13: +8:17
+-     }
+- 
+-     bb11: {
+-         StorageDead(_4);                 // scope 0 at $DIR/matches_reduce_branches.rs:+6:9: +6:10
+-         StorageDead(_3);                 // scope 0 at $DIR/matches_reduce_branches.rs:+6:9: +6:10
+-         _1 = const false;                // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
+-         goto -> bb12;                    // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
+-     }
+- 
+-     bb12: {
++         _1 = Ne(_10, const false);       // scope 0 at $DIR/matches_reduce_branches.rs:+10:14: +10:19
++         StorageDead(_10);                // scope 0 at $DIR/matches_reduce_branches.rs:+2:15: +6:10
+          StorageDead(_2);                 // scope 0 at $DIR/matches_reduce_branches.rs:+11:6: +11:7
           _0 = _1;                         // scope 1 at $DIR/matches_reduce_branches.rs:+12:5: +12:8
           StorageDead(_1);                 // scope 0 at $DIR/matches_reduce_branches.rs:+13:1: +13:2
           return;                          // scope 0 at $DIR/matches_reduce_branches.rs:+13:2: +13:2
index 51be3884d48dd27b7a8f86d586a10bba0de5209b..c122b4c69d15a1a8f17411371eec649a526e8e05 100644 (file)
@@ -1,6 +1,7 @@
+// unit-test: MatchBranchSimplification
+
 // EMIT_MIR_FOR_EACH_BIT_WIDTH
 // EMIT_MIR matches_reduce_branches.foo.MatchBranchSimplification.diff
-// EMIT_MIR matches_reduce_branches.foo.PreCodegen.before.mir
 // EMIT_MIR matches_reduce_branches.bar.MatchBranchSimplification.diff
 // EMIT_MIR matches_reduce_branches.match_nested_if.MatchBranchSimplification.diff
 
index 78373be48b6854d5efdbb6cf5ef0c85881eb677d..2c748b02a8b76711fc937d7447016410a440644d 100644 (file)
@@ -1,3 +1,5 @@
+// unit-test: MatchBranchSimplification
+
 // EMIT_MIR_FOR_EACH_BIT_WIDTH
 // EMIT_MIR matches_u8.exhaustive_match.MatchBranchSimplification.diff
 // EMIT_MIR matches_u8.exhaustive_match_i8.MatchBranchSimplification.diff
index b8c554d3ea6b02818cb2b26c179b21531e089f07..f25b3ce724be2db89b3f95fff98746d059aaaa80 100644 (file)
@@ -15,7 +15,7 @@
       scope 1 {
           debug residual => _6;            // in scope 1 at $DIR/separate_const_switch.rs:+1:9: +1:10
           scope 2 {
-              scope 8 (inlined #[track_caller] <Result<i32, i32> as FromResidual<Result<Infallible, i32>>>::from_residual) { // at $DIR/separate_const_switch.rs:29:8: 29:10
+              scope 8 (inlined #[track_caller] <Result<i32, i32> as FromResidual<Result<Infallible, i32>>>::from_residual) { // at $DIR/separate_const_switch.rs:25:8: 25:10
                   debug residual => _8;    // in scope 8 at $SRC_DIR/core/src/result.rs:LL:COL
                   let _16: i32;            // in scope 8 at $SRC_DIR/core/src/result.rs:LL:COL
                   let mut _17: i32;        // in scope 8 at $SRC_DIR/core/src/result.rs:LL:COL
@@ -34,7 +34,7 @@
           scope 4 {
           }
       }
-      scope 5 (inlined <Result<i32, i32> as Try>::branch) { // at $DIR/separate_const_switch.rs:29:8: 29:10
+      scope 5 (inlined <Result<i32, i32> as Try>::branch) { // at $DIR/separate_const_switch.rs:25:8: 25:10
           debug self => _4;                // in scope 5 at $SRC_DIR/core/src/result.rs:LL:COL
           let mut _10: isize;              // in scope 5 at $SRC_DIR/core/src/result.rs:LL:COL
           let _11: i32;                    // in scope 5 at $SRC_DIR/core/src/result.rs:LL:COL
index 5d82acf4d60905259414f168367a26ac7b818044..c809e5629cc152b4c02cd0b92efb6d138bc5c127 100644 (file)
@@ -4,8 +4,6 @@
 use std::ops::ControlFlow;
 
 // EMIT_MIR separate_const_switch.too_complex.SeparateConstSwitch.diff
-// EMIT_MIR separate_const_switch.too_complex.ConstProp.diff
-// EMIT_MIR separate_const_switch.too_complex.PreCodegen.after.mir
 fn too_complex(x: Result<i32, usize>) -> Option<i32> {
     // The pass should break the outer match into
     // two blocks that only have one parent each.
@@ -23,8 +21,6 @@ fn too_complex(x: Result<i32, usize>) -> Option<i32> {
 }
 
 // EMIT_MIR separate_const_switch.identity.SeparateConstSwitch.diff
-// EMIT_MIR separate_const_switch.identity.ConstProp.diff
-// EMIT_MIR separate_const_switch.identity.PreCodegen.after.mir
 fn identity(x: Result<i32, i32>) -> Result<i32, i32> {
     Ok(x?)
 }
index bedc86bbacb8c67fbe2d3b965e0e20a7fcad2ed5..cf6ff57aa96deef66017ce5bbde5f94fe420f23e 100644 (file)
@@ -4,6 +4,9 @@
 // compile-flags: -Zmir-opt-level=3
 // EMIT_MIR_FOR_EACH_BIT_WIDTH
 
+// This pass is broken since deaggregation changed
+// ignore-test
+
 enum Src {
     Foo(u8),
     Bar,
index f7dcaa13449eac88c17898376922e5975859a142..c247872e2af46fb4bad904d0185a647a5559ea57 100644 (file)
@@ -6,6 +6,9 @@
 // EMIT_MIR simplify_arm.id_try.SimplifyArmIdentity.diff
 // EMIT_MIR simplify_arm.id_try.SimplifyBranchSame.diff
 
+// This pass is broken since deaggregation changed
+// ignore-test
+
 fn id(o: Option<u8>) -> Option<u8> {
     match o {
         Some(v) => Some(v),
index 84f57deccf7e0fa810dbe1039d5e2da91b1b9cc7..62a15df04b14429940d05a89f1711268caa43dc2 100644 (file)
@@ -1,4 +1,4 @@
-// compile-flags: -Zunsound-mir-opts
+// unit-test: SimplifyLocals
 
 fn map(x: Option<Box<()>>) -> Option<Box<()>> {
     match x {
diff --git a/src/test/mir-opt/simplify_arm.id.SimplifyArmIdentity.diff b/src/test/mir-opt/simplify_arm.id.SimplifyArmIdentity.diff
deleted file mode 100644 (file)
index 9c3ad4b..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-- // MIR for `id` before SimplifyArmIdentity
-+ // MIR for `id` after SimplifyArmIdentity
-  
-  fn id(_1: Option<u8>) -> Option<u8> {
-      debug o => _1;                       // in scope 0 at $DIR/simplify-arm.rs:+0:7: +0:8
-      let mut _0: std::option::Option<u8>; // return place in scope 0 at $DIR/simplify-arm.rs:+0:25: +0:35
-      let mut _2: isize;                   // in scope 0 at $DIR/simplify-arm.rs:+2:9: +2:16
-      let _3: u8;                          // in scope 0 at $DIR/simplify-arm.rs:+2:14: +2:15
-      let mut _4: u8;                      // in scope 0 at $DIR/simplify-arm.rs:+2:25: +2:26
-      scope 1 {
-          debug v => _3;                   // in scope 1 at $DIR/simplify-arm.rs:+2:14: +2:15
-      }
-  
-      bb0: {
-          _2 = discriminant(_1);           // scope 0 at $DIR/simplify-arm.rs:+1:11: +1:12
-          switchInt(move _2) -> [0_isize: bb1, 1_isize: bb3, otherwise: bb2]; // scope 0 at $DIR/simplify-arm.rs:+1:5: +1:12
-      }
-  
-      bb1: {
-          Deinit(_0);                      // scope 0 at $DIR/simplify-arm.rs:+3:17: +3:21
-          discriminant(_0) = 0;            // scope 0 at $DIR/simplify-arm.rs:+3:17: +3:21
-          goto -> bb4;                     // scope 0 at $DIR/simplify-arm.rs:+3:17: +3:21
-      }
-  
-      bb2: {
-          unreachable;                     // scope 0 at $DIR/simplify-arm.rs:+1:11: +1:12
-      }
-  
-      bb3: {
-          StorageLive(_3);                 // scope 0 at $DIR/simplify-arm.rs:+2:14: +2:15
-          _3 = ((_1 as Some).0: u8);       // scope 0 at $DIR/simplify-arm.rs:+2:14: +2:15
-          StorageLive(_4);                 // scope 1 at $DIR/simplify-arm.rs:+2:25: +2:26
-          _4 = _3;                         // scope 1 at $DIR/simplify-arm.rs:+2:25: +2:26
-          Deinit(_0);                      // scope 1 at $DIR/simplify-arm.rs:+2:20: +2:27
-          ((_0 as Some).0: u8) = move _4;  // scope 1 at $DIR/simplify-arm.rs:+2:20: +2:27
-          discriminant(_0) = 1;            // scope 1 at $DIR/simplify-arm.rs:+2:20: +2:27
-          StorageDead(_4);                 // scope 1 at $DIR/simplify-arm.rs:+2:26: +2:27
-          StorageDead(_3);                 // scope 0 at $DIR/simplify-arm.rs:+2:26: +2:27
-          goto -> bb4;                     // scope 0 at $DIR/simplify-arm.rs:+2:26: +2:27
-      }
-  
-      bb4: {
-          return;                          // scope 0 at $DIR/simplify-arm.rs:+5:2: +5:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/simplify_arm.id.SimplifyBranchSame.diff b/src/test/mir-opt/simplify_arm.id.SimplifyBranchSame.diff
deleted file mode 100644 (file)
index 7b3a699..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-- // MIR for `id` before SimplifyBranchSame
-+ // MIR for `id` after SimplifyBranchSame
-  
-  fn id(_1: Option<u8>) -> Option<u8> {
-      debug o => _1;                       // in scope 0 at $DIR/simplify-arm.rs:+0:7: +0:8
-      let mut _0: std::option::Option<u8>; // return place in scope 0 at $DIR/simplify-arm.rs:+0:25: +0:35
-      let mut _2: isize;                   // in scope 0 at $DIR/simplify-arm.rs:+2:9: +2:16
-      let _3: u8;                          // in scope 0 at $DIR/simplify-arm.rs:+2:14: +2:15
-      let mut _4: u8;                      // in scope 0 at $DIR/simplify-arm.rs:+2:25: +2:26
-      scope 1 {
-          debug v => _3;                   // in scope 1 at $DIR/simplify-arm.rs:+2:14: +2:15
-      }
-  
-      bb0: {
-          _2 = discriminant(_1);           // scope 0 at $DIR/simplify-arm.rs:+1:11: +1:12
-          switchInt(move _2) -> [0_isize: bb1, 1_isize: bb3, otherwise: bb2]; // scope 0 at $DIR/simplify-arm.rs:+1:5: +1:12
-      }
-  
-      bb1: {
-          Deinit(_0);                      // scope 0 at $DIR/simplify-arm.rs:+3:17: +3:21
-          discriminant(_0) = 0;            // scope 0 at $DIR/simplify-arm.rs:+3:17: +3:21
-          goto -> bb4;                     // scope 0 at $DIR/simplify-arm.rs:+3:17: +3:21
-      }
-  
-      bb2: {
-          unreachable;                     // scope 0 at $DIR/simplify-arm.rs:+1:11: +1:12
-      }
-  
-      bb3: {
-          StorageLive(_3);                 // scope 0 at $DIR/simplify-arm.rs:+2:14: +2:15
-          _3 = ((_1 as Some).0: u8);       // scope 0 at $DIR/simplify-arm.rs:+2:14: +2:15
-          StorageLive(_4);                 // scope 1 at $DIR/simplify-arm.rs:+2:25: +2:26
-          _4 = _3;                         // scope 1 at $DIR/simplify-arm.rs:+2:25: +2:26
-          Deinit(_0);                      // scope 1 at $DIR/simplify-arm.rs:+2:20: +2:27
-          ((_0 as Some).0: u8) = move _4;  // scope 1 at $DIR/simplify-arm.rs:+2:20: +2:27
-          discriminant(_0) = 1;            // scope 1 at $DIR/simplify-arm.rs:+2:20: +2:27
-          StorageDead(_4);                 // scope 1 at $DIR/simplify-arm.rs:+2:26: +2:27
-          StorageDead(_3);                 // scope 0 at $DIR/simplify-arm.rs:+2:26: +2:27
-          goto -> bb4;                     // scope 0 at $DIR/simplify-arm.rs:+2:26: +2:27
-      }
-  
-      bb4: {
-          return;                          // scope 0 at $DIR/simplify-arm.rs:+5:2: +5:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/simplify_arm.id_result.SimplifyArmIdentity.diff b/src/test/mir-opt/simplify_arm.id_result.SimplifyArmIdentity.diff
deleted file mode 100644 (file)
index 31d8453..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-- // MIR for `id_result` before SimplifyArmIdentity
-+ // MIR for `id_result` after SimplifyArmIdentity
-  
-  fn id_result(_1: Result<u8, i32>) -> Result<u8, i32> {
-      debug r => _1;                       // in scope 0 at $DIR/simplify-arm.rs:+0:14: +0:15
-      let mut _0: std::result::Result<u8, i32>; // return place in scope 0 at $DIR/simplify-arm.rs:+0:37: +0:52
-      let mut _2: isize;                   // in scope 0 at $DIR/simplify-arm.rs:+2:9: +2:14
-      let _3: u8;                          // in scope 0 at $DIR/simplify-arm.rs:+2:12: +2:13
-      let mut _4: u8;                      // in scope 0 at $DIR/simplify-arm.rs:+2:21: +2:22
-      let _5: i32;                         // in scope 0 at $DIR/simplify-arm.rs:+3:13: +3:14
-      let mut _6: i32;                     // in scope 0 at $DIR/simplify-arm.rs:+3:23: +3:24
-      scope 1 {
-          debug x => _3;                   // in scope 1 at $DIR/simplify-arm.rs:+2:12: +2:13
-      }
-      scope 2 {
-          debug y => _5;                   // in scope 2 at $DIR/simplify-arm.rs:+3:13: +3:14
-      }
-  
-      bb0: {
-          _2 = discriminant(_1);           // scope 0 at $DIR/simplify-arm.rs:+1:11: +1:12
-          switchInt(move _2) -> [0_isize: bb3, 1_isize: bb1, otherwise: bb2]; // scope 0 at $DIR/simplify-arm.rs:+1:5: +1:12
-      }
-  
-      bb1: {
-          StorageLive(_5);                 // scope 0 at $DIR/simplify-arm.rs:+3:13: +3:14
-          _5 = ((_1 as Err).0: i32);       // scope 0 at $DIR/simplify-arm.rs:+3:13: +3:14
-          StorageLive(_6);                 // scope 2 at $DIR/simplify-arm.rs:+3:23: +3:24
-          _6 = _5;                         // scope 2 at $DIR/simplify-arm.rs:+3:23: +3:24
-          Deinit(_0);                      // scope 2 at $DIR/simplify-arm.rs:+3:19: +3:25
-          ((_0 as Err).0: i32) = move _6;  // scope 2 at $DIR/simplify-arm.rs:+3:19: +3:25
-          discriminant(_0) = 1;            // scope 2 at $DIR/simplify-arm.rs:+3:19: +3:25
-          StorageDead(_6);                 // scope 2 at $DIR/simplify-arm.rs:+3:24: +3:25
-          StorageDead(_5);                 // scope 0 at $DIR/simplify-arm.rs:+3:24: +3:25
-          goto -> bb4;                     // scope 0 at $DIR/simplify-arm.rs:+3:24: +3:25
-      }
-  
-      bb2: {
-          unreachable;                     // scope 0 at $DIR/simplify-arm.rs:+1:11: +1:12
-      }
-  
-      bb3: {
-          StorageLive(_3);                 // scope 0 at $DIR/simplify-arm.rs:+2:12: +2:13
-          _3 = ((_1 as Ok).0: u8);         // scope 0 at $DIR/simplify-arm.rs:+2:12: +2:13
-          StorageLive(_4);                 // scope 1 at $DIR/simplify-arm.rs:+2:21: +2:22
-          _4 = _3;                         // scope 1 at $DIR/simplify-arm.rs:+2:21: +2:22
-          Deinit(_0);                      // scope 1 at $DIR/simplify-arm.rs:+2:18: +2:23
-          ((_0 as Ok).0: u8) = move _4;    // scope 1 at $DIR/simplify-arm.rs:+2:18: +2:23
-          discriminant(_0) = 0;            // scope 1 at $DIR/simplify-arm.rs:+2:18: +2:23
-          StorageDead(_4);                 // scope 1 at $DIR/simplify-arm.rs:+2:22: +2:23
-          StorageDead(_3);                 // scope 0 at $DIR/simplify-arm.rs:+2:22: +2:23
-          goto -> bb4;                     // scope 0 at $DIR/simplify-arm.rs:+2:22: +2:23
-      }
-  
-      bb4: {
-          return;                          // scope 0 at $DIR/simplify-arm.rs:+5:2: +5:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/simplify_arm.id_result.SimplifyBranchSame.diff b/src/test/mir-opt/simplify_arm.id_result.SimplifyBranchSame.diff
deleted file mode 100644 (file)
index 3692ebf..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-- // MIR for `id_result` before SimplifyBranchSame
-+ // MIR for `id_result` after SimplifyBranchSame
-  
-  fn id_result(_1: Result<u8, i32>) -> Result<u8, i32> {
-      debug r => _1;                       // in scope 0 at $DIR/simplify-arm.rs:+0:14: +0:15
-      let mut _0: std::result::Result<u8, i32>; // return place in scope 0 at $DIR/simplify-arm.rs:+0:37: +0:52
-      let mut _2: isize;                   // in scope 0 at $DIR/simplify-arm.rs:+2:9: +2:14
-      let _3: u8;                          // in scope 0 at $DIR/simplify-arm.rs:+2:12: +2:13
-      let mut _4: u8;                      // in scope 0 at $DIR/simplify-arm.rs:+2:21: +2:22
-      let _5: i32;                         // in scope 0 at $DIR/simplify-arm.rs:+3:13: +3:14
-      let mut _6: i32;                     // in scope 0 at $DIR/simplify-arm.rs:+3:23: +3:24
-      scope 1 {
-          debug x => _3;                   // in scope 1 at $DIR/simplify-arm.rs:+2:12: +2:13
-      }
-      scope 2 {
-          debug y => _5;                   // in scope 2 at $DIR/simplify-arm.rs:+3:13: +3:14
-      }
-  
-      bb0: {
-          _2 = discriminant(_1);           // scope 0 at $DIR/simplify-arm.rs:+1:11: +1:12
-          switchInt(move _2) -> [0_isize: bb3, 1_isize: bb1, otherwise: bb2]; // scope 0 at $DIR/simplify-arm.rs:+1:5: +1:12
-      }
-  
-      bb1: {
-          StorageLive(_5);                 // scope 0 at $DIR/simplify-arm.rs:+3:13: +3:14
-          _5 = ((_1 as Err).0: i32);       // scope 0 at $DIR/simplify-arm.rs:+3:13: +3:14
-          StorageLive(_6);                 // scope 2 at $DIR/simplify-arm.rs:+3:23: +3:24
-          _6 = _5;                         // scope 2 at $DIR/simplify-arm.rs:+3:23: +3:24
-          Deinit(_0);                      // scope 2 at $DIR/simplify-arm.rs:+3:19: +3:25
-          ((_0 as Err).0: i32) = move _6;  // scope 2 at $DIR/simplify-arm.rs:+3:19: +3:25
-          discriminant(_0) = 1;            // scope 2 at $DIR/simplify-arm.rs:+3:19: +3:25
-          StorageDead(_6);                 // scope 2 at $DIR/simplify-arm.rs:+3:24: +3:25
-          StorageDead(_5);                 // scope 0 at $DIR/simplify-arm.rs:+3:24: +3:25
-          goto -> bb4;                     // scope 0 at $DIR/simplify-arm.rs:+3:24: +3:25
-      }
-  
-      bb2: {
-          unreachable;                     // scope 0 at $DIR/simplify-arm.rs:+1:11: +1:12
-      }
-  
-      bb3: {
-          StorageLive(_3);                 // scope 0 at $DIR/simplify-arm.rs:+2:12: +2:13
-          _3 = ((_1 as Ok).0: u8);         // scope 0 at $DIR/simplify-arm.rs:+2:12: +2:13
-          StorageLive(_4);                 // scope 1 at $DIR/simplify-arm.rs:+2:21: +2:22
-          _4 = _3;                         // scope 1 at $DIR/simplify-arm.rs:+2:21: +2:22
-          Deinit(_0);                      // scope 1 at $DIR/simplify-arm.rs:+2:18: +2:23
-          ((_0 as Ok).0: u8) = move _4;    // scope 1 at $DIR/simplify-arm.rs:+2:18: +2:23
-          discriminant(_0) = 0;            // scope 1 at $DIR/simplify-arm.rs:+2:18: +2:23
-          StorageDead(_4);                 // scope 1 at $DIR/simplify-arm.rs:+2:22: +2:23
-          StorageDead(_3);                 // scope 0 at $DIR/simplify-arm.rs:+2:22: +2:23
-          goto -> bb4;                     // scope 0 at $DIR/simplify-arm.rs:+2:22: +2:23
-      }
-  
-      bb4: {
-          return;                          // scope 0 at $DIR/simplify-arm.rs:+5:2: +5:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/simplify_arm_identity.main.SimplifyArmIdentity.32bit.diff b/src/test/mir-opt/simplify_arm_identity.main.SimplifyArmIdentity.32bit.diff
deleted file mode 100644 (file)
index 118f5dd..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-- // MIR for `main` before SimplifyArmIdentity
-+ // MIR for `main` after SimplifyArmIdentity
-  
-  fn main() -> () {
-      let mut _0: ();                      // return place in scope 0 at $DIR/simplify-arm-identity.rs:+0:11: +0:11
-      let _1: Src;                         // in scope 0 at $DIR/simplify-arm-identity.rs:+1:9: +1:10
-      let mut _2: Dst;                     // in scope 0 at $DIR/simplify-arm-identity.rs:+2:18: +5:6
-      let mut _3: isize;                   // in scope 0 at $DIR/simplify-arm-identity.rs:+3:9: +3:20
-      let mut _5: u8;                      // in scope 0 at $DIR/simplify-arm-identity.rs:+3:33: +3:34
-      scope 1 {
-          debug e => _1;                   // in scope 1 at $DIR/simplify-arm-identity.rs:+1:9: +1:10
-          let _4: u8;                      // in scope 1 at $DIR/simplify-arm-identity.rs:+3:18: +3:19
-          scope 2 {
-          }
-          scope 3 {
-              debug x => _4;               // in scope 3 at $DIR/simplify-arm-identity.rs:+3:18: +3:19
-          }
-      }
-  
-      bb0: {
-          StorageLive(_1);                 // scope 0 at $DIR/simplify-arm-identity.rs:+1:9: +1:10
-          Deinit(_1);                      // scope 0 at $DIR/simplify-arm-identity.rs:+1:18: +1:29
-          ((_1 as Foo).0: u8) = const 0_u8; // scope 0 at $DIR/simplify-arm-identity.rs:+1:18: +1:29
-          discriminant(_1) = 0;            // scope 0 at $DIR/simplify-arm-identity.rs:+1:18: +1:29
-          StorageLive(_2);                 // scope 1 at $DIR/simplify-arm-identity.rs:+2:18: +5:6
-          _3 = const 0_isize;              // scope 1 at $DIR/simplify-arm-identity.rs:+2:24: +2:25
-          goto -> bb3;                     // scope 1 at $DIR/simplify-arm-identity.rs:+2:18: +2:25
-      }
-  
-      bb1: {
-          Deinit(_2);                      // scope 1 at $DIR/simplify-arm-identity.rs:+4:21: +4:32
-          ((_2 as Foo).0: u8) = const 0_u8; // scope 1 at $DIR/simplify-arm-identity.rs:+4:21: +4:32
-          discriminant(_2) = 0;            // scope 1 at $DIR/simplify-arm-identity.rs:+4:21: +4:32
-          goto -> bb4;                     // scope 1 at $DIR/simplify-arm-identity.rs:+4:21: +4:32
-      }
-  
-      bb2: {
-          unreachable;                     // scope 1 at $DIR/simplify-arm-identity.rs:+2:24: +2:25
-      }
-  
-      bb3: {
-          StorageLive(_4);                 // scope 1 at $DIR/simplify-arm-identity.rs:+3:18: +3:19
-          _4 = ((_1 as Foo).0: u8);        // scope 1 at $DIR/simplify-arm-identity.rs:+3:18: +3:19
-          StorageLive(_5);                 // scope 3 at $DIR/simplify-arm-identity.rs:+3:33: +3:34
-          _5 = _4;                         // scope 3 at $DIR/simplify-arm-identity.rs:+3:33: +3:34
-          Deinit(_2);                      // scope 3 at $DIR/simplify-arm-identity.rs:+3:24: +3:35
-          ((_2 as Foo).0: u8) = move _5;   // scope 3 at $DIR/simplify-arm-identity.rs:+3:24: +3:35
-          discriminant(_2) = 0;            // scope 3 at $DIR/simplify-arm-identity.rs:+3:24: +3:35
-          StorageDead(_5);                 // scope 3 at $DIR/simplify-arm-identity.rs:+3:34: +3:35
-          StorageDead(_4);                 // scope 1 at $DIR/simplify-arm-identity.rs:+3:34: +3:35
-          goto -> bb4;                     // scope 1 at $DIR/simplify-arm-identity.rs:+3:34: +3:35
-      }
-  
-      bb4: {
-          StorageDead(_2);                 // scope 1 at $DIR/simplify-arm-identity.rs:+5:6: +5:7
-          nop;                             // scope 0 at $DIR/simplify-arm-identity.rs:+0:11: +6:2
-          StorageDead(_1);                 // scope 0 at $DIR/simplify-arm-identity.rs:+6:1: +6:2
-          return;                          // scope 0 at $DIR/simplify-arm-identity.rs:+6:2: +6:2
-      }
-  }
-  
diff --git a/src/test/mir-opt/simplify_arm_identity.main.SimplifyArmIdentity.64bit.diff b/src/test/mir-opt/simplify_arm_identity.main.SimplifyArmIdentity.64bit.diff
deleted file mode 100644 (file)
index 118f5dd..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-- // MIR for `main` before SimplifyArmIdentity
-+ // MIR for `main` after SimplifyArmIdentity
-  
-  fn main() -> () {
-      let mut _0: ();                      // return place in scope 0 at $DIR/simplify-arm-identity.rs:+0:11: +0:11
-      let _1: Src;                         // in scope 0 at $DIR/simplify-arm-identity.rs:+1:9: +1:10
-      let mut _2: Dst;                     // in scope 0 at $DIR/simplify-arm-identity.rs:+2:18: +5:6
-      let mut _3: isize;                   // in scope 0 at $DIR/simplify-arm-identity.rs:+3:9: +3:20
-      let mut _5: u8;                      // in scope 0 at $DIR/simplify-arm-identity.rs:+3:33: +3:34
-      scope 1 {
-          debug e => _1;                   // in scope 1 at $DIR/simplify-arm-identity.rs:+1:9: +1:10
-          let _4: u8;                      // in scope 1 at $DIR/simplify-arm-identity.rs:+3:18: +3:19
-          scope 2 {
-          }
-          scope 3 {
-              debug x => _4;               // in scope 3 at $DIR/simplify-arm-identity.rs:+3:18: +3:19
-          }
-      }
-  
-      bb0: {
-          StorageLive(_1);                 // scope 0 at $DIR/simplify-arm-identity.rs:+1:9: +1:10
-          Deinit(_1);                      // scope 0 at $DIR/simplify-arm-identity.rs:+1:18: +1:29
-          ((_1 as Foo).0: u8) = const 0_u8; // scope 0 at $DIR/simplify-arm-identity.rs:+1:18: +1:29
-          discriminant(_1) = 0;            // scope 0 at $DIR/simplify-arm-identity.rs:+1:18: +1:29
-          StorageLive(_2);                 // scope 1 at $DIR/simplify-arm-identity.rs:+2:18: +5:6
-          _3 = const 0_isize;              // scope 1 at $DIR/simplify-arm-identity.rs:+2:24: +2:25
-          goto -> bb3;                     // scope 1 at $DIR/simplify-arm-identity.rs:+2:18: +2:25
-      }
-  
-      bb1: {
-          Deinit(_2);                      // scope 1 at $DIR/simplify-arm-identity.rs:+4:21: +4:32
-          ((_2 as Foo).0: u8) = const 0_u8; // scope 1 at $DIR/simplify-arm-identity.rs:+4:21: +4:32
-          discriminant(_2) = 0;            // scope 1 at $DIR/simplify-arm-identity.rs:+4:21: +4:32
-          goto -> bb4;                     // scope 1 at $DIR/simplify-arm-identity.rs:+4:21: +4:32
-      }
-  
-      bb2: {
-          unreachable;                     // scope 1 at $DIR/simplify-arm-identity.rs:+2:24: +2:25
-      }
-  
-      bb3: {
-          StorageLive(_4);                 // scope 1 at $DIR/simplify-arm-identity.rs:+3:18: +3:19
-          _4 = ((_1 as Foo).0: u8);        // scope 1 at $DIR/simplify-arm-identity.rs:+3:18: +3:19
-          StorageLive(_5);                 // scope 3 at $DIR/simplify-arm-identity.rs:+3:33: +3:34
-          _5 = _4;                         // scope 3 at $DIR/simplify-arm-identity.rs:+3:33: +3:34
-          Deinit(_2);                      // scope 3 at $DIR/simplify-arm-identity.rs:+3:24: +3:35
-          ((_2 as Foo).0: u8) = move _5;   // scope 3 at $DIR/simplify-arm-identity.rs:+3:24: +3:35
-          discriminant(_2) = 0;            // scope 3 at $DIR/simplify-arm-identity.rs:+3:24: +3:35
-          StorageDead(_5);                 // scope 3 at $DIR/simplify-arm-identity.rs:+3:34: +3:35
-          StorageDead(_4);                 // scope 1 at $DIR/simplify-arm-identity.rs:+3:34: +3:35
-          goto -> bb4;                     // scope 1 at $DIR/simplify-arm-identity.rs:+3:34: +3:35
-      }
-  
-      bb4: {
-          StorageDead(_2);                 // scope 1 at $DIR/simplify-arm-identity.rs:+5:6: +5:7
-          nop;                             // scope 0 at $DIR/simplify-arm-identity.rs:+0:11: +6:2
-          StorageDead(_1);                 // scope 0 at $DIR/simplify-arm-identity.rs:+6:1: +6:2
-          return;                          // scope 0 at $DIR/simplify-arm-identity.rs:+6:2: +6:2
-      }
-  }
-  
index d8e0657c6ebc66908583970518b57cdbb9328851..51d26b08b2a1c69217fbf247a24d4bf5f43efa4d 100644 (file)
@@ -5,24 +5,32 @@
       debug x => _1;                       // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+0:8: +0:9
       let mut _0: std::option::Option<std::boxed::Box<()>>; // return place in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+0:31: +0:46
       let mut _2: isize;                   // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+2:9: +2:13
--     let _3: std::boxed::Box<()>;         // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
--     let mut _4: std::boxed::Box<()>;     // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:25: +3:26
+      let _3: std::boxed::Box<()>;         // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
+      let mut _4: std::boxed::Box<()>;     // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:25: +3:26
 -     let mut _5: bool;                    // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+5:1: +5:2
 -     let mut _6: isize;                   // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+5:1: +5:2
 -     let mut _7: isize;                   // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+5:1: +5:2
       scope 1 {
-          debug x => ((_0 as Some).0: std::boxed::Box<()>); // in scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
+          debug x => _3;                   // in scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
       }
   
       bb0: {
+-         _5 = const false;                // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+1:11: +1:12
+-         _5 = const true;                 // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+1:11: +1:12
           _2 = discriminant(_1);           // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+1:11: +1:12
           switchInt(move _2) -> [0_isize: bb3, 1_isize: bb1, otherwise: bb2]; // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+1:5: +1:12
       }
   
       bb1: {
-          ((_0 as Some).0: std::boxed::Box<()>) = move ((_1 as Some).0: std::boxed::Box<()>); // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
+          StorageLive(_3);                 // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
+          _3 = move ((_1 as Some).0: std::boxed::Box<()>); // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
+          StorageLive(_4);                 // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:25: +3:26
+          _4 = move _3;                    // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:25: +3:26
           Deinit(_0);                      // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:20: +3:27
+          ((_0 as Some).0: std::boxed::Box<()>) = move _4; // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:20: +3:27
           discriminant(_0) = 1;            // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:20: +3:27
+          StorageDead(_4);                 // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:26: +3:27
+          StorageDead(_3);                 // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:26: +3:27
           goto -> bb4;                     // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:26: +3:27
       }
   
@@ -37,6 +45,7 @@
       }
   
       bb4: {
+-         _6 = discriminant(_1);           // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+5:1: +5:2
           return;                          // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+5:2: +5:2
       }
   }
index d8e0657c6ebc66908583970518b57cdbb9328851..51d26b08b2a1c69217fbf247a24d4bf5f43efa4d 100644 (file)
@@ -5,24 +5,32 @@
       debug x => _1;                       // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+0:8: +0:9
       let mut _0: std::option::Option<std::boxed::Box<()>>; // return place in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+0:31: +0:46
       let mut _2: isize;                   // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+2:9: +2:13
--     let _3: std::boxed::Box<()>;         // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
--     let mut _4: std::boxed::Box<()>;     // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:25: +3:26
+      let _3: std::boxed::Box<()>;         // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
+      let mut _4: std::boxed::Box<()>;     // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:25: +3:26
 -     let mut _5: bool;                    // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+5:1: +5:2
 -     let mut _6: isize;                   // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+5:1: +5:2
 -     let mut _7: isize;                   // in scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+5:1: +5:2
       scope 1 {
-          debug x => ((_0 as Some).0: std::boxed::Box<()>); // in scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
+          debug x => _3;                   // in scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
       }
   
       bb0: {
+-         _5 = const false;                // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+1:11: +1:12
+-         _5 = const true;                 // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+1:11: +1:12
           _2 = discriminant(_1);           // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+1:11: +1:12
           switchInt(move _2) -> [0_isize: bb3, 1_isize: bb1, otherwise: bb2]; // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+1:5: +1:12
       }
   
       bb1: {
-          ((_0 as Some).0: std::boxed::Box<()>) = move ((_1 as Some).0: std::boxed::Box<()>); // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
+          StorageLive(_3);                 // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
+          _3 = move ((_1 as Some).0: std::boxed::Box<()>); // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:14: +3:15
+          StorageLive(_4);                 // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:25: +3:26
+          _4 = move _3;                    // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:25: +3:26
           Deinit(_0);                      // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:20: +3:27
+          ((_0 as Some).0: std::boxed::Box<()>) = move _4; // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:20: +3:27
           discriminant(_0) = 1;            // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:20: +3:27
+          StorageDead(_4);                 // scope 1 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:26: +3:27
+          StorageDead(_3);                 // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:26: +3:27
           goto -> bb4;                     // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+3:26: +3:27
       }
   
@@ -37,6 +45,7 @@
       }
   
       bb4: {
+-         _6 = discriminant(_1);           // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+5:1: +5:2
           return;                          // scope 0 at $DIR/simplify-locals-removes-unused-discriminant-reads.rs:+5:2: +5:2
       }
   }
diff --git a/src/test/mir-opt/simplify_try.rs b/src/test/mir-opt/simplify_try.rs
deleted file mode 100644 (file)
index 15e351e..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-// compile-flags: -Zunsound-mir-opts
-// EMIT_MIR simplify_try.try_identity.SimplifyArmIdentity.diff
-// EMIT_MIR simplify_try.try_identity.SimplifyBranchSame.after.mir
-// EMIT_MIR simplify_try.try_identity.SimplifyLocals.after.mir
-// EMIT_MIR simplify_try.try_identity.DestinationPropagation.diff
-
-
-fn into_result<T, E>(r: Result<T, E>) -> Result<T, E> {
-    r
-}
-
-fn from_error<T, E>(e: E) -> Result<T, E> {
-    Err(e)
-}
-
-// This was written to the `?` from `try_trait`, but `try_trait_v2` uses a different structure,
-// so the relevant desugar is copied inline in order to keep the test testing the same thing.
-// FIXME(#85133): while this might be useful for `r#try!`, it would be nice to have a MIR
-// optimization that picks up the `?` desugaring, as `SimplifyArmIdentity` does not.
-fn try_identity(x: Result<u32, i32>) -> Result<u32, i32> {
-    let y = match into_result(x) {
-        Err(e) => return from_error(From::from(e)),
-        Ok(v) => v,
-    };
-    Ok(y)
-}
-
-fn main() {
-    let _ = try_identity(Ok(0));
-}
diff --git a/src/test/mir-opt/try_identity_e2e.new.PreCodegen.after.mir b/src/test/mir-opt/try_identity_e2e.new.PreCodegen.after.mir
new file mode 100644 (file)
index 0000000..330929c
--- /dev/null
@@ -0,0 +1,96 @@
+// MIR for `new` after PreCodegen
+
+fn new(_1: Result<T, E>) -> Result<T, E> {
+    debug x => _1;                       // in scope 0 at $DIR/try_identity_e2e.rs:+0:14: +0:15
+    let mut _0: std::result::Result<T, E>; // return place in scope 0 at $DIR/try_identity_e2e.rs:+0:34: +0:46
+    let mut _2: T;                       // in scope 0 at $DIR/try_identity_e2e.rs:+2:9: +10:10
+    let mut _3: std::ops::ControlFlow<E, T>; // in scope 0 at $DIR/try_identity_e2e.rs:+2:15: +7:10
+    let mut _4: isize;                   // in scope 0 at $DIR/try_identity_e2e.rs:+4:17: +4:22
+    let _5: T;                           // in scope 0 at $DIR/try_identity_e2e.rs:+4:20: +4:21
+    let mut _6: T;                       // in scope 0 at $DIR/try_identity_e2e.rs:+4:48: +4:49
+    let _7: E;                           // in scope 0 at $DIR/try_identity_e2e.rs:+5:21: +5:22
+    let mut _8: E;                       // in scope 0 at $DIR/try_identity_e2e.rs:+5:46: +5:47
+    let mut _9: isize;                   // in scope 0 at $DIR/try_identity_e2e.rs:+8:13: +8:37
+    let _10: T;                          // in scope 0 at $DIR/try_identity_e2e.rs:+8:35: +8:36
+    let _11: E;                          // in scope 0 at $DIR/try_identity_e2e.rs:+9:32: +9:33
+    let mut _12: E;                      // in scope 0 at $DIR/try_identity_e2e.rs:+9:49: +9:50
+    scope 1 {
+        debug v => _5;                   // in scope 1 at $DIR/try_identity_e2e.rs:+4:20: +4:21
+    }
+    scope 2 {
+        debug e => _7;                   // in scope 2 at $DIR/try_identity_e2e.rs:+5:21: +5:22
+    }
+    scope 3 {
+        debug v => _10;                  // in scope 3 at $DIR/try_identity_e2e.rs:+8:35: +8:36
+    }
+    scope 4 {
+        debug e => _11;                  // in scope 4 at $DIR/try_identity_e2e.rs:+9:32: +9:33
+    }
+
+    bb0: {
+        StorageLive(_2);                 // scope 0 at $DIR/try_identity_e2e.rs:+2:9: +10:10
+        StorageLive(_3);                 // scope 0 at $DIR/try_identity_e2e.rs:+2:15: +7:10
+        _4 = discriminant(_1);           // scope 0 at $DIR/try_identity_e2e.rs:+3:19: +3:20
+        switchInt(move _4) -> [0_isize: bb2, 1_isize: bb1, otherwise: bb4]; // scope 0 at $DIR/try_identity_e2e.rs:+3:13: +3:20
+    }
+
+    bb1: {
+        StorageLive(_7);                 // scope 0 at $DIR/try_identity_e2e.rs:+5:21: +5:22
+        _7 = move ((_1 as Err).0: E);    // scope 0 at $DIR/try_identity_e2e.rs:+5:21: +5:22
+        StorageLive(_8);                 // scope 2 at $DIR/try_identity_e2e.rs:+5:46: +5:47
+        _8 = move _7;                    // scope 2 at $DIR/try_identity_e2e.rs:+5:46: +5:47
+        Deinit(_3);                      // scope 2 at $DIR/try_identity_e2e.rs:+5:27: +5:48
+        ((_3 as Break).0: E) = move _8;  // scope 2 at $DIR/try_identity_e2e.rs:+5:27: +5:48
+        discriminant(_3) = 1;            // scope 2 at $DIR/try_identity_e2e.rs:+5:27: +5:48
+        StorageDead(_8);                 // scope 2 at $DIR/try_identity_e2e.rs:+5:47: +5:48
+        StorageDead(_7);                 // scope 0 at $DIR/try_identity_e2e.rs:+5:47: +5:48
+        _9 = discriminant(_3);           // scope 0 at $DIR/try_identity_e2e.rs:+2:15: +7:10
+        switchInt(move _9) -> [0_isize: bb5, 1_isize: bb3, otherwise: bb4]; // scope 0 at $DIR/try_identity_e2e.rs:+2:9: +7:10
+    }
+
+    bb2: {
+        StorageLive(_5);                 // scope 0 at $DIR/try_identity_e2e.rs:+4:20: +4:21
+        _5 = move ((_1 as Ok).0: T);     // scope 0 at $DIR/try_identity_e2e.rs:+4:20: +4:21
+        StorageLive(_6);                 // scope 1 at $DIR/try_identity_e2e.rs:+4:48: +4:49
+        _6 = move _5;                    // scope 1 at $DIR/try_identity_e2e.rs:+4:48: +4:49
+        Deinit(_3);                      // scope 1 at $DIR/try_identity_e2e.rs:+4:26: +4:50
+        ((_3 as Continue).0: T) = move _6; // scope 1 at $DIR/try_identity_e2e.rs:+4:26: +4:50
+        discriminant(_3) = 0;            // scope 1 at $DIR/try_identity_e2e.rs:+4:26: +4:50
+        StorageDead(_6);                 // scope 1 at $DIR/try_identity_e2e.rs:+4:49: +4:50
+        StorageDead(_5);                 // scope 0 at $DIR/try_identity_e2e.rs:+4:49: +4:50
+        _9 = discriminant(_3);           // scope 0 at $DIR/try_identity_e2e.rs:+2:15: +7:10
+        switchInt(move _9) -> [0_isize: bb5, 1_isize: bb3, otherwise: bb4]; // scope 0 at $DIR/try_identity_e2e.rs:+2:9: +7:10
+    }
+
+    bb3: {
+        StorageLive(_11);                // scope 0 at $DIR/try_identity_e2e.rs:+9:32: +9:33
+        _11 = move ((_3 as Break).0: E); // scope 0 at $DIR/try_identity_e2e.rs:+9:32: +9:33
+        StorageLive(_12);                // scope 4 at $DIR/try_identity_e2e.rs:+9:49: +9:50
+        _12 = move _11;                  // scope 4 at $DIR/try_identity_e2e.rs:+9:49: +9:50
+        Deinit(_0);                      // scope 4 at $DIR/try_identity_e2e.rs:+9:45: +9:51
+        ((_0 as Err).0: E) = move _12;   // scope 4 at $DIR/try_identity_e2e.rs:+9:45: +9:51
+        discriminant(_0) = 1;            // scope 4 at $DIR/try_identity_e2e.rs:+9:45: +9:51
+        StorageDead(_12);                // scope 4 at $DIR/try_identity_e2e.rs:+9:50: +9:51
+        StorageDead(_11);                // scope 0 at $DIR/try_identity_e2e.rs:+9:50: +9:51
+        StorageDead(_2);                 // scope 0 at $DIR/try_identity_e2e.rs:+11:5: +11:6
+        StorageDead(_3);                 // scope 0 at $DIR/try_identity_e2e.rs:+12:1: +12:2
+        return;                          // scope 0 at $DIR/try_identity_e2e.rs:+12:1: +12:2
+    }
+
+    bb4: {
+        unreachable;                     // scope 0 at $DIR/try_identity_e2e.rs:+2:15: +7:10
+    }
+
+    bb5: {
+        StorageLive(_10);                // scope 0 at $DIR/try_identity_e2e.rs:+8:35: +8:36
+        _10 = move ((_3 as Continue).0: T); // scope 0 at $DIR/try_identity_e2e.rs:+8:35: +8:36
+        _2 = move _10;                   // scope 3 at $DIR/try_identity_e2e.rs:+8:41: +8:42
+        StorageDead(_10);                // scope 0 at $DIR/try_identity_e2e.rs:+8:41: +8:42
+        Deinit(_0);                      // scope 0 at $DIR/try_identity_e2e.rs:+1:5: +11:6
+        ((_0 as Ok).0: T) = move _2;     // scope 0 at $DIR/try_identity_e2e.rs:+1:5: +11:6
+        discriminant(_0) = 0;            // scope 0 at $DIR/try_identity_e2e.rs:+1:5: +11:6
+        StorageDead(_2);                 // scope 0 at $DIR/try_identity_e2e.rs:+11:5: +11:6
+        StorageDead(_3);                 // scope 0 at $DIR/try_identity_e2e.rs:+12:1: +12:2
+        return;                          // scope 0 at $DIR/try_identity_e2e.rs:+12:1: +12:2
+    }
+}
diff --git a/src/test/mir-opt/try_identity_e2e.old.PreCodegen.after.mir b/src/test/mir-opt/try_identity_e2e.old.PreCodegen.after.mir
new file mode 100644 (file)
index 0000000..18d3e0f
--- /dev/null
@@ -0,0 +1,53 @@
+// MIR for `old` after PreCodegen
+
+fn old(_1: Result<T, E>) -> Result<T, E> {
+    debug x => _1;                       // in scope 0 at $DIR/try_identity_e2e.rs:+0:14: +0:15
+    let mut _0: std::result::Result<T, E>; // return place in scope 0 at $DIR/try_identity_e2e.rs:+0:34: +0:46
+    let mut _2: T;                       // in scope 0 at $DIR/try_identity_e2e.rs:+2:9: +5:10
+    let mut _3: isize;                   // in scope 0 at $DIR/try_identity_e2e.rs:+3:13: +3:18
+    let _4: T;                           // in scope 0 at $DIR/try_identity_e2e.rs:+3:16: +3:17
+    let _5: E;                           // in scope 0 at $DIR/try_identity_e2e.rs:+4:17: +4:18
+    let mut _6: E;                       // in scope 0 at $DIR/try_identity_e2e.rs:+4:34: +4:35
+    scope 1 {
+        debug v => _4;                   // in scope 1 at $DIR/try_identity_e2e.rs:+3:16: +3:17
+    }
+    scope 2 {
+        debug e => _5;                   // in scope 2 at $DIR/try_identity_e2e.rs:+4:17: +4:18
+    }
+
+    bb0: {
+        StorageLive(_2);                 // scope 0 at $DIR/try_identity_e2e.rs:+2:9: +5:10
+        _3 = discriminant(_1);           // scope 0 at $DIR/try_identity_e2e.rs:+2:15: +2:16
+        switchInt(move _3) -> [0_isize: bb3, 1_isize: bb1, otherwise: bb2]; // scope 0 at $DIR/try_identity_e2e.rs:+2:9: +2:16
+    }
+
+    bb1: {
+        StorageLive(_5);                 // scope 0 at $DIR/try_identity_e2e.rs:+4:17: +4:18
+        _5 = move ((_1 as Err).0: E);    // scope 0 at $DIR/try_identity_e2e.rs:+4:17: +4:18
+        StorageLive(_6);                 // scope 2 at $DIR/try_identity_e2e.rs:+4:34: +4:35
+        _6 = move _5;                    // scope 2 at $DIR/try_identity_e2e.rs:+4:34: +4:35
+        Deinit(_0);                      // scope 2 at $DIR/try_identity_e2e.rs:+4:30: +4:36
+        ((_0 as Err).0: E) = move _6;    // scope 2 at $DIR/try_identity_e2e.rs:+4:30: +4:36
+        discriminant(_0) = 1;            // scope 2 at $DIR/try_identity_e2e.rs:+4:30: +4:36
+        StorageDead(_6);                 // scope 2 at $DIR/try_identity_e2e.rs:+4:35: +4:36
+        StorageDead(_5);                 // scope 0 at $DIR/try_identity_e2e.rs:+4:35: +4:36
+        StorageDead(_2);                 // scope 0 at $DIR/try_identity_e2e.rs:+6:5: +6:6
+        return;                          // scope 0 at $DIR/try_identity_e2e.rs:+7:1: +7:2
+    }
+
+    bb2: {
+        unreachable;                     // scope 0 at $DIR/try_identity_e2e.rs:+2:15: +2:16
+    }
+
+    bb3: {
+        StorageLive(_4);                 // scope 0 at $DIR/try_identity_e2e.rs:+3:16: +3:17
+        _4 = move ((_1 as Ok).0: T);     // scope 0 at $DIR/try_identity_e2e.rs:+3:16: +3:17
+        _2 = move _4;                    // scope 1 at $DIR/try_identity_e2e.rs:+3:22: +3:23
+        StorageDead(_4);                 // scope 0 at $DIR/try_identity_e2e.rs:+3:22: +3:23
+        Deinit(_0);                      // scope 0 at $DIR/try_identity_e2e.rs:+1:5: +6:6
+        ((_0 as Ok).0: T) = move _2;     // scope 0 at $DIR/try_identity_e2e.rs:+1:5: +6:6
+        discriminant(_0) = 0;            // scope 0 at $DIR/try_identity_e2e.rs:+1:5: +6:6
+        StorageDead(_2);                 // scope 0 at $DIR/try_identity_e2e.rs:+6:5: +6:6
+        return;                          // scope 0 at $DIR/try_identity_e2e.rs:+7:1: +7:2
+    }
+}
diff --git a/src/test/mir-opt/try_identity_e2e.rs b/src/test/mir-opt/try_identity_e2e.rs
new file mode 100644 (file)
index 0000000..00cb80f
--- /dev/null
@@ -0,0 +1,34 @@
+// Track the status of MIR optimizations simplifying `Ok(res?)` for both the old and new desugarings
+// of that syntax.
+
+use std::ops::ControlFlow;
+
+// EMIT_MIR try_identity_e2e.new.PreCodegen.after.mir
+fn new<T, E>(x: Result<T, E>) -> Result<T, E> {
+    Ok(
+        match {
+            match x {
+                Ok(v) => ControlFlow::Continue(v),
+                Err(e) => ControlFlow::Break(e),
+            }
+        } {
+            ControlFlow::Continue(v) => v,
+            ControlFlow::Break(e) => return Err(e),
+        }
+    )
+}
+
+// EMIT_MIR try_identity_e2e.old.PreCodegen.after.mir
+fn old<T, E>(x: Result<T, E>) -> Result<T, E> {
+    Ok(
+        match x {
+            Ok(v) => v,
+            Err(e) => return Err(e),
+        }
+    )
+}
+
+fn main() {
+    let _ = new::<(), ()>(Ok(()));
+    let _ = old::<(), ()>(Ok(()));
+}
index 87f91be3ac82cec26d87785a1afe2debd038aed8..7f3172878bfb5f74325ee5b1a0f75db7143c30d1 100644 (file)
@@ -143,3 +143,30 @@ pub trait SimpleTrait {}
 /// Some docs.
 #[doc(cfg(any(target_os = "android", target_os = "linux", target_os = "emscripten", target_os = "dragonfly", target_os = "freebsd", target_os = "netbsd", target_os = "openbsd")))]
 impl SimpleTrait for LongItemInfo2 {}
+
+pub struct WhereWhitespace<T>;
+
+impl<T> WhereWhitespace<T> {
+    pub fn new<F>(f: F) -> Self
+    where
+        F: FnMut() -> i32,
+    {}
+}
+
+impl<K, T> Whitespace<&K> for WhereWhitespace<T>
+where
+    K: std::fmt::Debug,
+{
+    type Output = WhereWhitespace<T>;
+    fn index(&self, _key: &K) -> &Self::Output {
+        self
+    }
+}
+
+pub trait Whitespace<Idx>
+where
+    Idx: ?Sized,
+{
+    type Output;
+    fn index(&self, index: Idx) -> &Self::Output;
+}
diff --git a/src/test/rustdoc-gui/where-whitespace.goml b/src/test/rustdoc-gui/where-whitespace.goml
new file mode 100644 (file)
index 0000000..1a3ff1f
--- /dev/null
@@ -0,0 +1,27 @@
+// This test ensures that the where conditions are correctly displayed.
+goto: file://|DOC_PATH|/lib2/trait.Whitespace.html
+show-text: true
+// First, we check in the trait definition if the where clause is "on its own" (not on the same
+// line than "pub trait Whitespace<Idx>").
+compare-elements-position-false: (".item-decl code", ".where.fmt-newline", ("y"))
+// And that the code following it isn't on the same line either.
+compare-elements-position-false: (".item-decl .fnname", ".where.fmt-newline", ("y"))
+
+goto: file://|DOC_PATH|/lib2/struct.WhereWhitespace.html
+// We make the screen a bit wider to ensure that the trait impl is on one line.
+size: (915, 915)
+
+compare-elements-position-false: ("#method\.new .fnname", "#method\.new .where.fmt-newline", ("y"))
+// We ensure that both the trait name and the struct name are on the same line in
+// "impl<K, T> Whitespace<&K> for WhereWhitespace<T>".
+compare-elements-position: (
+    "#trait-implementations-list .impl h3 .trait",
+    "#trait-implementations-list .impl h3 .struct",
+    ("y"),
+)
+// And we now check that the where condition isn't on the same line.
+compare-elements-position-false: (
+    "#trait-implementations-list .impl h3 .trait",
+    "#trait-implementations-list .impl h3 .where.fmt-newline",
+    ("y"),
+)
index 352a8e646bb49fe76e9fc548a87be15378b2dd20..87d2f29e26055461a284f5b581469cc2e421e399 100644 (file)
@@ -31,12 +31,12 @@ impl Trait<{1 + 2}> for u8 {}
 impl<const N: usize> Trait<N> for [u8; N] {}
 
 // @has foo/struct.Foo.html '//pre[@class="rust struct"]' \
-//      'pub struct Foo<const N: usize> where u8: Trait<N>'
+//      'pub struct Foo<const N: usize>where u8: Trait<N>'
 pub struct Foo<const N: usize> where u8: Trait<N>;
 // @has foo/struct.Bar.html '//pre[@class="rust struct"]' 'pub struct Bar<T, const N: usize>(_)'
 pub struct Bar<T, const N: usize>([T; N]);
 
-// @has foo/struct.Foo.html '//*[@id="impl-Foo%3CM%3E"]/h3[@class="code-header in-band"]' 'impl<const M: usize> Foo<M> where u8: Trait<M>'
+// @has foo/struct.Foo.html '//*[@id="impl-Foo%3CM%3E"]/h3[@class="code-header in-band"]' 'impl<const M: usize> Foo<M>where u8: Trait<M>'
 impl<const M: usize> Foo<M> where u8: Trait<M> {
     // @has - '//*[@id="associatedconstant.FOO_ASSOC"]' 'pub const FOO_ASSOC: usize'
     pub const FOO_ASSOC: usize = M + 13;
@@ -50,14 +50,14 @@ pub fn hey<const N: usize>(&self) -> Bar<u8, N> {
 // @has foo/struct.Bar.html '//*[@id="impl-Bar%3Cu8%2C%20M%3E"]/h3[@class="code-header in-band"]' 'impl<const M: usize> Bar<u8, M>'
 impl<const M: usize> Bar<u8, M> {
     // @has - '//*[@id="method.hey"]' \
-    //      'pub fn hey<const N: usize>(&self) -> Foo<N> where u8: Trait<N>'
+    //      'pub fn hey<const N: usize>(&self) -> Foo<N>where u8: Trait<N>'
     pub fn hey<const N: usize>(&self) -> Foo<N> where u8: Trait<N> {
         Foo
     }
 }
 
 // @has foo/fn.test.html '//pre[@class="rust fn"]' \
-//      'pub fn test<const N: usize>() -> impl Trait<N> where u8: Trait<N>'
+//      'pub fn test<const N: usize>() -> impl Trait<N>where u8: Trait<N>'
 pub fn test<const N: usize>() -> impl Trait<N> where u8: Trait<N> {
     2u8
 }
diff --git a/src/test/rustdoc/doc_auto_cfg_nested_impl.rs b/src/test/rustdoc/doc_auto_cfg_nested_impl.rs
new file mode 100644 (file)
index 0000000..4d73e0d
--- /dev/null
@@ -0,0 +1,24 @@
+// Regression test for <https://github.com/rust-lang/rust/issues/101129>.
+
+#![feature(doc_auto_cfg)]
+#![crate_type = "lib"]
+#![crate_name = "foo"]
+
+pub struct S;
+pub trait MyTrait1 {}
+pub trait MyTrait2 {}
+
+// @has foo/struct.S.html
+// @has - '//*[@id="impl-MyTrait1-for-S"]//*[@class="stab portability"]' \
+//        'Available on non-crate feature coolstuff only.'
+#[cfg(not(feature = "coolstuff"))]
+impl MyTrait1 for S {}
+
+#[cfg(not(feature = "coolstuff"))]
+mod submod {
+    use crate::{S, MyTrait2};
+    // This impl should also have the `not(feature = "coolstuff")`.
+    // @has - '//*[@id="impl-MyTrait2-for-S"]//*[@class="stab portability"]' \
+    //        'Available on non-crate feature coolstuff only.'
+    impl MyTrait2 for S {}
+}
index ae981b9499a67cb20d131528639b836c2196ae34..2b9d4952d04eecd6c670d920b4f530b62dfc009d 100644 (file)
@@ -3,7 +3,7 @@
 
 // @has foo/trait.LendingIterator.html
 pub trait LendingIterator {
-    // @has - '//*[@id="associatedtype.Item"]//h4[@class="code-header"]' "type Item<'a> where Self: 'a"
+    // @has - '//*[@id="associatedtype.Item"]//h4[@class="code-header"]' "type Item<'a>where Self: 'a"
     type Item<'a> where Self: 'a;
 
     // @has - '//*[@id="tymethod.next"]//h4[@class="code-header"]' \
@@ -24,7 +24,7 @@ fn next<'a>(&self) -> () {}
 pub struct Infinite<T>(T);
 
 // @has foo/trait.LendingIterator.html
-// @has - '//*[@id="associatedtype.Item-2"]//h4[@class="code-header"]' "type Item<'a> where Self: 'a = &'a T"
+// @has - '//*[@id="associatedtype.Item-2"]//h4[@class="code-header"]' "type Item<'a>where Self: 'a = &'a T"
 impl<T> LendingIterator for Infinite<T> {
     type Item<'a> where Self: 'a = &'a T;
 
index b75b8de52f9cb6c3fab04e3a1dbf86caa7d4e019..59b5b6e5797cc47e3037fdd914df2f6476a24187 100644 (file)
@@ -4,7 +4,7 @@
 pub trait Trait<'x> {}
 
 // @has foo/fn.test1.html
-// @has - '//pre' "pub fn test1<T>() where for<'a> &'a T: Iterator,"
+// @has - '//pre' "pub fn test1<T>()where for<'a> &'a T: Iterator,"
 pub fn test1<T>()
 where
     for<'a> &'a T: Iterator,
@@ -12,7 +12,7 @@ pub fn test1<T>()
 }
 
 // @has foo/fn.test2.html
-// @has - '//pre' "pub fn test2<T>() where for<'a, 'b> &'a T: Trait<'b>,"
+// @has - '//pre' "pub fn test2<T>()where for<'a, 'b> &'a T: Trait<'b>,"
 pub fn test2<T>()
 where
     for<'a, 'b> &'a T: Trait<'b>,
@@ -20,7 +20,7 @@ pub fn test2<T>()
 }
 
 // @has foo/fn.test3.html
-// @has - '//pre' "pub fn test3<F>() where F: for<'a, 'b> Fn(&'a u8, &'b u8),"
+// @has - '//pre' "pub fn test3<F>()where F: for<'a, 'b> Fn(&'a u8, &'b u8),"
 pub fn test3<F>()
 where
     F: for<'a, 'b> Fn(&'a u8, &'b u8),
@@ -38,7 +38,7 @@ pub struct Foo<'a> {
 // @has - '//span[@id="structfield.some_trait"]' "some_trait: &'a dyn for<'b> Trait<'b>"
 
 impl<'a> Foo<'a> {
-    // @has - '//h4[@class="code-header"]' "pub fn bar<T>() where T: Trait<'a>,"
+    // @has - '//h4[@class="code-header"]' "pub fn bar<T>()where T: Trait<'a>,"
     pub fn bar<T>()
     where
         T: Trait<'a>,
index 249158c1a1f89bca9a9f1b63f1da16c76785e388..b1481e1f27978045e6864c92d42841fdf5d0755a 100644 (file)
@@ -6,7 +6,7 @@
 pub struct Foo<T> { field: T }
 
 // @has impl_parts/struct.Foo.html '//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-//     "impl<T: Clone> !AnAutoTrait for Foo<T> where T: Sync,"
+//     "impl<T: Clone> !AnAutoTrait for Foo<T>where T: Sync,"
 // @has impl_parts/trait.AnAutoTrait.html '//*[@class="item-list"]//h3[@class="code-header in-band"]' \
-//     "impl<T: Clone> !AnAutoTrait for Foo<T> where T: Sync,"
+//     "impl<T: Clone> !AnAutoTrait for Foo<T>where T: Sync,"
 impl<T: Clone> !AnAutoTrait for Foo<T> where T: Sync {}
index 84fc6f94a265a62a5d5d1becf5daf1f7efaf389d..643f93875909390b0b8bf410c325ecfd9393a309 100644 (file)
@@ -25,7 +25,7 @@ pub trait IndexMut<Idx: ?Sized>: Index<Idx> {
 
 pub mod reexport {
     // @has issue_20727_4/reexport/trait.Index.html
-    // @has - '//*[@class="rust trait"]' 'trait Index<Idx> where Idx: ?Sized, {'
+    // @has - '//*[@class="rust trait"]' 'trait Index<Idx>where Idx: ?Sized,{'
     // @has - '//*[@class="rust trait"]' 'type Output: ?Sized'
     // @has - '//*[@class="rust trait"]' \
     //        'fn index(&self, index: Idx) -> &Self::Output'
@@ -33,7 +33,7 @@ pub mod reexport {
 
     // @has issue_20727_4/reexport/trait.IndexMut.html
     // @has - '//*[@class="rust trait"]' \
-    //        'trait IndexMut<Idx>: Index<Idx> where Idx: ?Sized, {'
+    //        'trait IndexMut<Idx>: Index<Idx>where Idx: ?Sized,{'
     // @has - '//*[@class="rust trait"]' \
     //        'fn index_mut(&mut self, index: Idx) -> &mut Self::Output;'
     pub use issue_20727::IndexMut;
index 2a586b6ff6cdcfe3f427800bfe57cdeabb89c50f..29d2ec64c206d007d1d1a395fc0c38a3feb10615 100644 (file)
@@ -5,5 +5,5 @@
 
 // @has issue_21801/struct.Foo.html
 // @has - '//*[@id="method.new"]' \
-//        'fn new<F>(f: F) -> Foo where F: FnMut() -> i32'
+//        'fn new<F>(f: F) -> Foowhere F: FnMut() -> i32'
 pub use issue_21801::Foo;
index 635c3175f8138a39e40bc83d04f2bc1a6c0386be..134821e1ef3ea9bc724bb81e119a664724597461 100644 (file)
@@ -5,7 +5,7 @@ pub trait MyTrait {
     fn my_string(&self) -> String;
 }
 
-// @has - "//div[@id='implementors-list']//*[@id='impl-MyTrait-for-T']//h3[@class='code-header in-band']" "impl<T> MyTrait for T where T: Debug"
+// @has - "//div[@id='implementors-list']//*[@id='impl-MyTrait-for-T']//h3[@class='code-header in-band']" "impl<T> MyTrait for Twhere T: Debug"
 impl<T> MyTrait for T
 where
     T: fmt::Debug,
index 4184086f622abaff7f57fb211360c358ccfe15c8..91b67757453d2e788343eb82a15fa1d26313d309 100644 (file)
@@ -2,5 +2,5 @@
 
 pub trait Bar {}
 
-// @has foo/struct.Foo.html '//pre' 'pub struct Foo<T>(pub T) where T: Bar;'
+// @has foo/struct.Foo.html '//pre' 'pub struct Foo<T>(pub T)where T: Bar;'
 pub struct Foo<T>(pub T) where T: Bar;
index d88c29217023a9f9b5da233a3766297a872eeb0b..43fb705f58994717d9868b4942bdf5801c7fb847 100644 (file)
@@ -11,8 +11,8 @@ impl<B, C> Signal2 for B where B: Signal<Item = C> {
 }
 
 // @has issue_50159/struct.Switch.html
-// @has - '//h3[@class="code-header in-band"]' 'impl<B> Send for Switch<B> where <B as Signal>::Item: Send'
-// @has - '//h3[@class="code-header in-band"]' 'impl<B> Sync for Switch<B> where <B as Signal>::Item: Sync'
+// @has - '//h3[@class="code-header in-band"]' 'impl<B> Send for Switch<B>where <B as Signal>::Item: Send'
+// @has - '//h3[@class="code-header in-band"]' 'impl<B> Sync for Switch<B>where <B as Signal>::Item: Sync'
 // @count - '//*[@id="implementations-list"]//*[@class="impl"]' 0
 // @count - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]' 5
 pub struct Switch<B: Signal> {
index ee11ccc6811633fac9cd3f6b09abfc35b7e0a62f..aa5890a84514fc56364e8724fbcaf5891fdbf6d0 100644 (file)
@@ -8,7 +8,7 @@ pub trait Owned<'a> {
 
 // @has issue_51236/struct.Owned.html
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// "impl<T> Send for Owned<T> where <T as Owned<'static>>::Reader: Send"
+// "impl<T> Send for Owned<T>where <T as Owned<'static>>::Reader: Send"
 pub struct Owned<T> where T: for<'a> ::traits::Owned<'a> {
     marker: PhantomData<<T as ::traits::Owned<'static>>::Reader>,
 }
index bedaf5c4ddc360a311c83fc415943cab0b1e08f2..ce0f85d25da56d70009b7fee9911db47c06bd05e 100644 (file)
@@ -1,13 +1,11 @@
 pub trait ScopeHandle<'scope> {}
 
-
-
 // @has issue_54705/struct.ScopeFutureContents.html
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// "impl<'scope, S> Send for ScopeFutureContents<'scope, S> where S: Sync"
+// "impl<'scope, S> Send for ScopeFutureContents<'scope, S>where S: Sync"
 //
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// "impl<'scope, S> Sync for ScopeFutureContents<'scope, S> where S: Sync"
+// "impl<'scope, S> Sync for ScopeFutureContents<'scope, S>where S: Sync"
 pub struct ScopeFutureContents<'scope, S>
     where S: ScopeHandle<'scope>,
 {
index 83e08094c09534abf9da016c5c95fd7c42c8e9e9..a8841f137fecff11bb32a8a7fa028e850e30d40d 100644 (file)
@@ -8,7 +8,7 @@
 
 extern crate issue_98697_reexport_with_anonymous_lifetime;
 
-// @has issue_98697/fn.repro.html '//pre[@class="rust fn"]/code' 'fn repro<F>() where F: Fn(&str)'
+// @has issue_98697/fn.repro.html '//pre[@class="rust fn"]/code' 'fn repro<F>()where F: Fn(&str)'
 // @!has issue_98697/fn.repro.html '//pre[@class="rust fn"]/code' 'for<'
 pub use issue_98697_reexport_with_anonymous_lifetime::repro;
 
index b3f511bc1f153fc423b713ea2866bccc7cc4d65f..7f8f74ff457a5ab906ec670ea3d930d4e049adaa 100644 (file)
@@ -7,8 +7,8 @@
 // @has - '//span[@class="in-band"]' 'Primitive Type slice'
 // @has - '//section[@id="main-content"]//div[@class="docblock"]//p' 'this is a test!'
 // @has - '//h2[@id="synthetic-implementations"]' 'Auto Trait Implementations'
-// @has - '//div[@id="synthetic-implementations-list"]//h3' 'impl<T> Send for [T] where T: Send'
-// @has - '//div[@id="synthetic-implementations-list"]//h3' 'impl<T> Sync for [T] where T: Sync'
+// @has - '//div[@id="synthetic-implementations-list"]//h3' 'impl<T> Send for [T]where T: Send'
+// @has - '//div[@id="synthetic-implementations-list"]//h3' 'impl<T> Sync for [T]where T: Sync'
 #[doc(primitive = "slice")]
 /// this is a test!
 mod slice_prim {}
index 54c54fdbf68a8acafc9e50e48d0af6f9f7d3bc7b..19138fd1aceb20d1c1c8edb5699b83befb86cac9 100644 (file)
@@ -1,6 +1,6 @@
 // @has basic/struct.Foo.html
-// @has - '//h3[@class="code-header in-band"]' 'impl<T> Send for Foo<T> where T: Send'
-// @has - '//h3[@class="code-header in-band"]' 'impl<T> Sync for Foo<T> where T: Sync'
+// @has - '//h3[@class="code-header in-band"]' 'impl<T> Send for Foo<T>where T: Send'
+// @has - '//h3[@class="code-header in-band"]' 'impl<T> Sync for Foo<T>where T: Sync'
 // @count - '//*[@id="implementations-list"]//*[@class="impl has-srclink"]' 0
 // @count - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]' 5
 pub struct Foo<T> {
index f9017b90caee774d2022797e0321002bb77b630f..39f78983da2b031766ab2c8968a2d26d73e4f320 100644 (file)
@@ -21,7 +21,7 @@ pub struct Foo<T> {
 
 // @has complex/struct.NotOuter.html
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// "impl<'a, T, K: ?Sized> Send for Outer<'a, T, K> where K: for<'b> Fn((&'b bool, &'a u8)) \
+// "impl<'a, T, K: ?Sized> Send for Outer<'a, T, K>where K: for<'b> Fn((&'b bool, &'a u8)) \
 // -> &'b i8, T: MyTrait<'a>, <T as MyTrait<'a>>::MyItem: Copy, 'a: 'static"
 
 pub use foo::{Foo, Inner as NotInner, MyTrait as NotMyTrait, Outer as NotOuter};
index ee1393f9729c176ccff505f02e489c9e2116a2dc..0c94850e78608c2cb12b5f90bf4cf80d6fd18e77 100644 (file)
@@ -10,10 +10,10 @@ unsafe impl<'a, T> Send for Inner<'a, T>
 
 // @has lifetimes/struct.Foo.html
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// "impl<'c, K> Send for Foo<'c, K> where K: for<'b> Fn(&'b bool) -> &'c u8, 'c: 'static"
+// "impl<'c, K> Send for Foo<'c, K>where K: for<'b> Fn(&'b bool) -> &'c u8, 'c: 'static"
 //
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// "impl<'c, K> Sync for Foo<'c, K> where K: Sync"
+// "impl<'c, K> Sync for Foo<'c, K>where K: Sync"
 pub struct Foo<'c, K: 'c> {
     inner_field: Inner<'c, K>,
 }
index 49bad162211b7041be4ba179022091d2d11f3b9f..35047e3e8c0717349eca64a02043ac1b06c4bc97 100644 (file)
@@ -1,6 +1,6 @@
 // @has manual/struct.Foo.html
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// 'impl<T> Sync for Foo<T> where T: Sync'
+// 'impl<T> Sync for Foo<T>where T: Sync'
 //
 // @has - '//*[@id="trait-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
 // 'impl<T> Send for Foo<T>'
index 69edbee619e31e8316c1796bcc7916cfd9cd9c28..09587bcc30f13954f3c742080c7ec24be6453d9e 100644 (file)
@@ -10,10 +10,10 @@ unsafe impl<T> Send for Inner<T>
 
 // @has nested/struct.Foo.html
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// 'impl<T> Send for Foo<T> where T: Copy'
+// 'impl<T> Send for Foo<T>where T: Copy'
 //
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// 'impl<T> Sync for Foo<T> where T: Sync'
+// 'impl<T> Sync for Foo<T>where T: Sync'
 pub struct Foo<T> {
     inner_field: Inner<T>,
 }
index 16ab876e829ef8f25f4d82d79529e4c89c84f3ca..41375decc8a4aa6c9971764ab82fab822973f17c 100644 (file)
@@ -10,7 +10,7 @@ unsafe impl<T> Send for Inner<T>
 
 // @has no_redundancy/struct.Outer.html
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// "impl<T> Send for Outer<T> where T: Send + Copy"
+// "impl<T> Send for Outer<T>where T: Send + Copy"
 pub struct Outer<T> {
     inner_field: Inner<T>,
 }
index 8b020582563f3d3ac9fe6cd6be4975c2c66641bf..e80b1b1dc9bcf99c96fc535bcc8d9ca7f9ed470a 100644 (file)
@@ -24,10 +24,10 @@ unsafe impl<'a, T> Sync for Inner<'a, T>
 
 // @has project/struct.Foo.html
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// "impl<'c, K> Send for Foo<'c, K> where K: MyTrait<MyItem = bool>, 'c: 'static"
+// "impl<'c, K> Send for Foo<'c, K>where K: MyTrait<MyItem = bool>, 'c: 'static"
 //
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// "impl<'c, K> Sync for Foo<'c, K> where K: MyTrait, <K as MyTrait>::MyItem: OtherTrait, \
+// "impl<'c, K> Sync for Foo<'c, K>where K: MyTrait, <K as MyTrait>::MyItem: OtherTrait, \
 // 'c: 'static,"
 pub struct Foo<'c, K: 'c> {
     inner_field: Inner<'c, K>,
index ccef901b18da3e57b359973eb52e04cb3f5f19ad..d15a8de7d2fe14fdb20381086bc6dc7a6762e58c 100644 (file)
@@ -24,6 +24,6 @@ impl<T> Pattern for Wrapper<T> {
 
 // @has self_referential/struct.WriteAndThen.html
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// "impl<P1> Send for WriteAndThen<P1>  where  <P1 as Pattern>::Value: Send"
+// "impl<P1> Send for WriteAndThen<P1>where    <P1 as Pattern>::Value: Send"
 pub struct WriteAndThen<P1>(pub P1::Value,pub <Constrain<P1, Wrapper<P1::Value>> as Pattern>::Value)
     where P1: Pattern;
index 36e985144b0e09026e60796a8908419b766eb363..08e9567313e22bb78f0faf6f5701537b6c9e3ecf 100644 (file)
@@ -4,7 +4,7 @@ pub trait OwnedTrait<'a> {
 
 // @has static_region/struct.Owned.html
 // @has - '//*[@id="synthetic-implementations-list"]//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-// "impl<T> Send for Owned<T> where <T as OwnedTrait<'static>>::Reader: Send"
+// "impl<T> Send for Owned<T>where <T as OwnedTrait<'static>>::Reader: Send"
 pub struct Owned<T> where T: OwnedTrait<'static> {
     marker: <T as OwnedTrait<'static>>::Reader,
 }
index 3150a8ea05f41f321dde58bbe2dded183deead48..b8502e10a48c4dcb5ad05e763930a673bae55046 100644 (file)
@@ -7,7 +7,7 @@ pub trait SomeTrait<Rhs = Self>
 }
 
 // @has 'foo/trait.SomeTrait.html'
-// @has - "//*[@id='impl-SomeTrait%3C(A%2C%20B%2C%20C%2C%20D%2C%20E)%3E-for-(A%2C%20B%2C%20C%2C%20D%2C%20E)']/h3" "impl<A, B, C, D, E> SomeTrait<(A, B, C, D, E)> for (A, B, C, D, E) where A: PartialOrd<A> + PartialEq<A>, B: PartialOrd<B> + PartialEq<B>, C: PartialOrd<C> + PartialEq<C>, D: PartialOrd<D> + PartialEq<D>, E: PartialOrd<E> + PartialEq<E> + ?Sized, "
+// @has - "//*[@id='impl-SomeTrait%3C(A%2C%20B%2C%20C%2C%20D%2C%20E)%3E-for-(A%2C%20B%2C%20C%2C%20D%2C%20E)']/h3" "impl<A, B, C, D, E> SomeTrait<(A, B, C, D, E)> for (A, B, C, D, E)where A: PartialOrd<A> + PartialEq<A>, B: PartialOrd<B> + PartialEq<B>, C: PartialOrd<C> + PartialEq<C>, D: PartialOrd<D> + PartialEq<D>, E: PartialOrd<E> + PartialEq<E> + ?Sized, "
 impl<A, B, C, D, E> SomeTrait<(A, B, C, D, E)> for (A, B, C, D, E)
 where
     A: PartialOrd<A> + PartialEq<A>,
index 50a5722fbaff6926e5feec51c6ffd18d531bac5a..c1a630e25ba0ef00881c4682afd10ed922f97351 100644 (file)
@@ -3,17 +3,17 @@
 
 pub trait MyTrait { fn dummy(&self) { } }
 
-// @has foo/struct.Alpha.html '//pre' "pub struct Alpha<A>(_) where A: MyTrait"
+// @has foo/struct.Alpha.html '//pre' "pub struct Alpha<A>(_)where A: MyTrait"
 pub struct Alpha<A>(A) where A: MyTrait;
-// @has foo/trait.Bravo.html '//pre' "pub trait Bravo<B> where B: MyTrait"
+// @has foo/trait.Bravo.html '//pre' "pub trait Bravo<B>where B: MyTrait"
 pub trait Bravo<B> where B: MyTrait { fn get(&self, B: B); }
-// @has foo/fn.charlie.html '//pre' "pub fn charlie<C>() where C: MyTrait"
+// @has foo/fn.charlie.html '//pre' "pub fn charlie<C>()where C: MyTrait"
 pub fn charlie<C>() where C: MyTrait {}
 
 pub struct Delta<D>(D);
 
 // @has foo/struct.Delta.html '//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-//          "impl<D> Delta<D> where D: MyTrait"
+//          "impl<D> Delta<D>where D: MyTrait"
 impl<D> Delta<D> where D: MyTrait {
     pub fn delta() {}
 }
@@ -33,19 +33,19 @@ pub trait TraitWhere {
 }
 
 // @has foo/struct.Echo.html '//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-//          "impl<E> MyTrait for Echo<E> where E: MyTrait"
+//          "impl<E> MyTrait for Echo<E>where E: MyTrait"
 // @has foo/trait.MyTrait.html '//*[@id="implementors-list"]//h3[@class="code-header in-band"]' \
-//          "impl<E> MyTrait for Echo<E> where E: MyTrait"
-impl<E> MyTrait for Echo<E> where E: MyTrait {}
+//          "impl<E> MyTrait for Echo<E>where E: MyTrait"
+impl<E> MyTrait for Echo<E>where E: MyTrait {}
 
 pub enum Foxtrot<F> { Foxtrot1(F) }
 
 // @has foo/enum.Foxtrot.html '//*[@class="impl has-srclink"]//h3[@class="code-header in-band"]' \
-//          "impl<F> MyTrait for Foxtrot<F> where F: MyTrait"
+//          "impl<F> MyTrait for Foxtrot<F>where F: MyTrait"
 // @has foo/trait.MyTrait.html '//*[@id="implementors-list"]//h3[@class="code-header in-band"]' \
-//          "impl<F> MyTrait for Foxtrot<F> where F: MyTrait"
-impl<F> MyTrait for Foxtrot<F> where F: MyTrait {}
+//          "impl<F> MyTrait for Foxtrot<F>where F: MyTrait"
+impl<F> MyTrait for Foxtrot<F>where F: MyTrait {}
 
 // @has foo/type.Golf.html '//pre[@class="rust typedef"]' \
-//          "type Golf<T> where T: Clone, = (T, T)"
+//          "type Golf<T>where T: Clone, = (T, T)"
 pub type Golf<T> where T: Clone = (T, T);
index b1f557cb94de8538e58ef71051a7628f05fbf842..c1c109ac1eade556f168b1c2000ef8ff04d624e2 100644 (file)
@@ -2,7 +2,7 @@
 // Tests error conditions for specifying diagnostics using #[derive(SessionDiagnostic)]
 
 // normalize-stderr-test "the following other types implement trait `IntoDiagnosticArg`:(?:.*\n){0,9}\s+and \d+ others" -> "normalized in stderr"
-
+// normalize-stderr-test "diagnostic_builder\.rs:[0-9]+:[0-9]+" -> "diagnostic_builder.rs:LL:CC"
 // The proc_macro2 crate handles spans differently when on beta/stable release rather than nightly,
 // changing the output of this test. Since SessionDiagnostic is strictly internal to the compiler
 // the test is just ignored on stable and beta:
index 621c59f448951ed0d972684a86272be7438063bf..ab5c28fe473326aa02b4a5a42cd62e32a4dc57e5 100644 (file)
@@ -453,7 +453,7 @@ LL | #[derive(SessionDiagnostic)]
    |
    = help: normalized in stderr
 note: required by a bound in `DiagnosticBuilder::<'a, G>::set_arg`
-  --> $COMPILER_DIR/rustc_errors/src/diagnostic_builder.rs:569:19
+  --> $COMPILER_DIR/rustc_errors/src/diagnostic_builder.rs:LL:CC
    |
 LL |         arg: impl IntoDiagnosticArg,
    |                   ^^^^^^^^^^^^^^^^^ required by this bound in `DiagnosticBuilder::<'a, G>::set_arg`
index f0843c60543df4203c9a15cb6a8560196567aa82..812ca0c72bd058178d518b539eb4c709db737759 100644 (file)
@@ -167,8 +167,8 @@ enum P {
 #[derive(SessionSubdiagnostic)]
 enum Q {
     #[bar]
-//~^ ERROR `#[bar]` is not a valid attribute
-//~^^ ERROR cannot find attribute `bar` in this scope
+    //~^ ERROR `#[bar]` is not a valid attribute
+    //~^^ ERROR cannot find attribute `bar` in this scope
     A {
         #[primary_span]
         span: Span,
@@ -179,8 +179,8 @@ enum Q {
 #[derive(SessionSubdiagnostic)]
 enum R {
     #[bar = "..."]
-//~^ ERROR `#[bar = ...]` is not a valid attribute
-//~^^ ERROR cannot find attribute `bar` in this scope
+    //~^ ERROR `#[bar = ...]` is not a valid attribute
+    //~^^ ERROR cannot find attribute `bar` in this scope
     A {
         #[primary_span]
         span: Span,
@@ -191,8 +191,8 @@ enum R {
 #[derive(SessionSubdiagnostic)]
 enum S {
     #[bar = 4]
-//~^ ERROR `#[bar = ...]` is not a valid attribute
-//~^^ ERROR cannot find attribute `bar` in this scope
+    //~^ ERROR `#[bar = ...]` is not a valid attribute
+    //~^^ ERROR cannot find attribute `bar` in this scope
     A {
         #[primary_span]
         span: Span,
@@ -203,8 +203,8 @@ enum S {
 #[derive(SessionSubdiagnostic)]
 enum T {
     #[bar("...")]
-//~^ ERROR `#[bar("...")]` is not a valid attribute
-//~^^ ERROR cannot find attribute `bar` in this scope
+    //~^ ERROR `#[bar(...)]` is not a valid attribute
+    //~^^ ERROR cannot find attribute `bar` in this scope
     A {
         #[primary_span]
         span: Span,
@@ -215,7 +215,7 @@ enum T {
 #[derive(SessionSubdiagnostic)]
 enum U {
     #[label(code = "...")]
-//~^ ERROR diagnostic slug must be first argument of a `#[label(...)]` attribute
+    //~^ ERROR diagnostic slug must be first argument of a `#[label(...)]` attribute
     A {
         #[primary_span]
         span: Span,
@@ -232,7 +232,7 @@ enum V {
         var: String,
     },
     B {
-//~^ ERROR subdiagnostic kind not specified
+    //~^ ERROR subdiagnostic kind not specified
         #[primary_span]
         span: Span,
         var: String,
@@ -307,6 +307,14 @@ union AC {
     b: u64
 }
 
+#[derive(SessionSubdiagnostic)]
+#[label(parser::add_paren)]
+#[label(parser::add_paren)]
+struct AD {
+    #[primary_span]
+    span: Span,
+}
+
 #[derive(SessionSubdiagnostic)]
 #[label(parser::add_paren, parser::add_paren)]
 //~^ ERROR `#[label(parser::add_paren)]` is not a valid attribute
@@ -319,16 +327,16 @@ struct AE {
 #[label(parser::add_paren)]
 struct AF {
     #[primary_span]
-//~^ NOTE previously specified here
+    //~^ NOTE previously specified here
     span_a: Span,
     #[primary_span]
-//~^ ERROR specified multiple times
+    //~^ ERROR specified multiple times
     span_b: Span,
 }
 
 #[derive(SessionSubdiagnostic)]
 struct AG {
-//~^ ERROR subdiagnostic kind not specified
+    //~^ ERROR subdiagnostic kind not specified
     #[primary_span]
     span: Span,
 }
@@ -380,27 +388,25 @@ struct AK {
     #[primary_span]
     span: Span,
     #[applicability]
-//~^ NOTE previously specified here
+    //~^ NOTE previously specified here
     applicability_a: Applicability,
     #[applicability]
-//~^ ERROR specified multiple times
+    //~^ ERROR specified multiple times
     applicability_b: Applicability,
 }
 
 #[derive(SessionSubdiagnostic)]
 #[suggestion(parser::add_paren, code = "...")]
-//~^ ERROR suggestion without `applicability`
 struct AL {
     #[primary_span]
     span: Span,
     #[applicability]
-//~^ ERROR the `#[applicability]` attribute can only be applied to fields of type `Applicability`
+    //~^ ERROR the `#[applicability]` attribute can only be applied to fields of type `Applicability`
     applicability: Span,
 }
 
 #[derive(SessionSubdiagnostic)]
 #[suggestion(parser::add_paren, code = "...")]
-//~^ ERROR suggestion without `applicability`
 struct AM {
     #[primary_span]
     span: Span,
@@ -436,8 +442,7 @@ struct AP {
 
 #[derive(SessionSubdiagnostic)]
 #[suggestion(parser::add_paren, code = "...")]
-//~^ ERROR suggestion without `applicability`
-//~^^ ERROR suggestion without `#[primary_span]` field
+//~^ ERROR suggestion without `#[primary_span]` field
 struct AR {
     var: String,
 }
@@ -507,3 +512,120 @@ struct AZ {
     #[primary_span]
     span: Span,
 }
+
+#[derive(SessionSubdiagnostic)]
+#[suggestion(parser::add_paren, code = "...")]
+//~^ ERROR suggestion without `#[primary_span]` field
+struct BA {
+    #[suggestion_part]
+    //~^ ERROR `#[suggestion_part]` is not a valid attribute
+    span: Span,
+    #[suggestion_part(code = "...")]
+    //~^ ERROR `#[suggestion_part(...)]` is not a valid attribute
+    span2: Span,
+    #[applicability]
+    applicability: Applicability,
+    var: String,
+}
+
+#[derive(SessionSubdiagnostic)]
+#[multipart_suggestion(parser::add_paren, code = "...", applicability = "machine-applicable")]
+//~^ ERROR multipart suggestion without any `#[suggestion_part(...)]` fields
+//~| ERROR `code` is not a valid nested attribute of a `multipart_suggestion` attribute
+struct BBa {
+    var: String,
+}
+
+#[derive(SessionSubdiagnostic)]
+#[multipart_suggestion(parser::add_paren, applicability = "machine-applicable")]
+struct BBb {
+    #[suggestion_part]
+    //~^ ERROR `#[suggestion_part(...)]` attribute without `code = "..."`
+    span1: Span,
+}
+
+#[derive(SessionSubdiagnostic)]
+#[multipart_suggestion(parser::add_paren, applicability = "machine-applicable")]
+struct BBc {
+    #[suggestion_part()]
+    //~^ ERROR `#[suggestion_part(...)]` attribute without `code = "..."`
+    span1: Span,
+}
+
+#[derive(SessionSubdiagnostic)]
+#[multipart_suggestion(parser::add_paren)]
+//~^ ERROR multipart suggestion without any `#[suggestion_part(...)]` fields
+struct BC {
+    #[primary_span]
+    //~^ ERROR `#[primary_span]` is not a valid attribute
+    span: Span,
+}
+
+#[derive(SessionSubdiagnostic)]
+#[multipart_suggestion(parser::add_paren)]
+struct BD {
+    #[suggestion_part]
+    //~^ ERROR `#[suggestion_part(...)]` attribute without `code = "..."`
+    span1: Span,
+    #[suggestion_part()]
+    //~^ ERROR `#[suggestion_part(...)]` attribute without `code = "..."`
+    span2: Span,
+    #[suggestion_part(foo = "bar")]
+    //~^ ERROR `#[suggestion_part(foo = ...)]` is not a valid attribute
+    span4: Span,
+    #[suggestion_part(code = "...")]
+    //~^ ERROR the `#[suggestion_part(...)]` attribute can only be applied to fields of type `Span` or `MultiSpan`
+    s1: String,
+    #[suggestion_part()]
+    //~^ ERROR the `#[suggestion_part(...)]` attribute can only be applied to fields of type `Span` or `MultiSpan`
+    s2: String,
+}
+
+#[derive(SessionSubdiagnostic)]
+#[multipart_suggestion(parser::add_paren, applicability = "machine-applicable")]
+struct BE {
+    #[suggestion_part(code = "...", code = ",,,")]
+    //~^ ERROR specified multiple times
+    //~| NOTE previously specified here
+    span: Span,
+}
+
+#[derive(SessionSubdiagnostic)]
+#[multipart_suggestion(parser::add_paren, applicability = "machine-applicable")]
+struct BF {
+    #[suggestion_part(code = "(")]
+    first: Span,
+    #[suggestion_part(code = ")")]
+    second: Span,
+}
+
+#[derive(SessionSubdiagnostic)]
+#[multipart_suggestion(parser::add_paren)]
+struct BG {
+    #[applicability]
+    appl: Applicability,
+    #[suggestion_part(code = "(")]
+    first: Span,
+    #[suggestion_part(code = ")")]
+    second: Span,
+}
+
+#[derive(SessionSubdiagnostic)]
+#[multipart_suggestion(parser::add_paren, applicability = "machine-applicable")]
+//~^ NOTE previously specified here
+struct BH {
+    #[applicability]
+    //~^ ERROR specified multiple times
+    appl: Applicability,
+    #[suggestion_part(code = "(")]
+    first: Span,
+    #[suggestion_part(code = ")")]
+    second: Span,
+}
+
+#[derive(SessionSubdiagnostic)]
+#[multipart_suggestion(parser::add_paren, applicability = "machine-applicable")]
+struct BI {
+    #[suggestion_part(code = "")]
+    spans: Vec<Span>,
+}
index 6bd9144dbf6f0b8e8be1ca2dfb273f4cb1b17cb8..0a0247e898088b41bcb6592e1a53afb59cc76ec8 100644 (file)
@@ -65,16 +65,16 @@ LL | #[label()]
    | ^^^^^^^^^^
 
 error: `code` is not a valid nested attribute of a `label` attribute
-  --> $DIR/subdiagnostic-derive.rs:137:1
+  --> $DIR/subdiagnostic-derive.rs:137:28
    |
 LL | #[label(parser::add_paren, code = "...")]
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |                            ^^^^^^^^^^^^
 
 error: `applicability` is not a valid nested attribute of a `label` attribute
-  --> $DIR/subdiagnostic-derive.rs:146:1
+  --> $DIR/subdiagnostic-derive.rs:146:28
    |
 LL | #[label(parser::add_paren, applicability = "machine-applicable")]
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |                            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: unsupported type attribute for subdiagnostic enum
   --> $DIR/subdiagnostic-derive.rs:155:1
@@ -100,13 +100,11 @@ error: `#[bar = ...]` is not a valid attribute
 LL |     #[bar = 4]
    |     ^^^^^^^^^^
 
-error: `#[bar("...")]` is not a valid attribute
-  --> $DIR/subdiagnostic-derive.rs:205:11
+error: `#[bar(...)]` is not a valid attribute
+  --> $DIR/subdiagnostic-derive.rs:205:5
    |
 LL |     #[bar("...")]
-   |           ^^^^^
-   |
-   = help: first argument of the attribute should be the diagnostic slug
+   |     ^^^^^^^^^^^^^
 
 error: diagnostic slug must be first argument of a `#[label(...)]` attribute
   --> $DIR/subdiagnostic-derive.rs:217:5
@@ -163,6 +161,8 @@ error: `#[bar(...)]` is not a valid attribute
    |
 LL |     #[bar("...")]
    |     ^^^^^^^^^^^^^
+   |
+   = help: only `primary_span`, `applicability` and `skip_arg` are valid field attributes
 
 error: unexpected unsupported untagged union
   --> $DIR/subdiagnostic-derive.rs:304:1
@@ -175,7 +175,7 @@ LL | | }
    | |_^
 
 error: `#[label(parser::add_paren)]` is not a valid attribute
-  --> $DIR/subdiagnostic-derive.rs:311:28
+  --> $DIR/subdiagnostic-derive.rs:319:28
    |
 LL | #[label(parser::add_paren, parser::add_paren)]
    |                            ^^^^^^^^^^^^^^^^^
@@ -183,133 +183,225 @@ LL | #[label(parser::add_paren, parser::add_paren)]
    = help: a diagnostic slug must be the first argument to the attribute
 
 error: specified multiple times
-  --> $DIR/subdiagnostic-derive.rs:324:5
+  --> $DIR/subdiagnostic-derive.rs:332:5
    |
 LL |     #[primary_span]
    |     ^^^^^^^^^^^^^^^
    |
 note: previously specified here
-  --> $DIR/subdiagnostic-derive.rs:321:5
+  --> $DIR/subdiagnostic-derive.rs:329:5
    |
 LL |     #[primary_span]
    |     ^^^^^^^^^^^^^^^
 
 error: subdiagnostic kind not specified
-  --> $DIR/subdiagnostic-derive.rs:330:8
+  --> $DIR/subdiagnostic-derive.rs:338:8
    |
 LL | struct AG {
    |        ^^
 
 error: specified multiple times
-  --> $DIR/subdiagnostic-derive.rs:367:47
+  --> $DIR/subdiagnostic-derive.rs:375:47
    |
 LL | #[suggestion(parser::add_paren, code = "...", code = "...")]
    |                                               ^^^^^^^^^^^^
    |
 note: previously specified here
-  --> $DIR/subdiagnostic-derive.rs:367:33
+  --> $DIR/subdiagnostic-derive.rs:375:33
    |
 LL | #[suggestion(parser::add_paren, code = "...", code = "...")]
    |                                 ^^^^^^^^^^^^
 
 error: specified multiple times
-  --> $DIR/subdiagnostic-derive.rs:385:5
+  --> $DIR/subdiagnostic-derive.rs:393:5
    |
 LL |     #[applicability]
    |     ^^^^^^^^^^^^^^^^
    |
 note: previously specified here
-  --> $DIR/subdiagnostic-derive.rs:382:5
+  --> $DIR/subdiagnostic-derive.rs:390:5
    |
 LL |     #[applicability]
    |     ^^^^^^^^^^^^^^^^
 
 error: the `#[applicability]` attribute can only be applied to fields of type `Applicability`
-  --> $DIR/subdiagnostic-derive.rs:396:5
+  --> $DIR/subdiagnostic-derive.rs:403:5
    |
 LL |     #[applicability]
    |     ^^^^^^^^^^^^^^^^
 
-error: suggestion without `applicability`
-  --> $DIR/subdiagnostic-derive.rs:391:1
+error: suggestion without `code = "..."`
+  --> $DIR/subdiagnostic-derive.rs:416:1
    |
-LL | / #[suggestion(parser::add_paren, code = "...")]
-LL | |
-LL | | struct AL {
-LL | |     #[primary_span]
-...  |
-LL | |     applicability: Span,
-LL | | }
-   | |_^
+LL | #[suggestion(parser::add_paren)]
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: suggestion without `applicability`
-  --> $DIR/subdiagnostic-derive.rs:402:1
+error: invalid applicability
+  --> $DIR/subdiagnostic-derive.rs:426:46
+   |
+LL | #[suggestion(parser::add_paren, code ="...", applicability = "foo")]
+   |                                              ^^^^^^^^^^^^^^^^^^^^^
+
+error: suggestion without `#[primary_span]` field
+  --> $DIR/subdiagnostic-derive.rs:444:1
    |
 LL | / #[suggestion(parser::add_paren, code = "...")]
 LL | |
-LL | | struct AM {
-LL | |     #[primary_span]
-LL | |     span: Span,
+LL | | struct AR {
+LL | |     var: String,
 LL | | }
    | |_^
 
-error: suggestion without `code = "..."`
-  --> $DIR/subdiagnostic-derive.rs:410:1
+error: unsupported type attribute for subdiagnostic enum
+  --> $DIR/subdiagnostic-derive.rs:458:1
    |
-LL | / #[suggestion(parser::add_paren)]
+LL | #[label]
+   | ^^^^^^^^
+
+error: `var` doesn't refer to a field on this type
+  --> $DIR/subdiagnostic-derive.rs:478:39
+   |
+LL | #[suggestion(parser::add_paren, code ="{var}", applicability = "machine-applicable")]
+   |                                       ^^^^^^^
+
+error: `var` doesn't refer to a field on this type
+  --> $DIR/subdiagnostic-derive.rs:497:43
+   |
+LL |     #[suggestion(parser::add_paren, code ="{var}", applicability = "machine-applicable")]
+   |                                           ^^^^^^^
+
+error: `#[suggestion_part]` is not a valid attribute
+  --> $DIR/subdiagnostic-derive.rs:520:5
+   |
+LL |     #[suggestion_part]
+   |     ^^^^^^^^^^^^^^^^^^
+   |
+   = help: `#[suggestion_part(...)]` is only valid in multipart suggestions, use `#[primary_span]` instead
+
+error: `#[suggestion_part(...)]` is not a valid attribute
+  --> $DIR/subdiagnostic-derive.rs:523:5
+   |
+LL |     #[suggestion_part(code = "...")]
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = help: `#[suggestion_part(...)]` is only valid in multipart suggestions
+
+error: suggestion without `#[primary_span]` field
+  --> $DIR/subdiagnostic-derive.rs:517:1
+   |
+LL | / #[suggestion(parser::add_paren, code = "...")]
 LL | |
-LL | | struct AN {
-LL | |     #[primary_span]
+LL | | struct BA {
+LL | |     #[suggestion_part]
 ...  |
-LL | |     applicability: Applicability,
+LL | |     var: String,
 LL | | }
    | |_^
 
-error: invalid applicability
-  --> $DIR/subdiagnostic-derive.rs:420:46
+error: `code` is not a valid nested attribute of a `multipart_suggestion` attribute
+  --> $DIR/subdiagnostic-derive.rs:532:43
    |
-LL | #[suggestion(parser::add_paren, code ="...", applicability = "foo")]
-   |                                              ^^^^^^^^^^^^^^^^^^^^^
+LL | #[multipart_suggestion(parser::add_paren, code = "...", applicability = "machine-applicable")]
+   |                                           ^^^^^^^^^^^^
 
-error: suggestion without `applicability`
-  --> $DIR/subdiagnostic-derive.rs:438:1
+error: multipart suggestion without any `#[suggestion_part(...)]` fields
+  --> $DIR/subdiagnostic-derive.rs:532:1
    |
-LL | / #[suggestion(parser::add_paren, code = "...")]
+LL | / #[multipart_suggestion(parser::add_paren, code = "...", applicability = "machine-applicable")]
 LL | |
 LL | |
-LL | | struct AR {
+LL | | struct BBa {
 LL | |     var: String,
 LL | | }
    | |_^
 
-error: suggestion without `#[primary_span]` field
-  --> $DIR/subdiagnostic-derive.rs:438:1
+error: `#[suggestion_part(...)]` attribute without `code = "..."`
+  --> $DIR/subdiagnostic-derive.rs:542:5
    |
-LL | / #[suggestion(parser::add_paren, code = "...")]
+LL |     #[suggestion_part]
+   |     ^^^^^^^^^^^^^^^^^^
+
+error: `#[suggestion_part(...)]` attribute without `code = "..."`
+  --> $DIR/subdiagnostic-derive.rs:550:5
+   |
+LL |     #[suggestion_part()]
+   |     ^^^^^^^^^^^^^^^^^^^^
+
+error: `#[primary_span]` is not a valid attribute
+  --> $DIR/subdiagnostic-derive.rs:559:5
+   |
+LL |     #[primary_span]
+   |     ^^^^^^^^^^^^^^^
+   |
+   = help: multipart suggestions use one or more `#[suggestion_part]`s rather than one `#[primary_span]`
+
+error: multipart suggestion without any `#[suggestion_part(...)]` fields
+  --> $DIR/subdiagnostic-derive.rs:556:1
+   |
+LL | / #[multipart_suggestion(parser::add_paren)]
 LL | |
+LL | | struct BC {
+LL | |     #[primary_span]
 LL | |
-LL | | struct AR {
-LL | |     var: String,
+LL | |     span: Span,
 LL | | }
    | |_^
 
-error: unsupported type attribute for subdiagnostic enum
-  --> $DIR/subdiagnostic-derive.rs:453:1
+error: `#[suggestion_part(...)]` attribute without `code = "..."`
+  --> $DIR/subdiagnostic-derive.rs:567:5
    |
-LL | #[label]
-   | ^^^^^^^^
+LL |     #[suggestion_part]
+   |     ^^^^^^^^^^^^^^^^^^
 
-error: `var` doesn't refer to a field on this type
-  --> $DIR/subdiagnostic-derive.rs:473:39
+error: `#[suggestion_part(...)]` attribute without `code = "..."`
+  --> $DIR/subdiagnostic-derive.rs:570:5
    |
-LL | #[suggestion(parser::add_paren, code ="{var}", applicability = "machine-applicable")]
-   |                                       ^^^^^^^
+LL |     #[suggestion_part()]
+   |     ^^^^^^^^^^^^^^^^^^^^
 
-error: `var` doesn't refer to a field on this type
-  --> $DIR/subdiagnostic-derive.rs:492:43
+error: `#[suggestion_part(foo = ...)]` is not a valid attribute
+  --> $DIR/subdiagnostic-derive.rs:573:23
    |
-LL |     #[suggestion(parser::add_paren, code ="{var}", applicability = "machine-applicable")]
-   |                                           ^^^^^^^
+LL |     #[suggestion_part(foo = "bar")]
+   |                       ^^^^^^^^^^^
+   |
+   = help: `code` is the only valid nested attribute
+
+error: the `#[suggestion_part(...)]` attribute can only be applied to fields of type `Span` or `MultiSpan`
+  --> $DIR/subdiagnostic-derive.rs:576:5
+   |
+LL |     #[suggestion_part(code = "...")]
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: the `#[suggestion_part(...)]` attribute can only be applied to fields of type `Span` or `MultiSpan`
+  --> $DIR/subdiagnostic-derive.rs:579:5
+   |
+LL |     #[suggestion_part()]
+   |     ^^^^^^^^^^^^^^^^^^^^
+
+error: specified multiple times
+  --> $DIR/subdiagnostic-derive.rs:587:37
+   |
+LL |     #[suggestion_part(code = "...", code = ",,,")]
+   |                                     ^^^^^^^^^^^^
+   |
+note: previously specified here
+  --> $DIR/subdiagnostic-derive.rs:587:23
+   |
+LL |     #[suggestion_part(code = "...", code = ",,,")]
+   |                       ^^^^^^^^^^^^
+
+error: specified multiple times
+  --> $DIR/subdiagnostic-derive.rs:617:5
+   |
+LL |     #[applicability]
+   |     ^^^^^^^^^^^^^^^^
+   |
+note: previously specified here
+  --> $DIR/subdiagnostic-derive.rs:614:43
+   |
+LL | #[multipart_suggestion(parser::add_paren, applicability = "machine-applicable")]
+   |                                           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: cannot find attribute `foo` in this scope
   --> $DIR/subdiagnostic-derive.rs:63:3
@@ -371,6 +463,6 @@ error[E0425]: cannot find value `slug` in module `rustc_errors::fluent`
 LL | #[label(slug)]
    |         ^^^^ not found in `rustc_errors::fluent`
 
-error: aborting due to 50 previous errors
+error: aborting due to 63 previous errors
 
 For more information about this error, try `rustc --explain E0425`.
diff --git a/src/test/ui/borrowck/do-not-suggest-adding-move-when-closure-is-already-marked-as-move.rs b/src/test/ui/borrowck/do-not-suggest-adding-move-when-closure-is-already-marked-as-move.rs
new file mode 100644 (file)
index 0000000..5244592
--- /dev/null
@@ -0,0 +1,8 @@
+fn main() {
+    let mut vec: Vec<i32> = Vec::new();
+    let closure = move || {
+        vec.clear();
+        let mut iter = vec.iter();
+        move || { iter.next() } //~ ERROR captured variable cannot escape `FnMut` closure bod
+    };
+}
diff --git a/src/test/ui/borrowck/do-not-suggest-adding-move-when-closure-is-already-marked-as-move.stderr b/src/test/ui/borrowck/do-not-suggest-adding-move-when-closure-is-already-marked-as-move.stderr
new file mode 100644 (file)
index 0000000..78ca090
--- /dev/null
@@ -0,0 +1,18 @@
+error: captured variable cannot escape `FnMut` closure body
+  --> $DIR/do-not-suggest-adding-move-when-closure-is-already-marked-as-move.rs:6:9
+   |
+LL |     let mut vec: Vec<i32> = Vec::new();
+   |         ------- variable defined here
+LL |     let closure = move || {
+   |                         - inferred to be a `FnMut` closure
+LL |         vec.clear();
+   |         --- variable captured here
+LL |         let mut iter = vec.iter();
+LL |         move || { iter.next() }
+   |         ^^^^^^^^^^^^^^^^^^^^^^^ returns a closure that contains a reference to a captured variable, which then escapes the closure body
+   |
+   = note: `FnMut` closures only have access to their captured variables while they are executing...
+   = note: ...therefore, they cannot allow references to captured variables to escape
+
+error: aborting due to previous error
+
diff --git a/src/test/ui/lint/let_underscore/let_underscore_drop.rs b/src/test/ui/lint/let_underscore/let_underscore_drop.rs
new file mode 100644 (file)
index 0000000..f298871
--- /dev/null
@@ -0,0 +1,14 @@
+// check-pass
+#![warn(let_underscore_drop)]
+
+struct NontrivialDrop;
+
+impl Drop for NontrivialDrop {
+    fn drop(&mut self) {
+        println!("Dropping!");
+    }
+}
+
+fn main() {
+    let _ = NontrivialDrop; //~WARNING non-binding let on a type that implements `Drop`
+}
diff --git a/src/test/ui/lint/let_underscore/let_underscore_drop.stderr b/src/test/ui/lint/let_underscore/let_underscore_drop.stderr
new file mode 100644 (file)
index 0000000..7b7de20
--- /dev/null
@@ -0,0 +1,22 @@
+warning: non-binding let on a type that implements `Drop`
+  --> $DIR/let_underscore_drop.rs:13:5
+   |
+LL |     let _ = NontrivialDrop;
+   |     ^^^^^^^^^^^^^^^^^^^^^^^
+   |
+note: the lint level is defined here
+  --> $DIR/let_underscore_drop.rs:2:9
+   |
+LL | #![warn(let_underscore_drop)]
+   |         ^^^^^^^^^^^^^^^^^^^
+help: consider binding to an unused variable to avoid immediately dropping the value
+   |
+LL |     let _unused = NontrivialDrop;
+   |         ~~~~~~~
+help: consider immediately dropping the value
+   |
+LL |     drop(NontrivialDrop);
+   |     ~~~~~              +
+
+warning: 1 warning emitted
+
diff --git a/src/test/ui/lint/let_underscore/let_underscore_lock.rs b/src/test/ui/lint/let_underscore/let_underscore_lock.rs
new file mode 100644 (file)
index 0000000..7423862
--- /dev/null
@@ -0,0 +1,7 @@
+// check-fail
+use std::sync::{Arc, Mutex};
+
+fn main() {
+    let data = Arc::new(Mutex::new(0));
+    let _ = data.lock().unwrap(); //~ERROR non-binding let on a synchronization lock
+}
diff --git a/src/test/ui/lint/let_underscore/let_underscore_lock.stderr b/src/test/ui/lint/let_underscore/let_underscore_lock.stderr
new file mode 100644 (file)
index 0000000..fb58af0
--- /dev/null
@@ -0,0 +1,20 @@
+error: non-binding let on a synchronization lock
+  --> $DIR/let_underscore_lock.rs:6:9
+   |
+LL |     let _ = data.lock().unwrap();
+   |         ^   ^^^^^^^^^^^^^^^^^^^^ this binding will immediately drop the value assigned to it
+   |         |
+   |         this lock is not assigned to a binding and is immediately dropped
+   |
+   = note: `#[deny(let_underscore_lock)]` on by default
+help: consider binding to an unused variable to avoid immediately dropping the value
+   |
+LL |     let _unused = data.lock().unwrap();
+   |         ~~~~~~~
+help: consider immediately dropping the value
+   |
+LL |     drop(data.lock().unwrap());
+   |     ~~~~~                    +
+
+error: aborting due to previous error
+
diff --git a/src/test/ui/mir/issue-99866.rs b/src/test/ui/mir/issue-99866.rs
new file mode 100644 (file)
index 0000000..d39ae6e
--- /dev/null
@@ -0,0 +1,25 @@
+// check-pass
+pub trait Backend {
+    type DescriptorSetLayout;
+}
+
+pub struct Back;
+
+impl Backend for Back {
+    type DescriptorSetLayout = u32;
+}
+
+pub struct HalSetLayouts {
+    vertex_layout: <Back as Backend>::DescriptorSetLayout,
+}
+
+impl HalSetLayouts {
+    pub fn iter<DSL>(self) -> DSL
+    where
+        Back: Backend<DescriptorSetLayout = DSL>,
+    {
+        self.vertex_layout
+    }
+}
+
+fn main() {}
diff --git a/src/test/ui/modules/auxiliary/dummy_lib.rs b/src/test/ui/modules/auxiliary/dummy_lib.rs
new file mode 100644 (file)
index 0000000..ef805c1
--- /dev/null
@@ -0,0 +1,2 @@
+#[allow(dead_code)]
+pub struct Dummy;
diff --git a/src/test/ui/modules/special_module_name.rs b/src/test/ui/modules/special_module_name.rs
new file mode 100644 (file)
index 0000000..15c59b2
--- /dev/null
@@ -0,0 +1,8 @@
+mod lib;
+//~^ WARN found module declaration for lib.rs
+//~| ERROR file not found for module `lib`
+mod main;
+//~^ WARN found module declaration for main.rs
+//~| ERROR file not found for module `main`
+
+fn main() {}
diff --git a/src/test/ui/modules/special_module_name.stderr b/src/test/ui/modules/special_module_name.stderr
new file mode 100644 (file)
index 0000000..8b3da29
--- /dev/null
@@ -0,0 +1,37 @@
+error[E0583]: file not found for module `lib`
+  --> $DIR/special_module_name.rs:1:1
+   |
+LL | mod lib;
+   | ^^^^^^^^
+   |
+   = help: to create the module `lib`, create file "$DIR/lib.rs" or "$DIR/lib/mod.rs"
+
+error[E0583]: file not found for module `main`
+  --> $DIR/special_module_name.rs:4:1
+   |
+LL | mod main;
+   | ^^^^^^^^^
+   |
+   = help: to create the module `main`, create file "$DIR/main.rs" or "$DIR/main/mod.rs"
+
+warning: found module declaration for lib.rs
+  --> $DIR/special_module_name.rs:1:1
+   |
+LL | mod lib;
+   | ^^^^^^^^
+   |
+   = note: `#[warn(special_module_name)]` on by default
+   = note: lib.rs is the root of this crate's library target
+   = help: to refer to it from other targets, use the library's name as the path
+
+warning: found module declaration for main.rs
+  --> $DIR/special_module_name.rs:4:1
+   |
+LL | mod main;
+   | ^^^^^^^^^
+   |
+   = note: a binary crate cannot be used as library
+
+error: aborting due to 2 previous errors; 2 warnings emitted
+
+For more information about this error, try `rustc --explain E0583`.
diff --git a/src/test/ui/modules/special_module_name_ignore.rs b/src/test/ui/modules/special_module_name_ignore.rs
new file mode 100644 (file)
index 0000000..07cea9b
--- /dev/null
@@ -0,0 +1,9 @@
+// run-pass
+
+#[path = "auxiliary/dummy_lib.rs"]
+mod lib;
+
+#[path = "auxiliary/dummy_lib.rs"]
+mod main;
+
+fn main() {}
diff --git a/src/test/ui/privacy/access_levels.rs b/src/test/ui/privacy/access_levels.rs
new file mode 100644 (file)
index 0000000..d51d2b5
--- /dev/null
@@ -0,0 +1,49 @@
+#![feature(rustc_attrs)]
+
+#[rustc_access_level] mod outer { //~ ERROR None
+    #[rustc_access_level] pub mod inner { //~ ERROR Some(Exported)
+        #[rustc_access_level]
+        extern "C" { //~ ERROR Some(Exported)
+            #[rustc_access_level] static a: u8; //~ ERROR None
+            #[rustc_access_level] pub fn b(); //~ ERROR Some(Exported)
+        }
+        #[rustc_access_level]
+        pub trait Trait { //~ ERROR Some(Exported)
+            #[rustc_access_level] const A: i32; //~ ERROR Some(Exported)
+            #[rustc_access_level] type B; //~ ERROR Some(Exported)
+        }
+
+        #[rustc_access_level]
+        pub struct Struct { //~ ERROR Some(Exported)
+            #[rustc_access_level] a: u8, //~ ERROR None
+            #[rustc_access_level] pub b: u8, //~ ERROR Some(Exported)
+        }
+
+        #[rustc_access_level]
+        pub union Union { //~ ERROR Some(Exported)
+            #[rustc_access_level] a: u8, //~ ERROR None
+            #[rustc_access_level] pub b: u8, //~ ERROR Some(Exported)
+        }
+
+        #[rustc_access_level]
+        pub enum Enum { //~ ERROR Some(Exported)
+            #[rustc_access_level] A( //~ ERROR Some(Exported)
+                #[rustc_access_level] Struct, //~ ERROR Some(Exported)
+                #[rustc_access_level] Union,  //~ ERROR Some(Exported)
+            ),
+        }
+    }
+
+    #[rustc_access_level] macro_rules! none_macro { //~ ERROR None
+        () => {};
+    }
+
+    #[macro_export]
+    #[rustc_access_level] macro_rules! public_macro { //~ ERROR Some(Public)
+        () => {};
+    }
+}
+
+pub use outer::inner;
+
+fn main() {}
diff --git a/src/test/ui/privacy/access_levels.stderr b/src/test/ui/privacy/access_levels.stderr
new file mode 100644 (file)
index 0000000..f326293
--- /dev/null
@@ -0,0 +1,125 @@
+error: None
+  --> $DIR/access_levels.rs:3:23
+   |
+LL | #[rustc_access_level] mod outer {
+   |                       ^^^^^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:4:27
+   |
+LL |     #[rustc_access_level] pub mod inner {
+   |                           ^^^^^^^^^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:6:9
+   |
+LL | /         extern "C" {
+LL | |             #[rustc_access_level] static a: u8;
+LL | |             #[rustc_access_level] pub fn b();
+LL | |         }
+   | |_________^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:11:9
+   |
+LL |         pub trait Trait {
+   |         ^^^^^^^^^^^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:17:9
+   |
+LL |         pub struct Struct {
+   |         ^^^^^^^^^^^^^^^^^
+
+error: None
+  --> $DIR/access_levels.rs:18:35
+   |
+LL |             #[rustc_access_level] a: u8,
+   |                                   ^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:19:35
+   |
+LL |             #[rustc_access_level] pub b: u8,
+   |                                   ^^^^^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:23:9
+   |
+LL |         pub union Union {
+   |         ^^^^^^^^^^^^^^^
+
+error: None
+  --> $DIR/access_levels.rs:24:35
+   |
+LL |             #[rustc_access_level] a: u8,
+   |                                   ^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:25:35
+   |
+LL |             #[rustc_access_level] pub b: u8,
+   |                                   ^^^^^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:29:9
+   |
+LL |         pub enum Enum {
+   |         ^^^^^^^^^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:30:35
+   |
+LL |             #[rustc_access_level] A(
+   |                                   ^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:31:39
+   |
+LL |                 #[rustc_access_level] Struct,
+   |                                       ^^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:32:39
+   |
+LL |                 #[rustc_access_level] Union,
+   |                                       ^^^^^
+
+error: None
+  --> $DIR/access_levels.rs:37:27
+   |
+LL |     #[rustc_access_level] macro_rules! none_macro {
+   |                           ^^^^^^^^^^^^^^^^^^^^^^^
+
+error: Some(Public)
+  --> $DIR/access_levels.rs:42:27
+   |
+LL |     #[rustc_access_level] macro_rules! public_macro {
+   |                           ^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:12:35
+   |
+LL |             #[rustc_access_level] const A: i32;
+   |                                   ^^^^^^^^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:13:35
+   |
+LL |             #[rustc_access_level] type B;
+   |                                   ^^^^^^
+
+error: None
+  --> $DIR/access_levels.rs:7:35
+   |
+LL |             #[rustc_access_level] static a: u8;
+   |                                   ^^^^^^^^^^^^
+
+error: Some(Exported)
+  --> $DIR/access_levels.rs:8:35
+   |
+LL |             #[rustc_access_level] pub fn b();
+   |                                   ^^^^^^^^^^
+
+error: aborting due to 20 previous errors
+
index b9fd852f742cf81360c0cb167683acde754b63eb..f4dac6e947e323e37c7c1996fb982061159d7c39 100644 (file)
@@ -4,7 +4,7 @@ version = "0.0.0"
 edition = "2021"
 
 [dependencies]
-rustdoc = { path = "../../librustdoc" }
+mdbook = { version = "0.4", default-features = false, features = ["search"] }
 
 [[bin]]
 name = "error_index_generator"
diff --git a/src/tools/error_index_generator/book_config.toml b/src/tools/error_index_generator/book_config.toml
new file mode 100644 (file)
index 0000000..885100a
--- /dev/null
@@ -0,0 +1,19 @@
+[book]
+title = "Error codes index"
+description = "Book listing all Rust error codes"
+src = ""
+
+[output.html]
+git-repository-url = "https://github.com/rust-lang/rust/"
+additional-css = ["error-index.css"]
+additional-js = ["error-index.js"]
+
+[output.html.search]
+enable = true
+limit-results = 20
+use-boolean-and = true
+boost-title = 2
+boost-hierarchy = 2
+boost-paragraph = 1
+expand = true
+heading-split-level = 0
diff --git a/src/tools/error_index_generator/error-index.css b/src/tools/error_index_generator/error-index.css
new file mode 100644 (file)
index 0000000..8975af8
--- /dev/null
@@ -0,0 +1,38 @@
+code.compile_fail {
+       border-left: 2px solid red;
+}
+
+pre .tooltip {
+       position: absolute;
+       left: -25px;
+       top: 0;
+       z-index: 1;
+       color: red;
+       cursor: pointer;
+}
+pre .tooltip::after {
+       display: none;
+       content: "This example deliberately fails to compile";
+       background-color: #000;
+       color: #fff;
+       border-color: #000;
+       text-align: center;
+       padding: 5px 3px 3px 3px;
+       border-radius: 6px;
+       margin-left: 5px;
+}
+pre .tooltip::before {
+       display: none;
+       border-color: transparent black transparent transparent;
+       content: " ";
+       position: absolute;
+       top: 50%;
+       left: 16px;
+       margin-top: -5px;
+       border-width: 5px;
+       border-style: solid;
+}
+
+pre .tooltip:hover::before, pre .tooltip:hover::after {
+       display: inline;
+}
diff --git a/src/tools/error_index_generator/error-index.js b/src/tools/error_index_generator/error-index.js
new file mode 100644 (file)
index 0000000..39b371b
--- /dev/null
@@ -0,0 +1,9 @@
+for (const elem of document.querySelectorAll("pre.playground")) {
+    if (elem.querySelector(".compile_fail") === null) {
+        continue;
+    }
+    const child = document.createElement("div");
+    child.className = "tooltip";
+    child.textContent = "ⓘ";
+    elem.appendChild(child);
+}
index 68c46700361a8da36dd766f53a69e5720760b6b9..1bde8e007826dffca053aa69474ecba3530ea68a 100644 (file)
@@ -1,20 +1,21 @@
 #![feature(rustc_private)]
 
 extern crate rustc_driver;
-extern crate rustc_span;
 
+// We use the function we generate from `register_diagnostics!`.
 use crate::error_codes::error_codes;
 
 use std::env;
 use std::error::Error;
-use std::fs::{create_dir_all, File};
+use std::fs::{self, File};
 use std::io::Write;
 use std::path::Path;
 use std::path::PathBuf;
 
-use rustc_span::edition::DEFAULT_EDITION;
+use std::str::FromStr;
 
-use rustdoc::html::markdown::{ErrorCodes, HeadingOffset, IdMap, Markdown, Playground};
+use mdbook::book::{parse_summary, BookItem, Chapter};
+use mdbook::{Config, MDBook};
 
 macro_rules! register_diagnostics {
     ($($error_code:ident: $message:expr,)+ ; $($undocumented:ident,)* ) => {
@@ -33,104 +34,21 @@ pub fn error_codes() -> Vec<(&'static str, Option<&'static str>)> {
 mod error_codes;
 
 enum OutputFormat {
-    HTML(HTMLFormatter),
+    HTML,
     Markdown,
     Unknown(String),
 }
 
 impl OutputFormat {
-    fn from(format: &str, resource_suffix: &str) -> OutputFormat {
+    fn from(format: &str) -> OutputFormat {
         match &*format.to_lowercase() {
-            "html" => OutputFormat::HTML(HTMLFormatter(resource_suffix.to_owned())),
+            "html" => OutputFormat::HTML,
             "markdown" => OutputFormat::Markdown,
             s => OutputFormat::Unknown(s.to_owned()),
         }
     }
 }
 
-struct HTMLFormatter(String);
-
-impl HTMLFormatter {
-    fn create_error_code_file(
-        &self,
-        err_code: &str,
-        explanation: &str,
-        parent_dir: &Path,
-    ) -> Result<(), Box<dyn Error>> {
-        let mut output_file = File::create(parent_dir.join(err_code).with_extension("html"))?;
-
-        self.header(&mut output_file, "../", "")?;
-        self.title(&mut output_file, &format!("Error code {}", err_code))?;
-
-        let mut id_map = IdMap::new();
-        let playground =
-            Playground { crate_name: None, url: String::from("https://play.rust-lang.org/") };
-        write!(
-            output_file,
-            "{}",
-            Markdown {
-                content: explanation,
-                links: &[],
-                ids: &mut id_map,
-                error_codes: ErrorCodes::Yes,
-                edition: DEFAULT_EDITION,
-                playground: &Some(playground),
-                heading_offset: HeadingOffset::H1,
-            }
-            .into_string()
-        )?;
-        write!(
-            output_file,
-            "<p>\
-                <a style='text-align: center;display: block;width: 100%;' \
-                   href='../error-index.html'>Back to list of error codes</a>\
-             </p>",
-        )?;
-
-        self.footer(&mut output_file)
-    }
-
-    fn header(
-        &self,
-        output: &mut dyn Write,
-        extra_path: &str,
-        extra: &str,
-    ) -> Result<(), Box<dyn Error>> {
-        write!(
-            output,
-            r##"<!DOCTYPE html>
-<html>
-<head>
-<title>Rust Compiler Error Index</title>
-<meta charset="utf-8">
-<!-- Include rust.css after light.css so its rules take priority. -->
-<link rel="stylesheet" type="text/css" href="{extra_path}rustdoc{suffix}.css"/>
-<link rel="stylesheet" type="text/css" href="{extra_path}light{suffix}.css"/>
-<link rel="stylesheet" type="text/css" href="{extra_path}rust.css"/>
-<style>
-.error-undescribed {{
-    display: none;
-}}
-</style>{extra}
-</head>
-<body>
-"##,
-            suffix = self.0,
-        )?;
-        Ok(())
-    }
-
-    fn title(&self, output: &mut dyn Write, title: &str) -> Result<(), Box<dyn Error>> {
-        write!(output, "<h1>{}</h1>\n", title)?;
-        Ok(())
-    }
-
-    fn footer(&self, output: &mut dyn Write) -> Result<(), Box<dyn Error>> {
-        write!(output, "</body></html>")?;
-        Ok(())
-    }
-}
-
 /// Output an HTML page for the errors in `err_map` to `output_path`.
 fn render_markdown(output_path: &Path) -> Result<(), Box<dyn Error>> {
     let mut output_file = File::create(output_path)?;
@@ -147,61 +65,119 @@ fn render_markdown(output_path: &Path) -> Result<(), Box<dyn Error>> {
     Ok(())
 }
 
-fn render_html(output_path: &Path, formatter: HTMLFormatter) -> Result<(), Box<dyn Error>> {
-    let mut output_file = File::create(output_path)?;
+// By default, mdbook doesn't consider code blocks as Rust ones contrary to rustdoc so we have
+// to manually add `rust` attribute whenever needed.
+fn add_rust_attribute_on_codeblock(explanation: &str) -> String {
+    // Very hacky way to add the rust attribute on all code blocks.
+    let mut skip = true;
+    explanation.split("\n```").fold(String::new(), |mut acc, part| {
+        if !acc.is_empty() {
+            acc.push_str("\n```");
+        }
+        if !skip {
+            if let Some(attrs) = part.split('\n').next() {
+                if !attrs.contains("rust")
+                    && (attrs.is_empty()
+                        || attrs.contains("compile_fail")
+                        || attrs.contains("ignore")
+                        || attrs.contains("edition"))
+                {
+                    if !attrs.is_empty() {
+                        acc.push_str("rust,");
+                    } else {
+                        acc.push_str("rust");
+                    }
+                }
+            }
+        }
+        skip = !skip;
+        acc.push_str(part);
+        acc
+    })
+}
 
-    let error_codes_dir = "error_codes";
+fn render_html(output_path: &Path) -> Result<(), Box<dyn Error>> {
+    let mut introduction = format!(
+        "<script src='redirect.js'></script>
+# Rust error codes index
 
-    let parent = output_path.parent().expect("There should have a parent").join(error_codes_dir);
+This page lists all the error codes emitted by the Rust compiler.
 
-    if !parent.exists() {
-        create_dir_all(&parent)?;
-    }
+"
+    );
 
-    formatter.header(
-        &mut output_file,
-        "",
-        &format!(
-            r#"<script>(function() {{
-    if (window.location.hash) {{
-        let code = window.location.hash.replace(/^#/, '');
-        // We have to make sure this pattern matches to avoid inadvertently creating an
-        // open redirect.
-        if (/^E[0-9]+$/.test(code)) {{
-            window.location = './{error_codes_dir}/' + code + '.html';
-        }}
-    }}
-}})()</script>"#
-        ),
-    )?;
-    formatter.title(&mut output_file, "Rust Compiler Error Index")?;
+    let err_codes = error_codes();
+    let mut chapters = Vec::with_capacity(err_codes.len());
 
-    write!(
-        output_file,
-        "<p>This page lists all the error codes emitted by the Rust compiler. If you want a full \
-            explanation on an error code, click on it.</p>\
-         <ul>",
-    )?;
-    for (err_code, explanation) in error_codes().iter() {
+    for (err_code, explanation) in err_codes.iter() {
         if let Some(explanation) = explanation {
-            write!(
-                output_file,
-                "<li><a href='./{0}/{1}.html'>{1}</a></li>",
-                error_codes_dir, err_code
-            )?;
-            formatter.create_error_code_file(err_code, explanation, &parent)?;
+            introduction.push_str(&format!(" * [{0}](./{0}.html)\n", err_code));
+
+            let content = add_rust_attribute_on_codeblock(explanation);
+            chapters.push(BookItem::Chapter(Chapter {
+                name: err_code.to_string(),
+                content: format!("# Error code {}\n\n{}\n", err_code, content),
+                number: None,
+                sub_items: Vec::new(),
+                // We generate it into the `error_codes` folder.
+                path: Some(PathBuf::from(&format!("{}.html", err_code))),
+                source_path: None,
+                parent_names: Vec::new(),
+            }));
         } else {
-            write!(output_file, "<li>{}</li>", err_code)?;
+            introduction.push_str(&format!(" * {}\n", err_code));
         }
     }
-    write!(output_file, "</ul>")?;
-    formatter.footer(&mut output_file)
+
+    let mut config = Config::from_str(include_str!("book_config.toml"))?;
+    config.build.build_dir = output_path.join("error_codes").to_path_buf();
+    let mut book = MDBook::load_with_config_and_summary(
+        env!("CARGO_MANIFEST_DIR"),
+        config,
+        parse_summary("")?,
+    )?;
+    let chapter = Chapter {
+        name: "Rust error codes index".to_owned(),
+        content: introduction,
+        number: None,
+        sub_items: chapters,
+        // Very important: this file is named as `error-index.html` and not `index.html`!
+        path: Some(PathBuf::from("error-index.html")),
+        source_path: None,
+        parent_names: Vec::new(),
+    };
+    book.book.sections.push(BookItem::Chapter(chapter));
+    book.build()?;
+
+    // We can't put this content into another file, otherwise `mbdbook` will also put it into the
+    // output directory, making a duplicate.
+    fs::write(
+        output_path.join("error-index.html"),
+        r#"<!DOCTYPE html>
+<html>
+    <head>
+        <title>Rust error codes index - Error codes index</title>
+        <meta content="text/html; charset=utf-8" http-equiv="Content-Type">
+        <meta name="description" content="Book listing all Rust error codes">
+        <script src="error_codes/redirect.js"></script>
+    </head>
+    <body>
+        <div>If you are not automatically redirected to the error code index, please <a id="index-link" href="./error_codes/error-index.html">here</a>.
+        <script>document.getElementById("index-link").click()</script>
+    </body>
+</html>"#,
+    )?;
+
+    // No need for a 404 file, it's already handled by the server.
+    fs::remove_file(output_path.join("error_codes/404.html"))?;
+
+    Ok(())
 }
 
 fn main_with_result(format: OutputFormat, dst: &Path) -> Result<(), Box<dyn Error>> {
     match format {
         OutputFormat::Unknown(s) => panic!("Unknown output format: {}", s),
-        OutputFormat::HTML(h) => render_html(dst, h),
+        OutputFormat::HTML => render_html(dst),
         OutputFormat::Markdown => render_markdown(dst),
     }
 }
@@ -210,12 +186,9 @@ fn parse_args() -> (OutputFormat, PathBuf) {
     let mut args = env::args().skip(1);
     let format = args.next();
     let dst = args.next();
-    let resource_suffix = args.next().unwrap_or_else(String::new);
-    let format = format
-        .map(|a| OutputFormat::from(&a, &resource_suffix))
-        .unwrap_or(OutputFormat::from("html", &resource_suffix));
+    let format = format.map(|a| OutputFormat::from(&a)).unwrap_or(OutputFormat::from("html"));
     let dst = dst.map(PathBuf::from).unwrap_or_else(|| match format {
-        OutputFormat::HTML(..) => PathBuf::from("doc/error-index.html"),
+        OutputFormat::HTML => PathBuf::from("doc"),
         OutputFormat::Markdown => PathBuf::from("doc/error-index.md"),
         OutputFormat::Unknown(..) => PathBuf::from("<nul>"),
     });
@@ -225,9 +198,8 @@ fn parse_args() -> (OutputFormat, PathBuf) {
 fn main() {
     rustc_driver::init_env_logger("RUST_LOG");
     let (format, dst) = parse_args();
-    let result =
-        rustc_span::create_default_session_globals_then(move || main_with_result(format, &dst));
+    let result = main_with_result(format, &dst);
     if let Err(e) = result {
-        panic!("{}", e.to_string());
+        panic!("{:?}", e);
     }
 }
diff --git a/src/tools/error_index_generator/redirect.js b/src/tools/error_index_generator/redirect.js
new file mode 100644 (file)
index 0000000..8c907f5
--- /dev/null
@@ -0,0 +1,16 @@
+(function() {
+    if (window.location.hash) {
+        let code = window.location.hash.replace(/^#/, '');
+        // We have to make sure this pattern matches to avoid inadvertently creating an
+        // open redirect.
+        if (!/^E[0-9]+$/.test(code)) {
+            return;
+        }
+        if (window.location.pathname.indexOf("/error_codes/") !== -1) {
+            // We're not at the top level, so we don't prepend with "./error_codes/".
+            window.location = './' + code + '.html';
+        } else {
+            window.location = './error_codes/' + code + '.html';
+        }
+    }
+})()
index 9696e35b7963f8a42f880c78f11ecb015a168e76..2a923a61b0a70b74a78127746059ff568d470386 100644 (file)
@@ -8,6 +8,7 @@
 /// Descriptions of rustc lint groups.
 static GROUP_DESCRIPTIONS: &[(&str, &str)] = &[
     ("unused", "Lints that detect things being declared but not used, or excess syntax"),
+    ("let-underscore", "Lints that detect wildcard let bindings that are likely to be invalid"),
     ("rustdoc", "Rustdoc-specific lints"),
     ("rust-2018-idioms", "Lints to nudge you toward idiomatic features of Rust 2018"),
     ("nonstandard-style", "Violation of standard naming conventions"),
index 90bd24a75e0649d82863c41536a532267e96bac0..1795f3d7fe5bc5a3a0a9b908f333681274971dbb 100644 (file)
@@ -8,8 +8,8 @@
 //! make gcc/clang pass `-flavor <flavor>` as the first two arguments in the linker invocation
 //! and since Windows does not support symbolic links for files this wrapper is used in place of a
 //! symbolic link. It execs `../rust-lld -flavor <flavor>` by propagating the flavor argument
-//! passed to the wrapper as the first two arguments. On Windows it spawns a `..\rust-lld.exe`
-//! child process.
+//! obtained from the wrapper's name as the first two arguments.
+//! On Windows it spawns a `..\rust-lld.exe` child process.
 
 use std::fmt::Display;
 use std::path::{Path, PathBuf};
@@ -53,29 +53,32 @@ fn get_rust_lld_path(current_exe_path: &Path) -> PathBuf {
     rust_lld_path
 }
 
+/// Extract LLD flavor name from the lld-wrapper executable name.
+fn get_lld_flavor(current_exe_path: &Path) -> Result<&'static str, String> {
+    let stem = current_exe_path.file_stem();
+    Ok(match stem.and_then(|s| s.to_str()) {
+        Some("ld.lld") => "gnu",
+        Some("ld64.lld") => "darwin",
+        Some("lld-link") => "link",
+        Some("wasm-ld") => "wasm",
+        _ => return Err(format!("{:?}", stem)),
+    })
+}
+
 /// Returns the command for invoking rust-lld with the correct flavor.
-/// LLD only accepts the flavor argument at the first two arguments, so move it there.
+/// LLD only accepts the flavor argument at the first two arguments, so pass it there.
 ///
 /// Exits on error.
 fn get_rust_lld_command(current_exe_path: &Path) -> process::Command {
     let rust_lld_path = get_rust_lld_path(current_exe_path);
     let mut command = process::Command::new(rust_lld_path);
 
-    let mut flavor = None;
-    let args = env::args_os()
-        .skip(1)
-        .filter(|arg| match arg.to_str().and_then(|s| s.strip_prefix("-rustc-lld-flavor=")) {
-            Some(suffix) => {
-                flavor = Some(suffix.to_string());
-                false
-            }
-            None => true,
-        })
-        .collect::<Vec<_>>();
+    let flavor =
+        get_lld_flavor(current_exe_path).unwrap_or_exit_with("executable has unexpected name");
 
     command.arg("-flavor");
-    command.arg(flavor.unwrap_or_exit_with("-rustc-lld-flavor=<flavor> is not passed"));
-    command.args(args);
+    command.arg(flavor);
+    command.args(env::args_os().skip(1));
     command
 }
 
index ab88e64b152d3704c35db96dbbc6efaaed67773f..8c8b479be723fb103b0b1203faf9246a3f587250 160000 (submodule)
@@ -1 +1 @@
-Subproject commit ab88e64b152d3704c35db96dbbc6efaaed67773f
+Subproject commit 8c8b479be723fb103b0b1203faf9246a3f587250
index 8a90bc0e3c143c91f8d9ca8c2cc87e396da1ef11..89d1574726f090597e9a130fa3c1ebfa935857f5 100644 (file)
@@ -195,6 +195,13 @@ trigger_files = [
     "compiler/rustc_macros/src/diagnostics"
 ]
 
+[autolabel."A-query-system"]
+trigger_files = [
+    "compiler/rustc_query_system",
+    "compiler/rustc_query_impl",
+    "compiler/rustc_macros/src/query.rs"
+]
+
 [notify-zulip."I-prioritize"]
 zulip_stream = 245100 # #t-compiler/wg-prioritization/alerts
 topic = "#{number} {title}"