CPU 构建选项#
描述#
以下选项主要用于更改针对特定 CPU 特性优化的默认行为
cpu-baseline
:所需 CPU 特性的最小集合。默认值为
min
,它提供了一系列处理器家族中可以在各种平台上安全运行的最低 CPU 特性。注意
在运行时,如果目标 CPU 不支持任何指定的特性(会引发 Python 运行时错误),NumPy 模块将无法加载。
cpu-dispatch
:额外 CPU 特性的调度集合。默认值为
max -xop -fma4
,它启用所有 CPU 特性,但 AMD 传统特性除外(X86 架构下)。注意
在运行时,如果目标 CPU 中不可用,NumPy 模块将跳过任何指定的特性。
这些选项在构建时可通过构建前端(例如 pip
或 build
)将设置参数传递给 meson-python 来访问。它们接受一组 CPU 特性 或聚合了多个特性的特性组,或者执行一系列过程的 特殊选项。
自定义 CPU/构建选项
pip install . -Csetup-args=-Dcpu-baseline="avx2 fma3" -Csetup-args=-Dcpu-dispatch="max"
快速入门#
通常,默认设置倾向于不强制要求某些在旧处理器上可能不可用的 CPU 特性。提高基线特性要求通常会改善性能,并可能减小二进制文件大小。
以下是可能需要更改默认设置的最常见场景
我正在为本地使用构建 NumPy#
并且我不打算将此构建版本导出给其他用户,也不针对与主机不同的 CPU。
为基线设置 native
,或者在您的平台不支持 native
选项的情况下手动指定 CPU 特性
python -m build --wheel -Csetup-args=-Dcpu-baseline="native"
在这种情况下,使用额外的 CPU 特性构建 NumPy 是不必要的,因为所有支持的特性都已在基线特性中定义。
python -m build --wheel -Csetup-args=-Dcpu-baseline="native" \
-Csetup-args=-Dcpu-dispatch="none"
注意
如果主机平台不支持 native
,将引发致命错误。
我不想支持 x86 架构的旧处理器#
由于现在大多数 CPU 都至少支持 AVX
、F16C
特性,您可以使用
python -m build --wheel -Csetup-args=-Dcpu-baseline="avx f16c"
注意
cpu-baseline
会强制合并所有隐含特性,因此无需添加 SSE 特性。
我遇到与上述情况相同的问题,但使用的是 ppc64 架构#
那么将基线特性的上限提高到 Power8
python -m build --wheel -Csetup-args=-Dcpu-baseline="vsx2"
AVX512 特性有问题?#
您可能对包含 AVX512
或任何其他 CPU 特性有所保留,并希望将其从调度特性中排除。
python -m build --wheel -Csetup-args=-Dcpu-dispatch="max -avx512f -avx512cd \
-avx512_knl -avx512_knm -avx512_skx -avx512_clx -avx512_cnl -avx512_icl -avx512_spr"
支持的特性#
特性名称可以表示一个特性或一组特性,如下表所示,支持情况取决于最低限度。
注意
以下特性可能不被所有编译器支持,此外,某些编译器在处理 AVX512
、AVX2
和 FMA3
等特性时可能会生成不同的隐含特性集。更多详情请参阅 平台差异。
在 x86 上#
名称 |
隐含 |
包含 |
---|---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
在 IBM/POWER 大端模式上#
名称 |
隐含 |
---|---|
|
|
|
|
|
|
|
|
在 IBM/POWER 小端模式上#
名称 |
隐含 |
---|---|
|
|
|
|
|
|
|
|
在 ARMv7/A32 上#
名称 |
隐含 |
---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
在 ARMv8/A64 上#
名称 |
隐含 |
---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
在 IBM/ZSYSTEM(S390X) 上#
名称 |
隐含 |
---|---|
|
|
|
|
|
|
特殊选项#
NONE
:不启用任何特性。NATIVE
:启用主机 CPU 支持的所有 CPU 特性,此操作基于编译器标志(-march=native
,-xHost
,/QxHost
)MIN
:启用可在广泛平台上安全运行的最低 CPU 特性。对于架构
隐含
x86 (32 位模式)
SSE
SSE2
x86_64
SSE
SSE2
SSE3
IBM/POWER (大端模式)
NONE
IBM/POWER (小端模式)
VSX
VSX2
ARMHF
NONE
ARM64 即 AARCH64
NEON
NEON_FP16
NEON_VFPV4
ASIMD
IBM/ZSYSTEM(S390X)
NONE
MAX
:启用编译器和平台支持的所有 CPU 特性。Operators-/+
:移除或添加特性,与MAX
、MIN
和NATIVE
选项结合使用时非常有用。
行为#
CPU 特性和其他选项不区分大小写,例如
python -m build --wheel -Csetup-args=-Dcpu-dispatch="SSE41 avx2 FMA3"
请求的优化顺序无关紧要
python -m build --wheel -Csetup-args=-Dcpu-dispatch="SSE41 AVX2 FMA3" # equivalent to python -m build --wheel -Csetup-args=-Dcpu-dispatch="FMA3 AVX2 SSE41"
逗号、空格或“+”都可以用作分隔符,例如
python -m build --wheel -Csetup-args=-Dcpu-dispatch="avx2 avx512f" # or python -m build --wheel -Csetup-args=-Dcpu-dispatch=avx2,avx512f # or python -m build --wheel -Csetup-args=-Dcpu-dispatch="avx2+avx512f"
所有方法都有效,但如果使用空格,参数应加引号或用反斜杠转义。
cpu-baseline
会合并所有隐含的 CPU 特性,例如python -m build --wheel -Csetup-args=-Dcpu-baseline=sse42 # equivalent to python -m build --wheel -Csetup-args=-Dcpu-baseline="sse sse2 sse3 ssse3 sse41 popcnt sse42"
如果通过环境变量
CFLAGS
启用了编译器原生标志-march=native
或-xHost
或/QxHost
,则cpu-baseline
将被视为“原生”。export CFLAGS="-march=native" pip install . # is equivalent to pip install . -Csetup-args=-Dcpu-baseline=native
cpu-baseline
会跳过目标平台或编译器不支持的任何指定特性,而不是引发致命错误。注意
由于
cpu-baseline
会合并所有隐含特性,因此将启用最大支持的隐含特性,而不是跳过所有这些特性。例如# Requesting `AVX2,FMA3` but the compiler only support **SSE** features python -m build --wheel -Csetup-args=-Dcpu-baseline="avx2 fma3" # is equivalent to python -m build --wheel -Csetup-args=-Dcpu-baseline="sse sse2 sse3 ssse3 sse41 popcnt sse42"
cpu-dispatch
不会合并任何隐含的 CPU 特性,因此除非您想禁用其中一个或全部特性,否则必须手动添加它们。# Only dispatches AVX2 and FMA3 python -m build --wheel -Csetup-args=-Dcpu-dispatch=avx2,fma3 # Dispatches AVX and SSE features python -m build --wheel -Csetup-args=-Dcpu-dispatch=ssse3,sse41,sse42,avx,avx2,fma3
cpu-dispatch
会跳过任何指定的基线特性,也会跳过目标平台或编译器不支持的任何特性,而不会引发致命错误。
最后,您应该始终通过构建日志检查最终报告,以验证启用的特性。更多详情请参阅 构建报告。
平台差异#
在某些编译器或架构下,一些特殊情况迫使我们将某些特性关联在一起,导致无法单独构建它们。
这些条件可分为两部分,如下所示
架构兼容性
需要对齐相同架构的后续代次确定支持的某些 CPU 特性,一些情况
在 ppc64le 上,
VSX(ISA 2.06)
和VSX2(ISA 2.07)
相互隐含,因为支持小端模式的第一代是 Power-8`(ISA 2.07)`在 AArch64 上,
NEON NEON_FP16 NEON_VFPV4 ASIMD
相互隐含,因为它们是硬件基线的一部分。
例如
# On ARMv8/A64, specify NEON is going to enable Advanced SIMD
# and all predecessor extensions
python -m build --wheel -Csetup-args=-Dcpu-baseline=neon
# which is equivalent to
python -m build --wheel -Csetup-args=-Dcpu-baseline="neon neon_fp16 neon_vfpv4 asimd"
注意
请仔细查阅 支持的特性,以确定相互隐含的特性。
编译兼容性
有些编译器不为所有 CPU 特性提供独立支持。例如,**Intel** 的编译器不为 AVX2
和 FMA3
提供单独的标志,这是有道理的,因为所有支持 AVX2
的 Intel CPU 也支持 FMA3
,但这种方法与来自 **AMD** 或 **VIA** 的其他 **x86** CPU 不兼容。
例如
# Specify AVX2 will force enables FMA3 on Intel compilers
python -m build --wheel -Csetup-args=-Dcpu-baseline=avx2
# which is equivalent to
python -m build --wheel -Csetup-args=-Dcpu-baseline="avx2 fma3"
以下表格仅显示了某些编译器在 支持的特性 表格中所示的一般上下文中强加的差异
注意
带删除线的特性名称表示不支持的 CPU 特性。
在 x86::Intel 编译器上#
名称 |
隐含 |
包含 |
---|---|---|
FMA3 |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C AVX2 |
|
AVX2 |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 |
|
AVX512F |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 AVX2 AVX512CD |
|
XOP |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX |
|
FMA4 |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX |
|
AVX512_SPR |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 AVX2 AVX512F AVX512CD AVX512_SKX AVX512_CLX AVX512_CNL AVX512_ICL |
AVX512FP16 |
在 x86::Microsoft Visual C/C++ 上#
名称 |
隐含 |
包含 |
---|---|---|
FMA3 |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C AVX2 |
|
AVX2 |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 |
|
AVX512F |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 AVX2 AVX512CD AVX512_SKX |
|
AVX512CD |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 AVX2 AVX512F AVX512_SKX |
|
AVX512_KNL |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 AVX2 AVX512F AVX512CD |
AVX512ER AVX512PF |
AVX512_KNM |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 AVX2 AVX512F AVX512CD AVX512_KNL |
AVX5124FMAPS AVX5124VNNIW AVX512VPOPCNTDQ |
AVX512_SPR |
SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 AVX2 AVX512F AVX512CD AVX512_SKX AVX512_CLX AVX512_CNL AVX512_ICL |
AVX512FP16 |
构建报告#
在大多数情况下,CPU 构建选项不会产生任何导致构建挂起的致命错误。构建日志中可能出现的大多数错误都可视为严重的警告,这是因为编译器缺少一些预期的 CPU 特性。
因此,我们强烈建议您检查最终报告日志,以了解哪些 CPU 特性已启用,哪些未启用。
您可以在构建日志的末尾找到 CPU 优化最终报告,以下是其在 x86_64/gcc 上的样子
########### EXT COMPILER OPTIMIZATION ###########
Platform :
Architecture: x64
Compiler : gcc
CPU baseline :
Requested : 'min'
Enabled : SSE SSE2 SSE3
Flags : -msse -msse2 -msse3
Extra checks: none
CPU dispatch :
Requested : 'max -xop -fma4'
Enabled : SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 AVX2 AVX512F AVX512CD AVX512_KNL AVX512_KNM AVX512_SKX AVX512_CLX AVX512_CNL AVX512_ICL
Generated :
:
SSE41 : SSE SSE2 SSE3 SSSE3
Flags : -msse -msse2 -msse3 -mssse3 -msse4.1
Extra checks: none
Detect : SSE SSE2 SSE3 SSSE3 SSE41
: build/src.linux-x86_64-3.9/numpy/_core/src/umath/loops_arithmetic.dispatch.c
: numpy/_core/src/umath/_umath_tests.dispatch.c
:
SSE42 : SSE SSE2 SSE3 SSSE3 SSE41 POPCNT
Flags : -msse -msse2 -msse3 -mssse3 -msse4.1 -mpopcnt -msse4.2
Extra checks: none
Detect : SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42
: build/src.linux-x86_64-3.9/numpy/_core/src/_simd/_simd.dispatch.c
:
AVX2 : SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C
Flags : -msse -msse2 -msse3 -mssse3 -msse4.1 -mpopcnt -msse4.2 -mavx -mf16c -mavx2
Extra checks: none
Detect : AVX F16C AVX2
: build/src.linux-x86_64-3.9/numpy/_core/src/umath/loops_arithm_fp.dispatch.c
: build/src.linux-x86_64-3.9/numpy/_core/src/umath/loops_arithmetic.dispatch.c
: numpy/_core/src/umath/_umath_tests.dispatch.c
:
(FMA3 AVX2) : SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C
Flags : -msse -msse2 -msse3 -mssse3 -msse4.1 -mpopcnt -msse4.2 -mavx -mf16c -mfma -mavx2
Extra checks: none
Detect : AVX F16C FMA3 AVX2
: build/src.linux-x86_64-3.9/numpy/_core/src/_simd/_simd.dispatch.c
: build/src.linux-x86_64-3.9/numpy/_core/src/umath/loops_exponent_log.dispatch.c
: build/src.linux-x86_64-3.9/numpy/_core/src/umath/loops_trigonometric.dispatch.c
:
AVX512F : SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 AVX2
Flags : -msse -msse2 -msse3 -mssse3 -msse4.1 -mpopcnt -msse4.2 -mavx -mf16c -mfma -mavx2 -mavx512f
Extra checks: AVX512F_REDUCE
Detect : AVX512F
: build/src.linux-x86_64-3.9/numpy/_core/src/_simd/_simd.dispatch.c
: build/src.linux-x86_64-3.9/numpy/_core/src/umath/loops_arithm_fp.dispatch.c
: build/src.linux-x86_64-3.9/numpy/_core/src/umath/loops_arithmetic.dispatch.c
: build/src.linux-x86_64-3.9/numpy/_core/src/umath/loops_exponent_log.dispatch.c
: build/src.linux-x86_64-3.9/numpy/_core/src/umath/loops_trigonometric.dispatch.c
:
AVX512_SKX : SSE SSE2 SSE3 SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 AVX2 AVX512F AVX512CD
Flags : -msse -msse2 -msse3 -mssse3 -msse4.1 -mpopcnt -msse4.2 -mavx -mf16c -mfma -mavx2 -mavx512f -mavx512cd -mavx512vl -mavx512bw -mavx512dq
Extra checks: AVX512BW_MASK AVX512DQ_MASK
Detect : AVX512_SKX
: build/src.linux-x86_64-3.9/numpy/_core/src/_simd/_simd.dispatch.c
: build/src.linux-x86_64-3.9/numpy/_core/src/umath/loops_arithmetic.dispatch.c
: build/src.linux-x86_64-3.9/numpy/_core/src/umath/loops_exponent_log.dispatch.c
CCompilerOpt.cache_flush[804] : write cache to path -> /home/seiko/work/repos/numpy/build/temp.linux-x86_64-3.9/ccompiler_opt_cache_ext.py
########### CLIB COMPILER OPTIMIZATION ###########
Platform :
Architecture: x64
Compiler : gcc
CPU baseline :
Requested : 'min'
Enabled : SSE SSE2 SSE3
Flags : -msse -msse2 -msse3
Extra checks: none
CPU dispatch :
Requested : 'max -xop -fma4'
Enabled : SSSE3 SSE41 POPCNT SSE42 AVX F16C FMA3 AVX2 AVX512F AVX512CD AVX512_KNL AVX512_KNM AVX512_SKX AVX512_CLX AVX512_CNL AVX512_ICL
Generated : none
build_ext
和 build_clib
各有一个单独的报告,其中包含多个部分,每个部分有多个值,表示以下内容
平台:
架构:目标 CPU 的架构名称。应为
x86
,x64
,ppc64
,ppc64le
,armhf
,aarch64
,s390x
或unknown
之一。编译器:编译器名称。应为 gcc, clang, msvc, icc, iccw 或类 Unix 之一。
CPU 基线:
请求:
cpu-baseline
的具体特性和选项(原样)。已启用:最终启用的 CPU 特性集。
标志:编译期间用于所有 NumPy C/C++ 源文件的编译器标志,但用于生成调度特性二进制对象的临时源文件除外。
额外检查:内部检查列表,用于激活与已启用特性相关的某些功能或内在函数,在开发 SIMD 内核时有助于调试。
CPU 调度:
请求:
cpu-dispatch
的具体特性和选项(原样)。已启用:最终启用的 CPU 特性集。
已生成:在此属性的下一行开头,显示了已生成优化特性的形式,分为几个部分,其属性解释如下
一个或多个调度特性:隐含的 CPU 特性。
标志:用于这些特性的编译器标志。
额外检查:与基线类似,但针对这些调度特性。
检测:在运行时需要检测的 CPU 特性集,以便执行生成的优化。
上述属性之后以“:”在单独一行结尾的行,表示定义生成优化的 C/C++ 源文件路径。
运行时调度#
导入 NumPy 会触发对可调度特性集中可用 CPU 特性的扫描。可以通过将环境变量 NPY_DISABLE_CPU_FEATURES
设置为逗号、制表符或空格分隔的要禁用特性列表来进一步限制此操作。如果解析失败或特性未启用,这将引发错误。例如,在 x86_64
上,这将禁用 AVX2
和 FMA3
NPY_DISABLE_CPU_FEATURES="AVX2,FMA3"
如果该特性不可用,将发出警告。
跟踪调度函数#
通过 Python 函数 numpy.lib.introspect.opt_func_info
可以发现不同优化函数启用了哪些 CPU 目标。此函数提供了使用两个可选参数应用过滤器的灵活性:一个用于精炼函数名称,另一个用于指定签名中的数据类型。
例如
>> func_info = numpy.lib.introspect.opt_func_info(func_name='add|abs', signature='float64|complex64')
>> print(json.dumps(func_info, indent=2))
{
"absolute": {
"dd": {
"current": "SSE41",
"available": "SSE41 baseline(SSE SSE2 SSE3)"
},
"Ff": {
"current": "FMA3__AVX2",
"available": "AVX512F FMA3__AVX2 baseline(SSE SSE2 SSE3)"
},
"Dd": {
"current": "FMA3__AVX2",
"available": "AVX512F FMA3__AVX2 baseline(SSE SSE2 SSE3)"
}
},
"add": {
"ddd": {
"current": "FMA3__AVX2",
"available": "FMA3__AVX2 baseline(SSE SSE2 SSE3)"
},
"FFF": {
"current": "FMA3__AVX2",
"available": "FMA3__AVX2 baseline(SSE SSE2 SSE3)"
}
}
}