match.pd (X >/>=/</<= 0 ? 1.0 : -1.0): New patterns.
authorAndrew Pinski <apinski@cavium.com>
Tue, 27 Jun 2017 17:57:23 +0000 (17:57 +0000)
committerAndrew Pinski <pinskia@gcc.gnu.org>
Tue, 27 Jun 2017 17:57:23 +0000 (10:57 -0700)
2017-06-27  Andrew Pinski  <apinski@cavium.com>

        * match.pd (X >/>=/</<= 0 ? 1.0 : -1.0): New patterns.
        (X * copysign (1.0, X)): New pattern.
        (X * copysign (1.0, -X)): New pattern.
        (copysign (-1.0, CST)): New pattern.

2017-06-27  Andrew Pinski  <apinski@cavium.com>

        * gcc.dg/tree-ssa/copy-sign-1.c: New testcase.
        * gcc.dg/tree-ssa/copy-sign-2.c: New testcase.
        * gcc.dg/tree-ssa/mult-abs-2.c: New testcase.

From-SVN: r249704

gcc/ChangeLog
gcc/match.pd
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/tree-ssa/copy-sign-1.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/tree-ssa/copy-sign-2.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/tree-ssa/mult-abs-2.c [new file with mode: 0644]

index fcabe2595f3f4a473a111315a3ba1ff52e15d2ef..f52d1b92a236af0f32c552b2407e4c03e1b9b825 100644 (file)
@@ -1,3 +1,10 @@
+2017-06-27  Andrew Pinski  <apinski@cavium.com>
+
+       * match.pd (X >/>=/</<= 0 ? 1.0 : -1.0): New patterns.
+       (X * copysign (1.0, X)): New pattern.
+       (X * copysign (1.0, -X)): New pattern.
+       (copysign (-1.0, CST)): New pattern.
+
 2017-06-27  Joseph Myers  <joseph@codesourcery.com>
 
        * genmultilib (combination_space): Remove variable.
index 083a5742bc37b6bdd5cc81d1616dd98efa0e1d4c..c132cba09cd1faaddf1c68d5dfdc40dbe2c3a06f 100644 (file)
@@ -155,6 +155,58 @@ DEFINE_INT_AND_FLOAT_ROUND_FN (RINT)
            || !COMPLEX_FLOAT_TYPE_P (type)))
    (negate @0)))
 
