about summary refs log tree commit diff
diff options
context:
space:
mode:
authorJonas Schievink <jonas.schievink@ferrous-systems.com>2022-04-08 18:05:34 +0200
committerJonas Schievink <jonas.schievink@ferrous-systems.com>2022-04-08 18:05:34 +0200
commitcdeb6140bf88b34771f13bccb81d604b2ef9ad62 (patch)
treea1547a10aef9376ae9b37c2134ce8d1c6b38c79c
parent847c552ab3d257a45fee6ef2c1737de52c081d11 (diff)
downloadrust-cdeb6140bf88b34771f13bccb81d604b2ef9ad62.tar.gz
rust-cdeb6140bf88b34771f13bccb81d604b2ef9ad62.zip
Account for macros in `get_missing_assoc_items`
-rw-r--r--crates/ide_db/src/traits.rs58
1 files changed, 34 insertions, 24 deletions
diff --git a/crates/ide_db/src/traits.rs b/crates/ide_db/src/traits.rs
index c8cb1a26a87..0fbfd869921 100644
--- a/crates/ide_db/src/traits.rs
+++ b/crates/ide_db/src/traits.rs
@@ -3,10 +3,7 @@
 use crate::RootDatabase;
 use hir::Semantics;
 use rustc_hash::FxHashSet;
-use syntax::{
-    ast::{self, HasName},
-    AstNode,
-};
+use syntax::{ast, AstNode};
 
 /// Given the `impl` block, attempts to find the trait this `impl` corresponds to.
 pub fn resolve_target_trait(
@@ -28,32 +25,28 @@ pub fn get_missing_assoc_items(
     sema: &Semantics<RootDatabase>,
     impl_def: &ast::Impl,
 ) -> Vec<hir::AssocItem> {
+    let imp = match sema.to_def(impl_def) {
+        Some(it) => it,
+        None => return vec![],
+    };
+
     // Names must be unique between constants and functions. However, type aliases
     // may share the same name as a function or constant.
     let mut impl_fns_consts = FxHashSet::default();
     let mut impl_type = FxHashSet::default();
 
-    if let Some(item_list) = impl_def.assoc_item_list() {
-        for item in item_list.assoc_items() {
-            match item {
-                ast::AssocItem::Fn(f) => {
-                    if let Some(n) = f.name() {
-                        impl_fns_consts.insert(n.syntax().to_string());
-                    }
-                }
-
-                ast::AssocItem::TypeAlias(t) => {
-                    if let Some(n) = t.name() {
-                        impl_type.insert(n.syntax().to_string());
-                    }
-                }
-
-                ast::AssocItem::Const(c) => {
-                    if let Some(n) = c.name() {
-                        impl_fns_consts.insert(n.syntax().to_string());
-                    }
+    for item in imp.items(sema.db) {
+        match item {
+            hir::AssocItem::Function(it) => {
+                impl_fns_consts.insert(it.name(sema.db).to_string());
+            }
+            hir::AssocItem::Const(it) => {
+                if let Some(name) = it.name(sema.db) {
+                    impl_fns_consts.insert(name.to_string());
                 }
-                ast::AssocItem::MacroCall(_) => (),
+            }
+            hir::AssocItem::TypeAlias(it) => {
+                impl_type.insert(it.name(sema.db).to_string());
             }
         }
     }
@@ -219,5 +212,22 @@ impl Foo {
 }"#,
             expect![[r#""#]],
         );
+
+        check_missing_assoc(
+            r#"
+trait Tr {
+    fn required();
+}
+macro_rules! m {
+    () => { fn required() {} };
+}
+impl Tr for () {
+    m!();
+    $0
+}
+
+            "#,
+            expect![[r#""#]],
+        );
     }
 }