target/ppc: move FP and VMX registers into aligned vsr register array

The VSX register array is a block of 64 128-bit registers where the first 32
registers consist of the existing 64-bit FP registers extended to 128-bit
using new VSR registers, and the last 32 registers are the VMX 128-bit
registers as show below:

            64-bit               64-bit
    +--------------------+--------------------+
    |        FP0         |                    |  VSR0
    +--------------------+--------------------+
    |        FP1         |                    |  VSR1
    +--------------------+--------------------+
    |        ...         |        ...         |  ...
    +--------------------+--------------------+
    |        FP30        |                    |  VSR30
    +--------------------+--------------------+
    |        FP31        |                    |  VSR31
    +--------------------+--------------------+
    |                  VMX0                   |  VSR32
    +-----------------------------------------+
    |                  VMX1                   |  VSR33
    +-----------------------------------------+
    |                  ...                    |  ...
    +-----------------------------------------+
    |                  VMX30                  |  VSR62
    +-----------------------------------------+
    |                  VMX31                  |  VSR63
    +-----------------------------------------+

In order to allow for future conversion of VSX instructions to use TCG vector
operations, recreate the same layout using an aligned version of the existing
vsr register array.

Since the old fpr and avr register arrays are removed, the existing callers
must also be updated to use the correct offset in the vsr register array. This
also includes switching the relevant VMState fields over to using subarrays
to make sure that migration is preserved.

Signed-off-by: Mark Cave-Ayland <mark.cave-ayland@ilande.co.uk>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Acked-by: David Gibson <david@gibson.dropbear.id.au>
Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
This commit is contained in:
Mark Cave-Ayland 2019-01-02 09:14:22 +00:00 committed by David Gibson
parent 05ee3e8aa0
commit ef96e3ae96
13 changed files with 165 additions and 82 deletions

View File

