1 //! Parsers working with single stream items.
2 
3 use crate::{
4     error::{
5         self, ErrorInfo, ParseError,
6         ParseResult::{self, *},
7         ResultExt, StreamError, Tracked,
8     },
9     lib::marker::PhantomData,
10     stream::{uncons, Stream, StreamOnce},
11     Parser,
12 };
13 
14 #[derive(Copy, Clone)]
15 pub struct Any<Input>(PhantomData<fn(Input) -> Input>);
16 
17 impl<Input> Parser<Input> for Any<Input>
18 where
19     Input: Stream,
20 {
21     type Output = Input::Token;
22     type PartialState = ();
23 
24     #[inline]
parse_lazy(&mut self, input: &mut Input) -> ParseResult<Input::Token, Input::Error>25     fn parse_lazy(&mut self, input: &mut Input) -> ParseResult<Input::Token, Input::Error> {
26         uncons(input)
27     }
28 }
29 
30 /// Parses any token.
31 ///
32 /// ```
33 /// # extern crate combine;
34 /// # use combine::*;
35 /// # fn main() {
36 /// let mut char_parser = any();
37 /// assert_eq!(char_parser.parse("!").map(|x| x.0), Ok('!'));
38 /// assert!(char_parser.parse("").is_err());
39 /// let mut byte_parser = any();
40 /// assert_eq!(byte_parser.parse(&b"!"[..]).map(|x| x.0), Ok(b'!'));
41 /// assert!(byte_parser.parse(&b""[..]).is_err());
42 /// # }
43 /// ```
any<Input>() -> Any<Input> where Input: Stream,44 pub fn any<Input>() -> Any<Input>
45 where
46     Input: Stream,
47 {
48     Any(PhantomData)
49 }
50 
51 #[derive(Copy, Clone)]
52 pub struct Satisfy<Input, P> {
53     predicate: P,
54     _marker: PhantomData<Input>,
55 }
56 
satisfy_impl<Input, P, R>(input: &mut Input, mut predicate: P) -> ParseResult<R, Input::Error> where Input: Stream, P: FnMut(Input::Token) -> Option<R>,57 fn satisfy_impl<Input, P, R>(input: &mut Input, mut predicate: P) -> ParseResult<R, Input::Error>
58 where
59     Input: Stream,
60     P: FnMut(Input::Token) -> Option<R>,
61 {
62     let position = input.position();
63     match uncons(input) {
64         PeekOk(c) | CommitOk(c) => match predicate(c) {
65             Some(c) => CommitOk(c),
66             None => PeekErr(Input::Error::empty(position).into()),
67         },
68         PeekErr(err) => PeekErr(err),
69         CommitErr(err) => CommitErr(err),
70     }
71 }
72 
73 impl<Input, P> Parser<Input> for Satisfy<Input, P>
74 where
75     Input: Stream,
76     P: FnMut(Input::Token) -> bool,
77 {
78     type Output = Input::Token;
79     type PartialState = ();
80 
81     #[inline]
parse_lazy(&mut self, input: &mut Input) -> ParseResult<Self::Output, Input::Error>82     fn parse_lazy(&mut self, input: &mut Input) -> ParseResult<Self::Output, Input::Error> {
83         satisfy_impl(input, |c| {
84             if (self.predicate)(c.clone()) {
85                 Some(c)
86             } else {
87                 None
88             }
89         })
90     }
91 }
92 
93 /// Parses a token and succeeds depending on the result of `predicate`.
94 ///
95 /// ```
96 /// # extern crate combine;
97 /// # use combine::*;
98 /// # fn main() {
99 /// let mut parser = satisfy(|c| c == '!' || c == '?');
100 /// assert_eq!(parser.parse("!").map(|x| x.0), Ok('!'));
101 /// assert_eq!(parser.parse("?").map(|x| x.0), Ok('?'));
102 /// # }
103 /// ```
satisfy<Input, P>(predicate: P) -> Satisfy<Input, P> where Input: Stream, P: FnMut(Input::Token) -> bool,104 pub fn satisfy<Input, P>(predicate: P) -> Satisfy<Input, P>
105 where
106     Input: Stream,
107     P: FnMut(Input::Token) -> bool,
108 {
109     Satisfy {
110         predicate,
111         _marker: PhantomData,
112     }
113 }
114 
115 #[derive(Copy, Clone)]
116 pub struct SatisfyMap<Input, P> {
117     predicate: P,
118     _marker: PhantomData<Input>,
119 }
120 
121 impl<Input, P, R> Parser<Input> for SatisfyMap<Input, P>
122 where
123     Input: Stream,
124     P: FnMut(Input::Token) -> Option<R>,
125 {
126     type Output = R;
127     type PartialState = ();
128     #[inline]
parse_lazy(&mut self, input: &mut Input) -> ParseResult<Self::Output, Input::Error>129     fn parse_lazy(&mut self, input: &mut Input) -> ParseResult<Self::Output, Input::Error> {
130         satisfy_impl(input, &mut self.predicate)
131     }
132 }
133 
134 /// Parses a token and passes it to `predicate`. If `predicate` returns `Some` the parser succeeds
135 /// and returns the value inside the `Option`. If `predicate` returns `None` the parser fails
136 /// without consuming any input.
137 ///
138 /// ```
139 /// # extern crate combine;
140 /// # use combine::*;
141 /// # fn main() {
142 /// #[derive(Debug, PartialEq)]
143 /// enum YesNo {
144 ///     Yes,
145 ///     No,
146 /// }
147 /// let mut parser = satisfy_map(|c| {
148 ///     match c {
149 ///         'Y' => Some(YesNo::Yes),
150 ///         'N' => Some(YesNo::No),
151 ///         _ => None,
152 ///     }
153 /// });
154 /// assert_eq!(parser.parse("Y").map(|x| x.0), Ok(YesNo::Yes));
155 /// assert!(parser.parse("A").map(|x| x.0).is_err());
156 /// # }
157 /// ```
satisfy_map<Input, P, R>(predicate: P) -> SatisfyMap<Input, P> where Input: Stream, P: FnMut(Input::Token) -> Option<R>,158 pub fn satisfy_map<Input, P, R>(predicate: P) -> SatisfyMap<Input, P>
159 where
160     Input: Stream,
161     P: FnMut(Input::Token) -> Option<R>,
162 {
163     SatisfyMap {
164         predicate,
165         _marker: PhantomData,
166     }
167 }
168 
169 #[derive(Copy, Clone)]
170 pub struct Token<Input>
171 where
172     Input: Stream,
173     Input::Token: PartialEq,
174 {
175     c: Input::Token,
176     _marker: PhantomData<Input>,
177 }
178 
179 impl<Input> Parser<Input> for Token<Input>
180 where
181     Input: Stream,
182     Input::Token: PartialEq + Clone,
183 {
184     type Output = Input::Token;
185     type PartialState = ();
186 
187     #[inline]
parse_lazy(&mut self, input: &mut Input) -> ParseResult<Input::Token, Input::Error>188     fn parse_lazy(&mut self, input: &mut Input) -> ParseResult<Input::Token, Input::Error> {
189         satisfy_impl(input, |c| if c == self.c { Some(c) } else { None })
190     }
add_error(&mut self, errors: &mut Tracked<<Input as StreamOnce>::Error>)191     fn add_error(&mut self, errors: &mut Tracked<<Input as StreamOnce>::Error>) {
192         errors.error.add_expected(error::Token(self.c.clone()));
193     }
194 }
195 
196 /// Parses a character and succeeds if the character is equal to `c`.
197 ///
198 /// ```
199 /// # extern crate combine;
200 /// # use combine::*;
201 /// # fn main() {
202 /// let result = token('!')
203 ///     .parse("!")
204 ///     .map(|x| x.0);
205 /// assert_eq!(result, Ok('!'));
206 /// # }
207 /// ```
token<Input>(c: Input::Token) -> Token<Input> where Input: Stream, Input::Token: PartialEq,208 pub fn token<Input>(c: Input::Token) -> Token<Input>
209 where
210     Input: Stream,
211     Input::Token: PartialEq,
212 {
213     Token {
214         c,
215         _marker: PhantomData,
216     }
217 }
218 
219 #[derive(Clone)]
220 pub struct Tokens<C, E, T, Input>
221 where
222     Input: Stream,
223 {
224     cmp: C,
225     expected: E,
226     tokens: T,
227     _marker: PhantomData<Input>,
228 }
229 
230 impl<Input, C, E, T> Parser<Input> for Tokens<C, E, T, Input>
231 where
232     C: FnMut(T::Item, Input::Token) -> bool,
233     E: for<'s> ErrorInfo<'s, Input::Token, Input::Range>,
234     T: Clone + IntoIterator,
235     Input: Stream,
236 {
237     type Output = T;
238     type PartialState = ();
239     #[inline]
parse_lazy(&mut self, input: &mut Input) -> ParseResult<T, Input::Error>240     fn parse_lazy(&mut self, input: &mut Input) -> ParseResult<T, Input::Error> {
241         let start = input.position();
242         let mut committed = false;
243         for c in self.tokens.clone() {
244             match crate::stream::uncons(input) {
245                 CommitOk(other) | PeekOk(other) => {
246                     if !(self.cmp)(c, other.clone()) {
247                         return if committed {
248                             let mut errors = <Input as StreamOnce>::Error::from_error(
249                                 start,
250                                 StreamError::unexpected_token(other),
251                             );
252                             errors.add_expected(&self.expected);
253                             CommitErr(errors)
254                         } else {
255                             PeekErr(<Input as StreamOnce>::Error::empty(start).into())
256                         };
257                     }
258                     committed = true;
259                 }
260                 PeekErr(mut error) => {
261                     error.error.set_position(start);
262                     return if committed {
263                         CommitErr(error.error)
264                     } else {
265                         PeekErr(error)
266                     };
267                 }
268                 CommitErr(mut error) => {
269                     error.set_position(start);
270                     return CommitErr(error);
271                 }
272             }
273         }
274         if committed {
275             CommitOk(self.tokens.clone())
276         } else {
277             PeekOk(self.tokens.clone())
278         }
279     }
add_error(&mut self, errors: &mut Tracked<<Input as StreamOnce>::Error>)280     fn add_error(&mut self, errors: &mut Tracked<<Input as StreamOnce>::Error>) {
281         errors.error.add_expected(&self.expected);
282     }
283 }
284 
285 /// Parses multiple tokens.
286 ///
287 /// Consumes items from the input and compares them to the values from `tokens` using the
288 /// comparison function `cmp`. Succeeds if all the items from `tokens` are matched in the input
289 /// stream and fails otherwise with `expected` used as part of the error.
290 ///
291 /// ```
292 /// # extern crate combine;
293 /// # use combine::*;
294 /// # use combine::error;
295 /// # fn main() {
296 /// let result = tokens(|l, r| l.eq_ignore_ascii_case(&r), "abc", "abc".chars())
297 ///     .parse("AbC")
298 ///     .map(|x| x.0.as_str());
299 /// assert_eq!(result, Ok("abc"));
300 /// let result = tokens(
301 ///     |&l, r| (if l < r { r - l } else { l - r }) <= 2,
302 ///     error::Range(&b"025"[..]),
303 ///     &b"025"[..]
304 /// )
305 ///     .parse(&b"123"[..])
306 ///     .map(|x| x.0);
307 /// assert_eq!(result, Ok(&b"025"[..]));
308 /// # }
309 /// ```
tokens<C, E, T, Input>(cmp: C, expected: E, tokens: T) -> Tokens<C, E, T, Input> where C: FnMut(T::Item, Input::Token) -> bool, T: Clone + IntoIterator, Input: Stream,310 pub fn tokens<C, E, T, Input>(cmp: C, expected: E, tokens: T) -> Tokens<C, E, T, Input>
311 where
312     C: FnMut(T::Item, Input::Token) -> bool,
313     T: Clone + IntoIterator,
314     Input: Stream,
315 {
316     Tokens {
317         cmp,
318         expected,
319         tokens,
320         _marker: PhantomData,
321     }
322 }
323 
324 #[derive(Clone)]
325 pub struct TokensCmp<C, T, Input>
326 where
327     Input: Stream,
328 {
329     cmp: C,
330     tokens: T,
331     _marker: PhantomData<Input>,
332 }
333 
334 impl<Input, C, T> Parser<Input> for TokensCmp<C, T, Input>
335 where
336     C: FnMut(T::Item, Input::Token) -> bool,
337     T: Clone + IntoIterator,
338     Input: Stream,
339 {
340     type Output = T;
341     type PartialState = ();
342 
343     #[inline]
parse_lazy(&mut self, input: &mut Input) -> ParseResult<T, Input::Error>344     fn parse_lazy(&mut self, input: &mut Input) -> ParseResult<T, Input::Error> {
345         let start = input.position();
346         let mut committed = false;
347         for c in self.tokens.clone() {
348             match crate::stream::uncons(input) {
349                 CommitOk(other) | PeekOk(other) => {
350                     if !(self.cmp)(c, other.clone()) {
351                         return if committed {
352                             let errors = <Input as StreamOnce>::Error::from_error(
353                                 start,
354                                 StreamError::unexpected_token(other),
355                             );
356                             CommitErr(errors)
357                         } else {
358                             PeekErr(<Input as StreamOnce>::Error::empty(start).into())
359                         };
360                     }
361                     committed = true;
362                 }
363                 PeekErr(mut error) => {
364                     error.error.set_position(start);
365                     return if committed {
366                         CommitErr(error.error)
367                     } else {
368                         PeekErr(error)
369                     };
370                 }
371                 CommitErr(mut error) => {
372                     error.set_position(start);
373                     return CommitErr(error);
374                 }
375             }
376         }
377         if committed {
378             CommitOk(self.tokens.clone())
379         } else {
380             PeekOk(self.tokens.clone())
381         }
382     }
383 }
384 
385 /// Parses multiple tokens.
386 ///
387 /// Consumes items from the input and compares them to the values from `tokens` using the
388 /// comparison function `cmp`. Succeeds if all the items from `tokens` are matched in the input
389 /// stream and fails otherwise.
390 ///
391 /// ```
392 /// # extern crate combine;
393 /// # use combine::*;
394 /// # fn main() {
395 /// # #[allow(deprecated)]
396 /// # use std::ascii::AsciiExt;
397 /// let result = tokens_cmp("abc".chars(), |l, r| l.eq_ignore_ascii_case(&r))
398 ///     .parse("AbC")
399 ///     .map(|x| x.0.as_str());
400 /// assert_eq!(result, Ok("abc"));
401 /// let result = tokens_cmp(
402 ///     &b"025"[..],
403 ///     |&l, r| (if l < r { r - l } else { l - r }) <= 2,
404 /// )
405 ///     .parse(&b"123"[..])
406 ///     .map(|x| x.0);
407 /// assert_eq!(result, Ok(&b"025"[..]));
408 /// # }
409 /// ```
tokens_cmp<C, T, I>(tokens: T, cmp: C) -> TokensCmp<C, T, I> where C: FnMut(T::Item, I::Token) -> bool, T: Clone + IntoIterator, I: Stream,410 pub fn tokens_cmp<C, T, I>(tokens: T, cmp: C) -> TokensCmp<C, T, I>
411 where
412     C: FnMut(T::Item, I::Token) -> bool,
413     T: Clone + IntoIterator,
414     I: Stream,
415 {
416     TokensCmp {
417         cmp,
418         tokens,
419         _marker: PhantomData,
420     }
421 }
422 
423 #[derive(Copy, Clone)]
424 pub struct Position<Input>
425 where
426     Input: Stream,
427 {
428     _marker: PhantomData<Input>,
429 }
430 
431 impl<Input> Parser<Input> for Position<Input>
432 where
433     Input: Stream,
434 {
435     type Output = Input::Position;
436     type PartialState = ();
437 
438     #[inline]
parse_lazy(&mut self, input: &mut Input) -> ParseResult<Input::Position, Input::Error>439     fn parse_lazy(&mut self, input: &mut Input) -> ParseResult<Input::Position, Input::Error> {
440         PeekOk(input.position())
441     }
442 }
443 
444 /// Parser which just returns the current position in the stream.
445 ///
446 /// ```
447 /// # extern crate combine;
448 /// # use combine::*;
449 /// # use combine::stream::position::{self, SourcePosition};
450 /// # fn main() {
451 /// let result = (position(), token('!'), position())
452 ///     .parse(position::Stream::new("!"))
453 ///     .map(|x| x.0);
454 /// assert_eq!(result, Ok((SourcePosition { line: 1, column: 1 },
455 ///                        '!',
456 ///                        SourcePosition { line: 1, column: 2 })));
457 /// # }
458 /// ```
position<Input>() -> Position<Input> where Input: Stream,459 pub fn position<Input>() -> Position<Input>
460 where
461     Input: Stream,
462 {
463     Position {
464         _marker: PhantomData,
465     }
466 }
467 
468 #[derive(Copy, Clone)]
469 pub struct OneOf<T, Input>
470 where
471     Input: Stream,
472 {
473     tokens: T,
474     _marker: PhantomData<Input>,
475 }
476 
477 impl<Input, T> Parser<Input> for OneOf<T, Input>
478 where
479     T: Clone + IntoIterator<Item = Input::Token>,
480     Input: Stream,
481     Input::Token: PartialEq,
482 {
483     type Output = Input::Token;
484     type PartialState = ();
485 
486     #[inline]
parse_lazy(&mut self, input: &mut Input) -> ParseResult<Input::Token, Input::Error>487     fn parse_lazy(&mut self, input: &mut Input) -> ParseResult<Input::Token, Input::Error> {
488         satisfy(|c| self.tokens.clone().into_iter().any(|t| t == c)).parse_lazy(input)
489     }
490 
add_error(&mut self, errors: &mut Tracked<<Input as StreamOnce>::Error>)491     fn add_error(&mut self, errors: &mut Tracked<<Input as StreamOnce>::Error>) {
492         for expected in self.tokens.clone() {
493             errors.error.add_expected(error::Token(expected));
494         }
495     }
496 }
497 
498 /// Extract one token and succeeds if it is part of `tokens`.
499 ///
500 /// ```
501 /// # extern crate combine;
502 /// # use combine::*;
503 /// # fn main() {
504 /// let result = many(one_of("abc".chars()))
505 ///     .parse("abd");
506 /// assert_eq!(result, Ok((String::from("ab"), "d")));
507 /// # }
508 /// ```
one_of<T, Input>(tokens: T) -> OneOf<T, Input> where T: Clone + IntoIterator, Input: Stream, Input::Token: PartialEq<T::Item>,509 pub fn one_of<T, Input>(tokens: T) -> OneOf<T, Input>
510 where
511     T: Clone + IntoIterator,
512     Input: Stream,
513     Input::Token: PartialEq<T::Item>,
514 {
515     OneOf {
516         tokens,
517         _marker: PhantomData,
518     }
519 }
520 
521 #[derive(Copy, Clone)]
522 pub struct NoneOf<T, Input>
523 where
524     Input: Stream,
525 {
526     tokens: T,
527     _marker: PhantomData<Input>,
528 }
529 
530 impl<Input, T> Parser<Input> for NoneOf<T, Input>
531 where
532     T: Clone + IntoIterator<Item = Input::Token>,
533     Input: Stream,
534     Input::Token: PartialEq,
535 {
536     type Output = Input::Token;
537     type PartialState = ();
538 
539     #[inline]
parse_lazy(&mut self, input: &mut Input) -> ParseResult<Input::Token, Input::Error>540     fn parse_lazy(&mut self, input: &mut Input) -> ParseResult<Input::Token, Input::Error> {
541         satisfy(|c| self.tokens.clone().into_iter().all(|t| t != c)).parse_lazy(input)
542     }
543 }
544 
545 /// Extract one token and succeeds if it is not part of `tokens`.
546 ///
547 /// ```
548 /// # extern crate combine;
549 /// # use combine::*;
550 /// # use combine::stream::easy;
551 /// # use combine::stream::position;
552 /// # fn main() {
553 /// let mut parser = many1(none_of(b"abc".iter().cloned()));
554 /// let result = parser.easy_parse(position::Stream::new(&b"xyb"[..]))
555 ///     .map(|(output, input)| (output, input.input));
556 /// assert_eq!(result, Ok((b"xy"[..].to_owned(), &b"b"[..])));
557 ///
558 /// let result = parser.easy_parse(position::Stream::new(&b"ab"[..]));
559 /// assert_eq!(result, Err(easy::Errors {
560 ///     position: 0,
561 ///     errors: vec![
562 ///         easy::Error::Unexpected(easy::Info::Token(b'a')),
563 ///     ]
564 /// }));
565 /// # }
566 /// ```
none_of<T, Input>(tokens: T) -> NoneOf<T, Input> where T: Clone + IntoIterator, Input: Stream, Input::Token: PartialEq<T::Item>,567 pub fn none_of<T, Input>(tokens: T) -> NoneOf<T, Input>
568 where
569     T: Clone + IntoIterator,
570     Input: Stream,
571     Input::Token: PartialEq<T::Item>,
572 {
573     NoneOf {
574         tokens,
575         _marker: PhantomData,
576     }
577 }
578 
579 #[derive(Copy, Clone)]
580 pub struct Value<Input, T>(T, PhantomData<fn(Input) -> Input>);
581 impl<Input, T> Parser<Input> for Value<Input, T>
582 where
583     Input: Stream,
584     T: Clone,
585 {
586     type Output = T;
587     type PartialState = ();
588     #[inline]
parse_lazy(&mut self, _: &mut Input) -> ParseResult<T, Input::Error>589     fn parse_lazy(&mut self, _: &mut Input) -> ParseResult<T, Input::Error> {
590         PeekOk(self.0.clone())
591     }
592 }
593 
594 /// Always returns the value `v` without consuming any input.
595 ///
596 /// ```
597 /// # extern crate combine;
598 /// # use combine::*;
599 /// # fn main() {
600 /// let result = value(42)
601 ///     .parse("hello world")
602 ///     .map(|x| x.0);
603 /// assert_eq!(result, Ok(42));
604 /// # }
605 /// ```
value<Input, T>(v: T) -> Value<Input, T> where Input: Stream, T: Clone,606 pub fn value<Input, T>(v: T) -> Value<Input, T>
607 where
608     Input: Stream,
609     T: Clone,
610 {
611     Value(v, PhantomData)
612 }
613 
614 #[derive(Copy, Clone)]
615 pub struct Produce<Input, F>(F, PhantomData<fn(Input) -> Input>);
616 impl<Input, F, R> Parser<Input> for Produce<Input, F>
617 where
618     Input: Stream,
619     F: FnMut() -> R,
620 {
621     type Output = R;
622     type PartialState = ();
623     #[inline]
parse_lazy(&mut self, _: &mut Input) -> ParseResult<R, Input::Error>624     fn parse_lazy(&mut self, _: &mut Input) -> ParseResult<R, Input::Error> {
625         PeekOk((self.0)())
626     }
627 }
628 
629 /// Always returns the value produced by calling `f`.
630 ///
631 /// Can be used when `value` is unable to be used for lack of `Clone` implementation on the value.
632 ///
633 /// ```
634 /// # use combine::*;
635 /// #[derive(Debug, PartialEq)]
636 /// struct NoClone;
637 /// let result = produce(|| vec![NoClone])
638 ///     .parse("hello world")
639 ///     .map(|x| x.0);
640 /// assert_eq!(result, Ok(vec![NoClone]));
641 /// ```
produce<Input, F, R>(f: F) -> Produce<Input, F> where Input: Stream, F: FnMut() -> R,642 pub fn produce<Input, F, R>(f: F) -> Produce<Input, F>
643 where
644     Input: Stream,
645     F: FnMut() -> R,
646 {
647     Produce(f, PhantomData)
648 }
649 
650 #[derive(Copy, Clone)]
651 pub struct Eof<Input>(PhantomData<Input>);
652 impl<Input> Parser<Input> for Eof<Input>
653 where
654     Input: Stream,
655 {
656     type Output = ();
657     type PartialState = ();
658 
659     #[inline]
parse_lazy(&mut self, input: &mut Input) -> ParseResult<(), Input::Error>660     fn parse_lazy(&mut self, input: &mut Input) -> ParseResult<(), Input::Error> {
661         let before = input.checkpoint();
662         match input.uncons() {
663             Err(ref err) if err.is_unexpected_end_of_input() => PeekOk(()),
664             _ => {
665                 ctry!(input.reset(before).committed());
666                 PeekErr(<Input as StreamOnce>::Error::empty(input.position()).into())
667             }
668         }
669     }
670 
add_error(&mut self, errors: &mut Tracked<<Input as StreamOnce>::Error>)671     fn add_error(&mut self, errors: &mut Tracked<<Input as StreamOnce>::Error>) {
672         errors.error.add_expected("end of input");
673     }
674 }
675 
676 /// Succeeds only if the stream is at end of input, fails otherwise.
677 ///
678 /// ```
679 /// # extern crate combine;
680 /// # use combine::*;
681 /// # use combine::stream::easy;
682 /// # use combine::stream::position::{self, SourcePosition};
683 /// # fn main() {
684 /// let mut parser = eof();
685 /// assert_eq!(parser.easy_parse(position::Stream::new("")), Ok(((), position::Stream::new(""))));
686 /// assert_eq!(parser.easy_parse(position::Stream::new("x")), Err(easy::Errors {
687 ///     position: SourcePosition::default(),
688 ///     errors: vec![
689 ///         easy::Error::Unexpected('x'.into()),
690 ///         easy::Error::Expected("end of input".into())
691 ///     ]
692 /// }));
693 /// # }
694 /// ```
eof<Input>() -> Eof<Input> where Input: Stream,695 pub fn eof<Input>() -> Eof<Input>
696 where
697     Input: Stream,
698 {
699     Eof(PhantomData)
700 }
701