Add HasResolver trait

This commit is contained in:
Aleksey Kladov 2019-11-20 21:55:33 +03:00
parent 7c275a7ed2
commit 6241cf9a59
9 changed files with 145 additions and 134 deletions

View File

@ -30,7 +30,7 @@
AstItemDef, ConstId, EnumId, FunctionId, MacroDefId, StaticId, StructId, TraitId,
TypeAliasId,
},
resolve::{Resolver, Scope, TypeNs},
resolve::{HasResolver, TypeNs},
ty::{InferenceResult, Namespace, TraitRef},
Either, HasSource, ImportId, Name, ScopeDef, Source, Ty,
};
@ -223,11 +223,6 @@ pub fn diagnostics(self, db: &impl HirDatabase, sink: &mut DiagnosticSink) {
}
}
pub(crate) fn resolver(self, db: &impl DefDatabase) -> Resolver {
let def_map = db.crate_def_map(self.id.krate);
Resolver::default().push_module_scope(def_map, self.id.module_id)
}
pub fn declarations(self, db: &impl DefDatabase) -> Vec<ModuleDef> {
let def_map = db.crate_def_map(self.id.krate);
def_map[self.id.module_id].scope.declarations().map(ModuleDef::from).collect()
@ -315,15 +310,6 @@ pub fn constructor_ty(self, db: &impl HirDatabase) -> Ty {
db.type_for_def(self.into(), Namespace::Values)
}
// FIXME move to a more general type
/// Builds a resolver for type references inside this struct.
pub(crate) fn resolver(self, db: &impl HirDatabase) -> Resolver {
// take the outer scope...
let r = self.module(db).resolver(db);
// ...and add generic params, if present
r.push_generic_params_scope(db, self.into())
}
fn variant_data(self, db: &impl DefDatabase) -> Arc<VariantData> {
db.struct_data(self.id.into()).variant_data.clone()
}
@ -339,22 +325,13 @@ pub fn name(self, db: &impl DefDatabase) -> Option<Name> {
db.struct_data(self.id.into()).name.clone()
}
pub fn module(self, db: &impl HirDatabase) -> Module {
pub fn module(self, db: &impl DefDatabase) -> Module {
Module { id: self.id.0.module(db) }
}
pub fn ty(self, db: &impl HirDatabase) -> Ty {
db.type_for_def(self.into(), Namespace::Types)
}
// FIXME move to a more general type
/// Builds a resolver for type references inside this union.
pub(crate) fn resolver(self, db: &impl HirDatabase) -> Resolver {
// take the outer scope...
let r = self.module(db).resolver(db);
// ...and add generic params, if present
r.push_generic_params_scope(db, self.into())
}
}
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
@ -394,16 +371,6 @@ pub fn variant(self, db: &impl DefDatabase, name: &Name) -> Option<EnumVariant>
pub fn ty(self, db: &impl HirDatabase) -> Ty {
db.type_for_def(self.into(), Namespace::Types)
}
// FIXME: move to a more general type
/// Builds a resolver for type references inside this struct.
pub(crate) fn resolver(self, db: &impl HirDatabase) -> Resolver {
// take the outer scope...
let r = self.module(db).resolver(db);
// ...and add generic params, if present
let r = r.push_generic_params_scope(db, self.into());
r.push_scope(Scope::AdtScope(self.into()))
}
}
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
@ -475,14 +442,6 @@ pub fn krate(self, db: &impl HirDatabase) -> Option<Crate> {
.krate(),
)
}
pub(crate) fn resolver(self, db: &impl HirDatabase) -> Resolver {
match self {
Adt::Struct(it) => it.resolver(db),
Adt::Union(it) => it.resolver(db),
Adt::Enum(it) => it.resolver(db),
}
}
}
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
@ -533,15 +492,6 @@ pub enum DefWithBody {
impl_froms!(DefWithBody: Function, Const, Static);
impl DefWithBody {
/// Builds a resolver for code inside this item.
pub(crate) fn resolver(self, db: &impl HirDatabase) -> Resolver {
match self {
DefWithBody::Const(c) => c.resolver(db),
DefWithBody::Function(f) => f.resolver(db),
DefWithBody::Static(s) => s.resolver(db),
}
}
pub(crate) fn krate(self, db: &impl HirDatabase) -> Option<Crate> {
match self {
DefWithBody::Const(c) => c.krate(db),
@ -738,15 +688,6 @@ pub fn container(self, db: &impl DefDatabase) -> Option<Container> {
}
}
// FIXME: move to a more general type for 'body-having' items
/// Builds a resolver for code inside this item.
pub(crate) fn resolver(self, db: &impl HirDatabase) -> Resolver {
// take the outer scope...
let r = self.container(db).map_or_else(|| self.module(db).resolver(db), |c| c.resolver(db));
// ...and add generic params, if present
r.push_generic_params_scope(db, self.into())
}
pub fn diagnostics(self, db: &impl HirDatabase, sink: &mut DiagnosticSink) {
let infer = self.infer(db);
infer.add_diagnostics(db, self, sink);
@ -804,17 +745,6 @@ pub fn container(self, db: &impl DefDatabase) -> Option<Container> {
ContainerId::ModuleId(_) => None,
}
}
// FIXME: move to a more general type for 'body-having' items
/// Builds a resolver for code inside this item.
pub(crate) fn resolver(self, db: &impl HirDatabase) -> Resolver {
// take the outer scope...
let r = self
.impl_block(db)
.map(|ib| ib.resolver(db))
.unwrap_or_else(|| self.module(db).resolver(db));
r
}
}
#[derive(Debug, Clone, PartialEq, Eq)]
@ -874,12 +804,6 @@ pub fn data(self, db: &impl HirDatabase) -> Arc<ConstData> {
db.static_data(self)
}
/// Builds a resolver for code inside this item.
pub(crate) fn resolver(self, db: &impl HirDatabase) -> Resolver {
// take the outer scope...
self.module(db).resolver(db)
}
pub fn infer(self, db: &impl HirDatabase) -> Arc<InferenceResult> {
db.infer(self.into())
}
@ -975,12 +899,6 @@ pub fn trait_ref(self, db: &impl HirDatabase) -> TraitRef {
pub fn is_auto(self, db: &impl DefDatabase) -> bool {
self.trait_data(db).auto
}
pub(crate) fn resolver(self, db: &impl DefDatabase) -> Resolver {
let r = self.module(db).resolver(db);
// add generic params, if present
r.push_generic_params_scope(db, self.into())
}
}
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
@ -1032,17 +950,6 @@ pub fn ty(self, db: &impl HirDatabase) -> Ty {
pub fn name(self, db: &impl DefDatabase) -> Name {
db.type_alias_data(self).name.clone()
}
/// Builds a resolver for the type references in this type alias.
pub(crate) fn resolver(self, db: &impl HirDatabase) -> Resolver {
// take the outer scope...
let r = self
.impl_block(db)
.map(|ib| ib.resolver(db))
.unwrap_or_else(|| self.module(db).resolver(db));
// ...and add generic params, if present
r.push_generic_params_scope(db, self.into())
}
}
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
@ -1058,15 +965,6 @@ pub enum Container {
}
impl_froms!(Container: Trait, ImplBlock);
impl Container {
pub(crate) fn resolver(self, db: &impl DefDatabase) -> Resolver {
match self {
Container::Trait(trait_) => trait_.resolver(db),
Container::ImplBlock(impl_block) => impl_block.resolver(db),
}
}
}
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub enum AssocItem {
Function(Function),

View File

@ -11,6 +11,7 @@
use crate::{
db::HirDatabase,
diagnostics::{MissingFields, MissingOkInTailExpr},
resolve::HasResolver,
ty::{ApplicationTy, InferenceResult, Ty, TypeCtor},
Adt, DefWithBody, Function, HasBody, Name, Path, Resolver,
};

View File

@ -2,8 +2,8 @@
use std::sync::Arc;
use crate::{
db::{DefDatabase, HirDatabase},
Adt, Const, Container, Enum, EnumVariant, Function, ImplBlock, Struct, Trait, TypeAlias, Union,
db::DefDatabase, Adt, Const, Container, Enum, EnumVariant, Function, ImplBlock, Struct, Trait,
TypeAlias, Union,
};
pub use hir_def::generics::{GenericParam, GenericParams, WherePredicate};
@ -31,20 +31,6 @@ pub enum GenericDef {
Const
);
impl GenericDef {
pub(crate) fn resolver(&self, db: &impl HirDatabase) -> crate::Resolver {
match self {
GenericDef::Function(inner) => inner.resolver(db),
GenericDef::Adt(adt) => adt.resolver(db),
GenericDef::Trait(inner) => inner.resolver(db),
GenericDef::TypeAlias(inner) => inner.resolver(db),
GenericDef::ImplBlock(inner) => inner.resolver(db),
GenericDef::EnumVariant(inner) => inner.parent_enum(db).resolver(db),
GenericDef::Const(inner) => inner.resolver(db),
}
}
}
impl From<Container> for GenericDef {
fn from(c: Container) -> Self {
match c {

View File

@ -5,7 +5,7 @@
use crate::{
db::{AstDatabase, DefDatabase, HirDatabase},
resolve::Resolver,
resolve::HasResolver,
ty::Ty,
AssocItem, Crate, HasSource, ImplBlock, Module, Source, TraitRef,
};
@ -50,12 +50,4 @@ pub fn module(&self, db: &impl DefDatabase) -> Module {
pub fn krate(&self, db: &impl DefDatabase) -> Crate {
Crate { crate_id: self.module(db).id.krate }
}
pub(crate) fn resolver(self, db: &impl DefDatabase) -> Resolver {
let r = self.module(db).resolver(db);
// add generic params, if present
let r = r.push_generic_params_scope(db, self.into());
let r = r.push_impl_block_scope(self);
r
}
}

View File

@ -15,8 +15,8 @@
db::{DefDatabase, HirDatabase},
expr::{ExprScopes, PatId, ScopeId},
generics::{GenericParams, HasGenericParams},
Adt, Const, DefWithBody, Enum, EnumVariant, Function, GenericDef, ImplBlock, Local, MacroDef,
ModuleDef, PerNs, Static, Struct, Trait, TypeAlias,
Adt, Const, Container, DefWithBody, Enum, EnumVariant, Function, GenericDef, ImplBlock, Local,
MacroDef, Module, ModuleDef, PerNs, Static, Struct, Trait, TypeAlias, Union,
};
#[derive(Debug, Clone, Default)]
@ -486,3 +486,130 @@ fn process_names(&self, db: &impl HirDatabase, f: &mut dyn FnMut(Name, ScopeDef)
}
}
}
pub(crate) trait HasResolver {
/// Builds a resolver for type references inside this def.
fn resolver(self, db: &impl DefDatabase) -> Resolver;
}
impl HasResolver for Module {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
let def_map = db.crate_def_map(self.id.krate);
Resolver::default().push_module_scope(def_map, self.id.module_id)
}
}
impl HasResolver for Trait {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
self.module(db).resolver(db).push_generic_params_scope(db, self.into())
}
}
impl HasResolver for Struct {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
self.module(db)
.resolver(db)
.push_generic_params_scope(db, self.into())
.push_scope(Scope::AdtScope(self.into()))
}
}
impl HasResolver for Union {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
self.module(db)
.resolver(db)
.push_generic_params_scope(db, self.into())
.push_scope(Scope::AdtScope(self.into()))
}
}
impl HasResolver for Enum {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
self.module(db)
.resolver(db)
.push_generic_params_scope(db, self.into())
.push_scope(Scope::AdtScope(self.into()))
}
}
impl HasResolver for Adt {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
match self {
Adt::Struct(it) => it.resolver(db),
Adt::Union(it) => it.resolver(db),
Adt::Enum(it) => it.resolver(db),
}
}
}
impl HasResolver for Function {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
self.container(db)
.map(|c| c.resolver(db))
.unwrap_or_else(|| self.module(db).resolver(db))
.push_generic_params_scope(db, self.into())
}
}
impl HasResolver for DefWithBody {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
match self {
DefWithBody::Const(c) => c.resolver(db),
DefWithBody::Function(f) => f.resolver(db),
DefWithBody::Static(s) => s.resolver(db),
}
}
}
impl HasResolver for Const {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
self.container(db).map(|c| c.resolver(db)).unwrap_or_else(|| self.module(db).resolver(db))
}
}
impl HasResolver for Static {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
self.module(db).resolver(db)
}
}
impl HasResolver for TypeAlias {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
self.container(db)
.map(|ib| ib.resolver(db))
.unwrap_or_else(|| self.module(db).resolver(db))
.push_generic_params_scope(db, self.into())
}
}
impl HasResolver for Container {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
match self {
Container::Trait(trait_) => trait_.resolver(db),
Container::ImplBlock(impl_block) => impl_block.resolver(db),
}
}
}
impl HasResolver for GenericDef {
fn resolver(self, db: &impl DefDatabase) -> crate::Resolver {
match self {
GenericDef::Function(inner) => inner.resolver(db),
GenericDef::Adt(adt) => adt.resolver(db),
GenericDef::Trait(inner) => inner.resolver(db),
GenericDef::TypeAlias(inner) => inner.resolver(db),
GenericDef::ImplBlock(inner) => inner.resolver(db),
GenericDef::EnumVariant(inner) => inner.parent_enum(db).resolver(db),
GenericDef::Const(inner) => inner.resolver(db),
}
}
}
impl HasResolver for ImplBlock {
fn resolver(self, db: &impl DefDatabase) -> Resolver {
self.module(db)
.resolver(db)
.push_generic_params_scope(db, self.into())
.push_impl_block_scope(self)
}
}

