/*===-- X86DisassemblerDecoder.c - Disassembler decoder ------------*- C -*-===*
 *
 *                     The LLVM Compiler Infrastructure
 *
 * This file is distributed under the University of Illinois Open Source
 * License. See LICENSE.TXT for details.
 *
 *===----------------------------------------------------------------------===*
 *
 * This file is part of the X86 Disassembler.
 * It contains the implementation of the instruction decoder.
 * Documentation for the disassembler can be found in X86Disassembler.h.
 *
 *===----------------------------------------------------------------------===*/

/* Capstone Disassembly Engine */
/* By Nguyen Anh Quynh <aquynh@gmail.com>, 2013-2015 */

#ifdef CAPSTONE_HAS_X86

#include <stdarg.h>   /* for va_*()       */
#if defined(CAPSTONE_HAS_OSXKERNEL)
#include <libkern/libkern.h>
#else
#include <stdlib.h>   /* for exit()       */
#endif

#include "../../cs_priv.h"
#include "../../utils.h"

#include "X86DisassemblerDecoder.h"

/// Specifies whether a ModR/M byte is needed and (if so) which
/// instruction each possible value of the ModR/M byte corresponds to.  Once
/// this information is known, we have narrowed down to a single instruction.
struct ModRMDecision {
	uint8_t modrm_type;
	uint16_t instructionIDs;
};

/// Specifies which set of ModR/M->instruction tables to look at
/// given a particular opcode.
struct OpcodeDecision {
	struct ModRMDecision modRMDecisions[256];
};

/// Specifies which opcode->instruction tables to look at given
/// a particular context (set of attributes).  Since there are many possible
/// contexts, the decoder first uses CONTEXTS_SYM to determine which context
/// applies given a specific set of attributes.  Hence there are only IC_max
/// entries in this table, rather than 2^(ATTR_max).
struct ContextDecision {
	struct OpcodeDecision opcodeDecisions[IC_max];
};

#ifdef CAPSTONE_X86_REDUCE
#include "X86GenDisassemblerTables_reduce.inc"
#else
#include "X86GenDisassemblerTables.inc"
#endif

//#define GET_INSTRINFO_ENUM
#define GET_INSTRINFO_MC_DESC
#ifdef CAPSTONE_X86_REDUCE
#include "X86GenInstrInfo_reduce.inc"
#else
#include "X86GenInstrInfo.inc"
#endif

/*
 * contextForAttrs - Client for the instruction context table.  Takes a set of
 *   attributes and returns the appropriate decode context.
 *
 * @param attrMask  - Attributes, from the enumeration attributeBits.
 * @return          - The InstructionContext to use when looking up an
 *                    an instruction with these attributes.
 */
static InstructionContext contextForAttrs(uint16_t attrMask)
{
	return CONTEXTS_SYM[attrMask];
}

/*
 * modRMRequired - Reads the appropriate instruction table to determine whether
 *   the ModR/M byte is required to decode a particular instruction.
 *
 * @param type        - The opcode type (i.e., how many bytes it has).
 * @param insnContext - The context for the instruction, as returned by
 *                      contextForAttrs.
 * @param opcode      - The last byte of the instruction's opcode, not counting
 *                      ModR/M extensions and escapes.
 * @return            - true if the ModR/M byte is required, false otherwise.
 */
static int modRMRequired(OpcodeType type,
		InstructionContext insnContext,
		uint16_t opcode)
{
	const struct OpcodeDecision *decision = NULL;
	const uint8_t *indextable = NULL;
	uint8_t index;

	switch (type) {
		default:
		case ONEBYTE:
			decision = ONEBYTE_SYM;
			indextable = index_x86DisassemblerOneByteOpcodes;
			break;
		case TWOBYTE:
			decision = TWOBYTE_SYM;
			indextable = index_x86DisassemblerTwoByteOpcodes;
			break;
		case THREEBYTE_38:
			decision = THREEBYTE38_SYM;
			indextable = index_x86DisassemblerThreeByte38Opcodes;
			break;
		case THREEBYTE_3A:
			decision = THREEBYTE3A_SYM;
			indextable = index_x86DisassemblerThreeByte3AOpcodes;
			break;
#ifndef CAPSTONE_X86_REDUCE
		case XOP8_MAP:
			decision = XOP8_MAP_SYM;
			indextable = index_x86DisassemblerXOP8Opcodes;
			break;
		case XOP9_MAP:
			decision = XOP9_MAP_SYM;
			indextable = index_x86DisassemblerXOP9Opcodes;
			break;
		case XOPA_MAP:
			decision = XOPA_MAP_SYM;
			indextable = index_x86DisassemblerXOPAOpcodes;
			break;
		case T3DNOW_MAP:
			// 3DNow instructions always have ModRM byte
			return true;
#endif
	}

	index = indextable[insnContext];
	if (index)
		return decision[index - 1].modRMDecisions[opcode].modrm_type != MODRM_ONEENTRY;
	else
		return false;
}

/*
 * decode - Reads the appropriate instruction table to obtain the unique ID of
 *   an instruction.
 *
 * @param type        - See modRMRequired().
 * @param insnContext - See modRMRequired().
 * @param opcode      - See modRMRequired().
 * @param modRM       - The ModR/M byte if required, or any value if not.
 * @return            - The UID of the instruction, or 0 on failure.
 */
static InstrUID decode(OpcodeType type,
		InstructionContext insnContext,
		uint8_t opcode,
		uint8_t modRM)
{
	const struct ModRMDecision *dec = NULL;
	const uint8_t *indextable = NULL;
	uint8_t index;

	switch (type) {
		default:
		case ONEBYTE:
			indextable = index_x86DisassemblerOneByteOpcodes;
			index = indextable[insnContext];
			if (index)
				dec = &ONEBYTE_SYM[index - 1].modRMDecisions[opcode];
			else
				dec = &emptyTable.modRMDecisions[opcode];
			break;
		case TWOBYTE:
			indextable = index_x86DisassemblerTwoByteOpcodes;
			index = indextable[insnContext];
			if (index)
				dec = &TWOBYTE_SYM[index - 1].modRMDecisions[opcode];
			else
				dec = &emptyTable.modRMDecisions[opcode];
			break;
		case THREEBYTE_38:
			indextable = index_x86DisassemblerThreeByte38Opcodes;
			index = indextable[insnContext];
			if (index)
				dec = &THREEBYTE38_SYM[index - 1].modRMDecisions[opcode];
			else
				dec = &emptyTable.modRMDecisions[opcode];
			break;
		case THREEBYTE_3A:
			indextable = index_x86DisassemblerThreeByte3AOpcodes;
			index = indextable[insnContext];
			if (index)
				dec = &THREEBYTE3A_SYM[index - 1].modRMDecisions[opcode];
			else
				dec = &emptyTable.modRMDecisions[opcode];
			break;
#ifndef CAPSTONE_X86_REDUCE
		case XOP8_MAP:
			indextable = index_x86DisassemblerXOP8Opcodes;
			index = indextable[insnContext];
			if (index)
				dec = &XOP8_MAP_SYM[index - 1].modRMDecisions[opcode];
			else
				dec = &emptyTable.modRMDecisions[opcode];
			break;
		case XOP9_MAP:
			indextable = index_x86DisassemblerXOP9Opcodes;
			index = indextable[insnContext];
			if (index)
				dec = &XOP9_MAP_SYM[index - 1].modRMDecisions[opcode];
			else
				dec = &emptyTable.modRMDecisions[opcode];
			break;
		case XOPA_MAP:
			indextable = index_x86DisassemblerXOPAOpcodes;
			index = indextable[insnContext];
			if (index)
				dec = &XOPA_MAP_SYM[index - 1].modRMDecisions[opcode];
			else
				dec = &emptyTable.modRMDecisions[opcode];
			break;
		case T3DNOW_MAP:
			indextable = index_x86DisassemblerT3DNOWOpcodes;
			index = indextable[insnContext];
			if (index)
				dec = &T3DNOW_MAP_SYM[index - 1].modRMDecisions[opcode];
			else
				dec = &emptyTable.modRMDecisions[opcode];
			break;
#endif
	}

	switch (dec->modrm_type) {
		default:
			//debug("Corrupt table!  Unknown modrm_type");
			return 0;
		case MODRM_ONEENTRY:
			return modRMTable[dec->instructionIDs];
		case MODRM_SPLITRM:
			if (modFromModRM(modRM) == 0x3)
				return modRMTable[dec->instructionIDs+1];
			return modRMTable[dec->instructionIDs];
		case MODRM_SPLITREG:
			if (modFromModRM(modRM) == 0x3)
				return modRMTable[dec->instructionIDs+((modRM & 0x38) >> 3)+8];
			return modRMTable[dec->instructionIDs+((modRM & 0x38) >> 3)];
		case MODRM_SPLITMISC:
			if (modFromModRM(modRM) == 0x3)
				return modRMTable[dec->instructionIDs+(modRM & 0x3f)+8];
			return modRMTable[dec->instructionIDs+((modRM & 0x38) >> 3)];
		case MODRM_FULL:
			return modRMTable[dec->instructionIDs+modRM];
	}
}

/*
 * specifierForUID - Given a UID, returns the name and operand specification for
 *   that instruction.
 *
 * @param uid - The unique ID for the instruction.  This should be returned by
 *              decode(); specifierForUID will not check bounds.
 * @return    - A pointer to the specification for that instruction.
 */
static const struct InstructionSpecifier *specifierForUID(InstrUID uid)
{
	return &INSTRUCTIONS_SYM[uid];
}

/*
 * consumeByte - Uses the reader function provided by the user to consume one
 *   byte from the instruction's memory and advance the cursor.
 *
 * @param insn  - The instruction with the reader function to use.  The cursor
 *                for this instruction is advanced.
 * @param byte  - A pointer to a pre-allocated memory buffer to be populated
 *                with the data read.
 * @return      - 0 if the read was successful; nonzero otherwise.
 */
static int consumeByte(struct InternalInstruction *insn, uint8_t *byte)
{
	int ret = insn->reader(insn->readerArg, byte, insn->readerCursor);

	if (!ret)
		++(insn->readerCursor);

	return ret;
}

