@@ -70,21 +70,26 @@ predicate semBackEdge(SemSsaPhiNode phi, SemSsaVariable inp, SemSsaReadPositionP
70
70
// Conservatively assume that every edge is a back edge if we don't have dominance information.
71
71
(
72
72
phi .getBasicBlock ( ) .bbDominates ( edge .getOrigBlock ( ) ) or
73
- trimmedReachable ( phi .getBasicBlock ( ) , edge .getOrigBlock ( ) ) or
73
+ irreducibleSccEdge ( phi .getBasicBlock ( ) , edge .getOrigBlock ( ) ) or
74
74
not edge .getOrigBlock ( ) .hasDominanceInformation ( )
75
75
)
76
76
}
77
77
78
- private predicate trimmedReachable ( SemBasicBlock b1 , SemBasicBlock b2 ) {
79
- b1 = b2
80
- or
81
- exists ( SemBasicBlock mid |
82
- trimmedReachable ( b1 , mid ) and
83
- trimmedEdges ( mid , b2 )
84
- )
78
+ /**
79
+ * Holds if the edge from b1 to b2 is part of a multiple-entry cycle in an irreducible control flow
80
+ * graph.
81
+ *
82
+ * An ireducible control flow graph is one where the usual dominance-based back edge detection does
83
+ * not work, because there is a cycle with multiple entry points, meaning there are
84
+ * mutually-reachable basic blocks where neither dominates the other. For such a graph, we first
85
+ * all detectable back-edges using the normal condition that the predecessor block is dominated by
86
+ * the successor block, then mark all edges in a cycle in the resulting graph as back edges.
87
+ */
88
+ private predicate irreducibleSccEdge ( SemBasicBlock b1 , SemBasicBlock b2 ) {
89
+ trimmedEdge ( b1 , b2 ) and trimmedEdge + ( b2 , b1 )
85
90
}
86
91
87
- private predicate trimmedEdges ( SemBasicBlock pred , SemBasicBlock succ ) {
92
+ private predicate trimmedEdge ( SemBasicBlock pred , SemBasicBlock succ ) {
88
93
pred .getASuccessor ( ) = succ and
89
94
not succ .bbDominates ( pred )
90
95
}
0 commit comments