cpu/x86/tsc: Flip and rename TSC_CONSTANT_RATE to UNKNOWN_TSC_RATE
The x86 timers are a bit of a mess. Cases where different stages use different counters and timestamps use different counters from udelays. The original intention was to only flip TSC_CONSTANT_RATE Kconfig to NOT_CONSTANT_TSC_RATE. The name would be incorrect though, those counters do run with a constant rate but we just lack tsc_freq_mhz() implementation for three platforms. Note that for boards with UNKNOWN_TSC_RATE=y, each stage will have a slow run of calibrate_tsc_with_pit(). This is easy enough to fix with followup implementation of tsc_freq_mhz() for the platforms. Implementations with LAPIC_MONOTONIC_TIMER typically will not have tsc_freq_mhz() implemented and default to UNKNOWN_TSC_RATE. However, as they don't use TSC for udelay() the slow calibrate_tsc_with_pit() is avoided. Because x86/tsc_delay.tsc was using two different guards and nb/via/vx900 claimed UDELAY_TSC, but pulled UDELAY_IO implementation, we also switch that romstage to use UDELAY_TSC. Change-Id: I1690cb80295d6b006b75ed69edea28899b674b68 Signed-off-by: Kyösti Mälkki <kyosti.malkki@gmail.com> Reviewed-on: https://review.coreboot.org/c/coreboot/+/33928 Tested-by: build bot (Jenkins) <no-reply@coreboot.org> Reviewed-by: Aaron Durbin <adurbin@chromium.org>
This commit is contained in:
		@@ -32,7 +32,6 @@ config CPU_SPECIFIC_OPTIONS
 | 
			
		||||
	select PARALLEL_CPU_INIT
 | 
			
		||||
	select TSC_SYNC_MFENCE
 | 
			
		||||
	select TSC_MONOTONIC_TIMER
 | 
			
		||||
	select TSC_CONSTANT_RATE
 | 
			
		||||
	select CPU_INTEL_COMMON
 | 
			
		||||
	select CPU_INTEL_COMMON_TIMEBASE
 | 
			
		||||
	select NO_SMM
 | 
			
		||||
 
 | 
			
		||||
@@ -14,7 +14,6 @@ config CPU_SPECIFIC_OPTIONS
 | 
			
		||||
	select MMX
 | 
			
		||||
	select SSE2
 | 
			
		||||
	select UDELAY_TSC
 | 
			
		||||
	select TSC_CONSTANT_RATE
 | 
			
		||||
	select TSC_MONOTONIC_TIMER
 | 
			
		||||
	select SUPPORT_CPU_UCODE_IN_CBFS
 | 
			
		||||
	#select AP_IN_SIPI_WAIT
 | 
			
		||||
 
 | 
			
		||||
@@ -7,7 +7,6 @@ config CPU_INTEL_MODEL_1067X
 | 
			
		||||
	select SMP
 | 
			
		||||
	select SSE2
 | 
			
		||||
	select UDELAY_TSC
 | 
			
		||||
	select TSC_CONSTANT_RATE
 | 
			
		||||
	select TSC_MONOTONIC_TIMER
 | 
			
		||||
	select TSC_SYNC_MFENCE
 | 
			
		||||
	select SUPPORT_CPU_UCODE_IN_CBFS
 | 
			
		||||
 
 | 
			
		||||
@@ -7,7 +7,6 @@ config CPU_INTEL_MODEL_106CX
 | 
			
		||||
	select SMP
 | 
			
		||||
	select SSE2
 | 
			
		||||
	select UDELAY_TSC
 | 
			
		||||
	select TSC_CONSTANT_RATE
 | 
			
		||||
	select TSC_MONOTONIC_TIMER
 | 
			
		||||
	select SIPI_VECTOR_IN_ROM
 | 
			
		||||
	select AP_IN_SIPI_WAIT
 | 
			
		||||
 
 | 
			
		||||
@@ -12,7 +12,6 @@ config CPU_SPECIFIC_OPTIONS
 | 
			
		||||
	select SMP
 | 
			
		||||
	select SSE2
 | 
			
		||||
	select UDELAY_TSC
 | 
			
		||||
	select TSC_CONSTANT_RATE
 | 
			
		||||
	select TSC_MONOTONIC_TIMER
 | 
			
		||||
	select SUPPORT_CPU_UCODE_IN_CBFS
 | 
			
		||||
	select PARALLEL_CPU_INIT
 | 
			
		||||
 
 | 
			
		||||
