Skip to main content

rustc_ast/
tokenstream.rs

1//! # Token Streams
2//!
3//! `TokenStream`s represent syntactic objects before they are converted into ASTs.
4//! A `TokenStream` is, roughly speaking, a sequence of [`TokenTree`]s,
5//! which are themselves a single [`Token`] or a `Delimited` subsequence of tokens.
6
7use std::borrow::Cow;
8use std::hash::Hash;
9use std::ops::Range;
10use std::sync::Arc;
11use std::{cmp, fmt, iter, mem};
12
13use rustc_data_structures::stable_hash::{StableHash, StableHashCtxt, StableHasher};
14use rustc_data_structures::sync;
15use rustc_macros::{Decodable, Encodable, StableHash, Walkable};
16use rustc_serialize::{Decodable, Encodable};
17use rustc_span::{DUMMY_SP, Span, SpanDecoder, SpanEncoder, Symbol, sym};
18use thin_vec::ThinVec;
19
20use crate::ast::AttrStyle;
21use crate::ast_traits::HasTokens;
22use crate::token::{self, Delimiter, Token, TokenKind};
23use crate::{AttrVec, Attribute};
24
25#[cfg(test)]
26mod tests;
27
28/// Part of a `TokenStream`.
29#[derive(#[automatically_derived]
impl ::core::fmt::Debug for TokenTree {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        match self {
            TokenTree::Token(__self_0, __self_1) =>
                ::core::fmt::Formatter::debug_tuple_field2_finish(f, "Token",
                    __self_0, &__self_1),
            TokenTree::Delimited(__self_0, __self_1, __self_2, __self_3) =>
                ::core::fmt::Formatter::debug_tuple_field4_finish(f,
                    "Delimited", __self_0, __self_1, __self_2, &__self_3),
        }
    }
}Debug, #[automatically_derived]
impl ::core::clone::Clone for TokenTree {
    #[inline]
    fn clone(&self) -> TokenTree {
        match self {
            TokenTree::Token(__self_0, __self_1) =>
                TokenTree::Token(::core::clone::Clone::clone(__self_0),
                    ::core::clone::Clone::clone(__self_1)),
            TokenTree::Delimited(__self_0, __self_1, __self_2, __self_3) =>
                TokenTree::Delimited(::core::clone::Clone::clone(__self_0),
                    ::core::clone::Clone::clone(__self_1),
                    ::core::clone::Clone::clone(__self_2),
                    ::core::clone::Clone::clone(__self_3)),
        }
    }
}Clone, #[automatically_derived]
impl ::core::cmp::PartialEq for TokenTree {
    #[inline]
    fn eq(&self, other: &TokenTree) -> bool {
        let __self_discr = ::core::intrinsics::discriminant_value(self);
        let __arg1_discr = ::core::intrinsics::discriminant_value(other);
        __self_discr == __arg1_discr &&
            match (self, other) {
                (TokenTree::Token(__self_0, __self_1),
                    TokenTree::Token(__arg1_0, __arg1_1)) =>
                    __self_0 == __arg1_0 && __self_1 == __arg1_1,
                (TokenTree::Delimited(__self_0, __self_1, __self_2, __self_3),
                    TokenTree::Delimited(__arg1_0, __arg1_1, __arg1_2,
                    __arg1_3)) =>
                    __self_0 == __arg1_0 && __self_1 == __arg1_1 &&
                            __self_2 == __arg1_2 && __self_3 == __arg1_3,
                _ => unsafe { ::core::intrinsics::unreachable() }
            }
    }
}PartialEq, #[automatically_derived]
impl ::core::cmp::Eq for TokenTree {
    #[inline]
    #[doc(hidden)]
    #[coverage(off)]
    fn assert_fields_are_eq(&self) {
        let _: ::core::cmp::AssertParamIsEq<Token>;
        let _: ::core::cmp::AssertParamIsEq<Spacing>;
        let _: ::core::cmp::AssertParamIsEq<DelimSpan>;
        let _: ::core::cmp::AssertParamIsEq<DelimSpacing>;
        let _: ::core::cmp::AssertParamIsEq<Delimiter>;
        let _: ::core::cmp::AssertParamIsEq<TokenStream>;
    }
}Eq, #[automatically_derived]
impl ::core::hash::Hash for TokenTree {
    #[inline]
    fn hash<__H: ::core::hash::Hasher>(&self, state: &mut __H) {
        let __self_discr = ::core::intrinsics::discriminant_value(self);
        ::core::hash::Hash::hash(&__self_discr, state);
        match self {
            TokenTree::Token(__self_0, __self_1) => {
                ::core::hash::Hash::hash(__self_0, state);
                ::core::hash::Hash::hash(__self_1, state)
            }
            TokenTree::Delimited(__self_0, __self_1, __self_2, __self_3) => {
                ::core::hash::Hash::hash(__self_0, state);
                ::core::hash::Hash::hash(__self_1, state);
                ::core::hash::Hash::hash(__self_2, state);
                ::core::hash::Hash::hash(__self_3, state)
            }
        }
    }
}Hash, const _: () =
    {
        impl<__E: ::rustc_span::SpanEncoder> ::rustc_serialize::Encodable<__E>
            for TokenTree {
            fn encode(&self, __encoder: &mut __E) {
                let disc =
                    match *self {
                        TokenTree::Token(ref __binding_0, ref __binding_1) => {
                            0usize
                        }
                        TokenTree::Delimited(ref __binding_0, ref __binding_1,
                            ref __binding_2, ref __binding_3) => {
                            1usize
                        }
                    };
                ::rustc_serialize::Encoder::emit_u8(__encoder, disc as u8);
                match *self {
                    TokenTree::Token(ref __binding_0, ref __binding_1) => {
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_0,
                            __encoder);
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_1,
                            __encoder);
                    }
                    TokenTree::Delimited(ref __binding_0, ref __binding_1,
                        ref __binding_2, ref __binding_3) => {
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_0,
                            __encoder);
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_1,
                            __encoder);
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_2,
                            __encoder);
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_3,
                            __encoder);
                    }
                }
            }
        }
    };Encodable, const _: () =
    {
        impl<__D: ::rustc_span::SpanDecoder> ::rustc_serialize::Decodable<__D>
            for TokenTree {
            fn decode(__decoder: &mut __D) -> Self {
                match ::rustc_serialize::Decoder::read_u8(__decoder) as usize
                    {
                    0usize => {
                        TokenTree::Token(::rustc_serialize::Decodable::decode(__decoder),
                            ::rustc_serialize::Decodable::decode(__decoder))
                    }
                    1usize => {
                        TokenTree::Delimited(::rustc_serialize::Decodable::decode(__decoder),
                            ::rustc_serialize::Decodable::decode(__decoder),
                            ::rustc_serialize::Decodable::decode(__decoder),
                            ::rustc_serialize::Decodable::decode(__decoder))
                    }
                    n => {
                        ::core::panicking::panic_fmt(format_args!("invalid enum variant tag while decoding `TokenTree`, expected 0..2, actual {0}",
                                n));
                    }
                }
            }
        }
    };Decodable, const _: () =
    {
        impl ::rustc_data_structures::stable_hash::StableHash for TokenTree {
            #[inline]
            fn stable_hash<__Hcx: ::rustc_data_structures::stable_hash::StableHashCtxt>(&self,
                __hcx: &mut __Hcx,
                __hasher:
                    &mut ::rustc_data_structures::stable_hash::StableHasher) {
                ::std::mem::discriminant(self).stable_hash(__hcx, __hasher);
                match *self {
                    TokenTree::Token(ref __binding_0, ref __binding_1) => {
                        { __binding_0.stable_hash(__hcx, __hasher); }
                        { __binding_1.stable_hash(__hcx, __hasher); }
                    }
                    TokenTree::Delimited(ref __binding_0, ref __binding_1,
                        ref __binding_2, ref __binding_3) => {
                        { __binding_0.stable_hash(__hcx, __hasher); }
                        { __binding_1.stable_hash(__hcx, __hasher); }
                        { __binding_2.stable_hash(__hcx, __hasher); }
                        { __binding_3.stable_hash(__hcx, __hasher); }
                    }
                }
            }
        }
    };StableHash)]
