aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRamana Radhakrishnan <ramana.radhakrishnan@arm.com>2015-06-24 08:28:08 +0000
committerRamana Radhakrishnan <ramana@gcc.gnu.org>2015-06-24 08:28:08 +0000
commitce72a3c995a9731307583933a01d2599654d1a36 (patch)
treea9d4ab4f22bdb53d8684a942ea13d10fd39d15de
parent0bc64a6ca5b518419c91637f88635c95e3c3acb9 (diff)
downloadgcc-ce72a3c995a9731307583933a01d2599654d1a36.zip
gcc-ce72a3c995a9731307583933a01d2599654d1a36.tar.gz
gcc-ce72a3c995a9731307583933a01d2599654d1a36.tar.bz2
re PR target/63408 (GCC emits incorrect fixed->fp conversion instruction on Cortex-M4 target)
Fix PR target/63408 The attached patch fixes PR target/63408 and adds a regression test for the same. The problem is essentially that vfp3_const_double_for_fract_bits() needs to be aware that negative values cannot be used in this context. Tested with a bootstrap and regression test run on armhf. Applied. 2015-06-24 Ramana Radhakrishnan <ramana.radhakrishnan@arm.com> PR target/63408 * config/arm/arm.c (vfp3_const_double_for_fract_bits): Disable for negative numbers. 2015-06-24 Ramana Radhakrishnan <ramana.radhakrishnan@arm.com> PR target/63408 * gcc.target/arm/pr63408.c: New test. From-SVN: r224879
-rw-r--r--gcc/ChangeLog6
-rw-r--r--gcc/config/arm/arm.c3
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/gcc.target/arm/pr63408.c23
4 files changed, 36 insertions, 1 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index d1f82b2..8a95bc27 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,9 @@
+2015-06-24 Ramana Radhakrishnan <ramana.radhakrishnan@arm.com>
+
+ PR target/63408
+ * config/arm/arm.c (vfp3_const_double_for_fract_bits): Disable
+ for negative numbers.
+
2015-06-24 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
PR rtl-optimization/66306
diff --git a/gcc/config/arm/arm.c b/gcc/config/arm/arm.c
index ced4231..09191e5 100644
--- a/gcc/config/arm/arm.c
+++ b/gcc/config/arm/arm.c
@@ -27382,7 +27382,8 @@ vfp3_const_double_for_fract_bits (rtx operand)
return 0;
REAL_VALUE_FROM_CONST_DOUBLE (r0, operand);
- if (exact_real_inverse (DFmode, &r0))
+ if (exact_real_inverse (DFmode, &r0)
+ && !REAL_VALUE_NEGATIVE (r0))
{
if (exact_real_truncate (DFmode, &r0))
{
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index ee58cdc..daadf4c 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2015-06-24 Ramana Radhakrishnan <ramana.radhakrishnan@arm.com>
+
+ PR target/63408
+ * gcc.target/arm/pr63408.c: New test.
+
2015-06-24 James Greenhalgh <james.greenhalgh@arm.com>
* lib/c-torture.exp: Don't call check_effective_target_lto
diff --git a/gcc/testsuite/gcc.target/arm/pr63408.c b/gcc/testsuite/gcc.target/arm/pr63408.c
new file mode 100644
index 0000000..850596b
--- /dev/null
+++ b/gcc/testsuite/gcc.target/arm/pr63408.c
@@ -0,0 +1,23 @@
+/* { dg-do run } */
+/* { dg-options "-O2" } */
+void abort (void) __attribute__ ((noreturn));
+float __attribute__((noinline))
+f(float a, int b)
+{
+ return a - (((float)b / 0x7fffffff) * 100);
+}
+
+int
+main (void)
+{
+ float a[] = { 100.0, 0.0, 0.0};
+ int b[] = { 0x7fffffff, 0x7fffffff/100.0f, -0x7fffffff / 100.0f};
+ float c[] = { 0.0, -1.0, 1.0 };
+ int i;
+
+ for (i = 0; i < (sizeof(a) / sizeof (float)); i++)
+ if (f (a[i], b[i]) != c[i])
+ abort ();
+
+ return 0;
+}