Use ids for Callable

This commit is contained in:
Aleksey Kladov 2019-11-25 16:26:52 +03:00
parent 9047a4ad46
commit 78791d6fac
4 changed files with 50 additions and 34 deletions

View file

@ -171,7 +171,7 @@ impl TypeCtor {
| TypeCtor::Tuple { .. } => None, | TypeCtor::Tuple { .. } => None,
TypeCtor::Closure { def, .. } => def.krate(db), TypeCtor::Closure { def, .. } => def.krate(db),
TypeCtor::Adt(adt) => adt.krate(db), TypeCtor::Adt(adt) => adt.krate(db),
TypeCtor::FnDef(callable) => callable.krate(db), TypeCtor::FnDef(callable) => Some(callable.krate(db).into()),
TypeCtor::AssociatedType(type_alias) => type_alias.krate(db), TypeCtor::AssociatedType(type_alias) => type_alias.krate(db),
} }
} }
@ -856,13 +856,20 @@ impl HirDisplay for ApplicationTy {
TypeCtor::FnDef(def) => { TypeCtor::FnDef(def) => {
let sig = f.db.callable_item_signature(def); let sig = f.db.callable_item_signature(def);
let name = match def { let name = match def {
CallableDef::Function(ff) => ff.name(f.db), CallableDef::FunctionId(ff) => f.db.function_data(ff).name.clone(),
CallableDef::Struct(s) => s.name(f.db).unwrap_or_else(Name::missing), CallableDef::StructId(s) => {
CallableDef::EnumVariant(e) => e.name(f.db).unwrap_or_else(Name::missing), f.db.struct_data(s.0).name.clone().unwrap_or_else(Name::missing)
}
CallableDef::EnumVariantId(e) => {
let enum_data = f.db.enum_data(e.parent);
enum_data.variants[e.local_id].name.clone().unwrap_or_else(Name::missing)
}
}; };
match def { match def {
CallableDef::Function(_) => write!(f, "fn {}", name)?, CallableDef::FunctionId(_) => write!(f, "fn {}", name)?,
CallableDef::Struct(_) | CallableDef::EnumVariant(_) => write!(f, "{}", name)?, CallableDef::StructId(_) | CallableDef::EnumVariantId(_) => {
write!(f, "{}", name)?
}
} }
if self.parameters.len() > 0 { if self.parameters.len() > 0 {
write!(f, "<")?; write!(f, "<")?;

View file

@ -8,6 +8,7 @@ use hir_def::{
generics::GenericParams, generics::GenericParams,
path::{GenericArg, GenericArgs}, path::{GenericArg, GenericArgs},
resolver::resolver_for_expr, resolver::resolver_for_expr,
ContainerId, Lookup,
}; };
use hir_expand::name; use hir_expand::name;
@ -660,18 +661,21 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> {
} }
// add obligation for trait implementation, if this is a trait method // add obligation for trait implementation, if this is a trait method
match def { match def {
CallableDef::Function(f) => { CallableDef::FunctionId(f) => {
if let Some(trait_) = f.parent_trait(self.db) { if let ContainerId::TraitId(trait_) = f.lookup(self.db).container {
// construct a TraitDef // construct a TraitDef
let substs = a_ty.parameters.prefix( let substs = a_ty.parameters.prefix(
self.db self.db
.generic_params(trait_.id.into()) .generic_params(trait_.into())
.count_params_including_parent(), .count_params_including_parent(),
); );
self.obligations.push(Obligation::Trait(TraitRef { trait_, substs })); self.obligations.push(Obligation::Trait(TraitRef {
trait_: trait_.into(),
substs,
}));
} }
} }
CallableDef::Struct(_) | CallableDef::EnumVariant(_) => {} CallableDef::StructId(_) | CallableDef::EnumVariantId(_) => {}
} }
} }
} }

View file

