@@ -186,12 +186,16 @@ pub enum LiteralKind {
186
186
Str { terminated : bool } ,
187
187
/// "b"abc"", "b"abc"
188
188
ByteStr { terminated : bool } ,
189
+ /// `c"abc"`, `c"abc`
190
+ CStr { terminated : bool } ,
189
191
/// "r"abc"", "r#"abc"#", "r####"ab"###"c"####", "r#"a". `None` indicates
190
192
/// an invalid literal.
191
193
RawStr { n_hashes : Option < u8 > } ,
192
194
/// "br"abc"", "br#"abc"#", "br####"ab"###"c"####", "br#"a". `None`
193
195
/// indicates an invalid literal.
194
196
RawByteStr { n_hashes : Option < u8 > } ,
197
+ /// `cr"abc"`, "cr#"abc"#", `cr#"a`. `None` indicates an invalid literal.
198
+ RawCStr { n_hashes : Option < u8 > } ,
195
199
}
196
200
197
201
#[ derive( Clone , Copy , Debug , PartialEq , Eq , PartialOrd , Ord ) ]
@@ -357,39 +361,18 @@ impl Cursor<'_> {
357
361
} ,
358
362
359
363
// Byte literal, byte string literal, raw byte string literal or identifier.
360
- 'b' => match ( self . first ( ) , self . second ( ) ) {
361
- ( '\'' , _) => {
362
- self . bump ( ) ;
363
- let terminated = self . single_quoted_string ( ) ;
364
- let suffix_start = self . pos_within_token ( ) ;
365
- if terminated {
366
- self . eat_literal_suffix ( ) ;
367
- }
368
- let kind = Byte { terminated } ;
369
- Literal { kind, suffix_start }
370
- }
371
- ( '"' , _) => {
372
- self . bump ( ) ;
373
- let terminated = self . double_quoted_string ( ) ;
374
- let suffix_start = self . pos_within_token ( ) ;
375
- if terminated {
376
- self . eat_literal_suffix ( ) ;
377
- }
378
- let kind = ByteStr { terminated } ;
379
- Literal { kind, suffix_start }
380
- }
381
- ( 'r' , '"' ) | ( 'r' , '#' ) => {
382
- self . bump ( ) ;
383
- let res = self . raw_double_quoted_string ( 2 ) ;
384
- let suffix_start = self . pos_within_token ( ) ;
385
- if res. is_ok ( ) {
386
- self . eat_literal_suffix ( ) ;
387
- }
388
- let kind = RawByteStr { n_hashes : res. ok ( ) } ;
389
- Literal { kind, suffix_start }
390
- }
391
- _ => self . ident_or_unknown_prefix ( ) ,
392
- } ,
364
+ 'b' => self . c_or_byte_string (
365
+ |terminated| ByteStr { terminated } ,
366
+ |n_hashes| RawByteStr { n_hashes } ,
367
+ Some ( |terminated| Byte { terminated } ) ,
368
+ ) ,
369
+
370
+ // c-string literal, raw c-string literal or identifier.
371
+ 'c' => self . c_or_byte_string (
372
+ |terminated| CStr { terminated } ,
373
+ |n_hashes| RawCStr { n_hashes } ,
374
+ None ,
375
+ ) ,
393
376
394
377
// Identifier (this should be checked after other variant that can
395
378
// start as identifier).
@@ -553,6 +536,47 @@ impl Cursor<'_> {
553
536
}
554
537
}
555
538
539
+ fn c_or_byte_string (
540
+ & mut self ,
541
+ mk_kind : impl FnOnce ( bool ) -> LiteralKind ,
542
+ mk_kind_raw : impl FnOnce ( Option < u8 > ) -> LiteralKind ,
543
+ single_quoted : Option < fn ( bool ) -> LiteralKind > ,
544
+ ) -> TokenKind {
545
+ match ( self . first ( ) , self . second ( ) , single_quoted) {
546
+ ( '\'' , _, Some ( mk_kind) ) => {
547
+ self . bump ( ) ;
548
+ let terminated = self . single_quoted_string ( ) ;
549
+ let suffix_start = self . pos_within_token ( ) ;
550
+ if terminated {
551
+ self . eat_literal_suffix ( ) ;
552
+ }
553
+ let kind = mk_kind ( terminated) ;
554
+ Literal { kind, suffix_start }
555
+ }
556
+ ( '"' , _, _) => {
557
+ self . bump ( ) ;
558
+ let terminated = self . double_quoted_string ( ) ;
559
+ let suffix_start = self . pos_within_token ( ) ;
560
+ if terminated {
561
+ self . eat_literal_suffix ( ) ;
562
+ }
563
+ let kind = mk_kind ( terminated) ;
564
+ Literal { kind, suffix_start }
565
+ }
566
+ ( 'r' , '"' , _) | ( 'r' , '#' , _) => {
567
+ self . bump ( ) ;
568
+ let res = self . raw_double_quoted_string ( 2 ) ;
569
+ let suffix_start = self . pos_within_token ( ) ;
570
+ if res. is_ok ( ) {
571
+ self . eat_literal_suffix ( ) ;
572
+ }
573
+ let kind = mk_kind_raw ( res. ok ( ) ) ;
574
+ Literal { kind, suffix_start }
575
+ }
576
+ _ => self . ident_or_unknown_prefix ( ) ,
577
+ }
578
+ }
579
+
556
580
fn number ( & mut self , first_digit : char ) -> LiteralKind {
557
581
debug_assert ! ( '0' <= self . prev( ) && self . prev( ) <= '9' ) ;
558
582
let mut base = Base :: Decimal ;
0 commit comments