Cleanup alpha, hppa, or1k wrt tcg_constant_tl.

Implement x86 fcs:fip, fds:fdp.
 Trivial x86 watchpoint cleanup.
 -----BEGIN PGP SIGNATURE-----
 
 iQFRBAABCgA7FiEEekgeeIaLTbaoWgXAZN846K9+IV8FAmDtwQ0dHHJpY2hhcmQu
 aGVuZGVyc29uQGxpbmFyby5vcmcACgkQZN846K9+IV/GnAf/SYNhdmIuKCWk/uk8
 IC0v2sm5KHVFfkfkobQ+04pFB26tX557i2zTtEfj/A5QVlJSvliZowCVIO6JV63N
 9oedLSzdqrxRqDb+Mpmkwnam/k5XfrC20V7os17FuZE98u3Jgky8QNs7Uxq0bCBZ
 01AKB9HNRFKeY2o55IxPwC7CLtyz3SStJJP28aa5ROYK7MIP303qsI5pezgkHgGo
 /qo5GXwHs/Pu4pnFuAJyOfG38wT6uTt7NrAGjTH0VhbAKNMSP/QND+VvxbuCugZR
 6MEVeb+rLy+MN4b3dH6kI89JQvQGBCaWZD/eTF5+8UDPj3I8vpRqufRh8l5WukT1
 Q2g1zA==
 =eqkT
 -----END PGP SIGNATURE-----

Merge remote-tracking branch 'remotes/rth-gitlab/tags/pull-misc-20210713' into staging

Cleanup alpha, hppa, or1k wrt tcg_constant_tl.
Implement x86 fcs:fip, fds:fdp.
Trivial x86 watchpoint cleanup.

# gpg: Signature made Tue 13 Jul 2021 17:36:29 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-gitlab/tags/pull-misc-20210713:
  target/hppa: Clean up DisasCond
  target/hppa: Use tcg_constant_*
  target/openrisc: Use dc->zero in gen_add, gen_addc
  target/openrisc: Cache constant 0 in DisasContext
  target/openrisc: Use tcg_constant_tl for dc->R0
  target/openrisc: Use tcg_constant_*
  target/alpha: Use tcg_constant_* elsewhere
  target/alpha: Use tcg_constant_i64 for zero and lit
  target/alpha: Use dest_sink for HW_RET temporary
  target/alpha: Store set into rx flag
  target/i386: Correct implementation for FCS, FIP, FDS and FDP
  target/i386: Split out do_fninit
  target/i386: Trivial code motion and code style fix
  target/i386: Tidy hw_breakpoint_remove

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
This commit is contained in:
Peter Maydell 2021-07-14 14:12:08 +01:00
commit 20a9676179
7 changed files with 599 additions and 656 deletions

View File

