mirror of https://github.com/xemu-project/xemu.git
Implement ldxfsr/stxfsr, fix ld(x)fsr masks, convert to TCG
git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@5185 c046a42c-6fe2-441c-8c8c-71466251a162
This commit is contained in:
parent
6f9e38017c
commit
3a3b925d47
|
@ -147,10 +147,15 @@
|
|||
#ifdef TARGET_SPARC64
|
||||
#define FSR_FTT_NMASK 0xfffffffffffe3fffULL
|
||||
#define FSR_FTT_CEXC_NMASK 0xfffffffffffe3fe0ULL
|
||||
#define FSR_LDFSR_OLDMASK 0x0000003f000fc000ULL
|
||||
#define FSR_LDXFSR_MASK 0x0000003fcfc00fffULL
|
||||
#define FSR_LDXFSR_OLDMASK 0x00000000000fc000ULL
|
||||
#else
|
||||
#define FSR_FTT_NMASK 0xfffe3fffULL
|
||||
#define FSR_FTT_CEXC_NMASK 0xfffe3fe0ULL
|
||||
#define FSR_LDFSR_OLDMASK 0x000fc000ULL
|
||||
#endif
|
||||
#define FSR_LDFSR_MASK 0xcfc00fffULL
|
||||
#define FSR_FTT_IEEE_EXCP (1ULL << 14)
|
||||
#define FSR_FTT_UNIMPFPOP (3ULL << 14)
|
||||
#define FSR_FTT_SEQ_ERROR (4ULL << 14)
|
||||
|
@ -329,22 +334,6 @@ typedef struct CPUSPARCState {
|
|||
sparc_def_t *def;
|
||||
} CPUSPARCState;
|
||||
|
||||
#if defined(TARGET_SPARC64)
|
||||
#define GET_FSR32(env) (env->fsr & 0xcfc1ffff)
|
||||
#define PUT_FSR32(env, val) do { uint32_t _tmp = val; \
|
||||
env->fsr = (_tmp & 0xcfc1c3ff) | (env->fsr & 0x3f00000000ULL); \
|
||||
} while (0)
|
||||
#define GET_FSR64(env) (env->fsr & 0x3fcfc1ffffULL)
|
||||
#define PUT_FSR64(env, val) do { uint64_t _tmp = val; \
|
||||
env->fsr = _tmp & 0x3fcfc1c3ffULL; \
|
||||
} while (0)
|
||||
#else
|
||||
#define GET_FSR32(env) (env->fsr)
|
||||
#define PUT_FSR32(env, val) do { uint32_t _tmp = val; \
|
||||
env->fsr = (_tmp & 0xcfc1dfff) | (env->fsr & 0x000e0000); \
|
||||
} while (0)
|
||||
#endif
|
||||
|
||||
/* helper.c */
|
||||
CPUSPARCState *cpu_sparc_init(const char *cpu_model);
|
||||
void cpu_sparc_set_id(CPUSPARCState *env, unsigned int cpu);
|
||||
|
|
|
@ -1412,7 +1412,7 @@ void cpu_dump_state(CPUState *env, FILE *f,
|
|||
env->psrs?'S':'-', env->psrps?'P':'-',
|
||||
env->psret?'E':'-', env->wim);
|
||||
#endif
|
||||
cpu_fprintf(f, "fsr: 0x%08x\n", GET_FSR32(env));
|
||||
cpu_fprintf(f, "fsr: 0x%08x\n", env->fsr);
|
||||
}
|
||||
|
||||
#ifdef TARGET_SPARC64
|
||||
|
|
|
@ -55,8 +55,7 @@ DEF_HELPER(uint64_t, helper_ld_asi, (target_ulong addr, int asi, int size, \
|
|||
DEF_HELPER(void, helper_st_asi, (target_ulong addr, uint64_t val, int asi, \
|
||||
int size))
|
||||
#endif
|
||||
DEF_HELPER(void, helper_ldfsr, (void))
|
||||
DEF_HELPER(void, helper_stfsr, (void))
|
||||
DEF_HELPER(void, helper_ldfsr, (uint32_t new_fsr))
|
||||
DEF_HELPER(void, helper_check_ieee_exceptions, (void))
|
||||
DEF_HELPER(void, helper_clear_float_exceptions, (void))
|
||||
DEF_HELPER(void, helper_fabss, (void))
|
||||
|
@ -70,6 +69,7 @@ DEF_HELPER(void, helper_fsqrtq, (void))
|
|||
DEF_HELPER(void, helper_fcmpq, (void))
|
||||
DEF_HELPER(void, helper_fcmpeq, (void))
|
||||
#ifdef TARGET_SPARC64
|
||||
DEF_HELPER(void, helper_ldxfsr, (uint64_t new_fsr))
|
||||
DEF_HELPER(void, helper_fabsd, (void))
|
||||
DEF_HELPER(void, helper_fcmps_fcc1, (void))
|
||||
DEF_HELPER(void, helper_fcmpd_fcc1, (void))
|
||||
|
|
|
@ -2487,11 +2487,10 @@ void helper_stqf(target_ulong addr, int mem_idx)
|
|||
#endif
|
||||
}
|
||||
|
||||
void helper_ldfsr(void)
|
||||
static inline void set_fsr(void)
|
||||
{
|
||||
int rnd_mode;
|
||||
|
||||
PUT_FSR32(env, *((uint32_t *) &FT0));
|
||||
switch (env->fsr & FSR_RD_MASK) {
|
||||
case FSR_RD_NEAREST:
|
||||
rnd_mode = float_round_nearest_even;
|
||||
|
@ -2510,11 +2509,20 @@ void helper_ldfsr(void)
|
|||
set_float_rounding_mode(rnd_mode, &env->fp_status);
|
||||
}
|
||||
|
||||
void helper_stfsr(void)
|
||||
void helper_ldfsr(uint32_t new_fsr)
|
||||
{
|
||||
*((uint32_t *) &FT0) = GET_FSR32(env);
|
||||
env->fsr = (new_fsr & FSR_LDFSR_MASK) | (env->fsr & FSR_LDFSR_OLDMASK);
|
||||
set_fsr();
|
||||
}
|
||||
|
||||
#ifdef TARGET_SPARC64
|
||||
void helper_ldxfsr(uint64_t new_fsr)
|
||||
{
|
||||
env->fsr = (new_fsr & FSR_LDXFSR_MASK) | (env->fsr & FSR_LDXFSR_OLDMASK);
|
||||
set_fsr();
|
||||
}
|
||||
#endif
|
||||
|
||||
void helper_debug(void)
|
||||
{
|
||||
env->exception_index = EXCP_DEBUG;
|
||||
|
|
|
@ -4368,12 +4368,19 @@ static void disas_sparc_insn(DisasContext * dc)
|
|||
tcg_gen_st_i32(cpu_tmp32, cpu_env,
|
||||
offsetof(CPUState, fpr[rd]));
|
||||
break;
|
||||
case 0x21: /* load fsr */
|
||||
case 0x21: /* ldfsr, V9 ldxfsr */
|
||||
#ifdef TARGET_SPARC64
|
||||
gen_address_mask(dc, cpu_addr);
|
||||
tcg_gen_qemu_ld32u(cpu_tmp32, cpu_addr, dc->mem_idx);
|
||||
tcg_gen_st_i32(cpu_tmp32, cpu_env,
|
||||
offsetof(CPUState, ft0));
|
||||
tcg_gen_helper_0_0(helper_ldfsr);
|
||||
if (rd == 1) {
|
||||
tcg_gen_qemu_ld64(cpu_tmp64, cpu_addr, dc->mem_idx);
|
||||
tcg_gen_helper_0_1(helper_ldxfsr, cpu_tmp64);
|
||||
} else
|
||||
#else
|
||||
{
|
||||
tcg_gen_qemu_ld32u(cpu_tmp32, cpu_addr, dc->mem_idx);
|
||||
tcg_gen_helper_0_1(helper_ldfsr, cpu_tmp32);
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
case 0x22: /* load quad fpreg */
|
||||
{
|
||||
|
@ -4506,11 +4513,19 @@ static void disas_sparc_insn(DisasContext * dc)
|
|||
tcg_gen_qemu_st32(cpu_tmp32, cpu_addr, dc->mem_idx);
|
||||
break;
|
||||
case 0x25: /* stfsr, V9 stxfsr */
|
||||
#ifdef TARGET_SPARC64
|
||||
gen_address_mask(dc, cpu_addr);
|
||||
tcg_gen_helper_0_0(helper_stfsr);
|
||||
tcg_gen_ld_i32(cpu_tmp32, cpu_env,
|
||||
offsetof(CPUState, ft0));
|
||||
tcg_gen_ld_i64(cpu_tmp64, cpu_env, offsetof(CPUState, fsr));
|
||||
if (rd == 1)
|
||||
tcg_gen_qemu_st64(cpu_tmp64, cpu_addr, dc->mem_idx);
|
||||
else {
|
||||
tcg_gen_trunc_tl_i32(cpu_tmp32, cpu_tmp64);
|
||||
tcg_gen_qemu_st32(cpu_tmp32, cpu_addr, dc->mem_idx);
|
||||
}
|
||||
#else
|
||||
tcg_gen_ld_i32(cpu_tmp32, cpu_env, offsetof(CPUState, fsr));
|
||||
tcg_gen_qemu_st32(cpu_tmp32, cpu_addr, dc->mem_idx);
|
||||
#endif
|
||||
break;
|
||||
case 0x26:
|
||||
#ifdef TARGET_SPARC64
|
||||
|
|
Loading…
Reference in New Issue