diff --git a/src/librustc/hir/mod.rs b/src/librustc/hir/mod.rs index 30c9a2ee769f..fd0a7e73b347 100644 --- a/src/librustc/hir/mod.rs +++ b/src/librustc/hir/mod.rs @@ -7,12 +7,36 @@ pub mod map; use crate::ty::query::Providers; use crate::ty::TyCtxt; +use rustc_data_structures::fx::FxHashMap; use rustc_hir::def_id::{DefId, LOCAL_CRATE}; use rustc_hir::print; +use rustc_hir::Body; use rustc_hir::Crate; use rustc_hir::HirId; +use rustc_hir::ItemLocalId; +use rustc_hir::Node; +use rustc_index::vec::IndexVec; use std::ops::Deref; +#[derive(HashStable)] +pub struct HirOwner<'tcx> { + parent: HirId, + node: Node<'tcx>, +} + +#[derive(HashStable)] +pub struct HirItem<'tcx> { + parent: ItemLocalId, + node: Node<'tcx>, +} + +#[derive(HashStable)] +pub struct HirOwnerItems<'tcx> { + owner: &'tcx HirOwner<'tcx>, + items: IndexVec>>, + bodies: FxHashMap>, +} + /// A wrapper type which allows you to access HIR. #[derive(Clone)] pub struct Hir<'tcx> { diff --git a/src/librustc/ich/hcx.rs b/src/librustc/ich/hcx.rs index f28e26ef2c39..5a49d9a1f1ae 100644 --- a/src/librustc/ich/hcx.rs +++ b/src/librustc/ich/hcx.rs @@ -164,15 +164,6 @@ impl<'a> StableHashingContext<'a> { } IGNORED_ATTRIBUTES.with(|attrs| attrs.contains(&name)) } - - pub fn hash_hir_item_like(&mut self, f: F) { - let prev_hash_node_ids = self.node_id_hashing_mode; - self.node_id_hashing_mode = NodeIdHashingMode::Ignore; - - f(self); - - self.node_id_hashing_mode = prev_hash_node_ids; - } } /// Something that can provide a stable hashing context. diff --git a/src/librustc/ich/impls_hir.rs b/src/librustc/ich/impls_hir.rs index eadc9ddeee6f..1015ffdbf283 100644 --- a/src/librustc/ich/impls_hir.rs +++ b/src/librustc/ich/impls_hir.rs @@ -105,6 +105,15 @@ impl<'ctx> rustc_hir::HashStableContext for StableHashingContext<'ctx> { } } } + + fn hash_hir_item_like(&mut self, f: F) { + let prev_hash_node_ids = self.node_id_hashing_mode; + self.node_id_hashing_mode = NodeIdHashingMode::Ignore; + + f(self); + + self.node_id_hashing_mode = prev_hash_node_ids; + } } impl<'a> ToStableHashKey> for DefId { @@ -158,59 +167,6 @@ impl<'a> ToStableHashKey> for hir::ItemLocalId { } } -impl<'a> HashStable> for hir::TraitItem<'_> { - fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) { - let hir::TraitItem { hir_id: _, ident, ref attrs, ref generics, ref kind, span } = *self; - - hcx.hash_hir_item_like(|hcx| { - ident.name.hash_stable(hcx, hasher); - attrs.hash_stable(hcx, hasher); - generics.hash_stable(hcx, hasher); - kind.hash_stable(hcx, hasher); - span.hash_stable(hcx, hasher); - }); - } -} - -impl<'a> HashStable> for hir::ImplItem<'_> { - fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) { - let hir::ImplItem { - hir_id: _, - ident, - ref vis, - defaultness, - ref attrs, - ref generics, - ref kind, - span, - } = *self; - - hcx.hash_hir_item_like(|hcx| { - ident.name.hash_stable(hcx, hasher); - vis.hash_stable(hcx, hasher); - defaultness.hash_stable(hcx, hasher); - attrs.hash_stable(hcx, hasher); - generics.hash_stable(hcx, hasher); - kind.hash_stable(hcx, hasher); - span.hash_stable(hcx, hasher); - }); - } -} - -impl<'a> HashStable> for hir::Item<'_> { - fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) { - let hir::Item { ident, ref attrs, hir_id: _, ref kind, ref vis, span } = *self; - - hcx.hash_hir_item_like(|hcx| { - ident.name.hash_stable(hcx, hasher); - attrs.hash_stable(hcx, hasher); - kind.hash_stable(hcx, hasher); - vis.hash_stable(hcx, hasher); - span.hash_stable(hcx, hasher); - }); - } -} - impl<'a> HashStable> for hir::Body<'_> { fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) { let hir::Body { params, value, generator_kind } = self; diff --git a/src/librustc/query/mod.rs b/src/librustc/query/mod.rs index 11e9acf3a391..cf7cb30a056d 100644 --- a/src/librustc/query/mod.rs +++ b/src/librustc/query/mod.rs @@ -55,6 +55,14 @@ rustc_queries! { desc { "get the crate HIR" } } + query hir_owner(key: DefId) -> &'tcx HirOwner<'tcx> { + eval_always + } + + query hir_owner_items(key: DefId) -> &'tcx HirOwnerItems<'tcx> { + eval_always + } + /// Records the type of every item. query type_of(key: DefId) -> Ty<'tcx> { cache_on_disk_if { key.is_local() } diff --git a/src/librustc/ty/query/mod.rs b/src/librustc/ty/query/mod.rs index 8adb828fbebc..667c00a3df16 100644 --- a/src/librustc/ty/query/mod.rs +++ b/src/librustc/ty/query/mod.rs @@ -1,5 +1,6 @@ use crate::dep_graph::{self, DepConstructor, DepNode, DepNodeParams}; use crate::hir::exports::Export; +use crate::hir::{HirOwner, HirOwnerItems}; use crate::infer::canonical::{self, Canonical}; use crate::lint::LintLevelMap; use crate::middle::codegen_fn_attrs::CodegenFnAttrs; diff --git a/src/librustc_hir/hir.rs b/src/librustc_hir/hir.rs index 9993e5c55f66..ed06aeb60bb1 100644 --- a/src/librustc_hir/hir.rs +++ b/src/librustc_hir/hir.rs @@ -2653,7 +2653,7 @@ pub type TraitMap = NodeMap>>; // imported. pub type GlobMap = NodeMap>; -#[derive(Copy, Clone, Debug)] +#[derive(Copy, Clone, Debug, HashStable_Generic)] pub enum Node<'hir> { Param(&'hir Param<'hir>), Item(&'hir Item<'hir>), diff --git a/src/librustc_hir/stable_hash_impls.rs b/src/librustc_hir/stable_hash_impls.rs index 3938a0369b92..9756edc3f4dc 100644 --- a/src/librustc_hir/stable_hash_impls.rs +++ b/src/librustc_hir/stable_hash_impls.rs @@ -1,6 +1,9 @@ use rustc_data_structures::stable_hasher::{HashStable, StableHasher}; -use crate::hir::{BodyId, Expr, ImplItemId, ItemId, Mod, TraitItemId, Ty, VisibilityKind}; +use crate::hir::{ + BodyId, Expr, ImplItem, ImplItemId, Item, ItemId, Mod, TraitItem, TraitItemId, Ty, + VisibilityKind, +}; use crate::hir_id::HirId; /// Requirements for a `StableHashingContext` to be used in this crate. @@ -16,6 +19,7 @@ pub trait HashStableContext: fn hash_hir_expr(&mut self, _: &Expr<'_>, hasher: &mut StableHasher); fn hash_hir_ty(&mut self, _: &Ty<'_>, hasher: &mut StableHasher); fn hash_hir_visibility_kind(&mut self, _: &VisibilityKind<'_>, hasher: &mut StableHasher); + fn hash_hir_item_like(&mut self, f: F); } impl HashStable for HirId { @@ -78,3 +82,56 @@ impl HashStable for VisibilityKind<'_> hcx.hash_hir_visibility_kind(self, hasher) } } + +impl HashStable for TraitItem<'_> { + fn hash_stable(&self, hcx: &mut HirCtx, hasher: &mut StableHasher) { + let TraitItem { hir_id: _, ident, ref attrs, ref generics, ref kind, span } = *self; + + hcx.hash_hir_item_like(|hcx| { + ident.name.hash_stable(hcx, hasher); + attrs.hash_stable(hcx, hasher); + generics.hash_stable(hcx, hasher); + kind.hash_stable(hcx, hasher); + span.hash_stable(hcx, hasher); + }); + } +} + +impl HashStable for ImplItem<'_> { + fn hash_stable(&self, hcx: &mut HirCtx, hasher: &mut StableHasher) { + let ImplItem { + hir_id: _, + ident, + ref vis, + defaultness, + ref attrs, + ref generics, + ref kind, + span, + } = *self; + + hcx.hash_hir_item_like(|hcx| { + ident.name.hash_stable(hcx, hasher); + vis.hash_stable(hcx, hasher); + defaultness.hash_stable(hcx, hasher); + attrs.hash_stable(hcx, hasher); + generics.hash_stable(hcx, hasher); + kind.hash_stable(hcx, hasher); + span.hash_stable(hcx, hasher); + }); + } +} + +impl HashStable for Item<'_> { + fn hash_stable(&self, hcx: &mut HirCtx, hasher: &mut StableHasher) { + let Item { ident, ref attrs, hir_id: _, ref kind, ref vis, span } = *self; + + hcx.hash_hir_item_like(|hcx| { + ident.name.hash_stable(hcx, hasher); + attrs.hash_stable(hcx, hasher); + kind.hash_stable(hcx, hasher); + vis.hash_stable(hcx, hasher); + span.hash_stable(hcx, hasher); + }); + } +}