Branch data Line data Source code
1 : : // Copyright (C) 2020-2025 Free Software Foundation, Inc.
2 : :
3 : : // This file is part of GCC.
4 : :
5 : : // GCC is free software; you can redistribute it and/or modify it under
6 : : // the terms of the GNU General Public License as published by the Free
7 : : // Software Foundation; either version 3, or (at your option) any later
8 : : // version.
9 : :
10 : : // GCC is distributed in the hope that it will be useful, but WITHOUT ANY
11 : : // WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 : : // FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
13 : : // for more details.
14 : :
15 : : // You should have received a copy of the GNU General Public License
16 : : // along with GCC; see the file COPYING3. If not see
17 : : // <http://www.gnu.org/licenses/>.
18 : :
19 : : #ifndef RUST_HIR_MAP_H
20 : : #define RUST_HIR_MAP_H
21 : :
22 : : #include "optional.h"
23 : : #include "rust-system.h"
24 : : #include "rust-location.h"
25 : : #include "rust-mapping-common.h"
26 : : #include "rust-canonical-path.h"
27 : : #include "rust-ast-full-decls.h"
28 : : #include "rust-hir-full-decls.h"
29 : : #include "rust-lang-item.h"
30 : : #include "rust-privacy-common.h"
31 : : #include "libproc_macro_internal/proc_macro.h"
32 : : #include "rust-proc-macro.h"
33 : : #include "optional.h"
34 : :
35 : : namespace Rust {
36 : : namespace Analysis {
37 : :
38 : : class NodeMapping
39 : : {
40 : : public:
41 : 685001 : NodeMapping (CrateNum crateNum, NodeId nodeId, HirId hirId,
42 : : LocalDefId localDefId)
43 : 645820 : : crateNum (crateNum), nodeId (nodeId), hirId (hirId),
44 : 645820 : localDefId (localDefId)
45 : : {}
46 : :
47 : : static NodeMapping get_error ();
48 : :
49 : : CrateNum get_crate_num () const;
50 : : NodeId get_nodeid () const;
51 : : HirId get_hirid () const;
52 : : LocalDefId get_local_defid () const;
53 : : DefId get_defid () const;
54 : :
55 : : static DefId get_defid (CrateNum crate_num, LocalDefId local_defid);
56 : :
57 : : std::string as_string () const;
58 : :
59 : : bool is_equal (const NodeMapping &other) const
60 : : {
61 : : return get_crate_num () == other.get_crate_num ()
62 : : && get_nodeid () == other.get_nodeid ()
63 : : && get_hirid () == other.get_hirid ()
64 : : && get_local_defid () == other.get_local_defid ();
65 : : }
66 : :
67 : : private:
68 : : CrateNum crateNum;
69 : : NodeId nodeId;
70 : : HirId hirId;
71 : : LocalDefId localDefId;
72 : : };
73 : :
74 : : class Mappings
75 : : {
76 : : public:
77 : : static Mappings &get ();
78 : : ~Mappings ();
79 : :
80 : : CrateNum get_next_crate_num (const std::string &name);
81 : : void set_current_crate (CrateNum crateNum);
82 : : CrateNum get_current_crate () const;
83 : : tl::optional<const std::string &> get_crate_name (CrateNum crate_num) const;
84 : :
85 : : tl::optional<CrateNum> lookup_crate_num (NodeId node_id) const;
86 : : void set_crate_name (CrateNum crate_num, const std::string &name);
87 : : const std::string &get_current_crate_name () const;
88 : : tl::optional<CrateNum>
89 : : lookup_crate_name (const std::string &crate_name) const;
90 : : tl::optional<NodeId> crate_num_to_nodeid (const CrateNum &crate_num) const;
91 : : bool node_is_crate (NodeId node_id) const;
92 : :
93 : : NodeId get_next_node_id ();
94 : 225937 : HirId get_next_hir_id () { return get_next_hir_id (get_current_crate ()); }
95 : : HirId get_next_hir_id (CrateNum crateNum);
96 : : LocalDefId get_next_localdef_id ()
97 : : {
98 : : return get_next_localdef_id (get_current_crate ());
99 : : }
100 : : LocalDefId get_next_localdef_id (CrateNum crateNum);
101 : :
102 : : AST::Crate &get_ast_crate (CrateNum crateNum);
103 : : AST::Crate &get_ast_crate_by_node_id (NodeId id);
104 : : AST::Crate &insert_ast_crate (std::unique_ptr<AST::Crate> &&crate,
105 : : CrateNum crate_num);
106 : : HIR::Crate &insert_hir_crate (std::unique_ptr<HIR::Crate> &&crate);
107 : : HIR::Crate &get_hir_crate (CrateNum crateNum);
108 : : bool is_local_hirid_crate (HirId crateNum);
109 : :
110 : : void insert_defid_mapping (DefId id, HIR::Item *item);
111 : : tl::optional<HIR::Item *> lookup_defid (DefId id);
112 : : void insert_defid_mapping (DefId id, HIR::TraitItem *item);
113 : : tl::optional<HIR::TraitItem *> lookup_trait_item_defid (DefId id);
114 : :
115 : : void insert_local_defid_mapping (CrateNum crateNum, LocalDefId id,
116 : : HIR::Item *item);
117 : : tl::optional<HIR::Item *> lookup_local_defid (CrateNum crateNum,
118 : : LocalDefId id);
119 : :
120 : : void insert_hir_item (HIR::Item *item);
121 : : tl::optional<HIR::Item *> lookup_hir_item (HirId id);
122 : :
123 : : void insert_hir_enumitem (HIR::Enum *parent, HIR::EnumItem *item);
124 : : std::pair<HIR::Enum *, HIR::EnumItem *> lookup_hir_enumitem (HirId id);
125 : :
126 : : void insert_hir_trait_item (HIR::TraitItem *item);
127 : : tl::optional<HIR::TraitItem *> lookup_hir_trait_item (HirId id);
128 : :
129 : : void insert_hir_extern_block (HIR::ExternBlock *block);
130 : : tl::optional<HIR::ExternBlock *> lookup_hir_extern_block (HirId id);
131 : :
132 : : void insert_hir_extern_item (HIR::ExternalItem *item, HirId parent_block);
133 : :
134 : : // std::pair<hir_extern_item, parent hirid>
135 : : tl::optional<std::pair<HIR::ExternalItem *, HirId>>
136 : : lookup_hir_extern_item (HirId id);
137 : :
138 : : void insert_hir_impl_block (HIR::ImplBlock *item);
139 : : tl::optional<HIR::ImplBlock *> lookup_hir_impl_block (HirId id);
140 : : tl::optional<HIR::ImplBlock *> lookup_impl_block_type (HirId id);
141 : :
142 : : void insert_module (HIR::Module *module);
143 : : tl::optional<HIR::Module *> lookup_module (HirId id);
144 : :
145 : : void insert_hir_implitem (HirId parent_impl_id, HIR::ImplItem *item);
146 : : // Optional<ImpItem, ParentImpl Hir id>
147 : : tl::optional<std::pair<HIR::ImplItem *, HirId>>
148 : : lookup_hir_implitem (HirId id);
149 : :
150 : : void insert_hir_expr (HIR::Expr *expr);
151 : : tl::optional<HIR::Expr *> lookup_hir_expr (HirId id);
152 : :
153 : : void insert_hir_path_expr_seg (HIR::PathExprSegment *expr);
154 : : tl::optional<HIR::PathExprSegment *> lookup_hir_path_expr_seg (HirId id);
155 : :
156 : : void insert_hir_generic_param (HIR::GenericParam *expr);
157 : : tl::optional<HIR::GenericParam *> lookup_hir_generic_param (HirId id);
158 : :
159 : : void insert_hir_type (HIR::Type *type);
160 : : tl::optional<HIR::Type *> lookup_hir_type (HirId id);
161 : :
162 : : void insert_hir_stmt (HIR::Stmt *stmt);
163 : : tl::optional<HIR::Stmt *> lookup_hir_stmt (HirId id);
164 : :
165 : : void insert_hir_param (HIR::FunctionParam *type);
166 : : tl::optional<HIR::FunctionParam *> lookup_hir_param (HirId id);
167 : :
168 : : void insert_hir_self_param (HIR::SelfParam *type);
169 : : tl::optional<HIR::SelfParam *> lookup_hir_self_param (HirId id);
170 : :
171 : : void insert_hir_struct_field (HIR::StructExprField *type);
172 : : tl::optional<HIR::StructExprField *> lookup_hir_struct_field (HirId id);
173 : :
174 : : void insert_hir_pattern (HIR::Pattern *pattern);
175 : : tl::optional<HIR::Pattern *> lookup_hir_pattern (HirId id);
176 : :
177 : : void walk_local_defids_for_crate (CrateNum crateNum,
178 : : std::function<bool (HIR::Item *)> cb);
179 : :
180 : : void insert_node_to_hir (NodeId id, HirId ref);
181 : : tl::optional<HirId> lookup_node_to_hir (NodeId id);
182 : : tl::optional<NodeId> lookup_hir_to_node (HirId id);
183 : :
184 : : void insert_location (HirId id, location_t locus);
185 : : location_t lookup_location (HirId id);
186 : :
187 : : tl::optional<HIR::Stmt *> resolve_nodeid_to_stmt (NodeId id);
188 : :
189 : : std::set<HirId> &get_hirids_within_crate (CrateNum crate)
190 : : {
191 : : return hirNodesWithinCrate[crate];
192 : : }
193 : :
194 : 7103 : void insert_impl_item_mapping (HirId impl_item_id, HIR::ImplBlock *impl)
195 : : {
196 : 7103 : rust_assert (hirImplItemsToImplMappings.find (impl_item_id)
197 : : == hirImplItemsToImplMappings.end ());
198 : 7103 : hirImplItemsToImplMappings[impl_item_id] = impl;
199 : 7103 : }
200 : :
201 : 206129 : HIR::ImplBlock *lookup_associated_impl (HirId impl_item_id)
202 : : {
203 : 206129 : auto lookup = hirImplItemsToImplMappings.find (impl_item_id);
204 : 206129 : rust_assert (lookup != hirImplItemsToImplMappings.end ());
205 : 206129 : return lookup->second;
206 : : }
207 : :
208 : : void iterate_impl_items (
209 : : std::function<bool (HirId, HIR::ImplItem *, HIR::ImplBlock *)> cb);
210 : :
211 : : void iterate_impl_blocks (std::function<bool (HirId, HIR::ImplBlock *)> cb);
212 : :
213 : : void iterate_trait_items (
214 : : std::function<bool (HIR::TraitItem *item, HIR::Trait *)> cb);
215 : :
216 : 2977 : bool is_impl_item (HirId id) { return lookup_hir_implitem (id).has_value (); }
217 : :
218 : 2504 : void insert_trait_item_mapping (HirId trait_item_id, HIR::Trait *trait)
219 : : {
220 : 2504 : rust_assert (hirTraitItemsToTraitMappings.find (trait_item_id)
221 : : == hirTraitItemsToTraitMappings.end ());
222 : 2504 : hirTraitItemsToTraitMappings[trait_item_id] = trait;
223 : 2504 : }
224 : :
225 : 722 : HIR::Trait *lookup_trait_item_mapping (HirId trait_item_id)
226 : : {
227 : 722 : auto lookup = hirTraitItemsToTraitMappings.find (trait_item_id);
228 : 722 : rust_assert (lookup != hirTraitItemsToTraitMappings.end ());
229 : 722 : return lookup->second;
230 : : }
231 : :
232 : 131221 : void insert_canonical_path (NodeId id, const Resolver::CanonicalPath path)
233 : : {
234 : 131221 : if (auto p = lookup_canonical_path (id))
235 : : {
236 : : // if we have already stored a canonical path this is ok so long as
237 : : // this new path is equal or is smaller that the existing one but in
238 : : // that case we ignore it.
239 : 12909 : if (p->is_equal (path))
240 : 12909 : return;
241 : : else
242 : : {
243 : 2163 : rust_assert (p->size () >= path.size ());
244 : : return;
245 : : }
246 : : }
247 : :
248 : 118312 : paths.emplace (id, std::move (path));
249 : : }
250 : :
251 : : tl::optional<const Resolver::CanonicalPath &>
252 : 174219 : lookup_canonical_path (NodeId id)
253 : : {
254 : 174219 : auto it = paths.find (id);
255 : 174219 : if (it == paths.end ())
256 : 118312 : return tl::nullopt;
257 : :
258 : 55907 : return it->second;
259 : : }
260 : :
261 : : void insert_lang_item (LangItem::Kind item_type, DefId id);
262 : : tl::optional<DefId &> lookup_lang_item (LangItem::Kind item_type);
263 : :
264 : : void insert_lang_item_node (LangItem::Kind item_type, NodeId node_id);
265 : : tl::optional<NodeId &> lookup_lang_item_node (LangItem::Kind item_type);
266 : : NodeId get_lang_item_node (LangItem::Kind item_type);
267 : :
268 : : // This will fatal_error when this lang item does not exist
269 : : DefId get_lang_item (LangItem::Kind item_type, location_t locus);
270 : :
271 : : void insert_macro_def (AST::MacroRulesDefinition *macro);
272 : :
273 : : tl::optional<AST::MacroRulesDefinition *> lookup_macro_def (NodeId id);
274 : : tl::optional<CrateNum> lookup_macro_def_crate (NodeId id);
275 : :
276 : : void insert_macro_invocation (AST::MacroInvocation &invoc,
277 : : AST::MacroRulesDefinition *def);
278 : : tl::optional<AST::MacroRulesDefinition *>
279 : : lookup_macro_invocation (AST::MacroInvocation &invoc);
280 : :
281 : : void insert_exported_macro (AST::MacroRulesDefinition &def);
282 : : std::vector<NodeId> &get_exported_macros ();
283 : :
284 : : void insert_derive_proc_macros (CrateNum num,
285 : : std::vector<CustomDeriveProcMacro> macros);
286 : : void insert_bang_proc_macros (CrateNum num,
287 : : std::vector<BangProcMacro> macros);
288 : : void insert_attribute_proc_macros (CrateNum num,
289 : : std::vector<AttributeProcMacro> macros);
290 : :
291 : : tl::optional<std::vector<CustomDeriveProcMacro> &>
292 : : lookup_derive_proc_macros (CrateNum num);
293 : : tl::optional<std::vector<BangProcMacro> &>
294 : : lookup_bang_proc_macros (CrateNum num);
295 : : tl::optional<std::vector<AttributeProcMacro> &>
296 : : lookup_attribute_proc_macros (CrateNum num);
297 : :
298 : : void insert_derive_proc_macro_def (CustomDeriveProcMacro macro);
299 : : void insert_bang_proc_macro_def (BangProcMacro macro);
300 : : void insert_attribute_proc_macro_def (AttributeProcMacro macro);
301 : :
302 : : tl::optional<CustomDeriveProcMacro &>
303 : : lookup_derive_proc_macro_def (NodeId id);
304 : : tl::optional<BangProcMacro &> lookup_bang_proc_macro_def (NodeId id);
305 : : tl::optional<AttributeProcMacro &>
306 : : lookup_attribute_proc_macro_def (NodeId id);
307 : :
308 : : tl::optional<CustomDeriveProcMacro &>
309 : : lookup_derive_proc_macro_invocation (AST::SimplePath &invoc);
310 : : tl::optional<BangProcMacro &>
311 : : lookup_bang_proc_macro_invocation (AST::MacroInvocation &invoc_id);
312 : : tl::optional<AttributeProcMacro &>
313 : : lookup_attribute_proc_macro_invocation (AST::SimplePath &invoc);
314 : : void insert_derive_proc_macro_invocation (AST::SimplePath &invoc,
315 : : CustomDeriveProcMacro def);
316 : : void insert_bang_proc_macro_invocation (AST::MacroInvocation &invoc,
317 : : BangProcMacro def);
318 : : void insert_attribute_proc_macro_invocation (AST::SimplePath &invoc,
319 : : AttributeProcMacro def);
320 : :
321 : : void insert_visibility (NodeId id, Privacy::ModuleVisibility visibility);
322 : : tl::optional<Privacy::ModuleVisibility &> lookup_visibility (NodeId id);
323 : :
324 : : void insert_ast_module (AST::Module *);
325 : : tl::optional<AST::Module *> lookup_ast_module (NodeId id);
326 : : void insert_module_child (NodeId module, NodeId child);
327 : : tl::optional<std::vector<NodeId> &> lookup_module_children (NodeId module);
328 : :
329 : : void insert_module_child_item (NodeId module, Resolver::CanonicalPath item);
330 : : tl::optional<std::vector<Resolver::CanonicalPath> &>
331 : : lookup_module_chidren_items (NodeId module);
332 : : tl::optional<Resolver::CanonicalPath &>
333 : : lookup_module_child (NodeId module, const std::string &item_name);
334 : :
335 : : void insert_child_item_to_parent_module_mapping (NodeId child_item,
336 : : NodeId parent_module);
337 : : tl::optional<NodeId> lookup_parent_module (NodeId child_item);
338 : : bool node_is_module (NodeId query);
339 : :
340 : : void insert_ast_item (AST::Item *item);
341 : : tl::optional<AST::Item *> lookup_ast_item (NodeId id);
342 : :
343 : : HIR::ImplBlock *lookup_builtin_marker ();
344 : :
345 : : tl::optional<HIR::TraitItem *>
346 : : lookup_trait_item_lang_item (LangItem::Kind item, location_t locus);
347 : :
348 : : void insert_auto_trait (HIR::Trait *trait);
349 : : std::vector<HIR::Trait *> &get_auto_traits ();
350 : : void add_capture (NodeId closure, NodeId definition);
351 : : tl::optional<std::vector<NodeId>> lookup_captures (NodeId closure);
352 : :
353 : : private:
354 : : Mappings ();
355 : :
356 : : CrateNum crateNumItr;
357 : : CrateNum currentCrateNum;
358 : : HirId hirIdIter;
359 : : NodeId nodeIdIter;
360 : : std::map<CrateNum, LocalDefId> localIdIter;
361 : : HIR::ImplBlock *builtinMarker;
362 : :
363 : : std::map<NodeId, CrateNum> crate_node_to_crate_num;
364 : : std::map<CrateNum, AST::Crate *> ast_crate_mappings;
365 : : std::map<CrateNum, HIR::Crate *> hir_crate_mappings;
366 : : std::map<DefId, HIR::Item *> defIdMappings;
367 : : std::map<DefId, HIR::TraitItem *> defIdTraitItemMappings;
368 : : std::map<CrateNum, std::map<LocalDefId, HIR::Item *>> localDefIdMappings;
369 : :
370 : : std::map<HirId, HIR::Module *> hirModuleMappings;
371 : : std::map<HirId, HIR::Item *> hirItemMappings;
372 : : std::map<HirId, std::pair<HIR::Enum *, HIR::EnumItem *>> hirEnumItemMappings;
373 : : std::map<HirId, HIR::Type *> hirTypeMappings;
374 : : std::map<HirId, HIR::Expr *> hirExprMappings;
375 : : std::map<HirId, HIR::Stmt *> hirStmtMappings;
376 : : std::map<HirId, HIR::FunctionParam *> hirParamMappings;
377 : : std::map<HirId, HIR::StructExprField *> hirStructFieldMappings;
378 : : std::map<HirId, std::pair<HirId, HIR::ImplItem *>> hirImplItemMappings;
379 : : std::map<HirId, HIR::SelfParam *> hirSelfParamMappings;
380 : : std::map<HirId, HIR::ImplBlock *> hirImplItemsToImplMappings;
381 : : std::map<HirId, HIR::ImplBlock *> hirImplBlockMappings;
382 : : std::map<HirId, HIR::ImplBlock *> hirImplBlockTypeMappings;
383 : : std::map<HirId, HIR::TraitItem *> hirTraitItemMappings;
384 : : std::map<HirId, HIR::ExternBlock *> hirExternBlockMappings;
385 : : std::map<HirId, std::pair<HIR::ExternalItem *, HirId>> hirExternItemMappings;
386 : : std::map<HirId, HIR::PathExprSegment *> hirPathSegMappings;
387 : : std::map<HirId, HIR::GenericParam *> hirGenericParamMappings;
388 : : std::map<HirId, HIR::Trait *> hirTraitItemsToTraitMappings;
389 : : std::map<HirId, HIR::Pattern *> hirPatternMappings;
390 : :
391 : : // FIXME: Add documentation
392 : : std::vector<HIR::Trait *> auto_traits;
393 : :
394 : : // We need to have two maps here, as lang-items need to be used for both AST
395 : : // passes and HIR passes. Thus those two maps are created at different times.
396 : : std::map<LangItem::Kind, DefId> lang_item_mappings;
397 : : std::map<LangItem::Kind, NodeId> lang_item_nodes;
398 : :
399 : : std::map<NodeId, Resolver::CanonicalPath> paths;
400 : : std::map<NodeId, location_t> locations;
401 : : std::map<NodeId, HirId> nodeIdToHirMappings;
402 : : std::map<HirId, NodeId> hirIdToNodeMappings;
403 : :
404 : : // all hirid nodes
405 : : std::map<CrateNum, std::set<HirId>> hirNodesWithinCrate;
406 : :
407 : : // MBE macros
408 : : std::map<NodeId, std::pair<AST::MacroRulesDefinition *, CrateNum>>
409 : : macroMappings;
410 : : std::map<NodeId, AST::MacroRulesDefinition *> macroInvocations;
411 : : std::vector<NodeId> exportedMacros;
412 : :
413 : : // Procedural macros
414 : : std::map<CrateNum, std::vector<CustomDeriveProcMacro>>
415 : : procmacrosDeriveMappings;
416 : : std::map<CrateNum, std::vector<BangProcMacro>> procmacrosBangMappings;
417 : : std::map<CrateNum, std::vector<AttributeProcMacro>>
418 : : procmacrosAttributeMappings;
419 : :
420 : : std::map<NodeId, CustomDeriveProcMacro> procmacroDeriveMappings;
421 : : std::map<NodeId, BangProcMacro> procmacroBangMappings;
422 : : std::map<NodeId, AttributeProcMacro> procmacroAttributeMappings;
423 : : std::map<NodeId, CustomDeriveProcMacro> procmacroDeriveInvocations;
424 : : std::map<NodeId, BangProcMacro> procmacroBangInvocations;
425 : : std::map<NodeId, AttributeProcMacro> procmacroAttributeInvocations;
426 : :
427 : : // crate names
428 : : std::map<CrateNum, std::string> crate_names;
429 : :
430 : : // Low level visibility map for each DefId
431 : : std::map<NodeId, Privacy::ModuleVisibility> visibility_map;
432 : :
433 : : // Module tree maps
434 : :
435 : : // Maps each module's node id to a list of its children
436 : : std::map<NodeId, std::vector<NodeId>> module_child_map;
437 : : std::map<NodeId, std::vector<Resolver::CanonicalPath>> module_child_items;
438 : : std::map<NodeId, NodeId> child_to_parent_module_map;
439 : : std::map<NodeId, AST::Module *> modules;
440 : :
441 : : // AST mappings
442 : : std::map<NodeId, AST::Item *> ast_item_mappings;
443 : :
444 : : // Closure AST NodeId -> vector of Definition node ids
445 : : std::unordered_map<NodeId, std::vector<NodeId>> captures;
446 : : };
447 : :
448 : : } // namespace Analysis
449 : : } // namespace Rust
450 : :
451 : : #endif // RUST_HIR_MAP_H
|