|
47 | 47 | #define DstDI (5<<1) /* Destination is in ES:(E)DI */
|
48 | 48 | #define DstMem64 (6<<1) /* 64bit memory operand */
|
49 | 49 | #define DstImmUByte (7<<1) /* 8-bit unsigned immediate operand */
|
50 |
| -#define DstMask (7<<1) |
| 50 | +#define DstDX (8<<1) /* Destination is in DX register */ |
| 51 | +#define DstMask (0xf<<1) |
51 | 52 | /* Source operand type. */
|
52 |
| -#define SrcNone (0<<4) /* No source operand. */ |
53 |
| -#define SrcReg (1<<4) /* Register operand. */ |
54 |
| -#define SrcMem (2<<4) /* Memory operand. */ |
55 |
| -#define SrcMem16 (3<<4) /* Memory operand (16-bit). */ |
56 |
| -#define SrcMem32 (4<<4) /* Memory operand (32-bit). */ |
57 |
| -#define SrcImm (5<<4) /* Immediate operand. */ |
58 |
| -#define SrcImmByte (6<<4) /* 8-bit sign-extended immediate operand. */ |
59 |
| -#define SrcOne (7<<4) /* Implied '1' */ |
60 |
| -#define SrcImmUByte (8<<4) /* 8-bit unsigned immediate operand. */ |
61 |
| -#define SrcImmU (9<<4) /* Immediate operand, unsigned */ |
62 |
| -#define SrcSI (0xa<<4) /* Source is in the DS:RSI */ |
63 |
| -#define SrcImmFAddr (0xb<<4) /* Source is immediate far address */ |
64 |
| -#define SrcMemFAddr (0xc<<4) /* Source is far address in memory */ |
65 |
| -#define SrcAcc (0xd<<4) /* Source Accumulator */ |
66 |
| -#define SrcImmU16 (0xe<<4) /* Immediate operand, unsigned, 16 bits */ |
67 |
| -#define SrcMask (0xf<<4) |
| 53 | +#define SrcNone (0<<5) /* No source operand. */ |
| 54 | +#define SrcReg (1<<5) /* Register operand. */ |
| 55 | +#define SrcMem (2<<5) /* Memory operand. */ |
| 56 | +#define SrcMem16 (3<<5) /* Memory operand (16-bit). */ |
| 57 | +#define SrcMem32 (4<<5) /* Memory operand (32-bit). */ |
| 58 | +#define SrcImm (5<<5) /* Immediate operand. */ |
| 59 | +#define SrcImmByte (6<<5) /* 8-bit sign-extended immediate operand. */ |
| 60 | +#define SrcOne (7<<5) /* Implied '1' */ |
| 61 | +#define SrcImmUByte (8<<5) /* 8-bit unsigned immediate operand. */ |
| 62 | +#define SrcImmU (9<<5) /* Immediate operand, unsigned */ |
| 63 | +#define SrcSI (0xa<<5) /* Source is in the DS:RSI */ |
| 64 | +#define SrcImmFAddr (0xb<<5) /* Source is immediate far address */ |
| 65 | +#define SrcMemFAddr (0xc<<5) /* Source is far address in memory */ |
| 66 | +#define SrcAcc (0xd<<5) /* Source Accumulator */ |
| 67 | +#define SrcImmU16 (0xe<<5) /* Immediate operand, unsigned, 16 bits */ |
| 68 | +#define SrcDX (0xf<<5) /* Source is in DX register */ |
| 69 | +#define SrcMask (0xf<<5) |
68 | 70 | /* Generic ModRM decode. */
|
69 |
| -#define ModRM (1<<8) |
| 71 | +#define ModRM (1<<9) |
70 | 72 | /* Destination is only written; never read. */
|
71 |
| -#define Mov (1<<9) |
72 |
| -#define BitOp (1<<10) |
73 |
| -#define MemAbs (1<<11) /* Memory operand is absolute displacement */ |
74 |
| -#define String (1<<12) /* String instruction (rep capable) */ |
75 |
| -#define Stack (1<<13) /* Stack instruction (push/pop) */ |
76 |
| -#define GroupMask (7<<14) /* Opcode uses one of the group mechanisms */ |
77 |
| -#define Group (1<<14) /* Bits 3:5 of modrm byte extend opcode */ |
78 |
| -#define GroupDual (2<<14) /* Alternate decoding of mod == 3 */ |
79 |
| -#define Prefix (3<<14) /* Instruction varies with 66/f2/f3 prefix */ |
80 |
| -#define RMExt (4<<14) /* Opcode extension in ModRM r/m if mod == 3 */ |
81 |
| -#define Sse (1<<17) /* SSE Vector instruction */ |
| 73 | +#define Mov (1<<10) |
| 74 | +#define BitOp (1<<11) |
| 75 | +#define MemAbs (1<<12) /* Memory operand is absolute displacement */ |
| 76 | +#define String (1<<13) /* String instruction (rep capable) */ |
| 77 | +#define Stack (1<<14) /* Stack instruction (push/pop) */ |
| 78 | +#define GroupMask (7<<15) /* Opcode uses one of the group mechanisms */ |
| 79 | +#define Group (1<<15) /* Bits 3:5 of modrm byte extend opcode */ |
| 80 | +#define GroupDual (2<<15) /* Alternate decoding of mod == 3 */ |
| 81 | +#define Prefix (3<<15) /* Instruction varies with 66/f2/f3 prefix */ |
| 82 | +#define RMExt (4<<15) /* Opcode extension in ModRM r/m if mod == 3 */ |
| 83 | +#define Sse (1<<18) /* SSE Vector instruction */ |
82 | 84 | /* Misc flags */
|
83 | 85 | #define Prot (1<<21) /* instruction generates #UD if not in prot-mode */
|
84 | 86 | #define VendorSpecific (1<<22) /* Vendor specific instruction */
|
@@ -3154,8 +3156,8 @@ static struct opcode opcode_table[256] = {
|
3154 | 3156 | I(DstReg | SrcMem | ModRM | Src2Imm, em_imul_3op),
|
3155 | 3157 | I(SrcImmByte | Mov | Stack, em_push),
|
3156 | 3158 | I(DstReg | SrcMem | ModRM | Src2ImmByte, em_imul_3op),
|
3157 |
| - D2bvIP(DstDI | Mov | String, ins, check_perm_in), /* insb, insw/insd */ |
3158 |
| - D2bvIP(SrcSI | ImplicitOps | String, outs, check_perm_out), /* outsb, outsw/outsd */ |
| 3159 | + D2bvIP(DstDI | SrcDX | Mov | String, ins, check_perm_in), /* insb, insw/insd */ |
| 3160 | + D2bvIP(SrcSI | DstDX | String, outs, check_perm_out), /* outsb, outsw/outsd */ |
3159 | 3161 | /* 0x70 - 0x7F */
|
3160 | 3162 | X16(D(SrcImmByte)),
|
3161 | 3163 | /* 0x80 - 0x87 */
|
@@ -3212,8 +3214,8 @@ static struct opcode opcode_table[256] = {
|
3212 | 3214 | /* 0xE8 - 0xEF */
|
3213 | 3215 | D(SrcImm | Stack), D(SrcImm | ImplicitOps),
|
3214 | 3216 | D(SrcImmFAddr | No64), D(SrcImmByte | ImplicitOps),
|
3215 |
| - D2bvIP(SrcNone | DstAcc, in, check_perm_in), |
3216 |
| - D2bvIP(SrcAcc | ImplicitOps, out, check_perm_out), |
| 3217 | + D2bvIP(SrcDX | DstAcc, in, check_perm_in), |
| 3218 | + D2bvIP(SrcAcc | DstDX, out, check_perm_out), |
3217 | 3219 | /* 0xF0 - 0xF7 */
|
3218 | 3220 | N, DI(ImplicitOps, icebp), N, N,
|
3219 | 3221 | DI(ImplicitOps | Priv, hlt), D(ImplicitOps),
|
@@ -3613,6 +3615,12 @@ x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len)
|
3613 | 3615 | memop.bytes = c->op_bytes + 2;
|
3614 | 3616 | goto srcmem_common;
|
3615 | 3617 | break;
|
| 3618 | + case SrcDX: |
| 3619 | + c->src.type = OP_REG; |
| 3620 | + c->src.bytes = 2; |
| 3621 | + c->src.addr.reg = &c->regs[VCPU_REGS_RDX]; |
| 3622 | + fetch_register_operand(&c->src); |
| 3623 | + break; |
3616 | 3624 | }
|
3617 | 3625 |
|
3618 | 3626 | if (rc != X86EMUL_CONTINUE)
|
@@ -3682,6 +3690,12 @@ x86_decode_insn(struct x86_emulate_ctxt *ctxt, void *insn, int insn_len)
|
3682 | 3690 | c->dst.addr.mem.seg = VCPU_SREG_ES;
|
3683 | 3691 | c->dst.val = 0;
|
3684 | 3692 | break;
|
| 3693 | + case DstDX: |
| 3694 | + c->dst.type = OP_REG; |
| 3695 | + c->dst.bytes = 2; |
| 3696 | + c->dst.addr.reg = &c->regs[VCPU_REGS_RDX]; |
| 3697 | + fetch_register_operand(&c->dst); |
| 3698 | + break; |
3685 | 3699 | case ImplicitOps:
|
3686 | 3700 | /* Special instructions do their own operand decoding. */
|
3687 | 3701 | default:
|
@@ -4027,15 +4041,13 @@ x86_emulate_insn(struct x86_emulate_ctxt *ctxt)
|
4027 | 4041 | break;
|
4028 | 4042 | case 0xec: /* in al,dx */
|
4029 | 4043 | case 0xed: /* in (e/r)ax,dx */
|
4030 |
| - c->src.val = c->regs[VCPU_REGS_RDX]; |
4031 | 4044 | do_io_in:
|
4032 | 4045 | if (!pio_in_emulated(ctxt, ops, c->dst.bytes, c->src.val,
|
4033 | 4046 | &c->dst.val))
|
4034 | 4047 | goto done; /* IO is needed */
|
4035 | 4048 | break;
|
4036 | 4049 | case 0xee: /* out dx,al */
|
4037 | 4050 | case 0xef: /* out dx,(e/r)ax */
|
4038 |
| - c->dst.val = c->regs[VCPU_REGS_RDX]; |
4039 | 4051 | do_io_out:
|
4040 | 4052 | ops->pio_out_emulated(ctxt, c->src.bytes, c->dst.val,
|
4041 | 4053 | &c->src.val, 1);
|
|
0 commit comments