diff options
author | Zdenek Dvorak <rakdver@atrey.karlin.mff.cuni.cz> | 2004-02-17 20:51:15 +0100 |
---|---|---|
committer | Jeff Law <law@gcc.gnu.org> | 2004-02-17 12:51:15 -0700 |
commit | 017b3258fa075ff64facea88e200ee6b88bcd602 (patch) | |
tree | 8a82c181579a38d2a696ed2860af7e1f75ec4e38 /gcc/cfghooks.c | |
parent | e70e9b0faac98b2f123c0cd1c20da1d54e986738 (diff) | |
download | gcc-017b3258fa075ff64facea88e200ee6b88bcd602.zip gcc-017b3258fa075ff64facea88e200ee6b88bcd602.tar.gz gcc-017b3258fa075ff64facea88e200ee6b88bcd602.tar.bz2 |
* cfghooks.c (split_edge): Speed up updating of dominators.
From-SVN: r77973
Diffstat (limited to 'gcc/cfghooks.c')
-rw-r--r-- | gcc/cfghooks.c | 31 |
1 files changed, 28 insertions, 3 deletions
diff --git a/gcc/cfghooks.c b/gcc/cfghooks.c index ab47181..e256124 100644 --- a/gcc/cfghooks.c +++ b/gcc/cfghooks.c @@ -373,6 +373,7 @@ split_edge (edge e) basic_block ret; gcov_type count = e->count; int freq = EDGE_FREQUENCY (e); + edge f; if (!cfg_hooks->split_edge) internal_error ("%s does not support split_edge.", cfg_hooks->name); @@ -387,9 +388,33 @@ split_edge (edge e) set_immediate_dominator (CDI_DOMINATORS, ret, ret->pred->src); if (dom_computed[CDI_DOMINATORS] >= DOM_NO_FAST_QUERY) - set_immediate_dominator (CDI_DOMINATORS, ret->succ->dest, - recount_dominator (CDI_DOMINATORS, - ret->succ->dest)); + { + /* There are two cases: + + If the immediate dominator of e->dest is not e->src, it + remains unchanged. + + If immediate dominator of e->dest is e->src, it may become + ret, provided that all other predecessors of e->dest are + dominated by e->dest. */ + + if (get_immediate_dominator (CDI_DOMINATORS, ret->succ->dest) + == ret->pred->src) + { + for (f = ret->succ->dest->pred; f; f = f->pred_next) + { + if (f == ret->succ) + continue; + + if (!dominated_by_p (CDI_DOMINATORS, f->src, + ret->succ->dest)) + break; + } + + if (!f) + set_immediate_dominator (CDI_DOMINATORS, ret->succ->dest, ret); + } + }; return ret; } |