diff --git a/src/soc/intel/baytrail/baytrail/lpc.h b/src/soc/intel/baytrail/baytrail/lpc.h index 31de3105e2..2f6256cc41 100644 --- a/src/soc/intel/baytrail/baytrail/lpc.h +++ b/src/soc/intel/baytrail/baytrail/lpc.h @@ -47,4 +47,8 @@ enum baytrail_stepping { STEP_C0, }; +/* Registers behind the RCBA_BASE_ADDRESS bar. */ +#define GCS 0x00 +# define BILD (1 << 0) + #endif /* _BAYTRAIL_LPC_H_ */ diff --git a/src/soc/intel/baytrail/southcluster.c b/src/soc/intel/baytrail/southcluster.c index 527ae648bf..046f3bdab8 100644 --- a/src/soc/intel/baytrail/southcluster.c +++ b/src/soc/intel/baytrail/southcluster.c @@ -20,6 +20,7 @@ #include #include +#include #include #include #include @@ -35,6 +36,7 @@ #include #include #include +#include #include "chip.h" static inline void @@ -419,3 +421,30 @@ static const struct pci_driver southcluster __pci_driver = { .vendor = PCI_VENDOR_ID_INTEL, .device = LPC_DEVID, }; + +static void finalize_chipset(void *unused) +{ + const unsigned long bcr = SPI_BASE_ADDRESS + BCR; + const unsigned long gcs = RCBA_BASE_ADDRESS + GCS; + const unsigned long gen_pmcon2 = PMC_BASE_ADDRESS + GEN_PMCON2; + const unsigned long etr = PMC_BASE_ADDRESS + ETR; + + /* Set the lock enable on the BIOS control register. */ + write32(bcr, read32(bcr) | BCR_LE); + + /* Set BIOS lock down bit controlling boot block size and swapping. */ + write32(gcs, read32(gcs) | BILD); + + /* Lock sleep stretching policy and set SMI lock. */ + write32(gen_pmcon2, read32(gen_pmcon2) | SLPSX_STR_POL_LOCK | SMI_LOCK); + + /* Set the CF9 lock. */ + write32(etr, read32(etr) | CF9LOCK); +} + +BOOT_STATE_INIT_ENTRIES(finalize_bscb) = { + BOOT_STATE_INIT_ENTRY(BS_OS_RESUME, BS_ON_ENTRY, + finalize_chipset, NULL), + BOOT_STATE_INIT_ENTRY(BS_PAYLOAD_LOAD, BS_ON_EXIT, + finalize_chipset, NULL), +};