blob: 0017d502dbf900dd6c6b3673855b7a56c3529e3a [file] [log] [blame]
David Tolnay55535012018-01-05 16:39:23 -08001// Copyright 2018 Syn Developers
2//
3// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
4// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
5// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
6// option. This file may not be copied, modified, or distributed
7// except according to those terms.
8
David Tolnay3cfd1d32018-01-03 00:22:08 -08009#[cfg(any(feature = "full", feature = "derive"))]
Alex Crichton62a0a592017-05-22 13:58:53 -070010macro_rules! ast_struct {
11 (
12 $(#[$attr:meta])*
Michael Layzell734adb42017-06-07 16:58:31 -040013 pub struct $name:ident #full $($rest:tt)*
14 ) => {
15 #[cfg(feature = "full")]
16 $(#[$attr])*
17 #[cfg_attr(feature = "extra-traits", derive(Debug, Eq, PartialEq, Hash))]
18 #[cfg_attr(feature = "clone-impls", derive(Clone))]
19 pub struct $name $($rest)*
20
21 #[cfg(not(feature = "full"))]
22 $(#[$attr])*
23 #[cfg_attr(feature = "extra-traits", derive(Debug, Eq, PartialEq, Hash))]
24 #[cfg_attr(feature = "clone-impls", derive(Clone))]
25 pub struct $name {
26 _noconstruct: (),
27 }
28 };
29
30 (
31 $(#[$attr:meta])*
David Tolnay9c76bcb2017-12-26 23:14:59 -050032 pub struct $name:ident #manual_extra_traits $($rest:tt)*
33 ) => {
34 $(#[$attr])*
35 #[cfg_attr(feature = "extra-traits", derive(Debug))]
36 #[cfg_attr(feature = "clone-impls", derive(Clone))]
37 pub struct $name $($rest)*
38 };
39
40 (
41 $(#[$attr:meta])*
Alex Crichton2e0229c2017-05-23 09:34:50 -070042 pub struct $name:ident $($rest:tt)*
Alex Crichton62a0a592017-05-22 13:58:53 -070043 ) => {
44 $(#[$attr])*
Alex Crichton2e0229c2017-05-23 09:34:50 -070045 #[cfg_attr(feature = "extra-traits", derive(Debug, Eq, PartialEq, Hash))]
46 #[cfg_attr(feature = "clone-impls", derive(Clone))]
47 pub struct $name $($rest)*
Michael Layzell734adb42017-06-07 16:58:31 -040048 };
Alex Crichton62a0a592017-05-22 13:58:53 -070049}
50
David Tolnay3cfd1d32018-01-03 00:22:08 -080051#[cfg(any(feature = "full", feature = "derive"))]
Alex Crichton62a0a592017-05-22 13:58:53 -070052macro_rules! ast_enum {
53 (
54 $(#[$enum_attr:meta])*
David Tolnay360efd22018-01-04 23:35:26 -080055 pub enum $name:ident $(# $tags:ident)* { $($variants:tt)* }
Alex Crichton62a0a592017-05-22 13:58:53 -070056 ) => (
57 $(#[$enum_attr])*
Alex Crichton2e0229c2017-05-23 09:34:50 -070058 #[cfg_attr(feature = "extra-traits", derive(Debug, Eq, PartialEq, Hash))]
59 #[cfg_attr(feature = "clone-impls", derive(Clone))]
Alex Crichton62a0a592017-05-22 13:58:53 -070060 pub enum $name {
61 $($variants)*
62 }
63 )
64}
65
David Tolnay3cfd1d32018-01-03 00:22:08 -080066#[cfg(any(feature = "full", feature = "derive"))]
Alex Crichton62a0a592017-05-22 13:58:53 -070067macro_rules! ast_enum_of_structs {
68 (
69 $(#[$enum_attr:meta])*
70 pub enum $name:ident {
71 $(
72 $(#[$variant_attr:meta])*
David Tolnayfcfb9002017-12-28 22:04:29 -050073 pub $variant:ident $( ($member:ident $($rest:tt)*) )*,
Alex Crichton62a0a592017-05-22 13:58:53 -070074 )*
75 }
76
77 $($remaining:tt)*
78 ) => (
79 ast_enum! {
80 $(#[$enum_attr])*
81 pub enum $name {
82 $(
83 $(#[$variant_attr])*
David Tolnayfcfb9002017-12-28 22:04:29 -050084 $variant $( ($member) )*,
Alex Crichton62a0a592017-05-22 13:58:53 -070085 )*
86 }
87 }
88
89 $(
90 maybe_ast_struct! {
91 $(#[$variant_attr])*
David Tolnayfcfb9002017-12-28 22:04:29 -050092 $(
93 pub struct $member $($rest)*
94 )*
Alex Crichton62a0a592017-05-22 13:58:53 -070095 }
96
David Tolnayfcfb9002017-12-28 22:04:29 -050097 $(
98 impl From<$member> for $name {
99 fn from(e: $member) -> $name {
100 $name::$variant(e)
101 }
Alex Crichton62a0a592017-05-22 13:58:53 -0700102 }
David Tolnayfcfb9002017-12-28 22:04:29 -0500103 )*
Alex Crichton62a0a592017-05-22 13:58:53 -0700104 )*
105
David Tolnay85f07bb2017-11-12 10:25:17 -0800106 #[cfg(feature = "printing")]
Alex Crichton62a0a592017-05-22 13:58:53 -0700107 generate_to_tokens! {
108 $($remaining)*
David Tolnayfcfb9002017-12-28 22:04:29 -0500109 ()
110 tokens
111 $name { $($variant $( [$($rest)*] )*,)* }
Alex Crichton62a0a592017-05-22 13:58:53 -0700112 }
113 )
114}
115
David Tolnay3cfd1d32018-01-03 00:22:08 -0800116#[cfg(all(feature = "printing", any(feature = "full", feature = "derive")))]
Alex Crichton62a0a592017-05-22 13:58:53 -0700117macro_rules! generate_to_tokens {
118 (do_not_generate_to_tokens $($foo:tt)*) => ();
119
David Tolnayfcfb9002017-12-28 22:04:29 -0500120 (($($arms:tt)*) $tokens:ident $name:ident { $variant:ident, $($next:tt)*}) => {
121 generate_to_tokens!(
122 ($($arms)* $name::$variant => {})
123 $tokens $name { $($next)* }
124 );
125 };
126
127 (($($arms:tt)*) $tokens:ident $name:ident { $variant:ident [$($rest:tt)*], $($next:tt)*}) => {
128 generate_to_tokens!(
129 ($($arms)* $name::$variant(ref _e) => to_tokens_call!(_e, $tokens, $($rest)*),)
130 $tokens $name { $($next)* }
131 );
132 };
133
134 (($($arms:tt)*) $tokens:ident $name:ident {}) => {
Alex Crichton62a0a592017-05-22 13:58:53 -0700135 impl ::quote::ToTokens for $name {
Alex Crichtona74a1c82018-05-16 10:20:44 -0700136 fn to_tokens(&self, $tokens: &mut ::proc_macro2::TokenStream) {
Alex Crichton62a0a592017-05-22 13:58:53 -0700137 match *self {
David Tolnayfcfb9002017-12-28 22:04:29 -0500138 $($arms)*
Alex Crichton62a0a592017-05-22 13:58:53 -0700139 }
140 }
141 }
David Tolnayfcfb9002017-12-28 22:04:29 -0500142 };
Michael Layzell734adb42017-06-07 16:58:31 -0400143}
144
David Tolnay85f07bb2017-11-12 10:25:17 -0800145#[cfg(all(feature = "printing", feature = "full"))]
Michael Layzell734adb42017-06-07 16:58:31 -0400146macro_rules! to_tokens_call {
147 ($e:ident, $tokens:ident, $($rest:tt)*) => {
148 $e.to_tokens($tokens)
149 };
150}
151
David Tolnay3cfd1d32018-01-03 00:22:08 -0800152#[cfg(all(feature = "printing", feature = "derive", not(feature = "full")))]
Michael Layzell734adb42017-06-07 16:58:31 -0400153macro_rules! to_tokens_call {
154 // If the variant is marked as #full, don't auto-generate to-tokens for it.
155 ($e:ident, $tokens:ident, #full $($rest:tt)*) => {
156 unreachable!()
157 };
158 ($e:ident, $tokens:ident, $($rest:tt)*) => {
159 $e.to_tokens($tokens)
160 };
Alex Crichton62a0a592017-05-22 13:58:53 -0700161}
162
David Tolnay3cfd1d32018-01-03 00:22:08 -0800163#[cfg(any(feature = "full", feature = "derive"))]
Alex Crichton62a0a592017-05-22 13:58:53 -0700164macro_rules! maybe_ast_struct {
165 (
166 $(#[$attr:meta])*
David Tolnayfcfb9002017-12-28 22:04:29 -0500167 $(
168 pub struct $name:ident
169 )*
Alex Crichton62a0a592017-05-22 13:58:53 -0700170 ) => ();
171
172 ($($rest:tt)*) => (ast_struct! { $($rest)* });
173}
David Tolnay4c614be2017-11-10 00:02:38 -0800174
David Tolnay0a0d78c2018-01-05 15:24:01 -0800175#[cfg(all(feature = "parsing", any(feature = "full", feature = "derive")))]
David Tolnay4c614be2017-11-10 00:02:38 -0800176macro_rules! impl_synom {
177 ($t:ident $description:tt $($parser:tt)+) => {
178 impl Synom for $t {
179 named!(parse -> Self, $($parser)+);
180
181 fn description() -> Option<&'static str> {
182 Some($description)
183 }
184 }
185 }
186}