@@ -181,6 +181,8 @@ struct MatcherPos {
181
181
match_hi : usize ,
182
182
183
183
// Specifically used if we are matching a repetition. If we aren't both should be `None`.
184
+ /// The KleeneOp of this sequence if we are in a repetition.
185
+ seq_op : Option < quoted:: KleeneOp > ,
184
186
/// The separator if we are in a repetition
185
187
sep : Option < Token > ,
186
188
/// The "parent" matcher position if we are in a repetition. That is, the matcher position just
@@ -263,6 +265,7 @@ fn initial_matcher_pos(ms: Vec<TokenTree>, lo: BytePos) -> Box<MatcherPos> {
263
265
stack : vec ! [ ] ,
264
266
265
267
// Haven't descended into any sequences, so both of these are `None`.
268
+ seq_op : None ,
266
269
sep : None ,
267
270
up : None ,
268
271
} )
@@ -464,10 +467,11 @@ fn inner_parse_loop(
464
467
item. idx += 1 ;
465
468
next_items. push ( item) ;
466
469
}
467
- }
470
+ }
468
471
// We don't need a separator. Move the "dot" back to the beginning of the matcher
469
- // and try to match again.
470
- else {
472
+ // and try to match again UNLESS we are only allowed to have _one_ repetition.
473
+ else if item. seq_op != Some ( quoted:: KleeneOp :: ZeroOrOne ) {
474
+ // we don't need a separator
471
475
item. match_cur = item. match_lo ;
472
476
item. idx = 0 ;
473
477
cur_items. push ( item) ;
@@ -499,26 +503,20 @@ fn inner_parse_loop(
499
503
cur_items. push ( new_item) ;
500
504
}
501
505
502
- // For ZeroOrMore and OneOrMore, we want to examine the case were there is at
503
- // least one match. For ZeroOrOne, we only want the case where there is exactly
504
- // one match.
505
- if ( seq. op == quoted:: KleeneOp :: ZeroOrOne && seq. num_captures == 1 )
506
- || seq. op != quoted:: KleeneOp :: ZeroOrOne
507
- {
508
- let matches = create_matches ( item. matches . len ( ) ) ;
509
- cur_items. push ( Box :: new ( MatcherPos {
510
- stack : vec ! [ ] ,
511
- sep : seq. separator . clone ( ) ,
512
- idx : 0 ,
513
- matches,
514
- match_lo : item. match_cur ,
515
- match_cur : item. match_cur ,
516
- match_hi : item. match_cur + seq. num_captures ,
517
- up : Some ( item) ,
518
- sp_lo : sp. lo ( ) ,
519
- top_elts : Tt ( TokenTree :: Sequence ( sp, seq) ) ,
520
- } ) ) ;
521
- }
506
+ let matches = create_matches ( item. matches . len ( ) ) ;
507
+ cur_items. push ( Box :: new ( MatcherPos {
508
+ stack : vec ! [ ] ,
509
+ sep : seq. separator . clone ( ) ,
510
+ seq_op : Some ( seq. op ) ,
511
+ idx : 0 ,
512
+ matches,
513
+ match_lo : item. match_cur ,
514
+ match_cur : item. match_cur ,
515
+ match_hi : item. match_cur + seq. num_captures ,
516
+ up : Some ( item) ,
517
+ sp_lo : sp. lo ( ) ,
518
+ top_elts : Tt ( TokenTree :: Sequence ( sp, seq) ) ,
519
+ } ) ) ;
522
520
}
523
521
524
522
// We need to match a metavar (but the identifier is invalid)... this is an error
0 commit comments