target/i386: use shr to load high-byte registers into T0/T1

Using a sextract or extract operation is only necessary if a
sign or zero extended value is needed.  If not, a shift is
enough.

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
This commit is contained in:
Paolo Bonzini 2024-11-21 13:01:45 +01:00
parent 88716ae79f
commit ef682b08a0
2 changed files with 13 additions and 12 deletions

View File

@ -286,24 +286,25 @@ static void gen_load(DisasContext *s, X86DecodedInsn *decode, int opn, TCGv v)
gen_op_ld_v(s, op->ot, v, s->A0); gen_op_ld_v(s, op->ot, v, s->A0);
} }
} else if (op->ot == MO_8 && byte_reg_is_xH(s, op->n)) {
if (v == s->T0 && decode->e.special == X86_SPECIAL_SExtT0) {
tcg_gen_sextract_tl(v, cpu_regs[op->n - 4], 8, 8);
} else {
tcg_gen_extract_tl(v, cpu_regs[op->n - 4], 8, 8);
}
} else if (op->ot < MO_TL && v == s->T0 && } else if (op->ot < MO_TL && v == s->T0 &&
(decode->e.special == X86_SPECIAL_SExtT0 || (decode->e.special == X86_SPECIAL_SExtT0 ||
decode->e.special == X86_SPECIAL_ZExtT0)) { decode->e.special == X86_SPECIAL_ZExtT0)) {
if (decode->e.special == X86_SPECIAL_SExtT0) { if (op->ot == MO_8 && byte_reg_is_xH(s, op->n)) {
tcg_gen_ext_tl(v, cpu_regs[op->n], op->ot | MO_SIGN); if (decode->e.special == X86_SPECIAL_SExtT0) {
tcg_gen_sextract_tl(v, cpu_regs[op->n - 4], 8, 8);
} else {
tcg_gen_extract_tl(v, cpu_regs[op->n - 4], 8, 8);
}
} else { } else {
tcg_gen_ext_tl(v, cpu_regs[op->n], op->ot); if (decode->e.special == X86_SPECIAL_SExtT0) {
tcg_gen_ext_tl(v, cpu_regs[op->n], op->ot | MO_SIGN);
} else {
tcg_gen_ext_tl(v, cpu_regs[op->n], op->ot);
}
} }
} else { } else {
tcg_gen_mov_tl(v, cpu_regs[op->n]); gen_op_mov_v_reg(s, op->ot, v, op->n);
} }
break; break;
case X86_OP_IMM: case X86_OP_IMM:

View File

@ -486,7 +486,7 @@ static inline
void gen_op_mov_v_reg(DisasContext *s, MemOp ot, TCGv t0, int reg) void gen_op_mov_v_reg(DisasContext *s, MemOp ot, TCGv t0, int reg)
{ {
if (ot == MO_8 && byte_reg_is_xH(s, reg)) { if (ot == MO_8 && byte_reg_is_xH(s, reg)) {
tcg_gen_extract_tl(t0, cpu_regs[reg - 4], 8, 8); tcg_gen_shri_tl(t0, cpu_regs[reg - 4], 8);
} else { } else {
tcg_gen_mov_tl(t0, cpu_regs[reg]); tcg_gen_mov_tl(t0, cpu_regs[reg]);
} }