Jeff Law wrote: > I'm a bit worried about compile-time impacts of the all the > recursion
I will also restrict the recursion to the loop in which we look for the FSM thread, like this: diff --git a/gcc/tree-ssa-threadedge.c b/gcc/tree-ssa-threadedge.c index a6fb361..9a153bb 100644 --- a/gcc/tree-ssa-threadedge.c +++ b/gcc/tree-ssa-threadedge.c @@ -959,13 +959,17 @@ thread_around_empty_blocks (edge taken_edge, /* Return true if the CFG contains at least one path from START_BB to END_BB. When a path is found, record in PATH the blocks from END_BB to START_BB. - VISITED_BBS is used to make sure we don't fall into an infinite loop. */ + VISITED_BBS is used to make sure we don't fall into an infinite loop. Bound + the recursion to basic blocks belonging to LOOP. */ static bool fsm_find_thread_path (basic_block start_bb, basic_block end_bb, vec<basic_block, va_gc> *&path, - hash_set<basic_block> *visited_bbs, int n_insns) + hash_set<basic_block> *visited_bbs, loop_p loop) { + if (loop != start_bb->loop_father) + return false; + if (start_bb == end_bb) { vec_safe_push (path, start_bb); @@ -977,7 +981,7 @@ fsm_find_thread_path (basic_block start_bb, basic_block end_bb, edge e; edge_iterator ei; FOR_EACH_EDGE (e, ei, start_bb->succs) - if (fsm_find_thread_path (e->dest, end_bb, path, visited_bbs, n_insns)) + if (fsm_find_thread_path (e->dest, end_bb, path, visited_bbs, loop)) { vec_safe_push (path, start_bb); return true; @@ -1035,7 +1039,8 @@ fsm_find_control_statement_thread_paths (tree expr, { hash_set<basic_block> *visited_bbs = new hash_set<basic_block>; - if (fsm_find_thread_path (var_bb, e->src, next_path, visited_bbs, 0)) + if (fsm_find_thread_path (var_bb, e->src, next_path, visited_bbs, + e->src->loop_father)) ++e_count; delete visited_bbs;