about summary refs log tree commit diff
diff options
context:
space:
mode:
authorEsteban Küber <esteban@kuber.com.ar>2019-04-14 17:09:03 -0700
committerEsteban Küber <esteban@kuber.com.ar>2019-04-19 10:13:44 -0700
commit2f36b54f0f33427e926872935c325a660967af6f (patch)
tree1ed541f3fee0898fef1b7676da1c248effc29f88
parenta2bbf7debaab60be33bd8008a71bca69576945a0 (diff)
downloadrust-2f36b54f0f33427e926872935c325a660967af6f.tar.gz
rust-2f36b54f0f33427e926872935c325a660967af6f.zip
Emit specific error for struct literal in conditions
-rw-r--r--src/librustc_borrowck/borrowck/mod.rs4
-rw-r--r--src/libsyntax/parse/parser.rs57
-rw-r--r--src/test/ui/error-codes/E0423.rs6
-rw-r--r--src/test/ui/error-codes/E0423.stderr54
-rw-r--r--src/test/ui/parser/struct-literal-in-for.rs6
-rw-r--r--src/test/ui/parser/struct-literal-in-for.stderr41
-rw-r--r--src/test/ui/parser/struct-literal-in-if.rs6
-rw-r--r--src/test/ui/parser/struct-literal-in-if.stderr34
-rw-r--r--src/test/ui/parser/struct-literal-in-match-discriminant.rs10
-rw-r--r--src/test/ui/parser/struct-literal-in-match-discriminant.stderr48
-rw-r--r--src/test/ui/parser/struct-literal-in-while.rs7
-rw-r--r--src/test/ui/parser/struct-literal-in-while.stderr41
-rw-r--r--src/test/ui/parser/struct-literal-restrictions-in-lamda.rs7
-rw-r--r--src/test/ui/parser/struct-literal-restrictions-in-lamda.stderr48
14 files changed, 162 insertions, 207 deletions
diff --git a/src/librustc_borrowck/borrowck/mod.rs b/src/librustc_borrowck/borrowck/mod.rs
index fe39e3ae0c6..a2f6d9713f0 100644
--- a/src/librustc_borrowck/borrowck/mod.rs
+++ b/src/librustc_borrowck/borrowck/mod.rs
@@ -897,8 +897,7 @@ impl<'a, 'tcx> BorrowckCtxt<'a, 'tcx> {
                         self.cannot_borrow_path_as_mutable(error_span, &descr, Origin::Ast)
                     }
                     BorrowViolation(euv::ClosureInvocation) => {
-                        span_bug!(err.span,
-                            "err_mutbl with a closure invocation");
+                        span_bug!(err.span, "err_mutbl with a closure invocation");
                     }
                 };
 
