8
8
use crate :: unicode_table;
9
9
use nom:: {
10
10
branch:: alt,
11
- bytes:: complete:: { tag, take, take_till} ,
11
+ bytes:: complete:: { tag, take, take_till, take_until } ,
12
12
character:: complete:: one_of,
13
13
combinator:: { map, map_opt, peek, recognize, value} ,
14
14
multi:: { many0, many_m_n} ,
15
- sequence:: { delimited, preceded, separated_pair} ,
15
+ sequence:: { delimited, preceded, separated_pair, terminated } ,
16
16
IResult , Parser ,
17
17
} ;
18
18
use std:: {
@@ -39,6 +39,7 @@ pub enum BadSequence {
39
39
Set1LongerSet2EndsInClass ,
40
40
ComplementMoreThanOneUniqueInSet2 ,
41
41
BackwardsRange { end : u32 , start : u32 } ,
42
+ MultipleCharInEquivalence ( String ) ,
42
43
}
43
44
44
45
impl Display for BadSequence {
@@ -89,6 +90,10 @@ impl Display for BadSequence {
89
90
end_or_start_to_string( end)
90
91
)
91
92
}
93
+ Self :: MultipleCharInEquivalence ( s) => write ! (
94
+ f,
95
+ "{s}: equivalence class operand must be a single character"
96
+ ) ,
92
97
}
93
98
}
94
99
}
@@ -492,18 +497,37 @@ impl Sequence {
492
497
}
493
498
494
499
fn parse_char_equal ( input : & [ u8 ] ) -> IResult < & [ u8 ] , Result < Self , BadSequence > > {
495
- delimited (
500
+ preceded (
496
501
tag ( "[=" ) ,
497
- alt ( (
498
- value (
499
- Err ( BadSequence :: MissingEquivalentClassChar ) ,
500
- peek ( tag ( "=]" ) ) ,
501
- ) ,
502
- map ( Self :: parse_backslash_or_char, |c| Ok ( Self :: Char ( c) ) ) ,
503
- ) ) ,
504
- tag ( "=]" ) ,
502
+ (
503
+ alt ( (
504
+ value ( Err ( ( ) ) , peek ( tag ( "=]" ) ) ) ,
505
+ map ( Self :: parse_backslash_or_char, Ok ) ,
506
+ ) ) ,
507
+ map ( terminated ( take_until ( "=]" ) , tag ( "=]" ) ) , |v : & [ u8 ] | {
508
+ if v. is_empty ( ) {
509
+ Ok ( ( ) )
510
+ } else {
511
+ Err ( v)
512
+ }
513
+ } ) ,
514
+ ) ,
505
515
)
506
516
. parse ( input)
517
+ . map ( |( l, ( a, b) ) | {
518
+ (
519
+ l,
520
+ match ( a, b) {
521
+ ( Err ( ( ) ) , _) => Err ( BadSequence :: MissingEquivalentClassChar ) ,
522
+ ( Ok ( c) , Ok ( ( ) ) ) => Ok ( Self :: Char ( c) ) ,
523
+ ( Ok ( c) , Err ( v) ) => Err ( BadSequence :: MultipleCharInEquivalence ( format ! (
524
+ "{}{}" ,
525
+ String :: from_utf8_lossy( & [ c] ) . into_owned( ) ,
526
+ String :: from_utf8_lossy( v) . into_owned( )
527
+ ) ) ) ,
528
+ } ,
529
+ )
530
+ } )
507
531
}
508
532
}
509
533
0 commit comments