1
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

vpshufb

Posted at

512bit 内の 128bit に含まれる8bit値16個をまぜまぜします。x86の伝統に従い、128bit 境界は超えられません。

GCC 4.9 では _mm512_shuffle_epi8 が無かったので asm 書きました。

trunk にはあるので、5.0では使えると予想されます。
https://github.com/gcc-mirror/gcc/blob/master/gcc/config/i386/avx512bwintrin.h#L1598

#include <immintrin.h>
#include <stdio.h>

unsigned char in[64];
unsigned char table[64];
unsigned char out[64];

static void
test(int idx)
{
    for (int i=0; i<64; i++) {
        in[i] = 100+i;
        table[i] = idx;
    }

    __m512i vtable = _mm512_loadu_si512(table);
    __m512i vin = _mm512_loadu_si512(in);

    __m512i v;

    __asm__ __volatile__("vpshufb %[src1], %[src2], %[dest]\n\t"
                         :[dest]"=v"(v)
                         :[src1]"v"(vtable),
                          [src2]"v"(vin));

    _mm512_storeu_si512(out, v);

    for (int i=0; i<64; i++) {
        printf("idx=%2d,out[%d]=%d\n",
               idx, i, out[i]);
    }
}

int
main()
{
    test(0);

    test(17);

    test(8);
}
 $ ./sde -- ./a.out
