about summary refs log tree commit diff
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2022-11-19 09:33:10 +0000
committerbors <bors@rust-lang.org>2022-11-19 09:33:10 +0000
commitac60077ee5d9aa94b60587029322d35d9f218374 (patch)
treed172173afef325d8891e02677ef7528d7566200f
parent791cb87cdf47ddfd2a2b1a726dab3aa66ec2bff3 (diff)
parentdc8254c6abdfcd273cb49475e798048558dcf4db (diff)
downloadrust-ac60077ee5d9aa94b60587029322d35d9f218374.tar.gz
rust-ac60077ee5d9aa94b60587029322d35d9f218374.zip
Auto merge of #13639 - Veykril:macro-diags, r=Veykril
fix: Fix proc-macro-srv search paths for Arch Linux

Fixes https://github.com/rust-lang/rust-analyzer/issues/13616
-rw-r--r--crates/ide-diagnostics/src/handlers/macro_error.rs5
-rw-r--r--crates/ide-diagnostics/src/handlers/unresolved_macro_call.rs5
-rw-r--r--crates/ide-diagnostics/src/handlers/unresolved_proc_macro.rs12
-rw-r--r--crates/ide-diagnostics/src/lib.rs22
-rw-r--r--crates/project-model/src/workspace.rs15
-rw-r--r--crates/rust-analyzer/src/cli/load_cargo.rs22
-rw-r--r--crates/rust-analyzer/src/reload.rs36
7 files changed, 50 insertions, 67 deletions
diff --git a/crates/ide-diagnostics/src/handlers/macro_error.rs b/crates/ide-diagnostics/src/handlers/macro_error.rs
index 43ff4ed5a6c..870c78d1f1e 100644
--- a/crates/ide-diagnostics/src/handlers/macro_error.rs
+++ b/crates/ide-diagnostics/src/handlers/macro_error.rs
@@ -5,10 +5,7 @@ use crate::{Diagnostic, DiagnosticsContext};
 // This diagnostic is shown for macro expansion errors.
 pub(crate) fn macro_error(ctx: &DiagnosticsContext<'_>, d: &hir::MacroError) -> Diagnostic {
     // Use more accurate position if available.
-    let display_range = d
-        .precise_location
-        .unwrap_or_else(|| ctx.sema.diagnostics_display_range(d.node.clone()).range);
-
+    let display_range = ctx.resolve_precise_location(&d.node, d.precise_location);
     Diagnostic::new("macro-error", d.message.clone(), display_range).experimental()
 }
 