30pub enum TokenTree {
31    /// A single token. Should never be `OpenDelim` or `CloseDelim`, because
32    /// delimiters are implicitly represented by `Delimited`.
33    Token(Token, Spacing),
34    /// A delimited sequence of token trees.
35    Delimited(DelimSpan, DelimSpacing, Delimiter, TokenStream),
36}
37
38// Ensure all fields of `TokenTree` are `DynSend` and `DynSync`.
39fn _dummy()
40where
41    Token: sync::DynSend + sync::DynSync,
42    Spacing: sync::DynSend + sync::DynSync,
43    DelimSpan: sync::DynSend + sync::DynSync,
44    Delimiter: sync::DynSend + sync::DynSync,
45    TokenStream: sync::DynSend + sync::DynSync,
46{
47}
48
49impl TokenTree {
50    /// Checks if this `TokenTree` is equal to the other, regardless of span/spacing information.
51    pub fn eq_unspanned(&self, other: &TokenTree) -> bool {
52        match (self, other) {
53            (TokenTree::Token(token, _), TokenTree::Token(token2, _)) => token.kind == token2.kind,
54            (TokenTree::Delimited(.., delim, tts), TokenTree::Delimited(.., delim2, tts2)) => {
55                delim == delim2 && tts.iter().eq_by(tts2.iter(), |a, b| a.eq_unspanned(b))
56            }
57            _ => false,
58        }
59    }
60
61    /// Retrieves the `TokenTree`'s span.
62    pub fn span(&self) -> Span {
63        match self {
64            TokenTree::Token(token, _) => token.span,
65            TokenTree::Delimited(sp, ..) => sp.entire(),
66        }
67    }
68
69    /// Create a `TokenTree::Token` with alone spacing.
70    pub fn token_alone(kind: TokenKind, span: Span) -> TokenTree {
71        TokenTree::Token(Token::new(kind, span), Spacing::Alone)
72    }
73
74    /// Create a `TokenTree::Token` with joint spacing.
75    pub fn token_joint(kind: TokenKind, span: Span) -> TokenTree {
76        TokenTree::Token(Token::new(kind, span), Spacing::Joint)
77    }
78
79    /// Create a `TokenTree::Token` with joint-hidden spacing.
80    pub fn token_joint_hidden(kind: TokenKind, span: Span) -> TokenTree {
81        TokenTree::Token(Token::new(kind, span), Spacing::JointHidden)
82    }
83
84    pub fn uninterpolate(&self) -> Cow<'_, TokenTree> {
85        match self {
86            TokenTree::Token(token, spacing) => match token.uninterpolate() {
87                Cow::Owned(token) => Cow::Owned(TokenTree::Token(token, *spacing)),
88                Cow::Borrowed(_) => Cow::Borrowed(self),
89            },
90            _ => Cow::Borrowed(self),
91        }
92    }
93}
94
95#[derive(#[automatically_derived]
impl<T: ::core::clone::Clone> ::core::clone::Clone for WithTokens<T> {
    #[inline]
    fn clone(&self) -> WithTokens<T> {
        WithTokens {
            node: ::core::clone::Clone::clone(&self.node),
            tokens: ::core::clone::Clone::clone(&self.tokens),
        }
    }
}Clone, #[automatically_derived]
impl<T: ::core::fmt::Debug> ::core::fmt::Debug for WithTokens<T> {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::debug_struct_field2_finish(f, "WithTokens",
            "node", &self.node, "tokens", &&self.tokens)
    }
}Debug)]
96pub struct WithTokens<T> {
97    pub node: T,
98    pub tokens: Option<LazyAttrTokenStream>,
99}
100
101impl<T> WithTokens<T> {
102    pub fn new(node: T) -> WithTokens<T> {
103        WithTokens { node, tokens: None }
104    }
105
106    pub fn map<U>(self, f: impl FnOnce(T) -> U) -> WithTokens<U> {
107        WithTokens { node: f(self.node), tokens: self.tokens }
108    }
109}
110
111/// A lazy version of [`AttrTokenStream`], which defers creation of an actual
112/// `AttrTokenStream` until it is needed.
113#[derive(#[automatically_derived]
impl ::core::clone::Clone for LazyAttrTokenStream {
    #[inline]
    fn clone(&self) -> LazyAttrTokenStream {
        LazyAttrTokenStream(::core::clone::Clone::clone(&self.0))
    }
}Clone)]
114pub struct LazyAttrTokenStream(Arc<LazyAttrTokenStreamInner>);
115
116impl LazyAttrTokenStream {
117    pub fn new_direct(stream: AttrTokenStream) -> LazyAttrTokenStream {
118        LazyAttrTokenStream(Arc::new(LazyAttrTokenStreamInner::Direct(stream)))
119    }
120
121    pub fn new_pending(
122        start_token: (Token, Spacing),
123        cursor_snapshot: TokenCursor,
124        num_calls: u32,
125        break_last_token: u32,
126        node_replacements: ThinVec<NodeReplacement>,
127    ) -> LazyAttrTokenStream {
128        LazyAttrTokenStream(Arc::new(LazyAttrTokenStreamInner::Pending {
129            start_token,
130            cursor_snapshot,
131            num_calls,
132            break_last_token,
133            node_replacements,
134        }))
135    }
136
137    pub fn to_attr_token_stream(&self) -> AttrTokenStream {
138        self.0.to_attr_token_stream()
139    }
140}
141
142impl fmt::Debug for LazyAttrTokenStream {
143    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
144        f.write_fmt(format_args!("LazyAttrTokenStream({0:?})",
        self.to_attr_token_stream()))write!(f, "LazyAttrTokenStream({:?})", self.to_attr_token_stream())
145    }
146}
147
148impl<S: SpanEncoder> Encodable<S> for LazyAttrTokenStream {
149    fn encode(&self, _s: &mut S) {
150        {
    ::core::panicking::panic_fmt(format_args!("Attempted to encode LazyAttrTokenStream"));
};panic!("Attempted to encode LazyAttrTokenStream");
151    }
152}
153
154impl<D: SpanDecoder> Decodable<D> for LazyAttrTokenStream {
155    fn decode(_d: &mut D) -> Self {
156        {
    ::core::panicking::panic_fmt(format_args!("Attempted to decode LazyAttrTokenStream"));
};panic!("Attempted to decode LazyAttrTokenStream");
157    }
158}
159
160impl StableHash for LazyAttrTokenStream {
161    fn stable_hash<Hcx: StableHashCtxt>(&self, _hcx: &mut Hcx, _hasher: &mut StableHasher) {
162        {
    ::core::panicking::panic_fmt(format_args!("Attempted to compute stable hash for LazyAttrTokenStream"));
};panic!("Attempted to compute stable hash for LazyAttrTokenStream");
163    }
164}
165
166/// A token range within a `Parser`'s full token stream.
167#[derive(#[automatically_derived]
impl ::core::clone::Clone for ParserRange {
    #[inline]
    fn clone(&self) -> ParserRange {
        ParserRange(::core::clone::Clone::clone(&self.0))
    }
}Clone, #[automatically_derived]
impl ::core::fmt::Debug for ParserRange {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::debug_tuple_field1_finish(f, "ParserRange",
            &&self.0)
    }
}Debug)]
168pub struct ParserRange(pub Range<u32>);
169
170/// A token range within an individual AST node's (lazy) token stream, i.e.
171/// relative to that node's first token. Distinct from `ParserRange` so the two
172/// kinds of range can't be mixed up.
173#[derive(#[automatically_derived]
impl ::core::clone::Clone for NodeRange {
    #[inline]
    fn clone(&self) -> NodeRange {
        NodeRange(::core::clone::Clone::clone(&self.0))
    }
}Clone, #[automatically_derived]
impl ::core::fmt::Debug for NodeRange {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::debug_tuple_field1_finish(f, "NodeRange",
            &&self.0)
    }
}Debug)]
174pub struct NodeRange(pub Range<u32>);
175
176/// Indicates a range of tokens that should be replaced by an `AttrsTarget`
177/// (replacement) or be replaced by nothing (deletion). This is used in two
178/// places during token collection.
179///
180/// 1. Replacement. During the parsing of an AST node that may have a
181///    `#[derive]` attribute, when we parse a nested AST node that has `#[cfg]`
182///    or `#[cfg_attr]`, we replace the entire inner AST node with
183///    `FlatToken::AttrsTarget`. This lets us perform eager cfg-expansion on an
184///    `AttrTokenStream`.
185///
186/// 2. Deletion. We delete inner attributes from all collected token streams,
187///    and instead track them through the `attrs` field on the AST node. This
188///    lets us manipulate them similarly to outer attributes. When we create a
189///    `TokenStream`, the inner attributes are inserted into the proper place
190///    in the token stream.
191///
192/// Each replacement starts off in `ParserReplacement` form but is converted to
193/// `NodeReplacement` form when it is attached to a single AST node, via
194/// `LazyAttrTokenStreamImpl`.
195pub type ParserReplacement = (ParserRange, Option<AttrsTarget>);
196
197/// See the comment on `ParserReplacement`.
198pub type NodeReplacement = (NodeRange, Option<AttrsTarget>);
199
200impl NodeRange {
201    // Converts a range within a parser's tokens to a range within a
202    // node's tokens beginning at `start_pos`.
203    //
204    // For example, imagine a parser with 50 tokens in its token stream, a
205    // function that spans `ParserRange(20..40)` and an inner attribute within
206    // that function that spans `ParserRange(30..35)`. We would find the inner
207    // attribute's range within the function's tokens by subtracting 20, which
208    // is the position of the function's start token. This gives
209    // `NodeRange(10..15)`.
210    pub fn new(ParserRange(parser_range): ParserRange, start_pos: u32) -> NodeRange {
211        if !!parser_range.is_empty() {
    ::core::panicking::panic("assertion failed: !parser_range.is_empty()")
};assert!(!parser_range.is_empty());
212        if !(parser_range.start >= start_pos) {
    ::core::panicking::panic("assertion failed: parser_range.start >= start_pos")
};assert!(parser_range.start >= start_pos);
213        NodeRange((parser_range.start - start_pos)..(parser_range.end - start_pos))
214    }
215}
216
217enum LazyAttrTokenStreamInner {
218    // The token stream has already been produced.
219    Direct(AttrTokenStream),
220
221    // From a value of this type we can reconstruct the `TokenStream` seen by
222    // the `f` callback passed to a call to `Parser::collect_tokens`, by
223    // replaying the getting of the tokens. This saves us producing a
224    // `TokenStream` if it is never needed, e.g. a captured `macro_rules!`
225    // argument that is never passed to a proc macro. In practice, token stream
226    // creation happens rarely compared to calls to `collect_tokens` (see some
227    // statistics in #78736) so we are doing as little up-front work as
228    // possible.
229    //
230    // This also makes `Parser` very cheap to clone, since there is no
231    // intermediate collection buffer to clone.
232    Pending {
233        start_token: (Token, Spacing),
234        cursor_snapshot: TokenCursor,
235        num_calls: u32,
236        break_last_token: u32,
237        node_replacements: ThinVec<NodeReplacement>,
238    },
239}
240
241impl LazyAttrTokenStreamInner {
242    fn to_attr_token_stream(&self) -> AttrTokenStream {
243        match self {
244            LazyAttrTokenStreamInner::Direct(stream) => stream.clone(),
245            LazyAttrTokenStreamInner::Pending {
246                start_token,
247                cursor_snapshot,
248                num_calls,
249                break_last_token,
250                node_replacements,
251            } => {
252                // The token produced by the final call to `{,inlined_}next` was not
253                // actually consumed by the callback. The combination of chaining the
254                // initial token and using `take` produces the desired result - we
255                // produce an empty `TokenStream` if no calls were made, and omit the
256                // final token otherwise.
257                let mut cursor_snapshot = cursor_snapshot.clone();
258                let tokens = iter::once(FlatToken::Token(*start_token))
259                    .chain(iter::repeat_with(|| FlatToken::Token(cursor_snapshot.next())))
260                    .take(*num_calls as usize);
261
262                if node_replacements.is_empty() {
263                    make_attr_token_stream(tokens, *break_last_token)
264                } else {
265                    let mut tokens: Vec<_> = tokens.collect();
266                    let mut node_replacements = node_replacements.to_vec();
267                    node_replacements.sort_by_key(|(range, _)| range.0.start);
268
269                    #[cfg(debug_assertions)]
270                    for [(node_range, tokens), (next_node_range, next_tokens)] in
271                        node_replacements.array_windows()
272                    {
273                        if !(node_range.0.end <= next_node_range.0.start ||
            node_range.0.end >= next_node_range.0.end) {
    {
        ::core::panicking::panic_fmt(format_args!("Node ranges should be disjoint or nested: ({0:?}, {1:?}) ({2:?}, {3:?})",
                node_range, tokens, next_node_range, next_tokens));
    }
};assert!(
274                            node_range.0.end <= next_node_range.0.start
275                                || node_range.0.end >= next_node_range.0.end,
276                            "Node ranges should be disjoint or nested: ({:?}, {:?}) ({:?}, {:?})",
277                            node_range,
278                            tokens,
279                            next_node_range,
280                            next_tokens,
281                        );
282                    }
283
284                    // Process the replace ranges, starting from the highest start
285                    // position and working our way back. If have tokens like:
286                    //
287                    // `#[cfg(FALSE)] struct Foo { #[cfg(FALSE)] field: bool }`
288                    //
289                    // Then we will generate replace ranges for both
290                    // the `#[cfg(FALSE)] field: bool` and the entire
291                    // `#[cfg(FALSE)] struct Foo { #[cfg(FALSE)] field: bool }`
292                    //
293                    // By starting processing from the replace range with the greatest
294                    // start position, we ensure that any (outer) replace range which
295                    // encloses another (inner) replace range will fully overwrite the
296                    // inner range's replacement.
297                    for (node_range, target) in node_replacements.into_iter().rev() {
298                        if !!node_range.0.is_empty() {
    {
        ::core::panicking::panic_fmt(format_args!("Cannot replace an empty node range: {0:?}",
                node_range.0));
    }
};assert!(
299                            !node_range.0.is_empty(),
300                            "Cannot replace an empty node range: {:?}",
301                            node_range.0
302                        );
303
304                        // Replace the tokens in range with zero or one `FlatToken::AttrsTarget`s,
305                        // plus enough `FlatToken::Empty`s to fill up the rest of the range. This
306                        // keeps the total length of `tokens` constant throughout the replacement
307                        // process, allowing us to do all replacements without adjusting indices.
308                        let target_len = target.is_some() as usize;
309                        tokens.splice(
310                            (node_range.0.start as usize)..(node_range.0.end as usize),
311                            target.into_iter().map(|target| FlatToken::AttrsTarget(target)).chain(
312                                iter::repeat(FlatToken::Empty)
313                                    .take(node_range.0.len() - target_len),
314                            ),
315                        );
316                    }
317                    make_attr_token_stream(tokens.into_iter(), *break_last_token)
318                }
319            }
320        }
321    }
322}
323
324/// A helper struct used when building an `AttrTokenStream` from
325/// a `LazyAttrTokenStream`. Both delimiter and non-delimited tokens
326/// are stored as `FlatToken::Token`. A vector of `FlatToken`s
327/// is then 'parsed' to build up an `AttrTokenStream` with nested
328/// `AttrTokenTree::Delimited` tokens.
329#[derive(#[automatically_derived]
impl ::core::fmt::Debug for FlatToken {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        match self {
            FlatToken::Token(__self_0) =>
                ::core::fmt::Formatter::debug_tuple_field1_finish(f, "Token",
                    &__self_0),
            FlatToken::AttrsTarget(__self_0) =>
                ::core::fmt::Formatter::debug_tuple_field1_finish(f,
                    "AttrsTarget", &__self_0),
            FlatToken::Empty => ::core::fmt::Formatter::write_str(f, "Empty"),
        }
    }
}Debug, #[automatically_derived]
impl ::core::clone::Clone for FlatToken {
    #[inline]
    fn clone(&self) -> FlatToken {
        match self {
            FlatToken::Token(__self_0) =>
                FlatToken::Token(::core::clone::Clone::clone(__self_0)),
            FlatToken::AttrsTarget(__self_0) =>
                FlatToken::AttrsTarget(::core::clone::Clone::clone(__self_0)),
            FlatToken::Empty => FlatToken::Empty,
        }
    }
}Clone)]
330enum FlatToken {
331    /// A token - this holds both delimiter (e.g. '{' and '}')
332    /// and non-delimiter tokens
333    Token((Token, Spacing)),
334    /// Holds the `AttrsTarget` for an AST node. The `AttrsTarget` is inserted
335    /// directly into the constructed `AttrTokenStream` as an
336    /// `AttrTokenTree::AttrsTarget`.
337    AttrsTarget(AttrsTarget),
338    /// A special 'empty' token that is ignored during the conversion
339    /// to an `AttrTokenStream`. This is used to simplify the
340    /// handling of replace ranges.
341    Empty,
342}
343
344/// An `AttrTokenStream` is similar to a `TokenStream`, but with extra
345/// information about the tokens for attribute targets. This is used
346/// during expansion to perform early cfg-expansion, and to process attributes
347/// during proc-macro invocations.
348#[derive(#[automatically_derived]
impl ::core::clone::Clone for AttrTokenStream {
    #[inline]
    fn clone(&self) -> AttrTokenStream {
        AttrTokenStream(::core::clone::Clone::clone(&self.0))
    }
}Clone, #[automatically_derived]
impl ::core::fmt::Debug for AttrTokenStream {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::debug_tuple_field1_finish(f,
            "AttrTokenStream", &&self.0)
    }
}Debug, #[automatically_derived]
impl ::core::default::Default for AttrTokenStream {
    #[inline]
    fn default() -> AttrTokenStream {
        AttrTokenStream(::core::default::Default::default())
    }
}Default, const _: () =
    {
        impl<__E: ::rustc_span::SpanEncoder> ::rustc_serialize::Encodable<__E>
            for AttrTokenStream {
            fn encode(&self, __encoder: &mut __E) {
                match *self {
                    AttrTokenStream(ref __binding_0) => {
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_0,
                            __encoder);
                    }
                }
            }
        }
    };Encodable, const _: () =
    {
        impl<__D: ::rustc_span::SpanDecoder> ::rustc_serialize::Decodable<__D>
            for AttrTokenStream {
            fn decode(__decoder: &mut __D) -> Self {
                AttrTokenStream(::rustc_serialize::Decodable::decode(__decoder))
            }
        }
    };Decodable)]
