From 36e3fc9d5413f7e6e17e82867aae1318645880a3 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Wed, 20 Nov 2019 09:40:36 +0300 Subject: Rename Source::ast -> Source::value --- crates/ra_hir_def/src/lib.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'crates/ra_hir_def/src/lib.rs') diff --git a/crates/ra_hir_def/src/lib.rs b/crates/ra_hir_def/src/lib.rs index a240a10b8..50caf4f83 100644 --- a/crates/ra_hir_def/src/lib.rs +++ b/crates/ra_hir_def/src/lib.rs @@ -80,7 +80,7 @@ impl ModuleSource { pub fn from_child_node(db: &impl db::DefDatabase2, child: Source<&SyntaxNode>) -> ModuleSource { if let Some(m) = - child.ast.ancestors().filter_map(ast::Module::cast).find(|it| !it.has_semi()) + child.value.ancestors().filter_map(ast::Module::cast).find(|it| !it.has_semi()) { ModuleSource::Module(m) } else { @@ -184,8 +184,8 @@ pub trait AstItemDef: salsa::InternKey + Clone { } fn source(self, db: &(impl AstDatabase + InternDatabase)) -> Source { let loc = self.lookup_intern(db); - let ast = loc.ast_id.to_node(db); - Source { file_id: loc.ast_id.file_id(), ast } + let value = loc.ast_id.to_node(db); + Source { file_id: loc.ast_id.file_id(), value } } fn module(self, db: &impl InternDatabase) -> ModuleId { let loc = self.lookup_intern(db); -- cgit v1.2.3 From e1a6e38767c1e47e5e88a97a9ef5b4547390803c Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Wed, 20 Nov 2019 12:25:02 +0300 Subject: Move Generics to hir_def --- crates/ra_hir_def/src/lib.rs | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) (limited to 'crates/ra_hir_def/src/lib.rs') diff --git a/crates/ra_hir_def/src/lib.rs b/crates/ra_hir_def/src/lib.rs index 50caf4f83..dffc82ff8 100644 --- a/crates/ra_hir_def/src/lib.rs +++ b/crates/ra_hir_def/src/lib.rs @@ -17,6 +17,7 @@ pub mod imp; pub mod diagnostics; pub mod expr; pub mod body; +pub mod generics; #[cfg(test)] mod test_db; @@ -408,3 +409,26 @@ pub enum AssocItemId { // require not implementing From, and instead having some checked way of // casting them, and somehow making the constructors private, which would be annoying. impl_froms!(AssocItemId: FunctionId, ConstId, TypeAliasId); + +#[derive(Clone, Copy, PartialEq, Eq, Debug, Hash)] +pub enum GenericDefId { + FunctionId(FunctionId), + AdtId(AdtId), + TraitId(TraitId), + TypeAliasId(TypeAliasId), + ImplId(ImplId), + // enum variants cannot have generics themselves, but their parent enums + // can, and this makes some code easier to write + EnumVariantId(EnumVariantId), + // consts can have type parameters from their parents (i.e. associated consts of traits) + ConstId(ConstId), +} +impl_froms!( + GenericDefId: FunctionId, + AdtId(StructId, EnumId, UnionId), + TraitId, + TypeAliasId, + ImplId, + EnumVariantId, + ConstId +); -- cgit v1.2.3 From 06fa3d8389c833b01f482bf35b0f850e627612b9 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Wed, 20 Nov 2019 14:22:06 +0300 Subject: Move traits to hir_def --- crates/ra_hir_def/src/lib.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'crates/ra_hir_def/src/lib.rs') diff --git a/crates/ra_hir_def/src/lib.rs b/crates/ra_hir_def/src/lib.rs index dffc82ff8..38c110570 100644 --- a/crates/ra_hir_def/src/lib.rs +++ b/crates/ra_hir_def/src/lib.rs @@ -13,11 +13,12 @@ pub mod path; pub mod type_ref; pub mod builtin_type; pub mod adt; -pub mod imp; +pub mod impls; pub mod diagnostics; pub mod expr; pub mod body; pub mod generics; +pub mod traits; #[cfg(test)] mod test_db; -- cgit v1.2.3 From cebeedc66fc40097eae20bf1767a285d00269966 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Wed, 20 Nov 2019 16:03:59 +0300 Subject: Next gen IDs for functions The current system with AstIds has two primaraly drawbacks: * It is possible to manufacture IDs out of thin air. For example, it's possible to create IDs for items which are not considered in CrateDefMap due to cfg. Or it is possible to mixup structs and unions, because they share ID space. * Getting the ID of a parent requires a secondary index. Instead, the plan is to pursue the more traditional approach, where each items stores the id of the parent declaration. This makes `FromSource` more awkward, but also more correct: now, to get from an AST to HIR, we first do this recursively for the parent item, and the just search the children of the parent for the matching def --- crates/ra_hir_def/src/lib.rs | 66 ++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 61 insertions(+), 5 deletions(-) (limited to 'crates/ra_hir_def/src/lib.rs') diff --git a/crates/ra_hir_def/src/lib.rs b/crates/ra_hir_def/src/lib.rs index 38c110570..b9a13776f 100644 --- a/crates/ra_hir_def/src/lib.rs +++ b/crates/ra_hir_def/src/lib.rs @@ -199,15 +199,33 @@ pub trait AstItemDef: salsa::InternKey + Clone { pub struct FunctionId(salsa::InternId); impl_intern_key!(FunctionId); -impl AstItemDef for FunctionId { - fn intern(db: &impl InternDatabase, loc: ItemLoc) -> Self { - db.intern_function(loc) +#[derive(Debug, Clone, PartialEq, Eq, Hash)] +pub struct FunctionLoc { + pub container: FunctionContainerId, + pub ast_id: AstId, +} + +impl Intern for FunctionLoc { + type ID = FunctionId; + fn intern(self, db: &impl db::DefDatabase2) -> FunctionId { + db.intern_function(self) } - fn lookup_intern(self, db: &impl InternDatabase) -> ItemLoc { - db.lookup_intern_function(self) +} + +impl Lookup for FunctionId { + type Data = FunctionLoc; + fn lookup(&self, db: &impl db::DefDatabase2) -> FunctionLoc { + db.lookup_intern_function(*self) } } +#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] +pub enum FunctionContainerId { + ModuleId(ModuleId), + ImplId(ImplId), + TraitId(TraitId), +} + #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] pub struct StructOrUnionId(salsa::InternId); impl_intern_key!(StructOrUnionId); @@ -433,3 +451,41 @@ impl_froms!( EnumVariantId, ConstId ); + +trait Intern { + type ID; + fn intern(self, db: &impl db::DefDatabase2) -> Self::ID; +} + +pub trait Lookup { + type Data; + fn lookup(&self, db: &impl db::DefDatabase2) -> Self::Data; +} + +pub trait HasModule { + fn module(&self, db: &impl db::DefDatabase2) -> ModuleId; +} + +impl HasModule for FunctionLoc { + fn module(&self, db: &impl db::DefDatabase2) -> ModuleId { + match self.container { + FunctionContainerId::ModuleId(it) => it, + FunctionContainerId::ImplId(it) => it.module(db), + FunctionContainerId::TraitId(it) => it.module(db), + } + } +} + +pub trait HasSource { + type Value; + fn source(&self, db: &impl db::DefDatabase2) -> Source; +} + +impl HasSource for FunctionLoc { + type Value = ast::FnDef; + + fn source(&self, db: &impl db::DefDatabase2) -> Source { + let node = self.ast_id.to_node(db); + Source::new(self.ast_id.file_id(), node) + } +} -- cgit v1.2.3 From 64c21ed19594b323e72605ba8c5dd4c6eee433f6 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Wed, 20 Nov 2019 17:39:58 +0300 Subject: Switch type aliases to new sources --- crates/ra_hir_def/src/lib.rs | 48 +++++++++++++++++++++++++++++++++++++++----- 1 file changed, 43 insertions(+), 5 deletions(-) (limited to 'crates/ra_hir_def/src/lib.rs') diff --git a/crates/ra_hir_def/src/lib.rs b/crates/ra_hir_def/src/lib.rs index b9a13776f..6052370b4 100644 --- a/crates/ra_hir_def/src/lib.rs +++ b/crates/ra_hir_def/src/lib.rs @@ -332,15 +332,34 @@ impl AstItemDef for TraitId { #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] pub struct TypeAliasId(salsa::InternId); impl_intern_key!(TypeAliasId); -impl AstItemDef for TypeAliasId { - fn intern(db: &impl InternDatabase, loc: ItemLoc) -> Self { - db.intern_type_alias(loc) + +#[derive(Debug, Clone, PartialEq, Eq, Hash)] +pub struct TypeAliasLoc { + pub container: TypeAliasContainerId, + pub ast_id: AstId, +} + +impl Intern for TypeAliasLoc { + type ID = TypeAliasId; + fn intern(self, db: &impl db::DefDatabase2) -> TypeAliasId { + db.intern_type_alias(self) } - fn lookup_intern(self, db: &impl InternDatabase) -> ItemLoc { - db.lookup_intern_type_alias(self) +} + +impl Lookup for TypeAliasId { + type Data = TypeAliasLoc; + fn lookup(&self, db: &impl db::DefDatabase2) -> TypeAliasLoc { + db.lookup_intern_type_alias(*self) } } +#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] +pub enum TypeAliasContainerId { + ModuleId(ModuleId), + ImplId(ImplId), + TraitId(TraitId), +} + #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] pub struct ImplId(salsa::InternId); impl_intern_key!(ImplId); @@ -476,6 +495,16 @@ impl HasModule for FunctionLoc { } } +impl HasModule for TypeAliasLoc { + fn module(&self, db: &impl db::DefDatabase2) -> ModuleId { + match self.container { + TypeAliasContainerId::ModuleId(it) => it, + TypeAliasContainerId::ImplId(it) => it.module(db), + TypeAliasContainerId::TraitId(it) => it.module(db), + } + } +} + pub trait HasSource { type Value; fn source(&self, db: &impl db::DefDatabase2) -> Source; @@ -489,3 +518,12 @@ impl HasSource for FunctionLoc { Source::new(self.ast_id.file_id(), node) } } + +impl HasSource for TypeAliasLoc { + type Value = ast::TypeAliasDef; + + fn source(&self, db: &impl db::DefDatabase2) -> Source { + let node = self.ast_id.to_node(db); + Source::new(self.ast_id.file_id(), node) + } +} -- cgit v1.2.3 From ee95a35664e6fe9153f6324cfc57872ca365887c Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Wed, 20 Nov 2019 17:49:57 +0300 Subject: Don't duplicate ContainerId type --- crates/ra_hir_def/src/lib.rs | 37 +++++++++++++++---------------------- 1 file changed, 15 insertions(+), 22 deletions(-) (limited to 'crates/ra_hir_def/src/lib.rs') diff --git a/crates/ra_hir_def/src/lib.rs b/crates/ra_hir_def/src/lib.rs index 6052370b4..da6506fcd 100644 --- a/crates/ra_hir_def/src/lib.rs +++ b/crates/ra_hir_def/src/lib.rs @@ -201,7 +201,7 @@ impl_intern_key!(FunctionId); #[derive(Debug, Clone, PartialEq, Eq, Hash)] pub struct FunctionLoc { - pub container: FunctionContainerId, + pub container: ContainerId, pub ast_id: AstId, } @@ -219,13 +219,6 @@ impl Lookup for FunctionId { } } -#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] -pub enum FunctionContainerId { - ModuleId(ModuleId), - ImplId(ImplId), - TraitId(TraitId), -} - #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] pub struct StructOrUnionId(salsa::InternId); impl_intern_key!(StructOrUnionId); @@ -335,7 +328,7 @@ impl_intern_key!(TypeAliasId); #[derive(Debug, Clone, PartialEq, Eq, Hash)] pub struct TypeAliasLoc { - pub container: TypeAliasContainerId, + pub container: ContainerId, pub ast_id: AstId, } @@ -353,13 +346,6 @@ impl Lookup for TypeAliasId { } } -#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] -pub enum TypeAliasContainerId { - ModuleId(ModuleId), - ImplId(ImplId), - TraitId(TraitId), -} - #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] pub struct ImplId(salsa::InternId); impl_intern_key!(ImplId); @@ -391,6 +377,13 @@ macro_rules! impl_froms { } } +#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] +pub enum ContainerId { + ModuleId(ModuleId), + ImplId(ImplId), + TraitId(TraitId), +} + /// A Data Type #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] pub enum AdtId { @@ -488,9 +481,9 @@ pub trait HasModule { impl HasModule for FunctionLoc { fn module(&self, db: &impl db::DefDatabase2) -> ModuleId { match self.container { - FunctionContainerId::ModuleId(it) => it, - FunctionContainerId::ImplId(it) => it.module(db), - FunctionContainerId::TraitId(it) => it.module(db), + ContainerId::ModuleId(it) => it, + ContainerId::ImplId(it) => it.module(db), + ContainerId::TraitId(it) => it.module(db), } } } @@ -498,9 +491,9 @@ impl HasModule for FunctionLoc { impl HasModule for TypeAliasLoc { fn module(&self, db: &impl db::DefDatabase2) -> ModuleId { match self.container { - TypeAliasContainerId::ModuleId(it) => it, - TypeAliasContainerId::ImplId(it) => it.module(db), - TypeAliasContainerId::TraitId(it) => it.module(db), + ContainerId::ModuleId(it) => it, + ContainerId::ImplId(it) => it.module(db), + ContainerId::TraitId(it) => it.module(db), } } } -- cgit v1.2.3 From 111891dc2dc1d2c7ea87144e8e3ddefe23fc7b6d Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Wed, 20 Nov 2019 18:00:01 +0300 Subject: Move constants to new ID This allows us to get rid of trait item index --- crates/ra_hir_def/src/lib.rs | 40 +++++++++++++++++++++++++++++++++++----- 1 file changed, 35 insertions(+), 5 deletions(-) (limited to 'crates/ra_hir_def/src/lib.rs') diff --git a/crates/ra_hir_def/src/lib.rs b/crates/ra_hir_def/src/lib.rs index da6506fcd..0af41de87 100644 --- a/crates/ra_hir_def/src/lib.rs +++ b/crates/ra_hir_def/src/lib.rs @@ -289,12 +289,23 @@ impl_arena_id!(LocalStructFieldId); #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] pub struct ConstId(salsa::InternId); impl_intern_key!(ConstId); -impl AstItemDef for ConstId { - fn intern(db: &impl InternDatabase, loc: ItemLoc) -> Self { - db.intern_const(loc) +#[derive(Debug, Clone, PartialEq, Eq, Hash)] +pub struct ConstLoc { + pub container: ContainerId, + pub ast_id: AstId, +} + +impl Intern for ConstLoc { + type ID = ConstId; + fn intern(self, db: &impl db::DefDatabase2) -> ConstId { + db.intern_const(self) } - fn lookup_intern(self, db: &impl InternDatabase) -> ItemLoc { - db.lookup_intern_const(self) +} + +impl Lookup for ConstId { + type Data = ConstLoc; + fn lookup(&self, db: &impl db::DefDatabase2) -> ConstLoc { + db.lookup_intern_const(*self) } } @@ -498,6 +509,16 @@ impl HasModule for TypeAliasLoc { } } +impl HasModule for ConstLoc { + fn module(&self, db: &impl db::DefDatabase2) -> ModuleId { + match self.container { + ContainerId::ModuleId(it) => it, + ContainerId::ImplId(it) => it.module(db), + ContainerId::TraitId(it) => it.module(db), + } + } +} + pub trait HasSource { type Value; fn source(&self, db: &impl db::DefDatabase2) -> Source; @@ -520,3 +541,12 @@ impl HasSource for TypeAliasLoc { Source::new(self.ast_id.file_id(), node) } } + +impl HasSource for ConstLoc { + type Value = ast::ConstDef; + + fn source(&self, db: &impl db::DefDatabase2) -> Source { + let node = self.ast_id.to_node(db); + Source::new(self.ast_id.file_id(), node) + } +} -- cgit v1.2.3