idx= 0,out[0]=100
idx= 0,out[1]=100
idx= 0,out[2]=100
idx= 0,out[3]=100
idx= 0,out[4]=100
idx= 0,out[5]=100
idx= 0,out[6]=100
idx= 0,out[7]=100
idx= 0,out[8]=100
idx= 0,out[9]=100
idx= 0,out[10]=100
idx= 0,out[11]=100
idx= 0,out[12]=100
idx= 0,out[13]=100
idx= 0,out[14]=100
idx= 0,out[15]=100
idx= 0,out[16]=116
idx= 0,out[17]=116
idx= 0,out[18]=116
idx= 0,out[19]=116
idx= 0,out[20]=116
idx= 0,out[21]=116
idx= 0,out[22]=116
idx= 0,out[23]=116
idx= 0,out[24]=116
idx= 0,out[25]=116
idx= 0,out[26]=116
idx= 0,out[27]=116
idx= 0,out[28]=116
idx= 0,out[29]=116
idx= 0,out[30]=116
idx= 0,out[31]=116
idx= 0,out[32]=132
idx= 0,out[33]=132
idx= 0,out[34]=132
idx= 0,out[35]=132
idx= 0,out[36]=132
idx= 0,out[37]=132
idx= 0,out[38]=132
idx= 0,out[39]=132
idx= 0,out[40]=132
idx= 0,out[41]=132
idx= 0,out[42]=132
idx= 0,out[43]=132
idx= 0,out[44]=132
idx= 0,out[45]=132
idx= 0,out[46]=132
idx= 0,out[47]=132
idx= 0,out[48]=148
idx= 0,out[49]=148
idx= 0,out[50]=148
idx= 0,out[51]=148
idx= 0,out[52]=148
idx= 0,out[53]=148
idx= 0,out[54]=148
idx= 0,out[55]=148
idx= 0,out[56]=148
idx= 0,out[57]=148
idx= 0,out[58]=148
idx= 0,out[59]=148
idx= 0,out[60]=148
idx= 0,out[61]=148
idx= 0,out[62]=148
idx= 0,out[63]=148
idx=17,out[0]=101
idx=17,out[1]=101
idx=17,out[2]=101
idx=17,out[3]=101
idx=17,out[4]=101
idx=17,out[5]=101
idx=17,out[6]=101
idx=17,out[7]=101
idx=17,out[8]=101
idx=17,out[9]=101
idx=17,out[10]=101
idx=17,out[11]=101
idx=17,out[12]=101
idx=17,out[13]=101
idx=17,out[14]=101
idx=17,out[15]=101
idx=17,out[16]=117
idx=17,out[17]=117
idx=17,out[18]=117
idx=17,out[19]=117
idx=17,out[20]=117
idx=17,out[21]=117
idx=17,out[22]=117
idx=17,out[23]=117
idx=17,out[24]=117
idx=17,out[25]=117
idx=17,out[26]=117
idx=17,out[27]=117
idx=17,out[28]=117
idx=17,out[29]=117
idx=17,out[30]=117
idx=17,out[31]=117
idx=17,out[32]=133
idx=17,out[33]=133
idx=17,out[34]=133
idx=17,out[35]=133
idx=17,out[36]=133
idx=17,out[37]=133
idx=17,out[38]=133
idx=17,out[39]=133
idx=17,out[40]=133
idx=17,out[41]=133
idx=17,out[42]=133
idx=17,out[43]=133
idx=17,out[44]=133
idx=17,out[45]=133
idx=17,out[46]=133
idx=17,out[47]=133
idx=17,out[48]=149
idx=17,out[49]=149
idx=17,out[50]=149
idx=17,out[51]=149
idx=17,out[52]=149
idx=17,out[53]=149
idx=17,out[54]=149
idx=17,out[55]=149
idx=17,out[56]=149
idx=17,out[57]=149
idx=17,out[58]=149
idx=17,out[59]=149
idx=17,out[60]=149
idx=17,out[61]=149
idx=17,out[62]=149
idx=17,out[63]=149
idx= 8,out[0]=108
idx= 8,out[1]=108
idx= 8,out[2]=108
idx= 8,out[3]=108
idx= 8,out[4]=108
idx= 8,out[5]=108
idx= 8,out[6]=108
idx= 8,out[7]=108
idx= 8,out[8]=108
idx= 8,out[9]=108
idx= 8,out[10]=108
idx= 8,out[11]=108
idx= 8,out[12]=108
idx= 8,out[13]=108
idx= 8,out[14]=108
idx= 8,out[15]=108
idx= 8,out[16]=124
idx= 8,out[17]=124
idx= 8,out[18]=124
idx= 8,out[19]=124
idx= 8,out[20]=124
idx= 8,out[21]=124
idx= 8,out[22]=124
idx= 8,out[23]=124
idx= 8,out[24]=124
idx= 8,out[25]=124
idx= 8,out[26]=124
idx= 8,out[27]=124
idx= 8,out[28]=124
idx= 8,out[29]=124
idx= 8,out[30]=124
idx= 8,out[31]=124
idx= 8,out[32]=140
idx= 8,out[33]=140
idx= 8,out[34]=140
idx= 8,out[35]=140
idx= 8,out[36]=140
idx= 8,out[37]=140
idx= 8,out[38]=140
idx= 8,out[39]=140
idx= 8,out[40]=140
idx= 8,out[41]=140
idx= 8,out[42]=140
idx= 8,out[43]=140
idx= 8,out[44]=140
idx= 8,out[45]=140
idx= 8,out[46]=140
idx= 8,out[47]=140
idx= 8,out[48]=156
idx= 8,out[49]=156
idx= 8,out[50]=156
idx= 8,out[51]=156
idx= 8,out[52]=156
idx= 8,out[53]=156
idx= 8,out[54]=156
idx= 8,out[55]=156
idx= 8,out[56]=156
idx= 8,out[57]=156
idx= 8,out[58]=156
idx= 8,out[59]=156
idx= 8,out[60]=156
idx= 8,out[61]=156
idx= 8,out[62]=156
idx= 8,out[63]=156

https://software.intel.com/sites/landingpage/IntrinsicsGuide/ に書いてある疑似コードと挙動合わない気が…?

FOR j := 0 to 63
    i := j*8
    IF b[i+7] == 1
        dst[i+7:i] := 0
    ELSE
        index[3:0] := b[i+3:i]
        dst[i+7:i] := a[index*8+7:index*8]
    FI
ENDFOR dst[MAX:512] := 0

https://software.intel.com/en-us/intel-isa-extensions に書いてある疑似コードは…意味がよくわからなかった。

それはともかく、GCC 4.9では対応されてない理由が、これがAVX512BWという後から発表された別の拡張になっているからですね。

なお、このAVX512BW拡張はKNL(XeonPhi) では使えません。

 $ ./sde -knl -- ./a.out 
TID 0 SDE-ERROR: Executed instruction not valid for specified chip (KNL): 0x4005e5: vpshufb zmm0, zmm1, zmm0
Image: /home/w0/test/avx512/a.out+0x5e5
Function: test
Instruction bytes are: 62 f2 75 48 00 c0 

世界は悲しみの炎に包まれた。

明日は @tanakmura が vshufps について書きます。

1
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?