diff --git a/crates/ide-diagnostics/src/handlers/unresolved_macro_call.rs b/crates/ide-diagnostics/src/handlers/unresolved_macro_call.rs
index 4b43124757f..87531f4acfb 100644
--- a/crates/ide-diagnostics/src/handlers/unresolved_macro_call.rs
+++ b/crates/ide-diagnostics/src/handlers/unresolved_macro_call.rs
@@ -9,10 +9,7 @@ pub(crate) fn unresolved_macro_call(
     d: &hir::UnresolvedMacroCall,
 ) -> Diagnostic {
     // Use more accurate position if available.
-    let display_range = d
-        .precise_location
-        .unwrap_or_else(|| ctx.sema.diagnostics_display_range(d.macro_call.clone()).range);
-
+    let display_range = ctx.resolve_precise_location(&d.macro_call, d.precise_location);
     let bang = if d.is_bang { "!" } else { "" };
     Diagnostic::new(
         "unresolved-macro-call",
diff --git a/crates/ide-diagnostics/src/handlers/unresolved_proc_macro.rs b/crates/ide-diagnostics/src/handlers/unresolved_proc_macro.rs
index 760f51f9049..23818d883f7 100644
--- a/crates/ide-diagnostics/src/handlers/unresolved_proc_macro.rs
+++ b/crates/ide-diagnostics/src/handlers/unresolved_proc_macro.rs
@@ -1,5 +1,4 @@
 use hir::db::DefDatabase;
-use syntax::NodeOrToken;
 
 use crate::{Diagnostic, DiagnosticsContext, Severity};
 
@@ -19,16 +18,7 @@ pub(crate) fn unresolved_proc_macro(
     proc_attr_macros_enabled: bool,
 ) -> Diagnostic {
     // Use more accurate position if available.
-    let display_range = (|| {
-        let precise_location = d.precise_location?;
-        let root = ctx.sema.parse_or_expand(d.node.file_id)?;
-        match root.covering_element(precise_location) {
-            NodeOrToken::Node(it) => Some(ctx.sema.original_range(&it)),
-            NodeOrToken::Token(it) => d.node.with_value(it).original_file_range_opt(ctx.sema.db),
-        }
-    })()
-    .unwrap_or_else(|| ctx.sema.diagnostics_display_range(d.node.clone()))
-    .range;
+    let display_range = ctx.resolve_precise_location(&d.node, d.precise_location);
 
     let config_enabled = match d.kind {
         hir::MacroKind::Attr => proc_macros_enabled && proc_attr_macros_enabled,
diff --git a/crates/ide-diagnostics/src/lib.rs b/crates/ide-diagnostics/src/lib.rs
index ae299f05841..d81e36a1f86 100644
--- a/crates/ide-diagnostics/src/lib.rs
+++ b/crates/ide-diagnostics/src/lib.rs
@@ -182,6 +182,28 @@ struct DiagnosticsContext<'a> {
     resolve: &'a AssistResolveStrategy,
 }
 
+impl<'a> DiagnosticsContext<'a> {
+    fn resolve_precise_location(
+        &self,
+        node: &InFile<SyntaxNodePtr>,
+        precise_location: Option<TextRange>,
+    ) -> TextRange {
+        let sema = &self.sema;
+        (|| {
+            let precise_location = precise_location?;
+            let root = sema.parse_or_expand(node.file_id)?;
+            match root.covering_element(precise_location) {
+                syntax::NodeOrToken::Node(it) => Some(sema.original_range(&it)),
+                syntax::NodeOrToken::Token(it) => {
+                    node.with_value(it).original_file_range_opt(sema.db)
+                }
+            }
+        })()
+        .unwrap_or_else(|| sema.diagnostics_display_range(node.clone()))
+        .range
+    }
+}
+
 pub fn diagnostics(
     db: &RootDatabase,
     config: &DiagnosticsConfig,
diff --git a/crates/project-model/src/workspace.rs b/crates/project-model/src/workspace.rs
index 4a2f468de72..3d199ed24af 100644
--- a/crates/project-model/src/workspace.rs
+++ b/crates/project-model/src/workspace.rs
@@ -377,6 +377,21 @@ impl ProjectWorkspace {
         }
     }
 
+    pub fn find_sysroot_proc_macro_srv(&self) -> Option<AbsPathBuf> {
+        match self {
+            ProjectWorkspace::Cargo { sysroot: Some(sysroot), .. }
+            | ProjectWorkspace::Json { sysroot: Some(sysroot), .. } => {
+                let standalone_server_name =
+                    format!("rust-analyzer-proc-macro-srv{}", std::env::consts::EXE_SUFFIX);
+                ["libexec", "lib"]
+                    .into_iter()
+                    .map(|segment| sysroot.root().join(segment).join(&standalone_server_name))
+                    .find(|server_path| std::fs::metadata(&server_path).is_ok())
+            }
+            _ => None,
+        }
+    }
+
     /// Returns the roots for the current `ProjectWorkspace`
     /// The return type contains the path and whether or not
     /// the root is a member of the current workspace
diff --git a/crates/rust-analyzer/src/cli/load_cargo.rs b/crates/rust-analyzer/src/cli/load_cargo.rs
index 5dba545b871..762d7d3a18e 100644
--- a/crates/rust-analyzer/src/cli/load_cargo.rs
+++ b/crates/rust-analyzer/src/cli/load_cargo.rs
@@ -60,24 +60,12 @@ pub fn load_workspace(
     };
 
     let proc_macro_client = if load_config.with_proc_macro {
-        let mut path = AbsPathBuf::assert(std::env::current_exe()?);
-        let mut args = vec!["proc-macro"];
-
-        if let ProjectWorkspace::Cargo { sysroot, .. } | ProjectWorkspace::Json { sysroot, .. } =
-            &ws
-        {
-            if let Some(sysroot) = sysroot.as_ref() {
-                let standalone_server_name =
-                    format!("rust-analyzer-proc-macro-srv{}", std::env::consts::EXE_SUFFIX);
-                let server_path = sysroot.root().join("libexec").join(&standalone_server_name);
-                if std::fs::metadata(&server_path).is_ok() {
-                    path = server_path;
-                    args = vec![];
-                }
-            }
-        }
+        let (server_path, args): (_, &[_]) = match ws.find_sysroot_proc_macro_srv() {
+            Some(server_path) => (server_path, &[]),
+            None => (AbsPathBuf::assert(std::env::current_exe()?), &["proc-macro"]),
+        };
 
-        ProcMacroServer::spawn(path.clone(), args.clone()).map_err(|e| e.to_string())
+        ProcMacroServer::spawn(server_path, args).map_err(|e| e.to_string())
     } else {
         Err("proc macro server disabled".to_owned())
     };
diff --git a/crates/rust-analyzer/src/reload.rs b/crates/rust-analyzer/src/reload.rs
index aa0510a4ea6..fcfe4be0b8c 100644
--- a/crates/rust-analyzer/src/reload.rs
+++ b/crates/rust-analyzer/src/reload.rs
@@ -305,9 +305,6 @@ impl GlobalState {
         let files_config = self.config.files();
         let project_folders = ProjectFolders::new(&self.workspaces, &files_config.exclude);
 
-        let standalone_server_name =
-            format!("rust-analyzer-proc-macro-srv{}", std::env::consts::EXE_SUFFIX);
-
         if self.proc_macro_clients.is_empty() {
             if let Some((path, path_manually_set)) = self.config.proc_macro_srv() {
                 tracing::info!("Spawning proc-macro servers");
@@ -315,40 +312,17 @@ impl GlobalState {
                     .workspaces
                     .iter()
                     .map(|ws| {
-                        let (path, args) = if path_manually_set {
+                        let (path, args): (_, &[_]) = if path_manually_set {
                             tracing::debug!(
                                 "Pro-macro server path explicitly set: {}",
                                 path.display()
                             );
-                            (path.clone(), vec![])
+                            (path.clone(), &[])
                         } else {
-                            let mut sysroot_server = None;
-                            if let ProjectWorkspace::Cargo { sysroot, .. }
-                            | ProjectWorkspace::Json { sysroot, .. } = ws
-                            {
-                                if let Some(sysroot) = sysroot.as_ref() {
-                                    let server_path = sysroot
-                                        .root()
-                                        .join("libexec")
-                                        .join(&standalone_server_name);
-                                    if std::fs::metadata(&server_path).is_ok() {
-                                        tracing::debug!(
-                                            "Sysroot proc-macro server exists at {}",
-                                            server_path.display()
-                                        );
-                                        sysroot_server = Some(server_path);
-                                    } else {
-                                        tracing::debug!(
-                                            "Sysroot proc-macro server does not exist at {}",
-                                            server_path.display()
-                                        );
-                                    }
-                                }
+                            match ws.find_sysroot_proc_macro_srv() {
+                                Some(server_path) => (server_path, &[]),
+                                None => (path.clone(), &["proc-macro"]),
                             }
-                            sysroot_server.map_or_else(
-                                || (path.clone(), vec!["proc-macro".to_owned()]),
-                                |path| (path, vec![]),
-                            )
                         };
 
                         tracing::info!(?args, "Using proc-macro server at {}", path.display(),);