1
1
use crate :: ast:: NodeId ;
2
- use crate :: early_buffered_lints:: BufferedEarlyLintId ;
3
2
use crate :: ext:: tt:: macro_parser;
4
3
use crate :: feature_gate:: Features ;
5
4
use crate :: parse:: token:: { self , Token , TokenKind } ;
@@ -250,19 +249,16 @@ pub fn parse(
250
249
/// - `sess`: the parsing session. Any errors will be emitted to this session.
251
250
/// - `features`, `attrs`: language feature flags and attributes so that we know whether to use
252
251
/// unstable features or not.
253
- fn parse_tree < I > (
252
+ fn parse_tree (
254
253
tree : tokenstream:: TokenTree ,
255
- trees : & mut Peekable < I > ,
254
+ trees : & mut Peekable < impl Iterator < Item = tokenstream :: TokenTree > > ,
256
255
expect_matchers : bool ,
257
256
sess : & ParseSess ,
258
257
features : & Features ,
259
258
attrs : & [ ast:: Attribute ] ,
260
259
edition : Edition ,
261
260
macro_node_id : NodeId ,
262
- ) -> TokenTree
263
- where
264
- I : Iterator < Item = tokenstream:: TokenTree > ,
265
- {
261
+ ) -> TokenTree {
266
262
// Depending on what `tree` is, we could be parsing different parts of a macro
267
263
match tree {
268
264
// `tree` is a `$` token. Look at the next token in `trees`
@@ -287,16 +283,7 @@ where
287
283
macro_node_id,
288
284
) ;
289
285
// Get the Kleene operator and optional separator
290
- let ( separator, op) =
291
- parse_sep_and_kleene_op (
292
- trees,
293
- span. entire ( ) ,
294
- sess,
295
- features,
296
- attrs,
297
- edition,
298
- macro_node_id,
299
- ) ;
286
+ let ( separator, op) = parse_sep_and_kleene_op ( trees, span. entire ( ) , sess) ;
300
287
// Count the number of captured "names" (i.e., named metavars)
301
288
let name_captures = macro_parser:: count_names ( & sequence) ;
302
289
TokenTree :: Sequence (
@@ -375,10 +362,10 @@ fn kleene_op(token: &Token) -> Option<KleeneOp> {
375
362
/// - Ok(Ok((op, span))) if the next token tree is a KleeneOp
376
363
/// - Ok(Err(tok, span)) if the next token tree is a token but not a KleeneOp
377
364
/// - Err(span) if the next token tree is not a token
378
- fn parse_kleene_op < I > ( input : & mut I , span : Span ) -> Result < Result < ( KleeneOp , Span ) , Token > , Span >
379
- where
380
- I : Iterator < Item = tokenstream :: TokenTree > ,
381
- {
365
+ fn parse_kleene_op (
366
+ input : & mut impl Iterator < Item = tokenstream :: TokenTree > ,
367
+ span : Span ,
368
+ ) -> Result < Result < ( KleeneOp , Span ) , Token > , Span > {
382
369
match input. next ( ) {
383
370
Some ( tokenstream:: TokenTree :: Token ( token) ) => match kleene_op ( & token) {
384
371
Some ( op) => Ok ( Ok ( ( op, token. span ) ) ) ,
@@ -403,178 +390,20 @@ where
403
390
/// session `sess`. If the next one (or possibly two) tokens in `input` correspond to a Kleene
404
391
/// operator and separator, then a tuple with `(separator, KleeneOp)` is returned. Otherwise, an
405
392
/// error with the appropriate span is emitted to `sess` and a dummy value is returned.
406
- ///
407
- /// N.B., in the 2015 edition, `*` and `+` are the only Kleene operators, and `?` is a separator.
408
- /// In the 2018 edition however, `?` is a Kleene operator, and not a separator.
409
- fn parse_sep_and_kleene_op < I > (
410
- input : & mut Peekable < I > ,
411
- span : Span ,
412
- sess : & ParseSess ,
413
- features : & Features ,
414
- attrs : & [ ast:: Attribute ] ,
415
- edition : Edition ,
416
- macro_node_id : NodeId ,
417
- ) -> ( Option < Token > , KleeneOp )
418
- where
419
- I : Iterator < Item = tokenstream:: TokenTree > ,
420
- {
421
- match edition {
422
- Edition :: Edition2015 => parse_sep_and_kleene_op_2015 (
423
- input,
424
- span,
425
- sess,
426
- features,
427
- attrs,
428
- macro_node_id,
429
- ) ,
430
- Edition :: Edition2018 => parse_sep_and_kleene_op_2018 ( input, span, sess, features, attrs) ,
431
- }
432
- }
433
-
434
- // `?` is a separator (with a migration warning) and never a KleeneOp.
435
- fn parse_sep_and_kleene_op_2015 < I > (
436
- input : & mut Peekable < I > ,
437
- span : Span ,
438
- sess : & ParseSess ,
439
- _features : & Features ,
440
- _attrs : & [ ast:: Attribute ] ,
441
- macro_node_id : NodeId ,
442
- ) -> ( Option < Token > , KleeneOp )
443
- where
444
- I : Iterator < Item = tokenstream:: TokenTree > ,
445
- {
446
- // We basically look at two token trees here, denoted as #1 and #2 below
447
- let span = match parse_kleene_op ( input, span) {
448
- // #1 is a `+` or `*` KleeneOp
449
- //
450
- // `?` is ambiguous: it could be a separator (warning) or a Kleene::ZeroOrOne (error), so
451
- // we need to look ahead one more token to be sure.
452
- Ok ( Ok ( ( op, _) ) ) if op != KleeneOp :: ZeroOrOne => return ( None , op) ,
453
-
454
- // #1 is `?` token, but it could be a Kleene::ZeroOrOne (error in 2015) without a separator
455
- // or it could be a `?` separator followed by any Kleene operator. We need to look ahead 1
456
- // token to find out which.
457
- Ok ( Ok ( ( op, op1_span) ) ) => {
458
- assert_eq ! ( op, KleeneOp :: ZeroOrOne ) ;
459
-
460
- // Lookahead at #2. If it is a KleenOp, then #1 is a separator.
461
- let is_1_sep = if let Some ( tokenstream:: TokenTree :: Token ( tok2) ) = input. peek ( ) {
462
- kleene_op ( tok2) . is_some ( )
463
- } else {
464
- false
465
- } ;
466
-
467
- if is_1_sep {
468
- // #1 is a separator and #2 should be a KleepeOp.
469
- // (N.B. We need to advance the input iterator.)
470
- match parse_kleene_op ( input, span) {
471
- // #2 is `?`, which is not allowed as a Kleene op in 2015 edition,
472
- // but is allowed in the 2018 edition.
473
- Ok ( Ok ( ( op, op2_span) ) ) if op == KleeneOp :: ZeroOrOne => {
474
- sess. span_diagnostic
475
- . struct_span_err ( op2_span, "expected `*` or `+`" )
476
- . note ( "`?` is not a macro repetition operator in the 2015 edition, \
477
- but is accepted in the 2018 edition")
478
- . emit ( ) ;
479
-
480
- // Return a dummy
481
- return ( None , KleeneOp :: ZeroOrMore ) ;
482
- }
483
-
484
- // #2 is a Kleene op, which is the only valid option
485
- Ok ( Ok ( ( op, _) ) ) => {
486
- // Warn that `?` as a separator will be deprecated
487
- sess. buffer_lint (
488
- BufferedEarlyLintId :: QuestionMarkMacroSep ,
489
- op1_span,
490
- macro_node_id,
491
- "using `?` as a separator is deprecated and will be \
492
- a hard error in an upcoming edition",
493
- ) ;
494
-
495
- return ( Some ( Token :: new ( token:: Question , op1_span) ) , op) ;
496
- }
497
-
498
- // #2 is a random token (this is an error) :(
499
- Ok ( Err ( _) ) => op1_span,
500
-
501
- // #2 is not even a token at all :(
502
- Err ( _) => op1_span,
503
- }
504
- } else {
505
- // `?` is not allowed as a Kleene op in 2015,
506
- // but is allowed in the 2018 edition
507
- sess. span_diagnostic
508
- . struct_span_err ( op1_span, "expected `*` or `+`" )
509
- . note ( "`?` is not a macro repetition operator in the 2015 edition, \
510
- but is accepted in the 2018 edition")
511
- . emit ( ) ;
512
-
513
- // Return a dummy
514
- return ( None , KleeneOp :: ZeroOrMore ) ;
515
- }
516
- }
517
-
518
- // #1 is a separator followed by #2, a KleeneOp
519
- Ok ( Err ( token) ) => match parse_kleene_op ( input, token. span ) {
520
- // #2 is a `?`, which is not allowed as a Kleene op in 2015 edition,
521
- // but is allowed in the 2018 edition
522
- Ok ( Ok ( ( op, op2_span) ) ) if op == KleeneOp :: ZeroOrOne => {
523
- sess. span_diagnostic
524
- . struct_span_err ( op2_span, "expected `*` or `+`" )
525
- . note ( "`?` is not a macro repetition operator in the 2015 edition, \
526
- but is accepted in the 2018 edition")
527
- . emit ( ) ;
528
-
529
- // Return a dummy
530
- return ( None , KleeneOp :: ZeroOrMore ) ;
531
- }
532
-
533
- // #2 is a KleeneOp :D
534
- Ok ( Ok ( ( op, _) ) ) => return ( Some ( token) , op) ,
535
-
536
- // #2 is a random token :(
537
- Ok ( Err ( token) ) => token. span ,
538
-
539
- // #2 is not a token at all :(
540
- Err ( span) => span,
541
- } ,
542
-
543
- // #1 is not a token
544
- Err ( span) => span,
545
- } ;
546
-
547
- sess. span_diagnostic . span_err ( span, "expected `*` or `+`" ) ;
548
-
549
- // Return a dummy
550
- ( None , KleeneOp :: ZeroOrMore )
551
- }
552
-
553
- // `?` is a Kleene op, not a separator
554
- fn parse_sep_and_kleene_op_2018 < I > (
555
- input : & mut Peekable < I > ,
393
+ fn parse_sep_and_kleene_op (
394
+ input : & mut Peekable < impl Iterator < Item = tokenstream:: TokenTree > > ,
556
395
span : Span ,
557
396
sess : & ParseSess ,
558
- _features : & Features ,
559
- _attrs : & [ ast:: Attribute ] ,
560
- ) -> ( Option < Token > , KleeneOp )
561
- where
562
- I : Iterator < Item = tokenstream:: TokenTree > ,
563
- {
397
+ ) -> ( Option < Token > , KleeneOp ) {
564
398
// We basically look at two token trees here, denoted as #1 and #2 below
565
399
let span = match parse_kleene_op ( input, span) {
566
- // #1 is a `?` (needs feature gate)
567
- Ok ( Ok ( ( op, _op1_span) ) ) if op == KleeneOp :: ZeroOrOne => {
568
- return ( None , op) ;
569
- }
570
-
571
- // #1 is a `+` or `*` KleeneOp
400
+ // #1 is a `?`, `+`, or `*` KleeneOp
572
401
Ok ( Ok ( ( op, _) ) ) => return ( None , op) ,
573
402
574
403
// #1 is a separator followed by #2, a KleeneOp
575
404
Ok ( Err ( token) ) => match parse_kleene_op ( input, token. span ) {
576
405
// #2 is the `?` Kleene op, which does not take a separator (error)
577
- Ok ( Ok ( ( op , _op2_span ) ) ) if op == KleeneOp :: ZeroOrOne => {
406
+ Ok ( Ok ( ( KleeneOp :: ZeroOrOne , _ ) ) ) => {
578
407
// Error!
579
408
sess. span_diagnostic . span_err (
580
409
token. span ,
@@ -588,11 +417,8 @@ where
588
417
// #2 is a KleeneOp :D
589
418
Ok ( Ok ( ( op, _) ) ) => return ( Some ( token) , op) ,
590
419
591
- // #2 is a random token :(
592
- Ok ( Err ( token) ) => token. span ,
593
-
594
- // #2 is not a token at all :(
595
- Err ( span) => span,
420
+ // #2 is a random token or not a token at all :(
421
+ Ok ( Err ( Token { span, .. } ) ) | Err ( span) => span,
596
422
} ,
597
423
598
424
// #1 is not a token
0 commit comments