/*
 * lookAtByte - Like consumeByte, but does not advance the cursor.
 *
 * @param insn  - See consumeByte().
 * @param byte  - See consumeByte().
 * @return      - See consumeByte().
 */
static int lookAtByte(struct InternalInstruction *insn, uint8_t *byte)
{
	return insn->reader(insn->readerArg, byte, insn->readerCursor);
}

static void unconsumeByte(struct InternalInstruction *insn)
{
	insn->readerCursor--;
}

#define CONSUME_FUNC(name, type)                                  \
	static int name(struct InternalInstruction *insn, type *ptr) {  \
		type combined = 0;                                            \
		unsigned offset;                                              \
		for (offset = 0; offset < sizeof(type); ++offset) {           \
			uint8_t byte;                                               \
			int ret = insn->reader(insn->readerArg,                     \
					&byte,                               \
					insn->readerCursor + offset);        \
			if (ret)                                                    \
			return ret;                                               \
			combined = combined | (type)((uint64_t)byte << (offset * 8));     \
		}                                                             \
		*ptr = combined;                                              \
		insn->readerCursor += sizeof(type);                           \
		return 0;                                                     \
	}

/*
 * consume* - Use the reader function provided by the user to consume data
 *   values of various sizes from the instruction's memory and advance the
 *   cursor appropriately.  These readers perform endian conversion.
 *
 * @param insn    - See consumeByte().
 * @param ptr     - A pointer to a pre-allocated memory of appropriate size to
 *                  be populated with the data read.
 * @return        - See consumeByte().
 */
CONSUME_FUNC(consumeInt8, int8_t)
CONSUME_FUNC(consumeInt16, int16_t)
CONSUME_FUNC(consumeInt32, int32_t)
CONSUME_FUNC(consumeUInt16, uint16_t)
CONSUME_FUNC(consumeUInt32, uint32_t)
CONSUME_FUNC(consumeUInt64, uint64_t)

/*
 * setPrefixPresent - Marks that a particular prefix is present at a particular
 *   location.
 *
 * @param insn      - The instruction to be marked as having the prefix.
 * @param prefix    - The prefix that is present.
 * @param location  - The location where the prefix is located (in the address
 *                    space of the instruction's reader).
 */
static void setPrefixPresent(struct InternalInstruction *insn, uint8_t prefix, uint64_t location)
{
	switch (prefix) {
	case 0x26:
		insn->isPrefix26 = true;
		insn->prefix26 = location;
		break;
	case 0x2e:
		insn->isPrefix2e = true;
		insn->prefix2e = location;
		break;
	case 0x36:
		insn->isPrefix36 = true;
		insn->prefix36 = location;
		break;
	case 0x3e:
		insn->isPrefix3e = true;
		insn->prefix3e = location;
		break;
	case 0x64:
		insn->isPrefix64 = true;
		insn->prefix64 = location;
		break;
	case 0x65:
		insn->isPrefix65 = true;
		insn->prefix65 = location;
		break;
	case 0x66:
		insn->isPrefix66 = true;
		insn->prefix66 = location;
		break;
	case 0x67:
		insn->isPrefix67 = true;
		insn->prefix67 = location;
		break;
	case 0xf0:
		insn->isPrefixf0 = true;
		insn->prefixf0 = location;
		break;
	case 0xf2:
		insn->isPrefixf2 = true;
		insn->prefixf2 = location;
		break;
	case 0xf3:
		insn->isPrefixf3 = true;
		insn->prefixf3 = location;
		break;
	default:
		break;
	}
}

/*
 * isPrefixAtLocation - Queries an instruction to determine whether a prefix is
 *   present at a given location.
 *
 * @param insn      - The instruction to be queried.
 * @param prefix    - The prefix.
 * @param location  - The location to query.
 * @return          - Whether the prefix is at that location.
 */
static bool isPrefixAtLocation(struct InternalInstruction *insn, uint8_t prefix,
		uint64_t location)
{
	switch (prefix) {
	case 0x26:
		if (insn->isPrefix26 && insn->prefix26 == location)
			return true;
		break;
	case 0x2e:
		if (insn->isPrefix2e && insn->prefix2e == location)
			return true;
		break;
	case 0x36:
		if (insn->isPrefix36 && insn->prefix36 == location)
			return true;
		break;
	case 0x3e:
		if (insn->isPrefix3e && insn->prefix3e == location)
			return true;
		break;
	case 0x64:
		if (insn->isPrefix64 && insn->prefix64 == location)
			return true;
		break;
	case 0x65:
		if (insn->isPrefix65 && insn->prefix65 == location)
			return true;
		break;
	case 0x66:
		if (insn->isPrefix66 && insn->prefix66 == location)
			return true;
		break;
	case 0x67:
		if (insn->isPrefix67 && insn->prefix67 == location)
			return true;
		break;
	case 0xf0:
		if (insn->isPrefixf0 && insn->prefixf0 == location)
			return true;
		break;
	case 0xf2:
		if (insn->isPrefixf2 && insn->prefixf2 == location)
			return true;
		break;
	case 0xf3:
		if (insn->isPrefixf3 && insn->prefixf3 == location)
			return true;
		break;
	default:
		break;
	}
	return false;
}

/*
 * readPrefixes - Consumes all of an instruction's prefix bytes, and marks the
 *   instruction as having them.  Also sets the instruction's default operand,
 *   address, and other relevant data sizes to report operands correctly.
 *
 * @param insn  - The instruction whose prefixes are to be read.
 * @return      - 0 if the instruction could be read until the end of the prefix
 *                bytes, and no prefixes conflicted; nonzero otherwise.
 */