@ -66,8 +66,6 @@ struct DisasContext {
/* Temporaries for $31 and $f31 as source and destination. */ /* Temporaries for $31 and $f31 as source and destination. */
TCGv zero; TCGv zero;
TCGv sink; TCGv sink;
/* Temporary for immediate constants. */
TCGv lit;
}; };
/* Target-specific return values from translate_one, indicating the /* Target-specific return values from translate_one, indicating the
@ -157,7 +155,7 @@ void alpha_translate_init(void)
static TCGv load_zero(DisasContext *ctx) static TCGv load_zero(DisasContext *ctx)
{ {
if (!ctx->zero) { if (!ctx->zero) {
ctx->zero = tcg_const_i64(0); ctx->zero = tcg_constant_i64(0);
} }
return ctx->zero; return ctx->zero;
} }
@ -177,14 +175,6 @@ static void free_context_temps(DisasContext *ctx)
tcg_temp_free(ctx->sink); tcg_temp_free(ctx->sink);
ctx->sink = NULL; ctx->sink = NULL;
} }
if (ctx->zero) {
tcg_temp_free(ctx->zero);
ctx->zero = NULL;
}
if (ctx->lit) {
tcg_temp_free(ctx->lit);
ctx->lit = NULL;
}
} }
static TCGv load_gpr(DisasContext *ctx, unsigned reg) static TCGv load_gpr(DisasContext *ctx, unsigned reg)
@ -200,8 +190,7 @@ static TCGv load_gpr_lit(DisasContext *ctx, unsigned reg,
uint8_t lit, bool islit) uint8_t lit, bool islit)
{ {
if (islit) { if (islit) {
ctx->lit = tcg_const_i64(lit); return tcg_constant_i64(lit);
return ctx->lit;
} else if (likely(reg < 31)) { } else if (likely(reg < 31)) {
return ctx->ir[reg]; return ctx->ir[reg];
} else { } else {
@ -261,11 +250,9 @@ static void gen_excp_1(int exception, int error_code)
{ {
TCGv_i32 tmp1, tmp2; TCGv_i32 tmp1, tmp2;
tmp1 = tcg_const_i32(exception); tmp1 = tcg_constant_i32(exception);
tmp2 = tcg_const_i32(error_code); tmp2 = tcg_constant_i32(error_code);
gen_helper_excp(cpu_env, tmp1, tmp2); gen_helper_excp(cpu_env, tmp1, tmp2);
tcg_temp_free_i32(tmp2);
tcg_temp_free_i32(tmp1);
} }
static DisasJumpType gen_excp(DisasContext *ctx, int exception, int error_code) static DisasJumpType gen_excp(DisasContext *ctx, int exception, int error_code)
@ -485,15 +472,11 @@ static DisasJumpType gen_bcond_internal(DisasContext *ctx, TCGCond cond,
return DISAS_NORETURN; return DISAS_NORETURN;
} else { } else {
TCGv_i64 z = tcg_const_i64(0); TCGv_i64 z = load_zero(ctx);
TCGv_i64 d = tcg_const_i64(dest); TCGv_i64 d = tcg_constant_i64(dest);
TCGv_i64 p = tcg_const_i64(ctx->base.pc_next); TCGv_i64 p = tcg_constant_i64(ctx->base.pc_next);
tcg_gen_movcond_i64(cond, cpu_pc, cmp, z, d, p); tcg_gen_movcond_i64(cond, cpu_pc, cmp, z, d, p);
tcg_temp_free_i64(z);
tcg_temp_free_i64(d);
tcg_temp_free_i64(p);
return DISAS_PC_UPDATED; return DISAS_PC_UPDATED;
} }
} }
@ -695,22 +678,19 @@ static void gen_fp_exc_raise(int rc, int fn11)
if (!(fn11 & QUAL_I)) { if (!(fn11 & QUAL_I)) {
ignore |= FPCR_INE; ignore |= FPCR_INE;
} }
ign = tcg_const_i32(ignore); ign = tcg_constant_i32(ignore);
/* ??? Pass in the regno of the destination so that the helper can /* ??? Pass in the regno of the destination so that the helper can
set EXC_MASK, which contains a bitmask of destination registers set EXC_MASK, which contains a bitmask of destination registers
that have caused arithmetic traps. A simple userspace emulation that have caused arithmetic traps. A simple userspace emulation
does not require this. We do need it for a guest kernel's entArith, does not require this. We do need it for a guest kernel's entArith,
or if we were to do something clever with imprecise exceptions. */ or if we were to do something clever with imprecise exceptions. */
reg = tcg_const_i32(rc + 32); reg = tcg_constant_i32(rc + 32);
if (fn11 & QUAL_S) { if (fn11 & QUAL_S) {
gen_helper_fp_exc_raise_s(cpu_env, ign, reg); gen_helper_fp_exc_raise_s(cpu_env, ign, reg);
} else { } else {
gen_helper_fp_exc_raise(cpu_env, ign, reg); gen_helper_fp_exc_raise(cpu_env, ign, reg);
} }
tcg_temp_free_i32(reg);
tcg_temp_free_i32(ign);
} }
static void gen_cvtlq(TCGv vc, TCGv vb) static void gen_cvtlq(TCGv vc, TCGv vb)
@ -803,7 +783,7 @@ IEEE_INTCVT(cvtqt)
static void gen_cpy_mask(TCGv vc, TCGv va, TCGv vb, bool inv_a, uint64_t mask) static void gen_cpy_mask(TCGv vc, TCGv va, TCGv vb, bool inv_a, uint64_t mask)
{ {
TCGv vmask = tcg_const_i64(mask); TCGv vmask = tcg_constant_i64(mask);
TCGv tmp = tcg_temp_new_i64(); TCGv tmp = tcg_temp_new_i64();
if (inv_a) { if (inv_a) {
@ -815,7 +795,6 @@ static void gen_cpy_mask(TCGv vc, TCGv va, TCGv vb, bool inv_a, uint64_t mask)
tcg_gen_andc_i64(vc, vb, vmask); tcg_gen_andc_i64(vc, vb, vmask);
tcg_gen_or_i64(vc, vc, tmp); tcg_gen_or_i64(vc, vc, tmp);
tcg_temp_free(vmask);
tcg_temp_free(tmp); tcg_temp_free(tmp);
} }
@ -1084,15 +1063,11 @@ static void gen_msk_l(DisasContext *ctx, TCGv vc, TCGv va, int rb, bool islit,
static void gen_rx(DisasContext *ctx, int ra, int set) static void gen_rx(DisasContext *ctx, int ra, int set)
{ {
TCGv tmp;
if (ra != 31) { if (ra != 31) {
ld_flag_byte(ctx->ir[ra], ENV_FLAG_RX_SHIFT); ld_flag_byte(ctx->ir[ra], ENV_FLAG_RX_SHIFT);
} }
tmp = tcg_const_i64(set); st_flag_byte(tcg_constant_i64(set), ENV_FLAG_RX_SHIFT);
st_flag_byte(ctx->ir[ra], ENV_FLAG_RX_SHIFT);
tcg_temp_free(tmp);
} }
static DisasJumpType gen_call_pal(DisasContext *ctx, int palcode) static DisasJumpType gen_call_pal(DisasContext *ctx, int palcode)
@ -1193,12 +1168,9 @@ static DisasJumpType gen_call_pal(DisasContext *ctx, int palcode)
case 0x3E: case 0x3E:
/* WTINT */ /* WTINT */
{ tcg_gen_st_i32(tcg_constant_i32(1), cpu_env,
TCGv_i32 tmp = tcg_const_i32(1); -offsetof(AlphaCPU, env) +
tcg_gen_st_i32(tmp, cpu_env, -offsetof(AlphaCPU, env) + offsetof(CPUState, halted));
offsetof(CPUState, halted));
tcg_temp_free_i32(tmp);
}
tcg_gen_movi_i64(ctx->ir[IR_V0], 0); tcg_gen_movi_i64(ctx->ir[IR_V0], 0);
return gen_excp(ctx, EXCP_HALTED, 0); return gen_excp(ctx, EXCP_HALTED, 0);
@ -1349,12 +1321,8 @@ static DisasJumpType gen_mtpr(DisasContext *ctx, TCGv vb, int regno)
case 253: case 253:
/* WAIT */ /* WAIT */
{ tcg_gen_st_i32(tcg_constant_i32(1), cpu_env,
TCGv_i32 tmp = tcg_const_i32(1); -offsetof(AlphaCPU, env) + offsetof(CPUState, halted));
tcg_gen_st_i32(tmp, cpu_env, -offsetof(AlphaCPU, env) +
offsetof(CPUState, halted));
tcg_temp_free_i32(tmp);
}
return gen_excp(ctx, EXCP_HALTED, 0); return gen_excp(ctx, EXCP_HALTED, 0);
case 252: case 252:
@ -2721,15 +2689,14 @@ static DisasJumpType translate_one(DisasContext *ctx, uint32_t insn)
/* Pre-EV6 CPUs interpreted this as HW_REI, loading the return /* Pre-EV6 CPUs interpreted this as HW_REI, loading the return
address from EXC_ADDR. This turns out to be useful for our address from EXC_ADDR. This turns out to be useful for our
emulation PALcode, so continue to accept it. */ emulation PALcode, so continue to accept it. */
ctx->lit = vb = tcg_temp_new(); vb = dest_sink(ctx);
tcg_gen_ld_i64(vb, cpu_env, offsetof(CPUAlphaState, exc_addr)); tcg_gen_ld_i64(vb, cpu_env, offsetof(CPUAlphaState, exc_addr));
} else { } else {
vb = load_gpr(ctx, rb); vb = load_gpr(ctx, rb);
} }
tcg_gen_movi_i64(cpu_lock_addr, -1); tcg_gen_movi_i64(cpu_lock_addr, -1);
st_flag_byte(load_zero(ctx), ENV_FLAG_RX_SHIFT);
tmp = tcg_temp_new(); tmp = tcg_temp_new();
tcg_gen_movi_i64(tmp, 0);
st_flag_byte(tmp, ENV_FLAG_RX_SHIFT);
tcg_gen_andi_i64(tmp, vb, 1); tcg_gen_andi_i64(tmp, vb, 1);
st_flag_byte(tmp, ENV_FLAG_PAL_SHIFT); st_flag_byte(tmp, ENV_FLAG_PAL_SHIFT);
tcg_temp_free(tmp); tcg_temp_free(tmp);
@ -2996,7 +2963,6 @@ static void alpha_tr_init_disas_context(DisasContextBase *dcbase, CPUState *cpu)
ctx->zero = NULL; ctx->zero = NULL;
ctx->sink = NULL; ctx->sink = NULL;
ctx->lit = NULL;
/* Bound the number of insns to execute to those left on the page. */ /* Bound the number of insns to execute to those left on the page. */
bound = -(ctx->base.pc_first | TARGET_PAGE_MASK) / 4; bound = -(ctx->base.pc_first | TARGET_PAGE_MASK) / 4;

View File

@ -144,6 +144,7 @@
#define tcg_gen_sextract_reg tcg_gen_sextract_i64 #define tcg_gen_sextract_reg tcg_gen_sextract_i64
#define tcg_const_reg tcg_const_i64 #define tcg_const_reg tcg_const_i64
#define tcg_const_local_reg tcg_const_local_i64 #define tcg_const_local_reg tcg_const_local_i64
#define tcg_constant_reg tcg_constant_i64
#define tcg_gen_movcond_reg tcg_gen_movcond_i64 #define tcg_gen_movcond_reg tcg_gen_movcond_i64
#define tcg_gen_add2_reg tcg_gen_add2_i64 #define tcg_gen_add2_reg tcg_gen_add2_i64
#define tcg_gen_sub2_reg tcg_gen_sub2_i64 #define tcg_gen_sub2_reg tcg_gen_sub2_i64
@ -238,6 +239,7 @@
#define tcg_gen_sextract_reg tcg_gen_sextract_i32 #define tcg_gen_sextract_reg tcg_gen_sextract_i32
#define tcg_const_reg tcg_const_i32 #define tcg_const_reg tcg_const_i32
#define tcg_const_local_reg tcg_const_local_i32 #define tcg_const_local_reg tcg_const_local_i32
#define tcg_constant_reg tcg_constant_i32
#define tcg_gen_movcond_reg tcg_gen_movcond_i32 #define tcg_gen_movcond_reg tcg_gen_movcond_i32
#define tcg_gen_add2_reg tcg_gen_add2_i32 #define tcg_gen_add2_reg tcg_gen_add2_i32
#define tcg_gen_sub2_reg tcg_gen_sub2_i32 #define tcg_gen_sub2_reg tcg_gen_sub2_i32
@ -250,8 +252,6 @@
typedef struct DisasCond { typedef struct DisasCond {
TCGCond c; TCGCond c;
TCGv_reg a0, a1; TCGv_reg a0, a1;
bool a0_is_n;
bool a1_is_0;
} DisasCond; } DisasCond;
typedef struct DisasContext { typedef struct DisasContext {
@ -446,9 +446,7 @@ static DisasCond cond_make_n(void)
return (DisasCond){ return (DisasCond){
.c = TCG_COND_NE, .c = TCG_COND_NE,
.a0 = cpu_psw_n, .a0 = cpu_psw_n,
.a0_is_n = true, .a1 = tcg_constant_reg(0)
.a1 = NULL,
.a1_is_0 = true
}; };
} }
@ -456,7 +454,7 @@ static DisasCond cond_make_0_tmp(TCGCond c, TCGv_reg a0)
{ {
assert (c != TCG_COND_NEVER && c != TCG_COND_ALWAYS); assert (c != TCG_COND_NEVER && c != TCG_COND_ALWAYS);
return (DisasCond){ return (DisasCond){
.c = c, .a0 = a0, .a1_is_0 = true .c = c, .a0 = a0, .a1 = tcg_constant_reg(0)
}; };
} }
@ -480,26 +478,14 @@ static DisasCond cond_make(TCGCond c, TCGv_reg a0, TCGv_reg a1)
return r; return r;
} }
static void cond_prep(DisasCond *cond)
{
if (cond->a1_is_0) {
cond->a1_is_0 = false;
cond->a1 = tcg_const_reg(0);
}
}
static void cond_free(DisasCond *cond) static void cond_free(DisasCond *cond)
{ {
switch (cond->c) { switch (cond->c) {
default: default:
if (!cond->a0_is_n) { if (cond->a0 != cpu_psw_n) {
tcg_temp_free(cond->a0); tcg_temp_free(cond->a0);
} }
if (!cond->a1_is_0) { tcg_temp_free(cond->a1);
tcg_temp_free(cond->a1);
}
cond->a0_is_n = false;
cond->a1_is_0 = false;
cond->a0 = NULL; cond->a0 = NULL;
cond->a1 = NULL; cond->a1 = NULL;
/* fallthru */ /* fallthru */
@ -557,9 +543,8 @@ static TCGv_reg dest_gpr(DisasContext *ctx, unsigned reg)
static void save_or_nullify(DisasContext *ctx, TCGv_reg dest, TCGv_reg t) static void save_or_nullify(DisasContext *ctx, TCGv_reg dest, TCGv_reg t)
{ {
if (ctx->null_cond.c != TCG_COND_NEVER) { if (ctx->null_cond.c != TCG_COND_NEVER) {
cond_prep(&ctx->null_cond);
tcg_gen_movcond_reg(ctx->null_cond.c, dest, ctx->null_cond.a0, tcg_gen_movcond_reg(ctx->null_cond.c, dest, ctx->null_cond.a0,
ctx->null_cond.a1, dest, t); ctx->null_cond.a1, dest, t);
} else { } else {
tcg_gen_mov_reg(dest, t); tcg_gen_mov_reg(dest, t);
} }
@ -666,11 +651,9 @@ static void nullify_over(DisasContext *ctx)
assert(ctx->null_cond.c != TCG_COND_ALWAYS); assert(ctx->null_cond.c != TCG_COND_ALWAYS);
ctx->null_lab = gen_new_label(); ctx->null_lab = gen_new_label();
cond_prep(&ctx->null_cond);
/* If we're using PSW[N], copy it to a temp because... */ /* If we're using PSW[N], copy it to a temp because... */
if (ctx->null_cond.a0_is_n) { if (ctx->null_cond.a0 == cpu_psw_n) {
ctx->null_cond.a0_is_n = false;
ctx->null_cond.a0 = tcg_temp_new(); ctx->null_cond.a0 = tcg_temp_new();
tcg_gen_mov_reg(ctx->null_cond.a0, cpu_psw_n); tcg_gen_mov_reg(ctx->null_cond.a0, cpu_psw_n);
} }
@ -683,7 +666,7 @@ static void nullify_over(DisasContext *ctx)
} }
tcg_gen_brcond_reg(ctx->null_cond.c, ctx->null_cond.a0, tcg_gen_brcond_reg(ctx->null_cond.c, ctx->null_cond.a0,
ctx->null_cond.a1, ctx->null_lab); ctx->null_cond.a1, ctx->null_lab);
cond_free(&ctx->null_cond); cond_free(&ctx->null_cond);
} }
} }
@ -697,10 +680,9 @@ static void nullify_save(DisasContext *ctx)
} }
return; return;
} }
if (!ctx->null_cond.a0_is_n) { if (ctx->null_cond.a0 != cpu_psw_n) {
cond_prep(&ctx->null_cond);
tcg_gen_setcond_reg(ctx->null_cond.c, cpu_psw_n, tcg_gen_setcond_reg(ctx->null_cond.c, cpu_psw_n,
ctx->null_cond.a0, ctx->null_cond.a1); ctx->null_cond.a0, ctx->null_cond.a1);
ctx->psw_n_nonzero = true; ctx->psw_n_nonzero = true;
} }
cond_free(&ctx->null_cond); cond_free(&ctx->null_cond);
@ -771,9 +753,7 @@ static inline target_ureg iaoq_dest(DisasContext *ctx, target_sreg disp)
static void gen_excp_1(int exception) static void gen_excp_1(int exception)
{ {
TCGv_i32 t = tcg_const_i32(exception); gen_helper_excp(cpu_env, tcg_constant_i32(exception));
gen_helper_excp(cpu_env, t);
tcg_temp_free_i32(t);
} }
static void gen_excp(DisasContext *ctx, int exception) static void gen_excp(DisasContext *ctx, int exception)
@ -787,12 +767,9 @@ static void gen_excp(DisasContext *ctx, int exception)
static bool gen_excp_iir(DisasContext *ctx, int exc) static bool gen_excp_iir(DisasContext *ctx, int exc)
{ {
TCGv_reg tmp;
nullify_over(ctx); nullify_over(ctx);
tmp = tcg_const_reg(ctx->insn); tcg_gen_st_reg(tcg_constant_reg(ctx->insn),
tcg_gen_st_reg(tmp, cpu_env, offsetof(CPUHPPAState, cr[CR_IIR])); cpu_env, offsetof(CPUHPPAState, cr[CR_IIR]));
tcg_temp_free(tmp);
gen_excp(ctx, exc); gen_excp(ctx, exc);
return nullify_end(ctx); return nullify_end(ctx);
} }
@ -1150,13 +1127,12 @@ static void do_add(DisasContext *ctx, unsigned rt, TCGv_reg in1,
} }
if (!is_l || cond_need_cb(c)) { if (!is_l || cond_need_cb(c)) {
TCGv_reg zero = tcg_const_reg(0); TCGv_reg zero = tcg_constant_reg(0);
cb_msb = get_temp(ctx); cb_msb = get_temp(ctx);
tcg_gen_add2_reg(dest, cb_msb, in1, zero, in2, zero); tcg_gen_add2_reg(dest, cb_msb, in1, zero, in2, zero);
if (is_c) { if (is_c) {
tcg_gen_add2_reg(dest, cb_msb, dest, cb_msb, cpu_psw_cb_msb, zero); tcg_gen_add2_reg(dest, cb_msb, dest, cb_msb, cpu_psw_cb_msb, zero);
} }
tcg_temp_free(zero);
if (!is_l) { if (!is_l) {
cb = get_temp(ctx); cb = get_temp(ctx);
tcg_gen_xor_reg(cb, in1, in2); tcg_gen_xor_reg(cb, in1, in2);
@ -1182,7 +1158,6 @@ static void do_add(DisasContext *ctx, unsigned rt, TCGv_reg in1,
/* Emit any conditional trap before any writeback. */ /* Emit any conditional trap before any writeback. */
cond = do_cond(cf, dest, cb_msb, sv); cond = do_cond(cf, dest, cb_msb, sv);
if (is_tc) { if (is_tc) {
cond_prep(&cond);
tmp = tcg_temp_new(); tmp = tcg_temp_new();
tcg_gen_setcond_reg(cond.c, tmp, cond.a0, cond.a1); tcg_gen_setcond_reg(cond.c, tmp, cond.a0, cond.a1);
gen_helper_tcond(cpu_env, tmp); gen_helper_tcond(cpu_env, tmp);
@ -1242,7 +1217,7 @@ static void do_sub(DisasContext *ctx, unsigned rt, TCGv_reg in1,
cb = tcg_temp_new(); cb = tcg_temp_new();
cb_msb = tcg_temp_new(); cb_msb = tcg_temp_new();
zero = tcg_const_reg(0); zero = tcg_constant_reg(0);
if (is_b) { if (is_b) {
/* DEST,C = IN1 + ~IN2 + C. */ /* DEST,C = IN1 + ~IN2 + C. */
tcg_gen_not_reg(cb, in2); tcg_gen_not_reg(cb, in2);
@ -1258,7 +1233,6 @@ static void do_sub(DisasContext *ctx, unsigned rt, TCGv_reg in1,
tcg_gen_eqv_reg(cb, in1, in2); tcg_gen_eqv_reg(cb, in1, in2);
tcg_gen_xor_reg(cb, cb, dest); tcg_gen_xor_reg(cb, cb, dest);
} }
tcg_temp_free(zero);
/* Compute signed overflow if required. */ /* Compute signed overflow if required. */
sv = NULL; sv = NULL;
@ -1278,7 +1252,6 @@ static void do_sub(DisasContext *ctx, unsigned rt, TCGv_reg in1,
/* Emit any conditional trap before any writeback. */ /* Emit any conditional trap before any writeback. */
if (is_tc) { if (is_tc) {
cond_prep(&cond);
tmp = tcg_temp_new(); tmp = tcg_temp_new();
tcg_gen_setcond_reg(cond.c, tmp, cond.a0, cond.a1); tcg_gen_setcond_reg(cond.c, tmp, cond.a0, cond.a1);
gen_helper_tcond(cpu_env, tmp); gen_helper_tcond(cpu_env, tmp);
@ -1404,7 +1377,6 @@ static void do_unit(DisasContext *ctx, unsigned rt, TCGv_reg in1,
if (is_tc) { if (is_tc) {
TCGv_reg tmp = tcg_temp_new(); TCGv_reg tmp = tcg_temp_new();
cond_prep(&cond);
tcg_gen_setcond_reg(cond.c, tmp, cond.a0, cond.a1); tcg_gen_setcond_reg(cond.c, tmp, cond.a0, cond.a1);
gen_helper_tcond(cpu_env, tmp); gen_helper_tcond(cpu_env, tmp);
tcg_temp_free(tmp); tcg_temp_free(tmp);
@ -1860,7 +1832,6 @@ static bool do_cbranch(DisasContext *ctx, target_sreg disp, bool is_n,
} }
taken = gen_new_label(); taken = gen_new_label();
cond_prep(cond);
tcg_gen_brcond_reg(c, cond->a0, cond->a1, taken); tcg_gen_brcond_reg(c, cond->a0, cond->a1, taken);
cond_free(cond); cond_free(cond);
@ -1957,7 +1928,6 @@ static bool do_ibranch(DisasContext *ctx, TCGv_reg dest,
tcg_gen_lookup_and_goto_ptr(); tcg_gen_lookup_and_goto_ptr();
return nullify_end(ctx); return nullify_end(ctx);
} else { } else {
cond_prep(&ctx->null_cond);
c = ctx->null_cond.c; c = ctx->null_cond.c;
a0 = ctx->null_cond.a0; a0 = ctx->null_cond.a0;
a1 = ctx->null_cond.a1; a1 = ctx->null_cond.a1;
@ -2449,17 +2419,16 @@ static bool trans_probe(DisasContext *ctx, arg_probe *a)
form_gva(ctx, &addr, &ofs, a->b, 0, 0, 0, a->sp, 0, false); form_gva(ctx, &addr, &ofs, a->b, 0, 0, 0, a->sp, 0, false);
if (a->imm) { if (a->imm) {
level = tcg_const_i32(a->ri); level = tcg_constant_i32(a->ri);
} else { } else {
level = tcg_temp_new_i32(); level = tcg_temp_new_i32();
tcg_gen_trunc_reg_i32(level, load_gpr(ctx, a->ri)); tcg_gen_trunc_reg_i32(level, load_gpr(ctx, a->ri));
tcg_gen_andi_i32(level, level, 3); tcg_gen_andi_i32(level, level, 3);
} }
want = tcg_const_i32(a->write ? PAGE_WRITE : PAGE_READ); want = tcg_constant_i32(a->write ? PAGE_WRITE : PAGE_READ);
gen_helper_probe(dest, cpu_env, addr, level, want); gen_helper_probe(dest, cpu_env, addr, level, want);
tcg_temp_free_i32(want);
tcg_temp_free_i32(level); tcg_temp_free_i32(level);
save_gpr(ctx, a->t, dest); save_gpr(ctx, a->t, dest);
@ -2599,17 +2568,13 @@ static bool trans_lpa(DisasContext *ctx, arg_ldst *a)
static bool trans_lci(DisasContext *ctx, arg_lci *a) static bool trans_lci(DisasContext *ctx, arg_lci *a)
{ {
TCGv_reg ci;
CHECK_MOST_PRIVILEGED(EXCP_PRIV_OPR); CHECK_MOST_PRIVILEGED(EXCP_PRIV_OPR);
/* The Coherence Index is an implementation-defined function of the /* The Coherence Index is an implementation-defined function of the
physical address. Two addresses with the same CI have a coherent physical address. Two addresses with the same CI have a coherent
view of the cache. Our implementation is to return 0 for all, view of the cache. Our implementation is to return 0 for all,
since the entire address space is coherent. */ since the entire address space is coherent. */
ci = tcg_const_reg(0); save_gpr(ctx, a->t, tcg_constant_reg(0));
save_gpr(ctx, a->t, ci);
tcg_temp_free(ci);
cond_free(&ctx->null_cond); cond_free(&ctx->null_cond);
return true; return true;
@ -2710,8 +2675,6 @@ static bool trans_or(DisasContext *ctx, arg_rrr_cf *a)
* currently implemented as idle. * currently implemented as idle.
*/ */
if ((rt == 10 || rt == 31) && r1 == rt && r2 == rt) { /* PAUSE */ if ((rt == 10 || rt == 31) && r1 == rt && r2 == rt) { /* PAUSE */
TCGv_i32 tmp;
/* No need to check for supervisor, as userland can only pause /* No need to check for supervisor, as userland can only pause
until the next timer interrupt. */ until the next timer interrupt. */
nullify_over(ctx); nullify_over(ctx);
@ -2722,10 +2685,8 @@ static bool trans_or(DisasContext *ctx, arg_rrr_cf *a)
nullify_set(ctx, 0); nullify_set(ctx, 0);
/* Tell the qemu main loop to halt until this cpu has work. */ /* Tell the qemu main loop to halt until this cpu has work. */
tmp = tcg_const_i32(1); tcg_gen_st_i32(tcg_constant_i32(1), cpu_env,
tcg_gen_st_i32(tmp, cpu_env, -offsetof(HPPACPU, env) + offsetof(CPUState, halted) - offsetof(HPPACPU, env));
offsetof(CPUState, halted));
tcg_temp_free_i32(tmp);
gen_excp_1(EXCP_HALTED); gen_excp_1(EXCP_HALTED);
ctx->base.is_jmp = DISAS_NORETURN; ctx->base.is_jmp = DISAS_NORETURN;
@ -2833,7 +2794,7 @@ static bool trans_ds(DisasContext *ctx, arg_rrr_cf *a)
add2 = tcg_temp_new(); add2 = tcg_temp_new();
addc = tcg_temp_new(); addc = tcg_temp_new();
dest = tcg_temp_new(); dest = tcg_temp_new();
zero = tcg_const_reg(0); zero = tcg_constant_reg(0);
/* Form R1 << 1 | PSW[CB]{8}. */ /* Form R1 << 1 | PSW[CB]{8}. */
tcg_gen_add_reg(add1, in1, in1); tcg_gen_add_reg(add1, in1, in1);
@ -2851,7 +2812,6 @@ static bool trans_ds(DisasContext *ctx, arg_rrr_cf *a)
tcg_gen_add2_i32(dest, cpu_psw_cb_msb, dest, cpu_psw_cb_msb, addc, zero); tcg_gen_add2_i32(dest, cpu_psw_cb_msb, dest, cpu_psw_cb_msb, addc, zero);
tcg_temp_free(addc); tcg_temp_free(addc);
tcg_temp_free(zero);
/* Write back the result register. */ /* Write back the result register. */
save_gpr(ctx, a->t, dest); save_gpr(ctx, a->t, dest);
@ -2967,9 +2927,8 @@ static bool trans_ldc(DisasContext *ctx, arg_ldst *a)
*/ */
gen_helper_ldc_check(addr); gen_helper_ldc_check(addr);
zero = tcg_const_reg(0); zero = tcg_constant_reg(0);
tcg_gen_atomic_xchg_reg(dest, addr, zero, ctx->mmu_idx, mop); tcg_gen_atomic_xchg_reg(dest, addr, zero, ctx->mmu_idx, mop);
tcg_temp_free(zero);
if (a->m) { if (a->m) {
save_gpr(ctx, a->b, ofs); save_gpr(ctx, a->b, ofs);
@ -3882,15 +3841,13 @@ static bool trans_fcmp_f(DisasContext *ctx, arg_fclass2 *a)
ta = load_frw0_i32(a->r1); ta = load_frw0_i32(a->r1);
tb = load_frw0_i32(a->r2); tb = load_frw0_i32(a->r2);
ty = tcg_const_i32(a->y); ty = tcg_constant_i32(a->y);
tc = tcg_const_i32(a->c); tc = tcg_constant_i32(a->c);
gen_helper_fcmp_s(cpu_env, ta, tb, ty, tc); gen_helper_fcmp_s(cpu_env, ta, tb, ty, tc);
tcg_temp_free_i32(ta); tcg_temp_free_i32(ta);
tcg_temp_free_i32(tb); tcg_temp_free_i32(tb);
tcg_temp_free_i32(ty);
tcg_temp_free_i32(tc);
return nullify_end(ctx); return nullify_end(ctx);
} }
@ -3904,15 +3861,13 @@ static bool trans_fcmp_d(DisasContext *ctx, arg_fclass2 *a)
ta = load_frd0(a->r1); ta = load_frd0(a->r1);
tb = load_frd0(a->r2); tb = load_frd0(a->r2);
ty = tcg_const_i32(a->y); ty = tcg_constant_i32(a->y);
tc = tcg_const_i32(a->c); tc = tcg_constant_i32(a->c);
gen_helper_fcmp_d(cpu_env, ta, tb, ty, tc); gen_helper_fcmp_d(cpu_env, ta, tb, ty, tc);
tcg_temp_free_i64(ta); tcg_temp_free_i64(ta);
tcg_temp_free_i64(tb); tcg_temp_free_i64(tb);
tcg_temp_free_i32(ty);
tcg_temp_free_i32(tc);
return nullify_end(ctx); return nullify_end(ctx);
} }

View File

@ -1437,6 +1437,8 @@ typedef struct CPUX86State {
FPReg fpregs[8]; FPReg fpregs[8];
/* KVM-only so far */ /* KVM-only so far */
uint16_t fpop; uint16_t fpop;
uint16_t fpcs;
uint16_t fpds;
uint64_t fpip; uint64_t fpip;
uint64_t fpdp; uint64_t fpdp;

View File

@ -727,10 +727,14 @@ void helper_fwait(CPUX86State *env)
} }
} }
void helper_fninit(CPUX86State *env) static void do_fninit(CPUX86State *env)
{ {
env->fpus = 0; env->fpus = 0;
env->fpstt = 0; env->fpstt = 0;
env->fpcs = 0;
env->fpds = 0;
env->fpip = 0;
env->fpdp = 0;
cpu_set_fpuc(env, 0x37f); cpu_set_fpuc(env, 0x37f);
env->fptags[0] = 1; env->fptags[0] = 1;
env->fptags[1] = 1; env->fptags[1] = 1;
@ -742,6 +746,11 @@ void helper_fninit(CPUX86State *env)
env->fptags[7] = 1; env->fptags[7] = 1;
} }
void helper_fninit(CPUX86State *env)
{
do_fninit(env);
}
/* BCD ops */ /* BCD ops */
void helper_fbld_ST0(CPUX86State *env, target_ulong ptr) void helper_fbld_ST0(CPUX86State *env, target_ulong ptr)
@ -2373,19 +2382,19 @@ static void do_fstenv(CPUX86State *env, target_ulong ptr, int data32,
cpu_stl_data_ra(env, ptr, env->fpuc, retaddr); cpu_stl_data_ra(env, ptr, env->fpuc, retaddr);
cpu_stl_data_ra(env, ptr + 4, fpus, retaddr); cpu_stl_data_ra(env, ptr + 4, fpus, retaddr);
cpu_stl_data_ra(env, ptr + 8, fptag, retaddr); cpu_stl_data_ra(env, ptr + 8, fptag, retaddr);
cpu_stl_data_ra(env, ptr + 12, 0, retaddr); /* fpip */ cpu_stl_data_ra(env, ptr + 12, env->fpip, retaddr); /* fpip */
cpu_stl_data_ra(env, ptr + 16, 0, retaddr); /* fpcs */ cpu_stl_data_ra(env, ptr + 16, env->fpcs, retaddr); /* fpcs */
cpu_stl_data_ra(env, ptr + 20, 0, retaddr); /* fpoo */ cpu_stl_data_ra(env, ptr + 20, env->fpdp, retaddr); /* fpoo */
cpu_stl_data_ra(env, ptr + 24, 0, retaddr); /* fpos */ cpu_stl_data_ra(env, ptr + 24, env->fpds, retaddr); /* fpos */
} else { } else {
/* 16 bit */ /* 16 bit */
cpu_stw_data_ra(env, ptr, env->fpuc, retaddr); cpu_stw_data_ra(env, ptr, env->fpuc, retaddr);
cpu_stw_data_ra(env, ptr + 2, fpus, retaddr); cpu_stw_data_ra(env, ptr + 2, fpus, retaddr);
cpu_stw_data_ra(env, ptr + 4, fptag, retaddr); cpu_stw_data_ra(env, ptr + 4, fptag, retaddr);
cpu_stw_data_ra(env, ptr + 6, 0, retaddr); cpu_stw_data_ra(env, ptr + 6, env->fpip, retaddr);
cpu_stw_data_ra(env, ptr + 8, 0, retaddr); cpu_stw_data_ra(env, ptr + 8, env->fpcs, retaddr);
cpu_stw_data_ra(env, ptr + 10, 0, retaddr); cpu_stw_data_ra(env, ptr + 10, env->fpdp, retaddr);
cpu_stw_data_ra(env, ptr + 12, 0, retaddr); cpu_stw_data_ra(env, ptr + 12, env->fpds, retaddr);
} }
} }
@ -2451,18 +2460,7 @@ static void do_fsave(CPUX86State *env, target_ulong ptr, int data32,
ptr += 10; ptr += 10;
} }
/* fninit */ do_fninit(env);
env->fpus = 0;
env->fpstt = 0;
cpu_set_fpuc(env, 0x37f);
env->fptags[0] = 1;
env->fptags[1] = 1;
env->fptags[2] = 1;
env->fptags[3] = 1;
env->fptags[4] = 1;
env->fptags[5] = 1;
env->fptags[6] = 1;
env->fptags[7] = 1;
} }
void helper_fsave(CPUX86State *env, target_ulong ptr, int data32) void helper_fsave(CPUX86State *env, target_ulong ptr, int data32)
@ -2834,7 +2832,7 @@ void helper_xrstor(CPUX86State *env, target_ulong ptr, uint64_t rfbm)
if (xstate_bv & XSTATE_FP_MASK) { if (xstate_bv & XSTATE_FP_MASK) {
do_xrstor_fpu(env, ptr, ra); do_xrstor_fpu(env, ptr, ra);
} else { } else {
helper_fninit(env); do_fninit(env);
memset(env->fpregs, 0, sizeof(env->fpregs)); memset(env->fpregs, 0, sizeof(env->fpregs));
} }
} }

View File

@ -109,9 +109,9 @@ static void hw_breakpoint_remove(CPUX86State *env, int index)
case DR7_TYPE_DATA_WR: case DR7_TYPE_DATA_WR:
case DR7_TYPE_DATA_RW: case DR7_TYPE_DATA_RW:
if (env->cpu_breakpoint[index]) { if (env->cpu_watchpoint[index]) {
cpu_watchpoint_remove_by_ref(cs, env->cpu_watchpoint[index]); cpu_watchpoint_remove_by_ref(cs, env->cpu_watchpoint[index]);
env->cpu_breakpoint[index] = NULL; env->cpu_watchpoint[index] = NULL;
} }
break; break;

File diff suppressed because it is too large Load Diff

View File

@ -52,6 +52,8 @@ typedef struct DisasContext {
/* The temporary corresponding to register 0 for this compilation. */ /* The temporary corresponding to register 0 for this compilation. */
TCGv R0; TCGv R0;
/* The constant zero. */
TCGv zero;
} DisasContext; } DisasContext;
static inline bool is_user(DisasContext *dc) static inline bool is_user(DisasContext *dc)
@ -129,9 +131,7 @@ void openrisc_translate_init(void)
static void gen_exception(DisasContext *dc, unsigned int excp) static void gen_exception(DisasContext *dc, unsigned int excp)
{ {
TCGv_i32 tmp = tcg_const_i32(excp); gen_helper_exception(cpu_env, tcg_constant_i32(excp));
gen_helper_exception(cpu_env, tmp);
tcg_temp_free_i32(tmp);
} }
static void gen_illegal_exception(DisasContext *dc) static void gen_illegal_exception(DisasContext *dc)
@ -199,10 +199,10 @@ static void gen_ove_cyov(DisasContext *dc)
static void gen_add(DisasContext *dc, TCGv dest, TCGv srca, TCGv srcb) static void gen_add(DisasContext *dc, TCGv dest, TCGv srca, TCGv srcb)
{ {
TCGv t0 = tcg_const_tl(0); TCGv t0 = tcg_temp_new();
TCGv res = tcg_temp_new(); TCGv res = tcg_temp_new();
tcg_gen_add2_tl(res, cpu_sr_cy, srca, t0, srcb, t0); tcg_gen_add2_tl(res, cpu_sr_cy, srca, dc->zero, srcb, dc->zero);
tcg_gen_xor_tl(cpu_sr_ov, srca, srcb); tcg_gen_xor_tl(cpu_sr_ov, srca, srcb);
tcg_gen_xor_tl(t0, res, srcb); tcg_gen_xor_tl(t0, res, srcb);
tcg_gen_andc_tl(cpu_sr_ov, t0, cpu_sr_ov); tcg_gen_andc_tl(cpu_sr_ov, t0, cpu_sr_ov);
@ -216,11 +216,11 @@ static void gen_add(DisasContext *dc, TCGv dest, TCGv srca, TCGv srcb)
static void gen_addc(DisasContext *dc, TCGv dest, TCGv srca, TCGv srcb) static void gen_addc(DisasContext *dc, TCGv dest, TCGv srca, TCGv srcb)
{ {
TCGv t0 = tcg_const_tl(0); TCGv t0 = tcg_temp_new();
TCGv res = tcg_temp_new(); TCGv res = tcg_temp_new();
tcg_gen_add2_tl(res, cpu_sr_cy, srca, t0, cpu_sr_cy, t0); tcg_gen_add2_tl(res, cpu_sr_cy, srca, dc->zero, cpu_sr_cy, dc->zero);
tcg_gen_add2_tl(res, cpu_sr_cy, res, cpu_sr_cy, srcb, t0); tcg_gen_add2_tl(res, cpu_sr_cy, res, cpu_sr_cy, srcb, dc->zero);
tcg_gen_xor_tl(cpu_sr_ov, srca, srcb); tcg_gen_xor_tl(cpu_sr_ov, srca, srcb);
tcg_gen_xor_tl(t0, res, srcb); tcg_gen_xor_tl(t0, res, srcb);
tcg_gen_andc_tl(cpu_sr_ov, t0, cpu_sr_ov); tcg_gen_andc_tl(cpu_sr_ov, t0, cpu_sr_ov);
@ -538,13 +538,9 @@ static bool trans_l_extbz(DisasContext *dc, arg_da *a)
static bool trans_l_cmov(DisasContext *dc, arg_dab *a) static bool trans_l_cmov(DisasContext *dc, arg_dab *a)
{ {
TCGv zero;
check_r0_write(dc, a->d); check_r0_write(dc, a->d);
zero = tcg_const_tl(0); tcg_gen_movcond_tl(TCG_COND_NE, cpu_R(dc, a->d), cpu_sr_f, dc->zero,
tcg_gen_movcond_tl(TCG_COND_NE, cpu_R(dc, a->d), cpu_sr_f, zero,
cpu_R(dc, a->a), cpu_R(dc, a->b)); cpu_R(dc, a->a), cpu_R(dc, a->b));
tcg_temp_free(zero);
return true; return true;
} }
@ -632,15 +628,10 @@ static bool trans_l_jal(DisasContext *dc, arg_l_jal *a)
static void do_bf(DisasContext *dc, arg_l_bf *a, TCGCond cond) static void do_bf(DisasContext *dc, arg_l_bf *a, TCGCond cond)
{ {
target_ulong tmp_pc = dc->base.pc_next + a->n * 4; target_ulong tmp_pc = dc->base.pc_next + a->n * 4;
TCGv t_next = tcg_const_tl(dc->base.pc_next + 8); TCGv t_next = tcg_constant_tl(dc->base.pc_next + 8);
TCGv t_true = tcg_const_tl(tmp_pc); TCGv t_true = tcg_constant_tl(tmp_pc);
TCGv t_zero = tcg_const_tl(0);
tcg_gen_movcond_tl(cond, jmp_pc, cpu_sr_f, t_zero, t_true, t_next); tcg_gen_movcond_tl(cond, jmp_pc, cpu_sr_f, dc->zero, t_true, t_next);
tcg_temp_free(t_next);
tcg_temp_free(t_true);
tcg_temp_free(t_zero);
dc->delayed_branch = 2; dc->delayed_branch = 2;
} }
@ -740,12 +731,6 @@ static bool trans_l_swa(DisasContext *dc, arg_store *a)
ea = tcg_temp_new(); ea = tcg_temp_new();
tcg_gen_addi_tl(ea, cpu_R(dc, a->a), a->i); tcg_gen_addi_tl(ea, cpu_R(dc, a->a), a->i);
/* For TB_FLAGS_R0_0, the branch below invalidates the temporary assigned
to cpu_regs[0]. Since l.swa is quite often immediately followed by a
branch, don't bother reallocating; finish the TB using the "real" R0.
This also takes care of RB input across the branch. */
dc->R0 = cpu_regs[0];
lab_fail = gen_new_label(); lab_fail = gen_new_label();
lab_done = gen_new_label(); lab_done = gen_new_label();
tcg_gen_brcond_tl(TCG_COND_NE, ea, cpu_lock_addr, lab_fail); tcg_gen_brcond_tl(TCG_COND_NE, ea, cpu_lock_addr, lab_fail);
@ -753,7 +738,7 @@ static bool trans_l_swa(DisasContext *dc, arg_store *a)
val = tcg_temp_new(); val = tcg_temp_new();
tcg_gen_atomic_cmpxchg_tl(val, cpu_lock_addr, cpu_lock_value, tcg_gen_atomic_cmpxchg_tl(val, cpu_lock_addr, cpu_lock_value,
cpu_regs[a->b], dc->mem_idx, MO_TEUL); cpu_R(dc, a->b), dc->mem_idx, MO_TEUL);
tcg_gen_setcond_tl(TCG_COND_EQ, cpu_sr_f, val, cpu_lock_value); tcg_gen_setcond_tl(TCG_COND_EQ, cpu_sr_f, val, cpu_lock_value);
tcg_temp_free(val); tcg_temp_free(val);
@ -813,44 +798,28 @@ static bool trans_l_adrp(DisasContext *dc, arg_l_adrp *a)
static bool trans_l_addi(DisasContext *dc, arg_rri *a) static bool trans_l_addi(DisasContext *dc, arg_rri *a)
{ {
TCGv t0;
check_r0_write(dc, a->d); check_r0_write(dc, a->d);
t0 = tcg_const_tl(a->i); gen_add(dc, cpu_R(dc, a->d), cpu_R(dc, a->a), tcg_constant_tl(a->i));
gen_add(dc, cpu_R(dc, a->d), cpu_R(dc, a->a), t0);
tcg_temp_free(t0);
return true; return true;
} }
static bool trans_l_addic(DisasContext *dc, arg_rri *a) static bool trans_l_addic(DisasContext *dc, arg_rri *a)
{ {
TCGv t0;
check_r0_write(dc, a->d); check_r0_write(dc, a->d);
t0 = tcg_const_tl(a->i); gen_addc(dc, cpu_R(dc, a->d), cpu_R(dc, a->a), tcg_constant_tl(a->i));
gen_addc(dc, cpu_R(dc, a->d), cpu_R(dc, a->a), t0);
tcg_temp_free(t0);
return true; return true;
} }
static bool trans_l_muli(DisasContext *dc, arg_rri *a) static bool trans_l_muli(DisasContext *dc, arg_rri *a)
{ {
TCGv t0;
check_r0_write(dc, a->d); check_r0_write(dc, a->d);
t0 = tcg_const_tl(a->i); gen_mul(dc, cpu_R(dc, a->d), cpu_R(dc, a->a), tcg_constant_tl(a->i));
gen_mul(dc, cpu_R(dc, a->d), cpu_R(dc, a->a), t0);
tcg_temp_free(t0);
return true; return true;
} }
static bool trans_l_maci(DisasContext *dc, arg_l_maci *a) static bool trans_l_maci(DisasContext *dc, arg_l_maci *a)
{ {
TCGv t0; gen_mac(dc, cpu_R(dc, a->a), tcg_constant_tl(a->i));
t0 = tcg_const_tl(a->i);
gen_mac(dc, cpu_R(dc, a->a), t0);
tcg_temp_free(t0);
return true; return true;
} }
@ -1624,8 +1593,9 @@ static void openrisc_tr_tb_start(DisasContextBase *db, CPUState *cs)
/* Allow the TCG optimizer to see that R0 == 0, /* Allow the TCG optimizer to see that R0 == 0,
when it's true, which is the common case. */ when it's true, which is the common case. */
dc->zero = tcg_constant_tl(0);
if (dc->tb_flags & TB_FLAGS_R0_0) { if (dc->tb_flags & TB_FLAGS_R0_0) {
dc->R0 = tcg_const_tl(0); dc->R0 = dc->zero;
} else { } else {
dc->R0 = cpu_regs[0]; dc->R0 = cpu_regs[0];
} }