Skip to content

Commit c02371c

Browse files
committed
Auto merge of #88880 - cjgillot:no-krate, r=oli-obk
Rework HIR API to make invocations of the hir_crate query harder. `hir_crate` forces the recomputation of queries that depend on it. This PR aims at avoiding useless invocations of `hir_crate` by making dependent code go through `tcx.hir()`.
2 parents b6057bf + 77c3002 commit c02371c

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

64 files changed

+193
-209
lines changed

Diff for: compiler/rustc_driver/src/pretty.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -489,7 +489,7 @@ fn print_with_analysis(
489489
let mut out = String::new();
490490
abort_on_err(rustc_typeck::check_crate(tcx), tcx.sess);
491491
debug!("pretty printing THIR tree");
492-
for did in tcx.body_owners() {
492+
for did in tcx.hir().body_owners() {
493493
let _ = writeln!(
494494
out,
495495
"{:?}:\n{}\n",

Diff for: compiler/rustc_hir/src/hir.rs

+1-48
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
use crate::def::{CtorKind, DefKind, Res};
22
use crate::def_id::{DefId, CRATE_DEF_ID};
33
crate use crate::hir_id::{HirId, ItemLocalId};
4-
use crate::{itemlikevisit, LangItem};
4+
use crate::LangItem;
55

66
use rustc_ast::util::parser::ExprPrecedence;
77
use rustc_ast::{self as ast, CrateSugar, LlvmAsmDialect};
@@ -10,7 +10,6 @@ pub use rustc_ast::{BorrowKind, ImplPolarity, IsAuto};
1010
pub use rustc_ast::{CaptureBy, Movability, Mutability};
1111
use rustc_ast::{InlineAsmOptions, InlineAsmTemplatePiece};
1212
use rustc_data_structures::fx::FxHashMap;
13-
use rustc_data_structures::sync::{par_for_each_in, Send, Sync};
1413
use rustc_index::vec::IndexVec;
1514
use rustc_macros::HashStable_Generic;
1615
use rustc_span::source_map::Spanned;
@@ -708,52 +707,6 @@ impl Crate<'hir> {
708707
}
709708
}
710709

711-
impl Crate<'_> {
712-
/// Visits all items in the crate in some deterministic (but
713-
/// unspecified) order. If you just need to process every item,
714-
/// but don't care about nesting, this method is the best choice.
715-
///
716-
/// If you do care about nesting -- usually because your algorithm
717-
/// follows lexical scoping rules -- then you want a different
718-
/// approach. You should override `visit_nested_item` in your
719-
/// visitor and then call `intravisit::walk_crate` instead.
720-
pub fn visit_all_item_likes<'hir, V>(&'hir self, visitor: &mut V)
721-
where
722-
V: itemlikevisit::ItemLikeVisitor<'hir>,
723-
{
724-
for owner in self.owners.iter().filter_map(Option::as_ref) {
725-
match owner {
726-
OwnerNode::Item(item) => visitor.visit_item(item),
727-
OwnerNode::ForeignItem(item) => visitor.visit_foreign_item(item),
728-
OwnerNode::ImplItem(item) => visitor.visit_impl_item(item),
729-
OwnerNode::TraitItem(item) => visitor.visit_trait_item(item),
730-
OwnerNode::Crate(_) => {}
731-
}
732-
}
733-
}
734-
735-
/// A parallel version of `visit_all_item_likes`.
736-
pub fn par_visit_all_item_likes<'hir, V>(&'hir self, visitor: &V)
737-
where
738-
V: itemlikevisit::ParItemLikeVisitor<'hir> + Sync + Send,
739-
{
740-
par_for_each_in(&self.owners.raw, |owner| match owner {
741-
Some(OwnerNode::Item(item)) => visitor.visit_item(item),
742-
Some(OwnerNode::ForeignItem(item)) => visitor.visit_foreign_item(item),
743-
Some(OwnerNode::ImplItem(item)) => visitor.visit_impl_item(item),
744-
Some(OwnerNode::TraitItem(item)) => visitor.visit_trait_item(item),
745-
Some(OwnerNode::Crate(_)) | None => {}
746-
})
747-
}
748-
749-
pub fn items<'hir>(&'hir self) -> impl Iterator<Item = &'hir Item<'hir>> + 'hir {
750-
self.owners.iter().filter_map(|owner| match owner {
751-
Some(OwnerNode::Item(item)) => Some(*item),
752-
_ => None,
753-
})
754-
}
755-
}
756-
757710
/// A block of statements `{ .. }`, which may have a label (in this case the
758711
/// `targeted_by_break` field will be `true`) and may be `unsafe` by means of
759712
/// the `rules` being anything but `DefaultBlock`.

