@@ -227,6 +227,8 @@ impl Hir {
227
227
info. set_any_anchored_start ( false ) ;
228
228
info. set_any_anchored_end ( false ) ;
229
229
info. set_match_empty ( true ) ;
230
+ info. set_literal ( true ) ;
231
+ info. set_alternation_literal ( true ) ;
230
232
Hir {
231
233
kind : HirKind :: Empty ,
232
234
info : info,
@@ -253,6 +255,8 @@ impl Hir {
253
255
info. set_any_anchored_start ( false ) ;
254
256
info. set_any_anchored_end ( false ) ;
255
257
info. set_match_empty ( false ) ;
258
+ info. set_literal ( true ) ;
259
+ info. set_alternation_literal ( true ) ;
256
260
Hir {
257
261
kind : HirKind :: Literal ( lit) ,
258
262
info : info,
@@ -271,6 +275,8 @@ impl Hir {
271
275
info. set_any_anchored_start ( false ) ;
272
276
info. set_any_anchored_end ( false ) ;
273
277
info. set_match_empty ( false ) ;
278
+ info. set_literal ( false ) ;
279
+ info. set_alternation_literal ( false ) ;
274
280
Hir {
275
281
kind : HirKind :: Class ( class) ,
276
282
info : info,
@@ -289,6 +295,8 @@ impl Hir {
289
295
info. set_any_anchored_start ( false ) ;
290
296
info. set_any_anchored_end ( false ) ;
291
297
info. set_match_empty ( true ) ;
298
+ info. set_literal ( false ) ;
299
+ info. set_alternation_literal ( false ) ;
292
300
if let Anchor :: StartText = anchor {
293
301
info. set_anchored_start ( true ) ;
294
302
info. set_line_anchored_start ( true ) ;
@@ -322,6 +330,8 @@ impl Hir {
322
330
info. set_line_anchored_end ( false ) ;
323
331
info. set_any_anchored_start ( false ) ;
324
332
info. set_any_anchored_end ( false ) ;
333
+ info. set_literal ( false ) ;
334
+ info. set_alternation_literal ( false ) ;
325
335
// A negated word boundary matches the empty string, but a normal
326
336
// word boundary does not!
327
337
info. set_match_empty ( word_boundary. is_negated ( ) ) ;
@@ -357,6 +367,8 @@ impl Hir {
357
367
info. set_any_anchored_start ( rep. hir . is_any_anchored_start ( ) ) ;
358
368
info. set_any_anchored_end ( rep. hir . is_any_anchored_end ( ) ) ;
359
369
info. set_match_empty ( rep. is_match_empty ( ) || rep. hir . is_match_empty ( ) ) ;
370
+ info. set_literal ( false ) ;
371
+ info. set_alternation_literal ( false ) ;
360
372
Hir {
361
373
kind : HirKind :: Repetition ( rep) ,
362
374
info : info,
@@ -375,6 +387,8 @@ impl Hir {
375
387
info. set_any_anchored_start ( group. hir . is_any_anchored_start ( ) ) ;
376
388
info. set_any_anchored_end ( group. hir . is_any_anchored_end ( ) ) ;
377
389
info. set_match_empty ( group. hir . is_match_empty ( ) ) ;
390
+ info. set_literal ( false ) ;
391
+ info. set_alternation_literal ( false ) ;
378
392
Hir {
379
393
kind : HirKind :: Group ( group) ,
380
394
info : info,
@@ -395,6 +409,8 @@ impl Hir {
395
409
info. set_any_anchored_start ( false ) ;
396
410
info. set_any_anchored_end ( false ) ;
397
411
info. set_match_empty ( true ) ;
412
+ info. set_literal ( true ) ;
413
+ info. set_alternation_literal ( true ) ;
398
414
399
415
// Some attributes require analyzing all sub-expressions.
400
416
for e in & exprs {
@@ -416,6 +432,14 @@ impl Hir {
416
432
417
433
let x = info. is_match_empty ( ) && e. is_match_empty ( ) ;
418
434
info. set_match_empty ( x) ;
435
+
436
+ let x = info. is_literal ( ) && e. is_literal ( ) ;
437
+ info. set_literal ( x) ;
438
+
439
+ let x =
440
+ info. is_alternation_literal ( )
441
+ && e. is_alternation_literal ( ) ;
442
+ info. set_alternation_literal ( x) ;
419
443
}
420
444
// Anchored attributes require something slightly more
421
445
// sophisticated. Normally, WLOG, to determine whether an
@@ -488,6 +512,8 @@ impl Hir {
488
512
info. set_any_anchored_start ( false ) ;
489
513
info. set_any_anchored_end ( false ) ;
490
514
info. set_match_empty ( false ) ;
515
+ info. set_literal ( false ) ;
516
+ info. set_alternation_literal ( true ) ;
491
517
492
518
// Some attributes require analyzing all sub-expressions.
493
519
for e in & exprs {
@@ -523,6 +549,11 @@ impl Hir {
523
549
524
550
let x = info. is_match_empty ( ) || e. is_match_empty ( ) ;
525
551
info. set_match_empty ( x) ;
552
+
553
+ let x =
554
+ info. is_alternation_literal ( )
555
+ && e. is_literal ( ) ;
556
+ info. set_alternation_literal ( x) ;
526
557
}
527
558
Hir {
528
559
kind : HirKind :: Alternation ( exprs) ,
@@ -655,6 +686,28 @@ impl Hir {
655
686
pub fn is_match_empty ( & self ) -> bool {
656
687
self . info . is_match_empty ( )
657
688
}
689
+
690
+ /// Return true if and only if this HIR is a simple literal. This is only
691
+ /// true when this HIR expression is either itself a `Literal` or a
692
+ /// concatenation of only `Literal`s.
693
+ ///
694
+ /// For example, `f` and `foo` are literals, but `f+`, `(foo)`, `foo()`
695
+ /// are not (even though that contain sub-expressions that are literals).
696
+ pub fn is_literal ( & self ) -> bool {
697
+ self . info . is_literal ( )
698
+ }
699
+
700
+ /// Return true if and only if this HIR is either a simple literal or an
701
+ /// alternation of simple literals. This is only
702
+ /// true when this HIR expression is either itself a `Literal` or a
703
+ /// concatenation of only `Literal`s or an alternation of only `Literal`s.
704
+ ///
705
+ /// For example, `f`, `foo`, `a|b|c`, and `foo|bar|baz` are alternaiton
706
+ /// literals, but `f+`, `(foo)`, `foo()`
707
+ /// are not (even though that contain sub-expressions that are literals).
708
+ pub fn is_alternation_literal ( & self ) -> bool {
709
+ self . info . is_alternation_literal ( )
710
+ }
658
711
}
659
712
660
713
impl HirKind {
@@ -1415,6 +1468,8 @@ impl HirInfo {
1415
1468
define_bool ! ( 6 , is_any_anchored_start, set_any_anchored_start) ;
1416
1469
define_bool ! ( 7 , is_any_anchored_end, set_any_anchored_end) ;
1417
1470
define_bool ! ( 8 , is_match_empty, set_match_empty) ;
1471
+ define_bool ! ( 9 , is_literal, set_literal) ;
1472
+ define_bool ! ( 10 , is_alternation_literal, set_alternation_literal) ;
1418
1473
}
1419
1474
1420
1475
#[ cfg( test) ]
0 commit comments