Werner Zeh has uploaded this change for review. ( https://review.coreboot.org/28834
Change subject: mc_apl1: Set up SPI OPCODE menu before locking ......................................................................
mc_apl1: Set up SPI OPCODE menu before locking
In order to enable the OS SPI driver to use the software interface of this controller the OPCODE menu has to be set up properly before locking the controller. This is done on baseboard level so that all variants will get this done as well.
Change-Id: I0bf0619ff0610c00325f03d13b6794aee8a62504 Signed-off-by: Werner Zeh werner.zeh@siemens.com --- M src/mainboard/siemens/mc_apl1/mainboard.c 1 file changed, 55 insertions(+), 0 deletions(-)
git pull ssh://review.coreboot.org:29418/coreboot refs/changes/34/28834/1
diff --git a/src/mainboard/siemens/mc_apl1/mainboard.c b/src/mainboard/siemens/mc_apl1/mainboard.c index b81da5f..58a053e 100644 --- a/src/mainboard/siemens/mc_apl1/mainboard.c +++ b/src/mainboard/siemens/mc_apl1/mainboard.c @@ -36,6 +36,51 @@ #define BIOS_MAILBOX_INTERFACE 0x7084 #define RUN_BUSY_STS (1 << 31)
+/* + * SPI Opcode Menu setup for SPIBAR lock down + * should support most common flash chips. + */ +#define SPI_OPMENU_0 0x01 /* WRSR: Write Status Register */ +#define SPI_OPTYPE_0 0x01 /* Write, no address */ + +#define SPI_OPMENU_1 0x02 /* BYPR: Byte Program */ +#define SPI_OPTYPE_1 0x03 /* Write, address required */ + +#define SPI_OPMENU_2 0x03 /* READ: Read Data */ +#define SPI_OPTYPE_2 0x02 /* Read, address required */ + +#define SPI_OPMENU_3 0x05 /* RDSR: Read Status Register */ +#define SPI_OPTYPE_3 0x00 /* Read, no address */ + +#define SPI_OPMENU_4 0x20 /* SE20: Sector Erase 0x20 */ +#define SPI_OPTYPE_4 0x03 /* Write, address required */ + +#define SPI_OPMENU_5 0x9f /* RDID: Read ID */ +#define SPI_OPTYPE_5 0x00 /* Read, no address */ + +#define SPI_OPMENU_6 0xd8 /* BED8: Block Erase 0xd8 */ +#define SPI_OPTYPE_6 0x03 /* Write, address required */ + +#define SPI_OPMENU_7 0x0b /* FAST: Fast Read */ +#define SPI_OPTYPE_7 0x02 /* Read, address required */ + +#define SPI_OPMENU_UPPER ((SPI_OPMENU_7 << 24) | (SPI_OPMENU_6 << 16) | \ + (SPI_OPMENU_5 << 8) | SPI_OPMENU_4) +#define SPI_OPMENU_LOWER ((SPI_OPMENU_3 << 24) | (SPI_OPMENU_2 << 16) | \ + (SPI_OPMENU_1 << 8) | SPI_OPMENU_0) + +#define SPI_OPTYPE ((SPI_OPTYPE_7 << 14) | (SPI_OPTYPE_6 << 12) | \ + (SPI_OPTYPE_5 << 10) | (SPI_OPTYPE_4 << 8) | \ + (SPI_OPTYPE_3 << 6) | (SPI_OPTYPE_2 << 4) | \ + (SPI_OPTYPE_1 << 2) | (SPI_OPTYPE_0)) + +#define SPI_OPPREFIX ((0x50 << 8) | 0x06) /* EWSR and WREN */ + +#define SPIBAR_OFFSET 0x3800 +#define SPI_REG_PREOP_OPTYPE 0xa4 +#define SPI_REG_OPMENU_L 0xa8 +#define SPI_REG_OPMENU_H 0xac + /** \brief This function can decide if a given MAC address is valid or not. * Currently, addresses filled with 0xff or 0x00 are not valid. * @param mac Buffer to the MAC address to check @@ -197,6 +242,7 @@ { uint16_t cmd = 0; struct device *dev = NULL; + void *spi_base = NULL;
/* Do board specific things */ variant_mainboard_final(); @@ -208,6 +254,15 @@ cmd |= PCI_COMMAND_MASTER; pci_write_config16(dev, PCI_COMMAND, cmd); } + /* Setup SPI OPCODE menu before the controller is locked. */ + dev = PCH_DEV_SPI; + spi_base = (void *)pci_read_config32(dev, PCI_BASE_ADDRESS_0); + if (!spi_base) + return; + write32((spi_base + SPI_REG_PREOP_OPTYPE), + ((SPI_OPTYPE << 16) | SPI_OPPREFIX)); + write32((spi_base + SPI_REG_OPMENU_L), SPI_OPMENU_LOWER); + write32((spi_base + SPI_REG_OPMENU_H), SPI_OPMENU_UPPER); }
/* The following function performs board specific things. */