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>
---
target/i386/tcg/translate.c | 2 +-
target/i386/tcg/emit.c.inc | 23 ++++++++++++-----------
2 files changed, 13 insertions(+), 12 deletions(-)
diff --git a/target/i386/tcg/translate.c b/target/i386/tcg/translate.c
index 834aea1e594..dbc9d637c4b 100644
--- a/target/i386/tcg/translate.c
+++ b/target/i386/tcg/translate.c
@@ -486,7 +486,7 @@ static inline
void gen_op_mov_v_reg(DisasContext *s, MemOp ot, TCGv t0, int 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 {
tcg_gen_mov_tl(t0, cpu_regs[reg]);
}
diff --git a/target/i386/tcg/emit.c.inc b/target/i386/tcg/emit.c.inc
index 5c115429350..c4cc5f48d83 100644
--- a/target/i386/tcg/emit.c.inc
+++ b/target/i386/tcg/emit.c.inc
@@ -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);
}
- } 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 &&
(decode->e.special == X86_SPECIAL_SExtT0 ||
decode->e.special == X86_SPECIAL_ZExtT0)) {
- if (decode->e.special == X86_SPECIAL_SExtT0) {
- tcg_gen_ext_tl(v, cpu_regs[op->n], op->ot | MO_SIGN);
+ if (op->ot == MO_8 && byte_reg_is_xH(s, op->n)) {
+ 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 {
- 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 {
- tcg_gen_mov_tl(v, cpu_regs[op->n]);
+ gen_op_mov_v_reg(s, op->ot, v, op->n);
}
break;
case X86_OP_IMM:
--
2.47.1