@@ -422,8 +422,8 @@ extension Parser {
422
422
return . scalarSequence( . init( scalars, trivia: trivia) )
423
423
}
424
424
425
- /// Eat a scalar off the front, starting from after the
426
- /// backslash and base character (e.g. `\u` or `\x`).
425
+ /// Try to eat a scalar off the front, starting from after the backslash and
426
+ /// base character (e.g. `\u` or `\x`).
427
427
///
428
428
/// UniScalar -> 'u{' UniScalarSequence '}'
429
429
/// | 'u' HexDigit{4}
@@ -433,18 +433,16 @@ extension Parser {
433
433
/// | 'o{' OctalDigit{1...} '}'
434
434
/// | '0' OctalDigit{0...3}
435
435
///
436
- mutating func expectUnicodeScalar(
437
- escapedCharacter base: Character
438
- ) -> AST . Atom . Kind {
439
- recordLoc { p in
436
+ mutating func lexUnicodeScalar( ) -> AST . Atom . Kind ? {
437
+ tryEating { p in
440
438
441
439
func nullScalar( ) -> AST . Atom . Scalar {
442
440
. init( UnicodeScalar ( 0 ) , p. loc ( p. src. currentPosition) )
443
441
}
444
442
445
443
// TODO: PCRE offers a different behavior if PCRE2_ALT_BSUX is set.
446
- switch base {
447
- // Hex numbers.
444
+ switch p . tryEat ( ) {
445
+ // Hex numbers.
448
446
case " u " where p. tryEat ( " { " ) :
449
447
return p. expectUnicodeScalarSequence ( eating: " } " )
450
448
@@ -469,7 +467,7 @@ extension Parser {
469
467
case " U " :
470
468
return . scalar( p. expectUnicodeScalar ( numDigits: 8 ) )
471
469
472
- // Octal numbers.
470
+ // Octal numbers.
473
471
case " o " where p. tryEat ( " { " ) :
474
472
let str = p. lexUntil ( eating: " } " )
475
473
return . scalar( p. validateUnicodeScalar ( str, . octal) )
@@ -485,10 +483,9 @@ extension Parser {
485
483
return . scalar( p. validateUnicodeScalar ( digits, . octal) )
486
484
487
485
default :
488
- p. unreachable ( " Unexpected scalar start " )
489
- return . scalar( nullScalar ( ) )
486
+ return nil
490
487
}
491
- } . value
488
+ }
492
489
}
493
490
494
491
/// Try to consume a quantifier
@@ -1739,6 +1736,11 @@ extension Parser {
1739
1736
return ref
1740
1737
}
1741
1738
1739
+ // Hexadecimal and octal unicode scalars.
1740
+ if let scalar = p. lexUnicodeScalar ( ) {
1741
+ return scalar
1742
+ }
1743
+
1742
1744
guard let charLoc = p. tryEatWithLoc ( ) else {
1743
1745
p. errorAtCurrentPosition ( . expectedEscape)
1744
1746
return . invalid
@@ -1752,14 +1754,6 @@ extension Parser {
1752
1754
return . escaped( builtin)
1753
1755
}
1754
1756
1755
- switch char {
1756
- // Hexadecimal and octal unicode scalars.
1757
- case " u " , " x " , " U " , " o " , " 0 " :
1758
- return p. expectUnicodeScalar ( escapedCharacter: char)
1759
- default :
1760
- break
1761
- }
1762
-
1763
1757
// We only allow unknown escape sequences for non-letter non-number ASCII,
1764
1758
// and non-ASCII whitespace.
1765
1759
// TODO: Once we have fix-its, suggest a `0` prefix for octal `[\7]`.
0 commit comments