Commit f09ed83e authored by Avi Kivity's avatar Avi Kivity

KVM: x86 emulator: move memop, memopp into emulation context

Simplifies further generalization of decode.
Signed-off-by: default avatarAvi Kivity <avi@redhat.com>
Signed-off-by: default avatarMarcelo Tosatti <mtosatti@redhat.com>
parent 3329ece1
...@@ -275,6 +275,8 @@ struct x86_emulate_ctxt { ...@@ -275,6 +275,8 @@ struct x86_emulate_ctxt {
unsigned long _eip; unsigned long _eip;
/* Fields above regs are cleared together. */ /* Fields above regs are cleared together. */
unsigned long regs[NR_VCPU_REGS]; unsigned long regs[NR_VCPU_REGS];
struct operand memop;
struct operand *memopp;
struct fetch_cache fetch; struct fetch_cache fetch;
struct read_cache io_read; struct read_cache io_read;
struct read_cache mem_read; struct read_cache mem_read;
......
...@@ -3323,8 +3323,9 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len) ...@@ -3323,8 +3323,9 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len)
int def_op_bytes, def_ad_bytes, goffset, simd_prefix; int def_op_bytes, def_ad_bytes, goffset, simd_prefix;
bool op_prefix = false; bool op_prefix = false;
struct opcode opcode; struct opcode opcode;
struct operand memop = { .type = OP_NONE }, *memopp = NULL;
ctxt->memop.type = OP_NONE;
ctxt->memopp = NULL;
ctxt->_eip = ctxt->eip; ctxt->_eip = ctxt->eip;
ctxt->fetch.start = ctxt->_eip; ctxt->fetch.start = ctxt->_eip;
ctxt->fetch.end = ctxt->fetch.start + insn_len; ctxt->fetch.end = ctxt->fetch.start + insn_len;
...@@ -3482,21 +3483,21 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len) ...@@ -3482,21 +3483,21 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len)
/* ModRM and SIB bytes. */ /* ModRM and SIB bytes. */
if (ctxt->d & ModRM) { if (ctxt->d & ModRM) {
rc = decode_modrm(ctxt, &memop); rc = decode_modrm(ctxt, &ctxt->memop);
if (!ctxt->has_seg_override) if (!ctxt->has_seg_override)
set_seg_override(ctxt, ctxt->modrm_seg); set_seg_override(ctxt, ctxt->modrm_seg);
} else if (ctxt->d & MemAbs) } else if (ctxt->d & MemAbs)
rc = decode_abs(ctxt, &memop); rc = decode_abs(ctxt, &ctxt->memop);
if (rc != X86EMUL_CONTINUE) if (rc != X86EMUL_CONTINUE)
goto done; goto done;
if (!ctxt->has_seg_override) if (!ctxt->has_seg_override)
set_seg_override(ctxt, VCPU_SREG_DS); set_seg_override(ctxt, VCPU_SREG_DS);
memop.addr.mem.seg = seg_override(ctxt); ctxt->memop.addr.mem.seg = seg_override(ctxt);
if (memop.type == OP_MEM && ctxt->ad_bytes != 8) if (ctxt->memop.type == OP_MEM && ctxt->ad_bytes != 8)
memop.addr.mem.ea = (u32)memop.addr.mem.ea; ctxt->memop.addr.mem.ea = (u32)ctxt->memop.addr.mem.ea;
/* /*
* Decode and fetch the source operand: register, memory * Decode and fetch the source operand: register, memory
...@@ -3509,17 +3510,16 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len) ...@@ -3509,17 +3510,16 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len)
decode_register_operand(ctxt, &ctxt->src, 0); decode_register_operand(ctxt, &ctxt->src, 0);
break; break;
case SrcMem16: case SrcMem16:
memop.bytes = 2; ctxt->memop.bytes = 2;
goto srcmem_common; goto srcmem_common;
case SrcMem32: case SrcMem32:
memop.bytes = 4; ctxt->memop.bytes = 4;
goto srcmem_common; goto srcmem_common;
case SrcMem: case SrcMem:
memop.bytes = (ctxt->d & ByteOp) ? 1 : ctxt->memop.bytes = (ctxt->d & ByteOp) ? 1 : ctxt->op_bytes;
ctxt->op_bytes;
srcmem_common: srcmem_common:
ctxt->src = memop; ctxt->src = ctxt->memop;
memopp = &ctxt->src; ctxt->memopp = &ctxt->src;
break; break;
case SrcImmU16: case SrcImmU16:
rc = decode_imm(ctxt, &ctxt->src, 2, false); rc = decode_imm(ctxt, &ctxt->src, 2, false);
...@@ -3561,7 +3561,7 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len) ...@@ -3561,7 +3561,7 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len)
insn_fetch_arr(ctxt->src.valptr, ctxt->src.bytes, ctxt); insn_fetch_arr(ctxt->src.valptr, ctxt->src.bytes, ctxt);
break; break;
case SrcMemFAddr: case SrcMemFAddr:
memop.bytes = ctxt->op_bytes + 2; ctxt->memop.bytes = ctxt->op_bytes + 2;
goto srcmem_common; goto srcmem_common;
break; break;
case SrcDX: case SrcDX:
...@@ -3615,8 +3615,8 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len) ...@@ -3615,8 +3615,8 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len)
break; break;
case DstMem: case DstMem:
case DstMem64: case DstMem64:
ctxt->dst = memop; ctxt->dst = ctxt->memop;
memopp = &ctxt->dst; ctxt->memopp = &ctxt->dst;
if ((ctxt->d & DstMask) == DstMem64) if ((ctxt->d & DstMask) == DstMem64)
ctxt->dst.bytes = 8; ctxt->dst.bytes = 8;
else else
...@@ -3654,8 +3654,8 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len) ...@@ -3654,8 +3654,8 @@ int x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len)
} }
done: done:
if (memopp && memopp->type == OP_MEM && ctxt->rip_relative) if (ctxt->memopp && ctxt->memopp->type == OP_MEM && ctxt->rip_relative)
memopp->addr.mem.ea += ctxt->_eip; ctxt->memopp->addr.mem.ea += ctxt->_eip;
return (rc != X86EMUL_CONTINUE) ? EMULATION_FAILED : EMULATION_OK; return (rc != X86EMUL_CONTINUE) ? EMULATION_FAILED : EMULATION_OK;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment