https://gcc.gnu.org/bugzilla/show_bug.cgi?id=93199
--- Comment #12 from Richard Biener <rguenth at gcc dot gnu.org> --- (In reply to Richard Biener from comment #11) > - 77.83% 0.45% 16118 cc1plus cc1plus [.] > (anonymous namespace)::pass_cleanup_eh::execute ▒ > - 77.38% (anonymous namespace)::pass_cleanup_eh::execute > - 77.29% cleanup_empty_eh_merge_phis > - 44.55% redirect_eh_edge_1 > 30.45% last_stmt > > + 4.01% lookup_stmt_eh_lp_fn > > + 2.96% remove_stmt_from_eh_lp_fn > > 2.77% gimple_block_label > > 0.55% get_eh_landing_pad_from_number > + 16.68% add_stmt_to_eh_lp_fn > 5.34% find_edge > + 4.58% redirect_edge_succ > 0.59% gimple_execute_on_growing_pred > > that last_stmt figure looks odd tho (I blame perf for this). This is on > the original redhat bugzilla testcase btw, will check your reduced one. Apart from structural quadraticnesses involving edges the main hog seems to be the quadratic updating of the RESX stmt moving here: static void redirect_eh_edge_1 (edge edge_in, basic_block new_bb, bool change_region) { ... /* Maybe move the throwing statement to the new region. */ if (old_lp != new_lp) { remove_stmt_from_eh_lp (throw_stmt); add_stmt_to_eh_lp (throw_stmt, new_lp->index); } which boils down to the very same issue. We're also getting a very big in-degree for the EH redirection probably because we're walking the EH LP array when optimizing empty EH. Thus code like /* Notice when we redirect the last EH edge away from OLD_BB. */ FOR_EACH_EDGE (e, ei, old_bb->preds) if (e != edge_in && (e->flags & EDGE_EH)) break; ends up expensive as well (we will move all EH edges anyway so the above at least could be avoided with some care). Not to mention FOR_EACH_EDGE (e, ei, old_bb->preds) if (find_edge (e->src, new_bb)) return false; which we can short-cut when new_bb has a single predecessor. So I have some micro-optimizing things here (only). But I wonder whether walking the landing pads in some better order in cleanup_all_empty_eh would fix things. Simply walking the array in reverse already helps a tremedous amount! tree eh : 4.75 ( 35%) 0.01 ( 3%) 4.75 ( 34%) 16911 kB ( 9%) vs. tree eh : 182.21 ( 95%) 0.84 ( 65%) 183.07 ( 95%) 4653260 kB ( 97%) on your testcase and tree eh : 29.56 ( 30%) 0.05 ( 1%) 29.60 ( 28%) 246315 kB ( 8%) vs. tree eh : 626.00 ( 89%) 5.75 ( 45%) 631.88 ( 88%)38736930 kB ( 93%) on the redhat bugzilla one.