blob: e78054049d43e3c7441d7d9dbe941650c93b85ad [file] [log] [blame]
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001use delimited::Delimited;
David Tolnayb79ee962016-09-04 09:39:20 -07002use super::*;
3
Alex Crichton62a0a592017-05-22 13:58:53 -07004ast_enum_of_structs! {
5 /// The different kinds of types recognized by the compiler
David Tolnayfd6bf5c2017-11-12 09:41:14 -08006 pub enum Type {
Alex Crichton62a0a592017-05-22 13:58:53 -07007 /// A variable-length array (`[T]`)
David Tolnayfd6bf5c2017-11-12 09:41:14 -08008 pub Slice(TypeSlice {
David Tolnay32954ef2017-12-26 22:43:16 -05009 pub bracket_token: token::Bracket,
David Tolnay4a3f59a2017-12-28 21:21:12 -050010 pub ty: Box<Type>,
Alex Crichton62a0a592017-05-22 13:58:53 -070011 }),
12 /// A fixed length array (`[T; n]`)
David Tolnayfd6bf5c2017-11-12 09:41:14 -080013 pub Array(TypeArray {
David Tolnay32954ef2017-12-26 22:43:16 -050014 pub bracket_token: token::Bracket,
David Tolnayfd6bf5c2017-11-12 09:41:14 -080015 pub ty: Box<Type>,
David Tolnayf8db7ba2017-11-11 22:52:16 -080016 pub semi_token: Token![;],
Michael Layzelld7ee9102017-06-07 10:02:19 -040017 pub amt: Expr,
Alex Crichton62a0a592017-05-22 13:58:53 -070018 }),
19 /// A raw pointer (`*const T` or `*mut T`)
David Tolnayfd6bf5c2017-11-12 09:41:14 -080020 pub Ptr(TypePtr {
David Tolnayf8db7ba2017-11-11 22:52:16 -080021 pub star_token: Token![*],
22 pub const_token: Option<Token![const]>,
David Tolnayfd6bf5c2017-11-12 09:41:14 -080023 pub ty: Box<MutType>,
Alex Crichton62a0a592017-05-22 13:58:53 -070024 }),
25 /// A reference (`&'a T` or `&'a mut T`)
David Tolnay0a89b4d2017-11-13 00:55:45 -080026 pub Reference(TypeReference {
David Tolnayf8db7ba2017-11-11 22:52:16 -080027 pub and_token: Token![&],
Alex Crichton62a0a592017-05-22 13:58:53 -070028 pub lifetime: Option<Lifetime>,
David Tolnayfd6bf5c2017-11-12 09:41:14 -080029 pub ty: Box<MutType>,
Alex Crichton62a0a592017-05-22 13:58:53 -070030 }),
31 /// A bare function (e.g. `fn(usize) -> bool`)
David Tolnayfd6bf5c2017-11-12 09:41:14 -080032 pub BareFn(TypeBareFn {
33 pub ty: Box<BareFnType>,
Alex Crichton62a0a592017-05-22 13:58:53 -070034 }),
35 /// The never type (`!`)
David Tolnayfd6bf5c2017-11-12 09:41:14 -080036 pub Never(TypeNever {
David Tolnayf8db7ba2017-11-11 22:52:16 -080037 pub bang_token: Token![!],
Alex Crichtonccbb45d2017-05-23 10:58:24 -070038 }),
Alex Crichton62a0a592017-05-22 13:58:53 -070039 /// A tuple (`(A, B, C, D, ...)`)
David Tolnay05362582017-12-26 01:33:57 -050040 pub Tuple(TypeTuple {
David Tolnay32954ef2017-12-26 22:43:16 -050041 pub paren_token: token::Paren,
David Tolnayfd6bf5c2017-11-12 09:41:14 -080042 pub tys: Delimited<Type, Token![,]>,
Alex Crichton62a0a592017-05-22 13:58:53 -070043 }),
44 /// A path (`module::module::...::Type`), optionally
45 /// "qualified", e.g. `<Vec<T> as SomeTrait>::SomeType`.
46 ///
Nika Layzellc08227a2017-12-04 16:30:17 -050047 /// Type arguments are stored in the Path itself
David Tolnayfd6bf5c2017-11-12 09:41:14 -080048 pub Path(TypePath {
Alex Crichton62a0a592017-05-22 13:58:53 -070049 pub qself: Option<QSelf>,
50 pub path: Path,
51 }),
52 /// A trait object type `Bound1 + Bound2 + Bound3`
53 /// where `Bound` is a trait or a lifetime.
David Tolnayfd6bf5c2017-11-12 09:41:14 -080054 pub TraitObject(TypeTraitObject {
David Tolnaye45b59f2017-12-25 18:44:49 -050055 pub dyn_token: Option<Token![dyn]>,
David Tolnayfd6bf5c2017-11-12 09:41:14 -080056 pub bounds: Delimited<TypeParamBound, Token![+]>,
Alex Crichton62a0a592017-05-22 13:58:53 -070057 }),
58 /// An `impl Bound1 + Bound2 + Bound3` type
59 /// where `Bound` is a trait or a lifetime.
David Tolnayfd6bf5c2017-11-12 09:41:14 -080060 pub ImplTrait(TypeImplTrait {
David Tolnayf8db7ba2017-11-11 22:52:16 -080061 pub impl_token: Token![impl],
David Tolnayfd6bf5c2017-11-12 09:41:14 -080062 pub bounds: Delimited<TypeParamBound, Token![+]>,
Alex Crichton62a0a592017-05-22 13:58:53 -070063 }),
64 /// No-op; kept solely so that we can pretty-print faithfully
David Tolnayfd6bf5c2017-11-12 09:41:14 -080065 pub Paren(TypeParen {
David Tolnay32954ef2017-12-26 22:43:16 -050066 pub paren_token: token::Paren,
David Tolnayfd6bf5c2017-11-12 09:41:14 -080067 pub ty: Box<Type>,
Alex Crichton62a0a592017-05-22 13:58:53 -070068 }),
Michael Layzell93c36282017-06-04 20:43:14 -040069 /// No-op: kept solely so that we can pretty-print faithfully
David Tolnayfd6bf5c2017-11-12 09:41:14 -080070 pub Group(TypeGroup {
David Tolnay32954ef2017-12-26 22:43:16 -050071 pub group_token: token::Group,
David Tolnayfd6bf5c2017-11-12 09:41:14 -080072 pub ty: Box<Type>,
Michael Layzell93c36282017-06-04 20:43:14 -040073 }),
David Tolnayfd6bf5c2017-11-12 09:41:14 -080074 /// TypeKind::Infer means the type should be inferred instead of it having been
Alex Crichton62a0a592017-05-22 13:58:53 -070075 /// specified. This can appear anywhere in a type.
David Tolnayfd6bf5c2017-11-12 09:41:14 -080076 pub Infer(TypeInfer {
David Tolnayf8db7ba2017-11-11 22:52:16 -080077 pub underscore_token: Token![_],
Alex Crichtonccbb45d2017-05-23 10:58:24 -070078 }),
Alex Crichton62a0a592017-05-22 13:58:53 -070079 /// A macro in the type position.
David Tolnaydecf28d2017-11-11 11:56:45 -080080 pub Macro(Macro),
Alex Crichton62a0a592017-05-22 13:58:53 -070081 }
82}
83
84ast_struct! {
David Tolnayfd6bf5c2017-11-12 09:41:14 -080085 pub struct MutType {
David Tolnay24237fb2017-12-29 02:15:26 -050086 pub mutability: Option<Token![mut]>,
David Tolnay4a3f59a2017-12-28 21:21:12 -050087 pub ty: Type,
Alex Crichton62a0a592017-05-22 13:58:53 -070088 }
89}
90
Alex Crichton62a0a592017-05-22 13:58:53 -070091ast_struct! {
92 /// A "Path" is essentially Rust's notion of a name.
David Tolnayb79ee962016-09-04 09:39:20 -070093 ///
Alex Crichton62a0a592017-05-22 13:58:53 -070094 /// It's represented as a sequence of identifiers,
95 /// along with a bunch of supporting information.
96 ///
97 /// E.g. `std::cmp::PartialEq`
98 pub struct Path {
99 /// A `::foo` path, is relative to the crate root rather than current
100 /// module (like paths in an import).
David Tolnayf8db7ba2017-11-11 22:52:16 -0800101 pub leading_colon: Option<Token![::]>,
Alex Crichton62a0a592017-05-22 13:58:53 -0700102 /// The segments in the path: the things separated by `::`.
David Tolnayf8db7ba2017-11-11 22:52:16 -0800103 pub segments: Delimited<PathSegment, Token![::]>,
Alex Crichton62a0a592017-05-22 13:58:53 -0700104 }
David Tolnayb79ee962016-09-04 09:39:20 -0700105}
106
David Tolnay570695e2017-06-03 16:15:13 -0700107impl Path {
108 pub fn global(&self) -> bool {
109 self.leading_colon.is_some()
110 }
111}
112
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700113#[cfg(feature = "printing")]
Nika Layzell6b38b132017-10-24 23:09:39 -0400114#[cfg_attr(feature = "extra-traits", derive(Debug, Eq, PartialEq, Hash))]
115#[cfg_attr(feature = "clone-impls", derive(Clone))]
116pub struct PathTokens<'a>(pub &'a Option<QSelf>, pub &'a Path);
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700117
David Tolnaydaaf7742016-10-03 11:11:43 -0700118impl<T> From<T> for Path
David Tolnay51382052017-12-27 13:46:21 -0500119where
120 T: Into<PathSegment>,
David Tolnaydaaf7742016-10-03 11:11:43 -0700121{
David Tolnay84aa0752016-10-02 23:01:13 -0700122 fn from(segment: T) -> Self {
123 Path {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700124 leading_colon: None,
125 segments: vec![(segment.into(), None)].into(),
David Tolnay84aa0752016-10-02 23:01:13 -0700126 }
127 }
128}
129
Alex Crichton62a0a592017-05-22 13:58:53 -0700130ast_struct! {
131 /// A segment of a path: an identifier, an optional lifetime, and a set of types.
132 ///
133 /// E.g. `std`, `String` or `Box<T>`
134 pub struct PathSegment {
135 /// The identifier portion of this path segment.
136 pub ident: Ident,
Nika Layzellc08227a2017-12-04 16:30:17 -0500137 /// Type/lifetime arguments attached to this path. They come in
Alex Crichton62a0a592017-05-22 13:58:53 -0700138 /// two flavors: `Path<A,B,C>` and `Path(A,B) -> C`. Note that
139 /// this is more than just simple syntactic sugar; the use of
140 /// parens affects the region binding rules, so we preserve the
141 /// distinction.
Nika Layzellc08227a2017-12-04 16:30:17 -0500142 pub arguments: PathArguments,
Alex Crichton62a0a592017-05-22 13:58:53 -0700143 }
David Tolnayb79ee962016-09-04 09:39:20 -0700144}
145
David Tolnaydaaf7742016-10-03 11:11:43 -0700146impl<T> From<T> for PathSegment
David Tolnay51382052017-12-27 13:46:21 -0500147where
148 T: Into<Ident>,
David Tolnaydaaf7742016-10-03 11:11:43 -0700149{
David Tolnay84aa0752016-10-02 23:01:13 -0700150 fn from(ident: T) -> Self {
David Tolnayb79ee962016-09-04 09:39:20 -0700151 PathSegment {
David Tolnay84aa0752016-10-02 23:01:13 -0700152 ident: ident.into(),
Nika Layzellc08227a2017-12-04 16:30:17 -0500153 arguments: PathArguments::None,
David Tolnayb79ee962016-09-04 09:39:20 -0700154 }
155 }
156}
157
Alex Crichton62a0a592017-05-22 13:58:53 -0700158ast_enum! {
Nika Layzellc08227a2017-12-04 16:30:17 -0500159 /// Arguments of a path segment.
Alex Crichton62a0a592017-05-22 13:58:53 -0700160 ///
161 /// E.g. `<A, B>` as in `Foo<A, B>` or `(A, B)` as in `Foo(A, B)`
Nika Layzellc08227a2017-12-04 16:30:17 -0500162 pub enum PathArguments {
David Tolnay570695e2017-06-03 16:15:13 -0700163 None,
Alex Crichton62a0a592017-05-22 13:58:53 -0700164 /// The `<'a, A, B, C>` in `foo::bar::baz::<'a, A, B, C>`
Nika Layzellc08227a2017-12-04 16:30:17 -0500165 AngleBracketed(AngleBracketedGenericArguments),
Alex Crichton62a0a592017-05-22 13:58:53 -0700166 /// The `(A, B)` and `C` in `Foo(A, B) -> C`
Nika Layzellc08227a2017-12-04 16:30:17 -0500167 Parenthesized(ParenthesizedGenericArguments),
Alex Crichton62a0a592017-05-22 13:58:53 -0700168 }
David Tolnayb79ee962016-09-04 09:39:20 -0700169}
170
Nika Layzellc08227a2017-12-04 16:30:17 -0500171impl Default for PathArguments {
David Tolnay570695e2017-06-03 16:15:13 -0700172 fn default() -> Self {
Nika Layzellc08227a2017-12-04 16:30:17 -0500173 PathArguments::None
David Tolnayb79ee962016-09-04 09:39:20 -0700174 }
David Tolnay570695e2017-06-03 16:15:13 -0700175}
David Tolnay5332d4b2016-10-30 14:25:22 -0700176
Nika Layzellc08227a2017-12-04 16:30:17 -0500177impl PathArguments {
David Tolnay5332d4b2016-10-30 14:25:22 -0700178 pub fn is_empty(&self) -> bool {
179 match *self {
Nika Layzellc08227a2017-12-04 16:30:17 -0500180 PathArguments::None => true,
181 PathArguments::AngleBracketed(ref bracketed) => bracketed.args.is_empty(),
182 PathArguments::Parenthesized(_) => false,
David Tolnay5332d4b2016-10-30 14:25:22 -0700183 }
184 }
David Tolnayb79ee962016-09-04 09:39:20 -0700185}
186
Nika Layzell357885a2017-12-04 15:47:07 -0500187ast_enum! {
188 /// A individual generic argument, like `'a`, `T`, or `Item=T`.
Nika Layzellc08227a2017-12-04 16:30:17 -0500189 pub enum GenericArgument {
Nika Layzell357885a2017-12-04 15:47:07 -0500190 /// The lifetime parameters for this path segment.
191 Lifetime(Lifetime),
192 /// The type parameters for this path segment, if present.
193 Type(Type),
194 /// Bindings (equality constraints) on associated types, if present.
195 ///
196 /// E.g., `Foo<A=Bar>`.
197 TypeBinding(TypeBinding),
Nika Layzellc680e612017-12-04 19:07:20 -0500198 /// Const expression. Must be inside of a block.
199 ///
200 /// NOTE: Identity expressions are represented as Type arguments, as
201 /// they are indistinguishable syntactically.
Nika Layzellce37f332017-12-05 12:01:22 -0500202 Const(Expr),
Nika Layzell357885a2017-12-04 15:47:07 -0500203 }
204}
205
Alex Crichton62a0a592017-05-22 13:58:53 -0700206ast_struct! {
207 /// A path like `Foo<'a, T>`
Nika Layzellc08227a2017-12-04 16:30:17 -0500208 pub struct AngleBracketedGenericArguments {
David Tolnay2d4e08a2017-12-28 23:54:07 -0500209 pub colon2_token: Option<Token![::]>,
David Tolnayf8db7ba2017-11-11 22:52:16 -0800210 pub lt_token: Token![<],
Nika Layzellc08227a2017-12-04 16:30:17 -0500211 pub args: Delimited<GenericArgument, Token![,]>,
David Tolnayf8db7ba2017-11-11 22:52:16 -0800212 pub gt_token: Token![>],
Alex Crichton62a0a592017-05-22 13:58:53 -0700213 }
214}
215
216ast_struct! {
217 /// Bind a type to an associated type: `A=Foo`.
218 pub struct TypeBinding {
219 pub ident: Ident,
David Tolnayf8db7ba2017-11-11 22:52:16 -0800220 pub eq_token: Token![=],
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800221 pub ty: Type,
Alex Crichton62a0a592017-05-22 13:58:53 -0700222 }
223}
224
Alex Crichton62a0a592017-05-22 13:58:53 -0700225ast_struct! {
226 /// A path like `Foo(A,B) -> C`
Nika Layzellc08227a2017-12-04 16:30:17 -0500227 pub struct ParenthesizedGenericArguments {
David Tolnay32954ef2017-12-26 22:43:16 -0500228 pub paren_token: token::Paren,
Alex Crichton62a0a592017-05-22 13:58:53 -0700229 /// `(A, B)`
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800230 pub inputs: Delimited<Type, Token![,]>,
Alex Crichton62a0a592017-05-22 13:58:53 -0700231 /// `C`
David Tolnayf93b90d2017-11-11 19:21:26 -0800232 pub output: ReturnType,
Alex Crichton62a0a592017-05-22 13:58:53 -0700233 }
234}
235
236ast_struct! {
237 pub struct PolyTraitRef {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700238 /// The `for<'a>` in `for<'a> Foo<&'a T>`
239 pub bound_lifetimes: Option<BoundLifetimes>,
David Tolnay7d38c7e2017-12-25 22:31:50 -0500240 /// The `Foo<&'a T>` in `for<'a> Foo<&'a T>`
Alex Crichton62a0a592017-05-22 13:58:53 -0700241 pub trait_ref: Path,
242 }
243}
244
245ast_struct! {
246 /// The explicit Self type in a "qualified path". The actual
247 /// path, including the trait and the associated item, is stored
248 /// separately. `position` represents the index of the associated
249 /// item qualified with this Self type.
David Tolnayb79ee962016-09-04 09:39:20 -0700250 ///
David Tolnaybcf26022017-12-25 22:10:52 -0500251 /// ```text
Alex Crichton62a0a592017-05-22 13:58:53 -0700252 /// <Vec<T> as a::b::Trait>::AssociatedItem
David Tolnaybcf26022017-12-25 22:10:52 -0500253 /// ^~~~~~ ~~~~~~~~~~~~~~^
Alex Crichton62a0a592017-05-22 13:58:53 -0700254 /// ty position = 3
David Tolnayb79ee962016-09-04 09:39:20 -0700255 ///
Alex Crichton62a0a592017-05-22 13:58:53 -0700256 /// <Vec<T>>::AssociatedItem
David Tolnaybcf26022017-12-25 22:10:52 -0500257 /// ^~~~~~ ^
Alex Crichton62a0a592017-05-22 13:58:53 -0700258 /// ty position = 0
259 /// ```
260 pub struct QSelf {
David Tolnayf8db7ba2017-11-11 22:52:16 -0800261 pub lt_token: Token![<],
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800262 pub ty: Box<Type>,
Michael Layzell3936ceb2017-07-08 00:28:36 -0400263 pub position: usize,
David Tolnayf8db7ba2017-11-11 22:52:16 -0800264 pub as_token: Option<Token![as]>,
265 pub gt_token: Token![>],
Alex Crichton62a0a592017-05-22 13:58:53 -0700266 }
267}
268
269ast_struct! {
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800270 pub struct BareFnType {
Alex Crichton62a0a592017-05-22 13:58:53 -0700271 pub unsafety: Unsafety,
272 pub abi: Option<Abi>,
David Tolnayf8db7ba2017-11-11 22:52:16 -0800273 pub fn_token: Token![fn],
David Tolnay4a3f59a2017-12-28 21:21:12 -0500274 pub lifetimes: Option<BoundLifetimes>,
David Tolnay32954ef2017-12-26 22:43:16 -0500275 pub paren_token: token::Paren,
David Tolnayf8db7ba2017-11-11 22:52:16 -0800276 pub inputs: Delimited<BareFnArg, Token![,]>,
277 pub variadic: Option<Token![...]>,
David Tolnayf93b90d2017-11-11 19:21:26 -0800278 pub output: ReturnType,
Alex Crichton62a0a592017-05-22 13:58:53 -0700279 }
280}
281
282ast_enum! {
Alex Crichton2e0229c2017-05-23 09:34:50 -0700283 #[cfg_attr(feature = "clone-impls", derive(Copy))]
Alex Crichton62a0a592017-05-22 13:58:53 -0700284 pub enum Unsafety {
David Tolnayf8db7ba2017-11-11 22:52:16 -0800285 Unsafe(Token![unsafe]),
Alex Crichton62a0a592017-05-22 13:58:53 -0700286 Normal,
287 }
288}
289
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700290ast_struct! {
291 pub struct Abi {
David Tolnayf8db7ba2017-11-11 22:52:16 -0800292 pub extern_token: Token![extern],
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700293 pub kind: AbiKind,
294 }
295}
296
Alex Crichton62a0a592017-05-22 13:58:53 -0700297ast_enum! {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700298 pub enum AbiKind {
299 Named(Lit),
300 Default,
Alex Crichton62a0a592017-05-22 13:58:53 -0700301 }
302}
303
304ast_struct! {
305 /// An argument in a function type.
306 ///
307 /// E.g. `bar: usize` as in `fn foo(bar: usize)`
308 pub struct BareFnArg {
David Tolnayf8db7ba2017-11-11 22:52:16 -0800309 pub name: Option<(BareFnArgName, Token![:])>,
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800310 pub ty: Type,
Alex Crichton62a0a592017-05-22 13:58:53 -0700311 }
312}
313
Alex Crichton23a15f62017-08-28 12:34:23 -0700314ast_enum! {
315 /// Names of arguments in the `BareFnArg` structure
316 pub enum BareFnArgName {
317 /// Argument with the provided name
318 Named(Ident),
319 /// Argument matched with `_`
David Tolnayf8db7ba2017-11-11 22:52:16 -0800320 Wild(Token![_]),
Alex Crichton23a15f62017-08-28 12:34:23 -0700321 }
322}
Alex Crichton62a0a592017-05-22 13:58:53 -0700323
324ast_enum! {
David Tolnayf93b90d2017-11-11 19:21:26 -0800325 pub enum ReturnType {
Alex Crichton62a0a592017-05-22 13:58:53 -0700326 /// Return type is not specified.
327 ///
328 /// Functions default to `()` and
329 /// closures default to inference. Span points to where return
330 /// type would be inserted.
331 Default,
332 /// Everything else
David Tolnay4a3f59a2017-12-28 21:21:12 -0500333 Type(Token![->], Box<Type>),
Alex Crichton62a0a592017-05-22 13:58:53 -0700334 }
David Tolnayb79ee962016-09-04 09:39:20 -0700335}
336
David Tolnay86eca752016-09-04 11:26:41 -0700337#[cfg(feature = "parsing")]
David Tolnay9d8f1972016-09-04 11:58:48 -0700338pub mod parsing {
339 use super::*;
Michael Layzell92639a52017-06-01 00:07:44 -0400340 use synom::Synom;
David Tolnayda4049b2016-09-04 10:59:23 -0700341
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800342 impl Synom for Type {
Michael Layzell9bf2b002017-06-04 18:49:53 -0400343 named!(parse -> Self, call!(ambig_ty, true));
David Tolnayb79ee962016-09-04 09:39:20 -0700344
Alex Crichton954046c2017-05-30 21:49:42 -0700345 fn description() -> Option<&'static str> {
346 Some("type")
347 }
348 }
David Tolnay0047c712016-12-21 21:59:25 -0500349
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800350 impl Type {
Michael Layzell9bf2b002017-06-04 18:49:53 -0400351 /// In some positions, types may not contain the `+` character, to
352 /// disambiguate them. For example in the expression `1 as T`, T may not
353 /// contain a `+` character.
354 ///
355 /// This parser does not allow a `+`, while the default parser does.
Michael Layzell6a5a1642017-06-04 19:35:15 -0400356 named!(pub without_plus -> Self, call!(ambig_ty, false));
Michael Layzell9bf2b002017-06-04 18:49:53 -0400357 }
358
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800359 named!(ambig_ty(allow_plus: bool) -> Type, alt!(
360 syn!(TypeGroup) => { Type::Group }
Michael Layzell93c36282017-06-04 20:43:14 -0400361 |
David Tolnay05362582017-12-26 01:33:57 -0500362 // must be before TypeTuple
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800363 syn!(TypeParen) => { Type::Paren }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400364 |
David Tolnay7d38c7e2017-12-25 22:31:50 -0500365 // must be before TypePath
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800366 syn!(Macro) => { Type::Macro }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400367 |
David Tolnay7d38c7e2017-12-25 22:31:50 -0500368 // must be before TypeTraitObject
369 call!(TypePath::parse, allow_plus) => { Type::Path }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400370 |
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800371 syn!(TypeSlice) => { Type::Slice }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400372 |
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800373 syn!(TypeArray) => { Type::Array }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400374 |
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800375 syn!(TypePtr) => { Type::Ptr }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400376 |
David Tolnay0a89b4d2017-11-13 00:55:45 -0800377 syn!(TypeReference) => { Type::Reference }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400378 |
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800379 syn!(TypeBareFn) => { Type::BareFn }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400380 |
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800381 syn!(TypeNever) => { Type::Never }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400382 |
David Tolnay05362582017-12-26 01:33:57 -0500383 syn!(TypeTuple) => { Type::Tuple }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400384 |
David Tolnay7d38c7e2017-12-25 22:31:50 -0500385 // Don't try parsing more than one trait bound if we aren't allowing it
386 call!(TypeTraitObject::parse, allow_plus) => { Type::TraitObject }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400387 |
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800388 syn!(TypeImplTrait) => { Type::ImplTrait }
Alex Crichton23a15f62017-08-28 12:34:23 -0700389 |
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800390 syn!(TypeInfer) => { Type::Infer }
Michael Layzell9bf2b002017-06-04 18:49:53 -0400391 ));
392
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800393 impl Synom for TypeSlice {
Michael Layzell92639a52017-06-01 00:07:44 -0400394 named!(parse -> Self, map!(
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800395 brackets!(syn!(Type)),
396 |(ty, b)| TypeSlice {
Michael Layzell92639a52017-06-01 00:07:44 -0400397 ty: Box::new(ty),
398 bracket_token: b,
Alex Crichton954046c2017-05-30 21:49:42 -0700399 }
Michael Layzell92639a52017-06-01 00:07:44 -0400400 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700401 }
David Tolnayb79ee962016-09-04 09:39:20 -0700402
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800403 impl Synom for TypeArray {
Michael Layzell92639a52017-06-01 00:07:44 -0400404 named!(parse -> Self, map!(
405 brackets!(do_parse!(
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800406 elem: syn!(Type) >>
David Tolnayf8db7ba2017-11-11 22:52:16 -0800407 semi: punct!(;) >>
Michael Layzelld7ee9102017-06-07 10:02:19 -0400408 len: syn!(Expr) >>
Alex Crichton954046c2017-05-30 21:49:42 -0700409 (elem, semi, len)
Michael Layzell92639a52017-06-01 00:07:44 -0400410 )),
411 |((elem, semi, len), brackets)| {
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800412 TypeArray {
Michael Layzell92639a52017-06-01 00:07:44 -0400413 ty: Box::new(elem),
414 amt: len,
415 bracket_token: brackets,
416 semi_token: semi,
Alex Crichton954046c2017-05-30 21:49:42 -0700417 }
418 }
Michael Layzell92639a52017-06-01 00:07:44 -0400419 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700420 }
David Tolnayfa94b6f2016-10-05 23:26:11 -0700421
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800422 impl Synom for TypePtr {
Michael Layzell92639a52017-06-01 00:07:44 -0400423 named!(parse -> Self, do_parse!(
David Tolnayf8db7ba2017-11-11 22:52:16 -0800424 star: punct!(*) >>
Michael Layzell92639a52017-06-01 00:07:44 -0400425 mutability: alt!(
David Tolnay24237fb2017-12-29 02:15:26 -0500426 keyword!(const) => { |c| (None, Some(c)) }
Michael Layzell92639a52017-06-01 00:07:44 -0400427 |
David Tolnay24237fb2017-12-29 02:15:26 -0500428 keyword!(mut) => { |m| (Some(m), None) }
Michael Layzell92639a52017-06-01 00:07:44 -0400429 ) >>
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800430 target: call!(Type::without_plus) >>
431 (TypePtr {
Michael Layzell92639a52017-06-01 00:07:44 -0400432 const_token: mutability.1,
433 star_token: star,
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800434 ty: Box::new(MutType {
Michael Layzell92639a52017-06-01 00:07:44 -0400435 ty: target,
436 mutability: mutability.0,
437 }),
438 })
439 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700440 }
David Tolnay9d8f1972016-09-04 11:58:48 -0700441
David Tolnay0a89b4d2017-11-13 00:55:45 -0800442 impl Synom for TypeReference {
Michael Layzell92639a52017-06-01 00:07:44 -0400443 named!(parse -> Self, do_parse!(
David Tolnayf8db7ba2017-11-11 22:52:16 -0800444 amp: punct!(&) >>
Michael Layzell92639a52017-06-01 00:07:44 -0400445 life: option!(syn!(Lifetime)) >>
David Tolnay24237fb2017-12-29 02:15:26 -0500446 mutability: option!(keyword!(mut)) >>
Michael Layzell9bf2b002017-06-04 18:49:53 -0400447 // & binds tighter than +, so we don't allow + here.
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800448 target: call!(Type::without_plus) >>
David Tolnay0a89b4d2017-11-13 00:55:45 -0800449 (TypeReference {
Michael Layzell92639a52017-06-01 00:07:44 -0400450 lifetime: life,
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800451 ty: Box::new(MutType {
Michael Layzell92639a52017-06-01 00:07:44 -0400452 ty: target,
453 mutability: mutability,
454 }),
455 and_token: amp,
456 })
457 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700458 }
David Tolnay9d8f1972016-09-04 11:58:48 -0700459
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800460 impl Synom for TypeBareFn {
Michael Layzell92639a52017-06-01 00:07:44 -0400461 named!(parse -> Self, do_parse!(
462 lifetimes: option!(syn!(BoundLifetimes)) >>
463 unsafety: syn!(Unsafety) >>
464 abi: option!(syn!(Abi)) >>
David Tolnayf8db7ba2017-11-11 22:52:16 -0800465 fn_: keyword!(fn) >>
Michael Layzell92639a52017-06-01 00:07:44 -0400466 parens: parens!(do_parse!(
467 inputs: call!(Delimited::parse_terminated) >>
468 variadic: option!(cond_reduce!(inputs.is_empty() || inputs.trailing_delim(),
David Tolnayf8db7ba2017-11-11 22:52:16 -0800469 punct!(...))) >>
Michael Layzell92639a52017-06-01 00:07:44 -0400470 (inputs, variadic)
471 )) >>
David Tolnayf93b90d2017-11-11 19:21:26 -0800472 output: syn!(ReturnType) >>
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800473 (TypeBareFn {
474 ty: Box::new(BareFnType {
Michael Layzell92639a52017-06-01 00:07:44 -0400475 unsafety: unsafety,
476 abi: abi,
477 lifetimes: lifetimes,
478 output: output,
479 variadic: (parens.0).1,
480 fn_token: fn_,
481 paren_token: parens.1,
482 inputs: (parens.0).0,
483 }),
484 })
485 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700486 }
David Tolnay9d8f1972016-09-04 11:58:48 -0700487
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800488 impl Synom for TypeNever {
Michael Layzell92639a52017-06-01 00:07:44 -0400489 named!(parse -> Self, map!(
David Tolnayf8db7ba2017-11-11 22:52:16 -0800490 punct!(!),
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800491 |b| TypeNever { bang_token: b }
Michael Layzell92639a52017-06-01 00:07:44 -0400492 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700493 }
David Tolnay9d8f1972016-09-04 11:58:48 -0700494
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800495 impl Synom for TypeInfer {
Alex Crichton23a15f62017-08-28 12:34:23 -0700496 named!(parse -> Self, map!(
David Tolnayf8db7ba2017-11-11 22:52:16 -0800497 punct!(_),
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800498 |u| TypeInfer { underscore_token: u }
Alex Crichton23a15f62017-08-28 12:34:23 -0700499 ));
500 }
501
David Tolnay05362582017-12-26 01:33:57 -0500502 impl Synom for TypeTuple {
Michael Layzell92639a52017-06-01 00:07:44 -0400503 named!(parse -> Self, do_parse!(
504 data: parens!(call!(Delimited::parse_terminated)) >>
David Tolnay05362582017-12-26 01:33:57 -0500505 (TypeTuple {
Michael Layzell92639a52017-06-01 00:07:44 -0400506 tys: data.0,
507 paren_token: data.1,
Michael Layzell92639a52017-06-01 00:07:44 -0400508 })
509 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700510 }
David Tolnay9d8f1972016-09-04 11:58:48 -0700511
David Tolnay7d38c7e2017-12-25 22:31:50 -0500512 impl TypePath {
513 named!(parse(allow_plus: bool) -> Self, do_parse!(
514 qpath: qpath >>
515 parenthesized: cond!(
516 qpath.1.segments.last().unwrap().item().arguments.is_empty(),
517 option!(syn!(ParenthesizedGenericArguments))
518 ) >>
519 cond!(allow_plus, not!(peek!(punct!(+)))) >>
520 ({
521 let (qself, mut path) = qpath;
522 if let Some(Some(parenthesized)) = parenthesized {
523 let parenthesized = PathArguments::Parenthesized(parenthesized);
524 path.segments.last_mut().unwrap().item_mut().arguments = parenthesized;
525 }
526 TypePath { qself: qself, path: path }
527 })
528 ));
529 }
David Tolnay9d8f1972016-09-04 11:58:48 -0700530
David Tolnay9636c052016-10-02 17:11:17 -0700531 named!(pub qpath -> (Option<QSelf>, Path), alt!(
Alex Crichton954046c2017-05-30 21:49:42 -0700532 map!(syn!(Path), |p| (None, p))
David Tolnay9636c052016-10-02 17:11:17 -0700533 |
534 do_parse!(
David Tolnayf8db7ba2017-11-11 22:52:16 -0800535 lt: punct!(<) >>
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800536 this: syn!(Type) >>
David Tolnay7d38c7e2017-12-25 22:31:50 -0500537 path: option!(tuple!(keyword!(as), syn!(Path))) >>
David Tolnayf8db7ba2017-11-11 22:52:16 -0800538 gt: punct!(>) >>
539 colon2: punct!(::) >>
Alex Crichton954046c2017-05-30 21:49:42 -0700540 rest: call!(Delimited::parse_separated_nonempty) >>
David Tolnay9636c052016-10-02 17:11:17 -0700541 ({
Michael Layzell3936ceb2017-07-08 00:28:36 -0400542 let (pos, as_, path) = match path {
Alex Crichton954046c2017-05-30 21:49:42 -0700543 Some((as_, mut path)) => {
David Tolnay9636c052016-10-02 17:11:17 -0700544 let pos = path.segments.len();
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700545 if !path.segments.is_empty() && !path.segments.trailing_delim() {
Alex Crichton954046c2017-05-30 21:49:42 -0700546 path.segments.push_trailing(colon2);
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700547 }
Alex Crichton954046c2017-05-30 21:49:42 -0700548 for item in rest {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700549 path.segments.push(item);
550 }
Michael Layzell3936ceb2017-07-08 00:28:36 -0400551 (pos, Some(as_), path)
David Tolnay9636c052016-10-02 17:11:17 -0700552 }
553 None => {
Michael Layzell3936ceb2017-07-08 00:28:36 -0400554 (0, None, Path {
David Tolnay570695e2017-06-03 16:15:13 -0700555 leading_colon: Some(colon2),
David Tolnay9636c052016-10-02 17:11:17 -0700556 segments: rest,
David Tolnay570695e2017-06-03 16:15:13 -0700557 })
David Tolnay9636c052016-10-02 17:11:17 -0700558 }
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700559 };
560 (Some(QSelf {
David Tolnay570695e2017-06-03 16:15:13 -0700561 lt_token: lt,
562 ty: Box::new(this),
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700563 position: pos,
Michael Layzell3936ceb2017-07-08 00:28:36 -0400564 as_token: as_,
Alex Crichton954046c2017-05-30 21:49:42 -0700565 gt_token: gt,
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700566 }), path)
David Tolnay9636c052016-10-02 17:11:17 -0700567 })
568 )
David Tolnay6cd2a232016-10-24 22:41:08 -0700569 |
David Tolnayf8db7ba2017-11-11 22:52:16 -0800570 map!(keyword!(self), |s| (None, s.into()))
David Tolnay9d8f1972016-09-04 11:58:48 -0700571 ));
David Tolnayb79ee962016-09-04 09:39:20 -0700572
Nika Layzellc08227a2017-12-04 16:30:17 -0500573 impl Synom for ParenthesizedGenericArguments {
Michael Layzell92639a52017-06-01 00:07:44 -0400574 named!(parse -> Self, do_parse!(
575 data: parens!(call!(Delimited::parse_terminated)) >>
David Tolnayf93b90d2017-11-11 19:21:26 -0800576 output: syn!(ReturnType) >>
Nika Layzellc08227a2017-12-04 16:30:17 -0500577 (ParenthesizedGenericArguments {
Michael Layzell92639a52017-06-01 00:07:44 -0400578 paren_token: data.1,
579 inputs: data.0,
580 output: output,
581 })
582 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700583 }
584
David Tolnayf93b90d2017-11-11 19:21:26 -0800585 impl Synom for ReturnType {
Michael Layzell92639a52017-06-01 00:07:44 -0400586 named!(parse -> Self, alt!(
587 do_parse!(
David Tolnayf8db7ba2017-11-11 22:52:16 -0800588 arrow: punct!(->) >>
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800589 ty: syn!(Type) >>
David Tolnay4a3f59a2017-12-28 21:21:12 -0500590 (ReturnType::Type(arrow, Box::new(ty)))
Michael Layzell92639a52017-06-01 00:07:44 -0400591 )
592 |
David Tolnayf93b90d2017-11-11 19:21:26 -0800593 epsilon!() => { |_| ReturnType::Default }
Michael Layzell92639a52017-06-01 00:07:44 -0400594 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700595 }
596
David Tolnay7d38c7e2017-12-25 22:31:50 -0500597 impl TypeTraitObject {
598 // Only allow multiple trait references if allow_plus is true.
599 named!(parse(allow_plus: bool) -> Self, do_parse!(
600 dyn_token: option!(keyword!(dyn)) >>
601 bounds: alt!(
602 cond_reduce!(allow_plus, call!(Delimited::parse_terminated_nonempty))
603 |
604 syn!(TypeParamBound) => { |x| vec![x].into() }
605 ) >>
606 (TypeTraitObject {
607 dyn_token: dyn_token,
608 bounds: bounds,
609 })
610 ));
611 }
David Tolnay6414da72016-10-08 00:55:17 -0700612
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800613 impl Synom for TypeImplTrait {
Michael Layzell92639a52017-06-01 00:07:44 -0400614 named!(parse -> Self, do_parse!(
David Tolnayf8db7ba2017-11-11 22:52:16 -0800615 impl_: keyword!(impl) >>
Michael Layzell9bf2b002017-06-04 18:49:53 -0400616 // NOTE: rust-lang/rust#34511 includes discussion about whether or
617 // not + should be allowed in ImplTrait directly without ().
Nika Layzellb49a9e52017-12-05 13:31:52 -0500618 elem: call!(Delimited::parse_terminated_nonempty) >>
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800619 (TypeImplTrait {
Michael Layzell92639a52017-06-01 00:07:44 -0400620 impl_token: impl_,
621 bounds: elem,
622 })
623 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700624 }
David Tolnayb79ee962016-09-04 09:39:20 -0700625
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800626 impl Synom for TypeGroup {
Michael Layzell93c36282017-06-04 20:43:14 -0400627 named!(parse -> Self, do_parse!(
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800628 data: grouped!(syn!(Type)) >>
629 (TypeGroup {
Michael Layzell93c36282017-06-04 20:43:14 -0400630 group_token: data.1,
631 ty: Box::new(data.0),
632 })
633 ));
634 }
635
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800636 impl Synom for TypeParen {
Michael Layzell92639a52017-06-01 00:07:44 -0400637 named!(parse -> Self, do_parse!(
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800638 data: parens!(syn!(Type)) >>
639 (TypeParen {
Michael Layzell92639a52017-06-01 00:07:44 -0400640 paren_token: data.1,
641 ty: Box::new(data.0),
642 })
643 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700644 }
David Tolnayb79ee962016-09-04 09:39:20 -0700645
Alex Crichton954046c2017-05-30 21:49:42 -0700646 impl Synom for Path {
Michael Layzell92639a52017-06-01 00:07:44 -0400647 named!(parse -> Self, do_parse!(
David Tolnayf8db7ba2017-11-11 22:52:16 -0800648 colon: option!(punct!(::)) >>
David Tolnaye45b59f2017-12-25 18:44:49 -0500649 segments: call!(Delimited::<PathSegment, Token![::]>::parse_separated_nonempty) >>
650 cond_reduce!(segments.first().map_or(true, |seg| seg.item().ident != "dyn"), epsilon!()) >>
Michael Layzell92639a52017-06-01 00:07:44 -0400651 (Path {
David Tolnay570695e2017-06-03 16:15:13 -0700652 leading_colon: colon,
Michael Layzell92639a52017-06-01 00:07:44 -0400653 segments: segments,
Michael Layzell92639a52017-06-01 00:07:44 -0400654 })
655 ));
Alex Crichton36e91bf2017-07-06 14:59:56 -0700656
657 fn description() -> Option<&'static str> {
658 Some("path")
659 }
Alex Crichton954046c2017-05-30 21:49:42 -0700660 }
David Tolnay9d8f1972016-09-04 11:58:48 -0700661
Nika Layzellc680e612017-12-04 19:07:20 -0500662 #[cfg(not(feature = "full"))]
Nika Layzellc08227a2017-12-04 16:30:17 -0500663 impl Synom for GenericArgument {
Nika Layzell357885a2017-12-04 15:47:07 -0500664 named!(parse -> Self, alt!(
Nika Layzellc08227a2017-12-04 16:30:17 -0500665 call!(ty_no_eq_after) => { GenericArgument::Type }
Nika Layzell357885a2017-12-04 15:47:07 -0500666 |
Nika Layzellc08227a2017-12-04 16:30:17 -0500667 syn!(Lifetime) => { GenericArgument::Lifetime }
Nika Layzell357885a2017-12-04 15:47:07 -0500668 |
Nika Layzellc08227a2017-12-04 16:30:17 -0500669 syn!(TypeBinding) => { GenericArgument::TypeBinding }
Nika Layzell357885a2017-12-04 15:47:07 -0500670 ));
671 }
672
Nika Layzellc680e612017-12-04 19:07:20 -0500673 #[cfg(feature = "full")]
674 impl Synom for GenericArgument {
675 named!(parse -> Self, alt!(
676 call!(ty_no_eq_after) => { GenericArgument::Type }
677 |
678 syn!(Lifetime) => { GenericArgument::Lifetime }
679 |
680 syn!(TypeBinding) => { GenericArgument::TypeBinding }
681 |
David Tolnay8c91b882017-12-28 23:04:32 -0500682 syn!(ExprLit) => { |l| GenericArgument::Const(Expr::Lit(l).into()) }
Nika Layzellce37f332017-12-05 12:01:22 -0500683 |
David Tolnay8c91b882017-12-28 23:04:32 -0500684 syn!(ExprBlock) => { |b| GenericArgument::Const(Expr::Block(b).into()) }
Nika Layzellc680e612017-12-04 19:07:20 -0500685 ));
686 }
687
Nika Layzellc08227a2017-12-04 16:30:17 -0500688 impl Synom for AngleBracketedGenericArguments {
Nika Layzell357885a2017-12-04 15:47:07 -0500689 named!(parse -> Self, do_parse!(
David Tolnay2d4e08a2017-12-28 23:54:07 -0500690 colon2: option!(punct!(::)) >>
Nika Layzell357885a2017-12-04 15:47:07 -0500691 lt: punct!(<) >>
692 args: call!(Delimited::parse_terminated) >>
693 gt: punct!(>) >>
Nika Layzellc08227a2017-12-04 16:30:17 -0500694 (AngleBracketedGenericArguments {
David Tolnay2d4e08a2017-12-28 23:54:07 -0500695 colon2_token: colon2,
Nika Layzell357885a2017-12-04 15:47:07 -0500696 lt_token: lt,
697 args: args,
698 gt_token: gt,
699 })
700 ));
701 }
702
Alex Crichton954046c2017-05-30 21:49:42 -0700703 impl Synom for PathSegment {
Michael Layzell92639a52017-06-01 00:07:44 -0400704 named!(parse -> Self, alt!(
705 do_parse!(
David Tolnay570695e2017-06-03 16:15:13 -0700706 ident: syn!(Ident) >>
Nika Layzellc08227a2017-12-04 16:30:17 -0500707 arguments: syn!(AngleBracketedGenericArguments) >>
Michael Layzell92639a52017-06-01 00:07:44 -0400708 (PathSegment {
David Tolnay570695e2017-06-03 16:15:13 -0700709 ident: ident,
Nika Layzellc08227a2017-12-04 16:30:17 -0500710 arguments: PathArguments::AngleBracketed(arguments),
Michael Layzell92639a52017-06-01 00:07:44 -0400711 })
712 )
713 |
714 mod_style_path_segment
715 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700716 }
David Tolnay570695e2017-06-03 16:15:13 -0700717
David Tolnayd60cfec2017-12-29 00:21:38 -0500718 named!(pub ty_no_eq_after -> Type, terminated!(syn!(Type), not!(punct!(=))));
David Tolnay9d8f1972016-09-04 11:58:48 -0700719
Alex Crichton954046c2017-05-30 21:49:42 -0700720 impl Path {
Michael Layzell92639a52017-06-01 00:07:44 -0400721 named!(pub parse_mod_style -> Self, do_parse!(
David Tolnayf8db7ba2017-11-11 22:52:16 -0800722 colon: option!(punct!(::)) >>
Michael Layzell92639a52017-06-01 00:07:44 -0400723 segments: call!(Delimited::parse_separated_nonempty_with,
724 mod_style_path_segment) >>
725 (Path {
David Tolnay570695e2017-06-03 16:15:13 -0700726 leading_colon: colon,
Michael Layzell92639a52017-06-01 00:07:44 -0400727 segments: segments,
Michael Layzell92639a52017-06-01 00:07:44 -0400728 })
729 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700730 }
Arnavionf2dada12017-04-20 23:55:20 -0700731
732 named!(mod_style_path_segment -> PathSegment, alt!(
David Tolnay5f332a92017-12-26 00:42:45 -0500733 syn!(Ident) => { Into::into }
Arnavionf2dada12017-04-20 23:55:20 -0700734 |
David Tolnay5f332a92017-12-26 00:42:45 -0500735 keyword!(super) => { Into::into }
736 |
737 keyword!(self) => { Into::into }
738 |
739 keyword!(Self) => { Into::into }
740 |
741 keyword!(crate) => { Into::into }
Arnavionf2dada12017-04-20 23:55:20 -0700742 ));
743
Alex Crichton954046c2017-05-30 21:49:42 -0700744 impl Synom for TypeBinding {
Michael Layzell92639a52017-06-01 00:07:44 -0400745 named!(parse -> Self, do_parse!(
746 id: syn!(Ident) >>
David Tolnayf8db7ba2017-11-11 22:52:16 -0800747 eq: punct!(=) >>
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800748 ty: syn!(Type) >>
Michael Layzell92639a52017-06-01 00:07:44 -0400749 (TypeBinding {
750 ident: id,
751 eq_token: eq,
752 ty: ty,
753 })
754 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700755 }
756
757 impl Synom for PolyTraitRef {
Michael Layzell92639a52017-06-01 00:07:44 -0400758 named!(parse -> Self, do_parse!(
759 bound_lifetimes: option!(syn!(BoundLifetimes)) >>
760 trait_ref: syn!(Path) >>
761 parenthesized: option!(cond_reduce!(
Nika Layzellc08227a2017-12-04 16:30:17 -0500762 trait_ref.segments.get(trait_ref.segments.len() - 1).item().arguments.is_empty(),
763 syn!(ParenthesizedGenericArguments)
Michael Layzell92639a52017-06-01 00:07:44 -0400764 )) >>
765 ({
766 let mut trait_ref = trait_ref;
767 if let Some(parenthesized) = parenthesized {
Nika Layzellc08227a2017-12-04 16:30:17 -0500768 let parenthesized = PathArguments::Parenthesized(parenthesized);
Michael Layzell92639a52017-06-01 00:07:44 -0400769 let len = trait_ref.segments.len();
Nika Layzellc08227a2017-12-04 16:30:17 -0500770 trait_ref.segments.get_mut(len - 1).item_mut().arguments = parenthesized;
Michael Layzell92639a52017-06-01 00:07:44 -0400771 }
772 PolyTraitRef {
773 bound_lifetimes: bound_lifetimes,
774 trait_ref: trait_ref,
775 }
776 })
777 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700778 }
David Tolnay9d8f1972016-09-04 11:58:48 -0700779
Alex Crichton954046c2017-05-30 21:49:42 -0700780 impl Synom for BareFnArg {
Michael Layzell92639a52017-06-01 00:07:44 -0400781 named!(parse -> Self, do_parse!(
782 name: option!(do_parse!(
Alex Crichton23a15f62017-08-28 12:34:23 -0700783 name: syn!(BareFnArgName) >>
David Tolnayf8db7ba2017-11-11 22:52:16 -0800784 not!(punct!(::)) >>
785 colon: punct!(:) >>
Michael Layzell92639a52017-06-01 00:07:44 -0400786 (name, colon)
787 )) >>
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800788 ty: syn!(Type) >>
Michael Layzell92639a52017-06-01 00:07:44 -0400789 (BareFnArg {
790 name: name,
791 ty: ty,
792 })
793 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700794 }
David Tolnayb8d8ef52016-10-29 14:30:08 -0700795
Alex Crichton23a15f62017-08-28 12:34:23 -0700796 impl Synom for BareFnArgName {
797 named!(parse -> Self, alt!(
798 map!(syn!(Ident), BareFnArgName::Named)
799 |
David Tolnayf8db7ba2017-11-11 22:52:16 -0800800 map!(punct!(_), BareFnArgName::Wild)
Alex Crichton23a15f62017-08-28 12:34:23 -0700801 ));
802 }
803
Alex Crichton954046c2017-05-30 21:49:42 -0700804 impl Synom for Unsafety {
Michael Layzell92639a52017-06-01 00:07:44 -0400805 named!(parse -> Self, alt!(
David Tolnayf8db7ba2017-11-11 22:52:16 -0800806 keyword!(unsafe) => { Unsafety::Unsafe }
Michael Layzell92639a52017-06-01 00:07:44 -0400807 |
808 epsilon!() => { |_| Unsafety::Normal }
809 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700810 }
David Tolnayb8d8ef52016-10-29 14:30:08 -0700811
Alex Crichton954046c2017-05-30 21:49:42 -0700812 impl Synom for Abi {
Michael Layzell92639a52017-06-01 00:07:44 -0400813 named!(parse -> Self, do_parse!(
David Tolnayf8db7ba2017-11-11 22:52:16 -0800814 extern_: keyword!(extern) >>
Michael Layzell92639a52017-06-01 00:07:44 -0400815 // TODO: this parses all literals, not just strings
816 name: option!(syn!(Lit)) >>
817 (Abi {
818 extern_token: extern_,
819 kind: match name {
820 Some(name) => AbiKind::Named(name),
821 None => AbiKind::Default,
822 },
823 })
824 ));
Alex Crichton954046c2017-05-30 21:49:42 -0700825 }
David Tolnay9d8f1972016-09-04 11:58:48 -0700826}
David Tolnay87d0b442016-09-04 11:52:12 -0700827
828#[cfg(feature = "printing")]
829mod printing {
830 use super::*;
David Tolnay51382052017-12-27 13:46:21 -0500831 use quote::{ToTokens, Tokens};
David Tolnay87d0b442016-09-04 11:52:12 -0700832
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800833 impl ToTokens for TypeSlice {
David Tolnay87d0b442016-09-04 11:52:12 -0700834 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700835 self.bracket_token.surround(tokens, |tokens| {
836 self.ty.to_tokens(tokens);
837 });
Alex Crichton62a0a592017-05-22 13:58:53 -0700838 }
839 }
840
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800841 impl ToTokens for TypeArray {
Alex Crichton62a0a592017-05-22 13:58:53 -0700842 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700843 self.bracket_token.surround(tokens, |tokens| {
844 self.ty.to_tokens(tokens);
845 self.semi_token.to_tokens(tokens);
846 self.amt.to_tokens(tokens);
847 });
Alex Crichton62a0a592017-05-22 13:58:53 -0700848 }
849 }
850
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800851 impl ToTokens for TypePtr {
Alex Crichton62a0a592017-05-22 13:58:53 -0700852 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700853 self.star_token.to_tokens(tokens);
Michael Layzell3936ceb2017-07-08 00:28:36 -0400854 match self.ty.mutability {
David Tolnay24237fb2017-12-29 02:15:26 -0500855 Some(ref tok) => tok.to_tokens(tokens),
856 None => {
Alex Crichton259ee532017-07-14 06:51:02 -0700857 TokensOrDefault(&self.const_token).to_tokens(tokens);
Michael Layzell3936ceb2017-07-08 00:28:36 -0400858 }
859 }
Alex Crichton62a0a592017-05-22 13:58:53 -0700860 self.ty.ty.to_tokens(tokens);
861 }
862 }
863
David Tolnay0a89b4d2017-11-13 00:55:45 -0800864 impl ToTokens for TypeReference {
Alex Crichton62a0a592017-05-22 13:58:53 -0700865 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700866 self.and_token.to_tokens(tokens);
Alex Crichton62a0a592017-05-22 13:58:53 -0700867 self.lifetime.to_tokens(tokens);
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700868 self.ty.mutability.to_tokens(tokens);
Alex Crichton62a0a592017-05-22 13:58:53 -0700869 self.ty.ty.to_tokens(tokens);
870 }
871 }
872
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800873 impl ToTokens for TypeBareFn {
Alex Crichton62a0a592017-05-22 13:58:53 -0700874 fn to_tokens(&self, tokens: &mut Tokens) {
875 self.ty.to_tokens(tokens)
876 }
877 }
878
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800879 impl ToTokens for TypeNever {
Alex Crichton62a0a592017-05-22 13:58:53 -0700880 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700881 self.bang_token.to_tokens(tokens);
Alex Crichton62a0a592017-05-22 13:58:53 -0700882 }
883 }
884
David Tolnay05362582017-12-26 01:33:57 -0500885 impl ToTokens for TypeTuple {
Alex Crichton62a0a592017-05-22 13:58:53 -0700886 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700887 self.paren_token.surround(tokens, |tokens| {
888 self.tys.to_tokens(tokens);
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700889 })
Alex Crichton62a0a592017-05-22 13:58:53 -0700890 }
891 }
892
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800893 impl ToTokens for TypePath {
Alex Crichton62a0a592017-05-22 13:58:53 -0700894 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700895 PathTokens(&self.qself, &self.path).to_tokens(tokens);
896 }
897 }
898
899 impl<'a> ToTokens for PathTokens<'a> {
900 fn to_tokens(&self, tokens: &mut Tokens) {
901 let qself = match *self.0 {
Alex Crichton62a0a592017-05-22 13:58:53 -0700902 Some(ref qself) => qself,
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700903 None => return self.1.to_tokens(tokens),
Alex Crichton62a0a592017-05-22 13:58:53 -0700904 };
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700905 qself.lt_token.to_tokens(tokens);
Alex Crichton62a0a592017-05-22 13:58:53 -0700906 qself.ty.to_tokens(tokens);
Michael Layzell3936ceb2017-07-08 00:28:36 -0400907
908 // XXX: Gross.
909 let pos = if qself.position > 0 && qself.position >= self.1.segments.len() {
910 self.1.segments.len() - 1
911 } else {
912 qself.position
913 };
David Tolnay570695e2017-06-03 16:15:13 -0700914 let mut segments = self.1.segments.iter();
Michael Layzell3936ceb2017-07-08 00:28:36 -0400915 if pos > 0 {
Alex Crichton259ee532017-07-14 06:51:02 -0700916 TokensOrDefault(&qself.as_token).to_tokens(tokens);
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700917 self.1.leading_colon.to_tokens(tokens);
David Tolnay570695e2017-06-03 16:15:13 -0700918 for (i, segment) in (&mut segments).take(pos).enumerate() {
919 if i + 1 == pos {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700920 segment.item().to_tokens(tokens);
921 qself.gt_token.to_tokens(tokens);
922 segment.delimiter().to_tokens(tokens);
923 } else {
924 segment.to_tokens(tokens);
Alex Crichton62a0a592017-05-22 13:58:53 -0700925 }
Alex Crichton62a0a592017-05-22 13:58:53 -0700926 }
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700927 } else {
928 qself.gt_token.to_tokens(tokens);
David Tolnay570695e2017-06-03 16:15:13 -0700929 self.1.leading_colon.to_tokens(tokens);
Alex Crichton62a0a592017-05-22 13:58:53 -0700930 }
David Tolnay570695e2017-06-03 16:15:13 -0700931 for segment in segments {
Alex Crichton62a0a592017-05-22 13:58:53 -0700932 segment.to_tokens(tokens);
933 }
934 }
935 }
936
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800937 impl ToTokens for TypeTraitObject {
Alex Crichton62a0a592017-05-22 13:58:53 -0700938 fn to_tokens(&self, tokens: &mut Tokens) {
David Tolnaye45b59f2017-12-25 18:44:49 -0500939 self.dyn_token.to_tokens(tokens);
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700940 self.bounds.to_tokens(tokens);
Alex Crichton62a0a592017-05-22 13:58:53 -0700941 }
942 }
943
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800944 impl ToTokens for TypeImplTrait {
Alex Crichton62a0a592017-05-22 13:58:53 -0700945 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700946 self.impl_token.to_tokens(tokens);
947 self.bounds.to_tokens(tokens);
Alex Crichton62a0a592017-05-22 13:58:53 -0700948 }
949 }
950
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800951 impl ToTokens for TypeGroup {
Michael Layzell93c36282017-06-04 20:43:14 -0400952 fn to_tokens(&self, tokens: &mut Tokens) {
953 self.group_token.surround(tokens, |tokens| {
954 self.ty.to_tokens(tokens);
955 });
956 }
957 }
958
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800959 impl ToTokens for TypeParen {
Alex Crichton62a0a592017-05-22 13:58:53 -0700960 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700961 self.paren_token.surround(tokens, |tokens| {
962 self.ty.to_tokens(tokens);
963 });
Alex Crichton62a0a592017-05-22 13:58:53 -0700964 }
965 }
966
David Tolnayfd6bf5c2017-11-12 09:41:14 -0800967 impl ToTokens for TypeInfer {
Alex Crichton62a0a592017-05-22 13:58:53 -0700968 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700969 self.underscore_token.to_tokens(tokens);
David Tolnay87d0b442016-09-04 11:52:12 -0700970 }
971 }
972
973 impl ToTokens for Path {
974 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -0700975 self.leading_colon.to_tokens(tokens);
976 self.segments.to_tokens(tokens);
David Tolnay87d0b442016-09-04 11:52:12 -0700977 }
978 }
979
980 impl ToTokens for PathSegment {
981 fn to_tokens(&self, tokens: &mut Tokens) {
982 self.ident.to_tokens(tokens);
Nika Layzellc08227a2017-12-04 16:30:17 -0500983 self.arguments.to_tokens(tokens);
David Tolnay87d0b442016-09-04 11:52:12 -0700984 }
985 }
986
Nika Layzellc08227a2017-12-04 16:30:17 -0500987 impl ToTokens for PathArguments {
David Tolnay87d0b442016-09-04 11:52:12 -0700988 fn to_tokens(&self, tokens: &mut Tokens) {
989 match *self {
Nika Layzellc08227a2017-12-04 16:30:17 -0500990 PathArguments::None => {}
991 PathArguments::AngleBracketed(ref arguments) => {
992 arguments.to_tokens(tokens);
David Tolnay87d0b442016-09-04 11:52:12 -0700993 }
Nika Layzellc08227a2017-12-04 16:30:17 -0500994 PathArguments::Parenthesized(ref arguments) => {
995 arguments.to_tokens(tokens);
David Tolnay87d0b442016-09-04 11:52:12 -0700996 }
997 }
998 }
999 }
1000
Nika Layzellc08227a2017-12-04 16:30:17 -05001001 impl ToTokens for GenericArgument {
David Tolnaybb4ca9f2017-12-26 12:28:58 -05001002 #[cfg_attr(feature = "cargo-clippy", allow(match_same_arms))]
Nika Layzell357885a2017-12-04 15:47:07 -05001003 fn to_tokens(&self, tokens: &mut Tokens) {
1004 match *self {
Nika Layzellc08227a2017-12-04 16:30:17 -05001005 GenericArgument::Lifetime(ref lt) => lt.to_tokens(tokens),
1006 GenericArgument::Type(ref ty) => ty.to_tokens(tokens),
1007 GenericArgument::TypeBinding(ref tb) => tb.to_tokens(tokens),
David Tolnay8c91b882017-12-28 23:04:32 -05001008 GenericArgument::Const(ref e) => match *e {
1009 Expr::Lit(_) => e.to_tokens(tokens),
Nika Layzellce37f332017-12-05 12:01:22 -05001010
1011 // NOTE: We should probably support parsing blocks with only
1012 // expressions in them without the full feature for const
1013 // generics.
1014 #[cfg(feature = "full")]
David Tolnay8c91b882017-12-28 23:04:32 -05001015 Expr::Block(_) => e.to_tokens(tokens),
Nika Layzellce37f332017-12-05 12:01:22 -05001016
1017 // ERROR CORRECTION: Add braces to make sure that the
1018 // generated code is valid.
David Tolnay32954ef2017-12-26 22:43:16 -05001019 _ => token::Brace::default().surround(tokens, |tokens| {
Nika Layzellce37f332017-12-05 12:01:22 -05001020 e.to_tokens(tokens);
1021 }),
David Tolnay51382052017-12-27 13:46:21 -05001022 },
Nika Layzell357885a2017-12-04 15:47:07 -05001023 }
1024 }
1025 }
1026
Nika Layzellc08227a2017-12-04 16:30:17 -05001027 impl ToTokens for AngleBracketedGenericArguments {
David Tolnay87d0b442016-09-04 11:52:12 -07001028 fn to_tokens(&self, tokens: &mut Tokens) {
David Tolnay2d4e08a2017-12-28 23:54:07 -05001029 self.colon2_token.to_tokens(tokens);
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001030 self.lt_token.to_tokens(tokens);
Nika Layzell357885a2017-12-04 15:47:07 -05001031 self.args.to_tokens(tokens);
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001032 self.gt_token.to_tokens(tokens);
David Tolnay87d0b442016-09-04 11:52:12 -07001033 }
1034 }
1035
1036 impl ToTokens for TypeBinding {
1037 fn to_tokens(&self, tokens: &mut Tokens) {
1038 self.ident.to_tokens(tokens);
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001039 self.eq_token.to_tokens(tokens);
David Tolnay87d0b442016-09-04 11:52:12 -07001040 self.ty.to_tokens(tokens);
1041 }
1042 }
1043
Nika Layzellc08227a2017-12-04 16:30:17 -05001044 impl ToTokens for ParenthesizedGenericArguments {
David Tolnay87d0b442016-09-04 11:52:12 -07001045 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001046 self.paren_token.surround(tokens, |tokens| {
1047 self.inputs.to_tokens(tokens);
1048 });
1049 self.output.to_tokens(tokens);
1050 }
1051 }
1052
David Tolnayf93b90d2017-11-11 19:21:26 -08001053 impl ToTokens for ReturnType {
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001054 fn to_tokens(&self, tokens: &mut Tokens) {
1055 match *self {
David Tolnayf93b90d2017-11-11 19:21:26 -08001056 ReturnType::Default => {}
David Tolnay4a3f59a2017-12-28 21:21:12 -05001057 ReturnType::Type(ref arrow, ref ty) => {
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001058 arrow.to_tokens(tokens);
1059 ty.to_tokens(tokens);
1060 }
David Tolnay87d0b442016-09-04 11:52:12 -07001061 }
1062 }
1063 }
1064
1065 impl ToTokens for PolyTraitRef {
1066 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001067 self.bound_lifetimes.to_tokens(tokens);
David Tolnay87d0b442016-09-04 11:52:12 -07001068 self.trait_ref.to_tokens(tokens);
1069 }
1070 }
1071
David Tolnayfd6bf5c2017-11-12 09:41:14 -08001072 impl ToTokens for BareFnType {
David Tolnay87d0b442016-09-04 11:52:12 -07001073 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001074 self.lifetimes.to_tokens(tokens);
David Tolnayb8d8ef52016-10-29 14:30:08 -07001075 self.unsafety.to_tokens(tokens);
1076 self.abi.to_tokens(tokens);
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001077 self.fn_token.to_tokens(tokens);
1078 self.paren_token.surround(tokens, |tokens| {
1079 self.inputs.to_tokens(tokens);
David Tolnay73cc6442017-12-27 22:17:57 -05001080 if let Some(ref variadic) = self.variadic {
David Tolnay0bdb0552017-12-27 21:31:51 -05001081 if !self.inputs.empty_or_trailing() {
1082 let span = variadic.0[0];
1083 <Token![,]>::new(span).to_tokens(tokens);
1084 }
1085 variadic.to_tokens(tokens);
Michael Layzell3936ceb2017-07-08 00:28:36 -04001086 }
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001087 });
1088 self.output.to_tokens(tokens);
David Tolnay42602292016-10-01 22:25:45 -07001089 }
1090 }
1091
David Tolnay62f374c2016-10-02 13:37:00 -07001092 impl ToTokens for BareFnArg {
David Tolnay42602292016-10-01 22:25:45 -07001093 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001094 if let Some((ref name, ref colon)) = self.name {
David Tolnay62f374c2016-10-02 13:37:00 -07001095 name.to_tokens(tokens);
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001096 colon.to_tokens(tokens);
David Tolnay42602292016-10-01 22:25:45 -07001097 }
1098 self.ty.to_tokens(tokens);
David Tolnay87d0b442016-09-04 11:52:12 -07001099 }
1100 }
David Tolnayb8d8ef52016-10-29 14:30:08 -07001101
Alex Crichton23a15f62017-08-28 12:34:23 -07001102 impl ToTokens for BareFnArgName {
1103 fn to_tokens(&self, tokens: &mut Tokens) {
1104 match *self {
1105 BareFnArgName::Named(ref t) => t.to_tokens(tokens),
1106 BareFnArgName::Wild(ref t) => t.to_tokens(tokens),
1107 }
1108 }
1109 }
1110
David Tolnayb8d8ef52016-10-29 14:30:08 -07001111 impl ToTokens for Unsafety {
1112 fn to_tokens(&self, tokens: &mut Tokens) {
1113 match *self {
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001114 Unsafety::Unsafe(ref t) => t.to_tokens(tokens),
David Tolnayb8d8ef52016-10-29 14:30:08 -07001115 Unsafety::Normal => {
1116 // nothing
1117 }
1118 }
1119 }
1120 }
1121
1122 impl ToTokens for Abi {
1123 fn to_tokens(&self, tokens: &mut Tokens) {
Alex Crichtonccbb45d2017-05-23 10:58:24 -07001124 self.extern_token.to_tokens(tokens);
1125 match self.kind {
1126 AbiKind::Named(ref named) => named.to_tokens(tokens),
1127 AbiKind::Default => {}
David Tolnayb8d8ef52016-10-29 14:30:08 -07001128 }
1129 }
1130 }
David Tolnay87d0b442016-09-04 11:52:12 -07001131}