From 978184fab75b3709da0548e9fa948e7d61e606a6 Mon Sep 17 00:00:00 2001
From: jakub <jakub@138bc75d-0d04-0410-961f-82ee72b054a4>
Date: Tue, 30 Apr 2019 20:47:52 +0000
Subject: [PATCH] 	Backported from mainline 	2019-03-19  Jakub
 Jelinek  <jakub@redhat.com>

	PR target/89726
	* config/i386/i386.c (ix86_expand_floorceildf_32): In ceil
	compensation use x2 += 1 instead of x2 -= -1 and when honoring
	signed zeros, do another copysign after the compensation.

	* gcc.target/i386/fpprec-1.c (x): Add 6 new constants.
	(expect_round, expect_rint, expect_floor, expect_ceil, expect_trunc):
	Add expected results for them.


git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/branches/gcc-8-branch@270734 138bc75d-0d04-0410-961f-82ee72b054a4

Upstream-Status: Backport
---
 gcc/ChangeLog                            |  7 +++++++
 gcc/config/i386/i386.c                   | 17 +++++++++--------
 gcc/testsuite/ChangeLog                  |  5 +++++
 gcc/testsuite/gcc.target/i386/fpprec-1.c |  8 ++++++++
 4 files changed, 29 insertions(+), 8 deletions(-)

Index: gcc-8.2.0/gcc/ChangeLog
===================================================================
--- gcc-8.2.0.orig/gcc/ChangeLog
+++ gcc-8.2.0/gcc/ChangeLog
@@ -1,3 +1,13 @@
+2019-04-30  Jakub Jelinek  <jakub@redhat.com>
+
+	Backported from mainline
+	2019-03-19  Jakub Jelinek  <jakub@redhat.com>
+
+	PR target/89726
+	* gcc.target/i386/fpprec-1.c (x): Add 6 new constants.
+	(expect_round, expect_rint, expect_floor, expect_ceil, expect_trunc):
+	Add expected results for them.
+
 2019-01-08  Jakub Jelinek  <jakub@redhat.com>
 
 	Backported from mainline