349pub struct AttrTokenStream(pub Arc<Vec<AttrTokenTree>>);
350
351/// Converts a flattened iterator of tokens (including open and close delimiter tokens) into an
352/// `AttrTokenStream`, creating an `AttrTokenTree::Delimited` for each matching pair of open and
353/// close delims.
354fn make_attr_token_stream(
355    iter: impl Iterator<Item = FlatToken>,
356    break_last_token: u32,
357) -> AttrTokenStream {
358    #[derive(#[automatically_derived]
impl ::core::fmt::Debug for FrameData {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::debug_struct_field2_finish(f, "FrameData",
            "open_delim_sp", &self.open_delim_sp, "inner", &&self.inner)
    }
}Debug)]
359    struct FrameData {
360        // This is `None` for the first frame, `Some` for all others.
361        open_delim_sp: Option<(Delimiter, Span, Spacing)>,
362        inner: Vec<AttrTokenTree>,
363    }
364    // The stack always has at least one element. Storing it separately makes for shorter code.
365    let mut stack_top = FrameData { open_delim_sp: None, inner: ::alloc::vec::Vec::new()vec![] };
366    let mut stack_rest = ::alloc::vec::Vec::new()vec![];
367    for flat_token in iter {
368        match flat_token {
369            FlatToken::Token((token @ Token { kind, span }, spacing)) => {
370                if let Some(delim) = kind.open_delim() {
371                    stack_rest.push(mem::replace(
372                        &mut stack_top,
373                        FrameData { open_delim_sp: Some((delim, span, spacing)), inner: ::alloc::vec::Vec::new()vec![] },
374                    ));
375                } else if let Some(delim) = kind.close_delim() {
376                    // If there's no matching opening delimiter, the token stream is malformed,
377                    // likely due to a improper delimiter positions in the source code.
378                    // It's not delimiter mismatch, and lexer can not detect it, so we just ignore it here.
379                    let Some(frame) = stack_rest.pop() else {
380                        return AttrTokenStream::new(stack_top.inner);
381                    };
382                    let frame_data = mem::replace(&mut stack_top, frame);
383                    let (open_delim, open_sp, open_spacing) = frame_data.open_delim_sp.unwrap();
384                    if !open_delim.eq_ignoring_invisible_origin(&delim) {
    {
        ::core::panicking::panic_fmt(format_args!("Mismatched open/close delims: open={0:?} close={1:?}",
                open_delim, span));
    }
};assert!(
385                        open_delim.eq_ignoring_invisible_origin(&delim),
386                        "Mismatched open/close delims: open={open_delim:?} close={span:?}"
387                    );
388                    let dspan = DelimSpan::from_pair(open_sp, span);
389                    let dspacing = DelimSpacing::new(open_spacing, spacing);
390                    let stream = AttrTokenStream::new(frame_data.inner);
391                    let delimited = AttrTokenTree::Delimited(dspan, dspacing, delim, stream);
392                    stack_top.inner.push(delimited);
393                } else {
394                    stack_top.inner.push(AttrTokenTree::Token(token, spacing))
395                }
396            }
397            FlatToken::AttrsTarget(target) => {
398                stack_top.inner.push(AttrTokenTree::AttrsTarget(target))
399            }
400            FlatToken::Empty => {}
401        }
402    }
403
404    if break_last_token > 0 {
405        let last_token = stack_top.inner.pop().unwrap();
406        if let AttrTokenTree::Token(last_token, spacing) = last_token {
407            let (unglued, _) = last_token.kind.break_two_token_op(break_last_token).unwrap();
408
409            // Tokens are always ASCII chars, so we can use byte arithmetic here.
410            let mut first_span = last_token.span.shrink_to_lo();
411            first_span =
412                first_span.with_hi(first_span.lo() + rustc_span::BytePos(break_last_token));
413
414            stack_top.inner.push(AttrTokenTree::Token(Token::new(unglued, first_span), spacing));
415        } else {
416            {
    ::core::panicking::panic_fmt(format_args!("Unexpected last token {0:?}",
            last_token));
}panic!("Unexpected last token {last_token:?}")
417        }
418    }
419    AttrTokenStream::new(stack_top.inner)
420}
421
422/// Like `TokenTree`, but for `AttrTokenStream`.
423#[derive(#[automatically_derived]
impl ::core::clone::Clone for AttrTokenTree {
    #[inline]
    fn clone(&self) -> AttrTokenTree {
        match self {
            AttrTokenTree::Token(__self_0, __self_1) =>
                AttrTokenTree::Token(::core::clone::Clone::clone(__self_0),
                    ::core::clone::Clone::clone(__self_1)),
            AttrTokenTree::Delimited(__self_0, __self_1, __self_2, __self_3)
                =>
                AttrTokenTree::Delimited(::core::clone::Clone::clone(__self_0),
                    ::core::clone::Clone::clone(__self_1),
                    ::core::clone::Clone::clone(__self_2),
                    ::core::clone::Clone::clone(__self_3)),
            AttrTokenTree::AttrsTarget(__self_0) =>
                AttrTokenTree::AttrsTarget(::core::clone::Clone::clone(__self_0)),
        }
    }
}Clone, #[automatically_derived]
impl ::core::fmt::Debug for AttrTokenTree {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        match self {
            AttrTokenTree::Token(__self_0, __self_1) =>
                ::core::fmt::Formatter::debug_tuple_field2_finish(f, "Token",
                    __self_0, &__self_1),
            AttrTokenTree::Delimited(__self_0, __self_1, __self_2, __self_3)
                =>
                ::core::fmt::Formatter::debug_tuple_field4_finish(f,
                    "Delimited", __self_0, __self_1, __self_2, &__self_3),
            AttrTokenTree::AttrsTarget(__self_0) =>
                ::core::fmt::Formatter::debug_tuple_field1_finish(f,
                    "AttrsTarget", &__self_0),
        }
    }
}Debug, const _: () =
    {
        impl<__E: ::rustc_span::SpanEncoder> ::rustc_serialize::Encodable<__E>
            for AttrTokenTree {
            fn encode(&self, __encoder: &mut __E) {
                let disc =
                    match *self {
                        AttrTokenTree::Token(ref __binding_0, ref __binding_1) => {
                            0usize
                        }
                        AttrTokenTree::Delimited(ref __binding_0, ref __binding_1,
                            ref __binding_2, ref __binding_3) => {
                            1usize
                        }
                        AttrTokenTree::AttrsTarget(ref __binding_0) => { 2usize }
                    };
                ::rustc_serialize::Encoder::emit_u8(__encoder, disc as u8);
                match *self {
                    AttrTokenTree::Token(ref __binding_0, ref __binding_1) => {
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_0,
                            __encoder);
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_1,
                            __encoder);
                    }
                    AttrTokenTree::Delimited(ref __binding_0, ref __binding_1,
                        ref __binding_2, ref __binding_3) => {
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_0,
                            __encoder);
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_1,
                            __encoder);
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_2,
                            __encoder);
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_3,
                            __encoder);
                    }
                    AttrTokenTree::AttrsTarget(ref __binding_0) => {
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_0,
                            __encoder);
                    }
                }
            }
        }
    };Encodable, const _: () =
    {
        impl<__D: ::rustc_span::SpanDecoder> ::rustc_serialize::Decodable<__D>
            for AttrTokenTree {
            fn decode(__decoder: &mut __D) -> Self {
                match ::rustc_serialize::Decoder::read_u8(__decoder) as usize
                    {
                    0usize => {
                        AttrTokenTree::Token(::rustc_serialize::Decodable::decode(__decoder),
                            ::rustc_serialize::Decodable::decode(__decoder))
                    }
                    1usize => {
                        AttrTokenTree::Delimited(::rustc_serialize::Decodable::decode(__decoder),
                            ::rustc_serialize::Decodable::decode(__decoder),
                            ::rustc_serialize::Decodable::decode(__decoder),
                            ::rustc_serialize::Decodable::decode(__decoder))
                    }
                    2usize => {
                        AttrTokenTree::AttrsTarget(::rustc_serialize::Decodable::decode(__decoder))
                    }
                    n => {
                        ::core::panicking::panic_fmt(format_args!("invalid enum variant tag while decoding `AttrTokenTree`, expected 0..3, actual {0}",
                                n));
                    }
                }
            }
        }
    };Decodable)]