static int readPrefixes(struct InternalInstruction *insn)
{
	bool isPrefix = true;
	uint64_t prefixLocation;
	uint8_t byte = 0, nextByte;

	bool hasAdSize = false;
	bool hasOpSize = false;

	while (isPrefix) {
		if (insn->mode == MODE_64BIT) {
			// eliminate consecutive redundant REX bytes in front
			if (consumeByte(insn, &byte))
				return -1;

			if ((byte & 0xf0) == 0x40) {
				while(true) {
					if (lookAtByte(insn, &byte))	// out of input code
						return -1;
					if ((byte & 0xf0) == 0x40) {
						// another REX prefix, but we only remember the last one
						if (consumeByte(insn, &byte))
							return -1;
					} else
						break;
				}

				// recover the last REX byte if next byte is not a legacy prefix
				switch (byte) {
					case 0xf2:  /* REPNE/REPNZ */
					case 0xf3:  /* REP or REPE/REPZ */
					case 0xf0:  /* LOCK */
					case 0x2e:  /* CS segment override -OR- Branch not taken */
					case 0x36:  /* SS segment override -OR- Branch taken */
					case 0x3e:  /* DS segment override */
					case 0x26:  /* ES segment override */
					case 0x64:  /* FS segment override */
					case 0x65:  /* GS segment override */
					case 0x66:  /* Operand-size override */
					case 0x67:  /* Address-size override */
						break;
					default:    /* Not a prefix byte */
						unconsumeByte(insn);
						break;
				}
			} else {
				unconsumeByte(insn);
			}
		}

		prefixLocation = insn->readerCursor;

		/* If we fail reading prefixes, just stop here and let the opcode reader deal with it */
		if (consumeByte(insn, &byte))
			return -1;

		if (insn->readerCursor - 1 == insn->startLocation
				&& (byte == 0xf2 || byte == 0xf3)) {

			if (lookAtByte(insn, &nextByte))
				return -1;

			/*
			 * If the byte is 0xf2 or 0xf3, and any of the following conditions are
			 * met:
			 * - it is followed by a LOCK (0xf0) prefix
			 * - it is followed by an xchg instruction
			 * then it should be disassembled as a xacquire/xrelease not repne/rep.
			 */
			if ((byte == 0xf2 || byte == 0xf3) &&
					((nextByte == 0xf0) |
					 ((nextByte & 0xfe) == 0x86 || (nextByte & 0xf8) == 0x90)))
				insn->xAcquireRelease = true;
			/*
			 * Also if the byte is 0xf3, and the following condition is met:
			 * - it is followed by a "mov mem, reg" (opcode 0x88/0x89) or
			 *                       "mov mem, imm" (opcode 0xc6/0xc7) instructions.
			 * then it should be disassembled as an xrelease not rep.
			 */
			if (byte == 0xf3 &&
					(nextByte == 0x88 || nextByte == 0x89 ||
					 nextByte == 0xc6 || nextByte == 0xc7))
				insn->xAcquireRelease = true;

			if (insn->mode == MODE_64BIT && (nextByte & 0xf0) == 0x40) {
				if (consumeByte(insn, &nextByte))
					return -1;
				if (lookAtByte(insn, &nextByte))
					return -1;
				unconsumeByte(insn);
			}
		}

		switch (byte) {
			case 0xf2:  /* REPNE/REPNZ */
			case 0xf3:  /* REP or REPE/REPZ */
			case 0xf0:  /* LOCK */
				// only accept the last prefix
				insn->isPrefixf2 = false;
				insn->isPrefixf3 = false;
				insn->isPrefixf0 = false;
				setPrefixPresent(insn, byte, prefixLocation);
				insn->prefix0 = byte;
				break;
			case 0x2e:  /* CS segment override -OR- Branch not taken */
				insn->segmentOverride = SEG_OVERRIDE_CS;
				// only accept the last prefix
				insn->isPrefix2e = false;
				insn->isPrefix36 = false;
				insn->isPrefix3e = false;
				insn->isPrefix26 = false;
				insn->isPrefix64 = false;
				insn->isPrefix65 = false;

				setPrefixPresent(insn, byte, prefixLocation);
				insn->prefix1 = byte;
				break;
			case 0x36:  /* SS segment override -OR- Branch taken */
				insn->segmentOverride = SEG_OVERRIDE_SS;
				// only accept the last prefix
				insn->isPrefix2e = false;
				insn->isPrefix36 = false;
				insn->isPrefix3e = false;
				insn->isPrefix26 = false;
				insn->isPrefix64 = false;
				insn->isPrefix65 = false;

				setPrefixPresent(insn, byte, prefixLocation);
				insn->prefix1 = byte;
				break;
			case 0x3e:  /* DS segment override */
				insn->segmentOverride = SEG_OVERRIDE_DS;
				// only accept the last prefix
				insn->isPrefix2e = false;
				insn->isPrefix36 = false;
				insn->isPrefix3e = false;
				insn->isPrefix26 = false;
				insn->isPrefix64 = false;
				insn->isPrefix65 = false;

				setPrefixPresent(insn, byte, prefixLocation);
				insn->prefix1 = byte;
				break;
			case 0x26:  /* ES segment override */
				insn->segmentOverride = SEG_OVERRIDE_ES;
				// only accept the last prefix
				insn->isPrefix2e = false;
				insn->isPrefix36 = false;
				insn->isPrefix3e = false;
				insn->isPrefix26 = false;
				insn->isPrefix64 = false;
				insn->isPrefix65 = false;

				setPrefixPresent(insn, byte, prefixLocation);
				insn->prefix1 = byte;
				break;
			case 0x64:  /* FS segment override */
				insn->segmentOverride = SEG_OVERRIDE_FS;
				// only accept the last prefix
				insn->isPrefix2e = false;
				insn->isPrefix36 = false;
				insn->isPrefix3e = false;
				insn->isPrefix26 = false;
				insn->isPrefix64 = false;
				insn->isPrefix65 = false;

				setPrefixPresent(insn, byte, prefixLocation);
				insn->prefix1 = byte;
				break;
			case 0x65:  /* GS segment override */
				insn->segmentOverride = SEG_OVERRIDE_GS;
				// only accept the last prefix
				insn->isPrefix2e = false;
				insn->isPrefix36 = false;
				insn->isPrefix3e = false;
				insn->isPrefix26 = false;
				insn->isPrefix64 = false;
				insn->isPrefix65 = false;

				setPrefixPresent(insn, byte, prefixLocation);
				insn->prefix1 = byte;
				break;
			case 0x66:  /* Operand-size override */
				hasOpSize = true;
				setPrefixPresent(insn, byte, prefixLocation);
				insn->prefix2 = byte;
				break;
			case 0x67:  /* Address-size override */
				hasAdSize = true;
				setPrefixPresent(insn, byte, prefixLocation);
				insn->prefix3 = byte;
				break;
			default:    /* Not a prefix byte */
				isPrefix = false;
				break;
		}

		//if (isPrefix)
		//	dbgprintf(insn, "Found prefix 0x%hhx", byte);
	}

	insn->vectorExtensionType = TYPE_NO_VEX_XOP;


	if (byte == 0x62) {
		uint8_t byte1, byte2;

		if (consumeByte(insn, &byte1)) {
			//dbgprintf(insn, "Couldn't read second byte of EVEX prefix");
			return -1;
		}

		if ((insn->mode == MODE_64BIT || (byte1 & 0xc0) == 0xc0) &&
				((~byte1 & 0xc) == 0xc)) {
			if (lookAtByte(insn, &byte2)) {
				//dbgprintf(insn, "Couldn't read third byte of EVEX prefix");
				return -1;
			}

			if ((byte2 & 0x4) == 0x4) {
				insn->vectorExtensionType = TYPE_EVEX;
			} else {
				unconsumeByte(insn); /* unconsume byte1 */
				unconsumeByte(insn); /* unconsume byte  */
				insn->necessaryPrefixLocation = insn->readerCursor - 2;
			}

			if (insn->vectorExtensionType == TYPE_EVEX) {
				insn->vectorExtensionPrefix[0] = byte;
				insn->vectorExtensionPrefix[1] = byte1;

				if (consumeByte(insn, &insn->vectorExtensionPrefix[2])) {
					//dbgprintf(insn, "Couldn't read third byte of EVEX prefix");
					return -1;
				}

				if (consumeByte(insn, &insn->vectorExtensionPrefix[3])) {
					//dbgprintf(insn, "Couldn't read fourth byte of EVEX prefix");
					return -1;
				}

				/* We simulate the REX prefix for simplicity's sake */
				if (insn->mode == MODE_64BIT) {
					insn->rexPrefix = 0x40
						| (wFromEVEX3of4(insn->vectorExtensionPrefix[2]) << 3)
						| (rFromEVEX2of4(insn->vectorExtensionPrefix[1]) << 2)
						| (xFromEVEX2of4(insn->vectorExtensionPrefix[1]) << 1)
						| (bFromEVEX2of4(insn->vectorExtensionPrefix[1]) << 0);
				}

				//dbgprintf(insn, "Found EVEX prefix 0x%hhx 0x%hhx 0x%hhx 0x%hhx",
				//		insn->vectorExtensionPrefix[0], insn->vectorExtensionPrefix[1],
				//		insn->vectorExtensionPrefix[2], insn->vectorExtensionPrefix[3]);
			}
		} else {
			// BOUND instruction
			unconsumeByte(insn); /* unconsume byte1 */
			unconsumeByte(insn); /* unconsume byte */
		}
	} else if (byte == 0xc4) {
		uint8_t byte1;

		if (lookAtByte(insn, &byte1)) {
			//dbgprintf(insn, "Couldn't read second byte of VEX");
			return -1;
		}

		if (insn->mode == MODE_64BIT || (byte1 & 0xc0) == 0xc0) {
			insn->vectorExtensionType = TYPE_VEX_3B;
			insn->necessaryPrefixLocation = insn->readerCursor - 1;
		} else {
			unconsumeByte(insn);
			insn->necessaryPrefixLocation = insn->readerCursor - 1;
		}

		if (insn->vectorExtensionType == TYPE_VEX_3B) {
			insn->vectorExtensionPrefix[0] = byte;
			if (consumeByte(insn, &insn->vectorExtensionPrefix[1]))
				return -1;
			if (consumeByte(insn, &insn->vectorExtensionPrefix[2]))
				return -1;

			/* We simulate the REX prefix for simplicity's sake */
			if (insn->mode == MODE_64BIT) {
				insn->rexPrefix = 0x40
					| (wFromVEX3of3(insn->vectorExtensionPrefix[2]) << 3)
					| (rFromVEX2of3(insn->vectorExtensionPrefix[1]) << 2)
					| (xFromVEX2of3(insn->vectorExtensionPrefix[1]) << 1)
					| (bFromVEX2of3(insn->vectorExtensionPrefix[1]) << 0);

			}
		}
	} else if (byte == 0xc5) {
		uint8_t byte1;

		if (lookAtByte(insn, &byte1)) {
			//dbgprintf(insn, "Couldn't read second byte of VEX");
			return -1;
		}

		if (insn->mode == MODE_64BIT || (byte1 & 0xc0) == 0xc0) {
			insn->vectorExtensionType = TYPE_VEX_2B;
		} else {
			unconsumeByte(insn);
		}

		if (insn->vectorExtensionType == TYPE_VEX_2B) {
			insn->vectorExtensionPrefix[0] = byte;
			if (consumeByte(insn, &insn->vectorExtensionPrefix[1]))
				return -1;

			if (insn->mode == MODE_64BIT) {
				insn->rexPrefix = 0x40
					| (rFromVEX2of2(insn->vectorExtensionPrefix[1]) << 2);
			}

			switch (ppFromVEX2of2(insn->vectorExtensionPrefix[1])) {
				default:
					break;
				case VEX_PREFIX_66:
					hasOpSize = true;
					break;
			}
		}
	} else if (byte == 0x8f) {
		uint8_t byte1;

		if (lookAtByte(insn, &byte1)) {
			// dbgprintf(insn, "Couldn't read second byte of XOP");
			return -1;
		}

		if ((byte1 & 0x38) != 0x0) { /* 0 in these 3 bits is a POP instruction. */
			insn->vectorExtensionType = TYPE_XOP;
			insn->necessaryPrefixLocation = insn->readerCursor - 1;
		} else {
			unconsumeByte(insn);
			insn->necessaryPrefixLocation = insn->readerCursor - 1;
		}

		if (insn->vectorExtensionType == TYPE_XOP) {
			insn->vectorExtensionPrefix[0] = byte;
			if (consumeByte(insn, &insn->vectorExtensionPrefix[1]))
				return -1;
			if (consumeByte(insn, &insn->vectorExtensionPrefix[2]))
				return -1;

			/* We simulate the REX prefix for simplicity's sake */
			if (insn->mode == MODE_64BIT) {
				insn->rexPrefix = 0x40
					| (wFromXOP3of3(insn->vectorExtensionPrefix[2]) << 3)
					| (rFromXOP2of3(insn->vectorExtensionPrefix[1]) << 2)
					| (xFromXOP2of3(insn->vectorExtensionPrefix[1]) << 1)
					| (bFromXOP2of3(insn->vectorExtensionPrefix[1]) << 0);
			}

			switch (ppFromXOP3of3(insn->vectorExtensionPrefix[2])) {
				default:
					break;
				case VEX_PREFIX_66:
					hasOpSize = true;
					break;
			}
		}
	} else {
		if (insn->mode == MODE_64BIT) {
			if ((byte & 0xf0) == 0x40) {
				uint8_t opcodeByte;

				while(true) {
					if (lookAtByte(insn, &opcodeByte))	// out of input code
						return -1;
					if ((opcodeByte & 0xf0) == 0x40) {
						// another REX prefix, but we only remember the last one
						if (consumeByte(insn, &byte))
							return -1;
					} else
						break;
				}

				insn->rexPrefix = byte;
				insn->necessaryPrefixLocation = insn->readerCursor - 2;
				// dbgprintf(insn, "Found REX prefix 0x%hhx", byte);
			} else {
				unconsumeByte(insn);
				insn->necessaryPrefixLocation = insn->readerCursor - 1;
			}
		} else {
			unconsumeByte(insn);
			insn->necessaryPrefixLocation = insn->readerCursor - 1;
		}
	}

	if (insn->mode == MODE_16BIT) {
		insn->registerSize       = (hasOpSize ? 4 : 2);
		insn->addressSize        = (hasAdSize ? 4 : 2);
		insn->displacementSize   = (hasAdSize ? 4 : 2);
		insn->immediateSize      = (hasOpSize ? 4 : 2);
		insn->immSize = (hasOpSize ? 4 : 2);
	} else if (insn->mode == MODE_32BIT) {
		insn->registerSize       = (hasOpSize ? 2 : 4);
		insn->addressSize        = (hasAdSize ? 2 : 4);
		insn->displacementSize   = (hasAdSize ? 2 : 4);
		insn->immediateSize      = (hasOpSize ? 2 : 4);
		insn->immSize = (hasOpSize ? 2 : 4);
	} else if (insn->mode == MODE_64BIT) {
		if (insn->rexPrefix && wFromREX(insn->rexPrefix)) {
			insn->registerSize       = 8;
			insn->addressSize        = (hasAdSize ? 4 : 8);
			insn->displacementSize   = 4;
			insn->immediateSize      = 4;
			insn->immSize      = 4;
		} else if (insn->rexPrefix) {
			insn->registerSize       = (hasOpSize ? 2 : 4);
			insn->addressSize        = (hasAdSize ? 4 : 8);
			insn->displacementSize   = (hasOpSize ? 2 : 4);
			insn->immediateSize      = (hasOpSize ? 2 : 4);
			insn->immSize      = (hasOpSize ? 2 : 4);
		} else {
			insn->registerSize       = (hasOpSize ? 2 : 4);
			insn->addressSize        = (hasAdSize ? 4 : 8);
			insn->displacementSize   = (hasOpSize ? 2 : 4);
			insn->immediateSize      = (hasOpSize ? 2 : 4);
			insn->immSize      = (hasOpSize ? 4 : 8);
		}
	}

	return 0;
}

