broadwell: ACPI, romstage, and other updates

broadwell: Add romstage usbdebug support
Reviewed-on: https://chromium-review.googlesource.com/199412
(cherry picked from commit 1050e7d3be6ec1e4fe5aa2df408f4bb6d33a42b5)

broadwell: Add romstage code to configure PCH UART for console
Reviewed-on: https://chromium-review.googlesource.com/199807
(cherry picked from commit ecebda4eb5d6fe58473d25c2898ba1a2eac0f39a)

broadwell: Expand the PCI device convenience macros
Reviewed-on: https://chromium-review.googlesource.com/199891
(cherry picked from commit f8c54c70f136cd2cb8f977bc25661974d7e529ad)

broadwell: Add ramstage driver for ADSP
Reviewed-on: https://chromium-review.googlesource.com/199892
(cherry picked from commit e8e986b0ba52bbfc9923d71009fbd31e749ca43f)

broadwell: Update ACPI devices
Reviewed-on: https://chromium-review.googlesource.com/201080
(cherry picked from commit 2446b35578eb36e0009415bec340059135751549)

broadwell: Reserve DPR region
Reviewed-on: https://chromium-review.googlesource.com/201081
(cherry picked from commit 8ecd9d2096db2bded6f27ef6ee9a9b39ce2dfec6)

broadwell: Remove old pei_data and add cpu function for romstage
Reviewed-on: https://chromium-review.googlesource.com/201690
(cherry picked from commit d206c9cdd69519d502a90bb0595f0e3a7cb50274)

broadwell: Fixes for graphics without executing VBIOS
Reviewed-on: https://chromium-review.googlesource.com/202356
(cherry picked from commit 0c031df1ce92c875e95ddfd3f026f649c342c7fa)

broadwell: Fix compilation failure when loglevel is lowered
Reviewed-on: https://chromium-review.googlesource.com/202357
(cherry picked from commit 708ce78b2bfae5664b1238e17b086c88cac55bdc)

broadwell: Disable GPIO controller interrupt
Reviewed-on: https://chromium-review.googlesource.com/203645
(cherry picked from commit 2d17e98eded5958258ba5c0abf600284d8d03af9)

broadwell: Add support for E0 stepping
Reviewed-on: https://chromium-review.googlesource.com/205160
(cherry picked from commit 802e9d371418cc7a7fc7af131d7e5dda0ae5b273)

broadwell: misc updates for CPU driver
Reviewed-on: https://chromium-review.googlesource.com/205161
(cherry picked from commit ea1d403817ee193648f2c119fd45894e32e57e97)

broadwell: Read power state earlier and store in romstage params
Reviewed-on: https://chromium-review.googlesource.com/208151
(cherry picked from commit b2198d71084ad3c1360a0bfedc46c8dd3825bd0e)

broadwell: Add parameters to pei_data structure
Reviewed-on: https://chromium-review.googlesource.com/208153
(cherry picked from commit 423fbf67e497a907fbc8e12caf2929d4951858af)

broadwell: Move platform report output after power state is read
Reviewed-on: https://chromium-review.googlesource.com/208213
(cherry picked from commit acedf4146bf9377133433046dae1fa9c8bc69d78)

Squashed 15 commits for broadwell support.

Change-Id: I87e320d3d5376b84dd9c146b0b833e5ce53244aa
Signed-off-by: Isaac Christensen <isaac.christensen@se-eng.com>
Reviewed-on: http://review.coreboot.org/6982
Tested-by: build bot (Jenkins)
Reviewed-by: Marc Jones <marc.jones@se-eng.com>
This commit is contained in:
Duncan Laurie 2014-05-05 12:42:35 -05:00 committed by Marc Jones
parent e256295218
commit 61680274c1
34 changed files with 937 additions and 247 deletions

View File

@ -11,6 +11,7 @@ config CPU_SPECIFIC_OPTIONS
select ARCH_ROMSTAGE_X86_32
select ARCH_RAMSTAGE_X86_32
select ALT_CBFS_LOAD_PAYLOAD
select ALWAYS_LOAD_OPROM
select BACKUP_DEFAULT_SMM_REGION
select CACHE_MRC_BIN
select CACHE_MRC_SETTINGS
@ -175,6 +176,23 @@ config MONOTONIC_TIMER_MSR
help
Provide a monotonic timer using the 24MHz MSR counter.
config INTEL_PCH_UART_CONSOLE
bool "Use Serial IO UART for console"
default n
select HAVE_UART_MEMORY_MAPPED
select CONSOLE_SERIAL8250MEM
depends on !CONFIG_DRIVERS_OXFORD_OXPCIE
config INTEL_PCH_UART_CONSOLE_NUMBER
hex "Serial IO UART number to use for console"
default "0x0"
depends on INTEL_PCH_UART_CONSOLE
config TTYS0_BASE
hex
default 0xd6000000
depends on INTEL_PCH_UART_CONSOLE
config EHCI_BAR
hex
default 0xd8000000

View File

@ -10,6 +10,7 @@ subdirs-y += ../../../cpu/intel/microcode
subdirs-y += ../../../cpu/intel/turbo
ramstage-y += acpi.c
ramstage-y += adsp.c
ramstage-y += chip.c
ramstage-y += cpu.c
ramstage-y += elog.c
@ -62,6 +63,12 @@ ramstage-y += ehci.c
ramstage-y += xhci.c
smm-y += xhci.c
ifeq ($(CONFIG_USBDEBUG),y)
ramstage-y += usbdebug.c
romstage-y += usbdebug.c
smm-y += usbdebug.c
endif
INCLUDES += -Isrc/soc/intel/broadwell/
# Run an intermediate step when producing coreboot.rom

View File

@ -604,10 +604,5 @@ unsigned long acpi_madt_irq_overrides(unsigned long current)
irqovr = (void *)current;
current += acpi_create_madt_irqoverride(irqovr, 0, sci, sci, flags);
/* GPIO Controller */
irqovr = (void *)current;
flags = MP_IRQ_TRIGGER_LEVEL | MP_IRQ_POLARITY_HIGH;
current += acpi_create_madt_irqoverride(irqovr, 0, 14, 14, flags);
return current;
}

View File

@ -0,0 +1,63 @@
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2014 Google Inc.
*
* 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
* the Free Software Foundation; version 2 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* 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
*/
Device (ADSP)
{
Method (_HID, 0, Serialized)
{
If (\ISWP ()) {
// WildcatPoint
Return ("INT3438")
}
// LynxPoint-LP
Return ("INT33C8")
}
Name (_UID, 1)
Name (_DDN, "Intel Smart Sound Technology")
Name (RBUF, ResourceTemplate ()
{
Memory32Fixed (ReadWrite, 0x00000000, 0x00100000, BAR0)
Memory32Fixed (ReadWrite, 0x00000000, 0x00001000, BAR1)
Interrupt (ResourceConsumer, Level, ActiveLow, Shared, , , ) {3}
})
Method (_CRS, 0, NotSerialized)
{
// Update BAR0 address and length if set in NVS
If (LNotEqual (\S8B0, Zero)) {
CreateDwordField (^RBUF, ^BAR0._BAS, B8A0)
CreateDwordField (^RBUF, ^BAR1._BAS, B8A1)
Store (\S8B0, B8A0)
Store (\S8B1, B8A1)
}
Return (RBUF)
}
Method (_STA, 0, NotSerialized)
{
If (LEqual (\S8EN, 0)) {
Return (0x0)
} Else {
Return (0xF)
}
}
}

View File

@ -27,6 +27,7 @@ S4EN, 8, // SPI1 Enable
S5EN, 8, // UART0 Enable
S6EN, 8, // UART1 Enable
S7EN, 8, // SDIO Enable
S8EN, 8, // ADSP Enable
/* BAR 0 */
@ -38,6 +39,7 @@ S4B0, 32, // SPI1 BAR0
S5B0, 32, // UART0 BAR0
S6B0, 32, // UART1 BAR0
S7B0, 32, // SDIO BAR0
S8B0, 32, // ADSP BAR0
/* BAR 1 */
@ -49,3 +51,4 @@ S4B1, 32, // SPI1 BAR1
S5B1, 32, // UART0 BAR1
S6B1, 32, // UART1 BAR1
S7B1, 32, // SDIO BAR1
S8B1, 32, // ADSP BAR1

View File

@ -20,8 +20,16 @@
Device (GPIO)
{
// GPIO Controller
Name (_HID, "INT33C7")
Name (_CID, "INT33C7")
Method (_HID)
{
If (\ISWP ()) {
// WildcatPoint
Return ("INT3437")
}
// LynxPoint-LP
Return ("INT33C7")
}
Name (_UID, 1)
Name (RBUF, ResourceTemplate()
@ -39,8 +47,9 @@ Device (GPIO)
, // ResourceSourceIndex
, // ResourceSource
BAR0)
Interrupt (ResourceConsumer,
Level, ActiveHigh, Shared, , , ) {14}
// Disabled due to IRQ storm: http://crosbug.com/p/29548
//Interrupt (ResourceConsumer,
// Level, ActiveHigh, Shared, , , ) {14}
})
Method (_CRS, 0, NotSerialized)