424pub enum AttrTokenTree {
425    Token(Token, Spacing),
426    Delimited(DelimSpan, DelimSpacing, Delimiter, AttrTokenStream),
427    /// Stores the attributes for an attribute target,
428    /// along with the tokens for that attribute target.
429    /// See `AttrsTarget` for more information
430    AttrsTarget(AttrsTarget),
431}
432
433impl AttrTokenStream {
434    pub fn new(tokens: Vec<AttrTokenTree>) -> AttrTokenStream {
435        AttrTokenStream(Arc::new(tokens))
436    }
437
438    /// Converts this `AttrTokenStream` to a plain `Vec<TokenTree>`. During
439    /// conversion, any `AttrTokenTree::AttrsTarget` gets "flattened" back to a
440    /// `TokenStream`, as described in the comment on
441    /// `attrs_and_tokens_to_token_trees`.
442    pub fn to_token_trees(&self) -> Vec<TokenTree> {
443        let mut res = Vec::with_capacity(self.0.len());
444        for tree in self.0.iter() {
445            match tree {
446                AttrTokenTree::Token(inner, spacing) => {
447                    res.push(TokenTree::Token(inner.clone(), *spacing));
448                }
449                AttrTokenTree::Delimited(span, spacing, delim, stream) => {
450                    res.push(TokenTree::Delimited(
451                        *span,
452                        *spacing,
453                        *delim,
454                        TokenStream::new(stream.to_token_trees()),
455                    ))
456                }
457                AttrTokenTree::AttrsTarget(target) => {
458                    attrs_and_tokens_to_token_trees(&target.attrs, &target.tokens, &mut res);
459                }
460            }
461        }
462        res
463    }
464}
465
466// Converts multiple attributes and the tokens for a target AST node into token trees, and appends
467// them to `res`.
468//
469// Example: if the AST node is "fn f() { blah(); }", then:
470// - Simple if no attributes are present, e.g. "fn f() { blah(); }"
471// - Simple if only outer attribute are present, e.g. "#[outer1] #[outer2] fn f() { blah(); }"
472// - Trickier if inner attributes are present, because they must be moved within the AST node's
473//   tokens, e.g. "#[outer] fn f() { #![inner] blah() }"
474fn attrs_and_tokens_to_token_trees(
475    attrs: &[Attribute],
476    target_tokens: &LazyAttrTokenStream,
477    res: &mut Vec<TokenTree>,
478) {
479    let idx = attrs.partition_point(|attr| #[allow(non_exhaustive_omitted_patterns)] match attr.style {
    crate::AttrStyle::Outer => true,
    _ => false,
}matches!(attr.style, crate::AttrStyle::Outer));
480    let (outer_attrs, inner_attrs) = attrs.split_at(idx);
481
482    // Add outer attribute tokens.
483    for attr in outer_attrs {
484        res.extend(attr.token_trees());
485    }
486
487    // Add target AST node tokens.
488    res.extend(target_tokens.to_attr_token_stream().to_token_trees());
489
490    // Insert inner attribute tokens.
491    if !inner_attrs.is_empty() {
492        let found = insert_inner_attrs(inner_attrs, res);
493        if !found {
    {
        ::core::panicking::panic_fmt(format_args!("Failed to find trailing delimited group in: {0:?}",
                res));
    }
};assert!(found, "Failed to find trailing delimited group in: {res:?}");
494    }
495
496    // Inner attributes are only supported on blocks, functions, impls, and
497    // modules. All of these have their inner attributes placed at the
498    // beginning of the rightmost outermost braced group:
499    // e.g. `fn foo() { #![my_attr] }`. (Note: the braces may be within
500    // invisible delimiters.)
501    //
502    // Therefore, we can insert them back into the right location without
503    // needing to do any extra position tracking.
504    //
505    // Note: Outline modules are an exception - they can have attributes like
506    // `#![my_attr]` at the start of a file. Support for custom attributes in
507    // this position is not properly implemented - we always synthesize fake
508    // tokens, so we never reach this code.
509    fn insert_inner_attrs(inner_attrs: &[Attribute], tts: &mut Vec<TokenTree>) -> bool {
510        for tree in tts.iter_mut().rev() {
511            if let TokenTree::Delimited(span, spacing, Delimiter::Brace, stream) = tree {
512                // Found it: the rightmost, outermost braced group.
513                let mut tts = ::alloc::vec::Vec::new()vec![];
514                for inner_attr in inner_attrs {
515                    tts.extend(inner_attr.token_trees());
516                }
517                tts.extend(stream.0.iter().cloned());
518                let stream = TokenStream::new(tts);
519                *tree = TokenTree::Delimited(*span, *spacing, Delimiter::Brace, stream);
520                return true;
521            } else if let TokenTree::Delimited(span, spacing, Delimiter::Invisible(src), stream) =
522                tree
523            {
524                // Recurse inside invisible delimiters.
525                let mut vec: Vec<_> = stream.iter().cloned().collect();
526                if insert_inner_attrs(inner_attrs, &mut vec) {
527                    *tree = TokenTree::Delimited(
528                        *span,
529                        *spacing,
530                        Delimiter::Invisible(*src),
531                        TokenStream::new(vec),
532                    );
533                    return true;
534                }
535            }
536        }
537        false
538    }
539}
540
541/// Stores the tokens for an attribute target, along
542/// with its attributes.
543///
544/// This is constructed during parsing when we need to capture
545/// tokens, for `cfg` and `cfg_attr` attributes.
546///
547/// For example, `#[cfg(FALSE)] struct Foo {}` would
548/// have an `attrs` field containing the `#[cfg(FALSE)]` attr,
549/// and a `tokens` field storing the (unparsed) tokens `struct Foo {}`
550///
551/// The `cfg`/`cfg_attr` processing occurs in
552/// `StripUnconfigured::configure_tokens`.
553#[derive(#[automatically_derived]
impl ::core::clone::Clone for AttrsTarget {
    #[inline]
    fn clone(&self) -> AttrsTarget {
        AttrsTarget {
            attrs: ::core::clone::Clone::clone(&self.attrs),
            tokens: ::core::clone::Clone::clone(&self.tokens),
        }
    }
}Clone, #[automatically_derived]
impl ::core::fmt::Debug for AttrsTarget {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::debug_struct_field2_finish(f, "AttrsTarget",
            "attrs", &self.attrs, "tokens", &&self.tokens)
    }
}Debug, const _: () =
    {
        impl<__E: ::rustc_span::SpanEncoder> ::rustc_serialize::Encodable<__E>
            for AttrsTarget {
            fn encode(&self, __encoder: &mut __E) {
                match *self {
                    AttrsTarget {
                        attrs: ref __binding_0, tokens: ref __binding_1 } => {
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_0,
                            __encoder);
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_1,
                            __encoder);
                    }
                }
            }
        }
    };Encodable, const _: () =
    {
        impl<__D: ::rustc_span::SpanDecoder> ::rustc_serialize::Decodable<__D>
            for AttrsTarget {
            fn decode(__decoder: &mut __D) -> Self {
                AttrsTarget {
                    attrs: ::rustc_serialize::Decodable::decode(__decoder),
                    tokens: ::rustc_serialize::Decodable::decode(__decoder),
                }
            }
        }
    };Decodable)]
