diff --git a/src/soc/intel/apollolake/bootblock/bootblock.c b/src/soc/intel/apollolake/bootblock/bootblock.c index 28a912818f..be10a22736 100644 --- a/src/soc/intel/apollolake/bootblock/bootblock.c +++ b/src/soc/intel/apollolake/bootblock/bootblock.c @@ -41,22 +41,6 @@ static void tpm_enable(void) gpio_configure_pads(tpm_spi_configs, ARRAY_SIZE(tpm_spi_configs)); } -static void enable_pm_timer(void) -{ - /* ACPI PM timer emulation */ - msr_t msr; - /* - * The derived frequency is calculated as follows: - * (CTC_FREQ * msr[63:32]) >> 32 = target frequency. - * Back solve the multiplier so the 3.579545MHz ACPI timer - * frequency is used. - */ - msr.hi = (3579545ULL << 32) / CTC_FREQ; - /* Set PM1 timer IO port and enable*/ - msr.lo = EMULATE_PM_TMR_EN | (ACPI_PMIO_BASE + R_ACPI_PM1_TMR); - wrmsr(MSR_EMULATE_PM_TMR, msr); -} - static void enable_cmos_upper_bank(void) { uint32_t reg = iosf_read(IOSF_RTC_PORT_ID, RTC_CONFIG); @@ -177,7 +161,7 @@ void bootblock_soc_early_init(void) if (IS_ENABLED(CONFIG_TPM_ON_FAST_SPI)) tpm_enable(); - enable_pm_timer(); + enable_pm_timer_emulation(); enable_spibar(); diff --git a/src/soc/intel/apollolake/cpu.c b/src/soc/intel/apollolake/cpu.c index 916d7c5cf4..949736821e 100644 --- a/src/soc/intel/apollolake/cpu.c +++ b/src/soc/intel/apollolake/cpu.c @@ -28,6 +28,7 @@ #include #include #include +#include #include #include @@ -56,6 +57,12 @@ static void soc_core_init(device_t cpu) { /* Set core MSRs */ reg_script_run(core_msr_script); + /* + * Enable ACPI PM timer emulation, which also lets microcode know + * location of ACPI_PMIO_BASE. This also enables other features + * implemented in microcode. + */ + enable_pm_timer_emulation(); } static struct device_operations cpu_dev_ops = { diff --git a/src/soc/intel/apollolake/include/soc/pm.h b/src/soc/intel/apollolake/include/soc/pm.h index dd9e5265a1..16fc1e4248 100644 --- a/src/soc/intel/apollolake/include/soc/pm.h +++ b/src/soc/intel/apollolake/include/soc/pm.h @@ -213,4 +213,6 @@ void global_reset_lock(void); void pch_log_state(void); +void enable_pm_timer_emulation(void); + #endif diff --git a/src/soc/intel/apollolake/pmutil.c b/src/soc/intel/apollolake/pmutil.c index c88e5ae8bf..12a1051246 100644 --- a/src/soc/intel/apollolake/pmutil.c +++ b/src/soc/intel/apollolake/pmutil.c @@ -21,10 +21,12 @@ #include #include #include +#include #include #include #include #include +#include #include #include #include @@ -551,3 +553,19 @@ void pmc_gpe_init(void) /* Set the routes in the GPIO communities as well. */ gpio_route_gpe(dw1, dw2, dw3); } + +void enable_pm_timer_emulation(void) +{ + /* ACPI PM timer emulation */ + msr_t msr; + /* + * The derived frequency is calculated as follows: + * (CTC_FREQ * msr[63:32]) >> 32 = target frequency. + * Back solve the multiplier so the 3.579545MHz ACPI timer + * frequency is used. + */ + msr.hi = (3579545ULL << 32) / CTC_FREQ; + /* Set PM1 timer IO port and enable*/ + msr.lo = EMULATE_PM_TMR_EN | (ACPI_PMIO_BASE + R_ACPI_PM1_TMR); + wrmsr(MSR_EMULATE_PM_TMR, msr); +}