@@ -13,7 +13,6 @@ config CPU_SPECIFIC_OPTIONS
 | 
			
		||||
	select MMX
 | 
			
		||||
	select SSE2
 | 
			
		||||
	select UDELAY_TSC
 | 
			
		||||
	select TSC_CONSTANT_RATE
 | 
			
		||||
	select TSC_MONOTONIC_TIMER
 | 
			
		||||
	select SUPPORT_CPU_UCODE_IN_CBFS
 | 
			
		||||
	#select AP_IN_SIPI_WAIT
 | 
			
		||||
 
 | 
			
		||||
@@ -7,7 +7,6 @@ config CPU_INTEL_MODEL_6EX
 | 
			
		||||
	select SMP
 | 
			
		||||
	select SSE2
 | 
			
		||||
	select UDELAY_TSC
 | 
			
		||||
	select TSC_CONSTANT_RATE
 | 
			
		||||
	select TSC_MONOTONIC_TIMER
 | 
			
		||||
	select AP_IN_SIPI_WAIT
 | 
			
		||||
	select TSC_SYNC_MFENCE
 | 
			
		||||
 
 | 
			
		||||
@@ -7,7 +7,6 @@ config CPU_INTEL_MODEL_6FX
 | 
			
		||||
	select SMP
 | 
			
		||||
	select SSE2
 | 
			
		||||
	select UDELAY_TSC
 | 
			
		||||
	select TSC_CONSTANT_RATE
 | 
			
		||||
	select TSC_MONOTONIC_TIMER
 | 
			
		||||
	select AP_IN_SIPI_WAIT
 | 
			
		||||
	select TSC_SYNC_MFENCE
 | 
			
		||||
 
 | 
			
		||||
@@ -25,6 +25,7 @@ config SLOT_SPECIFIC_OPTIONS # dummy
 | 
			
		||||
	select CPU_INTEL_MODEL_6XX
 | 
			
		||||
	select NO_SMM
 | 
			
		||||
	select NO_MONOTONIC_TIMER
 | 
			
		||||
	select UNKNOWN_TSC_RATE
 | 
			
		||||
 | 
			
		||||
config DCACHE_RAM_BASE
 | 
			
		||||
	hex
 | 
			
		||||
 
 | 
			
		||||
@@ -9,7 +9,6 @@ config SOCKET_SPECIFIC_OPTIONS # dummy
 | 
			
		||||
	select MMX
 | 
			
		||||
	select SSE
 | 
			
		||||
	select UDELAY_TSC
 | 
			
		||||
	select TSC_CONSTANT_RATE
 | 
			
		||||
	select TSC_MONOTONIC_TIMER
 | 
			
		||||
	select SIPI_VECTOR_IN_ROM
 | 
			
		||||
	select C_ENVIRONMENT_BOOTBLOCK
 | 
			
		||||
 
 | 
			
		||||
@@ -20,5 +20,6 @@ config CPU_QEMU_X86
 | 
			
		||||
	select SMP
 | 
			
		||||
	select UDELAY_TSC
 | 
			
		||||
	select TSC_MONOTONIC_TIMER
 | 
			
		||||
	select UNKNOWN_TSC_RATE
 | 
			
		||||
	select C_ENVIRONMENT_BOOTBLOCK
 | 
			
		||||
	select SMM_ASEG
 | 
			
		||||
 
 | 
			
		||||
@@ -25,6 +25,7 @@ config CPU_SPECIFIC_OPTIONS
 | 
			
		||||
	select ARCH_RAMSTAGE_X86_32
 | 
			
		||||
	select UDELAY_TSC
 | 
			
		||||
	select TSC_MONOTONIC_TIMER
 | 
			
		||||
	select UNKNOWN_TSC_RATE
 | 
			
		||||
	select MMX
 | 
			
		||||
	select SSE2
 | 
			
		||||
	select SUPPORT_CPU_UCODE_IN_CBFS
 | 
			
		||||
 
 | 
			
		||||
