From 1d14b3e926c15027f9272f1e80b8913fef8cf25d Mon Sep 17 00:00:00 2001 From: Lee Leahy Date: Tue, 12 May 2015 18:23:27 -0700 Subject: soc/intel: Add Skylake SOC support Add the files to support the Skylake SOC. Matches chromium tree at 927026db BRANCH=none BUG=None TEST=Build and run on a Skylake platform Change-Id: I80248f7e47eaf13b52e3c7ff951eb1976edbaa15 Signed-off-by: Lee Leahy Reviewed-on: http://review.coreboot.org/10341 Tested-by: build bot (Jenkins) Reviewed-by: Aaron Durbin --- src/soc/intel/skylake/bootblock/Makefile.inc | 2 +- src/soc/intel/skylake/bootblock/cpu.c | 96 ++++++++++++++++++++------- src/soc/intel/skylake/bootblock/pch.c | 47 ++----------- src/soc/intel/skylake/bootblock/systemagent.c | 5 +- src/soc/intel/skylake/bootblock/timestamp.inc | 6 +- 5 files changed, 83 insertions(+), 73 deletions(-) (limited to 'src/soc/intel/skylake/bootblock') diff --git a/src/soc/intel/skylake/bootblock/Makefile.inc b/src/soc/intel/skylake/bootblock/Makefile.inc index 2ca5a4569f..a31f588f58 100644 --- a/src/soc/intel/skylake/bootblock/Makefile.inc +++ b/src/soc/intel/skylake/bootblock/Makefile.inc @@ -1 +1 @@ -chipset_bootblock_inc += $(src)/soc/intel/broadwell/bootblock/timestamp.inc +chipset_bootblock_inc += $(src)/soc/intel/skylake/bootblock/timestamp.inc diff --git a/src/soc/intel/skylake/bootblock/cpu.c b/src/soc/intel/skylake/bootblock/cpu.c index 3a47d13f0a..d4506e592a 100644 --- a/src/soc/intel/skylake/bootblock/cpu.c +++ b/src/soc/intel/skylake/bootblock/cpu.c @@ -2,6 +2,7 @@ * This file is part of the coreboot project. * * Copyright (C) 2014 Google Inc. + * Copyright (C) 2015 Intel Corporation. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -14,7 +15,7 @@ * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Foundation, Inc. */ #include @@ -22,11 +23,18 @@ #include #include #include +#include #include -#include #include -#include +#include #include +#include +#include + +/* Soft Reset Data Register Bit 12 = MAX Boot Frequency */ +#define SPI_STRAP_MAX_FREQ (1<<12) +/* Soft Reset Data Register Bit 6-11 = Flex Ratio */ +#define FLEX_RATIO_BIT 6 static void set_var_mtrr( unsigned reg, unsigned base, unsigned size, unsigned type) @@ -47,7 +55,6 @@ static void enable_rom_caching(void) msr_t msr; disable_cache(); - /* Why only top 4MiB ? */ set_var_mtrr(1, CACHE_ROM_BASE, CACHE_ROM_SIZE, MTRR_TYPE_WRPROT); enable_cache(); @@ -68,10 +75,59 @@ static void bootblock_mdelay(int ms) } while ((current.lo - start.lo) < target); } +static void set_pch_cpu_strap(u8 flex_ratio) +{ + device_t dev = PCH_DEV_SPI; + uint8_t *spibar = (void *)TEMP_SPI_BAR; + u32 ssl, ssms, soft_reset_data; + u8 pcireg; + + /* Assign Resources to SPI Controller */ + /* Clear BIT 1-2 SPI Command Register */ + pcireg = pci_read_config8(dev, PCI_COMMAND); + pcireg &= ~(PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY); + pci_write_config8(dev, PCI_COMMAND, pcireg); + + /* Program Temporary BAR for SPI */ + pci_write_config32(dev, PCH_SPI_BASE_ADDRESS, TEMP_SPI_BAR); + + /* Enable Bus Master and MMIO Space */ + pcireg = pci_read_config8(dev, PCI_COMMAND); + pcireg |= PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY; + pci_write_config8(dev, PCI_COMMAND, pcireg); + + /* Set Strap Lock Disable*/ + ssl = read32(spibar + SPIBAR_RESET_LOCK); + ssl |= SPIBAR_RESET_LOCK_DISABLE; + write32(spibar + SPIBAR_RESET_LOCK, ssl); + + /* Soft Reset Data Register Bit 12 = MAX Boot Frequency + * Bit 6-11 = Flex Ratio + * Soft Reset Data register located at SPIBAR0 offset 0xF8[0:15]. + */ + soft_reset_data = SPI_STRAP_MAX_FREQ; + soft_reset_data |= (flex_ratio << FLEX_RATIO_BIT); + write32(spibar + SPIBAR_RESET_DATA, soft_reset_data); + + /* Set Strap Mux Select set to '1' */ + ssms = read32(spibar + SPIBAR_RESET_CTRL); + ssms |= SPIBAR_RESET_CTRL_SSMC; + write32(spibar + SPIBAR_RESET_CTRL, ssms); + + /* Set Strap Lock Enable*/ + ssl = read32(spibar + SPIBAR_RESET_LOCK); + ssl |= SPIBAR_RESET_LOCK_ENABLE; + write32(spibar + SPIBAR_RESET_LOCK, ssl); + + /* Disable SPI Controller MMIO space */ + pcireg = pci_read_config8(dev, PCI_COMMAND); + pcireg &= ~(PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY); + pci_write_config8(dev, PCI_COMMAND, pcireg); +} + static void set_flex_ratio_to_tdp_nominal(void) { msr_t flex_ratio, msr; - u32 soft_reset; u8 nominal_ratio; /* Check for Flex Ratio support */ @@ -98,23 +154,14 @@ static void set_flex_ratio_to_tdp_nominal(void) flex_ratio.lo |= FLEX_RATIO_LOCK; wrmsr(MSR_FLEX_RATIO, flex_ratio); - /* Set flex ratio in soft reset data register bits 11:6. - * RCBA region is enabled in southbridge bootblock */ - soft_reset = RCBA32(SOFT_RESET_DATA); - soft_reset &= ~(0x3f << 6); - soft_reset |= (nominal_ratio & 0x3f) << 6; - RCBA32(SOFT_RESET_DATA) = soft_reset; - - /* Set soft reset control to use register value */ - RCBA32_OR(SOFT_RESET_CTRL, 1); + /* Set PCH Soft Reset Data Register with new Flex Ratio */ + set_pch_cpu_strap(nominal_ratio); /* Delay before reset to avoid potential TPM lockout */ bootblock_mdelay(30); - /* Issue warm reset, will be "CPU only" due to soft reset data */ - outb(0x0, 0xcf9); - outb(0x6, 0xcf9); - halt(); + /* Issue soft reset, will be "CPU only" due to soft reset data */ + soft_reset(); } static void check_for_clean_reset(void) @@ -122,14 +169,13 @@ static void check_for_clean_reset(void) msr_t msr; msr = rdmsr(MTRRdefType_MSR); - /* Use the MTRR default type MSR as a proxy for detecting INIT#. + /* + * Use the MTRR default type MSR as a proxy for detecting INIT#. * Reset the system if any known bits are set in that MSR. That is - * an indication of the CPU not being properly reset. */ - if (msr.lo & (MTRRdefTypeEn | MTRRdefTypeFixEn)) { - outb(0x0, 0xcf9); - outb(0x6, 0xcf9); - halt(); - } + * an indication of the CPU not being properly reset. + */ + if (msr.lo & (MTRRdefTypeEn | MTRRdefTypeFixEn)) + soft_reset(); } static void bootblock_cpu_init(void) diff --git a/src/soc/intel/skylake/bootblock/pch.c b/src/soc/intel/skylake/bootblock/pch.c index 2fa722097c..9f256e3a95 100644 --- a/src/soc/intel/skylake/bootblock/pch.c +++ b/src/soc/intel/skylake/bootblock/pch.c @@ -2,6 +2,7 @@ * This file is part of the coreboot project. * * Copyright (C) 2014 Google Inc. + * Copyright (C) 2015 Intel Corporation. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -14,14 +15,12 @@ * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Foundation, Inc. */ - #include #include #include #include -#include #include /* @@ -29,51 +28,13 @@ */ static void enable_spi_prefetch(void) { - u8 reg8 = pci_read_config8(PCH_DEV_LPC, 0xdc); + u8 reg8 = pci_read_config8(PCH_DEV_SPI, 0xdc); reg8 &= ~(3 << 2); reg8 |= (2 << 2); /* Prefetching and Caching Enabled */ - pci_write_config8(PCH_DEV_LPC, 0xdc, reg8); -} - - -static void map_rcba(void) -{ - pci_write_config32(PCH_DEV_LPC, RCBA, RCBA_BASE_ADDRESS | 1); -} - -static void enable_port80_on_lpc(void) -{ - /* Enable port 80 POST on LPC. The chipset does this by default, - * but it doesn't appear to hurt anything. */ - u32 gcs = RCBA32(GCS); - gcs = gcs & ~0x4; - RCBA32(GCS) = gcs; -} - -static void set_spi_speed(void) -{ - u32 fdod; - u8 ssfc; - - /* Observe SPI Descriptor Component Section 0 */ - SPIBAR32(SPIBAR_FDOC) = 0x1000; - - /* Extract the Write/Erase SPI Frequency from descriptor */ - fdod = SPIBAR32(SPIBAR_FDOD); - fdod >>= 24; - fdod &= 7; - - /* Set Software Sequence frequency to match */ - ssfc = SPIBAR8(SPIBAR_SSFC + 2); - ssfc &= ~7; - ssfc |= fdod; - SPIBAR8(SPIBAR_SSFC + 2) = ssfc; + pci_write_config8(PCH_DEV_SPI, 0xdc, reg8); } static void bootblock_southbridge_init(void) { - map_rcba(); enable_spi_prefetch(); - enable_port80_on_lpc(); - set_spi_speed(); } diff --git a/src/soc/intel/skylake/bootblock/systemagent.c b/src/soc/intel/skylake/bootblock/systemagent.c index 15e7fc88b4..6f029f0053 100644 --- a/src/soc/intel/skylake/bootblock/systemagent.c +++ b/src/soc/intel/skylake/bootblock/systemagent.c @@ -2,6 +2,7 @@ * This file is part of the coreboot project. * * Copyright (C) 2014 Google Inc. + * Copyright (C) 2015 Intel Corporation. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -14,7 +15,7 @@ * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Foundation, Inc. */ #include @@ -32,7 +33,7 @@ static void bootblock_northbridge_init(void) * MCFG. This code also assumes that bootblock_northbridge_init() is * the first thing called in the non-asm boot block code. The final * assumption is that no assembly code is using the - * CONFIG_MMCONF_SUPPORT_DEFAULT option to do PCI config accesses. + * CONFIG_MMCONF_SUPPORT_DEFAULT option to do PCI config acceses. * * The PCIEXBAR is assumed to live in the memory mapped IO space under * 4GiB. diff --git a/src/soc/intel/skylake/bootblock/timestamp.inc b/src/soc/intel/skylake/bootblock/timestamp.inc index f565775ed8..e5041326ee 100644 --- a/src/soc/intel/skylake/bootblock/timestamp.inc +++ b/src/soc/intel/skylake/bootblock/timestamp.inc @@ -1,6 +1,8 @@ -/* Store the initial timestamp for booting in mmx registers. This works +/* + * Store the initial timestamp for booting in mmx registers. This works * because the bootblock isn't being compiled with MMX support so mm0 and - * mm1 will be preserved into romstage. */ + * mm1 will be preserved into romstage. + */ .code32 .global stash_timestamp -- cgit v1.2.3