Skip to content

Commit

Permalink
trait-object-lifetime-parens: improve recovery.
Browse files Browse the repository at this point in the history
  • Loading branch information
Centril committed Mar 10, 2020
1 parent d1822b3 commit ba3ae46
Show file tree
Hide file tree
Showing 5 changed files with 40 additions and 33 deletions.
17 changes: 11 additions & 6 deletions src/librustc_parse/parser/ty.rs
Original file line number Diff line number Diff line change
Expand Up @@ -148,18 +148,14 @@ impl<'a> Parser<'a> {
self.parse_impl_ty(&mut impl_dyn_multi)?
} else if self.is_explicit_dyn_type() {
self.parse_dyn_ty(&mut impl_dyn_multi)?
} else if self.check(&token::Question)
|| self.check_lifetime() && self.look_ahead(1, |t| t.is_like_plus())
{
// Bound list (trait object type)
let bounds = self.parse_generic_bounds_common(allow_plus, None)?;
TyKind::TraitObject(bounds, TraitObjectSyntax::None)
} else if self.eat_lt() {
// Qualified path
let (qself, path) = self.parse_qpath(PathStyle::Type)?;
TyKind::Path(Some(qself), path)
} else if self.check_path() {
self.parse_path_start_ty(lo, allow_plus)?
} else if self.can_begin_bound() {
self.parse_bare_trait_object(lo, allow_plus)?
} else if self.eat(&token::DotDotDot) {
if allow_c_variadic == AllowCVariadic::Yes {
TyKind::CVarArgs
Expand Down Expand Up @@ -218,6 +214,15 @@ impl<'a> Parser<'a> {
}
}

fn parse_bare_trait_object(&mut self, lo: Span, allow_plus: AllowPlus) -> PResult<'a, TyKind> {
let lt_no_plus = self.check_lifetime() && !self.look_ahead(1, |t| t.is_like_plus());
let bounds = self.parse_generic_bounds_common(allow_plus, None)?;
if lt_no_plus {
self.struct_span_err(lo, "lifetime in trait object type must be followed by `+`").emit()
}
Ok(TyKind::TraitObject(bounds, TraitObjectSyntax::None))
}

fn parse_remaining_bounds_path(
&mut self,
generic_params: Vec<GenericParam>,
Expand Down
9 changes: 7 additions & 2 deletions src/test/ui/parser/macro/trait-object-macro-matcher.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,14 @@
// `ty` matcher in particular doesn't accept a single lifetime

macro_rules! m {
($t: ty) => ( let _: $t; )
($t: ty) => {
let _: $t;
};
}

fn main() {
m!('static); //~ ERROR expected type, found `'static`
m!('static);
//~^ ERROR lifetime in trait object type must be followed by `+`
//~| ERROR at least one trait is required for an object type
//~| WARN trait objects without an explicit `dyn` are deprecated
}
22 changes: 18 additions & 4 deletions src/test/ui/parser/macro/trait-object-macro-matcher.stderr
Original file line number Diff line number Diff line change
@@ -1,8 +1,22 @@
error: expected type, found `'static`
--> $DIR/trait-object-macro-matcher.rs:9:8
error: lifetime in trait object type must be followed by `+`
--> $DIR/trait-object-macro-matcher.rs:11:8
|
LL | m!('static);
| ^^^^^^^ expected type
| ^^^^^^^

error: aborting due to previous error
warning: trait objects without an explicit `dyn` are deprecated
--> $DIR/trait-object-macro-matcher.rs:11:8
|
LL | m!('static);
| ^^^^^^^ help: use `dyn`: `dyn 'static`
|
= note: `#[warn(bare_trait_objects)]` on by default

error[E0224]: at least one trait is required for an object type
--> $DIR/trait-object-macro-matcher.rs:11:8
|
LL | m!('static);
| ^^^^^^^

error: aborting due to 2 previous errors

5 changes: 1 addition & 4 deletions src/test/ui/parser/trait-object-lifetime-parens.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,7 @@ fn f<'a, T: Trait + ('a)>() {} //~ ERROR parenthesized lifetime bounds are not s

fn check<'a>() {
let _: Box<Trait + ('a)>; //~ ERROR parenthesized lifetime bounds are not supported
let _: Box<('a) + Trait>;
//~^ ERROR expected type, found `'a`
//~| ERROR expected `while`, `for`, `loop` or `{` after a label
//~| ERROR expected expression, found `)`
let _: Box<('a) + Trait>; //~ ERROR lifetime in trait object type must be followed by `+`
}

fn main() {}
20 changes: 3 additions & 17 deletions src/test/ui/parser/trait-object-lifetime-parens.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -10,25 +10,11 @@ error: parenthesized lifetime bounds are not supported
LL | let _: Box<Trait + ('a)>;
| ^^^^ help: remove the parentheses

error: expected `while`, `for`, `loop` or `{` after a label
--> $DIR/trait-object-lifetime-parens.rs:9:19
|
LL | let _: Box<('a) + Trait>;
| ^ expected `while`, `for`, `loop` or `{` after a label

error: expected expression, found `)`
--> $DIR/trait-object-lifetime-parens.rs:9:19
|
LL | let _: Box<('a) + Trait>;
| ^ expected expression

error: expected type, found `'a`
error: lifetime in trait object type must be followed by `+`
--> $DIR/trait-object-lifetime-parens.rs:9:17
|
LL | let _: Box<('a) + Trait>;
| - ^^ expected type
| |
| while parsing the type for `_`
| ^^

error: aborting due to 5 previous errors
error: aborting due to 3 previous errors

0 comments on commit ba3ae46

Please sign in to comment.