Diff for: compiler/rustc_hir_pretty/src/lib.rs

-13
Original file line numberDiff line numberDiff line change
@@ -51,19 +51,6 @@ pub struct NoAnn;
5151
impl PpAnn for NoAnn {}
5252
pub const NO_ANN: &dyn PpAnn = &NoAnn;
5353

54-
impl PpAnn for hir::Crate<'_> {
55-
fn nested(&self, state: &mut State<'_>, nested: Nested) {
56-
match nested {
57-
Nested::Item(id) => state.print_item(self.item(id)),
58-
Nested::TraitItem(id) => state.print_trait_item(self.trait_item(id)),
59-
Nested::ImplItem(id) => state.print_impl_item(self.impl_item(id)),
60-
Nested::ForeignItem(id) => state.print_foreign_item(self.foreign_item(id)),
61-
Nested::Body(id) => state.print_expr(&self.body(id).value),
62-
Nested::BodyParamPat(id, i) => state.print_pat(&self.body(id).params[i].pat),
63-
}
64-
}
65-
}
66-
6754
/// Identical to the `PpAnn` implementation for `hir::Crate`,
6855
/// except it avoids creating a dependency on the whole crate.
6956
impl PpAnn for &dyn rustc_hir::intravisit::Map<'_> {

Diff for: compiler/rustc_incremental/src/assert_dep_graph.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,7 @@ pub fn assert_dep_graph(tcx: TyCtxt<'_>) {
7474
let mut visitor =
7575
IfThisChanged { tcx, if_this_changed: vec![], then_this_would_need: vec![] };
7676
visitor.process_attrs(hir::CRATE_HIR_ID);
77-
tcx.hir().krate().visit_all_item_likes(&mut visitor.as_deep_visitor());
77+
tcx.hir().visit_all_item_likes(&mut visitor.as_deep_visitor());
7878
(visitor.if_this_changed, visitor.then_this_would_need)
7979
};
8080

Diff for: compiler/rustc_incremental/src/persist/dirty_clean.rs

+1-2
Original file line numberDiff line numberDiff line change
@@ -137,9 +137,8 @@ pub fn check_dirty_clean_annotations(tcx: TyCtxt<'_>) {
137137
}
138138

