]> git.lizzy.rs Git - rust.git/commitdiff
Rollup merge of #107413 - tshepang:pleasant-readin, r=Nilstrieb
authorMatthias Krüger <matthias.krueger@famsik.de>
Sun, 29 Jan 2023 05:14:19 +0000 (06:14 +0100)
committerGitHub <noreply@github.com>
Sun, 29 Jan 2023 05:14:19 +0000 (06:14 +0100)
make more pleasant to read

165 files changed:
compiler/rustc_ast_lowering/src/index.rs
compiler/rustc_ast_lowering/src/item.rs
compiler/rustc_ast_lowering/src/lib.rs
compiler/rustc_builtin_macros/src/deriving/cmp/partial_ord.rs
compiler/rustc_codegen_ssa/src/mir/analyze.rs
compiler/rustc_error_messages/locales/en-US/codegen_gcc.ftl
compiler/rustc_error_messages/locales/en-US/codegen_ssa.ftl
compiler/rustc_hir/src/hir.rs
compiler/rustc_hir/src/intravisit.rs
compiler/rustc_hir/src/stable_hash_impls.rs
compiler/rustc_hir_analysis/src/check/check.rs
compiler/rustc_hir_analysis/src/check/intrinsicck.rs
compiler/rustc_hir_analysis/src/check/wfcheck.rs
compiler/rustc_hir_analysis/src/collect/lifetimes.rs
compiler/rustc_hir_analysis/src/collect/predicates_of.rs
compiler/rustc_hir_analysis/src/collect/type_of.rs
compiler/rustc_hir_typeck/src/_match.rs
compiler/rustc_hir_typeck/src/check.rs
compiler/rustc_hir_typeck/src/fn_ctxt/_impl.rs
compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs
compiler/rustc_hir_typeck/src/gather_locals.rs
compiler/rustc_hir_typeck/src/inherited.rs
compiler/rustc_hir_typeck/src/writeback.rs
compiler/rustc_incremental/src/assert_dep_graph.rs
compiler/rustc_infer/src/infer/canonical/mod.rs
compiler/rustc_infer/src/infer/canonical/query_response.rs
compiler/rustc_infer/src/infer/canonical/substitute.rs
compiler/rustc_infer/src/infer/combine.rs
compiler/rustc_lint/src/builtin.rs
compiler/rustc_lint/src/late.rs
compiler/rustc_lint/src/nonstandard_style.rs
compiler/rustc_lint/src/passes.rs
compiler/rustc_lint/src/types.rs
compiler/rustc_macros/src/diagnostics/fluent.rs
compiler/rustc_metadata/src/rmeta/encoder.rs
compiler/rustc_middle/src/arena.rs
compiler/rustc_middle/src/hir/map/mod.rs
compiler/rustc_middle/src/infer/canonical.rs
compiler/rustc_middle/src/mir/mod.rs
compiler/rustc_middle/src/mir/spanview.rs
compiler/rustc_middle/src/query/mod.rs
compiler/rustc_middle/src/ty/context.rs
compiler/rustc_middle/src/ty/mod.rs
compiler/rustc_middle/src/ty/query.rs
compiler/rustc_mir_build/src/thir/pattern/const_to_pat.rs
compiler/rustc_mir_transform/src/check_unsafety.rs
compiler/rustc_mir_transform/src/coverage/mod.rs
compiler/rustc_mir_transform/src/generator.rs
compiler/rustc_mir_transform/src/lib.rs
compiler/rustc_parse/src/lexer/diagnostics.rs [new file with mode: 0644]
compiler/rustc_parse/src/lexer/mod.rs
compiler/rustc_parse/src/lexer/tokentrees.rs
compiler/rustc_passes/src/check_attr.rs
compiler/rustc_passes/src/dead.rs
compiler/rustc_passes/src/hir_stats.rs
compiler/rustc_passes/src/lang_items.rs
compiler/rustc_passes/src/stability.rs
compiler/rustc_privacy/src/lib.rs
compiler/rustc_save_analysis/src/dump_visitor.rs
compiler/rustc_save_analysis/src/lib.rs
compiler/rustc_save_analysis/src/sig.rs
compiler/rustc_trait_selection/src/solve/assembly.rs
compiler/rustc_trait_selection/src/solve/mod.rs
compiler/rustc_trait_selection/src/solve/project_goals.rs
compiler/rustc_trait_selection/src/solve/search_graph/cache.rs
compiler/rustc_trait_selection/src/solve/trait_goals.rs
compiler/rustc_trait_selection/src/traits/error_reporting/suggestions.rs
compiler/rustc_traits/src/chalk/mod.rs
library/core/src/iter/adapters/filter_map.rs
library/core/src/iter/adapters/flatten.rs
library/core/src/iter/traits/double_ended.rs
library/core/src/iter/traits/iterator.rs
library/core/src/ops/control_flow.rs
library/std/src/fs/tests.rs
library/std/src/lib.rs
library/std/src/net/socket_addr.rs
library/std/src/os/net/mod.rs
library/std/src/personality/emcc.rs
library/std/src/personality/gcc.rs
library/std/src/sys/common/alloc.rs
library/std/src/sys/windows/thread_parking.rs
library/std/src/sys_common/net.rs
src/bootstrap/lib.rs
src/librustdoc/clean/mod.rs
src/librustdoc/html/length_limit.rs
src/librustdoc/html/length_limit/tests.rs
src/librustdoc/html/markdown.rs
src/librustdoc/html/static/js/main.js
src/librustdoc/html/templates/print_item.html
src/librustdoc/lib.rs
src/tools/clippy/clippy_lints/src/booleans.rs
src/tools/clippy/clippy_lints/src/cognitive_complexity.rs
src/tools/clippy/clippy_lints/src/dereference.rs
src/tools/clippy/clippy_lints/src/derive.rs
src/tools/clippy/clippy_lints/src/doc.rs
src/tools/clippy/clippy_lints/src/escape.rs
src/tools/clippy/clippy_lints/src/excessive_bools.rs
src/tools/clippy/clippy_lints/src/exhaustive_items.rs
src/tools/clippy/clippy_lints/src/functions/misnamed_getters.rs
src/tools/clippy/clippy_lints/src/functions/mod.rs
src/tools/clippy/clippy_lints/src/functions/must_use.rs
src/tools/clippy/clippy_lints/src/functions/not_unsafe_ptr_arg_deref.rs
src/tools/clippy/clippy_lints/src/future_not_send.rs
src/tools/clippy/clippy_lints/src/implicit_return.rs
src/tools/clippy/clippy_lints/src/inherent_to_string.rs
src/tools/clippy/clippy_lints/src/lib.rs
src/tools/clippy/clippy_lints/src/lifetimes.rs
src/tools/clippy/clippy_lints/src/manual_async_fn.rs
src/tools/clippy/clippy_lints/src/manual_non_exhaustive.rs
src/tools/clippy/clippy_lints/src/methods/collapsible_str_replace.rs
src/tools/clippy/clippy_lints/src/methods/mod.rs
src/tools/clippy/clippy_lints/src/methods/suspicious_map.rs
src/tools/clippy/clippy_lints/src/methods/unnecessary_to_owned.rs
src/tools/clippy/clippy_lints/src/misc.rs
src/tools/clippy/clippy_lints/src/missing_const_for_fn.rs
src/tools/clippy/clippy_lints/src/mut_key.rs
src/tools/clippy/clippy_lints/src/needless_pass_by_value.rs
src/tools/clippy/clippy_lints/src/new_without_default.rs
src/tools/clippy/clippy_lints/src/operators/arithmetic_side_effects.rs
src/tools/clippy/clippy_lints/src/operators/numeric_arithmetic.rs
src/tools/clippy/clippy_lints/src/panic_in_result_fn.rs
src/tools/clippy/clippy_lints/src/pass_by_ref_or_value.rs
src/tools/clippy/clippy_lints/src/pattern_type_mismatch.rs
src/tools/clippy/clippy_lints/src/redundant_clone.rs
src/tools/clippy/clippy_lints/src/return_self_not_must_use.rs
src/tools/clippy/clippy_lints/src/returns.rs
src/tools/clippy/clippy_lints/src/self_named_constructors.rs
src/tools/clippy/clippy_lints/src/trailing_empty_array.rs
src/tools/clippy/clippy_lints/src/types/mod.rs
src/tools/clippy/clippy_lints/src/unnecessary_wraps.rs
src/tools/clippy/clippy_lints/src/unused_async.rs
src/tools/clippy/clippy_lints/src/unwrap.rs
src/tools/clippy/clippy_lints/src/unwrap_in_result.rs
src/tools/clippy/clippy_utils/src/lib.rs
src/tools/clippy/clippy_utils/src/macros.rs
src/tools/clippy/clippy_utils/src/mir/possible_borrower.rs
src/tools/clippy/clippy_utils/src/sugg.rs
tests/ui-fulldeps/auxiliary/issue-40001-plugin.rs
tests/ui-fulldeps/fluent-messages/missing-message-ref.ftl [new file with mode: 0644]
tests/ui-fulldeps/fluent-messages/test.rs
tests/ui-fulldeps/fluent-messages/test.stderr
tests/ui/deriving/deriving-all-codegen.stdout
tests/ui/mir/mir_codegen_ssa.rs [new file with mode: 0644]
tests/ui/parser/deli-ident-issue-1.rs [new file with mode: 0644]
tests/ui/parser/deli-ident-issue-1.stderr [new file with mode: 0644]
tests/ui/parser/deli-ident-issue-2.rs [new file with mode: 0644]
tests/ui/parser/deli-ident-issue-2.stderr [new file with mode: 0644]
tests/ui/parser/issue-68987-unmatch-issue-1.rs [new file with mode: 0644]
tests/ui/parser/issue-68987-unmatch-issue-1.stderr [new file with mode: 0644]
tests/ui/parser/issue-68987-unmatch-issue-2.rs [new file with mode: 0644]
tests/ui/parser/issue-68987-unmatch-issue-2.stderr [new file with mode: 0644]
tests/ui/parser/issue-68987-unmatch-issue-3.rs [new file with mode: 0644]
tests/ui/parser/issue-68987-unmatch-issue-3.stderr [new file with mode: 0644]
tests/ui/parser/issue-68987-unmatch-issue.rs [new file with mode: 0644]
tests/ui/parser/issue-68987-unmatch-issue.stderr [new file with mode: 0644]
tests/ui/parser/issue-81827.stderr
tests/ui/parser/issues/issue-62973.stderr
tests/ui/parser/issues/issue-63116.stderr
tests/ui/parser/issues/issue-69259.rs [new file with mode: 0644]
tests/ui/parser/issues/issue-69259.stderr [new file with mode: 0644]
tests/ui/parser/issues/issue-70583-block-is-empty-1.stderr
tests/ui/parser/issues/issue-70583-block-is-empty-2.stderr
tests/ui/parser/macro-mismatched-delim-paren-brace.stderr
tests/ui/traits/alias/issue-60755.rs [new file with mode: 0644]
tests/ui/typeck/issue-91334.stderr

index 63033085bec674de5bbc4159cf980c8f5a5ed289..f7fe0d771a13c495cf7f14e77ee9363beba686df 100644 (file)
@@ -275,19 +275,6 @@ fn visit_trait_ref(&mut self, tr: &'hir TraitRef<'hir>) {
         });
     }
 
