ia64/xen-unstable

changeset 17354:d434c73ec8b7

x86_emulate: Remove environment-specific definitions from core
emulator source files.
Signed-off-by: Keir Fraser <keir.fraser@citrix.com>
author Keir Fraser <keir.fraser@citrix.com>
date Mon Mar 31 14:21:13 2008 +0100 (2008-03-31)
parents d24f37b31030
children ffcc213f8711
files .hgignore tools/tests/Makefile tools/tests/test_x86_emulator.c tools/tests/x86_emulate.c xen/arch/x86/x86_emulate.c xen/arch/x86/x86_emulate/x86_emulate.c xen/arch/x86/x86_emulate/x86_emulate.h xen/include/asm-x86/x86_emulate.h
line diff
     1.1 --- a/.hgignore	Mon Mar 31 10:40:43 2008 +0100
     1.2 +++ b/.hgignore	Mon Mar 31 14:21:13 2008 +0100
     1.3 @@ -179,6 +179,7 @@
     1.4  ^tools/tests/blowfish\.bin$
     1.5  ^tools/tests/blowfish\.h$
     1.6  ^tools/tests/test_x86_emulator$
     1.7 +^tools/tests/x86_emulate$
     1.8  ^tools/vnet/Make.local$
     1.9  ^tools/vnet/build/.*$
    1.10  ^tools/vnet/gc$
     2.1 --- a/tools/tests/Makefile	Mon Mar 31 10:40:43 2008 +0100
     2.2 +++ b/tools/tests/Makefile	Mon Mar 31 14:21:13 2008 +0100
     2.3 @@ -21,13 +21,17 @@ blowfish.h: blowfish.bin
     2.4  
     2.5  .PHONY: clean
     2.6  clean:
     2.7 -	rm -rf $(TARGET) *.o *~ core blowfish.h blowfish.bin
     2.8 +	rm -rf $(TARGET) *.o *~ core blowfish.h blowfish.bin x86_emulate
     2.9  
    2.10  .PHONY: install
    2.11  install:
    2.12  
    2.13 -x86_emulate.o: $(XEN_ROOT)/xen/arch/x86/x86_emulate.c
    2.14 +.PHONY: x86_emulate
    2.15 +x86_emulate:
    2.16 +	[ -L x86_emulate ] || ln -sf $(XEN_ROOT)/xen/arch/x86/x86_emulate .
    2.17 +
    2.18 +x86_emulate.o: x86_emulate.c x86_emulate
    2.19  	$(HOSTCC) $(HOSTCFLAGS) -I$(XEN_ROOT)/xen/include -c -o $@ $<
    2.20  
    2.21 -test_x86_emulator.o: test_x86_emulator.c blowfish.h
    2.22 +test_x86_emulator.o: test_x86_emulator.c blowfish.h x86_emulate
    2.23  	$(HOSTCC) $(HOSTCFLAGS) -I$(XEN_ROOT)/xen/include -c -o $@ $<
     3.1 --- a/tools/tests/test_x86_emulator.c	Mon Mar 31 10:40:43 2008 +0100
     3.2 +++ b/tools/tests/test_x86_emulator.c	Mon Mar 31 14:21:13 2008 +0100
     3.3 @@ -1,20 +1,11 @@
     3.4 -
     3.5  #include <stdio.h>
     3.6  #include <stdlib.h>
     3.7  #include <string.h>
     3.8  #include <stdint.h>
     3.9 -typedef uint8_t            u8;
    3.10 -typedef uint16_t           u16;
    3.11 -typedef uint32_t           u32;
    3.12 -typedef uint64_t           u64;
    3.13 -typedef int8_t             s8;
    3.14 -typedef int16_t            s16;
    3.15 -typedef int32_t            s32;
    3.16 -typedef int64_t            s64;
    3.17  #include <public/xen.h>
    3.18 -#include <asm-x86/x86_emulate.h>
    3.19  #include <sys/mman.h>
    3.20  
    3.21 +#include "x86_emulate/x86_emulate.h"
    3.22  #include "blowfish.h"
    3.23  
    3.24  #define MMAP_SZ 16384
    3.25 @@ -38,9 +29,9 @@ static int read(
    3.26      unsigned long addr = offset;
    3.27      switch ( bytes )
    3.28      {
    3.29 -    case 1: *val = *(u8 *)addr; break;
    3.30 -    case 2: *val = *(u16 *)addr; break;
    3.31 -    case 4: *val = *(u32 *)addr; break;
    3.32 +    case 1: *val = *(uint8_t *)addr; break;
    3.33 +    case 2: *val = *(uint16_t *)addr; break;
    3.34 +    case 4: *val = *(uint32_t *)addr; break;
    3.35      case 8: *val = *(unsigned long *)addr; break;
    3.36      }
    3.37      return X86EMUL_OKAY;
    3.38 @@ -56,9 +47,9 @@ static int write(
    3.39      unsigned long addr = offset;
    3.40      switch ( bytes )
    3.41      {
    3.42 -    case 1: *(u8 *)addr = (u8)val; break;
    3.43 -    case 2: *(u16 *)addr = (u16)val; break;
    3.44 -    case 4: *(u32 *)addr = (u32)val; break;
    3.45 +    case 1: *(uint8_t *)addr = (uint8_t)val; break;
    3.46 +    case 2: *(uint16_t *)addr = (uint16_t)val; break;
    3.47 +    case 4: *(uint32_t *)addr = (uint32_t)val; break;
    3.48      case 8: *(unsigned long *)addr = val; break;
    3.49      }
    3.50      return X86EMUL_OKAY;
    3.51 @@ -75,9 +66,9 @@ static int cmpxchg(
    3.52      unsigned long addr = offset;
    3.53      switch ( bytes )
    3.54      {
    3.55 -    case 1: *(u8 *)addr = (u8)new; break;
    3.56 -    case 2: *(u16 *)addr = (u16)new; break;
    3.57 -    case 4: *(u32 *)addr = (u32)new; break;
    3.58 +    case 1: *(uint8_t *)addr = (uint8_t)new; break;
    3.59 +    case 2: *(uint16_t *)addr = (uint16_t)new; break;
    3.60 +    case 4: *(uint32_t *)addr = (uint32_t)new; break;
    3.61      case 8: *(unsigned long *)addr = new; break;
    3.62      }
    3.63      return X86EMUL_OKAY;
     4.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     4.2 +++ b/tools/tests/x86_emulate.c	Mon Mar 31 14:21:13 2008 +0100
     4.3 @@ -0,0 +1,13 @@
     4.4 +#include <stddef.h>
     4.5 +#include <stdint.h>
     4.6 +#include <string.h>
     4.7 +#include <public/xen.h>
     4.8 +
     4.9 +#include "x86_emulate/x86_emulate.h"
    4.10 +
    4.11 +#define __emulate_fpu_insn(_op)                 \
    4.12 +do{ rc = X86EMUL_UNHANDLEABLE;                  \
    4.13 +    goto done;                                  \
    4.14 +} while (0)
    4.15 +
    4.16 +#include "x86_emulate/x86_emulate.c"
     5.1 --- a/xen/arch/x86/x86_emulate.c	Mon Mar 31 10:40:43 2008 +0100
     5.2 +++ b/xen/arch/x86/x86_emulate.c	Mon Mar 31 14:21:13 2008 +0100
     5.3 @@ -1,484 +1,18 @@
     5.4  /******************************************************************************
     5.5   * x86_emulate.c
     5.6   * 
     5.7 - * Generic x86 (32-bit and 64-bit) instruction decoder and emulator.
     5.8 - * 
     5.9 - * Copyright (c) 2005-2007 Keir Fraser
    5.10 - * Copyright (c) 2005-2007 XenSource Inc.
    5.11 + * Wrapper for generic x86 instruction decoder and emulator.
    5.12   * 
    5.13 - * This program is free software; you can redistribute it and/or modify
    5.14 - * it under the terms of the GNU General Public License as published by
    5.15 - * the Free Software Foundation; either version 2 of the License, or
    5.16 - * (at your option) any later version.
    5.17 + * Copyright (c) 2008, Citrix Systems, Inc.
    5.18   * 
    5.19 - * This program is distributed in the hope that it will be useful,
    5.20 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
    5.21 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    5.22 - * GNU General Public License for more details.
    5.23 - * 
    5.24 - * You should have received a copy of the GNU General Public License
    5.25 - * along with this program; if not, write to the Free Software
    5.26 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
    5.27 + * Authors:
    5.28 + *    Keir Fraser <keir.fraser@citrix.com>
    5.29   */
    5.30  
    5.31 -#ifndef __XEN__
    5.32 -#include <stddef.h>
    5.33 -#include <stdint.h>
    5.34 -#include <string.h>
    5.35 -#include <public/xen.h>
    5.36 -#else
    5.37 -#include <xen/config.h>
    5.38 -#include <xen/types.h>
    5.39 -#include <xen/lib.h>
    5.40 -#include <asm/regs.h>
    5.41 -#undef cmpxchg
    5.42 -#endif
    5.43 -#include <asm-x86/x86_emulate.h>
    5.44 -
    5.45 -/* Operand sizes: 8-bit operands or specified/overridden size. */
    5.46 -#define ByteOp      (1<<0) /* 8-bit operands. */
    5.47 -/* Destination operand type. */
    5.48 -#define DstBitBase  (0<<1) /* Memory operand, bit string. */
    5.49 -#define ImplicitOps (1<<1) /* Implicit in opcode. No generic decode. */
    5.50 -#define DstReg      (2<<1) /* Register operand. */
    5.51 -#define DstMem      (3<<1) /* Memory operand. */
    5.52 -#define DstMask     (3<<1)
    5.53 -/* Source operand type. */
    5.54 -#define SrcNone     (0<<3) /* No source operand. */
    5.55 -#define SrcImplicit (0<<3) /* Source operand is implicit in the opcode. */
    5.56 -#define SrcReg      (1<<3) /* Register operand. */
    5.57 -#define SrcMem      (2<<3) /* Memory operand. */
    5.58 -#define SrcMem16    (3<<3) /* Memory operand (16-bit). */
    5.59 -#define SrcImm      (4<<3) /* Immediate operand. */
    5.60 -#define SrcImmByte  (5<<3) /* 8-bit sign-extended immediate operand. */
    5.61 -#define SrcMask     (7<<3)
    5.62 -/* Generic ModRM decode. */
    5.63 -#define ModRM       (1<<6)
    5.64 -/* Destination is only written; never read. */
    5.65 -#define Mov         (1<<7)
    5.66 -
    5.67 -static uint8_t opcode_table[256] = {
    5.68 -    /* 0x00 - 0x07 */
    5.69 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    5.70 -    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    5.71 -    ByteOp|DstReg|SrcImm, DstReg|SrcImm, ImplicitOps, ImplicitOps,
    5.72 -    /* 0x08 - 0x0F */
    5.73 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    5.74 -    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    5.75 -    ByteOp|DstReg|SrcImm, DstReg|SrcImm, ImplicitOps, 0,
    5.76 -    /* 0x10 - 0x17 */
    5.77 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    5.78 -    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    5.79 -    ByteOp|DstReg|SrcImm, DstReg|SrcImm, ImplicitOps, ImplicitOps,
    5.80 -    /* 0x18 - 0x1F */
    5.81 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    5.82 -    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    5.83 -    ByteOp|DstReg|SrcImm, DstReg|SrcImm, ImplicitOps, ImplicitOps,
    5.84 -    /* 0x20 - 0x27 */
    5.85 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    5.86 -    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    5.87 -    ByteOp|DstReg|SrcImm, DstReg|SrcImm, 0, ImplicitOps,
    5.88 -    /* 0x28 - 0x2F */
    5.89 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    5.90 -    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    5.91 -    ByteOp|DstReg|SrcImm, DstReg|SrcImm, 0, ImplicitOps,
    5.92 -    /* 0x30 - 0x37 */
    5.93 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    5.94 -    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    5.95 -    ByteOp|DstReg|SrcImm, DstReg|SrcImm, 0, ImplicitOps,
    5.96 -    /* 0x38 - 0x3F */
    5.97 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    5.98 -    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    5.99 -    ByteOp|DstReg|SrcImm, DstReg|SrcImm, 0, ImplicitOps,
   5.100 -    /* 0x40 - 0x4F */
   5.101 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.102 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.103 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.104 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.105 -    /* 0x50 - 0x5F */
   5.106 -    ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov,
   5.107 -    ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov,
   5.108 -    ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov,
   5.109 -    ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov,
   5.110 -    /* 0x60 - 0x67 */
   5.111 -    ImplicitOps, ImplicitOps, DstReg|SrcMem|ModRM, DstReg|SrcMem16|ModRM|Mov,
   5.112 -    0, 0, 0, 0,
   5.113 -    /* 0x68 - 0x6F */
   5.114 -    ImplicitOps|Mov, DstReg|SrcImm|ModRM|Mov,
   5.115 -    ImplicitOps|Mov, DstReg|SrcImmByte|ModRM|Mov,
   5.116 -    ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov,
   5.117 -    /* 0x70 - 0x77 */
   5.118 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.119 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.120 -    /* 0x78 - 0x7F */
   5.121 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.122 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.123 -    /* 0x80 - 0x87 */
   5.124 -    ByteOp|DstMem|SrcImm|ModRM, DstMem|SrcImm|ModRM,
   5.125 -    ByteOp|DstMem|SrcImm|ModRM, DstMem|SrcImmByte|ModRM,
   5.126 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
   5.127 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
   5.128 -    /* 0x88 - 0x8F */
   5.129 -    ByteOp|DstMem|SrcReg|ModRM|Mov, DstMem|SrcReg|ModRM|Mov,
   5.130 -    ByteOp|DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   5.131 -    DstMem|SrcReg|ModRM|Mov, DstReg|SrcNone|ModRM,
   5.132 -    DstReg|SrcMem|ModRM|Mov, DstMem|SrcNone|ModRM|Mov,
   5.133 -    /* 0x90 - 0x97 */
   5.134 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.135 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.136 -    /* 0x98 - 0x9F */
   5.137 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.138 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.139 -    /* 0xA0 - 0xA7 */
   5.140 -    ByteOp|ImplicitOps|Mov, ImplicitOps|Mov,
   5.141 -    ByteOp|ImplicitOps|Mov, ImplicitOps|Mov,
   5.142 -    ByteOp|ImplicitOps|Mov, ImplicitOps|Mov,
   5.143 -    ByteOp|ImplicitOps, ImplicitOps,
   5.144 -    /* 0xA8 - 0xAF */
   5.145 -    ByteOp|DstReg|SrcImm, DstReg|SrcImm,
   5.146 -    ByteOp|ImplicitOps|Mov, ImplicitOps|Mov,
   5.147 -    ByteOp|ImplicitOps|Mov, ImplicitOps|Mov,
   5.148 -    ByteOp|ImplicitOps, ImplicitOps,
   5.149 -    /* 0xB0 - 0xB7 */
   5.150 -    ByteOp|DstReg|SrcImm|Mov, ByteOp|DstReg|SrcImm|Mov,
   5.151 -    ByteOp|DstReg|SrcImm|Mov, ByteOp|DstReg|SrcImm|Mov,
   5.152 -    ByteOp|DstReg|SrcImm|Mov, ByteOp|DstReg|SrcImm|Mov,
   5.153 -    ByteOp|DstReg|SrcImm|Mov, ByteOp|DstReg|SrcImm|Mov,
   5.154 -    /* 0xB8 - 0xBF */
   5.155 -    DstReg|SrcImm|Mov, DstReg|SrcImm|Mov, DstReg|SrcImm|Mov, DstReg|SrcImm|Mov,
   5.156 -    DstReg|SrcImm|Mov, DstReg|SrcImm|Mov, DstReg|SrcImm|Mov, DstReg|SrcImm|Mov,
   5.157 -    /* 0xC0 - 0xC7 */
   5.158 -    ByteOp|DstMem|SrcImm|ModRM, DstMem|SrcImmByte|ModRM,
   5.159 -    ImplicitOps, ImplicitOps,
   5.160 -    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   5.161 -    ByteOp|DstMem|SrcImm|ModRM|Mov, DstMem|SrcImm|ModRM|Mov,
   5.162 -    /* 0xC8 - 0xCF */
   5.163 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.164 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.165 -    /* 0xD0 - 0xD7 */
   5.166 -    ByteOp|DstMem|SrcImplicit|ModRM, DstMem|SrcImplicit|ModRM, 
   5.167 -    ByteOp|DstMem|SrcImplicit|ModRM, DstMem|SrcImplicit|ModRM, 
   5.168 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.169 -    /* 0xD8 - 0xDF */
   5.170 -    0, ImplicitOps|ModRM|Mov, 0, ImplicitOps|ModRM|Mov,
   5.171 -    0, ImplicitOps|ModRM|Mov, ImplicitOps|ModRM|Mov, ImplicitOps|ModRM|Mov,
   5.172 -    /* 0xE0 - 0xE7 */
   5.173 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.174 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.175 -    /* 0xE8 - 0xEF */
   5.176 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.177 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.178 -    /* 0xF0 - 0xF7 */
   5.179 -    0, ImplicitOps, 0, 0,
   5.180 -    ImplicitOps, ImplicitOps,
   5.181 -    ByteOp|DstMem|SrcNone|ModRM, DstMem|SrcNone|ModRM,
   5.182 -    /* 0xF8 - 0xFF */
   5.183 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.184 -    ImplicitOps, ImplicitOps, ByteOp|DstMem|SrcNone|ModRM, DstMem|SrcNone|ModRM
   5.185 -};
   5.186 +#include <asm/x86_emulate.h>
   5.187  
   5.188 -static uint8_t twobyte_table[256] = {
   5.189 -    /* 0x00 - 0x07 */
   5.190 -    0, ImplicitOps|ModRM, 0, 0, 0, 0, ImplicitOps, 0,
   5.191 -    /* 0x08 - 0x0F */
   5.192 -    ImplicitOps, ImplicitOps, 0, 0, 0, ImplicitOps|ModRM, 0, 0,
   5.193 -    /* 0x10 - 0x17 */
   5.194 -    0, 0, 0, 0, 0, 0, 0, 0,
   5.195 -    /* 0x18 - 0x1F */
   5.196 -    ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM,
   5.197 -    ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM,
   5.198 -    /* 0x20 - 0x27 */
   5.199 -    ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM,
   5.200 -    0, 0, 0, 0,
   5.201 -    /* 0x28 - 0x2F */
   5.202 -    0, 0, 0, 0, 0, 0, 0, 0,
   5.203 -    /* 0x30 - 0x37 */
   5.204 -    ImplicitOps, ImplicitOps, ImplicitOps, 0, 0, 0, 0, 0,
   5.205 -    /* 0x38 - 0x3F */
   5.206 -    0, 0, 0, 0, 0, 0, 0, 0,
   5.207 -    /* 0x40 - 0x47 */
   5.208 -    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   5.209 -    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   5.210 -    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   5.211 -    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   5.212 -    /* 0x48 - 0x4F */
   5.213 -    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   5.214 -    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   5.215 -    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   5.216 -    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   5.217 -    /* 0x50 - 0x5F */
   5.218 -    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
   5.219 -    /* 0x60 - 0x6F */
   5.220 -    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
   5.221 -    /* 0x70 - 0x7F */
   5.222 -    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
   5.223 -    /* 0x80 - 0x87 */
   5.224 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.225 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.226 -    /* 0x88 - 0x8F */
   5.227 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.228 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.229 -    /* 0x90 - 0x97 */
   5.230 -    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   5.231 -    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   5.232 -    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   5.233 -    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   5.234 -    /* 0x98 - 0x9F */
   5.235 -    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   5.236 -    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   5.237 -    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   5.238 -    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   5.239 -    /* 0xA0 - 0xA7 */
   5.240 -    ImplicitOps, ImplicitOps, ImplicitOps, DstBitBase|SrcReg|ModRM,
   5.241 -    DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM, 0, 0, 
   5.242 -    /* 0xA8 - 0xAF */
   5.243 -    ImplicitOps, ImplicitOps, 0, DstBitBase|SrcReg|ModRM,
   5.244 -    DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM, 0, DstReg|SrcMem|ModRM,
   5.245 -    /* 0xB0 - 0xB7 */
   5.246 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
   5.247 -    DstReg|SrcMem|ModRM|Mov, DstBitBase|SrcReg|ModRM,
   5.248 -    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   5.249 -    ByteOp|DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem16|ModRM|Mov,
   5.250 -    /* 0xB8 - 0xBF */
   5.251 -    0, 0, DstBitBase|SrcImmByte|ModRM, DstBitBase|SrcReg|ModRM,
   5.252 -    DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
   5.253 -    ByteOp|DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem16|ModRM|Mov,
   5.254 -    /* 0xC0 - 0xC7 */
   5.255 -    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM, 0, 0,
   5.256 -    0, 0, 0, ImplicitOps|ModRM,
   5.257 -    /* 0xC8 - 0xCF */
   5.258 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.259 -    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   5.260 -    /* 0xD0 - 0xDF */
   5.261 -    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
   5.262 -    /* 0xE0 - 0xEF */
   5.263 -    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
   5.264 -    /* 0xF0 - 0xFF */
   5.265 -    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
   5.266 -};
   5.267 -
   5.268 -/* Type, address-of, and value of an instruction's operand. */
   5.269 -struct operand {
   5.270 -    enum { OP_REG, OP_MEM, OP_IMM, OP_NONE } type;
   5.271 -    unsigned int  bytes;
   5.272 -    unsigned long val, orig_val;
   5.273 -    union {
   5.274 -        /* OP_REG: Pointer to register field. */
   5.275 -        unsigned long *reg;
   5.276 -        /* OP_MEM: Segment and offset. */
   5.277 -        struct {
   5.278 -            enum x86_segment seg;
   5.279 -            unsigned long    off;
   5.280 -        } mem;
   5.281 -    };
   5.282 -};
   5.283 -
   5.284 -/* MSRs. */
   5.285 -#define MSR_TSC   0x10
   5.286 -
   5.287 -/* Control register flags. */
   5.288 -#define CR0_PE    (1<<0)
   5.289 -#define CR4_TSD   (1<<2)
   5.290 -
   5.291 -/* EFLAGS bit definitions. */
   5.292 -#define EFLG_VIP  (1<<20)
   5.293 -#define EFLG_VIF  (1<<19)
   5.294 -#define EFLG_AC   (1<<18)
   5.295 -#define EFLG_VM   (1<<17)
   5.296 -#define EFLG_RF   (1<<16)
   5.297 -#define EFLG_NT   (1<<14)
   5.298 -#define EFLG_IOPL (3<<12)
   5.299 -#define EFLG_OF   (1<<11)
   5.300 -#define EFLG_DF   (1<<10)
   5.301 -#define EFLG_IF   (1<<9)
   5.302 -#define EFLG_TF   (1<<8)
   5.303 -#define EFLG_SF   (1<<7)
   5.304 -#define EFLG_ZF   (1<<6)
   5.305 -#define EFLG_AF   (1<<4)
   5.306 -#define EFLG_PF   (1<<2)
   5.307 -#define EFLG_CF   (1<<0)
   5.308 -
   5.309 -/* Exception definitions. */
   5.310 -#define EXC_DE  0
   5.311 -#define EXC_DB  1
   5.312 -#define EXC_BP  3
   5.313 -#define EXC_OF  4
   5.314 -#define EXC_BR  5
   5.315 -#define EXC_UD  6
   5.316 -#define EXC_TS 10
   5.317 -#define EXC_NP 11
   5.318 -#define EXC_SS 12
   5.319 -#define EXC_GP 13
   5.320 -#define EXC_PF 14
   5.321 -#define EXC_MF 16
   5.322 -
   5.323 -/*
   5.324 - * Instruction emulation:
   5.325 - * Most instructions are emulated directly via a fragment of inline assembly
   5.326 - * code. This allows us to save/restore EFLAGS and thus very easily pick up
   5.327 - * any modified flags.
   5.328 - */
   5.329 +#undef cmpxchg
   5.330  
   5.331 -#if defined(__x86_64__)
   5.332 -#define _LO32 "k"          /* force 32-bit operand */
   5.333 -#define _STK  "%%rsp"      /* stack pointer */
   5.334 -#define _BYTES_PER_LONG "8"
   5.335 -#elif defined(__i386__)
   5.336 -#define _LO32 ""           /* force 32-bit operand */
   5.337 -#define _STK  "%%esp"      /* stack pointer */
   5.338 -#define _BYTES_PER_LONG "4"
   5.339 -#endif
   5.340 -
   5.341 -/*
   5.342 - * These EFLAGS bits are restored from saved value during emulation, and
   5.343 - * any changes are written back to the saved value after emulation.
   5.344 - */
   5.345 -#define EFLAGS_MASK (EFLG_OF|EFLG_SF|EFLG_ZF|EFLG_AF|EFLG_PF|EFLG_CF)
   5.346 -
   5.347 -/* Before executing instruction: restore necessary bits in EFLAGS. */
   5.348 -#define _PRE_EFLAGS(_sav, _msk, _tmp)                           \
   5.349 -/* EFLAGS = (_sav & _msk) | (EFLAGS & ~_msk); _sav &= ~_msk; */ \
   5.350 -"movl %"_sav",%"_LO32 _tmp"; "                                  \
   5.351 -"push %"_tmp"; "                                                \
   5.352 -"push %"_tmp"; "                                                \
   5.353 -"movl %"_msk",%"_LO32 _tmp"; "                                  \
   5.354 -"andl %"_LO32 _tmp",("_STK"); "                                 \
   5.355 -"pushf; "                                                       \
   5.356 -"notl %"_LO32 _tmp"; "                                          \
   5.357 -"andl %"_LO32 _tmp",("_STK"); "                                 \
   5.358 -"andl %"_LO32 _tmp",2*"_BYTES_PER_LONG"("_STK"); "              \
   5.359 -"pop  %"_tmp"; "                                                \
   5.360 -"orl  %"_LO32 _tmp",("_STK"); "                                 \
   5.361 -"popf; "                                                        \
   5.362 -"pop  %"_sav"; "
   5.363 -
   5.364 -/* After executing instruction: write-back necessary bits in EFLAGS. */
   5.365 -#define _POST_EFLAGS(_sav, _msk, _tmp)          \
   5.366 -/* _sav |= EFLAGS & _msk; */                    \
   5.367 -"pushf; "                                       \
   5.368 -"pop  %"_tmp"; "                                \
   5.369 -"andl %"_msk",%"_LO32 _tmp"; "                  \
   5.370 -"orl  %"_LO32 _tmp",%"_sav"; "
   5.371 -
   5.372 -/* Raw emulation: instruction has two explicit operands. */
   5.373 -#define __emulate_2op_nobyte(_op,_src,_dst,_eflags,_wx,_wy,_lx,_ly,_qx,_qy)\
   5.374 -do{ unsigned long _tmp;                                                    \
   5.375 -    switch ( (_dst).bytes )                                                \
   5.376 -    {                                                                      \
   5.377 -    case 2:                                                                \
   5.378 -        asm volatile (                                                     \
   5.379 -            _PRE_EFLAGS("0","4","2")                                       \
   5.380 -            _op"w %"_wx"3,%1; "                                            \
   5.381 -            _POST_EFLAGS("0","4","2")                                      \
   5.382 -            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   5.383 -            : _wy ((_src).val), "i" (EFLAGS_MASK),                         \
   5.384 -              "m" (_eflags), "m" ((_dst).val) );                           \
   5.385 -        break;                                                             \
   5.386 -    case 4:                                                                \
   5.387 -        asm volatile (                                                     \
   5.388 -            _PRE_EFLAGS("0","4","2")                                       \
   5.389 -            _op"l %"_lx"3,%1; "                                            \
   5.390 -            _POST_EFLAGS("0","4","2")                                      \
   5.391 -            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   5.392 -            : _ly ((_src).val), "i" (EFLAGS_MASK),                         \
   5.393 -              "m" (_eflags), "m" ((_dst).val) );                           \
   5.394 -        break;                                                             \
   5.395 -    case 8:                                                                \
   5.396 -        __emulate_2op_8byte(_op, _src, _dst, _eflags, _qx, _qy);           \
   5.397 -        break;                                                             \
   5.398 -    }                                                                      \
   5.399 -} while (0)
   5.400 -#define __emulate_2op(_op,_src,_dst,_eflags,_bx,_by,_wx,_wy,_lx,_ly,_qx,_qy)\
   5.401 -do{ unsigned long _tmp;                                                    \
   5.402 -    switch ( (_dst).bytes )                                                \
   5.403 -    {                                                                      \
   5.404 -    case 1:                                                                \
   5.405 -        asm volatile (                                                     \
   5.406 -            _PRE_EFLAGS("0","4","2")                                       \
   5.407 -            _op"b %"_bx"3,%1; "                                            \
   5.408 -            _POST_EFLAGS("0","4","2")                                      \
   5.409 -            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   5.410 -            : _by ((_src).val), "i" (EFLAGS_MASK),                         \
   5.411 -              "m" (_eflags), "m" ((_dst).val) );                           \
   5.412 -        break;                                                             \
   5.413 -    default:                                                               \
   5.414 -        __emulate_2op_nobyte(_op,_src,_dst,_eflags,_wx,_wy,_lx,_ly,_qx,_qy);\
   5.415 -        break;                                                             \
   5.416 -    }                                                                      \
   5.417 -} while (0)
   5.418 -/* Source operand is byte-sized and may be restricted to just %cl. */
   5.419 -#define emulate_2op_SrcB(_op, _src, _dst, _eflags)                         \
   5.420 -    __emulate_2op(_op, _src, _dst, _eflags,                                \
   5.421 -                  "b", "c", "b", "c", "b", "c", "b", "c")
   5.422 -/* Source operand is byte, word, long or quad sized. */
   5.423 -#define emulate_2op_SrcV(_op, _src, _dst, _eflags)                         \
   5.424 -    __emulate_2op(_op, _src, _dst, _eflags,                                \
   5.425 -                  "b", "q", "w", "r", _LO32, "r", "", "r")
   5.426 -/* Source operand is word, long or quad sized. */
   5.427 -#define emulate_2op_SrcV_nobyte(_op, _src, _dst, _eflags)                  \
   5.428 -    __emulate_2op_nobyte(_op, _src, _dst, _eflags,                         \
   5.429 -                  "w", "r", _LO32, "r", "", "r")
   5.430 -
   5.431 -/* Instruction has only one explicit operand (no source operand). */
   5.432 -#define emulate_1op(_op,_dst,_eflags)                                      \
   5.433 -do{ unsigned long _tmp;                                                    \
   5.434 -    switch ( (_dst).bytes )                                                \
   5.435 -    {                                                                      \
   5.436 -    case 1:                                                                \
   5.437 -        asm volatile (                                                     \
   5.438 -            _PRE_EFLAGS("0","3","2")                                       \
   5.439 -            _op"b %1; "                                                    \
   5.440 -            _POST_EFLAGS("0","3","2")                                      \
   5.441 -            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   5.442 -            : "i" (EFLAGS_MASK), "m" (_eflags), "m" ((_dst).val) );        \
   5.443 -        break;                                                             \
   5.444 -    case 2:                                                                \
   5.445 -        asm volatile (                                                     \
   5.446 -            _PRE_EFLAGS("0","3","2")                                       \
   5.447 -            _op"w %1; "                                                    \
   5.448 -            _POST_EFLAGS("0","3","2")                                      \
   5.449 -            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   5.450 -            : "i" (EFLAGS_MASK), "m" (_eflags), "m" ((_dst).val) );        \
   5.451 -        break;                                                             \
   5.452 -    case 4:                                                                \
   5.453 -        asm volatile (                                                     \
   5.454 -            _PRE_EFLAGS("0","3","2")                                       \
   5.455 -            _op"l %1; "                                                    \
   5.456 -            _POST_EFLAGS("0","3","2")                                      \
   5.457 -            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   5.458 -            : "i" (EFLAGS_MASK), "m" (_eflags), "m" ((_dst).val) );        \
   5.459 -        break;                                                             \
   5.460 -    case 8:                                                                \
   5.461 -        __emulate_1op_8byte(_op, _dst, _eflags);                           \
   5.462 -        break;                                                             \
   5.463 -    }                                                                      \
   5.464 -} while (0)
   5.465 -
   5.466 -/* Emulate an instruction with quadword operands (x86/64 only). */
   5.467 -#if defined(__x86_64__)
   5.468 -#define __emulate_2op_8byte(_op, _src, _dst, _eflags, _qx, _qy)         \
   5.469 -do{ asm volatile (                                                      \
   5.470 -        _PRE_EFLAGS("0","4","2")                                        \
   5.471 -        _op"q %"_qx"3,%1; "                                             \
   5.472 -        _POST_EFLAGS("0","4","2")                                       \
   5.473 -        : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)               \
   5.474 -        : _qy ((_src).val), "i" (EFLAGS_MASK),                          \
   5.475 -          "m" (_eflags), "m" ((_dst).val) );                            \
   5.476 -} while (0)
   5.477 -#define __emulate_1op_8byte(_op, _dst, _eflags)                         \
   5.478 -do{ asm volatile (                                                      \
   5.479 -        _PRE_EFLAGS("0","3","2")                                        \
   5.480 -        _op"q %1; "                                                     \
   5.481 -        _POST_EFLAGS("0","3","2")                                       \
   5.482 -        : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)               \
   5.483 -        : "i" (EFLAGS_MASK), "m" (_eflags), "m" ((_dst).val) );         \
   5.484 -} while (0)
   5.485 -#elif defined(__i386__)
   5.486 -#define __emulate_2op_8byte(_op, _src, _dst, _eflags, _qx, _qy)
   5.487 -#define __emulate_1op_8byte(_op, _dst, _eflags)
   5.488 -#endif /* __i386__ */
   5.489 -
   5.490 -#ifdef __XEN__
   5.491  #define __emulate_fpu_insn(_op)                 \
   5.492  do{ int _exn;                                   \
   5.493      asm volatile (                              \
   5.494 @@ -495,2984 +29,5 @@ do{ int _exn;                           
   5.495          : "=r" (_exn) : "0" (0) );              \
   5.496      generate_exception_if(_exn, EXC_MF, -1);    \
   5.497  } while (0)
   5.498 -#else
   5.499 -#define __emulate_fpu_insn(_op)                 \
   5.500 -do{ rc = X86EMUL_UNHANDLEABLE;                  \
   5.501 -    goto done;                                  \
   5.502 -} while (0)
   5.503 -#endif
   5.504  
   5.505 -
   5.506 -/* Fetch next part of the instruction being emulated. */
   5.507 -#define insn_fetch_bytes(_size)                                         \
   5.508 -({ unsigned long _x, _eip = _regs.eip;                                  \
   5.509 -   if ( !mode_64bit() ) _eip = (uint32_t)_eip; /* ignore upper dword */ \
   5.510 -   _regs.eip += (_size); /* real hardware doesn't truncate */           \
   5.511 -   generate_exception_if((uint8_t)(_regs.eip - ctxt->regs->eip) > 15,   \
   5.512 -                         EXC_GP, 0);                                    \
   5.513 -   rc = ops->insn_fetch(x86_seg_cs, _eip, &_x, (_size), ctxt);          \
   5.514 -   if ( rc ) goto done;                                                 \
   5.515 -   _x;                                                                  \
   5.516 -})
   5.517 -#define insn_fetch_type(_type) ((_type)insn_fetch_bytes(sizeof(_type)))
   5.518 -
   5.519 -#define truncate_word(ea, byte_width)           \
   5.520 -({  unsigned long __ea = (ea);                  \
   5.521 -    unsigned int _width = (byte_width);         \
   5.522 -    ((_width == sizeof(unsigned long)) ? __ea : \
   5.523 -     (__ea & ((1UL << (_width << 3)) - 1)));    \
   5.524 -})
   5.525 -#define truncate_ea(ea) truncate_word((ea), ad_bytes)
   5.526 -
   5.527 -#define mode_64bit() (def_ad_bytes == 8)
   5.528 -
   5.529 -#define fail_if(p)                                      \
   5.530 -do {                                                    \
   5.531 -    rc = (p) ? X86EMUL_UNHANDLEABLE : X86EMUL_OKAY;     \
   5.532 -    if ( rc ) goto done;                                \
   5.533 -} while (0)
   5.534 -
   5.535 -#define generate_exception_if(p, e, ec)                                   \
   5.536 -({  if ( (p) ) {                                                          \
   5.537 -        fail_if(ops->inject_hw_exception == NULL);                        \
   5.538 -        rc = ops->inject_hw_exception(e, ec, ctxt) ? : X86EMUL_EXCEPTION; \
   5.539 -        goto done;                                                        \
   5.540 -    }                                                                     \
   5.541 -})
   5.542 -
   5.543 -/*
   5.544 - * Given byte has even parity (even number of 1s)? SDM Vol. 1 Sec. 3.4.3.1,
   5.545 - * "Status Flags": EFLAGS.PF reflects parity of least-sig. byte of result only.
   5.546 - */
   5.547 -static int even_parity(uint8_t v)
   5.548 -{
   5.549 -    asm ( "test %b0,%b0; setp %b0" : "=a" (v) : "0" (v) );
   5.550 -    return v;
   5.551 -}
   5.552 -
   5.553 -/* Update address held in a register, based on addressing mode. */
   5.554 -#define _register_address_increment(reg, inc, byte_width)               \
   5.555 -do {                                                                    \
   5.556 -    int _inc = (inc); /* signed type ensures sign extension to long */  \
   5.557 -    unsigned int _width = (byte_width);                                 \
   5.558 -    if ( _width == sizeof(unsigned long) )                              \
   5.559 -        (reg) += _inc;                                                  \
   5.560 -    else if ( mode_64bit() )                                            \
   5.561 -        (reg) = ((reg) + _inc) & ((1UL << (_width << 3)) - 1);          \
   5.562 -    else                                                                \
   5.563 -        (reg) = ((reg) & ~((1UL << (_width << 3)) - 1)) |               \
   5.564 -                (((reg) + _inc) & ((1UL << (_width << 3)) - 1));        \
   5.565 -} while (0)
   5.566 -#define register_address_increment(reg, inc) \
   5.567 -    _register_address_increment((reg), (inc), ad_bytes)
   5.568 -
   5.569 -#define sp_pre_dec(dec) ({                                              \
   5.570 -    _register_address_increment(_regs.esp, -(dec), ctxt->sp_size/8);    \
   5.571 -    truncate_word(_regs.esp, ctxt->sp_size/8);                          \
   5.572 -})
   5.573 -#define sp_post_inc(inc) ({                                             \
   5.574 -    unsigned long __esp = truncate_word(_regs.esp, ctxt->sp_size/8);    \
   5.575 -    _register_address_increment(_regs.esp, (inc), ctxt->sp_size/8);     \
   5.576 -    __esp;                                                              \
   5.577 -})
   5.578 -
   5.579 -#define jmp_rel(rel)                                                    \
   5.580 -do {                                                                    \
   5.581 -    int _rel = (int)(rel);                                              \
   5.582 -    _regs.eip += _rel;                                                  \
   5.583 -    if ( !mode_64bit() )                                                \
   5.584 -        _regs.eip = ((op_bytes == 2)                                    \
   5.585 -                     ? (uint16_t)_regs.eip : (uint32_t)_regs.eip);      \
   5.586 -} while (0)
   5.587 -
   5.588 -static unsigned long __get_rep_prefix(
   5.589 -    struct cpu_user_regs *int_regs,
   5.590 -    struct cpu_user_regs *ext_regs,
   5.591 -    int ad_bytes)
   5.592 -{
   5.593 -    unsigned long ecx = ((ad_bytes == 2) ? (uint16_t)int_regs->ecx :
   5.594 -                         (ad_bytes == 4) ? (uint32_t)int_regs->ecx :
   5.595 -                         int_regs->ecx);
   5.596 -
   5.597 -    /* Skip the instruction if no repetitions are required. */
   5.598 -    if ( ecx == 0 )
   5.599 -        ext_regs->eip = int_regs->eip;
   5.600 -
   5.601 -    return ecx;
   5.602 -}
   5.603 -
   5.604 -#define get_rep_prefix() ({                                             \
   5.605 -    unsigned long max_reps = 1;                                         \
   5.606 -    if ( rep_prefix )                                                   \
   5.607 -        max_reps = __get_rep_prefix(&_regs, ctxt->regs, ad_bytes);      \
   5.608 -    if ( max_reps == 0 )                                                \
   5.609 -        goto done;                                                      \
   5.610 -   max_reps;                                                            \
   5.611 -})
   5.612 -
   5.613 -static void __put_rep_prefix(
   5.614 -    struct cpu_user_regs *int_regs,
   5.615 -    struct cpu_user_regs *ext_regs,
   5.616 -    int ad_bytes,
   5.617 -    unsigned long reps_completed)
   5.618 -{
   5.619 -    unsigned long ecx = ((ad_bytes == 2) ? (uint16_t)int_regs->ecx :
   5.620 -                         (ad_bytes == 4) ? (uint32_t)int_regs->ecx :
   5.621 -                         int_regs->ecx);
   5.622 -
   5.623 -    /* Reduce counter appropriately, and repeat instruction if non-zero. */
   5.624 -    ecx -= reps_completed;
   5.625 -    if ( ecx != 0 )
   5.626 -        int_regs->eip = ext_regs->eip;
   5.627 -
   5.628 -    if ( ad_bytes == 2 )
   5.629 -        *(uint16_t *)&int_regs->ecx = ecx;
   5.630 -    else if ( ad_bytes == 4 )
   5.631 -        int_regs->ecx = (uint32_t)ecx;
   5.632 -    else
   5.633 -        int_regs->ecx = ecx;
   5.634 -}
   5.635 -
   5.636 -#define put_rep_prefix(reps_completed) ({                               \
   5.637 -    if ( rep_prefix )                                                   \
   5.638 -        __put_rep_prefix(&_regs, ctxt->regs, ad_bytes, reps_completed); \
   5.639 -})
   5.640 -
   5.641 -/*
   5.642 - * Unsigned multiplication with double-word result.
   5.643 - * IN:  Multiplicand=m[0], Multiplier=m[1]
   5.644 - * OUT: Return CF/OF (overflow status); Result=m[1]:m[0]
   5.645 - */
   5.646 -static int mul_dbl(unsigned long m[2])
   5.647 -{
   5.648 -    int rc;
   5.649 -    asm ( "mul %4; seto %b2"
   5.650 -          : "=a" (m[0]), "=d" (m[1]), "=q" (rc)
   5.651 -          : "0" (m[0]), "1" (m[1]), "2" (0) );
   5.652 -    return rc;
   5.653 -}
   5.654 -
   5.655 -/*
   5.656 - * Signed multiplication with double-word result.
   5.657 - * IN:  Multiplicand=m[0], Multiplier=m[1]
   5.658 - * OUT: Return CF/OF (overflow status); Result=m[1]:m[0]
   5.659 - */
   5.660 -static int imul_dbl(unsigned long m[2])
   5.661 -{
   5.662 -    int rc;
   5.663 -    asm ( "imul %4; seto %b2"
   5.664 -          : "=a" (m[0]), "=d" (m[1]), "=q" (rc)
   5.665 -          : "0" (m[0]), "1" (m[1]), "2" (0) );
   5.666 -    return rc;
   5.667 -}
   5.668 -
   5.669 -/*
   5.670 - * Unsigned division of double-word dividend.
   5.671 - * IN:  Dividend=u[1]:u[0], Divisor=v
   5.672 - * OUT: Return 1: #DE
   5.673 - *      Return 0: Quotient=u[0], Remainder=u[1]
   5.674 - */
   5.675 -static int div_dbl(unsigned long u[2], unsigned long v)
   5.676 -{
   5.677 -    if ( (v == 0) || (u[1] >= v) )
   5.678 -        return 1;
   5.679 -    asm ( "div %4"
   5.680 -          : "=a" (u[0]), "=d" (u[1])
   5.681 -          : "0" (u[0]), "1" (u[1]), "r" (v) );
   5.682 -    return 0;
   5.683 -}
   5.684 -
   5.685 -/*
   5.686 - * Signed division of double-word dividend.
   5.687 - * IN:  Dividend=u[1]:u[0], Divisor=v
   5.688 - * OUT: Return 1: #DE
   5.689 - *      Return 0: Quotient=u[0], Remainder=u[1]
   5.690 - * NB. We don't use idiv directly as it's moderately hard to work out
   5.691 - *     ahead of time whether it will #DE, which we cannot allow to happen.
   5.692 - */
   5.693 -static int idiv_dbl(unsigned long u[2], unsigned long v)
   5.694 -{
   5.695 -    int negu = (long)u[1] < 0, negv = (long)v < 0;
   5.696 -
   5.697 -    /* u = abs(u) */
   5.698 -    if ( negu )
   5.699 -    {
   5.700 -        u[1] = ~u[1];
   5.701 -        if ( (u[0] = -u[0]) == 0 )
   5.702 -            u[1]++;
   5.703 -    }
   5.704 -
   5.705 -    /* abs(u) / abs(v) */
   5.706 -    if ( div_dbl(u, negv ? -v : v) )
   5.707 -        return 1;
   5.708 -
   5.709 -    /* Remainder has same sign as dividend. It cannot overflow. */
   5.710 -    if ( negu )
   5.711 -        u[1] = -u[1];
   5.712 -
   5.713 -    /* Quotient is overflowed if sign bit is set. */
   5.714 -    if ( negu ^ negv )
   5.715 -    {
   5.716 -        if ( (long)u[0] >= 0 )
   5.717 -            u[0] = -u[0];
   5.718 -        else if ( (u[0] << 1) != 0 ) /* == 0x80...0 is okay */
   5.719 -            return 1;
   5.720 -    }
   5.721 -    else if ( (long)u[0] < 0 )
   5.722 -        return 1;
   5.723 -
   5.724 -    return 0;
   5.725 -}
   5.726 -
   5.727 -static int
   5.728 -test_cc(
   5.729 -    unsigned int condition, unsigned int flags)
   5.730 -{
   5.731 -    int rc = 0;
   5.732 -
   5.733 -    switch ( (condition & 15) >> 1 )
   5.734 -    {
   5.735 -    case 0: /* o */
   5.736 -        rc |= (flags & EFLG_OF);
   5.737 -        break;
   5.738 -    case 1: /* b/c/nae */
   5.739 -        rc |= (flags & EFLG_CF);
   5.740 -        break;
   5.741 -    case 2: /* z/e */
   5.742 -        rc |= (flags & EFLG_ZF);
   5.743 -        break;
   5.744 -    case 3: /* be/na */
   5.745 -        rc |= (flags & (EFLG_CF|EFLG_ZF));
   5.746 -        break;
   5.747 -    case 4: /* s */
   5.748 -        rc |= (flags & EFLG_SF);
   5.749 -        break;
   5.750 -    case 5: /* p/pe */
   5.751 -        rc |= (flags & EFLG_PF);
   5.752 -        break;
   5.753 -    case 7: /* le/ng */
   5.754 -        rc |= (flags & EFLG_ZF);
   5.755 -        /* fall through */
   5.756 -    case 6: /* l/nge */
   5.757 -        rc |= (!(flags & EFLG_SF) != !(flags & EFLG_OF));
   5.758 -        break;
   5.759 -    }
   5.760 -
   5.761 -    /* Odd condition identifiers (lsb == 1) have inverted sense. */
   5.762 -    return (!!rc ^ (condition & 1));
   5.763 -}
   5.764 -
   5.765 -static int
   5.766 -get_cpl(
   5.767 -    struct x86_emulate_ctxt *ctxt,
   5.768 -    struct x86_emulate_ops  *ops)
   5.769 -{
   5.770 -    struct segment_register reg;
   5.771 -
   5.772 -    if ( ctxt->regs->eflags & EFLG_VM )
   5.773 -        return 3;
   5.774 -
   5.775 -    if ( (ops->read_segment == NULL) ||
   5.776 -         ops->read_segment(x86_seg_ss, &reg, ctxt) )
   5.777 -        return -1;
   5.778 -
   5.779 -    return reg.attr.fields.dpl;
   5.780 -}
   5.781 -
   5.782 -static int
   5.783 -_mode_iopl(
   5.784 -    struct x86_emulate_ctxt *ctxt,
   5.785 -    struct x86_emulate_ops  *ops)
   5.786 -{
   5.787 -    int cpl = get_cpl(ctxt, ops);
   5.788 -    if ( cpl == -1 )
   5.789 -        return -1;
   5.790 -    return (cpl <= ((ctxt->regs->eflags >> 12) & 3));
   5.791 -}
   5.792 -
   5.793 -#define mode_ring0() ({                         \
   5.794 -    int _cpl = get_cpl(ctxt, ops);              \
   5.795 -    fail_if(_cpl < 0);                          \
   5.796 -    (_cpl == 0);                                \
   5.797 -})
   5.798 -#define mode_iopl() ({                          \
   5.799 -    int _iopl = _mode_iopl(ctxt, ops);          \
   5.800 -    fail_if(_iopl < 0);                         \
   5.801 -    _iopl;                                      \
   5.802 -})
   5.803 -
   5.804 -static int ioport_access_check(
   5.805 -    unsigned int first_port,
   5.806 -    unsigned int bytes,
   5.807 -    struct x86_emulate_ctxt *ctxt,
   5.808 -    struct x86_emulate_ops *ops)
   5.809 -{
   5.810 -    unsigned long iobmp;
   5.811 -    struct segment_register tr;
   5.812 -    int rc = X86EMUL_OKAY;
   5.813 -
   5.814 -    if ( !(ctxt->regs->eflags & EFLG_VM) && mode_iopl() )
   5.815 -        return X86EMUL_OKAY;
   5.816 -
   5.817 -    fail_if(ops->read_segment == NULL);
   5.818 -    if ( (rc = ops->read_segment(x86_seg_tr, &tr, ctxt)) != 0 )
   5.819 -        return rc;
   5.820 -
   5.821 -    /* Ensure that the TSS is valid and has an io-bitmap-offset field. */
   5.822 -    if ( !tr.attr.fields.p ||
   5.823 -         ((tr.attr.fields.type & 0xd) != 0x9) ||
   5.824 -         (tr.limit < 0x67) )
   5.825 -        goto raise_exception;
   5.826 -
   5.827 -    if ( (rc = ops->read(x86_seg_none, tr.base + 0x66, &iobmp, 2, ctxt)) )
   5.828 -        return rc;
   5.829 -
   5.830 -    /* Ensure TSS includes two bytes including byte containing first port. */
   5.831 -    iobmp += first_port / 8;
   5.832 -    if ( tr.limit <= iobmp )
   5.833 -        goto raise_exception;
   5.834 -
   5.835 -    if ( (rc = ops->read(x86_seg_none, tr.base + iobmp, &iobmp, 2, ctxt)) )
   5.836 -        return rc;
   5.837 -    if ( (iobmp & (((1<<bytes)-1) << (first_port&7))) != 0 )
   5.838 -        goto raise_exception;
   5.839 -
   5.840 - done:
   5.841 -    return rc;
   5.842 -
   5.843 - raise_exception:
   5.844 -    fail_if(ops->inject_hw_exception == NULL);
   5.845 -    return ops->inject_hw_exception(EXC_GP, 0, ctxt) ? : X86EMUL_EXCEPTION;
   5.846 -}
   5.847 -
   5.848 -static int
   5.849 -in_realmode(
   5.850 -    struct x86_emulate_ctxt *ctxt,
   5.851 -    struct x86_emulate_ops  *ops)
   5.852 -{
   5.853 -    unsigned long cr0;
   5.854 -    int rc;
   5.855 -
   5.856 -    if ( ops->read_cr == NULL )
   5.857 -        return 0;
   5.858 -
   5.859 -    rc = ops->read_cr(0, &cr0, ctxt);
   5.860 -    return (!rc && !(cr0 & CR0_PE));
   5.861 -}
   5.862 -
   5.863 -static int
   5.864 -realmode_load_seg(
   5.865 -    enum x86_segment seg,
   5.866 -    uint16_t sel,
   5.867 -    struct x86_emulate_ctxt *ctxt,
   5.868 -    struct x86_emulate_ops *ops)
   5.869 -{
   5.870 -    struct segment_register reg;
   5.871 -    int rc;
   5.872 -
   5.873 -    if ( (rc = ops->read_segment(seg, &reg, ctxt)) != 0 )
   5.874 -        return rc;
   5.875 -
   5.876 -    reg.sel  = sel;
   5.877 -    reg.base = (uint32_t)sel << 4;
   5.878 -
   5.879 -    return ops->write_segment(seg, &reg, ctxt);
   5.880 -}
   5.881 -
   5.882 -static int
   5.883 -protmode_load_seg(
   5.884 -    enum x86_segment seg,
   5.885 -    uint16_t sel,
   5.886 -    struct x86_emulate_ctxt *ctxt,
   5.887 -    struct x86_emulate_ops *ops)
   5.888 -{
   5.889 -    struct segment_register desctab, cs, segr;
   5.890 -    struct { uint32_t a, b; } desc;
   5.891 -    unsigned long val;
   5.892 -    uint8_t dpl, rpl, cpl;
   5.893 -    int rc, fault_type = EXC_TS;
   5.894 -
   5.895 -    /* NULL selector? */
   5.896 -    if ( (sel & 0xfffc) == 0 )
   5.897 -    {
   5.898 -        if ( (seg == x86_seg_cs) || (seg == x86_seg_ss) )
   5.899 -            goto raise_exn;
   5.900 -        memset(&segr, 0, sizeof(segr));
   5.901 -        return ops->write_segment(seg, &segr, ctxt);
   5.902 -    }
   5.903 -
   5.904 -    /* LDT descriptor must be in the GDT. */
   5.905 -    if ( (seg == x86_seg_ldtr) && (sel & 4) )
   5.906 -        goto raise_exn;
   5.907 -
   5.908 -    if ( (rc = ops->read_segment(x86_seg_cs, &cs, ctxt)) ||
   5.909 -         (rc = ops->read_segment((sel & 4) ? x86_seg_ldtr : x86_seg_gdtr,
   5.910 -                                 &desctab, ctxt)) )
   5.911 -        return rc;
   5.912 -
   5.913 -    /* Check against descriptor table limit. */
   5.914 -    if ( ((sel & 0xfff8) + 7) > desctab.limit )
   5.915 -        goto raise_exn;
   5.916 -
   5.917 -    do {
   5.918 -        if ( (rc = ops->read(x86_seg_none, desctab.base + (sel & 0xfff8),
   5.919 -                             &val, 4, ctxt)) )
   5.920 -            return rc;
   5.921 -        desc.a = val;
   5.922 -        if ( (rc = ops->read(x86_seg_none, desctab.base + (sel & 0xfff8) + 4,
   5.923 -                             &val, 4, ctxt)) )
   5.924 -            return rc;
   5.925 -        desc.b = val;
   5.926 -
   5.927 -        /* Segment present in memory? */
   5.928 -        if ( !(desc.b & (1u<<15)) )
   5.929 -        {
   5.930 -            fault_type = EXC_NP;
   5.931 -            goto raise_exn;
   5.932 -        }
   5.933 -
   5.934 -        /* LDT descriptor is a system segment. All others are code/data. */
   5.935 -        if ( (desc.b & (1u<<12)) == ((seg == x86_seg_ldtr) << 12) )
   5.936 -            goto raise_exn;
   5.937 -
   5.938 -        dpl = (desc.b >> 13) & 3;
   5.939 -        rpl = sel & 3;
   5.940 -        cpl = cs.sel & 3;
   5.941 -
   5.942 -        switch ( seg )
   5.943 -        {
   5.944 -        case x86_seg_cs:
   5.945 -            /* Code segment? */
   5.946 -            if ( !(desc.b & (1u<<11)) )
   5.947 -                goto raise_exn;
   5.948 -            /* Non-conforming segment: check DPL against RPL. */
   5.949 -            if ( ((desc.b & (6u<<9)) != 6) && (dpl != rpl) )
   5.950 -                goto raise_exn;
   5.951 -            break;
   5.952 -        case x86_seg_ss:
   5.953 -            /* Writable data segment? */
   5.954 -            if ( (desc.b & (5u<<9)) != (1u<<9) )
   5.955 -                goto raise_exn;
   5.956 -            if ( (dpl != cpl) || (dpl != rpl) )
   5.957 -                goto raise_exn;
   5.958 -            break;
   5.959 -        case x86_seg_ldtr:
   5.960 -            /* LDT system segment? */
   5.961 -            if ( (desc.b & (15u<<8)) != (2u<<8) )
   5.962 -                goto raise_exn;
   5.963 -            goto skip_accessed_flag;
   5.964 -        default:
   5.965 -            /* Readable code or data segment? */
   5.966 -            if ( (desc.b & (5u<<9)) == (4u<<9) )
   5.967 -                goto raise_exn;
   5.968 -            /* Non-conforming segment: check DPL against RPL and CPL. */
   5.969 -            if ( ((desc.b & (6u<<9)) != 6) && ((dpl < cpl) || (dpl < rpl)) )
   5.970 -                goto raise_exn;
   5.971 -            break;
   5.972 -        }
   5.973 -
   5.974 -        /* Ensure Accessed flag is set. */
   5.975 -        rc = ((desc.b & 0x100) ? X86EMUL_OKAY : 
   5.976 -              ops->cmpxchg(
   5.977 -                  x86_seg_none, desctab.base + (sel & 0xfff8) + 4, desc.b,
   5.978 -                  desc.b | 0x100, 4, ctxt));
   5.979 -    } while ( rc == X86EMUL_CMPXCHG_FAILED );
   5.980 -
   5.981 -    if ( rc )
   5.982 -        return rc;
   5.983 -
   5.984 -    /* Force the Accessed flag in our local copy. */
   5.985 -    desc.b |= 0x100;
   5.986 -
   5.987 - skip_accessed_flag:
   5.988 -    segr.base = (((desc.b <<  0) & 0xff000000u) |
   5.989 -                 ((desc.b << 16) & 0x00ff0000u) |
   5.990 -                 ((desc.a >> 16) & 0x0000ffffu));
   5.991 -    segr.attr.bytes = (((desc.b >>  8) & 0x00ffu) |
   5.992 -                       ((desc.b >> 12) & 0x0f00u));
   5.993 -    segr.limit = (desc.b & 0x000f0000u) | (desc.a & 0x0000ffffu);
   5.994 -    if ( segr.attr.fields.g )
   5.995 -        segr.limit = (segr.limit << 12) | 0xfffu;
   5.996 -    segr.sel = sel;
   5.997 -    return ops->write_segment(seg, &segr, ctxt);
   5.998 -
   5.999 - raise_exn:
  5.1000 -    if ( ops->inject_hw_exception == NULL )
  5.1001 -        return X86EMUL_UNHANDLEABLE;
  5.1002 -    if ( (rc = ops->inject_hw_exception(fault_type, sel & 0xfffc, ctxt)) )
  5.1003 -        return rc;
  5.1004 -    return X86EMUL_EXCEPTION;
  5.1005 -}
  5.1006 -
  5.1007 -static int
  5.1008 -load_seg(
  5.1009 -    enum x86_segment seg,
  5.1010 -    uint16_t sel,
  5.1011 -    struct x86_emulate_ctxt *ctxt,
  5.1012 -    struct x86_emulate_ops *ops)
  5.1013 -{
  5.1014 -    if ( (ops->read_segment == NULL) ||
  5.1015 -         (ops->write_segment == NULL) )
  5.1016 -        return X86EMUL_UNHANDLEABLE;
  5.1017 -
  5.1018 -    if ( in_realmode(ctxt, ops) )
  5.1019 -        return realmode_load_seg(seg, sel, ctxt, ops);
  5.1020 -
  5.1021 -    return protmode_load_seg(seg, sel, ctxt, ops);
  5.1022 -}
  5.1023 -
  5.1024 -void *
  5.1025 -decode_register(
  5.1026 -    uint8_t modrm_reg, struct cpu_user_regs *regs, int highbyte_regs)
  5.1027 -{
  5.1028 -    void *p;
  5.1029 -
  5.1030 -    switch ( modrm_reg )
  5.1031 -    {
  5.1032 -    case  0: p = &regs->eax; break;
  5.1033 -    case  1: p = &regs->ecx; break;
  5.1034 -    case  2: p = &regs->edx; break;
  5.1035 -    case  3: p = &regs->ebx; break;
  5.1036 -    case  4: p = (highbyte_regs ?
  5.1037 -                  ((unsigned char *)&regs->eax + 1) : 
  5.1038 -                  (unsigned char *)&regs->esp); break;
  5.1039 -    case  5: p = (highbyte_regs ?
  5.1040 -                  ((unsigned char *)&regs->ecx + 1) : 
  5.1041 -                  (unsigned char *)&regs->ebp); break;
  5.1042 -    case  6: p = (highbyte_regs ?
  5.1043 -                  ((unsigned char *)&regs->edx + 1) : 
  5.1044 -                  (unsigned char *)&regs->esi); break;
  5.1045 -    case  7: p = (highbyte_regs ?
  5.1046 -                  ((unsigned char *)&regs->ebx + 1) : 
  5.1047 -                  (unsigned char *)&regs->edi); break;
  5.1048 -#if defined(__x86_64__)
  5.1049 -    case  8: p = &regs->r8;  break;
  5.1050 -    case  9: p = &regs->r9;  break;
  5.1051 -    case 10: p = &regs->r10; break;
  5.1052 -    case 11: p = &regs->r11; break;
  5.1053 -    case 12: p = &regs->r12; break;
  5.1054 -    case 13: p = &regs->r13; break;
  5.1055 -    case 14: p = &regs->r14; break;
  5.1056 -    case 15: p = &regs->r15; break;
  5.1057 -#endif
  5.1058 -    default: p = NULL; break;
  5.1059 -    }
  5.1060 -
  5.1061 -    return p;
  5.1062 -}
  5.1063 -
  5.1064 -#define decode_segment_failed x86_seg_tr
  5.1065 -enum x86_segment
  5.1066 -decode_segment(
  5.1067 -    uint8_t modrm_reg)
  5.1068 -{
  5.1069 -    switch ( modrm_reg )
  5.1070 -    {
  5.1071 -    case 0: return x86_seg_es;
  5.1072 -    case 1: return x86_seg_cs;
  5.1073 -    case 2: return x86_seg_ss;
  5.1074 -    case 3: return x86_seg_ds;
  5.1075 -    case 4: return x86_seg_fs;
  5.1076 -    case 5: return x86_seg_gs;
  5.1077 -    default: break;
  5.1078 -    }
  5.1079 -    return decode_segment_failed;
  5.1080 -}
  5.1081 -
  5.1082 -int
  5.1083 -x86_emulate(
  5.1084 -    struct x86_emulate_ctxt *ctxt,
  5.1085 -    struct x86_emulate_ops  *ops)
  5.1086 -{
  5.1087 -    /* Shadow copy of register state. Committed on successful emulation. */
  5.1088 -    struct cpu_user_regs _regs = *ctxt->regs;
  5.1089 -
  5.1090 -    uint8_t b, d, sib, sib_index, sib_base, twobyte = 0, rex_prefix = 0;
  5.1091 -    uint8_t modrm = 0, modrm_mod = 0, modrm_reg = 0, modrm_rm = 0;
  5.1092 -    unsigned int op_bytes, def_op_bytes, ad_bytes, def_ad_bytes;
  5.1093 -#define REPE_PREFIX  1
  5.1094 -#define REPNE_PREFIX 2
  5.1095 -    unsigned int lock_prefix = 0, rep_prefix = 0;
  5.1096 -    int override_seg = -1, rc = X86EMUL_OKAY;
  5.1097 -    struct operand src, dst;
  5.1098 -
  5.1099 -    /* Data operand effective address (usually computed from ModRM). */
  5.1100 -    struct operand ea;
  5.1101 -
  5.1102 -    /* Default is a memory operand relative to segment DS. */
  5.1103 -    ea.type    = OP_MEM;
  5.1104 -    ea.mem.seg = x86_seg_ds;
  5.1105 -    ea.mem.off = 0;
  5.1106 -
  5.1107 -    ctxt->retire.byte = 0;
  5.1108 -
  5.1109 -    op_bytes = def_op_bytes = ad_bytes = def_ad_bytes = ctxt->addr_size/8;
  5.1110 -    if ( op_bytes == 8 )
  5.1111 -    {
  5.1112 -        op_bytes = def_op_bytes = 4;
  5.1113 -#ifndef __x86_64__
  5.1114 -        return X86EMUL_UNHANDLEABLE;
  5.1115 -#endif
  5.1116 -    }
  5.1117 -
  5.1118 -    /* Prefix bytes. */
  5.1119 -    for ( ; ; )
  5.1120 -    {
  5.1121 -        switch ( b = insn_fetch_type(uint8_t) )
  5.1122 -        {
  5.1123 -        case 0x66: /* operand-size override */
  5.1124 -            op_bytes = def_op_bytes ^ 6;
  5.1125 -            break;
  5.1126 -        case 0x67: /* address-size override */
  5.1127 -            ad_bytes = def_ad_bytes ^ (mode_64bit() ? 12 : 6);
  5.1128 -            break;
  5.1129 -        case 0x2e: /* CS override */
  5.1130 -            override_seg = x86_seg_cs;
  5.1131 -            break;
  5.1132 -        case 0x3e: /* DS override */
  5.1133 -            override_seg = x86_seg_ds;
  5.1134 -            break;
  5.1135 -        case 0x26: /* ES override */
  5.1136 -            override_seg = x86_seg_es;
  5.1137 -            break;
  5.1138 -        case 0x64: /* FS override */
  5.1139 -            override_seg = x86_seg_fs;
  5.1140 -            break;
  5.1141 -        case 0x65: /* GS override */
  5.1142 -            override_seg = x86_seg_gs;
  5.1143 -            break;
  5.1144 -        case 0x36: /* SS override */
  5.1145 -            override_seg = x86_seg_ss;
  5.1146 -            break;
  5.1147 -        case 0xf0: /* LOCK */
  5.1148 -            lock_prefix = 1;
  5.1149 -            break;
  5.1150 -        case 0xf2: /* REPNE/REPNZ */
  5.1151 -            rep_prefix = REPNE_PREFIX;
  5.1152 -            break;
  5.1153 -        case 0xf3: /* REP/REPE/REPZ */
  5.1154 -            rep_prefix = REPE_PREFIX;
  5.1155 -            break;
  5.1156 -        case 0x40 ... 0x4f: /* REX */
  5.1157 -            if ( !mode_64bit() )
  5.1158 -                goto done_prefixes;
  5.1159 -            rex_prefix = b;
  5.1160 -            continue;
  5.1161 -        default:
  5.1162 -            goto done_prefixes;
  5.1163 -        }
  5.1164 -
  5.1165 -        /* Any legacy prefix after a REX prefix nullifies its effect. */
  5.1166 -        rex_prefix = 0;
  5.1167 -    }
  5.1168 - done_prefixes:
  5.1169 -
  5.1170 -    if ( rex_prefix & 8 ) /* REX.W */
  5.1171 -        op_bytes = 8;
  5.1172 -
  5.1173 -    /* Opcode byte(s). */
  5.1174 -    d = opcode_table[b];
  5.1175 -    if ( d == 0 )
  5.1176 -    {
  5.1177 -        /* Two-byte opcode? */
  5.1178 -        if ( b == 0x0f )
  5.1179 -        {
  5.1180 -            twobyte = 1;
  5.1181 -            b = insn_fetch_type(uint8_t);
  5.1182 -            d = twobyte_table[b];
  5.1183 -        }
  5.1184 -
  5.1185 -        /* Unrecognised? */
  5.1186 -        if ( d == 0 )
  5.1187 -            goto cannot_emulate;
  5.1188 -    }
  5.1189 -
  5.1190 -    /* Lock prefix is allowed only on RMW instructions. */
  5.1191 -    generate_exception_if((d & Mov) && lock_prefix, EXC_GP, 0);
  5.1192 -
  5.1193 -    /* ModRM and SIB bytes. */
  5.1194 -    if ( d & ModRM )
  5.1195 -    {
  5.1196 -        modrm = insn_fetch_type(uint8_t);
  5.1197 -        modrm_mod = (modrm & 0xc0) >> 6;
  5.1198 -        modrm_reg = ((rex_prefix & 4) << 1) | ((modrm & 0x38) >> 3);
  5.1199 -        modrm_rm  = modrm & 0x07;
  5.1200 -
  5.1201 -        if ( modrm_mod == 3 )
  5.1202 -        {
  5.1203 -            modrm_rm |= (rex_prefix & 1) << 3;
  5.1204 -            ea.type = OP_REG;
  5.1205 -            ea.reg  = decode_register(
  5.1206 -                modrm_rm, &_regs, (d & ByteOp) && (rex_prefix == 0));
  5.1207 -        }
  5.1208 -        else if ( ad_bytes == 2 )
  5.1209 -        {
  5.1210 -            /* 16-bit ModR/M decode. */
  5.1211 -            switch ( modrm_rm )
  5.1212 -            {
  5.1213 -            case 0:
  5.1214 -                ea.mem.off = _regs.ebx + _regs.esi;
  5.1215 -                break;
  5.1216 -            case 1:
  5.1217 -                ea.mem.off = _regs.ebx + _regs.edi;
  5.1218 -                break;
  5.1219 -            case 2:
  5.1220 -                ea.mem.seg = x86_seg_ss;
  5.1221 -                ea.mem.off = _regs.ebp + _regs.esi;
  5.1222 -                break;
  5.1223 -            case 3:
  5.1224 -                ea.mem.seg = x86_seg_ss;
  5.1225 -                ea.mem.off = _regs.ebp + _regs.edi;
  5.1226 -                break;
  5.1227 -            case 4:
  5.1228 -                ea.mem.off = _regs.esi;
  5.1229 -                break;
  5.1230 -            case 5:
  5.1231 -                ea.mem.off = _regs.edi;
  5.1232 -                break;
  5.1233 -            case 6:
  5.1234 -                if ( modrm_mod == 0 )
  5.1235 -                    break;
  5.1236 -                ea.mem.seg = x86_seg_ss;
  5.1237 -                ea.mem.off = _regs.ebp;
  5.1238 -                break;
  5.1239 -            case 7:
  5.1240 -                ea.mem.off = _regs.ebx;
  5.1241 -                break;
  5.1242 -            }
  5.1243 -            switch ( modrm_mod )
  5.1244 -            {
  5.1245 -            case 0:
  5.1246 -                if ( modrm_rm == 6 )
  5.1247 -                    ea.mem.off = insn_fetch_type(int16_t);
  5.1248 -                break;
  5.1249 -            case 1:
  5.1250 -                ea.mem.off += insn_fetch_type(int8_t);
  5.1251 -                break;
  5.1252 -            case 2:
  5.1253 -                ea.mem.off += insn_fetch_type(int16_t);
  5.1254 -                break;
  5.1255 -            }
  5.1256 -            ea.mem.off = truncate_ea(ea.mem.off);
  5.1257 -        }
  5.1258 -        else
  5.1259 -        {
  5.1260 -            /* 32/64-bit ModR/M decode. */
  5.1261 -            if ( modrm_rm == 4 )
  5.1262 -            {
  5.1263 -                sib = insn_fetch_type(uint8_t);
  5.1264 -                sib_index = ((sib >> 3) & 7) | ((rex_prefix << 2) & 8);
  5.1265 -                sib_base  = (sib & 7) | ((rex_prefix << 3) & 8);
  5.1266 -                if ( sib_index != 4 )
  5.1267 -                    ea.mem.off = *(long*)decode_register(sib_index, &_regs, 0);
  5.1268 -                ea.mem.off <<= (sib >> 6) & 3;
  5.1269 -                if ( (modrm_mod == 0) && ((sib_base & 7) == 5) )
  5.1270 -                    ea.mem.off += insn_fetch_type(int32_t);
  5.1271 -                else if ( sib_base == 4 )
  5.1272 -                {
  5.1273 -                    ea.mem.seg  = x86_seg_ss;
  5.1274 -                    ea.mem.off += _regs.esp;
  5.1275 -                    if ( !twobyte && (b == 0x8f) )
  5.1276 -                        /* POP <rm> computes its EA post increment. */
  5.1277 -                        ea.mem.off += ((mode_64bit() && (op_bytes == 4))
  5.1278 -                                       ? 8 : op_bytes);
  5.1279 -                }
  5.1280 -                else if ( sib_base == 5 )
  5.1281 -                {
  5.1282 -                    ea.mem.seg  = x86_seg_ss;
  5.1283 -                    ea.mem.off += _regs.ebp;
  5.1284 -                }
  5.1285 -                else
  5.1286 -                    ea.mem.off += *(long*)decode_register(sib_base, &_regs, 0);
  5.1287 -            }
  5.1288 -            else
  5.1289 -            {
  5.1290 -                modrm_rm |= (rex_prefix & 1) << 3;
  5.1291 -                ea.mem.off = *(long *)decode_register(modrm_rm, &_regs, 0);
  5.1292 -                if ( (modrm_rm == 5) && (modrm_mod != 0) )
  5.1293 -                    ea.mem.seg = x86_seg_ss;
  5.1294 -            }
  5.1295 -            switch ( modrm_mod )
  5.1296 -            {
  5.1297 -            case 0:
  5.1298 -                if ( (modrm_rm & 7) != 5 )
  5.1299 -                    break;
  5.1300 -                ea.mem.off = insn_fetch_type(int32_t);
  5.1301 -                if ( !mode_64bit() )
  5.1302 -                    break;
  5.1303 -                /* Relative to RIP of next instruction. Argh! */
  5.1304 -                ea.mem.off += _regs.eip;
  5.1305 -                if ( (d & SrcMask) == SrcImm )
  5.1306 -                    ea.mem.off += (d & ByteOp) ? 1 :
  5.1307 -                        ((op_bytes == 8) ? 4 : op_bytes);
  5.1308 -                else if ( (d & SrcMask) == SrcImmByte )
  5.1309 -                    ea.mem.off += 1;
  5.1310 -                else if ( !twobyte && ((b & 0xfe) == 0xf6) &&
  5.1311 -                          ((modrm_reg & 7) <= 1) )
  5.1312 -                    /* Special case in Grp3: test has immediate operand. */
  5.1313 -                    ea.mem.off += (d & ByteOp) ? 1
  5.1314 -                        : ((op_bytes == 8) ? 4 : op_bytes);
  5.1315 -                else if ( twobyte && ((b & 0xf7) == 0xa4) )
  5.1316 -                    /* SHLD/SHRD with immediate byte third operand. */
  5.1317 -                    ea.mem.off++;
  5.1318 -                break;
  5.1319 -            case 1:
  5.1320 -                ea.mem.off += insn_fetch_type(int8_t);
  5.1321 -                break;
  5.1322 -            case 2:
  5.1323 -                ea.mem.off += insn_fetch_type(int32_t);
  5.1324 -                break;
  5.1325 -            }
  5.1326 -            ea.mem.off = truncate_ea(ea.mem.off);
  5.1327 -        }
  5.1328 -    }
  5.1329 -
  5.1330 -    if ( override_seg != -1 )
  5.1331 -        ea.mem.seg = override_seg;
  5.1332 -
  5.1333 -    /* Special instructions do their own operand decoding. */
  5.1334 -    if ( (d & DstMask) == ImplicitOps )
  5.1335 -        goto special_insn;
  5.1336 -
  5.1337 -    /* Decode and fetch the source operand: register, memory or immediate. */
  5.1338 -    switch ( d & SrcMask )
  5.1339 -    {
  5.1340 -    case SrcNone:
  5.1341 -        break;
  5.1342 -    case SrcReg:
  5.1343 -        src.type = OP_REG;
  5.1344 -        if ( d & ByteOp )
  5.1345 -        {
  5.1346 -            src.reg = decode_register(modrm_reg, &_regs, (rex_prefix == 0));
  5.1347 -            src.val = *(uint8_t *)src.reg;
  5.1348 -            src.bytes = 1;
  5.1349 -        }
  5.1350 -        else
  5.1351 -        {
  5.1352 -            src.reg = decode_register(modrm_reg, &_regs, 0);
  5.1353 -            switch ( (src.bytes = op_bytes) )
  5.1354 -            {
  5.1355 -            case 2: src.val = *(uint16_t *)src.reg; break;
  5.1356 -            case 4: src.val = *(uint32_t *)src.reg; break;
  5.1357 -            case 8: src.val = *(uint64_t *)src.reg; break;
  5.1358 -            }
  5.1359 -        }
  5.1360 -        break;
  5.1361 -    case SrcMem16:
  5.1362 -        ea.bytes = 2;
  5.1363 -        goto srcmem_common;
  5.1364 -    case SrcMem:
  5.1365 -        ea.bytes = (d & ByteOp) ? 1 : op_bytes;
  5.1366 -    srcmem_common:
  5.1367 -        src = ea;
  5.1368 -        if ( src.type == OP_REG )
  5.1369 -        {
  5.1370 -            switch ( src.bytes )
  5.1371 -            {
  5.1372 -            case 1: src.val = *(uint8_t  *)src.reg; break;
  5.1373 -            case 2: src.val = *(uint16_t *)src.reg; break;
  5.1374 -            case 4: src.val = *(uint32_t *)src.reg; break;
  5.1375 -            case 8: src.val = *(uint64_t *)src.reg; break;
  5.1376 -            }
  5.1377 -        }
  5.1378 -        else if ( (rc = ops->read(src.mem.seg, src.mem.off,
  5.1379 -                                  &src.val, src.bytes, ctxt)) )
  5.1380 -            goto done;
  5.1381 -        break;
  5.1382 -    case SrcImm:
  5.1383 -        src.type  = OP_IMM;
  5.1384 -        src.bytes = (d & ByteOp) ? 1 : op_bytes;
  5.1385 -        if ( src.bytes == 8 ) src.bytes = 4;
  5.1386 -        /* NB. Immediates are sign-extended as necessary. */
  5.1387 -        switch ( src.bytes )
  5.1388 -        {
  5.1389 -        case 1: src.val = insn_fetch_type(int8_t);  break;
  5.1390 -        case 2: src.val = insn_fetch_type(int16_t); break;
  5.1391 -        case 4: src.val = insn_fetch_type(int32_t); break;
  5.1392 -        }
  5.1393 -        break;
  5.1394 -    case SrcImmByte:
  5.1395 -        src.type  = OP_IMM;
  5.1396 -        src.bytes = 1;
  5.1397 -        src.val   = insn_fetch_type(int8_t);
  5.1398 -        break;
  5.1399 -    }
  5.1400 -
  5.1401 -    /* Decode and fetch the destination operand: register or memory. */
  5.1402 -    switch ( d & DstMask )
  5.1403 -    {
  5.1404 -    case DstReg:
  5.1405 -        dst.type = OP_REG;
  5.1406 -        if ( d & ByteOp )
  5.1407 -        {
  5.1408 -            dst.reg = decode_register(modrm_reg, &_regs, (rex_prefix == 0));
  5.1409 -            dst.val = *(uint8_t *)dst.reg;
  5.1410 -            dst.bytes = 1;
  5.1411 -        }
  5.1412 -        else
  5.1413 -        {
  5.1414 -            dst.reg = decode_register(modrm_reg, &_regs, 0);
  5.1415 -            switch ( (dst.bytes = op_bytes) )
  5.1416 -            {
  5.1417 -            case 2: dst.val = *(uint16_t *)dst.reg; break;
  5.1418 -            case 4: dst.val = *(uint32_t *)dst.reg; break;
  5.1419 -            case 8: dst.val = *(uint64_t *)dst.reg; break;
  5.1420 -            }
  5.1421 -        }
  5.1422 -        break;
  5.1423 -    case DstBitBase:
  5.1424 -        if ( ((d & SrcMask) == SrcImmByte) || (ea.type == OP_REG) )
  5.1425 -        {
  5.1426 -            src.val &= (op_bytes << 3) - 1;
  5.1427 -        }
  5.1428 -        else
  5.1429 -        {
  5.1430 -            /*
  5.1431 -             * EA       += BitOffset DIV op_bytes*8
  5.1432 -             * BitOffset = BitOffset MOD op_bytes*8
  5.1433 -             * DIV truncates towards negative infinity.
  5.1434 -             * MOD always produces a positive result.
  5.1435 -             */
  5.1436 -            if ( op_bytes == 2 )
  5.1437 -                src.val = (int16_t)src.val;
  5.1438 -            else if ( op_bytes == 4 )
  5.1439 -                src.val = (int32_t)src.val;
  5.1440 -            if ( (long)src.val < 0 )
  5.1441 -            {
  5.1442 -                unsigned long byte_offset;
  5.1443 -                byte_offset = op_bytes + (((-src.val-1) >> 3) & ~(op_bytes-1));
  5.1444 -                ea.mem.off -= byte_offset;
  5.1445 -                src.val = (byte_offset << 3) + src.val;
  5.1446 -            }
  5.1447 -            else
  5.1448 -            {
  5.1449 -                ea.mem.off += (src.val >> 3) & ~(op_bytes - 1);
  5.1450 -                src.val &= (op_bytes << 3) - 1;
  5.1451 -            }
  5.1452 -        }
  5.1453 -        /* Becomes a normal DstMem operation from here on. */
  5.1454 -        d = (d & ~DstMask) | DstMem;
  5.1455 -    case DstMem:
  5.1456 -        ea.bytes = (d & ByteOp) ? 1 : op_bytes;
  5.1457 -        dst = ea;
  5.1458 -        if ( dst.type == OP_REG )
  5.1459 -        {
  5.1460 -            switch ( dst.bytes )
  5.1461 -            {
  5.1462 -            case 1: dst.val = *(uint8_t  *)dst.reg; break;
  5.1463 -            case 2: dst.val = *(uint16_t *)dst.reg; break;
  5.1464 -            case 4: dst.val = *(uint32_t *)dst.reg; break;
  5.1465 -            case 8: dst.val = *(uint64_t *)dst.reg; break;
  5.1466 -            }
  5.1467 -        }
  5.1468 -        else if ( !(d & Mov) ) /* optimisation - avoid slow emulated read */
  5.1469 -        {
  5.1470 -            if ( (rc = ops->read(dst.mem.seg, dst.mem.off,
  5.1471 -                                 &dst.val, dst.bytes, ctxt)) )
  5.1472 -                goto done;
  5.1473 -            dst.orig_val = dst.val;
  5.1474 -        }
  5.1475 -        break;
  5.1476 -    }
  5.1477 -
  5.1478 -    /* LOCK prefix allowed only on instructions with memory destination. */
  5.1479 -    generate_exception_if(lock_prefix && (dst.type != OP_MEM), EXC_GP, 0);
  5.1480 -
  5.1481 -    if ( twobyte )
  5.1482 -        goto twobyte_insn;
  5.1483 -
  5.1484 -    switch ( b )
  5.1485 -    {
  5.1486 -    case 0x04 ... 0x05: /* add imm,%%eax */
  5.1487 -        dst.reg = (unsigned long *)&_regs.eax;
  5.1488 -        dst.val = _regs.eax;
  5.1489 -    case 0x00 ... 0x03: add: /* add */
  5.1490 -        emulate_2op_SrcV("add", src, dst, _regs.eflags);
  5.1491 -        break;
  5.1492 -
  5.1493 -    case 0x0c ... 0x0d: /* or imm,%%eax */
  5.1494 -        dst.reg = (unsigned long *)&_regs.eax;
  5.1495 -        dst.val = _regs.eax;
  5.1496 -    case 0x08 ... 0x0b: or:  /* or */
  5.1497 -        emulate_2op_SrcV("or", src, dst, _regs.eflags);
  5.1498 -        break;
  5.1499 -
  5.1500 -    case 0x14 ... 0x15: /* adc imm,%%eax */
  5.1501 -        dst.reg = (unsigned long *)&_regs.eax;
  5.1502 -        dst.val = _regs.eax;
  5.1503 -    case 0x10 ... 0x13: adc: /* adc */
  5.1504 -        emulate_2op_SrcV("adc", src, dst, _regs.eflags);
  5.1505 -        break;
  5.1506 -
  5.1507 -    case 0x1c ... 0x1d: /* sbb imm,%%eax */
  5.1508 -        dst.reg = (unsigned long *)&_regs.eax;
  5.1509 -        dst.val = _regs.eax;
  5.1510 -    case 0x18 ... 0x1b: sbb: /* sbb */
  5.1511 -        emulate_2op_SrcV("sbb", src, dst, _regs.eflags);
  5.1512 -        break;
  5.1513 -
  5.1514 -    case 0x24 ... 0x25: /* and imm,%%eax */
  5.1515 -        dst.reg = (unsigned long *)&_regs.eax;
  5.1516 -        dst.val = _regs.eax;
  5.1517 -    case 0x20 ... 0x23: and: /* and */
  5.1518 -        emulate_2op_SrcV("and", src, dst, _regs.eflags);
  5.1519 -        break;
  5.1520 -
  5.1521 -    case 0x2c ... 0x2d: /* sub imm,%%eax */
  5.1522 -        dst.reg = (unsigned long *)&_regs.eax;
  5.1523 -        dst.val = _regs.eax;
  5.1524 -    case 0x28 ... 0x2b: sub: /* sub */
  5.1525 -        emulate_2op_SrcV("sub", src, dst, _regs.eflags);
  5.1526 -        break;
  5.1527 -
  5.1528 -    case 0x34 ... 0x35: /* xor imm,%%eax */
  5.1529 -        dst.reg = (unsigned long *)&_regs.eax;
  5.1530 -        dst.val = _regs.eax;
  5.1531 -    case 0x30 ... 0x33: xor: /* xor */
  5.1532 -        emulate_2op_SrcV("xor", src, dst, _regs.eflags);
  5.1533 -        break;
  5.1534 -
  5.1535 -    case 0x3c ... 0x3d: /* cmp imm,%%eax */
  5.1536 -        dst.reg = (unsigned long *)&_regs.eax;
  5.1537 -        dst.val = _regs.eax;
  5.1538 -    case 0x38 ... 0x3b: cmp: /* cmp */
  5.1539 -        emulate_2op_SrcV("cmp", src, dst, _regs.eflags);
  5.1540 -        break;
  5.1541 -
  5.1542 -    case 0x62: /* bound */ {
  5.1543 -        unsigned long src_val2;
  5.1544 -        int lb, ub, idx;
  5.1545 -        generate_exception_if(mode_64bit() || (src.type != OP_MEM),
  5.1546 -                              EXC_UD, -1);
  5.1547 -        if ( (rc = ops->read(src.mem.seg, src.mem.off + op_bytes,
  5.1548 -                             &src_val2, op_bytes, ctxt)) )
  5.1549 -            goto done;
  5.1550 -        ub  = (op_bytes == 2) ? (int16_t)src_val2 : (int32_t)src_val2;
  5.1551 -        lb  = (op_bytes == 2) ? (int16_t)src.val  : (int32_t)src.val;
  5.1552 -        idx = (op_bytes == 2) ? (int16_t)dst.val  : (int32_t)dst.val;
  5.1553 -        generate_exception_if((idx < lb) || (idx > ub), EXC_BR, -1);
  5.1554 -        dst.type = OP_NONE;
  5.1555 -        break;
  5.1556 -    }
  5.1557 -
  5.1558 -    case 0x63: /* movsxd (x86/64) / arpl (x86/32) */
  5.1559 -        if ( mode_64bit() )
  5.1560 -        {
  5.1561 -            /* movsxd */
  5.1562 -            if ( src.type == OP_REG )
  5.1563 -                src.val = *(int32_t *)src.reg;
  5.1564 -            else if ( (rc = ops->read(src.mem.seg, src.mem.off,
  5.1565 -                                      &src.val, 4, ctxt)) )
  5.1566 -                goto done;
  5.1567 -            dst.val = (int32_t)src.val;
  5.1568 -        }
  5.1569 -        else
  5.1570 -        {
  5.1571 -            /* arpl */
  5.1572 -            uint16_t src_val = dst.val;
  5.1573 -            dst = src;
  5.1574 -            _regs.eflags &= ~EFLG_ZF;
  5.1575 -            _regs.eflags |= ((src_val & 3) > (dst.val & 3)) ? EFLG_ZF : 0;
  5.1576 -            if ( _regs.eflags & EFLG_ZF )
  5.1577 -                dst.val  = (dst.val & ~3) | (src_val & 3);
  5.1578 -            else
  5.1579 -                dst.type = OP_NONE;
  5.1580 -            generate_exception_if(in_realmode(ctxt, ops), EXC_UD, -1);
  5.1581 -        }
  5.1582 -        break;
  5.1583 -
  5.1584 -    case 0x69: /* imul imm16/32 */
  5.1585 -    case 0x6b: /* imul imm8 */ {
  5.1586 -        unsigned long src1; /* ModR/M source operand */
  5.1587 -        if ( ea.type == OP_REG )
  5.1588 -            src1 = *ea.reg;
  5.1589 -        else if ( (rc = ops->read(ea.mem.seg, ea.mem.off,
  5.1590 -                                  &src1, op_bytes, ctxt)) )
  5.1591 -            goto done;
  5.1592 -        _regs.eflags &= ~(EFLG_OF|EFLG_CF);
  5.1593 -        switch ( dst.bytes )
  5.1594 -        {
  5.1595 -        case 2:
  5.1596 -            dst.val = ((uint32_t)(int16_t)src.val *
  5.1597 -                       (uint32_t)(int16_t)src1);
  5.1598 -            if ( (int16_t)dst.val != (uint32_t)dst.val )
  5.1599 -                _regs.eflags |= EFLG_OF|EFLG_CF;
  5.1600 -            break;
  5.1601 -#ifdef __x86_64__
  5.1602 -        case 4:
  5.1603 -            dst.val = ((uint64_t)(int32_t)src.val *
  5.1604 -                       (uint64_t)(int32_t)src1);
  5.1605 -            if ( (int32_t)dst.val != dst.val )
  5.1606 -                _regs.eflags |= EFLG_OF|EFLG_CF;
  5.1607 -            break;
  5.1608 -#endif
  5.1609 -        default: {
  5.1610 -            unsigned long m[2] = { src.val, src1 };
  5.1611 -            if ( imul_dbl(m) )
  5.1612 -                _regs.eflags |= EFLG_OF|EFLG_CF;
  5.1613 -            dst.val = m[0];
  5.1614 -            break;
  5.1615 -        }
  5.1616 -        }
  5.1617 -        break;
  5.1618 -    }
  5.1619 -
  5.1620 -    case 0x82: /* Grp1 (x86/32 only) */
  5.1621 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.1622 -    case 0x80: case 0x81: case 0x83: /* Grp1 */
  5.1623 -        switch ( modrm_reg & 7 )
  5.1624 -        {
  5.1625 -        case 0: goto add;
  5.1626 -        case 1: goto or;
  5.1627 -        case 2: goto adc;
  5.1628 -        case 3: goto sbb;
  5.1629 -        case 4: goto and;
  5.1630 -        case 5: goto sub;
  5.1631 -        case 6: goto xor;
  5.1632 -        case 7: goto cmp;
  5.1633 -        }
  5.1634 -        break;
  5.1635 -
  5.1636 -    case 0xa8 ... 0xa9: /* test imm,%%eax */
  5.1637 -        dst.reg = (unsigned long *)&_regs.eax;
  5.1638 -        dst.val = _regs.eax;
  5.1639 -    case 0x84 ... 0x85: test: /* test */
  5.1640 -        emulate_2op_SrcV("test", src, dst, _regs.eflags);
  5.1641 -        break;
  5.1642 -
  5.1643 -    case 0x86 ... 0x87: xchg: /* xchg */
  5.1644 -        /* Write back the register source. */
  5.1645 -        switch ( dst.bytes )
  5.1646 -        {
  5.1647 -        case 1: *(uint8_t  *)src.reg = (uint8_t)dst.val; break;
  5.1648 -        case 2: *(uint16_t *)src.reg = (uint16_t)dst.val; break;
  5.1649 -        case 4: *src.reg = (uint32_t)dst.val; break; /* 64b reg: zero-extend */
  5.1650 -        case 8: *src.reg = dst.val; break;
  5.1651 -        }
  5.1652 -        /* Write back the memory destination with implicit LOCK prefix. */
  5.1653 -        dst.val = src.val;
  5.1654 -        lock_prefix = 1;
  5.1655 -        break;
  5.1656 -
  5.1657 -    case 0xc6 ... 0xc7: /* mov (sole member of Grp11) */
  5.1658 -        generate_exception_if((modrm_reg & 7) != 0, EXC_UD, -1);
  5.1659 -    case 0x88 ... 0x8b: /* mov */
  5.1660 -        dst.val = src.val;
  5.1661 -        break;
  5.1662 -
  5.1663 -    case 0x8c: /* mov Sreg,r/m */ {
  5.1664 -        struct segment_register reg;
  5.1665 -        enum x86_segment seg = decode_segment(modrm_reg);
  5.1666 -        generate_exception_if(seg == decode_segment_failed, EXC_UD, -1);
  5.1667 -        fail_if(ops->read_segment == NULL);
  5.1668 -        if ( (rc = ops->read_segment(seg, &reg, ctxt)) != 0 )
  5.1669 -            goto done;
  5.1670 -        dst.val = reg.sel;
  5.1671 -        if ( dst.type == OP_MEM )
  5.1672 -            dst.bytes = 2;
  5.1673 -        break;
  5.1674 -    }
  5.1675 -
  5.1676 -    case 0x8e: /* mov r/m,Sreg */ {
  5.1677 -        enum x86_segment seg = decode_segment(modrm_reg);
  5.1678 -        generate_exception_if(seg == decode_segment_failed, EXC_UD, -1);
  5.1679 -        if ( (rc = load_seg(seg, (uint16_t)src.val, ctxt, ops)) != 0 )
  5.1680 -            goto done;
  5.1681 -        if ( seg == x86_seg_ss )
  5.1682 -            ctxt->retire.flags.mov_ss = 1;
  5.1683 -        dst.type = OP_NONE;
  5.1684 -        break;
  5.1685 -    }
  5.1686 -
  5.1687 -    case 0x8d: /* lea */
  5.1688 -        dst.val = ea.mem.off;
  5.1689 -        break;
  5.1690 -
  5.1691 -    case 0x8f: /* pop (sole member of Grp1a) */
  5.1692 -        generate_exception_if((modrm_reg & 7) != 0, EXC_UD, -1);
  5.1693 -        /* 64-bit mode: POP defaults to a 64-bit operand. */
  5.1694 -        if ( mode_64bit() && (dst.bytes == 4) )
  5.1695 -            dst.bytes = 8;
  5.1696 -        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(dst.bytes),
  5.1697 -                             &dst.val, dst.bytes, ctxt)) != 0 )
  5.1698 -            goto done;
  5.1699 -        break;
  5.1700 -
  5.1701 -    case 0xb0 ... 0xb7: /* mov imm8,r8 */
  5.1702 -        dst.reg = decode_register(
  5.1703 -            (b & 7) | ((rex_prefix & 1) << 3), &_regs, (rex_prefix == 0));
  5.1704 -        dst.val = src.val;
  5.1705 -        break;
  5.1706 -
  5.1707 -    case 0xb8 ... 0xbf: /* mov imm{16,32,64},r{16,32,64} */
  5.1708 -        if ( dst.bytes == 8 ) /* Fetch more bytes to obtain imm64 */
  5.1709 -            src.val = ((uint32_t)src.val |
  5.1710 -                       ((uint64_t)insn_fetch_type(uint32_t) << 32));
  5.1711 -        dst.reg = decode_register(
  5.1712 -            (b & 7) | ((rex_prefix & 1) << 3), &_regs, 0);
  5.1713 -        dst.val = src.val;
  5.1714 -        break;
  5.1715 -
  5.1716 -    case 0xc0 ... 0xc1: grp2: /* Grp2 */
  5.1717 -        switch ( modrm_reg & 7 )
  5.1718 -        {
  5.1719 -        case 0: /* rol */
  5.1720 -            emulate_2op_SrcB("rol", src, dst, _regs.eflags);
  5.1721 -            break;
  5.1722 -        case 1: /* ror */
  5.1723 -            emulate_2op_SrcB("ror", src, dst, _regs.eflags);
  5.1724 -            break;
  5.1725 -        case 2: /* rcl */
  5.1726 -            emulate_2op_SrcB("rcl", src, dst, _regs.eflags);
  5.1727 -            break;
  5.1728 -        case 3: /* rcr */
  5.1729 -            emulate_2op_SrcB("rcr", src, dst, _regs.eflags);
  5.1730 -            break;
  5.1731 -        case 4: /* sal/shl */
  5.1732 -        case 6: /* sal/shl */
  5.1733 -            emulate_2op_SrcB("sal", src, dst, _regs.eflags);
  5.1734 -            break;
  5.1735 -        case 5: /* shr */
  5.1736 -            emulate_2op_SrcB("shr", src, dst, _regs.eflags);
  5.1737 -            break;
  5.1738 -        case 7: /* sar */
  5.1739 -            emulate_2op_SrcB("sar", src, dst, _regs.eflags);
  5.1740 -            break;
  5.1741 -        }
  5.1742 -        break;
  5.1743 -
  5.1744 -    case 0xc4: /* les */ {
  5.1745 -        unsigned long sel;
  5.1746 -        dst.val = x86_seg_es;
  5.1747 -    les: /* dst.val identifies the segment */
  5.1748 -        generate_exception_if(src.type != OP_MEM, EXC_UD, -1);
  5.1749 -        if ( (rc = ops->read(src.mem.seg, src.mem.off + src.bytes,
  5.1750 -                             &sel, 2, ctxt)) != 0 )
  5.1751 -            goto done;
  5.1752 -        if ( (rc = load_seg(dst.val, (uint16_t)sel, ctxt, ops)) != 0 )
  5.1753 -            goto done;
  5.1754 -        dst.val = src.val;
  5.1755 -        break;
  5.1756 -    }
  5.1757 -
  5.1758 -    case 0xc5: /* lds */
  5.1759 -        dst.val = x86_seg_ds;
  5.1760 -        goto les;
  5.1761 -
  5.1762 -    case 0xd0 ... 0xd1: /* Grp2 */
  5.1763 -        src.val = 1;
  5.1764 -        goto grp2;
  5.1765 -
  5.1766 -    case 0xd2 ... 0xd3: /* Grp2 */
  5.1767 -        src.val = _regs.ecx;
  5.1768 -        goto grp2;
  5.1769 -
  5.1770 -    case 0xf6 ... 0xf7: /* Grp3 */
  5.1771 -        switch ( modrm_reg & 7 )
  5.1772 -        {
  5.1773 -        case 0 ... 1: /* test */
  5.1774 -            /* Special case in Grp3: test has an immediate source operand. */
  5.1775 -            src.type = OP_IMM;
  5.1776 -            src.bytes = (d & ByteOp) ? 1 : op_bytes;
  5.1777 -            if ( src.bytes == 8 ) src.bytes = 4;
  5.1778 -            switch ( src.bytes )
  5.1779 -            {
  5.1780 -            case 1: src.val = insn_fetch_type(int8_t);  break;
  5.1781 -            case 2: src.val = insn_fetch_type(int16_t); break;
  5.1782 -            case 4: src.val = insn_fetch_type(int32_t); break;
  5.1783 -            }
  5.1784 -            goto test;
  5.1785 -        case 2: /* not */
  5.1786 -            dst.val = ~dst.val;
  5.1787 -            break;
  5.1788 -        case 3: /* neg */
  5.1789 -            emulate_1op("neg", dst, _regs.eflags);
  5.1790 -            break;
  5.1791 -        case 4: /* mul */
  5.1792 -            src = dst;
  5.1793 -            dst.type = OP_REG;
  5.1794 -            dst.reg  = (unsigned long *)&_regs.eax;
  5.1795 -            dst.val  = *dst.reg;
  5.1796 -            _regs.eflags &= ~(EFLG_OF|EFLG_CF);
  5.1797 -            switch ( src.bytes )
  5.1798 -            {
  5.1799 -            case 1:
  5.1800 -                dst.val = (uint8_t)dst.val;
  5.1801 -                dst.val *= src.val;
  5.1802 -                if ( (uint8_t)dst.val != (uint16_t)dst.val )
  5.1803 -                    _regs.eflags |= EFLG_OF|EFLG_CF;
  5.1804 -                dst.bytes = 2;
  5.1805 -                break;
  5.1806 -            case 2:
  5.1807 -                dst.val = (uint16_t)dst.val;
  5.1808 -                dst.val *= src.val;
  5.1809 -                if ( (uint16_t)dst.val != (uint32_t)dst.val )
  5.1810 -                    _regs.eflags |= EFLG_OF|EFLG_CF;
  5.1811 -                *(uint16_t *)&_regs.edx = dst.val >> 16;
  5.1812 -                break;
  5.1813 -#ifdef __x86_64__
  5.1814 -            case 4:
  5.1815 -                dst.val = (uint32_t)dst.val;
  5.1816 -                dst.val *= src.val;
  5.1817 -                if ( (uint32_t)dst.val != dst.val )
  5.1818 -                    _regs.eflags |= EFLG_OF|EFLG_CF;
  5.1819 -                _regs.edx = (uint32_t)(dst.val >> 32);
  5.1820 -                break;
  5.1821 -#endif
  5.1822 -            default: {
  5.1823 -                unsigned long m[2] = { src.val, dst.val };
  5.1824 -                if ( mul_dbl(m) )
  5.1825 -                    _regs.eflags |= EFLG_OF|EFLG_CF;
  5.1826 -                _regs.edx = m[1];
  5.1827 -                dst.val  = m[0];
  5.1828 -                break;
  5.1829 -            }
  5.1830 -            }
  5.1831 -            break;
  5.1832 -        case 5: /* imul */
  5.1833 -            src = dst;
  5.1834 -            dst.type = OP_REG;
  5.1835 -            dst.reg  = (unsigned long *)&_regs.eax;
  5.1836 -            dst.val  = *dst.reg;
  5.1837 -            _regs.eflags &= ~(EFLG_OF|EFLG_CF);
  5.1838 -            switch ( src.bytes )
  5.1839 -            {
  5.1840 -            case 1:
  5.1841 -                dst.val = ((uint16_t)(int8_t)src.val *
  5.1842 -                           (uint16_t)(int8_t)dst.val);
  5.1843 -                if ( (int8_t)dst.val != (uint16_t)dst.val )
  5.1844 -                    _regs.eflags |= EFLG_OF|EFLG_CF;
  5.1845 -                dst.bytes = 2;
  5.1846 -                break;
  5.1847 -            case 2:
  5.1848 -                dst.val = ((uint32_t)(int16_t)src.val *
  5.1849 -                           (uint32_t)(int16_t)dst.val);
  5.1850 -                if ( (int16_t)dst.val != (uint32_t)dst.val )
  5.1851 -                    _regs.eflags |= EFLG_OF|EFLG_CF;
  5.1852 -                *(uint16_t *)&_regs.edx = dst.val >> 16;
  5.1853 -                break;
  5.1854 -#ifdef __x86_64__
  5.1855 -            case 4:
  5.1856 -                dst.val = ((uint64_t)(int32_t)src.val *
  5.1857 -                           (uint64_t)(int32_t)dst.val);
  5.1858 -                if ( (int32_t)dst.val != dst.val )
  5.1859 -                    _regs.eflags |= EFLG_OF|EFLG_CF;
  5.1860 -                _regs.edx = (uint32_t)(dst.val >> 32);
  5.1861 -                break;
  5.1862 -#endif
  5.1863 -            default: {
  5.1864 -                unsigned long m[2] = { src.val, dst.val };
  5.1865 -                if ( imul_dbl(m) )
  5.1866 -                    _regs.eflags |= EFLG_OF|EFLG_CF;
  5.1867 -                _regs.edx = m[1];
  5.1868 -                dst.val  = m[0];
  5.1869 -                break;
  5.1870 -            }
  5.1871 -            }
  5.1872 -            break;
  5.1873 -        case 6: /* div */ {
  5.1874 -            unsigned long u[2], v;
  5.1875 -            src = dst;
  5.1876 -            dst.type = OP_REG;
  5.1877 -            dst.reg  = (unsigned long *)&_regs.eax;
  5.1878 -            switch ( src.bytes )
  5.1879 -            {
  5.1880 -            case 1:
  5.1881 -                u[0] = (uint16_t)_regs.eax;
  5.1882 -                u[1] = 0;
  5.1883 -                v    = (uint8_t)src.val;
  5.1884 -                generate_exception_if(
  5.1885 -                    div_dbl(u, v) || ((uint8_t)u[0] != (uint16_t)u[0]),
  5.1886 -                    EXC_DE, -1);
  5.1887 -                dst.val = (uint8_t)u[0];
  5.1888 -                ((uint8_t *)&_regs.eax)[1] = u[1];
  5.1889 -                break;
  5.1890 -            case 2:
  5.1891 -                u[0] = ((uint32_t)_regs.edx << 16) | (uint16_t)_regs.eax;
  5.1892 -                u[1] = 0;
  5.1893 -                v    = (uint16_t)src.val;
  5.1894 -                generate_exception_if(
  5.1895 -                    div_dbl(u, v) || ((uint16_t)u[0] != (uint32_t)u[0]),
  5.1896 -                    EXC_DE, -1);
  5.1897 -                dst.val = (uint16_t)u[0];
  5.1898 -                *(uint16_t *)&_regs.edx = u[1];
  5.1899 -                break;
  5.1900 -#ifdef __x86_64__
  5.1901 -            case 4:
  5.1902 -                u[0] = (_regs.edx << 32) | (uint32_t)_regs.eax;
  5.1903 -                u[1] = 0;
  5.1904 -                v    = (uint32_t)src.val;
  5.1905 -                generate_exception_if(
  5.1906 -                    div_dbl(u, v) || ((uint32_t)u[0] != u[0]),
  5.1907 -                    EXC_DE, -1);
  5.1908 -                dst.val   = (uint32_t)u[0];
  5.1909 -                _regs.edx = (uint32_t)u[1];
  5.1910 -                break;
  5.1911 -#endif
  5.1912 -            default:
  5.1913 -                u[0] = _regs.eax;
  5.1914 -                u[1] = _regs.edx;
  5.1915 -                v    = src.val;
  5.1916 -                generate_exception_if(div_dbl(u, v), EXC_DE, -1);
  5.1917 -                dst.val   = u[0];
  5.1918 -                _regs.edx = u[1];
  5.1919 -                break;
  5.1920 -            }
  5.1921 -            break;
  5.1922 -        }
  5.1923 -        case 7: /* idiv */ {
  5.1924 -            unsigned long u[2], v;
  5.1925 -            src = dst;
  5.1926 -            dst.type = OP_REG;
  5.1927 -            dst.reg  = (unsigned long *)&_regs.eax;
  5.1928 -            switch ( src.bytes )
  5.1929 -            {
  5.1930 -            case 1:
  5.1931 -                u[0] = (int16_t)_regs.eax;
  5.1932 -                u[1] = ((long)u[0] < 0) ? ~0UL : 0UL;
  5.1933 -                v    = (int8_t)src.val;
  5.1934 -                generate_exception_if(
  5.1935 -                    idiv_dbl(u, v) || ((int8_t)u[0] != (int16_t)u[0]),
  5.1936 -                    EXC_DE, -1);
  5.1937 -                dst.val = (int8_t)u[0];
  5.1938 -                ((int8_t *)&_regs.eax)[1] = u[1];
  5.1939 -                break;
  5.1940 -            case 2:
  5.1941 -                u[0] = (int32_t)((_regs.edx << 16) | (uint16_t)_regs.eax);
  5.1942 -                u[1] = ((long)u[0] < 0) ? ~0UL : 0UL;
  5.1943 -                v    = (int16_t)src.val;
  5.1944 -                generate_exception_if(
  5.1945 -                    idiv_dbl(u, v) || ((int16_t)u[0] != (int32_t)u[0]),
  5.1946 -                    EXC_DE, -1);
  5.1947 -                dst.val = (int16_t)u[0];
  5.1948 -                *(int16_t *)&_regs.edx = u[1];
  5.1949 -                break;
  5.1950 -#ifdef __x86_64__
  5.1951 -            case 4:
  5.1952 -                u[0] = (_regs.edx << 32) | (uint32_t)_regs.eax;
  5.1953 -                u[1] = ((long)u[0] < 0) ? ~0UL : 0UL;
  5.1954 -                v    = (int32_t)src.val;
  5.1955 -                generate_exception_if(
  5.1956 -                    idiv_dbl(u, v) || ((int32_t)u[0] != u[0]),
  5.1957 -                    EXC_DE, -1);
  5.1958 -                dst.val   = (int32_t)u[0];
  5.1959 -                _regs.edx = (uint32_t)u[1];
  5.1960 -                break;
  5.1961 -#endif
  5.1962 -            default:
  5.1963 -                u[0] = _regs.eax;
  5.1964 -                u[1] = _regs.edx;
  5.1965 -                v    = src.val;
  5.1966 -                generate_exception_if(idiv_dbl(u, v), EXC_DE, -1);
  5.1967 -                dst.val   = u[0];
  5.1968 -                _regs.edx = u[1];
  5.1969 -                break;
  5.1970 -            }
  5.1971 -            break;
  5.1972 -        }
  5.1973 -        default:
  5.1974 -            goto cannot_emulate;
  5.1975 -        }
  5.1976 -        break;
  5.1977 -
  5.1978 -    case 0xfe: /* Grp4 */
  5.1979 -        generate_exception_if((modrm_reg & 7) >= 2, EXC_UD, -1);
  5.1980 -    case 0xff: /* Grp5 */
  5.1981 -        switch ( modrm_reg & 7 )
  5.1982 -        {
  5.1983 -        case 0: /* inc */
  5.1984 -            emulate_1op("inc", dst, _regs.eflags);
  5.1985 -            break;
  5.1986 -        case 1: /* dec */
  5.1987 -            emulate_1op("dec", dst, _regs.eflags);
  5.1988 -            break;
  5.1989 -        case 2: /* call (near) */
  5.1990 -        case 4: /* jmp (near) */
  5.1991 -            if ( (dst.bytes != 8) && mode_64bit() )
  5.1992 -            {
  5.1993 -                dst.bytes = op_bytes = 8;
  5.1994 -                if ( dst.type == OP_REG )
  5.1995 -                    dst.val = *dst.reg;
  5.1996 -                else if ( (rc = ops->read(dst.mem.seg, dst.mem.off,
  5.1997 -                                          &dst.val, 8, ctxt)) != 0 )
  5.1998 -                    goto done;
  5.1999 -            }
  5.2000 -            src.val = _regs.eip;
  5.2001 -            _regs.eip = dst.val;
  5.2002 -            if ( (modrm_reg & 7) == 2 )
  5.2003 -                goto push; /* call */
  5.2004 -            dst.type = OP_NONE;
  5.2005 -            break;
  5.2006 -        case 3: /* call (far, absolute indirect) */
  5.2007 -        case 5: /* jmp (far, absolute indirect) */ {
  5.2008 -            unsigned long sel;
  5.2009 -
  5.2010 -            generate_exception_if(dst.type != OP_MEM, EXC_UD, -1);
  5.2011 -
  5.2012 -            if ( (rc = ops->read(dst.mem.seg, dst.mem.off+dst.bytes,
  5.2013 -                                 &sel, 2, ctxt)) )
  5.2014 -                goto done;
  5.2015 -
  5.2016 -            if ( (modrm_reg & 7) == 3 ) /* call */
  5.2017 -            {
  5.2018 -                struct segment_register reg;
  5.2019 -                fail_if(ops->read_segment == NULL);
  5.2020 -                if ( (rc = ops->read_segment(x86_seg_cs, &reg, ctxt)) ||
  5.2021 -                     (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  5.2022 -                                      reg.sel, op_bytes, ctxt)) ||
  5.2023 -                     (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  5.2024 -                                      _regs.eip, op_bytes, ctxt)) )
  5.2025 -                    goto done;
  5.2026 -            }
  5.2027 -
  5.2028 -            if ( (rc = load_seg(x86_seg_cs, sel, ctxt, ops)) != 0 )
  5.2029 -                goto done;
  5.2030 -            _regs.eip = dst.val;
  5.2031 -
  5.2032 -            dst.type = OP_NONE;
  5.2033 -            break;
  5.2034 -        }
  5.2035 -        case 6: /* push */
  5.2036 -            /* 64-bit mode: PUSH defaults to a 64-bit operand. */
  5.2037 -            if ( mode_64bit() && (dst.bytes == 4) )
  5.2038 -            {
  5.2039 -                dst.bytes = 8;
  5.2040 -                if ( dst.type == OP_REG )
  5.2041 -                    dst.val = *dst.reg;
  5.2042 -                else if ( (rc = ops->read(dst.mem.seg, dst.mem.off,
  5.2043 -                                          &dst.val, 8, ctxt)) != 0 )
  5.2044 -                    goto done;
  5.2045 -            }
  5.2046 -            if ( (rc = ops->write(x86_seg_ss, sp_pre_dec(dst.bytes),
  5.2047 -                                  dst.val, dst.bytes, ctxt)) != 0 )
  5.2048 -                goto done;
  5.2049 -            dst.type = OP_NONE;
  5.2050 -            break;
  5.2051 -        case 7:
  5.2052 -            generate_exception_if(1, EXC_UD, -1);
  5.2053 -        default:
  5.2054 -            goto cannot_emulate;
  5.2055 -        }
  5.2056 -        break;
  5.2057 -    }
  5.2058 -
  5.2059 - writeback:
  5.2060 -    switch ( dst.type )
  5.2061 -    {
  5.2062 -    case OP_REG:
  5.2063 -        /* The 4-byte case *is* correct: in 64-bit mode we zero-extend. */
  5.2064 -        switch ( dst.bytes )
  5.2065 -        {
  5.2066 -        case 1: *(uint8_t  *)dst.reg = (uint8_t)dst.val; break;
  5.2067 -        case 2: *(uint16_t *)dst.reg = (uint16_t)dst.val; break;
  5.2068 -        case 4: *dst.reg = (uint32_t)dst.val; break; /* 64b: zero-ext */
  5.2069 -        case 8: *dst.reg = dst.val; break;
  5.2070 -        }
  5.2071 -        break;
  5.2072 -    case OP_MEM:
  5.2073 -        if ( !(d & Mov) && (dst.orig_val == dst.val) &&
  5.2074 -             !ctxt->force_writeback )
  5.2075 -            /* nothing to do */;
  5.2076 -        else if ( lock_prefix )
  5.2077 -            rc = ops->cmpxchg(
  5.2078 -                dst.mem.seg, dst.mem.off, dst.orig_val,
  5.2079 -                dst.val, dst.bytes, ctxt);
  5.2080 -        else
  5.2081 -            rc = ops->write(
  5.2082 -                dst.mem.seg, dst.mem.off, dst.val, dst.bytes, ctxt);
  5.2083 -        if ( rc != 0 )
  5.2084 -            goto done;
  5.2085 -    default:
  5.2086 -        break;
  5.2087 -    }
  5.2088 -
  5.2089 -    /* Commit shadow register state. */
  5.2090 -    _regs.eflags &= ~EFLG_RF;
  5.2091 -    *ctxt->regs = _regs;
  5.2092 -    if ( (_regs.eflags & EFLG_TF) && (rc == X86EMUL_OKAY) &&
  5.2093 -         (ops->inject_hw_exception != NULL) )
  5.2094 -        rc = ops->inject_hw_exception(EXC_DB, -1, ctxt) ? : X86EMUL_EXCEPTION;
  5.2095 -
  5.2096 - done:
  5.2097 -    return rc;
  5.2098 -
  5.2099 - special_insn:
  5.2100 -    dst.type = OP_NONE;
  5.2101 -
  5.2102 -    /*
  5.2103 -     * The only implicit-operands instructions allowed a LOCK prefix are
  5.2104 -     * CMPXCHG{8,16}B, MOV CRn, MOV DRn.
  5.2105 -     */
  5.2106 -    generate_exception_if(lock_prefix &&
  5.2107 -                          ((b < 0x20) || (b > 0x23)) && /* MOV CRn/DRn */
  5.2108 -                          (b != 0xc7),                  /* CMPXCHG{8,16}B */
  5.2109 -                          EXC_GP, 0);
  5.2110 -
  5.2111 -    if ( twobyte )
  5.2112 -        goto twobyte_special_insn;
  5.2113 -
  5.2114 -    switch ( b )
  5.2115 -    {
  5.2116 -    case 0x06: /* push %%es */ {
  5.2117 -        struct segment_register reg;
  5.2118 -        src.val = x86_seg_es;
  5.2119 -    push_seg:
  5.2120 -        fail_if(ops->read_segment == NULL);
  5.2121 -        if ( (rc = ops->read_segment(src.val, &reg, ctxt)) != 0 )
  5.2122 -            return rc;
  5.2123 -        /* 64-bit mode: PUSH defaults to a 64-bit operand. */
  5.2124 -        if ( mode_64bit() && (op_bytes == 4) )
  5.2125 -            op_bytes = 8;
  5.2126 -        if ( (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  5.2127 -                              reg.sel, op_bytes, ctxt)) != 0 )
  5.2128 -            goto done;
  5.2129 -        break;
  5.2130 -    }
  5.2131 -
  5.2132 -    case 0x07: /* pop %%es */
  5.2133 -        src.val = x86_seg_es;
  5.2134 -    pop_seg:
  5.2135 -        fail_if(ops->write_segment == NULL);
  5.2136 -        /* 64-bit mode: POP defaults to a 64-bit operand. */
  5.2137 -        if ( mode_64bit() && (op_bytes == 4) )
  5.2138 -            op_bytes = 8;
  5.2139 -        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  5.2140 -                             &dst.val, op_bytes, ctxt)) != 0 )
  5.2141 -            goto done;
  5.2142 -        if ( (rc = load_seg(src.val, (uint16_t)dst.val, ctxt, ops)) != 0 )
  5.2143 -            return rc;
  5.2144 -        break;
  5.2145 -
  5.2146 -    case 0x0e: /* push %%cs */
  5.2147 -        src.val = x86_seg_cs;
  5.2148 -        goto push_seg;
  5.2149 -
  5.2150 -    case 0x16: /* push %%ss */
  5.2151 -        src.val = x86_seg_ss;
  5.2152 -        goto push_seg;
  5.2153 -
  5.2154 -    case 0x17: /* pop %%ss */
  5.2155 -        src.val = x86_seg_ss;
  5.2156 -        ctxt->retire.flags.mov_ss = 1;
  5.2157 -        goto pop_seg;
  5.2158 -
  5.2159 -    case 0x1e: /* push %%ds */
  5.2160 -        src.val = x86_seg_ds;
  5.2161 -        goto push_seg;
  5.2162 -
  5.2163 -    case 0x1f: /* pop %%ds */
  5.2164 -        src.val = x86_seg_ds;
  5.2165 -        goto pop_seg;
  5.2166 -
  5.2167 -    case 0x27: /* daa */ {
  5.2168 -        uint8_t al = _regs.eax;
  5.2169 -        unsigned long eflags = _regs.eflags;
  5.2170 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.2171 -        _regs.eflags &= ~(EFLG_CF|EFLG_AF);
  5.2172 -        if ( ((al & 0x0f) > 9) || (eflags & EFLG_AF) )
  5.2173 -        {
  5.2174 -            *(uint8_t *)&_regs.eax += 6;
  5.2175 -            _regs.eflags |= EFLG_AF;
  5.2176 -        }
  5.2177 -        if ( (al > 0x99) || (eflags & EFLG_CF) )
  5.2178 -        {
  5.2179 -            *(uint8_t *)&_regs.eax += 0x60;
  5.2180 -            _regs.eflags |= EFLG_CF;
  5.2181 -        }
  5.2182 -        _regs.eflags &= ~(EFLG_SF|EFLG_ZF|EFLG_PF);
  5.2183 -        _regs.eflags |= ((uint8_t)_regs.eax == 0) ? EFLG_ZF : 0;
  5.2184 -        _regs.eflags |= (( int8_t)_regs.eax <  0) ? EFLG_SF : 0;
  5.2185 -        _regs.eflags |= even_parity(_regs.eax) ? EFLG_PF : 0;
  5.2186 -        break;
  5.2187 -    }
  5.2188 -
  5.2189 -    case 0x2f: /* das */ {
  5.2190 -        uint8_t al = _regs.eax;
  5.2191 -        unsigned long eflags = _regs.eflags;
  5.2192 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.2193 -        _regs.eflags &= ~(EFLG_CF|EFLG_AF);
  5.2194 -        if ( ((al & 0x0f) > 9) || (eflags & EFLG_AF) )
  5.2195 -        {
  5.2196 -            _regs.eflags |= EFLG_AF;
  5.2197 -            if ( (al < 6) || (eflags & EFLG_CF) )
  5.2198 -                _regs.eflags |= EFLG_CF;
  5.2199 -            *(uint8_t *)&_regs.eax -= 6;
  5.2200 -        }
  5.2201 -        if ( (al > 0x99) || (eflags & EFLG_CF) )
  5.2202 -        {
  5.2203 -            *(uint8_t *)&_regs.eax -= 0x60;
  5.2204 -            _regs.eflags |= EFLG_CF;
  5.2205 -        }
  5.2206 -        _regs.eflags &= ~(EFLG_SF|EFLG_ZF|EFLG_PF);
  5.2207 -        _regs.eflags |= ((uint8_t)_regs.eax == 0) ? EFLG_ZF : 0;
  5.2208 -        _regs.eflags |= (( int8_t)_regs.eax <  0) ? EFLG_SF : 0;
  5.2209 -        _regs.eflags |= even_parity(_regs.eax) ? EFLG_PF : 0;
  5.2210 -        break;
  5.2211 -    }
  5.2212 -
  5.2213 -    case 0x37: /* aaa */
  5.2214 -    case 0x3f: /* aas */
  5.2215 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.2216 -        _regs.eflags &= ~EFLG_CF;
  5.2217 -        if ( ((uint8_t)_regs.eax > 9) || (_regs.eflags & EFLG_AF) )
  5.2218 -        {
  5.2219 -            ((uint8_t *)&_regs.eax)[0] += (b == 0x37) ? 6 : -6;
  5.2220 -            ((uint8_t *)&_regs.eax)[1] += (b == 0x37) ? 1 : -1;
  5.2221 -            _regs.eflags |= EFLG_CF | EFLG_AF;
  5.2222 -        }
  5.2223 -        ((uint8_t *)&_regs.eax)[0] &= 0x0f;
  5.2224 -        break;
  5.2225 -
  5.2226 -    case 0x40 ... 0x4f: /* inc/dec reg */
  5.2227 -        dst.type  = OP_REG;
  5.2228 -        dst.reg   = decode_register(b & 7, &_regs, 0);
  5.2229 -        dst.bytes = op_bytes;
  5.2230 -        dst.val   = *dst.reg;
  5.2231 -        if ( b & 8 )
  5.2232 -            emulate_1op("dec", dst, _regs.eflags);
  5.2233 -        else
  5.2234 -            emulate_1op("inc", dst, _regs.eflags);
  5.2235 -        break;
  5.2236 -
  5.2237 -    case 0x50 ... 0x57: /* push reg */
  5.2238 -        src.val = *(unsigned long *)decode_register(
  5.2239 -            (b & 7) | ((rex_prefix & 1) << 3), &_regs, 0);
  5.2240 -        goto push;
  5.2241 -
  5.2242 -    case 0x58 ... 0x5f: /* pop reg */
  5.2243 -        dst.type  = OP_REG;
  5.2244 -        dst.reg   = decode_register(
  5.2245 -            (b & 7) | ((rex_prefix & 1) << 3), &_regs, 0);
  5.2246 -        dst.bytes = op_bytes;
  5.2247 -        if ( mode_64bit() && (dst.bytes == 4) )
  5.2248 -            dst.bytes = 8;
  5.2249 -        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(dst.bytes),
  5.2250 -                             &dst.val, dst.bytes, ctxt)) != 0 )
  5.2251 -            goto done;
  5.2252 -        break;
  5.2253 -
  5.2254 -    case 0x60: /* pusha */ {
  5.2255 -        int i;
  5.2256 -        unsigned long regs[] = {
  5.2257 -            _regs.eax, _regs.ecx, _regs.edx, _regs.ebx,
  5.2258 -            _regs.esp, _regs.ebp, _regs.esi, _regs.edi };
  5.2259 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.2260 -        for ( i = 0; i < 8; i++ )
  5.2261 -            if ( (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  5.2262 -                                  regs[i], op_bytes, ctxt)) != 0 )
  5.2263 -            goto done;
  5.2264 -        break;
  5.2265 -    }
  5.2266 -
  5.2267 -    case 0x61: /* popa */ {
  5.2268 -        int i;
  5.2269 -        unsigned long dummy_esp, *regs[] = {
  5.2270 -            (unsigned long *)&_regs.edi, (unsigned long *)&_regs.esi,
  5.2271 -            (unsigned long *)&_regs.ebp, (unsigned long *)&dummy_esp,
  5.2272 -            (unsigned long *)&_regs.ebx, (unsigned long *)&_regs.edx,
  5.2273 -            (unsigned long *)&_regs.ecx, (unsigned long *)&_regs.eax };
  5.2274 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.2275 -        for ( i = 0; i < 8; i++ )
  5.2276 -        {
  5.2277 -            if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  5.2278 -                                 &dst.val, op_bytes, ctxt)) != 0 )
  5.2279 -                goto done;
  5.2280 -            switch ( op_bytes )
  5.2281 -            {
  5.2282 -            case 1: *(uint8_t  *)regs[i] = (uint8_t)dst.val; break;
  5.2283 -            case 2: *(uint16_t *)regs[i] = (uint16_t)dst.val; break;
  5.2284 -            case 4: *regs[i] = (uint32_t)dst.val; break; /* 64b: zero-ext */
  5.2285 -            case 8: *regs[i] = dst.val; break;
  5.2286 -            }
  5.2287 -        }
  5.2288 -        break;
  5.2289 -    }
  5.2290 -
  5.2291 -    case 0x68: /* push imm{16,32,64} */
  5.2292 -        src.val = ((op_bytes == 2)
  5.2293 -                   ? (int32_t)insn_fetch_type(int16_t)
  5.2294 -                   : insn_fetch_type(int32_t));
  5.2295 -        goto push;
  5.2296 -
  5.2297 -    case 0x6a: /* push imm8 */
  5.2298 -        src.val = insn_fetch_type(int8_t);
  5.2299 -    push:
  5.2300 -        d |= Mov; /* force writeback */
  5.2301 -        dst.type  = OP_MEM;
  5.2302 -        dst.bytes = op_bytes;
  5.2303 -        if ( mode_64bit() && (dst.bytes == 4) )
  5.2304 -            dst.bytes = 8;
  5.2305 -        dst.val = src.val;
  5.2306 -        dst.mem.seg = x86_seg_ss;
  5.2307 -        dst.mem.off = sp_pre_dec(dst.bytes);
  5.2308 -        break;
  5.2309 -
  5.2310 -    case 0x6c ... 0x6d: /* ins %dx,%es:%edi */ {
  5.2311 -        unsigned long nr_reps = get_rep_prefix();
  5.2312 -        unsigned int port = (uint16_t)_regs.edx;
  5.2313 -        dst.bytes = !(b & 1) ? 1 : (op_bytes == 8) ? 4 : op_bytes;
  5.2314 -        dst.mem.seg = x86_seg_es;
  5.2315 -        dst.mem.off = truncate_ea(_regs.edi);
  5.2316 -        if ( (rc = ioport_access_check(port, dst.bytes, ctxt, ops)) != 0 )
  5.2317 -            goto done;
  5.2318 -        if ( (nr_reps > 1) && (ops->rep_ins != NULL) &&
  5.2319 -             ((rc = ops->rep_ins(port, dst.mem.seg, dst.mem.off, dst.bytes,
  5.2320 -                                 &nr_reps, ctxt)) != X86EMUL_UNHANDLEABLE) )
  5.2321 -        {
  5.2322 -            if ( rc != 0 )
  5.2323 -                goto done;
  5.2324 -        }
  5.2325 -        else
  5.2326 -        {
  5.2327 -            fail_if(ops->read_io == NULL);
  5.2328 -            if ( (rc = ops->read_io(port, dst.bytes, &dst.val, ctxt)) != 0 )
  5.2329 -                goto done;
  5.2330 -            dst.type = OP_MEM;
  5.2331 -            nr_reps = 1;
  5.2332 -        }
  5.2333 -        register_address_increment(
  5.2334 -            _regs.edi,
  5.2335 -            nr_reps * ((_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes));
  5.2336 -        put_rep_prefix(nr_reps);
  5.2337 -        break;
  5.2338 -    }
  5.2339 -
  5.2340 -    case 0x6e ... 0x6f: /* outs %esi,%dx */ {
  5.2341 -        unsigned long nr_reps = get_rep_prefix();
  5.2342 -        unsigned int port = (uint16_t)_regs.edx;
  5.2343 -        dst.bytes = !(b & 1) ? 1 : (op_bytes == 8) ? 4 : op_bytes;
  5.2344 -        if ( (rc = ioport_access_check(port, dst.bytes, ctxt, ops)) != 0 )
  5.2345 -            goto done;
  5.2346 -        if ( (nr_reps > 1) && (ops->rep_outs != NULL) &&
  5.2347 -             ((rc = ops->rep_outs(ea.mem.seg, truncate_ea(_regs.esi),
  5.2348 -                                  port, dst.bytes,
  5.2349 -                                  &nr_reps, ctxt)) != X86EMUL_UNHANDLEABLE) )
  5.2350 -        {
  5.2351 -            if ( rc != 0 )
  5.2352 -                goto done;
  5.2353 -        }
  5.2354 -        else
  5.2355 -        {
  5.2356 -            if ( (rc = ops->read(ea.mem.seg, truncate_ea(_regs.esi),
  5.2357 -                                 &dst.val, dst.bytes, ctxt)) != 0 )
  5.2358 -                goto done;
  5.2359 -            fail_if(ops->write_io == NULL);
  5.2360 -            if ( (rc = ops->write_io(port, dst.bytes, dst.val, ctxt)) != 0 )
  5.2361 -                goto done;
  5.2362 -            nr_reps = 1;
  5.2363 -        }
  5.2364 -        register_address_increment(
  5.2365 -            _regs.esi,
  5.2366 -            nr_reps * ((_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes));
  5.2367 -        put_rep_prefix(nr_reps);
  5.2368 -        break;
  5.2369 -    }
  5.2370 -
  5.2371 -    case 0x70 ... 0x7f: /* jcc (short) */ {
  5.2372 -        int rel = insn_fetch_type(int8_t);
  5.2373 -        if ( test_cc(b, _regs.eflags) )
  5.2374 -            jmp_rel(rel);
  5.2375 -        break;
  5.2376 -    }
  5.2377 -
  5.2378 -    case 0x90: /* nop / xchg %%r8,%%rax */
  5.2379 -        if ( !(rex_prefix & 1) )
  5.2380 -            break; /* nop */
  5.2381 -
  5.2382 -    case 0x91 ... 0x97: /* xchg reg,%%rax */
  5.2383 -        src.type = dst.type = OP_REG;
  5.2384 -        src.bytes = dst.bytes = op_bytes;
  5.2385 -        src.reg  = (unsigned long *)&_regs.eax;
  5.2386 -        src.val  = *src.reg;
  5.2387 -        dst.reg  = decode_register(
  5.2388 -            (b & 7) | ((rex_prefix & 1) << 3), &_regs, 0);
  5.2389 -        dst.val  = *dst.reg;
  5.2390 -        goto xchg;
  5.2391 -
  5.2392 -    case 0x98: /* cbw/cwde/cdqe */
  5.2393 -        switch ( op_bytes )
  5.2394 -        {
  5.2395 -        case 2: *(int16_t *)&_regs.eax = (int8_t)_regs.eax; break; /* cbw */
  5.2396 -        case 4: _regs.eax = (uint32_t)(int16_t)_regs.eax; break; /* cwde */
  5.2397 -        case 8: _regs.eax = (int32_t)_regs.eax; break; /* cdqe */
  5.2398 -        }
  5.2399 -        break;
  5.2400 -
  5.2401 -    case 0x99: /* cwd/cdq/cqo */
  5.2402 -        switch ( op_bytes )
  5.2403 -        {
  5.2404 -        case 2:
  5.2405 -            *(int16_t *)&_regs.edx = ((int16_t)_regs.eax < 0) ? -1 : 0;
  5.2406 -            break;
  5.2407 -        case 4:
  5.2408 -            _regs.edx = (uint32_t)(((int32_t)_regs.eax < 0) ? -1 : 0);
  5.2409 -            break;
  5.2410 -        case 8:
  5.2411 -            _regs.edx = (_regs.eax < 0) ? -1 : 0;
  5.2412 -            break;
  5.2413 -        }
  5.2414 -        break;
  5.2415 -
  5.2416 -    case 0x9a: /* call (far, absolute) */ {
  5.2417 -        struct segment_register reg;
  5.2418 -        uint16_t sel;
  5.2419 -        uint32_t eip;
  5.2420 -
  5.2421 -        fail_if(ops->read_segment == NULL);
  5.2422 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.2423 -
  5.2424 -        eip = insn_fetch_bytes(op_bytes);
  5.2425 -        sel = insn_fetch_type(uint16_t);
  5.2426 -
  5.2427 -        if ( (rc = ops->read_segment(x86_seg_cs, &reg, ctxt)) ||
  5.2428 -             (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  5.2429 -                              reg.sel, op_bytes, ctxt)) ||
  5.2430 -             (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  5.2431 -                              _regs.eip, op_bytes, ctxt)) )
  5.2432 -            goto done;
  5.2433 -
  5.2434 -        if ( (rc = load_seg(x86_seg_cs, sel, ctxt, ops)) != 0 )
  5.2435 -            goto done;
  5.2436 -        _regs.eip = eip;
  5.2437 -        break;
  5.2438 -    }
  5.2439 -
  5.2440 -    case 0x9b:  /* wait/fwait */
  5.2441 -        fail_if(ops->load_fpu_ctxt == NULL);
  5.2442 -        ops->load_fpu_ctxt(ctxt);
  5.2443 -        __emulate_fpu_insn("fwait");
  5.2444 -        break;
  5.2445 -
  5.2446 -    case 0x9c: /* pushf */
  5.2447 -        src.val = _regs.eflags;
  5.2448 -        goto push;
  5.2449 -
  5.2450 -    case 0x9d: /* popf */ {
  5.2451 -        uint32_t mask = EFLG_VIP | EFLG_VIF | EFLG_VM;
  5.2452 -        if ( !mode_ring0() )
  5.2453 -            mask |= EFLG_IOPL;
  5.2454 -        if ( !mode_iopl() )
  5.2455 -            mask |= EFLG_IF;
  5.2456 -        /* 64-bit mode: POP defaults to a 64-bit operand. */
  5.2457 -        if ( mode_64bit() && (op_bytes == 4) )
  5.2458 -            op_bytes = 8;
  5.2459 -        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  5.2460 -                             &dst.val, op_bytes, ctxt)) != 0 )
  5.2461 -            goto done;
  5.2462 -        if ( op_bytes == 2 )
  5.2463 -            dst.val = (uint16_t)dst.val | (_regs.eflags & 0xffff0000u);
  5.2464 -        dst.val &= 0x257fd5;
  5.2465 -        _regs.eflags &= mask;
  5.2466 -        _regs.eflags |= (uint32_t)(dst.val & ~mask) | 0x02;
  5.2467 -        break;
  5.2468 -    }
  5.2469 -
  5.2470 -    case 0x9e: /* sahf */
  5.2471 -        *(uint8_t *)&_regs.eflags = (((uint8_t *)&_regs.eax)[1] & 0xd7) | 0x02;
  5.2472 -        break;
  5.2473 -
  5.2474 -    case 0x9f: /* lahf */
  5.2475 -        ((uint8_t *)&_regs.eax)[1] = (_regs.eflags & 0xd7) | 0x02;
  5.2476 -        break;
  5.2477 -
  5.2478 -    case 0xa0 ... 0xa1: /* mov mem.offs,{%al,%ax,%eax,%rax} */
  5.2479 -        /* Source EA is not encoded via ModRM. */
  5.2480 -        dst.type  = OP_REG;
  5.2481 -        dst.reg   = (unsigned long *)&_regs.eax;
  5.2482 -        dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  5.2483 -        if ( (rc = ops->read(ea.mem.seg, insn_fetch_bytes(ad_bytes),
  5.2484 -                             &dst.val, dst.bytes, ctxt)) != 0 )
  5.2485 -            goto done;
  5.2486 -        break;
  5.2487 -
  5.2488 -    case 0xa2 ... 0xa3: /* mov {%al,%ax,%eax,%rax},mem.offs */
  5.2489 -        /* Destination EA is not encoded via ModRM. */
  5.2490 -        dst.type  = OP_MEM;
  5.2491 -        dst.mem.seg = ea.mem.seg;
  5.2492 -        dst.mem.off = insn_fetch_bytes(ad_bytes);
  5.2493 -        dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  5.2494 -        dst.val   = (unsigned long)_regs.eax;
  5.2495 -        break;
  5.2496 -
  5.2497 -    case 0xa4 ... 0xa5: /* movs */ {
  5.2498 -        unsigned long nr_reps = get_rep_prefix();
  5.2499 -        dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  5.2500 -        dst.mem.seg = x86_seg_es;
  5.2501 -        dst.mem.off = truncate_ea(_regs.edi);
  5.2502 -        if ( (nr_reps > 1) && (ops->rep_movs != NULL) &&
  5.2503 -             ((rc = ops->rep_movs(ea.mem.seg, truncate_ea(_regs.esi),
  5.2504 -                                  dst.mem.seg, dst.mem.off, dst.bytes,
  5.2505 -                                  &nr_reps, ctxt)) != X86EMUL_UNHANDLEABLE) )
  5.2506 -        {
  5.2507 -            if ( rc != 0 )
  5.2508 -                goto done;
  5.2509 -        }
  5.2510 -        else
  5.2511 -        {
  5.2512 -            if ( (rc = ops->read(ea.mem.seg, truncate_ea(_regs.esi),
  5.2513 -                                 &dst.val, dst.bytes, ctxt)) != 0 )
  5.2514 -                goto done;
  5.2515 -            dst.type = OP_MEM;
  5.2516 -            nr_reps = 1;
  5.2517 -        }
  5.2518 -        register_address_increment(
  5.2519 -            _regs.esi,
  5.2520 -            nr_reps * ((_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes));
  5.2521 -        register_address_increment(
  5.2522 -            _regs.edi,
  5.2523 -            nr_reps * ((_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes));
  5.2524 -        put_rep_prefix(nr_reps);
  5.2525 -        break;
  5.2526 -    }
  5.2527 -
  5.2528 -    case 0xa6 ... 0xa7: /* cmps */ {
  5.2529 -        unsigned long next_eip = _regs.eip;
  5.2530 -        get_rep_prefix();
  5.2531 -        src.bytes = dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  5.2532 -        if ( (rc = ops->read(ea.mem.seg, truncate_ea(_regs.esi),
  5.2533 -                             &dst.val, dst.bytes, ctxt)) ||
  5.2534 -             (rc = ops->read(x86_seg_es, truncate_ea(_regs.edi),
  5.2535 -                             &src.val, src.bytes, ctxt)) )
  5.2536 -            goto done;
  5.2537 -        register_address_increment(
  5.2538 -            _regs.esi, (_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes);
  5.2539 -        register_address_increment(
  5.2540 -            _regs.edi, (_regs.eflags & EFLG_DF) ? -src.bytes : src.bytes);
  5.2541 -        put_rep_prefix(1);
  5.2542 -        /* cmp: dst - src ==> src=*%%edi,dst=*%%esi ==> *%%esi - *%%edi */
  5.2543 -        emulate_2op_SrcV("cmp", src, dst, _regs.eflags);
  5.2544 -        if ( ((rep_prefix == REPE_PREFIX) && !(_regs.eflags & EFLG_ZF)) ||
  5.2545 -             ((rep_prefix == REPNE_PREFIX) && (_regs.eflags & EFLG_ZF)) )
  5.2546 -            _regs.eip = next_eip;
  5.2547 -        break;
  5.2548 -    }
  5.2549 -
  5.2550 -    case 0xaa ... 0xab: /* stos */ {
  5.2551 -        /* unsigned long max_reps = */get_rep_prefix();
  5.2552 -        dst.type  = OP_MEM;
  5.2553 -        dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  5.2554 -        dst.mem.seg = x86_seg_es;
  5.2555 -        dst.mem.off = truncate_ea(_regs.edi);
  5.2556 -        dst.val   = _regs.eax;
  5.2557 -        register_address_increment(
  5.2558 -            _regs.edi, (_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes);
  5.2559 -        put_rep_prefix(1);
  5.2560 -        break;
  5.2561 -    }
  5.2562 -
  5.2563 -    case 0xac ... 0xad: /* lods */ {
  5.2564 -        /* unsigned long max_reps = */get_rep_prefix();
  5.2565 -        dst.type  = OP_REG;
  5.2566 -        dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  5.2567 -        dst.reg   = (unsigned long *)&_regs.eax;
  5.2568 -        if ( (rc = ops->read(ea.mem.seg, truncate_ea(_regs.esi),
  5.2569 -                             &dst.val, dst.bytes, ctxt)) != 0 )
  5.2570 -            goto done;
  5.2571 -        register_address_increment(
  5.2572 -            _regs.esi, (_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes);
  5.2573 -        put_rep_prefix(1);
  5.2574 -        break;
  5.2575 -    }
  5.2576 -
  5.2577 -    case 0xae ... 0xaf: /* scas */ {
  5.2578 -        unsigned long next_eip = _regs.eip;
  5.2579 -        get_rep_prefix();
  5.2580 -        src.bytes = dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  5.2581 -        dst.val = _regs.eax;
  5.2582 -        if ( (rc = ops->read(x86_seg_es, truncate_ea(_regs.edi),
  5.2583 -                             &src.val, src.bytes, ctxt)) != 0 )
  5.2584 -            goto done;
  5.2585 -        register_address_increment(
  5.2586 -            _regs.edi, (_regs.eflags & EFLG_DF) ? -src.bytes : src.bytes);
  5.2587 -        put_rep_prefix(1);
  5.2588 -        /* cmp: dst - src ==> src=*%%edi,dst=%%eax ==> %%eax - *%%edi */
  5.2589 -        emulate_2op_SrcV("cmp", src, dst, _regs.eflags);
  5.2590 -        if ( ((rep_prefix == REPE_PREFIX) && !(_regs.eflags & EFLG_ZF)) ||
  5.2591 -             ((rep_prefix == REPNE_PREFIX) && (_regs.eflags & EFLG_ZF)) )
  5.2592 -            _regs.eip = next_eip;
  5.2593 -        break;
  5.2594 -    }
  5.2595 -
  5.2596 -    case 0xc2: /* ret imm16 (near) */
  5.2597 -    case 0xc3: /* ret (near) */ {
  5.2598 -        int offset = (b == 0xc2) ? insn_fetch_type(uint16_t) : 0;
  5.2599 -        op_bytes = mode_64bit() ? 8 : op_bytes;
  5.2600 -        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes + offset),
  5.2601 -                             &dst.val, op_bytes, ctxt)) != 0 )
  5.2602 -            goto done;
  5.2603 -        _regs.eip = dst.val;
  5.2604 -        break;
  5.2605 -    }
  5.2606 -
  5.2607 -    case 0xc8: /* enter imm16,imm8 */ {
  5.2608 -        uint16_t size = insn_fetch_type(uint16_t);
  5.2609 -        uint8_t depth = insn_fetch_type(uint8_t) & 31;
  5.2610 -        int i;
  5.2611 -
  5.2612 -        dst.type = OP_REG;
  5.2613 -        dst.bytes = (mode_64bit() && (op_bytes == 4)) ? 8 : op_bytes;
  5.2614 -        dst.reg = (unsigned long *)&_regs.ebp;
  5.2615 -        if ( (rc = ops->write(x86_seg_ss, sp_pre_dec(dst.bytes),
  5.2616 -                              _regs.ebp, dst.bytes, ctxt)) )
  5.2617 -            goto done;
  5.2618 -        dst.val = _regs.esp;
  5.2619 -
  5.2620 -        if ( depth > 0 )
  5.2621 -        {
  5.2622 -            for ( i = 1; i < depth; i++ )
  5.2623 -            {
  5.2624 -                unsigned long ebp, temp_data;
  5.2625 -                ebp = truncate_word(_regs.ebp - i*dst.bytes, ctxt->sp_size/8);
  5.2626 -                if ( (rc = ops->read(x86_seg_ss, ebp,
  5.2627 -                                     &temp_data, dst.bytes, ctxt)) ||
  5.2628 -                     (rc = ops->write(x86_seg_ss, sp_pre_dec(dst.bytes),
  5.2629 -                                      temp_data, dst.bytes, ctxt)) )
  5.2630 -                    goto done;
  5.2631 -            }
  5.2632 -            if ( (rc = ops->write(x86_seg_ss, sp_pre_dec(dst.bytes),
  5.2633 -                                  dst.val, dst.bytes, ctxt)) )
  5.2634 -                goto done;
  5.2635 -        }
  5.2636 -
  5.2637 -        sp_pre_dec(size);
  5.2638 -        break;
  5.2639 -    }
  5.2640 -
  5.2641 -    case 0xc9: /* leave */
  5.2642 -        /* First writeback, to %%esp. */
  5.2643 -        dst.type = OP_REG;
  5.2644 -        dst.bytes = (mode_64bit() && (op_bytes == 4)) ? 8 : op_bytes;
  5.2645 -        dst.reg = (unsigned long *)&_regs.esp;
  5.2646 -        dst.val = _regs.ebp;
  5.2647 -
  5.2648 -        /* Flush first writeback, since there is a second. */
  5.2649 -        switch ( dst.bytes )
  5.2650 -        {
  5.2651 -        case 1: *(uint8_t  *)dst.reg = (uint8_t)dst.val; break;
  5.2652 -        case 2: *(uint16_t *)dst.reg = (uint16_t)dst.val; break;
  5.2653 -        case 4: *dst.reg = (uint32_t)dst.val; break; /* 64b: zero-ext */
  5.2654 -        case 8: *dst.reg = dst.val; break;
  5.2655 -        }
  5.2656 -
  5.2657 -        /* Second writeback, to %%ebp. */
  5.2658 -        dst.reg = (unsigned long *)&_regs.ebp;
  5.2659 -        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(dst.bytes),
  5.2660 -                             &dst.val, dst.bytes, ctxt)) )
  5.2661 -            goto done;
  5.2662 -        break;
  5.2663 -
  5.2664 -    case 0xca: /* ret imm16 (far) */
  5.2665 -    case 0xcb: /* ret (far) */ {
  5.2666 -        int offset = (b == 0xca) ? insn_fetch_type(uint16_t) : 0;
  5.2667 -        op_bytes = mode_64bit() ? 8 : op_bytes;
  5.2668 -        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  5.2669 -                             &dst.val, op_bytes, ctxt)) || 
  5.2670 -             (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes + offset),
  5.2671 -                             &src.val, op_bytes, ctxt)) ||
  5.2672 -             (rc = load_seg(x86_seg_cs, (uint16_t)src.val, ctxt, ops)) )
  5.2673 -            goto done;
  5.2674 -        _regs.eip = dst.val;
  5.2675 -        break;
  5.2676 -    }
  5.2677 -
  5.2678 -    case 0xcc: /* int3 */
  5.2679 -        src.val = EXC_BP;
  5.2680 -        goto swint;
  5.2681 -
  5.2682 -    case 0xcd: /* int imm8 */
  5.2683 -        src.val = insn_fetch_type(uint8_t);
  5.2684 -    swint:
  5.2685 -        fail_if(ops->inject_sw_interrupt == NULL);
  5.2686 -        rc = ops->inject_sw_interrupt(src.val, _regs.eip - ctxt->regs->eip,
  5.2687 -                                      ctxt) ? : X86EMUL_EXCEPTION;
  5.2688 -        goto done;
  5.2689 -
  5.2690 -    case 0xce: /* into */
  5.2691 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.2692 -        if ( !(_regs.eflags & EFLG_OF) )
  5.2693 -            break;
  5.2694 -        src.val = EXC_OF;
  5.2695 -        goto swint;
  5.2696 -
  5.2697 -    case 0xcf: /* iret */ {
  5.2698 -        unsigned long cs, eip, eflags;
  5.2699 -        uint32_t mask = EFLG_VIP | EFLG_VIF | EFLG_VM;
  5.2700 -        if ( !mode_ring0() )
  5.2701 -            mask |= EFLG_IOPL;
  5.2702 -        if ( !mode_iopl() )
  5.2703 -            mask |= EFLG_IF;
  5.2704 -        fail_if(!in_realmode(ctxt, ops));
  5.2705 -        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  5.2706 -                             &eip, op_bytes, ctxt)) ||
  5.2707 -             (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  5.2708 -                             &cs, op_bytes, ctxt)) ||
  5.2709 -             (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  5.2710 -                             &eflags, op_bytes, ctxt)) )
  5.2711 -            goto done;
  5.2712 -        if ( op_bytes == 2 )
  5.2713 -            eflags = (uint16_t)eflags | (_regs.eflags & 0xffff0000u);
  5.2714 -        eflags &= 0x257fd5;
  5.2715 -        _regs.eflags &= mask;
  5.2716 -        _regs.eflags |= (uint32_t)(eflags & ~mask) | 0x02;
  5.2717 -        _regs.eip = eip;
  5.2718 -        if ( (rc = load_seg(x86_seg_cs, (uint16_t)cs, ctxt, ops)) != 0 )
  5.2719 -            goto done;
  5.2720 -        break;
  5.2721 -    }
  5.2722 -
  5.2723 -    case 0xd4: /* aam */ {
  5.2724 -        unsigned int base = insn_fetch_type(uint8_t);
  5.2725 -        uint8_t al = _regs.eax;
  5.2726 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.2727 -        generate_exception_if(base == 0, EXC_DE, -1);
  5.2728 -        *(uint16_t *)&_regs.eax = ((al / base) << 8) | (al % base);
  5.2729 -        _regs.eflags &= ~(EFLG_SF|EFLG_ZF|EFLG_PF);
  5.2730 -        _regs.eflags |= ((uint8_t)_regs.eax == 0) ? EFLG_ZF : 0;
  5.2731 -        _regs.eflags |= (( int8_t)_regs.eax <  0) ? EFLG_SF : 0;
  5.2732 -        _regs.eflags |= even_parity(_regs.eax) ? EFLG_PF : 0;
  5.2733 -        break;
  5.2734 -    }
  5.2735 -
  5.2736 -    case 0xd5: /* aad */ {
  5.2737 -        unsigned int base = insn_fetch_type(uint8_t);
  5.2738 -        uint16_t ax = _regs.eax;
  5.2739 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.2740 -        *(uint16_t *)&_regs.eax = (uint8_t)(ax + ((ax >> 8) * base));
  5.2741 -        _regs.eflags &= ~(EFLG_SF|EFLG_ZF|EFLG_PF);
  5.2742 -        _regs.eflags |= ((uint8_t)_regs.eax == 0) ? EFLG_ZF : 0;
  5.2743 -        _regs.eflags |= (( int8_t)_regs.eax <  0) ? EFLG_SF : 0;
  5.2744 -        _regs.eflags |= even_parity(_regs.eax) ? EFLG_PF : 0;
  5.2745 -        break;
  5.2746 -    }
  5.2747 -
  5.2748 -    case 0xd6: /* salc */
  5.2749 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.2750 -        *(uint8_t *)&_regs.eax = (_regs.eflags & EFLG_CF) ? 0xff : 0x00;
  5.2751 -        break;
  5.2752 -
  5.2753 -    case 0xd7: /* xlat */ {
  5.2754 -        unsigned long al = (uint8_t)_regs.eax;
  5.2755 -        if ( (rc = ops->read(ea.mem.seg, truncate_ea(_regs.ebx + al),
  5.2756 -                             &al, 1, ctxt)) != 0 )
  5.2757 -            goto done;
  5.2758 -        *(uint8_t *)&_regs.eax = al;
  5.2759 -        break;
  5.2760 -    }
  5.2761 -
  5.2762 -    case 0xd9: /* FPU 0xd9 */
  5.2763 -        fail_if(ops->load_fpu_ctxt == NULL);
  5.2764 -        ops->load_fpu_ctxt(ctxt);
  5.2765 -        switch ( modrm )
  5.2766 -        {
  5.2767 -        case 0xc0: __emulate_fpu_insn(".byte 0xd9,0xc0"); break;
  5.2768 -        case 0xc1: __emulate_fpu_insn(".byte 0xd9,0xc1"); break;
  5.2769 -        case 0xc2: __emulate_fpu_insn(".byte 0xd9,0xc2"); break;
  5.2770 -        case 0xc3: __emulate_fpu_insn(".byte 0xd9,0xc3"); break;
  5.2771 -        case 0xc4: __emulate_fpu_insn(".byte 0xd9,0xc4"); break;
  5.2772 -        case 0xc5: __emulate_fpu_insn(".byte 0xd9,0xc5"); break;
  5.2773 -        case 0xc6: __emulate_fpu_insn(".byte 0xd9,0xc6"); break;
  5.2774 -        case 0xc7: __emulate_fpu_insn(".byte 0xd9,0xc7"); break;
  5.2775 -        case 0xe0: __emulate_fpu_insn(".byte 0xd9,0xe0"); break;
  5.2776 -        case 0xe8: __emulate_fpu_insn(".byte 0xd9,0xe8"); break;
  5.2777 -        case 0xee: __emulate_fpu_insn(".byte 0xd9,0xee"); break;
  5.2778 -        default:
  5.2779 -            fail_if((modrm_reg & 7) != 7);
  5.2780 -            fail_if(modrm >= 0xc0);
  5.2781 -            /* fnstcw m2byte */
  5.2782 -            ea.bytes = 2;
  5.2783 -            dst = ea;
  5.2784 -            asm volatile ( "fnstcw %0" : "=m" (dst.val) );
  5.2785 -        }
  5.2786 -        break;
  5.2787 -
  5.2788 -    case 0xdb: /* FPU 0xdb */
  5.2789 -        fail_if(ops->load_fpu_ctxt == NULL);
  5.2790 -        ops->load_fpu_ctxt(ctxt);
  5.2791 -        fail_if(modrm != 0xe3);
  5.2792 -        /* fninit */
  5.2793 -        asm volatile ( "fninit" );
  5.2794 -        break;
  5.2795 -
  5.2796 -    case 0xdd: /* FPU 0xdd */
  5.2797 -        fail_if(ops->load_fpu_ctxt == NULL);
  5.2798 -        ops->load_fpu_ctxt(ctxt);
  5.2799 -        fail_if((modrm_reg & 7) != 7);
  5.2800 -        fail_if(modrm >= 0xc0);
  5.2801 -        /* fnstsw m2byte */
  5.2802 -        ea.bytes = 2;
  5.2803 -        dst = ea;
  5.2804 -        asm volatile ( "fnstsw %0" : "=m" (dst.val) );
  5.2805 -        break;
  5.2806 -
  5.2807 -    case 0xde: /* FPU 0xde */
  5.2808 -        fail_if(ops->load_fpu_ctxt == NULL);
  5.2809 -        ops->load_fpu_ctxt(ctxt);
  5.2810 -        switch ( modrm )
  5.2811 -        {
  5.2812 -        case 0xd9: __emulate_fpu_insn(".byte 0xde,0xd9"); break;
  5.2813 -        case 0xf8: __emulate_fpu_insn(".byte 0xde,0xf8"); break;
  5.2814 -        case 0xf9: __emulate_fpu_insn(".byte 0xde,0xf9"); break;
  5.2815 -        case 0xfa: __emulate_fpu_insn(".byte 0xde,0xfa"); break;
  5.2816 -        case 0xfb: __emulate_fpu_insn(".byte 0xde,0xfb"); break;
  5.2817 -        case 0xfc: __emulate_fpu_insn(".byte 0xde,0xfc"); break;
  5.2818 -        case 0xfd: __emulate_fpu_insn(".byte 0xde,0xfd"); break;
  5.2819 -        case 0xfe: __emulate_fpu_insn(".byte 0xde,0xfe"); break;
  5.2820 -        case 0xff: __emulate_fpu_insn(".byte 0xde,0xff"); break;
  5.2821 -        default: goto cannot_emulate;
  5.2822 -        }
  5.2823 -        break;
  5.2824 -
  5.2825 -    case 0xdf: /* FPU 0xdf */
  5.2826 -        fail_if(ops->load_fpu_ctxt == NULL);
  5.2827 -        ops->load_fpu_ctxt(ctxt);
  5.2828 -        fail_if(modrm != 0xe0);
  5.2829 -        /* fnstsw %ax */
  5.2830 -        dst.bytes = 2;
  5.2831 -        dst.type = OP_REG;
  5.2832 -        dst.reg = (unsigned long *)&_regs.eax;
  5.2833 -        asm volatile ( "fnstsw %0" : "=m" (dst.val) );
  5.2834 -        break;
  5.2835 -
  5.2836 -    case 0xe0 ... 0xe2: /* loop{,z,nz} */ {
  5.2837 -        int rel = insn_fetch_type(int8_t);
  5.2838 -        int do_jmp = !(_regs.eflags & EFLG_ZF); /* loopnz */
  5.2839 -        if ( b == 0xe1 )
  5.2840 -            do_jmp = !do_jmp; /* loopz */
  5.2841 -        else if ( b == 0xe2 )
  5.2842 -            do_jmp = 1; /* loop */
  5.2843 -        switch ( ad_bytes )
  5.2844 -        {
  5.2845 -        case 2:
  5.2846 -            do_jmp &= --(*(uint16_t *)&_regs.ecx) != 0;
  5.2847 -            break;
  5.2848 -        case 4:
  5.2849 -            do_jmp &= --(*(uint32_t *)&_regs.ecx) != 0;
  5.2850 -            _regs.ecx = (uint32_t)_regs.ecx; /* zero extend in x86/64 mode */
  5.2851 -            break;
  5.2852 -        default: /* case 8: */
  5.2853 -            do_jmp &= --_regs.ecx != 0;
  5.2854 -            break;
  5.2855 -        }
  5.2856 -        if ( do_jmp )
  5.2857 -            jmp_rel(rel);
  5.2858 -        break;
  5.2859 -    }
  5.2860 -
  5.2861 -    case 0xe3: /* jcxz/jecxz (short) */ {
  5.2862 -        int rel = insn_fetch_type(int8_t);
  5.2863 -        if ( (ad_bytes == 2) ? !(uint16_t)_regs.ecx :
  5.2864 -             (ad_bytes == 4) ? !(uint32_t)_regs.ecx : !_regs.ecx )
  5.2865 -            jmp_rel(rel);
  5.2866 -        break;
  5.2867 -    }
  5.2868 -
  5.2869 -    case 0xe4: /* in imm8,%al */
  5.2870 -    case 0xe5: /* in imm8,%eax */
  5.2871 -    case 0xe6: /* out %al,imm8 */
  5.2872 -    case 0xe7: /* out %eax,imm8 */
  5.2873 -    case 0xec: /* in %dx,%al */
  5.2874 -    case 0xed: /* in %dx,%eax */
  5.2875 -    case 0xee: /* out %al,%dx */
  5.2876 -    case 0xef: /* out %eax,%dx */ {
  5.2877 -        unsigned int port = ((b < 0xe8)
  5.2878 -                             ? insn_fetch_type(uint8_t)
  5.2879 -                             : (uint16_t)_regs.edx);
  5.2880 -        op_bytes = !(b & 1) ? 1 : (op_bytes == 8) ? 4 : op_bytes;
  5.2881 -        if ( (rc = ioport_access_check(port, op_bytes, ctxt, ops)) != 0 )
  5.2882 -            goto done;
  5.2883 -        if ( b & 2 )
  5.2884 -        {
  5.2885 -            /* out */
  5.2886 -            fail_if(ops->write_io == NULL);
  5.2887 -            rc = ops->write_io(port, op_bytes, _regs.eax, ctxt);
  5.2888 -            
  5.2889 -        }
  5.2890 -        else
  5.2891 -        {
  5.2892 -            /* in */
  5.2893 -            dst.type  = OP_REG;
  5.2894 -            dst.bytes = op_bytes;
  5.2895 -            dst.reg   = (unsigned long *)&_regs.eax;
  5.2896 -            fail_if(ops->read_io == NULL);
  5.2897 -            rc = ops->read_io(port, dst.bytes, &dst.val, ctxt);
  5.2898 -        }
  5.2899 -        if ( rc != 0 )
  5.2900 -            goto done;
  5.2901 -        break;
  5.2902 -    }
  5.2903 -
  5.2904 -    case 0xe8: /* call (near) */ {
  5.2905 -        int rel = (((op_bytes == 2) && !mode_64bit())
  5.2906 -                   ? (int32_t)insn_fetch_type(int16_t)
  5.2907 -                   : insn_fetch_type(int32_t));
  5.2908 -        op_bytes = mode_64bit() ? 8 : op_bytes;
  5.2909 -        src.val = _regs.eip;
  5.2910 -        jmp_rel(rel);
  5.2911 -        goto push;
  5.2912 -    }
  5.2913 -
  5.2914 -    case 0xe9: /* jmp (near) */ {
  5.2915 -        int rel = (((op_bytes == 2) && !mode_64bit())
  5.2916 -                   ? (int32_t)insn_fetch_type(int16_t)
  5.2917 -                   : insn_fetch_type(int32_t));
  5.2918 -        jmp_rel(rel);
  5.2919 -        break;
  5.2920 -    }
  5.2921 -
  5.2922 -    case 0xea: /* jmp (far, absolute) */ {
  5.2923 -        uint16_t sel;
  5.2924 -        uint32_t eip;
  5.2925 -        generate_exception_if(mode_64bit(), EXC_UD, -1);
  5.2926 -        eip = insn_fetch_bytes(op_bytes);
  5.2927 -        sel = insn_fetch_type(uint16_t);
  5.2928 -        if ( (rc = load_seg(x86_seg_cs, sel, ctxt, ops)) != 0 )
  5.2929 -            goto done;
  5.2930 -        _regs.eip = eip;
  5.2931 -        break;
  5.2932 -    }
  5.2933 -
  5.2934 -    case 0xeb: /* jmp (short) */ {
  5.2935 -        int rel = insn_fetch_type(int8_t);
  5.2936 -        jmp_rel(rel);
  5.2937 -        break;
  5.2938 -    }
  5.2939 -
  5.2940 -    case 0xf1: /* int1 (icebp) */
  5.2941 -        src.val = EXC_DB;
  5.2942 -        goto swint;
  5.2943 -
  5.2944 -    case 0xf4: /* hlt */
  5.2945 -        ctxt->retire.flags.hlt = 1;
  5.2946 -        break;
  5.2947 -
  5.2948 -    case 0xf5: /* cmc */
  5.2949 -        _regs.eflags ^= EFLG_CF;
  5.2950 -        break;
  5.2951 -
  5.2952 -    case 0xf8: /* clc */
  5.2953 -        _regs.eflags &= ~EFLG_CF;
  5.2954 -        break;
  5.2955 -
  5.2956 -    case 0xf9: /* stc */
  5.2957 -        _regs.eflags |= EFLG_CF;
  5.2958 -        break;
  5.2959 -
  5.2960 -    case 0xfa: /* cli */
  5.2961 -        generate_exception_if(!mode_iopl(), EXC_GP, 0);
  5.2962 -        _regs.eflags &= ~EFLG_IF;
  5.2963 -        break;
  5.2964 -
  5.2965 -    case 0xfb: /* sti */
  5.2966 -        generate_exception_if(!mode_iopl(), EXC_GP, 0);
  5.2967 -        if ( !(_regs.eflags & EFLG_IF) )
  5.2968 -        {
  5.2969 -            _regs.eflags |= EFLG_IF;
  5.2970 -            ctxt->retire.flags.sti = 1;
  5.2971 -        }
  5.2972 -        break;
  5.2973 -
  5.2974 -    case 0xfc: /* cld */
  5.2975 -        _regs.eflags &= ~EFLG_DF;
  5.2976 -        break;
  5.2977 -
  5.2978 -    case 0xfd: /* std */
  5.2979 -        _regs.eflags |= EFLG_DF;
  5.2980 -        break;
  5.2981 -    }
  5.2982 -    goto writeback;
  5.2983 -
  5.2984 - twobyte_insn:
  5.2985 -    switch ( b )
  5.2986 -    {
  5.2987 -    case 0x40 ... 0x4f: /* cmovcc */
  5.2988 -        dst.val = src.val;
  5.2989 -        if ( !test_cc(b, _regs.eflags) )
  5.2990 -            dst.type = OP_NONE;
  5.2991 -        break;
  5.2992 -
  5.2993 -    case 0x90 ... 0x9f: /* setcc */
  5.2994 -        dst.val = test_cc(b, _regs.eflags);
  5.2995 -        break;
  5.2996 -
  5.2997 -    case 0xb0 ... 0xb1: /* cmpxchg */
  5.2998 -        /* Save real source value, then compare EAX against destination. */
  5.2999 -        src.orig_val = src.val;
  5.3000 -        src.val = _regs.eax;
  5.3001 -        emulate_2op_SrcV("cmp", src, dst, _regs.eflags);
  5.3002 -        if ( _regs.eflags & EFLG_ZF )
  5.3003 -        {
  5.3004 -            /* Success: write back to memory. */
  5.3005 -            dst.val = src.orig_val;
  5.3006 -        }
  5.3007 -        else
  5.3008 -        {
  5.3009 -            /* Failure: write the value we saw to EAX. */
  5.3010 -            dst.type = OP_REG;
  5.3011 -            dst.reg  = (unsigned long *)&_regs.eax;
  5.3012 -        }
  5.3013 -        break;
  5.3014 -
  5.3015 -    case 0xa3: bt: /* bt */
  5.3016 -        emulate_2op_SrcV_nobyte("bt", src, dst, _regs.eflags);
  5.3017 -        break;
  5.3018 -
  5.3019 -    case 0xa4: /* shld imm8,r,r/m */
  5.3020 -    case 0xa5: /* shld %%cl,r,r/m */
  5.3021 -    case 0xac: /* shrd imm8,r,r/m */
  5.3022 -    case 0xad: /* shrd %%cl,r,r/m */ {
  5.3023 -        uint8_t shift, width = dst.bytes << 3;
  5.3024 -        shift = (b & 1) ? (uint8_t)_regs.ecx : insn_fetch_type(uint8_t);
  5.3025 -        if ( (shift &= width - 1) == 0 )
  5.3026 -            break;
  5.3027 -        dst.orig_val = truncate_word(dst.val, dst.bytes);
  5.3028 -        dst.val = ((shift == width) ? src.val :
  5.3029 -                   (b & 8) ?
  5.3030 -                   /* shrd */
  5.3031 -                   ((dst.orig_val >> shift) |
  5.3032 -                    truncate_word(src.val << (width - shift), dst.bytes)) :
  5.3033 -                   /* shld */
  5.3034 -                   ((dst.orig_val << shift) |
  5.3035 -                    ((src.val >> (width - shift)) & ((1ull << shift) - 1))));
  5.3036 -        dst.val = truncate_word(dst.val, dst.bytes);
  5.3037 -        _regs.eflags &= ~(EFLG_OF|EFLG_SF|EFLG_ZF|EFLG_PF|EFLG_CF);
  5.3038 -        if ( (dst.val >> ((b & 8) ? (shift - 1) : (width - shift))) & 1 )
  5.3039 -            _regs.eflags |= EFLG_CF;
  5.3040 -        if ( ((dst.val ^ dst.orig_val) >> (width - 1)) & 1 )
  5.3041 -            _regs.eflags |= EFLG_OF;
  5.3042 -        _regs.eflags |= ((dst.val >> (width - 1)) & 1) ? EFLG_SF : 0;
  5.3043 -        _regs.eflags |= (dst.val == 0) ? EFLG_ZF : 0;
  5.3044 -        _regs.eflags |= even_parity(dst.val) ? EFLG_PF : 0;
  5.3045 -        break;
  5.3046 -    }
  5.3047 -
  5.3048 -    case 0xb3: btr: /* btr */
  5.3049 -        emulate_2op_SrcV_nobyte("btr", src, dst, _regs.eflags);
  5.3050 -        break;
  5.3051 -
  5.3052 -    case 0xab: bts: /* bts */
  5.3053 -        emulate_2op_SrcV_nobyte("bts", src, dst, _regs.eflags);
  5.3054 -        break;
  5.3055 -
  5.3056 -    case 0xaf: /* imul */
  5.3057 -        _regs.eflags &= ~(EFLG_OF|EFLG_CF);
  5.3058 -        switch ( dst.bytes )
  5.3059 -        {
  5.3060 -        case 2:
  5.3061 -            dst.val = ((uint32_t)(int16_t)src.val *
  5.3062 -                       (uint32_t)(int16_t)dst.val);
  5.3063 -            if ( (int16_t)dst.val != (uint32_t)dst.val )
  5.3064 -                _regs.eflags |= EFLG_OF|EFLG_CF;
  5.3065 -            break;
  5.3066 -#ifdef __x86_64__
  5.3067 -        case 4:
  5.3068 -            dst.val = ((uint64_t)(int32_t)src.val *
  5.3069 -                       (uint64_t)(int32_t)dst.val);
  5.3070 -            if ( (int32_t)dst.val != dst.val )
  5.3071 -                _regs.eflags |= EFLG_OF|EFLG_CF;
  5.3072 -            break;
  5.3073 -#endif
  5.3074 -        default: {
  5.3075 -            unsigned long m[2] = { src.val, dst.val };
  5.3076 -            if ( imul_dbl(m) )
  5.3077 -                _regs.eflags |= EFLG_OF|EFLG_CF;
  5.3078 -            dst.val = m[0];
  5.3079 -            break;
  5.3080 -        }
  5.3081 -        }
  5.3082 -        break;
  5.3083 -
  5.3084 -    case 0xb2: /* lss */
  5.3085 -        dst.val = x86_seg_ss;
  5.3086 -        goto les;
  5.3087 -
  5.3088 -    case 0xb4: /* lfs */
  5.3089 -        dst.val = x86_seg_fs;
  5.3090 -        goto les;
  5.3091 -
  5.3092 -    case 0xb5: /* lgs */
  5.3093 -        dst.val = x86_seg_gs;
  5.3094 -        goto les;
  5.3095 -
  5.3096 -    case 0xb6: /* movzx rm8,r{16,32,64} */
  5.3097 -        /* Recompute DstReg as we may have decoded AH/BH/CH/DH. */
  5.3098 -        dst.reg   = decode_register(modrm_reg, &_regs, 0);
  5.3099 -        dst.bytes = op_bytes;
  5.3100 -        dst.val   = (uint8_t)src.val;
  5.3101 -        break;
  5.3102 -
  5.3103 -    case 0xbc: /* bsf */ {
  5.3104 -        int zf;
  5.3105 -        asm ( "bsf %2,%0; setz %b1"
  5.3106 -              : "=r" (dst.val), "=q" (zf)
  5.3107 -              : "r" (src.val), "1" (0) );
  5.3108 -        _regs.eflags &= ~EFLG_ZF;
  5.3109 -        _regs.eflags |= zf ? EFLG_ZF : 0;
  5.3110 -        break;
  5.3111 -    }
  5.3112 -
  5.3113 -    case 0xbd: /* bsr */ {
  5.3114 -        int zf;
  5.3115 -        asm ( "bsr %2,%0; setz %b1"
  5.3116 -              : "=r" (dst.val), "=q" (zf)
  5.3117 -              : "r" (src.val), "1" (0) );
  5.3118 -        _regs.eflags &= ~EFLG_ZF;
  5.3119 -        _regs.eflags |= zf ? EFLG_ZF : 0;
  5.3120 -        break;
  5.3121 -    }
  5.3122 -
  5.3123 -    case 0xb7: /* movzx rm16,r{16,32,64} */
  5.3124 -        dst.val = (uint16_t)src.val;
  5.3125 -        break;
  5.3126 -
  5.3127 -    case 0xbb: btc: /* btc */
  5.3128 -        emulate_2op_SrcV_nobyte("btc", src, dst, _regs.eflags);
  5.3129 -        break;
  5.3130 -
  5.3131 -    case 0xba: /* Grp8 */
  5.3132 -        switch ( modrm_reg & 7 )
  5.3133 -        {
  5.3134 -        case 4: goto bt;
  5.3135 -        case 5: goto bts;
  5.3136 -        case 6: goto btr;
  5.3137 -        case 7: goto btc;
  5.3138 -        default: generate_exception_if(1, EXC_UD, -1);
  5.3139 -        }
  5.3140 -        break;
  5.3141 -
  5.3142 -    case 0xbe: /* movsx rm8,r{16,32,64} */
  5.3143 -        /* Recompute DstReg as we may have decoded AH/BH/CH/DH. */
  5.3144 -        dst.reg   = decode_register(modrm_reg, &_regs, 0);
  5.3145 -        dst.bytes = op_bytes;
  5.3146 -        dst.val   = (int8_t)src.val;
  5.3147 -        break;
  5.3148 -
  5.3149 -    case 0xbf: /* movsx rm16,r{16,32,64} */
  5.3150 -        dst.val = (int16_t)src.val;
  5.3151 -        break;
  5.3152 -
  5.3153 -    case 0xc0 ... 0xc1: /* xadd */
  5.3154 -        /* Write back the register source. */
  5.3155 -        switch ( dst.bytes )
  5.3156 -        {
  5.3157 -        case 1: *(uint8_t  *)src.reg = (uint8_t)dst.val; break;
  5.3158 -        case 2: *(uint16_t *)src.reg = (uint16_t)dst.val; break;
  5.3159 -        case 4: *src.reg = (uint32_t)dst.val; break; /* 64b reg: zero-extend */
  5.3160 -        case 8: *src.reg = dst.val; break;
  5.3161 -        }
  5.3162 -        goto add;
  5.3163 -    }
  5.3164 -    goto writeback;
  5.3165 -
  5.3166 - twobyte_special_insn:
  5.3167 -    switch ( b )
  5.3168 -    {
  5.3169 -    case 0x01: /* Grp7 */ {
  5.3170 -        struct segment_register reg;
  5.3171 -        unsigned long base, limit, cr0, cr0w;
  5.3172 -
  5.3173 -        if ( modrm == 0xdf ) /* invlpga */
  5.3174 -        {
  5.3175 -            generate_exception_if(in_realmode(ctxt, ops), EXC_UD, -1);
  5.3176 -            generate_exception_if(!mode_ring0(), EXC_GP, 0);
  5.3177 -            fail_if(ops->invlpg == NULL);
  5.3178 -            if ( (rc = ops->invlpg(x86_seg_none, truncate_ea(_regs.eax),
  5.3179 -                                   ctxt)) )
  5.3180 -                goto done;
  5.3181 -            break;
  5.3182 -        }
  5.3183 -
  5.3184 -        switch ( modrm_reg & 7 )
  5.3185 -        {
  5.3186 -        case 0: /* sgdt */
  5.3187 -        case 1: /* sidt */
  5.3188 -            generate_exception_if(ea.type != OP_MEM, EXC_UD, -1);
  5.3189 -            fail_if(ops->read_segment == NULL);
  5.3190 -            if ( (rc = ops->read_segment((modrm_reg & 1) ?
  5.3191 -                                         x86_seg_idtr : x86_seg_gdtr,
  5.3192 -                                         &reg, ctxt)) )
  5.3193 -                goto done;
  5.3194 -            if ( op_bytes == 2 )
  5.3195 -                reg.base &= 0xffffff;
  5.3196 -            if ( (rc = ops->write(ea.mem.seg, ea.mem.off+0,
  5.3197 -                                  reg.limit, 2, ctxt)) ||
  5.3198 -                 (rc = ops->write(ea.mem.seg, ea.mem.off+2,
  5.3199 -                                  reg.base, mode_64bit() ? 8 : 4, ctxt)) )
  5.3200 -                goto done;
  5.3201 -            break;
  5.3202 -        case 2: /* lgdt */
  5.3203 -        case 3: /* lidt */
  5.3204 -            generate_exception_if(ea.type != OP_MEM, EXC_UD, -1);
  5.3205 -            fail_if(ops->write_segment == NULL);
  5.3206 -            memset(&reg, 0, sizeof(reg));
  5.3207 -            if ( (rc = ops->read(ea.mem.seg, ea.mem.off+0,
  5.3208 -                                 &limit, 2, ctxt)) ||
  5.3209 -                 (rc = ops->read(ea.mem.seg, ea.mem.off+2,
  5.3210 -                                 &base, mode_64bit() ? 8 : 4, ctxt)) )
  5.3211 -                goto done;
  5.3212 -            reg.base = base;
  5.3213 -            reg.limit = limit;
  5.3214 -            if ( op_bytes == 2 )
  5.3215 -                reg.base &= 0xffffff;
  5.3216 -            if ( (rc = ops->write_segment((modrm_reg & 1) ?
  5.3217 -                                          x86_seg_idtr : x86_seg_gdtr,
  5.3218 -                                          &reg, ctxt)) )
  5.3219 -                goto done;
  5.3220 -            break;
  5.3221 -        case 4: /* smsw */
  5.3222 -            ea.bytes = 2;
  5.3223 -            dst = ea;
  5.3224 -            fail_if(ops->read_cr == NULL);
  5.3225 -            if ( (rc = ops->read_cr(0, &dst.val, ctxt)) )
  5.3226 -                goto done;
  5.3227 -            d |= Mov; /* force writeback */
  5.3228 -            break;
  5.3229 -        case 6: /* lmsw */
  5.3230 -            fail_if(ops->read_cr == NULL);
  5.3231 -            fail_if(ops->write_cr == NULL);
  5.3232 -            if ( (rc = ops->read_cr(0, &cr0, ctxt)) )
  5.3233 -                goto done;
  5.3234 -            if ( ea.type == OP_REG )
  5.3235 -                cr0w = *ea.reg;
  5.3236 -            else if ( (rc = ops->read(ea.mem.seg, ea.mem.off,
  5.3237 -                                      &cr0w, 2, ctxt)) )
  5.3238 -                goto done;
  5.3239 -            cr0 &= 0xffff0000;
  5.3240 -            cr0 |= (uint16_t)cr0w;
  5.3241 -            if ( (rc = ops->write_cr(0, cr0, ctxt)) )
  5.3242 -                goto done;
  5.3243 -            break;
  5.3244 -        case 7: /* invlpg */
  5.3245 -            generate_exception_if(!mode_ring0(), EXC_GP, 0);
  5.3246 -            generate_exception_if(ea.type != OP_MEM, EXC_UD, -1);
  5.3247 -            fail_if(ops->invlpg == NULL);
  5.3248 -            if ( (rc = ops->invlpg(ea.mem.seg, ea.mem.off, ctxt)) )
  5.3249 -                goto done;
  5.3250 -            break;
  5.3251 -        default:
  5.3252 -            goto cannot_emulate;
  5.3253 -        }
  5.3254 -        break;
  5.3255 -    }
  5.3256 -
  5.3257 -    case 0x06: /* clts */
  5.3258 -        generate_exception_if(!mode_ring0(), EXC_GP, 0);
  5.3259 -        fail_if((ops->read_cr == NULL) || (ops->write_cr == NULL));
  5.3260 -        if ( (rc = ops->read_cr(0, &dst.val, ctxt)) ||
  5.3261 -             (rc = ops->write_cr(0, dst.val&~8, ctxt)) )
  5.3262 -            goto done;
  5.3263 -        break;
  5.3264 -
  5.3265 -    case 0x08: /* invd */
  5.3266 -    case 0x09: /* wbinvd */
  5.3267 -        generate_exception_if(!mode_ring0(), EXC_GP, 0);
  5.3268 -        fail_if(ops->wbinvd == NULL);
  5.3269 -        if ( (rc = ops->wbinvd(ctxt)) != 0 )
  5.3270 -            goto done;
  5.3271 -        break;
  5.3272 -
  5.3273 -    case 0x0d: /* GrpP (prefetch) */
  5.3274 -    case 0x18: /* Grp16 (prefetch/nop) */
  5.3275 -    case 0x19 ... 0x1f: /* nop (amd-defined) */
  5.3276 -        break;
  5.3277 -
  5.3278 -    case 0x20: /* mov cr,reg */
  5.3279 -    case 0x21: /* mov dr,reg */
  5.3280 -    case 0x22: /* mov reg,cr */
  5.3281 -    case 0x23: /* mov reg,dr */
  5.3282 -        generate_exception_if(ea.type != OP_REG, EXC_UD, -1);
  5.3283 -        generate_exception_if(!mode_ring0(), EXC_GP, 0);
  5.3284 -        modrm_reg |= lock_prefix << 3;
  5.3285 -        if ( b & 2 )
  5.3286 -        {
  5.3287 -            /* Write to CR/DR. */
  5.3288 -            src.val = *(unsigned long *)decode_register(modrm_rm, &_regs, 0);
  5.3289 -            if ( !mode_64bit() )
  5.3290 -                src.val = (uint32_t)src.val;
  5.3291 -            rc = ((b & 1)
  5.3292 -                  ? (ops->write_dr
  5.3293 -                     ? ops->write_dr(modrm_reg, src.val, ctxt)
  5.3294 -                     : X86EMUL_UNHANDLEABLE)
  5.3295 -                  : (ops->write_cr
  5.3296 -                     ? ops->write_cr(modrm_reg, src.val, ctxt)
  5.3297 -                     : X86EMUL_UNHANDLEABLE));
  5.3298 -        }
  5.3299 -        else
  5.3300 -        {
  5.3301 -            /* Read from CR/DR. */
  5.3302 -            dst.type  = OP_REG;
  5.3303 -            dst.bytes = mode_64bit() ? 8 : 4;
  5.3304 -            dst.reg   = decode_register(modrm_rm, &_regs, 0);
  5.3305 -            rc = ((b & 1)
  5.3306 -                  ? (ops->read_dr
  5.3307 -                     ? ops->read_dr(modrm_reg, &dst.val, ctxt)
  5.3308 -                     : X86EMUL_UNHANDLEABLE)
  5.3309 -                  : (ops->read_cr
  5.3310 -                     ? ops->read_cr(modrm_reg, &dst.val, ctxt)
  5.3311 -                     : X86EMUL_UNHANDLEABLE));
  5.3312 -        }
  5.3313 -        if ( rc != 0 )
  5.3314 -            goto done;
  5.3315 -        break;
  5.3316 -
  5.3317 -    case 0x30: /* wrmsr */ {
  5.3318 -        uint64_t val = ((uint64_t)_regs.edx << 32) | (uint32_t)_regs.eax;
  5.3319 -        generate_exception_if(!mode_ring0(), EXC_GP, 0);
  5.3320 -        fail_if(ops->write_msr == NULL);
  5.3321 -        if ( (rc = ops->write_msr((uint32_t)_regs.ecx, val, ctxt)) != 0 )
  5.3322 -            goto done;
  5.3323 -        break;
  5.3324 -    }
  5.3325 -
  5.3326 -    case 0x31: /* rdtsc */ {
  5.3327 -        unsigned long cr4;
  5.3328 -        uint64_t val;
  5.3329 -        fail_if(ops->read_cr == NULL);
  5.3330 -        if ( (rc = ops->read_cr(4, &cr4, ctxt)) )
  5.3331 -            goto done;
  5.3332 -        generate_exception_if((cr4 & CR4_TSD) && !mode_ring0(), EXC_GP, 0);
  5.3333 -        fail_if(ops->read_msr == NULL);
  5.3334 -        if ( (rc = ops->read_msr(MSR_TSC, &val, ctxt)) != 0 )
  5.3335 -            goto done;
  5.3336 -        _regs.edx = (uint32_t)(val >> 32);
  5.3337 -        _regs.eax = (uint32_t)(val >>  0);
  5.3338 -        break;
  5.3339 -    }
  5.3340 -
  5.3341 -    case 0x32: /* rdmsr */ {
  5.3342 -        uint64_t val;
  5.3343 -        generate_exception_if(!mode_ring0(), EXC_GP, 0);
  5.3344 -        fail_if(ops->read_msr == NULL);
  5.3345 -        if ( (rc = ops->read_msr((uint32_t)_regs.ecx, &val, ctxt)) != 0 )
  5.3346 -            goto done;
  5.3347 -        _regs.edx = (uint32_t)(val >> 32);
  5.3348 -        _regs.eax = (uint32_t)(val >>  0);
  5.3349 -        break;
  5.3350 -    }
  5.3351 -
  5.3352 -    case 0x80 ... 0x8f: /* jcc (near) */ {
  5.3353 -        int rel = (((op_bytes == 2) && !mode_64bit())
  5.3354 -                   ? (int32_t)insn_fetch_type(int16_t)
  5.3355 -                   : insn_fetch_type(int32_t));
  5.3356 -        if ( test_cc(b, _regs.eflags) )
  5.3357 -            jmp_rel(rel);
  5.3358 -        break;
  5.3359 -    }
  5.3360 -
  5.3361 -    case 0xa0: /* push %%fs */
  5.3362 -        src.val = x86_seg_fs;
  5.3363 -        goto push_seg;
  5.3364 -
  5.3365 -    case 0xa1: /* pop %%fs */
  5.3366 -        src.val = x86_seg_fs;
  5.3367 -        goto pop_seg;
  5.3368 -
  5.3369 -    case 0xa2: /* cpuid */ {
  5.3370 -        unsigned int eax = _regs.eax, ebx = _regs.ebx;
  5.3371 -        unsigned int ecx = _regs.ecx, edx = _regs.edx;
  5.3372 -        fail_if(ops->cpuid == NULL);
  5.3373 -        if ( (rc = ops->cpuid(&eax, &ebx, &ecx, &edx, ctxt)) != 0 )
  5.3374 -            goto done;
  5.3375 -        _regs.eax = eax; _regs.ebx = ebx;
  5.3376 -        _regs.ecx = ecx; _regs.edx = edx;
  5.3377 -        break;
  5.3378 -    }
  5.3379 -
  5.3380 -    case 0xa8: /* push %%gs */
  5.3381 -        src.val = x86_seg_gs;
  5.3382 -        goto push_seg;
  5.3383 -
  5.3384 -    case 0xa9: /* pop %%gs */
  5.3385 -        src.val = x86_seg_gs;
  5.3386 -        goto pop_seg;
  5.3387 -
  5.3388 -    case 0xc7: /* Grp9 (cmpxchg8b) */
  5.3389 -#if defined(__i386__)
  5.3390 -    {
  5.3391 -        unsigned long old_lo, old_hi;
  5.3392 -        generate_exception_if((modrm_reg & 7) != 1, EXC_UD, -1);
  5.3393 -        generate_exception_if(ea.type != OP_MEM, EXC_UD, -1);
  5.3394 -        if ( (rc = ops->read(ea.mem.seg, ea.mem.off+0, &old_lo, 4, ctxt)) ||
  5.3395 -             (rc = ops->read(ea.mem.seg, ea.mem.off+4, &old_hi, 4, ctxt)) )
  5.3396 -            goto done;
  5.3397 -        if ( (old_lo != _regs.eax) || (old_hi != _regs.edx) )
  5.3398 -        {
  5.3399 -            _regs.eax = old_lo;
  5.3400 -            _regs.edx = old_hi;
  5.3401 -            _regs.eflags &= ~EFLG_ZF;
  5.3402 -        }
  5.3403 -        else if ( ops->cmpxchg8b == NULL )
  5.3404 -        {
  5.3405 -            rc = X86EMUL_UNHANDLEABLE;
  5.3406 -            goto done;
  5.3407 -        }
  5.3408 -        else
  5.3409 -        {
  5.3410 -            if ( (rc = ops->cmpxchg8b(ea.mem.seg, ea.mem.off, old_lo, old_hi,
  5.3411 -                                      _regs.ebx, _regs.ecx, ctxt)) != 0 )
  5.3412 -                goto done;
  5.3413 -            _regs.eflags |= EFLG_ZF;
  5.3414 -        }
  5.3415 -        break;
  5.3416 -    }
  5.3417 -#elif defined(__x86_64__)
  5.3418 -    {
  5.3419 -        unsigned long old, new;
  5.3420 -        generate_exception_if((modrm_reg & 7) != 1, EXC_UD, -1);
  5.3421 -        generate_exception_if(ea.type != OP_MEM, EXC_UD, -1);
  5.3422 -        if ( (rc = ops->read(ea.mem.seg, ea.mem.off, &old, 8, ctxt)) != 0 )
  5.3423 -            goto done;
  5.3424 -        if ( ((uint32_t)(old>>0) != (uint32_t)_regs.eax) ||
  5.3425 -             ((uint32_t)(old>>32) != (uint32_t)_regs.edx) )
  5.3426 -        {
  5.3427 -            _regs.eax = (uint32_t)(old>>0);
  5.3428 -            _regs.edx = (uint32_t)(old>>32);
  5.3429 -            _regs.eflags &= ~EFLG_ZF;
  5.3430 -        }
  5.3431 -        else
  5.3432 -        {
  5.3433 -            new = (_regs.ecx<<32)|(uint32_t)_regs.ebx;
  5.3434 -            if ( (rc = ops->cmpxchg(ea.mem.seg, ea.mem.off, old,
  5.3435 -                                    new, 8, ctxt)) != 0 )
  5.3436 -                goto done;
  5.3437 -            _regs.eflags |= EFLG_ZF;
  5.3438 -        }
  5.3439 -        break;
  5.3440 -    }
  5.3441 -#endif
  5.3442 -
  5.3443 -    case 0xc8 ... 0xcf: /* bswap */
  5.3444 -        dst.type = OP_REG;
  5.3445 -        dst.reg  = decode_register(
  5.3446 -            (b & 7) | ((rex_prefix & 1) << 3), &_regs, 0);
  5.3447 -        switch ( dst.bytes = op_bytes )
  5.3448 -        {
  5.3449 -        default: /* case 2: */
  5.3450 -            /* Undefined behaviour. Writes zero on all tested CPUs. */
  5.3451 -            dst.val = 0;
  5.3452 -            break;
  5.3453 -        case 4:
  5.3454 -#ifdef __x86_64__
  5.3455 -            asm ( "bswap %k0" : "=r" (dst.val) : "0" (*dst.reg) );
  5.3456 -            break;
  5.3457 -        case 8:
  5.3458 -#endif
  5.3459 -            asm ( "bswap %0" : "=r" (dst.val) : "0" (*dst.reg) );
  5.3460 -            break;
  5.3461 -        }
  5.3462 -        break;
  5.3463 -    }
  5.3464 -    goto writeback;
  5.3465 -
  5.3466 - cannot_emulate:
  5.3467 -#if 0
  5.3468 -    gdprintk(XENLOG_DEBUG, "Instr:");
  5.3469 -    for ( ea.mem.off = ctxt->regs->eip; ea.mem.off < _regs.eip; ea.mem.off++ )
  5.3470 -    {
  5.3471 -        unsigned long x;
  5.3472 -        ops->insn_fetch(x86_seg_cs, ea.mem.off, &x, 1, ctxt);
  5.3473 -        printk(" %02x", (uint8_t)x);
  5.3474 -    }
  5.3475 -    printk("\n");
  5.3476 -#endif
  5.3477 -    return X86EMUL_UNHANDLEABLE;
  5.3478 -}
  5.3479 +#include "x86_emulate/x86_emulate.c"
     6.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     6.2 +++ b/xen/arch/x86/x86_emulate/x86_emulate.c	Mon Mar 31 14:21:13 2008 +0100
     6.3 @@ -0,0 +1,3429 @@
     6.4 +/******************************************************************************
     6.5 + * x86_emulate.c
     6.6 + * 
     6.7 + * Generic x86 (32-bit and 64-bit) instruction decoder and emulator.
     6.8 + * 
     6.9 + * Copyright (c) 2005-2007 Keir Fraser
    6.10 + * Copyright (c) 2005-2007 XenSource Inc.
    6.11 + * 
    6.12 + * This program is free software; you can redistribute it and/or modify
    6.13 + * it under the terms of the GNU General Public License as published by
    6.14 + * the Free Software Foundation; either version 2 of the License, or
    6.15 + * (at your option) any later version.
    6.16 + * 
    6.17 + * This program is distributed in the hope that it will be useful,
    6.18 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
    6.19 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    6.20 + * GNU General Public License for more details.
    6.21 + * 
    6.22 + * You should have received a copy of the GNU General Public License
    6.23 + * along with this program; if not, write to the Free Software
    6.24 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
    6.25 + */
    6.26 +
    6.27 +/* Operand sizes: 8-bit operands or specified/overridden size. */
    6.28 +#define ByteOp      (1<<0) /* 8-bit operands. */
    6.29 +/* Destination operand type. */
    6.30 +#define DstBitBase  (0<<1) /* Memory operand, bit string. */
    6.31 +#define ImplicitOps (1<<1) /* Implicit in opcode. No generic decode. */
    6.32 +#define DstReg      (2<<1) /* Register operand. */
    6.33 +#define DstMem      (3<<1) /* Memory operand. */
    6.34 +#define DstMask     (3<<1)
    6.35 +/* Source operand type. */
    6.36 +#define SrcNone     (0<<3) /* No source operand. */
    6.37 +#define SrcImplicit (0<<3) /* Source operand is implicit in the opcode. */
    6.38 +#define SrcReg      (1<<3) /* Register operand. */
    6.39 +#define SrcMem      (2<<3) /* Memory operand. */
    6.40 +#define SrcMem16    (3<<3) /* Memory operand (16-bit). */
    6.41 +#define SrcImm      (4<<3) /* Immediate operand. */
    6.42 +#define SrcImmByte  (5<<3) /* 8-bit sign-extended immediate operand. */
    6.43 +#define SrcMask     (7<<3)
    6.44 +/* Generic ModRM decode. */
    6.45 +#define ModRM       (1<<6)
    6.46 +/* Destination is only written; never read. */
    6.47 +#define Mov         (1<<7)
    6.48 +
    6.49 +static uint8_t opcode_table[256] = {
    6.50 +    /* 0x00 - 0x07 */
    6.51 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    6.52 +    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    6.53 +    ByteOp|DstReg|SrcImm, DstReg|SrcImm, ImplicitOps, ImplicitOps,
    6.54 +    /* 0x08 - 0x0F */
    6.55 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    6.56 +    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    6.57 +    ByteOp|DstReg|SrcImm, DstReg|SrcImm, ImplicitOps, 0,
    6.58 +    /* 0x10 - 0x17 */
    6.59 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    6.60 +    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    6.61 +    ByteOp|DstReg|SrcImm, DstReg|SrcImm, ImplicitOps, ImplicitOps,
    6.62 +    /* 0x18 - 0x1F */
    6.63 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    6.64 +    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    6.65 +    ByteOp|DstReg|SrcImm, DstReg|SrcImm, ImplicitOps, ImplicitOps,
    6.66 +    /* 0x20 - 0x27 */
    6.67 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    6.68 +    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    6.69 +    ByteOp|DstReg|SrcImm, DstReg|SrcImm, 0, ImplicitOps,
    6.70 +    /* 0x28 - 0x2F */
    6.71 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    6.72 +    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    6.73 +    ByteOp|DstReg|SrcImm, DstReg|SrcImm, 0, ImplicitOps,
    6.74 +    /* 0x30 - 0x37 */
    6.75 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    6.76 +    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    6.77 +    ByteOp|DstReg|SrcImm, DstReg|SrcImm, 0, ImplicitOps,
    6.78 +    /* 0x38 - 0x3F */
    6.79 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
    6.80 +    ByteOp|DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
    6.81 +    ByteOp|DstReg|SrcImm, DstReg|SrcImm, 0, ImplicitOps,
    6.82 +    /* 0x40 - 0x4F */
    6.83 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
    6.84 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
    6.85 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
    6.86 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
    6.87 +    /* 0x50 - 0x5F */
    6.88 +    ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov,
    6.89 +    ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov,
    6.90 +    ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov,
    6.91 +    ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov,
    6.92 +    /* 0x60 - 0x67 */
    6.93 +    ImplicitOps, ImplicitOps, DstReg|SrcMem|ModRM, DstReg|SrcMem16|ModRM|Mov,
    6.94 +    0, 0, 0, 0,
    6.95 +    /* 0x68 - 0x6F */
    6.96 +    ImplicitOps|Mov, DstReg|SrcImm|ModRM|Mov,
    6.97 +    ImplicitOps|Mov, DstReg|SrcImmByte|ModRM|Mov,
    6.98 +    ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov, ImplicitOps|Mov,
    6.99 +    /* 0x70 - 0x77 */
   6.100 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.101 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.102 +    /* 0x78 - 0x7F */
   6.103 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.104 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.105 +    /* 0x80 - 0x87 */
   6.106 +    ByteOp|DstMem|SrcImm|ModRM, DstMem|SrcImm|ModRM,
   6.107 +    ByteOp|DstMem|SrcImm|ModRM, DstMem|SrcImmByte|ModRM,
   6.108 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
   6.109 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
   6.110 +    /* 0x88 - 0x8F */
   6.111 +    ByteOp|DstMem|SrcReg|ModRM|Mov, DstMem|SrcReg|ModRM|Mov,
   6.112 +    ByteOp|DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   6.113 +    DstMem|SrcReg|ModRM|Mov, DstReg|SrcNone|ModRM,
   6.114 +    DstReg|SrcMem|ModRM|Mov, DstMem|SrcNone|ModRM|Mov,
   6.115 +    /* 0x90 - 0x97 */
   6.116 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.117 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.118 +    /* 0x98 - 0x9F */
   6.119 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.120 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.121 +    /* 0xA0 - 0xA7 */
   6.122 +    ByteOp|ImplicitOps|Mov, ImplicitOps|Mov,
   6.123 +    ByteOp|ImplicitOps|Mov, ImplicitOps|Mov,
   6.124 +    ByteOp|ImplicitOps|Mov, ImplicitOps|Mov,
   6.125 +    ByteOp|ImplicitOps, ImplicitOps,
   6.126 +    /* 0xA8 - 0xAF */
   6.127 +    ByteOp|DstReg|SrcImm, DstReg|SrcImm,
   6.128 +    ByteOp|ImplicitOps|Mov, ImplicitOps|Mov,
   6.129 +    ByteOp|ImplicitOps|Mov, ImplicitOps|Mov,
   6.130 +    ByteOp|ImplicitOps, ImplicitOps,
   6.131 +    /* 0xB0 - 0xB7 */
   6.132 +    ByteOp|DstReg|SrcImm|Mov, ByteOp|DstReg|SrcImm|Mov,
   6.133 +    ByteOp|DstReg|SrcImm|Mov, ByteOp|DstReg|SrcImm|Mov,
   6.134 +    ByteOp|DstReg|SrcImm|Mov, ByteOp|DstReg|SrcImm|Mov,
   6.135 +    ByteOp|DstReg|SrcImm|Mov, ByteOp|DstReg|SrcImm|Mov,
   6.136 +    /* 0xB8 - 0xBF */
   6.137 +    DstReg|SrcImm|Mov, DstReg|SrcImm|Mov, DstReg|SrcImm|Mov, DstReg|SrcImm|Mov,
   6.138 +    DstReg|SrcImm|Mov, DstReg|SrcImm|Mov, DstReg|SrcImm|Mov, DstReg|SrcImm|Mov,
   6.139 +    /* 0xC0 - 0xC7 */
   6.140 +    ByteOp|DstMem|SrcImm|ModRM, DstMem|SrcImmByte|ModRM,
   6.141 +    ImplicitOps, ImplicitOps,
   6.142 +    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   6.143 +    ByteOp|DstMem|SrcImm|ModRM|Mov, DstMem|SrcImm|ModRM|Mov,
   6.144 +    /* 0xC8 - 0xCF */
   6.145 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.146 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.147 +    /* 0xD0 - 0xD7 */
   6.148 +    ByteOp|DstMem|SrcImplicit|ModRM, DstMem|SrcImplicit|ModRM, 
   6.149 +    ByteOp|DstMem|SrcImplicit|ModRM, DstMem|SrcImplicit|ModRM, 
   6.150 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.151 +    /* 0xD8 - 0xDF */
   6.152 +    0, ImplicitOps|ModRM|Mov, 0, ImplicitOps|ModRM|Mov,
   6.153 +    0, ImplicitOps|ModRM|Mov, ImplicitOps|ModRM|Mov, ImplicitOps|ModRM|Mov,
   6.154 +    /* 0xE0 - 0xE7 */
   6.155 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.156 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.157 +    /* 0xE8 - 0xEF */
   6.158 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.159 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.160 +    /* 0xF0 - 0xF7 */
   6.161 +    0, ImplicitOps, 0, 0,
   6.162 +    ImplicitOps, ImplicitOps,
   6.163 +    ByteOp|DstMem|SrcNone|ModRM, DstMem|SrcNone|ModRM,
   6.164 +    /* 0xF8 - 0xFF */
   6.165 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.166 +    ImplicitOps, ImplicitOps, ByteOp|DstMem|SrcNone|ModRM, DstMem|SrcNone|ModRM
   6.167 +};
   6.168 +
   6.169 +static uint8_t twobyte_table[256] = {
   6.170 +    /* 0x00 - 0x07 */
   6.171 +    0, ImplicitOps|ModRM, 0, 0, 0, 0, ImplicitOps, 0,
   6.172 +    /* 0x08 - 0x0F */
   6.173 +    ImplicitOps, ImplicitOps, 0, 0, 0, ImplicitOps|ModRM, 0, 0,
   6.174 +    /* 0x10 - 0x17 */
   6.175 +    0, 0, 0, 0, 0, 0, 0, 0,
   6.176 +    /* 0x18 - 0x1F */
   6.177 +    ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM,
   6.178 +    ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM,
   6.179 +    /* 0x20 - 0x27 */
   6.180 +    ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM, ImplicitOps|ModRM,
   6.181 +    0, 0, 0, 0,
   6.182 +    /* 0x28 - 0x2F */
   6.183 +    0, 0, 0, 0, 0, 0, 0, 0,
   6.184 +    /* 0x30 - 0x37 */
   6.185 +    ImplicitOps, ImplicitOps, ImplicitOps, 0, 0, 0, 0, 0,
   6.186 +    /* 0x38 - 0x3F */
   6.187 +    0, 0, 0, 0, 0, 0, 0, 0,
   6.188 +    /* 0x40 - 0x47 */
   6.189 +    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   6.190 +    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   6.191 +    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   6.192 +    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   6.193 +    /* 0x48 - 0x4F */
   6.194 +    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   6.195 +    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   6.196 +    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   6.197 +    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   6.198 +    /* 0x50 - 0x5F */
   6.199 +    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
   6.200 +    /* 0x60 - 0x6F */
   6.201 +    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
   6.202 +    /* 0x70 - 0x7F */
   6.203 +    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
   6.204 +    /* 0x80 - 0x87 */
   6.205 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.206 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.207 +    /* 0x88 - 0x8F */
   6.208 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.209 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.210 +    /* 0x90 - 0x97 */
   6.211 +    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   6.212 +    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   6.213 +    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   6.214 +    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   6.215 +    /* 0x98 - 0x9F */
   6.216 +    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   6.217 +    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   6.218 +    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   6.219 +    ByteOp|DstMem|SrcNone|ModRM|Mov, ByteOp|DstMem|SrcNone|ModRM|Mov,
   6.220 +    /* 0xA0 - 0xA7 */
   6.221 +    ImplicitOps, ImplicitOps, ImplicitOps, DstBitBase|SrcReg|ModRM,
   6.222 +    DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM, 0, 0, 
   6.223 +    /* 0xA8 - 0xAF */
   6.224 +    ImplicitOps, ImplicitOps, 0, DstBitBase|SrcReg|ModRM,
   6.225 +    DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM, 0, DstReg|SrcMem|ModRM,
   6.226 +    /* 0xB0 - 0xB7 */
   6.227 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM,
   6.228 +    DstReg|SrcMem|ModRM|Mov, DstBitBase|SrcReg|ModRM,
   6.229 +    DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem|ModRM|Mov,
   6.230 +    ByteOp|DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem16|ModRM|Mov,
   6.231 +    /* 0xB8 - 0xBF */
   6.232 +    0, 0, DstBitBase|SrcImmByte|ModRM, DstBitBase|SrcReg|ModRM,
   6.233 +    DstReg|SrcMem|ModRM, DstReg|SrcMem|ModRM,
   6.234 +    ByteOp|DstReg|SrcMem|ModRM|Mov, DstReg|SrcMem16|ModRM|Mov,
   6.235 +    /* 0xC0 - 0xC7 */
   6.236 +    ByteOp|DstMem|SrcReg|ModRM, DstMem|SrcReg|ModRM, 0, 0,
   6.237 +    0, 0, 0, ImplicitOps|ModRM,
   6.238 +    /* 0xC8 - 0xCF */
   6.239 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.240 +    ImplicitOps, ImplicitOps, ImplicitOps, ImplicitOps,
   6.241 +    /* 0xD0 - 0xDF */
   6.242 +    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
   6.243 +    /* 0xE0 - 0xEF */
   6.244 +    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
   6.245 +    /* 0xF0 - 0xFF */
   6.246 +    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
   6.247 +};
   6.248 +
   6.249 +/* Type, address-of, and value of an instruction's operand. */
   6.250 +struct operand {
   6.251 +    enum { OP_REG, OP_MEM, OP_IMM, OP_NONE } type;
   6.252 +    unsigned int  bytes;
   6.253 +    unsigned long val, orig_val;
   6.254 +    union {
   6.255 +        /* OP_REG: Pointer to register field. */
   6.256 +        unsigned long *reg;
   6.257 +        /* OP_MEM: Segment and offset. */
   6.258 +        struct {
   6.259 +            enum x86_segment seg;
   6.260 +            unsigned long    off;
   6.261 +        } mem;
   6.262 +    };
   6.263 +};
   6.264 +
   6.265 +/* MSRs. */
   6.266 +#define MSR_TSC   0x10
   6.267 +
   6.268 +/* Control register flags. */
   6.269 +#define CR0_PE    (1<<0)
   6.270 +#define CR4_TSD   (1<<2)
   6.271 +
   6.272 +/* EFLAGS bit definitions. */
   6.273 +#define EFLG_VIP  (1<<20)
   6.274 +#define EFLG_VIF  (1<<19)
   6.275 +#define EFLG_AC   (1<<18)
   6.276 +#define EFLG_VM   (1<<17)
   6.277 +#define EFLG_RF   (1<<16)
   6.278 +#define EFLG_NT   (1<<14)
   6.279 +#define EFLG_IOPL (3<<12)
   6.280 +#define EFLG_OF   (1<<11)
   6.281 +#define EFLG_DF   (1<<10)
   6.282 +#define EFLG_IF   (1<<9)
   6.283 +#define EFLG_TF   (1<<8)
   6.284 +#define EFLG_SF   (1<<7)
   6.285 +#define EFLG_ZF   (1<<6)
   6.286 +#define EFLG_AF   (1<<4)
   6.287 +#define EFLG_PF   (1<<2)
   6.288 +#define EFLG_CF   (1<<0)
   6.289 +
   6.290 +/* Exception definitions. */
   6.291 +#define EXC_DE  0
   6.292 +#define EXC_DB  1
   6.293 +#define EXC_BP  3
   6.294 +#define EXC_OF  4
   6.295 +#define EXC_BR  5
   6.296 +#define EXC_UD  6
   6.297 +#define EXC_TS 10
   6.298 +#define EXC_NP 11
   6.299 +#define EXC_SS 12
   6.300 +#define EXC_GP 13
   6.301 +#define EXC_PF 14
   6.302 +#define EXC_MF 16
   6.303 +
   6.304 +/*
   6.305 + * Instruction emulation:
   6.306 + * Most instructions are emulated directly via a fragment of inline assembly
   6.307 + * code. This allows us to save/restore EFLAGS and thus very easily pick up
   6.308 + * any modified flags.
   6.309 + */
   6.310 +
   6.311 +#if defined(__x86_64__)
   6.312 +#define _LO32 "k"          /* force 32-bit operand */
   6.313 +#define _STK  "%%rsp"      /* stack pointer */
   6.314 +#define _BYTES_PER_LONG "8"
   6.315 +#elif defined(__i386__)
   6.316 +#define _LO32 ""           /* force 32-bit operand */
   6.317 +#define _STK  "%%esp"      /* stack pointer */
   6.318 +#define _BYTES_PER_LONG "4"
   6.319 +#endif
   6.320 +
   6.321 +/*
   6.322 + * These EFLAGS bits are restored from saved value during emulation, and
   6.323 + * any changes are written back to the saved value after emulation.
   6.324 + */
   6.325 +#define EFLAGS_MASK (EFLG_OF|EFLG_SF|EFLG_ZF|EFLG_AF|EFLG_PF|EFLG_CF)
   6.326 +
   6.327 +/* Before executing instruction: restore necessary bits in EFLAGS. */
   6.328 +#define _PRE_EFLAGS(_sav, _msk, _tmp)                           \
   6.329 +/* EFLAGS = (_sav & _msk) | (EFLAGS & ~_msk); _sav &= ~_msk; */ \
   6.330 +"movl %"_sav",%"_LO32 _tmp"; "                                  \
   6.331 +"push %"_tmp"; "                                                \
   6.332 +"push %"_tmp"; "                                                \
   6.333 +"movl %"_msk",%"_LO32 _tmp"; "                                  \
   6.334 +"andl %"_LO32 _tmp",("_STK"); "                                 \
   6.335 +"pushf; "                                                       \
   6.336 +"notl %"_LO32 _tmp"; "                                          \
   6.337 +"andl %"_LO32 _tmp",("_STK"); "                                 \
   6.338 +"andl %"_LO32 _tmp",2*"_BYTES_PER_LONG"("_STK"); "              \
   6.339 +"pop  %"_tmp"; "                                                \
   6.340 +"orl  %"_LO32 _tmp",("_STK"); "                                 \
   6.341 +"popf; "                                                        \
   6.342 +"pop  %"_sav"; "
   6.343 +
   6.344 +/* After executing instruction: write-back necessary bits in EFLAGS. */
   6.345 +#define _POST_EFLAGS(_sav, _msk, _tmp)          \
   6.346 +/* _sav |= EFLAGS & _msk; */                    \
   6.347 +"pushf; "                                       \
   6.348 +"pop  %"_tmp"; "                                \
   6.349 +"andl %"_msk",%"_LO32 _tmp"; "                  \
   6.350 +"orl  %"_LO32 _tmp",%"_sav"; "
   6.351 +
   6.352 +/* Raw emulation: instruction has two explicit operands. */
   6.353 +#define __emulate_2op_nobyte(_op,_src,_dst,_eflags,_wx,_wy,_lx,_ly,_qx,_qy)\
   6.354 +do{ unsigned long _tmp;                                                    \
   6.355 +    switch ( (_dst).bytes )                                                \
   6.356 +    {                                                                      \
   6.357 +    case 2:                                                                \
   6.358 +        asm volatile (                                                     \
   6.359 +            _PRE_EFLAGS("0","4","2")                                       \
   6.360 +            _op"w %"_wx"3,%1; "                                            \
   6.361 +            _POST_EFLAGS("0","4","2")                                      \
   6.362 +            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   6.363 +            : _wy ((_src).val), "i" (EFLAGS_MASK),                         \
   6.364 +              "m" (_eflags), "m" ((_dst).val) );                           \
   6.365 +        break;                                                             \
   6.366 +    case 4:                                                                \
   6.367 +        asm volatile (                                                     \
   6.368 +            _PRE_EFLAGS("0","4","2")                                       \
   6.369 +            _op"l %"_lx"3,%1; "                                            \
   6.370 +            _POST_EFLAGS("0","4","2")                                      \
   6.371 +            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   6.372 +            : _ly ((_src).val), "i" (EFLAGS_MASK),                         \
   6.373 +              "m" (_eflags), "m" ((_dst).val) );                           \
   6.374 +        break;                                                             \
   6.375 +    case 8:                                                                \
   6.376 +        __emulate_2op_8byte(_op, _src, _dst, _eflags, _qx, _qy);           \
   6.377 +        break;                                                             \
   6.378 +    }                                                                      \
   6.379 +} while (0)
   6.380 +#define __emulate_2op(_op,_src,_dst,_eflags,_bx,_by,_wx,_wy,_lx,_ly,_qx,_qy)\
   6.381 +do{ unsigned long _tmp;                                                    \
   6.382 +    switch ( (_dst).bytes )                                                \
   6.383 +    {                                                                      \
   6.384 +    case 1:                                                                \
   6.385 +        asm volatile (                                                     \
   6.386 +            _PRE_EFLAGS("0","4","2")                                       \
   6.387 +            _op"b %"_bx"3,%1; "                                            \
   6.388 +            _POST_EFLAGS("0","4","2")                                      \
   6.389 +            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   6.390 +            : _by ((_src).val), "i" (EFLAGS_MASK),                         \
   6.391 +              "m" (_eflags), "m" ((_dst).val) );                           \
   6.392 +        break;                                                             \
   6.393 +    default:                                                               \
   6.394 +        __emulate_2op_nobyte(_op,_src,_dst,_eflags,_wx,_wy,_lx,_ly,_qx,_qy);\
   6.395 +        break;                                                             \
   6.396 +    }                                                                      \
   6.397 +} while (0)
   6.398 +/* Source operand is byte-sized and may be restricted to just %cl. */
   6.399 +#define emulate_2op_SrcB(_op, _src, _dst, _eflags)                         \
   6.400 +    __emulate_2op(_op, _src, _dst, _eflags,                                \
   6.401 +                  "b", "c", "b", "c", "b", "c", "b", "c")
   6.402 +/* Source operand is byte, word, long or quad sized. */
   6.403 +#define emulate_2op_SrcV(_op, _src, _dst, _eflags)                         \
   6.404 +    __emulate_2op(_op, _src, _dst, _eflags,                                \
   6.405 +                  "b", "q", "w", "r", _LO32, "r", "", "r")
   6.406 +/* Source operand is word, long or quad sized. */
   6.407 +#define emulate_2op_SrcV_nobyte(_op, _src, _dst, _eflags)                  \
   6.408 +    __emulate_2op_nobyte(_op, _src, _dst, _eflags,                         \
   6.409 +                  "w", "r", _LO32, "r", "", "r")
   6.410 +
   6.411 +/* Instruction has only one explicit operand (no source operand). */
   6.412 +#define emulate_1op(_op,_dst,_eflags)                                      \
   6.413 +do{ unsigned long _tmp;                                                    \
   6.414 +    switch ( (_dst).bytes )                                                \
   6.415 +    {                                                                      \
   6.416 +    case 1:                                                                \
   6.417 +        asm volatile (                                                     \
   6.418 +            _PRE_EFLAGS("0","3","2")                                       \
   6.419 +            _op"b %1; "                                                    \
   6.420 +            _POST_EFLAGS("0","3","2")                                      \
   6.421 +            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   6.422 +            : "i" (EFLAGS_MASK), "m" (_eflags), "m" ((_dst).val) );        \
   6.423 +        break;                                                             \
   6.424 +    case 2:                                                                \
   6.425 +        asm volatile (                                                     \
   6.426 +            _PRE_EFLAGS("0","3","2")                                       \
   6.427 +            _op"w %1; "                                                    \
   6.428 +            _POST_EFLAGS("0","3","2")                                      \
   6.429 +            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   6.430 +            : "i" (EFLAGS_MASK), "m" (_eflags), "m" ((_dst).val) );        \
   6.431 +        break;                                                             \
   6.432 +    case 4:                                                                \
   6.433 +        asm volatile (                                                     \
   6.434 +            _PRE_EFLAGS("0","3","2")                                       \
   6.435 +            _op"l %1; "                                                    \
   6.436 +            _POST_EFLAGS("0","3","2")                                      \
   6.437 +            : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)              \
   6.438 +            : "i" (EFLAGS_MASK), "m" (_eflags), "m" ((_dst).val) );        \
   6.439 +        break;                                                             \
   6.440 +    case 8:                                                                \
   6.441 +        __emulate_1op_8byte(_op, _dst, _eflags);                           \
   6.442 +        break;                                                             \
   6.443 +    }                                                                      \
   6.444 +} while (0)
   6.445 +
   6.446 +/* Emulate an instruction with quadword operands (x86/64 only). */
   6.447 +#if defined(__x86_64__)
   6.448 +#define __emulate_2op_8byte(_op, _src, _dst, _eflags, _qx, _qy)         \
   6.449 +do{ asm volatile (                                                      \
   6.450 +        _PRE_EFLAGS("0","4","2")                                        \
   6.451 +        _op"q %"_qx"3,%1; "                                             \
   6.452 +        _POST_EFLAGS("0","4","2")                                       \
   6.453 +        : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)               \
   6.454 +        : _qy ((_src).val), "i" (EFLAGS_MASK),                          \
   6.455 +          "m" (_eflags), "m" ((_dst).val) );                            \
   6.456 +} while (0)
   6.457 +#define __emulate_1op_8byte(_op, _dst, _eflags)                         \
   6.458 +do{ asm volatile (                                                      \
   6.459 +        _PRE_EFLAGS("0","3","2")                                        \
   6.460 +        _op"q %1; "                                                     \
   6.461 +        _POST_EFLAGS("0","3","2")                                       \
   6.462 +        : "=m" (_eflags), "=m" ((_dst).val), "=&r" (_tmp)               \
   6.463 +        : "i" (EFLAGS_MASK), "m" (_eflags), "m" ((_dst).val) );         \
   6.464 +} while (0)
   6.465 +#elif defined(__i386__)
   6.466 +#define __emulate_2op_8byte(_op, _src, _dst, _eflags, _qx, _qy)
   6.467 +#define __emulate_1op_8byte(_op, _dst, _eflags)
   6.468 +#endif /* __i386__ */
   6.469 +
   6.470 +/* Fetch next part of the instruction being emulated. */
   6.471 +#define insn_fetch_bytes(_size)                                         \
   6.472 +({ unsigned long _x, _eip = _regs.eip;                                  \
   6.473 +   if ( !mode_64bit() ) _eip = (uint32_t)_eip; /* ignore upper dword */ \
   6.474 +   _regs.eip += (_size); /* real hardware doesn't truncate */           \
   6.475 +   generate_exception_if((uint8_t)(_regs.eip - ctxt->regs->eip) > 15,   \
   6.476 +                         EXC_GP, 0);                                    \
   6.477 +   rc = ops->insn_fetch(x86_seg_cs, _eip, &_x, (_size), ctxt);          \
   6.478 +   if ( rc ) goto done;                                                 \
   6.479 +   _x;                                                                  \
   6.480 +})
   6.481 +#define insn_fetch_type(_type) ((_type)insn_fetch_bytes(sizeof(_type)))
   6.482 +
   6.483 +#define truncate_word(ea, byte_width)           \
   6.484 +({  unsigned long __ea = (ea);                  \
   6.485 +    unsigned int _width = (byte_width);         \
   6.486 +    ((_width == sizeof(unsigned long)) ? __ea : \
   6.487 +     (__ea & ((1UL << (_width << 3)) - 1)));    \
   6.488 +})
   6.489 +#define truncate_ea(ea) truncate_word((ea), ad_bytes)
   6.490 +
   6.491 +#define mode_64bit() (def_ad_bytes == 8)
   6.492 +
   6.493 +#define fail_if(p)                                      \
   6.494 +do {                                                    \
   6.495 +    rc = (p) ? X86EMUL_UNHANDLEABLE : X86EMUL_OKAY;     \
   6.496 +    if ( rc ) goto done;                                \
   6.497 +} while (0)
   6.498 +
   6.499 +#define generate_exception_if(p, e, ec)                                   \
   6.500 +({  if ( (p) ) {                                                          \
   6.501 +        fail_if(ops->inject_hw_exception == NULL);                        \
   6.502 +        rc = ops->inject_hw_exception(e, ec, ctxt) ? : X86EMUL_EXCEPTION; \
   6.503 +        goto done;                                                        \
   6.504 +    }                                                                     \
   6.505 +})
   6.506 +
   6.507 +/*
   6.508 + * Given byte has even parity (even number of 1s)? SDM Vol. 1 Sec. 3.4.3.1,
   6.509 + * "Status Flags": EFLAGS.PF reflects parity of least-sig. byte of result only.
   6.510 + */
   6.511 +static int even_parity(uint8_t v)
   6.512 +{
   6.513 +    asm ( "test %b0,%b0; setp %b0" : "=a" (v) : "0" (v) );
   6.514 +    return v;
   6.515 +}
   6.516 +
   6.517 +/* Update address held in a register, based on addressing mode. */
   6.518 +#define _register_address_increment(reg, inc, byte_width)               \
   6.519 +do {                                                                    \
   6.520 +    int _inc = (inc); /* signed type ensures sign extension to long */  \
   6.521 +    unsigned int _width = (byte_width);                                 \
   6.522 +    if ( _width == sizeof(unsigned long) )                              \
   6.523 +        (reg) += _inc;                                                  \
   6.524 +    else if ( mode_64bit() )                                            \
   6.525 +        (reg) = ((reg) + _inc) & ((1UL << (_width << 3)) - 1);          \
   6.526 +    else                                                                \
   6.527 +        (reg) = ((reg) & ~((1UL << (_width << 3)) - 1)) |               \
   6.528 +                (((reg) + _inc) & ((1UL << (_width << 3)) - 1));        \
   6.529 +} while (0)
   6.530 +#define register_address_increment(reg, inc) \
   6.531 +    _register_address_increment((reg), (inc), ad_bytes)
   6.532 +
   6.533 +#define sp_pre_dec(dec) ({                                              \
   6.534 +    _register_address_increment(_regs.esp, -(dec), ctxt->sp_size/8);    \
   6.535 +    truncate_word(_regs.esp, ctxt->sp_size/8);                          \
   6.536 +})
   6.537 +#define sp_post_inc(inc) ({                                             \
   6.538 +    unsigned long __esp = truncate_word(_regs.esp, ctxt->sp_size/8);    \
   6.539 +    _register_address_increment(_regs.esp, (inc), ctxt->sp_size/8);     \
   6.540 +    __esp;                                                              \
   6.541 +})
   6.542 +
   6.543 +#define jmp_rel(rel)                                                    \
   6.544 +do {                                                                    \
   6.545 +    int _rel = (int)(rel);                                              \
   6.546 +    _regs.eip += _rel;                                                  \
   6.547 +    if ( !mode_64bit() )                                                \
   6.548 +        _regs.eip = ((op_bytes == 2)                                    \
   6.549 +                     ? (uint16_t)_regs.eip : (uint32_t)_regs.eip);      \
   6.550 +} while (0)
   6.551 +
   6.552 +static unsigned long __get_rep_prefix(
   6.553 +    struct cpu_user_regs *int_regs,
   6.554 +    struct cpu_user_regs *ext_regs,
   6.555 +    int ad_bytes)
   6.556 +{
   6.557 +    unsigned long ecx = ((ad_bytes == 2) ? (uint16_t)int_regs->ecx :
   6.558 +                         (ad_bytes == 4) ? (uint32_t)int_regs->ecx :
   6.559 +                         int_regs->ecx);
   6.560 +
   6.561 +    /* Skip the instruction if no repetitions are required. */
   6.562 +    if ( ecx == 0 )
   6.563 +        ext_regs->eip = int_regs->eip;
   6.564 +
   6.565 +    return ecx;
   6.566 +}
   6.567 +
   6.568 +#define get_rep_prefix() ({                                             \
   6.569 +    unsigned long max_reps = 1;                                         \
   6.570 +    if ( rep_prefix )                                                   \
   6.571 +        max_reps = __get_rep_prefix(&_regs, ctxt->regs, ad_bytes);      \
   6.572 +    if ( max_reps == 0 )                                                \
   6.573 +        goto done;                                                      \
   6.574 +   max_reps;                                                            \
   6.575 +})
   6.576 +
   6.577 +static void __put_rep_prefix(
   6.578 +    struct cpu_user_regs *int_regs,
   6.579 +    struct cpu_user_regs *ext_regs,
   6.580 +    int ad_bytes,
   6.581 +    unsigned long reps_completed)
   6.582 +{
   6.583 +    unsigned long ecx = ((ad_bytes == 2) ? (uint16_t)int_regs->ecx :
   6.584 +                         (ad_bytes == 4) ? (uint32_t)int_regs->ecx :
   6.585 +                         int_regs->ecx);
   6.586 +
   6.587 +    /* Reduce counter appropriately, and repeat instruction if non-zero. */
   6.588 +    ecx -= reps_completed;
   6.589 +    if ( ecx != 0 )
   6.590 +        int_regs->eip = ext_regs->eip;
   6.591 +
   6.592 +    if ( ad_bytes == 2 )
   6.593 +        *(uint16_t *)&int_regs->ecx = ecx;
   6.594 +    else if ( ad_bytes == 4 )
   6.595 +        int_regs->ecx = (uint32_t)ecx;
   6.596 +    else
   6.597 +        int_regs->ecx = ecx;
   6.598 +}
   6.599 +
   6.600 +#define put_rep_prefix(reps_completed) ({                               \
   6.601 +    if ( rep_prefix )                                                   \
   6.602 +        __put_rep_prefix(&_regs, ctxt->regs, ad_bytes, reps_completed); \
   6.603 +})
   6.604 +
   6.605 +/*
   6.606 + * Unsigned multiplication with double-word result.
   6.607 + * IN:  Multiplicand=m[0], Multiplier=m[1]
   6.608 + * OUT: Return CF/OF (overflow status); Result=m[1]:m[0]
   6.609 + */
   6.610 +static int mul_dbl(unsigned long m[2])
   6.611 +{
   6.612 +    int rc;
   6.613 +    asm ( "mul %4; seto %b2"
   6.614 +          : "=a" (m[0]), "=d" (m[1]), "=q" (rc)
   6.615 +          : "0" (m[0]), "1" (m[1]), "2" (0) );
   6.616 +    return rc;
   6.617 +}
   6.618 +
   6.619 +/*
   6.620 + * Signed multiplication with double-word result.
   6.621 + * IN:  Multiplicand=m[0], Multiplier=m[1]
   6.622 + * OUT: Return CF/OF (overflow status); Result=m[1]:m[0]
   6.623 + */
   6.624 +static int imul_dbl(unsigned long m[2])
   6.625 +{
   6.626 +    int rc;
   6.627 +    asm ( "imul %4; seto %b2"
   6.628 +          : "=a" (m[0]), "=d" (m[1]), "=q" (rc)
   6.629 +          : "0" (m[0]), "1" (m[1]), "2" (0) );
   6.630 +    return rc;
   6.631 +}
   6.632 +
   6.633 +/*
   6.634 + * Unsigned division of double-word dividend.
   6.635 + * IN:  Dividend=u[1]:u[0], Divisor=v
   6.636 + * OUT: Return 1: #DE
   6.637 + *      Return 0: Quotient=u[0], Remainder=u[1]
   6.638 + */
   6.639 +static int div_dbl(unsigned long u[2], unsigned long v)
   6.640 +{
   6.641 +    if ( (v == 0) || (u[1] >= v) )
   6.642 +        return 1;
   6.643 +    asm ( "div %4"
   6.644 +          : "=a" (u[0]), "=d" (u[1])
   6.645 +          : "0" (u[0]), "1" (u[1]), "r" (v) );
   6.646 +    return 0;
   6.647 +}
   6.648 +
   6.649 +/*
   6.650 + * Signed division of double-word dividend.
   6.651 + * IN:  Dividend=u[1]:u[0], Divisor=v
   6.652 + * OUT: Return 1: #DE
   6.653 + *      Return 0: Quotient=u[0], Remainder=u[1]
   6.654 + * NB. We don't use idiv directly as it's moderately hard to work out
   6.655 + *     ahead of time whether it will #DE, which we cannot allow to happen.
   6.656 + */
   6.657 +static int idiv_dbl(unsigned long u[2], unsigned long v)
   6.658 +{
   6.659 +    int negu = (long)u[1] < 0, negv = (long)v < 0;
   6.660 +
   6.661 +    /* u = abs(u) */
   6.662 +    if ( negu )
   6.663 +    {
   6.664 +        u[1] = ~u[1];
   6.665 +        if ( (u[0] = -u[0]) == 0 )
   6.666 +            u[1]++;
   6.667 +    }
   6.668 +
   6.669 +    /* abs(u) / abs(v) */
   6.670 +    if ( div_dbl(u, negv ? -v : v) )
   6.671 +        return 1;
   6.672 +
   6.673 +    /* Remainder has same sign as dividend. It cannot overflow. */
   6.674 +    if ( negu )
   6.675 +        u[1] = -u[1];
   6.676 +
   6.677 +    /* Quotient is overflowed if sign bit is set. */
   6.678 +    if ( negu ^ negv )
   6.679 +    {
   6.680 +        if ( (long)u[0] >= 0 )
   6.681 +            u[0] = -u[0];
   6.682 +        else if ( (u[0] << 1) != 0 ) /* == 0x80...0 is okay */
   6.683 +            return 1;
   6.684 +    }
   6.685 +    else if ( (long)u[0] < 0 )
   6.686 +        return 1;
   6.687 +
   6.688 +    return 0;
   6.689 +}
   6.690 +
   6.691 +static int
   6.692 +test_cc(
   6.693 +    unsigned int condition, unsigned int flags)
   6.694 +{
   6.695 +    int rc = 0;
   6.696 +
   6.697 +    switch ( (condition & 15) >> 1 )
   6.698 +    {
   6.699 +    case 0: /* o */
   6.700 +        rc |= (flags & EFLG_OF);
   6.701 +        break;
   6.702 +    case 1: /* b/c/nae */
   6.703 +        rc |= (flags & EFLG_CF);
   6.704 +        break;
   6.705 +    case 2: /* z/e */
   6.706 +        rc |= (flags & EFLG_ZF);
   6.707 +        break;
   6.708 +    case 3: /* be/na */
   6.709 +        rc |= (flags & (EFLG_CF|EFLG_ZF));
   6.710 +        break;
   6.711 +    case 4: /* s */
   6.712 +        rc |= (flags & EFLG_SF);
   6.713 +        break;
   6.714 +    case 5: /* p/pe */
   6.715 +        rc |= (flags & EFLG_PF);
   6.716 +        break;
   6.717 +    case 7: /* le/ng */
   6.718 +        rc |= (flags & EFLG_ZF);
   6.719 +        /* fall through */
   6.720 +    case 6: /* l/nge */
   6.721 +        rc |= (!(flags & EFLG_SF) != !(flags & EFLG_OF));
   6.722 +        break;
   6.723 +    }
   6.724 +
   6.725 +    /* Odd condition identifiers (lsb == 1) have inverted sense. */
   6.726 +    return (!!rc ^ (condition & 1));
   6.727 +}
   6.728 +
   6.729 +static int
   6.730 +get_cpl(
   6.731 +    struct x86_emulate_ctxt *ctxt,
   6.732 +    struct x86_emulate_ops  *ops)
   6.733 +{
   6.734 +    struct segment_register reg;
   6.735 +
   6.736 +    if ( ctxt->regs->eflags & EFLG_VM )
   6.737 +        return 3;
   6.738 +
   6.739 +    if ( (ops->read_segment == NULL) ||
   6.740 +         ops->read_segment(x86_seg_ss, &reg, ctxt) )
   6.741 +        return -1;
   6.742 +
   6.743 +    return reg.attr.fields.dpl;
   6.744 +}
   6.745 +
   6.746 +static int
   6.747 +_mode_iopl(
   6.748 +    struct x86_emulate_ctxt *ctxt,
   6.749 +    struct x86_emulate_ops  *ops)
   6.750 +{
   6.751 +    int cpl = get_cpl(ctxt, ops);
   6.752 +    if ( cpl == -1 )
   6.753 +        return -1;
   6.754 +    return (cpl <= ((ctxt->regs->eflags >> 12) & 3));
   6.755 +}
   6.756 +
   6.757 +#define mode_ring0() ({                         \
   6.758 +    int _cpl = get_cpl(ctxt, ops);              \
   6.759 +    fail_if(_cpl < 0);                          \
   6.760 +    (_cpl == 0);                                \
   6.761 +})
   6.762 +#define mode_iopl() ({                          \
   6.763 +    int _iopl = _mode_iopl(ctxt, ops);          \
   6.764 +    fail_if(_iopl < 0);                         \
   6.765 +    _iopl;                                      \
   6.766 +})
   6.767 +
   6.768 +static int ioport_access_check(
   6.769 +    unsigned int first_port,
   6.770 +    unsigned int bytes,
   6.771 +    struct x86_emulate_ctxt *ctxt,
   6.772 +    struct x86_emulate_ops *ops)
   6.773 +{
   6.774 +    unsigned long iobmp;
   6.775 +    struct segment_register tr;
   6.776 +    int rc = X86EMUL_OKAY;
   6.777 +
   6.778 +    if ( !(ctxt->regs->eflags & EFLG_VM) && mode_iopl() )
   6.779 +        return X86EMUL_OKAY;
   6.780 +
   6.781 +    fail_if(ops->read_segment == NULL);
   6.782 +    if ( (rc = ops->read_segment(x86_seg_tr, &tr, ctxt)) != 0 )
   6.783 +        return rc;
   6.784 +
   6.785 +    /* Ensure that the TSS is valid and has an io-bitmap-offset field. */
   6.786 +    if ( !tr.attr.fields.p ||
   6.787 +         ((tr.attr.fields.type & 0xd) != 0x9) ||
   6.788 +         (tr.limit < 0x67) )
   6.789 +        goto raise_exception;
   6.790 +
   6.791 +    if ( (rc = ops->read(x86_seg_none, tr.base + 0x66, &iobmp, 2, ctxt)) )
   6.792 +        return rc;
   6.793 +
   6.794 +    /* Ensure TSS includes two bytes including byte containing first port. */
   6.795 +    iobmp += first_port / 8;
   6.796 +    if ( tr.limit <= iobmp )
   6.797 +        goto raise_exception;
   6.798 +
   6.799 +    if ( (rc = ops->read(x86_seg_none, tr.base + iobmp, &iobmp, 2, ctxt)) )
   6.800 +        return rc;
   6.801 +    if ( (iobmp & (((1<<bytes)-1) << (first_port&7))) != 0 )
   6.802 +        goto raise_exception;
   6.803 +
   6.804 + done:
   6.805 +    return rc;
   6.806 +
   6.807 + raise_exception:
   6.808 +    fail_if(ops->inject_hw_exception == NULL);
   6.809 +    return ops->inject_hw_exception(EXC_GP, 0, ctxt) ? : X86EMUL_EXCEPTION;
   6.810 +}
   6.811 +
   6.812 +static int
   6.813 +in_realmode(
   6.814 +    struct x86_emulate_ctxt *ctxt,
   6.815 +    struct x86_emulate_ops  *ops)
   6.816 +{
   6.817 +    unsigned long cr0;
   6.818 +    int rc;
   6.819 +
   6.820 +    if ( ops->read_cr == NULL )
   6.821 +        return 0;
   6.822 +
   6.823 +    rc = ops->read_cr(0, &cr0, ctxt);
   6.824 +    return (!rc && !(cr0 & CR0_PE));
   6.825 +}
   6.826 +
   6.827 +static int
   6.828 +realmode_load_seg(
   6.829 +    enum x86_segment seg,
   6.830 +    uint16_t sel,
   6.831 +    struct x86_emulate_ctxt *ctxt,
   6.832 +    struct x86_emulate_ops *ops)
   6.833 +{
   6.834 +    struct segment_register reg;
   6.835 +    int rc;
   6.836 +
   6.837 +    if ( (rc = ops->read_segment(seg, &reg, ctxt)) != 0 )
   6.838 +        return rc;
   6.839 +
   6.840 +    reg.sel  = sel;
   6.841 +    reg.base = (uint32_t)sel << 4;
   6.842 +
   6.843 +    return ops->write_segment(seg, &reg, ctxt);
   6.844 +}
   6.845 +
   6.846 +static int
   6.847 +protmode_load_seg(
   6.848 +    enum x86_segment seg,
   6.849 +    uint16_t sel,
   6.850 +    struct x86_emulate_ctxt *ctxt,
   6.851 +    struct x86_emulate_ops *ops)
   6.852 +{
   6.853 +    struct segment_register desctab, cs, segr;
   6.854 +    struct { uint32_t a, b; } desc;
   6.855 +    unsigned long val;
   6.856 +    uint8_t dpl, rpl, cpl;
   6.857 +    int rc, fault_type = EXC_TS;
   6.858 +
   6.859 +    /* NULL selector? */
   6.860 +    if ( (sel & 0xfffc) == 0 )
   6.861 +    {
   6.862 +        if ( (seg == x86_seg_cs) || (seg == x86_seg_ss) )
   6.863 +            goto raise_exn;
   6.864 +        memset(&segr, 0, sizeof(segr));
   6.865 +        return ops->write_segment(seg, &segr, ctxt);
   6.866 +    }
   6.867 +
   6.868 +    /* LDT descriptor must be in the GDT. */
   6.869 +    if ( (seg == x86_seg_ldtr) && (sel & 4) )
   6.870 +        goto raise_exn;
   6.871 +
   6.872 +    if ( (rc = ops->read_segment(x86_seg_cs, &cs, ctxt)) ||
   6.873 +         (rc = ops->read_segment((sel & 4) ? x86_seg_ldtr : x86_seg_gdtr,
   6.874 +                                 &desctab, ctxt)) )
   6.875 +        return rc;
   6.876 +
   6.877 +    /* Check against descriptor table limit. */
   6.878 +    if ( ((sel & 0xfff8) + 7) > desctab.limit )
   6.879 +        goto raise_exn;
   6.880 +
   6.881 +    do {
   6.882 +        if ( (rc = ops->read(x86_seg_none, desctab.base + (sel & 0xfff8),
   6.883 +                             &val, 4, ctxt)) )
   6.884 +            return rc;
   6.885 +        desc.a = val;
   6.886 +        if ( (rc = ops->read(x86_seg_none, desctab.base + (sel & 0xfff8) + 4,
   6.887 +                             &val, 4, ctxt)) )
   6.888 +            return rc;
   6.889 +        desc.b = val;
   6.890 +
   6.891 +        /* Segment present in memory? */
   6.892 +        if ( !(desc.b & (1u<<15)) )
   6.893 +        {
   6.894 +            fault_type = EXC_NP;
   6.895 +            goto raise_exn;
   6.896 +        }
   6.897 +
   6.898 +        /* LDT descriptor is a system segment. All others are code/data. */
   6.899 +        if ( (desc.b & (1u<<12)) == ((seg == x86_seg_ldtr) << 12) )
   6.900 +            goto raise_exn;
   6.901 +
   6.902 +        dpl = (desc.b >> 13) & 3;
   6.903 +        rpl = sel & 3;
   6.904 +        cpl = cs.sel & 3;
   6.905 +
   6.906 +        switch ( seg )
   6.907 +        {
   6.908 +        case x86_seg_cs:
   6.909 +            /* Code segment? */
   6.910 +            if ( !(desc.b & (1u<<11)) )
   6.911 +                goto raise_exn;
   6.912 +            /* Non-conforming segment: check DPL against RPL. */
   6.913 +            if ( ((desc.b & (6u<<9)) != 6) && (dpl != rpl) )
   6.914 +                goto raise_exn;
   6.915 +            break;
   6.916 +        case x86_seg_ss:
   6.917 +            /* Writable data segment? */
   6.918 +            if ( (desc.b & (5u<<9)) != (1u<<9) )
   6.919 +                goto raise_exn;
   6.920 +            if ( (dpl != cpl) || (dpl != rpl) )
   6.921 +                goto raise_exn;
   6.922 +            break;
   6.923 +        case x86_seg_ldtr:
   6.924 +            /* LDT system segment? */
   6.925 +            if ( (desc.b & (15u<<8)) != (2u<<8) )
   6.926 +                goto raise_exn;
   6.927 +            goto skip_accessed_flag;
   6.928 +        default:
   6.929 +            /* Readable code or data segment? */
   6.930 +            if ( (desc.b & (5u<<9)) == (4u<<9) )
   6.931 +                goto raise_exn;
   6.932 +            /* Non-conforming segment: check DPL against RPL and CPL. */
   6.933 +            if ( ((desc.b & (6u<<9)) != 6) && ((dpl < cpl) || (dpl < rpl)) )
   6.934 +                goto raise_exn;
   6.935 +            break;
   6.936 +        }
   6.937 +
   6.938 +        /* Ensure Accessed flag is set. */
   6.939 +        rc = ((desc.b & 0x100) ? X86EMUL_OKAY : 
   6.940 +              ops->cmpxchg(
   6.941 +                  x86_seg_none, desctab.base + (sel & 0xfff8) + 4, desc.b,
   6.942 +                  desc.b | 0x100, 4, ctxt));
   6.943 +    } while ( rc == X86EMUL_CMPXCHG_FAILED );
   6.944 +
   6.945 +    if ( rc )
   6.946 +        return rc;
   6.947 +
   6.948 +    /* Force the Accessed flag in our local copy. */
   6.949 +    desc.b |= 0x100;
   6.950 +
   6.951 + skip_accessed_flag:
   6.952 +    segr.base = (((desc.b <<  0) & 0xff000000u) |
   6.953 +                 ((desc.b << 16) & 0x00ff0000u) |
   6.954 +                 ((desc.a >> 16) & 0x0000ffffu));
   6.955 +    segr.attr.bytes = (((desc.b >>  8) & 0x00ffu) |
   6.956 +                       ((desc.b >> 12) & 0x0f00u));
   6.957 +    segr.limit = (desc.b & 0x000f0000u) | (desc.a & 0x0000ffffu);
   6.958 +    if ( segr.attr.fields.g )
   6.959 +        segr.limit = (segr.limit << 12) | 0xfffu;
   6.960 +    segr.sel = sel;
   6.961 +    return ops->write_segment(seg, &segr, ctxt);
   6.962 +
   6.963 + raise_exn:
   6.964 +    if ( ops->inject_hw_exception == NULL )
   6.965 +        return X86EMUL_UNHANDLEABLE;
   6.966 +    if ( (rc = ops->inject_hw_exception(fault_type, sel & 0xfffc, ctxt)) )
   6.967 +        return rc;
   6.968 +    return X86EMUL_EXCEPTION;
   6.969 +}
   6.970 +
   6.971 +static int
   6.972 +load_seg(
   6.973 +    enum x86_segment seg,
   6.974 +    uint16_t sel,
   6.975 +    struct x86_emulate_ctxt *ctxt,
   6.976 +    struct x86_emulate_ops *ops)
   6.977 +{
   6.978 +    if ( (ops->read_segment == NULL) ||
   6.979 +         (ops->write_segment == NULL) )
   6.980 +        return X86EMUL_UNHANDLEABLE;
   6.981 +
   6.982 +    if ( in_realmode(ctxt, ops) )
   6.983 +        return realmode_load_seg(seg, sel, ctxt, ops);
   6.984 +
   6.985 +    return protmode_load_seg(seg, sel, ctxt, ops);
   6.986 +}
   6.987 +
   6.988 +void *
   6.989 +decode_register(
   6.990 +    uint8_t modrm_reg, struct cpu_user_regs *regs, int highbyte_regs)
   6.991 +{
   6.992 +    void *p;
   6.993 +
   6.994 +    switch ( modrm_reg )
   6.995 +    {
   6.996 +    case  0: p = &regs->eax; break;
   6.997 +    case  1: p = &regs->ecx; break;
   6.998 +    case  2: p = &regs->edx; break;
   6.999 +    case  3: p = &regs->ebx; break;
  6.1000 +    case  4: p = (highbyte_regs ?
  6.1001 +                  ((unsigned char *)&regs->eax + 1) : 
  6.1002 +                  (unsigned char *)&regs->esp); break;
  6.1003 +    case  5: p = (highbyte_regs ?
  6.1004 +                  ((unsigned char *)&regs->ecx + 1) : 
  6.1005 +                  (unsigned char *)&regs->ebp); break;
  6.1006 +    case  6: p = (highbyte_regs ?
  6.1007 +                  ((unsigned char *)&regs->edx + 1) : 
  6.1008 +                  (unsigned char *)&regs->esi); break;
  6.1009 +    case  7: p = (highbyte_regs ?
  6.1010 +                  ((unsigned char *)&regs->ebx + 1) : 
  6.1011 +                  (unsigned char *)&regs->edi); break;
  6.1012 +#if defined(__x86_64__)
  6.1013 +    case  8: p = &regs->r8;  break;
  6.1014 +    case  9: p = &regs->r9;  break;
  6.1015 +    case 10: p = &regs->r10; break;
  6.1016 +    case 11: p = &regs->r11; break;
  6.1017 +    case 12: p = &regs->r12; break;
  6.1018 +    case 13: p = &regs->r13; break;
  6.1019 +    case 14: p = &regs->r14; break;
  6.1020 +    case 15: p = &regs->r15; break;
  6.1021 +#endif
  6.1022 +    default: p = NULL; break;
  6.1023 +    }
  6.1024 +
  6.1025 +    return p;
  6.1026 +}
  6.1027 +
  6.1028 +#define decode_segment_failed x86_seg_tr
  6.1029 +enum x86_segment
  6.1030 +decode_segment(
  6.1031 +    uint8_t modrm_reg)
  6.1032 +{
  6.1033 +    switch ( modrm_reg )
  6.1034 +    {
  6.1035 +    case 0: return x86_seg_es;
  6.1036 +    case 1: return x86_seg_cs;
  6.1037 +    case 2: return x86_seg_ss;
  6.1038 +    case 3: return x86_seg_ds;
  6.1039 +    case 4: return x86_seg_fs;
  6.1040 +    case 5: return x86_seg_gs;
  6.1041 +    default: break;
  6.1042 +    }
  6.1043 +    return decode_segment_failed;
  6.1044 +}
  6.1045 +
  6.1046 +int
  6.1047 +x86_emulate(
  6.1048 +    struct x86_emulate_ctxt *ctxt,
  6.1049 +    struct x86_emulate_ops  *ops)
  6.1050 +{
  6.1051 +    /* Shadow copy of register state. Committed on successful emulation. */
  6.1052 +    struct cpu_user_regs _regs = *ctxt->regs;
  6.1053 +
  6.1054 +    uint8_t b, d, sib, sib_index, sib_base, twobyte = 0, rex_prefix = 0;
  6.1055 +    uint8_t modrm = 0, modrm_mod = 0, modrm_reg = 0, modrm_rm = 0;
  6.1056 +    unsigned int op_bytes, def_op_bytes, ad_bytes, def_ad_bytes;
  6.1057 +#define REPE_PREFIX  1
  6.1058 +#define REPNE_PREFIX 2
  6.1059 +    unsigned int lock_prefix = 0, rep_prefix = 0;
  6.1060 +    int override_seg = -1, rc = X86EMUL_OKAY;
  6.1061 +    struct operand src, dst;
  6.1062 +
  6.1063 +    /* Data operand effective address (usually computed from ModRM). */
  6.1064 +    struct operand ea;
  6.1065 +
  6.1066 +    /* Default is a memory operand relative to segment DS. */
  6.1067 +    ea.type    = OP_MEM;
  6.1068 +    ea.mem.seg = x86_seg_ds;
  6.1069 +    ea.mem.off = 0;
  6.1070 +
  6.1071 +    ctxt->retire.byte = 0;
  6.1072 +
  6.1073 +    op_bytes = def_op_bytes = ad_bytes = def_ad_bytes = ctxt->addr_size/8;
  6.1074 +    if ( op_bytes == 8 )
  6.1075 +    {
  6.1076 +        op_bytes = def_op_bytes = 4;
  6.1077 +#ifndef __x86_64__
  6.1078 +        return X86EMUL_UNHANDLEABLE;
  6.1079 +#endif
  6.1080 +    }
  6.1081 +
  6.1082 +    /* Prefix bytes. */
  6.1083 +    for ( ; ; )
  6.1084 +    {
  6.1085 +        switch ( b = insn_fetch_type(uint8_t) )
  6.1086 +        {
  6.1087 +        case 0x66: /* operand-size override */
  6.1088 +            op_bytes = def_op_bytes ^ 6;
  6.1089 +            break;
  6.1090 +        case 0x67: /* address-size override */
  6.1091 +            ad_bytes = def_ad_bytes ^ (mode_64bit() ? 12 : 6);
  6.1092 +            break;
  6.1093 +        case 0x2e: /* CS override */
  6.1094 +            override_seg = x86_seg_cs;
  6.1095 +            break;
  6.1096 +        case 0x3e: /* DS override */
  6.1097 +            override_seg = x86_seg_ds;
  6.1098 +            break;
  6.1099 +        case 0x26: /* ES override */
  6.1100 +            override_seg = x86_seg_es;
  6.1101 +            break;
  6.1102 +        case 0x64: /* FS override */
  6.1103 +            override_seg = x86_seg_fs;
  6.1104 +            break;
  6.1105 +        case 0x65: /* GS override */
  6.1106 +            override_seg = x86_seg_gs;
  6.1107 +            break;
  6.1108 +        case 0x36: /* SS override */
  6.1109 +            override_seg = x86_seg_ss;
  6.1110 +            break;
  6.1111 +        case 0xf0: /* LOCK */
  6.1112 +            lock_prefix = 1;
  6.1113 +            break;
  6.1114 +        case 0xf2: /* REPNE/REPNZ */
  6.1115 +            rep_prefix = REPNE_PREFIX;
  6.1116 +            break;
  6.1117 +        case 0xf3: /* REP/REPE/REPZ */
  6.1118 +            rep_prefix = REPE_PREFIX;
  6.1119 +            break;
  6.1120 +        case 0x40 ... 0x4f: /* REX */
  6.1121 +            if ( !mode_64bit() )
  6.1122 +                goto done_prefixes;
  6.1123 +            rex_prefix = b;
  6.1124 +            continue;
  6.1125 +        default:
  6.1126 +            goto done_prefixes;
  6.1127 +        }
  6.1128 +
  6.1129 +        /* Any legacy prefix after a REX prefix nullifies its effect. */
  6.1130 +        rex_prefix = 0;
  6.1131 +    }
  6.1132 + done_prefixes:
  6.1133 +
  6.1134 +    if ( rex_prefix & 8 ) /* REX.W */
  6.1135 +        op_bytes = 8;
  6.1136 +
  6.1137 +    /* Opcode byte(s). */
  6.1138 +    d = opcode_table[b];
  6.1139 +    if ( d == 0 )
  6.1140 +    {
  6.1141 +        /* Two-byte opcode? */
  6.1142 +        if ( b == 0x0f )
  6.1143 +        {
  6.1144 +            twobyte = 1;
  6.1145 +            b = insn_fetch_type(uint8_t);
  6.1146 +            d = twobyte_table[b];
  6.1147 +        }
  6.1148 +
  6.1149 +        /* Unrecognised? */
  6.1150 +        if ( d == 0 )
  6.1151 +            goto cannot_emulate;
  6.1152 +    }
  6.1153 +
  6.1154 +    /* Lock prefix is allowed only on RMW instructions. */
  6.1155 +    generate_exception_if((d & Mov) && lock_prefix, EXC_GP, 0);
  6.1156 +
  6.1157 +    /* ModRM and SIB bytes. */
  6.1158 +    if ( d & ModRM )
  6.1159 +    {
  6.1160 +        modrm = insn_fetch_type(uint8_t);
  6.1161 +        modrm_mod = (modrm & 0xc0) >> 6;
  6.1162 +        modrm_reg = ((rex_prefix & 4) << 1) | ((modrm & 0x38) >> 3);
  6.1163 +        modrm_rm  = modrm & 0x07;
  6.1164 +
  6.1165 +        if ( modrm_mod == 3 )
  6.1166 +        {
  6.1167 +            modrm_rm |= (rex_prefix & 1) << 3;
  6.1168 +            ea.type = OP_REG;
  6.1169 +            ea.reg  = decode_register(
  6.1170 +                modrm_rm, &_regs, (d & ByteOp) && (rex_prefix == 0));
  6.1171 +        }
  6.1172 +        else if ( ad_bytes == 2 )
  6.1173 +        {
  6.1174 +            /* 16-bit ModR/M decode. */
  6.1175 +            switch ( modrm_rm )
  6.1176 +            {
  6.1177 +            case 0:
  6.1178 +                ea.mem.off = _regs.ebx + _regs.esi;
  6.1179 +                break;
  6.1180 +            case 1:
  6.1181 +                ea.mem.off = _regs.ebx + _regs.edi;
  6.1182 +                break;
  6.1183 +            case 2:
  6.1184 +                ea.mem.seg = x86_seg_ss;
  6.1185 +                ea.mem.off = _regs.ebp + _regs.esi;
  6.1186 +                break;
  6.1187 +            case 3:
  6.1188 +                ea.mem.seg = x86_seg_ss;
  6.1189 +                ea.mem.off = _regs.ebp + _regs.edi;
  6.1190 +                break;
  6.1191 +            case 4:
  6.1192 +                ea.mem.off = _regs.esi;
  6.1193 +                break;
  6.1194 +            case 5:
  6.1195 +                ea.mem.off = _regs.edi;
  6.1196 +                break;
  6.1197 +            case 6:
  6.1198 +                if ( modrm_mod == 0 )
  6.1199 +                    break;
  6.1200 +                ea.mem.seg = x86_seg_ss;
  6.1201 +                ea.mem.off = _regs.ebp;
  6.1202 +                break;
  6.1203 +            case 7:
  6.1204 +                ea.mem.off = _regs.ebx;
  6.1205 +                break;
  6.1206 +            }
  6.1207 +            switch ( modrm_mod )
  6.1208 +            {
  6.1209 +            case 0:
  6.1210 +                if ( modrm_rm == 6 )
  6.1211 +                    ea.mem.off = insn_fetch_type(int16_t);
  6.1212 +                break;
  6.1213 +            case 1:
  6.1214 +                ea.mem.off += insn_fetch_type(int8_t);
  6.1215 +                break;
  6.1216 +            case 2:
  6.1217 +                ea.mem.off += insn_fetch_type(int16_t);
  6.1218 +                break;
  6.1219 +            }
  6.1220 +            ea.mem.off = truncate_ea(ea.mem.off);
  6.1221 +        }
  6.1222 +        else
  6.1223 +        {
  6.1224 +            /* 32/64-bit ModR/M decode. */
  6.1225 +            if ( modrm_rm == 4 )
  6.1226 +            {
  6.1227 +                sib = insn_fetch_type(uint8_t);
  6.1228 +                sib_index = ((sib >> 3) & 7) | ((rex_prefix << 2) & 8);
  6.1229 +                sib_base  = (sib & 7) | ((rex_prefix << 3) & 8);
  6.1230 +                if ( sib_index != 4 )
  6.1231 +                    ea.mem.off = *(long*)decode_register(sib_index, &_regs, 0);
  6.1232 +                ea.mem.off <<= (sib >> 6) & 3;
  6.1233 +                if ( (modrm_mod == 0) && ((sib_base & 7) == 5) )
  6.1234 +                    ea.mem.off += insn_fetch_type(int32_t);
  6.1235 +                else if ( sib_base == 4 )
  6.1236 +                {
  6.1237 +                    ea.mem.seg  = x86_seg_ss;
  6.1238 +                    ea.mem.off += _regs.esp;
  6.1239 +                    if ( !twobyte && (b == 0x8f) )
  6.1240 +                        /* POP <rm> computes its EA post increment. */
  6.1241 +                        ea.mem.off += ((mode_64bit() && (op_bytes == 4))
  6.1242 +                                       ? 8 : op_bytes);
  6.1243 +                }
  6.1244 +                else if ( sib_base == 5 )
  6.1245 +                {
  6.1246 +                    ea.mem.seg  = x86_seg_ss;
  6.1247 +                    ea.mem.off += _regs.ebp;
  6.1248 +                }
  6.1249 +                else
  6.1250 +                    ea.mem.off += *(long*)decode_register(sib_base, &_regs, 0);
  6.1251 +            }
  6.1252 +            else
  6.1253 +            {
  6.1254 +                modrm_rm |= (rex_prefix & 1) << 3;
  6.1255 +                ea.mem.off = *(long *)decode_register(modrm_rm, &_regs, 0);
  6.1256 +                if ( (modrm_rm == 5) && (modrm_mod != 0) )
  6.1257 +                    ea.mem.seg = x86_seg_ss;
  6.1258 +            }
  6.1259 +            switch ( modrm_mod )
  6.1260 +            {
  6.1261 +            case 0:
  6.1262 +                if ( (modrm_rm & 7) != 5 )
  6.1263 +                    break;
  6.1264 +                ea.mem.off = insn_fetch_type(int32_t);
  6.1265 +                if ( !mode_64bit() )
  6.1266 +                    break;
  6.1267 +                /* Relative to RIP of next instruction. Argh! */
  6.1268 +                ea.mem.off += _regs.eip;
  6.1269 +                if ( (d & SrcMask) == SrcImm )
  6.1270 +                    ea.mem.off += (d & ByteOp) ? 1 :
  6.1271 +                        ((op_bytes == 8) ? 4 : op_bytes);
  6.1272 +                else if ( (d & SrcMask) == SrcImmByte )
  6.1273 +                    ea.mem.off += 1;
  6.1274 +                else if ( !twobyte && ((b & 0xfe) == 0xf6) &&
  6.1275 +                          ((modrm_reg & 7) <= 1) )
  6.1276 +                    /* Special case in Grp3: test has immediate operand. */
  6.1277 +                    ea.mem.off += (d & ByteOp) ? 1
  6.1278 +                        : ((op_bytes == 8) ? 4 : op_bytes);
  6.1279 +                else if ( twobyte && ((b & 0xf7) == 0xa4) )
  6.1280 +                    /* SHLD/SHRD with immediate byte third operand. */
  6.1281 +                    ea.mem.off++;
  6.1282 +                break;
  6.1283 +            case 1:
  6.1284 +                ea.mem.off += insn_fetch_type(int8_t);
  6.1285 +                break;
  6.1286 +            case 2:
  6.1287 +                ea.mem.off += insn_fetch_type(int32_t);
  6.1288 +                break;
  6.1289 +            }
  6.1290 +            ea.mem.off = truncate_ea(ea.mem.off);
  6.1291 +        }
  6.1292 +    }
  6.1293 +
  6.1294 +    if ( override_seg != -1 )
  6.1295 +        ea.mem.seg = override_seg;
  6.1296 +
  6.1297 +    /* Special instructions do their own operand decoding. */
  6.1298 +    if ( (d & DstMask) == ImplicitOps )
  6.1299 +        goto special_insn;
  6.1300 +
  6.1301 +    /* Decode and fetch the source operand: register, memory or immediate. */
  6.1302 +    switch ( d & SrcMask )
  6.1303 +    {
  6.1304 +    case SrcNone:
  6.1305 +        break;
  6.1306 +    case SrcReg:
  6.1307 +        src.type = OP_REG;
  6.1308 +        if ( d & ByteOp )
  6.1309 +        {
  6.1310 +            src.reg = decode_register(modrm_reg, &_regs, (rex_prefix == 0));
  6.1311 +            src.val = *(uint8_t *)src.reg;
  6.1312 +            src.bytes = 1;
  6.1313 +        }
  6.1314 +        else
  6.1315 +        {
  6.1316 +            src.reg = decode_register(modrm_reg, &_regs, 0);
  6.1317 +            switch ( (src.bytes = op_bytes) )
  6.1318 +            {
  6.1319 +            case 2: src.val = *(uint16_t *)src.reg; break;
  6.1320 +            case 4: src.val = *(uint32_t *)src.reg; break;
  6.1321 +            case 8: src.val = *(uint64_t *)src.reg; break;
  6.1322 +            }
  6.1323 +        }
  6.1324 +        break;
  6.1325 +    case SrcMem16:
  6.1326 +        ea.bytes = 2;
  6.1327 +        goto srcmem_common;
  6.1328 +    case SrcMem:
  6.1329 +        ea.bytes = (d & ByteOp) ? 1 : op_bytes;
  6.1330 +    srcmem_common:
  6.1331 +        src = ea;
  6.1332 +        if ( src.type == OP_REG )
  6.1333 +        {
  6.1334 +            switch ( src.bytes )
  6.1335 +            {
  6.1336 +            case 1: src.val = *(uint8_t  *)src.reg; break;
  6.1337 +            case 2: src.val = *(uint16_t *)src.reg; break;
  6.1338 +            case 4: src.val = *(uint32_t *)src.reg; break;
  6.1339 +            case 8: src.val = *(uint64_t *)src.reg; break;
  6.1340 +            }
  6.1341 +        }
  6.1342 +        else if ( (rc = ops->read(src.mem.seg, src.mem.off,
  6.1343 +                                  &src.val, src.bytes, ctxt)) )
  6.1344 +            goto done;
  6.1345 +        break;
  6.1346 +    case SrcImm:
  6.1347 +        src.type  = OP_IMM;
  6.1348 +        src.bytes = (d & ByteOp) ? 1 : op_bytes;
  6.1349 +        if ( src.bytes == 8 ) src.bytes = 4;
  6.1350 +        /* NB. Immediates are sign-extended as necessary. */
  6.1351 +        switch ( src.bytes )
  6.1352 +        {
  6.1353 +        case 1: src.val = insn_fetch_type(int8_t);  break;
  6.1354 +        case 2: src.val = insn_fetch_type(int16_t); break;
  6.1355 +        case 4: src.val = insn_fetch_type(int32_t); break;
  6.1356 +        }
  6.1357 +        break;
  6.1358 +    case SrcImmByte:
  6.1359 +        src.type  = OP_IMM;
  6.1360 +        src.bytes = 1;
  6.1361 +        src.val   = insn_fetch_type(int8_t);
  6.1362 +        break;
  6.1363 +    }
  6.1364 +
  6.1365 +    /* Decode and fetch the destination operand: register or memory. */
  6.1366 +    switch ( d & DstMask )
  6.1367 +    {
  6.1368 +    case DstReg:
  6.1369 +        dst.type = OP_REG;
  6.1370 +        if ( d & ByteOp )
  6.1371 +        {
  6.1372 +            dst.reg = decode_register(modrm_reg, &_regs, (rex_prefix == 0));
  6.1373 +            dst.val = *(uint8_t *)dst.reg;
  6.1374 +            dst.bytes = 1;
  6.1375 +        }
  6.1376 +        else
  6.1377 +        {
  6.1378 +            dst.reg = decode_register(modrm_reg, &_regs, 0);
  6.1379 +            switch ( (dst.bytes = op_bytes) )
  6.1380 +            {
  6.1381 +            case 2: dst.val = *(uint16_t *)dst.reg; break;
  6.1382 +            case 4: dst.val = *(uint32_t *)dst.reg; break;
  6.1383 +            case 8: dst.val = *(uint64_t *)dst.reg; break;
  6.1384 +            }
  6.1385 +        }
  6.1386 +        break;
  6.1387 +    case DstBitBase:
  6.1388 +        if ( ((d & SrcMask) == SrcImmByte) || (ea.type == OP_REG) )
  6.1389 +        {
  6.1390 +            src.val &= (op_bytes << 3) - 1;
  6.1391 +        }
  6.1392 +        else
  6.1393 +        {
  6.1394 +            /*
  6.1395 +             * EA       += BitOffset DIV op_bytes*8
  6.1396 +             * BitOffset = BitOffset MOD op_bytes*8
  6.1397 +             * DIV truncates towards negative infinity.
  6.1398 +             * MOD always produces a positive result.
  6.1399 +             */
  6.1400 +            if ( op_bytes == 2 )
  6.1401 +                src.val = (int16_t)src.val;
  6.1402 +            else if ( op_bytes == 4 )
  6.1403 +                src.val = (int32_t)src.val;
  6.1404 +            if ( (long)src.val < 0 )
  6.1405 +            {
  6.1406 +                unsigned long byte_offset;
  6.1407 +                byte_offset = op_bytes + (((-src.val-1) >> 3) & ~(op_bytes-1));
  6.1408 +                ea.mem.off -= byte_offset;
  6.1409 +                src.val = (byte_offset << 3) + src.val;
  6.1410 +            }
  6.1411 +            else
  6.1412 +            {
  6.1413 +                ea.mem.off += (src.val >> 3) & ~(op_bytes - 1);
  6.1414 +                src.val &= (op_bytes << 3) - 1;
  6.1415 +            }
  6.1416 +        }
  6.1417 +        /* Becomes a normal DstMem operation from here on. */
  6.1418 +        d = (d & ~DstMask) | DstMem;
  6.1419 +    case DstMem:
  6.1420 +        ea.bytes = (d & ByteOp) ? 1 : op_bytes;
  6.1421 +        dst = ea;
  6.1422 +        if ( dst.type == OP_REG )
  6.1423 +        {
  6.1424 +            switch ( dst.bytes )
  6.1425 +            {
  6.1426 +            case 1: dst.val = *(uint8_t  *)dst.reg; break;
  6.1427 +            case 2: dst.val = *(uint16_t *)dst.reg; break;
  6.1428 +            case 4: dst.val = *(uint32_t *)dst.reg; break;
  6.1429 +            case 8: dst.val = *(uint64_t *)dst.reg; break;
  6.1430 +            }
  6.1431 +        }
  6.1432 +        else if ( !(d & Mov) ) /* optimisation - avoid slow emulated read */
  6.1433 +        {
  6.1434 +            if ( (rc = ops->read(dst.mem.seg, dst.mem.off,
  6.1435 +                                 &dst.val, dst.bytes, ctxt)) )
  6.1436 +                goto done;
  6.1437 +            dst.orig_val = dst.val;
  6.1438 +        }
  6.1439 +        break;
  6.1440 +    }
  6.1441 +
  6.1442 +    /* LOCK prefix allowed only on instructions with memory destination. */
  6.1443 +    generate_exception_if(lock_prefix && (dst.type != OP_MEM), EXC_GP, 0);
  6.1444 +
  6.1445 +    if ( twobyte )
  6.1446 +        goto twobyte_insn;
  6.1447 +
  6.1448 +    switch ( b )
  6.1449 +    {
  6.1450 +    case 0x04 ... 0x05: /* add imm,%%eax */
  6.1451 +        dst.reg = (unsigned long *)&_regs.eax;
  6.1452 +        dst.val = _regs.eax;
  6.1453 +    case 0x00 ... 0x03: add: /* add */
  6.1454 +        emulate_2op_SrcV("add", src, dst, _regs.eflags);
  6.1455 +        break;
  6.1456 +
  6.1457 +    case 0x0c ... 0x0d: /* or imm,%%eax */
  6.1458 +        dst.reg = (unsigned long *)&_regs.eax;
  6.1459 +        dst.val = _regs.eax;
  6.1460 +    case 0x08 ... 0x0b: or:  /* or */
  6.1461 +        emulate_2op_SrcV("or", src, dst, _regs.eflags);
  6.1462 +        break;
  6.1463 +
  6.1464 +    case 0x14 ... 0x15: /* adc imm,%%eax */
  6.1465 +        dst.reg = (unsigned long *)&_regs.eax;
  6.1466 +        dst.val = _regs.eax;
  6.1467 +    case 0x10 ... 0x13: adc: /* adc */
  6.1468 +        emulate_2op_SrcV("adc", src, dst, _regs.eflags);
  6.1469 +        break;
  6.1470 +
  6.1471 +    case 0x1c ... 0x1d: /* sbb imm,%%eax */
  6.1472 +        dst.reg = (unsigned long *)&_regs.eax;
  6.1473 +        dst.val = _regs.eax;
  6.1474 +    case 0x18 ... 0x1b: sbb: /* sbb */
  6.1475 +        emulate_2op_SrcV("sbb", src, dst, _regs.eflags);
  6.1476 +        break;
  6.1477 +
  6.1478 +    case 0x24 ... 0x25: /* and imm,%%eax */
  6.1479 +        dst.reg = (unsigned long *)&_regs.eax;
  6.1480 +        dst.val = _regs.eax;
  6.1481 +    case 0x20 ... 0x23: and: /* and */
  6.1482 +        emulate_2op_SrcV("and", src, dst, _regs.eflags);
  6.1483 +        break;
  6.1484 +
  6.1485 +    case 0x2c ... 0x2d: /* sub imm,%%eax */
  6.1486 +        dst.reg = (unsigned long *)&_regs.eax;
  6.1487 +        dst.val = _regs.eax;
  6.1488 +    case 0x28 ... 0x2b: sub: /* sub */
  6.1489 +        emulate_2op_SrcV("sub", src, dst, _regs.eflags);
  6.1490 +        break;
  6.1491 +
  6.1492 +    case 0x34 ... 0x35: /* xor imm,%%eax */
  6.1493 +        dst.reg = (unsigned long *)&_regs.eax;
  6.1494 +        dst.val = _regs.eax;
  6.1495 +    case 0x30 ... 0x33: xor: /* xor */
  6.1496 +        emulate_2op_SrcV("xor", src, dst, _regs.eflags);
  6.1497 +        break;
  6.1498 +
  6.1499 +    case 0x3c ... 0x3d: /* cmp imm,%%eax */
  6.1500 +        dst.reg = (unsigned long *)&_regs.eax;
  6.1501 +        dst.val = _regs.eax;
  6.1502 +    case 0x38 ... 0x3b: cmp: /* cmp */
  6.1503 +        emulate_2op_SrcV("cmp", src, dst, _regs.eflags);
  6.1504 +        break;
  6.1505 +
  6.1506 +    case 0x62: /* bound */ {
  6.1507 +        unsigned long src_val2;
  6.1508 +        int lb, ub, idx;
  6.1509 +        generate_exception_if(mode_64bit() || (src.type != OP_MEM),
  6.1510 +                              EXC_UD, -1);
  6.1511 +        if ( (rc = ops->read(src.mem.seg, src.mem.off + op_bytes,
  6.1512 +                             &src_val2, op_bytes, ctxt)) )
  6.1513 +            goto done;
  6.1514 +        ub  = (op_bytes == 2) ? (int16_t)src_val2 : (int32_t)src_val2;
  6.1515 +        lb  = (op_bytes == 2) ? (int16_t)src.val  : (int32_t)src.val;
  6.1516 +        idx = (op_bytes == 2) ? (int16_t)dst.val  : (int32_t)dst.val;
  6.1517 +        generate_exception_if((idx < lb) || (idx > ub), EXC_BR, -1);
  6.1518 +        dst.type = OP_NONE;
  6.1519 +        break;
  6.1520 +    }
  6.1521 +
  6.1522 +    case 0x63: /* movsxd (x86/64) / arpl (x86/32) */
  6.1523 +        if ( mode_64bit() )
  6.1524 +        {
  6.1525 +            /* movsxd */
  6.1526 +            if ( src.type == OP_REG )
  6.1527 +                src.val = *(int32_t *)src.reg;
  6.1528 +            else if ( (rc = ops->read(src.mem.seg, src.mem.off,
  6.1529 +                                      &src.val, 4, ctxt)) )
  6.1530 +                goto done;
  6.1531 +            dst.val = (int32_t)src.val;
  6.1532 +        }
  6.1533 +        else
  6.1534 +        {
  6.1535 +            /* arpl */
  6.1536 +            uint16_t src_val = dst.val;
  6.1537 +            dst = src;
  6.1538 +            _regs.eflags &= ~EFLG_ZF;
  6.1539 +            _regs.eflags |= ((src_val & 3) > (dst.val & 3)) ? EFLG_ZF : 0;
  6.1540 +            if ( _regs.eflags & EFLG_ZF )
  6.1541 +                dst.val  = (dst.val & ~3) | (src_val & 3);
  6.1542 +            else
  6.1543 +                dst.type = OP_NONE;
  6.1544 +            generate_exception_if(in_realmode(ctxt, ops), EXC_UD, -1);
  6.1545 +        }
  6.1546 +        break;
  6.1547 +
  6.1548 +    case 0x69: /* imul imm16/32 */
  6.1549 +    case 0x6b: /* imul imm8 */ {
  6.1550 +        unsigned long src1; /* ModR/M source operand */
  6.1551 +        if ( ea.type == OP_REG )
  6.1552 +            src1 = *ea.reg;
  6.1553 +        else if ( (rc = ops->read(ea.mem.seg, ea.mem.off,
  6.1554 +                                  &src1, op_bytes, ctxt)) )
  6.1555 +            goto done;
  6.1556 +        _regs.eflags &= ~(EFLG_OF|EFLG_CF);
  6.1557 +        switch ( dst.bytes )
  6.1558 +        {
  6.1559 +        case 2:
  6.1560 +            dst.val = ((uint32_t)(int16_t)src.val *
  6.1561 +                       (uint32_t)(int16_t)src1);
  6.1562 +            if ( (int16_t)dst.val != (uint32_t)dst.val )
  6.1563 +                _regs.eflags |= EFLG_OF|EFLG_CF;
  6.1564 +            break;
  6.1565 +#ifdef __x86_64__
  6.1566 +        case 4:
  6.1567 +            dst.val = ((uint64_t)(int32_t)src.val *
  6.1568 +                       (uint64_t)(int32_t)src1);
  6.1569 +            if ( (int32_t)dst.val != dst.val )
  6.1570 +                _regs.eflags |= EFLG_OF|EFLG_CF;
  6.1571 +            break;
  6.1572 +#endif
  6.1573 +        default: {
  6.1574 +            unsigned long m[2] = { src.val, src1 };
  6.1575 +            if ( imul_dbl(m) )
  6.1576 +                _regs.eflags |= EFLG_OF|EFLG_CF;
  6.1577 +            dst.val = m[0];
  6.1578 +            break;
  6.1579 +        }
  6.1580 +        }
  6.1581 +        break;
  6.1582 +    }
  6.1583 +
  6.1584 +    case 0x82: /* Grp1 (x86/32 only) */
  6.1585 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.1586 +    case 0x80: case 0x81: case 0x83: /* Grp1 */
  6.1587 +        switch ( modrm_reg & 7 )
  6.1588 +        {
  6.1589 +        case 0: goto add;
  6.1590 +        case 1: goto or;
  6.1591 +        case 2: goto adc;
  6.1592 +        case 3: goto sbb;
  6.1593 +        case 4: goto and;
  6.1594 +        case 5: goto sub;
  6.1595 +        case 6: goto xor;
  6.1596 +        case 7: goto cmp;
  6.1597 +        }
  6.1598 +        break;
  6.1599 +
  6.1600 +    case 0xa8 ... 0xa9: /* test imm,%%eax */
  6.1601 +        dst.reg = (unsigned long *)&_regs.eax;
  6.1602 +        dst.val = _regs.eax;
  6.1603 +    case 0x84 ... 0x85: test: /* test */
  6.1604 +        emulate_2op_SrcV("test", src, dst, _regs.eflags);
  6.1605 +        break;
  6.1606 +
  6.1607 +    case 0x86 ... 0x87: xchg: /* xchg */
  6.1608 +        /* Write back the register source. */
  6.1609 +        switch ( dst.bytes )
  6.1610 +        {
  6.1611 +        case 1: *(uint8_t  *)src.reg = (uint8_t)dst.val; break;
  6.1612 +        case 2: *(uint16_t *)src.reg = (uint16_t)dst.val; break;
  6.1613 +        case 4: *src.reg = (uint32_t)dst.val; break; /* 64b reg: zero-extend */
  6.1614 +        case 8: *src.reg = dst.val; break;
  6.1615 +        }
  6.1616 +        /* Write back the memory destination with implicit LOCK prefix. */
  6.1617 +        dst.val = src.val;
  6.1618 +        lock_prefix = 1;
  6.1619 +        break;
  6.1620 +
  6.1621 +    case 0xc6 ... 0xc7: /* mov (sole member of Grp11) */
  6.1622 +        generate_exception_if((modrm_reg & 7) != 0, EXC_UD, -1);
  6.1623 +    case 0x88 ... 0x8b: /* mov */
  6.1624 +        dst.val = src.val;
  6.1625 +        break;
  6.1626 +
  6.1627 +    case 0x8c: /* mov Sreg,r/m */ {
  6.1628 +        struct segment_register reg;
  6.1629 +        enum x86_segment seg = decode_segment(modrm_reg);
  6.1630 +        generate_exception_if(seg == decode_segment_failed, EXC_UD, -1);
  6.1631 +        fail_if(ops->read_segment == NULL);
  6.1632 +        if ( (rc = ops->read_segment(seg, &reg, ctxt)) != 0 )
  6.1633 +            goto done;
  6.1634 +        dst.val = reg.sel;
  6.1635 +        if ( dst.type == OP_MEM )
  6.1636 +            dst.bytes = 2;
  6.1637 +        break;
  6.1638 +    }
  6.1639 +
  6.1640 +    case 0x8e: /* mov r/m,Sreg */ {
  6.1641 +        enum x86_segment seg = decode_segment(modrm_reg);
  6.1642 +        generate_exception_if(seg == decode_segment_failed, EXC_UD, -1);
  6.1643 +        if ( (rc = load_seg(seg, (uint16_t)src.val, ctxt, ops)) != 0 )
  6.1644 +            goto done;
  6.1645 +        if ( seg == x86_seg_ss )
  6.1646 +            ctxt->retire.flags.mov_ss = 1;
  6.1647 +        dst.type = OP_NONE;
  6.1648 +        break;
  6.1649 +    }
  6.1650 +
  6.1651 +    case 0x8d: /* lea */
  6.1652 +        dst.val = ea.mem.off;
  6.1653 +        break;
  6.1654 +
  6.1655 +    case 0x8f: /* pop (sole member of Grp1a) */
  6.1656 +        generate_exception_if((modrm_reg & 7) != 0, EXC_UD, -1);
  6.1657 +        /* 64-bit mode: POP defaults to a 64-bit operand. */
  6.1658 +        if ( mode_64bit() && (dst.bytes == 4) )
  6.1659 +            dst.bytes = 8;
  6.1660 +        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(dst.bytes),
  6.1661 +                             &dst.val, dst.bytes, ctxt)) != 0 )
  6.1662 +            goto done;
  6.1663 +        break;
  6.1664 +
  6.1665 +    case 0xb0 ... 0xb7: /* mov imm8,r8 */
  6.1666 +        dst.reg = decode_register(
  6.1667 +            (b & 7) | ((rex_prefix & 1) << 3), &_regs, (rex_prefix == 0));
  6.1668 +        dst.val = src.val;
  6.1669 +        break;
  6.1670 +
  6.1671 +    case 0xb8 ... 0xbf: /* mov imm{16,32,64},r{16,32,64} */
  6.1672 +        if ( dst.bytes == 8 ) /* Fetch more bytes to obtain imm64 */
  6.1673 +            src.val = ((uint32_t)src.val |
  6.1674 +                       ((uint64_t)insn_fetch_type(uint32_t) << 32));
  6.1675 +        dst.reg = decode_register(
  6.1676 +            (b & 7) | ((rex_prefix & 1) << 3), &_regs, 0);
  6.1677 +        dst.val = src.val;
  6.1678 +        break;
  6.1679 +
  6.1680 +    case 0xc0 ... 0xc1: grp2: /* Grp2 */
  6.1681 +        switch ( modrm_reg & 7 )
  6.1682 +        {
  6.1683 +        case 0: /* rol */
  6.1684 +            emulate_2op_SrcB("rol", src, dst, _regs.eflags);
  6.1685 +            break;
  6.1686 +        case 1: /* ror */
  6.1687 +            emulate_2op_SrcB("ror", src, dst, _regs.eflags);
  6.1688 +            break;
  6.1689 +        case 2: /* rcl */
  6.1690 +            emulate_2op_SrcB("rcl", src, dst, _regs.eflags);
  6.1691 +            break;
  6.1692 +        case 3: /* rcr */
  6.1693 +            emulate_2op_SrcB("rcr", src, dst, _regs.eflags);
  6.1694 +            break;
  6.1695 +        case 4: /* sal/shl */
  6.1696 +        case 6: /* sal/shl */
  6.1697 +            emulate_2op_SrcB("sal", src, dst, _regs.eflags);
  6.1698 +            break;
  6.1699 +        case 5: /* shr */
  6.1700 +            emulate_2op_SrcB("shr", src, dst, _regs.eflags);
  6.1701 +            break;
  6.1702 +        case 7: /* sar */
  6.1703 +            emulate_2op_SrcB("sar", src, dst, _regs.eflags);
  6.1704 +            break;
  6.1705 +        }
  6.1706 +        break;
  6.1707 +
  6.1708 +    case 0xc4: /* les */ {
  6.1709 +        unsigned long sel;
  6.1710 +        dst.val = x86_seg_es;
  6.1711 +    les: /* dst.val identifies the segment */
  6.1712 +        generate_exception_if(src.type != OP_MEM, EXC_UD, -1);
  6.1713 +        if ( (rc = ops->read(src.mem.seg, src.mem.off + src.bytes,
  6.1714 +                             &sel, 2, ctxt)) != 0 )
  6.1715 +            goto done;
  6.1716 +        if ( (rc = load_seg(dst.val, (uint16_t)sel, ctxt, ops)) != 0 )
  6.1717 +            goto done;
  6.1718 +        dst.val = src.val;
  6.1719 +        break;
  6.1720 +    }
  6.1721 +
  6.1722 +    case 0xc5: /* lds */
  6.1723 +        dst.val = x86_seg_ds;
  6.1724 +        goto les;
  6.1725 +
  6.1726 +    case 0xd0 ... 0xd1: /* Grp2 */
  6.1727 +        src.val = 1;
  6.1728 +        goto grp2;
  6.1729 +
  6.1730 +    case 0xd2 ... 0xd3: /* Grp2 */
  6.1731 +        src.val = _regs.ecx;
  6.1732 +        goto grp2;
  6.1733 +
  6.1734 +    case 0xf6 ... 0xf7: /* Grp3 */
  6.1735 +        switch ( modrm_reg & 7 )
  6.1736 +        {
  6.1737 +        case 0 ... 1: /* test */
  6.1738 +            /* Special case in Grp3: test has an immediate source operand. */
  6.1739 +            src.type = OP_IMM;
  6.1740 +            src.bytes = (d & ByteOp) ? 1 : op_bytes;
  6.1741 +            if ( src.bytes == 8 ) src.bytes = 4;
  6.1742 +            switch ( src.bytes )
  6.1743 +            {
  6.1744 +            case 1: src.val = insn_fetch_type(int8_t);  break;
  6.1745 +            case 2: src.val = insn_fetch_type(int16_t); break;
  6.1746 +            case 4: src.val = insn_fetch_type(int32_t); break;
  6.1747 +            }
  6.1748 +            goto test;
  6.1749 +        case 2: /* not */
  6.1750 +            dst.val = ~dst.val;
  6.1751 +            break;
  6.1752 +        case 3: /* neg */
  6.1753 +            emulate_1op("neg", dst, _regs.eflags);
  6.1754 +            break;
  6.1755 +        case 4: /* mul */
  6.1756 +            src = dst;
  6.1757 +            dst.type = OP_REG;
  6.1758 +            dst.reg  = (unsigned long *)&_regs.eax;
  6.1759 +            dst.val  = *dst.reg;
  6.1760 +            _regs.eflags &= ~(EFLG_OF|EFLG_CF);
  6.1761 +            switch ( src.bytes )
  6.1762 +            {
  6.1763 +            case 1:
  6.1764 +                dst.val = (uint8_t)dst.val;
  6.1765 +                dst.val *= src.val;
  6.1766 +                if ( (uint8_t)dst.val != (uint16_t)dst.val )
  6.1767 +                    _regs.eflags |= EFLG_OF|EFLG_CF;
  6.1768 +                dst.bytes = 2;
  6.1769 +                break;
  6.1770 +            case 2:
  6.1771 +                dst.val = (uint16_t)dst.val;
  6.1772 +                dst.val *= src.val;
  6.1773 +                if ( (uint16_t)dst.val != (uint32_t)dst.val )
  6.1774 +                    _regs.eflags |= EFLG_OF|EFLG_CF;
  6.1775 +                *(uint16_t *)&_regs.edx = dst.val >> 16;
  6.1776 +                break;
  6.1777 +#ifdef __x86_64__
  6.1778 +            case 4:
  6.1779 +                dst.val = (uint32_t)dst.val;
  6.1780 +                dst.val *= src.val;
  6.1781 +                if ( (uint32_t)dst.val != dst.val )
  6.1782 +                    _regs.eflags |= EFLG_OF|EFLG_CF;
  6.1783 +                _regs.edx = (uint32_t)(dst.val >> 32);
  6.1784 +                break;
  6.1785 +#endif
  6.1786 +            default: {
  6.1787 +                unsigned long m[2] = { src.val, dst.val };
  6.1788 +                if ( mul_dbl(m) )
  6.1789 +                    _regs.eflags |= EFLG_OF|EFLG_CF;
  6.1790 +                _regs.edx = m[1];
  6.1791 +                dst.val  = m[0];
  6.1792 +                break;
  6.1793 +            }
  6.1794 +            }
  6.1795 +            break;
  6.1796 +        case 5: /* imul */
  6.1797 +            src = dst;
  6.1798 +            dst.type = OP_REG;
  6.1799 +            dst.reg  = (unsigned long *)&_regs.eax;
  6.1800 +            dst.val  = *dst.reg;
  6.1801 +            _regs.eflags &= ~(EFLG_OF|EFLG_CF);
  6.1802 +            switch ( src.bytes )
  6.1803 +            {
  6.1804 +            case 1:
  6.1805 +                dst.val = ((uint16_t)(int8_t)src.val *
  6.1806 +                           (uint16_t)(int8_t)dst.val);
  6.1807 +                if ( (int8_t)dst.val != (uint16_t)dst.val )
  6.1808 +                    _regs.eflags |= EFLG_OF|EFLG_CF;
  6.1809 +                dst.bytes = 2;
  6.1810 +                break;
  6.1811 +            case 2:
  6.1812 +                dst.val = ((uint32_t)(int16_t)src.val *
  6.1813 +                           (uint32_t)(int16_t)dst.val);
  6.1814 +                if ( (int16_t)dst.val != (uint32_t)dst.val )
  6.1815 +                    _regs.eflags |= EFLG_OF|EFLG_CF;
  6.1816 +                *(uint16_t *)&_regs.edx = dst.val >> 16;
  6.1817 +                break;
  6.1818 +#ifdef __x86_64__
  6.1819 +            case 4:
  6.1820 +                dst.val = ((uint64_t)(int32_t)src.val *
  6.1821 +                           (uint64_t)(int32_t)dst.val);
  6.1822 +                if ( (int32_t)dst.val != dst.val )
  6.1823 +                    _regs.eflags |= EFLG_OF|EFLG_CF;
  6.1824 +                _regs.edx = (uint32_t)(dst.val >> 32);
  6.1825 +                break;
  6.1826 +#endif
  6.1827 +            default: {
  6.1828 +                unsigned long m[2] = { src.val, dst.val };
  6.1829 +                if ( imul_dbl(m) )
  6.1830 +                    _regs.eflags |= EFLG_OF|EFLG_CF;
  6.1831 +                _regs.edx = m[1];
  6.1832 +                dst.val  = m[0];
  6.1833 +                break;
  6.1834 +            }
  6.1835 +            }
  6.1836 +            break;
  6.1837 +        case 6: /* div */ {
  6.1838 +            unsigned long u[2], v;
  6.1839 +            src = dst;
  6.1840 +            dst.type = OP_REG;
  6.1841 +            dst.reg  = (unsigned long *)&_regs.eax;
  6.1842 +            switch ( src.bytes )
  6.1843 +            {
  6.1844 +            case 1:
  6.1845 +                u[0] = (uint16_t)_regs.eax;
  6.1846 +                u[1] = 0;
  6.1847 +                v    = (uint8_t)src.val;
  6.1848 +                generate_exception_if(
  6.1849 +                    div_dbl(u, v) || ((uint8_t)u[0] != (uint16_t)u[0]),
  6.1850 +                    EXC_DE, -1);
  6.1851 +                dst.val = (uint8_t)u[0];
  6.1852 +                ((uint8_t *)&_regs.eax)[1] = u[1];
  6.1853 +                break;
  6.1854 +            case 2:
  6.1855 +                u[0] = ((uint32_t)_regs.edx << 16) | (uint16_t)_regs.eax;
  6.1856 +                u[1] = 0;
  6.1857 +                v    = (uint16_t)src.val;
  6.1858 +                generate_exception_if(
  6.1859 +                    div_dbl(u, v) || ((uint16_t)u[0] != (uint32_t)u[0]),
  6.1860 +                    EXC_DE, -1);
  6.1861 +                dst.val = (uint16_t)u[0];
  6.1862 +                *(uint16_t *)&_regs.edx = u[1];
  6.1863 +                break;
  6.1864 +#ifdef __x86_64__
  6.1865 +            case 4:
  6.1866 +                u[0] = (_regs.edx << 32) | (uint32_t)_regs.eax;
  6.1867 +                u[1] = 0;
  6.1868 +                v    = (uint32_t)src.val;
  6.1869 +                generate_exception_if(
  6.1870 +                    div_dbl(u, v) || ((uint32_t)u[0] != u[0]),
  6.1871 +                    EXC_DE, -1);
  6.1872 +                dst.val   = (uint32_t)u[0];
  6.1873 +                _regs.edx = (uint32_t)u[1];
  6.1874 +                break;
  6.1875 +#endif
  6.1876 +            default:
  6.1877 +                u[0] = _regs.eax;
  6.1878 +                u[1] = _regs.edx;
  6.1879 +                v    = src.val;
  6.1880 +                generate_exception_if(div_dbl(u, v), EXC_DE, -1);
  6.1881 +                dst.val   = u[0];
  6.1882 +                _regs.edx = u[1];
  6.1883 +                break;
  6.1884 +            }
  6.1885 +            break;
  6.1886 +        }
  6.1887 +        case 7: /* idiv */ {
  6.1888 +            unsigned long u[2], v;
  6.1889 +            src = dst;
  6.1890 +            dst.type = OP_REG;
  6.1891 +            dst.reg  = (unsigned long *)&_regs.eax;
  6.1892 +            switch ( src.bytes )
  6.1893 +            {
  6.1894 +            case 1:
  6.1895 +                u[0] = (int16_t)_regs.eax;
  6.1896 +                u[1] = ((long)u[0] < 0) ? ~0UL : 0UL;
  6.1897 +                v    = (int8_t)src.val;
  6.1898 +                generate_exception_if(
  6.1899 +                    idiv_dbl(u, v) || ((int8_t)u[0] != (int16_t)u[0]),
  6.1900 +                    EXC_DE, -1);
  6.1901 +                dst.val = (int8_t)u[0];
  6.1902 +                ((int8_t *)&_regs.eax)[1] = u[1];
  6.1903 +                break;
  6.1904 +            case 2:
  6.1905 +                u[0] = (int32_t)((_regs.edx << 16) | (uint16_t)_regs.eax);
  6.1906 +                u[1] = ((long)u[0] < 0) ? ~0UL : 0UL;
  6.1907 +                v    = (int16_t)src.val;
  6.1908 +                generate_exception_if(
  6.1909 +                    idiv_dbl(u, v) || ((int16_t)u[0] != (int32_t)u[0]),
  6.1910 +                    EXC_DE, -1);
  6.1911 +                dst.val = (int16_t)u[0];
  6.1912 +                *(int16_t *)&_regs.edx = u[1];
  6.1913 +                break;
  6.1914 +#ifdef __x86_64__
  6.1915 +            case 4:
  6.1916 +                u[0] = (_regs.edx << 32) | (uint32_t)_regs.eax;
  6.1917 +                u[1] = ((long)u[0] < 0) ? ~0UL : 0UL;
  6.1918 +                v    = (int32_t)src.val;
  6.1919 +                generate_exception_if(
  6.1920 +                    idiv_dbl(u, v) || ((int32_t)u[0] != u[0]),
  6.1921 +                    EXC_DE, -1);
  6.1922 +                dst.val   = (int32_t)u[0];
  6.1923 +                _regs.edx = (uint32_t)u[1];
  6.1924 +                break;
  6.1925 +#endif
  6.1926 +            default:
  6.1927 +                u[0] = _regs.eax;
  6.1928 +                u[1] = _regs.edx;
  6.1929 +                v    = src.val;
  6.1930 +                generate_exception_if(idiv_dbl(u, v), EXC_DE, -1);
  6.1931 +                dst.val   = u[0];
  6.1932 +                _regs.edx = u[1];
  6.1933 +                break;
  6.1934 +            }
  6.1935 +            break;
  6.1936 +        }
  6.1937 +        default:
  6.1938 +            goto cannot_emulate;
  6.1939 +        }
  6.1940 +        break;
  6.1941 +
  6.1942 +    case 0xfe: /* Grp4 */
  6.1943 +        generate_exception_if((modrm_reg & 7) >= 2, EXC_UD, -1);
  6.1944 +    case 0xff: /* Grp5 */
  6.1945 +        switch ( modrm_reg & 7 )
  6.1946 +        {
  6.1947 +        case 0: /* inc */
  6.1948 +            emulate_1op("inc", dst, _regs.eflags);
  6.1949 +            break;
  6.1950 +        case 1: /* dec */
  6.1951 +            emulate_1op("dec", dst, _regs.eflags);
  6.1952 +            break;
  6.1953 +        case 2: /* call (near) */
  6.1954 +        case 4: /* jmp (near) */
  6.1955 +            if ( (dst.bytes != 8) && mode_64bit() )
  6.1956 +            {
  6.1957 +                dst.bytes = op_bytes = 8;
  6.1958 +                if ( dst.type == OP_REG )
  6.1959 +                    dst.val = *dst.reg;
  6.1960 +                else if ( (rc = ops->read(dst.mem.seg, dst.mem.off,
  6.1961 +                                          &dst.val, 8, ctxt)) != 0 )
  6.1962 +                    goto done;
  6.1963 +            }
  6.1964 +            src.val = _regs.eip;
  6.1965 +            _regs.eip = dst.val;
  6.1966 +            if ( (modrm_reg & 7) == 2 )
  6.1967 +                goto push; /* call */
  6.1968 +            dst.type = OP_NONE;
  6.1969 +            break;
  6.1970 +        case 3: /* call (far, absolute indirect) */
  6.1971 +        case 5: /* jmp (far, absolute indirect) */ {
  6.1972 +            unsigned long sel;
  6.1973 +
  6.1974 +            generate_exception_if(dst.type != OP_MEM, EXC_UD, -1);
  6.1975 +
  6.1976 +            if ( (rc = ops->read(dst.mem.seg, dst.mem.off+dst.bytes,
  6.1977 +                                 &sel, 2, ctxt)) )
  6.1978 +                goto done;
  6.1979 +
  6.1980 +            if ( (modrm_reg & 7) == 3 ) /* call */
  6.1981 +            {
  6.1982 +                struct segment_register reg;
  6.1983 +                fail_if(ops->read_segment == NULL);
  6.1984 +                if ( (rc = ops->read_segment(x86_seg_cs, &reg, ctxt)) ||
  6.1985 +                     (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  6.1986 +                                      reg.sel, op_bytes, ctxt)) ||
  6.1987 +                     (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  6.1988 +                                      _regs.eip, op_bytes, ctxt)) )
  6.1989 +                    goto done;
  6.1990 +            }
  6.1991 +
  6.1992 +            if ( (rc = load_seg(x86_seg_cs, sel, ctxt, ops)) != 0 )
  6.1993 +                goto done;
  6.1994 +            _regs.eip = dst.val;
  6.1995 +
  6.1996 +            dst.type = OP_NONE;
  6.1997 +            break;
  6.1998 +        }
  6.1999 +        case 6: /* push */
  6.2000 +            /* 64-bit mode: PUSH defaults to a 64-bit operand. */
  6.2001 +            if ( mode_64bit() && (dst.bytes == 4) )
  6.2002 +            {
  6.2003 +                dst.bytes = 8;
  6.2004 +                if ( dst.type == OP_REG )
  6.2005 +                    dst.val = *dst.reg;
  6.2006 +                else if ( (rc = ops->read(dst.mem.seg, dst.mem.off,
  6.2007 +                                          &dst.val, 8, ctxt)) != 0 )
  6.2008 +                    goto done;
  6.2009 +            }
  6.2010 +            if ( (rc = ops->write(x86_seg_ss, sp_pre_dec(dst.bytes),
  6.2011 +                                  dst.val, dst.bytes, ctxt)) != 0 )
  6.2012 +                goto done;
  6.2013 +            dst.type = OP_NONE;
  6.2014 +            break;
  6.2015 +        case 7:
  6.2016 +            generate_exception_if(1, EXC_UD, -1);
  6.2017 +        default:
  6.2018 +            goto cannot_emulate;
  6.2019 +        }
  6.2020 +        break;
  6.2021 +    }
  6.2022 +
  6.2023 + writeback:
  6.2024 +    switch ( dst.type )
  6.2025 +    {
  6.2026 +    case OP_REG:
  6.2027 +        /* The 4-byte case *is* correct: in 64-bit mode we zero-extend. */
  6.2028 +        switch ( dst.bytes )
  6.2029 +        {
  6.2030 +        case 1: *(uint8_t  *)dst.reg = (uint8_t)dst.val; break;
  6.2031 +        case 2: *(uint16_t *)dst.reg = (uint16_t)dst.val; break;
  6.2032 +        case 4: *dst.reg = (uint32_t)dst.val; break; /* 64b: zero-ext */
  6.2033 +        case 8: *dst.reg = dst.val; break;
  6.2034 +        }
  6.2035 +        break;
  6.2036 +    case OP_MEM:
  6.2037 +        if ( !(d & Mov) && (dst.orig_val == dst.val) &&
  6.2038 +             !ctxt->force_writeback )
  6.2039 +            /* nothing to do */;
  6.2040 +        else if ( lock_prefix )
  6.2041 +            rc = ops->cmpxchg(
  6.2042 +                dst.mem.seg, dst.mem.off, dst.orig_val,
  6.2043 +                dst.val, dst.bytes, ctxt);
  6.2044 +        else
  6.2045 +            rc = ops->write(
  6.2046 +                dst.mem.seg, dst.mem.off, dst.val, dst.bytes, ctxt);
  6.2047 +        if ( rc != 0 )
  6.2048 +            goto done;
  6.2049 +    default:
  6.2050 +        break;
  6.2051 +    }
  6.2052 +
  6.2053 +    /* Commit shadow register state. */
  6.2054 +    _regs.eflags &= ~EFLG_RF;
  6.2055 +    *ctxt->regs = _regs;
  6.2056 +    if ( (_regs.eflags & EFLG_TF) && (rc == X86EMUL_OKAY) &&
  6.2057 +         (ops->inject_hw_exception != NULL) )
  6.2058 +        rc = ops->inject_hw_exception(EXC_DB, -1, ctxt) ? : X86EMUL_EXCEPTION;
  6.2059 +
  6.2060 + done:
  6.2061 +    return rc;
  6.2062 +
  6.2063 + special_insn:
  6.2064 +    dst.type = OP_NONE;
  6.2065 +
  6.2066 +    /*
  6.2067 +     * The only implicit-operands instructions allowed a LOCK prefix are
  6.2068 +     * CMPXCHG{8,16}B, MOV CRn, MOV DRn.
  6.2069 +     */
  6.2070 +    generate_exception_if(lock_prefix &&
  6.2071 +                          ((b < 0x20) || (b > 0x23)) && /* MOV CRn/DRn */
  6.2072 +                          (b != 0xc7),                  /* CMPXCHG{8,16}B */
  6.2073 +                          EXC_GP, 0);
  6.2074 +
  6.2075 +    if ( twobyte )
  6.2076 +        goto twobyte_special_insn;
  6.2077 +
  6.2078 +    switch ( b )
  6.2079 +    {
  6.2080 +    case 0x06: /* push %%es */ {
  6.2081 +        struct segment_register reg;
  6.2082 +        src.val = x86_seg_es;
  6.2083 +    push_seg:
  6.2084 +        fail_if(ops->read_segment == NULL);
  6.2085 +        if ( (rc = ops->read_segment(src.val, &reg, ctxt)) != 0 )
  6.2086 +            return rc;
  6.2087 +        /* 64-bit mode: PUSH defaults to a 64-bit operand. */
  6.2088 +        if ( mode_64bit() && (op_bytes == 4) )
  6.2089 +            op_bytes = 8;
  6.2090 +        if ( (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  6.2091 +                              reg.sel, op_bytes, ctxt)) != 0 )
  6.2092 +            goto done;
  6.2093 +        break;
  6.2094 +    }
  6.2095 +
  6.2096 +    case 0x07: /* pop %%es */
  6.2097 +        src.val = x86_seg_es;
  6.2098 +    pop_seg:
  6.2099 +        fail_if(ops->write_segment == NULL);
  6.2100 +        /* 64-bit mode: POP defaults to a 64-bit operand. */
  6.2101 +        if ( mode_64bit() && (op_bytes == 4) )
  6.2102 +            op_bytes = 8;
  6.2103 +        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  6.2104 +                             &dst.val, op_bytes, ctxt)) != 0 )
  6.2105 +            goto done;
  6.2106 +        if ( (rc = load_seg(src.val, (uint16_t)dst.val, ctxt, ops)) != 0 )
  6.2107 +            return rc;
  6.2108 +        break;
  6.2109 +
  6.2110 +    case 0x0e: /* push %%cs */
  6.2111 +        src.val = x86_seg_cs;
  6.2112 +        goto push_seg;
  6.2113 +
  6.2114 +    case 0x16: /* push %%ss */
  6.2115 +        src.val = x86_seg_ss;
  6.2116 +        goto push_seg;
  6.2117 +
  6.2118 +    case 0x17: /* pop %%ss */
  6.2119 +        src.val = x86_seg_ss;
  6.2120 +        ctxt->retire.flags.mov_ss = 1;
  6.2121 +        goto pop_seg;
  6.2122 +
  6.2123 +    case 0x1e: /* push %%ds */
  6.2124 +        src.val = x86_seg_ds;
  6.2125 +        goto push_seg;
  6.2126 +
  6.2127 +    case 0x1f: /* pop %%ds */
  6.2128 +        src.val = x86_seg_ds;
  6.2129 +        goto pop_seg;
  6.2130 +
  6.2131 +    case 0x27: /* daa */ {
  6.2132 +        uint8_t al = _regs.eax;
  6.2133 +        unsigned long eflags = _regs.eflags;
  6.2134 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.2135 +        _regs.eflags &= ~(EFLG_CF|EFLG_AF);
  6.2136 +        if ( ((al & 0x0f) > 9) || (eflags & EFLG_AF) )
  6.2137 +        {
  6.2138 +            *(uint8_t *)&_regs.eax += 6;
  6.2139 +            _regs.eflags |= EFLG_AF;
  6.2140 +        }
  6.2141 +        if ( (al > 0x99) || (eflags & EFLG_CF) )
  6.2142 +        {
  6.2143 +            *(uint8_t *)&_regs.eax += 0x60;
  6.2144 +            _regs.eflags |= EFLG_CF;
  6.2145 +        }
  6.2146 +        _regs.eflags &= ~(EFLG_SF|EFLG_ZF|EFLG_PF);
  6.2147 +        _regs.eflags |= ((uint8_t)_regs.eax == 0) ? EFLG_ZF : 0;
  6.2148 +        _regs.eflags |= (( int8_t)_regs.eax <  0) ? EFLG_SF : 0;
  6.2149 +        _regs.eflags |= even_parity(_regs.eax) ? EFLG_PF : 0;
  6.2150 +        break;
  6.2151 +    }
  6.2152 +
  6.2153 +    case 0x2f: /* das */ {
  6.2154 +        uint8_t al = _regs.eax;
  6.2155 +        unsigned long eflags = _regs.eflags;
  6.2156 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.2157 +        _regs.eflags &= ~(EFLG_CF|EFLG_AF);
  6.2158 +        if ( ((al & 0x0f) > 9) || (eflags & EFLG_AF) )
  6.2159 +        {
  6.2160 +            _regs.eflags |= EFLG_AF;
  6.2161 +            if ( (al < 6) || (eflags & EFLG_CF) )
  6.2162 +                _regs.eflags |= EFLG_CF;
  6.2163 +            *(uint8_t *)&_regs.eax -= 6;
  6.2164 +        }
  6.2165 +        if ( (al > 0x99) || (eflags & EFLG_CF) )
  6.2166 +        {
  6.2167 +            *(uint8_t *)&_regs.eax -= 0x60;
  6.2168 +            _regs.eflags |= EFLG_CF;
  6.2169 +        }
  6.2170 +        _regs.eflags &= ~(EFLG_SF|EFLG_ZF|EFLG_PF);
  6.2171 +        _regs.eflags |= ((uint8_t)_regs.eax == 0) ? EFLG_ZF : 0;
  6.2172 +        _regs.eflags |= (( int8_t)_regs.eax <  0) ? EFLG_SF : 0;
  6.2173 +        _regs.eflags |= even_parity(_regs.eax) ? EFLG_PF : 0;
  6.2174 +        break;
  6.2175 +    }
  6.2176 +
  6.2177 +    case 0x37: /* aaa */
  6.2178 +    case 0x3f: /* aas */
  6.2179 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.2180 +        _regs.eflags &= ~EFLG_CF;
  6.2181 +        if ( ((uint8_t)_regs.eax > 9) || (_regs.eflags & EFLG_AF) )
  6.2182 +        {
  6.2183 +            ((uint8_t *)&_regs.eax)[0] += (b == 0x37) ? 6 : -6;
  6.2184 +            ((uint8_t *)&_regs.eax)[1] += (b == 0x37) ? 1 : -1;
  6.2185 +            _regs.eflags |= EFLG_CF | EFLG_AF;
  6.2186 +        }
  6.2187 +        ((uint8_t *)&_regs.eax)[0] &= 0x0f;
  6.2188 +        break;
  6.2189 +
  6.2190 +    case 0x40 ... 0x4f: /* inc/dec reg */
  6.2191 +        dst.type  = OP_REG;
  6.2192 +        dst.reg   = decode_register(b & 7, &_regs, 0);
  6.2193 +        dst.bytes = op_bytes;
  6.2194 +        dst.val   = *dst.reg;
  6.2195 +        if ( b & 8 )
  6.2196 +            emulate_1op("dec", dst, _regs.eflags);
  6.2197 +        else
  6.2198 +            emulate_1op("inc", dst, _regs.eflags);
  6.2199 +        break;
  6.2200 +
  6.2201 +    case 0x50 ... 0x57: /* push reg */
  6.2202 +        src.val = *(unsigned long *)decode_register(
  6.2203 +            (b & 7) | ((rex_prefix & 1) << 3), &_regs, 0);
  6.2204 +        goto push;
  6.2205 +
  6.2206 +    case 0x58 ... 0x5f: /* pop reg */
  6.2207 +        dst.type  = OP_REG;
  6.2208 +        dst.reg   = decode_register(
  6.2209 +            (b & 7) | ((rex_prefix & 1) << 3), &_regs, 0);
  6.2210 +        dst.bytes = op_bytes;
  6.2211 +        if ( mode_64bit() && (dst.bytes == 4) )
  6.2212 +            dst.bytes = 8;
  6.2213 +        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(dst.bytes),
  6.2214 +                             &dst.val, dst.bytes, ctxt)) != 0 )
  6.2215 +            goto done;
  6.2216 +        break;
  6.2217 +
  6.2218 +    case 0x60: /* pusha */ {
  6.2219 +        int i;
  6.2220 +        unsigned long regs[] = {
  6.2221 +            _regs.eax, _regs.ecx, _regs.edx, _regs.ebx,
  6.2222 +            _regs.esp, _regs.ebp, _regs.esi, _regs.edi };
  6.2223 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.2224 +        for ( i = 0; i < 8; i++ )
  6.2225 +            if ( (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  6.2226 +                                  regs[i], op_bytes, ctxt)) != 0 )
  6.2227 +            goto done;
  6.2228 +        break;
  6.2229 +    }
  6.2230 +
  6.2231 +    case 0x61: /* popa */ {
  6.2232 +        int i;
  6.2233 +        unsigned long dummy_esp, *regs[] = {
  6.2234 +            (unsigned long *)&_regs.edi, (unsigned long *)&_regs.esi,
  6.2235 +            (unsigned long *)&_regs.ebp, (unsigned long *)&dummy_esp,
  6.2236 +            (unsigned long *)&_regs.ebx, (unsigned long *)&_regs.edx,
  6.2237 +            (unsigned long *)&_regs.ecx, (unsigned long *)&_regs.eax };
  6.2238 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.2239 +        for ( i = 0; i < 8; i++ )
  6.2240 +        {
  6.2241 +            if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  6.2242 +                                 &dst.val, op_bytes, ctxt)) != 0 )
  6.2243 +                goto done;
  6.2244 +            switch ( op_bytes )
  6.2245 +            {
  6.2246 +            case 1: *(uint8_t  *)regs[i] = (uint8_t)dst.val; break;
  6.2247 +            case 2: *(uint16_t *)regs[i] = (uint16_t)dst.val; break;
  6.2248 +            case 4: *regs[i] = (uint32_t)dst.val; break; /* 64b: zero-ext */
  6.2249 +            case 8: *regs[i] = dst.val; break;
  6.2250 +            }
  6.2251 +        }
  6.2252 +        break;
  6.2253 +    }
  6.2254 +
  6.2255 +    case 0x68: /* push imm{16,32,64} */
  6.2256 +        src.val = ((op_bytes == 2)
  6.2257 +                   ? (int32_t)insn_fetch_type(int16_t)
  6.2258 +                   : insn_fetch_type(int32_t));
  6.2259 +        goto push;
  6.2260 +
  6.2261 +    case 0x6a: /* push imm8 */
  6.2262 +        src.val = insn_fetch_type(int8_t);
  6.2263 +    push:
  6.2264 +        d |= Mov; /* force writeback */
  6.2265 +        dst.type  = OP_MEM;
  6.2266 +        dst.bytes = op_bytes;
  6.2267 +        if ( mode_64bit() && (dst.bytes == 4) )
  6.2268 +            dst.bytes = 8;
  6.2269 +        dst.val = src.val;
  6.2270 +        dst.mem.seg = x86_seg_ss;
  6.2271 +        dst.mem.off = sp_pre_dec(dst.bytes);
  6.2272 +        break;
  6.2273 +
  6.2274 +    case 0x6c ... 0x6d: /* ins %dx,%es:%edi */ {
  6.2275 +        unsigned long nr_reps = get_rep_prefix();
  6.2276 +        unsigned int port = (uint16_t)_regs.edx;
  6.2277 +        dst.bytes = !(b & 1) ? 1 : (op_bytes == 8) ? 4 : op_bytes;
  6.2278 +        dst.mem.seg = x86_seg_es;
  6.2279 +        dst.mem.off = truncate_ea(_regs.edi);
  6.2280 +        if ( (rc = ioport_access_check(port, dst.bytes, ctxt, ops)) != 0 )
  6.2281 +            goto done;
  6.2282 +        if ( (nr_reps > 1) && (ops->rep_ins != NULL) &&
  6.2283 +             ((rc = ops->rep_ins(port, dst.mem.seg, dst.mem.off, dst.bytes,
  6.2284 +                                 &nr_reps, ctxt)) != X86EMUL_UNHANDLEABLE) )
  6.2285 +        {
  6.2286 +            if ( rc != 0 )
  6.2287 +                goto done;
  6.2288 +        }
  6.2289 +        else
  6.2290 +        {
  6.2291 +            fail_if(ops->read_io == NULL);
  6.2292 +            if ( (rc = ops->read_io(port, dst.bytes, &dst.val, ctxt)) != 0 )
  6.2293 +                goto done;
  6.2294 +            dst.type = OP_MEM;
  6.2295 +            nr_reps = 1;
  6.2296 +        }
  6.2297 +        register_address_increment(
  6.2298 +            _regs.edi,
  6.2299 +            nr_reps * ((_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes));
  6.2300 +        put_rep_prefix(nr_reps);
  6.2301 +        break;
  6.2302 +    }
  6.2303 +
  6.2304 +    case 0x6e ... 0x6f: /* outs %esi,%dx */ {
  6.2305 +        unsigned long nr_reps = get_rep_prefix();
  6.2306 +        unsigned int port = (uint16_t)_regs.edx;
  6.2307 +        dst.bytes = !(b & 1) ? 1 : (op_bytes == 8) ? 4 : op_bytes;
  6.2308 +        if ( (rc = ioport_access_check(port, dst.bytes, ctxt, ops)) != 0 )
  6.2309 +            goto done;
  6.2310 +        if ( (nr_reps > 1) && (ops->rep_outs != NULL) &&
  6.2311 +             ((rc = ops->rep_outs(ea.mem.seg, truncate_ea(_regs.esi),
  6.2312 +                                  port, dst.bytes,
  6.2313 +                                  &nr_reps, ctxt)) != X86EMUL_UNHANDLEABLE) )
  6.2314 +        {
  6.2315 +            if ( rc != 0 )
  6.2316 +                goto done;
  6.2317 +        }
  6.2318 +        else
  6.2319 +        {
  6.2320 +            if ( (rc = ops->read(ea.mem.seg, truncate_ea(_regs.esi),
  6.2321 +                                 &dst.val, dst.bytes, ctxt)) != 0 )
  6.2322 +                goto done;
  6.2323 +            fail_if(ops->write_io == NULL);
  6.2324 +            if ( (rc = ops->write_io(port, dst.bytes, dst.val, ctxt)) != 0 )
  6.2325 +                goto done;
  6.2326 +            nr_reps = 1;
  6.2327 +        }
  6.2328 +        register_address_increment(
  6.2329 +            _regs.esi,
  6.2330 +            nr_reps * ((_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes));
  6.2331 +        put_rep_prefix(nr_reps);
  6.2332 +        break;
  6.2333 +    }
  6.2334 +
  6.2335 +    case 0x70 ... 0x7f: /* jcc (short) */ {
  6.2336 +        int rel = insn_fetch_type(int8_t);
  6.2337 +        if ( test_cc(b, _regs.eflags) )
  6.2338 +            jmp_rel(rel);
  6.2339 +        break;
  6.2340 +    }
  6.2341 +
  6.2342 +    case 0x90: /* nop / xchg %%r8,%%rax */
  6.2343 +        if ( !(rex_prefix & 1) )
  6.2344 +            break; /* nop */
  6.2345 +
  6.2346 +    case 0x91 ... 0x97: /* xchg reg,%%rax */
  6.2347 +        src.type = dst.type = OP_REG;
  6.2348 +        src.bytes = dst.bytes = op_bytes;
  6.2349 +        src.reg  = (unsigned long *)&_regs.eax;
  6.2350 +        src.val  = *src.reg;
  6.2351 +        dst.reg  = decode_register(
  6.2352 +            (b & 7) | ((rex_prefix & 1) << 3), &_regs, 0);
  6.2353 +        dst.val  = *dst.reg;
  6.2354 +        goto xchg;
  6.2355 +
  6.2356 +    case 0x98: /* cbw/cwde/cdqe */
  6.2357 +        switch ( op_bytes )
  6.2358 +        {
  6.2359 +        case 2: *(int16_t *)&_regs.eax = (int8_t)_regs.eax; break; /* cbw */
  6.2360 +        case 4: _regs.eax = (uint32_t)(int16_t)_regs.eax; break; /* cwde */
  6.2361 +        case 8: _regs.eax = (int32_t)_regs.eax; break; /* cdqe */
  6.2362 +        }
  6.2363 +        break;
  6.2364 +
  6.2365 +    case 0x99: /* cwd/cdq/cqo */
  6.2366 +        switch ( op_bytes )
  6.2367 +        {
  6.2368 +        case 2:
  6.2369 +            *(int16_t *)&_regs.edx = ((int16_t)_regs.eax < 0) ? -1 : 0;
  6.2370 +            break;
  6.2371 +        case 4:
  6.2372 +            _regs.edx = (uint32_t)(((int32_t)_regs.eax < 0) ? -1 : 0);
  6.2373 +            break;
  6.2374 +        case 8:
  6.2375 +            _regs.edx = (_regs.eax < 0) ? -1 : 0;
  6.2376 +            break;
  6.2377 +        }
  6.2378 +        break;
  6.2379 +
  6.2380 +    case 0x9a: /* call (far, absolute) */ {
  6.2381 +        struct segment_register reg;
  6.2382 +        uint16_t sel;
  6.2383 +        uint32_t eip;
  6.2384 +
  6.2385 +        fail_if(ops->read_segment == NULL);
  6.2386 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.2387 +
  6.2388 +        eip = insn_fetch_bytes(op_bytes);
  6.2389 +        sel = insn_fetch_type(uint16_t);
  6.2390 +
  6.2391 +        if ( (rc = ops->read_segment(x86_seg_cs, &reg, ctxt)) ||
  6.2392 +             (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  6.2393 +                              reg.sel, op_bytes, ctxt)) ||
  6.2394 +             (rc = ops->write(x86_seg_ss, sp_pre_dec(op_bytes),
  6.2395 +                              _regs.eip, op_bytes, ctxt)) )
  6.2396 +            goto done;
  6.2397 +
  6.2398 +        if ( (rc = load_seg(x86_seg_cs, sel, ctxt, ops)) != 0 )
  6.2399 +            goto done;
  6.2400 +        _regs.eip = eip;
  6.2401 +        break;
  6.2402 +    }
  6.2403 +
  6.2404 +    case 0x9b:  /* wait/fwait */
  6.2405 +        fail_if(ops->load_fpu_ctxt == NULL);
  6.2406 +        ops->load_fpu_ctxt(ctxt);
  6.2407 +        __emulate_fpu_insn("fwait");
  6.2408 +        break;
  6.2409 +
  6.2410 +    case 0x9c: /* pushf */
  6.2411 +        src.val = _regs.eflags;
  6.2412 +        goto push;
  6.2413 +
  6.2414 +    case 0x9d: /* popf */ {
  6.2415 +        uint32_t mask = EFLG_VIP | EFLG_VIF | EFLG_VM;
  6.2416 +        if ( !mode_ring0() )
  6.2417 +            mask |= EFLG_IOPL;
  6.2418 +        if ( !mode_iopl() )
  6.2419 +            mask |= EFLG_IF;
  6.2420 +        /* 64-bit mode: POP defaults to a 64-bit operand. */
  6.2421 +        if ( mode_64bit() && (op_bytes == 4) )
  6.2422 +            op_bytes = 8;
  6.2423 +        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  6.2424 +                             &dst.val, op_bytes, ctxt)) != 0 )
  6.2425 +            goto done;
  6.2426 +        if ( op_bytes == 2 )
  6.2427 +            dst.val = (uint16_t)dst.val | (_regs.eflags & 0xffff0000u);
  6.2428 +        dst.val &= 0x257fd5;
  6.2429 +        _regs.eflags &= mask;
  6.2430 +        _regs.eflags |= (uint32_t)(dst.val & ~mask) | 0x02;
  6.2431 +        break;
  6.2432 +    }
  6.2433 +
  6.2434 +    case 0x9e: /* sahf */
  6.2435 +        *(uint8_t *)&_regs.eflags = (((uint8_t *)&_regs.eax)[1] & 0xd7) | 0x02;
  6.2436 +        break;
  6.2437 +
  6.2438 +    case 0x9f: /* lahf */
  6.2439 +        ((uint8_t *)&_regs.eax)[1] = (_regs.eflags & 0xd7) | 0x02;
  6.2440 +        break;
  6.2441 +
  6.2442 +    case 0xa0 ... 0xa1: /* mov mem.offs,{%al,%ax,%eax,%rax} */
  6.2443 +        /* Source EA is not encoded via ModRM. */
  6.2444 +        dst.type  = OP_REG;
  6.2445 +        dst.reg   = (unsigned long *)&_regs.eax;
  6.2446 +        dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  6.2447 +        if ( (rc = ops->read(ea.mem.seg, insn_fetch_bytes(ad_bytes),
  6.2448 +                             &dst.val, dst.bytes, ctxt)) != 0 )
  6.2449 +            goto done;
  6.2450 +        break;
  6.2451 +
  6.2452 +    case 0xa2 ... 0xa3: /* mov {%al,%ax,%eax,%rax},mem.offs */
  6.2453 +        /* Destination EA is not encoded via ModRM. */
  6.2454 +        dst.type  = OP_MEM;
  6.2455 +        dst.mem.seg = ea.mem.seg;
  6.2456 +        dst.mem.off = insn_fetch_bytes(ad_bytes);
  6.2457 +        dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  6.2458 +        dst.val   = (unsigned long)_regs.eax;
  6.2459 +        break;
  6.2460 +
  6.2461 +    case 0xa4 ... 0xa5: /* movs */ {
  6.2462 +        unsigned long nr_reps = get_rep_prefix();
  6.2463 +        dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  6.2464 +        dst.mem.seg = x86_seg_es;
  6.2465 +        dst.mem.off = truncate_ea(_regs.edi);
  6.2466 +        if ( (nr_reps > 1) && (ops->rep_movs != NULL) &&
  6.2467 +             ((rc = ops->rep_movs(ea.mem.seg, truncate_ea(_regs.esi),
  6.2468 +                                  dst.mem.seg, dst.mem.off, dst.bytes,
  6.2469 +                                  &nr_reps, ctxt)) != X86EMUL_UNHANDLEABLE) )
  6.2470 +        {
  6.2471 +            if ( rc != 0 )
  6.2472 +                goto done;
  6.2473 +        }
  6.2474 +        else
  6.2475 +        {
  6.2476 +            if ( (rc = ops->read(ea.mem.seg, truncate_ea(_regs.esi),
  6.2477 +                                 &dst.val, dst.bytes, ctxt)) != 0 )
  6.2478 +                goto done;
  6.2479 +            dst.type = OP_MEM;
  6.2480 +            nr_reps = 1;
  6.2481 +        }
  6.2482 +        register_address_increment(
  6.2483 +            _regs.esi,
  6.2484 +            nr_reps * ((_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes));
  6.2485 +        register_address_increment(
  6.2486 +            _regs.edi,
  6.2487 +            nr_reps * ((_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes));
  6.2488 +        put_rep_prefix(nr_reps);
  6.2489 +        break;
  6.2490 +    }
  6.2491 +
  6.2492 +    case 0xa6 ... 0xa7: /* cmps */ {
  6.2493 +        unsigned long next_eip = _regs.eip;
  6.2494 +        get_rep_prefix();
  6.2495 +        src.bytes = dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  6.2496 +        if ( (rc = ops->read(ea.mem.seg, truncate_ea(_regs.esi),
  6.2497 +                             &dst.val, dst.bytes, ctxt)) ||
  6.2498 +             (rc = ops->read(x86_seg_es, truncate_ea(_regs.edi),
  6.2499 +                             &src.val, src.bytes, ctxt)) )
  6.2500 +            goto done;
  6.2501 +        register_address_increment(
  6.2502 +            _regs.esi, (_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes);
  6.2503 +        register_address_increment(
  6.2504 +            _regs.edi, (_regs.eflags & EFLG_DF) ? -src.bytes : src.bytes);
  6.2505 +        put_rep_prefix(1);
  6.2506 +        /* cmp: dst - src ==> src=*%%edi,dst=*%%esi ==> *%%esi - *%%edi */
  6.2507 +        emulate_2op_SrcV("cmp", src, dst, _regs.eflags);
  6.2508 +        if ( ((rep_prefix == REPE_PREFIX) && !(_regs.eflags & EFLG_ZF)) ||
  6.2509 +             ((rep_prefix == REPNE_PREFIX) && (_regs.eflags & EFLG_ZF)) )
  6.2510 +            _regs.eip = next_eip;
  6.2511 +        break;
  6.2512 +    }
  6.2513 +
  6.2514 +    case 0xaa ... 0xab: /* stos */ {
  6.2515 +        /* unsigned long max_reps = */get_rep_prefix();
  6.2516 +        dst.type  = OP_MEM;
  6.2517 +        dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  6.2518 +        dst.mem.seg = x86_seg_es;
  6.2519 +        dst.mem.off = truncate_ea(_regs.edi);
  6.2520 +        dst.val   = _regs.eax;
  6.2521 +        register_address_increment(
  6.2522 +            _regs.edi, (_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes);
  6.2523 +        put_rep_prefix(1);
  6.2524 +        break;
  6.2525 +    }
  6.2526 +
  6.2527 +    case 0xac ... 0xad: /* lods */ {
  6.2528 +        /* unsigned long max_reps = */get_rep_prefix();
  6.2529 +        dst.type  = OP_REG;
  6.2530 +        dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  6.2531 +        dst.reg   = (unsigned long *)&_regs.eax;
  6.2532 +        if ( (rc = ops->read(ea.mem.seg, truncate_ea(_regs.esi),
  6.2533 +                             &dst.val, dst.bytes, ctxt)) != 0 )
  6.2534 +            goto done;
  6.2535 +        register_address_increment(
  6.2536 +            _regs.esi, (_regs.eflags & EFLG_DF) ? -dst.bytes : dst.bytes);
  6.2537 +        put_rep_prefix(1);
  6.2538 +        break;
  6.2539 +    }
  6.2540 +
  6.2541 +    case 0xae ... 0xaf: /* scas */ {
  6.2542 +        unsigned long next_eip = _regs.eip;
  6.2543 +        get_rep_prefix();
  6.2544 +        src.bytes = dst.bytes = (d & ByteOp) ? 1 : op_bytes;
  6.2545 +        dst.val = _regs.eax;
  6.2546 +        if ( (rc = ops->read(x86_seg_es, truncate_ea(_regs.edi),
  6.2547 +                             &src.val, src.bytes, ctxt)) != 0 )
  6.2548 +            goto done;
  6.2549 +        register_address_increment(
  6.2550 +            _regs.edi, (_regs.eflags & EFLG_DF) ? -src.bytes : src.bytes);
  6.2551 +        put_rep_prefix(1);
  6.2552 +        /* cmp: dst - src ==> src=*%%edi,dst=%%eax ==> %%eax - *%%edi */
  6.2553 +        emulate_2op_SrcV("cmp", src, dst, _regs.eflags);
  6.2554 +        if ( ((rep_prefix == REPE_PREFIX) && !(_regs.eflags & EFLG_ZF)) ||
  6.2555 +             ((rep_prefix == REPNE_PREFIX) && (_regs.eflags & EFLG_ZF)) )
  6.2556 +            _regs.eip = next_eip;
  6.2557 +        break;
  6.2558 +    }
  6.2559 +
  6.2560 +    case 0xc2: /* ret imm16 (near) */
  6.2561 +    case 0xc3: /* ret (near) */ {
  6.2562 +        int offset = (b == 0xc2) ? insn_fetch_type(uint16_t) : 0;
  6.2563 +        op_bytes = mode_64bit() ? 8 : op_bytes;
  6.2564 +        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes + offset),
  6.2565 +                             &dst.val, op_bytes, ctxt)) != 0 )
  6.2566 +            goto done;
  6.2567 +        _regs.eip = dst.val;
  6.2568 +        break;
  6.2569 +    }
  6.2570 +
  6.2571 +    case 0xc8: /* enter imm16,imm8 */ {
  6.2572 +        uint16_t size = insn_fetch_type(uint16_t);
  6.2573 +        uint8_t depth = insn_fetch_type(uint8_t) & 31;
  6.2574 +        int i;
  6.2575 +
  6.2576 +        dst.type = OP_REG;
  6.2577 +        dst.bytes = (mode_64bit() && (op_bytes == 4)) ? 8 : op_bytes;
  6.2578 +        dst.reg = (unsigned long *)&_regs.ebp;
  6.2579 +        if ( (rc = ops->write(x86_seg_ss, sp_pre_dec(dst.bytes),
  6.2580 +                              _regs.ebp, dst.bytes, ctxt)) )
  6.2581 +            goto done;
  6.2582 +        dst.val = _regs.esp;
  6.2583 +
  6.2584 +        if ( depth > 0 )
  6.2585 +        {
  6.2586 +            for ( i = 1; i < depth; i++ )
  6.2587 +            {
  6.2588 +                unsigned long ebp, temp_data;
  6.2589 +                ebp = truncate_word(_regs.ebp - i*dst.bytes, ctxt->sp_size/8);
  6.2590 +                if ( (rc = ops->read(x86_seg_ss, ebp,
  6.2591 +                                     &temp_data, dst.bytes, ctxt)) ||
  6.2592 +                     (rc = ops->write(x86_seg_ss, sp_pre_dec(dst.bytes),
  6.2593 +                                      temp_data, dst.bytes, ctxt)) )
  6.2594 +                    goto done;
  6.2595 +            }
  6.2596 +            if ( (rc = ops->write(x86_seg_ss, sp_pre_dec(dst.bytes),
  6.2597 +                                  dst.val, dst.bytes, ctxt)) )
  6.2598 +                goto done;
  6.2599 +        }
  6.2600 +
  6.2601 +        sp_pre_dec(size);
  6.2602 +        break;
  6.2603 +    }
  6.2604 +
  6.2605 +    case 0xc9: /* leave */
  6.2606 +        /* First writeback, to %%esp. */
  6.2607 +        dst.type = OP_REG;
  6.2608 +        dst.bytes = (mode_64bit() && (op_bytes == 4)) ? 8 : op_bytes;
  6.2609 +        dst.reg = (unsigned long *)&_regs.esp;
  6.2610 +        dst.val = _regs.ebp;
  6.2611 +
  6.2612 +        /* Flush first writeback, since there is a second. */
  6.2613 +        switch ( dst.bytes )
  6.2614 +        {
  6.2615 +        case 1: *(uint8_t  *)dst.reg = (uint8_t)dst.val; break;
  6.2616 +        case 2: *(uint16_t *)dst.reg = (uint16_t)dst.val; break;
  6.2617 +        case 4: *dst.reg = (uint32_t)dst.val; break; /* 64b: zero-ext */
  6.2618 +        case 8: *dst.reg = dst.val; break;
  6.2619 +        }
  6.2620 +
  6.2621 +        /* Second writeback, to %%ebp. */
  6.2622 +        dst.reg = (unsigned long *)&_regs.ebp;
  6.2623 +        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(dst.bytes),
  6.2624 +                             &dst.val, dst.bytes, ctxt)) )
  6.2625 +            goto done;
  6.2626 +        break;
  6.2627 +
  6.2628 +    case 0xca: /* ret imm16 (far) */
  6.2629 +    case 0xcb: /* ret (far) */ {
  6.2630 +        int offset = (b == 0xca) ? insn_fetch_type(uint16_t) : 0;
  6.2631 +        op_bytes = mode_64bit() ? 8 : op_bytes;
  6.2632 +        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  6.2633 +                             &dst.val, op_bytes, ctxt)) || 
  6.2634 +             (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes + offset),
  6.2635 +                             &src.val, op_bytes, ctxt)) ||
  6.2636 +             (rc = load_seg(x86_seg_cs, (uint16_t)src.val, ctxt, ops)) )
  6.2637 +            goto done;
  6.2638 +        _regs.eip = dst.val;
  6.2639 +        break;
  6.2640 +    }
  6.2641 +
  6.2642 +    case 0xcc: /* int3 */
  6.2643 +        src.val = EXC_BP;
  6.2644 +        goto swint;
  6.2645 +
  6.2646 +    case 0xcd: /* int imm8 */
  6.2647 +        src.val = insn_fetch_type(uint8_t);
  6.2648 +    swint:
  6.2649 +        fail_if(ops->inject_sw_interrupt == NULL);
  6.2650 +        rc = ops->inject_sw_interrupt(src.val, _regs.eip - ctxt->regs->eip,
  6.2651 +                                      ctxt) ? : X86EMUL_EXCEPTION;
  6.2652 +        goto done;
  6.2653 +
  6.2654 +    case 0xce: /* into */
  6.2655 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.2656 +        if ( !(_regs.eflags & EFLG_OF) )
  6.2657 +            break;
  6.2658 +        src.val = EXC_OF;
  6.2659 +        goto swint;
  6.2660 +
  6.2661 +    case 0xcf: /* iret */ {
  6.2662 +        unsigned long cs, eip, eflags;
  6.2663 +        uint32_t mask = EFLG_VIP | EFLG_VIF | EFLG_VM;
  6.2664 +        if ( !mode_ring0() )
  6.2665 +            mask |= EFLG_IOPL;
  6.2666 +        if ( !mode_iopl() )
  6.2667 +            mask |= EFLG_IF;
  6.2668 +        fail_if(!in_realmode(ctxt, ops));
  6.2669 +        if ( (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  6.2670 +                             &eip, op_bytes, ctxt)) ||
  6.2671 +             (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  6.2672 +                             &cs, op_bytes, ctxt)) ||
  6.2673 +             (rc = ops->read(x86_seg_ss, sp_post_inc(op_bytes),
  6.2674 +                             &eflags, op_bytes, ctxt)) )
  6.2675 +            goto done;
  6.2676 +        if ( op_bytes == 2 )
  6.2677 +            eflags = (uint16_t)eflags | (_regs.eflags & 0xffff0000u);
  6.2678 +        eflags &= 0x257fd5;
  6.2679 +        _regs.eflags &= mask;
  6.2680 +        _regs.eflags |= (uint32_t)(eflags & ~mask) | 0x02;
  6.2681 +        _regs.eip = eip;
  6.2682 +        if ( (rc = load_seg(x86_seg_cs, (uint16_t)cs, ctxt, ops)) != 0 )
  6.2683 +            goto done;
  6.2684 +        break;
  6.2685 +    }
  6.2686 +
  6.2687 +    case 0xd4: /* aam */ {
  6.2688 +        unsigned int base = insn_fetch_type(uint8_t);
  6.2689 +        uint8_t al = _regs.eax;
  6.2690 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.2691 +        generate_exception_if(base == 0, EXC_DE, -1);
  6.2692 +        *(uint16_t *)&_regs.eax = ((al / base) << 8) | (al % base);
  6.2693 +        _regs.eflags &= ~(EFLG_SF|EFLG_ZF|EFLG_PF);
  6.2694 +        _regs.eflags |= ((uint8_t)_regs.eax == 0) ? EFLG_ZF : 0;
  6.2695 +        _regs.eflags |= (( int8_t)_regs.eax <  0) ? EFLG_SF : 0;
  6.2696 +        _regs.eflags |= even_parity(_regs.eax) ? EFLG_PF : 0;
  6.2697 +        break;
  6.2698 +    }
  6.2699 +
  6.2700 +    case 0xd5: /* aad */ {
  6.2701 +        unsigned int base = insn_fetch_type(uint8_t);
  6.2702 +        uint16_t ax = _regs.eax;
  6.2703 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.2704 +        *(uint16_t *)&_regs.eax = (uint8_t)(ax + ((ax >> 8) * base));
  6.2705 +        _regs.eflags &= ~(EFLG_SF|EFLG_ZF|EFLG_PF);
  6.2706 +        _regs.eflags |= ((uint8_t)_regs.eax == 0) ? EFLG_ZF : 0;
  6.2707 +        _regs.eflags |= (( int8_t)_regs.eax <  0) ? EFLG_SF : 0;
  6.2708 +        _regs.eflags |= even_parity(_regs.eax) ? EFLG_PF : 0;
  6.2709 +        break;
  6.2710 +    }
  6.2711 +
  6.2712 +    case 0xd6: /* salc */
  6.2713 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.2714 +        *(uint8_t *)&_regs.eax = (_regs.eflags & EFLG_CF) ? 0xff : 0x00;
  6.2715 +        break;
  6.2716 +
  6.2717 +    case 0xd7: /* xlat */ {
  6.2718 +        unsigned long al = (uint8_t)_regs.eax;
  6.2719 +        if ( (rc = ops->read(ea.mem.seg, truncate_ea(_regs.ebx + al),
  6.2720 +                             &al, 1, ctxt)) != 0 )
  6.2721 +            goto done;
  6.2722 +        *(uint8_t *)&_regs.eax = al;
  6.2723 +        break;
  6.2724 +    }
  6.2725 +
  6.2726 +    case 0xd9: /* FPU 0xd9 */
  6.2727 +        fail_if(ops->load_fpu_ctxt == NULL);
  6.2728 +        ops->load_fpu_ctxt(ctxt);
  6.2729 +        switch ( modrm )
  6.2730 +        {
  6.2731 +        case 0xc0: __emulate_fpu_insn(".byte 0xd9,0xc0"); break;
  6.2732 +        case 0xc1: __emulate_fpu_insn(".byte 0xd9,0xc1"); break;
  6.2733 +        case 0xc2: __emulate_fpu_insn(".byte 0xd9,0xc2"); break;
  6.2734 +        case 0xc3: __emulate_fpu_insn(".byte 0xd9,0xc3"); break;
  6.2735 +        case 0xc4: __emulate_fpu_insn(".byte 0xd9,0xc4"); break;
  6.2736 +        case 0xc5: __emulate_fpu_insn(".byte 0xd9,0xc5"); break;
  6.2737 +        case 0xc6: __emulate_fpu_insn(".byte 0xd9,0xc6"); break;
  6.2738 +        case 0xc7: __emulate_fpu_insn(".byte 0xd9,0xc7"); break;
  6.2739 +        case 0xe0: __emulate_fpu_insn(".byte 0xd9,0xe0"); break;
  6.2740 +        case 0xe8: __emulate_fpu_insn(".byte 0xd9,0xe8"); break;
  6.2741 +        case 0xee: __emulate_fpu_insn(".byte 0xd9,0xee"); break;
  6.2742 +        default:
  6.2743 +            fail_if((modrm_reg & 7) != 7);
  6.2744 +            fail_if(modrm >= 0xc0);
  6.2745 +            /* fnstcw m2byte */
  6.2746 +            ea.bytes = 2;
  6.2747 +            dst = ea;
  6.2748 +            asm volatile ( "fnstcw %0" : "=m" (dst.val) );
  6.2749 +        }
  6.2750 +        break;
  6.2751 +
  6.2752 +    case 0xdb: /* FPU 0xdb */
  6.2753 +        fail_if(ops->load_fpu_ctxt == NULL);
  6.2754 +        ops->load_fpu_ctxt(ctxt);
  6.2755 +        fail_if(modrm != 0xe3);
  6.2756 +        /* fninit */
  6.2757 +        asm volatile ( "fninit" );
  6.2758 +        break;
  6.2759 +
  6.2760 +    case 0xdd: /* FPU 0xdd */
  6.2761 +        fail_if(ops->load_fpu_ctxt == NULL);
  6.2762 +        ops->load_fpu_ctxt(ctxt);
  6.2763 +        fail_if((modrm_reg & 7) != 7);
  6.2764 +        fail_if(modrm >= 0xc0);
  6.2765 +        /* fnstsw m2byte */
  6.2766 +        ea.bytes = 2;
  6.2767 +        dst = ea;
  6.2768 +        asm volatile ( "fnstsw %0" : "=m" (dst.val) );
  6.2769 +        break;
  6.2770 +
  6.2771 +    case 0xde: /* FPU 0xde */
  6.2772 +        fail_if(ops->load_fpu_ctxt == NULL);
  6.2773 +        ops->load_fpu_ctxt(ctxt);
  6.2774 +        switch ( modrm )
  6.2775 +        {
  6.2776 +        case 0xd9: __emulate_fpu_insn(".byte 0xde,0xd9"); break;
  6.2777 +        case 0xf8: __emulate_fpu_insn(".byte 0xde,0xf8"); break;
  6.2778 +        case 0xf9: __emulate_fpu_insn(".byte 0xde,0xf9"); break;
  6.2779 +        case 0xfa: __emulate_fpu_insn(".byte 0xde,0xfa"); break;
  6.2780 +        case 0xfb: __emulate_fpu_insn(".byte 0xde,0xfb"); break;
  6.2781 +        case 0xfc: __emulate_fpu_insn(".byte 0xde,0xfc"); break;
  6.2782 +        case 0xfd: __emulate_fpu_insn(".byte 0xde,0xfd"); break;
  6.2783 +        case 0xfe: __emulate_fpu_insn(".byte 0xde,0xfe"); break;
  6.2784 +        case 0xff: __emulate_fpu_insn(".byte 0xde,0xff"); break;
  6.2785 +        default: goto cannot_emulate;
  6.2786 +        }
  6.2787 +        break;
  6.2788 +
  6.2789 +    case 0xdf: /* FPU 0xdf */
  6.2790 +        fail_if(ops->load_fpu_ctxt == NULL);
  6.2791 +        ops->load_fpu_ctxt(ctxt);
  6.2792 +        fail_if(modrm != 0xe0);
  6.2793 +        /* fnstsw %ax */
  6.2794 +        dst.bytes = 2;
  6.2795 +        dst.type = OP_REG;
  6.2796 +        dst.reg = (unsigned long *)&_regs.eax;
  6.2797 +        asm volatile ( "fnstsw %0" : "=m" (dst.val) );
  6.2798 +        break;
  6.2799 +
  6.2800 +    case 0xe0 ... 0xe2: /* loop{,z,nz} */ {
  6.2801 +        int rel = insn_fetch_type(int8_t);
  6.2802 +        int do_jmp = !(_regs.eflags & EFLG_ZF); /* loopnz */
  6.2803 +        if ( b == 0xe1 )
  6.2804 +            do_jmp = !do_jmp; /* loopz */
  6.2805 +        else if ( b == 0xe2 )
  6.2806 +            do_jmp = 1; /* loop */
  6.2807 +        switch ( ad_bytes )
  6.2808 +        {
  6.2809 +        case 2:
  6.2810 +            do_jmp &= --(*(uint16_t *)&_regs.ecx) != 0;
  6.2811 +            break;
  6.2812 +        case 4:
  6.2813 +            do_jmp &= --(*(uint32_t *)&_regs.ecx) != 0;
  6.2814 +            _regs.ecx = (uint32_t)_regs.ecx; /* zero extend in x86/64 mode */
  6.2815 +            break;
  6.2816 +        default: /* case 8: */
  6.2817 +            do_jmp &= --_regs.ecx != 0;
  6.2818 +            break;
  6.2819 +        }
  6.2820 +        if ( do_jmp )
  6.2821 +            jmp_rel(rel);
  6.2822 +        break;
  6.2823 +    }
  6.2824 +
  6.2825 +    case 0xe3: /* jcxz/jecxz (short) */ {
  6.2826 +        int rel = insn_fetch_type(int8_t);
  6.2827 +        if ( (ad_bytes == 2) ? !(uint16_t)_regs.ecx :
  6.2828 +             (ad_bytes == 4) ? !(uint32_t)_regs.ecx : !_regs.ecx )
  6.2829 +            jmp_rel(rel);
  6.2830 +        break;
  6.2831 +    }
  6.2832 +
  6.2833 +    case 0xe4: /* in imm8,%al */
  6.2834 +    case 0xe5: /* in imm8,%eax */
  6.2835 +    case 0xe6: /* out %al,imm8 */
  6.2836 +    case 0xe7: /* out %eax,imm8 */
  6.2837 +    case 0xec: /* in %dx,%al */
  6.2838 +    case 0xed: /* in %dx,%eax */
  6.2839 +    case 0xee: /* out %al,%dx */
  6.2840 +    case 0xef: /* out %eax,%dx */ {
  6.2841 +        unsigned int port = ((b < 0xe8)
  6.2842 +                             ? insn_fetch_type(uint8_t)
  6.2843 +                             : (uint16_t)_regs.edx);
  6.2844 +        op_bytes = !(b & 1) ? 1 : (op_bytes == 8) ? 4 : op_bytes;
  6.2845 +        if ( (rc = ioport_access_check(port, op_bytes, ctxt, ops)) != 0 )
  6.2846 +            goto done;
  6.2847 +        if ( b & 2 )
  6.2848 +        {
  6.2849 +            /* out */
  6.2850 +            fail_if(ops->write_io == NULL);
  6.2851 +            rc = ops->write_io(port, op_bytes, _regs.eax, ctxt);
  6.2852 +            
  6.2853 +        }
  6.2854 +        else
  6.2855 +        {
  6.2856 +            /* in */
  6.2857 +            dst.type  = OP_REG;
  6.2858 +            dst.bytes = op_bytes;
  6.2859 +            dst.reg   = (unsigned long *)&_regs.eax;
  6.2860 +            fail_if(ops->read_io == NULL);
  6.2861 +            rc = ops->read_io(port, dst.bytes, &dst.val, ctxt);
  6.2862 +        }
  6.2863 +        if ( rc != 0 )
  6.2864 +            goto done;
  6.2865 +        break;
  6.2866 +    }
  6.2867 +
  6.2868 +    case 0xe8: /* call (near) */ {
  6.2869 +        int rel = (((op_bytes == 2) && !mode_64bit())
  6.2870 +                   ? (int32_t)insn_fetch_type(int16_t)
  6.2871 +                   : insn_fetch_type(int32_t));
  6.2872 +        op_bytes = mode_64bit() ? 8 : op_bytes;
  6.2873 +        src.val = _regs.eip;
  6.2874 +        jmp_rel(rel);
  6.2875 +        goto push;
  6.2876 +    }
  6.2877 +
  6.2878 +    case 0xe9: /* jmp (near) */ {
  6.2879 +        int rel = (((op_bytes == 2) && !mode_64bit())
  6.2880 +                   ? (int32_t)insn_fetch_type(int16_t)
  6.2881 +                   : insn_fetch_type(int32_t));
  6.2882 +        jmp_rel(rel);
  6.2883 +        break;
  6.2884 +    }
  6.2885 +
  6.2886 +    case 0xea: /* jmp (far, absolute) */ {
  6.2887 +        uint16_t sel;
  6.2888 +        uint32_t eip;
  6.2889 +        generate_exception_if(mode_64bit(), EXC_UD, -1);
  6.2890 +        eip = insn_fetch_bytes(op_bytes);
  6.2891 +        sel = insn_fetch_type(uint16_t);
  6.2892 +        if ( (rc = load_seg(x86_seg_cs, sel, ctxt, ops)) != 0 )
  6.2893 +            goto done;
  6.2894 +        _regs.eip = eip;
  6.2895 +        break;
  6.2896 +    }
  6.2897 +
  6.2898 +    case 0xeb: /* jmp (short) */ {
  6.2899 +        int rel = insn_fetch_type(int8_t);
  6.2900 +        jmp_rel(rel);
  6.2901 +        break;
  6.2902 +    }
  6.2903 +
  6.2904 +    case 0xf1: /* int1 (icebp) */
  6.2905 +        src.val = EXC_DB;
  6.2906 +        goto swint;
  6.2907 +
  6.2908 +    case 0xf4: /* hlt */
  6.2909 +        ctxt->retire.flags.hlt = 1;
  6.2910 +        break;
  6.2911 +
  6.2912 +    case 0xf5: /* cmc */
  6.2913 +        _regs.eflags ^= EFLG_CF;
  6.2914 +        break;
  6.2915 +
  6.2916 +    case 0xf8: /* clc */
  6.2917 +        _regs.eflags &= ~EFLG_CF;
  6.2918 +        break;
  6.2919 +
  6.2920 +    case 0xf9: /* stc */
  6.2921 +        _regs.eflags |= EFLG_CF;
  6.2922 +        break;
  6.2923 +
  6.2924 +    case 0xfa: /* cli */
  6.2925 +        generate_exception_if(!mode_iopl(), EXC_GP, 0);
  6.2926 +        _regs.eflags &= ~EFLG_IF;
  6.2927 +        break;
  6.2928 +
  6.2929 +    case 0xfb: /* sti */
  6.2930 +        generate_exception_if(!mode_iopl(), EXC_GP, 0);
  6.2931 +        if ( !(_regs.eflags & EFLG_IF) )
  6.2932 +        {
  6.2933 +            _regs.eflags |= EFLG_IF;
  6.2934 +            ctxt->retire.flags.sti = 1;
  6.2935 +        }
  6.2936 +        break;
  6.2937 +
  6.2938 +    case 0xfc: /* cld */
  6.2939 +        _regs.eflags &= ~EFLG_DF;
  6.2940 +        break;
  6.2941 +
  6.2942 +    case 0xfd: /* std */
  6.2943 +        _regs.eflags |= EFLG_DF;
  6.2944 +        break;
  6.2945 +    }
  6.2946 +    goto writeback;
  6.2947 +
  6.2948 + twobyte_insn:
  6.2949 +    switch ( b )
  6.2950 +    {
  6.2951 +    case 0x40 ... 0x4f: /* cmovcc */
  6.2952 +        dst.val = src.val;
  6.2953 +        if ( !test_cc(b, _regs.eflags) )
  6.2954 +            dst.type = OP_NONE;
  6.2955 +        break;
  6.2956 +
  6.2957 +    case 0x90 ... 0x9f: /* setcc */
  6.2958 +        dst.val = test_cc(b, _regs.eflags);
  6.2959 +        break;
  6.2960 +
  6.2961 +    case 0xb0 ... 0xb1: /* cmpxchg */
  6.2962 +        /* Save real source value, then compare EAX against destination. */
  6.2963 +        src.orig_val = src.val;
  6.2964 +        src.val = _regs.eax;
  6.2965 +        emulate_2op_SrcV("cmp", src, dst, _regs.eflags);
  6.2966 +        if ( _regs.eflags & EFLG_ZF )
  6.2967 +        {
  6.2968 +            /* Success: write back to memory. */
  6.2969 +            dst.val = src.orig_val;
  6.2970 +        }
  6.2971 +        else
  6.2972 +        {
  6.2973 +            /* Failure: write the value we saw to EAX. */
  6.2974 +            dst.type = OP_REG;
  6.2975 +            dst.reg  = (unsigned long *)&_regs.eax;
  6.2976 +        }
  6.2977 +        break;
  6.2978 +
  6.2979 +    case 0xa3: bt: /* bt */
  6.2980 +        emulate_2op_SrcV_nobyte("bt", src, dst, _regs.eflags);
  6.2981 +        break;
  6.2982 +
  6.2983 +    case 0xa4: /* shld imm8,r,r/m */
  6.2984 +    case 0xa5: /* shld %%cl,r,r/m */
  6.2985 +    case 0xac: /* shrd imm8,r,r/m */
  6.2986 +    case 0xad: /* shrd %%cl,r,r/m */ {
  6.2987 +        uint8_t shift, width = dst.bytes << 3;
  6.2988 +        shift = (b & 1) ? (uint8_t)_regs.ecx : insn_fetch_type(uint8_t);
  6.2989 +        if ( (shift &= width - 1) == 0 )
  6.2990 +            break;
  6.2991 +        dst.orig_val = truncate_word(dst.val, dst.bytes);
  6.2992 +        dst.val = ((shift == width) ? src.val :
  6.2993 +                   (b & 8) ?
  6.2994 +                   /* shrd */
  6.2995 +                   ((dst.orig_val >> shift) |
  6.2996 +                    truncate_word(src.val << (width - shift), dst.bytes)) :
  6.2997 +                   /* shld */
  6.2998 +                   ((dst.orig_val << shift) |
  6.2999 +                    ((src.val >> (width - shift)) & ((1ull << shift) - 1))));
  6.3000 +        dst.val = truncate_word(dst.val, dst.bytes);
  6.3001 +        _regs.eflags &= ~(EFLG_OF|EFLG_SF|EFLG_ZF|EFLG_PF|EFLG_CF);
  6.3002 +        if ( (dst.val >> ((b & 8) ? (shift - 1) : (width - shift))) & 1 )
  6.3003 +            _regs.eflags |= EFLG_CF;
  6.3004 +        if ( ((dst.val ^ dst.orig_val) >> (width - 1)) & 1 )
  6.3005 +            _regs.eflags |= EFLG_OF;
  6.3006 +        _regs.eflags |= ((dst.val >> (width - 1)) & 1) ? EFLG_SF : 0;
  6.3007 +        _regs.eflags |= (dst.val == 0) ? EFLG_ZF : 0;
  6.3008 +        _regs.eflags |= even_parity(dst.val) ? EFLG_PF : 0;
  6.3009 +        break;
  6.3010 +    }
  6.3011 +
  6.3012 +    case 0xb3: btr: /* btr */
  6.3013 +        emulate_2op_SrcV_nobyte("btr", src, dst, _regs.eflags);
  6.3014 +        break;
  6.3015 +
  6.3016 +    case 0xab: bts: /* bts */
  6.3017 +        emulate_2op_SrcV_nobyte("bts", src, dst, _regs.eflags);
  6.3018 +        break;
  6.3019 +
  6.3020 +    case 0xaf: /* imul */
  6.3021 +        _regs.eflags &= ~(EFLG_OF|EFLG_CF);
  6.3022 +        switch ( dst.bytes )
  6.3023 +        {
  6.3024 +        case 2:
  6.3025 +            dst.val = ((uint32_t)(int16_t)src.val *
  6.3026 +                       (uint32_t)(int16_t)dst.val);
  6.3027 +            if ( (int16_t)dst.val != (uint32_t)dst.val )
  6.3028 +                _regs.eflags |= EFLG_OF|EFLG_CF;
  6.3029 +            break;
  6.3030 +#ifdef __x86_64__
  6.3031 +        case 4:
  6.3032 +            dst.val = ((uint64_t)(int32_t)src.val *
  6.3033 +                       (uint64_t)(int32_t)dst.val);
  6.3034 +            if ( (int32_t)dst.val != dst.val )
  6.3035 +                _regs.eflags |= EFLG_OF|EFLG_CF;
  6.3036 +            break;
  6.3037 +#endif
  6.3038 +        default: {
  6.3039 +            unsigned long m[2] = { src.val, dst.val };
  6.3040 +            if ( imul_dbl(m) )
  6.3041 +                _regs.eflags |= EFLG_OF|EFLG_CF;
  6.3042 +            dst.val = m[0];
  6.3043 +            break;
  6.3044 +        }
  6.3045 +        }
  6.3046 +        break;
  6.3047 +
  6.3048 +    case 0xb2: /* lss */
  6.3049 +        dst.val = x86_seg_ss;
  6.3050 +        goto les;
  6.3051 +
  6.3052 +    case 0xb4: /* lfs */
  6.3053 +        dst.val = x86_seg_fs;
  6.3054 +        goto les;
  6.3055 +
  6.3056 +    case 0xb5: /* lgs */
  6.3057 +        dst.val = x86_seg_gs;
  6.3058 +        goto les;
  6.3059 +
  6.3060 +    case 0xb6: /* movzx rm8,r{16,32,64} */
  6.3061 +        /* Recompute DstReg as we may have decoded AH/BH/CH/DH. */
  6.3062 +        dst.reg   = decode_register(modrm_reg, &_regs, 0);
  6.3063 +        dst.bytes = op_bytes;
  6.3064 +        dst.val   = (uint8_t)src.val;
  6.3065 +        break;
  6.3066 +
  6.3067 +    case 0xbc: /* bsf */ {
  6.3068 +        int zf;
  6.3069 +        asm ( "bsf %2,%0; setz %b1"
  6.3070 +              : "=r" (dst.val), "=q" (zf)
  6.3071 +              : "r" (src.val), "1" (0) );
  6.3072 +        _regs.eflags &= ~EFLG_ZF;
  6.3073 +        _regs.eflags |= zf ? EFLG_ZF : 0;
  6.3074 +        break;
  6.3075 +    }
  6.3076 +
  6.3077 +    case 0xbd: /* bsr */ {
  6.3078 +        int zf;
  6.3079 +        asm ( "bsr %2,%0; setz %b1"
  6.3080 +              : "=r" (dst.val), "=q" (zf)
  6.3081 +              : "r" (src.val), "1" (0) );
  6.3082 +        _regs.eflags &= ~EFLG_ZF;
  6.3083 +        _regs.eflags |= zf ? EFLG_ZF : 0;
  6.3084 +        break;
  6.3085 +    }
  6.3086 +
  6.3087 +    case 0xb7: /* movzx rm16,r{16,32,64} */
  6.3088 +        dst.val = (uint16_t)src.val;
  6.3089 +        break;
  6.3090 +
  6.3091 +    case 0xbb: btc: /* btc */
  6.3092 +        emulate_2op_SrcV_nobyte("btc", src, dst, _regs.eflags);
  6.3093 +        break;
  6.3094 +
  6.3095 +    case 0xba: /* Grp8 */
  6.3096 +        switch ( modrm_reg & 7 )
  6.3097 +        {
  6.3098 +        case 4: goto bt;
  6.3099 +        case 5: goto bts;
  6.3100 +        case 6: goto btr;
  6.3101 +        case 7: goto btc;
  6.3102 +        default: generate_exception_if(1, EXC_UD, -1);
  6.3103 +        }
  6.3104 +        break;
  6.3105 +
  6.3106 +    case 0xbe: /* movsx rm8,r{16,32,64} */
  6.3107 +        /* Recompute DstReg as we may have decoded AH/BH/CH/DH. */
  6.3108 +        dst.reg   = decode_register(modrm_reg, &_regs, 0);
  6.3109 +        dst.bytes = op_bytes;
  6.3110 +        dst.val   = (int8_t)src.val;
  6.3111 +        break;
  6.3112 +
  6.3113 +    case 0xbf: /* movsx rm16,r{16,32,64} */
  6.3114 +        dst.val = (int16_t)src.val;
  6.3115 +        break;
  6.3116 +
  6.3117 +    case 0xc0 ... 0xc1: /* xadd */
  6.3118 +        /* Write back the register source. */
  6.3119 +        switch ( dst.bytes )
  6.3120 +        {
  6.3121 +        case 1: *(uint8_t  *)src.reg = (uint8_t)dst.val; break;
  6.3122 +        case 2: *(uint16_t *)src.reg = (uint16_t)dst.val; break;
  6.3123 +        case 4: *src.reg = (uint32_t)dst.val; break; /* 64b reg: zero-extend */
  6.3124 +        case 8: *src.reg = dst.val; break;
  6.3125 +        }
  6.3126 +        goto add;
  6.3127 +    }
  6.3128 +    goto writeback;
  6.3129 +
  6.3130 + twobyte_special_insn:
  6.3131 +    switch ( b )
  6.3132 +    {
  6.3133 +    case 0x01: /* Grp7 */ {
  6.3134 +        struct segment_register reg;
  6.3135 +        unsigned long base, limit, cr0, cr0w;
  6.3136 +
  6.3137 +        if ( modrm == 0xdf ) /* invlpga */
  6.3138 +        {
  6.3139 +            generate_exception_if(in_realmode(ctxt, ops), EXC_UD, -1);
  6.3140 +            generate_exception_if(!mode_ring0(), EXC_GP, 0);
  6.3141 +            fail_if(ops->invlpg == NULL);
  6.3142 +            if ( (rc = ops->invlpg(x86_seg_none, truncate_ea(_regs.eax),
  6.3143 +                                   ctxt)) )
  6.3144 +                goto done;
  6.3145 +            break;
  6.3146 +        }
  6.3147 +
  6.3148 +        switch ( modrm_reg & 7 )
  6.3149 +        {
  6.3150 +        case 0: /* sgdt */
  6.3151 +        case 1: /* sidt */
  6.3152 +            generate_exception_if(ea.type != OP_MEM, EXC_UD, -1);
  6.3153 +            fail_if(ops->read_segment == NULL);
  6.3154 +            if ( (rc = ops->read_segment((modrm_reg & 1) ?
  6.3155 +                                         x86_seg_idtr : x86_seg_gdtr,
  6.3156 +                                         &reg, ctxt)) )
  6.3157 +                goto done;
  6.3158 +            if ( op_bytes == 2 )
  6.3159 +                reg.base &= 0xffffff;
  6.3160 +            if ( (rc = ops->write(ea.mem.seg, ea.mem.off+0,
  6.3161 +                                  reg.limit, 2, ctxt)) ||
  6.3162 +                 (rc = ops->write(ea.mem.seg, ea.mem.off+2,
  6.3163 +                                  reg.base, mode_64bit() ? 8 : 4, ctxt)) )
  6.3164 +                goto done;
  6.3165 +            break;
  6.3166 +        case 2: /* lgdt */
  6.3167 +        case 3: /* lidt */
  6.3168 +            generate_exception_if(ea.type != OP_MEM, EXC_UD, -1);
  6.3169 +            fail_if(ops->write_segment == NULL);
  6.3170 +            memset(&reg, 0, sizeof(reg));
  6.3171 +            if ( (rc = ops->read(ea.mem.seg, ea.mem.off+0,
  6.3172 +                                 &limit, 2, ctxt)) ||
  6.3173 +                 (rc = ops->read(ea.mem.seg, ea.mem.off+2,
  6.3174 +                                 &base, mode_64bit() ? 8 : 4, ctxt)) )
  6.3175 +                goto done;
  6.3176 +            reg.base = base;
  6.3177 +            reg.limit = limit;
  6.3178 +            if ( op_bytes == 2 )
  6.3179 +                reg.base &= 0xffffff;
  6.3180 +            if ( (rc = ops->write_segment((modrm_reg & 1) ?
  6.3181 +                                          x86_seg_idtr : x86_seg_gdtr,
  6.3182 +                                          &reg, ctxt)) )
  6.3183 +                goto done;
  6.3184 +            break;
  6.3185 +        case 4: /* smsw */
  6.3186 +            ea.bytes = 2;
  6.3187 +            dst = ea;
  6.3188 +            fail_if(ops->read_cr == NULL);
  6.3189 +            if ( (rc = ops->read_cr(0, &dst.val, ctxt)) )
  6.3190 +                goto done;
  6.3191 +            d |= Mov; /* force writeback */
  6.3192 +            break;
  6.3193 +        case 6: /* lmsw */
  6.3194 +            fail_if(ops->read_cr == NULL);
  6.3195 +            fail_if(ops->write_cr == NULL);
  6.3196 +            if ( (rc = ops->read_cr(0, &cr0, ctxt)) )
  6.3197 +                goto done;
  6.3198 +            if ( ea.type == OP_REG )
  6.3199 +                cr0w = *ea.reg;
  6.3200 +            else if ( (rc = ops->read(ea.mem.seg, ea.mem.off,
  6.3201 +                                      &cr0w, 2, ctxt)) )
  6.3202 +                goto done;
  6.3203 +            cr0 &= 0xffff0000;
  6.3204 +            cr0 |= (uint16_t)cr0w;
  6.3205 +            if ( (rc = ops->write_cr(0, cr0, ctxt)) )
  6.3206 +                goto done;
  6.3207 +            break;
  6.3208 +        case 7: /* invlpg */
  6.3209 +            generate_exception_if(!mode_ring0(), EXC_GP, 0);
  6.3210 +            generate_exception_if(ea.type != OP_MEM, EXC_UD, -1);
  6.3211 +            fail_if(ops->invlpg == NULL);
  6.3212 +            if ( (rc = ops->invlpg(ea.mem.seg, ea.mem.off, ctxt)) )
  6.3213 +                goto done;
  6.3214 +            break;
  6.3215 +        default:
  6.3216 +            goto cannot_emulate;
  6.3217 +        }
  6.3218 +        break;
  6.3219 +    }
  6.3220 +
  6.3221 +    case 0x06: /* clts */
  6.3222 +        generate_exception_if(!mode_ring0(), EXC_GP, 0);
  6.3223 +        fail_if((ops->read_cr == NULL) || (ops->write_cr == NULL));
  6.3224 +        if ( (rc = ops->read_cr(0, &dst.val, ctxt)) ||
  6.3225 +             (rc = ops->write_cr(0, dst.val&~8, ctxt)) )
  6.3226 +            goto done;
  6.3227 +        break;
  6.3228 +
  6.3229 +    case 0x08: /* invd */
  6.3230 +    case 0x09: /* wbinvd */
  6.3231 +        generate_exception_if(!mode_ring0(), EXC_GP, 0);
  6.3232 +        fail_if(ops->wbinvd == NULL);
  6.3233 +        if ( (rc = ops->wbinvd(ctxt)) != 0 )
  6.3234 +            goto done;
  6.3235 +        break;
  6.3236 +
  6.3237 +    case 0x0d: /* GrpP (prefetch) */
  6.3238 +    case 0x18: /* Grp16 (prefetch/nop) */
  6.3239 +    case 0x19 ... 0x1f: /* nop (amd-defined) */
  6.3240 +        break;
  6.3241 +
  6.3242 +    case 0x20: /* mov cr,reg */
  6.3243 +    case 0x21: /* mov dr,reg */
  6.3244 +    case 0x22: /* mov reg,cr */
  6.3245 +    case 0x23: /* mov reg,dr */
  6.3246 +        generate_exception_if(ea.type != OP_REG, EXC_UD, -1);
  6.3247 +        generate_exception_if(!mode_ring0(), EXC_GP, 0);
  6.3248 +        modrm_reg |= lock_prefix << 3;
  6.3249 +        if ( b & 2 )
  6.3250 +        {
  6.3251 +            /* Write to CR/DR. */
  6.3252 +            src.val = *(unsigned long *)decode_register(modrm_rm, &_regs, 0);
  6.3253 +            if ( !mode_64bit() )
  6.3254 +                src.val = (uint32_t)src.val;
  6.3255 +            rc = ((b & 1)
  6.3256 +                  ? (ops->write_dr
  6.3257 +                     ? ops->write_dr(modrm_reg, src.val, ctxt)
  6.3258 +                     : X86EMUL_UNHANDLEABLE)
  6.3259 +                  : (ops->write_cr
  6.3260 +                     ? ops->write_cr(modrm_reg, src.val, ctxt)
  6.3261 +                     : X86EMUL_UNHANDLEABLE));
  6.3262 +        }
  6.3263 +        else
  6.3264 +        {
  6.3265 +            /* Read from CR/DR. */
  6.3266 +            dst.type  = OP_REG;
  6.3267 +            dst.bytes = mode_64bit() ? 8 : 4;
  6.3268 +            dst.reg   = decode_register(modrm_rm, &_regs, 0);
  6.3269 +            rc = ((b & 1)
  6.3270 +                  ? (ops->read_dr
  6.3271 +                     ? ops->read_dr(modrm_reg, &dst.val, ctxt)
  6.3272 +                     : X86EMUL_UNHANDLEABLE)
  6.3273 +                  : (ops->read_cr
  6.3274 +                     ? ops->read_cr(modrm_reg, &dst.val, ctxt)
  6.3275 +                     : X86EMUL_UNHANDLEABLE));
  6.3276 +        }
  6.3277 +        if ( rc != 0 )
  6.3278 +            goto done;
  6.3279 +        break;
  6.3280 +
  6.3281 +    case 0x30: /* wrmsr */ {
  6.3282 +        uint64_t val = ((uint64_t)_regs.edx << 32) | (uint32_t)_regs.eax;
  6.3283 +        generate_exception_if(!mode_ring0(), EXC_GP, 0);
  6.3284 +        fail_if(ops->write_msr == NULL);
  6.3285 +        if ( (rc = ops->write_msr((uint32_t)_regs.ecx, val, ctxt)) != 0 )
  6.3286 +            goto done;
  6.3287 +        break;
  6.3288 +    }
  6.3289 +
  6.3290 +    case 0x31: /* rdtsc */ {
  6.3291 +        unsigned long cr4;
  6.3292 +        uint64_t val;
  6.3293 +        fail_if(ops->read_cr == NULL);
  6.3294 +        if ( (rc = ops->read_cr(4, &cr4, ctxt)) )
  6.3295 +            goto done;
  6.3296 +        generate_exception_if((cr4 & CR4_TSD) && !mode_ring0(), EXC_GP, 0);
  6.3297 +        fail_if(ops->read_msr == NULL);
  6.3298 +        if ( (rc = ops->read_msr(MSR_TSC, &val, ctxt)) != 0 )
  6.3299 +            goto done;
  6.3300 +        _regs.edx = (uint32_t)(val >> 32);
  6.3301 +        _regs.eax = (uint32_t)(val >>  0);
  6.3302 +        break;
  6.3303 +    }
  6.3304 +
  6.3305 +    case 0x32: /* rdmsr */ {
  6.3306 +        uint64_t val;
  6.3307 +        generate_exception_if(!mode_ring0(), EXC_GP, 0);
  6.3308 +        fail_if(ops->read_msr == NULL);
  6.3309 +        if ( (rc = ops->read_msr((uint32_t)_regs.ecx, &val, ctxt)) != 0 )
  6.3310 +            goto done;
  6.3311 +        _regs.edx = (uint32_t)(val >> 32);
  6.3312 +        _regs.eax = (uint32_t)(val >>  0);
  6.3313 +        break;
  6.3314 +    }
  6.3315 +
  6.3316 +    case 0x80 ... 0x8f: /* jcc (near) */ {
  6.3317 +        int rel = (((op_bytes == 2) && !mode_64bit())
  6.3318 +                   ? (int32_t)insn_fetch_type(int16_t)
  6.3319 +                   : insn_fetch_type(int32_t));
  6.3320 +        if ( test_cc(b, _regs.eflags) )
  6.3321 +            jmp_rel(rel);
  6.3322 +        break;
  6.3323 +    }
  6.3324 +
  6.3325 +    case 0xa0: /* push %%fs */
  6.3326 +        src.val = x86_seg_fs;
  6.3327 +        goto push_seg;
  6.3328 +
  6.3329 +    case 0xa1: /* pop %%fs */
  6.3330 +        src.val = x86_seg_fs;
  6.3331 +        goto pop_seg;
  6.3332 +
  6.3333 +    case 0xa2: /* cpuid */ {
  6.3334 +        unsigned int eax = _regs.eax, ebx = _regs.ebx;
  6.3335 +        unsigned int ecx = _regs.ecx, edx = _regs.edx;
  6.3336 +        fail_if(ops->cpuid == NULL);
  6.3337 +        if ( (rc = ops->cpuid(&eax, &ebx, &ecx, &edx, ctxt)) != 0 )
  6.3338 +            goto done;
  6.3339 +        _regs.eax = eax; _regs.ebx = ebx;
  6.3340 +        _regs.ecx = ecx; _regs.edx = edx;
  6.3341 +        break;
  6.3342 +    }
  6.3343 +
  6.3344 +    case 0xa8: /* push %%gs */
  6.3345 +        src.val = x86_seg_gs;
  6.3346 +        goto push_seg;
  6.3347 +
  6.3348 +    case 0xa9: /* pop %%gs */
  6.3349 +        src.val = x86_seg_gs;
  6.3350 +        goto pop_seg;
  6.3351 +
  6.3352 +    case 0xc7: /* Grp9 (cmpxchg8b) */
  6.3353 +#if defined(__i386__)
  6.3354 +    {
  6.3355 +        unsigned long old_lo, old_hi;
  6.3356 +        generate_exception_if((modrm_reg & 7) != 1, EXC_UD, -1);
  6.3357 +        generate_exception_if(ea.type != OP_MEM, EXC_UD, -1);
  6.3358 +        if ( (rc = ops->read(ea.mem.seg, ea.mem.off+0, &old_lo, 4, ctxt)) ||
  6.3359 +             (rc = ops->read(ea.mem.seg, ea.mem.off+4, &old_hi, 4, ctxt)) )
  6.3360 +            goto done;
  6.3361 +        if ( (old_lo != _regs.eax) || (old_hi != _regs.edx) )
  6.3362 +        {
  6.3363 +            _regs.eax = old_lo;
  6.3364 +            _regs.edx = old_hi;
  6.3365 +            _regs.eflags &= ~EFLG_ZF;
  6.3366 +        }
  6.3367 +        else if ( ops->cmpxchg8b == NULL )
  6.3368 +        {
  6.3369 +            rc = X86EMUL_UNHANDLEABLE;
  6.3370 +            goto done;
  6.3371 +        }
  6.3372 +        else
  6.3373 +        {
  6.3374 +            if ( (rc = ops->cmpxchg8b(ea.mem.seg, ea.mem.off, old_lo, old_hi,
  6.3375 +                                      _regs.ebx, _regs.ecx, ctxt)) != 0 )
  6.3376 +                goto done;
  6.3377 +            _regs.eflags |= EFLG_ZF;
  6.3378 +        }
  6.3379 +        break;
  6.3380 +    }
  6.3381 +#elif defined(__x86_64__)
  6.3382 +    {
  6.3383 +        unsigned long old, new;
  6.3384 +        generate_exception_if((modrm_reg & 7) != 1, EXC_UD, -1);
  6.3385 +        generate_exception_if(ea.type != OP_MEM, EXC_UD, -1);
  6.3386 +        if ( (rc = ops->read(ea.mem.seg, ea.mem.off, &old, 8, ctxt)) != 0 )
  6.3387 +            goto done;
  6.3388 +        if ( ((uint32_t)(old>>0) != (uint32_t)_regs.eax) ||
  6.3389 +             ((uint32_t)(old>>32) != (uint32_t)_regs.edx) )
  6.3390 +        {
  6.3391 +            _regs.eax = (uint32_t)(old>>0);
  6.3392 +            _regs.edx = (uint32_t)(old>>32);
  6.3393 +            _regs.eflags &= ~EFLG_ZF;
  6.3394 +        }
  6.3395 +        else
  6.3396 +        {
  6.3397 +            new = (_regs.ecx<<32)|(uint32_t)_regs.ebx;
  6.3398 +            if ( (rc = ops->cmpxchg(ea.mem.seg, ea.mem.off, old,
  6.3399 +                                    new, 8, ctxt)) != 0 )
  6.3400 +                goto done;
  6.3401 +            _regs.eflags |= EFLG_ZF;
  6.3402 +        }
  6.3403 +        break;
  6.3404 +    }
  6.3405 +#endif
  6.3406 +
  6.3407 +    case 0xc8 ... 0xcf: /* bswap */
  6.3408 +        dst.type = OP_REG;
  6.3409 +        dst.reg  = decode_register(
  6.3410 +            (b & 7) | ((rex_prefix & 1) << 3), &_regs, 0);
  6.3411 +        switch ( dst.bytes = op_bytes )
  6.3412 +        {
  6.3413 +        default: /* case 2: */
  6.3414 +            /* Undefined behaviour. Writes zero on all tested CPUs. */
  6.3415 +            dst.val = 0;
  6.3416 +            break;
  6.3417 +        case 4:
  6.3418 +#ifdef __x86_64__
  6.3419 +            asm ( "bswap %k0" : "=r" (dst.val) : "0" (*dst.reg) );
  6.3420 +            break;
  6.3421 +        case 8:
  6.3422 +#endif
  6.3423 +            asm ( "bswap %0" : "=r" (dst.val) : "0" (*dst.reg) );
  6.3424 +            break;
  6.3425 +        }
  6.3426 +        break;
  6.3427 +    }
  6.3428 +    goto writeback;
  6.3429 +
  6.3430 + cannot_emulate:
  6.3431 +    return X86EMUL_UNHANDLEABLE;
  6.3432 +}
     7.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     7.2 +++ b/xen/arch/x86/x86_emulate/x86_emulate.h	Mon Mar 31 14:21:13 2008 +0100
     7.3 @@ -0,0 +1,401 @@
     7.4 +/******************************************************************************
     7.5 + * x86_emulate.h
     7.6 + * 
     7.7 + * Generic x86 (32-bit and 64-bit) instruction decoder and emulator.
     7.8 + * 
     7.9 + * Copyright (c) 2005-2007 Keir Fraser
    7.10 + * Copyright (c) 2005-2007 XenSource Inc.
    7.11 + * 
    7.12 + * This program is free software; you can redistribute it and/or modify
    7.13 + * it under the terms of the GNU General Public License as published by
    7.14 + * the Free Software Foundation; either version 2 of the License, or
    7.15 + * (at your option) any later version.
    7.16 + * 
    7.17 + * This program is distributed in the hope that it will be useful,
    7.18 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
    7.19 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    7.20 + * GNU General Public License for more details.
    7.21 + * 
    7.22 + * You should have received a copy of the GNU General Public License
    7.23 + * along with this program; if not, write to the Free Software
    7.24 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
    7.25 + */
    7.26 +
    7.27 +#ifndef __X86_EMULATE_H__
    7.28 +#define __X86_EMULATE_H__
    7.29 +
    7.30 +struct x86_emulate_ctxt;
    7.31 +
    7.32 +/* Comprehensive enumeration of x86 segment registers. */
    7.33 +enum x86_segment {
    7.34 +    /* General purpose. */
    7.35 +    x86_seg_cs,
    7.36 +    x86_seg_ss,
    7.37 +    x86_seg_ds,
    7.38 +    x86_seg_es,
    7.39 +    x86_seg_fs,
    7.40 +    x86_seg_gs,
    7.41 +    /* System. */
    7.42 +    x86_seg_tr,
    7.43 +    x86_seg_ldtr,
    7.44 +    x86_seg_gdtr,
    7.45 +    x86_seg_idtr,
    7.46 +    /*
    7.47 +     * Dummy: used to emulate direct processor accesses to management
    7.48 +     * structures (TSS, GDT, LDT, IDT, etc.) which use linear addressing
    7.49 +     * (no segment component) and bypass usual segment- and page-level
    7.50 +     * protection checks.
    7.51 +     */
    7.52 +    x86_seg_none
    7.53 +};
    7.54 +
    7.55 +#define is_x86_user_segment(seg) ((unsigned)(seg) <= x86_seg_gs)
    7.56 +
    7.57 +/* 
    7.58 + * Attribute for segment selector. This is a copy of bit 40:47 & 52:55 of the
    7.59 + * segment descriptor. It happens to match the format of an AMD SVM VMCB.
    7.60 + */
    7.61 +typedef union segment_attributes {
    7.62 +    uint16_t bytes;
    7.63 +    struct
    7.64 +    {
    7.65 +        uint16_t type:4;    /* 0;  Bit 40-43 */
    7.66 +        uint16_t s:   1;    /* 4;  Bit 44 */
    7.67 +        uint16_t dpl: 2;    /* 5;  Bit 45-46 */
    7.68 +        uint16_t p:   1;    /* 7;  Bit 47 */
    7.69 +        uint16_t avl: 1;    /* 8;  Bit 52 */
    7.70 +        uint16_t l:   1;    /* 9;  Bit 53 */
    7.71 +        uint16_t db:  1;    /* 10; Bit 54 */
    7.72 +        uint16_t g:   1;    /* 11; Bit 55 */
    7.73 +    } fields;
    7.74 +} __attribute__ ((packed)) segment_attributes_t;
    7.75 +
    7.76 +/*
    7.77 + * Full state of a segment register (visible and hidden portions).
    7.78 + * Again, this happens to match the format of an AMD SVM VMCB.
    7.79 + */
    7.80 +struct segment_register {
    7.81 +    uint16_t   sel;
    7.82 +    segment_attributes_t attr;
    7.83 +    uint32_t   limit;
    7.84 +    uint64_t   base;
    7.85 +} __attribute__ ((packed));
    7.86 +
    7.87 +/*
    7.88 + * Return codes from state-accessor functions and from x86_emulate().
    7.89 + */
    7.90 + /* Completed successfully. State modified appropriately. */
    7.91 +#define X86EMUL_OKAY           0
    7.92 + /* Unhandleable access or emulation. No state modified. */
    7.93 +#define X86EMUL_UNHANDLEABLE   1
    7.94 + /* Exception raised and requires delivery. */
    7.95 +#define X86EMUL_EXCEPTION      2
    7.96 + /* Retry the emulation for some reason. No state modified. */
    7.97 +#define X86EMUL_RETRY          3
    7.98 + /* (cmpxchg accessor): CMPXCHG failed. Maps to X86EMUL_RETRY in caller. */
    7.99 +#define X86EMUL_CMPXCHG_FAILED 3
   7.100 +
   7.101 +/*
   7.102 + * These operations represent the instruction emulator's interface to memory.
   7.103 + * 
   7.104 + * NOTES:
   7.105 + *  1. If the access fails (cannot emulate, or a standard access faults) then
   7.106 + *     it is up to the memop to propagate the fault to the guest VM via
   7.107 + *     some out-of-band mechanism, unknown to the emulator. The memop signals
   7.108 + *     failure by returning X86EMUL_EXCEPTION to the emulator, which will
   7.109 + *     then immediately bail.
   7.110 + *  2. Valid access sizes are 1, 2, 4 and 8 bytes. On x86/32 systems only
   7.111 + *     cmpxchg8b_emulated need support 8-byte accesses.
   7.112 + *  3. The emulator cannot handle 64-bit mode emulation on an x86/32 system.
   7.113 + */
   7.114 +struct x86_emulate_ops
   7.115 +{
   7.116 +    /*
   7.117 +     * All functions:
   7.118 +     *  @ctxt:  [IN ] Emulation context info as passed to the emulator.
   7.119 +     * All memory-access functions:
   7.120 +     *  @seg:   [IN ] Segment being dereferenced (specified as x86_seg_??).
   7.121 +     *  @offset:[IN ] Offset within segment.
   7.122 +     * Read functions:
   7.123 +     *  @val:   [OUT] Value read, zero-extended to 'ulong'.
   7.124 +     * Write functions:
   7.125 +     *  @val:   [IN ] Value to write (low-order bytes used as req'd).
   7.126 +     * Variable-length access functions:
   7.127 +     *  @bytes: [IN ] Number of bytes to read or write.
   7.128 +     */
   7.129 +
   7.130 +    /* read: Emulate a memory read. */
   7.131 +    int (*read)(
   7.132 +        enum x86_segment seg,
   7.133 +        unsigned long offset,
   7.134 +        unsigned long *val,
   7.135 +        unsigned int bytes,
   7.136 +        struct x86_emulate_ctxt *ctxt);
   7.137 +
   7.138 +    /*
   7.139 +     * insn_fetch: Emulate fetch from instruction byte stream.
   7.140 +     *  Parameters are same as for 'read'. @seg is always x86_seg_cs.
   7.141 +     */
   7.142 +    int (*insn_fetch)(
   7.143 +        enum x86_segment seg,
   7.144 +        unsigned long offset,
   7.145 +        unsigned long *val,
   7.146 +        unsigned int bytes,
   7.147 +        struct x86_emulate_ctxt *ctxt);
   7.148 +
   7.149 +    /* write: Emulate a memory write. */
   7.150 +    int (*write)(
   7.151 +        enum x86_segment seg,
   7.152 +        unsigned long offset,
   7.153 +        unsigned long val,
   7.154 +        unsigned int bytes,
   7.155 +        struct x86_emulate_ctxt *ctxt);
   7.156 +
   7.157 +    /*
   7.158 +     * cmpxchg: Emulate an atomic (LOCKed) CMPXCHG operation.
   7.159 +     *  @old:   [IN ] Value expected to be current at @addr.
   7.160 +     *  @new:   [IN ] Value to write to @addr.
   7.161 +     */
   7.162 +    int (*cmpxchg)(
   7.163 +        enum x86_segment seg,
   7.164 +        unsigned long offset,
   7.165 +        unsigned long old,
   7.166 +        unsigned long new,
   7.167 +        unsigned int bytes,
   7.168 +        struct x86_emulate_ctxt *ctxt);
   7.169 +
   7.170 +    /*
   7.171 +     * cmpxchg8b: Emulate an atomic (LOCKed) CMPXCHG8B operation.
   7.172 +     *  @old:   [IN ] Value expected to be current at @addr.
   7.173 +     *  @new:   [IN ] Value to write to @addr.
   7.174 +     * NOTES:
   7.175 +     *  1. This function is only ever called when emulating a real CMPXCHG8B.
   7.176 +     *  2. This function is *never* called on x86/64 systems.
   7.177 +     *  2. Not defining this function (i.e., specifying NULL) is equivalent
   7.178 +     *     to defining a function that always returns X86EMUL_UNHANDLEABLE.
   7.179 +     */
   7.180 +    int (*cmpxchg8b)(
   7.181 +        enum x86_segment seg,
   7.182 +        unsigned long offset,
   7.183 +        unsigned long old_lo,
   7.184 +        unsigned long old_hi,
   7.185 +        unsigned long new_lo,
   7.186 +        unsigned long new_hi,
   7.187 +        struct x86_emulate_ctxt *ctxt);
   7.188 +
   7.189 +    /*
   7.190 +     * rep_ins: Emulate INS: <src_port> -> <dst_seg:dst_offset>.
   7.191 +     *  @bytes_per_rep: [IN ] Bytes transferred per repetition.
   7.192 +     *  @reps:  [IN ] Maximum repetitions to be emulated.
   7.193 +     *          [OUT] Number of repetitions actually emulated.
   7.194 +     */
   7.195 +    int (*rep_ins)(
   7.196 +        uint16_t src_port,
   7.197 +        enum x86_segment dst_seg,
   7.198 +        unsigned long dst_offset,
   7.199 +        unsigned int bytes_per_rep,
   7.200 +        unsigned long *reps,
   7.201 +        struct x86_emulate_ctxt *ctxt);
   7.202 +
   7.203 +    /*
   7.204 +     * rep_outs: Emulate OUTS: <src_seg:src_offset> -> <dst_port>.
   7.205 +     *  @bytes_per_rep: [IN ] Bytes transferred per repetition.
   7.206 +     *  @reps:  [IN ] Maximum repetitions to be emulated.
   7.207 +     *          [OUT] Number of repetitions actually emulated.
   7.208 +     */
   7.209 +    int (*rep_outs)(
   7.210 +        enum x86_segment src_seg,
   7.211 +        unsigned long src_offset,
   7.212 +        uint16_t dst_port,
   7.213 +        unsigned int bytes_per_rep,
   7.214 +        unsigned long *reps,
   7.215 +        struct x86_emulate_ctxt *ctxt);
   7.216 +
   7.217 +    /*
   7.218 +     * rep_movs: Emulate MOVS: <src_seg:src_offset> -> <dst_seg:dst_offset>.
   7.219 +     *  @bytes_per_rep: [IN ] Bytes transferred per repetition.
   7.220 +     *  @reps:  [IN ] Maximum repetitions to be emulated.
   7.221 +     *          [OUT] Number of repetitions actually emulated.
   7.222 +     */
   7.223 +    int (*rep_movs)(
   7.224 +        enum x86_segment src_seg,
   7.225 +        unsigned long src_offset,
   7.226 +        enum x86_segment dst_seg,
   7.227 +        unsigned long dst_offset,
   7.228 +        unsigned int bytes_per_rep,
   7.229 +        unsigned long *reps,
   7.230 +        struct x86_emulate_ctxt *ctxt);
   7.231 +
   7.232 +    /*
   7.233 +     * read_segment: Emulate a read of full context of a segment register.
   7.234 +     *  @reg:   [OUT] Contents of segment register (visible and hidden state).
   7.235 +     */
   7.236 +    int (*read_segment)(
   7.237 +        enum x86_segment seg,
   7.238 +        struct segment_register *reg,
   7.239 +        struct x86_emulate_ctxt *ctxt);
   7.240 +
   7.241 +    /*
   7.242 +     * write_segment: Emulate a read of full context of a segment register.
   7.243 +     *  @reg:   [OUT] Contents of segment register (visible and hidden state).
   7.244 +     */
   7.245 +    int (*write_segment)(
   7.246 +        enum x86_segment seg,
   7.247 +        struct segment_register *reg,
   7.248 +        struct x86_emulate_ctxt *ctxt);
   7.249 +
   7.250 +    /*
   7.251 +     * read_io: Read from I/O port(s).
   7.252 +     *  @port:  [IN ] Base port for access.
   7.253 +     */
   7.254 +    int (*read_io)(
   7.255 +        unsigned int port,
   7.256 +        unsigned int bytes,
   7.257 +        unsigned long *val,
   7.258 +        struct x86_emulate_ctxt *ctxt);
   7.259 +
   7.260 +    /*
   7.261 +     * write_io: Write to I/O port(s).
   7.262 +     *  @port:  [IN ] Base port for access.
   7.263 +     */
   7.264 +    int (*write_io)(
   7.265 +        unsigned int port,
   7.266 +        unsigned int bytes,
   7.267 +        unsigned long val,
   7.268 +        struct x86_emulate_ctxt *ctxt);
   7.269 +
   7.270 +    /*
   7.271 +     * read_cr: Read from control register.
   7.272 +     *  @reg:   [IN ] Register to read (0-15).
   7.273 +     */
   7.274 +    int (*read_cr)(
   7.275 +        unsigned int reg,
   7.276 +        unsigned long *val,
   7.277 +        struct x86_emulate_ctxt *ctxt);
   7.278 +
   7.279 +    /*
   7.280 +     * write_cr: Write to control register.
   7.281 +     *  @reg:   [IN ] Register to write (0-15).
   7.282 +     */
   7.283 +    int (*write_cr)(
   7.284 +        unsigned int reg,
   7.285 +        unsigned long val,
   7.286 +        struct x86_emulate_ctxt *ctxt);
   7.287 +
   7.288 +    /*
   7.289 +     * read_dr: Read from debug register.
   7.290 +     *  @reg:   [IN ] Register to read (0-15).
   7.291 +     */
   7.292 +    int (*read_dr)(
   7.293 +        unsigned int reg,
   7.294 +        unsigned long *val,
   7.295 +        struct x86_emulate_ctxt *ctxt);
   7.296 +
   7.297 +    /*
   7.298 +     * write_dr: Write to debug register.
   7.299 +     *  @reg:   [IN ] Register to write (0-15).
   7.300 +     */
   7.301 +    int (*write_dr)(
   7.302 +        unsigned int reg,
   7.303 +        unsigned long val,
   7.304 +        struct x86_emulate_ctxt *ctxt);
   7.305 +
   7.306 +    /*
   7.307 +     * read_msr: Read from model-specific register.
   7.308 +     *  @reg:   [IN ] Register to read.
   7.309 +     */
   7.310 +    int (*read_msr)(
   7.311 +        unsigned long reg,
   7.312 +        uint64_t *val,
   7.313 +        struct x86_emulate_ctxt *ctxt);
   7.314 +
   7.315 +    /*
   7.316 +     * write_dr: Write to model-specific register.
   7.317 +     *  @reg:   [IN ] Register to write.
   7.318 +     */
   7.319 +    int (*write_msr)(
   7.320 +        unsigned long reg,
   7.321 +        uint64_t val,
   7.322 +        struct x86_emulate_ctxt *ctxt);
   7.323 +
   7.324 +    /* wbinvd: Write-back and invalidate cache contents. */
   7.325 +    int (*wbinvd)(
   7.326 +        struct x86_emulate_ctxt *ctxt);
   7.327 +
   7.328 +    /* cpuid: Emulate CPUID via given set of EAX-EDX inputs/outputs. */
   7.329 +    int (*cpuid)(
   7.330 +        unsigned int *eax,
   7.331 +        unsigned int *ebx,
   7.332 +        unsigned int *ecx,
   7.333 +        unsigned int *edx,
   7.334 +        struct x86_emulate_ctxt *ctxt);
   7.335 +
   7.336 +    /* inject_hw_exception */
   7.337 +    int (*inject_hw_exception)(
   7.338 +        uint8_t vector,
   7.339 +        int32_t error_code,
   7.340 +        struct x86_emulate_ctxt *ctxt);
   7.341 +
   7.342 +    /* inject_sw_interrupt */
   7.343 +    int (*inject_sw_interrupt)(
   7.344 +        uint8_t vector,
   7.345 +        uint8_t insn_len,
   7.346 +        struct x86_emulate_ctxt *ctxt);
   7.347 +
   7.348 +    /* load_fpu_ctxt: Load emulated environment's FPU state onto processor. */
   7.349 +    void (*load_fpu_ctxt)(
   7.350 +        struct x86_emulate_ctxt *ctxt);
   7.351 +
   7.352 +    /* invlpg: Invalidate paging structures which map addressed byte. */
   7.353 +    int (*invlpg)(
   7.354 +        enum x86_segment seg,
   7.355 +        unsigned long offset,
   7.356 +        struct x86_emulate_ctxt *ctxt);
   7.357 +};
   7.358 +
   7.359 +struct cpu_user_regs;
   7.360 +
   7.361 +struct x86_emulate_ctxt
   7.362 +{
   7.363 +    /* Register state before/after emulation. */
   7.364 +    struct cpu_user_regs *regs;
   7.365 +
   7.366 +    /* Default address size in current execution mode (16, 32, or 64). */
   7.367 +    unsigned int addr_size;
   7.368 +
   7.369 +    /* Stack pointer width in bits (16, 32 or 64). */
   7.370 +    unsigned int sp_size;
   7.371 +
   7.372 +    /* Set this if writes may have side effects. */
   7.373 +    uint8_t force_writeback;
   7.374 +
   7.375 +    /* Retirement state, set by the emulator (valid only on X86EMUL_OKAY). */
   7.376 +    union {
   7.377 +        struct {
   7.378 +            uint8_t hlt:1;          /* Instruction HLTed. */
   7.379 +            uint8_t mov_ss:1;       /* Instruction sets MOV-SS irq shadow. */
   7.380 +            uint8_t sti:1;          /* Instruction sets STI irq shadow. */
   7.381 +        } flags;
   7.382 +        uint8_t byte;
   7.383 +    } retire;
   7.384 +};
   7.385 +
   7.386 +/*
   7.387 + * x86_emulate: Emulate an instruction.
   7.388 + * Returns -1 on failure, 0 on success.
   7.389 + */
   7.390 +int
   7.391 +x86_emulate(
   7.392 +    struct x86_emulate_ctxt *ctxt,
   7.393 +    struct x86_emulate_ops  *ops);
   7.394 +
   7.395 +/*
   7.396 + * Given the 'reg' portion of a ModRM byte, and a register block, return a
   7.397 + * pointer into the block that addresses the relevant register.
   7.398 + * @highbyte_regs specifies whether to decode AH,CH,DH,BH.
   7.399 + */
   7.400 +void *
   7.401 +decode_register(
   7.402 +    uint8_t modrm_reg, struct cpu_user_regs *regs, int highbyte_regs);
   7.403 +
   7.404 +#endif /* __X86_EMULATE_H__ */
     8.1 --- a/xen/include/asm-x86/x86_emulate.h	Mon Mar 31 10:40:43 2008 +0100
     8.2 +++ b/xen/include/asm-x86/x86_emulate.h	Mon Mar 31 14:21:13 2008 +0100
     8.3 @@ -1,401 +1,22 @@
     8.4  /******************************************************************************
     8.5   * x86_emulate.h
     8.6   * 
     8.7 - * Generic x86 (32-bit and 64-bit) instruction decoder and emulator.
     8.8 - * 
     8.9 - * Copyright (c) 2005-2007 Keir Fraser
    8.10 - * Copyright (c) 2005-2007 XenSource Inc.
    8.11 + * Wrapper for generic x86 instruction decoder and emulator.
    8.12   * 
    8.13 - * This program is free software; you can redistribute it and/or modify
    8.14 - * it under the terms of the GNU General Public License as published by
    8.15 - * the Free Software Foundation; either version 2 of the License, or
    8.16 - * (at your option) any later version.
    8.17 + * Copyright (c) 2008, Citrix Systems, Inc.
    8.18   * 
    8.19 - * This program is distributed in the hope that it will be useful,
    8.20 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
    8.21 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    8.22 - * GNU General Public License for more details.
    8.23 - * 
    8.24 - * You should have received a copy of the GNU General Public License
    8.25 - * along with this program; if not, write to the Free Software
    8.26 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
    8.27 + * Authors:
    8.28 + *    Keir Fraser <keir.fraser@citrix.com>
    8.29   */
    8.30  
    8.31 -#ifndef __X86_EMULATE_H__
    8.32 -#define __X86_EMULATE_H__
    8.33 -
    8.34 -struct x86_emulate_ctxt;
    8.35 -
    8.36 -/* Comprehensive enumeration of x86 segment registers. */
    8.37 -enum x86_segment {
    8.38 -    /* General purpose. */
    8.39 -    x86_seg_cs,
    8.40 -    x86_seg_ss,
    8.41 -    x86_seg_ds,
    8.42 -    x86_seg_es,
    8.43 -    x86_seg_fs,
    8.44 -    x86_seg_gs,
    8.45 -    /* System. */
    8.46 -    x86_seg_tr,
    8.47 -    x86_seg_ldtr,
    8.48 -    x86_seg_gdtr,
    8.49 -    x86_seg_idtr,
    8.50 -    /*
    8.51 -     * Dummy: used to emulate direct processor accesses to management
    8.52 -     * structures (TSS, GDT, LDT, IDT, etc.) which use linear addressing
    8.53 -     * (no segment component) and bypass usual segment- and page-level
    8.54 -     * protection checks.
    8.55 -     */
    8.56 -    x86_seg_none
    8.57 -};
    8.58 -
    8.59 -#define is_x86_user_segment(seg) ((unsigned)(seg) <= x86_seg_gs)
    8.60 -
    8.61 -/* 
    8.62 - * Attribute for segment selector. This is a copy of bit 40:47 & 52:55 of the
    8.63 - * segment descriptor. It happens to match the format of an AMD SVM VMCB.
    8.64 - */
    8.65 -typedef union segment_attributes {
    8.66 -    uint16_t bytes;
    8.67 -    struct
    8.68 -    {
    8.69 -        uint16_t type:4;    /* 0;  Bit 40-43 */
    8.70 -        uint16_t s:   1;    /* 4;  Bit 44 */
    8.71 -        uint16_t dpl: 2;    /* 5;  Bit 45-46 */
    8.72 -        uint16_t p:   1;    /* 7;  Bit 47 */
    8.73 -        uint16_t avl: 1;    /* 8;  Bit 52 */
    8.74 -        uint16_t l:   1;    /* 9;  Bit 53 */
    8.75 -        uint16_t db:  1;    /* 10; Bit 54 */
    8.76 -        uint16_t g:   1;    /* 11; Bit 55 */
    8.77 -    } fields;
    8.78 -} __attribute__ ((packed)) segment_attributes_t;
    8.79 -
    8.80 -/*
    8.81 - * Full state of a segment register (visible and hidden portions).
    8.82 - * Again, this happens to match the format of an AMD SVM VMCB.
    8.83 - */
    8.84 -struct segment_register {
    8.85 -    uint16_t   sel;
    8.86 -    segment_attributes_t attr;
    8.87 -    uint32_t   limit;
    8.88 -    uint64_t   base;
    8.89 -} __attribute__ ((packed));
    8.90 -
    8.91 -/*
    8.92 - * Return codes from state-accessor functions and from x86_emulate().
    8.93 - */
    8.94 - /* Completed successfully. State modified appropriately. */
    8.95 -#define X86EMUL_OKAY           0
    8.96 - /* Unhandleable access or emulation. No state modified. */
    8.97 -#define X86EMUL_UNHANDLEABLE   1
    8.98 - /* Exception raised and requires delivery. */
    8.99 -#define X86EMUL_EXCEPTION      2
   8.100 - /* Retry the emulation for some reason. No state modified. */
   8.101 -#define X86EMUL_RETRY          3
   8.102 - /* (cmpxchg accessor): CMPXCHG failed. Maps to X86EMUL_RETRY in caller. */
   8.103 -#define X86EMUL_CMPXCHG_FAILED 3
   8.104 -
   8.105 -/*
   8.106 - * These operations represent the instruction emulator's interface to memory.
   8.107 - * 
   8.108 - * NOTES:
   8.109 - *  1. If the access fails (cannot emulate, or a standard access faults) then
   8.110 - *     it is up to the memop to propagate the fault to the guest VM via
   8.111 - *     some out-of-band mechanism, unknown to the emulator. The memop signals
   8.112 - *     failure by returning X86EMUL_EXCEPTION to the emulator, which will
   8.113 - *     then immediately bail.
   8.114 - *  2. Valid access sizes are 1, 2, 4 and 8 bytes. On x86/32 systems only
   8.115 - *     cmpxchg8b_emulated need support 8-byte accesses.
   8.116 - *  3. The emulator cannot handle 64-bit mode emulation on an x86/32 system.
   8.117 - */
   8.118 -struct x86_emulate_ops
   8.119 -{
   8.120 -    /*
   8.121 -     * All functions:
   8.122 -     *  @ctxt:  [IN ] Emulation context info as passed to the emulator.
   8.123 -     * All memory-access functions:
   8.124 -     *  @seg:   [IN ] Segment being dereferenced (specified as x86_seg_??).
   8.125 -     *  @offset:[IN ] Offset within segment.
   8.126 -     * Read functions:
   8.127 -     *  @val:   [OUT] Value read, zero-extended to 'ulong'.
   8.128 -     * Write functions:
   8.129 -     *  @val:   [IN ] Value to write (low-order bytes used as req'd).
   8.130 -     * Variable-length access functions:
   8.131 -     *  @bytes: [IN ] Number of bytes to read or write.
   8.132 -     */
   8.133 -
   8.134 -    /* read: Emulate a memory read. */
   8.135 -    int (*read)(
   8.136 -        enum x86_segment seg,
   8.137 -        unsigned long offset,
   8.138 -        unsigned long *val,
   8.139 -        unsigned int bytes,
   8.140 -        struct x86_emulate_ctxt *ctxt);
   8.141 -
   8.142 -    /*
   8.143 -     * insn_fetch: Emulate fetch from instruction byte stream.
   8.144 -     *  Parameters are same as for 'read'. @seg is always x86_seg_cs.
   8.145 -     */
   8.146 -    int (*insn_fetch)(
   8.147 -        enum x86_segment seg,
   8.148 -        unsigned long offset,
   8.149 -        unsigned long *val,
   8.150 -        unsigned int bytes,
   8.151 -        struct x86_emulate_ctxt *ctxt);
   8.152 -
   8.153 -    /* write: Emulate a memory write. */
   8.154 -    int (*write)(
   8.155 -        enum x86_segment seg,
   8.156 -        unsigned long offset,
   8.157 -        unsigned long val,
   8.158 -        unsigned int bytes,
   8.159 -        struct x86_emulate_ctxt *ctxt);
   8.160 -
   8.161 -    /*
   8.162 -     * cmpxchg: Emulate an atomic (LOCKed) CMPXCHG operation.
   8.163 -     *  @old:   [IN ] Value expected to be current at @addr.
   8.164 -     *  @new:   [IN ] Value to write to @addr.
   8.165 -     */
   8.166 -    int (*cmpxchg)(
   8.167 -        enum x86_segment seg,
   8.168 -        unsigned long offset,
   8.169 -        unsigned long old,
   8.170 -        unsigned long new,
   8.171 -        unsigned int bytes,
   8.172 -        struct x86_emulate_ctxt *ctxt);
   8.173 -
   8.174 -    /*
   8.175 -     * cmpxchg8b: Emulate an atomic (LOCKed) CMPXCHG8B operation.
   8.176 -     *  @old:   [IN ] Value expected to be current at @addr.
   8.177 -     *  @new:   [IN ] Value to write to @addr.
   8.178 -     * NOTES:
   8.179 -     *  1. This function is only ever called when emulating a real CMPXCHG8B.
   8.180 -     *  2. This function is *never* called on x86/64 systems.
   8.181 -     *  2. Not defining this function (i.e., specifying NULL) is equivalent
   8.182 -     *     to defining a function that always returns X86EMUL_UNHANDLEABLE.
   8.183 -     */
   8.184 -    int (*cmpxchg8b)(
   8.185 -        enum x86_segment seg,
   8.186 -        unsigned long offset,
   8.187 -        unsigned long old_lo,
   8.188 -        unsigned long old_hi,
   8.189 -        unsigned long new_lo,
   8.190 -        unsigned long new_hi,
   8.191 -        struct x86_emulate_ctxt *ctxt);
   8.192 -
   8.193 -    /*
   8.194 -     * rep_ins: Emulate INS: <src_port> -> <dst_seg:dst_offset>.
   8.195 -     *  @bytes_per_rep: [IN ] Bytes transferred per repetition.
   8.196 -     *  @reps:  [IN ] Maximum repetitions to be emulated.
   8.197 -     *          [OUT] Number of repetitions actually emulated.
   8.198 -     */
   8.199 -    int (*rep_ins)(
   8.200 -        uint16_t src_port,
   8.201 -        enum x86_segment dst_seg,
   8.202 -        unsigned long dst_offset,
   8.203 -        unsigned int bytes_per_rep,
   8.204 -        unsigned long *reps,
   8.205 -        struct x86_emulate_ctxt *ctxt);
   8.206 +#ifndef __ASM_X86_X86_EMULATE_H__
   8.207 +#define __ASM_X86_X86_EMULATE_H__
   8.208  
   8.209 -    /*
   8.210 -     * rep_outs: Emulate OUTS: <src_seg:src_offset> -> <dst_port>.
   8.211 -     *  @bytes_per_rep: [IN ] Bytes transferred per repetition.
   8.212 -     *  @reps:  [IN ] Maximum repetitions to be emulated.
   8.213 -     *          [OUT] Number of repetitions actually emulated.
   8.214 -     */
   8.215 -    int (*rep_outs)(
   8.216 -        enum x86_segment src_seg,
   8.217 -        unsigned long src_offset,
   8.218 -        uint16_t dst_port,
   8.219 -        unsigned int bytes_per_rep,
   8.220 -        unsigned long *reps,
   8.221 -        struct x86_emulate_ctxt *ctxt);
   8.222 -
   8.223 -    /*
   8.224 -     * rep_movs: Emulate MOVS: <src_seg:src_offset> -> <dst_seg:dst_offset>.
   8.225 -     *  @bytes_per_rep: [IN ] Bytes transferred per repetition.
   8.226 -     *  @reps:  [IN ] Maximum repetitions to be emulated.
   8.227 -     *          [OUT] Number of repetitions actually emulated.
   8.228 -     */
   8.229 -    int (*rep_movs)(
   8.230 -        enum x86_segment src_seg,
   8.231 -        unsigned long src_offset,
   8.232 -        enum x86_segment dst_seg,
   8.233 -        unsigned long dst_offset,
   8.234 -        unsigned int bytes_per_rep,
   8.235 -        unsigned long *reps,
   8.236 -        struct x86_emulate_ctxt *ctxt);
   8.237 -
   8.238 -    /*
   8.239 -     * read_segment: Emulate a read of full context of a segment register.
   8.240 -     *  @reg:   [OUT] Contents of segment register (visible and hidden state).
   8.241 -     */
   8.242 -    int (*read_segment)(
   8.243 -        enum x86_segment seg,
   8.244 -        struct segment_register *reg,
   8.245 -        struct x86_emulate_ctxt *ctxt);
   8.246 -
   8.247 -    /*
   8.248 -     * write_segment: Emulate a read of full context of a segment register.
   8.249 -     *  @reg:   [OUT] Contents of segment register (visible and hidden state).
   8.250 -     */
   8.251 -    int (*write_segment)(
   8.252 -        enum x86_segment seg,
   8.253 -        struct segment_register *reg,
   8.254 -        struct x86_emulate_ctxt *ctxt);
   8.255 -
   8.256 -    /*
   8.257 -     * read_io: Read from I/O port(s).
   8.258 -     *  @port:  [IN ] Base port for access.
   8.259 -     */
   8.260 -    int (*read_io)(
   8.261 -        unsigned int port,
   8.262 -        unsigned int bytes,
   8.263 -        unsigned long *val,
   8.264 -        struct x86_emulate_ctxt *ctxt);
   8.265 -
   8.266 -    /*
   8.267 -     * write_io: Write to I/O port(s).
   8.268 -     *  @port:  [IN ] Base port for access.
   8.269 -     */
   8.270 -    int (*write_io)(
   8.271 -        unsigned int port,
   8.272 -        unsigned int bytes,
   8.273 -        unsigned long val,
   8.274 -        struct x86_emulate_ctxt *ctxt);
   8.275 -
   8.276 -    /*
   8.277 -     * read_cr: Read from control register.
   8.278 -     *  @reg:   [IN ] Register to read (0-15).
   8.279 -     */
   8.280 -    int (*read_cr)(
   8.281 -        unsigned int reg,
   8.282 -        unsigned long *val,
   8.283 -        struct x86_emulate_ctxt *ctxt);
   8.284 -
   8.285 -    /*
   8.286 -     * write_cr: Write to control register.
   8.287 -     *  @reg:   [IN ] Register to write (0-15).
   8.288 -     */
   8.289 -    int (*write_cr)(
   8.290 -        unsigned int reg,
   8.291 -        unsigned long val,
   8.292 -        struct x86_emulate_ctxt *ctxt);
   8.293 -
   8.294 -    /*
   8.295 -     * read_dr: Read from debug register.
   8.296 -     *  @reg:   [IN ] Register to read (0-15).
   8.297 -     */
   8.298 -    int (*read_dr)(
   8.299 -        unsigned int reg,
   8.300 -        unsigned long *val,
   8.301 -        struct x86_emulate_ctxt *ctxt);
   8.302 +#include <xen/config.h>
   8.303 +#include <xen/types.h>
   8.304 +#include <xen/lib.h>
   8.305 +#include <asm/regs.h>
   8.306  
   8.307 -    /*
   8.308 -     * write_dr: Write to debug register.
   8.309 -     *  @reg:   [IN ] Register to write (0-15).
   8.310 -     */
   8.311 -    int (*write_dr)(
   8.312 -        unsigned int reg,
   8.313 -        unsigned long val,
   8.314 -        struct x86_emulate_ctxt *ctxt);
   8.315 -
   8.316 -    /*
   8.317 -     * read_msr: Read from model-specific register.
   8.318 -     *  @reg:   [IN ] Register to read.
   8.319 -     */
   8.320 -    int (*read_msr)(
   8.321 -        unsigned long reg,
   8.322 -        uint64_t *val,
   8.323 -        struct x86_emulate_ctxt *ctxt);
   8.324 -
   8.325 -    /*
   8.326 -     * write_dr: Write to model-specific register.
   8.327 -     *  @reg:   [IN ] Register to write.
   8.328 -     */
   8.329 -    int (*write_msr)(
   8.330 -        unsigned long reg,
   8.331 -        uint64_t val,
   8.332 -        struct x86_emulate_ctxt *ctxt);
   8.333 -
   8.334 -    /* wbinvd: Write-back and invalidate cache contents. */
   8.335 -    int (*wbinvd)(
   8.336 -        struct x86_emulate_ctxt *ctxt);
   8.337 -
   8.338 -    /* cpuid: Emulate CPUID via given set of EAX-EDX inputs/outputs. */
   8.339 -    int (*cpuid)(
   8.340 -        unsigned int *eax,
   8.341 -        unsigned int *ebx,
   8.342 -        unsigned int *ecx,
   8.343 -        unsigned int *edx,
   8.344 -        struct x86_emulate_ctxt *ctxt);
   8.345 -
   8.346 -    /* inject_hw_exception */
   8.347 -    int (*inject_hw_exception)(
   8.348 -        uint8_t vector,
   8.349 -        int32_t error_code,
   8.350 -        struct x86_emulate_ctxt *ctxt);
   8.351 -
   8.352 -    /* inject_sw_interrupt */
   8.353 -    int (*inject_sw_interrupt)(
   8.354 -        uint8_t vector,
   8.355 -        uint8_t insn_len,
   8.356 -        struct x86_emulate_ctxt *ctxt);
   8.357 +#include "../../arch/x86/x86_emulate/x86_emulate.h"
   8.358  
   8.359 -    /* load_fpu_ctxt: Load emulated environment's FPU state onto processor. */
   8.360 -    void (*load_fpu_ctxt)(
   8.361 -        struct x86_emulate_ctxt *ctxt);
   8.362 -
   8.363 -    /* invlpg: Invalidate paging structures which map addressed byte. */
   8.364 -    int (*invlpg)(
   8.365 -        enum x86_segment seg,
   8.366 -        unsigned long offset,
   8.367 -        struct x86_emulate_ctxt *ctxt);
   8.368 -};
   8.369 -
   8.370 -struct cpu_user_regs;
   8.371 -
   8.372 -struct x86_emulate_ctxt
   8.373 -{
   8.374 -    /* Register state before/after emulation. */
   8.375 -    struct cpu_user_regs *regs;
   8.376 -
   8.377 -    /* Default address size in current execution mode (16, 32, or 64). */
   8.378 -    unsigned int addr_size;
   8.379 -
   8.380 -    /* Stack pointer width in bits (16, 32 or 64). */
   8.381 -    unsigned int sp_size;
   8.382 -
   8.383 -    /* Set this if writes may have side effects. */
   8.384 -    uint8_t force_writeback;
   8.385 -
   8.386 -    /* Retirement state, set by the emulator (valid only on X86EMUL_OKAY). */
   8.387 -    union {
   8.388 -        struct {
   8.389 -            uint8_t hlt:1;          /* Instruction HLTed. */
   8.390 -            uint8_t mov_ss:1;       /* Instruction sets MOV-SS irq shadow. */
   8.391 -            uint8_t sti:1;          /* Instruction sets STI irq shadow. */
   8.392 -        } flags;
   8.393 -        uint8_t byte;
   8.394 -    } retire;
   8.395 -};
   8.396 -
   8.397 -/*
   8.398 - * x86_emulate: Emulate an instruction.
   8.399 - * Returns -1 on failure, 0 on success.
   8.400 - */
   8.401 -int
   8.402 -x86_emulate(
   8.403 -    struct x86_emulate_ctxt *ctxt,
   8.404 -    struct x86_emulate_ops  *ops);
   8.405 -
   8.406 -/*
   8.407 - * Given the 'reg' portion of a ModRM byte, and a register block, return a
   8.408 - * pointer into the block that addresses the relevant register.
   8.409 - * @highbyte_regs specifies whether to decode AH,CH,DH,BH.
   8.410 - */
   8.411 -void *
   8.412 -decode_register(
   8.413 -    uint8_t modrm_reg, struct cpu_user_regs *regs, int highbyte_regs);
   8.414 -
   8.415 -#endif /* __X86_EMULATE_H__ */
   8.416 +#endif /* __ASM_X86_X86_EMULATE_H__ */