aboutsummaryrefslogtreecommitdiff
path: root/crates/hir/src/semantics.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/hir/src/semantics.rs')
-rw-r--r--crates/hir/src/semantics.rs26
1 files changed, 25 insertions, 1 deletions
diff --git a/crates/hir/src/semantics.rs b/crates/hir/src/semantics.rs
index 945638cc5..2a0a36de4 100644
--- a/crates/hir/src/semantics.rs
+++ b/crates/hir/src/semantics.rs
@@ -2,10 +2,12 @@
2 2
3mod source_to_def; 3mod source_to_def;
4 4
5use std::{cell::RefCell, fmt, iter::successors}; 5use std::{cell::RefCell, collections::VecDeque, fmt, iter::successors};
6 6
7use base_db::{FileId, FileRange}; 7use base_db::{FileId, FileRange};
8use either::Either;
8use hir_def::{ 9use hir_def::{
10 nameres::ModuleSource,
9 resolver::{self, HasResolver, Resolver, TypeNs}, 11 resolver::{self, HasResolver, Resolver, TypeNs},
10 AsMacroCall, FunctionId, TraitId, VariantId, 12 AsMacroCall, FunctionId, TraitId, VariantId,
11}; 13};
@@ -155,6 +157,28 @@ impl<'db, DB: HirDatabase> Semantics<'db, DB> {
155 self.imp.ancestors_at_offset_with_macros(node, offset) 157 self.imp.ancestors_at_offset_with_macros(node, offset)
156 } 158 }
157 159
160 /// Iterates all `ModuleDef`s and `Impl` blocks of the given file.
161 pub fn visit_file_defs(&self, file_id: FileId, cb: &mut dyn FnMut(Either<ModuleDef, Impl>)) {
162 let module = match self.to_module_def(file_id) {
163 Some(it) => it,
164 None => return,
165 };
166 let mut defs: VecDeque<_> = module.declarations(self.db).into();
167 while let Some(def) = defs.pop_front() {
168 if let ModuleDef::Module(submodule) = def {
169 if let ModuleSource::Module(_) = submodule.definition_source(self.db).value {
170 defs.extend(submodule.declarations(self.db));
171 submodule
172 .impl_defs(self.db)
173 .into_iter()
174 .for_each(|impl_| cb(Either::Right(impl_)));
175 }
176 }
177 cb(Either::Left(def));
178 }
179 module.impl_defs(self.db).into_iter().for_each(|impl_| cb(Either::Right(impl_)));
180 }
181
158 /// Find a AstNode by offset inside SyntaxNode, if it is inside *Macrofile*, 182 /// Find a AstNode by offset inside SyntaxNode, if it is inside *Macrofile*,
159 /// search up until it is of the target AstNode type 183 /// search up until it is of the target AstNode type
160 pub fn find_node_at_offset_with_macros<N: AstNode>( 184 pub fn find_node_at_offset_with_macros<N: AstNode>(