diff options
| author | yukang <moorekang@gmail.com> | 2022-11-25 17:11:47 +0800 |
|---|---|---|
| committer | yukang <moorekang@gmail.com> | 2022-11-25 17:13:45 +0800 |
| commit | 7c11a53f9ccb4040995b9e054b093a47fef29cc1 (patch) | |
| tree | 67c683a12e99f16e17bc221ffa87e01edd1c3d59 /compiler/rustc_parse | |
| parent | 1dda298ad39a64e019a3511139c5b13ac0a18e54 (diff) | |
| download | rust-7c11a53f9ccb4040995b9e054b093a47fef29cc1.tar.gz rust-7c11a53f9ccb4040995b9e054b093a47fef29cc1.zip | |
fix #104867, Properly handle postfix inc/dec in standalone and subexpr scenarios
Diffstat (limited to 'compiler/rustc_parse')
| -rw-r--r-- | compiler/rustc_parse/src/parser/diagnostics.rs | 57 | ||||
| -rw-r--r-- | compiler/rustc_parse/src/parser/expr.rs | 10 |
2 files changed, 25 insertions, 42 deletions
diff --git a/compiler/rustc_parse/src/parser/diagnostics.rs b/compiler/rustc_parse/src/parser/diagnostics.rs index 3f5baf343c9..eba0f22f37f 100644 --- a/compiler/rustc_parse/src/parser/diagnostics.rs +++ b/compiler/rustc_parse/src/parser/diagnostics.rs @@ -159,8 +159,6 @@ enum IsStandalone { Standalone, /// It's a subexpression, i.e., *not* standalone. Subexpr, - /// It's maybe standalone; we're not sure. - Maybe, } #[derive(Debug, Copy, Clone, PartialEq, Eq)] @@ -213,14 +211,8 @@ impl MultiSugg { err.multipart_suggestion(&self.msg, self.patches, self.applicability); } - /// Overrides individual messages and applicabilities. - fn emit_many( - err: &mut Diagnostic, - msg: &str, - applicability: Applicability, - suggestions: impl Iterator<Item = Self>, - ) { - err.multipart_suggestions(msg, suggestions.map(|s| s.patches), applicability); + fn emit_verbose(self, err: &mut Diagnostic) { + err.multipart_suggestion_verbose(&self.msg, self.patches, self.applicability); } } @@ -1272,7 +1264,6 @@ impl<'a> Parser<'a> { let standalone = if prev_is_semi { IsStandalone::Standalone } else { IsStandalone::Subexpr }; let kind = IncDecRecovery { standalone, op: IncOrDec::Inc, fixity: UnaryFixity::Pre }; - self.recover_from_inc_dec(operand_expr, kind, op_span) } @@ -1280,13 +1271,13 @@ impl<'a> Parser<'a> { &mut self, operand_expr: P<Expr>, op_span: Span, + prev_is_semi: bool, ) -> PResult<'a, P<Expr>> { let kind = IncDecRecovery { - standalone: IsStandalone::Maybe, + standalone: if prev_is_semi { IsStandalone::Standalone } else { IsStandalone::Subexpr }, op: IncOrDec::Inc, fixity: UnaryFixity::Post, }; - self.recover_from_inc_dec(operand_expr, kind, op_span) } @@ -1314,35 +1305,20 @@ impl<'a> Parser<'a> { UnaryFixity::Post => (base.span.shrink_to_lo(), op_span), }; + let Ok(base_src) = self.span_to_snippet(base.span) + else { return help_base_case(err, base) }; match kind.standalone { - IsStandalone::Standalone => self.inc_dec_standalone_suggest(kind, spans).emit(&mut err), - IsStandalone::Subexpr => { - let Ok(base_src) = self.span_to_snippet(base.span) - else { return help_base_case(err, base) }; - match kind.fixity { - UnaryFixity::Pre => { - self.prefix_inc_dec_suggest(base_src, kind, spans).emit(&mut err) - } - UnaryFixity::Post => { - self.postfix_inc_dec_suggest(base_src, kind, spans).emit(&mut err) - } - } - } - IsStandalone::Maybe => { - let Ok(base_src) = self.span_to_snippet(base.span) - else { return help_base_case(err, base) }; - let sugg1 = match kind.fixity { - UnaryFixity::Pre => self.prefix_inc_dec_suggest(base_src, kind, spans), - UnaryFixity::Post => self.postfix_inc_dec_suggest(base_src, kind, spans), - }; - let sugg2 = self.inc_dec_standalone_suggest(kind, spans); - MultiSugg::emit_many( - &mut err, - "use `+= 1` instead", - Applicability::Unspecified, - [sugg1, sugg2].into_iter(), - ) + IsStandalone::Standalone => { + self.inc_dec_standalone_suggest(kind, spans).emit_verbose(&mut err) } + IsStandalone::Subexpr => match kind.fixity { + UnaryFixity::Pre => { + self.prefix_inc_dec_suggest(base_src, kind, spans).emit(&mut err) + } + UnaryFixity::Post => { + self.postfix_inc_dec_suggest(base_src, kind, spans).emit(&mut err) + } + }, } Err(err) } @@ -1392,7 +1368,6 @@ impl<'a> Parser<'a> { } patches.push((post_span, format!(" {}= 1", kind.op.chr()))); - MultiSugg { msg: format!("use `{}= 1` instead", kind.op.chr()), patches, diff --git a/compiler/rustc_parse/src/parser/expr.rs b/compiler/rustc_parse/src/parser/expr.rs index 9f2267efb82..b98372d0f28 100644 --- a/compiler/rustc_parse/src/parser/expr.rs +++ b/compiler/rustc_parse/src/parser/expr.rs @@ -292,7 +292,15 @@ impl<'a> Parser<'a> { let op_span = self.prev_token.span.to(self.token.span); // Eat the second `+` self.bump(); - lhs = self.recover_from_postfix_increment(lhs, op_span)?; + let prev_is_semi = { + if let Ok(prev_code) = self.sess.source_map().span_to_prev_source(lhs.span) && + prev_code.trim_end().ends_with(";") { + true + } else { + false + } + }; + lhs = self.recover_from_postfix_increment(lhs, op_span, prev_is_semi)?; continue; } |