554pub struct AttrsTarget {
555    /// Attributes, both outer and inner.
556    /// These are stored in the original order that they were parsed in.
557    pub attrs: AttrVec,
558    /// The underlying tokens for the attribute target that `attrs`
559    /// are applied to
560    pub tokens: LazyAttrTokenStream,
561}
562
563/// Indicates whether a token can join with the following token to form a
564/// compound token. Used for conversions to `proc_macro::Spacing`. Also used to
565/// guide pretty-printing, which is where the `JointHidden` value (which isn't
566/// part of `proc_macro::Spacing`) comes in useful.
567#[derive(#[automatically_derived]
impl ::core::clone::Clone for Spacing {
    #[inline]
    fn clone(&self) -> Spacing { *self }
}Clone, #[automatically_derived]
impl ::core::marker::Copy for Spacing { }Copy, #[automatically_derived]
impl ::core::fmt::Debug for Spacing {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::write_str(f,
            match self {
                Spacing::Alone => "Alone",
                Spacing::Joint => "Joint",
                Spacing::JointHidden => "JointHidden",
            })
    }
}Debug, #[automatically_derived]
impl ::core::cmp::PartialEq for Spacing {
    #[inline]
    fn eq(&self, other: &Spacing) -> bool {
        let __self_discr = ::core::intrinsics::discriminant_value(self);
        let __arg1_discr = ::core::intrinsics::discriminant_value(other);
        __self_discr == __arg1_discr
    }
}PartialEq, #[automatically_derived]
impl ::core::cmp::Eq for Spacing {
    #[inline]
    #[doc(hidden)]
    #[coverage(off)]
    fn assert_fields_are_eq(&self) {}
}Eq, #[automatically_derived]
impl ::core::hash::Hash for Spacing {
    #[inline]
    fn hash<__H: ::core::hash::Hasher>(&self, state: &mut __H) {
        let __self_discr = ::core::intrinsics::discriminant_value(self);
        ::core::hash::Hash::hash(&__self_discr, state)
    }
}Hash, const _: () =
    {
        impl<__E: ::rustc_span::SpanEncoder> ::rustc_serialize::Encodable<__E>
            for Spacing {
            fn encode(&self, __encoder: &mut __E) {
                let disc =
                    match *self {
                        Spacing::Alone => { 0usize }
                        Spacing::Joint => { 1usize }
                        Spacing::JointHidden => { 2usize }
                    };
                ::rustc_serialize::Encoder::emit_u8(__encoder, disc as u8);
                match *self {
                    Spacing::Alone => {}
                    Spacing::Joint => {}
                    Spacing::JointHidden => {}
                }
            }
        }
    };Encodable, const _: () =
    {
        impl<__D: ::rustc_span::SpanDecoder> ::rustc_serialize::Decodable<__D>
            for Spacing {
            fn decode(__decoder: &mut __D) -> Self {
                match ::rustc_serialize::Decoder::read_u8(__decoder) as usize
                    {
                    0usize => { Spacing::Alone }
                    1usize => { Spacing::Joint }
                    2usize => { Spacing::JointHidden }
                    n => {
                        ::core::panicking::panic_fmt(format_args!("invalid enum variant tag while decoding `Spacing`, expected 0..3, actual {0}",
                                n));
                    }
                }
            }
        }
    };Decodable, const _: () =
    {
        impl ::rustc_data_structures::stable_hash::StableHash for Spacing {
            #[inline]
            fn stable_hash<__Hcx: ::rustc_data_structures::stable_hash::StableHashCtxt>(&self,
                __hcx: &mut __Hcx,
                __hasher:
                    &mut ::rustc_data_structures::stable_hash::StableHasher) {
                ::std::mem::discriminant(self).stable_hash(__hcx, __hasher);
                match *self {
                    Spacing::Alone => {}
                    Spacing::Joint => {}
                    Spacing::JointHidden => {}
                }
            }
        }
    };StableHash)]
568pub enum Spacing {
569    /// The token cannot join with the following token to form a compound
570    /// token.
571    ///
572    /// In token streams parsed from source code, the compiler will use `Alone`
573    /// for any token immediately followed by whitespace, a non-doc comment, or
574    /// EOF.
575    ///
576    /// When constructing token streams within the compiler, use this for each
577    /// token that (a) should be pretty-printed with a space after it, or (b)
578    /// is the last token in the stream. (In the latter case the choice of
579    /// spacing doesn't matter because it is never used for the last token. We
580    /// arbitrarily use `Alone`.)
581    ///
582    /// Converts to `proc_macro::Spacing::Alone`, and
583    /// `proc_macro::Spacing::Alone` converts back to this.
584    Alone,
585
586    /// The token can join with the following token to form a compound token.
587    ///
588    /// In token streams parsed from source code, the compiler will use `Joint`
589    /// for any token immediately followed by punctuation (as determined by
590    /// `Token::is_punct`).
591    ///
592    /// When constructing token streams within the compiler, use this for each
593    /// token that (a) should be pretty-printed without a space after it, and
594    /// (b) is followed by a punctuation token.
595    ///
596    /// Converts to `proc_macro::Spacing::Joint`, and
597    /// `proc_macro::Spacing::Joint` converts back to this.
598    Joint,
599
600    /// The token can join with the following token to form a compound token,
601    /// but this will not be visible at the proc macro level. (This is what the
602    /// `Hidden` means; see below.)
603    ///
604    /// In token streams parsed from source code, the compiler will use
605    /// `JointHidden` for any token immediately followed by anything not
606    /// covered by the `Alone` and `Joint` cases: an identifier, lifetime,
607    /// literal, delimiter, doc comment.
608    ///
609    /// When constructing token streams, use this for each token that (a)
610    /// should be pretty-printed without a space after it, and (b) is followed
611    /// by a non-punctuation token.
612    ///
613    /// Converts to `proc_macro::Spacing::Alone`, but
614    /// `proc_macro::Spacing::Alone` converts back to `token::Spacing::Alone`.
615    /// Because of that, pretty-printing of `TokenStream`s produced by proc
616    /// macros is unavoidably uglier (with more whitespace between tokens) than
617    /// pretty-printing of `TokenStream`'s produced by other means (i.e. parsed
618    /// source code, internally constructed token streams, and token streams
619    /// produced by declarative macros).
620    JointHidden,
621}
622
623/// A `TokenStream` is an abstract sequence of tokens, organized into [`TokenTree`]s.
624#[derive(#[automatically_derived]
impl ::core::clone::Clone for TokenStream {
    #[inline]
    fn clone(&self) -> TokenStream {
        TokenStream(::core::clone::Clone::clone(&self.0))
    }
}Clone, #[automatically_derived]
impl ::core::fmt::Debug for TokenStream {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::debug_tuple_field1_finish(f, "TokenStream",
            &&self.0)
    }
}Debug, #[automatically_derived]
impl ::core::default::Default for TokenStream {
    #[inline]
    fn default() -> TokenStream {
        TokenStream(::core::default::Default::default())
    }
}Default, #[automatically_derived]
impl ::core::cmp::PartialEq for TokenStream {
    #[inline]
    fn eq(&self, other: &TokenStream) -> bool { self.0 == other.0 }
}PartialEq, #[automatically_derived]
impl ::core::cmp::Eq for TokenStream {
    #[inline]
    #[doc(hidden)]
    #[coverage(off)]
    fn assert_fields_are_eq(&self) {
        let _: ::core::cmp::AssertParamIsEq<Arc<Vec<TokenTree>>>;
    }
}Eq, #[automatically_derived]
impl ::core::hash::Hash for TokenStream {
    #[inline]
    fn hash<__H: ::core::hash::Hasher>(&self, state: &mut __H) {
        ::core::hash::Hash::hash(&self.0, state)
    }
}Hash, const _: () =
    {
        impl<__E: ::rustc_span::SpanEncoder> ::rustc_serialize::Encodable<__E>
            for TokenStream {
            fn encode(&self, __encoder: &mut __E) {
                match *self {
                    TokenStream(ref __binding_0) => {
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_0,
                            __encoder);
                    }
                }
            }
        }
    };Encodable, const _: () =
    {
        impl<__D: ::rustc_span::SpanDecoder> ::rustc_serialize::Decodable<__D>
            for TokenStream {
            fn decode(__decoder: &mut __D) -> Self {
                TokenStream(::rustc_serialize::Decodable::decode(__decoder))
            }
        }
    };Decodable)]