static int readModRM(struct InternalInstruction *insn);

/*
 * readOpcode - Reads the opcode (excepting the ModR/M byte in the case of
 *   extended or escape opcodes).
 *
 * @param insn  - The instruction whose opcode is to be read.
 * @return      - 0 if the opcode could be read successfully; nonzero otherwise.
 */
static int readOpcode(struct InternalInstruction *insn)
{
	/* Determine the length of the primary opcode */
	uint8_t current;

	// printf(">>> readOpcode() = %x\n", insn->readerCursor);

	insn->opcodeType = ONEBYTE;

	if (insn->vectorExtensionType == TYPE_EVEX) {
		switch (mmFromEVEX2of4(insn->vectorExtensionPrefix[1])) {
			default:
				// dbgprintf(insn, "Unhandled mm field for instruction (0x%hhx)",
				// 		mmFromEVEX2of4(insn->vectorExtensionPrefix[1]));
				return -1;
			case VEX_LOB_0F:
				insn->opcodeType = TWOBYTE;
				return consumeByte(insn, &insn->opcode);
			case VEX_LOB_0F38:
				insn->opcodeType = THREEBYTE_38;
				return consumeByte(insn, &insn->opcode);
			case VEX_LOB_0F3A:
				insn->opcodeType = THREEBYTE_3A;
				return consumeByte(insn, &insn->opcode);
		}
	} else if (insn->vectorExtensionType == TYPE_VEX_3B) {
		switch (mmmmmFromVEX2of3(insn->vectorExtensionPrefix[1])) {
			default:
				// dbgprintf(insn, "Unhandled m-mmmm field for instruction (0x%hhx)",
				//		mmmmmFromVEX2of3(insn->vectorExtensionPrefix[1]));
				return -1;
			case VEX_LOB_0F:
				insn->twoByteEscape = 0x0f;
				insn->opcodeType = TWOBYTE;
				return consumeByte(insn, &insn->opcode);
			case VEX_LOB_0F38:
				insn->twoByteEscape = 0x0f;
				insn->threeByteEscape = 0x38;
				insn->opcodeType = THREEBYTE_38;
				return consumeByte(insn, &insn->opcode);
			case VEX_LOB_0F3A:
				insn->twoByteEscape = 0x0f;
				insn->threeByteEscape = 0x3a;
				insn->opcodeType = THREEBYTE_3A;
				return consumeByte(insn, &insn->opcode);
		}
	} else if (insn->vectorExtensionType == TYPE_VEX_2B) {
		insn->twoByteEscape = 0x0f;
		insn->opcodeType = TWOBYTE;
		return consumeByte(insn, &insn->opcode);
	} else if (insn->vectorExtensionType == TYPE_XOP) {
		switch (mmmmmFromXOP2of3(insn->vectorExtensionPrefix[1])) {
			default:
				// dbgprintf(insn, "Unhandled m-mmmm field for instruction (0x%hhx)",
				// 		mmmmmFromVEX2of3(insn->vectorExtensionPrefix[1]));
				return -1;
			case XOP_MAP_SELECT_8:
				// FIXME: twoByteEscape?
				insn->opcodeType = XOP8_MAP;
				return consumeByte(insn, &insn->opcode);
			case XOP_MAP_SELECT_9:
				// FIXME: twoByteEscape?
				insn->opcodeType = XOP9_MAP;
				return consumeByte(insn, &insn->opcode);
			case XOP_MAP_SELECT_A:
				// FIXME: twoByteEscape?
				insn->opcodeType = XOPA_MAP;
				return consumeByte(insn, &insn->opcode);
		}
	}

	if (consumeByte(insn, &current))
		return -1;

	// save this first byte for MOVcr, MOVdr, MOVrc, MOVrd
	insn->firstByte = current;

	if (current == 0x0f) {
		// dbgprintf(insn, "Found a two-byte escape prefix (0x%hhx)", current);

		insn->twoByteEscape = current;

		if (consumeByte(insn, &current))
			return -1;

		if (current == 0x38) {
			// dbgprintf(insn, "Found a three-byte escape prefix (0x%hhx)", current);

			insn->threeByteEscape = current;

			if (consumeByte(insn, &current))
				return -1;

			insn->opcodeType = THREEBYTE_38;
		} else if (current == 0x3a) {
			// dbgprintf(insn, "Found a three-byte escape prefix (0x%hhx)", current);

			insn->threeByteEscape = current;

			if (consumeByte(insn, &current))
				return -1;

			insn->opcodeType = THREEBYTE_3A;
		} else {
#ifndef CAPSTONE_X86_REDUCE
			switch(current) {
				default:
					// dbgprintf(insn, "Didn't find a three-byte escape prefix");
					insn->opcodeType = TWOBYTE;
					break;
				case 0x0e:	// HACK for femms. to be handled properly in next version 3.x
					insn->opcodeType = T3DNOW_MAP;
					// this encode does not have ModRM
					insn->consumedModRM = true;
					break;
				case 0x0f:
					// 3DNow instruction has weird format: ModRM/SIB/displacement + opcode
					if (readModRM(insn))
						return -1;
					// next is 3DNow opcode
					if (consumeByte(insn, &current))
						return -1;
					insn->opcodeType = T3DNOW_MAP;
					break;
			}
#endif
		}
	}

	/*
	 * At this point we have consumed the full opcode.
	 * Anything we consume from here on must be unconsumed.
	 */

	insn->opcode = current;

	return 0;
}

// Hacky for FEMMS
#define GET_INSTRINFO_ENUM
#ifndef CAPSTONE_X86_REDUCE
#include "X86GenInstrInfo.inc"
#else
#include "X86GenInstrInfo_reduce.inc"
#endif

/*
 * getIDWithAttrMask - Determines the ID of an instruction, consuming
 *   the ModR/M byte as appropriate for extended and escape opcodes,
 *   and using a supplied attribute mask.
 *
 * @param instructionID - A pointer whose target is filled in with the ID of the
 *                        instruction.
 * @param insn          - The instruction whose ID is to be determined.
 * @param attrMask      - The attribute mask to search.
 * @return              - 0 if the ModR/M could be read when needed or was not
 *                        needed; nonzero otherwise.
 */
static int getIDWithAttrMask(uint16_t *instructionID,
		struct InternalInstruction *insn,
		uint16_t attrMask)
{
	bool hasModRMExtension;

	InstructionContext instructionClass;

#ifndef CAPSTONE_X86_REDUCE
	// HACK for femms. to be handled properly in next version 3.x
	if (insn->opcode == 0x0e && insn->opcodeType == T3DNOW_MAP) {
		*instructionID = X86_FEMMS;
		return 0;
	}
#endif

	if (insn->opcodeType == T3DNOW_MAP)
		instructionClass = IC_OF;
	else
		instructionClass = contextForAttrs(attrMask);

	hasModRMExtension = modRMRequired(insn->opcodeType,
			instructionClass,
			insn->opcode) != 0;

	if (hasModRMExtension) {
		if (readModRM(insn))
			return -1;

		*instructionID = decode(insn->opcodeType,
				instructionClass,
				insn->opcode,
				insn->modRM);
	} else {
		*instructionID = decode(insn->opcodeType,
				instructionClass,
				insn->opcode,
				0);
	}

	return 0;
}

/*
 * is16BitEquivalent - Determines whether two instruction names refer to
 * equivalent instructions but one is 16-bit whereas the other is not.
 *
 * @param orig  - The instruction ID that is not 16-bit
 * @param equiv - The instruction ID that is 16-bit
 */
static bool is16BitEquivalent(unsigned orig, unsigned equiv)
{
	size_t i;
	uint16_t idx;

	if ((idx = x86_16_bit_eq_lookup[orig]) != 0) {
		for (i = idx - 1; i < ARR_SIZE(x86_16_bit_eq_tbl) && x86_16_bit_eq_tbl[i].first == orig; i++) {
			if (x86_16_bit_eq_tbl[i].second == equiv)
				return true;
		}
	}

	return false;
}

/*
 * is64Bit - Determines whether this instruction is a 64-bit instruction.
 *
 * @param name - The instruction that is not 16-bit
 */
static bool is64Bit(uint16_t id)
{
	return is_64bit_insn[id];
}

/*
 * getID - Determines the ID of an instruction, consuming the ModR/M byte as
 *   appropriate for extended and escape opcodes.  Determines the attributes and
 *   context for the instruction before doing so.
 *
 * @param insn  - The instruction whose ID is to be determined.
 * @return      - 0 if the ModR/M could be read when needed or was not needed;
 *                nonzero otherwise.
 */