+(for cmp (gt ge lt le)
+     outp (convert convert negate negate)
+     outn (negate negate convert convert)
+ /* Transform (X > 0.0 ? 1.0 : -1.0) into copysign(1, X). */
+ /* Transform (X >= 0.0 ? 1.0 : -1.0) into copysign(1, X). */
+ /* Transform (X < 0.0 ? 1.0 : -1.0) into copysign(1,-X). */
+ /* Transform (X <= 0.0 ? 1.0 : -1.0) into copysign(1,-X). */
+ (simplify
+  (cond (cmp @0 real_zerop) real_onep@1 real_minus_onep)
+  (if (!HONOR_NANS (type) && !HONOR_SIGNED_ZEROS (type)
+       && types_match (type, TREE_TYPE (@0)))
+   (switch
+    (if (types_match (type, float_type_node))
+     (BUILT_IN_COPYSIGNF @1 (outp @0)))
+    (if (types_match (type, double_type_node))
+     (BUILT_IN_COPYSIGN @1 (outp @0)))
+    (if (types_match (type, long_double_type_node))
+     (BUILT_IN_COPYSIGNL @1 (outp @0))))))
+ /* Transform (X > 0.0 ? -1.0 : 1.0) into copysign(1,-X). */
+ /* Transform (X >= 0.0 ? -1.0 : 1.0) into copysign(1,-X). */
+ /* Transform (X < 0.0 ? -1.0 : 1.0) into copysign(1,X). */
+ /* Transform (X <= 0.0 ? -1.0 : 1.0) into copysign(1,X). */
+ (simplify
+  (cond (cmp @0 real_zerop) real_minus_onep real_onep@1)
+  (if (!HONOR_NANS (type) && !HONOR_SIGNED_ZEROS (type)
+       && types_match (type, TREE_TYPE (@0)))
+   (switch
+    (if (types_match (type, float_type_node))
+     (BUILT_IN_COPYSIGNF @1 (outn @0)))
+    (if (types_match (type, double_type_node))
+     (BUILT_IN_COPYSIGN @1 (outn @0)))
+    (if (types_match (type, long_double_type_node))
+     (BUILT_IN_COPYSIGNL @1 (outn @0)))))))
+
+/* Transform X * copysign (1.0, X) into abs(X). */
+(simplify
+ (mult:c @0 (COPYSIGN real_onep @0))
+ (if (!HONOR_NANS (type) && !HONOR_SIGNED_ZEROS (type))
+  (abs @0)))
+
+/* Transform X * copysign (1.0, -X) into -abs(X). */
+(simplify
+ (mult:c @0 (COPYSIGN real_onep (negate @0)))
+ (if (!HONOR_NANS (type) && !HONOR_SIGNED_ZEROS (type))
+  (negate (abs @0))))
+
+/* Transform copysign (CST, X) into copysign (ABS(CST), X). */
+(simplify
+ (COPYSIGN REAL_CST@0 @1)
+ (if (REAL_VALUE_NEGATIVE (TREE_REAL_CST (@0)))
+  (COPYSIGN (negate @0) @1)))
+
 /* X * 1, X / 1 -> X.  */
 (for op (mult trunc_div ceil_div floor_div round_div exact_div)
   (simplify
index 98faa118078c1182248f511b0dd9bcd6e059a54e..56123195e8dfca7371014496e47517193a23468c 100644 (file)
@@ -1,3 +1,9 @@
+2017-06-27  Andrew Pinski  <apinski@cavium.com>
+
+       * gcc.dg/tree-ssa/copy-sign-1.c: New testcase.
+       * gcc.dg/tree-ssa/copy-sign-2.c: New testcase.
+       * gcc.dg/tree-ssa/mult-abs-2.c: New testcase.
+
 2017-06-27  Marek Polacek  <polacek@redhat.com>
 
        PR sanitizer/81223
diff --git a/gcc/testsuite/gcc.dg/tree-ssa/copy-sign-1.c b/gcc/testsuite/gcc.dg/tree-ssa/copy-sign-1.c
new file mode 100644 (file)
index 0000000..9ebdf50
--- /dev/null
@@ -0,0 +1,35 @@
+/* { dg-options "-O2 -ffast-math -fdump-tree-gimple" } */
+/* { dg-do compile } */
+float f(float x)
+{
+  return (x > 0.f ? -1.f : 1.f);
+}
+float f1(float x)
+{
+  return (x > 0.f ? 1.f : -1.f);
+}
+float g(float x)
+{
+  return (x >= 0.f ? -1.f : 1.f);
+}
+float g1(float x)
+{
+  return (x >= 0.f ? 1.f : -1.f);
+}
+float h(float x)
+{
+  return (x < 0.f ? -1.f : 1.f);
+}
+float h1(float x)
+{
+  return (x < 0.f ? 1.f : -1.f);
+}
+float i(float x)
+{
+  return (x <= 0.f ? -1.f : 1.f);
+}
+float i1(float x)
+{
+  return (x <= 0.f ? 1.f : -1.f);
+}
+/* { dg-final { scan-tree-dump-times "copysign" 8 "gimple"} } */
diff --git a/gcc/testsuite/gcc.dg/tree-ssa/copy-sign-2.c b/gcc/testsuite/gcc.dg/tree-ssa/copy-sign-2.c
new file mode 100644 (file)
index 0000000..de52c5f
--- /dev/null
@@ -0,0 +1,13 @@
+/* { dg-options "-O2 -ffast-math -fdump-tree-optimized" } */
+/* { dg-do compile } */
+float f(float x)
+{
+  float t = __builtin_copysignf (1.0f, x);
+  return x * t;
+}
+float f1(float x)
+{
+  float t = __builtin_copysignf (1.0f, -x);
+  return x * t;
+}
+/* { dg-final { scan-tree-dump-times "ABS" 2 "optimized"} } */
diff --git a/gcc/testsuite/gcc.dg/tree-ssa/mult-abs-2.c b/gcc/testsuite/gcc.dg/tree-ssa/mult-abs-2.c
new file mode 100644 (file)
index 0000000..b6a1a79
--- /dev/null
@@ -0,0 +1,35 @@
+/* { dg-options "-O2 -ffast-math -fdump-tree-gimple" } */
+/* { dg-do compile } */
+float f(float x)
+{
+  return x * (x > 0.f ? -1.f : 1.f);
+}
+float f1(float x)
+{
+  return x * (x > 0.f ? 1.f : -1.f);
+}
+float g(float x)
+{
+  return x * (x >= 0.f ? -1.f : 1.f);
+}
+float g1(float x)
+{
+  return x * (x >= 0.f ? 1.f : -1.f);
+}
+float h(float x)
+{
+  return x * (x < 0.f ? -1.f : 1.f);
+}
+float h1(float x)
+{
+  return x * (x < 0.f ? 1.f : -1.f);
+}
+float i(float x)
+{
+  return x * (x <= 0.f ? -1.f : 1.f);
+}
+float i1(float x)
+{
+  return x * (x <= 0.f ? 1.f : -1.f);
+}
+/* { dg-final { scan-tree-dump-times "ABS" 8 "gimple"} } */