625pub struct TokenStream(Arc<Vec<TokenTree>>);
626
627impl TokenStream {
628    pub fn new(tts: Vec<TokenTree>) -> TokenStream {
629        TokenStream(Arc::new(tts))
630    }
631
632    pub fn is_empty(&self) -> bool {
633        self.0.is_empty()
634    }
635
636    pub fn len(&self) -> usize {
637        self.0.len()
638    }
639
640    pub fn get(&self, index: usize) -> Option<&TokenTree> {
641        self.0.get(index)
642    }
643
644    pub fn iter(&self) -> TokenStreamIter<'_> {
645        TokenStreamIter::new(self)
646    }
647
648    /// Create a token stream containing a single token with alone spacing. The
649    /// spacing used for the final token in a constructed stream doesn't matter
650    /// because it's never used. In practice we arbitrarily use
651    /// `Spacing::Alone`.
652    pub fn token_alone(kind: TokenKind, span: Span) -> TokenStream {
653        TokenStream::new(::alloc::boxed::box_assume_init_into_vec_unsafe(::alloc::intrinsics::write_box_via_move(::alloc::boxed::Box::new_uninit(),
        [TokenTree::token_alone(kind, span)]))vec![TokenTree::token_alone(kind, span)])
654    }
655
656    pub fn from_ast(node: &(impl HasTokens + fmt::Debug)) -> TokenStream {
657        let tokens = node.tokens().unwrap_or_else(|| {
    ::core::panicking::panic_fmt(format_args!("missing tokens for node: {0:?}",
            node));
}panic!("missing tokens for node: {:?}", node));
658        let mut tts = ::alloc::vec::Vec::new()vec![];
659        attrs_and_tokens_to_token_trees(node.attrs(), tokens, &mut tts);
660        TokenStream::new(tts)
661    }
662
663    // If `vec` is not empty, try to glue `tt` onto its last token. The return
664    // value indicates if gluing took place.
665    fn try_glue_to_last(vec: &mut [TokenTree], tt: &TokenTree) -> bool {
666        if let Some(TokenTree::Token(last_tok, Spacing::Joint | Spacing::JointHidden)) = vec.last()
667            && let TokenTree::Token(tok, spacing) = tt
668            && let Some(glued_tok) = last_tok.glue(tok)
669        {
670            // ...then overwrite the last token tree in `vec` with the glued token.
671            *vec.last_mut().unwrap() = TokenTree::Token(glued_tok, *spacing);
672            true
673        } else {
674            false
675        }
676    }
677
678    /// Push `tt` onto the end of the stream, possibly gluing it to the last
679    /// token. Uses `make_mut` to maximize efficiency.
680    ///
681    /// This is intended for specific proc macro use. For general `TokenStream`
682    /// construction within the compiler just build a `Vec<TokenTree>` with
683    /// normal `Vec` operations and then do `TokenStream::new`.
684    pub fn push_tree_with_gluing(&mut self, tt: TokenTree) {
685        let vec_mut = Arc::make_mut(&mut self.0);
686
687        if Self::try_glue_to_last(vec_mut, &tt) {
688            // nothing else to do
689        } else {
690            vec_mut.push(tt);
691        }
692    }
693
694    /// Push `stream` onto the end of the stream, possibly gluing the first
695    /// token tree to the last token. (No other token trees will be glued.)
696    /// Uses `make_mut` to maximize efficiency.
697    ///
698    /// This is intended for specific proc macro use. For general `TokenStream`
699    /// construction within the compiler just build a `Vec<TokenTree>` with
700    /// normal `Vec` operations and then do `TokenStream::new`.
701    pub fn push_stream_with_gluing(&mut self, stream: TokenStream) {
702        let vec_mut = Arc::make_mut(&mut self.0);
703
704        let stream_iter = stream.0.iter().cloned();
705
706        if let Some(first) = stream.0.first()
707            && Self::try_glue_to_last(vec_mut, first)
708        {
709            // Now skip the first token tree from `stream`.
710            vec_mut.extend(stream_iter.skip(1));
711        } else {
712            // Append all of `stream`.
713            vec_mut.extend(stream_iter);
714        }
715    }
716
717    /// Desugar doc comments like `/// foo` in the stream into `#[doc =
718    /// r"foo"]`. Modifies the `TokenStream` via `Arc::make_mut`, but as little
719    /// as possible.
720    pub fn desugar_doc_comments(&mut self) {
721        if let Some(desugared_stream) = desugar_inner(self.clone()) {
722            *self = desugared_stream;
723        }
724
725        // The return value is `None` if nothing in `stream` changed.
726        fn desugar_inner(mut stream: TokenStream) -> Option<TokenStream> {
727            let mut i = 0;
728            let mut modified = false;
729            while let Some(tt) = stream.0.get(i) {
730                match tt {
731                    &TokenTree::Token(
732                        Token { kind: token::DocComment(_, attr_style, data), span },
733                        _spacing,
734                    ) => {
735                        let desugared = desugared_tts(attr_style, data, span);
736                        let desugared_len = desugared.len();
737                        Arc::make_mut(&mut stream.0).splice(i..i + 1, desugared);
738                        modified = true;
739                        i += desugared_len;
740                    }
741
742                    &TokenTree::Token(..) => i += 1,
743
744                    &TokenTree::Delimited(sp, spacing, delim, ref delim_stream) => {
745                        if let Some(desugared_delim_stream) = desugar_inner(delim_stream.clone()) {
746                            let new_tt =
747                                TokenTree::Delimited(sp, spacing, delim, desugared_delim_stream);
748                            Arc::make_mut(&mut stream.0)[i] = new_tt;
749                            modified = true;
750                        }
751                        i += 1;
752                    }
753                }
754            }
755            if modified { Some(stream) } else { None }
756        }
757
758        fn desugared_tts(attr_style: AttrStyle, data: Symbol, span: Span) -> Vec<TokenTree> {
759            // Searches for the occurrences of `"#*` and returns the minimum number of `#`s
760            // required to wrap the text. E.g.
761            // - `abc d` is wrapped as `r"abc d"` (num_of_hashes = 0)
762            // - `abc "d"` is wrapped as `r#"abc "d""#` (num_of_hashes = 1)
763            // - `abc "##d##"` is wrapped as `r###"abc ##"d"##"###` (num_of_hashes = 3)
764            let mut num_of_hashes = 0;
765            let mut count = 0;
766            for ch in data.as_str().chars() {
767                count = match ch {
768                    '"' => 1,
769                    '#' if count > 0 => count + 1,
770                    _ => 0,
771                };
772                num_of_hashes = cmp::max(num_of_hashes, count);
773            }
774
775            // `/// foo` becomes `[doc = r"foo"]`.
776            let delim_span = DelimSpan::from_single(span);
777            let body = TokenTree::Delimited(
778                delim_span,
779                DelimSpacing::new(Spacing::JointHidden, Spacing::Alone),
780                Delimiter::Bracket,
781                [
782                    TokenTree::token_alone(token::Ident(sym::doc, token::IdentIsRaw::No), span),
783                    TokenTree::token_alone(token::Eq, span),
784                    TokenTree::token_alone(
785                        TokenKind::lit(token::StrRaw(num_of_hashes), data, None),
786                        span,
787                    ),
788                ]
789                .into_iter()
790                .collect::<TokenStream>(),
791            );
792
793            if attr_style == AttrStyle::Inner {
794                ::alloc::boxed::box_assume_init_into_vec_unsafe(::alloc::intrinsics::write_box_via_move(::alloc::boxed::Box::new_uninit(),
        [TokenTree::token_joint(token::Pound, span),
                TokenTree::token_joint_hidden(token::Bang, span), body]))vec![
795                    TokenTree::token_joint(token::Pound, span),
796                    TokenTree::token_joint_hidden(token::Bang, span),
797                    body,
798                ]
799            } else {
800                ::alloc::boxed::box_assume_init_into_vec_unsafe(::alloc::intrinsics::write_box_via_move(::alloc::boxed::Box::new_uninit(),
        [TokenTree::token_joint_hidden(token::Pound, span), body]))vec![TokenTree::token_joint_hidden(token::Pound, span), body]
801            }
802        }
803    }
804
805    /// Given a `TokenStream` with a `Stream` of only two arguments, return a new `TokenStream`
806    /// separating the two arguments with a comma for diagnostic suggestions.
807    pub fn add_comma(&self) -> Option<(TokenStream, Span)> {
808        // Used to suggest if a user writes `foo!(a b);`
809        let mut suggestion = None;
810        let mut iter = self.0.iter().enumerate().peekable();
811        while let Some((pos, ts)) = iter.next() {
812            if let Some((_, next)) = iter.peek() {
813                let sp = match (&ts, &next) {
814                    (_, TokenTree::Token(Token { kind: token::Comma, .. }, _)) => continue,
815                    (
816                        TokenTree::Token(token_left, Spacing::Alone),
817                        TokenTree::Token(token_right, _),
818                    ) if (token_left.is_non_reserved_ident() || token_left.is_lit())
819                        && (token_right.is_non_reserved_ident() || token_right.is_lit()) =>
820                    {
821                        token_left.span
822                    }
823                    (TokenTree::Delimited(sp, ..), _) => sp.entire(),
824                    _ => continue,
825                };
826                let sp = sp.shrink_to_hi();
827                let comma = TokenTree::token_alone(token::Comma, sp);
828                suggestion = Some((pos, comma, sp));
829            }
830        }
831        if let Some((pos, comma, sp)) = suggestion {
832            let mut new_stream = Vec::with_capacity(self.0.len() + 1);
833            let parts = self.0.split_at(pos + 1);
834            new_stream.extend_from_slice(parts.0);
835            new_stream.push(comma);
836            new_stream.extend_from_slice(parts.1);
837            return Some((TokenStream::new(new_stream), sp));
838        }
839        None
840    }
841}
842
843impl FromIterator<TokenTree> for TokenStream {
844    fn from_iter<I: IntoIterator<Item = TokenTree>>(iter: I) -> Self {
845        TokenStream::new(iter.into_iter().collect::<Vec<TokenTree>>())
846    }
847}
848
849impl StableHash for TokenStream {
850    fn stable_hash<Hcx: StableHashCtxt>(&self, hcx: &mut Hcx, hasher: &mut StableHasher) {
851        self.0.as_slice().stable_hash(hcx, hasher);
852    }
853}
854
855#[derive(#[automatically_derived]
impl<'t> ::core::clone::Clone for TokenStreamIter<'t> {
    #[inline]
    fn clone(&self) -> TokenStreamIter<'t> {
        TokenStreamIter(::core::clone::Clone::clone(&self.0))
    }
}Clone)]
856pub struct TokenStreamIter<'t>(std::slice::Iter<'t, TokenTree>);
857
858impl<'t> TokenStreamIter<'t> {
859    fn new(stream: &'t TokenStream) -> Self {
860        TokenStreamIter(stream.0.as_slice().iter())
861    }
862
863    // Peeking could be done via `Peekable`, but most iterators need peeking,
864    // and this is simple and avoids the need to use `peekable` and `Peekable`
865    // at all the use sites.
866    pub fn peek(&self) -> Option<&'t TokenTree> {
867        self.0.as_slice().first()
868    }
869}
870
871impl<'t> Iterator for TokenStreamIter<'t> {
872    type Item = &'t TokenTree;
873
874    fn next(&mut self) -> Option<&'t TokenTree> {
875        self.0.next()
876    }
877
878    fn size_hint(&self) -> (usize, Option<usize>) {
879        self.0.size_hint()
880    }
881}
882
883#[derive(#[automatically_derived]
impl ::core::clone::Clone for TokenTreeCursor {
    #[inline]
    fn clone(&self) -> TokenTreeCursor {
        TokenTreeCursor {
            stream: ::core::clone::Clone::clone(&self.stream),
            index: ::core::clone::Clone::clone(&self.index),
        }
    }
}Clone, #[automatically_derived]
impl ::core::fmt::Debug for TokenTreeCursor {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::debug_struct_field2_finish(f,
            "TokenTreeCursor", "stream", &self.stream, "index", &&self.index)
    }
}Debug)]
884struct TokenTreeCursor {
885    stream: TokenStream,
886    /// Points to the current token tree in the stream. In `TokenCursor::curr`,
887    /// this can be any token tree. In `TokenCursor::stack`, this is always a
888    /// `TokenTree::Delimited`.
889    index: usize,
890}
891
892impl TokenTreeCursor {
893    #[inline]
894    fn new(stream: TokenStream) -> Self {
895        TokenTreeCursor { stream, index: 0 }
896    }
897
898    #[inline]
899    fn curr(&self) -> Option<&TokenTree> {
900        self.stream.get(self.index)
901    }
902
903    fn look_ahead(&self, n: usize) -> Option<&TokenTree> {
904        self.stream.get(self.index + n)
905    }
906
907    #[inline]
908    fn bump(&mut self) {
909        self.index += 1;
910    }
911
912    // For skipping ahead in rare circumstances.
913    #[inline]
914    fn bump_to_end(&mut self) {
915        self.index = self.stream.len();
916    }
917}
918
919/// A `TokenStream` cursor that produces `Token`s. It's a bit odd that
920/// we (a) lex tokens into a nice tree structure (`TokenStream`), and then (b)
921/// use this type to emit them as a linear sequence. But a linear sequence is
922/// what the parser expects, for the most part.
923#[derive(#[automatically_derived]
impl ::core::clone::Clone for TokenCursor {
    #[inline]
    fn clone(&self) -> TokenCursor {
        TokenCursor {
            curr: ::core::clone::Clone::clone(&self.curr),
            stack: ::core::clone::Clone::clone(&self.stack),
        }
    }
}Clone, #[automatically_derived]
impl ::core::fmt::Debug for TokenCursor {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::debug_struct_field2_finish(f, "TokenCursor",
            "curr", &self.curr, "stack", &&self.stack)
    }
}Debug)]
924pub struct TokenCursor {
925    // Cursor for the current (innermost) token stream. The index within the
926    // cursor can point to any token tree in the stream (or one past the end).
927    // The delimiters for this token stream are found in `self.stack.last()`;
928    // if that is `None` we are in the outermost token stream which never has
929    // delimiters.
930    curr: TokenTreeCursor,
931
932    // Token streams surrounding the current one. The index within each cursor
933    // always points to a `TokenTree::Delimited`.
934    stack: Vec<TokenTreeCursor>,
935}
936
937impl TokenCursor {
938    #[inline]
939    pub fn new(stream: TokenStream) -> Self {
940        TokenCursor { curr: TokenTreeCursor::new(stream), stack: ::alloc::vec::Vec::new()vec![] }
941    }
942
943    pub fn next(&mut self) -> (Token, Spacing) {
944        self.inlined_next()
945    }
946
947    /// An `n` of zero is the next token tree in the current token stream; won't look outside the
948    /// current token stream.
949    #[inline]
950    pub fn look_ahead(&self, n: usize) -> Option<&TokenTree> {
951        self.curr.look_ahead(n)
952    }
953
954    /// Returns the first token tree (if there is one) past the close delimiter of the enclosing
955    /// delimited sequence. Panics if we are not within a delimited sequence.
956    #[inline]
957    pub fn look_ahead_past_close_delim(&self) -> Option<&TokenTree> {
958        self.stack.last().unwrap().look_ahead(1)
959    }
960
961    /// Clones the `TokenTree::Delimited` that we are currently within. Panics if we are not within
962    /// a delimited sequence.
963    #[inline]
964    pub fn clone_enclosing_delim(&self) -> TokenTree {
965        self.stack.last().unwrap().curr().unwrap().clone()
966    }
967
968    /// For skipping to the end of the current sequence, in rare circumstances.
969    #[inline]
970    pub fn bump_to_end(&mut self) {
971        self.curr.bump_to_end()
972    }
973
974    /// Note: the outermost stream has depth of 0.
975    #[inline]
976    pub fn depth(&self) -> usize {
977        self.stack.len()
978    }
979
980    /// Returns details about the parent delimited sequence, if there is one.
981    #[inline]
982    pub fn parent_delim_and_span(&self) -> Option<(Delimiter, DelimSpan)> {
983        if let Some(last) = self.stack.last()
984            && let Some(TokenTree::Delimited(span, _, delim, _)) = last.curr()
985        {
986            Some((*delim, *span))
987        } else {
988            None
989        }
990    }
991
992    /// This always-inlined version should only be used on hot code paths.
993    #[inline(always)]
994    pub fn inlined_next(&mut self) -> (Token, Spacing) {
995        loop {
996            // FIXME: we currently don't return `Delimiter::Invisible` open/close delims. To fix
997            // #67062 we will need to, whereupon the `delim != Delimiter::Invisible` conditions
998            // below can be removed.
999            if let Some(tree) = self.curr.curr() {
1000                match tree {
1001                    &TokenTree::Token(token, spacing) => {
1002                        if true {
    if !!token.kind.is_delim() {
        ::core::panicking::panic("assertion failed: !token.kind.is_delim()")
    };
};debug_assert!(!token.kind.is_delim());
1003                        let res = (token, spacing);
1004                        self.curr.bump();
1005                        return res;
1006                    }
1007                    &TokenTree::Delimited(sp, spacing, delim, ref tts) => {
1008                        let trees = TokenTreeCursor::new(tts.clone());
1009                        self.stack.push(mem::replace(&mut self.curr, trees));
1010                        if !delim.skip() {
1011                            return (Token::new(delim.as_open_token_kind(), sp.open), spacing.open);
1012                        }
1013                        // No open delimiter to return; continue on to the next iteration.
1014                    }
1015                };
1016            } else if let Some(parent) = self.stack.pop() {
1017                // We have exhausted this token stream. Move back to its parent token stream.
1018                let Some(&TokenTree::Delimited(span, spacing, delim, _)) = parent.curr() else {
1019                    { ::core::panicking::panic_fmt(format_args!("parent should be Delimited")); }panic!("parent should be Delimited")
1020                };
1021                self.curr = parent;
1022                self.curr.bump(); // move past the `Delimited`
1023                if !delim.skip() {
1024                    return (Token::new(delim.as_close_token_kind(), span.close), spacing.close);
1025                }
1026                // No close delimiter to return; continue on to the next iteration.
1027            } else {
1028                // We have exhausted the outermost token stream. The use of
1029                // `Spacing::Alone` is arbitrary and immaterial, because the
1030                // `Eof` token's spacing is never used.
1031                return (Token::new(token::Eof, DUMMY_SP), Spacing::Alone);
1032            }
1033        }
1034    }
1035}
1036
1037#[derive(#[automatically_derived]
impl ::core::fmt::Debug for DelimSpan {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::debug_struct_field2_finish(f, "DelimSpan",
            "open", &self.open, "close", &&self.close)
    }
}Debug, #[automatically_derived]
impl ::core::marker::Copy for DelimSpan { }Copy, #[automatically_derived]
impl ::core::clone::Clone for DelimSpan {
    #[inline]
    fn clone(&self) -> DelimSpan {
        let _: ::core::clone::AssertParamIsClone<Span>;
        *self
    }
}Clone, #[automatically_derived]
impl ::core::cmp::PartialEq for DelimSpan {
    #[inline]
    fn eq(&self, other: &DelimSpan) -> bool {
        self.open == other.open && self.close == other.close
    }
}PartialEq, #[automatically_derived]
impl ::core::cmp::Eq for DelimSpan {
    #[inline]
    #[doc(hidden)]
    #[coverage(off)]
    fn assert_fields_are_eq(&self) {
        let _: ::core::cmp::AssertParamIsEq<Span>;
    }
}Eq, #[automatically_derived]
impl ::core::hash::Hash for DelimSpan {
    #[inline]
    fn hash<__H: ::core::hash::Hasher>(&self, state: &mut __H) {
        ::core::hash::Hash::hash(&self.open, state);
        ::core::hash::Hash::hash(&self.close, state)
    }
}Hash)]
1038#[derive(const _: () =
    {
        impl<__E: ::rustc_span::SpanEncoder> ::rustc_serialize::Encodable<__E>
            for DelimSpan {
            fn encode(&self, __encoder: &mut __E) {
                match *self {
                    DelimSpan { open: ref __binding_0, close: ref __binding_1 }
                        => {
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_0,
                            __encoder);
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_1,
                            __encoder);
                    }
                }
            }
        }
    };Encodable, const _: () =
    {
        impl<__D: ::rustc_span::SpanDecoder> ::rustc_serialize::Decodable<__D>
            for DelimSpan {
            fn decode(__decoder: &mut __D) -> Self {
                DelimSpan {
                    open: ::rustc_serialize::Decodable::decode(__decoder),
                    close: ::rustc_serialize::Decodable::decode(__decoder),
                }
            }
        }
    };Decodable, const _: () =
    {
        impl ::rustc_data_structures::stable_hash::StableHash for DelimSpan {
            #[inline]
            fn stable_hash<__Hcx: ::rustc_data_structures::stable_hash::StableHashCtxt>(&self,
                __hcx: &mut __Hcx,
                __hasher:
                    &mut ::rustc_data_structures::stable_hash::StableHasher) {
                match *self {
                    DelimSpan { open: ref __binding_0, close: ref __binding_1 }
                        => {
                        { __binding_0.stable_hash(__hcx, __hasher); }
                        { __binding_1.stable_hash(__hcx, __hasher); }
                    }
                }
            }
        }
    };StableHash, const _: () =
    {
        impl<'__ast, __V> crate::visit::Walkable<'__ast, __V> for DelimSpan
            where __V: crate::visit::Visitor<'__ast> {
            fn walk_ref(&'__ast self, __visitor: &mut __V) -> __V::Result {
                match *self {
                    DelimSpan { open: ref __binding_0, close: ref __binding_1 }
                        => {
                        {
                            match ::rustc_ast_ir::visit::VisitorResult::branch(crate::visit::Visitable::visit(__binding_0,
                                        __visitor, ())) {
                                core::ops::ControlFlow::Continue(()) =>
                                    (),
                                    #[allow(unreachable_code)]
                                    core::ops::ControlFlow::Break(r) => {
                                    return ::rustc_ast_ir::visit::VisitorResult::from_residual(r);
                                }
                            }
                        }
                        {
                            match ::rustc_ast_ir::visit::VisitorResult::branch(crate::visit::Visitable::visit(__binding_1,
                                        __visitor, ())) {
                                core::ops::ControlFlow::Continue(()) =>
                                    (),
                                    #[allow(unreachable_code)]
                                    core::ops::ControlFlow::Break(r) => {
                                    return ::rustc_ast_ir::visit::VisitorResult::from_residual(r);
                                }
                            }
                        }
                    }
                }
                <__V::Result as rustc_ast_ir::visit::VisitorResult>::output()
            }
        }
        impl<__V> crate::mut_visit::MutWalkable<__V> for DelimSpan where
            __V: crate::mut_visit::MutVisitor {
            fn walk_mut(&mut self, __visitor: &mut __V) {
                match *self {
                    DelimSpan {
                        open: ref mut __binding_0, close: ref mut __binding_1 } => {
                        {
                            crate::mut_visit::MutVisitable::visit_mut(__binding_0,
                                __visitor, ())
                        }
                        {
                            crate::mut_visit::MutVisitable::visit_mut(__binding_1,
                                __visitor, ())
                        }
                    }
                }
            }
        }
    };Walkable)]
