Provide specific label for patern parsing error
This commit is contained in:
parent
d491734b15
commit
adb96ec64b
11 changed files with 40 additions and 44 deletions
|
@ -1030,7 +1030,7 @@ impl<'a> Parser<'a> {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
AstFragmentKind::Ty => AstFragment::Ty(self.parse_ty()?),
|
AstFragmentKind::Ty => AstFragment::Ty(self.parse_ty()?),
|
||||||
AstFragmentKind::Pat => AstFragment::Pat(self.parse_pat()?),
|
AstFragmentKind::Pat => AstFragment::Pat(self.parse_pat(None)?),
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -419,7 +419,7 @@ pub fn parse_item_panic(parser: &mut Parser) -> Option<P<Item>> {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn parse_pat_panic(parser: &mut Parser) -> P<Pat> {
|
pub fn parse_pat_panic(parser: &mut Parser) -> P<Pat> {
|
||||||
panictry!(parser.parse_pat())
|
panictry!(parser.parse_pat(None))
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn parse_arm_panic(parser: &mut Parser) -> Arm {
|
pub fn parse_arm_panic(parser: &mut Parser) -> Arm {
|
||||||
|
|
|
@ -881,7 +881,7 @@ fn parse_nt<'a>(p: &mut Parser<'a>, sp: Span, name: &str) -> Nonterminal {
|
||||||
FatalError.raise();
|
FatalError.raise();
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"pat" => token::NtPat(panictry!(p.parse_pat())),
|
"pat" => token::NtPat(panictry!(p.parse_pat(None))),
|
||||||
"expr" => token::NtExpr(panictry!(p.parse_expr())),
|
"expr" => token::NtExpr(panictry!(p.parse_expr())),
|
||||||
"literal" => token::NtLiteral(panictry!(p.parse_literal_maybe_minus())),
|
"literal" => token::NtLiteral(panictry!(p.parse_literal_maybe_minus())),
|
||||||
"ty" => token::NtTy(panictry!(p.parse_ty())),
|
"ty" => token::NtTy(panictry!(p.parse_ty())),
|
||||||
|
|
|
@ -1827,10 +1827,7 @@ impl<'a> Parser<'a> {
|
||||||
debug!("parse_arg_general parse_pat (require_name:{})",
|
debug!("parse_arg_general parse_pat (require_name:{})",
|
||||||
require_name);
|
require_name);
|
||||||
self.eat_incorrect_doc_comment("method arguments");
|
self.eat_incorrect_doc_comment("method arguments");
|
||||||
let pat = self.parse_pat().map_err(|mut err| {
|
let pat = self.parse_pat(Some("argument name"))?;
|
||||||
err.span_label(self.span, "expected argument name");
|
|
||||||
err
|
|
||||||
})?;
|
|
||||||
|
|
||||||
if let Err(mut err) = self.expect(&token::Colon) {
|
if let Err(mut err) = self.expect(&token::Colon) {
|
||||||
// If we find a pattern followed by an identifier, it could be an (incorrect)
|
// If we find a pattern followed by an identifier, it could be an (incorrect)
|
||||||
|
@ -1879,7 +1876,7 @@ impl<'a> Parser<'a> {
|
||||||
// Recover from attempting to parse the argument as a type without pattern.
|
// Recover from attempting to parse the argument as a type without pattern.
|
||||||
err.cancel();
|
err.cancel();
|
||||||
mem::replace(self, parser_snapshot_before_ty);
|
mem::replace(self, parser_snapshot_before_ty);
|
||||||
let pat = self.parse_pat()?;
|
let pat = self.parse_pat(Some("argument name"))?;
|
||||||
self.expect(&token::Colon)?;
|
self.expect(&token::Colon)?;
|
||||||
let ty = self.parse_ty()?;
|
let ty = self.parse_ty()?;
|
||||||
|
|
||||||
|
@ -1917,7 +1914,7 @@ impl<'a> Parser<'a> {
|
||||||
|
|
||||||
/// Parse an argument in a lambda header e.g. |arg, arg|
|
/// Parse an argument in a lambda header e.g. |arg, arg|
|
||||||
fn parse_fn_block_arg(&mut self) -> PResult<'a, Arg> {
|
fn parse_fn_block_arg(&mut self) -> PResult<'a, Arg> {
|
||||||
let pat = self.parse_pat()?;
|
let pat = self.parse_pat(Some("argument name"))?;
|
||||||
let t = if self.eat(&token::Colon) {
|
let t = if self.eat(&token::Colon) {
|
||||||
self.parse_ty()?
|
self.parse_ty()?
|
||||||
} else {
|
} else {
|
||||||
|
@ -3784,7 +3781,7 @@ impl<'a> Parser<'a> {
|
||||||
"`..` can only be used once per tuple or tuple struct pattern");
|
"`..` can only be used once per tuple or tuple struct pattern");
|
||||||
}
|
}
|
||||||
} else if !self.check(&token::CloseDelim(token::Paren)) {
|
} else if !self.check(&token::CloseDelim(token::Paren)) {
|
||||||
fields.push(self.parse_pat()?);
|
fields.push(self.parse_pat(None)?);
|
||||||
} else {
|
} else {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
|
@ -3840,7 +3837,7 @@ impl<'a> Parser<'a> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let subpat = self.parse_pat()?;
|
let subpat = self.parse_pat(None)?;
|
||||||
if before_slice && self.eat(&token::DotDot) {
|
if before_slice && self.eat(&token::DotDot) {
|
||||||
slice = Some(subpat);
|
slice = Some(subpat);
|
||||||
before_slice = false;
|
before_slice = false;
|
||||||
|
@ -3865,7 +3862,7 @@ impl<'a> Parser<'a> {
|
||||||
// Parsing a pattern of the form "fieldname: pat"
|
// Parsing a pattern of the form "fieldname: pat"
|
||||||
let fieldname = self.parse_field_name()?;
|
let fieldname = self.parse_field_name()?;
|
||||||
self.bump();
|
self.bump();
|
||||||
let pat = self.parse_pat()?;
|
let pat = self.parse_pat(None)?;
|
||||||
hi = pat.span;
|
hi = pat.span;
|
||||||
(pat, fieldname, false)
|
(pat, fieldname, false)
|
||||||
} else {
|
} else {
|
||||||
|
@ -4067,7 +4064,7 @@ impl<'a> Parser<'a> {
|
||||||
/// "top-level" patterns in a match arm, `for` loop, `let`, &c. (in contrast
|
/// "top-level" patterns in a match arm, `for` loop, `let`, &c. (in contrast
|
||||||
/// to subpatterns within such).
|
/// to subpatterns within such).
|
||||||
fn parse_top_level_pat(&mut self) -> PResult<'a, P<Pat>> {
|
fn parse_top_level_pat(&mut self) -> PResult<'a, P<Pat>> {
|
||||||
let pat = self.parse_pat()?;
|
let pat = self.parse_pat(None)?;
|
||||||
if self.token == token::Comma {
|
if self.token == token::Comma {
|
||||||
// An unexpected comma after a top-level pattern is a clue that the
|
// An unexpected comma after a top-level pattern is a clue that the
|
||||||
// user (perhaps more accustomed to some other language) forgot the
|
// user (perhaps more accustomed to some other language) forgot the
|
||||||
|
@ -4099,13 +4096,17 @@ impl<'a> Parser<'a> {
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Parse a pattern.
|
/// Parse a pattern.
|
||||||
pub fn parse_pat(&mut self) -> PResult<'a, P<Pat>> {
|
pub fn parse_pat(&mut self, expected: Option<&'static str>) -> PResult<'a, P<Pat>> {
|
||||||
self.parse_pat_with_range_pat(true)
|
self.parse_pat_with_range_pat(true, expected)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Parse a pattern, with a setting whether modern range patterns e.g. `a..=b`, `a..b` are
|
/// Parse a pattern, with a setting whether modern range patterns e.g. `a..=b`, `a..b` are
|
||||||
/// allowed.
|
/// allowed.
|
||||||
fn parse_pat_with_range_pat(&mut self, allow_range_pat: bool) -> PResult<'a, P<Pat>> {
|
fn parse_pat_with_range_pat(
|
||||||
|
&mut self,
|
||||||
|
allow_range_pat: bool,
|
||||||
|
expected: Option<&'static str>,
|
||||||
|
) -> PResult<'a, P<Pat>> {
|
||||||
maybe_whole!(self, NtPat, |x| x);
|
maybe_whole!(self, NtPat, |x| x);
|
||||||
|
|
||||||
let lo = self.span;
|
let lo = self.span;
|
||||||
|
@ -4121,7 +4122,7 @@ impl<'a> Parser<'a> {
|
||||||
err.span_label(self.span, "unexpected lifetime");
|
err.span_label(self.span, "unexpected lifetime");
|
||||||
return Err(err);
|
return Err(err);
|
||||||
}
|
}
|
||||||
let subpat = self.parse_pat_with_range_pat(false)?;
|
let subpat = self.parse_pat_with_range_pat(false, expected)?;
|
||||||
pat = PatKind::Ref(subpat, mutbl);
|
pat = PatKind::Ref(subpat, mutbl);
|
||||||
}
|
}
|
||||||
token::OpenDelim(token::Paren) => {
|
token::OpenDelim(token::Paren) => {
|
||||||
|
@ -4167,7 +4168,7 @@ impl<'a> Parser<'a> {
|
||||||
pat = self.parse_pat_ident(BindingMode::ByRef(mutbl))?;
|
pat = self.parse_pat_ident(BindingMode::ByRef(mutbl))?;
|
||||||
} else if self.eat_keyword(keywords::Box) {
|
} else if self.eat_keyword(keywords::Box) {
|
||||||
// Parse box pat
|
// Parse box pat
|
||||||
let subpat = self.parse_pat_with_range_pat(false)?;
|
let subpat = self.parse_pat_with_range_pat(false, None)?;
|
||||||
pat = PatKind::Box(subpat);
|
pat = PatKind::Box(subpat);
|
||||||
} else if self.token.is_ident() && !self.token.is_reserved_ident() &&
|
} else if self.token.is_ident() && !self.token.is_reserved_ident() &&
|
||||||
self.parse_as_ident() {
|
self.parse_as_ident() {
|
||||||
|
@ -4267,9 +4268,14 @@ impl<'a> Parser<'a> {
|
||||||
}
|
}
|
||||||
Err(mut err) => {
|
Err(mut err) => {
|
||||||
self.cancel(&mut err);
|
self.cancel(&mut err);
|
||||||
let msg = format!("expected pattern, found {}", self.this_token_descr());
|
let expected = expected.unwrap_or("pattern");
|
||||||
|
let msg = format!(
|
||||||
|
"expected {}, found {}",
|
||||||
|
expected,
|
||||||
|
self.this_token_descr(),
|
||||||
|
);
|
||||||
let mut err = self.fatal(&msg);
|
let mut err = self.fatal(&msg);
|
||||||
err.span_label(self.span, "expected pattern");
|
err.span_label(self.span, format!("expected {}", expected));
|
||||||
return Err(err);
|
return Err(err);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -4313,7 +4319,7 @@ impl<'a> Parser<'a> {
|
||||||
-> PResult<'a, PatKind> {
|
-> PResult<'a, PatKind> {
|
||||||
let ident = self.parse_ident()?;
|
let ident = self.parse_ident()?;
|
||||||
let sub = if self.eat(&token::At) {
|
let sub = if self.eat(&token::At) {
|
||||||
Some(self.parse_pat()?)
|
Some(self.parse_pat(Some("binding pattern"))?)
|
||||||
} else {
|
} else {
|
||||||
None
|
None
|
||||||
};
|
};
|
||||||
|
|
|
@ -68,7 +68,7 @@ pub fn string_to_item (source_str : String) -> Option<P<ast::Item>> {
|
||||||
pub fn string_to_pat(source_str: String) -> P<ast::Pat> {
|
pub fn string_to_pat(source_str: String) -> P<ast::Pat> {
|
||||||
let ps = ParseSess::new(FilePathMapping::empty());
|
let ps = ParseSess::new(FilePathMapping::empty());
|
||||||
with_error_checking_parse(source_str, &ps, |p| {
|
with_error_checking_parse(source_str, &ps, |p| {
|
||||||
p.parse_pat()
|
p.parse_pat(None)
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -11,5 +11,6 @@
|
||||||
// compile-flags: -Z parse-only
|
// compile-flags: -Z parse-only
|
||||||
|
|
||||||
impl S {
|
impl S {
|
||||||
fn f(*, a: u8) -> u8 {} //~ ERROR expected pattern, found `*`
|
fn f(*, a: u8) -> u8 {}
|
||||||
|
//~^ ERROR expected argument name, found `*`
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,11 +1,8 @@
|
||||||
error: expected pattern, found `*`
|
error: expected argument name, found `*`
|
||||||
--> $DIR/issue-33413.rs:14:10
|
--> $DIR/issue-33413.rs:14:10
|
||||||
|
|
|
|
||||||
LL | fn f(*, a: u8) -> u8 {} //~ ERROR expected pattern, found `*`
|
LL | fn f(*, a: u8) -> u8 {}
|
||||||
| ^
|
| ^ expected argument name
|
||||||
| |
|
|
||||||
| expected pattern
|
|
||||||
| expected argument name
|
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to previous error
|
||||||
|
|
||||||
|
|
|
@ -2,10 +2,7 @@ error: unexpected lifetime `'a` in pattern
|
||||||
--> $DIR/lifetime-in-pattern.rs:13:10
|
--> $DIR/lifetime-in-pattern.rs:13:10
|
||||||
|
|
|
|
||||||
LL | fn test(&'a str) {
|
LL | fn test(&'a str) {
|
||||||
| ^^
|
| ^^ unexpected lifetime
|
||||||
| |
|
|
||||||
| unexpected lifetime
|
|
||||||
| expected argument name
|
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to previous error
|
||||||
|
|
||||||
|
|
|
@ -10,4 +10,5 @@
|
||||||
|
|
||||||
// compile-flags: -Z parse-only
|
// compile-flags: -Z parse-only
|
||||||
|
|
||||||
fn f(+x: isize) {} //~ ERROR expected pattern, found `+`
|
fn f(+x: isize) {}
|
||||||
|
//~^ ERROR expected argument name, found `+`
|
||||||
|
|
|
@ -1,11 +1,8 @@
|
||||||
error: expected pattern, found `+`
|
error: expected argument name, found `+`
|
||||||
--> $DIR/removed-syntax-mode.rs:13:6
|
--> $DIR/removed-syntax-mode.rs:13:6
|
||||||
|
|
|
|
||||||
LL | fn f(+x: isize) {} //~ ERROR expected pattern, found `+`
|
LL | fn f(+x: isize) {}
|
||||||
| ^
|
| ^ expected argument name
|
||||||
| |
|
|
||||||
| expected pattern
|
|
||||||
| expected argument name
|
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to previous error
|
||||||
|
|
||||||
|
|
|
@ -2,10 +2,7 @@ error: unexpected lifetime `'a` in pattern
|
||||||
--> $DIR/self-vs-path-ambiguity.rs:19:11
|
--> $DIR/self-vs-path-ambiguity.rs:19:11
|
||||||
|
|
|
|
||||||
LL | fn i(&'a self::S: &S) {} //~ ERROR unexpected lifetime `'a` in pattern
|
LL | fn i(&'a self::S: &S) {} //~ ERROR unexpected lifetime `'a` in pattern
|
||||||
| ^^
|
| ^^ unexpected lifetime
|
||||||
| |
|
|
||||||
| unexpected lifetime
|
|
||||||
| expected argument name
|
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to previous error
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue