about summary refs log tree commit diff
diff options
context:
space:
mode:
authorLeón Orell Valerian Liehr <me@fmease.dev>2023-09-12 16:30:38 +0200
committerLeón Orell Valerian Liehr <me@fmease.dev>2023-09-12 16:38:59 +0200
commit3ed77e98fa9e9a03940b55b0bbc10615b446f299 (patch)
treedc2298cc0df4255e74f0e7fbb4c9523632206a6b
parent3cd97ed3c3efe11bf6b63d23dce2515238b78a57 (diff)
downloadrust-3ed77e98fa9e9a03940b55b0bbc10615b446f299.tar.gz
rust-3ed77e98fa9e9a03940b55b0bbc10615b446f299.zip
Only suggest turbofish in patterns if we may recover
-rw-r--r--compiler/rustc_parse/src/parser/pat.rs3
-rw-r--r--tests/ui/parser/issues/issue-115780-pat-lt-bracket-in-macro-call.rs21
2 files changed, 23 insertions, 1 deletions
diff --git a/compiler/rustc_parse/src/parser/pat.rs b/compiler/rustc_parse/src/parser/pat.rs
index 4aadb7d7ca5..3e4e9278910 100644
--- a/compiler/rustc_parse/src/parser/pat.rs
+++ b/compiler/rustc_parse/src/parser/pat.rs
@@ -830,7 +830,8 @@ impl<'a> Parser<'a> {
     ) -> PResult<'a, PatKind> {
         let ident = self.parse_ident()?;
 
-        if !matches!(syntax_loc, Some(PatternLocation::FunctionParameter))
+        if self.may_recover()
+            && !matches!(syntax_loc, Some(PatternLocation::FunctionParameter))
             && self.check_noexpect(&token::Lt)
             && self.look_ahead(1, |t| t.can_begin_type())
         {
diff --git a/tests/ui/parser/issues/issue-115780-pat-lt-bracket-in-macro-call.rs b/tests/ui/parser/issues/issue-115780-pat-lt-bracket-in-macro-call.rs
new file mode 100644
index 00000000000..3421333b8a0
--- /dev/null
+++ b/tests/ui/parser/issues/issue-115780-pat-lt-bracket-in-macro-call.rs
@@ -0,0 +1,21 @@
+// Regression test for issue #115780.
+// Ensure that we don't emit a parse error for the token sequence `Ident "<" Ty` in pattern position
+// if we are inside a macro call since it can be valid input for a subsequent macro rule.
+// See also #103534.
+
+// check-pass
+
+macro_rules! mdo {
+    ($p: pat =<< $e: expr ; $( $t: tt )*) => {
+        $e.and_then(|$p| mdo! { $( $t )* })
+    };
+    (ret<$ty: ty> $e: expr;) => { Some::<$ty>($e) };
+}
+
+fn main() {
+    mdo! {
+        x_val =<< Some(0);
+        y_val =<< Some(1);
+        ret<(i32, i32)> (x_val, y_val);
+    };
+}