1use std::sync::Arc;
9
10use rustc_ast::visit::{self, AssocCtxt, Visitor, WalkItemKind};
11use rustc_ast::{
12 self as ast, AssocItem, AssocItemKind, Block, ConstItem, Delegation, Fn, ForeignItem,
13 ForeignItemKind, Inline, Item, ItemKind, NodeId, StaticItem, StmtKind, TraitAlias, TyAlias,
14};
15use rustc_attr_parsing::AttributeParser;
16use rustc_expand::base::ResolverExpand;
17use rustc_hir::Attribute;
18use rustc_hir::attrs::{AttributeKind, MacroUseArgs};
19use rustc_hir::def::{self, *};
20use rustc_hir::def_id::{CRATE_DEF_ID, DefId, LocalDefId};
21use rustc_index::bit_set::DenseBitSet;
22use rustc_metadata::creader::LoadedMacro;
23use rustc_middle::metadata::{ModChild, Reexport};
24use rustc_middle::ty::{TyCtxtFeed, Visibility};
25use rustc_middle::{bug, span_bug};
26use rustc_span::hygiene::{ExpnId, LocalExpnId, MacroKind};
27use rustc_span::{Ident, Span, Symbol, kw, sym};
28use thin_vec::ThinVec;
29use tracing::debug;
30
31use crate::Namespace::{MacroNS, TypeNS, ValueNS};
32use crate::def_collector::DefCollector;
33use crate::diagnostics::StructCtor;
34use crate::imports::{ImportData, ImportKind, OnUnknownData};
35use crate::macros::{MacroRulesDecl, MacroRulesScope, MacroRulesScopeRef};
36use crate::ref_mut::CmCell;
37use crate::{
38 BindingKey, Decl, DeclData, DeclKind, ExternModule, ExternPreludeEntry, Finalize, IdentKey,
39 LocalModule, MacroData, Module, ModuleKind, ModuleOrUniformRoot, ParentScope, PathResult, Res,
40 Resolver, Segment, Used, VisResolutionError, errors,
41};
42
43impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
44 pub(crate) fn plant_decl_into_local_module(
47 &mut self,
48 ident: IdentKey,
49 orig_ident_span: Span,
50 ns: Namespace,
51 decl: Decl<'ra>,
52 ) {
53 if let Err(old_decl) =
54 self.try_plant_decl_into_local_module(ident, orig_ident_span, ns, decl, false)
55 {
56 self.report_conflict(ident, ns, old_decl, decl);
57 }
58 }
59
60 fn define_local(
62 &mut self,
63 parent: LocalModule<'ra>,
64 orig_ident: Ident,
65 ns: Namespace,
66 res: Res,
67 vis: Visibility,
68 span: Span,
69 expn_id: LocalExpnId,
70 ) {
71 let decl =
72 self.arenas.new_def_decl(res, vis.to_def_id(), span, expn_id, Some(parent.to_module()));
73 let ident = IdentKey::new(orig_ident);
74 self.plant_decl_into_local_module(ident, orig_ident.span, ns, decl);
75 }
76
77 fn define_extern(
79 &self,
80 parent: ExternModule<'ra>,
81 ident: IdentKey,
82 orig_ident_span: Span,
83 ns: Namespace,
84 child_index: usize,
85 res: Res,
86 vis: Visibility<DefId>,
87 span: Span,
88 expansion: LocalExpnId,
89 ambiguity: Option<Decl<'ra>>,
90 ) {
91 let decl = self.arenas.alloc_decl(DeclData {
92 kind: DeclKind::Def(res),
93 ambiguity: CmCell::new(ambiguity),
94 warn_ambiguity: CmCell::new(true),
96 initial_vis: vis,
97 ambiguity_vis_max: CmCell::new(None),
98 ambiguity_vis_min: CmCell::new(None),
99 span,
100 expansion,
101 parent_module: Some(parent.to_module()),
102 });
103 let key =
107 BindingKey::new_disambiguated(ident, ns, || (child_index + 1).try_into().unwrap()); if self
109 .resolution_or_default(parent.to_module(), key, orig_ident_span)
110 .borrow_mut_unchecked()
111 .non_glob_decl
112 .replace(decl)
113 .is_some()
114 {
115 ::rustc_middle::util::bug::span_bug_fmt(span,
format_args!("an external binding was already defined"));span_bug!(span, "an external binding was already defined");
116 }
117 }
118
119 pub(crate) fn get_nearest_non_block_module(&self, mut def_id: DefId) -> Module<'ra> {
136 loop {
137 match self.get_module(def_id) {
138 Some(module) => return module,
139 None => def_id = self.tcx.parent(def_id),
140 }
141 }
142 }
143
144 pub(crate) fn expect_module(&self, def_id: DefId) -> Module<'ra> {
145 self.get_module(def_id).expect("argument `DefId` is not a module")
146 }
147
148 pub(crate) fn get_module(&self, def_id: DefId) -> Option<Module<'ra>> {
152 match def_id.as_local() {
153 Some(local_def_id) => self.local_module_map.get(&local_def_id).map(|m| m.to_module()),
154 None => {
155 if let module @ Some(..) = self.extern_module_map.borrow().get(&def_id) {
156 return module.map(|m| m.to_module());
157 }
158
159 let def_kind = self.cstore().def_kind_untracked(def_id);
161 if def_kind.is_module_like() {
162 let parent = self.tcx.opt_parent(def_id).map(|parent_id| {
163 self.get_nearest_non_block_module(parent_id).expect_extern()
164 });
165 let expn_id = self.cstore().expn_that_defined_untracked(self.tcx, def_id);
168 let module = self.new_extern_module(
169 parent,
170 ModuleKind::Def(def_kind, def_id, Some(self.tcx.item_name(def_id))),
171 expn_id,
172 self.def_span(def_id),
173 parent.is_some_and(|module| module.no_implicit_prelude),
175 );
176 return Some(module.to_module());
177 }
178
179 None
180 }
181 }
182 }
183
184 pub(crate) fn expn_def_scope(&self, expn_id: ExpnId) -> Module<'ra> {
185 match expn_id.expn_data().macro_def_id {
186 Some(def_id) => self.macro_def_scope(def_id),
187 None => expn_id
188 .as_local()
189 .and_then(|expn_id| self.ast_transform_scopes.get(&expn_id).copied())
190 .unwrap_or(self.graph_root)
191 .to_module(),
192 }
193 }
194
195 pub(crate) fn macro_def_scope(&self, def_id: DefId) -> Module<'ra> {
196 if let Some(id) = def_id.as_local() {
197 self.local_macro_def_scopes[&id].to_module()
198 } else {
199 self.get_nearest_non_block_module(def_id)
200 }
201 }
202
203 pub(crate) fn get_macro(&self, res: Res) -> Option<&'ra MacroData> {
204 match res {
205 Res::Def(DefKind::Macro(..), def_id) => Some(self.get_macro_by_def_id(def_id)),
206 Res::NonMacroAttr(_) => Some(self.non_macro_attr),
207 _ => None,
208 }
209 }
210
211 pub(crate) fn get_macro_by_def_id(&self, def_id: DefId) -> &'ra MacroData {
212 match def_id.as_local() {
214 Some(local_def_id) => self.local_macro_map[&local_def_id],
215 None => *self.extern_macro_map.borrow_mut().entry(def_id).or_insert_with(|| {
216 let loaded_macro = self.cstore().load_macro_untracked(self.tcx, def_id);
217 let macro_data = match loaded_macro {
218 LoadedMacro::MacroDef { def, ident, attrs, span, edition } => {
219 self.compile_macro(&def, ident, &attrs, span, ast::DUMMY_NODE_ID, edition)
220 }
221 LoadedMacro::ProcMacro(ext) => MacroData::new(Arc::new(ext)),
222 };
223
224 self.arenas.alloc_macro(macro_data)
225 }),
226 }
227 }
228
229 pub(crate) fn register_macros_for_all_crates(&mut self) {
232 if !self.all_crate_macros_already_registered {
233 for def_id in self.cstore().all_proc_macro_def_ids(self.tcx) {
234 self.get_macro_by_def_id(def_id);
235 }
236 self.all_crate_macros_already_registered = true;
237 }
238 }
239
240 pub(crate) fn build_reduced_graph_external(&self, module: ExternModule<'ra>) {
241 let def_id = module.def_id();
242 let children = self.tcx.module_children(def_id);
243 for (i, child) in children.iter().enumerate() {
244 self.build_reduced_graph_for_external_crate_res(child, module, i, None)
245 }
246 for (i, child) in
247 self.cstore().ambig_module_children_untracked(self.tcx, def_id).enumerate()
248 {
249 self.build_reduced_graph_for_external_crate_res(
250 &child.main,
251 module,
252 children.len() + i,
253 Some(&child.second),
254 )
255 }
256 }
257
258 fn build_reduced_graph_for_external_crate_res(
260 &self,
261 child: &ModChild,
262 parent: ExternModule<'ra>,
263 child_index: usize,
264 ambig_child: Option<&ModChild>,
265 ) {
266 let child_span = |this: &Self, reexport_chain: &[Reexport], res: def::Res<_>| {
267 this.def_span(
268 reexport_chain
269 .first()
270 .and_then(|reexport| reexport.id())
271 .unwrap_or_else(|| res.def_id()),
272 )
273 };
274 let ModChild { ident: orig_ident, res, vis, ref reexport_chain } = *child;
275 let ident = IdentKey::new(orig_ident);
276 let span = child_span(self, reexport_chain, res);
277 let res = res.expect_non_local();
278 let expansion = LocalExpnId::ROOT;
279 let ambig = ambig_child.map(|ambig_child| {
280 let ModChild { ident: _, res, vis, ref reexport_chain } = *ambig_child;
281 let span = child_span(self, reexport_chain, res);
282 let res = res.expect_non_local();
283 self.arenas.new_def_decl(res, vis, span, expansion, Some(parent.to_module()))
284 });
285
286 let define_extern = |ns| {
288 self.define_extern(
289 parent,
290 ident,
291 orig_ident.span,
292 ns,
293 child_index,
294 res,
295 vis,
296 span,
297 expansion,
298 ambig,
299 )
300 };
301 match res {
302 Res::Def(
303 DefKind::Mod
304 | DefKind::Enum
305 | DefKind::Trait
306 | DefKind::Struct
307 | DefKind::Union
308 | DefKind::Variant
309 | DefKind::TyAlias
310 | DefKind::ForeignTy
311 | DefKind::OpaqueTy
312 | DefKind::TraitAlias
313 | DefKind::AssocTy,
314 _,
315 )
316 | Res::PrimTy(..)
317 | Res::ToolMod => define_extern(TypeNS),
318 Res::Def(
319 DefKind::Fn
320 | DefKind::AssocFn
321 | DefKind::Static { .. }
322 | DefKind::Const { .. }
323 | DefKind::AssocConst { .. }
324 | DefKind::Ctor(..),
325 _,
326 ) => define_extern(ValueNS),
327 Res::Def(DefKind::Macro(..), _) | Res::NonMacroAttr(..) => define_extern(MacroNS),
328 Res::Def(
329 DefKind::TyParam
330 | DefKind::ConstParam
331 | DefKind::ExternCrate
332 | DefKind::Use
333 | DefKind::ForeignMod
334 | DefKind::AnonConst
335 | DefKind::InlineConst
336 | DefKind::Field
337 | DefKind::LifetimeParam
338 | DefKind::GlobalAsm
339 | DefKind::Closure
340 | DefKind::SyntheticCoroutineBody
341 | DefKind::Impl { .. },
342 _,
343 )
344 | Res::Local(..)
345 | Res::SelfTyParam { .. }
346 | Res::SelfTyAlias { .. }
347 | Res::SelfCtor(..)
348 | Res::OpenMod(..)
349 | Res::Err => ::rustc_middle::util::bug::bug_fmt(format_args!("unexpected resolution: {0:?}",
res))bug!("unexpected resolution: {:?}", res),
350 }
351 }
352}
353
354impl<'ra, 'tcx> AsMut<Resolver<'ra, 'tcx>> for DefCollector<'_, 'ra, 'tcx> {
355 fn as_mut(&mut self) -> &mut Resolver<'ra, 'tcx> {
356 self.r
357 }
358}
359
360impl<'a, 'ra, 'tcx> DefCollector<'a, 'ra, 'tcx> {
361 fn res(&self, def_id: impl Into<DefId>) -> Res {
362 let def_id = def_id.into();
363 Res::Def(self.r.tcx.def_kind(def_id), def_id)
364 }
365
366 fn resolve_visibility(&mut self, vis: &ast::Visibility) -> Visibility {
367 self.try_resolve_visibility(vis, true).unwrap_or_else(|err| {
368 self.r.report_vis_error(err);
369 Visibility::Public
370 })
371 }
372
373 fn try_resolve_visibility<'ast>(
374 &mut self,
375 vis: &'ast ast::Visibility,
376 finalize: bool,
377 ) -> Result<Visibility, VisResolutionError<'ast>> {
378 let parent_scope = &self.parent_scope;
379 match vis.kind {
380 ast::VisibilityKind::Public => Ok(Visibility::Public),
381 ast::VisibilityKind::Inherited => {
382 Ok(match self.parent_scope.module.kind {
383 ModuleKind::Def(DefKind::Enum | DefKind::Trait, def_id, _) => {
387 self.r.tcx.visibility(def_id).expect_local()
388 }
389 _ => Visibility::Restricted(
391 self.parent_scope.module.nearest_parent_mod().expect_local(),
392 ),
393 })
394 }
395 ast::VisibilityKind::Restricted { ref path, id, .. } => {
396 let ident = path.segments.get(0).expect("empty path in visibility").ident;
401 let crate_root = if ident.is_path_segment_keyword() {
402 None
403 } else if ident.span.is_rust_2015() {
404 Some(Segment::from_ident(Ident::new(
405 kw::PathRoot,
406 path.span.shrink_to_lo().with_ctxt(ident.span.ctxt()),
407 )))
408 } else {
409 return Err(VisResolutionError::Relative2018(ident.span, path));
410 };
411
412 let segments = crate_root
413 .into_iter()
414 .chain(path.segments.iter().map(|seg| seg.into()))
415 .collect::<Vec<_>>();
416 let expected_found_error = |res| {
417 Err(VisResolutionError::ExpectedFound(
418 path.span,
419 Segment::names_to_string(&segments),
420 res,
421 ))
422 };
423 match self.r.cm().resolve_path(
424 &segments,
425 None,
426 parent_scope,
427 finalize.then(|| Finalize::new(id, path.span)),
428 None,
429 None,
430 ) {
431 PathResult::Module(ModuleOrUniformRoot::Module(module)) => {
432 let res = module.res().expect("visibility resolved to unnamed block");
433 if finalize {
434 self.r.record_partial_res(id, PartialRes::new(res));
435 }
436 if module.is_normal() {
437 match res {
438 Res::Err => Ok(Visibility::Public),
439 _ => {
440 let vis = Visibility::Restricted(res.def_id());
441 if self.r.is_accessible_from(vis, parent_scope.module) {
442 Ok(vis.expect_local())
443 } else {
444 Err(VisResolutionError::AncestorOnly(path.span))
445 }
446 }
447 }
448 } else {
449 expected_found_error(res)
450 }
451 }
452 PathResult::Module(..) => Err(VisResolutionError::ModuleOnly(path.span)),
453 PathResult::NonModule(partial_res) => {
454 expected_found_error(partial_res.expect_full_res())
455 }
456 PathResult::Failed {
457 span, label, suggestion, message, segment_name, ..
458 } => Err(VisResolutionError::FailedToResolve(
459 span,
460 segment_name,
461 label,
462 suggestion,
463 message,
464 )),
465 PathResult::Indeterminate => Err(VisResolutionError::Indeterminate(path.span)),
466 }
467 }
468 }
469 }
470
471 fn insert_field_idents(&mut self, def_id: LocalDefId, fields: &[ast::FieldDef]) {
472 if fields.iter().any(|field| field.is_placeholder) {
473 return;
475 }
476 let field_name = |i, field: &ast::FieldDef| {
477 field.ident.unwrap_or_else(|| Ident::from_str_and_span(&::alloc::__export::must_use({ ::alloc::fmt::format(format_args!("{0}", i)) })format!("{i}"), field.span))
478 };
479 let field_names: Vec<_> =
480 fields.iter().enumerate().map(|(i, field)| field_name(i, field)).collect();
481 let defaults = fields
482 .iter()
483 .enumerate()
484 .filter_map(|(i, field)| field.default.as_ref().map(|_| field_name(i, field).name))
485 .collect();
486 self.r.field_names.insert(def_id, field_names);
487 self.r.field_defaults.insert(def_id, defaults);
488 }
489
490 fn insert_field_visibilities_local(&mut self, def_id: DefId, fields: &[ast::FieldDef]) {
491 let field_vis = fields
492 .iter()
493 .map(|field| field.vis.span.until(field.ident.map_or(field.ty.span, |i| i.span)))
494 .collect();
495 self.r.field_visibility_spans.insert(def_id, field_vis);
496 }
497
498 fn block_needs_anonymous_module(&self, block: &Block) -> bool {
499 block
501 .stmts
502 .iter()
503 .any(|statement| #[allow(non_exhaustive_omitted_patterns)] match statement.kind {
StmtKind::Item(_) | StmtKind::MacCall(_) => true,
_ => false,
}matches!(statement.kind, StmtKind::Item(_) | StmtKind::MacCall(_)))
504 }
505
506 fn add_import(
508 &mut self,
509 module_path: Vec<Segment>,
510 kind: ImportKind<'ra>,
511 span: Span,
512 item: &ast::Item,
513 root_span: Span,
514 root_id: NodeId,
515 vis: Visibility,
516 ) {
517 let current_module = self.parent_scope.module;
518 let import = self.r.arenas.alloc_import(ImportData {
519 kind,
520 parent_scope: self.parent_scope,
521 module_path,
522 imported_module: CmCell::new(None),
523 span,
524 use_span: item.span,
525 use_span_with_attributes: item.span_with_attributes(),
526 has_attributes: !item.attrs.is_empty(),
527 root_span,
528 root_id,
529 vis,
530 vis_span: item.vis.span,
531 on_unknown_attr: OnUnknownData::from_attrs(self.r.tcx, item),
532 });
533
534 self.r.indeterminate_imports.push(import);
535 match import.kind {
536 ImportKind::Single { target, .. } => {
537 if target.name != kw::Underscore {
540 self.r.per_ns(|this, ns| {
541 let key = BindingKey::new(IdentKey::new(target), ns);
542 this.resolution_or_default(current_module, key, target.span)
543 .borrow_mut(this)
544 .single_imports
545 .insert(import);
546 });
547 }
548 }
549 ImportKind::Glob { .. } => current_module.globs.borrow_mut(self.r).push(import),
550 _ => ::core::panicking::panic("internal error: entered unreachable code")unreachable!(),
551 }
552 }
553
554 fn build_reduced_graph_for_use_tree(
555 &mut self,
556 use_tree: &ast::UseTree,
558 id: NodeId,
559 parent_prefix: &[Segment],
560 nested: bool,
561 list_stem: bool,
562 item: &Item,
564 vis: Visibility,
565 root_span: Span,
566 feed: TyCtxtFeed<'tcx, LocalDefId>,
567 ) {
568 {
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("event compiler/rustc_resolve/src/build_reduced_graph.rs:568",
"rustc_resolve::build_reduced_graph",
::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("compiler/rustc_resolve/src/build_reduced_graph.rs"),
::tracing_core::__macro_support::Option::Some(568u32),
::tracing_core::__macro_support::Option::Some("rustc_resolve::build_reduced_graph"),
::tracing_core::field::FieldSet::new(&["message"],
::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::EVENT)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let enabled =
::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{
let interest = __CALLSITE.interest();
!interest.is_never() &&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest)
};
if enabled {
(|value_set: ::tracing::field::ValueSet|
{
let meta = __CALLSITE.metadata();
::tracing::Event::dispatch(meta, &value_set);
;
})({
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
let mut iter = __CALLSITE.metadata().fields().iter();
__CALLSITE.metadata().fields().value_set(&[(&::tracing::__macro_support::Iterator::next(&mut iter).expect("FieldSet corrupted (this is a bug)"),
::tracing::__macro_support::Option::Some(&format_args!("build_reduced_graph_for_use_tree(parent_prefix={0:?}, use_tree={1:?}, nested={2})",
parent_prefix, use_tree, nested) as &dyn Value))])
});
} else { ; }
};debug!(
569 "build_reduced_graph_for_use_tree(parent_prefix={:?}, use_tree={:?}, nested={})",
570 parent_prefix, use_tree, nested
571 );
572
573 if nested && !list_stem {
576 self.r.feed_visibility(feed, vis);
577 }
578
579 let mut prefix_iter = parent_prefix
580 .iter()
581 .cloned()
582 .chain(use_tree.prefix.segments.iter().map(|seg| seg.into()))
583 .peekable();
584
585 let crate_root = match prefix_iter.peek() {
590 Some(seg) if !seg.ident.is_path_segment_keyword() && seg.ident.span.is_rust_2015() => {
591 Some(seg.ident.span.ctxt())
592 }
593 None if let ast::UseTreeKind::Glob(span) = use_tree.kind
594 && span.is_rust_2015() =>
595 {
596 Some(span.ctxt())
597 }
598 _ => None,
599 }
600 .map(|ctxt| {
601 Segment::from_ident(Ident::new(
602 kw::PathRoot,
603 use_tree.prefix.span.shrink_to_lo().with_ctxt(ctxt),
604 ))
605 });
606
607 let prefix = crate_root.into_iter().chain(prefix_iter).collect::<Vec<_>>();
608 {
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("event compiler/rustc_resolve/src/build_reduced_graph.rs:608",
"rustc_resolve::build_reduced_graph",
::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("compiler/rustc_resolve/src/build_reduced_graph.rs"),
::tracing_core::__macro_support::Option::Some(608u32),
::tracing_core::__macro_support::Option::Some("rustc_resolve::build_reduced_graph"),
::tracing_core::field::FieldSet::new(&["message"],
::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::EVENT)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let enabled =
::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{
let interest = __CALLSITE.interest();
!interest.is_never() &&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest)
};
if enabled {
(|value_set: ::tracing::field::ValueSet|
{
let meta = __CALLSITE.metadata();
::tracing::Event::dispatch(meta, &value_set);
;
})({
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
let mut iter = __CALLSITE.metadata().fields().iter();
__CALLSITE.metadata().fields().value_set(&[(&::tracing::__macro_support::Iterator::next(&mut iter).expect("FieldSet corrupted (this is a bug)"),
::tracing::__macro_support::Option::Some(&format_args!("build_reduced_graph_for_use_tree: prefix={0:?}",
prefix) as &dyn Value))])
});
} else { ; }
};debug!("build_reduced_graph_for_use_tree: prefix={:?}", prefix);
609
610 match use_tree.kind {
611 ast::UseTreeKind::Simple(rename) => {
612 let mut module_path = prefix;
613 let source = module_path.pop().unwrap();
614
615 let ident = if source.ident.name == kw::SelfLower
618 && rename.is_none()
619 && let Some(parent) = module_path.last()
620 {
621 Ident::new(parent.ident.name, source.ident.span)
622 } else {
623 use_tree.ident()
624 };
625
626 match source.ident.name {
627 kw::DollarCrate => {
628 if !module_path.is_empty() {
629 self.r.dcx().span_err(
630 source.ident.span,
631 "`$crate` in paths can only be used in start position",
632 );
633 return;
634 }
635 }
636 kw::Crate => {
637 if !module_path.is_empty() {
638 self.r.dcx().span_err(
639 source.ident.span,
640 "`crate` in paths can only be used in start position",
641 );
642 return;
643 }
644 }
645 kw::Super => {
646 let valid_prefix = module_path.iter().enumerate().all(|(i, seg)| {
649 let name = seg.ident.name;
650 name == kw::Super || (name == kw::SelfLower && i == 0)
651 });
652
653 if !valid_prefix {
654 self.r.dcx().span_err(
655 source.ident.span,
656 "`super` in paths can only be used in start position, after `self`, or after another `super`",
657 );
658 return;
659 }
660 }
661 kw::SelfLower
663 if let Some(parent) = module_path.last()
664 && parent.ident.name == kw::PathRoot
665 && !self.r.path_root_is_crate_root(parent.ident) =>
666 {
667 self.r.dcx().span_err(use_tree.span(), "extern prelude cannot be imported");
668 return;
669 }
670 _ => (),
671 }
672
673 if let Some(parent) = module_path.last()
676 && parent.ident.name == kw::SelfLower
677 && module_path.len() > 1
678 {
679 self.r.dcx().span_err(
680 parent.ident.span,
681 "`self` in paths can only be used in start position or last position",
682 );
683 return;
684 }
685
686 if rename.is_none() && ident.is_path_segment_keyword() {
688 let ident = use_tree.ident();
689 self.r.dcx().emit_err(errors::UnnamedImport {
690 span: ident.span,
691 sugg: errors::UnnamedImportSugg { span: ident.span, ident },
692 });
693 return;
694 }
695
696 let kind = ImportKind::Single {
697 source: source.ident,
698 target: ident,
699 decls: Default::default(),
700 nested,
701 id,
702 };
703
704 self.add_import(module_path, kind, use_tree.span(), item, root_span, item.id, vis);
705 }
706 ast::UseTreeKind::Glob(_) => {
707 if !ast::attr::contains_name(&item.attrs, sym::prelude_import) {
708 let kind = ImportKind::Glob { max_vis: CmCell::new(None), id };
709 self.add_import(prefix, kind, use_tree.span(), item, root_span, item.id, vis);
710 } else {
711 let path_res =
713 self.r.cm().maybe_resolve_path(&prefix, None, &self.parent_scope, None);
714 if let PathResult::Module(ModuleOrUniformRoot::Module(module)) = path_res {
715 self.r.prelude = Some(module);
716 } else {
717 self.r.dcx().span_err(use_tree.span(), "cannot resolve a prelude import");
718 }
719 }
720 }
721 ast::UseTreeKind::Nested { ref items, .. } => {
722 for &(ref tree, id) in items {
723 let feed = self.create_def(id, None, DefKind::Use, use_tree.span());
724 self.build_reduced_graph_for_use_tree(
725 tree, id, &prefix, true, false, item, vis, root_span, feed,
728 );
729 }
730
731 if items.is_empty()
735 && !prefix.is_empty()
736 && (prefix.len() > 1 || prefix[0].ident.name != kw::PathRoot)
737 {
738 let new_span = prefix[prefix.len() - 1].ident.span;
739 let tree = ast::UseTree {
740 prefix: ast::Path::from_ident(Ident::new(kw::SelfLower, new_span)),
741 kind: ast::UseTreeKind::Simple(Some(Ident::new(kw::Underscore, new_span))),
742 };
743 self.build_reduced_graph_for_use_tree(
744 &tree,
746 id,
747 &prefix,
748 true,
749 true,
750 item,
752 Visibility::Restricted(
753 self.parent_scope.module.nearest_parent_mod().expect_local(),
754 ),
755 root_span,
756 feed,
757 );
758 }
759 }
760 }
761 }
762
763 fn build_reduced_graph_for_struct_variant(
764 &mut self,
765 fields: &[ast::FieldDef],
766 ident: Ident,
767 feed: TyCtxtFeed<'tcx, LocalDefId>,
768 adt_res: Res,
769 adt_vis: Visibility,
770 adt_span: Span,
771 ) {
772 let parent_scope = &self.parent_scope;
773 let parent = parent_scope.module.expect_local();
774 let expansion = parent_scope.expansion;
775
776 self.r.define_local(parent, ident, TypeNS, adt_res, adt_vis, adt_span, expansion);
778 self.r.feed_visibility(feed, adt_vis);
779 let def_id = feed.key();
780
781 self.insert_field_idents(def_id, fields);
783 self.insert_field_visibilities_local(def_id.to_def_id(), fields);
784 }
785
786 fn build_reduced_graph_for_item(&mut self, item: &'a Item, feed: TyCtxtFeed<'tcx, LocalDefId>) {
788 let parent_scope = &self.parent_scope;
789 let parent = parent_scope.module.expect_local();
790 let expansion = parent_scope.expansion;
791 let sp = item.span;
792 let vis = self.resolve_visibility(&item.vis);
793 let local_def_id = feed.key();
794 let def_id = local_def_id.to_def_id();
795 let def_kind = self.r.tcx.def_kind(def_id);
796 let res = Res::Def(def_kind, def_id);
797
798 self.r.feed_visibility(feed, vis);
799
800 match item.kind {
801 ItemKind::Use(ref use_tree) => {
802 self.build_reduced_graph_for_use_tree(
803 use_tree,
805 item.id,
806 &[],
807 false,
808 false,
809 item,
811 vis,
812 use_tree.span(),
813 feed,
814 );
815 }
816
817 ItemKind::ExternCrate(orig_name, ident) => {
818 self.build_reduced_graph_for_extern_crate(
819 orig_name,
820 item,
821 ident,
822 local_def_id,
823 vis,
824 );
825 }
826
827 ItemKind::Mod(_, ident, ref mod_kind) => {
828 self.r.define_local(parent, ident, TypeNS, res, vis, sp, expansion);
829
830 if let ast::ModKind::Loaded(_, Inline::No { had_parse_error: Err(_) }, _) = mod_kind
831 {
832 self.r.mods_with_parse_errors.insert(def_id);
833 }
834 let module = self.r.new_local_module(
835 Some(parent),
836 ModuleKind::Def(def_kind, def_id, Some(ident.name)),
837 expansion.to_expn_id(),
838 item.span,
839 parent.no_implicit_prelude
840 || ast::attr::contains_name(&item.attrs, sym::no_implicit_prelude),
841 );
842 self.parent_scope.module = module.to_module();
843 }
844
845 ItemKind::Const(box ConstItem { ident, .. })
847 | ItemKind::Delegation(box Delegation { ident, .. })
848 | ItemKind::Static(box StaticItem { ident, .. }) => {
849 self.r.define_local(parent, ident, ValueNS, res, vis, sp, expansion);
850 }
851 ItemKind::Fn(box Fn { ident, .. }) => {
852 self.r.define_local(parent, ident, ValueNS, res, vis, sp, expansion);
853
854 self.define_macro(item, feed);
857 }
858
859 ItemKind::TyAlias(box TyAlias { ident, .. })
861 | ItemKind::TraitAlias(box TraitAlias { ident, .. }) => {
862 self.r.define_local(parent, ident, TypeNS, res, vis, sp, expansion);
863 }
864
865 ItemKind::Enum(ident, _, _) | ItemKind::Trait(box ast::Trait { ident, .. }) => {
866 self.r.define_local(parent, ident, TypeNS, res, vis, sp, expansion);
867
868 let module = self.r.new_local_module(
869 Some(parent),
870 ModuleKind::Def(def_kind, def_id, Some(ident.name)),
871 expansion.to_expn_id(),
872 item.span,
873 parent.no_implicit_prelude,
874 );
875 self.parent_scope.module = module.to_module();
876 }
877
878 ItemKind::Struct(ident, ref generics, ref vdata) => {
880 self.build_reduced_graph_for_struct_variant(
881 vdata.fields(),
882 ident,
883 feed,
884 res,
885 vis,
886 sp,
887 );
888
889 if let Some((ctor_kind, ctor_node_id)) = CtorKind::from_ast(vdata) {
892 let mut ctor_vis = if vis.is_public()
895 && ast::attr::contains_name(&item.attrs, sym::non_exhaustive)
896 {
897 Visibility::Restricted(CRATE_DEF_ID)
898 } else {
899 vis
900 };
901
902 let mut field_visibilities = Vec::with_capacity(vdata.fields().len());
903
904 for field in vdata.fields() {
905 let field_vis = self
909 .try_resolve_visibility(&field.vis, false)
910 .unwrap_or(Visibility::Public);
911 if ctor_vis.greater_than(field_vis, self.r.tcx) {
912 ctor_vis = field_vis;
913 }
914 field_visibilities.push(field_vis.to_def_id());
915 }
916 let feed = self.create_def(
918 ctor_node_id,
919 None,
920 DefKind::Ctor(CtorOf::Struct, ctor_kind),
921 item.span,
922 );
923
924 let ctor_def_id = feed.key();
925 let ctor_res = self.res(ctor_def_id);
926 self.r.define_local(parent, ident, ValueNS, ctor_res, ctor_vis, sp, expansion);
927 self.r.feed_visibility(feed, ctor_vis);
928 self.insert_field_visibilities_local(ctor_def_id.to_def_id(), vdata.fields());
930
931 let ctor =
932 StructCtor { res: ctor_res, vis: ctor_vis.to_def_id(), field_visibilities };
933 self.r.struct_ctors.insert(local_def_id, ctor);
934 }
935 self.r.struct_generics.insert(local_def_id, generics.clone());
936 }
937
938 ItemKind::Union(ident, _, ref vdata) => {
939 self.build_reduced_graph_for_struct_variant(
940 vdata.fields(),
941 ident,
942 feed,
943 res,
944 vis,
945 sp,
946 );
947 }
948
949 ItemKind::Impl { .. }
951 | ItemKind::ForeignMod(..)
952 | ItemKind::GlobalAsm(..)
953 | ItemKind::ConstBlock(..) => {}
954
955 ItemKind::MacroDef(..) | ItemKind::MacCall(_) | ItemKind::DelegationMac(..) => {
956 ::core::panicking::panic("internal error: entered unreachable code")unreachable!()
957 }
958 }
959 }
960
961 fn build_reduced_graph_for_extern_crate(
962 &mut self,
963 orig_name: Option<Symbol>,
964 item: &Item,
965 orig_ident: Ident,
966 local_def_id: LocalDefId,
967 vis: Visibility,
968 ) {
969 let sp = item.span;
970 let parent_scope = self.parent_scope;
971 let parent = parent_scope.module;
972 let expansion = parent_scope.expansion;
973
974 let (used, module, decl) = if orig_name.is_none() && orig_ident.name == kw::SelfLower {
975 self.r.dcx().emit_err(errors::ExternCrateSelfRequiresRenaming { span: sp });
976 return;
977 } else if orig_name == Some(kw::SelfLower) {
978 Some(self.r.graph_root.to_module())
979 } else {
980 let tcx = self.r.tcx;
981 let crate_id = self.r.cstore_mut().process_extern_crate(
982 self.r.tcx,
983 item,
984 local_def_id,
985 &tcx.definitions_untracked(),
986 );
987 crate_id.map(|crate_id| {
988 self.r.extern_crate_map.insert(local_def_id, crate_id);
989 self.r.expect_module(crate_id.as_def_id())
990 })
991 }
992 .map(|module| {
993 let used = self.process_macro_use_imports(item, module);
994 let decl = self.r.arenas.new_pub_def_decl(module.res().unwrap(), sp, expansion);
995 (used, Some(ModuleOrUniformRoot::Module(module)), decl)
996 })
997 .unwrap_or((true, None, self.r.dummy_decl));
998 let import = self.r.arenas.alloc_import(ImportData {
999 kind: ImportKind::ExternCrate { source: orig_name, target: orig_ident, id: item.id },
1000 root_id: item.id,
1001 parent_scope,
1002 imported_module: CmCell::new(module),
1003 has_attributes: !item.attrs.is_empty(),
1004 use_span_with_attributes: item.span_with_attributes(),
1005 use_span: item.span,
1006 root_span: item.span,
1007 span: item.span,
1008 module_path: Vec::new(),
1009 vis,
1010 vis_span: item.vis.span,
1011 on_unknown_attr: OnUnknownData::from_attrs(self.r.tcx, item),
1012 });
1013 if used {
1014 self.r.import_use_map.insert(import, Used::Other);
1015 }
1016 self.r.potentially_unused_imports.push(import);
1017 let import_decl = self.r.new_import_decl(decl, import);
1018 let ident = IdentKey::new(orig_ident);
1019 if ident.name != kw::Underscore && parent == self.r.graph_root.to_module() {
1020 if let Some(entry) = self.r.extern_prelude.get(&ident)
1023 && expansion != LocalExpnId::ROOT
1024 && orig_name.is_some()
1025 && entry.item_decl.is_none()
1026 {
1027 self.r.dcx().emit_err(
1028 errors::MacroExpandedExternCrateCannotShadowExternArguments { span: item.span },
1029 );
1030 }
1031
1032 use indexmap::map::Entry;
1033 match self.r.extern_prelude.entry(ident) {
1034 Entry::Occupied(mut occupied) => {
1035 let entry = occupied.get_mut();
1036 if entry.item_decl.is_some() {
1037 let msg = ::alloc::__export::must_use({
::alloc::fmt::format(format_args!("extern crate `{0}` already in extern prelude",
orig_ident))
})format!("extern crate `{orig_ident}` already in extern prelude");
1038 self.r.tcx.dcx().span_delayed_bug(item.span, msg);
1039 } else {
1040 entry.item_decl = Some((import_decl, orig_ident.span, orig_name.is_some()));
1041 }
1042 entry
1043 }
1044 Entry::Vacant(vacant) => vacant.insert(ExternPreludeEntry {
1045 item_decl: Some((import_decl, orig_ident.span, true)),
1046 flag_decl: None,
1047 }),
1048 };
1049 }
1050 self.r.plant_decl_into_local_module(ident, orig_ident.span, TypeNS, import_decl);
1051 }
1052
1053 pub(crate) fn build_reduced_graph_for_foreign_item(
1055 &mut self,
1056 item: &ForeignItem,
1057 ident: Ident,
1058 feed: TyCtxtFeed<'tcx, LocalDefId>,
1059 ) {
1060 let local_def_id = feed.key();
1061 let def_id = local_def_id.to_def_id();
1062 let ns = match item.kind {
1063 ForeignItemKind::Fn(..) => ValueNS,
1064 ForeignItemKind::Static(..) => ValueNS,
1065 ForeignItemKind::TyAlias(..) => TypeNS,
1066 ForeignItemKind::MacCall(..) => ::core::panicking::panic("internal error: entered unreachable code")unreachable!(),
1067 };
1068 let parent = self.parent_scope.module.expect_local();
1069 let expansion = self.parent_scope.expansion;
1070 let vis = self.resolve_visibility(&item.vis);
1071 self.r.define_local(parent, ident, ns, self.res(def_id), vis, item.span, expansion);
1072 self.r.feed_visibility(feed, vis);
1073 }
1074
1075 fn build_reduced_graph_for_block(&mut self, block: &Block) {
1076 let parent = self.parent_scope.module.expect_local();
1077 let expansion = self.parent_scope.expansion;
1078 if self.block_needs_anonymous_module(block) {
1079 let module = self.r.new_local_module(
1080 Some(parent),
1081 ModuleKind::Block,
1082 expansion.to_expn_id(),
1083 block.span,
1084 parent.no_implicit_prelude,
1085 );
1086 self.r.block_map.insert(block.id, module);
1087 self.parent_scope.module = module.to_module(); }
1089 }
1090
1091 fn add_macro_use_decl(
1092 &mut self,
1093 name: Symbol,
1094 decl: Decl<'ra>,
1095 span: Span,
1096 allow_shadowing: bool,
1097 ) {
1098 if self.r.macro_use_prelude.insert(name, decl).is_some() && !allow_shadowing {
1099 self.r.dcx().emit_err(errors::MacroUseNameAlreadyInUse { span, name });
1100 }
1101 }
1102
1103 fn process_macro_use_imports(&mut self, item: &Item, module: Module<'ra>) -> bool {
1105 let mut import_all = None;
1106 let mut single_imports = ThinVec::new();
1107 if let Some(Attribute::Parsed(AttributeKind::MacroUse { span, arguments })) =
1108 AttributeParser::parse_limited(self.r.tcx.sess, &item.attrs, &[sym::macro_use])
1109 {
1110 if self.parent_scope.module.parent.is_some() {
1111 self.r
1112 .dcx()
1113 .emit_err(errors::ExternCrateLoadingMacroNotAtCrateRoot { span: item.span });
1114 }
1115 if let ItemKind::ExternCrate(Some(orig_name), _) = item.kind
1116 && orig_name == kw::SelfLower
1117 {
1118 self.r.dcx().emit_err(errors::MacroUseExternCrateSelf { span });
1119 }
1120
1121 match arguments {
1122 MacroUseArgs::UseAll => import_all = Some(span),
1123 MacroUseArgs::UseSpecific(imports) => single_imports = imports,
1124 }
1125 }
1126
1127 let macro_use_import = |this: &Self, span, warn_private| {
1128 this.r.arenas.alloc_import(ImportData {
1129 kind: ImportKind::MacroUse { warn_private },
1130 root_id: item.id,
1131 parent_scope: this.parent_scope,
1132 imported_module: CmCell::new(Some(ModuleOrUniformRoot::Module(module))),
1133 use_span_with_attributes: item.span_with_attributes(),
1134 has_attributes: !item.attrs.is_empty(),
1135 use_span: item.span,
1136 root_span: span,
1137 span,
1138 module_path: Vec::new(),
1139 vis: Visibility::Restricted(CRATE_DEF_ID),
1140 vis_span: item.vis.span,
1141 on_unknown_attr: OnUnknownData::from_attrs(this.r.tcx, item),
1142 })
1143 };
1144
1145 let allow_shadowing = self.parent_scope.expansion == LocalExpnId::ROOT;
1146 if let Some(span) = import_all {
1147 let import = macro_use_import(self, span, false);
1148 self.r.potentially_unused_imports.push(import);
1149 module.for_each_child_mut(self, |this, ident, _, ns, binding| {
1150 if ns == MacroNS {
1151 let import =
1152 if this.r.is_accessible_from(binding.vis(), this.parent_scope.module) {
1153 import
1154 } else {
1155 if this.r.macro_use_prelude.contains_key(&ident.name) {
1158 return;
1160 }
1161 macro_use_import(this, span, true)
1162 };
1163 let import_decl = this.r.new_import_decl(binding, import);
1164 this.add_macro_use_decl(ident.name, import_decl, span, allow_shadowing);
1165 }
1166 });
1167 } else {
1168 for ident in single_imports.iter().cloned() {
1169 let result = self.r.cm().maybe_resolve_ident_in_module(
1170 ModuleOrUniformRoot::Module(module),
1171 ident,
1172 MacroNS,
1173 &self.parent_scope,
1174 None,
1175 );
1176 if let Ok(binding) = result {
1177 let import = macro_use_import(self, ident.span, false);
1178 self.r.potentially_unused_imports.push(import);
1179 let import_decl = self.r.new_import_decl(binding, import);
1180 self.add_macro_use_decl(ident.name, import_decl, ident.span, allow_shadowing);
1181 } else {
1182 self.r.dcx().emit_err(errors::ImportedMacroNotFound { span: ident.span });
1183 }
1184 }
1185 }
1186 import_all.is_some() || !single_imports.is_empty()
1187 }
1188
1189 pub(crate) fn contains_macro_use(&self, attrs: &[ast::Attribute]) -> bool {
1191 for attr in attrs {
1192 if attr.has_name(sym::macro_escape) {
1193 let inner_attribute = #[allow(non_exhaustive_omitted_patterns)] match attr.style {
ast::AttrStyle::Inner => true,
_ => false,
}matches!(attr.style, ast::AttrStyle::Inner);
1194 self.r
1195 .dcx()
1196 .emit_warn(errors::MacroExternDeprecated { span: attr.span, inner_attribute });
1197 } else if !attr.has_name(sym::macro_use) {
1198 continue;
1199 }
1200
1201 if !attr.is_word() {
1202 self.r.dcx().emit_err(errors::ArgumentsMacroUseNotAllowed { span: attr.span });
1203 }
1204 return true;
1205 }
1206
1207 false
1208 }
1209
1210 pub(crate) fn visit_invoc(&mut self, id: NodeId) -> LocalExpnId {
1211 let invoc_id = id.placeholder_to_expn_id();
1212 let old_parent_scope = self.r.invocation_parent_scopes.insert(invoc_id, self.parent_scope);
1213 if !old_parent_scope.is_none() {
{
::core::panicking::panic_fmt(format_args!("invocation data is reset for an invocation"));
}
};assert!(old_parent_scope.is_none(), "invocation data is reset for an invocation");
1214 invoc_id
1215 }
1216
1217 pub(crate) fn visit_invoc_in_module(&mut self, id: NodeId) -> MacroRulesScopeRef<'ra> {
1220 let invoc_id = self.visit_invoc(id);
1221 self.parent_scope.module.unexpanded_invocations.borrow_mut(self.r).insert(invoc_id);
1222 self.r.arenas.alloc_macro_rules_scope(MacroRulesScope::Invocation(invoc_id))
1223 }
1224
1225 fn proc_macro_stub(
1226 &self,
1227 item: &ast::Item,
1228 fn_ident: Ident,
1229 ) -> Option<(MacroKind, Ident, Span)> {
1230 if ast::attr::contains_name(&item.attrs, sym::proc_macro) {
1231 return Some((MacroKind::Bang, fn_ident, item.span));
1232 } else if ast::attr::contains_name(&item.attrs, sym::proc_macro_attribute) {
1233 return Some((MacroKind::Attr, fn_ident, item.span));
1234 } else if let Some(attr) = ast::attr::find_by_name(&item.attrs, sym::proc_macro_derive)
1235 && let Some(meta_item_inner) =
1236 attr.meta_item_list().and_then(|list| list.get(0).cloned())
1237 && let Some(ident) = meta_item_inner.ident()
1238 {
1239 return Some((MacroKind::Derive, ident, ident.span));
1240 }
1241 None
1242 }
1243
1244 fn insert_unused_macro(&mut self, ident: Ident, def_id: LocalDefId, node_id: NodeId) {
1248 if !ident.as_str().starts_with('_') {
1249 self.r.unused_macros.insert(def_id, (node_id, ident));
1250 let nrules = self.r.local_macro_map[&def_id].nrules;
1251 self.r.unused_macro_rules.insert(node_id, DenseBitSet::new_filled(nrules));
1252 }
1253 }
1254
1255 fn define_macro(
1256 &mut self,
1257 item: &ast::Item,
1258 feed: TyCtxtFeed<'tcx, LocalDefId>,
1259 ) -> MacroRulesScopeRef<'ra> {
1260 let parent_scope = self.parent_scope;
1261 let expansion = parent_scope.expansion;
1262 let def_id = feed.key();
1263 let (res, orig_ident, span, macro_rules) = match &item.kind {
1264 ItemKind::MacroDef(ident, def) => {
1265 (self.res(def_id), *ident, item.span, def.macro_rules)
1266 }
1267 ItemKind::Fn(box ast::Fn { ident: fn_ident, .. }) => {
1268 match self.proc_macro_stub(item, *fn_ident) {
1269 Some((macro_kind, ident, span)) => {
1270 let macro_kinds = macro_kind.into();
1271 let res = Res::Def(DefKind::Macro(macro_kinds), def_id.to_def_id());
1272 let macro_data = MacroData::new(self.r.dummy_ext(macro_kind));
1273 self.r.new_local_macro(def_id, macro_data);
1274 self.r.proc_macro_stubs.insert(def_id);
1275 (res, ident, span, false)
1276 }
1277 None => return parent_scope.macro_rules,
1278 }
1279 }
1280 _ => ::core::panicking::panic("internal error: entered unreachable code")unreachable!(),
1281 };
1282
1283 self.r.local_macro_def_scopes.insert(def_id, parent_scope.module.expect_local());
1284
1285 if macro_rules {
1286 let ident = IdentKey::new(orig_ident);
1287 self.r.macro_names.insert(ident);
1288 let is_macro_export = ast::attr::contains_name(&item.attrs, sym::macro_export);
1289 let vis = if is_macro_export {
1290 Visibility::Public
1291 } else {
1292 Visibility::Restricted(CRATE_DEF_ID)
1293 };
1294 let decl = self.r.arenas.new_def_decl(
1295 res,
1296 vis.to_def_id(),
1297 span,
1298 expansion,
1299 Some(parent_scope.module),
1300 );
1301 self.r.all_macro_rules.insert(ident.name);
1302 if is_macro_export {
1303 let import = self.r.arenas.alloc_import(ImportData {
1304 kind: ImportKind::MacroExport,
1305 root_id: item.id,
1306 parent_scope: ParentScope {
1307 module: self.r.graph_root.to_module(),
1308 ..parent_scope
1309 },
1310 imported_module: CmCell::new(None),
1311 has_attributes: false,
1312 use_span_with_attributes: span,
1313 use_span: span,
1314 root_span: span,
1315 span,
1316 module_path: Vec::new(),
1317 vis,
1318 vis_span: item.vis.span,
1319 on_unknown_attr: OnUnknownData::from_attrs(self.r.tcx, item),
1320 });
1321 self.r.import_use_map.insert(import, Used::Other);
1322 let import_decl = self.r.new_import_decl(decl, import);
1323 self.r.plant_decl_into_local_module(ident, orig_ident.span, MacroNS, import_decl);
1324 } else {
1325 self.r.check_reserved_macro_name(ident.name, orig_ident.span, res);
1326 self.insert_unused_macro(orig_ident, def_id, item.id);
1327 }
1328 self.r.feed_visibility(feed, vis);
1329 let scope = self.r.arenas.alloc_macro_rules_scope(MacroRulesScope::Def(
1330 self.r.arenas.alloc_macro_rules_decl(MacroRulesDecl {
1331 parent_macro_rules_scope: parent_scope.macro_rules,
1332 decl,
1333 ident,
1334 orig_ident_span: orig_ident.span,
1335 }),
1336 ));
1337 self.r.macro_rules_scopes.insert(def_id, scope);
1338 scope
1339 } else {
1340 let module = parent_scope.module.expect_local();
1341 let vis = match item.kind {
1342 ItemKind::Fn(..) => {
1345 self.try_resolve_visibility(&item.vis, false).unwrap_or(Visibility::Public)
1346 }
1347 _ => self.resolve_visibility(&item.vis),
1348 };
1349 if !vis.is_public() {
1350 self.insert_unused_macro(orig_ident, def_id, item.id);
1351 }
1352 self.r.define_local(module, orig_ident, MacroNS, res, vis, span, expansion);
1353 self.r.feed_visibility(feed, vis);
1354 self.parent_scope.macro_rules
1355 }
1356 }
1357}
1358
1359impl<'a, 'ra, 'tcx> DefCollector<'a, 'ra, 'tcx> {
1360 pub(crate) fn brg_visit_item(&mut self, item: &'a Item, feed: TyCtxtFeed<'tcx, LocalDefId>) {
1361 let orig_module_scope = self.parent_scope.module;
1362 self.parent_scope.macro_rules = match item.kind {
1363 ItemKind::MacroDef(..) => {
1364 let macro_rules_scope = self.define_macro(item, feed);
1365 visit::walk_item(self, item);
1366 macro_rules_scope
1367 }
1368 _ => {
1369 let orig_macro_rules_scope = self.parent_scope.macro_rules;
1370 self.build_reduced_graph_for_item(item, feed);
1371 match item.kind {
1372 ItemKind::Mod(..) => {
1373 self.visit_vis(&item.vis);
1376 item.kind.walk(&item.attrs, item.span, item.id, &item.vis, (), self);
1377 for elem in &item.attrs {
match ::rustc_ast_ir::visit::VisitorResult::branch(self.visit_attribute(elem))
{
core::ops::ControlFlow::Continue(()) =>
(),
#[allow(unreachable_code)]
core::ops::ControlFlow::Break(r) => {
return ::rustc_ast_ir::visit::VisitorResult::from_residual(r);
}
};
};visit::walk_list!(self, visit_attribute, &item.attrs);
1378 }
1379 _ => visit::walk_item(self, item),
1380 }
1381 match item.kind {
1382 ItemKind::Mod(..) if self.contains_macro_use(&item.attrs) => {
1383 self.parent_scope.macro_rules
1384 }
1385 _ => orig_macro_rules_scope,
1386 }
1387 }
1388 };
1389 self.parent_scope.module = orig_module_scope;
1390 }
1391
1392 pub(crate) fn brg_visit_mac_call_in_module(&mut self, id: NodeId) {
1395 self.parent_scope.macro_rules = self.visit_invoc_in_module(id);
1396 }
1397
1398 pub(crate) fn brg_visit_block(&mut self, block: &'a Block) {
1399 let orig_current_module = self.parent_scope.module;
1400 let orig_current_macro_rules_scope = self.parent_scope.macro_rules;
1401 self.build_reduced_graph_for_block(block);
1402 visit::walk_block(self, block);
1403 self.parent_scope.module = orig_current_module;
1404 self.parent_scope.macro_rules = orig_current_macro_rules_scope;
1405 }
1406
1407 pub(crate) fn brg_visit_assoc_item(
1408 &mut self,
1409 item: &'a AssocItem,
1410 ctxt: AssocCtxt,
1411 ident: Ident,
1412 ns: Namespace,
1413 feed: TyCtxtFeed<'tcx, LocalDefId>,
1414 ) {
1415 let vis = self.resolve_visibility(&item.vis);
1416 let local_def_id = feed.key();
1417 let def_id = local_def_id.to_def_id();
1418
1419 if !(#[allow(non_exhaustive_omitted_patterns)] match ctxt {
AssocCtxt::Impl { of_trait: true } => true,
_ => false,
}matches!(ctxt, AssocCtxt::Impl { of_trait: true })
1420 && #[allow(non_exhaustive_omitted_patterns)] match item.vis.kind {
ast::VisibilityKind::Inherited => true,
_ => false,
}matches!(item.vis.kind, ast::VisibilityKind::Inherited))
1421 {
1422 self.r.feed_visibility(feed, vis);
1426 }
1427
1428 if ctxt == AssocCtxt::Trait {
1429 let parent = self.parent_scope.module.expect_local();
1430 let expansion = self.parent_scope.expansion;
1431 self.r.define_local(parent, ident, ns, self.res(def_id), vis, item.span, expansion);
1432 } else if !#[allow(non_exhaustive_omitted_patterns)] match &item.kind {
AssocItemKind::Delegation(deleg) if deleg.from_glob => true,
_ => false,
}matches!(&item.kind, AssocItemKind::Delegation(deleg) if deleg.from_glob)
1433 && ident.name != kw::Underscore
1434 {
1435 let impl_def_id = self.r.tcx.local_parent(local_def_id);
1437 let key = BindingKey::new(IdentKey::new(ident), ns);
1438 self.r.impl_binding_keys.entry(impl_def_id).or_default().insert(key);
1439 }
1440
1441 visit::walk_assoc_item(self, item, ctxt);
1442 }
1443
1444 pub(crate) fn visit_assoc_item_mac_call(
1445 &mut self,
1446 item: &'a Item<AssocItemKind>,
1447 ctxt: AssocCtxt,
1448 ) {
1449 match ctxt {
1450 AssocCtxt::Trait => {
1451 self.visit_invoc_in_module(item.id);
1452 }
1453 AssocCtxt::Impl { .. } => {
1454 let invoc_id = item.id.placeholder_to_expn_id();
1455 if !self.r.glob_delegation_invoc_ids.contains(&invoc_id) {
1456 self.r
1457 .impl_unexpanded_invocations
1458 .entry(self.r.invocation_parent(invoc_id))
1459 .or_default()
1460 .insert(invoc_id);
1461 }
1462 self.visit_invoc(item.id);
1463 }
1464 }
1465 }
1466
1467 pub(crate) fn brg_visit_field_def(
1468 &mut self,
1469 sf: &'a ast::FieldDef,
1470 feed: TyCtxtFeed<'tcx, LocalDefId>,
1471 ) {
1472 let vis = self.resolve_visibility(&sf.vis);
1473 self.r.feed_visibility(feed, vis);
1474 visit::walk_field_def(self, sf);
1475 }
1476
1477 pub(crate) fn brg_visit_variant(
1480 &mut self,
1481 variant: &'a ast::Variant,
1482 feed: TyCtxtFeed<'tcx, LocalDefId>,
1483 ) {
1484 let parent = self.parent_scope.module.expect_local();
1485 let expn_id = self.parent_scope.expansion;
1486 let ident = variant.ident;
1487
1488 let def_id = feed.key();
1490 let vis = self.resolve_visibility(&variant.vis);
1491 self.r.define_local(parent, ident, TypeNS, self.res(def_id), vis, variant.span, expn_id);
1492 self.r.feed_visibility(feed, vis);
1493
1494 let ctor_vis =
1496 if vis.is_public() && ast::attr::contains_name(&variant.attrs, sym::non_exhaustive) {
1497 Visibility::Restricted(CRATE_DEF_ID)
1498 } else {
1499 vis
1500 };
1501
1502 if let Some((ctor_kind, ctor_node_id)) = CtorKind::from_ast(&variant.data) {
1504 let feed = self.create_def(
1505 ctor_node_id,
1506 None,
1507 DefKind::Ctor(CtorOf::Variant, ctor_kind),
1508 variant.span,
1509 );
1510 let ctor_def_id = feed.key();
1511 let ctor_res = self.res(ctor_def_id);
1512 self.r.define_local(parent, ident, ValueNS, ctor_res, ctor_vis, variant.span, expn_id);
1513 self.r.feed_visibility(feed, ctor_vis);
1514 }
1515
1516 self.insert_field_idents(def_id, variant.data.fields());
1518 self.insert_field_visibilities_local(def_id.to_def_id(), variant.data.fields());
1519
1520 visit::walk_variant(self, variant);
1521 }
1522}