@@ -1096,7 +1095,6 @@ impl<'a, 'tcx> BorrowckCtxt<'a, 'tcx> {
             BorrowViolation(euv::MatchDiscriminant) => {
                 "cannot borrow data mutably"
             }
-
             BorrowViolation(euv::ClosureInvocation) => {
                 is_closure = true;
                 "closure invocation"
diff --git a/src/libsyntax/parse/parser.rs b/src/libsyntax/parse/parser.rs
index a5adb37f745..7d130470c6a 100644
--- a/src/libsyntax/parse/parser.rs
+++ b/src/libsyntax/parse/parser.rs
@@ -2855,11 +2855,13 @@ impl<'a> Parser<'a> {
                         let (delim, tts) = self.expect_delimited_token_tree()?;
                         hi = self.prev_span;
                         ex = ExprKind::Mac(respan(lo.to(hi), Mac_ { path, tts, delim }));
-                    } else if self.check(&token::OpenDelim(token::Brace)) &&
-                              !self.restrictions.contains(Restrictions::NO_STRUCT_LITERAL) {
-                        // This is a struct literal, unless we're prohibited
-                        // from parsing struct literals here.
-                        return self.parse_struct_expr(lo, path, attrs);
+                    } else if self.check(&token::OpenDelim(token::Brace)) {
+                        if let Some(expr) = self.should_parse_struct_expr(lo, path.clone(), attrs.clone()) {
+                            return expr;
+                        } else {
+                            hi = path.span;
+                            ex = ExprKind::Path(None, path);
+                        }
                     } else {
                         hi = path.span;
                         ex = ExprKind::Path(None, path);
@@ -2902,6 +2904,51 @@ impl<'a> Parser<'a> {
         self.maybe_recover_from_bad_qpath(expr, true)
     }
 
+    fn should_parse_struct_expr(
+        &mut self,
+        lo: Span,
+        path: ast::Path,
+        attrs: ThinVec<Attribute>,
+    ) -> Option<PResult<'a, P<Expr>>> {
+        let could_be_struct = self.look_ahead(1, |t| t.is_ident()) && (
+            self.look_ahead(2, |t| *t == token::Colon)
+            || self.look_ahead(2, |t| *t == token::Comma)
+            // We could also check for `token::CloseDelim(token::Brace)`, but that would
+            // have false positives in the case of `if x == y { z } { a }`.
+        );
+        let mut bad_struct = false;
+        let mut parse_struct = !self.restrictions.contains(Restrictions::NO_STRUCT_LITERAL);
+        if self.restrictions.contains(Restrictions::NO_STRUCT_LITERAL) && could_be_struct {
+            // This is a struct literal, but we don't can't accept them here
+            bad_struct = true;
+            parse_struct = true;
+        }
+        if parse_struct {
+            match self.parse_struct_expr(lo, path, attrs) {
+                Err(err) => return Some(Err(err)),
+                Ok(expr) => {
+                    if bad_struct {
+                        let mut err = self.diagnostic().struct_span_err(
+                            expr.span,
+                            "struct literals are not allowed here",
+                        );
+                        err.multipart_suggestion(
+                            "surround the struct literal with parenthesis",
+                            vec![
+                                (lo.shrink_to_lo(), "(".to_string()),
+                                (expr.span.shrink_to_hi(), ")".to_string()),
+                            ],
+                            Applicability::MachineApplicable,
+                        );
+                        err.emit();
+                    }
+                    return Some(Ok(expr));
+                }
+            }
+        }
+        None
+    }
+
     fn parse_struct_expr(&mut self, lo: Span, pth: ast::Path, mut attrs: ThinVec<Attribute>)
                          -> PResult<'a, P<Expr>> {
         let struct_sp = lo.to(self.prev_span);
diff --git a/src/test/ui/error-codes/E0423.rs b/src/test/ui/error-codes/E0423.rs
index 2b26808d4bd..5080a5e0599 100644
--- a/src/test/ui/error-codes/E0423.rs
+++ b/src/test/ui/error-codes/E0423.rs
@@ -10,8 +10,7 @@ fn bar() {
     struct T {}
 
     if let S { x: _x, y: 2 } = S { x: 1, y: 2 } { println!("Ok"); }
-    //~^ ERROR E0423
-    //~|  expected type, found `1`
+    //~^ ERROR struct literals are not allowed here
     if T {} == T {} { println!("Ok"); }
     //~^ ERROR E0423
     //~| ERROR expected expression, found `==`
@@ -19,6 +18,5 @@ fn bar() {
 
 fn foo() {
     for _ in std::ops::Range { start: 0, end: 10 } {}
-    //~^ ERROR E0423
-    //~| ERROR expected type, found `0`
+    //~^ ERROR struct literals are not allowed here
 }
diff --git a/src/test/ui/error-codes/E0423.stderr b/src/test/ui/error-codes/E0423.stderr
index b0ef4e1b254..5cb7121a0d1 100644
--- a/src/test/ui/error-codes/E0423.stderr
+++ b/src/test/ui/error-codes/E0423.stderr
@@ -1,36 +1,28 @@
-error: expected type, found `1`
-  --> $DIR/E0423.rs:12:39
+error: struct literals are not allowed here
+  --> $DIR/E0423.rs:12:32
    |
 LL |     if let S { x: _x, y: 2 } = S { x: 1, y: 2 } { println!("Ok"); }
-   |                                       ^ expecting a type here because of type ascription
-   |
-   = note: type ascription is a nightly-only feature that lets you annotate an expression with a type: `<expr>: <type>`
-note: this expression expects an ascribed type after the colon
-  --> $DIR/E0423.rs:12:36
+   |                                ^^^^^^^^^^^^^^^^
+help: surround the struct literal with parenthesis
    |
-LL |     if let S { x: _x, y: 2 } = S { x: 1, y: 2 } { println!("Ok"); }
-   |                                    ^
-   = help: this might be indicative of a syntax error elsewhere
+LL |     if let S { x: _x, y: 2 } = (S { x: 1, y: 2 }) { println!("Ok"); }
+   |                                ^                ^
 
 error: expected expression, found `==`
-  --> $DIR/E0423.rs:15:13
+  --> $DIR/E0423.rs:14:13
    |
 LL |     if T {} == T {} { println!("Ok"); }
    |             ^^ expected expression
 
-error: expected type, found `0`
-  --> $DIR/E0423.rs:21:39
+error: struct literals are not allowed here
+  --> $DIR/E0423.rs:20:14
    |
 LL |     for _ in std::ops::Range { start: 0, end: 10 } {}
-   |                                       ^ expecting a type here because of type ascription
+   |              ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+help: surround the struct literal with parenthesis
    |
-   = note: type ascription is a nightly-only feature that lets you annotate an expression with a type: `<expr>: <type>`
-note: this expression expects an ascribed type after the colon
-  --> $DIR/E0423.rs:21:32
-   |
-LL |     for _ in std::ops::Range { start: 0, end: 10 } {}
-   |                                ^^^^^
-   = help: this might be indicative of a syntax error elsewhere
+LL |     for _ in (std::ops::Range { start: 0, end: 10 }) {}
+   |              ^                                     ^
 
 error[E0423]: expected function, found struct `Foo`
   --> $DIR/E0423.rs:4:13
@@ -41,30 +33,14 @@ LL |     let f = Foo();
    |             did you mean `Foo { /* fields */ }`?
    |             help: a function with a similar name exists: `foo`
 
-error[E0423]: expected value, found struct `S`
-  --> $DIR/E0423.rs:12:32
-   |
-LL |     if let S { x: _x, y: 2 } = S { x: 1, y: 2 } { println!("Ok"); }
-   |                                ^---------------
-   |                                |
-   |                                help: surround the struct literal with parenthesis: `(S { x: 1, y: 2 })`
-
 error[E0423]: expected value, found struct `T`
-  --> $DIR/E0423.rs:15:8
+  --> $DIR/E0423.rs:14:8
    |
 LL |     if T {} == T {} { println!("Ok"); }
    |        ^---
    |        |
    |        help: surround the struct literal with parenthesis: `(T {})`
 
-error[E0423]: expected value, found struct `std::ops::Range`
-  --> $DIR/E0423.rs:21:14
-   |
-LL |     for _ in std::ops::Range { start: 0, end: 10 } {}
-   |              ^^^^^^^^^^^^^^^----------------------
-   |              |
-   |              help: surround the struct literal with parenthesis: `(std::ops::Range { start: 0, end: 10 })`
-
-error: aborting due to 7 previous errors
+error: aborting due to 5 previous errors
 
 For more information about this error, try `rustc --explain E0423`.
diff --git a/src/test/ui/parser/struct-literal-in-for.rs b/src/test/ui/parser/struct-literal-in-for.rs
index 526b5e75c45..3227ae37bfd 100644
--- a/src/test/ui/parser/struct-literal-in-for.rs
+++ b/src/test/ui/parser/struct-literal-in-for.rs
@@ -9,9 +9,9 @@ impl Foo {
 }
 
 fn main() {
-    for x in Foo { //~ ERROR expected value, found struct `Foo`
-        x: 3    //~ ERROR expected type, found `3`
-    }.hi() { //~ ERROR expected one of `.`, `;`, `?`, `}`, or an operator, found `{`
+    for x in Foo { //~ ERROR struct literals are not allowed here
+        x: 3       //~^ ERROR `bool` is not an iterator
+    }.hi() {
         println!("yo");
     }
 }
diff --git a/src/test/ui/parser/struct-literal-in-for.stderr b/src/test/ui/parser/struct-literal-in-for.stderr
index 07f2e41ac4f..3c3f6e7f032 100644
--- a/src/test/ui/parser/struct-literal-in-for.stderr
+++ b/src/test/ui/parser/struct-literal-in-for.stderr
@@ -1,29 +1,30 @@
-error: expected type, found `3`
-  --> $DIR/struct-literal-in-for.rs:13:12
-   |
-LL |         x: 3
-   |            ^ expecting a type here because of type ascription
+error: struct literals are not allowed here
+  --> $DIR/struct-literal-in-for.rs:12:14
    |
-   = note: type ascription is a nightly-only feature that lets you annotate an expression with a type: `<expr>: <type>`
-note: this expression expects an ascribed type after the colon
-  --> $DIR/struct-literal-in-for.rs:13:9
+LL |       for x in Foo {
+   |  ______________^
+LL | |         x: 3
+LL | |     }.hi() {
+   | |_____^
+help: surround the struct literal with parenthesis
    |
+LL |     for x in (Foo {
 LL |         x: 3
-   |         ^
-   = help: this might be indicative of a syntax error elsewhere
-
-error: expected one of `.`, `;`, `?`, `}`, or an operator, found `{`
-  --> $DIR/struct-literal-in-for.rs:14:12
+LL |     }).hi() {
    |
-LL |     }.hi() {
-   |            ^ expected one of `.`, `;`, `?`, `}`, or an operator here
 
-error[E0423]: expected value, found struct `Foo`
+error[E0277]: `bool` is not an iterator
   --> $DIR/struct-literal-in-for.rs:12:14
    |
-LL |     for x in Foo {
-   |              ^^^ did you mean `(Foo { /* fields */ })`?
+LL |       for x in Foo {
+   |  ______________^
+LL | |         x: 3
+LL | |     }.hi() {
+   | |__________^ `bool` is not an iterator
+   |
+   = help: the trait `std::iter::Iterator` is not implemented for `bool`
+   = note: required by `std::iter::IntoIterator::into_iter`
 
-error: aborting due to 3 previous errors
+error: aborting due to 2 previous errors
 
-For more information about this error, try `rustc --explain E0423`.
+For more information about this error, try `rustc --explain E0277`.
diff --git a/src/test/ui/parser/struct-literal-in-if.rs b/src/test/ui/parser/struct-literal-in-if.rs
index 362a71c577f..2ce2c8f1899 100644
--- a/src/test/ui/parser/struct-literal-in-if.rs
+++ b/src/test/ui/parser/struct-literal-in-if.rs
@@ -9,9 +9,9 @@ impl Foo {
 }
 
 fn main() {
-    if Foo { //~ ERROR expected value, found struct `Foo`
-        x: 3    //~ ERROR expected type, found `3`
-    }.hi() { //~ ERROR expected one of `.`, `;`, `?`, `}`, or an operator, found `{`
+    if Foo { //~ ERROR struct literals are not allowed here
+        x: 3
+    }.hi() {
         println!("yo");
     }
 }
diff --git a/src/test/ui/parser/struct-literal-in-if.stderr b/src/test/ui/parser/struct-literal-in-if.stderr
index 3dd61e74f12..851c495abb4 100644
--- a/src/test/ui/parser/struct-literal-in-if.stderr
+++ b/src/test/ui/parser/struct-literal-in-if.stderr
@@ -1,29 +1,17 @@
-error: expected type, found `3`
-  --> $DIR/struct-literal-in-if.rs:13:12
-   |
-LL |         x: 3
-   |            ^ expecting a type here because of type ascription
+error: struct literals are not allowed here
+  --> $DIR/struct-literal-in-if.rs:12:8
    |
-   = note: type ascription is a nightly-only feature that lets you annotate an expression with a type: `<expr>: <type>`
-note: this expression expects an ascribed type after the colon
-  --> $DIR/struct-literal-in-if.rs:13:9
+LL |       if Foo {
+   |  ________^
+LL | |         x: 3
+LL | |     }.hi() {
+   | |_____^
+help: surround the struct literal with parenthesis
    |
+LL |     if (Foo {
 LL |         x: 3
-   |         ^
-   = help: this might be indicative of a syntax error elsewhere
-
-error: expected one of `.`, `;`, `?`, `}`, or an operator, found `{`
-  --> $DIR/struct-literal-in-if.rs:14:12
-   |
-LL |     }.hi() {
-   |            ^ expected one of `.`, `;`, `?`, `}`, or an operator here
-
-error[E0423]: expected value, found struct `Foo`
-  --> $DIR/struct-literal-in-if.rs:12:8
+LL |     }).hi() {
    |
-LL |     if Foo {
-   |        ^^^ did you mean `(Foo { /* fields */ })`?
 
-error: aborting due to 3 previous errors
+error: aborting due to previous error
 
-For more information about this error, try `rustc --explain E0423`.
diff --git a/src/test/ui/parser/struct-literal-in-match-discriminant.rs b/src/test/ui/parser/struct-literal-in-match-discriminant.rs
index 35a11090351..ce132df5a88 100644
--- a/src/test/ui/parser/struct-literal-in-match-discriminant.rs
+++ b/src/test/ui/parser/struct-literal-in-match-discriminant.rs
@@ -3,11 +3,11 @@ struct Foo {
 }
 
 fn main() {
-    match Foo { //~ ERROR expected value, found struct `Foo`
-        x: 3    //~ ERROR expected one of `=>`, `@`, `if`, or `|`, found `:`
+    match Foo { //~ ERROR struct literals are not allowed here
+        x: 3
     } {
-        Foo { //~ ERROR mismatched types
-            x: x //~ ERROR cannot find value `x` in this scope
-        } => {} //~ ERROR expected one of `.`, `;`, `?`, `}`, or an operator, found `=>`
+        Foo {
+            x: x
+        } => {}
     }
 }
diff --git a/src/test/ui/parser/struct-literal-in-match-discriminant.stderr b/src/test/ui/parser/struct-literal-in-match-discriminant.stderr
index d061591e510..b8818ccba39 100644
--- a/src/test/ui/parser/struct-literal-in-match-discriminant.stderr
+++ b/src/test/ui/parser/struct-literal-in-match-discriminant.stderr
@@ -1,42 +1,16 @@
-error: expected one of `=>`, `@`, `if`, or `|`, found `:`
-  --> $DIR/struct-literal-in-match-discriminant.rs:7:10
-   |
-LL |         x: 3
-   |          ^ expected one of `=>`, `@`, `if`, or `|` here
-
-error: expected one of `.`, `;`, `?`, `}`, or an operator, found `=>`
-  --> $DIR/struct-literal-in-match-discriminant.rs:11:11
-   |
-LL |         } => {}
-   |           ^^ expected one of `.`, `;`, `?`, `}`, or an operator here
-
-error[E0423]: expected value, found struct `Foo`
+error: struct literals are not allowed here
   --> $DIR/struct-literal-in-match-discriminant.rs:6:11
    |
-LL |     match Foo {
-   |           ^^^ did you mean `(Foo { /* fields */ })`?
-
-error[E0425]: cannot find value `x` in this scope
-  --> $DIR/struct-literal-in-match-discriminant.rs:10:16
-   |
-LL |             x: x
-   |                ^ not found in this scope
-
-error[E0308]: mismatched types
-  --> $DIR/struct-literal-in-match-discriminant.rs:9:9
+LL |       match Foo {
+   |  ___________^
+LL | |         x: 3
+LL | |     } {
+   | |_____^
+help: surround the struct literal with parenthesis
    |
-LL |   fn main() {
-   |             - expected `()` because of default return type
-...
-LL | /         Foo {
-LL | |             x: x
-LL | |         } => {}
-   | |_________^ expected (), found struct `Foo`
+LL |     match (Foo {
+LL |         x: 3
+LL |     }) {
    |
-   = note: expected type `()`
-              found type `Foo`
-
-error: aborting due to 5 previous errors
 
-Some errors have detailed explanations: E0308, E0423, E0425.
-For more information about an error, try `rustc --explain E0308`.
+error: aborting due to previous error
diff --git a/src/test/ui/parser/struct-literal-in-while.rs b/src/test/ui/parser/struct-literal-in-while.rs
index 561cdcea089..5000ce85b7f 100644
--- a/src/test/ui/parser/struct-literal-in-while.rs
+++ b/src/test/ui/parser/struct-literal-in-while.rs
@@ -9,10 +9,9 @@ impl Foo {
 }
 
 fn main() {
-    while Foo { //~ ERROR expected value, found struct `Foo`
-        x: 3    //~ ERROR expected type, found `3`
-    }.hi() { //~ ERROR expected one of `.`, `;`, `?`, `}`, or an operator, found `{`
-             //~| ERROR no method named `hi` found for type `()` in the current scope
+    while Foo { //~ ERROR struct literals are not allowed here
+        x: 3
+    }.hi() {
         println!("yo");
     }
 }
diff --git a/src/test/ui/parser/struct-literal-in-while.stderr b/src/test/ui/parser/struct-literal-in-while.stderr
index c07975331f8..9959a57be85 100644
--- a/src/test/ui/parser/struct-literal-in-while.stderr
+++ b/src/test/ui/parser/struct-literal-in-while.stderr
@@ -1,36 +1,17 @@
-error: expected type, found `3`
-  --> $DIR/struct-literal-in-while.rs:13:12
-   |
-LL |         x: 3
-   |            ^ expecting a type here because of type ascription
+error: struct literals are not allowed here
+  --> $DIR/struct-literal-in-while.rs:12:11
    |
-   = note: type ascription is a nightly-only feature that lets you annotate an expression with a type: `<expr>: <type>`
-note: this expression expects an ascribed type after the colon
-  --> $DIR/struct-literal-in-while.rs:13:9
+LL |       while Foo {
+   |  ___________^
+LL | |         x: 3
+LL | |     }.hi() {
+   | |_____^
+help: surround the struct literal with parenthesis
    |
+LL |     while (Foo {
 LL |         x: 3
-   |         ^
-   = help: this might be indicative of a syntax error elsewhere
-
-error: expected one of `.`, `;`, `?`, `}`, or an operator, found `{`
-  --> $DIR/struct-literal-in-while.rs:14:12
-   |
-LL |     }.hi() {
-   |            ^ expected one of `.`, `;`, `?`, `}`, or an operator here
-
-error[E0423]: expected value, found struct `Foo`
-  --> $DIR/struct-literal-in-while.rs:12:11
-   |
-LL |     while Foo {
-   |           ^^^ did you mean `(Foo { /* fields */ })`?
-
-error[E0599]: no method named `hi` found for type `()` in the current scope
-  --> $DIR/struct-literal-in-while.rs:14:7
+LL |     }).hi() {
    |
-LL |     }.hi() {
-   |       ^^
 
-error: aborting due to 4 previous errors
+error: aborting due to previous error
 
-Some errors have detailed explanations: E0423, E0599.
-For more information about an error, try `rustc --explain E0423`.
diff --git a/src/test/ui/parser/struct-literal-restrictions-in-lamda.rs b/src/test/ui/parser/struct-literal-restrictions-in-lamda.rs
index e5049082ab0..e185153dcf6 100644
--- a/src/test/ui/parser/struct-literal-restrictions-in-lamda.rs
+++ b/src/test/ui/parser/struct-literal-restrictions-in-lamda.rs
@@ -9,10 +9,9 @@ impl Foo {
 }
 
 fn main() {
-    while || Foo { //~ ERROR expected value, found struct `Foo`
-        x: 3    //~ ERROR expected type, found `3`
-    }.hi() { //~ ERROR expected one of `.`, `;`, `?`, `}`, or an operator, found `{`
-             //~| ERROR no method named `hi` found for type `()` in the current scope
+    while || Foo { //~ ERROR struct literals are not allowed here
+        x: 3       //~^ ERROR mismatched types
+    }.hi() {
         println!("yo");
     }
 }
diff --git a/src/test/ui/parser/struct-literal-restrictions-in-lamda.stderr b/src/test/ui/parser/struct-literal-restrictions-in-lamda.stderr
index 977875dd938..81f7a91ddb3 100644
--- a/src/test/ui/parser/struct-literal-restrictions-in-lamda.stderr
+++ b/src/test/ui/parser/struct-literal-restrictions-in-lamda.stderr
@@ -1,36 +1,30 @@
-error: expected type, found `3`
-  --> $DIR/struct-literal-restrictions-in-lamda.rs:13:12
-   |
-LL |         x: 3
-   |            ^ expecting a type here because of type ascription
+error: struct literals are not allowed here
+  --> $DIR/struct-literal-restrictions-in-lamda.rs:12:14
    |
-   = note: type ascription is a nightly-only feature that lets you annotate an expression with a type: `<expr>: <type>`
-note: this expression expects an ascribed type after the colon
-  --> $DIR/struct-literal-restrictions-in-lamda.rs:13:9
+LL |       while || Foo {
+   |  ______________^
+LL | |         x: 3
+LL | |     }.hi() {
+   | |_____^
+help: surround the struct literal with parenthesis
    |
+LL |     while || (Foo {
 LL |         x: 3
-   |         ^
-   = help: this might be indicative of a syntax error elsewhere
-
-error: expected one of `.`, `;`, `?`, `}`, or an operator, found `{`
-  --> $DIR/struct-literal-restrictions-in-lamda.rs:14:12
+LL |     }).hi() {
    |
-LL |     }.hi() {
-   |            ^ expected one of `.`, `;`, `?`, `}`, or an operator here
 
-error[E0423]: expected value, found struct `Foo`
-  --> $DIR/struct-literal-restrictions-in-lamda.rs:12:14
+error[E0308]: mismatched types
+  --> $DIR/struct-literal-restrictions-in-lamda.rs:12:11
    |
-LL |     while || Foo {
-   |              ^^^ did you mean `(Foo { /* fields */ })`?
-
-error[E0599]: no method named `hi` found for type `()` in the current scope
-  --> $DIR/struct-literal-restrictions-in-lamda.rs:14:7
+LL |       while || Foo {
+   |  ___________^
+LL | |         x: 3
+LL | |     }.hi() {
+   | |__________^ expected bool, found closure
    |
-LL |     }.hi() {
-   |       ^^
+   = note: expected type `bool`
+              found type `[closure@$DIR/struct-literal-restrictions-in-lamda.rs:12:11: 14:11]`
 
-error: aborting due to 4 previous errors
+error: aborting due to 2 previous errors
 
-Some errors have detailed explanations: E0423, E0599.
-For more information about an error, try `rustc --explain E0423`.
+For more information about this error, try `rustc --explain E0308`.