Xcode Apple Clang 启用 avx512

冯剑龙*_*冯剑龙 1 xcode clang avx avx2 avx512

在 Xcode(Version 10.1 (10B61)) 中,我使用如下宏来检测 AVX512 支持。

#ifdef __SSE4_1__
#error "sse4_1"
#endif

#ifdef __AVX__
#error "avx"
#endif

#ifdef __AVX2__
#error "avx2"
#endif

#ifdef __AVX512__
#error "avx512"
#endif
Run Code Online (Sandbox Code Playgroud)

在默认构建设置中,SSE4_1处于活动状态,但 avx、avx2 未处于活动状态。当我在 Building Settings-->Apple Clang-Custom Compiler Flags-->Other C Flags 中添加-mavx时,启用AVX,进一步添加-mavx2以启用AVXAVX2,但未知参数:'-mavx512'。你如何启用avx512并检测它?似乎很少有宏来检测avx512。

#define __AVX512BW__ 1  
#define __AVX512CD__ 1  
#define __AVX512DQ__ 1  
#define __AVX512F__ 1  
#define __AVX512VL__ 1   
Run Code Online (Sandbox Code Playgroud)

它们之间有什么区别?

Pet*_*des 5

AVX512 不是一个单一的扩展,在这种情况下没有足够具体的意义来有用。编译器只处理特定的CPU 特性,如 AVX512F、AVX512DQ、AVX512CD 等。

所有支持任何 AVX512 扩展的 CPU 都必须支持 AVX512F,即“基础”。 AVX512F其他 AVX512 扩展构建的基准 AVX512 扩展。

在想要使用 AVX512 内在函数的代码中,您应该查看https://en.wikipedia.org/wiki/AVX-512#CPUs_with_AVX-512并选择一组可以在您关心的 CPU 上一起使用的扩展,例如当前可用的 Skylake-X 上的 F + CD 和 VL、DQ、BW。

然后例如#if defined(__AVX512BW__) && defined(__AVX512VL__)在使用vpermt2w256 位向量或其他东西的代码之前使用。 __AVX512(anything)__暗示__AVX512F__; 这是您不必单独检查的一个扩展。

但是如果你使用 AVX512F 指令,他们只是检查那个宏。


您几乎不应该-mavx512f直接使用:使用-march=skylake-avx512, -march=knl, 或-march=native。或者在未来,-march=icelake或者其他什么。

  • 编译器知道哪些 CPU 支持哪些扩展集(或者可以检测您正在编译的机器支持哪些扩展)。有很多,忽略像 AVX512VL(支持 128 位和 256 位向量上的 AVX512 指令)或 Xeon Phi 的 AVX512ER(速度快1/x1/sqrt(x)精度是普通 AVX512 14 位版本的两倍)等重要的严重损害性能。如果您在 Xeon Phi 上进行任何除法或 log/exp,则 AVX512ER 尤其重要,因为与 Skylake 相比,KNL 上的全精度除法非常慢。
  • -march=x意味着-mtune=x,启用与目标相关的调整选项。KNL 基本上是安装了 AVX512 的 Silvermont,与-mtune=skylake-avx512.

这些都是你通常不应该-mfma -mavx2直接使用的相同原因,除了目前没有 AVX512 的 AMD CPU,所以只有 2 个主要的调优目标(至强融核和主流 Skylake/CannonLake/Icelake),并且它们还支持不同的设置AVX512 扩展。不幸的是没有-mtune=generic-avx2调整设置,但 Ryzen 支持 Haswell 所做的几乎所有扩展(并且它不支持 GCC / clang 的扩展不会自动使用,例如事务内存),因此-march=haswell使用 FMA 为 CPU 调整代码可能是合理的、AVX2、popcnt 等,而不会在 Ryzen 上受太多影响。


也有相关(GCC的,也许不是目前铛。 https://gcc.gnu.org/onlinedocs/gcc/x86-Options.html):

  • -mprefer-vector-width=256默认情况下使用 256 位向量自动向量化,以防大部分时间花在非向量化循环中。使用 512 位向量在 Intel Xeon CPU 上显着降低了最大涡轮时钟速度(在 Skylake-X 的 i9 桌面版本上可能没有那么多),因此在分散的小空间中使用 512 位向量可能会导致净减速你的程序的一部分。所以 256 是tune=skylake-avx512GCC 中的默认值,但 KNL 使用 512。

  • -mprefer-avx-128-mprefer-vector-width=选项的旧版本,在 AVX512 存在之前。

使用 AVX512 掩码寄存器、32 个向量寄存器和/或其新指令,即使在向量宽度相同的情况下也能取得重大胜利,因此即使您不想使用 512 位向量宽度,启用 AVX512 也是有意义的。(尽管有时使用内在函数或自动矢量化的代码会以更糟糕的方式编译,而不是更好,如果 AVX512 比较到寄存器版本的比较可用。但希望像这样的反优化错误将被整理为 AVX512得到更广泛的应用。)