aboutsummaryrefslogtreecommitdiffstats
path: root/arch
diff options
context:
space:
mode:
authorAvi Kivity <avi@redhat.com>2012-01-16 08:08:45 -0500
committerAvi Kivity <avi@redhat.com>2012-03-05 07:52:42 -0500
commit2adb5ad9fe1b44d0ae8b00d2bd6568e6163215b3 (patch)
tree810f4ee0e638b1774efae25cfcc5a7090e47fed7 /arch
parent28867cee754c07b3fa0a679ed2ea394843130217 (diff)
KVM: x86 emulator: Remove byte-sized MOVSX/MOVZX hack
Currently we treat MOVSX/MOVZX with a byte source as a byte instruction, and change the destination operand size with a hack. Change it to be a word instruction, so the destination receives its natural size, and change the source to be SrcMem8. Signed-off-by: Avi Kivity <avi@redhat.com> Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com>
Diffstat (limited to 'arch')
-rw-r--r--arch/x86/kvm/emulate.c13
1 files changed, 5 insertions, 8 deletions
diff --git a/arch/x86/kvm/emulate.c b/arch/x86/kvm/emulate.c
index 5da6b3619201..6eaedac7cf6a 100644
--- a/arch/x86/kvm/emulate.c
+++ b/arch/x86/kvm/emulate.c
@@ -860,8 +860,7 @@ static void write_sse_reg(struct x86_emulate_ctxt *ctxt, sse128_t *data,
860} 860}
861 861
862static void decode_register_operand(struct x86_emulate_ctxt *ctxt, 862static void decode_register_operand(struct x86_emulate_ctxt *ctxt,
863 struct operand *op, 863 struct operand *op)
864 int inhibit_bytereg)
865{ 864{
866 unsigned reg = ctxt->modrm_reg; 865 unsigned reg = ctxt->modrm_reg;
867 int highbyte_regs = ctxt->rex_prefix == 0; 866 int highbyte_regs = ctxt->rex_prefix == 0;
@@ -878,7 +877,7 @@ static void decode_register_operand(struct x86_emulate_ctxt *ctxt,
878 } 877 }
879 878
880 op->type = OP_REG; 879 op->type = OP_REG;
881 if ((ctxt->d & ByteOp) && !inhibit_bytereg) { 880 if (ctxt->d & ByteOp) {
882 op->addr.reg = decode_register(reg, ctxt->regs, highbyte_regs); 881 op->addr.reg = decode_register(reg, ctxt->regs, highbyte_regs);
883 op->bytes = 1; 882 op->bytes = 1;
884 } else { 883 } else {
@@ -3516,13 +3515,13 @@ static struct opcode twobyte_table[256] = {
3516 I(DstMem | SrcReg | ModRM | BitOp | Lock, em_btr), 3515 I(DstMem | SrcReg | ModRM | BitOp | Lock, em_btr),
3517 I(DstReg | SrcMemFAddr | ModRM | Src2FS, em_lseg), 3516 I(DstReg | SrcMemFAddr | ModRM | Src2FS, em_lseg),
3518 I(DstReg | SrcMemFAddr | ModRM | Src2GS, em_lseg), 3517 I(DstReg | SrcMemFAddr | ModRM | Src2GS, em_lseg),
3519 D(ByteOp | DstReg | SrcMem | ModRM | Mov), D(DstReg | SrcMem16 | ModRM | Mov), 3518 D(DstReg | SrcMem8 | ModRM | Mov), D(DstReg | SrcMem16 | ModRM | Mov),
3520 /* 0xB8 - 0xBF */ 3519 /* 0xB8 - 0xBF */
3521 N, N, 3520 N, N,
3522 G(BitOp, group8), 3521 G(BitOp, group8),
3523 I(DstMem | SrcReg | ModRM | BitOp | Lock | PageTable, em_btc), 3522 I(DstMem | SrcReg | ModRM | BitOp | Lock | PageTable, em_btc),
3524 I(DstReg | SrcMem | ModRM, em_bsf), I(DstReg | SrcMem | ModRM, em_bsr), 3523 I(DstReg | SrcMem | ModRM, em_bsf), I(DstReg | SrcMem | ModRM, em_bsr),
3525 D(ByteOp | DstReg | SrcMem | ModRM | Mov), D(DstReg | SrcMem16 | ModRM | Mov), 3524 D(DstReg | SrcMem8 | ModRM | Mov), D(DstReg | SrcMem16 | ModRM | Mov),
3526 /* 0xC0 - 0xCF */ 3525 /* 0xC0 - 0xCF */
3527 D2bv(DstMem | SrcReg | ModRM | Lock), 3526 D2bv(DstMem | SrcReg | ModRM | Lock),
3528 N, D(DstMem | SrcReg | ModRM | Mov), 3527 N, D(DstMem | SrcReg | ModRM | Mov),
@@ -3604,9 +3603,7 @@ static int decode_operand(struct x86_emulate_ctxt *ctxt, struct operand *op,
3604 3603
3605 switch (d) { 3604 switch (d) {
3606 case OpReg: 3605 case OpReg:
3607 decode_register_operand(ctxt, op, 3606 decode_register_operand(ctxt, op);
3608 op == &ctxt->dst &&
3609 ctxt->twobyte && (ctxt->b == 0xb6 || ctxt->b == 0xb7));
3610 break; 3607 break;
3611 case OpImmUByte: 3608 case OpImmUByte:
3612 rc = decode_imm(ctxt, op, 1, false); 3609 rc = decode_imm(ctxt, op, 1, false);