Commit 5cc7a54c authored by Peter Maydell's avatar Peter Maydell
Browse files

Merge remote-tracking branch 'remotes/rth/tags/pull-tcg-20200602' into staging



Vector rotate support
Signal handling support for NetBSD arm/aarch64

# gpg: Signature made Tue 02 Jun 2020 17:43:05 BST
# gpg:                using RSA key 7A481E78868B4DB6A85A05C064DF38E8AF7E215F
# gpg:                issuer "richard.henderson@linaro.org"
# gpg: Good signature from "Richard Henderson <richard.henderson@linaro.org>" [full]
# Primary key fingerprint: 7A48 1E78 868B 4DB6 A85A  05C0 64DF 38E8 AF7E 215F

* remotes/rth/tags/pull-tcg-20200602:
  accel/tcg: Provide a NetBSD specific aarch64 cpu_signal_handler
  accel/tcg: Adjust cpu_signal_handler for NetBSD/arm
  tcg: Improve move ops in liveness_pass_2
  target/s390x: Use tcg_gen_gvec_rotl{i,s,v}
  target/ppc: Use tcg_gen_gvec_rotlv
  tcg/ppc: Implement INDEX_op_rot[lr]v_vec
  tcg/aarch64: Implement INDEX_op_rotl{i,v}_vec
  tcg/i386: Implement INDEX_op_rotl{i,s,v}_vec
  tcg: Implement gvec support for rotate by scalar
  tcg: Remove expansion to shift by vector from do_shifts
  tcg: Implement gvec support for rotate by vector
  tcg: Implement gvec support for rotate by immediate

Signed-off-by: default avatarPeter Maydell <peter.maydell@linaro.org>
parents 98d59d5d 71b04329
Loading
Loading
Loading
Loading
+144 −0
Original line number Diff line number Diff line
@@ -716,6 +716,54 @@ void HELPER(gvec_sar64i)(void *d, void *a, uint32_t desc)
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotl8i)(void *d, void *a, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    int shift = simd_data(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint8_t)) {
        *(uint8_t *)(d + i) = rol8(*(uint8_t *)(a + i), shift);
    }
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotl16i)(void *d, void *a, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    int shift = simd_data(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint16_t)) {
        *(uint16_t *)(d + i) = rol16(*(uint16_t *)(a + i), shift);
    }
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotl32i)(void *d, void *a, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    int shift = simd_data(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint32_t)) {
        *(uint32_t *)(d + i) = rol32(*(uint32_t *)(a + i), shift);
    }
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotl64i)(void *d, void *a, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    int shift = simd_data(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint64_t)) {
        *(uint64_t *)(d + i) = rol64(*(uint64_t *)(a + i), shift);
    }
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_shl8v)(void *d, void *a, void *b, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
@@ -860,6 +908,102 @@ void HELPER(gvec_sar64v)(void *d, void *a, void *b, uint32_t desc)
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotl8v)(void *d, void *a, void *b, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint8_t)) {
        uint8_t sh = *(uint8_t *)(b + i) & 7;
        *(uint8_t *)(d + i) = rol8(*(uint8_t *)(a + i), sh);
    }
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotl16v)(void *d, void *a, void *b, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint16_t)) {
        uint8_t sh = *(uint16_t *)(b + i) & 15;
        *(uint16_t *)(d + i) = rol16(*(uint16_t *)(a + i), sh);
    }
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotl32v)(void *d, void *a, void *b, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint32_t)) {
        uint8_t sh = *(uint32_t *)(b + i) & 31;
        *(uint32_t *)(d + i) = rol32(*(uint32_t *)(a + i), sh);
    }
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotl64v)(void *d, void *a, void *b, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint64_t)) {
        uint8_t sh = *(uint64_t *)(b + i) & 63;
        *(uint64_t *)(d + i) = rol64(*(uint64_t *)(a + i), sh);
    }
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotr8v)(void *d, void *a, void *b, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint8_t)) {
        uint8_t sh = *(uint8_t *)(b + i) & 7;
        *(uint8_t *)(d + i) = ror8(*(uint8_t *)(a + i), sh);
    }
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotr16v)(void *d, void *a, void *b, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint16_t)) {
        uint8_t sh = *(uint16_t *)(b + i) & 15;
        *(uint16_t *)(d + i) = ror16(*(uint16_t *)(a + i), sh);
    }
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotr32v)(void *d, void *a, void *b, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint32_t)) {
        uint8_t sh = *(uint32_t *)(b + i) & 31;
        *(uint32_t *)(d + i) = ror32(*(uint32_t *)(a + i), sh);
    }
    clear_high(d, oprsz, desc);
}

void HELPER(gvec_rotr64v)(void *d, void *a, void *b, uint32_t desc)
{
    intptr_t oprsz = simd_oprsz(desc);
    intptr_t i;

    for (i = 0; i < oprsz; i += sizeof(uint64_t)) {
        uint8_t sh = *(uint64_t *)(b + i) & 63;
        *(uint64_t *)(d + i) = ror64(*(uint64_t *)(a + i), sh);
    }
    clear_high(d, oprsz, desc);
}