View File

@ -27,10 +27,12 @@ Device (LPCB)
OperationRegion(LPC0, PCI_Config, 0x00, 0x100)
Field (LPC0, AnyAcc, NoLock, Preserve)
{
Offset (0x02),
PDID, 16, // Device ID
Offset (0x40),
PMBS, 16, // PMBASE
Offset (0x48),
GPBS, 16, // GPIOBASE
GPBS, 16, // GPIOBASE
Offset (0x60), // Interrupt Routing Registers
PRTA, 8,
PRTB, 8,

View File

@ -39,11 +39,29 @@ Scope (\)
, 5,
HPTE, 1, // Address Enable
}
/*
* Check PCH type
* Return 1 if PCH is WildcatPoint
* Return 0 if PCH is LynxPoint
*/
Method (ISWP)
{
And (\_SB.PCI0.LPCB.PDID, 0xfff0, Local0)
If (LEqual (Local0, 0x9cc0)) {
Return (1)
} Else {
Return (0)
}
}
}
// High Definition Audio (Azalia) 0:1b.0
#include "hda.asl"
// ADSP/SST 0:13.0
#include "adsp.asl"
// PCI Express Ports 0:1c.x
#include "pcie.asl"

View File

@ -22,6 +22,46 @@
// Serial IO Device BAR0 and BAR1 is 4KB
#define SIO_BAR_LEN 0x1000
// Put SerialIO device in D0 state
// Arg0 - BAR1 of device
// Arg1 - Set if device is in ACPI mode
Method (LPD0, 2, Serialized)
{
// PCI mode devices will be handled by OS PCI bus driver
If (LEqual (Arg1, 0)) {
Return
}
OperationRegion (SPRT, SystemMemory, Add (Arg0, 0x84), 4)
Field (SPRT, DWordAcc, NoLock, Preserve)
{
SPCS, 32
}
And (SPCS, 0xFFFFFFFC, SPCS)
Store (SPCS, Local0) // Read back after writing
}
// Put SerialIO device in D3 state
// Arg0 - BAR1 of device
// Arg1 - Set if device is in ACPI mode
Method (LPD3, 2, Serialized)
{
// PCI mode devices will be handled by OS PCI bus driver
If (LEqual (Arg1, 0)) {
Return
}
OperationRegion (SPRT, SystemMemory, Add (Arg0, 0x84), 4)
Field (SPRT, DWordAcc, NoLock, Preserve)
{
SPCS, 32
}
Or (SPCS, 0x3, SPCS)
Store (SPCS, Local0) // Read back after writing
}
// Serial IO Resource Consumption for BAR1
Device (SIOR)
{
@ -152,11 +192,22 @@ Device (SDMA)
Device (I2C0)
{
// Serial IO I2C0 Controller
Name (_HID, "INT33C2")
Name (_CID, "INT33C2")
Method (_HID)
{
If (\ISWP ()) {
// WildcatPoint
Return ("INT3432")
}
// LynxPoint-LP
Return ("INT33C2")
}
Name (_UID, 1)
Name (_ADR, 0x00150001)
Name (SSCN, Package () { 432, 507, 9 })
Name (FMCN, Package () { 72, 160, 9 })
// BAR0 is assigned during PCI enumeration and saved into NVS
Name (RBUF, ResourceTemplate ()
{
@ -167,9 +218,8 @@ Device (I2C0)
// DMA channels are only used if Serial IO DMA controller is enabled
Name (DBUF, ResourceTemplate ()
{
// TODO: Need to update IASL to support FixedDMA
//FixedDMA (0x18, 4, Width32Bit, DMA1) // Tx
//FixedDMA (0x19, 5, Width32Bit, DMA2) // Rx
FixedDMA (0x18, 4, Width32Bit, DMA1) // Tx
FixedDMA (0x19, 5, Width32Bit, DMA2) // Rx
})
Method (_CRS, 0, NotSerialized)
@ -198,16 +248,37 @@ Device (I2C0)
Return (0xF)
}
}
Method (_PS0, 0, Serialized)
{
^^LPD0 (\S1B1, \S1EN)
}
Method (_PS3, 0, Serialized)
{
^^LPD3 (\S1B1, \S1EN)
}
}
Device (I2C1)
{
// Serial IO I2C1 Controller
Name (_HID, "INT33C3")
Name (_CID, "INT33C3")
Method (_HID)
{
If (\ISWP ()) {
// WildcatPoint
Return ("INT3433")
}
// LynxPoint-LP
Return ("INT33C3")
}
Name (_UID, 1)
Name (_ADR, 0x00150002)
Name (SSCN, Package () { 432, 507, 9 })
Name (FMCN, Package () { 72, 160, 9 })
// BAR0 is assigned during PCI enumeration and saved into NVS
Name (RBUF, ResourceTemplate ()
{
@ -218,9 +289,8 @@ Device (I2C1)
// DMA channels are only used if Serial IO DMA controller is enabled
Name (DBUF, ResourceTemplate ()
{
// TODO: Need to update IASL to support FixedDMA
//FixedDMA (0x1A, 6, Width32Bit, DMA1) // Tx
//FixedDMA (0x1B, 7, Width32Bit, DMA2) // Rx
FixedDMA (0x1A, 6, Width32Bit, DMA1) // Tx
FixedDMA (0x1B, 7, Width32Bit, DMA2) // Rx
})
Method (_CRS, 0, NotSerialized)
@ -249,13 +319,31 @@ Device (I2C1)
Return (0xF)
}
}
Method (_PS0, 0, Serialized)
{
^^LPD0 (\S2B1, \S2EN)
}
Method (_PS3, 0, Serialized)
{
^^LPD3 (\S2B1, \S2EN)
}
}
Device (SPI0)
{
// Serial IO SPI0 Controller
Name (_HID, "INT33C0")
Name (_CID, "INT33C0")
Method (_HID)
{
If (\ISWP ()) {
// WildcatPoint
Return ("INT3430")
}
// LynxPoint-LP
Return ("INT33C0")
}
Name (_UID, 1)
Name (_ADR, 0x00150003)
@ -287,13 +375,31 @@ Device (SPI0)
Return (0xF)
}
}
Method (_PS0, 0, Serialized)
{
^^LPD0 (\S3B1, \S3EN)
}
Method (_PS3, 0, Serialized)
{
^^LPD3 (\S3B1, \S3EN)
}
}
Device (SPI1)
{
// Serial IO SPI1 Controller
Name (_HID, "INT33C1")
Name (_CID, "INT33C1")
Method (_HID)
{
If (\ISWP ()) {
// WildcatPoint
Return ("INT3431")
}
// LynxPoint-LP
Return ("INT33C1")
}
Name (_UID, 1)
Name (_ADR, 0x00150004)
@ -307,9 +413,8 @@ Device (SPI1)
// DMA channels are only used if Serial IO DMA controller is enabled
Name (DBUF, ResourceTemplate ()
{
// TODO: Need to update IASL to support FixedDMA
//FixedDMA (0x10, 0, Width32Bit, DMA1) // Tx
//FixedDMA (0x11, 1, Width32Bit, DMA2) // Rx
FixedDMA (0x10, 0, Width32Bit, DMA1) // Tx
FixedDMA (0x11, 1, Width32Bit, DMA2) // Rx
})
Method (_CRS, 0, NotSerialized)
@ -338,13 +443,31 @@ Device (SPI1)
Return (0xF)
}
}
Method (_PS0, 0, Serialized)
{
^^LPD0 (\S4B1, \S4EN)
}
Method (_PS3, 0, Serialized)
{
^^LPD3 (\S4B1, \S4EN)
}
}
Device (UAR0)
{
// Serial IO UART0 Controller
Name (_HID, "INT33C4")
Name (_CID, "INT33C4")
Method (_HID)
{
If (\ISWP ()) {
// WildcatPoint
Return ("INT3434")
}
// LynxPoint-LP
Return ("INT33C4")
}
Name (_UID, 1)
Name (_ADR, 0x00150005)
@ -358,9 +481,8 @@ Device (UAR0)
// DMA channels are only used if Serial IO DMA controller is enabled
Name (DBUF, ResourceTemplate ()
{
// TODO: Need to update IASL to support FixedDMA
//FixedDMA (0x16, 2, Width32Bit, DMA1) // Tx
//FixedDMA (0x17, 3, Width32Bit, DMA2) // Rx
FixedDMA (0x16, 2, Width32Bit, DMA1) // Tx
FixedDMA (0x17, 3, Width32Bit, DMA2) // Rx
})
Method (_CRS, 0, NotSerialized)
@ -389,13 +511,31 @@ Device (UAR0)
Return (0xF)
}
}
Method (_PS0, 0, Serialized)
{
^^LPD0 (\S5B1, \S5EN)
}
Method (_PS3, 0, Serialized)
{
^^LPD3 (\S5B1, \S5EN)
}
}
Device (UAR1)
{
// Serial IO UART1 Controller
Name (_HID, "INT33C5")
Name (_CID, "INT33C5")
Method (_HID)
{
If (\ISWP ()) {
// WildcatPoint
Return ("INT3435")
}
// LynxPoint-LP
Return ("INT33C5")
}
Name (_UID, 1)
Name (_ADR, 0x00150006)
@ -427,12 +567,31 @@ Device (UAR1)
Return (0xF)
}
}
Method (_PS0, 0, Serialized)
{
^^LPD0 (\S6B1, \S6EN)
}
Method (_PS3, 0, Serialized)
{
^^LPD3 (\S6B1, \S6EN)
}
}
Device (SDIO)
{
// Serial IO SDIO Controller
Name (_HID, "INT33C6")
Method (_HID)
{
If (\ISWP ()) {
// WildcatPoint
Return ("INT3436")
}
// LynxPoint-LP
Return ("INT33C6")
}
Name (_CID, "PNP0D40")
Name (_UID, 1)
Name (_ADR, 0x00170000)

View File

@ -0,0 +1,152 @@
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2014 Google Inc.
*
* 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
* the Free Software Foundation; version 2 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* 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
*/
#include <cbmem.h>
#include <console/console.h>
#include <device/device.h>
#include <device/pci.h>
#include <device/pci_ids.h>
#include <device/pci_ops.h>
#include <arch/io.h>
#include <delay.h>
#include <broadwell/adsp.h>
#include <broadwell/device_nvs.h>
#include <broadwell/iobp.h>
#include <broadwell/nvs.h>
#include <broadwell/pch.h>
#include <broadwell/ramstage.h>
#include <broadwell/rcba.h>
#include <chip.h>
static void adsp_init(struct device *dev)
{
config_t *config = dev->chip_info;
struct resource *bar0, *bar1;
u32 tmp32;
/* Ensure memory and bus master are enabled */
tmp32 = pci_read_config32(dev, PCI_COMMAND);
tmp32 |= PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY;
pci_write_config32(dev, PCI_COMMAND, tmp32);
/* Find BAR0 and BAR1 */
bar0 = find_resource(dev, PCI_BASE_ADDRESS_0);
if (!bar0)
return;
bar1 = find_resource(dev, PCI_BASE_ADDRESS_1);
if (!bar1)
return;
/*
* Set LTR value in DSP shim LTR control register to 3ms
* SNOOP_REQ[13]=1b SNOOP_SCALE[12:10]=100b (1ms) SNOOP_VAL[9:0]=3h
*/
tmp32 = pch_is_wpt() ? ADSP_SHIM_BASE_WPT : ADSP_SHIM_BASE_LPT;
write32(bar0->base + tmp32 + ADSP_SHIM_LTRC, ADSP_SHIM_LTRC_VALUE);
/* Program VDRTCTL2 D19:F0:A8[31:0] = 0x00000fff */
pci_write_config32(dev, ADSP_PCI_VDRTCTL2, ADSP_VDRTCTL2_VALUE);
/* Program ADSP IOBP VDLDAT1 to 0x040100 */
pch_iobp_write(ADSP_IOBP_VDLDAT1, ADSP_VDLDAT1_VALUE);
/* Set D3 Power Gating Enable in D19:F0:A0 based on PCH type */
tmp32 = pci_read_config32(dev, ADSP_PCI_VDRTCTL0);
if (pch_is_wpt()) {
tmp32 &= ~ADSP_VDRTCTL0_D3PGD_WPT;
tmp32 &= ~ADSP_VDRTCTL0_D3SRAMPGD_WPT;
} else {
tmp32 &= ~ADSP_VDRTCTL0_D3PGD_LPT;
tmp32 &= ~ADSP_VDRTCTL0_D3SRAMPGD_LPT;
}
pci_write_config32(dev, ADSP_PCI_VDRTCTL0, tmp32);
/* Set PSF Snoop to SA, RCBA+0x3350[10]=1b */
RCBA32_OR(0x3350, (1 << 10));
/* Set DSP IOBP PMCTL 0x1e0=0x3f */
pch_iobp_write(ADSP_IOBP_PMCTL, ADSP_PMCTL_VALUE);
if (config->sio_acpi_mode) {
/* Configure for ACPI mode */
global_nvs_t *gnvs;
printk(BIOS_INFO, "ADSP: Enable ACPI Mode IRQ3\n");
/* Find ACPI NVS to update BARs */
gnvs = (global_nvs_t *)cbmem_find(CBMEM_ID_ACPI_GNVS);
if (!gnvs) {
printk(BIOS_ERR, "Unable to locate Global NVS\n");
return;
}
/* Save BAR0 and BAR1 to ACPI NVS */
gnvs->dev.bar0[SIO_NVS_ADSP] = (u32)bar0->base;
gnvs->dev.bar1[SIO_NVS_ADSP] = (u32)bar1->base;
gnvs->dev.enable[SIO_NVS_ADSP] = 1;
/* Set PCI Config Disable Bit */
pch_iobp_update(ADSP_IOBP_PCICFGCTL, ~0, ADSP_PCICFGCTL_PCICD);
/* Set interrupt de-assert/assert opcode override to IRQ3 */
pch_iobp_write(ADSP_IOBP_VDLDAT2, ADSP_IOBP_ACPI_IRQ3);
/* Enable IRQ3 in RCBA */
RCBA32_OR(ACPIIRQEN, ADSP_ACPI_IRQEN);
/* Set ACPI Interrupt Enable Bit */
pch_iobp_update(ADSP_IOBP_PCICFGCTL, ~ADSP_PCICFGCTL_SPCBAD,
ADSP_PCICFGCTL_ACPIIE);
/* Put ADSP in D3hot */
tmp32 = read32(bar1->base + PCH_PCS);
tmp32 |= PCH_PCS_PS_D3HOT;
write32(bar1->base + PCH_PCS, tmp32);
} else {
printk(BIOS_INFO, "ADSP: Enable PCI Mode IRQ23\n");
/* Configure for PCI mode */
pci_write_config32(dev, PCI_INTERRUPT_LINE, ADSP_PCI_IRQ);
/* Clear ACPI Interrupt Enable Bit */
pch_iobp_update(ADSP_IOBP_PCICFGCTL,
~(ADSP_PCICFGCTL_SPCBAD | ADSP_PCICFGCTL_ACPIIE), 0);
}
}
static struct device_operations adsp_ops = {
.read_resources = &pci_dev_read_resources,
.set_resources = &pci_dev_set_resources,
.enable_resources = &pci_dev_enable_resources,
.init = &adsp_init,
.ops_pci = &broadwell_pci_ops,
};
static const unsigned short pci_device_ids[] = {
0x9c36, /* LynxPoint */
0x9cb6, /* WildcatPoint */
0
};
static const struct pci_driver pch_adsp __pci_driver = {
.ops = &adsp_ops,
.vendor = PCI_VENDOR_ID_INTEL,
.devices = pci_device_ids,
};

View File

@ -0,0 +1,56 @@
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2014 Google Inc.
*
* 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
* the Free Software Foundation; version 2 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* 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
*/
#ifndef _BROADWELL_ADSP_H_
#define _BROADWELL_ADSP_H_
#define ADSP_PCI_IRQ 23
#define ADSP_ACPI_IRQ 3
#define ADSP_ACPI_IRQEN (1 << 3)
#define ADSP_SHIM_BASE_LPT 0xe7000
#define ADSP_SHIM_BASE_WPT 0xfb000
#define ADSP_SHIM_LTRC 0xe0
#define ADSP_SHIM_LTRC_VALUE 0x3003
#define ADSP_SHIM_IMC 0x28
#define ADSP_SHIM_IPCD 0x40
#define ADSP_PCI_VDRTCTL0 0xa0
#define ADSP_VDRTCTL0_D3PGD_LPT (1 << 1)
#define ADSP_VDRTCTL0_D3PGD_WPT (1 << 0)
#define ADSP_VDRTCTL0_D3SRAMPGD_LPT (1 << 2)
#define ADSP_VDRTCTL0_D3SRAMPGD_WPT (1 << 1)
#define ADSP_PCI_VDRTCTL1 0xa4
#define ADSP_PCI_VDRTCTL2 0xa8
#define ADSP_VDRTCTL2_VALUE 0x00000fff
#define ADSP_IOBP_VDLDAT1 0xd7000624
#define ADSP_VDLDAT1_VALUE 0x00040100
#define ADSP_IOBP_VDLDAT2 0xd7000628
#define ADSP_IOBP_ACPI_IRQ3 0xd9d8
#define ADSP_IOBP_ACPI_IRQ3I 0xd8d9
#define ADSP_IOBP_ACPI_IRQ4 0xdbda
#define ADSP_IOBP_PMCTL 0xd70001e0
#define ADSP_PMCTL_VALUE 0x3f
#define ADSP_IOBP_PCICFGCTL 0xd7000500
#define ADSP_PCICFGCTL_PCICD (1 << 0)
#define ADSP_PCICFGCTL_ACPIIE (1 << 1)
#define ADSP_PCICFGCTL_SPCBAD (1 << 7)
#endif

View File

@ -36,6 +36,7 @@
#define CPUID_HASWELL_HALO 0x40661
#define CPUID_BROADWELL_C0 0x306d2
#define CPUID_BROADWELL_D0 0x306d3
#define CPUID_BROADWELL_E0 0x306d4
/* CPU bus clock is fixed at 100MHz */
#define CPU_BCLK 100

View File

@ -33,11 +33,12 @@
#define SIO_NVS_UART0 5
#define SIO_NVS_UART1 6
#define SIO_NVS_SDIO 7
#define SIO_NVS_ADSP 8
typedef struct {
u8 enable[8];
u32 bar0[8];
u32 bar1[8];
u8 enable[9];
u32 bar0[9];
u32 bar1[9];
} __attribute__((packed)) device_nvs_t;
#endif

View File

@ -20,6 +20,9 @@
#ifndef _BROADWELL_PCI_DEVS_H_
#define _BROADWELL_PCI_DEVS_H_
#define _SA_DEVFN(slot) PCI_DEVFN(SA_DEV_SLOT_ ## slot, 0)
#define _PCH_DEVFN(slot,func) PCI_DEVFN(PCH_DEV_SLOT_ ## slot, func)
#if defined(__PRE_RAM__) || defined(__SMM__) || defined(__ROMCC__)
#include <arch/io.h>
#define _SA_DEV(slot) PCI_DEV(0, SA_DEV_SLOT_ ## slot, 0)
@ -27,43 +30,90 @@
#else
#include <device/device.h>
#include <device/pci_def.h>
#define _SA_DEV(slot) dev_find_slot(0, \
PCI_DEVFN(SA_DEV_SLOT_ ## slot, 0))
#define _PCH_DEV(slot,func) dev_find_slot(0, \
PCI_DEVFN(PCH_DEV_SLOT_ ## slot, func))
#define _SA_DEV(slot) dev_find_slot(0, _SA_DEVFN(slot))
#define _PCH_DEV(slot,func) dev_find_slot(0, _PCH_DEVFN(slot, func))
#endif
/* System Agent Devices */
#define SA_DEV_SLOT_ROOT 0x00
#define SA_DEV_SLOT_IGD 0x02
#define SA_DEV_SLOT_MINIHD 0x03
#define SA_DEVFN_ROOT _SA_DEVFN(ROOT)
#define SA_DEV_ROOT _SA_DEV(ROOT)
#define SA_DEV_ROOT _SA_DEV(ROOT)
#define SA_DEV_IGD _SA_DEV(IGD)
#define SA_DEV_MINIHD _SA_DEV(MINIHD)
#define SA_DEV_SLOT_IGD 0x02
#define SA_DEVFN_IGD _SA_DEVFN(IGD)
#define SA_DEV_IGD _SA_DEV(IGD)
#define SA_DEV_SLOT_MINIHD 0x03
#define SA_DEVFN_MINIHD _SA_DEVFN(MINIHD)
#define SA_DEV_MINIHD _SA_DEV(MINIHD)
/* PCH Devices */
#define PCH_DEV_SLOT_XHCI 0x14
#define PCH_DEV_SLOT_SIO 0x15
#define PCH_DEV_SLOT_ME 0x16
#define PCH_DEV_SLOT_HDA 0x1b
#define PCH_DEV_SLOT_PCIE 0x1c
#define PCH_DEV_SLOT_EHCI 0x1d
#define PCH_DEV_SLOT_LPC 0x1f
#define PCH_DEV_SLOT_ADSP 0x13
#define PCH_DEVFN_ADSP _PCH_DEVFN(ADSP, 0)
#define PCH_DEV_ADSP _PCH_DEV(ADSP, 0)
#define PCH_DEV_XHCI _PCH_DEV(XHCI, 0)
#define PCH_DEV_UART0 _PCH_DEV(UART0, 0)
#define PCH_DEV_UART1 _PCH_DEV(UART1, 0)
#define PCH_DEV_ME _PCH_DEV(ME, 0)
#define PCH_DEV_HDA _PCH_DEV(HDA, 0)
#define PCH_DEV_EHCI _PCH_DEV(EHCI, 0)
#define PCH_DEV_LPC _PCH_DEV(LPC, 0)
#define PCH_DEV_IDE _PCH_DEV(LPC, 1)
#define PCH_DEV_SATA _PCH_DEV(LPC, 2)
#define PCH_DEV_SMBUS _PCH_DEV(LPC, 3)
#define PCH_DEV_SATA2 _PCH_DEV(LPC, 5)
#define PCH_DEV_THERMAL _PCH_DEV(LPC, 6)
#define PCH_DEV_SLOT_XHCI 0x14
#define PCH_DEVFN_XHCI _PCH_DEVFN(XHCI, 0)
#define PCH_DEV_XHCI _PCH_DEV(XHCI, 0)
#define PCH_DEV_SLOT_SIO 0x15
#define PCH_DEV_SDMA _PCH_DEV(SIO, 0)
#define PCH_DEV_I2C0 _PCH_DEV(SIO, 1)
#define PCH_DEV_I2C1 _PCH_DEV(SIO, 2)
#define PCH_DEV_SPI0 _PCH_DEV(SIO, 3)
#define PCH_DEV_SPI1 _PCH_DEV(SIO, 4)
#define PCH_DEV_UART0 _PCH_DEV(SIO, 5)
#define PCH_DEV_UART1 _PCH_DEV(SIO, 6)
#define PCH_DEVFN_SDMA _PCH_DEVFN(SIO, 0)
#define PCH_DEVFN_I2C0 _PCH_DEVFN(SIO, 1)
#define PCH_DEVFN_I2C1 _PCH_DEVFN(SIO, 2)
#define PCH_DEVFN_SPI0 _PCH_DEVFN(SIO, 3)
#define PCH_DEVFN_SPI1 _PCH_DEVFN(SIO, 4)
#define PCH_DEVFN_UART0 _PCH_DEVFN(SIO, 5)
#define PCH_DEVFN_UART1 _PCH_DEVFN(SIO, 6)
#define PCH_DEV_SLOT_ME 0x16
#define PCH_DEVFN_ME _PCH_DEVFN(ME, 0)
#define PCH_DEVFN_ME_2 _PCH_DEVFN(ME, 1)
#define PCH_DEVFN_ME_IDER _PCH_DEVFN(ME, 2)
#define PCH_DEVFN_ME_KT _PCH_DEVFN(ME, 3)
#define PCH_DEV_ME _PCH_DEV(ME, 0)
#define PCH_DEV_ME_2 _PCH_DEV(ME, 1)
#define PCH_DEV_ME_IDER _PCH_DEV(ME, 2)
#define PCH_DEV_ME_KT _PCH_DEV(ME, 3)
#define PCH_DEV_SLOT_SDIO 0x17
#define PCH_DEVFN_SDIO _PCH_DEVFN(SDIO, 0)
#define PCH_DEV_SDIO _PCH_DEV(SDIO, 0)
#define PCH_DEV_SLOT_GBE 0x19
#define PCH_DEVFN_GBE _PCH_DEVFN(GBE, 0)
#define PCH_DEV_GBE _PCH_DEV(GBE, 0)
#define PCH_DEV_SLOT_HDA 0x1b
#define PCH_DEVFN_HDA _PCH_DEVFN(HDA, 0)
#define PCH_DEV_HDA _PCH_DEV(HDA, 0)
#define PCH_DEV_SLOT_PCIE 0x1c
#define PCH_DEV_SLOT_EHCI 0x1d
#define PCH_DEVFN_EHCI _PCH_DEVFN(EHCI, 0)
#define PCH_DEV_EHCI _PCH_DEV(EHCI, 0)
#define PCH_DEV_SLOT_LPC 0x1f
#define PCH_DEVFN_LPC _PCH_DEVFN(LPC, 0)
#define PCH_DEVFN_IDE _PCH_DEVFN(LPC, 1)
#define PCH_DEVFN_SATA _PCH_DEVFN(LPC, 2)
#define PCH_DEVFN_SMBUS _PCH_DEVFN(LPC, 3)
#define PCH_DEVFN_SATA2 _PCH_DEVFN(LPC, 5)
#define PCH_DEVFN_THERMAL _PCH_DEVFN(LPC, 6)
#define PCH_DEV_LPC _PCH_DEV(LPC, 0)
#define PCH_DEV_IDE _PCH_DEV(LPC, 1)
#define PCH_DEV_SATA _PCH_DEV(LPC, 2)
#define PCH_DEV_SMBUS _PCH_DEV(LPC, 3)
#define PCH_DEV_SATA2 _PCH_DEV(LPC, 5)
#define PCH_DEV_THERMAL _PCH_DEV(LPC, 6)
#endif

View File

@ -31,7 +31,7 @@
#include <types.h>
#define PEI_VERSION 20
#define PEI_VERSION 21
#define ABI_X86 __attribute__((regparm(0)))
@ -122,6 +122,8 @@ struct pei_data
int dq_pins_interleaved;
/* Limit DDR3 frequency */
int max_ddr3_freq;
/* Disable self refresh */
int disable_self_refresh;
/* USB port configuration */
struct usb2_port_setting usb2_ports[MAX_USB2_PORTS];
@ -167,6 +169,9 @@ struct pei_data
const void *saved_data;
int saved_data_size;
/* Disable use of saved data (can be set by mainboard) */
int disable_saved_data;
/* Data from MRC that should be saved to flash */
void *data_to_save;
int data_to_save_size;

View File

@ -29,9 +29,12 @@ struct romstage_timestamps {
int count;
};
struct chipset_power_state;
struct pei_data;
struct romstage_params {
struct romstage_timestamps ts;
unsigned long bist;
struct chipset_power_state *power_state;
struct pei_data *pei_data;
};
@ -52,6 +55,7 @@ void set_max_freq(void);
void systemagent_early_init(void);
void pch_early_init(void);
void pch_uart_init(void);
void intel_early_me_status(void);
void enable_smbus(void);

View File

@ -52,6 +52,10 @@
#define DEVEN_D1F1EN (1 << 2)
#define DEVEN_D1F2EN (1 << 1)
#define DEVEN_D0EN (1 << 0)
#define DPR 0x5c
#define DPR_EPM (1 << 2)
#define DPR_PRS (1 << 1)
#define DPR_SIZE_MASK 0xff0
#define PAM0 0x80
#define PAM1 0x81

View File

@ -218,7 +218,7 @@ static void initialize_vr_config(void)
msr.hi &= 0xc0000000;
msr.hi |= (0x01 << (52 - 32)); /* PSI3 threshold - 1A. */
msr.hi |= (0x05 << (42 - 32)); /* PSI2 threshold - 5A. */
msr.hi |= (0x0f << (32 - 32)); /* PSI1 threshold - 15A. */
msr.hi |= (0x14 << (32 - 32)); /* PSI1 threshold - 20A. */
msr.hi |= (1 << (62 - 32)); /* Enable PSI4 */
/* Leave the max instantaneous current limit (12:0) to default. */
wrmsr(MSR_VR_CURRENT_CONFIG, msr);
@ -387,6 +387,7 @@ static void configure_c_states(void)
msr_t msr;
msr = rdmsr(MSR_PMG_CST_CONFIG_CONTROL);
msr.lo |= (1 << 31); // Timed MWAIT Enable
msr.lo |= (1 << 30); // Package c-state Undemotion Enable
msr.lo |= (1 << 29); // Package c-state Demotion Enable
msr.lo |= (1 << 28); // C1 Auto Undemotion Enable
@ -661,6 +662,7 @@ static struct cpu_device_id cpu_table[] = {
{ X86_VENDOR_INTEL, CPUID_HASWELL_ULT },
{ X86_VENDOR_INTEL, CPUID_BROADWELL_C0 },
{ X86_VENDOR_INTEL, CPUID_BROADWELL_D0 },
{ X86_VENDOR_INTEL, CPUID_BROADWELL_E0 },
{ 0, 0 },
};

View File

@ -26,6 +26,7 @@
#include <usbdebug.h>
#include <arch/io.h>
#include <broadwell/ehci.h>
#include <broadwell/pch.h>
static void usb_ehci_set_subsystem(device_t dev, unsigned vendor, unsigned device)
{
@ -70,6 +71,14 @@ static void usb_ehci_set_resources(struct device *dev)
#endif
}
static void ehci_enable(struct device *dev)
{
if (CONFIG_USBDEBUG)
dev->enabled = 1;
else
pch_disable_devfn(dev);
}
static struct pci_operations ehci_ops_pci = {
.set_subsystem = &usb_ehci_set_subsystem,
};
@ -79,6 +88,7 @@ static struct device_operations usb_ehci_ops = {
.set_resources = &usb_ehci_set_resources,
.enable_resources = &pci_dev_enable_resources,
.ops_pci = &ehci_ops_pci,
.enable = &ehci_enable,
};
static const unsigned short pci_device_ids[] = {

View File

@ -27,6 +27,7 @@
#include <arch/io.h>
#include <delay.h>
#include <soc/intel/common/hda_verb.h>
#include <broadwell/pch.h>
#include <broadwell/ramstage.h>
#include <broadwell/rcba.h>
@ -134,11 +135,35 @@ static void hda_init(struct device *dev)
}
}
static void hda_enable(struct device *dev)
{
u32 reg32;
if (!dev->enabled) {
/* Route I/O buffers to ADSP function */
reg32 = pci_read_config32(dev, 0x42);
reg32 |= (1 << 7) | (1 << 6);
pci_write_config32(dev, 0x42, reg32);
printk(BIOS_INFO, "HDA disabled, I/O buffers routed to ADSP\n");
/* Ensure memory, io, and bus master are all disabled */
reg32 = pci_read_config32(dev, PCI_COMMAND);
reg32 &= ~(PCI_COMMAND_MASTER |
PCI_COMMAND_MEMORY | PCI_COMMAND_IO);
pci_write_config32(dev, PCI_COMMAND, reg32);
/* Disable this device */
pch_disable_devfn(dev);
}
}
static struct device_operations hda_ops = {
.read_resources = &pci_dev_read_resources,
.set_resources = &pci_dev_set_resources,
.enable_resources = &pci_dev_enable_resources,
.init = &hda_init,
.enable = &hda_enable,
.ops_pci = &broadwell_pci_ops,
};

View File

@ -472,6 +472,7 @@ static void igd_init(struct device *dev)
{
int is_broadwell = !!(cpu_family_model() == BROADWELL_FAMILY_ULT);
u32 rp1_gfx_freq;
extern int oprom_is_loaded;
/* IGD needs to be Bus Master */
u32 reg32 = pci_read_config32(dev, PCI_COMMAND);
@ -510,6 +511,18 @@ static void igd_init(struct device *dev)
igd_cdclk_init_haswell(dev);
reg_script_run_on_dev(dev, haswell_late_init_script);
}
if (!oprom_is_loaded) {
/*
* Enable DDI-A if the Option ROM did not execute:
*
* bit 0: Display detected (RO)
* bit 4: DDI A supports 4 lanes and DDI E is not used
* bit 7: DDI buffer is idle
*/
gtt_write(DDI_BUF_CTL_A, DDI_BUF_IS_IDLE | DDI_A_4_LANES |
DDI_INIT_DISPLAY_DETECTED);
}
}
static void igd_read_resources(struct device *dev)

View File

@ -26,6 +26,8 @@
#include <broadwell/pci_devs.h>
#include <broadwell/me.h>
#if (CONFIG_DEFAULT_CONSOLE_LOGLEVEL >= BIOS_DEBUG)
/* HFS1[3:0] Current Working State Values */
static const char *me_cws_values[] = {
[ME_HFS_CWS_RESET] = "Reset",
@ -276,3 +278,4 @@ void intel_me_status(void)
}
printk(BIOS_DEBUG, "\n");
}
#endif

