IntelのIntrinsicをコンパイルして逆アセンブルする


以下のソースコードをコンパイルします。Ubuntu 21.04を使いました

test.c
#include <immintrin.h>

__m512i test__mm512_add_epi8 (__m512i a, __m512i b)
{
    return _mm512_add_epi8 (a,b);
}

int main()
{
}

コンパイルにはオプションが必要です。

$ gcc -march=icelake-client test.c -g -c
$ objdump test.o -S

test.o:     ファイル形式 elf64-x86-64


セクション .text の逆アセンブル:

0000000000000000 <test__mm512_add_epi8>:
#include <immintrin.h>

__m512i test__mm512_add_epi8 (__m512i a, __m512i b)
{
   0:   f3 0f 1e fa             endbr64 
   4:   55                      push   %rbp
   5:   48 89 e5                mov    %rsp,%rbp
   8:   48 83 e4 c0             and    $0xffffffffffffffc0,%rsp
   c:   48 81 ec 88 00 00 00    sub    $0x88,%rsp
  13:   62 f1 fd 48 7f 84 24    vmovdqa64 %zmm0,-0x38(%rsp)
  1a:   c8 ff ff ff 
  1e:   62 f1 fd 48 7f 8c 24    vmovdqa64 %zmm1,-0x78(%rsp)
  25:   88 ff ff ff 
  29:   62 f1 fd 48 6f 84 24    vmovdqa64 -0x38(%rsp),%zmm0
  30:   c8 ff ff ff 
  34:   62 f1 fd 48 7f 84 24    vmovdqa64 %zmm0,0x8(%rsp)
  3b:   08 00 00 00 
  3f:   62 f1 fd 48 6f 84 24    vmovdqa64 -0x78(%rsp),%zmm0
  46:   88 ff ff ff 
  4a:   62 f1 fd 48 7f 84 24    vmovdqa64 %zmm0,0x48(%rsp)
  51:   48 00 00 00 

extern __inline __m512i
__attribute__ ((__gnu_inline__, __always_inline__, __artificial__))
_mm512_add_epi8 (__m512i __A, __m512i __B)
{
  return (__m512i) ((__v64qu) __A + (__v64qu) __B);
  55:   62 f1 fd 48 6f 8c 24    vmovdqa64 0x8(%rsp),%zmm1
  5c:   08 00 00 00 
  60:   62 f1 fd 48 6f 84 24    vmovdqa64 0x48(%rsp),%zmm0
  67:   48 00 00 00 
  6b:   62 f1 75 48 fc c0       vpaddb %zmm0,%zmm1,%zmm0
    return _mm512_add_epi8 (a,b);
}
  71:   c9                      leaveq 
  72:   c3                      retq   

0000000000000073 <main>:

int main()
{
  73:   f3 0f 1e fa             endbr64 
  77:   55                      push   %rbp
  78:   48 89 e5                mov    %rsp,%rbp
  7b:   b8 00 00 00 00          mov    $0x0,%eax
}
  80:   5d                      pop    %rbp
  81:   c3                      retq    

以下のサイトで教えていただきました。ありがとうございました

追記

最適化オプションを加えると最適化されるようです。

$ gcc -march=icelake-client test.c -g -c -O
$ objdump test.o -S

test.o:     ファイル形式 elf64-x86-64


セクション .text の逆アセンブル:

0000000000000000 <test__mm512_add_epi8>:
#include <immintrin.h>

__m512i test__mm512_add_epi8 (__m512i a, __m512i b)
{
   0:   f3 0f 1e fa             endbr64 

extern __inline __m512i
__attribute__ ((__gnu_inline__, __always_inline__, __artificial__))
_mm512_add_epi8 (__m512i __A, __m512i __B)
{
  return (__m512i) ((__v64qu) __A + (__v64qu) __B);
   4:   62 f1 7d 48 fc c1       vpaddb %zmm1,%zmm0,%zmm0
    return _mm512_add_epi8 (a,b);
}
   a:   c3                      retq   

000000000000000b <main>:

int main()
{
   b:   f3 0f 1e fa             endbr64 
}
   f:   b8 00 00 00 00          mov    $0x0,%eax
  14:   c3                      retq

デバッグ情報を埋め込まない場合は以下の通り

$ gcc -march=icelake-client test.c -c -O
$ objdump test.o -S

test.o:     ファイル形式 elf64-x86-64


セクション .text の逆アセンブル:

0000000000000000 <test__mm512_add_epi8>:
   0:   f3 0f 1e fa             endbr64 
   4:   62 f1 7d 48 fc c1       vpaddb %zmm1,%zmm0,%zmm0
   a:   c3                      retq   

000000000000000b <main>:
   b:   f3 0f 1e fa             endbr64 
   f:   b8 00 00 00 00          mov    $0x0,%eax
  14:   c3                      retq 

@fujitanozomu さん指摘ありがとうございました。