@@ -147,23 +147,15 @@ class BlockExprTree extends StandardPostOrderTree, BlockExpr {
147
147
override predicate propagatesAbnormal ( AstNode child ) { child = this .getChildNode ( _) }
148
148
}
149
149
150
- class BreakExprTree extends PostOrderTree , BreakExpr {
151
- override predicate propagatesAbnormal ( AstNode child ) { child = this .getExpr ( ) }
152
-
153
- override predicate first ( AstNode node ) {
154
- first ( this .getExpr ( ) , node )
155
- or
156
- not this .hasExpr ( ) and node = this
157
- }
150
+ class BreakExprTree extends StandardPostOrderTree , BreakExpr {
151
+ override AstNode getChildNode ( int i ) { i = 0 and result = this .getExpr ( ) }
158
152
159
153
override predicate last ( AstNode last , Completion c ) { none ( ) }
160
154
161
155
override predicate succ ( AstNode pred , AstNode succ , Completion c ) {
162
- last ( super .getExpr ( ) , pred , c ) and succ = this
156
+ super .succ ( pred , succ , c )
163
157
or
164
- pred = this and
165
- c .isValidFor ( pred ) and
166
- succ = this .getTarget ( )
158
+ pred = this and c .isValidFor ( pred ) and succ = this .getTarget ( )
167
159
}
168
160
}
169
161
@@ -325,7 +317,7 @@ class LetStmtTree extends PreOrderTree, LetStmt {
325
317
not this .hasInitializer ( )
326
318
or
327
319
// Edge from end of initializer to pattern.
328
- last ( this .getInitializer ( ) , pred , c ) and first ( this .getPat ( ) , succ )
320
+ last ( this .getInitializer ( ) , pred , c ) and first ( this .getPat ( ) , succ ) and completionIsNormal ( c )
329
321
or
330
322
// Edge from failed pattern to `else` branch.
331
323
last ( this .getPat ( ) , pred , c ) and
@@ -502,14 +494,21 @@ class MatchExprTree extends PostOrderTree instanceof MatchExpr {
502
494
override predicate first ( AstNode node ) { first ( super .getExpr ( ) , node ) }
503
495
504
496
override predicate succ ( AstNode pred , AstNode succ , Completion c ) {
505
- // Edge from the scrutinee to the first arm.
497
+ // Edge from the scrutinee to the first arm or to the match expression if no arms .
506
498
last ( super .getExpr ( ) , pred , c ) and
507
- first ( super .getArm ( 0 ) .getPat ( ) , succ ) and
499
+ (
500
+ first ( super .getArm ( 0 ) .getPat ( ) , succ )
501
+ or
502
+ not exists ( super .getArm ( 0 ) ) and succ = this
503
+ ) and
508
504
completionIsNormal ( c )
509
505
or
510
- // Edge from a failed match/ guard in one arm to the beginning of the next arm.
506
+ // Edge from a failed pattern or guard in one arm to the beginning of the next arm.
511
507
exists ( int i |
512
- last ( super .getArm ( i ) , pred , c ) and
508
+ (
509
+ last ( super .getArm ( i ) .getPat ( ) , pred , c ) or
510
+ last ( super .getArm ( i ) .getGuard ( ) .getCondition ( ) , pred , c )
511
+ ) and
513
512
first ( super .getArm ( i + 1 ) , succ ) and
514
513
c .( ConditionalCompletion ) .failed ( )
515
514
)
@@ -521,10 +520,7 @@ class MatchExprTree extends PostOrderTree instanceof MatchExpr {
521
520
522
521
class MethodCallExprTree extends StandardPostOrderTree , MethodCallExpr {
523
522
override AstNode getChildNode ( int i ) {
524
- i = 0 and
525
- result = this .getReceiver ( )
526
- or
527
- result = this .getArgList ( ) .getArg ( i + 1 )
523
+ if i = 0 then result = this .getReceiver ( ) else result = this .getArgList ( ) .getArg ( i - 1 )
528
524
}
529
525
}
530
526
@@ -605,89 +601,48 @@ class YeetExprTree extends StandardPostOrderTree instanceof YeetExpr {
605
601
* `OrPat`s and `IdentPat`s.
606
602
*/
607
603
module PatternTrees {
608
- abstract class PreOrderPatTree extends PreOrderTree {
604
+ abstract class StandardPatTree extends StandardTree {
609
605
abstract Pat getPat ( int i ) ;
610
606
611
- private Pat getPatRanked ( int i ) {
607
+ Pat getPatRanked ( int i ) {
612
608
result = rank [ i + 1 ] ( Pat pat , int j | pat = this .getPat ( j ) | pat order by j )
613
609
}
614
610
615
- override predicate propagatesAbnormal ( AstNode child ) { child = this .getPatRanked ( _) }
611
+ override AstNode getChildNode ( int i ) { result = this .getPat ( i ) }
612
+ }
616
613
614
+ abstract class PreOrderPatTree extends StandardPatTree , StandardPreOrderTree {
617
615
override predicate succ ( AstNode pred , AstNode succ , Completion c ) {
618
- pred = this and
619
- completionIsValidFor ( c , this ) and
620
616
c .( MatchCompletion ) .succeeded ( ) and
621
- first ( this .getPatRanked ( 0 ) , succ )
622
- or
623
- exists ( int i | last ( this .getPatRanked ( i ) , pred , c ) |
624
- // Edge from successful pattern to the next
625
- c .( MatchCompletion ) .succeeded ( ) and
626
- first ( this .getPatRanked ( i + 1 ) , succ )
617
+ (
618
+ StandardPatTree .super .succ ( pred , succ , c )
619
+ or
620
+ pred = this and first ( this .getFirstChildNode ( ) , succ ) and completionIsValidFor ( c , this )
627
621
)
628
622
}
629
623
630
624
override predicate last ( AstNode node , Completion c ) {
631
- node = this and
632
- completionIsValidFor ( c , this ) and
633
- c .( MatchCompletion ) .failed ( )
625
+ super .last ( node , c )
634
626
or
635
- exists ( int i | last ( this .getPatRanked ( i ) , node , c ) |
636
- c .( MatchCompletion ) .failed ( )
637
- or
638
- not exists ( this .getPatRanked ( i + 1 ) ) and
639
- completionIsNormal ( c )
640
- )
627
+ c .( MatchCompletion ) .failed ( ) and
628
+ completionIsValidFor ( c , this ) and
629
+ ( node = this or last ( this .getPatRanked ( _) , node , c ) )
641
630
}
642
631
}
643
632
644
- abstract class PostOrderPatTree extends PostOrderTree {
645
- abstract Pat getPat ( int i ) ;
646
-
647
- private Pat getPatRanked ( int i ) {
648
- result = rank [ i + 1 ] ( Pat pat , int j | pat = this .getPat ( j ) | pat order by j )
649
- }
650
-
651
- override predicate propagatesAbnormal ( AstNode child ) { child = this .getPatRanked ( _) }
652
-
653
- override predicate first ( AstNode node ) {
654
- first ( this .getPat ( 0 ) , node )
655
- or
656
- not exists ( this .getPat ( _) ) and
657
- node = this
658
- }
659
-
660
- override predicate succ ( AstNode pred , AstNode succ , Completion c ) {
661
- exists ( int i | last ( this .getPat ( i ) , pred , c ) |
662
- // Edge from unsuccessful pattern to the next
663
- c .( MatchCompletion ) .failed ( ) and
664
- first ( this .getPat ( i + 1 ) , succ )
665
- or
666
- // Edge from successful pattern to this
667
- c .( MatchCompletion ) .succeeded ( ) and
668
- succ = this
669
- or
670
- // Edge from last pattern to this
671
- not exists ( this .getPat ( i + 1 ) ) and
672
- succ = this and
673
- completionIsNormal ( c )
674
- )
675
- }
676
- }
633
+ abstract class PostOrderPatTree extends StandardPatTree , StandardPostOrderTree { }
677
634
678
635
class IdentPatTree extends PostOrderPatTree , IdentPat {
679
636
override Pat getPat ( int i ) { i = 0 and result = this .getPat ( ) }
680
637
681
638
override predicate last ( AstNode node , Completion c ) {
682
639
super .last ( node , c )
683
640
or
684
- last ( this .getPat ( ) , node , c ) and
685
- c .( MatchCompletion ) .failed ( )
641
+ last ( this .getPat ( ) , node , c ) and c .( MatchCompletion ) .failed ( )
686
642
}
687
643
688
644
override predicate succ ( AstNode pred , AstNode succ , Completion c ) {
689
- super .succ ( pred , succ , c ) and
690
- not ( succ = this and c .( MatchCompletion ) .failed ( ) )
645
+ super .succ ( pred , succ , c ) and c .( MatchCompletion ) .succeeded ( )
691
646
}
692
647
}
693
648
@@ -705,6 +660,14 @@ module PatternTrees {
705
660
706
661
class OrPatTree extends PostOrderPatTree instanceof OrPat {
707
662
override Pat getPat ( int i ) { result = OrPat .super .getPat ( i ) }
663
+
664
+ override predicate succ ( AstNode pred , AstNode succ , Completion c ) {
665
+ // Failed patterns advance normally between children
666
+ c .( MatchCompletion ) .failed ( ) and super .succ ( pred , succ , c )
667
+ or
668
+ // Successful pattern step to this
669
+ c .( MatchCompletion ) .succeeded ( ) and succ = this and last ( this .getPat ( _) , pred , c )
670
+ }
708
671
}
709
672
710
673
class ParenPatTree extends ControlFlowTree , ParenPat {
0 commit comments