summaryrefslogtreecommitdiff
path: root/src/soc/intel/baytrail/smm.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/soc/intel/baytrail/smm.c')
-rw-r--r--src/soc/intel/baytrail/smm.c39
1 files changed, 39 insertions, 0 deletions
diff --git a/src/soc/intel/baytrail/smm.c b/src/soc/intel/baytrail/smm.c
index 124f93be59..1ba6246596 100644
--- a/src/soc/intel/baytrail/smm.c
+++ b/src/soc/intel/baytrail/smm.c
@@ -27,9 +27,19 @@
#include <cpu/x86/smm.h>
#include <string.h>
+#include <baytrail/iomap.h>
#include <baytrail/pmc.h>
#include <baytrail/smm.h>
+/* Save the gpio route register. The settings are committed from
+ * southcluster_smm_enable_smi(). */
+static uint32_t gpio_route;
+
+void southcluster_smm_save_gpio_route(uint32_t route)
+{
+ gpio_route = route;
+}
+
void southcluster_smm_clear_state(void)
{
uint32_t smi_en;
@@ -53,13 +63,42 @@ void southcluster_smm_clear_state(void)
clear_gpe_status();
}
+static void southcluster_smm_route_gpios(void)
+{
+ const unsigned long gpio_rout = PMC_BASE_ADDRESS + GPIO_ROUT;
+ const unsigned short alt_gpio_smi = ACPI_BASE_ADDRESS + ALT_GPIO_SMI;
+ uint32_t alt_gpio_reg = 0;
+ uint32_t route_reg = gpio_route;
+ int i;
+
+ printk(BIOS_DEBUG, "GPIO_ROUT = %08x\n", route_reg);
+
+ /* Start the routing for the specific gpios. */
+ write32(gpio_rout, route_reg);
+
+ /* Enable SMIs for the gpios that are set to trigger the SMI. */
+ for (i = 0; i < 16; i++) {
+ if ((route_reg & ROUTE_MASK) == ROUTE_SMI) {
+ alt_gpio_reg |= (1 << i);
+ }
+ route_reg >>= 2;
+ }
+ printk(BIOS_DEBUG, "ALT_GPIO_SMI = %08x\n", alt_gpio_reg);
+
+ outl(alt_gpio_reg, alt_gpio_smi);
+}
+
void southcluster_smm_enable_smi(void)
{
+
printk(BIOS_DEBUG, "Enabling SMIs.\n");
/* Configure events */
enable_pm1(PWRBTN_EN | GBL_EN);
disable_gpe(PME_B0_EN);
+ /* Set up the GPIO route. */
+ southcluster_smm_route_gpios();
+
/* Enable SMI generation:
* - on TCO events
* - on APMC writes (io 0xb2)