Skip to content

Commit

Permalink
Account for trailing closing angle brackets
Browse files Browse the repository at this point in the history
  • Loading branch information
estebank committed Jul 23, 2020
1 parent 20f4e5d commit d090e5e
Show file tree
Hide file tree
Showing 3 changed files with 75 additions and 23 deletions.
57 changes: 35 additions & 22 deletions src/librustc_parse/parser/diagnostics.rs
@@ -1,9 +1,9 @@
use super::ty::AllowPlus;
use super::{BlockMode, Parser, PathStyle, SemiColonMode, SeqSep, TokenExpectType, TokenType};

use rustc_ast::ast::{self, BinOpKind, BindingMode, BlockCheckMode, Expr, ExprKind, Item, Param};
use rustc_ast::ast::{
AngleBracketedArgs, AttrVec, ItemKind, Mutability, Pat, PatKind, PathSegment, QSelf, Ty, TyKind,
self, AngleBracketedArgs, AttrVec, BinOpKind, BindingMode, BlockCheckMode, Expr, ExprKind,
Item, ItemKind, Mutability, Param, Pat, PatKind, PathSegment, QSelf, Ty, TyKind,
};
use rustc_ast::ptr::P;
use rustc_ast::token::{self, Lit, LitKind, TokenKind};
Expand Down Expand Up @@ -498,29 +498,42 @@ impl<'a> Parser<'a> {
self.bump();
let lo = self.token.span;
match self.parse_angle_args() {
Ok(args) if self.token.kind == token::OpenDelim(token::Paren) => {
// Recover from bad turbofish: `foo.collect::Vec<_>()`.
Ok(args) => {
let span = lo.to(self.prev_token.span);
let args = AngleBracketedArgs { args, span }.into();
segment.args = args;
self.struct_span_err(
span,
"generic parameters without surrounding angle brackets",
)
.multipart_suggestion(
"surround the type parameters with angle brackets",
vec![
(span.shrink_to_lo(), "<".to_string()),
(span.shrink_to_hi(), ">".to_string()),
],
Applicability::MachineApplicable,
)
.emit();
}
Ok(_) => {
*self = snapshot;
// Detect trailing `>` like in `x.collect::Vec<_>>()`.
let mut trailing_span = self.prev_token.span.shrink_to_hi();
while self.token.kind == token::BinOp(token::Shr)
|| self.token.kind == token::Gt
{
trailing_span = trailing_span.to(self.token.span);
self.bump();
}
if self.token.kind == token::OpenDelim(token::Paren) {
// Recover from bad turbofish: `foo.collect::Vec<_>()`.
let args = AngleBracketedArgs { args, span }.into();
segment.args = args;

self.struct_span_err(
span,
"generic parameters without surrounding angle brackets",
)
.multipart_suggestion(
"surround the type parameters with angle brackets",
vec![
(span.shrink_to_lo(), "<".to_string()),
(trailing_span, ">".to_string()),
],
Applicability::MachineApplicable,
)
.emit();
} else {
// This doesn't look like an invalid turbofish, can't recover parse state.
*self = snapshot;
}
}
Err(mut err) => {
// We could't parse generic parameters, unlikely to be a turbofish. Rely on
// generic parse error instead.
err.cancel();
*self = snapshot;
}
Expand Down
@@ -1,4 +1,10 @@
fn main() {
let _ = vec![1, 2, 3].into_iter().collect::Vec<_>();
//~^ ERROR generic parameters without surrounding angle brackets
let _ = vec![1, 2, 3].into_iter().collect::Vec<_>>>>();
//~^ ERROR generic parameters without surrounding angle brackets
let _ = vec![1, 2, 3].into_iter().collect::Vec<_>>>();
//~^ ERROR generic parameters without surrounding angle brackets
let _ = vec![1, 2, 3].into_iter().collect::Vec<_>>();
//~^ ERROR generic parameters without surrounding angle brackets
}
Expand Up @@ -9,5 +9,38 @@ help: surround the type parameters with angle brackets
LL | let _ = vec![1, 2, 3].into_iter().collect::<Vec<_>>();
| ^ ^

error: aborting due to previous error
error: generic parameters without surrounding angle brackets
--> $DIR/recover-missing-turbofish-surrounding-angle-braket.rs:4:48
|
LL | let _ = vec![1, 2, 3].into_iter().collect::Vec<_>>>>();
| ^^^^^^
|
help: surround the type parameters with angle brackets
|
LL | let _ = vec![1, 2, 3].into_iter().collect::<Vec<_>>();
| ^ ^

error: generic parameters without surrounding angle brackets
--> $DIR/recover-missing-turbofish-surrounding-angle-braket.rs:6:48
|
LL | let _ = vec![1, 2, 3].into_iter().collect::Vec<_>>>();
| ^^^^^^
|
help: surround the type parameters with angle brackets
|
LL | let _ = vec![1, 2, 3].into_iter().collect::<Vec<_>>();
| ^ ^

error: generic parameters without surrounding angle brackets
--> $DIR/recover-missing-turbofish-surrounding-angle-braket.rs:8:48
|
LL | let _ = vec![1, 2, 3].into_iter().collect::Vec<_>>();
| ^^^^^^
|
help: surround the type parameters with angle brackets
|
LL | let _ = vec![1, 2, 3].into_iter().collect::<Vec<_>>();
| ^ ^

error: aborting due to 4 previous errors

0 comments on commit d090e5e

Please sign in to comment.