|
|
ABS(SRC1[I+23: I+16]- TMP1[I+23: I+16]) +
ABS(SRC1[I+31: I+24]- TMP1[I+31: I+24])
TMP_DEST[I+31: I+16] := ABS(SRC1[I+7: I] - TMP1[I+15: I+8]) +
ABS(SRC1[I+15: I+8]- TMP1[I+23: I+16]) +
ABS(SRC1[I+23: I+16]- TMP1[I+31: I+24]) +
ABS(SRC1[I+31: I+24]- TMP1[I+39: I+32])
TMP_DEST[I+47: I+32] := ABS(SRC1[I+39: I+32] - TMP1[I+23: I+16]) +
ABS(SRC1[I+47: I+40]- TMP1[I+31: I+24]) +
ABS(SRC1[I+55: I+48]- TMP1[I+39: I+32]) +
ABS(SRC1[I+63: I+56]- TMP1[I+47: I+40])
TMP_DEST[I+63: I+48] := ABS(SRC1[I+39: I+32] - TMP1[I+31: I+24]) +
ABS(SRC1[I+47: I+40] - TMP1[I+39: I+32]) +
ABS(SRC1[I+55: I+48] - TMP1[I+47: I+40]) +
ABS(SRC1[I+63: I+56] - TMP1[I+55: I+48])
ENDFOR
FOR j := 0 TO KL-1
i := j * 16
IF k1[j] OR *no writemask*
THEN DEST[i+15:i] := TMP_DEST[i+15:i]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+15:i] remains unchanged*
ELSE
; zeroing-masking
DEST[i+15:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:VL] := 0
Intel C/C++ Compiler Intrinsic Equivalent
VDBPSADBW __m512i _mm512_dbsad_epu8(__m512i a, __m512i b int imm8);
VDBPSADBW __m512i _mm512_mask_dbsad_epu8(__m512i s, __mmask32 m, __m512i a, __m512i b int imm8);
VDBPSADBW __m512i _mm512_maskz_dbsad_epu8(__mmask32 m, __m512i a, __m512i b int imm8);
VDBPSADBW __m256i _mm256_dbsad_epu8(__m256i a, __m256i b int imm8);
VDBPSADBW __m256i _mm256_mask_dbsad_epu8(__m256i s, __mmask16 m, __m256i a, __m256i b int imm8);
VDBPSADBW __m256i _mm256_maskz_dbsad_epu8(__mmask16 m, __m256i a, __m256i b int imm8);
VDBPSADBW __m128i _mm_dbsad_epu8(__m128i a, __m128i b int imm8);
VDBPSADBW __m128i _mm_mask_dbsad_epu8(__m128i s, __mmask8 m, __m128i a, __m128i b int imm8);
VDBPSADBW __m128i _mm_maskz_dbsad_epu8(__mmask8 m, __m128i a, __m128i b int imm8);
SIMD Floating-Point Exceptions
None.
Other Exceptions
See Exceptions Type E4NF.nb in Table 2-52, “Type E4NF Class Exception Conditions.”
VDBPSADBW-Double Block Packed Sum-Absolute-Differences (SAD) on Unsigned Bytes
Vol. 2C
5-156
VDIVPH-Divide Packed FP16 Values
Opcode/
Op/
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.128.NP.MAP5.W0 5E /r
A
V/V
(AVX512_FP16
Divide packed FP16 values in xmm2 by packed
VDIVPH xmm1{k1}{z}, xmm2,
AND AVX512VL)
FP16 values in xmm3/m128/m16bcst, and store
xmm3/m128/m16bcst
OR AVX10.1
the result in xmm1 subject to writemask k1.
EVEX.256.NP.MAP5.W0 5E /r
A
V/V
(AVX512_FP16
Divide packed FP16 values in ymm2 by packed
VDIVPH ymm1{k1}{z}, ymm2,
AND AVX512VL)
FP16 values in ymm3/m256/m16bcst, and store
ymm3/m256/m16bcst
OR AVX10.1
the result in ymm1 subject to writemask k1.
EVEX.512.NP.MAP5.W0 5E /r
A
V/V
AVX512_FP16
Divide packed FP16 values in zmm2 by packed
VDIVPH zmm1{k1}{z}, zmm2,
OR AVX10.1
FP16 values in zmm3/m512/m16bcst, and store
zmm3/m512/m16bcst {er}
the result in zmm1 subject to writemask k1.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
Full
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction divides packed FP16 values from the first source operand by the corresponding elements in the
second source operand, storing the packed FP16 result in the destination operand. The destination elements are
updated according to the writemask.
Operation
VDIVPH (EVEX Encoded Versions) When SRC2 Operand is a Register
VL = 128, 256 or 512
KL := VL/16
IF (VL = 512) AND (EVEX.b = 1):
SET_RM(EVEX.RC)
ELSE
SET_RM(MXCSR.RC)
FOR j := 0 TO KL-1:
IF k1[j] OR *no writemask*:
DEST.fp16[j] := SRC1.fp16[j] / SRC2.fp16[j]
ELSE IF *zeroing*:
DEST.fp16[j] := 0
// else dest.fp16[j] remains unchanged
DEST[MAXVL-1:VL] := 0
VDIVPH-Divide Packed FP16 Values
Vol. 2C
5-157
VDIVPH (EVEX Encoded Versions) When SRC2 Operand is a Memory Source
VL = 128, 256 or 512
KL := VL/16
FOR j := 0 TO KL-1:
IF k1[j] OR *no writemask*:
IF EVEX.b = 1:
DEST.fp16[j] := SRC1.fp16[j] / SRC2.fp16[0]
ELSE:
DEST.fp16[j] := SRC1.fp16[j] / SRC2.fp16[j]
ELSE IF *zeroing*:
DEST.fp16[j] := 0
// else dest.fp16[j] remains unchanged
DEST[MAXVL-1:VL] := 0
Intel C/C++ Compiler Intrinsic Equivalent
VDIVPH __m128h _mm_div_ph (__m128h a, __m128h b);
VDIVPH __m128h _mm_mask_div_ph (__m128h src, __mmask8 k, __m128h a, __m128h b);
VDIVPH __m128h _mm_maskz_div_ph (__mmask8 k, __m128h a, __m128h b);
VDIVPH __m256h _mm256_div_ph (__m256h a, __m256h b);
VDIVPH __m256h _mm256_mask_div_ph (__m256h src, __mmask16 k, __m256h a, __m256h b);
VDIVPH __m256h _mm256_maskz_div_ph (__mmask16 k, __m256h a, __m256h b);
VDIVPH __m512h _mm512_div_ph (__m512h a, __m512h b);
VDIVPH __m512h _mm512_mask_div_ph (__m512h src, __mmask32 k, __m512h a, __m512h b);
VDIVPH __m512h _mm512_maskz_div_ph (__mmask32 k, __m512h a, __m512h b);
VDIVPH __m512h _mm512_div_round_ph (__m512h a, __m512h b, int rounding);
VDIVPH __m512h _mm512_mask_div_round_ph (__m512h src, __mmask32 k, __m512h a, __m512h b, int rounding);
VDIVPH __m512h _mm512_maskz_div_round_ph (__mmask32 k, __m512h a, __m512h b, int rounding);
SIMD Floating-Point Exceptions
Invalid, Underflow, Overflow, Precision, Denormal, Zero.
Other Exceptions
EVEX-encoded instructions, see Table 2-48, “Type E2 Class Exception Conditions.”
VDIVPH-Divide Packed FP16 Values
Vol. 2C
5-158
VDIVSH-Divide Scalar FP16 Values
Opcode/
Op/
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.LLIG.F3.MAP5.W0 5E /r
A
V/V
AVX512_FP16
Divide low FP16 value in xmm2 by low FP16
VDIVSH xmm1{k1}{z}, xmm2,
OR AVX10.1
value in xmm3/m16, and store the result in xmm1
xmm3/m16 {er}
subject to writemask k1. Bits 127:16 of xmm2
are copied to xmm1[127:16].
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
Scalar
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction divides the low FP16 value from the first source operand by the corresponding value in the second
source operand, storing the FP16 result in the destination operand. Bits 127:16 of the destination operand are
copied from the corresponding bits of the first source operand. Bits MAXVL-1:128 of the destination operand are
zeroed. The low FP16 element of the destination is updated according to the writemask.
Operation
VDIVSH (EVEX Encoded Versions)
IF EVEX.b = 1 and SRC2 is a register:
SET_RM(EVEX.RC)
ELSE
SET_RM(MXCSR.RC)
IF k1[0] OR *no writemask*:
DEST.fp16[0] := SRC1.fp16[0] / SRC2.fp16[0]
ELSE IF *zeroing*:
DEST.fp16[0] := 0
// else dest.fp16[0] remains unchanged
DEST[127:16] := SRC1[127:16]
DEST[MAXVL-1:128] := 0
Intel C/C++ Compiler Intrinsic Equivalent
VDIVSH __m128h _mm_div_round_sh (__m128h a, __m128h b, int rounding);
VDIVSH __m128h _mm_mask_div_round_sh (__m128h src, __mmask8 k, __m128h a, __m128h b, int rounding);
VDIVSH __m128h _mm_maskz_div_round_sh (__mmask8 k, __m128h a, __m128h b, int rounding);
VDIVSH __m128h _mm_div_sh (__m128h a, __m128h b);
VDIVSH __m128h _mm_mask_div_sh (__m128h src, __mmask8 k, __m128h a, __m128h b);
VDIVSH __m128h _mm_maskz_div_sh (__mmask8 k, __m128h a, __m128h b);
SIMD Floating-Point Exceptions
Invalid, Underflow, Overflow, Precision, Denormal, Zero.
Other Exceptions
EVEX-encoded instructions, see Table 2-49, “Type E3 Class Exception Conditions.”
VDIVSH-Divide Scalar FP16 Values
Vol. 2C
5-159
VDPBF16PS-Dot Product of BF16 Pairs Accumulated Into Packed Single Precision
Opcode/
Op/
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.128.F3.0F38.W0 52 /r
A
V/V
(AVX512_BF16
Multiply BF16 pairs from xmm2 and
VDPBF16PS xmm1{k1}{z}, xmm2,
AND AVX512VL)
xmm3/m128, and accumulate the resulting
xmm3/m128/m32bcst
OR AVX10.1
packed single precision results in xmm1 with
writemask k1.
EVEX.256.F3.0F38.W0 52 /r
A
V/V
(AVX512_BF16
Multiply BF16 pairs from ymm2 and
VDPBF16PS ymm1{k1}{z}, ymm2,
AND AVX512VL)
ymm3/m256, and accumulate the resulting
ymm3/m256/m32bcst
OR AVX10.1
packed single precision results in ymm1 with
writemask k1.
EVEX.512.F3.0F38.W0 52 /r
A
V/V
(AVX512_BF16
Multiply BF16 pairs from zmm2 and
VDPBF16PS zmm1{k1}{z}, zmm2,
AND AVX512F)
zmm3/m512, and accumulate the resulting
zmm3/m512/m32bcst
OR AVX10.1
packed single precision results in zmm1 with
writemask k1.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
Full
ModRM:reg (w)
EVEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction performs a SIMD dot-product of two BF16 pairs and accumulates into a packed single precision
register.
“Round to nearest even” rounding mode is used when doing each accumulation of the FMA. Output denormals are
always flushed to zero and input denormals are always treated as zero. MXCSR is not consulted nor updated.
NaN propagation priorities are described in Table 5-4.
Table 5-4. NaN Propagation Priorities
NaN Priority
Description
Comments
1
src1 low is NaN
Lower part has priority over upper part, i.e., it overrides the upper part.
2
src2 low is NaN
3
src1 high is NaN
Upper part may be overridden if lower has NaN.
4
src2 high is NaN
5
srcdest is NaN
Dest is propagated if no NaN is encountered by src2.
Operation
Define make_fp32(x):
// The x parameter is bfloat16. Pack it in to upper 16b of a dword. The bit pattern is a legal fp32 value. Return that bit pattern.
dword := 0
dword[31:16] := x
RETURN dword
VDPBF16PS-Dot Product of BF16 Pairs Accumulated Into Packed Single Precision
Vol. 2C
5-160
VDPBF16PS srcdest, src1, src2
VL = (128, 256, 512)
KL = VL/32
origdest := srcdest
FOR i := 0 to KL-1:
IF k1[ i ] or *no writemask*:
IF src2 is memory and evex.b == 1:
t := src2.dword[0]
ELSE:
t := src2.dword[ i ]
// FP32 FMA with daz in, ftz out and RNE rounding. MXCSR neither consulted nor updated.
srcdest.fp32[ i ] += make_fp32(src1.bfloat16[2*i+1]) * make_fp32(t.bfloat[1])
srcdest.fp32[ i ] += make_fp32(src1.bfloat16[2*i+0]) * make_fp32(t.bfloat[0])
ELSE IF *zeroing*:
srcdest.dword[ i ] := 0
ELSE: // merge masking, dest element unchanged
srcdest.dword[ i ] := origdest.dword[ i ]
srcdest[MAXVL-1:VL] := 0
Intel C/C++ Compiler Intrinsic Equivalent
VDPBF16PS __m128 _mm_dpbf16_ps(__m128, __m128bh, __m128bh);
VDPBF16PS __m128 _mm_mask_dpbf16_ps( __m128, __mmask8, __m128bh, __m128bh);
VDPBF16PS __m128 _mm_maskz_dpbf16_ps(__mmask8, __m128, __m128bh, __m128bh);
VDPBF16PS __m256 _mm256_dpbf16_ps(__m256, __m256bh, __m256bh);
VDPBF16PS __m256 _mm256_mask_dpbf16_ps(__m256, __mmask8, __m256bh, __m256bh);
VDPBF16PS __m256 _mm256_maskz_dpbf16_ps(__mmask8, __m256, __m256bh, __m256bh);
VDPBF16PS __m512 _mm512_dpbf16_ps(__m512, __m512bh, __m512bh);
VDPBF16PS __m512 _mm512_mask_dpbf16_ps(__m512, __mmask16, __m512bh, __m512bh);
VDPBF16PS __m512 _mm512_maskz_dpbf16_ps(__mmask16, __m512, __m512bh, __m512bh);
SIMD Floating-Point Exceptions
None.
Other Exceptions
See Table 2-51, “Type E4 Class Exception Conditions.”
VDPBF16PS-Dot Product of BF16 Pairs Accumulated Into Packed Single Precision
Vol. 2C
5-161
VERR/VERW-Verify a Segment for Reading or Writing
Opcode/
Op/
64-Bit
Compat/
Description
Instruction
En
Mode
Leg
Mode
0F 00 /4
M
Valid
Valid
Set ZF=1 if segment specified with r/m16 can be read.
VERR r/m16
0F 00 /5
M
Valid
Valid
Set ZF=1 if segment specified with r/m16 can be written.
VERW r/m16
Instruction Operand Encoding
Op/En
Operand 1
Operand 2
Operand 3
Operand 4
M
ModRM:r/m (r)
N/A
N/A
N/A
Description
Verifies whether the code or data segment specified with the source operand is readable (VERR) or writable
(VERW) from the current privilege level (CPL). The source operand is a 16-bit register or a memory location that
contains the segment selector for the segment to be verified. If the segment is accessible and readable (VERR) or
writable (VERW), the ZF flag is set; otherwise, the ZF flag is cleared. Code segments are never verified as writable.
This check cannot be performed on system segments.
To set the ZF flag, the following conditions must be met:
• The segment selector is not NULL.
• The selector must denote a descriptor within the bounds of the descriptor table (GDT or LDT).
• The selector must denote the descriptor of a code or data segment (not that of a system segment or gate).
• For the VERR instruction, the segment must be readable.
• For the VERW instruction, the segment must be a writable data segment.
• If the segment is not a conforming code segment, the segment’s DPL must be greater than or equal to (have
less or the same privilege as) both the CPL and the segment selector's RPL.
The validation performed is the same as is performed when a segment selector is loaded into the DS, ES, FS, or GS
register, and the indicated access (read or write) is performed. The segment selector's value cannot result in a
protection exception, enabling the software to anticipate possible segment access problems.
This instruction’s operation is the same in non-64-bit modes and 64-bit mode. The operand size is fixed at 16 bits.
Operation
IF SRC(Offset) > (GDTR(Limit) or (LDTR(Limit))
THEN ZF := 0; FI;
Read segment descriptor;
IF SegmentDescriptor(DescriptorType) = 0 (* System segment *)
or (SegmentDescriptor(Type) ≠ conforming code segment)
and (CPL > DPL) or (RPL > DPL)
THEN
ZF := 0;
ELSE
IF ((Instruction = VERR) and (Segment readable))
or ((Instruction = VERW) and (Segment writable))
THEN
ZF := 1;
ELSE
ZF := 0;
VERR/VERW-Verify a Segment for Reading or Writing
Vol. 2C
5-162
FI;
FI;
Flags Affected
The ZF flag is set to 1 if the segment is accessible and readable (VERR) or writable (VERW); otherwise, it is set to 0.
Protected Mode Exceptions
The only exceptions generated for these instructions are those related to illegal addressing of the source operand.
#GP(0)
If a memory operand effective address is outside the CS, DS, ES, FS, or GS segment limit.
If the DS, ES, FS, or GS register is used to access memory and it contains a NULL segment
selector.
#SS(0)
If a memory operand effective address is outside the SS segment limit.
#PF(fault-code)
If a page fault occurs.
#AC(0)
If alignment checking is enabled and an unaligned memory reference is made while the
current privilege level is 3.
#UD
If the LOCK prefix is used.
Real-Address Mode Exceptions
#UD
The VERR and VERW instructions are not recognized in real-address mode.
If the LOCK prefix is used.
Virtual-8086 Mode Exceptions
#UD
The VERR and VERW instructions are not recognized in virtual-8086 mode.
If the LOCK prefix is used.
Compatibility Mode Exceptions
Same exceptions as in protected mode.
64-Bit Mode Exceptions
#SS(0)
If a memory address referencing the SS segment is in a non-canonical form.
#GP(0)
If the memory address is in a non-canonical form.
#PF(fault-code)
If a page fault occurs.
#AC(0)
If alignment checking is enabled and an unaligned memory reference is made while the
current privilege level is 3.
#UD
If the LOCK prefix is used.
VERR/VERW-Verify a Segment for Reading or Writing
Vol. 2C
5-163
VEXPANDPD-Load Sparse Packed Double Precision Floating-Point Values From Dense Memory
Opcode/
Op /
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.128.66.0F38.W1 88 /r
A
V/V
(AVX512VL AND
Expand packed double precision floating-point
VEXPANDPD xmm1 {k1}{z},
AVX512F) OR
values from xmm2/m128 to xmm1 using
xmm2/m128
AVX10.1
writemask k1.
EVEX.256.66.0F38.W1 88 /r
A
V/V
(AVX512VL AND
Expand packed double precision floating-point
VEXPANDPD ymm1 {k1}{z}, ymm2/m256
AVX512F) OR
values from ymm2/m256 to ymm1 using
AVX10.1
writemask k1.
EVEX.512.66.0F38.W1 88 /r
A
V/V
AVX512F
Expand packed double precision floating-point
VEXPANDPD zmm1 {k1}{z}, zmm2/m512
OR AVX10.1
values from zmm2/m512 to zmm1 using
writemask k1.
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
Tuple1 Scalar
ModRM:reg (w)
ModRM:r/m (r)
N/A
N/A
Description
Expand (load) up to 8/4/2, contiguous, double precision floating-point values of the input vector in the source
operand (the second operand) to sparse elements in the destination operand (the first operand) selected by the
writemask k1.
The destination operand is a ZMM/YMM/XMM register, the source operand can be a ZMM/YMM/XMM register or a
512/256/128-bit memory location.
The input vector starts from the lowest element in the source operand. The writemask register k1 selects the desti-
nation elements (a partial vector or sparse elements if less than 8 elements) to be replaced by the ascending
elements in the input vector. Destination elements not selected by the writemask k1 are either unmodified or
zeroed, depending on EVEX.z.
EVEX.vvvv is reserved and must be 1111b otherwise instructions will #UD.
Note that the compressed displacement assumes a pre-scaling (N) corresponding to the size of one single element
instead of the size of the full vector.
VEXPANDPD-Load Sparse Packed Double Precision Floating-Point Values From Dense Memory
Vol. 2C
5-164
Operation
VEXPANDPD (EVEX Encoded Versions)
(KL, VL) = (2, 128), (4, 256), (8, 512)
k := 0
FOR j := 0 TO KL-1
i := j * 64
IF k1[j] OR *no writemask*
THEN
DEST[i+63:i] := SRC[k+63:k];
k := k + 64
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+63:i] remains unchanged*
ELSE
; zeroing-masking
THEN DEST[i+63:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:VL] := 0
Intel C/C++ Compiler Intrinsic Equivalent
VEXPANDPD __m512d _mm512_mask_expand_pd( __m512d s, __mmask8 k, __m512d a);
VEXPANDPD __m512d _mm512_maskz_expand_pd( __mmask8 k, __m512d a);
VEXPANDPD __m512d _mm512_mask_expandloadu_pd( __m512d s, __mmask8 k, void * a);
VEXPANDPD __m512d _mm512_maskz_expandloadu_pd( __mmask8 k, void * a);
VEXPANDPD __m256d _mm256_mask_expand_pd( __m256d s, __mmask8 k, __m256d a);
VEXPANDPD __m256d _mm256_maskz_expand_pd( __mmask8 k, __m256d a);
VEXPANDPD __m256d _mm256_mask_expandloadu_pd( __m256d s, __mmask8 k, void * a);
VEXPANDPD __m256d _mm256_maskz_expandloadu_pd( __mmask8 k, void * a);
VEXPANDPD __m128d _mm_mask_expand_pd( __m128d s, __mmask8 k, __m128d a);
VEXPANDPD __m128d _mm_maskz_expand_pd( __mmask8 k, __m128d a);
VEXPANDPD __m128d _mm_mask_expandloadu_pd( __m128d s, __mmask8 k, void * a);
VEXPANDPD __m128d _mm_maskz_expandloadu_pd( __mmask8 k, void * a);
SIMD Floating-Point Exceptions
None.
Other Exceptions
See Exceptions Type E4.nb in Table 2-51, “Type E4 Class Exception Conditions.”
Additionally:
#UD
If EVEX.vvvv != 1111B.
VEXPANDPD-Load Sparse Packed Double Precision Floating-Point Values From Dense Memory
Vol. 2C
5-165
VEXPANDPS-Load Sparse Packed Single Precision Floating-Point Values From Dense Memory
Opcode/
Op /
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.128.66.0F38.W0 88 /r
A
V/V
(AVX512VL AND
Expand packed single precision floating-point
VEXPANDPS xmm1 {k1}{z}, xmm2/m128
AVX512F) OR
values from xmm2/m128 to xmm1 using
AVX10.1
writemask k1.
EVEX.256.66.0F38.W0 88 /r
A
V/V
(AVX512VL AND
Expand packed single precision floating-point
VEXPANDPS ymm1 {k1}{z}, ymm2/m256
AVX512F) OR
values from ymm2/m256 to ymm1 using
AVX10.1
writemask k1.
EVEX.512.66.0F38.W0 88 /r
A
V/V
AVX512F
Expand packed single precision floating-point
VEXPANDPS zmm1 {k1}{z}, zmm2/m512
OR AVX10.1
values from zmm2/m512 to zmm1 using
writemask k1.
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
Tuple1 Scalar
ModRM:reg (w)
ModRM:r/m (r)
N/A
N/A
Description
Expand (load) up to 16/8/4, contiguous, single precision floating-point values of the input vector in the source
operand (the second operand) to sparse elements of the destination operand (the first operand) selected by the
writemask k1.
The destination operand is a ZMM/YMM/XMM register, the source operand can be a ZMM/YMM/XMM register or a
512/256/128-bit memory location.
The input vector starts from the lowest element in the source operand. The writemask k1 selects the destination
elements (a partial vector or sparse elements if less than 16 elements) to be replaced by the ascending elements
in the input vector. Destination elements not selected by the writemask k1 are either unmodified or zeroed,
depending on EVEX.z.
EVEX.vvvv is reserved and must be 1111b otherwise instructions will #UD.
Note that the compressed displacement assumes a pre-scaling (N) corresponding to the size of one single element
instead of the size of the full vector.
VEXPANDPS-Load Sparse Packed Single Precision Floating-Point Values From Dense Memory
Vol. 2C
5-166
Operation
VEXPANDPS (EVEX Encoded Versions)
(KL, VL) = (4, 128), (8, 256), (16, 512)
k := 0
FOR j := 0 TO KL-1
i := j * 32
IF k1[j] OR *no writemask*
THEN
DEST[i+31:i] := SRC[k+31:k];
k := k + 32
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
Intel C/C++ Compiler Intrinsic Equivalent
VEXPANDPS __m512 _mm512_mask_expand_ps( __m512 s, __mmask16 k, __m512 a);
VEXPANDPS __m512 _mm512_maskz_expand_ps( __mmask16 k, __m512 a);
VEXPANDPS __m512 _mm512_mask_expandloadu_ps( __m512 s, __mmask16 k, void * a);
VEXPANDPS __m512 _mm512_maskz_expandloadu_ps( __mmask16 k, void * a);
VEXPANDPD __m256 _mm256_mask_expand_ps( __m256 s, __mmask8 k, __m256 a);
VEXPANDPD __m256 _mm256_maskz_expand_ps( __mmask8 k, __m256 a);
VEXPANDPD __m256 _mm256_mask_expandloadu_ps( __m256 s, __mmask8 k, void * a);
VEXPANDPD __m256 _mm256_maskz_expandloadu_ps( __mmask8 k, void * a);
VEXPANDPD __m128 _mm_mask_expand_ps( __m128 s, __mmask8 k, __m128 a);
VEXPANDPD __m128 _mm_maskz_expand_ps( __mmask8 k, __m128 a);
VEXPANDPD __m128 _mm_mask_expandloadu_ps( __m128 s, __mmask8 k, void * a);
VEXPANDPD __m128 _mm_maskz_expandloadu_ps( __mmask8 k, void * a);
SIMD Floating-Point Exceptions
None.
Other Exceptions
See Exceptions Type E4.nb in Table 2-51, “Type E4 Class Exception Conditions.”
Additionally:
#UD
If EVEX.vvvv != 1111B.
VEXPANDPS-Load Sparse Packed Single Precision Floating-Point Values From Dense Memory
Vol. 2C
5-167
VEXTRACTF128/VEXTRACTF32x4/VEXTRACTF64x2/VEXTRACTF32x8/VEXTRACTF64x4-
Extract Packed Floating-Point Values
Opcode/
Op /
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
VEX.256.66.0F3A.W0 19 /r ib
A
V/V
AVX
Extract 128 bits of packed floating-point values
VEXTRACTF128 xmm1/m128, ymm2,
from ymm2 and store results in xmm1/m128.
imm8
EVEX.256.66.0F3A.W0 19 /r ib
C
V/V
(AVX512VL AND
Extract 128 bits of packed single precision
VEXTRACTF32X4 xmm1/m128 {k1}{z},
AVX512F) OR
floating-point values from ymm2 and store
ymm2, imm8
AVX10.1
results in xmm1/m128 subject to writemask k1.
EVEX.512.66.0F3A.W0 19 /r ib
C
V/V
AVX512F
Extract 128 bits of packed single precision
VEXTRACTF32x4 xmm1/m128 {k1}{z},
OR AVX10.1
floating-point values from zmm2 and store
zmm2, imm8
results in xmm1/m128 subject to writemask k1.
EVEX.256.66.0F3A.W1 19 /r ib
B
V/V
(AVX512VL AND
Extract 128 bits of packed double precision
VEXTRACTF64X2 xmm1/m128 {k1}{z},
AVX512DQ) OR
floating-point values from ymm2 and store
ymm2, imm8
AVX10.1
results in xmm1/m128 subject to writemask k1.
EVEX.512.66.0F3A.W1 19 /r ib
B
V/V
AVX512DQ
Extract 128 bits of packed double precision
VEXTRACTF64X2 xmm1/m128 {k1}{z},
OR AVX10.1
floating-point values from zmm2 and store
zmm2, imm8
results in xmm1/m128 subject to writemask k1.
EVEX.512.66.0F3A.W0 1B /r ib
D
V/V
AVX512DQ
Extract 256 bits of packed single precision
VEXTRACTF32X8 ymm1/m256 {k1}{z},
OR AVX10.1
floating-point values from zmm2 and store
zmm2, imm8
results in ymm1/m256 subject to writemask k1.
EVEX.512.66.0F3A.W1 1B /r ib
C
V/V
AVX512F
Extract 256 bits of packed double precision
VEXTRACTF64x4 ymm1/m256 {k1}{z},
OR AVX10.1
floating-point values from zmm2 and store
zmm2, imm8
results in ymm1/m256 subject to writemask k1.
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:r/m (w)
ModRM:reg (r)
imm8
N/A
B
Tuple2
ModRM:r/m (w)
ModRM:reg (r)
imm8
N/A
C
Tuple4
ModRM:r/m (w)
ModRM:reg (r)
imm8
N/A
D
Tuple8
ModRM:r/m (w)
ModRM:reg (r)
imm8
N/A
Description
VEXTRACTF128/VEXTRACTF32x4 and VEXTRACTF64x2 extract 128-bits of single precision floating-point values
from the source operand (the second operand) and store to the low 128-bit of the destination operand (the first
operand). The 128-bit data extraction occurs at an 128-bit granular offset specified by imm8[0] (256-bit) or
imm8[1:0] as the multiply factor. The destination may be either a vector register or an 128-bit memory location.
VEXTRACTF32x4: The low 128-bit of the destination operand is updated at 32-bit granularity according to the
writemask.
VEXTRACTF32x8 and VEXTRACTF64x4 extract 256-bits of double precision floating-point values from the source
operand (second operand) and store to the low 256-bit of the destination operand (the first operand). The 256-bit
data extraction occurs at an 256-bit granular offset specified by imm8[0] (256-bit) or imm8[0] as the multiply
factor The destination may be either a vector register or a 256-bit memory location.
VEXTRACTF64x4: The low 256-bit of the destination operand is updated at 64-bit granularity according to the
writemask.
VEX.vvvv and EVEX.vvvv are reserved and must be 1111b otherwise instructions will #UD.
The high 6 bits of the immediate are ignored.
VEXTRACTF128/VEXTRACTF32x4/VEXTRACTF64x2/VEXTRACTF32x8/VEXTRACTF64x4- Extract Packed Floating-Point Values
Vol. 2C
5-168
If VEXTRACTF128 is encoded with VEX.L= 0, an attempt to execute the instruction encoded with VEX.L= 0 will
cause an #UD exception.
Operation
VEXTRACTF32x4 (EVEX Encoded Versions) When Destination is a Register
VL = 256, 512
IF VL = 256
CASE (imm8[0]) OF
0: TMP_DEST[127:0] := SRC1[127:0]
1: TMP_DEST[127:0] := SRC1[255:128]
ESAC.
FI;
IF VL = 512
CASE (imm8[1:0]) OF
00: TMP_DEST[127:0] := SRC1[127:0]
01: TMP_DEST[127:0] := SRC1[255:128]
10: TMP_DEST[127:0] := SRC1[383:256]
11: TMP_DEST[127:0] := SRC1[511:384]
ESAC.
FI;
FOR j := 0 TO 3
i := j * 32
IF k1[j] OR *no writemask*
THEN DEST[i+31:i] := TMP_DEST[i+31:i]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+31:i] remains unchanged*
ELSE *zeroing-masking*
; zeroing-masking
DEST[i+31:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:128] := 0
VEXTRACTF32x4 (EVEX Encoded Versions) When Destination is Memory
VL = 256, 512
IF VL = 256
CASE (imm8[0]) OF
0: TMP_DEST[127:0] := SRC1[127:0]
1: TMP_DEST[127:0] := SRC1[255:128]
ESAC.
FI;
IF VL = 512
CASE (imm8[1:0]) OF
00: TMP_DEST[127:0] := SRC1[127:0]
01: TMP_DEST[127:0] := SRC1[255:128]
10: TMP_DEST[127:0] := SRC1[383:256]
11: TMP_DEST[127:0] := SRC1[511:384]
ESAC.
FI;
FOR j := 0 TO 3
i := j * 32
IF k1[j] OR *no writemask*
VEXTRACTF128/VEXTRACTF32x4/VEXTRACTF64x2/VEXTRACTF32x8/VEXTRACTF64x4- Extract Packed Floating-Point Values
Vol. 2C
5-169
THEN DEST[i+31:i] := TMP_DEST[i+31:i]
ELSE *DEST[i+31:i] remains unchanged*
; merging-masking
FI;
ENDFOR
VEXTRACTF64x2 (EVEX Encoded Versions) When Destination is a Register
VL = 256, 512
IF VL = 256
CASE (imm8[0]) OF
0: TMP_DEST[127:0] := SRC1[127:0]
1: TMP_DEST[127:0] := SRC1[255:128]
ESAC.
FI;
IF VL = 512
CASE (imm8[1:0]) OF
00: TMP_DEST[127:0] := SRC1[127:0]
01: TMP_DEST[127:0] := SRC1[255:128]
10: TMP_DEST[127:0] := SRC1[383:256]
11: TMP_DEST[127:0] := SRC1[511:384]
ESAC.
FI;
FOR j := 0 TO 1
i := j * 64
IF k1[j] OR *no writemask*
THEN DEST[i+63:i] := TMP_DEST[i+63:i]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+63:i] remains unchanged*
ELSE *zeroing-masking*
; zeroing-masking
DEST[i+63:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:128] := 0
VEXTRACTF64x2 (EVEX Encoded Versions) When Destination is Memory
VL = 256, 512
IF VL = 256
CASE (imm8[0]) OF
0: TMP_DEST[127:0] := SRC1[127:0]
1: TMP_DEST[127:0] := SRC1[255:128]
ESAC.
FI;
IF VL = 512
CASE (imm8[1:0]) OF
00: TMP_DEST[127:0] := SRC1[127:0]
01: TMP_DEST[127:0] := SRC1[255:128]
10: TMP_DEST[127:0] := SRC1[383:256]
11: TMP_DEST[127:0] := SRC1[511:384]
ESAC.
FI;
FOR j := 0 TO 1
VEXTRACTF128/VEXTRACTF32x4/VEXTRACTF64x2/VEXTRACTF32x8/VEXTRACTF64x4- Extract Packed Floating-Point Values
Vol. 2C
5-170
i := j * 64
IF k1[j] OR *no writemask*
THEN DEST[i+63:i] := TMP_DEST[i+63:i]
ELSE *DEST[i+63:i] remains unchanged*
; merging-masking
FI;
ENDFOR
VEXTRACTF32x8 (EVEX.U1.512 Encoded Version) When Destination is a Register
VL = 512
CASE (imm8[0]) OF
0: TMP_DEST[255:0] := SRC1[255:0]
1: TMP_DEST[255:0] := SRC1[511:256]
ESAC.
FOR j := 0 TO 7
i := j * 32
IF k1[j] OR *no writemask*
THEN DEST[i+31:i] := TMP_DEST[i+31:i]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+31:i] remains unchanged*
ELSE *zeroing-masking*
; zeroing-masking
DEST[i+31:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:256] := 0
VEXTRACTF32x8 (EVEX.U1.512 Encoded Version) When Destination is Memory
CASE (imm8[0]) OF
0: TMP_DEST[255:0] := SRC1[255:0]
1: TMP_DEST[255:0] := SRC1[511:256]
ESAC.
FOR j := 0 TO 7
i := j * 32
IF k1[j] OR *no writemask*
THEN DEST[i+31:i] := TMP_DEST[i+31:i]
ELSE *DEST[i+31:i] remains unchanged*
; merging-masking
FI;
ENDFOR
VEXTRACTF64x4 (EVEX.512 Encoded Version) When Destination is a Register
VL = 512
CASE (imm8[0]) OF
0: TMP_DEST[255:0] := SRC1[255:0]
1: TMP_DEST[255:0] := SRC1[511:256]
ESAC.
FOR j := 0 TO 3
i := j * 64
IF k1[j] OR *no writemask*
THEN DEST[i+63:i] := TMP_DEST[i+63:i]
ELSE
VEXTRACTF128/VEXTRACTF32x4/VEXTRACTF64x2/VEXTRACTF32x8/VEXTRACTF64x4- Extract Packed Floating-Point Values
Vol. 2C
5-171
IF *merging-masking*
; merging-masking
THEN *DEST[i+63:i] remains unchanged*
ELSE *zeroing-masking*
; zeroing-masking
DEST[i+63:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:256] := 0
VEXTRACTF64x4 (EVEX.512 Encoded Version) When Destination is Memory
CASE (imm8[0]) OF
0: TMP_DEST[255:0] := SRC1[255:0]
1: TMP_DEST[255:0] := SRC1[511:256]
ESAC.
FOR j := 0 TO 3
i := j * 64
IF k1[j] OR *no writemask*
THEN DEST[i+63:i] := TMP_DEST[i+63:i]
ELSE
; merging-masking
*DEST[i+63:i] remains unchanged*
FI;
ENDFOR
VEXTRACTF128 (Memory Destination Form)
CASE (imm8[0]) OF
0: DEST[127:0] := SRC1[127:0]
1: DEST[127:0] := SRC1[255:128]
ESAC.
VEXTRACTF128 (Register Destination Form)
CASE (imm8[0]) OF
0: DEST[127:0] := SRC1[127:0]
1: DEST[127:0] := SRC1[255:128]
ESAC.
DEST[MAXVL-1:128] := 0
Intel C/C++ Compiler Intrinsic Equivalent
VEXTRACTF32x4 __m128 _mm512_extractf32x4_ps(__m512 a, const int nidx);
VEXTRACTF32x4 __m128 _mm512_mask_extractf32x4_ps(__m128 s, __mmask8 k, __m512 a, const int nidx);
VEXTRACTF32x4 __m128 _mm512_maskz_extractf32x4_ps( __mmask8 k, __m512 a, const int nidx);
VEXTRACTF32x4 __m128 _mm256_extractf32x4_ps(__m256 a, const int nidx);
VEXTRACTF32x4 __m128 _mm256_mask_extractf32x4_ps(__m128 s, __mmask8 k, __m256 a, const int nidx);
VEXTRACTF32x4 __m128 _mm256_maskz_extractf32x4_ps( __mmask8 k, __m256 a, const int nidx);
VEXTRACTF32x8 __m256 _mm512_extractf32x8_ps(__m512 a, const int nidx);
VEXTRACTF32x8 __m256 _mm512_mask_extractf32x8_ps(__m256 s, __mmask8 k, __m512 a, const int nidx);
VEXTRACTF32x8 __m256 _mm512_maskz_extractf32x8_ps( __mmask8 k, __m512 a, const int nidx);
VEXTRACTF64x2 __m128d _mm512_extractf64x2_pd(__m512d a, const int nidx);
VEXTRACTF64x2 __m128d _mm512_mask_extractf64x2_pd(__m128d s, __mmask8 k, __m512d a, const int nidx);
VEXTRACTF64x2 __m128d _mm512_maskz_extractf64x2_pd( __mmask8 k, __m512d a, const int nidx);
VEXTRACTF64x2 __m128d _mm256_extractf64x2_pd(__m256d a, const int nidx);
VEXTRACTF64x2 __m128d _mm256_mask_extractf64x2_pd(__m128d s, __mmask8 k, __m256d a, const int nidx);
VEXTRACTF64x2 __m128d _mm256_maskz_extractf64x2_pd( __mmask8 k, __m256d a, const int nidx);
VEXTRACTF64x4 __m256d _mm512_extractf64x4_pd( __m512d a, const int nidx);
VEXTRACTF128/VEXTRACTF32x4/VEXTRACTF64x2/VEXTRACTF32x8/VEXTRACTF64x4- Extract Packed Floating-Point Values
Vol. 2C
5-172
VEXTRACTF64x4 __m256d _mm512_mask_extractf64x4_pd(__m256d s, __mmask8 k, __m512d a, const int nidx);
VEXTRACTF64x4 __m256d _mm512_maskz_extractf64x4_pd( __mmask8 k, __m512d a, const int nidx);
VEXTRACTF128 __m128 _mm256_extractf128_ps (__m256 a, int offset);
VEXTRACTF128 __m128d _mm256_extractf128_pd (__m256d a, int offset);
VEXTRACTF128 __m128i_mm256_extractf128_si256(__m256i a, int offset);
SIMD Floating-Point Exceptions
None.
Other Exceptions
VEX-encoded instructions, see Table 2-23, “Type 6 Class Exception Conditions.”
EVEX-encoded instructions, see Table 2-56, “Type E6NF Class Exception Conditions.”
Additionally:
#UD
IF VEX.L = 0.
#UD
If VEX.vvvv != 1111B or EVEX.vvvv != 1111B.
VEXTRACTF128/VEXTRACTF32x4/VEXTRACTF64x2/VEXTRACTF32x8/VEXTRACTF64x4- Extract Packed Floating-Point Values
Vol. 2C
5-173
VEXTRACTI128/VEXTRACTI32x4/VEXTRACTI64x2/VEXTRACTI32x8/VEXTRACTI64x4-Extract
Packed Integer Values
Opcode/
Op /
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
VEX.256.66.0F3A.W0 39 /r ib
A
V/V
AVX2
Extract 128 bits of integer data from ymm2
VEXTRACTI128 xmm1/m128, ymm2,
and store results in xmm1/m128.
imm8
EVEX.256.66.0F3A.W0 39 /r ib
C
V/V
(AVX512VL AND
Extract 128 bits of double-word integer values
VEXTRACTI32X4 xmm1/m128 {k1}{z},
AVX512F) OR
from ymm2 and store results in xmm1/m128
ymm2, imm8
AVX10.1
subject to writemask k1.
EVEX.512.66.0F3A.W0 39 /r ib
C
V/V
AVX512F
Extract 128 bits of double-word integer values
VEXTRACTI32x4 xmm1/m128 {k1}{z},
OR AVX10.1
from zmm2 and store results in xmm1/m128
zmm2, imm8
subject to writemask k1.
EVEX.256.66.0F3A.W1 39 /r ib
B
V/V
(AVX512VL AND
Extract 128 bits of quad-word integer values
VEXTRACTI64X2 xmm1/m128 {k1}{z},
AVX512DQ) OR
from ymm2 and store results in xmm1/m128
ymm2, imm8
AVX10.1
subject to writemask k1.
EVEX.512.66.0F3A.W1 39 /r ib
B
V/V
AVX512DQ
Extract 128 bits of quad-word integer values
VEXTRACTI64X2 xmm1/m128 {k1}{z},
OR AVX10.1
from zmm2 and store results in xmm1/m128
zmm2, imm8
subject to writemask k1.
EVEX.512.66.0F3A.W0 3B /r ib
D
V/V
AVX512DQ
Extract 256 bits of double-word integer values
VEXTRACTI32X8 ymm1/m256 {k1}{z},
OR AVX10.1
from zmm2 and store results in ymm1/m256
zmm2, imm8
subject to writemask k1.
EVEX.512.66.0F3A.W1 3B /r ib
C
V/V
AVX512F
Extract 256 bits of quad-word integer values
VEXTRACTI64x4 ymm1/m256 {k1}{z},
OR AVX10.1
from zmm2 and store results in ymm1/m256
zmm2, imm8
subject to writemask k1.
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:r/m (w)
ModRM:reg (r)
imm8
N/A
B
Tuple2
ModRM:r/m (w)
ModRM:reg (r)
imm8
N/A
C
Tuple4
ModRM:r/m (w)
ModRM:reg (r)
imm8
N/A
D
Tuple8
ModRM:r/m (w)
ModRM:reg (r)
imm8
N/A
Description
VEXTRACTI128/VEXTRACTI32x4 and VEXTRACTI64x2 extract 128-bits of doubleword integer values from the
source operand (the second operand) and store to the low 128-bit of the destination operand (the first operand).
The 128-bit data extraction occurs at an 128-bit granular offset specified by imm8[0] (256-bit) or imm8[1:0] as
the multiply factor. The destination may be either a vector register or an 128-bit memory location.
VEXTRACTI32x4: The low 128-bit of the destination operand is updated at 32-bit granularity according to the
writemask.
VEXTRACTI64x2: The low 128-bit of the destination operand is updated at 64-bit granularity according to the
writemask.
VEXTRACTI32x8 and VEXTRACTI64x4 extract 256-bits of quadword integer values from the source operand (the
second operand) and store to the low 256-bit of the destination operand (the first operand). The 256-bit data
extraction occurs at an 256-bit granular offset specified by imm8[0] (256-bit) or imm8[0] as the multiply factor
The destination may be either a vector register or a 256-bit memory location.
VEXTRACTI32x8: The low 256-bit of the destination operand is updated at 32-bit granularity according to the
writemask.
VEXTRACTI128/VEXTRACTI32x4/VEXTRACTI64x2/VEXTRACTI32x8/VEXTRACTI64x4-Extract Packed Integer Values
Vol. 2C
5-174
VEXTRACTI64x4: The low 256-bit of the destination operand is updated at 64-bit granularity according to the
writemask.
VEX.vvvv and EVEX.vvvv are reserved and must be 1111b otherwise instructions will #UD.
The high 7 bits (6 bits in EVEX.512) of the immediate are ignored.
If VEXTRACTI128 is encoded with VEX.L= 0, an attempt to execute the instruction encoded with VEX.L= 0 will
cause an #UD exception.
Operation
VEXTRACTI32x4 (EVEX encoded versions) when destination is a register
VL = 256, 512
IF VL = 256
CASE (imm8[0]) OF
0: TMP_DEST[127:0] := SRC1[127:0]
1: TMP_DEST[127:0] := SRC1[255:128]
ESAC.
FI;
IF VL = 512
CASE (imm8[1:0]) OF
00: TMP_DEST[127:0] := SRC1[127:0]
01: TMP_DEST[127:0] := SRC1[255:128]
10: TMP_DEST[127:0] := SRC1[383:256]
11: TMP_DEST[127:0] := SRC1[511:384]
ESAC.
FI;
FOR j := 0 TO 3
i := j * 32
IF k1[j] OR *no writemask*
THEN DEST[i+31:i] := TMP_DEST[i+31:i]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+31:i] remains unchanged*
ELSE *zeroing-masking*
; zeroing-masking
DEST[i+31:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:128] := 0
VEXTRACTI32x4 (EVEX encoded versions) when destination is memory
VL = 256, 512
IF VL = 256
CASE (imm8[0]) OF
0: TMP_DEST[127:0] := SRC1[127:0]
1: TMP_DEST[127:0] := SRC1[255:128]
ESAC.
FI;
IF VL = 512
CASE (imm8[1:0]) OF
00: TMP_DEST[127:0] := SRC1[127:0]
01: TMP_DEST[127:0] := SRC1[255:128]
10: TMP_DEST[127:0] := SRC1[383:256]
11: TMP_DEST[127:0] := SRC1[511:384]
ESAC.
VEXTRACTI128/VEXTRACTI32x4/VEXTRACTI64x2/VEXTRACTI32x8/VEXTRACTI64x4-Extract Packed Integer Values
Vol. 2C
5-175
FI;
FOR j := 0 TO 3
i := j * 32
IF k1[j] OR *no writemask*
THEN DEST[i+31:i] := TMP_DEST[i+31:i]
ELSE *DEST[i+31:i] remains unchanged*
; merging-masking
FI;
ENDFOR
VEXTRACTI64x2 (EVEX encoded versions) when destination is a register
VL = 256, 512
IF VL = 256
CASE (imm8[0]) OF
0: TMP_DEST[127:0] := SRC1[127:0]
1: TMP_DEST[127:0] := SRC1[255:128]
ESAC.
FI;
IF VL = 512
CASE (imm8[1:0]) OF
00: TMP_DEST[127:0] := SRC1[127:0]
01: TMP_DEST[127:0] := SRC1[255:128]
10: TMP_DEST[127:0] := SRC1[383:256]
11: TMP_DEST[127:0] := SRC1[511:384]
ESAC.
FI;
FOR j := 0 TO 1
i := j * 64
IF k1[j] OR *no writemask*
THEN DEST[i+63:i] := TMP_DEST[i+63:i]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+63:i] remains unchanged*
ELSE *zeroing-masking*
; zeroing-masking
DEST[i+63:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:128] := 0
VEXTRACTI64x2 (EVEX encoded versions) when destination is memory
VL = 256, 512
IF VL = 256
CASE (imm8[0]) OF
0: TMP_DEST[127:0] := SRC1[127:0]
1: TMP_DEST[127:0] := SRC1[255:128]
ESAC.
FI;
IF VL = 512
CASE (imm8[1:0]) OF
00: TMP_DEST[127:0] := SRC1[127:0]
01: TMP_DEST[127:0] := SRC1[255:128]
10: TMP_DEST[127:0] := SRC1[383:256]
VEXTRACTI128/VEXTRACTI32x4/VEXTRACTI64x2/VEXTRACTI32x8/VEXTRACTI64x4-Extract Packed Integer Values
Vol. 2C
5-176
11: TMP_DEST[127:0] := SRC1[511:384]
ESAC.
FI;
FOR j := 0 TO 1
i := j * 64
IF k1[j] OR *no writemask*
THEN DEST[i+63:i] := TMP_DEST[i+63:i]
ELSE *DEST[i+63:i] remains unchanged*
; merging-masking
FI;
ENDFOR
VEXTRACTI32x8 (EVEX.U1.512 encoded version) when destination is a register
VL = 512
CASE (imm8[0]) OF
0: TMP_DEST[255:0] := SRC1[255:0]
1: TMP_DEST[255:0] := SRC1[511:256]
ESAC.
FOR j := 0 TO 7
i := j * 32
IF k1[j] OR *no writemask*
THEN DEST[i+31:i] := TMP_DEST[i+31:i]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+31:i] remains unchanged*
ELSE *zeroing-masking*
; zeroing-masking
DEST[i+31:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:256] := 0
VEXTRACTI32x8 (EVEX.U1.512 encoded version) when destination is memory
CASE (imm8[0]) OF
0: TMP_DEST[255:0] := SRC1[255:0]
1: TMP_DEST[255:0] := SRC1[511:256]
ESAC.
FOR j := 0 TO 7
i := j * 32
IF k1[j] OR *no writemask*
THEN DEST[i+31:i] := TMP_DEST[i+31:i]
ELSE *DEST[i+31:i] remains unchanged*
; merging-masking
FI;
ENDFOR
VEXTRACTI128/VEXTRACTI32x4/VEXTRACTI64x2/VEXTRACTI32x8/VEXTRACTI64x4-Extract Packed Integer Values
Vol. 2C
5-177
VEXTRACTI64x4 (EVEX.512 encoded version) when destination is a register
VL = 512
CASE (imm8[0]) OF
0: TMP_DEST[255:0] := SRC1[255:0]
1: TMP_DEST[255:0] := SRC1[511:256]
ESAC.
FOR j := 0 TO 3
i := j * 64
IF k1[j] OR *no writemask*
THEN DEST[i+63:i] := TMP_DEST[i+63:i]
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+63:i] remains unchanged*
ELSE *zeroing-masking*
; zeroing-masking
DEST[i+63:i] := 0
FI
FI;
ENDFOR
DEST[MAXVL-1:256] := 0
VEXTRACTI64x4 (EVEX.512 encoded version) when destination is memory
CASE (imm8[0]) OF
0: TMP_DEST[255:0] := SRC1[255:0]
1: TMP_DEST[255:0] := SRC1[511:256]
ESAC.
FOR j := 0 TO 3
i := j * 64
IF k1[j] OR *no writemask*
THEN DEST[i+63:i] := TMP_DEST[i+63:i]
ELSE *DEST[i+63:i] remains unchanged*
; merging-masking
FI;
ENDFOR
VEXTRACTI128 (memory destination form)
CASE (imm8[0]) OF
0: DEST[127:0] := SRC1[127:0]
1: DEST[127:0] := SRC1[255:128]
ESAC.
VEXTRACTI128 (register destination form)
CASE (imm8[0]) OF
0: DEST[127:0] := SRC1[127:0]
1: DEST[127:0] := SRC1[255:128]
ESAC.
DEST[MAXVL-1:128] := 0
VEXTRACTI128/VEXTRACTI32x4/VEXTRACTI64x2/VEXTRACTI32x8/VEXTRACTI64x4-Extract Packed Integer Values
Vol. 2C
5-178
Intel C/C++ Compiler Intrinsic Equivalent
VEXTRACTI32x4 __m128i _mm512_extracti32x4_epi32(__m512i a, const int nidx);
VEXTRACTI32x4 __m128i _mm512_mask_extracti32x4_epi32(__m128i s, __mmask8 k, __m512i a, const int nidx);
VEXTRACTI32x4 __m128i _mm512_maskz_extracti32x4_epi32( __mmask8 k, __m512i a, const int nidx);
VEXTRACTI32x4 __m128i _mm256_extracti32x4_epi32(__m256i a, const int nidx);
VEXTRACTI32x4 __m128i _mm256_mask_extracti32x4_epi32(__m128i s, __mmask8 k, __m256i a, const int nidx);
VEXTRACTI32x4 __m128i _mm256_maskz_extracti32x4_epi32( __mmask8 k, __m256i a, const int nidx);
VEXTRACTI32x8 __m256i _mm512_extracti32x8_epi32(__m512i a, const int nidx);
VEXTRACTI32x8 __m256i _mm512_mask_extracti32x8_epi32(__m256i s, __mmask8 k, __m512i a, const int nidx);
VEXTRACTI32x8 __m256i _mm512_maskz_extracti32x8_epi32( __mmask8 k, __m512i a, const int nidx);
VEXTRACTI64x2 __m128i _mm512_extracti64x2_epi64(__m512i a, const int nidx);
VEXTRACTI64x2 __m128i _mm512_mask_extracti64x2_epi64(__m128i s, __mmask8 k, __m512i a, const int nidx);
VEXTRACTI64x2 __m128i _mm512_maskz_extracti64x2_epi64( __mmask8 k, __m512i a, const int nidx);
VEXTRACTI64x2 __m128i _mm256_extracti64x2_epi64(__m256i a, const int nidx);
VEXTRACTI64x2 __m128i _mm256_mask_extracti64x2_epi64(__m128i s, __mmask8 k, __m256i a, const int nidx);
VEXTRACTI64x2 __m128i _mm256_maskz_extracti64x2_epi64( __mmask8 k, __m256i a, const int nidx);
VEXTRACTI64x4 __m256i _mm512_extracti64x4_epi64(__m512i a, const int nidx);
VEXTRACTI64x4 __m256i _mm512_mask_extracti64x4_epi64(__m256i s, __mmask8 k, __m512i a, const int nidx);
VEXTRACTI64x4 __m256i _mm512_maskz_extracti64x4_epi64( __mmask8 k, __m512i a, const int nidx);
VEXTRACTI128 __m128i _mm256_extracti128_si256(__m256i a, int offset);
SIMD Floating-Point Exceptions
None
Other Exceptions
VEX-encoded instructions, see Table 2-23, “Type 6 Class Exception Conditions.”
EVEX-encoded instructions, see Table 2-56, “Type E6NF Class Exception Conditions.”
Additionally:
#UD
IF VEX.L = 0.
#UD
If VEX.vvvv != 1111B or EVEX.vvvv != 1111B.
VEXTRACTI128/VEXTRACTI32x4/VEXTRACTI64x2/VEXTRACTI32x8/VEXTRACTI64x4-Extract Packed Integer Values
Vol. 2C
5-179
VFCMADDCPH/VFMADDCPH-Complex Multiply and Accumulate FP16 Values
Opcode/
Op/
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.128.F2.MAP6.W0 56 /r
A
V/V
(AVX512_FP16
Complex multiply a pair of FP16 values from
VFCMADDCPH xmm1{k1}{z}, xmm2,
AND AVX512VL)
xmm2 and xmm3/m128/m32bcst, add to xmm1
xmm3/m128/m32bcst
OR AVX10.1
and store the result in xmm1 subject to
writemask k1.
EVEX.256.F2.MAP6.W0 56 /r
A
V/V
(AVX512_FP16
Complex multiply a pair of FP16 values from
VFCMADDCPH ymm1{k1}{z}, ymm2,
AND AVX512VL)
ymm2 and ymm3/m256/m32bcst, add to ymm1
ymm3/m256/m32bcst
OR AVX10.1
and store the result in ymm1 subject to
writemask k1.
EVEX.512.F2.MAP6.W0 56 /r
A
V/V
AVX512_FP16
Complex multiply a pair of FP16 values from
VFCMADDCPH zmm1{k1}{z}, zmm2,
OR AVX10.1
zmm2 and zmm3/m512/m32bcst, add to zmm1
zmm3/m512/m32bcst {er}
and store the result in zmm1 subject to
writemask k1.
EVEX.128.F3.MAP6.W0 56 /r
A
V/V
(AVX512_FP16
Complex multiply a pair of FP16 values from
VFMADDCPH xmm1{k1}{z}, xmm2,
AND AVX512VL)
xmm2 and the complex conjugate of
xmm3/m128/m32bcst
OR AVX10.1
xmm3/m128/m32bcst, add to xmm1 and store
the result in xmm1 subject to writemask k1.
EVEX.256.F3.MAP6.W0 56 /r
A
V/V
(AVX512_FP16
Complex multiply a pair of FP16 values from
VFMADDCPH ymm1{k1}{z}, ymm2,
AND AVX512VL)
ymm2 and the complex conjugate of
ymm3/m256/m32bcst
OR AVX10.1
ymm3/m256/m32bcst, add to ymm1 and store
the result in ymm1 subject to writemask k1.
EVEX.512.F3.MAP6.W0 56 /r
A
V/V
AVX512_FP16
Complex multiply a pair of FP16 values from
VFMADDCPH zmm1{k1}{z}, zmm2,
OR AVX10.1
zmm2 and the complex conjugate of
zmm3/m512/m32bcst {er}
zmm3/m512/m32bcst, add to zmm1 and store
the result in zmm1 subject to writemask k1.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
Full
ModRM:reg (r, w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction performs a complex multiply and accumulate operation. There are normal and complex conjugate
forms of the operation.
The broadcasting and masking for this operation is done on 32-bit quantities representing a pair of FP16 values.
Rounding is performed at every FMA (fused multiply and add) boundary. Execution occurs as if all MXCSR excep-
tions are masked. MXCSR status bits are updated to reflect exceptional conditions.
VFCMADDCPH/VFMADDCPH-Complex Multiply and Accumulate FP16 Values
Vol. 2C
5-180
Operation
VFCMADDCPH dest{k1}, src1, src2 (AVX512)
VL = 128, 256, 512
KL := VL / 32
FOR i := 0 to KL-1:
IF k1[i] or *no writemask*:
IF broadcasting and src2 is memory:
tsrc2.fp16[2*i+0] := src2.fp16[0]
tsrc2.fp16[2*i+1] := src2.fp16[1]
ELSE:
tsrc2.fp16[2*i+0] := src2.fp16[2*i+0]
tsrc2.fp16[2*i+1] := src2.fp16[2*i+1]
FOR i := 0 to KL-1:
IF k1[i] or *no writemask*:
tmp[2*i+0] := dest.fp16[2*i+0] + src1.fp16[2*i+0] * tsrc2.fp16[2*i+0]
tmp[2*i+1] := dest.fp16[2*i+1] + src1.fp16[2*i+1] * tsrc2.fp16[2*i+0]
FOR i := 0 to KL-1:
IF k1[i] or *no writemask*:
// conjugate version subtracts odd final term
dest.fp16[2*i+0] := tmp[2*i+0] + src1.fp16[2*i+1] * tsrc2.fp16[2*i+1]
dest.fp16[2*i+1] := tmp[2*i+1] - src1.fp16[2*i+0] * tsrc2.fp16[2*i+1]
ELSE IF *zeroing*:
dest.fp16[2*i+0] := 0
dest.fp16[2*i+1] := 0
DEST[MAXVL-1:VL] := 0
VFMADDCPH dest{k1}, src1, src2 (AVX512)
VL = 128, 256, 512
KL := VL / 32
FOR i := 0 to KL-1:
IF k1[i] or *no writemask*:
IF broadcasting and src2 is memory:
tsrc2.fp16[2*i+0] := src2.fp16[0]
tsrc2.fp16[2*i+1] := src2.fp16[1]
ELSE:
tsrc2.fp16[2*i+0] := src2.fp16[2*i+0]
tsrc2.fp16[2*i+1] := src2.fp16[2*i+1]
FOR i := 0 to KL-1:
IF k1[i] or *no writemask*:
tmp[2*i+0] := dest.fp16[2*i+0] + src1.fp16[2*i+0] * tsrc2.fp16[2*i+0]
tmp[2*i+1] := dest.fp16[2*i+1] + src1.fp16[2*i+1] * tsrc2.fp16[2*i+0]
FOR i := 0 to KL-1:
IF k1[i] or *no writemask*:
// non-conjugate version subtracts even term
dest.fp16[2*i+0] := tmp[2*i+0] - src1.fp16[2*i+1] * tsrc2.fp16[2*i+1]
dest.fp16[2*i+1] := tmp[2*i+1] + src1.fp16[2*i+0] * tsrc2.fp16[2*i+1]
ELSE IF *zeroing*:
VFCMADDCPH/VFMADDCPH-Complex Multiply and Accumulate FP16 Values
Vol. 2C
5-181
dest.fp16[2*i+0] := 0
dest.fp16[2*i+1] := 0
DEST[MAXVL-1:VL] := 0
Intel C/C++ Compiler Intrinsic Equivalent
VFCMADDCPH __m128h _mm_fcmadd_pch (__m128h a, __m128h b, __m128h c);
VFCMADDCPH __m128h _mm_mask_fcmadd_pch (__m128h a, __mmask8 k, __m128h b, __m128h c);
VFCMADDCPH __m128h _mm_mask3_fcmadd_pch (__m128h a, __m128h b, __m128h c, __mmask8 k);
VFCMADDCPH __m128h _mm_maskz_fcmadd_pch (__mmask8 k, __m128h a, __m128h b, __m128h c);
VFCMADDCPH __m256h _mm256_fcmadd_pch (__m256h a, __m256h b, __m256h c);
VFCMADDCPH __m256h _mm256_mask_fcmadd_pch (__m256h a, __mmask8 k, __m256h b, __m256h c);
VFCMADDCPH __m256h _mm256_mask3_fcmadd_pch (__m256h a, __m256h b, __m256h c, __mmask8 k);
VFCMADDCPH __m256h _mm256_maskz_fcmadd_pch (__mmask8 k, __m256h a, __m256h b, __m256h c);
VFCMADDCPH __m512h _mm512_fcmadd_pch (__m512h a, __m512h b, __m512h c);
VFCMADDCPH __m512h _mm512_mask_fcmadd_pch (__m512h a, __mmask16 k, __m512h b, __m512h c);
VFCMADDCPH __m512h _mm512_mask3_fcmadd_pch (__m512h a, __m512h b, __m512h c, __mmask16 k);
VFCMADDCPH __m512h _mm512_maskz_fcmadd_pch (__mmask16 k, __m512h a, __m512h b, __m512h c);
VFCMADDCPH __m512h _mm512_fcmadd_round_pch (__m512h a, __m512h b, __m512h c, const int rounding);
VFCMADDCPH __m512h _mm512_mask_fcmadd_round_pch (__m512h a, __mmask16 k, __m512h b, __m512h c, const int rounding);
VFCMADDCPH __m512h _mm512_mask3_fcmadd_round_pch (__m512h a, __m512h b, __m512h c, __mmask16 k, const int rounding);
VFCMADDCPH __m512h _mm512_maskz_fcmadd_round_pch (__mmask16 k, __m512h a, __m512h b, __m512h c, const int rounding);
VFMADDCPH __m128h _mm_fmadd_pch (__m128h a, __m128h b, __m128h c);
VFMADDCPH __m128h _mm_mask_fmadd_pch (__m128h a, __mmask8 k, __m128h b, __m128h c);
VFMADDCPH __m128h _mm_mask3_fmadd_pch (__m128h a, __m128h b, __m128h c, __mmask8 k);
VFMADDCPH __m128h _mm_maskz_fmadd_pch (__mmask8 k, __m128h a, __m128h b, __m128h c);
VFMADDCPH __m256h _mm256_fmadd_pch (__m256h a, __m256h b, __m256h c);
VFMADDCPH __m256h _mm256_mask_fmadd_pch (__m256h a, __mmask8 k, __m256h b, __m256h c);
VFMADDCPH __m256h _mm256_mask3_fmadd_pch (__m256h a, __m256h b, __m256h c, __mmask8 k);
VFMADDCPH __m256h _mm256_maskz_fmadd_pch (__mmask8 k, __m256h a, __m256h b, __m256h c);
VFMADDCPH __m512h _mm512_fmadd_pch (__m512h a, __m512h b, __m512h c);
VFMADDCPH __m512h _mm512_mask_fmadd_pch (__m512h a, __mmask16 k, __m512h b, __m512h c);
VFMADDCPH __m512h _mm512_mask3_fmadd_pch (__m512h a, __m512h b, __m512h c, __mmask16 k);
VFMADDCPH __m512h _mm512_maskz_fmadd_pch (__mmask16 k, __m512h a, __m512h b, __m512h c);
VFMADDCPH __m512h _mm512_fmadd_round_pch (__m512h a, __m512h b, __m512h c, const int rounding);
VFMADDCPH __m512h _mm512_mask_fmadd_round_pch (__m512h a, __mmask16 k, __m512h b, __m512h c, const int rounding);
VFMADDCPH __m512h _mm512_mask3_fmadd_round_pch (__m512h a, __m512h b, __m512h c, __mmask16 k, const int rounding);
VFMADDCPH __m512h _mm512_maskz_fmadd_round_pch (__mmask16 k, __m512h a, __m512h b, __m512h c, const int rounding);
SIMD Floating-Point Exceptions
Invalid, Underflow, Overflow, Precision, Denormal.
Other Exceptions
EVEX-encoded instructions, see Table 2-51, “Type E4 Class Exception Conditions.”
Additionally:
#UD
If (dest_reg == src1_reg) or (dest_reg == src2_reg).
VFCMADDCPH/VFMADDCPH-Complex Multiply and Accumulate FP16 Values
Vol. 2C
5-182
VFCMADDCSH/VFMADDCSH-Complex Multiply and Accumulate Scalar FP16 Values
Opcode/
Op/
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.LLIG.F2.MAP6.W0 57 /r
A
V/V
AVX512_FP16
Complex multiply a pair of FP16 values from
VFCMADDCSH xmm1{k1}{z}, xmm2,
OR AVX10.1
xmm2 and xmm3/m32, add to xmm1 and store
xmm3/m32 {er}
the result in xmm1 subject to writemask k1. Bits
127:32 of xmm2 are copied to xmm1[127:32].
EVEX.LLIG.F3.MAP6.W0 57 /r
A
V/V
AVX512_FP16
Complex multiply a pair of FP16 values from
VFMADDCSH xmm1{k1}{z}, xmm2,
OR AVX10.1
xmm2 and the complex conjugate of xmm3/m32,
xmm3/m32 {er}
add to xmm1 and store the result in xmm1
subject to writemask k1. Bits 127:32 of xmm2
are copied to xmm1[127:32].
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
Scalar
ModRM:reg (r, w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction performs a complex multiply and accumulate operation. There are normal and complex conjugate
forms of the operation.
The masking for this operation is done on 32-bit quantities representing a pair of FP16 values.
Bits 127:32 of the destination operand are copied from the corresponding bits of the first source operand. Bits
MAXVL-1:128 of the destination operand are zeroed. The low FP16 element of the destination is updated according
to the writemask.
Rounding is performed at every FMA (fused multiply and add) boundary. Execution occurs as if all MXCSR excep-
tions are masked. MXCSR status bits are updated to reflect exceptional conditions.
Operation
VFCMADDCSH dest{k1}, src1, src2 (AVX512)
IF k1[0] or *no writemask*:
tmp[0] := dest.fp16[0] + src1.fp16[0] * src2.fp16[0]
tmp[1] := dest.fp16[1] + src1.fp16[1] * src2.fp16[0]
// conjugate version subtracts odd final term
dest.fp16[0] := tmp[0] + src1.fp16[1] * src2.fp16[1]
dest.fp16[1] := tmp[1] - src1.fp16[0] * src2.fp16[1]
ELSE IF *zeroing*:
dest.fp16[0] := 0
dest.fp16[1] := 0
DEST[127:32] := src1[127:32] // copy upper part of src1
DEST[MAXVL-1:128] := 0
VFCMADDCSH/VFMADDCSH-Complex Multiply and Accumulate Scalar FP16 Values
Vol. 2C
5-183
VFMADDCSH dest{k1}, src1, src2 (AVX512)
IF k1[0] or *no writemask*:
tmp[0] := dest.fp16[0] + src1.fp16[0] * src2.fp16[0]
tmp[1] := dest.fp16[1] + src1.fp16[1] * src2.fp16[0]
// non-conjugate version subtracts last even term
dest.fp16[0] := tmp[0] - src1.fp16[1] * src2.fp16[1]
dest.fp16[1] := tmp[1] + src1.fp16[0] * src2.fp16[1]
ELSE IF *zeroing*:
dest.fp16[0] := 0
dest.fp16[1] := 0
DEST[127:32] := src1[127:32] // copy upper part of src1
DEST[MAXVL-1:128] := 0
Intel C/C++ Compiler Intrinsic Equivalent
VFCMADDCSH __m128h _mm_fcmadd_round_sch (__m128h a, __m128h b, __m128h c, const int rounding);
VFCMADDCSH __m128h _mm_mask_fcmadd_round_sch (__m128h a, __mmask8 k, __m128h b, __m128h c, const int rounding);
VFCMADDCSH __m128h _mm_mask3_fcmadd_round_sch (__m128h a, __m128h b, __m128h c, __mmask8 k, const int rounding);
VFCMADDCSH __m128h _mm_maskz_fcmadd_round_sch (__mmask8 k, __m128h a, __m128h b, __m128h c, const int rounding);
VFCMADDCSH __m128h _mm_fcmadd_sch (__m128h a, __m128h b, __m128h c);
VFCMADDCSH __m128h _mm_mask_fcmadd_sch (__m128h a, __mmask8 k, __m128h b, __m128h c);
VFCMADDCSH __m128h _mm_mask3_fcmadd_sch (__m128h a, __m128h b, __m128h c, __mmask8 k);
VFCMADDCSH __m128h _mm_maskz_fcmadd_sch (__mmask8 k, __m128h a, __m128h b, __m128h c);
VFMADDCSH __m128h _mm_fmadd_round_sch (__m128h a, __m128h b, __m128h c, const int rounding);
VFMADDCSH __m128h _mm_mask_fmadd_round_sch (__m128h a, __mmask8 k, __m128h b, __m128h c, const int rounding);
VFMADDCSH __m128h _mm_mask3_fmadd_round_sch (__m128h a, __m128h b, __m128h c, __mmask8 k, const int rounding);
VFMADDCSH __m128h _mm_maskz_fmadd_round_sch (__mmask8 k, __m128h a, __m128h b, __m128h c, const int rounding);
VFMADDCSH __m128h _mm_fmadd_sch (__m128h a, __m128h b, __m128h c);
VFMADDCSH __m128h _mm_mask_fmadd_sch (__m128h a, __mmask8 k, __m128h b, __m128h c);
VFMADDCSH __m128h _mm_mask3_fmadd_sch (__m128h a, __m128h b, __m128h c, __mmask8 k);
VFMADDCSH __m128h _mm_maskz_fmadd_sch (__mmask8 k, __m128h a, __m128h b, __m128h c);
SIMD Floating-Point Exceptions
Invalid, Underflow, Overflow, Precision, Denormal.
Other Exceptions
EVEX-encoded instructions, see Table 2-60, “Type E10 Class Exception Conditions.”
Additionally:
#UD
If (dest_reg == src1_reg) or (dest_reg == src2_reg).
VFCMADDCSH/VFMADDCSH-Complex Multiply and Accumulate Scalar FP16 Values
Vol. 2C
5-184
VFCMULCPH/VFMULCPH-Complex Multiply FP16 Values
Opcode/
Op/
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.128.F2.MAP6.W0 D6 /r
A
V/V
(AVX512_FP16
Complex multiply a pair of FP16 values from
VFCMULCPH xmm1{k1}{z}, xmm2,
AND AVX512VL)
xmm2 and xmm3/m128/m32bcst, and store the
xmm3/m128/m32bcst
OR AVX10.1
result in xmm1 subject to writemask k1.
EVEX.256.F2.MAP6.W0 D6 /r
A
V/V
(AVX512_FP16
Complex multiply a pair of FP16 values from
VFCMULCPH ymm1{k1}{z}, ymm2,
AND AVX512VL)
ymm2 and ymm3/m256/m32bcst, and store the
ymm3/m256/m32bcst
OR AVX10.1
result in ymm1 subject to writemask k1.
EVEX.512.F2.MAP6.W0 D6 /r
A
V/V
AVX512_FP16
Complex multiply a pair of FP16 values from
VFCMULCPH zmm1{k1}{z}, zmm2,
OR AVX10.1
zmm2 and zmm3/m512/m32bcst, and store the
zmm3/m512/m32bcst {er}
result in zmm1 subject to writemask k1.
EVEX.128.F3.MAP6.W0 D6 /r
A
V/V
(AVX512_FP16
Complex multiply a pair of FP16 values from
VFMULCPH xmm1{k1}{z}, xmm2,
AND AVX512VL)
xmm2 and the complex conjugate of
xmm3/m128/m32bcst
OR AVX10.1
xmm3/m128/m32bcst, and store the result in
xmm1 subject to writemask k1.
EVEX.256.F3.MAP6.W0 D6 /r
A
V/V
(AVX512_FP16
Complex multiply a pair of FP16 values from
VFMULCPH ymm1{k1}{z}, ymm2,
AND AVX512VL)
ymm2 and the complex conjugate of
ymm3/m256/m32bcst
OR AVX10.1
ymm3/m256/m32bcst, and store the result in
ymm1 subject to writemask k1.
EVEX.512.F3.MAP6.W0 D6 /r
A
V/V
AVX512_FP16
Complex multiply a pair of FP16 values from
VFMULCPH zmm1{k1}{z}, zmm2,
OR AVX10.1
zmm2 and the complex conjugate of
zmm3/m512/m32bcst {er}
zmm3/m512/m32bcst, and store the result in
zmm1 subject to writemask k1.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
Full
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction performs a complex multiply operation. There are normal and complex conjugate forms of the oper-
ation. The broadcasting and masking for this operation is done on 32-bit quantities representing a pair of FP16
values.
Rounding is performed at every FMA (fused multiply and add) boundary. Execution occurs as if all MXCSR excep-
tions are masked. MXCSR status bits are updated to reflect exceptional conditions.
Operation
VFCMULCPH dest{k1}, src1, src2 (AVX512)
VL = 128, 256 or 512
KL := VL/32
FOR i := 0 to KL-1:
IF k1[i] or *no writemask*:
IF broadcasting and src2 is memory:
tsrc2.fp16[2*i+0] := src2.fp16[0]
tsrc2.fp16[2*i+1] := src2.fp16[1]
ELSE:
tsrc2.fp16[2*i+0] := src2.fp16[2*i+0]
tsrc2.fp16[2*i+1] := src2.fp16[2*i+1]
FOR i := 0 to KL-1:
VFCMULCPH/VFMULCPH-Complex Multiply FP16 Values
Vol. 2C
5-185
IF k1[i] or *no writemask*:
tmp.fp16[2*i+0] := src1.fp16[2*i+0] * tsrc2.fp16[2*i+0]
tmp.fp16[2*i+1] := src1.fp16[2*i+1] * tsrc2.fp16[2*i+0]
FOR i := 0 to KL-1:
IF k1[i] or *no writemask*:
// conjugate version subtracts odd final term
dest.fp16[2*i] := tmp.fp16[2*i+0] +src1.fp16[2*i+1] * tsrc2.fp16[2*i+1]
dest.fp16[2*i+1] := tmp.fp16[2*i+1] - src1.fp16[2*i+0] * tsrc2.fp16[2*i+1]
ELSE IF *zeroing*:
dest.fp16[2*i+0] := 0
dest.fp16[2*i+1] := 0
DEST[MAXVL-1:VL] := 0
VFMULCPH dest{k1}, src1, src2 (AVX512)
VL = 128, 256 or 512
KL := VL/32
FOR i := 0 to KL-1:
IF k1[i] or *no writemask*:
IF broadcasting and src2 is memory:
tsrc2.fp16[2*i+0] := src2.fp16[0]
tsrc2.fp16[2*i+1] := src2.fp16[1]
ELSE:
tsrc2.fp16[2*i+0] := src2.fp16[2*i+0]
tsrc2.fp16[2*i+1] := src2.fp16[2*i+1]
FOR i := 0 to kl-1:
IF k1[i] or *no writemask*:
tmp.fp16[2*i+0] := src1.fp16[2*i+0] * tsrc2.fp16[2*i+0]
tmp.fp16[2*i+1] := src1.fp16[2*i+1] * tsrc2.fp16[2*i+0]
FOR i := 0 to KL-1:
IF k1[i] or *no writemask*:
// non-conjugate version subtracts last even term
dest.fp16[2*i+0] := tmp.fp16[2*i+0] - src1.fp16[2*i+1] * tsrc2.fp16[2*i+1]
dest.fp16[2*i+1] := tmp.fp16[2*i+1] + src1.fp16[2*i+0] * tsrc2.fp16[2*i+1]
ELSE IF *zeroing*:
dest.fp16[2*i+0] := 0
dest.fp16[2*i+1] := 0
DEST[MAXVL-1:VL] := 0
VFCMULCPH/VFMULCPH-Complex Multiply FP16 Values
Vol. 2C
5-186
Intel C/C++ Compiler Intrinsic Equivalent
VFCMULCPH __m128h _mm_cmul_pch (__m128h a, __m128h b);
VFCMULCPH __m128h _mm_mask_cmul_pch (__m128h src, __mmask8 k, __m128h a, __m128h b);
VFCMULCPH __m128h _mm_maskz_cmul_pch (__mmask8 k, __m128h a, __m128h b);
VFCMULCPH __m256h _mm256_cmul_pch (__m256h a, __m256h b);
VFCMULCPH __m256h _mm256_mask_cmul_pch (__m256h src, __mmask8 k, __m256h a, __m256h b);
VFCMULCPH __m256h _mm256_maskz_cmul_pch (__mmask8 k, __m256h a, __m256h b);
VFCMULCPH __m512h _mm512_cmul_pch (__m512h a, __m512h b);
VFCMULCPH __m512h _mm512_mask_cmul_pch (__m512h src, __mmask16 k, __m512h a, __m512h b);
VFCMULCPH __m512h _mm512_maskz_cmul_pch (__mmask16 k, __m512h a, __m512h b);
VFCMULCPH __m512h _mm512_cmul_round_pch (__m512h a, __m512h b, const int rounding);
VFCMULCPH __m512h _mm512_mask_cmul_round_pch (__m512h src, __mmask16 k, __m512h a, __m512h b, const int rounding);
VFCMULCPH __m512h _mm512_maskz_cmul_round_pch (__mmask16 k, __m512h a, __m512h b, const int rounding);
VFCMULCPH __m128h _mm_fcmul_pch (__m128h a, __m128h b);
VFCMULCPH __m128h _mm_mask_fcmul_pch (__m128h src, __mmask8 k, __m128h a, __m128h b);
VFCMULCPH __m128h _mm_maskz_fcmul_pch (__mmask8 k, __m128h a, __m128h b);
VFCMULCPH __m256h _mm256_fcmul_pch (__m256h a, __m256h b);
VFCMULCPH __m256h _mm256_mask_fcmul_pch (__m256h src, __mmask8 k, __m256h a, __m256h b);
VFCMULCPH __m256h _mm256_maskz_fcmul_pch (__mmask8 k, __m256h a, __m256h b);
VFCMULCPH __m512h _mm512_fcmul_pch (__m512h a, __m512h b);
VFCMULCPH __m512h _mm512_mask_fcmul_pch (__m512h src, __mmask16 k, __m512h a, __m512h b);
VFCMULCPH __m512h _mm512_maskz_fcmul_pch (__mmask16 k, __m512h a, __m512h b);
VFCMULCPH __m512h _mm512_fcmul_round_pch (__m512h a, __m512h b, const int rounding);
VFCMULCPH __m512h _mm512_mask_fcmul_round_pch (__m512h src, __mmask16 k, __m512h a, __m512h b, const int rounding);
VFCMULCPH __m512h _mm512_maskz_fcmul_round_pch (__mmask16 k, __m512h a, __m512h b, const int rounding);
VFMULCPH __m128h _mm_fmul_pch (__m128h a, __m128h b);
VFMULCPH __m128h _mm_mask_fmul_pch (__m128h src, __mmask8 k, __m128h a, __m128h b);
VFMULCPH __m128h _mm_maskz_fmul_pch (__mmask8 k, __m128h a, __m128h b);
VFMULCPH __m256h _mm256_fmul_pch (__m256h a, __m256h b);
VFMULCPH __m256h _mm256_mask_fmul_pch (__m256h src, __mmask8 k, __m256h a, __m256h b);
VFMULCPH __m256h _mm256_maskz_fmul_pch (__mmask8 k, __m256h a, __m256h b);
VFMULCPH __m512h _mm512_fmul_pch (__m512h a, __m512h b);
VFMULCPH __m512h _mm512_mask_fmul_pch (__m512h src, __mmask16 k, __m512h a, __m512h b);
VFMULCPH __m512h _mm512_maskz_fmul_pch (__mmask16 k, __m512h a, __m512h b);
VFMULCPH __m512h _mm512_fmul_round_pch (__m512h a, __m512h b, const int rounding);
VFMULCPH __m512h _mm512_mask_fmul_round_pch (__m512h src, __mmask16 k, __m512h a, __m512h b, const int rounding);
VFMULCPH __m512h _mm512_maskz_fmul_round_pch (__mmask16 k, __m512h a, __m512h b, const int rounding);
VFMULCPH __m128h _mm_mask_mul_pch (__m128h src, __mmask8 k, __m128h a, __m128h b);
VFMULCPH __m128h _mm_maskz_mul_pch (__mmask8 k, __m128h a, __m128h b);
VFMULCPH __m128h _mm_mul_pch (__m128h a, __m128h b);
VFMULCPH __m256h _mm256_mask_mul_pch (__m256h src, __mmask8 k, __m256h a, __m256h b);
VFMULCPH __m256h _mm256_maskz_mul_pch (__mmask8 k, __m256h a, __m256h b);
VFMULCPH __m256h _mm256_mul_pch (__m256h a, __m256h b);
VFMULCPH __m512h _mm512_mask_mul_pch (__m512h src, __mmask16 k, __m512h a, __m512h b);
VFMULCPH __m512h _mm512_maskz_mul_pch (__mmask16 k, __m512h a, __m512h b);
VFMULCPH __m512h _mm512_mul_pch (__m512h a, __m512h b);
VFMULCPH __m512h _mm512_mask_mul_round_pch (__m512h src, __mmask16 k, __m512h a, __m512h b, const int rounding);
VFMULCPH __m512h _mm512_maskz_mul_round_pch (__mmask16 k, __m512h a, __m512h b, const int rounding);
VFMULCPH __m512h _mm512_mul_round_pch (__m512h a, __m512h b, const int rounding);
SIMD Floating-Point Exceptions
Invalid, Underflow, Overflow, Precision, Denormal.
VFCMULCPH/VFMULCPH-Complex Multiply FP16 Values
Vol. 2C
5-187
Other Exceptions
EVEX-encoded instructions, see Table 2-51, “Type E4 Class Exception Conditions.”
Additionally:
#UD
If (dest_reg == src1_reg) or (dest_reg == src2_reg).
VFCMULCPH/VFMULCPH-Complex Multiply FP16 Values
Vol. 2C
5-188
VFCMULCSH/VFMULCSH-Complex Multiply Scalar FP16 Values
Opcode/
Op/
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.LLIG.F2.MAP6.W0 D7 /r
A
V/V
AVX512_FP16
Complex multiply a pair of FP16 values from
VFCMULCSH xmm1{k1}{z}, xmm2,
OR AVX10.1
xmm2 and xmm3/m32, and store the result in
xmm3/m32 {er}
xmm1 subject to writemask k1. Bits 127:32 of
xmm2 are copied to xmm1[127:32].
EVEX.LLIG.F3.MAP6.W0 D7 /r
A
V/V
AVX512_FP16
Complex multiply a pair of FP16 values from
VFMULCSH xmm1{k1}{z}, xmm2,
OR AVX10.1
xmm2 and the complex conjugate of xmm3/m32,
xmm3/m32 {er}
and store the result in xmm1 subject to
writemask k1. Bits 127:32 of xmm2 are copied to
xmm1[127:32].
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
Scalar
ModRM:reg (w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction performs a complex multiply operation. There are normal and complex conjugate forms of the oper-
ation. The masking for this operation is done on 32-bit quantities representing a pair of FP16 values.
Bits 127:32 of the destination operand are copied from the corresponding bits of the first source operand. Bits
MAXVL-1:128 of the destination operand are zeroed. The low FP16 element of the destination is updated according
to the writemask.
Rounding is performed at every FMA (fused multiply and add) boundary. Execution occurs as if all MXCSR excep-
tions are masked. MXCSR status bits are updated to reflect exceptional conditions.
Operation
VFCMULCSH dest{k1}, src1, src2 (AVX512)
KL := VL / 32
IF k1[0] or *no writemask*:
tmp.fp16[0] := src1.fp16[0] * src2.fp16[0]
tmp.fp16[1] := src1.fp16[1] * src2.fp16[0]
// conjugate version subtracts odd final term
dest.fp16[0] := tmp.fp16[0] + src1.fp16[1] * src2.fp16[1]
dest.fp16[1] := tmp.fp16[1] - src1.fp16[0] * src2.fp16[1]
ELSE IF *zeroing*:
dest.fp16[0] := 0
dest.fp16[1] := 0
DEST[127:32] := src1[127:32] // copy upper part of src1
DEST[MAXVL-1:128] := 0
VFCMULCSH/VFMULCSH-Complex Multiply Scalar FP16 Values
Vol. 2C
5-189
VFMULCSH dest{k1}, src1, src2 (AVX512)
KL := VL / 32
IF k1[0] or *no writemask*:
// non-conjugate version subtracts last even term
tmp.fp16[0] := src1.fp16[0] * src2.fp16[0]
tmp.fp16[1] := src1.fp16[1] * src2.fp16[0]
dest.fp16[0] := tmp.fp16[0] - src1.fp16[1] * src2.fp16[1]
dest.fp16[1] := tmp.fp16[1] + src1.fp16[0] * src2.fp16[1]
ELSE IF *zeroing*:
dest.fp16[0] := 0
dest.fp16[1] := 0
DEST[127:32] := src1[127:32] // copy upper part of src1
DEST[MAXVL-1:128] := 0
Intel C/C++ Compiler Intrinsic Equivalent
VFCMULCSH __m128h _mm_cmul_round_sch (__m128h a, __m128h b, const int rounding);
VFCMULCSH __m128h _mm_mask_cmul_round_sch (__m128h src, __mmask8 k, __m128h a, __m128h b, const int rounding);
VFCMULCSH __m128h _mm_maskz_cmul_round_sch (__mmask8 k, __m128h a, __m128h b, const int rounding);
VFCMULCSH __m128h _mm_cmul_sch (__m128h a, __m128h b);
VFCMULCSH __m128h _mm_mask_cmul_sch (__m128h src, __mmask8 k, __m128h a, __m128h b);
VFCMULCSH __m128h _mm_maskz_cmul_sch (__mmask8 k, __m128h a, __m128h b);
VFCMULCSH __m128h _mm_fcmul_round_sch (__m128h a, __m128h b, const int rounding);
VFCMULCSH __m128h _mm_mask_fcmul_round_sch (__m128h src, __mmask8 k, __m128h a, __m128h b, const int rounding);
VFCMULCSH __m128h _mm_maskz_fcmul_round_sch (__mmask8 k, __m128h a, __m128h b, const int rounding);
VFCMULCSH __m128h _mm_fcmul_sch (__m128h a, __m128h b);
VFCMULCSH __m128h _mm_mask_fcmul_sch (__m128h src, __mmask8 k, __m128h a, __m128h b);
VFCMULCSH __m128h _mm_maskz_fcmul_sch (__mmask8 k, __m128h a, __m128h b);
VFMULCSH __m128h _mm_fmul_round_sch (__m128h a, __m128h b, const int rounding);
VFMULCSH __m128h _mm_mask_fmul_round_sch (__m128h src, __mmask8 k, __m128h a, __m128h b, const int rounding);
VFMULCSH __m128h _mm_maskz_fmul_round_sch (__mmask8 k, __m128h a, __m128h b, const int rounding);
VFMULCSH __m128h _mm_fmul_sch (__m128h a, __m128h b);
VFMULCSH __m128h _mm_mask_fmul_sch (__m128h src, __mmask8 k, __m128h a, __m128h b);
VFMULCSH __m128h _mm_maskz_fmul_sch (__mmask8 k, __m128h a, __m128h b);
VFMULCSH __m128h _mm_mask_mul_round_sch (__m128h src, __mmask8 k, __m128h a, __m128h b, const int rounding);
VFMULCSH __m128h _mm_maskz_mul_round_sch (__mmask8 k, __m128h a, __m128h b, const int rounding);
VFMULCSH __m128h _mm_mul_round_sch (__m128h a, __m128h b, const int rounding);
VFMULCSH __m128h _mm_mask_mul_sch (__m128h src, __mmask8 k, __m128h a, __m128h b);
VFMULCSH __m128h _mm_maskz_mul_sch (__mmask8 k, __m128h a, __m128h b);
VFMULCSH __m128h _mm_mul_sch (__m128h a, __m128h b);
SIMD Floating-Point Exceptions
Invalid, Underflow, Overflow, Precision, Denormal.
Other Exceptions
EVEX-encoded instructions, see Table 2-60, “Type E10 Class Exception Conditions.”
Additionally:
#UD
If (dest_reg == src1_reg) or (dest_reg == src2_reg).
VFCMULCSH/VFMULCSH-Complex Multiply Scalar FP16 Values
Vol. 2C
5-190
VFIXUPIMMPD-Fix Up Special Packed Float64 Values
Opcode/
Op /
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.128.66.0F3A.W1 54 /r ib
A
V/V
(AVX512VL AND
Fix up special numbers in float64 vector xmm1,
VFIXUPIMMPD xmm1 {k1}{z}, xmm2,
AVX512F) OR
float64 vector xmm2 and int64 vector
xmm3/m128/m64bcst, imm8
AVX10.1
xmm3/m128/m64bcst and store the result in
xmm1, under writemask.
EVEX.256.66.0F3A.W1 54 /r ib
A
V/V
(AVX512VL AND
Fix up special numbers in float64 vector ymm1,
VFIXUPIMMPD ymm1 {k1}{z}, ymm2,
AVX512F) OR
float64 vector ymm2 and int64 vector
ymm3/m256/m64bcst, imm8
AVX10.1
ymm3/m256/m64bcst and store the result in
ymm1, under writemask.
EVEX.512.66.0F3A.W1 54 /r ib
A
V/V
AVX512F
Fix up elements of float64 vector in zmm2 using
VFIXUPIMMPD zmm1 {k1}{z}, zmm2,
OR AVX10.1
int64 vector table in zmm3/m512/m64bcst,
zmm3/m512/m64bcst{sae}, imm8
combine with preserved elements from zmm1,
and store the result in zmm1.
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
Full
ModRM:reg (r, w)
EVEX.vvvv (r)
ModRM:r/m (r)
imm8
Description
Perform fix-up of quad-word elements encoded in double precision floating-point format in the first source operand
(the second operand) using a 32-bit, two-level look-up table specified in the corresponding quadword element of
the second source operand (the third operand) with exception reporting specifier imm8. The elements that are
fixed-up are selected by mask bits of 1 specified in the opmask k1. Mask bits of 0 in the opmask k1 or table
response action of 0000b preserves the corresponding element of the first operand. The fixed-up elements from
the first source operand and the preserved element in the first operand are combined as the final results in the
destination operand (the first operand).
The destination and the first source operands are ZMM/YMM/XMM registers. 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 two-level look-up table perform a fix-up of each double precision floating-point input data in the first source
operand by decoding the input data encoding into 8 token types. A response table is defined for each token type
that converts the input encoding in the first source operand with one of 16 response actions.
This instruction is specifically intended for use in fixing up the results of arithmetic calculations involving one source
so that they match the spec, although it is generally useful for fixing up the results of multiple-instruction
sequences to reflect special-number inputs. For example, consider rcp(0). Input 0 to rcp, and you should get INF
according to the DX10 spec. However, evaluating rcp via Newton-Raphson, where x=approx(1/0), yields an incor-
rect result. To deal with this, VFIXUPIMMPD can be used after the N-R reciprocal sequence to set the result to the
correct value (i.e., INF when the input is 0).
If MXCSR.DAZ is not set, denormal input elements in the first source operand are considered as normal inputs and
do not trigger any fixup nor fault reporting.
Imm8 is used to set the required flags reporting. It supports #ZE and #IE fault reporting (see details below).
MXCSR mask bits are ignored and are treated as if all mask bits are set to masked response). If any of the imm8
bits is set and the condition met for fault reporting, MXCSR.IE or MXCSR.ZE might be updated.
This instruction is writemasked, so only those elements with the corresponding bit set in vector mask register k1
are computed and stored into zmm1. Elements in the destination with the corresponding bit clear in k1 retain their
previous values or are set to 0.
Operation
enum TOKEN_TYPE
VFIXUPIMMPD-Fix Up Special Packed Float64 Values
Vol. 2C
5-191
{
QNAN_TOKEN := 0,
SNAN_TOKEN := 1,
ZERO_VALUE_TOKEN := 2,
POS_ONE_VALUE_TOKEN := 3,
NEG_INF_TOKEN := 4,
POS_INF_TOKEN := 5,
NEG_VALUE_TOKEN := 6,
POS_VALUE_TOKEN := 7
}
FIXUPIMM_DP (dest[63:0], src1[63:0],tbl3[63:0], imm8 [7:0]){
tsrc[63:0] := ((src1[62:52] = 0) AND (MXCSR.DAZ =1)) ? 0.0 : src1[63:0]
CASE(tsrc[63:0] of TOKEN_TYPE) {
QNAN_TOKEN: j := 0;
SNAN_TOKEN: j := 1;
ZERO_VALUE_TOKEN: j := 2;
POS_ONE_VALUE_TOKEN: j := 3;
NEG_INF_TOKEN: j := 4;
POS_INF_TOKEN: j := 5;
NEG_VALUE_TOKEN: j := 6;
POS_VALUE_TOKEN: j := 7;
}
; end source special CASE(tsrc…)
; The required response from src3 table is extracted
token_response[3:0] = tbl3[3+4*j:4*j];
CASE(token_response[3:0]) {
0000: dest[63:0] := dest[63:0];
; preserve content of DEST
0001: dest[63:0] := tsrc[63:0];
; pass through src1 normal input value, denormal as zero
0010: dest[63:0] := QNaN(tsrc[63:0]);
0011: dest[63:0] := QNAN_Indefinite;
0100: dest[63:0] := -INF;
0101: dest[63:0] := +INF;
0110: dest[63:0] := tsrc.sign? -INF : +INF;
0111: dest[63:0] := -0;
1000: dest[63:0] := +0;
1001: dest[63:0] := -1;
1010: dest[63:0] := +1;
1011: dest[63:0] := ½;
1100: dest[63:0] := 90.0;
1101: dest[63:0] := PI/2;
1110: dest[63:0] := MAX_FLOAT;
1111: dest[63:0] := -MAX_FLOAT;
}
; end of token_response CASE
; The required fault reporting from imm8 is extracted
; TOKENs are mutually exclusive and TOKENs priority defines the order.
; Multiple faults related to a single token can occur simultaneously.
IF (tsrc[63:0] of TOKEN_TYPE: ZERO_VALUE_TOKEN) AND imm8[0] then set #ZE;
IF (tsrc[63:0] of TOKEN_TYPE: ZERO_VALUE_TOKEN) AND imm8[1] then set #IE;
IF (tsrc[63:0] of TOKEN_TYPE: ONE_VALUE_TOKEN) AND imm8[2] then set #ZE;
IF (tsrc[63:0] of TOKEN_TYPE: ONE_VALUE_TOKEN) AND imm8[3] then set #IE;
IF (tsrc[63:0] of TOKEN_TYPE: SNAN_TOKEN) AND imm8[4] then set #IE;
VFIXUPIMMPD-Fix Up Special Packed Float64 Values
Vol. 2C
5-192
IF (tsrc[63:0] of TOKEN_TYPE: NEG_INF_TOKEN) AND imm8[5] then set #IE;
IF (tsrc[63:0] of TOKEN_TYPE: NEG_VALUE_TOKEN) AND imm8[6] then set #IE;
IF (tsrc[63:0] of TOKEN_TYPE: POS_INF_TOKEN) AND imm8[7] then set #IE;
; end fault reporting
return dest[63:0];
}
; end of FIXUPIMM_DP()
VFIXUPIMMPD
(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) AND (SRC2 *is memory*)
THEN
DEST[i+63:i] := FIXUPIMM_DP(DEST[i+63:i], SRC1[i+63:i], SRC2[63:0], imm8 [7:0])
ELSE
DEST[i+63:i] := FIXUPIMM_DP(DEST[i+63:i], SRC1[i+63:i], SRC2[i+63:i], imm8 [7:0])
FI;
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+63:i] remains unchanged*
ELSE DEST[i+63:i] := 0
; zeroing-masking
FI
FI;
ENDFOR
DEST[MAXVL-1:VL] := 0
Immediate Control Description:
7
6
5
4
3
2
1
0
+ INF #IE
- VE #IE
- INF #IE
SNaN #IE
ONE #IE
ONE #ZE
ZERO #IE
ZERO #ZE
Figure 5-9. VFIXUPIMMPD Immediate Control Description
Intel C/C++ Compiler Intrinsic Equivalent
VFIXUPIMMPD __m512d _mm512_fixupimm_pd( __m512d a, __m512d b, __m512i c, int imm8);
VFIXUPIMMPD __m512d _mm512_mask_fixupimm_pd(__m512d a, __mmask8 k, __m512d b, __m512i c, int imm8);
VFIXUPIMMPD-Fix Up Special Packed Float64 Values
Vol. 2C
5-193
VFIXUPIMMPD __m512d _mm512_maskz_fixupimm_pd( __mmask8 k, __m512d a, __m512d b, __m512i c, int imm8);
VFIXUPIMMPD __m512d _mm512_fixupimm_round_pd( __m512d a, __m512d b, __m512i c, int imm8, int sae);
VFIXUPIMMPD __m512d _mm512_mask_fixupimm_round_pd(__m512d a, __mmask8 k, __m512d b, __m512i c, int imm8, int sae);
VFIXUPIMMPD __m512d _mm512_maskz_fixupimm_round_pd( __mmask8 k, __m512d a, __m512d b, __m512i c, int imm8, int sae);
VFIXUPIMMPD __m256d _mm256_fixupimm_pd( __m256d a, m256d b, __m256i c, int imm8);
VFIXUPIMMPD __m256d _mm256_mask_fixupimm_pd(__m256d a, __mmask8 k, __m256d b, __m256i c, int imm8);
VFIXUPIMMPD __m256d _mm256_maskz_fixupimm_pd( __mmask8 k, __m256d a, __m256d b, __m256i c, int imm8);
VFIXUPIMMPD __m128d _mm_fixupimm_pd( __m128d a, __m128d b, __m128i c, int imm8);
VFIXUPIMMPD __m128d _mm_mask_fixupimm_pd(__m128d a, __mmask8 k, __m128d b, __m128i c, int imm8);
VFIXUPIMMPD __m128d _mm_maskz_fixupimm_pd( __mmask8 k, __m128d a, __m128d b, __m128i c, int imm8);
SIMD Floating-Point Exceptions
Zero, Invalid.
Other Exceptions
See Table 2-48, “Type E2 Class Exception Conditions.”
VFIXUPIMMPD-Fix Up Special Packed Float64 Values
Vol. 2C
5-194
VFIXUPIMMPS-Fix Up Special Packed Float32 Values
Opcode/
Op /
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.128.66.0F3A.W0 54 /r
A
V/V
(AVX512VL AND
Fix up special numbers in float32 vector xmm1,
VFIXUPIMMPS xmm1 {k1}{z}, xmm2,
AVX512F) OR
float32 vector xmm2 and int32 vector
xmm3/m128/m32bcst, imm8
AVX10.1
xmm3/m128/m32bcst and store the result in
xmm1, under writemask.
EVEX.256.66.0F3A.W0 54 /r
A
V/V
(AVX512VL AND
Fix up special numbers in float32 vector ymm1,
VFIXUPIMMPS ymm1 {k1}{z}, ymm2,
AVX512F) OR
float32 vector ymm2 and int32 vector
ymm3/m256/m32bcst, imm8
AVX10.1
ymm3/m256/m32bcst and store the result in
ymm1, under writemask.
EVEX.512.66.0F3A.W0 54 /r ib
A
V/V
AVX512F
Fix up elements of float32 vector in zmm2 using
VFIXUPIMMPS zmm1 {k1}{z}, zmm2,
OR AVX10.1
int32 vector table in zmm3/m512/m32bcst,
zmm3/m512/m32bcst{sae}, imm8
combine with preserved elements from zmm1,
and store the result in zmm1.
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
Full
ModRM:reg (r, w)
EVEX.vvvv (r)
ModRM:r/m (r)
imm8
Description
Perform fix-up of doubleword elements encoded in single precision floating-point format in the first source operand
(the second operand) using a 32-bit, two-level look-up table specified in the corresponding doubleword element of
the second source operand (the third operand) with exception reporting specifier imm8. The elements that are
fixed-up are selected by mask bits of 1 specified in the opmask k1. Mask bits of 0 in the opmask k1 or table
response action of 0000b preserves the corresponding element of the first operand. The fixed-up elements from
the first source operand and the preserved element in the first operand are combined as the final results in the
destination operand (the first operand).
The destination and the first source operands are ZMM/YMM/XMM registers. 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 two-level look-up table perform a fix-up of each single precision floating-point input data in the first source
operand by decoding the input data encoding into 8 token types. A response table is defined for each token type
that converts the input encoding in the first source operand with one of 16 response actions.
This instruction is specifically intended for use in fixing up the results of arithmetic calculations involving one source
so that they match the spec, although it is generally useful for fixing up the results of multiple-instruction
sequences to reflect special-number inputs. For example, consider rcp(0). Input 0 to rcp, and you should get INF
according to the DX10 spec. However, evaluating rcp via Newton-Raphson, where x=approx(1/0), yields an incor-
rect result. To deal with this, VFIXUPIMMPS can be used after the N-R reciprocal sequence to set the result to the
correct value (i.e., INF when the input is 0).
If MXCSR.DAZ is not set, denormal input elements in the first source operand are considered as normal inputs and
do not trigger any fixup nor fault reporting.
Imm8 is used to set the required flags reporting. It supports #ZE and #IE fault reporting (see details below).
MXCSR.DAZ is used and refer to zmm2 only (i.e., zmm1 is not considered as zero in case MXCSR.DAZ is set).
MXCSR mask bits are ignored and are treated as if all mask bits are set to masked response). If any of the imm8
bits is set and the condition met for fault reporting, MXCSR.IE or MXCSR.ZE might be updated.
VFIXUPIMMPS-Fix Up Special Packed Float32 Values
Vol. 2C
5-195
Operation
enum TOKEN_TYPE
{
QNAN_TOKEN := 0,
SNAN_TOKEN := 1,
ZERO_VALUE_TOKEN := 2,
POS_ONE_VALUE_TOKEN := 3,
NEG_INF_TOKEN := 4,
POS_INF_TOKEN := 5,
NEG_VALUE_TOKEN := 6,
POS_VALUE_TOKEN := 7
}
FIXUPIMM_SP ( dest[31:0], src1[31:0],tbl3[31:0], imm8 [7:0]){
tsrc[31:0] := ((src1[30:23] = 0) AND (MXCSR.DAZ =1)) ? 0.0 : src1[31:0]
CASE(tsrc[31:0] of TOKEN_TYPE) {
QNAN_TOKEN: j := 0;
SNAN_TOKEN: j := 1;
ZERO_VALUE_TOKEN: j := 2;
POS_ONE_VALUE_TOKEN: j := 3;
NEG_INF_TOKEN: j := 4;
POS_INF_TOKEN: j := 5;
NEG_VALUE_TOKEN: j := 6;
POS_VALUE_TOKEN: j := 7;
}
; end source special CASE(tsrc…)
; The required response from src3 table is extracted
token_response[3:0] = tbl3[3+4*j:4*j];
CASE(token_response[3:0]) {
0000: dest[31:0] := dest[31:0];
; preserve content of DEST
0001: dest[31:0] := tsrc[31:0];
; pass through src1 normal input value, denormal as zero
0010: dest[31:0] := QNaN(tsrc[31:0]);
0011: dest[31:0] := QNAN_Indefinite;
0100: dest[31:0] := -INF;
0101: dest[31:0] := +INF;
0110: dest[31:0] := tsrc.sign? -INF : +INF;
0111: dest[31:0] := -0;
1000: dest[31:0] := +0;
1001: dest[31:0] := -1;
1010: dest[31:0] := +1;
1011: dest[31:0] := ½;
1100: dest[31:0] := 90.0;
1101: dest[31:0] := PI/2;
1110: dest[31:0] := MAX_FLOAT;
1111: dest[31:0] := -MAX_FLOAT;
}
; end of token_response CASE
; The required fault reporting from imm8 is extracted
; TOKENs are mutually exclusive and TOKENs priority defines the order.
; Multiple faults related to a single token can occur simultaneously.
IF (tsrc[31:0] of TOKEN_TYPE: ZERO_VALUE_TOKEN) AND imm8[0] then set #ZE;
IF (tsrc[31:0] of TOKEN_TYPE: ZERO_VALUE_TOKEN) AND imm8[1] then set #IE;
IF (tsrc[31:0] of TOKEN_TYPE: ONE_VALUE_TOKEN) AND imm8[2] then set #ZE;
VFIXUPIMMPS-Fix Up Special Packed Float32 Values
Vol. 2C
5-196
IF (tsrc[31:0] of TOKEN_TYPE: ONE_VALUE_TOKEN) AND imm8[3] then set #IE;
IF (tsrc[31:0] of TOKEN_TYPE: SNAN_TOKEN) AND imm8[4] then set #IE;
IF (tsrc[31:0] of TOKEN_TYPE: NEG_INF_TOKEN) AND imm8[5] then set #IE;
IF (tsrc[31:0] of TOKEN_TYPE: NEG_VALUE_TOKEN) AND imm8[6] then set #IE;
IF (tsrc[31:0] of TOKEN_TYPE: POS_INF_TOKEN) AND imm8[7] then set #IE;
; end fault reporting
return dest[31:0];
}
; end of FIXUPIMM_SP()
VFIXUPIMMPS (EVEX)
(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) AND (SRC2 *is memory*)
THEN
DEST[i+31:i] := FIXUPIMM_SP(DEST[i+31:i], SRC1[i+31:i], SRC2[31:0], imm8 [7:0])
ELSE
DEST[i+31:i] := FIXUPIMM_SP(DEST[i+31:i], SRC1[i+31:i], SRC2[i+31:i], imm8 [7:0])
FI;
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[i+31:i] remains unchanged*
ELSE DEST[i+31:i] := 0
; zeroing-masking
FI
FI;
ENDFOR
DEST[MAXVL-1:VL] := 0
Immediate Control Description:
7
6
5
4
3
2
1
0
+ INF #IE
- VE #IE
- INF #IE
SNaN #IE
ONE #IE
ONE #ZE
ZERO #IE
ZERO #ZE
Figure 5-10. VFIXUPIMMPS Immediate Control Description
VFIXUPIMMPS-Fix Up Special Packed Float32 Values
Vol. 2C
5-197
Intel C/C++ Compiler Intrinsic Equivalent
VFIXUPIMMPS __m512 _mm512_fixupimm_ps( __m512 a, __m512 b, __m512i c, int imm8);
VFIXUPIMMPS __m512 _mm512_mask_fixupimm_ps(__m512 a, __mmask16 k, __m512 b, __m512i c, int imm8);
VFIXUPIMMPS __m512 _mm512_maskz_fixupimm_ps( __mmask16 k, __m512 a, __m512 b, __m512i c, int imm8);
VFIXUPIMMPS __m512 _mm512_fixupimm_round_ps( __m512 a, __m512 b, __m512i c, int imm8, int sae);
VFIXUPIMMPS __m512 _mm512_mask_fixupimm_round_ps(__m512 a, __mmask16 k, __m512 b, __m512i c, int imm8, int sae);
VFIXUPIMMPS __m512 _mm512_maskz_fixupimm_round_ps( __mmask16 k, __m512 a, __m512 b, __m512i c, int imm8, int sae);
VFIXUPIMMPS __m256 _mm256_fixupimm_ps( __m256 a, __m256 b, __m256i c, int imm8);
VFIXUPIMMPS __m256 _mm256_mask_fixupimm_ps(__m256 a, __mmask8 k, __m256 b, __m256i c, int imm8);
VFIXUPIMMPS __m256 _mm256_maskz_fixupimm_ps( __mmask8 k, __m256 a, __m256 b, __m256i c, int imm8);
VFIXUPIMMPS __m128 _mm_fixupimm_ps( __m128 a, __m128 b, __m128i c, int imm8);
VFIXUPIMMPS __m128 _mm_mask_fixupimm_ps(__m128 a, __mmask8 k, __m128 b, __m128i c, int imm8);
VFIXUPIMMPS __m128 _mm_maskz_fixupimm_ps( __mmask8 k, __m128 a, __m128 b, __m128i c, int imm8);
SIMD Floating-Point Exceptions
Zero, Invalid.
Other Exceptions
See Table 2-48, “Type E2 Class Exception Conditions.”
VFIXUPIMMPS-Fix Up Special Packed Float32 Values
Vol. 2C
5-198
VFIXUPIMMSD-Fix Up Special Scalar Float64 Value
Opcode/
Op /
64/32
CPUID
Description
Instruction
En
Bit Mode
Feature Flag
Support
EVEX.LLIG.66.0F3A.W1 55 /r ib
A
V/V
AVX512F
Fix up a float64 number in the low quadword element
VFIXUPIMMSD xmm1 {k1}{z},
OR AVX10.1
of xmm2 using scalar int32 table in xmm3/m64 and
xmm2, xmm3/m64{sae}, imm8
store the result in xmm1.
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
Tuple1 Scalar
ModRM:reg (r, w)
EVEX.vvvv (r)
ModRM:r/m (r)
imm8
Description
Perform a fix-up of the low quadword element encoded in double precision floating-point format in the first source
operand (the second operand) using a 32-bit, two-level look-up table specified in the low quadword element of the
second source operand (the third operand) with exception reporting specifier imm8. The element that is fixed-up
is selected by mask bit of 1 specified in the opmask k1. Mask bit of 0 in the opmask k1 or table response action of
0000b preserves the corresponding element of the first operand. The fixed-up element from the first source
operand or the preserved element in the first operand becomes the low quadword element of the destination
operand (the first operand). Bits 127:64 of the destination operand is copied from the corresponding bits of the
first source operand. The destination and first source operands are XMM registers. The second source operand can
be a XMM register or a 64- bit memory location.
The two-level look-up table perform a fix-up of each double precision floating-point input data in the first source
operand by decoding the input data encoding into 8 token types. A response table is defined for each token type
that converts the input encoding in the first source operand with one of 16 response actions.
This instruction is specifically intended for use in fixing up the results of arithmetic calculations involving one source
so that they match the spec, although it is generally useful for fixing up the results of multiple-instruction
sequences to reflect special-number inputs. For example, consider rcp(0). Input 0 to rcp, and you should get INF
according to the DX10 spec. However, evaluating rcp via Newton-Raphson, where x=approx(1/0), yields an incor-
rect result. To deal with this, VFIXUPIMMPD can be used after the N-R reciprocal sequence to set the result to the
correct value (i.e., INF when the input is 0).
If MXCSR.DAZ is not set, denormal input elements in the first source operand are considered as normal inputs and
do not trigger any fixup nor fault reporting.
Imm8 is used to set the required flags reporting. It supports #ZE and #IE fault reporting (see details below).
MXCSR.DAZ is used and refer to zmm2 only (i.e., zmm1 is not considered as zero in case MXCSR.DAZ is set).
MXCSR mask bits are ignored and are treated as if all mask bits are set to masked response). If any of the imm8
bits is set and the condition met for fault reporting, MXCSR.IE or MXCSR.ZE might be updated.
VFIXUPIMMSD-Fix Up Special Scalar Float64 Value
Vol. 2C
5-199
Operation
enum TOKEN_TYPE
{
QNAN_TOKEN := 0,
SNAN_TOKEN := 1,
ZERO_VALUE_TOKEN := 2,
POS_ONE_VALUE_TOKEN := 3,
NEG_INF_TOKEN := 4,
POS_INF_TOKEN := 5,
NEG_VALUE_TOKEN := 6,
POS_VALUE_TOKEN := 7
}
FIXUPIMM_DP (dest[63:0], src1[63:0],tbl3[63:0], imm8 [7:0]){
tsrc[63:0] := ((src1[62:52] = 0) AND (MXCSR.DAZ =1)) ? 0.0 : src1[63:0]
CASE(tsrc[63:0] of TOKEN_TYPE) {
QNAN_TOKEN: j := 0;
SNAN_TOKEN: j := 1;
ZERO_VALUE_TOKEN: j := 2;
POS_ONE_VALUE_TOKEN: j := 3;
NEG_INF_TOKEN: j := 4;
POS_INF_TOKEN: j := 5;
NEG_VALUE_TOKEN: j := 6;
POS_VALUE_TOKEN: j := 7;
}
; end source special CASE(tsrc…)
; The required response from src3 table is extracted
token_response[3:0] = tbl3[3+4*j:4*j];
CASE(token_response[3:0]) {
0000: dest[63:0] := dest[63:0]
; preserve content of DEST
0001: dest[63:0] := tsrc[63:0];
; pass through src1 normal input value, denormal as zero
0010: dest[63:0] := QNaN(tsrc[63:0]);
0011: dest[63:0] := QNAN_Indefinite;
0100:dest[63:0] := -INF;
0101: dest[63:0] := +INF;
0110: dest[63:0] := tsrc.sign? -INF : +INF;
0111: dest[63:0] := -0;
1000: dest[63:0] := +0;
1001: dest[63:0] := -1;
1010: dest[63:0] := +1;
1011: dest[63:0] := ½;
1100: dest[63:0] := 90.0;
1101: dest[63:0] := PI/2;
1110: dest[63:0] := MAX_FLOAT;
1111: dest[63:0] := -MAX_FLOAT;
}
; end of token_response CASE
; The required fault reporting from imm8 is extracted
; TOKENs are mutually exclusive and TOKENs priority defines the order.
; Multiple faults related to a single token can occur simultaneously.
IF (tsrc[63:0] of TOKEN_TYPE: ZERO_VALUE_TOKEN) AND imm8[0] then set #ZE;
IF (tsrc[63:0] of TOKEN_TYPE: ZERO_VALUE_TOKEN) AND imm8[1] then set #IE;
IF (tsrc[63:0] of TOKEN_TYPE: ONE_VALUE_TOKEN) AND imm8[2] then set #ZE;
VFIXUPIMMSD-Fix Up Special Scalar Float64 Value
Vol. 2C
5-200
IF (tsrc[63:0] of TOKEN_TYPE: ONE_VALUE_TOKEN) AND imm8[3] then set #IE;
IF (tsrc[63:0] of TOKEN_TYPE: SNAN_TOKEN) AND imm8[4] then set #IE;
IF (tsrc[63:0] of TOKEN_TYPE: NEG_INF_TOKEN) AND imm8[5] then set #IE;
IF (tsrc[63:0] of TOKEN_TYPE: NEG_VALUE_TOKEN) AND imm8[6] then set #IE;
IF (tsrc[63:0] of TOKEN_TYPE: POS_INF_TOKEN) AND imm8[7] then set #IE;
; end fault reporting
return dest[63:0];
}
; end of FIXUPIMM_DP()
VFIXUPIMMSD (EVEX encoded version)
IF k1[0] OR *no writemask*
THEN DEST[63:0] := FIXUPIMM_DP(DEST[63:0], SRC1[63:0], SRC2[63:0], imm8 [7:0])
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[63:0] remains unchanged*
ELSE DEST[63:0] := 0
; zeroing-masking
FI
FI;
DEST[127:64] := SRC1[127:64]
DEST[MAXVL-1:128] := 0
Immediate Control Description:
7
6
5
4
3
2
1
0
+ INF #IE
- VE #IE
- INF #IE
SNaN #IE
ONE #IE
ONE #ZE
ZERO #IE
ZERO #ZE
Figure 5-11. VFIXUPIMMSD Immediate Control Description
Intel C/C++ Compiler Intrinsic Equivalent
VFIXUPIMMSD __m128d _mm_fixupimm_sd( __m128d a, __m128d b, __m128i c, int imm8);
VFIXUPIMMSD __m128d _mm_mask_fixupimm_sd(__m128d a, __mmask8 k, __m128d b, __m128i c, int imm8);
VFIXUPIMMSD __m128d _mm_maskz_fixupimm_sd( __mmask8 k, __m128d a, __m128d b, __m128i c, int imm8);
VFIXUPIMMSD __m128d _mm_fixupimm_round_sd( __m128d a, __m128d b, __m128i c, int imm8, int sae);
VFIXUPIMMSD __m128d _mm_mask_fixupimm_round_sd(__m128d a, __mmask8 k, __m128d b, __m128i c, int imm8, int sae);
VFIXUPIMMSD __m128d _mm_maskz_fixupimm_round_sd( __mmask8 k, __m128d a, __m128d b, __m128i c, int imm8, int sae);
SIMD Floating-Point Exceptions
Zero, Invalid
VFIXUPIMMSD-Fix Up Special Scalar Float64 Value
Vol. 2C
5-201
Other Exceptions
See Table 2-49, “Type E3 Class Exception Conditions.”
VFIXUPIMMSD-Fix Up Special Scalar Float64 Value
Vol. 2C
5-202
VFIXUPIMMSS-Fix Up Special Scalar Float32 Value
Opcode/
Op /
64/32
CPUID
Description
Instruction
En
Bit Mode
Feature Flag
Support
EVEX.LLIG.66.0F3A.W0 55 /r ib
A
V/V
AVX512F
Fix up a float32 number in the low doubleword
VFIXUPIMMSS xmm1 {k1}{z}, xmm2,
OR AVX10.1
element in xmm2 using scalar int32 table in
xmm3/m32{sae}, imm8
xmm3/m32 and store the result in xmm1.
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
Tuple1 Scalar
ModRM:reg (r, w)
EVEX.vvvv (r)
ModRM:r/m (r)
imm8
Description
Perform a fix-up of the low doubleword element encoded in single precision floating-point format in the first source
operand (the second operand) using a 32-bit, two-level look-up table specified in the low doubleword element of
the second source operand (the third operand) with exception reporting specifier imm8. The element that is fixed-
up is selected by mask bit of 1 specified in the opmask k1. Mask bit of 0 in the opmask k1 or table response action
of 0000b preserves the corresponding element of the first operand. The fixed-up element from the first source
operand or the preserved element in the first operand becomes the low doubleword element of the destination
operand (the first operand) Bits 127:32 of the destination operand is copied from the corresponding bits of the first
source operand. The destination and first source operands are XMM registers. The second source operand can be a
XMM register or a 32-bit memory location.
The two-level look-up table perform a fix-up of each single precision floating-point input data in the first source
operand by decoding the input data encoding into 8 token types. A response table is defined for each token type
that converts the input encoding in the first source operand with one of 16 response actions.
This instruction is specifically intended for use in fixing up the results of arithmetic calculations involving one source
so that they match the spec, although it is generally useful for fixing up the results of multiple-instruction
sequences to reflect special-number inputs. For example, consider rcp(0). Input 0 to rcp, and you should get INF
according to the DX10 spec. However, evaluating rcp via Newton-Raphson, where x=approx(1/0), yields an incor-
rect result. To deal with this, VFIXUPIMMPD can be used after the N-R reciprocal sequence to set the result to the
correct value (i.e., INF when the input is 0).
If MXCSR.DAZ is not set, denormal input elements in the first source operand are considered as normal inputs and
do not trigger any fixup nor fault reporting.
Imm8 is used to set the required flags reporting. It supports #ZE and #IE fault reporting (see details below).
MXCSR.DAZ is used and refer to zmm2 only (i.e., zmm1 is not considered as zero in case MXCSR.DAZ is set).
MXCSR mask bits are ignored and are treated as if all mask bits are set to masked response). If any of the imm8
bits is set and the condition met for fault reporting, MXCSR.IE or MXCSR.ZE might be updated.
VFIXUPIMMSS-Fix Up Special Scalar Float32 Value
Vol. 2C
5-203
Operation
enum TOKEN_TYPE
{
QNAN_TOKEN := 0,
SNAN_TOKEN := 1,
ZERO_VALUE_TOKEN := 2,
POS_ONE_VALUE_TOKEN := 3,
NEG_INF_TOKEN := 4,
POS_INF_TOKEN := 5,
NEG_VALUE_TOKEN := 6,
POS_VALUE_TOKEN := 7
}
FIXUPIMM_SP (dest[31:0], src1[31:0],tbl3[31:0], imm8 [7:0]){
tsrc[31:0] := ((src1[30:23] = 0) AND (MXCSR.DAZ =1)) ? 0.0 : src1[31:0]
CASE(tsrc[63:0] of TOKEN_TYPE) {
QNAN_TOKEN: j := 0;
SNAN_TOKEN: j := 1;
ZERO_VALUE_TOKEN: j := 2;
POS_ONE_VALUE_TOKEN: j := 3;
NEG_INF_TOKEN: j := 4;
POS_INF_TOKEN: j := 5;
NEG_VALUE_TOKEN: j := 6;
POS_VALUE_TOKEN: j := 7;
}
; end source special CASE(tsrc…)
; The required response from src3 table is extracted
token_response[3:0] = tbl3[3+4*j:4*j];
CASE(token_response[3:0]) {
0000: dest[31:0] := dest[31:0];
; preserve content of DEST
0001: dest[31:0] := tsrc[31:0];
; pass through src1 normal input value, denormal as zero
0010: dest[31:0] := QNaN(tsrc[31:0]);
0011: dest[31:0] := QNAN_Indefinite;
0100: dest[31:0] := -INF;
0101: dest[31:0] := +INF;
0110: dest[31:0] := tsrc.sign? -INF : +INF;
0111: dest[31:0] := -0;
1000: dest[31:0] := +0;
1001: dest[31:0] := -1;
1010: dest[31:0] := +1;
1011: dest[31:0] := ½;
1100: dest[31:0] := 90.0;
1101: dest[31:0] := PI/2;
1110: dest[31:0] := MAX_FLOAT;
1111: dest[31:0] := -MAX_FLOAT;
}
; end of token_response CASE
; The required fault reporting from imm8 is extracted
; TOKENs are mutually exclusive and TOKENs priority defines the order.
; Multiple faults related to a single token can occur simultaneously.
IF (tsrc[31:0] of TOKEN_TYPE: ZERO_VALUE_TOKEN) AND imm8[0] then set #ZE;
IF (tsrc[31:0] of TOKEN_TYPE: ZERO_VALUE_TOKEN) AND imm8[1] then set #IE;
IF (tsrc[31:0] of TOKEN_TYPE: ONE_VALUE_TOKEN) AND imm8[2] then set #ZE;
VFIXUPIMMSS-Fix Up Special Scalar Float32 Value
Vol. 2C
5-204
IF (tsrc[31:0] of TOKEN_TYPE: ONE_VALUE_TOKEN) AND imm8[3] then set #IE;
IF (tsrc[31:0] of TOKEN_TYPE: SNAN_TOKEN) AND imm8[4] then set #IE;
IF (tsrc[31:0] of TOKEN_TYPE: NEG_INF_TOKEN) AND imm8[5] then set #IE;
IF (tsrc[31:0] of TOKEN_TYPE: NEG_VALUE_TOKEN) AND imm8[6] then set #IE;
IF (tsrc[31:0] of TOKEN_TYPE: POS_INF_TOKEN) AND imm8[7] then set #IE;
; end fault reporting
return dest[31:0];
}
; end of FIXUPIMM_SP()
VFIXUPIMMSS (EVEX encoded version)
IF k1[0] OR *no writemask*
THEN DEST[31:0] := FIXUPIMM_SP(DEST[31:0], SRC1[31:0], SRC2[31:0], imm8 [7:0])
ELSE
IF *merging-masking*
; merging-masking
THEN *DEST[31:0] remains unchanged*
ELSE DEST[31:0] := 0
; zeroing-masking
FI
FI;
DEST[127:32] := SRC1[127:32]
DEST[MAXVL-1:128] := 0
Immediate Control Description:
7
6
5
4
3
2
1
0
+ INF #IE
- VE #IE
- INF #IE
SNaN #IE
ONE #IE
ONE #ZE
ZERO #IE
ZERO #ZE
Figure 5-12. VFIXUPIMMSS Immediate Control Description
Intel C/C++ Compiler Intrinsic Equivalent
VFIXUPIMMSS __m128 _mm_fixupimm_ss( __m128 a, __m128 b, __m128i c, int imm8);
VFIXUPIMMSS __m128 _mm_mask_fixupimm_ss(__m128 a, __mmask8 k, __m128 b, __m128i c, int imm8);
VFIXUPIMMSS __m128 _mm_maskz_fixupimm_ss( __mmask8 k, __m128 a, __m128 b, __m128i c, int imm8);
VFIXUPIMMSS __m128 _mm_fixupimm_round_ss( __m128 a, __m128 b, __m128i c, int imm8, int sae);
VFIXUPIMMSS __m128 _mm_mask_fixupimm_round_ss(__m128 a, __mmask8 k, __m128 b, __m128i c, int imm8, int sae);
VFIXUPIMMSS __m128 _mm_maskz_fixupimm_round_ss( __mmask8 k, __m128 a, __m128 b, __m128i c, int imm8, int sae);
VFIXUPIMMSS-Fix Up Special Scalar Float32 Value
Vol. 2C
5-205
SIMD Floating-Point Exceptions
Zero, Invalid
Other Exceptions
See Table 2-49, “Type E3 Class Exception Conditions.”
VFIXUPIMMSS-Fix Up Special Scalar Float32 Value
Vol. 2C
5-206
VFMADD132PD/VFMADD213PD/VFMADD231PD-Fused Multiply-Add of Packed Double
Precision Floating-Point Values
Opcode/
Op/
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
VEX.128.66.0F38.W1 98 /r
A
V/V
FMA
Multiply packed double precision floating-point
VFMADD132PD xmm1, xmm2,
values from xmm1 and xmm3/mem, add to
xmm3/m128
xmm2 and put result in xmm1.
VEX.128.66.0F38.W1 A8 /r
A
V/V
FMA
Multiply packed double precision floating-point
VFMADD213PD xmm1, xmm2,
values from xmm1 and xmm2, add to
xmm3/m128
xmm3/mem and put result in xmm1.
VEX.128.66.0F38.W1 B8 /r
A
V/V
FMA
Multiply packed double precision floating-point
VFMADD231PD xmm1, xmm2,
values from xmm2 and xmm3/mem, add to
xmm3/m128
xmm1 and put result in xmm1.
VEX.256.66.0F38.W1 98 /r
A
V/V
FMA
Multiply packed double precision floating-point
VFMADD132PD ymm1, ymm2,
values from ymm1 and ymm3/mem, add to
ymm3/m256
ymm2 and put result in ymm1.
VEX.256.66.0F38.W1 A8 /r
A
V/V
FMA
Multiply packed double precision floating-point
VFMADD213PD ymm1, ymm2,
values from ymm1 and ymm2, add to
ymm3/m256
ymm3/mem and put result in ymm1.
VEX.256.66.0F38.W1 B8 /r
A
V/V
FMA
Multiply packed double precision floating-point
VFMADD231PD ymm1, ymm2,
values from ymm2 and ymm3/mem, add to
ymm3/m256
ymm1 and put result in ymm1.
EVEX.128.66.0F38.W1 98 /r
B
V/V
(AVX512VL AND
Multiply packed double precision floating-point
VFMADD132PD xmm1 {k1}{z}, xmm2,
AVX512F) OR
values from xmm1 and xmm3/m128/m64bcst,
xmm3/m128/m64bcst
AVX10.1
add to xmm2 and put result in xmm1.
EVEX.128.66.0F38.W1 A8 /r
B
V/V
(AVX512VL AND
Multiply packed double precision floating-point
VFMADD213PD xmm1 {k1}{z}, xmm2,
AVX512F) OR
values from xmm1 and xmm2, add to
xmm3/m128/m64bcst
AVX10.1
xmm3/m128/m64bcst and put result in xmm1.
EVEX.128.66.0F38.W1 B8 /r
B
V/V
(AVX512VL AND
Multiply packed double precision floating-point
VFMADD231PD xmm1 {k1}{z}, xmm2,
AVX512F) OR
values from xmm2 and xmm3/m128/m64bcst,
xmm3/m128/m64bcst
AVX10.1
add to xmm1 and put result in xmm1.
EVEX.256.66.0F38.W1 98 /r
B
V/V
(AVX512VL AND
Multiply packed double precision floating-point
VFMADD132PD ymm1 {k1}{z}, ymm2,
AVX512F) OR
values from ymm1 and ymm3/m256/m64bcst,
ymm3/m256/m64bcst
AVX10.1
add to ymm2 and put result in ymm1.
EVEX.256.66.0F38.W1 A8 /r
B
V/V
(AVX512VL AND
Multiply packed double precision floating-point
VFMADD213PD ymm1 {k1}{z}, ymm2,
AVX512F) OR
values from ymm1 and ymm2, add to
ymm3/m256/m64bcst
AVX10.1
ymm3/m256/m64bcst and put result in ymm1.
EVEX.256.66.0F38.W1 B8 /r
B
V/V
(AVX512VL AND
Multiply packed double precision floating-point
VFMADD231PD ymm1 {k1}{z}, ymm2,
AVX512F) OR
values from ymm2 and ymm3/m256/m64bcst,
ymm3/m256/m64bcst
AVX10.1
add to ymm1 and put result in ymm1.
EVEX.512.66.0F38.W1 98 /r
B
V/V
AVX512F
Multiply packed double precision floating-point
VFMADD132PD zmm1 {k1}{z}, zmm2,
OR AVX10.1
values from zmm1 and zmm3/m512/m64bcst,
zmm3/m512/m64bcst{er}
add to zmm2 and put result in zmm1.
EVEX.512.66.0F38.W1 A8 /r
B
V/V
AVX512F
Multiply packed double precision floating-point
VFMADD213PD zmm1 {k1}{z}, zmm2,
OR AVX10.1
values from zmm1 and zmm2, add to
zmm3/m512/m64bcst{er}
zmm3/m512/m64bcst and put result in zmm1.
EVEX.512.66.0F38.W1 B8 /r
B
V/V
AVX512F
Multiply packed double precision floating-point
VFMADD231PD zmm1 {k1}{z}, zmm2,
OR AVX10.1
values from zmm2 and zmm3/m512/m64bcst,
zmm3/m512/m64bcst{er}
add to zmm1 and put result in zmm1.
VFMADD132PD/VFMADD213PD/VFMADD231PD-Fused Multiply-Add of Packed Double Precision Floating-Point Values
Vol. 2C
5-207
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
B
Full
ModRM:reg (r, w)
EVEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
Performs a set of SIMD multiply-add computation on packed double precision floating-point values using three
source operands and writes the multiply-add results in the destination operand. The destination operand is also the
first source operand. The second operand must be a SIMD register. The third source operand can be a SIMD
register or a memory location.
VFMADD132PD: Multiplies the two, four or eight packed double precision floating-point values from the first source
operand to the two, four or eight packed double precision floating-point values in the third source operand, adds
the infinite precision intermediate result to the two, four or eight packed double precision floating-point values in
the second source operand, performs rounding and stores the resulting two, four or eight packed double precision
floating-point values to the destination operand (first source operand).
VFMADD213PD: Multiplies the two, four or eight packed double precision floating-point values from the second
source operand to the two, four or eight packed double precision floating-point values in the first source operand,
adds the infinite precision intermediate result to the two, four or eight packed double precision floating-point
values in the third source operand, performs rounding and stores the resulting two, four or eight packed double
precision floating-point values to the destination operand (first source operand).
VFMADD231PD: Multiplies the two, four or eight packed double precision floating-point values from the second
source to the two, four or eight packed double precision floating-point values in the third source operand, adds the
infinite precision intermediate result to the two, four or eight packed double precision floating-point values in the
first source operand, performs rounding and stores the resulting two, four or eight packed double precision
floating-point values to the destination operand (first source operand).
EVEX encoded versions: The destination operand (also first source operand) is a ZMM register and encoded in
reg_field. The second source operand is a ZMM register and encoded in EVEX.vvvv. The third source operand is a
ZMM register, a 512-bit memory location, or a 512-bit vector broadcasted from a 64-bit memory location. The
destination operand is conditionally updated with write mask k1.
VEX.256 encoded version: The destination operand (also first source operand) is a YMM register and encoded in
reg_field. The second source operand is a YMM register and encoded in VEX.vvvv. The third source operand is a
YMM register or a 256-bit memory location and encoded in rm_field.
VEX.128 encoded version: The destination operand (also first source operand) is a XMM register and encoded in
reg_field. The second source operand is a XMM register and encoded in VEX.vvvv. The third source operand is a
XMM register or a 128-bit memory location and encoded in rm_field. The upper 128 bits of the YMM destination
register are zeroed.
VFMADD132PD/VFMADD213PD/VFMADD231PD-Fused Multiply-Add of Packed Double Precision Floating-Point Values
Vol. 2C
5-208
Operation
In the operations below, “*” and “+” symbols represent multiplication and addition with infinite precision inputs and outputs (no
rounding).
VFMADD132PD DEST, SRC2, SRC3 (VEX encoded version)
IF (VEX.128) THEN
MAXNUM := 2
ELSEIF (VEX.256)
MAXNUM := 4
FI
For i = 0 to MAXNUM-1 {
n := 64*i;
DEST[n+63:n] := RoundFPControl_MXCSR(DEST[n+63:n]*SRC3[n+63:n] + SRC2[n+63:n])
}
IF (VEX.128) THEN
DEST[MAXVL-1:128] := 0
ELSEIF (VEX.256)
DEST[MAXVL-1:256] := 0
FI
VFMADD213PD DEST, SRC2, SRC3 (VEX encoded version)
IF (VEX.128) THEN
MAXNUM := 2
ELSEIF (VEX.256)
MAXNUM := 4
FI
For i = 0 to MAXNUM-1 {
n := 64*i;
DEST[n+63:n] := RoundFPControl_MXCSR(SRC2[n+63:n]*DEST[n+63:n] + SRC3[n+63:n])
}
IF (VEX.128) THEN
DEST[MAXVL-1:128] := 0
ELSEIF (VEX.256)
DEST[MAXVL-1:256] := 0
FI
VFMADD231PD DEST, SRC2, SRC3 (VEX encoded version)
IF (VEX.128) THEN
MAXNUM := 2
ELSEIF (VEX.256)
MAXNUM := 4
FI
For i = 0 to MAXNUM-1 {
n := 64*i;
DEST[n+63:n] := RoundFPControl_MXCSR(SRC2[n+63:n]*SRC3[n+63:n] + DEST[n+63:n])
}
IF (VEX.128) THEN
DEST[MAXVL-1:128] := 0
ELSEIF (VEX.256)
DEST[MAXVL-1:256] := 0
FI
VFMADD132PD/VFMADD213PD/VFMADD231PD-Fused Multiply-Add of Packed Double Precision Floating-Point Values
Vol. 2C
5-209
VFMADD132PD DEST, SRC2, SRC3 (EVEX encoded version, when src3 operand is a 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] :=
RoundFPControl(DEST[i+63:i]*SRC3[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
VFMADD132PD DEST, SRC2, SRC3 (EVEX encoded version, when src3 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] :=
RoundFPControl_MXCSR(DEST[i+63:i]*SRC3[63:0] + SRC2[i+63:i])
ELSE
DEST[i+63:i] :=
RoundFPControl_MXCSR(DEST[i+63:i]*SRC3[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
VFMADD132PD/VFMADD213PD/VFMADD231PD-Fused Multiply-Add of Packed Double Precision Floating-Point Values
Vol. 2C
5-210
VFMADD213PD DEST, SRC2, SRC3 (EVEX encoded version, when src3 operand is a is a 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] :=
RoundFPControl(SRC2[i+63:i]*DEST[i+63:i] + SRC3[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
VFMADD213PD DEST, SRC2, SRC3 (EVEX encoded version, when src3 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] :=
RoundFPControl_MXCSR(SRC2[i+63:i]*DEST[i+63:i] + SRC3[63:0])
ELSE
DEST[i+63:i] :=
RoundFPControl_MXCSR(SRC2[i+63:i]*DEST[i+63:i] + SRC3[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
VFMADD132PD/VFMADD213PD/VFMADD231PD-Fused Multiply-Add of Packed Double Precision Floating-Point Values
Vol. 2C
5-211
VFMADD231PD DEST, SRC2, SRC3 (EVEX encoded version, when src3 operand is a 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] :=
RoundFPControl(SRC2[i+63:i]*SRC3[i+63:i] + DEST[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
VFMADD231PD DEST, SRC2, SRC3 (EVEX encoded version, when src3 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] :=
RoundFPControl_MXCSR(SRC2[i+63:i]*SRC3[63:0] + DEST[i+63:i])
ELSE
DEST[i+63:i] :=
RoundFPControl_MXCSR(SRC2[i+63:i]*SRC3[i+63:i] + DEST[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
VFMADD132PD/VFMADD213PD/VFMADD231PD-Fused Multiply-Add of Packed Double Precision Floating-Point Values
Vol. 2C
5-212
Intel C/C++ Compiler Intrinsic Equivalent
VFMADDxxxPD __m512d _mm512_fmadd_pd(__m512d a, __m512d b, __m512d c);
VFMADDxxxPD __m512d _mm512_fmadd_round_pd(__m512d a, __m512d b, __m512d c, int r);
VFMADDxxxPD __m512d _mm512_mask_fmadd_pd(__m512d a, __mmask8 k, __m512d b, __m512d c);
VFMADDxxxPD __m512d _mm512_maskz_fmadd_pd(__mmask8 k, __m512d a, __m512d b, __m512d c);
VFMADDxxxPD __m512d _mm512_mask3_fmadd_pd(__m512d a, __m512d b, __m512d c, __mmask8 k);
VFMADDxxxPD __m512d _mm512_mask_fmadd_round_pd(__m512d a, __mmask8 k, __m512d b, __m512d c, int r);
VFMADDxxxPD __m512d _mm512_maskz_fmadd_round_pd(__mmask8 k, __m512d a, __m512d b, __m512d c, int r);
VFMADDxxxPD __m512d _mm512_mask3_fmadd_round_pd(__m512d a, __m512d b, __m512d c, __mmask8 k, int r);
VFMADDxxxPD __m256d _mm256_mask_fmadd_pd(__m256d a, __mmask8 k, __m256d b, __m256d c);
VFMADDxxxPD __m256d _mm256_maskz_fmadd_pd(__mmask8 k, __m256d a, __m256d b, __m256d c);
VFMADDxxxPD __m256d _mm256_mask3_fmadd_pd(__m256d a, __m256d b, __m256d c, __mmask8 k);
VFMADDxxxPD __m128d _mm_mask_fmadd_pd(__m128d a, __mmask8 k, __m128d b, __m128d c);
VFMADDxxxPD __m128d _mm_maskz_fmadd_pd(__mmask8 k, __m128d a, __m128d b, __m128d c);
VFMADDxxxPD __m128d _mm_mask3_fmadd_pd(__m128d a, __m128d b, __m128d c, __mmask8 k);
VFMADDxxxPD __m128d _mm_fmadd_pd (__m128d a, __m128d b, __m128d c);
VFMADDxxxPD __m256d _mm256_fmadd_pd (__m256d a, __m256d b, __m256d c);
SIMD Floating-Point Exceptions
Overflow, Underflow, Invalid, Precision, Denormal.
Other Exceptions
VEX-encoded instructions, see Table 2-19, “Type 2 Class Exception Conditions.”
EVEX-encoded instructions, see Table 2-48, “Type E2 Class Exception Conditions.”
VFMADD132PD/VFMADD213PD/VFMADD231PD-Fused Multiply-Add of Packed Double Precision Floating-Point Values
Vol. 2C
5-213
VF[,N]MADD[132,213,231]PH-Fused Multiply-Add of Packed FP16 Values
Opcode/
Op/
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.128.66.MAP6.W0 98 /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from xmm1 and
VFMADD132PH xmm1{k1}{z}, xmm2,
AND AVX512VL)
xmm3/m128/m16bcst, add to xmm2, and store
xmm3/m128/m16bcst
OR AVX10.1
the result in xmm1.
EVEX.256.66.MAP6.W0 98 /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from ymm1 and
VFMADD132PH ymm1{k1}{z}, ymm2,
AND AVX512VL)
ymm3/m256/m16bcst, add to ymm2, and store
ymm3/m256/m16bcst
OR AVX10.1
the result in ymm1.
EVEX.512.66.MAP6.W0 98 /r
A
V/V
AVX512_FP16
Multiply packed FP16 values from zmm1 and
VFMADD132PH zmm1{k1}{z}, zmm2,
OR AVX10.1
zmm3/m512/m16bcst, add to zmm2, and store
zmm3/m512/m16bcst {er}
the result in zmm1.
EVEX.128.66.MAP6.W0 A8 /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from xmm1 and
VFMADD213PH xmm1{k1}{z}, xmm2,
AND AVX512VL)
xmm2, add to xmm3/m128/m16bcst, and store
xmm3/m128/m16bcst
OR AVX10.1
the result in xmm1.
EVEX.256.66.MAP6.W0 A8 /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from ymm1 and
VFMADD213PH ymm1{k1}{z}, ymm2,
AND AVX512VL)
ymm2, add to ymm3/m256/m16bcst, and store
ymm3/m256/m16bcst
OR AVX10.1
the result in ymm1.
EVEX.512.66.MAP6.W0 A8 /r
A
V/V
AVX512_FP16
Multiply packed FP16 values from zmm1 and
VFMADD213PH zmm1{k1}{z}, zmm2,
OR AVX10.1
zmm2, add to zmm3/m512/m16bcst, and store
zmm3/m512/m16bcst {er}
the result in zmm1.
EVEX.128.66.MAP6.W0 B8 /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from xmm2 and
VFMADD231PH xmm1{k1}{z}, xmm2,
AND AVX512VL)
xmm3/m128/m16bcst, add to xmm1, and store
xmm3/m128/m16bcst
OR AVX10.1
the result in xmm1.
EVEX.256.66.MAP6.W0 B8 /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from ymm2 and
VFMADD231PH ymm1{k1}{z}, ymm2,
AND AVX512VL)
ymm3/m256/m16bcst, add to ymm1, and store
ymm3/m256/m16bcst
OR AVX10.1
the result in ymm1.
EVEX.512.66.MAP6.W0 B8 /r
A
V/V
AVX512_FP16
Multiply packed FP16 values from zmm2 and
VFMADD231PH zmm1{k1}{z}, zmm2,
OR AVX10.1
zmm3/m512/m16bcst, add to zmm1, and store
zmm3/m512/m16bcst {er}
the result in zmm1.
EVEX.128.66.MAP6.W0 9C /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from xmm1 and
VFNMADD132PH xmm1{k1}{z},
AND AVX512VL)
xmm3/m128/m16bcst, and negate the value.
xmm2, xmm3/m128/m16bcst
OR AVX10.1
Add this value to xmm2, and store the result in
xmm1.
EVEX.256.66.MAP6.W0 9C /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from ymm1 and
VFNMADD132PH ymm1{k1}{z},
AND AVX512VL)
ymm3/m256/m16bcst, and negate the value.
ymm2, ymm3/m256/m16bcst
OR AVX10.1
Add this value to ymm2, and store the result in
ymm1.
EVEX.512.66.MAP6.W0 9C /r
A
V/V
AVX512_FP16
Multiply packed FP16 values from zmm1 and
VFNMADD132PH zmm1{k1}{z},
OR AVX10.1
zmm3/m512/m16bcst, and negate the value.
zmm2, zmm3/m512/m16bcst {er}
Add this value to zmm2, and store the result in
zmm1.
EVEX.128.66.MAP6.W0 AC /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from xmm1 and
VFNMADD213PH xmm1{k1}{z},
AND AVX512VL)
xmm2, and negate the value. Add this value to
xmm2, xmm3/m128/m16bcst
OR AVX10.1
xmm3/m128/m16bcst, and store the result in
xmm1.
EVEX.256.66.MAP6.W0 AC /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from ymm1 and
VFNMADD213PH ymm1{k1}{z},
AND AVX512VL)
ymm2, and negate the value. Add this value to
ymm2, ymm3/m256/m16bcst
OR AVX10.1
ymm3/m256/m16bcst, and store the result in
ymm1.
VF[,N]MADD[132,213,231]PH-Fused Multiply-Add of Packed FP16 Values
Vol. 2C
5-214
Opcode/
Op/
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
EVEX.512.66.MAP6.W0 AC /r
A
V/V
AVX512_FP16
Multiply packed FP16 values from zmm1 and
VFNMADD213PH zmm1{k1}{z},
OR AVX10.1
zmm2, and negate the value. Add this value to
zmm2, zmm3/m512/m16bcst {er}
zmm3/m512/m16bcst, and store the result in
zmm1.
EVEX.128.66.MAP6.W0 BC /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from xmm2 and
VFNMADD231PH xmm1{k1}{z},
AND AVX512VL)
xmm3/m128/m16bcst, and negate the value.
xmm2, xmm3/m128/m16bcst
OR AVX10.1
Add this value to xmm1, and store the result in
xmm1.
EVEX.256.66.MAP6.W0 BC /r
A
V/V
(AVX512_FP16
Multiply packed FP16 values from ymm2 and
VFNMADD231PH ymm1{k1}{z},
AND AVX512VL)
ymm3/m256/m16bcst, and negate the value.
ymm2, ymm3/m256/m16bcst
OR AVX10.1
Add this value to ymm1, and store the result in
ymm1.
EVEX.512.66.MAP6.W0 BC /r
A
V/V
AVX512_FP16
Multiply packed FP16 values from zmm2 and
VFNMADD231PH zmm1{k1}{z},
OR AVX10.1
zmm3/m512/m16bcst, and negate the value.
zmm2, zmm3/m512/m16bcst {er}
Add this value to zmm1, and store the result in
zmm1.
Instruction Operand Encoding
Op/En
Tuple
Operand 1
Operand 2
Operand 3
Operand 4
A
Full
ModRM:reg (r, w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
This instruction performs a packed multiply-add or negated multiply-add computation on FP16 values using three
source operands and writes the results in the destination operand. The destination operand is also the first source
operand. The “N” (negated) forms of this instruction add the negated infinite precision intermediate product to the
corresponding remaining operand. The notation’ “132”, “213” and “231” indicate the use of the operands in ±A * B
+ C, where each digit corresponds to the operand number, with the destination being operand 1; see Table 5-5.
The destination elements are updated according to the writemask.
Table 5-5. VF[,N]MADD[132,213,231]PH Notation for Operands
Notation
Operands
132
dest = ± dest*src3+src2
231
dest = ± src2*src3+dest
213
dest = ± src2*dest+src3
VF[,N]MADD[132,213,231]PH-Fused Multiply-Add of Packed FP16 Values
Vol. 2C
5-215
Operation
VF[,N]MADD132PH DEST, SRC2, SRC3 (EVEX encoded versions) when src3 operand is a register
VL = 128, 256 or 512
KL := VL/16
IF (VL = 512) AND (EVEX.b = 1):
SET_RM(EVEX.RC)
ELSE
SET_RM(MXCSR.RC)
FOR j := 0 TO KL-1:
IF k1[j] OR *no writemask*:
IF *negative form*:
DEST.fp16[j] := RoundFPControl(-DEST.fp16[j]*SRC3.fp16[j] + SRC2.fp16[j])
ELSE:
DEST.fp16[j] := RoundFPControl(DEST.fp16[j]*SRC3.fp16[j] + SRC2.fp16[j])
ELSE IF *zeroing*:
DEST.fp16[j] := 0
// else dest.fp16[j] remains unchanged
DEST[MAXVL-1:VL] := 0
VF[,N]MADD132PH DEST, SRC2, SRC3 (EVEX encoded versions) when src3 operand is a memory source
VL = 128, 256 or 512
KL := VL/16
FOR j := 0 TO KL-1:
IF k1[j] OR *no writemask*:
IF EVEX.b = 1:
t3 := SRC3.fp16[0]
ELSE:
t3 := SRC3.fp16[j]
IF *negative form*:
DEST.fp16[j] := RoundFPControl(-DEST.fp16[j] * t3 + SRC2.fp16[j])
ELSE:
DEST.fp16[j] := RoundFPControl(DEST.fp16[j] * t3 + SRC2.fp16[j])
ELSE IF *zeroing*:
DEST.fp16[j] := 0
// else dest.fp16[j] remains unchanged
DEST[MAXVL-1:VL] := 0
VF[,N]MADD[132,213,231]PH-Fused Multiply-Add of Packed FP16 Values
Vol. 2C
5-216
VF[,N]MADD213PH DEST, SRC2, SRC3 (EVEX encoded versions) when src3 operand is a register
VL = 128, 256 or 512
KL := VL/16
IF (VL = 512) AND (EVEX.b = 1):
SET_RM(EVEX.RC)
ELSE
SET_RM(MXCSR.RC)
FOR j := 0 TO KL-1:
IF k1[j] OR *no writemask*:
IF *negative form*:
DEST.fp16[j] := RoundFPControl(-SRC2.fp16[j]*DEST.fp16[j] + SRC3.fp16[j])
ELSE
DEST.fp16[j] := RoundFPControl(SRC2.fp16[j]*DEST.fp16[j] + SRC3.fp16[j])
ELSE IF *zeroing*:
DEST.fp16[j] := 0
// else dest.fp16[j] remains unchanged
DEST[MAXVL-1:VL] := 0
VF[,N]MADD213PH DEST, SRC2, SRC3 (EVEX encoded versions) when src3 operand is a memory source
VL = 128, 256 or 512
KL := VL/16
FOR j := 0 TO KL-1:
IF k1[j] OR *no writemask*:
IF EVEX.b = 1:
t3 := SRC3.fp16[0]
ELSE:
t3 := SRC3.fp16[j]
IF *negative form*:
DEST.fp16[j] := RoundFPControl(-SRC2.fp16[j] * DEST.fp16[j] + t3 )
ELSE:
DEST.fp16[j] := RoundFPControl(SRC2.fp16[j] * DEST.fp16[j] + t3 )
ELSE IF *zeroing*:
DEST.fp16[j] := 0
// else dest.fp16[j] remains unchanged
DEST[MAXVL-1:VL] := 0
VF[,N]MADD[132,213,231]PH-Fused Multiply-Add of Packed FP16 Values
Vol. 2C
5-217
VF[,N]MADD231PH DEST, SRC2, SRC3 (EVEX encoded versions) when src3 operand is a register
VL = 128, 256 or 512
KL := VL/16
IF (VL = 512) AND (EVEX.b = 1):
SET_RM(EVEX.RC)
ELSE
SET_RM(MXCSR.RC)
FOR j := 0 TO KL-1:
IF k1[j] OR *no writemask*:
IF *negative form:
DEST.fp16[j] := RoundFPControl(-SRC2.fp16[j]*SRC3.fp16[j] + DEST.fp16[j])
ELSE:
DEST.fp16[j] := RoundFPControl(SRC2.fp16[j]*SRC3.fp16[j] + DEST.fp16[j])
ELSE IF *zeroing*:
DEST.fp16[j] := 0
// else dest.fp16[j] remains unchanged
DEST[MAXVL-1:VL] := 0
VF[,N]MADD231PH DEST, SRC2, SRC3 (EVEX encoded versions) when src3 operand is a memory source
VL = 128, 256 or 512
KL := VL/16
FOR j := 0 TO KL-1:
IF k1[j] OR *no writemask*:
IF EVEX.b = 1:
t3 := SRC3.fp16[0]
ELSE:
t3 := SRC3.fp16[j]
IF *negative form*:
DEST.fp16[j] := RoundFPControl(-SRC2.fp16[j] * t3 + DEST.fp16[j] )
ELSE:
DEST.fp16[j] := RoundFPControl(SRC2.fp16[j] * t3 + DEST.fp16[j] )
ELSE IF *zeroing*:
DEST.fp16[j] := 0
// else dest.fp16[j] remains unchanged
DEST[MAXVL-1:VL] := 0
VF[,N]MADD[132,213,231]PH-Fused Multiply-Add of Packed FP16 Values
Vol. 2C
5-218
Intel C/C++ Compiler Intrinsic Equivalent
VFMADD132PH, VFMADD213PH , and VFMADD231PH:
__m128h _mm_fmadd_ph (__m128h a, __m128h b, __m128h c);
__m128h _mm_mask_fmadd_ph (__m128h a, __mmask8 k, __m128h b, __m128h c);
__m128h _mm_mask3_fmadd_ph (__m128h a, __m128h b, __m128h c, __mmask8 k);
__m128h _mm_maskz_fmadd_ph (__mmask8 k, __m128h a, __m128h b, __m128h c);
__m256h _mm256_fmadd_ph (__m256h a, __m256h b, __m256h c);
__m256h _mm256_mask_fmadd_ph (__m256h a, __mmask16 k, __m256h b, __m256h c);
__m256h _mm256_mask3_fmadd_ph (__m256h a, __m256h b, __m256h c, __mmask16 k);
__m256h _mm256_maskz_fmadd_ph (__mmask16 k, __m256h a, __m256h b, __m256h c);
__m512h _mm512_fmadd_ph (__m512h a, __m512h b, __m512h c);
__m512h _mm512_mask_fmadd_ph (__m512h a, __mmask32 k, __m512h b, __m512h c);
__m512h _mm512_mask3_fmadd_ph (__m512h a, __m512h b, __m512h c, __mmask32 k);
__m512h _mm512_maskz_fmadd_ph (__mmask32 k, __m512h a, __m512h b, __m512h c);
__m512h _mm512_fmadd_round_ph (__m512h a, __m512h b, __m512h c, const int rounding);
__m512h _mm512_mask_fmadd_round_ph (__m512h a, __mmask32 k, __m512h b, __m512h c, const int rounding);
__m512h _mm512_mask3_fmadd_round_ph (__m512h a, __m512h b, __m512h c, __mmask32 k, const int rounding);
__m512h _mm512_maskz_fmadd_round_ph (__mmask32 k, __m512h a, __m512h b, __m512h c, const int rounding);
VFNMADD132PH, VFNMADD213PH, and VFNMADD231PH:
__m128h _mm_fnmadd_ph (__m128h a, __m128h b, __m128h c);
__m128h _mm_mask_fnmadd_ph (__m128h a, __mmask8 k, __m128h b, __m128h c);
__m128h _mm_mask3_fnmadd_ph (__m128h a, __m128h b, __m128h c, __mmask8 k);
__m128h _mm_maskz_fnmadd_ph (__mmask8 k, __m128h a, __m128h b, __m128h c);
__m256h _mm256_fnmadd_ph (__m256h a, __m256h b, __m256h c);
__m256h _mm256_mask_fnmadd_ph (__m256h a, __mmask16 k, __m256h b, __m256h c);
__m256h _mm256_mask3_fnmadd_ph (__m256h a, __m256h b, __m256h c, __mmask16 k);
__m256h _mm256_maskz_fnmadd_ph (__mmask16 k, __m256h a, __m256h b, __m256h c);
__m512h _mm512_fnmadd_ph (__m512h a, __m512h b, __m512h c);
__m512h _mm512_mask_fnmadd_ph (__m512h a, __mmask32 k, __m512h b, __m512h c);
__m512h _mm512_mask3_fnmadd_ph (__m512h a, __m512h b, __m512h c, __mmask32 k);
__m512h _mm512_maskz_fnmadd_ph (__mmask32 k, __m512h a, __m512h b, __m512h c);
__m512h _mm512_fnmadd_round_ph (__m512h a, __m512h b, __m512h c, const int rounding);
__m512h _mm512_mask_fnmadd_round_ph (__m512h a, __mmask32 k, __m512h b, __m512h c, const int rounding);
__m512h _mm512_mask3_fnmadd_round_ph (__m512h a, __m512h b, __m512h c, __mmask32 k, const int rounding);
__m512h _mm512_maskz_fnmadd_round_ph (__mmask32 k, __m512h a, __m512h b, __m512h c, const int rounding);
SIMD Floating-Point Exceptions
Invalid, Underflow, Overflow, Precision, Denormal
Other Exceptions
EVEX-encoded instructions, see Table 2-48, “Type E2 Class Exception Conditions.”
VF[,N]MADD[132,213,231]PH-Fused Multiply-Add of Packed FP16 Values
Vol. 2C
5-219
VFMADD132PS/VFMADD213PS/VFMADD231PS-Fused Multiply-Add of Packed Single
Precision Floating-Point Values
Opcode/
Op/
64/32
CPUID Feature
Description
Instruction
En
Bit Mode
Flag
Support
VEX.128.66.0F38.W0 98 /r
A
V/V
FMA
Multiply packed single precision floating-point
VFMADD132PS xmm1, xmm2,
values from xmm1 and xmm3/mem, add to
xmm3/m128
xmm2 and put result in xmm1.
VEX.128.66.0F38.W0 A8 /r
A
V/V
FMA
Multiply packed single precision floating-point
VFMADD213PS xmm1, xmm2,
values from xmm1 and xmm2, add to
xmm3/m128
xmm3/mem and put result in xmm1.
VEX.128.66.0F38.W0 B8 /r
A
V/V
FMA
Multiply packed single precision floating-point
VFMADD231PS xmm1, xmm2,
values from xmm2 and xmm3/mem, add to
xmm3/m128
xmm1 and put result in xmm1.
VEX.256.66.0F38.W0 98 /r
A
V/V
FMA
Multiply packed single precision floating-point
VFMADD132PS ymm1, ymm2,
values from ymm1 and ymm3/mem, add to
ymm3/m256
ymm2 and put result in ymm1.
VEX.256.66.0F38.W0 A8 /r
A
V/V
FMA
Multiply packed single precision floating-point
VFMADD213PS ymm1, ymm2,
values from ymm1 and ymm2, add to
ymm3/m256
ymm3/mem and put result in ymm1.
VEX.256.66.0F38.0 B8 /r
A
V/V
FMA
Multiply packed single precision floating-point
VFMADD231PS ymm1, ymm2,
values from ymm2 and ymm3/mem, add to
ymm3/m256
ymm1 and put result in ymm1.
EVEX.128.66.0F38.W0 98 /r
B
V/V
(AVX512VL
Multiply packed single precision floating-point
VFMADD132PS xmm1 {k1}{z}, xmm2,
AND AVX512F)
values from xmm1 and xmm3/m128/m32bcst,
xmm3/m128/m32bcst
OR AVX10.1
add to xmm2 and put result in xmm1.
EVEX.128.66.0F38.W0 A8 /r
B
V/V
(AVX512VL
Multiply packed single precision floating-point
VFMADD213PS xmm1 {k1}{z}, xmm2,
AND AVX512F)
values from xmm1 and xmm2, add to
xmm3/m128/m32bcst
OR AVX10.1
xmm3/m128/m32bcst and put result in xmm1.
EVEX.128.66.0F38.W0 B8 /r
B
V/V
(AVX512VL
Multiply packed single precision floating-point
VFMADD231PS xmm1 {k1}{z}, xmm2,
AND AVX512F)
values from xmm2 and xmm3/m128/m32bcst,
xmm3/m128/m32bcst
OR AVX10.1
add to xmm1 and put result in xmm1.
EVEX.256.66.0F38.W0 98 /r
B
V/V
(AVX512VL
Multiply packed single precision floating-point
VFMADD132PS ymm1 {k1}{z}, ymm2,
AND AVX512F)
values from ymm1 and ymm3/m256/m32bcst,
ymm3/m256/m32bcst
OR AVX10.1
add to ymm2 and put result in ymm1.
EVEX.256.66.0F38.W0 A8 /r
B
V/V
(AVX512VL
Multiply packed single precision floating-point
VFMADD213PS ymm1 {k1}{z}, ymm2,
AND AVX512F)
values from ymm1 and ymm2, add to
ymm3/m256/m32bcst
OR AVX10.1
ymm3/m256/m32bcst and put result in ymm1.
EVEX.256.66.0F38.W0 B8 /r
B
V/V
(AVX512VL
Multiply packed single precision floating-point
VFMADD231PS ymm1 {k1}{z}, ymm2,
AND AVX512F)
values from ymm2 and ymm3/m256/m32bcst,
ymm3/m256/m32bcst
OR AVX10.1
add to ymm1 and put result in ymm1.
EVEX.512.66.0F38.W0 98 /r
B
V/V
AVX512F
Multiply packed single precision floating-point
VFMADD132PS zmm1 {k1}{z}, zmm2,
OR AVX10.1
values from zmm1 and zmm3/m512/m32bcst,
zmm3/m512/m32bcst{er}
add to zmm2 and put result in zmm1.
EVEX.512.66.0F38.W0 A8 /r
B
V/V
AVX512F
Multiply packed single precision floating-point
VFMADD213PS zmm1 {k1}{z}, zmm2,
OR AVX10.1
values from zmm1 and zmm2, add to
zmm3/m512/m32bcst{er}
zmm3/m512/m32bcst and put result in zmm1.
EVEX.512.66.0F38.W0 B8 /r
B
V/V
AVX512F
Multiply packed single precision floating-point
VFMADD231PS zmm1 {k1}{z}, zmm2,
OR AVX10.1
values from zmm2 and zmm3/m512/m32bcst,
zmm3/m512/m32bcst{er}
add to zmm1 and put result in zmm1.
VFMADD132PS/VFMADD213PS/VFMADD231PS-Fused Multiply-Add of Packed Single Precision Floating-Point Values
Vol. 2C
5-220
Instruction Operand Encoding
Op/En
Tuple Type
Operand 1
Operand 2
Operand 3
Operand 4
A
N/A
ModRM:reg (r, w)
VEX.vvvv (r)
ModRM:r/m (r)
N/A
B
Full
ModRM:reg (r, w)
EVEX.vvvv (r)
ModRM:r/m (r)
N/A
Description
Performs a set of SIMD multiply-add computation on packed single precision floating-point values using three
source operands and writes the multiply-add results in the destination operand. The destination operand is also the
first source operand. The second operand must be a SIMD register. The third source operand can be a SIMD
register or a memory location.
VFMADD132PS: Multiplies the four, eight or sixteen packed single precision floating-point values from the first
source operand to the four, eight or sixteen packed single precision floating-point values in the third source
operand, adds the infinite precision intermediate result to the four, eight or sixteen packed single precision floating-
point values in the second source operand, performs rounding and stores the resulting four, eight or sixteen packed
single precision floating-point values to the destination operand (first source operand).
VFMADD213PS: Multiplies the four, eight or sixteen packed single precision floating-point values from the second
source operand to the four, eight or sixteen packed single precision floating-point values in the first source
operand, adds the infinite precision intermediate result to the four, eight or sixteen packed single precision floating-
point values in the third source operand, performs rounding and stores the resulting the four, eight or sixteen
packed single precision floating-point values to the destination operand (first source operand).
VFMADD231PS: Multiplies the four, eight or sixteen packed single precision floating-point values from the second
source operand to the four, eight or sixteen packed single precision floating-point values in the third source
operand, adds the infinite precision intermediate result to the four, eight or sixteen packed single precision floating-
point values in the first source operand, performs rounding and stores the resulting four, eight or sixteen packed
single precision floating-point values to the destination operand (first source operand).
EVEX encoded versions: The destination operand (also first source operand) is a ZMM register and encoded in
reg_field. The second source operand is a ZMM register and encoded in EVEX.vvvv. The third source operand is a
ZMM register, a 512-bit memory location, or a 512-bit vector broadcasted from a 32-bit memory location. The
destination operand is conditionally updated with write mask k1.
VEX.256 encoded version: The destination operand (also first source operand) is a YMM register and encoded in
reg_field. The second source operand is a YMM register and encoded in VEX.vvvv. The third source operand is a
YMM register or a 256-bit memory location and encoded in rm_field.
VEX.128 encoded version: The destination operand (also first source operand) is a XMM register and encoded in
reg_field. The second source operand is a XMM register and encoded in VEX.vvvv. The third source operand is a
XMM register or a 128-bit memory location and encoded in rm_field. The upper 128 bits of the YMM destination
register are zeroed.
Operation
In the operations below, “*” and “+” symbols represent multiplication and addition with infinite precision inputs and outputs (no
rounding).
VFMADD132PS DEST, SRC2, SRC3
IF (VEX.128) THEN
MAXNUM := 4
ELSEIF (VEX.256)
MAXNUM := 8
FI
For i = 0 to MAXNUM-1 {
n := 32*i;
DEST[n+31:n] := RoundFPControl_MXCSR(DEST[n+31:n]*SRC3[n+31:n] + SRC2[n+31:n])
}
IF (VEX.128) THEN
DEST[MAXVL-1:128] := 0
VFMADD132PS/VFMADD213PS/VFMADD231PS-Fused Multiply-Add of Packed Single Precision Floating-Point Values
Vol. 2C
5-221
ELSEIF (VEX.256)
DEST[MAXVL-1:256] := 0
FI
VFMADD213PS DEST, SRC2, SRC3
IF (VEX.128) THEN
MAXNUM := 4
ELSEIF (VEX.256)
MAXNUM := 8
FI
For i = 0 to MAXNUM-1 {
n := 32*i;
DEST[n+31:n] := RoundFPControl_MXCSR(SRC2[n+31:n]*DEST[n+31:n] + SRC3[n+31:n])
}
IF (VEX.128) THEN
DEST[MAXVL-1:128] := 0
ELSEIF (VEX.256)
DEST[MAXVL-1:256] := 0
FI
VFMADD231PS DEST, SRC2, SRC3
IF (VEX.128) THEN
MAXNUM := 4
ELSEIF (VEX.256)
MAXNUM := 8
FI
For i = 0 to MAXNUM-1 {
n := 32*i;
DEST[n+31:n] := RoundFPControl_MXCSR(SRC2[n+31:n]*SRC3[n+31:n] + DEST[n+31:n])
}
IF (VEX.128) THEN
DEST[MAXVL-1:128] := 0
ELSEIF (VEX.256)
DEST[MAXVL-1:256] := 0
FI
VFMADD132PS DEST, SRC2, SRC3 (EVEX encoded version, when src3 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] :=
RoundFPControl(DEST[i+31:i]*SRC3[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
VFMADD132PS/VFMADD213PS/VFMADD231PS-Fused Multiply-Add of Packed Single Precision Floating-Point Values
Vol. 2C
5-222
FI
FI;
ENDFOR
DEST[MAXVL-1:VL] := 0
VFMADD132PS DEST, SRC2, SRC3 (EVEX encoded version, when src3 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] :=
RoundFPControl_MXCSR(DEST[i+31:i]*SRC3[31:0] + SRC2[i+31:i])
ELSE
DEST[i+31:i] :=
RoundFPControl_MXCSR(DEST[i+31:i]*SRC3[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
VFMADD213PS DEST, SRC2, SRC3 (EVEX encoded version, when src3 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] :=
RoundFPControl(SRC2[i+31:i]*DEST[i+31:i] + SRC3[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
VFMADD213PS DEST, SRC2, SRC3 (EVEX encoded version, when src3 operand is a memory source)
VFMADD132PS/VFMADD213PS/VFMADD231PS-Fused Multiply-Add of Packed Single Precision Floating-Point Values
Vol. 2C
5-223
(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] :=
RoundFPControl_MXCSR(SRC2[i+31:i]*DEST[i+31:i] + SRC3[31:0])
ELSE
DEST[i+31:i] :=
RoundFPControl_MXCSR(SRC2[i+31:i]*DEST[i+31:i] + SRC3[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
VFMADD231PS DEST, SRC2, SRC3 (EVEX encoded version, when src3 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] :=
RoundFPControl(SRC2[i+31:i]*SRC3[i+31:i] + DEST[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
VFMADD231PS DEST, SRC2, SRC3 (EVEX encoded version, when src3 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
VFMADD132PS/VFMADD213PS/VFMADD231PS-Fused Multiply-Add of Packed Single Precision Floating-Point Values
Vol. 2C
5-224
IF (EVEX.b = 1)
THEN
DEST[i+31:i] :=
RoundFPControl_MXCSR(SRC2[i+31:i]*SRC3[31:0] + DEST[i+31:i])
ELSE
DEST[i+31:i] :=
RoundFPControl_MXCSR(SRC2[i+31:i]*SRC3[i+31:i] + DEST[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
Intel C/C++ Compiler Intrinsic Equivalent
VFMADDxxxPS __m512 _mm512_fmadd_ps(__m512 a, __m512 b, __m512 c);
VFMADDxxxPS __m512 _mm512_fmadd_round_ps(__m512 a, __m512 b, __m512 c, int r);
VFMADDxxxPS __m512 _mm512_mask_fmadd_ps(__m512 a, __mmask16 k, __m512 b, __m512 c);
VFMADDxxxPS __m512 _mm512_maskz_fmadd_ps(__mmask16 k, __m512 a, __m512 b, __m512 c);
VFMADDxxxPS __m512 _mm512_mask3_fmadd_ps(__m512 a, __m512 b, __m512 c, __mmask16 k);
VFMADDxxxPS __m512 _mm512_mask_fmadd_round_ps(__m512 a, __mmask16 k, __m512 b, __m512 c, int r);
VFMADDxxxPS __m512 _mm512_maskz_fmadd_round_ps(__mmask16 k, __m512 a, __m512 b, __m512 c, int r);
VFMADDxxxPS __m512 _mm512_mask3_fmadd_round_ps(__m512 a, __m512 b, __m512 c, __mmask16 k, int r);
VFMADDxxxPS __m256 _mm256_mask_fmadd_ps(__m256 a, __mmask8 k, __m256 b, __m256 c);
VFMADDxxxPS __m256 _mm256_maskz_fmadd_ps(__mmask8 k, __m256 a, __m256 b, __m256 c);
VFMADDxxxPS __m256 _mm256_mask3_fmadd_ps(__m256 a, __m256 b, __m256 c, __mmask8 k);
VFMADDxxxPS __m128 _mm_mask_fmadd_ps(__m128 a, __mmask8 k, __m128 b, __m128 c);
VFMADDxxxPS __m128 _mm_maskz_fmadd_ps(__mmask8 k, __m128 a, __m128 b, __m128 c);
VFMADDxxxPS __m128 _mm_mask3_fmadd_ps(__m128 a, __m128 b, __m128 c, __mmask8 k);
VFMADDxxxPS __m128 _mm_fmadd_ps (__m128 a, __m128 b, __m128 c);
VFMADDxxxPS __m256 _mm256_fmadd_ps (__m256 a, __m256 b, __m256 c);
SIMD Floating-Point Exceptions
Overflow, Underflow, Invalid, Precision, Denormal.
Other Exceptions
VEX-encoded instructions, see Table 2-19, “Type 2 Class Exception Conditions.”
EVEX-encoded instructions, see Table 2-48, “Type E2 Class Exception Conditions.”
VFMADD132PS/VFMADD213PS/VFMADD231PS-Fused Multiply-Add of Packed Single Precision Floating-Point Values
Vol. 2C
5-225
|
||
|
|
|