1 use super::*;
2 use crate::punctuated::Punctuated;
3 use proc_macro2::TokenStream;
4 
5 ast_enum_of_structs! {
6     /// The possible types that a Rust value could have.
7     ///
8     /// *This type is available only if Syn is built with the `"derive"` or `"full"`
9     /// feature.*
10     ///
11     /// # Syntax tree enum
12     ///
13     /// This type is a [syntax tree enum].
14     ///
15     /// [syntax tree enum]: enum.Expr.html#syntax-tree-enums
16     //
17     // TODO: change syntax-tree-enum link to an intra rustdoc link, currently
18     // blocked on https://github.com/rust-lang/rust/issues/62833
19     pub enum Type {
20         /// A fixed size array type: `[T; n]`.
21         Array(TypeArray),
22 
23         /// A bare function type: `fn(usize) -> bool`.
24         BareFn(TypeBareFn),
25 
26         /// A type contained within invisible delimiters.
27         Group(TypeGroup),
28 
29         /// An `impl Bound1 + Bound2 + Bound3` type where `Bound` is a trait or
30         /// a lifetime.
31         ImplTrait(TypeImplTrait),
32 
33         /// Indication that a type should be inferred by the compiler: `_`.
34         Infer(TypeInfer),
35 
36         /// A macro in the type position.
37         Macro(TypeMacro),
38 
39         /// The never type: `!`.
40         Never(TypeNever),
41 
42         /// A parenthesized type equivalent to the inner type.
43         Paren(TypeParen),
44 
45         /// A path like `std::slice::Iter`, optionally qualified with a
46         /// self-type as in `<Vec<T> as SomeTrait>::Associated`.
47         Path(TypePath),
48 
49         /// A raw pointer type: `*const T` or `*mut T`.
50         Ptr(TypePtr),
51 
52         /// A reference type: `&'a T` or `&'a mut T`.
53         Reference(TypeReference),
54 
55         /// A dynamically sized slice type: `[T]`.
56         Slice(TypeSlice),
57 
58         /// A trait object type `Bound1 + Bound2 + Bound3` where `Bound` is a
59         /// trait or a lifetime.
60         TraitObject(TypeTraitObject),
61 
62         /// A tuple type: `(A, B, C, String)`.
63         Tuple(TypeTuple),
64 
65         /// Tokens in type position not interpreted by Syn.
66         Verbatim(TokenStream),
67 
68         #[doc(hidden)]
69         __Nonexhaustive,
70     }
71 }
72 
73 ast_struct! {
74     /// A fixed size array type: `[T; n]`.
75     ///
76     /// *This type is available only if Syn is built with the `"derive"` or
77     /// `"full"` feature.*
78     pub struct TypeArray {
79         pub bracket_token: token::Bracket,
80         pub elem: Box<Type>,
81         pub semi_token: Token![;],
82         pub len: Expr,
83     }
84 }
85 
86 ast_struct! {
87     /// A bare function type: `fn(usize) -> bool`.
88     ///
89     /// *This type is available only if Syn is built with the `"derive"` or
90     /// `"full"` feature.*
91     pub struct TypeBareFn {
92         pub lifetimes: Option<BoundLifetimes>,
93         pub unsafety: Option<Token![unsafe]>,
94         pub abi: Option<Abi>,
95         pub fn_token: Token![fn],
96         pub paren_token: token::Paren,
97         pub inputs: Punctuated<BareFnArg, Token![,]>,
98         pub variadic: Option<Variadic>,
99         pub output: ReturnType,
100     }
101 }
102 
103 ast_struct! {
104     /// A type contained within invisible delimiters.
105     ///
106     /// *This type is available only if Syn is built with the `"derive"` or
107     /// `"full"` feature.*
108     pub struct TypeGroup {
109         pub group_token: token::Group,
110         pub elem: Box<Type>,
111     }
112 }
113 
114 ast_struct! {
115     /// An `impl Bound1 + Bound2 + Bound3` type where `Bound` is a trait or
116     /// a lifetime.
117     ///
118     /// *This type is available only if Syn is built with the `"derive"` or
119     /// `"full"` feature.*
120     pub struct TypeImplTrait {
121         pub impl_token: Token![impl],
122         pub bounds: Punctuated<TypeParamBound, Token![+]>,
123     }
124 }
125 
126 ast_struct! {
127     /// Indication that a type should be inferred by the compiler: `_`.
128     ///
129     /// *This type is available only if Syn is built with the `"derive"` or
130     /// `"full"` feature.*
131     pub struct TypeInfer {
132         pub underscore_token: Token![_],
133     }
134 }
135 
136 ast_struct! {
137     /// A macro in the type position.
138     ///
139     /// *This type is available only if Syn is built with the `"derive"` or
140     /// `"full"` feature.*
141     pub struct TypeMacro {
142         pub mac: Macro,
143     }
144 }
145 
146 ast_struct! {
147     /// The never type: `!`.
148     ///
149     /// *This type is available only if Syn is built with the `"derive"` or
150     /// `"full"` feature.*
151     pub struct TypeNever {
152         pub bang_token: Token![!],
153     }
154 }
155 
156 ast_struct! {
157     /// A parenthesized type equivalent to the inner type.
158     ///
159     /// *This type is available only if Syn is built with the `"derive"` or
160     /// `"full"` feature.*
161     pub struct TypeParen {
162         pub paren_token: token::Paren,
163         pub elem: Box<Type>,
164     }
165 }
166 
167 ast_struct! {
168     /// A path like `std::slice::Iter`, optionally qualified with a
169     /// self-type as in `<Vec<T> as SomeTrait>::Associated`.
170     ///
171     /// *This type is available only if Syn is built with the `"derive"` or
172     /// `"full"` feature.*
173     pub struct TypePath {
174         pub qself: Option<QSelf>,
175         pub path: Path,
176     }
177 }
178 
179 ast_struct! {
180     /// A raw pointer type: `*const T` or `*mut T`.
181     ///
182     /// *This type is available only if Syn is built with the `"derive"` or
183     /// `"full"` feature.*
184     pub struct TypePtr {
185         pub star_token: Token![*],
186         pub const_token: Option<Token![const]>,
187         pub mutability: Option<Token![mut]>,
188         pub elem: Box<Type>,
189     }
190 }
191 
192 ast_struct! {
193     /// A reference type: `&'a T` or `&'a mut T`.
194     ///
195     /// *This type is available only if Syn is built with the `"derive"` or
196     /// `"full"` feature.*
197     pub struct TypeReference {
198         pub and_token: Token![&],
199         pub lifetime: Option<Lifetime>,
200         pub mutability: Option<Token![mut]>,
201         pub elem: Box<Type>,
202     }
203 }
204 
205 ast_struct! {
206     /// A dynamically sized slice type: `[T]`.
207     ///
208     /// *This type is available only if Syn is built with the `"derive"` or
209     /// `"full"` feature.*
210     pub struct TypeSlice {
211         pub bracket_token: token::Bracket,
212         pub elem: Box<Type>,
213     }
214 }
215 
216 ast_struct! {
217     /// A trait object type `Bound1 + Bound2 + Bound3` where `Bound` is a
218     /// trait or a lifetime.
219     ///
220     /// *This type is available only if Syn is built with the `"derive"` or
221     /// `"full"` feature.*
222     pub struct TypeTraitObject {
223         pub dyn_token: Option<Token![dyn]>,
224         pub bounds: Punctuated<TypeParamBound, Token![+]>,
225     }
226 }
227 
228 ast_struct! {
229     /// A tuple type: `(A, B, C, String)`.
230     ///
231     /// *This type is available only if Syn is built with the `"derive"` or
232     /// `"full"` feature.*
233     pub struct TypeTuple {
234         pub paren_token: token::Paren,
235         pub elems: Punctuated<Type, Token![,]>,
236     }
237 }
238 
239 ast_struct! {
240     /// The binary interface of a function: `extern "C"`.
241     ///
242     /// *This type is available only if Syn is built with the `"derive"` or `"full"`
243     /// feature.*
244     pub struct Abi {
245         pub extern_token: Token![extern],
246         pub name: Option<LitStr>,
247     }
248 }
249 
250 ast_struct! {
251     /// An argument in a function type: the `usize` in `fn(usize) -> bool`.
252     ///
253     /// *This type is available only if Syn is built with the `"derive"` or `"full"`
254     /// feature.*
255     pub struct BareFnArg {
256         pub attrs: Vec<Attribute>,
257         pub name: Option<(Ident, Token![:])>,
258         pub ty: Type,
259     }
260 }
261 
262 ast_struct! {
263     /// The variadic argument of a foreign function.
264     ///
265     /// ```rust
266     /// # struct c_char;
267     /// # struct c_int;
268     /// #
269     /// extern "C" {
270     ///     fn printf(format: *const c_char, ...) -> c_int;
271     ///     //                               ^^^
272     /// }
273     /// ```
274     ///
275     /// *This type is available only if Syn is built with the `"derive"` or `"full"`
276     /// feature.*
277     pub struct Variadic {
278         pub attrs: Vec<Attribute>,
279         pub dots: Token![...],
280     }
281 }
282 
283 ast_enum! {
284     /// Return type of a function signature.
285     ///
286     /// *This type is available only if Syn is built with the `"derive"` or `"full"`
287     /// feature.*
288     pub enum ReturnType {
289         /// Return type is not specified.
290         ///
291         /// Functions default to `()` and closures default to type inference.
292         Default,
293         /// A particular type is returned.
294         Type(Token![->], Box<Type>),
295     }
296 }
297 
298 #[cfg(feature = "parsing")]
299 pub mod parsing {
300     use super::*;
301 
302     use crate::ext::IdentExt;
303     use crate::parse::{Parse, ParseStream, Result};
304     use crate::path;
305     use proc_macro2::{Punct, Spacing, TokenTree};
306     use std::iter::FromIterator;
307 
308     impl Parse for Type {
309         fn parse(input: ParseStream) -> Result<Self> {
310             let allow_plus = true;
311             ambig_ty(input, allow_plus)
312         }
313     }
314 
315     impl Type {
316         /// In some positions, types may not contain the `+` character, to
317         /// disambiguate them. For example in the expression `1 as T`, T may not
318         /// contain a `+` character.
319         ///
320         /// This parser does not allow a `+`, while the default parser does.
321         pub fn without_plus(input: ParseStream) -> Result<Self> {
322             let allow_plus = false;
323             ambig_ty(input, allow_plus)
324         }
325     }
326 
327     fn ambig_ty(input: ParseStream, allow_plus: bool) -> Result<Type> {
328         if input.peek(token::Group) && !input.peek2(Token![::]) && !input.peek2(Token![<]) {
329             return input.parse().map(Type::Group);
330         }
331 
332         let begin = input.fork();
333         let mut lifetimes = None::<BoundLifetimes>;
334         let mut lookahead = input.lookahead1();
335         if lookahead.peek(Token![for]) {
336             lifetimes = input.parse()?;
337             lookahead = input.lookahead1();
338             if !lookahead.peek(Ident)
339                 && !lookahead.peek(Token![fn])
340                 && !lookahead.peek(Token![unsafe])
341                 && !lookahead.peek(Token![extern])
342                 && !lookahead.peek(Token![super])
343                 && !lookahead.peek(Token![self])
344                 && !lookahead.peek(Token![Self])
345                 && !lookahead.peek(Token![crate])
346             {
347                 return Err(lookahead.error());
348             }
349         }
350 
351         if lookahead.peek(token::Paren) {
352             let content;
353             let paren_token = parenthesized!(content in input);
354             if content.is_empty() {
355                 return Ok(Type::Tuple(TypeTuple {
356                     paren_token,
357                     elems: Punctuated::new(),
358                 }));
359             }
360             if content.peek(Lifetime) {
361                 return Ok(Type::Paren(TypeParen {
362                     paren_token,
363                     elem: Box::new(Type::TraitObject(content.parse()?)),
364                 }));
365             }
366             if content.peek(Token![?]) {
367                 return Ok(Type::TraitObject(TypeTraitObject {
368                     dyn_token: None,
369                     bounds: {
370                         let mut bounds = Punctuated::new();
371                         bounds.push_value(TypeParamBound::Trait(TraitBound {
372                             paren_token: Some(paren_token),
373                             ..content.parse()?
374                         }));
375                         while let Some(plus) = input.parse()? {
376                             bounds.push_punct(plus);
377                             bounds.push_value(input.parse()?);
378                         }
379                         bounds
380                     },
381                 }));
382             }
383             let mut first: Type = content.parse()?;
384             if content.peek(Token![,]) {
385                 return Ok(Type::Tuple(TypeTuple {
386                     paren_token,
387                     elems: {
388                         let mut elems = Punctuated::new();
389                         elems.push_value(first);
390                         elems.push_punct(content.parse()?);
391                         let rest: Punctuated<Type, Token![,]> =
392                             content.parse_terminated(Parse::parse)?;
393                         elems.extend(rest);
394                         elems
395                     },
396                 }));
397             }
398             if allow_plus && input.peek(Token![+]) {
399                 loop {
400                     let first = match first {
401                         Type::Path(TypePath { qself: None, path }) => {
402                             TypeParamBound::Trait(TraitBound {
403                                 paren_token: Some(paren_token),
404                                 modifier: TraitBoundModifier::None,
405                                 lifetimes: None,
406                                 path,
407                             })
408                         }
409                         Type::TraitObject(TypeTraitObject {
410                             dyn_token: None,
411                             bounds,
412                         }) => {
413                             if bounds.len() > 1 || bounds.trailing_punct() {
414                                 first = Type::TraitObject(TypeTraitObject {
415                                     dyn_token: None,
416                                     bounds,
417                                 });
418                                 break;
419                             }
420                             match bounds.into_iter().next().unwrap() {
421                                 TypeParamBound::Trait(trait_bound) => {
422                                     TypeParamBound::Trait(TraitBound {
423                                         paren_token: Some(paren_token),
424                                         ..trait_bound
425                                     })
426                                 }
427                                 other @ TypeParamBound::Lifetime(_) => other,
428                             }
429                         }
430                         _ => break,
431                     };
432                     return Ok(Type::TraitObject(TypeTraitObject {
433                         dyn_token: None,
434                         bounds: {
435                             let mut bounds = Punctuated::new();
436                             bounds.push_value(first);
437                             while let Some(plus) = input.parse()? {
438                                 bounds.push_punct(plus);
439                                 bounds.push_value(input.parse()?);
440                             }
441                             bounds
442                         },
443                     }));
444                 }
445             }
446             Ok(Type::Paren(TypeParen {
447                 paren_token,
448                 elem: Box::new(first),
449             }))
450         } else if lookahead.peek(Token![fn])
451             || lookahead.peek(Token![unsafe])
452             || lookahead.peek(Token![extern])
453         {
454             let allow_mut_self = true;
455             if let Some(mut bare_fn) = parse_bare_fn(input, allow_mut_self)? {
456                 bare_fn.lifetimes = lifetimes;
457                 Ok(Type::BareFn(bare_fn))
458             } else {
459                 Ok(Type::Verbatim(verbatim::between(begin, input)))
460             }
461         } else if lookahead.peek(Ident)
462             || input.peek(Token![super])
463             || input.peek(Token![self])
464             || input.peek(Token![Self])
465             || input.peek(Token![crate])
466             || lookahead.peek(Token![::])
467             || lookahead.peek(Token![<])
468         {
469             if input.peek(Token![dyn]) {
470                 let mut trait_object: TypeTraitObject = input.parse()?;
471                 if lifetimes.is_some() {
472                     match trait_object.bounds.iter_mut().next().unwrap() {
473                         TypeParamBound::Trait(trait_bound) => {
474                             trait_bound.lifetimes = lifetimes;
475                         }
476                         TypeParamBound::Lifetime(_) => unreachable!(),
477                     }
478                 }
479                 return Ok(Type::TraitObject(trait_object));
480             }
481 
482             let ty: TypePath = input.parse()?;
483             if ty.qself.is_some() {
484                 return Ok(Type::Path(ty));
485             }
486 
487             if input.peek(Token![!]) && !input.peek(Token![!=]) {
488                 let mut contains_arguments = false;
489                 for segment in &ty.path.segments {
490                     match segment.arguments {
491                         PathArguments::None => {}
492                         PathArguments::AngleBracketed(_) | PathArguments::Parenthesized(_) => {
493                             contains_arguments = true;
494                         }
495                     }
496                 }
497 
498                 if !contains_arguments {
499                     let bang_token: Token![!] = input.parse()?;
500                     let (delimiter, tokens) = mac::parse_delimiter(input)?;
501                     return Ok(Type::Macro(TypeMacro {
502                         mac: Macro {
503                             path: ty.path,
504                             bang_token,
505                             delimiter,
506                             tokens,
507                         },
508                     }));
509                 }
510             }
511 
512             if lifetimes.is_some() || allow_plus && input.peek(Token![+]) {
513                 let mut bounds = Punctuated::new();
514                 bounds.push_value(TypeParamBound::Trait(TraitBound {
515                     paren_token: None,
516                     modifier: TraitBoundModifier::None,
517                     lifetimes,
518                     path: ty.path,
519                 }));
520                 if allow_plus {
521                     while input.peek(Token![+]) {
522                         bounds.push_punct(input.parse()?);
523                         if input.peek(Token![>]) {
524                             break;
525                         }
526                         bounds.push_value(input.parse()?);
527                     }
528                 }
529                 return Ok(Type::TraitObject(TypeTraitObject {
530                     dyn_token: None,
531                     bounds,
532                 }));
533             }
534 
535             Ok(Type::Path(ty))
536         } else if lookahead.peek(token::Bracket) {
537             let content;
538             let bracket_token = bracketed!(content in input);
539             let elem: Type = content.parse()?;
540             if content.peek(Token![;]) {
541                 Ok(Type::Array(TypeArray {
542                     bracket_token,
543                     elem: Box::new(elem),
544                     semi_token: content.parse()?,
545                     len: content.parse()?,
546                 }))
547             } else {
548                 Ok(Type::Slice(TypeSlice {
549                     bracket_token,
550                     elem: Box::new(elem),
551                 }))
552             }
553         } else if lookahead.peek(Token![*]) {
554             input.parse().map(Type::Ptr)
555         } else if lookahead.peek(Token![&]) {
556             input.parse().map(Type::Reference)
557         } else if lookahead.peek(Token![!]) && !input.peek(Token![=]) {
558             input.parse().map(Type::Never)
559         } else if lookahead.peek(Token![impl]) {
560             input.parse().map(Type::ImplTrait)
561         } else if lookahead.peek(Token![_]) {
562             input.parse().map(Type::Infer)
563         } else if lookahead.peek(Lifetime) {
564             input.parse().map(Type::TraitObject)
565         } else {
566             Err(lookahead.error())
567         }
568     }
569 
570     impl Parse for TypeSlice {
571         fn parse(input: ParseStream) -> Result<Self> {
572             let content;
573             Ok(TypeSlice {
574                 bracket_token: bracketed!(content in input),
575                 elem: content.parse()?,
576             })
577         }
578     }
579 
580     impl Parse for TypeArray {
581         fn parse(input: ParseStream) -> Result<Self> {
582             let content;
583             Ok(TypeArray {
584                 bracket_token: bracketed!(content in input),
585                 elem: content.parse()?,
586                 semi_token: content.parse()?,
587                 len: content.parse()?,
588             })
589         }
590     }
591 
592     impl Parse for TypePtr {
593         fn parse(input: ParseStream) -> Result<Self> {
594             let star_token: Token![*] = input.parse()?;
595 
596             let lookahead = input.lookahead1();
597             let (const_token, mutability) = if lookahead.peek(Token![const]) {
598                 (Some(input.parse()?), None)
599             } else if lookahead.peek(Token![mut]) {
600                 (None, Some(input.parse()?))
601             } else {
602                 return Err(lookahead.error());
603             };
604 
605             Ok(TypePtr {
606                 star_token,
607                 const_token,
608                 mutability,
609                 elem: Box::new(input.call(Type::without_plus)?),
610             })
611         }
612     }
613 
614     impl Parse for TypeReference {
615         fn parse(input: ParseStream) -> Result<Self> {
616             Ok(TypeReference {
617                 and_token: input.parse()?,
618                 lifetime: input.parse()?,
619                 mutability: input.parse()?,
620                 // & binds tighter than +, so we don't allow + here.
621                 elem: Box::new(input.call(Type::without_plus)?),
622             })
623         }
624     }
625 
626     impl Parse for TypeBareFn {
627         fn parse(input: ParseStream) -> Result<Self> {
628             let allow_mut_self = false;
629             parse_bare_fn(input, allow_mut_self).map(Option::unwrap)
630         }
631     }
632 
633     fn parse_bare_fn(input: ParseStream, allow_mut_self: bool) -> Result<Option<TypeBareFn>> {
634         let args;
635         let mut variadic = None;
636         let mut has_mut_self = false;
637 
638         let bare_fn = TypeBareFn {
639             lifetimes: input.parse()?,
640             unsafety: input.parse()?,
641             abi: input.parse()?,
642             fn_token: input.parse()?,
643             paren_token: parenthesized!(args in input),
644             inputs: {
645                 let mut inputs = Punctuated::new();
646 
647                 while !args.is_empty() {
648                     let attrs = args.call(Attribute::parse_outer)?;
649 
650                     if inputs.empty_or_trailing() && args.peek(Token![...]) {
651                         variadic = Some(Variadic {
652                             attrs,
653                             dots: args.parse()?,
654                         });
655                         break;
656                     }
657 
658                     if let Some(arg) = parse_bare_fn_arg(&args, allow_mut_self)? {
659                         inputs.push_value(BareFnArg { attrs, ..arg });
660                     } else {
661                         has_mut_self = true;
662                     }
663                     if args.is_empty() {
664                         break;
665                     }
666 
667                     inputs.push_punct(args.parse()?);
668                 }
669 
670                 inputs
671             },
672             variadic,
673             output: input.call(ReturnType::without_plus)?,
674         };
675 
676         if has_mut_self {
677             Ok(None)
678         } else {
679             Ok(Some(bare_fn))
680         }
681     }
682 
683     impl Parse for TypeNever {
684         fn parse(input: ParseStream) -> Result<Self> {
685             Ok(TypeNever {
686                 bang_token: input.parse()?,
687             })
688         }
689     }
690 
691     impl Parse for TypeInfer {
692         fn parse(input: ParseStream) -> Result<Self> {
693             Ok(TypeInfer {
694                 underscore_token: input.parse()?,
695             })
696         }
697     }
698 
699     impl Parse for TypeTuple {
700         fn parse(input: ParseStream) -> Result<Self> {
701             let content;
702             let paren_token = parenthesized!(content in input);
703 
704             if content.is_empty() {
705                 return Ok(TypeTuple {
706                     paren_token,
707                     elems: Punctuated::new(),
708                 });
709             }
710 
711             let first: Type = content.parse()?;
712             Ok(TypeTuple {
713                 paren_token,
714                 elems: {
715                     let mut elems = Punctuated::new();
716                     elems.push_value(first);
717                     elems.push_punct(content.parse()?);
718                     let rest: Punctuated<Type, Token![,]> =
719                         content.parse_terminated(Parse::parse)?;
720                     elems.extend(rest);
721                     elems
722                 },
723             })
724         }
725     }
726 
727     impl Parse for TypeMacro {
728         fn parse(input: ParseStream) -> Result<Self> {
729             Ok(TypeMacro {
730                 mac: input.parse()?,
731             })
732         }
733     }
734 
735     impl Parse for TypePath {
736         fn parse(input: ParseStream) -> Result<Self> {
737             let (qself, mut path) = path::parsing::qpath(input, false)?;
738 
739             if path.segments.last().unwrap().arguments.is_empty() && input.peek(token::Paren) {
740                 let args: ParenthesizedGenericArguments = input.parse()?;
741                 let parenthesized = PathArguments::Parenthesized(args);
742                 path.segments.last_mut().unwrap().arguments = parenthesized;
743             }
744 
745             Ok(TypePath { qself, path })
746         }
747     }
748 
749     impl ReturnType {
750         pub fn without_plus(input: ParseStream) -> Result<Self> {
751             let allow_plus = false;
752             Self::parse(input, allow_plus)
753         }
754 
755         #[doc(hidden)]
756         pub fn parse(input: ParseStream, allow_plus: bool) -> Result<Self> {
757             if input.peek(Token![->]) {
758                 let arrow = input.parse()?;
759                 let ty = ambig_ty(input, allow_plus)?;
760                 Ok(ReturnType::Type(arrow, Box::new(ty)))
761             } else {
762                 Ok(ReturnType::Default)
763             }
764         }
765     }
766 
767     impl Parse for ReturnType {
768         fn parse(input: ParseStream) -> Result<Self> {
769             Self::parse(input, true)
770         }
771     }
772 
773     impl Parse for TypeTraitObject {
774         fn parse(input: ParseStream) -> Result<Self> {
775             Self::parse(input, true)
776         }
777     }
778 
779     fn at_least_one_type(bounds: &Punctuated<TypeParamBound, Token![+]>) -> bool {
780         for bound in bounds {
781             if let TypeParamBound::Trait(_) = *bound {
782                 return true;
783             }
784         }
785         false
786     }
787 
788     impl TypeTraitObject {
789         pub fn without_plus(input: ParseStream) -> Result<Self> {
790             let allow_plus = false;
791             Self::parse(input, allow_plus)
792         }
793 
794         // Only allow multiple trait references if allow_plus is true.
795         #[doc(hidden)]
796         pub fn parse(input: ParseStream, allow_plus: bool) -> Result<Self> {
797             Ok(TypeTraitObject {
798                 dyn_token: input.parse()?,
799                 bounds: {
800                     let mut bounds = Punctuated::new();
801                     if allow_plus {
802                         loop {
803                             bounds.push_value(input.parse()?);
804                             if !input.peek(Token![+]) {
805                                 break;
806                             }
807                             bounds.push_punct(input.parse()?);
808                             if input.peek(Token![>]) {
809                                 break;
810                             }
811                         }
812                     } else {
813                         bounds.push_value(input.parse()?);
814                     }
815                     // Just lifetimes like `'a + 'b` is not a TraitObject.
816                     if !at_least_one_type(&bounds) {
817                         return Err(input.error("expected at least one type"));
818                     }
819                     bounds
820                 },
821             })
822         }
823     }
824 
825     impl Parse for TypeImplTrait {
826         fn parse(input: ParseStream) -> Result<Self> {
827             Ok(TypeImplTrait {
828                 impl_token: input.parse()?,
829                 // NOTE: rust-lang/rust#34511 includes discussion about whether
830                 // or not + should be allowed in ImplTrait directly without ().
831                 bounds: {
832                     let mut bounds = Punctuated::new();
833                     loop {
834                         bounds.push_value(input.parse()?);
835                         if !input.peek(Token![+]) {
836                             break;
837                         }
838                         bounds.push_punct(input.parse()?);
839                     }
840                     bounds
841                 },
842             })
843         }
844     }
845 
846     impl Parse for TypeGroup {
847         fn parse(input: ParseStream) -> Result<Self> {
848             let group = crate::group::parse_group(input)?;
849             Ok(TypeGroup {
850                 group_token: group.token,
851                 elem: group.content.parse()?,
852             })
853         }
854     }
855 
856     impl Parse for TypeParen {
857         fn parse(input: ParseStream) -> Result<Self> {
858             let allow_plus = false;
859             Self::parse(input, allow_plus)
860         }
861     }
862 
863     impl TypeParen {
864         fn parse(input: ParseStream, allow_plus: bool) -> Result<Self> {
865             let content;
866             Ok(TypeParen {
867                 paren_token: parenthesized!(content in input),
868                 elem: Box::new(ambig_ty(&content, allow_plus)?),
869             })
870         }
871     }
872 
873     impl Parse for BareFnArg {
874         fn parse(input: ParseStream) -> Result<Self> {
875             let allow_mut_self = false;
876             parse_bare_fn_arg(input, allow_mut_self).map(Option::unwrap)
877         }
878     }
879 
880     fn parse_bare_fn_arg(
881         input: ParseStream,
882         mut allow_mut_self: bool,
883     ) -> Result<Option<BareFnArg>> {
884         let mut has_mut_self = false;
885         let arg = BareFnArg {
886             attrs: input.call(Attribute::parse_outer)?,
887             name: {
888                 if (input.peek(Ident) || input.peek(Token![_]) || input.peek(Token![self]))
889                     && input.peek2(Token![:])
890                     && !input.peek2(Token![::])
891                 {
892                     let name = input.call(Ident::parse_any)?;
893                     let colon: Token![:] = input.parse()?;
894                     Some((name, colon))
895                 } else if allow_mut_self
896                     && input.peek(Token![mut])
897                     && input.peek2(Token![self])
898                     && input.peek3(Token![:])
899                     && !input.peek3(Token![::])
900                 {
901                     has_mut_self = true;
902                     allow_mut_self = false;
903                     input.parse::<Token![mut]>()?;
904                     input.parse::<Token![self]>()?;
905                     input.parse::<Token![:]>()?;
906                     None
907                 } else {
908                     None
909                 }
910             },
911             ty: if !has_mut_self && input.peek(Token![...]) {
912                 let dot3 = input.parse::<Token![...]>()?;
913                 let args = vec![
914                     TokenTree::Punct(Punct::new('.', Spacing::Joint)),
915                     TokenTree::Punct(Punct::new('.', Spacing::Joint)),
916                     TokenTree::Punct(Punct::new('.', Spacing::Alone)),
917                 ];
918                 let tokens = TokenStream::from_iter(args.into_iter().zip(&dot3.spans).map(
919                     |(mut arg, span)| {
920                         arg.set_span(*span);
921                         arg
922                     },
923                 ));
924                 Type::Verbatim(tokens)
925             } else if allow_mut_self && input.peek(Token![mut]) && input.peek2(Token![self]) {
926                 has_mut_self = true;
927                 input.parse::<Token![mut]>()?;
928                 Type::Path(TypePath {
929                     qself: None,
930                     path: input.parse::<Token![self]>()?.into(),
931                 })
932             } else {
933                 input.parse()?
934             },
935         };
936 
937         if has_mut_self {
938             Ok(None)
939         } else {
940             Ok(Some(arg))
941         }
942     }
943 
944     impl Parse for Abi {
945         fn parse(input: ParseStream) -> Result<Self> {
946             Ok(Abi {
947                 extern_token: input.parse()?,
948                 name: input.parse()?,
949             })
950         }
951     }
952 
953     impl Parse for Option<Abi> {
954         fn parse(input: ParseStream) -> Result<Self> {
955             if input.peek(Token![extern]) {
956                 input.parse().map(Some)
957             } else {
958                 Ok(None)
959             }
960         }
961     }
962 }
963 
964 #[cfg(feature = "printing")]
965 mod printing {
966     use super::*;
967 
968     use proc_macro2::TokenStream;
969     use quote::{ToTokens, TokenStreamExt};
970 
971     use crate::attr::FilterAttrs;
972     use crate::print::TokensOrDefault;
973 
974     impl ToTokens for TypeSlice {
975         fn to_tokens(&self, tokens: &mut TokenStream) {
976             self.bracket_token.surround(tokens, |tokens| {
977                 self.elem.to_tokens(tokens);
978             });
979         }
980     }
981 
982     impl ToTokens for TypeArray {
983         fn to_tokens(&self, tokens: &mut TokenStream) {
984             self.bracket_token.surround(tokens, |tokens| {
985                 self.elem.to_tokens(tokens);
986                 self.semi_token.to_tokens(tokens);
987                 self.len.to_tokens(tokens);
988             });
989         }
990     }
991 
992     impl ToTokens for TypePtr {
993         fn to_tokens(&self, tokens: &mut TokenStream) {
994             self.star_token.to_tokens(tokens);
995             match &self.mutability {
996                 Some(tok) => tok.to_tokens(tokens),
997                 None => {
998                     TokensOrDefault(&self.const_token).to_tokens(tokens);
999                 }
1000             }
1001             self.elem.to_tokens(tokens);
1002         }
1003     }
1004 
1005     impl ToTokens for TypeReference {
1006         fn to_tokens(&self, tokens: &mut TokenStream) {
1007             self.and_token.to_tokens(tokens);
1008             self.lifetime.to_tokens(tokens);
1009             self.mutability.to_tokens(tokens);
1010             self.elem.to_tokens(tokens);
1011         }
1012     }
1013 
1014     impl ToTokens for TypeBareFn {
1015         fn to_tokens(&self, tokens: &mut TokenStream) {
1016             self.lifetimes.to_tokens(tokens);
1017             self.unsafety.to_tokens(tokens);
1018             self.abi.to_tokens(tokens);
1019             self.fn_token.to_tokens(tokens);
1020             self.paren_token.surround(tokens, |tokens| {
1021                 self.inputs.to_tokens(tokens);
1022                 if let Some(variadic) = &self.variadic {
1023                     if !self.inputs.empty_or_trailing() {
1024                         let span = variadic.dots.spans[0];
1025                         Token![,](span).to_tokens(tokens);
1026                     }
1027                     variadic.to_tokens(tokens);
1028                 }
1029             });
1030             self.output.to_tokens(tokens);
1031         }
1032     }
1033 
1034     impl ToTokens for TypeNever {
1035         fn to_tokens(&self, tokens: &mut TokenStream) {
1036             self.bang_token.to_tokens(tokens);
1037         }
1038     }
1039 
1040     impl ToTokens for TypeTuple {
1041         fn to_tokens(&self, tokens: &mut TokenStream) {
1042             self.paren_token.surround(tokens, |tokens| {
1043                 self.elems.to_tokens(tokens);
1044             });
1045         }
1046     }
1047 
1048     impl ToTokens for TypePath {
1049         fn to_tokens(&self, tokens: &mut TokenStream) {
1050             private::print_path(tokens, &self.qself, &self.path);
1051         }
1052     }
1053 
1054     impl ToTokens for TypeTraitObject {
1055         fn to_tokens(&self, tokens: &mut TokenStream) {
1056             self.dyn_token.to_tokens(tokens);
1057             self.bounds.to_tokens(tokens);
1058         }
1059     }
1060 
1061     impl ToTokens for TypeImplTrait {
1062         fn to_tokens(&self, tokens: &mut TokenStream) {
1063             self.impl_token.to_tokens(tokens);
1064             self.bounds.to_tokens(tokens);
1065         }
1066     }
1067 
1068     impl ToTokens for TypeGroup {
1069         fn to_tokens(&self, tokens: &mut TokenStream) {
1070             self.group_token.surround(tokens, |tokens| {
1071                 self.elem.to_tokens(tokens);
1072             });
1073         }
1074     }
1075 
1076     impl ToTokens for TypeParen {
1077         fn to_tokens(&self, tokens: &mut TokenStream) {
1078             self.paren_token.surround(tokens, |tokens| {
1079                 self.elem.to_tokens(tokens);
1080             });
1081         }
1082     }
1083 
1084     impl ToTokens for TypeInfer {
1085         fn to_tokens(&self, tokens: &mut TokenStream) {
1086             self.underscore_token.to_tokens(tokens);
1087         }
1088     }
1089 
1090     impl ToTokens for TypeMacro {
1091         fn to_tokens(&self, tokens: &mut TokenStream) {
1092             self.mac.to_tokens(tokens);
1093         }
1094     }
1095 
1096     impl ToTokens for ReturnType {
1097         fn to_tokens(&self, tokens: &mut TokenStream) {
1098             match self {
1099                 ReturnType::Default => {}
1100                 ReturnType::Type(arrow, ty) => {
1101                     arrow.to_tokens(tokens);
1102                     ty.to_tokens(tokens);
1103                 }
1104             }
1105         }
1106     }
1107 
1108     impl ToTokens for BareFnArg {
1109         fn to_tokens(&self, tokens: &mut TokenStream) {
1110             tokens.append_all(self.attrs.outer());
1111             if let Some((name, colon)) = &self.name {
1112                 name.to_tokens(tokens);
1113                 colon.to_tokens(tokens);
1114             }
1115             self.ty.to_tokens(tokens);
1116         }
1117     }
1118 
1119     impl ToTokens for Variadic {
1120         fn to_tokens(&self, tokens: &mut TokenStream) {
1121             tokens.append_all(self.attrs.outer());
1122             self.dots.to_tokens(tokens);
1123         }
1124     }
1125 
1126     impl ToTokens for Abi {
1127         fn to_tokens(&self, tokens: &mut TokenStream) {
1128             self.extern_token.to_tokens(tokens);
1129             self.name.to_tokens(tokens);
1130         }
1131     }
1132 }
1133