aboutsummaryrefslogtreecommitdiff
path: root/crates/mbe/src/syntax_bridge.rs
diff options
context:
space:
mode:
authorbors[bot] <26634292+bors[bot]@users.noreply.github.com>2021-03-21 00:10:14 +0000
committerGitHub <[email protected]>2021-03-21 00:10:14 +0000
commit787bd3c5516d250245f6070308d689311b638fbe (patch)
tree3513cb44470b7ff148258bc300402be778c7f097 /crates/mbe/src/syntax_bridge.rs
parent090e013161ab5b1679554ddd53683e81e3fe845a (diff)
parent0a7f28620a7002f47890c2030862052bcbf25cdb (diff)
Merge #8122
8122: Make bare underscore token an Ident rather than Punct in proc-macro r=edwin0cheng a=kevinmehall In rustc and proc-macro2, a bare `_` token is parsed for procedural macro purposes as `Ident` rather than `Punct` (see https://github.com/rust-lang/rust/pull/48842). This changes rust-analyzer to match rustc's behavior and implementation by handling `_` as an Ident in token trees, but explicitly preventing `$x:ident` from matching it in MBE. proc macro crate: ```rust #[proc_macro] pub fn input(input: proc_macro::TokenStream) -> proc_macro::TokenStream { dbg!(input) } ``` test crate: ```rust test_proc_macro::input!(_); ``` output (rustc): ```rust [test-proc-macro/src/lib.rs:10] input = TokenStream [ Ident { ident: "_", span: #0 bytes(173..174), }, ] ``` output (rust-analyzer before this change): ```rust [test-proc-macro/src/lib.rs:10] input = TokenStream [ Punct { ch: '_', spacing: Joint, span: 4294967295, }, ] ``` output (rust-analyzer after this change): ```rust [test-proc-macro/src/lib.rs:10] input = TokenStream [ Ident { ident: "_", span: 4294967295, }, ] ``` Co-authored-by: Kevin Mehall <[email protected]>
Diffstat (limited to 'crates/mbe/src/syntax_bridge.rs')
-rw-r--r--crates/mbe/src/syntax_bridge.rs7
1 files changed, 5 insertions, 2 deletions
diff --git a/crates/mbe/src/syntax_bridge.rs b/crates/mbe/src/syntax_bridge.rs
index 85163c4b3..8bba3d3d5 100644
--- a/crates/mbe/src/syntax_bridge.rs
+++ b/crates/mbe/src/syntax_bridge.rs
@@ -350,7 +350,7 @@ trait TokenConvertor {
350 return; 350 return;
351 } 351 }
352 352
353 result.push(if k.is_punct() { 353 result.push(if k.is_punct() && k != UNDERSCORE {
354 assert_eq!(range.len(), TextSize::of('.')); 354 assert_eq!(range.len(), TextSize::of('.'));
355 let delim = match k { 355 let delim = match k {
356 T!['('] => Some((tt::DelimiterKind::Parenthesis, T![')'])), 356 T!['('] => Some((tt::DelimiterKind::Parenthesis, T![')'])),
@@ -395,7 +395,9 @@ trait TokenConvertor {
395 { 395 {
396 tt::Spacing::Alone 396 tt::Spacing::Alone
397 } 397 }
398 Some(next) if next.kind().is_punct() => tt::Spacing::Joint, 398 Some(next) if next.kind().is_punct() && next.kind() != UNDERSCORE => {
399 tt::Spacing::Joint
400 }
399 _ => tt::Spacing::Alone, 401 _ => tt::Spacing::Alone,
400 }; 402 };
401 let char = match token.to_char() { 403 let char = match token.to_char() {
@@ -415,6 +417,7 @@ trait TokenConvertor {
415 let leaf: tt::Leaf = match k { 417 let leaf: tt::Leaf = match k {
416 T![true] | T![false] => make_leaf!(Ident), 418 T![true] | T![false] => make_leaf!(Ident),
417 IDENT => make_leaf!(Ident), 419 IDENT => make_leaf!(Ident),
420 UNDERSCORE => make_leaf!(Ident),
418 k if k.is_keyword() => make_leaf!(Ident), 421 k if k.is_keyword() => make_leaf!(Ident),
419 k if k.is_literal() => make_leaf!(Literal), 422 k if k.is_literal() => make_leaf!(Literal),
420 LIFETIME_IDENT => { 423 LIFETIME_IDENT => {