Unnamed repository; edit this file 'description' to name the repository.
Merge pull request #21345 from Shourya742/2025-12-27-remove-channel-mess
Remove Channel workaround from proc-macro-srv
Chayim Refael Friedman 4 months ago
parent bbd40f8 · parent bac9cc2 · commit 96d0670
-rw-r--r--crates/proc-macro-api/src/transport/framing.rs2
-rw-r--r--crates/proc-macro-srv-cli/src/main_loop.rs190
-rw-r--r--crates/proc-macro-srv/src/dylib.rs6
-rw-r--r--crates/proc-macro-srv/src/dylib/proc_macros.rs2
-rw-r--r--crates/proc-macro-srv/src/lib.rs32
-rw-r--r--crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs18
-rw-r--r--crates/proc-macro-srv/src/server_impl/token_id.rs16
7 files changed, 114 insertions, 152 deletions
diff --git a/crates/proc-macro-api/src/transport/framing.rs b/crates/proc-macro-api/src/transport/framing.rs
index 2a11eb19c3..1e29c1982a 100644
--- a/crates/proc-macro-api/src/transport/framing.rs
+++ b/crates/proc-macro-api/src/transport/framing.rs
@@ -3,7 +3,7 @@
use std::io::{self, BufRead, Write};
pub trait Framing {
- type Buf: Default;
+ type Buf: Default + Send;
fn read<'a, R: BufRead + ?Sized>(
inp: &mut R,
diff --git a/crates/proc-macro-srv-cli/src/main_loop.rs b/crates/proc-macro-srv-cli/src/main_loop.rs
index 6ed42204df..4d98a8e29d 100644
--- a/crates/proc-macro-srv-cli/src/main_loop.rs
+++ b/crates/proc-macro-srv-cli/src/main_loop.rs
@@ -6,7 +6,7 @@ use proc_macro_api::{
transport::codec::{json::JsonProtocol, postcard::PostcardProtocol},
version::CURRENT_API_VERSION,
};
-use std::{io, sync::mpsc};
+use std::io;
use legacy::Message;
@@ -52,8 +52,8 @@ fn run_new<C: Codec>() -> io::Result<()> {
}
let mut buf = C::Buf::default();
- let mut stdin = io::stdin().lock();
- let mut stdout = io::stdout().lock();
+ let mut stdin = io::stdin();
+ let mut stdout = io::stdout();
let env_snapshot = EnvSnapshot::default();
let srv = proc_macro_srv::ProcMacroSrv::new(&env_snapshot);
@@ -61,7 +61,8 @@ fn run_new<C: Codec>() -> io::Result<()> {
let mut span_mode = legacy::SpanMode::Id;
'outer: loop {
- let req_opt = bidirectional::BidirectionalMessage::read::<_, C>(&mut stdin, &mut buf)?;
+ let req_opt =
+ bidirectional::BidirectionalMessage::read::<_, C>(&mut stdin.lock(), &mut buf)?;
let Some(req) = req_opt else {
break 'outer;
};
@@ -76,30 +77,23 @@ fn run_new<C: Codec>() -> io::Result<()> {
.collect()
});
- send_response::<_, C>(&mut stdout, bidirectional::Response::ListMacros(res))?;
+ send_response::<C>(&stdout, bidirectional::Response::ListMacros(res))?;
}
bidirectional::Request::ApiVersionCheck {} => {
// bidirectional::Response::ApiVersionCheck(CURRENT_API_VERSION).write::<_, C>(stdout)
- send_response::<_, C>(
- &mut stdout,
+ send_response::<C>(
+ &stdout,
bidirectional::Response::ApiVersionCheck(CURRENT_API_VERSION),
)?;
}
bidirectional::Request::SetConfig(config) => {
span_mode = config.span_mode;
- send_response::<_, C>(&mut stdout, bidirectional::Response::SetConfig(config))?;
+ send_response::<C>(&stdout, bidirectional::Response::SetConfig(config))?;
}
bidirectional::Request::ExpandMacro(task) => {
- handle_expand::<_, _, C>(
- &srv,
- &mut stdin,
- &mut stdout,
- &mut buf,
- span_mode,
- *task,
- )?;
+ handle_expand::<C>(&srv, &mut stdin, &mut stdout, &mut buf, span_mode, *task)?;
}
},
_ => continue,
@@ -109,25 +103,23 @@ fn run_new<C: Codec>() -> io::Result<()> {
Ok(())
}
-fn handle_expand<W: std::io::Write, R: std::io::BufRead, C: Codec>(
+fn handle_expand<C: Codec>(
srv: &proc_macro_srv::ProcMacroSrv<'_>,
- stdin: &mut R,
- stdout: &mut W,
+ stdin: &io::Stdin,
+ stdout: &io::Stdout,
buf: &mut C::Buf,
span_mode: legacy::SpanMode,
task: bidirectional::ExpandMacro,
) -> io::Result<()> {
match span_mode {
- legacy::SpanMode::Id => handle_expand_id::<_, C>(srv, stdout, task),
- legacy::SpanMode::RustAnalyzer => {
- handle_expand_ra::<_, _, C>(srv, stdin, stdout, buf, task)
- }
+ legacy::SpanMode::Id => handle_expand_id::<C>(srv, stdout, task),
+ legacy::SpanMode::RustAnalyzer => handle_expand_ra::<C>(srv, stdin, stdout, buf, task),
}
}
-fn handle_expand_id<W: std::io::Write, C: Codec>(
+fn handle_expand_id<C: Codec>(
srv: &proc_macro_srv::ProcMacroSrv<'_>,
- stdout: &mut W,
+ stdout: &io::Stdout,
task: bidirectional::ExpandMacro,
) -> io::Result<()> {
let bidirectional::ExpandMacro { lib, env, current_dir, data } = task;
@@ -166,28 +158,46 @@ fn handle_expand_id<W: std::io::Write, C: Codec>(
})
.map_err(|e| legacy::PanicMessage(e.into_string().unwrap_or_default()));
- send_response::<_, C>(stdout, bidirectional::Response::ExpandMacro(res))
+ send_response::<C>(&stdout, bidirectional::Response::ExpandMacro(res))
}
-struct ProcMacroClientHandle {
- subreq_tx: mpsc::Sender<bidirectional::SubRequest>,
- subresp_rx: mpsc::Receiver<bidirectional::SubResponse>,
+struct ProcMacroClientHandle<'a, C: Codec> {
+ stdin: &'a io::Stdin,
+ stdout: &'a io::Stdout,
+ buf: &'a mut C::Buf,
}
-impl proc_macro_srv::ProcMacroClientInterface for ProcMacroClientHandle {
- fn source_text(&self, file_id: u32, start: u32, end: u32) -> Option<String> {
- self.subreq_tx.send(bidirectional::SubRequest::SourceText { file_id, start, end }).ok()?;
+impl<C: Codec> proc_macro_srv::ProcMacroClientInterface for ProcMacroClientHandle<'_, C> {
+ fn source_text(&mut self, file_id: u32, start: u32, end: u32) -> Option<String> {
+ let req = bidirectional::BidirectionalMessage::SubRequest(
+ bidirectional::SubRequest::SourceText { file_id, start, end },
+ );
+
+ if req.write::<_, C>(&mut self.stdout.lock()).is_err() {
+ return None;
+ }
+
+ let msg = match bidirectional::BidirectionalMessage::read::<_, C>(
+ &mut self.stdin.lock(),
+ self.buf,
+ ) {
+ Ok(Some(msg)) => msg,
+ _ => return None,
+ };
- match self.subresp_rx.recv().ok()? {
- bidirectional::SubResponse::SourceTextResult { text } => text,
+ match msg {
+ bidirectional::BidirectionalMessage::SubResponse(
+ bidirectional::SubResponse::SourceTextResult { text },
+ ) => text,
+ _ => None,
}
}
}
-fn handle_expand_ra<W: io::Write, R: io::BufRead, C: Codec>(
+fn handle_expand_ra<C: Codec>(
srv: &proc_macro_srv::ProcMacroSrv<'_>,
- stdin: &mut R,
- stdout: &mut W,
+ stdin: &io::Stdin,
+ stdout: &io::Stdout,
buf: &mut C::Buf,
task: bidirectional::ExpandMacro,
) -> io::Result<()> {
@@ -222,81 +232,34 @@ fn handle_expand_ra<W: io::Write, R: io::BufRead, C: Codec>(
})
});
- let (subreq_tx, subreq_rx) = mpsc::channel();
- let (subresp_tx, subresp_rx) = mpsc::channel();
- let (result_tx, result_rx) = mpsc::channel();
-
- std::thread::scope(|s| {
- s.spawn(|| {
- let callback = ProcMacroClientHandle { subreq_tx, subresp_rx };
-
- let res = srv
- .expand(
- lib,
- &env,
- current_dir,
- &macro_name,
- macro_body,
- attributes,
- def_site,
+ let res = srv
+ .expand(
+ lib,
+ &env,
+ current_dir,
+ &macro_name,
+ macro_body,
+ attributes,
+ def_site,
+ call_site,
+ mixed_site,
+ Some(Box::new(ProcMacroClientHandle::<C> { stdin, stdout, buf })),
+ )
+ .map(|it| {
+ (
+ legacy::FlatTree::from_tokenstream(
+ it,
+ CURRENT_API_VERSION,
call_site,
- mixed_site,
- Some(Box::new(callback)),
- )
- .map(|it| {
- (
- legacy::FlatTree::from_tokenstream(
- it,
- CURRENT_API_VERSION,
- call_site,
- &mut span_data_table,
- ),
- legacy::serialize_span_data_index_map(&span_data_table),
- )
- })
- .map(|(tree, span_data_table)| bidirectional::ExpandMacroExtended {
- tree,
- span_data_table,
- })
- .map_err(|e| legacy::PanicMessage(e.into_string().unwrap_or_default()));
-
- let _ = result_tx.send(res);
- });
-
- loop {
- if let Ok(res) = result_rx.try_recv() {
- let _ = send_response::<_, C>(
- stdout,
- bidirectional::Response::ExpandMacroExtended(res),
- );
- break;
- }
-
- let sub_req = match subreq_rx.recv() {
- Ok(r) => r,
- Err(_) => break,
- };
-
- if bidirectional::BidirectionalMessage::SubRequest(sub_req)
- .write::<_, C>(stdout)
- .is_err()
- {
- break;
- }
- let resp = match bidirectional::BidirectionalMessage::read::<_, C>(stdin, buf) {
- Ok(Some(r)) => r,
- _ => break,
- };
- match resp {
- bidirectional::BidirectionalMessage::SubResponse(resp) => {
- let _ = subresp_tx.send(resp);
- }
- other => panic!("expected SubResponse, got {other:?}"),
- }
- }
- });
+ &mut span_data_table,
+ ),
+ legacy::serialize_span_data_index_map(&span_data_table),
+ )
+ })
+ .map(|(tree, span_data_table)| bidirectional::ExpandMacroExtended { tree, span_data_table })
+ .map_err(|e| legacy::PanicMessage(e.into_string().unwrap_or_default()));
- Ok(())
+ send_response::<C>(&stdout, bidirectional::Response::ExpandMacroExtended(res))
}
fn run_<C: Codec>() -> io::Result<()> {
@@ -441,10 +404,7 @@ fn run_<C: Codec>() -> io::Result<()> {
Ok(())
}
-fn send_response<W: std::io::Write, C: Codec>(
- stdout: &mut W,
- resp: bidirectional::Response,
-) -> io::Result<()> {
+fn send_response<C: Codec>(stdout: &io::Stdout, resp: bidirectional::Response) -> io::Result<()> {
let resp = bidirectional::BidirectionalMessage::Response(resp);
- resp.write::<W, C>(stdout)
+ resp.write::<_, C>(&mut stdout.lock())
}
diff --git a/crates/proc-macro-srv/src/dylib.rs b/crates/proc-macro-srv/src/dylib.rs
index d34f37b16a..02bdcc50d3 100644
--- a/crates/proc-macro-srv/src/dylib.rs
+++ b/crates/proc-macro-srv/src/dylib.rs
@@ -37,7 +37,7 @@ impl Expander {
Ok(Expander { inner: library, modified_time })
}
- pub(crate) fn expand<S: ProcMacroSrvSpan>(
+ pub(crate) fn expand<'a, S: ProcMacroSrvSpan + 'a>(
&self,
macro_name: &str,
macro_body: TokenStream<S>,
@@ -45,10 +45,10 @@ impl Expander {
def_site: S,
call_site: S,
mixed_site: S,
- callback: Option<ProcMacroClientHandle>,
+ callback: Option<ProcMacroClientHandle<'_>>,
) -> Result<TokenStream<S>, PanicMessage>
where
- <S::Server as bridge::server::Types>::TokenStream: Default,
+ <S::Server<'a> as bridge::server::Types>::TokenStream: Default,
{
self.inner
.proc_macros
diff --git a/crates/proc-macro-srv/src/dylib/proc_macros.rs b/crates/proc-macro-srv/src/dylib/proc_macros.rs
index ddbb0128f5..c763301135 100644
--- a/crates/proc-macro-srv/src/dylib/proc_macros.rs
+++ b/crates/proc-macro-srv/src/dylib/proc_macros.rs
@@ -20,7 +20,7 @@ impl ProcMacros {
def_site: S,
call_site: S,
mixed_site: S,
- callback: Option<ProcMacroClientHandle>,
+ callback: Option<ProcMacroClientHandle<'_>>,
) -> Result<TokenStream<S>, crate::PanicMessage> {
let parsed_attributes = attribute.unwrap_or_default();
diff --git a/crates/proc-macro-srv/src/lib.rs b/crates/proc-macro-srv/src/lib.rs
index ff5623f39e..687a4218b4 100644
--- a/crates/proc-macro-srv/src/lib.rs
+++ b/crates/proc-macro-srv/src/lib.rs
@@ -91,10 +91,10 @@ impl<'env> ProcMacroSrv<'env> {
}
}
-pub type ProcMacroClientHandle = Box<dyn ProcMacroClientInterface + Send>;
+pub type ProcMacroClientHandle<'a> = Box<dyn ProcMacroClientInterface + Send + 'a>;
pub trait ProcMacroClientInterface {
- fn source_text(&self, file_id: u32, start: u32, end: u32) -> Option<String>;
+ fn source_text(&mut self, file_id: u32, start: u32, end: u32) -> Option<String>;
}
const EXPANDER_STACK_SIZE: usize = 8 * 1024 * 1024;
@@ -111,7 +111,7 @@ impl ProcMacroSrv<'_> {
def_site: S,
call_site: S,
mixed_site: S,
- callback: Option<ProcMacroClientHandle>,
+ callback: Option<ProcMacroClientHandle<'_>>,
) -> Result<token_stream::TokenStream<S>, PanicMessage> {
let snapped_env = self.env;
let expander = self.expander(lib.as_ref()).map_err(|err| PanicMessage {
@@ -178,24 +178,26 @@ impl ProcMacroSrv<'_> {
}
pub trait ProcMacroSrvSpan: Copy + Send + Sync {
- type Server: proc_macro::bridge::server::Server<TokenStream = crate::token_stream::TokenStream<Self>>;
- fn make_server(
+ type Server<'a>: proc_macro::bridge::server::Server<TokenStream = crate::token_stream::TokenStream<Self>>
+ where
+ Self: 'a;
+ fn make_server<'a>(
call_site: Self,
def_site: Self,
mixed_site: Self,
- callback: Option<ProcMacroClientHandle>,
- ) -> Self::Server;
+ callback: Option<ProcMacroClientHandle<'a>>,
+ ) -> Self::Server<'a>;
}
impl ProcMacroSrvSpan for SpanId {
- type Server = server_impl::token_id::SpanIdServer;
+ type Server<'a> = server_impl::token_id::SpanIdServer<'a>;
- fn make_server(
+ fn make_server<'a>(
call_site: Self,
def_site: Self,
mixed_site: Self,
- callback: Option<ProcMacroClientHandle>,
- ) -> Self::Server {
+ callback: Option<ProcMacroClientHandle<'a>>,
+ ) -> Self::Server<'a> {
Self::Server {
call_site,
def_site,
@@ -208,13 +210,13 @@ impl ProcMacroSrvSpan for SpanId {
}
impl ProcMacroSrvSpan for Span {
- type Server = server_impl::rust_analyzer_span::RaSpanServer;
- fn make_server(
+ type Server<'a> = server_impl::rust_analyzer_span::RaSpanServer<'a>;
+ fn make_server<'a>(
call_site: Self,
def_site: Self,
mixed_site: Self,
- callback: Option<ProcMacroClientHandle>,
- ) -> Self::Server {
+ callback: Option<ProcMacroClientHandle<'a>>,
+ ) -> Self::Server<'a> {
Self::Server {
call_site,
def_site,
diff --git a/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs b/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs
index 5f7c0a5202..5d9090c060 100644
--- a/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs
+++ b/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs
@@ -21,7 +21,7 @@ use crate::{
pub struct FreeFunctions;
-pub struct RaSpanServer {
+pub struct RaSpanServer<'a> {
// FIXME: Report this back to the caller to track as dependencies
pub tracked_env_vars: HashMap<Box<str>, Option<Box<str>>>,
// FIXME: Report this back to the caller to track as dependencies
@@ -29,17 +29,17 @@ pub struct RaSpanServer {
pub call_site: Span,
pub def_site: Span,
pub mixed_site: Span,
- pub callback: Option<ProcMacroClientHandle>,
+ pub callback: Option<ProcMacroClientHandle<'a>>,
}
-impl server::Types for RaSpanServer {
+impl server::Types for RaSpanServer<'_> {
type FreeFunctions = FreeFunctions;
type TokenStream = crate::token_stream::TokenStream<Span>;
type Span = Span;
type Symbol = Symbol;
}
-impl server::FreeFunctions for RaSpanServer {
+impl server::FreeFunctions for RaSpanServer<'_> {
fn injected_env_var(&mut self, _: &str) -> Option<std::string::String> {
None
}
@@ -60,7 +60,7 @@ impl server::FreeFunctions for RaSpanServer {
}
}
-impl server::TokenStream for RaSpanServer {
+impl server::TokenStream for RaSpanServer<'_> {
fn is_empty(&mut self, stream: &Self::TokenStream) -> bool {
stream.is_empty()
}
@@ -123,7 +123,7 @@ impl server::TokenStream for RaSpanServer {
}
}
-impl server::Span for RaSpanServer {
+impl server::Span for RaSpanServer<'_> {
fn debug(&mut self, span: Self::Span) -> String {
format!("{:?}", span)
}
@@ -156,7 +156,7 @@ impl server::Span for RaSpanServer {
let start: u32 = span.range.start().into();
let end: u32 = span.range.end().into();
- self.callback.as_ref()?.source_text(file_id.file_id().index(), start, end)
+ self.callback.as_mut()?.source_text(file_id.file_id().index(), start, end)
}
fn parent(&mut self, _span: Self::Span) -> Option<Self::Span> {
@@ -274,14 +274,14 @@ impl server::Span for RaSpanServer {
}
}
-impl server::Symbol for RaSpanServer {
+impl server::Symbol for RaSpanServer<'_> {
fn normalize_and_validate_ident(&mut self, string: &str) -> Result<Self::Symbol, ()> {
// FIXME: nfc-normalize and validate idents
Ok(<Self as server::Server>::intern_symbol(string))
}
}
-impl server::Server for RaSpanServer {
+impl server::Server for RaSpanServer<'_> {
fn globals(&mut self) -> ExpnGlobals<Self::Span> {
ExpnGlobals {
def_site: self.def_site,
diff --git a/crates/proc-macro-srv/src/server_impl/token_id.rs b/crates/proc-macro-srv/src/server_impl/token_id.rs
index 646dde7952..a968ea4cd2 100644
--- a/crates/proc-macro-srv/src/server_impl/token_id.rs
+++ b/crates/proc-macro-srv/src/server_impl/token_id.rs
@@ -27,7 +27,7 @@ type Span = SpanId;
pub struct FreeFunctions;
-pub struct SpanIdServer {
+pub struct SpanIdServer<'a> {
// FIXME: Report this back to the caller to track as dependencies
pub tracked_env_vars: HashMap<Box<str>, Option<Box<str>>>,
// FIXME: Report this back to the caller to track as dependencies
@@ -35,17 +35,17 @@ pub struct SpanIdServer {
pub call_site: Span,
pub def_site: Span,
pub mixed_site: Span,
- pub callback: Option<ProcMacroClientHandle>,
+ pub callback: Option<ProcMacroClientHandle<'a>>,
}
-impl server::Types for SpanIdServer {
+impl server::Types for SpanIdServer<'_> {
type FreeFunctions = FreeFunctions;
type TokenStream = crate::token_stream::TokenStream<Span>;
type Span = Span;
type Symbol = Symbol;
}
-impl server::FreeFunctions for SpanIdServer {
+impl server::FreeFunctions for SpanIdServer<'_> {
fn injected_env_var(&mut self, _: &str) -> Option<std::string::String> {
None
}
@@ -63,7 +63,7 @@ impl server::FreeFunctions for SpanIdServer {
fn emit_diagnostic(&mut self, _: Diagnostic<Self::Span>) {}
}
-impl server::TokenStream for SpanIdServer {
+impl server::TokenStream for SpanIdServer<'_> {
fn is_empty(&mut self, stream: &Self::TokenStream) -> bool {
stream.is_empty()
}
@@ -120,7 +120,7 @@ impl server::TokenStream for SpanIdServer {
}
}
-impl server::Span for SpanIdServer {
+impl server::Span for SpanIdServer<'_> {
fn debug(&mut self, span: Self::Span) -> String {
format!("{:?}", span.0)
}
@@ -187,14 +187,14 @@ impl server::Span for SpanIdServer {
}
}
-impl server::Symbol for SpanIdServer {
+impl server::Symbol for SpanIdServer<'_> {
fn normalize_and_validate_ident(&mut self, string: &str) -> Result<Self::Symbol, ()> {
// FIXME: nfc-normalize and validate idents
Ok(<Self as server::Server>::intern_symbol(string))
}
}
-impl server::Server for SpanIdServer {
+impl server::Server for SpanIdServer<'_> {
fn globals(&mut self) -> ExpnGlobals<Self::Span> {
ExpnGlobals {
def_site: self.def_site,