Tweak unclosed generics errors
Remove unnecessary span label for parse errors that already have a suggestion. Provide structured suggestion to close generics in more cases.
This commit is contained in:
parent
64d7e0d0b6
commit
4e99db9e54
@ -674,15 +674,6 @@ fn is_ident_eq_keyword(found: &TokenKind, expected: &TokenType) -> bool {
|
||||
);
|
||||
}
|
||||
|
||||
// Add suggestion for a missing closing angle bracket if '>' is included in expected_tokens
|
||||
// there are unclosed angle brackets
|
||||
if self.unmatched_angle_bracket_count > 0
|
||||
&& self.token.kind == TokenKind::Eq
|
||||
&& expected.iter().any(|tok| matches!(tok, TokenType::Token(TokenKind::Gt)))
|
||||
{
|
||||
err.span_label(self.prev_token.span, "maybe try to close unmatched angle bracket");
|
||||
}
|
||||
|
||||
let sp = if self.token == token::Eof {
|
||||
// This is EOF; don't want to point at the following char, but rather the last token.
|
||||
self.prev_token.span
|
||||
@ -819,6 +810,7 @@ pub(super) fn attr_on_non_tail_expr(&self, expr: &Expr) {
|
||||
}
|
||||
err.emit();
|
||||
}
|
||||
|
||||
fn check_too_many_raw_str_terminators(&mut self, err: &mut Diagnostic) -> bool {
|
||||
let sm = self.sess.source_map();
|
||||
match (&self.prev_token.kind, &self.token.kind) {
|
||||
@ -1994,6 +1986,39 @@ pub(super) fn try_macro_suggestion(&mut self) -> PResult<'a, P<Expr>> {
|
||||
}
|
||||
}
|
||||
|
||||
/// When trying to close a generics list and encountering code like
|
||||
/// ```text
|
||||
/// impl<S: Into<std::borrow::Cow<'static, str>> From<S> for Canonical {}
|
||||
/// // ^ missing > here
|
||||
/// ```
|
||||
/// we provide a structured suggestion on the error from `expect_gt`.
|
||||
pub(super) fn expect_gt_or_maybe_suggest_closing_generics(
|
||||
&mut self,
|
||||
params: &[ast::GenericParam],
|
||||
) -> PResult<'a, ()> {
|
||||
let Err(mut err) = self.expect_gt() else {
|
||||
return Ok(());
|
||||
};
|
||||
// Attempt to find places where a missing `>` might belong.
|
||||
if let [.., ast::GenericParam { bounds, .. }] = params
|
||||
&& let Some(poly) = bounds
|
||||
.iter()
|
||||
.filter_map(|bound| match bound {
|
||||
ast::GenericBound::Trait(poly, _) => Some(poly),
|
||||
_ => None,
|
||||
})
|
||||
.last()
|
||||
{
|
||||
err.span_suggestion_verbose(
|
||||
poly.span.shrink_to_hi(),
|
||||
"you might have meant to end the type parameters here",
|
||||
">",
|
||||
Applicability::MaybeIncorrect,
|
||||
);
|
||||
}
|
||||
Err(err)
|
||||
}
|
||||
|
||||
pub(super) fn recover_seq_parse_error(
|
||||
&mut self,
|
||||
delim: Delimiter,
|
||||
|
@ -279,7 +279,7 @@ pub(super) fn parse_generics(&mut self) -> PResult<'a, ast::Generics> {
|
||||
let span_lo = self.token.span;
|
||||
let (params, span) = if self.eat_lt() {
|
||||
let params = self.parse_generic_params()?;
|
||||
self.expect_gt()?;
|
||||
self.expect_gt_or_maybe_suggest_closing_generics(¶ms)?;
|
||||
(params, span_lo.to(self.prev_token.span))
|
||||
} else {
|
||||
(ThinVec::new(), self.prev_token.span.shrink_to_hi())
|
||||
|
@ -2,9 +2,7 @@ error: expected one of `!`, `(`, `+`, `,`, `::`, `<`, or `>`, found `=`
|
||||
--> $DIR/trait-path-expected-token.rs:5:33
|
||||
|
|
||||
LL | fn f1<'a>(arg : Box<dyn X<Y = B = &'a ()>>) {}
|
||||
| - ^ expected one of 7 possible tokens
|
||||
| |
|
||||
| maybe try to close unmatched angle bracket
|
||||
| ^ expected one of 7 possible tokens
|
||||
|
||||
error: aborting due to 1 previous error
|
||||
|
||||
|
@ -10,9 +10,7 @@ error: expected one of `,`, `:`, or `>`, found `=`
|
||||
--> $DIR/trait-path-expressions.rs:16:36
|
||||
|
|
||||
LL | fn f2<'a>(arg : Box<dyn X< { 1 } = 32 >>) {}
|
||||
| - ^ expected one of `,`, `:`, or `>`
|
||||
| |
|
||||
| maybe try to close unmatched angle bracket
|
||||
| ^ expected one of `,`, `:`, or `>`
|
||||
|
|
||||
help: you might have meant to end the type parameters here
|
||||
|
|
||||
|
@ -8,9 +8,7 @@ error: expected one of `>`, a const expression, lifetime, or type, found `=`
|
||||
--> $DIR/trait-path-missing-gen_arg.rs:11:30
|
||||
|
|
||||
LL | fn f1<'a>(arg : Box<dyn X< = 32 >>) {}
|
||||
| - ^ expected one of `>`, a const expression, lifetime, or type
|
||||
| |
|
||||
| maybe try to close unmatched angle bracket
|
||||
| ^ expected one of `>`, a const expression, lifetime, or type
|
||||
|
||||
error: aborting due to 2 previous errors
|
||||
|
||||
|
@ -2,9 +2,7 @@ error: expected one of `!`, `(`, `+`, `,`, `::`, `:`, `<`, or `>`, found `=`
|
||||
--> $DIR/trait-path-segments.rs:6:36
|
||||
|
|
||||
LL | fn f1<'a>(arg : Box<dyn X<X::Y = u32>>) {}
|
||||
| - ^ expected one of 8 possible tokens
|
||||
| |
|
||||
| maybe try to close unmatched angle bracket
|
||||
| ^ expected one of 8 possible tokens
|
||||
|
|
||||
help: you might have meant to end the type parameters here
|
||||
|
|
||||
@ -15,9 +13,7 @@ error: expected one of `,`, `::`, `:`, or `>`, found `=`
|
||||
--> $DIR/trait-path-segments.rs:17:35
|
||||
|
|
||||
LL | impl<T : X<<Self as X>::Y<'a> = &'a u32>> Z for T {}
|
||||
| - ^ expected one of `,`, `::`, `:`, or `>`
|
||||
| |
|
||||
| maybe try to close unmatched angle bracket
|
||||
| ^ expected one of `,`, `::`, `:`, or `>`
|
||||
|
|
||||
help: you might have meant to end the type parameters here
|
||||
|
|
||||
@ -28,9 +24,7 @@ error: expected one of `!`, `+`, `,`, `::`, `:`, or `>`, found `=`
|
||||
--> $DIR/trait-path-segments.rs:28:25
|
||||
|
|
||||
LL | impl<T : X<X::Y<'a> = &'a u32>> Z for T {}
|
||||
| - ^ expected one of `!`, `+`, `,`, `::`, `:`, or `>`
|
||||
| |
|
||||
| maybe try to close unmatched angle bracket
|
||||
| ^ expected one of `!`, `+`, `,`, `::`, `:`, or `>`
|
||||
|
|
||||
help: you might have meant to end the type parameters here
|
||||
|
|
||||
|
@ -2,9 +2,7 @@ error: expected one of `,`, `:`, or `>`, found `=`
|
||||
--> $DIR/trait-path-types.rs:6:37
|
||||
|
|
||||
LL | fn f<'a>(arg : Box<dyn X< [u8; 1] = u32>>) {}
|
||||
| - ^ expected one of `,`, `:`, or `>`
|
||||
| |
|
||||
| maybe try to close unmatched angle bracket
|
||||
| ^ expected one of `,`, `:`, or `>`
|
||||
|
|
||||
help: you might have meant to end the type parameters here
|
||||
|
|
||||
@ -15,9 +13,7 @@ error: expected one of `,`, `:`, or `>`, found `=`
|
||||
--> $DIR/trait-path-types.rs:11:37
|
||||
|
|
||||
LL | fn f1<'a>(arg : Box<dyn X<(Y<'a>) = &'a ()>>) {}
|
||||
| - ^ expected one of `,`, `:`, or `>`
|
||||
| |
|
||||
| maybe try to close unmatched angle bracket
|
||||
| ^ expected one of `,`, `:`, or `>`
|
||||
|
|
||||
help: you might have meant to end the type parameters here
|
||||
|
|
||||
@ -28,9 +24,7 @@ error: expected one of `,`, `:`, or `>`, found `=`
|
||||
--> $DIR/trait-path-types.rs:16:33
|
||||
|
|
||||
LL | fn f1<'a>(arg : Box<dyn X< 'a = u32 >>) {}
|
||||
| -- ^ expected one of `,`, `:`, or `>`
|
||||
| |
|
||||
| maybe try to close unmatched angle bracket
|
||||
| ^ expected one of `,`, `:`, or `>`
|
||||
|
|
||||
help: you might have meant to end the type parameters here
|
||||
|
|
||||
|
2
tests/ui/generics/unclosed-generics-in-impl-def.rs
Normal file
2
tests/ui/generics/unclosed-generics-in-impl-def.rs
Normal file
@ -0,0 +1,2 @@
|
||||
impl<S: Into<std::borrow::Cow<'static, str>> From<S> for Canonical {} //~ ERROR expected
|
||||
fn main() {}
|
13
tests/ui/generics/unclosed-generics-in-impl-def.stderr
Normal file
13
tests/ui/generics/unclosed-generics-in-impl-def.stderr
Normal file
@ -0,0 +1,13 @@
|
||||
error: expected one of `+`, `,`, `::`, `=`, or `>`, found `From`
|
||||
--> $DIR/unclosed-generics-in-impl-def.rs:1:46
|
||||
|
|
||||
LL | impl<S: Into<std::borrow::Cow<'static, str>> From<S> for Canonical {}
|
||||
| ^^^^ expected one of `+`, `,`, `::`, `=`, or `>`
|
||||
|
|
||||
help: you might have meant to end the type parameters here
|
||||
|
|
||||
LL | impl<S: Into<std::borrow::Cow<'static, str>>> From<S> for Canonical {}
|
||||
| +
|
||||
|
||||
error: aborting due to 1 previous error
|
||||
|
@ -2,9 +2,8 @@ error: expected one of `,`, `:`, or `>`, found `=`
|
||||
--> $DIR/issue-34334.rs:2:29
|
||||
|
|
||||
LL | let sr: Vec<(u32, _, _) = vec![];
|
||||
| -- - ^ expected one of `,`, `:`, or `>`
|
||||
| | |
|
||||
| | maybe try to close unmatched angle bracket
|
||||
| -- ^ expected one of `,`, `:`, or `>`
|
||||
| |
|
||||
| while parsing the type for `sr`
|
||||
|
|
||||
help: you might have meant to end the type parameters here
|
||||
|
@ -2,9 +2,8 @@ error: expected one of `,`, `:`, or `>`, found `=`
|
||||
--> $DIR/missing-closing-angle-bracket-eq-constraint.rs:7:23
|
||||
|
|
||||
LL | let v : Vec<(u32,_) = vec![];
|
||||
| - - ^ expected one of `,`, `:`, or `>`
|
||||
| | |
|
||||
| | maybe try to close unmatched angle bracket
|
||||
| - ^ expected one of `,`, `:`, or `>`
|
||||
| |
|
||||
| while parsing the type for `v`
|
||||
|
|
||||
help: you might have meant to end the type parameters here
|
||||
@ -29,9 +28,8 @@ error: expected one of `,`, `:`, or `>`, found `=`
|
||||
--> $DIR/missing-closing-angle-bracket-eq-constraint.rs:18:18
|
||||
|
|
||||
LL | let v : Vec<'a = vec![];
|
||||
| - -- ^ expected one of `,`, `:`, or `>`
|
||||
| | |
|
||||
| | maybe try to close unmatched angle bracket
|
||||
| - ^ expected one of `,`, `:`, or `>`
|
||||
| |
|
||||
| while parsing the type for `v`
|
||||
|
|
||||
help: you might have meant to end the type parameters here
|
||||
|
Loading…
Reference in New Issue
Block a user