1#![deny(missing_docs)]
6
7pub trait Parser {
13 type Terminal;
15 type Nonterminal;
18
19 #[inline(always)]
21 fn peek(&mut self) -> &Self::Terminal;
22
23 #[inline(always)]
27 fn shift(&mut self, state_fn: fn(&mut Self), goto_fn: fn(&mut Self, Self::Nonterminal));
28
29 #[inline(always)]
33 fn goto(
34 &mut self,
35 nonterminal: Self::Nonterminal,
36 state_fn: fn(&mut Self),
37 goto_fn: fn(&mut Self, Self::Nonterminal),
38 );
39
40 #[inline(always)]
46 fn reduce<F: Fn(Vec<Symbol<Self::Terminal, Self::Nonterminal>>) -> Self::Nonterminal>(
47 &mut self,
48 length: usize,
49 f: F,
50 );
51
52 fn accept(&mut self);
56}
57
58#[allow(missing_docs)]
62pub enum Symbol<T, NT> {
63 Terminal(T),
64 Nonterminal(NT),
65}
66
67impl<T, NT> Symbol<T, NT> {
68 #[inline(always)]
72 pub fn unwrap_terminal(self) -> T {
73 match self {
74 Symbol::Terminal(x) => x,
75 _ => panic!("symbol is not a terminal"),
76 }
77 }
78
79 #[inline(always)]
83 pub fn unwrap_nonterminal(self) -> NT {
84 match self {
85 Symbol::Nonterminal(x) => x,
86 _ => panic!("symbol is not a nonterminal"),
87 }
88 }
89}
90
91pub trait StateSpace {
93 type Terminal;
95 type Nonterminal;
97 type Root;
99
100 fn root_state_fn<P: Parser<Terminal = Self::Terminal, Nonterminal = Self::Nonterminal>>(
102) -> fn(&mut P);
103
104 fn root_goto_fn<P: Parser<Terminal = Self::Terminal, Nonterminal = Self::Nonterminal>>(
106) -> fn(&mut P, Self::Nonterminal);
107}
108
109pub struct ParserMachine<I: ParserInput, S: StateSpace> {
114 input: I,
115 result: Option<S::Nonterminal>,
116 stack: Vec<StackEntry<I, S>>,
117}
118
119struct StackEntry<I: ParserInput, S: StateSpace> {
124 symbol: Symbol<S::Terminal, S::Nonterminal>,
125 state_fn: fn(&mut ParserMachine<I, S>),
126 goto_fn: fn(&mut ParserMachine<I, S>, S::Nonterminal),
127}
128
129impl<I: ParserInput<Item = S::Terminal>, S: StateSpace> ParserMachine<I, S> {
130 pub fn new(input: I) -> ParserMachine<I, S> {
132 ParserMachine {
133 input: input,
134 result: None,
135 stack: Vec::new(),
136 }
137 }
138
139 fn step(&mut self) {
140 if self.result.is_some() {
141 return;
142 }
143 let state_fn = self.stack
144 .last()
145 .map(|e| e.state_fn)
146 .unwrap_or(S::root_state_fn());
147 state_fn(self);
148 }
149
150 pub fn run(mut self) -> S::Nonterminal {
152 while self.result.is_none() {
153 self.step()
154 }
155 self.result.unwrap()
156 }
157}
158
159impl<I: Iterator, S: StateSpace<Terminal = Option<I::Item>>> ParserMachine<IterInput<I>, S> {
160 pub fn from_iter(input: I) -> ParserMachine<IterInput<I>, S> {
162 ParserMachine::new(IterInput::new(input))
163 }
164}
165
166impl<I, S> Parser for ParserMachine<I, S>
167where
168 I: ParserInput<Item = S::Terminal>,
169 S: StateSpace,
170{
171 type Terminal = S::Terminal;
172 type Nonterminal = S::Nonterminal;
173
174 fn peek(&mut self) -> &S::Terminal {
175 self.input.peek()
176 }
177
178 fn shift(&mut self, state_fn: fn(&mut Self), goto_fn: fn(&mut Self, S::Nonterminal)) {
179 let terminal = self.input.next();
180 self.stack.push(StackEntry {
181 symbol: Symbol::Terminal(terminal),
182 state_fn: state_fn,
183 goto_fn: goto_fn,
184 });
185 }
186
187 fn goto(
188 &mut self,
189 nonterminal: S::Nonterminal,
190 state_fn: fn(&mut Self),
191 goto_fn: fn(&mut Self, S::Nonterminal),
192 ) {
193 self.stack.push(StackEntry {
194 symbol: Symbol::Nonterminal(nonterminal),
195 state_fn: state_fn,
196 goto_fn: goto_fn,
197 });
198 }
199
200 fn reduce<F: Fn(Vec<Symbol<S::Terminal, S::Nonterminal>>) -> S::Nonterminal>(
201 &mut self,
202 length: usize,
203 f: F,
204 ) {
205 let at = self.stack.len() - length;
206 let args = self.stack.drain(at..).map(|e| e.symbol).collect();
207 let goto_fn = self.stack
208 .last()
209 .map(|e| e.goto_fn)
210 .unwrap_or(S::root_goto_fn());
211 let nonterminal = f(args);
212 goto_fn(self, nonterminal);
213 }
214
215 fn accept(&mut self) {
216 self.result = Some(self.stack.pop().unwrap().symbol.unwrap_nonterminal());
217 }
218}
219
220pub trait ParserInput {
222 type Item;
224
225 #[inline(always)]
227 fn peek(&mut self) -> &Self::Item;
228
229 #[inline(always)]
231 fn next(&mut self) -> Self::Item;
232
233 #[inline(always)]
239 fn marker() -> Self::Item;
240}
241
242pub struct IterInput<I: Iterator> {
244 iter: I,
245 peek: Option<I::Item>,
246}
247
248impl<I: Iterator> IterInput<I> {
249 pub fn new(mut iter: I) -> IterInput<I> {
251 IterInput {
252 peek: iter.next(),
253 iter: iter,
254 }
255 }
256}
257
258impl<I: Iterator> ParserInput for IterInput<I> {
259 type Item = Option<I::Item>;
260
261 fn peek(&mut self) -> &Self::Item {
262 &self.peek
263 }
264
265 fn next(&mut self) -> Self::Item {
266 std::mem::replace(&mut self.peek, self.iter.next())
267 }
268
269 fn marker() -> Self::Item {
270 None
271 }
272}