Commit effa992f authored by Richard Henderson's avatar Richard Henderson Committed by Peter Maydell
Browse files

target/arm: Convert sha1 and sha256 to gvec helpers



Do not yet convert the helpers to loop over opr_sz, but the
descriptor allows the vector tail to be cleared.  Which fixes
an existing bug vs SVE.

Signed-off-by: default avatarRichard Henderson <richard.henderson@linaro.org>
Message-id: 20200514212831.31248-5-richard.henderson@linaro.org
Reviewed-by: default avatarPeter Maydell <peter.maydell@linaro.org>
Signed-off-by: default avatarPeter Maydell <peter.maydell@linaro.org>
parent aaffebd6
Loading
Loading
Loading
Loading
+18 −6
Original line number Diff line number Diff line
@@ -303,7 +303,7 @@ void HELPER(crypto_sha1_3reg)(void *vd, void *vn, void *vm, uint32_t op)
    rd[1] = d.l[1];
}

void HELPER(crypto_sha1h)(void *vd, void *vm)
void HELPER(crypto_sha1h)(void *vd, void *vm, uint32_t desc)
{
    uint64_t *rd = vd;
    uint64_t *rm = vm;
@@ -314,9 +314,11 @@ void HELPER(crypto_sha1h)(void *vd, void *vm)

    rd[0] = m.l[0];
    rd[1] = m.l[1];

    clear_tail_16(vd, desc);
}

void HELPER(crypto_sha1su1)(void *vd, void *vm)
void HELPER(crypto_sha1su1)(void *vd, void *vm, uint32_t desc)
{
    uint64_t *rd = vd;
    uint64_t *rm = vm;
@@ -330,6 +332,8 @@ void HELPER(crypto_sha1su1)(void *vd, void *vm)

    rd[0] = d.l[0];
    rd[1] = d.l[1];

    clear_tail_16(vd, desc);
}

