mirror of
https://github.com/rust-lang/rust-analyzer.git
synced 2025-09-28 21:05:02 +00:00
Move expr resolver to resolve
This commit is contained in:
parent
0102fb4133
commit
24964ca58e
4 changed files with 35 additions and 33 deletions
|
@ -13,7 +13,7 @@ use crate::{
|
||||||
diagnostics::{MissingFields, MissingOkInTailExpr},
|
diagnostics::{MissingFields, MissingOkInTailExpr},
|
||||||
resolve::HasResolver,
|
resolve::HasResolver,
|
||||||
ty::{ApplicationTy, InferenceResult, Ty, TypeCtor},
|
ty::{ApplicationTy, InferenceResult, Ty, TypeCtor},
|
||||||
Adt, DefWithBody, Function, HasBody, Name, Path, Resolver,
|
Adt, Function, Name, Path,
|
||||||
};
|
};
|
||||||
|
|
||||||
pub use hir_def::{
|
pub use hir_def::{
|
||||||
|
@ -27,30 +27,6 @@ pub use hir_def::{
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
// needs arbitrary_self_types to be a method... or maybe move to the def?
|
|
||||||
pub(crate) fn resolver_for_expr(
|
|
||||||
db: &impl HirDatabase,
|
|
||||||
owner: DefWithBody,
|
|
||||||
expr_id: ExprId,
|
|
||||||
) -> Resolver {
|
|
||||||
let scopes = owner.expr_scopes(db);
|
|
||||||
resolver_for_scope(db, owner, scopes.scope_for(expr_id))
|
|
||||||
}
|
|
||||||
|
|
||||||
pub(crate) fn resolver_for_scope(
|
|
||||||
db: &impl HirDatabase,
|
|
||||||
owner: DefWithBody,
|
|
||||||
scope_id: Option<ScopeId>,
|
|
||||||
) -> Resolver {
|
|
||||||
let mut r = owner.resolver(db);
|
|
||||||
let scopes = owner.expr_scopes(db);
|
|
||||||
let scope_chain = scopes.scope_chain(scope_id).collect::<Vec<_>>();
|
|
||||||
for scope in scope_chain.into_iter().rev() {
|
|
||||||
r = r.push_expr_scope(owner.into(), Arc::clone(&scopes), scope);
|
|
||||||
}
|
|
||||||
r
|
|
||||||
}
|
|
||||||
|
|
||||||
pub(crate) struct ExprValidator<'a, 'b: 'a> {
|
pub(crate) struct ExprValidator<'a, 'b: 'a> {
|
||||||
func: Function,
|
func: Function,
|
||||||
infer: Arc<InferenceResult>,
|
infer: Arc<InferenceResult>,
|
||||||
|
|
|
@ -4,6 +4,7 @@ use std::sync::Arc;
|
||||||
use hir_def::{
|
use hir_def::{
|
||||||
builtin_type::BuiltinType,
|
builtin_type::BuiltinType,
|
||||||
db::DefDatabase2,
|
db::DefDatabase2,
|
||||||
|
expr::ExprId,
|
||||||
generics::GenericParams,
|
generics::GenericParams,
|
||||||
nameres::CrateDefMap,
|
nameres::CrateDefMap,
|
||||||
path::{Path, PathKind},
|
path::{Path, PathKind},
|
||||||
|
@ -15,10 +16,10 @@ use rustc_hash::FxHashSet;
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
code_model::Crate,
|
code_model::Crate,
|
||||||
db::DefDatabase,
|
db::{DefDatabase, HirDatabase},
|
||||||
expr::{ExprScopes, PatId, ScopeId},
|
expr::{ExprScopes, PatId, ScopeId},
|
||||||
Adt, Const, Container, DefWithBody, EnumVariant, Function, GenericDef, ImplBlock, Local,
|
Adt, Const, Container, DefWithBody, EnumVariant, Function, GenericDef, HasBody, ImplBlock,
|
||||||
MacroDef, Module, ModuleDef, PerNs, Static, Struct, Trait, TypeAlias,
|
Local, MacroDef, Module, ModuleDef, PerNs, Static, Struct, Trait, TypeAlias,
|
||||||
};
|
};
|
||||||
|
|
||||||
#[derive(Debug, Clone, Default)]
|
#[derive(Debug, Clone, Default)]
|
||||||
|
@ -492,6 +493,30 @@ impl Scope {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// needs arbitrary_self_types to be a method... or maybe move to the def?
|
||||||
|
pub(crate) fn resolver_for_expr(
|
||||||
|
db: &impl HirDatabase,
|
||||||
|
owner: DefWithBody,
|
||||||
|
expr_id: ExprId,
|
||||||
|
) -> Resolver {
|
||||||
|
let scopes = owner.expr_scopes(db);
|
||||||
|
resolver_for_scope(db, owner, scopes.scope_for(expr_id))
|
||||||
|
}
|
||||||
|
|
||||||
|
pub(crate) fn resolver_for_scope(
|
||||||
|
db: &impl HirDatabase,
|
||||||
|
owner: DefWithBody,
|
||||||
|
scope_id: Option<ScopeId>,
|
||||||
|
) -> Resolver {
|
||||||
|
let mut r = owner.resolver(db);
|
||||||
|
let scopes = owner.expr_scopes(db);
|
||||||
|
let scope_chain = scopes.scope_chain(scope_id).collect::<Vec<_>>();
|
||||||
|
for scope in scope_chain.into_iter().rev() {
|
||||||
|
r = r.push_expr_scope(owner.into(), Arc::clone(&scopes), scope);
|
||||||
|
}
|
||||||
|
r
|
||||||
|
}
|
||||||
|
|
||||||
pub(crate) trait HasResolver {
|
pub(crate) trait HasResolver {
|
||||||
/// Builds a resolver for type references inside this def.
|
/// Builds a resolver for type references inside this def.
|
||||||
fn resolver(self, db: &impl DefDatabase) -> Resolver;
|
fn resolver(self, db: &impl DefDatabase) -> Resolver;
|
||||||
|
|
|
@ -21,9 +21,9 @@ use ra_syntax::{
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
db::HirDatabase,
|
db::HirDatabase,
|
||||||
expr::{self, BodySourceMap, ExprScopes, ScopeId},
|
expr::{BodySourceMap, ExprScopes, ScopeId},
|
||||||
ids::LocationCtx,
|
ids::LocationCtx,
|
||||||
resolve::{HasResolver, ScopeDef, TypeNs, ValueNs},
|
resolve::{resolver_for_scope, HasResolver, ScopeDef, TypeNs, ValueNs},
|
||||||
ty::method_resolution::{self, implements_trait},
|
ty::method_resolution::{self, implements_trait},
|
||||||
Adt, AssocItem, Const, DefWithBody, Either, Enum, EnumVariant, FromSource, Function,
|
Adt, AssocItem, Const, DefWithBody, Either, Enum, EnumVariant, FromSource, Function,
|
||||||
GenericParam, HasBody, HirFileId, Local, MacroDef, Module, Name, Path, Resolver, Static,
|
GenericParam, HasBody, HirFileId, Local, MacroDef, Module, Name, Path, Resolver, Static,
|
||||||
|
@ -160,7 +160,7 @@ impl SourceAnalyzer {
|
||||||
None => scope_for(&scopes, &source_map, node),
|
None => scope_for(&scopes, &source_map, node),
|
||||||
Some(offset) => scope_for_offset(&scopes, &source_map, node.with_value(offset)),
|
Some(offset) => scope_for_offset(&scopes, &source_map, node.with_value(offset)),
|
||||||
};
|
};
|
||||||
let resolver = expr::resolver_for_scope(db, def, scope);
|
let resolver = resolver_for_scope(db, def, scope);
|
||||||
SourceAnalyzer {
|
SourceAnalyzer {
|
||||||
resolver,
|
resolver,
|
||||||
body_owner: Some(def),
|
body_owner: Some(def),
|
||||||
|
|
|
@ -12,8 +12,9 @@ use hir_expand::name;
|
||||||
use super::{BindingMode, Expectation, InferenceContext, InferenceDiagnostic, TypeMismatch};
|
use super::{BindingMode, Expectation, InferenceContext, InferenceDiagnostic, TypeMismatch};
|
||||||
use crate::{
|
use crate::{
|
||||||
db::HirDatabase,
|
db::HirDatabase,
|
||||||
expr::{self, Array, BinaryOp, Expr, ExprId, Literal, Statement, UnaryOp},
|
expr::{Array, BinaryOp, Expr, ExprId, Literal, Statement, UnaryOp},
|
||||||
generics::{GenericParams, HasGenericParams},
|
generics::{GenericParams, HasGenericParams},
|
||||||
|
resolve::resolver_for_expr,
|
||||||
ty::{
|
ty::{
|
||||||
autoderef, method_resolution, op, CallableDef, InferTy, IntTy, Mutability, Namespace,
|
autoderef, method_resolution, op, CallableDef, InferTy, IntTy, Mutability, Namespace,
|
||||||
Obligation, ProjectionPredicate, ProjectionTy, Substs, TraitRef, Ty, TypeCtor, TypeWalk,
|
Obligation, ProjectionPredicate, ProjectionTy, Substs, TraitRef, Ty, TypeCtor, TypeWalk,
|
||||||
|
@ -186,7 +187,7 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> {
|
||||||
}
|
}
|
||||||
Expr::Path(p) => {
|
Expr::Path(p) => {
|
||||||
// FIXME this could be more efficient...
|
// FIXME this could be more efficient...
|
||||||
let resolver = expr::resolver_for_expr(self.db, self.owner, tgt_expr);
|
let resolver = resolver_for_expr(self.db, self.owner, tgt_expr);
|
||||||
self.infer_path(&resolver, p, tgt_expr.into()).unwrap_or(Ty::Unknown)
|
self.infer_path(&resolver, p, tgt_expr.into()).unwrap_or(Ty::Unknown)
|
||||||
}
|
}
|
||||||
Expr::Continue => Ty::simple(TypeCtor::Never),
|
Expr::Continue => Ty::simple(TypeCtor::Never),
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue