aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
Diffstat (limited to 'gcc')
-rw-r--r--gcc/c/ChangeLog6
-rw-r--r--gcc/c/c-typeck.c14
-rw-r--r--gcc/testsuite/ChangeLog6
-rw-r--r--gcc/testsuite/gcc.target/i386/excess-precision-10.c52
-rw-r--r--gcc/testsuite/gcc.target/i386/excess-precision-9.c52
5 files changed, 130 insertions, 0 deletions
diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog
index 1ea87b9..a8e235c 100644
--- a/gcc/c/ChangeLog
+++ b/gcc/c/ChangeLog
@@ -1,3 +1,9 @@
+2018-09-26 Joseph Myers <joseph@codesourcery.com>
+
+ PR c/87390
+ * c-typeck.c (build_binary_op): Use excess precision for
+ comparisons of integers and floating-point for C11 and later.
+
2018-09-26 Martin Jambor <mjambor@suse.cz>
PR c/87347
diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c
index a5a7da0..9d09b8d 100644
--- a/gcc/c/c-typeck.c
+++ b/gcc/c/c-typeck.c
@@ -11249,6 +11249,20 @@ build_binary_op (location_t location, enum tree_code code,
case EXACT_DIV_EXPR:
may_need_excess_precision = true;
break;
+
+ case EQ_EXPR:
+ case NE_EXPR:
+ case LE_EXPR:
+ case GE_EXPR:
+ case LT_EXPR:
+ case GT_EXPR:
+ /* Excess precision for implicit conversions of integers to
+ floating point in C11 and later. */
+ may_need_excess_precision = (flag_isoc11
+ && (ANY_INTEGRAL_TYPE_P (type0)
+ || ANY_INTEGRAL_TYPE_P (type1)));
+ break;
+
default:
may_need_excess_precision = false;
break;
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index aa005e7..16407e5 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,9 @@
+2018-09-26 Joseph Myers <joseph@codesourcery.com>
+
+ PR c/87390
+ * gcc.target/i386/excess-precision-9.c,
+ gcc.target/i386/excess-precision-10.c: New tests.
+
2018-09-26 Richard Biener <rguenther@suse.de>
PR debug/87443
diff --git a/gcc/testsuite/gcc.target/i386/excess-precision-10.c b/gcc/testsuite/gcc.target/i386/excess-precision-10.c
new file mode 100644
index 0000000..f1b9b7e
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/excess-precision-10.c
@@ -0,0 +1,52 @@
+/* Excess precision tests. Test implicit conversions in comparisons:
+ excess precision in C11 mode. */
+/* { dg-do run } */
+/* { dg-options "-std=c11 -mfpmath=387 -fexcess-precision=standard" } */
+
+extern void abort (void);
+extern void exit (int);
+
+int
+main (void)
+{
+ float f = 0x1p63f;
+ unsigned long long int u = (1ULL << 63) + 1;
+
+ if ((f == u) != 0)
+ abort ();
+
+ if ((u == f) != 0)
+ abort ();
+
+ if ((f != u) != 1)
+ abort ();
+
+ if ((u != f) != 1)
+ abort ();
+
+ if ((f < u) != 1)
+ abort ();
+
+ if ((u < f) != 0)
+ abort ();
+
+ if ((f <= u) != 1)
+ abort ();
+
+ if ((u <= f) != 0)
+ abort ();
+
+ if ((f > u) != 0)
+ abort ();
+
+ if ((u > f) != 1)
+ abort ();
+
+ if ((f >= u) != 0)
+ abort ();
+
+ if ((u >= f) != 1)
+ abort ();
+
+ exit (0);
+}
diff --git a/gcc/testsuite/gcc.target/i386/excess-precision-9.c b/gcc/testsuite/gcc.target/i386/excess-precision-9.c
new file mode 100644
index 0000000..61e5fc1
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/excess-precision-9.c
@@ -0,0 +1,52 @@
+/* Excess precision tests. Test implicit conversions in comparisons:
+ no excess precision in C99 mode. */
+/* { dg-do run } */
+/* { dg-options "-std=c99 -mfpmath=387 -fexcess-precision=standard" } */
+
+extern void abort (void);
+extern void exit (int);
+
+int
+main (void)
+{
+ float f = 0x1p63f;
+ unsigned long long int u = (1ULL << 63) + 1;
+
+ if ((f == u) != 1)
+ abort ();
+
+ if ((u == f) != 1)
+ abort ();
+
+ if ((f != u) != 0)
+ abort ();
+
+ if ((u != f) != 0)
+ abort ();
+
+ if ((f < u) != 0)
+ abort ();
+
+ if ((u < f) != 0)
+ abort ();
+
+ if ((f <= u) != 1)
+ abort ();
+
+ if ((u <= f) != 1)
+ abort ();
+
+ if ((f > u) != 0)
+ abort ();
+
+ if ((u > f) != 0)
+ abort ();
+
+ if ((f >= u) != 1)
+ abort ();
+
+ if ((u >= f) != 1)
+ abort ();
+
+ exit (0);
+}