diff options
| author | Esteban Küber <esteban@kuber.com.ar> | 2019-09-05 13:15:42 -0700 |
|---|---|---|
| committer | Esteban Küber <esteban@kuber.com.ar> | 2019-09-05 13:18:05 -0700 |
| commit | afcf9b262d450edd1a7d54754e62f62d50052d8d (patch) | |
| tree | d66b027530131e3ed57c65ecb073237ebd3a2d2e | |
| parent | dfd43f0fdd4e6969c7d82c0670d70bf305fbccf8 (diff) | |
| download | rust-afcf9b262d450edd1a7d54754e62f62d50052d8d.tar.gz rust-afcf9b262d450edd1a7d54754e62f62d50052d8d.zip | |
Bail out when encountering likely missing turbofish in parser
When encountering a likely intended turbofish without `::`, bubble up the diagnostic instead of emitting it to allow the parser to recover more gracefully and avoid uneccessary type errors that are likely to be wrong.
| -rw-r--r-- | src/libsyntax/parse/diagnostics.rs | 5 | ||||
| -rw-r--r-- | src/libsyntax/parse/parser/expr.rs | 2 | ||||
| -rw-r--r-- | src/test/ui/did_you_mean/issue-40396.rs | 11 | ||||
| -rw-r--r-- | src/test/ui/did_you_mean/issue-40396.stderr | 80 | ||||
| -rw-r--r-- | src/test/ui/parser/require-parens-for-chained-comparison.rs | 3 | ||||
| -rw-r--r-- | src/test/ui/parser/require-parens-for-chained-comparison.stderr | 15 | ||||
| -rw-r--r-- | src/test/ui/parser/trait-object-lifetime-parens.rs | 1 | ||||
| -rw-r--r-- | src/test/ui/parser/trait-object-lifetime-parens.stderr | 11 |
8 files changed, 12 insertions, 116 deletions
diff --git a/src/libsyntax/parse/diagnostics.rs b/src/libsyntax/parse/diagnostics.rs index d4e661d1a38..d050d4f4ce7 100644 --- a/src/libsyntax/parse/diagnostics.rs +++ b/src/libsyntax/parse/diagnostics.rs @@ -544,7 +544,7 @@ impl<'a> Parser<'a> { /// Produce an error if comparison operators are chained (RFC #558). /// We only need to check lhs, not rhs, because all comparison ops /// have same precedence and are left-associative - crate fn check_no_chained_comparison(&self, lhs: &Expr, outer_op: &AssocOp) { + crate fn check_no_chained_comparison(&self, lhs: &Expr, outer_op: &AssocOp) -> PResult<'a, ()> { debug_assert!(outer_op.is_comparison(), "check_no_chained_comparison: {:?} is not comparison", outer_op); @@ -563,11 +563,14 @@ impl<'a> Parser<'a> { err.help( "use `::<...>` instead of `<...>` if you meant to specify type arguments"); err.help("or use `(...)` if you meant to specify fn arguments"); + // These cases cause too many knock-down errors, bail out (#61329). + return Err(err); } err.emit(); } _ => {} } + Ok(()) } crate fn maybe_report_ambiguous_plus( diff --git a/src/libsyntax/parse/parser/expr.rs b/src/libsyntax/parse/parser/expr.rs index 5b9f0f1df67..aeef2161412 100644 --- a/src/libsyntax/parse/parser/expr.rs +++ b/src/libsyntax/parse/parser/expr.rs @@ -231,7 +231,7 @@ impl<'a> Parser<'a> { self.bump(); if op.is_comparison() { - self.check_no_chained_comparison(&lhs, &op); + self.check_no_chained_comparison(&lhs, &op)?; } // Special cases: if op == AssocOp::As { diff --git a/src/test/ui/did_you_mean/issue-40396.rs b/src/test/ui/did_you_mean/issue-40396.rs index 63eec50c2d2..6902779f33d 100644 --- a/src/test/ui/did_you_mean/issue-40396.rs +++ b/src/test/ui/did_you_mean/issue-40396.rs @@ -1,27 +1,16 @@ fn foo() { (0..13).collect<Vec<i32>>(); //~^ ERROR chained comparison - //~| ERROR expected value, found struct `Vec` - //~| ERROR expected value, found builtin type `i32` - //~| ERROR attempted to take value of method `collect` } fn bar() { Vec<i32>::new(); //~^ ERROR chained comparison - //~| ERROR expected value, found struct `Vec` - //~| ERROR expected value, found builtin type `i32` - //~| ERROR cannot find function `new` in the crate root } fn qux() { (0..13).collect<Vec<i32>(); //~^ ERROR chained comparison - //~| ERROR chained comparison - //~| ERROR expected value, found struct `Vec` - //~| ERROR expected value, found builtin type `i32` - //~| ERROR attempted to take value of method `collect` - //~| ERROR mismatched types } fn main() {} diff --git a/src/test/ui/did_you_mean/issue-40396.stderr b/src/test/ui/did_you_mean/issue-40396.stderr index fe517ee3494..7a08fda27e3 100644 --- a/src/test/ui/did_you_mean/issue-40396.stderr +++ b/src/test/ui/did_you_mean/issue-40396.stderr @@ -8,7 +8,7 @@ LL | (0..13).collect<Vec<i32>>(); = help: or use `(...)` if you meant to specify fn arguments error: chained comparison operators require parentheses - --> $DIR/issue-40396.rs:10:8 + --> $DIR/issue-40396.rs:7:8 | LL | Vec<i32>::new(); | ^^^^^^^ @@ -17,7 +17,7 @@ LL | Vec<i32>::new(); = help: or use `(...)` if you meant to specify fn arguments error: chained comparison operators require parentheses - --> $DIR/issue-40396.rs:18:20 + --> $DIR/issue-40396.rs:12:20 | LL | (0..13).collect<Vec<i32>(); | ^^^^^^^^ @@ -25,79 +25,5 @@ LL | (0..13).collect<Vec<i32>(); = help: use `::<...>` instead of `<...>` if you meant to specify type arguments = help: or use `(...)` if you meant to specify fn arguments -error: chained comparison operators require parentheses - --> $DIR/issue-40396.rs:18:24 - | -LL | (0..13).collect<Vec<i32>(); - | ^^^^^^ - | - = help: use `::<...>` instead of `<...>` if you meant to specify type arguments - = help: or use `(...)` if you meant to specify fn arguments - -error[E0423]: expected value, found struct `Vec` - --> $DIR/issue-40396.rs:2:21 - | -LL | (0..13).collect<Vec<i32>>(); - | ^^^ did you mean `Vec { /* fields */ }`? - -error[E0423]: expected value, found builtin type `i32` - --> $DIR/issue-40396.rs:2:25 - | -LL | (0..13).collect<Vec<i32>>(); - | ^^^ not a value - -error[E0423]: expected value, found struct `Vec` - --> $DIR/issue-40396.rs:10:5 - | -LL | Vec<i32>::new(); - | ^^^ did you mean `Vec { /* fields */ }`? - -error[E0423]: expected value, found builtin type `i32` - --> $DIR/issue-40396.rs:10:9 - | -LL | Vec<i32>::new(); - | ^^^ not a value - -error[E0425]: cannot find function `new` in the crate root - --> $DIR/issue-40396.rs:10:15 - | -LL | Vec<i32>::new(); - | ^^^ not found in the crate root - -error[E0423]: expected value, found struct `Vec` - --> $DIR/issue-40396.rs:18:21 - | -LL | (0..13).collect<Vec<i32>(); - | ^^^ did you mean `Vec { /* fields */ }`? - -error[E0423]: expected value, found builtin type `i32` - --> $DIR/issue-40396.rs:18:25 - | -LL | (0..13).collect<Vec<i32>(); - | ^^^ not a value - -error[E0615]: attempted to take value of method `collect` on type `std::ops::Range<{integer}>` - --> $DIR/issue-40396.rs:2:13 - | -LL | (0..13).collect<Vec<i32>>(); - | ^^^^^^^ help: use parentheses to call the method: `collect()` - -error[E0615]: attempted to take value of method `collect` on type `std::ops::Range<{integer}>` - --> $DIR/issue-40396.rs:18:13 - | -LL | (0..13).collect<Vec<i32>(); - | ^^^^^^^ help: use parentheses to call the method: `collect()` - -error[E0308]: mismatched types - --> $DIR/issue-40396.rs:18:29 - | -LL | (0..13).collect<Vec<i32>(); - | ^^ expected bool, found () - | - = note: expected type `bool` - found type `()` - -error: aborting due to 14 previous errors +error: aborting due to 3 previous errors -Some errors have detailed explanations: E0308, E0423, E0425, E0615. -For more information about an error, try `rustc --explain E0308`. diff --git a/src/test/ui/parser/require-parens-for-chained-comparison.rs b/src/test/ui/parser/require-parens-for-chained-comparison.rs index 525be5d20e2..3dcc0c8f3d4 100644 --- a/src/test/ui/parser/require-parens-for-chained-comparison.rs +++ b/src/test/ui/parser/require-parens-for-chained-comparison.rs @@ -11,8 +11,7 @@ fn main() { //~| ERROR: mismatched types f<X>(); - //~^ ERROR: chained comparison operators require parentheses - //~| ERROR: binary operation `<` cannot be applied to type `fn() {f::<_>}` + //~^ ERROR chained comparison operators require parentheses //~| HELP: use `::<...>` instead of `<...>` //~| HELP: or use `(...)` } diff --git a/src/test/ui/parser/require-parens-for-chained-comparison.stderr b/src/test/ui/parser/require-parens-for-chained-comparison.stderr index 76e548de045..e927f4c3248 100644 --- a/src/test/ui/parser/require-parens-for-chained-comparison.stderr +++ b/src/test/ui/parser/require-parens-for-chained-comparison.stderr @@ -37,17 +37,6 @@ LL | false == 0 < 2; = note: expected type `bool` found type `{integer}` -error[E0369]: binary operation `<` cannot be applied to type `fn() {f::<_>}` - --> $DIR/require-parens-for-chained-comparison.rs:13:6 - | -LL | f<X>(); - | -^- X - | | - | fn() {f::<_>} - | - = note: an implementation of `std::cmp::PartialOrd` might be missing for `fn() {f::<_>}` - -error: aborting due to 6 previous errors +error: aborting due to 5 previous errors -Some errors have detailed explanations: E0308, E0369. -For more information about an error, try `rustc --explain E0308`. +For more information about this error, try `rustc --explain E0308`. diff --git a/src/test/ui/parser/trait-object-lifetime-parens.rs b/src/test/ui/parser/trait-object-lifetime-parens.rs index 5bbda4296ca..c8b0eb684f3 100644 --- a/src/test/ui/parser/trait-object-lifetime-parens.rs +++ b/src/test/ui/parser/trait-object-lifetime-parens.rs @@ -9,7 +9,6 @@ fn check<'a>() { let _: Box<('a) + Trait>; //~^ ERROR expected type, found `'a` //~| ERROR expected `:`, found `)` - //~| ERROR chained comparison operators require parentheses } fn main() {} diff --git a/src/test/ui/parser/trait-object-lifetime-parens.stderr b/src/test/ui/parser/trait-object-lifetime-parens.stderr index 7ffc26e9ede..319a308c013 100644 --- a/src/test/ui/parser/trait-object-lifetime-parens.stderr +++ b/src/test/ui/parser/trait-object-lifetime-parens.stderr @@ -16,15 +16,6 @@ error: expected `:`, found `)` LL | let _: Box<('a) + Trait>; | ^ expected `:` -error: chained comparison operators require parentheses - --> $DIR/trait-object-lifetime-parens.rs:9:15 - | -LL | let _: Box<('a) + Trait>; - | ^^^^^^^^^^^^^^^ - | - = help: use `::<...>` instead of `<...>` if you meant to specify type arguments - = help: or use `(...)` if you meant to specify fn arguments - error: expected type, found `'a` --> $DIR/trait-object-lifetime-parens.rs:9:17 | @@ -33,5 +24,5 @@ LL | let _: Box<('a) + Trait>; | | | while parsing the type for `_` -error: aborting due to 5 previous errors +error: aborting due to 4 previous errors |
