Skip to content

Commit 508ce7c

Browse files
authored
Merge pull request #18669 from Veykril/push-qqkuxtvsmsut
internal: Only parse the object file once in proc-macro-srv
2 parents d41ad2c + b6b7c57 commit 508ce7c

File tree

8 files changed

+31
-32
lines changed

8 files changed

+31
-32
lines changed

src/tools/rust-analyzer/crates/proc-macro-srv-cli/src/main.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ fn run() -> io::Result<()> {
6969

7070
let write_response = |msg: msg::Response| msg.write(write_json, &mut io::stdout().lock());
7171

72-
let env = EnvSnapshot::new();
72+
let env = EnvSnapshot::default();
7373
let mut srv = proc_macro_srv::ProcMacroSrv::new(&env);
7474
let mut buf = String::new();
7575

src/tools/rust-analyzer/crates/proc-macro-srv/src/dylib.rs

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,6 @@ use proc_macro::bridge;
66
use std::{fmt, fs, io, time::SystemTime};
77

88
use libloading::Library;
9-
use memmap2::Mmap;
109
use object::Object;
1110
use paths::{Utf8Path, Utf8PathBuf};
1211
use proc_macro_api::ProcMacroKind;
@@ -23,8 +22,8 @@ fn is_derive_registrar_symbol(symbol: &str) -> bool {
2322
symbol.contains(NEW_REGISTRAR_SYMBOL)
2423
}
2524

26-
fn find_registrar_symbol(buffer: &[u8]) -> object::Result<Option<String>> {
27-
Ok(object::File::parse(buffer)?
25+
fn find_registrar_symbol(obj: &object::File<'_>) -> object::Result<Option<String>> {
26+
Ok(obj
2827
.exports()?
2928
.into_iter()
3029
.map(|export| export.name())
@@ -109,15 +108,16 @@ struct ProcMacroLibraryLibloading {
109108

110109
impl ProcMacroLibraryLibloading {
111110
fn open(path: &Utf8Path) -> Result<Self, LoadProcMacroDylibError> {
112-
let buffer = unsafe { Mmap::map(&fs::File::open(path)?)? };
111+
let file = fs::File::open(path)?;
112+
let file = unsafe { memmap2::Mmap::map(&file) }?;
113+
let obj = object::File::parse(&*file)
114+
.map_err(|e| io::Error::new(io::ErrorKind::InvalidData, e))?;
115+
let version_info = version::read_dylib_info(&obj)?;
113116
let symbol_name =
114-
find_registrar_symbol(&buffer).map_err(invalid_data_err)?.ok_or_else(|| {
117+
find_registrar_symbol(&obj).map_err(invalid_data_err)?.ok_or_else(|| {
115118
invalid_data_err(format!("Cannot find registrar symbol in file {path}"))
116119
})?;
117120

118-
let version_info = version::read_dylib_info(&buffer)?;
119-
drop(buffer);
120-
121121
let lib = load_library(path).map_err(invalid_data_err)?;
122122
let proc_macros = crate::proc_macros::ProcMacros::from_lib(
123123
&lib,

src/tools/rust-analyzer/crates/proc-macro-srv/src/dylib/version.rs

Lines changed: 11 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
33
use std::io::{self, Read};
44

5-
use object::read::{File as BinaryFile, Object, ObjectSection};
5+
use object::read::{Object, ObjectSection};
66

77
#[derive(Debug)]
88
#[allow(dead_code)]
@@ -16,14 +16,14 @@ pub struct RustCInfo {
1616
}
1717

1818
/// Read rustc dylib information
19-
pub fn read_dylib_info(buffer: &[u8]) -> io::Result<RustCInfo> {
19+
pub fn read_dylib_info(obj: &object::File<'_>) -> io::Result<RustCInfo> {
2020
macro_rules! err {
2121
($e:literal) => {
2222
io::Error::new(io::ErrorKind::InvalidData, $e)
2323
};
2424
}
2525

26-
let ver_str = read_version(buffer)?;
26+
let ver_str = read_version(obj)?;
2727
let mut items = ver_str.split_whitespace();
2828
let tag = items.next().ok_or_else(|| err!("version format error"))?;
2929
if tag != "rustc" {
@@ -70,10 +70,8 @@ pub fn read_dylib_info(buffer: &[u8]) -> io::Result<RustCInfo> {
7070

7171
/// This is used inside read_version() to locate the ".rustc" section
7272
/// from a proc macro crate's binary file.
73-
fn read_section<'a>(dylib_binary: &'a [u8], section_name: &str) -> io::Result<&'a [u8]> {
74-
BinaryFile::parse(dylib_binary)
75-
.map_err(|e| io::Error::new(io::ErrorKind::InvalidData, e))?
76-
.section_by_name(section_name)
73+
fn read_section<'a>(obj: &object::File<'a>, section_name: &str) -> io::Result<&'a [u8]> {
74+
obj.section_by_name(section_name)
7775
.ok_or_else(|| io::Error::new(io::ErrorKind::InvalidData, "section read error"))?
7876
.data()
7977
.map_err(|e| io::Error::new(io::ErrorKind::InvalidData, e))
@@ -101,8 +99,8 @@ fn read_section<'a>(dylib_binary: &'a [u8], section_name: &str) -> io::Result<&'
10199
///
102100
/// Check this issue for more about the bytes layout:
103101
/// <https://github.com/rust-lang/rust-analyzer/issues/6174>
104-
pub fn read_version(buffer: &[u8]) -> io::Result<String> {
105-
let dot_rustc = read_section(buffer, ".rustc")?;
102+
pub fn read_version(obj: &object::File<'_>) -> io::Result<String> {
103+
let dot_rustc = read_section(obj, ".rustc")?;
106104

107105
// check if magic is valid
108106
if &dot_rustc[0..4] != b"rust" {
@@ -151,10 +149,10 @@ pub fn read_version(buffer: &[u8]) -> io::Result<String> {
151149

152150
#[test]
153151
fn test_version_check() {
154-
let info = read_dylib_info(&unsafe {
155-
memmap2::Mmap::map(&std::fs::File::open(crate::proc_macro_test_dylib_path()).unwrap())
156-
.unwrap()
157-
})
152+
let info = read_dylib_info(
153+
&object::File::parse(&*std::fs::read(crate::proc_macro_test_dylib_path()).unwrap())
154+
.unwrap(),
155+
)
158156
.unwrap();
159157

160158
assert_eq!(

src/tools/rust-analyzer/crates/proc-macro-srv/src/lib.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
#![cfg(any(feature = "sysroot-abi", rust_analyzer))]
1414
#![cfg_attr(feature = "in-rust-tree", feature(rustc_private))]
1515
#![feature(proc_macro_internals, proc_macro_diagnostic, proc_macro_span)]
16-
#![allow(unreachable_pub, internal_features)]
16+
#![allow(unreachable_pub, internal_features, clippy::disallowed_types, clippy::print_stderr)]
1717

1818
extern crate proc_macro;
1919
#[cfg(feature = "in-rust-tree")]
@@ -65,7 +65,7 @@ impl<'env> ProcMacroSrv<'env> {
6565

6666
const EXPANDER_STACK_SIZE: usize = 8 * 1024 * 1024;
6767

68-
impl<'env> ProcMacroSrv<'env> {
68+
impl ProcMacroSrv<'_> {
6969
pub fn set_span_mode(&mut self, span_mode: SpanMode) {
7070
self.span_mode = span_mode;
7171
}
@@ -248,8 +248,8 @@ pub struct EnvSnapshot {
248248
vars: HashMap<OsString, OsString>,
249249
}
250250

251-
impl EnvSnapshot {
252-
pub fn new() -> EnvSnapshot {
251+
impl Default for EnvSnapshot {
252+
fn default() -> EnvSnapshot {
253253
EnvSnapshot { vars: env::vars_os().collect() }
254254
}
255255
}
@@ -305,7 +305,7 @@ impl Drop for EnvChange<'_> {
305305
}
306306

307307
if let Some(dir) = &self.prev_working_dir {
308-
if let Err(err) = std::env::set_current_dir(&dir) {
308+
if let Err(err) = std::env::set_current_dir(dir) {
309309
eprintln!(
310310
"Failed to set the current working dir to {}. Error: {:?}",
311311
dir.display(),

src/tools/rust-analyzer/crates/proc-macro-srv/src/proc_macros.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ pub(crate) struct ProcMacros {
1313

1414
impl From<bridge::PanicMessage> for crate::PanicMessage {
1515
fn from(p: bridge::PanicMessage) -> Self {
16-
Self { message: p.as_str().map(|s| s.to_string()) }
16+
Self { message: p.as_str().map(|s| s.to_owned()) }
1717
}
1818
}
1919

src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -498,7 +498,7 @@ mod tests {
498498
})),
499499
tt::TokenTree::Leaf(tt::Leaf::Ident(tt::Ident {
500500
sym: Symbol::intern("T"),
501-
span: span,
501+
span,
502502
is_raw: tt::IdentIsRaw::No,
503503
})),
504504
tt::TokenTree::Subtree(tt::Subtree {

src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_stream.rs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -99,7 +99,7 @@ pub(super) struct TokenStreamBuilder<S> {
9999
}
100100

101101
/// pub(super)lic implementation details for the `TokenStream` type, such as iterators.
102-
pub(super) mod token_stream {
102+
pub(super) mod token_stream_impls {
103103

104104
use core::fmt;
105105

@@ -137,6 +137,7 @@ pub(super) mod token_stream {
137137
}
138138
}
139139

140+
#[allow(clippy::to_string_trait_impl)]
140141
impl<S> ToString for TokenStream<S> {
141142
fn to_string(&self) -> String {
142143
::tt::pretty(&self.token_trees)
@@ -150,7 +151,7 @@ impl<S> TokenStreamBuilder<S> {
150151
}
151152

152153
pub(super) fn push(&mut self, stream: TokenStream<S>) {
153-
self.acc.extend(stream.into_iter())
154+
self.acc.extend(stream)
154155
}
155156

156157
pub(super) fn build(self) -> TokenStream<S> {

src/tools/rust-analyzer/crates/proc-macro-srv/src/tests/utils.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -97,7 +97,7 @@ fn assert_expand_impl(
9797

9898
pub(crate) fn list() -> Vec<String> {
9999
let dylib_path = proc_macro_test_dylib_path();
100-
let env = EnvSnapshot::new();
100+
let env = EnvSnapshot::default();
101101
let mut srv = ProcMacroSrv::new(&env);
102102
let res = srv.list_macros(&dylib_path).unwrap();
103103
res.into_iter().map(|(name, kind)| format!("{name} [{kind:?}]")).collect()

0 commit comments

Comments
 (0)