about summary refs log tree commit diff
path: root/compiler/rustc_parse
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2022-03-21 02:29:55 +0000
committerbors <bors@rust-lang.org>2022-03-21 02:29:55 +0000
commit051d1176b786aadd7d7c048f822cb6bfab00fe03 (patch)
tree8110d46108a24f55795dc54f0abf271877d52713 /compiler/rustc_parse
parenteded76b6f16ca0e5b10259f60092aeceeb60b67e (diff)
parent3516a16eebc93c2ebcf049ce9bb83748f365a57d (diff)
downloadrust-051d1176b786aadd7d7c048f822cb6bfab00fe03.tar.gz
rust-051d1176b786aadd7d7c048f822cb6bfab00fe03.zip
Auto merge of #95104 - compiler-errors:remove-ascription, r=davidtwco
suggest removing type ascription in bad parsing position

Not sure how to test this with the non-nightly suggestion. Didn't add a new UI test because it already manifests in an existing UI test.

Fixes #95014
Diffstat (limited to 'compiler/rustc_parse')
-rw-r--r--compiler/rustc_parse/src/parser/expr.rs41
1 files changed, 35 insertions, 6 deletions
diff --git a/compiler/rustc_parse/src/parser/expr.rs b/compiler/rustc_parse/src/parser/expr.rs
index a907f50a11b..148e0a24ec3 100644
--- a/compiler/rustc_parse/src/parser/expr.rs
+++ b/compiler/rustc_parse/src/parser/expr.rs
@@ -800,11 +800,17 @@ impl<'a> Parser<'a> {
         &mut self,
         cast_expr: P<Expr>,
     ) -> PResult<'a, P<Expr>> {
+        let span = cast_expr.span;
+        let maybe_ascription_span = if let ExprKind::Type(ascripted_expr, _) = &cast_expr.kind {
+            Some(ascripted_expr.span.shrink_to_hi().with_hi(span.hi()))
+        } else {
+            None
+        };
+
         // Save the memory location of expr before parsing any following postfix operators.
         // This will be compared with the memory location of the output expression.
         // If they different we can assume we parsed another expression because the existing expression is not reallocated.
         let addr_before = &*cast_expr as *const _ as usize;
-        let span = cast_expr.span;
         let with_postfix = self.parse_dot_or_call_expr_with_(cast_expr, span)?;
         let changed = addr_before != &*with_postfix as *const _ as usize;
 
@@ -825,11 +831,8 @@ impl<'a> Parser<'a> {
                 }
             );
             let mut err = self.struct_span_err(span, &msg);
-            // If type ascription is "likely an error", the user will already be getting a useful
-            // help message, and doesn't need a second.
-            if self.last_type_ascription.map_or(false, |last_ascription| last_ascription.1) {
-                self.maybe_annotate_with_ascription(&mut err, false);
-            } else {
+
+            let suggest_parens = |err: &mut DiagnosticBuilder<'_, _>| {
                 let suggestions = vec![
                     (span.shrink_to_lo(), "(".to_string()),
                     (span.shrink_to_hi(), ")".to_string()),
@@ -839,6 +842,32 @@ impl<'a> Parser<'a> {
                     suggestions,
                     Applicability::MachineApplicable,
                 );
+            };
+
+            // If type ascription is "likely an error", the user will already be getting a useful
+            // help message, and doesn't need a second.
+            if self.last_type_ascription.map_or(false, |last_ascription| last_ascription.1) {
+                self.maybe_annotate_with_ascription(&mut err, false);
+            } else if let Some(ascription_span) = maybe_ascription_span {
+                let is_nightly = self.sess.unstable_features.is_nightly_build();
+                if is_nightly {
+                    suggest_parens(&mut err);
+                }
+                err.span_suggestion(
+                    ascription_span,
+                    &format!(
+                        "{}remove the type ascription",
+                        if is_nightly { "alternatively, " } else { "" }
+                    ),
+                    String::new(),
+                    if is_nightly {
+                        Applicability::MaybeIncorrect
+                    } else {
+                        Applicability::MachineApplicable
+                    },
+                );
+            } else {
+                suggest_parens(&mut err);
             }
             err.emit();
         };