This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[PATCH][combine] PR middle-end/71074 Check that const_op is >= 0 before potentially shifting in simplify_comparison
- From: Kyrill Tkachov <kyrylo dot tkachov at foss dot arm dot com>
- To: GCC Patches <gcc-patches at gcc dot gnu dot org>
- Date: Fri, 13 May 2016 13:21:03 +0100
- Subject: [PATCH][combine] PR middle-end/71074 Check that const_op is >= 0 before potentially shifting in simplify_comparison
- Authentication-results: sourceware.org; auth=none
Hi all,
In this PR we may end up shifting a negative value left in simplify_comparison.
The statement is:
const_op <<= INTVAL (XEXP (op0, 1));
This patch guards the block of that statement by const_op >= 0.
I _think_ that's a correct thing to do for that trasnformation:
"If we have (compare (xshiftrt FOO N) (const_int C)) and
the low order N bits of FOO are known to be zero, we can do this
by comparing FOO with C shifted left N bits so long as no
overflow occurs."
The constant C here is const_op.
Bootstrapped and tested on arm-none-linux-gnueabihf, aarch64-none-linux-gnu.
Ok for trunk?
Thanks,
Kyrill
2016-05-13 Kyrylo Tkachov <kyrylo.tkachov@arm.com>
PR middle-end/71074
* combine.c (simplify_comparison): Avoid left shift of negative
const_op in LSHIFTRT case.
2016-05-13 Kyrylo Tkachov <kyrylo.tkachov@arm.com>
PR middle-end/71074
* gcc.c-torture/compile/pr71074.c: New test.
diff --git a/gcc/combine.c b/gcc/combine.c
index 2a7a9e6e2b597246392ede22552af1bdd7e1a794..7a21d593777ef267942e0ee80e024b147907652f 100644
--- a/gcc/combine.c
+++ b/gcc/combine.c
@@ -12321,6 +12321,7 @@ simplify_comparison (enum rtx_code code, rtx *pop0, rtx *pop1)
optimization and for > or <= by setting all the low
order N bits in the comparison constant. */
if (CONST_INT_P (XEXP (op0, 1))
+ && const_op >= 0
&& INTVAL (XEXP (op0, 1)) > 0
&& INTVAL (XEXP (op0, 1)) < HOST_BITS_PER_WIDE_INT
&& mode_width <= HOST_BITS_PER_WIDE_INT
diff --git a/gcc/testsuite/gcc.c-torture/compile/pr71074.c b/gcc/testsuite/gcc.c-torture/compile/pr71074.c
new file mode 100644
index 0000000000000000000000000000000000000000..9ad6cbe7c231069c86d3ade22784f338f331b657
--- /dev/null
+++ b/gcc/testsuite/gcc.c-torture/compile/pr71074.c
@@ -0,0 +1,13 @@
+int bar (void);
+
+void
+foo (unsigned long long a, int b)
+{
+ int i;
+
+ for (a = -12; a >= 10; a = bar ())
+ break;
+
+ if (i == bar () || bar () >= a)
+ bar ();
+}