cmpb-1.c: New test.
gcc/testsuite/ChangeLog: 2017-05-11 Kelvin Nilsen <kelvin@gcc.gnu.org> * gcc.target/powerpc/cmpb-1.c: New test. * gcc.target/powerpc/cmpb-2.c: New test. * gcc.target/powerpc/cmpb-3.c: New test. * gcc.target/powerpc/cmpb32-1.c: New test. * gcc.target/powerpc/cmpb32-2.c: New test. gcc/ChangeLog: 2017-05-11 Kelvin Nilsen <kelvin@gcc.gnu.org> * config/rs6000/rs6000-c.c (altivec_overloaded_builtins): Add array entries to represent two legal parameterizations of the overloaded __builtin_cmpb function, as represented by the P6_OV_BUILTIN_CMPB constant. (altivec_resolve_overloaded_builtin): Add special case handling for the __builtin_cmpb function, as represented by the P6_OV_BUILTIN_CMPB constant. * config/rs6000/rs6000-builtin.def (BU_P6_2): New macro. (BU_P6_64BIT_2): New macro. (BU_P6_OVERLOAD_2): New macro (CMPB_32): Add 32-bit compare-bytes support for 32-bit only targets. (CMPB): Add 64-bit compare-bytes support for 32-bit and 64-bit targets. (CMPB): Add overload support to represent both 32-bit and 64-bit compare-bytes function. * config/rs6000/rs6000.c (rs6000_builtin_mask_calculate): Add support for TARGET_CMPB. * config/rs6000/rs6000.h: Add support for RS6000_BTM_CMPB. * doc/extend.texi (PowerPC AltiVec Built-in Functions): Add documentation of the __builtin_cmpb overloaded built-in function. From-SVN: r247907
This commit is contained in:
parent
43b883a990
commit
4fd18c782d
12 changed files with 298 additions and 11 deletions
|
@ -1,3 +1,25 @@
|
|||
2017-05-11 Kelvin Nilsen <kelvin@gcc.gnu.org>
|
||||
|
||||
* config/rs6000/rs6000-c.c (altivec_overloaded_builtins): Add
|
||||
array entries to represent two legal parameterizations of the
|
||||
overloaded __builtin_cmpb function, as represented by the
|
||||
P6_OV_BUILTIN_CMPB constant.
|
||||
(altivec_resolve_overloaded_builtin): Add special case handling
|
||||
for the __builtin_cmpb function, as represented by the
|
||||
P6_OV_BUILTIN_CMPB constant.
|
||||
* config/rs6000/rs6000-builtin.def (BU_P6_2): New macro.
|
||||
(BU_P6_64BIT_2): New macro.
|
||||
(BU_P6_OVERLOAD_2): New macro
|
||||
(CMPB_32): Add 32-bit compare-bytes support for 32-bit only targets.
|
||||
(CMPB): Add 64-bit compare-bytes support for 32-bit and 64-bit targets.
|
||||
(CMPB): Add overload support to represent both 32-bit and 64-bit
|
||||
compare-bytes function.
|
||||
* config/rs6000/rs6000.c (rs6000_builtin_mask_calculate): Add
|
||||
support for TARGET_CMPB.
|
||||
* config/rs6000/rs6000.h: Add support for RS6000_BTM_CMPB.
|
||||
* doc/extend.texi (PowerPC AltiVec Built-in Functions): Add
|
||||
documentation of the __builtin_cmpb overloaded built-in function.
|
||||
|
||||
2017-05-11 Richard Biener <rguenther@suse.de>
|
||||
|
||||
PR tree-optimization/80705
|
||||
|
|
|
@ -339,6 +339,34 @@
|
|||
| RS6000_BTC_SPECIAL), \
|
||||
CODE_FOR_nothing) /* ICODE */
|
||||
|
||||
/* ISA 2.05 (power6) convenience macros. */
|
||||
/* For functions that depend on the CMPB instruction */
|
||||
#define BU_P6_2(ENUM, NAME, ATTR, ICODE) \
|
||||
RS6000_BUILTIN_2 (P6_BUILTIN_ ## ENUM, /* ENUM */ \
|
||||
"__builtin_p6_" NAME, /* NAME */ \
|
||||
RS6000_BTM_CMPB, /* MASK */ \
|
||||
(RS6000_BTC_ ## ATTR /* ATTR */ \
|
||||
| RS6000_BTC_BINARY), \
|
||||
CODE_FOR_ ## ICODE) /* ICODE */
|
||||
|
||||
/* For functions that depend on 64-BIT support and on the CMPB instruction */
|
||||
#define BU_P6_64BIT_2(ENUM, NAME, ATTR, ICODE) \
|
||||
RS6000_BUILTIN_2 (P6_BUILTIN_ ## ENUM, /* ENUM */ \
|
||||
"__builtin_p6_" NAME, /* NAME */ \
|
||||
RS6000_BTM_CMPB \
|
||||
| RS6000_BTM_64BIT, /* MASK */ \
|
||||
(RS6000_BTC_ ## ATTR /* ATTR */ \
|
||||
| RS6000_BTC_BINARY), \
|
||||
CODE_FOR_ ## ICODE) /* ICODE */
|
||||
|
||||
#define BU_P6_OVERLOAD_2(ENUM, NAME) \
|
||||
RS6000_BUILTIN_2 (P6_OV_BUILTIN_ ## ENUM, /* ENUM */ \
|
||||
"__builtin_" NAME, /* NAME */ \
|
||||
RS6000_BTM_CMPB, /* MASK */ \
|
||||
(RS6000_BTC_OVERLOADED /* ATTR */ \
|
||||
| RS6000_BTC_BINARY), \
|
||||
CODE_FOR_nothing) /* ICODE */
|
||||
|
||||
/* ISA 2.07 (power8) vector convenience macros. */
|
||||
/* For the instructions that are encoded as altivec instructions use
|
||||
__builtin_altivec_ as the builtin name. */
|
||||
|
@ -1787,6 +1815,10 @@ BU_VSX_OVERLOAD_X (ST, "st")
|
|||
BU_VSX_OVERLOAD_X (XL, "xl")
|
||||
BU_VSX_OVERLOAD_X (XST, "xst")
|
||||
|
||||
/* 2 argument CMPB instructions added in ISA 2.05. */
|
||||
BU_P6_2 (CMPB_32, "cmpb_32", CONST, cmpbsi3)
|
||||
BU_P6_64BIT_2 (CMPB, "cmpb", CONST, cmpbdi3)
|
||||
|
||||
/* 1 argument VSX instructions added in ISA 2.07. */
|
||||
BU_P8V_VSX_1 (XSCVSPDPN, "xscvspdpn", CONST, vsx_xscvspdpn)
|
||||
BU_P8V_VSX_1 (XSCVDPSPN, "xscvdpspn", CONST, vsx_xscvdpspn)
|
||||
|
@ -1873,6 +1905,9 @@ BU_P8V_AV_P (VCMPEQUD_P, "vcmpequd_p", CONST, vector_eq_v2di_p)
|
|||
BU_P8V_AV_P (VCMPGTSD_P, "vcmpgtsd_p", CONST, vector_gt_v2di_p)
|
||||
BU_P8V_AV_P (VCMPGTUD_P, "vcmpgtud_p", CONST, vector_gtu_v2di_p)
|
||||
|
||||
/* ISA 2.05 overloaded 2 argument functions. */
|
||||
BU_P6_OVERLOAD_2 (CMPB, "cmpb")
|
||||
|
||||
/* ISA 2.07 vector overloaded 1 argument functions. */
|
||||
BU_P8V_OVERLOAD_1 (VUPKHSW, "vupkhsw")
|
||||
BU_P8V_OVERLOAD_1 (VUPKLSW, "vupklsw")
|
||||
|
|
|
@ -5362,6 +5362,11 @@ const struct altivec_builtin_types altivec_overloaded_builtins[] = {
|
|||
RS6000_BTI_unsigned_V1TI, RS6000_BTI_unsigned_V1TI,
|
||||
RS6000_BTI_unsigned_V1TI, 0 },
|
||||
|
||||
{ P6_OV_BUILTIN_CMPB, P6_BUILTIN_CMPB_32,
|
||||
RS6000_BTI_UINTSI, RS6000_BTI_UINTSI, RS6000_BTI_UINTSI, 0 },
|
||||
{ P6_OV_BUILTIN_CMPB, P6_BUILTIN_CMPB,
|
||||
RS6000_BTI_UINTDI, RS6000_BTI_UINTDI, RS6000_BTI_UINTDI, 0 },
|
||||
|
||||
{ P8V_BUILTIN_VEC_VUPKHSW, P8V_BUILTIN_VUPKHSW,
|
||||
RS6000_BTI_V2DI, RS6000_BTI_V4SI, 0, 0 },
|
||||
{ P8V_BUILTIN_VEC_VUPKHSW, P8V_BUILTIN_VUPKHSW,
|
||||
|
@ -6424,17 +6429,48 @@ altivec_resolve_overloaded_builtin (location_t loc, tree fndecl,
|
|||
for (desc = altivec_overloaded_builtins;
|
||||
desc->code && desc->code != fcode; desc++)
|
||||
continue;
|
||||
|
||||
/* For arguments after the last, we have RS6000_BTI_NOT_OPAQUE in
|
||||
the opX fields. */
|
||||
for (; desc->code == fcode; desc++)
|
||||
|
||||
/* Need to special case __builtin_cmp because the overloaded forms
|
||||
of this function take (unsigned int, unsigned int) or (unsigned
|
||||
long long int, unsigned long long int). Since C conventions
|
||||
allow the respective argument types to be implicitly coerced into
|
||||
each other, the default handling does not provide adequate
|
||||
discrimination between the desired forms of the function. */
|
||||
if (fcode == P6_OV_BUILTIN_CMPB)
|
||||
{
|
||||
if ((desc->op1 == RS6000_BTI_NOT_OPAQUE
|
||||
|| rs6000_builtin_type_compatible (types[0], desc->op1))
|
||||
&& (desc->op2 == RS6000_BTI_NOT_OPAQUE
|
||||
|| rs6000_builtin_type_compatible (types[1], desc->op2))
|
||||
&& (desc->op3 == RS6000_BTI_NOT_OPAQUE
|
||||
|| rs6000_builtin_type_compatible (types[2], desc->op3)))
|
||||
int overloaded_code;
|
||||
int arg1_mode = TYPE_MODE (types[0]);
|
||||
int arg2_mode = TYPE_MODE (types[1]);
|
||||
|
||||
if (nargs != 2)
|
||||
{
|
||||
error ("__builtin_cmpb only accepts 2 arguments");
|
||||
return error_mark_node;
|
||||
}
|
||||
|
||||
/* If any supplied arguments are wider than 32 bits, resolve to
|
||||
64-bit variant of built-in function. */
|
||||
if ((GET_MODE_PRECISION (arg1_mode) > 32)
|
||||
|| (GET_MODE_PRECISION (arg2_mode) > 32))
|
||||
{
|
||||
/* Assure all argument and result types are compatible with
|
||||
the built-in function represented by P6_BUILTIN_CMPB. */
|
||||
overloaded_code = P6_BUILTIN_CMPB;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Assure all argument and result types are compatible with
|
||||
the built-in function represented by P6_BUILTIN_CMPB_32. */
|
||||
overloaded_code = P6_BUILTIN_CMPB_32;
|
||||
}
|
||||
|
||||
while (desc->code && desc->code == fcode &&
|
||||
desc->overloaded_code != overloaded_code)
|
||||
desc++;
|
||||
|
||||
if (desc->code && (desc->code == fcode)
|
||||
&& rs6000_builtin_type_compatible (types[0], desc->op1)
|
||||
&& rs6000_builtin_type_compatible (types[1], desc->op2))
|
||||
{
|
||||
if (rs6000_builtin_decls[desc->overloaded_code] != NULL_TREE)
|
||||
return altivec_build_resolved_builtin (args, n, desc);
|
||||
|
@ -6442,7 +6478,27 @@ altivec_resolve_overloaded_builtin (location_t loc, tree fndecl,
|
|||
unsupported_builtin = true;
|
||||
}
|
||||
}
|
||||
|
||||
else
|
||||
{
|
||||
/* For arguments after the last, we have RS6000_BTI_NOT_OPAQUE in
|
||||
the opX fields. */
|
||||
for (; desc->code == fcode; desc++)
|
||||
{
|
||||
if ((desc->op1 == RS6000_BTI_NOT_OPAQUE
|
||||
|| rs6000_builtin_type_compatible (types[0], desc->op1))
|
||||
&& (desc->op2 == RS6000_BTI_NOT_OPAQUE
|
||||
|| rs6000_builtin_type_compatible (types[1], desc->op2))
|
||||
&& (desc->op3 == RS6000_BTI_NOT_OPAQUE
|
||||
|| rs6000_builtin_type_compatible (types[2], desc->op3)))
|
||||
{
|
||||
if (rs6000_builtin_decls[desc->overloaded_code] != NULL_TREE)
|
||||
return altivec_build_resolved_builtin (args, n, desc);
|
||||
else
|
||||
unsupported_builtin = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (unsupported_builtin)
|
||||
{
|
||||
const char *name = rs6000_overloaded_builtin_name (fcode);
|
||||
|
|
|
@ -3873,6 +3873,7 @@ HOST_WIDE_INT
|
|||
rs6000_builtin_mask_calculate (void)
|
||||
{
|
||||
return (((TARGET_ALTIVEC) ? RS6000_BTM_ALTIVEC : 0)
|
||||
| ((TARGET_CMPB) ? RS6000_BTM_CMPB : 0)
|
||||
| ((TARGET_VSX) ? RS6000_BTM_VSX : 0)
|
||||
| ((TARGET_SPE) ? RS6000_BTM_SPE : 0)
|
||||
| ((TARGET_PAIRED_FLOAT) ? RS6000_BTM_PAIRED : 0)
|
||||
|
|
|
@ -2717,6 +2717,7 @@ extern int frame_pointer_needed;
|
|||
aren't in target_flags. */
|
||||
#define RS6000_BTM_ALWAYS 0 /* Always enabled. */
|
||||
#define RS6000_BTM_ALTIVEC MASK_ALTIVEC /* VMX/altivec vectors. */
|
||||
#define RS6000_BTM_CMPB MASK_CMPB /* ISA 2.05: compare bytes. */
|
||||
#define RS6000_BTM_VSX MASK_VSX /* VSX (vector/scalar). */
|
||||
#define RS6000_BTM_P8_VECTOR MASK_P8_VECTOR /* ISA 2.07 vector. */
|
||||
#define RS6000_BTM_P9_VECTOR MASK_P9_VECTOR /* ISA 3.0 vector. */
|
||||
|
|
|
@ -15106,6 +15106,24 @@ Similar to @code{__builtin_nans}, except the return type is @code{__float128}.
|
|||
@findex __builtin_nansq
|
||||
@end table
|
||||
|
||||
The following built-in functions are available for the PowerPC family
|
||||
of processors, starting with ISA 2.05 or later (@option{-mcpu=power6}
|
||||
or @option{-mcmpb}):
|
||||
@smallexample
|
||||
unsigned long long __builtin_cmpb (unsigned long long int, unsigned long long int);
|
||||
unsigned int __builtin_cmpb (unsigned int, unsigned int);
|
||||
@end smallexample
|
||||
|
||||
The @code{__builtin_cmpb} function
|
||||
performs a byte-wise compare on the contents of its two arguments,
|
||||
returning the result of the byte-wise comparison as the returned
|
||||
value. For each byte comparison, the corresponding byte of the return
|
||||
value holds 0xff if the input bytes are equal and 0 if the input bytes
|
||||
are not equal. If either of the arguments to this built-in function
|
||||
is wider than 32 bits, the function call expands into the form that
|
||||
expects @code{unsigned long long int} arguments
|
||||
which is only available on 64-bit targets.
|
||||
|
||||
The following built-in functions are available for the PowerPC family
|
||||
of processors, starting with ISA 2.06 or later (@option{-mcpu=power7}
|
||||
or @option{-mpopcntd}):
|
||||
|
|
|
@ -1,3 +1,11 @@
|
|||
2017-05-11 Kelvin Nilsen <kelvin@gcc.gnu.org>
|
||||
|
||||
* gcc.target/powerpc/cmpb-1.c: New test.
|
||||
* gcc.target/powerpc/cmpb-2.c: New test.
|
||||
* gcc.target/powerpc/cmpb-3.c: New test.
|
||||
* gcc.target/powerpc/cmpb32-1.c: New test.
|
||||
* gcc.target/powerpc/cmpb32-2.c: New test.
|
||||
|
||||
2017-05-11 Richard Biener <rguenther@suse.de>
|
||||
|
||||
PR tree-optimization/80705
|
||||
|
|
31
gcc/testsuite/gcc.target/powerpc/cmpb-1.c
Normal file
31
gcc/testsuite/gcc.target/powerpc/cmpb-1.c
Normal file
|
@ -0,0 +1,31 @@
|
|||
/* { dg-do run { target { powerpc*-*-* } } } */
|
||||
/* { dg-skip-if "do not override -mcpu" { powerpc*-*-* } { "-mcpu=*" } { "-mcpu=power6" } } */
|
||||
/* { dg-require-effective-target lp64 } */
|
||||
/* { dg-require-effective-target dfp_hw } */
|
||||
/* { dg-options "-mcpu=power6" } */
|
||||
|
||||
void abort ();
|
||||
|
||||
unsigned long long int
|
||||
do_compare (unsigned long long int a, unsigned long long int b)
|
||||
{
|
||||
return __builtin_cmpb (a, b);
|
||||
}
|
||||
|
||||
void
|
||||
expect (unsigned long long int pattern, unsigned long long int value)
|
||||
{
|
||||
if (pattern != value)
|
||||
abort ();
|
||||
}
|
||||
|
||||
int
|
||||
main (int argc, char *argv[])
|
||||
{
|
||||
expect (0xff00000000000000LL,
|
||||
do_compare (0x0123456789abcdefLL, 0x0100000000000000LL));
|
||||
expect (0x00ffffffffffffff,
|
||||
do_compare (0x0123456789abcdefLL, 0x0023456789abcdefLL));
|
||||
expect (0x00000000000000ff,
|
||||
do_compare (0x00000000000000efLL, 0x0123456789abcdefLL));
|
||||
}
|
31
gcc/testsuite/gcc.target/powerpc/cmpb-2.c
Normal file
31
gcc/testsuite/gcc.target/powerpc/cmpb-2.c
Normal file
|
@ -0,0 +1,31 @@
|
|||
/* { dg-do compile { target { powerpc*-*-* } } } */
|
||||
/* { dg-skip-if "do not override -mcpu" { powerpc*-*-* } { "-mcpu=*" } { "-mcpu=power5" } } */
|
||||
/* { dg-require-effective-target lp64 } */
|
||||
/* { dg-require-effective-target powerpc_popcntb_ok } */
|
||||
/* { dg-options "-mcpu=power5" } */
|
||||
|
||||
void abort ();
|
||||
|
||||
unsigned long long int
|
||||
do_compare (unsigned long long int a, unsigned long long int b)
|
||||
{
|
||||
return __builtin_cmpb (a, b); /* { dg-warning "implicit declaration of function '__builtin_cmpb'" } */
|
||||
}
|
||||
|
||||
void
|
||||
expect (unsigned long long int pattern, unsigned long long int value)
|
||||
{
|
||||
if (pattern != value)
|
||||
abort ();
|
||||
}
|
||||
|
||||
int
|
||||
main (int argc, char *argv[])
|
||||
{
|
||||
expect (0xff00000000000000LL,
|
||||
do_compare (0x0123456789abcdefLL, 0x0100000000000000LL));
|
||||
expect (0x00ffffffffffffff,
|
||||
do_compare (0x0123456789abcdefLL, 0x0023456789abcdefLL));
|
||||
expect (0x00000000000000ff,
|
||||
do_compare (0x00000000000000efLL, 0x0123456789abcdefLL));
|
||||
}
|
30
gcc/testsuite/gcc.target/powerpc/cmpb-3.c
Normal file
30
gcc/testsuite/gcc.target/powerpc/cmpb-3.c
Normal file
|
@ -0,0 +1,30 @@
|
|||
/* { dg-do compile { target { powerpc*-*-* } } } */
|
||||
/* { dg-skip-if "do not override -mcpu" { powerpc*-*-* } { "-mcpu=*" } { "-mcpu=power6" } } */
|
||||
/* { dg-require-effective-target ilp32 } */
|
||||
/* { dg-require-effective-target powerpc_popcntb_ok } */
|
||||
/* { dg-options "-mcpu=power6" } */
|
||||
|
||||
void abort ();
|
||||
|
||||
long long int
|
||||
do_compare (long long int a, long long int b)
|
||||
{
|
||||
return __builtin_cmpb (a, b); /* { dg-error "Builtin function __builtin_cmpb not supported in this compiler configuration" } */
|
||||
}
|
||||
|
||||
void expect (long long int pattern, long long int value)
|
||||
{
|
||||
if (pattern != value)
|
||||
abort ();
|
||||
}
|
||||
|
||||
int
|
||||
main (int argc, char *argv[])
|
||||
{
|
||||
expect (0xff00000000000000LL,
|
||||
do_compare (0x0123456789abcdefLL, 0x0100000000000000LL));
|
||||
expect (0x00ffffffffffffff,
|
||||
do_compare (0x0123456789abcdefLL, 0x0023456789abcdefLL));
|
||||
expect (0x00000000000000ff,
|
||||
do_compare (0x00000000000000efLL, 0x0123456789abcdefLL));
|
||||
}
|
27
gcc/testsuite/gcc.target/powerpc/cmpb32-1.c
Normal file
27
gcc/testsuite/gcc.target/powerpc/cmpb32-1.c
Normal file
|
@ -0,0 +1,27 @@
|
|||
/* { dg-do run { target { powerpc*-*-* } } } */
|
||||
/* { dg-skip-if "do not override -mcpu" { powerpc*-*-* } { "-mcpu=*" } { "-mcpu=power6" } } */
|
||||
/* { dg-require-effective-target dfp_hw } */
|
||||
/* { dg-options "-mcpu=power6" } */
|
||||
|
||||
void abort ();
|
||||
|
||||
unsigned int
|
||||
do_compare (unsigned int a, unsigned int b)
|
||||
{
|
||||
return __builtin_cmpb (a, b);
|
||||
}
|
||||
|
||||
void
|
||||
expect (unsigned int pattern, unsigned int value)
|
||||
{
|
||||
if (pattern != value)
|
||||
abort ();
|
||||
}
|
||||
|
||||
int
|
||||
main (int argc, char *argv[])
|
||||
{
|
||||
expect (0xff000000, do_compare (0x12345678, 0x12000000));
|
||||
expect (0x00ffffff, do_compare (0x12345678, 0x00345678));
|
||||
expect (0x000000ff, do_compare (0x00000078, 0x12345678));
|
||||
}
|
27
gcc/testsuite/gcc.target/powerpc/cmpb32-2.c
Normal file
27
gcc/testsuite/gcc.target/powerpc/cmpb32-2.c
Normal file
|
@ -0,0 +1,27 @@
|
|||
/* { dg-do compile { target { powerpc*-*-* } } } */
|
||||
/* { dg-skip-if "do not override -mcpu" { powerpc*-*-* } { "-mcpu=*" } { "-mcpu=power5" } } */
|
||||
/* { dg-require-effective-target powerpc_popcntb_ok } */
|
||||
/* { dg-options "-mcpu=power5" } */
|
||||
|
||||
void abort ();
|
||||
|
||||
unsigned int
|
||||
do_compare (unsigned int a, unsigned int b)
|
||||
{
|
||||
return __builtin_cmpb (a, b); /* { dg-warning "implicit declaration of function '__builtin_cmpb'" } */
|
||||
}
|
||||
|
||||
void
|
||||
expect (unsigned int pattern, unsigned int value)
|
||||
{
|
||||
if (pattern != value)
|
||||
abort ();
|
||||
}
|
||||
|
||||
int
|
||||
main (int argc, char *argv[])
|
||||
{
|
||||
expect (0xff000000, do_compare (0x12345678, 0x12000000));
|
||||
expect (0x00ffffff, do_compare (0x12345678, 0x00345678));
|
||||
expect (0x000000ff, do_compare (0x00000078, 0x12345678));
|
||||
}
|
Loading…
Add table
Reference in a new issue