Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Failure to parse {2} + {2} #54482

Open
blaztinn opened this issue Sep 22, 2018 · 7 comments
Open

Failure to parse {2} + {2} #54482

blaztinn opened this issue Sep 22, 2018 · 7 comments
Labels
A-grammar Area: The grammar of Rust A-parser Area: The parsing of Rust source code to an AST C-discussion Category: Discussion or questions that doesn't represent real issues. T-lang Relevant to the language team, which will review and decide on the PR/issue.

Comments

@blaztinn
Copy link

These examples should compile according to the rust reference:

fn compiles() -> i32 {
    ({2}) + ({2})
}

fn fails() -> i32 {
    {2} + {2}
}

fn compiles2() -> i32 {
    2 + {2}
}

fn fails2() -> i32 {
    {2} + 2
}

(Playground)

Errors:

   Compiling playground v0.0.1 (file:///playground)
error: expected expression, found `+`
 --> src/lib.rs:6:9
  |
6 |     {2} + {2}
  |         ^ expected expression

error: expected expression, found `+`
  --> src/lib.rs:14:9
   |
14 |     {2} + 2
   |         ^ expected expression

error: aborting due to 2 previous errors

error: Could not compile `playground`.

To learn more, run the command again with --verbose.

Rust reference snippet (thanks @Moongoodboy-K for the help here):

Expression : BlockExpression | OperatorExpression | ..
OperatorExpression : ArithmeticOrLogicalExpression | ..
ArithmeticOrLogicalExpression : Expression + Expression | ..
BlockExpression : { InnerAttribute* Statement* Expression? }

cc: @Moongoodboy-K

@zackmdavis zackmdavis added the A-parser Area: The parsing of Rust source code to an AST label Sep 22, 2018
@Centril Centril added the C-bug Category: This is a bug. label Sep 22, 2018
@nagisa
Copy link
Member

nagisa commented Sep 22, 2018

Note: this is not a regression, these fail to parse all the way back to 1.0. I think this is a duplicate of #7909, but since we are now fairly accepting of look-ahead, this seems fairly valid.

@estebank
Copy link
Contributor

but since we are now fairly accepting of look-ahead,

I believe that conversation is still ongoing, we'll probably have to go the RFCS route for that...

@scottmcm
Copy link
Member

I'm not certain this is actually a bug; it might be worse for + and - to have difference parser behaviour here.

@Havvy
Copy link
Contributor

Havvy commented Sep 23, 2018

This isn't a bug. It falls out of block expression statements terminating at the }.

@Havvy
Copy link
Contributor

Havvy commented Sep 23, 2018

The relevant section of the reference:

An expression statement is one that evaluates an expression and ignores its result. As a rule, an expression statement's purpose is to trigger the effects of evaluating its expression.

An expression that consists of only a block expression or control flow expression, if used in a context where a statement is permitted, can omit the trailing semicolon. This can cause an ambiguity between it being parsed as a standalone statement and as a part of another expression; in this case, it is parsed as a statement.

v.pop();          // Ignore the element returned from pop
if v.is_empty() {
    v.push(5);
} else {
    v.remove(0);
}                 // Semicolon can be omitted.
[1];              // Separate expression statement, not an indexing expression.

While we could theoretically make { {2} + {2} } work since { + {2} } is not a valid expression, the same cannot be true of other binary ops. Specifically -. { - {2}; } is valid.

That said, the error for this is terrible. Most likely you want to change your expression statement to be ({2} + {2}); in these cases. Is there a diagnostic issue open for that?

@Havvy Havvy added A-diagnostics Area: Messages for errors, warnings, and lints and removed C-bug Category: This is a bug. labels Sep 23, 2018
rinon pushed a commit to immunant/c2rust that referenced this issue Apr 8, 2019
@estebank estebank added A-grammar Area: The grammar of Rust and removed A-diagnostics Area: Messages for errors, warnings, and lints labels May 2, 2019
Centril added a commit to Centril/rust that referenced this issue May 9, 2019
Identify when a stmt could have been parsed as an expr

There are some expressions that can be parsed as a statement without
a trailing semicolon depending on the context, which can lead to
confusing errors due to the same looking code being accepted in some
places and not others. Identify these cases and suggest enclosing in
parenthesis making the parse non-ambiguous without changing the
accepted grammar.

Fix rust-lang#54186, cc rust-lang#54482, fix rust-lang#59975, fix rust-lang#47287.
@estebank
Copy link
Contributor

The current output for this is:

error: expected expression, found `+`
 --> src/lib.rs:6:9
  |
6 |     {2} + {2}
  |     --- ^ expected expression
  |     |
  |     help: parentheses are required to parse this as an expression: `({2})`

error: expected expression, found `+`
  --> src/lib.rs:14:9
   |
14 |     {2} + 2
   |     --- ^ expected expression
   |     |
   |     help: parentheses are required to parse this as an expression: `({2})`

error[E0308]: mismatched types
 --> src/lib.rs:6:6
  |
6 |     {2} + {2}
  |      ^ expected (), found integer
  |
  = note: expected type `()`
             found type `{integer}`

error[E0308]: mismatched types
  --> src/lib.rs:14:6
   |
14 |     {2} + 2
   |      ^ expected (), found integer
   |
   = note: expected type `()`
              found type `{integer}`

error: aborting due to 4 previous errors

@Spoonbender
Copy link

Triage: no change

@fmease fmease added T-lang Relevant to the language team, which will review and decide on the PR/issue. C-discussion Category: Discussion or questions that doesn't represent real issues. labels May 15, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-grammar Area: The grammar of Rust A-parser Area: The parsing of Rust source code to an AST C-discussion Category: Discussion or questions that doesn't represent real issues. T-lang Relevant to the language team, which will review and decide on the PR/issue.
Projects
None yet
Development

No branches or pull requests

9 participants