Messages in this thread Patch in this message | | | Date | Fri, 6 Dec 2019 11:39:42 +0100 | From | Peter Zijlstra <> | Subject | Re: [PATCH] x86/tsc: Don't use cpuid 0x16 leaf to determine cpu speed. |
| |
On Thu, Dec 05, 2019 at 07:15:03PM +0000, Krzysztof Piecuch wrote: > This patch corrects tsc drift on systems with changed base clock frequency > (e.g. overclocking). > > We can't use 0x16 cpu leaf as it's documented as "not reflecting actual > values" and is supposed to be used only as a mean to determine "processor > brand string and for determining the appropriate range to use when > displaying processor information e.g. frequency history graphs".
What is the actual problem you're seeing? Because if CPUID.16h is used, we don't set KNOWN_FREQ and will thus run tsc_refine_calibration_work() (against HPET/PIT) later.
The CPUIS.16h value is only used as an initial guess.
> Signed-off-by: Krzysztof Piecuch <piecuch@protonmail.com> > --- > arch/x86/kernel/tsc.c | 21 ++++----------------- > 1 file changed, 4 insertions(+), 17 deletions(-) > > diff --git a/arch/x86/kernel/tsc.c b/arch/x86/kernel/tsc.c > index 7e322e2daaf5..fc9a000a814c 100644 > --- a/arch/x86/kernel/tsc.c > +++ b/arch/x86/kernel/tsc.c > @@ -641,29 +641,16 @@ unsigned long native_calibrate_tsc(void) > boot_cpu_data.x86_model == INTEL_FAM6_ATOM_GOLDMONT_D) > crystal_khz = 25000; > > + if (crystal_khz == 0) > + return 0; > + > /* > * TSC frequency reported directly by CPUID is a "hardware reported" > * frequency and is the most accurate one so far we have. This > * is considered a known frequency. > */ > - if (crystal_khz != 0) > - setup_force_cpu_cap(X86_FEATURE_TSC_KNOWN_FREQ); > - > - /* > - * Some Intel SoCs like Skylake and Kabylake don't report the crystal > - * clock, but we can easily calculate it to a high degree of accuracy > - * by considering the crystal ratio and the CPU speed. > - */ > - if (crystal_khz == 0 && boot_cpu_data.cpuid_level >= 0x16) { > - unsigned int eax_base_mhz, ebx, ecx, edx; > - > - cpuid(0x16, &eax_base_mhz, &ebx, &ecx, &edx); > - crystal_khz = eax_base_mhz * 1000 * > - eax_denominator / ebx_numerator; > - } > > - if (crystal_khz == 0) > - return 0; > + setup_force_cpu_cap(X86_FEATURE_TSC_KNOWN_FREQ); > > /* > * For Atom SoCs TSC is the only reliable clocksource.
This completely screws over everything that doesn't have HPET/PIT and doesn't have a useful CPUID.15h.
If you're on a system that has no HPET/PIT and also doesn't have a useful CPUID.15h and CPUID.16h is wrong, then you're up a creek without paddles.
So please, be more specific in your problem description.
| |