about summary refs log tree commit diff
path: root/compiler/rustc_expand/src
diff options
context:
space:
mode:
authorTrevor Gross <tmgross@umich.edu>2025-06-17 22:25:51 -0400
committerTrevor Gross <tmgross@umich.edu>2025-06-24 04:37:32 -0400
commitbe927caf063b5da94cae8f3f697d190f83115a4f (patch)
tree0fcb8bdfbe94e940442a6b6969fb130feb9c2022 /compiler/rustc_expand/src
parent77ec48f5642ee1aa451d270f11f308c297f55f76 (diff)
downloadrust-be927caf063b5da94cae8f3f697d190f83115a4f.tar.gz
rust-be927caf063b5da94cae8f3f697d190f83115a4f.zip
mbe: Unnest nested matches with let-else and let chains
Non-functional change to simplify control flow.
Diffstat (limited to 'compiler/rustc_expand/src')
-rw-r--r--compiler/rustc_expand/src/mbe/quoted.rs121
1 files changed, 63 insertions, 58 deletions
diff --git a/compiler/rustc_expand/src/mbe/quoted.rs b/compiler/rustc_expand/src/mbe/quoted.rs
index 0c2362f23bc..de3e949af23 100644
--- a/compiler/rustc_expand/src/mbe/quoted.rs
+++ b/compiler/rustc_expand/src/mbe/quoted.rs
@@ -54,66 +54,71 @@ pub(super) fn parse(
         // Given the parsed tree, if there is a metavar and we are expecting matchers, actually
         // parse out the matcher (i.e., in `$id:ident` this would parse the `:` and `ident`).
         let tree = parse_tree(tree, &mut iter, parsing_patterns, sess, node_id, features, edition);
-        match tree {
-            TokenTree::MetaVar(start_sp, ident) if parsing_patterns => {
-                // Not consuming the next token immediately, as it may not be a colon
-                let span = match iter.peek() {
-                    Some(&tokenstream::TokenTree::Token(
-                        Token { kind: token::Colon, span: colon_span },
-                        _,
-                    )) => {
-                        // Consume the colon first
-                        iter.next();
-
-                        // It's ok to consume the next tree no matter how,
-                        // since if it's not a token then it will be an invalid declaration.
-                        match iter.next() {
-                            Some(tokenstream::TokenTree::Token(token, _)) => match token.ident() {
-                                Some((fragment, _)) => {
-                                    let span = token.span.with_lo(start_sp.lo());
-                                    let edition = || {
-                                        // FIXME(#85708) - once we properly decode a foreign
-                                        // crate's `SyntaxContext::root`, then we can replace
-                                        // this with just `span.edition()`. A
-                                        // `SyntaxContext::root()` from the current crate will
-                                        // have the edition of the current crate, and a
-                                        // `SyntaxContext::root()` from a foreign crate will
-                                        // have the edition of that crate (which we manually
-                                        // retrieve via the `edition` parameter).
-                                        if !span.from_expansion() {
-                                            edition
-                                        } else {
-                                            span.edition()
-                                        }
-                                    };
-                                    let kind = NonterminalKind::from_symbol(fragment.name, edition)
-                                        .unwrap_or_else(|| {
-                                            sess.dcx().emit_err(errors::InvalidFragmentSpecifier {
-                                                span,
-                                                fragment,
-                                                help: VALID_FRAGMENT_NAMES_MSG.into(),
-                                            });
-                                            NonterminalKind::Ident
-                                        });
-                                    result.push(TokenTree::MetaVarDecl(span, ident, Some(kind)));
-                                    continue;
-                                }
-                                _ => token.span,
-                            },
-                            // Invalid, return a nice source location
-                            _ => colon_span.with_lo(start_sp.lo()),
-                        }
-                    }
-                    // Whether it's none or some other tree, it doesn't belong to
-                    // the current meta variable, returning the original span.
-                    _ => start_sp,
-                };
 
-                result.push(TokenTree::MetaVarDecl(span, ident, None));
-            }
+        if !parsing_patterns {
+            // No matchers allowed, nothing to process here
+            result.push(tree);
+            continue;
+        }
+
+        let TokenTree::MetaVar(start_sp, ident) = tree else {
+            // Not a metavariable, just return the tree
+            result.push(tree);
+            continue;
+        };
 
-            // Not a metavar or no matchers allowed, so just return the tree
-            _ => result.push(tree),
+        // Push a metavariable with no fragment specifier at the given span
+        let mut push_empty_metavar = |span| {
+            result.push(TokenTree::MetaVarDecl(span, ident, None));
+        };
+
+        // Not consuming the next token immediately, as it may not be a colon
+        if let Some(peek) = iter.peek()
+            && let tokenstream::TokenTree::Token(token, _spacing) = peek
+            && let Token { kind: token::Colon, span: colon_span } = token
+        {
+            // Next token is a colon; consume it
+            iter.next();
+
+            // It's ok to consume the next tree no matter how,
+            // since if it's not a token then it will be an invalid declaration.
+            let Some(tokenstream::TokenTree::Token(token, _)) = iter.next() else {
+                // Invalid, return a nice source location as `var:`
+                push_empty_metavar(colon_span.with_lo(start_sp.lo()));
+                continue;
+            };
+
+            let Some((fragment, _)) = token.ident() else {
+                // No identifier for the fragment specifier;
+                push_empty_metavar(token.span);
+                continue;
+            };
+
+            let span = token.span.with_lo(start_sp.lo());
+            let edition = || {
+                // FIXME(#85708) - once we properly decode a foreign
+                // crate's `SyntaxContext::root`, then we can replace
+                // this with just `span.edition()`. A
+                // `SyntaxContext::root()` from the current crate will
+                // have the edition of the current crate, and a
+                // `SyntaxContext::root()` from a foreign crate will
+                // have the edition of that crate (which we manually
+                // retrieve via the `edition` parameter).
+                if !span.from_expansion() { edition } else { span.edition() }
+            };
+            let kind = NonterminalKind::from_symbol(fragment.name, edition).unwrap_or_else(|| {
+                sess.dcx().emit_err(errors::InvalidFragmentSpecifier {
+                    span,
+                    fragment,
+                    help: VALID_FRAGMENT_NAMES_MSG.into(),
+                });
+                NonterminalKind::Ident
+            });
+            result.push(TokenTree::MetaVarDecl(span, ident, Some(kind)));
+        } else {
+            // Whether it's none or some other tree, it doesn't belong to
+            // the current meta variable, returning the original span.
+            push_empty_metavar(start_sp);
         }
     }
     result