about summary refs log tree commit diff
path: root/compiler/rustc_ast_pretty
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2024-01-31 02:01:43 +0000
committerbors <bors@rust-lang.org>2024-01-31 02:01:43 +0000
commit80deabd0987201e1b8d060400f50e03309a0105e (patch)
treeacdccbae91c5e6a9fa59d3b4dbfc031bd2339621 /compiler/rustc_ast_pretty
parentcb4d9a1902b3ea17e93872dafb76d24aa6295c47 (diff)
parent1fbabeeb2e0e737301f6527ec3a22f1fa2f87676 (diff)
downloadrust-80deabd0987201e1b8d060400f50e03309a0105e.tar.gz
rust-80deabd0987201e1b8d060400f50e03309a0105e.zip
Auto merge of #120227 - nnethercote:further-improve-space_between, r=petrochenkov
Further improve `space_between`

`space_between` is used by `print_tts` to decide when spaces should be put between  tokens. This PR improves it in two ways:
- avoid unnecessary spaces before semicolons, and
- don't omit some necessary spaces before/after some punctuation symbols.

r? `@petrochenkov`
Diffstat (limited to 'compiler/rustc_ast_pretty')
-rw-r--r--compiler/rustc_ast_pretty/src/pprust/state.rs51
1 files changed, 33 insertions, 18 deletions
diff --git a/compiler/rustc_ast_pretty/src/pprust/state.rs b/compiler/rustc_ast_pretty/src/pprust/state.rs
index c2fd4558fd7..a6f6f0b29a0 100644
--- a/compiler/rustc_ast_pretty/src/pprust/state.rs
+++ b/compiler/rustc_ast_pretty/src/pprust/state.rs
@@ -160,6 +160,10 @@ fn space_between(tt1: &TokenTree, tt2: &TokenTree) -> bool {
     use TokenTree::Delimited as Del;
     use TokenTree::Token as Tok;
 
+    fn is_punct(tt: &TokenTree) -> bool {
+        matches!(tt, TokenTree::Token(tok, _) if tok.is_punct())
+    }
+
     // Each match arm has one or more examples in comments. The default is to
     // insert space between adjacent tokens, except for the cases listed in
     // this match.
@@ -167,24 +171,35 @@ fn space_between(tt1: &TokenTree, tt2: &TokenTree) -> bool {
         // No space after line doc comments.
         (Tok(Token { kind: DocComment(CommentKind::Line, ..), .. }, _), _) => false,
 
-        // `.` + ANYTHING: `x.y`, `tup.0`
-        // `$` + ANYTHING: `$e`
-        (Tok(Token { kind: Dot | Dollar, .. }, _), _) => false,
-
-        // ANYTHING + `,`: `foo,`
-        // ANYTHING + `.`: `x.y`, `tup.0`
-        // ANYTHING + `!`: `foo! { ... }`
-        //
-        // FIXME: Incorrect cases:
-        // - Logical not: `x =! y`, `if! x { f(); }`
-        // - Never type: `Fn() ->!`
-        (_, Tok(Token { kind: Comma | Dot | Not, .. }, _)) => false,
-
-        // IDENT + `(`: `f(3)`
-        //
-        // FIXME: Incorrect cases:
-        // - Let: `let(a, b) = (1, 2)`
-        (Tok(Token { kind: Ident(..), .. }, _), Del(_, _, Parenthesis, _)) => false,
+        // `.` + NON-PUNCT: `x.y`, `tup.0`
+        (Tok(Token { kind: Dot, .. }, _), tt2) if !is_punct(tt2) => false,
+
+        // `$` + IDENT: `$e`
+        (Tok(Token { kind: Dollar, .. }, _), Tok(Token { kind: Ident(..), .. }, _)) => false,
+
+        // NON-PUNCT + `,`: `foo,`
+        // NON-PUNCT + `;`: `x = 3;`, `[T; 3]`
+        // NON-PUNCT + `.`: `x.y`, `tup.0`
+        (tt1, Tok(Token { kind: Comma | Semi | Dot, .. }, _)) if !is_punct(tt1) => false,
+
+        // IDENT + `!`: `println!()`, but `if !x { ... }` needs a space after the `if`
+        (Tok(Token { kind: Ident(sym, is_raw), span }, _), Tok(Token { kind: Not, .. }, _))
+            if !Ident::new(*sym, *span).is_reserved() || *is_raw =>
+        {
+            false
+        }
+
+        // IDENT|`fn`|`Self`|`pub` + `(`: `f(3)`, `fn(x: u8)`, `Self()`, `pub(crate)`,
+        //      but `let (a, b) = (1, 2)` needs a space after the `let`
+        (Tok(Token { kind: Ident(sym, is_raw), span }, _), Del(_, _, Parenthesis, _))
+            if !Ident::new(*sym, *span).is_reserved()
+                || *sym == kw::Fn
+                || *sym == kw::SelfUpper
+                || *sym == kw::Pub
+                || *is_raw =>
+        {
+            false
+        }
 
         // `#` + `[`: `#[attr]`
         (Tok(Token { kind: Pound, .. }, _), Del(_, _, Bracket, _)) => false,