mirror of git://gcc.gnu.org/git/gcc.git
This patch adds support for the missing versions of the vec_mul altivec...
This patch adds support for the missing versions of the vec_mul altivec
builtins from the Power Architecture 64-Bit ELF V2 ABI OpenPOWER ABI for
Linux Supplement (16 July 2015 Version 1.1). There are many of the builtins
that are missing and this is part of a series of patches to add them.
There aren't instructions for the {un}signed char, {un}signed short, and
{un}signed int versions of vec_mul so the output code is built from other
built-ins and operations that do have instructions.
The new test case is an executable test which verifies that the generated
code produces expected values. C macros were used so that the same
test case could be used for all the various supported types.
Bootstrapped and tested on powerpc64le-unknown-linux-gnu and
powerpc64-unknown-linux-gnu with no regressions. Is this ok for trunk?
[gcc]
2016-06-07 Bill Seurer <seurer@linux.vnet.ibm.com>
* config/rs6000/altivec.h: Add __builtin_vec_mul.
* config/rs6000/rs6000-builtin.def (vec_mul): Change vec_mul to a
special case Altivec builtin.
* config/rs6000/rs6000-c.c (altivec_overloaded_builtins): Remove
VSX_BUILTIN_VEC_MUL (replaced with special case code).
* config/rs6000/rs6000-c.c (altivec_resolve_overloaded_builtin): Add
code for ALTIVEC_BUILTIN_VEC_MUL.
* config/rs6000/rs6000.c (altivec_init_builtins): Add definition
for __builtin_vec_mul.
[gcc/testsuite]
2016-06-07 Bill Seurer <seurer@linux.vnet.ibm.com>
* gcc.target/powerpc/vec-mul.c: New test.
From-SVN: r237183
This commit is contained in:
parent
ca51b2afc6
commit
a23e6f1c59
|
|
@ -1,3 +1,15 @@
|
||||||
|
2016-06-07 Bill Seurer <seurer@linux.vnet.ibm.com>
|
||||||
|
|
||||||
|
* config/rs6000/altivec.h: Add __builtin_vec_mul.
|
||||||
|
* config/rs6000/rs6000-builtin.def (vec_mul): Change vec_mul to a
|
||||||
|
special case Altivec builtin.
|
||||||
|
* config/rs6000/rs6000-c.c (altivec_overloaded_builtins): Remove
|
||||||
|
VSX_BUILTIN_VEC_MUL (replaced with special case code).
|
||||||
|
* config/rs6000/rs6000-c.c (altivec_resolve_overloaded_builtin): Add
|
||||||
|
code for ALTIVEC_BUILTIN_VEC_MUL.
|
||||||
|
* config/rs6000/rs6000.c (altivec_init_builtins): Add definition
|
||||||
|
for __builtin_vec_mul.
|
||||||
|
|
||||||
2016-06-07 Peter Bergner <bergner@vnet.ibm.com>
|
2016-06-07 Peter Bergner <bergner@vnet.ibm.com>
|
||||||
|
|
||||||
* doc/invoke.texi (RS/6000 and PowerPC Options): Document -mhtm and
|
* doc/invoke.texi (RS/6000 and PowerPC Options): Document -mhtm and
|
||||||
|
|
|
||||||
|
|
@ -229,6 +229,7 @@
|
||||||
#define vec_mladd __builtin_vec_mladd
|
#define vec_mladd __builtin_vec_mladd
|
||||||
#define vec_msum __builtin_vec_msum
|
#define vec_msum __builtin_vec_msum
|
||||||
#define vec_msums __builtin_vec_msums
|
#define vec_msums __builtin_vec_msums
|
||||||
|
#define vec_mul __builtin_vec_mul
|
||||||
#define vec_mule __builtin_vec_mule
|
#define vec_mule __builtin_vec_mule
|
||||||
#define vec_mulo __builtin_vec_mulo
|
#define vec_mulo __builtin_vec_mulo
|
||||||
#define vec_nor __builtin_vec_nor
|
#define vec_nor __builtin_vec_nor
|
||||||
|
|
|
||||||
|
|
@ -1300,6 +1300,7 @@ BU_ALTIVEC_OVERLOAD_X (LVRX, "lvrx")
|
||||||
BU_ALTIVEC_OVERLOAD_X (LVRXL, "lvrxl")
|
BU_ALTIVEC_OVERLOAD_X (LVRXL, "lvrxl")
|
||||||
BU_ALTIVEC_OVERLOAD_X (LVSL, "lvsl")
|
BU_ALTIVEC_OVERLOAD_X (LVSL, "lvsl")
|
||||||
BU_ALTIVEC_OVERLOAD_X (LVSR, "lvsr")
|
BU_ALTIVEC_OVERLOAD_X (LVSR, "lvsr")
|
||||||
|
BU_ALTIVEC_OVERLOAD_X (MUL, "mul")
|
||||||
BU_ALTIVEC_OVERLOAD_X (PROMOTE, "promote")
|
BU_ALTIVEC_OVERLOAD_X (PROMOTE, "promote")
|
||||||
BU_ALTIVEC_OVERLOAD_X (SLD, "sld")
|
BU_ALTIVEC_OVERLOAD_X (SLD, "sld")
|
||||||
BU_ALTIVEC_OVERLOAD_X (SPLAT, "splat")
|
BU_ALTIVEC_OVERLOAD_X (SPLAT, "splat")
|
||||||
|
|
@ -1600,7 +1601,6 @@ BU_VSX_OVERLOAD_3V (XXPERMDI, "xxpermdi")
|
||||||
BU_VSX_OVERLOAD_3V (XXSLDWI, "xxsldwi")
|
BU_VSX_OVERLOAD_3V (XXSLDWI, "xxsldwi")
|
||||||
|
|
||||||
/* 2 argument VSX overloaded builtin functions. */
|
/* 2 argument VSX overloaded builtin functions. */
|
||||||
BU_VSX_OVERLOAD_2 (MUL, "mul")
|
|
||||||
BU_VSX_OVERLOAD_2 (DIV, "div")
|
BU_VSX_OVERLOAD_2 (DIV, "div")
|
||||||
BU_VSX_OVERLOAD_2 (XXMRGHW, "xxmrghw")
|
BU_VSX_OVERLOAD_2 (XXMRGHW, "xxmrghw")
|
||||||
BU_VSX_OVERLOAD_2 (XXMRGLW, "xxmrglw")
|
BU_VSX_OVERLOAD_2 (XXMRGLW, "xxmrglw")
|
||||||
|
|
|
||||||
|
|
@ -1941,14 +1941,6 @@ const struct altivec_builtin_types altivec_overloaded_builtins[] = {
|
||||||
RS6000_BTI_unsigned_V16QI, RS6000_BTI_bool_V16QI, RS6000_BTI_unsigned_V16QI, 0 },
|
RS6000_BTI_unsigned_V16QI, RS6000_BTI_bool_V16QI, RS6000_BTI_unsigned_V16QI, 0 },
|
||||||
{ ALTIVEC_BUILTIN_VEC_VMINUB, ALTIVEC_BUILTIN_VMINUB,
|
{ ALTIVEC_BUILTIN_VEC_VMINUB, ALTIVEC_BUILTIN_VMINUB,
|
||||||
RS6000_BTI_unsigned_V16QI, RS6000_BTI_unsigned_V16QI, RS6000_BTI_bool_V16QI, 0 },
|
RS6000_BTI_unsigned_V16QI, RS6000_BTI_unsigned_V16QI, RS6000_BTI_bool_V16QI, 0 },
|
||||||
{ VSX_BUILTIN_VEC_MUL, VSX_BUILTIN_XVMULSP,
|
|
||||||
RS6000_BTI_V4SF, RS6000_BTI_V4SF, RS6000_BTI_V4SF, 0 },
|
|
||||||
{ VSX_BUILTIN_VEC_MUL, VSX_BUILTIN_XVMULDP,
|
|
||||||
RS6000_BTI_V2DF, RS6000_BTI_V2DF, RS6000_BTI_V2DF, 0 },
|
|
||||||
{ VSX_BUILTIN_VEC_MUL, VSX_BUILTIN_MUL_V2DI,
|
|
||||||
RS6000_BTI_V2DI, RS6000_BTI_V2DI, RS6000_BTI_V2DI, 0 },
|
|
||||||
{ VSX_BUILTIN_VEC_MUL, VSX_BUILTIN_MUL_V2DI,
|
|
||||||
RS6000_BTI_unsigned_V2DI, RS6000_BTI_unsigned_V2DI, RS6000_BTI_unsigned_V2DI, 0 },
|
|
||||||
{ ALTIVEC_BUILTIN_VEC_MULE, ALTIVEC_BUILTIN_VMULEUB,
|
{ ALTIVEC_BUILTIN_VEC_MULE, ALTIVEC_BUILTIN_VMULEUB,
|
||||||
RS6000_BTI_unsigned_V8HI, RS6000_BTI_unsigned_V16QI, RS6000_BTI_unsigned_V16QI, 0 },
|
RS6000_BTI_unsigned_V8HI, RS6000_BTI_unsigned_V16QI, RS6000_BTI_unsigned_V16QI, 0 },
|
||||||
{ ALTIVEC_BUILTIN_VEC_MULE, ALTIVEC_BUILTIN_VMULESB,
|
{ ALTIVEC_BUILTIN_VEC_MULE, ALTIVEC_BUILTIN_VMULESB,
|
||||||
|
|
@ -4683,6 +4675,57 @@ assignment for unaligned loads and stores");
|
||||||
warning (OPT_Wdeprecated, "vec_lvsr is deprecated for little endian; use \
|
warning (OPT_Wdeprecated, "vec_lvsr is deprecated for little endian; use \
|
||||||
assignment for unaligned loads and stores");
|
assignment for unaligned loads and stores");
|
||||||
|
|
||||||
|
if (fcode == ALTIVEC_BUILTIN_VEC_MUL)
|
||||||
|
{
|
||||||
|
/* vec_mul needs to be special cased because there are no instructions
|
||||||
|
for it for the {un}signed char, {un}signed short, and {un}signed int
|
||||||
|
types. */
|
||||||
|
if (nargs != 2)
|
||||||
|
{
|
||||||
|
error ("vec_mul only accepts 2 arguments");
|
||||||
|
return error_mark_node;
|
||||||
|
}
|
||||||
|
|
||||||
|
tree arg0 = (*arglist)[0];
|
||||||
|
tree arg0_type = TREE_TYPE (arg0);
|
||||||
|
tree arg1 = (*arglist)[1];
|
||||||
|
tree arg1_type = TREE_TYPE (arg1);
|
||||||
|
|
||||||
|
/* Both arguments must be vectors and the types must match. */
|
||||||
|
if (arg0_type != arg1_type)
|
||||||
|
goto bad;
|
||||||
|
if (TREE_CODE (arg0_type) != VECTOR_TYPE)
|
||||||
|
goto bad;
|
||||||
|
|
||||||
|
switch (TYPE_MODE (TREE_TYPE (arg0_type)))
|
||||||
|
{
|
||||||
|
case QImode:
|
||||||
|
case HImode:
|
||||||
|
case SImode:
|
||||||
|
case DImode:
|
||||||
|
case TImode:
|
||||||
|
{
|
||||||
|
/* For scalar types just use a multiply expression. */
|
||||||
|
return fold_build2_loc (loc, MULT_EXPR, TREE_TYPE (arg0),
|
||||||
|
arg0, arg1);
|
||||||
|
}
|
||||||
|
case SFmode:
|
||||||
|
{
|
||||||
|
/* For floats use the xvmulsp instruction directly. */
|
||||||
|
tree call = rs6000_builtin_decls[VSX_BUILTIN_XVMULSP];
|
||||||
|
return build_call_expr (call, 2, arg0, arg1);
|
||||||
|
}
|
||||||
|
case DFmode:
|
||||||
|
{
|
||||||
|
/* For doubles use the xvmuldp instruction directly. */
|
||||||
|
tree call = rs6000_builtin_decls[VSX_BUILTIN_XVMULDP];
|
||||||
|
return build_call_expr (call, 2, arg0, arg1);
|
||||||
|
}
|
||||||
|
/* Other types are errors. */
|
||||||
|
default:
|
||||||
|
goto bad;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (fcode == ALTIVEC_BUILTIN_VEC_CMPNE)
|
if (fcode == ALTIVEC_BUILTIN_VEC_CMPNE)
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -16573,6 +16573,8 @@ altivec_init_builtins (void)
|
||||||
ALTIVEC_BUILTIN_VEC_ADDEC);
|
ALTIVEC_BUILTIN_VEC_ADDEC);
|
||||||
def_builtin ("__builtin_vec_cmpne", opaque_ftype_opaque_opaque,
|
def_builtin ("__builtin_vec_cmpne", opaque_ftype_opaque_opaque,
|
||||||
ALTIVEC_BUILTIN_VEC_CMPNE);
|
ALTIVEC_BUILTIN_VEC_CMPNE);
|
||||||
|
def_builtin ("__builtin_vec_mul", opaque_ftype_opaque_opaque,
|
||||||
|
ALTIVEC_BUILTIN_VEC_MUL);
|
||||||
|
|
||||||
/* Cell builtins. */
|
/* Cell builtins. */
|
||||||
def_builtin ("__builtin_altivec_lvlx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVLX);
|
def_builtin ("__builtin_altivec_lvlx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVLX);
|
||||||
|
|
|
||||||
|
|
@ -1,3 +1,7 @@
|
||||||
|
2016-06-07 Bill Seurer <seurer@linux.vnet.ibm.com>
|
||||||
|
|
||||||
|
* gcc.target/powerpc/vec-mul.c: New test.
|
||||||
|
|
||||||
2016-06-07 David Malcolm <dmalcolm@redhat.com>
|
2016-06-07 David Malcolm <dmalcolm@redhat.com>
|
||||||
|
|
||||||
* gcc.dg/spellcheck-fields-2.c: New test case.
|
* gcc.dg/spellcheck-fields-2.c: New test case.
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,86 @@
|
||||||
|
/* { dg-do run { target { powerpc64*-*-* } } } */
|
||||||
|
/* { dg-require-effective-target powerpc_vsx_ok } */
|
||||||
|
/* { dg-options "-mvsx -O3" } */
|
||||||
|
|
||||||
|
/* Test that the vec_mul builtin works as expected. */
|
||||||
|
|
||||||
|
#include "altivec.h"
|
||||||
|
|
||||||
|
#define N 4096
|
||||||
|
|
||||||
|
void abort ();
|
||||||
|
|
||||||
|
#define define_test_functions(STYPE, NAMESUFFIX) \
|
||||||
|
\
|
||||||
|
STYPE result_##NAMESUFFIX[N]; \
|
||||||
|
STYPE operand1_##NAMESUFFIX[N]; \
|
||||||
|
STYPE operand2_##NAMESUFFIX[N]; \
|
||||||
|
STYPE expected_##NAMESUFFIX[N]; \
|
||||||
|
\
|
||||||
|
__attribute__((noinline)) void vector_tests_##NAMESUFFIX () \
|
||||||
|
{ \
|
||||||
|
int i; \
|
||||||
|
vector STYPE v1, v2, tmp; \
|
||||||
|
for (i = 0; i < N; i+=16/sizeof (STYPE)) \
|
||||||
|
{ \
|
||||||
|
/* result=operand1*operand2. */ \
|
||||||
|
v1 = vec_vsx_ld (0, &operand1_##NAMESUFFIX[i]); \
|
||||||
|
v2 = vec_vsx_ld (0, &operand2_##NAMESUFFIX[i]); \
|
||||||
|
\
|
||||||
|
tmp = vec_mul (v1, v2); \
|
||||||
|
vec_vsx_st (tmp, 0, &result_##NAMESUFFIX[i]); \
|
||||||
|
} \
|
||||||
|
} \
|
||||||
|
\
|
||||||
|
__attribute__((noinline)) void init_##NAMESUFFIX () \
|
||||||
|
{ \
|
||||||
|
int i; \
|
||||||
|
for (i = 0; i < N; ++i) \
|
||||||
|
{ \
|
||||||
|
result_##NAMESUFFIX[i] = 0; \
|
||||||
|
operand1_##NAMESUFFIX[i] = (i+1) % 31; \
|
||||||
|
operand2_##NAMESUFFIX[i] = (i*2) % 15; \
|
||||||
|
expected_##NAMESUFFIX[i] = operand1_##NAMESUFFIX[i] * \
|
||||||
|
operand2_##NAMESUFFIX[i]; \
|
||||||
|
} \
|
||||||
|
} \
|
||||||
|
\
|
||||||
|
__attribute__((noinline)) void verify_results_##NAMESUFFIX () \
|
||||||
|
{ \
|
||||||
|
int i; \
|
||||||
|
for (i = 0; i < N; ++i) \
|
||||||
|
{ \
|
||||||
|
if (result_##NAMESUFFIX[i] != expected_##NAMESUFFIX[i]) \
|
||||||
|
abort (); \
|
||||||
|
} \
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#define execute_test_functions(STYPE, NAMESUFFIX) \
|
||||||
|
{ \
|
||||||
|
init_##NAMESUFFIX (); \
|
||||||
|
vector_tests_##NAMESUFFIX (); \
|
||||||
|
verify_results_##NAMESUFFIX (); \
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
define_test_functions (signed int, si);
|
||||||
|
define_test_functions (unsigned int, ui);
|
||||||
|
define_test_functions (signed short, ss);
|
||||||
|
define_test_functions (unsigned short, us);
|
||||||
|
define_test_functions (signed char, sc);
|
||||||
|
define_test_functions (unsigned char, uc);
|
||||||
|
define_test_functions (float, f);
|
||||||
|
|
||||||
|
int main ()
|
||||||
|
{
|
||||||
|
execute_test_functions (signed int, si);
|
||||||
|
execute_test_functions (unsigned int, ui);
|
||||||
|
execute_test_functions (signed short, ss);
|
||||||
|
execute_test_functions (unsigned short, us);
|
||||||
|
execute_test_functions (signed char, sc);
|
||||||
|
execute_test_functions (unsigned char, uc);
|
||||||
|
execute_test_functions (float, f);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
Loading…
Reference in New Issue