blob: cf96c2ab48d5168cab99c773748d5c2ac530206a [file] [log] [blame]
David Tolnayb79ee962016-09-04 09:39:20 -07001use super::*;
2
David Tolnay771ecf42016-09-23 19:26:37 -07003/// An item
4///
5/// The name might be a dummy name in case of anonymous items
David Tolnayb79ee962016-09-04 09:39:20 -07006#[derive(Debug, Clone, Eq, PartialEq)]
7pub struct Item {
8 pub ident: Ident,
9 pub vis: Visibility,
10 pub attrs: Vec<Attribute>,
David Tolnayf38cdf62016-09-23 19:07:09 -070011 pub node: ItemKind,
David Tolnayb79ee962016-09-04 09:39:20 -070012}
13
14#[derive(Debug, Clone, Eq, PartialEq)]
David Tolnayf38cdf62016-09-23 19:07:09 -070015pub enum ItemKind {
16 /// An`extern crate` item, with optional original crate name.
17 ///
18 /// E.g. `extern crate foo` or `extern crate foo_bar as foo`
19 ExternCrate(Option<Ident>),
20 /// A use declaration (`use` or `pub use`) item.
21 ///
22 /// E.g. `use foo;`, `use foo::bar;` or `use foo::bar as FooBar;`
23 Use(Box<ViewPath>),
24 /// A static item (`static` or `pub static`).
25 ///
26 /// E.g. `static FOO: i32 = 42;` or `static FOO: &'static str = "bar";`
27 Static(Box<Ty>, Mutability, Box<Expr>),
28 /// A constant item (`const` or `pub const`).
29 ///
30 /// E.g. `const FOO: i32 = 42;`
31 Const(Box<Ty>, Box<Expr>),
32 /// A function declaration (`fn` or `pub fn`).
33 ///
34 /// E.g. `fn foo(bar: usize) -> usize { .. }`
David Tolnay42602292016-10-01 22:25:45 -070035 Fn(Box<FnDecl>, Unsafety, Constness, Option<Abi>, Generics, Box<Block>),
David Tolnayf38cdf62016-09-23 19:07:09 -070036 /// A module declaration (`mod` or `pub mod`).
37 ///
38 /// E.g. `mod foo;` or `mod foo { .. }`
David Tolnay37d10332016-10-13 20:51:04 -070039 Mod(Option<Vec<Item>>),
David Tolnayf38cdf62016-09-23 19:07:09 -070040 /// An external module (`extern` or `pub extern`).
41 ///
42 /// E.g. `extern {}` or `extern "C" {}`
43 ForeignMod(ForeignMod),
44 /// A type alias (`type` or `pub type`).
45 ///
46 /// E.g. `type Foo = Bar<u8>;`
47 Ty(Box<Ty>, Generics),
48 /// An enum definition (`enum` or `pub enum`).
49 ///
50 /// E.g. `enum Foo<A, B> { C<A>, D<B> }`
51 Enum(Vec<Variant>, Generics),
52 /// A struct definition (`struct` or `pub struct`).
53 ///
54 /// E.g. `struct Foo<A> { x: A }`
55 Struct(VariantData, Generics),
56 /// A union definition (`union` or `pub union`).
57 ///
58 /// E.g. `union Foo<A, B> { x: A, y: B }`
59 Union(VariantData, Generics),
60 /// A Trait declaration (`trait` or `pub trait`).
61 ///
62 /// E.g. `trait Foo { .. }` or `trait Foo<T> { .. }`
63 Trait(Unsafety, Generics, Vec<TyParamBound>, Vec<TraitItem>),
David Tolnay0aecb732016-10-03 23:03:50 -070064 /// Default trait implementation.
David Tolnayf38cdf62016-09-23 19:07:09 -070065 ///
66 /// E.g. `impl Trait for .. {}` or `impl<T> Trait<T> for .. {}`
67 DefaultImpl(Unsafety, Path),
68 /// An implementation.
69 ///
70 /// E.g. `impl<A> Foo<A> { .. }` or `impl<A> Trait for Foo<A> { .. }`
71 Impl(Unsafety,
David Tolnaydaaf7742016-10-03 11:11:43 -070072 ImplPolarity,
73 Generics,
74 Option<Path>, // (optional) trait this impl implements
75 Box<Ty>, // self
76 Vec<ImplItem>),
David Tolnayf38cdf62016-09-23 19:07:09 -070077 /// A macro invocation (which includes macro definition).
78 ///
79 /// E.g. `macro_rules! foo { .. }` or `foo!(..)`
80 Mac(Mac),
David Tolnayb79ee962016-09-04 09:39:20 -070081}
82
David Tolnay453cfd12016-10-23 11:00:14 -070083impl From<MacroInput> for Item {
84 fn from(input: MacroInput) -> Item {
85 Item {
86 ident: input.ident,
87 vis: input.vis,
88 attrs: input.attrs,
89 node: match input.body {
90 Body::Enum(variants) => ItemKind::Enum(variants, input.generics),
91 Body::Struct(variant_data) => ItemKind::Struct(variant_data, input.generics),
92 },
93 }
94 }
95}
96
David Tolnayb79ee962016-09-04 09:39:20 -070097#[derive(Debug, Clone, Eq, PartialEq)]
David Tolnayf38cdf62016-09-23 19:07:09 -070098pub enum ViewPath {
99 /// `foo::bar::baz as quux`
100 ///
101 /// or just
102 ///
103 /// `foo::bar::baz` (with `as baz` implicitly on the right)
David Tolnay4a057422016-10-08 00:02:31 -0700104 Simple(Path, Option<Ident>),
David Tolnayf38cdf62016-09-23 19:07:09 -0700105
106 /// `foo::bar::*`
David Tolnayaed77b02016-09-23 20:50:31 -0700107 Glob(Path),
David Tolnayf38cdf62016-09-23 19:07:09 -0700108
David Tolnayaed77b02016-09-23 20:50:31 -0700109 /// `foo::bar::{a, b, c}`
David Tolnaydaaf7742016-10-03 11:11:43 -0700110 List(Path, Vec<PathListItem>),
David Tolnayf38cdf62016-09-23 19:07:09 -0700111}
112
113#[derive(Debug, Clone, Eq, PartialEq)]
114pub struct PathListItem {
115 pub name: Ident,
116 /// renamed in list, e.g. `use foo::{bar as baz};`
117 pub rename: Option<Ident>,
118}
119
120#[derive(Debug, Copy, Clone, Eq, PartialEq)]
121pub enum Unsafety {
122 Unsafe,
123 Normal,
124}
125
126#[derive(Debug, Copy, Clone, Eq, PartialEq)]
127pub enum Constness {
128 Const,
129 NotConst,
130}
131
132#[derive(Debug, Copy, Clone, Eq, PartialEq)]
133pub enum Defaultness {
134 Default,
135 Final,
136}
137
138#[derive(Debug, Clone, Eq, PartialEq)]
139pub struct Abi(pub String);
140
141/// Foreign module declaration.
142///
David Tolnay35902302016-10-06 01:11:08 -0700143/// E.g. `extern { .. }` or `extern "C" { .. }`
David Tolnayf38cdf62016-09-23 19:07:09 -0700144#[derive(Debug, Clone, Eq, PartialEq)]
145pub struct ForeignMod {
David Tolnay35902302016-10-06 01:11:08 -0700146 pub abi: Option<Abi>,
David Tolnayf38cdf62016-09-23 19:07:09 -0700147 pub items: Vec<ForeignItem>,
148}
149
150#[derive(Debug, Clone, Eq, PartialEq)]
151pub struct ForeignItem {
David Tolnayb79ee962016-09-04 09:39:20 -0700152 pub ident: Ident,
153 pub attrs: Vec<Attribute>,
David Tolnayf38cdf62016-09-23 19:07:09 -0700154 pub node: ForeignItemKind,
David Tolnayb79ee962016-09-04 09:39:20 -0700155 pub vis: Visibility,
David Tolnayf38cdf62016-09-23 19:07:09 -0700156}
157
David Tolnay771ecf42016-09-23 19:26:37 -0700158/// An item within an `extern` block
David Tolnayf38cdf62016-09-23 19:07:09 -0700159#[derive(Debug, Clone, Eq, PartialEq)]
160pub enum ForeignItemKind {
161 /// A foreign function
162 Fn(Box<FnDecl>, Generics),
David Tolnay35902302016-10-06 01:11:08 -0700163 /// A foreign static item (`static ext: u8`)
164 Static(Box<Ty>, Mutability),
David Tolnayf38cdf62016-09-23 19:07:09 -0700165}
166
167/// Represents an item declaration within a trait declaration,
168/// possibly including a default implementation. A trait item is
169/// either required (meaning it doesn't have an implementation, just a
170/// signature) or provided (meaning it has a default implementation).
171#[derive(Debug, Clone, Eq, PartialEq)]
172pub struct TraitItem {
173 pub ident: Ident,
David Tolnayb79ee962016-09-04 09:39:20 -0700174 pub attrs: Vec<Attribute>,
David Tolnayf38cdf62016-09-23 19:07:09 -0700175 pub node: TraitItemKind,
176}
177
178#[derive(Debug, Clone, Eq, PartialEq)]
179pub enum TraitItemKind {
180 Const(Ty, Option<Expr>),
181 Method(MethodSig, Option<Block>),
182 Type(Vec<TyParamBound>, Option<Ty>),
183 Macro(Mac),
David Tolnayb79ee962016-09-04 09:39:20 -0700184}
185
David Tolnay55337722016-09-11 12:58:56 -0700186#[derive(Debug, Copy, Clone, Eq, PartialEq)]
David Tolnayf38cdf62016-09-23 19:07:09 -0700187pub enum ImplPolarity {
188 /// `impl Trait for Type`
189 Positive,
190 /// `impl !Trait for Type`
191 Negative,
David Tolnay55337722016-09-11 12:58:56 -0700192}
193
David Tolnayf38cdf62016-09-23 19:07:09 -0700194#[derive(Debug, Clone, Eq, PartialEq)]
195pub struct ImplItem {
196 pub ident: Ident,
197 pub vis: Visibility,
198 pub defaultness: Defaultness,
199 pub attrs: Vec<Attribute>,
200 pub node: ImplItemKind,
David Tolnayf4bbbd92016-09-23 14:41:55 -0700201}
202
David Tolnayf38cdf62016-09-23 19:07:09 -0700203#[derive(Debug, Clone, Eq, PartialEq)]
204pub enum ImplItemKind {
205 Const(Ty, Expr),
206 Method(MethodSig, Block),
207 Type(Ty),
208 Macro(Mac),
David Tolnay9d8f1972016-09-04 11:58:48 -0700209}
David Tolnayd5025812016-09-04 14:21:46 -0700210
David Tolnayf38cdf62016-09-23 19:07:09 -0700211/// Represents a method's signature in a trait declaration,
212/// or in an implementation.
213#[derive(Debug, Clone, Eq, PartialEq)]
214pub struct MethodSig {
215 pub unsafety: Unsafety,
216 pub constness: Constness,
David Tolnay0aecb732016-10-03 23:03:50 -0700217 pub abi: Option<Abi>,
David Tolnayf38cdf62016-09-23 19:07:09 -0700218 pub decl: FnDecl,
219 pub generics: Generics,
David Tolnayd5025812016-09-04 14:21:46 -0700220}
David Tolnayedf2b992016-09-23 20:43:45 -0700221
David Tolnay62f374c2016-10-02 13:37:00 -0700222/// Header (not the body) of a function declaration.
223///
224/// E.g. `fn foo(bar: baz)`
225#[derive(Debug, Clone, Eq, PartialEq)]
226pub struct FnDecl {
227 pub inputs: Vec<FnArg>,
228 pub output: FunctionRetTy,
229}
230
231/// An argument in a function header.
232///
233/// E.g. `bar: usize` as in `fn foo(bar: usize)`
234#[derive(Debug, Clone, Eq, PartialEq)]
David Tolnayca085422016-10-04 00:12:38 -0700235pub enum FnArg {
236 SelfRef(Option<Lifetime>, Mutability),
237 SelfValue(Mutability),
238 Captured(Pat, Ty),
239 Ignored(Ty),
David Tolnay62f374c2016-10-02 13:37:00 -0700240}
241
David Tolnayedf2b992016-09-23 20:43:45 -0700242#[cfg(feature = "parsing")]
243pub mod parsing {
244 use super::*;
David Tolnay4a057422016-10-08 00:02:31 -0700245 use {DelimToken, FunctionRetTy, Generics, Ident, Mac, Path, TokenTree, VariantData, Visibility};
David Tolnay4a51dc72016-10-01 00:40:31 -0700246 use attr::parsing::outer_attr;
David Tolnay2f9fa632016-10-03 22:08:48 -0700247 use data::parsing::{struct_like_body, visibility};
David Tolnay62f374c2016-10-02 13:37:00 -0700248 use expr::parsing::{block, expr, pat};
David Tolnayca085422016-10-04 00:12:38 -0700249 use generics::parsing::{generics, lifetime, ty_param_bound, where_clause};
David Tolnayedf2b992016-09-23 20:43:45 -0700250 use ident::parsing::ident;
David Tolnay42602292016-10-01 22:25:45 -0700251 use lit::parsing::quoted_string;
David Tolnay84aa0752016-10-02 23:01:13 -0700252 use mac::parsing::delimited;
David Tolnayedf2b992016-09-23 20:43:45 -0700253 use macro_input::{Body, MacroInput};
254 use macro_input::parsing::macro_input;
David Tolnayf94e2362016-10-04 00:29:51 -0700255 use ty::parsing::{mutability, path, ty};
David Tolnayedf2b992016-09-23 20:43:45 -0700256
257 named!(pub item -> Item, alt!(
David Tolnaya96a3fa2016-09-24 07:17:42 -0700258 item_extern_crate
David Tolnay4a057422016-10-08 00:02:31 -0700259 |
260 item_use
David Tolnay47a877c2016-10-01 16:50:55 -0700261 |
262 item_static
263 |
264 item_const
David Tolnay42602292016-10-01 22:25:45 -0700265 |
266 item_fn
David Tolnay35902302016-10-06 01:11:08 -0700267 |
268 item_mod
269 |
270 item_foreign_mod
David Tolnay3cf52982016-10-01 17:11:37 -0700271 |
272 item_ty
David Tolnayedf2b992016-09-23 20:43:45 -0700273 |
David Tolnaya96a3fa2016-09-24 07:17:42 -0700274 item_struct_or_enum
David Tolnay2f9fa632016-10-03 22:08:48 -0700275 |
276 item_union
David Tolnay0aecb732016-10-03 23:03:50 -0700277 |
278 item_trait
David Tolnayf94e2362016-10-04 00:29:51 -0700279 |
280 item_default_impl
David Tolnay4c9be372016-10-06 00:47:37 -0700281 |
282 item_impl
David Tolnay84aa0752016-10-02 23:01:13 -0700283 |
284 item_mac
285 ));
286
David Tolnay453cfd12016-10-23 11:00:14 -0700287 named!(pub items -> Vec<Item>, many0!(item));
288
David Tolnay84aa0752016-10-02 23:01:13 -0700289 named!(item_mac -> Item, do_parse!(
290 attrs: many0!(outer_attr) >>
291 path: ident >>
292 punct!("!") >>
293 name: option!(ident) >>
294 body: delimited >>
David Tolnay1a8b3522016-10-08 22:27:00 -0700295 cond!(match body.delim {
296 DelimToken::Paren | DelimToken::Bracket => true,
297 DelimToken::Brace => false,
298 }, punct!(";")) >>
David Tolnay84aa0752016-10-02 23:01:13 -0700299 (Item {
300 ident: name.unwrap_or_else(|| Ident::new("")),
301 vis: Visibility::Inherited,
302 attrs: attrs,
303 node: ItemKind::Mac(Mac {
304 path: path.into(),
305 tts: vec![TokenTree::Delimited(body)],
306 }),
307 })
David Tolnayedf2b992016-09-23 20:43:45 -0700308 ));
309
David Tolnaya96a3fa2016-09-24 07:17:42 -0700310 named!(item_extern_crate -> Item, do_parse!(
David Tolnay4a51dc72016-10-01 00:40:31 -0700311 attrs: many0!(outer_attr) >>
David Tolnayedf2b992016-09-23 20:43:45 -0700312 vis: visibility >>
David Tolnay10413f02016-09-30 09:12:02 -0700313 keyword!("extern") >>
314 keyword!("crate") >>
David Tolnayedf2b992016-09-23 20:43:45 -0700315 id: ident >>
316 rename: option!(preceded!(
David Tolnay10413f02016-09-30 09:12:02 -0700317 keyword!("as"),
David Tolnayedf2b992016-09-23 20:43:45 -0700318 ident
319 )) >>
320 punct!(";") >>
321 ({
322 let (name, original_name) = match rename {
323 Some(rename) => (rename, Some(id)),
324 None => (id, None),
325 };
326 Item {
327 ident: name,
328 vis: vis,
329 attrs: attrs,
330 node: ItemKind::ExternCrate(original_name),
331 }
332 })
333 ));
334
David Tolnay4a057422016-10-08 00:02:31 -0700335 named!(item_use -> Item, do_parse!(
336 attrs: many0!(outer_attr) >>
337 vis: visibility >>
338 keyword!("use") >>
339 what: view_path >>
340 punct!(";") >>
341 (Item {
342 ident: "".into(),
343 vis: vis,
344 attrs: attrs,
345 node: ItemKind::Use(Box::new(what)),
346 })
347 ));
348
349 named!(view_path -> ViewPath, alt!(
350 view_path_glob
351 |
352 view_path_list
353 |
354 view_path_list_root
355 |
356 view_path_simple // must be last
357 ));
358
359
360 named!(view_path_simple -> ViewPath, do_parse!(
361 path: path >>
362 rename: option!(preceded!(keyword!("as"), ident)) >>
363 (ViewPath::Simple(path, rename))
364 ));
365
366 named!(view_path_glob -> ViewPath, do_parse!(
367 path: path >>
368 punct!("::") >>
369 punct!("*") >>
370 (ViewPath::Glob(path))
371 ));
372
373 named!(view_path_list -> ViewPath, do_parse!(
374 path: path >>
375 punct!("::") >>
376 punct!("{") >>
377 items: separated_nonempty_list!(punct!(","), path_list_item) >>
378 punct!("}") >>
379 (ViewPath::List(path, items))
380 ));
381
382 named!(view_path_list_root -> ViewPath, do_parse!(
383 global: option!(punct!("::")) >>
384 punct!("{") >>
385 items: separated_nonempty_list!(punct!(","), path_list_item) >>
386 punct!("}") >>
387 (ViewPath::List(Path {
388 global: global.is_some(),
389 segments: Vec::new(),
390 }, items))
391 ));
392
393 named!(path_list_item -> PathListItem, do_parse!(
David Tolnaye6e42542016-10-24 22:37:11 -0700394 name: alt!(
395 ident
396 |
397 map!(keyword!("self"), Into::into)
398 ) >>
David Tolnay4a057422016-10-08 00:02:31 -0700399 rename: option!(preceded!(keyword!("as"), ident)) >>
400 (PathListItem {
401 name: name,
402 rename: rename,
403 })
404 ));
405
David Tolnay47a877c2016-10-01 16:50:55 -0700406 named!(item_static -> Item, do_parse!(
407 attrs: many0!(outer_attr) >>
408 vis: visibility >>
409 keyword!("static") >>
410 mutability: mutability >>
411 id: ident >>
412 punct!(":") >>
413 ty: ty >>
414 punct!("=") >>
415 value: expr >>
416 punct!(";") >>
417 (Item {
418 ident: id,
419 vis: vis,
420 attrs: attrs,
421 node: ItemKind::Static(Box::new(ty), mutability, Box::new(value)),
422 })
423 ));
424
425 named!(item_const -> Item, do_parse!(
426 attrs: many0!(outer_attr) >>
427 vis: visibility >>
428 keyword!("const") >>
429 id: ident >>
430 punct!(":") >>
431 ty: ty >>
432 punct!("=") >>
433 value: expr >>
434 punct!(";") >>
435 (Item {
436 ident: id,
437 vis: vis,
438 attrs: attrs,
439 node: ItemKind::Const(Box::new(ty), Box::new(value)),
440 })
441 ));
442
David Tolnay42602292016-10-01 22:25:45 -0700443 named!(item_fn -> Item, do_parse!(
444 attrs: many0!(outer_attr) >>
445 vis: visibility >>
446 constness: constness >>
447 unsafety: unsafety >>
448 abi: option!(preceded!(keyword!("extern"), quoted_string)) >>
449 keyword!("fn") >>
450 name: ident >>
451 generics: generics >>
452 punct!("(") >>
David Tolnayff46fd22016-10-08 13:53:28 -0700453 inputs: terminated_list!(punct!(","), fn_arg) >>
David Tolnay42602292016-10-01 22:25:45 -0700454 punct!(")") >>
455 ret: option!(preceded!(punct!("->"), ty)) >>
456 where_clause: where_clause >>
457 body: block >>
458 (Item {
459 ident: name,
460 vis: vis,
461 attrs: attrs,
462 node: ItemKind::Fn(
463 Box::new(FnDecl {
464 inputs: inputs,
465 output: ret.map(FunctionRetTy::Ty).unwrap_or(FunctionRetTy::Default),
466 }),
467 unsafety,
468 constness,
469 abi.map(Abi),
470 Generics {
471 where_clause: where_clause,
472 .. generics
473 },
474 Box::new(body),
475 ),
476 })
477 ));
478
David Tolnayca085422016-10-04 00:12:38 -0700479 named!(fn_arg -> FnArg, alt!(
480 do_parse!(
481 punct!("&") >>
482 lt: option!(lifetime) >>
483 mutability: mutability >>
484 keyword!("self") >>
485 (FnArg::SelfRef(lt, mutability))
486 )
487 |
488 do_parse!(
489 mutability: mutability >>
490 keyword!("self") >>
491 (FnArg::SelfValue(mutability))
492 )
493 |
494 do_parse!(
495 pat: pat >>
496 punct!(":") >>
497 ty: ty >>
498 (FnArg::Captured(pat, ty))
499 )
500 |
501 ty => { FnArg::Ignored }
David Tolnay62f374c2016-10-02 13:37:00 -0700502 ));
503
David Tolnay35902302016-10-06 01:11:08 -0700504 named!(item_mod -> Item, do_parse!(
505 attrs: many0!(outer_attr) >>
506 vis: visibility >>
507 keyword!("mod") >>
508 id: ident >>
David Tolnay37d10332016-10-13 20:51:04 -0700509 items: alt!(
510 punct!(";") => { |_| None }
511 |
David Tolnay453cfd12016-10-23 11:00:14 -0700512 delimited!(punct!("{"), items, punct!("}")) => { Some }
David Tolnay37d10332016-10-13 20:51:04 -0700513 ) >>
David Tolnay35902302016-10-06 01:11:08 -0700514 (Item {
515 ident: id,
516 vis: vis,
517 attrs: attrs,
518 node: ItemKind::Mod(items),
519 })
520 ));
521
522 named!(item_foreign_mod -> Item, do_parse!(
523 attrs: many0!(outer_attr) >>
524 keyword!("extern") >>
525 abi: option!(quoted_string) >>
526 punct!("{") >>
527 items: many0!(foreign_item) >>
528 punct!("}") >>
529 (Item {
530 ident: "".into(),
531 vis: Visibility::Inherited,
532 attrs: attrs,
533 node: ItemKind::ForeignMod(ForeignMod {
534 abi: abi.map(Abi),
535 items: items,
536 }),
537 })
538 ));
539
540 named!(foreign_item -> ForeignItem, alt!(
541 foreign_fn
542 |
543 foreign_static
544 ));
545
546 named!(foreign_fn -> ForeignItem, do_parse!(
547 attrs: many0!(outer_attr) >>
548 vis: visibility >>
549 keyword!("fn") >>
550 name: ident >>
551 generics: generics >>
552 punct!("(") >>
David Tolnayff46fd22016-10-08 13:53:28 -0700553 inputs: terminated_list!(punct!(","), fn_arg) >>
David Tolnay35902302016-10-06 01:11:08 -0700554 punct!(")") >>
555 ret: option!(preceded!(punct!("->"), ty)) >>
556 where_clause: where_clause >>
557 punct!(";") >>
558 (ForeignItem {
559 ident: name,
560 attrs: attrs,
561 node: ForeignItemKind::Fn(
562 Box::new(FnDecl {
563 inputs: inputs,
564 output: ret.map(FunctionRetTy::Ty).unwrap_or(FunctionRetTy::Default),
565 }),
566 Generics {
567 where_clause: where_clause,
568 .. generics
569 },
570 ),
571 vis: vis,
572 })
573 ));
574
575 named!(foreign_static -> ForeignItem, do_parse!(
576 attrs: many0!(outer_attr) >>
577 vis: visibility >>
578 keyword!("static") >>
579 mutability: mutability >>
580 id: ident >>
581 punct!(":") >>
582 ty: ty >>
583 punct!(";") >>
584 (ForeignItem {
585 ident: id,
586 attrs: attrs,
587 node: ForeignItemKind::Static(Box::new(ty), mutability),
588 vis: vis,
589 })
590 ));
591
David Tolnay3cf52982016-10-01 17:11:37 -0700592 named!(item_ty -> Item, do_parse!(
593 attrs: many0!(outer_attr) >>
594 vis: visibility >>
595 keyword!("type") >>
596 id: ident >>
597 generics: generics >>
598 punct!("=") >>
599 ty: ty >>
600 punct!(";") >>
601 (Item {
602 ident: id,
603 vis: vis,
604 attrs: attrs,
605 node: ItemKind::Ty(Box::new(ty), generics),
606 })
607 ));
608
David Tolnaya96a3fa2016-09-24 07:17:42 -0700609 named!(item_struct_or_enum -> Item, map!(
David Tolnayedf2b992016-09-23 20:43:45 -0700610 macro_input,
611 |def: MacroInput| Item {
612 ident: def.ident,
613 vis: def.vis,
614 attrs: def.attrs,
615 node: match def.body {
616 Body::Enum(variants) => {
617 ItemKind::Enum(variants, def.generics)
618 }
619 Body::Struct(variant_data) => {
620 ItemKind::Struct(variant_data, def.generics)
621 }
622 }
623 }
624 ));
David Tolnay42602292016-10-01 22:25:45 -0700625
David Tolnay2f9fa632016-10-03 22:08:48 -0700626 named!(item_union -> Item, do_parse!(
627 attrs: many0!(outer_attr) >>
628 vis: visibility >>
629 keyword!("union") >>
630 id: ident >>
631 generics: generics >>
632 where_clause: where_clause >>
633 fields: struct_like_body >>
634 (Item {
635 ident: id,
636 vis: vis,
637 attrs: attrs,
638 node: ItemKind::Union(
639 VariantData::Struct(fields),
640 Generics {
641 where_clause: where_clause,
642 .. generics
643 },
644 ),
645 })
646 ));
647
David Tolnay0aecb732016-10-03 23:03:50 -0700648 named!(item_trait -> Item, do_parse!(
649 attrs: many0!(outer_attr) >>
650 vis: visibility >>
651 unsafety: unsafety >>
652 keyword!("trait") >>
653 id: ident >>
654 generics: generics >>
655 bounds: opt_vec!(preceded!(
656 punct!(":"),
657 separated_nonempty_list!(punct!("+"), ty_param_bound)
658 )) >>
659 where_clause: where_clause >>
660 punct!("{") >>
661 body: many0!(trait_item) >>
662 punct!("}") >>
663 (Item {
664 ident: id,
665 vis: vis,
666 attrs: attrs,
667 node: ItemKind::Trait(
668 unsafety,
669 Generics {
670 where_clause: where_clause,
671 .. generics
672 },
673 bounds,
674 body,
675 ),
676 })
677 ));
678
David Tolnayf94e2362016-10-04 00:29:51 -0700679 named!(item_default_impl -> Item, do_parse!(
680 attrs: many0!(outer_attr) >>
681 unsafety: unsafety >>
682 keyword!("impl") >>
683 path: path >>
684 keyword!("for") >>
685 punct!("..") >>
686 punct!("{") >>
687 punct!("}") >>
688 (Item {
689 ident: "".into(),
690 vis: Visibility::Inherited,
691 attrs: attrs,
692 node: ItemKind::DefaultImpl(unsafety, path),
693 })
694 ));
695
David Tolnay0aecb732016-10-03 23:03:50 -0700696 named!(trait_item -> TraitItem, alt!(
697 trait_item_const
698 |
699 trait_item_method
700 |
701 trait_item_type
702 |
703 trait_item_mac
704 ));
705
706 named!(trait_item_const -> TraitItem, do_parse!(
707 attrs: many0!(outer_attr) >>
708 keyword!("const") >>
709 id: ident >>
710 punct!(":") >>
711 ty: ty >>
712 value: option!(preceded!(punct!("="), expr)) >>
713 punct!(";") >>
714 (TraitItem {
715 ident: id,
716 attrs: attrs,
717 node: TraitItemKind::Const(ty, value),
718 })
719 ));
720
721 named!(trait_item_method -> TraitItem, do_parse!(
722 attrs: many0!(outer_attr) >>
723 constness: constness >>
724 unsafety: unsafety >>
725 abi: option!(preceded!(keyword!("extern"), quoted_string)) >>
726 keyword!("fn") >>
727 name: ident >>
728 generics: generics >>
729 punct!("(") >>
David Tolnayff46fd22016-10-08 13:53:28 -0700730 inputs: terminated_list!(punct!(","), fn_arg) >>
David Tolnay0aecb732016-10-03 23:03:50 -0700731 punct!(")") >>
732 ret: option!(preceded!(punct!("->"), ty)) >>
733 where_clause: where_clause >>
734 body: option!(block) >>
735 cond!(body.is_none(), punct!(";")) >>
736 (TraitItem {
737 ident: name,
738 attrs: attrs,
739 node: TraitItemKind::Method(
740 MethodSig {
741 unsafety: unsafety,
742 constness: constness,
743 abi: abi.map(Abi),
744 decl: FnDecl {
745 inputs: inputs,
746 output: ret.map(FunctionRetTy::Ty).unwrap_or(FunctionRetTy::Default),
747 },
748 generics: Generics {
749 where_clause: where_clause,
750 .. generics
751 },
752 },
753 body,
754 ),
755 })
756 ));
757
758 named!(trait_item_type -> TraitItem, do_parse!(
759 attrs: many0!(outer_attr) >>
760 keyword!("type") >>
761 id: ident >>
762 bounds: opt_vec!(preceded!(
763 punct!(":"),
764 separated_nonempty_list!(punct!("+"), ty_param_bound)
765 )) >>
766 default: option!(preceded!(punct!("="), ty)) >>
David Tolnayca085422016-10-04 00:12:38 -0700767 punct!(";") >>
David Tolnay0aecb732016-10-03 23:03:50 -0700768 (TraitItem {
769 ident: id,
770 attrs: attrs,
771 node: TraitItemKind::Type(bounds, default),
772 })
773 ));
774
775 named!(trait_item_mac -> TraitItem, do_parse!(
776 attrs: many0!(outer_attr) >>
777 id: ident >>
778 punct!("!") >>
779 body: delimited >>
David Tolnaye3198932016-10-04 00:21:34 -0700780 cond!(match body.delim {
781 DelimToken::Paren | DelimToken::Bracket => true,
782 DelimToken::Brace => false,
783 }, punct!(";")) >>
David Tolnay0aecb732016-10-03 23:03:50 -0700784 (TraitItem {
785 ident: id.clone(),
786 attrs: attrs,
787 node: TraitItemKind::Macro(Mac {
788 path: id.into(),
789 tts: vec![TokenTree::Delimited(body)],
790 }),
791 })
792 ));
793
David Tolnay4c9be372016-10-06 00:47:37 -0700794 named!(item_impl -> Item, do_parse!(
795 attrs: many0!(outer_attr) >>
796 unsafety: unsafety >>
797 keyword!("impl") >>
798 generics: generics >>
799 polarity_path: alt!(
800 do_parse!(
801 polarity: impl_polarity >>
802 path: path >>
803 keyword!("for") >>
804 ((polarity, Some(path)))
805 )
806 |
807 epsilon!() => { |_| (ImplPolarity::Positive, None) }
808 ) >>
809 self_ty: ty >>
810 where_clause: where_clause >>
811 punct!("{") >>
812 body: many0!(impl_item) >>
813 punct!("}") >>
814 (Item {
815 ident: "".into(),
816 vis: Visibility::Inherited,
817 attrs: attrs,
818 node: ItemKind::Impl(
819 unsafety,
820 polarity_path.0,
821 Generics {
822 where_clause: where_clause,
823 .. generics
824 },
825 polarity_path.1,
826 Box::new(self_ty),
827 body,
828 ),
829 })
830 ));
831
832 named!(impl_item -> ImplItem, alt!(
833 impl_item_const
834 |
835 impl_item_method
836 |
837 impl_item_type
838 |
839 impl_item_macro
840 ));
841
842 named!(impl_item_const -> ImplItem, do_parse!(
843 attrs: many0!(outer_attr) >>
844 vis: visibility >>
845 defaultness: defaultness >>
846 keyword!("const") >>
847 id: ident >>
848 punct!(":") >>
849 ty: ty >>
850 punct!("=") >>
851 value: expr >>
852 punct!(";") >>
853 (ImplItem {
854 ident: id,
855 vis: vis,
856 defaultness: defaultness,
857 attrs: attrs,
858 node: ImplItemKind::Const(ty, value),
859 })
860 ));
861
862 named!(impl_item_method -> ImplItem, do_parse!(
863 attrs: many0!(outer_attr) >>
864 vis: visibility >>
865 defaultness: defaultness >>
866 constness: constness >>
867 unsafety: unsafety >>
868 abi: option!(preceded!(keyword!("extern"), quoted_string)) >>
869 keyword!("fn") >>
870 name: ident >>
871 generics: generics >>
872 punct!("(") >>
David Tolnayff46fd22016-10-08 13:53:28 -0700873 inputs: terminated_list!(punct!(","), fn_arg) >>
David Tolnay4c9be372016-10-06 00:47:37 -0700874 punct!(")") >>
875 ret: option!(preceded!(punct!("->"), ty)) >>
876 where_clause: where_clause >>
877 body: block >>
878 (ImplItem {
879 ident: name,
880 vis: vis,
881 defaultness: defaultness,
882 attrs: attrs,
883 node: ImplItemKind::Method(
884 MethodSig {
885 unsafety: unsafety,
886 constness: constness,
887 abi: abi.map(Abi),
888 decl: FnDecl {
889 inputs: inputs,
890 output: ret.map(FunctionRetTy::Ty).unwrap_or(FunctionRetTy::Default),
891 },
892 generics: Generics {
893 where_clause: where_clause,
894 .. generics
895 },
896 },
897 body,
898 ),
899 })
900 ));
901
902 named!(impl_item_type -> ImplItem, do_parse!(
903 attrs: many0!(outer_attr) >>
904 vis: visibility >>
905 defaultness: defaultness >>
906 keyword!("type") >>
907 id: ident >>
908 punct!("=") >>
909 ty: ty >>
910 punct!(";") >>
911 (ImplItem {
912 ident: id,
913 vis: vis,
914 defaultness: defaultness,
915 attrs: attrs,
916 node: ImplItemKind::Type(ty),
917 })
918 ));
919
920 named!(impl_item_macro -> ImplItem, do_parse!(
921 attrs: many0!(outer_attr) >>
922 id: ident >>
923 punct!("!") >>
924 body: delimited >>
925 cond!(match body.delim {
926 DelimToken::Paren | DelimToken::Bracket => true,
927 DelimToken::Brace => false,
928 }, punct!(";")) >>
929 (ImplItem {
930 ident: id.clone(),
931 vis: Visibility::Inherited,
932 defaultness: Defaultness::Final,
933 attrs: attrs,
934 node: ImplItemKind::Macro(Mac {
935 path: id.into(),
936 tts: vec![TokenTree::Delimited(body)],
937 }),
938 })
939 ));
940
941 named!(impl_polarity -> ImplPolarity, alt!(
942 punct!("!") => { |_| ImplPolarity::Negative }
943 |
944 epsilon!() => { |_| ImplPolarity::Positive }
945 ));
946
David Tolnay42602292016-10-01 22:25:45 -0700947 named!(constness -> Constness, alt!(
David Tolnaybd76e572016-10-02 13:43:16 -0700948 keyword!("const") => { |_| Constness::Const }
David Tolnay42602292016-10-01 22:25:45 -0700949 |
950 epsilon!() => { |_| Constness::NotConst }
951 ));
952
953 named!(unsafety -> Unsafety, alt!(
David Tolnaybd76e572016-10-02 13:43:16 -0700954 keyword!("unsafe") => { |_| Unsafety::Unsafe }
David Tolnay42602292016-10-01 22:25:45 -0700955 |
956 epsilon!() => { |_| Unsafety::Normal }
957 ));
David Tolnay4c9be372016-10-06 00:47:37 -0700958
959 named!(defaultness -> Defaultness, alt!(
960 keyword!("default") => { |_| Defaultness::Default }
961 |
962 epsilon!() => { |_| Defaultness::Final }
963 ));
David Tolnayedf2b992016-09-23 20:43:45 -0700964}
David Tolnay4a51dc72016-10-01 00:40:31 -0700965
966#[cfg(feature = "printing")]
967mod printing {
968 use super::*;
David Tolnaycc3d66e2016-10-02 23:36:05 -0700969 use {Delimited, DelimToken, FunctionRetTy, TokenTree};
David Tolnay4a51dc72016-10-01 00:40:31 -0700970 use attr::FilterAttrs;
David Tolnay47a877c2016-10-01 16:50:55 -0700971 use data::VariantData;
David Tolnay4a51dc72016-10-01 00:40:31 -0700972 use quote::{Tokens, ToTokens};
973
974 impl ToTokens for Item {
975 fn to_tokens(&self, tokens: &mut Tokens) {
David Tolnayca085422016-10-04 00:12:38 -0700976 tokens.append_all(self.attrs.outer());
David Tolnay4a51dc72016-10-01 00:40:31 -0700977 match self.node {
978 ItemKind::ExternCrate(ref original) => {
979 tokens.append("extern");
980 tokens.append("crate");
981 if let Some(ref original) = *original {
982 original.to_tokens(tokens);
983 tokens.append("as");
984 }
985 self.ident.to_tokens(tokens);
986 tokens.append(";");
987 }
David Tolnay4a057422016-10-08 00:02:31 -0700988 ItemKind::Use(ref view_path) => {
989 self.vis.to_tokens(tokens);
990 tokens.append("use");
991 view_path.to_tokens(tokens);
992 tokens.append(";");
993 }
David Tolnay47a877c2016-10-01 16:50:55 -0700994 ItemKind::Static(ref ty, ref mutability, ref expr) => {
995 self.vis.to_tokens(tokens);
996 tokens.append("static");
997 mutability.to_tokens(tokens);
998 self.ident.to_tokens(tokens);
999 tokens.append(":");
1000 ty.to_tokens(tokens);
1001 tokens.append("=");
1002 expr.to_tokens(tokens);
1003 tokens.append(";");
1004 }
1005 ItemKind::Const(ref ty, ref expr) => {
1006 self.vis.to_tokens(tokens);
1007 tokens.append("const");
1008 self.ident.to_tokens(tokens);
1009 tokens.append(":");
1010 ty.to_tokens(tokens);
1011 tokens.append("=");
1012 expr.to_tokens(tokens);
1013 tokens.append(";");
1014 }
David Tolnay42602292016-10-01 22:25:45 -07001015 ItemKind::Fn(ref decl, unsafety, constness, ref abi, ref generics, ref block) => {
1016 self.vis.to_tokens(tokens);
1017 constness.to_tokens(tokens);
1018 unsafety.to_tokens(tokens);
1019 abi.to_tokens(tokens);
1020 tokens.append("fn");
1021 self.ident.to_tokens(tokens);
1022 generics.to_tokens(tokens);
David Tolnay62f374c2016-10-02 13:37:00 -07001023 tokens.append("(");
1024 tokens.append_separated(&decl.inputs, ",");
1025 tokens.append(")");
1026 if let FunctionRetTy::Ty(ref ty) = decl.output {
1027 tokens.append("->");
1028 ty.to_tokens(tokens);
1029 }
David Tolnay42602292016-10-01 22:25:45 -07001030 generics.where_clause.to_tokens(tokens);
1031 block.to_tokens(tokens);
1032 }
David Tolnay35902302016-10-06 01:11:08 -07001033 ItemKind::Mod(ref items) => {
1034 self.vis.to_tokens(tokens);
1035 tokens.append("mod");
1036 self.ident.to_tokens(tokens);
David Tolnay37d10332016-10-13 20:51:04 -07001037 match *items {
1038 Some(ref items) => {
1039 tokens.append("{");
1040 tokens.append_all(items);
1041 tokens.append("}");
1042 }
1043 None => tokens.append(";"),
1044 }
David Tolnay35902302016-10-06 01:11:08 -07001045 }
1046 ItemKind::ForeignMod(ref foreign_mod) => {
1047 self.vis.to_tokens(tokens);
1048 match foreign_mod.abi {
1049 Some(ref abi) => abi.to_tokens(tokens),
1050 None => tokens.append("extern"),
1051 }
1052 tokens.append("{");
1053 tokens.append_all(&foreign_mod.items);
1054 tokens.append("}");
1055 }
David Tolnay3cf52982016-10-01 17:11:37 -07001056 ItemKind::Ty(ref ty, ref generics) => {
1057 self.vis.to_tokens(tokens);
1058 tokens.append("type");
1059 self.ident.to_tokens(tokens);
1060 generics.to_tokens(tokens);
1061 tokens.append("=");
1062 ty.to_tokens(tokens);
1063 tokens.append(";");
1064 }
David Tolnay4a51dc72016-10-01 00:40:31 -07001065 ItemKind::Enum(ref variants, ref generics) => {
David Tolnay47a877c2016-10-01 16:50:55 -07001066 self.vis.to_tokens(tokens);
David Tolnay4a51dc72016-10-01 00:40:31 -07001067 tokens.append("enum");
1068 self.ident.to_tokens(tokens);
1069 generics.to_tokens(tokens);
1070 generics.where_clause.to_tokens(tokens);
1071 tokens.append("{");
1072 for variant in variants {
1073 variant.to_tokens(tokens);
1074 tokens.append(",");
1075 }
1076 tokens.append("}");
1077 }
1078 ItemKind::Struct(ref variant_data, ref generics) => {
David Tolnay47a877c2016-10-01 16:50:55 -07001079 self.vis.to_tokens(tokens);
David Tolnay4a51dc72016-10-01 00:40:31 -07001080 tokens.append("struct");
1081 self.ident.to_tokens(tokens);
1082 generics.to_tokens(tokens);
1083 generics.where_clause.to_tokens(tokens);
1084 variant_data.to_tokens(tokens);
1085 match *variant_data {
David Tolnaydaaf7742016-10-03 11:11:43 -07001086 VariantData::Struct(_) => {
1087 // no semicolon
1088 }
David Tolnay4a51dc72016-10-01 00:40:31 -07001089 VariantData::Tuple(_) |
1090 VariantData::Unit => tokens.append(";"),
1091 }
1092 }
David Tolnay2f9fa632016-10-03 22:08:48 -07001093 ItemKind::Union(ref variant_data, ref generics) => {
1094 self.vis.to_tokens(tokens);
1095 tokens.append("union");
1096 self.ident.to_tokens(tokens);
1097 generics.to_tokens(tokens);
1098 generics.where_clause.to_tokens(tokens);
1099 variant_data.to_tokens(tokens);
1100 }
David Tolnayca085422016-10-04 00:12:38 -07001101 ItemKind::Trait(unsafety, ref generics, ref bound, ref items) => {
1102 self.vis.to_tokens(tokens);
1103 unsafety.to_tokens(tokens);
1104 tokens.append("trait");
1105 self.ident.to_tokens(tokens);
David Tolnaye4606332016-10-25 21:57:41 -07001106 generics.to_tokens(tokens);
David Tolnayca085422016-10-04 00:12:38 -07001107 if !bound.is_empty() {
1108 tokens.append(":");
1109 tokens.append_separated(bound, "+");
1110 }
David Tolnayca085422016-10-04 00:12:38 -07001111 generics.where_clause.to_tokens(tokens);
1112 tokens.append("{");
1113 tokens.append_all(items);
1114 tokens.append("}");
1115 }
David Tolnayf94e2362016-10-04 00:29:51 -07001116 ItemKind::DefaultImpl(unsafety, ref path) => {
1117 unsafety.to_tokens(tokens);
1118 tokens.append("impl");
1119 path.to_tokens(tokens);
1120 tokens.append("for");
1121 tokens.append("..");
1122 tokens.append("{");
1123 tokens.append("}");
1124 }
David Tolnay3bcfb722016-10-08 11:58:36 -07001125 ItemKind::Impl(unsafety, polarity, ref generics, ref path, ref ty, ref items) => {
David Tolnay4c9be372016-10-06 00:47:37 -07001126 unsafety.to_tokens(tokens);
1127 tokens.append("impl");
1128 generics.to_tokens(tokens);
1129 if let Some(ref path) = *path {
1130 polarity.to_tokens(tokens);
1131 path.to_tokens(tokens);
1132 tokens.append("for");
1133 }
1134 ty.to_tokens(tokens);
1135 generics.where_clause.to_tokens(tokens);
1136 tokens.append("{");
1137 tokens.append_all(items);
1138 tokens.append("}");
1139 }
David Tolnaycc3d66e2016-10-02 23:36:05 -07001140 ItemKind::Mac(ref mac) => {
1141 mac.path.to_tokens(tokens);
1142 tokens.append("!");
1143 self.ident.to_tokens(tokens);
1144 for tt in &mac.tts {
1145 tt.to_tokens(tokens);
1146 }
1147 match mac.tts.last() {
David Tolnaydaaf7742016-10-03 11:11:43 -07001148 Some(&TokenTree::Delimited(Delimited { delim: DelimToken::Brace, .. })) => {
1149 // no semicolon
1150 }
David Tolnaycc3d66e2016-10-02 23:36:05 -07001151 _ => tokens.append(";"),
1152 }
1153 }
David Tolnay4a51dc72016-10-01 00:40:31 -07001154 }
1155 }
1156 }
David Tolnay42602292016-10-01 22:25:45 -07001157
David Tolnay4a057422016-10-08 00:02:31 -07001158 impl ToTokens for ViewPath {
1159 fn to_tokens(&self, tokens: &mut Tokens) {
1160 match *self {
1161 ViewPath::Simple(ref path, ref rename) => {
1162 path.to_tokens(tokens);
1163 if let Some(ref rename) = *rename {
1164 tokens.append("as");
1165 rename.to_tokens(tokens);
1166 }
1167 }
1168 ViewPath::Glob(ref path) => {
1169 path.to_tokens(tokens);
1170 tokens.append("::");
1171 tokens.append("*");
1172 }
1173 ViewPath::List(ref path, ref items) => {
1174 path.to_tokens(tokens);
David Tolnay12417832016-10-08 00:12:37 -07001175 if path.global || !path.segments.is_empty() {
1176 tokens.append("::");
1177 }
David Tolnay4a057422016-10-08 00:02:31 -07001178 tokens.append("{");
1179 tokens.append_separated(items, ",");
1180 tokens.append("}");
1181 }
1182 }
1183 }
1184 }
1185
1186 impl ToTokens for PathListItem {
1187 fn to_tokens(&self, tokens: &mut Tokens) {
1188 self.name.to_tokens(tokens);
1189 if let Some(ref rename) = self.rename {
1190 tokens.append("as");
1191 rename.to_tokens(tokens);
1192 }
1193 }
1194 }
1195
David Tolnayca085422016-10-04 00:12:38 -07001196 impl ToTokens for TraitItem {
1197 fn to_tokens(&self, tokens: &mut Tokens) {
1198 tokens.append_all(self.attrs.outer());
1199 match self.node {
1200 TraitItemKind::Const(ref ty, ref expr) => {
1201 tokens.append("const");
1202 self.ident.to_tokens(tokens);
1203 tokens.append(":");
1204 ty.to_tokens(tokens);
1205 if let Some(ref expr) = *expr {
1206 tokens.append("=");
1207 expr.to_tokens(tokens);
1208 }
1209 tokens.append(";");
1210 }
1211 TraitItemKind::Method(ref sig, ref block) => {
David Tolnayb31d3f02016-10-25 21:15:13 -07001212 sig.constness.to_tokens(tokens);
David Tolnayca085422016-10-04 00:12:38 -07001213 sig.unsafety.to_tokens(tokens);
1214 sig.abi.to_tokens(tokens);
1215 tokens.append("fn");
1216 self.ident.to_tokens(tokens);
1217 sig.generics.to_tokens(tokens);
1218 tokens.append("(");
1219 tokens.append_separated(&sig.decl.inputs, ",");
1220 tokens.append(")");
1221 if let FunctionRetTy::Ty(ref ty) = sig.decl.output {
1222 tokens.append("->");
1223 ty.to_tokens(tokens);
1224 }
1225 sig.generics.where_clause.to_tokens(tokens);
1226 match *block {
1227 Some(ref block) => block.to_tokens(tokens),
1228 None => tokens.append(";"),
1229 }
1230 }
1231 TraitItemKind::Type(ref bound, ref default) => {
1232 tokens.append("type");
1233 self.ident.to_tokens(tokens);
1234 if !bound.is_empty() {
1235 tokens.append(":");
1236 tokens.append_separated(bound, "+");
1237 }
1238 if let Some(ref default) = *default {
1239 tokens.append("=");
1240 default.to_tokens(tokens);
1241 }
1242 tokens.append(";");
1243 }
1244 TraitItemKind::Macro(ref mac) => {
1245 mac.to_tokens(tokens);
David Tolnaye3198932016-10-04 00:21:34 -07001246 match mac.tts.last() {
1247 Some(&TokenTree::Delimited(Delimited { delim: DelimToken::Brace, .. })) => {
1248 // no semicolon
1249 }
1250 _ => tokens.append(";"),
1251 }
David Tolnayca085422016-10-04 00:12:38 -07001252 }
1253 }
1254 }
1255 }
1256
David Tolnay4c9be372016-10-06 00:47:37 -07001257 impl ToTokens for ImplItem {
1258 fn to_tokens(&self, tokens: &mut Tokens) {
1259 tokens.append_all(self.attrs.outer());
1260 match self.node {
1261 ImplItemKind::Const(ref ty, ref expr) => {
1262 self.vis.to_tokens(tokens);
1263 self.defaultness.to_tokens(tokens);
1264 tokens.append("const");
1265 self.ident.to_tokens(tokens);
1266 tokens.append(":");
1267 ty.to_tokens(tokens);
1268 tokens.append("=");
1269 expr.to_tokens(tokens);
1270 tokens.append(";");
1271 }
1272 ImplItemKind::Method(ref sig, ref block) => {
1273 self.vis.to_tokens(tokens);
1274 self.defaultness.to_tokens(tokens);
David Tolnayb31d3f02016-10-25 21:15:13 -07001275 sig.constness.to_tokens(tokens);
David Tolnay4c9be372016-10-06 00:47:37 -07001276 sig.unsafety.to_tokens(tokens);
1277 sig.abi.to_tokens(tokens);
1278 tokens.append("fn");
1279 self.ident.to_tokens(tokens);
1280 sig.generics.to_tokens(tokens);
1281 tokens.append("(");
1282 tokens.append_separated(&sig.decl.inputs, ",");
1283 tokens.append(")");
1284 if let FunctionRetTy::Ty(ref ty) = sig.decl.output {
1285 tokens.append("->");
1286 ty.to_tokens(tokens);
1287 }
1288 sig.generics.where_clause.to_tokens(tokens);
1289 block.to_tokens(tokens);
1290 }
1291 ImplItemKind::Type(ref ty) => {
1292 self.vis.to_tokens(tokens);
1293 self.defaultness.to_tokens(tokens);
1294 tokens.append("type");
1295 self.ident.to_tokens(tokens);
1296 tokens.append("=");
1297 ty.to_tokens(tokens);
1298 tokens.append(";");
1299 }
1300 ImplItemKind::Macro(ref mac) => {
1301 mac.to_tokens(tokens);
1302 match mac.tts.last() {
1303 Some(&TokenTree::Delimited(Delimited { delim: DelimToken::Brace, .. })) => {
1304 // no semicolon
1305 }
1306 _ => tokens.append(";"),
1307 }
1308 }
1309 }
1310 }
1311 }
1312
David Tolnay35902302016-10-06 01:11:08 -07001313 impl ToTokens for ForeignItem {
1314 fn to_tokens(&self, tokens: &mut Tokens) {
1315 tokens.append_all(self.attrs.outer());
1316 match self.node {
1317 ForeignItemKind::Fn(ref decl, ref generics) => {
1318 self.vis.to_tokens(tokens);
1319 tokens.append("fn");
1320 self.ident.to_tokens(tokens);
1321 generics.to_tokens(tokens);
1322 tokens.append("(");
1323 tokens.append_separated(&decl.inputs, ",");
1324 tokens.append(")");
1325 if let FunctionRetTy::Ty(ref ty) = decl.output {
1326 tokens.append("->");
1327 ty.to_tokens(tokens);
1328 }
1329 generics.where_clause.to_tokens(tokens);
1330 tokens.append(";");
1331 }
1332 ForeignItemKind::Static(ref ty, mutability) => {
1333 self.vis.to_tokens(tokens);
1334 tokens.append("static");
1335 mutability.to_tokens(tokens);
1336 self.ident.to_tokens(tokens);
1337 tokens.append(":");
1338 ty.to_tokens(tokens);
1339 tokens.append(";");
1340 }
1341 }
1342 }
1343 }
1344
David Tolnay62f374c2016-10-02 13:37:00 -07001345 impl ToTokens for FnArg {
1346 fn to_tokens(&self, tokens: &mut Tokens) {
David Tolnayca085422016-10-04 00:12:38 -07001347 match *self {
1348 FnArg::SelfRef(ref lifetime, mutability) => {
1349 tokens.append("&");
1350 lifetime.to_tokens(tokens);
1351 mutability.to_tokens(tokens);
1352 tokens.append("self");
1353 }
1354 FnArg::SelfValue(mutability) => {
1355 mutability.to_tokens(tokens);
1356 tokens.append("self");
1357 }
1358 FnArg::Captured(ref pat, ref ty) => {
1359 pat.to_tokens(tokens);
1360 tokens.append(":");
1361 ty.to_tokens(tokens);
1362 }
1363 FnArg::Ignored(ref ty) => {
1364 ty.to_tokens(tokens);
1365 }
1366 }
David Tolnay62f374c2016-10-02 13:37:00 -07001367 }
1368 }
1369
David Tolnay42602292016-10-01 22:25:45 -07001370 impl ToTokens for Unsafety {
1371 fn to_tokens(&self, tokens: &mut Tokens) {
1372 match *self {
1373 Unsafety::Unsafe => tokens.append("unsafe"),
David Tolnaydaaf7742016-10-03 11:11:43 -07001374 Unsafety::Normal => {
1375 // nothing
1376 }
David Tolnay42602292016-10-01 22:25:45 -07001377 }
1378 }
1379 }
1380
1381 impl ToTokens for Constness {
1382 fn to_tokens(&self, tokens: &mut Tokens) {
1383 match *self {
1384 Constness::Const => tokens.append("const"),
David Tolnaydaaf7742016-10-03 11:11:43 -07001385 Constness::NotConst => {
1386 // nothing
1387 }
David Tolnay42602292016-10-01 22:25:45 -07001388 }
1389 }
1390 }
1391
David Tolnay4c9be372016-10-06 00:47:37 -07001392 impl ToTokens for Defaultness {
1393 fn to_tokens(&self, tokens: &mut Tokens) {
1394 match *self {
1395 Defaultness::Default => tokens.append("default"),
1396 Defaultness::Final => {
1397 // nothing
1398 }
1399 }
1400 }
1401 }
1402
1403 impl ToTokens for ImplPolarity {
1404 fn to_tokens(&self, tokens: &mut Tokens) {
1405 match *self {
1406 ImplPolarity::Negative => tokens.append("!"),
1407 ImplPolarity::Positive => {
1408 // nothing
1409 }
1410 }
1411 }
1412 }
1413
David Tolnay42602292016-10-01 22:25:45 -07001414 impl ToTokens for Abi {
1415 fn to_tokens(&self, tokens: &mut Tokens) {
1416 tokens.append("extern");
1417 self.0.to_tokens(tokens);
1418 }
1419 }
David Tolnay4a51dc72016-10-01 00:40:31 -07001420}