The x86 instruction set refers to the set of instructions that x86-compatible microprocessors support. The instructions are usually part of an executable program, often stored as a computer file and executed on the processor.
The x86 instruction set has been extended several times, introducing wider registers and datatypes as well as new functionality.
x86 integer instructions
Below is the full 8086/8088 instruction set of Intel (81 instructions total). These instructions are also available in 32-bit mode, in which they operate on 32-bit registers (eax, ebx, etc.) and values instead of their 16-bit (ax, bx, etc.) counterparts. The updated instruction set is grouped according to architecture (i186, i286, i386, i486, i586/i686) and is referred to as (32-bit) x86 and (64-bit) x86-64 (also known as AMD64).
Original 8086/8088 instructions
This is the original instruction set. In the 'Notes' column, r means register, m means memory address and imm means immediate (i.e. a value).
+ Original 8086/8088 instruction set In-struc-tion Meaning Notes Opcode ASCII adjust AL after addition used with unpacked binary-coded decimal ASCII adjust AX before division 8086/8088 datasheet documents only base 10 version of the AAD instruction (opcode ), but any other base will work. Later Intel's documentation has the generic form too. NEC V20 and V30 (and possibly other NEC V-series CPUs) always use base 10, and ignore the argument, causing a number of incompatibilities ASCII adjust AX after multiplication Only base 10 version (Operand is 0xA) is documented, see notes for AAD ASCII adjust AL after subtraction Add with carry (1) r += (r/m/imm+CF); (2) m += (r/imm+CF); ..., ..., Add (1) r += r/m/imm; (2) m += r/imm; ..., ..., Logical AND (1) r &= r/m/imm; (2) m &= r/imm; ..., ..., Call procedure (1) push IP, jmp within segment; (2) push CS:IP, jump intersegment , , , Convert byte to word AH = (sign)AL Clear carry flag CF = 0; Clear direction flag DF = 0; Clear interrupt flag IF = 0; Complement carry flag CF = !CF; Compare operands (1) r - r/m/imm; (2) m - r/imm; ..., ..., Compare bytes in memory. May be used with a or prefix to test and repeat the instruction times. Compare words. May be used with a or prefix to test and repeat the instruction times. Convert word to doubleword DX = (sign)AX Decimal adjust AL after addition (used with packed BCD) Decimal adjust AL after subtraction (used with packed BCD) Decrement by 1 ..., , Unsigned divide (1) AX = DX:AX / r/m; DX = remainder (2) AL = AX / r/m;] AH = remainder , Used with floating-point unit .. Enter halt state Signed divide (1) AX = DX:AX / r/m; DX = remainder (2) AL = AX / r/m; AH = remainder , Signed multiply in One-operand form (1) DX:AX = AX * r/m; (2) AX = AL * r/m , Input from port (1) AL = port[imm]; (2) AL = port[DX]; (3) AX = port[imm]; (4) AX = port[DX]; , , , Increment by 1 ..., , Call to interrupt *--SP = FLAGS; *--SP = CS; *--SP = IP , Call to interrupt if overflow if (O == 1) *--SP = FLAGS; *--SP = CS; *--SP = IP Return from interrupt IP = *SP++, CS = *SP++, FLAGS = *SP++; Jump if condition . ... Jump if CX is zero for ECX instead of CX in 32 bit mode (same opcode). Jump (1) jump within segment; (2) jump intersegment ..., , Load FLAGS into AH register Load DS:r with far pointer r = m; DS = 2 + m; Load Effective Address Load ES:r with far pointer r = m; ES = 2 + m; Assert BUS LOCK# signal (for multiprocessing) Load string byte. May be used with a prefix to repeat the instruction times. Load string word. May be used with a prefix to repeat the instruction times. / Loop control () ... Move (1) r = r/m/imm; (2) m = r/imm; (3) r/m = sreg; (4) sreg = r/m; ..., , ..., ..., , Move byte from string to string. May be used with a prefix to repeat the instruction times. . Move word from string to string. May be used with a prefix to repeat the instruction times. Unsigned multiply (1) DX:AX = AX * r/m; (2) AX = AL * r/m; , Two's complement negation ... No operation opcode equivalent to Negate the operand, logical NOT ... Logical OR (1) r ∣= r/m/imm; (2) m ∣= r/imm; ..., ..., Output to port (1) port[imm] = AL; (2) port[DX] = AL; (3) port[imm] = AX; (4) port[DX] = AX; , , , Pop data from stack r/m/sreg = *SP++; , , , ..., Pop FLAGS register from stack FLAGS = *SP++; Push data onto stack , , , , ..., Push FLAGS onto stack Rotate left (with carry) ... (186+), ... Rotate right (with carry) ... (186+), ... Repeat MOVS/STOS/CMPS/LODS/SCAS () , Return from procedure Not a real instruction. The assembler will translate these to a RETN or a RETF depending on the memory model of the target system. Return from near procedure , Return from far procedure , Rotate left ... (186+), ... Rotate right ... (186+), ... Store AH into FLAGS Shift Arithmetically left (signed shift left) (1) r/m <<= 1; (2) r/m <<= CL; ... (186+), ... Shift Arithmetically right (signed shift right) (1) (signed) r/m >>= 1; (2) (signed) r/m >>= CL; ... (186+), ... Subtraction with borrow (1) r -= (r/m/imm+CF); (2) m -= (r/imm+CF); alternative 1-byte encoding of is available via undocumented SALC instruction ..., ..., Compare byte string. May be used with a or prefix to test and repeat the instruction times. Compare word string. May be used with a or prefix to test and repeat the instruction times. Shift left (unsigned shift left) Same opcode as SAL, since logical left shifts are equal to arithmetical left shifts. ... (186+), ... Shift right (unsigned shift right) ... (186+), ... Set carry flag CF = 1; Set direction flag DF = 1; Set interrupt flag IF = 1; Store byte in string. May be used with a prefix to repeat the instruction times. Store word in string. May be used with a prefix to repeat the instruction times. Subtraction (1) r -= r/m/imm; (2) m -= r/imm; ..., ..., Logical compare (AND) (1) r & r/m/imm; (2) m & r/imm; , , , , , Wait until not busy Waits until BUSY# pin is inactive (used with floating-point unit) Exchange data A spinlock typically uses xchg as an atomic operation. (coma bug). , , ... Table look-up translation behaves like Exclusive OR (1) r ^+= r/m/imm; (2) m ^= r/imm; ..., ...,
Added in specific processors
Added with 80186/80188 New instructions and instruction forms added in the Intel 80186 and 80188. Also present in the NEC V20/V30 processors and their successors.
Instruction mnemonic Opcode Instruction description Ring PUSHA 60 Push all general purpose registers onto the stack.
Pushes AX,CX,DX,BX,SP,BP,SI,DI onto the stack in that order. The value of SP pushed onto the stack is the initial value of SP before the PUSHA instruction. rowspan=3 POPA 61 Pop all general purpose registers from stack. The registers are popped from the stack into registers in the reverse order of that of PUSHA (the popped item that corresponds to the SP register is popped but not put in any register.) BOUND reg,m16&16 Read a pair of signed array bounds from memory, then check that the register-argument is neither below the first bound nor above the second bound.
If either test fails, a bounds range-exceeded exception (#BR, interrupt vector 5) is raised. PUSH imm 68 iw Push an immediate word (or byte sign-extended to word) value onto the stack. Examples: PUSH 12h ; encoded as 6Ah 12h PUSH 1234h ; encoded as 68h 34h 12h rowspan=4 6A ib IMUL reg,r/m,imm, Non-widening 3-argument integer word multiply with immediate. Examples: IMUL CX, DX, 12h IMUL BX, SI, 1200h IMUL DI, word ptr [BX+SI], 12h IMUL SI, word ptr [BP-4], 1200h Note that since the lower half is the same for unsigned and signed multiplication, this version of the instruction can be used for both. INSB 6C 8-bit input from I/O port to string. Operation is equivalent to: IN AL, DX STOSB ; adjust DI according to operand size and DF rowspan=4 INSW 6D 16-bit input from I/O port to string. OUTSB 6E 8-bit output from string to I/O port. Operation is equivalent to: LODSB ; adjust SI according to operand size and DF OUT DX, AL OUTSW 6F 16-bit output from string to I/O port. ROL r/m, imm8 C0 /0 ib Rotate left immediate rowspan=8 ROR r/m, imm8 C0 /1 ib,C1 /1 ib Rotate right immediate RCL r/m, imm8 C0 /2 ib,C1 /2 ib Rotate left through carry with immediate rotate-amount RCR r/m, imm8 C0 /3 ib,C1 /3 ib Rotate right through carry with immediate rotate-amount SHL r/m, imm8 C0 /4 ib,C1 /4 ib Shift left immediate SHR r/m, imm8 C0 /5 ib,C1 /5 ib Unsigned shift right immediate SAR r/m, imm8 C0 /7 ib,C1 /7 ib Signed shift right immediate Create procedure stack frame. The first operand specifies the size of the stack frame to allocate by the instruction, the second operand specifies nesting level (the number of earlier stack frame pointers for the CPU to copy before adjusting the stack pointer). The operation of ENTER arg1,arg2 is: PUSH rBP temp1 := rSP if( arg2 > 0 ) { for( i = 1; i<arg2; i++ ) { temp2 := read_mem[SS:rBP-i*OperandSize] PUSH temp2
PUSH rBP } rSP := rSP - arg1 ; allocate stack - updates SP/ESP/RSP based on StackAddressSize rBP := temp1 ; set frame pointer - updates BP/EBP/RBP based on OperandSize rowspan=2 LEAVE C9 Release procedure stack created by previous ENTER instruction. Operation is equivalent to:MOV rSP,rBP ; release stack - updates SP/ESP/RSP based on StackAddressSize POP rBP ; restore old frame pointer - updates BP/EBP/RBP based on OperandSizeUDWFF FFThe 80186/80188 did introduce the #UD exception, but did not explicitly reserve any opcode encoding for triggering #UD. The use of two bytes with all bits set to one is convenient – it works if memory has been explicitly initialized to all bits set to one, and it works if a chipset responds to non-DRAM non-MMIO accesses (in this case: code fetches) with bytes that have all bits set to one.
No subsequent x86 processor has ever allocated this encoding for anything else.
To ensure that its #UD behavior persists, the name UDW is used. This follows the naming convention precedence set by UDB: there the B denotes the byte length; here the W denotes the x86 word length. It also avoids UD{0,1,2}.
group #5 (1st FF) with a modrm byte of mod=11b r/m=111b (/7) reg=111b (2nd FF)
Added with 80286 The new instructions added in 80286 add support for x86 protected mode. Some but not all of the instructions are available in real mode as well.
Instruction Opcode Instruction description Real mode Ring LGDT m16&32 0F 01 /2 Load GDTR (Global Descriptor Table Register) from memory. rowspan="4" rowspan="6" 0F 01 /3 Load IDTR (Interrupt Descriptor Table Register) from memory.The IDTR controls not just the address/size of the IDT (interrupt Descriptor Table) in protected mode, but the IVT (Interrupt Vector Table) in real mode as well. LMSW r/m16 0F 01 /6 Load MSW (Machine Status Word) from 16-bit register or memory. CLTS 0F 06 Clear task-switched flag in the MSW. LLDT r/m16 0F 00 /2 Load LDTR (Local Descriptor Table Register) from 16-bit register or memory. rowspan="2" LTR r/m16 0F 00 /3 Load TR (Task Register) from 16-bit register or memory.
The TSS (Task State Segment) specified by the 16-bit argument is marked busy, but a task switch is not done. 0F 01 /0 Store GDTR to memory. rowspan="3" rowspan="5" SIDT m16&32 0F 01 /1 Store IDTR to memory. SMSW r/m16 0F 01 /4 Store MSW to register or 16-bit memory. SLDT r/m16 0F 00 /0 Store LDTR to register or 16-bit memory. rowspan="2" STR r/m16 0F 00 /1 Store TR to register or 16-bit memory. 63 /r Adjust RPL (Requested Privilege Level) field of selector. The operation performed is:if (dst & 3) < (src & 3) then dst = (dst & 0xFFFC) | (src & 3) eflags.zf = 1 else