1 //! An NFA-based parser, which is porting from rustc mbe parsing code
3 //! See <https://github.com/rust-lang/rust/blob/70b18bc2cbac4712020019f5bf57c00905373205/compiler/rustc_expand/src/mbe/macro_parser.rs>
4 //! Here is a quick intro to how the parser works, copied from rustc:
6 //! A 'position' is a dot in the middle of a matcher, usually represented as a
7 //! dot. For example `· a $( a )* a b` is a position, as is `a $( · a )* a b`.
9 //! The parser walks through the input a character at a time, maintaining a list
10 //! of threads consistent with the current position in the input string: `cur_items`.
12 //! As it processes them, it fills up `eof_items` with threads that would be valid if
13 //! the macro invocation is now over, `bb_items` with threads that are waiting on
14 //! a Rust non-terminal like `$e:expr`, and `next_items` with threads that are waiting
15 //! on a particular token. Most of the logic concerns moving the · through the
16 //! repetitions indicated by Kleene stars. The rules for moving the · without
17 //! consuming any input are called epsilon transitions. It only advances or calls
18 //! out to the real Rust parser when no `cur_items` threads remain.
23 //! Start parsing a a a a b against [· a $( a )* a b].
25 //! Remaining input: a a a a b
26 //! next: [· a $( a )* a b]
28 //! - - - Advance over an a. - - -
30 //! Remaining input: a a a b
31 //! cur: [a · $( a )* a b]
32 //! Descend/Skip (first item).
33 //! next: [a $( · a )* a b] [a $( a )* · a b].
35 //! - - - Advance over an a. - - -
37 //! Remaining input: a a b
38 //! cur: [a $( a · )* a b] [a $( a )* a · b]
39 //! Follow epsilon transition: Finish/Repeat (first item)
40 //! next: [a $( a )* · a b] [a $( · a )* a b] [a $( a )* a · b]
42 //! - - - Advance over an a. - - - (this looks exactly like the last step)
44 //! Remaining input: a b
45 //! cur: [a $( a · )* a b] [a $( a )* a · b]
46 //! Follow epsilon transition: Finish/Repeat (first item)
47 //! next: [a $( a )* · a b] [a $( · a )* a b] [a $( a )* a · b]
49 //! - - - Advance over an a. - - - (this looks exactly like the last step)
51 //! Remaining input: b
52 //! cur: [a $( a · )* a b] [a $( a )* a · b]
53 //! Follow epsilon transition: Finish/Repeat (first item)
54 //! next: [a $( a )* · a b] [a $( · a )* a b] [a $( a )* a · b]
56 //! - - - Advance over a b. - - -
58 //! Remaining input: ''
59 //! eof: [a $( a )* a b ·]
65 expander::{Binding, Bindings, Fragment},
66 parser::{Op, RepeatKind, Separator},
68 ExpandError, MetaTemplate,
71 use super::ExpandResult;
72 use parser::ParserEntryPoint::*;
73 use smallvec::{smallvec, SmallVec};
77 fn push_optional(&mut self, name: &SmolStr) {
78 // FIXME: Do we have a better way to represent an empty token ?
79 // Insert an empty subtree for empty token
80 let tt = tt::Subtree::default().into();
81 self.inner.insert(name.clone(), Binding::Fragment(Fragment::Tokens(tt)));
84 fn push_empty(&mut self, name: &SmolStr) {
85 self.inner.insert(name.clone(), Binding::Empty);
88 fn bindings(&self) -> impl Iterator<Item = &Binding> {
95 ExpandError::BindingError(format!(""))
98 ExpandError::BindingError(format!($($tt)*))
102 #[derive(Clone, Debug, Default, PartialEq, Eq)]
103 pub(super) struct Match {
104 pub(super) bindings: Bindings,
105 /// We currently just keep the first error and count the rest to compare matches.
106 pub(super) err: Option<ExpandError>,
107 pub(super) err_count: usize,
108 /// How many top-level token trees were left to match.
109 pub(super) unmatched_tts: usize,
110 /// The number of bound variables
111 pub(super) bound_count: usize,
115 fn add_err(&mut self, err: ExpandError) {
116 let prev_err = self.err.take();
117 self.err = prev_err.or(Some(err));
122 /// Matching errors are added to the `Match`.
123 pub(super) fn match_(pattern: &MetaTemplate, input: &tt::Subtree) -> Match {
124 let mut res = match_loop(pattern, input);
125 res.bound_count = count(res.bindings.bindings());
128 fn count<'a>(bindings: impl Iterator<Item = &'a Binding>) -> usize {
131 Binding::Fragment(_) => 1,
133 Binding::Nested(it) => count(it.iter()),
139 #[derive(Debug, Clone)]
143 Fragment(SmolStr, Fragment),
144 Nested(usize, usize),
147 #[derive(Debug, Clone)]
148 struct BindingsIdx(usize, usize);
150 #[derive(Debug, Clone)]
153 Parent { idx: usize, len: usize },
157 struct BindingsBuilder {
158 nodes: Vec<Vec<LinkNode<Rc<BindingKind>>>>,
159 nested: Vec<Vec<LinkNode<usize>>>,
162 impl BindingsBuilder {
163 fn alloc(&mut self) -> BindingsIdx {
164 let idx = self.nodes.len();
165 self.nodes.push(Vec::new());
166 let nidx = self.nested.len();
167 self.nested.push(Vec::new());
168 BindingsIdx(idx, nidx)
171 fn copy(&mut self, bindings: &BindingsIdx) -> BindingsIdx {
172 let idx = copy_parent(bindings.0, &mut self.nodes);
173 let nidx = copy_parent(bindings.1, &mut self.nested);
174 return BindingsIdx(idx, nidx);
176 fn copy_parent<T>(idx: usize, target: &mut Vec<Vec<LinkNode<T>>>) -> usize
180 let new_idx = target.len();
181 let len = target[idx].len();
183 target.push(target[idx].clone())
185 target.push(vec![LinkNode::Parent { idx, len }]);
191 fn push_empty(&mut self, idx: &mut BindingsIdx, var: &SmolStr) {
192 self.nodes[idx.0].push(LinkNode::Node(Rc::new(BindingKind::Empty(var.clone()))));
195 fn push_optional(&mut self, idx: &mut BindingsIdx, var: &SmolStr) {
196 self.nodes[idx.0].push(LinkNode::Node(Rc::new(BindingKind::Optional(var.clone()))));
199 fn push_fragment(&mut self, idx: &mut BindingsIdx, var: &SmolStr, fragment: Fragment) {
201 .push(LinkNode::Node(Rc::new(BindingKind::Fragment(var.clone(), fragment))));
204 fn push_nested(&mut self, parent: &mut BindingsIdx, child: &BindingsIdx) {
205 let BindingsIdx(idx, nidx) = self.copy(child);
206 self.nodes[parent.0].push(LinkNode::Node(Rc::new(BindingKind::Nested(idx, nidx))));
209 fn push_default(&mut self, idx: &mut BindingsIdx) {
210 self.nested[idx.1].push(LinkNode::Node(idx.0));
211 let new_idx = self.nodes.len();
212 self.nodes.push(Vec::new());
216 fn build(self, idx: &BindingsIdx) -> Bindings {
217 let mut bindings = Bindings::default();
218 self.build_inner(&mut bindings, &self.nodes[idx.0]);
222 fn build_inner(&self, bindings: &mut Bindings, link_nodes: &[LinkNode<Rc<BindingKind>>]) {
223 let mut nodes = Vec::new();
224 self.collect_nodes(link_nodes, &mut nodes);
228 BindingKind::Empty(name) => {
229 bindings.push_empty(name);
231 BindingKind::Optional(name) => {
232 bindings.push_optional(name);
234 BindingKind::Fragment(name, fragment) => {
235 bindings.inner.insert(name.clone(), Binding::Fragment(fragment.clone()));
237 BindingKind::Nested(idx, nested_idx) => {
238 let mut nested_nodes = Vec::new();
239 self.collect_nested(*idx, *nested_idx, &mut nested_nodes);
241 for (idx, iter) in nested_nodes.into_iter().enumerate() {
242 for (key, value) in &iter.inner {
243 let bindings = bindings
246 .or_insert_with(|| Binding::Nested(Vec::new()));
248 if let Binding::Nested(it) = bindings {
249 // insert empty nested bindings before this one
250 while it.len() < idx {
251 it.push(Binding::Nested(Vec::new()));
253 it.push(value.clone());
262 fn collect_nested_ref<'a>(
266 nested_refs: &mut Vec<&'a Vec<LinkNode<Rc<BindingKind>>>>,
268 self.nested[id].iter().take(len).for_each(|it| match it {
269 LinkNode::Node(id) => nested_refs.push(&self.nodes[*id]),
270 LinkNode::Parent { idx, len } => self.collect_nested_ref(*idx, *len, nested_refs),
274 fn collect_nested(&self, idx: usize, nested_idx: usize, nested: &mut Vec<Bindings>) {
275 let last = &self.nodes[idx];
276 let mut nested_refs = Vec::new();
277 self.nested[nested_idx].iter().for_each(|it| match *it {
278 LinkNode::Node(idx) => nested_refs.push(&self.nodes[idx]),
279 LinkNode::Parent { idx, len } => self.collect_nested_ref(idx, len, &mut nested_refs),
281 nested_refs.push(last);
283 nested_refs.into_iter().for_each(|iter| {
284 let mut child_bindings = Bindings::default();
285 self.build_inner(&mut child_bindings, iter);
286 nested.push(child_bindings)
290 fn collect_nodes_ref<'a>(
294 nodes: &mut Vec<&'a Rc<BindingKind>>,
296 self.nodes[id].iter().take(len).for_each(|it| match it {
297 LinkNode::Node(it) => nodes.push(it),
298 LinkNode::Parent { idx, len } => self.collect_nodes_ref(*idx, *len, nodes),
302 fn collect_nodes<'a>(
304 link_nodes: &'a [LinkNode<Rc<BindingKind>>],
305 nodes: &mut Vec<&'a Rc<BindingKind>>,
307 link_nodes.iter().for_each(|it| match it {
308 LinkNode::Node(it) => nodes.push(it),
309 LinkNode::Parent { idx, len } => self.collect_nodes_ref(*idx, *len, nodes),
314 #[derive(Debug, Clone)]
315 struct MatchState<'t> {
316 /// The position of the "dot" in this matcher
317 dot: OpDelimitedIter<'t>,
319 /// Token subtree stack
320 /// When matching against matchers with nested delimited submatchers (e.g., `pat ( pat ( .. )
321 /// pat ) pat`), we need to keep track of the matchers we are descending into. This stack does
322 /// that where the bottom of the stack is the outermost matcher.
323 stack: SmallVec<[OpDelimitedIter<'t>; 4]>,
325 /// The "parent" matcher position if we are in a repetition. That is, the matcher position just
326 /// before we enter the repetition.
327 up: Option<Box<MatchState<'t>>>,
329 /// The separator if we are in a repetition.
330 sep: Option<Separator>,
332 /// The KleeneOp of this sequence if we are in a repetition.
333 sep_kind: Option<RepeatKind>,
335 /// Number of tokens of seperator parsed
336 sep_parsed: Option<usize>,
338 /// Matched meta variables bindings
339 bindings: BindingsIdx,
341 /// Cached result of meta variable parsing
342 meta_result: Option<(TtIter<'t>, ExpandResult<Option<Fragment>>)>,
344 /// Is error occuried in this state, will `poised` to "parent"
348 /// Process the matcher positions of `cur_items` until it is empty. In the process, this will
349 /// produce more items in `next_items`, `eof_items`, and `bb_items`.
351 /// For more info about the how this happens, see the module-level doc comments and the inline
352 /// comments of this function.
356 /// - `src`: the current token of the parser.
357 /// - `stack`: the "parent" frames of the token tree
358 /// - `res`: the match result to store errors
359 /// - `cur_items`: the set of current items to be processed. This should be empty by the end of a
360 /// successful execution of this function.
361 /// - `next_items`: the set of newly generated items. These are used to replenish `cur_items` in
362 /// the function `parse`.
363 /// - `eof_items`: the set of items that would be valid if this was the EOF.
364 /// - `bb_items`: the set of items that are waiting for the black-box parser.
365 /// - `error_items`: the set of items in errors, used for error-resilient parsing
366 fn match_loop_inner<'t>(
368 stack: &[TtIter<'t>],
370 bindings_builder: &mut BindingsBuilder,
371 cur_items: &mut SmallVec<[MatchState<'t>; 1]>,
372 bb_items: &mut SmallVec<[MatchState<'t>; 1]>,
373 next_items: &mut Vec<MatchState<'t>>,
374 eof_items: &mut SmallVec<[MatchState<'t>; 1]>,
375 error_items: &mut SmallVec<[MatchState<'t>; 1]>,
377 macro_rules! try_push {
378 ($items: expr, $it:expr) => {
380 error_items.push($it);
387 while let Some(mut item) = cur_items.pop() {
388 while item.dot.is_eof() {
389 match item.stack.pop() {
397 let op = match item.dot.peek() {
399 // We are at or past the end of the matcher of `item`.
400 if item.up.is_some() {
401 if item.sep_parsed.is_none() {
402 // Get the `up` matcher
403 let mut new_pos = *item.up.clone().unwrap();
404 new_pos.bindings = bindings_builder.copy(&new_pos.bindings);
405 // Add matches from this repetition to the `matches` of `up`
406 bindings_builder.push_nested(&mut new_pos.bindings, &item.bindings);
408 // Move the "dot" past the repetition in `up`
410 new_pos.is_error = new_pos.is_error || item.is_error;
411 cur_items.push(new_pos);
414 // Check if we need a separator.
415 // We check the separator one by one
416 let sep_idx = *item.sep_parsed.as_ref().unwrap_or(&0);
417 let sep_len = item.sep.as_ref().map_or(0, Separator::tt_count);
418 if item.sep.is_some() && sep_idx != sep_len {
419 let sep = item.sep.as_ref().unwrap();
420 if src.clone().expect_separator(sep, sep_idx) {
422 item.sep_parsed = Some(sep_idx + 1);
423 try_push!(next_items, item);
426 // We don't need a separator. Move the "dot" back to the beginning of the matcher
427 // and try to match again UNLESS we are only allowed to have _one_ repetition.
428 else if item.sep_kind != Some(RepeatKind::ZeroOrOne) {
429 item.dot = item.dot.reset();
430 item.sep_parsed = None;
431 bindings_builder.push_default(&mut item.bindings);
432 cur_items.push(item);
435 // If we are not in a repetition, then being at the end of a matcher means that we have
436 // reached the potential end of the input.
437 try_push!(eof_items, item);
444 // We are in the middle of a matcher.
446 OpDelimited::Op(Op::Repeat { tokens, kind, separator }) => {
447 if matches!(kind, RepeatKind::ZeroOrMore | RepeatKind::ZeroOrOne) {
448 let mut new_item = item.clone();
449 new_item.bindings = bindings_builder.copy(&new_item.bindings);
451 let mut vars = Vec::new();
452 collect_vars(&mut vars, tokens);
454 bindings_builder.push_empty(&mut new_item.bindings, &var);
456 cur_items.push(new_item);
458 cur_items.push(MatchState {
459 dot: tokens.iter_delimited(None),
460 stack: Default::default(),
461 up: Some(Box::new(item)),
462 sep: separator.clone(),
463 sep_kind: Some(*kind),
465 bindings: bindings_builder.alloc(),
470 OpDelimited::Op(Op::Subtree { tokens, delimiter }) => {
471 if let Ok(subtree) = src.clone().expect_subtree() {
472 if subtree.delimiter_kind() == delimiter.map(|it| it.kind) {
473 item.stack.push(item.dot);
474 item.dot = tokens.iter_delimited(delimiter.as_ref());
475 cur_items.push(item);
479 OpDelimited::Op(Op::Var { kind, name, .. }) => {
480 if let Some(kind) = kind {
481 let mut fork = src.clone();
482 let match_res = match_meta_var(kind.as_str(), &mut fork);
483 match match_res.err {
485 // Some meta variables are optional (e.g. vis)
486 if match_res.value.is_some() {
487 item.meta_result = Some((fork, match_res));
488 try_push!(bb_items, item);
490 bindings_builder.push_optional(&mut item.bindings, name);
492 cur_items.push(item);
497 if let Some(fragment) = match_res.value {
498 bindings_builder.push_fragment(&mut item.bindings, name, fragment);
500 item.is_error = true;
501 error_items.push(item);
506 OpDelimited::Op(Op::Leaf(leaf)) => {
507 if let Err(err) = match_leaf(leaf, &mut src.clone()) {
509 item.is_error = true;
513 try_push!(next_items, item);
515 OpDelimited::Open => {
516 if matches!(src.clone().next(), Some(tt::TokenTree::Subtree(..))) {
518 try_push!(next_items, item);
521 OpDelimited::Close => {
522 let is_delim_closed = src.peek_n(0).is_none() && !stack.is_empty();
525 try_push!(next_items, item);
532 fn match_loop(pattern: &MetaTemplate, src: &tt::Subtree) -> Match {
533 let mut src = TtIter::new(src);
534 let mut stack: SmallVec<[TtIter; 1]> = SmallVec::new();
535 let mut res = Match::default();
536 let mut error_recover_item = None;
538 let mut bindings_builder = BindingsBuilder::default();
540 let mut cur_items = smallvec![MatchState {
541 dot: pattern.iter_delimited(None),
542 stack: Default::default(),
547 bindings: bindings_builder.alloc(),
552 let mut next_items = vec![];
555 let mut bb_items = SmallVec::new();
556 let mut eof_items = SmallVec::new();
557 let mut error_items = SmallVec::new();
559 stdx::always!(next_items.is_empty());
565 &mut bindings_builder,
572 stdx::always!(cur_items.is_empty());
574 if !error_items.is_empty() {
575 error_recover_item = error_items.pop().map(|it| it.bindings);
576 } else if !eof_items.is_empty() {
577 error_recover_item = Some(eof_items[0].bindings.clone());
580 // We need to do some post processing after the `match_loop_inner`.
581 // If we reached the EOF, check that there is EXACTLY ONE possible matcher. Otherwise,
582 // either the parse is ambiguous (which should never happen) or there is a syntax error.
583 if src.peek_n(0).is_none() && stack.is_empty() {
584 if eof_items.len() == 1 {
585 // remove all errors, because it is the correct answer !
586 res = Match::default();
587 res.bindings = bindings_builder.build(&eof_items[0].bindings);
590 if let Some(item) = error_recover_item {
591 res.bindings = bindings_builder.build(&item);
593 res.add_err(ExpandError::UnexpectedToken);
598 // If there are no possible next positions AND we aren't waiting for the black-box parser,
599 // then there is a syntax error.
601 // Another possibility is that we need to call out to parse some rust nonterminal
602 // (black-box) parser. However, if there is not EXACTLY ONE of these, something is wrong.
603 if (bb_items.is_empty() && next_items.is_empty())
604 || (!bb_items.is_empty() && !next_items.is_empty())
605 || bb_items.len() > 1
607 res.unmatched_tts += src.len();
608 while let Some(it) = stack.pop() {
610 res.unmatched_tts += src.len();
612 res.add_err(err!("leftover tokens"));
614 if let Some(error_reover_item) = error_recover_item {
615 res.bindings = bindings_builder.build(&error_reover_item);
619 // Dump all possible `next_items` into `cur_items` for the next iteration.
620 else if !next_items.is_empty() {
621 // Now process the next token
622 cur_items.extend(next_items.drain(..));
625 Some(tt::TokenTree::Subtree(subtree)) => {
626 stack.push(src.clone());
627 src = TtIter::new(subtree);
629 None if !stack.is_empty() => src = stack.pop().unwrap(),
633 // Finally, we have the case where we need to call the black-box parser to get some
636 stdx::always!(bb_items.len() == 1);
637 let mut item = bb_items.pop().unwrap();
639 if let Some(OpDelimited::Op(Op::Var { name, .. })) = item.dot.peek() {
640 let (iter, match_res) = item.meta_result.take().unwrap();
641 match match_res.value {
643 bindings_builder.push_fragment(&mut item.bindings, name, fragment);
645 None if match_res.err.is_none() => {
646 bindings_builder.push_optional(&mut item.bindings, name);
650 if let Some(err) = match_res.err {
658 cur_items.push(item);
660 stdx::always!(!cur_items.is_empty());
664 fn match_leaf(lhs: &tt::Leaf, src: &mut TtIter) -> Result<(), ExpandError> {
665 let rhs = match src.expect_leaf() {
668 return Err(err!("expected leaf: `{}`", lhs));
673 tt::Leaf::Punct(tt::Punct { char: lhs, .. }),
674 tt::Leaf::Punct(tt::Punct { char: rhs, .. }),
675 ) if lhs == rhs => (),
677 tt::Leaf::Ident(tt::Ident { text: lhs, .. }),
678 tt::Leaf::Ident(tt::Ident { text: rhs, .. }),
679 ) if lhs == rhs => (),
681 tt::Leaf::Literal(tt::Literal { text: lhs, .. }),
682 tt::Leaf::Literal(tt::Literal { text: rhs, .. }),
683 ) if lhs == rhs => (),
685 return Err(ExpandError::UnexpectedToken);
692 fn match_meta_var(kind: &str, input: &mut TtIter) -> ExpandResult<Option<Fragment>> {
693 let fragment = match kind {
697 "pat" | "pat_param" => Pattern, // FIXME: edition2021
703 let tt_result = match kind {
706 .map(|ident| Some(tt::Leaf::from(ident.clone()).into()))
707 .map_err(|()| err!("expected ident")),
708 "tt" => input.expect_tt().map(Some).map_err(|()| err!()),
710 input.expect_lifetime().map(Some).map_err(|()| err!("expected lifetime"))
713 let neg = input.eat_char('-');
717 let lit = literal.clone();
719 None => Some(lit.into()),
720 Some(neg) => Some(tt::TokenTree::Subtree(tt::Subtree {
722 token_trees: vec![neg, lit.into()],
726 .map_err(|()| err!())
729 "vis" => Ok(input.eat_vis()),
730 _ => Err(ExpandError::UnexpectedToken),
732 return tt_result.map(|it| it.map(Fragment::Tokens)).into();
735 let result = input.expect_fragment(fragment);
736 result.map(|tt| if kind == "expr" { tt.map(Fragment::Expr) } else { tt.map(Fragment::Tokens) })
739 fn collect_vars(buf: &mut Vec<SmolStr>, pattern: &MetaTemplate) {
740 for op in pattern.iter() {
742 Op::Var { name, .. } => buf.push(name.clone()),
744 Op::Subtree { tokens, .. } => collect_vars(buf, tokens),
745 Op::Repeat { tokens, .. } => collect_vars(buf, tokens),
751 fn iter_delimited<'a>(&'a self, delimited: Option<&'a tt::Delimiter>) -> OpDelimitedIter<'a> {
752 OpDelimitedIter { inner: &self.0, idx: 0, delimited }
756 #[derive(Debug, Clone, Copy)]
757 enum OpDelimited<'a> {
763 #[derive(Debug, Clone, Copy)]
764 struct OpDelimitedIter<'a> {
766 delimited: Option<&'a tt::Delimiter>,
770 impl<'a> OpDelimitedIter<'a> {
771 fn is_eof(&self) -> bool {
772 let len = self.inner.len() + if self.delimited.is_some() { 2 } else { 0 };
776 fn peek(&self) -> Option<OpDelimited<'a>> {
777 match self.delimited {
778 None => self.inner.get(self.idx).map(OpDelimited::Op),
779 Some(_) => match self.idx {
780 0 => Some(OpDelimited::Open),
781 i if i == self.inner.len() + 1 => Some(OpDelimited::Close),
782 i => self.inner.get(i - 1).map(OpDelimited::Op),
787 fn reset(&self) -> Self {
788 Self { inner: self.inner, idx: 0, delimited: self.delimited }
792 impl<'a> Iterator for OpDelimitedIter<'a> {
793 type Item = OpDelimited<'a>;
795 fn next(&mut self) -> Option<Self::Item> {
796 let res = self.peek();
801 fn size_hint(&self) -> (usize, Option<usize>) {
802 let len = self.inner.len() + if self.delimited.is_some() { 2 } else { 0 };
803 let remain = len.saturating_sub(self.idx);
804 (remain, Some(remain))
808 impl<'a> TtIter<'a> {
809 fn expect_separator(&mut self, separator: &Separator, idx: usize) -> bool {
810 let mut fork = self.clone();
811 let ok = match separator {
812 Separator::Ident(lhs) if idx == 0 => match fork.expect_ident_or_underscore() {
813 Ok(rhs) => rhs.text == lhs.text,
816 Separator::Literal(lhs) if idx == 0 => match fork.expect_literal() {
817 Ok(rhs) => match rhs {
818 tt::Leaf::Literal(rhs) => rhs.text == lhs.text,
819 tt::Leaf::Ident(rhs) => rhs.text == lhs.text,
820 tt::Leaf::Punct(_) => false,
824 Separator::Puncts(lhss) if idx < lhss.len() => match fork.expect_punct() {
825 Ok(rhs) => rhs.char == lhss[idx].char,
836 fn expect_tt(&mut self) -> Result<tt::TokenTree, ()> {
837 match self.peek_n(0) {
838 Some(tt::TokenTree::Leaf(tt::Leaf::Punct(punct))) if punct.char == '\'' => {
839 return self.expect_lifetime();
844 let tt = self.next().ok_or(())?.clone();
845 let punct = match tt {
846 tt::TokenTree::Leaf(tt::Leaf::Punct(punct)) if punct.spacing == tt::Spacing::Joint => {
852 let (second, third) = match (self.peek_n(0), self.peek_n(1)) {
854 Some(tt::TokenTree::Leaf(tt::Leaf::Punct(p2))),
855 Some(tt::TokenTree::Leaf(tt::Leaf::Punct(p3))),
856 ) if p2.spacing == tt::Spacing::Joint => (p2.char, Some(p3.char)),
857 (Some(tt::TokenTree::Leaf(tt::Leaf::Punct(p2))), _) => (p2.char, None),
861 match (punct.char, second, third) {
862 ('.', '.', Some('.' | '=')) | ('<', '<', Some('=')) | ('>', '>', Some('=')) => {
863 let tt2 = self.next().unwrap().clone();
864 let tt3 = self.next().unwrap().clone();
865 Ok(tt::Subtree { delimiter: None, token_trees: vec![tt, tt2, tt3] }.into())
867 ('-' | '!' | '*' | '/' | '&' | '%' | '^' | '+' | '<' | '=' | '>' | '|', '=', _)
868 | ('-' | '=' | '>', '>', _)
874 let tt2 = self.next().unwrap().clone();
875 Ok(tt::Subtree { delimiter: None, token_trees: vec![tt, tt2] }.into())
881 fn expect_lifetime(&mut self) -> Result<tt::TokenTree, ()> {
882 let punct = self.expect_punct()?;
883 if punct.char != '\'' {
886 let ident = self.expect_ident_or_underscore()?;
891 tt::Leaf::Punct(*punct).into(),
892 tt::Leaf::Ident(ident.clone()).into(),
898 fn eat_vis(&mut self) -> Option<tt::TokenTree> {
899 self.expect_fragment(Visibility).value
902 fn eat_char(&mut self, c: char) -> Option<tt::TokenTree> {
903 let mut fork = self.clone();
904 match fork.expect_char(c) {
906 let tt = self.next().cloned();