static int getID(struct InternalInstruction *insn)
{
	uint16_t attrMask;
	uint16_t instructionID;

	// printf(">>> getID()\n");
	attrMask = ATTR_NONE;

	if (insn->mode == MODE_64BIT)
		attrMask |= ATTR_64BIT;

	if (insn->vectorExtensionType != TYPE_NO_VEX_XOP) {
		attrMask |= (insn->vectorExtensionType == TYPE_EVEX) ? ATTR_EVEX : ATTR_VEX;

		if (insn->vectorExtensionType == TYPE_EVEX) {
			switch (ppFromEVEX3of4(insn->vectorExtensionPrefix[2])) {
				case VEX_PREFIX_66:
					attrMask |= ATTR_OPSIZE;
					break;
				case VEX_PREFIX_F3:
					attrMask |= ATTR_XS;
					break;
				case VEX_PREFIX_F2:
					attrMask |= ATTR_XD;
					break;
			}

			if (zFromEVEX4of4(insn->vectorExtensionPrefix[3]))
				attrMask |= ATTR_EVEXKZ;
			if (bFromEVEX4of4(insn->vectorExtensionPrefix[3]))
				attrMask |= ATTR_EVEXB;
			if (aaaFromEVEX4of4(insn->vectorExtensionPrefix[3]))
				attrMask |= ATTR_EVEXK;
			if (lFromEVEX4of4(insn->vectorExtensionPrefix[3]))
				attrMask |= ATTR_EVEXL;
			if (l2FromEVEX4of4(insn->vectorExtensionPrefix[3]))
				attrMask |= ATTR_EVEXL2;
		} else if (insn->vectorExtensionType == TYPE_VEX_3B) {
			switch (ppFromVEX3of3(insn->vectorExtensionPrefix[2])) {
				case VEX_PREFIX_66:
					attrMask |= ATTR_OPSIZE;
					break;
				case VEX_PREFIX_F3:
					attrMask |= ATTR_XS;
					break;
				case VEX_PREFIX_F2:
					attrMask |= ATTR_XD;
					break;
			}

			if (lFromVEX3of3(insn->vectorExtensionPrefix[2]))
				attrMask |= ATTR_VEXL;
		} else if (insn->vectorExtensionType == TYPE_VEX_2B) {
			switch (ppFromVEX2of2(insn->vectorExtensionPrefix[1])) {
				case VEX_PREFIX_66:
					attrMask |= ATTR_OPSIZE;
					break;
				case VEX_PREFIX_F3:
					attrMask |= ATTR_XS;
					break;
				case VEX_PREFIX_F2:
					attrMask |= ATTR_XD;
					break;
			}

			if (lFromVEX2of2(insn->vectorExtensionPrefix[1]))
				attrMask |= ATTR_VEXL;
		} else if (insn->vectorExtensionType == TYPE_XOP) {
			switch (ppFromXOP3of3(insn->vectorExtensionPrefix[2])) {
				case VEX_PREFIX_66:
					attrMask |= ATTR_OPSIZE;
					break;
				case VEX_PREFIX_F3:
					attrMask |= ATTR_XS;
					break;
				case VEX_PREFIX_F2:
					attrMask |= ATTR_XD;
					break;
			}

			if (lFromXOP3of3(insn->vectorExtensionPrefix[2]))
				attrMask |= ATTR_VEXL;
		} else {
			return -1;
		}
	} else {
		if (insn->mode != MODE_16BIT && isPrefixAtLocation(insn, 0x66, insn->necessaryPrefixLocation)) {
			attrMask |= ATTR_OPSIZE;
		} else if (isPrefixAtLocation(insn, 0x67, insn->necessaryPrefixLocation)) {
			attrMask |= ATTR_ADSIZE;
		} else if (isPrefixAtLocation(insn, 0xf3, insn->necessaryPrefixLocation)) {
			attrMask |= ATTR_XS;
		} else if (isPrefixAtLocation(insn, 0xf2, insn->necessaryPrefixLocation)) {
			attrMask |= ATTR_XD;
		}
	}

	if (insn->rexPrefix & 0x08)
		attrMask |= ATTR_REXW;

	/*
	 * JCXZ/JECXZ need special handling for 16-bit mode because the meaning
	 * of the AdSize prefix is inverted w.r.t. 32-bit mode.
	 */
	if (insn->mode == MODE_16BIT && insn->opcodeType == ONEBYTE &&
			insn->opcode == 0xE3)
		attrMask ^= ATTR_ADSIZE;

	if (getIDWithAttrMask(&instructionID, insn, attrMask))
		return -1;

	/* The following clauses compensate for limitations of the tables. */
	if (insn->mode != MODE_64BIT &&
			insn->vectorExtensionType != TYPE_NO_VEX_XOP) {
		/*
		 * The tables can't distinquish between cases where the W-bit is used to
		 * select register size and cases where its a required part of the opcode.
		 */
		if ((insn->vectorExtensionType == TYPE_EVEX &&
					wFromEVEX3of4(insn->vectorExtensionPrefix[2])) ||
				(insn->vectorExtensionType == TYPE_VEX_3B &&
				 wFromVEX3of3(insn->vectorExtensionPrefix[2])) ||
				(insn->vectorExtensionType == TYPE_XOP &&
				 wFromXOP3of3(insn->vectorExtensionPrefix[2]))) {
			uint16_t instructionIDWithREXW;
			if (getIDWithAttrMask(&instructionIDWithREXW,
						insn, attrMask | ATTR_REXW)) {
				insn->instructionID = instructionID;
				insn->spec = specifierForUID(instructionID);

				return 0;
			}

			// If not a 64-bit instruction. Switch the opcode.
			if (!is64Bit(instructionIDWithREXW)) {
				insn->instructionID = instructionIDWithREXW;
				insn->spec = specifierForUID(instructionIDWithREXW);

				return 0;
			}
		}
	}

	/*
	 * Absolute moves need special handling.
	 * -For 16-bit mode because the meaning of the AdSize and OpSize prefixes are
	 *  inverted w.r.t.
	 * -For 32-bit mode we need to ensure the ADSIZE prefix is observed in
	 *  any position.
	 */
	if (insn->opcodeType == ONEBYTE && ((insn->opcode & 0xFC) == 0xA0)) {
		/* Make sure we observed the prefixes in any position. */
		if (insn->isPrefix67)
			attrMask |= ATTR_ADSIZE;
		if (insn->isPrefix66)
			attrMask |= ATTR_OPSIZE;

		/* In 16-bit, invert the attributes. */
		if (insn->mode == MODE_16BIT)
			attrMask ^= ATTR_ADSIZE | ATTR_OPSIZE;

		if (getIDWithAttrMask(&instructionID, insn, attrMask))
			return -1;

		insn->instructionID = instructionID;
		insn->spec = specifierForUID(instructionID);

		return 0;
	}

	if ((insn->mode == MODE_16BIT || insn->isPrefix66) &&
			!(attrMask & ATTR_OPSIZE)) {
		/*
		 * The instruction tables make no distinction between instructions that
		 * allow OpSize anywhere (i.e., 16-bit operations) and that need it in a
		 * particular spot (i.e., many MMX operations).  In general we're
		 * conservative, but in the specific case where OpSize is present but not
		 * in the right place we check if there's a 16-bit operation.
		 */

		const struct InstructionSpecifier *spec;
		uint16_t instructionIDWithOpsize;

		spec = specifierForUID(instructionID);

		if (getIDWithAttrMask(&instructionIDWithOpsize,
					insn, attrMask | ATTR_OPSIZE)) {
			/*
			 * ModRM required with OpSize but not present; give up and return version
			 * without OpSize set
			 */

			insn->instructionID = instructionID;
			insn->spec = spec;
			return 0;
		}

		if (is16BitEquivalent(instructionID, instructionIDWithOpsize) &&
				(insn->mode == MODE_16BIT) ^ insn->isPrefix66) {
			insn->instructionID = instructionIDWithOpsize;
			insn->spec = specifierForUID(instructionIDWithOpsize);
		} else {
			insn->instructionID = instructionID;
			insn->spec = spec;
		}
		return 0;
	}

	if (insn->opcodeType == ONEBYTE && insn->opcode == 0x90 &&
			insn->rexPrefix & 0x01) {
		/*
		 * NOOP shouldn't decode as NOOP if REX.b is set. Instead
		 * it should decode as XCHG %r8, %eax.
		 */

		const struct InstructionSpecifier *spec;
		uint16_t instructionIDWithNewOpcode;
		const struct InstructionSpecifier *specWithNewOpcode;

		spec = specifierForUID(instructionID);

		/* Borrow opcode from one of the other XCHGar opcodes */
		insn->opcode = 0x91;

		if (getIDWithAttrMask(&instructionIDWithNewOpcode,
					insn,
					attrMask)) {
			insn->opcode = 0x90;

			insn->instructionID = instructionID;
			insn->spec = spec;
			return 0;
		}

		specWithNewOpcode = specifierForUID(instructionIDWithNewOpcode);

		/* Change back */
		insn->opcode = 0x90;

		insn->instructionID = instructionIDWithNewOpcode;
		insn->spec = specWithNewOpcode;

		return 0;
	}

	insn->instructionID = instructionID;
	insn->spec = specifierForUID(insn->instructionID);

	return 0;
}

/*
 * readSIB - Consumes the SIB byte to determine addressing information for an
 *   instruction.
 *
 * @param insn  - The instruction whose SIB byte is to be read.
 * @return      - 0 if the SIB byte was successfully read; nonzero otherwise.
 */
