@@ -258,8 +258,8 @@ static void save_user_regs(CPUPPCState *env, struct target_mcontext *frame)
/* Save Altivec registers if necessary. */
if (env->insns_flags & PPC_ALTIVEC) {
uint32_t *vrsave;
- for (i = 0; i < ARRAY_SIZE(env->avr); i++) {
- ppc_avr_t *avr = &env->avr[i];
+ for (i = 0; i < 32; i++) {
+ ppc_avr_t *avr = &env->vsr[32 + i];
ppc_avr_t *vreg = (ppc_avr_t *)&frame->mc_vregs.altivec[i];
__put_user(avr->u64[PPC_VEC_HI], &vreg->u64[0]);
@@ -281,15 +281,15 @@ static void save_user_regs(CPUPPCState *env, struct target_mcontext *frame)
/* Save VSX second halves */
if (env->insns_flags2 & PPC2_VSX) {
uint64_t *vsregs = (uint64_t *)&frame->mc_vregs.altivec[34];
- for (i = 0; i < ARRAY_SIZE(env->vsr); i++) {
- __put_user(env->vsr[i], &vsregs[i]);
+ for (i = 0; i < 32; i++) {
+ __put_user(env->vsr[i].u64[1], &vsregs[i]);
}
}
/* Save floating point registers. */
if (env->insns_flags & PPC_FLOAT) {
- for (i = 0; i < ARRAY_SIZE(env->fpr); i++) {
- __put_user(env->fpr[i], &frame->mc_fregs[i]);
+ for (i = 0; i < 32; i++) {
+ __put_user(env->vsr[i].u64[0], &frame->mc_fregs[i]);
}
__put_user((uint64_t) env->fpscr, &frame->mc_fregs[32]);
}
@@ -373,8 +373,8 @@ static void restore_user_regs(CPUPPCState *env,
#else
v_regs = (ppc_avr_t *)frame->mc_vregs.altivec;
#endif
- for (i = 0; i < ARRAY_SIZE(env->avr); i++) {
- ppc_avr_t *avr = &env->avr[i];
+ for (i = 0; i < 32; i++) {
+ ppc_avr_t *avr = &env->vsr[32 + i];
ppc_avr_t *vreg = &v_regs[i];
__get_user(avr->u64[PPC_VEC_HI], &vreg->u64[0]);
@@ -393,16 +393,16 @@ static void restore_user_regs(CPUPPCState *env,
/* Restore VSX second halves */
if (env->insns_flags2 & PPC2_VSX) {
uint64_t *vsregs = (uint64_t *)&frame->mc_vregs.altivec[34];
- for (i = 0; i < ARRAY_SIZE(env->vsr); i++) {
- __get_user(env->vsr[i], &vsregs[i]);
+ for (i = 0; i < 32; i++) {
+ __get_user(env->vsr[i].u64[1], &vsregs[i]);
}
}
/* Restore floating point registers. */
if (env->insns_flags & PPC_FLOAT) {
uint64_t fpscr;
- for (i = 0; i < ARRAY_SIZE(env->fpr); i++) {
- __get_user(env->fpr[i], &frame->mc_fregs[i]);
+ for (i = 0; i < 32; i++) {
+ __get_user(env->vsr[i].u64[0], &frame->mc_fregs[i]);
}
__get_user(fpscr, &frame->mc_fregs[32]);
env->fpscr = (uint32_t) fpscr;
@@ -140,7 +140,7 @@ static void ppc_write_elf_fpregset(NoteFuncArg *arg, PowerPCCPU *cpu)
memset(fpregset, 0, sizeof(*fpregset));
for (i = 0; i < 32; i++) {
- fpregset->fpr[i] = cpu_to_dump64(s, cpu->env.fpr[i]);
+ fpregset->fpr[i] = cpu_to_dump64(s, cpu->env.vsr[i].u64[0]);
}
fpregset->fpscr = cpu_to_dump_reg(s, cpu->env.fpscr);
}
@@ -166,11 +166,11 @@ static void ppc_write_elf_vmxregset(NoteFuncArg *arg, PowerPCCPU *cpu)
#endif
if (needs_byteswap) {
- vmxregset->avr[i].u64[0] = bswap64(cpu->env.avr[i].u64[1]);
- vmxregset->avr[i].u64[1] = bswap64(cpu->env.avr[i].u64[0]);
+ vmxregset->avr[i].u64[0] = bswap64(cpu->env.vsr[32 + i].u64[1]);
+ vmxregset->avr[i].u64[1] = bswap64(cpu->env.vsr[32 + i].u64[0]);
} else {
- vmxregset->avr[i].u64[0] = cpu->env.avr[i].u64[0];
- vmxregset->avr[i].u64[1] = cpu->env.avr[i].u64[1];
+ vmxregset->avr[i].u64[0] = cpu->env.vsr[32 + i].u64[0];
+ vmxregset->avr[i].u64[1] = cpu->env.vsr[32 + i].u64[1];
}
}
vmxregset->vscr.u32[3] = cpu_to_dump32(s, cpu->env.vscr);
@@ -188,7 +188,7 @@ static void ppc_write_elf_vsxregset(NoteFuncArg *arg, PowerPCCPU *cpu)
memset(vsxregset, 0, sizeof(*vsxregset));
for (i = 0; i < 32; i++) {
- vsxregset->vsr[i] = cpu_to_dump64(s, cpu->env.vsr[i]);
+ vsxregset->vsr[i] = cpu_to_dump64(s, cpu->env.vsr[i].u64[1]);
}
}
@@ -1016,8 +1016,6 @@ struct CPUPPCState {
/* Floating point execution context */
float_status fp_status;
- /* floating point registers */
- float64 fpr[32];
/* floating point status and control register */
target_ulong fpscr;
@@ -1067,11 +1065,10 @@ struct CPUPPCState {
/* Special purpose registers */
target_ulong spr[1024];
ppc_spr_t spr_cb[1024];
- /* Altivec registers */
- ppc_avr_t avr[32];
+ /* Vector status and control register */
uint32_t vscr;
- /* VSX registers */
- uint64_t vsr[32];
+ /* VSX registers (including FP and AVR) */
+ ppc_vsr_t vsr[64] QEMU_ALIGNED(16);
/* SPE registers */
uint64_t spe_acc;
uint32_t spe_fscr;
@@ -126,7 +126,7 @@ int ppc_cpu_gdb_read_register(CPUState *cs, uint8_t *mem_buf, int n)
gdb_get_regl(mem_buf, env->gpr[n]);
} else if (n < 64) {
/* fprs */
- stfq_p(mem_buf, env->fpr[n-32]);
+ stfq_p(mem_buf, env->vsr[n - 32].u64[0]);
} else {
switch (n) {
case 64:
@@ -178,7 +178,7 @@ int ppc_cpu_gdb_read_register_apple(CPUState *cs, uint8_t *mem_buf, int n)
gdb_get_reg64(mem_buf, env->gpr[n]);
} else if (n < 64) {
/* fprs */
- stfq_p(mem_buf, env->fpr[n-32]);
+ stfq_p(mem_buf, env->vsr[n - 32].u64[0]);
} else if (n < 96) {
/* Altivec */
stq_p(mem_buf, n - 64);
@@ -234,7 +234,7 @@ int ppc_cpu_gdb_write_register(CPUState *cs, uint8_t *mem_buf, int n)
env->gpr[n] = ldtul_p(mem_buf);
} else if (n < 64) {
/* fprs */
- env->fpr[n-32] = ldfq_p(mem_buf);
+ env->vsr[n - 32].u64[0] = ldfq_p(mem_buf);
} else {
switch (n) {
case 64:
@@ -284,7 +284,7 @@ int ppc_cpu_gdb_write_register_apple(CPUState *cs, uint8_t *mem_buf, int n)
env->gpr[n] = ldq_p(mem_buf);
} else if (n < 64) {
/* fprs */
- env->fpr[n-32] = ldfq_p(mem_buf);
+ env->vsr[n - 32].u64[0] = ldfq_p(mem_buf);
} else {
switch (n) {
case 64 + 32:
@@ -218,24 +218,14 @@ EXTRACT_HELPER_SPLIT_3(DCMX_XV, 5, 16, 0, 1, 2, 5, 1, 6, 6);
static inline void getVSR(int n, ppc_vsr_t *vsr, CPUPPCState *env)
{
- if (n < 32) {
- vsr->VsrD(0) = env->fpr[n];
- vsr->VsrD(1) = env->vsr[n];
- } else {
- vsr->u64[0] = env->avr[n - 32].u64[0];
- vsr->u64[1] = env->avr[n - 32].u64[1];
- }
+ vsr->VsrD(0) = env->vsr[n].u64[0];
+ vsr->VsrD(1) = env->vsr[n].u64[1];
}
static inline void putVSR(int n, ppc_vsr_t *vsr, CPUPPCState *env)
{
- if (n < 32) {
- env->fpr[n] = vsr->VsrD(0);
- env->vsr[n] = vsr->VsrD(1);
- } else {
- env->avr[n - 32].u64[0] = vsr->u64[0];
- env->avr[n - 32].u64[1] = vsr->u64[1];
- }
+ env->vsr[n].u64[0] = vsr->VsrD(0);
+ env->vsr[n].u64[1] = vsr->VsrD(1);
}
void helper_compute_fprf_float16(CPUPPCState *env, float16 arg);
@@ -45,7 +45,7 @@ static int cpu_load_old(QEMUFile *f, void *opaque, int version_id)
uint64_t l;
} u;
u.l = qemu_get_be64(f);
- env->fpr[i] = u.d;
+ env->vsr[i].u64[0] = u.d;
}
qemu_get_be32s(f, &fpscr);
env->fpscr = fpscr;
@@ -138,11 +138,73 @@ static const VMStateInfo vmstate_info_avr = {
};
#define VMSTATE_AVR_ARRAY_V(_f, _s, _n, _v) \
- VMSTATE_ARRAY(_f, _s, _n, _v, vmstate_info_avr, ppc_avr_t)
+ VMSTATE_SUB_ARRAY(_f, _s, 32, _n, _v, vmstate_info_avr, ppc_avr_t)
#define VMSTATE_AVR_ARRAY(_f, _s, _n) \
VMSTATE_AVR_ARRAY_V(_f, _s, _n, 0)
+static int get_fpr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field)
+{
+ ppc_vsr_t *v = pv;
+
+ v->u64[0] = qemu_get_be64(f);
+
+ return 0;
+}
+
+static int put_fpr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, QJSON *vmdesc)
+{
+ ppc_vsr_t *v = pv;
+
+ qemu_put_be64(f, v->u64[0]);
+ return 0;
+}
+
+static const VMStateInfo vmstate_info_fpr = {
+ .name = "fpr",
+ .get = get_fpr,
+ .put = put_fpr,
+};
+
+#define VMSTATE_FPR_ARRAY_V(_f, _s, _n, _v) \
+ VMSTATE_SUB_ARRAY(_f, _s, 0, _n, _v, vmstate_info_fpr, ppc_vsr_t)
+
+#define VMSTATE_FPR_ARRAY(_f, _s, _n) \
+ VMSTATE_FPR_ARRAY_V(_f, _s, _n, 0)
+
+static int get_vsr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field)
+{
+ ppc_vsr_t *v = pv;
+
+ v->u64[1] = qemu_get_be64(f);
+
+ return 0;
+}
+
+static int put_vsr(QEMUFile *f, void *pv, size_t size,
+ const VMStateField *field, QJSON *vmdesc)
+{
+ ppc_vsr_t *v = pv;
+
+ qemu_put_be64(f, v->u64[1]);
+ return 0;
+}
+
+static const VMStateInfo vmstate_info_vsr = {
+ .name = "vsr",
+ .get = get_vsr,
+ .put = put_vsr,
+};
+
+#define VMSTATE_VSR_ARRAY_V(_f, _s, _n, _v) \
+ VMSTATE_SUB_ARRAY(_f, _s, 0, _n, _v, vmstate_info_vsr, ppc_vsr_t)
+
+#define VMSTATE_VSR_ARRAY(_f, _s, _n) \
+ VMSTATE_VSR_ARRAY_V(_f, _s, _n, 0)
+
static bool cpu_pre_2_8_migration(void *opaque, int version_id)
{
PowerPCCPU *cpu = opaque;
@@ -354,7 +416,7 @@ static const VMStateDescription vmstate_fpu = {
.minimum_version_id = 1,
.needed = fpu_needed,
.fields = (VMStateField[]) {
- VMSTATE_FLOAT64_ARRAY(env.fpr, PowerPCCPU, 32),
+ VMSTATE_FPR_ARRAY(env.vsr, PowerPCCPU, 32),
VMSTATE_UINTTL(env.fpscr, PowerPCCPU),
VMSTATE_END_OF_LIST()
},
@@ -373,7 +435,7 @@ static const VMStateDescription vmstate_altivec = {
.minimum_version_id = 1,
.needed = altivec_needed,
.fields = (VMStateField[]) {
- VMSTATE_AVR_ARRAY(env.avr, PowerPCCPU, 32),
+ VMSTATE_AVR_ARRAY(env.vsr, PowerPCCPU, 32),
VMSTATE_UINT32(env.vscr, PowerPCCPU),
VMSTATE_END_OF_LIST()
},
@@ -392,7 +454,7 @@ static const VMStateDescription vmstate_vsx = {
.minimum_version_id = 1,
.needed = vsx_needed,
.fields = (VMStateField[]) {
- VMSTATE_UINT64_ARRAY(env.vsr, PowerPCCPU, 32),
+ VMSTATE_VSR_ARRAY(env.vsr, PowerPCCPU, 32),
VMSTATE_END_OF_LIST()
},
};
@@ -123,8 +123,8 @@ int target_get_monitor_def(CPUState *cs, const char *name, uint64_t *pval)
/* Floating point registers */
if ((qemu_tolower(name[0]) == 'f') &&
- ppc_cpu_get_reg_num(name + 1, ARRAY_SIZE(env->fpr), ®num)) {
- *pval = env->fpr[regnum];
+ ppc_cpu_get_reg_num(name + 1, 32, ®num)) {
+ *pval = env->vsr[regnum].u64[0];
return 0;
}
@@ -6657,22 +6657,22 @@ GEN_TM_PRIV_NOOP(trechkpt);
static inline void get_fpr(TCGv_i64 dst, int regno)
{
- tcg_gen_ld_i64(dst, cpu_env, offsetof(CPUPPCState, fpr[regno]));
+ tcg_gen_ld_i64(dst, cpu_env, offsetof(CPUPPCState, vsr[regno].u64[0]));
}
static inline void set_fpr(int regno, TCGv_i64 src)
{
- tcg_gen_st_i64(src, cpu_env, offsetof(CPUPPCState, fpr[regno]));
+ tcg_gen_st_i64(src, cpu_env, offsetof(CPUPPCState, vsr[regno].u64[0]));
}
static inline void get_avr64(TCGv_i64 dst, int regno, bool high)
{
#ifdef HOST_WORDS_BIGENDIAN
tcg_gen_ld_i64(dst, cpu_env, offsetof(CPUPPCState,
- avr[regno].u64[(high ? 0 : 1)]));
+ vsr[32 + regno].u64[(high ? 0 : 1)]));
#else
tcg_gen_ld_i64(dst, cpu_env, offsetof(CPUPPCState,
- avr[regno].u64[(high ? 1 : 0)]));
+ vsr[32 + regno].u64[(high ? 1 : 0)]));
#endif
}
@@ -6680,10 +6680,10 @@ static inline void set_avr64(int regno, TCGv_i64 src, bool high)
{
#ifdef HOST_WORDS_BIGENDIAN
tcg_gen_st_i64(src, cpu_env, offsetof(CPUPPCState,
- avr[regno].u64[(high ? 0 : 1)]));
+ vsr[32 + regno].u64[(high ? 0 : 1)]));
#else
tcg_gen_st_i64(src, cpu_env, offsetof(CPUPPCState,
- avr[regno].u64[(high ? 1 : 0)]));
+ vsr[32 + regno].u64[(high ? 1 : 0)]));
#endif
}
@@ -7434,7 +7434,7 @@ void ppc_cpu_dump_state(CPUState *cs, FILE *f, fprintf_function cpu_fprintf,
if ((i & (RFPL - 1)) == 0) {
cpu_fprintf(f, "FPR%02d", i);
}
- cpu_fprintf(f, " %016" PRIx64, *((uint64_t *)&env->fpr[i]));
+ cpu_fprintf(f, " %016" PRIx64, *(&env->vsr[i].u64[0]));
if ((i & (RFPL - 1)) == (RFPL - 1)) {
cpu_fprintf(f, "\n");
}
@@ -3,7 +3,7 @@
static inline TCGv_ptr gen_fprp_ptr(int reg)
{
TCGv_ptr r = tcg_temp_new_ptr();
- tcg_gen_addi_ptr(r, cpu_env, offsetof(CPUPPCState, fpr[reg]));
+ tcg_gen_addi_ptr(r, cpu_env, offsetof(CPUPPCState, vsr[reg].u64[0]));
return r;
}
@@ -10,10 +10,15 @@
static inline TCGv_ptr gen_avr_ptr(int reg)
{
TCGv_ptr r = tcg_temp_new_ptr();
- tcg_gen_addi_ptr(r, cpu_env, offsetof(CPUPPCState, avr[reg]));
+ tcg_gen_addi_ptr(r, cpu_env, offsetof(CPUPPCState, vsr[32 + reg].u64[0]));
return r;
}
+static inline long avr64_offset(int reg, bool high)
+{
+ return offsetof(CPUPPCState, vsr[32 + reg].u64[(high ? 0 : 1)]);
+}
+
#define GEN_VR_LDX(name, opc2, opc3) \
static void glue(gen_, name)(DisasContext *ctx) \
{ \
@@ -2,12 +2,12 @@
static inline void get_vsr(TCGv_i64 dst, int n)
{
- tcg_gen_ld_i64(dst, cpu_env, offsetof(CPUPPCState, vsr[n]));
+ tcg_gen_ld_i64(dst, cpu_env, offsetof(CPUPPCState, vsr[n].u64[1]));
}
static inline void set_vsr(int n, TCGv_i64 src)
{
- tcg_gen_st_i64(src, cpu_env, offsetof(CPUPPCState, vsr[n]));
+ tcg_gen_st_i64(src, cpu_env, offsetof(CPUPPCState, vsr[n].u64[1]));
}
static inline void get_cpu_vsrh(TCGv_i64 dst, int n)
@@ -9486,7 +9486,7 @@ static bool avr_need_swap(CPUPPCState *env)
static int gdb_get_float_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
{
if (n < 32) {
- stfq_p(mem_buf, env->fpr[n]);
+ stfq_p(mem_buf, env->vsr[n].u64[0]);
ppc_maybe_bswap_register(env, mem_buf, 8);
return 8;
}
@@ -9502,7 +9502,7 @@ static int gdb_set_float_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
{
if (n < 32) {
ppc_maybe_bswap_register(env, mem_buf, 8);
- env->fpr[n] = ldfq_p(mem_buf);
+ env->vsr[n].u64[0] = ldfq_p(mem_buf);
return 8;
}
if (n == 32) {
@@ -9517,11 +9517,11 @@ static int gdb_get_avr_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
{
if (n < 32) {
if (!avr_need_swap(env)) {
- stq_p(mem_buf, env->avr[n].u64[0]);
- stq_p(mem_buf+8, env->avr[n].u64[1]);
+ stq_p(mem_buf, env->vsr[32 + n].u64[0]);
+ stq_p(mem_buf + 8, env->vsr[32 + n].u64[1]);
} else {
- stq_p(mem_buf, env->avr[n].u64[1]);
- stq_p(mem_buf+8, env->avr[n].u64[0]);
+ stq_p(mem_buf, env->vsr[32 + n].u64[1]);
+ stq_p(mem_buf + 8, env->vsr[32 + n].u64[0]);
}
ppc_maybe_bswap_register(env, mem_buf, 8);
ppc_maybe_bswap_register(env, mem_buf + 8, 8);
@@ -9546,11 +9546,11 @@ static int gdb_set_avr_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
ppc_maybe_bswap_register(env, mem_buf, 8);
ppc_maybe_bswap_register(env, mem_buf + 8, 8);
if (!avr_need_swap(env)) {
- env->avr[n].u64[0] = ldq_p(mem_buf);
- env->avr[n].u64[1] = ldq_p(mem_buf+8);
+ env->vsr[32 + n].u64[0] = ldq_p(mem_buf);
+ env->vsr[32 + n].u64[1] = ldq_p(mem_buf + 8);
} else {
- env->avr[n].u64[1] = ldq_p(mem_buf);
- env->avr[n].u64[0] = ldq_p(mem_buf+8);
+ env->vsr[32 + n].u64[1] = ldq_p(mem_buf);
+ env->vsr[32 + n].u64[0] = ldq_p(mem_buf + 8);
}
return 16;
}
@@ -9623,7 +9623,7 @@ static int gdb_set_spe_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
static int gdb_get_vsx_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
{
if (n < 32) {
- stq_p(mem_buf, env->vsr[n]);
+ stq_p(mem_buf, env->vsr[n].u64[1]);
ppc_maybe_bswap_register(env, mem_buf, 8);
return 8;
}
@@ -9634,7 +9634,7 @@ static int gdb_set_vsx_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
{
if (n < 32) {
ppc_maybe_bswap_register(env, mem_buf, 8);
- env->vsr[n] = ldq_p(mem_buf);
+ env->vsr[n].u64[1] = ldq_p(mem_buf);
return 8;
}
return 0;