View File

@ -23,7 +23,7 @@
db::HirDatabase,
expr::{self, BodySourceMap, ExprScopes, ScopeId},
ids::LocationCtx,
resolve::{ScopeDef, TypeNs, ValueNs},
resolve::{HasResolver, ScopeDef, TypeNs, ValueNs},
ty::method_resolution::{self, implements_trait},
AssocItem, Const, DefWithBody, Either, Enum, FromSource, Function, GenericParam, HasBody,
HirFileId, Local, MacroDef, Module, Name, Path, Resolver, Static, Struct, Ty,

View File

@ -40,7 +40,7 @@
code_model::TypeAlias,
db::HirDatabase,
expr::{BindingAnnotation, Body, ExprId, PatId},
resolve::{Resolver, TypeNs},
resolve::{HasResolver, Resolver, TypeNs},
ty::infer::diagnostics::InferenceDiagnostic,
Adt, AssocItem, ConstData, DefWithBody, FloatTy, FnData, Function, HasBody, IntTy, Path,
StructField, VariantDef,

View File

@ -22,7 +22,7 @@
db::HirDatabase,
generics::HasGenericParams,
generics::{GenericDef, WherePredicate},
resolve::{Resolver, TypeNs},
resolve::{HasResolver, Resolver, TypeNs},
ty::{
primitive::{FloatTy, IntTy, Uncertain},
Adt,

View File

@ -304,6 +304,13 @@ struct X<T> {
),
@r###"
[
CompletionItem {
label: "Self",
source_range: [54; 54),
delete: [54; 54),
insert: "Self",
kind: TypeParam,
},
CompletionItem {
label: "T",
source_range: [54; 54),