]> git.lizzy.rs Git - rust.git/blob - src/librustc/ich/impls_hir.rs
Rollup merge of #68837 - jonas-schievink:assoc-item-lookup-2, r=estebank
[rust.git] / src / librustc / ich / impls_hir.rs
1 //! This module contains `HashStable` implementations for various HIR data
2 //! types in no particular order.
3
4 use crate::hir::map::DefPathHash;
5 use crate::ich::{Fingerprint, NodeIdHashingMode, StableHashingContext};
6 use rustc_attr as attr;
7 use rustc_data_structures::stable_hasher::{HashStable, StableHasher, ToStableHashKey};
8 use rustc_hir as hir;
9 use rustc_hir::def_id::{CrateNum, DefId, LocalDefId, CRATE_DEF_INDEX};
10 use smallvec::SmallVec;
11 use std::mem;
12
13 impl<'ctx> rustc_hir::HashStableContext for StableHashingContext<'ctx> {
14     #[inline]
15     fn hash_def_id(&mut self, def_id: DefId, hasher: &mut StableHasher) {
16         let hcx = self;
17         hcx.def_path_hash(def_id).hash_stable(hcx, hasher);
18     }
19
20     #[inline]
21     fn hash_hir_id(&mut self, hir_id: hir::HirId, hasher: &mut StableHasher) {
22         let hcx = self;
23         match hcx.node_id_hashing_mode {
24             NodeIdHashingMode::Ignore => {
25                 // Don't do anything.
26             }
27             NodeIdHashingMode::HashDefPath => {
28                 let hir::HirId { owner, local_id } = hir_id;
29
30                 hcx.local_def_path_hash(owner).hash_stable(hcx, hasher);
31                 local_id.hash_stable(hcx, hasher);
32             }
33         }
34     }
35
36     fn hash_body_id(&mut self, id: hir::BodyId, hasher: &mut StableHasher) {
37         let hcx = self;
38         if hcx.hash_bodies() {
39             hcx.body_resolver.body(id).hash_stable(hcx, hasher);
40         }
41     }
42
43     fn hash_reference_to_item(&mut self, id: hir::HirId, hasher: &mut StableHasher) {
44         let hcx = self;
45
46         hcx.with_node_id_hashing_mode(NodeIdHashingMode::HashDefPath, |hcx| {
47             id.hash_stable(hcx, hasher);
48         })
49     }
50
51     fn hash_hir_mod(&mut self, module: &hir::Mod<'_>, hasher: &mut StableHasher) {
52         let hcx = self;
53         let hir::Mod { inner: ref inner_span, ref item_ids } = *module;
54
55         inner_span.hash_stable(hcx, hasher);
56
57         // Combining the `DefPathHash`s directly is faster than feeding them
58         // into the hasher. Because we use a commutative combine, we also don't
59         // have to sort the array.
60         let item_ids_hash = item_ids
61             .iter()
62             .map(|id| {
63                 let (def_path_hash, local_id) = id.id.to_stable_hash_key(hcx);
64                 debug_assert_eq!(local_id, hir::ItemLocalId::from_u32(0));
65                 def_path_hash.0
66             })
67             .fold(Fingerprint::ZERO, |a, b| a.combine_commutative(b));
68
69         item_ids.len().hash_stable(hcx, hasher);
70         item_ids_hash.hash_stable(hcx, hasher);
71     }
72
73     fn hash_hir_expr(&mut self, expr: &hir::Expr<'_>, hasher: &mut StableHasher) {
74         self.while_hashing_hir_bodies(true, |hcx| {
75             let hir::Expr { hir_id: _, ref span, ref kind, ref attrs } = *expr;
76
77             span.hash_stable(hcx, hasher);
78             kind.hash_stable(hcx, hasher);
79             attrs.hash_stable(hcx, hasher);
80         })
81     }
82
83     fn hash_hir_ty(&mut self, ty: &hir::Ty<'_>, hasher: &mut StableHasher) {
84         self.while_hashing_hir_bodies(true, |hcx| {
85             let hir::Ty { hir_id: _, ref kind, ref span } = *ty;
86
87             kind.hash_stable(hcx, hasher);
88             span.hash_stable(hcx, hasher);
89         })
90     }
91
92     fn hash_hir_visibility_kind(
93         &mut self,
94         vis: &hir::VisibilityKind<'_>,
95         hasher: &mut StableHasher,
96     ) {
97         let hcx = self;
98         mem::discriminant(vis).hash_stable(hcx, hasher);
99         match *vis {
100             hir::VisibilityKind::Public | hir::VisibilityKind::Inherited => {
101                 // No fields to hash.
102             }
103             hir::VisibilityKind::Crate(sugar) => {
104                 sugar.hash_stable(hcx, hasher);
105             }
106             hir::VisibilityKind::Restricted { ref path, hir_id } => {
107                 hcx.with_node_id_hashing_mode(NodeIdHashingMode::HashDefPath, |hcx| {
108                     hir_id.hash_stable(hcx, hasher);
109                 });
110                 path.hash_stable(hcx, hasher);
111             }
112         }
113     }
114 }
115
116 impl<'a> ToStableHashKey<StableHashingContext<'a>> for DefId {
117     type KeyType = DefPathHash;
118
119     #[inline]
120     fn to_stable_hash_key(&self, hcx: &StableHashingContext<'a>) -> DefPathHash {
121         hcx.def_path_hash(*self)
122     }
123 }
124
125 impl<'a> HashStable<StableHashingContext<'a>> for LocalDefId {
126     #[inline]
127     fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) {
128         hcx.def_path_hash(self.to_def_id()).hash_stable(hcx, hasher);
129     }
130 }
131
132 impl<'a> ToStableHashKey<StableHashingContext<'a>> for LocalDefId {
133     type KeyType = DefPathHash;
134
135     #[inline]
136     fn to_stable_hash_key(&self, hcx: &StableHashingContext<'a>) -> DefPathHash {
137         hcx.def_path_hash(self.to_def_id())
138     }
139 }
140
141 impl<'a> HashStable<StableHashingContext<'a>> for CrateNum {
142     #[inline]
143     fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) {
144         hcx.def_path_hash(DefId { krate: *self, index: CRATE_DEF_INDEX }).hash_stable(hcx, hasher);
145     }
146 }
147
148 impl<'a> ToStableHashKey<StableHashingContext<'a>> for CrateNum {
149     type KeyType = DefPathHash;
150
151     #[inline]
152     fn to_stable_hash_key(&self, hcx: &StableHashingContext<'a>) -> DefPathHash {
153         let def_id = DefId { krate: *self, index: CRATE_DEF_INDEX };
154         def_id.to_stable_hash_key(hcx)
155     }
156 }
157
158 impl<'a> ToStableHashKey<StableHashingContext<'a>> for hir::ItemLocalId {
159     type KeyType = hir::ItemLocalId;
160
161     #[inline]
162     fn to_stable_hash_key(&self, _: &StableHashingContext<'a>) -> hir::ItemLocalId {
163         *self
164     }
165 }
166
167 impl<'a> HashStable<StableHashingContext<'a>> for hir::TraitItem<'_> {
168     fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) {
169         let hir::TraitItem { hir_id: _, ident, ref attrs, ref generics, ref kind, span } = *self;
170
171         hcx.hash_hir_item_like(|hcx| {
172             ident.name.hash_stable(hcx, hasher);
173             attrs.hash_stable(hcx, hasher);
174             generics.hash_stable(hcx, hasher);
175             kind.hash_stable(hcx, hasher);
176             span.hash_stable(hcx, hasher);
177         });
178     }
179 }
180
181 impl<'a> HashStable<StableHashingContext<'a>> for hir::ImplItem<'_> {
182     fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) {
183         let hir::ImplItem {
184             hir_id: _,
185             ident,
186             ref vis,
187             defaultness,
188             ref attrs,
189             ref generics,
190             ref kind,
191             span,
192         } = *self;
193
194         hcx.hash_hir_item_like(|hcx| {
195             ident.name.hash_stable(hcx, hasher);
196             vis.hash_stable(hcx, hasher);
197             defaultness.hash_stable(hcx, hasher);
198             attrs.hash_stable(hcx, hasher);
199             generics.hash_stable(hcx, hasher);
200             kind.hash_stable(hcx, hasher);
201             span.hash_stable(hcx, hasher);
202         });
203     }
204 }
205
206 impl<'a> HashStable<StableHashingContext<'a>> for hir::Item<'_> {
207     fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) {
208         let hir::Item { ident, ref attrs, hir_id: _, ref kind, ref vis, span } = *self;
209
210         hcx.hash_hir_item_like(|hcx| {
211             ident.name.hash_stable(hcx, hasher);
212             attrs.hash_stable(hcx, hasher);
213             kind.hash_stable(hcx, hasher);
214             vis.hash_stable(hcx, hasher);
215             span.hash_stable(hcx, hasher);
216         });
217     }
218 }
219
220 impl<'a> HashStable<StableHashingContext<'a>> for hir::Body<'_> {
221     fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) {
222         let hir::Body { params, value, generator_kind } = self;
223
224         hcx.with_node_id_hashing_mode(NodeIdHashingMode::Ignore, |hcx| {
225             params.hash_stable(hcx, hasher);
226             value.hash_stable(hcx, hasher);
227             generator_kind.hash_stable(hcx, hasher);
228         });
229     }
230 }
231
232 impl<'a> ToStableHashKey<StableHashingContext<'a>> for hir::BodyId {
233     type KeyType = (DefPathHash, hir::ItemLocalId);
234
235     #[inline]
236     fn to_stable_hash_key(
237         &self,
238         hcx: &StableHashingContext<'a>,
239     ) -> (DefPathHash, hir::ItemLocalId) {
240         let hir::BodyId { hir_id } = *self;
241         hir_id.to_stable_hash_key(hcx)
242     }
243 }
244
245 impl<'a> HashStable<StableHashingContext<'a>> for hir::def_id::DefIndex {
246     fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) {
247         hcx.local_def_path_hash(*self).hash_stable(hcx, hasher);
248     }
249 }
250
251 impl<'a> ToStableHashKey<StableHashingContext<'a>> for hir::def_id::DefIndex {
252     type KeyType = DefPathHash;
253
254     #[inline]
255     fn to_stable_hash_key(&self, hcx: &StableHashingContext<'a>) -> DefPathHash {
256         hcx.local_def_path_hash(*self)
257     }
258 }
259
260 impl<'a> HashStable<StableHashingContext<'a>> for crate::middle::lang_items::LangItem {
261     fn hash_stable(&self, _: &mut StableHashingContext<'a>, hasher: &mut StableHasher) {
262         ::std::hash::Hash::hash(self, hasher);
263     }
264 }
265
266 impl<'a> HashStable<StableHashingContext<'a>> for hir::TraitCandidate {
267     fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) {
268         hcx.with_node_id_hashing_mode(NodeIdHashingMode::HashDefPath, |hcx| {
269             let hir::TraitCandidate { def_id, import_ids } = self;
270
271             def_id.hash_stable(hcx, hasher);
272             import_ids.hash_stable(hcx, hasher);
273         });
274     }
275 }
276
277 impl<'a> ToStableHashKey<StableHashingContext<'a>> for hir::TraitCandidate {
278     type KeyType = (DefPathHash, SmallVec<[(DefPathHash, hir::ItemLocalId); 1]>);
279
280     fn to_stable_hash_key(&self, hcx: &StableHashingContext<'a>) -> Self::KeyType {
281         let hir::TraitCandidate { def_id, import_ids } = self;
282
283         let import_keys = import_ids
284             .iter()
285             .map(|node_id| hcx.node_to_hir_id(*node_id))
286             .map(|hir_id| (hcx.local_def_path_hash(hir_id.owner), hir_id.local_id))
287             .collect();
288         (hcx.def_path_hash(*def_id), import_keys)
289     }
290 }
291
292 impl<'hir> HashStable<StableHashingContext<'hir>> for attr::InlineAttr {
293     fn hash_stable(&self, hcx: &mut StableHashingContext<'hir>, hasher: &mut StableHasher) {
294         mem::discriminant(self).hash_stable(hcx, hasher);
295     }
296 }
297
298 impl<'hir> HashStable<StableHashingContext<'hir>> for attr::OptimizeAttr {
299     fn hash_stable(&self, hcx: &mut StableHashingContext<'hir>, hasher: &mut StableHasher) {
300         mem::discriminant(self).hash_stable(hcx, hasher);
301     }
302 }