Index: gcc-8.2.0/gcc/config/i386/i386.c
===================================================================
--- gcc-8.2.0.orig/gcc/config/i386/i386.c
+++ gcc-8.2.0/gcc/config/i386/i386.c
@@ -45635,8 +45635,10 @@ ix86_expand_floorceildf_32 (rtx operand0
           x2 -= 1;
      Compensate.  Ceil:
         if (x2 < x)
-          x2 -= -1;
-        return x2;
+          x2 += 1;
+	if (HONOR_SIGNED_ZEROS (mode))
+	  x2 = copysign (x2, x);
+	return x2;
    */
   machine_mode mode = GET_MODE (operand0);
   rtx xa, TWO52, tmp, one, res, mask;
@@ -45662,17 +45664,16 @@ ix86_expand_floorceildf_32 (rtx operand0
   /* xa = copysign (xa, operand1) */
   ix86_sse_copysign_to_positive (xa, xa, res, mask);
 
-  /* generate 1.0 or -1.0 */
-  one = force_reg (mode,
-	           const_double_from_real_value (do_floor
-						 ? dconst1 : dconstm1, mode));
+  /* generate 1.0 */
+  one = force_reg (mode, const_double_from_real_value (dconst1, mode));
 
   /* Compensate: xa = xa - (xa > operand1 ? 1 : 0) */
   tmp = ix86_expand_sse_compare_mask (UNGT, xa, res, !do_floor);
   emit_insn (gen_rtx_SET (tmp, gen_rtx_AND (mode, one, tmp)));
-  /* We always need to subtract here to preserve signed zero.  */
-  tmp = expand_simple_binop (mode, MINUS,
+  tmp = expand_simple_binop (mode, do_floor ? MINUS : PLUS,
 			     xa, tmp, NULL_RTX, 0, OPTAB_DIRECT);
+  if (!do_floor && HONOR_SIGNED_ZEROS (mode))
+    ix86_sse_copysign_to_positive (tmp, tmp, res, mask);
   emit_move_insn (res, tmp);
 
   emit_label (label);
Index: gcc-8.2.0/gcc/testsuite/gcc.target/i386/fpprec-1.c
===================================================================
--- gcc-8.2.0.orig/gcc/testsuite/gcc.target/i386/fpprec-1.c
+++ gcc-8.2.0/gcc/testsuite/gcc.target/i386/fpprec-1.c
@@ -11,6 +11,9 @@ double x[] = { __builtin_nan(""), __buil
 	0x1.0000000000001p-1, 0x1.fffffffffffffp-2,
 	0x1.0000000000001p+0, 0x1.fffffffffffffp-1,
 	0x1.8000000000001p+0, 0x1.7ffffffffffffp+0,
+	-0x1.0000000000001p-1, -0x1.fffffffffffffp-2,
+	-0x1.0000000000001p+0, -0x1.fffffffffffffp-1,
+	-0x1.8000000000001p+0, -0x1.7ffffffffffffp+0,
 	-0.0, 0.0, -0.5, 0.5, -1.0, 1.0, -1.5, 1.5, -2.0, 2.0,
 	-2.5, 2.5 };
 #define NUM (sizeof(x)/sizeof(double))
@@ -19,6 +22,7 @@ double expect_round[] = { __builtin_nan(
 	-0x1.fffffffffffffp+1023, 0x1.fffffffffffffp+1023,
 	-0.0, 0.0,
 	1.0, 0.0, 1.0, 1.0, 2.0, 1.0,
+	-1.0, -0.0, -1.0, -1.0, -2.0, -1.0,
 	-0.0, 0.0, -1.0, 1.0, -1.0, 1.0, -2.0, 2.0, -2.0, 2.0,
 	-3.0, 3.0 };
 
@@ -26,6 +30,7 @@ double expect_rint[] = { __builtin_nan("
         -0x1.fffffffffffffp+1023, 0x1.fffffffffffffp+1023,
         -0.0, 0.0,
         1.0, 0.0, 1.0, 1.0, 2.0, 1.0,
+        -1.0, -0.0, -1.0, -1.0, -2.0, -1.0,
         -0.0, 0.0, -0.0, 0.0, -1.0, 1.0, -2.0, 2.0, -2.0, 2.0,
         -2.0, 2.0 };
 
@@ -33,6 +38,7 @@ double expect_floor[] = { __builtin_nan(
         -0x1.fffffffffffffp+1023, 0x1.fffffffffffffp+1023,
         -1.0, 0.0,
         0.0, 0.0, 1.0, 0.0, 1.0, 1.0,
+        -1.0, -1.0, -2.0, -1.0, -2.0, -2.0,
         -0.0, 0.0, -1.0, 0.0, -1.0, 1.0, -2.0, 1.0, -2.0, 2.0,
         -3.0, 2.0 };
 
@@ -40,6 +46,7 @@ double expect_ceil[] = { __builtin_nan("
         -0x1.fffffffffffffp+1023, 0x1.fffffffffffffp+1023,
         -0.0, 1.0,
         1.0, 1.0, 2.0, 1.0, 2.0, 2.0,
+        -0.0, -0.0, -1.0, -0.0, -1.0, -1.0,
         -0.0, 0.0, -0.0, 1.0, -1.0, 1.0, -1.0, 2.0, -2.0, 2.0,
         -2.0, 3.0 };
 
@@ -47,6 +54,7 @@ double expect_trunc[] = { __builtin_nan(
         -0x1.fffffffffffffp+1023, 0x1.fffffffffffffp+1023,
         -0.0, 0.0,
         0.0, 0.0, 1.0, 0.0, 1.0, 1.0,
+        -0.0, -0.0, -1.0, -0.0, -1.0, -1.0,
         -0.0, 0.0, -0.0, 0.0, -1.0, 1.0, -1.0, 1.0, -2.0, 2.0,
         -2.0, 2.0 };
 