@@ -34,12 +34,9 @@ config UDELAY_TSC
 | 
			
		||||
	bool
 | 
			
		||||
	default n
 | 
			
		||||
 | 
			
		||||
config TSC_CONSTANT_RATE
 | 
			
		||||
	def_bool n
 | 
			
		||||
	depends on UDELAY_TSC
 | 
			
		||||
	help
 | 
			
		||||
	  This option asserts that the TSC ticks at a known constant rate.
 | 
			
		||||
	  Therefore, no TSC calibration is required.
 | 
			
		||||
config UNKNOWN_TSC_RATE
 | 
			
		||||
	bool
 | 
			
		||||
	default y if LAPIC_MONOTONIC_TIMER
 | 
			
		||||
 | 
			
		||||
config TSC_MONOTONIC_TIMER
 | 
			
		||||
	def_bool n
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,6 @@
 | 
			
		||||
bootblock-$(CONFIG_UDELAY_TSC) += delay_tsc.c
 | 
			
		||||
ramstage-$(CONFIG_UDELAY_TSC) += delay_tsc.c
 | 
			
		||||
romstage-$(CONFIG_TSC_CONSTANT_RATE) += delay_tsc.c
 | 
			
		||||
verstage-$(CONFIG_TSC_CONSTANT_RATE) += delay_tsc.c
 | 
			
		||||
postcar-$(CONFIG_TSC_CONSTANT_RATE) += delay_tsc.c
 | 
			
		||||
smm-$(CONFIG_TSC_CONSTANT_RATE) += delay_tsc.c
 | 
			
		||||
romstage-$(CONFIG_UDELAY_TSC) += delay_tsc.c
 | 
			
		||||
verstage-$(CONFIG_UDELAY_TSC) += delay_tsc.c
 | 
			
		||||
postcar-$(CONFIG_UDELAY_TSC) += delay_tsc.c
 | 
			
		||||
smm-$(CONFIG_UDELAY_TSC) += delay_tsc.c
 | 
			
		||||
 
 | 
			
		||||
@@ -18,26 +18,9 @@
 | 
			
		||||
#include <delay.h>
 | 
			
		||||
#include <thread.h>
 | 
			
		||||
 | 
			
		||||
static unsigned long clocks_per_usec CAR_GLOBAL;
 | 
			
		||||
 | 
			
		||||
static unsigned long calibrate_tsc(void)
 | 
			
		||||
{
 | 
			
		||||
	if (CONFIG(TSC_CONSTANT_RATE))
 | 
			
		||||
		return tsc_freq_mhz();
 | 
			
		||||
	else
 | 
			
		||||
		return calibrate_tsc_with_pit();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void init_timer(void)
 | 
			
		||||
{
 | 
			
		||||
	if (!car_get_var(clocks_per_usec))
 | 
			
		||||
		car_set_var(clocks_per_usec, calibrate_tsc());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static inline unsigned long get_clocks_per_usec(void)
 | 
			
		||||
{
 | 
			
		||||
	init_timer();
 | 
			
		||||
	return car_get_var(clocks_per_usec);
 | 
			
		||||
	(void)tsc_freq_mhz();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void udelay(unsigned int us)
 | 
			
		||||
@@ -51,7 +34,7 @@ void udelay(unsigned int us)
 | 
			
		||||
 | 
			
		||||
	start = rdtscll();
 | 
			
		||||
	clocks = us;
 | 
			
		||||
	clocks *= get_clocks_per_usec();
 | 
			
		||||
	clocks *= tsc_freq_mhz();
 | 
			
		||||
	current = rdtscll();
 | 
			
		||||
	while ((current - start) < clocks) {
 | 
			
		||||
		cpu_relax();
 | 
			
		||||
@@ -89,7 +72,7 @@ void timer_monotonic_get(struct mono_time *mt)
 | 
			
		||||
 | 
			
		||||
	current_tick = rdtscll();
 | 
			
		||||
	ticks_elapsed = current_tick - mono_counter->last_value;
 | 
			
		||||
	ticks_per_usec = get_clocks_per_usec();
 | 
			
		||||
	ticks_per_usec = tsc_freq_mhz();
 | 
			
		||||
 | 
			
		||||
	/* Update current time and tick values only if a full tick occurred. */
 | 
			
		||||
	if (ticks_elapsed >= ticks_per_usec) {
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user