]> git.ipfire.org Git - thirdparty/postgresql.git/commitdiff
Check for __cpuidex and __get_cpuid_count separately
authorJohn Naylor <john.naylor@postgresql.org>
Thu, 2 Apr 2026 12:39:57 +0000 (19:39 +0700)
committerJohn Naylor <john.naylor@postgresql.org>
Thu, 2 Apr 2026 12:39:57 +0000 (19:39 +0700)
Previously we would only check for the availability of __cpuidex if
the related __get_cpuid_count was not available on a platform.

Future commits will need to access hypervisor information about
the TSC frequency of x86 CPUs. For that case __cpuidex is the only
viable option for accessing a high leaf (e.g. 0x40000000), since
__get_cpuid_count does not allow that.

__cpuidex is defined in cpuid.h for gcc/clang, but in intrin.h
for MSVC, so adjust tests to suite. We also need to cast the array
of unsigned ints to signed, since gcc (with -Wall) and clang emit
warnings otherwise.

Author: Lukas Fittl <lukas@fittl.com>
Reviewed-by: Andres Freund <andres@anarazel.de>
Reviewed-by: John Naylor <john.naylor@postgresql.org>
Discussion: https://postgr.es/m/CAP53PkyooCeR8YV0BUD_xC7oTZESHz8OdA=tP7pBRHFVQ9xtKg@mail.gmail.com

configure
configure.ac
meson.build
src/port/pg_cpu_x86.c

index 0d123d7dc8a548a76c9b4ca66951e7bf2072444a..fe22bc71d0cd18cc489843ce5b6f781c2b034ae4 100755 (executable)
--- a/configure
+++ b/configure
@@ -17746,7 +17746,7 @@ $as_echo "#define HAVE__CPUID 1" >>confdefs.h
   fi
 fi
 
-# Check for __get_cpuid_count() and __cpuidex() in a similar fashion.
+# Check for __get_cpuid_count()
 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for __get_cpuid_count" >&5
 $as_echo_n "checking for __get_cpuid_count... " >&6; }
 if ${pgac_cv__get_cpuid_count+:} false; then :
@@ -17779,21 +17779,26 @@ if test x"$pgac_cv__get_cpuid_count" = x"yes"; then
 
 $as_echo "#define HAVE__GET_CPUID_COUNT 1" >>confdefs.h
 
-else
-  # __cpuidex()
-  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for __cpuidex" >&5
+fi
+
+# Check for __cpuidex()
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for __cpuidex" >&5
 $as_echo_n "checking for __cpuidex... " >&6; }
 if ${pgac_cv__cpuidex+:} false; then :
   $as_echo_n "(cached) " >&6
 else
   cat confdefs.h - <<_ACEOF >conftest.$ac_ext
 /* end confdefs.h.  */
-#include <intrin.h>
+#ifdef _MSC_VER
+    #include <intrin.h>
+    #else
+    #include <cpuid.h>
+    #endif
 int
 main ()
 {
 unsigned int exx[4] = {0, 0, 0, 0};
-    __cpuidex(exx, 7, 0);
+  __cpuidex((int *) exx, 7, 0);
 
   ;
   return 0;
@@ -17809,11 +17814,10 @@ rm -f core conftest.err conftest.$ac_objext \
 fi
 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $pgac_cv__cpuidex" >&5
 $as_echo "$pgac_cv__cpuidex" >&6; }
-  if test x"$pgac_cv__cpuidex" = x"yes"; then
+if test x"$pgac_cv__cpuidex" = x"yes"; then
 
 $as_echo "#define HAVE__CPUIDEX 1" >>confdefs.h
 
-  fi
 fi
 
 # Check for XSAVE intrinsics
index 2342780359a0c510778e0cc3fc08b1e91111fde9..6873b7546dd5f8f61a3723ca0ad40d2c57db20d8 100644 (file)
@@ -2107,7 +2107,7 @@ else
   fi
 fi
 