static int readSIB(struct InternalInstruction *insn)
{
	SIBIndex sibIndexBase = SIB_INDEX_NONE;
	SIBBase sibBaseBase = SIB_BASE_NONE;
	uint8_t index, base;

	// dbgprintf(insn, "readSIB()");

	if (insn->consumedSIB)
		return 0;

	insn->consumedSIB = true;

	switch (insn->addressSize) {
		case 2:
			// dbgprintf(insn, "SIB-based addressing doesn't work in 16-bit mode");
			return -1;
		case 4:
			sibIndexBase = SIB_INDEX_EAX;
			sibBaseBase = SIB_BASE_EAX;
			break;
		case 8:
			sibIndexBase = SIB_INDEX_RAX;
			sibBaseBase = SIB_BASE_RAX;
			break;
	}

	if (consumeByte(insn, &insn->sib))
		return -1;

	index = indexFromSIB(insn->sib) | (xFromREX(insn->rexPrefix) << 3);
	if (insn->vectorExtensionType == TYPE_EVEX)
		index |= v2FromEVEX4of4(insn->vectorExtensionPrefix[3]) << 4;

	switch (index) {
		case 0x4:
			insn->sibIndex = SIB_INDEX_NONE;
			break;
		default:
			insn->sibIndex = (SIBIndex)(sibIndexBase + index);
			if (insn->sibIndex == SIB_INDEX_sib ||
					insn->sibIndex == SIB_INDEX_sib64)
				insn->sibIndex = SIB_INDEX_NONE;
			break;
	}

	switch (scaleFromSIB(insn->sib)) {
		case 0:
			insn->sibScale = 1;
			break;
		case 1:
			insn->sibScale = 2;
			break;
		case 2:
			insn->sibScale = 4;
			break;
		case 3:
			insn->sibScale = 8;
			break;
	}

	base = baseFromSIB(insn->sib) | (bFromREX(insn->rexPrefix) << 3);

	switch (base) {
		case 0x5:
		case 0xd:
			switch (modFromModRM(insn->modRM)) {
				case 0x0:
					insn->eaDisplacement = EA_DISP_32;
					insn->sibBase = SIB_BASE_NONE;
					break;
				case 0x1:
					insn->eaDisplacement = EA_DISP_8;
					insn->sibBase = (SIBBase)(sibBaseBase + base);
					break;
				case 0x2:
					insn->eaDisplacement = EA_DISP_32;
					insn->sibBase = (SIBBase)(sibBaseBase + base);
					break;
				case 0x3:
					//debug("Cannot have Mod = 0b11 and a SIB byte");
					return -1;
			}
			break;
		default:
			insn->sibBase = (SIBBase)(sibBaseBase + base);
			break;
	}

	return 0;
}

/*
 * readDisplacement - Consumes the displacement of an instruction.
 *
 * @param insn  - The instruction whose displacement is to be read.
 * @return      - 0 if the displacement byte was successfully read; nonzero
 *                otherwise.
 */
static int readDisplacement(struct InternalInstruction *insn)
{
	int8_t d8;
	int16_t d16;
	int32_t d32;

	// dbgprintf(insn, "readDisplacement()");

	if (insn->consumedDisplacement)
		return 0;

	insn->consumedDisplacement = true;
	insn->displacementOffset = (uint8_t)(insn->readerCursor - insn->startLocation);

	switch (insn->eaDisplacement) {
		case EA_DISP_NONE:
			insn->consumedDisplacement = false;
			break;
		case EA_DISP_8:
			if (consumeInt8(insn, &d8))
				return -1;
			insn->displacement = d8;
			break;
		case EA_DISP_16:
			if (consumeInt16(insn, &d16))
				return -1;
			insn->displacement = d16;
			break;
		case EA_DISP_32:
			if (consumeInt32(insn, &d32))
				return -1;
			insn->displacement = d32;
			break;
	}

	insn->consumedDisplacement = true;
	return 0;
}

/*
 * readModRM - Consumes all addressing information (ModR/M byte, SIB byte, and
 *   displacement) for an instruction and interprets it.
 *
 * @param insn  - The instruction whose addressing information is to be read.
 * @return      - 0 if the information was successfully read; nonzero otherwise.
 */
static int readModRM(struct InternalInstruction *insn)
{
	uint8_t mod, rm, reg;

	// dbgprintf(insn, "readModRM()");

	// already got ModRM byte?
	if (insn->consumedModRM)
		return 0;

	if (consumeByte(insn, &insn->modRM))
		return -1;

	// mark that we already got ModRM
	insn->consumedModRM = true;

	// save original ModRM for later reference
	insn->orgModRM = insn->modRM;

	// handle MOVcr, MOVdr, MOVrc, MOVrd by pretending they have MRM.mod = 3
	if ((insn->firstByte == 0x0f && insn->opcodeType == TWOBYTE) &&
			(insn->opcode >= 0x20 && insn->opcode <= 0x23 ))
		insn->modRM |= 0xC0;

	mod     = modFromModRM(insn->modRM);
	rm      = rmFromModRM(insn->modRM);
	reg     = regFromModRM(insn->modRM);

	/*
	 * This goes by insn->registerSize to pick the correct register, which messes
	 * up if we're using (say) XMM or 8-bit register operands.  That gets fixed in
	 * fixupReg().
	 */
	switch (insn->registerSize) {
		case 2:
			insn->regBase = MODRM_REG_AX;
			insn->eaRegBase = EA_REG_AX;
			break;
		case 4:
			insn->regBase = MODRM_REG_EAX;
			insn->eaRegBase = EA_REG_EAX;
			break;
		case 8:
			insn->regBase = MODRM_REG_RAX;
			insn->eaRegBase = EA_REG_RAX;
			break;
	}

	reg |= rFromREX(insn->rexPrefix) << 3;
	rm  |= bFromREX(insn->rexPrefix) << 3;
	if (insn->vectorExtensionType == TYPE_EVEX) {
		reg |= r2FromEVEX2of4(insn->vectorExtensionPrefix[1]) << 4;
		rm  |=  xFromEVEX2of4(insn->vectorExtensionPrefix[1]) << 4;
	}

	insn->reg = (Reg)(insn->regBase + reg);

	switch (insn->addressSize) {
		case 2:
			insn->eaBaseBase = EA_BASE_BX_SI;

			switch (mod) {
				case 0x0:
					if (rm == 0x6) {
						insn->eaBase = EA_BASE_NONE;
						insn->eaDisplacement = EA_DISP_16;
						if (readDisplacement(insn))
							return -1;
					} else {
						insn->eaBase = (EABase)(insn->eaBaseBase + rm);
						insn->eaDisplacement = EA_DISP_NONE;
					}
					break;
				case 0x1:
					insn->eaBase = (EABase)(insn->eaBaseBase + rm);
					insn->eaDisplacement = EA_DISP_8;
					insn->displacementSize = 1;
					if (readDisplacement(insn))
						return -1;
					break;
				case 0x2:
					insn->eaBase = (EABase)(insn->eaBaseBase + rm);
					insn->eaDisplacement = EA_DISP_16;
					if (readDisplacement(insn))
						return -1;
					break;
				case 0x3:
					insn->eaBase = (EABase)(insn->eaRegBase + rm);
					if (readDisplacement(insn))
						return -1;
					break;
			}
			break;
		case 4:
		case 8:
			insn->eaBaseBase = (insn->addressSize == 4 ? EA_BASE_EAX : EA_BASE_RAX);

			switch (mod) {
				case 0x0:
					insn->eaDisplacement = EA_DISP_NONE; /* readSIB may override this */
					switch (rm) {
						case 0x14:
						case 0x4:
						case 0xc:   /* in case REXW.b is set */
							insn->eaBase = (insn->addressSize == 4 ?
									EA_BASE_sib : EA_BASE_sib64);
							if (readSIB(insn) || readDisplacement(insn))
								return -1;
							break;
						case 0x5:
						case 0xd:
							insn->eaBase = EA_BASE_NONE;
							insn->eaDisplacement = EA_DISP_32;
							if (readDisplacement(insn))
								return -1;
							break;
						default:
							insn->eaBase = (EABase)(insn->eaBaseBase + rm);
							break;
					}

					break;
				case 0x1:
					insn->displacementSize = 1;
					/* FALLTHROUGH */
				case 0x2:
					insn->eaDisplacement = (mod == 0x1 ? EA_DISP_8 : EA_DISP_32);
					switch (rm) {
						case 0x14:
						case 0x4:
						case 0xc:   /* in case REXW.b is set */
							insn->eaBase = EA_BASE_sib;
							if (readSIB(insn) || readDisplacement(insn))
								return -1;
							break;
						default:
							insn->eaBase = (EABase)(insn->eaBaseBase + rm);
							if (readDisplacement(insn))
								return -1;
							break;
					}
					break;
				case 0x3:
					insn->eaDisplacement = EA_DISP_NONE;
					insn->eaBase = (EABase)(insn->eaRegBase + rm);
					break;
			}
			break;
	} /* switch (insn->addressSize) */

	return 0;
}

#define GENERIC_FIXUP_FUNC(name, base, prefix)            \
  static uint8_t name(struct InternalInstruction *insn,   \
                      OperandType type,                   \
                      uint8_t index,                      \
                      uint8_t *valid) {                   \
    *valid = 1;                                           \
    switch (type) {                                       \
    default:                                              \
      *valid = 0;                                         \
      return 0;                                           \
    case TYPE_Rv:                                         \
      return base + index;                                \
    case TYPE_R8:                                         \
      if (insn->rexPrefix &&                              \
         index >= 4 && index <= 7) {                      \
        return prefix##_SPL + (index - 4);                \
      } else {                                            \
        return prefix##_AL + index;                       \
      }                                                   \
    case TYPE_R16:                                        \
      return prefix##_AX + index;                         \
    case TYPE_R32:                                        \
      return prefix##_EAX + index;                        \
    case TYPE_R64:                                        \
      return prefix##_RAX + index;                        \
    case TYPE_XMM512:                                     \
      return prefix##_ZMM0 + index;                       \
    case TYPE_XMM256:                                     \
      return prefix##_YMM0 + index;                       \
    case TYPE_XMM128:                                     \
    case TYPE_XMM64:                                      \
    case TYPE_XMM32:                                      \
    case TYPE_XMM:                                        \
      return prefix##_XMM0 + index;                       \
    case TYPE_VK1:                                        \
    case TYPE_VK8:                                        \
    case TYPE_VK16:                                       \
      if (index > 7)                                      \
        *valid = 0;                                       \
      return prefix##_K0 + index;                         \
    case TYPE_MM64:                                       \
      return prefix##_MM0 + (index & 0x7);                \
    case TYPE_SEGMENTREG:                                 \
      if (index > 5)                                      \
        *valid = 0;                                       \
      return prefix##_ES + index;                         \
    case TYPE_DEBUGREG:                                   \
      return prefix##_DR0 + index;                        \
    case TYPE_CONTROLREG:                                 \
      return prefix##_CR0 + index;                        \
    }                                                     \
  }