-    fn visit_fn(
-        &mut self,
-        fk: intravisit::FnKind<'hir>,
-        fd: &'hir FnDecl<'hir>,
-        b: BodyId,
-        _: Span,
-        id: HirId,
-    ) {
-        assert_eq!(self.owner, id.owner);
-        assert_eq!(self.parent_node, id.local_id);
-        intravisit::walk_fn(self, fk, fd, b, id);
-    }
-
     fn visit_block(&mut self, block: &'hir Block<'hir>) {
         self.insert(block.span, block.hir_id, Node::Block(block));
         self.with_parent(block.hir_id, |this| {
index 5d2589cb2b2f7817a8603a1319eed39a727fd597..2865082bd7a47c5322019389fa660118b1a99cc9 100644 (file)
@@ -67,7 +67,6 @@ fn with_lctx(
             current_hir_id_owner: hir::CRATE_OWNER_ID,
             item_local_id_counter: hir::ItemLocalId::new(0),
             node_id_to_local_id: Default::default(),
-            local_id_to_def_id: SortedMap::new(),
             trait_map: Default::default(),
 
             // Lowering state.
index 35849a6b944e481591f8a451646bba6dfd7c0afe..a04a259529310959009d81dec2ca644f71548d31 100644 (file)
@@ -119,7 +119,6 @@ struct LoweringContext<'a, 'hir> {
 
     current_hir_id_owner: hir::OwnerId,
     item_local_id_counter: hir::ItemLocalId,
-    local_id_to_def_id: SortedMap<ItemLocalId, LocalDefId>,
     trait_map: FxHashMap<ItemLocalId, Box<[TraitCandidate]>>,
 
     impl_trait_defs: Vec<hir::GenericParam<'hir>>,
@@ -567,7 +566,6 @@ fn with_hir_id_owner(
         let current_attrs = std::mem::take(&mut self.attrs);
         let current_bodies = std::mem::take(&mut self.bodies);
         let current_node_ids = std::mem::take(&mut self.node_id_to_local_id);
-        let current_id_to_def_id = std::mem::take(&mut self.local_id_to_def_id);
         let current_trait_map = std::mem::take(&mut self.trait_map);
         let current_owner =
             std::mem::replace(&mut self.current_hir_id_owner, hir::OwnerId { def_id });
@@ -594,7 +592,6 @@ fn with_hir_id_owner(
         self.attrs = current_attrs;
         self.bodies = current_bodies;
         self.node_id_to_local_id = current_node_ids;
-        self.local_id_to_def_id = current_id_to_def_id;
         self.trait_map = current_trait_map;
         self.current_hir_id_owner = current_owner;
         self.item_local_id_counter = current_local_counter;
@@ -629,7 +626,6 @@ fn with_remapping<R>(
     fn make_owner_info(&mut self, node: hir::OwnerNode<'hir>) -> &'hir hir::OwnerInfo<'hir> {
         let attrs = std::mem::take(&mut self.attrs);
         let mut bodies = std::mem::take(&mut self.bodies);
-        let local_id_to_def_id = std::mem::take(&mut self.local_id_to_def_id);
         let trait_map = std::mem::take(&mut self.trait_map);
 
         #[cfg(debug_assertions)]
@@ -645,13 +641,7 @@ fn make_owner_info(&mut self, node: hir::OwnerNode<'hir>) -> &'hir hir::OwnerInf
         let (hash_including_bodies, hash_without_bodies) = self.hash_owner(node, &bodies);
         let (nodes, parenting) =
             index::index_hir(self.tcx.sess, &*self.tcx.definitions_untracked(), node, &bodies);
-        let nodes = hir::OwnerNodes {
-            hash_including_bodies,
-            hash_without_bodies,
-            nodes,
-            bodies,
-            local_id_to_def_id,
-        };
+        let nodes = hir::OwnerNodes { hash_including_bodies, hash_without_bodies, nodes, bodies };
         let attrs = {
             let hash = self.tcx.with_stable_hashing_context(|mut hcx| {
                 let mut stable_hasher = StableHasher::new();
@@ -710,7 +700,6 @@ fn lower_node_id(&mut self, ast_node_id: NodeId) -> hir::HirId {
                 assert_ne!(local_id, hir::ItemLocalId::new(0));
                 if let Some(def_id) = self.opt_local_def_id(ast_node_id) {
                     self.children.push((def_id, hir::MaybeOwner::NonOwner(hir_id)));
-                    self.local_id_to_def_id.insert(local_id, def_id);
                 }
 
                 if let Some(traits) = self.resolver.trait_map.remove(&ast_node_id) {
index c9dc89212622d70d7d6ddc2bdbfac0093a7bf263..2fc30d8e05f2c6748c4e03ed0a07d056105e3439 100644 (file)
@@ -1,7 +1,7 @@
 use crate::deriving::generic::ty::*;
 use crate::deriving::generic::*;
 use crate::deriving::{path_std, pathvec_std};
-use rustc_ast::MetaItem;
+use rustc_ast::{ExprKind, ItemKind, MetaItem, PatKind};
 use rustc_expand::base::{Annotatable, ExtCtxt};
 use rustc_span::symbol::{sym, Ident};
 use rustc_span::Span;
@@ -21,6 +21,27 @@ pub fn expand_deriving_partial_ord(
 
     let attrs = thin_vec![cx.attr_word(sym::inline, span)];
 
+    // Order in which to perform matching
+    let tag_then_data = if let Annotatable::Item(item) = item
+        && let ItemKind::Enum(def, _) = &item.kind {
+            let dataful: Vec<bool> = def.variants.iter().map(|v| !v.data.fields().is_empty()).collect();
+            match dataful.iter().filter(|&&b| b).count() {
+                // No data, placing the tag check first makes codegen simpler
+                0 => true,
+                1..=2 => false,
+                _ => {
+                    (0..dataful.len()-1).any(|i| {
+                        if dataful[i] && let Some(idx) = dataful[i+1..].iter().position(|v| *v) {
+                            idx >= 2
+                        } else {
+                            false
+                        }
+                    })
+                }
+            }
+        } else {
+            true
+        };
     let partial_cmp_def = MethodDef {
         name: sym::partial_cmp,
         generics: Bounds::empty(),
@@ -30,7 +51,7 @@ pub fn expand_deriving_partial_ord(
         attributes: attrs,
         fieldless_variants_strategy: FieldlessVariantsStrategy::Unify,
         combine_substructure: combine_substructure(Box::new(|cx, span, substr| {
-            cs_partial_cmp(cx, span, substr)
+            cs_partial_cmp(cx, span, substr, tag_then_data)
         })),
     };
 
@@ -47,7 +68,12 @@ pub fn expand_deriving_partial_ord(
     trait_def.expand(cx, mitem, item, push)
 }
 
-pub fn cs_partial_cmp(cx: &mut ExtCtxt<'_>, span: Span, substr: &Substructure<'_>) -> BlockOrExpr {
+fn cs_partial_cmp(
+    cx: &mut ExtCtxt<'_>,
+    span: Span,
+    substr: &Substructure<'_>,
+    tag_then_data: bool,
+) -> BlockOrExpr {
     let test_id = Ident::new(sym::cmp, span);
     let equal_path = cx.path_global(span, cx.std_path(&[sym::cmp, sym::Ordering, sym::Equal]));
     let partial_cmp_path = cx.std_path(&[sym::cmp, sym::PartialOrd, sym::partial_cmp]);
@@ -74,12 +100,50 @@ pub fn cs_partial_cmp(cx: &mut ExtCtxt<'_>, span: Span, substr: &Substructure<'_
                 let args = vec![field.self_expr.clone(), other_expr.clone()];
                 cx.expr_call_global(field.span, partial_cmp_path.clone(), args)
             }
-            CsFold::Combine(span, expr1, expr2) => {
-                let eq_arm =
-                    cx.arm(span, cx.pat_some(span, cx.pat_path(span, equal_path.clone())), expr1);
-                let neq_arm =
-                    cx.arm(span, cx.pat_ident(span, test_id), cx.expr_ident(span, test_id));
-                cx.expr_match(span, expr2, vec![eq_arm, neq_arm])
+            CsFold::Combine(span, mut expr1, expr2) => {
+                // When the item is an enum, this expands to
+                // ```
+                // match (expr2) {
+                //     Some(Ordering::Equal) => expr1,
+                //     cmp => cmp
+                // }
+                // ```
+                // where `expr2` is `partial_cmp(self_tag, other_tag)`, and `expr1` is a `match`
+                //  against the enum variants. This means that we begin by comparing the enum tags,
+                // before either inspecting their contents (if they match), or returning
+                // the `cmp::Ordering` of comparing the enum tags.
+                // ```
+                // match partial_cmp(self_tag, other_tag) {
+                //     Some(Ordering::Equal) => match (self, other)  {
+                //         (Self::A(self_0), Self::A(other_0)) => partial_cmp(self_0, other_0),
+                //         (Self::B(self_0), Self::B(other_0)) => partial_cmp(self_0, other_0),
+                //         _ => Some(Ordering::Equal)
+                //     }
+                //     cmp => cmp
+                // }
+                // ```
+                // If we have any certain enum layouts, flipping this results in better codegen
+                // ```
+                // match (self, other) {
+                //     (Self::A(self_0), Self::A(other_0)) => partial_cmp(self_0, other_0),
+                //     _ => partial_cmp(self_tag, other_tag)
+                // }
+                // ```
+                // Reference: https://github.com/rust-lang/rust/pull/103659#issuecomment-1328126354
+
+                if !tag_then_data
+                    && let ExprKind::Match(_, arms) = &mut expr1.kind
+                    && let Some(last) = arms.last_mut()
+                    && let PatKind::Wild = last.pat.kind {
+                        last.body = expr2;
+                        expr1
+                } else {
+                    let eq_arm =
+                        cx.arm(span, cx.pat_some(span, cx.pat_path(span, equal_path.clone())), expr1);
+                    let neq_arm =
+                        cx.arm(span, cx.pat_ident(span, test_id), cx.expr_ident(span, test_id));
+                    cx.expr_match(span, expr2, vec![eq_arm, neq_arm])
+                }
             }
             CsFold::Fieldless => cx.expr_some(span, cx.expr_path(equal_path.clone())),
         },
index dd1ac2c74aed4fe2d628ffc17958f407a3a0a461..95aad10fdb0f9852505cd08ebffa88f6f62ac7c2 100644 (file)
@@ -36,7 +36,7 @@ pub fn non_ssa_locals<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(
 
     // Arguments get assigned to by means of the function being called
     for arg in mir.args_iter() {
-        analyzer.assign(arg, mir::START_BLOCK.start_location());
+        analyzer.assign(arg, DefLocation::Argument);
     }
 
     // If there exists a local definition that dominates all uses of that local,
@@ -64,7 +64,22 @@ enum LocalKind {
     /// A scalar or a scalar pair local that is neither defined nor used.
     Unused,
     /// A scalar or a scalar pair local with a single definition that dominates all uses.
-    SSA(mir::Location),
+    SSA(DefLocation),
+}
+
+#[derive(Copy, Clone, PartialEq, Eq)]
+enum DefLocation {
+    Argument,
+    Body(Location),
+}
+
+impl DefLocation {
+    fn dominates(self, location: Location, dominators: &Dominators<mir::BasicBlock>) -> bool {
+        match self {
+            DefLocation::Argument => true,
+            DefLocation::Body(def) => def.successor_within_block().dominates(location, dominators),
+        }
+    }
 }
 
 struct LocalAnalyzer<'mir, 'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> {
@@ -74,17 +89,13 @@ struct LocalAnalyzer<'mir, 'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> {
 }
 
 impl<'mir, 'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> LocalAnalyzer<'mir, 'a, 'tcx, Bx> {
-    fn assign(&mut self, local: mir::Local, location: Location) {
+    fn assign(&mut self, local: mir::Local, location: DefLocation) {
         let kind = &mut self.locals[local];
         match *kind {
             LocalKind::ZST => {}
             LocalKind::Memory => {}
-            LocalKind::Unused => {
-                *kind = LocalKind::SSA(location);
-            }
-            LocalKind::SSA(_) => {
-                *kind = LocalKind::Memory;
-            }
+            LocalKind::Unused => *kind = LocalKind::SSA(location),
+            LocalKind::SSA(_) => *kind = LocalKind::Memory,
         }
     }
 
@@ -166,7 +177,7 @@ fn visit_assign(
         debug!("visit_assign(place={:?}, rvalue={:?})", place, rvalue);
 
         if let Some(local) = place.as_local() {
-            self.assign(local, location);
+            self.assign(local, DefLocation::Body(location));
             if self.locals[local] != LocalKind::Memory {
                 let decl_span = self.fx.mir.local_decls[local].source_info.span;
                 if !self.fx.rvalue_creates_operand(rvalue, decl_span) {
@@ -189,7 +200,7 @@ fn visit_local(&mut self, local: mir::Local, context: PlaceContext, location: Lo
         match context {
             PlaceContext::MutatingUse(MutatingUseContext::Call)
             | PlaceContext::MutatingUse(MutatingUseContext::Yield) => {
-                self.assign(local, location);
+                self.assign(local, DefLocation::Body(location));
             }
 
             PlaceContext::NonUse(_) | PlaceContext::MutatingUse(MutatingUseContext::Retag) => {}
index 08ce5172574ac3bb1af28314ec2200a26b8d221a..6101b28ab0cdde9a42b69834de91ea4bff2d6198 100644 (file)
@@ -23,7 +23,7 @@ codegen_gcc_invalid_monomorphization_unsupported_element =
     invalid monomorphization of `{$name}` intrinsic: unsupported {$name} from `{$in_ty}` with element `{$elem_ty}` to `{$ret_ty}`
 
 codegen_gcc_invalid_monomorphization_invalid_bitmask =
-    invalid monomorphization of `{$name}` intrinsic: invalid bitmask `{ty}`, expected `u{$expected_int_bits}` or `[u8; {$expected_bytes}]`
+    invalid monomorphization of `{$name}` intrinsic: invalid bitmask `{$ty}`, expected `u{$expected_int_bits}` or `[u8; {$expected_bytes}]`
 
 codegen_gcc_invalid_monomorphization_simd_shuffle =
     invalid monomorphization of `{$name}` intrinsic: simd_shuffle index must be an array of `u32`, got `{$ty}`
index c8c7afb5f919632b8555682136978d0ea4dc4c99..4924105128db6eb1d55afa46efdb612999b7fd5b 100644 (file)
@@ -179,9 +179,9 @@ codegen_ssa_extract_bundled_libs_write_file = failed to write file '{$rlib}': {$
 
 codegen_ssa_unsupported_arch = unsupported arch `{$arch}` for os `{$os}`
 
-codegen_ssa_apple_sdk_error_sdk_path = failed to get {$sdk_name} SDK path: {error}
+codegen_ssa_apple_sdk_error_sdk_path = failed to get {$sdk_name} SDK path: {$error}
 
-codegen_ssa_read_file = failed to read file: {message}
+codegen_ssa_read_file = failed to read file: {$message}
 
 codegen_ssa_unsupported_link_self_contained = option `-C link-self-contained` is not supported on this target
 
index b688922a31130681a65d537d852638d0b82c4699..4696a4bd9ab63aeab10c4291c451fc93d1eddce4 100644 (file)
@@ -831,8 +831,6 @@ pub struct OwnerNodes<'tcx> {
     pub nodes: IndexVec<ItemLocalId, Option<ParentedNode<'tcx>>>,
     /// Content of local bodies.
     pub bodies: SortedMap<ItemLocalId, &'tcx Body<'tcx>>,
-    /// Non-owning definitions contained in this owner.
-    pub local_id_to_def_id: SortedMap<ItemLocalId, LocalDefId>,
 }
 
 impl<'tcx> OwnerNodes<'tcx> {
@@ -862,7 +860,6 @@ fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
                     .collect::<Vec<_>>(),
             )
             .field("bodies", &self.bodies)
-            .field("local_id_to_def_id", &self.local_id_to_def_id)
             .field("hash_without_bodies", &self.hash_without_bodies)
             .field("hash_including_bodies", &self.hash_including_bodies)
             .finish()
index 02641b7cf8fb5e037599f4d46e4c63eb3dcb9d29..f632babab0b24476b299f943d74ef2462d42afa7 100644 (file)
@@ -67,6 +67,7 @@
 use crate::hir::*;
 use rustc_ast::walk_list;
 use rustc_ast::{Attribute, Label};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::symbol::{Ident, Symbol};
 use rustc_span::Span;
 
@@ -364,7 +365,7 @@ fn visit_fn_ret_ty(&mut self, ret_ty: &'v FnRetTy<'v>) {
     fn visit_fn_decl(&mut self, fd: &'v FnDecl<'v>) {
         walk_fn_decl(self, fd)
     }
-    fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v FnDecl<'v>, b: BodyId, _: Span, id: HirId) {
+    fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v FnDecl<'v>, b: BodyId, _: Span, id: LocalDefId) {
         walk_fn(self, fk, fd, b, id)
     }
     fn visit_use(&mut self, path: &'v UsePath<'v>, hir_id: HirId) {
@@ -468,13 +469,16 @@ pub fn walk_item<'v, V: Visitor<'v>>(visitor: &mut V, item: &'v Item<'v>) {
             visitor.visit_ty(typ);
             visitor.visit_nested_body(body);
         }
-        ItemKind::Fn(ref sig, ref generics, body_id) => visitor.visit_fn(
-            FnKind::ItemFn(item.ident, generics, sig.header),
-            sig.decl,
-            body_id,
-            item.span,
-            item.hir_id(),
-        ),
+        ItemKind::Fn(ref sig, ref generics, body_id) => {
+            visitor.visit_id(item.hir_id());
+            visitor.visit_fn(
+                FnKind::ItemFn(item.ident, generics, sig.header),
+                sig.decl,
+                body_id,
+                item.span,
+                item.owner_id.def_id,
+            )
+        }
         ItemKind::Macro(..) => {
             visitor.visit_id(item.hir_id());
         }
@@ -733,7 +737,7 @@ pub fn walk_expr<'v, V: Visitor<'v>>(visitor: &mut V, expression: &'v Expr<'v>)
             walk_list!(visitor, visit_arm, arms);
         }
         ExprKind::Closure(&Closure {
-            def_id: _,
+            def_id,
             binder: _,
             bound_generic_params,
             fn_decl,
@@ -745,7 +749,7 @@ pub fn walk_expr<'v, V: Visitor<'v>>(visitor: &mut V, expression: &'v Expr<'v>)
             constness: _,
         }) => {
             walk_list!(visitor, visit_generic_param, bound_generic_params);
-            visitor.visit_fn(FnKind::Closure, fn_decl, body, expression.span, expression.hir_id)
+            visitor.visit_fn(FnKind::Closure, fn_decl, body, expression.span, def_id)
         }
         ExprKind::Block(ref block, ref opt_label) => {
             walk_list!(visitor, visit_label, opt_label);
@@ -923,9 +927,8 @@ pub fn walk_fn<'v, V: Visitor<'v>>(
     function_kind: FnKind<'v>,
     function_declaration: &'v FnDecl<'v>,
     body_id: BodyId,
-    id: HirId,
+    _: LocalDefId,
 ) {
-    visitor.visit_id(id);
     visitor.visit_fn_decl(function_declaration);
     walk_fn_kind(visitor, function_kind);
     visitor.visit_nested_body(body_id)
@@ -953,26 +956,30 @@ pub fn walk_trait_item<'v, V: Visitor<'v>>(visitor: &mut V, trait_item: &'v Trai
     let TraitItem { ident, generics, ref defaultness, ref kind, span, owner_id: _ } = *trait_item;
     let hir_id = trait_item.hir_id();
     visitor.visit_ident(ident);
-    visitor.visit_generics(generics);
-    visitor.visit_defaultness(defaultness);
+    visitor.visit_generics(&generics);
+    visitor.visit_defaultness(&defaultness);
+    visitor.visit_id(hir_id);
     match *kind {
         TraitItemKind::Const(ref ty, default) => {
-            visitor.visit_id(hir_id);
             visitor.visit_ty(ty);
             walk_list!(visitor, visit_nested_body, default);
         }
         TraitItemKind::Fn(ref sig, TraitFn::Required(param_names)) => {
-            visitor.visit_id(hir_id);
             visitor.visit_fn_decl(sig.decl);
             for &param_name in param_names {
                 visitor.visit_ident(param_name);
             }
         }
         TraitItemKind::Fn(ref sig, TraitFn::Provided(body_id)) => {
-            visitor.visit_fn(FnKind::Method(ident, sig), sig.decl, body_id, span, hir_id);
+            visitor.visit_fn(
+                FnKind::Method(ident, sig),
+                sig.decl,
+                body_id,
+                span,
+                trait_item.owner_id.def_id,
+            );
         }
         TraitItemKind::Type(bounds, ref default) => {
-            visitor.visit_id(hir_id);
             walk_list!(visitor, visit_param_bound, bounds);
             walk_list!(visitor, visit_ty, default);
         }
@@ -1002,9 +1009,9 @@ pub fn walk_impl_item<'v, V: Visitor<'v>>(visitor: &mut V, impl_item: &'v ImplIt
     visitor.visit_ident(ident);
     visitor.visit_generics(generics);
     visitor.visit_defaultness(defaultness);
+    visitor.visit_id(impl_item.hir_id());
     match *kind {
         ImplItemKind::Const(ref ty, body) => {
-            visitor.visit_id(impl_item.hir_id());
             visitor.visit_ty(ty);
             visitor.visit_nested_body(body);
         }
@@ -1014,11 +1021,10 @@ pub fn walk_impl_item<'v, V: Visitor<'v>>(visitor: &mut V, impl_item: &'v ImplIt
                 sig.decl,
                 body_id,
                 impl_item.span,
-                impl_item.hir_id(),
+                impl_item.owner_id.def_id,
             );
         }
         ImplItemKind::Type(ref ty) => {
-            visitor.visit_id(impl_item.hir_id());
             visitor.visit_ty(ty);
         }
     }
index 23423e8f3b3bff5f7121730e857a190e665d8667..85d0e02d0b6834004ca51eacdd1bf62093e600e7 100644 (file)
@@ -100,13 +100,8 @@ fn hash_stable(&self, hcx: &mut HirCtx, hasher: &mut StableHasher) {
         // `local_id_to_def_id` is also ignored because is dependent on the body, then just hashing
         // the body satisfies the condition of two nodes being different have different
         // `hash_stable` results.
-        let OwnerNodes {
-            hash_including_bodies,
-            hash_without_bodies: _,
-            nodes: _,
-            bodies: _,
-            local_id_to_def_id: _,
-        } = *self;
+        let OwnerNodes { hash_including_bodies, hash_without_bodies: _, nodes: _, bodies: _ } =
+            *self;
         hash_including_bodies.hash_stable(hcx, hasher);
     }
 }
index c89db538aa6d395e642a3e5a1bc983ae3b8a4f3c..6f4ebc987e6a97ee0951550e5c894f76a68f8f41 100644 (file)
@@ -665,7 +665,7 @@ fn check_item_type(tcx: TyCtxt<'_>, id: hir::ItemId) {
         DefKind::GlobalAsm => {
             let it = tcx.hir().item(id);
             let hir::ItemKind::GlobalAsm(asm) = it.kind else { span_bug!(it.span, "DefKind::GlobalAsm but got {:#?}", it) };
-            InlineAsmCtxt::new_global_asm(tcx).check_asm(asm, id.hir_id());
+            InlineAsmCtxt::new_global_asm(tcx).check_asm(asm, id.owner_id.def_id);
         }
         _ => {}
     }
index 82030d82f57a0536f90667df5ba79183aeed8f02..122b6ead8e9d7f8432a6078cf2b58a318b63db93 100644 (file)
@@ -3,6 +3,7 @@
 use rustc_hir as hir;
 use rustc_middle::ty::{self, Article, FloatTy, IntTy, Ty, TyCtxt, TypeVisitable, UintTy};
 use rustc_session::lint;
+use rustc_span::def_id::LocalDefId;
 use rustc_span::{Symbol, DUMMY_SP};
 use rustc_target::asm::{InlineAsmReg, InlineAsmRegClass, InlineAsmRegOrRegClass, InlineAsmType};
 
@@ -253,10 +254,8 @@ fn check_asm_operand_type(
         Some(asm_ty)
     }
 
-    pub fn check_asm(&self, asm: &hir::InlineAsm<'tcx>, enclosing_id: hir::HirId) {
-        let hir = self.tcx.hir();
-        let enclosing_def_id = hir.local_def_id(enclosing_id).to_def_id();
-        let target_features = self.tcx.asm_target_features(enclosing_def_id);
+    pub fn check_asm(&self, asm: &hir::InlineAsm<'tcx>, enclosing_id: LocalDefId) {
+        let target_features = self.tcx.asm_target_features(enclosing_id.to_def_id());
         let Some(asm_arch) = self.tcx.sess.asm_arch else {
             self.tcx.sess.delay_span_bug(DUMMY_SP, "target architecture does not support asm");
             return;
index 870c57d5e0595354f7a8bc54b54b482b28f3bdf4..e15b7c897302458692029128b25b579b6653b8e6 100644 (file)
@@ -391,7 +391,7 @@ fn check_gat_where_clauses(tcx: TyCtxt<'_>, associated_items: &[hir::TraitItemRe
                         gather_gat_bounds(
                             tcx,
                             param_env,
-                            item_def_id.def_id,
+                            item_def_id,
                             sig.inputs_and_output,
                             // We also assume that all of the function signature's parameter types
                             // are well formed.
@@ -413,7 +413,7 @@ fn check_gat_where_clauses(tcx: TyCtxt<'_>, associated_items: &[hir::TraitItemRe
                         gather_gat_bounds(
                             tcx,
                             param_env,
-                            item_def_id.def_id,
+                            item_def_id,
                             tcx.explicit_item_bounds(item_def_id).to_vec(),
                             &FxIndexSet::default(),
                             gat_def_id.def_id,
@@ -563,7 +563,7 @@ fn augment_param_env<'tcx>(
 fn gather_gat_bounds<'tcx, T: TypeFoldable<'tcx>>(
     tcx: TyCtxt<'tcx>,
     param_env: ty::ParamEnv<'tcx>,
-    item_def_id: LocalDefId,
+    item_def_id: hir::OwnerId,
     to_check: T,
     wf_tys: &FxIndexSet<Ty<'tcx>>,
     gat_def_id: LocalDefId,
@@ -596,7 +596,7 @@ fn gather_gat_bounds<'tcx, T: TypeFoldable<'tcx>>(
         // reflected in a where clause on the GAT itself.
         for (ty, ty_idx) in &types {
             // In our example, requires that `Self: 'a`
-            if ty_known_to_outlive(tcx, item_def_id, param_env, &wf_tys, *ty, *region_a) {
+            if ty_known_to_outlive(tcx, item_def_id.def_id, param_env, &wf_tys, *ty, *region_a) {
                 debug!(?ty_idx, ?region_a_idx);
                 debug!("required clause: {ty} must outlive {region_a}");
                 // Translate into the generic parameters of the GAT. In
@@ -634,7 +634,14 @@ fn gather_gat_bounds<'tcx, T: TypeFoldable<'tcx>>(
             if ty::ReStatic == **region_b || region_a == region_b {
                 continue;
             }
-            if region_known_to_outlive(tcx, item_def_id, param_env, &wf_tys, *region_a, *region_b) {
+            if region_known_to_outlive(
+                tcx,
+                item_def_id.def_id,
+                param_env,
+                &wf_tys,
+                *region_a,
+                *region_b,
+            ) {
                 debug!(?region_a_idx, ?region_b_idx);
                 debug!("required clause: {region_a} must outlive {region_b}");
                 // Translate into the generic parameters of the GAT.
index 359122d4e16abd81c0f79463bcdad18cc21c4230..3c67722b637bfa93aa9c33d5c0a3ea1955c2dbf5 100644 (file)
@@ -829,7 +829,7 @@ fn visit_fn(
         fd: &'tcx hir::FnDecl<'tcx>,
         body_id: hir::BodyId,
         _: Span,
-        _: hir::HirId,
+        _: LocalDefId,
     ) {
         let output = match fd.output {
             hir::FnRetTy::DefaultReturn(_) => None,
@@ -1264,14 +1264,21 @@ fn resolve_lifetime_ref(
             } else if let Some(body_id) = outermost_body {
                 let fn_id = self.tcx.hir().body_owner(body_id);
                 match self.tcx.hir().get(fn_id) {
-                    Node::Item(hir::Item { kind: hir::ItemKind::Fn(..), .. })
+                    Node::Item(hir::Item { owner_id, kind: hir::ItemKind::Fn(..), .. })
                     | Node::TraitItem(hir::TraitItem {
-                        kind: hir::TraitItemKind::Fn(..), ..
+                        owner_id,
+                        kind: hir::TraitItemKind::Fn(..),
+                        ..
                     })
-                    | Node::ImplItem(hir::ImplItem { kind: hir::ImplItemKind::Fn(..), .. })
-                    | Node::Expr(hir::Expr { kind: hir::ExprKind::Closure(..), .. }) => {
-                        let scope = self.tcx.hir().local_def_id(fn_id);
-                        def = Region::Free(scope.to_def_id(), def.id().unwrap());
+                    | Node::ImplItem(hir::ImplItem {
+                        owner_id,
+                        kind: hir::ImplItemKind::Fn(..),
+                        ..
+                    }) => {
+                        def = Region::Free(owner_id.to_def_id(), def.id().unwrap());
+                    }
+                    Node::Expr(hir::Expr { kind: hir::ExprKind::Closure(closure), .. }) => {
+                        def = Region::Free(closure.def_id.to_def_id(), def.id().unwrap());
                     }
                     _ => {}
                 }
@@ -1658,10 +1665,12 @@ fn uninsert_lifetime_on_error(&mut self, lifetime_ref: &'tcx hir::Lifetime, bad_
 /// "Constrained" basically means that it appears in any type but
 /// not amongst the inputs to a projection. In other words, `<&'a
 /// T as Trait<''b>>::Foo` does not constrain `'a` or `'b`.
-fn is_late_bound_map(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Option<&FxIndexSet<LocalDefId>> {
-    let hir_id = tcx.hir().local_def_id_to_hir_id(def_id);
-    let decl = tcx.hir().fn_decl_by_hir_id(hir_id)?;
-    let generics = tcx.hir().get_generics(def_id)?;
+fn is_late_bound_map(
+    tcx: TyCtxt<'_>,
+    owner_id: hir::OwnerId,
+) -> Option<&FxIndexSet<hir::ItemLocalId>> {
+    let decl = tcx.hir().fn_decl_by_hir_id(owner_id.into())?;
+    let generics = tcx.hir().get_generics(owner_id.def_id)?;
 
     let mut late_bound = FxIndexSet::default();
 
@@ -1695,24 +1704,22 @@ fn is_late_bound_map(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Option<&FxIndexSet<
             hir::GenericParamKind::Type { .. } | hir::GenericParamKind::Const { .. } => continue,
         }
 
-        let param_def_id = tcx.hir().local_def_id(param.hir_id);
-
         // appears in the where clauses? early-bound.
-        if appears_in_where_clause.regions.contains(&param_def_id) {
+        if appears_in_where_clause.regions.contains(&param.def_id) {
             continue;
         }
 
         // does not appear in the inputs, but appears in the return type? early-bound.
-        if !constrained_by_input.regions.contains(&param_def_id)
-            && appears_in_output.regions.contains(&param_def_id)
+        if !constrained_by_input.regions.contains(&param.def_id)
+            && appears_in_output.regions.contains(&param.def_id)
         {
             continue;
         }
 
-        debug!("lifetime {:?} with id {:?} is late-bound", param.name.ident(), param.hir_id);
+        debug!("lifetime {:?} with id {:?} is late-bound", param.name.ident(), param.def_id);
 
-        let inserted = late_bound.insert(param_def_id);
-        assert!(inserted, "visited lifetime {:?} twice", param.hir_id);
+        let inserted = late_bound.insert(param.hir_id.local_id);
+        assert!(inserted, "visited lifetime {:?} twice", param.def_id);
     }
 
     debug!(?late_bound);
index 46b277d9803d78db081c53ea63bc3861aa209c7c..d0d67ae9257c5ddcb959b28ee5f0e752c6fccc01 100644 (file)
@@ -280,7 +280,7 @@ fn gather_explicit_predicates_of(tcx: TyCtxt<'_>, def_id: DefId) -> ty::GenericP
             }
 
             let hir::GenericParamKind::Lifetime { .. } = duplicate.kind else { continue };
-            let dup_def = tcx.hir().local_def_id(duplicate.hir_id).to_def_id();
+            let dup_def = duplicate.def_id.to_def_id();
 
             let Some(dup_index) = generics.param_def_id_to_index(tcx, dup_def) else { bug!() };
 
index d0d819d9687bbd673211447b5eeeb84fef955104..e7b0846e10352b1093b1d7efdd2174629513267e 100644 (file)
@@ -54,15 +54,14 @@ pub(super) fn opt_const_param_of(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Option<
             // ty which is a fully resolved projection.
             // For the code example above, this would mean converting Self::Assoc<3>
             // into a ty::Alias(ty::Projection, <Self as Foo>::Assoc<3>)
-            let item_hir_id = tcx
+            let item_def_id = tcx
                 .hir()
-                .parent_iter(hir_id)
-                .filter(|(_, node)| matches!(node, Node::Item(_)))
-                .map(|(id, _)| id)
-                .next()
-                .unwrap();
-            let item_did = tcx.hir().local_def_id(item_hir_id).to_def_id();
-            let item_ctxt = &ItemCtxt::new(tcx, item_did) as &dyn crate::astconv::AstConv<'_>;
+                .parent_owner_iter(hir_id)
+                .find(|(_, node)| matches!(node, OwnerNode::Item(_)))
+                .unwrap()
+                .0
+                .to_def_id();
+            let item_ctxt = &ItemCtxt::new(tcx, item_def_id) as &dyn crate::astconv::AstConv<'_>;
             let ty = item_ctxt.ast_ty_to_ty(hir_ty);
 
             // Iterate through the generics of the projection to find the one that corresponds to
index 73aba2780d680388e6496981672e40da59fe2529..88fb26535868603907dfdd4ec89c8678f301c024 100644 (file)
@@ -186,6 +186,7 @@ fn suggest_removing_semicolon_for_coerce(
         prior_arm: Option<(Option<hir::HirId>, Ty<'tcx>, Span)>,
     ) {
         let hir = self.tcx.hir();
+
         // First, check that we're actually in the tail of a function.
         let Some(body_id) = hir.maybe_body_owned_by(self.body_id) else { return; };
         let body = hir.body(body_id);
index 17f736475dd37e0d7e4d5d3599ae4d0a8e52888f..1c70c1b71e7639315f741329413e96be905b73b3 100644 (file)
@@ -130,7 +130,12 @@ pub(super) fn check_fn<'a, 'tcx>(
     let gen_ty = if let (Some(_), Some(gen_kind)) = (can_be_generator, body.generator_kind) {
         let interior = fcx
             .next_ty_var(TypeVariableOrigin { kind: TypeVariableOriginKind::MiscVariable, span });
-        fcx.deferred_generator_interiors.borrow_mut().push((fn_id, body.id(), interior, gen_kind));
+        fcx.deferred_generator_interiors.borrow_mut().push((
+            fn_def_id,
+            body.id(),
+            interior,
+            gen_kind,
+        ));
 
         let (resume_ty, yield_ty) = fcx.resume_yield_tys.unwrap();
         Some(GeneratorTypes {
@@ -167,12 +172,12 @@ pub(super) fn check_fn<'a, 'tcx>(
 
     // Check that a function marked as `#[panic_handler]` has signature `fn(&PanicInfo) -> !`
     if let Some(panic_impl_did) = tcx.lang_items().panic_impl()
-        && panic_impl_did == hir.local_def_id(fn_id).to_def_id()
+        && panic_impl_did == fn_def_id.to_def_id()
     {
         check_panic_info_fn(tcx, panic_impl_did.expect_local(), fn_sig, decl, declared_ret_ty);
     }
 
-    if let Some(lang_start_defid) = tcx.lang_items().start_fn() && lang_start_defid == hir.local_def_id(fn_id).to_def_id() {
+    if let Some(lang_start_defid) = tcx.lang_items().start_fn() && lang_start_defid == fn_def_id.to_def_id() {
         check_lang_start_fn(tcx, fn_sig, decl, fn_def_id);
     }
 
index 126355c5bfa27bc105b91be13138029ca4cc7ffb..a355a54d6959abb5570144e9c40b53f2e973ce3f 100644 (file)
@@ -549,8 +549,7 @@ fn save_generator_interior_predicates(&self, def_id: DefId) {
         let generators = std::mem::take(&mut *self.deferred_generator_interiors.borrow_mut());
         debug!(?generators);
 
-        for &(expr_hir_id, body_id, interior, _) in generators.iter() {
-            let expr_def_id = self.tcx.hir().local_def_id(expr_hir_id);
+        for &(expr_def_id, body_id, interior, _) in generators.iter() {
             debug!(?expr_def_id);
 
             // Create the `GeneratorWitness` type that we will unify with `interior`.
index e78c76d5dde7031337b15a34272520d5438cebff..47ef106e750321470003d3b25103cbcb25b98d9c 100644 (file)
@@ -79,7 +79,7 @@ pub(in super::super) fn check_asms(&self) {
                 }
             };
             InlineAsmCtxt::new_in_fn(self.tcx, self.param_env, get_operand_ty)
-                .check_asm(asm, self.tcx.hir().local_def_id_to_hir_id(enclosing_id));
+                .check_asm(asm, enclosing_id);
         }
     }
 
index 15dd3412c34093e062eb5b74aa36a77fd5a3010a..38445f28440527822932e6424379d6419ddb46e5 100644 (file)
@@ -5,6 +5,7 @@
 use rustc_infer::infer::type_variable::{TypeVariableOrigin, TypeVariableOriginKind};
 use rustc_middle::ty::Ty;
 use rustc_middle::ty::UserType;
+use rustc_span::def_id::LocalDefId;
 use rustc_span::Span;
 use rustc_trait_selection::traits;
 
@@ -156,7 +157,7 @@ fn visit_fn(
         _: &'tcx hir::FnDecl<'tcx>,
         _: hir::BodyId,
         _: Span,
-        _: hir::HirId,
+        _: LocalDefId,
     ) {
     }
 }
index c6ce2f450d915111ac72ef90bdbd3c1a4a002f7d..87e54025330e8a928873fc3295a31dd5e17d1a78 100644 (file)
@@ -56,7 +56,7 @@ pub struct Inherited<'tcx> {
     pub(super) deferred_asm_checks: RefCell<Vec<(&'tcx hir::InlineAsm<'tcx>, hir::HirId)>>,
 
     pub(super) deferred_generator_interiors:
-        RefCell<Vec<(hir::HirId, hir::BodyId, Ty<'tcx>, hir::GeneratorKind)>>,
+        RefCell<Vec<(LocalDefId, hir::BodyId, Ty<'tcx>, hir::GeneratorKind)>>,
 
     pub(super) body_id: Option<hir::BodyId>,
 
index 20d6ce5ed516d684440630f7140a58475f0e3e95..0aa34f9dd70724d2b0588fec4de21bbe150d0b57 100644 (file)
@@ -40,8 +40,7 @@ pub fn resolve_type_vars_in_body(
         &self,
         body: &'tcx hir::Body<'tcx>,
     ) -> &'tcx ty::TypeckResults<'tcx> {
-        let item_id = self.tcx.hir().body_owner(body.id());
-        let item_def_id = self.tcx.hir().local_def_id(item_id);
+        let item_def_id = self.tcx.hir().body_owner_def_id(body.id());
 
         // This attribute causes us to dump some writeback information
         // in the form of errors, which is used for unit tests.
@@ -55,7 +54,8 @@ pub fn resolve_type_vars_in_body(
         // Type only exists for constants and statics, not functions.
         match self.tcx.hir().body_owner_kind(item_def_id) {
             hir::BodyOwnerKind::Const | hir::BodyOwnerKind::Static(_) => {
-                wbcx.visit_node_id(body.value.span, item_id);
+                let item_hir_id = self.tcx.hir().local_def_id_to_hir_id(item_def_id);
+                wbcx.visit_node_id(body.value.span, item_hir_id);
             }
             hir::BodyOwnerKind::Closure | hir::BodyOwnerKind::Fn => (),
         }
index 33a9a0cabb9d5067266f1d9025e4d04bc8cf324a..6703d53f3805cfe2884d2a649d4c033b5149d9e5 100644 (file)
@@ -38,7 +38,7 @@
 use rustc_data_structures::graph::implementation::{Direction, NodeIndex, INCOMING, OUTGOING};
 use rustc_graphviz as dot;
 use rustc_hir as hir;
-use rustc_hir::def_id::DefId;
+use rustc_hir::def_id::{DefId, LocalDefId, CRATE_DEF_ID};
 use rustc_hir::intravisit::{self, Visitor};
 use rustc_middle::dep_graph::{
     DepGraphQuery, DepKind, DepNode, DepNodeExt, DepNodeFilter, EdgeFilter,
@@ -74,7 +74,7 @@ pub fn assert_dep_graph(tcx: TyCtxt<'_>) {
         let (if_this_changed, then_this_would_need) = {
             let mut visitor =
                 IfThisChanged { tcx, if_this_changed: vec![], then_this_would_need: vec![] };
-            visitor.process_attrs(hir::CRATE_HIR_ID);
+            visitor.process_attrs(CRATE_DEF_ID);
             tcx.hir().visit_all_item_likes_in_crate(&mut visitor);
             (visitor.if_this_changed, visitor.then_this_would_need)
         };
@@ -119,9 +119,9 @@ fn argument(&self, attr: &ast::Attribute) -> Option<Symbol> {
         value
     }
 
-    fn process_attrs(&mut self, hir_id: hir::HirId) {
-        let def_id = self.tcx.hir().local_def_id(hir_id);
+    fn process_attrs(&mut self, def_id: LocalDefId) {
         let def_path_hash = self.tcx.def_path_hash(def_id.to_def_id());
+        let hir_id = self.tcx.hir().local_def_id_to_hir_id(def_id);
         let attrs = self.tcx.hir().attrs(hir_id);
         for attr in attrs {
             if attr.has_name(sym::rustc_if_this_changed) {
@@ -180,22 +180,22 @@ fn nested_visit_map(&mut self) -> Self::Map {
     }
 
     fn visit_item(&mut self, item: &'tcx hir::Item<'tcx>) {
-        self.process_attrs(item.hir_id());
+        self.process_attrs(item.owner_id.def_id);
         intravisit::walk_item(self, item);
     }
 
     fn visit_trait_item(&mut self, trait_item: &'tcx hir::TraitItem<'tcx>) {
-        self.process_attrs(trait_item.hir_id());
+        self.process_attrs(trait_item.owner_id.def_id);
         intravisit::walk_trait_item(self, trait_item);
     }
 
     fn visit_impl_item(&mut self, impl_item: &'tcx hir::ImplItem<'tcx>) {
-        self.process_attrs(impl_item.hir_id());
+        self.process_attrs(impl_item.owner_id.def_id);
         intravisit::walk_impl_item(self, impl_item);
     }
 
     fn visit_field_def(&mut self, s: &'tcx hir::FieldDef<'tcx>) {
-        self.process_attrs(s.hir_id);
+        self.process_attrs(s.def_id);
         intravisit::walk_field_def(self, s);
     }
 }
index e59715b706b29c0c4da6afde7ba99fe9b5a3f737..f7e3e4a1cc09ee2583ecbce9e4c0c2269e3c8c5a 100644 (file)
@@ -26,7 +26,7 @@
 use rustc_index::vec::IndexVec;
 use rustc_middle::ty::fold::TypeFoldable;
 use rustc_middle::ty::subst::GenericArg;
-use rustc_middle::ty::{self, BoundVar, List};
+use rustc_middle::ty::{self, List};
 use rustc_span::source_map::Span;
 
 pub use rustc_middle::infer::canonical::*;
@@ -87,12 +87,13 @@ fn instantiate_canonical_vars(
         variables: &List<CanonicalVarInfo<'tcx>>,
         universe_map: impl Fn(ty::UniverseIndex) -> ty::UniverseIndex,
     ) -> CanonicalVarValues<'tcx> {
-        let var_values: IndexVec<BoundVar, GenericArg<'tcx>> = variables
-            .iter()
-            .map(|info| self.instantiate_canonical_var(span, info, &universe_map))
-            .collect();
-
-        CanonicalVarValues { var_values }
+        CanonicalVarValues {
+            var_values: self.tcx.mk_substs(
+                variables
+                    .iter()
+                    .map(|info| self.instantiate_canonical_var(span, info, &universe_map)),
+            ),
+        }
     }
 
     /// Given the "info" about a canonical variable, creates a fresh
index 9174bd524bee6d50b74246c8ea0e8df156907041..3e8e7734a5a5de61d34fefba70cf674f0be512d7 100644 (file)
@@ -482,11 +482,8 @@ fn query_response_substitution_guess<R>(
         // given variable in the loop above, use that. Otherwise, use
         // a fresh inference variable.
         let result_subst = CanonicalVarValues {
-            var_values: query_response
-                .variables
-                .iter()
-                .enumerate()
-                .map(|(index, info)| {
+            var_values: self.tcx.mk_substs(query_response.variables.iter().enumerate().map(
+                |(index, info)| {
                     if info.is_existential() {
                         match opt_values[BoundVar::new(index)] {
                             Some(k) => k,
@@ -499,8 +496,8 @@ fn query_response_substitution_guess<R>(
                             universe_map[u.as_usize()]
                         })
                     }
-                })
-                .collect(),
+                },
+            )),
         };
 
         let mut obligations = vec![];
index 389afe22eb7672afe16c801ca97c9b1c940390fe..e77f2d37b7dae8d5c6314c8f22092d28d05b95b1 100644 (file)
@@ -72,16 +72,15 @@ pub(super) fn substitute_value<'tcx, T>(
         value
     } else {
         let delegate = FnMutDelegate {
-            regions: &mut |br: ty::BoundRegion| match var_values.var_values[br.var].unpack() {
+            regions: &mut |br: ty::BoundRegion| match var_values[br.var].unpack() {
                 GenericArgKind::Lifetime(l) => l,
                 r => bug!("{:?} is a region but value is {:?}", br, r),
             },
-            types: &mut |bound_ty: ty::BoundTy| match var_values.var_values[bound_ty.var].unpack() {
+            types: &mut |bound_ty: ty::BoundTy| match var_values[bound_ty.var].unpack() {
                 GenericArgKind::Type(ty) => ty,
                 r => bug!("{:?} is a type but value is {:?}", bound_ty, r),
             },
-            consts: &mut |bound_ct: ty::BoundVar, _| match var_values.var_values[bound_ct].unpack()
-            {
+            consts: &mut |bound_ct: ty::BoundVar, _| match var_values[bound_ct].unpack() {
                 GenericArgKind::Const(ct) => ct,
                 c => bug!("{:?} is a const but value is {:?}", bound_ct, c),
             },
index 72676b718fabe61853a9820a3282e271b8aed203..a567b6acdbeeb2dc802175bea078a979d6795a7c 100644 (file)
 use rustc_middle::ty::error::{ExpectedFound, TypeError};
 use rustc_middle::ty::relate::{self, Relate, RelateResult, TypeRelation};
 use rustc_middle::ty::subst::SubstsRef;
-use rustc_middle::ty::{self, InferConst, Ty, TyCtxt, TypeVisitable};
+use rustc_middle::ty::{
+    self, FallibleTypeFolder, InferConst, Ty, TyCtxt, TypeFoldable, TypeSuperFoldable,
+    TypeVisitable,
+};
 use rustc_middle::ty::{IntType, UintType};
 use rustc_span::{Span, DUMMY_SP};
 
@@ -140,8 +143,6 @@ pub fn super_combine_consts<R>(
         let a = self.shallow_resolve(a);
         let b = self.shallow_resolve(b);
 
-        let a_is_expected = relation.a_is_expected();
-
         match (a.kind(), b.kind()) {
             (
                 ty::ConstKind::Infer(InferConst::Var(a_vid)),
@@ -158,11 +159,11 @@ pub fn super_combine_consts<R>(
             }
 
             (ty::ConstKind::Infer(InferConst::Var(vid)), _) => {
-                return self.unify_const_variable(relation.param_env(), vid, b, a_is_expected);
+                return self.unify_const_variable(vid, b);
             }
 
             (_, ty::ConstKind::Infer(InferConst::Var(vid))) => {
-                return self.unify_const_variable(relation.param_env(), vid, a, !a_is_expected);
+                return self.unify_const_variable(vid, a);
             }
             (ty::ConstKind::Unevaluated(..), _) if self.tcx.lazy_normalization() => {
                 // FIXME(#59490): Need to remove the leak check to accommodate
@@ -223,10 +224,8 @@ pub fn super_combine_consts<R>(
     #[instrument(level = "debug", skip(self))]
     fn unify_const_variable(
         &self,
-        param_env: ty::ParamEnv<'tcx>,
         target_vid: ty::ConstVid<'tcx>,
         ct: ty::Const<'tcx>,
-        vid_is_expected: bool,
     ) -> RelateResult<'tcx, ty::Const<'tcx>> {
         let (for_universe, span) = {
             let mut inner = self.inner.borrow_mut();
@@ -239,8 +238,12 @@ fn unify_const_variable(
                 ConstVariableValue::Unknown { universe } => (universe, var_value.origin.span),
             }
         };
-        let value = ConstInferUnifier { infcx: self, span, param_env, for_universe, target_vid }
-            .relate(ct, ct)?;
+        let value = ct.try_fold_with(&mut ConstInferUnifier {
+            infcx: self,
+            span,
+            for_universe,
+            target_vid,
+        })?;
 
         self.inner.borrow_mut().const_unification_table().union_value(
             target_vid,
@@ -800,8 +803,6 @@ struct ConstInferUnifier<'cx, 'tcx> {
 
     span: Span,
 
-    param_env: ty::ParamEnv<'tcx>,
-
     for_universe: ty::UniverseIndex,
 
     /// The vid of the const variable that is in the process of being
@@ -810,61 +811,15 @@ struct ConstInferUnifier<'cx, 'tcx> {
     target_vid: ty::ConstVid<'tcx>,
 }
 
-// We use `TypeRelation` here to propagate `RelateResult` upwards.
-//
-// Both inputs are expected to be the same.
-impl<'tcx> TypeRelation<'tcx> for ConstInferUnifier<'_, 'tcx> {
-    fn tcx(&self) -> TyCtxt<'tcx> {
-        self.infcx.tcx
-    }
-
-    fn intercrate(&self) -> bool {
-        assert!(!self.infcx.intercrate);
-        false
-    }
-
-    fn param_env(&self) -> ty::ParamEnv<'tcx> {
-        self.param_env
-    }
-
-    fn tag(&self) -> &'static str {
-        "ConstInferUnifier"
-    }
-
-    fn a_is_expected(&self) -> bool {
-        true
-    }
-
-    fn mark_ambiguous(&mut self) {
-        bug!()
-    }
-
-    fn relate_with_variance<T: Relate<'tcx>>(
-        &mut self,
-        _variance: ty::Variance,
-        _info: ty::VarianceDiagInfo<'tcx>,
-        a: T,
-        b: T,
-    ) -> RelateResult<'tcx, T> {
-        // We don't care about variance here.
-        self.relate(a, b)
-    }
+impl<'tcx> FallibleTypeFolder<'tcx> for ConstInferUnifier<'_, 'tcx> {
+    type Error = TypeError<'tcx>;
 
-    fn binders<T>(
-        &mut self,
-        a: ty::Binder<'tcx, T>,
-        b: ty::Binder<'tcx, T>,
-    ) -> RelateResult<'tcx, ty::Binder<'tcx, T>>
-    where
-        T: Relate<'tcx>,
-    {
-        Ok(a.rebind(self.relate(a.skip_binder(), b.skip_binder())?))
+    fn tcx<'a>(&'a self) -> TyCtxt<'tcx> {
+        self.infcx.tcx
     }
 
     #[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);
-
+    fn try_fold_ty(&mut self, t: Ty<'tcx>) -> Result<Ty<'tcx>, TypeError<'tcx>> {
         match t.kind() {
             &ty::Infer(ty::TyVar(vid)) => {
                 let vid = self.infcx.inner.borrow_mut().type_variables().root_var(vid);
@@ -872,7 +827,7 @@ fn tys(&mut self, t: Ty<'tcx>, _t: Ty<'tcx>) -> RelateResult<'tcx, Ty<'tcx>> {
                 match probe {
                     TypeVariableValue::Known { value: u } => {
                         debug!("ConstOccursChecker: known value {:?}", u);
-                        self.tys(u, u)
+                        u.try_fold_with(self)
                     }
                     TypeVariableValue::Unknown { universe } => {
                         if self.for_universe.can_name(universe) {
@@ -892,16 +847,15 @@ fn tys(&mut self, t: Ty<'tcx>, _t: Ty<'tcx>) -> RelateResult<'tcx, Ty<'tcx>> {
                 }
             }
             ty::Infer(ty::IntVar(_) | ty::FloatVar(_)) => Ok(t),
-            _ => relate::super_relate_tys(self, t, t),
+            _ => t.try_super_fold_with(self),
         }
     }
 
-    fn regions(
+    #[instrument(level = "debug", skip(self), ret)]
+    fn try_fold_region(
         &mut self,
         r: ty::Region<'tcx>,
-        _r: ty::Region<'tcx>,
-    ) -> RelateResult<'tcx, ty::Region<'tcx>> {
-        debug_assert_eq!(r, _r);
+    ) -> Result<ty::Region<'tcx>, TypeError<'tcx>> {
         debug!("ConstInferUnifier: r={:?}", r);
 
         match *r {
@@ -930,14 +884,8 @@ fn regions(
         }
     }
 
-    #[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);
-
+    #[instrument(level = "debug", skip(self), ret)]
+    fn try_fold_const(&mut self, c: ty::Const<'tcx>) -> Result<ty::Const<'tcx>, TypeError<'tcx>> {
         match c.kind() {
             ty::ConstKind::Infer(InferConst::Var(vid)) => {
                 // Check if the current unification would end up
@@ -958,7 +906,7 @@ fn consts(
                 let var_value =
                     self.infcx.inner.borrow_mut().const_unification_table().probe_value(vid);
                 match var_value.val {
-                    ConstVariableValue::Known { value: u } => self.consts(u, u),
+                    ConstVariableValue::Known { value: u } => u.try_fold_with(self),
                     ConstVariableValue::Unknown { universe } => {
                         if self.for_universe.can_name(universe) {
                             Ok(c)
@@ -977,17 +925,7 @@ fn consts(
                     }
                 }
             }
-            ty::ConstKind::Unevaluated(ty::UnevaluatedConst { def, substs }) => {
-                let substs = self.relate_with_variance(
-                    ty::Variance::Invariant,
-                    ty::VarianceDiagInfo::default(),
-                    substs,
-                    substs,
-                )?;
-
-                Ok(self.tcx().mk_const(ty::UnevaluatedConst { def, substs }, c.ty()))
-            }
-            _ => relate::super_relate_consts(self, c, c),
+            _ => c.try_super_fold_with(self),
         }
     }
 }
index 9b22ad098b2f85068609cbe4800f672f62cc17fb..8361c81f0efe35f63d22fe9bc08ce52217e0d2b1 100644 (file)
@@ -56,9 +56,7 @@
 use rustc_hir::def::{DefKind, Res};
 use rustc_hir::def_id::{DefId, LocalDefId, LocalDefIdSet, CRATE_DEF_ID};
 use rustc_hir::intravisit::FnKind as HirFnKind;
-use rustc_hir::{
-    Body, FnDecl, ForeignItemKind, GenericParamKind, HirId, Node, PatKind, PredicateOrigin,
-};
+use rustc_hir::{Body, FnDecl, ForeignItemKind, GenericParamKind, Node, PatKind, PredicateOrigin};
 use rustc_index::vec::Idx;
 use rustc_middle::lint::in_external_macro;
 use rustc_middle::ty::layout::{LayoutError, LayoutOf};
@@ -583,12 +581,13 @@ fn check_trait_item(&mut self, cx: &LateContext<'_>, trait_item: &hir::TraitItem
 
     fn check_impl_item(&mut self, cx: &LateContext<'_>, impl_item: &hir::ImplItem<'_>) {
         // If the method is an impl for a trait, don't doc.
-        if method_context(cx, impl_item.hir_id()) == MethodLateContext::TraitImpl {
+        let context = method_context(cx, impl_item.owner_id.def_id);
+        if context == MethodLateContext::TraitImpl {
             return;
         }
 
         // If the method is an impl for an item with docs_hidden, don't doc.
-        if method_context(cx, impl_item.hir_id()) == MethodLateContext::PlainImpl {
+        if context == MethodLateContext::PlainImpl {
             let parent = cx.tcx.hir().get_parent_item(impl_item.hir_id());
             let impl_ty = cx.tcx.type_of(parent);
             let outerdef = match impl_ty.kind() {
@@ -1296,19 +1295,18 @@ fn check_fn(
         _: &'tcx FnDecl<'_>,
         _: &'tcx Body<'_>,
         span: Span,
-        hir_id: HirId,
+        def_id: LocalDefId,
     ) {
         if fn_kind.asyncness() == IsAsync::Async
             && !cx.tcx.features().closure_track_caller
-            && let attrs = cx.tcx.hir().attrs(hir_id)
             // Now, check if the function has the `#[track_caller]` attribute
-            && let Some(attr) = attrs.iter().find(|attr| attr.has_name(sym::track_caller))
-            {
-                cx.emit_spanned_lint(UNGATED_ASYNC_FN_TRACK_CALLER, attr.span, BuiltinUngatedAsyncFnTrackCaller {
-                    label: span,
-                    parse_sess: &cx.tcx.sess.parse_sess,
-                });
-            }
+            && let Some(attr) = cx.tcx.get_attr(def_id.to_def_id(), sym::track_caller)
+        {
+            cx.emit_spanned_lint(UNGATED_ASYNC_FN_TRACK_CALLER, attr.span, BuiltinUngatedAsyncFnTrackCaller {
+                label: span,
+                parse_sess: &cx.tcx.sess.parse_sess,
+            });
+        }
     }
 }
 
@@ -2684,7 +2682,7 @@ pub struct ClashingExternDeclarations {
     /// the symbol should be reported as a clashing declaration.
     // FIXME: Technically, we could just store a &'tcx str here without issue; however, the
     // `impl_lint_pass` macro doesn't currently support lints parametric over a lifetime.
-    seen_decls: FxHashMap<Symbol, HirId>,
+    seen_decls: FxHashMap<Symbol, hir::OwnerId>,
 }
 
 /// Differentiate between whether the name for an extern decl came from the link_name attribute or
@@ -2710,19 +2708,20 @@ impl ClashingExternDeclarations {
     pub(crate) fn new() -> Self {
         ClashingExternDeclarations { seen_decls: FxHashMap::default() }
     }
+
     /// Insert a new foreign item into the seen set. If a symbol with the same name already exists
     /// for the item, return its HirId without updating the set.
-    fn insert(&mut self, tcx: TyCtxt<'_>, fi: &hir::ForeignItem<'_>) -> Option<HirId> {
+    fn insert(&mut self, tcx: TyCtxt<'_>, fi: &hir::ForeignItem<'_>) -> Option<hir::OwnerId> {
         let did = fi.owner_id.to_def_id();
         let instance = Instance::new(did, ty::List::identity_for_item(tcx, did));
         let name = Symbol::intern(tcx.symbol_name(instance).name);
-        if let Some(&hir_id) = self.seen_decls.get(&name) {
+        if let Some(&existing_id) = self.seen_decls.get(&name) {
             // Avoid updating the map with the new entry when we do find a collision. We want to
             // make sure we're always pointing to the first definition as the previous declaration.
             // This lets us avoid emitting "knock-on" diagnostics.
-            Some(hir_id)
+            Some(existing_id)
         } else {
-            self.seen_decls.insert(name, fi.hir_id())
+            self.seen_decls.insert(name, fi.owner_id)
         }
     }
 
@@ -2949,16 +2948,16 @@ fn structurally_same_type_impl<'tcx>(
 impl_lint_pass!(ClashingExternDeclarations => [CLASHING_EXTERN_DECLARATIONS]);
 
 impl<'tcx> LateLintPass<'tcx> for ClashingExternDeclarations {
+    #[instrument(level = "trace", skip(self, cx))]
     fn check_foreign_item(&mut self, cx: &LateContext<'tcx>, this_fi: &hir::ForeignItem<'_>) {
-        trace!("ClashingExternDeclarations: check_foreign_item: {:?}", this_fi);
         if let ForeignItemKind::Fn(..) = this_fi.kind {
             let tcx = cx.tcx;
-            if let Some(existing_hid) = self.insert(tcx, this_fi) {
-                let existing_decl_ty = tcx.type_of(tcx.hir().local_def_id(existing_hid));
+            if let Some(existing_did) = self.insert(tcx, this_fi) {
+                let existing_decl_ty = tcx.type_of(existing_did);
                 let this_decl_ty = tcx.type_of(this_fi.owner_id);
                 debug!(
                     "ClashingExternDeclarations: Comparing existing {:?}: {:?} to this {:?}: {:?}",
-                    existing_hid, existing_decl_ty, this_fi.owner_id, this_decl_ty
+                    existing_did, existing_decl_ty, this_fi.owner_id, this_decl_ty
                 );
                 // Check that the declarations match.
                 if !Self::structurally_same_type(
@@ -2967,7 +2966,7 @@ fn check_foreign_item(&mut self, cx: &LateContext<'tcx>, this_fi: &hir::ForeignI
                     this_decl_ty,
                     CItemKind::Declaration,
                 ) {
-                    let orig_fi = tcx.hir().expect_foreign_item(existing_hid.expect_owner());
+                    let orig_fi = tcx.hir().expect_foreign_item(existing_did);
                     let orig = Self::name_of_extern_decl(tcx, orig_fi);
 
                     // We want to ensure that we use spans for both decls that include where the
index b2a2656746eec8b45849ec4faf9ce905ef15ec69..b42878a02ee02985408d41e21ac7efd4aaf7392a 100644 (file)
@@ -66,13 +66,12 @@ fn with_lint_attrs<F>(&mut self, id: hir::HirId, f: F)
         self.context.last_node_with_lint_attrs = prev;
     }
 
-    fn with_param_env<F>(&mut self, id: hir::HirId, f: F)
+    fn with_param_env<F>(&mut self, id: hir::OwnerId, f: F)
     where
         F: FnOnce(&mut Self),
     {
         let old_param_env = self.context.param_env;
-        self.context.param_env =
-            self.context.tcx.param_env(self.context.tcx.hir().local_def_id(id));
+        self.context.param_env = self.context.tcx.param_env(id);
         f(self);
         self.context.param_env = old_param_env;
     }
@@ -132,7 +131,7 @@ fn visit_item(&mut self, it: &'tcx hir::Item<'tcx>) {
         let old_cached_typeck_results = self.context.cached_typeck_results.take();
         let old_enclosing_body = self.context.enclosing_body.take();
         self.with_lint_attrs(it.hir_id(), |cx| {
-            cx.with_param_env(it.hir_id(), |cx| {
+            cx.with_param_env(it.owner_id, |cx| {
                 lint_callback!(cx, check_item, it);
                 hir_visit::walk_item(cx, it);
                 lint_callback!(cx, check_item_post, it);
@@ -145,7 +144,7 @@ fn visit_item(&mut self, it: &'tcx hir::Item<'tcx>) {
 
     fn visit_foreign_item(&mut self, it: &'tcx hir::ForeignItem<'tcx>) {
         self.with_lint_attrs(it.hir_id(), |cx| {
-            cx.with_param_env(it.hir_id(), |cx| {
+            cx.with_param_env(it.owner_id, |cx| {
                 lint_callback!(cx, check_foreign_item, it);
                 hir_visit::walk_foreign_item(cx, it);
             });
@@ -180,7 +179,7 @@ fn visit_fn(
         decl: &'tcx hir::FnDecl<'tcx>,
         body_id: hir::BodyId,
         span: Span,
-        id: hir::HirId,
+        id: LocalDefId,
     ) {
         // Wrap in typeck results here, not just in visit_nested_body,
         // in order for `check_fn` to be able to use them.
@@ -268,7 +267,7 @@ fn visit_trait_item(&mut self, trait_item: &'tcx hir::TraitItem<'tcx>) {
         let generics = self.context.generics.take();
         self.context.generics = Some(&trait_item.generics);
         self.with_lint_attrs(trait_item.hir_id(), |cx| {
-            cx.with_param_env(trait_item.hir_id(), |cx| {
+            cx.with_param_env(trait_item.owner_id, |cx| {
                 lint_callback!(cx, check_trait_item, trait_item);
                 hir_visit::walk_trait_item(cx, trait_item);
             });
@@ -280,7 +279,7 @@ fn visit_impl_item(&mut self, impl_item: &'tcx hir::ImplItem<'tcx>) {
         let generics = self.context.generics.take();
         self.context.generics = Some(&impl_item.generics);
         self.with_lint_attrs(impl_item.hir_id(), |cx| {
-            cx.with_param_env(impl_item.hir_id(), |cx| {
+            cx.with_param_env(impl_item.owner_id, |cx| {
                 lint_callback!(cx, check_impl_item, impl_item);
                 hir_visit::walk_impl_item(cx, impl_item);
                 lint_callback!(cx, check_impl_item_post, impl_item);
index 74d234fabea0872467d98c5828b39e472ddc9e0f..71e2e66bdebc2786b0459478b5bfa7b54954a222 100644 (file)
@@ -10,8 +10,9 @@
 use rustc_hir::intravisit::FnKind;
 use rustc_hir::{GenericParamKind, PatKind};
 use rustc_middle::ty;
-use rustc_span::symbol::sym;
-use rustc_span::{symbol::Ident, BytePos, Span};
+use rustc_span::def_id::LocalDefId;
+use rustc_span::symbol::{sym, Ident};
+use rustc_span::{BytePos, Span};
 use rustc_target::spec::abi::Abi;
 
 #[derive(PartialEq)]
@@ -21,9 +22,8 @@ pub enum MethodLateContext {
     PlainImpl,
 }
 
-pub fn method_context(cx: &LateContext<'_>, id: hir::HirId) -> MethodLateContext {
-    let def_id = cx.tcx.hir().local_def_id(id);
-    let item = cx.tcx.associated_item(def_id);
+pub fn method_context(cx: &LateContext<'_>, id: LocalDefId) -> MethodLateContext {
+    let item = cx.tcx.associated_item(id);
     match item.container {
         ty::TraitContainer => MethodLateContext::TraitAutoImpl,
         ty::ImplContainer => match cx.tcx.impl_trait_ref(item.container_id(cx.tcx)) {
@@ -379,13 +379,13 @@ fn check_fn(
         _: &hir::FnDecl<'_>,
         _: &hir::Body<'_>,
         _: Span,
-        id: hir::HirId,
+        id: LocalDefId,
     ) {
-        let attrs = cx.tcx.hir().attrs(id);
         match &fk {
             FnKind::Method(ident, sig, ..) => match method_context(cx, id) {
                 MethodLateContext::PlainImpl => {
-                    if sig.header.abi != Abi::Rust && cx.sess().contains_name(attrs, sym::no_mangle)
+                    if sig.header.abi != Abi::Rust
+                        && cx.tcx.has_attr(id.to_def_id(), sym::no_mangle)
                     {
                         return;
                     }
@@ -398,7 +398,7 @@ fn check_fn(
             },
             FnKind::ItemFn(ident, _, header) => {
                 // Skip foreign-ABI #[no_mangle] functions (Issue #31924)
-                if header.abi != Abi::Rust && cx.sess().contains_name(attrs, sym::no_mangle) {
+                if header.abi != Abi::Rust && cx.tcx.has_attr(id.to_def_id(), sym::no_mangle) {
                     return;
                 }
                 self.check_snake_case(cx, "function", ident);
index 0bf01c4e567814f1f720de66362f310cf5c0f934..16964565b010328935a346de5052081512758374 100644 (file)
@@ -4,6 +4,7 @@
 use rustc_hir as hir;
 use rustc_session::lint::builtin::HardwiredLints;
 use rustc_session::lint::LintPass;
+use rustc_span::def_id::LocalDefId;
 use rustc_span::symbol::Ident;
 use rustc_span::Span;
 
@@ -36,7 +37,7 @@ fn check_fn(
                 b: &'tcx hir::FnDecl<'tcx>,
                 c: &'tcx hir::Body<'tcx>,
                 d: Span,
-                e: hir::HirId);
+                e: LocalDefId);
             fn check_trait_item(a: &'tcx hir::TraitItem<'tcx>);
             fn check_impl_item(a: &'tcx hir::ImplItem<'tcx>);
             fn check_impl_item_post(a: &'tcx hir::ImplItem<'tcx>);
index c32aeaa87223617dffee4ffbf8c7177fc48bddc4..b0a5d3674ad2795d75fdcefe041c68c2db19f7de 100644 (file)
@@ -14,6 +14,7 @@
 use rustc_middle::ty::layout::{IntegerExt, LayoutOf, SizeSkeleton};
 use rustc_middle::ty::subst::SubstsRef;
 use rustc_middle::ty::{self, AdtKind, DefIdTree, Ty, TyCtxt, TypeSuperVisitable, TypeVisitable};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map;
 use rustc_span::symbol::sym;
 use rustc_span::{Span, Symbol};
@@ -1224,8 +1225,7 @@ fn check_type_for_ffi_and_report_errors(
         }
     }
 
-    fn check_foreign_fn(&mut self, id: hir::HirId, decl: &hir::FnDecl<'_>) {
-        let def_id = self.cx.tcx.hir().local_def_id(id);
+    fn check_foreign_fn(&mut self, def_id: LocalDefId, decl: &hir::FnDecl<'_>) {
         let sig = self.cx.tcx.fn_sig(def_id).subst_identity();
         let sig = self.cx.tcx.erase_late_bound_regions(sig);
 
@@ -1239,9 +1239,8 @@ fn check_foreign_fn(&mut self, id: hir::HirId, decl: &hir::FnDecl<'_>) {
         }
     }
 
-    fn check_foreign_static(&mut self, id: hir::HirId, span: Span) {
-        let def_id = self.cx.tcx.hir().local_def_id(id);
-        let ty = self.cx.tcx.type_of(def_id);
+    fn check_foreign_static(&mut self, id: hir::OwnerId, span: Span) {
+        let ty = self.cx.tcx.type_of(id);
         self.check_type_for_ffi_and_report_errors(span, ty, true, false);
     }
 
@@ -1261,10 +1260,10 @@ fn check_foreign_item(&mut self, cx: &LateContext<'_>, it: &hir::ForeignItem<'_>
         if !vis.is_internal_abi(abi) {
             match it.kind {
                 hir::ForeignItemKind::Fn(ref decl, _, _) => {
-                    vis.check_foreign_fn(it.hir_id(), decl);
+                    vis.check_foreign_fn(it.owner_id.def_id, decl);
                 }
                 hir::ForeignItemKind::Static(ref ty, _) => {
-                    vis.check_foreign_static(it.hir_id(), ty.span);
+                    vis.check_foreign_static(it.owner_id, ty.span);
                 }
                 hir::ForeignItemKind::Type => (),
             }
@@ -1280,7 +1279,7 @@ fn check_fn(
         decl: &'tcx hir::FnDecl<'_>,
         _: &'tcx hir::Body<'_>,
         _: Span,
-        hir_id: hir::HirId,
+        id: LocalDefId,
     ) {
         use hir::intravisit::FnKind;
 
@@ -1292,7 +1291,7 @@ fn check_fn(
 
         let mut vis = ImproperCTypesVisitor { cx, mode: CItemKind::Definition };
         if !vis.is_internal_abi(abi) {
-            vis.check_foreign_fn(hir_id, decl);
+            vis.check_foreign_fn(id, decl);
         }
     }
 }
index 32338f9dfc5e3893c833eb754769309379b6f1e9..08098c9bb2a85c5a2c37b7a557e7b91fc5f4a2bc 100644 (file)
@@ -4,7 +4,10 @@
 };
 use fluent_bundle::{FluentBundle, FluentError, FluentResource};
 use fluent_syntax::{
-    ast::{Attribute, Entry, Identifier, Message},
+    ast::{
+        Attribute, Entry, Expression, Identifier, InlineExpression, Message, Pattern,
+        PatternElement,
+    },
     parser::ParserError,
 };
 use proc_macro::{Diagnostic, Level, Span};
@@ -185,9 +188,12 @@ pub(crate) fn fluent_messages(input: proc_macro::TokenStream) -> proc_macro::Tok
         };
 
         let mut constants = TokenStream::new();
+        let mut messagerefs = Vec::new();
         for entry in resource.entries() {
             let span = res.krate.span();
-            if let Entry::Message(Message { id: Identifier { name }, attributes, .. }) = entry {
+            if let Entry::Message(Message { id: Identifier { name }, attributes, value, .. }) =
+                entry
+            {
                 let _ = previous_defns.entry(name.to_string()).or_insert(path_span);
 
                 if name.contains('-') {
@@ -200,6 +206,18 @@ pub(crate) fn fluent_messages(input: proc_macro::TokenStream) -> proc_macro::Tok
                     .emit();
                 }
 
+                if let Some(Pattern { elements }) = value {
+                    for elt in elements {
+                        if let PatternElement::Placeable {
+                            expression:
+                                Expression::Inline(InlineExpression::MessageReference { id, .. }),
+                        } = elt
+                        {
+                            messagerefs.push((id.name, *name));
+                        }
+                    }
+                }
+
                 // Require that the message name starts with the crate name
                 // `hir_typeck_foo_bar` (in `hir_typeck.ftl`)
                 // `const_eval_baz` (in `const_eval.ftl`)
@@ -258,6 +276,18 @@ pub(crate) fn fluent_messages(input: proc_macro::TokenStream) -> proc_macro::Tok
             }
         }
 
+        for (mref, name) in messagerefs.into_iter() {
+            if !previous_defns.contains_key(mref) {
+                Diagnostic::spanned(
+                    path_span,
+                    Level::Error,
+                    format!("referenced message `{mref}` does not exist (in message `{name}`)"),
+                )
+                .help(&format!("you may have meant to use a variable reference (`{{${mref}}}`)"))
+                .emit();
+            }
+        }
+
         if let Err(errs) = bundle.add_resource(resource) {
             for e in errs {
                 match e {
index a72089338ee32b1aab683bd005aa625ca5951b39..29507ff3a86c1dc2f27e66027f67e46ceea53331 100644 (file)
@@ -1310,8 +1310,8 @@ fn encode_info_for_mod(&mut self, local_def_id: LocalDefId, md: &hir::Mod<'_>) {
                         hir::ItemKind::Struct(ref vdata, _) => {
                             yield item_id.owner_id.def_id.local_def_index;
                             // Encode constructors which take a separate slot in value namespace.
-                            if let Some(ctor_hir_id) = vdata.ctor_hir_id() {
-                                yield tcx.hir().local_def_id(ctor_hir_id).local_def_index;
+                            if let Some(ctor_def_id) = vdata.ctor_def_id() {
+                                yield ctor_def_id.local_def_index;
                             }
                         }
                         _ if tcx.def_key(item_id.owner_id.to_def_id()).get_opt_name().is_some() => {
@@ -1415,7 +1415,7 @@ fn encode_mir(&mut self) {
             if encode_opt {
                 record!(self.tables.optimized_mir[def_id.to_def_id()] <- tcx.optimized_mir(def_id));
 
-                if let DefKind::Generator = self.tcx.def_kind(def_id) {
+                if let DefKind::Generator = self.tcx.def_kind(def_id) && tcx.sess.opts.unstable_opts.drop_tracking_mir {
                     record!(self.tables.mir_generator_witnesses[def_id.to_def_id()] <- tcx.mir_generator_witnesses(def_id));
                 }
             }
index f816d614500a07b9322ae679745de27cb097fc98..72f4f6e649bcf178e51017fc2fb8a57bb81b52a0 100644 (file)
@@ -105,7 +105,7 @@ macro_rules! arena_types {
             // (during lowering) and the `librustc_middle` arena (for decoding MIR)
             [decode] asm_template: rustc_ast::InlineAsmTemplatePiece,
             [decode] used_trait_imports: rustc_data_structures::unord::UnordSet<rustc_hir::def_id::LocalDefId>,
-            [decode] is_late_bound_map: rustc_data_structures::fx::FxIndexSet<rustc_hir::def_id::LocalDefId>,
+            [decode] is_late_bound_map: rustc_data_structures::fx::FxIndexSet<rustc_hir::ItemLocalId>,
             [decode] impl_source: rustc_middle::traits::ImplSource<'tcx, ()>,
 
             [] dep_kind: rustc_middle::dep_graph::DepKindStruct<'tcx>,
index 9e63c2bd2216ff652f879dd787d551ce5a13471a..5bd6b0704426b667b4e0435cd4ac3bb30f5f66a8 100644 (file)
 use rustc_target::spec::abi::Abi;
 
 #[inline]
-pub fn associated_body(node: Node<'_>) -> Option<BodyId> {
+pub fn associated_body(node: Node<'_>) -> Option<(LocalDefId, BodyId)> {
     match node {
         Node::Item(Item {
+            owner_id,
             kind: ItemKind::Const(_, body) | ItemKind::Static(.., body) | ItemKind::Fn(.., body),
             ..
         })
         | Node::TraitItem(TraitItem {
+            owner_id,
             kind:
                 TraitItemKind::Const(_, Some(body)) | TraitItemKind::Fn(_, TraitFn::Provided(body)),
             ..
         })
         | Node::ImplItem(ImplItem {
+            owner_id,
             kind: ImplItemKind::Const(_, body) | ImplItemKind::Fn(_, body),
             ..
-        })
-        | Node::Expr(Expr { kind: ExprKind::Closure(Closure { body, .. }), .. }) => Some(*body),
+        }) => Some((owner_id.def_id, *body)),
+
+        Node::Expr(Expr { kind: ExprKind::Closure(Closure { def_id, body, .. }), .. }) => {
+            Some((*def_id, *body))
+        }
 
-        Node::AnonConst(constant) => Some(constant.body),
+        Node::AnonConst(constant) => Some((constant.def_id, constant.body)),
 
         _ => None,
     }
@@ -43,7 +49,7 @@ pub fn associated_body(node: Node<'_>) -> Option<BodyId> {
 
 fn is_body_owner(node: Node<'_>, hir_id: HirId) -> bool {
     match associated_body(node) {
-        Some(b) => b.hir_id == hir_id,
+        Some((_, b)) => b.hir_id == hir_id,
         None => false,
     }
 }
@@ -154,10 +160,6 @@ pub fn def_key(self, def_id: LocalDefId) -> DefKey {
         self.tcx.definitions_untracked().def_key(def_id)
     }
 
-    pub fn def_path_from_hir_id(self, id: HirId) -> Option<DefPath> {
-        self.opt_local_def_id(id).map(|def_id| self.def_path(def_id))
-    }
-
     pub fn def_path(self, def_id: LocalDefId) -> DefPath {
         // Accessing the DefPath is ok, since it is part of DefPathHash.
         self.tcx.definitions_untracked().def_path(def_id)
@@ -169,32 +171,6 @@ pub fn def_path_hash(self, def_id: LocalDefId) -> DefPathHash {
         self.tcx.definitions_untracked().def_path_hash(def_id)
     }
 
-    #[inline]
-    #[track_caller]
-    pub fn local_def_id(self, hir_id: HirId) -> LocalDefId {
-        self.opt_local_def_id(hir_id).unwrap_or_else(|| {
-            bug!(
-                "local_def_id: no entry for `{:?}`, which has a map of `{:?}`",
-                hir_id,
-                self.find(hir_id)
-            )
-        })
-    }
-
-    #[inline]
-    pub fn opt_local_def_id(self, hir_id: HirId) -> Option<LocalDefId> {
-        if hir_id.local_id == ItemLocalId::new(0) {
-            Some(hir_id.owner.def_id)
-        } else {
-            self.tcx
-                .hir_owner_nodes(hir_id.owner)
-                .as_owner()?
-                .local_id_to_def_id
-                .get(&hir_id.local_id)
-                .copied()
-        }
-    }
-
     #[inline]
     pub fn local_def_id_to_hir_id(self, def_id: LocalDefId) -> HirId {
         self.tcx.local_def_id_to_hir_id(def_id)
@@ -410,8 +386,8 @@ pub fn fn_sig_by_hir_id(self, hir_id: HirId) -> Option<&'hir FnSig<'hir>> {
     #[track_caller]
     pub fn enclosing_body_owner(self, hir_id: HirId) -> LocalDefId {
         for (_, node) in self.parent_iter(hir_id) {
-            if let Some(body) = associated_body(node) {
-                return self.body_owner_def_id(body);
+            if let Some((def_id, _)) = associated_body(node) {
+                return def_id;
             }
         }
 
@@ -427,14 +403,17 @@ pub fn body_owner(self, BodyId { hir_id }: BodyId) -> HirId {
         parent
     }
 
-    pub fn body_owner_def_id(self, id: BodyId) -> LocalDefId {
-        self.local_def_id(self.body_owner(id))
+    pub fn body_owner_def_id(self, BodyId { hir_id }: BodyId) -> LocalDefId {
+        let parent = self.parent_id(hir_id);
+        associated_body(self.get(parent)).unwrap().0
     }
 
     /// Given a `LocalDefId`, returns the `BodyId` associated with it,
     /// if the node is a body owner, otherwise returns `None`.
     pub fn maybe_body_owned_by(self, id: LocalDefId) -> Option<BodyId> {
-        self.find_by_def_id(id).and_then(associated_body)
+        let node = self.find_by_def_id(id)?;
+        let (_, body_id) = associated_body(node)?;
+        Some(body_id)
     }
 
     /// Given a body owner's id, returns the `BodyId` associated with it.
index 43583b5723e698f763e7c03f5a35b19b41e25108..6e130bbf7d8284403fccb3af90c7e1a229a08c86 100644 (file)
 use crate::mir::ConstraintCategory;
 use crate::ty::subst::GenericArg;
 use crate::ty::{self, BoundVar, List, Region, Ty, TyCtxt};
-use rustc_index::vec::IndexVec;
 use rustc_macros::HashStable;
 use smallvec::SmallVec;
-use std::iter;
 use std::ops::Index;
 
 /// A "canonicalized" type `V` is one where all free inference
@@ -62,23 +60,23 @@ fn try_fold_with<F: ty::FallibleTypeFolder<'tcx>>(
 /// vectors with the original values that were replaced by canonical
 /// variables. You will need to supply it later to instantiate the
 /// canonicalized query response.
-#[derive(Clone, Debug, PartialEq, Eq, Hash, TyDecodable, TyEncodable)]
+#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash, TyDecodable, TyEncodable)]
 #[derive(HashStable, TypeFoldable, TypeVisitable, Lift)]
 pub struct CanonicalVarValues<'tcx> {
-    pub var_values: IndexVec<BoundVar, GenericArg<'tcx>>,
+    pub var_values: ty::SubstsRef<'tcx>,
 }
 
 impl CanonicalVarValues<'_> {
     pub fn is_identity(&self) -> bool {
-        self.var_values.iter_enumerated().all(|(bv, arg)| match arg.unpack() {
+        self.var_values.iter().enumerate().all(|(bv, arg)| match arg.unpack() {
             ty::GenericArgKind::Lifetime(r) => {
-                matches!(*r, ty::ReLateBound(ty::INNERMOST, br) if br.var == bv)
+                matches!(*r, ty::ReLateBound(ty::INNERMOST, br) if br.var.as_usize() == bv)
             }
             ty::GenericArgKind::Type(ty) => {
-                matches!(*ty.kind(), ty::Bound(ty::INNERMOST, bt) if bt.var == bv)
+                matches!(*ty.kind(), ty::Bound(ty::INNERMOST, bt) if bt.var.as_usize() == bv)
             }
             ty::GenericArgKind::Const(ct) => {
-                matches!(ct.kind(), ty::ConstKind::Bound(ty::INNERMOST, bc) if bc == bv)
+                matches!(ct.kind(), ty::ConstKind::Bound(ty::INNERMOST, bc) if bc.as_usize() == bv)
             }
         })
     }
@@ -339,57 +337,57 @@ pub fn unchecked_rebind<W>(self, value: W) -> Canonical<'tcx, W> {
 }
 
 impl<'tcx> CanonicalVarValues<'tcx> {
+    // Given a list of canonical variables, construct a set of values which are
+    // the identity response.
+    pub fn make_identity(
+        tcx: TyCtxt<'tcx>,
+        infos: CanonicalVarInfos<'tcx>,
+    ) -> CanonicalVarValues<'tcx> {
+        CanonicalVarValues {
+            var_values: tcx.mk_substs(infos.iter().enumerate().map(
+                |(i, info)| -> ty::GenericArg<'tcx> {
+                    match info.kind {
+                        CanonicalVarKind::Ty(_) | CanonicalVarKind::PlaceholderTy(_) => tcx
+                            .mk_ty(ty::Bound(ty::INNERMOST, ty::BoundVar::from_usize(i).into()))
+                            .into(),
+                        CanonicalVarKind::Region(_) | CanonicalVarKind::PlaceholderRegion(_) => {
+                            let br = ty::BoundRegion {
+                                var: ty::BoundVar::from_usize(i),
+                                kind: ty::BrAnon(i as u32, None),
+                            };
+                            tcx.mk_region(ty::ReLateBound(ty::INNERMOST, br)).into()
+                        }
+                        CanonicalVarKind::Const(_, ty)
+                        | CanonicalVarKind::PlaceholderConst(_, ty) => tcx
+                            .mk_const(
+                                ty::ConstKind::Bound(ty::INNERMOST, ty::BoundVar::from_usize(i)),
+                                ty,
+                            )
+                            .into(),
+                    }
+                },
+            )),
+        }
+    }
+
     /// Creates dummy var values which should not be used in a
     /// canonical response.
     pub fn dummy() -> CanonicalVarValues<'tcx> {
-        CanonicalVarValues { var_values: Default::default() }
+        CanonicalVarValues { var_values: ty::List::empty() }
     }
 
     #[inline]
     pub fn len(&self) -> usize {
         self.var_values.len()
     }
-
-    /// Makes an identity substitution from this one: each bound var
-    /// is matched to the same bound var, preserving the original kinds.
-    /// For example, if we have:
-    /// `self.var_values == [Type(u32), Lifetime('a), Type(u64)]`
-    /// we'll return a substitution `subst` with:
-    /// `subst.var_values == [Type(^0), Lifetime(^1), Type(^2)]`.
-    pub fn make_identity(&self, tcx: TyCtxt<'tcx>) -> Self {
-        use crate::ty::subst::GenericArgKind;
-
-        CanonicalVarValues {
-            var_values: iter::zip(&self.var_values, 0..)
-                .map(|(kind, i)| match kind.unpack() {
-                    GenericArgKind::Type(..) => {
-                        tcx.mk_ty(ty::Bound(ty::INNERMOST, ty::BoundVar::from_u32(i).into())).into()
-                    }
-                    GenericArgKind::Lifetime(..) => {
-                        let br = ty::BoundRegion {
-                            var: ty::BoundVar::from_u32(i),
-                            kind: ty::BrAnon(i, None),
-                        };
-                        tcx.mk_region(ty::ReLateBound(ty::INNERMOST, br)).into()
-                    }
-                    GenericArgKind::Const(ct) => tcx
-                        .mk_const(
-                            ty::ConstKind::Bound(ty::INNERMOST, ty::BoundVar::from_u32(i)),
-                            ct.ty(),
-                        )
-                        .into(),
-                })
-                .collect(),
-        }
-    }
 }
 
 impl<'a, 'tcx> IntoIterator for &'a CanonicalVarValues<'tcx> {
     type Item = GenericArg<'tcx>;
-    type IntoIter = ::std::iter::Cloned<::std::slice::Iter<'a, GenericArg<'tcx>>>;
+    type IntoIter = ::std::iter::Copied<::std::slice::Iter<'a, GenericArg<'tcx>>>;
 
     fn into_iter(self) -> Self::IntoIter {
-        self.var_values.iter().cloned()
+        self.var_values.iter()
     }
 }
 
@@ -397,6 +395,6 @@ impl<'tcx> Index<BoundVar> for CanonicalVarValues<'tcx> {
     type Output = GenericArg<'tcx>;
 
     fn index(&self, value: BoundVar) -> &GenericArg<'tcx> {
-        &self.var_values[value]
+        &self.var_values[value.as_usize()]
     }
 }
index 63b8dd055bd5b413f4c02d3e6f3d91449dcd4230..bc3c38fdb1c2ad8427222062882f1f1823b5645d 100644 (file)
@@ -2506,7 +2506,7 @@ fn from_opt_const_arg_anon_const(
 
         let hir_id = tcx.hir().local_def_id_to_hir_id(def.did);
         let parent_substs = if let Some(parent_hir_id) = tcx.hir().opt_parent_id(hir_id) {
-            if let Some(parent_did) = tcx.hir().opt_local_def_id(parent_hir_id) {
+            if let Some(parent_did) = parent_hir_id.as_owner() {
                 InternalSubsts::identity_for_item(tcx, parent_did.to_def_id())
             } else {
                 tcx.mk_substs(Vec::<GenericArg<'tcx>>::new().into_iter())
index 887ee57157540e6f408de841d5825761978af356..fb1e3d233a2a5e8f00d29f4801a505dcd79b2933 100644 (file)
@@ -670,7 +670,7 @@ fn fn_span(tcx: TyCtxt<'_>, def_id: DefId) -> Span {
 
 fn hir_body(tcx: TyCtxt<'_>, def_id: DefId) -> Option<&rustc_hir::Body<'_>> {
     let hir_node = tcx.hir().get_if_local(def_id).expect("expected DefId is local");
-    hir::map::associated_body(hir_node).map(|fn_body_id| tcx.hir().body(fn_body_id))
+    hir::map::associated_body(hir_node).map(|(_, fn_body_id)| tcx.hir().body(fn_body_id))
 }
 
 fn escape_html(s: &str) -> String {
index e4df309e0089bb59eb4513264aeae2654ce8cecb..460a5147766b59e52515ad24581f96297ef83d27 100644 (file)
         Option<&'tcx FxHashMap<ItemLocalId, Region>> {
         desc { "looking up a named region" }
     }
-    query is_late_bound_map(_: LocalDefId) -> Option<&'tcx FxIndexSet<LocalDefId>> {
+    query is_late_bound_map(_: hir::OwnerId) -> Option<&'tcx FxIndexSet<ItemLocalId>> {
         desc { "testing if a region is late bound" }
     }
     /// For a given item's generic parameter, gets the default lifetimes to be used
index c680eeb1fdaf088ccb4888d9d165e0fe02033561..526df090a3cd90f1a7e9a77d30caac14a88d7b5e 100644 (file)
@@ -2157,10 +2157,7 @@ pub fn named_region(self, id: HirId) -> Option<resolve_lifetime::Region> {
     }
 
     pub fn is_late_bound(self, id: HirId) -> bool {
-        self.is_late_bound_map(id.owner.def_id).map_or(false, |set| {
-            let def_id = self.hir().local_def_id(id);
-            set.contains(&def_id)
-        })
+        self.is_late_bound_map(id.owner).map_or(false, |set| set.contains(&id.local_id))
     }
 
     pub fn late_bound_vars(self, id: HirId) -> &'tcx List<ty::BoundVariableKind> {
index 4af29fcbfb58645f30d3d74be4af30a4d3c4a53b..7001f81aa77502fea419f94595502fadbedd26b0 100644 (file)
@@ -31,7 +31,6 @@
 use rustc_ast as ast;
 use rustc_ast::node_id::NodeMap;
 use rustc_attr as attr;
-use rustc_data_structures::fingerprint::Fingerprint;
 use rustc_data_structures::fx::{FxHashMap, FxHashSet, FxIndexMap, FxIndexSet};
 use rustc_data_structures::intern::Interned;
 use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
@@ -453,18 +452,6 @@ pub struct CReaderCacheKey {
 #[rustc_pass_by_value]
 pub struct Ty<'tcx>(Interned<'tcx, WithCachedTypeInfo<TyKind<'tcx>>>);
 
-impl<'tcx> TyCtxt<'tcx> {
-    /// A "bool" type used in rustc_mir_transform unit tests when we
-    /// have not spun up a TyCtxt.
-    pub const BOOL_TY_FOR_UNIT_TESTING: Ty<'tcx> =
-        Ty(Interned::new_unchecked(&WithCachedTypeInfo {
-            internee: ty::Bool,
-            stable_hash: Fingerprint::ZERO,
-            flags: TypeFlags::empty(),
-            outer_exclusive_binder: DebruijnIndex::from_usize(0),
-        }));
-}
-
 impl ty::EarlyBoundRegion {
     /// Does this early bound region have a name? Early bound regions normally
     /// always have names except when using anonymous lifetimes (`'_`).
index 28b9bdf566018b06c4dab41fdb7b15d601dcb851..1be819ca610c7c644f7b3c9c9325f4c52bf81494 100644 (file)
@@ -118,6 +118,7 @@ fn copy<T: Copy>(x: &T) -> T {
 
 macro_rules! query_helper_param_ty {
     (DefId) => { impl IntoQueryParam<DefId> };
+    (LocalDefId) => { impl IntoQueryParam<LocalDefId> };
     ($K:ty) => { $K };
 }
 
@@ -418,6 +419,13 @@ fn into_query_param(self) -> P {
         }
     }
 
+    impl IntoQueryParam<LocalDefId> for OwnerId {
+        #[inline(always)]
+        fn into_query_param(self) -> LocalDefId {
+            self.def_id
+        }
+    }
+
     impl IntoQueryParam<DefId> for LocalDefId {
         #[inline(always)]
         fn into_query_param(self) -> DefId {
index b0d24af958dd7bed2f854c5d41c213412c518af6..ff88d00135173ec90be84ffdef34170ea2d1f005 100644 (file)
@@ -5,7 +5,6 @@
 use rustc_middle::thir::{FieldPat, Pat, PatKind};
 use rustc_middle::ty::{self, Ty, TyCtxt};
 use rustc_session::lint;
-use rustc_span::def_id::CRATE_DEF_ID;
 use rustc_span::Span;
 use rustc_trait_selection::traits::predicate_for_trait_def;
 use rustc_trait_selection::traits::query::evaluate_obligation::InferCtxtExt;
@@ -190,11 +189,10 @@ fn type_may_have_partial_eq_impl(&self, ty: Ty<'tcx>) -> bool {
         // using `PartialEq::eq` in this scenario in the past.)
         let partial_eq_trait_id =
             self.tcx().require_lang_item(hir::LangItem::PartialEq, Some(self.span));
-        let def_id = self.tcx().hir().opt_local_def_id(self.id).unwrap_or(CRATE_DEF_ID);
         let obligation: PredicateObligation<'_> = predicate_for_trait_def(
             self.tcx(),
             self.param_env,
-            ObligationCause::misc(self.span, def_id),
+            ObligationCause::misc(self.span, self.id.owner.def_id),
             partial_eq_trait_id,
             0,
             [ty, ty],
index adf6ae4c7270fbe37b642bb26e738d7cb1063354..9f006a76162a6be007b2aea6c2dffa94f05a0e39 100644 (file)
@@ -445,7 +445,7 @@ fn visit_fn(
         _fd: &'tcx hir::FnDecl<'tcx>,
         b: hir::BodyId,
         _s: rustc_span::Span,
-        _id: HirId,
+        _id: LocalDefId,
     ) {
         if matches!(fk, intravisit::FnKind::Closure) {
             self.visit_body(self.tcx.hir().body(b))
index 1468afc64563dc20bba1ea5e4e2f062918042d99..9a617159813caeca77f5342ffebcf714a5b9643b 100644 (file)
@@ -540,7 +540,8 @@ fn fn_sig_and_body(
     // FIXME(#79625): Consider improving MIR to provide the information needed, to avoid going back
     // to HIR for it.
     let hir_node = tcx.hir().get_if_local(def_id).expect("expected DefId is local");
-    let fn_body_id = hir::map::associated_body(hir_node).expect("HIR node is a function with body");
+    let (_, fn_body_id) =
+        hir::map::associated_body(hir_node).expect("HIR node is a function with body");
     (hir_node.fn_sig(), tcx.hir().body(fn_body_id))
 }
 
index e8871ff37f24ab2d3e67740fc2ffd4f8d354b9cf..a9fd95f45412f587fca98fcb66e1cf602126e4a9 100644 (file)
@@ -1390,6 +1390,7 @@ pub(crate) fn mir_generator_witnesses<'tcx>(
     tcx: TyCtxt<'tcx>,
     def_id: DefId,
 ) -> GeneratorLayout<'tcx> {
+    assert!(tcx.sess.opts.unstable_opts.drop_tracking_mir);
     let def_id = def_id.expect_local();
 
     let (body, _) = tcx.mir_promoted(ty::WithOptConstParam::unknown(def_id));
@@ -1400,15 +1401,8 @@ pub(crate) fn mir_generator_witnesses<'tcx>(
     let gen_ty = body.local_decls[ty::CAPTURE_STRUCT_LOCAL].ty;
 
     // Get the interior types and substs which typeck computed
-    let (upvars, interior, movable) = match *gen_ty.kind() {
-        ty::Generator(_, substs, movability) => {
-            let substs = substs.as_generator();
-            (
-                substs.upvar_tys().collect::<Vec<_>>(),
-                substs.witness(),
-                movability == hir::Movability::Movable,
-            )
-        }
+    let movable = match *gen_ty.kind() {
+        ty::Generator(_, _, movability) => movability == hir::Movability::Movable,
         _ => span_bug!(body.span, "unexpected generator type {}", gen_ty),
     };
 
@@ -1422,11 +1416,7 @@ pub(crate) fn mir_generator_witnesses<'tcx>(
     // `storage_liveness` tells us which locals have live storage at suspension points
     let (_, generator_layout, _) = compute_layout(tcx, liveness_info, body);
 
-    if tcx.sess.opts.unstable_opts.drop_tracking_mir {
-        check_suspend_tys(tcx, &generator_layout, &body);
-    } else {
-        sanitize_witness(tcx, body, interior, upvars, &generator_layout);
-    }
+    check_suspend_tys(tcx, &generator_layout, &body);
 
     generator_layout
 }
@@ -1444,10 +1434,15 @@ fn run_pass(&self, tcx: TyCtxt<'tcx>, body: &mut Body<'tcx>) {
         let gen_ty = body.local_decls.raw[1].ty;
 
         // Get the discriminant type and substs which typeck computed
-        let (discr_ty, movable) = match *gen_ty.kind() {
+        let (discr_ty, upvars, interior, movable) = match *gen_ty.kind() {
             ty::Generator(_, substs, movability) => {
                 let substs = substs.as_generator();
-                (substs.discr_ty(tcx), movability == hir::Movability::Movable)
+                (
+                    substs.discr_ty(tcx),
+                    substs.upvar_tys().collect::<Vec<_>>(),
+                    substs.witness(),
+                    movability == hir::Movability::Movable,
+                )
             }
             _ => {
                 tcx.sess
@@ -1524,6 +1519,12 @@ fn run_pass(&self, tcx: TyCtxt<'tcx>, body: &mut Body<'tcx>) {
         // `storage_liveness` tells us which locals have live storage at suspension points
         let (remap, layout, storage_liveness) = compute_layout(tcx, liveness_info, body);
 
+        if tcx.sess.opts.unstable_opts.validate_mir
+            && !tcx.sess.opts.unstable_opts.drop_tracking_mir
+        {
+            sanitize_witness(tcx, body, interior, upvars, &layout);
+        }
+
         let can_return = can_return(tcx, body, tcx.param_env(body.source.def_id()));
 
         // Run the transformation which converts Places from Local to generator struct
index fe3d5b1cce4589470872382c17aa82a06d77af5f..fcb09fa02dd2a393cfc20025f942692200a5107b 100644 (file)
@@ -426,7 +426,7 @@ fn mir_drops_elaborated_and_const_checked(
         return tcx.mir_drops_elaborated_and_const_checked(def);
     }
 
-    if tcx.generator_kind(def.did).is_some() {
+    if tcx.generator_kind(def.did).is_some() && tcx.sess.opts.unstable_opts.drop_tracking_mir {
         tcx.ensure().mir_generator_witnesses(def.did);
     }
     let mir_borrowck = tcx.mir_borrowck_opt_const_arg(def);
diff --git a/compiler/rustc_parse/src/lexer/diagnostics.rs b/compiler/rustc_parse/src/lexer/diagnostics.rs
new file mode 100644 (file)
index 0000000..386bf02
--- /dev/null
@@ -0,0 +1,119 @@
+use super::UnmatchedBrace;
+use rustc_ast::token::Delimiter;
+use rustc_errors::Diagnostic;
+use rustc_span::source_map::SourceMap;
+use rustc_span::Span;
+
+#[derive(Default)]
+pub struct TokenTreeDiagInfo {
+    /// Stack of open delimiters and their spans. Used for error message.
+    pub open_braces: Vec<(Delimiter, Span)>,
+    pub unmatched_braces: Vec<UnmatchedBrace>,
+
+    /// Used only for error recovery when arriving to EOF with mismatched braces.
+    pub last_unclosed_found_span: Option<Span>,
+
+    /// Collect empty block spans that might have been auto-inserted by editors.
+    pub empty_block_spans: Vec<Span>,
+
+    /// Collect the spans of braces (Open, Close). Used only
+    /// for detecting if blocks are empty and only braces.
+    pub matching_block_spans: Vec<(Span, Span)>,
+}
+
+pub fn same_identation_level(sm: &SourceMap, open_sp: Span, close_sp: Span) -> bool {
+    match (sm.span_to_margin(open_sp), sm.span_to_margin(close_sp)) {
+        (Some(open_padding), Some(close_padding)) => open_padding == close_padding,
+        _ => false,
+    }
+}
+
+// When we get a `)` or `]` for `{`, we should emit help message here
+// it's more friendly compared to report `unmatched error` in later phase
+pub fn report_missing_open_delim(
+    err: &mut Diagnostic,
+    unmatched_braces: &[UnmatchedBrace],
+) -> bool {
+    let mut reported_missing_open = false;
+    for unmatch_brace in unmatched_braces.iter() {
+        if let Some(delim) = unmatch_brace.found_delim
+            && matches!(delim, Delimiter::Parenthesis | Delimiter::Bracket)
+        {
+            let missed_open = match delim {
+                Delimiter::Parenthesis => "(",
+                Delimiter::Bracket => "[",
+                _ => unreachable!(),
+            };
+            err.span_label(
+                unmatch_brace.found_span.shrink_to_lo(),
+                format!("missing open `{}` for this delimiter", missed_open),
+            );
+            reported_missing_open = true;
+        }
+    }
+    reported_missing_open
+}
+
+pub fn report_suspicious_mismatch_block(
+    err: &mut Diagnostic,
+    diag_info: &TokenTreeDiagInfo,
+    sm: &SourceMap,
+    delim: Delimiter,
+) {
+    if report_missing_open_delim(err, &diag_info.unmatched_braces) {
+        return;
+    }
+
+    let mut matched_spans: Vec<(Span, bool)> = diag_info
+        .matching_block_spans
+        .iter()
+        .map(|&(open, close)| (open.with_hi(close.lo()), same_identation_level(sm, open, close)))
+        .collect();
+
+    // sort by `lo`, so the large block spans in the front
+    matched_spans.sort_by(|a, b| a.0.lo().cmp(&b.0.lo()));
+
+    // We use larger block whose identation is well to cover those inner mismatched blocks
+    // O(N^2) here, but we are on error reporting path, so it is fine
+    for i in 0..matched_spans.len() {
+        let (block_span, same_ident) = matched_spans[i];
+        if same_ident {
+            for j in i + 1..matched_spans.len() {
+                let (inner_block, inner_same_ident) = matched_spans[j];
+                if block_span.contains(inner_block) && !inner_same_ident {
+                    matched_spans[j] = (inner_block, true);
+                }
+            }
+        }
+    }
+
+    // Find the inner-most span candidate for final report
+    let candidate_span =
+        matched_spans.into_iter().rev().find(|&(_, same_ident)| !same_ident).map(|(span, _)| span);
+
+    if let Some(block_span) = candidate_span {
+        err.span_label(block_span.shrink_to_lo(), "this delimiter might not be properly closed...");
+        err.span_label(
+            block_span.shrink_to_hi(),
+            "...as it matches this but it has different indentation",
+        );
+
+        // If there is a empty block in the mismatched span, note it
+        if delim == Delimiter::Brace {
+            for span in diag_info.empty_block_spans.iter() {
+                if block_span.contains(*span) {
+                    err.span_label(*span, "block is empty, you might have not meant to close it");
+                    break;
+                }
+            }
+        }
+    } else {
+        // If there is no suspicious span, give the last properly closed block may help
+        if let Some(parent) = diag_info.matching_block_spans.last()
+            && diag_info.open_braces.last().is_none()
+            && diag_info.empty_block_spans.iter().all(|&sp| sp != parent.0.to(parent.1)) {
+                err.span_label(parent.0, "this opening brace...");
+                err.span_label(parent.1, "...matches this closing brace");
+        }
+    }
+}
index 9fe8d9836ba60ca8ecfb16eea7d0383617931c0e..e957224a03377805bbfb7fa666d60df3c29cb607 100644 (file)
@@ -17,6 +17,7 @@
 use rustc_span::symbol::{sym, Symbol};
 use rustc_span::{edition::Edition, BytePos, Pos, Span};
 
+mod diagnostics;
 mod tokentrees;
 mod unescape_error_reporting;
 mod unicode_chars;
index b2701817d489ba89c22e8c5692b0e906229bcc36..0de8f79112c654033ef64b8efe0441ff0cb152cf 100644 (file)
@@ -1,29 +1,18 @@
+use super::diagnostics::report_suspicious_mismatch_block;
+use super::diagnostics::same_identation_level;
+use super::diagnostics::TokenTreeDiagInfo;
 use super::{StringReader, UnmatchedBrace};
 use rustc_ast::token::{self, Delimiter, Token};
 use rustc_ast::tokenstream::{DelimSpan, Spacing, TokenStream, TokenTree};
 use rustc_ast_pretty::pprust::token_to_string;
-use rustc_data_structures::fx::FxHashMap;
 use rustc_errors::{PErr, PResult};
-use rustc_span::Span;
 
 pub(super) struct TokenTreesReader<'a> {
     string_reader: StringReader<'a>,
     /// The "next" token, which has been obtained from the `StringReader` but
     /// not yet handled by the `TokenTreesReader`.
     token: Token,
-    /// Stack of open delimiters and their spans. Used for error message.
-    open_braces: Vec<(Delimiter, Span)>,
-    unmatched_braces: Vec<UnmatchedBrace>,
-    /// The type and spans for all braces
-    ///
-    /// Used only for error recovery when arriving to EOF with mismatched braces.
-    matching_delim_spans: Vec<(Delimiter, Span, Span)>,
-    last_unclosed_found_span: Option<Span>,
-    /// Collect empty block spans that might have been auto-inserted by editors.
-    last_delim_empty_block_spans: FxHashMap<Delimiter, Span>,
-    /// Collect the spans of braces (Open, Close). Used only
-    /// for detecting if blocks are empty and only braces.
-    matching_block_spans: Vec<(Span, Span)>,
+    diag_info: TokenTreeDiagInfo,
 }
 
 impl<'a> TokenTreesReader<'a> {
@@ -33,15 +22,10 @@ pub(super) fn parse_all_token_trees(
         let mut tt_reader = TokenTreesReader {
             string_reader,
             token: Token::dummy(),
-            open_braces: Vec::new(),
-            unmatched_braces: Vec::new(),
-            matching_delim_spans: Vec::new(),
-            last_unclosed_found_span: None,
-            last_delim_empty_block_spans: FxHashMap::default(),
-            matching_block_spans: Vec::new(),
+            diag_info: TokenTreeDiagInfo::default(),
         };
         let res = tt_reader.parse_token_trees(/* is_delimited */ false);
-        (res, tt_reader.unmatched_braces)
+        (res, tt_reader.diag_info.unmatched_braces)
     }
 
     // Parse a stream of tokens into a list of `TokenTree`s.
@@ -92,9 +76,9 @@ fn parse_token_trees(&mut self, is_delimited: bool) -> PResult<'a, TokenStream>
     fn eof_err(&mut self) -> PErr<'a> {
         let msg = "this file contains an unclosed delimiter";
         let mut err = self.string_reader.sess.span_diagnostic.struct_span_err(self.token.span, msg);
-        for &(_, sp) in &self.open_braces {
+        for &(_, sp) in &self.diag_info.open_braces {
             err.span_label(sp, "unclosed delimiter");
-            self.unmatched_braces.push(UnmatchedBrace {
+            self.diag_info.unmatched_braces.push(UnmatchedBrace {
                 expected_delim: Delimiter::Brace,
                 found_delim: None,
                 found_span: self.token.span,
@@ -103,23 +87,13 @@ fn eof_err(&mut self) -> PErr<'a> {
             });
         }
 
-        if let Some((delim, _)) = self.open_braces.last() {
-            if let Some((_, open_sp, close_sp)) =
-                self.matching_delim_spans.iter().find(|(d, open_sp, close_sp)| {
-                    let sm = self.string_reader.sess.source_map();
-                    if let Some(close_padding) = sm.span_to_margin(*close_sp) {
-                        if let Some(open_padding) = sm.span_to_margin(*open_sp) {
-                            return delim == d && close_padding != open_padding;
-                        }
-                    }
-                    false
-                })
-            // these are in reverse order as they get inserted on close, but
-            {
-                // we want the last open/first close
-                err.span_label(*open_sp, "this delimiter might not be properly closed...");
-                err.span_label(*close_sp, "...as it matches this but it has different indentation");
-            }
+        if let Some((delim, _)) = self.diag_info.open_braces.last() {
+            report_suspicious_mismatch_block(
+                &mut err,
+                &self.diag_info,
+                &self.string_reader.sess.source_map(),
+                *delim,
+            )
         }
         err
     }
@@ -128,7 +102,7 @@ fn parse_token_tree_open_delim(&mut self, open_delim: Delimiter) -> TokenTree {
         // The span for beginning of the delimited section
         let pre_span = self.token.span;
 
-        self.open_braces.push((open_delim, self.token.span));
+        self.diag_info.open_braces.push((open_delim, self.token.span));
 
         // Parse the token trees within the delimiters.
         // We stop at any delimiter so we can try to recover if the user
@@ -137,35 +111,29 @@ fn parse_token_tree_open_delim(&mut self, open_delim: Delimiter) -> TokenTree {
 
         // Expand to cover the entire delimited token tree
         let delim_span = DelimSpan::from_pair(pre_span, self.token.span);
+        let sm = self.string_reader.sess.source_map();
 
         match self.token.kind {
             // Correct delimiter.
             token::CloseDelim(close_delim) if close_delim == open_delim => {
-                let (open_brace, open_brace_span) = self.open_braces.pop().unwrap();
+                let (open_brace, open_brace_span) = self.diag_info.open_braces.pop().unwrap();
                 let close_brace_span = self.token.span;
 
-                if tts.is_empty() {
+                if tts.is_empty() && close_delim == Delimiter::Brace {
                     let empty_block_span = open_brace_span.to(close_brace_span);
-                    let sm = self.string_reader.sess.source_map();
                     if !sm.is_multiline(empty_block_span) {
                         // Only track if the block is in the form of `{}`, otherwise it is
                         // likely that it was written on purpose.
-                        self.last_delim_empty_block_spans.insert(open_delim, empty_block_span);
+                        self.diag_info.empty_block_spans.push(empty_block_span);
                     }
                 }
 
-                //only add braces
+                // only add braces
                 if let (Delimiter::Brace, Delimiter::Brace) = (open_brace, open_delim) {
-                    self.matching_block_spans.push((open_brace_span, close_brace_span));
+                    // Add all the matching spans, we will sort by span later
+                    self.diag_info.matching_block_spans.push((open_brace_span, close_brace_span));
                 }
 
-                if self.open_braces.is_empty() {
-                    // Clear up these spans to avoid suggesting them as we've found
-                    // properly matched delimiters so far for an entire block.
-                    self.matching_delim_spans.clear();
-                } else {
-                    self.matching_delim_spans.push((open_brace, open_brace_span, close_brace_span));
-                }
                 // Move past the closing delimiter.
                 self.token = self.string_reader.next_token().0;
             }
@@ -174,28 +142,25 @@ fn parse_token_tree_open_delim(&mut self, open_delim: Delimiter) -> TokenTree {
                 let mut unclosed_delimiter = None;
                 let mut candidate = None;
 
-                if self.last_unclosed_found_span != Some(self.token.span) {
+                if self.diag_info.last_unclosed_found_span != Some(self.token.span) {
                     // do not complain about the same unclosed delimiter multiple times
-                    self.last_unclosed_found_span = Some(self.token.span);
+                    self.diag_info.last_unclosed_found_span = Some(self.token.span);
                     // This is a conservative error: only report the last unclosed
                     // delimiter. The previous unclosed delimiters could actually be
                     // closed! The parser just hasn't gotten to them yet.
-                    if let Some(&(_, sp)) = self.open_braces.last() {
+                    if let Some(&(_, sp)) = self.diag_info.open_braces.last() {
                         unclosed_delimiter = Some(sp);
                     };
-                    let sm = self.string_reader.sess.source_map();
-                    if let Some(current_padding) = sm.span_to_margin(self.token.span) {
-                        for (brace, brace_span) in &self.open_braces {
-                            if let Some(padding) = sm.span_to_margin(*brace_span) {
-                                // high likelihood of these two corresponding
-                                if current_padding == padding && brace == &close_delim {
-                                    candidate = Some(*brace_span);
-                                }
-                            }
+                    for (brace, brace_span) in &self.diag_info.open_braces {
+                        if same_identation_level(&sm, self.token.span, *brace_span)
+                            && brace == &close_delim
+                        {
+                            // high likelihood of these two corresponding
+                            candidate = Some(*brace_span);
                         }
                     }
-                    let (tok, _) = self.open_braces.pop().unwrap();
-                    self.unmatched_braces.push(UnmatchedBrace {
+                    let (tok, _) = self.diag_info.open_braces.pop().unwrap();
+                    self.diag_info.unmatched_braces.push(UnmatchedBrace {
                         expected_delim: tok,
                         found_delim: Some(close_delim),
                         found_span: self.token.span,
@@ -203,7 +168,7 @@ fn parse_token_tree_open_delim(&mut self, open_delim: Delimiter) -> TokenTree {
                         candidate_span: candidate,
                     });
                 } else {
-                    self.open_braces.pop();
+                    self.diag_info.open_braces.pop();
                 }
 
                 // If the incorrect delimiter matches an earlier opening
@@ -213,7 +178,7 @@ fn parse_token_tree_open_delim(&mut self, open_delim: Delimiter) -> TokenTree {
                 // fn foo() {
                 //     bar(baz(
                 // }  // Incorrect delimiter but matches the earlier `{`
-                if !self.open_braces.iter().any(|&(b, _)| b == close_delim) {
+                if !self.diag_info.open_braces.iter().any(|&(b, _)| b == close_delim) {
                     self.token = self.string_reader.next_token().0;
                 }
             }
@@ -236,22 +201,12 @@ fn close_delim_err(&mut self, delim: Delimiter) -> PErr<'a> {
         let mut err =
             self.string_reader.sess.span_diagnostic.struct_span_err(self.token.span, &msg);
 
-        // Braces are added at the end, so the last element is the biggest block
-        if let Some(parent) = self.matching_block_spans.last() {
-            if let Some(span) = self.last_delim_empty_block_spans.remove(&delim) {
-                // Check if the (empty block) is in the last properly closed block
-                if (parent.0.to(parent.1)).contains(span) {
-                    err.span_label(span, "block is empty, you might have not meant to close it");
-                } else {
-                    err.span_label(parent.0, "this opening brace...");
-                    err.span_label(parent.1, "...matches this closing brace");
-                }
-            } else {
-                err.span_label(parent.0, "this opening brace...");
-                err.span_label(parent.1, "...matches this closing brace");
-            }
-        }
-
+        report_suspicious_mismatch_block(
+            &mut err,
+            &self.diag_info,
+            &self.string_reader.sess.source_map(),
+            delim,
+        );
         err.span_label(self.token.span, "unexpected closing delimiter");
         err
     }
index f4673c332b88702778ffe77a8e800ba0cc696e7b..25cc65ba04c8b7ca083695b7426179bf41208939 100644 (file)
@@ -453,7 +453,9 @@ fn check_cmse_nonsecure_entry(
     /// Debugging aid for `object_lifetime_default` query.
     fn check_object_lifetime_default(&self, hir_id: HirId) {
         let tcx = self.tcx;
-        if let Some(generics) = tcx.hir().get_generics(tcx.hir().local_def_id(hir_id)) {
+        if let Some(owner_id) = hir_id.as_owner()
+            && let Some(generics) = tcx.hir().get_generics(owner_id.def_id)
+        {
             for p in generics.params {
                 let hir::GenericParamKind::Type { .. } = p.kind else { continue };
                 let default = tcx.object_lifetime_default(p.def_id);
@@ -1943,7 +1945,7 @@ fn check_rustc_allow_const_fn_unstable(
     ) -> bool {
         match target {
             Target::Fn | Target::Method(_)
-                if self.tcx.is_const_fn_raw(self.tcx.hir().local_def_id(hir_id).to_def_id()) =>
+                if self.tcx.is_const_fn_raw(hir_id.expect_owner().to_def_id()) =>
             {
                 true
             }
index 94171b4b0c8f1b5ffa6021d2bf3a68c035aceb5c..127acb46e9242c36de20f6d42ddb098020d5445c 100644 (file)
@@ -451,29 +451,23 @@ fn visit_anon_const(&mut self, c: &'tcx hir::AnonConst) {
         // referenced by it should be considered as used.
         let in_pat = mem::replace(&mut self.in_pat, false);
 
-        self.live_symbols.insert(self.tcx.hir().local_def_id(c.hir_id));
+        self.live_symbols.insert(c.def_id);
         intravisit::walk_anon_const(self, c);
 
         self.in_pat = in_pat;
     }
 }
 
-fn has_allow_dead_code_or_lang_attr_helper(
-    tcx: TyCtxt<'_>,
-    id: hir::HirId,
-    lint: &'static lint::Lint,
-) -> bool {
-    let attrs = tcx.hir().attrs(id);
-    if tcx.sess.contains_name(attrs, sym::lang) {
+fn has_allow_dead_code_or_lang_attr(tcx: TyCtxt<'_>, def_id: LocalDefId) -> bool {
+    if tcx.has_attr(def_id.to_def_id(), sym::lang) {
         return true;
     }
 
     // Stable attribute for #[lang = "panic_impl"]
-    if tcx.sess.contains_name(attrs, sym::panic_handler) {
+    if tcx.has_attr(def_id.to_def_id(), sym::panic_handler) {
         return true;
     }
 
-    let def_id = tcx.hir().local_def_id(id);
     if tcx.def_kind(def_id).has_codegen_attrs() {
         let cg_attrs = tcx.codegen_fn_attrs(def_id);
 
@@ -487,11 +481,8 @@ fn has_allow_dead_code_or_lang_attr_helper(
         }
     }
 
-    tcx.lint_level_at_node(lint, id).0 == lint::Allow
-}
-
-fn has_allow_dead_code_or_lang_attr(tcx: TyCtxt<'_>, id: hir::HirId) -> bool {
-    has_allow_dead_code_or_lang_attr_helper(tcx, id, lint::builtin::DEAD_CODE)
+    let hir_id = tcx.hir().local_def_id_to_hir_id(def_id);
+    tcx.lint_level_at_node(lint::builtin::DEAD_CODE, hir_id).0 == lint::Allow
 }
 
 // These check_* functions seeds items that
@@ -513,7 +504,7 @@ fn check_item<'tcx>(
     struct_constructors: &mut FxHashMap<LocalDefId, LocalDefId>,
     id: hir::ItemId,
 ) {
-    let allow_dead_code = has_allow_dead_code_or_lang_attr(tcx, id.hir_id());
+    let allow_dead_code = has_allow_dead_code_or_lang_attr(tcx, id.owner_id.def_id);
     if allow_dead_code {
         worklist.push(id.owner_id.def_id);
     }
@@ -548,9 +539,7 @@ fn check_item<'tcx>(
 
             // And we access the Map here to get HirId from LocalDefId
             for id in local_def_ids {
-                if of_trait.is_some()
-                    || has_allow_dead_code_or_lang_attr(tcx, tcx.hir().local_def_id_to_hir_id(id))
-                {
+                if of_trait.is_some() || has_allow_dead_code_or_lang_attr(tcx, id) {
                     worklist.push(id);
                 }
             }
@@ -558,9 +547,9 @@ fn check_item<'tcx>(
         DefKind::Struct => {
             let item = tcx.hir().item(id);
             if let hir::ItemKind::Struct(ref variant_data, _) = item.kind
-                && let Some(ctor_hir_id) = variant_data.ctor_hir_id()
+                && let Some(ctor_def_id) = variant_data.ctor_def_id()
             {
-                struct_constructors.insert(tcx.hir().local_def_id(ctor_hir_id), item.owner_id.def_id);
+                struct_constructors.insert(ctor_def_id, item.owner_id.def_id);
             }
         }
         DefKind::GlobalAsm => {
@@ -576,7 +565,7 @@ fn check_trait_item(tcx: TyCtxt<'_>, worklist: &mut Vec<LocalDefId>, id: hir::Tr
     if matches!(tcx.def_kind(id.owner_id), DefKind::AssocConst | DefKind::AssocFn) {
         let trait_item = tcx.hir().trait_item(id);
         if matches!(trait_item.kind, Const(_, Some(_)) | Fn(_, hir::TraitFn::Provided(_)))
-            && has_allow_dead_code_or_lang_attr(tcx, trait_item.hir_id())
+            && has_allow_dead_code_or_lang_attr(tcx, trait_item.owner_id.def_id)
         {
             worklist.push(trait_item.owner_id.def_id);
         }
@@ -585,7 +574,7 @@ fn check_trait_item(tcx: TyCtxt<'_>, worklist: &mut Vec<LocalDefId>, id: hir::Tr
 
 fn check_foreign_item(tcx: TyCtxt<'_>, worklist: &mut Vec<LocalDefId>, id: hir::ForeignItemId) {
     if matches!(tcx.def_kind(id.owner_id), DefKind::Static(_) | DefKind::Fn)
-        && has_allow_dead_code_or_lang_attr(tcx, id.hir_id())
+        && has_allow_dead_code_or_lang_attr(tcx, id.owner_id.def_id)
     {
         worklist.push(id.owner_id.def_id);
     }
@@ -806,8 +795,7 @@ fn check_definition(&mut self, def_id: LocalDefId) {
         if self.live_symbols.contains(&def_id) {
             return;
         }
-        let hir_id = self.tcx.hir().local_def_id_to_hir_id(def_id);
-        if has_allow_dead_code_or_lang_attr(self.tcx, hir_id) {
+        if has_allow_dead_code_or_lang_attr(self.tcx, def_id) {
             return;
         }
         let Some(name) = self.tcx.opt_item_name(def_id.to_def_id()) else {
index d1b896e940e6e7d6f054b22c2ac7bc0f98e8b592..51a19c8e3c02ba227bfdb3b792c208a5ada546e0 100644 (file)
@@ -12,6 +12,7 @@
 use rustc_middle::hir::map::Map;
 use rustc_middle::ty::TyCtxt;
 use rustc_middle::util::common::to_readable_str;
+use rustc_span::def_id::LocalDefId;
 use rustc_span::Span;
 
 #[derive(Copy, Clone, PartialEq, Eq, Hash)]
@@ -363,7 +364,7 @@ fn visit_fn(
         fd: &'v hir::FnDecl<'v>,
         b: hir::BodyId,
         _: Span,
-        id: hir::HirId,
+        id: LocalDefId,
     ) {
         self.record("FnDecl", Id::None, fd);
         hir_visit::walk_fn(self, fk, fd, b, id)
index 9a40b847d8552ebd9800fa42f6a6791b17562f73..fdd0e5dab705cb17691d0a45b489f6d54dbcaf1c 100644 (file)
@@ -15,9 +15,9 @@
 
 use rustc_hir as hir;
 use rustc_hir::def::DefKind;
-use rustc_hir::def_id::DefId;
+use rustc_hir::def_id::{DefId, LocalDefId};
 use rustc_hir::lang_items::{extract, GenericRequirement};
-use rustc_hir::{HirId, LangItem, LanguageItems, Target};
+use rustc_hir::{LangItem, LanguageItems, Target};
 use rustc_middle::ty::TyCtxt;
 use rustc_session::cstore::ExternCrate;
 use rustc_span::{symbol::kw::Empty, Span};
@@ -40,13 +40,13 @@ fn new(tcx: TyCtxt<'tcx>) -> LanguageItemCollector<'tcx> {
         LanguageItemCollector { tcx, items: LanguageItems::new() }
     }
 
-    fn check_for_lang(&mut self, actual_target: Target, hir_id: HirId) {
-        let attrs = self.tcx.hir().attrs(hir_id);
+    fn check_for_lang(&mut self, actual_target: Target, def_id: LocalDefId) {
+        let attrs = self.tcx.hir().attrs(self.tcx.hir().local_def_id_to_hir_id(def_id));
         if let Some((name, span)) = extract(&attrs) {
             match LangItem::from_name(name) {
                 // Known lang item with attribute on correct target.
                 Some(lang_item) if actual_target == lang_item.target() => {
-                    self.collect_item_extended(lang_item, hir_id, span);
+                    self.collect_item_extended(lang_item, def_id, span);
                 }
                 // Known lang item with attribute on incorrect target.
                 Some(lang_item) => {
@@ -142,8 +142,7 @@ fn collect_item(&mut self, lang_item: LangItem, item_def_id: DefId) {
 
     // Like collect_item() above, but also checks whether the lang item is declared
     // with the right number of generic arguments.
-    fn collect_item_extended(&mut self, lang_item: LangItem, hir_id: HirId, span: Span) {
-        let item_def_id = self.tcx.hir().local_def_id(hir_id).to_def_id();
+    fn collect_item_extended(&mut self, lang_item: LangItem, item_def_id: LocalDefId, span: Span) {
         let name = lang_item.name();
 
         // Now check whether the lang_item has the expected number of generic
@@ -154,7 +153,8 @@ fn collect_item_extended(&mut self, lang_item: LangItem, hir_id: HirId, span: Sp
         // Some other types like Box and various functions like drop_in_place
         // have minimum requirements.
 
-        if let hir::Node::Item(hir::Item { kind, span: item_span, .. }) = self.tcx.hir().get(hir_id)
+        if let hir::Node::Item(hir::Item { kind, span: item_span, .. }) =
+            self.tcx.hir().get_by_def_id(item_def_id)
         {
             let (actual_num, generics_span) = match kind.generics() {
                 Some(generics) => (generics.params.len(), generics.span),
@@ -191,7 +191,7 @@ fn collect_item_extended(&mut self, lang_item: LangItem, hir_id: HirId, span: Sp
             }
         }
 
-        self.collect_item(lang_item, item_def_id);
+        self.collect_item(lang_item, item_def_id.to_def_id());
     }
 }
 
@@ -211,13 +211,14 @@ fn get_lang_items(tcx: TyCtxt<'_>, (): ()) -> LanguageItems {
     let crate_items = tcx.hir_crate_items(());
 
     for id in crate_items.items() {
-        collector.check_for_lang(Target::from_def_kind(tcx.def_kind(id.owner_id)), id.hir_id());
+        collector
+            .check_for_lang(Target::from_def_kind(tcx.def_kind(id.owner_id)), id.owner_id.def_id);
 
         if matches!(tcx.def_kind(id.owner_id), DefKind::Enum) {
             let item = tcx.hir().item(id);
             if let hir::ItemKind::Enum(def, ..) = &item.kind {
                 for variant in def.variants {
-                    collector.check_for_lang(Target::Variant, variant.hir_id);
+                    collector.check_for_lang(Target::Variant, variant.def_id);
                 }
             }
         }
@@ -226,13 +227,13 @@ fn get_lang_items(tcx: TyCtxt<'_>, (): ()) -> LanguageItems {
     // FIXME: avoid calling trait_item() when possible
     for id in crate_items.trait_items() {
         let item = tcx.hir().trait_item(id);
-        collector.check_for_lang(Target::from_trait_item(item), item.hir_id())
+        collector.check_for_lang(Target::from_trait_item(item), item.owner_id.def_id)
     }
 
     // FIXME: avoid calling impl_item() when possible
     for id in crate_items.impl_items() {
         let item = tcx.hir().impl_item(id);
-        collector.check_for_lang(target_from_impl_item(tcx, item), item.hir_id())
+        collector.check_for_lang(target_from_impl_item(tcx, item), item.owner_id.def_id)
     }
 
     // Extract out the found lang items.
index 34e1abb78b2d4fa33323c278cd85d36d24a70fce..0bde7502e3991665a0af77a14c9552e2edcb618e 100644 (file)
@@ -855,7 +855,8 @@ fn visit_path(&mut self, path: &hir::Path<'tcx>, id: hir::HirId) {
 /// See issue #94972 for details on why this is a special case
 fn is_unstable_reexport(tcx: TyCtxt<'_>, id: hir::HirId) -> bool {
     // Get the LocalDefId so we can lookup the item to check the kind.
-    let Some(def_id) = tcx.hir().opt_local_def_id(id) else { return false; };
+    let Some(owner) = id.as_owner() else { return false; };
+    let def_id = owner.def_id;
 
     let Some(stab) = tcx.stability().local_stability(def_id) else {
         return false;
index 59972b2e408bcac2e35b8350dcfd2859b38322d3..43552861532235ef5c78d931a75bcf2f9f27b2d1 100644 (file)
@@ -18,7 +18,7 @@
 use rustc_data_structures::intern::Interned;
 use rustc_hir as hir;
 use rustc_hir::def::{DefKind, Res};
-use rustc_hir::def_id::{DefId, LocalDefId, LocalDefIdSet, CRATE_DEF_ID};
+use rustc_hir::def_id::{DefId, LocalDefId, CRATE_DEF_ID};
 use rustc_hir::intravisit::{self, Visitor};
 use rustc_hir::{AssocItemKind, HirIdSet, ItemId, Node, PatKind};
 use rustc_middle::bug;
@@ -1879,7 +1879,7 @@ fn visit_def_id(
 
 struct PrivateItemsInPublicInterfacesChecker<'tcx> {
     tcx: TyCtxt<'tcx>,
-    old_error_set_ancestry: LocalDefIdSet,
+    old_error_set_ancestry: HirIdSet,
 }
 
 impl<'tcx> PrivateItemsInPublicInterfacesChecker<'tcx> {
@@ -1892,7 +1892,9 @@ fn check(
             tcx: self.tcx,
             item_def_id: def_id,
             required_visibility,
-            has_old_errors: self.old_error_set_ancestry.contains(&def_id),
+            has_old_errors: self
+                .old_error_set_ancestry
+                .contains(&self.tcx.hir().local_def_id_to_hir_id(def_id)),
             in_assoc_ty: false,
         }
     }
@@ -2158,15 +2160,7 @@ fn check_private_in_public(tcx: TyCtxt<'_>, (): ()) {
     }
 
     // Check for private types and traits in public interfaces.
-    let mut checker = PrivateItemsInPublicInterfacesChecker {
-        tcx,
-        // Only definition IDs are ever searched in `old_error_set_ancestry`,
-        // so we can filter away all non-definition IDs at this point.
-        old_error_set_ancestry: old_error_set_ancestry
-            .into_iter()
-            .filter_map(|hir_id| tcx.hir().opt_local_def_id(hir_id))
-            .collect(),
-    };
+    let mut checker = PrivateItemsInPublicInterfacesChecker { tcx, old_error_set_ancestry };
 
     for id in tcx.hir().items() {
         checker.check_item(id);
index a5f09de1c401ba0c86fac6d1df3953b109de29fa..3982111e38e08307f6aaacebe270a3c947f2cd78 100644 (file)
@@ -211,7 +211,7 @@ fn process_formals(&mut self, formals: &'tcx [hir::Param<'tcx>], qualname: &str)
                     None => continue,
                 };
                 if !self.span.filter_generated(ident.span) {
-                    let id = id_from_hir_id(hir_id, &self.save_ctxt);
+                    let id = id_from_hir_id(hir_id);
                     let span = self.span_from_span(ident.span);
 
                     self.dumper.dump_def(
@@ -240,17 +240,17 @@ fn process_method(
         &mut self,
         sig: &'tcx hir::FnSig<'tcx>,
         body: Option<hir::BodyId>,
-        def_id: LocalDefId,
+        owner_id: hir::OwnerId,
         ident: Ident,
         generics: &'tcx hir::Generics<'tcx>,
         span: Span,
     ) {
-        debug!("process_method: {:?}:{}", def_id, ident);
+        debug!("process_method: {:?}:{}", owner_id, ident);
 
         let map = self.tcx.hir();
-        let hir_id = map.local_def_id_to_hir_id(def_id);
-        self.nest_typeck_results(def_id, |v| {
-            if let Some(mut method_data) = v.save_ctxt.get_method_data(hir_id, ident, span) {
+        let hir_id: hir::HirId = owner_id.into();
+        self.nest_typeck_results(owner_id.def_id, |v| {
+            if let Some(mut method_data) = v.save_ctxt.get_method_data(owner_id, ident, span) {
                 if let Some(body) = body {
                     v.process_formals(map.body(body).params, &method_data.qualname);
                 }
@@ -258,9 +258,10 @@ fn process_method(
 
                 method_data.value =
                     fn_to_string(sig.decl, sig.header, Some(ident.name), generics, &[], None);
-                method_data.sig = sig::method_signature(hir_id, ident, generics, sig, &v.save_ctxt);
+                method_data.sig =
+                    sig::method_signature(owner_id, ident, generics, sig, &v.save_ctxt);
 
-                v.dumper.dump_def(&access_from!(v.save_ctxt, def_id), method_data);
+                v.dumper.dump_def(&access_from!(v.save_ctxt, owner_id.def_id), method_data);
             }
 
             // walk arg and return types
@@ -282,14 +283,11 @@ fn process_method(
     fn process_struct_field_def(
         &mut self,
         field: &'tcx hir::FieldDef<'tcx>,
-        parent_id: hir::HirId,
+        parent_id: LocalDefId,
     ) {
         let field_data = self.save_ctxt.get_field_data(field, parent_id);
         if let Some(field_data) = field_data {
-            self.dumper.dump_def(
-                &access_from!(self.save_ctxt, self.tcx.hir().local_def_id(field.hir_id)),
-                field_data,
-            );
+            self.dumper.dump_def(&access_from!(self.save_ctxt, field.def_id), field_data);
         }
     }
 
@@ -309,7 +307,7 @@ fn process_generic_params(
                     // Append $id to name to make sure each one is unique.
                     let qualname = format!("{}::{}${}", prefix, name, id);
                     if !self.span.filter_generated(param_ss) {
-                        let id = id_from_hir_id(param.hir_id, &self.save_ctxt);
+                        let id = id_from_def_id(param.def_id.to_def_id());
                         let span = self.span_from_span(param_ss);
 
                         self.dumper.dump_def(
@@ -387,25 +385,24 @@ fn process_static_or_const_item(
 
     fn process_assoc_const(
         &mut self,
-        def_id: LocalDefId,
+        owner_id: hir::OwnerId,
         ident: Ident,
         typ: &'tcx hir::Ty<'tcx>,
         expr: Option<&'tcx hir::Expr<'tcx>>,
         parent_id: DefId,
         attrs: &'tcx [ast::Attribute],
     ) {
-        let qualname = format!("::{}", self.tcx.def_path_str(def_id.to_def_id()));
+        let qualname = format!("::{}", self.tcx.def_path_str(owner_id.to_def_id()));
 
         if !self.span.filter_generated(ident.span) {
-            let hir_id = self.tcx.hir().local_def_id_to_hir_id(def_id);
-            let sig = sig::assoc_const_signature(hir_id, ident.name, typ, expr, &self.save_ctxt);
+            let sig = sig::assoc_const_signature(owner_id, ident.name, typ, expr, &self.save_ctxt);
             let span = self.span_from_span(ident.span);
 
             self.dumper.dump_def(
-                &access_from!(self.save_ctxt, def_id),
+                &access_from!(self.save_ctxt, owner_id.def_id),
                 Def {
                     kind: DefKind::Const,
-                    id: id_from_hir_id(hir_id, &self.save_ctxt),
+                    id: id_from_def_id(owner_id.to_def_id()),
                     span,
                     name: ident.name.to_string(),
                     qualname,
@@ -421,7 +418,7 @@ fn process_assoc_const(
         }
 
         // walk type and init value
-        self.nest_typeck_results(def_id, |v| {
+        self.nest_typeck_results(owner_id.def_id, |v| {
             v.visit_ty(typ);
             if let Some(expr) = expr {
                 v.visit_expr(expr);
@@ -456,8 +453,7 @@ fn process_struct(
                         if include_priv_fields {
                             return Some(f.ident.to_string());
                         }
-                        let def_id = self.save_ctxt.tcx.hir().local_def_id(f.hir_id);
-                        if self.save_ctxt.tcx.visibility(def_id).is_public() {
+                        if self.save_ctxt.tcx.visibility(f.def_id).is_public() {
                             Some(f.ident.to_string())
                         } else {
                             None
@@ -466,7 +462,7 @@ fn process_struct(
                     .collect::<Vec<_>>()
                     .join(", ");
                 let value = format!("{} {{ {} }}", name, fields_str);
-                (value, fields.iter().map(|f| id_from_hir_id(f.hir_id, &self.save_ctxt)).collect())
+                (value, fields.iter().map(|f| id_from_def_id(f.def_id.to_def_id())).collect())
             }
             _ => (String::new(), vec![]),
         };
@@ -495,7 +491,7 @@ fn process_struct(
 
         self.nest_typeck_results(item.owner_id.def_id, |v| {
             for field in def.fields() {
-                v.process_struct_field_def(field, item.hir_id());
+                v.process_struct_field_def(field, item.owner_id.def_id);
                 v.visit_ty(&field.ty);
             }
 
@@ -529,7 +525,7 @@ fn process_enum(
                     let value = format!("{}::{} {{ {} }}", enum_data.name, name, fields_str);
                     if !self.span.filter_generated(name_span) {
                         let span = self.span_from_span(name_span);
-                        let id = id_from_hir_id(variant.hir_id, &self.save_ctxt);
+                        let id = id_from_def_id(variant.def_id.to_def_id());
                         let parent = Some(id_from_def_id(item.owner_id.to_def_id()));
                         let attrs = self.tcx.hir().attrs(variant.hir_id);
 
@@ -567,7 +563,7 @@ fn process_enum(
                     }
                     if !self.span.filter_generated(name_span) {
                         let span = self.span_from_span(name_span);
-                        let id = id_from_hir_id(variant.hir_id, &self.save_ctxt);
+                        let id = id_from_def_id(variant.def_id.to_def_id());
                         let parent = Some(id_from_def_id(item.owner_id.to_def_id()));
                         let attrs = self.tcx.hir().attrs(variant.hir_id);
 
@@ -593,7 +589,7 @@ fn process_enum(
             }
 
             for field in variant.data.fields() {
-                self.process_struct_field_def(field, variant.hir_id);
+                self.process_struct_field_def(field, variant.def_id);
                 self.visit_ty(field.ty);
             }
         }
@@ -883,7 +879,7 @@ fn process_var_decl(&mut self, pat: &'tcx hir::Pat<'tcx>) {
                     // Rust uses the id of the pattern for var lookups, so we'll use it too.
                     if !self.span.filter_generated(ident.span) {
                         let qualname = format!("{}${}", ident, hir_id);
-                        let id = id_from_hir_id(hir_id, &self.save_ctxt);
+                        let id = id_from_hir_id(hir_id);
                         let span = self.span_from_span(ident.span);
 
                         self.dumper.dump_def(
@@ -983,7 +979,7 @@ fn process_trait_item(&mut self, trait_item: &'tcx hir::TraitItem<'tcx>, trait_i
                 let body = body.map(|b| self.tcx.hir().body(b).value);
                 let attrs = self.tcx.hir().attrs(trait_item.hir_id());
                 self.process_assoc_const(
-                    trait_item.owner_id.def_id,
+                    trait_item.owner_id,
                     trait_item.ident,
                     &ty,
                     body,
@@ -997,7 +993,7 @@ fn process_trait_item(&mut self, trait_item: &'tcx hir::TraitItem<'tcx>, trait_i
                 self.process_method(
                     sig,
                     body,
-                    trait_item.owner_id.def_id,
+                    trait_item.owner_id,
                     trait_item.ident,
                     &trait_item.generics,
                     trait_item.span,
@@ -1028,7 +1024,7 @@ fn process_trait_item(&mut self, trait_item: &'tcx hir::TraitItem<'tcx>, trait_i
                             decl_id: None,
                             docs: self.save_ctxt.docs_for_attrs(attrs),
                             sig: sig::assoc_type_signature(
-                                trait_item.hir_id(),
+                                trait_item.owner_id,
                                 trait_item.ident,
                                 Some(bounds),
                                 default_ty.as_deref(),
@@ -1053,7 +1049,7 @@ fn process_impl_item(&mut self, impl_item: &'tcx hir::ImplItem<'tcx>, impl_id: D
                 let body = self.tcx.hir().body(body);
                 let attrs = self.tcx.hir().attrs(impl_item.hir_id());
                 self.process_assoc_const(
-                    impl_item.owner_id.def_id,
+                    impl_item.owner_id,
                     impl_item.ident,
                     &ty,
                     Some(&body.value),
@@ -1065,7 +1061,7 @@ fn process_impl_item(&mut self, impl_item: &'tcx hir::ImplItem<'tcx>, impl_id: D
                 self.process_method(
                     sig,
                     Some(body),
-                    impl_item.owner_id.def_id,
+                    impl_item.owner_id,
                     impl_item.ident,
                     &impl_item.generics,
                     impl_item.span,
@@ -1081,18 +1077,16 @@ fn process_impl_item(&mut self, impl_item: &'tcx hir::ImplItem<'tcx>, impl_id: D
     }
 
     pub(crate) fn process_crate(&mut self) {
-        let id = hir::CRATE_HIR_ID;
-        let qualname =
-            format!("::{}", self.tcx.def_path_str(self.tcx.hir().local_def_id(id).to_def_id()));
+        let qualname = format!("::{}", self.tcx.def_path_str(CRATE_DEF_ID.to_def_id()));
 
         let sm = self.tcx.sess.source_map();
         let krate_mod = self.tcx.hir().root_module();
         let filename = sm.span_to_filename(krate_mod.spans.inner_span);
-        let data_id = id_from_hir_id(id, &self.save_ctxt);
+        let data_id = id_from_def_id(CRATE_DEF_ID.to_def_id());
         let children =
             krate_mod.item_ids.iter().map(|i| id_from_def_id(i.owner_id.to_def_id())).collect();
         let span = self.span_from_span(krate_mod.spans.inner_span);
-        let attrs = self.tcx.hir().attrs(id);
+        let attrs = self.tcx.hir().attrs(hir::CRATE_HIR_ID);
 
         self.dumper.dump_def(
             &Access { public: true, reachable: true },
@@ -1319,7 +1313,7 @@ fn visit_ty(&mut self, t: &'tcx hir::Ty<'tcx>) {
                     // output the inferred type here? :shrug:
                     hir::ArrayLen::Infer(..) => {}
                     hir::ArrayLen::Body(anon_const) => self
-                        .nest_typeck_results(self.tcx.hir().local_def_id(anon_const.hir_id), |v| {
+                        .nest_typeck_results(anon_const.def_id, |v| {
                             v.visit_expr(&map.body(anon_const.body).value)
                         }),
                 }
@@ -1361,7 +1355,7 @@ fn visit_expr(&mut self, ex: &'tcx hir::Expr<'tcx>) {
                     }
                 }
             }
-            hir::ExprKind::Closure(&hir::Closure { ref fn_decl, body, .. }) => {
+            hir::ExprKind::Closure(&hir::Closure { ref fn_decl, body, def_id, .. }) => {
                 let id = format!("${}", ex.hir_id);
 
                 // walk arg and return types
@@ -1375,7 +1369,7 @@ fn visit_expr(&mut self, ex: &'tcx hir::Expr<'tcx>) {
 
                 // walk the body
                 let map = self.tcx.hir();
-                self.nest_typeck_results(self.tcx.hir().local_def_id(ex.hir_id), |v| {
+                self.nest_typeck_results(def_id, |v| {
                     let body = map.body(body);
                     v.process_formals(body.params, &id);
                     v.visit_expr(&body.value)
@@ -1389,7 +1383,7 @@ fn visit_expr(&mut self, ex: &'tcx hir::Expr<'tcx>) {
                     // output the inferred type here? :shrug:
                     hir::ArrayLen::Infer(..) => {}
                     hir::ArrayLen::Body(anon_const) => self
-                        .nest_typeck_results(self.tcx.hir().local_def_id(anon_const.hir_id), |v| {
+                        .nest_typeck_results(anon_const.def_id, |v| {
                             v.visit_expr(&map.body(anon_const.body).value)
                         }),
                 }
index a8d82de02b7548836d5b8e3a7e70ae07caab06a2..a9a92cc4f62ed9102a3039f58f01657f60eaef8d 100644 (file)
@@ -21,7 +21,7 @@
 use rustc_ast_pretty::pprust::attribute_to_string;
 use rustc_hir as hir;
 use rustc_hir::def::{DefKind as HirDefKind, Res};
-use rustc_hir::def_id::{DefId, LOCAL_CRATE};
+use rustc_hir::def_id::{DefId, LocalDefId, LOCAL_CRATE};
 use rustc_hir::intravisit::{self, Visitor};
 use rustc_hir::Node;
 use rustc_hir_pretty::{enum_def_to_string, fn_to_string, ty_to_string};
@@ -318,7 +318,7 @@ pub fn get_item_data(&self, item: &hir::Item<'_>) -> Option<Data> {
                     qualname,
                     value,
                     parent: None,
-                    children: def.variants.iter().map(|v| id_from_hir_id(v.hir_id, self)).collect(),
+                    children: def.variants.iter().map(|v| id_from_def_id(v.def_id.to_def_id())).collect(),
                     decl_id: None,
                     docs: self.docs_for_attrs(attrs),
                     sig: sig::item_signature(item, self),
@@ -379,12 +379,11 @@ pub fn get_item_data(&self, item: &hir::Item<'_>) -> Option<Data> {
         }
     }
 
-    pub fn get_field_data(&self, field: &hir::FieldDef<'_>, scope: hir::HirId) -> Option<Def> {
+    pub fn get_field_data(&self, field: &hir::FieldDef<'_>, scope: LocalDefId) -> Option<Def> {
         let name = field.ident.to_string();
-        let scope_def_id = self.tcx.hir().local_def_id(scope).to_def_id();
-        let qualname = format!("::{}::{}", self.tcx.def_path_str(scope_def_id), field.ident);
+        let qualname = format!("::{}::{}", self.tcx.def_path_str(scope.to_def_id()), field.ident);
         filter!(self.span_utils, field.ident.span);
-        let field_def_id = self.tcx.hir().local_def_id(field.hir_id).to_def_id();
+        let field_def_id = field.def_id.to_def_id();
         let typ = self.tcx.type_of(field_def_id).to_string();
 
         let id = id_from_def_id(field_def_id);
@@ -398,7 +397,7 @@ pub fn get_field_data(&self, field: &hir::FieldDef<'_>, scope: hir::HirId) -> Op
             name,
             qualname,
             value: typ,
-            parent: Some(id_from_def_id(scope_def_id)),
+            parent: Some(id_from_def_id(scope.to_def_id())),
             children: vec![],
             decl_id: None,
             docs: self.docs_for_attrs(attrs),
@@ -409,12 +408,11 @@ pub fn get_field_data(&self, field: &hir::FieldDef<'_>, scope: hir::HirId) -> Op
 
     // FIXME would be nice to take a MethodItem here, but the ast provides both
     // trait and impl flavours, so the caller must do the disassembly.
-    pub fn get_method_data(&self, hir_id: hir::HirId, ident: Ident, span: Span) -> Option<Def> {
+    pub fn get_method_data(&self, owner_id: hir::OwnerId, ident: Ident, span: Span) -> Option<Def> {
         // The qualname for a method is the trait name or name of the struct in an impl in
         // which the method is declared in, followed by the method's name.
-        let def_id = self.tcx.hir().local_def_id(hir_id).to_def_id();
         let (qualname, parent_scope, decl_id, docs, attributes) =
-            match self.tcx.impl_of_method(def_id) {
+            match self.tcx.impl_of_method(owner_id.to_def_id()) {
                 Some(impl_id) => match self.tcx.hir().get_if_local(impl_id) {
                     Some(Node::Item(item)) => match item.kind {
                         hir::ItemKind::Impl(hir::Impl { ref self_ty, .. }) => {
@@ -427,8 +425,8 @@ pub fn get_method_data(&self, hir_id: hir::HirId, ident: Ident, span: Span) -> O
                             let trait_id = self.tcx.trait_id_of_impl(impl_id);
                             let mut docs = String::new();
                             let mut attrs = vec![];
-                            if let Some(Node::ImplItem(_)) = hir.find(hir_id) {
-                                attrs = self.tcx.hir().attrs(hir_id).to_vec();
+                            if let Some(Node::ImplItem(_)) = hir.find(owner_id.into()) {
+                                attrs = self.tcx.hir().attrs(owner_id.into()).to_vec();
                                 docs = self.docs_for_attrs(&attrs);
                             }
 
@@ -452,29 +450,29 @@ pub fn get_method_data(&self, hir_id: hir::HirId, ident: Ident, span: Span) -> O
                         _ => {
                             span_bug!(
                                 span,
-                                "Container {:?} for method {} not an impl?",
+                                "Container {:?} for method {:?} not an impl?",
                                 impl_id,
-                                hir_id
+                                owner_id,
                             );
                         }
                     },
                     r => {
                         span_bug!(
                             span,
-                            "Container {:?} for method {} is not a node item {:?}",
+                            "Container {:?} for method {:?} is not a node item {:?}",
                             impl_id,
-                            hir_id,
+                            owner_id,
                             r
                         );
                     }
                 },
-                None => match self.tcx.trait_of_item(def_id) {
+                None => match self.tcx.trait_of_item(owner_id.to_def_id()) {
                     Some(def_id) => {
                         let mut docs = String::new();
                         let mut attrs = vec![];
 
-                        if let Some(Node::TraitItem(_)) = self.tcx.hir().find(hir_id) {
-                            attrs = self.tcx.hir().attrs(hir_id).to_vec();
+                        if let Some(Node::TraitItem(_)) = self.tcx.hir().find(owner_id.into()) {
+                            attrs = self.tcx.hir().attrs(owner_id.into()).to_vec();
                             docs = self.docs_for_attrs(&attrs);
                         }
 
@@ -487,7 +485,7 @@ pub fn get_method_data(&self, hir_id: hir::HirId, ident: Ident, span: Span) -> O
                         )
                     }
                     None => {
-                        debug!("could not find container for method {} at {:?}", hir_id, span);
+                        debug!("could not find container for method {:?} at {:?}", owner_id, span);
                         // This is not necessarily a bug, if there was a compilation error,
                         // the typeck results we need might not exist.
                         return None;
@@ -501,7 +499,7 @@ pub fn get_method_data(&self, hir_id: hir::HirId, ident: Ident, span: Span) -> O
 
         Some(Def {
             kind: DefKind::Method,
-            id: id_from_def_id(def_id),
+            id: id_from_def_id(owner_id.to_def_id()),
             span: self.span_from_span(ident.span),
             name: ident.name.to_string(),
             qualname,
@@ -669,7 +667,7 @@ fn fn_type(seg: &hir::PathSegment<'_>) -> bool {
 
         match res {
             Res::Local(id) => {
-                Some(Ref { kind: RefKind::Variable, span, ref_id: id_from_hir_id(id, self) })
+                Some(Ref { kind: RefKind::Variable, span, ref_id: id_from_hir_id(id) })
             }
             Res::Def(HirDefKind::Trait, def_id) if fn_type(path_seg) => {
                 Some(Ref { kind: RefKind::Type, span, ref_id: id_from_def_id(def_id) })
@@ -1033,18 +1031,15 @@ fn id_from_def_id(id: DefId) -> rls_data::Id {
     rls_data::Id { krate: id.krate.as_u32(), index: id.index.as_u32() }
 }
 
-fn id_from_hir_id(id: hir::HirId, scx: &SaveContext<'_>) -> rls_data::Id {
-    let def_id = scx.tcx.hir().opt_local_def_id(id);
-    def_id.map(|id| id_from_def_id(id.to_def_id())).unwrap_or_else(|| {
-        // Create a *fake* `DefId` out of a `HirId` by combining the owner
-        // `local_def_index` and the `local_id`.
-        // This will work unless you have *billions* of definitions in a single
-        // crate (very unlikely to actually happen).
-        rls_data::Id {
-            krate: LOCAL_CRATE.as_u32(),
-            index: id.owner.def_id.local_def_index.as_u32() | id.local_id.as_u32().reverse_bits(),
-        }
-    })
+fn id_from_hir_id(id: hir::HirId) -> rls_data::Id {
+    // Create a *fake* `DefId` out of a `HirId` by combining the owner
+    // `local_def_index` and the `local_id`.
+    // This will work unless you have *billions* of definitions in a single
+    // crate (very unlikely to actually happen).
+    rls_data::Id {
+        krate: LOCAL_CRATE.as_u32(),
+        index: id.owner.def_id.local_def_index.as_u32() | id.local_id.as_u32().reverse_bits(),
+    }
 }
 
 fn null_id() -> rls_data::Id {
index 5a1bcb8fdc87be9a82047dbed9040ee4e3c17afd..979305547c14b23afe616ee78f6d9d88993aed5a 100644 (file)
@@ -25,7 +25,7 @@
 //
 // FIXME where clauses need implementing, defs/refs in generics are mostly missing.
 
-use crate::{id_from_def_id, id_from_hir_id, SaveContext};
+use crate::{id_from_def_id, SaveContext};
 
 use rls_data::{SigElement, Signature};
 
@@ -34,6 +34,7 @@
 use rustc_hir::def::{DefKind, Res};
 use rustc_hir_pretty::id_to_string;
 use rustc_hir_pretty::{bounds_to_string, path_segment_to_string, path_to_string, ty_to_string};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::symbol::{Ident, Symbol};
 
 pub fn item_signature(item: &hir::Item<'_>, scx: &SaveContext<'_>) -> Option<Signature> {
@@ -71,7 +72,7 @@ pub fn variant_signature(variant: &hir::Variant<'_>, scx: &SaveContext<'_>) -> O
 }
 
 pub fn method_signature(
-    id: hir::HirId,
+    id: hir::OwnerId,
     ident: Ident,
     generics: &hir::Generics<'_>,
     m: &hir::FnSig<'_>,
@@ -84,7 +85,7 @@ pub fn method_signature(
 }
 
 pub fn assoc_const_signature(
-    id: hir::HirId,
+    id: hir::OwnerId,
     ident: Symbol,
     ty: &hir::Ty<'_>,
     default: Option<&hir::Expr<'_>>,
@@ -97,7 +98,7 @@ pub fn assoc_const_signature(
 }
 
 pub fn assoc_type_signature(
-    id: hir::HirId,
+    id: hir::OwnerId,
     ident: Ident,
     bounds: Option<hir::GenericBounds<'_>>,
     default: Option<&hir::Ty<'_>>,
@@ -112,7 +113,8 @@ pub fn assoc_type_signature(
 type Result = std::result::Result<Signature, &'static str>;
 
 trait Sig {
-    fn make(&self, offset: usize, id: Option<hir::HirId>, scx: &SaveContext<'_>) -> Result;
+    type Parent;
+    fn make(&self, offset: usize, id: Option<Self::Parent>, scx: &SaveContext<'_>) -> Result;
 }
 
 fn extend_sig(
@@ -148,6 +150,7 @@ fn text_sig(text: String) -> Signature {
 }
 
 impl<'hir> Sig for hir::Ty<'hir> {
+    type Parent = hir::HirId;
     fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<'_>) -> Result {
         let id = Some(self.hir_id);
         match self.kind {
@@ -326,6 +329,7 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
 }
 
 impl<'hir> Sig for hir::Item<'hir> {
+    type Parent = hir::HirId;
     fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<'_>) -> Result {
         let id = Some(self.hir_id());
 
@@ -391,7 +395,7 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
                 text.push_str("fn ");
 
                 let mut sig =
-                    name_and_generics(text, offset, generics, self.hir_id(), self.ident, scx)?;
+                    name_and_generics(text, offset, generics, self.owner_id, self.ident, scx)?;
 
                 sig.text.push('(');
                 for i in decl.inputs {
@@ -441,7 +445,7 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
             hir::ItemKind::TyAlias(ref ty, ref generics) => {
                 let text = "type ".to_owned();
                 let mut sig =
-                    name_and_generics(text, offset, generics, self.hir_id(), self.ident, scx)?;
+                    name_and_generics(text, offset, generics, self.owner_id, self.ident, scx)?;
 
                 sig.text.push_str(" = ");
                 let ty = ty.make(offset + sig.text.len(), id, scx)?;
@@ -453,21 +457,21 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
             hir::ItemKind::Enum(_, ref generics) => {
                 let text = "enum ".to_owned();
                 let mut sig =
-                    name_and_generics(text, offset, generics, self.hir_id(), self.ident, scx)?;
+                    name_and_generics(text, offset, generics, self.owner_id, self.ident, scx)?;
                 sig.text.push_str(" {}");
                 Ok(sig)
             }
             hir::ItemKind::Struct(_, ref generics) => {
                 let text = "struct ".to_owned();
                 let mut sig =
-                    name_and_generics(text, offset, generics, self.hir_id(), self.ident, scx)?;
+                    name_and_generics(text, offset, generics, self.owner_id, self.ident, scx)?;
                 sig.text.push_str(" {}");
                 Ok(sig)
             }
             hir::ItemKind::Union(_, ref generics) => {
                 let text = "union ".to_owned();
                 let mut sig =
-                    name_and_generics(text, offset, generics, self.hir_id(), self.ident, scx)?;
+                    name_and_generics(text, offset, generics, self.owner_id, self.ident, scx)?;
                 sig.text.push_str(" {}");
                 Ok(sig)
             }
@@ -483,7 +487,7 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
                 }
                 text.push_str("trait ");
                 let mut sig =
-                    name_and_generics(text, offset, generics, self.hir_id(), self.ident, scx)?;
+                    name_and_generics(text, offset, generics, self.owner_id, self.ident, scx)?;
 
                 if !bounds.is_empty() {
                     sig.text.push_str(": ");
@@ -498,7 +502,7 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
                 let mut text = String::new();
                 text.push_str("trait ");
                 let mut sig =
-                    name_and_generics(text, offset, generics, self.hir_id(), self.ident, scx)?;
+                    name_and_generics(text, offset, generics, self.owner_id, self.ident, scx)?;
 
                 if !bounds.is_empty() {
                     sig.text.push_str(" = ");
@@ -532,7 +536,8 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
                     text.push_str(" const");
                 }
 
-                let generics_sig = generics.make(offset + text.len(), id, scx)?;
+                let generics_sig =
+                    generics.make(offset + text.len(), Some(self.owner_id.def_id), scx)?;
                 text.push_str(&generics_sig.text);
 
                 text.push(' ');
@@ -575,6 +580,7 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
 }
 
 impl<'hir> Sig for hir::Path<'hir> {
+    type Parent = hir::HirId;
     fn make(&self, offset: usize, id: Option<hir::HirId>, scx: &SaveContext<'_>) -> Result {
         let res = scx.get_path_res(id.ok_or("Missing id for Path")?);
 
@@ -609,7 +615,8 @@ fn make(&self, offset: usize, id: Option<hir::HirId>, scx: &SaveContext<'_>) ->
 
 // This does not cover the where clause, which must be processed separately.
 impl<'hir> Sig for hir::Generics<'hir> {
-    fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<'_>) -> Result {
+    type Parent = LocalDefId;
+    fn make(&self, offset: usize, _parent_id: Option<LocalDefId>, scx: &SaveContext<'_>) -> Result {
         if self.params.is_empty() {
             return Ok(text_sig(String::new()));
         }
@@ -624,7 +631,7 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
             }
             param_text.push_str(param.name.ident().as_str());
             defs.push(SigElement {
-                id: id_from_hir_id(param.hir_id, scx),
+                id: id_from_def_id(param.def_id.to_def_id()),
                 start: offset + text.len(),
                 end: offset + text.len() + param_text.as_str().len(),
             });
@@ -646,12 +653,13 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
 }
 
 impl<'hir> Sig for hir::FieldDef<'hir> {
-    fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<'_>) -> Result {
+    type Parent = LocalDefId;
+    fn make(&self, offset: usize, _parent_id: Option<LocalDefId>, scx: &SaveContext<'_>) -> Result {
         let mut text = String::new();
 
         text.push_str(&self.ident.to_string());
         let defs = Some(SigElement {
-            id: id_from_hir_id(self.hir_id, scx),
+            id: id_from_def_id(self.def_id.to_def_id()),
             start: offset,
             end: offset + text.len(),
         });
@@ -666,13 +674,14 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
 }
 
 impl<'hir> Sig for hir::Variant<'hir> {
-    fn make(&self, offset: usize, parent_id: Option<hir::HirId>, scx: &SaveContext<'_>) -> Result {
+    type Parent = LocalDefId;
+    fn make(&self, offset: usize, parent_id: Option<LocalDefId>, scx: &SaveContext<'_>) -> Result {
         let mut text = self.ident.to_string();
         match self.data {
             hir::VariantData::Struct(fields, r) => {
                 let id = parent_id.ok_or("Missing id for Variant's parent")?;
                 let name_def = SigElement {
-                    id: id_from_hir_id(id, scx),
+                    id: id_from_def_id(id.to_def_id()),
                     start: offset,
                     end: offset + text.len(),
                 };
@@ -693,9 +702,9 @@ fn make(&self, offset: usize, parent_id: Option<hir::HirId>, scx: &SaveContext<'
                 text.push('}');
                 Ok(Signature { text, defs, refs })
             }
-            hir::VariantData::Tuple(fields, id, _) => {
+            hir::VariantData::Tuple(fields, _, def_id) => {
                 let name_def = SigElement {
-                    id: id_from_hir_id(id, scx),
+                    id: id_from_def_id(def_id.to_def_id()),
                     start: offset,
                     end: offset + text.len(),
                 };
@@ -703,7 +712,7 @@ fn make(&self, offset: usize, parent_id: Option<hir::HirId>, scx: &SaveContext<'
                 let mut defs = vec![name_def];
                 let mut refs = vec![];
                 for f in fields {
-                    let field_sig = f.make(offset + text.len(), Some(id), scx)?;
+                    let field_sig = f.make(offset + text.len(), Some(def_id), scx)?;
                     text.push_str(&field_sig.text);
                     text.push_str(", ");
                     defs.extend(field_sig.defs.into_iter());
@@ -712,9 +721,9 @@ fn make(&self, offset: usize, parent_id: Option<hir::HirId>, scx: &SaveContext<'
                 text.push(')');
                 Ok(Signature { text, defs, refs })
             }
-            hir::VariantData::Unit(id, _) => {
+            hir::VariantData::Unit(_, def_id) => {
                 let name_def = SigElement {
-                    id: id_from_hir_id(id, scx),
+                    id: id_from_def_id(def_id.to_def_id()),
                     start: offset,
                     end: offset + text.len(),
                 };
@@ -725,6 +734,7 @@ fn make(&self, offset: usize, parent_id: Option<hir::HirId>, scx: &SaveContext<'
 }
 
 impl<'hir> Sig for hir::ForeignItem<'hir> {
+    type Parent = hir::HirId;
     fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<'_>) -> Result {
         let id = Some(self.hir_id());
         match self.kind {
@@ -733,7 +743,7 @@ fn make(&self, offset: usize, _parent_id: Option<hir::HirId>, scx: &SaveContext<
                 text.push_str("fn ");
 
                 let mut sig =
-                    name_and_generics(text, offset, generics, self.hir_id(), self.ident, scx)?;
+                    name_and_generics(text, offset, generics, self.owner_id, self.ident, scx)?;
 
                 sig.text.push('(');
                 for i in decl.inputs {
@@ -797,25 +807,25 @@ fn name_and_generics(
     mut text: String,
     offset: usize,
     generics: &hir::Generics<'_>,
-    id: hir::HirId,
+    id: hir::OwnerId,
     name: Ident,
     scx: &SaveContext<'_>,
 ) -> Result {
     let name = name.to_string();
     let def = SigElement {
-        id: id_from_hir_id(id, scx),
+        id: id_from_def_id(id.to_def_id()),
         start: offset + text.len(),
         end: offset + text.len() + name.len(),
     };
     text.push_str(&name);
-    let generics: Signature = generics.make(offset + text.len(), Some(id), scx)?;
+    let generics: Signature = generics.make(offset + text.len(), Some(id.def_id), scx)?;
     // FIXME where clause
     let text = format!("{}{}", text, generics.text);
     Ok(extend_sig(generics, text, vec![def], vec![]))
 }
 
 fn make_assoc_type_signature(
-    id: hir::HirId,
+    id: hir::OwnerId,
     ident: Ident,
     bounds: Option<hir::GenericBounds<'_>>,
     default: Option<&hir::Ty<'_>>,
@@ -824,7 +834,7 @@ fn make_assoc_type_signature(
     let mut text = "type ".to_owned();
     let name = ident.to_string();
     let mut defs = vec![SigElement {
-        id: id_from_hir_id(id, scx),
+        id: id_from_def_id(id.to_def_id()),
         start: text.len(),
         end: text.len() + name.len(),
     }];
@@ -837,7 +847,7 @@ fn make_assoc_type_signature(
     }
     if let Some(default) = default {
         text.push_str(" = ");
-        let ty_sig = default.make(text.len(), Some(id), scx)?;
+        let ty_sig = default.make(text.len(), Some(id.into()), scx)?;
         text.push_str(&ty_sig.text);
         defs.extend(ty_sig.defs.into_iter());
         refs.extend(ty_sig.refs.into_iter());
@@ -847,7 +857,7 @@ fn make_assoc_type_signature(
 }
 
 fn make_assoc_const_signature(
-    id: hir::HirId,
+    id: hir::OwnerId,
     ident: Symbol,
     ty: &hir::Ty<'_>,
     default: Option<&hir::Expr<'_>>,
@@ -856,7 +866,7 @@ fn make_assoc_const_signature(
     let mut text = "const ".to_owned();
     let name = ident.to_string();
     let mut defs = vec![SigElement {
-        id: id_from_hir_id(id, scx),
+        id: id_from_def_id(id.to_def_id()),
         start: text.len(),
         end: text.len() + name.len(),
     }];
@@ -864,7 +874,7 @@ fn make_assoc_const_signature(
     text.push_str(&name);
     text.push_str(": ");
 
-    let ty_sig = ty.make(text.len(), Some(id), scx)?;
+    let ty_sig = ty.make(text.len(), Some(id.into()), scx)?;
     text.push_str(&ty_sig.text);
     defs.extend(ty_sig.defs.into_iter());
     refs.extend(ty_sig.refs.into_iter());
@@ -878,7 +888,7 @@ fn make_assoc_const_signature(
 }
 
 fn make_method_signature(
-    id: hir::HirId,
+    id: hir::OwnerId,
     ident: Ident,
     generics: &hir::Generics<'_>,
     m: &hir::FnSig<'_>,
index f7cf81da497529af14920277b0bb892aa9323ae6..e44fd82ba22362d1b26e06032c275027e36c39a2 100644 (file)
@@ -78,7 +78,7 @@ pub(super) enum CandidateSource {
     ///     let _y = x.clone();
     /// }
     /// ```
-    AliasBound(usize),
+    AliasBound,
 }
 
 pub(super) trait GoalKind<'tcx>: TypeFoldable<'tcx> + Copy + Eq {
@@ -242,8 +242,6 @@ fn assemble_candidates_after_normalizing_self_ty<G: GoalKind<'tcx>>(
             // NOTE: Alternatively we could call `evaluate_goal` here and only have a `Normalized` candidate.
             // This doesn't work as long as we use `CandidateSource` in winnowing.
             let goal = goal.with(tcx, goal.predicate.with_self_ty(tcx, normalized_ty));
-            // FIXME: This is broken if we care about the `usize` of `AliasBound` because the self type
-            // could be normalized to yet another projection with different item bounds.
             let normalized_candidates = self.assemble_and_evaluate_candidates(goal);
             for mut normalized_candidate in normalized_candidates {
                 normalized_candidate.result =
@@ -368,15 +366,14 @@ fn assemble_alias_bound_candidates<G: GoalKind<'tcx>>(
             ty::Alias(_, alias_ty) => alias_ty,
         };
 
-        for (i, (assumption, _)) in self
+        for (assumption, _) in self
             .tcx()
             .bound_explicit_item_bounds(alias_ty.def_id)
             .subst_iter_copied(self.tcx(), alias_ty.substs)
-            .enumerate()
         {
             match G::consider_assumption(self, goal, assumption) {
                 Ok(result) => {
-                    candidates.push(Candidate { source: CandidateSource::AliasBound(i), result })
+                    candidates.push(Candidate { source: CandidateSource::AliasBound, result })
                 }
                 Err(NoSolution) => (),
             }
index e240dd5a2257a062f2b8e117e104c7a34b952f79..cbe64ae4f4e39cc860accecdfcbd1edf45d39300 100644 (file)
 // preserves universes and creates a unique var (in the highest universe) for each
 // appearance of a region.
 
-// FIXME: `CanonicalVarValues` should be interned and `Copy`.
-
 // FIXME: uses of `infcx.at` need to enable deferred projection equality once that's implemented.
 
 use std::mem;
 
 use rustc_hir::def_id::DefId;
-use rustc_infer::infer::canonical::{Canonical, CanonicalVarKind, CanonicalVarValues};
+use rustc_infer::infer::canonical::{Canonical, CanonicalVarValues};
 use rustc_infer::infer::canonical::{OriginalQueryValues, QueryRegionConstraints, QueryResponse};
 use rustc_infer::infer::{InferCtxt, InferOk, TyCtxtInferExt};
 use rustc_infer::traits::query::NoSolution;
@@ -225,7 +223,7 @@ fn make_canonical_response(&self, certainty: Certainty) -> QueryResult<'tcx> {
         let external_constraints = take_external_constraints(self.infcx)?;
 
         Ok(self.infcx.canonicalize_response(Response {
-            var_values: self.var_values.clone(),
+            var_values: self.var_values,
             external_constraints,
             certainty,
         }))
@@ -483,32 +481,11 @@ pub(super) fn response_no_constraints<'tcx>(
     goal: Canonical<'tcx, impl Sized>,
     certainty: Certainty,
 ) -> QueryResult<'tcx> {
-    let var_values = goal
-        .variables
-        .iter()
-        .enumerate()
-        .map(|(i, info)| match info.kind {
-            CanonicalVarKind::Ty(_) | CanonicalVarKind::PlaceholderTy(_) => {
-                tcx.mk_ty(ty::Bound(ty::INNERMOST, ty::BoundVar::from_usize(i).into())).into()
-            }
-            CanonicalVarKind::Region(_) | CanonicalVarKind::PlaceholderRegion(_) => {
-                let br = ty::BoundRegion {
-                    var: ty::BoundVar::from_usize(i),
-                    kind: ty::BrAnon(i as u32, None),
-                };
-                tcx.mk_region(ty::ReLateBound(ty::INNERMOST, br)).into()
-            }
-            CanonicalVarKind::Const(_, ty) | CanonicalVarKind::PlaceholderConst(_, ty) => tcx
-                .mk_const(ty::ConstKind::Bound(ty::INNERMOST, ty::BoundVar::from_usize(i)), ty)
-                .into(),
-        })
-        .collect();
-
     Ok(Canonical {
         max_universe: goal.max_universe,
         variables: goal.variables,
         value: Response {
-            var_values: CanonicalVarValues { var_values },
+            var_values: CanonicalVarValues::make_identity(tcx, goal.variables),
             external_constraints: Default::default(),
             certainty,
         },
index 638efaa2ba5d2f388a4ddd432ccc68bf0f0812ad..b175a6dde179f1378ab0570c69607a5bbce246df 100644 (file)
@@ -93,24 +93,24 @@ impl<'tcx> TypeVisitor<'tcx> for ContainsTerm<'tcx> {
             fn visit_ty(&mut self, t: Ty<'tcx>) -> ControlFlow<Self::BreakTy> {
                 if t.needs_infer() {
                     if ty::Term::from(t) == self.term {
-                        ControlFlow::BREAK
+                        ControlFlow::Break(())
                     } else {
                         t.super_visit_with(self)
                     }
                 } else {
-                    ControlFlow::CONTINUE
+                    ControlFlow::Continue(())
                 }
             }
 
             fn visit_const(&mut self, c: ty::Const<'tcx>) -> ControlFlow<Self::BreakTy> {
                 if c.needs_infer() {
                     if ty::Term::from(c) == self.term {
-                        ControlFlow::BREAK
+                        ControlFlow::Break(())
                     } else {
                         c.super_visit_with(self)
                     }
                 } else {
-                    ControlFlow::CONTINUE
+                    ControlFlow::Continue(())
                 }
             }
         }
@@ -171,7 +171,7 @@ fn project_candidate_should_be_dropped_in_favor_of(
             (CandidateSource::Impl(_), _)
             | (CandidateSource::ParamEnv(_), _)
             | (CandidateSource::BuiltinImpl, _)
-            | (CandidateSource::AliasBound(_), _) => unimplemented!(),
+            | (CandidateSource::AliasBound, _) => unimplemented!(),
         }
     }
 }
index 730a8e6125887ae6fcdfb1e7379f38df33d2016e..80a388b8498b9784677f17ee2fdf7bb39f0a0761 100644 (file)
@@ -95,6 +95,7 @@ pub(super) fn depth(&self, entry_index: EntryIndex) -> StackDepth {
     }
 
     pub(super) fn provisional_result(&self, entry_index: EntryIndex) -> QueryResult<'tcx> {
+        // FIXME: Responses should probably be `Copy` as well
         self.entries[entry_index].response.clone()
     }
 }
index 45b6a5f4ec578b3ce19b4c9f60a03c9649fc88b5..1ea8fb8fd3dcc8d0d40a2c9dd415e46d808bc101 100644 (file)
@@ -322,7 +322,7 @@ fn trait_candidate_should_be_dropped_in_favor_of(
         match (candidate.source, other.source) {
             (CandidateSource::Impl(_), _)
             | (CandidateSource::ParamEnv(_), _)
-            | (CandidateSource::AliasBound(_), _)
+            | (CandidateSource::AliasBound, _)
             | (CandidateSource::BuiltinImpl, _) => unimplemented!(),
         }
     }
index 26c0b3beb37ba91df6fc0bc309f331d161c40061..ee0c07e15a3add65ba31bac75870c6ec01f2f3ec 100644 (file)
@@ -399,7 +399,7 @@ fn predicate_constraint(generics: &hir::Generics<'_>, pred: ty::Predicate<'_>) -
 /// param for cleaner code.
 fn suggest_restriction<'tcx>(
     tcx: TyCtxt<'tcx>,
-    hir_id: HirId,
+    item_id: LocalDefId,
     hir_generics: &hir::Generics<'tcx>,
     msg: &str,
     err: &mut Diagnostic,
@@ -418,7 +418,6 @@ fn suggest_restriction<'tcx>(
     {
         return;
     }
-    let Some(item_id) = hir_id.as_owner() else { return; };
     let generics = tcx.generics_of(item_id);
     // Given `fn foo(t: impl Trait)` where `Trait` requires assoc type `A`...
     if let Some((param, bound_str, fn_sig)) =
@@ -523,7 +522,7 @@ fn suggest_restricting_param_bound(
         mut err: &mut Diagnostic,
         trait_pred: ty::PolyTraitPredicate<'tcx>,
         associated_ty: Option<(&'static str, Ty<'tcx>)>,
-        body_id: LocalDefId,
+        mut body_id: LocalDefId,
     ) {
         let trait_pred = self.resolve_numeric_literals_with_default(trait_pred);
 
@@ -536,9 +535,7 @@ fn suggest_restricting_param_bound(
 
         // FIXME: Add check for trait bound that is already present, particularly `?Sized` so we
         //        don't suggest `T: Sized + ?Sized`.
-        let mut body_id = body_id;
         while let Some(node) = self.tcx.hir().find_by_def_id(body_id) {
-            let hir_id = self.tcx.hir().local_def_id_to_hir_id(body_id);
             match node {
                 hir::Node::Item(hir::Item {
                     ident,
@@ -549,7 +546,7 @@ fn suggest_restricting_param_bound(
                     // Restricting `Self` for a single method.
                     suggest_restriction(
                         self.tcx,
-                        hir_id,
+                        body_id,
                         &generics,
                         "`Self`",
                         err,
@@ -569,7 +566,7 @@ fn suggest_restricting_param_bound(
                     assert!(param_ty);
                     // Restricting `Self` for a single method.
                     suggest_restriction(
-                        self.tcx, hir_id, &generics, "`Self`", err, None, projection, trait_pred,
+                        self.tcx, body_id, &generics, "`Self`", err, None, projection, trait_pred,
                         None,
                     );
                     return;
@@ -591,7 +588,7 @@ fn suggest_restricting_param_bound(
                     // Missing restriction on associated type of type parameter (unmet projection).
                     suggest_restriction(
                         self.tcx,
-                        hir_id,
+                        body_id,
                         &generics,
                         "the associated type",
                         err,
@@ -611,7 +608,7 @@ fn suggest_restricting_param_bound(
                     // Missing restriction on associated type of type parameter (unmet projection).
                     suggest_restriction(
                         self.tcx,
-                        hir_id,
+                        body_id,
                         &generics,
                         "the associated type",
                         err,
index f76386fa720dfaa6b2e9e5dbe95ba8ccae81ba10..13d83b92689415f84fee9a26f9c96069c1822981 100644 (file)
@@ -8,13 +8,10 @@
 
 use rustc_data_structures::fx::FxHashMap;
 
-use rustc_index::vec::IndexVec;
-
 use rustc_middle::infer::canonical::{CanonicalTyVarKind, CanonicalVarKind};
 use rustc_middle::traits::ChalkRustInterner;
 use rustc_middle::ty::query::Providers;
-use rustc_middle::ty::subst::GenericArg;
-use rustc_middle::ty::{self, BoundVar, ParamTy, TyCtxt, TypeFoldable, TypeVisitable};
+use rustc_middle::ty::{self, ParamTy, TyCtxt, TypeFoldable, TypeVisitable};
 
 use rustc_infer::infer::canonical::{
     Canonical, CanonicalVarValues, Certainty, QueryRegionConstraints, QueryResponse,
@@ -100,11 +97,13 @@ pub(crate) fn evaluate_goal<'tcx>(
                          binders: chalk_ir::CanonicalVarKinds<_>| {
         use rustc_middle::infer::canonical::CanonicalVarInfo;
 
-        let mut var_values: IndexVec<BoundVar, GenericArg<'tcx>> = IndexVec::new();
         let mut reverse_param_substitutor = ReverseParamsSubstitutor::new(tcx, params);
-        subst.as_slice(interner).iter().for_each(|p| {
-            var_values.push(p.lower_into(interner).fold_with(&mut reverse_param_substitutor));
-        });
+        let var_values = tcx.mk_substs(
+            subst
+                .as_slice(interner)
+                .iter()
+                .map(|p| p.lower_into(interner).fold_with(&mut reverse_param_substitutor)),
+        );
         let variables: Vec<_> = binders
             .iter(interner)
             .map(|var| {
@@ -159,8 +158,7 @@ pub(crate) fn evaluate_goal<'tcx>(
                             max_universe: ty::UniverseIndex::from_usize(0),
                             variables: obligation.variables,
                             value: QueryResponse {
-                                var_values: CanonicalVarValues { var_values: IndexVec::new() }
-                                    .make_identity(tcx),
+                                var_values: CanonicalVarValues::dummy(),
                                 region_constraints: QueryRegionConstraints::default(),
                                 certainty: Certainty::Ambiguous,
                                 opaque_types: vec![],
index e0d665c9e12ba0e2465197f0f642d01e1ea23710..6bdf53f7fc9dd8a0d0a0ced46f5dd9ea2941bf7d 100644 (file)
@@ -99,7 +99,7 @@ fn find<T, B>(
         ) -> impl FnMut((), T) -> ControlFlow<B> + '_ {
             move |(), x| match f(x) {
                 Some(x) => ControlFlow::Break(x),
-                None => ControlFlow::CONTINUE,
+                None => ControlFlow::Continue(()),
             }
         }
 
index 307016c269099cf7d4d74981711e8fbe79763059..b040a0ea9011bb88ae1fc35fe153367be3eec980 100644 (file)
@@ -539,7 +539,7 @@ fn advance_by(&mut self, n: usize) -> Result<(), usize> {
         #[rustc_inherit_overflow_checks]
         fn advance<U: Iterator>(n: usize, iter: &mut U) -> ControlFlow<(), usize> {
             match iter.advance_by(n) {
-                Ok(()) => ControlFlow::BREAK,
+                Ok(()) => ControlFlow::Break(()),
                 Err(advanced) => ControlFlow::Continue(n - advanced),
             }
         }
@@ -629,7 +629,7 @@ fn advance_back_by(&mut self, n: usize) -> Result<(), usize> {
         #[rustc_inherit_overflow_checks]
         fn advance<U: DoubleEndedIterator>(n: usize, iter: &mut U) -> ControlFlow<(), usize> {
             match iter.advance_back_by(n) {
-                Ok(()) => ControlFlow::BREAK,
+                Ok(()) => ControlFlow::Break(()),
                 Err(advanced) => ControlFlow::Continue(n - advanced),
             }
         }
index bdf94c792c27c34a3742392440ea53cb7e4adeda..ed23873cdde7cc7e0ae7232504265d5494b96842 100644 (file)
@@ -352,7 +352,7 @@ fn rfind<P>(&mut self, predicate: P) -> Option<Self::Item>
         #[inline]
         fn check<T>(mut predicate: impl FnMut(&T) -> bool) -> impl FnMut((), T) -> ControlFlow<T> {
             move |(), x| {
-                if predicate(&x) { ControlFlow::Break(x) } else { ControlFlow::CONTINUE }
+                if predicate(&x) { ControlFlow::Break(x) } else { ControlFlow::Continue(()) }
             }
         }
 
index a4a665d48d58cfa15cade9488137e37e2d0d248c..5a0b8594104ee1d1d5e120f5704539205d8bf946 100644 (file)
@@ -2601,10 +2601,10 @@ fn all<F>(&mut self, f: F) -> bool
         #[inline]
         fn check<T>(mut f: impl FnMut(T) -> bool) -> impl FnMut((), T) -> ControlFlow<()> {
             move |(), x| {
-                if f(x) { ControlFlow::CONTINUE } else { ControlFlow::BREAK }
+                if f(x) { ControlFlow::Continue(()) } else { ControlFlow::Break(()) }
             }
         }
-        self.try_fold((), check(f)) == ControlFlow::CONTINUE
+        self.try_fold((), check(f)) == ControlFlow::Continue(())
     }
 
     /// Tests if any element of the iterator matches a predicate.
@@ -2654,11 +2654,11 @@ fn any<F>(&mut self, f: F) -> bool
         #[inline]
         fn check<T>(mut f: impl FnMut(T) -> bool) -> impl FnMut((), T) -> ControlFlow<()> {
             move |(), x| {
-                if f(x) { ControlFlow::BREAK } else { ControlFlow::CONTINUE }
+                if f(x) { ControlFlow::Break(()) } else { ControlFlow::Continue(()) }
             }
         }
 
-        self.try_fold((), check(f)) == ControlFlow::BREAK
+        self.try_fold((), check(f)) == ControlFlow::Break(())
     }
 
     /// Searches for an element of an iterator that satisfies a predicate.
@@ -2717,7 +2717,7 @@ fn find<P>(&mut self, predicate: P) -> Option<Self::Item>
         #[inline]
         fn check<T>(mut predicate: impl FnMut(&T) -> bool) -> impl FnMut((), T) -> ControlFlow<T> {
             move |(), x| {
-                if predicate(&x) { ControlFlow::Break(x) } else { ControlFlow::CONTINUE }
+                if predicate(&x) { ControlFlow::Break(x) } else { ControlFlow::Continue(()) }
             }
         }
 
@@ -2749,7 +2749,7 @@ fn find_map<B, F>(&mut self, f: F) -> Option<B>
         fn check<T, B>(mut f: impl FnMut(T) -> Option<B>) -> impl FnMut((), T) -> ControlFlow<B> {
             move |(), x| match f(x) {
                 Some(x) => ControlFlow::Break(x),
-                None => ControlFlow::CONTINUE,
+                None => ControlFlow::Continue(()),
             }
         }
 
@@ -2812,7 +2812,7 @@ fn check<I, V, R>(
             R: Residual<Option<I>>,
         {
             move |(), x| match f(&x).branch() {
-                ControlFlow::Continue(false) => ControlFlow::CONTINUE,
+                ControlFlow::Continue(false) => ControlFlow::Continue(()),
                 ControlFlow::Continue(true) => ControlFlow::Break(Try::from_output(Some(x))),
                 ControlFlow::Break(r) => ControlFlow::Break(FromResidual::from_residual(r)),
             }
@@ -3491,7 +3491,7 @@ fn compare<X, Y, F>(mut cmp: F) -> impl FnMut(X, Y) -> ControlFlow<Ordering>
             F: FnMut(X, Y) -> Ordering,
         {
             move |x, y| match cmp(x, y) {
-                Ordering::Equal => ControlFlow::CONTINUE,
+                Ordering::Equal => ControlFlow::Continue(()),
                 non_eq => ControlFlow::Break(non_eq),
             }
         }
@@ -3567,7 +3567,7 @@ fn compare<X, Y, F>(mut partial_cmp: F) -> impl FnMut(X, Y) -> ControlFlow<Optio
             F: FnMut(X, Y) -> Option<Ordering>,
         {
             move |x, y| match partial_cmp(x, y) {
-                Some(Ordering::Equal) => ControlFlow::CONTINUE,
+                Some(Ordering::Equal) => ControlFlow::Continue(()),
                 non_eq => ControlFlow::Break(non_eq),
             }
         }
@@ -3625,7 +3625,7 @@ fn compare<X, Y, F>(mut eq: F) -> impl FnMut(X, Y) -> ControlFlow<()>
             F: FnMut(X, Y) -> bool,
         {
             move |x, y| {
-                if eq(x, y) { ControlFlow::CONTINUE } else { ControlFlow::BREAK }
+                if eq(x, y) { ControlFlow::Continue(()) } else { ControlFlow::Break(()) }
             }
         }
 
@@ -3859,7 +3859,7 @@ unsafe fn __iterator_get_unchecked(&mut self, _idx: usize) -> Self::Item
 
 /// Compares two iterators element-wise using the given function.
 ///
-/// If `ControlFlow::CONTINUE` is returned from the function, the comparison moves on to the next
+/// If `ControlFlow::Continue(())` is returned from the function, the comparison moves on to the next
 /// elements of both iterators. Returning `ControlFlow::Break(x)` short-circuits the iteration and
 /// returns `ControlFlow::Break(x)`. If one of the iterators runs out of elements,
 /// `ControlFlow::Continue(ord)` is returned where `ord` is the result of comparing the lengths of
index cd183540cd5e9d3c5d20d2e4d12156a7502571c5..117706fb4b28d3379bf1d8176a4cf9bbc2832018 100644 (file)
@@ -259,46 +259,3 @@ pub(crate) fn into_try(self) -> R {
         }
     }
 }
-
-impl<B> ControlFlow<B, ()> {
-    /// It's frequently the case that there's no value needed with `Continue`,
-    /// so this provides a way to avoid typing `(())`, if you prefer it.
-    ///
-    /// # Examples
-    ///
-    /// ```
-    /// #![feature(control_flow_enum)]
-    /// use std::ops::ControlFlow;
-    ///
-    /// let mut partial_sum = 0;
-    /// let last_used = (1..10).chain(20..25).try_for_each(|x| {
-    ///     partial_sum += x;
-    ///     if partial_sum > 100 { ControlFlow::Break(x) }
-    ///     else { ControlFlow::CONTINUE }
-    /// });
-    /// assert_eq!(last_used.break_value(), Some(22));
-    /// ```
-    #[unstable(feature = "control_flow_enum", reason = "new API", issue = "75744")]
-    pub const CONTINUE: Self = ControlFlow::Continue(());
-}
-
-impl<C> ControlFlow<(), C> {
-    /// APIs like `try_for_each` don't need values with `Break`,
-    /// so this provides a way to avoid typing `(())`, if you prefer it.
-    ///
-    /// # Examples
-    ///
-    /// ```
-    /// #![feature(control_flow_enum)]
-    /// use std::ops::ControlFlow;
-    ///
-    /// let mut partial_sum = 0;
-    /// (1..10).chain(20..25).try_for_each(|x| {
-    ///     if partial_sum > 100 { ControlFlow::BREAK }
-    ///     else { partial_sum += x; ControlFlow::CONTINUE }
-    /// });
-    /// assert_eq!(partial_sum, 108);
-    /// ```
-    #[unstable(feature = "control_flow_enum", reason = "new API", issue = "75744")]
-    pub const BREAK: Self = ControlFlow::Break(());
-}
index eb582be012bd54d72940ab3c694d99c769e0b236..839fdc96632d1eea31a5e621d9ed66a24848d320 100644 (file)
@@ -12,6 +12,8 @@
 
 use rand::RngCore;
 
+#[cfg(target_os = "macos")]
+use crate::ffi::{c_char, c_int};
 #[cfg(unix)]
 use crate::os::unix::fs::symlink as symlink_dir;
 #[cfg(unix)]
@@ -24,8 +26,6 @@
 use crate::sys::fs::symlink_junction;
 #[cfg(target_os = "macos")]
 use crate::sys::weak::weak;
-#[cfg(target_os = "macos")]
-use libc::{c_char, c_int};
 
 macro_rules! check {
     ($e:expr) => {
index 99cc01863104850f21f1aba37334021cc8cba5f6..762f7a7c9a1a0a5907b4c6f39a9bb29b8796f96b 100644 (file)
 #![feature(const_ip)]
 #![feature(const_ipv4)]
 #![feature(const_ipv6)]
-#![feature(const_socketaddr)]
 #![feature(thread_local_internals)]
 //
 #![default_lib_allocator]
index 33b0dfa03e0ed3b029138814e459330962dbd1f5..1264bae809b264c21015bcbdc3f0d632dae93c46 100644 (file)
@@ -133,7 +133,7 @@ impl SocketAddr {
     /// ```
     #[stable(feature = "ip_addr", since = "1.7.0")]
     #[must_use]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn new(ip: IpAddr, port: u16) -> SocketAddr {
         match ip {
             IpAddr::V4(a) => SocketAddr::V4(SocketAddrV4::new(a, port)),
@@ -153,7 +153,7 @@ pub const fn new(ip: IpAddr, port: u16) -> SocketAddr {
     /// ```
     #[must_use]
     #[stable(feature = "ip_addr", since = "1.7.0")]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn ip(&self) -> IpAddr {
         match *self {
             SocketAddr::V4(ref a) => IpAddr::V4(*a.ip()),
@@ -194,7 +194,7 @@ pub fn set_ip(&mut self, new_ip: IpAddr) {
     /// ```
     #[must_use]
     #[stable(feature = "rust1", since = "1.0.0")]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn port(&self) -> u16 {
         match *self {
             SocketAddr::V4(ref a) => a.port(),
@@ -238,7 +238,7 @@ pub fn set_port(&mut self, new_port: u16) {
     /// ```
     #[must_use]
     #[stable(feature = "sockaddr_checker", since = "1.16.0")]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn is_ipv4(&self) -> bool {
         matches!(*self, SocketAddr::V4(_))
     }
@@ -260,7 +260,7 @@ pub const fn is_ipv4(&self) -> bool {
     /// ```
     #[must_use]
     #[stable(feature = "sockaddr_checker", since = "1.16.0")]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn is_ipv6(&self) -> bool {
         matches!(*self, SocketAddr::V6(_))
     }
@@ -280,7 +280,7 @@ impl SocketAddrV4 {
     /// ```
     #[stable(feature = "rust1", since = "1.0.0")]
     #[must_use]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn new(ip: Ipv4Addr, port: u16) -> SocketAddrV4 {
         SocketAddrV4 { ip, port }
     }
@@ -297,7 +297,7 @@ pub const fn new(ip: Ipv4Addr, port: u16) -> SocketAddrV4 {
     /// ```
     #[must_use]
     #[stable(feature = "rust1", since = "1.0.0")]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn ip(&self) -> &Ipv4Addr {
         &self.ip
     }
@@ -330,7 +330,7 @@ pub fn set_ip(&mut self, new_ip: Ipv4Addr) {
     /// ```
     #[must_use]
     #[stable(feature = "rust1", since = "1.0.0")]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn port(&self) -> u16 {
         self.port
     }
@@ -371,7 +371,7 @@ impl SocketAddrV6 {
     /// ```
     #[stable(feature = "rust1", since = "1.0.0")]
     #[must_use]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn new(ip: Ipv6Addr, port: u16, flowinfo: u32, scope_id: u32) -> SocketAddrV6 {
         SocketAddrV6 { ip, port, flowinfo, scope_id }
     }
@@ -388,7 +388,7 @@ pub const fn new(ip: Ipv6Addr, port: u16, flowinfo: u32, scope_id: u32) -> Socke
     /// ```
     #[must_use]
     #[stable(feature = "rust1", since = "1.0.0")]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn ip(&self) -> &Ipv6Addr {
         &self.ip
     }
@@ -421,7 +421,7 @@ pub fn set_ip(&mut self, new_ip: Ipv6Addr) {
     /// ```
     #[must_use]
     #[stable(feature = "rust1", since = "1.0.0")]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn port(&self) -> u16 {
         self.port
     }
@@ -464,7 +464,7 @@ pub fn set_port(&mut self, new_port: u16) {
     /// ```
     #[must_use]
     #[stable(feature = "rust1", since = "1.0.0")]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn flowinfo(&self) -> u32 {
         self.flowinfo
     }
@@ -504,7 +504,7 @@ pub fn set_flowinfo(&mut self, new_flowinfo: u32) {
     /// ```
     #[must_use]
     #[stable(feature = "rust1", since = "1.0.0")]
-    #[rustc_const_unstable(feature = "const_socketaddr", issue = "82485")]
+    #[rustc_const_stable(feature = "const_socketaddr", since = "CURRENT_RUSTC_VERSION")]
     pub const fn scope_id(&self) -> u32 {
         self.scope_id
     }
index 5ec267c41e97ca77a5e3a920b30c918633e2fd77..b7046dd7c598c923f80b9bf470d957ebd64851f1 100644 (file)
@@ -1,4 +1,13 @@
 //! OS-specific networking functionality.
 
+// See cfg macros in `library/std/src/os/mod.rs` for why these platforms must
+// be special-cased during rustdoc generation.
+#[cfg(not(all(
+    doc,
+    any(
+        all(target_arch = "wasm32", not(target_os = "wasi")),
+        all(target_vendor = "fortanix", target_env = "sgx")
+    )
+)))]
 #[cfg(any(target_os = "linux", target_os = "android", doc))]
 pub(super) mod linux_ext;
index f942bdf18c1806ef55ab60733e2f2bb26a7062b5..cb52ae89b1911e06a59acc2e047dc565ed1c225b 100644 (file)
@@ -1,7 +1,7 @@
 //! On Emscripten Rust panics are wrapped in C++ exceptions, so we just forward
 //! to `__gxx_personality_v0` which is provided by Emscripten.
 
-use libc::c_int;
+use crate::ffi::c_int;
 use unwind as uw;
 
 // This is required by the compiler to exist (e.g., it's a lang item), but it's
index 5fc1b91a1c35780fda47ef22f7722a94b9966e22..41c0fe725a540bff6e99936f30b25ac29ebbb966 100644 (file)
@@ -37,7 +37,8 @@
 //! and the last personality routine transfers control to the catch block.
 
 use super::dwarf::eh::{self, EHAction, EHContext};
-use libc::{c_int, uintptr_t};
+use crate::ffi::c_int;
+use libc::uintptr_t;
 use unwind as uw;
 
 // Register ids were lifted from LLVM's TargetLowering::getExceptionPointerRegister()
index 3edbe7280774d44d75ff56e5bb4100ff6b10d272..403a5e627f1e7fe6b2b6b71c0c2c13ede23a3f5a 100644 (file)
@@ -7,6 +7,7 @@
 #[cfg(any(
     target_arch = "x86",
     target_arch = "arm",
+    target_arch = "m68k",
     target_arch = "mips",
     target_arch = "powerpc",
     target_arch = "powerpc64",
index 5d43676adbb11f0428d99c796fe58eaa3b3b2c45..eb9167cd8552bb047fd7ef1a4707fd43b15a6be4 100644 (file)
@@ -221,7 +221,7 @@ fn ptr(&self) -> c::LPVOID {
 
 fn keyed_event_handle() -> c::HANDLE {
     const INVALID: c::HANDLE = ptr::invalid_mut(!0);
-    static HANDLE: AtomicPtr<libc::c_void> = AtomicPtr::new(INVALID);
+    static HANDLE: AtomicPtr<crate::ffi::c_void> = AtomicPtr::new(INVALID);
     match HANDLE.load(Relaxed) {
         INVALID => {
             let mut handle = c::INVALID_HANDLE_VALUE;
index fad4a63331b5976b11c57dfddf04a1aaea890e3d..2c38dfecf9734d75048cf2c3f2d92cb261ab8e75 100644 (file)
@@ -14,7 +14,7 @@
 use crate::sys_common::{AsInner, FromInner, IntoInner};
 use crate::time::Duration;
 
-use libc::{c_int, c_void};
+use crate::ffi::{c_int, c_void};
 
 cfg_if::cfg_if! {
     if #[cfg(any(
@@ -47,7 +47,7 @@
         target_os = "dragonfly", target_os = "freebsd",
         target_os = "openbsd", target_os = "netbsd",
         target_os = "solaris", target_os = "illumos"))] {
-        use libc::c_uchar;
+        use crate::ffi::c_uchar;
         type IpV4MultiCastType = c_uchar;
     } else {
         type IpV4MultiCastType = c_int;
@@ -127,8 +127,8 @@ fn to_ipv6mr_interface(value: u32) -> c_int {
 }
 
 #[cfg(not(target_os = "android"))]
-fn to_ipv6mr_interface(value: u32) -> libc::c_uint {
-    value as libc::c_uint
+fn to_ipv6mr_interface(value: u32) -> crate::ffi::c_uint {
+    value as crate::ffi::c_uint
 }
 
 ////////////////////////////////////////////////////////////////////////////////
index d44b96cfb991ece07a53944f225a0624737b2921..522b3b7e851ff725ab97c2c4002eb47aeeb84740 100644 (file)
@@ -1431,6 +1431,13 @@ fn read_stamp_file(&self, stamp: &Path) -> Vec<(PathBuf, DependencyType)> {
             return Vec::new();
         }
 
+        if !stamp.exists() {
+            eprintln!(
+                "Warning: Unable to find the stamp file, did you try to keep a nonexistent build stage?"
+            );
+            crate::detail_exit(1);
+        }
+
         let mut paths = Vec::new();
         let contents = t!(fs::read(stamp), &stamp);
         // This is the method we use for extracting paths from the stamp file passed to us. See
index 614a262beda9bbc51e0ab20f06bd510adeb87d96..e2ced191a00c0e267eaf71e3d353eed379d7bd6b 100644 (file)
@@ -383,13 +383,10 @@ fn clean_middle_term<'tcx>(
 fn clean_hir_term<'tcx>(term: &hir::Term<'tcx>, cx: &mut DocContext<'tcx>) -> Term {
     match term {
         hir::Term::Ty(ty) => Term::Type(clean_ty(ty, cx)),
-        hir::Term::Const(c) => {
-            let def_id = cx.tcx.hir().local_def_id(c.hir_id);
-            Term::Constant(clean_middle_const(
-                ty::Binder::dummy(ty::Const::from_anon_const(cx.tcx, def_id)),
-                cx,
-            ))
-        }
+        hir::Term::Const(c) => Term::Constant(clean_middle_const(
+            ty::Binder::dummy(ty::Const::from_anon_const(cx.tcx, c.def_id)),
+            cx,
+        )),
     }
 }
 
@@ -524,12 +521,11 @@ fn clean_generic_param<'tcx>(
     generics: Option<&hir::Generics<'tcx>>,
     param: &hir::GenericParam<'tcx>,
 ) -> GenericParamDef {
-    let did = cx.tcx.hir().local_def_id(param.hir_id);
     let (name, kind) = match param.kind {
         hir::GenericParamKind::Lifetime { .. } => {
             let outlives = if let Some(generics) = generics {
                 generics
-                    .outlives_for_param(did)
+                    .outlives_for_param(param.def_id)
                     .filter(|bp| !bp.in_where_clause)
                     .flat_map(|bp| bp.bounds)
                     .map(|bound| match bound {
@@ -545,7 +541,7 @@ fn clean_generic_param<'tcx>(
         hir::GenericParamKind::Type { ref default, synthetic } => {
             let bounds = if let Some(generics) = generics {
                 generics
-                    .bounds_for_param(did)
+                    .bounds_for_param(param.def_id)
                     .filter(|bp| bp.origin != PredicateOrigin::WhereClause)
                     .flat_map(|bp| bp.bounds)
                     .filter_map(|x| clean_generic_bound(x, cx))
@@ -556,7 +552,7 @@ fn clean_generic_param<'tcx>(
             (
                 param.name.ident().name,
                 GenericParamDefKind::Type {
-                    did: did.to_def_id(),
+                    did: param.def_id.to_def_id(),
                     bounds,
                     default: default.map(|t| clean_ty(t, cx)).map(Box::new),
                     synthetic,
@@ -566,12 +562,10 @@ fn clean_generic_param<'tcx>(
         hir::GenericParamKind::Const { ty, default } => (
             param.name.ident().name,
             GenericParamDefKind::Const {
-                did: did.to_def_id(),
+                did: param.def_id.to_def_id(),
                 ty: Box::new(clean_ty(ty, cx)),
-                default: default.map(|ct| {
-                    let def_id = cx.tcx.hir().local_def_id(ct.hir_id);
-                    Box::new(ty::Const::from_anon_const(cx.tcx, def_id).to_string())
-                }),
+                default: default
+                    .map(|ct| Box::new(ty::Const::from_anon_const(cx.tcx, ct.def_id).to_string())),
             },
         ),
     };
@@ -1548,18 +1542,16 @@ fn maybe_expand_private_type_alias<'tcx>(
                     _ => None,
                 });
                 if let Some(lt) = lifetime {
-                    let lt_def_id = cx.tcx.hir().local_def_id(param.hir_id);
                     let cleaned = if !lt.is_anonymous() {
                         clean_lifetime(lt, cx)
                     } else {
                         Lifetime::elided()
                     };
-                    substs.insert(lt_def_id.to_def_id(), SubstParam::Lifetime(cleaned));
+                    substs.insert(param.def_id.to_def_id(), SubstParam::Lifetime(cleaned));
                 }
                 indices.lifetimes += 1;
             }
             hir::GenericParamKind::Type { ref default, .. } => {
-                let ty_param_def_id = cx.tcx.hir().local_def_id(param.hir_id);
                 let mut j = 0;
                 let type_ = generic_args.args.iter().find_map(|arg| match arg {
                     hir::GenericArg::Type(ty) => {
@@ -1572,17 +1564,14 @@ fn maybe_expand_private_type_alias<'tcx>(
                     _ => None,
                 });
                 if let Some(ty) = type_ {
-                    substs.insert(ty_param_def_id.to_def_id(), SubstParam::Type(clean_ty(ty, cx)));
+                    substs.insert(param.def_id.to_def_id(), SubstParam::Type(clean_ty(ty, cx)));
                 } else if let Some(default) = *default {
-                    substs.insert(
-                        ty_param_def_id.to_def_id(),
-                        SubstParam::Type(clean_ty(default, cx)),
-                    );
+                    substs
+                        .insert(param.def_id.to_def_id(), SubstParam::Type(clean_ty(default, cx)));
                 }
                 indices.types += 1;
             }
             hir::GenericParamKind::Const { .. } => {
-                let const_param_def_id = cx.tcx.hir().local_def_id(param.hir_id);
                 let mut j = 0;
                 let const_ = generic_args.args.iter().find_map(|arg| match arg {
                     hir::GenericArg::Const(ct) => {
@@ -1596,7 +1585,7 @@ fn maybe_expand_private_type_alias<'tcx>(
                 });
                 if let Some(ct) = const_ {
                     substs.insert(
-                        const_param_def_id.to_def_id(),
+                        param.def_id.to_def_id(),
                         SubstParam::Constant(clean_const(ct, cx)),
                     );
                 }
@@ -1624,7 +1613,6 @@ pub(crate) fn clean_ty<'tcx>(ty: &hir::Ty<'tcx>, cx: &mut DocContext<'tcx>) -> T
             let length = match length {
                 hir::ArrayLen::Infer(_, _) => "_".to_string(),
                 hir::ArrayLen::Body(anon_const) => {
-                    let def_id = cx.tcx.hir().local_def_id(anon_const.hir_id);
                     // NOTE(min_const_generics): We can't use `const_eval_poly` for constants
                     // as we currently do not supply the parent generics to anonymous constants
                     // but do allow `ConstKind::Param`.
@@ -1632,8 +1620,8 @@ pub(crate) fn clean_ty<'tcx>(ty: &hir::Ty<'tcx>, cx: &mut DocContext<'tcx>) -> T
                     // `const_eval_poly` tries to first substitute generic parameters which
                     // results in an ICE while manually constructing the constant and using `eval`
                     // does nothing for `ConstKind::Param`.
-                    let ct = ty::Const::from_anon_const(cx.tcx, def_id);
-                    let param_env = cx.tcx.param_env(def_id);
+                    let ct = ty::Const::from_anon_const(cx.tcx, anon_const.def_id);
+                    let param_env = cx.tcx.param_env(anon_const.def_id);
                     print_const(cx, ct.eval(cx.tcx, param_env))
                 }
             };
@@ -1930,8 +1918,7 @@ fn clean_middle_opaque_bounds<'tcx>(
 }
 
 pub(crate) fn clean_field<'tcx>(field: &hir::FieldDef<'tcx>, cx: &mut DocContext<'tcx>) -> Item {
-    let def_id = cx.tcx.hir().local_def_id(field.hir_id).to_def_id();
-    clean_field_with_def_id(def_id, field.ident.name, clean_ty(field.ty, cx), cx)
+    clean_field_with_def_id(field.def_id.to_def_id(), field.ident.name, clean_ty(field.ty, cx), cx)
 }
 
 pub(crate) fn clean_middle_field<'tcx>(field: &ty::FieldDef, cx: &mut DocContext<'tcx>) -> Item {
@@ -1981,10 +1968,8 @@ fn clean_variant_data<'tcx>(
     disr_expr: &Option<hir::AnonConst>,
     cx: &mut DocContext<'tcx>,
 ) -> Variant {
-    let discriminant = disr_expr.map(|disr| Discriminant {
-        expr: Some(disr.body),
-        value: cx.tcx.hir().local_def_id(disr.hir_id).to_def_id(),
-    });
+    let discriminant = disr_expr
+        .map(|disr| Discriminant { expr: Some(disr.body), value: disr.def_id.to_def_id() });
 
     let kind = match variant {
         hir::VariantData::Struct(..) => VariantKind::Struct(VariantStruct {
index bbdc91c8d2ec8fbbe3b686002cd0bf34e249c32b..4c8db2c6784a52267c06cfb68db3c2382296624c 100644 (file)
@@ -61,14 +61,14 @@ pub(super) fn finish(mut self) -> String {
     /// and returns [`ControlFlow::Break`].
     pub(super) fn push(&mut self, text: &str) -> ControlFlow<(), ()> {
         if self.len + text.len() > self.limit {
-            return ControlFlow::BREAK;
+            return ControlFlow::Break(());
         }
 
         self.flush_queue();
         write!(self.buf, "{}", Escape(text)).unwrap();
         self.len += text.len();
 
-        ControlFlow::CONTINUE
+        ControlFlow::Continue(())
     }
 
     /// Open an HTML tag.
index 2d02b8a16da67415c0e6b8f8016a318bfe117f89..2185c034890fa3de43c28546d9a6844f465a2d99 100644 (file)
@@ -83,7 +83,7 @@ fn past_the_limit() {
         buf.push("word#")?;
         buf.push(&n.to_string())?;
         buf.close_tag();
-        ControlFlow::CONTINUE
+        ControlFlow::Continue(())
     });
     buf.close_tag();
     assert_eq!(
index d7739b8534f309e29eec30e308c77ee97b0702b6..00e3f859bfcb30dd62dd1f1cde00a9ba41a294ea 100644 (file)
@@ -1188,18 +1188,18 @@ fn markdown_summary_with_limit(
             Event::Start(tag) => match tag {
                 Tag::Emphasis => buf.open_tag("em"),
                 Tag::Strong => buf.open_tag("strong"),
-                Tag::CodeBlock(..) => return ControlFlow::BREAK,
+                Tag::CodeBlock(..) => return ControlFlow::Break(()),
                 _ => {}
             },
             Event::End(tag) => match tag {
                 Tag::Emphasis | Tag::Strong => buf.close_tag(),
-                Tag::Paragraph | Tag::Heading(..) => return ControlFlow::BREAK,
+                Tag::Paragraph | Tag::Heading(..) => return ControlFlow::Break(()),
                 _ => {}
             },
             Event::HardBreak | Event::SoftBreak => buf.push(" ")?,
             _ => {}
         };
-        ControlFlow::CONTINUE
+        ControlFlow::Continue(())
     });
 
     (buf.finish(), stopped_early)
index 604ab147f6a16ea5a251d6ed4a71aa59f295f9ac..b9ad8ef70e917af855f4857ed46fbc40c5056194 100644 (file)
@@ -1142,7 +1142,11 @@ function loadCss(cssUrl) {
 (function() {
     let reset_button_timeout = null;
 
-    window.copy_path = but => {
+    const but = document.getElementById("copy-path");
+    if (!but) {
+        return;
+    }
+    but.onclick = () => {
         const parent = but.parentElement;
         const path = [];
 
index ee2880bf6d195e23a91bedf640a667c29052cbc3..3a1867b7feba3eda5980b0b3d8235fe59c8ab234 100644 (file)
@@ -6,7 +6,7 @@
         <a href="{{component.path|safe}}index.html">{{component.name}}</a>::<wbr>
         {%- endfor -%}
         <a class="{{item_type}}" href="#">{{name}}</a> {#- -#}
-        <button id="copy-path" onclick="copy_path(this)" title="Copy item path to clipboard"> {#- -#}
+        <button id="copy-path" title="Copy item path to clipboard"> {#- -#}
         <img src="{{static_root_path|safe}}{{clipboard_svg}}" {# -#}
                 width="19" height="18" {# -#}
                 alt="Copy item path"> {#- -#}
index a689b502f0fccb1d3fe8fd81059c9dcecba64b90..64108c882851838286923356613f93490bf5e7a2 100644 (file)
@@ -6,7 +6,6 @@
 #![feature(array_methods)]
 #![feature(assert_matches)]
 #![feature(box_patterns)]
-#![feature(control_flow_enum)]
 #![feature(drain_filter)]
 #![feature(is_terminal)]
 #![feature(let_chains)]
index 939bdbcdc7cd7e245b733bed959c419f0b336f76..e8106beec37423b191d554b31c4700f8922bb776 100644 (file)
@@ -6,9 +6,10 @@
 use rustc_ast::ast::LitKind;
 use rustc_errors::Applicability;
 use rustc_hir::intravisit::{walk_expr, FnKind, Visitor};
-use rustc_hir::{BinOpKind, Body, Expr, ExprKind, FnDecl, HirId, UnOp};
+use rustc_hir::{BinOpKind, Body, Expr, ExprKind, FnDecl, UnOp};
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map::Span;
 use rustc_span::sym;
 
@@ -82,7 +83,7 @@ fn check_fn(
         _: &'tcx FnDecl<'_>,
         body: &'tcx Body<'_>,
         _: Span,
-        _: HirId,
+        _: LocalDefId,
     ) {
         NonminimalBoolVisitor { cx }.visit_body(body);
     }
index 1c3a89a97824c31ccdb1f4888fb2b85eb67b88ff..e8531157e0f7a538465c5adf5b3c4d055ea322d1 100644 (file)
@@ -8,9 +8,10 @@
 use core::ops::ControlFlow;
 use rustc_ast::ast::Attribute;
 use rustc_hir::intravisit::FnKind;
-use rustc_hir::{Body, Expr, ExprKind, FnDecl, HirId};
+use rustc_hir::{Body, Expr, ExprKind, FnDecl};
 use rustc_lint::{LateContext, LateLintPass, LintContext};
 use rustc_session::{declare_tool_lint, impl_lint_pass};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map::Span;
 use rustc_span::{sym, BytePos};
 
@@ -140,9 +141,8 @@ fn check_fn(
         decl: &'tcx FnDecl<'_>,
         body: &'tcx Body<'_>,
         span: Span,
-        hir_id: HirId,
+        def_id: LocalDefId,
     ) {
-        let def_id = cx.tcx.hir().local_def_id(hir_id);
         if !cx.tcx.has_attr(def_id.to_def_id(), sym::test) {
             let expr = if is_async_fn(kind) {
                 match get_async_fn_body(cx.tcx, body) {
index 8e921839e8b2fd48ac55a06530d3f33ee8a35390..6c333afacc648b41d567d36b9b782095d8936fce 100644 (file)
@@ -778,20 +778,20 @@ fn walk_parents<'tcx>(
 
             Node::Expr(parent) if parent.span.ctxt() == ctxt => match parent.kind {
                 ExprKind::Ret(_) => {
-                    let owner_id = cx.tcx.hir().body_owner(cx.enclosing_body.unwrap());
+                    let owner_id = cx.tcx.hir().body_owner_def_id(cx.enclosing_body.unwrap());
                     Some(
                         if let Node::Expr(
                             closure_expr @ Expr {
                                 kind: ExprKind::Closure(closure),
                                 ..
                             },
-                        ) = cx.tcx.hir().get(owner_id)
+                        ) = cx.tcx.hir().get_by_def_id(owner_id)
                         {
                             closure_result_position(cx, closure, cx.typeck_results().expr_ty(closure_expr), precedence)
                         } else {
                             let output = cx
                                 .tcx
-                                .erase_late_bound_regions(cx.tcx.fn_sig(cx.tcx.hir().local_def_id(owner_id)).subst_identity().output());
+                                .erase_late_bound_regions(cx.tcx.fn_sig(owner_id).subst_identity().output());
                             ty_auto_deref_stability(cx, output, precedence).position_for_result(cx)
                         },
                     )
index 248d7388410673c3da902461a252936750345e67..f8fc726d603f8dd5a32fdc1f5c740de1871f4f01 100644 (file)
@@ -7,7 +7,7 @@
 use rustc_hir::def_id::DefId;
 use rustc_hir::intravisit::{walk_expr, walk_fn, walk_item, FnKind, Visitor};
 use rustc_hir::{
-    self as hir, BlockCheckMode, BodyId, Constness, Expr, ExprKind, FnDecl, HirId, Impl, Item, ItemKind, UnsafeSource,
+    self as hir, BlockCheckMode, BodyId, Constness, Expr, ExprKind, FnDecl, Impl, Item, ItemKind, UnsafeSource,
     Unsafety,
 };
 use rustc_lint::{LateContext, LateLintPass};
@@ -18,6 +18,7 @@
     TraitPredicate, Ty, TyCtxt,
 };
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map::Span;
 use rustc_span::sym;
 
@@ -425,7 +426,7 @@ struct UnsafeVisitor<'a, 'tcx> {
 impl<'tcx> Visitor<'tcx> for UnsafeVisitor<'_, 'tcx> {
     type NestedFilter = nested_filter::All;
 
-    fn visit_fn(&mut self, kind: FnKind<'tcx>, decl: &'tcx FnDecl<'_>, body_id: BodyId, _: Span, id: HirId) {
+    fn visit_fn(&mut self, kind: FnKind<'tcx>, decl: &'tcx FnDecl<'_>, body_id: BodyId, _: Span, id: LocalDefId) {
         if self.has_unsafe {
             return;
         }
index f7a3d6d53f7141c21400d1f64fa748af75a6eaf6..127201b72e275948a46124bcb0c3cb7e97fac2e7 100644 (file)
@@ -23,7 +23,6 @@
 use rustc_parse::parser::ForceCollect;
 use rustc_session::parse::ParseSess;
 use rustc_session::{declare_tool_lint, impl_lint_pass};
-use rustc_span::def_id::LocalDefId;
 use rustc_span::edition::Edition;
 use rustc_span::source_map::{BytePos, FilePathMapping, SourceMap, Span};
 use rustc_span::{sym, FileName, Pos};
@@ -302,7 +301,7 @@ fn check_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::Item<'_>) {
                         panic_span: None,
                     };
                     fpu.visit_expr(body.value);
-                    lint_for_missing_headers(cx, item.owner_id.def_id, sig, headers, Some(body_id), fpu.panic_span);
+                    lint_for_missing_headers(cx, item.owner_id, sig, headers, Some(body_id), fpu.panic_span);
                 }
             },
             hir::ItemKind::Impl(impl_) => {
@@ -338,7 +337,7 @@ fn check_trait_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::TraitIte
         let Some(headers) = check_attrs(cx, &self.valid_idents, attrs) else { return };
         if let hir::TraitItemKind::Fn(ref sig, ..) = item.kind {
             if !in_external_macro(cx.tcx.sess, item.span) {
-                lint_for_missing_headers(cx, item.owner_id.def_id, sig, headers, None, None);
+                lint_for_missing_headers(cx, item.owner_id, sig, headers, None, None);
             }
         }
     }
@@ -357,20 +356,20 @@ fn check_impl_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::ImplItem<
                 panic_span: None,
             };
             fpu.visit_expr(body.value);
-            lint_for_missing_headers(cx, item.owner_id.def_id, sig, headers, Some(body_id), fpu.panic_span);
+            lint_for_missing_headers(cx, item.owner_id, sig, headers, Some(body_id), fpu.panic_span);
         }
     }
 }
 
 fn lint_for_missing_headers(
     cx: &LateContext<'_>,
-    def_id: LocalDefId,
+    owner_id: hir::OwnerId,
     sig: &hir::FnSig<'_>,
     headers: DocHeaders,
     body_id: Option<hir::BodyId>,
     panic_span: Option<Span>,
 ) {
-    if !cx.effective_visibilities.is_exported(def_id) {
+    if !cx.effective_visibilities.is_exported(owner_id.def_id) {
         return; // Private functions do not require doc comments
     }
 
@@ -378,13 +377,13 @@ fn lint_for_missing_headers(
     if cx
         .tcx
         .hir()
-        .parent_iter(cx.tcx.hir().local_def_id_to_hir_id(def_id))
+        .parent_iter(owner_id.into())
         .any(|(id, _node)| is_doc_hidden(cx.tcx.hir().attrs(id)))
     {
         return;
     }
 
-    let span = cx.tcx.def_span(def_id);
+    let span = cx.tcx.def_span(owner_id);
     match (headers.safety, sig.header.unsafety) {
         (false, hir::Unsafety::Unsafe) => span_lint(
             cx,
@@ -411,8 +410,7 @@ fn lint_for_missing_headers(
         );
     }
     if !headers.errors {
-        let hir_id = cx.tcx.hir().local_def_id_to_hir_id(def_id);
-        if is_type_diagnostic_item(cx, return_ty(cx, hir_id), sym::Result) {
+        if is_type_diagnostic_item(cx, return_ty(cx, owner_id), sym::Result) {
             span_lint(
                 cx,
                 MISSING_ERRORS_DOC,
index dfb43893326eb8a225ee72b7ef0ce5feaecd0886..d6ab4c25e83ef9a4593be1406173c043fd5c2585 100644 (file)
@@ -8,6 +8,7 @@
 use rustc_middle::ty::layout::LayoutOf;
 use rustc_middle::ty::{self, TraitRef, Ty};
 use rustc_session::{declare_tool_lint, impl_lint_pass};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map::Span;
 use rustc_span::symbol::kw;
 use rustc_target::spec::abi::Abi;
@@ -63,7 +64,7 @@ fn check_fn(
         _: &'tcx FnDecl<'_>,
         body: &'tcx Body<'_>,
         _: Span,
-        hir_id: HirId,
+        fn_def_id: LocalDefId,
     ) {
         if let Some(header) = fn_kind.header() {
             if header.abi != Abi::Rust {
@@ -71,7 +72,11 @@ fn check_fn(
             }
         }
 
-        let parent_id = cx.tcx.hir().get_parent_item(hir_id).def_id;
+        let parent_id = cx
+            .tcx
+            .hir()
+            .get_parent_item(cx.tcx.hir().local_def_id_to_hir_id(fn_def_id))
+            .def_id;
         let parent_node = cx.tcx.hir().find_by_def_id(parent_id);
 
         let mut trait_self_ty = None;
@@ -84,7 +89,7 @@ fn check_fn(
             // find `self` ty for this trait if relevant
             if let ItemKind::Trait(_, _, _, _, items) = item.kind {
                 for trait_item in items {
-                    if trait_item.id.hir_id() == hir_id {
+                    if trait_item.id.owner_id.def_id == fn_def_id {
                         // be sure we have `self` parameter in this function
                         if trait_item.kind == (AssocItemKind::Fn { has_self: true }) {
                             trait_self_ty = Some(
@@ -105,7 +110,6 @@ fn check_fn(
             too_large_for_stack: self.too_large_for_stack,
         };
 
-        let fn_def_id = cx.tcx.hir().local_def_id(hir_id);
         let infcx = cx.tcx.infer_ctxt().build();
         ExprUseVisitor::new(&mut v, &infcx, fn_def_id, cx.param_env, cx.typeck_results()).consume_body(body);
 
index fc2912f696e0384baa554564d683d4ba23f80fcd..9d089fcad70e695ccf8cf04160de13b42dccd497 100644 (file)
@@ -1,10 +1,11 @@
 use clippy_utils::diagnostics::span_lint_and_help;
 use clippy_utils::{get_parent_as_impl, has_repr_attr, is_bool};
 use rustc_hir::intravisit::FnKind;
-use rustc_hir::{Body, FnDecl, HirId, Item, ItemKind, TraitFn, TraitItem, TraitItemKind, Ty};
+use rustc_hir::{Body, FnDecl, Item, ItemKind, TraitFn, TraitItem, TraitItemKind, Ty};
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_session::{declare_tool_lint, impl_lint_pass};
 use rustc_span::Span;
+use rustc_span::def_id::LocalDefId;
 use rustc_target::spec::abi::Abi;
 
 declare_clippy_lint! {
@@ -168,8 +169,9 @@ fn check_fn(
         fn_decl: &'tcx FnDecl<'tcx>,
         _: &'tcx Body<'tcx>,
         span: Span,
-        hir_id: HirId,
+        def_id: LocalDefId,
     ) {
+        let hir_id = cx.tcx.hir().local_def_id_to_hir_id(def_id);
         if let Some(fn_header) = fn_kind.header()
             && fn_header.abi == Abi::Rust
             && get_parent_as_impl(cx.tcx, hir_id)
index 1fece5d1c480917f606856b1896611b8f3d2016e..9fd13084dc9e860b191a8e5de5f5b23e77ba5686 100644 (file)
@@ -79,8 +79,7 @@ fn check_item(&mut self, cx: &LateContext<'_>, item: &Item<'_>) {
             then {
                 let (lint, msg) = if let ItemKind::Struct(ref v, ..) = item.kind {
                     if v.fields().iter().any(|f| {
-                        let def_id = cx.tcx.hir().local_def_id(f.hir_id);
-                        !cx.tcx.visibility(def_id).is_public()
+                        !cx.tcx.visibility(f.def_id).is_public()
                     }) {
                         // skip structs with private fields
                         return;
index 27acad45ccf729e00e63982d50ead26f92ec6b7b..d6b50537c2e1d91e97195eeadbac58df8c5a9604 100644 (file)
@@ -1,7 +1,7 @@
 use clippy_utils::diagnostics::span_lint_and_then;
 use clippy_utils::source::snippet;
 use rustc_errors::Applicability;
-use rustc_hir::{intravisit::FnKind, Body, ExprKind, FnDecl, HirId, ImplicitSelfKind, Unsafety};
+use rustc_hir::{intravisit::FnKind, Body, ExprKind, FnDecl, ImplicitSelfKind, Unsafety};
 use rustc_lint::LateContext;
 use rustc_middle::ty;
 use rustc_span::Span;
@@ -16,7 +16,6 @@ pub fn check_fn(
     decl: &FnDecl<'_>,
     body: &Body<'_>,
     span: Span,
-    _hir_id: HirId,
 ) {
     let FnKind::Method(ref ident, sig) = kind else {
             return;
index 9dbce3f889bef117ddfcbba93d9de08a85bd60bf..4399c68e130f7b7330c1c2a6f782d26ab297fc1d 100644 (file)
@@ -9,6 +9,7 @@
 use rustc_hir::intravisit;
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_session::{declare_tool_lint, impl_lint_pass};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::Span;
 
 declare_clippy_lint! {
@@ -363,12 +364,13 @@ fn check_fn(
         decl: &'tcx hir::FnDecl<'_>,
         body: &'tcx hir::Body<'_>,
         span: Span,
-        hir_id: hir::HirId,
+        def_id: LocalDefId,
     ) {
+        let hir_id = cx.tcx.hir().local_def_id_to_hir_id(def_id);
         too_many_arguments::check_fn(cx, kind, decl, span, hir_id, self.too_many_arguments_threshold);
         too_many_lines::check_fn(cx, kind, span, body, self.too_many_lines_threshold);
-        not_unsafe_ptr_arg_deref::check_fn(cx, kind, decl, body, hir_id);
-        misnamed_getters::check_fn(cx, kind, decl, body, span, hir_id);
+        not_unsafe_ptr_arg_deref::check_fn(cx, kind, decl, body, def_id);
+        misnamed_getters::check_fn(cx, kind, decl, body, span);
     }
 
     fn check_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::Item<'_>) {
index d22bede36b419944b372f84594dd294b926442e1..29bdc46b647d5a8b807803d34f56949d5e0289bb 100644 (file)
@@ -1,6 +1,6 @@
 use rustc_ast::ast::Attribute;
 use rustc_errors::Applicability;
-use rustc_hir::def_id::{DefIdSet, LocalDefId};
+use rustc_hir::def_id::DefIdSet;
 use rustc_hir::{self as hir, def::Res, QPath};
 use rustc_lint::{LateContext, LintContext};
 use rustc_middle::{
@@ -27,14 +27,14 @@ pub(super) fn check_item<'tcx>(cx: &LateContext<'tcx>, item: &'tcx hir::Item<'_>
         let is_public = cx.effective_visibilities.is_exported(item.owner_id.def_id);
         let fn_header_span = item.span.with_hi(sig.decl.output.span().hi());
         if let Some(attr) = attr {
-            check_needless_must_use(cx, sig.decl, item.hir_id(), item.span, fn_header_span, attr);
+            check_needless_must_use(cx, sig.decl, item.owner_id, item.span, fn_header_span, attr);
         } else if is_public && !is_proc_macro(cx.sess(), attrs) && !attrs.iter().any(|a| a.has_name(sym::no_mangle)) {
             check_must_use_candidate(
                 cx,
                 sig.decl,
                 cx.tcx.hir().body(*body_id),
                 item.span,
-                item.owner_id.def_id,
+                item.owner_id,
                 item.span.with_hi(sig.decl.output.span().hi()),
                 "this function could have a `#[must_use]` attribute",
             );
@@ -49,7 +49,7 @@ pub(super) fn check_impl_item<'tcx>(cx: &LateContext<'tcx>, item: &'tcx hir::Imp
         let attrs = cx.tcx.hir().attrs(item.hir_id());
         let attr = cx.tcx.get_attr(item.owner_id.to_def_id(), sym::must_use);
         if let Some(attr) = attr {
-            check_needless_must_use(cx, sig.decl, item.hir_id(), item.span, fn_header_span, attr);
+            check_needless_must_use(cx, sig.decl, item.owner_id, item.span, fn_header_span, attr);
         } else if is_public
             && !is_proc_macro(cx.sess(), attrs)
             && trait_ref_of_method(cx, item.owner_id.def_id).is_none()
@@ -59,7 +59,7 @@ pub(super) fn check_impl_item<'tcx>(cx: &LateContext<'tcx>, item: &'tcx hir::Imp
                 sig.decl,
                 cx.tcx.hir().body(*body_id),
                 item.span,
-                item.owner_id.def_id,
+                item.owner_id,
                 item.span.with_hi(sig.decl.output.span().hi()),
                 "this method could have a `#[must_use]` attribute",
             );
@@ -75,7 +75,7 @@ pub(super) fn check_trait_item<'tcx>(cx: &LateContext<'tcx>, item: &'tcx hir::Tr
         let attrs = cx.tcx.hir().attrs(item.hir_id());
         let attr = cx.tcx.get_attr(item.owner_id.to_def_id(), sym::must_use);
         if let Some(attr) = attr {
-            check_needless_must_use(cx, sig.decl, item.hir_id(), item.span, fn_header_span, attr);
+            check_needless_must_use(cx, sig.decl, item.owner_id, item.span, fn_header_span, attr);
         } else if let hir::TraitFn::Provided(eid) = *eid {
             let body = cx.tcx.hir().body(eid);
             if attr.is_none() && is_public && !is_proc_macro(cx.sess(), attrs) {
@@ -84,7 +84,7 @@ pub(super) fn check_trait_item<'tcx>(cx: &LateContext<'tcx>, item: &'tcx hir::Tr
                     sig.decl,
                     body,
                     item.span,
-                    item.owner_id.def_id,
+                    item.owner_id,
                     item.span.with_hi(sig.decl.output.span().hi()),
                     "this method could have a `#[must_use]` attribute",
                 );
@@ -96,7 +96,7 @@ pub(super) fn check_trait_item<'tcx>(cx: &LateContext<'tcx>, item: &'tcx hir::Tr
 fn check_needless_must_use(
     cx: &LateContext<'_>,
     decl: &hir::FnDecl<'_>,
-    item_id: hir::HirId,
+    item_id: hir::OwnerId,
     item_span: Span,
     fn_header_span: Span,
     attr: &Attribute,
@@ -131,7 +131,7 @@ fn check_must_use_candidate<'tcx>(
     decl: &'tcx hir::FnDecl<'_>,
     body: &'tcx hir::Body<'_>,
     item_span: Span,
-    item_id: LocalDefId,
+    item_id: hir::OwnerId,
     fn_span: Span,
     msg: &str,
 ) {
@@ -139,8 +139,8 @@ fn check_must_use_candidate<'tcx>(
         || mutates_static(cx, body)
         || in_external_macro(cx.sess(), item_span)
         || returns_unit(decl)
-        || !cx.effective_visibilities.is_exported(item_id)
-        || is_must_use_ty(cx, return_ty(cx, cx.tcx.hir().local_def_id_to_hir_id(item_id)))
+        || !cx.effective_visibilities.is_exported(item_id.def_id)
+        || is_must_use_ty(cx, return_ty(cx, item_id))
     {
         return;
     }
index cdb5e22e759827f0190f421b3e13064b3da1dbe3..a13909a2cdb8fe9016ebc016eebc35285ba0f489 100644 (file)
@@ -17,7 +17,7 @@ pub(super) fn check_fn<'tcx>(
     kind: intravisit::FnKind<'tcx>,
     decl: &'tcx hir::FnDecl<'tcx>,
     body: &'tcx hir::Body<'tcx>,
-    hir_id: hir::HirId,
+    def_id: LocalDefId,
 ) {
     let unsafety = match kind {
         intravisit::FnKind::ItemFn(_, _, hir::FnHeader { unsafety, .. }) => unsafety,
@@ -25,7 +25,7 @@ pub(super) fn check_fn<'tcx>(
         intravisit::FnKind::Closure => return,
     };
 
-    check_raw_ptr(cx, unsafety, decl, body, cx.tcx.hir().local_def_id(hir_id));
+    check_raw_ptr(cx, unsafety, decl, body, def_id)
 }
 
 pub(super) fn check_trait_item<'tcx>(cx: &LateContext<'tcx>, item: &'tcx hir::TraitItem<'_>) {
index 2a79b18b829941c4a218843a84a135fc8b83a0ae..9fb73a371b8f478505a64142671b96256328c1bf 100644 (file)
@@ -1,11 +1,12 @@
 use clippy_utils::diagnostics::span_lint_and_then;
 use clippy_utils::return_ty;
 use rustc_hir::intravisit::FnKind;
-use rustc_hir::{Body, FnDecl, HirId};
+use rustc_hir::{Body, FnDecl};
 use rustc_infer::infer::TyCtxtInferExt;
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_middle::ty::{self, AliasTy, Clause, EarlyBinder, PredicateKind};
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::{sym, Span};
 use rustc_trait_selection::traits::error_reporting::suggestions::TypeErrCtxtExt;
 use rustc_trait_selection::traits::{self, FulfillmentError};
@@ -56,12 +57,12 @@ fn check_fn(
         decl: &'tcx FnDecl<'tcx>,
         _: &'tcx Body<'tcx>,
         _: Span,
-        hir_id: HirId,
+        fn_def_id: LocalDefId,
     ) {
         if let FnKind::Closure = kind {
             return;
         }
-        let ret_ty = return_ty(cx, hir_id);
+        let ret_ty = return_ty(cx, cx.tcx.hir().local_def_id_to_hir_id(fn_def_id).expect_owner());
         if let ty::Alias(ty::Opaque, AliasTy { def_id, substs, .. }) = *ret_ty.kind() {
             let preds = cx.tcx.explicit_item_bounds(def_id);
             let mut is_future = false;
@@ -78,8 +79,7 @@ fn check_fn(
                 let send_trait = cx.tcx.get_diagnostic_item(sym::Send).unwrap();
                 let span = decl.output.span();
                 let infcx = cx.tcx.infer_ctxt().build();
-                let def_id = cx.tcx.hir().local_def_id(hir_id);
-                let cause = traits::ObligationCause::misc(span, def_id);
+                let cause = traits::ObligationCause::misc(span, fn_def_id);
                 let send_errors = traits::fully_solve_bound(&infcx, cause, cx.param_env, ret_ty, send_trait);
                 if !send_errors.is_empty() {
                     span_lint_and_then(
index 946d04eff6f9850f6c81dce875bca890f0b9d76f..372b6ead3fe4685e6206645e17ec3a3dbd696207 100644 (file)
@@ -11,6 +11,7 @@
 use rustc_lint::{LateContext, LateLintPass, LintContext};
 use rustc_middle::lint::in_external_macro;
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::{Span, SyntaxContext};
 
 declare_clippy_lint! {
@@ -223,7 +224,7 @@ fn check_fn(
         decl: &'tcx FnDecl<'_>,
         body: &'tcx Body<'_>,
         span: Span,
-        _: HirId,
+        _: LocalDefId,
     ) {
         if (!matches!(kind, FnKind::Closure) && matches!(decl.output, FnRetTy::DefaultReturn(_)))
             || span.ctxt() != body.value.span.ctxt()
index 612c3ea8fdfd89253fbeb3e5a508628c82a1d47d..d43e5cc9b2c3d23c84edc14c121c5e2a2c654337 100644 (file)
@@ -105,7 +105,7 @@ fn check_impl_item(&mut self, cx: &LateContext<'tcx>, impl_item: &'tcx ImplItem<
             if impl_item.generics.params.iter().all(|p| matches!(p.kind, GenericParamKind::Lifetime { .. }));
 
             // Check if return type is String
-            if is_type_lang_item(cx, return_ty(cx, impl_item.hir_id()), LangItem::String);
+            if is_type_lang_item(cx, return_ty(cx, impl_item.owner_id), LangItem::String);
 
             // Filters instances of to_string which are required by a trait
             if trait_ref_of_method(cx, impl_item.owner_id.def_id).is_none();
index 5c4b604104417e86b99c28a6d6a1f6a172c33a0f..d06830397761bd4b9d52997caaaf2c024820c34a 100644 (file)
@@ -1,7 +1,6 @@
 #![feature(array_windows)]
 #![feature(binary_heap_into_iter_sorted)]
 #![feature(box_patterns)]
-#![feature(control_flow_enum)]
 #![feature(drain_filter)]
 #![feature(iter_intersperse)]
 #![feature(let_chains)]
index 7cf1a6b8084a613b9053e2c1fe18bd2498f590d8..747a94ba5a6edc23bf08c77b494393b2e9e75fbe 100644 (file)
@@ -15,7 +15,6 @@
 };
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_middle::hir::nested_filter as middle_nested_filter;
-use rustc_middle::ty::TyCtxt;
 use rustc_session::{declare_lint_pass, declare_tool_lint};
 use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map::Span;
@@ -154,7 +153,7 @@ fn check_fn_inner<'tcx>(
         .filter(|param| matches!(param.kind, GenericParamKind::Type { .. }));
 
     for typ in types {
-        for pred in generics.bounds_for_param(cx.tcx.hir().local_def_id(typ.hir_id)) {
+        for pred in generics.bounds_for_param(typ.def_id) {
             if pred.origin == PredicateOrigin::WhereClause {
                 // has_where_lifetimes checked that this predicate contains no lifetime.
                 continue;
@@ -251,7 +250,7 @@ fn could_use_elision<'tcx>(
     // level of the current item.
 
     // check named LTs
-    let allowed_lts = allowed_lts_from(cx.tcx, named_generics);
+    let allowed_lts = allowed_lts_from(named_generics);
 
     // these will collect all the lifetimes for references in arg/return types
     let mut input_visitor = RefVisitor::new(cx);
@@ -360,11 +359,11 @@ fn could_use_elision<'tcx>(
     }
 }
 
-fn allowed_lts_from(tcx: TyCtxt<'_>, named_generics: &[GenericParam<'_>]) -> FxHashSet<RefLt> {
+fn allowed_lts_from(named_generics: &[GenericParam<'_>]) -> FxHashSet<RefLt> {
     let mut allowed_lts = FxHashSet::default();
     for par in named_generics.iter() {
         if let GenericParamKind::Lifetime { .. } = par.kind {
-            allowed_lts.insert(RefLt::Named(tcx.hir().local_def_id(par.hir_id)));
+            allowed_lts.insert(RefLt::Named(par.def_id));
         }
     }
     allowed_lts.insert(RefLt::Unnamed);
@@ -516,7 +515,7 @@ fn has_where_lifetimes<'tcx>(cx: &LateContext<'tcx>, generics: &'tcx Generics<'_
                     return true;
                 }
                 // if the bounds define new lifetimes, they are fine to occur
-                let allowed_lts = allowed_lts_from(cx.tcx, pred.bound_generic_params);
+                let allowed_lts = allowed_lts_from(pred.bound_generic_params);
                 // now walk the bounds
                 for bound in pred.bounds.iter() {
                     walk_param_bound(&mut visitor, bound);
index 63212beaa63dd6b584685baf4650f718f8d0df2e..3778eb4c732d7ea73686ab434b0b9513fd68f0fa 100644 (file)
@@ -6,10 +6,11 @@
 use rustc_hir::intravisit::FnKind;
 use rustc_hir::{
     AsyncGeneratorKind, Block, Body, Closure, Expr, ExprKind, FnDecl, FnRetTy, GeneratorKind, GenericArg, GenericBound,
-    HirId, ItemKind, LifetimeName, Term, TraitRef, Ty, TyKind, TypeBindingKind,
+    ItemKind, LifetimeName, Term, TraitRef, Ty, TyKind, TypeBindingKind,
 };
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::{sym, Span};
 
 declare_clippy_lint! {
@@ -45,7 +46,7 @@ fn check_fn(
         decl: &'tcx FnDecl<'_>,
         body: &'tcx Body<'_>,
         span: Span,
-        _: HirId,
+        _: LocalDefId,
     ) {
         if_chain! {
             if let Some(header) = kind.header();
index bca193be9e711a520e3e4774c0c55a6af72559b8..9a84068d4487b3054607d5babc643b30aa15f5ac 100644 (file)
@@ -157,11 +157,10 @@ fn check_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::Item<'_>) {
             && def.variants.len() > 1
         {
             let mut iter = def.variants.iter().filter_map(|v| {
-                let id = cx.tcx.hir().local_def_id(v.hir_id);
-                (matches!(v.data, hir::VariantData::Unit(..))
+                (matches!(v.data, hir::VariantData::Unit(_, _))
                     && v.ident.as_str().starts_with('_')
                     && is_doc_hidden(cx.tcx.hir().attrs(v.hir_id)))
-                .then_some((id, v.span))
+                .then_some((v.def_id, v.span))
             });
             if let Some((id, span)) = iter.next()
                 && iter.next().is_none()
index ac61b4377885b8cfd2a179c901ee844be0cd8aef..5e01ed90ff0997402337ae9cba753f55495c2fb4 100644 (file)
@@ -54,7 +54,7 @@ fn collect_replace_calls<'tcx>(
                 from_args.push_front(from);
                 ControlFlow::Continue(())
             } else {
-                ControlFlow::BREAK
+                ControlFlow::Break(())
             }
         } else {
             ControlFlow::Continue(())
index 0c465e5daf9fd1bf717e89aa7a469accd89ee5e9..fb94dfa5980b76f05a9b002a765961379f3138b6 100644 (file)
@@ -3412,7 +3412,7 @@ fn check_impl_item(&mut self, cx: &LateContext<'tcx>, impl_item: &'tcx hir::Impl
         }
 
         if let hir::ImplItemKind::Fn(_, _) = impl_item.kind {
-            let ret_ty = return_ty(cx, impl_item.hir_id());
+            let ret_ty = return_ty(cx, impl_item.owner_id);
 
             if contains_ty_adt_constructor_opaque(cx, ret_ty, self_ty) {
                 return;
@@ -3460,7 +3460,7 @@ fn check_trait_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx TraitItem<'_>
         if_chain! {
             if item.ident.name == sym::new;
             if let TraitItemKind::Fn(_, _) = item.kind;
-            let ret_ty = return_ty(cx, item.hir_id());
+            let ret_ty = return_ty(cx, item.owner_id);
             let self_ty = TraitRef::identity(cx.tcx, item.owner_id.to_def_id())
                 .self_ty()
                 .skip_binder();
index 2ac0786b37b1e73fd431cd3267c30b0992bed0b3..0dc7fe2a2c5a36d900e9a43b61829a86d664ab1d 100644 (file)
 pub fn check(cx: &LateContext<'_>, expr: &hir::Expr<'_>, count_recv: &hir::Expr<'_>, map_arg: &hir::Expr<'_>) {
     if_chain! {
         if is_trait_method(cx, count_recv, sym::Iterator);
-        let closure = expr_or_init(cx, map_arg);
-        if let Some(def_id) = cx.tcx.hir().opt_local_def_id(closure.hir_id);
-        if let Some(body_id) = cx.tcx.hir().maybe_body_owned_by(def_id);
-        let closure_body = cx.tcx.hir().body(body_id);
+        if let hir::ExprKind::Closure(closure) = expr_or_init(cx, map_arg).kind;
+        let closure_body = cx.tcx.hir().body(closure.body);
         if !cx.typeck_results().expr_ty(closure_body.value).is_unit();
         then {
             if let Some(map_mutated_vars) = mutated_variables(closure_body.value, cx) {
index 12e053cb2134d1e3c5471707082368be6d0b2c00..4e5af1c7c71249bba4dab76cba74386d2214e484 100644 (file)
@@ -368,10 +368,9 @@ fn can_change_type<'a>(cx: &LateContext<'a>, mut expr: &'a Expr<'a>, mut ty: Ty<
             Node::Block(..) => continue,
             Node::Item(item) => {
                 if let ItemKind::Fn(_, _, body_id) = &item.kind
-                && let output_ty = return_ty(cx, item.hir_id())
-                && let local_def_id = cx.tcx.hir().local_def_id(item.hir_id())
-                && Inherited::build(cx.tcx, local_def_id).enter(|inherited| {
-                    let fn_ctxt = FnCtxt::new(inherited, cx.param_env, local_def_id);
+                && let output_ty = return_ty(cx, item.owner_id)
+                && Inherited::build(cx.tcx, item.owner_id.def_id).enter(|inherited| {
+                    let fn_ctxt = FnCtxt::new(inherited, cx.param_env, item.owner_id.def_id);
                     fn_ctxt.can_coerce(ty, output_ty)
                 }) {
                     if has_lifetime(output_ty) && has_lifetime(ty) {
index 9f4beb92b9d2e77bc265e5f13eb3b050989fc77a..0705029a613bba3e1f863e46eb68ca82bdcd73eb 100644 (file)
@@ -4,12 +4,13 @@
 use rustc_errors::Applicability;
 use rustc_hir::intravisit::FnKind;
 use rustc_hir::{
-    self as hir, def, BinOpKind, BindingAnnotation, Body, ByRef, Expr, ExprKind, FnDecl, HirId, Mutability, PatKind,
-    Stmt, StmtKind, TyKind,
+    self as hir, def, BinOpKind, BindingAnnotation, Body, ByRef, Expr, ExprKind, FnDecl, Mutability, PatKind, Stmt,
+    StmtKind, TyKind,
 };
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_middle::lint::in_external_macro;
 use rustc_session::{declare_tool_lint, impl_lint_pass};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::hygiene::DesugaringKind;
 use rustc_span::source_map::{ExpnKind, Span};
 
@@ -151,7 +152,7 @@ fn check_fn(
         decl: &'tcx FnDecl<'_>,
         body: &'tcx Body<'_>,
         span: Span,
-        _: HirId,
+        _: LocalDefId,
     ) {
         if let FnKind::Closure = k {
             // Does not apply to closures
index 5bc04bc17fb4f00bdf2cba1c1d9db4b08e8991a4..87bd007a26a241e7dcbf43bca5d01a10932ab39a 100644 (file)
@@ -6,11 +6,12 @@
 use rustc_hir as hir;
 use rustc_hir::def_id::CRATE_DEF_ID;
 use rustc_hir::intravisit::FnKind;
-use rustc_hir::{Body, Constness, FnDecl, GenericParamKind, HirId};
+use rustc_hir::{Body, Constness, FnDecl, GenericParamKind};
 use rustc_hir_analysis::hir_ty_to_ty;
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_middle::lint::in_external_macro;
 use rustc_session::{declare_tool_lint, impl_lint_pass};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::Span;
 
 declare_clippy_lint! {
@@ -91,14 +92,12 @@ fn check_fn(
         _: &FnDecl<'_>,
         body: &Body<'tcx>,
         span: Span,
-        hir_id: HirId,
+        def_id: LocalDefId,
     ) {
         if !self.msrv.meets(msrvs::CONST_IF_MATCH) {
             return;
         }
 
-        let def_id = cx.tcx.hir().local_def_id(hir_id);
-
         if in_external_macro(cx.tcx.sess, span) || is_entrypoint_fn(cx, def_id.to_def_id()) {
             return;
         }
@@ -132,6 +131,8 @@ fn check_fn(
             FnKind::Closure => return,
         }
 
+        let hir_id = cx.tcx.hir().local_def_id_to_hir_id(def_id);
+
         // Const fns are not allowed as methods in a trait.
         {
             let parent = cx.tcx.hir().get_parent_item(hir_id).def_id;
index 16947cd5e3548277f97d77a04d4adf5617c72e02..5f7aac21e6eb00a194ba232c714fb94017e82e5b 100644 (file)
@@ -6,6 +6,7 @@
 use rustc_middle::ty::TypeVisitable;
 use rustc_middle::ty::{Adt, Array, Ref, Slice, Tuple, Ty};
 use rustc_session::{declare_tool_lint, impl_lint_pass};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map::Span;
 use rustc_span::symbol::sym;
 use std::iter;
@@ -102,21 +103,21 @@ fn check_crate(&mut self, cx: &LateContext<'tcx>) {
 
     fn check_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::Item<'tcx>) {
         if let hir::ItemKind::Fn(ref sig, ..) = item.kind {
-            self.check_sig(cx, item.hir_id(), sig.decl);
+            self.check_sig(cx, item.owner_id.def_id, sig.decl);
         }
     }
 
     fn check_impl_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::ImplItem<'tcx>) {
         if let hir::ImplItemKind::Fn(ref sig, ..) = item.kind {
             if trait_ref_of_method(cx, item.owner_id.def_id).is_none() {
-                self.check_sig(cx, item.hir_id(), sig.decl);
+                self.check_sig(cx, item.owner_id.def_id, sig.decl);
             }
         }
     }
 
     fn check_trait_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::TraitItem<'tcx>) {
         if let hir::TraitItemKind::Fn(ref sig, ..) = item.kind {
-            self.check_sig(cx, item.hir_id(), sig.decl);
+            self.check_sig(cx, item.owner_id.def_id, sig.decl);
         }
     }
 
@@ -136,8 +137,7 @@ pub fn new(ignore_interior_mutability: Vec<String>) -> Self {
         }
     }
 
-    fn check_sig(&self, cx: &LateContext<'_>, item_hir_id: hir::HirId, decl: &hir::FnDecl<'_>) {
-        let fn_def_id = cx.tcx.hir().local_def_id(item_hir_id);
+    fn check_sig(&self, cx: &LateContext<'_>, fn_def_id: LocalDefId, decl: &hir::FnDecl<'_>) {
         let fn_sig = cx.tcx.fn_sig(fn_def_id).subst_identity();
         for (hir_ty, ty) in iter::zip(decl.inputs, fn_sig.inputs().skip_binder()) {
             self.check_ty_(cx, hir_ty.span, *ty);
index 25ec9082c7076677c5f1cc8d6ea1bdbc84a0141d..996ea6ed723160d8a7bb31d080059ffab7de6436 100644 (file)
@@ -20,6 +20,7 @@
 use rustc_middle::mir::FakeReadCause;
 use rustc_middle::ty::{self, TypeVisitable};
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::symbol::kw;
 use rustc_span::{sym, Span};
 use rustc_target::spec::abi::Abi;
@@ -82,12 +83,14 @@ fn check_fn(
         decl: &'tcx FnDecl<'_>,
         body: &'tcx Body<'_>,
         span: Span,
-        hir_id: HirId,
+        fn_def_id: LocalDefId,
     ) {
         if span.from_expansion() {
             return;
         }
 
+        let hir_id = cx.tcx.hir().local_def_id_to_hir_id(fn_def_id);
+
         match kind {
             FnKind::ItemFn(.., header) => {
                 let attrs = cx.tcx.hir().attrs(hir_id);
@@ -119,8 +122,6 @@ fn check_fn(
 
         let sized_trait = need!(cx.tcx.lang_items().sized_trait());
 
-        let fn_def_id = cx.tcx.hir().local_def_id(hir_id);
-
         let preds = traits::elaborate_predicates(cx.tcx, cx.param_env.caller_bounds().iter())
             .filter(|p| !p.is_global())
             .filter_map(|obligation| {
index 54a3c82b713daa36684d2da864cbeedc93b5abfc..faf9ec61ec504396d37c9eb076cfe9049d645602 100644 (file)
@@ -75,7 +75,7 @@ fn check_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::Item<'_>) {
                     }
                     if let hir::ImplItemKind::Fn(ref sig, _) = impl_item.kind {
                         let name = impl_item.ident.name;
-                        let id = impl_item.hir_id();
+                        let id = impl_item.owner_id;
                         if sig.header.constness == hir::Constness::Const {
                             // can't be implemented by default
                             return;
@@ -97,7 +97,7 @@ fn check_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::Item<'_>) {
                             if sig.decl.inputs.is_empty();
                             if name == sym::new;
                             if cx.effective_visibilities.is_reachable(impl_item.owner_id.def_id);
-                            let self_def_id = cx.tcx.hir().get_parent_item(id);
+                            let self_def_id = cx.tcx.hir().get_parent_item(id.into());
                             let self_ty = cx.tcx.type_of(self_def_id);
                             if self_ty == return_ty(cx, id);
                             if let Some(default_trait_id) = cx.tcx.get_diagnostic_item(sym::Default);
@@ -133,7 +133,7 @@ fn check_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::Item<'_>) {
                                 span_lint_hir_and_then(
                                     cx,
                                     NEW_WITHOUT_DEFAULT,
-                                    id,
+                                    id.into(),
                                     impl_item.span,
                                     &format!(
                                         "you should consider adding a `Default` implementation for `{self_type_snip}`"
index cff82b875f11a73830cf2ab574593664030ac9f2..d592f6e814c1d3599ceb0dcdac485a729d7d2c6b 100644 (file)
@@ -209,7 +209,8 @@ fn check_expr(&mut self, cx: &LateContext<'tcx>, expr: &hir::Expr<'tcx>) {
 
     fn check_body(&mut self, cx: &LateContext<'_>, body: &hir::Body<'_>) {
         let body_owner = cx.tcx.hir().body_owner(body.id());
-        let body_owner_def_id = cx.tcx.hir().local_def_id(body_owner);
+        let body_owner_def_id = cx.tcx.hir().body_owner_def_id(body.id());
+
         let body_owner_kind = cx.tcx.hir().body_owner_kind(body_owner_def_id);
         if let hir::BodyOwnerKind::Const | hir::BodyOwnerKind::Static(_) = body_owner_kind {
             let body_span = cx.tcx.hir().span_with_body(body_owner);
index 0830a106f55685014b50e19476296bddf8397519..777395f452c92397e47a9caeeee568184e3d6ed6 100644 (file)
@@ -96,7 +96,7 @@ pub fn expr_post(&mut self, id: hir::HirId) {
 
     pub fn enter_body(&mut self, cx: &LateContext<'_>, body: &hir::Body<'_>) {
         let body_owner = cx.tcx.hir().body_owner(body.id());
-        let body_owner_def_id = cx.tcx.hir().local_def_id(body_owner);
+        let body_owner_def_id = cx.tcx.hir().body_owner_def_id(body.id());
 
         match cx.tcx.hir().body_owner_kind(body_owner_def_id) {
             hir::BodyOwnerKind::Static(_) | hir::BodyOwnerKind::Const => {
index efec12489a9bad42708568988843610ddfb172b9..849cd03dd7bf639fd8e97d1fe884c16066b6f47e 100644 (file)
@@ -8,6 +8,7 @@
 use rustc_hir::intravisit::FnKind;
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::{sym, Span};
 
 declare_clippy_lint! {
@@ -49,9 +50,13 @@ fn check_fn(
         _: &'tcx hir::FnDecl<'tcx>,
         body: &'tcx hir::Body<'tcx>,
         span: Span,
-        hir_id: hir::HirId,
+        def_id: LocalDefId,
     ) {
-        if !matches!(fn_kind, FnKind::Closure) && is_type_diagnostic_item(cx, return_ty(cx, hir_id), sym::Result) {
+        if matches!(fn_kind, FnKind::Closure) {
+            return;
+        }
+        let owner = cx.tcx.hir().local_def_id_to_hir_id(def_id).expect_owner();
+        if is_type_diagnostic_item(cx, return_ty(cx, owner), sym::Result) {
             lint_impl_body(cx, span, body);
         }
     }
index 954eeba751ffa4307d712dad99ac5898bb5c12cc..0d78c3048ba127bc2ae74f88b0e7a9c8183f000e 100644 (file)
@@ -12,7 +12,7 @@
 use rustc_errors::Applicability;
 use rustc_hir as hir;
 use rustc_hir::intravisit::FnKind;
-use rustc_hir::{BindingAnnotation, Body, FnDecl, HirId, Impl, ItemKind, MutTy, Mutability, Node, PatKind};
+use rustc_hir::{BindingAnnotation, Body, FnDecl, Impl, ItemKind, MutTy, Mutability, Node, PatKind};
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_middle::ty::adjustment::{Adjust, PointerCast};
 use rustc_middle::ty::layout::LayoutOf;
@@ -272,12 +272,13 @@ fn check_fn(
         decl: &'tcx FnDecl<'_>,
         _body: &'tcx Body<'_>,
         span: Span,
-        hir_id: HirId,
+        def_id: LocalDefId,
     ) {
         if span.from_expansion() {
             return;
         }
 
+        let hir_id = cx.tcx.hir().local_def_id_to_hir_id(def_id);
         match kind {
             FnKind::ItemFn(.., header) => {
                 if header.abi != Abi::Rust {
@@ -308,6 +309,6 @@ fn check_fn(
             }
         }
 
-        self.check_poly_fn(cx, cx.tcx.hir().local_def_id(hir_id), decl, Some(span));
+        self.check_poly_fn(cx, def_id, decl, Some(span));
     }
 }
index 97b5a4ce36413f4820b209a68f45c3beeb26db54..9f98195d311fed80f3e84e79d64512809bbf1b1f 100644 (file)
@@ -1,11 +1,10 @@
 use clippy_utils::diagnostics::span_lint_and_help;
-use rustc_hir::{
-    intravisit, Body, Expr, ExprKind, FnDecl, HirId, Let, LocalSource, Mutability, Pat, PatKind, Stmt, StmtKind,
-};
+use rustc_hir::{intravisit, Body, Expr, ExprKind, FnDecl, Let, LocalSource, Mutability, Pat, PatKind, Stmt, StmtKind};
 use rustc_lint::{LateContext, LateLintPass, LintContext};
 use rustc_middle::lint::in_external_macro;
 use rustc_middle::ty;
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map::Span;
 
 declare_clippy_lint! {
@@ -116,7 +115,7 @@ fn check_fn(
         _: &'tcx FnDecl<'_>,
         body: &'tcx Body<'_>,
         _: Span,
-        _: HirId,
+        _: LocalDefId,
     ) {
         for param in body.params {
             apply_lint(cx, param.pat, DerefPossible::Impossible);
index c1677fb3da1c4850215dfd6a88e1ee485d4c54ed..944a33cc3e53fad4c0ee3d0fcd9944739fcb76b2 100644 (file)
@@ -6,11 +6,12 @@
 use if_chain::if_chain;
 use rustc_errors::Applicability;
 use rustc_hir::intravisit::FnKind;
-use rustc_hir::{def_id, Body, FnDecl, HirId, LangItem};
+use rustc_hir::{def_id, Body, FnDecl, LangItem};
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_middle::mir;
 use rustc_middle::ty::{self, Ty};
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map::{BytePos, Span};
 use rustc_span::sym;
 
@@ -69,12 +70,10 @@ fn check_fn(
         cx: &LateContext<'tcx>,
         _: FnKind<'tcx>,
         _: &'tcx FnDecl<'_>,
-        body: &'tcx Body<'_>,
+        _: &'tcx Body<'_>,
         _: Span,
-        _: HirId,
+        def_id: LocalDefId,
     ) {
-        let def_id = cx.tcx.hir().body_owner_def_id(body.id());
-
         // Building MIR for `fn`s with unsatisfiable preds results in ICE.
         if fn_has_unsatisfiable_preds(cx, def_id.to_def_id()) {
             return;
index b77faf7322bd00c054a275f4249e844ec9866455..8c39b4fc5691b97735a2a483b16ef2bf98a57510 100644 (file)
@@ -3,7 +3,7 @@
 use clippy_utils::{nth_arg, return_ty};
 use rustc_hir::def_id::LocalDefId;
 use rustc_hir::intravisit::FnKind;
-use rustc_hir::{Body, FnDecl, HirId, TraitItem, TraitItemKind};
+use rustc_hir::{Body, FnDecl, OwnerId, TraitItem, TraitItemKind};
 use rustc_lint::{LateContext, LateLintPass, LintContext};
 use rustc_middle::lint::in_external_macro;
 use rustc_session::{declare_lint_pass, declare_tool_lint};
@@ -68,7 +68,7 @@
 
 declare_lint_pass!(ReturnSelfNotMustUse => [RETURN_SELF_NOT_MUST_USE]);
 
-fn check_method(cx: &LateContext<'_>, decl: &FnDecl<'_>, fn_def: LocalDefId, span: Span, hir_id: HirId) {
+fn check_method(cx: &LateContext<'_>, decl: &FnDecl<'_>, fn_def: LocalDefId, span: Span, owner_id: OwnerId) {
     if_chain! {
         // If it comes from an external macro, better ignore it.
         if !in_external_macro(cx.sess(), span);
@@ -76,10 +76,10 @@ fn check_method(cx: &LateContext<'_>, decl: &FnDecl<'_>, fn_def: LocalDefId, spa
         // We only show this warning for public exported methods.
         if cx.effective_visibilities.is_exported(fn_def);
         // We don't want to emit this lint if the `#[must_use]` attribute is already there.
-        if !cx.tcx.hir().attrs(hir_id).iter().any(|attr| attr.has_name(sym::must_use));
+        if !cx.tcx.hir().attrs(owner_id.into()).iter().any(|attr| attr.has_name(sym::must_use));
         if cx.tcx.visibility(fn_def.to_def_id()).is_public();
-        let ret_ty = return_ty(cx, hir_id);
-        let self_arg = nth_arg(cx, hir_id, 0);
+        let ret_ty = return_ty(cx, owner_id.into());
+        let self_arg = nth_arg(cx, owner_id.into(), 0);
         // If `Self` has the same type as the returned type, then we want to warn.
         //
         // For this check, we don't want to remove the reference on the returned type because if
@@ -109,26 +109,26 @@ fn check_fn(
         decl: &'tcx FnDecl<'tcx>,
         _: &'tcx Body<'tcx>,
         span: Span,
-        hir_id: HirId,
+        fn_def: LocalDefId,
     ) {
         if_chain! {
             // We are only interested in methods, not in functions or associated functions.
             if matches!(kind, FnKind::Method(_, _));
-            if let Some(fn_def) = cx.tcx.hir().opt_local_def_id(hir_id);
             if let Some(impl_def) = cx.tcx.impl_of_method(fn_def.to_def_id());
             // We don't want this method to be te implementation of a trait because the
             // `#[must_use]` should be put on the trait definition directly.
             if cx.tcx.trait_id_of_impl(impl_def).is_none();
 
             then {
-                check_method(cx, decl, fn_def, span, hir_id);
+                let hir_id = cx.tcx.hir().local_def_id_to_hir_id(fn_def);
+                check_method(cx, decl, fn_def, span, hir_id.expect_owner());
             }
         }
     }
 
     fn check_trait_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx TraitItem<'tcx>) {
         if let TraitItemKind::Fn(ref sig, _) = item.kind {
-            check_method(cx, sig.decl, item.owner_id.def_id, item.span, item.hir_id());
+            check_method(cx, sig.decl, item.owner_id.def_id, item.span, item.owner_id);
         }
     }
 }
index a3e0811700beeda4664cc1770cc18cfe55805af2..84a0c6b9558531ae41f7116b69d09d8ec4ecd1d6 100644 (file)
@@ -6,11 +6,12 @@
 use if_chain::if_chain;
 use rustc_errors::Applicability;
 use rustc_hir::intravisit::FnKind;
-use rustc_hir::{Block, Body, Expr, ExprKind, FnDecl, HirId, LangItem, MatchSource, PatKind, QPath, StmtKind};
+use rustc_hir::{Block, Body, Expr, ExprKind, FnDecl, LangItem, MatchSource, PatKind, QPath, StmtKind};
 use rustc_lint::{LateContext, LateLintPass, LintContext};
 use rustc_middle::lint::in_external_macro;
 use rustc_middle::ty::subst::GenericArgKind;
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map::Span;
 use rustc_span::{BytePos, Pos};
 
@@ -152,7 +153,7 @@ fn check_fn(
         _: &'tcx FnDecl<'tcx>,
         body: &'tcx Body<'tcx>,
         sp: Span,
-        _: HirId,
+        _: LocalDefId,
     ) {
         match kind {
             FnKind::Closure => {
index 71b387c66a33084845f4b9adcb8ab930b138f672..3ce030cd721a713491a0db0fd79a1f4f72a045f0 100644 (file)
@@ -54,7 +54,7 @@ fn check_impl_item(&mut self, cx: &LateContext<'tcx>, impl_item: &'tcx ImplItem<
         let parent = cx.tcx.hir().get_parent_item(impl_item.hir_id()).def_id;
         let item = cx.tcx.hir().expect_item(parent);
         let self_ty = cx.tcx.type_of(item.owner_id);
-        let ret_ty = return_ty(cx, impl_item.hir_id());
+        let ret_ty = return_ty(cx, impl_item.owner_id);
 
         // Do not check trait impls
         if matches!(item.kind, ItemKind::Impl(Impl { of_trait: Some(_), .. })) {
index 63b326048a48fe2c1f4322daa6b3d8fe10fbe573..de0c5d56e41566ba89a39c34aad08fe6052283f1 100644 (file)
@@ -61,8 +61,7 @@ fn is_struct_with_trailing_zero_sized_array(cx: &LateContext<'_>, item: &Item<'_
         if let rustc_hir::TyKind::Array(_, rustc_hir::ArrayLen::Body(length)) = last_field.ty.kind;
 
         // Then check if that that array zero-sized
-        let length_ldid = cx.tcx.hir().local_def_id(length.hir_id);
-        let length = Const::from_anon_const(cx.tcx, length_ldid);
+        let length = Const::from_anon_const(cx.tcx, length.def_id);
         let length = length.try_eval_usize(cx.tcx, cx.param_env);
         if let Some(length) = length;
         then {
index 229478b7ce3c9c2b72cf80617fa2f204f3fe38f2..585e2075fa904d0d80549d8b9fe179f9f538ea26 100644 (file)
 use rustc_hir as hir;
 use rustc_hir::intravisit::FnKind;
 use rustc_hir::{
-    Body, FnDecl, FnRetTy, GenericArg, HirId, ImplItem, ImplItemKind, Item, ItemKind, Local, MutTy, QPath, TraitItem,
+    Body, FnDecl, FnRetTy, GenericArg, ImplItem, ImplItemKind, Item, ItemKind, Local, MutTy, QPath, TraitItem,
     TraitItemKind, TyKind,
 };
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_session::{declare_tool_lint, impl_lint_pass};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map::Span;
 
 declare_clippy_lint! {
@@ -311,15 +312,27 @@ pub struct Types {
 impl_lint_pass!(Types => [BOX_COLLECTION, VEC_BOX, OPTION_OPTION, LINKEDLIST, BORROWED_BOX, REDUNDANT_ALLOCATION, RC_BUFFER, RC_MUTEX, TYPE_COMPLEXITY]);
 
 impl<'tcx> LateLintPass<'tcx> for Types {
-    fn check_fn(&mut self, cx: &LateContext<'_>, _: FnKind<'_>, decl: &FnDecl<'_>, _: &Body<'_>, _: Span, id: HirId) {
-        let is_in_trait_impl =
-            if let Some(hir::Node::Item(item)) = cx.tcx.hir().find_by_def_id(cx.tcx.hir().get_parent_item(id).def_id) {
-                matches!(item.kind, ItemKind::Impl(hir::Impl { of_trait: Some(_), .. }))
-            } else {
-                false
-            };
+    fn check_fn(
+        &mut self,
+        cx: &LateContext<'_>,
+        _: FnKind<'_>,
+        decl: &FnDecl<'_>,
+        _: &Body<'_>,
+        _: Span,
+        def_id: LocalDefId,
+    ) {
+        let is_in_trait_impl = if let Some(hir::Node::Item(item)) = cx.tcx.hir().find_by_def_id(
+            cx.tcx
+                .hir()
+                .get_parent_item(cx.tcx.hir().local_def_id_to_hir_id(def_id))
+                .def_id,
+        ) {
+            matches!(item.kind, ItemKind::Impl(hir::Impl { of_trait: Some(_), .. }))
+        } else {
+            false
+        };
 
-        let is_exported = cx.effective_visibilities.is_exported(cx.tcx.hir().local_def_id(id));
+        let is_exported = cx.effective_visibilities.is_exported(def_id);
 
         self.check_fn_decl(
             cx,
@@ -381,7 +394,7 @@ fn check_impl_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx ImplItem<'_>)
     fn check_field_def(&mut self, cx: &LateContext<'_>, field: &hir::FieldDef<'_>) {
         let is_exported = cx
             .effective_visibilities
-            .is_exported(cx.tcx.hir().local_def_id(field.hir_id));
+            .is_exported(field.def_id);
 
         self.check_ty(
             cx,
index 84ec0d0fb1cf4ccf42e4bf43e8b4c34f84d192c1..8b0e0ce5a3001581d97c8c9708195e9ae92189ce 100644 (file)
@@ -5,10 +5,11 @@
 use rustc_errors::Applicability;
 use rustc_hir::intravisit::FnKind;
 use rustc_hir::LangItem::{OptionSome, ResultOk};
-use rustc_hir::{Body, ExprKind, FnDecl, HirId, Impl, ItemKind, Node};
+use rustc_hir::{Body, ExprKind, FnDecl, Impl, ItemKind, Node};
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_middle::ty;
 use rustc_session::{declare_tool_lint, impl_lint_pass};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::symbol::sym;
 use rustc_span::Span;
 
@@ -77,12 +78,11 @@ fn check_fn(
         fn_decl: &FnDecl<'tcx>,
         body: &Body<'tcx>,
         span: Span,
-        hir_id: HirId,
+        def_id: LocalDefId,
     ) {
         // Abort if public function/method or closure.
         match fn_kind {
             FnKind::ItemFn(..) | FnKind::Method(..) => {
-                let def_id = cx.tcx.hir().local_def_id(hir_id);
                 if self.avoid_breaking_exported_api && cx.effective_visibilities.is_exported(def_id) {
                     return;
                 }
@@ -91,6 +91,7 @@ fn check_fn(
         }
 
         // Abort if the method is implementing a trait or of it a trait method.
+        let hir_id = cx.tcx.hir().local_def_id_to_hir_id(def_id);
         if let Some(Node::Item(item)) = cx.tcx.hir().find_parent(hir_id) {
             if matches!(
                 item.kind,
@@ -101,17 +102,18 @@ fn check_fn(
         }
 
         // Get the wrapper and inner types, if can't, abort.
-        let (return_type_label, lang_item, inner_type) = if let ty::Adt(adt_def, subst) = return_ty(cx, hir_id).kind() {
-            if cx.tcx.is_diagnostic_item(sym::Option, adt_def.did()) {
-                ("Option", OptionSome, subst.type_at(0))
-            } else if cx.tcx.is_diagnostic_item(sym::Result, adt_def.did()) {
-                ("Result", ResultOk, subst.type_at(0))
+        let (return_type_label, lang_item, inner_type) =
+            if let ty::Adt(adt_def, subst) = return_ty(cx, hir_id.expect_owner()).kind() {
+                if cx.tcx.is_diagnostic_item(sym::Option, adt_def.did()) {
+                    ("Option", OptionSome, subst.type_at(0))
+                } else if cx.tcx.is_diagnostic_item(sym::Result, adt_def.did()) {
+                    ("Result", ResultOk, subst.type_at(0))
+                } else {
+                    return;
+                }
             } else {
                 return;
-            }
-        } else {
-            return;
-        };
+            };
 
         // Check if all return expression respect the following condition and collect them.
         let mut suggs = Vec::new();
index 3538bef6e06185a13eb5a17ea1e5a9fb99816a8d..55651a28be9246b660c9f81f7f886c14819ea612 100644 (file)
@@ -1,9 +1,10 @@
 use clippy_utils::diagnostics::span_lint_and_help;
 use rustc_hir::intravisit::{walk_expr, walk_fn, FnKind, Visitor};
-use rustc_hir::{Body, Expr, ExprKind, FnDecl, HirId, YieldSource};
+use rustc_hir::{Body, Expr, ExprKind, FnDecl, YieldSource};
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_middle::hir::nested_filter;
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::Span;
 
 declare_clippy_lint! {
@@ -66,11 +67,11 @@ fn check_fn(
         fn_decl: &'tcx FnDecl<'tcx>,
         body: &Body<'tcx>,
         span: Span,
-        hir_id: HirId,
+        def_id: LocalDefId,
     ) {
         if !span.from_expansion() && fn_kind.asyncness().is_async() {
             let mut visitor = AsyncFnVisitor { cx, found_await: false };
-            walk_fn(&mut visitor, fn_kind, fn_decl, body.id(), hir_id);
+            walk_fn(&mut visitor, fn_kind, fn_decl, body.id(), def_id);
             if !visitor.found_await {
                 span_lint_and_help(
                     cx,
index ea878043c04e3b789e351f99796d55b590d242d3..377d3fb6f4e1ccee8b6e9d9abc53dd571c95cd1e 100644 (file)
@@ -11,6 +11,7 @@
 use rustc_middle::lint::in_external_macro;
 use rustc_middle::ty::Ty;
 use rustc_session::{declare_lint_pass, declare_tool_lint};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map::Span;
 use rustc_span::sym;
 
@@ -312,7 +313,7 @@ fn check_fn(
         decl: &'tcx FnDecl<'_>,
         body: &'tcx Body<'_>,
         span: Span,
-        fn_id: HirId,
+        fn_id: LocalDefId,
     ) {
         if span.from_expansion() {
             return;
index f3611d174340458fa97177f28b63ddb8ab997b2d..3a1845425a251b12eb0c1f2b4d358282bded6dc8 100644 (file)
@@ -64,8 +64,8 @@ fn check_impl_item(&mut self, cx: &LateContext<'tcx>, impl_item: &'tcx hir::Impl
             // first check if it's a method or function
             if let hir::ImplItemKind::Fn(ref _signature, _) = impl_item.kind;
             // checking if its return type is `result` or `option`
-            if is_type_diagnostic_item(cx, return_ty(cx, impl_item.hir_id()), sym::Result)
-                || is_type_diagnostic_item(cx, return_ty(cx, impl_item.hir_id()), sym::Option);
+            if is_type_diagnostic_item(cx, return_ty(cx, impl_item.owner_id), sym::Result)
+                || is_type_diagnostic_item(cx, return_ty(cx, impl_item.owner_id), sym::Option);
             then {
                 lint_impl_body(cx, impl_item.span, impl_item);
             }
index e2965146cfe6dd49cebc0f62dcae9bb8e5d8f9a1..26f279f55855f3ef9dd1ca73705acc42f54470d0 100644 (file)
@@ -1,6 +1,5 @@
 #![feature(array_chunks)]
 #![feature(box_patterns)]
-#![feature(control_flow_enum)]
 #![feature(let_chains)]
 #![feature(lint_reasons)]
 #![feature(never_type)]
@@ -1119,9 +1118,8 @@ fn visit_expr(&mut self, e: &'tcx Expr<'_>) {
                         self.captures.entry(l).and_modify(|e| *e |= cap).or_insert(cap);
                     }
                 },
-                ExprKind::Closure { .. } => {
-                    let closure_id = self.cx.tcx.hir().local_def_id(e.hir_id);
-                    for capture in self.cx.typeck_results().closure_min_captures_flattened(closure_id) {
+                ExprKind::Closure(closure) => {
+                    for capture in self.cx.typeck_results().closure_min_captures_flattened(closure.def_id) {
                         let local_id = match capture.place.base {
                             PlaceBase::Local(id) => id,
                             PlaceBase::Upvar(var) => var.var_path.hir_id,
@@ -1578,15 +1576,13 @@ pub fn is_direct_expn_of(span: Span, name: &str) -> Option<Span> {
 }
 
 /// Convenience function to get the return type of a function.
-pub fn return_ty<'tcx>(cx: &LateContext<'tcx>, fn_item: hir::HirId) -> Ty<'tcx> {
-    let fn_def_id = cx.tcx.hir().local_def_id(fn_item);
+pub fn return_ty<'tcx>(cx: &LateContext<'tcx>, fn_def_id: hir::OwnerId) -> Ty<'tcx> {
     let ret_ty = cx.tcx.fn_sig(fn_def_id).subst_identity().output();
     cx.tcx.erase_late_bound_regions(ret_ty)
 }
 
 /// Convenience function to get the nth argument type of a function.
-pub fn nth_arg<'tcx>(cx: &LateContext<'tcx>, fn_item: hir::HirId, nth: usize) -> Ty<'tcx> {
-    let fn_def_id = cx.tcx.hir().local_def_id(fn_item);
+pub fn nth_arg<'tcx>(cx: &LateContext<'tcx>, fn_def_id: hir::OwnerId, nth: usize) -> Ty<'tcx> {
     let arg = cx.tcx.fn_sig(fn_def_id).subst_identity().input(nth);
     cx.tcx.erase_late_bound_regions(arg)
 }
index 659063b97e74a3559907622019f3ad85c4e38a5c..d7f466c1976361bb293a087f657f7478c9537ca5 100644 (file)
@@ -327,7 +327,7 @@ fn is_assert_arg(cx: &LateContext<'_>, expr: &Expr<'_>, assert_expn: ExpnId) ->
         } else {
             match cx.tcx.item_name(macro_call.def_id) {
                 // `cfg!(debug_assertions)` in `debug_assert!`
-                sym::cfg => ControlFlow::CONTINUE,
+                sym::cfg => ControlFlow::Continue(()),
                 // assert!(other_macro!(..))
                 _ => ControlFlow::Break(true),
             }
index 9adae7733894580fec10663a47c9ab9a69ebb635..5836eb73bd94c30e2a833250ddd538689a53b7ff 100644 (file)
@@ -140,7 +140,7 @@ impl TypeVisitor<'_> for ContainsRegion {
     type BreakTy = ();
 
     fn visit_region(&mut self, _: ty::Region<'_>) -> ControlFlow<Self::BreakTy> {
-        ControlFlow::BREAK
+        ControlFlow::Break(())
     }
 }
 
index 8d767f9d44d3a7f1189426f25cc16e29fa7e128e..b8c87aa5e1e423ab02d0593d679afe235f1c4a71 100644 (file)
@@ -809,7 +809,7 @@ pub struct DerefClosure {
 ///
 /// note: this only works on single line immutable closures with exactly one input parameter.
 pub fn deref_closure_args(cx: &LateContext<'_>, closure: &hir::Expr<'_>) -> Option<DerefClosure> {
-    if let hir::ExprKind::Closure(&Closure { fn_decl, body, .. }) = closure.kind {
+    if let hir::ExprKind::Closure(&Closure { fn_decl, def_id, body, .. }) = closure.kind {
         let closure_body = cx.tcx.hir().body(body);
         // is closure arg a type annotated double reference (i.e.: `|x: &&i32| ...`)
         // a type annotation is present if param `kind` is different from `TyKind::Infer`
@@ -829,10 +829,8 @@ pub fn deref_closure_args(cx: &LateContext<'_>, closure: &hir::Expr<'_>) -> Opti
             applicability: Applicability::MachineApplicable,
         };
 
-        let fn_def_id = cx.tcx.hir().local_def_id(closure.hir_id);
         let infcx = cx.tcx.infer_ctxt().build();
-        ExprUseVisitor::new(&mut visitor, &infcx, fn_def_id, cx.param_env, cx.typeck_results())
-            .consume_body(closure_body);
+        ExprUseVisitor::new(&mut visitor, &infcx, def_id, cx.param_env, cx.typeck_results()).consume_body(closure_body);
 
         if !visitor.suggestion_start.is_empty() {
             return Some(DerefClosure {
index c05443488c3ea9748a5473d7641696e5d8520bf9..3f6caecaa5ad0de40e27f2833a550309300839a6 100644 (file)
@@ -16,6 +16,7 @@
 use rustc_hir::intravisit;
 use rustc_hir::Node;
 use rustc_lint::{LateContext, LateLintPass, LintContext};
+use rustc_span::def_id::LocalDefId;
 use rustc_span::source_map;
 
 #[no_mangle]
@@ -40,8 +41,9 @@ fn check_fn(
         _: &'tcx hir::FnDecl,
         _: &'tcx hir::Body,
         span: source_map::Span,
-        id: hir::HirId,
+        def_id: LocalDefId,
     ) {
+        let id = cx.tcx.hir().local_def_id_to_hir_id(def_id);
         let item = match cx.tcx.hir().get(id) {
             Node::Item(item) => item,
             _ => cx.tcx.hir().expect_item(cx.tcx.hir().get_parent_item(id).def_id),
diff --git a/tests/ui-fulldeps/fluent-messages/missing-message-ref.ftl b/tests/ui-fulldeps/fluent-messages/missing-message-ref.ftl
new file mode 100644 (file)
index 0000000..0cd8229
--- /dev/null
@@ -0,0 +1 @@
+missing_message_ref = {message}
index 4e8147e2b76dce047fe95189e079aab739ee0ed2..74303e97dba947c5b9b1e4605c3566eb865f9eb8 100644 (file)
@@ -96,3 +96,12 @@ mod missing_crate_name {
 
     use self::fluent_generated::{DEFAULT_LOCALE_RESOURCES, test_crate_foo, with_hyphens};
 }
+
+mod missing_message_ref {
+    use super::fluent_messages;
+
+    fluent_messages! {
+        missing => "./missing-message-ref.ftl"
+//~^ ERROR referenced message `message` does not exist
+    }
+}
index d1cd4fe26da27aa3dd9e43168b30e3e2244acbd1..2631b0a623275a08382774ba415aec60889574f9 100644 (file)
@@ -93,6 +93,14 @@ LL |         test_crate => "./missing-crate-name.ftl",
    |
    = help: replace any '-'s with '_'s
 
-error: aborting due to 10 previous errors
+error: referenced message `message` does not exist (in message `missing_message_ref`)
+  --> $DIR/test.rs:104:20
+   |
+LL |         missing => "./missing-message-ref.ftl"
+   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = help: you may have meant to use a variable reference (`{$message}`)
+
+error: aborting due to 11 previous errors
 
 For more information about this error, try `rustc --explain E0428`.
index e6ee11a783b8849acabb006b020b5dad05d4f5ce..2a93a05c627698a2e1eb03e57133fed99215a508 100644 (file)
@@ -889,23 +889,20 @@ impl ::core::cmp::PartialOrd for Mixed {
         -> ::core::option::Option<::core::cmp::Ordering> {
         let __self_tag = ::core::intrinsics::discriminant_value(self);
         let __arg1_tag = ::core::intrinsics::discriminant_value(other);
-        match ::core::cmp::PartialOrd::partial_cmp(&__self_tag, &__arg1_tag) {
-            ::core::option::Option::Some(::core::cmp::Ordering::Equal) =>
-                match (self, other) {
-                    (Mixed::R(__self_0), Mixed::R(__arg1_0)) =>
-                        ::core::cmp::PartialOrd::partial_cmp(__self_0, __arg1_0),
-                    (Mixed::S { d1: __self_0, d2: __self_1 }, Mixed::S {
-                        d1: __arg1_0, d2: __arg1_1 }) =>
-                        match ::core::cmp::PartialOrd::partial_cmp(__self_0,
-                                __arg1_0) {
-                            ::core::option::Option::Some(::core::cmp::Ordering::Equal)
-                                => ::core::cmp::PartialOrd::partial_cmp(__self_1, __arg1_1),
-                            cmp => cmp,
-                        },
-                    _ =>
-                        ::core::option::Option::Some(::core::cmp::Ordering::Equal),
+        match (self, other) {
+            (Mixed::R(__self_0), Mixed::R(__arg1_0)) =>
+                ::core::cmp::PartialOrd::partial_cmp(__self_0, __arg1_0),
+            (Mixed::S { d1: __self_0, d2: __self_1 }, Mixed::S {
+                d1: __arg1_0, d2: __arg1_1 }) =>
+                match ::core::cmp::PartialOrd::partial_cmp(__self_0, __arg1_0)
+                    {
+                    ::core::option::Option::Some(::core::cmp::Ordering::Equal)
+                        => ::core::cmp::PartialOrd::partial_cmp(__self_1, __arg1_1),
+                    cmp => cmp,
                 },
-            cmp => cmp,
+            _ =>
+                ::core::cmp::PartialOrd::partial_cmp(&__self_tag,
+                    &__arg1_tag),
         }
     }
 }
@@ -1019,18 +1016,16 @@ impl ::core::cmp::PartialOrd for Fielded {
         -> ::core::option::Option<::core::cmp::Ordering> {
         let __self_tag = ::core::intrinsics::discriminant_value(self);
         let __arg1_tag = ::core::intrinsics::discriminant_value(other);
-        match ::core::cmp::PartialOrd::partial_cmp(&__self_tag, &__arg1_tag) {
-            ::core::option::Option::Some(::core::cmp::Ordering::Equal) =>
-                match (self, other) {
-                    (Fielded::X(__self_0), Fielded::X(__arg1_0)) =>
-                        ::core::cmp::PartialOrd::partial_cmp(__self_0, __arg1_0),
-                    (Fielded::Y(__self_0), Fielded::Y(__arg1_0)) =>
-                        ::core::cmp::PartialOrd::partial_cmp(__self_0, __arg1_0),
-                    (Fielded::Z(__self_0), Fielded::Z(__arg1_0)) =>
-                        ::core::cmp::PartialOrd::partial_cmp(__self_0, __arg1_0),
-                    _ => unsafe { ::core::intrinsics::unreachable() }
-                },
-            cmp => cmp,
+        match (self, other) {
+            (Fielded::X(__self_0), Fielded::X(__arg1_0)) =>
+                ::core::cmp::PartialOrd::partial_cmp(__self_0, __arg1_0),
+            (Fielded::Y(__self_0), Fielded::Y(__arg1_0)) =>
+                ::core::cmp::PartialOrd::partial_cmp(__self_0, __arg1_0),
+            (Fielded::Z(__self_0), Fielded::Z(__arg1_0)) =>
+                ::core::cmp::PartialOrd::partial_cmp(__self_0, __arg1_0),
+            _ =>
+                ::core::cmp::PartialOrd::partial_cmp(&__self_tag,
+                    &__arg1_tag),
         }
     }
 }
diff --git a/tests/ui/mir/mir_codegen_ssa.rs b/tests/ui/mir/mir_codegen_ssa.rs
new file mode 100644 (file)
index 0000000..5e2f10c
--- /dev/null
@@ -0,0 +1,19 @@
+// build-pass
+// compile-flags: --crate-type=lib
+#![feature(custom_mir, core_intrinsics)]
+use std::intrinsics::mir::*;
+
+#[custom_mir(dialect = "runtime", phase = "optimized")]
+pub fn f(a: u32) -> u32 {
+    mir!(
+        let x: u32;
+        {
+            // Previously code generation failed with ICE "use of .. before def ..." because the
+            // definition of x was incorrectly identified as dominating the use of x located in the
+            // same statement:
+            x = x + a;
+            RET = x;
+            Return()
+        }
+    )
+}
diff --git a/tests/ui/parser/deli-ident-issue-1.rs b/tests/ui/parser/deli-ident-issue-1.rs
new file mode 100644 (file)
index 0000000..5448526
--- /dev/null
@@ -0,0 +1,24 @@
+#![feature(let_chains)]
+trait Demo {}
+
+impl dyn Demo {
+    pub fn report(&self) -> u32 {
+        let sum = |a: u32,
+                   b: u32,
+                   c: u32| {
+            a + b + c
+        };
+        sum(1, 2, 3)
+    }
+
+    fn check(&self, val: Option<u32>, num: Option<u32>) {
+        if let Some(b) = val
+        && let Some(c) = num {
+        && b == c {
+            //~^ ERROR expected struct
+            //~| ERROR mismatched types
+        }
+    }
+}
+
+fn main() { } //~ ERROR this file contains an unclosed delimiter
diff --git a/tests/ui/parser/deli-ident-issue-1.stderr b/tests/ui/parser/deli-ident-issue-1.stderr
new file mode 100644 (file)
index 0000000..1119edb
--- /dev/null
@@ -0,0 +1,37 @@
+error: this file contains an unclosed delimiter
+  --> $DIR/deli-ident-issue-1.rs:24:66
+   |
+LL | impl dyn Demo {
+   |               - unclosed delimiter
+...
+LL |         && let Some(c) = num {
+   |                              - this delimiter might not be properly closed...
+...
+LL |     }
+   |     - ...as it matches this but it has different indentation
+...
+LL | fn main() { }
+   |                                                                  ^
+
+error[E0574]: expected struct, variant or union type, found local variable `c`
+  --> $DIR/deli-ident-issue-1.rs:17:17
+   |
+LL |         && b == c {
+   |                 ^ not a struct, variant or union type
+
+error[E0308]: mismatched types
+  --> $DIR/deli-ident-issue-1.rs:17:9
+   |
+LL |       fn check(&self, val: Option<u32>, num: Option<u32>) {
+   |                                                           - expected `()` because of default return type
+...
+LL | /         && b == c {
+LL | |
+LL | |
+LL | |         }
+   | |_________^ expected `()`, found `bool`
+
+error: aborting due to 3 previous errors
+
+Some errors have detailed explanations: E0308, E0574.
+For more information about an error, try `rustc --explain E0308`.
diff --git a/tests/ui/parser/deli-ident-issue-2.rs b/tests/ui/parser/deli-ident-issue-2.rs
new file mode 100644 (file)
index 0000000..5394760
--- /dev/null
@@ -0,0 +1,7 @@
+fn main() {
+    if 1 < 2 {
+        let _a = vec!]; //~ ERROR mismatched closing delimiter
+    }
+} //~ ERROR unexpected closing delimiter
+
+fn main() {}
diff --git a/tests/ui/parser/deli-ident-issue-2.stderr b/tests/ui/parser/deli-ident-issue-2.stderr
new file mode 100644 (file)
index 0000000..c8f59c9
--- /dev/null
@@ -0,0 +1,19 @@
+error: unexpected closing delimiter: `}`
+  --> $DIR/deli-ident-issue-2.rs:5:1
+   |
+LL |         let _a = vec!];
+   |                      - missing open `[` for this delimiter
+LL |     }
+LL | }
+   | ^ unexpected closing delimiter
+
+error: mismatched closing delimiter: `]`
+  --> $DIR/deli-ident-issue-2.rs:2:14
+   |
+LL |     if 1 < 2 {
+   |              ^ unclosed delimiter
+LL |         let _a = vec!];
+   |                      ^ mismatched closing delimiter
+
+error: aborting due to 2 previous errors
+
diff --git a/tests/ui/parser/issue-68987-unmatch-issue-1.rs b/tests/ui/parser/issue-68987-unmatch-issue-1.rs
new file mode 100644 (file)
index 0000000..30e7ef4
--- /dev/null
@@ -0,0 +1,12 @@
+// This file has unexpected closing delimiter,
+
+fn func(o: Option<u32>) {
+    match o {
+        Some(_x) => {}   // Extra '}'
+            let _ = if true {};
+        }
+        None => {}
+    }
+} //~ ERROR unexpected closing delimiter
+
+fn main() {}
diff --git a/tests/ui/parser/issue-68987-unmatch-issue-1.stderr b/tests/ui/parser/issue-68987-unmatch-issue-1.stderr
new file mode 100644 (file)
index 0000000..2d873b4
--- /dev/null
@@ -0,0 +1,16 @@
+error: unexpected closing delimiter: `}`
+  --> $DIR/issue-68987-unmatch-issue-1.rs:10:1
+   |
+LL |     match o {
+   |             - this delimiter might not be properly closed...
+LL |         Some(_x) => {}   // Extra '}'
+   |                     -- block is empty, you might have not meant to close it
+LL |             let _ = if true {};
+LL |         }
+   |         - ...as it matches this but it has different indentation
+...
+LL | }
+   | ^ unexpected closing delimiter
+
+error: aborting due to previous error
+
diff --git a/tests/ui/parser/issue-68987-unmatch-issue-2.rs b/tests/ui/parser/issue-68987-unmatch-issue-2.rs
new file mode 100644 (file)
index 0000000..89aaa68
--- /dev/null
@@ -0,0 +1,14 @@
+// FIXME: this case need more work to fix
+// currently the TokenTree matching ')' with '{', which is not user friendly for diagnostics
+async fn obstest() -> Result<> {
+    let obs_connect = || -> Result<(), MyError) { //~ ERROR mismatched closing delimiter
+        async {
+        }
+    }
+
+    if let Ok(version, scene_list) = obs_connect() {
+
+    } else {
+
+    }
+} //~ ERROR unexpected closing delimiter
diff --git a/tests/ui/parser/issue-68987-unmatch-issue-2.stderr b/tests/ui/parser/issue-68987-unmatch-issue-2.stderr
new file mode 100644 (file)
index 0000000..2c08d41
--- /dev/null
@@ -0,0 +1,19 @@
+error: unexpected closing delimiter: `}`
+  --> $DIR/issue-68987-unmatch-issue-2.rs:14:1
+   |
+LL |     let obs_connect = || -> Result<(), MyError) {
+   |                                               - missing open `(` for this delimiter
+...
+LL | }
+   | ^ unexpected closing delimiter
+
+error: mismatched closing delimiter: `)`
+  --> $DIR/issue-68987-unmatch-issue-2.rs:3:32
+   |
+LL | async fn obstest() -> Result<> {
+   |                                ^ unclosed delimiter
+LL |     let obs_connect = || -> Result<(), MyError) {
+   |                                               ^ mismatched closing delimiter
+
+error: aborting due to 2 previous errors
+
diff --git a/tests/ui/parser/issue-68987-unmatch-issue-3.rs b/tests/ui/parser/issue-68987-unmatch-issue-3.rs
new file mode 100644 (file)
index 0000000..e98df8d
--- /dev/null
@@ -0,0 +1,8 @@
+// the `{` is closed with `)`, there is a missing `(`
+fn f(i: u32, j: u32) {
+    let res = String::new();
+    let mut cnt = i;
+    while cnt < j {
+        write!&mut res, " "); //~ ERROR mismatched closing delimiter
+    }
+} //~ ERROR unexpected closing delimiter
diff --git a/tests/ui/parser/issue-68987-unmatch-issue-3.stderr b/tests/ui/parser/issue-68987-unmatch-issue-3.stderr
new file mode 100644 (file)
index 0000000..a3fc46a
--- /dev/null
@@ -0,0 +1,19 @@
+error: unexpected closing delimiter: `}`
+  --> $DIR/issue-68987-unmatch-issue-3.rs:8:1
+   |
+LL |         write!&mut res, " ");
+   |                            - missing open `(` for this delimiter
+LL |     }
+LL | }
+   | ^ unexpected closing delimiter
+
+error: mismatched closing delimiter: `)`
+  --> $DIR/issue-68987-unmatch-issue-3.rs:5:19
+   |
+LL |     while cnt < j {
+   |                   ^ unclosed delimiter
+LL |         write!&mut res, " ");
+   |                            ^ mismatched closing delimiter
+
+error: aborting due to 2 previous errors
+
diff --git a/tests/ui/parser/issue-68987-unmatch-issue.rs b/tests/ui/parser/issue-68987-unmatch-issue.rs
new file mode 100644 (file)
index 0000000..5a3620b
--- /dev/null
@@ -0,0 +1,12 @@
+// This file has unexpected closing delimiter,
+
+fn func(o: Option<u32>) {
+    match o {
+        Some(_x) =>   // Missing '{'
+            let _ = if true {};
+        }
+        None => {}
+    }
+} //~ ERROR unexpected closing delimiter
+
+fn main() {}
diff --git a/tests/ui/parser/issue-68987-unmatch-issue.stderr b/tests/ui/parser/issue-68987-unmatch-issue.stderr
new file mode 100644 (file)
index 0000000..cabd133
--- /dev/null
@@ -0,0 +1,16 @@
+error: unexpected closing delimiter: `}`
+  --> $DIR/issue-68987-unmatch-issue.rs:10:1
+   |
+LL |     match o {
+   |             - this delimiter might not be properly closed...
+LL |         Some(_x) =>   // Missing '{'
+LL |             let _ = if true {};
+   |                             -- block is empty, you might have not meant to close it
+LL |         }
+   |         - ...as it matches this but it has different indentation
+...
+LL | }
+   | ^ unexpected closing delimiter
+
+error: aborting due to previous error
+
index 069de33919494658162f84c21cabf37c923f562c..867244b72e8493a0c59974d331c2500ed2e74c17 100644 (file)
@@ -2,8 +2,9 @@ error: this file contains an unclosed delimiter
   --> $DIR/issue-81827.rs:11:27
    |
 LL | fn r()->i{0|{#[cfg(r(0{]0
-   |          -  -             ^
-   |          |  |
+   |          -  -          -  ^
+   |          |  |          |
+   |          |  |          missing open `[` for this delimiter
    |          |  unclosed delimiter
    |          unclosed delimiter
 
@@ -11,8 +12,9 @@ error: this file contains an unclosed delimiter
   --> $DIR/issue-81827.rs:11:27
    |
 LL | fn r()->i{0|{#[cfg(r(0{]0
-   |          -  -             ^
-   |          |  |
+   |          -  -          -  ^
+   |          |  |          |
+   |          |  |          missing open `[` for this delimiter
    |          |  unclosed delimiter
    |          unclosed delimiter
 
index 4737bc71860c24ef903af60947b32c449d636955..3cb6d75a6754b343c3be2e2ff72e7469038cb7a0 100644 (file)
@@ -2,8 +2,10 @@ error: this file contains an unclosed delimiter
   --> $DIR/issue-62973.rs:8:2
    |
 LL | fn p() { match s { v, E { [) {) }
-   |        -         - unclosed delimiter
-   |        |
+   |        -         -         -  - missing open `(` for this delimiter
+   |        |         |         |
+   |        |         |         missing open `(` for this delimiter
+   |        |         unclosed delimiter
    |        unclosed delimiter
 LL |
 LL |
@@ -13,8 +15,10 @@ error: this file contains an unclosed delimiter
   --> $DIR/issue-62973.rs:8:2
    |
 LL | fn p() { match s { v, E { [) {) }
-   |        -         - unclosed delimiter
-   |        |
+   |        -         -         -  - missing open `(` for this delimiter
+   |        |         |         |
+   |        |         |         missing open `(` for this delimiter
+   |        |         unclosed delimiter
    |        unclosed delimiter
 LL |
 LL |
index cfdd99d1434aef0f17965b4032a77111c9152e0d..a1f8a77ffa7c6cec978d163dbe15b1489b8341ed 100644 (file)
@@ -2,8 +2,9 @@ error: this file contains an unclosed delimiter
   --> $DIR/issue-63116.rs:3:18
    |
 LL | impl W <s(f;Y(;]
-   |          -       ^
-   |          |
+   |          -     - ^
+   |          |     |
+   |          |     missing open `[` for this delimiter
    |          unclosed delimiter
 
 error: expected one of `!`, `(`, `)`, `+`, `,`, `::`, or `<`, found `;`
diff --git a/tests/ui/parser/issues/issue-69259.rs b/tests/ui/parser/issues/issue-69259.rs
new file mode 100644 (file)
index 0000000..01fc2c0
--- /dev/null
@@ -0,0 +1,3 @@
+fn main() {}
+
+fn f) {} //~ ERROR unexpected closing delimiter
diff --git a/tests/ui/parser/issues/issue-69259.stderr b/tests/ui/parser/issues/issue-69259.stderr
new file mode 100644 (file)
index 0000000..604b7de
--- /dev/null
@@ -0,0 +1,8 @@
+error: unexpected closing delimiter: `)`
+  --> $DIR/issue-69259.rs:3:5
+   |
+LL | fn f) {}
+   |     ^ unexpected closing delimiter
+
+error: aborting due to previous error
+
index 39bf113ef83de58b648c2b9cd038ff58a2a178e4..46cbb056d1d880d798604ed18783d0e59da96856 100644 (file)
@@ -2,10 +2,10 @@ error: unexpected closing delimiter: `}`
   --> $DIR/issue-70583-block-is-empty-1.rs:20:1
    |
 LL | fn struct_generic(x: Vec<i32>) {
-   |                                - this opening brace...
+   |                                - this delimiter might not be properly closed...
 ...
 LL |     }
-   |     - ...matches this closing brace
+   |     - ...as it matches this but it has different indentation
 LL | }
    | ^ unexpected closing delimiter
 
index 5d37b216427f6b023c0389b70121018b39a62dbc..9ae94c701869b8c0effb6031d24b6ce51a6dba2d 100644 (file)
@@ -1,8 +1,12 @@
 error: unexpected closing delimiter: `}`
   --> $DIR/issue-70583-block-is-empty-2.rs:14:1
    |
+LL |         match self {
+   |                    - this delimiter might not be properly closed...
 LL |             ErrorHandled::Reported => {}}
-   |                                       -- block is empty, you might have not meant to close it
+   |                                       --- ...as it matches this but it has different indentation
+   |                                       |
+   |                                       block is empty, you might have not meant to close it
 ...
 LL | }
    | ^ unexpected closing delimiter
index 967a3e6fdc11b76a56a6f6cf88cf6eba459ad50a..689ce1eb6b70462c7f0f0c988efc73c3c2f0b1d5 100644 (file)
@@ -2,10 +2,10 @@ error: unexpected closing delimiter: `}`
   --> $DIR/macro-mismatched-delim-paren-brace.rs:5:1
    |
 LL | fn main() {
-   |           - this opening brace...
+   |           - this delimiter might not be properly closed...
 ...
 LL |     }
-   |     - ...matches this closing brace
+   |     - ...as it matches this but it has different indentation
 LL | }
    | ^ unexpected closing delimiter
 
diff --git a/tests/ui/traits/alias/issue-60755.rs b/tests/ui/traits/alias/issue-60755.rs
new file mode 100644 (file)
index 0000000..6b955a7
--- /dev/null
@@ -0,0 +1,12 @@
+// check-pass
+
+#![feature(trait_alias)]
+
+struct MyStruct {}
+trait MyFn = Fn(&MyStruct);
+
+fn foo(_: impl MyFn) {}
+
+fn main() {
+    foo(|_| {});
+}
index 8508f7a38e2399b054d079b300ad17b11bf5ffff..78f392c9a8acc87913e01acb5c4dcbdf067391f6 100644 (file)
@@ -2,8 +2,9 @@ error: this file contains an unclosed delimiter
   --> $DIR/issue-91334.rs:10:23
    |
 LL | fn f(){||yield(((){),
-   |       -       -       ^
-   |       |       |
+   |       -       -    -  ^
+   |       |       |    |
+   |       |       |    missing open `(` for this delimiter
    |       |       unclosed delimiter
    |       unclosed delimiter
 
@@ -11,8 +12,9 @@ error: this file contains an unclosed delimiter
   --> $DIR/issue-91334.rs:10:23
    |
 LL | fn f(){||yield(((){),
-   |       -       -       ^
-   |       |       |
+   |       -       -    -  ^
+   |       |       |    |
+   |       |       |    missing open `(` for this delimiter
    |       |       unclosed delimiter
    |       unclosed delimiter