#define DO_CMP1(NAME, TYPE, OP)                                            \
void HELPER(NAME)(void *d, void *a, void *b, uint32_t desc)                \
{                                                                          \
+15 −0
Original line number Diff line number Diff line
@@ -259,6 +259,11 @@ DEF_HELPER_FLAGS_3(gvec_sar16i, TCG_CALL_NO_RWG, void, ptr, ptr, i32)
DEF_HELPER_FLAGS_3(gvec_sar32i, TCG_CALL_NO_RWG, void, ptr, ptr, i32)
DEF_HELPER_FLAGS_3(gvec_sar64i, TCG_CALL_NO_RWG, void, ptr, ptr, i32)

DEF_HELPER_FLAGS_3(gvec_rotl8i, TCG_CALL_NO_RWG, void, ptr, ptr, i32)
DEF_HELPER_FLAGS_3(gvec_rotl16i, TCG_CALL_NO_RWG, void, ptr, ptr, i32)
DEF_HELPER_FLAGS_3(gvec_rotl32i, TCG_CALL_NO_RWG, void, ptr, ptr, i32)
DEF_HELPER_FLAGS_3(gvec_rotl64i, TCG_CALL_NO_RWG, void, ptr, ptr, i32)

DEF_HELPER_FLAGS_4(gvec_shl8v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_shl16v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_shl32v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
@@ -274,6 +279,16 @@ DEF_HELPER_FLAGS_4(gvec_sar16v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_sar32v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_sar64v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)

DEF_HELPER_FLAGS_4(gvec_rotl8v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_rotl16v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_rotl32v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_rotl64v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)

DEF_HELPER_FLAGS_4(gvec_rotr8v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_rotr16v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_rotr32v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_rotr64v, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)

DEF_HELPER_FLAGS_4(gvec_eq8, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_eq16, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_4(gvec_eq32, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
+40 −3
Original line number Diff line number Diff line
@@ -517,6 +517,7 @@ int cpu_signal_handler(int host_signum, void *pinfo,

#if defined(__NetBSD__)
#include <ucontext.h>
#include <sys/siginfo.h>
#endif

int cpu_signal_handler(int host_signum, void *pinfo,
@@ -525,10 +526,12 @@ int cpu_signal_handler(int host_signum, void *pinfo,
    siginfo_t *info = pinfo;
#if defined(__NetBSD__)
    ucontext_t *uc = puc;
    siginfo_t *si = pinfo;
#else
    ucontext_t *uc = puc;
#endif
    unsigned long pc;
    uint32_t fsr;
    int is_write;

#if defined(__NetBSD__)
@@ -539,15 +542,48 @@ int cpu_signal_handler(int host_signum, void *pinfo,
    pc = uc->uc_mcontext.arm_pc;
#endif

    /* error_code is the FSR value, in which bit 11 is WnR (assuming a v6 or
     * later processor; on v5 we will always report this as a read).
#ifdef __NetBSD__
    fsr = si->si_trap;
#else
    fsr = uc->uc_mcontext.error_code;
#endif
    /*
     * In the FSR, bit 11 is WnR, assuming a v6 or
     * later processor.  On v5 we will always report
     * this as a read, which will fail later.
     */
    is_write = extract32(uc->uc_mcontext.error_code, 11, 1);
    is_write = extract32(fsr, 11, 1);
    return handle_cpu_signal(pc, info, is_write, &uc->uc_sigmask);
}

#elif defined(__aarch64__)

#if defined(__NetBSD__)

#include <ucontext.h>
#include <sys/siginfo.h>

int cpu_signal_handler(int host_signum, void *pinfo, void *puc)
{
    ucontext_t *uc = puc;
    siginfo_t *si = pinfo;
    unsigned long pc;
    int is_write;
    uint32_t esr;

    pc = uc->uc_mcontext.__gregs[_REG_PC];
    esr = si->si_trap;

    /*
     * siginfo_t::si_trap is the ESR value, for data aborts ESR.EC
     * is 0b10010x: then bit 6 is the WnR bit
     */
    is_write = extract32(esr, 27, 5) == 0x12 && extract32(esr, 6, 1) == 1;
    return handle_cpu_signal(pc, si, is_write, &uc->uc_sigmask);
}

#else

#ifndef ESR_MAGIC
/* Pre-3.16 kernel headers don't have these, so provide fallback definitions */
#define ESR_MAGIC 0x45535201
@@ -610,6 +646,7 @@ int cpu_signal_handler(int host_signum, void *pinfo, void *puc)
    }
    return handle_cpu_signal(pc, info, is_write, &uc->uc_sigmask);
}
#endif

#elif defined(__s390__)

+12 −0
Original line number Diff line number Diff line
@@ -334,6 +334,10 @@ void tcg_gen_gvec_shri(unsigned vece, uint32_t dofs, uint32_t aofs,
                       int64_t shift, uint32_t oprsz, uint32_t maxsz);
void tcg_gen_gvec_sari(unsigned vece, uint32_t dofs, uint32_t aofs,
                       int64_t shift, uint32_t oprsz, uint32_t maxsz);
void tcg_gen_gvec_rotli(unsigned vece, uint32_t dofs, uint32_t aofs,
                        int64_t shift, uint32_t oprsz, uint32_t maxsz);
void tcg_gen_gvec_rotri(unsigned vece, uint32_t dofs, uint32_t aofs,
                        int64_t shift, uint32_t oprsz, uint32_t maxsz);

void tcg_gen_gvec_shls(unsigned vece, uint32_t dofs, uint32_t aofs,
                       TCGv_i32 shift, uint32_t oprsz, uint32_t maxsz);
@@ -341,6 +345,8 @@ void tcg_gen_gvec_shrs(unsigned vece, uint32_t dofs, uint32_t aofs,
                       TCGv_i32 shift, uint32_t oprsz, uint32_t maxsz);
void tcg_gen_gvec_sars(unsigned vece, uint32_t dofs, uint32_t aofs,
                       TCGv_i32 shift, uint32_t oprsz, uint32_t maxsz);
void tcg_gen_gvec_rotls(unsigned vece, uint32_t dofs, uint32_t aofs,
                        TCGv_i32 shift, uint32_t oprsz, uint32_t maxsz);

/*
 * Perform vector shift by vector element, modulo the element size.
@@ -352,6 +358,10 @@ void tcg_gen_gvec_shrv(unsigned vece, uint32_t dofs, uint32_t aofs,
                       uint32_t bofs, uint32_t oprsz, uint32_t maxsz);
void tcg_gen_gvec_sarv(unsigned vece, uint32_t dofs, uint32_t aofs,
                       uint32_t bofs, uint32_t oprsz, uint32_t maxsz);
void tcg_gen_gvec_rotlv(unsigned vece, uint32_t dofs, uint32_t aofs,
                        uint32_t bofs, uint32_t oprsz, uint32_t maxsz);
void tcg_gen_gvec_rotrv(unsigned vece, uint32_t dofs, uint32_t aofs,
                        uint32_t bofs, uint32_t oprsz, uint32_t maxsz);

void tcg_gen_gvec_cmp(TCGCond cond, unsigned vece, uint32_t dofs,
                      uint32_t aofs, uint32_t bofs,
@@ -388,5 +398,7 @@ void tcg_gen_vec_shr8i_i64(TCGv_i64 d, TCGv_i64 a, int64_t);
void tcg_gen_vec_shr16i_i64(TCGv_i64 d, TCGv_i64 a, int64_t);
void tcg_gen_vec_sar8i_i64(TCGv_i64 d, TCGv_i64 a, int64_t);
void tcg_gen_vec_sar16i_i64(TCGv_i64 d, TCGv_i64 a, int64_t);
void tcg_gen_vec_rotl8i_i64(TCGv_i64 d, TCGv_i64 a, int64_t c);
void tcg_gen_vec_rotl16i_i64(TCGv_i64 d, TCGv_i64 a, int64_t c);

#endif
+5 −0
Original line number Diff line number Diff line
@@ -999,14 +999,19 @@ void tcg_gen_umax_vec(unsigned vece, TCGv_vec r, TCGv_vec a, TCGv_vec b);
void tcg_gen_shli_vec(unsigned vece, TCGv_vec r, TCGv_vec a, int64_t i);
void tcg_gen_shri_vec(unsigned vece, TCGv_vec r, TCGv_vec a, int64_t i);
void tcg_gen_sari_vec(unsigned vece, TCGv_vec r, TCGv_vec a, int64_t i);
void tcg_gen_rotli_vec(unsigned vece, TCGv_vec r, TCGv_vec a, int64_t i);
void tcg_gen_rotri_vec(unsigned vece, TCGv_vec r, TCGv_vec a, int64_t i);

void tcg_gen_shls_vec(unsigned vece, TCGv_vec r, TCGv_vec a, TCGv_i32 s);
void tcg_gen_shrs_vec(unsigned vece, TCGv_vec r, TCGv_vec a, TCGv_i32 s);
void tcg_gen_sars_vec(unsigned vece, TCGv_vec r, TCGv_vec a, TCGv_i32 s);
void tcg_gen_rotls_vec(unsigned vece, TCGv_vec r, TCGv_vec a, TCGv_i32 s);

void tcg_gen_shlv_vec(unsigned vece, TCGv_vec r, TCGv_vec a, TCGv_vec s);
void tcg_gen_shrv_vec(unsigned vece, TCGv_vec r, TCGv_vec a, TCGv_vec s);
void tcg_gen_sarv_vec(unsigned vece, TCGv_vec r, TCGv_vec a, TCGv_vec s);
void tcg_gen_rotlv_vec(unsigned vece, TCGv_vec r, TCGv_vec a, TCGv_vec s);
void tcg_gen_rotrv_vec(unsigned vece, TCGv_vec r, TCGv_vec a, TCGv_vec s);

void tcg_gen_cmp_vec(TCGCond cond, unsigned vece, TCGv_vec r,
                     TCGv_vec a, TCGv_vec b);
Loading