Linux kernel mirror (for testing)
git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel
os
linux
1// SPDX-License-Identifier: Apache-2.0 OR MIT
2
3#[cfg_attr(
4 not(any(feature = "full", feature = "derive")),
5 allow(unknown_lints, unused_macro_rules)
6)]
7macro_rules! ast_struct {
8 (
9 $(#[$attr:meta])*
10 $pub:ident $struct:ident $name:ident #full $body:tt
11 ) => {
12 check_keyword_matches!(pub $pub);
13 check_keyword_matches!(struct $struct);
14
15 #[cfg(feature = "full")]
16 $(#[$attr])* $pub $struct $name $body
17
18 #[cfg(not(feature = "full"))]
19 $(#[$attr])* $pub $struct $name {
20 _noconstruct: ::std::marker::PhantomData<::proc_macro2::Span>,
21 }
22
23 #[cfg(all(not(feature = "full"), feature = "printing"))]
24 impl ::quote::ToTokens for $name {
25 fn to_tokens(&self, _: &mut ::proc_macro2::TokenStream) {
26 unreachable!()
27 }
28 }
29 };
30
31 (
32 $(#[$attr:meta])*
33 $pub:ident $struct:ident $name:ident $body:tt
34 ) => {
35 check_keyword_matches!(pub $pub);
36 check_keyword_matches!(struct $struct);
37
38 $(#[$attr])* $pub $struct $name $body
39 };
40}
41
42#[cfg(any(feature = "full", feature = "derive"))]
43macro_rules! ast_enum {
44 (
45 $(#[$enum_attr:meta])*
46 $pub:ident $enum:ident $name:ident $body:tt
47 ) => {
48 check_keyword_matches!(pub $pub);
49 check_keyword_matches!(enum $enum);
50
51 $(#[$enum_attr])* $pub $enum $name $body
52 };
53}
54
55macro_rules! ast_enum_of_structs {
56 (
57 $(#[$enum_attr:meta])*
58 $pub:ident $enum:ident $name:ident $body:tt
59 ) => {
60 check_keyword_matches!(pub $pub);
61 check_keyword_matches!(enum $enum);
62
63 $(#[$enum_attr])* $pub $enum $name $body
64
65 ast_enum_of_structs_impl!($name $body);
66
67 #[cfg(feature = "printing")]
68 generate_to_tokens!(() tokens $name $body);
69 };
70}
71
72macro_rules! ast_enum_of_structs_impl {
73 (
74 $name:ident {
75 $(
76 $(#[cfg $cfg_attr:tt])*
77 $(#[doc $($doc_attr:tt)*])*
78 $variant:ident $( ($member:ident) )*,
79 )*
80 }
81 ) => {
82 $($(
83 ast_enum_from_struct!($name::$variant, $member);
84 )*)*
85 };
86}
87
88macro_rules! ast_enum_from_struct {
89 // No From<TokenStream> for verbatim variants.
90 ($name:ident::Verbatim, $member:ident) => {};
91
92 ($name:ident::$variant:ident, $member:ident) => {
93 impl From<$member> for $name {
94 fn from(e: $member) -> $name {
95 $name::$variant(e)
96 }
97 }
98 };
99}
100
101#[cfg(feature = "printing")]
102macro_rules! generate_to_tokens {
103 (
104 ($($arms:tt)*) $tokens:ident $name:ident {
105 $(#[cfg $cfg_attr:tt])*
106 $(#[doc $($doc_attr:tt)*])*
107 $variant:ident,
108 $($next:tt)*
109 }
110 ) => {
111 generate_to_tokens!(
112 ($($arms)* $(#[cfg $cfg_attr])* $name::$variant => {})
113 $tokens $name { $($next)* }
114 );
115 };
116
117 (
118 ($($arms:tt)*) $tokens:ident $name:ident {
119 $(#[cfg $cfg_attr:tt])*
120 $(#[doc $($doc_attr:tt)*])*
121 $variant:ident($member:ident),
122 $($next:tt)*
123 }
124 ) => {
125 generate_to_tokens!(
126 ($($arms)* $(#[cfg $cfg_attr])* $name::$variant(_e) => _e.to_tokens($tokens),)
127 $tokens $name { $($next)* }
128 );
129 };
130
131 (($($arms:tt)*) $tokens:ident $name:ident {}) => {
132 #[cfg_attr(docsrs, doc(cfg(feature = "printing")))]
133 impl ::quote::ToTokens for $name {
134 fn to_tokens(&self, $tokens: &mut ::proc_macro2::TokenStream) {
135 match self {
136 $($arms)*
137 }
138 }
139 }
140 };
141}
142
143// Rustdoc bug: does not respect the doc(hidden) on some items.
144#[cfg(all(doc, feature = "parsing"))]
145macro_rules! pub_if_not_doc {
146 ($(#[$m:meta])* $pub:ident $($item:tt)*) => {
147 check_keyword_matches!(pub $pub);
148
149 $(#[$m])*
150 $pub(crate) $($item)*
151 };
152}
153
154#[cfg(all(not(doc), feature = "parsing"))]
155macro_rules! pub_if_not_doc {
156 ($(#[$m:meta])* $pub:ident $($item:tt)*) => {
157 check_keyword_matches!(pub $pub);
158
159 $(#[$m])*
160 $pub $($item)*
161 };
162}
163
164macro_rules! check_keyword_matches {
165 (enum enum) => {};
166 (pub pub) => {};
167 (struct struct) => {};
168}
169
170#[cfg(any(feature = "full", feature = "derive"))]
171macro_rules! return_impl_trait {
172 (
173 $(#[$attr:meta])*
174 $vis:vis fn $name:ident $args:tt -> $impl_trait:ty [$concrete:ty] $body:block
175 ) => {
176 #[cfg(not(docsrs))]
177 $(#[$attr])*
178 $vis fn $name $args -> $concrete $body
179
180 #[cfg(docsrs)]
181 $(#[$attr])*
182 $vis fn $name $args -> $impl_trait $body
183 };
184}