diff options
| author | Lukas Wirth <lukastw97@gmail.com> | 2025-05-05 13:56:24 +0200 |
|---|---|---|
| committer | Lukas Wirth <lukastw97@gmail.com> | 2025-05-05 14:10:42 +0200 |
| commit | 4f0c28e1dcc07052c1f8ddce686628c1c8f959c8 (patch) | |
| tree | 57c8dfaa10151a756a8e833e8563fafddd73bac1 | |
| parent | 53881efacb7af06677c1632523d43c5c173dd2dd (diff) | |
| download | rust-4f0c28e1dcc07052c1f8ddce686628c1c8f959c8.tar.gz rust-4f0c28e1dcc07052c1f8ddce686628c1c8f959c8.zip | |
fix: Fix proc-macro API creating malformed negative literals
4 files changed, 85 insertions, 29 deletions
diff --git a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs index 47555a5db2f..64b40e7b943 100644 --- a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs +++ b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs @@ -168,16 +168,38 @@ impl server::TokenStream for RaSpanServer { } bridge::TokenTree::Literal(literal) => { - let literal = tt::Literal { - symbol: literal.symbol, - suffix: literal.suffix, - span: literal.span, - kind: literal_kind_to_internal(literal.kind), - }; - - let leaf: tt::Leaf = tt::Leaf::from(literal); - let tree = tt::TokenTree::from(leaf); - TokenStream { token_trees: vec![tree] } + let token_trees = + if let Some((_minus, symbol)) = literal.symbol.as_str().split_once('-') { + let punct = tt::Punct { + spacing: tt::Spacing::Alone, + span: literal.span, + char: '-' as char, + }; + let leaf: tt::Leaf = tt::Leaf::from(punct); + let minus_tree = tt::TokenTree::from(leaf); + + let literal = tt::Literal { + symbol: Symbol::intern(symbol), + suffix: literal.suffix, + span: literal.span, + kind: literal_kind_to_internal(literal.kind), + }; + let leaf: tt::Leaf = tt::Leaf::from(literal); + let tree = tt::TokenTree::from(leaf); + vec![minus_tree, tree] + } else { + let literal = tt::Literal { + symbol: literal.symbol, + suffix: literal.suffix, + span: literal.span, + kind: literal_kind_to_internal(literal.kind), + }; + + let leaf: tt::Leaf = tt::Leaf::from(literal); + let tree = tt::TokenTree::from(leaf); + vec![tree] + }; + TokenStream { token_trees } } bridge::TokenTree::Punct(p) => { diff --git a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_id.rs b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_id.rs index c002be4be6f..24a67bf45c8 100644 --- a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_id.rs +++ b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_id.rs @@ -153,16 +153,38 @@ impl server::TokenStream for TokenIdServer { } bridge::TokenTree::Literal(literal) => { - let literal = Literal { - symbol: literal.symbol, - suffix: literal.suffix, - span: literal.span, - kind: literal_kind_to_internal(literal.kind), - }; - - let leaf = tt::Leaf::from(literal); - let tree = TokenTree::from(leaf); - TokenStream { token_trees: vec![tree] } + let token_trees = + if let Some((_minus, symbol)) = literal.symbol.as_str().split_once('-') { + let punct = tt::Punct { + spacing: tt::Spacing::Alone, + span: literal.span, + char: '-' as char, + }; + let leaf: tt::Leaf = tt::Leaf::from(punct); + let minus_tree = tt::TokenTree::from(leaf); + + let literal = Literal { + symbol: Symbol::intern(symbol), + suffix: literal.suffix, + span: literal.span, + kind: literal_kind_to_internal(literal.kind), + }; + let leaf: tt::Leaf = tt::Leaf::from(literal); + let tree = tt::TokenTree::from(leaf); + vec![minus_tree, tree] + } else { + let literal = Literal { + symbol: literal.symbol, + suffix: literal.suffix, + span: literal.span, + kind: literal_kind_to_internal(literal.kind), + }; + + let leaf: tt::Leaf = tt::Leaf::from(literal); + let tree = tt::TokenTree::from(leaf); + vec![tree] + }; + TokenStream { token_trees } } bridge::TokenTree::Punct(p) => { diff --git a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_stream.rs b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_stream.rs index 4946a4f2a62..072557913c2 100644 --- a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_stream.rs +++ b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_stream.rs @@ -68,6 +68,11 @@ impl<S: Copy> TokenStream<S> { span: ident.span, })) } + // Note, we do not have to assemble our `-` punct and literal split into a single + // negative bridge literal here. As the proc-macro docs state + // > Literals created from negative numbers might not survive round-trips through + // > TokenStream or strings and may be broken into two tokens (- and positive + // > literal). tt::TokenTree::Leaf(tt::Leaf::Literal(lit)) => { result.push(bridge::TokenTree::Literal(bridge::Literal { span: lit.span, diff --git a/src/tools/rust-analyzer/crates/proc-macro-srv/src/tests/mod.rs b/src/tools/rust-analyzer/crates/proc-macro-srv/src/tests/mod.rs index 7a0ac01c50d..36cd675b9a6 100644 --- a/src/tools/rust-analyzer/crates/proc-macro-srv/src/tests/mod.rs +++ b/src/tools/rust-analyzer/crates/proc-macro-srv/src/tests/mod.rs @@ -248,13 +248,17 @@ fn test_fn_like_mk_literals() { LITERAL Str string 1 LITERAL CStr cstring 1 LITERAL Float 3.14f64 1 - LITERAL Float -3.14f64 1 + PUNCH - [alone] 1 + LITERAL Float 3.14f64 1 + LITERAL Float 3.14 1 + PUNCH - [alone] 1 LITERAL Float 3.14 1 - LITERAL Float -3.14 1 LITERAL Integer 123i64 1 - LITERAL Integer -123i64 1 + PUNCH - [alone] 1 + LITERAL Integer 123i64 1 LITERAL Integer 123 1 - LITERAL Integer -123 1"#]], + PUNCH - [alone] 1 + LITERAL Integer 123 1"#]], expect![[r#" SUBTREE $$ 42:2@0..100#ROOT2024 42:2@0..100#ROOT2024 @@ -266,13 +270,17 @@ fn test_fn_like_mk_literals() { LITERAL Str string 42:2@0..100#ROOT2024 LITERAL CStr cstring 42:2@0..100#ROOT2024 LITERAL Float 3.14f64 42:2@0..100#ROOT2024 - LITERAL Float -3.14f64 42:2@0..100#ROOT2024 + PUNCH - [alone] 42:2@0..100#ROOT2024 + LITERAL Float 3.14f64 42:2@0..100#ROOT2024 + LITERAL Float 3.14 42:2@0..100#ROOT2024 + PUNCH - [alone] 42:2@0..100#ROOT2024 LITERAL Float 3.14 42:2@0..100#ROOT2024 - LITERAL Float -3.14 42:2@0..100#ROOT2024 LITERAL Integer 123i64 42:2@0..100#ROOT2024 - LITERAL Integer -123i64 42:2@0..100#ROOT2024 + PUNCH - [alone] 42:2@0..100#ROOT2024 + LITERAL Integer 123i64 42:2@0..100#ROOT2024 LITERAL Integer 123 42:2@0..100#ROOT2024 - LITERAL Integer -123 42:2@0..100#ROOT2024"#]], + PUNCH - [alone] 42:2@0..100#ROOT2024 + LITERAL Integer 123 42:2@0..100#ROOT2024"#]], ); } @@ -400,7 +408,6 @@ fn test_fn_like_macro_clone_literals() { ); } - #[test] fn test_fn_like_macro_negative_literals() { assert_expand( |