1039pub struct DelimSpan {
1040    pub open: Span,
1041    pub close: Span,
1042}
1043
1044impl DelimSpan {
1045    pub fn from_single(sp: Span) -> Self {
1046        DelimSpan { open: sp, close: sp }
1047    }
1048
1049    pub fn from_pair(open: Span, close: Span) -> Self {
1050        DelimSpan { open, close }
1051    }
1052
1053    pub fn dummy() -> Self {
1054        Self::from_single(DUMMY_SP)
1055    }
1056
1057    pub fn entire(self) -> Span {
1058        self.open.with_hi(self.close.hi())
1059    }
1060}
1061
1062#[derive(#[automatically_derived]
impl ::core::marker::Copy for DelimSpacing { }Copy, #[automatically_derived]
impl ::core::clone::Clone for DelimSpacing {
    #[inline]
    fn clone(&self) -> DelimSpacing {
        let _: ::core::clone::AssertParamIsClone<Spacing>;
        *self
    }
}Clone, #[automatically_derived]
impl ::core::fmt::Debug for DelimSpacing {
    #[inline]
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        ::core::fmt::Formatter::debug_struct_field2_finish(f, "DelimSpacing",
            "open", &self.open, "close", &&self.close)
    }
}Debug, #[automatically_derived]
impl ::core::cmp::PartialEq for DelimSpacing {
    #[inline]
    fn eq(&self, other: &DelimSpacing) -> bool {
        self.open == other.open && self.close == other.close
    }
}PartialEq, #[automatically_derived]
impl ::core::cmp::Eq for DelimSpacing {
    #[inline]
    #[doc(hidden)]
    #[coverage(off)]
    fn assert_fields_are_eq(&self) {
        let _: ::core::cmp::AssertParamIsEq<Spacing>;
    }
}Eq, #[automatically_derived]
impl ::core::hash::Hash for DelimSpacing {
    #[inline]
    fn hash<__H: ::core::hash::Hasher>(&self, state: &mut __H) {
        ::core::hash::Hash::hash(&self.open, state);
        ::core::hash::Hash::hash(&self.close, state)
    }
}Hash, const _: () =
    {
        impl<__E: ::rustc_span::SpanEncoder> ::rustc_serialize::Encodable<__E>
            for DelimSpacing {
            fn encode(&self, __encoder: &mut __E) {
                match *self {
                    DelimSpacing { open: ref __binding_0, close: ref __binding_1
                        } => {
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_0,
                            __encoder);
                        ::rustc_serialize::Encodable::<__E>::encode(__binding_1,
                            __encoder);
                    }
                }
            }
        }
    };Encodable, const _: () =
    {
        impl<__D: ::rustc_span::SpanDecoder> ::rustc_serialize::Decodable<__D>
            for DelimSpacing {
            fn decode(__decoder: &mut __D) -> Self {
                DelimSpacing {
                    open: ::rustc_serialize::Decodable::decode(__decoder),
                    close: ::rustc_serialize::Decodable::decode(__decoder),
                }
            }
        }
    };Decodable, const _: () =
    {
        impl ::rustc_data_structures::stable_hash::StableHash for DelimSpacing
            {
            #[inline]
            fn stable_hash<__Hcx: ::rustc_data_structures::stable_hash::StableHashCtxt>(&self,
                __hcx: &mut __Hcx,
                __hasher:
                    &mut ::rustc_data_structures::stable_hash::StableHasher) {
                match *self {
                    DelimSpacing { open: ref __binding_0, close: ref __binding_1
                        } => {
                        { __binding_0.stable_hash(__hcx, __hasher); }
                        { __binding_1.stable_hash(__hcx, __hasher); }
                    }
                }
            }
        }
    };StableHash)]