/*
 * fixup*Value - Consults an operand type to determine the meaning of the
 *   reg or R/M field.  If the operand is an XMM operand, for example, an
 *   operand would be XMM0 instead of AX, which readModRM() would otherwise
 *   misinterpret it as.
 *
 * @param insn  - The instruction containing the operand.
 * @param type  - The operand type.
 * @param index - The existing value of the field as reported by readModRM().
 * @param valid - The address of a uint8_t.  The target is set to 1 if the
 *                field is valid for the register class; 0 if not.
 * @return      - The proper value.
 */
GENERIC_FIXUP_FUNC(fixupRegValue, insn->regBase,    MODRM_REG)
GENERIC_FIXUP_FUNC(fixupRMValue,  insn->eaRegBase,  EA_REG)

/*
 * fixupReg - Consults an operand specifier to determine which of the
 *   fixup*Value functions to use in correcting readModRM()'ss interpretation.
 *
 * @param insn  - See fixup*Value().
 * @param op    - The operand specifier.
 * @return      - 0 if fixup was successful; -1 if the register returned was
 *                invalid for its class.
 */
static int fixupReg(struct InternalInstruction *insn,
		const struct OperandSpecifier *op)
{
	uint8_t valid;

	// dbgprintf(insn, "fixupReg()");

	switch ((OperandEncoding)op->encoding) {
		default:
			//debug("Expected a REG or R/M encoding in fixupReg");
			return -1;
		case ENCODING_VVVV:
			insn->vvvv = (Reg)fixupRegValue(insn,
					(OperandType)op->type,
					insn->vvvv,
					&valid);
			if (!valid)
				return -1;
			break;
		case ENCODING_REG:
			insn->reg = (Reg)fixupRegValue(insn,
					(OperandType)op->type,
					(uint8_t)(insn->reg - insn->regBase),
					&valid);
			if (!valid)
				return -1;
			break;
		CASE_ENCODING_RM:
			if (insn->eaBase >= insn->eaRegBase) {
				insn->eaBase = (EABase)fixupRMValue(insn,
						(OperandType)op->type,
						(uint8_t)(insn->eaBase - insn->eaRegBase),
						&valid);
				if (!valid)
					return -1;
			}
			break;
	}

	return 0;
}

/*
 * readOpcodeRegister - Reads an operand from the opcode field of an
 *   instruction and interprets it appropriately given the operand width.
 *   Handles AddRegFrm instructions.
 *
 * @param insn  - the instruction whose opcode field is to be read.
 * @param size  - The width (in bytes) of the register being specified.
 *                1 means AL and friends, 2 means AX, 4 means EAX, and 8 means
 *                RAX.
 * @return      - 0 on success; nonzero otherwise.
 */
static int readOpcodeRegister(struct InternalInstruction *insn, uint8_t size)
{
	// dbgprintf(insn, "readOpcodeRegister()");

	if (size == 0)
		size = insn->registerSize;

	insn->operandSize = size;

	switch (size) {
		case 1:
			insn->opcodeRegister = (Reg)(MODRM_REG_AL + ((bFromREX(insn->rexPrefix) << 3)
						| (insn->opcode & 7)));
			if (insn->rexPrefix &&
					insn->opcodeRegister >= MODRM_REG_AL + 0x4 &&
					insn->opcodeRegister < MODRM_REG_AL + 0x8) {
				insn->opcodeRegister = (Reg)(MODRM_REG_SPL
						+ (insn->opcodeRegister - MODRM_REG_AL - 4));
			}

			break;
		case 2:
			insn->opcodeRegister = (Reg)(MODRM_REG_AX
					+ ((bFromREX(insn->rexPrefix) << 3)
						| (insn->opcode & 7)));
			break;
		case 4:
			insn->opcodeRegister = (Reg)(MODRM_REG_EAX
					+ ((bFromREX(insn->rexPrefix) << 3)
						| (insn->opcode & 7)));
			break;
		case 8:
			insn->opcodeRegister = (Reg)(MODRM_REG_RAX
					+ ((bFromREX(insn->rexPrefix) << 3)
						| (insn->opcode & 7)));
			break;
	}

	return 0;
}

/*
 * readImmediate - Consumes an immediate operand from an instruction, given the
 *   desired operand size.
 *
 * @param insn  - The instruction whose operand is to be read.
 * @param size  - The width (in bytes) of the operand.
 * @return      - 0 if the immediate was successfully consumed; nonzero
 *                otherwise.
 */
static int readImmediate(struct InternalInstruction *insn, uint8_t size)
{
	uint8_t imm8;
	uint16_t imm16;
	uint32_t imm32;
	uint64_t imm64;

	// dbgprintf(insn, "readImmediate()");

	if (insn->numImmediatesConsumed == 2) {
		//debug("Already consumed two immediates");
		return -1;
	}

	if (size == 0)
		size = insn->immediateSize;
	else
		insn->immediateSize = size;
	insn->immediateOffset = (uint8_t)(insn->readerCursor - insn->startLocation);

	switch (size) {
		case 1:
			if (consumeByte(insn, &imm8))
				return -1;
			insn->immediates[insn->numImmediatesConsumed] = imm8;
			break;
		case 2:
			if (consumeUInt16(insn, &imm16))
				return -1;
			insn->immediates[insn->numImmediatesConsumed] = imm16;
			break;
		case 4:
			if (consumeUInt32(insn, &imm32))
				return -1;
			insn->immediates[insn->numImmediatesConsumed] = imm32;
			break;
		case 8:
			if (consumeUInt64(insn, &imm64))
				return -1;
			insn->immediates[insn->numImmediatesConsumed] = imm64;
			break;
	}

	insn->numImmediatesConsumed++;

	return 0;
}

/*
 * readVVVV - Consumes vvvv from an instruction if it has a VEX prefix.
 *
 * @param insn  - The instruction whose operand is to be read.
 * @return      - 0 if the vvvv was successfully consumed; nonzero
 *                otherwise.
 */
static int readVVVV(struct InternalInstruction *insn)
{
	int vvvv;
	// dbgprintf(insn, "readVVVV()");

	if (insn->vectorExtensionType == TYPE_EVEX)
		vvvv = (v2FromEVEX4of4(insn->vectorExtensionPrefix[3]) << 4 |
				vvvvFromEVEX3of4(insn->vectorExtensionPrefix[2]));
	else if (insn->vectorExtensionType == TYPE_VEX_3B)
		vvvv = vvvvFromVEX3of3(insn->vectorExtensionPrefix[2]);
	else if (insn->vectorExtensionType == TYPE_VEX_2B)
		vvvv = vvvvFromVEX2of2(insn->vectorExtensionPrefix[1]);
	else if (insn->vectorExtensionType == TYPE_XOP)
		vvvv = vvvvFromXOP3of3(insn->vectorExtensionPrefix[2]);
	else
		return -1;

	if (insn->mode != MODE_64BIT)
		vvvv &= 0x7;

	insn->vvvv = vvvv;

	return 0;
}

/*
 * readMaskRegister - Reads an mask register from the opcode field of an
 *   instruction.
 *
 * @param insn    - The instruction whose opcode field is to be read.
 * @return        - 0 on success; nonzero otherwise.
 */
static int readMaskRegister(struct InternalInstruction *insn)
{
	// dbgprintf(insn, "readMaskRegister()");

	if (insn->vectorExtensionType != TYPE_EVEX)
		return -1;

	insn->writemask = aaaFromEVEX4of4(insn->vectorExtensionPrefix[3]);

	return 0;
}

/*
 * readOperands - Consults the specifier for an instruction and consumes all
 *   operands for that instruction, interpreting them as it goes.
 *
 * @param insn  - The instruction whose operands are to be read and interpreted.
 * @return      - 0 if all operands could be read; nonzero otherwise.
 */
static int readOperands(struct InternalInstruction *insn)
{
	int index;
	int hasVVVV, needVVVV;
	int sawRegImm = 0;

	// printf(">>> readOperands(): ID = %u\n", insn->instructionID);
	/* If non-zero vvvv specified, need to make sure one of the operands
	   uses it. */
	hasVVVV = !readVVVV(insn);
	needVVVV = hasVVVV && (insn->vvvv != 0);

	for (index = 0; index < X86_MAX_OPERANDS; ++index) {
		//printf(">>> encoding[%u] = %u\n", index, x86OperandSets[insn->spec->operands][index].encoding);
		switch (x86OperandSets[insn->spec->operands][index].encoding) {
			case ENCODING_NONE:
			case ENCODING_SI:
			case ENCODING_DI:
				break;
			case ENCODING_REG:
			CASE_ENCODING_RM:
				if (readModRM(insn))
					return -1;
				if (fixupReg(insn, &x86OperandSets[insn->spec->operands][index]))
					return -1;
				// Apply the AVX512 compressed displacement scaling factor.
				if (x86OperandSets[insn->spec->operands][index].encoding != ENCODING_REG && insn->eaDisplacement == EA_DISP_8)
					insn->displacement *= 1 << (x86OperandSets[insn->spec->operands][index].encoding - ENCODING_RM);
				break;
			case ENCODING_CB:
			case ENCODING_CW:
			case ENCODING_CD:
			case ENCODING_CP:
			case ENCODING_CO:
			case ENCODING_CT:
				// dbgprintf(insn, "We currently don't hande code-offset encodings");
				return -1;
			case ENCODING_IB:
				if (sawRegImm) {
					/* Saw a register immediate so don't read again and instead split the
					   previous immediate.  FIXME: This is a hack. */
					insn->immediates[insn->numImmediatesConsumed] =
						insn->immediates[insn->numImmediatesConsumed - 1] & 0xf;
					++insn->numImmediatesConsumed;
					break;
				}
				if (readImmediate(insn, 1))
					return -1;
				if (x86OperandSets[insn->spec->operands][index].type == TYPE_XMM128 ||
						x86OperandSets[insn->spec->operands][index].type == TYPE_XMM256)
					sawRegImm = 1;
				break;
			case ENCODING_IW:
				if (readImmediate(insn, 2))
					return -1;
				break;
			case ENCODING_ID:
				if (readImmediate(insn, 4))
					return -1;
				break;
			case ENCODING_IO:
				if (readImmediate(insn, 8))
					return -1;
				break;
			case ENCODING_Iv:
				if (readImmediate(insn, insn->immediateSize))
					return -1;
				break;
			case ENCODING_Ia:
				if (readImmediate(insn, insn->addressSize))
					return -1;
				break;
			case ENCODING_RB:
				if (readOpcodeRegister(insn, 1))
					return -1;
				break;
			case ENCODING_RW:
				if (readOpcodeRegister(insn, 2))
					return -1;
				break;
			case ENCODING_RD:
				if (readOpcodeRegister(insn, 4))
					return -1;
				break;
			case ENCODING_RO:
				if (readOpcodeRegister(insn, 8))
					return -1;
				break;
			case ENCODING_Rv:
				if (readOpcodeRegister(insn, 0))
					return -1;
				break;
			case ENCODING_FP:
				break;
			case ENCODING_VVVV:
				needVVVV = 0; /* Mark that we have found a VVVV operand. */
				if (!hasVVVV)
					return -1;
				if (fixupReg(insn, &x86OperandSets[insn->spec->operands][index]))
					return -1;
				break;
			case ENCODING_WRITEMASK:
				if (readMaskRegister(insn))
					return -1;
				break;
			case ENCODING_DUP:
				break;
			default:
				// dbgprintf(insn, "Encountered an operand with an unknown encoding.");
				return -1;
		}
	}

	/* If we didn't find ENCODING_VVVV operand, but non-zero vvvv present, fail */
	if (needVVVV) return -1;

	return 0;
}

