rustc_resolve/ident.rs
1use Determinacy::*;
2use Namespace::*;
3use rustc_ast::{self as ast, NodeId};
4use rustc_errors::ErrorGuaranteed;
5use rustc_hir::def::{DefKind, Namespace, NonMacroAttrKind, PartialRes, PerNS};
6use rustc_middle::{bug, ty};
7use rustc_session::lint::BuiltinLintDiag;
8use rustc_session::lint::builtin::PROC_MACRO_DERIVE_RESOLUTION_FALLBACK;
9use rustc_session::parse::feature_err;
10use rustc_span::def_id::LocalDefId;
11use rustc_span::hygiene::{ExpnId, ExpnKind, LocalExpnId, MacroKind, SyntaxContext};
12use rustc_span::{Ident, Span, kw, sym};
13use tracing::{debug, instrument};
14
15use crate::errors::{ParamKindInEnumDiscriminant, ParamKindInNonTrivialAnonConst};
16use crate::imports::Import;
17use crate::late::{ConstantHasGenerics, NoConstantGenericsReason, PathSource, Rib, RibKind};
18use crate::macros::{MacroRulesScope, sub_namespace_match};
19use crate::{
20 AmbiguityError, AmbiguityErrorMisc, AmbiguityKind, BindingKey, Determinacy, Finalize,
21 ImportKind, LexicalScopeBinding, Module, ModuleKind, ModuleOrUniformRoot, NameBinding,
22 NameBindingKind, ParentScope, PathResult, PrivacyError, Res, ResolutionError, Resolver, Scope,
23 ScopeSet, Segment, ToNameBinding, Used, Weak, errors,
24};
25
26type Visibility = ty::Visibility<LocalDefId>;
27
28#[derive(Copy, Clone)]
29pub enum UsePrelude {
30 No,
31 Yes,
32}
33
34impl From<UsePrelude> for bool {
35 fn from(up: UsePrelude) -> bool {
36 matches!(up, UsePrelude::Yes)
37 }
38}
39
40#[derive(Debug, PartialEq)]
41enum Shadowing {
42 Restricted,
43 Unrestricted,
44}
45
46impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
47 /// A generic scope visitor.
48 /// Visits scopes in order to resolve some identifier in them or perform other actions.
49 /// If the callback returns `Some` result, we stop visiting scopes and return it.
50 pub(crate) fn visit_scopes<T>(
51 &mut self,
52 scope_set: ScopeSet<'ra>,
53 parent_scope: &ParentScope<'ra>,
54 ctxt: SyntaxContext,
55 mut visitor: impl FnMut(&mut Self, Scope<'ra>, UsePrelude, SyntaxContext) -> Option<T>,
56 ) -> Option<T> {
57 // General principles:
58 // 1. Not controlled (user-defined) names should have higher priority than controlled names
59 // built into the language or standard library. This way we can add new names into the
60 // language or standard library without breaking user code.
61 // 2. "Closed set" below means new names cannot appear after the current resolution attempt.
62 // Places to search (in order of decreasing priority):
63 // (Type NS)
64 // 1. FIXME: Ribs (type parameters), there's no necessary infrastructure yet
65 // (open set, not controlled).
66 // 2. Names in modules (both normal `mod`ules and blocks), loop through hygienic parents
67 // (open, not controlled).
68 // 3. Extern prelude (open, the open part is from macro expansions, not controlled).
69 // 4. Tool modules (closed, controlled right now, but not in the future).
70 // 5. Standard library prelude (de-facto closed, controlled).
71 // 6. Language prelude (closed, controlled).
72 // (Value NS)
73 // 1. FIXME: Ribs (local variables), there's no necessary infrastructure yet
74 // (open set, not controlled).
75 // 2. Names in modules (both normal `mod`ules and blocks), loop through hygienic parents
76 // (open, not controlled).
77 // 3. Standard library prelude (de-facto closed, controlled).
78 // (Macro NS)
79 // 1-3. Derive helpers (open, not controlled). All ambiguities with other names
80 // are currently reported as errors. They should be higher in priority than preludes
81 // and probably even names in modules according to the "general principles" above. They
82 // also should be subject to restricted shadowing because are effectively produced by
83 // derives (you need to resolve the derive first to add helpers into scope), but they
84 // should be available before the derive is expanded for compatibility.
85 // It's mess in general, so we are being conservative for now.
86 // 1-3. `macro_rules` (open, not controlled), loop through `macro_rules` scopes. Have higher
87 // priority than prelude macros, but create ambiguities with macros in modules.
88 // 1-3. Names in modules (both normal `mod`ules and blocks), loop through hygienic parents
89 // (open, not controlled). Have higher priority than prelude macros, but create
90 // ambiguities with `macro_rules`.
91 // 4. `macro_use` prelude (open, the open part is from macro expansions, not controlled).
92 // 4a. User-defined prelude from macro-use
93 // (open, the open part is from macro expansions, not controlled).
94 // 4b. "Standard library prelude" part implemented through `macro-use` (closed, controlled).
95 // 4c. Standard library prelude (de-facto closed, controlled).
96 // 6. Language prelude: builtin attributes (closed, controlled).
97
98 let rust_2015 = ctxt.edition().is_rust_2015();
99 let (ns, macro_kind, is_absolute_path) = match scope_set {
100 ScopeSet::All(ns) => (ns, None, false),
101 ScopeSet::AbsolutePath(ns) => (ns, None, true),
102 ScopeSet::Macro(macro_kind) => (MacroNS, Some(macro_kind), false),
103 ScopeSet::Late(ns, ..) => (ns, None, false),
104 };
105 let module = match scope_set {
106 // Start with the specified module.
107 ScopeSet::Late(_, module, _) => module,
108 // Jump out of trait or enum modules, they do not act as scopes.
109 _ => parent_scope.module.nearest_item_scope(),
110 };
111 let mut scope = match ns {
112 _ if is_absolute_path => Scope::CrateRoot,
113 TypeNS | ValueNS => Scope::Module(module, None),
114 MacroNS => Scope::DeriveHelpers(parent_scope.expansion),
115 };
116 let mut ctxt = ctxt.normalize_to_macros_2_0();
117 let mut use_prelude = !module.no_implicit_prelude;
118
119 loop {
120 let visit = match scope {
121 // Derive helpers are not in scope when resolving derives in the same container.
122 Scope::DeriveHelpers(expn_id) => {
123 !(expn_id == parent_scope.expansion && macro_kind == Some(MacroKind::Derive))
124 }
125 Scope::DeriveHelpersCompat => true,
126 Scope::MacroRules(macro_rules_scope) => {
127 // Use "path compression" on `macro_rules` scope chains. This is an optimization
128 // used to avoid long scope chains, see the comments on `MacroRulesScopeRef`.
129 // As another consequence of this optimization visitors never observe invocation
130 // scopes for macros that were already expanded.
131 while let MacroRulesScope::Invocation(invoc_id) = macro_rules_scope.get() {
132 if let Some(next_scope) = self.output_macro_rules_scopes.get(&invoc_id) {
133 macro_rules_scope.set(next_scope.get());
134 } else {
135 break;
136 }
137 }
138 true
139 }
140 Scope::CrateRoot => true,
141 Scope::Module(..) => true,
142 Scope::MacroUsePrelude => use_prelude || rust_2015,
143 Scope::BuiltinAttrs => true,
144 Scope::ExternPrelude => use_prelude || is_absolute_path,
145 Scope::ToolPrelude => use_prelude,
146 Scope::StdLibPrelude => use_prelude || ns == MacroNS,
147 Scope::BuiltinTypes => true,
148 };
149
150 if visit {
151 let use_prelude = if use_prelude { UsePrelude::Yes } else { UsePrelude::No };
152 if let break_result @ Some(..) = visitor(self, scope, use_prelude, ctxt) {
153 return break_result;
154 }
155 }
156
157 scope = match scope {
158 Scope::DeriveHelpers(LocalExpnId::ROOT) => Scope::DeriveHelpersCompat,
159 Scope::DeriveHelpers(expn_id) => {
160 // Derive helpers are not visible to code generated by bang or derive macros.
161 let expn_data = expn_id.expn_data();
162 match expn_data.kind {
163 ExpnKind::Root
164 | ExpnKind::Macro(MacroKind::Bang | MacroKind::Derive, _) => {
165 Scope::DeriveHelpersCompat
166 }
167 _ => Scope::DeriveHelpers(expn_data.parent.expect_local()),
168 }
169 }
170 Scope::DeriveHelpersCompat => Scope::MacroRules(parent_scope.macro_rules),
171 Scope::MacroRules(macro_rules_scope) => match macro_rules_scope.get() {
172 MacroRulesScope::Binding(binding) => {
173 Scope::MacroRules(binding.parent_macro_rules_scope)
174 }
175 MacroRulesScope::Invocation(invoc_id) => {
176 Scope::MacroRules(self.invocation_parent_scopes[&invoc_id].macro_rules)
177 }
178 MacroRulesScope::Empty => Scope::Module(module, None),
179 },
180 Scope::CrateRoot => match ns {
181 TypeNS => {
182 ctxt.adjust(ExpnId::root());
183 Scope::ExternPrelude
184 }
185 ValueNS | MacroNS => break,
186 },
187 Scope::Module(module, prev_lint_id) => {
188 use_prelude = !module.no_implicit_prelude;
189 let derive_fallback_lint_id = match scope_set {
190 ScopeSet::Late(.., lint_id) => lint_id,
191 _ => None,
192 };
193 match self.hygienic_lexical_parent(module, &mut ctxt, derive_fallback_lint_id) {
194 Some((parent_module, lint_id)) => {
195 Scope::Module(parent_module, lint_id.or(prev_lint_id))
196 }
197 None => {
198 ctxt.adjust(ExpnId::root());
199 match ns {
200 TypeNS => Scope::ExternPrelude,
201 ValueNS => Scope::StdLibPrelude,
202 MacroNS => Scope::MacroUsePrelude,
203 }
204 }
205 }
206 }
207 Scope::MacroUsePrelude => Scope::StdLibPrelude,
208 Scope::BuiltinAttrs => break, // nowhere else to search
209 Scope::ExternPrelude if is_absolute_path => break,
210 Scope::ExternPrelude => Scope::ToolPrelude,
211 Scope::ToolPrelude => Scope::StdLibPrelude,
212 Scope::StdLibPrelude => match ns {
213 TypeNS => Scope::BuiltinTypes,
214 ValueNS => break, // nowhere else to search
215 MacroNS => Scope::BuiltinAttrs,
216 },
217 Scope::BuiltinTypes => break, // nowhere else to search
218 };
219 }
220
221 None
222 }
223
224 fn hygienic_lexical_parent(
225 &mut self,
226 module: Module<'ra>,
227 ctxt: &mut SyntaxContext,
228 derive_fallback_lint_id: Option<NodeId>,
229 ) -> Option<(Module<'ra>, Option<NodeId>)> {
230 if !module.expansion.outer_expn_is_descendant_of(*ctxt) {
231 return Some((self.expn_def_scope(ctxt.remove_mark()), None));
232 }
233
234 if let ModuleKind::Block = module.kind {
235 return Some((module.parent.unwrap().nearest_item_scope(), None));
236 }
237
238 // We need to support the next case under a deprecation warning
239 // ```
240 // struct MyStruct;
241 // ---- begin: this comes from a proc macro derive
242 // mod implementation_details {
243 // // Note that `MyStruct` is not in scope here.
244 // impl SomeTrait for MyStruct { ... }
245 // }
246 // ---- end
247 // ```
248 // So we have to fall back to the module's parent during lexical resolution in this case.
249 if derive_fallback_lint_id.is_some()
250 && let Some(parent) = module.parent
251 // Inner module is inside the macro
252 && module.expansion != parent.expansion
253 // Parent module is outside of the macro
254 && module.expansion.is_descendant_of(parent.expansion)
255 // The macro is a proc macro derive
256 && let Some(def_id) = module.expansion.expn_data().macro_def_id
257 {
258 let ext = &self.get_macro_by_def_id(def_id).ext;
259 if ext.builtin_name.is_none()
260 && ext.macro_kind() == MacroKind::Derive
261 && parent.expansion.outer_expn_is_descendant_of(*ctxt)
262 {
263 return Some((parent, derive_fallback_lint_id));
264 }
265 }
266
267 None
268 }
269
270 /// This resolves the identifier `ident` in the namespace `ns` in the current lexical scope.
271 /// More specifically, we proceed up the hierarchy of scopes and return the binding for
272 /// `ident` in the first scope that defines it (or None if no scopes define it).
273 ///
274 /// A block's items are above its local variables in the scope hierarchy, regardless of where
275 /// the items are defined in the block. For example,
276 /// ```rust
277 /// fn f() {
278 /// g(); // Since there are no local variables in scope yet, this resolves to the item.
279 /// let g = || {};
280 /// fn g() {}
281 /// g(); // This resolves to the local variable `g` since it shadows the item.
282 /// }
283 /// ```
284 ///
285 /// Invariant: This must only be called during main resolution, not during
286 /// import resolution.
287 #[instrument(level = "debug", skip(self, ribs))]
288 pub(crate) fn resolve_ident_in_lexical_scope(
289 &mut self,
290 mut ident: Ident,
291 ns: Namespace,
292 parent_scope: &ParentScope<'ra>,
293 finalize: Option<Finalize>,
294 ribs: &[Rib<'ra>],
295 ignore_binding: Option<NameBinding<'ra>>,
296 ) -> Option<LexicalScopeBinding<'ra>> {
297 assert!(ns == TypeNS || ns == ValueNS);
298 let orig_ident = ident;
299 let (general_span, normalized_span) = if ident.name == kw::SelfUpper {
300 // FIXME(jseyfried) improve `Self` hygiene
301 let empty_span = ident.span.with_ctxt(SyntaxContext::root());
302 (empty_span, empty_span)
303 } else if ns == TypeNS {
304 let normalized_span = ident.span.normalize_to_macros_2_0();
305 (normalized_span, normalized_span)
306 } else {
307 (ident.span.normalize_to_macro_rules(), ident.span.normalize_to_macros_2_0())
308 };
309 ident.span = general_span;
310 let normalized_ident = Ident { span: normalized_span, ..ident };
311
312 // Walk backwards up the ribs in scope.
313 let mut module = self.graph_root;
314 for (i, rib) in ribs.iter().enumerate().rev() {
315 debug!("walk rib\n{:?}", rib.bindings);
316 // Use the rib kind to determine whether we are resolving parameters
317 // (macro 2.0 hygiene) or local variables (`macro_rules` hygiene).
318 let rib_ident = if rib.kind.contains_params() { normalized_ident } else { ident };
319 if let Some((original_rib_ident_def, res)) = rib.bindings.get_key_value(&rib_ident) {
320 // The ident resolves to a type parameter or local variable.
321 return Some(LexicalScopeBinding::Res(self.validate_res_from_ribs(
322 i,
323 rib_ident,
324 *res,
325 finalize.map(|finalize| finalize.path_span),
326 *original_rib_ident_def,
327 ribs,
328 )));
329 }
330
331 module = match rib.kind {
332 RibKind::Module(module) => module,
333 RibKind::MacroDefinition(def) if def == self.macro_def(ident.span.ctxt()) => {
334 // If an invocation of this macro created `ident`, give up on `ident`
335 // and switch to `ident`'s source from the macro definition.
336 ident.span.remove_mark();
337 continue;
338 }
339 _ => continue,
340 };
341
342 match module.kind {
343 ModuleKind::Block => {} // We can see through blocks
344 _ => break,
345 }
346
347 let item = self.resolve_ident_in_module_unadjusted(
348 ModuleOrUniformRoot::Module(module),
349 ident,
350 ns,
351 parent_scope,
352 Shadowing::Unrestricted,
353 finalize.map(|finalize| Finalize { used: Used::Scope, ..finalize }),
354 ignore_binding,
355 None,
356 );
357 if let Ok(binding) = item {
358 // The ident resolves to an item.
359 return Some(LexicalScopeBinding::Item(binding));
360 }
361 }
362 self.early_resolve_ident_in_lexical_scope(
363 orig_ident,
364 ScopeSet::Late(ns, module, finalize.map(|finalize| finalize.node_id)),
365 parent_scope,
366 finalize,
367 finalize.is_some(),
368 ignore_binding,
369 None,
370 )
371 .ok()
372 .map(LexicalScopeBinding::Item)
373 }
374
375 /// Resolve an identifier in lexical scope.
376 /// This is a variation of `fn resolve_ident_in_lexical_scope` that can be run during
377 /// expansion and import resolution (perhaps they can be merged in the future).
378 /// The function is used for resolving initial segments of macro paths (e.g., `foo` in
379 /// `foo::bar!();` or `foo!();`) and also for import paths on 2018 edition.
380 #[instrument(level = "debug", skip(self))]
381 pub(crate) fn early_resolve_ident_in_lexical_scope(
382 &mut self,
383 orig_ident: Ident,
384 scope_set: ScopeSet<'ra>,
385 parent_scope: &ParentScope<'ra>,
386 finalize: Option<Finalize>,
387 force: bool,
388 ignore_binding: Option<NameBinding<'ra>>,
389 ignore_import: Option<Import<'ra>>,
390 ) -> Result<NameBinding<'ra>, Determinacy> {
391 bitflags::bitflags! {
392 #[derive(Clone, Copy)]
393 struct Flags: u8 {
394 const MACRO_RULES = 1 << 0;
395 const MODULE = 1 << 1;
396 const MISC_SUGGEST_CRATE = 1 << 2;
397 const MISC_SUGGEST_SELF = 1 << 3;
398 const MISC_FROM_PRELUDE = 1 << 4;
399 }
400 }
401
402 assert!(force || finalize.is_none()); // `finalize` implies `force`
403
404 // Make sure `self`, `super` etc produce an error when passed to here.
405 if orig_ident.is_path_segment_keyword() {
406 return Err(Determinacy::Determined);
407 }
408
409 let (ns, macro_kind) = match scope_set {
410 ScopeSet::All(ns) => (ns, None),
411 ScopeSet::AbsolutePath(ns) => (ns, None),
412 ScopeSet::Macro(macro_kind) => (MacroNS, Some(macro_kind)),
413 ScopeSet::Late(ns, ..) => (ns, None),
414 };
415
416 // This is *the* result, resolution from the scope closest to the resolved identifier.
417 // However, sometimes this result is "weak" because it comes from a glob import or
418 // a macro expansion, and in this case it cannot shadow names from outer scopes, e.g.
419 // mod m { ... } // solution in outer scope
420 // {
421 // use prefix::*; // imports another `m` - innermost solution
422 // // weak, cannot shadow the outer `m`, need to report ambiguity error
423 // m::mac!();
424 // }
425 // So we have to save the innermost solution and continue searching in outer scopes
426 // to detect potential ambiguities.
427 let mut innermost_result: Option<(NameBinding<'_>, Flags)> = None;
428 let mut determinacy = Determinacy::Determined;
429
430 // Go through all the scopes and try to resolve the name.
431 let break_result = self.visit_scopes(
432 scope_set,
433 parent_scope,
434 orig_ident.span.ctxt(),
435 |this, scope, use_prelude, ctxt| {
436 let ident = Ident::new(orig_ident.name, orig_ident.span.with_ctxt(ctxt));
437 let result = match scope {
438 Scope::DeriveHelpers(expn_id) => {
439 if let Some(binding) = this.helper_attrs.get(&expn_id).and_then(|attrs| {
440 attrs.iter().rfind(|(i, _)| ident == *i).map(|(_, binding)| *binding)
441 }) {
442 Ok((binding, Flags::empty()))
443 } else {
444 Err(Determinacy::Determined)
445 }
446 }
447 Scope::DeriveHelpersCompat => {
448 // FIXME: Try running this logic earlier, to allocate name bindings for
449 // legacy derive helpers when creating an attribute invocation with
450 // following derives. Legacy derive helpers are not common, so it shouldn't
451 // affect performance. It should also allow to remove the `derives`
452 // component from `ParentScope`.
453 let mut result = Err(Determinacy::Determined);
454 for derive in parent_scope.derives {
455 let parent_scope = &ParentScope { derives: &[], ..*parent_scope };
456 match this.resolve_macro_path(
457 derive,
458 Some(MacroKind::Derive),
459 parent_scope,
460 true,
461 force,
462 ignore_import,
463 ) {
464 Ok((Some(ext), _)) => {
465 if ext.helper_attrs.contains(&ident.name) {
466 let binding = (
467 Res::NonMacroAttr(NonMacroAttrKind::DeriveHelperCompat),
468 Visibility::Public,
469 derive.span,
470 LocalExpnId::ROOT,
471 )
472 .to_name_binding(this.arenas);
473 result = Ok((binding, Flags::empty()));
474 break;
475 }
476 }
477 Ok(_) | Err(Determinacy::Determined) => {}
478 Err(Determinacy::Undetermined) => {
479 result = Err(Determinacy::Undetermined)
480 }
481 }
482 }
483 result
484 }
485 Scope::MacroRules(macro_rules_scope) => match macro_rules_scope.get() {
486 MacroRulesScope::Binding(macro_rules_binding)
487 if ident == macro_rules_binding.ident =>
488 {
489 Ok((macro_rules_binding.binding, Flags::MACRO_RULES))
490 }
491 MacroRulesScope::Invocation(_) => Err(Determinacy::Undetermined),
492 _ => Err(Determinacy::Determined),
493 },
494 Scope::CrateRoot => {
495 let root_ident = Ident::new(kw::PathRoot, ident.span);
496 let root_module = this.resolve_crate_root(root_ident);
497 let binding = this.resolve_ident_in_module(
498 ModuleOrUniformRoot::Module(root_module),
499 ident,
500 ns,
501 parent_scope,
502 finalize,
503 ignore_binding,
504 ignore_import,
505 );
506 match binding {
507 Ok(binding) => Ok((binding, Flags::MODULE | Flags::MISC_SUGGEST_CRATE)),
508 Err((Determinacy::Undetermined, Weak::No)) => {
509 return Some(Err(Determinacy::determined(force)));
510 }
511 Err((Determinacy::Undetermined, Weak::Yes)) => {
512 Err(Determinacy::Undetermined)
513 }
514 Err((Determinacy::Determined, _)) => Err(Determinacy::Determined),
515 }
516 }
517 Scope::Module(module, derive_fallback_lint_id) => {
518 let adjusted_parent_scope = &ParentScope { module, ..*parent_scope };
519 let binding = this.resolve_ident_in_module_unadjusted(
520 ModuleOrUniformRoot::Module(module),
521 ident,
522 ns,
523 adjusted_parent_scope,
524 if matches!(scope_set, ScopeSet::Late(..)) {
525 Shadowing::Unrestricted
526 } else {
527 Shadowing::Restricted
528 },
529 finalize.map(|finalize| Finalize { used: Used::Scope, ..finalize }),
530 ignore_binding,
531 ignore_import,
532 );
533 match binding {
534 Ok(binding) => {
535 if let Some(lint_id) = derive_fallback_lint_id {
536 this.lint_buffer.buffer_lint(
537 PROC_MACRO_DERIVE_RESOLUTION_FALLBACK,
538 lint_id,
539 orig_ident.span,
540 BuiltinLintDiag::ProcMacroDeriveResolutionFallback {
541 span: orig_ident.span,
542 ns,
543 ident,
544 },
545 );
546 }
547 let misc_flags = if module == this.graph_root {
548 Flags::MISC_SUGGEST_CRATE
549 } else if module.is_normal() {
550 Flags::MISC_SUGGEST_SELF
551 } else {
552 Flags::empty()
553 };
554 Ok((binding, Flags::MODULE | misc_flags))
555 }
556 Err((Determinacy::Undetermined, Weak::No)) => {
557 return Some(Err(Determinacy::determined(force)));
558 }
559 Err((Determinacy::Undetermined, Weak::Yes)) => {
560 Err(Determinacy::Undetermined)
561 }
562 Err((Determinacy::Determined, _)) => Err(Determinacy::Determined),
563 }
564 }
565 Scope::MacroUsePrelude => {
566 match this.macro_use_prelude.get(&ident.name).cloned() {
567 Some(binding) => Ok((binding, Flags::MISC_FROM_PRELUDE)),
568 None => Err(Determinacy::determined(
569 this.graph_root.unexpanded_invocations.borrow().is_empty(),
570 )),
571 }
572 }
573 Scope::BuiltinAttrs => match this.builtin_attrs_bindings.get(&ident.name) {
574 Some(binding) => Ok((*binding, Flags::empty())),
575 None => Err(Determinacy::Determined),
576 },
577 Scope::ExternPrelude => {
578 match this.extern_prelude_get(ident, finalize.is_some()) {
579 Some(binding) => Ok((binding, Flags::empty())),
580 None => Err(Determinacy::determined(
581 this.graph_root.unexpanded_invocations.borrow().is_empty(),
582 )),
583 }
584 }
585 Scope::ToolPrelude => match this.registered_tool_bindings.get(&ident) {
586 Some(binding) => Ok((*binding, Flags::empty())),
587 None => Err(Determinacy::Determined),
588 },
589 Scope::StdLibPrelude => {
590 let mut result = Err(Determinacy::Determined);
591 if let Some(prelude) = this.prelude
592 && let Ok(binding) = this.resolve_ident_in_module_unadjusted(
593 ModuleOrUniformRoot::Module(prelude),
594 ident,
595 ns,
596 parent_scope,
597 Shadowing::Unrestricted,
598 None,
599 ignore_binding,
600 ignore_import,
601 )
602 && (matches!(use_prelude, UsePrelude::Yes)
603 || this.is_builtin_macro(binding.res()))
604 {
605 result = Ok((binding, Flags::MISC_FROM_PRELUDE));
606 }
607
608 result
609 }
610 Scope::BuiltinTypes => match this.builtin_types_bindings.get(&ident.name) {
611 Some(binding) => {
612 if matches!(ident.name, sym::f16)
613 && !this.tcx.features().f16()
614 && !ident.span.allows_unstable(sym::f16)
615 && finalize.is_some()
616 && innermost_result.is_none()
617 {
618 feature_err(
619 this.tcx.sess,
620 sym::f16,
621 ident.span,
622 "the type `f16` is unstable",
623 )
624 .emit();
625 }
626 if matches!(ident.name, sym::f128)
627 && !this.tcx.features().f128()
628 && !ident.span.allows_unstable(sym::f128)
629 && finalize.is_some()
630 && innermost_result.is_none()
631 {
632 feature_err(
633 this.tcx.sess,
634 sym::f128,
635 ident.span,
636 "the type `f128` is unstable",
637 )
638 .emit();
639 }
640 Ok((*binding, Flags::empty()))
641 }
642 None => Err(Determinacy::Determined),
643 },
644 };
645
646 match result {
647 Ok((binding, flags))
648 if sub_namespace_match(binding.macro_kind(), macro_kind) =>
649 {
650 if finalize.is_none() || matches!(scope_set, ScopeSet::Late(..)) {
651 return Some(Ok(binding));
652 }
653
654 if let Some((innermost_binding, innermost_flags)) = innermost_result {
655 // Found another solution, if the first one was "weak", report an error.
656 let (res, innermost_res) = (binding.res(), innermost_binding.res());
657 if res != innermost_res {
658 let is_builtin = |res| {
659 matches!(res, Res::NonMacroAttr(NonMacroAttrKind::Builtin(..)))
660 };
661 let derive_helper =
662 Res::NonMacroAttr(NonMacroAttrKind::DeriveHelper);
663 let derive_helper_compat =
664 Res::NonMacroAttr(NonMacroAttrKind::DeriveHelperCompat);
665
666 let ambiguity_error_kind = if is_builtin(innermost_res)
667 || is_builtin(res)
668 {
669 Some(AmbiguityKind::BuiltinAttr)
670 } else if innermost_res == derive_helper_compat
671 || res == derive_helper_compat && innermost_res != derive_helper
672 {
673 Some(AmbiguityKind::DeriveHelper)
674 } else if innermost_flags.contains(Flags::MACRO_RULES)
675 && flags.contains(Flags::MODULE)
676 && !this.disambiguate_macro_rules_vs_modularized(
677 innermost_binding,
678 binding,
679 )
680 || flags.contains(Flags::MACRO_RULES)
681 && innermost_flags.contains(Flags::MODULE)
682 && !this.disambiguate_macro_rules_vs_modularized(
683 binding,
684 innermost_binding,
685 )
686 {
687 Some(AmbiguityKind::MacroRulesVsModularized)
688 } else if innermost_binding.is_glob_import() {
689 Some(AmbiguityKind::GlobVsOuter)
690 } else if innermost_binding
691 .may_appear_after(parent_scope.expansion, binding)
692 {
693 Some(AmbiguityKind::MoreExpandedVsOuter)
694 } else {
695 None
696 };
697 if let Some(kind) = ambiguity_error_kind {
698 let misc = |f: Flags| {
699 if f.contains(Flags::MISC_SUGGEST_CRATE) {
700 AmbiguityErrorMisc::SuggestCrate
701 } else if f.contains(Flags::MISC_SUGGEST_SELF) {
702 AmbiguityErrorMisc::SuggestSelf
703 } else if f.contains(Flags::MISC_FROM_PRELUDE) {
704 AmbiguityErrorMisc::FromPrelude
705 } else {
706 AmbiguityErrorMisc::None
707 }
708 };
709 this.ambiguity_errors.push(AmbiguityError {
710 kind,
711 ident: orig_ident,
712 b1: innermost_binding,
713 b2: binding,
714 warning: false,
715 misc1: misc(innermost_flags),
716 misc2: misc(flags),
717 });
718 return Some(Ok(innermost_binding));
719 }
720 }
721 } else {
722 // Found the first solution.
723 innermost_result = Some((binding, flags));
724 }
725 }
726 Ok(..) | Err(Determinacy::Determined) => {}
727 Err(Determinacy::Undetermined) => determinacy = Determinacy::Undetermined,
728 }
729
730 None
731 },
732 );
733
734 if let Some(break_result) = break_result {
735 return break_result;
736 }
737
738 // The first found solution was the only one, return it.
739 if let Some((binding, _)) = innermost_result {
740 return Ok(binding);
741 }
742
743 Err(Determinacy::determined(determinacy == Determinacy::Determined || force))
744 }
745
746 #[instrument(level = "debug", skip(self))]
747 pub(crate) fn maybe_resolve_ident_in_module(
748 &mut self,
749 module: ModuleOrUniformRoot<'ra>,
750 ident: Ident,
751 ns: Namespace,
752 parent_scope: &ParentScope<'ra>,
753 ignore_import: Option<Import<'ra>>,
754 ) -> Result<NameBinding<'ra>, Determinacy> {
755 self.resolve_ident_in_module(module, ident, ns, parent_scope, None, None, ignore_import)
756 .map_err(|(determinacy, _)| determinacy)
757 }
758
759 #[instrument(level = "debug", skip(self))]
760 pub(crate) fn resolve_ident_in_module(
761 &mut self,
762 module: ModuleOrUniformRoot<'ra>,
763 mut ident: Ident,
764 ns: Namespace,
765 parent_scope: &ParentScope<'ra>,
766 finalize: Option<Finalize>,
767 ignore_binding: Option<NameBinding<'ra>>,
768 ignore_import: Option<Import<'ra>>,
769 ) -> Result<NameBinding<'ra>, (Determinacy, Weak)> {
770 let tmp_parent_scope;
771 let mut adjusted_parent_scope = parent_scope;
772 match module {
773 ModuleOrUniformRoot::Module(m) => {
774 if let Some(def) = ident.span.normalize_to_macros_2_0_and_adjust(m.expansion) {
775 tmp_parent_scope =
776 ParentScope { module: self.expn_def_scope(def), ..*parent_scope };
777 adjusted_parent_scope = &tmp_parent_scope;
778 }
779 }
780 ModuleOrUniformRoot::ExternPrelude => {
781 ident.span.normalize_to_macros_2_0_and_adjust(ExpnId::root());
782 }
783 ModuleOrUniformRoot::CrateRootAndExternPrelude | ModuleOrUniformRoot::CurrentScope => {
784 // No adjustments
785 }
786 }
787 self.resolve_ident_in_module_unadjusted(
788 module,
789 ident,
790 ns,
791 adjusted_parent_scope,
792 Shadowing::Unrestricted,
793 finalize,
794 ignore_binding,
795 ignore_import,
796 )
797 }
798
799 /// Attempts to resolve `ident` in namespaces `ns` of `module`.
800 /// Invariant: if `finalize` is `Some`, expansion and import resolution must be complete.
801 #[instrument(level = "debug", skip(self))]
802 fn resolve_ident_in_module_unadjusted(
803 &mut self,
804 module: ModuleOrUniformRoot<'ra>,
805 ident: Ident,
806 ns: Namespace,
807 parent_scope: &ParentScope<'ra>,
808 shadowing: Shadowing,
809 finalize: Option<Finalize>,
810 // This binding should be ignored during in-module resolution, so that we don't get
811 // "self-confirming" import resolutions during import validation and checking.
812 ignore_binding: Option<NameBinding<'ra>>,
813 ignore_import: Option<Import<'ra>>,
814 ) -> Result<NameBinding<'ra>, (Determinacy, Weak)> {
815 let module = match module {
816 ModuleOrUniformRoot::Module(module) => module,
817 ModuleOrUniformRoot::CrateRootAndExternPrelude => {
818 assert_eq!(shadowing, Shadowing::Unrestricted);
819 let binding = self.early_resolve_ident_in_lexical_scope(
820 ident,
821 ScopeSet::AbsolutePath(ns),
822 parent_scope,
823 finalize,
824 finalize.is_some(),
825 ignore_binding,
826 ignore_import,
827 );
828 return binding.map_err(|determinacy| (determinacy, Weak::No));
829 }
830 ModuleOrUniformRoot::ExternPrelude => {
831 assert_eq!(shadowing, Shadowing::Unrestricted);
832 return if ns != TypeNS {
833 Err((Determined, Weak::No))
834 } else if let Some(binding) = self.extern_prelude_get(ident, finalize.is_some()) {
835 Ok(binding)
836 } else if !self.graph_root.unexpanded_invocations.borrow().is_empty() {
837 // Macro-expanded `extern crate` items can add names to extern prelude.
838 Err((Undetermined, Weak::No))
839 } else {
840 Err((Determined, Weak::No))
841 };
842 }
843 ModuleOrUniformRoot::CurrentScope => {
844 assert_eq!(shadowing, Shadowing::Unrestricted);
845 if ns == TypeNS {
846 if ident.name == kw::Crate || ident.name == kw::DollarCrate {
847 let module = self.resolve_crate_root(ident);
848 return Ok(self.module_self_bindings[&module]);
849 } else if ident.name == kw::Super || ident.name == kw::SelfLower {
850 // FIXME: Implement these with renaming requirements so that e.g.
851 // `use super;` doesn't work, but `use super as name;` does.
852 // Fall through here to get an error from `early_resolve_...`.
853 }
854 }
855
856 let binding = self.early_resolve_ident_in_lexical_scope(
857 ident,
858 ScopeSet::All(ns),
859 parent_scope,
860 finalize,
861 finalize.is_some(),
862 ignore_binding,
863 ignore_import,
864 );
865 return binding.map_err(|determinacy| (determinacy, Weak::No));
866 }
867 };
868
869 let key = BindingKey::new(ident, ns);
870 let resolution =
871 self.resolution(module, key).try_borrow_mut().map_err(|_| (Determined, Weak::No))?; // This happens when there is a cycle of imports.
872
873 // If the primary binding is unusable, search further and return the shadowed glob
874 // binding if it exists. What we really want here is having two separate scopes in
875 // a module - one for non-globs and one for globs, but until that's done use this
876 // hack to avoid inconsistent resolution ICEs during import validation.
877 let binding = [resolution.binding, resolution.shadowed_glob]
878 .into_iter()
879 .find_map(|binding| if binding == ignore_binding { None } else { binding });
880
881 if let Some(Finalize { path_span, report_private, used, root_span, .. }) = finalize {
882 let Some(binding) = binding else {
883 return Err((Determined, Weak::No));
884 };
885
886 if !self.is_accessible_from(binding.vis, parent_scope.module) {
887 if report_private {
888 self.privacy_errors.push(PrivacyError {
889 ident,
890 binding,
891 dedup_span: path_span,
892 outermost_res: None,
893 parent_scope: *parent_scope,
894 single_nested: path_span != root_span,
895 });
896 } else {
897 return Err((Determined, Weak::No));
898 }
899 }
900
901 // Forbid expanded shadowing to avoid time travel.
902 if let Some(shadowed_glob) = resolution.shadowed_glob
903 && shadowing == Shadowing::Restricted
904 && binding.expansion != LocalExpnId::ROOT
905 && binding.res() != shadowed_glob.res()
906 {
907 self.ambiguity_errors.push(AmbiguityError {
908 kind: AmbiguityKind::GlobVsExpanded,
909 ident,
910 b1: binding,
911 b2: shadowed_glob,
912 warning: false,
913 misc1: AmbiguityErrorMisc::None,
914 misc2: AmbiguityErrorMisc::None,
915 });
916 }
917
918 if shadowing == Shadowing::Unrestricted
919 && binding.expansion != LocalExpnId::ROOT
920 && let NameBindingKind::Import { import, .. } = binding.kind
921 && matches!(import.kind, ImportKind::MacroExport)
922 {
923 self.macro_expanded_macro_export_errors.insert((path_span, binding.span));
924 }
925
926 self.record_use(ident, binding, used);
927 return Ok(binding);
928 }
929
930 let check_usable = |this: &mut Self, binding: NameBinding<'ra>| {
931 let usable = this.is_accessible_from(binding.vis, parent_scope.module);
932 if usable { Ok(binding) } else { Err((Determined, Weak::No)) }
933 };
934
935 // Items and single imports are not shadowable, if we have one, then it's determined.
936 if let Some(binding) = binding
937 && !binding.is_glob_import()
938 {
939 return check_usable(self, binding);
940 }
941
942 // --- From now on we either have a glob resolution or no resolution. ---
943
944 // Check if one of single imports can still define the name,
945 // if it can then our result is not determined and can be invalidated.
946 for single_import in &resolution.single_imports {
947 if ignore_import == Some(*single_import) {
948 // This branch handles a cycle in single imports.
949 //
950 // For example:
951 // ```
952 // use a::b;
953 // use b as a;
954 // ```
955 // 1. Record `use a::b` as the `ignore_import` and attempt to locate `a` in the
956 // current module.
957 // 2. Encounter the import `use b as a`, which is a `single_import` for `a`,
958 // and try to find `b` in the current module.
959 // 3. Re-encounter the `use a::b` import since it's a `single_import` of `b`.
960 // This leads to entering this branch.
961 continue;
962 }
963 if !self.is_accessible_from(single_import.vis, parent_scope.module) {
964 continue;
965 }
966 if let Some(ignored) = ignore_binding
967 && let NameBindingKind::Import { import, .. } = ignored.kind
968 && import == *single_import
969 {
970 // Ignore not just the binding itself, but if it has a shadowed_glob,
971 // ignore that, too, because this loop is supposed to only process
972 // named imports.
973 continue;
974 }
975
976 let Some(module) = single_import.imported_module.get() else {
977 return Err((Undetermined, Weak::No));
978 };
979 let ImportKind::Single { source, target, target_bindings, .. } = &single_import.kind
980 else {
981 unreachable!();
982 };
983 if source != target {
984 // This branch allows the binding to be defined or updated later if the target name
985 // can hide the source.
986 if target_bindings.iter().all(|binding| binding.get().is_none()) {
987 // None of the target bindings are available, so we can't determine
988 // if this binding is correct or not.
989 // See more details in #124840
990 return Err((Undetermined, Weak::No));
991 } else if target_bindings[ns].get().is_none() && binding.is_some() {
992 // `binding.is_some()` avoids the condition where the binding
993 // truly doesn't exist in this namespace and should return `Err(Determined)`.
994 return Err((Undetermined, Weak::No));
995 }
996 }
997
998 match self.resolve_ident_in_module(
999 module,
1000 *source,
1001 ns,
1002 &single_import.parent_scope,
1003 None,
1004 ignore_binding,
1005 ignore_import,
1006 ) {
1007 Err((Determined, _)) => continue,
1008 Ok(binding)
1009 if !self.is_accessible_from(binding.vis, single_import.parent_scope.module) =>
1010 {
1011 continue;
1012 }
1013 Ok(_) | Err((Undetermined, _)) => return Err((Undetermined, Weak::No)),
1014 }
1015 }
1016
1017 // So we have a resolution that's from a glob import. This resolution is determined
1018 // if it cannot be shadowed by some new item/import expanded from a macro.
1019 // This happens either if there are no unexpanded macros, or expanded names cannot
1020 // shadow globs (that happens in macro namespace or with restricted shadowing).
1021 //
1022 // Additionally, any macro in any module can plant names in the root module if it creates
1023 // `macro_export` macros, so the root module effectively has unresolved invocations if any
1024 // module has unresolved invocations.
1025 // However, it causes resolution/expansion to stuck too often (#53144), so, to make
1026 // progress, we have to ignore those potential unresolved invocations from other modules
1027 // and prohibit access to macro-expanded `macro_export` macros instead (unless restricted
1028 // shadowing is enabled, see `macro_expanded_macro_export_errors`).
1029 if let Some(binding) = binding {
1030 if binding.determined() || ns == MacroNS || shadowing == Shadowing::Restricted {
1031 return check_usable(self, binding);
1032 } else {
1033 return Err((Undetermined, Weak::No));
1034 }
1035 }
1036
1037 // --- From now on we have no resolution. ---
1038
1039 // Now we are in situation when new item/import can appear only from a glob or a macro
1040 // expansion. With restricted shadowing names from globs and macro expansions cannot
1041 // shadow names from outer scopes, so we can freely fallback from module search to search
1042 // in outer scopes. For `early_resolve_ident_in_lexical_scope` to continue search in outer
1043 // scopes we return `Undetermined` with `Weak::Yes`.
1044
1045 // Check if one of unexpanded macros can still define the name,
1046 // if it can then our "no resolution" result is not determined and can be invalidated.
1047 if !module.unexpanded_invocations.borrow().is_empty() {
1048 return Err((Undetermined, Weak::Yes));
1049 }
1050
1051 // Check if one of glob imports can still define the name,
1052 // if it can then our "no resolution" result is not determined and can be invalidated.
1053 for glob_import in module.globs.borrow().iter() {
1054 if ignore_import == Some(*glob_import) {
1055 continue;
1056 }
1057 if !self.is_accessible_from(glob_import.vis, parent_scope.module) {
1058 continue;
1059 }
1060 let module = match glob_import.imported_module.get() {
1061 Some(ModuleOrUniformRoot::Module(module)) => module,
1062 Some(_) => continue,
1063 None => return Err((Undetermined, Weak::Yes)),
1064 };
1065 let tmp_parent_scope;
1066 let (mut adjusted_parent_scope, mut ident) =
1067 (parent_scope, ident.normalize_to_macros_2_0());
1068 match ident.span.glob_adjust(module.expansion, glob_import.span) {
1069 Some(Some(def)) => {
1070 tmp_parent_scope =
1071 ParentScope { module: self.expn_def_scope(def), ..*parent_scope };
1072 adjusted_parent_scope = &tmp_parent_scope;
1073 }
1074 Some(None) => {}
1075 None => continue,
1076 };
1077 let result = self.resolve_ident_in_module_unadjusted(
1078 ModuleOrUniformRoot::Module(module),
1079 ident,
1080 ns,
1081 adjusted_parent_scope,
1082 Shadowing::Unrestricted,
1083 None,
1084 ignore_binding,
1085 ignore_import,
1086 );
1087
1088 match result {
1089 Err((Determined, _)) => continue,
1090 Ok(binding)
1091 if !self.is_accessible_from(binding.vis, glob_import.parent_scope.module) =>
1092 {
1093 continue;
1094 }
1095 Ok(_) | Err((Undetermined, _)) => return Err((Undetermined, Weak::Yes)),
1096 }
1097 }
1098
1099 // No resolution and no one else can define the name - determinate error.
1100 Err((Determined, Weak::No))
1101 }
1102
1103 /// Validate a local resolution (from ribs).
1104 #[instrument(level = "debug", skip(self, all_ribs))]
1105 fn validate_res_from_ribs(
1106 &mut self,
1107 rib_index: usize,
1108 rib_ident: Ident,
1109 mut res: Res,
1110 finalize: Option<Span>,
1111 original_rib_ident_def: Ident,
1112 all_ribs: &[Rib<'ra>],
1113 ) -> Res {
1114 debug!("validate_res_from_ribs({:?})", res);
1115 let ribs = &all_ribs[rib_index + 1..];
1116
1117 // An invalid forward use of a generic parameter from a previous default
1118 // or in a const param ty.
1119 if let RibKind::ForwardGenericParamBan(reason) = all_ribs[rib_index].kind {
1120 if let Some(span) = finalize {
1121 let res_error = if rib_ident.name == kw::SelfUpper {
1122 ResolutionError::ForwardDeclaredSelf(reason)
1123 } else {
1124 ResolutionError::ForwardDeclaredGenericParam(rib_ident.name, reason)
1125 };
1126 self.report_error(span, res_error);
1127 }
1128 assert_eq!(res, Res::Err);
1129 return Res::Err;
1130 }
1131
1132 match res {
1133 Res::Local(_) => {
1134 use ResolutionError::*;
1135 let mut res_err = None;
1136
1137 for rib in ribs {
1138 match rib.kind {
1139 RibKind::Normal
1140 | RibKind::FnOrCoroutine
1141 | RibKind::Module(..)
1142 | RibKind::MacroDefinition(..)
1143 | RibKind::ForwardGenericParamBan(_) => {
1144 // Nothing to do. Continue.
1145 }
1146 RibKind::Item(..) | RibKind::AssocItem => {
1147 // This was an attempt to access an upvar inside a
1148 // named function item. This is not allowed, so we
1149 // report an error.
1150 if let Some(span) = finalize {
1151 // We don't immediately trigger a resolve error, because
1152 // we want certain other resolution errors (namely those
1153 // emitted for `ConstantItemRibKind` below) to take
1154 // precedence.
1155 res_err = Some((span, CannotCaptureDynamicEnvironmentInFnItem));
1156 }
1157 }
1158 RibKind::ConstantItem(_, item) => {
1159 // Still doesn't deal with upvars
1160 if let Some(span) = finalize {
1161 let (span, resolution_error) = match item {
1162 None if rib_ident.name == kw::SelfLower => {
1163 (span, LowercaseSelf)
1164 }
1165 None => {
1166 // If we have a `let name = expr;`, we have the span for
1167 // `name` and use that to see if it is followed by a type
1168 // specifier. If not, then we know we need to suggest
1169 // `const name: Ty = expr;`. This is a heuristic, it will
1170 // break down in the presence of macros.
1171 let sm = self.tcx.sess.source_map();
1172 let type_span = match sm.span_look_ahead(
1173 original_rib_ident_def.span,
1174 ":",
1175 None,
1176 ) {
1177 None => {
1178 Some(original_rib_ident_def.span.shrink_to_hi())
1179 }
1180 Some(_) => None,
1181 };
1182 (
1183 rib_ident.span,
1184 AttemptToUseNonConstantValueInConstant {
1185 ident: original_rib_ident_def,
1186 suggestion: "const",
1187 current: "let",
1188 type_span,
1189 },
1190 )
1191 }
1192 Some((ident, kind)) => (
1193 span,
1194 AttemptToUseNonConstantValueInConstant {
1195 ident,
1196 suggestion: "let",
1197 current: kind.as_str(),
1198 type_span: None,
1199 },
1200 ),
1201 };
1202 self.report_error(span, resolution_error);
1203 }
1204 return Res::Err;
1205 }
1206 RibKind::ConstParamTy => {
1207 if let Some(span) = finalize {
1208 self.report_error(
1209 span,
1210 ParamInTyOfConstParam { name: rib_ident.name },
1211 );
1212 }
1213 return Res::Err;
1214 }
1215 RibKind::InlineAsmSym => {
1216 if let Some(span) = finalize {
1217 self.report_error(span, InvalidAsmSym);
1218 }
1219 return Res::Err;
1220 }
1221 }
1222 }
1223 if let Some((span, res_err)) = res_err {
1224 self.report_error(span, res_err);
1225 return Res::Err;
1226 }
1227 }
1228 Res::Def(DefKind::TyParam, _) | Res::SelfTyParam { .. } | Res::SelfTyAlias { .. } => {
1229 for rib in ribs {
1230 let (has_generic_params, def_kind) = match rib.kind {
1231 RibKind::Normal
1232 | RibKind::FnOrCoroutine
1233 | RibKind::Module(..)
1234 | RibKind::MacroDefinition(..)
1235 | RibKind::InlineAsmSym
1236 | RibKind::AssocItem
1237 | RibKind::ForwardGenericParamBan(_) => {
1238 // Nothing to do. Continue.
1239 continue;
1240 }
1241
1242 RibKind::ConstParamTy => {
1243 if !self.tcx.features().generic_const_parameter_types() {
1244 if let Some(span) = finalize {
1245 self.report_error(
1246 span,
1247 ResolutionError::ParamInTyOfConstParam {
1248 name: rib_ident.name,
1249 },
1250 );
1251 }
1252 return Res::Err;
1253 } else {
1254 continue;
1255 }
1256 }
1257
1258 RibKind::ConstantItem(trivial, _) => {
1259 if let ConstantHasGenerics::No(cause) = trivial {
1260 // HACK(min_const_generics): If we encounter `Self` in an anonymous
1261 // constant we can't easily tell if it's generic at this stage, so
1262 // we instead remember this and then enforce the self type to be
1263 // concrete later on.
1264 if let Res::SelfTyAlias {
1265 alias_to: def,
1266 forbid_generic: _,
1267 is_trait_impl,
1268 } = res
1269 {
1270 res = Res::SelfTyAlias {
1271 alias_to: def,
1272 forbid_generic: true,
1273 is_trait_impl,
1274 }
1275 } else {
1276 if let Some(span) = finalize {
1277 let error = match cause {
1278 NoConstantGenericsReason::IsEnumDiscriminant => {
1279 ResolutionError::ParamInEnumDiscriminant {
1280 name: rib_ident.name,
1281 param_kind: ParamKindInEnumDiscriminant::Type,
1282 }
1283 }
1284 NoConstantGenericsReason::NonTrivialConstArg => {
1285 ResolutionError::ParamInNonTrivialAnonConst {
1286 name: rib_ident.name,
1287 param_kind:
1288 ParamKindInNonTrivialAnonConst::Type,
1289 }
1290 }
1291 };
1292 let _: ErrorGuaranteed = self.report_error(span, error);
1293 }
1294
1295 return Res::Err;
1296 }
1297 }
1298
1299 continue;
1300 }
1301
1302 // This was an attempt to use a type parameter outside its scope.
1303 RibKind::Item(has_generic_params, def_kind) => {
1304 (has_generic_params, def_kind)
1305 }
1306 };
1307
1308 if let Some(span) = finalize {
1309 self.report_error(
1310 span,
1311 ResolutionError::GenericParamsFromOuterItem(
1312 res,
1313 has_generic_params,
1314 def_kind,
1315 ),
1316 );
1317 }
1318 return Res::Err;
1319 }
1320 }
1321 Res::Def(DefKind::ConstParam, _) => {
1322 for rib in ribs {
1323 let (has_generic_params, def_kind) = match rib.kind {
1324 RibKind::Normal
1325 | RibKind::FnOrCoroutine
1326 | RibKind::Module(..)
1327 | RibKind::MacroDefinition(..)
1328 | RibKind::InlineAsmSym
1329 | RibKind::AssocItem
1330 | RibKind::ForwardGenericParamBan(_) => continue,
1331
1332 RibKind::ConstParamTy => {
1333 if !self.tcx.features().generic_const_parameter_types() {
1334 if let Some(span) = finalize {
1335 self.report_error(
1336 span,
1337 ResolutionError::ParamInTyOfConstParam {
1338 name: rib_ident.name,
1339 },
1340 );
1341 }
1342 return Res::Err;
1343 } else {
1344 continue;
1345 }
1346 }
1347
1348 RibKind::ConstantItem(trivial, _) => {
1349 if let ConstantHasGenerics::No(cause) = trivial {
1350 if let Some(span) = finalize {
1351 let error = match cause {
1352 NoConstantGenericsReason::IsEnumDiscriminant => {
1353 ResolutionError::ParamInEnumDiscriminant {
1354 name: rib_ident.name,
1355 param_kind: ParamKindInEnumDiscriminant::Const,
1356 }
1357 }
1358 NoConstantGenericsReason::NonTrivialConstArg => {
1359 ResolutionError::ParamInNonTrivialAnonConst {
1360 name: rib_ident.name,
1361 param_kind: ParamKindInNonTrivialAnonConst::Const {
1362 name: rib_ident.name,
1363 },
1364 }
1365 }
1366 };
1367 self.report_error(span, error);
1368 }
1369
1370 return Res::Err;
1371 }
1372
1373 continue;
1374 }
1375
1376 RibKind::Item(has_generic_params, def_kind) => {
1377 (has_generic_params, def_kind)
1378 }
1379 };
1380
1381 // This was an attempt to use a const parameter outside its scope.
1382 if let Some(span) = finalize {
1383 self.report_error(
1384 span,
1385 ResolutionError::GenericParamsFromOuterItem(
1386 res,
1387 has_generic_params,
1388 def_kind,
1389 ),
1390 );
1391 }
1392 return Res::Err;
1393 }
1394 }
1395 _ => {}
1396 }
1397
1398 res
1399 }
1400
1401 #[instrument(level = "debug", skip(self))]
1402 pub(crate) fn maybe_resolve_path(
1403 &mut self,
1404 path: &[Segment],
1405 opt_ns: Option<Namespace>, // `None` indicates a module path in import
1406 parent_scope: &ParentScope<'ra>,
1407 ignore_import: Option<Import<'ra>>,
1408 ) -> PathResult<'ra> {
1409 self.resolve_path_with_ribs(path, opt_ns, parent_scope, None, None, None, ignore_import)
1410 }
1411
1412 #[instrument(level = "debug", skip(self))]
1413 pub(crate) fn resolve_path(
1414 &mut self,
1415 path: &[Segment],
1416 opt_ns: Option<Namespace>, // `None` indicates a module path in import
1417 parent_scope: &ParentScope<'ra>,
1418 finalize: Option<Finalize>,
1419 ignore_binding: Option<NameBinding<'ra>>,
1420 ignore_import: Option<Import<'ra>>,
1421 ) -> PathResult<'ra> {
1422 self.resolve_path_with_ribs(
1423 path,
1424 opt_ns,
1425 parent_scope,
1426 finalize,
1427 None,
1428 ignore_binding,
1429 ignore_import,
1430 )
1431 }
1432
1433 pub(crate) fn resolve_path_with_ribs(
1434 &mut self,
1435 path: &[Segment],
1436 opt_ns: Option<Namespace>, // `None` indicates a module path in import
1437 parent_scope: &ParentScope<'ra>,
1438 finalize: Option<Finalize>,
1439 ribs: Option<&PerNS<Vec<Rib<'ra>>>>,
1440 ignore_binding: Option<NameBinding<'ra>>,
1441 ignore_import: Option<Import<'ra>>,
1442 ) -> PathResult<'ra> {
1443 let mut module = None;
1444 let mut module_had_parse_errors = false;
1445 let mut allow_super = true;
1446 let mut second_binding = None;
1447
1448 // We'll provide more context to the privacy errors later, up to `len`.
1449 let privacy_errors_len = self.privacy_errors.len();
1450
1451 for (segment_idx, &Segment { ident, id, .. }) in path.iter().enumerate() {
1452 debug!("resolve_path ident {} {:?} {:?}", segment_idx, ident, id);
1453 let record_segment_res = |this: &mut Self, res| {
1454 if finalize.is_some()
1455 && let Some(id) = id
1456 && !this.partial_res_map.contains_key(&id)
1457 {
1458 assert!(id != ast::DUMMY_NODE_ID, "Trying to resolve dummy id");
1459 this.record_partial_res(id, PartialRes::new(res));
1460 }
1461 };
1462
1463 let is_last = segment_idx + 1 == path.len();
1464 let ns = if is_last { opt_ns.unwrap_or(TypeNS) } else { TypeNS };
1465 let name = ident.name;
1466
1467 allow_super &= ns == TypeNS && (name == kw::SelfLower || name == kw::Super);
1468
1469 if ns == TypeNS {
1470 if allow_super && name == kw::Super {
1471 let mut ctxt = ident.span.ctxt().normalize_to_macros_2_0();
1472 let self_module = match segment_idx {
1473 0 => Some(self.resolve_self(&mut ctxt, parent_scope.module)),
1474 _ => match module {
1475 Some(ModuleOrUniformRoot::Module(module)) => Some(module),
1476 _ => None,
1477 },
1478 };
1479 if let Some(self_module) = self_module
1480 && let Some(parent) = self_module.parent
1481 {
1482 module =
1483 Some(ModuleOrUniformRoot::Module(self.resolve_self(&mut ctxt, parent)));
1484 continue;
1485 }
1486 return PathResult::failed(
1487 ident,
1488 false,
1489 finalize.is_some(),
1490 module_had_parse_errors,
1491 module,
1492 || ("there are too many leading `super` keywords".to_string(), None),
1493 );
1494 }
1495 if segment_idx == 0 {
1496 if name == kw::SelfLower {
1497 let mut ctxt = ident.span.ctxt().normalize_to_macros_2_0();
1498 let self_mod = self.resolve_self(&mut ctxt, parent_scope.module);
1499 if let Some(res) = self_mod.res() {
1500 record_segment_res(self, res);
1501 }
1502 module = Some(ModuleOrUniformRoot::Module(self_mod));
1503 continue;
1504 }
1505 if name == kw::PathRoot && ident.span.at_least_rust_2018() {
1506 module = Some(ModuleOrUniformRoot::ExternPrelude);
1507 continue;
1508 }
1509 if name == kw::PathRoot
1510 && ident.span.is_rust_2015()
1511 && self.tcx.sess.at_least_rust_2018()
1512 {
1513 // `::a::b` from 2015 macro on 2018 global edition
1514 module = Some(ModuleOrUniformRoot::CrateRootAndExternPrelude);
1515 continue;
1516 }
1517 if name == kw::PathRoot || name == kw::Crate || name == kw::DollarCrate {
1518 // `::a::b`, `crate::a::b` or `$crate::a::b`
1519 let crate_root = self.resolve_crate_root(ident);
1520 if let Some(res) = crate_root.res() {
1521 record_segment_res(self, res);
1522 }
1523 module = Some(ModuleOrUniformRoot::Module(crate_root));
1524 continue;
1525 }
1526 }
1527 }
1528
1529 // Report special messages for path segment keywords in wrong positions.
1530 if ident.is_path_segment_keyword() && segment_idx != 0 {
1531 return PathResult::failed(
1532 ident,
1533 false,
1534 finalize.is_some(),
1535 module_had_parse_errors,
1536 module,
1537 || {
1538 let name_str = if name == kw::PathRoot {
1539 "crate root".to_string()
1540 } else {
1541 format!("`{name}`")
1542 };
1543 let label = if segment_idx == 1 && path[0].ident.name == kw::PathRoot {
1544 format!("global paths cannot start with {name_str}")
1545 } else {
1546 format!("{name_str} in paths can only be used in start position")
1547 };
1548 (label, None)
1549 },
1550 );
1551 }
1552
1553 let binding = if let Some(module) = module {
1554 self.resolve_ident_in_module(
1555 module,
1556 ident,
1557 ns,
1558 parent_scope,
1559 finalize,
1560 ignore_binding,
1561 ignore_import,
1562 )
1563 .map_err(|(determinacy, _)| determinacy)
1564 } else if let Some(ribs) = ribs
1565 && let Some(TypeNS | ValueNS) = opt_ns
1566 {
1567 assert!(ignore_import.is_none());
1568 match self.resolve_ident_in_lexical_scope(
1569 ident,
1570 ns,
1571 parent_scope,
1572 finalize,
1573 &ribs[ns],
1574 ignore_binding,
1575 ) {
1576 // we found a locally-imported or available item/module
1577 Some(LexicalScopeBinding::Item(binding)) => Ok(binding),
1578 // we found a local variable or type param
1579 Some(LexicalScopeBinding::Res(res)) => {
1580 record_segment_res(self, res);
1581 return PathResult::NonModule(PartialRes::with_unresolved_segments(
1582 res,
1583 path.len() - 1,
1584 ));
1585 }
1586 _ => Err(Determinacy::determined(finalize.is_some())),
1587 }
1588 } else {
1589 self.early_resolve_ident_in_lexical_scope(
1590 ident,
1591 ScopeSet::All(ns),
1592 parent_scope,
1593 finalize,
1594 finalize.is_some(),
1595 ignore_binding,
1596 ignore_import,
1597 )
1598 };
1599
1600 match binding {
1601 Ok(binding) => {
1602 if segment_idx == 1 {
1603 second_binding = Some(binding);
1604 }
1605 let res = binding.res();
1606
1607 // Mark every privacy error in this path with the res to the last element. This allows us
1608 // to detect the item the user cares about and either find an alternative import, or tell
1609 // the user it is not accessible.
1610 for error in &mut self.privacy_errors[privacy_errors_len..] {
1611 error.outermost_res = Some((res, ident));
1612 }
1613
1614 let maybe_assoc = opt_ns != Some(MacroNS) && PathSource::Type.is_expected(res);
1615 if let Some(next_module) = binding.module() {
1616 if self.mods_with_parse_errors.contains(&next_module.def_id()) {
1617 module_had_parse_errors = true;
1618 }
1619 module = Some(ModuleOrUniformRoot::Module(next_module));
1620 record_segment_res(self, res);
1621 } else if res == Res::ToolMod && !is_last && opt_ns.is_some() {
1622 if binding.is_import() {
1623 self.dcx().emit_err(errors::ToolModuleImported {
1624 span: ident.span,
1625 import: binding.span,
1626 });
1627 }
1628 let res = Res::NonMacroAttr(NonMacroAttrKind::Tool);
1629 return PathResult::NonModule(PartialRes::new(res));
1630 } else if res == Res::Err {
1631 return PathResult::NonModule(PartialRes::new(Res::Err));
1632 } else if opt_ns.is_some() && (is_last || maybe_assoc) {
1633 self.lint_if_path_starts_with_module(finalize, path, second_binding);
1634 record_segment_res(self, res);
1635 return PathResult::NonModule(PartialRes::with_unresolved_segments(
1636 res,
1637 path.len() - segment_idx - 1,
1638 ));
1639 } else {
1640 return PathResult::failed(
1641 ident,
1642 is_last,
1643 finalize.is_some(),
1644 module_had_parse_errors,
1645 module,
1646 || {
1647 let label = format!(
1648 "`{ident}` is {} {}, not a module",
1649 res.article(),
1650 res.descr()
1651 );
1652 (label, None)
1653 },
1654 );
1655 }
1656 }
1657 Err(Undetermined) => return PathResult::Indeterminate,
1658 Err(Determined) => {
1659 if let Some(ModuleOrUniformRoot::Module(module)) = module
1660 && opt_ns.is_some()
1661 && !module.is_normal()
1662 {
1663 return PathResult::NonModule(PartialRes::with_unresolved_segments(
1664 module.res().unwrap(),
1665 path.len() - segment_idx,
1666 ));
1667 }
1668
1669 return PathResult::failed(
1670 ident,
1671 is_last,
1672 finalize.is_some(),
1673 module_had_parse_errors,
1674 module,
1675 || {
1676 self.report_path_resolution_error(
1677 path,
1678 opt_ns,
1679 parent_scope,
1680 ribs,
1681 ignore_binding,
1682 ignore_import,
1683 module,
1684 segment_idx,
1685 ident,
1686 )
1687 },
1688 );
1689 }
1690 }
1691 }
1692
1693 self.lint_if_path_starts_with_module(finalize, path, second_binding);
1694
1695 PathResult::Module(match module {
1696 Some(module) => module,
1697 None if path.is_empty() => ModuleOrUniformRoot::CurrentScope,
1698 _ => bug!("resolve_path: non-empty path `{:?}` has no module", path),
1699 })
1700 }
1701}