View File

@ -26,11 +26,18 @@
static unsigned long get_top_of_ram(void)
{
/*
* Base of TSEG is top of usable DRAM below 4GiB. The register has
* 1 MiB alignement.
* Base of DPR is top of usable DRAM below 4GiB. The register has
* 1 MiB alignment and reports the TOP of the range, the base
* must be calculated from the size in MiB in bits 11:4.
*/
u32 tom = pci_read_config32(SA_DEV_ROOT, TSEG);
return (unsigned long) tom & ~((1 << 20) - 1);
u32 dpr = pci_read_config32(SA_DEV_ROOT, DPR);
u32 tom = dpr & ~((1 << 20) - 1);
/* Subtract DMA Protected Range size if enabled */
if (dpr & DPR_EPM)
tom -= (dpr & DPR_SIZE_MASK) << 16;
return (unsigned long)tom;
}
void *cbmem_top(void)

View File

@ -92,91 +92,88 @@ static void pch_enable_d3hot(device_t dev)
void pch_disable_devfn(device_t dev)
{
switch (dev->path.pci.devfn) {
case PCI_DEVFN(19, 0): /* Audio DSP */
case PCH_DEVFN_ADSP: /* Audio DSP */
RCBA32_OR(FD, PCH_DISABLE_ADSPD);
break;
case PCI_DEVFN(20, 0): /* XHCI */
case PCH_DEVFN_XHCI: /* XHCI */
RCBA32_OR(FD, PCH_DISABLE_XHCI);
break;
case PCI_DEVFN(21, 0): /* DMA */
case PCH_DEVFN_SDMA: /* DMA */
pch_enable_d3hot(dev);
pch_iobp_update(SIO_IOBP_FUNCDIS0, ~0UL, SIO_IOBP_FUNCDIS_DIS);
break;
case PCI_DEVFN(21, 1): /* I2C0 */
case PCH_DEVFN_I2C0: /* I2C0 */
pch_enable_d3hot(dev);
pch_iobp_update(SIO_IOBP_FUNCDIS1, ~0UL, SIO_IOBP_FUNCDIS_DIS);
break;
case PCI_DEVFN(21, 2): /* I2C1 */
case PCH_DEVFN_I2C1: /* I2C1 */
pch_enable_d3hot(dev);
pch_iobp_update(SIO_IOBP_FUNCDIS2, ~0UL, SIO_IOBP_FUNCDIS_DIS);
break;
case PCI_DEVFN(21, 3): /* SPI0 */
case PCH_DEVFN_SPI0: /* SPI0 */
pch_enable_d3hot(dev);
pch_iobp_update(SIO_IOBP_FUNCDIS3, ~0UL, SIO_IOBP_FUNCDIS_DIS);
break;
case PCI_DEVFN(21, 4): /* SPI1 */
case PCH_DEVFN_SPI1: /* SPI1 */
pch_enable_d3hot(dev);
pch_iobp_update(SIO_IOBP_FUNCDIS4, ~0UL, SIO_IOBP_FUNCDIS_DIS);
break;
case PCI_DEVFN(21, 5): /* UART0 */
case PCH_DEVFN_UART0: /* UART0 */
pch_enable_d3hot(dev);
pch_iobp_update(SIO_IOBP_FUNCDIS5, ~0UL, SIO_IOBP_FUNCDIS_DIS);
break;
case PCI_DEVFN(21, 6): /* UART1 */
case PCH_DEVFN_UART1: /* UART1 */
pch_enable_d3hot(dev);
pch_iobp_update(SIO_IOBP_FUNCDIS6, ~0UL, SIO_IOBP_FUNCDIS_DIS);
break;
case PCI_DEVFN(22, 0): /* MEI #1 */
case PCH_DEVFN_ME: /* MEI #1 */
RCBA32_OR(FD2, PCH_DISABLE_MEI1);
break;
case PCI_DEVFN(22, 1): /* MEI #2 */
case PCH_DEVFN_ME_2: /* MEI #2 */
RCBA32_OR(FD2, PCH_DISABLE_MEI2);
break;
case PCI_DEVFN(22, 2): /* IDE-R */
case PCH_DEVFN_ME_IDER: /* IDE-R */
RCBA32_OR(FD2, PCH_DISABLE_IDER);
break;
case PCI_DEVFN(22, 3): /* KT */
case PCH_DEVFN_ME_KT: /* KT */
RCBA32_OR(FD2, PCH_DISABLE_KT);
break;
case PCI_DEVFN(23, 0): /* SDIO */
case PCH_DEVFN_SDIO: /* SDIO */
pch_enable_d3hot(dev);
pch_iobp_update(SIO_IOBP_FUNCDIS7, ~0UL, SIO_IOBP_FUNCDIS_DIS);
break;
case PCI_DEVFN(25, 0): /* Gigabit Ethernet */
case PCH_DEVFN_GBE: /* Gigabit Ethernet */
RCBA32_OR(BUC, PCH_DISABLE_GBE);
break;
case PCI_DEVFN(26, 0): /* EHCI #2 */
RCBA32_OR(FD, PCH_DISABLE_EHCI2);
break;
case PCI_DEVFN(27, 0): /* HD Audio Controller */
case PCH_DEVFN_HDA: /* HD Audio Controller */
RCBA32_OR(FD, PCH_DISABLE_HD_AUDIO);
break;
case PCI_DEVFN(28, 0): /* PCI Express Root Port 1 */
case PCI_DEVFN(28, 1): /* PCI Express Root Port 2 */
case PCI_DEVFN(28, 2): /* PCI Express Root Port 3 */
case PCI_DEVFN(28, 3): /* PCI Express Root Port 4 */
case PCI_DEVFN(28, 4): /* PCI Express Root Port 5 */
case PCI_DEVFN(28, 5): /* PCI Express Root Port 6 */
case PCI_DEVFN(28, 6): /* PCI Express Root Port 7 */
case PCI_DEVFN(28, 7): /* PCI Express Root Port 8 */
case PCI_DEVFN(PCH_DEV_SLOT_PCIE, 0): /* PCI Express Root Port 1 */
case PCI_DEVFN(PCH_DEV_SLOT_PCIE, 1): /* PCI Express Root Port 2 */
case PCI_DEVFN(PCH_DEV_SLOT_PCIE, 2): /* PCI Express Root Port 3 */
case PCI_DEVFN(PCH_DEV_SLOT_PCIE, 3): /* PCI Express Root Port 4 */
case PCI_DEVFN(PCH_DEV_SLOT_PCIE, 4): /* PCI Express Root Port 5 */
case PCI_DEVFN(PCH_DEV_SLOT_PCIE, 5): /* PCI Express Root Port 6 */
case PCI_DEVFN(PCH_DEV_SLOT_PCIE, 6): /* PCI Express Root Port 7 */
case PCI_DEVFN(PCH_DEV_SLOT_PCIE, 7): /* PCI Express Root Port 8 */
RCBA32_OR(FD, PCH_DISABLE_PCIE(PCI_FUNC(dev->path.pci.devfn)));
break;
case PCI_DEVFN(29, 0): /* EHCI #1 */
case PCH_DEVFN_EHCI: /* EHCI #1 */
RCBA32_OR(FD, PCH_DISABLE_EHCI1);
break;
case PCI_DEVFN(31, 0): /* LPC */
case PCH_DEVFN_LPC: /* LPC */
RCBA32_OR(FD, PCH_DISABLE_LPC);
break;
case PCI_DEVFN(31, 2): /* SATA #1 */
case PCH_DEVFN_SATA: /* SATA #1 */
RCBA32_OR(FD, PCH_DISABLE_SATA1);
break;
case PCI_DEVFN(31, 3): /* SMBUS */
case PCH_DEVFN_SMBUS: /* SMBUS */
RCBA32_OR(FD, PCH_DISABLE_SMBUS);
break;
case PCI_DEVFN(31, 5): /* SATA #2 */
case PCH_DEVFN_SATA2: /* SATA #2 */
RCBA32_OR(FD, PCH_DISABLE_SATA2);
break;
case PCI_DEVFN(31, 6): /* Thermal Subsystem */
case PCH_DEVFN_THERMAL: /* Thermal Subsystem */
RCBA32_OR(FD, PCH_DISABLE_THERMAL);
break;
}
@ -186,9 +183,13 @@ void broadwell_pch_enable_dev(device_t dev)
{
u32 reg32;
/* PCH PCIe Root Ports are handled in PCIe driver. */
if (PCI_SLOT(dev->path.pci.devfn) == PCH_DEV_SLOT_PCIE)
/* These devices need special enable/disable handling */
switch (PCI_SLOT(dev->path.pci.devfn)) {
case PCH_DEV_SLOT_PCIE:
case PCH_DEV_SLOT_EHCI:
case PCH_DEV_SLOT_HDA:
return;
}
if (!dev->enabled) {
printk(BIOS_DEBUG, "%s: Disabling device\n", dev_path(dev));

View File

@ -1,115 +0,0 @@
/*
* coreboot UEFI PEI wrapper
*
* Copyright (c) 2011, Google Inc.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* * Neither the name of Google Inc. nor the
* names of its contributors may be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL GOOGLE INC BE LIABLE FOR ANY DIRECT,
* INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef PEI_DATA_H
#define PEI_DATA_H
typedef void (*tx_byte_func)(unsigned char byte);
#define PEI_VERSION 15
#define MAX_USB2_PORTS 16
#define MAX_USB3_PORTS 16
#define USB_OC_PIN_SKIP 8
enum usb2_port_location {
USB_PORT_BACK_PANEL = 0,
USB_PORT_FRONT_PANEL,
USB_PORT_DOCK,
USB_PORT_MINI_PCIE,
USB_PORT_FLEX,
USB_PORT_INTERNAL,
USB_PORT_SKIP
};
/* Usb Port Length:
* [16:4] = length in inches in octal format
* [3:0] = decimal point
*/
struct usb2_port_setting {
uint16_t length;
uint8_t enable;
uint8_t over_current_pin;
uint8_t location;
} __attribute__((packed));
struct usb3_port_setting {
uint8_t enable;
uint8_t over_current_pin;
} __attribute__((packed));
struct pei_data
{
uint32_t pei_version;
uint32_t mchbar;
uint32_t dmibar;
uint32_t epbar;
uint32_t pciexbar;
uint16_t smbusbar;
uint32_t wdbbar;
uint32_t wdbsize;
uint32_t hpet_address;
uint32_t rcba;
uint32_t pmbase;
uint32_t gpiobase;
uint32_t temp_mmio_base;
uint32_t system_type; // 0 Mobile, 1 Desktop/Server
uint32_t tseg_size;
uint8_t spd_addresses[4];
int boot_mode;
int ec_present;
int gbe_enable;
// 0 = leave channel enabled
// 1 = disable dimm 0 on channel
// 2 = disable dimm 1 on channel
// 3 = disable dimm 0+1 on channel
int dimm_channel0_disabled;
int dimm_channel1_disabled;
/* Enable 2x Refresh Mode */
int ddr_refresh_2x;
int dq_pins_interleaved;
/* Data read from flash and passed into MRC */
unsigned char *mrc_input;
unsigned int mrc_input_len;
/* Data from MRC that should be saved to flash */
unsigned char *mrc_output;
unsigned int mrc_output_len;
/*
* Max frequency DDR3 could be ran at. Could be one of four values: 800,
* 1067, 1333, 1600
*/
uint32_t max_ddr3_freq;
/* Route all USB ports to XHCI controller in resume path */
int usb_xhci_on_resume;
struct usb2_port_setting usb2_ports[MAX_USB2_PORTS];
struct usb3_port_setting usb3_ports[MAX_USB3_PORTS];
uint8_t spd_data[4][256];
tx_byte_func tx_byte;
} __attribute__((packed));
#endif

View File

@ -10,3 +10,4 @@ romstage-y += smbus.c
romstage-y += spi.c
romstage-y += stack.c
romstage-y += systemagent.c
romstage-$(CONFIG_CONSOLE_SERIAL8250MEM) += uart.c

View File

@ -17,6 +17,7 @@
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include <arch/cpu.h>
#include <stdlib.h>
#include <console/console.h>
#include <cpu/x86/msr.h>
@ -24,6 +25,11 @@
#include <broadwell/msr.h>
#include <broadwell/romstage.h>
u32 cpu_family_model(void)
{
return cpuid_eax(1) & 0x0fff0ff0;
}
void set_max_freq(void)
{
msr_t msr, perf_ctl, platform_info;

View File

@ -24,6 +24,7 @@
#include <cbmem.h>
#include <console/console.h>
#include <device/pci_def.h>
#include <lib.h>
#include <string.h>
#if CONFIG_EC_GOOGLE_CHROMEEC
#include <ec/google/chromeec/ec.h>
@ -73,6 +74,16 @@ void raminit(struct pei_data *pei_data)
#endif
}
/*
* Do not use saved pei data. Can be set by mainboard romstage
* to force a full train of memory on every boot.
*/
if (pei_data->disable_saved_data) {
printk(BIOS_DEBUG, "Disabling PEI saved data by request\n");
pei_data->saved_data = NULL;
pei_data->saved_data_size = 0;
}
/* Determine if mrc.bin is in the cbfs. */
entry = (pei_wrapper_entry_t)cbfs_get_file_content(
CBFS_DEFAULT_MEDIA, "mrc.bin", 0xab);
@ -95,6 +106,9 @@ void raminit(struct pei_data *pei_data)
report_memory_config();
/* Basic memory sanity test */
quick_ram_check();
if (pei_data->boot_mode != SLEEP_STATE_S3) {
cbmem_initialize_empty();
} else if (cbmem_initialize()) {

View File

@ -41,6 +41,7 @@ static struct {
{ CPUID_HASWELL_HALO, "Haswell Perf Halo" },
{ CPUID_BROADWELL_C0, "Broadwell C0" },
{ CPUID_BROADWELL_D0, "Broadwell D0" },
{ CPUID_BROADWELL_E0, "Broadwell E0" },
};
static struct {

View File

@ -73,6 +73,9 @@ void * asmlinkage romstage_main(unsigned long bist,
/* Start console drivers */
console_init();
/* Get power state */
rp.power_state = fill_power_state();
/* Print useful platform information */
report_platform_info();
@ -96,19 +99,16 @@ static inline void chromeos_init(int prev_sleep_state)
/* Entry from the mainboard. */
void romstage_common(struct romstage_params *params)
{
struct chipset_power_state *ps;
struct romstage_handoff *handoff;
post_code(0x32);
mark_ts(params, timestamp_get());
/* Get power state */
ps = fill_power_state();
params->pei_data->boot_mode = ps->prev_sleep_state;
params->pei_data->boot_mode = params->power_state->prev_sleep_state;
#if CONFIG_ELOG_BOOT_COUNT
if (ps->prev_sleep_state != SLEEP_STATE_S3)
if (params->power_state->prev_sleep_state != SLEEP_STATE_S3)
boot_count_increment();
#endif
@ -121,11 +121,12 @@ void romstage_common(struct romstage_params *params)
handoff = romstage_handoff_find_or_add();
if (handoff != NULL)
handoff->s3_resume = (ps->prev_sleep_state == SLEEP_STATE_S3);
handoff->s3_resume = (params->power_state->prev_sleep_state ==
SLEEP_STATE_S3);
else
printk(BIOS_DEBUG, "Romstage handoff structure not added!\n");
chromeos_init(ps->prev_sleep_state);
chromeos_init(params->power_state->prev_sleep_state);
/* Save timestamp information. */
timestamp_init(params->ts.times[0]);

View File

@ -0,0 +1,85 @@
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2014 Google Inc.
*
* 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
* the Free Software Foundation; version 2 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* 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
*/
#include <arch/early_variables.h>
#include <arch/io.h>
#include <delay.h>
#include <device/pci_def.h>
#include <reg_script.h>
#include <stdint.h>
#include <uart8250.h>
#include <broadwell/iobp.h>
#include <broadwell/serialio.h>
const struct reg_script uart_init[] = {
/* Set MMIO BAR */
REG_PCI_WRITE32(PCI_BASE_ADDRESS_0, CONFIG_TTYS0_BASE),
/* Enable Memory access and Bus Master */
REG_PCI_OR32(PCI_COMMAND, PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER),
/* Initialize LTR */
REG_MMIO_RMW32(CONFIG_TTYS0_BASE + SIO_REG_PPR_GEN,
~SIO_REG_PPR_GEN_LTR_MODE_MASK, 0),
REG_MMIO_RMW32(CONFIG_TTYS0_BASE + SIO_REG_PPR_RST,
~(SIO_REG_PPR_RST_ASSERT), 0),
/* Take UART out of reset */
REG_MMIO_OR32(CONFIG_TTYS0_BASE + SIO_REG_PPR_RST,
SIO_REG_PPR_RST_ASSERT),
/* Set M and N divisor inputs and enable clock */
REG_MMIO_WRITE32(CONFIG_TTYS0_BASE + SIO_REG_PPR_CLOCK,
SIO_REG_PPR_CLOCK_EN | SIO_REG_PPR_CLOCK_UPDATE |
(SIO_REG_PPR_CLOCK_N_DIV << 16) |
(SIO_REG_PPR_CLOCK_M_DIV << 1)),
REG_SCRIPT_END
};
void pch_uart_init(void)
{
/* Program IOBP CB000154h[12,9:8,4:0] = 1001100011111b */
u32 gpiodf = 0x131f;
device_t dev;
/* Put UART in byte access mode for 16550 compatibility */
switch (CONFIG_INTEL_PCH_UART_CONSOLE_NUMBER) {
case 0:
dev = PCH_DEV_UART0;
gpiodf |= SIO_IOBP_GPIODF_UART0_BYTE_ACCESS;
break;
case 1:
dev = PCH_DEV_UART1;
gpiodf |= SIO_IOBP_GPIODF_UART1_BYTE_ACCESS;
break;
default:
return;
}
/* Program IOBP GPIODF */
pch_iobp_update(SIO_IOBP_GPIODF, ~gpiodf, gpiodf);
/* Program IOBP CB000180h[5:0] = 111111b (undefined register) */
pch_iobp_update(0xcb000180, ~0x0000003f, 0x0000003f);
/* Initialize chipset uart interface */
reg_script_run_on_dev(dev, uart_init);
/*
* Perform standard UART initialization
* Divisor 1 is 115200 BAUD
*/
uart8250_mem_init(CONFIG_TTYS0_BASE, 1);
}

View File

@ -27,6 +27,7 @@
#include <stdlib.h>
#include <broadwell/iobp.h>
#include <broadwell/nvs.h>
#include <broadwell/pci_devs.h>
#include <broadwell/pch.h>
#include <broadwell/ramstage.h>
#include <broadwell/rcba.h>
@ -34,11 +35,24 @@
#include <chip.h>
/* Set D3Hot Power State in ACPI mode */
static void serialio_enable_d3hot(struct device *dev)
static void serialio_enable_d3hot(struct resource *res)
{
u32 reg32 = pci_read_config32(dev, PCH_PCS);
u32 reg32 = read32(res->base + PCH_PCS);
reg32 |= PCH_PCS_PS_D3HOT;
pci_write_config32(dev, PCH_PCS, reg32);
write32(res->base + PCH_PCS, reg32);
}
static int serialio_uart_is_debug(struct device *dev)
{
#if CONFIG_INTEL_PCH_UART_CONSOLE
switch (dev->path.pci.devfn) {
case PCH_DEVFN_UART0: /* UART0 */
return !!(CONFIG_INTEL_PCH_UART_CONSOLE_NUMBER == 0);
case PCH_DEVFN_UART1: /* UART1 */
return !!(CONFIG_INTEL_PCH_UART_CONSOLE_NUMBER == 1);
}
#endif
return 0;
}
/* Enable clock in PCI mode */
@ -182,55 +196,55 @@ static void serialio_init(struct device *dev)
if (!config->sio_acpi_mode)
serialio_enable_clock(bar0);
else if (dev->path.pci.devfn != PCI_DEVFN(21, 0))
serialio_enable_d3hot(dev); /* all but SDMA */
switch (dev->path.pci.devfn) {
case PCI_DEVFN(21, 0): /* SDMA */
case PCH_DEVFN_SDMA: /* SDMA */
sio_index = SIO_ID_SDMA;
serialio_init_once(config->sio_acpi_mode);
serialio_d21_mode(sio_index, SIO_PIN_INTB,
config->sio_acpi_mode);
break;
case PCI_DEVFN(21, 1): /* I2C0 */
case PCH_DEVFN_I2C0: /* I2C0 */
sio_index = SIO_ID_I2C0;
serialio_d21_ltr(bar0);
serialio_i2c_voltage_sel(bar0, config->sio_i2c0_voltage);
serialio_d21_mode(sio_index, SIO_PIN_INTC,
config->sio_acpi_mode);
break;
case PCI_DEVFN(21, 2): /* I2C1 */
case PCH_DEVFN_I2C1: /* I2C1 */
sio_index = SIO_ID_I2C1;
serialio_d21_ltr(bar0);
serialio_i2c_voltage_sel(bar0, config->sio_i2c1_voltage);
serialio_d21_mode(sio_index, SIO_PIN_INTC,
config->sio_acpi_mode);
break;
case PCI_DEVFN(21, 3): /* SPI0 */
case PCH_DEVFN_SPI0: /* SPI0 */
sio_index = SIO_ID_SPI0;
serialio_d21_ltr(bar0);
serialio_d21_mode(sio_index, SIO_PIN_INTC,
config->sio_acpi_mode);
break;
case PCI_DEVFN(21, 4): /* SPI1 */
case PCH_DEVFN_SPI1: /* SPI1 */
sio_index = SIO_ID_SPI1;
serialio_d21_ltr(bar0);
serialio_d21_mode(sio_index, SIO_PIN_INTC,
config->sio_acpi_mode);
break;
case PCI_DEVFN(21, 5): /* UART0 */
case PCH_DEVFN_UART0: /* UART0 */
sio_index = SIO_ID_UART0;
serialio_d21_ltr(bar0);
if (!serialio_uart_is_debug(dev))
serialio_d21_ltr(bar0);
serialio_d21_mode(sio_index, SIO_PIN_INTD,
config->sio_acpi_mode);
break;
case PCI_DEVFN(21, 6): /* UART1 */
case PCH_DEVFN_UART1: /* UART1 */
sio_index = SIO_ID_UART1;
serialio_d21_ltr(bar0);
if (!serialio_uart_is_debug(dev))
serialio_d21_ltr(bar0);
serialio_d21_mode(sio_index, SIO_PIN_INTD,
config->sio_acpi_mode);
break;
case PCI_DEVFN(23, 0): /* SDIO */
case PCH_DEVFN_SDIO: /* SDIO */
sio_index = SIO_ID_SDIO;
serialio_d23_ltr(bar0);
serialio_d23_mode(config->sio_acpi_mode);
@ -252,6 +266,14 @@ static void serialio_init(struct device *dev)
/* Save BAR0 and BAR1 to ACPI NVS */
gnvs->dev.bar0[sio_index] = (u32)bar0->base;
gnvs->dev.bar1[sio_index] = (u32)bar1->base;
/* Do not enable UART if it is used as debug port */
if (!serialio_uart_is_debug(dev))
gnvs->dev.enable[sio_index] = 1;
/* Put device in D3hot state via BAR1 */
if (dev->path.pci.devfn != PCH_DEVFN_SDMA)
serialio_enable_d3hot(bar1); /* all but SDMA */
}
}

View File

@ -33,6 +33,7 @@
#include <vendorcode/google/chromeos/chromeos.h>
#include <broadwell/cpu.h>
#include <broadwell/iomap.h>
#include <broadwell/pci_devs.h>
#include <broadwell/ramstage.h>
#include <broadwell/systemagent.h>
@ -278,11 +279,25 @@ static void mc_add_dram_resources(device_t dev)
unsigned long index;
struct resource *resource;
uint64_t mc_values[NUM_MAP_ENTRIES];
unsigned long dpr_size = 0;
u32 dpr_reg;
/* Read in the MAP registers and report their values. */
mc_read_map_entries(dev, &mc_values[0]);
mc_report_map_entries(dev, &mc_values[0]);
/*
* DMA Protected Range can be reserved below TSEG for PCODE patch
* or TXT/BootGuard related data. Rather than report a base address
* the DPR register reports the TOP of the region, which is the same
* as TSEG base. The region size is reported in MiB in bits 11:4.
*/
dpr_reg = pci_read_config32(SA_DEV_ROOT, DPR);
if (dpr_reg & DPR_EPM) {
dpr_size = (dpr_reg & DPR_SIZE_MASK) << 16;
printk(BIOS_INFO, "DPR SIZE: 0x%lx\n", dpr_size);
}
/*
* These are the host memory ranges that should be added:
* - 0 -> 0xa0000: cacheable
@ -320,14 +335,15 @@ static void mc_add_dram_resources(device_t dev)
size_k = (0xa0000 >> 10) - base_k;
ram_resource(dev, index++, base_k, size_k);
/* 0xc0000 -> TSEG */
/* 0xc0000 -> TSEG - DPR */
base_k = 0xc0000 >> 10;
size_k = (unsigned long)(mc_values[TSEG_REG] >> 10) - base_k;
size_k -= dpr_size >> 10;
ram_resource(dev, index++, base_k, size_k);
/* TSEG -> BGSM */
/* TSEG - DPR -> BGSM */
resource = new_resource(dev, index++);
resource->base = mc_values[TSEG_REG];
resource->base = mc_values[TSEG_REG] - dpr_size;
resource->size = mc_values[BGSM_REG] - resource->base;
resource->flags = IORESOURCE_MEM | IORESOURCE_FIXED |
IORESOURCE_STORED | IORESOURCE_RESERVE |

View File

@ -0,0 +1,51 @@
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2014 Google Inc.
*
* 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
* the Free Software Foundation; version 2 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* 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
*/
#include <stdint.h>
#include <arch/io.h>
#include <console/console.h>
#include <usbdebug.h>
#include <device/pci.h>
#include <device/pci_def.h>
#include <broadwell/pci_devs.h>
void set_debug_port(unsigned int port)
{
/* Hardcoded to physical port 1 */
}
void enable_usbdebug(unsigned int port)
{
u32 tmp32;
tmp32 = pci_read_config32(PCH_DEV_EHCI, PCI_VENDOR_ID);
if (tmp32 == 0xffffffff || tmp32 == 0)
return;
/* Set the EHCI BAR address. */
pci_write_config32(PCH_DEV_EHCI, EHCI_BAR_INDEX, CONFIG_EHCI_BAR);
/* Enable access to the EHCI memory space registers. */
pci_write_config8(PCH_DEV_EHCI, PCI_COMMAND, PCI_COMMAND_MEMORY);
/* Force ownership of the Debug Port to the EHCI controller. */
tmp32 = read32(CONFIG_EHCI_BAR + CONFIG_EHCI_DEBUG_OFFSET);
tmp32 |= (1 << 30);
write32(CONFIG_EHCI_BAR + CONFIG_EHCI_DEBUG_OFFSET, tmp32);
}