[PATCH] rs6000, vector integer multiply/divide/modulo instructions

David Edelsohn dje.gcc@gmail.com
Sat Oct 31 13:28:02 GMT 2020


On Fri, Oct 30, 2020 at 4:07 PM Carl Love <cel@us.ibm.com> wrote:
>
> GCC maintainers:
>
> The following patch adds new builtins for the vector integer multiply,
> divide and modulo operations.  The builtins are:
> vec_mulh(), vec_div(), vec_dive(), vec_mod() for signed and unsigned
> integers and long long integers.  Support for signed and unsigned long
> long integers the exiting vec_mul() is added.  Note that the existing
> support for the vec_div()and vec_mul() builtins emulate the vector
> operations with multiple scalar instructions.  This patch adds support
> for these builtins to use the new vector instructions.
>
> The patch was compiled and tested on:
>
>   powerpc64le-unknown-linux-gnu (Power 9 LE)
>
> with no regressions. Additionally the new test case was compiled and
> executed by hand on Mambo to verify the test case passes.
>
> Please let me know if this patch is acceptable for mainline.  Thanks.
>
>                 Carl Love
>
> -------------------------------------------------------------
>
> 2020-10-30  Carl Love  <cel@us.ibm.com>
>
> gcc/
>         * config/rs6000/altivec.h (vec_mulh, vec_div, vec_dive, vec_mod): New
>         defines.
>         * config/rs6000/altivec.md (VIlong): Move define to file vector.md.
>         * config/rs6000/rs6000-builtin.def (VDIVES_V4SI, VDIVES_V2DI,
>         VDIVEU_V4SI, VDIVEU_V2DI, VDIVS_V4SI, VDIVS_V2DI, VDIVU_V4SI,
>         VDIVU_V2DI, VMODS_V2DI, VMODS_V4SI, VMODU_V2DI, VMODU_V4SI, VMULHS_V2DI,
>         VMULHS_V4SI, VMULHU_V2DI, VMULHU_V4SI, VMULLD_V2DI): Add builtin define.
>         (VMUL, VMULH, VDIVE, VMOD):  Add new BU_P10_OVERLOAD_2 definitions.
>         * config/rs6000/rs6000-call.c (VSX_BUILTIN_VEC_DIV, P10_BUILTIN_VEC_VDIVE,
>         P10_BUILTIN_VEC_VMOD, P10_BUILTIN_VEC_VMULH): New overloaded definitions.
>         (builtin_function_type)
>         [P10V_BUILTIN_VDIVEU_V4SI, P10V_BUILTIN_VDIVEU_V2DI,
>         P10V_BUILTIN_VDIVU_V4SI, P10V_BUILTIN_VDIVU_V2DI,
>         P10V_BUILTIN_VMODU_V2DI, P10V_BUILTIN_VMODU_V4SI, P10V_BUILTIN_VMULHU_V2DI,
>         P10V_BUILTIN_VMULHU_V4SI, P10V_BUILTIN_VMULLD_V2DI]: Add case statement
>         for builtins.
>         * config/rs6000/vector.md (UNSPEC_VDIVES, UNSPEC_VDIVEU, UNSPEC_VMULHS,
>         UNSPEC_VMULHU, UNSPEC_VMULLD): Add enum for UNSPECs.
>         (VIlong_char): Add define_mod_attribute.
>         (vdives_<mode>, vdiveu_<mode>, vdiv<mode>3, uuvdiv<mode>3, vdivs_<mode>,
>         vdivu_<mode>, vmods_<mode>, vmodu_<mode>, vmulhs_<mode>, vmulhu_<mode>,
>         mulv2di3): Add define_insn, mode is VIlong.
>         config/rs6000/vsx.md (vsx_mul_v2di, vsx_udiv_v2di): Add if (TARGET_POWER10)
>         statement.
>         * doc/extend.texi (vec_mulh, vec_mul, vec_div, vec_dive, vec_mod): Add
>         builtin descriptions.

> --- a/gcc/config/rs6000/vector.md
> +++ b/gcc/config/rs6000/vector.md

Hi, Carl

I thought that vector.md was a transfer vector for the patterns and
instructions were defined in vsx.md.  Why are the new insn patterns
defined in vector.md?

> +(define_insn "div<mode>3"
> +  [(set (match_operand:VIlong 0 "vsx_register_operand" "=v")
> +       (div:VIlong (match_operand:VIlong 1 "vsx_register_operand" "v")
> +                   (match_operand:VIlong 2 "vsx_register_operand" "v")))]
> +  "TARGET_POWER10"
> +  "vdivs<VIlong_char> %0,%1,%2"
> +  [(set_attr "type" "vecsimple")])
> +
> +(define_insn "udiv<mode>3"
> +  [(set (match_operand:VIlong 0 "vsx_register_operand" "=v")
> +       (udiv:VIlong (match_operand:VIlong 1 "vsx_register_operand" "v")
> +                   (match_operand:VIlong 2 "vsx_register_operand" "v")))]
> +  "TARGET_POWER10"
> +  "vdivu<VIlong_char> %0,%1,%2"
> +  [(set_attr "type" "vecsimple")])
> +
> +(define_insn "vdivs_<mode>"
> +  [(set (match_operand:VIlong 0 "vsx_register_operand" "=v")
> +       (div:VIlong (match_operand:VIlong 1 "vsx_register_operand" "v")
> +                   (match_operand:VIlong 2 "vsx_register_operand" "v")))]
> +  "TARGET_POWER10"
> +  "vdivs<VIlong_char> %0,%1,%2"
> +  [(set_attr "type" "vecsimple")])
> +
> +(define_insn "vdivu_<mode>"
> +  [(set (match_operand:VIlong 0 "vsx_register_operand" "=v")
> +       (udiv:VIlong (match_operand:VIlong 1 "vsx_register_operand" "v")
> +                    (match_operand:VIlong 2 "vsx_register_operand" "v")))]
> +  "TARGET_POWER10"
> +  "vdivu<VIlong_char> %0,%1,%2"
> +  [(set_attr "type" "vecsimple")])

Also, what is the reason to define div<mode>3 and udiv<mode>3, then
repeat the patterns for vdivs_<mode> and vdivu_<mode>?  Is there a
difference between the two patterns that I'm missing?  The new
builtins should be able to invoke the new named standard patterns.  Or
we really want an additional set of patterns that match the builtin
names?

The div<mode>3 and udiv<mode>3 patterns do not seem to be listed in
the ChangeLog.

Thanks, David


More information about the Gcc-patches mailing list