Remove TraitItem and ImplItem in favor of AssocItem

This commit is contained in:
Florian Diebold 2019-09-16 22:01:13 +02:00
parent 53a932509d
commit a040fde3ae
9 changed files with 46 additions and 93 deletions

View file

@ -1,7 +1,7 @@
use std::{collections::HashSet, fmt::Write, path::Path, time::Instant}; use std::{collections::HashSet, fmt::Write, path::Path, time::Instant};
use ra_db::SourceDatabase; use ra_db::SourceDatabase;
use ra_hir::{Crate, HasBodySource, HasSource, HirDisplay, ImplItem, ModuleDef, Ty, TypeWalk}; use ra_hir::{AssocItem, Crate, HasBodySource, HasSource, HirDisplay, ModuleDef, Ty, TypeWalk};
use ra_syntax::AstNode; use ra_syntax::AstNode;
use crate::{Result, Verbosity}; use crate::{Result, Verbosity};
@ -47,7 +47,7 @@ pub fn run(
for impl_block in module.impl_blocks(db) { for impl_block in module.impl_blocks(db) {
for item in impl_block.items(db) { for item in impl_block.items(db) {
num_decls += 1; num_decls += 1;
if let ImplItem::Method(f) = item { if let AssocItem::Function(f) = item {
funcs.push(f); funcs.push(f);
} }
} }

View file

@ -23,7 +23,7 @@ use crate::{
}, },
nameres::{CrateModuleId, ImportId, ModuleScope, Namespace}, nameres::{CrateModuleId, ImportId, ModuleScope, Namespace},
resolve::{Resolver, TypeNs}, resolve::{Resolver, TypeNs},
traits::{TraitData, TraitItem}, traits::TraitData,
ty::{ ty::{
primitive::{FloatBitness, FloatTy, IntBitness, IntTy, Signedness}, primitive::{FloatBitness, FloatTy, IntBitness, IntTy, Signedness},
InferenceResult, TraitRef, InferenceResult, TraitRef,
@ -269,7 +269,7 @@ impl Module {
for impl_block in self.impl_blocks(db) { for impl_block in self.impl_blocks(db) {
for item in impl_block.items(db) { for item in impl_block.items(db) {
if let crate::ImplItem::Method(f) = item { if let AssocItem::Function(f) = item {
f.diagnostics(db, sink); f.diagnostics(db, sink);
} }
} }
@ -853,7 +853,7 @@ impl Trait {
self.trait_data(db).name().clone() self.trait_data(db).name().clone()
} }
pub fn items(self, db: &impl DefDatabase) -> Vec<TraitItem> { pub fn items(self, db: &impl DefDatabase) -> Vec<AssocItem> {
self.trait_data(db).items().to_vec() self.trait_data(db).items().to_vec()
} }
@ -906,7 +906,7 @@ impl Trait {
.items() .items()
.iter() .iter()
.filter_map(|item| match item { .filter_map(|item| match item {
TraitItem::TypeAlias(t) => Some(*t), AssocItem::TypeAlias(t) => Some(*t),
_ => None, _ => None,
}) })
.find(|t| &t.name(db) == name) .find(|t| &t.name(db) == name)
@ -1030,23 +1030,8 @@ pub enum AssocItem {
Const(Const), Const(Const),
TypeAlias(TypeAlias), TypeAlias(TypeAlias),
} }
// FIXME: not every function, ... is actually an assoc item. maybe we should make
impl From<TraitItem> for AssocItem { // sure that you can only turn actual assoc items into AssocItems. This would
fn from(t: TraitItem) -> Self { // require not implementing From, and instead having some checked way of
match t { // casting them, and somehow making the constructors private, which would be annoying.
TraitItem::Function(f) => AssocItem::Function(f), impl_froms!(AssocItem: Function, Const, TypeAlias);
TraitItem::Const(c) => AssocItem::Const(c),
TraitItem::TypeAlias(t) => AssocItem::TypeAlias(t),
}
}
}
impl From<crate::ImplItem> for AssocItem {
fn from(i: crate::ImplItem) -> Self {
match i {
crate::ImplItem::Method(f) => AssocItem::Function(f),
crate::ImplItem::Const(c) => AssocItem::Const(c),
crate::ImplItem::TypeAlias(t) => AssocItem::TypeAlias(t),
}
}
}

View file

@ -15,7 +15,7 @@ use crate::{
resolve::Resolver, resolve::Resolver,
ty::Ty, ty::Ty,
type_ref::TypeRef, type_ref::TypeRef,
Const, Function, HasSource, HirFileId, Source, TraitRef, TypeAlias, AssocItem, Const, Function, HasSource, HirFileId, Source, TraitRef, TypeAlias,
}; };
#[derive(Debug, Default, PartialEq, Eq)] #[derive(Debug, Default, PartialEq, Eq)]
@ -56,7 +56,7 @@ impl HasSource for ImplBlock {
impl ImplBlock { impl ImplBlock {
pub(crate) fn containing( pub(crate) fn containing(
module_impl_blocks: Arc<ModuleImplBlocks>, module_impl_blocks: Arc<ModuleImplBlocks>,
item: ImplItem, item: AssocItem,
) -> Option<ImplBlock> { ) -> Option<ImplBlock> {
let impl_id = *module_impl_blocks.impls_by_def.get(&item)?; let impl_id = *module_impl_blocks.impls_by_def.get(&item)?;
Some(ImplBlock { module: module_impl_blocks.module, impl_id }) Some(ImplBlock { module: module_impl_blocks.module, impl_id })
@ -91,7 +91,7 @@ impl ImplBlock {
TraitRef::from_hir(db, &self.resolver(db), &self.target_trait(db)?, Some(target_ty)) TraitRef::from_hir(db, &self.resolver(db), &self.target_trait(db)?, Some(target_ty))
} }
pub fn items(&self, db: &impl DefDatabase) -> Vec<ImplItem> { pub fn items(&self, db: &impl DefDatabase) -> Vec<AssocItem> {
db.impls_in_module(self.module).impls[self.impl_id].items().to_vec() db.impls_in_module(self.module).impls[self.impl_id].items().to_vec()
} }
@ -113,7 +113,7 @@ impl ImplBlock {
pub struct ImplData { pub struct ImplData {
target_trait: Option<TypeRef>, target_trait: Option<TypeRef>,
target_type: TypeRef, target_type: TypeRef,
items: Vec<ImplItem>, items: Vec<AssocItem>,
negative: bool, negative: bool,
} }
@ -151,27 +151,11 @@ impl ImplData {
&self.target_type &self.target_type
} }
pub fn items(&self) -> &[ImplItem] { pub fn items(&self) -> &[AssocItem] {
&self.items &self.items
} }
} }
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
//FIXME: rename to ImplDef?
pub enum ImplItem {
Method(Function),
Const(Const),
TypeAlias(TypeAlias),
// Existential
}
impl_froms!(ImplItem: Const, TypeAlias);
impl From<Function> for ImplItem {
fn from(func: Function) -> ImplItem {
ImplItem::Method(func)
}
}
#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)] #[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
pub struct ImplId(pub RawId); pub struct ImplId(pub RawId);
impl_arena_id!(ImplId); impl_arena_id!(ImplId);
@ -185,7 +169,7 @@ impl_arena_id!(ImplId);
pub struct ModuleImplBlocks { pub struct ModuleImplBlocks {
pub(crate) module: Module, pub(crate) module: Module,
pub(crate) impls: Arena<ImplId, ImplData>, pub(crate) impls: Arena<ImplId, ImplData>,
impls_by_def: FxHashMap<ImplItem, ImplId>, impls_by_def: FxHashMap<AssocItem, ImplId>,
} }
impl ModuleImplBlocks { impl ModuleImplBlocks {

View file

@ -69,7 +69,7 @@ pub use self::{
expr::ExprScopes, expr::ExprScopes,
generics::{GenericParam, GenericParams, HasGenericParams}, generics::{GenericParam, GenericParams, HasGenericParams},
ids::{HirFileId, MacroCallId, MacroCallLoc, MacroDefId, MacroFile}, ids::{HirFileId, MacroCallId, MacroCallLoc, MacroDefId, MacroFile},
impl_block::{ImplBlock, ImplItem}, impl_block::ImplBlock,
name::Name, name::Name,
nameres::{ImportId, Namespace, PerNs}, nameres::{ImportId, Namespace, PerNs},
path::{Path, PathKind}, path::{Path, PathKind},

View file

@ -9,13 +9,13 @@ use crate::{
db::{AstDatabase, DefDatabase}, db::{AstDatabase, DefDatabase},
ids::LocationCtx, ids::LocationCtx,
name::AsName, name::AsName,
Const, Function, HasSource, Module, Name, Trait, TypeAlias, AssocItem, Const, Function, HasSource, Module, Name, Trait, TypeAlias,
}; };
#[derive(Debug, Clone, PartialEq, Eq)] #[derive(Debug, Clone, PartialEq, Eq)]
pub struct TraitData { pub struct TraitData {
name: Option<Name>, name: Option<Name>,
items: Vec<TraitItem>, items: Vec<AssocItem>,
auto: bool, auto: bool,
} }
@ -48,7 +48,7 @@ impl TraitData {
&self.name &self.name
} }
pub(crate) fn items(&self) -> &[TraitItem] { pub(crate) fn items(&self) -> &[AssocItem] {
&self.items &self.items
} }
@ -57,22 +57,9 @@ impl TraitData {
} }
} }
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
pub enum TraitItem {
Function(Function),
Const(Const),
TypeAlias(TypeAlias),
// Existential
}
// FIXME: not every function, ... is actually a trait item. maybe we should make
// sure that you can only turn actual trait items into TraitItems. This would
// require not implementing From, and instead having some checked way of
// casting them.
impl_froms!(TraitItem: Function, Const, TypeAlias);
#[derive(Debug, Clone, PartialEq, Eq)] #[derive(Debug, Clone, PartialEq, Eq)]
pub struct TraitItemsIndex { pub struct TraitItemsIndex {
traits_by_def: FxHashMap<TraitItem, Trait>, traits_by_def: FxHashMap<AssocItem, Trait>,
} }
impl TraitItemsIndex { impl TraitItemsIndex {
@ -88,7 +75,7 @@ impl TraitItemsIndex {
index index
} }
pub(crate) fn get_parent_trait(&self, item: TraitItem) -> Option<Trait> { pub(crate) fn get_parent_trait(&self, item: AssocItem) -> Option<Trait> {
self.traits_by_def.get(&item).cloned() self.traits_by_def.get(&item).cloned()
} }
} }

View file

@ -576,34 +576,32 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> {
// Find impl // Find impl
// FIXME: consider trait candidates // FIXME: consider trait candidates
let def = ty.clone().iterate_impl_items(self.db, krate, |item| match item { let item = ty.clone().iterate_impl_items(self.db, krate, |item| match item {
crate::ImplItem::Method(func) => { AssocItem::Function(func) => {
if segment.name == func.name(self.db) { if segment.name == func.name(self.db) {
Some(ValueNs::Function(func)) Some(AssocItem::Function(func))
} else { } else {
None None
} }
} }
crate::ImplItem::Const(konst) => { AssocItem::Const(konst) => {
if konst.name(self.db).map_or(false, |n| n == segment.name) { if konst.name(self.db).map_or(false, |n| n == segment.name) {
Some(ValueNs::Const(konst)) Some(AssocItem::Const(konst))
} else { } else {
None None
} }
} }
crate::ImplItem::TypeAlias(_) => None, AssocItem::TypeAlias(_) => None,
})?; })?;
let def = match item {
AssocItem::Function(f) => ValueNs::Function(f),
AssocItem::Const(c) => ValueNs::Const(c),
AssocItem::TypeAlias(_) => unreachable!(),
};
let substs = self.find_self_types(&def, ty); let substs = self.find_self_types(&def, ty);
self.write_assoc_resolution( self.write_assoc_resolution(id, item);
id,
match def {
ValueNs::Function(f) => AssocItem::Function(f),
ValueNs::Const(c) => AssocItem::Const(c),
_ => unreachable!(),
},
);
Some((def, substs)) Some((def, substs))
} }

View file

@ -11,13 +11,12 @@ use super::{autoderef, lower, Canonical, InEnvironment, TraitEnvironment, TraitR
use crate::{ use crate::{
db::HirDatabase, db::HirDatabase,
generics::HasGenericParams, generics::HasGenericParams,
impl_block::{ImplBlock, ImplId, ImplItem}, impl_block::{ImplBlock, ImplId},
nameres::CrateModuleId, nameres::CrateModuleId,
resolve::Resolver, resolve::Resolver,
traits::TraitItem,
ty::primitive::{FloatBitness, UncertainFloatTy, UncertainIntTy}, ty::primitive::{FloatBitness, UncertainFloatTy, UncertainIntTy},
ty::{Ty, TypeCtor}, ty::{Ty, TypeCtor},
Crate, Function, Module, Name, Trait, AssocItem, Crate, Function, Module, Name, Trait,
}; };
/// This is used as a key for indexing impls. /// This is used as a key for indexing impls.
@ -232,7 +231,7 @@ fn iterate_trait_method_candidates<T>(
// iteration // iteration
let mut known_implemented = inherently_implemented; let mut known_implemented = inherently_implemented;
for item in data.items() { for item in data.items() {
if let TraitItem::Function(m) = *item { if let AssocItem::Function(m) = *item {
let data = m.data(db); let data = m.data(db);
if name.map_or(true, |name| data.name() == name) && data.has_self_param() { if name.map_or(true, |name| data.name() == name) && data.has_self_param() {
if !known_implemented { if !known_implemented {
@ -264,7 +263,7 @@ fn iterate_inherent_methods<T>(
for impl_block in impls.lookup_impl_blocks(&ty.value) { for impl_block in impls.lookup_impl_blocks(&ty.value) {
for item in impl_block.items(db) { for item in impl_block.items(db) {
if let ImplItem::Method(f) = item { if let AssocItem::Function(f) = item {
let data = f.data(db); let data = f.data(db);
if name.map_or(true, |name| data.name() == name) && data.has_self_param() { if name.map_or(true, |name| data.name() == name) && data.has_self_param() {
if let Some(result) = callback(&ty.value, f) { if let Some(result) = callback(&ty.value, f) {
@ -304,7 +303,7 @@ impl Ty {
self, self,
db: &impl HirDatabase, db: &impl HirDatabase,
krate: Crate, krate: Crate,
mut callback: impl FnMut(ImplItem) -> Option<T>, mut callback: impl FnMut(AssocItem) -> Option<T>,
) -> Option<T> { ) -> Option<T> {
for krate in def_crates(db, krate, &self)? { for krate in def_crates(db, krate, &self)? {
let impls = db.impls_in_crate(krate); let impls = db.impls_in_crate(krate);

View file

@ -21,7 +21,7 @@ use crate::{
ApplicationTy, CallableDef, GenericPredicate, ProjectionTy, Substs, TraitRef, Ty, TypeCtor, ApplicationTy, CallableDef, GenericPredicate, ProjectionTy, Substs, TraitRef, Ty, TypeCtor,
TypeWalk, TypeWalk,
}, },
Crate, HasGenericParams, ImplBlock, ImplItem, Trait, TypeAlias, AssocItem, Crate, HasGenericParams, ImplBlock, Trait, TypeAlias,
}; };
/// This represents a trait whose name we could not resolve. /// This represents a trait whose name we could not resolve.
@ -496,7 +496,7 @@ pub(crate) fn trait_datum_query(
.items(db) .items(db)
.into_iter() .into_iter()
.filter_map(|trait_item| match trait_item { .filter_map(|trait_item| match trait_item {
crate::traits::TraitItem::TypeAlias(type_alias) => Some(type_alias), crate::AssocItem::TypeAlias(type_alias) => Some(type_alias),
_ => None, _ => None,
}) })
.map(|type_alias| type_alias.to_chalk(db)) .map(|type_alias| type_alias.to_chalk(db))
@ -616,7 +616,7 @@ pub(crate) fn impl_datum_query(
.items(db) .items(db)
.into_iter() .into_iter()
.filter_map(|item| match item { .filter_map(|item| match item {
ImplItem::TypeAlias(t) => Some(t), AssocItem::TypeAlias(t) => Some(t),
_ => None, _ => None,
}) })
.filter_map(|t| { .filter_map(|t| {

View file

@ -52,14 +52,14 @@ pub(super) fn complete_path(acc: &mut Completions, ctx: &CompletionContext) {
if let Some(krate) = krate { if let Some(krate) = krate {
ty.iterate_impl_items(ctx.db, krate, |item| { ty.iterate_impl_items(ctx.db, krate, |item| {
match item { match item {
hir::ImplItem::Method(func) => { hir::AssocItem::Function(func) => {
let data = func.data(ctx.db); let data = func.data(ctx.db);
if !data.has_self_param() { if !data.has_self_param() {
acc.add_function(ctx, func); acc.add_function(ctx, func);
} }
} }
hir::ImplItem::Const(ct) => acc.add_const(ctx, ct), hir::AssocItem::Const(ct) => acc.add_const(ctx, ct),
hir::ImplItem::TypeAlias(ty) => acc.add_type_alias(ctx, ty), hir::AssocItem::TypeAlias(ty) => acc.add_type_alias(ctx, ty),
} }
None::<()> None::<()>
}); });