rs6000.md (floor<mode>2): Add support for IEEE 128-bit round to integer instructions.
[gcc] 2018-01-02 Michael Meissner <meissner@linux.vnet.ibm.com> * config/rs6000/rs6000.md (floor<mode>2): Add support for IEEE 128-bit round to integer instructions. (ceil<mode>2): Likewise. (btrunc<mode>2): Likewise. (round<mode>2): Likewise. [gcc/testsuite] 2018-01-02 Michael Meissner <meissner@linux.vnet.ibm.com> * gcc.target/powerpc/float128-hw2.c: Add tests for ceilf128, floorf128, truncf128, and roundf128. * gcc.target/powerpc/float128-hw5.c: New tests for _Float128 optimizations added in match.pd. * gcc.target/powerpc/float128-hw6.c: Likewise. * gcc.target/powerpc/float128-hw7.c: Likewise. * gcc.target/powerpc/float128-hw8.c: Likewise. * gcc.target/powerpc/float128-hw9.c: Likewise. * gcc.target/powerpc/float128-hw10.c: Likewise. * gcc.target/powerpc/float128-hw11.c: Likewise. From-SVN: r256118
This commit is contained in:
parent
50d75500a3
commit
2d71e7b8d4
11 changed files with 314 additions and 0 deletions
|
@ -1,3 +1,11 @@
|
|||
2018-01-02 Michael Meissner <meissner@linux.vnet.ibm.com>
|
||||
|
||||
* config/rs6000/rs6000.md (floor<mode>2): Add support for IEEE
|
||||
128-bit round to integer instructions.
|
||||
(ceil<mode>2): Likewise.
|
||||
(btrunc<mode>2): Likewise.
|
||||
(round<mode>2): Likewise.
|
||||
|
||||
2018-01-02 Aaron Sawdey <acsawdey@linux.vnet.ibm.com>
|
||||
|
||||
* config/rs6000/rs6000-string.c (expand_block_move): Allow the use of
|
||||
|
|
|
@ -14777,6 +14777,47 @@
|
|||
(set_attr "type" "vecfloat")
|
||||
(set_attr "size" "128")])
|
||||
|
||||
;; IEEE 128-bit round to integer built-in functions
|
||||
(define_insn "floor<mode>2"
|
||||
[(set (match_operand:IEEE128 0 "altivec_register_operand" "=v")
|
||||
(unspec:IEEE128
|
||||
[(match_operand:IEEE128 1 "altivec_register_operand" "v")]
|
||||
UNSPEC_FRIM))]
|
||||
"TARGET_FLOAT128_HW && FLOAT128_IEEE_P (<MODE>mode)"
|
||||
"xsrqpi 1,%0,%1,3"
|
||||
[(set_attr "type" "vecfloat")
|
||||
(set_attr "size" "128")])
|
||||
|
||||
(define_insn "ceil<mode>2"
|
||||
[(set (match_operand:IEEE128 0 "altivec_register_operand" "=v")
|
||||
(unspec:IEEE128
|
||||
[(match_operand:IEEE128 1 "altivec_register_operand" "v")]
|
||||
UNSPEC_FRIP))]
|
||||
"TARGET_FLOAT128_HW && FLOAT128_IEEE_P (<MODE>mode)"
|
||||
"xsrqpi 1,%0,%1,2"
|
||||
[(set_attr "type" "vecfloat")
|
||||
(set_attr "size" "128")])
|
||||
|
||||
(define_insn "btrunc<mode>2"
|
||||
[(set (match_operand:IEEE128 0 "altivec_register_operand" "=v")
|
||||
(unspec:IEEE128
|
||||
[(match_operand:IEEE128 1 "altivec_register_operand" "v")]
|
||||
UNSPEC_FRIZ))]
|
||||
"TARGET_FLOAT128_HW && FLOAT128_IEEE_P (<MODE>mode)"
|
||||
"xsrqpi 1,%0,%1,1"
|
||||
[(set_attr "type" "vecfloat")
|
||||
(set_attr "size" "128")])
|
||||
|
||||
(define_insn "round<mode>2"
|
||||
[(set (match_operand:IEEE128 0 "altivec_register_operand" "=v")
|
||||
(unspec:IEEE128
|
||||
[(match_operand:IEEE128 1 "altivec_register_operand" "v")]
|
||||
UNSPEC_FRIN))]
|
||||
"TARGET_FLOAT128_HW && FLOAT128_IEEE_P (<MODE>mode)"
|
||||
"xsrqpi 0,%0,%1,0"
|
||||
[(set_attr "type" "vecfloat")
|
||||
(set_attr "size" "128")])
|
||||
|
||||
;; IEEE 128-bit instructions with round to odd semantics
|
||||
(define_insn "add<mode>3_odd"
|
||||
[(set (match_operand:IEEE128 0 "altivec_register_operand" "=v")
|
||||
|
|
|
@ -1,3 +1,16 @@
|
|||
2018-01-02 Michael Meissner <meissner@linux.vnet.ibm.com>
|
||||
|
||||
* gcc.target/powerpc/float128-hw2.c: Add tests for ceilf128,
|
||||
floorf128, truncf128, and roundf128.
|
||||
* gcc.target/powerpc/float128-hw5.c: New tests for _Float128
|
||||
optimizations added in match.pd.
|
||||
* gcc.target/powerpc/float128-hw6.c: Likewise.
|
||||
* gcc.target/powerpc/float128-hw7.c: Likewise.
|
||||
* gcc.target/powerpc/float128-hw8.c: Likewise.
|
||||
* gcc.target/powerpc/float128-hw9.c: Likewise.
|
||||
* gcc.target/powerpc/float128-hw10.c: Likewise.
|
||||
* gcc.target/powerpc/float128-hw11.c: Likewise.
|
||||
|
||||
2018-01-02 Jakub Jelinek <jakub@redhat.com>
|
||||
|
||||
PR c++/83556
|
||||
|
|
38
gcc/testsuite/gcc.target/powerpc/float128-hw10.c
Normal file
38
gcc/testsuite/gcc.target/powerpc/float128-hw10.c
Normal file
|
@ -0,0 +1,38 @@
|
|||
/* { dg-do compile { target { powerpc*-*-* && lp64 } } } */
|
||||
/* { dg-require-effective-target powerpc_p9vector_ok } */
|
||||
/* { dg-options "-mpower9-vector -O2" } */
|
||||
|
||||
extern _Float128 floorf128 (_Float128);
|
||||
extern _Float128 ceilf128 (_Float128);
|
||||
extern _Float128 roundf128 (_Float128);
|
||||
extern _Float128 truncf128 (_Float128);
|
||||
|
||||
/* Check rounding optimizations that are done for double are also done for
|
||||
_Float128. */
|
||||
|
||||
_Float128
|
||||
floor_floor_x (_Float128 x)
|
||||
{
|
||||
return floorf128 (floorf128 (x));
|
||||
}
|
||||
|
||||
_Float128
|
||||
ceil_ceil_x (_Float128 x)
|
||||
{
|
||||
return ceilf128 (ceilf128 (x));
|
||||
}
|
||||
|
||||
_Float128
|
||||
trunc_trunc_x (_Float128 x)
|
||||
{
|
||||
return truncf128 (truncf128 (x));
|
||||
}
|
||||
|
||||
_Float128
|
||||
round_round_x (_Float128 x)
|
||||
{
|
||||
return roundf128 (roundf128 (x));
|
||||
}
|
||||
|
||||
/* { dg-final { scan-assembler-times {\mxsrqpi\M} 4 } } */
|
||||
/* { dg-final { scan-assembler-not {\mbl\M} } } */
|
58
gcc/testsuite/gcc.target/powerpc/float128-hw11.c
Normal file
58
gcc/testsuite/gcc.target/powerpc/float128-hw11.c
Normal file
|
@ -0,0 +1,58 @@
|
|||
/* { dg-do run { target { powerpc*-*-* && lp64 } } } */
|
||||
/* { dg-require-effective-target p9vector_hw } */
|
||||
/* { dg-options "-mpower9-vector -O2" } */
|
||||
|
||||
#define __STDC_WANT_IEC_60559_TYPES_EXT__ 1
|
||||
#define __STDC_WANT_IEC_60559_FUNCS_EXT__ 1
|
||||
|
||||
#include <math.h>
|
||||
#include <stdlib.h>
|
||||
#include <stddef.h>
|
||||
|
||||
extern _Float128 roundf128 (_Float128);
|
||||
extern _Float128 floorf128 (_Float128);
|
||||
extern _Float128 ceilf128 (_Float128);
|
||||
extern _Float128 truncf128 (_Float128);
|
||||
|
||||
static const struct {
|
||||
_Float128 value;
|
||||
_Float128 exp_round;
|
||||
_Float128 exp_floor;
|
||||
_Float128 exp_ceil;
|
||||
_Float128 exp_trunc;
|
||||
} a[] = {
|
||||
{ -2.0Q, -2.0Q, -2.0Q, -2.0Q, -2.0Q },
|
||||
{ -1.7Q, -2.0Q, -2.0Q, -1.0Q, -1.0Q },
|
||||
{ -1.5Q, -2.0Q, -2.0Q, -1.0Q, -1.0Q },
|
||||
{ -1.3Q, -1.0Q, -2.0Q, -1.0Q, -1.0Q },
|
||||
{ +0.0Q, +0.0Q, +0.0Q, +0.0Q, +0.0Q },
|
||||
{ +1.3Q, +1.0Q, +1.0Q, +2.0Q, +1.0Q },
|
||||
{ +1.5Q, +2.0Q, +1.0Q, +2.0Q, +1.0Q },
|
||||
{ +1.7Q, +2.0Q, +1.0Q, +2.0Q, +1.0Q },
|
||||
{ +2.0Q, +2.0Q, +2.0Q, +2.0Q, +2.0Q }
|
||||
};
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
size_t i;
|
||||
_Float128 v;
|
||||
|
||||
for (i = 0; i < sizeof (a) / sizeof (a[0]); i++)
|
||||
{
|
||||
v = a[i].value;
|
||||
if (roundf128 (v) != a[i].exp_round)
|
||||
abort ();
|
||||
|
||||
if (floorf128 (v) != a[i].exp_floor)
|
||||
abort ();
|
||||
|
||||
if (ceilf128 (v) != a[i].exp_ceil)
|
||||
abort ();
|
||||
|
||||
if (truncf128 (v) != a[i].exp_trunc)
|
||||
abort ();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
|
@ -14,6 +14,10 @@
|
|||
extern _Float128 copysignf128 (_Float128, _Float128);
|
||||
extern _Float128 sqrtf128 (_Float128);
|
||||
extern _Float128 fmaf128 (_Float128, _Float128, _Float128);
|
||||
extern _Float128 ceilf128 (_Float128);
|
||||
extern _Float128 floorf128 (_Float128);
|
||||
extern _Float128 truncf128 (_Float128);
|
||||
extern _Float128 roundf128 (_Float128);
|
||||
|
||||
_Float128
|
||||
do_copysign (_Float128 a, _Float128 b)
|
||||
|
@ -51,10 +55,35 @@ do_nfms (_Float128 a, _Float128 b, _Float128 c)
|
|||
return -fmaf128 (a, b, -c);
|
||||
}
|
||||
|
||||
_Float128
|
||||
do_ceil (_Float128 a)
|
||||
{
|
||||
return ceilf128 (a);
|
||||
}
|
||||
|
||||
_Float128
|
||||
do_floor (_Float128 a)
|
||||
{
|
||||
return floorf128 (a);
|
||||
}
|
||||
|
||||
_Float128
|
||||
do_trunc (_Float128 a)
|
||||
{
|
||||
return truncf128 (a);
|
||||
}
|
||||
|
||||
_Float128
|
||||
do_round (_Float128 a)
|
||||
{
|
||||
return roundf128 (a);
|
||||
}
|
||||
|
||||
/* { dg-final { scan-assembler {\mxscpsgnqp\M} } } */
|
||||
/* { dg-final { scan-assembler {\mxssqrtqp\M} } } */
|
||||
/* { dg-final { scan-assembler {\mxsmaddqp\M} } } */
|
||||
/* { dg-final { scan-assembler {\mxsmsubqp\M} } } */
|
||||
/* { dg-final { scan-assembler {\mxsnmaddqp\M} } } */
|
||||
/* { dg-final { scan-assembler {\mxsnmsubqp\M} } } */
|
||||
/* { dg-final { scan-assembler {\mxsrqpi\M} } } */
|
||||
/* { dg-final { scan-assembler-not {\mbl\M} } } */
|
||||
|
|
33
gcc/testsuite/gcc.target/powerpc/float128-hw5.c
Normal file
33
gcc/testsuite/gcc.target/powerpc/float128-hw5.c
Normal file
|
@ -0,0 +1,33 @@
|
|||
/* { dg-do compile { target { powerpc*-*-* && lp64 } } } */
|
||||
/* { dg-require-effective-target powerpc_p9vector_ok } */
|
||||
/* { dg-options "-mpower9-vector -O2 -ffast-math" } */
|
||||
|
||||
extern _Float128 copysignf128 (_Float128, _Float128);
|
||||
|
||||
/* Check copysign optimizations that are done for double are also done for
|
||||
_Float128. */
|
||||
|
||||
_Float128
|
||||
x_times_cs_one_negx (_Float128 x)
|
||||
{
|
||||
return x * copysignf128 (1.0Q, -x); /* XSNABSQP */
|
||||
}
|
||||
|
||||
_Float128
|
||||
x_times_cs_one_x (_Float128 x)
|
||||
{
|
||||
return x * copysignf128 (1.0Q, x); /* XSABSQP */
|
||||
}
|
||||
|
||||
_Float128
|
||||
cs_x_x (_Float128 x)
|
||||
{
|
||||
return copysignf128 (x, x); /* no operation. */
|
||||
}
|
||||
|
||||
/* { dg-final { scan-assembler-times {\mxsabsqp\M} 1 } } */
|
||||
/* { dg-final { scan-assembler-times {\mxsnabsqp\M} 1 } } */
|
||||
/* { dg-final { scan-assembler-not {\mxscpsgnqp\M} } } */
|
||||
/* { dg-final { scan-assembler-not {\mlxvx\M} } } */
|
||||
/* { dg-final { scan-assembler-not {\mlxv\M} } } */
|
||||
/* { dg-final { scan-assembler-not {\mbl\M} } } */
|
26
gcc/testsuite/gcc.target/powerpc/float128-hw6.c
Normal file
26
gcc/testsuite/gcc.target/powerpc/float128-hw6.c
Normal file
|
@ -0,0 +1,26 @@
|
|||
/* { dg-do compile { target { powerpc*-*-* && lp64 } } } */
|
||||
/* { dg-require-effective-target powerpc_p9vector_ok } */
|
||||
/* { dg-options "-mpower9-vector -O2" } */
|
||||
|
||||
extern _Float128 fabsf128 (_Float128);
|
||||
extern _Float128 copysignf128 (_Float128, _Float128);
|
||||
|
||||
/* Check copysign optimizations that are done for double are also done for
|
||||
_Float128. */
|
||||
|
||||
_Float128
|
||||
cs_negx_y (_Float128 x, _Float128 y)
|
||||
{
|
||||
return copysignf128 (-x, y); /* eliminate negation. */
|
||||
}
|
||||
|
||||
_Float128
|
||||
cs_absx_y (_Float128 x, _Float128 y)
|
||||
{
|
||||
return copysignf128 (fabsf128 (x), y); /* eliminate fabsf128. */
|
||||
}
|
||||
|
||||
/* { dg-final { scan-assembler-times {\mxscpsgnqp\M} 2 } } */
|
||||
/* { dg-final { scan-assembler-not {\mxsnegqp\M} } } */
|
||||
/* { dg-final { scan-assembler-not {\mxsabsqp\M} } } */
|
||||
/* { dg-final { scan-assembler-not {\mbl\M} } } */
|
27
gcc/testsuite/gcc.target/powerpc/float128-hw7.c
Normal file
27
gcc/testsuite/gcc.target/powerpc/float128-hw7.c
Normal file
|
@ -0,0 +1,27 @@
|
|||
/* { dg-do compile { target { powerpc*-*-* && lp64 } } } */
|
||||
/* { dg-require-effective-target powerpc_p9vector_ok } */
|
||||
/* { dg-options "-mpower9-vector -O2" } */
|
||||
|
||||
extern _Float128 fabsf128 (_Float128);
|
||||
extern _Float128 copysignf128 (_Float128, _Float128);
|
||||
|
||||
/* Check copysign optimizations that are done for double are also done for
|
||||
_Float128. */
|
||||
|
||||
_Float128
|
||||
cs_x_pos1 (_Float128 x)
|
||||
{
|
||||
return copysignf128 (x, 1.0Q); /* XSABSQP. */
|
||||
}
|
||||
|
||||
_Float128 cs_x_neg2 (_Float128 x)
|
||||
{
|
||||
return copysignf128 (x, -2.0Q); /* XSNABSQP. */
|
||||
}
|
||||
|
||||
/* { dg-final { scan-assembler-times {\mxsabsqp\M} 1 } } */
|
||||
/* { dg-final { scan-assembler-not {\mxsnabsqp\M} 1 } } */
|
||||
/* { dg-final { scan-assembler-not {\mxscpsgnqp\M} } } */
|
||||
/* { dg-final { scan-assembler-not {\mlxvx\M} } } */
|
||||
/* { dg-final { scan-assembler-not {\mlxv\M} } } */
|
||||
/* { dg-final { scan-assembler-not {\mbl\M} } } */
|
24
gcc/testsuite/gcc.target/powerpc/float128-hw8.c
Normal file
24
gcc/testsuite/gcc.target/powerpc/float128-hw8.c
Normal file
|
@ -0,0 +1,24 @@
|
|||
/* { dg-do compile { target { powerpc*-*-* && lp64 } } } */
|
||||
/* { dg-require-effective-target powerpc_p9vector_ok } */
|
||||
/* { dg-options "-mpower9-vector -O2" } */
|
||||
|
||||
extern _Float128 fminf128 (_Float128, _Float128);
|
||||
extern _Float128 fmaxf128 (_Float128, _Float128);
|
||||
|
||||
/* Check min/max optimizations that are done for double are also done for
|
||||
_Float128. */
|
||||
|
||||
_Float128
|
||||
min_x_x (_Float128 x)
|
||||
{
|
||||
return fminf128 (x, x);
|
||||
}
|
||||
|
||||
_Float128
|
||||
max_x_x (_Float128 x)
|
||||
{
|
||||
return fmaxf128 (x, x);
|
||||
}
|
||||
|
||||
/* { dg-final { scan-assembler-not {\mxscmpuqp\M} } } */
|
||||
/* { dg-final { scan-assembler-not {\mbl\M} } } */
|
17
gcc/testsuite/gcc.target/powerpc/float128-hw9.c
Normal file
17
gcc/testsuite/gcc.target/powerpc/float128-hw9.c
Normal file
|
@ -0,0 +1,17 @@
|
|||
/* { dg-do compile { target { powerpc*-*-* && lp64 } } } */
|
||||
/* { dg-require-effective-target powerpc_p9vector_ok } */
|
||||
/* { dg-options "-mpower9-vector -O2 -ffast-math" } */
|
||||
|
||||
extern _Float128 sqrtf128 (_Float128);
|
||||
|
||||
/* Check sqrt optimizations that are done for double are also done for
|
||||
_Float128. */
|
||||
|
||||
_Float128
|
||||
sqrt_x_times_sqrt_x (_Float128 x)
|
||||
{
|
||||
return sqrtf128 (x) * sqrtf128 (x);
|
||||
}
|
||||
|
||||
/* { dg-final { scan-assembler-not {\mxssqrtqp\M} } } */
|
||||
/* { dg-final { scan-assembler-not {\mbl\M} } } */
|
Loading…
Add table
Reference in a new issue