检查我的平台上是否存在命令 AVX、SSE (SSE1-SSE4.2)、FPU
Check exist on my platform commands AVX, SSE (SSE1-SSE4.2), FPU
我有一个任务:检查我的平台上是否存在命令 AVX、SSE (SSE1-SSE4.2)、FPU。
我的汇编代码不工作,我不明白为什么。
我认为是不正确的描述输出修饰符。
unsigned int AVX;
unsigned int SSE1;
unsigned int SSE2;
unsigned int SSE3;
unsigned int SSSE3;
unsigned int SSE41;
unsigned int SSE42;
unsigned int FPU;
__asm__(
"cpuid\n\t"
"movl %%edx, %[AVX]\n\t"
"and $(1<<28), %[AVX]\n\t"
"movl %%edx, %[SSE1]\n\t"
"and $(1<<25), %[SSE1]\n\t"
"movl %%edx, %[SSE2]\n\t"
"and $(1<<26), %[SSE2]\n\t"
"movl %%ecx, %[SSE3]\n\t"
"and $(1<<9), %[SSE3]\n\t"
"movl %%ecx, %[SSSE3]\n\t"
"and $(1<<9), %[SSSE3]\n\t"
"movl %%edx, %[SSE41]\n\t"
"and $(1<<19), %[SSE41]\n\t"
"movl %%ecx, %[SSE42]\n\t"
"and $(1<<20), %[SSE42]\n\t"
"movl %%edx, %[FPU]\n\t"
"and $(1<<0), %[FPU]\n\t"
: [AVX] "=&r"(AVX), [SSE1]"=&r"(SSE1),
[SSE2]"=&r"(SSE2), [SSE3]"=&r"(SSE3),
[SSSE3]"=&r"(SSSE3), [SSE41]"=&r"(SSE41),
[SSE42]"=&r"(SSE42), [FPU]"=&r"(FPU)
: "a"(1)
: "cc"
);
cout << "AVX:" << (bool)AVX << endl;
cout << "SSE1:" << (bool)SSE1 << endl;
cout << "SSE2:" << (bool)SSE2 << endl;
cout << "SSE3:" << (bool)SSE3 << endl;
cout << "SSSE3:" << (bool)SSSE3 << endl;
cout << "SSE41:" << (bool)SSE41 << endl;
cout << "SSE42:" << (bool)SSE42 << endl;
cout << "FPU:" << (bool)FPU << endl;
错误:'asm'操作数具有不可能的约束
在32位模式下编程时,通用寄存器只有六七个,所以编译器无法将八个输出操作数和一个输入操作数分配给寄存器。您还忘记声明正确的 clobbers(cpuid
clobbers eax
、ebx
、ecx
和 edx
),如果不更正,将在运行时导致意外行为.
最好不要内联汇编来做这种事情,例如使用某种库或 gcc 的内置函数:
int AVX, SSE1, SSE2, SSE3, SSSE3, SSE41, SSE42;
__builtin_cpu_init();
SSE1 = __builtin_cpu_supports("sse");
SSE2 = __builtin_cpu_supports("sse2");
SSE3 = __builtin_cpu_supports("sse3");
SSSE3 = __builtin_cpu_supports("ssse3");
SSE41 = __builtin_cpu_supports("sse4.1");
SSE42 = __builtin_cpu_supports("sse4.2");
AVX = __builtin_cpu_supports("avx");
同时考虑使用 Intel 内部函数 _may_i_use_cpu_feature
and the <cpuid.h>
interface。
请注意,检查这些位并不能告诉您操作系统是否实际启用了 CPU 功能,因此尝试使用这些功能的代码可能仍会在运行时崩溃。
如果必须使用内联汇编,请尽量减少内联汇编的工作量。
int eax = 1, ecx, edx;
int AVX, FPU, SSE1, SSE2, SSE3, SSSE3, SSE41, SSE42;
asm ("cpuid" : "+a"(eax), "=c"(ecx), "=d"(edx) :: "ebx");
FPU = edx & 1 << 0;
AVX = ecx & 1 << 28;
SSE1 = edx & 1 << 25;
SSE2 = edx & 1 << 26;
SSE3 = ecx & 1 << 0;
SSSE3 = ecx & 1 << 9;
SSE41 = ecx & 1 << 19;
SSE42 = ecx & 1 << 20;
我有一个任务:检查我的平台上是否存在命令 AVX、SSE (SSE1-SSE4.2)、FPU。 我的汇编代码不工作,我不明白为什么。 我认为是不正确的描述输出修饰符。
unsigned int AVX;
unsigned int SSE1;
unsigned int SSE2;
unsigned int SSE3;
unsigned int SSSE3;
unsigned int SSE41;
unsigned int SSE42;
unsigned int FPU;
__asm__(
"cpuid\n\t"
"movl %%edx, %[AVX]\n\t"
"and $(1<<28), %[AVX]\n\t"
"movl %%edx, %[SSE1]\n\t"
"and $(1<<25), %[SSE1]\n\t"
"movl %%edx, %[SSE2]\n\t"
"and $(1<<26), %[SSE2]\n\t"
"movl %%ecx, %[SSE3]\n\t"
"and $(1<<9), %[SSE3]\n\t"
"movl %%ecx, %[SSSE3]\n\t"
"and $(1<<9), %[SSSE3]\n\t"
"movl %%edx, %[SSE41]\n\t"
"and $(1<<19), %[SSE41]\n\t"
"movl %%ecx, %[SSE42]\n\t"
"and $(1<<20), %[SSE42]\n\t"
"movl %%edx, %[FPU]\n\t"
"and $(1<<0), %[FPU]\n\t"
: [AVX] "=&r"(AVX), [SSE1]"=&r"(SSE1),
[SSE2]"=&r"(SSE2), [SSE3]"=&r"(SSE3),
[SSSE3]"=&r"(SSSE3), [SSE41]"=&r"(SSE41),
[SSE42]"=&r"(SSE42), [FPU]"=&r"(FPU)
: "a"(1)
: "cc"
);
cout << "AVX:" << (bool)AVX << endl;
cout << "SSE1:" << (bool)SSE1 << endl;
cout << "SSE2:" << (bool)SSE2 << endl;
cout << "SSE3:" << (bool)SSE3 << endl;
cout << "SSSE3:" << (bool)SSSE3 << endl;
cout << "SSE41:" << (bool)SSE41 << endl;
cout << "SSE42:" << (bool)SSE42 << endl;
cout << "FPU:" << (bool)FPU << endl;
错误:'asm'操作数具有不可能的约束
在32位模式下编程时,通用寄存器只有六七个,所以编译器无法将八个输出操作数和一个输入操作数分配给寄存器。您还忘记声明正确的 clobbers(cpuid
clobbers eax
、ebx
、ecx
和 edx
),如果不更正,将在运行时导致意外行为.
最好不要内联汇编来做这种事情,例如使用某种库或 gcc 的内置函数:
int AVX, SSE1, SSE2, SSE3, SSSE3, SSE41, SSE42;
__builtin_cpu_init();
SSE1 = __builtin_cpu_supports("sse");
SSE2 = __builtin_cpu_supports("sse2");
SSE3 = __builtin_cpu_supports("sse3");
SSSE3 = __builtin_cpu_supports("ssse3");
SSE41 = __builtin_cpu_supports("sse4.1");
SSE42 = __builtin_cpu_supports("sse4.2");
AVX = __builtin_cpu_supports("avx");
同时考虑使用 Intel 内部函数 _may_i_use_cpu_feature
and the <cpuid.h>
interface。
请注意,检查这些位并不能告诉您操作系统是否实际启用了 CPU 功能,因此尝试使用这些功能的代码可能仍会在运行时崩溃。
如果必须使用内联汇编,请尽量减少内联汇编的工作量。
int eax = 1, ecx, edx;
int AVX, FPU, SSE1, SSE2, SSE3, SSSE3, SSE41, SSE42;
asm ("cpuid" : "+a"(eax), "=c"(ecx), "=d"(edx) :: "ebx");
FPU = edx & 1 << 0;
AVX = ecx & 1 << 28;
SSE1 = edx & 1 << 25;
SSE2 = edx & 1 << 26;
SSE3 = ecx & 1 << 0;
SSSE3 = ecx & 1 << 9;
SSE41 = ecx & 1 << 19;
SSE42 = ecx & 1 << 20;