@ -258,8 +258,8 @@ static void save_user_regs(CPUPPCState *env, struct target_mcontext *frame)
/* Save Altivec registers if necessary. */ /* Save Altivec registers if necessary. */
if (env->insns_flags & PPC_ALTIVEC) { if (env->insns_flags & PPC_ALTIVEC) {
uint32_t *vrsave; uint32_t *vrsave;
for (i = 0; i < ARRAY_SIZE(env->avr); i++) { for (i = 0; i < 32; i++) {
ppc_avr_t *avr = &env->avr[i]; ppc_avr_t *avr = cpu_avr_ptr(env, i);
ppc_avr_t *vreg = (ppc_avr_t *)&frame->mc_vregs.altivec[i]; ppc_avr_t *vreg = (ppc_avr_t *)&frame->mc_vregs.altivec[i];
__put_user(avr->u64[PPC_VEC_HI], &vreg->u64[0]); __put_user(avr->u64[PPC_VEC_HI], &vreg->u64[0]);
@ -281,15 +281,17 @@ static void save_user_regs(CPUPPCState *env, struct target_mcontext *frame)
/* Save VSX second halves */ /* Save VSX second halves */
if (env->insns_flags2 & PPC2_VSX) { if (env->insns_flags2 & PPC2_VSX) {
uint64_t *vsregs = (uint64_t *)&frame->mc_vregs.altivec[34]; uint64_t *vsregs = (uint64_t *)&frame->mc_vregs.altivec[34];
for (i = 0; i < ARRAY_SIZE(env->vsr); i++) { for (i = 0; i < 32; i++) {
__put_user(env->vsr[i], &vsregs[i]); uint64_t *vsrl = cpu_vsrl_ptr(env, i);
__put_user(*vsrl, &vsregs[i]);
} }
} }
/* Save floating point registers. */ /* Save floating point registers. */
if (env->insns_flags & PPC_FLOAT) { if (env->insns_flags & PPC_FLOAT) {
for (i = 0; i < ARRAY_SIZE(env->fpr); i++) { for (i = 0; i < 32; i++) {
__put_user(env->fpr[i], &frame->mc_fregs[i]); uint64_t *fpr = cpu_fpr_ptr(env, i);
__put_user(*fpr, &frame->mc_fregs[i]);
} }
__put_user((uint64_t) env->fpscr, &frame->mc_fregs[32]); __put_user((uint64_t) env->fpscr, &frame->mc_fregs[32]);
} }
@ -373,8 +375,8 @@ static void restore_user_regs(CPUPPCState *env,
#else #else
v_regs = (ppc_avr_t *)frame->mc_vregs.altivec; v_regs = (ppc_avr_t *)frame->mc_vregs.altivec;
#endif #endif
for (i = 0; i < ARRAY_SIZE(env->avr); i++) { for (i = 0; i < 32; i++) {
ppc_avr_t *avr = &env->avr[i]; ppc_avr_t *avr = cpu_avr_ptr(env, i);
ppc_avr_t *vreg = &v_regs[i]; ppc_avr_t *vreg = &v_regs[i];
__get_user(avr->u64[PPC_VEC_HI], &vreg->u64[0]); __get_user(avr->u64[PPC_VEC_HI], &vreg->u64[0]);
@ -393,16 +395,18 @@ static void restore_user_regs(CPUPPCState *env,
/* Restore VSX second halves */ /* Restore VSX second halves */
if (env->insns_flags2 & PPC2_VSX) { if (env->insns_flags2 & PPC2_VSX) {
uint64_t *vsregs = (uint64_t *)&frame->mc_vregs.altivec[34]; uint64_t *vsregs = (uint64_t *)&frame->mc_vregs.altivec[34];
for (i = 0; i < ARRAY_SIZE(env->vsr); i++) { for (i = 0; i < 32; i++) {
__get_user(env->vsr[i], &vsregs[i]); uint64_t *vsrl = cpu_vsrl_ptr(env, i);
__get_user(*vsrl, &vsregs[i]);
} }
} }
/* Restore floating point registers. */ /* Restore floating point registers. */
if (env->insns_flags & PPC_FLOAT) { if (env->insns_flags & PPC_FLOAT) {
uint64_t fpscr; uint64_t fpscr;
for (i = 0; i < ARRAY_SIZE(env->fpr); i++) { for (i = 0; i < 32; i++) {
__get_user(env->fpr[i], &frame->mc_fregs[i]); uint64_t *fpr = cpu_fpr_ptr(env, i);
__get_user(*fpr, &frame->mc_fregs[i]);
} }
__get_user(fpscr, &frame->mc_fregs[32]); __get_user(fpscr, &frame->mc_fregs[32]);
env->fpscr = (uint32_t) fpscr; env->fpscr = (uint32_t) fpscr;

View File

@ -140,7 +140,8 @@ static void ppc_write_elf_fpregset(NoteFuncArg *arg, PowerPCCPU *cpu)
memset(fpregset, 0, sizeof(*fpregset)); memset(fpregset, 0, sizeof(*fpregset));
for (i = 0; i < 32; i++) { for (i = 0; i < 32; i++) {
fpregset->fpr[i] = cpu_to_dump64(s, cpu->env.fpr[i]); uint64_t *fpr = cpu_fpr_ptr(&cpu->env, i);
fpregset->fpr[i] = cpu_to_dump64(s, *fpr);
} }
fpregset->fpscr = cpu_to_dump_reg(s, cpu->env.fpscr); fpregset->fpscr = cpu_to_dump_reg(s, cpu->env.fpscr);
} }
@ -158,6 +159,7 @@ static void ppc_write_elf_vmxregset(NoteFuncArg *arg, PowerPCCPU *cpu)
for (i = 0; i < 32; i++) { for (i = 0; i < 32; i++) {
bool needs_byteswap; bool needs_byteswap;
ppc_avr_t *avr = cpu_avr_ptr(&cpu->env, i);
#ifdef HOST_WORDS_BIGENDIAN #ifdef HOST_WORDS_BIGENDIAN
needs_byteswap = s->dump_info.d_endian == ELFDATA2LSB; needs_byteswap = s->dump_info.d_endian == ELFDATA2LSB;
@ -166,11 +168,11 @@ static void ppc_write_elf_vmxregset(NoteFuncArg *arg, PowerPCCPU *cpu)
#endif #endif
if (needs_byteswap) { if (needs_byteswap) {
vmxregset->avr[i].u64[0] = bswap64(cpu->env.avr[i].u64[1]); vmxregset->avr[i].u64[0] = bswap64(avr->u64[1]);
vmxregset->avr[i].u64[1] = bswap64(cpu->env.avr[i].u64[0]); vmxregset->avr[i].u64[1] = bswap64(avr->u64[0]);
} else { } else {
vmxregset->avr[i].u64[0] = cpu->env.avr[i].u64[0]; vmxregset->avr[i].u64[0] = avr->u64[0];
vmxregset->avr[i].u64[1] = cpu->env.avr[i].u64[1]; vmxregset->avr[i].u64[1] = avr->u64[1];
} }
} }
vmxregset->vscr.u32[3] = cpu_to_dump32(s, cpu->env.vscr); vmxregset->vscr.u32[3] = cpu_to_dump32(s, cpu->env.vscr);
@ -188,7 +190,8 @@ static void ppc_write_elf_vsxregset(NoteFuncArg *arg, PowerPCCPU *cpu)
memset(vsxregset, 0, sizeof(*vsxregset)); memset(vsxregset, 0, sizeof(*vsxregset));
for (i = 0; i < 32; i++) { for (i = 0; i < 32; i++) {
vsxregset->vsr[i] = cpu_to_dump64(s, cpu->env.vsr[i]); uint64_t *vsrl = cpu_vsrl_ptr(&cpu->env, i);
vsxregset->vsr[i] = cpu_to_dump64(s, *vsrl);
} }
} }

View File

@ -1004,8 +1004,6 @@ struct CPUPPCState {
/* Floating point execution context */ /* Floating point execution context */
float_status fp_status; float_status fp_status;
/* floating point registers */
float64 fpr[32];
/* floating point status and control register */ /* floating point status and control register */
target_ulong fpscr; target_ulong fpscr;
@ -1055,11 +1053,10 @@ struct CPUPPCState {
/* Special purpose registers */ /* Special purpose registers */
target_ulong spr[1024]; target_ulong spr[1024];
ppc_spr_t spr_cb[1024]; ppc_spr_t spr_cb[1024];
/* Altivec registers */ /* Vector status and control register */
ppc_avr_t avr[32];
uint32_t vscr; uint32_t vscr;
/* VSX registers */ /* VSX registers (including FP and AVR) */
uint64_t vsr[32]; ppc_vsr_t vsr[64] QEMU_ALIGNED(16);
/* SPE registers */ /* SPE registers */
uint64_t spe_acc; uint64_t spe_acc;
uint32_t spe_fscr; uint32_t spe_fscr;
@ -2540,6 +2537,22 @@ static inline bool lsw_reg_in_range(int start, int nregs, int rx)
(start + nregs > 32 && (rx >= start || rx < start + nregs - 32)); (start + nregs > 32 && (rx >= start || rx < start + nregs - 32));
} }
/* Accessors for FP, VMX and VSX registers */
static inline uint64_t *cpu_fpr_ptr(CPUPPCState *env, int i)
{
return &env->vsr[i].u64[0];
}
static inline uint64_t *cpu_vsrl_ptr(CPUPPCState *env, int i)
{
return &env->vsr[i].u64[1];
}
static inline ppc_avr_t *cpu_avr_ptr(CPUPPCState *env, int i)
{
return &env->vsr[32 + i];
}
void dump_mmu(FILE *f, fprintf_function cpu_fprintf, CPUPPCState *env); void dump_mmu(FILE *f, fprintf_function cpu_fprintf, CPUPPCState *env);
void ppc_maybe_bswap_register(CPUPPCState *env, uint8_t *mem_buf, int len); void ppc_maybe_bswap_register(CPUPPCState *env, uint8_t *mem_buf, int len);

View File

@ -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]); gdb_get_regl(mem_buf, env->gpr[n]);
} else if (n < 64) { } else if (n < 64) {
/* fprs */ /* fprs */
stfq_p(mem_buf, env->fpr[n-32]); stfq_p(mem_buf, *cpu_fpr_ptr(env, n - 32));
} else { } else {
switch (n) { switch (n) {
case 64: 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]); gdb_get_reg64(mem_buf, env->gpr[n]);
} else if (n < 64) { } else if (n < 64) {
/* fprs */ /* fprs */
stfq_p(mem_buf, env->fpr[n-32]); stfq_p(mem_buf, *cpu_fpr_ptr(env, n - 32));
} else if (n < 96) { } else if (n < 96) {
/* Altivec */ /* Altivec */
stq_p(mem_buf, n - 64); 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); env->gpr[n] = ldtul_p(mem_buf);
} else if (n < 64) { } else if (n < 64) {
/* fprs */ /* fprs */
env->fpr[n-32] = ldfq_p(mem_buf); *cpu_fpr_ptr(env, n - 32) = ldfq_p(mem_buf);
} else { } else {
switch (n) { switch (n) {
case 64: 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); env->gpr[n] = ldq_p(mem_buf);
} else if (n < 64) { } else if (n < 64) {
/* fprs */ /* fprs */
env->fpr[n-32] = ldfq_p(mem_buf); *cpu_fpr_ptr(env, n - 32) = ldfq_p(mem_buf);
} else { } else {
switch (n) { switch (n) {
case 64 + 32: case 64 + 32:

View File

@ -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) static inline void getVSR(int n, ppc_vsr_t *vsr, CPUPPCState *env)
{ {
if (n < 32) { vsr->VsrD(0) = env->vsr[n].u64[0];
vsr->VsrD(0) = env->fpr[n]; vsr->VsrD(1) = env->vsr[n].u64[1];
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];
}
} }
static inline void putVSR(int n, ppc_vsr_t *vsr, CPUPPCState *env) static inline void putVSR(int n, ppc_vsr_t *vsr, CPUPPCState *env)
{ {
if (n < 32) { env->vsr[n].u64[0] = vsr->VsrD(0);
env->fpr[n] = vsr->VsrD(0); env->vsr[n].u64[1] = vsr->VsrD(1);
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];
}
} }
void helper_compute_fprf_float16(CPUPPCState *env, float16 arg); void helper_compute_fprf_float16(CPUPPCState *env, float16 arg);

View File

@ -629,13 +629,15 @@ static int kvm_put_fp(CPUState *cs)
for (i = 0; i < 32; i++) { for (i = 0; i < 32; i++) {
uint64_t vsr[2]; uint64_t vsr[2];
uint64_t *fpr = cpu_fpr_ptr(&cpu->env, i);
uint64_t *vsrl = cpu_vsrl_ptr(&cpu->env, i);
#ifdef HOST_WORDS_BIGENDIAN #ifdef HOST_WORDS_BIGENDIAN
vsr[0] = float64_val(env->fpr[i]); vsr[0] = float64_val(*fpr);
vsr[1] = env->vsr[i]; vsr[1] = *vsrl;
#else #else
vsr[0] = env->vsr[i]; vsr[0] = *vsrl;
vsr[1] = float64_val(env->fpr[i]); vsr[1] = float64_val(*fpr);
#endif #endif
reg.addr = (uintptr_t) &vsr; reg.addr = (uintptr_t) &vsr;
reg.id = vsx ? KVM_REG_PPC_VSR(i) : KVM_REG_PPC_FPR(i); reg.id = vsx ? KVM_REG_PPC_VSR(i) : KVM_REG_PPC_FPR(i);
@ -660,7 +662,7 @@ static int kvm_put_fp(CPUState *cs)
for (i = 0; i < 32; i++) { for (i = 0; i < 32; i++) {
reg.id = KVM_REG_PPC_VR(i); reg.id = KVM_REG_PPC_VR(i);
reg.addr = (uintptr_t)&env->avr[i]; reg.addr = (uintptr_t)cpu_avr_ptr(env, i);
ret = kvm_vcpu_ioctl(cs, KVM_SET_ONE_REG, &reg); ret = kvm_vcpu_ioctl(cs, KVM_SET_ONE_REG, &reg);
if (ret < 0) { if (ret < 0) {
DPRINTF("Unable to set VR%d to KVM: %s\n", i, strerror(errno)); DPRINTF("Unable to set VR%d to KVM: %s\n", i, strerror(errno));
@ -696,6 +698,8 @@ static int kvm_get_fp(CPUState *cs)
for (i = 0; i < 32; i++) { for (i = 0; i < 32; i++) {
uint64_t vsr[2]; uint64_t vsr[2];
uint64_t *fpr = cpu_fpr_ptr(&cpu->env, i);
uint64_t *vsrl = cpu_vsrl_ptr(&cpu->env, i);
reg.addr = (uintptr_t) &vsr; reg.addr = (uintptr_t) &vsr;
reg.id = vsx ? KVM_REG_PPC_VSR(i) : KVM_REG_PPC_FPR(i); reg.id = vsx ? KVM_REG_PPC_VSR(i) : KVM_REG_PPC_FPR(i);
@ -707,14 +711,14 @@ static int kvm_get_fp(CPUState *cs)
return ret; return ret;
} else { } else {
#ifdef HOST_WORDS_BIGENDIAN #ifdef HOST_WORDS_BIGENDIAN
env->fpr[i] = vsr[0]; *fpr = vsr[0];
if (vsx) { if (vsx) {
env->vsr[i] = vsr[1]; *vsrl = vsr[1];
} }
#else #else
env->fpr[i] = vsr[1]; *fpr = vsr[1];
if (vsx) { if (vsx) {
env->vsr[i] = vsr[0]; *vsrl = vsr[0];
} }
#endif #endif
} }
@ -732,7 +736,7 @@ static int kvm_get_fp(CPUState *cs)
for (i = 0; i < 32; i++) { for (i = 0; i < 32; i++) {
reg.id = KVM_REG_PPC_VR(i); reg.id = KVM_REG_PPC_VR(i);
reg.addr = (uintptr_t)&env->avr[i]; reg.addr = (uintptr_t)cpu_avr_ptr(env, i);
ret = kvm_vcpu_ioctl(cs, KVM_GET_ONE_REG, &reg); ret = kvm_vcpu_ioctl(cs, KVM_GET_ONE_REG, &reg);
if (ret < 0) { if (ret < 0) {
DPRINTF("Unable to get VR%d from KVM: %s\n", DPRINTF("Unable to get VR%d from KVM: %s\n",

View File

@ -45,7 +45,7 @@ static int cpu_load_old(QEMUFile *f, void *opaque, int version_id)
uint64_t l; uint64_t l;
} u; } u;
u.l = qemu_get_be64(f); u.l = qemu_get_be64(f);
env->fpr[i] = u.d; *cpu_fpr_ptr(env, i) = u.d;
} }
qemu_get_be32s(f, &fpscr); qemu_get_be32s(f, &fpscr);
env->fpscr = fpscr; env->fpscr = fpscr;
@ -138,11 +138,73 @@ static const VMStateInfo vmstate_info_avr = {
}; };
#define VMSTATE_AVR_ARRAY_V(_f, _s, _n, _v) \ #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) \ #define VMSTATE_AVR_ARRAY(_f, _s, _n) \
VMSTATE_AVR_ARRAY_V(_f, _s, _n, 0) 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) static bool cpu_pre_2_8_migration(void *opaque, int version_id)
{ {
PowerPCCPU *cpu = opaque; PowerPCCPU *cpu = opaque;
@ -354,7 +416,7 @@ static const VMStateDescription vmstate_fpu = {
.minimum_version_id = 1, .minimum_version_id = 1,
.needed = fpu_needed, .needed = fpu_needed,
.fields = (VMStateField[]) { .fields = (VMStateField[]) {
VMSTATE_FLOAT64_ARRAY(env.fpr, PowerPCCPU, 32), VMSTATE_FPR_ARRAY(env.vsr, PowerPCCPU, 32),
VMSTATE_UINTTL(env.fpscr, PowerPCCPU), VMSTATE_UINTTL(env.fpscr, PowerPCCPU),
VMSTATE_END_OF_LIST() VMSTATE_END_OF_LIST()
}, },
@ -373,7 +435,7 @@ static const VMStateDescription vmstate_altivec = {
.minimum_version_id = 1, .minimum_version_id = 1,
.needed = altivec_needed, .needed = altivec_needed,
.fields = (VMStateField[]) { .fields = (VMStateField[]) {
VMSTATE_AVR_ARRAY(env.avr, PowerPCCPU, 32), VMSTATE_AVR_ARRAY(env.vsr, PowerPCCPU, 32),
VMSTATE_UINT32(env.vscr, PowerPCCPU), VMSTATE_UINT32(env.vscr, PowerPCCPU),
VMSTATE_END_OF_LIST() VMSTATE_END_OF_LIST()
}, },
@ -392,7 +454,7 @@ static const VMStateDescription vmstate_vsx = {
.minimum_version_id = 1, .minimum_version_id = 1,
.needed = vsx_needed, .needed = vsx_needed,
.fields = (VMStateField[]) { .fields = (VMStateField[]) {
VMSTATE_UINT64_ARRAY(env.vsr, PowerPCCPU, 32), VMSTATE_VSR_ARRAY(env.vsr, PowerPCCPU, 32),
VMSTATE_END_OF_LIST() VMSTATE_END_OF_LIST()
}, },
}; };

View File

@ -123,8 +123,8 @@ int target_get_monitor_def(CPUState *cs, const char *name, uint64_t *pval)
/* Floating point registers */ /* Floating point registers */
if ((qemu_tolower(name[0]) == 'f') && if ((qemu_tolower(name[0]) == 'f') &&
ppc_cpu_get_reg_num(name + 1, ARRAY_SIZE(env->fpr), &regnum)) { ppc_cpu_get_reg_num(name + 1, 32, &regnum)) {
*pval = env->fpr[regnum]; *pval = *cpu_fpr_ptr(env, regnum);
return 0; return 0;
} }

View File

@ -6662,22 +6662,22 @@ GEN_TM_PRIV_NOOP(trechkpt);
static inline void get_fpr(TCGv_i64 dst, int regno) 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) 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) static inline void get_avr64(TCGv_i64 dst, int regno, bool high)
{ {
#ifdef HOST_WORDS_BIGENDIAN #ifdef HOST_WORDS_BIGENDIAN
tcg_gen_ld_i64(dst, cpu_env, offsetof(CPUPPCState, tcg_gen_ld_i64(dst, cpu_env, offsetof(CPUPPCState,
avr[regno].u64[(high ? 0 : 1)])); vsr[32 + regno].u64[(high ? 0 : 1)]));
#else #else
tcg_gen_ld_i64(dst, cpu_env, offsetof(CPUPPCState, tcg_gen_ld_i64(dst, cpu_env, offsetof(CPUPPCState,
avr[regno].u64[(high ? 1 : 0)])); vsr[32 + regno].u64[(high ? 1 : 0)]));
#endif #endif
} }
@ -6685,10 +6685,10 @@ static inline void set_avr64(int regno, TCGv_i64 src, bool high)
{ {
#ifdef HOST_WORDS_BIGENDIAN #ifdef HOST_WORDS_BIGENDIAN
tcg_gen_st_i64(src, cpu_env, offsetof(CPUPPCState, tcg_gen_st_i64(src, cpu_env, offsetof(CPUPPCState,
avr[regno].u64[(high ? 0 : 1)])); vsr[32 + regno].u64[(high ? 0 : 1)]));
#else #else
tcg_gen_st_i64(src, cpu_env, offsetof(CPUPPCState, tcg_gen_st_i64(src, cpu_env, offsetof(CPUPPCState,
avr[regno].u64[(high ? 1 : 0)])); vsr[32 + regno].u64[(high ? 1 : 0)]));
#endif #endif
} }
@ -7440,7 +7440,7 @@ void ppc_cpu_dump_state(CPUState *cs, FILE *f, fprintf_function cpu_fprintf,
if ((i & (RFPL - 1)) == 0) { if ((i & (RFPL - 1)) == 0) {
cpu_fprintf(f, "FPR%02d", i); cpu_fprintf(f, "FPR%02d", i);
} }
cpu_fprintf(f, " %016" PRIx64, *((uint64_t *)&env->fpr[i])); cpu_fprintf(f, " %016" PRIx64, *cpu_fpr_ptr(env, i));
if ((i & (RFPL - 1)) == (RFPL - 1)) { if ((i & (RFPL - 1)) == (RFPL - 1)) {
cpu_fprintf(f, "\n"); cpu_fprintf(f, "\n");
} }

View File

@ -3,7 +3,7 @@
static inline TCGv_ptr gen_fprp_ptr(int reg) static inline TCGv_ptr gen_fprp_ptr(int reg)
{ {
TCGv_ptr r = tcg_temp_new_ptr(); 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; return r;
} }

View File

@ -10,10 +10,15 @@
static inline TCGv_ptr gen_avr_ptr(int reg) static inline TCGv_ptr gen_avr_ptr(int reg)
{ {
TCGv_ptr r = tcg_temp_new_ptr(); 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; 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) \ #define GEN_VR_LDX(name, opc2, opc3) \
static void glue(gen_, name)(DisasContext *ctx) \ static void glue(gen_, name)(DisasContext *ctx) \
{ \ { \

View File

@ -2,12 +2,12 @@
static inline void get_vsr(TCGv_i64 dst, int n) 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) 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) static inline void get_cpu_vsrh(TCGv_i64 dst, int n)

View File

@ -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) static int gdb_get_float_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
{ {
if (n < 32) { if (n < 32) {
stfq_p(mem_buf, env->fpr[n]); stfq_p(mem_buf, *cpu_fpr_ptr(env, n));
ppc_maybe_bswap_register(env, mem_buf, 8); ppc_maybe_bswap_register(env, mem_buf, 8);
return 8; return 8;
} }
@ -9502,7 +9502,7 @@ static int gdb_set_float_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
{ {
if (n < 32) { if (n < 32) {
ppc_maybe_bswap_register(env, mem_buf, 8); ppc_maybe_bswap_register(env, mem_buf, 8);
env->fpr[n] = ldfq_p(mem_buf); *cpu_fpr_ptr(env, n) = ldfq_p(mem_buf);
return 8; return 8;
} }
if (n == 32) { if (n == 32) {
@ -9516,12 +9516,13 @@ static int gdb_set_float_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
static int gdb_get_avr_reg(CPUPPCState *env, uint8_t *mem_buf, int n) static int gdb_get_avr_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
{ {
if (n < 32) { if (n < 32) {
ppc_avr_t *avr = cpu_avr_ptr(env, n);
if (!avr_need_swap(env)) { if (!avr_need_swap(env)) {
stq_p(mem_buf, env->avr[n].u64[0]); stq_p(mem_buf, avr->u64[0]);
stq_p(mem_buf+8, env->avr[n].u64[1]); stq_p(mem_buf + 8, avr->u64[1]);
} else { } else {
stq_p(mem_buf, env->avr[n].u64[1]); stq_p(mem_buf, avr->u64[1]);
stq_p(mem_buf+8, env->avr[n].u64[0]); stq_p(mem_buf + 8, avr->u64[0]);
} }
ppc_maybe_bswap_register(env, mem_buf, 8); ppc_maybe_bswap_register(env, mem_buf, 8);
ppc_maybe_bswap_register(env, mem_buf + 8, 8); ppc_maybe_bswap_register(env, mem_buf + 8, 8);
@ -9543,14 +9544,15 @@ static int gdb_get_avr_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
static int gdb_set_avr_reg(CPUPPCState *env, uint8_t *mem_buf, int n) static int gdb_set_avr_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
{ {
if (n < 32) { if (n < 32) {
ppc_avr_t *avr = cpu_avr_ptr(env, n);
ppc_maybe_bswap_register(env, mem_buf, 8); ppc_maybe_bswap_register(env, mem_buf, 8);
ppc_maybe_bswap_register(env, mem_buf + 8, 8); ppc_maybe_bswap_register(env, mem_buf + 8, 8);
if (!avr_need_swap(env)) { if (!avr_need_swap(env)) {
env->avr[n].u64[0] = ldq_p(mem_buf); avr->u64[0] = ldq_p(mem_buf);
env->avr[n].u64[1] = ldq_p(mem_buf+8); avr->u64[1] = ldq_p(mem_buf + 8);
} else { } else {
env->avr[n].u64[1] = ldq_p(mem_buf); avr->u64[1] = ldq_p(mem_buf);
env->avr[n].u64[0] = ldq_p(mem_buf+8); avr->u64[0] = ldq_p(mem_buf + 8);
} }
return 16; return 16;
} }
@ -9623,7 +9625,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) static int gdb_get_vsx_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
{ {
if (n < 32) { if (n < 32) {
stq_p(mem_buf, env->vsr[n]); stq_p(mem_buf, *cpu_vsrl_ptr(env, n));
ppc_maybe_bswap_register(env, mem_buf, 8); ppc_maybe_bswap_register(env, mem_buf, 8);
return 8; return 8;
} }
@ -9634,7 +9636,7 @@ static int gdb_set_vsx_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
{ {
if (n < 32) { if (n < 32) {
ppc_maybe_bswap_register(env, mem_buf, 8); ppc_maybe_bswap_register(env, mem_buf, 8);
env->vsr[n] = ldq_p(mem_buf); *cpu_vsrl_ptr(env, n) = ldq_p(mem_buf);
return 8; return 8;
} }
return 0; return 0;