diff --git a/qemu/target-arm/cpu.h b/qemu/target-arm/cpu.h index 0c39b783..bd073c9b 100644 --- a/qemu/target-arm/cpu.h +++ b/qemu/target-arm/cpu.h @@ -1537,6 +1537,33 @@ static inline void cpu_get_tb_cpu_state(CPUARMState *env, target_ulong *pc, *cs_base = 0; } +/** + * aa32_vfp_dreg: + * Return a pointer to the Dn register within env in 32-bit mode. + */ +static inline uint64_t *aa32_vfp_dreg(CPUARMState *env, unsigned regno) +{ + return &env->vfp.regs[regno]; +} + +/** + * aa32_vfp_qreg: + * Return a pointer to the Qn register within env in 32-bit mode. + */ +static inline uint64_t *aa32_vfp_qreg(CPUARMState *env, unsigned regno) +{ + return &env->vfp.regs[2 * regno]; +} + +/** + * aa64_vfp_qreg: + * Return a pointer to the Qn register within env in 64-bit mode. + */ +static inline uint64_t *aa64_vfp_qreg(CPUARMState *env, unsigned regno) +{ + return &env->vfp.regs[2 * regno]; +} + #include "exec/exec-all.h" static inline void cpu_pc_from_tb(CPUARMState *env, TranslationBlock *tb) diff --git a/qemu/target-arm/helper-a64.c b/qemu/target-arm/helper-a64.c index 640585f9..02ecd378 100644 --- a/qemu/target-arm/helper-a64.c +++ b/qemu/target-arm/helper-a64.c @@ -172,13 +172,14 @@ uint64_t HELPER(simd_tbl)(CPUARMState *env, uint64_t result, uint64_t indices, if (index < 16 * numregs) { /* Convert index (a byte offset into the virtual table * which is a series of 128-bit vectors concatenated) - * into the correct vfp.regs[] element plus a bit offset + * into the correct register element plus a bit offset * into that element, bearing in mind that the table * can wrap around from V31 to V0. */ int elt = (rn * 2 + (index >> 3)) % 64; int bitidx = (index & 7) * 8; - uint64_t val = extract64(env->vfp.regs[elt], bitidx, 8); + uint64_t *q = aa64_vfp_qreg(env, elt >> 1); + uint64_t val = extract64(q[elt & 1], bitidx, 8); result = deposit64(result, shift, 8, val); } diff --git a/qemu/target-arm/translate-a64.c b/qemu/target-arm/translate-a64.c index 4a169ad4..ac68a4b9 100644 --- a/qemu/target-arm/translate-a64.c +++ b/qemu/target-arm/translate-a64.c @@ -143,15 +143,12 @@ void aarch64_cpu_dump_state(CPUState *cs, FILE *f, if (flags & CPU_DUMP_FPU) { int numvfpregs = 32; - for (i = 0; i < numvfpregs; i += 2) { - uint64_t vlo = env->vfp.regs[i * 2]; - uint64_t vhi = env->vfp.regs[(i * 2) + 1]; - cpu_fprintf(f, "q%02d=%016" PRIx64 ":%016" PRIx64 " ", - i, vhi, vlo); - vlo = env->vfp.regs[(i + 1) * 2]; - vhi = env->vfp.regs[((i + 1) * 2) + 1]; - cpu_fprintf(f, "q%02d=%016" PRIx64 ":%016" PRIx64 "\n", - i + 1, vhi, vlo); + for (i = 0; i < numvfpregs; i++) { + uint64_t *q = aa64_vfp_qreg(env, i); + uint64_t vlo = q[0]; + uint64_t vhi = q[1]; + cpu_fprintf(f, "q%02d=%016" PRIx64 ":%016" PRIx64 "%c", + i, vhi, vlo, (i & 1 ? '\n' : ' ')); } cpu_fprintf(f, "FPCR: %08x FPSR: %08x\n", vfp_get_fpcr(env), vfp_get_fpsr(env)); @@ -434,19 +431,13 @@ static inline int vec_reg_offset(DisasContext *s, int regno, */ static inline int fp_reg_offset(DisasContext *s, int regno, TCGMemOp size) { - int offs = offsetof(CPUARMState, vfp.regs[regno * 2]); -#ifdef HOST_WORDS_BIGENDIAN - offs += (8 - (1 << size)); -#endif - assert_fp_access_checked(s); - return offs; + return vec_reg_offset(s, regno, 0, size); } /* Offset of the high half of the 128 bit vector Qn */ static inline int fp_reg_hi_offset(DisasContext *s, int regno) { - assert_fp_access_checked(s); - return offsetof(CPUARMState, vfp.regs[regno * 2 + 1]); + return vec_reg_offset(s, regno, 1, MO_64); } /* Convenience accessors for reading and writing single and double diff --git a/qemu/target-arm/translate.c b/qemu/target-arm/translate.c index 017bd47b..a6660b1c 100644 --- a/qemu/target-arm/translate.c +++ b/qemu/target-arm/translate.c @@ -1298,14 +1298,16 @@ static inline void gen_vfp_st(DisasContext *s, int dp, TCGv_i32 addr) static inline long vfp_reg_offset (int dp, int reg) { - if (dp) + if (dp) { return offsetof(CPUARMState, vfp.regs[reg]); - else if (reg & 1) { - return offsetof(CPUARMState, vfp.regs[reg >> 1]) - + offsetof(CPU_DoubleU, l.upper); } else { - return offsetof(CPUARMState, vfp.regs[reg >> 1]) - + offsetof(CPU_DoubleU, l.lower); + long ofs = offsetof(CPUARMState, vfp.regs[reg >> 1]); + if (reg & 1) { + ofs += offsetof(CPU_DoubleU, l.upper); + } else { + ofs += offsetof(CPU_DoubleU, l.lower); + } + return ofs; } } @@ -11731,7 +11733,7 @@ void arm_cpu_dump_state(CPUState *cs, FILE *f, fprintf_function cpu_fprintf, numvfpregs += 16; } for (i = 0; i < numvfpregs; i++) { - uint64_t v = env->vfp.regs[i]; + uint64_t v = *aa32_vfp_dreg(env, i); cpu_fprintf(f, "s%02d=%08x s%02d=%08x d%02d=%016" PRIx64 "\n", i * 2, (uint32_t)v, i * 2 + 1, (uint32_t)(v >> 32),