-# Check for __get_cpuid_count() and __cpuidex() in a similar fashion.
+# Check for __get_cpuid_count()
 AC_CACHE_CHECK([for __get_cpuid_count], [pgac_cv__get_cpuid_count],
 [AC_LINK_IFELSE([AC_LANG_PROGRAM([#include <cpuid.h>],
   [[unsigned int exx[4] = {0, 0, 0, 0};
@@ -2117,18 +2117,22 @@ AC_CACHE_CHECK([for __get_cpuid_count], [pgac_cv__get_cpuid_count],
   [pgac_cv__get_cpuid_count="no"])])
 if test x"$pgac_cv__get_cpuid_count" = x"yes"; then
   AC_DEFINE(HAVE__GET_CPUID_COUNT, 1, [Define to 1 if you have __get_cpuid_count.])
-else
-  # __cpuidex()
-  AC_CACHE_CHECK([for __cpuidex], [pgac_cv__cpuidex],
-  [AC_LINK_IFELSE([AC_LANG_PROGRAM([#include <intrin.h>],
-    [[unsigned int exx[4] = {0, 0, 0, 0};
-    __cpuidex(exx, 7, 0);
-    ]])],
-    [pgac_cv__cpuidex="yes"],
-    [pgac_cv__cpuidex="no"])])
-  if test x"$pgac_cv__cpuidex" = x"yes"; then
-    AC_DEFINE(HAVE__CPUIDEX, 1, [Define to 1 if you have __cpuidex.])
-  fi
+fi
+
+# Check for __cpuidex()
+AC_CACHE_CHECK([for __cpuidex], [pgac_cv__cpuidex],
+[AC_LINK_IFELSE([AC_LANG_PROGRAM([#ifdef _MSC_VER
+    #include <intrin.h>
+    #else
+    #include <cpuid.h>
+    #endif],
+  [[unsigned int exx[4] = {0, 0, 0, 0};
+  __cpuidex((int *) exx, 7, 0);
+  ]])],
+  [pgac_cv__cpuidex="yes"],
+  [pgac_cv__cpuidex="no"])])
+if test x"$pgac_cv__cpuidex" = x"yes"; then
+  AC_DEFINE(HAVE__CPUIDEX, 1, [Define to 1 if you have __cpuidex.])
 fi
 
 # Check for XSAVE intrinsics
index 8b134b28a6948605965442712875ff1c5610a8f0..6bc74c2ba7908501313d1f420eb002593a66fee9 100644 (file)
@@ -2132,7 +2132,7 @@ elif cc.links('''
 endif
 
 
-# Check for __get_cpuid_count() and __cpuidex() in a similar fashion.
+# Check for __get_cpuid_count()
 if cc.links('''
     #include <cpuid.h>
     int main(int arg, char **argv)
@@ -2143,12 +2143,19 @@ if cc.links('''
     ''', name: '__get_cpuid_count',
     args: test_c_args)
   cdata.set('HAVE__GET_CPUID_COUNT', 1)
-elif cc.links('''
+endif
+
+# Check for __cpuidex()
+if cc.links('''
+    #ifdef _MSC_VER
     #include <intrin.h>
+    #else
+    #include <cpuid.h>
+    #endif
     int main(int arg, char **argv)
     {
         unsigned int exx[4] = {0, 0, 0, 0};
-        __cpuidex(exx, 7, 0);
+        __cpuidex((int *) exx, 7, 0);
     }
     ''', name: '__cpuidex',
     args: test_c_args)
index e2ab92b09acc0a7cfd951279e3793ddcb0b447d6..1331f3f4eb8f937bdfe800bc54d9b126c8610ec9 100644 (file)
 
 #if defined(USE_SSE2) || defined(__i386__)
 
-#if defined(HAVE__GET_CPUID) || defined(HAVE__GET_CPUID_COUNT)
-#include <cpuid.h>
-#endif
-
-#if defined(HAVE__CPUID) || defined(HAVE__CPUIDEX)
+#ifdef _MSC_VER
 #include <intrin.h>
+#else
+#include <cpuid.h>
 #endif
 
 #ifdef HAVE_XSAVE_INTRINSICS