Skip to content

Commit 66a4cb5

Browse files
authored
Rollup merge of #105223 - lukas-code:(ExprWithBlock), r=petrochenkov
suggest parenthesis around ExprWithBlock BinOp ExprWithBlock fix #105179 fix #102171
2 parents e84e8f4 + c808d0b commit 66a4cb5

File tree

5 files changed

+74
-16
lines changed

5 files changed

+74
-16
lines changed

compiler/rustc_hir_typeck/src/fn_ctxt/suggestions.rs

+3-1
Original file line numberDiff line numberDiff line change
@@ -32,11 +32,13 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
3232
}
3333

3434
pub(in super::super) fn suggest_semicolon_at_end(&self, span: Span, err: &mut Diagnostic) {
35+
// This suggestion is incorrect for
36+
// fn foo() -> bool { match () { () => true } || match () { () => true } }
3537
err.span_suggestion_short(
3638
span.shrink_to_hi(),
3739
"consider using a semicolon here",
3840
";",
39-
Applicability::MachineApplicable,
41+
Applicability::MaybeIncorrect,
4042
);
4143
}
4244

compiler/rustc_parse/src/parser/expr.rs

+5-14
Original file line numberDiff line numberDiff line change
@@ -390,20 +390,11 @@ impl<'a> Parser<'a> {
390390
// want to keep their span info to improve diagnostics in these cases in a later stage.
391391
(true, Some(AssocOp::Multiply)) | // `{ 42 } *foo = bar;` or `{ 42 } * 3`
392392
(true, Some(AssocOp::Subtract)) | // `{ 42 } -5`
393-
(true, Some(AssocOp::Add)) // `{ 42 } + 42
394-
// If the next token is a keyword, then the tokens above *are* unambiguously incorrect:
395-
// `if x { a } else { b } && if y { c } else { d }`
396-
if !self.look_ahead(1, |t| t.is_used_keyword()) => {
397-
// These cases are ambiguous and can't be identified in the parser alone.
398-
let sp = self.sess.source_map().start_point(self.token.span);
399-
self.sess.ambiguous_block_expr_parse.borrow_mut().insert(sp, lhs.span);
400-
false
401-
}
402-
(true, Some(AssocOp::LAnd)) |
403-
(true, Some(AssocOp::LOr)) |
404-
(true, Some(AssocOp::BitOr)) => {
405-
// `{ 42 } &&x` (#61475) or `{ 42 } && if x { 1 } else { 0 }`. Separated from the
406-
// above due to #74233.
393+
(true, Some(AssocOp::Add)) | // `{ 42 } + 42` (unary plus)
394+
(true, Some(AssocOp::LAnd)) | // `{ 42 } &&x` (#61475) or `{ 42 } && if x { 1 } else { 0 }`
395+
(true, Some(AssocOp::LOr)) | // `{ 42 } || 42` ("logical or" or closure)
396+
(true, Some(AssocOp::BitOr)) // `{ 42 } | 42` or `{ 42 } |x| 42`
397+
=> {
407398
// These cases are ambiguous and can't be identified in the parser alone.
408399
//
409400
// Bitwise AND is left out because guessing intent is hard. We can make

src/test/ui/parser/expr-as-stmt.fixed

+12
Original file line numberDiff line numberDiff line change
@@ -64,4 +64,16 @@ fn asteroids() -> impl FnOnce() -> bool {
6464
{ foo(); } || { true } //~ ERROR E0308
6565
}
6666

67+
// https://github.com/rust-lang/rust/issues/105179
68+
fn r#match() -> i32 {
69+
(match () { () => 1 }) + match () { () => 1 } //~ ERROR expected expression, found `+`
70+
//~^ ERROR mismatched types
71+
}
72+
73+
// https://github.com/rust-lang/rust/issues/102171
74+
fn r#unsafe() -> i32 {
75+
(unsafe { 1 }) + unsafe { 1 } //~ ERROR expected expression, found `+`
76+
//~^ ERROR mismatched types
77+
}
78+
6779
fn main() {}

src/test/ui/parser/expr-as-stmt.rs

+12
Original file line numberDiff line numberDiff line change
@@ -64,4 +64,16 @@ fn asteroids() -> impl FnOnce() -> bool {
6464
{ foo() } || { true } //~ ERROR E0308
6565
}
6666

67+
// https://github.com/rust-lang/rust/issues/105179
68+
fn r#match() -> i32 {
69+
match () { () => 1 } + match () { () => 1 } //~ ERROR expected expression, found `+`
70+
//~^ ERROR mismatched types
71+
}
72+
73+
// https://github.com/rust-lang/rust/issues/102171
74+
fn r#unsafe() -> i32 {
75+
unsafe { 1 } + unsafe { 1 } //~ ERROR expected expression, found `+`
76+
//~^ ERROR mismatched types
77+
}
78+
6779
fn main() {}

src/test/ui/parser/expr-as-stmt.stderr

+42-1
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,28 @@ help: parentheses are required to parse this as an expression
5555
LL | ({ true }) | { true }
5656
| + +
5757

58+
error: expected expression, found `+`
59+
--> $DIR/expr-as-stmt.rs:69:26
60+
|
61+
LL | match () { () => 1 } + match () { () => 1 }
62+
| ^ expected expression
63+
|
64+
help: parentheses are required to parse this as an expression
65+
|
66+
LL | (match () { () => 1 }) + match () { () => 1 }
67+
| + +
68+
69+
error: expected expression, found `+`
70+
--> $DIR/expr-as-stmt.rs:75:18
71+
|
72+
LL | unsafe { 1 } + unsafe { 1 }
73+
| ^ expected expression
74+
|
75+
help: parentheses are required to parse this as an expression
76+
|
77+
LL | (unsafe { 1 }) + unsafe { 1 }
78+
| + +
79+
5880
error[E0308]: mismatched types
5981
--> $DIR/expr-as-stmt.rs:64:7
6082
|
@@ -201,7 +223,26 @@ help: parentheses are required to parse this as an expression
201223
LL | ({ true }) || { true }
202224
| + +
203225

204-
error: aborting due to 18 previous errors
226+
error[E0308]: mismatched types
227+
--> $DIR/expr-as-stmt.rs:69:5
228+
|
229+
LL | match () { () => 1 } + match () { () => 1 }
230+
| ^^^^^^^^^^^^^^^^^^^^- help: consider using a semicolon here
231+
| |
232+
| expected `()`, found integer
233+
234+
error[E0308]: mismatched types
235+
--> $DIR/expr-as-stmt.rs:75:14
236+
|
237+
LL | unsafe { 1 } + unsafe { 1 }
238+
| ^ expected `()`, found integer
239+
|
240+
help: you might have meant to return this value
241+
|
242+
LL | unsafe { return 1; } + unsafe { 1 }
243+
| ++++++ +
244+
245+
error: aborting due to 22 previous errors
205246

206247
Some errors have detailed explanations: E0308, E0600, E0614.
207248
For more information about an error, try `rustc --explain E0308`.

0 commit comments

Comments
 (0)