/*
@@ -357,7 +361,7 @@ static uint32_t s1(uint32_t x)
    return ror32(x, 17) ^ ror32(x, 19) ^ (x >> 10);
}

void HELPER(crypto_sha256h)(void *vd, void *vn, void *vm)
void HELPER(crypto_sha256h)(void *vd, void *vn, void *vm, uint32_t desc)
{
    uint64_t *rd = vd;
    uint64_t *rn = vn;
@@ -388,9 +392,11 @@ void HELPER(crypto_sha256h)(void *vd, void *vn, void *vm)

    rd[0] = d.l[0];
    rd[1] = d.l[1];

    clear_tail_16(vd, desc);
}

void HELPER(crypto_sha256h2)(void *vd, void *vn, void *vm)
void HELPER(crypto_sha256h2)(void *vd, void *vn, void *vm, uint32_t desc)
{
    uint64_t *rd = vd;
    uint64_t *rn = vn;
@@ -413,9 +419,11 @@ void HELPER(crypto_sha256h2)(void *vd, void *vn, void *vm)

    rd[0] = d.l[0];
    rd[1] = d.l[1];

    clear_tail_16(vd, desc);
}

void HELPER(crypto_sha256su0)(void *vd, void *vm)
void HELPER(crypto_sha256su0)(void *vd, void *vm, uint32_t desc)
{
    uint64_t *rd = vd;
    uint64_t *rm = vm;
@@ -429,9 +437,11 @@ void HELPER(crypto_sha256su0)(void *vd, void *vm)

    rd[0] = d.l[0];
    rd[1] = d.l[1];

    clear_tail_16(vd, desc);
}

void HELPER(crypto_sha256su1)(void *vd, void *vn, void *vm)
void HELPER(crypto_sha256su1)(void *vd, void *vn, void *vm, uint32_t desc)
{
    uint64_t *rd = vd;
    uint64_t *rn = vn;
@@ -447,6 +457,8 @@ void HELPER(crypto_sha256su1)(void *vd, void *vn, void *vm)

    rd[0] = d.l[0];
    rd[1] = d.l[1];

    clear_tail_16(vd, desc);
}

/*
+6 −6
Original line number Diff line number Diff line
@@ -514,13 +514,13 @@ DEF_HELPER_FLAGS_4(crypto_aese, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_3(crypto_aesmc, TCG_CALL_NO_RWG, void, ptr, ptr, i32)

DEF_HELPER_FLAGS_4(crypto_sha1_3reg, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_2(crypto_sha1h, TCG_CALL_NO_RWG, void, ptr, ptr)
DEF_HELPER_FLAGS_2(crypto_sha1su1, TCG_CALL_NO_RWG, void, ptr, ptr)
DEF_HELPER_FLAGS_3(crypto_sha1h, TCG_CALL_NO_RWG, void, ptr, ptr, i32)
DEF_HELPER_FLAGS_3(crypto_sha1su1, TCG_CALL_NO_RWG, void, ptr, ptr, i32)

DEF_HELPER_FLAGS_3(crypto_sha256h, TCG_CALL_NO_RWG, void, ptr, ptr, ptr)
DEF_HELPER_FLAGS_3(crypto_sha256h2, TCG_CALL_NO_RWG, void, ptr, ptr, ptr)
DEF_HELPER_FLAGS_2(crypto_sha256su0, TCG_CALL_NO_RWG, void, ptr, ptr)
DEF_HELPER_FLAGS_3(crypto_sha256su1, TCG_CALL_NO_RWG, void, ptr, ptr, ptr)
DEF_HELPER_FLAGS_4(crypto_sha256h, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(crypto_sha256h2, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_3(crypto_sha256su0, TCG_CALL_NO_RWG, void, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(crypto_sha256su1, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)

DEF_HELPER_FLAGS_4(crypto_sha512h, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(crypto_sha512h2, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
+6 −6
Original line number Diff line number Diff line
@@ -165,14 +165,14 @@ VPADD_3s 1111 001 0 0 . .. .... .... 1011 . . . 1 .... @3same_q0

VQRDMLAH_3s      1111 001 1 0 . .. .... .... 1011 ... 1 .... @3same

@3same_crypto    .... .... .... .... .... .... .... .... \
                 &3same vm=%vm_dp vn=%vn_dp vd=%vd_dp size=0 q=1

SHA1_3s          1111 001 0 0 . optype:2 .... .... 1100 . 1 . 0 .... \
                 vm=%vm_dp vn=%vn_dp vd=%vd_dp
SHA256H_3s       1111 001 1 0 . 00 .... .... 1100 . 1 . 0 .... \
                 vm=%vm_dp vn=%vn_dp vd=%vd_dp
SHA256H2_3s      1111 001 1 0 . 01 .... .... 1100 . 1 . 0 .... \
                 vm=%vm_dp vn=%vn_dp vd=%vd_dp
SHA256SU1_3s     1111 001 1 0 . 10 .... .... 1100 . 1 . 0 .... \
                 vm=%vm_dp vn=%vn_dp vd=%vd_dp
SHA256H_3s       1111 001 1 0 . 00 .... .... 1100 . 1 . 0 .... @3same_crypto
SHA256H2_3s      1111 001 1 0 . 01 .... .... 1100 . 1 . 0 .... @3same_crypto
SHA256SU1_3s     1111 001 1 0 . 10 .... .... 1100 . 1 . 0 .... @3same_crypto

VFMA_fp_3s       1111 001 0 0 . 0 . .... .... 1100 ... 1 .... @3same_fp
VFMS_fp_3s       1111 001 0 0 . 1 . .... .... 1100 ... 1 .... @3same_fp
+11 −21
Original line number Diff line number Diff line
@@ -13465,8 +13465,7 @@ static void disas_crypto_three_reg_sha(DisasContext *s, uint32_t insn)
    int rm = extract32(insn, 16, 5);
    int rn = extract32(insn, 5, 5);
    int rd = extract32(insn, 0, 5);
    CryptoThreeOpFn *genfn;
    TCGv_ptr tcg_rd_ptr, tcg_rn_ptr, tcg_rm_ptr;
    gen_helper_gvec_3 *genfn;
    bool feature;

    if (size != 0) {
@@ -13508,24 +13507,23 @@ static void disas_crypto_three_reg_sha(DisasContext *s, uint32_t insn)
        return;
    }

    tcg_rd_ptr = vec_full_reg_ptr(s, rd);
    tcg_rn_ptr = vec_full_reg_ptr(s, rn);
    tcg_rm_ptr = vec_full_reg_ptr(s, rm);

    if (genfn) {
        genfn(tcg_rd_ptr, tcg_rn_ptr, tcg_rm_ptr);
        gen_gvec_op3_ool(s, true, rd, rn, rm, 0, genfn);
    } else {
        TCGv_i32 tcg_opcode = tcg_const_i32(opcode);
        TCGv_ptr tcg_rd_ptr = vec_full_reg_ptr(s, rd);
        TCGv_ptr tcg_rn_ptr = vec_full_reg_ptr(s, rn);
        TCGv_ptr tcg_rm_ptr = vec_full_reg_ptr(s, rm);

        gen_helper_crypto_sha1_3reg(tcg_rd_ptr, tcg_rn_ptr,
                                    tcg_rm_ptr, tcg_opcode);
        tcg_temp_free_i32(tcg_opcode);
    }

        tcg_temp_free_i32(tcg_opcode);
        tcg_temp_free_ptr(tcg_rd_ptr);
        tcg_temp_free_ptr(tcg_rn_ptr);
        tcg_temp_free_ptr(tcg_rm_ptr);
    }
}

/* Crypto two-reg SHA
 *  31             24 23  22 21       17 16    12 11 10 9    5 4    0
@@ -13539,9 +13537,8 @@ static void disas_crypto_two_reg_sha(DisasContext *s, uint32_t insn)
    int opcode = extract32(insn, 12, 5);
    int rn = extract32(insn, 5, 5);
    int rd = extract32(insn, 0, 5);
    CryptoTwoOpFn *genfn;
    gen_helper_gvec_2 *genfn;
    bool feature;
    TCGv_ptr tcg_rd_ptr, tcg_rn_ptr;

    if (size != 0) {
        unallocated_encoding(s);
@@ -13574,14 +13571,7 @@ static void disas_crypto_two_reg_sha(DisasContext *s, uint32_t insn)
    if (!fp_access_check(s)) {
        return;
    }

    tcg_rd_ptr = vec_full_reg_ptr(s, rd);
    tcg_rn_ptr = vec_full_reg_ptr(s, rn);

    genfn(tcg_rd_ptr, tcg_rn_ptr);

    tcg_temp_free_ptr(tcg_rd_ptr);
    tcg_temp_free_ptr(tcg_rn_ptr);
    gen_gvec_op2_ool(s, true, rd, rn, 0, genfn);
}

static void gen_rax1_i64(TCGv_i64 d, TCGv_i64 n, TCGv_i64 m)
+19 −105
Original line number Diff line number Diff line
@@ -661,13 +661,15 @@ DO_3SAME_CMP(VCGE_S, TCG_COND_GE)
DO_3SAME_CMP(VCGE_U, TCG_COND_GEU)
DO_3SAME_CMP(VCEQ, TCG_COND_EQ)

static void gen_VMUL_p_3s(unsigned vece, uint32_t rd_ofs, uint32_t rn_ofs,
                           uint32_t rm_ofs, uint32_t oprsz, uint32_t maxsz)
{
    tcg_gen_gvec_3_ool(rd_ofs, rn_ofs, rm_ofs, oprsz, maxsz,
                       0, gen_helper_gvec_pmul_b);
#define WRAP_OOL_FN(WRAPNAME, FUNC)                                        \
    static void WRAPNAME(unsigned vece, uint32_t rd_ofs, uint32_t rn_ofs,  \
                         uint32_t rm_ofs, uint32_t oprsz, uint32_t maxsz)  \
    {                                                                      \
        tcg_gen_gvec_3_ool(rd_ofs, rn_ofs, rm_ofs, oprsz, maxsz, 0, FUNC); \
    }

WRAP_OOL_FN(gen_VMUL_p_3s, gen_helper_gvec_pmul_b)

static bool trans_VMUL_p_3s(DisasContext *s, arg_3same *a)
{
    if (a->size != 0) {
@@ -728,107 +730,19 @@ static bool trans_SHA1_3s(DisasContext *s, arg_SHA1_3s *a)
    return true;
}

static bool trans_SHA256H_3s(DisasContext *s, arg_SHA256H_3s *a)
{
    TCGv_ptr ptr1, ptr2, ptr3;

    if (!arm_dc_feature(s, ARM_FEATURE_NEON) ||
        !dc_isar_feature(aa32_sha2, s)) {
        return false;
    }

    /* UNDEF accesses to D16-D31 if they don't exist. */
    if (!dc_isar_feature(aa32_simd_r32, s) &&
        ((a->vd | a->vn | a->vm) & 0x10)) {
        return false;
    }

    if ((a->vn | a->vm | a->vd) & 1) {
        return false;
    }

    if (!vfp_access_check(s)) {
        return true;
    }

    ptr1 = vfp_reg_ptr(true, a->vd);
    ptr2 = vfp_reg_ptr(true, a->vn);
    ptr3 = vfp_reg_ptr(true, a->vm);
    gen_helper_crypto_sha256h(ptr1, ptr2, ptr3);
    tcg_temp_free_ptr(ptr1);
    tcg_temp_free_ptr(ptr2);
    tcg_temp_free_ptr(ptr3);

    return true;
}

