Commit d6750811 authored by Richard Henderson's avatar Richard Henderson
Browse files

tcg/ppc: Add support for vector add/subtract



Add support for vector add/subtract using Altivec instructions:
VADDUBM, VADDUHM, VADDUWM, VSUBUBM, VSUBUHM, VSUBUWM.

Tested-by: default avatarMark Cave-Ayland <mark.cave-ayland@ilande.co.uk>
Reviewed-by: default avatarAleksandar Markovic <amarkovic@wavecomp.com>
Signed-off-by: default avatarRichard Henderson <richard.henderson@linaro.org>
Signed-off-by: default avatarAleksandar Markovic <amarkovic@wavecomp.com>
parent e2382972
Loading
Loading
Loading
Loading
+20 −0
Original line number Diff line number Diff line
@@ -471,6 +471,14 @@ static int tcg_target_const_match(tcg_target_long val, TCGType type,
#define STVX       XO31(231)
#define STVEWX     XO31(199)

#define VADDUBM    VX4(0)
#define VADDUHM    VX4(64)
#define VADDUWM    VX4(128)

#define VSUBUBM    VX4(1024)
#define VSUBUHM    VX4(1088)
#define VSUBUWM    VX4(1152)

#define VMAXSB     VX4(258)
#define VMAXSH     VX4(322)
#define VMAXSW     VX4(386)
@@ -2830,6 +2838,8 @@ int tcg_can_emit_vec_op(TCGOpcode opc, TCGType type, unsigned vece)
    case INDEX_op_andc_vec:
    case INDEX_op_not_vec:
        return 1;
    case INDEX_op_add_vec:
    case INDEX_op_sub_vec:
    case INDEX_op_smax_vec:
    case INDEX_op_smin_vec:
    case INDEX_op_umax_vec:
@@ -2930,6 +2940,8 @@ static void tcg_out_vec_op(TCGContext *s, TCGOpcode opc,
                           const TCGArg *args, const int *const_args)
{
    static const uint32_t
        add_op[4] = { VADDUBM, VADDUHM, VADDUWM, 0 },
        sub_op[4] = { VSUBUBM, VSUBUHM, VSUBUWM, 0 },
        eq_op[4]  = { VCMPEQUB, VCMPEQUH, VCMPEQUW, 0 },
        gts_op[4] = { VCMPGTSB, VCMPGTSH, VCMPGTSW, 0 },
        gtu_op[4] = { VCMPGTUB, VCMPGTUH, VCMPGTUW, 0 },
@@ -2953,6 +2965,12 @@ static void tcg_out_vec_op(TCGContext *s, TCGOpcode opc,
        tcg_out_dupm_vec(s, type, vece, a0, a1, a2);
        return;

    case INDEX_op_add_vec:
        insn = add_op[vece];
        break;
    case INDEX_op_sub_vec:
        insn = sub_op[vece];
        break;
    case INDEX_op_smin_vec:
        insn = smin_op[vece];
        break;
@@ -3251,6 +3269,8 @@ static const TCGTargetOpDef *tcg_target_op_def(TCGOpcode op)
        return (TCG_TARGET_REG_BITS == 64 ? &S_S
                : TARGET_LONG_BITS == 32 ? &S_S_S : &S_S_S_S);

    case INDEX_op_add_vec:
    case INDEX_op_sub_vec:
    case INDEX_op_and_vec:
    case INDEX_op_or_vec:
    case INDEX_op_xor_vec: