Do not modify resolver outputs during lowering

Co-authored-by: Camille Gillot <gillot.camille@gmail.com>
This commit is contained in:
Camille Gillot
2026-04-17 20:05:28 +00:00
parent 7c61a357e3
commit 0705bbac94
15 changed files with 121 additions and 238 deletions
+2 -5
View File
@@ -18,11 +18,9 @@
InvalidRegisterClass, RegisterClassOnlyClobber, RegisterClassOnlyClobberStable, InvalidRegisterClass, RegisterClassOnlyClobber, RegisterClassOnlyClobberStable,
RegisterConflict, RegisterConflict,
}; };
use crate::{ use crate::{AllowReturnTypeNotation, ImplTraitContext, ImplTraitPosition, ParamMode};
AllowReturnTypeNotation, ImplTraitContext, ImplTraitPosition, ParamMode, ResolverAstLoweringExt,
};
impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> { impl<'hir> LoweringContext<'_, 'hir> {
pub(crate) fn lower_inline_asm( pub(crate) fn lower_inline_asm(
&mut self, &mut self,
sp: Span, sp: Span,
@@ -203,7 +201,6 @@ pub(crate) fn lower_inline_asm(
}, },
InlineAsmOperand::Sym { sym } => { InlineAsmOperand::Sym { sym } => {
let static_def_id = self let static_def_id = self
.resolver
.get_partial_res(sym.id) .get_partial_res(sym.id)
.and_then(|res| res.full_res()) .and_then(|res| res.full_res())
.and_then(|res| match res { .and_then(|res| match res {
+2 -2
View File
@@ -4,9 +4,9 @@
use rustc_span::sym; use rustc_span::sym;
use smallvec::SmallVec; use smallvec::SmallVec;
use crate::{ImplTraitContext, ImplTraitPosition, LoweringContext, ResolverAstLoweringExt}; use crate::{ImplTraitContext, ImplTraitPosition, LoweringContext};
impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> { impl<'hir> LoweringContext<'_, 'hir> {
pub(super) fn lower_block( pub(super) fn lower_block(
&mut self, &mut self,
b: &Block, b: &Block,
+2 -2
View File
@@ -2,9 +2,9 @@
use thin_vec::thin_vec; use thin_vec::thin_vec;
use crate::{LoweringContext, ResolverAstLoweringExt}; use crate::LoweringContext;
impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> { impl<'hir> LoweringContext<'_, 'hir> {
/// Lowered contracts are guarded with the `contract_checks` compiler flag, /// Lowered contracts are guarded with the `contract_checks` compiler flag,
/// i.e. the flag turns into a boolean guard in the lowered HIR. The reason /// i.e. the flag turns into a boolean guard in the lowered HIR. The reason
/// for not eliminating the contract code entirely when the `contract_checks` /// for not eliminating the contract code entirely when the `contract_checks`
@@ -105,7 +105,7 @@ enum AttrAdditionKind {
}, },
]; ];
impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> { impl<'hir> LoweringContext<'_, 'hir> {
fn is_method(&self, def_id: DefId, span: Span) -> bool { fn is_method(&self, def_id: DefId, span: Span) -> bool {
match self.tcx.def_kind(def_id) { match self.tcx.def_kind(def_id) {
DefKind::Fn => false, DefKind::Fn => false,
@@ -266,7 +266,7 @@ fn get_sig_id(&self, mut node_id: NodeId, span: Span) -> Result<DefId, ErrorGuar
} }
fn get_resolution_id(&self, node_id: NodeId) -> Option<DefId> { fn get_resolution_id(&self, node_id: NodeId) -> Option<DefId> {
self.resolver.get_partial_res(node_id).and_then(|r| r.expect_full_res().opt_def_id()) self.get_partial_res(node_id).and_then(|r| r.expect_full_res().opt_def_id())
} }
// Function parameter count, including C variadic `...` if present. // Function parameter count, including C variadic `...` if present.
@@ -417,7 +417,7 @@ fn lower_delegation_body(
&& idx == 0 && idx == 0
{ {
let mut self_resolver = SelfResolver { let mut self_resolver = SelfResolver {
resolver: this.resolver, ctxt: this,
path_id: delegation.id, path_id: delegation.id,
self_param_id: pat_node_id, self_param_id: pat_node_id,
}; };
@@ -665,25 +665,25 @@ fn mk_expr(&mut self, kind: hir::ExprKind<'hir>, span: Span) -> hir::Expr<'hir>
} }
} }
struct SelfResolver<'a, R> { struct SelfResolver<'a, 'b, 'hir> {
resolver: &'a mut R, ctxt: &'a mut LoweringContext<'b, 'hir>,
path_id: NodeId, path_id: NodeId,
self_param_id: NodeId, self_param_id: NodeId,
} }
impl<'tcx, R: ResolverAstLoweringExt<'tcx>> SelfResolver<'_, R> { impl SelfResolver<'_, '_, '_> {
fn try_replace_id(&mut self, id: NodeId) { fn try_replace_id(&mut self, id: NodeId) {
if let Some(res) = self.resolver.get_partial_res(id) if let Some(res) = self.ctxt.get_partial_res(id)
&& let Some(Res::Local(sig_id)) = res.full_res() && let Some(Res::Local(sig_id)) = res.full_res()
&& sig_id == self.path_id && sig_id == self.path_id
{ {
let new_res = PartialRes::new(Res::Local(self.self_param_id)); let new_res = PartialRes::new(Res::Local(self.self_param_id));
self.resolver.insert_partial_res(id, new_res); self.ctxt.partial_res_overrides.insert(id, new_res);
} }
} }
} }
impl<'ast, 'tcx, R: ResolverAstLoweringExt<'tcx>> Visitor<'ast> for SelfResolver<'_, R> { impl<'ast> Visitor<'ast> for SelfResolver<'_, '_, '_> {
fn visit_id(&mut self, id: NodeId) { fn visit_id(&mut self, id: NodeId) {
self.try_replace_id(id); self.try_replace_id(id);
} }
@@ -8,7 +8,7 @@
use rustc_span::symbol::kw; use rustc_span::symbol::kw;
use rustc_span::{Ident, Span, sym}; use rustc_span::{Ident, Span, sym};
use crate::{LoweringContext, ResolverAstLoweringExt}; use crate::LoweringContext;
#[derive(Clone, Copy)] #[derive(Clone, Copy)]
pub(super) enum DelegationGenericsKind { pub(super) enum DelegationGenericsKind {
@@ -114,7 +114,7 @@ fn args_propagation_details(self) -> GenericArgsPropagationDetails {
impl<'hir> HirOrTyGenerics<'hir> { impl<'hir> HirOrTyGenerics<'hir> {
pub(super) fn into_hir_generics( pub(super) fn into_hir_generics(
&mut self, &mut self,
ctx: &mut LoweringContext<'_, 'hir, impl ResolverAstLoweringExt<'hir>>, ctx: &mut LoweringContext<'_, 'hir>,
span: Span, span: Span,
) -> &mut HirOrTyGenerics<'hir> { ) -> &mut HirOrTyGenerics<'hir> {
if let HirOrTyGenerics::Ty(ty) = self { if let HirOrTyGenerics::Ty(ty) = self {
@@ -140,7 +140,7 @@ fn hir_generics_or_empty(&self) -> &'hir hir::Generics<'hir> {
pub(super) fn into_generic_args( pub(super) fn into_generic_args(
&self, &self,
ctx: &mut LoweringContext<'_, 'hir, impl ResolverAstLoweringExt<'hir>>, ctx: &mut LoweringContext<'_, 'hir>,
span: Span, span: Span,
) -> &'hir hir::GenericArgs<'hir> { ) -> &'hir hir::GenericArgs<'hir> {
match self { match self {
@@ -174,7 +174,7 @@ impl<'hir> GenericsGenerationResults<'hir> {
pub(super) fn all_params( pub(super) fn all_params(
&mut self, &mut self,
span: Span, span: Span,
ctx: &mut LoweringContext<'_, 'hir, impl ResolverAstLoweringExt<'hir>>, ctx: &mut LoweringContext<'_, 'hir>,
) -> impl Iterator<Item = hir::GenericParam<'hir>> { ) -> impl Iterator<Item = hir::GenericParam<'hir>> {
// Now we always call `into_hir_generics` both on child and parent, // Now we always call `into_hir_generics` both on child and parent,
// however in future we would not do that, when scenarios like // however in future we would not do that, when scenarios like
@@ -208,7 +208,7 @@ pub(super) fn all_params(
pub(super) fn all_predicates( pub(super) fn all_predicates(
&mut self, &mut self,
span: Span, span: Span,
ctx: &mut LoweringContext<'_, 'hir, impl ResolverAstLoweringExt<'hir>>, ctx: &mut LoweringContext<'_, 'hir>,
) -> impl Iterator<Item = hir::WherePredicate<'hir>> { ) -> impl Iterator<Item = hir::WherePredicate<'hir>> {
// Now we always call `into_hir_generics` both on child and parent, // Now we always call `into_hir_generics` both on child and parent,
// however in future we would not do that, when scenarios like // however in future we would not do that, when scenarios like
@@ -226,7 +226,7 @@ pub(super) fn all_predicates(
} }
} }
impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> { impl<'hir> LoweringContext<'_, 'hir> {
pub(super) fn uplift_delegation_generics( pub(super) fn uplift_delegation_generics(
&mut self, &mut self,
delegation: &Delegation, delegation: &Delegation,
+4 -7
View File
@@ -51,7 +51,7 @@ fn visit_expr(&mut self, ex: &'v Expr) -> Self::Result {
} }
} }
impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> { impl<'hir> LoweringContext<'_, 'hir> {
fn lower_exprs(&mut self, exprs: &[Box<Expr>]) -> &'hir [hir::Expr<'hir>] { fn lower_exprs(&mut self, exprs: &[Box<Expr>]) -> &'hir [hir::Expr<'hir>] {
self.arena.alloc_from_iter(exprs.iter().map(|x| self.lower_expr_mut(x))) self.arena.alloc_from_iter(exprs.iter().map(|x| self.lower_expr_mut(x)))
} }
@@ -1235,10 +1235,7 @@ fn lower_expr_assign(
whole_span: Span, whole_span: Span,
) -> hir::ExprKind<'hir> { ) -> hir::ExprKind<'hir> {
// Return early in case of an ordinary assignment. // Return early in case of an ordinary assignment.
fn is_ordinary<'hir>( fn is_ordinary(lower_ctx: &mut LoweringContext<'_, '_>, lhs: &Expr) -> bool {
lower_ctx: &mut LoweringContext<'_, 'hir, impl ResolverAstLoweringExt<'hir>>,
lhs: &Expr,
) -> bool {
match &lhs.kind { match &lhs.kind {
ExprKind::Array(..) ExprKind::Array(..)
| ExprKind::Struct(..) | ExprKind::Struct(..)
@@ -1293,7 +1290,7 @@ fn extract_tuple_struct_path<'a>(
) -> Option<(&'a Option<Box<QSelf>>, &'a Path)> { ) -> Option<(&'a Option<Box<QSelf>>, &'a Path)> {
if let ExprKind::Path(qself, path) = &expr.kind { if let ExprKind::Path(qself, path) = &expr.kind {
// Does the path resolve to something disallowed in a tuple struct/variant pattern? // Does the path resolve to something disallowed in a tuple struct/variant pattern?
if let Some(partial_res) = self.resolver.get_partial_res(expr.id) { if let Some(partial_res) = self.get_partial_res(expr.id) {
if let Some(res) = partial_res.full_res() if let Some(res) = partial_res.full_res()
&& !res.expected_in_tuple_struct_pat() && !res.expected_in_tuple_struct_pat()
{ {
@@ -1315,7 +1312,7 @@ fn extract_unit_struct_path<'a>(
) -> Option<(&'a Option<Box<QSelf>>, &'a Path)> { ) -> Option<(&'a Option<Box<QSelf>>, &'a Path)> {
if let ExprKind::Path(qself, path) = &expr.kind { if let ExprKind::Path(qself, path) = &expr.kind {
// Does the path resolve to something disallowed in a unit struct/variant pattern? // Does the path resolve to something disallowed in a unit struct/variant pattern?
if let Some(partial_res) = self.resolver.get_partial_res(expr.id) { if let Some(partial_res) = self.get_partial_res(expr.id) {
if let Some(res) = partial_res.full_res() if let Some(res) = partial_res.full_res()
&& !res.expected_in_unit_struct_pat() && !res.expected_in_unit_struct_pat()
{ {
+3 -4
View File
@@ -7,9 +7,8 @@
use rustc_span::{ByteSymbol, DesugaringKind, Ident, Span, Symbol, sym}; use rustc_span::{ByteSymbol, DesugaringKind, Ident, Span, Symbol, sym};
use super::LoweringContext; use super::LoweringContext;
use crate::ResolverAstLoweringExt;
impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> { impl<'hir> LoweringContext<'_, 'hir> {
pub(crate) fn lower_format_args(&mut self, sp: Span, fmt: &FormatArgs) -> hir::ExprKind<'hir> { pub(crate) fn lower_format_args(&mut self, sp: Span, fmt: &FormatArgs) -> hir::ExprKind<'hir> {
// Never call the const constructor of `fmt::Arguments` if the // Never call the const constructor of `fmt::Arguments` if the
// format_args!() had any arguments _before_ flattening/inlining. // format_args!() had any arguments _before_ flattening/inlining.
@@ -231,7 +230,7 @@ enum ArgumentType {
/// <core::fmt::Argument>::new_…(arg) /// <core::fmt::Argument>::new_…(arg)
/// ``` /// ```
fn make_argument<'hir>( fn make_argument<'hir>(
ctx: &mut LoweringContext<'_, 'hir, impl ResolverAstLoweringExt<'hir>>, ctx: &mut LoweringContext<'_, 'hir>,
sp: Span, sp: Span,
arg: &'hir hir::Expr<'hir>, arg: &'hir hir::Expr<'hir>,
ty: ArgumentType, ty: ArgumentType,
@@ -278,7 +277,7 @@ fn make_count(
} }
fn expand_format_args<'hir>( fn expand_format_args<'hir>(
ctx: &mut LoweringContext<'_, 'hir, impl ResolverAstLoweringExt<'hir>>, ctx: &mut LoweringContext<'_, 'hir>,
macsp: Span, macsp: Span,
fmt: &FormatArgs, fmt: &FormatArgs,
allow_const: bool, allow_const: bool,
+14 -28
View File
@@ -1,22 +1,19 @@
use std::mem; use std::mem;
use std::sync::Arc;
use rustc_abi::ExternAbi; use rustc_abi::ExternAbi;
use rustc_ast::visit::AssocCtxt; use rustc_ast::visit::AssocCtxt;
use rustc_ast::*; use rustc_ast::*;
use rustc_data_structures::fx::FxIndexMap; use rustc_data_structures::fx::FxIndexMap;
use rustc_data_structures::steal::Steal;
use rustc_errors::{E0570, ErrorGuaranteed, struct_span_code_err}; use rustc_errors::{E0570, ErrorGuaranteed, struct_span_code_err};
use rustc_hir::attrs::{AttributeKind, EiiImplResolution}; use rustc_hir::attrs::{AttributeKind, EiiImplResolution};
use rustc_hir::def::{DefKind, PerNS, Res}; use rustc_hir::def::{DefKind, PerNS, Res};
use rustc_hir::def_id::{CRATE_DEF_ID, LocalDefId, LocalDefIdMap}; use rustc_hir::def_id::{CRATE_DEF_ID, LocalDefId};
use rustc_hir::definitions::PerParentDisambiguatorState;
use rustc_hir::{ use rustc_hir::{
self as hir, HirId, ImplItemImplKind, LifetimeSource, PredicateOrigin, Target, find_attr, self as hir, HirId, ImplItemImplKind, LifetimeSource, PredicateOrigin, Target, find_attr,
}; };
use rustc_index::{IndexSlice, IndexVec}; use rustc_index::{IndexSlice, IndexVec};
use rustc_middle::span_bug; use rustc_middle::span_bug;
use rustc_middle::ty::TyCtxt; use rustc_middle::ty::{ResolverAstLowering, TyCtxt};
use rustc_span::def_id::DefId; use rustc_span::def_id::DefId;
use rustc_span::edit_distance::find_best_match_for_name; use rustc_span::edit_distance::find_best_match_for_name;
use rustc_span::{DUMMY_SP, DesugaringKind, Ident, Span, Symbol, kw, sym}; use rustc_span::{DUMMY_SP, DesugaringKind, Ident, Span, Symbol, kw, sym};
@@ -51,21 +48,11 @@ fn get_or_insert_mut(&mut self, def_id: LocalDefId) -> &mut hir::MaybeOwner<'hir
} }
} }
/// Default disambiguators are used during default lowering, when we lower pub(super) struct ItemLowerer<'a, 'hir> {
/// AST owners in a loop we can use the whole map, in contrast delayed lowering
/// lowers each AST owner separately, so we use readonly disambiguators map
/// with `Steal`s to get disambiguators.
pub(super) enum Disambiguators {
Default(LocalDefIdMap<PerParentDisambiguatorState>),
Delayed(Arc<LocalDefIdMap<Steal<PerParentDisambiguatorState>>>),
}
pub(super) struct ItemLowerer<'a, 'hir, R> {
pub(super) tcx: TyCtxt<'hir>, pub(super) tcx: TyCtxt<'hir>,
pub(super) resolver: &'a mut R, pub(super) resolver: &'a ResolverAstLowering<'hir>,
pub(super) ast_index: &'a IndexSlice<LocalDefId, AstOwner<'a>>, pub(super) ast_index: &'a IndexSlice<LocalDefId, AstOwner<'a>>,
pub(super) owners: Owners<'a, 'hir>, pub(super) owners: Owners<'a, 'hir>,
pub(super) disambiguators: &'a mut Disambiguators,
} }
/// When we have a ty alias we *may* have two where clauses. To give the best diagnostics, we set the span /// When we have a ty alias we *may* have two where clauses. To give the best diagnostics, we set the span
@@ -87,13 +74,13 @@ fn add_ty_alias_where_clause(
if before.0 || !after.0 { before } else { after }; if before.0 || !after.0 { before } else { after };
} }
impl<'hir, R: ResolverAstLoweringExt<'hir>> ItemLowerer<'_, 'hir, R> { impl<'hir> ItemLowerer<'_, 'hir> {
fn with_lctx( fn with_lctx(
&mut self, &mut self,
owner: NodeId, owner: NodeId,
f: impl FnOnce(&mut LoweringContext<'_, 'hir, R>) -> hir::OwnerNode<'hir>, f: impl for<'a> FnOnce(&mut LoweringContext<'a, 'hir>) -> hir::OwnerNode<'hir>,
) { ) {
let mut lctx = LoweringContext::new(self.tcx, self.resolver, self.disambiguators); let mut lctx = LoweringContext::new(self.tcx, self.resolver);
lctx.with_hir_id_owner(owner, |lctx| f(lctx)); lctx.with_hir_id_owner(owner, |lctx| f(lctx));
for (def_id, info) in lctx.children { for (def_id, info) in lctx.children {
@@ -135,7 +122,7 @@ pub(super) fn lower_node(&mut self, def_id: LocalDefId) {
} }
} }
impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> { impl<'hir> LoweringContext<'_, 'hir> {
pub(super) fn lower_mod( pub(super) fn lower_mod(
&mut self, &mut self,
items: &[Box<Item>], items: &[Box<Item>],
@@ -648,7 +635,7 @@ fn lower_item_kind(
} }
fn lower_path_simple_eii(&mut self, id: NodeId, path: &Path) -> Option<DefId> { fn lower_path_simple_eii(&mut self, id: NodeId, path: &Path) -> Option<DefId> {
let res = self.resolver.get_partial_res(id)?; let res = self.get_partial_res(id)?;
let Some(did) = res.expect_full_res().opt_def_id() else { let Some(did) = res.expect_full_res().opt_def_id() else {
self.dcx().span_delayed_bug(path.span, "should have errored in resolve"); self.dcx().span_delayed_bug(path.span, "should have errored in resolve");
return None; return None;
@@ -1349,7 +1336,6 @@ fn lower_impl_item(
ImplItemImplKind::Trait { ImplItemImplKind::Trait {
defaultness, defaultness,
trait_item_def_id: self trait_item_def_id: self
.resolver
.get_partial_res(i.id) .get_partial_res(i.id)
.and_then(|r| r.expect_full_res().opt_def_id()) .and_then(|r| r.expect_full_res().opt_def_id())
.ok_or_else(|| { .ok_or_else(|| {
@@ -1545,7 +1531,7 @@ fn lower_maybe_coroutine_body(
pub(crate) fn lower_coroutine_body_with_moved_arguments( pub(crate) fn lower_coroutine_body_with_moved_arguments(
&mut self, &mut self,
decl: &FnDecl, decl: &FnDecl,
lower_body: impl FnOnce(&mut LoweringContext<'_, 'hir, R>) -> hir::Expr<'hir>, lower_body: impl FnOnce(&mut LoweringContext<'_, 'hir>) -> hir::Expr<'hir>,
fn_decl_span: Span, fn_decl_span: Span,
body_span: Span, body_span: Span,
coroutine_kind: CoroutineKind, coroutine_kind: CoroutineKind,
@@ -1682,7 +1668,7 @@ pub(crate) fn lower_coroutine_body_with_moved_arguments(
parameters.push(new_parameter); parameters.push(new_parameter);
} }
let mkbody = |this: &mut LoweringContext<'_, 'hir, R>| { let mkbody = |this: &mut LoweringContext<'_, 'hir>| {
// Create a block from the user's function body: // Create a block from the user's function body:
let user_body = lower_body(this); let user_body = lower_body(this);
@@ -1867,7 +1853,7 @@ pub(super) fn lower_impl_restriction(
let kind = match &r.kind { let kind = match &r.kind {
RestrictionKind::Unrestricted => hir::RestrictionKind::Unrestricted, RestrictionKind::Unrestricted => hir::RestrictionKind::Unrestricted,
RestrictionKind::Restricted { path, id, shorthand: _ } => { RestrictionKind::Restricted { path, id, shorthand: _ } => {
let res = self.resolver.get_partial_res(*id); let res = self.get_partial_res(*id);
if let Some(did) = res.and_then(|res| res.expect_full_res().opt_def_id()) { if let Some(did) = res.and_then(|res| res.expect_full_res().opt_def_id()) {
hir::RestrictionKind::Restricted(self.arena.alloc(hir::Path { hir::RestrictionKind::Restricted(self.arena.alloc(hir::Path {
res: did, res: did,
@@ -1933,7 +1919,7 @@ fn lower_generics<T>(
// Introduce extra lifetimes if late resolution tells us to. // Introduce extra lifetimes if late resolution tells us to.
let extra_lifetimes = self.resolver.extra_lifetime_params(parent_node_id); let extra_lifetimes = self.resolver.extra_lifetime_params(parent_node_id);
params.extend(extra_lifetimes.into_iter().filter_map(|(ident, node_id, res)| { params.extend(extra_lifetimes.into_iter().filter_map(|&(ident, node_id, res)| {
self.lifetime_res_to_generic_param( self.lifetime_res_to_generic_param(
ident, ident,
node_id, node_id,
@@ -1975,7 +1961,7 @@ pub(super) fn lower_define_opaque(
return; return;
}; };
let define_opaque = define_opaque.iter().filter_map(|(id, path)| { let define_opaque = define_opaque.iter().filter_map(|(id, path)| {
let res = self.resolver.get_partial_res(*id); let res = self.get_partial_res(*id);
let Some(did) = res.and_then(|res| res.expect_full_res().opt_def_id()) else { let Some(did) = res.and_then(|res| res.expect_full_res().opt_def_id()) else {
self.dcx().span_delayed_bug(path.span, "should have errored in resolve"); self.dcx().span_delayed_bug(path.span, "should have errored in resolve");
return None; return None;
+61 -153
View File
@@ -70,7 +70,7 @@
use tracing::{debug, instrument, trace}; use tracing::{debug, instrument, trace};
use crate::errors::{AssocTyParentheses, AssocTyParenthesesSub, MisplacedImplTrait}; use crate::errors::{AssocTyParentheses, AssocTyParenthesesSub, MisplacedImplTrait};
use crate::item::{Disambiguators, Owners}; use crate::item::Owners;
macro_rules! arena_vec { macro_rules! arena_vec {
($this:expr; $($x:expr),*) => ( ($this:expr; $($x:expr),*) => (
@@ -91,10 +91,9 @@ macro_rules! arena_vec {
mod path; mod path;
pub mod stability; pub mod stability;
struct LoweringContext<'a, 'hir, R> { struct LoweringContext<'a, 'hir> {
tcx: TyCtxt<'hir>, tcx: TyCtxt<'hir>,
resolver: &'a mut R, resolver: &'a ResolverAstLowering<'hir>,
disambiguators: &'a mut Disambiguators,
current_disambiguator: PerParentDisambiguatorState, current_disambiguator: PerParentDisambiguatorState,
/// Used to allocate HIR nodes. /// Used to allocate HIR nodes.
@@ -139,6 +138,14 @@ struct LoweringContext<'a, 'hir, R> {
/// NodeIds that are lowered inside the current HIR owner. Only used for duplicate lowering check. /// NodeIds that are lowered inside the current HIR owner. Only used for duplicate lowering check.
#[cfg(debug_assertions)] #[cfg(debug_assertions)]
node_id_to_local_id: NodeMap<hir::ItemLocalId>, node_id_to_local_id: NodeMap<hir::ItemLocalId>,
/// The `NodeId` space is split in two.
/// `0..resolver.next_node_id` are created by the resolver on the AST.
/// The higher part `resolver.next_node_id..next_node_id` are created during lowering.
next_node_id: NodeId,
/// Maps the `NodeId`s created during lowering to `LocalDefId`s.
node_id_to_def_id: NodeMap<LocalDefId>,
/// Overlay over resolver's `partial_res_map` used by delegation.
partial_res_overrides: NodeMap<PartialRes>,
allow_contracts: Arc<[Symbol]>, allow_contracts: Arc<[Symbol]>,
allow_try_trait: Arc<[Symbol]>, allow_try_trait: Arc<[Symbol]>,
@@ -154,13 +161,12 @@ struct LoweringContext<'a, 'hir, R> {
attribute_parser: AttributeParser<'hir>, attribute_parser: AttributeParser<'hir>,
} }
impl<'a, 'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'a, 'hir, R> { impl<'a, 'hir> LoweringContext<'a, 'hir> {
fn new(tcx: TyCtxt<'hir>, resolver: &'a mut R, disambiguators: &'a mut Disambiguators) -> Self { fn new(tcx: TyCtxt<'hir>, resolver: &'a ResolverAstLowering<'hir>) -> Self {
let registered_tools = tcx.registered_tools(()).iter().map(|x| x.name).collect(); let registered_tools = tcx.registered_tools(()).iter().map(|x| x.name).collect();
Self { Self {
tcx, tcx,
resolver, resolver,
disambiguators,
current_disambiguator: Default::default(), current_disambiguator: Default::default(),
arena: tcx.hir_arena, arena: tcx.hir_arena,
@@ -176,6 +182,9 @@ fn new(tcx: TyCtxt<'hir>, resolver: &'a mut R, disambiguators: &'a mut Disambigu
#[cfg(debug_assertions)] #[cfg(debug_assertions)]
node_id_to_local_id: Default::default(), node_id_to_local_id: Default::default(),
trait_map: Default::default(), trait_map: Default::default(),
next_node_id: resolver.next_node_id,
node_id_to_def_id: NodeMap::default(),
partial_res_overrides: NodeMap::default(),
// Lowering state. // Lowering state.
try_block_scope: TryBlockScope::Function, try_block_scope: TryBlockScope::Function,
@@ -239,81 +248,6 @@ fn lower(&self, span: Span) -> Span {
} }
} }
struct ResolverDelayedAstLowering<'a, 'tcx> {
node_id_to_def_id: NodeMap<LocalDefId>,
partial_res_map: NodeMap<PartialRes>,
next_node_id: NodeId,
base: &'a ResolverAstLowering<'tcx>,
}
// FIXME(fn_delegation): delegate this trait impl to `self.base`
impl<'a, 'tcx> ResolverAstLoweringExt<'tcx> for ResolverDelayedAstLowering<'a, 'tcx> {
fn legacy_const_generic_args(&self, expr: &Expr, tcx: TyCtxt<'tcx>) -> Option<Vec<usize>> {
self.base.legacy_const_generic_args(expr, tcx)
}
fn get_partial_res(&self, id: NodeId) -> Option<PartialRes> {
self.partial_res_map.get(&id).copied().or_else(|| self.base.get_partial_res(id))
}
fn get_import_res(&self, id: NodeId) -> PerNS<Option<Res<NodeId>>> {
self.base.get_import_res(id)
}
fn get_label_res(&self, id: NodeId) -> Option<NodeId> {
self.base.get_label_res(id)
}
fn get_lifetime_res(&self, id: NodeId) -> Option<LifetimeRes> {
self.base.get_lifetime_res(id)
}
fn extra_lifetime_params(&self, id: NodeId) -> Vec<(Ident, NodeId, LifetimeRes)> {
self.base.extra_lifetime_params(id)
}
fn delegation_info(&self, id: LocalDefId) -> Option<&DelegationInfo> {
self.base.delegation_info(id)
}
fn opt_local_def_id(&self, id: NodeId) -> Option<LocalDefId> {
self.node_id_to_def_id.get(&id).copied().or_else(|| self.base.opt_local_def_id(id))
}
fn local_def_id(&self, id: NodeId) -> LocalDefId {
self.opt_local_def_id(id).expect("must have def_id")
}
fn lifetime_elision_allowed(&self, id: NodeId) -> bool {
self.base.lifetime_elision_allowed(id)
}
fn insert_new_def_id(&mut self, node_id: NodeId, def_id: LocalDefId) {
self.node_id_to_def_id.insert(node_id, def_id);
}
fn insert_partial_res(&mut self, node_id: NodeId, res: PartialRes) {
self.partial_res_map.insert(node_id, res);
}
fn trait_candidates(&self, node_id: NodeId) -> Option<&'tcx [hir::TraitCandidate<'tcx>]> {
self.base.trait_candidates(node_id)
}
#[inline]
fn next_node_id(&mut self) -> NodeId {
next_node_id(&mut self.next_node_id)
}
}
fn next_node_id(current_id: &mut NodeId) -> NodeId {
let start = *current_id;
let next = start.as_u32().checked_add(1).expect("input too large; ran out of NodeIds");
*current_id = ast::NodeId::from_u32(next);
start
}
#[extension(trait ResolverAstLoweringExt<'tcx>)] #[extension(trait ResolverAstLoweringExt<'tcx>)]
impl<'tcx> ResolverAstLowering<'tcx> { impl<'tcx> ResolverAstLowering<'tcx> {
fn legacy_const_generic_args(&self, expr: &Expr, tcx: TyCtxt<'tcx>) -> Option<Vec<usize>> { fn legacy_const_generic_args(&self, expr: &Expr, tcx: TyCtxt<'tcx>) -> Option<Vec<usize>> {
@@ -327,7 +261,7 @@ fn legacy_const_generic_args(&self, expr: &Expr, tcx: TyCtxt<'tcx>) -> Option<Ve
return None; return None;
} }
let def_id = self.get_partial_res(expr.id)?.full_res()?.opt_def_id()?; let def_id = self.partial_res_map.get(&expr.id)?.full_res()?.opt_def_id()?;
// We only support cross-crate argument rewriting. Uses // We only support cross-crate argument rewriting. Uses
// within the same crate should be updated to use the new // within the same crate should be updated to use the new
@@ -344,10 +278,6 @@ fn legacy_const_generic_args(&self, expr: &Expr, tcx: TyCtxt<'tcx>) -> Option<Ve
.map(|fn_indexes| fn_indexes.iter().map(|(num, _)| *num).collect()) .map(|fn_indexes| fn_indexes.iter().map(|(num, _)| *num).collect())
} }
fn get_partial_res(&self, id: NodeId) -> Option<PartialRes> {
self.partial_res_map.get(&id).copied()
}
/// Obtains per-namespace resolutions for `use` statement with the given `NodeId`. /// Obtains per-namespace resolutions for `use` statement with the given `NodeId`.
fn get_import_res(&self, id: NodeId) -> PerNS<Option<Res<NodeId>>> { fn get_import_res(&self, id: NodeId) -> PerNS<Option<Res<NodeId>>> {
self.import_res_map.get(&id).copied().unwrap_or_default() self.import_res_map.get(&id).copied().unwrap_or_default()
@@ -370,8 +300,8 @@ fn get_lifetime_res(&self, id: NodeId) -> Option<LifetimeRes> {
/// ///
/// The extra lifetimes that appear from the parenthesized `Fn`-trait desugaring /// The extra lifetimes that appear from the parenthesized `Fn`-trait desugaring
/// should appear at the enclosing `PolyTraitRef`. /// should appear at the enclosing `PolyTraitRef`.
fn extra_lifetime_params(&self, id: NodeId) -> Vec<(Ident, NodeId, LifetimeRes)> { fn extra_lifetime_params(&self, id: NodeId) -> &[(Ident, NodeId, LifetimeRes)] {
self.extra_lifetime_params_map.get(&id).cloned().unwrap_or_default() self.extra_lifetime_params_map.get(&id).map_or(&[], |v| &v[..])
} }
fn delegation_info(&self, id: LocalDefId) -> Option<&DelegationInfo> { fn delegation_info(&self, id: LocalDefId) -> Option<&DelegationInfo> {
@@ -389,23 +319,6 @@ fn local_def_id(&self, id: NodeId) -> LocalDefId {
fn lifetime_elision_allowed(&self, id: NodeId) -> bool { fn lifetime_elision_allowed(&self, id: NodeId) -> bool {
self.lifetime_elision_allowed.contains(&id) self.lifetime_elision_allowed.contains(&id)
} }
fn insert_new_def_id(&mut self, node_id: NodeId, def_id: LocalDefId) {
self.node_id_to_def_id.insert(node_id, def_id);
}
fn insert_partial_res(&mut self, node_id: NodeId, res: PartialRes) {
self.partial_res_map.insert(node_id, res);
}
fn trait_candidates(&self, node_id: NodeId) -> Option<&'tcx [hir::TraitCandidate<'tcx>]> {
self.trait_map.get(&node_id).copied()
}
#[inline]
fn next_node_id(&mut self) -> NodeId {
next_node_id(&mut self.next_node_id)
}
} }
/// How relaxed bounds `?Trait` should be treated. /// How relaxed bounds `?Trait` should be treated.
@@ -546,7 +459,7 @@ enum TryBlockScope {
} }
fn index_crate<'a, 'b>( fn index_crate<'a, 'b>(
resolver: &'b impl ResolverAstLoweringExt<'a>, resolver: &'b ResolverAstLowering<'b>,
krate: &'a Crate, krate: &'a Crate,
) -> IndexVec<LocalDefId, AstOwner<'a>> { ) -> IndexVec<LocalDefId, AstOwner<'a>> {
let mut indexer = Indexer { resolver, index: IndexVec::new() }; let mut indexer = Indexer { resolver, index: IndexVec::new() };
@@ -556,12 +469,12 @@ fn index_crate<'a, 'b>(
return indexer.index; return indexer.index;
struct Indexer<'a, 'b, R> { struct Indexer<'a, 'b> {
resolver: &'b R, resolver: &'b ResolverAstLowering<'b>,
index: IndexVec<LocalDefId, AstOwner<'a>>, index: IndexVec<LocalDefId, AstOwner<'a>>,
} }
impl<'a, 'b, R: ResolverAstLoweringExt<'a>> visit::Visitor<'a> for Indexer<'a, 'b, R> { impl<'a, 'b> visit::Visitor<'a> for Indexer<'a, 'b> {
fn visit_attribute(&mut self, _: &'a Attribute) { fn visit_attribute(&mut self, _: &'a Attribute) {
// We do not want to lower expressions that appear in attributes, // We do not want to lower expressions that appear in attributes,
// as they are not accessible to the rest of the HIR. // as they are not accessible to the rest of the HIR.
@@ -618,7 +531,7 @@ pub fn lower_to_hir(tcx: TyCtxt<'_>, (): ()) -> mid_hir::Crate<'_> {
tcx.ensure_done().early_lint_checks(()); tcx.ensure_done().early_lint_checks(());
tcx.ensure_done().debugger_visualizers(LOCAL_CRATE); tcx.ensure_done().debugger_visualizers(LOCAL_CRATE);
tcx.ensure_done().get_lang_items(()); tcx.ensure_done().get_lang_items(());
let (mut resolver, krate) = tcx.resolver_for_lowering().steal(); let (resolver, krate) = tcx.resolver_for_lowering().steal();
let ast_index = index_crate(&resolver, &krate); let ast_index = index_crate(&resolver, &krate);
let mut owners = IndexVec::from_fn_n( let mut owners = IndexVec::from_fn_n(
@@ -626,13 +539,11 @@ pub fn lower_to_hir(tcx: TyCtxt<'_>, (): ()) -> mid_hir::Crate<'_> {
tcx.definitions_untracked().def_index_count(), tcx.definitions_untracked().def_index_count(),
); );
let mut disambiguators = Disambiguators::Default(resolver.disambiguators.steal());
let mut lowerer = item::ItemLowerer { let mut lowerer = item::ItemLowerer {
tcx, tcx,
resolver: &mut resolver, resolver: &resolver,
ast_index: &ast_index, ast_index: &ast_index,
owners: Owners::IndexVec(&mut owners), owners: Owners::IndexVec(&mut owners),
disambiguators: &mut disambiguators,
}; };
let mut delayed_ids: FxIndexSet<LocalDefId> = Default::default(); let mut delayed_ids: FxIndexSet<LocalDefId> = Default::default();
@@ -651,11 +562,7 @@ pub fn lower_to_hir(tcx: TyCtxt<'_>, (): ()) -> mid_hir::Crate<'_> {
let opt_hir_hash = let opt_hir_hash =
if tcx.needs_crate_hash() { Some(compute_hir_hash(tcx, &owners)) } else { None }; if tcx.needs_crate_hash() { Some(compute_hir_hash(tcx, &owners)) } else { None };
let Disambiguators::Default(disambiguators) = disambiguators else { unreachable!() }; let delayed_resolver = Steal::new((resolver, krate));
let delayed_disambigs =
Arc::new(disambiguators.into_items().map(|(id, d)| (id, Steal::new(d))).collect());
let delayed_resolver = Steal::new((resolver, krate, delayed_disambigs));
mid_hir::Crate::new(owners, delayed_ids, delayed_resolver, opt_hir_hash) mid_hir::Crate::new(owners, delayed_ids, delayed_resolver, opt_hir_hash)
} }
@@ -663,26 +570,18 @@ pub fn lower_to_hir(tcx: TyCtxt<'_>, (): ()) -> mid_hir::Crate<'_> {
pub fn lower_delayed_owner(tcx: TyCtxt<'_>, def_id: LocalDefId) { pub fn lower_delayed_owner(tcx: TyCtxt<'_>, def_id: LocalDefId) {
let krate = tcx.hir_crate(()); let krate = tcx.hir_crate(());
let (resolver, krate, delayed_disambigs) = &*krate.delayed_resolver.borrow(); let (resolver, krate) = &*krate.delayed_resolver.borrow();
// FIXME!!!(fn_delegation): make ast index lifetime same as resolver, // FIXME!!!(fn_delegation): make ast index lifetime same as resolver,
// as it is too bad to reindex whole crate on each delegation lowering. // as it is too bad to reindex whole crate on each delegation lowering.
let ast_index = index_crate(resolver, krate); let ast_index = index_crate(resolver, krate);
let mut resolver = ResolverDelayedAstLowering {
next_node_id: resolver.next_node_id,
partial_res_map: Default::default(),
node_id_to_def_id: Default::default(),
base: resolver,
};
let mut map = Default::default(); let mut map = Default::default();
let mut lowerer = item::ItemLowerer { let mut lowerer = item::ItemLowerer {
tcx, tcx,
resolver: &mut resolver, resolver: &resolver,
ast_index: &ast_index, ast_index: &ast_index,
owners: Owners::Map(&mut map), owners: Owners::Map(&mut map),
disambiguators: &mut Disambiguators::Delayed(Arc::clone(delayed_disambigs)),
}; };
lowerer.lower_node(def_id); lowerer.lower_node(def_id);
@@ -719,7 +618,7 @@ enum GenericArgsMode {
Silence, Silence,
} }
impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> { impl<'hir> LoweringContext<'_, 'hir> {
fn create_def( fn create_def(
&mut self, &mut self,
node_id: ast::NodeId, node_id: ast::NodeId,
@@ -744,25 +643,38 @@ fn create_def(
.def_id(); .def_id();
debug!("create_def: def_id_to_node_id[{:?}] <-> {:?}", def_id, node_id); debug!("create_def: def_id_to_node_id[{:?}] <-> {:?}", def_id, node_id);
self.resolver.insert_new_def_id(node_id, def_id); self.node_id_to_def_id.insert(node_id, def_id);
def_id def_id
} }
fn next_node_id(&mut self) -> NodeId { fn next_node_id(&mut self) -> NodeId {
self.resolver.next_node_id() let start = self.next_node_id;
let next = start.as_u32().checked_add(1).expect("input too large; ran out of NodeIds");
self.next_node_id = ast::NodeId::from_u32(next);
start
} }
/// Given the id of some node in the AST, finds the `LocalDefId` associated with it by the name /// Given the id of some node in the AST, finds the `LocalDefId` associated with it by the name
/// resolver (if any). /// resolver (if any).
fn opt_local_def_id(&self, node: NodeId) -> Option<LocalDefId> { fn opt_local_def_id(&self, node: NodeId) -> Option<LocalDefId> {
self.resolver.opt_local_def_id(node) self.node_id_to_def_id
.get(&node)
.or_else(|| self.resolver.node_id_to_def_id.get(&node))
.copied()
} }
fn local_def_id(&self, node: NodeId) -> LocalDefId { fn local_def_id(&self, node: NodeId) -> LocalDefId {
self.opt_local_def_id(node).unwrap_or_else(|| panic!("no entry for node id: `{node:?}`")) self.opt_local_def_id(node).unwrap_or_else(|| panic!("no entry for node id: `{node:?}`"))
} }
fn get_partial_res(&self, id: NodeId) -> Option<PartialRes> {
self.partial_res_overrides
.get(&id)
.or_else(|| self.resolver.partial_res_map.get(&id))
.copied()
}
/// Given the id of an owner node in the AST, returns the corresponding `OwnerId`. /// Given the id of an owner node in the AST, returns the corresponding `OwnerId`.
fn owner_id(&self, node: NodeId) -> hir::OwnerId { fn owner_id(&self, node: NodeId) -> hir::OwnerId {
hir::OwnerId { def_id: self.local_def_id(node) } hir::OwnerId { def_id: self.local_def_id(node) }
@@ -782,12 +694,12 @@ fn with_hir_id_owner(
let owner_id = self.owner_id(owner); let owner_id = self.owner_id(owner);
let def_id = owner_id.def_id; let def_id = owner_id.def_id;
let new_disambig = match &mut self.disambiguators { let new_disambig = self
Disambiguators::Default(map) => map.remove(&def_id), .resolver
Disambiguators::Delayed(map) => map.get(&def_id).map(Steal::steal), .disambiguators
}; .get(&def_id)
.map(|s| s.steal())
let new_disambig = new_disambig.unwrap_or_else(|| PerParentDisambiguatorState::new(def_id)); .unwrap_or_else(|| PerParentDisambiguatorState::new(def_id));
let disambiguator = std::mem::replace(&mut self.current_disambiguator, new_disambig); let disambiguator = std::mem::replace(&mut self.current_disambiguator, new_disambig);
let current_attrs = std::mem::take(&mut self.attrs); let current_attrs = std::mem::take(&mut self.attrs);
@@ -893,8 +805,8 @@ fn lower_node_id(&mut self, ast_node_id: NodeId) -> HirId {
self.children.push((def_id, hir::MaybeOwner::NonOwner(hir_id))); self.children.push((def_id, hir::MaybeOwner::NonOwner(hir_id)));
} }
if let Some(traits) = self.resolver.trait_candidates(ast_node_id) { if let Some(traits) = self.resolver.trait_map.get(&ast_node_id) {
self.trait_map.insert(hir_id.local_id, traits); self.trait_map.insert(hir_id.local_id, &traits[..]);
} }
// Check whether the same `NodeId` is lowered more than once. // Check whether the same `NodeId` is lowered more than once.
@@ -935,7 +847,7 @@ fn lower_res(&mut self, res: Res<NodeId>) -> Res {
} }
fn expect_full_res(&mut self, id: NodeId) -> Res<NodeId> { fn expect_full_res(&mut self, id: NodeId) -> Res<NodeId> {
self.resolver.get_partial_res(id).map_or(Res::Err, |pr| pr.expect_full_res()) self.get_partial_res(id).map_or(Res::Err, |pr| pr.expect_full_res())
} }
fn lower_import_res(&mut self, id: NodeId, span: Span) -> PerNS<Option<Res>> { fn lower_import_res(&mut self, id: NodeId, span: Span) -> PerNS<Option<Res>> {
@@ -1073,8 +985,8 @@ fn lower_lifetime_binder(
let extra_lifetimes = self.resolver.extra_lifetime_params(binder); let extra_lifetimes = self.resolver.extra_lifetime_params(binder);
debug!(?extra_lifetimes); debug!(?extra_lifetimes);
let extra_lifetimes: Vec<_> = extra_lifetimes let extra_lifetimes: Vec<_> = extra_lifetimes
.into_iter() .iter()
.filter_map(|(ident, node_id, res)| { .filter_map(|&(ident, node_id, res)| {
self.lifetime_res_to_generic_param( self.lifetime_res_to_generic_param(
ident, ident,
node_id, node_id,
@@ -1400,7 +1312,6 @@ fn lower_generic_arg(
// FIXME: Should we be handling `(PATH_TO_CONST)`? // FIXME: Should we be handling `(PATH_TO_CONST)`?
TyKind::Path(None, path) => { TyKind::Path(None, path) => {
if let Some(res) = self if let Some(res) = self
.resolver
.get_partial_res(ty.id) .get_partial_res(ty.id)
.and_then(|partial_res| partial_res.full_res()) .and_then(|partial_res| partial_res.full_res())
{ {
@@ -1451,7 +1362,7 @@ fn lower_path_ty(
// The other cases when a qpath should be opportunistically made a trait object are handled // The other cases when a qpath should be opportunistically made a trait object are handled
// by `ty_path`. // by `ty_path`.
if qself.is_none() if qself.is_none()
&& let Some(partial_res) = self.resolver.get_partial_res(t.id) && let Some(partial_res) = self.get_partial_res(t.id)
&& let Some(Res::Def(DefKind::Trait | DefKind::TraitAlias, _)) = partial_res.full_res() && let Some(Res::Def(DefKind::Trait | DefKind::TraitAlias, _)) = partial_res.full_res()
{ {
let (bounds, lifetime_bound) = self.with_dyn_type_scope(true, |this| { let (bounds, lifetime_bound) = self.with_dyn_type_scope(true, |this| {
@@ -1805,7 +1716,7 @@ fn lower_precise_capturing_args(
let [segment] = path.segments.as_slice() else { let [segment] = path.segments.as_slice() else {
panic!(); panic!();
}; };
let res = self.resolver.get_partial_res(*id).map_or(Res::Err, |partial_res| { let res = self.get_partial_res(*id).map_or(Res::Err, |partial_res| {
partial_res.full_res().expect("no partial res expected for precise capture arg") partial_res.full_res().expect("no partial res expected for precise capture arg")
}); });
hir::PreciseCapturingArg::Param(hir::PreciseCapturingNonLifetimeArg { hir::PreciseCapturingArg::Param(hir::PreciseCapturingNonLifetimeArg {
@@ -2334,7 +2245,7 @@ fn validate_relaxed_bound(
match rbp { match rbp {
RelaxedBoundPolicy::Allowed => return, RelaxedBoundPolicy::Allowed => return,
RelaxedBoundPolicy::AllowedIfOnTyParam(id, params) => { RelaxedBoundPolicy::AllowedIfOnTyParam(id, params) => {
if let Some(res) = self.resolver.get_partial_res(id).and_then(|r| r.full_res()) if let Some(res) = self.get_partial_res(id).and_then(|r| r.full_res())
&& let Res::Def(DefKind::TyParam, def_id) = res && let Res::Def(DefKind::TyParam, def_id) = res
&& params.iter().any(|p| def_id == self.local_def_id(p.id).to_def_id()) && params.iter().any(|p| def_id == self.local_def_id(p.id).to_def_id())
{ {
@@ -2804,7 +2715,7 @@ fn lower_anon_const_to_const_arg(
}; };
let maybe_res = let maybe_res =
self.resolver.get_partial_res(expr.id).and_then(|partial_res| partial_res.full_res()); self.get_partial_res(expr.id).and_then(|partial_res| partial_res.full_res());
if let ExprKind::Path(qself, path) = &expr.kind if let ExprKind::Path(qself, path) = &expr.kind
&& path.is_potential_trivial_const_arg() && path.is_potential_trivial_const_arg()
&& matches!(maybe_res, Some(Res::Def(DefKind::ConstParam, _))) && matches!(maybe_res, Some(Res::Def(DefKind::ConstParam, _)))
@@ -3116,10 +3027,7 @@ fn is_empty(&self) -> bool {
&& self.parenthesized == hir::GenericArgsParentheses::No && self.parenthesized == hir::GenericArgsParentheses::No
} }
fn into_generic_args( fn into_generic_args(self, this: &LoweringContext<'_, 'hir>) -> &'hir hir::GenericArgs<'hir> {
self,
this: &LoweringContext<'_, 'hir, impl ResolverAstLoweringExt<'hir>>,
) -> &'hir hir::GenericArgs<'hir> {
let ga = hir::GenericArgs { let ga = hir::GenericArgs {
args: this.arena.alloc_from_iter(self.args), args: this.arena.alloc_from_iter(self.args),
constraints: self.constraints, constraints: self.constraints,
+5 -4
View File
@@ -10,10 +10,11 @@
use super::errors::{ use super::errors::{
ArbitraryExpressionInPattern, ExtraDoubleDot, MisplacedDoubleDot, SubTupleBinding, ArbitraryExpressionInPattern, ExtraDoubleDot, MisplacedDoubleDot, SubTupleBinding,
}; };
use super::{ImplTraitContext, LoweringContext, ParamMode, ResolverAstLoweringExt}; use super::{
use crate::{AllowReturnTypeNotation, ImplTraitPosition}; AllowReturnTypeNotation, ImplTraitContext, ImplTraitPosition, LoweringContext, ParamMode,
};
impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> { impl<'hir> LoweringContext<'_, 'hir> {
pub(crate) fn lower_pat(&mut self, pattern: &Pat) -> &'hir hir::Pat<'hir> { pub(crate) fn lower_pat(&mut self, pattern: &Pat) -> &'hir hir::Pat<'hir> {
self.arena.alloc(self.lower_pat_mut(pattern)) self.arena.alloc(self.lower_pat_mut(pattern))
} }
@@ -287,7 +288,7 @@ fn lower_pat_ident(
hir_id: hir::HirId, hir_id: hir::HirId,
lower_sub: impl FnOnce(&mut Self) -> Option<&'hir hir::Pat<'hir>>, lower_sub: impl FnOnce(&mut Self) -> Option<&'hir hir::Pat<'hir>>,
) -> hir::PatKind<'hir> { ) -> hir::PatKind<'hir> {
match self.resolver.get_partial_res(p.id).map(|d| d.expect_full_res()) { match self.get_partial_res(p.id).map(|d| d.expect_full_res()) {
// `None` can occur in body-less function signatures // `None` can occur in body-less function signatures
res @ (None | Some(Res::Local(_))) => { res @ (None | Some(Res::Local(_))) => {
let binding_id = match res { let binding_id = match res {
+2 -3
View File
@@ -20,7 +20,7 @@
LifetimeRes, LoweringContext, ParamMode, ResolverAstLoweringExt, LifetimeRes, LoweringContext, ParamMode, ResolverAstLoweringExt,
}; };
impl<'hir, R: ResolverAstLoweringExt<'hir>> LoweringContext<'_, 'hir, R> { impl<'hir> LoweringContext<'_, 'hir> {
#[instrument(level = "trace", skip(self))] #[instrument(level = "trace", skip(self))]
pub(crate) fn lower_qpath( pub(crate) fn lower_qpath(
&mut self, &mut self,
@@ -41,8 +41,7 @@ pub(crate) fn lower_qpath(
self.lower_ty_alloc(&q.ty, ImplTraitContext::Disallowed(ImplTraitPosition::Path)) self.lower_ty_alloc(&q.ty, ImplTraitContext::Disallowed(ImplTraitPosition::Path))
}); });
let partial_res = let partial_res = self.get_partial_res(id).unwrap_or_else(|| PartialRes::new(Res::Err));
self.resolver.get_partial_res(id).unwrap_or_else(|| PartialRes::new(Res::Err));
let base_res = partial_res.base_res(); let base_res = partial_res.base_res();
let unresolved_segments = partial_res.unresolved_segments(); let unresolved_segments = partial_res.unresolved_segments();
+1 -1
View File
@@ -1261,7 +1261,7 @@ fn force_delayed_owners_lowering(tcx: TyCtxt<'_>) {
tcx.ensure_done().lower_delayed_owner(id); tcx.ensure_done().lower_delayed_owner(id);
} }
let (_, krate, _) = krate.delayed_resolver.steal(); let (_, krate) = krate.delayed_resolver.steal();
let prof = tcx.sess.prof.clone(); let prof = tcx.sess.prof.clone();
// Drop AST to free memory. It can be expensive so try to drop it on a separate thread. // Drop AST to free memory. It can be expensive so try to drop it on a separate thread.
+3 -12
View File
@@ -16,8 +16,7 @@
use rustc_data_structures::steal::Steal; use rustc_data_structures::steal::Steal;
use rustc_data_structures::sync::{DynSend, DynSync, try_par_for_each_in}; use rustc_data_structures::sync::{DynSend, DynSync, try_par_for_each_in};
use rustc_hir::def::{DefKind, Res}; use rustc_hir::def::{DefKind, Res};
use rustc_hir::def_id::{DefId, LocalDefId, LocalDefIdMap, LocalModDefId}; use rustc_hir::def_id::{DefId, LocalDefId, LocalModDefId};
use rustc_hir::definitions::PerParentDisambiguatorState;
use rustc_hir::*; use rustc_hir::*;
use rustc_index::IndexVec; use rustc_index::IndexVec;
use rustc_macros::{Decodable, Encodable, HashStable}; use rustc_macros::{Decodable, Encodable, HashStable};
@@ -40,11 +39,7 @@ pub struct Crate<'hir> {
pub delayed_ids: FxIndexSet<LocalDefId>, pub delayed_ids: FxIndexSet<LocalDefId>,
// The resolver and AST crate which are set in the end of the `hir_crate` query // The resolver and AST crate which are set in the end of the `hir_crate` query
// and then stolen and dropped in `force_delayed_owners_lowering`. // and then stolen and dropped in `force_delayed_owners_lowering`.
pub delayed_resolver: Steal<( pub delayed_resolver: Steal<(ResolverAstLowering<'hir>, Arc<ast::Crate>)>,
ResolverAstLowering<'hir>,
Arc<ast::Crate>,
Arc<LocalDefIdMap<Steal<PerParentDisambiguatorState>>>,
)>,
// Only present when incr. comp. is enabled. // Only present when incr. comp. is enabled.
pub opt_hir_hash: Option<Fingerprint>, pub opt_hir_hash: Option<Fingerprint>,
} }
@@ -53,11 +48,7 @@ impl<'hir> Crate<'hir> {
pub fn new( pub fn new(
owners: IndexVec<LocalDefId, MaybeOwner<'hir>>, owners: IndexVec<LocalDefId, MaybeOwner<'hir>>,
delayed_ids: FxIndexSet<LocalDefId>, delayed_ids: FxIndexSet<LocalDefId>,
delayed_resolver: Steal<( delayed_resolver: Steal<(ResolverAstLowering<'hir>, Arc<ast::Crate>)>,
ResolverAstLowering<'hir>,
Arc<ast::Crate>,
Arc<LocalDefIdMap<Steal<PerParentDisambiguatorState>>>,
)>,
opt_hir_hash: Option<Fingerprint>, opt_hir_hash: Option<Fingerprint>,
) -> Crate<'hir> { ) -> Crate<'hir> {
Crate { owners, delayed_ids, delayed_resolver, opt_hir_hash } Crate { owners, delayed_ids, delayed_resolver, opt_hir_hash }
+1 -1
View File
@@ -227,7 +227,7 @@ pub struct ResolverAstLowering<'tcx> {
// Information about delegations which is used when handling recursive delegations // Information about delegations which is used when handling recursive delegations
pub delegation_infos: LocalDefIdMap<DelegationInfo>, pub delegation_infos: LocalDefIdMap<DelegationInfo>,
pub disambiguators: Steal<LocalDefIdMap<PerParentDisambiguatorState>>, pub disambiguators: LocalDefIdMap<Steal<PerParentDisambiguatorState>>,
} }
#[derive(Debug)] #[derive(Debug)]
+6 -1
View File
@@ -1908,6 +1908,11 @@ pub fn into_outputs(self) -> ResolverOutputs<'tcx> {
Some(StrippedCfgItem { parent_scope, ident: item.ident, cfg: item.cfg }) Some(StrippedCfgItem { parent_scope, ident: item.ident, cfg: item.cfg })
}) })
.collect(); .collect();
let disambiguators = self
.disambiguators
.into_items()
.map(|(def_id, disamb)| (def_id, Steal::new(disamb)))
.collect();
let global_ctxt = ResolverGlobalCtxt { let global_ctxt = ResolverGlobalCtxt {
expn_that_defined, expn_that_defined,
@@ -1939,7 +1944,7 @@ pub fn into_outputs(self) -> ResolverOutputs<'tcx> {
lifetime_elision_allowed: self.lifetime_elision_allowed, lifetime_elision_allowed: self.lifetime_elision_allowed,
lint_buffer: Steal::new(self.lint_buffer), lint_buffer: Steal::new(self.lint_buffer),
delegation_infos: self.delegation_infos, delegation_infos: self.delegation_infos,
disambiguators: Steal::new(self.disambiguators), disambiguators,
}; };
ResolverOutputs { global_ctxt, ast_lowering } ResolverOutputs { global_ctxt, ast_lowering }
} }