* [PATCH] Fix PR middle-end/80775, -O3 produces ice in group_case_labels_stmt
@ 2017-05-16 22:48 Peter Bergner
2017-05-17 7:42 ` Richard Biener
0 siblings, 1 reply; 3+ messages in thread
From: Peter Bergner @ 2017-05-16 22:48 UTC (permalink / raw)
To: GCC Patches; +Cc: Richard Biener, David Binderman, Bill Schmidt
The test case in PR80775 exposes a problem in handling two separate
case labels that lead to the same block that contains a call to
__builtin_unreachable(). The current code handles the first label
and deletes the associated edge/block, but trips up when we see the
second case label that now points to a removed block. This patch moves
the deletion of the unreachable case statement to after the merging
of consecutive case labels, which easily fixes the issue. It also has
a side benefit of reducing the number of calls to gimple_seq_unreachable_p()
when we have consecutive case labels that point to unreachable blocks.
This bootstrapped and regtested with no regressions on both powerpc64le-linux
and x86_64-linux. Is this ok for trunk?
Peter
gcc/
PR middle-end/80775
* tree-cfg.c: Move deletion of unreachable case statements to after
the merging of consecutive case labels.
gcc/testsuite/
PR middle-end/80775
* gcc.dg/pr80775.c: New test.
Index: gcc/tree-cfg.c
===================================================================
--- gcc/tree-cfg.c (revision 248119)
+++ gcc/tree-cfg.c (working copy)
@@ -1661,7 +1661,7 @@ void
group_case_labels_stmt (gswitch *stmt)
{
int old_size = gimple_switch_num_labels (stmt);
- int i, j, new_size = old_size;
+ int i, j, base_index, new_size = old_size;
basic_block default_bb = NULL;
default_bb = label_to_block (CASE_LABEL (gimple_switch_default_label (stmt)));
@@ -1678,16 +1678,9 @@ group_case_labels_stmt (gswitch *stmt)
gcc_assert (base_case);
base_bb = label_to_block (CASE_LABEL (base_case));
- /* Discard cases that have the same destination as the default case
- or if their destination block is unreachable. */
- if (base_bb == default_bb
- || (EDGE_COUNT (base_bb->succs) == 0
- && gimple_seq_unreachable_p (bb_seq (base_bb))))
+ /* Discard cases that have the same destination as the default case. */
+ if (base_bb == default_bb)
{
- edge e;
- if (base_bb != default_bb
- && (e = find_edge (gimple_bb (stmt), base_bb)) != NULL)
- remove_edge_and_dominated_blocks (e);
gimple_switch_set_label (stmt, i, NULL_TREE);
i++;
new_size--;
@@ -1697,7 +1690,7 @@ group_case_labels_stmt (gswitch *stmt)
base_high = CASE_HIGH (base_case)
? CASE_HIGH (base_case)
: CASE_LOW (base_case);
- i++;
+ base_index = i++;
/* Try to merge case labels. Break out when we reach the end
of the label vector or when we cannot merge the next case
@@ -1723,6 +1716,18 @@ group_case_labels_stmt (gswitch *stmt)
else
break;
}
+
+ /* Discard cases that have an unreachable destination block. */
+ if (EDGE_COUNT (base_bb->succs) == 0
+ && gimple_seq_unreachable_p (bb_seq (base_bb)))
+ {
+ edge base_edge = find_edge (gimple_bb (stmt), base_bb);
+ if (base_edge != NULL)
+ remove_edge_and_dominated_blocks (base_edge);
+ gimple_switch_set_label (stmt, base_index, NULL_TREE);
+ new_size--;
+ i++;
+ }
}
/* Compress the case labels in the label vector, and adjust the
Index: gcc/testsuite/gcc.dg/pr80775.c
===================================================================
--- gcc/testsuite/gcc.dg/pr80775.c (nonexistent)
+++ gcc/testsuite/gcc.dg/pr80775.c (working copy)
@@ -0,0 +1,21 @@
+/* PR middle-end/80775 ICE: -O3 produces ice in group_case_labels_stmt. */
+/* { dg-do compile } */
+/* { dg-options "-O3" } */
+
+typedef struct { short a; } b;
+b c[10];
+int d, e, f, g, h;
+int
+i (void)
+{
+ f = 0;
+ for (; f < e; f++) {
+ switch (g) {
+ case 1:
+ d = 1;
+ case 2:
+ c[2 + f].a = 1;
+ }
+ h += c[f].a;
+ }
+}
^ permalink raw reply [flat|nested] 3+ messages in thread
* Re: [PATCH] Fix PR middle-end/80775, -O3 produces ice in group_case_labels_stmt
2017-05-16 22:48 [PATCH] Fix PR middle-end/80775, -O3 produces ice in group_case_labels_stmt Peter Bergner
@ 2017-05-17 7:42 ` Richard Biener
2017-05-17 15:26 ` Peter Bergner
0 siblings, 1 reply; 3+ messages in thread
From: Richard Biener @ 2017-05-17 7:42 UTC (permalink / raw)
To: Peter Bergner; +Cc: GCC Patches, David Binderman, Bill Schmidt
On Tue, 16 May 2017, Peter Bergner wrote:
> The test case in PR80775 exposes a problem in handling two separate
> case labels that lead to the same block that contains a call to
> __builtin_unreachable(). The current code handles the first label
> and deletes the associated edge/block, but trips up when we see the
> second case label that now points to a removed block. This patch moves
> the deletion of the unreachable case statement to after the merging
> of consecutive case labels, which easily fixes the issue. It also has
> a side benefit of reducing the number of calls to gimple_seq_unreachable_p()
> when we have consecutive case labels that point to unreachable blocks.
>
> This bootstrapped and regtested with no regressions on both powerpc64le-linux
> and x86_64-linux. Is this ok for trunk?
Ok.
Thanks,
Richard.
> Peter
>
> gcc/
> PR middle-end/80775
> * tree-cfg.c: Move deletion of unreachable case statements to after
> the merging of consecutive case labels.
>
> gcc/testsuite/
> PR middle-end/80775
> * gcc.dg/pr80775.c: New test.
>
> Index: gcc/tree-cfg.c
> ===================================================================
> --- gcc/tree-cfg.c (revision 248119)
> +++ gcc/tree-cfg.c (working copy)
> @@ -1661,7 +1661,7 @@ void
> group_case_labels_stmt (gswitch *stmt)
> {
> int old_size = gimple_switch_num_labels (stmt);
> - int i, j, new_size = old_size;
> + int i, j, base_index, new_size = old_size;
> basic_block default_bb = NULL;
>
> default_bb = label_to_block (CASE_LABEL (gimple_switch_default_label (stmt)));
> @@ -1678,16 +1678,9 @@ group_case_labels_stmt (gswitch *stmt)
> gcc_assert (base_case);
> base_bb = label_to_block (CASE_LABEL (base_case));
>
> - /* Discard cases that have the same destination as the default case
> - or if their destination block is unreachable. */
> - if (base_bb == default_bb
> - || (EDGE_COUNT (base_bb->succs) == 0
> - && gimple_seq_unreachable_p (bb_seq (base_bb))))
> + /* Discard cases that have the same destination as the default case. */
> + if (base_bb == default_bb)
> {
> - edge e;
> - if (base_bb != default_bb
> - && (e = find_edge (gimple_bb (stmt), base_bb)) != NULL)
> - remove_edge_and_dominated_blocks (e);
> gimple_switch_set_label (stmt, i, NULL_TREE);
> i++;
> new_size--;
> @@ -1697,7 +1690,7 @@ group_case_labels_stmt (gswitch *stmt)
> base_high = CASE_HIGH (base_case)
> ? CASE_HIGH (base_case)
> : CASE_LOW (base_case);
> - i++;
> + base_index = i++;
>
> /* Try to merge case labels. Break out when we reach the end
> of the label vector or when we cannot merge the next case
> @@ -1723,6 +1716,18 @@ group_case_labels_stmt (gswitch *stmt)
> else
> break;
> }
> +
> + /* Discard cases that have an unreachable destination block. */
> + if (EDGE_COUNT (base_bb->succs) == 0
> + && gimple_seq_unreachable_p (bb_seq (base_bb)))
> + {
> + edge base_edge = find_edge (gimple_bb (stmt), base_bb);
> + if (base_edge != NULL)
> + remove_edge_and_dominated_blocks (base_edge);
> + gimple_switch_set_label (stmt, base_index, NULL_TREE);
> + new_size--;
> + i++;
> + }
> }
>
> /* Compress the case labels in the label vector, and adjust the
> Index: gcc/testsuite/gcc.dg/pr80775.c
> ===================================================================
> --- gcc/testsuite/gcc.dg/pr80775.c (nonexistent)
> +++ gcc/testsuite/gcc.dg/pr80775.c (working copy)
> @@ -0,0 +1,21 @@
> +/* PR middle-end/80775 ICE: -O3 produces ice in group_case_labels_stmt. */
> +/* { dg-do compile } */
> +/* { dg-options "-O3" } */
> +
> +typedef struct { short a; } b;
> +b c[10];
> +int d, e, f, g, h;
> +int
> +i (void)
> +{
> + f = 0;
> + for (; f < e; f++) {
> + switch (g) {
> + case 1:
> + d = 1;
> + case 2:
> + c[2 + f].a = 1;
> + }
> + h += c[f].a;
> + }
> +}
>
>
--
Richard Biener <rguenther@suse.de>
SUSE LINUX GmbH, GF: Felix Imendoerffer, Jane Smithard, Graham Norton, HRB 21284 (AG Nuernberg)
^ permalink raw reply [flat|nested] 3+ messages in thread
* Re: [PATCH] Fix PR middle-end/80775, -O3 produces ice in group_case_labels_stmt
2017-05-17 7:42 ` Richard Biener
@ 2017-05-17 15:26 ` Peter Bergner
0 siblings, 0 replies; 3+ messages in thread
From: Peter Bergner @ 2017-05-17 15:26 UTC (permalink / raw)
To: Richard Biener; +Cc: GCC Patches, David Binderman, Bill Schmidt
On 5/17/17 2:21 AM, Richard Biener wrote:
> On Tue, 16 May 2017, Peter Bergner wrote:
>> This bootstrapped and regtested with no regressions on both powerpc64le-linux
>> and x86_64-linux. Is this ok for trunk?
>
> Ok.
Committed as revision 248155. Thanks.
Peter
^ permalink raw reply [flat|nested] 3+ messages in thread
end of thread, other threads:[~2017-05-17 15:11 UTC | newest]
Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2017-05-16 22:48 [PATCH] Fix PR middle-end/80775, -O3 produces ice in group_case_labels_stmt Peter Bergner
2017-05-17 7:42 ` Richard Biener
2017-05-17 15:26 ` Peter Bergner
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).