@@ -28,13 +28,20 @@ static void zend_mark_reachable(zend_op *opcodes, zend_cfg *cfg, zend_basic_bloc
28
28
{
29
29
zend_basic_block * blocks = cfg -> blocks ;
30
30
31
- while (1 ) {
31
+ zend_worklist work ;
32
+ ALLOCA_FLAG (list_use_heap )
33
+ ZEND_WORKLIST_ALLOCA (& work , cfg -> blocks_count , list_use_heap );
34
+
35
+ zend_worklist_push (& work , b - cfg -> blocks );
36
+
37
+ while (zend_worklist_len (& work )) {
32
38
int i ;
39
+ b = cfg -> blocks + zend_worklist_pop (& work );
33
40
34
41
b -> flags |= ZEND_BB_REACHABLE ;
35
42
if (b -> successors_count == 0 ) {
36
43
b -> flags |= ZEND_BB_EXIT ;
37
- return ;
44
+ continue ;
38
45
}
39
46
40
47
for (i = 0 ; i < b -> successors_count ; i ++ ) {
@@ -86,22 +93,14 @@ static void zend_mark_reachable(zend_op *opcodes, zend_cfg *cfg, zend_basic_bloc
86
93
succ -> flags |= ZEND_BB_FOLLOW ;
87
94
}
88
95
89
- if (i == b -> successors_count - 1 ) {
90
- /* Tail call optimization */
91
- if (succ -> flags & ZEND_BB_REACHABLE ) {
92
- return ;
93
- }
94
-
95
- b = succ ;
96
- break ;
97
- } else {
98
- /* Recursively check reachability */
99
- if (!(succ -> flags & ZEND_BB_REACHABLE )) {
100
- zend_mark_reachable (opcodes , cfg , succ );
101
- }
96
+ /* Check reachability of successor */
97
+ if (!(succ -> flags & ZEND_BB_REACHABLE )) {
98
+ zend_worklist_push (& work , succ - cfg -> blocks );
102
99
}
103
100
}
104
101
}
102
+
103
+ ZEND_WORKLIST_FREE_ALLOCA (& work , list_use_heap );
105
104
}
106
105
/* }}} */
107
106
0 commit comments