1#![doc = include_str!("../README.md")]
2pub mod ctx;
3pub mod err;
4pub mod iter;
5pub mod r#macro;
6pub mod map;
7pub mod neu;
8pub mod re;
9pub mod span;
10
11#[cfg(feature = "log")]
12pub(crate) use tracing::trace as trace_log;
13#[cfg(not(feature = "log"))]
14#[macro_use]
15pub(crate) mod log {
16 #[macro_export]
17 macro_rules! trace_log {
18 ($($arg:tt)*) => {
19 ();
20 };
21 }
22}
23
24#[cfg(feature = "log")]
25pub trait MayDebug: std::fmt::Debug {}
26
27#[cfg(feature = "log")]
28impl<T> MayDebug for T where T: std::fmt::Debug {}
29
30#[cfg(not(feature = "log"))]
31pub trait MayDebug {}
32
33#[cfg(not(feature = "log"))]
34impl<T> MayDebug for T {}
35
36pub use charize::charize;
37pub mod prelude {
38 pub use crate::ctx::BytesCtx;
39 pub use crate::ctx::CharsCtx;
40 pub use crate::ctx::Context;
41 pub use crate::ctx::Match;
42 pub use crate::ctx::RegexCtx;
43 pub use crate::ctx::Ret;
44 pub use crate::ctx::Span;
45 pub use crate::map;
46 pub use crate::neu;
47 pub use crate::neu::Condition;
48 pub use crate::neu::Neu;
49 pub use crate::neu::Neu2Re;
50 pub use crate::neu::NeuCond;
51 pub use crate::neu::NeuOp;
52 pub use crate::re;
53 pub use crate::re::ConstructIntoOp;
54 pub use crate::re::ConstructOp;
55 pub use crate::re::Regex;
56 pub use crate::re::RegexIntoOp;
57 pub use crate::span::SimpleStorer;
58}
59
60#[cfg(test)]
61mod test {
62
63 use crate::prelude::*;
64 use crate::re;
65
66 #[test]
67 fn test_all() {
68 assert!(test_space().is_ok());
69 assert!(test_char().is_ok());
70 assert!(test_chars().is_ok());
71 assert!(test_chars_negative().is_ok());
72 assert!(test_range().is_ok());
73 assert!(test_range_negative().is_ok());
74 assert!(test_other().is_ok());
75 }
76
77 macro_rules! test_t {
78 ($ctx:ident, $storer:ident, $str:literal, $id:literal, $parser:expr) => {
79 let space_parser = $parser;
80
81 $ctx.reset_with($str);
82 $storer.reset();
83 assert!($storer.try_cap($id, &mut $ctx, &space_parser).is_err());
84 };
85 ($ctx:ident, $storer:ident, $str:literal, $id:literal, $parser:expr, $($span:expr)*) => {
86 let space_parser = $parser;
87
88 $ctx.reset_with($str);
89 $storer.reset();
90 $storer.try_cap($id, &mut $ctx, &space_parser)?;
91 assert_eq!($storer.spans_iter($id).unwrap().collect::<Vec<_>>(), vec![$($span)*])
92 };
93 }
94
95 fn test_other() -> Result<(), Box<dyn std::error::Error>> {
96 let mut ctx = RegexCtx::new("");
97 let mut storer = SimpleStorer::new(1);
98
99 test_t!(ctx, storer, "abedf", 0, re!(.), Span { beg: 0, len: 1 });
100 test_t!(ctx, storer, "abedf", 0, re!(.?), Span { beg: 0, len: 1 });
101 test_t!(ctx, storer, "\nabedf", 0, re!(.?), Span { beg: 0, len: 0 });
102 test_t!(ctx, storer, "abedf", 0, re!(.*), Span { beg: 0, len: 5 });
103 test_t!(ctx, storer, "\nabedf", 0, re!(.*), Span { beg: 0, len: 0 });
104 test_t!(ctx, storer, "abedf", 0, re!(.+), Span { beg: 0, len: 5 });
105 test_t!(ctx, storer, "\nabedf", 0, re!(.+));
106 test_t!(ctx, storer, "abedf", 0, re!(.{2}), Span { beg: 0, len: 2 });
107 test_t!(ctx, storer, "ab\nedf", 0, re!(.{3}));
108 test_t!(ctx, storer, "abedf", 0, re!(.{2,}), Span { beg: 0, len: 5 });
109 test_t!(
110 ctx,
111 storer,
112 "abedf",
113 0,
114 re!(.{4,6}),
115 Span { beg: 0, len: 5 }
116 );
117 test_t!(ctx, storer, "abe\ndf", 0, re!(.{4,6}));
118 test_t!(ctx, storer, "c\nabedf", 0, re!(^), Span { beg: 0, len: 1 });
119
120 Ok(())
121 }
122
123 fn test_range_negative() -> Result<(), Box<dyn std::error::Error>> {
124 let mut ctx = RegexCtx::new("");
125 let mut storer = SimpleStorer::new(1);
126
127 test_t!(
128 ctx,
129 storer,
130 "Raefc",
131 0,
132 re!([^a - z]),
133 Span { beg: 0, len: 1 }
134 );
135 test_t!(
136 ctx,
137 storer,
138 "你aefc",
139 0,
140 re!([^a - z A - Z]),
141 Span { beg: 0, len: 3 }
142 );
143 test_t!(
144 ctx,
145 storer,
146 "aefc",
147 0,
148 re!([^a - z]?),
149 Span { beg: 0, len: 0 }
150 );
151 test_t!(
152 ctx,
153 storer,
154 "AEUF",
155 0,
156 re!([^a - z]?),
157 Span { beg: 0, len: 1 }
158 );
159 test_t!(
160 ctx,
161 storer,
162 "&AEUF",
163 0,
164 re!([^a - z A - Z]),
165 Span { beg: 0, len: 1 }
166 );
167 test_t!(
168 ctx,
169 storer,
170 "AEUF",
171 0,
172 re!([^a-z]*),
173 Span { beg: 0, len: 4 }
174 );
175 test_t!(
176 ctx,
177 storer,
178 "aefc",
179 0,
180 re!([^a-z]*),
181 Span { beg: 0, len: 0 }
182 );
183 test_t!(
184 ctx,
185 storer,
186 "@#$%",
187 0,
188 re!([^a - z A - Z]*),
189 Span { beg: 0, len: 4 }
190 );
191 test_t!(
192 ctx,
193 storer,
194 "AEUF",
195 0,
196 re!([^a-z]+),
197 Span { beg: 0, len: 4 }
198 );
199 test_t!(ctx, storer, "aefc", 0, re!([^a-z]+));
200 test_t!(
201 ctx,
202 storer,
203 "AEUF",
204 0,
205 re!([^a-z]{3}),
206 Span { beg: 0, len: 3 }
207 );
208 test_t!(ctx, storer, "aefc", 0, re!([^a-z]{3}));
209 test_t!(
210 ctx,
211 storer,
212 "AEUF",
213 0,
214 re!([^a-z]{3,6}),
215 Span { beg: 0, len: 4 }
216 );
217 test_t!(ctx, storer, "aefc", 0, re!([^a-z]{3,6}));
218 test_t!(
219 ctx,
220 storer,
221 "AEUF",
222 0,
223 re!([^a-z]{3,}),
224 Span { beg: 0, len: 4 }
225 );
226 test_t!(ctx, storer, "aefc", 0, re!([^a-z]{3,}));
227
228 test_t!(
229 ctx,
230 storer,
231 "@#$%",
232 0,
233 re!([^'a' - 'z' 'A' - 'Z']*),
234 Span { beg: 0, len: 4 }
235 );
236 test_t!(
237 ctx,
238 storer,
239 "AEUF",
240 0,
241 re!([^'a'-'z']+),
242 Span { beg: 0, len: 4 }
243 );
244 test_t!(ctx, storer, "aefc", 0, re!([^'a'-'z']+));
245 test_t!(
246 ctx,
247 storer,
248 "AEUF",
249 0,
250 re!([^'a'-'z']{3}),
251 Span { beg: 0, len: 3 }
252 );
253 test_t!(ctx, storer, "aefc", 0, re!([^'a'-'z']{3}));
254 test_t!(
255 ctx,
256 storer,
257 "AEUF",
258 0,
259 re!([^'a'-'z']{3,6}),
260 Span { beg: 0, len: 4 }
261 );
262 test_t!(ctx, storer, "aefc", 0, re!([^'a'-'z']{3,6}));
263 test_t!(
264 ctx,
265 storer,
266 "AEUF",
267 0,
268 re!([^'a'-'z']{3,}),
269 Span { beg: 0, len: 4 }
270 );
271 test_t!(ctx, storer, "aefc", 0, re!([^'a'-'z']{3,}));
272 Ok(())
273 }
274
275 fn test_range() -> Result<(), Box<dyn std::error::Error>> {
276 let mut ctx = RegexCtx::new("");
277 let mut storer = SimpleStorer::new(1);
278
279 test_t!(
280 ctx,
281 storer,
282 "aefc",
283 0,
284 re!([a - z]),
285 Span { beg: 0, len: 1 }
286 );
287 test_t!(
288 ctx,
289 storer,
290 "aefc",
291 0,
292 re!([a - z A - Z]),
293 Span { beg: 0, len: 1 }
294 );
295 test_t!(
296 ctx,
297 storer,
298 "aefc",
299 0,
300 re!([a - z]?),
301 Span { beg: 0, len: 1 }
302 );
303 test_t!(
304 ctx,
305 storer,
306 "AEUF",
307 0,
308 re!([a - z]?),
309 Span { beg: 0, len: 0 }
310 );
311 test_t!(
312 ctx,
313 storer,
314 "AEUF",
315 0,
316 re!([a - z A - Z]),
317 Span { beg: 0, len: 1 }
318 );
319 test_t!(ctx, storer, "aefc", 0, re!([a-z]*), Span { beg: 0, len: 4 });
320 test_t!(ctx, storer, "AEUF", 0, re!([a-z]*), Span { beg: 0, len: 0 });
321 test_t!(
322 ctx,
323 storer,
324 "AEUF",
325 0,
326 re!([a - z A - Z]*),
327 Span { beg: 0, len: 4 }
328 );
329 test_t!(ctx, storer, "aefc", 0, re!([a-z]+), Span { beg: 0, len: 4 });
330 test_t!(ctx, storer, "AEUF", 0, re!([a-z]+));
331 test_t!(
332 ctx,
333 storer,
334 "aefc",
335 0,
336 re!([a-z]{3}),
337 Span { beg: 0, len: 3 }
338 );
339 test_t!(ctx, storer, "AEUF", 0, re!([a-z]{3}));
340 test_t!(
341 ctx,
342 storer,
343 "aefc",
344 0,
345 re!([a-z]{3,6}),
346 Span { beg: 0, len: 4 }
347 );
348 test_t!(ctx, storer, "AEUF", 0, re!([a-z]{3,6}));
349 test_t!(
350 ctx,
351 storer,
352 "aefc",
353 0,
354 re!([a-z]{3,}),
355 Span { beg: 0, len: 4 }
356 );
357 test_t!(ctx, storer, "AEUF", 0, re!([a-z]{3,}));
358
359 test_t!(
360 ctx,
361 storer,
362 "aefc",
363 0,
364 re!(['a' - 'z']),
365 Span { beg: 0, len: 1 }
366 );
367 test_t!(
368 ctx,
369 storer,
370 "aefc",
371 0,
372 re!(['a' - 'z']?),
373 Span { beg: 0, len: 1 }
374 );
375 test_t!(
376 ctx,
377 storer,
378 "AEUF",
379 0,
380 re!(['a' - 'z']?),
381 Span { beg: 0, len: 0 }
382 );
383 test_t!(
384 ctx,
385 storer,
386 "aefc",
387 0,
388 re!(['a'-'z']*),
389 Span { beg: 0, len: 4 }
390 );
391 test_t!(
392 ctx,
393 storer,
394 "AEUF",
395 0,
396 re!(['a'-'z']*),
397 Span { beg: 0, len: 0 }
398 );
399 test_t!(
400 ctx,
401 storer,
402 "aefc",
403 0,
404 re!(['a'-'z']+),
405 Span { beg: 0, len: 4 }
406 );
407 test_t!(ctx, storer, "AEUF", 0, re!(['a'-'z']+));
408 test_t!(
409 ctx,
410 storer,
411 "AEUF",
412 0,
413 re!(['a'-'z''A'-'Z']+),
414 Span { beg: 0, len: 4 }
415 );
416 test_t!(
417 ctx,
418 storer,
419 "aefc",
420 0,
421 re!(['a'-'z']{3}),
422 Span { beg: 0, len: 3 }
423 );
424 test_t!(ctx, storer, "AEUF", 0, re!(['a'-'z']{3}));
425 test_t!(
426 ctx,
427 storer,
428 "aefc",
429 0,
430 re!(['a'-'z']{3,6}),
431 Span { beg: 0, len: 4 }
432 );
433 test_t!(ctx, storer, "AEUF", 0, re!(['a'-'z']{3,6}));
434 test_t!(
435 ctx,
436 storer,
437 "aefc",
438 0,
439 re!(['a'-'z']{3,}),
440 Span { beg: 0, len: 4 }
441 );
442 test_t!(ctx, storer, "AEUF", 0, re!(['a'-'z']{3,}));
443
444 Ok(())
445 }
446
447 fn test_chars_negative() -> Result<(), Box<dyn std::error::Error>> {
448 let mut ctx = RegexCtx::new("");
449 let mut storer = SimpleStorer::new(1);
450
451 test_t!(
452 ctx,
453 storer,
454 "aefc",
455 0,
456 re!([^b c d]),
457 Span { beg: 0, len: 1 }
458 );
459 test_t!(
460 ctx,
461 storer,
462 "aefc",
463 0,
464 re!([^b c d]?),
465 Span { beg: 0, len: 1 }
466 );
467 test_t!(
468 ctx,
469 storer,
470 "aefc",
471 0,
472 re!([^'b' 'c' 'd']),
473 Span { beg: 0, len: 1 }
474 );
475 test_t!(
476 ctx,
477 storer,
478 "aefc",
479 0,
480 re!([^'b' 'c' 'd']?),
481 Span { beg: 0, len: 1 }
482 );
483 test_t!(
484 ctx,
485 storer,
486 "daefc",
487 0,
488 re!([^b c d]?),
489 Span { beg: 0, len: 0 }
490 );
491 test_t!(
492 ctx,
493 storer,
494 "aefc",
495 0,
496 re!([^b c d]*),
497 Span { beg: 0, len: 3 }
498 );
499 test_t!(
500 ctx,
501 storer,
502 "daefc",
503 0,
504 re!([^b c d]*),
505 Span { beg: 0, len: 0 }
506 );
507 test_t!(
508 ctx,
509 storer,
510 "aefc",
511 0,
512 re!([^b c d]+),
513 Span { beg: 0, len: 3 }
514 );
515 test_t!(
516 ctx,
517 storer,
518 "aefcddd",
519 0,
520 re!([^b c d]+),
521 Span { beg: 0, len: 3 }
522 );
523 test_t!(ctx, storer, "baefcddd", 0, re!([^b c d]+));
524 test_t!(
525 ctx,
526 storer,
527 "aefh",
528 0,
529 re!([^b c d]{4}),
530 Span { beg: 0, len: 4 }
531 );
532 test_t!(
533 ctx,
534 storer,
535 "aefhcc",
536 0,
537 re!([^b c d]{4,}),
538 Span { beg: 0, len: 4 }
539 );
540 test_t!(
541 ctx,
542 storer,
543 "aefhccd",
544 0,
545 re!([^b c d]{4,7}),
546 Span { beg: 0, len: 4 }
547 );
548 test_t!(ctx, storer, "aecfhccd", 0, re!([^b c d]{4,7}));
549 Ok(())
550 }
551
552 fn test_chars() -> Result<(), Box<dyn std::error::Error>> {
553 let mut ctx = RegexCtx::new("");
554 let mut storer = SimpleStorer::new(1);
555
556 test_t!(
557 ctx,
558 storer,
559 "dabcd",
560 0,
561 re!([b c d]),
562 Span { beg: 0, len: 1 }
563 );
564 test_t!(
565 ctx,
566 storer,
567 "dabcd",
568 0,
569 re!([b c d]?),
570 Span { beg: 0, len: 1 }
571 );
572 test_t!(
573 ctx,
574 storer,
575 "edabcd",
576 0,
577 re!([b c d]?),
578 Span { beg: 0, len: 0 }
579 );
580 test_t!(
581 ctx,
582 storer,
583 "dbcd",
584 0,
585 re!([b c d]*),
586 Span { beg: 0, len: 4 }
587 );
588 test_t!(
589 ctx,
590 storer,
591 "aeuyf",
592 0,
593 re!([b c d]*),
594 Span { beg: 0, len: 0 }
595 );
596 test_t!(
597 ctx,
598 storer,
599 "dabcd",
600 0,
601 re!([b c d]+),
602 Span { beg: 0, len: 1 }
603 );
604 test_t!(
605 ctx,
606 storer,
607 "dbcdfff",
608 0,
609 re!([b c d]+),
610 Span { beg: 0, len: 4 }
611 );
612 test_t!(ctx, storer, "abcd", 0, re!([b c d]+));
613 test_t!(
614 ctx,
615 storer,
616 "dbcd",
617 0,
618 re!([b c d]{4}),
619 Span { beg: 0, len: 4 }
620 );
621 test_t!(
622 ctx,
623 storer,
624 "dbcdccc",
625 0,
626 re!([b c d]{4,}),
627 Span { beg: 0, len: 7 }
628 );
629 test_t!(
630 ctx,
631 storer,
632 "dbcdbb",
633 0,
634 re!([b c d]{4,7}),
635 Span { beg: 0, len: 6 }
636 );
637
638 test_t!(
639 ctx,
640 storer,
641 "dabcd",
642 0,
643 re!(['b' 'c' 'd']),
644 Span { beg: 0, len: 1 }
645 );
646 test_t!(
647 ctx,
648 storer,
649 "dabcd",
650 0,
651 re!(['b' 'c' 'd']?),
652 Span { beg: 0, len: 1 }
653 );
654 test_t!(
655 ctx,
656 storer,
657 "edabcd",
658 0,
659 re!(['b' 'c' 'd']?),
660 Span { beg: 0, len: 0 }
661 );
662 test_t!(
663 ctx,
664 storer,
665 "dbcd",
666 0,
667 re!(['b' 'c' 'd']*),
668 Span { beg: 0, len: 4 }
669 );
670 test_t!(
671 ctx,
672 storer,
673 "aeuyf",
674 0,
675 re!(['b' 'c' 'd']*),
676 Span { beg: 0, len: 0 }
677 );
678 test_t!(
679 ctx,
680 storer,
681 "dabcd",
682 0,
683 re!(['b' 'c' 'd']+),
684 Span { beg: 0, len: 1 }
685 );
686 test_t!(
687 ctx,
688 storer,
689 "dbcdfff",
690 0,
691 re!(['b' 'c' 'd']+),
692 Span { beg: 0, len: 4 }
693 );
694 test_t!(ctx, storer, "abcd", 0, re!(['b' 'c' 'd']+));
695 test_t!(
696 ctx,
697 storer,
698 "dbcd",
699 0,
700 re!(['b' 'c' 'd']{4}),
701 Span { beg: 0, len: 4 }
702 );
703 test_t!(
704 ctx,
705 storer,
706 "dbcdccc",
707 0,
708 re!(['b' 'c' 'd']{4,}),
709 Span { beg: 0, len: 7 }
710 );
711 test_t!(
712 ctx,
713 storer,
714 "dbcdbb",
715 0,
716 re!(['b' 'c' 'd']{4,7}),
717 Span { beg: 0, len: 6 }
718 );
719 Ok(())
720 }
721
722 fn test_char() -> Result<(), Box<dyn std::error::Error>> {
723 let mut ctx = RegexCtx::new("");
724 let mut storer = SimpleStorer::new(1);
725
726 test_t!(ctx, storer, "a", 0, re!(a), Span { beg: 0, len: 1 });
727 test_t!(ctx, storer, "a", 0, re!('a'), Span { beg: 0, len: 1 });
728 test_t!(ctx, storer, "a", 0, re!(a?), Span { beg: 0, len: 1 });
729 test_t!(ctx, storer, "a", 0, re!('a'?), Span { beg: 0, len: 1 });
730 test_t!(ctx, storer, "你", 0, re!(你), Span { beg: 0, len: 3 });
731 test_t!(ctx, storer, "你you", 0, re!('你'), Span { beg: 0, len: 3 });
732 test_t!(ctx, storer, "@", 0, re!('@'), Span { beg: 0, len: 1 });
733 test_t!(ctx, storer, "der", 0, re!(a?), Span { beg: 0, len: 0 });
734 test_t!(ctx, storer, "", 0, re!('a'?), Span { beg: 0, len: 0 });
735 test_t!(ctx, storer, "a", 0, re!(a*), Span { beg: 0, len: 1 });
736 test_t!(
737 ctx,
738 storer,
739 "aaaaaee",
740 0,
741 re!('a'*),
742 Span { beg: 0, len: 5 }
743 );
744 test_t!(ctx, storer, "cde", 0, re!(a*), Span { beg: 0, len: 0 });
745 test_t!(ctx, storer, "aaaaee", 0, re!('a'+), Span { beg: 0, len: 4 });
746 test_t!(ctx, storer, "你你你", 0, re!(你+), Span { beg: 0, len: 9 });
747 test_t!(ctx, storer, "我你你你", 0, re!(你+));
748 test_t!(
749 ctx,
750 storer,
751 "aaaaee",
752 0,
753 re!('a'{2}),
754 Span { beg: 0, len: 2 }
755 );
756 test_t!(
757 ctx,
758 storer,
759 "你你你",
760 0,
761 re!(你{2}),
762 Span { beg: 0, len: 6 }
763 );
764 test_t!(ctx, storer, "你", 0, re!(你{2}));
765 test_t!(
766 ctx,
767 storer,
768 "aaaaee",
769 0,
770 re!('a'{2,}),
771 Span { beg: 0, len: 4 }
772 );
773 test_t!(
774 ctx,
775 storer,
776 "你你你",
777 0,
778 re!(你{2,}),
779 Span { beg: 0, len: 9 }
780 );
781 test_t!(ctx, storer, "你", 0, re!(你{2,}));
782 test_t!(
783 ctx,
784 storer,
785 "aaaaee",
786 0,
787 re!('a'{2,3}),
788 Span { beg: 0, len: 3 }
789 );
790 test_t!(
791 ctx,
792 storer,
793 "你你你你你啊",
794 0,
795 re!(你{2,4}),
796 Span { beg: 0, len: 12 }
797 );
798 test_t!(ctx, storer, "你啊", 0, re!(你{2,4}));
799
800 Ok(())
801 }
802
803 fn test_space() -> Result<(), Box<dyn std::error::Error>> {
804 let mut ctx = RegexCtx::new("");
805 let mut storer = SimpleStorer::new(1);
806
807 test_t!(ctx, storer, "\tcd", 0, re!(), Span { beg: 0, len: 1 });
808 test_t!(ctx, storer, "\tdwq", 0, re!(?), Span { beg: 0, len: 1 });
809 test_t!(ctx, storer, "dwq", 0, re!(?), Span { beg: 0, len: 0 });
810 test_t!(ctx, storer, "\t\n\rdda", 0, re!(*), Span { beg: 0, len: 3 });
811 test_t!(ctx, storer, "dda", 0, re!(*), Span { beg: 0, len: 0 });
812 test_t!(ctx, storer, "\t\n\rdda", 0, re!(+), Span { beg: 0, len: 3 });
813 test_t!(ctx, storer, "\tdda", 0, re!(+), Span { beg: 0, len: 1 });
814 test_t!(ctx, storer, "dda", 0, re!(+));
815 test_t!(
816 ctx,
817 storer,
818 " \u{A0}dda",
819 0,
820 re!({ 2 }),
821 Span { beg: 0, len: 3 }
822 );
823 test_t!(ctx, storer, "\u{A0}dda", 0, re!({ 2 }));
824 test_t!(
825 ctx,
826 storer,
827 "\t\rdda",
828 0,
829 re!({2,}),
830 Span { beg: 0, len: 2 }
831 );
832 test_t!(
833 ctx,
834 storer,
835 "\t\r\u{A0}dda",
836 0,
837 re!({2,}),
838 Span { beg: 0, len: 4 }
839 );
840 test_t!(ctx, storer, "dda", 0, re!());
841 test_t!(
842 ctx,
843 storer,
844 "\t\ndda",
845 0,
846 re!({2,3}),
847 Span { beg: 0, len: 2 }
848 );
849 test_t!(
850 ctx,
851 storer,
852 "\t\r\u{A0}dda",
853 0,
854 re!({2,3}),
855 Span { beg: 0, len: 4 }
856 );
857 test_t!(
858 ctx,
859 storer,
860 "\t\r \u{A0}dda",
861 0,
862 re!({2,3}),
863 Span { beg: 0, len: 3 }
864 );
865 test_t!(ctx, storer, " dda", 0, re!({2,3}));
866
867 Ok(())
868 }
869}