summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--gcc/ChangeLog19
-rw-r--r--gcc/cfgloop.c7
-rw-r--r--gcc/ira-build.c24
-rw-r--r--gcc/ira-emit.c2
-rw-r--r--gcc/ira-int.h3
-rw-r--r--gcc/ira.c23
6 files changed, 44 insertions, 34 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 575f74a19a1..787efb718a9 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,5 +1,24 @@
2013-02-08 Richard Biener <rguenther@suse.de>
+ * cfgloop.c (verify_loop_structure): Properly handle
+ a loop exiting to another loop header.
+ * ira-int.h (ira_loops): Remove.
+ * ira.c (ira_loops): Remove.
+ (ira): Use loop_optimizer_init and loop_optimizer_finalize.
+ (do_reload): Use loop_optimizer_finalize.
+ * ira-build.c (create_loop_tree_nodes): Use get_loops and
+ number_of_loops to access the loop tree.
+ (more_one_region_p): Likewise.
+ (finish_loop_tree_nodes): Likewise.
+ (rebuild_regno_allocno_maps): Likewise.
+ (mark_loops_for_removal): Likewise.
+ (mark_all_loops_for_removal): Likewise.
+ (remove_unnecessary_regions): Likewise.
+ (ira_build): Likewise.
+ * ira-emit.c (setup_entered_from_non_parent_p): Likewise.
+
+2013-02-08 Richard Biener <rguenther@suse.de>
+
* Makefile.in (tree-tailcall.o): Add $(CFGLOOP_H) dependency.
* ipa-pure-const.c (analyze_function): Avoid calling
mark_irreducible_loops twice.
diff --git a/gcc/cfgloop.c b/gcc/cfgloop.c
index 9806090f1a9..3c8df30cd72 100644
--- a/gcc/cfgloop.c
+++ b/gcc/cfgloop.c
@@ -1542,7 +1542,12 @@ verify_loop_structure (void)
eloops++;
for (loop = bb->loop_father;
- loop != e->dest->loop_father;
+ loop != e->dest->loop_father
+ /* When a loop exit is also an entry edge which
+ can happen when avoiding CFG manipulations
+ then the last loop exited is the outer loop
+ of the loop entered. */
+ && loop != loop_outer (e->dest->loop_father);
loop = loop_outer (loop))
{
eloops--;
diff --git a/gcc/ira-build.c b/gcc/ira-build.c
index da19b590141..dd66091a335 100644
--- a/gcc/ira-build.c
+++ b/gcc/ira-build.c
@@ -149,10 +149,10 @@ create_loop_tree_nodes (void)
}
ira_loop_nodes = ((struct ira_loop_tree_node *)
ira_allocate (sizeof (struct ira_loop_tree_node)
- * vec_safe_length (ira_loops.larray)));
- FOR_EACH_VEC_SAFE_ELT (ira_loops.larray, i, loop)
+ * number_of_loops ()));
+ FOR_EACH_VEC_SAFE_ELT (get_loops (), i, loop)
{
- if (loop != ira_loops.tree_root)
+ if (loop_outer (loop) != NULL)
{
ira_loop_nodes[i].regno_allocno_map = NULL;
skip_p = false;
@@ -189,7 +189,7 @@ more_one_region_p (void)
loop_p loop;
if (current_loops != NULL)
- FOR_EACH_VEC_SAFE_ELT (ira_loops.larray, i, loop)
+ FOR_EACH_VEC_SAFE_ELT (get_loops (), i, loop)
if (ira_loop_nodes[i].regno_allocno_map != NULL
&& ira_loop_tree_root != &ira_loop_nodes[i])
return true;
@@ -222,7 +222,7 @@ finish_loop_tree_nodes (void)
if (current_loops == NULL)
finish_loop_tree_node (&ira_loop_nodes[0]);
else
- FOR_EACH_VEC_SAFE_ELT (ira_loops.larray, i, loop)
+ FOR_EACH_VEC_SAFE_ELT (get_loops (), i, loop)
finish_loop_tree_node (&ira_loop_nodes[i]);
ira_free (ira_loop_nodes);
for (i = 0; i < (unsigned int) last_basic_block_before_change; i++)
@@ -378,7 +378,7 @@ rebuild_regno_allocno_maps (void)
ira_assert (current_loops != NULL);
max_regno = max_reg_num ();
- FOR_EACH_VEC_SAFE_ELT (ira_loops.larray, l, loop)
+ FOR_EACH_VEC_SAFE_ELT (get_loops (), l, loop)
if (ira_loop_nodes[l].regno_allocno_map != NULL)
{
ira_free (ira_loop_nodes[l].regno_allocno_map);
@@ -2021,8 +2021,8 @@ mark_loops_for_removal (void)
ira_assert (current_loops != NULL);
sorted_loops
= (ira_loop_tree_node_t *) ira_allocate (sizeof (ira_loop_tree_node_t)
- * vec_safe_length (ira_loops.larray));
- for (n = i = 0; vec_safe_iterate (ira_loops.larray, i, &loop); i++)
+ * number_of_loops ());
+ for (n = i = 0; vec_safe_iterate (get_loops (), i, &loop); i++)
if (ira_loop_nodes[i].regno_allocno_map != NULL)
{
if (ira_loop_nodes[i].parent == NULL)
@@ -2066,7 +2066,7 @@ mark_all_loops_for_removal (void)
loop_p loop;
ira_assert (current_loops != NULL);
- FOR_EACH_VEC_SAFE_ELT (ira_loops.larray, i, loop)
+ FOR_EACH_VEC_SAFE_ELT (get_loops (), i, loop)
if (ira_loop_nodes[i].regno_allocno_map != NULL)
{
if (ira_loop_nodes[i].parent == NULL)
@@ -2376,8 +2376,8 @@ remove_unnecessary_regions (bool all_p)
mark_all_loops_for_removal ();
else
mark_loops_for_removal ();
- children_vec.create(last_basic_block + vec_safe_length(ira_loops.larray));
- removed_loop_vec.create(last_basic_block + vec_safe_length(ira_loops.larray));
+ children_vec.create(last_basic_block + number_of_loops ());
+ removed_loop_vec.create(last_basic_block + number_of_loops ());
remove_uneccesary_loop_nodes_from_loop_tree (ira_loop_tree_root);
children_vec.release ();
if (all_p)
@@ -3258,7 +3258,7 @@ ira_build (void)
}
}
fprintf (ira_dump_file, " regions=%d, blocks=%d, points=%d\n",
- current_loops == NULL ? 1 : vec_safe_length (ira_loops.larray),
+ current_loops == NULL ? 1 : number_of_loops (),
n_basic_blocks, ira_max_point);
fprintf (ira_dump_file,
" allocnos=%d (big %d), copies=%d, conflicts=%d, ranges=%d\n",
diff --git a/gcc/ira-emit.c b/gcc/ira-emit.c
index 661336050fc..c18391fc3e5 100644
--- a/gcc/ira-emit.c
+++ b/gcc/ira-emit.c
@@ -434,7 +434,7 @@ setup_entered_from_non_parent_p (void)
loop_p loop;
ira_assert (current_loops != NULL);
- FOR_EACH_VEC_SAFE_ELT (ira_loops.larray, i, loop)
+ FOR_EACH_VEC_SAFE_ELT (get_loops (), i, loop)
if (ira_loop_nodes[i].regno_allocno_map != NULL)
ira_loop_nodes[i].entered_from_non_parent_p
= entered_from_non_parent_p (&ira_loop_nodes[i]);
diff --git a/gcc/ira-int.h b/gcc/ira-int.h
index df64d3f12c0..096f33048e3 100644
--- a/gcc/ira-int.h
+++ b/gcc/ira-int.h
@@ -47,9 +47,6 @@ along with GCC; see the file COPYING3. If not see
? REG_FREQ_MAX : (freq * REG_FREQ_MAX / BB_FREQ_MAX) \
? (freq * REG_FREQ_MAX / BB_FREQ_MAX) : 1)
-/* All natural loops. */
-extern struct loops ira_loops;
-
/* A modified value of flag `-fira-verbose' used internally. */
extern int internal_flag_ira_verbose;
diff --git a/gcc/ira.c b/gcc/ira.c
index 2da7747e41a..f1ad9ecf76e 100644
--- a/gcc/ira.c
+++ b/gcc/ira.c
@@ -4338,9 +4338,6 @@ allocate_initial_values (void)
function. */
bool ira_use_lra_p;
-/* All natural loops. */
-struct loops ira_loops;
-
/* True if we have allocno conflicts. It is false for non-optimized
mode or when the conflict table is too big. */
bool ira_conflicts_p;
@@ -4464,11 +4461,7 @@ ira (FILE *f)
ira_assert (current_loops == NULL);
if (flag_ira_region == IRA_REGION_ALL || flag_ira_region == IRA_REGION_MIXED)
- {
- flow_loops_find (&ira_loops);
- current_loops = &ira_loops;
- record_loop_exits ();
- }
+ loop_optimizer_init (AVOID_CFG_MODIFICATIONS | LOOPS_HAVE_RECORDED_EXITS);
if (internal_flag_ira_verbose > 0 && ira_dump_file != NULL)
fprintf (ira_dump_file, "Building IRA IR\n");
@@ -4526,11 +4519,9 @@ ira (FILE *f)
/* ??? Rebuild the loop tree, but why? Does the loop tree
change if new insns were generated? Can that be handled
by updating the loop tree incrementally? */
- release_recorded_exits ();
- flow_loops_free (&ira_loops);
- flow_loops_find (&ira_loops);
- current_loops = &ira_loops;
- record_loop_exits ();
+ loop_optimizer_finalize ();
+ loop_optimizer_init (AVOID_CFG_MODIFICATIONS
+ | LOOPS_HAVE_RECORDED_EXITS);
if (! ira_use_lra_p)
{
@@ -4607,8 +4598,7 @@ do_reload (void)
{
if (current_loops != NULL)
{
- release_recorded_exits ();
- flow_loops_free (&ira_loops);
+ loop_optimizer_finalize ();
free_dominance_info (CDI_DOMINATORS);
}
FOR_ALL_BB (bb)
@@ -4657,8 +4647,7 @@ do_reload (void)
ira_destroy ();
if (current_loops != NULL)
{
- release_recorded_exits ();
- flow_loops_free (&ira_loops);
+ loop_optimizer_finalize ();
free_dominance_info (CDI_DOMINATORS);
}
FOR_ALL_BB (bb)