From 3289bca708bdd02c69a331095ac6ca9a1efd74cc Mon Sep 17 00:00:00 2001 From: Jussi Kivilinna Date: Sun, 9 Jun 2013 16:37:38 +0300 Subject: Add detection for Intel AVX2 instruction set * configure.ac: Add option --disable-avx2-support. (HAVE_GCC_INLINE_ASM_AVX2): New. (ENABLE_AVX2_SUPPORT): New. * src/g10lib.h (HWF_INTEL_AVX2): New. * src/global.c (hwflist): Add HWF_INTEL_AVX2. * src/hwf-x86.c [__i386__] (get_cpuid): Initialize registers to zero before cpuid. [__x86_64__] (get_cpuid): Initialize registers to zero before cpuid. (detect_x86_gnuc): Store maximum cpuid level. (detect_x86_gnuc) [ENABLE_AVX2_SUPPORT]: Add detection for AVX2. -- Signed-off-by: Jussi Kivilinna --- src/hwf-x86.c | 24 +++++++++++++++++++++--- 1 file changed, 21 insertions(+), 3 deletions(-) (limited to 'src/hwf-x86.c') diff --git a/src/hwf-x86.c b/src/hwf-x86.c index 1e6ec944..2ceb04c8 100644 --- a/src/hwf-x86.c +++ b/src/hwf-x86.c @@ -77,11 +77,12 @@ get_cpuid(unsigned int in, unsigned int *eax, unsigned int *ebx, asm volatile ("pushl %%ebx\n\t" /* Save GOT register. */ + "movl %1, %%ebx\n\t" "cpuid\n\t" "movl %%ebx, %1\n\t" "popl %%ebx\n\t" /* Restore GOT register. */ : "=a" (regs[0]), "=r" (regs[1]), "=c" (regs[2]), "=d" (regs[3]) - : "0" (in) + : "0" (in), "1" (0), "2" (0), "3" (0) : "cc" ); @@ -115,7 +116,7 @@ get_cpuid(unsigned int in, unsigned int *eax, unsigned int *ebx, asm volatile ("cpuid\n\t" : "=a" (regs[0]), "=b" (regs[1]), "=c" (regs[2]), "=d" (regs[3]) - : "0" (in) + : "0" (in), "1" (0), "2" (0), "3" (0) : "cc" ); @@ -137,12 +138,13 @@ detect_x86_gnuc (void) { char vendor_id[12+1]; unsigned int features; + unsigned int max_cpuid_level; unsigned int result = 0; if (!is_cpuid_available()) return 0; - get_cpuid(0, NULL, + get_cpuid(0, &max_cpuid_level, (unsigned int *)&vendor_id[0], (unsigned int *)&vendor_id[8], (unsigned int *)&vendor_id[4]); @@ -215,6 +217,22 @@ detect_x86_gnuc (void) result |= HWF_INTEL_RDRAND; #endif /*ENABLE_DRNG_SUPPORT*/ + /* Check additional Intel feature flags. Early Intel P5 processors report + * too high max_cpuid_level, so don't check level 7 if processor does not + * support SSE3 (as cpuid:7 contains only features for newer processors). + * Source: http://www.sandpile.org/x86/cpuid.htm */ + if (max_cpuid_level >= 7 && (features & 0x00000001)) + { +#ifdef ENABLE_AVX2_SUPPORT + /* Get CPUID:7 contains further Intel feature flags. */ + get_cpuid(7, NULL, &features, NULL, NULL); + + /* Test bit 5 for AVX2. */ + if (features & 0x00000020) + result |= HWF_INTEL_AVX2; +#endif /*ENABLE_AVX_SUPPORT*/ + } + return result; } #endif /* HAS_X86_CPUID */ -- cgit v1.2.1