aboutsummaryrefslogtreecommitdiff
path: root/crates/ide/src/references.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ide/src/references.rs')
-rw-r--r--crates/ide/src/references.rs72
1 files changed, 38 insertions, 34 deletions
diff --git a/crates/ide/src/references.rs b/crates/ide/src/references.rs
index 51a2f4327..3a4f4d80b 100644
--- a/crates/ide/src/references.rs
+++ b/crates/ide/src/references.rs
@@ -25,7 +25,7 @@ use syntax::{
25 AstNode, SyntaxNode, TextRange, TokenAtOffset, T, 25 AstNode, SyntaxNode, TextRange, TokenAtOffset, T,
26}; 26};
27 27
28use crate::{display::TryToNav, FilePosition, FileRange, NavigationTarget, RangeInfo}; 28use crate::{display::TryToNav, FilePosition, NavigationTarget};
29 29
30#[derive(Debug, Clone)] 30#[derive(Debug, Clone)]
31pub struct ReferenceSearchResult { 31pub struct ReferenceSearchResult {
@@ -41,14 +41,6 @@ pub struct Declaration {
41} 41}
42 42
43impl ReferenceSearchResult { 43impl ReferenceSearchResult {
44 pub fn declaration(&self) -> &Declaration {
45 &self.declaration
46 }
47
48 pub fn decl_target(&self) -> &NavigationTarget {
49 &self.declaration.nav
50 }
51
52 pub fn references(&self) -> &UsageSearchResult { 44 pub fn references(&self) -> &UsageSearchResult {
53 &self.references 45 &self.references
54 } 46 }
@@ -87,7 +79,7 @@ pub(crate) fn find_all_refs(
87 sema: &Semantics<RootDatabase>, 79 sema: &Semantics<RootDatabase>,
88 position: FilePosition, 80 position: FilePosition,
89 search_scope: Option<SearchScope>, 81 search_scope: Option<SearchScope>,
90) -> Option<RangeInfo<ReferenceSearchResult>> { 82) -> Option<ReferenceSearchResult> {
91 let _p = profile::span("find_all_refs"); 83 let _p = profile::span("find_all_refs");
92 let syntax = sema.parse(position.file_id).syntax().clone(); 84 let syntax = sema.parse(position.file_id).syntax().clone();
93 85
@@ -105,7 +97,7 @@ pub(crate) fn find_all_refs(
105 ) 97 )
106 }; 98 };
107 99
108 let RangeInfo { range, info: def } = find_name(&sema, &syntax, position, opt_name)?; 100 let def = find_name(&sema, &syntax, position, opt_name)?;
109 101
110 let mut usages = def.usages(sema).set_scope(search_scope).all(); 102 let mut usages = def.usages(sema).set_scope(search_scope).all();
111 usages 103 usages
@@ -139,7 +131,7 @@ pub(crate) fn find_all_refs(
139 131
140 let declaration = Declaration { nav, kind, access: decl_access(&def, &syntax, decl_range) }; 132 let declaration = Declaration { nav, kind, access: decl_access(&def, &syntax, decl_range) };
141 133
142 Some(RangeInfo::new(range, ReferenceSearchResult { declaration, references: usages })) 134 Some(ReferenceSearchResult { declaration, references: usages })
143} 135}
144 136
145fn find_name( 137fn find_name(
@@ -147,35 +139,27 @@ fn find_name(
147 syntax: &SyntaxNode, 139 syntax: &SyntaxNode,
148 position: FilePosition, 140 position: FilePosition,
149 opt_name: Option<ast::Name>, 141 opt_name: Option<ast::Name>,
150) -> Option<RangeInfo<Definition>> { 142) -> Option<Definition> {
151 if let Some(name) = opt_name { 143 let def = if let Some(name) = opt_name {
152 let def = NameClass::classify(sema, &name)?.referenced_or_defined(sema.db); 144 NameClass::classify(sema, &name)?.referenced_or_defined(sema.db)
153 let FileRange { range, .. } = sema.original_range(name.syntax()); 145 } else if let Some(lifetime) =
154 return Some(RangeInfo::new(range, def));
155 }
156
157 let (FileRange { range, .. }, def) = if let Some(lifetime) =
158 sema.find_node_at_offset_with_descend::<ast::Lifetime>(&syntax, position.offset) 146 sema.find_node_at_offset_with_descend::<ast::Lifetime>(&syntax, position.offset)
159 { 147 {
160 if let Some(def) = NameRefClass::classify_lifetime(sema, &lifetime) 148 if let Some(def) =
161 .map(|class| NameRefClass::referenced(class, sema.db)) 149 NameRefClass::classify_lifetime(sema, &lifetime).map(|class| class.referenced(sema.db))
162 { 150 {
163 (sema.original_range(lifetime.syntax()), def) 151 def
164 } else { 152 } else {
165 ( 153 NameClass::classify_lifetime(sema, &lifetime)?.referenced_or_defined(sema.db)
166 sema.original_range(lifetime.syntax()),
167 NameClass::classify_lifetime(sema, &lifetime)?.referenced_or_defined(sema.db),
168 )
169 } 154 }
155 } else if let Some(name_ref) =
156 sema.find_node_at_offset_with_descend::<ast::NameRef>(&syntax, position.offset)
157 {
158 NameRefClass::classify(sema, &name_ref)?.referenced(sema.db)
170 } else { 159 } else {
171 let name_ref = 160 return None;
172 sema.find_node_at_offset_with_descend::<ast::NameRef>(&syntax, position.offset)?;
173 (
174 sema.original_range(name_ref.syntax()),
175 NameRefClass::classify(sema, &name_ref)?.referenced(sema.db),
176 )
177 }; 161 };
178 Some(RangeInfo::new(range, def)) 162 Some(def)
179} 163}
180 164
181fn decl_access(def: &Definition, syntax: &SyntaxNode, range: TextRange) -> Option<ReferenceAccess> { 165fn decl_access(def: &Definition, syntax: &SyntaxNode, range: TextRange) -> Option<ReferenceAccess> {
@@ -930,6 +914,26 @@ impl Foo {
930 ); 914 );
931 } 915 }
932 916
917 #[test]
918 fn test_find_self_refs_decl() {
919 check(
920 r#"
921struct Foo { bar: i32 }
922
923impl Foo {
924 fn foo(self$0) {
925 self;
926 }
927}
928"#,
929 expect![[r#"
930 self SelfParam FileId(0) 47..51 47..51 SelfParam
931
932 FileId(0) 63..67 Other Read
933 "#]],
934 );
935 }
936
933 fn check(ra_fixture: &str, expect: Expect) { 937 fn check(ra_fixture: &str, expect: Expect) {
934 check_with_scope(ra_fixture, None, expect) 938 check_with_scope(ra_fixture, None, expect)
935 } 939 }