_mm_perm_epi8
Visual Studio 2010 SP1 is required.
Microsoft Specific
Generates the XOP instruction vpperm to select bytes from its first two sources and optionally transform them.
__m128i _mm_perm_epi8 (
__m128i src1,
__m128i src2,
__m128i selector
);
Parameters
[in] src1
A 128-bit parameter that contains sixteen bytes.[in] src2
A 128-bit parameter that contains sixteen bytes.[in] selector
A 128-bit parameter that selects bytes from src1 and src2 and optionally chooses a transformation to apply to the selected byte.
Return value
A 128-bit result r that contains bytes selected from src1 and src2 and is optionally transformed.
Requirements
Intrinsic |
Architecture |
---|---|
_mm_perm_epi8 |
XOP |
Header file <intrin.h>
Remarks
For each byte in selector, the low-order bits select a byte from src1 or src2. Values 0 to 15 select bytes 0 to 15 of src1, while values 16 to 31 select bytes 0 to 15 of src2. The high-order bits of each byte in selector determine what transformation, if any, to apply to the selected byte.
Value of high-order 3 bits of selector |
Transformation chosen |
---|---|
000b |
No transformation |
001b |
Invert (ones complement) source byte |
010b |
Bit reverse source byte |
011b |
Bit reverse inverted source byte |
100b |
Set result byte to 0x00 |
101b |
Set result byte to 0xFF |
110b |
Replicate most significant bit of source byte |
111b |
Replicate inverted most significant bit of source byte |
The vpperm instruction is part of the XOP family of instructions. Before you use this intrinsic, you must ensure that the processor supports this instruction. To determine hardware support for this instruction, call the __cpuid intrinsic with InfoType = 0x80000001 and check bit 11 of CPUInfo[2] (ECX). This bit is 1 when the instruction is supported, and 0 otherwise.
Example
#include <stdio.h>
#include <intrin.h>
int main()
{
__m128i a, b, selector, d;
int i;
for (i = 15; i >= 0; i--) {
a.m128i_u8[i] = i; // 0x0f0e0d0c...
b.m128i_u8[i] = (i << 4) | i; // 0xffeeddcc...
}
selector.m128i_u64[1] = 0xfedcba9876543210ll;
selector.m128i_u64[0] = 0x0011223344556677ll;
d = _mm_perm_epi8(a, b, selector);
printf_s("%016I64x %016I64x\n", d.m128i_u64[1], d.m128i_u64[0]);
}
00ffff009922dd00 0011fdcc20aa9f11