1use core::fmt;
2use core::slice;
3
4use crate::compile;
5
6use crate as rune;
7use crate::alloc;
8use crate::alloc::prelude::*;
9use crate::alloc::vec;
10use crate::ast;
11use crate::ast::{OptionSpanned, Span};
12use crate::macros::MacroContext;
13use crate::parse::{Parse, Parser};
14
15#[derive(Debug, TryClone, PartialEq, Eq, Default)]
17pub struct TokenStream {
18 stream: Vec<ast::Token>,
19}
20
21impl TokenStream {
22 #[inline]
24 pub fn new() -> Self {
25 Self::default()
26 }
27
28 #[inline]
30 pub fn push(&mut self, token: ast::Token) -> alloc::Result<()> {
31 self.stream.try_push(token)?;
32 Ok(())
33 }
34
35 #[inline]
37 pub fn extend<I>(
38 &mut self,
39 tokens: impl IntoIterator<Item: Into<ast::Token>>,
40 ) -> alloc::Result<()> {
41 self.stream.try_extend(tokens.into_iter().map(Into::into))?;
42 Ok(())
43 }
44
45 #[inline]
47 pub(crate) fn iter(&self) -> TokenStreamIter<'_> {
48 TokenStreamIter {
49 iter: self.stream.iter(),
50 }
51 }
52
53 #[inline]
55 pub fn kinds(&self) -> Kinds<'_> {
56 Kinds {
57 stream: &self.stream,
58 }
59 }
60}
61
62impl From<Vec<ast::Token>> for TokenStream {
63 fn from(stream: Vec<ast::Token>) -> Self {
64 Self { stream }
65 }
66}
67
68impl Parse for TokenStream {
69 fn parse(p: &mut Parser<'_>) -> compile::Result<Self> {
70 Ok(Self { stream: p.parse()? })
71 }
72}
73
74impl OptionSpanned for TokenStream {
75 fn option_span(&self) -> Option<Span> {
76 self.stream.option_span()
77 }
78}
79
80#[derive(Debug, Clone)]
82pub struct TokenStreamIter<'a> {
83 iter: slice::Iter<'a, ast::Token>,
84}
85
86impl OptionSpanned for TokenStreamIter<'_> {
87 fn option_span(&self) -> Option<Span> {
88 self.iter.as_slice().option_span()
89 }
90}
91
92impl Iterator for TokenStreamIter<'_> {
93 type Item = ast::Token;
94
95 fn next(&mut self) -> Option<Self::Item> {
96 self.iter.next().copied()
97 }
98}
99
100impl DoubleEndedIterator for TokenStreamIter<'_> {
101 fn next_back(&mut self) -> Option<Self::Item> {
102 self.iter.next_back().copied()
103 }
104}
105
106impl<'a> IntoIterator for &'a TokenStream {
107 type Item = &'a ast::Token;
108 type IntoIter = slice::Iter<'a, ast::Token>;
109
110 #[inline]
111 fn into_iter(self) -> Self::IntoIter {
112 self.stream.iter()
113 }
114}
115
116impl IntoIterator for TokenStream {
117 type Item = ast::Token;
118 type IntoIter = vec::IntoIter<ast::Token>;
119
120 #[inline]
121 fn into_iter(self) -> Self::IntoIter {
122 self.stream.into_iter()
123 }
124}
125
126pub trait ToTokens {
128 fn to_tokens(
130 &self,
131 cx: &mut MacroContext<'_, '_, '_>,
132 stream: &mut TokenStream,
133 ) -> alloc::Result<()>;
134}
135
136impl<T> ToTokens for Box<T>
137where
138 T: ToTokens,
139{
140 fn to_tokens(
141 &self,
142 context: &mut MacroContext<'_, '_, '_>,
143 stream: &mut TokenStream,
144 ) -> alloc::Result<()> {
145 (**self).to_tokens(context, stream)
146 }
147}
148
149impl<T> ToTokens for &T
150where
151 T: ?Sized + ToTokens,
152{
153 fn to_tokens(
154 &self,
155 context: &mut MacroContext<'_, '_, '_>,
156 stream: &mut TokenStream,
157 ) -> alloc::Result<()> {
158 ToTokens::to_tokens(*self, context, stream)
159 }
160}
161
162impl<T> ToTokens for Option<T>
163where
164 T: ToTokens,
165{
166 fn to_tokens(
167 &self,
168 context: &mut MacroContext<'_, '_, '_>,
169 stream: &mut TokenStream,
170 ) -> alloc::Result<()> {
171 if let Some(this) = self {
172 this.to_tokens(context, stream)?;
173 }
174
175 Ok(())
176 }
177}
178
179impl<T> ToTokens for Vec<T>
180where
181 T: ToTokens,
182{
183 fn to_tokens(
184 &self,
185 context: &mut MacroContext<'_, '_, '_>,
186 stream: &mut TokenStream,
187 ) -> alloc::Result<()> {
188 for item in self {
189 item.to_tokens(context, stream)?;
190 }
191
192 Ok(())
193 }
194}
195
196impl<A, B> ToTokens for (A, B)
197where
198 A: ToTokens,
199 B: ToTokens,
200{
201 fn to_tokens(
202 &self,
203 context: &mut MacroContext<'_, '_, '_>,
204 stream: &mut TokenStream,
205 ) -> alloc::Result<()> {
206 self.0.to_tokens(context, stream)?;
207 self.1.to_tokens(context, stream)?;
208 Ok(())
209 }
210}
211
212impl<A, B, C> ToTokens for (A, B, C)
213where
214 A: ToTokens,
215 B: ToTokens,
216 C: ToTokens,
217{
218 fn to_tokens(
219 &self,
220 context: &mut MacroContext<'_, '_, '_>,
221 stream: &mut TokenStream,
222 ) -> alloc::Result<()> {
223 self.0.to_tokens(context, stream)?;
224 self.1.to_tokens(context, stream)?;
225 self.2.to_tokens(context, stream)?;
226 Ok(())
227 }
228}
229
230impl ToTokens for TokenStream {
231 fn to_tokens(
232 &self,
233 context: &mut MacroContext<'_, '_, '_>,
234 stream: &mut TokenStream,
235 ) -> alloc::Result<()> {
236 self.stream.to_tokens(context, stream)
237 }
238}
239
240impl PartialEq<Vec<ast::Token>> for TokenStream {
241 fn eq(&self, other: &Vec<ast::Token>) -> bool {
242 self.stream == *other
243 }
244}
245
246impl PartialEq<TokenStream> for Vec<ast::Token> {
247 fn eq(&self, other: &TokenStream) -> bool {
248 *self == other.stream
249 }
250}
251
252pub struct Kinds<'a> {
253 stream: &'a [ast::Token],
254}
255
256impl Iterator for Kinds<'_> {
257 type Item = ast::Kind;
258
259 fn next(&mut self) -> Option<Self::Item> {
260 let (first, rest) = self.stream.split_first()?;
261 self.stream = rest;
262 Some(first.kind)
263 }
264}
265
266impl fmt::Debug for Kinds<'_> {
267 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
268 let mut it = self.stream.iter();
269 let last = it.next_back();
270
271 for t in it {
272 write!(f, "{} ", t.kind)?;
273 }
274
275 if let Some(t) = last {
276 write!(f, "{}", t.kind)?;
277 }
278
279 Ok(())
280 }
281}