// return True if instruction is illegal to use with prefixes
// This also check & fix the isPrefixNN when a prefix is irrelevant.
static bool checkPrefix(struct InternalInstruction *insn)
{
	// LOCK prefix
	if (insn->isPrefixf0) {
		switch(insn->instructionID) {
			default:
				// invalid LOCK
				return true;

			// DEC
			case X86_DEC16m:
			case X86_DEC32m:
			case X86_DEC64m:
			case X86_DEC8m:

			// ADC
			case X86_ADC16mi:
			case X86_ADC16mi8:
			case X86_ADC16mr:
			case X86_ADC32mi:
			case X86_ADC32mi8:
			case X86_ADC32mr:
			case X86_ADC64mi32:
			case X86_ADC64mi8:
			case X86_ADC64mr:
			case X86_ADC8mi:
			case X86_ADC8mi8:
			case X86_ADC8mr:

			// ADD
			case X86_ADD16mi:
			case X86_ADD16mi8:
			case X86_ADD16mr:
			case X86_ADD32mi:
			case X86_ADD32mi8:
			case X86_ADD32mr:
			case X86_ADD64mi32:
			case X86_ADD64mi8:
			case X86_ADD64mr:
			case X86_ADD8mi:
			case X86_ADD8mi8:
			case X86_ADD8mr:

			// AND
			case X86_AND16mi:
			case X86_AND16mi8:
			case X86_AND16mr:
			case X86_AND32mi:
			case X86_AND32mi8:
			case X86_AND32mr:
			case X86_AND64mi32:
			case X86_AND64mi8:
			case X86_AND64mr:
			case X86_AND8mi:
			case X86_AND8mi8:
			case X86_AND8mr:

			// BTC
			case X86_BTC16mi8:
			case X86_BTC16mr:
			case X86_BTC32mi8:
			case X86_BTC32mr:
			case X86_BTC64mi8:
			case X86_BTC64mr:

			// BTR
			case X86_BTR16mi8:
			case X86_BTR16mr:
			case X86_BTR32mi8:
			case X86_BTR32mr:
			case X86_BTR64mi8:
			case X86_BTR64mr:

			// BTS
			case X86_BTS16mi8:
			case X86_BTS16mr:
			case X86_BTS32mi8:
			case X86_BTS32mr:
			case X86_BTS64mi8:
			case X86_BTS64mr:

			// CMPXCHG
			case X86_CMPXCHG16B:
			case X86_CMPXCHG16rm:
			case X86_CMPXCHG32rm:
			case X86_CMPXCHG64rm:
			case X86_CMPXCHG8rm:
			case X86_CMPXCHG8B:

			// INC
			case X86_INC16m:
			case X86_INC32m:
			case X86_INC64m:
			case X86_INC8m:

			// NEG
			case X86_NEG16m:
			case X86_NEG32m:
			case X86_NEG64m:
			case X86_NEG8m:

			// NOT
			case X86_NOT16m:
			case X86_NOT32m:
			case X86_NOT64m:
			case X86_NOT8m:

			// OR
			case X86_OR16mi:
			case X86_OR16mi8:
			case X86_OR16mr:
			case X86_OR32mi:
			case X86_OR32mi8:
			case X86_OR32mr:
			case X86_OR32mrLocked:
			case X86_OR64mi32:
			case X86_OR64mi8:
			case X86_OR64mr:
			case X86_OR8mi8:
			case X86_OR8mi:
			case X86_OR8mr:

			// SBB
			case X86_SBB16mi:
			case X86_SBB16mi8:
			case X86_SBB16mr:
			case X86_SBB32mi:
			case X86_SBB32mi8:
			case X86_SBB32mr:
			case X86_SBB64mi32:
			case X86_SBB64mi8:
			case X86_SBB64mr:
			case X86_SBB8mi:
			case X86_SBB8mi8:
			case X86_SBB8mr:

			// SUB
			case X86_SUB16mi:
			case X86_SUB16mi8:
			case X86_SUB16mr:
			case X86_SUB32mi:
			case X86_SUB32mi8:
			case X86_SUB32mr:
			case X86_SUB64mi32:
			case X86_SUB64mi8:
			case X86_SUB64mr:
			case X86_SUB8mi8:
			case X86_SUB8mi:
			case X86_SUB8mr:

			// XADD
			case X86_XADD16rm:
			case X86_XADD32rm:
			case X86_XADD64rm:
			case X86_XADD8rm:

			// XCHG
			case X86_XCHG16rm:
			case X86_XCHG32rm:
			case X86_XCHG64rm:
			case X86_XCHG8rm:

			// XOR
			case X86_XOR16mi:
			case X86_XOR16mi8:
			case X86_XOR16mr:
			case X86_XOR32mi:
			case X86_XOR32mi8:
			case X86_XOR32mr:
			case X86_XOR64mi32:
			case X86_XOR64mi8:
			case X86_XOR64mr:
			case X86_XOR8mi8:
			case X86_XOR8mi:
			case X86_XOR8mr:

				// this instruction can be used with LOCK prefix
				return false;
		}
	}

	// REPNE prefix
	if (insn->isPrefixf2) {
		// 0xf2 can be a part of instruction encoding, but not really a prefix.
		// In such a case, clear it.
		if (insn->twoByteEscape == 0x0f) {
			insn->prefix0 = 0;
		}
	}

	// no invalid prefixes
	return false;
}

/*
 * decodeInstruction - Reads and interprets a full instruction provided by the
 *   user.
 *
 * @param insn      - A pointer to the instruction to be populated.  Must be
 *                    pre-allocated.
 * @param reader    - The function to be used to read the instruction's bytes.
 * @param readerArg - A generic argument to be passed to the reader to store
 *                    any internal state.
 * @param startLoc  - The address (in the reader's address space) of the first
 *                    byte in the instruction.
 * @param mode      - The mode (real mode, IA-32e, or IA-32e in 64-bit mode) to
 *                    decode the instruction in.
 * @return          - 0 if instruction is valid; nonzero if not.
 */
int decodeInstruction(struct InternalInstruction *insn,
		byteReader_t reader,
		const void *readerArg,
		uint64_t startLoc,
		DisassemblerMode mode)
{
	insn->reader = reader;
	insn->readerArg = readerArg;
	insn->startLocation = startLoc;
	insn->readerCursor = startLoc;
	insn->mode = mode;

	if (readPrefixes(insn)       ||
			readOpcode(insn)         ||
			getID(insn)      ||
			insn->instructionID == 0 ||
			checkPrefix(insn) ||
			readOperands(insn))
		return -1;

	insn->length = (size_t)(insn->readerCursor - insn->startLocation);

	// instruction length must be <= 15 to be valid
	if (insn->length > 15)
		return -1;

	if (insn->operandSize == 0)
		insn->operandSize = insn->registerSize;

	insn->operands = &x86OperandSets[insn->spec->operands][0];

	// dbgprintf(insn, "Read from 0x%llx to 0x%llx: length %zu",
	// 		startLoc, insn->readerCursor, insn->length);

	//if (insn->length > 15)
	//	dbgprintf(insn, "Instruction exceeds 15-byte limit");

#if 0
	printf("\n>>> x86OperandSets = %lu\n", sizeof(x86OperandSets));
	printf(">>> x86DisassemblerInstrSpecifiers = %lu\n", sizeof(x86DisassemblerInstrSpecifiers));
	printf(">>> x86DisassemblerContexts = %lu\n", sizeof(x86DisassemblerContexts));
	printf(">>> modRMTable = %lu\n", sizeof(modRMTable));
	printf(">>> x86DisassemblerOneByteOpcodes = %lu\n", sizeof(x86DisassemblerOneByteOpcodes));
	printf(">>> x86DisassemblerTwoByteOpcodes = %lu\n", sizeof(x86DisassemblerTwoByteOpcodes));
	printf(">>> x86DisassemblerThreeByte38Opcodes = %lu\n", sizeof(x86DisassemblerThreeByte38Opcodes));
	printf(">>> x86DisassemblerThreeByte3AOpcodes = %lu\n", sizeof(x86DisassemblerThreeByte3AOpcodes));
	printf(">>> x86DisassemblerThreeByteA6Opcodes = %lu\n", sizeof(x86DisassemblerThreeByteA6Opcodes));
	printf(">>> x86DisassemblerThreeByteA7Opcodes= %lu\n", sizeof(x86DisassemblerThreeByteA7Opcodes));
	printf(">>> x86DisassemblerXOP8Opcodes = %lu\n", sizeof(x86DisassemblerXOP8Opcodes));
	printf(">>> x86DisassemblerXOP9Opcodes = %lu\n", sizeof(x86DisassemblerXOP9Opcodes));
	printf(">>> x86DisassemblerXOPAOpcodes = %lu\n\n", sizeof(x86DisassemblerXOPAOpcodes));
#endif

	return 0;
}

#endif