1063pub struct DelimSpacing {
1064    pub open: Spacing,
1065    pub close: Spacing,
1066}
1067
1068impl DelimSpacing {
1069    pub fn new(open: Spacing, close: Spacing) -> DelimSpacing {
1070        DelimSpacing { open, close }
1071    }
1072}
1073
1074// Some types are used a lot. Make sure they don't unintentionally get bigger.
1075#[cfg(target_pointer_width = "64")]
1076mod size_asserts {
1077    use rustc_data_structures::static_assert_size;
1078
1079    use super::*;
1080    // tidy-alphabetical-start
1081    const _: [(); 8] = [(); ::std::mem::size_of::<AttrTokenStream>()];static_assert_size!(AttrTokenStream, 8);
1082    const _: [(); 32] = [(); ::std::mem::size_of::<AttrTokenTree>()];static_assert_size!(AttrTokenTree, 32);
1083    const _: [(); 8] = [(); ::std::mem::size_of::<LazyAttrTokenStream>()];static_assert_size!(LazyAttrTokenStream, 8);
1084    const _: [(); 88] = [(); ::std::mem::size_of::<LazyAttrTokenStreamInner>()];static_assert_size!(LazyAttrTokenStreamInner, 88);
1085    const _: [(); 8] = [(); ::std::mem::size_of::<Option<LazyAttrTokenStream>>()];static_assert_size!(Option<LazyAttrTokenStream>, 8); // must be small, used in many AST nodes
1086    const _: [(); 8] = [(); ::std::mem::size_of::<TokenStream>()];static_assert_size!(TokenStream, 8);
1087    const _: [(); 32] = [(); ::std::mem::size_of::<TokenTree>()];static_assert_size!(TokenTree, 32);
1088    // tidy-alphabetical-end
1089}