@ -14,9 +14,11 @@ use hir_def::{
path::{GenericArg, PathSegment}, path::{GenericArg, PathSegment},
resolver::{HasResolver, Resolver, TypeNs}, resolver::{HasResolver, Resolver, TypeNs},
type_ref::{TypeBound, TypeRef}, type_ref::{TypeBound, TypeRef},
AdtId, EnumVariantId, FunctionId, GenericDefId, LocalStructFieldId, StructId, VariantId, AdtId, AstItemDef, EnumVariantId, FunctionId, GenericDefId, HasModule, LocalStructFieldId,
Lookup, StructId, VariantId,
}; };
use ra_arena::map::ArenaMap; use ra_arena::map::ArenaMap;
use ra_db::CrateId;
use super::{ use super::{
FnSig, GenericPredicate, ProjectionPredicate, ProjectionTy, Substs, TraitEnvironment, TraitRef, FnSig, GenericPredicate, ProjectionPredicate, ProjectionTy, Substs, TraitEnvironment, TraitRef,
@ -546,9 +548,9 @@ pub(crate) fn type_for_def(db: &impl HirDatabase, def: TypableDef, ns: Namespace
/// Build the signature of a callable item (function, struct or enum variant). /// Build the signature of a callable item (function, struct or enum variant).
pub(crate) fn callable_item_sig(db: &impl HirDatabase, def: CallableDef) -> FnSig { pub(crate) fn callable_item_sig(db: &impl HirDatabase, def: CallableDef) -> FnSig {
match def { match def {
CallableDef::Function(f) => fn_sig_for_fn(db, f.id), CallableDef::FunctionId(f) => fn_sig_for_fn(db, f),
CallableDef::Struct(s) => fn_sig_for_struct_constructor(db, s.id), CallableDef::StructId(s) => fn_sig_for_struct_constructor(db, s),
CallableDef::EnumVariant(e) => fn_sig_for_enum_variant_constructor(db, e.into()), CallableDef::EnumVariantId(e) => fn_sig_for_enum_variant_constructor(db, e),
} }
} }
@ -643,7 +645,7 @@ fn fn_sig_for_fn(db: &impl HirDatabase, def: FunctionId) -> FnSig {
fn type_for_fn(db: &impl HirDatabase, def: Function) -> Ty { fn type_for_fn(db: &impl HirDatabase, def: Function) -> Ty {
let generics = db.generic_params(def.id.into()); let generics = db.generic_params(def.id.into());
let substs = Substs::identity(&generics); let substs = Substs::identity(&generics);
Ty::apply(TypeCtor::FnDef(def.into()), substs) Ty::apply(TypeCtor::FnDef(def.id.into()), substs)
} }
/// Build the declared type of a const. /// Build the declared type of a const.
@ -723,7 +725,7 @@ fn type_for_struct_constructor(db: &impl HirDatabase, def: Struct) -> Ty {
} }
let generics = db.generic_params(def.id.into()); let generics = db.generic_params(def.id.into());
let substs = Substs::identity(&generics); let substs = Substs::identity(&generics);
Ty::apply(TypeCtor::FnDef(def.into()), substs) Ty::apply(TypeCtor::FnDef(def.id.into()), substs)
} }
fn fn_sig_for_enum_variant_constructor(db: &impl HirDatabase, def: EnumVariantId) -> FnSig { fn fn_sig_for_enum_variant_constructor(db: &impl HirDatabase, def: EnumVariantId) -> FnSig {
@ -749,7 +751,7 @@ fn type_for_enum_variant_constructor(db: &impl HirDatabase, def: EnumVariant) ->
} }
let generics = db.generic_params(def.parent_enum(db).id.into()); let generics = db.generic_params(def.parent_enum(db).id.into());
let substs = Substs::identity(&generics); let substs = Substs::identity(&generics);
Ty::apply(TypeCtor::FnDef(def.into()), substs) Ty::apply(TypeCtor::FnDef(EnumVariantId::from(def).into()), substs)
} }
fn type_for_adt(db: &impl HirDatabase, adt: impl Into<Adt>) -> Ty { fn type_for_adt(db: &impl HirDatabase, adt: impl Into<Adt>) -> Ty {
@ -806,18 +808,18 @@ impl From<ModuleDef> for Option<TypableDef> {
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
pub enum CallableDef { pub enum CallableDef {
Function(Function), FunctionId(FunctionId),
Struct(Struct), StructId(StructId),
EnumVariant(EnumVariant), EnumVariantId(EnumVariantId),
} }
impl_froms!(CallableDef: Function, Struct, EnumVariant); impl_froms!(CallableDef: FunctionId, StructId, EnumVariantId);
impl CallableDef { impl CallableDef {
pub fn krate(self, db: &impl HirDatabase) -> Option<crate::Crate> { pub fn krate(self, db: &impl HirDatabase) -> CrateId {
match self { match self {
CallableDef::Function(f) => f.krate(db), CallableDef::FunctionId(f) => f.lookup(db).module(db).krate,
CallableDef::Struct(s) => s.krate(db), CallableDef::StructId(s) => s.0.module(db).krate,
CallableDef::EnumVariant(e) => e.parent_enum(db).krate(db), CallableDef::EnumVariantId(e) => e.parent.module(db).krate,
} }
} }
} }
@ -825,9 +827,9 @@ impl CallableDef {
impl From<CallableDef> for GenericDefId { impl From<CallableDef> for GenericDefId {
fn from(def: CallableDef) -> GenericDefId { fn from(def: CallableDef) -> GenericDefId {
match def { match def {
CallableDef::Function(f) => f.id.into(), CallableDef::FunctionId(f) => f.into(),
CallableDef::Struct(s) => s.id.into(), CallableDef::StructId(s) => s.into(),
CallableDef::EnumVariant(e) => EnumVariantId::from(e).into(), CallableDef::EnumVariantId(e) => e.into(),
} }
} }
} }

View file

@ -26,14 +26,17 @@ pub(crate) fn call_info(db: &RootDatabase, position: FilePosition) -> Option<Cal
); );
let (mut call_info, has_self) = match &calling_node { let (mut call_info, has_self) = match &calling_node {
FnCallNode::CallExpr(expr) => { FnCallNode::CallExpr(expr) => {
//FIXME: apply subst //FIXME: don't poke into Ty
let (callable_def, _subst) = analyzer.type_of(db, &expr.expr()?)?.as_callable()?; let (callable_def, _subst) = analyzer.type_of(db, &expr.expr()?)?.as_callable()?;
match callable_def { match callable_def {
hir::CallableDef::Function(it) => { hir::CallableDef::FunctionId(it) => {
(CallInfo::with_fn(db, it), it.has_self_param(db)) let fn_def = it.into();
(CallInfo::with_fn(db, fn_def), fn_def.has_self_param(db))
}
hir::CallableDef::StructId(it) => (CallInfo::with_struct(db, it.into())?, false),
hir::CallableDef::EnumVariantId(it) => {
(CallInfo::with_enum_variant(db, it.into())?, false)
} }
hir::CallableDef::Struct(it) => (CallInfo::with_struct(db, it)?, false),
hir::CallableDef::EnumVariant(it) => (CallInfo::with_enum_variant(db, it)?, false),
} }
} }
FnCallNode::MethodCallExpr(expr) => { FnCallNode::MethodCallExpr(expr) => {