This is the mail archive of the libc-alpha@sourceware.org mailing list for the glibc project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

PATCH: Add family and model to cpu_features


We need to select different implementation not only on features, but
also on processor family/model.  This patch adds family and model to
cpu_features.

Our upcoming SSSE3 strcpy/stpcpy patch needs it.

Thanks.


H.J.
---
2009-06-26  H.J. Lu  <hongjiu.lu@intel.com>

	* sysdeps/x86_64/multiarch/ifunc-defines.sym (FAMILIY_OFFSET): New.
	(MODEL_OFFSET): Likewise.

	* sysdeps/x86_64/multiarch/init-arch.h (cpu_features): Add
	family and model.

	* sysdeps/x86_64/multiarch/init-arch.c (__init_cpu_features): Set 
	family and model.

diff --git a/sysdeps/x86_64/multiarch/ifunc-defines.sym b/sysdeps/x86_64/multiarch/ifunc-defines.sym
index 48d1287..24b3aec 100644
--- a/sysdeps/x86_64/multiarch/ifunc-defines.sym
+++ b/sysdeps/x86_64/multiarch/ifunc-defines.sym
@@ -5,6 +5,8 @@
 
 CPU_FEATURES_SIZE	sizeof (struct cpu_features)
 KIND_OFFSET		offsetof (struct cpu_features, kind)
+FAMILIY_OFFSET		offsetof (struct cpu_features, family)
+MODEL_OFFSET		offsetof (struct cpu_features, model)
 CPUID_OFFSET		offsetof (struct cpu_features, cpuid)
 CPUID_SIZE		sizeof (struct cpuid_registers)
 CPUID_EAX_OFFSET	offsetof (struct cpuid_registers, eax)
diff --git a/sysdeps/x86_64/multiarch/init-arch.c b/sysdeps/x86_64/multiarch/init-arch.c
index ec0eb29..1127e61 100644
--- a/sysdeps/x86_64/multiarch/init-arch.c
+++ b/sysdeps/x86_64/multiarch/init-arch.c
@@ -39,15 +39,39 @@ __init_cpu_features (void)
   /* This spells out "GenuineIntel".  */
   if (ebx == 0x756e6547 && ecx == 0x6c65746e && edx == 0x49656e69)
     {
+      unsigned int eax;
+      unsigned int model, family;
+
       __cpu_features.kind = arch_kind_intel;
 
     get_common_cpuid:
       asm volatile ("cpuid"
-		    : "=a" (__cpu_features.cpuid[COMMON_CPUID_INDEX_1].eax),
+		    : "=a" (eax),
 		      "=b" (__cpu_features.cpuid[COMMON_CPUID_INDEX_1].ebx),
 		      "=c" (__cpu_features.cpuid[COMMON_CPUID_INDEX_1].ecx),
 		      "=d" (__cpu_features.cpuid[COMMON_CPUID_INDEX_1].edx)
 		    : "0" (1));
+
+      __cpu_features.cpuid[COMMON_CPUID_INDEX_1].eax = eax;
+
+      family = (eax >> 8) & 0x0f;
+      model = (eax >> 4) & 0x0f;
+      if (__cpu_features.kind == arch_kind_intel)
+	{
+	  unsigned int extended_model, extended_family;
+
+	  extended_family = (eax >> 20) & 0xff;
+	  extended_model = (eax >> 12) & 0xf0;
+	  if (family == 0x0f)
+	    {
+	      family += extended_family;
+	      model += extended_model;
+	    }
+	  else if (family == 0x06)
+	    model += extended_model;
+	}
+      __cpu_features.family = family;
+      __cpu_features.model = model;
     }
   /* This spells out "AuthenticAMD".  */
   else if (ebx == 0x68747541 && ecx == 0x444d4163 && edx == 0x69746e65)
diff --git a/sysdeps/x86_64/multiarch/init-arch.h b/sysdeps/x86_64/multiarch/init-arch.h
index 5c4892d..48a2127 100644
--- a/sysdeps/x86_64/multiarch/init-arch.h
+++ b/sysdeps/x86_64/multiarch/init-arch.h
@@ -42,6 +42,8 @@ extern struct cpu_features
     unsigned int ecx;
     unsigned int edx;
   } cpuid[COMMON_CPUID_INDEX_MAX];
+  unsigned int family;
+  unsigned int model;
 } __cpu_features attribute_hidden;
 
 


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]