rustc_parse/parser/
ty.rs

1use rustc_ast::ptr::P;
2use rustc_ast::token::{self, IdentIsRaw, MetaVarKind, Token, TokenKind};
3use rustc_ast::util::case::Case;
4use rustc_ast::{
5    self as ast, BareFnTy, BoundAsyncness, BoundConstness, BoundPolarity, DUMMY_NODE_ID, FnRetTy,
6    GenericBound, GenericBounds, GenericParam, Generics, Lifetime, MacCall, MutTy, Mutability,
7    Pinnedness, PolyTraitRef, PreciseCapturingArg, TraitBoundModifiers, TraitObjectSyntax, Ty,
8    TyKind, UnsafeBinderTy,
9};
10use rustc_data_structures::stack::ensure_sufficient_stack;
11use rustc_errors::{Applicability, Diag, PResult};
12use rustc_span::{ErrorGuaranteed, Ident, Span, kw, sym};
13use thin_vec::{ThinVec, thin_vec};
14
15use super::{Parser, PathStyle, SeqSep, TokenType, Trailing};
16use crate::errors::{
17    self, DynAfterMut, ExpectedFnPathFoundFnKeyword, ExpectedMutOrConstInRawPointerType,
18    FnPtrWithGenerics, FnPtrWithGenericsSugg, HelpUseLatestEdition, InvalidDynKeyword,
19    LifetimeAfterMut, NeedPlusAfterTraitObjectLifetime, NestedCVariadicType,
20    ReturnTypesUseThinArrow,
21};
22use crate::parser::item::FrontMatterParsingMode;
23use crate::{exp, maybe_recover_from_interpolated_ty_qpath};
24
25/// Signals whether parsing a type should allow `+`.
26///
27/// For example, let T be the type `impl Default + 'static`
28/// With `AllowPlus::Yes`, T will be parsed successfully
29/// With `AllowPlus::No`, parsing T will return a parse error
30#[derive(Copy, Clone, PartialEq)]
31pub(super) enum AllowPlus {
32    Yes,
33    No,
34}
35
36#[derive(PartialEq)]
37pub(super) enum RecoverQPath {
38    Yes,
39    No,
40}
41
42pub(super) enum RecoverQuestionMark {
43    Yes,
44    No,
45}
46
47/// Signals whether parsing a type should recover `->`.
48///
49/// More specifically, when parsing a function like:
50/// ```compile_fail
51/// fn foo() => u8 { 0 }
52/// fn bar(): u8 { 0 }
53/// ```
54/// The compiler will try to recover interpreting `foo() => u8` as `foo() -> u8` when calling
55/// `parse_ty` with anything except `RecoverReturnSign::No`, and it will try to recover `bar(): u8`
56/// as `bar() -> u8` when passing `RecoverReturnSign::Yes` to `parse_ty`
57#[derive(Copy, Clone, PartialEq)]
58pub(super) enum RecoverReturnSign {
59    Yes,
60    OnlyFatArrow,
61    No,
62}
63
64impl RecoverReturnSign {
65    /// [RecoverReturnSign::Yes] allows for recovering `fn foo() => u8` and `fn foo(): u8`,
66    /// [RecoverReturnSign::OnlyFatArrow] allows for recovering only `fn foo() => u8` (recovering
67    /// colons can cause problems when parsing where clauses), and
68    /// [RecoverReturnSign::No] doesn't allow for any recovery of the return type arrow
69    fn can_recover(self, token: &TokenKind) -> bool {
70        match self {
71            Self::Yes => matches!(token, token::FatArrow | token::Colon),
72            Self::OnlyFatArrow => matches!(token, token::FatArrow),
73            Self::No => false,
74        }
75    }
76}
77
78// Is `...` (`CVarArgs`) legal at this level of type parsing?
79#[derive(PartialEq)]
80enum AllowCVariadic {
81    Yes,
82    No,
83}
84
85/// Returns `true` if `IDENT t` can start a type -- `IDENT::a::b`, `IDENT<u8, u8>`,
86/// `IDENT<<u8 as Trait>::AssocTy>`.
87///
88/// Types can also be of the form `IDENT(u8, u8) -> u8`, however this assumes
89/// that `IDENT` is not the ident of a fn trait.
90fn can_continue_type_after_non_fn_ident(t: &Token) -> bool {
91    t == &token::PathSep || t == &token::Lt || t == &token::Shl
92}
93
94fn can_begin_dyn_bound_in_edition_2015(t: &Token) -> bool {
95    // `Not`, `Tilde` & `Const` are deliberately not part of this list to
96    // contain the number of potential regressions esp. in MBE code.
97    // `Const` would regress `rfc-2632-const-trait-impl/mbe-dyn-const-2015.rs`.
98    // `Not` would regress `dyn!(...)` macro calls in Rust 2015.
99    t.is_path_start()
100        || t.is_lifetime()
101        || t == &TokenKind::Question
102        || t.is_keyword(kw::For)
103        || t == &TokenKind::OpenParen
104}
105
106impl<'a> Parser<'a> {
107    /// Parses a type.
108    pub fn parse_ty(&mut self) -> PResult<'a, P<Ty>> {
109        // Make sure deeply nested types don't overflow the stack.
110        ensure_sufficient_stack(|| {
111            self.parse_ty_common(
112                AllowPlus::Yes,
113                AllowCVariadic::No,
114                RecoverQPath::Yes,
115                RecoverReturnSign::Yes,
116                None,
117                RecoverQuestionMark::Yes,
118            )
119        })
120    }
121
122    pub(super) fn parse_ty_with_generics_recovery(
123        &mut self,
124        ty_params: &Generics,
125    ) -> PResult<'a, P<Ty>> {
126        self.parse_ty_common(
127            AllowPlus::Yes,
128            AllowCVariadic::No,
129            RecoverQPath::Yes,
130            RecoverReturnSign::Yes,
131            Some(ty_params),
132            RecoverQuestionMark::Yes,
133        )
134    }
135
136    /// Parse a type suitable for a function or function pointer parameter.
137    /// The difference from `parse_ty` is that this version allows `...`
138    /// (`CVarArgs`) at the top level of the type.
139    pub(super) fn parse_ty_for_param(&mut self) -> PResult<'a, P<Ty>> {
140        self.parse_ty_common(
141            AllowPlus::Yes,
142            AllowCVariadic::Yes,
143            RecoverQPath::Yes,
144            RecoverReturnSign::Yes,
145            None,
146            RecoverQuestionMark::Yes,
147        )
148    }
149
150    /// Parses a type in restricted contexts where `+` is not permitted.
151    ///
152    /// Example 1: `&'a TYPE`
153    ///     `+` is prohibited to maintain operator priority (P(+) < P(&)).
154    /// Example 2: `value1 as TYPE + value2`
155    ///     `+` is prohibited to avoid interactions with expression grammar.
156    pub(super) fn parse_ty_no_plus(&mut self) -> PResult<'a, P<Ty>> {
157        self.parse_ty_common(
158            AllowPlus::No,
159            AllowCVariadic::No,
160            RecoverQPath::Yes,
161            RecoverReturnSign::Yes,
162            None,
163            RecoverQuestionMark::Yes,
164        )
165    }
166
167    /// Parses a type following an `as` cast. Similar to `parse_ty_no_plus`, but signaling origin
168    /// for better diagnostics involving `?`.
169    pub(super) fn parse_as_cast_ty(&mut self) -> PResult<'a, P<Ty>> {
170        self.parse_ty_common(
171            AllowPlus::No,
172            AllowCVariadic::No,
173            RecoverQPath::Yes,
174            RecoverReturnSign::Yes,
175            None,
176            RecoverQuestionMark::No,
177        )
178    }
179
180    pub(super) fn parse_ty_no_question_mark_recover(&mut self) -> PResult<'a, P<Ty>> {
181        self.parse_ty_common(
182            AllowPlus::Yes,
183            AllowCVariadic::No,
184            RecoverQPath::Yes,
185            RecoverReturnSign::Yes,
186            None,
187            RecoverQuestionMark::No,
188        )
189    }
190
191    /// Parse a type without recovering `:` as `->` to avoid breaking code such
192    /// as `where fn() : for<'a>`.
193    pub(super) fn parse_ty_for_where_clause(&mut self) -> PResult<'a, P<Ty>> {
194        self.parse_ty_common(
195            AllowPlus::Yes,
196            AllowCVariadic::No,
197            RecoverQPath::Yes,
198            RecoverReturnSign::OnlyFatArrow,
199            None,
200            RecoverQuestionMark::Yes,
201        )
202    }
203
204    /// Parses an optional return type `[ -> TY ]` in a function declaration.
205    pub(super) fn parse_ret_ty(
206        &mut self,
207        allow_plus: AllowPlus,
208        recover_qpath: RecoverQPath,
209        recover_return_sign: RecoverReturnSign,
210    ) -> PResult<'a, FnRetTy> {
211        let lo = self.prev_token.span;
212        Ok(if self.eat(exp!(RArrow)) {
213            // FIXME(Centril): Can we unconditionally `allow_plus`?
214            let ty = self.parse_ty_common(
215                allow_plus,
216                AllowCVariadic::No,
217                recover_qpath,
218                recover_return_sign,
219                None,
220                RecoverQuestionMark::Yes,
221            )?;
222            FnRetTy::Ty(ty)
223        } else if recover_return_sign.can_recover(&self.token.kind) {
224            // Don't `eat` to prevent `=>` from being added as an expected token which isn't
225            // actually expected and could only confuse users
226            self.bump();
227            self.dcx().emit_err(ReturnTypesUseThinArrow {
228                span: self.prev_token.span,
229                suggestion: lo.between(self.token.span),
230            });
231            let ty = self.parse_ty_common(
232                allow_plus,
233                AllowCVariadic::No,
234                recover_qpath,
235                recover_return_sign,
236                None,
237                RecoverQuestionMark::Yes,
238            )?;
239            FnRetTy::Ty(ty)
240        } else {
241            FnRetTy::Default(self.prev_token.span.shrink_to_hi())
242        })
243    }
244
245    fn parse_ty_common(
246        &mut self,
247        allow_plus: AllowPlus,
248        allow_c_variadic: AllowCVariadic,
249        recover_qpath: RecoverQPath,
250        recover_return_sign: RecoverReturnSign,
251        ty_generics: Option<&Generics>,
252        recover_question_mark: RecoverQuestionMark,
253    ) -> PResult<'a, P<Ty>> {
254        let allow_qpath_recovery = recover_qpath == RecoverQPath::Yes;
255        maybe_recover_from_interpolated_ty_qpath!(self, allow_qpath_recovery);
256
257        if let Some(ty) = self.eat_metavar_seq_with_matcher(
258            |mv_kind| matches!(mv_kind, MetaVarKind::Ty { .. }),
259            |this| this.parse_ty_no_question_mark_recover(),
260        ) {
261            return Ok(ty);
262        }
263
264        let lo = self.token.span;
265        let mut impl_dyn_multi = false;
266        let kind = if self.check(exp!(OpenParen)) {
267            self.parse_ty_tuple_or_parens(lo, allow_plus)?
268        } else if self.eat(exp!(Bang)) {
269            // Never type `!`
270            TyKind::Never
271        } else if self.eat(exp!(Star)) {
272            self.parse_ty_ptr()?
273        } else if self.eat(exp!(OpenBracket)) {
274            self.parse_array_or_slice_ty()?
275        } else if self.check(exp!(And)) || self.check(exp!(AndAnd)) {
276            // Reference
277            self.expect_and()?;
278            self.parse_borrowed_pointee()?
279        } else if self.eat_keyword_noexpect(kw::Typeof) {
280            self.parse_typeof_ty()?
281        } else if self.eat_keyword(exp!(Underscore)) {
282            // A type to be inferred `_`
283            TyKind::Infer
284        } else if self.check_fn_front_matter(false, Case::Sensitive) {
285            // Function pointer type
286            self.parse_ty_bare_fn(lo, ThinVec::new(), None, recover_return_sign)?
287        } else if self.check_keyword(exp!(For)) {
288            // Function pointer type or bound list (trait object type) starting with a poly-trait.
289            //   `for<'lt> [unsafe] [extern "ABI"] fn (&'lt S) -> T`
290            //   `for<'lt> Trait1<'lt> + Trait2 + 'a`
291            let (lifetime_defs, _) = self.parse_late_bound_lifetime_defs()?;
292            if self.check_fn_front_matter(false, Case::Sensitive) {
293                self.parse_ty_bare_fn(
294                    lo,
295                    lifetime_defs,
296                    Some(self.prev_token.span.shrink_to_lo()),
297                    recover_return_sign,
298                )?
299            } else {
300                // Try to recover `for<'a> dyn Trait` or `for<'a> impl Trait`.
301                if self.may_recover()
302                    && (self.eat_keyword_noexpect(kw::Impl) || self.eat_keyword_noexpect(kw::Dyn))
303                {
304                    let kw = self.prev_token.ident().unwrap().0;
305                    let removal_span = kw.span.with_hi(self.token.span.lo());
306                    let path = self.parse_path(PathStyle::Type)?;
307                    let parse_plus = allow_plus == AllowPlus::Yes && self.check_plus();
308                    let kind =
309                        self.parse_remaining_bounds_path(lifetime_defs, path, lo, parse_plus)?;
310                    let err = self.dcx().create_err(errors::TransposeDynOrImpl {
311                        span: kw.span,
312                        kw: kw.name.as_str(),
313                        sugg: errors::TransposeDynOrImplSugg {
314                            removal_span,
315                            insertion_span: lo.shrink_to_lo(),
316                            kw: kw.name.as_str(),
317                        },
318                    });
319
320                    // Take the parsed bare trait object and turn it either
321                    // into a `dyn` object or an `impl Trait`.
322                    let kind = match (kind, kw.name) {
323                        (TyKind::TraitObject(bounds, _), kw::Dyn) => {
324                            TyKind::TraitObject(bounds, TraitObjectSyntax::Dyn)
325                        }
326                        (TyKind::TraitObject(bounds, _), kw::Impl) => {
327                            TyKind::ImplTrait(ast::DUMMY_NODE_ID, bounds)
328                        }
329                        _ => return Err(err),
330                    };
331                    err.emit();
332                    kind
333                } else {
334                    let path = self.parse_path(PathStyle::Type)?;
335                    let parse_plus = allow_plus == AllowPlus::Yes && self.check_plus();
336                    self.parse_remaining_bounds_path(lifetime_defs, path, lo, parse_plus)?
337                }
338            }
339        } else if self.eat_keyword(exp!(Impl)) {
340            self.parse_impl_ty(&mut impl_dyn_multi)?
341        } else if self.is_explicit_dyn_type() {
342            self.parse_dyn_ty(&mut impl_dyn_multi)?
343        } else if self.eat_lt() {
344            // Qualified path
345            let (qself, path) = self.parse_qpath(PathStyle::Type)?;
346            TyKind::Path(Some(qself), path)
347        } else if self.check_path() {
348            self.parse_path_start_ty(lo, allow_plus, ty_generics)?
349        } else if self.can_begin_bound() {
350            self.parse_bare_trait_object(lo, allow_plus)?
351        } else if self.eat(exp!(DotDotDot)) {
352            match allow_c_variadic {
353                AllowCVariadic::Yes => TyKind::CVarArgs,
354                AllowCVariadic::No => {
355                    // FIXME(c_variadic): Should we just allow `...` syntactically
356                    // anywhere in a type and use semantic restrictions instead?
357                    // NOTE: This may regress certain MBE calls if done incorrectly.
358                    let guar = self.dcx().emit_err(NestedCVariadicType { span: lo });
359                    TyKind::Err(guar)
360                }
361            }
362        } else if self.check_keyword(exp!(Unsafe))
363            && self.look_ahead(1, |tok| tok.kind == token::Lt)
364        {
365            self.parse_unsafe_binder_ty()?
366        } else {
367            let msg = format!("expected type, found {}", super::token_descr(&self.token));
368            let mut err = self.dcx().struct_span_err(lo, msg);
369            err.span_label(lo, "expected type");
370            return Err(err);
371        };
372
373        let span = lo.to(self.prev_token.span);
374        let mut ty = self.mk_ty(span, kind);
375
376        // Try to recover from use of `+` with incorrect priority.
377        match allow_plus {
378            AllowPlus::Yes => self.maybe_recover_from_bad_type_plus(&ty)?,
379            AllowPlus::No => self.maybe_report_ambiguous_plus(impl_dyn_multi, &ty),
380        }
381        if let RecoverQuestionMark::Yes = recover_question_mark {
382            ty = self.maybe_recover_from_question_mark(ty);
383        }
384        if allow_qpath_recovery { self.maybe_recover_from_bad_qpath(ty) } else { Ok(ty) }
385    }
386
387    fn parse_unsafe_binder_ty(&mut self) -> PResult<'a, TyKind> {
388        let lo = self.token.span;
389        assert!(self.eat_keyword(exp!(Unsafe)));
390        self.expect_lt()?;
391        let generic_params = self.parse_generic_params()?;
392        self.expect_gt()?;
393        let inner_ty = self.parse_ty()?;
394        let span = lo.to(self.prev_token.span);
395        self.psess.gated_spans.gate(sym::unsafe_binders, span);
396
397        Ok(TyKind::UnsafeBinder(P(UnsafeBinderTy { generic_params, inner_ty })))
398    }
399
400    /// Parses either:
401    /// - `(TYPE)`, a parenthesized type.
402    /// - `(TYPE,)`, a tuple with a single field of type TYPE.
403    fn parse_ty_tuple_or_parens(&mut self, lo: Span, allow_plus: AllowPlus) -> PResult<'a, TyKind> {
404        let mut trailing_plus = false;
405        let (ts, trailing) = self.parse_paren_comma_seq(|p| {
406            let ty = p.parse_ty()?;
407            trailing_plus = p.prev_token == TokenKind::Plus;
408            Ok(ty)
409        })?;
410
411        if ts.len() == 1 && matches!(trailing, Trailing::No) {
412            let ty = ts.into_iter().next().unwrap();
413            let maybe_bounds = allow_plus == AllowPlus::Yes && self.token.is_like_plus();
414            match ty.kind {
415                // `(TY_BOUND_NOPAREN) + BOUND + ...`.
416                TyKind::Path(None, path) if maybe_bounds => {
417                    self.parse_remaining_bounds_path(ThinVec::new(), path, lo, true)
418                }
419                // For `('a) + …`, we know that `'a` in type position already lead to an error being
420                // emitted. To reduce output, let's indirectly suppress E0178 (bad `+` in type) and
421                // other irrelevant consequential errors.
422                TyKind::TraitObject(bounds, TraitObjectSyntax::None)
423                    if maybe_bounds && bounds.len() == 1 && !trailing_plus =>
424                {
425                    self.parse_remaining_bounds(bounds, true)
426                }
427                // `(TYPE)`
428                _ => Ok(TyKind::Paren(ty)),
429            }
430        } else {
431            Ok(TyKind::Tup(ts))
432        }
433    }
434
435    fn parse_bare_trait_object(&mut self, lo: Span, allow_plus: AllowPlus) -> PResult<'a, TyKind> {
436        // A lifetime only begins a bare trait object type if it is followed by `+`!
437        if self.token.is_lifetime() && !self.look_ahead(1, |t| t.is_like_plus()) {
438            // In Rust 2021 and beyond, we assume that the user didn't intend to write a bare trait
439            // object type with a leading lifetime bound since that seems very unlikely given the
440            // fact that `dyn`-less trait objects are *semantically* invalid.
441            if self.psess.edition.at_least_rust_2021() {
442                let lt = self.expect_lifetime();
443                let mut err = self.dcx().struct_span_err(lo, "expected type, found lifetime");
444                err.span_label(lo, "expected type");
445                return Ok(match self.maybe_recover_ref_ty_no_leading_ampersand(lt, lo, err) {
446                    Ok(ref_ty) => ref_ty,
447                    Err(err) => TyKind::Err(err.emit()),
448                });
449            }
450
451            self.dcx().emit_err(NeedPlusAfterTraitObjectLifetime {
452                span: lo,
453                suggestion: lo.shrink_to_hi(),
454            });
455        }
456        Ok(TyKind::TraitObject(
457            self.parse_generic_bounds_common(allow_plus)?,
458            TraitObjectSyntax::None,
459        ))
460    }
461
462    fn maybe_recover_ref_ty_no_leading_ampersand<'cx>(
463        &mut self,
464        lt: Lifetime,
465        lo: Span,
466        mut err: Diag<'cx>,
467    ) -> Result<TyKind, Diag<'cx>> {
468        if !self.may_recover() {
469            return Err(err);
470        }
471        let snapshot = self.create_snapshot_for_diagnostic();
472        let mutbl = self.parse_mutability();
473        match self.parse_ty_no_plus() {
474            Ok(ty) => {
475                err.span_suggestion_verbose(
476                    lo.shrink_to_lo(),
477                    "you might have meant to write a reference type here",
478                    "&",
479                    Applicability::MaybeIncorrect,
480                );
481                err.emit();
482                Ok(TyKind::Ref(Some(lt), MutTy { ty, mutbl }))
483            }
484            Err(diag) => {
485                diag.cancel();
486                self.restore_snapshot(snapshot);
487                Err(err)
488            }
489        }
490    }
491
492    fn parse_remaining_bounds_path(
493        &mut self,
494        generic_params: ThinVec<GenericParam>,
495        path: ast::Path,
496        lo: Span,
497        parse_plus: bool,
498    ) -> PResult<'a, TyKind> {
499        let poly_trait_ref = PolyTraitRef::new(
500            generic_params,
501            path,
502            TraitBoundModifiers::NONE,
503            lo.to(self.prev_token.span),
504        );
505        let bounds = vec![GenericBound::Trait(poly_trait_ref)];
506        self.parse_remaining_bounds(bounds, parse_plus)
507    }
508
509    /// Parse the remainder of a bare trait object type given an already parsed list.
510    fn parse_remaining_bounds(
511        &mut self,
512        mut bounds: GenericBounds,
513        plus: bool,
514    ) -> PResult<'a, TyKind> {
515        if plus {
516            self.eat_plus(); // `+`, or `+=` gets split and `+` is discarded
517            bounds.append(&mut self.parse_generic_bounds()?);
518        }
519        Ok(TyKind::TraitObject(bounds, TraitObjectSyntax::None))
520    }
521
522    /// Parses a raw pointer type: `*[const | mut] $type`.
523    fn parse_ty_ptr(&mut self) -> PResult<'a, TyKind> {
524        let mutbl = self.parse_const_or_mut().unwrap_or_else(|| {
525            let span = self.prev_token.span;
526            self.dcx().emit_err(ExpectedMutOrConstInRawPointerType {
527                span,
528                after_asterisk: span.shrink_to_hi(),
529            });
530            Mutability::Not
531        });
532        let ty = self.parse_ty_no_plus()?;
533        Ok(TyKind::Ptr(MutTy { ty, mutbl }))
534    }
535
536    /// Parses an array (`[TYPE; EXPR]`) or slice (`[TYPE]`) type.
537    /// The opening `[` bracket is already eaten.
538    fn parse_array_or_slice_ty(&mut self) -> PResult<'a, TyKind> {
539        let elt_ty = match self.parse_ty() {
540            Ok(ty) => ty,
541            Err(err)
542                if self.look_ahead(1, |t| *t == token::CloseBracket)
543                    | self.look_ahead(1, |t| *t == token::Semi) =>
544            {
545                // Recover from `[LIT; EXPR]` and `[LIT]`
546                self.bump();
547                let guar = err.emit();
548                self.mk_ty(self.prev_token.span, TyKind::Err(guar))
549            }
550            Err(err) => return Err(err),
551        };
552
553        let ty = if self.eat(exp!(Semi)) {
554            let mut length = self.parse_expr_anon_const()?;
555            if let Err(e) = self.expect(exp!(CloseBracket)) {
556                // Try to recover from `X<Y, ...>` when `X::<Y, ...>` works
557                self.check_mistyped_turbofish_with_multiple_type_params(e, &mut length.value)?;
558                self.expect(exp!(CloseBracket))?;
559            }
560            TyKind::Array(elt_ty, length)
561        } else {
562            self.expect(exp!(CloseBracket))?;
563            TyKind::Slice(elt_ty)
564        };
565
566        Ok(ty)
567    }
568
569    fn parse_borrowed_pointee(&mut self) -> PResult<'a, TyKind> {
570        let and_span = self.prev_token.span;
571        let mut opt_lifetime = self.check_lifetime().then(|| self.expect_lifetime());
572        let (pinned, mut mutbl) = match self.parse_pin_and_mut() {
573            Some(pin_mut) => pin_mut,
574            None => (Pinnedness::Not, self.parse_mutability()),
575        };
576        if self.token.is_lifetime() && mutbl == Mutability::Mut && opt_lifetime.is_none() {
577            // A lifetime is invalid here: it would be part of a bare trait bound, which requires
578            // it to be followed by a plus, but we disallow plus in the pointee type.
579            // So we can handle this case as an error here, and suggest `'a mut`.
580            // If there *is* a plus next though, handling the error later provides better suggestions
581            // (like adding parentheses)
582            if !self.look_ahead(1, |t| t.is_like_plus()) {
583                let lifetime_span = self.token.span;
584                let span = and_span.to(lifetime_span);
585
586                let (suggest_lifetime, snippet) =
587                    if let Ok(lifetime_src) = self.span_to_snippet(lifetime_span) {
588                        (Some(span), lifetime_src)
589                    } else {
590                        (None, String::new())
591                    };
592                self.dcx().emit_err(LifetimeAfterMut { span, suggest_lifetime, snippet });
593
594                opt_lifetime = Some(self.expect_lifetime());
595            }
596        } else if self.token.is_keyword(kw::Dyn)
597            && mutbl == Mutability::Not
598            && self.look_ahead(1, |t| t.is_keyword(kw::Mut))
599        {
600            // We have `&dyn mut ...`, which is invalid and should be `&mut dyn ...`.
601            let span = and_span.to(self.look_ahead(1, |t| t.span));
602            self.dcx().emit_err(DynAfterMut { span });
603
604            // Recovery
605            mutbl = Mutability::Mut;
606            let (dyn_tok, dyn_tok_sp) = (self.token, self.token_spacing);
607            self.bump();
608            self.bump_with((dyn_tok, dyn_tok_sp));
609        }
610        let ty = self.parse_ty_no_plus()?;
611        Ok(match pinned {
612            Pinnedness::Not => TyKind::Ref(opt_lifetime, MutTy { ty, mutbl }),
613            Pinnedness::Pinned => TyKind::PinnedRef(opt_lifetime, MutTy { ty, mutbl }),
614        })
615    }
616
617    /// Parses `pin` and `mut` annotations on references.
618    ///
619    /// It must be either `pin const` or `pin mut`.
620    pub(crate) fn parse_pin_and_mut(&mut self) -> Option<(Pinnedness, Mutability)> {
621        if self.token.is_ident_named(sym::pin) {
622            let result = self.look_ahead(1, |token| {
623                if token.is_keyword(kw::Const) {
624                    Some((Pinnedness::Pinned, Mutability::Not))
625                } else if token.is_keyword(kw::Mut) {
626                    Some((Pinnedness::Pinned, Mutability::Mut))
627                } else {
628                    None
629                }
630            });
631            if result.is_some() {
632                self.psess.gated_spans.gate(sym::pin_ergonomics, self.token.span);
633                self.bump();
634                self.bump();
635            }
636            result
637        } else {
638            None
639        }
640    }
641
642    // Parses the `typeof(EXPR)`.
643    // To avoid ambiguity, the type is surrounded by parentheses.
644    fn parse_typeof_ty(&mut self) -> PResult<'a, TyKind> {
645        self.expect(exp!(OpenParen))?;
646        let expr = self.parse_expr_anon_const()?;
647        self.expect(exp!(CloseParen))?;
648        Ok(TyKind::Typeof(expr))
649    }
650
651    /// Parses a function pointer type (`TyKind::BareFn`).
652    /// ```ignore (illustrative)
653    ///    [unsafe] [extern "ABI"] fn (S) -> T
654    /// //  ^~~~~^          ^~~~^     ^~^    ^
655    /// //    |               |        |     |
656    /// //    |               |        |   Return type
657    /// // Function Style    ABI  Parameter types
658    /// ```
659    /// We actually parse `FnHeader FnDecl`, but we error on `const` and `async` qualifiers.
660    fn parse_ty_bare_fn(
661        &mut self,
662        lo: Span,
663        mut params: ThinVec<GenericParam>,
664        param_insertion_point: Option<Span>,
665        recover_return_sign: RecoverReturnSign,
666    ) -> PResult<'a, TyKind> {
667        let inherited_vis = rustc_ast::Visibility {
668            span: rustc_span::DUMMY_SP,
669            kind: rustc_ast::VisibilityKind::Inherited,
670            tokens: None,
671        };
672        let span_start = self.token.span;
673        let ast::FnHeader { ext, safety, .. } = self.parse_fn_front_matter(
674            &inherited_vis,
675            Case::Sensitive,
676            FrontMatterParsingMode::FunctionPtrType,
677        )?;
678        if self.may_recover() && self.token == TokenKind::Lt {
679            self.recover_fn_ptr_with_generics(lo, &mut params, param_insertion_point)?;
680        }
681        let decl = self.parse_fn_decl(|_| false, AllowPlus::No, recover_return_sign)?;
682
683        let decl_span = span_start.to(self.prev_token.span);
684        Ok(TyKind::BareFn(P(BareFnTy { ext, safety, generic_params: params, decl, decl_span })))
685    }
686
687    /// Recover from function pointer types with a generic parameter list (e.g. `fn<'a>(&'a str)`).
688    fn recover_fn_ptr_with_generics(
689        &mut self,
690        lo: Span,
691        params: &mut ThinVec<GenericParam>,
692        param_insertion_point: Option<Span>,
693    ) -> PResult<'a, ()> {
694        let generics = self.parse_generics()?;
695        let arity = generics.params.len();
696
697        let mut lifetimes: ThinVec<_> = generics
698            .params
699            .into_iter()
700            .filter(|param| matches!(param.kind, ast::GenericParamKind::Lifetime))
701            .collect();
702
703        let sugg = if !lifetimes.is_empty() {
704            let snippet =
705                lifetimes.iter().map(|param| param.ident.as_str()).intersperse(", ").collect();
706
707            let (left, snippet) = if let Some(span) = param_insertion_point {
708                (span, if params.is_empty() { snippet } else { format!(", {snippet}") })
709            } else {
710                (lo.shrink_to_lo(), format!("for<{snippet}> "))
711            };
712
713            Some(FnPtrWithGenericsSugg {
714                left,
715                snippet,
716                right: generics.span,
717                arity,
718                for_param_list_exists: param_insertion_point.is_some(),
719            })
720        } else {
721            None
722        };
723
724        self.dcx().emit_err(FnPtrWithGenerics { span: generics.span, sugg });
725        params.append(&mut lifetimes);
726        Ok(())
727    }
728
729    /// Parses an `impl B0 + ... + Bn` type.
730    fn parse_impl_ty(&mut self, impl_dyn_multi: &mut bool) -> PResult<'a, TyKind> {
731        if self.token.is_lifetime() {
732            self.look_ahead(1, |t| {
733                if let token::Ident(sym, _) = t.kind {
734                    // parse pattern with "'a Sized" we're supposed to give suggestion like
735                    // "'a + Sized"
736                    self.dcx().emit_err(errors::MissingPlusBounds {
737                        span: self.token.span,
738                        hi: self.token.span.shrink_to_hi(),
739                        sym,
740                    });
741                }
742            })
743        }
744
745        // Always parse bounds greedily for better error recovery.
746        let bounds = self.parse_generic_bounds()?;
747
748        *impl_dyn_multi = bounds.len() > 1 || self.prev_token == TokenKind::Plus;
749
750        Ok(TyKind::ImplTrait(ast::DUMMY_NODE_ID, bounds))
751    }
752
753    fn parse_precise_capturing_args(
754        &mut self,
755    ) -> PResult<'a, (ThinVec<PreciseCapturingArg>, Span)> {
756        let lo = self.token.span;
757        self.expect_lt()?;
758        let (args, _, _) = self.parse_seq_to_before_tokens(
759            &[exp!(Gt)],
760            &[&TokenKind::Ge, &TokenKind::Shr, &TokenKind::Shr],
761            SeqSep::trailing_allowed(exp!(Comma)),
762            |self_| {
763                if self_.check_keyword(exp!(SelfUpper)) {
764                    self_.bump();
765                    Ok(PreciseCapturingArg::Arg(
766                        ast::Path::from_ident(self_.prev_token.ident().unwrap().0),
767                        DUMMY_NODE_ID,
768                    ))
769                } else if self_.check_ident() {
770                    Ok(PreciseCapturingArg::Arg(
771                        ast::Path::from_ident(self_.parse_ident()?),
772                        DUMMY_NODE_ID,
773                    ))
774                } else if self_.check_lifetime() {
775                    Ok(PreciseCapturingArg::Lifetime(self_.expect_lifetime()))
776                } else {
777                    self_.unexpected_any()
778                }
779            },
780        )?;
781        self.expect_gt()?;
782        Ok((args, lo.to(self.prev_token.span)))
783    }
784
785    /// Is a `dyn B0 + ... + Bn` type allowed here?
786    fn is_explicit_dyn_type(&mut self) -> bool {
787        self.check_keyword(exp!(Dyn))
788            && (self.token_uninterpolated_span().at_least_rust_2018()
789                || self.look_ahead(1, |t| {
790                    (can_begin_dyn_bound_in_edition_2015(t) || *t == TokenKind::Star)
791                        && !can_continue_type_after_non_fn_ident(t)
792                }))
793    }
794
795    /// Parses a `dyn B0 + ... + Bn` type.
796    ///
797    /// Note that this does *not* parse bare trait objects.
798    fn parse_dyn_ty(&mut self, impl_dyn_multi: &mut bool) -> PResult<'a, TyKind> {
799        let lo = self.token.span;
800        self.bump(); // `dyn`
801
802        // parse dyn* types
803        let syntax = if self.eat(exp!(Star)) {
804            self.psess.gated_spans.gate(sym::dyn_star, lo.to(self.prev_token.span));
805            TraitObjectSyntax::DynStar
806        } else {
807            TraitObjectSyntax::Dyn
808        };
809
810        // Always parse bounds greedily for better error recovery.
811        let bounds = self.parse_generic_bounds()?;
812        *impl_dyn_multi = bounds.len() > 1 || self.prev_token == TokenKind::Plus;
813        Ok(TyKind::TraitObject(bounds, syntax))
814    }
815
816    /// Parses a type starting with a path.
817    ///
818    /// This can be:
819    /// 1. a type macro, `mac!(...)`,
820    /// 2. a bare trait object, `B0 + ... + Bn`,
821    /// 3. or a path, `path::to::MyType`.
822    fn parse_path_start_ty(
823        &mut self,
824        lo: Span,
825        allow_plus: AllowPlus,
826        ty_generics: Option<&Generics>,
827    ) -> PResult<'a, TyKind> {
828        // Simple path
829        let path = self.parse_path_inner(PathStyle::Type, ty_generics)?;
830        if self.eat(exp!(Bang)) {
831            // Macro invocation in type position
832            Ok(TyKind::MacCall(P(MacCall { path, args: self.parse_delim_args()? })))
833        } else if allow_plus == AllowPlus::Yes && self.check_plus() {
834            // `Trait1 + Trait2 + 'a`
835            self.parse_remaining_bounds_path(ThinVec::new(), path, lo, true)
836        } else {
837            // Just a type path.
838            Ok(TyKind::Path(None, path))
839        }
840    }
841
842    pub(super) fn parse_generic_bounds(&mut self) -> PResult<'a, GenericBounds> {
843        self.parse_generic_bounds_common(AllowPlus::Yes)
844    }
845
846    /// Parses bounds of a type parameter `BOUND + BOUND + ...`, possibly with trailing `+`.
847    ///
848    /// See `parse_generic_bound` for the `BOUND` grammar.
849    fn parse_generic_bounds_common(&mut self, allow_plus: AllowPlus) -> PResult<'a, GenericBounds> {
850        let mut bounds = Vec::new();
851
852        // In addition to looping while we find generic bounds:
853        // We continue even if we find a keyword. This is necessary for error recovery on,
854        // for example, `impl fn()`. The only keyword that can go after generic bounds is
855        // `where`, so stop if it's it.
856        // We also continue if we find types (not traits), again for error recovery.
857        while self.can_begin_bound()
858            || (self.may_recover()
859                && (self.token.can_begin_type()
860                    || (self.token.is_reserved_ident() && !self.token.is_keyword(kw::Where))))
861        {
862            if self.token.is_keyword(kw::Dyn) {
863                // Account for `&dyn Trait + dyn Other`.
864                self.bump();
865                self.dcx().emit_err(InvalidDynKeyword {
866                    span: self.prev_token.span,
867                    suggestion: self.prev_token.span.until(self.token.span),
868                });
869            }
870            bounds.push(self.parse_generic_bound()?);
871            if allow_plus == AllowPlus::No || !self.eat_plus() {
872                break;
873            }
874        }
875
876        Ok(bounds)
877    }
878
879    /// Can the current token begin a bound?
880    fn can_begin_bound(&mut self) -> bool {
881        self.check_path()
882            || self.check_lifetime()
883            || self.check(exp!(Bang))
884            || self.check(exp!(Question))
885            || self.check(exp!(Tilde))
886            || self.check_keyword(exp!(For))
887            || self.check(exp!(OpenParen))
888            || self.check(exp!(OpenBracket))
889            || self.check_keyword(exp!(Const))
890            || self.check_keyword(exp!(Async))
891            || self.check_keyword(exp!(Use))
892    }
893
894    /// Parses a bound according to the grammar:
895    /// ```ebnf
896    /// BOUND = TY_BOUND | LT_BOUND
897    /// ```
898    fn parse_generic_bound(&mut self) -> PResult<'a, GenericBound> {
899        let lo = self.token.span;
900        let leading_token = self.prev_token;
901        let has_parens = self.eat(exp!(OpenParen));
902
903        let bound = if self.token.is_lifetime() {
904            self.parse_generic_lt_bound(lo, has_parens)?
905        } else if self.eat_keyword(exp!(Use)) {
906            // parse precise captures, if any. This is `use<'lt, 'lt, P, P>`; a list of
907            // lifetimes and ident params (including SelfUpper). These are validated later
908            // for order, duplication, and whether they actually reference params.
909            let use_span = self.prev_token.span;
910            let (args, args_span) = self.parse_precise_capturing_args()?;
911            GenericBound::Use(args, use_span.to(args_span))
912        } else {
913            self.parse_generic_ty_bound(lo, has_parens, &leading_token)?
914        };
915
916        Ok(bound)
917    }
918
919    /// Parses a lifetime ("outlives") bound, e.g. `'a`, according to:
920    /// ```ebnf
921    /// LT_BOUND = LIFETIME
922    /// ```
923    fn parse_generic_lt_bound(&mut self, lo: Span, has_parens: bool) -> PResult<'a, GenericBound> {
924        let lt = self.expect_lifetime();
925        let bound = GenericBound::Outlives(lt);
926        if has_parens {
927            // FIXME(Centril): Consider not erroring here and accepting `('lt)` instead,
928            // possibly introducing `GenericBound::Paren(P<GenericBound>)`?
929            self.recover_paren_lifetime(lo)?;
930        }
931        Ok(bound)
932    }
933
934    /// Emits an error if any trait bound modifiers were present.
935    fn error_lt_bound_with_modifiers(
936        &self,
937        modifiers: TraitBoundModifiers,
938        binder_span: Option<Span>,
939    ) -> ErrorGuaranteed {
940        let TraitBoundModifiers { constness, asyncness, polarity } = modifiers;
941
942        match constness {
943            BoundConstness::Never => {}
944            BoundConstness::Always(span) | BoundConstness::Maybe(span) => {
945                return self
946                    .dcx()
947                    .emit_err(errors::ModifierLifetime { span, modifier: constness.as_str() });
948            }
949        }
950
951        match polarity {
952            BoundPolarity::Positive => {}
953            BoundPolarity::Negative(span) | BoundPolarity::Maybe(span) => {
954                return self
955                    .dcx()
956                    .emit_err(errors::ModifierLifetime { span, modifier: polarity.as_str() });
957            }
958        }
959
960        match asyncness {
961            BoundAsyncness::Normal => {}
962            BoundAsyncness::Async(span) => {
963                return self
964                    .dcx()
965                    .emit_err(errors::ModifierLifetime { span, modifier: asyncness.as_str() });
966            }
967        }
968
969        if let Some(span) = binder_span {
970            return self.dcx().emit_err(errors::ModifierLifetime { span, modifier: "for<...>" });
971        }
972
973        unreachable!("lifetime bound intercepted in `parse_generic_ty_bound` but no modifiers?")
974    }
975
976    /// Recover on `('lifetime)` with `(` already eaten.
977    fn recover_paren_lifetime(&mut self, lo: Span) -> PResult<'a, ()> {
978        self.expect(exp!(CloseParen))?;
979        let span = lo.to(self.prev_token.span);
980        let sugg = errors::RemoveParens { lo, hi: self.prev_token.span };
981
982        self.dcx().emit_err(errors::ParenthesizedLifetime { span, sugg });
983        Ok(())
984    }
985
986    /// Parses the modifiers that may precede a trait in a bound, e.g. `?Trait` or `[const] Trait`.
987    ///
988    /// If no modifiers are present, this does not consume any tokens.
989    ///
990    /// ```ebnf
991    /// CONSTNESS = [["["] "const" ["]"]]
992    /// ASYNCNESS = ["async"]
993    /// POLARITY = ["?" | "!"]
994    /// ```
995    ///
996    /// See `parse_generic_ty_bound` for the complete grammar of trait bound modifiers.
997    fn parse_trait_bound_modifiers(&mut self) -> PResult<'a, TraitBoundModifiers> {
998        let modifier_lo = self.token.span;
999        let constness = self.parse_bound_constness()?;
1000
1001        let asyncness = if self.token_uninterpolated_span().at_least_rust_2018()
1002            && self.eat_keyword(exp!(Async))
1003        {
1004            self.psess.gated_spans.gate(sym::async_trait_bounds, self.prev_token.span);
1005            BoundAsyncness::Async(self.prev_token.span)
1006        } else if self.may_recover()
1007            && self.token_uninterpolated_span().is_rust_2015()
1008            && self.is_kw_followed_by_ident(kw::Async)
1009        {
1010            self.bump(); // eat `async`
1011            self.dcx().emit_err(errors::AsyncBoundModifierIn2015 {
1012                span: self.prev_token.span,
1013                help: HelpUseLatestEdition::new(),
1014            });
1015            self.psess.gated_spans.gate(sym::async_trait_bounds, self.prev_token.span);
1016            BoundAsyncness::Async(self.prev_token.span)
1017        } else {
1018            BoundAsyncness::Normal
1019        };
1020        let modifier_hi = self.prev_token.span;
1021
1022        let polarity = if self.eat(exp!(Question)) {
1023            BoundPolarity::Maybe(self.prev_token.span)
1024        } else if self.eat(exp!(Bang)) {
1025            self.psess.gated_spans.gate(sym::negative_bounds, self.prev_token.span);
1026            BoundPolarity::Negative(self.prev_token.span)
1027        } else {
1028            BoundPolarity::Positive
1029        };
1030
1031        // Enforce the mutual-exclusivity of `const`/`async` and `?`/`!`.
1032        match polarity {
1033            BoundPolarity::Positive => {
1034                // All trait bound modifiers allowed to combine with positive polarity
1035            }
1036            BoundPolarity::Maybe(polarity_span) | BoundPolarity::Negative(polarity_span) => {
1037                match (asyncness, constness) {
1038                    (BoundAsyncness::Normal, BoundConstness::Never) => {
1039                        // Ok, no modifiers.
1040                    }
1041                    (_, _) => {
1042                        let constness = constness.as_str();
1043                        let asyncness = asyncness.as_str();
1044                        let glue =
1045                            if !constness.is_empty() && !asyncness.is_empty() { " " } else { "" };
1046                        let modifiers_concatenated = format!("{constness}{glue}{asyncness}");
1047                        self.dcx().emit_err(errors::PolarityAndModifiers {
1048                            polarity_span,
1049                            polarity: polarity.as_str(),
1050                            modifiers_span: modifier_lo.to(modifier_hi),
1051                            modifiers_concatenated,
1052                        });
1053                    }
1054                }
1055            }
1056        }
1057
1058        Ok(TraitBoundModifiers { constness, asyncness, polarity })
1059    }
1060
1061    pub fn parse_bound_constness(&mut self) -> PResult<'a, BoundConstness> {
1062        // FIXME(const_trait_impl): remove `~const` parser support once bootstrap has the new syntax
1063        // in rustfmt
1064        Ok(if self.eat(exp!(Tilde)) {
1065            let tilde = self.prev_token.span;
1066            self.expect_keyword(exp!(Const))?;
1067            let span = tilde.to(self.prev_token.span);
1068            self.psess.gated_spans.gate(sym::const_trait_impl, span);
1069            BoundConstness::Maybe(span)
1070        } else if self.check(exp!(OpenBracket))
1071            && self.look_ahead(1, |t| t.is_keyword(kw::Const))
1072            && self.look_ahead(2, |t| *t == token::CloseBracket)
1073        {
1074            let start = self.token.span;
1075            self.bump();
1076            self.expect_keyword(exp!(Const)).unwrap();
1077            self.bump();
1078            let span = start.to(self.prev_token.span);
1079            self.psess.gated_spans.gate(sym::const_trait_impl, span);
1080            BoundConstness::Maybe(span)
1081        } else if self.eat_keyword(exp!(Const)) {
1082            self.psess.gated_spans.gate(sym::const_trait_impl, self.prev_token.span);
1083            BoundConstness::Always(self.prev_token.span)
1084        } else {
1085            BoundConstness::Never
1086        })
1087    }
1088
1089    /// Parses a type bound according to:
1090    /// ```ebnf
1091    /// TY_BOUND = TY_BOUND_NOPAREN | (TY_BOUND_NOPAREN)
1092    /// TY_BOUND_NOPAREN = [for<GENERIC_PARAMS> CONSTNESS ASYNCNESS | POLARITY] SIMPLE_PATH
1093    /// ```
1094    ///
1095    /// For example, this grammar accepts `for<'a: 'b> [const] ?m::Trait<'a>`.
1096    fn parse_generic_ty_bound(
1097        &mut self,
1098        lo: Span,
1099        has_parens: bool,
1100        leading_token: &Token,
1101    ) -> PResult<'a, GenericBound> {
1102        let (mut lifetime_defs, binder_span) = self.parse_late_bound_lifetime_defs()?;
1103
1104        let modifiers_lo = self.token.span;
1105        let modifiers = self.parse_trait_bound_modifiers()?;
1106        let modifiers_span = modifiers_lo.to(self.prev_token.span);
1107
1108        if let Some(binder_span) = binder_span {
1109            match modifiers.polarity {
1110                BoundPolarity::Negative(polarity_span) | BoundPolarity::Maybe(polarity_span) => {
1111                    self.dcx().emit_err(errors::BinderAndPolarity {
1112                        binder_span,
1113                        polarity_span,
1114                        polarity: modifiers.polarity.as_str(),
1115                    });
1116                }
1117                BoundPolarity::Positive => {}
1118            }
1119        }
1120
1121        // Recover erroneous lifetime bound with modifiers or binder.
1122        // e.g. `T: for<'a> 'a` or `T: [const] 'a`.
1123        if self.token.is_lifetime() {
1124            let _: ErrorGuaranteed = self.error_lt_bound_with_modifiers(modifiers, binder_span);
1125            return self.parse_generic_lt_bound(lo, has_parens);
1126        }
1127
1128        if let (more_lifetime_defs, Some(binder_span)) = self.parse_late_bound_lifetime_defs()? {
1129            lifetime_defs.extend(more_lifetime_defs);
1130            self.dcx().emit_err(errors::BinderBeforeModifiers { binder_span, modifiers_span });
1131        }
1132
1133        let mut path = if self.token.is_keyword(kw::Fn)
1134            && self.look_ahead(1, |t| *t == TokenKind::OpenParen)
1135            && let Some(path) = self.recover_path_from_fn()
1136        {
1137            path
1138        } else if !self.token.is_path_start() && self.token.can_begin_type() {
1139            let ty = self.parse_ty_no_plus()?;
1140            // Instead of finding a path (a trait), we found a type.
1141            let mut err = self.dcx().struct_span_err(ty.span, "expected a trait, found type");
1142
1143            // If we can recover, try to extract a path from the type. Note
1144            // that we do not use the try operator when parsing the type because
1145            // if it fails then we get a parser error which we don't want (we're trying
1146            // to recover from errors, not make more).
1147            let path = if self.may_recover() {
1148                let (span, message, sugg, path, applicability) = match &ty.kind {
1149                    TyKind::Ptr(..) | TyKind::Ref(..)
1150                        if let TyKind::Path(_, path) = &ty.peel_refs().kind =>
1151                    {
1152                        (
1153                            ty.span.until(path.span),
1154                            "consider removing the indirection",
1155                            "",
1156                            path,
1157                            Applicability::MaybeIncorrect,
1158                        )
1159                    }
1160                    TyKind::ImplTrait(_, bounds)
1161                        if let [GenericBound::Trait(tr, ..), ..] = bounds.as_slice() =>
1162                    {
1163                        (
1164                            ty.span.until(tr.span),
1165                            "use the trait bounds directly",
1166                            "",
1167                            &tr.trait_ref.path,
1168                            Applicability::MachineApplicable,
1169                        )
1170                    }
1171                    _ => return Err(err),
1172                };
1173
1174                err.span_suggestion_verbose(span, message, sugg, applicability);
1175
1176                path.clone()
1177            } else {
1178                return Err(err);
1179            };
1180
1181            err.emit();
1182
1183            path
1184        } else {
1185            self.parse_path(PathStyle::Type)?
1186        };
1187
1188        if self.may_recover() && self.token == TokenKind::OpenParen {
1189            self.recover_fn_trait_with_lifetime_params(&mut path, &mut lifetime_defs)?;
1190        }
1191
1192        if has_parens {
1193            // Someone has written something like `&dyn (Trait + Other)`. The correct code
1194            // would be `&(dyn Trait + Other)`
1195            if self.token.is_like_plus() && leading_token.is_keyword(kw::Dyn) {
1196                let bounds = vec![];
1197                self.parse_remaining_bounds(bounds, true)?;
1198                self.expect(exp!(CloseParen))?;
1199                self.dcx().emit_err(errors::IncorrectParensTraitBounds {
1200                    span: vec![lo, self.prev_token.span],
1201                    sugg: errors::IncorrectParensTraitBoundsSugg {
1202                        wrong_span: leading_token.span.shrink_to_hi().to(lo),
1203                        new_span: leading_token.span.shrink_to_lo(),
1204                    },
1205                });
1206            } else {
1207                self.expect(exp!(CloseParen))?;
1208            }
1209        }
1210
1211        let poly_trait =
1212            PolyTraitRef::new(lifetime_defs, path, modifiers, lo.to(self.prev_token.span));
1213        Ok(GenericBound::Trait(poly_trait))
1214    }
1215
1216    // recovers a `Fn(..)` parenthesized-style path from `fn(..)`
1217    fn recover_path_from_fn(&mut self) -> Option<ast::Path> {
1218        let fn_token_span = self.token.span;
1219        self.bump();
1220        let args_lo = self.token.span;
1221        let snapshot = self.create_snapshot_for_diagnostic();
1222        match self.parse_fn_decl(|_| false, AllowPlus::No, RecoverReturnSign::OnlyFatArrow) {
1223            Ok(decl) => {
1224                self.dcx().emit_err(ExpectedFnPathFoundFnKeyword { fn_token_span });
1225                Some(ast::Path {
1226                    span: fn_token_span.to(self.prev_token.span),
1227                    segments: thin_vec![ast::PathSegment {
1228                        ident: Ident::new(sym::Fn, fn_token_span),
1229                        id: DUMMY_NODE_ID,
1230                        args: Some(P(ast::GenericArgs::Parenthesized(ast::ParenthesizedArgs {
1231                            span: args_lo.to(self.prev_token.span),
1232                            inputs: decl.inputs.iter().map(|a| a.ty.clone()).collect(),
1233                            inputs_span: args_lo.until(decl.output.span()),
1234                            output: decl.output.clone(),
1235                        }))),
1236                    }],
1237                    tokens: None,
1238                })
1239            }
1240            Err(diag) => {
1241                diag.cancel();
1242                self.restore_snapshot(snapshot);
1243                None
1244            }
1245        }
1246    }
1247
1248    /// Optionally parses `for<$generic_params>`.
1249    pub(super) fn parse_late_bound_lifetime_defs(
1250        &mut self,
1251    ) -> PResult<'a, (ThinVec<GenericParam>, Option<Span>)> {
1252        if self.eat_keyword(exp!(For)) {
1253            let lo = self.token.span;
1254            self.expect_lt()?;
1255            let params = self.parse_generic_params()?;
1256            self.expect_gt()?;
1257            // We rely on AST validation to rule out invalid cases: There must not be
1258            // type or const parameters, and parameters must not have bounds.
1259            Ok((params, Some(lo.to(self.prev_token.span))))
1260        } else {
1261            Ok((ThinVec::new(), None))
1262        }
1263    }
1264
1265    /// Recover from `Fn`-family traits (Fn, FnMut, FnOnce) with lifetime arguments
1266    /// (e.g. `FnOnce<'a>(&'a str) -> bool`). Up to generic arguments have already
1267    /// been eaten.
1268    fn recover_fn_trait_with_lifetime_params(
1269        &mut self,
1270        fn_path: &mut ast::Path,
1271        lifetime_defs: &mut ThinVec<GenericParam>,
1272    ) -> PResult<'a, ()> {
1273        let fn_path_segment = fn_path.segments.last_mut().unwrap();
1274        let generic_args = if let Some(p_args) = &fn_path_segment.args {
1275            *p_args.clone()
1276        } else {
1277            // Normally it wouldn't come here because the upstream should have parsed
1278            // generic parameters (otherwise it's impossible to call this function).
1279            return Ok(());
1280        };
1281        let lifetimes =
1282            if let ast::GenericArgs::AngleBracketed(ast::AngleBracketedArgs { span: _, args }) =
1283                &generic_args
1284            {
1285                args.into_iter()
1286                    .filter_map(|arg| {
1287                        if let ast::AngleBracketedArg::Arg(generic_arg) = arg
1288                            && let ast::GenericArg::Lifetime(lifetime) = generic_arg
1289                        {
1290                            Some(lifetime)
1291                        } else {
1292                            None
1293                        }
1294                    })
1295                    .collect()
1296            } else {
1297                Vec::new()
1298            };
1299        // Only try to recover if the trait has lifetime params.
1300        if lifetimes.is_empty() {
1301            return Ok(());
1302        }
1303
1304        // Parse `(T, U) -> R`.
1305        let inputs_lo = self.token.span;
1306        let inputs: ThinVec<_> =
1307            self.parse_fn_params(|_| false)?.into_iter().map(|input| input.ty).collect();
1308        let inputs_span = inputs_lo.to(self.prev_token.span);
1309        let output = self.parse_ret_ty(AllowPlus::No, RecoverQPath::No, RecoverReturnSign::No)?;
1310        let args = ast::ParenthesizedArgs {
1311            span: fn_path_segment.span().to(self.prev_token.span),
1312            inputs,
1313            inputs_span,
1314            output,
1315        }
1316        .into();
1317        *fn_path_segment = ast::PathSegment {
1318            ident: fn_path_segment.ident,
1319            args: Some(args),
1320            id: ast::DUMMY_NODE_ID,
1321        };
1322
1323        // Convert parsed `<'a>` in `Fn<'a>` into `for<'a>`.
1324        let mut generic_params = lifetimes
1325            .iter()
1326            .map(|lt| GenericParam {
1327                id: lt.id,
1328                ident: lt.ident,
1329                attrs: ast::AttrVec::new(),
1330                bounds: Vec::new(),
1331                is_placeholder: false,
1332                kind: ast::GenericParamKind::Lifetime,
1333                colon_span: None,
1334            })
1335            .collect::<ThinVec<GenericParam>>();
1336        lifetime_defs.append(&mut generic_params);
1337
1338        let generic_args_span = generic_args.span();
1339        let snippet = format!(
1340            "for<{}> ",
1341            lifetimes.iter().map(|lt| lt.ident.as_str()).intersperse(", ").collect::<String>(),
1342        );
1343        let before_fn_path = fn_path.span.shrink_to_lo();
1344        self.dcx()
1345            .struct_span_err(generic_args_span, "`Fn` traits cannot take lifetime parameters")
1346            .with_multipart_suggestion(
1347                "consider using a higher-ranked trait bound instead",
1348                vec![(generic_args_span, "".to_owned()), (before_fn_path, snippet)],
1349                Applicability::MaybeIncorrect,
1350            )
1351            .emit();
1352        Ok(())
1353    }
1354
1355    pub(super) fn check_lifetime(&mut self) -> bool {
1356        self.expected_token_types.insert(TokenType::Lifetime);
1357        self.token.is_lifetime()
1358    }
1359
1360    /// Parses a single lifetime `'a` or panics.
1361    pub(super) fn expect_lifetime(&mut self) -> Lifetime {
1362        if let Some((ident, is_raw)) = self.token.lifetime() {
1363            if matches!(is_raw, IdentIsRaw::No)
1364                && ident.without_first_quote().is_reserved()
1365                && ![kw::UnderscoreLifetime, kw::StaticLifetime].contains(&ident.name)
1366            {
1367                self.dcx().emit_err(errors::KeywordLifetime { span: ident.span });
1368            }
1369
1370            self.bump();
1371            Lifetime { ident, id: ast::DUMMY_NODE_ID }
1372        } else {
1373            self.dcx().span_bug(self.token.span, "not a lifetime")
1374        }
1375    }
1376
1377    pub(super) fn mk_ty(&self, span: Span, kind: TyKind) -> P<Ty> {
1378        P(Ty { kind, span, id: ast::DUMMY_NODE_ID, tokens: None })
1379    }
1380}