aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorSteven Bosscher <steven@gcc.gnu.org>2012-07-09 18:53:35 +0000
committerSteven Bosscher <steven@gcc.gnu.org>2012-07-09 18:53:35 +0000
commit238065a73bd2bab6c3eb69e6d43cd8115a5b4245 (patch)
treed7f84fe48d87db0df890f2f77c86736581a54e5d /gcc
parent06e3e32bcd55600300f4a393a77bb582ff68cdf9 (diff)
downloadgcc-238065a73bd2bab6c3eb69e6d43cd8115a5b4245.zip
gcc-238065a73bd2bab6c3eb69e6d43cd8115a5b4245.tar.gz
gcc-238065a73bd2bab6c3eb69e6d43cd8115a5b4245.tar.bz2
re PR middle-end/53887 (ICE in hoist_edge_and_branch_if_true, at tree-switch-conversion.c:79)
gcc/ PR tree-optimization/53887 * tree-cfg.c (group_case_labels_stmt): Make non-static. * tree-flow.h (group_case_labels_stmt): Add prototype. * tree-switch-conversion.c (process_switch): Use group_case_labels_stmt to pre-process every switch. testsuite/ PR tree-optimization/53887 * gcc.dg/pr53887.c: New test. From-SVN: r189389
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog8
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/gcc.dg/pr53887.c24
-rw-r--r--gcc/tree-cfg.c3
-rw-r--r--gcc/tree-flow.h1
-rw-r--r--gcc/tree-switch-conversion.c10
6 files changed, 47 insertions, 4 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 3e8bfc2..d8edad0 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,11 @@
+2012-07-09 Steven Bosscher <steven@gcc.gnu.org>
+
+ PR tree-optimization/53887
+ * tree-cfg.c (group_case_labels_stmt): Make non-static.
+ * tree-flow.h (group_case_labels_stmt): Add prototype.
+ * tree-switch-conversion.c (process_switch): Use group_case_labels_stmt
+ to pre-process every switch.
+
2012-07-09 Jason Merrill <jason@redhat.com>
PR c++/53882
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 07187eb..5777c5f 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2012-07-09 Steven Bosscher <steven@gcc.gnu.org>
+
+ PR tree-optimization/53887
+ * gcc.dg/pr53887.c: New test.
+
2012-07-09 Jason Merrill <jason@redhat.com>
PR c++/53882
diff --git a/gcc/testsuite/gcc.dg/pr53887.c b/gcc/testsuite/gcc.dg/pr53887.c
new file mode 100644
index 0000000..b46126c
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr53887.c
@@ -0,0 +1,24 @@
+/* { dg-do compile } */
+/* { dg-options "-O2" } */
+
+enum
+{ Failed, NoError, NoDiskette }
+a;
+int b, c;
+void
+fn1 ()
+{
+ if (c)
+ a << 1;
+ switch (b)
+ {
+ default:
+ a << 1;
+ case 0:
+ b = 0;
+ case 1:
+ case NoDiskette:
+ ;
+ }
+}
+
diff --git a/gcc/tree-cfg.c b/gcc/tree-cfg.c
index dd47609..bdcf7c3 100644
--- a/gcc/tree-cfg.c
+++ b/gcc/tree-cfg.c
@@ -125,7 +125,6 @@ static edge find_taken_edge_computed_goto (basic_block, tree);
static edge find_taken_edge_cond_expr (basic_block, tree);
static edge find_taken_edge_switch_expr (basic_block, tree);
static tree find_case_label_for_value (gimple, tree);
-static void group_case_labels_stmt (gimple);
void
init_empty_tree_cfg_for_function (struct function *fn)
@@ -1331,7 +1330,7 @@ cleanup_dead_labels (void)
the ones jumping to the same label.
Eg. three separate entries 1: 2: 3: become one entry 1..3: */
-static void
+void
group_case_labels_stmt (gimple stmt)
{
int old_size = gimple_switch_num_labels (stmt);
diff --git a/gcc/tree-flow.h b/gcc/tree-flow.h
index cf78839..8f7d336 100644
--- a/gcc/tree-flow.h
+++ b/gcc/tree-flow.h
@@ -428,6 +428,7 @@ extern void debug_loop_num (unsigned, int);
extern void print_loops (FILE *, int);
extern void print_loops_bb (FILE *, basic_block, int, int);
extern void cleanup_dead_labels (void);
+extern void group_case_labels_stmt (gimple);
extern void group_case_labels (void);
extern gimple first_stmt (basic_block);
extern gimple last_stmt (basic_block);
diff --git a/gcc/tree-switch-conversion.c b/gcc/tree-switch-conversion.c
index 94fbf1d..8045798 100644
--- a/gcc/tree-switch-conversion.c
+++ b/gcc/tree-switch-conversion.c
@@ -1339,8 +1339,14 @@ process_switch (gimple swtch)
{
struct switch_conv_info info;
- /* Degenerate case with only a default label should never happen. */
- gcc_checking_assert (gimple_switch_num_labels (swtch) > 1);
+ /* Group case labels so that we get the right results from the heuristics
+ that decide on the code generation approach for this switch. */
+ group_case_labels_stmt (swtch);
+
+ /* If this switch is now a degenerate case with only a default label,
+ there is nothing left for us to do. */
+ if (gimple_switch_num_labels (swtch) < 2)
+ return "switch is a degenerate case";
collect_switch_conv_info (swtch, &info);