1. 11

  2. 5

    Fun facts:

    • All instructions use modrm encoding for encoding memory operands, except for A0/A1/A2/A3, where the address is a constant encoded immediately after the instruction (“moffs”).
    • x86 has a single-byte encoding for INC esp (increment stack pointer by one).
    • x86 has a single-byte encoding for BCD-arithmetic. For example: AAA - ASCII Adjust After Addition.
    • POP [ptr] (pop a dword from the stack and move it to the specified address in memory) updates esp before resolving ptr (which can contain esp). In some sense it mixes decoding of the instruction and execution.
    • LEA reg, [ptr] is an instruction that computes ptr and stores it in a register without referencing memory. Pointer arithmetic is very flexible in x86, being able to add a register with a shift, another register and a constant offset. For example, it can encode a = b + c -1 in a single instruction. LEA is also the only instruction that fails when encoded with a register operand (because LEA reg1, reg2 is invalid) but never fails when encoded with a memory operand.
    • There are two ways to encode OP reg1, reg2 for most instructions.
    • XCHG eax, r is encoded as 0x90+r, NOP is 0x90 or XCHG eax, eax.
    • Most arithmetic instructions also compute the parity flag, which is the parity of the lowest byte of the result.
    • Most arithmetic instructions also compute the adjust flag, which is set when an overflow happens from the 4th bit of the result.
    • Due to a bug in Windows NT, CPUID reports some bits differently depending configuration registers. Search for “bug” in http://sandpile.org/x86/cpuid.htm.
    1. 2

      NOP hasn’t been XCHG EAX,EAX since the 80386—it causes an unnecessary dependency on EAX so it’s been special coded for quite a long time.