aboutsummaryrefslogtreecommitdiff
path: root/crates/hir_def
diff options
context:
space:
mode:
Diffstat (limited to 'crates/hir_def')
-rw-r--r--crates/hir_def/src/body.rs7
-rw-r--r--crates/hir_def/src/body/lower.rs143
-rw-r--r--crates/hir_def/src/item_scope.rs31
3 files changed, 6 insertions, 175 deletions
diff --git a/crates/hir_def/src/body.rs b/crates/hir_def/src/body.rs
index 9dbe717e5..19c4eb521 100644
--- a/crates/hir_def/src/body.rs
+++ b/crates/hir_def/src/body.rs
@@ -28,7 +28,6 @@ use crate::{
28 db::DefDatabase, 28 db::DefDatabase,
29 expr::{Expr, ExprId, Label, LabelId, Pat, PatId}, 29 expr::{Expr, ExprId, Label, LabelId, Pat, PatId},
30 item_scope::BuiltinShadowMode, 30 item_scope::BuiltinShadowMode,
31 item_scope::ItemScope,
32 nameres::DefMap, 31 nameres::DefMap,
33 path::{ModPath, Path}, 32 path::{ModPath, Path},
34 src::HasSource, 33 src::HasSource,
@@ -228,7 +227,6 @@ pub struct Body {
228 pub body_expr: ExprId, 227 pub body_expr: ExprId,
229 /// Block expressions in this body that may contain inner items. 228 /// Block expressions in this body that may contain inner items.
230 pub block_scopes: Vec<BlockId>, 229 pub block_scopes: Vec<BlockId>,
231 pub item_scope: ItemScope,
232 _c: Count<Self>, 230 _c: Count<Self>,
233} 231}
234 232
@@ -297,7 +295,7 @@ impl Body {
297 } 295 }
298 }; 296 };
299 let expander = Expander::new(db, file_id, module); 297 let expander = Expander::new(db, file_id, module);
300 let (body, source_map) = Body::new(db, def, expander, params, body); 298 let (body, source_map) = Body::new(db, expander, params, body);
301 (Arc::new(body), Arc::new(source_map)) 299 (Arc::new(body), Arc::new(source_map))
302 } 300 }
303 301
@@ -307,12 +305,11 @@ impl Body {
307 305
308 fn new( 306 fn new(
309 db: &dyn DefDatabase, 307 db: &dyn DefDatabase,
310 def: DefWithBodyId,
311 expander: Expander, 308 expander: Expander,
312 params: Option<ast::ParamList>, 309 params: Option<ast::ParamList>,
313 body: Option<ast::Expr>, 310 body: Option<ast::Expr>,
314 ) -> (Body, BodySourceMap) { 311 ) -> (Body, BodySourceMap) {
315 lower::lower(db, def, expander, params, body) 312 lower::lower(db, expander, params, body)
316 } 313 }
317} 314}
318 315
diff --git a/crates/hir_def/src/body/lower.rs b/crates/hir_def/src/body/lower.rs
index c3aa1dc37..4d79ab72c 100644
--- a/crates/hir_def/src/body/lower.rs
+++ b/crates/hir_def/src/body/lower.rs
@@ -1,13 +1,13 @@
1//! Transforms `ast::Expr` into an equivalent `hir_def::expr::Expr` 1//! Transforms `ast::Expr` into an equivalent `hir_def::expr::Expr`
2//! representation. 2//! representation.
3 3
4use std::{any::type_name, mem, sync::Arc}; 4use std::{mem, sync::Arc};
5 5
6use either::Either; 6use either::Either;
7use hir_expand::{ 7use hir_expand::{
8 hygiene::Hygiene, 8 hygiene::Hygiene,
9 name::{name, AsName, Name}, 9 name::{name, AsName, Name},
10 ExpandError, HirFileId, MacroDefId, MacroDefKind, 10 ExpandError, HirFileId,
11}; 11};
12use la_arena::Arena; 12use la_arena::Arena;
13use profile::Count; 13use profile::Count;
@@ -32,11 +32,10 @@ use crate::{
32 Statement, 32 Statement,
33 }, 33 },
34 item_scope::BuiltinShadowMode, 34 item_scope::BuiltinShadowMode,
35 item_tree::{ItemTree, ItemTreeId, ItemTreeNode}, 35 item_tree::ItemTree,
36 path::{GenericArgs, Path}, 36 path::{GenericArgs, Path},
37 type_ref::{Mutability, Rawness, TypeRef}, 37 type_ref::{Mutability, Rawness, TypeRef},
38 AdtId, BlockLoc, ConstLoc, ContainerId, DefWithBodyId, EnumLoc, FunctionLoc, Intern, 38 AdtId, BlockLoc, ModuleDefId,
39 ModuleDefId, StaticLoc, StructLoc, TraitLoc, TypeAliasLoc, UnionLoc,
40}; 39};
41 40
42use super::{diagnostics::BodyDiagnostic, ExprSource, PatSource}; 41use super::{diagnostics::BodyDiagnostic, ExprSource, PatSource};
@@ -60,7 +59,6 @@ impl LowerCtx {
60 59
61pub(super) fn lower( 60pub(super) fn lower(
62 db: &dyn DefDatabase, 61 db: &dyn DefDatabase,
63 def: DefWithBodyId,
64 expander: Expander, 62 expander: Expander,
65 params: Option<ast::ParamList>, 63 params: Option<ast::ParamList>,
66 body: Option<ast::Expr>, 64 body: Option<ast::Expr>,
@@ -68,7 +66,6 @@ pub(super) fn lower(
68 let item_tree = db.item_tree(expander.current_file_id); 66 let item_tree = db.item_tree(expander.current_file_id);
69 ExprCollector { 67 ExprCollector {
70 db, 68 db,
71 def,
72 source_map: BodySourceMap::default(), 69 source_map: BodySourceMap::default(),
73 body: Body { 70 body: Body {
74 exprs: Arena::default(), 71 exprs: Arena::default(),
@@ -77,7 +74,6 @@ pub(super) fn lower(
77 params: Vec::new(), 74 params: Vec::new(),
78 body_expr: dummy_expr_id(), 75 body_expr: dummy_expr_id(),
79 block_scopes: Vec::new(), 76 block_scopes: Vec::new(),
80 item_scope: Default::default(),
81 _c: Count::new(), 77 _c: Count::new(),
82 }, 78 },
83 item_trees: { 79 item_trees: {
@@ -92,7 +88,6 @@ pub(super) fn lower(
92 88
93struct ExprCollector<'a> { 89struct ExprCollector<'a> {
94 db: &'a dyn DefDatabase, 90 db: &'a dyn DefDatabase,
95 def: DefWithBodyId,
96 expander: Expander, 91 expander: Expander,
97 body: Body, 92 body: Body,
98 source_map: BodySourceMap, 93 source_map: BodySourceMap,
@@ -606,32 +601,6 @@ impl ExprCollector<'_> {
606 } 601 }
607 } 602 }
608 603
609 fn find_inner_item<N: ItemTreeNode>(&self, ast: &N::Source) -> Option<ItemTreeId<N>> {
610 let id = self.expander.ast_id(ast);
611 let tree = &self.item_trees[&id.file_id];
612
613 // FIXME: This probably breaks with `use` items, since they produce multiple item tree nodes
614
615 // Root file (non-macro).
616 let item_tree_id = tree
617 .all_inner_items()
618 .chain(tree.top_level_items().iter().copied())
619 .filter_map(|mod_item| mod_item.downcast::<N>())
620 .find(|tree_id| tree[*tree_id].ast_id().upcast() == id.value.upcast())
621 .or_else(|| {
622 log::debug!(
623 "couldn't find inner {} item for {:?} (AST: `{}` - {:?})",
624 type_name::<N>(),
625 id,
626 ast.syntax(),
627 ast.syntax(),
628 );
629 None
630 })?;
631
632 Some(ItemTreeId::new(id.file_id, item_tree_id))
633 }
634
635 fn collect_expr_opt(&mut self, expr: Option<ast::Expr>) -> ExprId { 604 fn collect_expr_opt(&mut self, expr: Option<ast::Expr>) -> ExprId {
636 if let Some(expr) = expr { 605 if let Some(expr) = expr {
637 self.collect_expr(expr) 606 self.collect_expr(expr)
@@ -663,7 +632,6 @@ impl ExprCollector<'_> {
663 match expansion { 632 match expansion {
664 Some(expansion) => { 633 Some(expansion) => {
665 let statements: ast::MacroStmts = expansion; 634 let statements: ast::MacroStmts = expansion;
666 this.collect_stmts_items(statements.statements());
667 635
668 statements.statements().for_each(|stmt| { 636 statements.statements().for_each(|stmt| {
669 if let Some(mut r) = this.collect_stmt(stmt) { 637 if let Some(mut r) = this.collect_stmt(stmt) {
@@ -710,7 +678,6 @@ impl ExprCollector<'_> {
710 let prev_def_map = mem::replace(&mut self.expander.def_map, def_map); 678 let prev_def_map = mem::replace(&mut self.expander.def_map, def_map);
711 let prev_local_module = mem::replace(&mut self.expander.module, module); 679 let prev_local_module = mem::replace(&mut self.expander.module, module);
712 680
713 self.collect_stmts_items(block.statements());
714 let statements = 681 let statements =
715 block.statements().filter_map(|s| self.collect_stmt(s)).flatten().collect(); 682 block.statements().filter_map(|s| self.collect_stmt(s)).flatten().collect();
716 let tail = block.tail_expr().map(|e| self.collect_expr(e)); 683 let tail = block.tail_expr().map(|e| self.collect_expr(e));
@@ -725,108 +692,6 @@ impl ExprCollector<'_> {
725 expr_id 692 expr_id
726 } 693 }
727 694
728 fn collect_stmts_items(&mut self, stmts: ast::AstChildren<ast::Stmt>) {
729 let container = ContainerId::DefWithBodyId(self.def);
730
731 let items = stmts
732 .filter_map(|stmt| match stmt {
733 ast::Stmt::Item(it) => Some(it),
734 ast::Stmt::LetStmt(_) | ast::Stmt::ExprStmt(_) => None,
735 })
736 .filter_map(|item| {
737 let (def, name): (ModuleDefId, Option<ast::Name>) = match item {
738 ast::Item::Fn(def) => {
739 let id = self.find_inner_item(&def)?;
740 (
741 FunctionLoc { container: container.into(), id }.intern(self.db).into(),
742 def.name(),
743 )
744 }
745 ast::Item::TypeAlias(def) => {
746 let id = self.find_inner_item(&def)?;
747 (
748 TypeAliasLoc { container: container.into(), id }.intern(self.db).into(),
749 def.name(),
750 )
751 }
752 ast::Item::Const(def) => {
753 let id = self.find_inner_item(&def)?;
754 (
755 ConstLoc { container: container.into(), id }.intern(self.db).into(),
756 def.name(),
757 )
758 }
759 ast::Item::Static(def) => {
760 let id = self.find_inner_item(&def)?;
761 (StaticLoc { container, id }.intern(self.db).into(), def.name())
762 }
763 ast::Item::Struct(def) => {
764 let id = self.find_inner_item(&def)?;
765 (StructLoc { container, id }.intern(self.db).into(), def.name())
766 }
767 ast::Item::Enum(def) => {
768 let id = self.find_inner_item(&def)?;
769 (EnumLoc { container, id }.intern(self.db).into(), def.name())
770 }
771 ast::Item::Union(def) => {
772 let id = self.find_inner_item(&def)?;
773 (UnionLoc { container, id }.intern(self.db).into(), def.name())
774 }
775 ast::Item::Trait(def) => {
776 let id = self.find_inner_item(&def)?;
777 (TraitLoc { container, id }.intern(self.db).into(), def.name())
778 }
779 ast::Item::ExternBlock(_) => return None, // FIXME: collect from extern blocks
780 ast::Item::Impl(_)
781 | ast::Item::Use(_)
782 | ast::Item::ExternCrate(_)
783 | ast::Item::Module(_)
784 | ast::Item::MacroCall(_) => return None,
785 ast::Item::MacroRules(def) => {
786 return Some(Either::Right(ast::Macro::from(def)));
787 }
788 ast::Item::MacroDef(def) => {
789 return Some(Either::Right(ast::Macro::from(def)));
790 }
791 };
792
793 Some(Either::Left((def, name)))
794 })
795 .collect::<Vec<_>>();
796
797 for either in items {
798 match either {
799 Either::Left((def, name)) => {
800 self.body.item_scope.define_def(def);
801 if let Some(name) = name {
802 let vis = crate::visibility::Visibility::Public; // FIXME determine correctly
803 let has_constructor = match def {
804 ModuleDefId::AdtId(AdtId::StructId(s)) => {
805 self.db.struct_data(s).variant_data.kind() != StructKind::Record
806 }
807 _ => true,
808 };
809 self.body.item_scope.push_res(
810 name.as_name(),
811 crate::per_ns::PerNs::from_def(def, vis, has_constructor),
812 );
813 }
814 }
815 Either::Right(e) => {
816 let mac = MacroDefId {
817 krate: self.expander.def_map.krate(),
818 ast_id: Some(self.expander.ast_id(&e)),
819 kind: MacroDefKind::Declarative,
820 local_inner: false,
821 };
822 if let Some(name) = e.name() {
823 self.body.item_scope.define_legacy_macro(name.as_name(), mac);
824 }
825 }
826 }
827 }
828 }
829
830 fn collect_block_opt(&mut self, expr: Option<ast::BlockExpr>) -> ExprId { 695 fn collect_block_opt(&mut self, expr: Option<ast::BlockExpr>) -> ExprId {
831 if let Some(block) = expr { 696 if let Some(block) = expr {
832 self.collect_block(block) 697 self.collect_block(block)
diff --git a/crates/hir_def/src/item_scope.rs b/crates/hir_def/src/item_scope.rs
index 919933813..aafd73b60 100644
--- a/crates/hir_def/src/item_scope.rs
+++ b/crates/hir_def/src/item_scope.rs
@@ -168,37 +168,6 @@ impl ItemScope {
168 self.unnamed_trait_imports.insert(tr, vis); 168 self.unnamed_trait_imports.insert(tr, vis);
169 } 169 }
170 170
171 pub(crate) fn push_res(&mut self, name: Name, def: PerNs) -> bool {
172 let mut changed = false;
173
174 if let Some(types) = def.types {
175 self.types.entry(name.clone()).or_insert_with(|| {
176 changed = true;
177 types
178 });
179 }
180 if let Some(values) = def.values {
181 self.values.entry(name.clone()).or_insert_with(|| {
182 changed = true;
183 values
184 });
185 }
186 if let Some(macros) = def.macros {
187 self.macros.entry(name.clone()).or_insert_with(|| {
188 changed = true;
189 macros
190 });
191 }
192
193 if def.is_none() {
194 if self.unresolved.insert(name) {
195 changed = true;
196 }
197 }
198
199 changed
200 }
201
202 pub(crate) fn push_res_with_import( 171 pub(crate) fn push_res_with_import(
203 &mut self, 172 &mut self,
204 glob_imports: &mut PerNsGlobImports, 173 glob_imports: &mut PerNsGlobImports,