# instructions

platform: x86
mnem: IMUL
description:
IMUL - Signed Multiply:
| Opcode          | Instruction           | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                               
| F6 /5           | IMUL r/m8*            | M    | Valid      | Valid          | AX← AL * r/m byte.                        
| F7 /5           | IMUL r/m16            | M    | Valid      | Valid          | DX:AX ← AX * r/m word.                    
| F7 /5           | IMUL r/m32            | M    | Valid      | Valid          | EDX:EAX ← EAX * r/m32.                    
| REX.W + F7 /5   | IMUL r/m64            | M    | Valid      | N.E.           | RDX:RAX ← RAX * r/m64.                    
| 0F AF /r        | IMUL r16, r/m16       | RM   | Valid      | Valid          | word register ← word register * r/m16.    
| 0F AF /r        | IMUL r32, r/m32       | RM   | Valid      | Valid          | doubleword register ← doubleword register 
|                 |                       |      |            |                | *r/m32.                                   
| REX.W + 0F AF /r| IMUL r64, r/m64       | RM   | Valid      | N.E.           | Quadword register ← Quadword register     
|                 |                       |      |            |                | *r/m64.                                   
| 6B /r ib        | IMUL r16, r/m16, imm8 | RMI  | Valid      | Valid          | word register ← r/m16 * sign-extended     
|                 |                       |      |            |                | immediate byte.                           
| 6B /r ib        | IMUL r32, r/m32, imm8 | RMI  | Valid      | Valid          | doubleword register ← r/m32 * signextended
|                 |                       |      |            |                | immediate byte.                           
| REX.W + 6B /r ib| IMUL r64, r/m64, imm8 | RMI  | Valid      | N.E.           | Quadword register ← r/m64 * sign-extended 
|                 |                       |      |            |                | immediate byte.                           
| 69 /r iw        | IMUL r16, r/m16, imm16| RMI  | Valid      | Valid          | word register ← r/m16 * immediate word.   
| 69 /r id        | IMUL r32, r/m32, imm32| RMI  | Valid      | Valid          | doubleword register ← r/m32 * immediate   
|                 |                       |      |            |                | doubleword.                               
| REX.W + 69 /r id| IMUL r64, r/m64, imm32| RMI  | Valid      | N.E.           | Quadword register ← r/m64 * immediate     
|                 |                       |      |            |                | doubleword.                               
Notes: * In 64-bit mode, r/m8 can not be encoded to access the following byte
registers if a REX prefix is used: AH, BH, CH, DH.


Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3 | Operand 4
| M    | ModRM:r/m (r, w)| NA           | NA        | NA       
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA        | NA       
| RMI  | ModRM:reg (r, w)| ModRM:r/m (r)| imm8/16/32| NA       

Description:
Performs a signed multiplication of two operands. This instruction has three
forms, depending on the number of operands.

 - One-operand form  -  This form is identical to that used by the MUL instruction.
Here, the source operand (in a general-purpose register or memory location)
is multiplied by the value in the AL, AX, EAX, or RAX register (depending on
the operand size) and the product is stored in the AX, DX:AX, EDX:EAX, or RDX:RAX
registers, respectively.
 - Two-operand form  -  With this form the destination operand (the first operand)
is multiplied by the source operand (second operand). The destination operand
is a general-purpose register and the source operand is an immediate value,
a general-purpose register, or a memory location. The product is then stored
in the destination operand location.
 - Three-operand form  -  This form requires a destination operand (the first operand)
and two source operands (the second and the third operands). Here, the first
source operand (which can be a general-purpose register or a memory location)
is multiplied by the second source operand (an immediate value). The product
is then stored in the destination operand (a general-purpose register).

When an immediate value is used as an operand, it is sign-extended to the length
of the destination operand format.

The CF and OF flags are set when significant bit (including the sign bit) are
carried into the upper half of the result. The CF and OF flags are cleared when
the result (including the sign bit) fits exactly in the lower half of the result.

The three forms of the IMUL instruction are similar in that the length of the
product is calculated to twice the length of the operands. With the one-operand
form, the product is stored exactly in the destination. With the two- and three-
operand forms, however, the result is truncated to the length of the destination
before it is stored in the destination register. Because of this truncation,
the CF or OF flag should be tested to ensure that no significant bits are lost.

The two- and three-operand forms may also be used with unsigned operands because
the lower half of the product is the same regardless if the operands are signed
or unsigned. The CF and OF flags, however, cannot be used to determine if the
upper half of the result is non-zero.

In 64-bit mode, the instruction's default operation size is 32 bits. Use of
the REX.R prefix permits access to additional registers (R8-R15). Use of the
REX.W prefix promotes operation to 64 bits. Use of REX.W modifies the three
forms of the instruction as follows.

 - One-operand form  - The source operand (in a 64-bit general-purpose register or
memory location) is multiplied by the value in the RAX register and the product
is stored in the RDX:RAX registers.
 - Two-operand form  -  The source operand is promoted to 64 bits if it is a register
or a memory location. The destination operand is promoted to 64 bits.
 - Three-operand form  -  The first source operand (either a register or a memory
location) and destination operand are promoted to 64 bits. If the source operand
is an immediate, it is sign extended to 64 bits.

Operation:

IF (NumberOfOperands = 1)
  THEN IF (OperandSize = 8)
     THEN
       AX <- AL * SRC (* Signed multiplication *)
       IF AL = AX
          THEN CF <- 0; OF <- 0;
          ELSE CF <- 1; OF <- 1; FI;
     ELSE IF OperandSize = 16
       THEN
          DX:AX <- AX * SRC (* Signed multiplication *)
          IF sign_extend_to_32 (AX) = DX:AX
             THEN CF <- 0; OF <- 0;
             ELSE CF <- 1; OF <- 1; FI;
       ELSE IF OperandSize = 32
          THEN
             EDX:EAX <- EAX * SRC (* Signed multiplication *)
             IF EAX = EDX:EAX
               THEN CF <- 0; OF <- 0;
               ELSE CF <- 1; OF <- 1; FI;
          ELSE (* OperandSize = 64 *)
             RDX:RAX <- RAX * SRC (* Signed multiplication *)
             IF RAX = RDX:RAX
               THEN CF <- 0; OF <- 0;
               ELSE CF <- 1; OF <- 1; FI;
          FI;
     FI;
  ELSE IF (NumberOfOperands = 2)
     THEN
       temp <- DEST * SRC (* Signed multiplication; temp is double DEST size *)
       DEST <- DEST * SRC (* Signed multiplication *)
       IF temp != DEST
          THEN CF <- 1; OF <- 1;
          ELSE CF <- 0; OF <- 0; FI;
     ELSE (* NumberOfOperands = 3 *)
       DEST <- SRC1 * SRC2 (* Signed multiplication *)
       temp <- SRC1 * SRC2 (* Signed multiplication; temp is double SRC1 size *)
       IF temp != DEST
          THEN CF <- 1; OF <- 1;
          ELSE CF <- 0; OF <- 0; FI;
  FI;
FI;

Flags Affected:
For the one operand form of the instruction, the CF and OF flags are set when
significant bits are carried into the upper half of the result and cleared when
the result fits exactly in the lower half of the result. For the two- and three-operand
forms of the instruction, the CF and OF flags are set when the result must be
truncated to fit in the destination operand size and cleared when the result
fits exactly in the destination operand size. The SF, ZF, AF, and PF flags are
undefined.


Protected Mode Exceptions:
| #GP(0)         | If a memory operand effective address
|                | is outside the CS, DS, ES, FS, or GS 
|                | segment limit. If the DS, ES, FS, or 
|                | GS register is used to access memory 
|                | and it contains a NULL NULL segment  
|                | selector.                            
| #SS(0)         | If a memory operand effective address
|                | is outside the SS segment limit.     
| #PF(fault-code)| If a page fault occurs.              
| #AC(0)         | If alignment checking is enabled and 
|                | an unaligned memory reference is made
|                | while the current privilege level is 
|                | 3.                                   
| #UD            | If the LOCK prefix is used.          

Real-Address Mode Exceptions:
| #GP| If a memory operand effective address
|    | is outside the CS, DS, ES, FS, or GS 
|    | segment limit.                       
| #SS| If a memory operand effective address
|    | is outside the SS segment limit.     
| #UD| If the LOCK prefix is used.          

Virtual-8086 Mode Exceptions:
| #GP(0)         | If a memory operand effective address 
|                | is outside the CS, DS, ES, FS, or GS  
|                | segment limit.                        
| #SS(0)         | If a memory operand effective address 
|                | is outside the SS segment limit.      
| #PF(fault-code)| If a page fault occurs.               
| #AC(0)         | If alignment checking is enabled and  
|                | an unaligned memory reference is made.
| #UD            | If the LOCK prefix is used.           

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)         | If a memory address referencing the        
|                | SS segment is in a non-canonical form.     
| #GP(0)         | If the memory address is in a non-canonical
|                | form.                                      
| #PF(fault-code)| If a page fault occurs.                    
| #AC(0)         | If alignment checking is enabled and       
|                | an unaligned memory reference is made      
|                | while the current privilege level is       
|                | 3.                                         
| #UD            | If the LOCK prefix is used.                


platform: x86
mnem: IN
description:
IN - Input from Port:
| Opcode| Instruction | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                           
| E4 ib | IN AL, imm8 | I    | Valid      | Valid          | Input byte from imm8 I/O port address 
|       |             |      |            |                | into AL.                              
| E5 ib | IN AX, imm8 | I    | Valid      | Valid          | Input word from imm8 I/O port address 
|       |             |      |            |                | into AX.                              
| E5 ib | IN EAX, imm8| I    | Valid      | Valid          | Input dword from imm8 I/O port address
|       |             |      |            |                | into EAX.                             
| EC    | IN AL,DX    | NP   | Valid      | Valid          | Input byte from I/O port in DX into   
|       |             |      |            |                | AL.                                   
| ED    | IN AX,DX    | NP   | Valid      | Valid          | Input word from I/O port in DX into   
|       |             |      |            |                | AX.                                   
| ED    | IN EAX,DX   | NP   | Valid      | Valid          | Input doubleword from I/O port in DX  
|       |             |      |            |                | into EAX.                             

Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| I    | imm8     | NA       | NA       | NA       
| NP   | NA       | NA       | NA       | NA       

Description:
Copies the value from the I/O port specified with the second operand (source
operand) to the destination operand (first operand). The source operand can
be a byte-immediate or the DX register; the destination operand can be register
AL, AX, or EAX, depending on the size of the port being accessed (8, 16, or
32 bits, respectively). Using the DX register as a source operand allows I/O
port addresses from 0 to 65,535 to be accessed; using a byte immediate allows
I/O port addresses 0 to 255 to be accessed.

When accessing an 8-bit I/O port, the opcode determines the port size; when
accessing a 16- and 32-bit I/O port, the operand-size attribute determines the
port size. At the machine code level, I/O instructions are shorter when accessing
8-bit I/O ports. Here, the upper eight bits of the port address will be 0.

This instruction is only useful for accessing I/O ports located in the processor's
I/O address space. See Chapter 16, “Input/Output,” in the Intel® 64 and IA-32
Architectures Software Developer's Manual, Volume 1, for more information on
accessing I/O ports in the I/O address space.

This instruction's operation is the same in non-64-bit modes and 64-bit mode.

Operation:

IF ((PE = 1) and ((CPL > IOPL) or (VM = 1)))
  THEN (* Protected mode with CPL > IOPL or virtual-8086 mode *)
     IF (Any I/O Permission Bit for I/O port being accessed = 1)
       THEN (* I/O operation is not allowed *)
          #GP(0);
       ELSE ( * I/O operation is allowed *)
          DEST <- SRC; (* Read from selected I/O port *)
     FI;
  ELSE (Real Mode or Protected Mode with CPL ≤ IOPL *)
     DEST <- SRC; (* Read from selected I/O port *)
FI;

Flags Affected:
None.


Protected Mode Exceptions:
| #GP(0)| If the CPL is greater than (has less       
|       | privilege) the I/O privilege level (IOPL)  
|       | and any of the corresponding I/O permission
|       | bits in TSS for the I/O port being accessed
|       | is 1.                                      
| #UD   | If the LOCK prefix is used.                

Real-Address Mode Exceptions:
| #UD| If the LOCK prefix is used.

Virtual-8086 Mode Exceptions:
| #GP(0)         | If any of the I/O permission bits in   
|                | the TSS for the I/O port being accessed
|                | is 1.                                  
| #PF(fault-code)| If a page fault occurs.                
| #UD            | If the LOCK prefix is used.            

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #GP(0)| If the CPL is greater than (has less       
|       | privilege) the I/O privilege level (IOPL)  
|       | and any of the corresponding I/O permission
|       | bits in TSS for the I/O port being accessed
|       | is 1.                                      
| #UD   | If the LOCK prefix is used.                


platform: x86
mnem: INC
description:
INC - Increment by 1:
| Opcode       | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                        
| FE /0        | INC r/m8   | M    | Valid      | Valid          | Increment r/m byte by 1.           
| REX + FE /0  | INC r/m8*  | M    | Valid      | N.E.           | Increment r/m byte by 1.           
| FF /0        | INC r/m16  | M    | Valid      | Valid          | Increment r/m word by 1.           
| FF /0        | INC r/m32  | M    | Valid      | Valid          | Increment r/m doubleword by 1.     
| REX.W + FF /0| INC r/m64  | M    | Valid      | N.E.           | Increment r/m quadword by 1.       
| 40+ rw**     | INC r16    | O    | N.E.       | Valid          | Increment word register by 1.      
| 40+ rd       | INC r32    | O    | N.E.       | Valid          | Increment doubleword register by 1.
Notes: * In 64-bit mode, r/m8 can not be encoded to access the following byte
registers if a REX prefix is used: AH, BH, CH, DH. ** 40H through 47H are REX
prefixes in 64-bit mode.


Instruction Operand Encoding:
| Op/En| Operand 1         | Operand 2| Operand 3| Operand 4
| M    | ModRM:r/m (r, w)  | NA       | NA       | NA       
| O    | opcode + rd (r, w)| NA       | NA       | NA       

Description:
Adds 1 to the destination operand, while preserving the state of the CF flag.
The destination operand can be a register or a memory location. This instruction
allows a loop counter to be updated without disturbing the CF flag. (Use a ADD
instruction with an immediate operand of 1 to perform an increment operation
that does updates the CF flag.)

This instruction can be used with a LOCK prefix to allow the instruction to
be executed atomically.

In 64-bit mode, INC r16 and INC r32 are not encodable (because opcodes 40H through
47H are REX prefixes). Otherwise, the instruction's 64-bit mode default operation
size is 32 bits. Use of the REX.R prefix permits access to additional registers
(R8-R15). Use of the REX.W prefix promotes operation to 64 bits.

Operation:

DEST <- DEST + 1;

AFlags Affected:
The CF flag is not affected. The OF, SF, ZF, AF, and PF flags are set according
to the result.


Protected Mode Exceptions:
| #GP(0)         | If the destination operand is located         
|                | in a non-writable segment. If a memory        
|                | operand effective address is outside          
|                | the CS, DS, ES, FS, or GS segment limit.      
|                | If the DS, ES, FS, or GS register is          
|                | used to access memory and it contains         
|                | a NULLsegment selector.                       
| #SS(0)         | If a memory operand effective address         
|                | is outside the SS segment limit.              
| #PF(fault-code)| If a page fault occurs.                       
| #AC(0)         | If alignment checking is enabled and          
|                | an unaligned memory reference is made         
|                | while the current privilege level is          
|                | 3.                                            
| #UD            | If the LOCK prefix is used but the destination
|                | is not a memory operand.                      

Real-Address Mode Exceptions:
| #GP| If a memory operand effective address         
|    | is outside the CS, DS, ES, FS, or GS          
|    | segment limit.                                
| #SS| If a memory operand effective address         
|    | is outside the SS segment limit.              
| #UD| If the LOCK prefix is used but the destination
|    | is not a memory operand.                      

Virtual-8086 Mode Exceptions:
| #GP(0)         | If a memory operand effective address         
|                | is outside the CS, DS, ES, FS, or GS          
|                | segment limit.                                
| #SS(0)         | If a memory operand effective address         
|                | is outside the SS segment limit.              
| #PF(fault-code)| If a page fault occurs.                       
| #AC(0)         | If alignment checking is enabled and          
|                | an unaligned memory reference is made.        
| #UD            | If the LOCK prefix is used but the destination
|                | is not a memory operand.                      

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)         | If a memory address referencing the           
|                | SS segment is in a non-canonical form.        
| #GP(0)         | If the memory address is in a non-canonical   
|                | form.                                         
| #PF(fault-code)| If a page fault occurs.                       
| #AC(0)         | If alignment checking is enabled and          
|                | an unaligned memory reference is made         
|                | while the current privilege level is          
|                | 3.                                            
| #UD            | If the LOCK prefix is used but the destination
|                | is not a memory operand.                      


platform: x86
mnem: INS
description:
INS/INSB/INSW/INSD - Input from Port to String:
| Opcode| Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                             
| 6C    | INS m8, DX | NP   | Valid      | Valid          | Input byte from I/O port specified in   
|       |            |      |            |                | DX into memory location specified in    
|       |            |      |            |                | ES:(E)DI or RDI.*                       
| 6D    | INS m16, DX| NP   | Valid      | Valid          | Input word from I/O port specified in   
|       |            |      |            |                | DX into memory location specified in    
|       |            |      |            |                | ES:(E)DI or RDI.1                       
| 6D    | INS m32, DX| NP   | Valid      | Valid          | Input doubleword from I/O port specified
|       |            |      |            |                | in DX into memory location specified    
|       |            |      |            |                | in ES:(E)DI or RDI.1                    
| 6C    | INSB       | NP   | Valid      | Valid          | Input byte from I/O port specified in   
|       |            |      |            |                | DX into memory location specified with  
|       |            |      |            |                | ES:(E)DI or RDI.1                       
| 6D    | INSW       | NP   | Valid      | Valid          | Input word from I/O port specified in   
|       |            |      |            |                | DX into memory location specified in    
|       |            |      |            |                | ES:(E)DI or RDI.1                       
| 6D    | INSD       | NP   | Valid      | Valid          | Input doubleword from I/O port specified
|       |            |      |            |                | in DX into memory location specified    
|       |            |      |            |                | in ES:(E)DI or RDI.1                    
Notes: * In 64-bit mode, only 64-bit (RDI) and 32-bit (EDI) address sizes are
supported. In non-64-bit mode, only 32-bit (EDI) and 16-bit (DI) address sizes
are supported.


Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| NP   | NA       | NA       | NA       | NA       

Description:
Copies the data from the I/O port specified with the source operand (second
operand) to the destination operand (first operand). The source operand is an
I/O port address (from 0 to 65,535) that is read from the DX register. The destination
operand is a memory location, the address of which is read from either the ES:DI,
ES:EDI or the RDI registers (depending on the address-size attribute of the
instruction, 16, 32 or 64, respectively). (The ES segment cannot be overridden
with a segment override prefix.) The size of the I/O port being accessed (that
is, the size of the source and destination operands) is determined by the opcode
for an 8-bit I/O port or by the operand-size attribute of the instruction for
a 16- or 32-bit I/O port.

At the assembly-code level, two forms of this instruction are allowed: the “explicit-operands”
form and the “nooperands” form. The explicit-operands form (specified with the
INS mnemonic) allows the source and destination operands to be specified explicitly.
Here, the source operand must be “DX,” and the destination operand should be
a symbol that indicates the size of the I/O port and the destination address.
This explicit-operands form is provided to allow documentation; however, note
that the documentation provided by this form can be misleading. That is, the
destination operand symbol must specify the correct type (size) of the operand
(byte, word, or doubleword), but it does not have to specify the correct location.
The location is always specified by the ES:(E)DI registers, which must be loaded
correctly before the INS instruction is executed.

The no-operands form provides “short forms” of the byte, word, and doubleword
versions of the INS instructions. Here also DX is assumed by the processor to
be the source operand and ES:(E)DI is assumed to be the destination operand.
The size of the I/O port is specified with the choice of mnemonic: INSB (byte),
INSW (word), or INSD (doubleword).

After the byte, word, or doubleword is transfer from the I/O port to the memory
location, the DI/EDI/RDI register is incremented or decremented automatically
according to the setting of the DF flag in the EFLAGS register. (If the DF flag
is 0, the (E)DI register is incremented; if the DF flag is 1, the (E)DI register
is decremented.) The (E)DI register is incremented or decremented by 1 for byte
operations, by 2 for word operations, or by 4 for doubleword operations.

The INS, INSB, INSW, and INSD instructions can be preceded by the REP prefix
for block input of ECX bytes, words, or doublewords. See “REP/REPE/REPZ /REPNE/REPNZ - Repeat
String Operation Prefix” in Chapter 4 of the Intel®64 and IA-32 Architectures
Software Developer's Manual, Volume 2B, for a description of the REP prefix.

These instructions are only useful for accessing I/O ports located in the processor's
I/O address space. See Chapter 16, “Input/Output,” in the Intel® 64 and IA-32
Architectures Software Developer's Manual, Volume 1, for more information on
accessing I/O ports in the I/O address space.

In 64-bit mode, default address size is 64 bits, 32 bit address size is supported
using the prefix 67H. The address of the memory destination is specified by
RDI or EDI. 16-bit address size is not supported in 64-bit mode. The operand
size is not promoted.

Operation:

IF ((PE = 1) and ((CPL > IOPL) or (VM = 1)))
  THEN (* Protected mode with CPL > IOPL or virtual-8086 mode *)
     IF (Any I/O Permission Bit for I/O port being accessed = 1)
       THEN (* I/O operation is not allowed *)
          #GP(0);
       ELSE (* I/O operation is allowed *)
          DEST <- SRC; (* Read from I/O port *)
     FI;
  ELSE (Real Mode or Protected Mode with CPL IOPL *)
     DEST <- SRC; (* Read from I/O port *)
FI;
Non-64-bit Mode:
IF (Byte transfer)
  THEN IF DF = 0
     THEN (E)DI <- (E)DI + 1;
     ELSE (E)DI <- (E)DI - 1; FI;
  ELSE IF (Word transfer)
     THEN IF DF = 0
       THEN (E)DI <- (E)DI + 2;
       ELSE (E)DI <- (E)DI - 2; FI;
     ELSE (* Doubleword transfer *)
       THEN IF DF = 0
          THEN (E)DI <- (E)DI + 4;
          ELSE (E)DI <- (E)DI - 4; FI;
     FI;
FI;
FI64-bit Mode:
IF (Byte transfer)
  THEN IF DF = 0
     THEN (E|R)DI <- (E|R)DI + 1;
     ELSE (E|R)DI <- (E|R)DI - 1; FI;
  ELSE IF (Word transfer)
     THEN IF DF = 0
       THEN (E)DI <- (E)DI + 2;
       ELSE (E)DI <- (E)DI - 2; FI;
     ELSE (* Doubleword transfer *)
       THEN IF DF = 0
          THEN (E|R)DI <- (E|R)DI + 4;
          ELSE (E|R)DI <- (E|R)DI - 4; FI;
     FI;
FI;

Flags Affected:
None.


Protected Mode Exceptions:
| #GP(0)         | If the CPL is greater than (has less       
|                | privilege) the I/O privilege level (IOPL)  
|                | and any of the corresponding I/O permission
|                | bits in TSS for the I/O port being accessed
|                | is 1. If the destination is located        
|                | in a non-writable segment. If an illegal   
|                | memory operand effective address in        
|                | the ES segments is given.                  
| #PF(fault-code)| If a page fault occurs.                    
| #AC(0)         | If alignment checking is enabled and       
|                | an unaligned memory reference is made      
|                | while the current privilege level is       
|                | 3.                                         
| #UD            | If the LOCK prefix is used.                

Real-Address Mode Exceptions:
| #GP| If a memory operand effective address
|    | is outside the CS, DS, ES, FS, or GS 
|    | segment limit.                       
| #SS| If a memory operand effective address
|    | is outside the SS segment limit.     
| #UD| If the LOCK prefix is used.          

Virtual-8086 Mode Exceptions:
| #GP(0)         | If any of the I/O permission bits in   
|                | the TSS for the I/O port being accessed
|                | is 1.                                  
| #PF(fault-code)| If a page fault occurs.                
| #AC(0)         | If alignment checking is enabled and   
|                | an unaligned memory reference is made. 
| #UD            | If the LOCK prefix is used.            

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)         | If a memory address referencing the        
|                | SS segment is in a non-canonical form.     
| #GP(0)         | If the CPL is greater than (has less       
|                | privilege) the I/O privilege level (IOPL)  
|                | and any of the corresponding I/O permission
|                | bits in TSS for the I/O port being accessed
|                | is 1. If the memory address is in a        
|                | non-canonical form.                        
| #PF(fault-code)| If a page fault occurs.                    
| #AC(0)         | If alignment checking is enabled and       
|                | an unaligned memory reference is made      
|                | while the current privilege level is       
|                | 3.                                         
| #UD            | If the LOCK prefix is used.                


platform: x86
mnem: INSERTPS
description:
INSERTPS  -  Insert Packed Single Precision Floating-Point Value:
| Opcode/Instruction                        | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                              
| 66 0F 3A 21 /r ib INSERTPS xmm1, xmm2/m32,| RMI  | V/V           | SSE4_1            | Insert a single precision floating-point 
| imm8                                      |      |               |                   | value selected by imm8 from xmm2/m32     
|                                           |      |               |                   | into xmm1 at the specified destination   
|                                           |      |               |                   | element specified by imm8 and zero out   
|                                           |      |               |                   | destination elements in xmm1 as indicated
|                                           |      |               |                   | in imm8.                                 
| VEX.NDS.128.66.0F3A.WIG 21 /r ib VINSERTPS| RVMI | V/V           | AVX               | Insert a single precision floating point 
| xmm1, xmm2, xmm3/m32, imm8                |      |               |                   | value selected by imm8 from xmm3/m32     
|                                           |      |               |                   | and merge into xmm2 at the specified     
|                                           |      |               |                   | destination element specified by imm8    
|                                           |      |               |                   | and zero out destination elements in     
|                                           |      |               |                   | xmm1 as indicated in imm8.               

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3    | Operand 4
| RMI  | ModRM:reg (w)| ModRM:r/m (r)| imm8         | NA       
| RVMI | ModRM:reg (w)| VEX.vvvv (r) | ModRM:r/m (r)| imm8     

Description:
(register source form) Select a single precision floating-point element from
second source as indicated by Count_S bits of the immediate operand and insert
it into the first source at the location indicated by the Count_D bits of the
immediate operand. Store in the destination and zero out destination elements
based on the ZMask bits of the immediate operand.

(memory source form) Load a floating-point element from a 32-bit memory location
and insert it into the first source at the location indicated by the Count_D
bits of the immediate operand. Store in the destination and zero out destination
elements based on the ZMask bits of the immediate operand.

128-bit Legacy SSE version: The first source register is an XMM register. The
second source operand is either an XMM register or a 32-bit memory location.
The destination is not distinct from the first source XMM register and the upper
bits (VLMAX-1:128) of the corresponding YMM register destination are unmodified.
VEX.128 encoded version. The destination and first source register is an XMM
register. The second source operand is either an XMM register or a 32-bit memory
location. The upper bits (VLMAX-1:128) of the corresponding YMM register destination
are zeroed. If VINSERTPS is encoded with VEX.L= 1, an attempt to execute the
instruction encoded with VEX.L= 1 will cause an #UD exception.

Operation:

INSERTPS (128-bit Legacy SSE version)
IF (SRC = REG) THEN COUNT_S <- imm8[7:6]
  ELSE COUNT_S <- 0
COUNT_D <- imm8[5:4]
ZMASK <- imm8[3:0]
CASE (COUNT_S) OF
  0: TMP <- SRC[31:0]
  1: TMP <- SRC[63:32]
  2: TMP <- SRC[95:64]
  3: TMP <- SRC[127:96]
ESAC;
CASE (COUNT_D) OF
  0: TMP2[31:0] <- TMP
     TMP2[127:32] <- DEST[127:32]
  1: TMP2[63:32] <- TMP
     TMP2[31:0] <- DEST[31:0]
     TMP2[127:64] <- DEST[127:64]
  2: TMP2[95:64] <- TMP
     TMP2[63:0] <- DEST[63:0]
     TMP2[127:96] <- DEST[127:96]
  3: TMP2[127:96] <- TMP
     TMP2[95:0] <- DEST[95:0]
ESAC;
IF (ZMASK[0] = 1) THEN DEST[31:0] <- 00000000H
  ELSE DEST[31:0] <- TMP2[31:0]
IF (ZMASK[1] = 1) THEN DEST[63:32] <- 00000000H
  ELSE DEST[63:32] <- TMP2[63:32]
IF (ZMASK[2] = 1) THEN DEST[95:64] <- 00000000H
  ELSE DEST[95:64] <- TMP2[95:64]
IF (ZMASK[3] = 1) THEN DEST[127:96] <- 00000000H
  ELSE DEST[127:96] <- TMP2[127:96]
DEST[VLMAX-1:128] (Unmodified)
VINSERTPS (VEX.128 encoded version)
IF (SRC = REG) THEN COUNT_S <- imm8[7:6]
  ELSE COUNT_S <- 0
COUNT_D <- imm8[5:4]
ZMASK <- imm8[3:0]
CASE (COUNT_S) OF
  0: TMP <- SRC2[31:0]
  1: TMP <- SRC2[63:32]
  2: TMP <- SRC2[95:64]
  3: TMP <- SRC2[127:96]
ESAC;
CASE (COUNT_D) OF
  0: TMP2[31:0] <- TMP
     TMP2[127:32] <- SRC1[127:32]
  1: TMP2[63:32] <- TMP
     TMP2[31:0] <- SRC1[31:0]
     TMP2[127:64] <- SRC1[127:64]
  2: TMP2[95:64] <- TMP
     TMP2[63:0] <- SRC1[63:0]
     TMP2[127:96] <- SRC1[127:96]
  3: TMP2[127:96] <- TMP
     TMP2[95:0] <- SRC1[95:0]
ESAC;
IF (ZMASK[0] = 1) THEN DEST[31:0] <- 00000000H
  ELSE DEST[31:0] <- TMP2[31:0]
IF (ZMASK[1] = 1) THEN DEST[63:32] <- 00000000H
  ELSE DEST[63:32] <- TMP2[63:32]
IF (ZMASK[2] = 1) THEN DEST[95:64] <- 00000000H
  ELSE DEST[95:64] <- TMP2[95:64]
IF (ZMASK[3] = 1) THEN DEST[127:96] <- 00000000H
  ELSE DEST[127:96] <- TMP2[127:96]
DEST[VLMAX-1:128] <- 0

Intel C/C++ Compiler Intrinsic Equivalent:
| INSERTPS:| __m128 _mm_insert_ps(__m128 dst, __m128
|          | src, const int ndx);                   

SIMD Floating-Point Exceptions:
None


Other Exceptions:
See Exceptions Type 5.


platform: x86
mnem: INT n
description:
INT n/INTO/INT 3 - Call to Interrupt Procedure:
| Opcode| Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                         
| CC    | INT 3      | NP   | Valid      | Valid          | Interrupt 3 - trap to debugger.       
| CD ib | INT imm8   | I    | Valid      | Valid          | Interrupt vector number specified by
|       |            |      |            |                | immediate byte.                     
| CE    | INTO       | NP   | Invalid    | Valid          | Interrupt 4 - if overflow flag is 1.  

Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| NP   | NA       | NA       | NA       | NA       
| I    | imm8     | NA       | NA       | NA       

Description:
The INT n instruction generates a call to the interrupt or exception handler
specified with the destination operand (see the section titled “Interrupts and
Exceptions” in Chapter 6 of the Intel® 64 and IA-32 Architectures Software Developer's
Manual, Volume 1). The destination operand specifies an interrupt vector number
from 0 to 255, encoded as an 8-bit unsigned intermediate value. Each interrupt
vector number provides an index to a gate descriptor in the IDT. The first 32
interrupt vector numbers are reserved by Intel for system use. Some of these
interrupts are used for internally generated exceptions.

The INT n instruction is the general mnemonic for executing a software-generated
call to an interrupt handler. The INTO instruction is a special mnemonic for
calling overflow exception (#OF), interrupt vector number 4. The overflow interrupt
checks the OF flag in the EFLAGS register and calls the overflow interrupt handler
if the OF flag is set to 1. (The INTO instruction cannot be used in 64-bit mode.)

The INT 3 instruction generates a special one byte opcode (CC) that is intended
for calling the debug exception handler. (This one byte form is valuable because
it can be used to replace the first byte of any instruction with a breakpoint,
including other one byte instructions, without over-writing other code). To
further support its function as a debug breakpoint, the interrupt generated
with the CC opcode also differs from the regular software interrupts as follows:

 - Interrupt redirection does not happen when in VME mode; the interrupt is handled
by a protected-mode handler.
 - The virtual-8086 mode IOPL checks do not occur. The interrupt is taken without
faulting at any IOPL level.

Note that the “normal” 2-byte opcode for INT 3 (CD03) does not have these special
features. Intel and Microsoft assemblers will not generate the CD03 opcode from
any mnemonic, but this opcode can be created by direct numeric code definition
or by self-modifying code.

The action of the INT n instruction (including the INTO and INT 3 instructions)
is similar to that of a far call made with the CALL instruction. The primary
difference is that with the INT n instruction, the EFLAGS register is pushed
onto the stack before the return address. (The return address is a far address
consisting of the current values of the CS and EIP registers.) Returns from
interrupt procedures are handled with the IRET instruction, which pops the EFLAGS
information and return address from the stack.

The interrupt vector number specifies an interrupt descriptor in the interrupt
descriptor table (IDT); that is, it provides index into the IDT. The selected
interrupt descriptor in turn contains a pointer to an interrupt or exception
handler procedure. In protected mode, the IDT contains an array of 8-byte descriptors,
each of which is an interrupt gate, trap gate, or task gate. In real-address
mode, the IDT is an array of 4-byte far pointers (2-byte code segment selector
and a 2-byte instruction pointer), each of which point directly to a procedure
in the selected segment. (Note that in real-address mode, the IDT is called
the interrupt vector table, and its pointers are called interrupt vectors.)

The following decision table indicates which action in the lower portion of
the table is taken given the conditions in the upper portion of the table. Each
Y in the lower section of the decision table represents a procedure defined
in

the “Operation” section for this instruction (except #GP).


Table 3-61. Decision Table:
| PE                                                            | 0| 1      | 1       | 1                      | 1                      | 1                      | 1                      | 1                      
| VM                                                            | -| -      | -       | -                      | -                      | 0                      | 1                      | 1                      
| IOPL                                                          | -| -      | -       | -                      | -                      | -                      | <3                     | =3                     
| DPL/CPL RELATIONSHIP                                          | -| DPL<CPL| -       | DPL>CPL                | DPL=CPL or C           | DPL<CPL & NC           | -                      | -                      
| INTERRUPT TYPE                                                | -| S/W    | -       | -                      | -                      | -                      | -                      | -                      
| GATE TYPE REAL-ADDRESS-MODE PROTECTED-MODE                    | Y| Y Y    | Task Y Y| Trap or Interrupt Y Y Y| Trap or Interrupt Y Y Y| Trap or Interrupt Y Y Y| Trap or Interrupt Y Y Y| Trap or Interrupt Y Y Y
| TRAP-OR-INTERRUPTGATE INTER-PRIVILEGE-LEVELINTERRUPT          |  |        |         |                        |                        |                        |                        |                        
| INTRA-PRIVILEGE-LEVELINTERRUPT INTERRUPT-FROMVIRTUAL-8086-MODE|  |        |         |                        |                        |                        |                        |                        
| TASK-GATE #GP                                                 |  |        |         |                        |                        |                        |                        |                        
Notes: 

| −| Don't Care.                         
| Y| Yes, action taken. Action not taken.
When the processor is executing in virtual-8086 mode, the IOPL determines the
action of the INT n instruction. If the IOPL is less than 3, the processor generates
a #GP(selector) exception; if the IOPL is 3, the processor executes a protected
mode interrupt to privilege level 0. The interrupt gate's DPL must be set to
3 and the target CPL of the interrupt handler procedure must be 0 to execute
the protected mode interrupt to privilege level 0.

The interrupt descriptor table register (IDTR) specifies the base linear address
and limit of the IDT. The initial base address value of the IDTR after the processor
is powered up or reset is 0.

Operation:

The following operational description applies not only to the INT n and INTO instructions, but also to external inter-
rupts, nonmaskable interrupts (NMIs), and exceptions. Some of these events push onto the stack an error code.
The operational description specifies numerous checks whose failure may result in delivery of a nested exception.
In these cases, the original event is not delivered.
The operational description specifies the error code delivered by any nested exception. In some cases, the error
code is specified with a pseudofunction error_code(num,idt,ext), where idt and ext are bit values. The pseudofunc-
tion produces an error code as follows: (1) if idt is 0, the error code is (num & FCH) | ext; (2) if idt is 1, the error
code is (num « 3) | 2 | ext.
In many cases, the pseudofunction error_code is invoked with a pseudovariable EXT. The value of EXT depends on
the nature of the event whose delivery encountered a nested exception: if that event is a software interrupt, EXT
is 0; otherwise, EXT is 1.
IF PE = 0
  THEN
     GOTO REAL-ADDRESS-MODE;
  ELSE (* PE = 1 *)
     IF (VM = 1 and IOPL < 3 AND INT n)
       THEN
          #GP(0); (* Bit 0 of error code is 0 because INT n *)
       ELSE (* Protected mode, IA-32e mode, or virtual-8086 mode interrupt *)
          IF (IA32_EFER.LMA = 0)
             THEN (* Protected mode, or virtual-8086 mode interrupt *)
               GOTO PROTECTED-MODE;
          ELSE (* IA-32e mode interrupt *)
             GOTO IA-32e-MODE;
          FI;
     FI;
FI;
REAL-ADDRESS-MODE:
  IF ((vector_number « 2) + 3) is not within IDT limit
     THEN #GP; FI;
  IF stack not large enough for a 6-byte return information
     THEN #SS; FI;
  Push (EFLAGS[15:0]);
  IF <- 0; (* Clear interrupt flag *)
  TF <- 0; (* Clear trap flag *)
  AC <- 0; (* Clear AC flag *)
  Push(CS);
  Push(IP);
  (* No error codes are pushed in real-address mode*)
  CS <- IDT(Descriptor (vector_number « 2), selector));
  EIP <- IDT(Descriptor (vector_number « 2), offset)); (* 16 bit offset AND 0000FFFFH *)
END;
PROTECTED-MODE:
  IF ((vector_number « 3) + 7) is not within IDT limits
  or selected IDT descriptor is not an interrupt-, trap-, or task-gate type
     THEN #GP(error_code(vector_number,1,EXT)); FI;
     (* idt operand to error_code set because vector is used *)
  IF software interrupt (* Generated by INT n, INT3, or INTO *)
     THEN
       IF gate DPL < CPL (* PE = 1, DPL < CPL, software interrupt *)
          THEN #GP(error_code(vector_number,1,0)); FI;
          (* idt operand to error_code set because vector is used *)
          (* ext operand to error_code is 0 because INT n, INT3, or INTO*)
  FI;
  IF gate not present
     THEN #NP(error_code(vector_number,1,EXT)); FI;
     (* idt operand to error_code set because vector is used *)
  IF task gate (* Specified in the selected interrupt table descriptor *)
     THEN GOTO TASK-GATE;
     ELSE GOTO TRAP-OR-INTERRUPT-GATE; (* PE = 1, trap/interrupt gate *)
  FI;
END;
IA-32e-MODE:
  IF INTO and CS.L = 1 (64-bit mode)
     THEN #UD;
  FI;
  IF ((vector_number « 4) + 15) is not in IDT limits
  or selected IDT descriptor is not an interrupt-, or trap-gate type
     THEN #GP(error_code(vector_number,1,EXT));
     (* idt operand to error_code set because vector is used *)
  FI;
  IF software interrupt (* Generated by INT n, INT 3, or INTO *)
     THEN
       IF gate DPL < CPL (* PE = 1, DPL < CPL, software interrupt *)
          THEN #GP(error_code(vector_number,1,0));
          (* idt operand to error_code set because vector is used *)
          (* ext operand to error_code is 0 because INT n, INT3, or INTO*)
       FI;
  FI;
  IF gate not present
     THEN #NP(error_code(vector_number,1,EXT));
     (* idt operand to error_code set because vector is used *)
  FI;
  GOTO TRAP-OR-INTERRUPT-GATE; (* Trap/interrupt gate *)
END;
TASK-GATE: (* PE = 1, task gate *)
  Read TSS selector in task gate (IDT descriptor);
     IF local/global bit is set to local or index not within GDT limits
       THEN #GP(error_code(TSS selector,0,EXT)); FI;
       (* idt operand to error_code is 0 because selector is used *)
     Access TSS descriptor in GDT;
     IF TSS descriptor specifies that the TSS is busy (low-order 5 bits set to 00001)
       THEN #GP(TSS selector,0,EXT)); FI;
       (* idt operand to error_code is 0 because selector is used *)
     IF TSS not present
       THEN #NP(TSS selector,0,EXT)); FI;
       (* idt operand to error_code is 0 because selector is used *)
  SWITCH-TASKS (with nesting) to TSS;
  IF interrupt caused by fault with error code
     THEN
       IF stack limit does not allow push of error code
          THEN #SS(EXT); FI;
       Push(error code);
  FI;
  IF EIP not within code segment limit
     THEN #GP(EXT); FI;
END;
TRAP-OR-INTERRUPT-GATE:
  Read new code-segment selector for trap or interrupt gate (IDT descriptor);
  IF new code-segment selector is NULL
     THEN #GP(EXT); FI; (* Error code contains NULL selector *)
  IF new code-segment selector is not within its descriptor table limits
     THEN #GP(error_code(new code-segment selector,0,EXT)); FI;
     (* idt operand to error_code is 0 because selector is used *)
  Read descriptor referenced by new code-segment selector;
  IF descriptor does not indicate a code segment or new code-segment DPL > CPL
     THEN #GP(error_code(new code-segment selector,0,EXT)); FI;
     (* idt operand to error_code is 0 because selector is used *)
  IF new code-segment descriptor is not present,
     THEN #NP(error_code(new code-segment selector,0,EXT)); FI;
     (* idt operand to error_code is 0 because selector is used *)
  IF new code segment is non-conforming with DPL < CPL
     THEN
       IF VM = 0
          THEN
             GOTO INTER-PRIVILEGE-LEVEL-INTERRUPT;
             (* PE = 1, VM = 0, interrupt or trap gate, nonconforming code segment,
             DPL < CPL *)
          ELSE (* VM = 1 *)
             IF new code-segment DPL != 0
               THEN #GP(error_code(new code-segment selector,0,EXT));
               (* idt operand to error_code is 0 because selector is used *)
             GOTO INTERRUPT-FROM-VIRTUAL-8086-MODE; FI;
             (* PE = 1, interrupt or trap gate, DPL < CPL, VM = 1 *)
       FI;
     ELSE (* PE = 1, interrupt or trap gate, DPL ≥ CPL *)
       IF VM = 1
          THEN #GP(error_code(new code-segment selector,0,EXT));
          (* idt operand to error_code is 0 because selector is used *)
       IF new code segment is conforming or new code-segment DPL = CPL
          THEN
             GOTO INTRA-PRIVILEGE-LEVEL-INTERRUPT;
          ELSE (* PE = 1, interrupt or trap gate, nonconforming code segment, DPL > CPL *)
             #GP(error_code(new code-segment selector,0,EXT));
             (* idt operand to error_code is 0 because selector is used *)
       FI;
  FI;
END;
INTER-PRIVILEGE-LEVEL-INTERRUPT:
  (* PE = 1, interrupt or trap gate, non-conforming code segment, DPL < CPL *)
  IF (IA32_EFER.LMA = 0) (* Not IA-32e mode *)
     THEN
     (* Identify stack-segment selector for new privilege level in current TSS *)
       IF current TSS is 32-bit
          THEN
             TSSstackAddress <- (new code-segment DPL « 3) + 4;
             IF (TSSstackAddress + 5) > current TSS limit
               THEN #TS(error_code(current TSS selector,0,EXT)); FI;
               (* idt operand to error_code is 0 because selector is used *)
             NewSS <- 2 bytes loaded from (TSS base + TSSstackAddress + 4);
             NewESP <- 4 bytes loaded from (TSS base + TSSstackAddress);
          ELSE
             TSSstackAddress <- (new code-segment DPL « 2) + 2
             IF (TSSstackAddress + 3) > current TSS limit
               THEN #TS(error_code(current TSS selector,0,EXT)); FI;
               (* idt operand to error_code is 0 because selector is used *)
             NewSS <- 2 bytes loaded from (TSS base + TSSstackAddress + 2);
             NewESP <- 2 bytes loaded from (TSS base + TSSstackAddress);
       FI;
       IF NewSS is NULL
          THEN #TS(EXT); FI;
       IF NewSS index is not within its descriptor-table limits
       or NewSS RPL != new code-segment DPL
          THEN #TS(error_code(NewSS,0,EXT)); FI;
          (* idt operand to error_code is 0 because selector is used *)
       Read new stack-segment descriptor for NewSS in GDT or LDT;
       IF new stack-segment DPL != new code-segment DPL
       or new stack-segment Type does not indicate writable data segment
          THEN #TS(error_code(NewSS,0,EXT)); FI;
          (* idt operand to error_code is 0 because selector is used *)
       IF NewSS is not present
          THEN #SS(error_code(NewSS,0,EXT)); FI;
          (* idt operand to error_code is 0 because selector is used *)
     ELSE (* IA-32e mode *)
       IF IDT-gate IST = 0
          THEN TSSstackAddress <- (new code-segment DPL « 3) + 4;
          ELSE TSSstackAddress <- (IDT gate IST « 3) + 28;
       FI;
       IF (TSSstackAddress + 7) > current TSS limit
          THEN #TS(error_code(current TSS selector,0,EXT); FI;
          (* idt operand to error_code is 0 because selector is used *)
       NewRSP <- 8 bytes loaded from (current TSS base + TSSstackAddress);
       NewSS <- new code-segment DPL; (* NULL selector with RPL = new CPL *)
  FI;
  IF IDT gate is 32-bit
       THEN
          IF new stack does not have room for 24 bytes (error code pushed)
          or 20 bytes (no error code pushed)
             THEN #SS(error_code(NewSS,0,EXT)); FI;
             (* idt operand to error_code is 0 because selector is used *)
       FI
     ELSE
       IF IDT gate is 16-bit
          THEN
             IF new stack does not have room for 12 bytes (error code pushed)
             or 10 bytes (no error code pushed);
               THEN #SS(error_code(NewSS,0,EXT)); FI;
               (* idt operand to error_code is 0 because selector is used *)
       ELSE (* 64-bit IDT gate*)
          IF StackAddress is non-canonical
             THEN #SS(EXT); FI; (* Error code contains NULL selector *)
     FI;
  FI;
  IF (IA32_EFER.LMA = 0) (* Not IA-32e mode *)
     THEN
       IF instruction pointer from IDT gate is not within new code-segment limits
          THEN #GP(EXT); FI; (* Error code contains NULL selector *)
       ESP <- NewESP;
       SS <- NewSS; (* Segment descriptor information also loaded *)
     ELSE (* IA-32e mode *)
       IF instruction pointer from IDT gate contains a non-canonical address
          THEN #GP(EXT); FI; (* Error code contains NULL selector *)
       RSP <- NewRSP & FFFFFFFFFFFFFFF0H;
       SS <- NewSS;
  FI;
  IF IDT gate is 32-bit
     THEN
       CS:EIP <- Gate(CS:EIP); (* Segment descriptor information also loaded *)
     ELSE
       IF IDT gate 16-bit
          THEN
             CS:IP <- Gate(CS:IP);
             (* Segment descriptor information also loaded *)
          ELSE (* 64-bit IDT gate *)
             CS:RIP <- Gate(CS:RIP);
             (* Segment descriptor information also loaded *)
       FI;
  FI;
  IF IDT gate is 32-bit
       THEN
          Push(far pointer to old stack);
          (* Old SS and ESP, 3 words padded to 4 *)
          Push(EFLAGS);
          Push(far pointer to return instruction);
          (* Old CS and EIP, 3 words padded to 4 *)
          Push(ErrorCode); (* If needed, 4 bytes *)
       ELSE
          IF IDT gate 16-bit
             THEN
               Push(far pointer to old stack);
               (* Old SS and SP, 2 words *)
               Push(EFLAGS(15-0]);
               Push(far pointer to return instruction);
               (* Old CS and IP, 2 words *)
               Push(ErrorCode); (* If needed, 2 bytes *)
             ELSE (* 64-bit IDT gate *)
               Push(far pointer to old stack);
               (* Old SS and SP, each an 8-byte push *)
               Push(RFLAGS); (* 8-byte push *)
               Push(far pointer to return instruction);
               (* Old CS and RIP, each an 8-byte push *)
               Push(ErrorCode); (* If needed, 8-bytes *)
       FI;
  FI;
  CPL <- new code-segment DPL;
  CS(RPL) <- CPL;
  IF IDT gate is interrupt gate
     THEN IF <- 0 (* Interrupt flag set to 0, interrupts disabled *); FI;
  TF <- 0;
  VM <- 0;
  RF <- 0;
  NT <- 0;
END;
INTERRUPT-FROM-VIRTUAL-8086-MODE:
  (* Identify stack-segment selector for privilege level 0 in current TSS *)
  IF current TSS is 32-bit
     THEN
       IF TSS limit < 9
          THEN #TS(error_code(current TSS selector,0,EXT)); FI;
          (* idt operand to error_code is 0 because selector is used *)
       NewSS <- 2 bytes loaded from (current TSS base + 8);
       NewESP <- 4 bytes loaded from (current TSS base + 4);
     ELSE (* current TSS is 16-bit *)
       IF TSS limit < 5
          THEN #TS(error_code(current TSS selector,0,EXT)); FI;
          (* idt operand to error_code is 0 because selector is used *)
       NewSS <- 2 bytes loaded from (current TSS base + 4);
       NewESP <- 2 bytes loaded from (current TSS base + 2);
  FI;
  IF NewSS is NULL
     THEN #TS(EXT); FI; (* Error code contains NULL selector *)
  IF NewSS index is not within its descriptor table limits
  or NewSS RPL != 0
     THEN #TS(error_code(NewSS,0,EXT)); FI;
     (* idt operand to error_code is 0 because selector is used *)
  Read new stack-segment descriptor for NewSS in GDT or LDT;
  IF new stack-segment DPL != 0 or stack segment does not indicate writable data segment
     THEN #TS(error_code(NewSS,0,EXT)); FI;
     (* idt operand to error_code is 0 because selector is used *)
  IF new stack segment not present
     THEN #SS(error_code(NewSS,0,EXT)); FI;
     (* idt operand to error_code is 0 because selector is used *)
  IF IDT gate is 32-bit
     THEN
       IF new stack does not have room for 40 bytes (error code pushed)
       or 36 bytes (no error code pushed)
          THEN #SS(error_code(NewSS,0,EXT)); FI;
          (* idt operand to error_code is 0 because selector is used *)
     ELSE (* IDT gate is 16-bit)
       IF new stack does not have room for 20 bytes (error code pushed)
       or 18 bytes (no error code pushed)
          THEN #SS(error_code(NewSS,0,EXT)); FI;
          (* idt operand to error_code is 0 because selector is used *)
  FI;
  IF instruction pointer from IDT gate is not within new code-segment limits
     THEN #GP(EXT); FI; (* Error code contains NULL selector *)
  tempEFLAGS <- EFLAGS;
  VM <- 0;
  TF <- 0;
  RF <- 0;
  NT <- 0;
  IF service through interrupt gate
     THEN IF = 0; FI;
  TempSS <- SS;
  TempESP <- ESP;
  SS <- NewSS;
  ESP <- NewESP;
  (* Following pushes are 16 bits for 16-bit IDT gates and 32 bits for 32-bit IDT gates;
  Segment selector pushes in 32-bit mode are padded to two words *)
  Push(GS);
  Push(FS);
  Push(DS);
  Push(ES);
  Push(TempSS);
  Push(TempESP);
  Push(TempEFlags);
  Push(CS);
  Push(EIP);
  GS <- 0; (* Segment registers made NULL, invalid for use in protected mode *)
  FS <- 0;
  DS <- 0;
  ES <- 0;
  CS:IP <- Gate(CS); (* Segment descriptor information also loaded *)
  IF OperandSize = 32
     THEN
       EIP <- Gate(instruction pointer);
     ELSE (* OperandSize is 16 *)
       EIP <- Gate(instruction pointer) AND 0000FFFFH;
  FI;
  (* Start execution of new routine in Protected Mode *)
END;
INTRA-PRIVILEGE-LEVEL-INTERRUPT:
  (* PE = 1, DPL = CPL or conforming segment *)
  IF IA32_EFER.LMA = 1 (* IA-32e mode *)
     IF IDT-descriptor IST != 0
       THEN
          TSSstackAddress <- (IDT-descriptor IST « 3) + 28;
          IF (TSSstackAddress + 7) > TSS limit
             THEN #TS(error_code(current TSS selector,0,EXT)); FI;
             (* idt operand to error_code is 0 because selector is used *)
          NewRSP <- 8 bytes loaded from (current TSS base + TSSstackAddress);
  FI;
  IF 32-bit gate (* implies IA32_EFER.LMA = 0 *)
     THEN
       IF current stack does not have room for 16 bytes (error code pushed)
       or 12 bytes (no error code pushed)
          THEN #SS(EXT); FI; (* Error code contains NULL selector *)
     ELSE IF 16-bit gate (* implies IA32_EFER.LMA = 0 *)
       IF current stack does not have room for 8 bytes (error code pushed)
       or 6 bytes (no error code pushed)
          THEN #SS(EXT); FI; (* Error code contains NULL selector *)
     ELSE (* IA32_EFER.LMA = 1, 64-bit gate*)
          IF NewRSP contains a non-canonical address
             THEN #SS(EXT); (* Error code contains NULL selector *)
     FI;
  FI;
  IF (IA32_EFER.LMA = 0) (* Not IA-32e mode *)
     THEN
       IF instruction pointer from IDT gate is not within new code-segment limit
          THEN #GP(EXT); FI; (* Error code contains NULL selector *)
     ELSE
       IF instruction pointer from IDT gate contains a non-canonical address
          THEN #GP(EXT); FI; (* Error code contains NULL selector *)
       RSP <- NewRSP & FFFFFFFFFFFFFFF0H;
  FI;
  IF IDT gate is 32-bit (* implies IA32_EFER.LMA = 0 *)
     THEN
       Push (EFLAGS);
       Push (far pointer to return instruction); (* 3 words padded to 4 *)
       CS:EIP <- Gate(CS:EIP); (* Segment descriptor information also loaded *)
       Push (ErrorCode); (* If any *)
     ELSE
       IF IDT gate is 16-bit (* implies IA32_EFER.LMA = 0 *)
          THEN
             Push (FLAGS);
             Push (far pointer to return location); (* 2 words *)
             CS:IP <- Gate(CS:IP);
             (* Segment descriptor information also loaded *)
             Push (ErrorCode); (* If any *)
          ELSE (* IA32_EFER.LMA = 1, 64-bit gate*)
             Push(far pointer to old stack);
             (* Old SS and SP, each an 8-byte push *)
             Push(RFLAGS); (* 8-byte push *)
             Push(far pointer to return instruction);
             (* Old CS and RIP, each an 8-byte push *)
             Push(ErrorCode); (* If needed, 8 bytes *)
             CS:RIP <- GATE(CS:RIP);
             (* Segment descriptor information also loaded *)
       FI;
  FI;
  CS(RPL) <- CPL;
  IF IDT gate is interrupt gate
     THEN IF <- 0; FI; (* Interrupt flag set to 0; interrupts disabled *)
  TF <- 0;
  NT <- 0;
  VM <- 0;
  RF <- 0;
END;

Flags Affected:
The EFLAGS register is pushed onto the stack. The IF, TF, NT, AC, RF, and VM
flags may be cleared, depending on the mode of operation of the processor when
the INT instruction is executed (see the “Operation” section). If the interrupt
uses a task gate, any flags may be set or cleared, controlled by the EFLAGS
image in the new task's TSS.


Protected Mode Exceptions:
| #GP(error_code)| If the instruction pointer in the IDT          
|                | or in the interrupt-, trap-, or task           
|                | gate is beyond the code segment limits.        
|                | If the segment selector in the interrupt-,     
|                | trap-, or task gate is NULL. If an interrupt-, 
|                | trap-, or task gate, code segment, or          
|                | TSS segment selector index is outside          
|                | its descriptor table limits. If the            
|                | interrupt vector number is outside the         
|                | IDT limits. If an IDT descriptor is            
|                | not an interrupt-, trap-, or task-descriptor.  
|                | If an interrupt is generated by the            
|                | INT n, INT 3, or INTO instruction and          
|                | the DPL of an interrupt-, trap-, or            
|                | task-descriptor is less than the CPL.          
|                | If the segment selector in an interrupt-       
|                | or trap-gate does not point to a segment       
|                | descriptor for a code segment. If the          
|                | segment selector for a TSS has its local/global
|                | bit set for local. If a TSS segment            
|                | descriptor specifies that the TSS is           
|                | busy or not available.                         
| #SS(error_code)| If pushing the return address, flags,          
|                | or error code onto the stack exceeds           
|                | the bounds of the stack segment and            
|                | no stack switch occurs. If the SS register     
|                | is being loaded and the segment pointed        
|                | to is marked not present.                      
If pushing the return address, flags, error code, or stack segment pointer exceeds
the bounds of the new stack segment when a stack switch occurs.

| #NP(error_code)| If code segment, interrupt-, trap-,          
|                | or task gate, or TSS is not present.         
| #TS(error_code)| If the RPL of the stack segment selector     
|                | in the TSS is not equal to the DPL of        
|                | the code segment being accessed by the       
|                | interrupt or trap gate. If DPL of the        
|                | stack segment descriptor pointed to          
|                | by the stack segment selector in the         
|                | TSS is not equal to the DPL of the code      
|                | segment descriptor for the interrupt         
|                | or trap gate. If the stack segment selector  
|                | in the TSS is NULL. If the stack segment     
|                | for the TSS is not a writable data segment.  
|                | If segment-selector index for stack          
|                | segment is outside descriptor table          
|                | limits.                                      
| #PF(fault-code)| If a page fault occurs.                      
| #UD            | If the LOCK prefix is used.                  
| #AC(EXT)       | If alignment checking is enabled, the        
|                | gate DPL is 3, and a stack push is unaligned.

Real-Address Mode Exceptions:
| #GP| If a memory operand effective address 
|    | is outside the CS, DS, ES, FS, or GS  
|    | segment limit. If the interrupt vector
|    | number is outside the IDT limits.     
| #SS| If stack limit violation on push. If  
|    | pushing the return address, flags, or 
|    | error code onto the stack exceeds the 
|    | bounds of the stack segment.          
| #UD| If the LOCK prefix is used.           

Virtual-8086 Mode Exceptions:
| #GP(error_code)| (For INT n, INTO, or BOUND instruction)         
|                | If the IOPL is less than 3 or the DPL           
|                | of the interrupt, trap-, or task-gate           
|                | descriptor is not equal to 3. If the            
|                | instruction pointer in the IDT or in            
|                | the interrupt-, trap-, or task gate             
|                | is beyond the code segment limits. If           
|                | the segment selector in the interrupt-,         
|                | trap-, or task gate is NULL. If a interrupt-,   
|                | trap-, or task gate, code segment, or           
|                | TSS segment selector index is outside           
|                | its descriptor table limits. If the             
|                | interrupt vector number is outside the          
|                | IDT limits. If an IDT descriptor is             
|                | not an interrupt-, trap-, or task-descriptor.   
|                | If an interrupt is generated by the             
|                | INT n instruction and the DPL of an             
|                | interrupt-, trap-, or taskdescriptor            
|                | is less than the CPL. If the segment            
|                | selector in an interrupt- or trap-gate          
|                | does not point to a segment descriptor          
|                | for a code segment. If the segment selector     
|                | for a TSS has its local/global bit set          
|                | for local.                                      
| #SS(error_code)| If the SS register is being loaded and          
|                | the segment pointed to is marked not            
|                | present. If pushing the return address,         
|                | flags, error code, stack segment pointer,       
|                | or data segments exceeds the bounds             
|                | of the stack segment.                           
| #NP(error_code)| If code segment, interrupt-, trap-,             
|                | or task gate, or TSS is not present.            
| #TS(error_code)| If the RPL of the stack segment selector        
|                | in the TSS is not equal to the DPL of           
|                | the code segment being accessed by the          
|                | interrupt or trap gate. If DPL of the           
|                | stack segment descriptor for the TSS's          
|                | stack segment is not equal to the DPL           
|                | of the code segment descriptor for the          
|                | interrupt or trap gate. If the stack            
|                | segment selector in the TSS is NULL.            
|                | If the stack segment for the TSS is             
|                | not a writable data segment. If segment-selector
|                | index for stack segment is outside descriptor   
|                | table limits.                                   
| #PF(fault-code)| If a page fault occurs.                         
| #BP            | If the INT 3 instruction is executed.           
| #OF            | If the INTO instruction is executed             
|                | and the OF flag is set.                         
| #UD            | If the LOCK prefix is used.                     
| #AC(EXT)       | If alignment checking is enabled, the           
|                | gate DPL is 3, and a stack push is unaligned.   

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #GP(error_code)| If the instruction pointer in the 64-bit     
|                | interrupt gate or 64-bit trap gate is        
|                | non-canonical. If the segment selector       
|                | in the 64-bit interrupt or trap gate         
|                | is NULL. If the interrupt vector number      
|                | is outside the IDT limits. If the interrupt  
|                | vector number points to a gate which         
|                | is in non-canonical space. If the interrupt  
|                | vector number points to a descriptor         
|                | which is not a 64-bit interrupt gate         
|                | or 64bit trap gate. If the descriptor        
|                | pointed to by the gate selector is outside   
|                | the descriptor table limit. If the descriptor
|                | pointed to by the gate selector is in        
|                | non-canonical space. If the descriptor       
|                | pointed to by the gate selector is not       
|                | a code segment. If the descriptor pointed    
|                | to by the gate selector doesn't have         
|                | the L-bit set, or has both the Lbit          
|                | and D-bit set. If the descriptor pointed     
|                | to by the gate selector has DPL > CPL.       
| #SS(error_code)| If a push of the old EFLAGS, CS selector,    
|                | EIP, or error code is in non-canonical       
|                | space with no stack switch. If a push        
|                | of the old SS selector, ESP, EFLAGS,         
|                | CS selector, EIP, or error code is in        
|                | non-canonical space on a stack switch        
|                | (either CPL change or no-CPL with IST).      
| #NP(error_code)| If the 64-bit interrupt-gate, 64-bit         
|                | trap-gate, or code segment is not present.   
| #TS(error_code)| If an attempt to load RSP from the TSS       
|                | causes an access to non-canonical space.     
|                | If the RSP from the TSS is outside descriptor
|                | table limits.                                
| #PF(fault-code)| If a page fault occurs.                      
| #UD            | If the LOCK prefix is used.                  
| #AC(EXT)       | If alignment checking is enabled, the        
|                | gate DPL is 3, and a stack push is unaligned.


platform: x86
mnem: INVD
description:
INVD - Invalidate Internal Caches:
| Opcode| Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                             
| 0F 08 | INVD       | NP   | Valid      | Valid          | Flush internal caches; initiate flushing
|       |            |      |            |                | of external caches.                     
Notes: * See the IA-32 Architecture Compatibility section below.


Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| NP   | NA       | NA       | NA       | NA       

Description:
Invalidates (flushes) the processor's internal caches and issues a special-function
bus cycle that directs external caches to also flush themselves. Data held in
internal caches is not written back to main memory.

After executing this instruction, the processor does not wait for the external
caches to complete their flushing operation before proceeding with instruction
execution. It is the responsibility of hardware to respond to the cache flush
signal.

The INVD instruction is a privileged instruction. When the processor is running
in protected mode, the CPL of a program or procedure must be 0 to execute this
instruction.

The INVD instruction may be used when the cache is used as temporary memory
and the cache contents need to be invalidated rather than written back to memory.
When the cache is used as temporary memory, no external device should be actively
writing data to main memory.

Use this instruction with care. Data cached internally and not written back
to main memory will be lost. Note that any data from an external device to main
memory (for example, via a PCIWrite) can be temporarily stored in the caches;
these data can be lost when an INVD instruction is executed. Unless there is
a specific requirement or benefit to flushing caches without writing back modified
cache lines (for example, temporary memory, testing, or fault recovery where
cache coherency with main memory is not a concern), software should instead
use the WBINVD instruction.

This instruction's operation is the same in non-64-bit modes and 64-bit mode.


IA-32 Architecture Compatibility:
The INVD instruction is implementation dependent; it may be implemented differently
on different families of Intel 64 or IA-32 processors. This instruction is not
supported on IA-32 processors earlier than the Intel486 processor.

Operation:

Flush(InternalCaches);
SignalFlush(ExternalCaches);
Continue (* Continue execution *)

Flags Affected:
None.


Protected Mode Exceptions:
| #GP(0)| If the current privilege level is not
|       | 0.                                   
| #UD   | If the LOCK prefix is used.          

Real-Address Mode Exceptions:
| #UD| If the LOCK prefix is used.

Virtual-8086 Mode Exceptions:
| #GP(0)| The INVD instruction cannot be executed
|       | in virtual-8086 mode.                  

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
Same exceptions as in protected mode.


platform: x86
mnem: INVLPG
description:
INVLPG - Invalidate TLB Entry:
| Opcode | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                                
| 0F 01/7| INVLPG m   | M    | Valid      | Valid          | Invalidate TLB Entry for page that contains
|        |            |      |            |                | m.                                         
Notes: * See the IA-32 Architecture Compatibility section below.


Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2| Operand 3| Operand 4
| M    | ModRM:r/m (r)| NA       | NA       | NA       

Description:
Invalidates (flushes) the translation lookaside buffer (TLB) entry specified
with the source operand. The source operand is a memory address. The processor
determines the page that contains that address and flushes the TLB entry for
that page.

The INVLPG instruction is a privileged instruction. When the processor is running
in protected mode, the CPL must be 0 to execute this instruction.

The INVLPG instruction normally flushes the TLB entry only for the specified
page; however, in some cases, it may flush more entries, even the entire TLB.
The instruction is guaranteed to invalidates only TLB entries associated with
the current PCID. (If PCIDs are disabled  -  CR4.PCIDE = 0  -  the current PCID
is 000H.) The instruction also invalidates any global TLB entries for the specified
page, regardless of PCID.

For more details on operations that flush the TLB, see “MOV - Move to/from Control
Registers” and Section 4.10.4.1, “Operations that Invalidate TLBs and Paging-Structure
Caches,” of the Intel® 64 and IA-32 Architectures Software Developer's Manual,
Volume 3A.

This instruction's operation is the same in all non-64-bit modes. It also operates
the same in 64-bit mode, except if the memory address is in non-canonical form.
In this case, INVLPG is the same as a NOP.


IA-32 Architecture Compatibility:
The INVLPG instruction is implementation dependent, and its function may be
implemented differently on different families of Intel 64 or IA-32 processors.
This instruction is not supported on IA-32 processors earlier than the Intel486
processor.

Operation:

Flush(RelevantTLBEntries);
Continue; (* Continue execution *)

Flags Affected:
None.


Protected Mode Exceptions:
| #GP(0)| If the current privilege level is not    
|       | 0.                                       
| #UD   | Operand is a register. If the LOCK prefix
|       | is used.                                 

Real-Address Mode Exceptions:
| #UD| Operand is a register. If the LOCK prefix
|    | is used.                                 

Virtual-8086 Mode Exceptions:
| #GP(0)| The INVLPG instruction cannot be executed
|       | at the virtual-8086 mode.                

64-Bit Mode Exceptions:
| #GP(0)| If the current privilege level is not    
|       | 0.                                       
| #UD   | Operand is a register. If the LOCK prefix
|       | is used.                                 


platform: x86
mnem: INVPCID
description:
INVPCID - Invalidate Process-Context Identifier:
| Opcode/Instruction              | Op/En| 64/32bit Mode| CPUID Feature Flag| Description                                  
| 66 0F 38 82 /r INVPCID r32, m128| RM   | NE/V         | INVPCID           | Invalidates entries in the TLBs and          
|                                 |      |              |                   | paging-structure caches based on invalidation
|                                 |      |              |                   | type in r32 and descriptor in m128.          
| 66 0F 38 82 /r INVPCID r64, m128| RM   | V/NE         | INVPCID           | Invalidates entries in the TLBs and          
|                                 |      |              |                   | paging-structure caches based on invalidation
|                                 |      |              |                   | type in r64 and descriptor in m128.          

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (R)| ModRM:r/m (R)| NA       | NA       

Description:
Invalidates mappings in the translation lookaside buffers (TLBs) and paging-structure
caches based on processcontext identifier (PCID). (See Section 4.10, “Caching
Translation Information,” in Intel 64 and IA-32 Architecture Software Developer's
Manual, Volume 3A.) Invalidation is based on the INVPCID type specified in the
register operand and the INVPCID descriptor specified in the memory operand.

Outside 64-bit mode, the register operand is always 32 bits, regardless of the
value of CS.D. In 64-bit mode the register operand has 64 bits.

There are four INVPCID types currently defined:

 - Individual-address invalidation: If the INVPCID type is 0, the logical processor
invalidates mappings - except global translations - for the linear address and PCID
specified in the INVPCID descriptor. In some cases, the instruction may invalidate
global translations or mappings for other linear addresses (or other PCIDs)
as well.
 - Single-context invalidation: If the INVPCID type is 1, the logical processor
invalidates all mappings - except global translations - associated with the PCID
specified in the INVPCID descriptor. In some cases, the instruction may invalidate
global translations or mappings for other PCIDs as well.
 - All-context invalidation, including global translations: If the INVPCID type
is 2, the logical processor invalidates all mappings - including global translations - associated
with any PCID.
 - All-context invalidation: If the INVPCID type is 3, the logical processor invalidates
all mappings - except global translations - associated with any PCID. In some case,
the instruction may invalidate global translations as well.

The INVPCID descriptor comprises 128 bits and consists of a PCID and a linear
address as shown in Figure 3-23. For INVPCID type 0, the processor uses the
full 64 bits of the linear address even outside 64-bit mode; the linear address
is not used for other INVPCID types.

| 127 Linear Address| 6463 Reserved (must be zero) Figure| 1211 PCID INVPCID Descriptor| 0
|                   | 3-23.                              |                             |  
If CR4.PCIDE = 0, a logical processor does not cache information for any PCID
other than 000H. In this case, executions with INVPCID types 0 and 1 are allowed
only if the PCID specified in the INVPCID descriptor is 000H;

executions with INVPCID types 2 and 3 invalidate mappings only for PCID 000H.
Note that CR4.PCIDE must be 0 outside 64-bit mode (see Chapter 4.10.1, “Process-Context
Identifiers (PCIDs)‚” of the Intel® 64 and IA-32 Architectures Software Developer's
Manual, Volume 3A).

Operation:

INVPCID_TYPE <- value of register operand;
INVPCID_DESC <- value of memory operand;
CASE INVPCID_TYPE OF
  0:
     PCID <- INVPCID_DESC[11:0];
     L_ADDR <- INVPCID_DESC[127:64];
     Invalidate mappings for L_ADDR associated with PCID except global translations;
     BREAK;
  1:
     PCID <- INVPCID_DESC[11:0];
     Invalidate all mappings associated with PCID except global translations;
     BREAK;
  2:
     Invalidate all mappings for all PCIDs, including global translations;
     BREAK;
  3:
     Invalidate all mappings for all PCIDs except global translations;
     BREAK;
ESAC;

Intel C/C++ Compiler Intrinsic Equivalent:
| INVPCID:| void _invpcid(unsigned __int32 type,
|         | void * descriptor);                 

SIMD Floating-Point Exceptions:
None


Protected Mode Exceptions:
| #GP(0)         | If the current privilege level is not     
|                | 0. If the memory operand effective address
|                | is outside the CS, DS, ES, FS, or GS      
|                | segment limit. If the DS, ES, FS, or      
|                | GS register contains an unusable segment. 
|                | If the source operand is located in       
|                | an execute-only code segment. If an       
|                | invalid type is specified in the register 
|                | operand, i.e., INVPCID_TYPE > 3. If       
|                | bits 63:12 of INVPCID_DESC are not all    
|                | zero. If INVPCID_TYPE is either 0 or      
|                | 1 and INVPCID_DESC[11:0] is not zero.     
|                | If INVPCID_TYPE is 0 and the linear       
|                | address in INVPCID_DESC[127:64] is not    
|                | canonical.                                
| #PF(fault-code)| If a page fault occurs in accessing       
|                | the memory operand.                       
| #SS(0)         | If the memory operand effective address   
|                | is outside the SS segment limit. If       
|                | the SS register contains an unusable      
|                | segment.                                  
| #UD            | If if CPUID.(EAX=07H, ECX=0H):EBX.INVPCID 
|                | (bit 10) = 0. If the LOCK prefix is       
|                | used.                                     

Real-Address Mode Exceptions:
| #GP| If an invalid type is specified in the
|    | register operand, i.e., INVPCID_TYPE  
|    | > 3. If bits 63:12 of INVPCID_DESC are
|    | not all zero.                         
If INVPCID_TYPE is either 0 or 1 and INVPCID_DESC[11:0] is not zero. If INVPCID_TYPE
is 0 and the linear address in INVPCID_DESC[127:64] is not canonical.

| #UD| If CPUID.(EAX=07H, ECX=0H):EBX.INVPCID
|    | (bit 10) = 0. If the LOCK prefix is   
|    | used.                                 

Virtual-8086 Mode Exceptions:
| #GP(0)| The INVPCID instruction is not recognized
|       | in virtual-8086 mode.                    

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #GP(0)         | If the current privilege level is not         
|                | 0. If the memory operand is in the CS,        
|                | DS, ES, FS, or GS segments and the memory     
|                | address is in a non-canonical form.           
|                | If an invalid type is specified in the        
|                | register operand, i.e., INVPCID_TYPE          
|                | > 3. If bits 63:12 of INVPCID_DESC are        
|                | not all zero. If CR4.PCIDE=0, INVPCID_TYPE    
|                | is either 0 or 1, and INVPCID_DESC[11:0]      
|                | is not zero. If INVPCID_TYPE is 0 and         
|                | the linear address in INVPCID_DESC[127:64]    
|                | is not canonical.                             
| #PF(fault-code)| If a page fault occurs in accessing           
|                | the memory operand.                           
| #SS(0)         | If the memory destination operand is          
|                | in the SS segment and the memory address      
|                | is in a noncanonical form.                    
| #UD            | If the LOCK prefix is used. If CPUID.(EAX=07H,
|                | ECX=0H):EBX.INVPCID (bit 10) = 0.             


platform: x86
mnem: IRET
description:
IRET/IRETD - Interrupt Return:
| Opcode    | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                            
| CF        | IRET       | NP   | Valid      | Valid          | Interrupt return (16-bit operand size).
| CF        | IRETD      | NP   | Valid      | Valid          | Interrupt return (32-bit operand size).
| REX.W + CF| IRETQ      | NP   | Valid      | N.E.           | Interrupt return (64-bit operand size).

Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| NP   | NA       | NA       | NA       | NA       

Description:
Returns program control from an exception or interrupt handler to a program
or procedure that was interrupted by an exception, an external interrupt, or
a software-generated interrupt. These instructions are also used to perform
a return from a nested task. (A nested task is created when a CALL instruction
is used to initiate a task switch or when an interrupt or exception causes a
task switch to an interrupt or exception handler.) See the section titled “Task
Linking” in Chapter 7 of the Intel® 64 and IA-32 Architectures Software Developer's
Manual, Volume 3A.

IRET and IRETD are mnemonics for the same opcode. The IRETD mnemonic (interrupt
return double) is intended for use when returning from an interrupt when using
the 32-bit operand size; however, most assemblers use the IRET mnemonic interchangeably
for both operand sizes.

In Real-Address Mode, the IRET instruction preforms a far return to the interrupted
program or procedure. During this operation, the processor pops the return instruction
pointer, return code segment selector, and EFLAGS image from the stack to the
EIP, CS, and EFLAGS registers, respectively, and then resumes execution of the
interrupted program or procedure.

In Protected Mode, the action of the IRET instruction depends on the settings
of the NT (nested task) and VM flags in the EFLAGS register and the VM flag
in the EFLAGS image stored on the current stack. Depending on the setting of
these flags, the processor performs the following types of interrupt returns:

 - Return from virtual-8086 mode.
 - Return to virtual-8086 mode.
 - Intra-privilege level return.
 - Inter-privilege level return.
 - Return from nested task (task switch).

If the NT flag (EFLAGS register) is cleared, the IRET instruction performs a
far return from the interrupt procedure, without a task switch. The code segment
being returned to must be equally or less privileged than the interrupt handler
routine (as indicated by the RPL field of the code segment selector popped from
the stack).

As with a real-address mode interrupt return, the IRET instruction pops the
return instruction pointer, return code segment selector, and EFLAGS image from
the stack to the EIP, CS, and EFLAGS registers, respectively, and then resumes
execution of the interrupted program or procedure. If the return is to another
privilege level, the IRET instruction also pops the stack pointer and SS from
the stack, before resuming program execution. If the return is to virtual-8086
mode, the processor also pops the data segment registers from the stack.

If the NT flag is set, the IRET instruction performs a task switch (return)
from a nested task (a task called with a CALL instruction, an interrupt, or
an exception) back to the calling or interrupted task. The updated state of
the task executing the IRET instruction is saved in its TSS. If the task is
re-entered later, the code that follows the IRET instruction is executed.

If the NT flag is set and the processor is in IA-32e mode, the IRET instruction
causes a general protection exception.

In 64-bit mode, the instruction's default operation size is 32 bits. Use of
the REX.W prefix promotes operation to 64 bits (IRETQ). See the summary chart
at the beginning of this section for encoding data and limits.

See “Changes to Instruction Behavior in VMX Non-Root Operation” in Chapter 25
of the Intel® 64 and IA-32 Architectures Software Developer's Manual, Volume
3C, for more information about the behavior of this instruction in VMX non-root
operation.

Operation:

IF PE = 0
  THEN
     GOTO REAL-ADDRESS-MODE;
  ELSE
     IF (IA32_EFER.LMA = 0)
          THEN (* Protected mode *)
             GOTO PROTECTED-MODE;
          ELSE (* IA-32e mode *)
             GOTO IA-32e-MODE;
     FI;
FI;
REAL-ADDRESS-MODE;
  IF OperandSize = 32
     THEN
       IF top 12 bytes of stack not within stack limits
          THEN #SS; FI;
       tempEIP <- 4 bytes at end of stack
       IF tempEIP[31:16] is not zero THEN #GP(0); FI;
       EIP <- Pop();
       CS <- Pop(); (* 32-bit pop, high-order 16 bits discarded *)
       tempEFLAGS <- Pop();
       EFLAGS <- (tempEFLAGS AND 257FD5H) OR (EFLAGS AND 1A0000H);
     ELSE (* OperandSize = 16 *)
       IF top 6 bytes of stack are not within stack limits
          THEN #SS; FI;
       EIP <- Pop(); (* 16-bit pop; clear upper 16 bits *)
       CS <- Pop(); (* 16-bit pop *)
       EFLAGS[15:0] <- Pop();
  FI;
  END;
PROTECTED-MODE:
  IF VM = 1 (* Virtual-8086 mode: PE = 1, VM = 1 *)
     THEN
       GOTO RETURN-FROM-VIRTUAL-8086-MODE; (* PE = 1, VM = 1 *)
  FI;
  IF NT = 1
     THEN
       GOTO TASK-RETURN; (* PE = 1, VM = 0, NT = 1 *)
  FI;
  IF OperandSize = 32
     THEN
       IF top 12 bytes of stack not within stack limits
          THEN #SS(0); FI;
       tempEIP <- Pop();
       tempCS <- Pop();
       tempEFLAGS <- Pop();
     ELSE (* OperandSize = 16 *)
       IF top 6 bytes of stack are not within stack limits
          THEN #SS(0); FI;
       tempEIP <- Pop();
       tempCS <- Pop();
       tempEFLAGS <- Pop();
       tempEIP <- tempEIP AND FFFFH;
       tempEFLAGS <- tempEFLAGS AND FFFFH;
  FI;
  IF tempEFLAGS(VM) = 1 and CPL = 0
     THEN
       GOTO RETURN-TO-VIRTUAL-8086-MODE;
     ELSE
       GOTO PROTECTED-MODE-RETURN;
  FI;
IA-32e-MODE:
  IF NT = 1
     THEN #GP(0);
  ELSE IF OperandSize = 32
     THEN
       IF top 12 bytes of stack not within stack limits
          THEN #SS(0); FI;
       tempEIP <- Pop();
       tempCS <- Pop();
       tempEFLAGS <- Pop();
     ELSE IF OperandSize = 16
       THEN
          IF top 6 bytes of stack are not within stack limits
             THEN #SS(0); FI;
          tempEIP <- Pop();
          tempCS <- Pop();
          tempEFLAGS <- Pop();
          tempEIP <- tempEIP AND FFFFH;
          tempEFLAGS <- tempEFLAGS AND FFFFH;
       FI;
     ELSE (* OperandSize = 64 *)
       THEN
             tempRIP <- Pop();
             tempCS <- Pop();
             tempEFLAGS <- Pop();
             tempRSP <- Pop();
             tempSS <- Pop();
  FI;
  GOTO IA-32e-MODE-RETURN;
RETURN-FROM-VIRTUAL-8086-MODE:
(* Processor is in virtual-8086 mode when IRET is executed and stays in virtual-8086 mode *)
  IF IOPL = 3 (* Virtual mode: PE = 1, VM = 1, IOPL = 3 *)
     THEN IF OperandSize = 32
       THEN
          IF top 12 bytes of stack not within stack limits
             THEN #SS(0); FI;
          IF instruction pointer not within code segment limits
             THEN #GP(0); FI;
          EIP <- Pop();
          CS <- Pop(); (* 32-bit pop, high-order 16 bits discarded *)
          EFLAGS <- Pop();
          (* VM, IOPL,VIP and VIF EFLAG bits not modified by pop *)
       ELSE (* OperandSize = 16 *)
          IF top 6 bytes of stack are not within stack limits
             THEN #SS(0); FI;
          IF instruction pointer not within code segment limits
             THEN #GP(0); FI;
          EIP <- Pop();
          EIP <- EIP AND 0000FFFFH;
          CS <- Pop(); (* 16-bit pop *)
          EFLAGS[15:0] <- Pop(); (* IOPL in EFLAGS not modified by pop *)
       FI;
     ELSE
       #GP(0); (* Trap to virtual-8086 monitor: PE = 1, VM = 1, IOPL < 3 *)
  FI;
END;
RETURN-TO-VIRTUAL-8086-MODE:
  (* Interrupted procedure was in virtual-8086 mode: PE = 1, CPL=0, VM = 1 in flag image *)
  IF top 24 bytes of stack are not within stack segment limits
     THEN #SS(0); FI;
  IF instruction pointer not within code segment limits
     THEN #GP(0); FI;
  CS <- tempCS;
  EIP <- tempEIP & FFFFH;
  EFLAGS <- tempEFLAGS;
  TempESP <- Pop();
  TempSS <- Pop();
  ES <- Pop(); (* Pop 2 words; throw away high-order word *)
  DS <- Pop(); (* Pop 2 words; throw away high-order word *)
  FS <- Pop(); (* Pop 2 words; throw away high-order word *)
  GS <- Pop(); (* Pop 2 words; throw away high-order word *)
  SS:ESP <- TempSS:TempESP;
  CPL <- 3;
  (* Resume execution in Virtual-8086 mode *)
END;
TASK-RETURN: (* PE = 1, VM = 0, NT = 1 *)
  Read segment selector in link field of current TSS;
  IF local/global bit is set to local
  or index not within GDT limits
     THEN #TS (TSS selector); FI;
  Access TSS for task specified in link field of current TSS;
  IF TSS descriptor type is not TSS or if the TSS is marked not busy
     THEN #TS (TSS selector); FI;
  IF TSS not present
     THEN #NP(TSS selector); FI;
  SWITCH-TASKS (without nesting) to TSS specified in link field of current TSS;
  Mark the task just abandoned as NOT BUSY;
  IF EIP is not within code segment limit
     THEN #GP(0); FI;
END;
PROTECTED-MODE-RETURN: (* PE = 1 *)
  IF return code segment selector is NULL
     THEN GP(0); FI;
  IF return code segment selector addresses descriptor beyond descriptor table limit
     THEN GP(selector); FI;
  Read segment descriptor pointed to by the return code segment selector;
  IF return code segment descriptor is not a code segment
     THEN #GP(selector); FI;
  IF return code segment selector RPL < CPL
     THEN #GP(selector); FI;
  IF return code segment descriptor is conforming
  and return code segment DPL > return code segment selector RPL
     THEN #GP(selector); FI;
  IF return code segment descriptor is not present
     THEN #NP(selector); FI;
  IF return code segment selector RPL > CPL
     THEN GOTO RETURN-OUTER-PRIVILEGE-LEVEL;
     ELSE GOTO RETURN-TO-SAME-PRIVILEGE-LEVEL; FI;
END;
RETURN-TO-SAME-PRIVILEGE-LEVEL: (* PE = 1, RPL = CPL *)
  IF new mode != 64-Bit Mode
     THEN
       IF tempEIP is not within code segment limits
          THEN #GP(0); FI;
       EIP <- tempEIP;
     ELSE (* new mode = 64-bit mode *)
       IF tempRIP is non-canonical
             THEN #GP(0); FI;
       RIP <- tempRIP;
  FI;
  CS <- tempCS; (* Segment descriptor information also loaded *)
  EFLAGS (CF, PF, AF, ZF, SF, TF, DF, OF, NT) <- tempEFLAGS;
  IF OperandSize = 32 or OperandSize = 64
     THEN EFLAGS(RF, AC, ID) <- tempEFLAGS; FI;
  IF CPL ≤ IOPL
     THEN EFLAGS(IF) <- tempEFLAGS; FI;
  IF CPL = 0
     THEN (* VM = 0 in flags image *)
     EFLAGS(IOPL) <- tempEFLAGS;
     IF OperandSize = 32 or OperandSize = 64
       THEN EFLAGS(VIF, VIP) <- tempEFLAGS; FI;
  FI;
END;
RETURN-TO-OUTER-PRIVILEGE-LEVEL:
  IF OperandSize = 32
     THEN
       IF top 8 bytes on stack are not within limits
          THEN #SS(0); FI;
     ELSE (* OperandSize = 16 *)
       IF top 4 bytes on stack are not within limits
          THEN #SS(0); FI;
  FI;
  Read return segment selector;
  IF stack segment selector is NULL
     THEN #GP(0); FI;
  IF return stack segment selector index is not within its descriptor table limits
     THEN #GP(SSselector); FI;
  Read segment descriptor pointed to by return segment selector;
  IF stack segment selector RPL != RPL of the return code segment selector
  or the stack segment descriptor does not indicate a a writable data segment;
  or the stack segment DPL != RPL of the return code segment selector
     THEN #GP(SS selector); FI;
  IF stack segment is not present
     THEN #SS(SS selector); FI;
  IF new mode != 64-Bit Mode
     THEN
       IF tempEIP is not within code segment limits
          THEN #GP(0); FI;
       EIP <- tempEIP;
     ELSE (* new mode = 64-bit mode *)
       IF tempRIP is non-canonical
             THEN #GP(0); FI;
       RIP <- tempRIP;
  FI;
  CS <- tempCS;
  EFLAGS (CF, PF, AF, ZF, SF, TF, DF, OF, NT) <- tempEFLAGS;
  IF OperandSize = 32
     THEN EFLAGS(RF, AC, ID) <- tempEFLAGS; FI;
  IF CPL ≤ IOPL
     THEN EFLAGS(IF) <- tempEFLAGS; FI;
  IF CPL = 0
     THEN
       EFLAGS(IOPL) <- tempEFLAGS;
       IF OperandSize = 32
          THEN EFLAGS(VM, VIF, VIP) <- tempEFLAGS; FI;
       IF OperandSize = 64
          THEN EFLAGS(VIF, VIP) <- tempEFLAGS; FI;
  FI;
  CPL <- RPL of the return code segment selector;
  FOR each of segment register (ES, FS, GS, and DS)
     DO
       IF segment register points to data or non-conforming code segment
       and CPL > segment descriptor DPL (* Stored in hidden part of segment register *)
          THEN (* Segment register invalid *)
             SegmentSelector <- 0; (* NULL segment selector *)
       FI;
     OD;
END;
IA-32e-MODE-RETURN: (* IA32_EFER.LMA = 1, PE = 1 *)
  IF ( (return code segment selector is NULL) or (return RIP is non-canonical) or
       (SS selector is NULL going back to compatibility mode) or
       (SS selector is NULL going back to CPL3 64-bit mode) or
       (RPL <> CPL going back to non-CPL3 64-bit mode for a NULL SS selector) )
     THEN GP(0); FI;
  IF return code segment selector addresses descriptor beyond descriptor table limit
     THEN GP(selector); FI;
  Read segment descriptor pointed to by the return code segment selector;
  IF return code segment descriptor is not a code segment
     THEN #GP(selector); FI;
  IF return code segment selector RPL < CPL
     THEN #GP(selector); FI;
  IF return code segment descriptor is conforming
  and return code segment DPL > return code segment selector RPL
     THEN #GP(selector); FI;
  IF return code segment descriptor is not present
     THEN #NP(selector); FI;
  IF return code segment selector RPL > CPL
     THEN GOTO RETURN-OUTER-PRIVILEGE-LEVEL;
     ELSE GOTO RETURN-TO-SAME-PRIVILEGE-LEVEL; FI;
END;

Flags Affected:
All the flags and fields in the EFLAGS register are potentially modified, depending
on the mode of operation of the processor. If performing a return from a nested
task to a previous task, the EFLAGS register will be modified according to the
EFLAGS image stored in the previous task's TSS.


Protected Mode Exceptions:
| #GP(0)         | If the return code or stack segment               
|                | selector is NULL. If the return instruction       
|                | pointer is not within the return code             
|                | segment limit.                                    
| #GP(selector)  | If a segment selector index is outside            
|                | its descriptor table limits. If the               
|                | return code segment selector RPL is               
|                | less than the CPL. If the DPL of a conforming-code
|                | segment is greater than the return code           
|                | segment selector RPL. If the DPL for              
|                | a nonconforming-code segment is not               
|                | equal to the RPL of the code segment              
|                | selector. If the stack segment descriptor         
|                | DPL is not equal to the RPL of the return         
|                | code segment selector. If the stack               
|                | segment is not a writable data segment.           
|                | If the stack segment selector RPL is              
|                | not equal to the RPL of the return code           
|                | segment selector. If the segment descriptor       
|                | for a code segment does not indicate              
|                | it is a code segment. If the segment              
|                | selector for a TSS has its local/global           
|                | bit set for local. If a TSS segment               
|                | descriptor specifies that the TSS is              
|                | not busy. If a TSS segment descriptor             
|                | specifies that the TSS is not available.          
| #SS(0)         | If the top bytes of stack are not within          
|                | stack limits.                                     
| #NP(selector)  | If the return code or stack segment               
|                | is not present.                                   
| #PF(fault-code)| If a page fault occurs.                           
| #AC(0)         | If an unaligned memory reference occurs           
|                | when the CPL is 3 and alignment checking          
|                | is enabled.                                       
| #UD            | If the LOCK prefix is used.                       

Real-Address Mode Exceptions:
| #GP| If the return instruction pointer is     
|    | not within the return code segment limit.
| #SS| If the top bytes of stack are not within 
|    | stack limits.                            

Virtual-8086 Mode Exceptions:
| #GP(0)| If the return instruction pointer is     
|       | not within the return code segment limit.
IF IOPL not equal to 3.

| #PF(fault-code)| If a page fault occurs.                 
| #SS(0)         | If the top bytes of stack are not within
|                | stack limits.                           
| #AC(0)         | If an unaligned memory reference occurs 
|                | and alignment checking is enabled.      
| #UD            | If the LOCK prefix is used.             

Compatibility Mode Exceptions:
| #GP(0) Other exceptions same as in Protected| If EFLAGS.NT[bit 14] = 1.
| Mode.                                       |                          

64-Bit Mode Exceptions:
| #GP(0)         | If EFLAGS.NT[bit 14] = 1. If the return    
|                | code segment selector is NULL. If the      
|                | stack segment selector is NULL going       
|                | back to compatibility mode. If the stack   
|                | segment selector is NULL going back        
|                | to CPL3 64-bit mode. If a NULL stack       
|                | segment selector RPL is not equal to       
|                | CPL going back to non-CPL3 64-bit mode.    
|                | If the return instruction pointer is       
|                | not within the return code segment limit.  
|                | If the return instruction pointer is       
|                | non-canonical.                             
| #GP(Selector)  | If a segment selector index is outside     
|                | its descriptor table limits. If a segment  
|                | descriptor memory address is non-canonical.
|                | If the segment descriptor for a code       
|                | segment does not indicate it is a code     
|                | segment. If the proposed new code segment  
|                | descriptor has both the D-bit and L-bit    
|                | set. If the DPL for a nonconforming-code   
|                | segment is not equal to the RPL of the     
|                | code segment selector. If CPL is greater   
|                | than the RPL of the code segment selector. 
|                | If the DPL of a conforming-code segment    
|                | is greater than the return code segment    
|                | selector RPL. If the stack segment is      
|                | not a writable data segment. If the        
|                | stack segment descriptor DPL is not        
|                | equal to the RPL of the return code        
|                | segment selector. If the stack segment     
|                | selector RPL is not equal to the RPL       
|                | of the return code segment selector.       
| #SS(0)         | If an attempt to pop a value off the       
|                | stack violates the SS limit. If an attempt 
|                | to pop a value off the stack causes        
|                | a non-canonical address to be referenced.  
| #NP(selector)  | If the return code or stack segment        
|                | is not present.                            
| #PF(fault-code)| If a page fault occurs.                    
| #AC(0)         | If an unaligned memory reference occurs    
|                | when the CPL is 3 and alignment checking   
|                | is enabled.                                
| #UD            | If the LOCK prefix is used.                


platform: x86
mnem: Jcc
description:
Jcc - Jump if Condition Is Met:
| Opcode  | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                                 
| 77 cb   | JA rel8    | D    | Valid      | Valid          | Jump short if above (CF=0 and ZF=0).        
| 73 cb   | JAE rel8   | D    | Valid      | Valid          | Jump short if above or equal (CF=0).        
| 72 cb   | JB rel8    | D    | Valid      | Valid          | Jump short if below (CF=1).                 
| 76 cb   | JBE rel8   | D    | Valid      | Valid          | Jump short if below or equal (CF=1 or       
|         |            |      |            |                | ZF=1).                                      
| 72 cb   | JC rel8    | D    | Valid      | Valid          | Jump short if carry (CF=1).                 
| E3 cb   | JCXZ rel8  | D    | N.E.       | Valid          | Jump short if CX register is 0.             
| E3 cb   | JECXZ rel8 | D    | Valid      | Valid          | Jump short if ECX register is 0.            
| E3 cb   | JRCXZ rel8 | D    | Valid      | N.E.           | Jump short if RCX register is 0.            
| 74 cb   | JE rel8    | D    | Valid      | Valid          | Jump short if equal (ZF=1).                 
| 7F cb   | JG rel8    | D    | Valid      | Valid          | Jump short if greater (ZF=0 and SF=OF).     
| 7D cb   | JGE rel8   | D    | Valid      | Valid          | Jump short if greater or equal (SF=OF).     
| 7C cb   | JL rel8    | D    | Valid      | Valid          | Jump short if less (SF!= OF).                
| 7E cb   | JLE rel8   | D    | Valid      | Valid          | Jump short if less or equal (ZF=1 or        
|         |            |      |            |                | SF!= OF).                                    
| 76 cb   | JNA rel8   | D    | Valid      | Valid          | Jump short if not above (CF=1 or ZF=1).     
| 72 cb   | JNAE rel8  | D    | Valid      | Valid          | Jump short if not above or equal (CF=1).    
| 73 cb   | JNB rel8   | D    | Valid      | Valid          | Jump short if not below (CF=0).             
| 77 cb   | JNBE rel8  | D    | Valid      | Valid          | Jump short if not below or equal (CF=0      
|         |            |      |            |                | and ZF=0).                                  
| 73 cb   | JNC rel8   | D    | Valid      | Valid          | Jump short if not carry (CF=0).             
| 75 cb   | JNE rel8   | D    | Valid      | Valid          | Jump short if not equal (ZF=0).             
| 7E cb   | JNG rel8   | D    | Valid      | Valid          | Jump short if not greater (ZF=1 or SF!=      
|         |            |      |            |                | OF).                                        
| 7C cb   | JNGE rel8  | D    | Valid      | Valid          | Jump short if not greater or equal (SF!=     
|         |            |      |            |                | OF).                                        
| 7D cb   | JNL rel8   | D    | Valid      | Valid          | Jump short if not less (SF=OF).             
| 7F cb   | JNLE rel8  | D    | Valid      | Valid          | Jump short if not less or equal (ZF=0       
|         |            |      |            |                | and SF=OF).                                 
| 71 cb   | JNO rel8   | D    | Valid      | Valid          | Jump short if not overflow (OF=0).          
| 7B cb   | JNP rel8   | D    | Valid      | Valid          | Jump short if not parity (PF=0).            
| 79 cb   | JNS rel8   | D    | Valid      | Valid          | Jump short if not sign (SF=0).              
| 75 cb   | JNZ rel8   | D    | Valid      | Valid          | Jump short if not zero (ZF=0).              
| 70 cb   | JO rel8    | D    | Valid      | Valid          | Jump short if overflow (OF=1).              
| 7A cb   | JP rel8    | D    | Valid      | Valid          | Jump short if parity (PF=1).                
| 7A cb   | JPE rel8   | D    | Valid      | Valid          | Jump short if parity even (PF=1).           
| 7B cb   | JPO rel8   | D    | Valid      | Valid          | Jump short if parity odd (PF=0).            
| 78 cb   | JS rel8    | D    | Valid      | Valid          | Jump short if sign (SF=1).                  
| 74 cb   | JZ rel8    | D    | Valid      | Valid          | Jump short if zero (ZF ← 1).                
| 0F 87 cw| JA rel16   | D    | N.S.       | Valid          | Jump near if above (CF=0 and ZF=0).         
|         |            |      |            |                | Not supported in 64-bit mode.               
| 0F 87 cd| JA rel32   | D    | Valid      | Valid          | Jump near if above (CF=0 and ZF=0).         
| 0F 83 cw| JAE rel16  | D    | N.S.       | Valid          | Jump near if above or equal (CF=0).         
|         |            |      |            |                | Not supported in 64-bit mode.               
| Opcode  | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                                 
| 0F 83 cd| JAE rel32  | D    | Valid      | Valid          | Jump near if above or equal (CF=0).         
| 0F 82 cw| JB rel16   | D    | N.S.       | Valid          | Jump near if below (CF=1). Not supported    
|         |            |      |            |                | in 64-bit mode.                             
| 0F 82 cd| JB rel32   | D    | Valid      | Valid          | Jump near if below (CF=1).                  
| 0F 86 cw| JBE rel16  | D    | N.S.       | Valid          | Jump near if below or equal (CF=1 or        
|         |            |      |            |                | ZF=1). Not supported in 64-bit mode.        
| 0F 86 cd| JBE rel32  | D    | Valid      | Valid          | Jump near if below or equal (CF=1 or        
|         |            |      |            |                | ZF=1).                                      
| 0F 82 cw| JC rel16   | D    | N.S.       | Valid          | Jump near if carry (CF=1). Not supported    
|         |            |      |            |                | in 64-bit mode.                             
| 0F 82 cd| JC rel32   | D    | Valid      | Valid          | Jump near if carry (CF=1).                  
| 0F 84 cw| JE rel16   | D    | N.S.       | Valid          | Jump near if equal (ZF=1). Not supported    
|         |            |      |            |                | in 64-bit mode.                             
| 0F 84 cd| JE rel32   | D    | Valid      | Valid          | Jump near if equal (ZF=1).                  
| 0F 84 cw| JZ rel16   | D    | N.S.       | Valid          | Jump near if 0 (ZF=1). Not supported        
|         |            |      |            |                | in 64-bit mode.                             
| 0F 84 cd| JZ rel32   | D    | Valid      | Valid          | Jump near if 0 (ZF=1).                      
| 0F 8F cw| JG rel16   | D    | N.S.       | Valid          | Jump near if greater (ZF=0 and SF=OF).      
|         |            |      |            |                | Not supported in 64-bit mode.               
| 0F 8F cd| JG rel32   | D    | Valid      | Valid          | Jump near if greater (ZF=0 and SF=OF).      
| 0F 8D cw| JGE rel16  | D    | N.S.       | Valid          | Jump near if greater or equal (SF=OF).      
|         |            |      |            |                | Not supported in 64-bit mode.               
| 0F 8D cd| JGE rel32  | D    | Valid      | Valid          | Jump near if greater or equal (SF=OF).      
| 0F 8C cw| JL rel16   | D    | N.S.       | Valid          | Jump near if less (SF!= OF). Not supported   
|         |            |      |            |                | in 64-bit mode.                             
| 0F 8C cd| JL rel32   | D    | Valid      | Valid          | Jump near if less (SF!= OF).                 
| 0F 8E cw| JLE rel16  | D    | N.S.       | Valid          | Jump near if less or equal (ZF=1 or         
|         |            |      |            |                | SF!= OF). Not supported in 64-bit mode.      
| 0F 8E cd| JLE rel32  | D    | Valid      | Valid          | Jump near if less or equal (ZF=1 or         
|         |            |      |            |                | SF!= OF).                                    
| 0F 86 cw| JNA rel16  | D    | N.S.       | Valid          | Jump near if not above (CF=1 or ZF=1).      
|         |            |      |            |                | Not supported in 64-bit mode.               
| 0F 86 cd| JNA rel32  | D    | Valid      | Valid          | Jump near if not above (CF=1 or ZF=1).      
| 0F 82 cw| JNAE rel16 | D    | N.S.       | Valid          | Jump near if not above or equal (CF=1).     
|         |            |      |            |                | Not supported in 64-bit mode.               
| 0F 82 cd| JNAE rel32 | D    | Valid      | Valid          | Jump near if not above or equal (CF=1).     
| 0F 83 cw| JNB rel16  | D    | N.S.       | Valid          | Jump near if not below (CF=0). Not supported
|         |            |      |            |                | in 64-bit mode.                             
| 0F 83 cd| JNB rel32  | D    | Valid      | Valid          | Jump near if not below (CF=0).              
| 0F 87 cw| JNBE rel16 | D    | N.S.       | Valid          | Jump near if not below or equal (CF=0       
|         |            |      |            |                | and ZF=0). Not supported in 64-bit mode.    
| 0F 87 cd| JNBE rel32 | D    | Valid      | Valid          | Jump near if not below or equal (CF=0       
|         |            |      |            |                | and ZF=0).                                  
| 0F 83 cw| JNC rel16  | D    | N.S.       | Valid          | Jump near if not carry (CF=0). Not supported
|         |            |      |            |                | in 64-bit mode.                             
| 0F 83 cd| JNC rel32  | D    | Valid      | Valid          | Jump near if not carry (CF=0).              
| Opcode  | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                                 
| 0F 85 cw| JNE rel16  | D    | N.S.       | Valid          | Jump near if not equal (ZF=0). Not supported
|         |            |      |            |                | in 64-bit mode.                             
| 0F 85 cd| JNE rel32  | D    | Valid      | Valid          | Jump near if not equal (ZF=0).              
| 0F 8E cw| JNG rel16  | D    | N.S.       | Valid          | Jump near if not greater (ZF=1 or SF!=       
|         |            |      |            |                | OF). Not supported in 64-bit mode.          
| 0F 8E cd| JNG rel32  | D    | Valid      | Valid          | Jump near if not greater (ZF=1 or SF!=       
|         |            |      |            |                | OF).                                        
| 0F 8C cw| JNGE rel16 | D    | N.S.       | Valid          | Jump near if not greater or equal (SF!=      
|         |            |      |            |                | OF). Not supported in 64-bit mode.          
| 0F 8C cd| JNGE rel32 | D    | Valid      | Valid          | Jump near if not greater or equal (SF!=      
|         |            |      |            |                | OF).                                        
| 0F 8D cw| JNL rel16  | D    | N.S.       | Valid          | Jump near if not less (SF=OF). Not supported
|         |            |      |            |                | in 64-bit mode.                             
| 0F 8D cd| JNL rel32  | D    | Valid      | Valid          | Jump near if not less (SF=OF).              
| 0F 8F cw| JNLE rel16 | D    | N.S.       | Valid          | Jump near if not less or equal (ZF=0        
|         |            |      |            |                | and SF=OF). Not supported in 64-bit         
|         |            |      |            |                | mode.                                       
| 0F 8F cd| JNLE rel32 | D    | Valid      | Valid          | Jump near if not less or equal (ZF=0        
|         |            |      |            |                | and SF=OF).                                 
| 0F 81 cw| JNO rel16  | D    | N.S.       | Valid          | Jump near if not overflow (OF=0). Not       
|         |            |      |            |                | supported in 64-bit mode.                   
| 0F 81 cd| JNO rel32  | D    | Valid      | Valid          | Jump near if not overflow (OF=0).           
| 0F 8B cw| JNP rel16  | D    | N.S.       | Valid          | Jump near if not parity (PF=0). Not         
|         |            |      |            |                | supported in 64-bit mode.                   
| 0F 8B cd| JNP rel32  | D    | Valid      | Valid          | Jump near if not parity (PF=0).             
| 0F 89 cw| JNS rel16  | D    | N.S.       | Valid          | Jump near if not sign (SF=0). Not supported 
|         |            |      |            |                | in 64-bit mode.                             
| 0F 89 cd| JNS rel32  | D    | Valid      | Valid          | Jump near if not sign (SF=0).               
| 0F 85 cw| JNZ rel16  | D    | N.S.       | Valid          | Jump near if not zero (ZF=0). Not supported 
|         |            |      |            |                | in 64-bit mode.                             
| 0F 85 cd| JNZ rel32  | D    | Valid      | Valid          | Jump near if not zero (ZF=0).               
| 0F 80 cw| JO rel16   | D    | N.S.       | Valid          | Jump near if overflow (OF=1). Not supported 
|         |            |      |            |                | in 64-bit mode.                             
| 0F 80 cd| JO rel32   | D    | Valid      | Valid          | Jump near if overflow (OF=1).               
| 0F 8A cw| JP rel16   | D    | N.S.       | Valid          | Jump near if parity (PF=1). Not supported   
|         |            |      |            |                | in 64-bit mode.                             
| 0F 8A cd| JP rel32   | D    | Valid      | Valid          | Jump near if parity (PF=1).                 
| 0F 8A cw| JPE rel16  | D    | N.S.       | Valid          | Jump near if parity even (PF=1). Not        
|         |            |      |            |                | supported in 64-bit mode.                   
| 0F 8A cd| JPE rel32  | D    | Valid      | Valid          | Jump near if parity even (PF=1).            
| 0F 8B cw| JPO rel16  | D    | N.S.       | Valid          | Jump near if parity odd (PF=0). Not         
|         |            |      |            |                | supported in 64-bit mode.                   
| 0F 8B cd| JPO rel32  | D    | Valid      | Valid          | Jump near if parity odd (PF=0).             
| 0F 88 cw| JS rel16   | D    | N.S.       | Valid          | Jump near if sign (SF=1). Not supported     
|         |            |      |            |                | in 64bit mode.                              
| Opcode  | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                                 
| 0F 88 cd| JS rel32   | D    | Valid      | Valid          | Jump near if sign (SF=1).                   
| 0F 84 cw| JZ rel16   | D    | N.S.       | Valid          | Jump near if 0 (ZF=1). Not supported        
|         |            |      |            |                | in 64-bit mode.                             
| 0F 84 cd| JZ rel32   | D    | Valid      | Valid          | Jump near if 0 (ZF=1).                      

Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| D    | Offset   | NA       | NA       | NA       

Description:
Checks the state of one or more of the status flags in the EFLAGS register (CF,
OF, PF, SF, and ZF) and, if the flags are in the specified state (condition),
performs a jump to the target instruction specified by the destination operand.
A condition code (cc) is associated with each instruction to indicate the condition
being tested for. If the condition is not satisfied, the jump is not performed
and execution continues with the instruction following the Jcc instruction.

The target instruction is specified with a relative offset (a signed offset
relative to the current value of the instruction pointer in the EIP register).
A relative offset (rel8, rel16, or rel32) is generally specified as a label
in assembly code, but at the machine code level, it is encoded as a signed,
8-bit or 32-bit immediate value, which is added to the instruction pointer.
Instruction coding is most efficient for offsets of -128 to +127. If the operand-size
attribute is 16, the upper two bytes of the EIP register are cleared, resulting
in a maximum instruction pointer size of 16 bits.

The conditions for each Jcc mnemonic are given in the “Description” column of
the table on the preceding page. The terms “less” and “greater” are used for
comparisons of signed integers and the terms “above” and “below” are used for
unsigned integers.

Because a particular state of the status flags can sometimes be interpreted
in two ways, two mnemonics are defined for some opcodes. For example, the JA
(jump if above) instruction and the JNBE (jump if not below or equal) instruction
are alternate mnemonics for the opcode 77H.

The Jcc instruction does not support far jumps (jumps to other code segments).
When the target for the conditional jump is in a different segment, use the
opposite condition from the condition being tested for the Jcc instruction,
and then access the target with an unconditional far jump (JMP instruction)
to the other segment. For example, the following conditional far jump is illegal:
JZ FARLABEL;

To accomplish this far jump, use the following two instructions: JNZ BEYOND;
JMP FARLABEL; BEYOND:

The JRCXZ, JECXZ and JCXZ instructions differ from other Jcc instructions because
they do not check status flags. Instead, they check RCX, ECX or CX for 0. The
register checked is determined by the address-size attribute. These instructions
are useful when used at the beginning of a loop that terminates with a conditional
loop instruction (such as LOOPNE). They can be used to prevent an instruction
sequence from entering a loop when RCX, ECX or CX is 0. This would cause the
loop to execute 264, 232 or 64K times (not zero times).

All conditional jumps are converted to code fetches of one or two cache lines,
regardless of jump address or cacheability.

In 64-bit mode, operand size is fixed at 64 bits. JMP Short is RIP = RIP + 8-bit
offset sign extended to 64 bits. JMP Near is RIP = RIP + 32-bit offset sign
extended to 64-bits.

Operation:

IF condition
  THEN
     tempEIP <- EIP + SignExtend(DEST);
     IF OperandSize = 16
       THEN tempEIP <- tempEIP AND 0000FFFFH;
     FI;
  IF tempEIP is not within code segment limit
     THEN #GP(0);
     ELSE EIP <- tempEIP
  FI;
FI;

Protected Mode Exceptions:
| #GP(0)| If the offset being jumped to is beyond
|       | the limits of the CS segment.          
| #UD   | If the LOCK prefix is used.            

Real-Address Mode Exceptions:
| #GP| If the offset being jumped to is beyond   
|    | the limits of the CS segment or is outside
|    | of the effective address space from       
|    | 0 to FFFFH. This condition can occur      
|    | if a 32-bit address size override prefix  
|    | is used.                                  
| #UD| If the LOCK prefix is used.               

Virtual-8086 Mode Exceptions:
Same exceptions as in real address mode.


Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #GP(0)| If the memory address is in a non-canonical
|       | form.                                      
| #UD   | If the LOCK prefix is used.                


platform: x86
mnem: JMP
description:
JMP - Jump:
| Opcode       | Instruction | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                               
| EB cb        | JMP rel8    | D    | Valid      | Valid          | Jump short, RIP = RIP + 8-bit displacement
|              |             |      |            |                | sign extended to 64-bits                  
| E9 cw        | JMP rel16   | D    | N.S.       | Valid          | Jump near, relative, displacement relative
|              |             |      |            |                | to next instruction. Not supported in     
|              |             |      |            |                | 64-bit mode.                              
| E9 cd        | JMP rel32   | D    | Valid      | Valid          | Jump near, relative, RIP = RIP + 32-bit   
|              |             |      |            |                | displacement sign extended to 64-bits     
| FF /4        | JMP r/m16   | M    | N.S.       | Valid          | Jump near, absolute indirect, address     
|              |             |      |            |                | = zeroextended r/m16. Not supported       
|              |             |      |            |                | in 64-bit mode.                           
| FF /4        | JMP r/m32   | M    | N.S.       | Valid          | Jump near, absolute indirect, address     
|              |             |      |            |                | given in r/m32. Not supported in 64-bit   
|              |             |      |            |                | mode.                                     
| FF /4        | JMP r/m64   | M    | Valid      | N.E.           | Jump near, absolute indirect, RIP =       
|              |             |      |            |                | 64-Bit offset from register or memory     
| EA cd        | JMP ptr16:16| D    | Inv.       | Valid          | Jump far, absolute, address given in      
|              |             |      |            |                | operand                                   
| EA cp        | JMP ptr16:32| D    | Inv.       | Valid          | Jump far, absolute, address given in      
|              |             |      |            |                | operand                                   
| FF /5        | JMP m16:16  | D    | Valid      | Valid          | Jump far, absolute indirect, address      
|              |             |      |            |                | given in m16:16                           
| FF /5        | JMP m16:32  | D    | Valid      | Valid          | Jump far, absolute indirect, address      
|              |             |      |            |                | given in m16:32.                          
| REX.W + FF /5| JMP m16:64  | D    | Valid      | N.E.           | Jump far, absolute indirect, address      
|              |             |      |            |                | given in m16:64.                          

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2| Operand 3| Operand 4
| D    | Offset       | NA       | NA       | NA       
| M    | ModRM:r/m (r)| NA       | NA       | NA       

Description:
Transfers program control to a different point in the instruction stream without
recording return information. The destination (target) operand specifies the
address of the instruction being jumped to. This operand can be an immediate
value, a general-purpose register, or a memory location.

This instruction can be used to execute four different types of jumps:

 - Near jump - A jump to an instruction within the current code segment (the segment
currently pointed to by the CS register), sometimes referred to as an intrasegment
jump.
 - Short jump - A near jump where the jump range is limited to -128 to +127 from
the current EIP value.
 - Far jump - A jump to an instruction located in a different segment than the current
code segment but at the same privilege level, sometimes referred to as an intersegment
jump.
 - Task switch - A jump to an instruction located in a different task.

A task switch can only be executed in protected mode (see Chapter 7, in the
Intel® 64 and IA-32 Architectures Software Developer's Manual, Volume 3A, for
information on performing task switches with the JMP instruction).

Near and Short Jumps. When executing a near jump, the processor jumps to the
address (within the current code segment) that is specified with the target
operand. The target operand specifies either an absolute offset (that is an
offset from the base of the code segment) or a relative offset (a signed displacement
relative to the current

value of the instruction pointer in the EIP register). A near jump to a relative
offset of 8-bits (rel8) is referred to as a short jump. The CS register is not
changed on near and short jumps.

An absolute offset is specified indirectly in a general-purpose register or
a memory location (r/m16 or r/m32). The operand-size attribute determines the
size of the target operand (16 or 32 bits). Absolute offsets are loaded directly
into the EIP register. If the operand-size attribute is 16, the upper two bytes
of the EIP register are cleared, resulting in a maximum instruction pointer
size of 16 bits.

A relative offset (rel8, rel16, or rel32) is generally specified as a label
in assembly code, but at the machine code level, it is encoded as a signed 8-,
16-, or 32-bit immediate value. This value is added to the value in the EIP
register. (Here, the EIP register contains the address of the instruction following
the JMP instruction). When using relative offsets, the opcode (for short vs.
near jumps) and the operand-size attribute (for near relative jumps) determines
the size of the target operand (8, 16, or 32 bits).

Far Jumps in Real-Address or Virtual-8086 Mode. When executing a far jump in
real-address or virtual-8086 mode, the processor jumps to the code segment and
offset specified with the target operand. Here the target operand specifies
an absolute far address either directly with a pointer (ptr16:16 or ptr16:32)
or indirectly with a memory location (m16:16 or m16:32). With the pointer method,
the segment and address of the called procedure is encoded in the instruction,
using a 4-byte (16-bit operand size) or 6-byte (32-bit operand size) far address
immediate. With the indirect method, the target operand specifies a memory location
that contains a 4-byte (16-bit operand size) or 6-byte (32-bit operand size)
far address. The far address is loaded directly into the CS and EIP registers.
If the operand-size attribute is 16, the upper two bytes of the EIP register
are cleared.

Far Jumps in Protected Mode. When the processor is operating in protected mode,
the JMP instruction can be used to perform the following three types of far
jumps:

 - A far jump to a conforming or non-conforming code segment.
 - A far jump through a call gate.
 - A task switch.

(The JMP instruction cannot be used to perform inter-privilege-level far jumps.)

In protected mode, the processor always uses the segment selector part of the
far address to access the corresponding descriptor in the GDT or LDT. The descriptor
type (code segment, call gate, task gate, or TSS) and access rights determine
the type of jump to be performed.

If the selected descriptor is for a code segment, a far jump to a code segment
at the same privilege level is performed. (If the selected code segment is at
a different privilege level and the code segment is non-conforming, a general-protection
exception is generated.) A far jump to the same privilege level in protected
mode is very similar to one carried out in real-address or virtual-8086 mode.
The target operand specifies an absolute far address either directly with a
pointer (ptr16:16 or ptr16:32) or indirectly with a memory location (m16:16
or m16:32). The operand-size attribute determines the size of the offset (16
or 32 bits) in the far address. The new code segment selector and its descriptor
are loaded into CS register, and the offset from the instruction is loaded into
the EIP register. Note that a call gate (described in the next paragraph) can
also be used to perform far call to a code segment at the same privilege level.
Using this mechanism provides an extra level of indirection and is the preferred
method of making jumps between 16-bit and 32-bit code segments.

When executing a far jump through a call gate, the segment selector specified
by the target operand identifies the call gate. (The offset part of the target
operand is ignored.) The processor then jumps to the code segment specified
in the call gate descriptor and begins executing the instruction at the offset
specified in the call gate. No stack switch occurs. Here again, the target operand
can specify the far address of the call gate either directly with a pointer
(ptr16:16 or ptr16:32) or indirectly with a memory location (m16:16 or m16:32).

Executing a task switch with the JMP instruction is somewhat similar to executing
a jump through a call gate. Here the target operand specifies the segment selector
of the task gate for the task being switched to (and the offset part of the
target operand is ignored). The task gate in turn points to the TSS for the
task, which contains the segment selectors for the task's code and stack segments.
The TSS also contains the EIP value for the next instruction that was to be
executed before the task was suspended. This instruction pointer value is loaded
into the EIP register so that the task begins executing again at this next instruction.

The JMP instruction can also specify the segment selector of the TSS directly,
which eliminates the indirection of the task gate. See Chapter 7 in Intel® 64
and IA-32 Architectures Software Developer's Manual, Volume 3A, for detailed
information on the mechanics of a task switch.

Note that when you execute at task switch with a JMP instruction, the nested
task flag (NT) is not set in the EFLAGS register and the new TSS's previous
task link field is not loaded with the old task's TSS selector. A return to
the previous task can thus not be carried out by executing the IRET instruction.
Switching tasks with the JMP instruction differs in this regard from the CALL
instruction which does set the NT flag and save the previous task link information,
allowing a return to the calling task with an IRET instruction.

In 64-Bit Mode  -  The instruction's operation size is fixed at 64 bits. If a
selector points to a gate, then RIP equals the 64-bit displacement taken from
gate; else RIP equals the zero-extended offset from the far pointer referenced
in the instruction.

See the summary chart at the beginning of this section for encoding data and
limits.

Operation:

IF near jump
  IF 64-bit Mode
     THEN
       IF near relative jump
        THEN
          tempRIP <- RIP + DEST; (* RIP is instruction following JMP instruction*)
        ELSE (* Near absolute jump *)
          tempRIP <- DEST;
       FI;
     ELSE
       IF near relative jump
        THEN
          tempEIP <- EIP + DEST; (* EIP is instruction following JMP instruction*)
        ELSE (* Near absolute jump *)
          tempEIP <- DEST;
       FI;
  FI;
  IF (IA32_EFER.LMA = 0 or target mode = Compatibility mode)
  and tempEIP outside code segment limit
     THEN #GP(0); FI
  IF 64-bit mode and tempRIP is not canonical
     THEN #GP(0);
  FI;
  IF OperandSize = 32
     THEN
       EIP <- tempEIP;
     ELSE
       IF OperandSize = 16
          THEN (* OperandSize = 16 *)
             EIP <- tempEIP AND 0000FFFFH;
          ELSE (* OperandSize = 64)
             RIP <- tempRIP;
       FI;
  FI;
FI;
IF far jump and (PE = 0 or (PE = 1 AND VM = 1)) (* Real-address or virtual-8086 mode *)
  THEN
     tempEIP <- DEST(Offset); (* DEST is ptr16:32 or [m16:32] *)
     IF tempEIP is beyond code segment limit
       THEN #GP(0); FI;
     CS <- DEST(segment selector); (* DEST is ptr16:32 or [m16:32] *)
     IF OperandSize = 32
        THEN
          EIP <- tempEIP; (* DEST is ptr16:32 or [m16:32] *)
        ELSE (* OperandSize = 16 *)
          EIP <- tempEIP AND 0000FFFFH; (* Clear upper 16 bits *)
     FI;
FI;
IF far jump and (PE = 1 and VM = 0)
(* IA-32e mode or protected mode, not virtual-8086 mode *)
  THEN
     IF effective address in the CS, DS, ES, FS, GS, or SS segment is illegal
     or segment selector in target operand NULL
          THEN #GP(0); FI;
     IF segment selector index not within descriptor table limits
       THEN #GP(new selector); FI;
     Read type and access rights of segment descriptor;
     IF (EFER.LMA = 0)
       THEN
          IF segment type is not a conforming or nonconforming code
          segment, call gate, task gate, or TSS
             THEN #GP(segment selector); FI;
       ELSE
          IF segment type is not a conforming or nonconforming code segment
          call gate
             THEN #GP(segment selector); FI;
     FI;
     Depending on type and access rights:
       GO TO CONFORMING-CODE-SEGMENT;
       GO TO NONCONFORMING-CODE-SEGMENT;
       GO TO CALL-GATE;
       GO TO TASK-GATE;
       GO TO TASK-STATE-SEGMENT;
  ELSE
     #GP(segment selector);
FI;
CONFORMING-CODE-SEGMENT:
  IF L-Bit = 1 and D-BIT = 1 and IA32_EFER.LMA = 1
     THEN GP(new code segment selector); FI;
  IF DPL > CPL
     THEN #GP(segment selector); FI;
  IF segment not present
     THEN #NP(segment selector); FI;
  tempEIP <- DEST(Offset);
  IF OperandSize = 16
     THEN tempEIP <- tempEIP AND 0000FFFFH;
  FI;
  IF (IA32_EFER.LMA = 0 or target mode = Compatibility mode) and
  tempEIP outside code segment limit
     THEN #GP(0); FI
  IF tempEIP is non-canonical
     THEN #GP(0); FI;
  CS <- DEST[segment selector]; (* Segment descriptor information also loaded *)
  CS(RPL) <- CPL
  EIP <- tempEIP;
END;
NONCONFORMING-CODE-SEGMENT:
  IF L-Bit = 1 and D-BIT = 1 and IA32_EFER.LMA = 1
     THEN GP(new code segment selector); FI;
  IF (RPL > CPL) OR (DPL != CPL)
     THEN #GP(code segment selector); FI;
  IF segment not present
     THEN #NP(segment selector); FI;
  tempEIP <- DEST(Offset);
  IF OperandSize = 16
     THEN tempEIP <- tempEIP AND 0000FFFFH; FI;
  IF (IA32_EFER.LMA = 0 OR target mode = Compatibility mode)
  and tempEIP outside code segment limit
     THEN #GP(0); FI
  IF tempEIP is non-canonical THEN #GP(0); FI;
  CS <- DEST[segment selector]; (* Segment descriptor information also loaded *)
  CS(RPL) <- CPL;
  EIP <- tempEIP;
END;
CALL-GATE:
  IF call gate DPL < CPL
  or call gate DPL < call gate segment-selector RPL
       THEN #GP(call gate selector); FI;
  IF call gate not present
     THEN #NP(call gate selector); FI;
  IF call gate code-segment selector is NULL
     THEN #GP(0); FI;
  IF call gate code-segment selector index outside descriptor table limits
     THEN #GP(code segment selector); FI;
  Read code segment descriptor;
  IF code-segment segment descriptor does not indicate a code segment
  or code-segment segment descriptor is conforming and DPL > CPL
  or code-segment segment descriptor is non-conforming and DPL != CPL
       THEN #GP(code segment selector); FI;
  IF IA32_EFER.LMA = 1 and (code-segment descriptor is not a 64-bit code segment
  or code-segment segment descriptor has both L-Bit and D-bit set)
       THEN #GP(code segment selector); FI;
  IF code segment is not present
     THEN #NP(code-segment selector); FI;
  IF instruction pointer is not within code-segment limit
     THEN #GP(0); FI;
  tempEIP <- DEST(Offset);
  IF GateSize = 16
     THEN tempEIP <- tempEIP AND 0000FFFFH; FI;
  IF (IA32_EFER.LMA = 0 OR target mode = Compatibility mode) AND tempEIP
  outside code segment limit
     THEN #GP(0); FI
  CS <- DEST[SegmentSelector); (* Segment descriptor information also loaded *)
  CS(RPL) <- CPL;
  EIP <- tempEIP;
END;
TASK-GATE:
  IF task gate DPL < CPL
  or task gate DPL < task gate segment-selector RPL
     THEN #GP(task gate selector); FI;
  IF task gate not present
     THEN #NP(gate selector); FI;
  Read the TSS segment selector in the task-gate descriptor;
  IF TSS segment selector local/global bit is set to local
  or index not within GDT limits
  or TSS descriptor specifies that the TSS is busy
     THEN #GP(TSS selector); FI;
  IF TSS not present
     THEN #NP(TSS selector); FI;
  SWITCH-TASKS to TSS;
  IF EIP not within code segment limit
     THEN #GP(0); FI;
END;
TASK-STATE-SEGMENT:
  IF TSS DPL < CPL
  or TSS DPL < TSS segment-selector RPL
  or TSS descriptor indicates TSS not available
     THEN #GP(TSS selector); FI;
  IF TSS is not present
     THEN #NP(TSS selector); FI;
  SWITCH-TASKS to TSS;
  IF EIP not within code segment limit
     THEN #GP(0); FI;
END;

Flags Affected:
All flags are affected if a task switch occurs; no flags are affected if a task
switch does not occur.


Protected Mode Exceptions:
| #GP(0)         | If offset in target operand, call gate,     
|                | or TSS is beyond the code segment limits.   
|                | If the segment selector in the destination  
|                | operand, call gate, task gate, or TSS       
|                | is NULL. If a memory operand effective      
|                | address is outside the CS, DS, ES, FS,      
|                | or GS segment limit. If the DS, ES,         
|                | FS, or GS register is used to access        
|                | memory and it contains a NULL segment       
|                | selector.                                   
| #GP(selector)  | If the segment selector index is outside    
|                | descriptor table limits. If the segment     
|                | descriptor pointed to by the segment        
|                | selector in the destination operand         
|                | is not for a conforming-code segment,       
|                | nonconforming-code segment, call gate,      
|                | task gate, or task state segment. If        
|                | the DPL for a nonconforming-code segment    
|                | is not equal to the CPL (When not using     
|                | a call gate.) If the RPL for the segment's  
|                | segment selector is greater than the        
|                | CPL. If the DPL for a conforming-code       
|                | segment is greater than the CPL. If         
|                | the DPL from a call-gate, task-gate,        
|                | or TSS segment descriptor is less than      
|                | the CPL or than the RPL of the call-gate,   
|                | task-gate, or TSS's segment selector.       
|                | If the segment descriptor for selector      
|                | in a call gate does not indicate it         
|                | is a code segment. If the segment descriptor
|                | for the segment selector in a task gate     
|                | does not indicate an available TSS.         
|                | If the segment selector for a TSS has       
|                | its local/global bit set for local.         
|                | If a TSS segment descriptor specifies       
|                | that the TSS is busy or not available.      
| #SS(0)         | If a memory operand effective address       
|                | is outside the SS segment limit.            
| #NP (selector) | If the code segment being accessed is       
|                | not present. If call gate, task gate,       
|                | or TSS not present.                         
| #PF(fault-code)| If a page fault occurs.                     
| #AC(0)         | If alignment checking is enabled and        
|                | an unaligned memory reference is made       
|                | while the current privilege level is        
|                | 3. (Only occurs when fetching target        
|                | from memory.)                               
| #UD            | If the LOCK prefix is used.                 

Real-Address Mode Exceptions:
| #GP| If a memory operand effective address       
|    | is outside the CS, DS, ES, FS, or GS        
|    | segment limit. If a memory operand effective
|    | address is outside the CS, DS, ES, FS,      
|    | or GS segment limit.                        
| #SS| If a memory operand effective address       
|    | is outside the SS segment limit.            
| #UD| If the LOCK prefix is used.                 

Virtual-8086 Mode Exceptions:
| #GP(0)         | If the target operand is beyond the     
|                | code segment limits. If a memory operand
|                | effective address is outside the CS,    
|                | DS, ES, FS, or GS segment limit.        
| #SS(0)         | If a memory operand effective address   
|                | is outside the SS segment limit.        
| #PF(fault-code)| If a page fault occurs.                 
| #AC(0)         | If alignment checking is enabled and    
|                | an unaligned memory reference is made.  
|                | (Only occurs when fetching target from  
|                | memory.)                                
| #UD            | If the LOCK prefix is used.             

Compatibility Mode Exceptions:
Same as 64-bit mode exceptions.


64-Bit Mode Exceptions:
| #GP(0)       | If a memory address is non-canonical.      
|              | If target offset in destination operand    
|              | is non-canonical. If target offset in      
|              | destination operand is beyond the new      
|              | code segment limit. If the segment selector
|              | in the destination operand is NULL.        
|              | If the code segment selector in the        
|              | 64-bit gate is NULL.                       
| #GP(selector)| If the code segment or 64-bit call gate    
|              | is outside descriptor table limits.        
|              | If the code segment or 64-bit call gate    
|              | overlaps non-canonical space. If the       
|              | segment descriptor from a 64-bit call      
|              | gate is in non-canonical space. If the     
|              | segment descriptor pointed to by the       
|              | segment selector in the destination        
|              | operand is not for a conforming-code       
|              | segment, nonconforming-code segment,       
|              | 64-bit call gate. If the segment descriptor
|              | pointed to by the segment selector in      
|              | the destination operand is a code segment, 
|              | and has both the D-bit and the L-bit       
|              | set. If the DPL for a nonconforming-code   
|              | segment is not equal to the CPL, or        
|              | the RPL for the segment's segment selector 
|              | is greater than the CPL. If the DPL        
|              | for a conforming-code segment is greater   
|              | than the CPL. If the DPL from a 64-bit     
|              | call-gate is less than the CPL or than     
|              | the RPL of the 64-bit call-gate. If        
|              | the upper type field of a 64-bit call      
|              | gate is not 0x0. If the segment selector   
|              | from a 64-bit call gate is beyond the      
|              | descriptor table limits. If the code       
|              | segment descriptor pointed to by the       
|              | selector in the 64-bit gate doesn't        
|              | have the Lbit set and the D-bit clear.     
|              | If the segment descriptor for a segment    
|              | selector from the 64-bit call gate does    
|              | not indicate it is a code segment.         
If the code segment is non-confirming and CPL != DPL. If the code segment is
confirming and CPL < DPL.

| #NP(selector)  | If a code segment or 64-bit call gate   
|                | is not present.                         
| #UD            | (64-bit mode only) If a far jump is     
|                | direct to an absolute address in memory.
|                | If the LOCK prefix is used.             
| #PF(fault-code)| If a page fault occurs.                 
| #AC(0)         | If alignment checking is enabled and    
|                | an unaligned memory reference is made   
|                | while the current privilege level is    
|                | 3.                                      


platform: x86
mnem: LAHF
description:
LAHF - Load Status Flags into AH Register:
| Opcode| Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                             
| 9F    | LAHF       | NP   | Invalid*   | Valid          | Load: AH ← EFLAGS(SF:ZF:0:AF:0:PF:1:CF).
Notes: *Valid in specific steppings. See Description section.


Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| NP   | NA       | NA       | NA       | NA       

Description:
This instruction executes as described above in compatibility mode and legacy
mode. It is valid in 64-bit mode only if CPUID.80000001H:ECX.LAHF-SAHF[bit 0]
= 1.

Operation:

IF 64-Bit Mode
  THEN
     IF CPUID.80000001H:ECX.LAHF-SAHF[bit 0] = 1;
       THEN AH <- RFLAGS(SF:ZF:0:AF:0:PF:1:CF);
       ELSE #UD;
     FI;
  ELSE
     AH <- EFLAGS(SF:ZF:0:AF:0:PF:1:CF);
FI;

Flags Affected:
None. The state of the flags in the EFLAGS register is not affected.


Protected Mode Exceptions:
| #UD| If the LOCK prefix is used.

Real-Address Mode Exceptions:
Same exceptions as in protected mode.


Virtual-8086 Mode Exceptions:
Same exceptions as in protected mode.


Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #UD| If CPUID.80000001H:ECX.LAHF-SAHF[bit
|    | 0] = 0. If the LOCK prefix is used. 


platform: x86
mnem: LAR
description:
LAR - Load Access Rights Byte:
| Opcode  | Instruction      | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                              
| 0F 02 /r| LAR r16, r16/m16 | RM   | Valid      | Valid          | r16 ← access rights referenced by r16/m16
| 0F 02 /r| LAR reg, r32/m161| RM   | Valid      | Valid          | reg ← access rights referenced by r32/m16
Notes: 1. For all loads (regardless of source or destination sizing) only bits
16-0 are used. Other bits are ignored.


Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
Loads the access rights from the segment descriptor specified by the second
operand (source operand) into the first operand (destination operand) and sets
the ZF flag in the flag register. The source operand (which can be a register
or a memory location) contains the segment selector for the segment descriptor
being accessed. If the source operand is a memory address, only 16 bits of data
are accessed. The destination operand is a generalpurpose register.

The processor performs access checks as part of the loading process. Once loaded
in the destination register, software can perform additional checks on the access
rights information.

The access rights for a segment descriptor include fields located in the second
doubleword (bytes 4-7) of the segment descriptor. The following fields are loaded
by the LAR instruction:

 - Bits 7:0 are returned as 0
 - Bits 11:8 return the segment type.
 - Bit 12 returns the S flag.
 - Bits 14:13 return the DPL.
 - Bit 15 returns the P flag.
 - The following fields are returned only if the operand size is greater than 16
bits:  - Bits 19:16 are undefined.  - Bit 20 returns the software-available bit
in the descriptor.  - Bit 21 returns the L flag.  - Bit 22 returns the D/B flag.
 - Bit 23 returns the G flag.  - Bits 31:24 are returned as 0.

This instruction performs the following checks before it loads the access rights
in the destination register:

 - Checks that the segment selector is not NULL.
 - Checks that the segment selector points to a descriptor that is within the limits
of the GDT or LDT being accessed
 - Checks that the descriptor type is valid for this instruction. All code and
data segment descriptors are valid for (can be accessed with) the LAR instruction.
The valid system segment and gate descriptor types are given in Table 3-62.
 - If the segment is not a conforming code segment, it checks that the specified
segment descriptor is visible at the CPL (that is, if the CPL and the RPL of
the segment selector are less than or equal to the DPL of the segment selector).

If the segment descriptor cannot be accessed or is an invalid type for the instruction,
the ZF flag is cleared and no access rights are loaded in the destination operand.

The LAR instruction can only be executed in protected mode and IA-32e mode.


Table 3-62. Segment and Gate Types:
| Type                   | Protected Mode Valid| IA-32e Mode Valid
| Reserved               | No                  | No               
| Available 16-bit TSS   | Yes                 | No               
| LDT                    | Yes                 | No               
| Busy 16-bit TSS        | Yes                 | No               
| 16-bit call gate       | Yes                 | No               
| 16-bit/32-bit task gate| Yes                 | No               
| 16-bit interrupt gate  | No                  | No               
| 16-bit trap gate       | No                  | No               
| Reserved               | No                  | No               
| Available 32-bit TSS   | Yes                 | Yes              
| Reserved               | No                  | No               
| Busy 32-bit TSS        | Yes                 | Yes              
| 32-bit call gate       | Yes                 | Yes              
| Reserved               | No                  | No               
| 32-bit interrupt gate  | No                  | No               
| 32-bit trap gate       | No                  | No               
Operation:

IF Offset(SRC) > descriptor table limit
  THEN
     ZF <- 0;
  ELSE
     SegmentDescriptor <- descriptor referenced by SRC;
     IF SegmentDescriptor(Type) != conforming code segment
     and (CPL > DPL) or (RPL > DPL)
     or SegmentDescriptor(Type) is not valid for instruction
       THEN
          ZF <- 0;
       ELSE
          DEST <- access rights from SegmentDescriptor as given in Description section;
          ZF <- 1;
     FI;
FI;

Flags Affected:
The ZF flag is set to 1 if the access rights are loaded successfully; otherwise,
it is cleared to 0.


Protected Mode Exceptions:
| #GP(0)         | If a memory operand effective address   
|                | is outside the CS, DS, ES, FS, or GS    
|                | segment limit. If the DS, ES, FS, or    
|                | GS register is used to access memory    
|                | and it contains a NULL segment selector.
| #SS(0)         | If a memory operand effective address   
|                | is outside the SS segment limit.        
| #PF(fault-code)| If a page fault occurs.                 
| #AC(0)         | If alignment checking is enabled and    
|                | the memory operand effective address    
|                | is unaligned while the current privilege
|                | level is 3.                             
| #UD            | If the LOCK prefix is used.             

Real-Address Mode Exceptions:
| #UD| The LAR instruction is not recognized
|    | in real-address mode.                

Virtual-8086 Mode Exceptions:
| #UD| The LAR instruction cannot be executed
|    | in virtual-8086 mode.                 

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)         | If the memory operand effective address         
|                | referencing the SS segment is in a non-canonical
|                | form.                                           
| #GP(0)         | If the memory operand effective address         
|                | is in a non-canonical form.                     
| #PF(fault-code)| If a page fault occurs.                         
| #AC(0)         | If alignment checking is enabled and            
|                | the memory operand effective address            
|                | is unaligned while the current privilege        
|                | level is 3.                                     
| #UD            | If the LOCK prefix is used.                     


platform: x86
mnem: LDDQU
description:
LDDQU - Load Unaligned Integer 128 Bits:
| Opcode/Instruction                  | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                            
| F2 0F F0 /r LDDQU xmm1, mem         | RM   | V/V           | SSE3              | Load unaligned data from mem and return
|                                     |      |               |                   | double quadword in xmm1.               
| VEX.128.F2.0F.WIG F0 /r VLDDQU xmm1,| RM   | V/V           | AVX               | Load unaligned packed integer values   
| m128                                |      |               |                   | from mem to xmm1.                      
| VEX.256.F2.0F.WIG F0 /r VLDDQU ymm1,| RM   | V/V           | AVX               | Load unaligned packed integer values   
| m256                                |      |               |                   | from mem to ymm1.                      

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
The instruction is functionally similar to (V)MOVDQU ymm/xmm, m256/m128 for
loading from memory. That is: 32/16 bytes of data starting at an address specified
by the source memory operand (second operand) are fetched from memory and placed
in a destination register (first operand). The source operand need not be aligned
on a 32/16-byte boundary. Up to 64/32 bytes may be loaded from memory; this
is implementation dependent.

This instruction may improve performance relative to (V)MOVDQU if the source
operand crosses a cache line boundary. In situations that require the data loaded
by (V)LDDQU be modified and stored to the same location, use (V)MOVDQU or (V)MOVDQA
instead of (V)LDDQU. To move a double quadword to or from memory locations that
are known to be aligned on 16-byte boundaries, use the (V)MOVDQA instruction.


Implementation Notes:
 - If the source is aligned to a 32/16-byte boundary, based on the implementation,
the 32/16 bytes may be loaded more than once. For that reason, the usage of
(V)LDDQU should be avoided when using uncached or write-combining (WC) memory
regions. For uncached or WC memory regions, keep using (V)MOVDQU.
 - This instruction is a replacement for (V)MOVDQU (load) in situations where cache
line splits significantly affect performance. It should not be used in situations
where store-load forwarding is performance critical. If performance of store-load
forwarding is critical to the application, use (V)MOVDQA store-load pairs when
data is 256/128-bit aligned or (V)MOVDQU store-load pairs when data is 256/128-bit
unaligned.
 - If the memory address is not aligned on 32/16-byte boundary, some implementations
may load up to 64/32 bytes and return 32/16 bytes in the destination. Some processor
implementations may issue multiple loads to access the appropriate 32/16 bytes.
Developers of multi-threaded or multi-processor software should be aware that
on these processors the loads will be performed in a non-atomic way.
 - If alignment checking is enabled (CR0.AM = 1, RFLAGS.AC = 1, and CPL = 3), an
alignment-check exception (#AC) may or may not be generated (depending on processor
implementation) when the memory address is not aligned on an 8-byte boundary.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). Note: In VEX-encoded versions, VEX.vvvv is reserved
and must be 1111b otherwise instructions will #UD.

Operation:

LDDQU (128-bit Legacy SSE version)
DEST[127:0] <- SRC[127:0]
DEST[VLMAX-1:128] (Unmodified)
VLDDQU (VEX.128 encoded version)
DEST[127:0] <- SRC[127:0]
DEST[VLMAX-1:128] <- 0
VLDDQU (VEX.256 encoded version)
DEST[255:0] <- SRC[255:0]

Intel C/C++ Compiler Intrinsic Equivalent:
| LDDQU:| __m128i _mm_lddqu_si128 (__m128i * p);
| LDDQU:| __m256i _mm256_lddqu_si256 (__m256i   
|       | * p);                                 

Numeric Exceptions:
None.


Other Exceptions:
See Exceptions Type 4; Note treatment of #AC varies.


platform: x86
mnem: LDMXCSR
description:
LDMXCSR - Load MXCSR Register:
| Opcode/Instruction              | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                  
| 0F,AE,/2 LDMXCSR m32            | M    | V/V           | SSE               | Load MXCSR register from m32.
| VEX.LZ.0F.WIG AE /2 VLDMXCSR m32| M    | V/V           | AVX               | Load MXCSR register from m32.

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2| Operand 3| Operand 4
| M    | ModRM:r/m (r)| NA       | NA       | NA       

Description:
Loads the source operand into the MXCSR control/status register. The source
operand is a 32-bit memory location. See “MXCSR Control and Status Register”
in Chapter 10, of the Intel® 64 and IA-32 Architectures Software Developer's
Manual, Volume 1, for a description of the MXCSR register and its contents.

The LDMXCSR instruction is typically used in conjunction with the (V)STMXCSR
instruction, which stores the contents of the MXCSR register in memory.

The default MXCSR value at reset is 1F80H.

If a (V)LDMXCSR instruction clears a SIMD floating-point exception mask bit
and sets the corresponding exception flag bit, a SIMD floating-point exception
will not be immediately generated. The exception will be generated only upon
the execution of the next instruction that meets both conditions below:

 - the instruction must operate on an XMM or YMM register operand,
 - the instruction causes that particular SIMD floating-point exception to be reported.

This instruction's operation is the same in non-64-bit modes and 64-bit mode.
If VLDMXCSR is encoded with VEX.L= 1, an attempt to execute the instruction
encoded with VEX.L= 1 will cause an #UD exception.

Note: In VEX-encoded versions, VEX.vvvv is reserved and must be 1111b, otherwise
instructions will #UD.

Operation:

MXCSR <- m32;

C/C++ Compiler Intrinsic Equivalent:
_mm_setcsr(unsigned int i)


Numeric Exceptions:
None.


Other Exceptions:
See Exceptions Type 5; additionally

| #GP| For an attempt to set reserved bits
|    | in MXCSR.                          
| #UD| If VEX.vvvv != 1111B.              


platform: x86
mnem: LDS
description:
LDS/LES/LFS/LGS/LSS - Load Far Pointer:
| Opcode        | Instruction   | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                              
| C5 /r         | LDS r16,m16:16| RM   | Invalid    | Valid          | Load DS:r16 with far pointer from memory.
| C5 /r         | LDS r32,m16:32| RM   | Invalid    | Valid          | Load DS:r32 with far pointer from memory.
| 0F B2 /r      | LSS r16,m16:16| RM   | Valid      | Valid          | Load SS:r16 with far pointer from memory.
| 0F B2 /r      | LSS r32,m16:32| RM   | Valid      | Valid          | Load SS:r32 with far pointer from memory.
| REX + 0F B2 /r| LSS r64,m16:64| RM   | Valid      | N.E.           | Load SS:r64 with far pointer from memory.
| C4 /r         | LES r16,m16:16| RM   | Invalid    | Valid          | Load ES:r16 with far pointer from memory.
| C4 /r         | LES r32,m16:32| RM   | Invalid    | Valid          | Load ES:r32 with far pointer from memory.
| 0F B4 /r      | LFS r16,m16:16| RM   | Valid      | Valid          | Load FS:r16 with far pointer from memory.
| 0F B4 /r      | LFS r32,m16:32| RM   | Valid      | Valid          | Load FS:r32 with far pointer from memory.
| REX + 0F B4 /r| LFS r64,m16:64| RM   | Valid      | N.E.           | Load FS:r64 with far pointer from memory.
| 0F B5 /r      | LGS r16,m16:16| RM   | Valid      | Valid          | Load GS:r16 with far pointer from memory.
| 0F B5 /r      | LGS r32,m16:32| RM   | Valid      | Valid          | Load GS:r32 with far pointer from memory.
| REX + 0F B5 /r| LGS r64,m16:64| RM   | Valid      | N.E.           | Load GS:r64 with far pointer from memory.

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
Loads a far pointer (segment selector and offset) from the second operand (source
operand) into a segment register and the first operand (destination operand).
The source operand specifies a 48-bit or a 32-bit pointer in memory depending
on the current setting of the operand-size attribute (32 bits or 16 bits, respectively).
The instruction opcode and the destination operand specify a segment register/general-purpose
register pair. The 16bit segment selector from the source operand is loaded
into the segment register specified with the opcode (DS, SS, ES, FS, or GS).
The 32-bit or 16-bit offset is loaded into the register specified with the destination
operand.

If one of these instructions is executed in protected mode, additional information
from the segment descriptor pointed to by the segment selector in the source
operand is loaded in the hidden part of the selected segment register.

Also in protected mode, a NULL selector (values 0000 through 0003) can be loaded
into DS, ES, FS, or GS registers without causing a protection exception. (Any
subsequent reference to a segment whose corresponding segment register is loaded
with a NULL selector, causes a general-protection exception (#GP) and no memory
reference to the segment occurs.)

In 64-bit mode, the instruction's default operation size is 32 bits. Using a
REX prefix in the form of REX.W promotes operation to specify a source operand
referencing an 80-bit pointer (16-bit selector, 64-bit offset) in memory. Using
a REX prefix in the form of REX.R permits access to additional registers (R8-R15).
See the summary chart at the beginning of this section for encoding data and
limits.

Operation:

64-BIT_MODE
  IF SS is loaded
     THEN
       IF SegmentSelector = NULL and ( (RPL = 3) or
             (RPL != 3 and RPL != CPL) )
          THEN #GP(0);
       ELSE IF descriptor is in non-canonical space
          THEN #GP(0); FI;
       ELSE IF Segment selector index is not within descriptor table limits
             or segment selector RPL != CPL
             or access rights indicate nonwritable data segment
             or DPL != CPL
          THEN #GP(selector); FI;
       ELSE IF Segment marked not present
          THEN #SS(selector); FI;
       FI;
       SS <- SegmentSelector(SRC);
       SS <- SegmentDescriptor([SRC]);
  ELSE IF attempt to load DS, or ES
     THEN #UD;
  ELSE IF FS, or GS is loaded with non-NULL segment selector
     THEN IF Segment selector index is not within descriptor table limits
       or access rights indicate segment neither data nor readable code segment
       or segment is data or nonconforming-code segment
       and ( RPL > DPL or CPL > DPL)
          THEN #GP(selector); FI;
       ELSE IF Segment marked not present
          THEN #NP(selector); FI;
       FI;
       SegmentRegister <- SegmentSelector(SRC) ;
       SegmentRegister <- SegmentDescriptor([SRC]);
     FI;
  ELSE IF FS, or GS is loaded with a NULL selector:
     THEN
       SegmentRegister <- NULLSelector;
       SegmentRegister(DescriptorValidBit) <- 0; FI; (* Hidden flag;
          not accessible by software *)
  FI;
  DEST <- Offset(SRC);
PREOTECTED MODE OR COMPATIBILITY MODE;
  IF SS is loaded
     THEN
       IF SegementSelector = NULL
          THEN #GP(0);
       ELSE IF Segment selector index is not within descriptor table limits
             or segment selector RPL != CPL
             or access rights indicate nonwritable data segment
             or DPL != CPL
          THEN #GP(selector); FI;
       ELSE IF Segment marked not present
          THEN #SS(selector); FI;
       FI;
       SS <- SegmentSelector(SRC);
       SS <- SegmentDescriptor([SRC]);
  ELSE IF DS, ES, FS, or GS is loaded with non-NULL segment selector
     THEN IF Segment selector index is not within descriptor table limits
       or access rights indicate segment neither data nor readable code segment
       or segment is data or nonconforming-code segment
       and (RPL > DPL or CPL > DPL)
          THEN #GP(selector); FI;
       ELSE IF Segment marked not present
          THEN #NP(selector); FI;
       FI;
       SegmentRegister <- SegmentSelector(SRC) AND RPL;
       SegmentRegister <- SegmentDescriptor([SRC]);
     FI;
  ELSE IF DS, ES, FS, or GS is loaded with a NULL selector:
     THEN
       SegmentRegister <- NULLSelector;
       SegmentRegister(DescriptorValidBit) <- 0; FI; (* Hidden flag;
          not accessible by software *)
  FI;
  DEST <- Offset(SRC);
Real-Address or Virtual-8086 Mode
  SegmentRegister <- SegmentSelector(SRC); FI;
  DEST <- Offset(SRC);

Flags Affected:
None.


Protected Mode Exceptions:
| #UD            | If source operand is not a memory location.   
|                | If the LOCK prefix is used.                   
| #GP(0)         | If a NULL selector is loaded into the         
|                | SS register. If a memory operand effective    
|                | address is outside the CS, DS, ES, FS,        
|                | or GS segment limit. If the DS, ES,           
|                | FS, or GS register is used to access          
|                | memory and it contains a NULL segment         
|                | selector.                                     
| #GP(selector)  | If the SS register is being loaded and        
|                | any of the following is true: the segment     
|                | selector index is not within the descriptor   
|                | table limits, the segment selector RPL        
|                | is not equal to CPL, the segment is           
|                | a non-writable data segment, or DPL           
|                | is not equal to CPL. If the DS, ES,           
|                | FS, or GS register is being loaded with       
|                | a non-NULL segment selector and any           
|                | of the following is true: the segment         
|                | selector index is not within descriptor       
|                | table limits, the segment is neither          
|                | a data nor a readable code segment,           
|                | or the segment is a data or nonconforming-code
|                | segment and both RPL and CPL are greater      
|                | than DPL.                                     
| #SS(0)         | If a memory operand effective address         
|                | is outside the SS segment limit.              
| #SS(selector)  | If the SS register is being loaded and        
|                | the segment is marked not present.            
| #NP(selector)  | If DS, ES, FS, or GS register is being        
|                | loaded with a non-NULL segment selector       
|                | and the segment is marked not present.        
| #PF(fault-code)| If a page fault occurs.                       
| #AC(0)         | If alignment checking is enabled and          
|                | an unaligned memory reference is made         
|                | while the current privilege level is          
|                | 3.                                            

Real-Address Mode Exceptions:
| #GP| If a memory operand effective address      
|    | is outside the CS, DS, ES, FS, or GS       
|    | segment limit.                             
| #SS| If a memory operand effective address      
|    | is outside the SS segment limit.           
| #UD| If source operand is not a memory location.
|    | If the LOCK prefix is used.                

Virtual-8086 Mode Exceptions:
| #UD            | If source operand is not a memory location.
|                | If the LOCK prefix is used.                
| #GP(0)         | If a memory operand effective address      
|                | is outside the CS, DS, ES, FS, or GS       
|                | segment limit.                             
| #SS(0)         | If a memory operand effective address      
|                | is outside the SS segment limit.           
| #PF(fault-code)| If a page fault occurs.                    
| #AC(0)         | If alignment checking is enabled and       
|                | an unaligned memory reference is made.     

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #GP(0)         | If the memory address is in a non-canonical
|                | form. If a NULL selector is attempted      
|                | to be loaded into the SS register in       
|                | compatibility mode. If a NULL selector     
|                | is attempted to be loaded into the SS      
|                | register in CPL3 and 64-bit mode. If       
|                | a NULL selector is attempted to be loaded  
|                | into the SS register in non-CPL3 and       
|                | 64-bit mode where its RPL is not equal     
|                | to CPL.                                    
| #GP(Selector)  | If the FS, or GS register is being loaded  
|                | with a non-NULL segment selector and       
|                | any of the following is true: the segment  
|                | selector index is not within descriptor    
|                | table limits, the memory address of        
|                | the descriptor is non-canonical, the       
|                | segment is neither a data nor a readable   
|                | code segment, or the segment is a data     
|                | or nonconforming-code segment and both     
|                | RPL and CPL are greater than DPL. If       
|                | the SS register is being loaded and        
|                | any of the following is true: the segment  
|                | selector index is not within the descriptor
|                | table limits, the memory address of        
|                | the descriptor is non-canonical, the       
|                | segment selector RPL is not equal to       
|                | CPL, the segment is a nonwritable data     
|                | segment, or DPL is not equal to CPL.       
| #SS(0)         | If a memory operand effective address      
|                | is non-canonical                           
| #SS(Selector)  | If the SS register is being loaded and     
|                | the segment is marked not present.         
| #NP(selector)  | If FS, or GS register is being loaded      
|                | with a non-NULL segment selector and       
|                | the segment is marked not present.         
| #PF(fault-code)| If a page fault occurs.                    
| #AC(0)         | If alignment checking is enabled and       
|                | an unaligned memory reference is made      
|                | while the current privilege level is       
|                | 3.                                         
| #UD            | If source operand is not a memory location.
|                | If the LOCK prefix is used.                


platform: x86
mnem: LEA
description:
LEA - Load Effective Address:
| Opcode       | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                              
| 8D /r        | LEA r16,m  | RM   | Valid      | Valid          | Store effective address for m in register
|              |            |      |            |                | r16.                                     
| 8D /r        | LEA r32,m  | RM   | Valid      | Valid          | Store effective address for m in register
|              |            |      |            |                | r32.                                     
| REX.W + 8D /r| LEA r64,m  | RM   | Valid      | N.E.           | Store effective address for m in register
|              |            |      |            |                | r64.                                     

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
Computes the effective address of the second operand (the source operand) and
stores it in the first operand (destination operand). The source operand is
a memory address (offset part) specified with one of the processors addressing
modes; the destination operand is a general-purpose register. The address-size
and operand-size attributes affect the action performed by this instruction,
as shown in the following table. The operand-size attribute of the instruction
is determined by the chosen register; the address-size attribute is determined
by the attribute of the code segment.


Table 3-63. Non-64-bit Mode LEA Operation with Address and Operand Size Attributes:
| Operand Size 16 16 32 32| Address Size 16-bit effective address        | Action Performed
|                         | is calculated and stored in requested        |                 
|                         | 16-bit register destination. 32-bit          |                 
|                         | effective address is calculated. The         |                 
|                         | lower 16 bits of the address are stored      |                 
|                         | in the requested 16-bit register destination.|                 
|                         | 16-bit effective address is calculated.      |                 
|                         | The 16-bit address is zero-extended          |                 
|                         | and stored in the requested 32-bit register  |                 
|                         | destination. 32-bit effective address        |                 
|                         | is calculated and stored in the requested    |                 
|                         | 32-bit register destination.                 |                 
Different assemblers may use different algorithms based on the size attribute
and symbolic reference of the source operand.

In 64-bit mode, the instruction's destination operand is governed by operand
size attribute, the default operand size is 32 bits. Address calculation is
governed by address size attribute, the default address size is 64-bits. In
64bit mode, address size of 16 bits is not encodable. See Table 3-64.


Table 3-64. 64-bit Mode LEA Operation with Address and Operand Size Attributes:
| Operand Size 16 16 32 32 64 64| Address Size 32-bit effective address       | Action Performed
|                               | is calculated (using 67H prefix). The       |                 
|                               | lower 16 bits of the address are stored     |                 
|                               | in the requested 16-bit register destination|                 
|                               | (using 66H prefix). 64-bit effective        |                 
|                               | address is calculated (default address      |                 
|                               | size). The lower 16 bits of the address     |                 
|                               | are stored in the requested 16-bit register |                 
|                               | destination (using 66H prefix). 32-bit      |                 
|                               | effective address is calculated (using      |                 
|                               | 67H prefix) and stored in the requested     |                 
|                               | 32-bit register destination. 64-bit         |                 
|                               | effective address is calculated (default    |                 
|                               | address size) and the lower 32 bits         |                 
|                               | of the address are stored in the requested  |                 
|                               | 32-bit register destination. 32-bit         |                 
|                               | effective address is calculated (using      |                 
|                               | 67H prefix), zero-extended to 64-bits,      |                 
|                               | and stored in the requested 64-bit register |                 
|                               | destination (using REX.W). 64-bit effective |                 
|                               | address is calculated (default address      |                 
|                               | size) and all 64-bits of the address        |                 
|                               | are stored in the requested 64-bit register |                 
|                               | destination (using REX.W).                  |                 
Operation:

IF OperandSize = 16 and AddressSize = 16
  THEN
     DEST <- EffectiveAddress(SRC); (* 16-bit address *)
  ELSE IF OperandSize = 16 and AddressSize = 32
     THEN
       temp <- EffectiveAddress(SRC); (* 32-bit address *)
       DEST <- temp[0:15]; (* 16-bit address *)
     FI;
  ELSE IF OperandSize = 32 and AddressSize = 16
     THEN
       temp <- EffectiveAddress(SRC); (* 16-bit address *)
       DEST <- ZeroExtend(temp); (* 32-bit address *)
     FI;
  ELSE IF OperandSize = 32 and AddressSize = 32
     THEN
       DEST <- EffectiveAddress(SRC); (* 32-bit address *)
     FI;
  ELSE IF OperandSize = 16 and AddressSize = 64
     THEN
       temp <- EffectiveAddress(SRC); (* 64-bit address *)
       DEST <- temp[0:15]; (* 16-bit address *)
     FI;
  ELSE IF OperandSize = 32 and AddressSize = 64
     THEN
       temp <- EffectiveAddress(SRC); (* 64-bit address *)
       DEST <- temp[0:31]; (* 16-bit address *)
     FI;
  ELSE IF OperandSize = 64 and AddressSize = 64
     THEN
       DEST <- EffectiveAddress(SRC); (* 64-bit address *)
     FI;
FI;

Flags Affected:
None.


Protected Mode Exceptions:
| #UD| If source operand is not a memory location.
|    | If the LOCK prefix is used.                

Real-Address Mode Exceptions:
Same exceptions as in protected mode.


Virtual-8086 Mode Exceptions:
Same exceptions as in protected mode.


Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
Same exceptions as in protected mode.


platform: x86
mnem: LEAVE
description:
LEAVE - High Level Procedure Exit:
| Opcode| Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                  
| C9    | LEAVE      | NP   | Valid      | Valid          | Set SP to BP, then pop BP.   
| C9    | LEAVE      | NP   | N.E.       | Valid          | Set ESP to EBP, then pop EBP.
| C9    | LEAVE      | NP   | Valid      | N.E.           | Set RSP to RBP, then pop RBP.

Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| NP   | NA       | NA       | NA       | NA       

Description:
Releases the stack frame set up by an earlier ENTER instruction. The LEAVE instruction
copies the frame pointer (in the EBP register) into the stack pointer register
(ESP), which releases the stack space allocated to the stack frame. The old
frame pointer (the frame pointer for the calling procedure that was saved by
the ENTER instruction) is then popped from the stack into the EBP register,
restoring the calling procedure's stack frame.

A RET instruction is commonly executed following a LEAVE instruction to return
program control to the calling procedure.

See “Procedure Calls for Block-Structured Languages” in Chapter 7 of the Intel®
64 and IA-32 Architectures Software Developer's Manual, Volume 1, for detailed
information on the use of the ENTER and LEAVE instructions.

In 64-bit mode, the instruction's default operation size is 64 bits; 32-bit
operation cannot be encoded. See the summary chart at the beginning of this
section for encoding data and limits.

Operation:

IF StackAddressSize = 32
  THEN
     ESP <- EBP;
  ELSE IF StackAddressSize = 64
     THEN RSP <- RBP; FI;
  ELSE IF StackAddressSize = 16
     THEN SP <- BP; FI;
FI;
IF OperandSize = 32
  THEN EBP <- Pop();
  ELSE IF OperandSize = 64
     THEN RBP <- Pop(); FI;
  ELSE IF OperandSize = 16
     THEN BP <- Pop(); FI;
FI;

Flags Affected:
None.


Protected Mode Exceptions:
| #SS(0)         | If the EBP register points to a location
|                | that is not within the limits of the    
|                | current stack segment.                  
| #PF(fault-code)| If a page fault occurs.                 
| #AC(0)         | If alignment checking is enabled and    
|                | an unaligned memory reference is made   
|                | while the current privilege level is    
|                | 3.                                      
| #UD            | If the LOCK prefix is used.             

Real-Address Mode Exceptions:
| #GP| If the EBP register points to a location
|    | outside of the effective address space  
|    | from 0 to FFFFH.                        
| #UD| If the LOCK prefix is used.             

Virtual-8086 Mode Exceptions:
| #GP(0)         | If the EBP register points to a location
|                | outside of the effective address space  
|                | from 0 to FFFFH.                        
| #PF(fault-code)| If a page fault occurs.                 
| #AC(0)         | If alignment checking is enabled and    
|                | an unaligned memory reference is made.  
| #UD            | If the LOCK prefix is used.             

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)| If the stack address is in a non-canonical
|       | form.                                     
| #AC(0)| If alignment checking is enabled and      
|       | an unaligned memory reference is made     
|       | while the current privilege level is      
|       | 3.                                        
| #UD   | If the LOCK prefix is used.               


platform: x86
mnem: LFENCE
description:
LFENCE - Load Fence:
| Opcode  | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                
| 0F AE /5| LFENCE     | NP   | Valid      | Valid          | Serializes load operations.

Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| NP   | NA       | NA       | NA       | NA       

Description:
Performs a serializing operation on all load-from-memory instructions that were
issued prior the LFENCE instruction. Specifically, LFENCE does not execute until
all prior instructions have completed locally, and no later instruction begins
execution until LFENCE completes. In particular, an instruction that loads from
memory and that precedes an LFENCE receives data from memory prior to completion
of the LFENCE. (An LFENCE that follows an instruction that stores to memory
might complete before the data being stored have become globally visible.) Instructions
following an LFENCE may be fetched from memory before the LFENCE, but they will
not execute until the LFENCE completes.

Weakly ordered memory types can be used to achieve higher processor performance
through such techniques as out-of-order issue and speculative reads. The degree
to which a consumer of data recognizes or knows that the data is weakly ordered
varies among applications and may be unknown to the producer of this data. The
LFENCE instruction provides a performance-efficient way of ensuring load ordering
between routines that produce weaklyordered results and routines that consume
that data.

Processors are free to fetch and cache data speculatively from regions of system
memory that use the WB, WC, and WT memory types. This speculative fetching can
occur at any time and is not tied to instruction execution. Thus, it is not
ordered with respect to executions of the LFENCE instruction; data can be brought
into the caches speculatively just before, during, or after the execution of
an LFENCE instruction.

This instruction's operation is the same in non-64-bit modes and 64-bit mode.

Operation:

Wait_On_Following_Instructions_Until(preceding_instructions_complete);

Intel C/C++ Compiler Intrinsic Equivalent:
void _mm_lfence(void)


Exceptions (All Modes of Operation):
| #UD| If CPUID.01H:EDX.SSE2[bit 26] = 0. If
|    | the LOCK prefix is used.             


platform: x86
mnem: LGDT
description:
LGDT/LIDT - Load Global/Interrupt Descriptor Table Register:
| Opcode  | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description      
| 0F 01 /2| LGDT m16&32| M    | N.E.       | Valid          | Load m into GDTR.
| 0F 01 /3| LIDT m16&32| M    | N.E.       | Valid          | Load m into IDTR.
| 0F 01 /2| LGDT m16&64| M    | Valid      | N.E.           | Load m into GDTR.
| 0F 01 /3| LIDT m16&64| M    | Valid      | N.E.           | Load m into IDTR.

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2| Operand 3| Operand 4
| M    | ModRM:r/m (r)| NA       | NA       | NA       

Description:
Loads the values in the source operand into the global descriptor table register
(GDTR) or the interrupt descriptor table register (IDTR). The source operand
specifies a 6-byte memory location that contains the base address (a linear
address) and the limit (size of table in bytes) of the global descriptor table
(GDT) or the interrupt descriptor table (IDT). If operand-size attribute is
32 bits, a 16-bit limit (lower 2 bytes of the 6-byte data operand) and a 32bit
base address (upper 4 bytes of the data operand) are loaded into the register.
If the operand-size attribute is 16 bits, a 16-bit limit (lower 2 bytes) and
a 24-bit base address (third, fourth, and fifth byte) are loaded. Here, the
high-order byte of the operand is not used and the high-order byte of the base
address in the GDTR or IDTR is filled with zeros.

The LGDT and LIDT instructions are used only in operating-system software; they
are not used in application programs. They are the only instructions that directly
load a linear address (that is, not a segment-relative address) and a limit
in protected mode. They are commonly executed in real-address mode to allow
processor initialization prior to switching to protected mode.

In 64-bit mode, the instruction's operand size is fixed at 8+2 bytes (an 8-byte
base and a 2-byte limit). See the summary chart at the beginning of this section
for encoding data and limits.

See “SGDT - Store Global Descriptor Table Register” in Chapter 4, Intel® 64 and
IA-32 Architectures Software Developer's Manual, Volume 2B, for information
on storing the contents of the GDTR and IDTR.

Operation:

IF Instruction is LIDT
  THEN
     IF OperandSize = 16
       THEN
          IDTR(Limit) <- SRC[0:15];
          IDTR(Base) <- SRC[16:47] AND 00FFFFFFH;
       ELSE IF 32-bit Operand Size
          THEN
             IDTR(Limit) <- SRC[0:15];
             IDTR(Base) <- SRC[16:47];
          FI;
       ELSE IF 64-bit Operand Size (* In 64-Bit Mode *)
          THEN
             IDTR(Limit) <- SRC[0:15];
             IDTR(Base) <- SRC[16:79];
          FI;
     FI;
  ELSE (* Instruction is LGDT *)
     IF OperandSize = 16
       THEN
          GDTR(Limit) <- SRC[0:15];
          GDTR(Base) <- SRC[16:47] AND 00FFFFFFH;
       ELSE IF 32-bit Operand Size
          THEN
             GDTR(Limit) <- SRC[0:15];
             GDTR(Base) <- SRC[16:47];
          FI;
       ELSE IF 64-bit Operand Size (* In 64-Bit Mode *)
          THEN
             GDTR(Limit) <- SRC[0:15];
             GDTR(Base) <- SRC[16:79];
          FI;
     FI;
FI;

Flags Affected:
None.


Protected Mode Exceptions:
| #UD            | If source operand is not a memory location.
|                | If the LOCK prefix is used.                
| #GP(0)         | If the current privilege level is not      
|                | 0. If a memory operand effective address   
|                | is outside the CS, DS, ES, FS, or GS       
|                | segment limit. If the DS, ES, FS, or       
|                | GS register is used to access memory       
|                | and it contains a NULL segment selector.   
| #SS(0)         | If a memory operand effective address      
|                | is outside the SS segment limit.           
| #PF(fault-code)| If a page fault occurs.                    

Real-Address Mode Exceptions:
| #UD| If source operand is not a memory location.
|    | If the LOCK prefix is used.                
| #GP| If a memory operand effective address      
|    | is outside the CS, DS, ES, FS, or GS       
|    | segment limit.                             
| #SS| If a memory operand effective address      
|    | is outside the SS segment limit.           

Virtual-8086 Mode Exceptions:
| #UD   | If source operand is not a memory location.
|       | If the LOCK prefix is used.                
| #GP(0)| The LGDT and LIDT instructions are not     
|       | recognized in virtual-8086 mode.           
| #GP   | If the current privilege level is not      
|       | 0.                                         

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)         | If a memory address referencing the           
|                | SS segment is in a non-canonical form.        
| #GP(0)         | If the current privilege level is not         
|                | 0. If the memory address is in a non-canonical
|                | form.                                         
| #UD            | If source operand is not a memory location.   
|                | If the LOCK prefix is used.                   
| #PF(fault-code)| If a page fault occurs.                       


platform: x86
mnem: LLDT
description:
LLDT - Load Local Descriptor Table Register:
| Opcode  | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                           
| 0F 00 /2| LLDT r/m16 | M    | Valid      | Valid          | Load segment selector r/m16 into LDTR.

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2| Operand 3| Operand 4
| M    | ModRM:r/m (r)| NA       | NA       | NA       

Description:
Loads the source operand into the segment selector field of the local descriptor
table register (LDTR). The source operand (a general-purpose register or a memory
location) contains a segment selector that points to a local descriptor table
(LDT). After the segment selector is loaded in the LDTR, the processor uses
the segment selector to locate the segment descriptor for the LDT in the global
descriptor table (GDT). It then loads the segment limit and base address for
the LDT from the segment descriptor into the LDTR. The segment registers DS,
ES, SS, FS, GS, and CS are not affected by this instruction, nor is the LDTR
field in the task state segment (TSS) for the current task.

If bits 2-15 of the source operand are 0, LDTR is marked invalid and the LLDT
instruction completes silently. However, all subsequent references to descriptors
in the LDT (except by the LAR, VERR, VERW or LSL instructions) cause a general
protection exception (#GP).

The operand-size attribute has no effect on this instruction.

The LLDT instruction is provided for use in operating-system software; it should
not be used in application programs. This instruction can only be executed in
protected mode or 64-bit mode.

In 64-bit mode, the operand size is fixed at 16 bits.

Operation:

IF SRC(Offset) > descriptor table limit
  THEN #GP(segment selector); FI;
IF segment selector is valid
  Read segment descriptor;
  IF SegmentDescriptor(Type) != LDT
     THEN #GP(segment selector); FI;
  IF segment descriptor is not present
     THEN #NP(segment selector); FI;
  LDTR(SegmentSelector) <- SRC;
  LDTR(SegmentDescriptor) <- GDTSegmentDescriptor;
ELSE LDTR <- INVALID
FI;

Flags Affected:
None.


Protected Mode Exceptions:
| #GP(0)         | If the current privilege level is not   
|                | 0. If a memory operand effective address
|                | is outside the CS, DS, ES, FS, or GS    
|                | segment limit. If the DS, ES, FS, or    
|                | GS register contains a NULL segment     
|                | selector.                               
| #GP(selector)  | If the selector operand does not point  
|                | into the Global Descriptor Table or     
|                | if the entry in the GDT is not a Local  
|                | Descriptor Table. Segment selector is   
|                | beyond GDT limit.                       
| #SS(0)         | If a memory operand effective address   
|                | is outside the SS segment limit.        
| #NP(selector)  | If the LDT descriptor is not present.   
| #PF(fault-code)| If a page fault occurs.                 
| #UD            | If the LOCK prefix is used.             

Real-Address Mode Exceptions:
| #UD| The LLDT instruction is not recognized
|    | in real-address mode.                 

Virtual-8086 Mode Exceptions:
| #UD| The LLDT instruction is not recognized
|    | in virtual-8086 mode.                 

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)         | If a memory address referencing the           
|                | SS segment is in a non-canonical form.        
| #GP(0)         | If the current privilege level is not         
|                | 0. If the memory address is in a non-canonical
|                | form.                                         
| #GP(selector)  | If the selector operand does not point        
|                | into the Global Descriptor Table or           
|                | if the entry in the GDT is not a Local        
|                | Descriptor Table. Segment selector is         
|                | beyond GDT limit.                             
| #NP(selector)  | If the LDT descriptor is not present.         
| #PF(fault-code)| If a page fault occurs.                       
| #UD            | If the LOCK prefix is used.                   


platform: x86
mnem: LMSW
description:
LMSW - Load Machine Status Word:
| Opcode  | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                          
| 0F 01 /6| LMSW r/m16 | M    | Valid      | Valid          | Loads r/m16 in machine status word of
|         |            |      |            |                | CR0.                                 

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2| Operand 3| Operand 4
| M    | ModRM:r/m (r)| NA       | NA       | NA       

Description:
Loads the source operand into the machine status word, bits 0 through 15 of
register CR0. The source operand can be a 16-bit general-purpose register or
a memory location. Only the low-order 4 bits of the source operand (which contains
the PE, MP, EM, and TS flags) are loaded into CR0. The PG, CD, NW, AM, WP, NE,
and ET flags of CR0 are not affected. The operand-size attribute has no effect
on this instruction.

If the PE flag of the source operand (bit 0) is set to 1, the instruction causes
the processor to switch to protected mode. While in protected mode, the LMSW
instruction cannot be used to clear the PE flag and force a switch back to real-address
mode.

The LMSW instruction is provided for use in operating-system software; it should
not be used in application programs. In protected or virtual-8086 mode, it can
only be executed at CPL 0.

This instruction is provided for compatibility with the Intel 286 processor;
programs and procedures intended to run on the Pentium 4, Intel Xeon, P6 family,
Pentium, Intel486, and Intel386 processors should use the MOV (control registers)
instruction to load the whole CR0 register. The MOV CR0 instruction can be used
to set and clear the PE flag in CR0, allowing a procedure or program to switch
between protected and real-address modes.

This instruction is a serializing instruction.

This instruction's operation is the same in non-64-bit modes and 64-bit mode.
Note that the operand size is fixed at 16 bits.

See “Changes to Instruction Behavior in VMX Non-Root Operation” in Chapter 25
of the Intel® 64 and IA-32 Architectures Software Developer's Manual, Volume
3C, for more information about the behavior of this instruction in VMX non-root
operation.

Operation:

CR0[0:3] <- SRC[0:3];

Flags Affected:
None.


Protected Mode Exceptions:
| #GP(0)         | If the current privilege level is not   
|                | 0. If a memory operand effective address
|                | is outside the CS, DS, ES, FS, or GS    
|                | segment limit. If the DS, ES, FS, or    
|                | GS register is used to access memory    
|                | and it contains a NULL segment selector.
| #SS(0)         | If a memory operand effective address   
|                | is outside the SS segment limit.        
| #PF(fault-code)| If a page fault occurs.                 
| #UD            | If the LOCK prefix is used.             

Real-Address Mode Exceptions:
| #GP| If a memory operand effective address
|    | is outside the CS, DS, ES, FS, or GS 
|    | segment limit.                       
| #UD| If the LOCK prefix is used.          

Virtual-8086 Mode Exceptions:
| #GP(0)         | If a memory operand effective address
|                | is outside the CS, DS, ES, FS, or GS 
|                | segment limit.                       
| #SS(0)         | If a memory operand effective address
|                | is outside the SS segment limit.     
| #PF(fault-code)| If a page fault occurs.              
| #UD            | If the LOCK prefix is used.          

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)         | If a memory address referencing the           
|                | SS segment is in a non-canonical form.        
| #GP(0)         | If the current privilege level is not         
|                | 0. If the memory address is in a non-canonical
|                | form.                                         
| #PF(fault-code)| If a page fault occurs.                       
| #UD            | If the LOCK prefix is used.                   


platform: x86
mnem: LOCK
description:
LOCK - Assert LOCK# Signal Prefix:
| Opcode| Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                         
| F0    | LOCK       | NP   | Valid      | Valid          | Asserts LOCK# signal for duration of
|       |            |      |            |                | the accompanying instruction.       
Notes: * See IA-32 Architecture Compatibility section below.


Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| NP   | NA       | NA       | NA       | NA       

Description:
Causes the processor's LOCK# signal to be asserted during execution of the accompanying
instruction (turns the instruction into an atomic instruction). In a multiprocessor
environment, the LOCK# signal ensures that the processor has exclusive use of
any shared memory while the signal is asserted.

Note that, in later Intel 64 and IA-32 processors (including the Pentium 4,
Intel Xeon, and P6 family processors), locking may occur without the LOCK# signal
being asserted. See the “IA-32 Architecture Compatibility” section below.

The LOCK prefix can be prepended only to the following instructions and only
to those forms of the instructions where the destination operand is a memory
operand: ADD, ADC, AND, BTC, BTR, BTS, CMPXCHG, CMPXCH8B, CMPXCHG16B, DEC, INC,
NEG, NOT, OR, SBB, SUB, XOR, XADD, and XCHG. If the LOCK prefix is used with
one of these instructions and the source operand is a memory operand, an undefined
opcode exception (#UD) may be generated. An undefined opcode exception will
also be generated if the LOCK prefix is used with any instruction not in the
above list. The XCHG instruction always asserts the LOCK# signal regardless
of the presence or absence of the LOCK prefix.

The LOCK prefix is typically used with the BTS instruction to perform a read-modify-write
operation on a memory location in shared memory environment.

The integrity of the LOCK prefix is not affected by the alignment of the memory
field. Memory locking is observed for arbitrarily misaligned fields.

This instruction's operation is the same in non-64-bit modes and 64-bit mode.


IA-32 Architecture Compatibility:
Beginning with the P6 family processors, when the LOCK prefix is prefixed to
an instruction and the memory area being accessed is cached internally in the
processor, the LOCK# signal is generally not asserted. Instead, only the processor's
cache is locked. Here, the processor's cache coherency mechanism ensures that
the operation is carried out atomically with regards to memory. See “Effects
of a Locked Operation on Internal Processor Caches”in Chapter 8 of Intel® 64
and IA-32 Architectures Software Developer's Manual, Volume 3A, the for more
information on locking of caches.

Operation:

AssertLOCK#(DurationOfAccompaningInstruction);

Flags Affected:
None.


Protected Mode Exceptions:
| #UD| If the LOCK prefix is used with an instruction
|    | not listed: ADD, ADC, AND, BTC, BTR,          
|    | BTS, CMPXCHG, CMPXCH8B, CMPXCHG16B,           
|    | DEC, INC, NEG, NOT, OR, SBB, SUB, XOR,        
|    | XADD, XCHG. Other exceptions can be           
|    | generated by the instruction when the         
|    | LOCK prefix is applied.                       

Real-Address Mode Exceptions:
Same exceptions as in protected mode.


Virtual-8086 Mode Exceptions:
Same exceptions as in protected mode.


Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
Same exceptions as in protected mode.


platform: x86
mnem: LODS
description:
LODS/LODSB/LODSW/LODSD/LODSQ - Load String:
| Opcode    | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                            
| AC        | LODS m8    | NP   | Valid      | Valid          | For legacy mode, Load byte at address  
|           |            |      |            |                | DS:(E)SI into AL. For 64-bit mode load 
|           |            |      |            |                | byte at address (R)SI into AL.         
| AD        | LODS m16   | NP   | Valid      | Valid          | For legacy mode, Load word at address  
|           |            |      |            |                | DS:(E)SI into AX. For 64-bit mode load 
|           |            |      |            |                | word at address (R)SI into AX.         
| AD        | LODS m32   | NP   | Valid      | Valid          | For legacy mode, Load dword at address 
|           |            |      |            |                | DS:(E)SI into EAX. For 64-bit mode load
|           |            |      |            |                | dword at address (R)SI into EAX.       
| REX.W + AD| LODS m64   | NP   | Valid      | N.E.           | Load qword at address (R)SI into RAX.  
| AC        | LODSB      | NP   | Valid      | Valid          | For legacy mode, Load byte at address  
|           |            |      |            |                | DS:(E)SI into AL. For 64-bit mode load 
|           |            |      |            |                | byte at address (R)SI into AL.         
| AD        | LODSW      | NP   | Valid      | Valid          | For legacy mode, Load word at address  
|           |            |      |            |                | DS:(E)SI into AX. For 64-bit mode load 
|           |            |      |            |                | word at address (R)SI into AX.         
| AD        | LODSD      | NP   | Valid      | Valid          | For legacy mode, Load dword at address 
|           |            |      |            |                | DS:(E)SI into EAX. For 64-bit mode load
|           |            |      |            |                | dword at address (R)SI into EAX.       
| REX.W + AD| LODSQ      | NP   | Valid      | N.E.           | Load qword at address (R)SI into RAX.  

Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| NP   | NA       | NA       | NA       | NA       

Description:
Loads a byte, word, or doubleword from the source operand into the AL, AX, or
EAX register, respectively. The source operand is a memory location, the address
of which is read from the DS:ESI or the DS:SI registers (depending on the address-size
attribute of the instruction, 32 or 16, respectively). The DS segment may be
overridden with a segment override prefix.

At the assembly-code level, two forms of this instruction are allowed: the “explicit-operands”
form and the “nooperands” form. The explicit-operands form (specified with the
LODS mnemonic) allows the source operand to be specified explicitly. Here, the
source operand should be a symbol that indicates the size and location of the
source value. The destination operand is then automatically selected to match
the size of the source operand (the AL register for byte operands, AX for word
operands, and EAX for doubleword operands). This explicit-operands form is provided
to allow documentation; however, note that the documentation provided by this
form can be misleading. That is, the source operand symbol must specify the
correct type (size) of the operand (byte, word, or doubleword), but it does
not have to specify the correct location. The location is always specified by
the DS:(E)SI registers, which must be loaded correctly before the load string
instruction is executed.

The no-operands form provides “short forms” of the byte, word, and doubleword
versions of the LODS instructions. Here also DS:(E)SI is assumed to be the source
operand and the AL, AX, or EAX register is assumed to be the destination operand.
The size of the source and destination operands is selected with the mnemonic:
LODSB (byte loaded into register AL), LODSW (word loaded into AX), or LODSD
(doubleword loaded into EAX).

After the byte, word, or doubleword is transferred from the memory location
into the AL, AX, or EAX register, the (E)SI register is incremented or decremented
automatically according to the setting of the DF flag in the EFLAGS register.
(If the DF flag is 0, the (E)SI register is incremented; if the DF flag is 1,
the ESI register is decremented.) The (E)SI register is incremented or decremented
by 1 for byte operations, by 2 for word operations, or by 4 for doubleword operations.

In 64-bit mode, use of the REX.W prefix promotes operation to 64 bits. LODS/LODSQ
load the quadword at address (R)SI into RAX. The (R)SI register is then incremented
or decremented automatically according to the setting of the DF flag in the
EFLAGS register.

The LODS, LODSB, LODSW, and LODSD instructions can be preceded by the REP prefix
for block loads of ECX bytes, words, or doublewords. More often, however, these
instructions are used within a LOOP construct because

| further processing of the data moved        | usually necessary before the next transfer
| into the register is See “REP/REPE/REPZ     | can be made.                              
| /REPNE/REPNZ - Repeat String Operation        |                                           
| Prefix” in Chapter 4 of the Intel® 64       |                                           
| and IA-32 Architectures Software Developer's|                                           
| Manual, Volume 2B, for a description        |                                           
| of the REP prefix.                          |                                           
Operation:

IF AL <- SRC; (* Byte load *)
  THEN AL <- SRC; (* Byte load *)
     IF DF = 0
       THEN (E)SI <- (E)SI + 1;
       ELSE (E)SI <- (E)SI - 1;
     FI;
ELSE IF AX <- SRC; (* Word load *)
  THEN IF DF = 0
       THEN (E)SI <- (E)SI + 2;
       ELSE (E)SI <- (E)SI - 2;
     IF;
  FI;
ELSE IF EAX <- SRC; (* Doubleword load *)
  THEN IF DF = 0
       THEN (E)SI <- (E)SI + 4;
       ELSE (E)SI <- (E)SI - 4;
     FI;
  FI;
ELSE IF RAX <- SRC; (* Quadword load *)
  THEN IF DF = 0
       THEN (R)SI <- (R)SI + 8;
       ELSE (R)SI <- (R)SI - 8;
     FI;
  FI;
FI;

Flags Affected:
None.


Protected Mode Exceptions:
| #GP(0)         | If a memory operand effective address
|                | is outside the CS, DS, ES, FS, or GS 
|                | segment limit. If the DS, ES, FS, or 
|                | GS register contains a NULL segment  
|                | selector.                            
| #SS(0)         | If a memory operand effective address
|                | is outside the SS segment limit.     
| #PF(fault-code)| If a page fault occurs.              
| #AC(0)         | If alignment checking is enabled and 
|                | an unaligned memory reference is made
|                | while the current privilege level is 
|                | 3.                                   
| #UD            | If the LOCK prefix is used.          

Real-Address Mode Exceptions:
| #GP| If a memory operand effective address
|    | is outside the CS, DS, ES, FS, or GS 
|    | segment limit.                       
| #SS| If a memory operand effective address
|    | is outside the SS segment limit.     
| #UD| If the LOCK prefix is used.          

Virtual-8086 Mode Exceptions:
| #GP(0)         | If a memory operand effective address 
|                | is outside the CS, DS, ES, FS, or GS  
|                | segment limit.                        
| #SS(0)         | If a memory operand effective address 
|                | is outside the SS segment limit.      
| #PF(fault-code)| If a page fault occurs.               
| #AC(0)         | If alignment checking is enabled and  
|                | an unaligned memory reference is made.
| #UD            | If the LOCK prefix is used.           

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)         | If a memory address referencing the        
|                | SS segment is in a non-canonical form.     
| #GP(0)         | If the memory address is in a non-canonical
|                | form.                                      
| #PF(fault-code)| If a page fault occurs.                    
| #AC(0)         | If alignment checking is enabled and       
|                | an unaligned memory reference is made      
|                | while the current privilege level is       
|                | 3.                                         
| #UD            | If the LOCK prefix is used.                


platform: x86
mnem: LOOP
description:
LOOP/LOOPcc - Loop According to ECX Counter:
| Opcode| Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                         
| E2 cb | LOOP rel8  | D    | Valid      | Valid          | Decrement count; jump short if count
|       |            |      |            |                | != 0.                                
| E1 cb | LOOPE rel8 | D    | Valid      | Valid          | Decrement count; jump short if count
|       |            |      |            |                | != 0 and ZF = 1.                     
| E0 cb | LOOPNE rel8| D    | Valid      | Valid          | Decrement count; jump short if count
|       |            |      |            |                | != 0 and ZF = 0.                     

Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| D    | Offset   | NA       | NA       | NA       

Description:
Performs a loop operation using the RCX, ECX or CX register as a counter (depending
on whether address size is 64 bits, 32 bits, or 16 bits). Note that the LOOP
instruction ignores REX.W; but 64-bit address size can be over-ridden using
a 67H prefix.

Each time the LOOP instruction is executed, the count register is decremented,
then checked for 0. If the count is 0, the loop is terminated and program execution
continues with the instruction following the LOOP instruction. If the count
is not zero, a near jump is performed to the destination (target) operand, which
is presumably the instruction at the beginning of the loop.

The target instruction is specified with a relative offset (a signed offset
relative to the current value of the instruction pointer in the IP/EIP/RIP register).
This offset is generally specified as a label in assembly code, but at the machine
code level, it is encoded as a signed, 8-bit immediate value, which is added
to the instruction pointer. Offsets of -128 to +127 are allowed with this instruction.

Some forms of the loop instruction (LOOPcc) also accept the ZF flag as a condition
for terminating the loop before the count reaches zero. With these forms of
the instruction, a condition code (cc) is associated with each instruction to
indicate the condition being tested for. Here, the LOOPcc instruction itself
does not affect the state of the ZF flag; the ZF flag is changed by other instructions
in the loop.

Operation:

IF (AddressSize = 32)
  THEN Count is ECX;
ELSE IF (AddressSize = 64)
  Count is RCX;
ELSE Count is CX;
FI;
Count <- Count - 1;
IF Instruction is not LOOP
  THEN
     IF (Instruction <- LOOPE) or (Instruction <- LOOPZ)
       THEN IF (ZF = 1) and (Count != 0)
             THEN BranchCond <- 1;
             ELSE BranchCond <- 0;
          FI;
       ELSE (Instruction = LOOPNE) or (Instruction = LOOPNZ)
          IF (ZF = 0 ) and (Count != 0)
             THEN BranchCond <- 1;
             ELSE BranchCond <- 0;
          FI;
     FI;
  ELSE (* Instruction = LOOP *)
     IF (Count != 0)
       THEN BranchCond <- 1;
       ELSE BranchCond <- 0;
     FI;
FI;
IF BranchCond = 1
  THEN
     IF OperandSize = 32
       THEN EIP <- EIP + SignExtend(DEST);
       ELSE IF OperandSize = 64
          THEN RIP <- RIP + SignExtend(DEST);
          FI;
       ELSE IF OperandSize = 16
          THEN EIP <- EIP AND 0000FFFFH;
          FI;
     FI;
     IF OperandSize = (32 or 64)
       THEN IF (R/E)IP < CS.Base or (R/E)IP > CS.Limit
          #GP; FI;
          FI;
     FI;
  ELSE
     Terminate loop and continue program execution at (R/E)IP;
FI;

Flags Affected:
None.


Protected Mode Exceptions:
| #GP(0)| If the offset being jumped to is beyond
|       | the limits of the CS segment.          
| #UD   | If the LOCK prefix is used.            

Real-Address Mode Exceptions:
| #GP| If the offset being jumped to is beyond   
|    | the limits of the CS segment or is outside
|    | of the effective address space from       
|    | 0 to FFFFH. This condition can occur      
|    | if a 32-bit address size override prefix  
|    | is used.                                  
| #UD| If the LOCK prefix is used.               

Virtual-8086 Mode Exceptions:
Same exceptions as in real address mode.


Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #GP(0)| If the offset being jumped to is in
|       | a non-canonical form.              
| #UD   | If the LOCK prefix is used.        


platform: x86
mnem: LSL
description:
LSL - Load Segment Limit:
| Opcode          | Instruction      | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                        
| 0F 03 /r        | LSL r16, r16/m16 | RM   | Valid      | Valid          | Load: r16 ← segment limit, selector
|                 |                  |      |            |                | r16/m16.                           
| 0F 03 /r        | LSL r32, r32/m16*| RM   | Valid      | Valid          | Load: r32 ← segment limit, selector
|                 |                  |      |            |                | r32/m16.                           
| REX.W + 0F 03 /r| LSL r64, r32/m16*| RM   | Valid      | Valid          | Load: r64 ← segment limit, selector
|                 |                  |      |            |                | r32/m16                            
Notes: * For all loads (regardless of destination sizing), only bits 16-0 are
used. Other bits are ignored.


Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
Loads the unscrambled segment limit from the segment descriptor specified with
the second operand (source operand) into the first operand (destination operand)
and sets the ZF flag in the EFLAGS register. The source operand (which can be
a register or a memory location) contains the segment selector for the segment
descriptor being accessed. The destination operand is a general-purpose register.

The processor performs access checks as part of the loading process. Once loaded
in the destination register, software can compare the segment limit with the
offset of a pointer.

The segment limit is a 20-bit value contained in bytes 0 and 1 and in the first
4 bits of byte 6 of the segment descriptor. If the descriptor has a byte granular
segment limit (the granularity flag is set to 0), the destination operand is
loaded with a byte granular value (byte limit). If the descriptor has a page
granular segment limit (the granularity flag is set to 1), the LSL instruction
will translate the page granular limit (page limit) into a byte limit before
loading it into the destination operand. The translation is performed by shifting
the 20-bit “raw” limit left 12 bits and filling the low-order 12 bits with 1s.

When the operand size is 32 bits, the 32-bit byte limit is stored in the destination
operand. When the operand size is 16 bits, a valid 32-bit limit is computed;
however, the upper 16 bits are truncated and only the low-order 16 bits are
loaded into the destination operand.

This instruction performs the following checks before it loads the segment limit
into the destination register:

 - Checks that the segment selector is not NULL.
 - Checks that the segment selector points to a descriptor that is within the limits
of the GDT or LDT being accessed
 - Checks that the descriptor type is valid for this instruction. All code and
data segment descriptors are valid for (can be accessed with) the LSL instruction.
The valid special segment and gate descriptor types are given in the following
table.
 - If the segment is not a conforming code segment, the instruction checks that
the specified segment descriptor is visible at the CPL (that is, if the CPL
and the RPL of the segment selector are less than or equal to the DPL of the
segment selector).

If the segment descriptor cannot be accessed or is an invalid type for the instruction,
the ZF flag is cleared and no value is loaded in the destination operand.


Table 3-65. Segment and Gate Descriptor Types:
| Type                   | Protected Mode Valid| IA-32e Mode Valid
| Reserved               | No                  | Yes descriptor   
| Available 16-bit TSS   | Yes                 | No               
| LDT                    | Yes                 | Yes              
| Busy 16-bit TSS        | Yes                 | No               
| 16-bit call gate       | No                  | No               
| 16-bit/32-bit task gate| No                  | No               
| 16-bit interrupt gate  | No                  | No               
| 16-bit trap gate       | No                  | No               
| Reserved               | No                  | No               
| Available 32-bit TSS   | Yes                 | Yes              
| Reserved               | No                  | No               
| Busy 32-bit TSS        | Yes                 | Yes              
| 32-bit call gate       | No                  | No               
| Reserved               | No                  | No               
| 32-bit interrupt gate  | No                  | No               
| 32-bit trap gate       | No                  | No               
Operation:

IF SRC(Offset) > descriptor table limit
  THEN ZF <- 0; FI;
Read segment descriptor;
IF SegmentDescriptor(Type) != conforming code segment
and (CPL > DPL) OR (RPL > DPL)
or Segment type is not valid for instruction
     THEN
       ZF <- 0;
     ELSE
       temp <- SegmentLimit([SRC]);
       IF (G <- 1)
          THEN temp <- ShiftLeft(12, temp) OR 00000FFFH;
       ELSE IF OperandSize = 32
          THEN DEST <- temp; FI;
       ELSE IF OperandSize = 64 (* REX.W used *)
          THEN DEST (* Zero-extended *) <- temp; FI;
       ELSE (* OperandSize = 16 *)
          DEST <- temp AND FFFFH;
       FI;
FI;

Flags Affected:
The ZF flag is set to 1 if the segment limit is loaded successfully; otherwise,
it is set to 0.


Protected Mode Exceptions:
| #GP(0)         | If a memory operand effective address   
|                | is outside the CS, DS, ES, FS, or GS    
|                | segment limit. If the DS, ES, FS, or    
|                | GS register is used to access memory    
|                | and it contains a NULL segment selector.
| #SS(0)         | If a memory operand effective address   
|                | is outside the SS segment limit.        
| #PF(fault-code)| If a page fault occurs.                 
| #AC(0)         | If alignment checking is enabled and    
|                | the memory operand effective address    
|                | is unaligned while the current privilege
|                | level is 3.                             
| #UD            | If the LOCK prefix is used.             

Real-Address Mode Exceptions:
| #UD| The LSL instruction cannot be executed
|    | in real-address mode.                 

Virtual-8086 Mode Exceptions:
| #UD| The LSL instruction cannot be executed
|    | in virtual-8086 mode.                 

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)         | If the memory operand effective address         
|                | referencing the SS segment is in a non-canonical
|                | form.                                           
| #GP(0)         | If the memory operand effective address         
|                | is in a non-canonical form.                     
| #PF(fault-code)| If a page fault occurs.                         
| #AC(0)         | If alignment checking is enabled and            
|                | the memory operand effective address            
|                | is unaligned while the current privilege        
|                | level is 3.                                     
| #UD            | If the LOCK prefix is used.                     


platform: x86
mnem: LTR
description:
LTR - Load Task Register:
| Opcode  | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                   
| 0F 00 /3| LTR r/m16  | M    | Valid      | Valid          | Load r/m16 into task register.

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2| Operand 3| Operand 4
| M    | ModRM:r/m (r)| NA       | NA       | NA       

Description:
Loads the source operand into the segment selector field of the task register.
The source operand (a generalpurpose register or a memory location) contains
a segment selector that points to a task state segment (TSS). After the segment
selector is loaded in the task register, the processor uses the segment selector
to locate the segment descriptor for the TSS in the global descriptor table
(GDT). It then loads the segment limit and base address for the TSS from the
segment descriptor into the task register. The task pointed to by the task register
is marked busy, but a switch to the task does not occur.

The LTR instruction is provided for use in operating-system software; it should
not be used in application programs. It can only be executed in protected mode
when the CPL is 0. It is commonly used in initialization code to establish the
first task to be executed.

The operand-size attribute has no effect on this instruction.

In 64-bit mode, the operand size is still fixed at 16 bits. The instruction
references a 16-byte descriptor to load the 64-bit base.

Operation:

IF SRC is a NULL selector
  THEN #GP(0);
IF SRC(Offset) > descriptor table limit OR IF SRC(type) != global
  THEN #GP(segment selector); FI;
Read segment descriptor;
IF segment descriptor is not for an available TSS
  THEN #GP(segment selector); FI;
IF segment descriptor is not present
  THEN #NP(segment selector); FI;
TSSsegmentDescriptor(busy) <- 1;
(* Locked read-modify-write operation on the entire descriptor when setting busy flag *)
TaskRegister(SegmentSelector) <- SRC;
TaskRegister(SegmentDescriptor) <- TSSSegmentDescriptor;

Flags Affected:
None.


Protected Mode Exceptions:
| #GP(0)         | If the current privilege level is not     
|                | 0. If a memory operand effective address  
|                | is outside the CS, DS, ES, FS, or GS      
|                | segment limit. If the source operand      
|                | contains a NULL segment selector. If      
|                | the DS, ES, FS, or GS register is used    
|                | to access memory and it contains a NULL   
|                | segment selector.                         
| #GP(selector)  | If the source selector points to a segment
|                | that is not a TSS or to one for a task    
|                | that is already busy. If the selector     
|                | points to LDT or is beyond the GDT limit. 
| #NP(selector)  | If the TSS is marked not present.         
| #SS(0)         | If a memory operand effective address     
|                | is outside the SS segment limit.          
| #PF(fault-code)| If a page fault occurs.                   
| #UD            | If the LOCK prefix is used.               

Real-Address Mode Exceptions:
| #UD| The LTR instruction is not recognized
|    | in real-address mode.                

Virtual-8086 Mode Exceptions:
| #UD| The LTR instruction is not recognized
|    | in virtual-8086 mode.                

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)         | If a memory address referencing the           
|                | SS segment is in a non-canonical form.        
| #GP(0)         | If the current privilege level is not         
|                | 0. If the memory address is in a non-canonical
|                | form. If the source operand contains          
|                | a NULL segment selector.                      
| #GP(selector)  | If the source selector points to a segment    
|                | that is not a TSS or to one for a task        
|                | that is already busy. If the selector         
|                | points to LDT or is beyond the GDT limit.     
|                | If the descriptor type of the upper           
|                | 8-byte of the 16-byte descriptor is           
|                | non-zero.                                     
| #NP(selector)  | If the TSS is marked not present.             
| #PF(fault-code)| If a page fault occurs.                       
| #UD            | If the LOCK prefix is used.                   


platform: x86
mnem: LZCNT
description:
LZCNT -  Count the Number of Leading Zero Bits:
| Opcode/Instruction                  | Op/En| 64/32 -bit Mode| CPUID Feature Flag| Description                          
| F3 0F BD /r LZCNT r16, r/m16        | RM   | V/V            | LZCNT             | Count the number of leading zero bits
|                                     |      |                |                   | in r/m16, return result in r16.      
| F3 0F BD /r LZCNT r32, r/m32        | RM   | V/V            | LZCNT             | Count the number of leading zero bits
|                                     |      |                |                   | in r/m32, return result in r32.      
| REX.W + F3 0F BD /r LZCNT r64, r/m64| RM   | V/N.E.         | LZCNT             | Count the number of leading zero bits
|                                     |      |                |                   | in r/m64, return result in r64.      

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
Counts the number of leading most significant zero bits in a source operand
(second operand) returning the result into a destination (first operand). LZCNT
differs from BSR. For example, LZCNT will produce the operand size when the
input operand is zero. It should be noted that on processors that do not support
LZCNT, the instruction byte encoding is executed as BSR. In 64-bit mode 64-bit
operand size requires REX.W=1.

Operation:

temp <- OperandSize - 1
DEST <- 0
WHILE (temp >= 0) AND (Bit(SRC, temp) = 0)
DO
  temp <- temp - 1
  DEST <- DEST+ 1
OD
IF DEST = OperandSize
  CF <- 1
ELSE
  CF <- 0
FI
IF DEST = 0
  ZF <- 1
ELSE
  ZF <- 0
FI

Flags Affected:
ZF flag is set to 1 in case of zero output (most significant bit of the source
is set), and to 0 otherwise, CF flag is set to 1 if input was zero and cleared
otherwise. OF, SF, PF and AF flags are undefined.


Intel C/C++ Compiler Intrinsic Equivalent:
| LZCNT:| unsigned __int32 _lzcnt_u32(unsigned
|       | __int32 src);                       
| LZCNT:| unsigned __int64 _lzcnt_u64(unsigned
|       | __int64 src);                       

Protected Mode Exceptions:
| #GP(0)          | For an illegal memory operand effective    
|                 | address in the CS, DS, ES, FS or GS        
|                 | segments. If the DS, ES, FS, or GS register
|                 | is used to access memory and it contains   
|                 | a null segment selector.                   
| #SS(0)          | For an illegal address in the SS segment.  
| #PF (fault-code)| For a page fault.                          
| #AC(0)          | If alignment checking is enabled and       
|                 | an unaligned memory reference is made      
|                 | while the current privilege level is       
|                 | 3.                                         

Real-Address Mode Exceptions:
| #GP(0)| If any part of the operand lies outside  
|       | of the effective address space from      
|       | 0 to 0FFFFH.                             
| #SS(0)| For an illegal address in the SS segment.

Virtual 8086 Mode Exceptions:
| #GP(0)          | If any part of the operand lies outside  
|                 | of the effective address space from      
|                 | 0 to 0FFFFH.                             
| #SS(0)          | For an illegal address in the SS segment.
| #PF (fault-code)| For a page fault.                        
| #AC(0)          | If alignment checking is enabled and     
|                 | an unaligned memory reference is made    
|                 | while the current privilege level is     
|                 | 3.                                       

Compatibility Mode Exceptions:
Same exceptions as in Protected Mode.


64-Bit Mode Exceptions:
| #GP(0)          | If the memory address is in a non-canonical
|                 | form.                                      
| #SS(0)          | If a memory address referencing the        
|                 | SS segment is in a non-canonical form.     
| #PF (fault-code)| For a page fault.                          
| #AC(0)          | If alignment checking is enabled and       
|                 | an unaligned memory reference is made      
|                 | while the current privilege level is       
|                 | 3.                                         


platform: x86
mnem: MASKMOVDQU
description:
MASKMOVDQU - Store Selected Bytes of Double Quadword:
| Opcode/Instruction                 | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                         
| 66 0F F7 /r MASKMOVDQU xmm1, xmm2  | RM   | V/V           | SSE2              | Selectively write bytes from xmm1 to
|                                    |      |               |                   | memory location using the byte mask 
|                                    |      |               |                   | in xmm2. The default memory location
|                                    |      |               |                   | is specified by DS:DI/EDI/RDI.      
| VEX.128.66.0F.WIG F7 /r VMASKMOVDQU| RM   | V/V           | AVX               | Selectively write bytes from xmm1 to
| xmm1, xmm2                         |      |               |                   | memory location using the byte mask 
|                                    |      |               |                   | in xmm2. The default memory location
|                                    |      |               |                   | is specified by DS:DI/EDI/RDI.      

Instruction Operand Encoding1:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (r)| ModRM:r/m (r)| NA       | NA       

Description:
Stores selected bytes from the source operand (first operand) into an 128-bit
memory location. The mask operand (second operand) selects which bytes from
the source operand are written to memory. The source and mask operands are XMM
registers. The memory location specified by the effective address in the DI/EDI/RDI
register (the default segment register is DS, but this may be overridden with
a segment-override prefix). The memory location does not need to be aligned
on a natural boundary. (The size of the store address depends on the address-size
attribute.)

The most significant bit in each byte of the mask operand determines whether
the corresponding byte in the source operand is written to the corresponding
byte location in memory: 0 indicates no write and 1 indicates write.

The MASKMOVDQU instruction generates a non-temporal hint to the processor to
minimize cache pollution. The non-temporal hint is implemented by using a write
combining (WC) memory type protocol (see “Caching of Temporal vs. Non-Temporal
Data” in Chapter 10, of the Intel® 64 and IA-32 Architectures Software Developer's
Manual, Volume 1). Because the WC protocol uses a weakly-ordered memory consistency
model, a fencing operation implemented with the SFENCE or MFENCE instruction
should be used in conjunction with MASKMOVDQU instructions if multiple processors
might use different memory types to read/write the destination memory locations.

Behavior with a mask of all 0s is as follows:

 - No data will be written to memory.
 - Signaling of breakpoints (code or data) is not guaranteed; different processor
implementations may signal or not signal these breakpoints.
 - Exceptions associated with addressing memory and page faults may still be signaled
(implementation dependent).
 - If the destination memory region is mapped as UC or WP, enforcement of associated
semantics for these memory types is not guaranteed (that is, is reserved) and
is implementation-specific.

The MASKMOVDQU instruction can be used to improve performance of algorithms
that need to merge data on a byte-by-byte basis. MASKMOVDQU should not cause
a read for ownership; doing so generates unnecessary bandwidth since data is
to be written directly using the byte-mask without allocating old data prior
to the store.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). Note: In VEX-encoded versions, VEX.vvvv is reserved
and must be 1111b otherwise instructions will #UD. If VMASKMOVDQU is encoded
with VEX.L= 1, an attempt to execute the instruction encoded with VEX.L= 1 will
cause an #UD exception.

1.ModRM.MOD = 011B required

Operation:

IF (MASK[7] = 1)
  THEN DEST[DI/EDI] <- SRC[7:0] ELSE (* Memory location unchanged *); FI;
IF (MASK[15] = 1)
  THEN DEST[DI/EDI +1] <- SRC[15:8] ELSE (* Memory location unchanged *); FI;
  (* Repeat operation for 3rd through 14th bytes in source operand *)
IF (MASK[127] = 1)
  THEN DEST[DI/EDI +15] <- SRC[127:120] ELSE (* Memory location unchanged *); FI;

Intel C/C++ Compiler Intrinsic Equivalent:
void _mm_maskmoveu_si128(__m128i d, __m128i n, char * p)


Other Exceptions:
See Exceptions Type 4; additionally

| #UD| If VEX.L= 1 If VEX.vvvv != 1111B.


platform: x86
mnem: MASKMOVQ
description:
MASKMOVQ - Store Selected Bytes of Quadword:
| Opcode/Instruction        | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                        
| 0F F7 /r MASKMOVQ mm1, mm2| RM   | Valid      | Valid          | Selectively write bytes from mm1 to
|                           |      |            |                | memory location using the byte mask
|                           |      |            |                | in mm2. The default memory location
|                           |      |            |                | is specified by DS:DI/EDI/RDI.     

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (r)| ModRM:r/m (r)| NA       | NA       

Description:
Stores selected bytes from the source operand (first operand) into a 64-bit
memory location. The mask operand (second operand) selects which bytes from
the source operand are written to memory. The source and mask operands are MMX
technology registers. The memory location specified by the effective address
in the DI/EDI/RDI register (the default segment register is DS, but this may
be overridden with a segment-override prefix). The memory location does not
need to be aligned on a natural boundary. (The size of the store address depends
on the address-size attribute.)

The most significant bit in each byte of the mask operand determines whether
the corresponding byte in the source operand is written to the corresponding
byte location in memory: 0 indicates no write and 1 indicates write.

The MASKMOVQ instruction generates a non-temporal hint to the processor to minimize
cache pollution. The nontemporal hint is implemented by using a write combining
(WC) memory type protocol (see “Caching of Temporal vs. Non-Temporal Data” in
Chapter 10, of the Intel® 64 and IA-32 Architectures Software Developer's Manual,
Volume 1). Because the WC protocol uses a weakly-ordered memory consistency
model, a fencing operation implemented with the SFENCE or MFENCE instruction
should be used in conjunction with MASKMOVQ instructions if multiple processors
might use different memory types to read/write the destination memory locations.

This instruction causes a transition from x87 FPU to MMX technology state (that
is, the x87 FPU top-of-stack pointer is set to 0 and the x87 FPU tag word is
set to all 0s [valid]).

The behavior of the MASKMOVQ instruction with a mask of all 0s is as follows:

 - No data will be written to memory.
 - Transition from x87 FPU to MMX technology state will occur.
 - Exceptions associated with addressing memory and page faults may still be signaled
(implementation dependent).
 - Signaling of breakpoints (code or data) is not guaranteed (implementation dependent).
 - If the destination memory region is mapped as UC or WP, enforcement of associated
semantics for these memory types is not guaranteed (that is, is reserved) and
is implementation-specific.

The MASKMOVQ instruction can be used to improve performance for algorithms that
need to merge data on a byteby-byte basis. It should not cause a read for ownership;
doing so generates unnecessary bandwidth since data is to be written directly
using the byte-mask without allocating old data prior to the store. In 64-bit
mode, the memory address is specified by DS:RDI.

Operation:

IF (MASK[7] = 1)
  THEN DEST[DI/EDI] <- SRC[7:0] ELSE (* Memory location unchanged *); FI;
IF (MASK[15] = 1)
  THEN DEST[DI/EDI +1] <- SRC[15:8] ELSE (* Memory location unchanged *); FI;
  (* Repeat operation for 3rd through 6th bytes in source operand *)
IF (MASK[63] = 1)
  THEN DEST[DI/EDI +15] <- SRC[63:56] ELSE (* Memory location unchanged *); FI;

Intel C/C++ Compiler Intrinsic Equivalent:
void _mm_maskmove_si64(__m64d, __m64n, char * p)


Other Exceptions:
See Table 22-8, “Exception Conditions for Legacy SIMD/MMX Instructions without
FP Exception,” in the Intel® 64 and IA-32 Architectures Software Developer's
Manual, Volume 3A.


platform: x86
mnem: MAXPD
description:
MAXPD - Return Maximum Packed Double-Precision Floating-Point Values:
| Opcode/Instruction                           | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                               
| 66 0F 5F /r MAXPD xmm1, xmm2/m128            | RM   | V/V           | SSE2              | Return the maximum double-precision       
|                                              |      |               |                   | floating-point values between xmm2/m128   
|                                              |      |               |                   | and xmm1.                                 
| VEX.NDS.128.66.0F.WIG 5F /r VMAXPD xmm1,xmm2,| RVM  | V/V           | AVX               | Return the maximum double-precision       
| xmm3/m128                                    |      |               |                   | floating-point values between xmm2 and    
|                                              |      |               |                   | xmm3/mem.                                 
| VEX.NDS.256.66.0F.WIG 5F /r VMAXPD ymm1,     | RVM  | V/V           | AVX               | Return the maximum packed double-precision
| ymm2, ymm3/m256                              |      |               |                   | floating-point values between ymm2 and    
|                                              |      |               |                   | ymm3/mem.                                 

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
Performs an SIMD compare of the packed double-precision floating-point values
in the first source operand and the second source operand and returns the maximum
value for each pair of values to the destination operand. If the values being
compared are both 0.0s (of either sign), the value in the second operand (source
operand) is returned. If a value in the second operand is an SNaN, that SNaN
is forwarded unchanged to the destination (that is, a QNaN version of the SNaN
is not returned). If only one value is a NaN (SNaN or QNaN) for this instruction,
the second operand (source operand), either a NaN or a valid floating-point
value, is written to the result. If instead of this behavior, it is required
that the NaN source operand (from either the first or second operand) be returned,
the action of MAXPD can be emulated using a sequence of instructions, such as,
a comparison followed by AND, ANDN and OR.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). 128-bit Legacy SSE version: The second source can be
an XMM register or an 128-bit memory location. The destination is not distinct
from the first source XMM register and the upper bits (VLMAX-1:128) of the corresponding
YMM register destination are unmodified. VEX.128 encoded version: the first
source operand is an XMM register or 128-bit memory location. The destination
operand is an XMM register. The upper bits (VLMAX-1:128) of the corresponding
YMM register destination are zeroed. VEX.256 encoded version: The first source
operand is a YMM register. The second source operand can be a YMM register or
a 256-bit memory location. The destination operand is a YMM register.

Operation:

MAX(SRC1, SRC2)
{
  IF ((SRC1 = 0.0) and (SRC2 = 0.0)) THEN DEST <- SRC2;
     ELSE IF (SRC1 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF (SRC2 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF (SRC1 > SRC2) THEN DEST <- SRC1;
     ELSE DEST <- SRC2;
  FI;
}
MAXPD (128-bit Legacy SSE version)
DEST[63:0] <- MAX(DEST[63:0], SRC[63:0])
DEST[127:64] <- MAX(DEST[127:64], SRC[127:64])
DEST[VLMAX-1:128] (Unmodified)
VMAXPD (VEX.128 encoded version)
DEST[63:0] <- MAX(SRC1[63:0], SRC2[63:0])
DEST[127:64] <- MAX(SRC1[127:64], SRC2[127:64])
DEST[VLMAX-1:128] <- 0
VMAXPD (VEX.256 encoded version)
DEST[63:0] <- MAX(SRC1[63:0], SRC2[63:0])
DEST[127:64] <- MAX(SRC1[127:64], SRC2[127:64])
DEST[191:128] <- MAX(SRC1[191:128], SRC2[191:128])
DEST[255:192] <- MAX(SRC1[255:192], SRC2[255:192])

Intel C/C++ Compiler Intrinsic Equivalent:
| MAXPD: | __m128d _mm_max_pd(__m128d a, __m128d    
|        | b);                                      
| VMAXPD:| __m256d _mm256_max_pd (__m256d a, __m256d
|        | b);                                      

SIMD Floating-Point Exceptions:
Invalid (including QNaN source operand), Denormal.


Other Exceptions:
See Exceptions Type 2.


platform: x86
mnem: MAXPS
description:
MAXPS - Return Maximum Packed Single-Precision Floating-Point Values:
| Opcode/Instruction                        | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                               
| 0F 5F /r MAXPS xmm1, xmm2/m128            | RM   | V/V           | SSE               | Return the maximum single-precision       
|                                           |      |               |                   | floatingpoint values between xmm2/m128    
|                                           |      |               |                   | and xmm1.                                 
| VEX.NDS.128.0F.WIG 5F /r VMAXPS xmm1,xmm2,| RVM  | V/V           | AVX               | Return the maximum single-precision       
| xmm3/m128                                 |      |               |                   | floatingpoint values between xmm2 and     
|                                           |      |               |                   | xmm3/mem.                                 
| VEX.NDS.256.0F.WIG 5F /r VMAXPS ymm1,     | RVM  | V/V           | AVX               | Return the maximum single double-precision
| ymm2, ymm3/m256                           |      |               |                   | floating-point values between ymm2 and    
|                                           |      |               |                   | ymm3/mem.                                 

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
Performs an SIMD compare of the packed single-precision floating-point values
in the first source operand and the second source operand and returns the maximum
value for each pair of values to the destination operand. If the values being
compared are both 0.0s (of either sign), the value in the second operand (source
operand) is returned. If a value in the second operand is an SNaN, that SNaN
is forwarded unchanged to the destination (that is, a QNaN version of the SNaN
is not returned). If only one value is a NaN (SNaN or QNaN) for this instruction,
the second operand (source operand), either a NaN or a valid floating-point
value, is written to the result. If instead of this behavior, it is required
that the NaN source operand (from either the first or second operand) be returned,
the action of MAXPS can be emulated using a sequence of instructions, such as,
a comparison followed by AND, ANDN and OR.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). 128-bit Legacy SSE version: The second source can be
an XMM register or an 128-bit memory location. The destination is not distinct
from the first source XMM register and the upper bits (VLMAX-1:128) of the corresponding
YMM register destination are unmodified. VEX.128 encoded version: the first
source operand is an XMM register or 128-bit memory location. The destination
operand is an XMM register. The upper bits (VLMAX-1:128) of the corresponding
YMM register destination are zeroed. VEX.256 encoded version: The first source
operand is a YMM register. The second source operand can be a YMM register or
a 256-bit memory location. The destination operand is a YMM register.

Operation:

MAX(SRC1, SRC2)
{
  IF ((SRC1 = 0.0) and (SRC2 = 0.0)) THEN DEST <- SRC2;
     ELSE IF (SRC1 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF SRC2 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF (SRC1 > SRC2) THEN DEST <- SRC1;
     ELSE DEST <- SRC2;
  FI;
}
MAXPS (128-bit Legacy SSE version)
DEST[31:0] <- MAX(DEST[31:0], SRC[31:0])
DEST[63:32] <- MAX(DEST[63:32], SRC[63:32])
DEST[95:64] <- MAX(DEST[95:64], SRC[95:64])
DEST[127:96] <- MAX(DEST[127:96], SRC[127:96])
DEST[VLMAX-1:128] (Unmodified)
VMAXPS (VEX.128 encoded version)
DEST[31:0] <- MAX(SRC1[31:0], SRC2[31:0])
DEST[63:32] <- MAX(SRC1[63:32], SRC2[63:32])
DEST[95:64] <- MAX(SRC1[95:64], SRC2[95:64])
DEST[127:96] <- MAX(SRC1[127:96], SRC2[127:96])
DEST[VLMAX-1:128] <- 0
VMAXPS (VEX.256 encoded version)
DEST[31:0] <- MAX(SRC1[31:0], SRC2[31:0])
DEST[63:32] <- MAX(SRC1[63:32], SRC2[63:32])
DEST[95:64] <- MAX(SRC1[95:64], SRC2[95:64])
DEST[127:96] <- MAX(SRC1[127:96], SRC2[127:96])
DEST[159:128] <- MAX(SRC1[159:128], SRC2[159:128])
DEST[191:160] <- MAX(SRC1[191:160], SRC2[191:160])
DEST[223:192] <- MAX(SRC1[223:192], SRC2[223:192])
DEST[255:224] <- MAX(SRC1[255:224], SRC2[255:224])

Intel C/C++ Compiler Intrinsic Equivalent:
| MAXPS: | __m128 _mm_max_ps (__m128 a, __m128   
|        | b);                                   
| VMAXPS:| __m256 _mm256_max_ps (__m256 a, __m256
|        | b);                                   

SIMD Floating-Point Exceptions:
Invalid (including QNaN source operand), Denormal.


Other Exceptions:
See Exceptions Type 2.


platform: x86
mnem: MAXSD
description:
MAXSD - Return Maximum Scalar Double-Precision Floating-Point Value:
| Opcode/Instruction                      | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                               
| F2 0F 5F /r MAXSD xmm1, xmm2/m64        | RM   | V/V           | SSE2              | Return the maximum scalar double-precision
|                                         |      |               |                   | floating-point value between xmm2/mem64   
|                                         |      |               |                   | and xmm1.                                 
| VEX.NDS.LIG.F2.0F.WIG 5F /r VMAXSD xmm1,| RVM  | V/V           | AVX               | Return the maximum scalar double-precision
| xmm2, xmm3/m64                          |      |               |                   | floating-point value between xmm3/mem64   
|                                         |      |               |                   | and xmm2.                                 

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
Compares the low double-precision floating-point values in the first source
operand and second the source operand, and returns the maximum value to the
low quadword of the destination operand. The second source operand can be an
XMM register or a 64-bit memory location. The first source and destination operands
are XMM registers. When the second source operand is a memory operand, only
64 bits are accessed. The high quadword of the destination operand is copied
from the same bits of first source operand. If the values being compared are
both 0.0s (of either sign), the value in the second source operand is returned.
If a value in the second source operand is an SNaN, that SNaN is returned unchanged
to the destination (that is, a QNaN version of the SNaN is not returned). If
only one value is a NaN (SNaN or QNaN) for this instruction, the second source
operand, either a NaN or a valid floating-point value, is written to the result.
If instead of this behavior, it is required that the NaN of either source operand
be returned, the action of MAXSD can be emulated using a sequence of instructions,
such as, a comparison followed by AND, ANDN and OR. The second source operand
can be an XMM register or a 64-bit memory location. The first source and destination
operands are XMM registers.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). 128-bit Legacy SSE version: The destination and first
source operand are the same. Bits (VLMAX-1:64) of the corresponding YMM destination
register remain unchanged. VEX.128 encoded version: Bits (127:64) of the XMM
register destination are copied from corresponding bits in the first source
operand. Bits (VLMAX-1:128) of the destination YMM register are zeroed.

Operation:

MAX(SRC1, SRC2)
{
  IF ((SRC1 = 0.0) and (SRC2 = 0.0)) THEN DEST <- SRC2;
     ELSE IF (SRC1 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF SRC2 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF (SRC1 > SRC2) THEN DEST <- SRC1;
     ELSE DEST <- SRC2;
  FI;
}
MAXSD (128-bit Legacy SSE version)
DEST[63:0] <-MAX(DEST[63:0], SRC[63:0])
DEST[VLMAX-1:64] (Unmodified)
VMAXSD (VEX.128 encoded version)
DEST[63:0] <-MAX(SRC1[63:0], SRC2[63:0])
DEST[127:64] <-SRC1[127:64]
DEST[VLMAX-1:128] <- 0

Intel C/C++ Compiler Intrinsic Equivalent:
| MAXSD:| __m128d _mm_max_sd(__m128d a, __m128d
|       | b)                                   

SIMD Floating-Point Exceptions:
Invalid (including QNaN source operand), Denormal.


Other Exceptions:
See Exceptions Type 3.


platform: x86
mnem: MAXSS
description:
MAXSS - Return Maximum Scalar Single-Precision Floating-Point Value:
| Opcode/Instruction                      | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                               
| F3 0F 5F /r MAXSS xmm1, xmm2/m32        | RM   | V/V           | SSE               | Return the maximum scalar single-precision
|                                         |      |               |                   | floating-point value between xmm2/mem32   
|                                         |      |               |                   | and xmm1.                                 
| VEX.NDS.LIG.F3.0F.WIG 5F /r VMAXSS xmm1,| RVM  | V/V           | AVX               | Return the maximum scalar single-precision
| xmm2, xmm3/m32                          |      |               |                   | floating-point value between xmm3/mem32   
|                                         |      |               |                   | and xmm2.                                 

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
Compares the low single-precision floating-point values in the first source
operand and the second source operand, and returns the maximum value to the
low doubleword of the destination operand. If the values being compared are
both 0.0s (of either sign), the value in the second source operand is returned.
If a value in the second source operand is an SNaN, that SNaN is returned unchanged
to the destination (that is, a QNaN version of the SNaN is not returned). If
only one value is a NaN (SNaN or QNaN) for this instruction, the second source
operand, either a NaN or a valid floating-point value, is written to the result.
If instead of this behavior, it is required that the NaN from either source
operand be returned, the action of MAXSS can be emulated using a sequence of
instructions, such as, a comparison followed by AND, ANDN and OR. The second
source operand can be an XMM register or a 32-bit memory location. The first
source and destination operands are XMM registers.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). 128-bit Legacy SSE version: The destination and first
source operand are the same. Bits (VLMAX-1:32) of the corresponding YMM destination
register remain unchanged. VEX.128 encoded version: Bits (127:32) of the XMM
register destination are copied from corresponding bits in the first source
operand. Bits (VLMAX-1:128) of the destination YMM register are zeroed.

Operation:

MAX(SRC1, SRC2)
{
  IF ((SRC1 = 0.0) and (SRC2 = 0.0)) THEN DEST <- SRC2;
     ELSE IF (SRC1 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF SRC2 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF (SRC1 > SRC2) THEN DEST <- SRC1;
     ELSE DEST <- SRC2;
  FI;
}
MAXSS (128-bit Legacy SSE version)
DEST[31:0] <-MAX(DEST[31:0], SRC[31:0])
DEST[VLMAX-1:32] (Unmodified)
VMAXSS (VEX.128 encoded version)
DEST[31:0] <-MAX(SRC1[31:0], SRC2[31:0])
DEST[127:32] <-SRC1[127:32]
DEST[VLMAX-1:128] <- 0

Intel C/C++ Compiler Intrinsic Equivalent:
__m128d _mm_max_ss(__m128d a, __m128d b)


SIMD Floating-Point Exceptions:
Invalid (including QNaN source operand), Denormal.


Other Exceptions:
See Exceptions Type 3.


platform: x86
mnem: MFENCE
description:
MFENCE - Memory Fence:
| Opcode  | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                          
| 0F AE /6| MFENCE     | NP   | Valid      | Valid          | Serializes load and store operations.

Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| NP   | NA       | NA       | NA       | NA       

Description:
Performs a serializing operation on all load-from-memory and store-to-memory
instructions that were issued prior the MFENCE instruction. This serializing
operation guarantees that every load and store instruction that precedes the
MFENCE instruction in program order becomes globally visible before any load
or store instruction that follows the MFENCE instruction.1 The MFENCE instruction
is ordered with respect to all load and store instructions, other MFENCE instructions,
any LFENCE and SFENCE instructions, and any serializing instructions (such as
the CPUID instruction). MFENCE does not serialize the instruction stream.

Weakly ordered memory types can be used to achieve higher processor performance
through such techniques as out-of-order issue, speculative reads, write-combining,
and write-collapsing. The degree to which a consumer of data recognizes or knows
that the data is weakly ordered varies among applications and may be unknown
to the producer of this data. The MFENCE instruction provides a performance-efficient
way of ensuring load and store ordering between routines that produce weakly-ordered
results and routines that consume that data.

Processors are free to fetch and cache data speculatively from regions of system
memory that use the WB, WC, and WT memory types. This speculative fetching can
occur at any time and is not tied to instruction execution. Thus, it is not
ordered with respect to executions of the MFENCE instruction; data can be brought
into the caches speculatively just before, during, or after the execution of
an MFENCE instruction.

This instruction's operation is the same in non-64-bit modes and 64-bit mode.

Operation:

Wait_On_Following_Loads_And_Stores_Until(preceding_loads_and_stores_globally_visible);

Intel C/C++ Compiler Intrinsic Equivalent:
void _mm_mfence(void)


Exceptions (All Modes of Operation):
| #UD| If CPUID.01H:EDX.SSE2[bit 26] = 0. If     
|    | the LOCK prefix is used.                  
| 1. | A load instruction is considered to       
|    | become globally visible when the value    
|    | to be loaded into its destination register
|    | is determined.                            


platform: x86
mnem: MINPD
description:
MINPD - Return Minimum Packed Double-Precision Floating-Point Values:
| Opcode/Instruction                           | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                               
| 66 0F 5D /r MINPD xmm1, xmm2/m128            | RM   | V/V           | SSE2              | Return the minimum double-precision       
|                                              |      |               |                   | floating-point values between xmm2/m128   
|                                              |      |               |                   | and xmm1.                                 
| VEX.NDS.128.66.0F.WIG 5D /r VMINPD xmm1,xmm2,| RVM  | V/V           | AVX               | Return the minimum double-precision       
| xmm3/m128                                    |      |               |                   | floatingpoint values between xmm2 and     
|                                              |      |               |                   | xmm3/mem.                                 
| VEX.NDS.256.66.0F.WIG 5D /r VMINPD ymm1,     | RVM  | V/V           | AVX               | Return the minimum packed double-precision
| ymm2, ymm3/m256                              |      |               |                   | floating-point values between ymm2 and    
|                                              |      |               |                   | ymm3/mem.                                 

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
Performs an SIMD compare of the packed double-precision floating-point values
in the first source operand and the second source operand and returns the minimum
value for each pair of values to the destination operand. If the values being
compared are both 0.0s (of either sign), the value in the second operand (source
operand) is returned. If a value in the second operand is an SNaN, that SNaN
is forwarded unchanged to the destination (that is, a QNaN version of the SNaN
is not returned). If only one value is a NaN (SNaN or QNaN) for this instruction,
the second operand (source operand), either a NaN or a valid floating-point
value, is written to the result. If instead of this behavior, it is required
that the NaN source operand (from either the first or second operand) be returned,
the action of MINPD can be emulated using a sequence of instructions, such as,
a comparison followed by AND, ANDN and OR.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). 128-bit Legacy SSE version: The second source can be
an XMM register or an 128-bit memory location. The destination is not distinct
from the first source XMM register and the upper bits (VLMAX-1:128) of the corresponding
YMM register destination are unmodified. VEX.128 encoded version: the first
source operand is an XMM register or 128-bit memory location. The destination
operand is an XMM register. The upper bits (VLMAX-1:128) of the corresponding
YMM register destination are zeroed.

Operation:

MIN(SRC1, SRC2)
{
  IF ((SRC1 = 0.0) and (SRC2 = 0.0)) THEN DEST <- SRC2;
     ELSE IF (SRC1 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF (SRC2 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF (SRC1 < SRC2) THEN DEST <- SRC1;
     ELSE DEST <- SRC2;
  FI;
}
MINPD (128-bit Legacy SSE version)
DEST[63:0] <- MIN(SRC1[63:0], SRC2[63:0])
DEST[127:64] <- MIN(SRC1[127:64], SRC2[127:64])
DEST[VLMAX-1:128] (Unmodified)
VMINPD (VEX.128 encoded version)
DEST[63:0] <- MIN(SRC1[63:0], SRC2[63:0])
DEST[127:64] <- MIN(SRC1[127:64], SRC2[127:64])
DEST[VLMAX-1:128] <- 0
VMINPD (VEX.256 encoded version)
DEST[63:0] <- MIN(SRC1[63:0], SRC2[63:0])
DEST[127:64] <- MIN(SRC1[127:64], SRC2[127:64])
DEST[191:128] <- MIN(SRC1[191:128], SRC2[191:128])
DEST[255:192] <- MIN(SRC1[255:192], SRC2[255:192])

Intel C/C++ Compiler Intrinsic Equivalent:
| MINPD: | __m128d _mm_min_pd(__m128d a, __m128d    
|        | b);                                      
| VMINPD:| __m256d _mm256_min_pd (__m256d a, __m256d
|        | b);                                      

SIMD Floating-Point Exceptions:
Invalid (including QNaN source operand), Denormal.


Other Exceptions:
See Exceptions Type 2.


platform: x86
mnem: MINPS
description:
MINPS - Return Minimum Packed Single-Precision Floating-Point Values:
| Opcode/Instruction                        | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                               
| 0F 5D /r MINPS xmm1, xmm2/m128            | RM   | V/V           | SSE               | Return the minimum single-precision       
|                                           |      |               |                   | floatingpoint values between xmm2/m128    
|                                           |      |               |                   | and xmm1.                                 
| VEX.NDS.128.0F.WIG 5D /r VMINPS xmm1,xmm2,| RVM  | V/V           | AVX               | Return the minimum single-precision       
| xmm3/m128                                 |      |               |                   | floatingpoint values between xmm2 and     
|                                           |      |               |                   | xmm3/mem.                                 
| VEX.NDS.256.0F.WIG 5D /r VMINPS ymm1,     | RVM  | V/V           | AVX               | Return the minimum single double-precision
| ymm2, ymm3/m256                           |      |               |                   | floating-point values between ymm2 and    
|                                           |      |               |                   | ymm3/mem.                                 

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
Performs an SIMD compare of the packed single-precision floating-point values
in the first source operand and the second source operand and returns the minimum
value for each pair of values to the destination operand. If the values being
compared are both 0.0s (of either sign), the value in the second operand (source
operand) is returned. If a value in the second operand is an SNaN, that SNaN
is forwarded unchanged to the destination (that is, a QNaN version of the SNaN
is not returned). If only one value is a NaN (SNaN or QNaN) for this instruction,
the second operand (source operand), either a NaN or a valid floating-point
value, is written to the result. If instead of this behavior, it is required
that the NaN source operand (from either the first or second operand) be returned,
the action of MINPS can be emulated using a sequence of instructions, such as,
a comparison followed by AND, ANDN and OR.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). 128-bit Legacy SSE version: The second source can be
an XMM register or an 128-bit memory location. The destination is not distinct
from the first source XMM register and the upper bits (VLMAX-1:128) of the corresponding
YMM register destination are unmodified. VEX.128 encoded version: the first
source operand is an XMM register or 128-bit memory location. The destination
operand is an XMM register. The upper bits (VLMAX-1:128) of the corresponding
YMM register destination are zeroed. VEX.256 encoded version: The first source
operand is a YMM register. The second source operand can be a YMM register or
a 256-bit memory location. The destination operand is a YMM register.

Operation:

MIN(SRC1, SRC2)
{
  IF ((SRC1 = 0.0) and (SRC2 = 0.0)) THEN DEST <- SRC2;
     ELSE IF (SRC1 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF (SRC2 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF (SRC1 < SRC2) THEN DEST <- SRC1;
     ELSE DEST <- SRC2;
  FI;
}
MINPS (128-bit Legacy SSE version)
DEST[31:0] <- MIN(SRC1[31:0], SRC2[31:0])
DEST[63:32] <- MIN(SRC1[63:32], SRC2[63:32])
DEST[95:64] <- MIN(SRC1[95:64], SRC2[95:64])
DEST[127:96] <- MIN(SRC1[127:96], SRC2[127:96])
DEST[VLMAX-1:128] (Unmodified)
VMINPS (VEX.128 encoded version)
DEST[31:0] <- MIN(SRC1[31:0], SRC2[31:0])
DEST[63:32] <- MIN(SRC1[63:32], SRC2[63:32])
DEST[95:64] <- MIN(SRC1[95:64], SRC2[95:64])
DEST[127:96] <- MIN(SRC1[127:96], SRC2[127:96])
DEST[VLMAX-1:128] <- 0
VMINPS (VEX.256 encoded version)
DEST[31:0] <- MIN(SRC1[31:0], SRC2[31:0])
DEST[63:32] <- MIN(SRC1[63:32], SRC2[63:32])
DEST[95:64] <- MIN(SRC1[95:64], SRC2[95:64])
DEST[127:96] <- MIN(SRC1[127:96], SRC2[127:96])
DEST[159:128] <- MIN(SRC1[159:128], SRC2[159:128])
DEST[191:160] <- MIN(SRC1[191:160], SRC2[191:160])
DEST[223:192] <- MIN(SRC1[223:192], SRC2[223:192])
DEST[255:224] <- MIN(SRC1[255:224], SRC2[255:224])

Intel C/C++ Compiler Intrinsic Equivalent:
| MINPS: | __m128d _mm_min_ps(__m128d a, __m128d 
|        | b);                                   
| VMINPS:| __m256 _mm256_min_ps (__m256 a, __m256
|        | b);                                   

SIMD Floating-Point Exceptions:
Invalid (including QNaN source operand), Denormal.


Other Exceptions:
See Exceptions Type 2.


platform: x86
mnem: MINSD
description:
MINSD - Return Minimum Scalar Double-Precision Floating-Point Value:
| Opcode/Instruction                      | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                               
| F2 0F 5D /r MINSD xmm1, xmm2/m64        | RM   | V/V           | SSE2              | Return the minimum scalar double-precision
|                                         |      |               |                   | floating-point value between xmm2/mem64   
|                                         |      |               |                   | and xmm1.                                 
| VEX.NDS.LIG.F2.0F.WIG 5D /r VMINSD xmm1,| RVM  | V/V           | AVX               | Return the minimum scalar double precision
| xmm2, xmm3/m64                          |      |               |                   | floating-point value between xmm3/mem64   
|                                         |      |               |                   | and xmm2.                                 

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
Compares the low double-precision floating-point values in the first source
operand and the second source operand, and returns the minimum value to the
low quadword of the destination operand. When the source operand is a memory
operand, only the 64 bits are accessed. The high quadword of the destination
operand is copied from the same bits in the first source operand. If the values
being compared are both 0.0s (of either sign), the value in the second source
operand is returned. If a value in the second source operand is an SNaN, that
SNaN is returned unchanged to the destination (that is, a QNaN version of the
SNaN is not returned). If only one value is a NaN (SNaN or QNaN) for this instruction,
the second source operand, either a NaN or a valid floating-point value, is
written to the result. If instead of this behavior, it is required that the
NaN source operand (from either the first or second source) be returned, the
action of MINSD can be emulated using a sequence of instructions, such as, a
comparison followed by AND, ANDN and OR. The second source operand can be an
XMM register or a 64-bit memory location. The first source and destination operands
are XMM registers.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). 128-bit Legacy SSE version: The destination and first
source operand are the same. Bits (VLMAX-1:64) of the corresponding YMM destination
register remain unchanged. VEX.128 encoded version: Bits (127:64) of the XMM
register destination are copied from corresponding bits in the first source
operand. Bits (VLMAX-1:128) of the destination YMM register are zeroed.

Operation:

MIN(SRC1, SRC2)
{
  IF ((SRC1 = 0.0) and (SRC2 = 0.0)) THEN DEST <- SRC2;
     ELSE IF (SRC1 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF SRC2 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF (SRC1 < SRC2) THEN DEST <- SRC1;
     ELSE DEST <- SRC2;
  FI;
}
MINSD (128-bit Legacy SSE version)
DEST[63:0] <- MIN(SRC1[63:0], SRC2[63:0])
DEST[VLMAX-1:64] (Unmodified)
MINSD (VEX.128 encoded version)
DEST[63:0] <- MIN(SRC1[63:0], SRC2[63:0])
DEST[127:64] <- SRC1[127:64]
DEST[VLMAX-1:128] <- 0

Intel C/C++ Compiler Intrinsic Equivalent:
| MINSD:| __m128d _mm_min_sd(__m128d a, __m128d
|       | b)                                   

SIMD Floating-Point Exceptions:
Invalid (including QNaN source operand), Denormal.


Other Exceptions:
See Exceptions Type 3.


platform: x86
mnem: MINSS
description:
MINSS - Return Minimum Scalar Single-Precision Floating-Point Value:
| Opcode/Instruction                           | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                               
| F3 0F 5D /r MINSS xmm1, xmm2/m32             | RM   | V/V           | SSE               | Return the minimum scalar single-precision
|                                              |      |               |                   | floating-point value between xmm2/mem32   
|                                              |      |               |                   | and xmm1.                                 
| VEX.NDS.LIG.F3.0F.WIG 5D /r VMINSS xmm1,xmm2,| RVM  | V/V           | AVX               | Return the minimum scalar single precision
| xmm3/m32                                     |      |               |                   | floating-point value between xmm3/mem32   
|                                              |      |               |                   | and xmm2.                                 

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
Compares the low single-precision floating-point values in the first source
operand and the second source operand and returns the minimum value to the low
doubleword of the destination operand. If the values being compared are both
0.0s (of either sign), the value in the second source operand is returned. If
a value in the second operand is an SNaN, that SNaN is returned unchanged to
the destination (that is, a QNaN version of the SNaN is not returned). If only
one value is a NaN (SNaN or QNaN) for this instruction, the second source operand,
either a NaN or a valid floating-point value, is written to the result. If instead
of this behavior, it is required that the NaN in either source operand be returned,
the action of MINSD can be emulated using a sequence of instructions, such as,
a comparison followed by AND, ANDN and OR. The second source operand can be
an XMM register or a 32-bit memory location. The first source and destination
operands are XMM registers.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). 128-bit Legacy SSE version: The destination and first
source operand are the same. Bits (VLMAX-1:32) of the corresponding YMM destination
register remain unchanged. VEX.128 encoded version: Bits (127:32) of the XMM
register destination are copied from corresponding bits in the first source
operand. Bits (VLMAX-1:128) of the destination YMM register are zeroed.

Operation:

MIN(SRC1, SRC2)
{
  IF ((SRC1 = 0.0) and (SRC2 = 0.0)) THEN DEST <- SRC2;
     ELSE IF (SRC1 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF SRC2 = SNaN) THEN DEST <- SRC2; FI;
     ELSE IF (SRC1 < SRC2) THEN DEST <- SRC1;
     ELSE DEST <- SRC2;
  FI;
}
MINSS (128-bit Legacy SSE version)
DEST[31:0] <- MIN(SRC1[31:0], SRC2[31:0])
DEST[VLMAX-1:32] (Unmodified)
VMINSS (VEX.128 encoded version)
DEST[31:0] <- MIN(SRC1[31:0], SRC2[31:0])
DEST[127:32] <- SRC1[127:32]
DEST[VLMAX-1:128] <- 0

Intel C/C++ Compiler Intrinsic Equivalent:
| MINSS:| __m128d _mm_min_ss(__m128d a, __m128d
|       | b)                                   

SIMD Floating-Point Exceptions:
Invalid (including QNaN source operand), Denormal.


Other Exceptions:
See Exceptions Type 3.


platform: x86
mnem: MONITOR
description:
MONITOR - Set Up Monitor Address:
| Opcode  | Instruction| Op/En| 64-Bit Mode| Compat/Leg Mode| Description                            
| 0F 01 C8| MONITOR    | NP   | Valid      | Valid          | Sets up a linear address range to be   
|         |            |      |            |                | monitored by hardware and activates    
|         |            |      |            |                | the monitor. The address range should  
|         |            |      |            |                | be a writeback memory caching type.    
|         |            |      |            |                | The address is DS:EAX (DS:RAX in 64-bit
|         |            |      |            |                | mode).                                 

Instruction Operand Encoding:
| Op/En| Operand 1| Operand 2| Operand 3| Operand 4
| NP   | NA       | NA       | NA       | NA       

Description:
The MONITOR instruction arms address monitoring hardware using an address specified
in EAX (the address range that the monitoring hardware checks for store operations
can be determined by using CPUID). A store to an address within the specified
address range triggers the monitoring hardware. The state of monitor hardware
is used by MWAIT.

The content of EAX is an effective address (in 64-bit mode, RAX is used). By
default, the DS segment is used to create a linear address that is monitored.
Segment overrides can be used.

ECX and EDX are also used. They communicate other information to MONITOR. ECX
specifies optional extensions. EDX specifies optional hints; it does not change
the architectural behavior of the instruction. For the Pentium 4 processor (family
15, model 3), no extensions or hints are defined. Undefined hints in EDX are
ignored by the processor; undefined extensions in ECX raises a general protection
fault.

The address range must use memory of the write-back type. Only write-back memory
will correctly trigger the monitoring hardware. Additional information on determining
what address range to use in order to prevent false wake-ups is described in
Chapter 8, “Multiple-Processor Management” of the Intel® 64 and IA-32 Architectures
Software Developer's Manual, Volume 3A.

The MONITOR instruction is ordered as a load operation with respect to other
memory transactions. The instruction is subject to the permission checking and
faults associated with a byte load. Like a load, MONITOR sets the A-bit but
not the D-bit in page tables.

CPUID.01H:ECX.MONITOR[bit 3] indicates the availability of MONITOR and MWAIT
in the processor. When set, MONITOR may be executed only at privilege level
0 (use at any other privilege level results in an invalid-opcode exception).
The operating system or system BIOS may disable this instruction by using the
IA32_MISC_ENABLE MSR; disabling MONITOR clears the CPUID feature flag and causes
execution to generate an invalid-opcode exception.

The instruction's operation is the same in non-64-bit modes and 64-bit mode.

Operation:

MONITOR sets up an address range for the monitor hardware using the content of EAX (RAX in 64-bit mode) as an
effective address and puts the monitor hardware in armed state. Always use memory of the write-back caching
type. A store to the specified address range will trigger the monitor hardware. The content of ECX and EDX are
used to communicate other information to the monitor hardware.

Intel C/C++ Compiler Intrinsic Equivalent:
| MONITOR:| void _mm_monitor(void const *p, unsigned
|         | extensions,unsigned hints)              

Numeric Exceptions:
None


Protected Mode Exceptions:
| #GP(0)         | If the value in EAX is outside the CS, 
|                | DS, ES, FS, or GS segment limit. If    
|                | the DS, ES, FS, or GS register is used 
|                | to access memory and it contains a NULL
|                | segment selector. If ECX != 0.          
| #SS(0)         | If the value in EAX is outside the SS  
|                | segment limit.                         
| #PF(fault-code)| For a page fault.                      
| #UD            | If CPUID.01H:ECX.MONITOR[bit 3] = 0.   
|                | If current privilege level is not 0.   

Real Address Mode Exceptions:
| #GP| If the CS, DS, ES, FS, or GS register     
|    | is used to access memory and the value    
|    | in EAX is outside of the effective address
|    | space from 0 to FFFFH. If ECX != 0.        
| #SS| If the SS register is used to access      
|    | memory and the value in EAX is outside    
|    | of the effective address space from       
|    | 0 to FFFFH.                               
| #UD| If CPUID.01H:ECX.MONITOR[bit 3] = 0.      

Virtual 8086 Mode Exceptions:
| #UD| The MONITOR instruction is not recognized              
|    | in virtual-8086 mode (even if CPUID.01H:ECX.MONITOR[bit
|    | 3] = 1).                                               

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #GP(0)         | If the linear address of the operand 
|                | in the CS, DS, ES, FS, or GS segment 
|                | is in a non-canonical form. If RCX != 
|                | 0.                                   
| #SS(0)         | If the SS register is used to access 
|                | memory and the value in EAX is in a  
|                | non-canonical form.                  
| #PF(fault-code)| For a page fault.                    
| #UD            | If the current privilege level is not
|                | 0. If CPUID.01H:ECX.MONITOR[bit 3] = 
|                | 0.                                   


platform: x86
mnem: MOV
description:
MOV - Move:
| Opcode                   | Instruction                   | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                               
| 88 /r REX + 88 /r        | MOV r/m8,r8 MOV r/m8***,r8*** | MR MR| Valid Valid| Valid N.E.     | Move r8 to r/m8. Move r8 to r/m8.         
| 89 /r                    | MOV r/m16,r16                 | MR   | Valid      | Valid          | Move r16 to r/m16.                        
| 89 /r                    | MOV r/m32,r32                 | MR   | Valid      | Valid          | Move r32 to r/m32.                        
| REX.W + 89 /r            | MOV r/m64,r64                 | MR   | Valid      | N.E.           | Move r64 to r/m64.                        
| 8A /r                    | MOV r8,r/m8                   | RM   | Valid      | Valid          | Move r/m8 to r8.                          
| REX + 8A /r              | MOV r8***,r/m8***             | RM   | Valid      | N.E.           | Move r/m8 to r8.                          
| 8B /r                    | MOV r16,r/m16                 | RM   | Valid      | Valid          | Move r/m16 to r16.                        
| 8B /r                    | MOV r32,r/m32                 | RM   | Valid      | Valid          | Move r/m32 to r32.                        
| REX.W + 8B /r            | MOV r64,r/m64                 | RM   | Valid      | N.E.           | Move r/m64 to r64.                        
| 8C /r                    | MOV r/m16,Sreg**              | MR   | Valid      | Valid          | Move segment register to r/m16.           
| REX.W + 8C /r            | MOV r/m64,Sreg**              | MR   | Valid      | Valid          | Move zero extended 16-bit segment register
|                          |                               |      |            |                | to r/m64.                                 
| 8E /r                    | MOV Sreg,r/m16**              | RM   | Valid      | Valid          | Move r/m16 to segment register.           
| REX.W + 8E /r            | MOV Sreg,r/m64**              | RM   | Valid      | Valid          | Move lower 16 bits of r/m64 to segment    
|                          |                               |      |            |                | register.                                 
| A0                       | MOV AL,moffs8*                | FD   | Valid      | Valid          | Move byte at (seg:offset) to AL.          
| REX.W + A0               | MOV AL,moffs8*                | FD   | Valid      | N.E.           | Move byte at (offset) to AL.              
| A1                       | MOV AX,moffs16*               | FD   | Valid      | Valid          | Move word at (seg:offset) to AX.          
| A1                       | MOV EAX,moffs32*              | FD   | Valid      | Valid          | Move doubleword at (seg:offset) to EAX.   
| REX.W + A1               | MOV RAX,moffs64*              | FD   | Valid      | N.E.           | Move quadword at (offset) to RAX.         
| A2 REX.W + A2            | MOV moffs8,AL MOV moffs8***,AL| TD TD| Valid Valid| Valid N.E.     | Move AL to (seg:offset). Move AL to       
|                          |                               |      |            |                | (offset).                                 
| A3                       | MOV moffs16*,AX               | TD   | Valid      | Valid          | Move AX to (seg:offset).                  
| A3                       | MOV moffs32*,EAX              | TD   | Valid      | Valid          | Move EAX to (seg:offset).                 
| REX.W + A3               | MOV moffs64*,RAX              | TD   | Valid      | N.E.           | Move RAX to (offset).                     
| B0+ rb ib REX + B0+ rb ib| MOV r8, imm8 MOV r8***, imm8  | OI OI| Valid Valid| Valid N.E.     | Move imm8 to r8. Move imm8 to r8.         
| B8+ rw iw                | MOV r16, imm16                | OI   | Valid      | Valid          | Move imm16 to r16.                        
| B8+ rd id                | MOV r32, imm32                | OI   | Valid      | Valid          | Move imm32 to r32.                        
| REX.W + B8+ rd io        | MOV r64, imm64                | OI   | Valid      | N.E.           | Move imm64 to r64.                        
| C6 /0 ib                 | MOV r/m8, imm8                | MI   | Valid      | Valid          | Move imm8 to r/m8.                        
| REX + C6 /0 ib           | MOV r/m8***, imm8             | MI   | Valid      | N.E.           | Move imm8 to r/m8.                        
| C7 /0 iw                 | MOV r/m16, imm16              | MI   | Valid      | Valid          | Move imm16 to r/m16.                      
| C7 /0 id                 | MOV r/m32, imm32              | MI   | Valid      | Valid          | Move imm32 to r/m32.                      
| REX.W + C7 /0 io         | MOV r/m64, imm32              | MI   | Valid      | N.E.           | Move imm32 sign extended to 64-bits       
|                          |                               |      |            |                | to r/m64.                                 
Notes: * The moffs8, moffs16, moffs32 and moffs64 operands specify a simple
offset relative to the segment base, where 8, 16, 32 and 64 refer to the size
of the data. The address-size attribute of the instruction determines the size
of the offset, either 16, 32 or 64 bits. ** In 32-bit mode, the assembler may
insert the 16-bit operand-size prefix with this instruction (see the following
“Description” section for further information). ***In 64-bit mode, r/m8 can
not be encoded to access the following byte registers if a REX prefix is used:
AH, BH, CH, DH.


Instruction Operand Encoding:
| Op/En| Operand 1      | Operand 2    | Operand 3| Operand 4
| MR   | ModRM:r/m (w)  | ModRM:reg (r)| NA       | NA       
| RM   | ModRM:reg (w)  | ModRM:r/m (r)| NA       | NA       
| FD   | AL/AX/EAX/RAX  | Moffs        | NA       | NA       
| TD   | Moffs (w)      | AL/AX/EAX/RAX| NA       | NA       
| OI   | opcode + rd (w)| imm8/16/32/64| NA       | NA       
| MI   | ModRM:r/m (w)  | imm8/16/32/64| NA       | NA       

Description:
Copies the second operand (source operand) to the first operand (destination
operand). The source operand can be an immediate value, general-purpose register,
segment register, or memory location; the destination register can be a general-purpose
register, segment register, or memory location. Both operands must be the same
size, which can be a byte, a word, a doubleword, or a quadword.

The MOV instruction cannot be used to load the CS register. Attempting to do
so results in an invalid opcode exception (#UD). To load the CS register, use
the far JMP, CALL, or RET instruction.

If the destination operand is a segment register (DS, ES, FS, GS, or SS), the
source operand must be a valid segment selector. In protected mode, moving a
segment selector into a segment register automatically causes the segment descriptor
information associated with that segment selector to be loaded into the hidden
(shadow) part of the segment register. While loading this information, the segment
selector and segment descriptor information is validated (see the “Operation”
algorithm below). The segment descriptor data is obtained from the GDT or LDT
entry for the specified segment selector.

A NULL segment selector (values 0000-0003) can be loaded into the DS, ES, FS,
and GS registers without causing a protection exception. However, any subsequent
attempt to reference a segment whose corresponding segment register is loaded
with a NULL value causes a general protection exception (#GP) and no memory
reference occurs.

Loading the SS register with a MOV instruction inhibits all interrupts until
after the execution of the next instruction. This operation allows a stack pointer
to be loaded into the ESP register with the next instruction (MOV ESP, stack-pointer
value) before an interrupt occurs1. Be aware that the LSS instruction offers
a more efficient method of loading the SS and ESP registers.

When operating in 32-bit mode and moving data between a segment register and
a general-purpose register, the 32-bit IA-32 processors do not require the use
of the 16-bit operand-size prefix (a byte with the value 66H) with

| 1.| If a code instruction breakpoint (for      
|   | debug) is placed on an instruction located 
|   | immediately after a MOV SS instruction,    
|   | the breakpoint may not be triggered.       
|   | However, in a sequence of instructions     
|   | that load the SS register, only the        
|   | first instruction in the sequence is       
|   | guaranteed to delay an interrupt. In       
|   | the following sequence, interrupts may     
|   | be recognized before MOV ESP, EBP executes:
|   | MOV SS, EDX MOV SS, EAX MOV ESP, EBP       
this instruction, but most assemblers will insert it if the standard form of
the instruction is used (for example, MOV DS, AX). The processor will execute
this instruction correctly, but it will usually require an extra clock. With
most assemblers, using the instruction form MOV DS, EAX will avoid this unneeded
66H prefix. When the processor executes the instruction with a 32-bit general-purpose
register, it assumes that the 16 least-significant bits of the general-purpose
register are the destination or source operand. If the register is a destination
operand, the resulting value in the two high-order bytes of the register is
implementation dependent. For the Pentium 4, Intel Xeon, and P6 family processors,
the two high-order bytes are filled with zeros; for earlier 32-bit IA-32 processors,
the two high order bytes are undefined.

In 64-bit mode, the instruction's default operation size is 32 bits. Use of
the REX.R prefix permits access to additional registers (R8-R15). Use of the
REX.W prefix promotes operation to 64 bits. See the summary chart at the beginning
of this section for encoding data and limits.

Operation:

DEST <- SRC;
Loading a segment register while in protected mode results in special checks and actions, as described in the
following listing. These checks are performed on the segment selector and the segment descriptor to which it
points.
IF SS is loaded
  THEN
     IF segment selector is NULL
       THEN #GP(0); FI;
     IF segment selector index is outside descriptor table limits
     or segment selector's RPL != CPL
     or segment is not a writable data segment
     or DPL != CPL
       THEN #GP(selector); FI;
     IF segment not marked present
       THEN #SS(selector);
       ELSE
          SS <- segment selector;
          SS <- segment descriptor; FI;
FI;
IF DS, ES, FS, or GS is loaded with non-NULL selector
THEN
  IF segment selector index is outside descriptor table limits
  or segment is not a data or readable code segment
  or ((segment is a data or nonconforming code segment)
  or ((RPL > DPL) and (CPL > DPL))
     THEN #GP(selector); FI;
  IF segment not marked present
     THEN #NP(selector);
     ELSE
       SegmentRegister <- segment selector;
       SegmentRegister <- segment descriptor; FI;
FI;
IF DS, ES, FS, or GS is loaded with NULL selector
  THEN
     SegmentRegister <- segment selector;
     SegmentRegister <- segment descriptor;
FI;

Flags Affected:
None.


Protected Mode Exceptions:
| #GP(0)         | If attempt is made to load SS register        
|                | with NULL segment selector. If the destination
|                | operand is in a non-writable segment.         
|                | If a memory operand effective address         
|                | is outside the CS, DS, ES, FS, or GS          
|                | segment limit. If the DS, ES, FS, or          
|                | GS register contains a NULL segment           
|                | selector.                                     
| #GP(selector)  | If segment selector index is outside          
|                | descriptor table limits. If the SS register   
|                | is being loaded and the segment selector's    
|                | RPL and the segment descriptor's DPL          
|                | are not equal to the CPL. If the SS           
|                | register is being loaded and the segment      
|                | pointed to is a non-writable data segment.    
|                | If the DS, ES, FS, or GS register is          
|                | being loaded and the segment pointed          
|                | to is not a data or readable code segment.    
|                | If the DS, ES, FS, or GS register is          
|                | being loaded and the segment pointed          
|                | to is a data or nonconforming code segment,   
|                | but both the RPL and the CPL are greater      
|                | than the DPL.                                 
| #SS(0)         | If a memory operand effective address         
|                | is outside the SS segment limit.              
| #SS(selector)  | If the SS register is being loaded and        
|                | the segment pointed to is marked not          
|                | present.                                      
| #NP            | If the DS, ES, FS, or GS register is          
|                | being loaded and the segment pointed          
|                | to is marked not present.                     
| #PF(fault-code)| If a page fault occurs.                       
| #AC(0)         | If alignment checking is enabled and          
|                | an unaligned memory reference is made         
|                | while the current privilege level is          
|                | 3.                                            
| #UD            | If attempt is made to load the CS register.   
|                | If the LOCK prefix is used.                   

Real-Address Mode Exceptions:
| #GP| If a memory operand effective address      
|    | is outside the CS, DS, ES, FS, or GS       
|    | segment limit.                             
| #SS| If a memory operand effective address      
|    | is outside the SS segment limit.           
| #UD| If attempt is made to load the CS register.
|    | If the LOCK prefix is used.                

Virtual-8086 Mode Exceptions:
| #GP(0)         | If a memory operand effective address      
|                | is outside the CS, DS, ES, FS, or GS       
|                | segment limit.                             
| #SS(0)         | If a memory operand effective address      
|                | is outside the SS segment limit.           
| #PF(fault-code)| If a page fault occurs.                    
| #AC(0)         | If alignment checking is enabled and       
|                | an unaligned memory reference is made.     
| #UD            | If attempt is made to load the CS register.
|                | If the LOCK prefix is used.                

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #GP(0)         | If the memory address is in a non-canonical     
|                | form. If an attempt is made to load             
|                | SS register with NULL segment selector          
|                | when CPL = 3. If an attempt is made             
|                | to load SS register with NULL segment           
|                | selector when CPL < 3 and CPL != RPL.            
| #GP(selector)  | If segment selector index is outside            
|                | descriptor table limits. If the memory          
|                | access to the descriptor table is non-canonical.
|                | If the SS register is being loaded and          
|                | the segment selector's RPL and the segment      
|                | descriptor's DPL are not equal to the           
|                | CPL. If the SS register is being loaded         
|                | and the segment pointed to is a nonwritable     
|                | data segment. If the DS, ES, FS, or             
|                | GS register is being loaded and the             
|                | segment pointed to is not a data or             
|                | readable code segment. If the DS, ES,           
|                | FS, or GS register is being loaded and          
|                | the segment pointed to is a data or             
|                | nonconforming code segment, but both            
|                | the RPL and the CPL are greater than            
|                | the DPL.                                        
| #SS(0)         | If the stack address is in a non-canonical      
|                | form.                                           
| #SS(selector)  | If the SS register is being loaded and          
|                | the segment pointed to is marked not            
|                | present.                                        
| #PF(fault-code)| If a page fault occurs.                         
| #AC(0)         | If alignment checking is enabled and            
|                | an unaligned memory reference is made           
|                | while the current privilege level is            
|                | 3.                                              
| #UD            | If attempt is made to load the CS register.     
|                | If the LOCK prefix is used.                     


platform: x86
mnem: MOV
description:
MOV - Move to/from Control Registers:
| Opcode/Instruction                 | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                           
| 0F 20/r MOV r32, CR0-CR7           | MR   | N.E.       | Valid          | Move control register to r32.         
| 0F 20/r MOV r64, CR0-CR7 REX.R + 0F| MR MR| Valid Valid| N.E. N.E.      | Move extended control register to r64.
| 20 /0 MOV r64, CR8                 |      |            |                | Move extended CR8 to r64.1            
| 0F 22 /r MOV CR0-CR7, r32          | RM   | N.E.       | Valid          | Move r32 to control register.         
| 0F 22 /r MOV CR0-CR7, r64          | RM   | Valid      | N.E.           | Move r64 to extended control register.
| REX.R + 0F 22 /0 MOV CR8, r64      | RM   | Valid      | N.E.           | Move r64 to extended CR8.1            

NOTE::
| 1.| MOV CR* instructions, except for MOV  
|   | CR8, are serializing instructions. MOV
|   | CR8 is not architecturally defined as 
|   | a serializing instruction. For more   
|   | information, see Chapter 8 in Intel®  
|   | 64 and IA-32 Architectures Software   
|   | Developer's Manual, Volume 3A.        

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
Moves the contents of a control register (CR0, CR2, CR3, CR4, or CR8) to a general-purpose
register or the contents of a general purpose register to a control register.
The operand size for these instructions is always 32 bits in non-64-bit modes,
regardless of the operand-size attribute. (See “Control Registers” in Chapter
2 of the Intel®64 and IA-32 Architectures Software Developer's Manual, Volume
3A, for a detailed description of the flags and fields in the control registers.)
This instruction can be executed only when the current privilege level is 0.

At the opcode level, the reg field within the ModR/M byte specifies which of
the control registers is loaded or read. The 2 bits in the mod field are ignored.
The r/m field specifies the general-purpose register loaded or read. Attempts
to reference CR1, CR5, CR6, CR7, and CR9-CR15 result in undefined opcode (#UD)
exceptions.

When loading control registers, programs should not attempt to change the reserved
bits; that is, always set reserved bits to the value previously read. An attempt
to change CR4's reserved bits will cause a general protection fault. Reserved
bits in CR0 and CR3 remain clear after any load of those registers; attempts
to set them have no impact. On Pentium 4, Intel Xeon and P6 family processors,
CR0.ET remains set after any load of CR0; attempts to clear this bit have no
impact.

In certain cases, these instructions have the side effect of invalidating entries
in the TLBs and the paging-structure caches. See Section 4.10.4.1, “Operations
that Invalidate TLBs and Paging-Structure Caches,” in the Intel® 64 and IA-32
Architectures Software Developer's Manual, Volume 3A for details.

The following side effects are implementation-specific for the Pentium 4, Intel
Xeon, and P6 processor family: when modifying PE or PG in register CR0, or PSE
or PAE in register CR4, all TLB entries are flushed, including global entries.
Software should not depend on this functionality in all Intel 64 or IA-32 processors.

In 64-bit mode, the instruction's default operation size is 64 bits. The REX.R
prefix must be used to access CR8. Use of REX.B permits access to additional
registers (R8-R15). Use of the REX.W prefix or 66H prefix is ignored. Use of

the REX.R prefix to specify a register other than CR8 causes an invalid-opcode
exception. See the summary chart at the beginning of this section for encoding
data and limits.

If CR4.PCIDE = 1, bit 63 of the source operand to MOV to CR3 determines whether
the instruction invalidates entries in the TLBs and the paging-structure caches
(see Section 4.10.4.1, “Operations that Invalidate TLBs and Paging-Structure
Caches,” in the Intel® 64 and IA-32 Architectures Software Developer's Manual,
Volume 3A). The instruction does not modify bit 63 of CR3, which is reserved
and always 0.

See “Changes to Instruction Behavior in VMX Non-Root Operation” in Chapter 25
of the Intel® 64 and IA-32 Architectures Software Developer's Manual, Volume
3C, for more information about the behavior of this instruction in VMX non-root
operation.

Operation:

DEST <- SRC;

Flags Affected:
The OF, SF, ZF, AF, PF, and CF flags are undefined.


Protected Mode Exceptions:
| #GP(0)| If the current privilege level is not    
|       | 0. If an attempt is made to write invalid
|       | bit combinations in CR0 (such as setting 
|       | the PG flag to 1 when the PE flag is     
|       | set to 0, or setting the CD flag to      
|       | 0 when the NW flag is set to 1). If      
|       | an attempt is made to write a 1 to any   
|       | reserved bit in CR4. If an attempt is    
|       | made to write 1 to CR4.PCIDE. If any     
|       | of the reserved bits are set in the      
|       | page-directory pointers table (PDPT)     
|       | and the loading of a control register    
|       | causes the PDPT to be loaded into the    
|       | processor.                               
| #UD   | If the LOCK prefix is used. If an attempt
|       | is made to access CR1, CR5, CR6, or      
|       | CR7.                                     

Real-Address Mode Exceptions:
| #GP| If an attempt is made to write a 1 to    
|    | any reserved bit in CR4. If an attempt   
|    | is made to write 1 to CR4.PCIDE. If      
|    | an attempt is made to write invalid      
|    | bit combinations in CR0 (such as setting 
|    | the PG flag to 1 when the PE flag is     
|    | set to 0).                               
| #UD| If the LOCK prefix is used. If an attempt
|    | is made to access CR1, CR5, CR6, or      
|    | CR7.                                     

Virtual-8086 Mode Exceptions:
| #GP(0)| These instructions cannot be executed
|       | in virtual-8086 mode.                

Compatibility Mode Exceptions:
| #GP(0)| If the current privilege level is not    
|       | 0. If an attempt is made to write invalid
|       | bit combinations in CR0 (such as setting 
|       | the PG flag to 1 when the PE flag is     
|       | set to 0, or setting the CD flag to      
|       | 0 when the NW flag is set to 1). If      
|       | an attempt is made to change CR4.PCIDE   
|       | from 0 to 1 while CR3[11:0] != 000H.      
|       | If an attempt is made to clear CR0.PG[bit
|       | 31] while CR4.PCIDE = 1. If an attempt   
|       | is made to write a 1 to any reserved     
|       | bit in CR3. If an attempt is made to     
|       | leave IA-32e mode by clearing CR4.PAE[bit
|       | 5].                                      
| #UD   | If the LOCK prefix is used. If an attempt
|       | is made to access CR1, CR5, CR6, or      
|       | CR7.                                     

64-Bit Mode Exceptions:
| #GP(0)| If the current privilege level is not    
|       | 0. If an attempt is made to write invalid
|       | bit combinations in CR0 (such as setting 
|       | the PG flag to 1 when the PE flag is     
|       | set to 0, or setting the CD flag to      
|       | 0 when the NW flag is set to 1). If      
|       | an attempt is made to change CR4.PCIDE   
|       | from 0 to 1 while CR3[11:0] != 000H.      
|       | If an attempt is made to clear CR0.PG[bit
|       | 31]. If an attempt is made to write      
|       | a 1 to any reserved bit in CR4. If an    
|       | attempt is made to write a 1 to any      
|       | reserved bit in CR8. If an attempt is    
|       | made to write a 1 to any reserved bit    
|       | in CR3. If an attempt is made to leave   
|       | IA-32e mode by clearing CR4.PAE[bit      
|       | 5].                                      
| #UD   | If the LOCK prefix is used. If an attempt
|       | is made to access CR1, CR5, CR6, or      
|       | CR7. If the REX.R prefix is used to      
|       | specify a register other than CR8.       


platform: x86
mnem: MOV
description:
MOV - Move to/from Debug Registers:
| Opcode/Instruction       | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                         
| 0F 21/r MOV r32, DR0-DR7 | MR   | N.E.       | Valid          | Move debug register to r32.         
| 0F 21/r MOV r64, DR0-DR7 | MR   | Valid      | N.E.           | Move extended debug register to r64.
| 0F 23 /r MOV DR0-DR7, r32| RM   | N.E.       | Valid          | Move r32 to debug register.         
| 0F 23 /r MOV DR0-DR7, r64| RM   | Valid      | N.E.           | Move r64 to extended debug register.

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
Moves the contents of a debug register (DR0, DR1, DR2, DR3, DR4, DR5, DR6, or
DR7) to a general-purpose register or vice versa. The operand size for these
instructions is always 32 bits in non-64-bit modes, regardless of the operand-size
attribute. (See Section 17.2, “Debug Registers”, of the Intel® 64 and IA-32
Architectures Software Developer's Manual, Volume 3A, for a detailed description
of the flags and fields in the debug registers.)

The instructions must be executed at privilege level 0 or in real-address mode.

When the debug extension (DE) flag in register CR4 is clear, these instructions
operate on debug registers in a manner that is compatible with Intel386 and
Intel486 processors. In this mode, references to DR4 and DR5 refer to DR6 and
DR7, respectively. When the DE flag in CR4 is set, attempts to reference DR4
and DR5 result in an undefined opcode (#UD) exception. (The CR4 register was
added to the IA-32 Architecture beginning with the Pentium processor.)

At the opcode level, the reg field within the ModR/M byte specifies which of
the debug registers is loaded or read. The two bits in the mod field are ignored.
The r/m field specifies the general-purpose register loaded or read.

In 64-bit mode, the instruction's default operation size is 64 bits. Use of
the REX.B prefix permits access to additional registers (R8-R15). Use of the
REX.W or 66H prefix is ignored. Use of the REX.R prefix causes an invalidopcode
exception. See the summary chart at the beginning of this section for encoding
data and limits.

Operation:

IF ((DE = 1) and (SRC or DEST = DR4 or DR5))
  THEN
     #UD;
  ELSE
     DEST <- SRC;
FI;

Flags Affected:
The OF, SF, ZF, AF, PF, and CF flags are undefined.


Protected Mode Exceptions:
| #GP(0)| If the current privilege level is not      
|       | 0.                                         
| #UD   | If CR4.DE[bit 3] = 1 (debug extensions)    
|       | and a MOV instruction is executed involving
|       | DR4 or DR5. If the LOCK prefix is used.    
| #DB   | If any debug register is accessed while    
|       | the DR7.GD[bit 13] = 1.                    

Real-Address Mode Exceptions:
| #UD| If CR4.DE[bit 3] = 1 (debug extensions)    
|    | and a MOV instruction is executed involving
|    | DR4 or DR5. If the LOCK prefix is used.    
| #DB| If any debug register is accessed while    
|    | the DR7.GD[bit 13] = 1.                    

Virtual-8086 Mode Exceptions:
| #GP(0)| The debug registers cannot be loaded
|       | or read when in virtual-8086 mode.  

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #GP(0)| If the current privilege level is not      
|       | 0. If an attempt is made to write a        
|       | 1 to any of bits 63:32 in DR6. If an       
|       | attempt is made to write a 1 to any        
|       | of bits 63:32 in DR7.                      
| #UD   | If CR4.DE[bit 3] = 1 (debug extensions)    
|       | and a MOV instruction is executed involving
|       | DR4 or DR5. If the LOCK prefix is used.    
|       | If the REX.R prefix is used.               
| #DB   | If any debug register is accessed while    
|       | the DR7.GD[bit 13] = 1.                    


platform: x86
mnem: MOVAPD
description:
MOVAPD - Move Aligned Packed Double-Precision Floating-Point Values:
| Opcode/Instruction                        | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                                
| 66 0F 28 /r MOVAPD xmm1, xmm2/m128        | RM   | V/V           | SSE2              | Move packed double-precision floating-point
|                                           |      |               |                   | values from xmm2/m128 to xmm1.             
| 66 0F 29 /r MOVAPD xmm2/m128, xmm1        | MR   | V/V           | SSE2              | Move packed double-precision floating-point
|                                           |      |               |                   | values from xmm1 to xmm2/m128.             
| VEX.128.66.0F.WIG 28 /r VMOVAPD xmm1,     | RM   | V/V           | AVX               | Move aligned packed double-precision       
| xmm2/m128                                 |      |               |                   | floatingpoint values from xmm2/mem to      
|                                           |      |               |                   | xmm1.                                      
| VEX.128.66.0F.WIG 29 /r VMOVAPD xmm2/m128,| MR   | V/V           | AVX               | Move aligned packed double-precision       
| xmm1                                      |      |               |                   | floatingpoint values from xmm1 to xmm2/mem.
| VEX.256.66.0F.WIG 28 /r VMOVAPD ymm1,     | RM   | V/V           | AVX               | Move aligned packed double-precision       
| ymm2/m256                                 |      |               |                   | floatingpoint values from ymm2/mem to      
|                                           |      |               |                   | ymm1.                                      
| VEX.256.66.0F.WIG 29 /r VMOVAPD ymm2/m256,| MR   | V/V           | AVX               | Move aligned packed double-precision       
| ymm1                                      |      |               |                   | floatingpoint values from ymm1 to ymm2/mem.

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       

Description:
Moves 2 or 4 double-precision floating-point values from the source operand
(second operand) to the destination operand (first operand). This instruction
can be used to load an XMM or YMM register from an 128-bit or 256-bit memory
location, to store the contents of an XMM or YMM register into a 128-bit or
256-bit memory location, or to move data between two XMM or two YMM registers.
When the source or destination operand is a memory operand, the operand must
be aligned on a 16-byte (128-bit version) or 32-byte (VEX.256 encoded version)
boundary or a general-protection exception (#GP) will be generated.

To move double-precision floating-point values to and from unaligned memory
locations, use the (V)MOVUPD instruction.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). 128-bit versions: Moves 128 bits of packed double-precision
floating-point values from the source operand (second operand) to the destination
operand (first operand). This instruction can be used to load an XMM register
from a 128-bit memory location, to store the contents of an XMM register into
a 128-bit memory location, or to move data between two XMM registers. When the
source or destination operand is a memory operand, the operand must be aligned
on a 16-byte boundary or a general-protection exception (#GP) will be generated.
To move single-precision floating-point values to and from unaligned memory
locations, use the VMOVUPD instruction. 128-bit Legacy SSE version: Bits (VLMAX-1:128)
of the corresponding YMM destination register remain unchanged. VEX.128 encoded
version: Bits (VLMAX-1:128) of the destination YMM register destination are
zeroed. VEX.256 encoded version: Moves 256 bits of packed double-precision floating-point
values from the source operand (second operand) to the destination operand (first
operand). This instruction can be used to load a YMM register from a 256-bit
memory location, to store the contents of a YMM register into a 256-bit memory
location, or to move data between two YMM registers. When the source or destination
operand is a memory operand, the operand must be aligned on a 32-byte boundary
or a general-protection exception (#GP) will be generated. To move single-precision
floating-point values to and from unaligned memory locations, use the VMOVUPD
instruction.

Note: In VEX-encoded versions, VEX.vvvv is reserved and must be 1111b otherwise
instructions will #UD.

Operation:

MOVAPD (128-bit load- and register-copy- form Legacy SSE version)
DEST[127:0] <- SRC[127:0]
DEST[VLMAX-1:128] (Unmodified)
(V)MOVAPD (128-bit store-form version)
DEST[127:0] <- SRC[127:0]
VMOVAPD (VEX.128 encoded version)
DEST[127:0] <- SRC[127:0]
DEST[VLMAX-1:128] <- 0
VMOVAPD (VEX.256 encoded version)
DEST[255:0] <- SRC[255:0]

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVAPD: | __m128d _mm_load_pd (double const * 
|         | p);                                 
| MOVAPD: | _mm_store_pd(double * p, __m128d a);
| VMOVAPD:| __m256d _mm256_load_pd (double const
|         | * p);                               
| VMOVAPD:| _mm256_store_pd(double * p, __m256d 
|         | a);                                 

SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 1.SSE2; additionally

| #UD| If VEX.vvvv != 1111B.


platform: x86
mnem: MOVAPS
description:
MOVAPS - Move Aligned Packed Single-Precision Floating-Point Values:
| Opcode/Instruction                          | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                                
| 0F 28 /r MOVAPS xmm1, xmm2/m128             | RM   | V/V           | SSE               | Move packed single-precision floating-point
|                                             |      |               |                   | values from xmm2/m128 to xmm1.             
| 0F 29 /r MOVAPS xmm2/m128, xmm1             | MR   | V/V           | SSE               | Move packed single-precision floating-point
|                                             |      |               |                   | values from xmm1 to xmm2/m128.             
| VEX.128.0F.WIG 28 /r VMOVAPS xmm1, xmm2/m128| RM   | V/V           | AVX               | Move aligned packed single-precision       
|                                             |      |               |                   | floatingpoint values from xmm2/mem to      
|                                             |      |               |                   | xmm1.                                      
| VEX.128.0F.WIG 29 /r VMOVAPS xmm2/m128,     | MR   | V/V           | AVX               | Move aligned packed single-precision       
| xmm1                                        |      |               |                   | floatingpoint values from xmm1 to xmm2/mem.
| VEX.256.0F.WIG 28 /r VMOVAPS ymm1, ymm2/m256| RM   | V/V           | AVX               | Move aligned packed single-precision       
|                                             |      |               |                   | floatingpoint values from ymm2/mem to      
|                                             |      |               |                   | ymm1.                                      
| VEX.256.0F.WIG 29 /r VMOVAPS ymm2/m256,     | MR   | V/V           | AVX               | Move aligned packed single-precision       
| ymm1                                        |      |               |                   | floatingpoint values from ymm1 to ymm2/mem.

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       

Description:
Moves 4 or8 single-precision floating-point values from the source operand (second
operand) to the destination operand (first operand). This instruction can be
used to load an XMM or YMM register from an 128-bit or 256-bit memory location,
to store the contents of an XMM or YMM register into a 128-bit or 256-bit memory
location, or to move data between two XMM or two YMM registers. When the source
or destination operand is a memory operand, the operand must be aligned on a
16-byte (128-bit version) or 32-byte (VEX.256 encoded version) boundary or a
general-protection exception (#GP) will be generated.

To move single-precision floating-point values to and from unaligned memory
locations, use the (V)MOVUPS instruction.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). Note: In VEX-encoded versions, VEX.vvvv is reserved
and must be 1111b otherwise instructions will #UD. 128-bit versions: Moves 128
bits of packed single-precision floating-point values from the source operand
(second operand) to the destination operand (first operand). This instruction
can be used to load an XMM register from a 128-bit memory location, to store
the contents of an XMM register into a 128-bit memory location, or to move data
between two XMM registers. When the source or destination operand is a memory
operand, the operand must be aligned on a 16-byte boundary or a general-protection
exception (#GP) will be generated. To move single-precision floatingpoint values
to and from unaligned memory locations, use the VMOVUPS instruction. 128-bit
Legacy SSE version: Bits (VLMAX-1:128) of the corresponding YMM destination
register remain unchanged. VEX.128 encoded version: Bits (VLMAX-1:128) of the
destination YMM register are zeroed. VEX.256 encoded version: Moves 256 bits
of packed single-precision floating-point values from the source operand (second
operand) to the destination operand (first operand). This instruction can be
used to load a YMM register from a 256-bit memory location, to store the contents
of a YMM register into a 256-bit memory location, or to move data between two
YMM registers.

Operation:

MOVAPS (128-bit load- and register-copy- form Legacy SSE version)
DEST[127:0] <- SRC[127:0]
DEST[VLMAX-1:128] (Unmodified)
(V)MOVAPS (128-bit store form)
DEST[127:0] <- SRC[127:0]
VMOVAPS (VEX.128 encoded version)
DEST[127:0] <- SRC[127:0]
DEST[VLMAX-1:128] <- 0
VMOVAPS (VEX.256 encoded version)
DEST[255:0] <- SRC[255:0]

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVAPS: | __m128 _mm_load_ps (float const * p);
| MOVAPS: | _mm_store_ps(float * p, __m128 a);   
| VMOVAPS:| __m256 _mm256_load_ps (float const * 
|         | p);                                  
| VMOVAPS:| _mm256_store_ps(float * p, __m256 a);

SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 1.SSE; additionally

| #UD| If VEX.vvvv != 1111B.


platform: x86
mnem: MOVBE
description:
MOVBE - Move Data After Swapping Bytes:
| Opcode             | Instruction   | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                          
| 0F 38 F0 /r        | MOVBE r16, m16| RM   | Valid      | Valid          | Reverse byte order in m16 and move to
|                    |               |      |            |                | r16.                                 
| 0F 38 F0 /r        | MOVBE r32, m32| RM   | Valid      | Valid          | Reverse byte order in m32 and move to
|                    |               |      |            |                | r32.                                 
| REX.W + 0F 38 F0 /r| MOVBE r64, m64| RM   | Valid      | N.E.           | Reverse byte order in m64 and move to
|                    |               |      |            |                | r64.                                 
| 0F 38 F1 /r        | MOVBE m16, r16| MR   | Valid      | Valid          | Reverse byte order in r16 and move to
|                    |               |      |            |                | m16.                                 
| 0F 38 F1 /r        | MOVBE m32, r32| MR   | Valid      | Valid          | Reverse byte order in r32 and move to
|                    |               |      |            |                | m32.                                 
| REX.W + 0F 38 F1 /r| MOVBE m64, r64| MR   | Valid      | N.E.           | Reverse byte order in r64 and move to
|                    |               |      |            |                | m64.                                 

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       

Description:
Performs a byte swap operation on the data copied from the second operand (source
operand) and store the result in the first operand (destination operand). The
source operand can be a general-purpose register, or memory location; the destination
register can be a general-purpose register, or a memory location; however, both
operands can not be registers, and only one operand can be a memory location.
Both operands must be the same size, which can be a word, a doubleword or quadword.

The MOVBE instruction is provided for swapping the bytes on a read from memory
or on a write to memory; thus providing support for converting little-endian
values to big-endian format and vice versa.

In 64-bit mode, the instruction's default operation size is 32 bits. Use of
the REX.R prefix permits access to additional registers (R8-R15). Use of the
REX.W prefix promotes operation to 64 bits. See the summary chart at the beginning
of this section for encoding data and limits.

Operation:

TEMP <- SRC
IF ( OperandSize = 16)
  THEN
     DEST[7:0] <- TEMP[15:8];
     DEST[15:8] <- TEMP[7:0];
  ELES IF
     DEST[7:0] <- TEMP[31:24];
     DEST[15:8] <- TEMP[23:16];
     DEST[23:16] <- TEMP[15:8];
     DEST[31:23] <- TEMP[7:0];
  ELSE IF ( OperandSize = 64)
     DEST[7:0] <- TEMP[63:56];
     DEST[15:8] <- TEMP[55:48];
     DEST[23:16] <- TEMP[47:40];
     DEST[31:24] <- TEMP[39:32];
     DEST[39:32] <- TEMP[31:24];
     DEST[47:40] <- TEMP[23:16];
     DEST[55:48] <- TEMP[15:8];
     DEST[63:56] <- TEMP[7:0];
FI;

Flags Affected:
None.


Protected Mode Exceptions:
| #GP(0)         | If the destination operand is in a non-writable
|                | segment. If a memory operand effective         
|                | address is outside the CS, DS, ES, FS,         
|                | or GS segment limit. If the DS, ES,            
|                | FS, or GS register contains a NULL segment     
|                | selector.                                      
| #SS(0)         | If a memory operand effective address          
|                | is outside the SS segment limit.               
| #PF(fault-code)| If a page fault occurs.                        
| #AC(0)         | If alignment checking is enabled and           
|                | an unaligned memory reference is made          
|                | while the current privilege level is           
|                | 3.                                             
| #UD            | If CPUID.01H:ECX.MOVBE[bit 22] = 0.            
|                | If the LOCK prefix is used. If REP (F3H)       
|                | prefix is used.                                

Real-Address Mode Exceptions:
| #GP| If a memory operand effective address   
|    | is outside the CS, DS, ES, FS, or GS    
|    | segment limit.                          
| #SS| If a memory operand effective address   
|    | is outside the SS segment limit.        
| #UD| If CPUID.01H:ECX.MOVBE[bit 22] = 0.     
|    | If the LOCK prefix is used. If REP (F3H)
|    | prefix is used.                         

Virtual-8086 Mode Exceptions:
| #GP(0)         | If a memory operand effective address   
|                | is outside the CS, DS, ES, FS, or GS    
|                | segment limit.                          
| #SS(0)         | If a memory operand effective address   
|                | is outside the SS segment limit.        
| #PF(fault-code)| If a page fault occurs.                 
| #AC(0)         | If alignment checking is enabled and    
|                | an unaligned memory reference is made   
|                | while the current privilege level is    
|                | 3.                                      
| #UD            | If CPUID.01H:ECX.MOVBE[bit 22] = 0.     
|                | If the LOCK prefix is used. If REP (F3H)
|                | prefix is used. If REPNE (F2H) prefix   
|                | is used and CPUID.01H:ECX.SSE4_2[bit    
|                | 20] = 0.                                

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #GP(0)         | If the memory address is in a non-canonical
|                | form.                                      
| #SS(0)         | If the stack address is in a non-canonical 
|                | form.                                      
| #PF(fault-code)| If a page fault occurs.                    
| #AC(0)         | If alignment checking is enabled and       
|                | an unaligned memory reference is made      
|                | while the current privilege level is       
|                | 3.                                         
| #UD            | If CPUID.01H:ECX.MOVBE[bit 22] = 0.        
|                | If the LOCK prefix is used. If REP (F3H)   
|                | prefix is used.                            


platform: x86
mnem: MOVD
description:
MOVD/MOVQ - Move Doubleword/Move Quadword:
| Opcode/Instruction                        | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                              
| 0F 6E /r MOVD mm, r/m32                   | RM   | V/V           | MMX               | Move doubleword from r/m32 to mm.        
| REX.W + 0F 6E /r MOVQ mm, r/m64           | RM   | V/N.E.        | MMX               | Move quadword from r/m64 to mm.          
| 0F 7E /r MOVD r/m32, mm                   | MR   | V/V           | MMX               | Move doubleword from mm to r/m32.        
| REX.W + 0F 7E /r MOVQ r/m64, mm           | MR   | V/N.E.        | MMX               | Move quadword from mm to r/m64.          
| VEX.128.66.0F.W0 6E /VMOVD xmm1, r32/m32  | RM   | V/V           | AVX               | Move doubleword from r/m32 to xmm1.      
| VEX.128.66.0F.W1 6E /r VMOVQ xmm1, r64/m64| RM   | V/N.E.        | AVX               | Move quadword from r/m64 to xmm1.        
| 66 0F 6E /r MOVD xmm, r/m32               | RM   | V/V           | SSE2              | Move doubleword from r/m32 to xmm.       
| 66 REX.W 0F 6E /r MOVQ xmm, r/m64         | RM   | V/N.E.        | SSE2              | Move quadword from r/m64 to xmm.         
| 66 0F 7E /r MOVD r/m32, xmm               | MR   | V/V           | SSE2              | Move doubleword from xmm register to     
|                                           |      |               |                   | r/m32.                                   
| 66 REX.W 0F 7E /r MOVQ r/m64, xmm         | MR   | V/N.E.        | SSE2              | Move quadword from xmm register to r/m64.
| VEX.128.66.0F.W0 7E /r VMOVD r32/m32,     | MR   | V/V           | AVX               | Move doubleword from xmm1 register to    
| xmm1                                      |      |               |                   | r/m32.                                   
| VEX.128.66.0F.W1 7E /r VMOVQ r64/m64,     | MR   | V/N.E.        | AVX               | Move quadword from xmm1 register to      
| xmm1                                      |      |               |                   | r/m64.                                   

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       

Description:
Copies a doubleword from the source operand (second operand) to the destination
operand (first operand). The source and destination operands can be general-purpose
registers, MMX technology registers, XMM registers, or 32-bit memory locations.
This instruction can be used to move a doubleword to and from the low doubleword
of an MMX technology register and a general-purpose register or a 32-bit memory
location, or to and from the low doubleword of an XMM register and a general-purpose
register or a 32-bit memory location. The instruction cannot be used to transfer
data between MMX technology registers, between XMM registers, between general-purpose
registers, or between memory locations.

When the destination operand is an MMX technology register, the source operand
is written to the low doubleword of the register, and the register is zero-extended
to 64 bits. When the destination operand is an XMM register, the source operand
is written to the low doubleword of the register, and the register is zero-extended
to 128 bits.

In 64-bit mode, the instruction's default operation size is 32 bits. Use of
the REX.R prefix permits access to additional registers (R8-R15). Use of the
REX.W prefix promotes operation to 64 bits. See the summary chart at the beginning
of this section for encoding data and limits.

Operation:

MOVD (when destination operand is MMX technology register)
  DEST[31:0] <- SRC;
  DEST[63:32] <- 00000000H;
MOVD (when destination operand is XMM register)
  DEST[31:0] <- SRC;
  DEST[127:32] <- 000000000000000000000000H;
  DEST[VLMAX-1:128] (Unmodified)
MOVD (when source operand is MMX technology or XMM register)
  DEST <- SRC[31:0];
VMOVD (VEX-encoded version when destination is an XMM register)
  DEST[31:0] <- SRC[31:0]
  DEST[VLMAX-1:32] <- 0
MOVQ (when destination operand is XMM register)
  DEST[63:0] <- SRC[63:0];
  DEST[127:64] <- 0000000000000000H;
  DEST[VLMAX-1:128] (Unmodified)
MOVQ (when destination operand is r/m64)
  DEST[63:0] <- SRC[63:0];
MOVQ (when source operand is XMM register or r/m64)
  DEST <- SRC[63:0];
VMOVQ (VEX-encoded version when destination is an XMM register)
  DEST[63:0] <- SRC[63:0]
  DEST[VLMAX-1:64] <- 0

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVD:| __m64 _mm_cvtsi32_si64 (int i )    
| MOVD:| int _mm_cvtsi64_si32 ( __m64m )    
| MOVD:| __m128i _mm_cvtsi32_si128 (int a)  
| MOVD:| int _mm_cvtsi128_si32 ( __m128i a) 
| MOVQ:| __int64 _mm_cvtsi128_si64(__m128i);
| MOVQ:| __m128i _mm_cvtsi64_si128(__int64);

Flags Affected:
None.


SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 5; additionally

| #UD| If VEX.L = 1. If VEX.vvvv != 1111B.


platform: x86
mnem: MOVDDUP
description:
MOVDDUP - Move One Double-FP and Duplicate:
| Opcode/Instruction                    | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                                   
| F2 0F 12 /r MOVDDUP xmm1, xmm2/m64    | RM   | V/V           | SSE3              | Move one double-precision floating-point      
|                                       |      |               |                   | value from the lower 64-bit operand           
|                                       |      |               |                   | in xmm2/m64 to xmm1 and duplicate.            
| VEX.128.F2.0F.WIG 12 /r VMOVDDUP xmm1,| RM   | V/V           | AVX               | Move double-precision floating-point          
| xmm2/m64                              |      |               |                   | values from xmm2/mem and duplicate into       
|                                       |      |               |                   | xmm1.                                         
| VEX.256.F2.0F.WIG 12 /r VMOVDDUP ymm1,| RM   | V/V           | AVX               | Move even index double-precision floatingpoint
| ymm2/m256                             |      |               |                   | values from ymm2/mem and duplicate each       
|                                       |      |               |                   | element into ymm1.                            

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
The linear address corresponds to the address of the least-significant byte
of the referenced memory data. When a memory address is indicated, the 8 bytes
of data at memory location m64 are loaded. When the register-register form of
this operation is used, the lower half of the 128-bit source register is duplicated
and copied into the 128-bit destination register. See Figure 3-24.

MOVDDUP xmm1, xmm2/m64

| [63:0]| xmm2/m64
RESULT:

| xmm1[127:64]| xmm2/m64[63:0][127:64]| xmm1[63:0]| xmm2/m64[63:0]xmm1 [63:0]
OM15997

| Figure 3-24.| MOVDDUP - Move One Double-FP and Duplicate
In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15).

Operation:

IF (Source = m64)
  THEN
     (* Load instruction *)
     xmm1[63:0] = m64;
     xmm1[127:64] = m64;
  ELSE
     (* Move instruction *)
     xmm1[63:0] = xmm2[63:0];
     xmm1[127:64] = xmm2[63:0];
FI;
MOVDDUP (128-bit Legacy SSE version)
DEST[63:0] <- SRC[63:0]
DEST[127:64] <- SRC[63:0]
DEST[VLMAX-1:128] (Unmodified)
VMOVDDUP (VEX.128 encoded version)
DEST[63:0] <- SRC[63:0]
DEST[127:64] <- SRC[63:0]
DEST[VLMAX-1:128] <- 0
VMOVDDUP (VEX.256 encoded version)
DEST[63:0] <- SRC[63:0]
DEST[127:64] <- SRC[63:0]
DEST[191:128] <- SRC[191:128]
DEST[255:192] <- SRC[191:128]

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVDDUP:| __m128d _mm_movedup_pd(__m128d a)  
| MOVDDUP:| __m128d _mm_loaddup_pd(double const
|         | * dp)                              

SIMD Floating-Point Exceptions:
None


Other Exceptions:
See Exceptions Type 5; additionally

| #UD| If VEX.vvvv != 1111B.


platform: x86
mnem: MOVDQA
description:
MOVDQA - Move Aligned Double Quadword:
| Opcode/Instruction                        | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                                
| 66 0F 6F /r MOVDQA xmm1, xmm2/m128        | RM   | V/V           | SSE2              | Move aligned double quadword from xmm2/m128
|                                           |      |               |                   | to xmm1.                                   
| 66 0F 7F /r MOVDQA xmm2/m128, xmm1        | MR   | V/V           | SSE2              | Move aligned double quadword from xmm1     
|                                           |      |               |                   | to xmm2/m128.                              
| VEX.128.66.0F.WIG 6F /r VMOVDQA xmm1,     | RM   | V/V           | AVX               | Move aligned packed integer values from    
| xmm2/m128                                 |      |               |                   | xmm2/mem to xmm1.                          
| VEX.128.66.0F.WIG 7F /r VMOVDQA xmm2/m128,| MR   | V/V           | AVX               | Move aligned packed integer values from    
| xmm1                                      |      |               |                   | xmm1 to xmm2/mem.                          
| VEX.256.66.0F.WIG 6F /r VMOVDQA ymm1,     | RM   | V/V           | AVX               | Move aligned packed integer values from    
| ymm2/m256                                 |      |               |                   | ymm2/mem to ymm1.                          
| VEX.256.66.0F.WIG 7F /r VMOVDQA ymm2/m256,| MR   | V/V           | AVX               | Move aligned packed integer values from    
| ymm1                                      |      |               |                   | ymm1 to ymm2/mem.                          

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       

Description:
128-bit versions: Moves 128 bits of packed integer values from the source operand
(second operand) to the destination operand (first operand). This instruction
can be used to load an XMM register from a 128-bit memory location, to store
the contents of an XMM register into a 128-bit memory location, or to move data
between two XMM registers. When the source or destination operand is a memory
operand, the operand must be aligned on a 16-byte boundary or a general-protection
exception (#GP) will be generated. To move integer data to and from unaligned
memory locations, use the VMOVDQU instruction.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). 128-bit Legacy SSE version: Bits (VLMAX-1:128) of the
corresponding YMM destination register remain unchanged. VEX.128 encoded version:
Bits (VLMAX-1:128) of the destination YMM register are zeroed. VEX.256 encoded
version: Moves 256 bits of packed integer values from the source operand (second
operand) to the destination operand (first operand). This instruction can be
used to load a YMM register from a 256-bit memory location, to store the contents
of a YMM register into a 256-bit memory location, or to move data between two
YMM registers. When the source or destination operand is a memory operand, the
operand must be aligned on a 32-byte boundary or a general-protection exception
(#GP) will be generated. To move integer data to and from unaligned memory locations,
use the VMOVDQU instruction. Note: In VEX-encoded versions, VEX.vvvv is reserved
and must be 1111b otherwise instructions will #UD.

Operation:

MOVDQA (128-bit load- and register- form Legacy SSE version)
DEST[127:0] <- SRC[127:0]
DEST[VLMAX-1:128] (Unmodified)
(* #GP if SRC or DEST unaligned memory operand *)
(V)MOVDQA (128-bit store forms)
DEST[127:0] <- SRC[127:0]
VMOVDQA (VEX.128 encoded version)
DEST[127:0] <- SRC[127:0]
DEST[VLMAX-1:128] <- 0
VMOVDQA (VEX.256 encoded version)
DEST[255:0] <- SRC[255:0]

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVDQA: | __m128i _mm_load_si128 ( __m128i *p)      
| MOVDQA: | void _mm_store_si128 ( __m128i *p, __m128i
|         | a)                                        
| VMOVDQA:| __m256i _mm256_load_si256 (__m256i *      
|         | p);                                       
| VMOVDQA:| _mm256_store_si256(_m256i *p, __m256i     
|         | a);                                       

SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 1.SSE2; additionally

| #UD| If VEX.vvvv != 1111B.


platform: x86
mnem: MOVDQU
description:
MOVDQU - Move Unaligned Double Quadword:
| Opcode/Instruction                        | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                         
| F3 0F 6F /r MOVDQU xmm1, xmm2/m128        | RM   | V/V           | SSE2              | Move unaligned double quadword from 
|                                           |      |               |                   | xmm2/m128 to xmm1.                  
| F3 0F 7F /r MOVDQU xmm2/m128, xmm1        | MR   | V/V           | SSE2              | Move unaligned double quadword from 
|                                           |      |               |                   | xmm1 to xmm2/m128.                  
| VEX.128.F3.0F.WIG 6F /r VMOVDQU xmm1,     | RM   | V/V           | AVX               | Move unaligned packed integer values
| xmm2/m128                                 |      |               |                   | from xmm2/mem to xmm1.              
| VEX.128.F3.0F.WIG 7F /r VMOVDQU xmm2/m128,| MR   | V/V           | AVX               | Move unaligned packed integer values
| xmm1                                      |      |               |                   | from xmm1 to xmm2/mem.              
| VEX.256.F3.0F.WIG 6F /r VMOVDQU ymm1,     | RM   | V/V           | AVX               | Move unaligned packed integer values
| ymm2/m256                                 |      |               |                   | from ymm2/mem to ymm1.              
| VEX.256.F3.0F.WIG 7F /r VMOVDQU ymm2/m256,| MR   | V/V           | AVX               | Move unaligned packed integer values
| ymm1                                      |      |               |                   | from ymm1 to ymm2/mem.              

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       

Description:
128-bit versions:

Moves 128 bits of packed integer values from the source operand (second operand)
to the destination operand (first operand). This instruction can be used to
load an XMM register from a 128-bit memory location, to store the contents of
an XMM register into a 128-bit memory location, or to move data between two
XMM registers. When the source or destination operand is a memory operand, the
operand may be unaligned on a 16-byte boundary without causing a general-protection
exception (#GP) to be generated.1

To move a double quadword to or from memory locations that are known to be aligned
on 16-byte boundaries, use the MOVDQA instruction.

While executing in 16-bit addressing mode, a linear address for a 128-bit data
access that overlaps the end of a 16bit segment is not allowed and is defined
as reserved behavior. A specific processor implementation may or may not generate
a general-protection exception (#GP) in this situation, and the address that
spans the end of the segment may or may not wrap around to the beginning of
the segment.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). 128-bit Legacy SSE version: Bits (VLMAX-1:128) of the
corresponding YMM destination register remain unchanged. When the source or
destination operand is a memory operand, the operand may be unaligned to any
alignment without causing a general-protection exception (#GP) to be generated
VEX.128 encoded version: Bits (VLMAX-1:128) of the destination YMM register
are zeroed.

VEX.256 encoded version: Moves 256 bits of packed integer values from the source
operand (second operand) to the destination operand (first operand). This instruction
can be used to load a YMM register from a 256-bit memory

| 1.| If alignment checking is enabled (CR0.AM  
|   | = 1, RFLAGS.AC = 1, and CPL = 3), an      
|   | alignment-check exception (#AC) may       
|   | or may not be generated (depending on     
|   | processor implementation) when the operand
|   | is not aligned on an 8-byte boundary.     
location, to store the contents of a YMM register into a 256-bit memory location,
or to move data between two YMM registers. Note: In VEX-encoded versions, VEX.vvvv
is reserved and must be 1111b otherwise instructions will #UD.

Operation:

MOVDQU load and register copy (128-bit Legacy SSE version)
DEST[127:0] <- SRC[127:0]
DEST[VLMAX-1:128] (Unmodified)
(V)MOVDQU 128-bit store-form versions
DEST[127:0] <- SRC[127:0]
VMOVDQU (VEX.128 encoded version)
DEST[127:0] <- SRC[127:0]
DEST[VLMAX-1:128] <- 0
VMOVDQU (VEX.256 encoded version)
DEST[255:0] <- SRC[255:0]

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVDQU: | void _mm_storeu_si128 ( __m128i *p,   
|         | __m128i a)                            
| MOVDQU: | __m128i _mm_loadu_si128 ( __m128i *p) 
| VMOVDQU:| __m256i _mm256_loadu_si256 (__m256i   
|         | * p);                                 
| VMOVDQU:| _mm256_storeu_si256(_m256i *p, __m256i
|         | a);                                   

SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 4; additionally

| #UD| If VEX.vvvv != 1111B.


platform: x86
mnem: MOVDQ2Q
description:
MOVDQ2Q - Move Quadword from XMM to MMX Technology Register:
| Opcode     | Instruction    | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                                
| F2 0F D6 /r| MOVDQ2Q mm, xmm| RM   | Valid      | Valid          | Move low quadword from xmm to mmx register.

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
Moves the low quadword from the source operand (second operand) to the destination
operand (first operand). The source operand is an XMM register and the destination
operand is an MMX technology register.

This instruction causes a transition from x87 FPU to MMX technology operation
(that is, the x87 FPU top-of-stack pointer is set to 0 and the x87 FPU tag word
is set to all 0s [valid]). If this instruction is executed while an x87 FPU
floating-point exception is pending, the exception is handled before the MOVDQ2Q
instruction is executed.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15).

Operation:

DEST <- SRC[63:0];

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVDQ2Q:| __m64 _mm_movepi64_pi64 ( __m128i a)

SIMD Floating-Point Exceptions:
None.


Protected Mode Exceptions:
| #NM| If CR0.TS[bit 3] = 1.                   
| #UD| If CR0.EM[bit 2] = 1. If CR4.OSFXSR[bit 
|    | 9] = 0. If CPUID.01H:EDX.SSE2[bit 26]   
|    | = 0. If the LOCK prefix is used.        
| #MF| If there is a pending x87 FPU exception.

Real-Address Mode Exceptions:
Same exceptions as in protected mode.


Virtual-8086 Mode Exceptions:
Same exceptions as in protected mode.


Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
Same exceptions as in protected mode.


platform: x86
mnem: MOVHLPS
description:
MOVHLPS -  Move Packed Single-Precision Floating-Point Values High to Low:
| Opcode/Instruction                     | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                                    
| 0F 12 /r MOVHLPS xmm1, xmm2            | RM   | V/V           | SSE               | Move two packed single-precision floatingpoint 
|                                        |      |               |                   | values from high quadword of xmm2 to           
|                                        |      |               |                   | low quadword of xmm1.                          
| VEX.NDS.128.0F.WIG 12 /r VMOVHLPS xmm1,| RVM  | V/V           | AVX               | Merge two packed single-precision floatingpoint
| xmm2, xmm3                             |      |               |                   | values from high quadword of xmm3 and          
|                                        |      |               |                   | low quadword of xmm2.                          

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA           | NA       
| RVM  | ModRM:reg (w)| VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
This instruction cannot be used for memory to register moves. 128-bit two-argument
form: Moves two packed single-precision floating-point values from the high
quadword of the second XMM argument (second operand) to the low quadword of
the first XMM register (first argument). The high quadword of the destination
operand is left unchanged. Bits (VLMAX-1:64) of the corresponding YMM destination
register are unmodified. 128-bit three-argument form Moves two packed single-precision
floating-point values from the high quadword of the third XMM argument (third
operand) to the low quadword of the destination (first operand). Copies the
high quadword from the second XMM argument (second operand) to the high quadword
of the destination (first operand). Bits (VLMAX-1:128) of the destination YMM
register are zeroed.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). If VMOVHLPS is encoded with VEX.L= 1, an attempt to
execute the instruction encoded with VEX.L= 1 will cause an #UD exception.

Operation:

MOVHLPS (128-bit two-argument form)
DEST[63:0] <- SRC[127:64]
DEST[VLMAX-1:64] (Unmodified)
VMOVHLPS (128-bit three-argument form)
DEST[63:0] <- SRC2[127:64]
DEST[127:64] <- SRC1[127:64]
DEST[VLMAX-1:128] <- 0

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVHLPS:| __m128 _mm_movehl_ps(__m128 a, __m128
|         | b)                                   

SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 7; additionally

| #UD| If VEX.L= 1.


platform: x86
mnem: MOVHPD
description:
MOVHPD - Move High Packed Double-Precision Floating-Point Value:
| Opcode/Instruction                     | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                            
| 66 0F 16 /r MOVHPD xmm, m64            | RM   | V/V           | SSE2              | Move double-precision floating-point   
|                                        |      |               |                   | value from m64 to high quadword of xmm.
| 66 0F 17 /r MOVHPD m64, xmm            | MR   | V/V           | SSE2              | Move double-precision floating-point   
|                                        |      |               |                   | value from high quadword of xmm to m64.
| VEX.NDS.128.66.0F.WIG 16 /r VMOVHPD    | RVM  | V/V           | AVX               | Merge double-precision floating-point  
| xmm2, xmm1, m64                        |      |               |                   | value from m64 and the low quadword    
|                                        |      |               |                   | of xmm1.                               
| VEX128.66.0F.WIG 17/r VMOVHPD m64, xmm1| MR   | V/V           | AVX               | Move double-precision floating-point   
|                                        |      |               |                   | values from high quadword of xmm1 to   
|                                        |      |               |                   | m64.                                   

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| MR   | ModRM:r/m (w)   | ModRM:reg (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
This instruction cannot be used for register to register or memory to memory
moves. 128-bit Legacy SSE load: Moves a double-precision floating-point value
from the source 64-bit memory operand and stores it in the high 64bits of the
destination XMM register. The lower 64bits of the XMM register are preserved.
The upper 128-bits of the corresponding YMM destination register are preserved.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). VEX.128 encoded load: Loads a double-precision floating-point
value from the source 64-bit memory operand (third operand) and stores it in
the upper 64-bits of the destination XMM register (first operand). The low 64-bits
from second XMM register (second operand) are stored in the lower 64-bits of
the destination. The upper 128-bits of the destination YMM register are zeroed.
128-bit store: Stores a double-precision floating-point value from the high
64-bits of the XMM register source (second operand) to the 64-bit memory location
(first operand). Note: VMOVHPD (store) (VEX.128.66.0F 17 /r) is legal and has
the same behavior as the existing 66 0F 17 store. For VMOVHPD (store) (VEX.128.66.0F
17 /r) instruction version, VEX.vvvv is reserved and must be 1111b otherwise
instruction will #UD. If VMOVHPD is encoded with VEX.L= 1, an attempt to execute
the instruction encoded with VEX.L= 1 will cause an #UD exception.

Operation:

MOVHPD (128-bit Legacy SSE load)
DEST[63:0] (Unmodified)
DEST[127:64] <- SRC[63:0]
DEST[VLMAX-1:128] (Unmodified)
VMOVHPD (VEX.128 encoded load)
DEST[63:0] <- SRC1[63:0]
DEST[127:64] <- SRC2[63:0]
DEST[VLMAX-1:128] <- 0
VMOVHPD (store)
DEST[63:0] <- SRC[127:64]

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVHPD:| __m128d _mm_loadh_pd ( __m128d a, double
|        | *p)                                     
| MOVHPD:| void _mm_storeh_pd (double *p, __m128d  
|        | a)                                      

SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 5; additionally

| #UD| If VEX.L= 1.


platform: x86
mnem: MOVHPS
description:
MOVHPS - Move High Packed Single-Precision Floating-Point Values:
| Opcode/Instruction                    | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                                    
| 0F 16 /r MOVHPS xmm, m64              | RM   | V/V           | SSE               | Move two packed single-precision floatingpoint 
|                                       |      |               |                   | values from m64 to high quadword of            
|                                       |      |               |                   | xmm.                                           
| 0F 17 /r MOVHPS m64, xmm              | MR   | V/V           | SSE               | Move two packed single-precision floatingpoint 
|                                       |      |               |                   | values from high quadword of xmm to            
|                                       |      |               |                   | m64.                                           
| VEX.NDS.128.0F.WIG 16 /r VMOVHPS xmm2,| RVM  | V/V           | AVX               | Merge two packed single-precision floatingpoint
| xmm1, m64                             |      |               |                   | values from m64 and the low quadword           
|                                       |      |               |                   | of xmm1.                                       
| VEX.128.0F.WIG 17/r VMOVHPS m64, xmm1 | MR   | V/V           | AVX               | Move two packed single-precision floatingpoint 
|                                       |      |               |                   | values from high quadword of xmm1to            
|                                       |      |               |                   | m64.                                           

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| MR   | ModRM:r/m (w)   | ModRM:reg (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
This instruction cannot be used for register to register or memory to memory
moves. 128-bit Legacy SSE load: Moves two packed single-precision floating-point
values from the source 64-bit memory operand and stores them in the high 64-bits
of the destination XMM register. The lower 64bits of the XMM register are preserved.
The upper 128-bits of the corresponding YMM destination register are preserved.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). VEX.128 encoded load: Loads two single-precision floating-point
values from the source 64-bit memory operand (third operand) and stores it in
the upper 64-bits of the destination XMM register (first operand). The low 64-bits
from second XMM register (second operand) are stored in the lower 64-bits of
the destination. The upper 128-bits of the destination YMM register are zeroed.
128-bit store: Stores two packed single-precision floating-point values from
the high 64-bits of the XMM register source (second operand) to the 64-bit memory
location (first operand). Note: VMOVHPS (store) (VEX.NDS.128.0F 17 /r) is legal
and has the same behavior as the existing 0F 17 store. For VMOVHPS (store) (VEX.NDS.128.0F
17 /r) instruction version, VEX.vvvv is reserved and must be 1111b otherwise
instruction will #UD. If VMOVHPS is encoded with VEX.L= 1, an attempt to execute
the instruction encoded with VEX.L= 1 will cause an #UD exception.

Operation:

MOVHPS (128-bit Legacy SSE load)
DEST[63:0] (Unmodified)
DEST[127:64] <- SRC[63:0]
DEST[VLMAX-1:128] (Unmodified)
VMOVHPS (VEX.128 encoded load)
DEST[63:0] <- SRC1[63:0]
DEST[127:64] <- SRC2[63:0]
DEST[VLMAX-1:128] <- 0
VMOVHPS (store)
DEST[63:0] <- SRC[127:64]

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVHPS:| __m128d _mm_loadh_pi ( __m128d a, __m64
|        | *p)                                    
| MOVHPS:| void _mm_storeh_pi (__m64 *p, __m128d  
|        | a)                                     

SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 5; additionally

| #UD| If VEX.L= 1.


platform: x86
mnem: MOVLHPS
description:
MOVLHPS - Move Packed Single-Precision Floating-Point Values Low to High:
| Opcode/Instruction                     | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                                    
| 0F 16 /r MOVLHPS xmm1, xmm2            | RM   | V/V           | SSE               | Move two packed single-precision floatingpoint 
|                                        |      |               |                   | values from low quadword of xmm2 to            
|                                        |      |               |                   | high quadword of xmm1.                         
| VEX.NDS.128.0F.WIG 16 /r VMOVLHPS xmm1,| RVM  | V/V           | AVX               | Merge two packed single-precision floatingpoint
| xmm2, xmm3                             |      |               |                   | values from low quadword of xmm3 and           
|                                        |      |               |                   | low quadword of xmm2.                          

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA           | NA       
| RVM  | ModRM:reg (w)| VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
This instruction cannot be used for memory to register moves. 128-bit two-argument
form: Moves two packed single-precision floating-point values from the low quadword
of the second XMM argument (second operand) to the high quadword of the first
XMM register (first argument). The low quadword of the destination operand is
left unchanged. The upper 128 bits of the corresponding YMM destination register
are unmodified. 128-bit three-argument form Moves two packed single-precision
floating-point values from the low quadword of the third XMM argument (third
operand) to the high quadword of the destination (first operand). Copies the
low quadword from the second XMM argument (second operand) to the low quadword
of the destination (first operand). The upper 128-bits of the destination YMM
register are zeroed. If VMOVLHPS is encoded with VEX.L= 1, an attempt to execute
the instruction encoded with VEX.L= 1 will cause an #UD exception.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15).

Operation:

MOVLHPS (128-bit two-argument form)
DEST[63:0] (Unmodified)
DEST[127:64] <- SRC[63:0]
DEST[VLMAX-1:128] (Unmodified)
VMOVLHPS (128-bit three-argument form)
DEST[63:0] <- SRC1[63:0]
DEST[127:64] <- SRC2[63:0]
DEST[VLMAX-1:128] <- 0

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVHLPS:| __m128 _mm_movelh_ps(__m128 a, __m128
|         | b)                                   

SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 7; additionally

| #UD| If VEX.L= 1.


platform: x86
mnem: MOVLPD
description:
MOVLPD - Move Low Packed Double-Precision Floating-Point Value:
| Opcode/Instruction                 | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                             
| 66 0F 12 /r MOVLPD xmm, m64        | RM   | V/V           | SSE2              | Move double-precision floating-point    
|                                    |      |               |                   | value from m64 to low quadword of xmm   
|                                    |      |               |                   | register.                               
| 66 0F 13 /r MOVLPD m64, xmm        | MR   | V/V           | SSE2              | Move double-precision floating-point    
|                                    |      |               |                   | nvalue from low quadword of xmm register
|                                    |      |               |                   | to m64.                                 
| VEX.NDS.128.66.0F.WIG 12 /r VMOVLPD| RVM  | V/V           | AVX               | Merge double-precision floating-point   
| xmm2, xmm1, m64                    |      |               |                   | value from m64 and the high quadword    
|                                    |      |               |                   | of xmm1.                                
| VEX.128.66.0F.WIG 13/r VMOVLPD m64,| MR   | V/V           | AVX               | Move double-precision floating-point    
| xmm1                               |      |               |                   | values from low quadword of xmm1 to     
|                                    |      |               |                   | m64.                                    

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| MR   | ModRM:r/m (w)   | ModRM:reg (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
This instruction cannot be used for register to register or memory to memory
moves. 128-bit Legacy SSE load: Moves a double-precision floating-point value
from the source 64-bit memory operand and stores it in the low 64bits of the
destination XMM register. The upper 64bits of the XMM register are preserved.
The upper 128-bits of the corresponding YMM destination register are preserved.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). VEX.128 encoded load: Loads a double-precision floating-point
value from the source 64-bit memory operand (third operand), merges it with
the upper 64-bits of the first source XMM register (second operand), and stores
it in the low 128-bits of the destination XMM register (first operand). The
upper 128-bits of the destination YMM register are zeroed. 128-bit store: Stores
a double-precision floating-point value from the low 64-bits of the XMM register
source (second operand) to the 64-bit memory location (first operand). Note:
VMOVLPD (store) (VEX.128.66.0F 13 /r) is legal and has the same behavior as
the existing 66 0F 13 store. For VMOVLPD (store) (VEX.128.66.0F 13 /r) instruction
version, VEX.vvvv is reserved and must be 1111b otherwise instruction will #UD.
If VMOVLPD is encoded with VEX.L= 1, an attempt to execute the instruction encoded
with VEX.L= 1 will cause an #UD exception.

Operation:

MOVLPD (128-bit Legacy SSE load)
DEST[63:0] <- SRC[63:0]
DEST[VLMAX-1:64] (Unmodified)
VMOVLPD (VEX.128 encoded load)
DEST[63:0] <- SRC2[63:0]
DEST[127:64] <- SRC1[127:64]
DEST[VLMAX-1:128] <- 0
VMOVLPD (store)
DEST[63:0] <- SRC[63:0]

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVLPD:| __m128d _mm_loadl_pd ( __m128d a, double
|        | *p)                                     
| MOVLPD:| void _mm_storel_pd (double *p, __m128d  
|        | a)                                      

SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 5; additionally

| #UD| If VEX.L= 1. If VEX.vvvv != 1111B.


platform: x86
mnem: MOVLPS
description:
MOVLPS - Move Low Packed Single-Precision Floating-Point Values:
| Opcode/Instruction                    | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                                    
| 0F 12 /r MOVLPS xmm, m64              | RM   | V/V           | SSE               | Move two packed single-precision floatingpoint 
|                                       |      |               |                   | values from m64 to low quadword of xmm.        
| 0F 13 /r MOVLPS m64, xmm              | MR   | V/V           | SSE               | Move two packed single-precision floatingpoint 
|                                       |      |               |                   | values from low quadword of xmm to m64.        
| VEX.NDS.128.0F.WIG 12 /r VMOVLPS xmm2,| RVM  | V/V           | AVX               | Merge two packed single-precision floatingpoint
| xmm1, m64                             |      |               |                   | values from m64 and the high quadword          
|                                       |      |               |                   | of xmm1.                                       
| VEX.128.0F.WIG 13/r VMOVLPS m64, xmm1 | MR   | V/V           | AVX               | Move two packed single-precision floatingpoint 
|                                       |      |               |                   | values from low quadword of xmm1 to            
|                                       |      |               |                   | m64.                                           

Instruction Operand Encoding:
| Op/En| Operand 1       | Operand 2    | Operand 3    | Operand 4
| RM   | ModRM:reg (r, w)| ModRM:r/m (r)| NA           | NA       
| MR   | ModRM:r/m (w)   | ModRM:reg (r)| NA           | NA       
| RVM  | ModRM:reg (w)   | VEX.vvvv (r) | ModRM:r/m (r)| NA       

Description:
This instruction cannot be used for register to register or memory to memory
moves. 128-bit Legacy SSE load: Moves two packed single-precision floating-point
values from the source 64-bit memory operand and stores them in the low 64-bits
of the destination XMM register. The upper 64bits of the XMM register are preserved.
The upper 128-bits of the corresponding YMM destination register are preserved.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). VEX.128 encoded load: Loads two packed single-precision
floating-point values from the source 64-bit memory operand (third operand),
merges them with the upper 64-bits of the first source XMM register (second
operand), and stores them in the low 128-bits of the destination XMM register
(first operand). The upper 128-bits of the destination YMM register are zeroed.
128-bit store: Loads two packed single-precision floating-point values from
the low 64-bits of the XMM register source (second operand) to the 64-bit memory
location (first operand). Note: VMOVLPS (store) (VEX.128.0F 13 /r) is legal
and has the same behavior as the existing 0F 13 store. For VMOVLPS (store) (VEX.128.0F
13 /r) instruction version, VEX.vvvv is reserved and must be 1111b otherwise
instruction will #UD.

If VMOVLPS is encoded with VEX.L= 1, an attempt to execute the instruction encoded
with VEX.L= 1 will cause an #UD exception.

Operation:

MOVLPS (128-bit Legacy SSE load)
DEST[63:0] <- SRC[63:0]
DEST[VLMAX-1:64] (Unmodified)
VMOVLPS (VEX.128 encoded load)
DEST[63:0] <- SRC2[63:0]
DEST[127:64] <- SRC1[127:64]
DEST[VLMAX-1:128] <- 0
VMOVLPS (store)
DEST[63:0] <- SRC[63:0]

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVLPS:| __m128 _mm_loadl_pi ( __m128 a, __m64
|        | *p)                                  
| MOVLPS:| void _mm_storel_pi (__m64 *p, __m128 
|        | a)                                   

SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 5; additionally

| #UD| If VEX.L= 1. If VEX.vvvv != 1111B.


platform: x86
mnem: MOVMSKPD
description:
MOVMSKPD - Extract Packed Double-Precision Floating-Point Sign Mask:
| Opcode/Instruction                    | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                          
| 66 0F 50 /r MOVMSKPD reg, xmm         | RM   | V/V           | SSE2              | Extract 2-bit sign mask from xmm and 
|                                       |      |               |                   | store in reg. The upper bits of r32  
|                                       |      |               |                   | or r64 are filled with zeros.        
| VEX.128.66.0F.WIG 50 /r VMOVMSKPD reg,| RM   | V/V           | AVX               | Extract 2-bit sign mask from xmm2 and
| xmm2                                  |      |               |                   | store in reg. The upper bits of r32  
|                                       |      |               |                   | or r64 are zeroed.                   
| VEX.256.66.0F.WIG 50 /r VMOVMSKPD reg,| RM   | V/V           | AVX               | Extract 4-bit sign mask from ymm2 and
| ymm2                                  |      |               |                   | store in reg. The upper bits of r32  
|                                       |      |               |                   | or r64 are zeroed.                   

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
Extracts the sign bits from the packed double-precision floating-point values
in the source operand (second operand), formats them into a 2-bit mask, and
stores the mask in the destination operand (first operand). The source operand
is an XMM register, and the destination operand is a general-purpose register.
The mask is stored in the 2 low-order bits of the destination operand. Zero-extend
the upper bits of the destination.

In 64-bit mode, the instruction can access additional registers (XMM8-XMM15,
R8-R15) when used with a REX.R prefix. The default operand size is 64-bit in
64-bit mode. 128-bit versions: The source operand is a YMM register. The destination
operand is a general purpose register. VEX.256 encoded version: The source operand
is a YMM register. The destination operand is a general purpose register. Note:
In VEX-encoded versions, VEX.vvvv is reserved and must be 1111b, otherwise instructions
will #UD.

Operation:

(V)MOVMSKPD (128-bit versions)
DEST[0] <- SRC[63]
DEST[1] <- SRC[127]
IF DEST = r32
  THEN DEST[31:2] <- 0;
  ELSE DEST[63:2] <- 0;
FI
VMOVMSKPD (VEX.256 encoded version)
DEST[0] <- SRC[63]
DEST[1] <- SRC[127]
DEST[2] <- SRC[191]
DEST[3] <- SRC[255]
IF DEST = r32
  THEN DEST[31:4] <- 0;
  ELSE DEST[63:4] <- 0;
FI

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVMSKPD:| int _mm_movemask_pd ( __m128d a)

SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 7; additionally

| #UD| If VEX.vvvv != 1111B.


platform: x86
mnem: MOVMSKPS
description:
MOVMSKPS - Extract Packed Single-Precision Floating-Point Sign Mask:
| Opcode/Instruction                 | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                          
| 0F 50 /r MOVMSKPS reg, xmm         | RM   | V/V           | SSE               | Extract 4-bit sign mask from xmm and 
|                                    |      |               |                   | store in reg. The upper bits of r32  
|                                    |      |               |                   | or r64 are filled with zeros.        
| VEX.128.0F.WIG 50 /r VMOVMSKPS reg,| RM   | V/V           | AVX               | Extract 4-bit sign mask from xmm2 and
| xmm2                               |      |               |                   | store in reg. The upper bits of r32  
|                                    |      |               |                   | or r64 are zeroed.                   
| VEX.256.0F.WIG 50 /r VMOVMSKPS reg,| RM   | V/V           | AVX               | Extract 8-bit sign mask from ymm2 and
| ymm2                               |      |               |                   | store in reg. The upper bits of r32  
|                                    |      |               |                   | or r64 are zeroed.                   

Instruction Operand Encoding1:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
Extracts the sign bits from the packed single-precision floating-point values
in the source operand (second operand), formats them into a 4- or 8-bit mask,
and stores the mask in the destination operand (first operand). The source operand
is an XMM or YMM register, and the destination operand is a general-purpose
register. The mask is stored in the 4 or 8 low-order bits of the destination
operand. The upper bits of the destination operand beyond the mask are filled
with zeros.

In 64-bit mode, the instruction can access additional registers (XMM8-XMM15,
R8-R15) when used with a REX.R prefix. The default operand size is 64-bit in
64-bit mode.

128-bit versions: The source operand is a YMM register. The destination operand
is a general purpose register. VEX.256 encoded version: The source operand is
a YMM register. The destination operand is a general purpose register. Note:
In VEX-encoded versions, VEX.vvvv is reserved and must be 1111b, otherwise instructions
will #UD.

Operation:

DEST[0] <- SRC[31];
DEST[1] <- SRC[63];
DEST[2] <- SRC[95];
DEST[3] <- SRC[127];
IF DEST = r32
  THEN DEST[31:4] <- ZeroExtend;
  ELSE DEST[63:4] <- ZeroExtend;
FI;
1.
(V)MOVMSKPS (128-bit version)
DEST[0] <- SRC[31]
DEST[1] <- SRC[63]
DEST[2] <- SRC[95]
DEST[3] <- SRC[127]
IF DEST = r32
  THEN DEST[31:4] <- 0;
  ELSE DEST[63:4] <- 0;
FI
VMOVMSKPS (VEX.256 encoded version)
DEST[0] <- SRC[31]
DEST[1] <- SRC[63]
DEST[2] <- SRC[95]
DEST[3] <- SRC[127]
DEST[4] <- SRC[159]
DEST[5] <- SRC[191]
DEST[6] <- SRC[223]
DEST[7] <- SRC[255]
IF DEST = r32
  THEN DEST[31:8] <- 0;
  ELSE DEST[63:8] <- 0;
FI

Intel C/C++ Compiler Intrinsic Equivalent:
int _mm_movemask_ps(__m128 a) int _mm256_movemask_ps(__m256 a)


SIMD Floating-Point Exceptions:
None.


Other Exceptions:
See Exceptions Type 7; additionally

| #UD| If VEX.vvvv != 1111B.


platform: x86
mnem: MOVNTDQA
description:
MOVNTDQA  -  Load Double Quadword Non-Temporal Aligned Hint:
| Opcode/Instruction                 | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                             
| 66 0F 38 2A /r MOVNTDQA xmm1, m128 | RM   | V/V           | SSE4_1            | Move double quadword from m128 to xmm   
|                                    |      |               |                   | using non-temporal hint if WC memory    
|                                    |      |               |                   | type.                                   
| VEX.128.66.0F38.WIG 2A /r VMOVNTDQA| RM   | V/V           | AVX               | Move double quadword from m128 to xmm   
| xmm1, m128                         |      |               |                   | using non-temporal hint if WC memory    
|                                    |      |               |                   | type.                                   
| VEX.256.66.0F38.WIG 2A /r VMOVNTDQA| RM   | V/V           | AVX2              | Move 256-bit data from m256 to ymm using
| ymm1, m256                         |      |               |                   | non-temporal hint if WC memory type.    

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| RM   | ModRM:reg (w)| ModRM:r/m (r)| NA       | NA       

Description:
(V)MOVNTDQA loads a double quadword from the source operand (second operand)
to the destination operand (first operand) using a non-temporal hint. A processor
implementation may make use of the non-temporal hint associated with this instruction
if the memory source is WC (write combining) memory type. An implementation
may also make use of the non-temporal hint associated with this instruction
if the memory source is WB (write back) memory type. A processor's implementation
of the non-temporal hint does not override the effective memory type semantics,
but the implementation of the hint is processor dependent. For example, a processor
implementation may choose to ignore the hint and process the instruction as
a normal MOVDQA for any memory type. Another implementation of the hint for
WC memory type may optimize data transfer throughput of WC reads. A third implementation
may optimize cache reads generated by (V)MOVNTDQA on WB memory type to reduce
cache evictions.

WC Streaming Load Hint

For WC memory type in particular, the processor never appears to read the data
into the cache hierarchy. Instead, the non-temporal hint may be implemented
by loading a temporary internal buffer with the equivalent of an aligned cache
line without filling this data to the cache. Any memory-type aliased lines in
the cache will be snooped and flushed. Subsequent MOVNTDQA reads to unread portions
of the WC cache line will receive data from the temporary internal buffer if
data is available. The temporary internal buffer may be flushed by the processor
at any time for any reason, for example:

 - A load operation other than a (V)MOVNTDQA which references memory already resident
in a temporary internal buffer.
 - A non-WC reference to memory already resident in a temporary internal buffer.
 - Interleaving of reads and writes to memory currently residing in a single temporary
internal buffer.
 - Repeated (V)MOVNTDQA loads of a particular 16-byte item in a streaming line.
 - Certain micro-architectural conditions including resource shortages, detection
of a mis-speculation condition, and various fault conditions

The memory type of the region being read can override the non-temporal hint,
if the memory address specified for the non-temporal read is not a WC memory
region. Information on non-temporal reads and writes can be found in Chapter
11, “Memory Cache Control” of Intel® 64 and IA-32 Architectures Software Developer's
Manual, Volume 3A. Because the WC protocol uses a weakly-ordered memory consistency
model, an MFENCE or locked instruction should be used in conjunction with MOVNTDQA
instructions if multiple processors might reference the same WC memory locations
or in order to synchronize reads of a processor with writes by other agents
in the system. Because of the speculative nature of fetching due to MOVNTDQA,
Streaming loads must not be used to reference memory addresses that are mapped
to I/O devices having side effects or when reads to these devices are destruc-

tive. For additional information on MOVNTDQA usages, see Section 12.10.3 in
Chapter 12, “Programming with SSE3, SSSE3 and SSE4” of Intel® 64 and IA-32 Architectures
Software Developer's Manual, Volume 1. The 128-bit (V)MOVNTDQA addresses must
be 16-byte aligned or the instruction will cause a #GP. The 256-bit VMOVNTDQA
addresses must be 32-byte aligned or the instruction will cause a #GP. Note:
In VEX-128 encoded versions, VEX.vvvv is reserved and must be 1111b, VEX.L must
be 0; otherwise instructions will #UD.

Operation:

MOVNTDQA (128bit- Legacy SSE form)
DEST <- SRC
DEST[VLMAX-1:128] (Unmodified)
VMOVNTDQA (VEX.128 encoded form)
DEST <- SRC
DEST[VLMAX-1:128] <- 0
VMOVNTDQA (VEX.256 encoded form)
DEST[255:0] <- SRC[255:0]

Intel C/C++ Compiler Intrinsic Equivalent:
| (V)MOVNTDQA:| __m128i _mm_stream_load_si128 (__m128i 
|             | *p);                                   
| VMOVNTDQA:  | __m256i _mm256_stream_load_si256 (const
|             | __m256i *p);                           

Flags Affected:
None


Other Exceptions:
See Exceptions Type 1.SSE4.1; additionally

| #UD| If VEX.L= 1. If VEX.vvvv != 1111B.


platform: x86
mnem: MOVNTDQ
description:
MOVNTDQ - Store Double Quadword Using Non-Temporal Hint:
| Opcode/Instruction                    | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                          
| 66 0F E7 /r MOVNTDQ m128, xmm         | MR   | V/V           | SSE2              | Move double quadword from xmm to m128
|                                       |      |               |                   | using non-temporal hint.             
| VEX.128.66.0F.WIG E7 /r VMOVNTDQ m128,| MR   | V/V           | AVX               | Move packed integer values in xmm1 to
| xmm1                                  |      |               |                   | m128 using non-temporal hint.        
| VEX.256.66.0F.WIG E7 /r VMOVNTDQ m256,| MR   | V/V           | AVX               | Move packed integer values in ymm1 to
| ymm1                                  |      |               |                   | m256 using non-temporal hint.        

Instruction Operand Encoding1:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       

Description:
Moves the packed integers in the source operand (second operand) to the destination
operand (first operand) using a non-temporal hint to prevent caching of the
data during the write to memory. The source operand is an XMM register or YMM
register, which is assumed to contain integer data (packed bytes, words, doublewords,
or quadwords). The destination operand is a 128-bit or 256-bit memory location.
The memory operand must be aligned on a 16-byte (128-bit version) or 32-byte
(VEX.256 encoded version) boundary otherwise a general-protection exception
(#GP) will be generated.

The non-temporal hint is implemented by using a write combining (WC) memory
type protocol when writing the data to memory. Using this protocol, the processor
does not write the data into the cache hierarchy, nor does it fetch the corresponding
cache line from memory into the cache hierarchy. The memory type of the region
being written to can override the non-temporal hint, if the memory address specified
for the non-temporal store is in an uncacheable (UC) or write protected (WP)
memory region. For more information on non-temporal stores, see “Caching of
Temporal vs. Non-Temporal Data” in Chapter 10 in the Intel® 64 and IA-32 Architectures
Software Developer's Manual, Volume 1.

Because the WC protocol uses a weakly-ordered memory consistency model, a fencing
operation implemented with the SFENCE or MFENCE instruction should be used in
conjunction with MOVNTDQ instructions if multiple processors might use different
memory types to read/write the destination memory locations.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). Note: In VEX-128 encoded versions, VEX.vvvv is reserved
and must be 1111b, VEX.L must be 0; otherwise instructions will #UD.

Operation:

DEST <- SRC;

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVNTDQ: | void _mm_stream_si128( __m128i *p, __m128i
|          | a);                                       
| VMOVNTDQ:| void _mm256_stream_si256 (__m256i *       
|          | p, __m256i a);                            

SIMD Floating-Point Exceptions:
None.

| 1.| ModRM.MOD = 011B is not permitted

Other Exceptions:
See Exceptions Type 1.SSE2; additionally

| #UD| If VEX.vvvv != 1111B.


platform: x86
mnem: MOVNTI
description:
MOVNTI - Store Doubleword Using Non-Temporal Hint:
| Opcode          | Instruction    | Op/En| 64-Bit Mode| Compat/Leg Mode| Description                          
| 0F C3 /r        | MOVNTI m32, r32| MR   | Valid      | Valid          | Move doubleword from r32 to m32 using
|                 |                |      |            |                | nontemporal hint.                    
| REX.W + 0F C3 /r| MOVNTI m64, r64| MR   | Valid      | N.E.           | Move quadword from r64 to m64 using  
|                 |                |      |            |                | nontemporal hint.                    

Instruction Operand Encoding:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       

Description:
Moves the doubleword integer in the source operand (second operand) to the destination
operand (first operand) using a non-temporal hint to minimize cache pollution
during the write to memory. The source operand is a general-purpose register.
The destination operand is a 32-bit memory location.

The non-temporal hint is implemented by using a write combining (WC) memory
type protocol when writing the data to memory. Using this protocol, the processor
does not write the data into the cache hierarchy, nor does it fetch the corresponding
cache line from memory into the cache hierarchy. The memory type of the region
being written to can override the non-temporal hint, if the memory address specified
for the non-temporal store is in an uncacheable (UC) or write protected (WP)
memory region. For more information on non-temporal stores, see “Caching of
Temporal vs. Non-Temporal Data” in Chapter 10 in the Intel® 64 and IA-32 Architectures
Software Developer's Manual, Volume 1.

Because the WC protocol uses a weakly-ordered memory consistency model, a fencing
operation implemented with the SFENCE or MFENCE instruction should be used in
conjunction with MOVNTI instructions if multiple processors might use different
memory types to read/write the destination memory locations.

In 64-bit mode, the instruction's default operation size is 32 bits. Use of
the REX.R prefix permits access to additional registers (R8-R15). Use of the
REX.W prefix promotes operation to 64 bits. See the summary chart at the beginning
of this section for encoding data and limits.

Operation:

DEST <- SRC;

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVNTI:| void _mm_stream_si32 (int *p, int a)    
| MOVNTI:| void _mm_stream_si64(__int64 *p, __int64
|        | a)                                      

SIMD Floating-Point Exceptions:
None.


Protected Mode Exceptions:
| #GP(0)         | For an illegal memory operand effective  
|                | address in the CS, DS, ES, FS or GS      
|                | segments.                                
| #SS(0)         | For an illegal address in the SS segment.
| #PF(fault-code)| For a page fault.                        
| #UD            | If CPUID.01H:EDX.SSE2[bit 26] = 0. If    
|                | the LOCK prefix is used.                 

Real-Address Mode Exceptions:
| #GP| If a memory operand is not aligned on     
|    | a 16-byte boundary, regardless of segment.
|    | If any part of the operand lies outside   
|    | the effective address space from 0 to     
|    | FFFFH.                                    
| #UD| If CPUID.01H:EDX.SSE2[bit 26] = 0. If     
|    | the LOCK prefix is used.                  

Virtual-8086 Mode Exceptions:
Same exceptions as in real address mode.

| #PF(fault-code)| For a page fault.

Compatibility Mode Exceptions:
Same exceptions as in protected mode.


64-Bit Mode Exceptions:
| #SS(0)         | If a memory address referencing the        
|                | SS segment is in a non-canonical form.     
| #GP(0)         | If the memory address is in a non-canonical
|                | form.                                      
| #PF(fault-code)| For a page fault.                          
| #UD            | If CPUID.01H:EDX.SSE2[bit 26] = 0. If      
|                | the LOCK prefix is used.                   
| #AC(0)         | If alignment checking is enabled and       
|                | an unaligned memory reference is made      
|                | while the current privilege level is       
|                | 3.                                         


platform: x86
mnem: MOVNTPD
description:
MOVNTPD - Store Packed Double-Precision Floating-Point Values Using Non-Temporal Hint:
| Opcode/Instruction                    | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                                
| 66 0F 2B /r MOVNTPD m128, xmm         | MR   | V/V           | SSE2              | Move packed double-precision floating-point
|                                       |      |               |                   | values from xmm to m128 using nontemporal  
|                                       |      |               |                   | hint.                                      
| VEX.128.66.0F.WIG 2B /r VMOVNTPD m128,| MR   | V/V           | AVX               | Move packed double-precision values        
| xmm1                                  |      |               |                   | in xmm1 to m128 using non-temporal hint.   
| VEX.256.66.0F.WIG 2B /r VMOVNTPD m256,| MR   | V/V           | AVX               | Move packed double-precision values        
| ymm1                                  |      |               |                   | in ymm1 to m256 using non-temporal hint.   

Instruction Operand Encoding1:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       

Description:
Moves the packed double-precision floating-point values in the source operand
(second operand) to the destination operand (first operand) using a non-temporal
hint to prevent caching of the data during the write to memory. The source operand
is an XMM register or YMM register, which is assumed to contain packed double-precision,
floatingpointing data. The destination operand is a 128-bit or 256-bit memory
location. The memory operand must be aligned on a 16-byte (128-bit version)
or 32-byte (VEX.256 encoded version) boundary otherwise a generalprotection
exception (#GP) will be generated.

The non-temporal hint is implemented by using a write combining (WC) memory
type protocol when writing the data to memory. Using this protocol, the processor
does not write the data into the cache hierarchy, nor does it fetch the corresponding
cache line from memory into the cache hierarchy. The memory type of the region
being written to can override the non-temporal hint, if the memory address specified
for the non-temporal store is in an uncacheable (UC) or write protected (WP)
memory region. For more information on non-temporal stores, see “Caching of
Temporal vs. Non-Temporal Data” in Chapter 10 in the Intel® 64 and IA-32 Architectures
Software Developer's Manual, Volume 1.

Because the WC protocol uses a weakly-ordered memory consistency model, a fencing
operation implemented with the SFENCE or MFENCE instruction should be used in
conjunction with MOVNTPD instructions if multiple processors might use different
memory types to read/write the destination memory locations.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). Note: In VEX-128 encoded versions, VEX.vvvv is reserved
and must be 1111b, VEX.L must be 0; otherwise instructions will #UD.

Operation:

DEST <- SRC;

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVNTPD: | void _mm_stream_pd(double *p, __m128d     
|          | a)                                        
| VMOVNTPD:| void _mm256_stream_pd (double * p, __m256d
|          | a);                                       

SIMD Floating-Point Exceptions:
None.

| 1.| ModRM.MOD = 011B is not permitted

Other Exceptions:
See Exceptions Type 1.SSE2; additionally

| #UD| If VEX.vvvv != 1111B.


platform: x86
mnem: MOVNTPS
description:
MOVNTPS - Store Packed Single-Precision Floating-Point Values Using Non-Temporal Hint:
| Opcode/Instruction                 | Op/En| 64/32-bit Mode| CPUID Feature Flag| Description                                
| 0F 2B /r MOVNTPS m128, xmm         | MR   | V/V           | SSE               | Move packed single-precision floating-point
|                                    |      |               |                   | values from xmm to m128 using nontemporal  
|                                    |      |               |                   | hint.                                      
| VEX.128.0F.WIG 2B /r VMOVNTPS m128,| MR   | V/V           | AVX               | Move packed single-precision values        
| xmm1                               |      |               |                   | xmm1 to mem using non-temporal hint.       
| VEX.256.0F.WIG 2B /r VMOVNTPS m256,| MR   | V/V           | AVX               | Move packed single-precision values        
| ymm1                               |      |               |                   | ymm1 to mem using non-temporal hint.       

Instruction Operand Encoding1:
| Op/En| Operand 1    | Operand 2    | Operand 3| Operand 4
| MR   | ModRM:r/m (w)| ModRM:reg (r)| NA       | NA       

Description:
Moves the packed single-precision floating-point values in the source operand
(second operand) to the destination operand (first operand) using a non-temporal
hint to prevent caching of the data during the write to memory. The source operand
is an XMM register or YMM register, which is assumed to contain packed single-precision,
floatingpointing. The destination operand is a 128-bit or 256-bit memory location.
The memory operand must be aligned on a 16-byte (128-bit version) or 32-byte
(VEX.256 encoded version) boundary otherwise a general-protection exception
(#GP) will be generated.

The non-temporal hint is implemented by using a write combining (WC) memory
type protocol when writing the data to memory. Using this protocol, the processor
does not write the data into the cache hierarchy, nor does it fetch the corresponding
cache line from memory into the cache hierarchy. The memory type of the region
being written to can override the non-temporal hint, if the memory address specified
for the non-temporal store is in an uncacheable (UC) or write protected (WP)
memory region. For more information on non-temporal stores, see “Caching of
Temporal vs. Non-Temporal Data” in Chapter 10 in the Intel® 64 and IA-32 Architectures
Software Developer's Manual, Volume 1.

Because the WC protocol uses a weakly-ordered memory consistency model, a fencing
operation implemented with the SFENCE or MFENCE instruction should be used in
conjunction with MOVNTPS instructions if multiple processors might use different
memory types to read/write the destination memory locations.

In 64-bit mode, use of the REX.R prefix permits this instruction to access additional
registers (XMM8-XMM15). Note: In VEX-encoded versions, VEX.vvvv is reserved
and must be 1111b otherwise instructions will #UD.

Operation:

DEST <- SRC;

Intel C/C++ Compiler Intrinsic Equivalent:
| MOVNTDQ: | void _mm_stream_ps(float * p, __m128    
|          | a)                                      
| VMOVNTPS:| void _mm256_stream_ps (float * p, __m256
|          | a);                                     

SIMD Floating-Point Exceptions:
None.

| 1.| ModRM.MOD = 011B is not permitted

Other Exceptions:
See Exceptions Type 1.SSE; additionally

| #UD| If VEX.vvvv != 1111B.


