Intel 64 and IA-32 Architectures. Software Developer’s Manual (Collection, 2023) - page 17

 

  Index      Manuals     Intel 64 and IA-32 Architectures. Software Developer’s Manual (Collection, 2023)

 

Search            copyright infringement  

 

   

 

   

 

Content      ..     15      16      17      18     ..

 

 

 

Intel 64 and IA-32 Architectures. Software Developer’s Manual (Collection, 2023) - page 17

 

 

INSTRUCTION SET REFERENCE, A-L
from F6H to a doubleword value of FFFFFFF6H. If the value passed to the SignExtend function and the operand-
size attribute are the same size, SignExtend returns the value unaltered.
SaturateSignedWordToSignedByte - Converts a signed 16-bit value to a signed 8-bit value. If the signed
16-bit value is less than -128, it is represented by the saturated value -128 (80H); if it is greater than 127, it
is represented by the saturated value 127 (7FH).
SaturateSignedDwordToSignedWord - Converts a signed 32-bit value to a signed 16-bit value. If the
signed 32-bit value is less than -32768, it is represented by the saturated value -32768 (8000H); if it is
greater than 32767, it is represented by the saturated value 32767 (7FFFH).
SaturateSignedWordToUnsignedByte - Converts a signed 16-bit value to an unsigned 8-bit value. If the
signed 16-bit value is less than zero, it is represented by the saturated value zero (00H); if it is greater than
255, it is represented by the saturated value 255 (FFH).
SaturateToSignedByte - Represents the result of an operation as a signed 8-bit value. If the result is less
than -128, it is represented by the saturated value -128 (80H); if it is greater than 127, it is represented by
the saturated value 127 (7FH).
SaturateToSignedWord - Represents the result of an operation as a signed 16-bit value. If the result is less
than -32768, it is represented by the saturated value -32768 (8000H); if it is greater than 32767, it is
represented by the saturated value 32767 (7FFFH).
SaturateToUnsignedByte - Represents the result of an operation as a signed 8-bit value. If the result is less
than zero it is represented by the saturated value zero (00H); if it is greater than 255, it is represented by the
saturated value 255 (FFH).
SaturateToUnsignedWord - Represents the result of an operation as a signed 16-bit value. If the result is
less than zero it is represented by the saturated value zero (00H); if it is greater than 65535, it is represented
by the saturated value 65535 (FFFFH).
LowOrderWord(DEST * SRC) - Multiplies a word operand by a word operand and stores the least significant
word of the doubleword result in the destination operand.
HighOrderWord(DEST * SRC) - Multiplies a word operand by a word operand and stores the most
significant word of the doubleword result in the destination operand.
Push(value) - Pushes a value onto the stack. The number of bytes pushed is determined by the operand-size
attribute of the instruction. See the “Operation” subsection of the “PUSH-Push Word, Doubleword, or
Quadword Onto the Stack” section in Chapter 4 of the Intel® 64 and IA-32 Architectures Software Developer’s
Manual, Volume 2B.
Pop() - removes the value from the top of the stack and returns it. The statement EAX := Pop(); assigns to
EAX the 32-bit value from the top of the stack. Pop will return either a word, a doubleword or a quadword
depending on the operand-size attribute. See the “Operation” subsection in the “POP-Pop a Value From the
Stack” section of Chapter 4 of the Intel® 64 and IA-32 Architectures Software Developer’s Manual, Volume 2B.
PopRegisterStack - Marks the FPU ST(0) register as empty and increments the FPU register stack pointer
(TOP) by 1.
Switch-Tasks - Performs a task switch.
Bit(BitBase, BitOffset) - Returns the value of a bit within a bit string. The bit string is a sequence of bits in
memory or a register. Bits are numbered from low-order to high-order within registers and within memory
bytes. If the BitBase is a register, the BitOffset can be in the range 0 to [15, 31, 63] depending on the mode
and register size. See Figure 3-1: the function Bit[RAX, 21] is illustrated.
63
31
21
0
Bit Offset := 21
Figure 3-1. Bit Offset for BIT[RAX, 21]
Vol. 2A
3-11
INSTRUCTION SET REFERENCE, A-L
If BitBase is a memory address, the BitOffset has different ranges depending on the operand size (see Table
3-2).
Table 3-2. Range of Bit Positions Specified by Bit Offset Operands
Operand Size
Immediate BitOffset
Register BitOffset
16
0 to 15
- 215 to 215 - 1
32
0 to 31
- 231 to 231 - 1
64
0 to 63
- 263 to 263 - 1
The addressed bit is numbered (Offset MOD 8) within the byte at address (BitBase + (BitOffset DIV 8)) where
DIV is signed division with rounding towards negative infinity and MOD returns a positive number (see
Figure 3-2).
7
5
0 7
0
7
0
BitBase + 1
BitBase
BitBase - 1
BitOffset := +13
7
0 7
0
7
5
0
BitBase
BitBase - 1
BitBase - 2
BitOffset := -11
Figure 3-2. Memory Bit Indexing
3.1.1.10 Intel® C/C++ Compiler Intrinsics Equivalents Section
The Intel C/C++ compiler intrinsic functions give access to the full power of the Intel Architecture Instruction Set,
while allowing the compiler to optimize register allocation and instruction scheduling for faster execution. Most of
these functions are associated with a single IA instruction, although some may generate multiple instructions or
different instructions depending upon how they are used. In particular, these functions are used to invoke instruc-
tions that perform operations on vector registers that can hold multiple data elements. These SIMD instructions
use the following data types.
__m128, __m256, and __m512 can represent 4, 8, or 16 packed single precision floating-point values, and are
used with the vector registers and SSE, AVX, or AVX-512 instruction set extension families. The __m128 data
type is also used with various single precision floating-point scalar instructions that perform calculations using
only the lowest 32 bits of a vector register; the remaining bits of the result come from one of the sources or are
set to zero depending upon the instruction.
__m128d, __m256d, and __m512d can represent 2, 4, or 8 packed double precision floating-point values, and
are used with the vector registers and SSE, AVX, or AVX-512 instruction set extension families. The __m128d
data type is also used with various double precision floating-point scalar instructions that perform calculations
using only the lowest 64 bits of a vector register; the remaining bits of the result come from one of the sources
or are set to zero depending upon the instruction.
__m128i, __m256i, and __m512i can represent integer data in bytes, words, doublewords, quadwords, and
occasionally larger data types.
3-12
Vol. 2A
INSTRUCTION SET REFERENCE, A-L
Each of these data types incorporates in its name the number of bits it can hold. For example, the __m128 type
holds 128 bits, and because each single precision floating-point value is 32 bits long the __m128 type holds
(128/32) or four values. Normally the compiler will allocate memory for these data types on an even multiple of the
size of the type. Such aligned memory locations may be faster to read and write than locations at other addresses.
These SIMD data types are not basic Standard C data types or C++ objects, so they may be used only with the
assignment operator, passed as function arguments, and returned from a function call. If you access the internal
members of these types directly, or indirectly by using them in a union, there may be side effects affecting optimi-
zation, so it is recommended to use them only with the SIMD instruction intrinsic functions described in this manual
or the Intel C/C++ compiler documentation.
Many intrinsic functions names are prefixed with an indicator of the vector length and suffixed by an indicator of
the vector element data type, although some functions do not follow the rules below. The prefixes are:
_mm_ indicates that the function operates on 128-bit (or sometimes 64-bit) vectors.
_mm256_ indicates the function operates on 256-bit vectors.
_mm512_ indicates that the function operates on 512-bit vectors.
The suffixes include:
_ps, which indicates a function that operates on packed single precision floating-point data. Packed single
precision floating-point data corresponds to arrays of the C/C++ type float with either 4, 8 or 16 elements.
Values of this type can be loaded from an array using the _mm_loadu_ps, _mm256_loadu_ps, or
_mm512_loadu_ps functions, or created from individual values using _mm_set_ps, _mm256_set_ps, or
_mm512_set_ps functions, and they can be stored in an array using _mm_storeu_ps, _mm256_storeu_ps, or
_mm512_storeu_ps.
_ss, which indicates a function that operates on scalar single precision floating-point data. Single precision
floating-point data corresponds to the C/C++ type float, and values of type float can be converted to type
__m128 for use with these functions using the _mm_set_ss function, and converted back using the
_mm_cvtss_f32 function. When used with functions that operate on packed single precision floating-point data
the scalar element corresponds with the first packed value.
_pd, which indicates a function that operates on packed double precision floating-point data. Packed double
precision floating-point data corresponds to arrays of the C/C++ type double with either 2, 4, or 8 elements.
Values of this type can be loaded from an array using the _mm_loadu_pd, _mm256_loadu_pd, or
_mm512_loadu_pd functions, or created from individual values using _mm_set_pd, _mm2566_set_pd, or
_mm512_set_pd functions, and they can be stored in an array using _mm_storeu_pd, _mm256_storeu_pd, or
_mm512_storeu_pd.
_sd, which indicates a function that operates on scalar double precision floating-point data. Double-precision
floating-point data corresponds to the C/C++ type double, and values of type double can be converted to type
__m128d for use with these functions using the _mm_set_sd function, and converted back using the
_mm_cvtsd_f64 function. When used with functions that operate on packed double precision floating-point
data the scalar element corresponds with the first packed value.
_epi8, which indicates a function that operates on packed 8-bit signed integer values. Packed 8-bit signed
integers correspond to an array of signed char with 16, 32 or 64 elements. Values of this type can be created
from individual elements using _mm_set_epi8, _mm256_set_epi8, or _mm512_set_epi8 functions.
_epi16, which indicates a function that operates on packed 16-bit signed integer values. Packed 16-bit signed
integers correspond to an array of short with 8, 16 or 32 elements. Values of this type can be created from
individual elements using _mm_set_epi16, _mm256_set_epi16, or _mm512_set_epi16 functions.
_epi32, which indicates a function that operates on packed 32-bit signed integer values. Packed 32-bit signed
integers correspond to an array of int with 4, 8 or 16 elements. Values of this type can be created from
individual elements using _mm_set_epi32, _mm256_set_epi32, or _mm512_set_epi32 functions.
_epi64, which indicates a function that operates on packed 64-bit signed integer values. Packed 64-bit signed
integers correspond to an array of long long (or long if it is a 64-bit data type) with 2, 4 or 8 elements. Values
of this type can be created from individual elements using _mm_set_epi32, _mm256_set_epi32, or
_mm512_set_epi32 functions.
_epu8, which indicates a function that operates on packed 8-bit unsigned integer values. Packed 8-bit unsigned
integers correspond to an array of unsigned char with 16, 32 or 64 elements.
Vol. 2A
3-13
INSTRUCTION SET REFERENCE, A-L
_epu16, which indicates a function that operates on packed 16-bit unsigned integer values. Packed 16-bit
unsigned integers correspond to an array of unsigned short with 8, 16 or 32 elements.
_epu32, which indicates a function that operates on packed 32-bit unsigned integer values. Packed 32-bit
unsigned integers correspond to an array of unsigned with 4, 8 or 16 elements.
_epu64, which indicates a function that operates on packed 64-bit unsigned integer values. Packed 64-bit
unsigned integers correspond to an array of unsigned long long (or unsigned long if it is a 64-bit data type) with
2, 4 or 8 elements.
_si128, which indicates a function that operates on a single 128-bit value of type __m128i.
_si256, which indicates a function that operates on a single a 256-bit value of type __m256i.
_si512, which indicates a function that operates on a single a 512-bit value of type __m512i.
Values of any packed integer type can be loaded from an array using the _mm_loadu_si128,
_mm256_loadu_si256, or _mm512_loadu_si512 functions, and they can be stored in an array using
_mm_storeu_si128, _mm256_storeu_si256, or _mm512_storeu_si512.
These functions and data types are used with the SSE, AVX, and AVX-512 instruction set extension families. In
addition there are similar functions that correspond to MMX instructions. These are less frequently used because
they require additional state management, and only operate on 64-bit packed integer values.
The declarations of Intel C/C++ compiler intrinsic functions may reference some non-standard data types, such as
__int64. The C Standard header stdint.h defines similar platform-independent types, and the documentation for
that header gives characteristics that apply to corresponding non-standard types according to the following table.
Table 3-3. Standard and Non-Standard Data Types
Non-standard Type
Standard Type (from stdint.h)
__int64
int64_t
unsigned __int64
uint64_t
__int32
int32_t
unsigned __int32
uint32_t
__int16
int16_t
unsigned __int16
uint16_t
For a more detailed description of each intrinsic function and additional information related to its usage, refer to the
online Intel Intrinsics Guide, https://software.intel.com/sites/landingpage/IntrinsicsGuide.
3.1.1.11 Flags Affected Section
The “Flags Affected” section lists the flags in the EFLAGS register that are affected by the instruction. When a flag
is cleared, it is equal to 0; when it is set, it is equal to 1. The arithmetic and logical instructions usually assign values
to the status flags in a uniform manner (see Appendix A, “EFLAGS Cross-Reference,” in the Intel® 64 and IA-32
Architectures Software Developer’s Manual, Volume 1). Non-conventional assignments are described in the “Oper-
ation” section. The values of flags listed as undefined may be changed by the instruction in an indeterminate
manner. Flags that are not listed are unchanged by the instruction.
3.1.1.12 FPU Flags Affected Section
The floating-point instructions have an “FPU Flags Affected” section that describes how each instruction can affect
the four condition code flags of the FPU status word.
3.1.1.13 Protected Mode Exceptions Section
The “Protected Mode Exceptions” section lists the exceptions that can occur when the instruction is executed in
protected mode and the reasons for the exceptions. Each exception is given a mnemonic that consists of a pound
3-14
Vol. 2A
INSTRUCTION SET REFERENCE, A-L
sign (#) followed by two letters and an optional error code in parentheses. For example, #GP(0) denotes a general
protection exception with an error code of 0. Table 3-4 associates each two-letter mnemonic with the corre-
sponding exception vector and name. See Chapter 6, “Procedure Calls, Interrupts, and Exceptions,” in the Intel®
64 and IA-32 Architectures Software Developer’s Manual, Volume 3A, for a detailed description of the exceptions.
Application programmers should consult the documentation provided with their operating systems to determine
the actions taken when exceptions occur.
Table 3-4. Intel 64 and IA-32 General Exceptions
Vector
Name
Source
Protected
Real
Virtual
Mode1
Address
8086
Mode
Mode
0
#DE-Divide Error
DIV and IDIV instructions.
Yes
Yes
Yes
1
#DB-Debug
Any code or data reference.
Yes
Yes
Yes
3
#BP-Breakpoint
INT3 instruction.
Yes
Yes
Yes
4
#OF-Overflow
INTO instruction.
Yes
Yes
Yes
5
#BR-BOUND Range Exceeded
BOUND instruction.
Yes
Yes
Yes
6
#UD-Invalid Opcode (Undefined
UD instruction or reserved opcode.
Yes
Yes
Yes
Opcode)
7
#NM-Device Not Available (No
Floating-point or WAIT/FWAIT instruction.
Yes
Yes
Yes
Math Coprocessor)
8
#DF-Double Fault
Any instruction that can generate an
Yes
Yes
Yes
exception, an NMI, or an INTR.
10
#TS-Invalid TSS
Task switch or TSS access.
Yes
Reserved
Yes
11
#NP-Segment Not Present
Loading segment registers or accessing system
Yes
Reserved
Yes
segments.
12
#SS-Stack Segment Fault
Stack operations and SS register loads.
Yes
Yes
Yes
13
#GP-General Protection2
Any memory reference and other protection
Yes
Yes
Yes
checks.
14
#PF-Page Fault
Any memory reference.
Yes
Reserved
Yes
16
#MF-Floating-Point Error (Math
Floating-point or WAIT/FWAIT instruction.
Yes
Yes
Yes
Fault)
17
#AC-Alignment Check
Any data reference in memory.
Yes
Reserved
Yes
18
#MC-Machine Check
Model dependent machine check errors.
Yes
Yes
Yes
19
#XM-SIMD Floating-Point
SSE/SSE2/SSE3 floating-point instructions.
Yes
Yes
Yes
Numeric Error
NOTES:
1. Apply to protected mode, compatibility mode, and 64-bit mode.
2. In the real-address mode, vector 13 is the segment overrun exception.
3.1.1.14 Real-Address Mode Exceptions Section
The “Real-Address Mode Exceptions” section lists the exceptions that can occur when the instruction is executed in
real-address mode (see Table 3-4).
3.1.1.15 Virtual-8086 Mode Exceptions Section
The “Virtual-8086 Mode Exceptions” section lists the exceptions that can occur when the instruction is executed in
virtual-8086 mode (see Table 3-4).
Vol. 2A
3-15
INSTRUCTION SET REFERENCE, A-L
3.1.1.16 Floating-Point Exceptions Section
The “Floating-Point Exceptions” section lists exceptions that can occur when an x87 FPU floating-point instruction
is executed. All of these exception conditions result in a floating-point error exception (#MF, exception 16) being
generated. Table 3-5 associates a one- or two-letter mnemonic with the corresponding exception name. See
“Floating-Point Exception Conditions” in Chapter 8 of the Intel® 64 and IA-32 Architectures Software Developer’s
Manual, Volume 1, for a detailed description of these exceptions.
Table 3-5. x87 FPU Floating-Point Exceptions
Mnemonic
Name
Source
Floating-point invalid operation:
#IS
- Stack overflow or underflow
- x87 FPU stack overflow or underflow
#IA
- Invalid arithmetic operation
- Invalid FPU arithmetic operation
#Z
Floating-point divide-by-zero
Divide-by-zero
#D
Floating-point denormal operand
Source operand that is a denormal number
#O
Floating-point numeric overflow
Overflow in result
#U
Floating-point numeric underflow
Underflow in result
#P
Floating-point inexact result (precision)
Inexact result (precision)
3.1.1.17 SIMD Floating-Point Exceptions Section
The “SIMD Floating-Point Exceptions” section lists exceptions that can occur when an SSE/SSE2/SSE3 floating-
point instruction is executed. All of these exception conditions result in a SIMD floating-point error exception (#XM,
exception 19) being generated. Table 3-6 associates a one-letter mnemonic with the corresponding exception
name. For a detailed description of these exceptions, refer to ”SSE and SSE2 Exceptions”, in Chapter 11 of the
Intel® 64 and IA-32 Architectures Software Developer’s Manual, Volume 1.
Table 3-6. SIMD Floating-Point Exceptions
Mnemonic
Name
Source
#I
Floating-point invalid operation
Invalid arithmetic operation or source operand
#Z
Floating-point divide-by-zero
Divide-by-zero
#D
Floating-point denormal operand
Source operand that is a denormal number
#O
Floating-point numeric overflow
Overflow in result
#U
Floating-point numeric underflow
Underflow in result
#P
Floating-point inexact result
Inexact result (precision)
3.1.1.18 Compatibility Mode Exceptions Section
This section lists exceptions that occur within compatibility mode.
3.1.1.19
64-Bit Mode Exceptions Section
This section lists exceptions that occur within 64-bit mode.
3.2
INTEL® AMX CONSIDERATIONS
The following implementation parameters and helper functions are applicable to the Intel® AMX instructions.
3-16
Vol. 2A
INSTRUCTION SET REFERENCE, A-L
3.2.1
Implementation Parameters
The parameters are reported via CPUID leaf 1DH. Index 0 reports all zeros for all fields.
define palette_table[id]:
uint16_t total_tile_bytes
uint16_t bytes_per_tile
uint16_t bytes_per_row
uint16_t max_names
uint16_t max_rows
The tile parameters are set by LDTILECFG or XRSTOR* of TILECFG:
define tile[tid]:
byte rows
word colsb // bytes_per_row
bool valid
3.2.2
Helper Functions
The helper functions used in Intel AMX instructions are defined below.
define write_row_and_zero(treg, r, data, nbytes):
for j in 0 ... nbytes-1:
treg.row[r].byte[j] := data.byte[j]
// zero the rest of the row
for j in nbytes ... palette_table[tilecfg.palette_id].bytes_per_row-1:
treg.row[r].byte[j] := 0
define zero_upper_rows(treg, r):
for i in r ... palette_table[tilecfg.palette_id].max_rows-1:
for j in 0 ... palette_table[tilecfg.palette_id].bytes_per_row-1:
treg.row[i].byte[j] := 0
define zero_tilecfg_start():
tilecfg.start_row := 0
define zero_all_tile_data():
if XCR0[TILEDATA]:
b := CPUID(0xD,TILEDATA).EAX // size of feature
for j in 0 ... b:
TILEDATA.byte[j] := 0
Vol. 2A
3-17
INSTRUCTION SET REFERENCE, A-L
define xcr0_supports_palette(palette_id):
if palette_id == 0:
return 1
elif palette_id == 1:
if XCR0[TILECFG] and XCR0[TILEDATA]:
return 1
return 0
3.3
INSTRUCTIONS (A-L)
The remainder of this chapter provides descriptions of Intel 64 and IA-32 instructions (A-L). See also: Chapter 4,
“Instruction Set Reference, M-U,” in the Intel® 64 and IA-32 Architectures Software Developer’s Manual, Volume
2B; Chapter 5, “Instruction Set Reference, V,” in the Intel® 64 and IA-32 Architectures Software Developer’s
Manual, Volume 2C; and Chapter 6, “Instruction Set Reference, W-Z,” in the Intel® 64 and IA-32 Architectures
Software Developer’s Manual, Volume 2D.
3-18
Vol. 2A
INSTRUCTION SET REFERENCE, A-L
AAA-ASCII Adjust After Addition
Opcode
Instruction
Op/
64-bit
Compat/
Description
En
Mode
Leg Mode
37
AAA
ZO
Invalid
Valid
ASCII adjust AL after addition.
Instruction Operand Encoding
Op/En
Operand 1
Operand 2
Operand 3
Operand 4
ZO
N/A
N/A
N/A
N/A
Description
Adjusts the sum of two unpacked BCD values to create an unpacked BCD result. The AL register is the implied
source and destination operand for this instruction. The AAA instruction is only useful when it follows an ADD
instruction that adds (binary addition) two unpacked BCD values and stores a byte result in the AL register. The
AAA instruction then adjusts the contents of the AL register to contain the correct 1-digit unpacked BCD result.
If the addition produces a decimal carry, the AH register increments by 1, and the CF and AF flags are set. If there
was no decimal carry, the CF and AF flags are cleared and the AH register is unchanged. In either case, bits 4
through 7 of the AL register are set to 0.
This instruction executes as described in compatibility mode and legacy mode. It is not valid in 64-bit mode.
Operation
IF 64-Bit Mode
THEN
#UD;
ELSE
IF ((AL AND 0FH) > 9) or (AF = 1)
THEN
AX := AX + 106H;
AF := 1;
CF := 1;
ELSE
AF := 0;
CF := 0;
FI;
AL := AL AND 0FH;
FI;
Flags Affected
The AF and CF flags are set to 1 if the adjustment results in a decimal carry; otherwise they are set to 0. The OF,
SF, ZF, and PF flags are undefined.
Protected Mode Exceptions
#UD
If the LOCK prefix is used.
Real-Address Mode Exceptions
Same exceptions as protected mode.
Virtual-8086 Mode Exceptions
Same exceptions as protected mode.
AAA-ASCII Adjust After Addition
Vol. 2A
3-19
INSTRUCTION SET REFERENCE, A-L
Compatibility Mode Exceptions
Same exceptions as protected mode.
64-Bit Mode Exceptions
#UD
If in 64-bit mode.
3-20
Vol. 2A
AAA-ASCII Adjust After Addition
INSTRUCTION SET REFERENCE, A-L
AAD-ASCII Adjust AX Before Division
Opcode
Instruction
Op/
64-bit
Compat/
Description
En
Mode
Leg Mode
D5 0A
AAD
ZO
Invalid
Valid
ASCII adjust AX before division.
D5 ib
AAD imm8
ZO
Invalid
Valid
Adjust AX before division to number base
imm8.
Instruction Operand Encoding
Op/En
Operand 1
Operand 2
Operand 3
Operand 4
ZO
N/A
N/A
N/A
N/A
Description
Adjusts two unpacked BCD digits (the least-significant digit in the AL register and the most-significant digit in the
AH register) so that a division operation performed on the result will yield a correct unpacked BCD value. The AAD
instruction is only useful when it precedes a DIV instruction that divides (binary division) the adjusted value in the
AX register by an unpacked BCD value.
The AAD instruction sets the value in the AL register to (AL + (10 * AH)), and then clears the AH register to 00H.
The value in the AX register is then equal to the binary equivalent of the original unpacked two-digit (base 10)
number in registers AH and AL.
The generalized version of this instruction allows adjustment of two unpacked digits of any number base (see the
“Operation” section below), by setting the imm8 byte to the selected number base (for example, 08H for octal, 0AH
for decimal, or 0CH for base 12 numbers). The AAD mnemonic is interpreted by all assemblers to mean adjust
ASCII (base 10) values. To adjust values in another number base, the instruction must be hand coded in machine
code (D5 imm8).
This instruction executes as described in compatibility mode and legacy mode. It is not valid in 64-bit mode.
Operation
IF 64-Bit Mode
THEN
#UD;
ELSE
tempAL := AL;
tempAH := AH;
AL := (tempAL + (tempAH ∗ imm8)) AND FFH;
(* imm8 is set to 0AH for the AAD mnemonic.*)
AH := 0;
FI;
The immediate value (imm8) is taken from the second byte of the instruction.
Flags Affected
The SF, ZF, and PF flags are set according to the resulting binary value in the AL register; the OF, AF, and CF flags
are undefined.
Protected Mode Exceptions
#UD
If the LOCK prefix is used.
Real-Address Mode Exceptions
Same exceptions as protected mode.
Virtual-8086 Mode Exceptions
Same exceptions as protected mode.
AAD-ASCII Adjust AX Before Division
Vol. 2A
3-21
INSTRUCTION SET REFERENCE, A-L
Compatibility Mode Exceptions
Same exceptions as protected mode.
64-Bit Mode Exceptions
#UD
If in 64-bit mode.
3-22
Vol. 2A
AAD-ASCII Adjust AX Before Division
INSTRUCTION SET REFERENCE, A-L
AAM-ASCII Adjust AX After Multiply
Opcode
Instruction
Op/
64-bit
Compat/
Description
En
Mode
Leg Mode
D4 0A
AAM
ZO
Invalid
Valid
ASCII adjust AX after multiply.
D4 ib
AAM imm8
ZO
Invalid
Valid
Adjust AX after multiply to number base
imm8.
Instruction Operand Encoding
Op/En
Operand 1
Operand 2
Operand 3
Operand 4
ZO
N/A
N/A
N/A
N/A
Description
Adjusts the result of the multiplication of two unpacked BCD values to create a pair of unpacked (base 10) BCD
values. The AX register is the implied source and destination operand for this instruction. The AAM instruction is
only useful when it follows an MUL instruction that multiplies (binary multiplication) two unpacked BCD values and
stores a word result in the AX register. The AAM instruction then adjusts the contents of the AX register to contain
the correct 2-digit unpacked (base 10) BCD result.
The generalized version of this instruction allows adjustment of the contents of the AX to create two unpacked
digits of any number base (see the “Operation” section below). Here, the imm8 byte is set to the selected number
base (for example, 08H for octal, 0AH for decimal, or 0CH for base 12 numbers). The AAM mnemonic is interpreted
by all assemblers to mean adjust to ASCII (base 10) values. To adjust to values in another number base, the
instruction must be hand coded in machine code (D4 imm8).
This instruction executes as described in compatibility mode and legacy mode. It is not valid in 64-bit mode.
Operation
IF 64-Bit Mode
THEN
#UD;
ELSE
tempAL := AL;
AH := tempAL / imm8; (* imm8 is set to 0AH for the AAM mnemonic *)
AL := tempAL MOD imm8;
FI;
The immediate value (imm8) is taken from the second byte of the instruction.
Flags Affected
The SF, ZF, and PF flags are set according to the resulting binary value in the AL register. The OF, AF, and CF flags
are undefined.
Protected Mode Exceptions
#DE
If an immediate value of 0 is used.
#UD
If the LOCK prefix is used.
Real-Address Mode Exceptions
Same exceptions as protected mode.
Virtual-8086 Mode Exceptions
Same exceptions as protected mode.
AAM-ASCII Adjust AX After Multiply
Vol. 2A
3-23
INSTRUCTION SET REFERENCE, A-L
Compatibility Mode Exceptions
Same exceptions as protected mode.
64-Bit Mode Exceptions
#UD
If in 64-bit mode.
3-24
Vol. 2A
AAM-ASCII Adjust AX After Multiply
INSTRUCTION SET REFERENCE, A-L
AAS-ASCII Adjust AL After Subtraction
Opcode
Instruction
Op/
64-bit
Compat/
Description
En
Mode
Leg Mode
3F
AAS
ZO
Invalid
Valid
ASCII adjust AL after subtraction.
Instruction Operand Encoding
Op/En
Operand 1
Operand 2
Operand 3
Operand 4
ZO
N/A
N/A
N/A
N/A
Description
Adjusts the result of the subtraction of two unpacked BCD values to create a unpacked BCD result. The AL register
is the implied source and destination operand for this instruction. The AAS instruction is only useful when it follows
a SUB instruction that subtracts (binary subtraction) one unpacked BCD value from another and stores a byte
result in the AL register. The AAA instruction then adjusts the contents of the AL register to contain the correct 1-
digit unpacked BCD result.
If the subtraction produced a decimal carry, the AH register decrements by 1, and the CF and AF flags are set. If no
decimal carry occurred, the CF and AF flags are cleared, and the AH register is unchanged. In either case, the AL
register is left with its top four bits set to 0.
This instruction executes as described in compatibility mode and legacy mode. It is not valid in 64-bit mode.
Operation
IF 64-bit mode
THEN
#UD;
ELSE
IF ((AL AND 0FH) > 9) or (AF = 1)
THEN
AX := AX - 6;
AH := AH - 1;
AF := 1;
CF := 1;
AL := AL AND 0FH;
ELSE
CF := 0;
AF := 0;
AL := AL AND 0FH;
FI;
FI;
Flags Affected
The AF and CF flags are set to 1 if there is a decimal borrow; otherwise, they are cleared to 0. The OF, SF, ZF, and
PF flags are undefined.
Protected Mode Exceptions
#UD
If the LOCK prefix is used.
Real-Address Mode Exceptions
Same exceptions as protected mode.
Virtual-8086 Mode Exceptions
Same exceptions as protected mode.
AAS-ASCII Adjust AL After Subtraction
Vol. 2A
3-25
INSTRUCTION SET REFERENCE, A-L
Compatibility Mode Exceptions
Same exceptions as protected mode.
64-Bit Mode Exceptions
#UD
If in 64-bit mode.
3-26
Vol. 2A
AAS-ASCII Adjust AL After Subtraction
INSTRUCTION SET REFERENCE, A-L
ADC-Add With Carry
Opcode
Instruction
Op/
64-bit
Compat/
Description
En
Mode
Leg Mode
14 ib
ADC AL, imm8
I
Valid
Valid
Add with carry imm8 to AL.
15 iw
ADC AX, imm16
I
Valid
Valid
Add with carry imm16 to AX.
15 id
ADC EAX, imm32
I
Valid
Valid
Add with carry imm32 to EAX.
REX.W + 15 id
ADC RAX, imm32
I
Valid
N.E.
Add with carry imm32 sign extended to 64-
bits to RAX.
80 /2 ib
ADC r/m8, imm8
MI
Valid
Valid
Add with carry imm8 to r/m8.
REX + 80 /2 ib
ADC r/m8*, imm8
MI
Valid
N.E.
Add with carry imm8 to r/m8.
81 /2 iw
ADC r/m16, imm16
MI
Valid
Valid
Add with carry imm16 to r/m16.
81 /2 id
ADC r/m32, imm32
MI
Valid
Valid
Add with CF imm32 to r/m32.
REX.W + 81 /2 id
ADC r/m64, imm32
MI
Valid
N.E.
Add with CF imm32 sign extended to 64-bits
to r/m64.
83 /2 ib
ADC r/m16, imm8
MI
Valid
Valid
Add with CF sign-extended imm8 to r/m16.
83 /2 ib
ADC r/m32, imm8
MI
Valid
Valid
Add with CF sign-extended imm8 into r/m32.
REX.W + 83 /2 ib
ADC r/m64, imm8
MI
Valid
N.E.
Add with CF sign-extended imm8 into r/m64.
10 /r
ADC r/m8, r8
MR
Valid
Valid
Add with carry byte register to r/m8.
REX + 10 /r
ADC r/m8*, r8*
MR
Valid
N.E.
Add with carry byte register to r/m64.
11 /r
ADC r/m16, r16
MR
Valid
Valid
Add with carry r16 to r/m16.
11 /r
ADC r/m32, r32
MR
Valid
Valid
Add with CF r32 to r/m32.
REX.W + 11 /r
ADC r/m64, r64
MR
Valid
N.E.
Add with CF r64 to r/m64.
12 /r
ADC r8, r/m8
RM
Valid
Valid
Add with carry r/m8 to byte register.
REX + 12 /r
ADC r8*, r/m8*
RM
Valid
N.E.
Add with carry r/m64 to byte register.
13 /r
ADC r16, r/m16
RM
Valid
Valid
Add with carry r/m16 to r16.
13 /r
ADC r32, r/m32
RM
Valid
Valid
Add with CF r/m32 to r32.
REX.W + 13 /r
ADC r64, r/m64
RM
Valid
N.E.
Add with CF r/m64 to r64.
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
RM
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
MR
ModRM:r/m (r, w)
ModRM:reg (r)
N/A
N/A
MI
ModRM:r/m (r, w)
imm8/16/32
N/A
N/A
I
AL/AX/EAX/RAX
imm8/16/32
N/A
N/A
Description
Adds the destination operand (first operand), the source operand (second operand), and the carry (CF) flag and
stores the result in the destination operand. The destination operand can be a register or a memory location; the
source operand can be an immediate, a register, or a memory location. (However, two memory operands cannot be
used in one instruction.) The state of the CF flag represents a carry from a previous addition. When an immediate
value is used as an operand, it is sign-extended to the length of the destination operand format.
ADC-Add With Carry
Vol. 2A
3-27
INSTRUCTION SET REFERENCE, A-L
The ADC instruction does not distinguish between signed or unsigned operands. Instead, the processor evaluates
the result for both data types and sets the OF and CF flags to indicate a carry in the signed or unsigned result,
respectively. The SF flag indicates the sign of the signed result.
The ADC instruction is usually executed as part of a multibyte or multiword addition in which an ADD instruction is
followed by an ADC instruction.
This instruction can be used with a LOCK prefix to allow the instruction to be executed atomically.
In 64-bit mode, the instruction’s default operation size is 32 bits. Using a REX prefix in the form of REX.R permits
access to additional registers (R8-R15). Using a REX prefix in the form of REX.W promotes operation to 64 bits. See
the summary chart at the beginning of this section for encoding data and limits.
Operation
DEST := DEST + SRC + CF;
Intel C/C++ Compiler Intrinsic Equivalent
ADC extern unsigned char _addcarry_u8(unsigned char c_in, unsigned char src1, unsigned char src2, unsigned char *sum_out);
ADC extern unsigned char _addcarry_u16(unsigned char c_in, unsigned short src1, unsigned short src2, unsigned short *sum_out);
ADC extern unsigned char _addcarry_u32(unsigned char c_in, unsigned int src1, unsigned char int, unsigned int *sum_out);
ADC extern unsigned char _addcarry_u64(unsigned char c_in, unsigned __int64 src1, unsigned __int64 src2, unsigned __int64
*sum_out);
Flags Affected
The OF, SF, ZF, AF, CF, and PF flags are set according to the result.
Protected Mode Exceptions
#GP(0)
If the destination 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 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 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.
3-28
Vol. 2A
ADC-Add With Carry
INSTRUCTION SET REFERENCE, A-L
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.
ADC-Add With Carry
Vol. 2A
3-29
INSTRUCTION SET REFERENCE, A-L
ADCX-Unsigned Integer Addition of Two Operands With Carry Flag
Opcode/
Op/
64/32bit
CPUID
Description
Instruction
En
Mode
Feature
Support
Flag
66 0F 38 F6 /r
RM
V/V
ADX
Unsigned addition of r32 with CF, r/m32 to r32, writes CF.
ADCX r32, r/m32
66 REX.w 0F 38 F6 /r
RM
V/NE
ADX
Unsigned addition of r64 with CF, r/m64 to r64, writes CF.
ADCX r64, r/m64
Instruction Operand Encoding
Op/En
Operand 1
Operand 2
Operand 3
Operand 4
RM
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
Description
Performs an unsigned addition of the destination operand (first operand), the source operand (second operand)
and the carry-flag (CF) and stores the result in the destination operand. The destination operand is a general-
purpose register, whereas the source operand can be a general-purpose register or memory location. The state of
CF can represent a carry from a previous addition. The instruction sets the CF flag with the carry generated by the
unsigned addition of the operands.
The ADCX instruction is executed in the context of multi-precision addition, where we add a series of operands with
a carry-chain. At the beginning of a chain of additions, we need to make sure the CF is in a desired initial state.
Often, this initial state needs to be 0, which can be achieved with an instruction to zero the CF (e.g. XOR).
This instruction is supported in real mode and virtual-8086 mode. The operand size is always 32 bits if not in 64-bit
mode.
In 64-bit mode, the default operation size is 32 bits. Using a REX Prefix in the form of REX.R permits access to addi-
tional registers (R8-15). Using REX Prefix in the form of REX.W promotes operation to 64 bits.
ADCX executes normally either inside or outside a transaction region.
Note: ADCX defines the OF flag differently than the ADD/ADC instructions as defined in the Intel® 64 and IA-32
Architectures Software Developer’s Manual, Volume 2A.
Operation
IF OperandSize is 64-bit
THEN CF:DEST[63:0] := DEST[63:0] + SRC[63:0] + CF;
ELSE CF:DEST[31:0] := DEST[31:0] + SRC[31:0] + CF;
FI;
Flags Affected
CF is updated based on result. OF, SF, ZF, AF, and PF flags are unmodified.
Intel C/C++ Compiler Intrinsic Equivalent
unsigned char _addcarryx_u32 (unsigned char c_in, unsigned int src1, unsigned int src2, unsigned int *sum_out);
unsigned char _addcarryx_u64 (unsigned char c_in, unsigned __int64 src1, unsigned __int64 src2, unsigned __int64 *sum_out);
SIMD Floating-Point Exceptions
None.
3-30
Vol. 2A
ADCX-Unsigned Integer Addition of Two Operands With Carry Flag
INSTRUCTION SET REFERENCE, A-L
Protected Mode Exceptions
#UD
If the LOCK prefix is used.
If CPUID.(EAX=07H, ECX=0H):EBX.ADX[bit 19] = 0.
#SS(0)
For an illegal address in the SS segment.
#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.
#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
#UD
If the LOCK prefix is used.
If CPUID.(EAX=07H, ECX=0H):EBX.ADX[bit 19] = 0.
#SS(0)
For an illegal address in the SS segment.
#GP(0)
If any part of the operand lies outside the effective address space from 0 to FFFFH.
Virtual-8086 Mode Exceptions
#UD
If the LOCK prefix is used.
If CPUID.(EAX=07H, ECX=0H):EBX.ADX[bit 19] = 0.
#SS(0)
For an illegal address in the SS segment.
#GP(0)
If any part of the operand lies outside the effective address space from 0 to FFFFH.
#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
#UD
If the LOCK prefix is used.
If CPUID.(EAX=07H, ECX=0H):EBX.ADX[bit 19] = 0.
#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.
#AC(0)
If alignment checking is enabled and an unaligned memory reference is made while the
current privilege level is 3.
ADCX-Unsigned Integer Addition of Two Operands With Carry Flag
Vol. 2A
3-31
INSTRUCTION SET REFERENCE, A-L
ADD-Add
Opcode
Instruction
Op/
64-bit
Compat/
Description
En
Mode
Leg Mode
04 ib
ADD AL, imm8
I
Valid
Valid
Add imm8 to AL.
05 iw
ADD AX, imm16
I
Valid
Valid
Add imm16 to AX.
05 id
ADD EAX, imm32
I
Valid
Valid
Add imm32 to EAX.
REX.W + 05 id
ADD RAX, imm32
I
Valid
N.E.
Add imm32 sign-extended to 64-bits to RAX.
80 /0 ib
ADD r/m8, imm8
MI
Valid
Valid
Add imm8 to r/m8.
REX + 80 /0 ib
ADD r/m8*, imm8
MI
Valid
N.E.
Add sign-extended imm8 to r/m8.
81 /0 iw
ADD r/m16, imm16
MI
Valid
Valid
Add imm16 to r/m16.
81 /0 id
ADD r/m32, imm32
MI
Valid
Valid
Add imm32 to r/m32.
REX.W + 81 /0 id
ADD r/m64, imm32
MI
Valid
N.E.
Add imm32 sign-extended to 64-bits to
r/m64.
83 /0 ib
ADD r/m16, imm8
MI
Valid
Valid
Add sign-extended imm8 to r/m16.
83 /0 ib
ADD r/m32, imm8
MI
Valid
Valid
Add sign-extended imm8 to r/m32.
REX.W + 83 /0 ib
ADD r/m64, imm8
MI
Valid
N.E.
Add sign-extended imm8 to r/m64.
00 /r
ADD r/m8, r8
MR
Valid
Valid
Add r8 to r/m8.
REX + 00 /r
ADD r/m8*, r8*
MR
Valid
N.E.
Add r8 to r/m8.
01 /r
ADD r/m16, r16
MR
Valid
Valid
Add r16 to r/m16.
01 /r
ADD r/m32, r32
MR
Valid
Valid
Add r32 to r/m32.
REX.W + 01 /r
ADD r/m64, r64
MR
Valid
N.E.
Add r64 to r/m64.
02 /r
ADD r8, r/m8
RM
Valid
Valid
Add r/m8 to r8.
REX + 02 /r
ADD r8*, r/m8*
RM
Valid
N.E.
Add r/m8 to r8.
03 /r
ADD r16, r/m16
RM
Valid
Valid
Add r/m16 to r16.
03 /r
ADD r32, r/m32
RM
Valid
Valid
Add r/m32 to r32.
REX.W + 03 /r
ADD r64, r/m64
RM
Valid
N.E.
Add r/m64 to r64.
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
RM
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
MR
ModRM:r/m (r, w)
ModRM:reg (r)
N/A
N/A
MI
ModRM:r/m (r, w)
imm8/16/32
N/A
N/A
I
AL/AX/EAX/RAX
imm8/16/32
N/A
N/A
Description
Adds the destination operand (first operand) and the source operand (second operand) and then stores the result
in the destination operand. The destination operand can be a register or a memory location; the source operand
can be an immediate, a register, or a memory location. (However, two memory operands cannot be used in one
instruction.) When an immediate value is used as an operand, it is sign-extended to the length of the destination
operand format.
The ADD instruction performs integer addition. It evaluates the result for both signed and unsigned integer oper-
ands and sets the OF and CF flags to indicate a carry (overflow) in the signed or unsigned result, respectively. The
SF flag indicates the sign of the signed result.
3-32
Vol. 2A
ADD-Add
INSTRUCTION SET REFERENCE, A-L
This instruction can be used with a LOCK prefix to allow the instruction to be executed atomically.
In 64-bit mode, the instruction’s default operation size is 32 bits. Using a REX prefix in the form of REX.R permits
access to additional registers (R8-R15). Using a REX prefix in the form of REX.W promotes operation to 64 bits. See
the summary chart at the beginning of this section for encoding data and limits.
Operation
DEST := DEST + SRC;
Flags Affected
The OF, SF, ZF, AF, CF, and PF flags are set according to the result.
Protected Mode Exceptions
#GP(0)
If the destination 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 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 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.
ADD-Add
Vol. 2A
3-33
INSTRUCTION SET REFERENCE, A-L
ADDPD-Add Packed Double Precision Floating-Point Values
Opcode/
Op /
64/32 bit
CPUID
Description
Instruction
En
Mode
Feature
Support
Flag
66 0F 58 /r
A
V/V
SSE2
Add packed double precision floating-point values from
ADDPD xmm1, xmm2/m128
xmm2/mem to xmm1 and store result in xmm1.
VEX.128.66.0F.WIG 58 /r
B
V/V
AVX
Add packed double precision floating-point values from
VADDPD xmm1,xmm2,
xmm3/mem to xmm2 and store result in xmm1.
xmm3/m128
VEX.256.66.0F.WIG 58 /r
B
V/V
AVX
Add packed double precision floating-point values from
VADDPD ymm1, ymm2,
ymm3/mem to ymm2 and store result in ymm1.
ymm3/m256
EVEX.128.66.0F.W1 58 /r
C
V/V
AVX512VL
Add packed double precision floating-point values from
VADDPD xmm1 {k1}{z}, xmm2,
AVX512F
xmm3/m128/m64bcst to xmm2 and store result in xmm1
xmm3/m128/m64bcst
with writemask k1.
EVEX.256.66.0F.W1 58 /r
C
V/V
AVX512VL
Add packed double precision floating-point values from
VADDPD ymm1 {k1}{z}, ymm2,
AVX512F
ymm3/m256/m64bcst to ymm2 and store result in ymm1
ymm3/m256/m64bcst
with writemask k1.
EVEX.512.66.0F.W1 58 /r
C
V/V
AVX512F
Add packed double precision floating-point values from
VADDPD zmm1 {k1}{z}, zmm2,
zmm3/m512/m64bcst to zmm2 and store result in zmm1
zmm3/m512/m64bcst{er}
with writemask k1.
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
B
N/A
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
C
Full
ModRM:reg (w)
EVEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
Adds two, four or eight packed double precision floating-point values from the first source operand to the second
source operand, and stores the packed double precision floating-point result in the destination operand.
EVEX encoded versions: The first source operand is a ZMM/YMM/XMM register. The second source operand can be
a ZMM/YMM/XMM register, a 512/256/128-bit memory location or a 512/256/128-bit vector broadcasted from a
64-bit memory location. The destination operand is a ZMM/YMM/XMM register conditionally updated with
writemask k1.
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. The upper bits (MAXVL-1:256) of
the corresponding ZMM register destination are zeroed.
VEX.128 encoded version: the first source operand is a XMM register. The second source operand is an XMM
register or 128-bit memory location. The destination operand is an XMM register. The upper bits (MAXVL-1:128) of
the corresponding ZMM register destination are zeroed.
128-bit Legacy SSE version: The second source can be an XMM register or an 128-bit memory location. The desti-
nation is not distinct from the first source XMM register and the upper Bits (MAXVL-1:128) of the corresponding
ZMM register destination are unmodified.
3-34
Vol. 2A
ADDPD-Add Packed Double Precision Floating-Point Values
INSTRUCTION SET REFERENCE, A-L
Operation
VADDPD (EVEX Encoded Versions) When SRC2 Operand is a Vector Register
(KL, VL) = (2, 128), (4, 256), (8, 512)
IF (VL = 512) AND (EVEX.b = 1)
THEN
SET_ROUNDING_MODE_FOR_THIS_INSTRUCTION(EVEX.RC);
ELSE
SET_ROUNDING_MODE_FOR_THIS_INSTRUCTION(MXCSR.RC);
FI;
FOR j := 0 TO KL-1
i := j * 64
IF k1[j] OR *no writemask*
THEN DEST[i+63:i] := SRC1[i+63:i] + SRC2[i+63:i]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+63:i] remains unchanged*
ELSE
; zeroing-masking
DEST[i+63:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:VL] := 0
VADDPD (EVEX Encoded Versions) When SRC2 Operand is a Memory Source
(KL, VL) = (2, 128), (4, 256), (8, 512)
FOR j := 0 TO KL-1
i := j * 64
IF k1[j] OR *no writemask*
THEN
IF (EVEX.b = 1)
THEN
DEST[i+63:i] := SRC1[i+63:i] + SRC2[63:0]
ELSE
DEST[i+63:i] := SRC1[i+63:i] + SRC2[i+63:i]
FI;
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+63:i] remains unchanged*
ELSE
; zeroing-masking
DEST[i+63:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:VL] := 0
VADDPD (VEX.256 Encoded Version)
DEST[63:0] := SRC1[63:0] + SRC2[63:0]
DEST[127:64] := SRC1[127:64] + SRC2[127:64]
DEST[191:128] := SRC1[191:128] + SRC2[191:128]
DEST[255:192] := SRC1[255:192] + SRC2[255:192]
DEST[MAXVL-1:256] := 0
ADDPD-Add Packed Double Precision Floating-Point Values
Vol. 2A
3-35
INSTRUCTION SET REFERENCE, A-L
VADDPD (VEX.128 Encoded Version)
DEST[63:0] := SRC1[63:0] + SRC2[63:0]
DEST[127:64] := SRC1[127:64] + SRC2[127:64]
DEST[MAXVL-1:128] := 0
ADDPD (128-bit Legacy SSE Version)
DEST[63:0] := DEST[63:0] + SRC[63:0]
DEST[127:64] := DEST[127:64] + SRC[127:64]
DEST[MAXVL-1:128] (Unmodified)
Intel C/C++ Compiler Intrinsic Equivalent
VADDPD __m512d _mm512_add_pd (__m512d a, __m512d b);
VADDPD __m512d _mm512_mask_add_pd (__m512d s, __mmask8 k, __m512d a, __m512d b);
VADDPD __m512d _mm512_maskz_add_pd (__mmask8 k, __m512d a, __m512d b);
VADDPD __m256d _mm256_mask_add_pd (__m256d s, __mmask8 k, __m256d a, __m256d b);
VADDPD __m256d _mm256_maskz_add_pd (__mmask8 k, __m256d a, __m256d b);
VADDPD __m128d _mm_mask_add_pd (__m128d s, __mmask8 k, __m128d a, __m128d b);
VADDPD __m128d _mm_maskz_add_pd (__mmask8 k, __m128d a, __m128d b);
VADDPD __m512d _mm512_add_round_pd (__m512d a, __m512d b, int);
VADDPD __m512d _mm512_mask_add_round_pd (__m512d s, __mmask8 k, __m512d a, __m512d b, int);
VADDPD __m512d _mm512_maskz_add_round_pd (__mmask8 k, __m512d a, __m512d b, int);
ADDPD __m256d _mm256_add_pd (__m256d a, __m256d b);
ADDPD __m128d _mm_add_pd (__m128d a, __m128d b);
SIMD Floating-Point Exceptions
Overflow, Underflow, Invalid, Precision, Denormal.
Other Exceptions
VEX-encoded instruction, see Table 2-19, “Type 2 Class Exception Conditions.”
EVEX-encoded instruction, see Table 2-46, “Type E2 Class Exception Conditions.”
3-36
Vol. 2A
ADDPD-Add Packed Double Precision Floating-Point Values
INSTRUCTION SET REFERENCE, A-L
ADDPS-Add Packed Single Precision Floating-Point Values
Opcode/
Op /
64/32 bit
CPUID
Description
Instruction
En
Mode
Feature
Support
Flag
NP 0F 58 /r
A
V/V
SSE
Add packed single precision floating-point values from
ADDPS xmm1, xmm2/m128
xmm2/m128 to xmm1 and store result in xmm1.
VEX.128.0F.WIG 58 /r
B
V/V
AVX
Add packed single precision floating-point values from
VADDPS xmm1,xmm2, xmm3/m128
xmm3/m128 to xmm2 and store result in xmm1.
VEX.256.0F.WIG 58 /r
B
V/V
AVX
Add packed single precision floating-point values from
VADDPS ymm1, ymm2, ymm3/m256
ymm3/m256 to ymm2 and store result in ymm1.
EVEX.128.0F.W0 58 /r
C
V/V
AVX512VL
Add packed single precision floating-point values from
VADDPS xmm1 {k1}{z}, xmm2,
AVX512F
xmm3/m128/m32bcst to xmm2 and store result in
xmm3/m128/m32bcst
xmm1 with writemask k1.
EVEX.256.0F.W0 58 /r
C
V/V
AVX512VL
Add packed single precision floating-point values from
VADDPS ymm1 {k1}{z}, ymm2,
AVX512F
ymm3/m256/m32bcst to ymm2 and store result in
ymm3/m256/m32bcst
ymm1 with writemask k1.
EVEX.512.0F.W0 58 /r
C
V/V
AVX512F
Add packed single precision floating-point values from
VADDPS zmm1 {k1}{z}, zmm2,
zmm3/m512/m32bcst to zmm2 and store result in
zmm3/m512/m32bcst {er}
zmm1 with writemask k1.
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
B
N/A
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
C
Full
ModRM:reg (w)
EVEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
Adds four, eight or sixteen packed single precision floating-point values from the first source operand with the
second source operand, and stores the packed single precision floating-point result in the destination operand.
EVEX encoded versions: The first source operand is a ZMM/YMM/XMM register. The second source operand can be
a ZMM/YMM/XMM register, a 512/256/128-bit memory location or a 512/256/128-bit vector broadcasted from a
32-bit memory location. The destination operand is a ZMM/YMM/XMM register conditionally updated with
writemask k1.
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. The upper bits (MAXVL-1:256) of
the corresponding ZMM register destination are zeroed.
VEX.128 encoded version: the first source operand is a XMM register. The second source operand is an XMM
register or 128-bit memory location. The destination operand is an XMM register. The upper bits (MAXVL-1:128) of
the corresponding ZMM register destination are zeroed.
128-bit Legacy SSE version: The second source can be an XMM register or an 128-bit memory location. The desti-
nation is not distinct from the first source XMM register and the upper Bits (MAXVL-1:128) of the corresponding
ZMM register destination are unmodified.
ADDPS-Add Packed Single Precision Floating-Point Values
Vol. 2A
3-37
INSTRUCTION SET REFERENCE, A-L
Operation
VADDPS (EVEX Encoded Versions) When SRC2 Operand is a Register
(KL, VL) = (4, 128), (8, 256), (16, 512)
IF (VL = 512) AND (EVEX.b = 1)
THEN
SET_ROUNDING_MODE_FOR_THIS_INSTRUCTION(EVEX.RC);
ELSE
SET_ROUNDING_MODE_FOR_THIS_INSTRUCTION(MXCSR.RC);
FI;
FOR j := 0 TO KL-1
i := j * 32
IF k1[j] OR *no writemask*
THEN DEST[i+31:i] := SRC1[i+31:i] + SRC2[i+31:i]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+31:i] remains unchanged*
ELSE
; zeroing-masking
DEST[i+31:i] := 0
FI
FI;
ENDFOR;
DEST[MAXVL-1:VL] := 0
VADDPS (EVEX Encoded Versions) When SRC2 Operand is a Memory Source
(KL, VL) = (4, 128), (8, 256), (16, 512)
FOR j := 0 TO KL-1
i := j * 32
IF k1[j] OR *no writemask*
THEN
IF (EVEX.b = 1)
THEN
DEST[i+31:i] := SRC1[i+31:i] + SRC2[31:0]
ELSE
DEST[i+31:i] := SRC1[i+31:i] + SRC2[i+31:i]
FI;
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+31:i] remains unchanged*
ELSE
; zeroing-masking
DEST[i+31:i] := 0
FI
FI;
ENDFOR;
DEST[MAXVL-1:VL] := 0
3-38
Vol. 2A
ADDPS-Add Packed Single Precision Floating-Point Values
INSTRUCTION SET REFERENCE, A-L
VADDPS (VEX.256 Encoded Version)
DEST[31:0] := SRC1[31:0] + SRC2[31:0]
DEST[63:32] := SRC1[63:32] + SRC2[63:32]
DEST[95:64] := SRC1[95:64] + SRC2[95:64]
DEST[127:96] := SRC1[127:96] + SRC2[127:96]
DEST[159:128] := SRC1[159:128] + SRC2[159:128]
DEST[191:160]:= SRC1[191:160] + SRC2[191:160]
DEST[223:192] := SRC1[223:192] + SRC2[223:192]
DEST[255:224] := SRC1[255:224] + SRC2[255:224].
DEST[MAXVL-1:256] := 0
VADDPS (VEX.128 Encoded Version)
DEST[31:0] := SRC1[31:0] + SRC2[31:0]
DEST[63:32] := SRC1[63:32] + SRC2[63:32]
DEST[95:64] := SRC1[95:64] + SRC2[95:64]
DEST[127:96] := SRC1[127:96] + SRC2[127:96]
DEST[MAXVL-1:128] := 0
ADDPS (128-bit Legacy SSE Version)
DEST[31:0] := SRC1[31:0] + SRC2[31:0]
DEST[63:32] := SRC1[63:32] + SRC2[63:32]
DEST[95:64] := SRC1[95:64] + SRC2[95:64]
DEST[127:96] := SRC1[127:96] + SRC2[127:96]
DEST[MAXVL-1:128] (Unmodified)
Intel C/C++ Compiler Intrinsic Equivalent
VADDPS __m512 _mm512_add_ps (__m512 a, __m512 b);
VADDPS __m512 _mm512_mask_add_ps (__m512 s, __mmask16 k, __m512 a, __m512 b);
VADDPS __m512 _mm512_maskz_add_ps (__mmask16 k, __m512 a, __m512 b);
VADDPS __m256 _mm256_mask_add_ps (__m256 s, __mmask8 k, __m256 a, __m256 b);
VADDPS __m256 _mm256_maskz_add_ps (__mmask8 k, __m256 a, __m256 b);
VADDPS __m128 _mm_mask_add_ps (__m128d s, __mmask8 k, __m128 a, __m128 b);
VADDPS __m128 _mm_maskz_add_ps (__mmask8 k, __m128 a, __m128 b);
VADDPS __m512 _mm512_add_round_ps (__m512 a, __m512 b, int);
VADDPS __m512 _mm512_mask_add_round_ps (__m512 s, __mmask16 k, __m512 a, __m512 b, int);
VADDPS __m512 _mm512_maskz_add_round_ps (__mmask16 k, __m512 a, __m512 b, int);
ADDPS __m256 _mm256_add_ps (__m256 a, __m256 b);
ADDPS __m128 _mm_add_ps (__m128 a, __m128 b);
SIMD Floating-Point Exceptions
Overflow, Underflow, Invalid, Precision, Denormal.
Other Exceptions
VEX-encoded instruction, see Table 2-19, “Type 2 Class Exception Conditions.”
EVEX-encoded instruction, see Table 2-46, “Type E2 Class Exception Conditions.”
ADDPS-Add Packed Single Precision Floating-Point Values
Vol. 2A
3-39
INSTRUCTION SET REFERENCE, A-L
ADDSD-Add Scalar Double Precision Floating-Point Values
Opcode/
Op /
64/32 bit
CPUID
Description
Instruction
En
Mode
Feature
Support
Flag
F2 0F 58 /r
A
V/V
SSE2
Add the low double precision floating-point value from
ADDSD xmm1, xmm2/m64
xmm2/mem to xmm1 and store the result in xmm1.
VEX.LIG.F2.0F.WIG 58 /r
B
V/V
AVX
Add the low double precision floating-point value from
VADDSD xmm1, xmm2,
xmm3/mem to xmm2 and store the result in xmm1.
xmm3/m64
EVEX.LLIG.F2.0F.W1 58 /r
C
V/V
AVX512F
Add the low double precision floating-point value from
VADDSD xmm1 {k1}{z}, xmm2,
xmm3/m64 to xmm2 and store the result in xmm1 with
xmm3/m64{er}
writemask k1.
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
B
N/A
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
C
Tuple1 Scalar
ModRM:reg (w)
EVEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
Adds the low double precision floating-point values from the second source operand and the first source operand
and stores the double precision floating-point result in 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.
128-bit Legacy SSE version: The first source and destination operands are the same. Bits (MAXVL-1:64) of the
corresponding destination register remain unchanged.
EVEX and VEX.128 encoded version: The first source operand is encoded by EVEX.vvvv/VEX.vvvv. Bits (127:64) of
the XMM register destination are copied from corresponding bits in the first source operand. Bits (MAXVL-1:128) of
the destination register are zeroed.
EVEX version: The low quadword element of the destination is updated according to the writemask.
Software should ensure VADDSD is encoded with VEX.L=0. Encoding VADDSD with VEX.L=1 may encounter unpre-
dictable behavior across different processor generations.
3-40
Vol. 2A
ADDSD-Add Scalar Double Precision Floating-Point Values
INSTRUCTION SET REFERENCE, A-L
Operation
VADDSD (EVEX Encoded Version)
IF (EVEX.b = 1) AND SRC2 *is a register*
THEN
SET_ROUNDING_MODE_FOR_THIS_INSTRUCTION(EVEX.RC);
ELSE
SET_ROUNDING_MODE_FOR_THIS_INSTRUCTION(MXCSR.RC);
FI;
IF k1[0] or *no writemask*
THEN
DEST[63:0] := SRC1[63:0] + SRC2[63:0]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[63:0] remains unchanged*
ELSE
; zeroing-masking
THEN DEST[63:0] := 0
FI;
FI;
DEST[127:64] := SRC1[127:64]
DEST[MAXVL-1:128] := 0
VADDSD (VEX.128 Encoded Version)
DEST[63:0] := SRC1[63:0] + SRC2[63:0]
DEST[127:64] := SRC1[127:64]
DEST[MAXVL-1:128] := 0
ADDSD (128-bit Legacy SSE Version)
DEST[63:0] := DEST[63:0] + SRC[63:0]
DEST[MAXVL-1:64] (Unmodified)
Intel C/C++ Compiler Intrinsic Equivalent
VADDSD __m128d _mm_mask_add_sd (__m128d s, __mmask8 k, __m128d a, __m128d b);
VADDSD __m128d _mm_maskz_add_sd (__mmask8 k, __m128d a, __m128d b);
VADDSD __m128d _mm_add_round_sd (__m128d a, __m128d b, int);
VADDSD __m128d _mm_mask_add_round_sd (__m128d s, __mmask8 k, __m128d a, __m128d b, int);
VADDSD __m128d _mm_maskz_add_round_sd (__mmask8 k, __m128d a, __m128d b, int);
ADDSD __m128d _mm_add_sd (__m128d a, __m128d b);
SIMD Floating-Point Exceptions
Overflow, Underflow, Invalid, Precision, Denormal.
Other Exceptions
VEX-encoded instruction, see Table 2-20, “Type 3 Class Exception Conditions.”
EVEX-encoded instruction, see Table 2-47, “Type E3 Class Exception Conditions.”
ADDSD-Add Scalar Double Precision Floating-Point Values
Vol. 2A
3-41
INSTRUCTION SET REFERENCE, A-L
ADDSS-Add Scalar Single Precision Floating-Point Values
Opcode/
Op /
64/32 bit
CPUID
Description
Instruction
En
Mode
Feature
Support
Flag
F3 0F 58 /r
A
V/V
SSE
Add the low single precision floating-point value from xmm2/mem
ADDSS xmm1, xmm2/m32
to xmm1 and store the result in xmm1.
VEX.LIG.F3.0F.WIG 58 /r
B
V/V
AVX
Add the low single precision floating-point value from xmm3/mem
VADDSS xmm1,xmm2,
to xmm2 and store the result in xmm1.
xmm3/m32
EVEX.LLIG.F3.0F.W0 58 /r
C
V/V
AVX512F
Add the low single precision floating-point value from xmm3/m32
VADDSS xmm1{k1}{z}, xmm2,
to xmm2 and store the result in xmm1with writemask k1.
xmm3/m32{er}
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
B
N/A
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
C
Tuple1 Scalar
ModRM:reg (w)
EVEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
Adds the low single precision floating-point values from the second source operand and the first source operand,
and stores the double precision floating-point result in 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.
128-bit Legacy SSE version: The first source and destination operands are the same. Bits (MAXVL-1:32) of the
corresponding the destination register remain unchanged.
EVEX and VEX.128 encoded version: The first source operand is encoded by EVEX.vvvv/VEX.vvvv. Bits (127:32) of
the XMM register destination are copied from corresponding bits in the first source operand. Bits (MAXVL-1:128) of
the destination register are zeroed.
EVEX version: The low doubleword element of the destination is updated according to the writemask.
Software should ensure VADDSS is encoded with VEX.L=0. Encoding VADDSS with VEX.L=1 may encounter unpre-
dictable behavior across different processor generations.
3-42
Vol. 2A
ADDSS-Add Scalar Single Precision Floating-Point Values
INSTRUCTION SET REFERENCE, A-L
Operation
VADDSS (EVEX Encoded Versions)
IF (EVEX.b = 1) AND SRC2 *is a register*
THEN
SET_ROUNDING_MODE_FOR_THIS_INSTRUCTION(EVEX.RC);
ELSE
SET_ROUNDING_MODE_FOR_THIS_INSTRUCTION(MXCSR.RC);
FI;
IF k1[0] or *no writemask*
THEN
DEST[31:0] := SRC1[31:0] + SRC2[31:0]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[31:0] remains unchanged*
ELSE
; zeroing-masking
THEN DEST[31:0] := 0
FI;
FI;
DEST[127:32] := SRC1[127:32]
DEST[MAXVL-1:128] := 0
VADDSS DEST, SRC1, SRC2 (VEX.128 Encoded Version)
DEST[31:0] := SRC1[31:0] + SRC2[31:0]
DEST[127:32] := SRC1[127:32]
DEST[MAXVL-1:128] := 0
ADDSS DEST, SRC (128-bit Legacy SSE Version)
DEST[31:0] := DEST[31:0] + SRC[31:0]
DEST[MAXVL-1:32] (Unmodified)
Intel C/C++ Compiler Intrinsic Equivalent
VADDSS __m128 _mm_mask_add_ss (__m128 s, __mmask8 k, __m128 a, __m128 b);
VADDSS __m128 _mm_maskz_add_ss (__mmask8 k, __m128 a, __m128 b);
VADDSS __m128 _mm_add_round_ss (__m128 a, __m128 b, int);
VADDSS __m128 _mm_mask_add_round_ss (__m128 s, __mmask8 k, __m128 a, __m128 b, int);
VADDSS __m128 _mm_maskz_add_round_ss (__mmask8 k, __m128 a, __m128 b, int);
ADDSS __m128 _mm_add_ss (__m128 a, __m128 b);
SIMD Floating-Point Exceptions
Overflow, Underflow, Invalid, Precision, Denormal.
Other Exceptions
VEX-encoded instruction, see Table 2-20, “Type 3 Class Exception Conditions.”
EVEX-encoded instruction, see Table 2-47, “Type E3 Class Exception Conditions.”
ADDSS-Add Scalar Single Precision Floating-Point Values
Vol. 2A
3-43
INSTRUCTION SET REFERENCE, A-L
ADDSUBPD-Packed Double Precision Floating-Point Add/Subtract
Opcode/
Op/
64/32-bit
CPUID
Description
Instruction
En
Mode
Feature
Flag
66 0F D0 /r
RM
V/V
SSE3
Add/subtract double precision floating-point
values from xmm2/m128 to xmm1.
ADDSUBPD xmm1, xmm2/m128
VEX.128.66.0F.WIG D0 /r
RVM
V/V
AVX
Add/subtract packed double precision
floating-point values from xmm3/mem to
VADDSUBPD xmm1, xmm2, xmm3/m128
xmm2 and stores result in xmm1.
VEX.256.66.0F.WIG D0 /r
RVM
V/V
AVX
Add / subtract packed double precision
floating-point values from ymm3/mem to
VADDSUBPD ymm1, ymm2, ymm3/m256
ymm2 and stores result in ymm1.
Instruction Operand Encoding
Op/En
Operand 1
Operand 2
Operand 3
Operand 4
RM
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
RVM
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
Adds odd-numbered double precision floating-point values of the first source operand (second operand) with the
corresponding double precision floating-point values from the second source operand (third operand); stores the
result in the odd-numbered values of the destination operand (first operand). Subtracts the even-numbered double
precision floating-point values from the second source operand from the corresponding double precision floating
values in the first source operand; stores the result into the even-numbered values of the destination operand.
In 64-bit mode, using a REX prefix in the form of REX.R 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 desti-
nation is not distinct from the first source XMM register and the upper bits (MAXVL-1:128) of the corresponding
YMM register destination are unmodified. See Figure 3-3.
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 (MAXVL-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.
3-44
Vol. 2A
ADDSUBPD-Packed Double Precision Floating-Point Add/Subtract
INSTRUCTION SET REFERENCE, A-L
ADDSUBPD xmm1, xmm2/m128
[127:64]
[63:0]
xmm2/m128
RESULT:
xmm1[127:64] + xmm2/m128[127:64]
xmm1[63:0] - xmm2/m128[63:0]
xmm1
[127:64]
[63:0]
Figure 3-3. ADDSUBPD-Packed Double Precision Floating-Point Add/Subtract
Operation
ADDSUBPD (128-bit Legacy SSE Version)
DEST[63:0] := DEST[63:0] - SRC[63:0]
DEST[127:64] := DEST[127:64] + SRC[127:64]
DEST[MAXVL-1:128] (Unmodified)
VADDSUBPD (VEX.128 Encoded Version)
DEST[63:0] := SRC1[63:0] - SRC2[63:0]
DEST[127:64] := SRC1[127:64] + SRC2[127:64]
DEST[MAXVL-1:128] := 0
VADDSUBPD (VEX.256 Encoded Version)
DEST[63:0] := SRC1[63:0] - SRC2[63:0]
DEST[127:64] := SRC1[127:64] + SRC2[127:64]
DEST[191:128] := SRC1[191:128] - SRC2[191:128]
DEST[255:192] := SRC1[255:192] + SRC2[255:192]
Intel C/C++ Compiler Intrinsic Equivalent
ADDSUBPD __m128d _mm_addsub_pd(__m128d a, __m128d b)
VADDSUBPD __m256d _mm256_addsub_pd (__m256d a, __m256d b)
Exceptions
When the source operand is a memory operand, it must be aligned on a 16-byte boundary or a general-protection
exception (#GP) will be generated.
SIMD Floating-Point Exceptions
Overflow, Underflow, Invalid, Precision, Denormal.
Other Exceptions
See Table 2-19, “Type 2 Class Exception Conditions.”
ADDSUBPD-Packed Double Precision Floating-Point Add/Subtract
Vol. 2A
3-45
INSTRUCTION SET REFERENCE, A-L
ADDSUBPS-Packed Single Precision Floating-Point Add/Subtract
Opcode/
Op/
64/32-bit
CPUID
Description
Instruction
En
Mode
Feature
Flag
F2 0F D0 /r
RM
V/V
SSE3
Add/subtract single precision floating-point
values from xmm2/m128 to xmm1.
ADDSUBPS xmm1, xmm2/m128
VEX.128.F2.0F.WIG D0 /r
RVM
V/V
AVX
Add/subtract single precision floating-point
values from xmm3/mem to xmm2 and stores
VADDSUBPS xmm1, xmm2, xmm3/m128
result in xmm1.
VEX.256.F2.0F.WIG D0 /r
RVM
V/V
AVX
Add / subtract single precision floating-point
values from ymm3/mem to ymm2 and stores
VADDSUBPS ymm1, ymm2, ymm3/m256
result in ymm1.
Instruction Operand Encoding
Op/En
Operand 1
Operand 2
Operand 3
Operand 4
RM
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
RVM
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
Adds odd-numbered single precision floating-point values of the first source operand (second operand) with the
corresponding single precision floating-point values from the second source operand (third operand); stores the
result in the odd-numbered values of the destination operand (first operand). Subtracts the even-numbered single
precision floating-point values from the second source operand from the corresponding single precision floating
values in the first source operand; stores the result into the even-numbered values of the destination operand.
In 64-bit mode, using a REX prefix in the form of REX.R 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 desti-
nation is not distinct from the first source XMM register and the upper bits (MAXVL-1:128) of the corresponding
YMM register destination are unmodified. See Figure 3-4.
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 (MAXVL-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.
3-46
Vol. 2A
ADDSUBPS-Packed Single Precision Floating-Point Add/Subtract
INSTRUCTION SET REFERENCE, A-L
ADDSUBPS xmm1, xmm2/m128
xmm2/
[127:96]
[95:64]
[63:32]
[31:0]
m128
xmm1[127:96] +
xmm1[95:64] - xmm2/
xmm1[63:32] +
xmm1[31:0] -
RESULT:
xmm2/m128[127:96]
m128[95:64]
xmm2/m128[63:32]
xmm2/m128[31:0]
xmm1
[127:96]
[95:64]
[63:32]
[31:0]
OM15992
Figure 3-4. ADDSUBPS-Packed Single Precision Floating-Point Add/Subtract
Operation
ADDSUBPS (128-bit Legacy SSE Version)
DEST[31:0] := DEST[31:0] - SRC[31:0]
DEST[63:32] := DEST[63:32] + SRC[63:32]
DEST[95:64] := DEST[95:64] - SRC[95:64]
DEST[127:96] := DEST[127:96] + SRC[127:96]
DEST[MAXVL-1:128] (Unmodified)
VADDSUBPS (VEX.128 Encoded Version)
DEST[31:0] := SRC1[31:0] - SRC2[31:0]
DEST[63:32] := SRC1[63:32] + SRC2[63:32]
DEST[95:64] := SRC1[95:64] - SRC2[95:64]
DEST[127:96] := SRC1[127:96] + SRC2[127:96]
DEST[MAXVL-1:128] := 0
VADDSUBPS (VEX.256 Encoded Version)
DEST[31:0] := SRC1[31:0] - SRC2[31:0]
DEST[63:32] := SRC1[63:32] + SRC2[63:32]
DEST[95:64] := SRC1[95:64] - SRC2[95:64]
DEST[127:96] := SRC1[127:96] + SRC2[127:96]
DEST[159:128] := SRC1[159:128] - SRC2[159:128]
DEST[191:160] := SRC1[191:160] + SRC2[191:160]
DEST[223:192] := SRC1[223:192] - SRC2[223:192]
DEST[255:224] := SRC1[255:224] + SRC2[255:224]
Intel C/C++ Compiler Intrinsic Equivalent
ADDSUBPS __m128 _mm_addsub_ps(__m128 a, __m128 b)
VADDSUBPS __m256 _mm256_addsub_ps (__m256 a, __m256 b)
Exceptions
When the source operand is a memory operand, the operand must be aligned on a 16-byte boundary or a general-
protection exception (#GP) will be generated.
ADDSUBPS-Packed Single Precision Floating-Point Add/Subtract
Vol. 2A
3-47
INSTRUCTION SET REFERENCE, A-L
SIMD Floating-Point Exceptions
Overflow, Underflow, Invalid, Precision, Denormal.
Other Exceptions
See Table 2-19, “Type 2 Class Exception Conditions.”
3-48
Vol. 2A
ADDSUBPS-Packed Single Precision Floating-Point Add/Subtract
INSTRUCTION SET REFERENCE, A-L
ADOX - Unsigned Integer Addition of Two Operands With Overflow Flag
Opcode/
Op/
64/32bit
CPUID
Description
Instruction
En
Mode
Feature
Support
Flag
F3 0F 38 F6 /r
RM
V/V
ADX
Unsigned addition of r32 with OF, r/m32 to r32, writes OF.
ADOX r32, r/m32
F3 REX.w 0F 38 F6 /r
RM
V/NE
ADX
Unsigned addition of r64 with OF, r/m64 to r64, writes OF.
ADOX r64, r/m64
Instruction Operand Encoding
Op/En
Operand 1
Operand 2
Operand 3
Operand 4
RM
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
Description
Performs an unsigned addition of the destination operand (first operand), the source operand (second operand)
and the overflow-flag (OF) and stores the result in the destination operand. The destination operand is a general-
purpose register, whereas the source operand can be a general-purpose register or memory location. The state of
OF represents a carry from a previous addition. The instruction sets the OF flag with the carry generated by the
unsigned addition of the operands.
The ADOX instruction is executed in the context of multi-precision addition, where we add a series of operands with
a carry-chain. At the beginning of a chain of additions, we execute an instruction to zero the OF (e.g. XOR).
This instruction is supported in real mode and virtual-8086 mode. The operand size is always 32 bits if not in 64-
bit mode.
In 64-bit mode, the default operation size is 32 bits. Using a REX Prefix in the form of REX.R permits access to addi-
tional registers (R8-15). Using REX Prefix in the form of REX.W promotes operation to 64-bits.
ADOX executes normally either inside or outside a transaction region.
Note: ADOX defines the CF and OF flags differently than the ADD/ADC instructions as defined in Intel® 64 and
IA-32 Architectures Software Developer’s Manual, Volume 2A.
Operation
IF OperandSize is 64-bit
THEN OF:DEST[63:0] := DEST[63:0] + SRC[63:0] + OF;
ELSE OF:DEST[31:0] := DEST[31:0] + SRC[31:0] + OF;
FI;
Flags Affected
OF is updated based on result. CF, SF, ZF, AF, and PF flags are unmodified.
Intel C/C++ Compiler Intrinsic Equivalent
unsigned char _addcarryx_u32 (unsigned char c_in, unsigned int src1, unsigned int src2, unsigned int *sum_out);
unsigned char _addcarryx_u64 (unsigned char c_in, unsigned __int64 src1, unsigned __int64 src2, unsigned __int64 *sum_out);
SIMD Floating-Point Exceptions
None.
ADOX - Unsigned Integer Addition of Two Operands With Overflow Flag
Vol. 2A
3-49
INSTRUCTION SET REFERENCE, A-L
Protected Mode Exceptions
#UD
If the LOCK prefix is used.
If CPUID.(EAX=07H, ECX=0H):EBX.ADX[bit 19] = 0.
#SS(0)
For an illegal address in the SS segment.
#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.
#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
#UD
If the LOCK prefix is used.
If CPUID.(EAX=07H, ECX=0H):EBX.ADX[bit 19] = 0.
#SS(0)
For an illegal address in the SS segment.
#GP(0)
If any part of the operand lies outside the effective address space from 0 to FFFFH.
Virtual-8086 Mode Exceptions
#UD
If the LOCK prefix is used.
If CPUID.(EAX=07H, ECX=0H):EBX.ADX[bit 19] = 0.
#SS(0)
For an illegal address in the SS segment.
#GP(0)
If any part of the operand lies outside the effective address space from 0 to FFFFH.
#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
#UD
If the LOCK prefix is used.
If CPUID.(EAX=07H, ECX=0H):EBX.ADX[bit 19] = 0.
#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.
#AC(0)
If alignment checking is enabled and an unaligned memory reference is made while the
current privilege level is 3.
3-50
Vol. 2A
ADOX - Unsigned Integer Addition of Two Operands With Overflow Flag
INSTRUCTION SET REFERENCE, A-L
AESDEC-Perform One Round of an AES Decryption Flow
Opcode/
Op/
64/32-bit
CPUID
Description
Instruction
En
Mode
Feature
Flag
66 0F 38 DE /r
A
V/V
AES
Perform one round of an AES decryption flow, using
AESDEC xmm1, xmm2/m128
the Equivalent Inverse Cipher, using one 128-bit data
(state) from xmm1 with one 128-bit round key from
xmm2/m128.
VEX.128.66.0F38.WIG DE /r
B
V/V
AES
Perform one round of an AES decryption flow, using
VAESDEC xmm1, xmm2, xmm3/m128
AVX
the Equivalent Inverse Cipher, using one 128-bit data
(state) from xmm2 with one 128-bit round key from
xmm3/m128; store the result in xmm1.
VEX.256.66.0F38.WIG DE /r
B
V/V
VAES
Perform one round of an AES decryption flow, using
VAESDEC ymm1, ymm2, ymm3/m256
the Equivalent Inverse Cipher, using two 128-bit data
(state) from ymm2 with two 128-bit round keys from
ymm3/m256; store the result in ymm1.
EVEX.128.66.0F38.WIG DE /r
C
V/V
VAES
Perform one round of an AES decryption flow, using
VAESDEC xmm1, xmm2, xmm3/m128
AVX512VL
the Equivalent Inverse Cipher, using one 128-bit data
(state) from xmm2 with one 128-bit round key from
xmm3/m128; store the result in xmm1.
EVEX.256.66.0F38.WIG DE /r
C
V/V
VAES
Perform one round of an AES decryption flow, using
VAESDEC ymm1, ymm2, ymm3/m256
AVX512VL
the Equivalent Inverse Cipher, using two 128-bit data
(state) from ymm2 with two 128-bit round keys from
ymm3/m256; store the result in ymm1.
EVEX.512.66.0F38.WIG DE /r
C
V/V
VAES
Perform one round of an AES decryption flow, using
VAESDEC zmm1, zmm2, zmm3/m512
AVX512F
the Equivalent Inverse Cipher, using four 128-bit data
(state) from zmm2 with four 128-bit round keys from
zmm3/m512; store the result in zmm1.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
B
N/A
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
C
Full Mem
ModRM:reg (w)
EVEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction performs a single round of the AES decryption flow using the Equivalent Inverse Cipher, using
one/two/four (depending on vector length) 128-bit data (state) from the first source operand with one/two/four
(depending on vector length) round key(s) from the second source operand, and stores the result in the destina-
tion operand.
Use the AESDEC instruction for all but the last decryption round. For the last decryption round, use the AESDE-
CLAST instruction.
VEX and EVEX encoded versions of the instruction allow 3-operand (non-destructive) operation. The legacy
encoded versions of the instruction require that the first source operand and the destination operand are the same
and must be an XMM register.
The EVEX encoded form of this instruction does not support memory fault suppression.
AESDEC-Perform One Round of an AES Decryption Flow
Vol. 2A
3-51
INSTRUCTION SET REFERENCE, A-L
Operation
AESDEC
STATE := SRC1;
RoundKey := SRC2;
STATE := InvShiftRows( STATE );
STATE := InvSubBytes( STATE );
STATE := InvMixColumns( STATE );
DEST[127:0] := STATE XOR RoundKey;
DEST[MAXVL-1:128] (Unmodified)
VAESDEC (128b and 256b VEX Encoded Versions)
(KL,VL) = (1,128), (2,256)
FOR i = 0 to KL-1:
STATE := SRC1.xmm[i]
RoundKey := SRC2.xmm[i]
STATE := InvShiftRows( STATE )
STATE := InvSubBytes( STATE )
STATE := InvMixColumns( STATE )
DEST.xmm[i] := STATE XOR RoundKey
DEST[MAXVL-1:VL] := 0
VAESDEC (EVEX Encoded Version)
(KL,VL) = (1,128), (2,256), (4,512)
FOR i = 0 to KL-1:
STATE := SRC1.xmm[i]
RoundKey := SRC2.xmm[i]
STATE := InvShiftRows( STATE )
STATE := InvSubBytes( STATE )
STATE := InvMixColumns( STATE )
DEST.xmm[i] := STATE XOR RoundKey
DEST[MAXVL-1:VL] :=0
Intel C/C++ Compiler Intrinsic Equivalent
(V)AESDEC __m128i _mm_aesdec (__m128i, __m128i)
VAESDEC __m256i _mm256_aesdec_epi128(__m256i, __m256i);
VAESDEC __m512i _mm512_aesdec_epi128(__m512i, __m512i);
SIMD Floating-Point Exceptions
None.
Other Exceptions
See Table 2-21, “Type 4 Class Exception Conditions.”
EVEX-encoded: See Table 2-50, “Type E4NF Class Exception Conditions.”
3-52
Vol. 2A
AESDEC-Perform One Round of an AES Decryption Flow
INSTRUCTION SET REFERENCE, A-L
AESDEC128KL-Perform Ten Rounds of AES Decryption Flow With Key Locker Using 128-Bit
Key
Opcode/
Op/
64/32-bit
CPUID
Description
Instruction
En
Mode
Feature
Flag
F3 0F 38 DD !(11):rrr:bbb
A
V/V
AESKLE
Decrypt xmm using 128-bit AES key indicated by han-
AESDEC128KL xmm, m384
dle at m384 and store result in xmm.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
Description
The AESDEC128KL1 instruction performs 10 rounds of AES to decrypt the first operand using the 128-bit key indi-
cated by the handle from the second operand. It stores the result in the first operand if the operation succeeds
(e.g., does not run into a handle violation failure).
Operation
AESDEC128KL
Handle := UnalignedLoad of 384 bit (SRC);
// Load is not guaranteed to be atomic.
Illegal Handle = (HandleReservedBitSet (Handle) ||
(Handle[0] AND (CPL > 0)) ||
Handle [2] ||
HandleKeyType (Handle) != HANDLE_KEY_TYPE_AES128);
IF (Illegal Handle) {
THEN RFLAGS.ZF := 1;
ELSE
(UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate384 (Handle[383:0], IWKey);
IF (Authentic == 0)
THEN RFLAGS.ZF := 1;
ELSE
DEST := AES128Decrypt (DEST, UnwrappedKey) ;
RFLAGS.ZF := 0;
FI;
FI;
RFLAGS.OF, SF, AF, PF, CF := 0;
Flags Affected
ZF is set to 0 if the operation succeeded and set to 1 if the operation failed due to a handle violation. The other
arithmetic flags (OF, SF, AF, PF, CF) are cleared to 0.
Intel C/C++ Compiler Intrinsic Equivalent
AESDEC128KL unsigned char _mm_aesdec128kl_u8(__m128i* odata, __m128i idata, const void* h);
1. Further details on Key Locker and usage of this instruction can be found here:
https://software.intel.com/content/www/us/en/develop/download/intel-key-locker-specification.html.
AESDEC128KL-Perform Ten Rounds of AES Decryption Flow With Key Locker Using 128-Bit Key
Vol. 2A
3-53
INSTRUCTION SET REFERENCE, A-L
Exceptions (All Operating Modes)
#UD
If the LOCK prefix is used.
If CPUID.07H:ECX.KL [bit 23] = 0.
If CR4.KL = 0.
If CPUID.19H:EBX.AESKLE [bit 0] = 0.
If CR0.EM = 1.
If CR4.OSFXSR = 0.
#NM
If CR0.TS = 1.
#PF
If a page fault occurs.
#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.
If the memory address is in a non-canonical form.
#SS(0)
If a memory operand effective address is outside the SS segment limit.
If a memory address referencing the SS segment is in a non-canonical form.
3-54
Vol. 2A
AESDEC128KL-Perform Ten Rounds of AES Decryption Flow With Key Locker Using 128-Bit Key
INSTRUCTION SET REFERENCE, A-L
AESDEC256KL-Perform 14 Rounds of AES Decryption Flow With Key Locker Using 256-Bit Key
Opcode/
Op/
64/32-bit
CPUID
Description
Instruction
En
Mode
Feature
Flag
F3 0F 38 DF !(11):rrr:bbb
A
V/V
AESKLE
Decrypt xmm using 256-bit AES key indicated by han-
AESDEC256KL xmm, m512
dle at m512 and store result in xmm.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
Description
The AESDEC256KL1 instruction performs 14 rounds of AES to decrypt the first operand using the 256-bit key indi-
cated by the handle from the second operand. It stores the result in the first operand if the operation succeeds
(e.g., does not run into a handle violation failure).
Operation
AESDEC256KL
Handle := UnalignedLoad of 512 bit (SRC);
// Load is not guaranteed to be atomic.
Illegal Handle = (HandleReservedBitSet (Handle) ||
(Handle[0] AND (CPL > 0)) ||
Handle [2] ||
HandleKeyType (Handle) != HANDLE_KEY_TYPE_AES256);
IF (Illegal Handle)
THEN RFLAGS.ZF := 1;
ELSE
(UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate512 (Handle[511:0], IWKey);
IF (Authentic == 0)
THEN RFLAGS.ZF := 1;
ELSE
DEST := AES256Decrypt (DEST, UnwrappedKey) ;
RFLAGS.ZF := 0;
FI;
FI;
RFLAGS.OF, SF, AF, PF, CF := 0;
Flags Affected
ZF is set to 0 if the operation succeeded and set to 1 if the operation failed due to a handle violation. The other
arithmetic flags (OF, SF, AF, PF, CF) are cleared to 0.
Intel C/C++ Compiler Intrinsic Equivalent
AESDEC256KL unsigned char _mm_aesdec256kl_u8(__m128i* odata, __m128i idata, const void* h);
1. Further details on Key Locker and usage of this instruction can be found here:
https://software.intel.com/content/www/us/en/develop/download/intel-key-locker-specification.html.
AESDEC256KL-Perform 14 Rounds of AES Decryption Flow With Key Locker Using 256-Bit Key
Vol. 2A
3-55
INSTRUCTION SET REFERENCE, A-L
Exceptions (All Operating Modes)
#UD
If the LOCK prefix is used.
If CPUID.07H:ECX.KL [bit 23] = 0.
If CR4.KL = 0.
If CPUID.19H:EBX.AESKLE [bit 0] = 0.
If CR0.EM = 1.
If CR4.OSFXSR = 0.
#NM
If CR0.TS = 1.
#PF
If a page fault occurs.
#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.
If the memory address is in a non-canonical form.
#SS(0)
If a memory operand effective address is outside the SS segment limit.
If a memory address referencing the SS segment is in a non-canonical form.
3-56
Vol. 2A
AESDEC256KL-Perform 14 Rounds of AES Decryption Flow With Key Locker Using 256-Bit Key
INSTRUCTION SET REFERENCE, A-L
AESDECLAST-Perform Last Round of an AES Decryption Flow
Opcode/
Op/
64/32-bit
CPUID
Description
Instruction
En
Mode
Feature
Flag
66 0F 38 DF /r
A
V/V
AES
Perform the last round of an AES decryption flow,
AESDECLAST xmm1, xmm2/m128
using the Equivalent Inverse Cipher, using one 128-bit
data (state) from xmm1 with one 128-bit round key
from xmm2/m128.
VEX.128.66.0F38.WIG DF /r
B
V/V
AES
Perform the last round of an AES decryption flow,
VAESDECLAST xmm1, xmm2, xmm3/m128
AVX
using the Equivalent Inverse Cipher, using one 128-bit
data (state) from xmm2 with one 128-bit round key
from xmm3/m128; store the result in xmm1.
VEX.256.66.0F38.WIG DF /r
B
V/V
VAES
Perform the last round of an AES decryption flow,
VAESDECLAST ymm1, ymm2, ymm3/m256
using the Equivalent Inverse Cipher, using two 128-
bit data (state) from ymm2 with two 128-bit round
keys from ymm3/m256; store the result in ymm1.
EVEX.128.66.0F38.WIG DF /r
C
V/V
VAES
Perform the last round of an AES decryption flow,
VAESDECLAST xmm1, xmm2, xmm3/m128
AVX512VL
using the Equivalent Inverse Cipher, using one 128-bit
data (state) from xmm2 with one 128-bit round key
from xmm3/m128; store the result in xmm1.
EVEX.256.66.0F38.WIG DF /r
C
V/V
VAES
Perform the last round of an AES decryption flow,
VAESDECLAST ymm1, ymm2, ymm3/m256
AVX512VL
using the Equivalent Inverse Cipher, using two 128-
bit data (state) from ymm2 with two 128-bit round
keys from ymm3/m256; store the result in ymm1.
EVEX.512.66.0F38.WIG DF /r
C
V/V
VAES
Perform the last round of an AES decryption flow,
VAESDECLAST zmm1, zmm2, zmm3/m512
AVX512F
using the Equivalent Inverse Cipher, using four128-bit
data (state) from zmm2 with four 128-bit round keys
from zmm3/m512; store the result in zmm1.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
B
N/A
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
C
Full Mem
ModRM:reg (w)
EVEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction performs the last round of the AES decryption flow using the Equivalent Inverse Cipher, using
one/two/four (depending on vector length) 128-bit data (state) from the first source operand with one/two/four
(depending on vector length) round key(s) from the second source operand, and stores the result in the destina-
tion operand.
VEX and EVEX encoded versions of the instruction allow 3-operand (non-destructive) operation. The legacy
encoded versions of the instruction require that the first source operand and the destination operand are the same
and must be an XMM register.
The EVEX encoded form of this instruction does not support memory fault suppression.
AESDECLAST-Perform Last Round of an AES Decryption Flow
Vol. 2A
3-57
INSTRUCTION SET REFERENCE, A-L
Operation
AESDECLAST
STATE := SRC1;
RoundKey := SRC2;
STATE := InvShiftRows( STATE );
STATE := InvSubBytes( STATE );
DEST[127:0] := STATE XOR RoundKey;
DEST[MAXVL-1:128] (Unmodified)
VAESDECLAST (128b and 256b VEX Encoded Versions)
(KL,VL) = (1,128), (2,256)
FOR i = 0 to KL-1:
STATE := SRC1.xmm[i]
RoundKey := SRC2.xmm[i]
STATE := InvShiftRows( STATE )
STATE := InvSubBytes( STATE )
DEST.xmm[i] := STATE XOR RoundKey
DEST[MAXVL-1:VL] := 0
VAESDECLAST (EVEX Encoded Version)
(KL,VL) = (1,128), (2,256), (4,512)
FOR i = 0 to KL-1:
STATE := SRC1.xmm[i]
RoundKey := SRC2.xmm[i]
STATE := InvShiftRows( STATE )
STATE := InvSubBytes( STATE )
DEST.xmm[i] := STATE XOR RoundKey
DEST[MAXVL-1:VL] := 0
Intel C/C++ Compiler Intrinsic Equivalent
(V)AESDECLAST __m128i _mm_aesdeclast (__m128i, __m128i)
VAESDECLAST __m256i _mm256_aesdeclast_epi128(__m256i, __m256i);
VAESDECLAST __m512i _mm512_aesdeclast_epi128(__m512i, __m512i);
SIMD Floating-Point Exceptions
None.
Other Exceptions
See Table 2-21, “Type 4 Class Exception Conditions.”
EVEX-encoded: See Table 2-50, “Type E4NF Class Exception Conditions.”
3-58
Vol. 2A
AESDECLAST-Perform Last Round of an AES Decryption Flow
INSTRUCTION SET REFERENCE, A-L
AESDECWIDE128KL-Perform Ten Rounds of AES Decryption Flow With Key Locker on 8 Blocks
Using 128-Bit Key
Opcode/
Op/
64/32-bit
CPUID Feature
Description
Instruction
En
Mode
Flag
F3 0F 38 D8 !(11):001:bbb
A
V/V
AESKLEWIDE_KL
Decrypt XMM0-7 using 128-bit AES key indicated
AESDECWIDE128KL m384, <XMM0-7>
by handle at m384 and store each resultant block
back to its corresponding register.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operands 2-9
A
N/A
ModRM:r/m (r)
Implicit XMM0-7 (r, w)
Description
The AESDECWIDE128KL1 instruction performs ten rounds of AES to decrypt each of the eight blocks in XMM0-7
using the 128-bit key indicated by the handle from the second operand. It replaces each input block in XMM0-7
with its corresponding decrypted block if the operation succeeds (e.g., does not run into a handle violation failure).
Operation
AESDECWIDE128KL
Handle := UnalignedLoad of 384 bit (SRC);
// Load is not guaranteed to be atomic.
Illegal Handle = (HandleReservedBitSet (Handle) ||
(Handle[0] AND (CPL > 0)) ||
Handle [2] ||
HandleKeyType (Handle) != HANDLE_KEY_TYPE_AES128);
IF (Illegal Handle)
THEN RFLAGS.ZF := 1;
ELSE
(UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate384 (Handle[383:0], IWKey);
IF Authentic == 0 {
THEN RFLAGS.ZF := 1;
ELSE
XMM0 := AES128Decrypt (XMM0, UnwrappedKey) ;
XMM1 := AES128Decrypt (XMM1, UnwrappedKey) ;
XMM2 := AES128Decrypt (XMM2, UnwrappedKey) ;
XMM3 := AES128Decrypt (XMM3, UnwrappedKey) ;
XMM4 := AES128Decrypt (XMM4, UnwrappedKey) ;
XMM5 := AES128Decrypt (XMM5, UnwrappedKey) ;
XMM6 := AES128Decrypt (XMM6, UnwrappedKey) ;
XMM7 := AES128Decrypt (XMM7, UnwrappedKey) ;
RFLAGS.ZF := 0;
FI;
FI;
RFLAGS.OF, SF, AF, PF, CF := 0;
Flags Affected
ZF is set to 0 if the operation succeeded and set to 1 if the operation failed due to a handle violation. The other
arithmetic flags (OF, SF, AF, PF, CF) are cleared to 0.
1. Further details on Key Locker and usage of this instruction can be found here:
https://software.intel.com/content/www/us/en/develop/download/intel-key-locker-specification.html.
AESDECWIDE128KL-Perform Ten Rounds of AES Decryption Flow With Key Locker on 8 Blocks Using 128-Bit Key
Vol. 2A
3-59
INSTRUCTION SET REFERENCE, A-L
Intel C/C++ Compiler Intrinsic Equivalent
AESDECWIDE128KLunsigned char _mm_aesdecwide128kl_u8(__m128i odata[8], const __m128i idata[8], const void* h);
Exceptions (All Operating Modes)
#UD
If the LOCK prefix is used.
If CPUID.07H:ECX.KL [bit 23] = 0.
If CR4.KL = 0.
If CPUID.19H:EBX.AESKLE [bit 0] = 0.
If CR0.EM = 1.
If CR4.OSFXSR = 0.
If CPUID.19H:EBX.WIDE_KL [bit 2] = 0.
#NM
If CR0.TS = 1.
#PF
If a page fault occurs.
#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.
If the memory address is in a non-canonical form.
#SS(0)
If a memory operand effective address is outside the SS segment limit.
If a memory address referencing the SS segment is in a non-canonical form.
3-60
Vol. 2A
AESDECWIDE128KL-Perform Ten Rounds of AES Decryption Flow With Key Locker on 8 Blocks Using 128-Bit Key
INSTRUCTION SET REFERENCE, A-L
AESDECWIDE256KL-Perform 14 Rounds of AES Decryption Flow With Key Locker on 8 Blocks
Using 256-Bit Key
Opcode/
Op/
64/32-bit
CPUID Feature
Description
Instruction
En
Mode
Flag
F3 0F 38 D8 !(11):011:bbb
A
V/V
AESKLEWIDE_KL
Decrypt XMM0-7 using 256-bit AES key indicated
AESDECWIDE256KL m512, <XMM0-7>
by handle at m512 and store each resultant block
back to its corresponding register.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operands 2-9
A
N/A
ModRM:r/m (r)
Implicit XMM0-7 (r, w)
Description
The AESDECWIDE256KL1 instruction performs 14 rounds of AES to decrypt each of the eight blocks in XMM0-7
using the 256-bit key indicated by the handle from the second operand. It replaces each input block in XMM0-7
with its corresponding decrypted block if the operation succeeds (e.g., does not run into a handle violation failure).
Operation
AESDECWIDE256KL
Handle := UnalignedLoad of 512 bit (SRC);
// Load is not guaranteed to be atomic.
Illegal Handle = (HandleReservedBitSet (Handle) ||
(Handle[0] AND (CPL > 0)) ||
Handle [2] ||
HandleKeyType (Handle) != HANDLE_KEY_TYPE_AES256);
IF (Illegal Handle) {
THEN RFLAGS.ZF := 1;
ELSE
(UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate512 (Handle[511:0], IWKey);
IF (Authentic == 0)
THEN RFLAGS.ZF := 1;
ELSE
XMM0 := AES256Decrypt (XMM0, UnwrappedKey) ;
XMM1 := AES256Decrypt (XMM1, UnwrappedKey) ;
XMM2 := AES256Decrypt (XMM2, UnwrappedKey) ;
XMM3 := AES256Decrypt (XMM3, UnwrappedKey) ;
XMM4 := AES256Decrypt (XMM4, UnwrappedKey) ;
XMM5 := AES256Decrypt (XMM5, UnwrappedKey) ;
XMM6 := AES256Decrypt (XMM6, UnwrappedKey) ;
XMM7 := AES256Decrypt (XMM7, UnwrappedKey) ;
RFLAGS.ZF := 0;
FI;
FI;
RFLAGS.OF, SF, AF, PF, CF := 0;
Flags Affected
ZF is set to 0 if the operation succeeded and set to 1 if the operation failed due to a handle violation. The other
arithmetic flags (OF, SF, AF, PF, CF) are cleared to 0.
1. Further details on Key Locker and usage of this instruction can be found here:
https://software.intel.com/content/www/us/en/develop/download/intel-key-locker-specification.html.
AESDECWIDE256KL-Perform 14 Rounds of AES Decryption Flow With Key Locker on 8 Blocks Using 256-Bit Key
Vol. 2A
3-61
INSTRUCTION SET REFERENCE, A-L
Intel C/C++ Compiler Intrinsic Equivalent
AESDECWIDE256KLunsigned char _mm_aesdecwide256kl_u8(__m128i odata[8], const __m128i idata[8], const void* h);
Exceptions (All Operating Modes)
#UD
If the LOCK prefix is used.
If CPUID.07H:ECX.KL [bit 23] = 0.
If CR4.KL = 0.
If CPUID.19H:EBX.AESKLE [bit 0] = 0.
If CR0.EM = 1.
If CR4.OSFXSR = 0.
If CPUID.19H:EBX.WIDE_KL [bit 2] = 0.
#NM
If CR0.TS = 1.
#PF
If a page fault occurs.
#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.
If the memory address is in a non-canonical form.
#SS(0)
If a memory operand effective address is outside the SS segment limit.
If a memory address referencing the SS segment is in a non-canonical form.
3-62
Vol. 2A
AESDECWIDE256KL-Perform 14 Rounds of AES Decryption Flow With Key Locker on 8 Blocks Using 256-Bit Key
INSTRUCTION SET REFERENCE, A-L
AESENC-Perform One Round of an AES Encryption Flow
Opcode/
Op/
64/32-bit
CPUID
Description
Instruction
En
Mode
Feature
Flag
66 0F 38 DC /r
A
V/V
AES
Perform one round of an AES encryption flow, using one
AESENC xmm1, xmm2/m128
128-bit data (state) from xmm1 with one 128-bit round
key from xmm2/m128.
VEX.128.66.0F38.WIG DC /r
B
V/V
AES
Perform one round of an AES encryption flow, using one
VAESENC xmm1, xmm2, xmm3/m128
AVX
128-bit data (state) from xmm2 with one 128-bit round
key from the xmm3/m128; store the result in xmm1.
VEX.256.66.0F38.WIG DC /r
B
V/V
VAES
Perform one round of an AES encryption flow, using two
VAESENC ymm1, ymm2, ymm3/m256
128-bit data (state) from ymm2 with two 128-bit round
keys from the ymm3/m256; store the result in ymm1.
EVEX.128.66.0F38.WIG DC /r
C
V/V
VAES
Perform one round of an AES encryption flow, using one
VAESENC xmm1, xmm2, xmm3/m128
AVX512VL
128-bit data (state) from xmm2 with one 128-bit round
key from the xmm3/m128; store the result in xmm1.
EVEX.256.66.0F38.WIG DC /r
C
V/V
VAES
Perform one round of an AES encryption flow, using two
VAESENC ymm1, ymm2, ymm3/m256
AVX512VL
128-bit data (state) from ymm2 with two 128-bit round
keys from the ymm3/m256; store the result in ymm1.
EVEX.512.66.0F38.WIG DC /r
C
V/V
VAES
Perform one round of an AES encryption flow, using four
VAESENC zmm1, zmm2, zmm3/m512
AVX512F
128-bit data (state) from zmm2 with four 128-bit round
keys from the zmm3/m512; store the result in zmm1.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
B
N/A
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
C
Full Mem
ModRM:reg (w)
EVEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction performs a single round of an AES encryption flow using one/two/four (depending on vector
length) 128-bit data (state) from the first source operand with one/two/four (depending on vector length) round
key(s) from the second source operand, and stores the result in the destination operand.
Use the AESENC instruction for all but the last encryption rounds. For the last encryption round, use the AESENC-
CLAST instruction.
VEX and EVEX encoded versions of the instruction allow 3-operand (non-destructive) operation. The legacy
encoded versions of the instruction require that the first source operand and the destination operand are the same
and must be an XMM register.
The EVEX encoded form of this instruction does not support memory fault suppression.
Operation
AESENC
STATE := SRC1;
RoundKey := SRC2;
STATE := ShiftRows( STATE );
STATE := SubBytes( STATE );
STATE := MixColumns( STATE );
DEST[127:0] := STATE XOR RoundKey;
DEST[MAXVL-1:128] (Unmodified)
AESENC-Perform One Round of an AES Encryption Flow
Vol. 2A
3-63
INSTRUCTION SET REFERENCE, A-L
VAESENC (128b and 256b VEX Encoded Versions)
(KL,VL) = (1,128), (2,256)
FOR I := 0 to KL-1:
STATE := SRC1.xmm[i]
RoundKey := SRC2.xmm[i]
STATE := ShiftRows( STATE )
STATE := SubBytes( STATE )
STATE := MixColumns( STATE )
DEST.xmm[i] := STATE XOR RoundKey
DEST[MAXVL-1:VL] := 0
VAESENC (EVEX Encoded Version)
(KL,VL) = (1,128), (2,256), (4,512)
FOR i := 0 to KL-1:
STATE := SRC1.xmm[i] // xmm[i] is the i’th xmm word in the SIMD register
RoundKey := SRC2.xmm[i]
STATE := ShiftRows( STATE )
STATE := SubBytes( STATE )
STATE := MixColumns( STATE )
DEST.xmm[i] := STATE XOR RoundKey
DEST[MAXVL-1:VL] := 0
Intel C/C++ Compiler Intrinsic Equivalent
(V)AESENC __m128i _mm_aesenc (__m128i, __m128i)
VAESENC __m256i _mm256_aesenc_epi128(__m256i, __m256i);
VAESENC __m512i _mm512_aesenc_epi128(__m512i, __m512i);
SIMD Floating-Point Exceptions
None.
Other Exceptions
See Table 2-21, “Type 4 Class Exception Conditions.”
EVEX-encoded: See Table 2-50, “Type E4NF Class Exception Conditions.”
3-64
Vol. 2A
AESENC-Perform One Round of an AES Encryption Flow
INSTRUCTION SET REFERENCE, A-L
AESENC128KL-Perform Ten Rounds of AES Encryption Flow With Key Locker Using 128-Bit Key
Opcode/
Op/
64/32-bit
CPUID
Description
Instruction
En
Mode
Feature
Flag
F3 0F 38 DC !(11):rrr:bbb
A
V/V
AESKLE
Encrypt xmm using 128-bit AES key indicated by han-
AESENC128KL xmm, m384
dle at m384 and store result in xmm.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
Description
The AESENC128KL1 instruction performs ten rounds of AES to encrypt the first operand using the 128-bit key indi-
cated by the handle from the second operand. It stores the result in the first operand if the operation succeeds
(e.g., does not run into a handle violation failure).
Operation
AESENC128KL
Handle := UnalignedLoad of 384 bit (SRC);
// Load is not guaranteed to be atomic.
Illegal Handle = (
HandleReservedBitSet (Handle) ||
(Handle[0] AND (CPL > 0)) ||
Handle [1] ||
HandleKeyType (Handle) != HANDLE_KEY_TYPE_AES128
);
IF (Illegal Handle) {
THEN RFLAGS.ZF := 1;
ELSE
(UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate384 (Handle[383:0], IWKey);
IF (Authentic == 0)
THEN RFLAGS.ZF := 1;
ELSE
DEST := AES128Encrypt (DEST, UnwrappedKey) ;
RFLAGS.ZF := 0;
FI;
FI;
RFLAGS.OF, SF, AF, PF, CF := 0;
Flags Affected
ZF is set to 0 if the operation succeeded and set to 1 if the operation failed due to a handle violation. The other
arithmetic flags (OF, SF, AF, PF, CF) are cleared to 0.
Intel C/C++ Compiler Intrinsic Equivalent
AESENC128KL unsigned char _mm_aesenc128kl_u8(__m128i* odata, __m128i idata, const void* h);
1. Further details on Key Locker and usage of this instruction can be found here:
AESENC128KL-Perform Ten Rounds of AES Encryption Flow With Key Locker Using 128-Bit Key
Vol. 2A
3-65
INSTRUCTION SET REFERENCE, A-L
Exceptions (All Operating Modes)
#UD
If the LOCK prefix is used.
If CPUID.07H:ECX.KL [bit 23] = 0.
If CR4.KL = 0.
If CPUID.19H:EBX.AESKLE [bit 0] = 0.
If CR0.EM = 1.
If CR4.OSFXSR = 0.
#NM
If CR0.TS = 1.
#PF
If a page fault occurs.
#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.
If the memory address is in a non-canonical form.
#SS(0)
If a memory operand effective address is outside the SS segment limit.
If a memory address referencing the SS segment is in a non-canonical form.
3-66
Vol. 2A
AESENC128KL-Perform Ten Rounds of AES Encryption Flow With Key Locker Using 128-Bit Key
INSTRUCTION SET REFERENCE, A-L
AESENC256KL-Perform 14 Rounds of AES Encryption Flow With Key Locker Using 256-Bit Key
Opcode/
Op/
64/32-bit
CPUID
Description
Instruction
En
Mode
Feature
Flag
F3 0F 38 DE !(11):rrr:bbb
A
V/V
AESKLE
Encrypt xmm using 256-bit AES key indicated by han-
AESENC256KL xmm, m512
dle at m512 and store result in xmm.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
Description
The AESENC256KL1 instruction performs 14 rounds of AES to encrypt the first operand using the 256-bit key indi-
cated by the handle from the second operand. It stores the result in the first operand if the operation succeeds
(e.g., does not run into a handle violation failure).
Operation
AESENC256KL
Handle := UnalignedLoad of 512 bit (SRC);
// Load is not guaranteed to be atomic.
Illegal Handle = (
HandleReservedBitSet (Handle) ||
(Handle[0] AND (CPL > 0)) ||
Handle [1] ||
HandleKeyType (Handle) != HANDLE_KEY_TYPE_AES256
);
IF (Illegal Handle)
THEN RFLAGS.ZF := 1;
ELSE
(UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate512 (Handle[511:0], IWKey);
IF (Authentic == 0)
THEN RFLAGS.ZF := 1;
ELSE
DEST := AES256Encrypt (DEST, UnwrappedKey) ;
RFLAGS.ZF := 0;
FI;
FI;
RFLAGS.OF, SF, AF, PF, CF := 0;
Flags Affected
ZF is set to 0 if the operation succeeded and set to 1 if the operation failed due to a handle violation. The other
arithmetic flags (OF, SF, AF, PF, CF) are cleared to 0.
Intel C/C++ Compiler Intrinsic Equivalent
AESENC256KL unsigned char _mm_aesenc256kl_u8(__m128i* odata, __m128i idata, const void* h);
1. Further details on Key Locker and usage of this instruction can be found here:
AESENC256KL-Perform 14 Rounds of AES Encryption Flow With Key Locker Using 256-Bit Key
Vol. 2A
3-67
INSTRUCTION SET REFERENCE, A-L
Exceptions (All Operating Modes)
#UD
If the LOCK prefix is used.
If CPUID.07H:ECX.KL [bit 23] = 0.
If CR4.KL = 0.
If CPUID.19H:EBX.AESKLE [bit 0] = 0.
If CR0.EM = 1.
If CR4.OSFXSR = 0.
#NM
If CR0.TS = 1.
#PF
If a page fault occurs.
#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.
If the memory address is in a non-canonical form.
#SS(0)
If a memory operand effective address is outside the SS segment limit.
If a memory address referencing the SS segment is in a non-canonical form.
3-68
Vol. 2A
AESENC256KL-Perform 14 Rounds of AES Encryption Flow With Key Locker Using 256-Bit Key
INSTRUCTION SET REFERENCE, A-L
AESENCLAST-Perform Last Round of an AES Encryption Flow
Opcode/
Op/
64/32-bit
CPUID
Description
Instruction
En
Mode
Feature
Flag
66 0F 38 DD /r
A
V/V
AES
Perform the last round of an AES encryption flow,
AESENCLAST xmm1, xmm2/m128
using one 128-bit data (state) from xmm1 with one
128-bit round key from xmm2/m128.
VEX.128.66.0F38.WIG DD /r
B
V/V
AES
Perform the last round of an AES encryption flow,
VAESENCLAST xmm1, xmm2, xmm3/m128
AVX
using one 128-bit data (state) from xmm2 with one
128-bit round key from xmm3/m128; store the result
in xmm1.
VEX.256.66.0F38.WIG DD /r
B
V/V
VAES
Perform the last round of an AES encryption flow,
VAESENCLAST ymm1, ymm2, ymm3/m256
using two 128-bit data (state) from ymm2 with two
128-bit round keys from ymm3/m256; store the
result in ymm1.
EVEX.128.66.0F38.WIG DD /r
C
V/V
VAES
Perform the last round of an AES encryption flow,
VAESENCLAST xmm1, xmm2, xmm3/m128
AVX512VL
using one 128-bit data (state) from xmm2 with one
128-bit round key from xmm3/m128; store the result
in xmm1.
EVEX.256.66.0F38.WIG DD /r
C
V/V
VAES
Perform the last round of an AES encryption flow,
VAESENCLAST ymm1, ymm2, ymm3/m256
AVX512VL
using two 128-bit data (state) from ymm2 with two
128-bit round keys from ymm3/m256; store the
result in ymm1.
EVEX.512.66.0F38.WIG DD /r
C
V/V
VAES
Perform the last round of an AES encryption flow,
VAESENCLAST zmm1, zmm2, zmm3/m512
AVX512F
using four 128-bit data (state) from zmm2 with four
128-bit round keys from zmm3/m512; store the
result in zmm1.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
ModRM:r/m (r)
N/A
N/A
B
N/A
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
C
Full Mem
ModRM:reg (w)
EVEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction performs the last round of an AES encryption flow using one/two/four (depending on vector length)
128-bit data (state) from the first source operand with one/two/four (depending on vector length) round key(s)
from the second source operand, and stores the result in the destination operand.
VEX and EVEX encoded versions of the instruction allows 3-operand (non-destructive) operation. The legacy
encoded versions of the instruction require that the first source operand and the destination operand are the same
and must be an XMM register.
The EVEX encoded form of this instruction does not support memory fault suppression.
AESENCLAST-Perform Last Round of an AES Encryption Flow
Vol. 2A
3-69
INSTRUCTION SET REFERENCE, A-L
Operation
AESENCLAST
STATE := SRC1;
RoundKey := SRC2;
STATE := ShiftRows( STATE );
STATE := SubBytes( STATE );
DEST[127:0] := STATE XOR RoundKey;
DEST[MAXVL-1:128] (Unmodified)
VAESENCLAST (128b and 256b VEX Encoded Versions)
(KL, VL) = (1,128), (2,256)
FOR I=0 to KL-1:
STATE := SRC1.xmm[i]
RoundKey := SRC2.xmm[i]
STATE := ShiftRows( STATE )
STATE := SubBytes( STATE )
DEST.xmm[i] := STATE XOR RoundKey
DEST[MAXVL-1:VL] := 0
VAESENCLAST (EVEX Encoded Version)
(KL,VL) = (1,128), (2,256), (4,512)
FOR i = 0 to KL-1:
STATE := SRC1.xmm[i]
RoundKey := SRC2.xmm[i]
STATE := ShiftRows( STATE )
STATE := SubBytes( STATE )
DEST.xmm[i] := STATE XOR RoundKey
DEST[MAXVL-1:VL] := 0
Intel C/C++ Compiler Intrinsic Equivalent
(V)AESENCLAST __m128i _mm_aesenclast (__m128i, __m128i)
VAESENCLAST __m256i _mm256_aesenclast_epi128(__m256i, __m256i);
VAESENCLAST __m512i _mm512_aesenclast_epi128(__m512i, __m512i);
SIMD Floating-Point Exceptions
None.
Other Exceptions
See Table 2-21, “Type 4 Class Exception Conditions.”
EVEX-encoded: See Table 2-50, “Type E4NF Class Exception Conditions.”
3-70
Vol. 2A
AESENCLAST-Perform Last Round of an AES Encryption Flow

 

 

 

 

 

 

 

Content      ..     15      16      17      18     ..