about summary refs log tree commit diff
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2023-07-30 10:55:14 +0000
committerbors <bors@rust-lang.org>2023-07-30 10:55:14 +0000
commitebcd25d46c1ecb9f2e70581e305f79a55b05b323 (patch)
treeec4c562782b629b7ce562d952de2381068d776e1
parent2266ecf9dda51f242dd1738354dc9d2c65f2a125 (diff)
parentdf725d6b6d841730fd07d68b62b6d8c2eb68a78f (diff)
downloadrust-ebcd25d46c1ecb9f2e70581e305f79a55b05b323.tar.gz
rust-ebcd25d46c1ecb9f2e70581e305f79a55b05b323.zip
Auto merge of #15357 - Veykril:mismatched-macro-def-call, r=Veykril
fix: Do not create fn macro calls with non-fn expanders

Fixes https://github.com/rust-lang/rust-analyzer/issues/15327
-rw-r--r--crates/hir-def/src/lib.rs17
-rw-r--r--crates/hir-expand/src/lib.rs18
2 files changed, 29 insertions, 6 deletions
diff --git a/crates/hir-def/src/lib.rs b/crates/hir-def/src/lib.rs
index 1e74e2dfcb4..9270cbfe890 100644
--- a/crates/hir-def/src/lib.rs
+++ b/crates/hir-def/src/lib.rs
@@ -1155,18 +1155,22 @@ fn macro_call_as_call_id_(
     let def =
         resolver(call.path.clone()).ok_or_else(|| UnresolvedMacro { path: call.path.clone() })?;
 
-    let res = if let MacroDefKind::BuiltInEager(..) = def.kind {
-        let macro_call = InFile::new(call.ast_id.file_id, call.ast_id.to_node(db));
-        expand_eager_macro_input(db, krate, macro_call, def, &resolver)?
-    } else {
-        ExpandResult {
+    let res = match def.kind {
+        MacroDefKind::BuiltInEager(..) => {
+            let macro_call = InFile::new(call.ast_id.file_id, call.ast_id.to_node(db));
+            expand_eager_macro_input(db, krate, macro_call, def, &|path| {
+                resolver(path).filter(MacroDefId::is_fn_like)
+            })?
+        }
+        _ if def.is_fn_like() => ExpandResult {
             value: Some(def.as_lazy_macro(
                 db,
                 krate,
                 MacroCallKind::FnLike { ast_id: call.ast_id, expand_to },
             )),
             err: None,
-        }
+        },
+        _ => return Err(UnresolvedMacro { path: call.path.clone() }),
     };
     Ok(res)
 }
@@ -1251,6 +1255,7 @@ fn derive_macro_as_call_id(
     resolver: impl Fn(path::ModPath) -> Option<(MacroId, MacroDefId)>,
 ) -> Result<(MacroId, MacroDefId, MacroCallId), UnresolvedMacro> {
     let (macro_id, def_id) = resolver(item_attr.path.clone())
+        .filter(|(_, def_id)| def_id.is_derive())
         .ok_or_else(|| UnresolvedMacro { path: item_attr.path.clone() })?;
     let call_id = def_id.as_lazy_macro(
         db.upcast(),
diff --git a/crates/hir-expand/src/lib.rs b/crates/hir-expand/src/lib.rs
index 9ed6c31ddde..1f1e20f49e3 100644
--- a/crates/hir-expand/src/lib.rs
+++ b/crates/hir-expand/src/lib.rs
@@ -415,6 +415,24 @@ impl MacroDefId {
         )
     }
 
+    pub fn is_derive(&self) -> bool {
+        matches!(
+            self.kind,
+            MacroDefKind::BuiltInDerive(..)
+                | MacroDefKind::ProcMacro(_, ProcMacroKind::CustomDerive, _)
+        )
+    }
+
+    pub fn is_fn_like(&self) -> bool {
+        matches!(
+            self.kind,
+            MacroDefKind::BuiltIn(..)
+                | MacroDefKind::ProcMacro(_, ProcMacroKind::FuncLike, _)
+                | MacroDefKind::BuiltInEager(..)
+                | MacroDefKind::Declarative(..)
+        )
+    }
+
     pub fn is_attribute_derive(&self) -> bool {
         matches!(self.kind, MacroDefKind::BuiltInAttr(expander, ..) if expander.is_derive())
     }