139139
tcx.dep_graph.with_ignore(|| {
140-
let krate = tcx.hir().krate();
141140
let mut dirty_clean_visitor = DirtyCleanVisitor { tcx, checked_attrs: Default::default() };
142-
krate.visit_all_item_likes(&mut dirty_clean_visitor);
141+
tcx.hir().visit_all_item_likes(&mut dirty_clean_visitor);
143142

144143
let mut all_attrs = FindAllAttrs { tcx, found_attrs: vec![] };
145144
tcx.hir().walk_attributes(&mut all_attrs);

Diff for: compiler/rustc_interface/src/passes.rs

+3-5
Original file line numberDiff line numberDiff line change
@@ -886,9 +886,7 @@ fn analysis(tcx: TyCtxt<'_>, (): ()) -> Result<()> {
886886
parallel!(
887887
{
888888
sess.time("match_checking", || {
889-
tcx.par_body_owners(|def_id| {
890-
tcx.ensure().check_match(def_id.to_def_id());
891-
});
889+
tcx.hir().par_body_owners(|def_id| tcx.ensure().check_match(def_id.to_def_id()))
892890
});
893891
},
894892
{
@@ -907,11 +905,11 @@ fn analysis(tcx: TyCtxt<'_>, (): ()) -> Result<()> {
907905
});
908906

909907
sess.time("MIR_borrow_checking", || {
910-
tcx.par_body_owners(|def_id| tcx.ensure().mir_borrowck(def_id));
908+
tcx.hir().par_body_owners(|def_id| tcx.ensure().mir_borrowck(def_id));
911909
});
912910

913911
sess.time("MIR_effect_checking", || {
914-
for def_id in tcx.body_owners() {
912+
for def_id in tcx.hir().body_owners() {
915913
tcx.ensure().thir_check_unsafety(def_id);
916914
if !tcx.sess.opts.debugging_opts.thir_unsafeck {
917915
rustc_mir_transform::check_unsafety::check_unsafety(tcx, def_id);

Diff for: compiler/rustc_interface/src/proc_macro_decls.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ use rustc_span::symbol::sym;
77

88
fn proc_macro_decls_static(tcx: TyCtxt<'_>, (): ()) -> Option<LocalDefId> {
99
let mut finder = Finder { tcx, decls: None };
10-
tcx.hir().krate().visit_all_item_likes(&mut finder);
10+
tcx.hir().visit_all_item_likes(&mut finder);
1111

1212
finder.decls.map(|id| tcx.hir().local_def_id(id))
1313
}

Diff for: compiler/rustc_lint/src/builtin.rs

+8-2
Original file line numberDiff line numberDiff line change
@@ -584,8 +584,14 @@ impl<'tcx> LateLintPass<'tcx> for MissingDoc {
584584
self.doc_hidden_stack.pop().expect("empty doc_hidden_stack");
585585
}
586586

587-
fn check_crate(&mut self, cx: &LateContext<'_>, krate: &hir::Crate<'_>) {
588-
self.check_missing_docs_attrs(cx, CRATE_DEF_ID, krate.module().inner, "the", "crate");
587+
fn check_crate(&mut self, cx: &LateContext<'_>) {
588+
self.check_missing_docs_attrs(
589+
cx,
590+
CRATE_DEF_ID,
591+
cx.tcx.def_span(CRATE_DEF_ID),
592+
"the",
593+
"crate",
594+
);
589595
}
590596

591597
fn check_item(&mut self, cx: &LateContext<'_>, it: &hir::Item<'_>) {

Diff for: compiler/rustc_lint/src/late.rs

+2-4
Original file line numberDiff line numberDiff line change
@@ -430,8 +430,6 @@ pub fn late_lint_mod<'tcx, T: LateLintPass<'tcx>>(
430430
fn late_lint_pass_crate<'tcx, T: LateLintPass<'tcx>>(tcx: TyCtxt<'tcx>, pass: T) {
431431
let access_levels = &tcx.privacy_access_levels(());
432432

433-
let krate = tcx.hir().krate();
434-
435433
let context = LateContext {
436434
tcx,
437435
enclosing_body: None,
@@ -450,10 +448,10 @@ fn late_lint_pass_crate<'tcx, T: LateLintPass<'tcx>>(tcx: TyCtxt<'tcx>, pass: T)
450448
cx.with_lint_attrs(hir::CRATE_HIR_ID, |cx| {
451449
// since the root module isn't visited as an item (because it isn't an
452450
// item), warn for it here.
453-
lint_callback!(cx, check_crate, krate);
451+
lint_callback!(cx, check_crate,);
454452
tcx.hir().walk_toplevel_module(cx);
455453
tcx.hir().walk_attributes(cx);
456-
lint_callback!(cx, check_crate_post, krate);
454+
lint_callback!(cx, check_crate_post,);
457455
})
458456
}
459457

Diff for: compiler/rustc_lint/src/passes.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -16,8 +16,8 @@ macro_rules! late_lint_methods {
1616
fn check_body(a: &$hir hir::Body<$hir>);
1717
fn check_body_post(a: &$hir hir::Body<$hir>);
1818
fn check_name(a: Span, b: Symbol);
19-
fn check_crate(a: &$hir hir::Crate<$hir>);
20-
fn check_crate_post(a: &$hir hir::Crate<$hir>);
19+
fn check_crate();
20+
fn check_crate_post();
2121
fn check_mod(a: &$hir hir::Mod<$hir>, b: Span, c: hir::HirId);
2222
fn check_mod_post(a: &$hir hir::Mod<$hir>, b: Span, c: hir::HirId);
2323
fn check_foreign_item(a: &$hir hir::ForeignItem<$hir>);

Diff for: compiler/rustc_metadata/src/foreign_modules.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ use rustc_middle::ty::TyCtxt;
55

66
crate fn collect(tcx: TyCtxt<'_>) -> Vec<ForeignModule> {
77
let mut collector = Collector { modules: Vec::new() };
8-
tcx.hir().krate().visit_all_item_likes(&mut collector);
8+
tcx.hir().visit_all_item_likes(&mut collector);
99
collector.modules
1010
}
1111

Diff for: compiler/rustc_metadata/src/native_libs.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ use rustc_target::spec::abi::Abi;
1414

1515
crate fn collect(tcx: TyCtxt<'_>) -> Vec<NativeLib> {
1616
let mut collector = Collector { tcx, libs: Vec::new() };
17-
tcx.hir().krate().visit_all_item_likes(&mut collector);
17+
tcx.hir().visit_all_item_likes(&mut collector);
1818
collector.process_command_line();
1919
collector.libs
2020
}

Diff for: compiler/rustc_metadata/src/rmeta/encoder.rs

+3-4
Original file line numberDiff line numberDiff line change
@@ -440,16 +440,15 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
440440
}
441441

442442
fn encode_info_for_items(&mut self) {
443-
let krate = self.tcx.hir().krate();
444-
self.encode_info_for_mod(CRATE_DEF_ID, krate.module());
443+
self.encode_info_for_mod(CRATE_DEF_ID, self.tcx.hir().root_module());
445444

446445
// Proc-macro crates only export proc-macro items, which are looked
447446
// up using `proc_macro_data`
448447
if self.is_proc_macro {
449448
return;
450449
}
451450

452-
krate.visit_all_item_likes(&mut self.as_deep_visitor());
451+
self.tcx.hir().visit_all_item_likes(&mut self.as_deep_visitor());
453452
}
454453

455454
fn encode_def_path_table(&mut self) {
@@ -1782,7 +1781,7 @@ impl EncodeContext<'a, 'tcx> {
17821781
debug!("EncodeContext::encode_impls()");
17831782
let tcx = self.tcx;
17841783
let mut visitor = ImplVisitor { tcx, impls: FxHashMap::default() };
1785-
tcx.hir().krate().visit_all_item_likes(&mut visitor);
1784+
tcx.hir().visit_all_item_likes(&mut visitor);
17861785

17871786
let mut all_impls: Vec<_> = visitor.impls.into_iter().collect();
17881787

Diff for: compiler/rustc_middle/src/hir/map/mod.rs

+66
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ use rustc_ast as ast;
66
use rustc_data_structures::fingerprint::Fingerprint;
77
use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
88
use rustc_data_structures::svh::Svh;
9+
use rustc_data_structures::sync::{par_for_each_in, Send, Sync};
910
use rustc_hir::def::{DefKind, Res};
1011
use rustc_hir::def_id::{CrateNum, DefId, LocalDefId, CRATE_DEF_ID, LOCAL_CRATE};
1112
use rustc_hir::definitions::{DefKey, DefPath, DefPathHash};
@@ -156,6 +157,21 @@ impl<'hir> Map<'hir> {
156157
self.tcx.hir_crate(())
157158
}
158159

160+
pub fn root_module(&self) -> &'hir Mod<'hir> {
161+
match self.tcx.hir_owner(CRATE_DEF_ID).map(|o| o.node) {
162+
Some(OwnerNode::Crate(item)) => item,
163+
_ => bug!(),
164+
}
165+
}
166+
167+
pub fn items(&self) -> impl Iterator<Item = &'hir Item<'hir>> + 'hir {
168+
let krate = self.krate();
169+
krate.owners.iter().filter_map(|owner| match owner.as_ref()? {
170+
OwnerNode::Item(item) => Some(*item),
171+
_ => None,
172+
})
173+
}
174+
159175
pub fn def_key(&self, def_id: LocalDefId) -> DefKey {
160176
// Accessing the DefKey is ok, since it is part of DefPathHash.
161177
self.tcx.untracked_resolutions.definitions.def_key(def_id)
@@ -475,6 +491,17 @@ impl<'hir> Map<'hir> {
475491
Some(ccx)
476492
}
477493

494+
/// Returns an iterator of the `DefId`s for all body-owners in this
495+
/// crate. If you would prefer to iterate over the bodies
496+
/// themselves, you can do `self.hir().krate().body_ids.iter()`.
497+
pub fn body_owners(self) -> impl Iterator<Item = LocalDefId> + 'hir {
498+
self.krate().bodies.keys().map(move |&body_id| self.body_owner_def_id(body_id))
499+
}
500+
501+
pub fn par_body_owners<F: Fn(LocalDefId) + Sync + Send>(self, f: F) {
502+
par_for_each_in(&self.krate().bodies, |(&body_id, _)| f(self.body_owner_def_id(body_id)));
503+
}
504+
478505
pub fn ty_param_owner(&self, id: HirId) -> HirId {
479506
match self.get(id) {
480507
Node::Item(&Item { kind: ItemKind::Trait(..) | ItemKind::TraitAlias(..), .. }) => id,
@@ -531,6 +558,45 @@ impl<'hir> Map<'hir> {
531558
}
532559
}
533560

561+
/// Visits all items in the crate in some deterministic (but
562+
/// unspecified) order. If you just need to process every item,
563+
/// but don't care about nesting, this method is the best choice.
564+
///
565+
/// If you do care about nesting -- usually because your algorithm
566+
/// follows lexical scoping rules -- then you want a different
567+
/// approach. You should override `visit_nested_item` in your
568+
/// visitor and then call `intravisit::walk_crate` instead.
569+
pub fn visit_all_item_likes<V>(&self, visitor: &mut V)
570+
where
571+
V: itemlikevisit::ItemLikeVisitor<'hir>,
572+
{
573+
let krate = self.krate();
574+
for owner in krate.owners.iter().filter_map(Option::as_ref) {
575+
match owner {
576+
OwnerNode::Item(item) => visitor.visit_item(item),
577+
OwnerNode::ForeignItem(item) => visitor.visit_foreign_item(item),
578+
OwnerNode::ImplItem(item) => visitor.visit_impl_item(item),
579+
OwnerNode::TraitItem(item) => visitor.visit_trait_item(item),
580+
OwnerNode::Crate(_) => {}
581+
}
582+
}
583+
}
584+
585+
/// A parallel version of `visit_all_item_likes`.
586+
pub fn par_visit_all_item_likes<V>(&self, visitor: &V)
587+
where
588+
V: itemlikevisit::ParItemLikeVisitor<'hir> + Sync + Send,
589+
{
590+
let krate = self.krate();
591+
par_for_each_in(&krate.owners.raw, |owner| match owner.as_ref() {
592+
Some(OwnerNode::Item(item)) => visitor.visit_item(item),
593+
Some(OwnerNode::ForeignItem(item)) => visitor.visit_foreign_item(item),
594+
Some(OwnerNode::ImplItem(item)) => visitor.visit_impl_item(item),
595+
Some(OwnerNode::TraitItem(item)) => visitor.visit_trait_item(item),
596+
Some(OwnerNode::Crate(_)) | None => {}
597+
})
598+
}
599+
534600
pub fn visit_item_likes_in_module<V>(&self, module: LocalDefId, visitor: &mut V)
535601
where
536602
V: ItemLikeVisitor<'hir>,

Diff for: compiler/rustc_middle/src/ty/mod.rs

-14
Original file line numberDiff line numberDiff line change
@@ -29,10 +29,8 @@ use crate::ty::subst::{GenericArg, InternalSubsts, Subst, SubstsRef};
2929
use crate::ty::util::Discr;
3030
use rustc_ast as ast;
3131
use rustc_attr as attr;
32-
use rustc_data_structures::captures::Captures;
3332
use rustc_data_structures::fx::{FxHashMap, FxHashSet};
3433
use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
35-
use rustc_data_structures::sync::{self, par_iter, ParallelIterator};
3634
use rustc_data_structures::tagged_ptr::CopyTaggedPtr;
3735
use rustc_hir as hir;
3836
use rustc_hir::def::{CtorKind, CtorOf, DefKind, Res};
@@ -1696,18 +1694,6 @@ impl<'tcx> TyCtxt<'tcx> {
16961694
self.typeck(self.hir().body_owner_def_id(body))
16971695
}
16981696

1699-
/// Returns an iterator of the `DefId`s for all body-owners in this
1700-
/// crate. If you would prefer to iterate over the bodies
1701-
/// themselves, you can do `self.hir().krate().body_ids.iter()`.
1702-
pub fn body_owners(self) -> impl Iterator<Item = LocalDefId> + Captures<'tcx> + 'tcx {
1703-
self.hir().krate().bodies.keys().map(move |&body_id| self.hir().body_owner_def_id(body_id))
1704-
}
1705-
1706-
pub fn par_body_owners<F: Fn(LocalDefId) + sync::Sync + sync::Send>(self, f: F) {
1707-
par_iter(&self.hir().krate().bodies)
1708-
.for_each(|(&body_id, _)| f(self.hir().body_owner_def_id(body_id)));
1709-
}
1710-
17111697
pub fn provided_trait_methods(self, id: DefId) -> impl 'tcx + Iterator<Item = &'tcx AssocItem> {
17121698
self.associated_items(id)
17131699
.in_definition_order()

Diff for: compiler/rustc_middle/src/ty/print/pretty.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -2340,7 +2340,7 @@ define_print_and_forward_display! {
23402340
fn for_each_def(tcx: TyCtxt<'_>, mut collect_fn: impl for<'b> FnMut(&'b Ident, Namespace, DefId)) {
23412341
// Iterate all local crate items no matter where they are defined.
23422342
let hir = tcx.hir();
2343-
for item in hir.krate().items() {
2343+
for item in hir.items() {
23442344
if item.ident.name.as_str().is_empty() || matches!(item.kind, ItemKind::Use(_, _)) {
23452345
continue;
23462346
}

0 commit comments

Comments
 (0)