|
@@ -546,6 +546,37 @@ static void __init amd_detect_cmp(struct cpuinfo_x86 *c)
|
|
|
#endif
|
|
|
}
|
|
|
|
|
|
+#define ENABLE_C1E_MASK 0x18000000
|
|
|
+#define CPUID_PROCESSOR_SIGNATURE 1
|
|
|
+#define CPUID_XFAM 0x0ff00000
|
|
|
+#define CPUID_XFAM_K8 0x00000000
|
|
|
+#define CPUID_XFAM_10H 0x00100000
|
|
|
+#define CPUID_XFAM_11H 0x00200000
|
|
|
+#define CPUID_XMOD 0x000f0000
|
|
|
+#define CPUID_XMOD_REV_F 0x00040000
|
|
|
+
|
|
|
+/* AMD systems with C1E don't have a working lAPIC timer. Check for that. */
|
|
|
+static __cpuinit int amd_apic_timer_broken(void)
|
|
|
+{
|
|
|
+ u32 lo, hi;
|
|
|
+ u32 eax = cpuid_eax(CPUID_PROCESSOR_SIGNATURE);
|
|
|
+ switch (eax & CPUID_XFAM) {
|
|
|
+ case CPUID_XFAM_K8:
|
|
|
+ if ((eax & CPUID_XMOD) < CPUID_XMOD_REV_F)
|
|
|
+ break;
|
|
|
+ case CPUID_XFAM_10H:
|
|
|
+ case CPUID_XFAM_11H:
|
|
|
+ rdmsr(MSR_K8_ENABLE_C1E, lo, hi);
|
|
|
+ if (lo & ENABLE_C1E_MASK)
|
|
|
+ return 1;
|
|
|
+ break;
|
|
|
+ default:
|
|
|
+ /* err on the side of caution */
|
|
|
+ return 1;
|
|
|
+ }
|
|
|
+ return 0;
|
|
|
+}
|
|
|
+
|
|
|
static void __cpuinit init_amd(struct cpuinfo_x86 *c)
|
|
|
{
|
|
|
unsigned level;
|
|
@@ -617,6 +648,9 @@ static void __cpuinit init_amd(struct cpuinfo_x86 *c)
|
|
|
/* Family 10 doesn't support C states in MWAIT so don't use it */
|
|
|
if (c->x86 == 0x10 && !force_mwait)
|
|
|
clear_bit(X86_FEATURE_MWAIT, &c->x86_capability);
|
|
|
+
|
|
|
+ if (amd_apic_timer_broken())
|
|
|
+ disable_apic_timer = 1;
|
|
|
}
|
|
|
|
|
|
static void __cpuinit detect_ht(struct cpuinfo_x86 *c)
|