Ste*_*nov 4 x86 sse simd intrinsics
_mm_broadcast_ss()和之间有什么区别_mm_load_ps1()?
void example(){
__declspec(align(32)) const float num = 20;
__m128 a1 = _mm_broadcast_ss(&num);
__declspec(align(32)) float f1[4];
_mm_store_ps (f1, a1);
std::cout << f1[0] << " " << f1[1] <<" " << f1[2] << " " << f1[3] << "\n";
__m128 a2 = _mm_load_ps1(&num);
__declspec(align(32)) float f2[4];
_mm_store_ps (f2, a2);
std::cout << f2[0] << " " << f2[1] <<" " << f2[2] << " " << f2[3] << "\n";
}
Run Code Online (Sandbox Code Playgroud)
我两种方式都有相同的输出,那么为什么它们都存在?
_mm_broadcast_ss 仅编译AVX目标.
_mm_load1_ps/ _mm_load_ps1将在编译不支持AVX的目标时编译为多个指令(movss/ shufps).当你正在编写一个AVX的目标,任何好的编译器将使用vbroadcastss来实现它们.
load1/ set1和其他便利函数在早期就已经引入,因为让编译器选择最佳的数据移动策略通常是好的.
_mm_broadcast_*内在函数是作为vbroadcastss/ vbroadcastsd指令的直接包装引入的.(AVX2有整数vpbroadcast...,vbroadcastss只有.AVX1 的reg-reg形式vbroadcastss x/ymm, [mem].)
_mm_load1_ps或没有任何缺点_mm_set1_ps.它对代码没有任何影响,并为非AVX目标提供相同的源代码构建.
选择可能会对asm输出产生影响-O0,但是IDK.如果你关心未优化构建中的asm输出,那么1:这很奇怪,2:你必须看看你的编译器做了什么.
正如你从godbolt上的asm输出中看到的那样(对于gcc):
-mno-avx)bcast: compile error so I #ifdef it out
__m128 load1(const float*p) { return _mm_load1_ps(p); }
movss xmm0, DWORD PTR [rdi]
shufps xmm0, xmm0, 0
ret
Run Code Online (Sandbox Code Playgroud)
-mavx)__m128 bcast(const float*p) { return _mm_broadcast_ss(p); }
vbroadcastss xmm0, DWORD PTR [rdi]
ret
__m128 load1(const float*p) { return _mm_load1_ps(p); }
vbroadcastss xmm0, DWORD PTR [rdi]
ret
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1326 次 |
| 最近记录: |