static bool trans_SHA256H2_3s(DisasContext *s, arg_SHA256H2_3s *a)
{
    TCGv_ptr ptr1, ptr2, ptr3;

    if (!arm_dc_feature(s, ARM_FEATURE_NEON) ||
        !dc_isar_feature(aa32_sha2, s)) {
        return false;
    }

    /* UNDEF accesses to D16-D31 if they don't exist. */
    if (!dc_isar_feature(aa32_simd_r32, s) &&
        ((a->vd | a->vn | a->vm) & 0x10)) {
        return false;
    }

    if ((a->vn | a->vm | a->vd) & 1) {
        return false;
    }

    if (!vfp_access_check(s)) {
        return true;
    }

    ptr1 = vfp_reg_ptr(true, a->vd);
    ptr2 = vfp_reg_ptr(true, a->vn);
    ptr3 = vfp_reg_ptr(true, a->vm);
    gen_helper_crypto_sha256h2(ptr1, ptr2, ptr3);
    tcg_temp_free_ptr(ptr1);
    tcg_temp_free_ptr(ptr2);
    tcg_temp_free_ptr(ptr3);

    return true;
}

static bool trans_SHA256SU1_3s(DisasContext *s, arg_SHA256SU1_3s *a)
{
    TCGv_ptr ptr1, ptr2, ptr3;

    if (!arm_dc_feature(s, ARM_FEATURE_NEON) ||
        !dc_isar_feature(aa32_sha2, s)) {
        return false;
    }

    /* UNDEF accesses to D16-D31 if they don't exist. */
    if (!dc_isar_feature(aa32_simd_r32, s) &&
        ((a->vd | a->vn | a->vm) & 0x10)) {
        return false;
    }

    if ((a->vn | a->vm | a->vd) & 1) {
        return false;
    }

    if (!vfp_access_check(s)) {
        return true;
#define DO_SHA2(NAME, FUNC)                                             \
    WRAP_OOL_FN(gen_##NAME##_3s, FUNC)                                  \
    static bool trans_##NAME##_3s(DisasContext *s, arg_3same *a)        \
    {                                                                   \
        if (!dc_isar_feature(aa32_sha2, s)) {                           \
            return false;                                               \
        }                                                               \
        return do_3same(s, a, gen_##NAME##_3s);                         \
    }

    ptr1 = vfp_reg_ptr(true, a->vd);
    ptr2 = vfp_reg_ptr(true, a->vn);
    ptr3 = vfp_reg_ptr(true, a->vm);
    gen_helper_crypto_sha256su1(ptr1, ptr2, ptr3);
    tcg_temp_free_ptr(ptr1);
    tcg_temp_free_ptr(ptr2);
    tcg_temp_free_ptr(ptr3);

    return true;
}
DO_SHA2(SHA256H, gen_helper_crypto_sha256h)
DO_SHA2(SHA256H2, gen_helper_crypto_sha256h2)
DO_SHA2(SHA256SU1, gen_helper_crypto_sha256su1)

#define DO_3SAME_64(INSN, FUNC)                                         \
    static void gen_##INSN##_3s(unsigned vece, uint32_t rd_ofs,         \
Loading