Kyösti Mälkki (kyosti.malkki(a)gmail.com) just uploaded a new patch set to gerrit, which you can find at http://review.coreboot.org/3854
-gerrit
commit 6162b7fd2122f740651d9b409693a5766f1433fb
Author: Kyösti Mälkki <kyosti.malkki(a)gmail.com>
Date: Mon Aug 12 23:29:57 2013 +0300
console: Squelch console output from AP CPUs in romstage
Add Kconfig option SQUELCH_EARLY_SMP and have it enabled by
default.
Console drivers have unpredictable results if multiple threads
attempt to share same resources without spinlock. Serial UARTs
have not had huge problems, only distorted output, but those
relying on cache-as-ram (CBMEM and usbdebug) may require this.
Change-Id: I7f406fdea7b6dc6a341c4da2fab56f7b7ff568b4
Signed-off-by: Kyösti Mälkki <kyosti.malkki(a)gmail.com>
---
src/arch/x86/lib/romstage_console.c | 9 ++++++++-
src/console/Kconfig | 12 ++++++++++++
2 files changed, 20 insertions(+), 1 deletion(-)
diff --git a/src/arch/x86/lib/romstage_console.c b/src/arch/x86/lib/romstage_console.c
index 2e743ad..1c3141c 100644
--- a/src/arch/x86/lib/romstage_console.c
+++ b/src/arch/x86/lib/romstage_console.c
@@ -31,7 +31,9 @@
#if CONFIG_SPKMODEM
#include <console/spkmodem.h>
#endif
-
+#if CONFIG_SQUELCH_EARLY_SMP
+#include <cpu/x86/lapic.h>
+#endif
void console_tx_byte(unsigned char byte)
{
@@ -86,6 +88,11 @@ int do_printk(int msg_level, const char *fmt, ...)
return 0;
}
+#if CONFIG_SQUELCH_EARLY_SMP
+ if (!boot_cpu())
+ return 0;
+#endif
+
va_start(args, fmt);
i = vtxprintf(console_tx_byte, fmt, args);
va_end(args);
diff --git a/src/console/Kconfig b/src/console/Kconfig
index 1d050f7..9b2e052 100644
--- a/src/console/Kconfig
+++ b/src/console/Kconfig
@@ -14,6 +14,18 @@ config EARLY_CONSOLE
help
Use console during early (pre-RAM) boot stages
+config SQUELCH_EARLY_SMP
+ bool "Squelch AP CPUs from early console."
+ default y
+ depends on EARLY_CONSOLE
+ help
+ When selected only BSP CPU will output to early console.
+
+ Console drivers have unpredictable results if multiple threads
+ attempt to share same resources without spinlock.
+
+ If unsure, say Y.
+
config CONSOLE_SERIAL
bool "Serial port console output"
default y
Andrew Wu (arw(a)dmp.com.tw) just uploaded a new patch set to gerrit, which you can find at http://review.coreboot.org/3844
-gerrit
commit 6296222ed1c80828d573e620657d68a1a4d2708c
Author: Andrew Wu <arw(a)dmp.com.tw>
Date: Mon Aug 12 20:07:47 2013 +0800
Add the generic Intel HD audio (Azalia) module azalia_device.c.
This module uses cim_verb_data to detects and initializes HD audio
codecs.
Module source code is based on southbridge/intel/sch/audio.c and
southbridge/nvidia/mcp55/azalia.c.
Change-Id: I810fef6fdcf55d66f62da58c3d7d99f006559d6e
Signed-off-by: Andrew Wu <arw(a)dmp.com.tw>
---
src/device/Kconfig | 5 +
src/device/Makefile.inc | 1 +
src/device/azalia_device.c | 276 +++++++++++++++++++++++++++++++++++++
src/include/device/azalia_device.h | 28 ++++
4 files changed, 310 insertions(+)
diff --git a/src/device/Kconfig b/src/device/Kconfig
index ca2fb33..4087f6f 100644
--- a/src/device/Kconfig
+++ b/src/device/Kconfig
@@ -226,6 +226,11 @@ config CARDBUS_PLUGIN_SUPPORT
depends on PCI
default y
+config AZALIA_PLUGIN_SUPPORT
+ bool
+ depends on PCI
+ default n
+
config PCIEXP_COMMON_CLOCK
prompt "Enable PCIe Common Clock"
bool
diff --git a/src/device/Makefile.inc b/src/device/Makefile.inc
index 9fe156b..96e2cd9 100644
--- a/src/device/Makefile.inc
+++ b/src/device/Makefile.inc
@@ -8,6 +8,7 @@ ramstage-$(CONFIG_PCIX_PLUGIN_SUPPORT) += pcix_device.c
ramstage-$(CONFIG_PCIEXP_PLUGIN_SUPPORT) += pciexp_device.c
ramstage-$(CONFIG_AGP_PLUGIN_SUPPORT) += agp_device.c
ramstage-$(CONFIG_CARDBUS_PLUGIN_SUPPORT) += cardbus_device.c
+ramstage-$(CONFIG_AZALIA_PLUGIN_SUPPORT) += azalia_device.c
ramstage-$(CONFIG_ARCH_X86) += pnp_device.c
ramstage-$(CONFIG_PCI) += pci_ops.c
ramstage-y += smbus_ops.c
diff --git a/src/device/azalia_device.c b/src/device/azalia_device.c
new file mode 100644
index 0000000..cbc878d
--- /dev/null
+++ b/src/device/azalia_device.c
@@ -0,0 +1,276 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyright (C) 2013 DMP Electronics 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 <console/console.h>
+#include <device/device.h>
+#include <device/pci.h>
+#include <device/pci_ids.h>
+#include <device/pci_ops.h>
+#include <device/azalia_device.h>
+#include <arch/io.h>
+#include <delay.h>
+
+#define HDA_ICII_REG 0x68
+#define HDA_ICII_BUSY (1 << 0)
+#define HDA_ICII_VALID (1 << 1)
+
+static int set_bits(u32 port, u32 mask, u32 val)
+{
+ u32 reg32;
+ int count;
+
+ /* Write (val & mask) to port */
+ val &= mask;
+ reg32 = read32(port);
+ reg32 &= ~mask;
+ reg32 |= val;
+ write32(port, reg32);
+
+ /* Wait for readback of register to
+ * match what was just written to it
+ */
+ count = 50;
+ do {
+ /* Wait 1ms based on BKDG wait time */
+ mdelay(1);
+ reg32 = read32(port);
+ reg32 &= mask;
+ } while ((reg32 != val) && --count);
+
+ /* Timeout occurred */
+ if (!count)
+ return -1;
+ return 0;
+}
+
+static int codec_detect(u32 base)
+{
+ u32 reg32;
+ int count;
+
+ /* Set Bit 0 to 1 to exit reset state (BAR + 0x8)[0] */
+ if (set_bits(base + 0x08, 1, 1) == -1)
+ goto no_codec;
+
+ /* clear STATESTS bits (BAR + 0xE)[2:0] */
+ reg32 = read32(base + 0x0E);
+ reg32 |= 7;
+ write32(base + 0x0E, reg32);
+
+ /* Wait for readback of register to
+ * match what was just written to it
+ */
+ count = 50;
+ do {
+ /* Wait 1ms based on BKDG wait time */
+ mdelay(1);
+ reg32 = read32(base + 0x0E);
+ } while ((reg32 != 0) && --count);
+ /* Timeout occured */
+ if (!count)
+ goto no_codec;
+
+ /* Set Bit0 to 0 to enter reset state (BAR + 0x8)[0] */
+ if (set_bits(base + 0x08, 1, 0) == -1)
+ goto no_codec;
+
+ /* Set Bit 0 to 1 to exit reset state (BAR + 0x8)[0] */
+ if (set_bits(base + 0x08, 1, 1) == -1)
+ goto no_codec;
+
+ /* Read in Codec location (BAR + 0xe)[2..0] */
+ reg32 = read32(base + 0xe);
+ reg32 &= 0x0f;
+ if (!reg32)
+ goto no_codec;
+
+ return reg32;
+
+no_codec:
+ /* Codec Not found */
+ /* Put HDA back in reset (BAR + 0x8) [0] */
+ set_bits(base + 0x08, 1, 0);
+ printk(BIOS_DEBUG, "azalia_audio: No codec!\n");
+ return 0;
+}
+
+const u32 *cim_verb_data = NULL;
+u32 cim_verb_data_size = 0;
+
+static u32 find_verb(struct device *dev, u32 viddid, const u32 ** verb)
+{
+ printk(BIOS_DEBUG, "azalia_audio: dev=%s\n", dev_path(dev));
+ printk(BIOS_DEBUG, "azalia_audio: Reading viddid=%x\n", viddid);
+
+ int idx = 0;
+
+ while (idx < (cim_verb_data_size / sizeof(u32))) {
+ u32 verb_size = 4 * cim_verb_data[idx + 2]; // in u32
+ if (cim_verb_data[idx] != viddid) {
+ idx += verb_size + 3; // skip verb + header
+ continue;
+ }
+ *verb = &cim_verb_data[idx + 3];
+ return verb_size;
+ }
+
+ /* Not all codecs need to load another verb */
+ return 0;
+}
+
+/**
+ * Wait 50usec for the codec to indicate it is ready
+ * no response would imply that the codec is non-operative
+ */
+
+static int wait_for_ready(u32 base)
+{
+ /* Use a 50 usec timeout - the Linux kernel uses the
+ * same duration */
+
+ int timeout = 50;
+
+ while (timeout--) {
+ u32 reg32 = read32(base + HDA_ICII_REG);
+ if (!(reg32 & HDA_ICII_BUSY))
+ return 0;
+ udelay(1);
+ }
+
+ return -1;
+}
+
+/**
+ * Wait 50usec for the codec to indicate that it accepted
+ * the previous command. No response would imply that the code
+ * is non-operative
+ */
+
+static int wait_for_valid(u32 base)
+{
+ /* Use a 50 usec timeout - the Linux kernel uses the
+ * same duration */
+
+ int timeout = 25;
+
+ write32(base + HDA_ICII_REG, HDA_ICII_VALID | HDA_ICII_BUSY);
+ while (timeout--) {
+ udelay(1);
+ }
+ timeout = 50;
+ while (timeout--) {
+ u32 reg32 = read32(base + HDA_ICII_REG);
+ if ((reg32 & (HDA_ICII_VALID | HDA_ICII_BUSY)) ==
+ HDA_ICII_VALID)
+ return 0;
+ udelay(1);
+ }
+
+ return -1;
+}
+
+static void codec_init(struct device *dev, u32 base, int addr)
+{
+ u32 reg32;
+ const u32 *verb;
+ u32 verb_size;
+ int i;
+
+ printk(BIOS_DEBUG, "azalia_audio: Initializing codec #%d\n", addr);
+
+ /* 1 */
+ if (wait_for_ready(base) == -1)
+ return;
+
+ reg32 = (addr << 28) | 0x000f0000;
+ write32(base + 0x60, reg32);
+
+ if (wait_for_valid(base) == -1)
+ return;
+
+ reg32 = read32(base + 0x64);
+
+ /* 2 */
+ printk(BIOS_DEBUG, "azalia_audio: codec viddid: %08x\n", reg32);
+ verb_size = find_verb(dev, reg32, &verb);
+
+ if (!verb_size) {
+ printk(BIOS_DEBUG, "azalia_audio: No verb!\n");
+ return;
+ }
+ printk(BIOS_DEBUG, "azalia_audio: verb_size: %d\n", verb_size);
+
+ /* 3 */
+ for (i = 0; i < verb_size; i++) {
+ if (wait_for_ready(base) == -1)
+ return;
+
+ write32(base + 0x60, verb[i]);
+
+ if (wait_for_valid(base) == -1)
+ return;
+ }
+ printk(BIOS_DEBUG, "azalia_audio: verb loaded.\n");
+}
+
+static void codecs_init(struct device *dev, u32 base, u32 codec_mask)
+{
+ int i;
+
+ for (i = 2; i >= 0; i--) {
+ if (codec_mask & (1 << i))
+ codec_init(dev, base, i);
+ }
+}
+
+void azalia_audio_init(struct device *dev)
+{
+ u32 base;
+ struct resource *res;
+ u32 codec_mask;
+
+ res = find_resource(dev, 0x10);
+ if (!res)
+ return;
+
+ // NOTE this will break as soon as the azalia_audio get's a bar above
+ // 4G. Is there anything we can do about it?
+ base = (u32) res->base;
+ printk(BIOS_DEBUG, "azalia_audio: base = %08x\n", (u32) base);
+ codec_mask = codec_detect(base);
+
+ if (codec_mask) {
+ printk(BIOS_DEBUG, "azalia_audio: codec_mask = %02x\n",
+ codec_mask);
+ codecs_init(dev, base, codec_mask);
+ }
+}
+
+struct pci_operations azalia_audio_pci_ops = {
+ .set_subsystem = pci_dev_set_subsystem,
+};
+
+struct device_operations default_azalia_audio_ops = {
+ .read_resources = pci_dev_read_resources,
+ .set_resources = pci_dev_set_resources,
+ .enable_resources = pci_dev_enable_resources,
+ .init = azalia_audio_init,
+ .scan_bus = 0,
+ .ops_pci = &azalia_audio_pci_ops,
+};
diff --git a/src/include/device/azalia_device.h b/src/include/device/azalia_device.h
new file mode 100644
index 0000000..10bc77d
--- /dev/null
+++ b/src/include/device/azalia_device.h
@@ -0,0 +1,28 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyright (C) 2013 DMP Electronics 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 DEVICE_AZALIA_H
+#define DEVICE_AZALIA_H
+
+#include <device/device.h>
+
+void azalia_audio_init(struct device *dev);
+extern struct device_operations default_azalia_audio_ops;
+
+#endif /* DEVICE_AZALIA_H */
the following patch was just integrated into master:
commit 3be80cce290e3ff2da6abc30addab79f5a5ffa07
Author: Kyösti Mälkki <kyosti.malkki(a)gmail.com>
Date: Thu Jun 6 10:46:37 2013 +0300
usbdebug: Add option for verbose logging of connection
Add option to log changes in USB 2.0 EHCI debug port connection.
For romstage move usbdebug as the last initialised console so one
actually can see these messages.
Init order of consoles in ramstage is undetermined and unchanged.
Change-Id: I3aceec8a93064bd952886839569e9f5beb6c5720
Signed-off-by: Kyösti Mälkki <kyosti.malkki(a)gmail.com>
Reviewed-on: http://review.coreboot.org/3387
Tested-by: build bot (Jenkins)
Reviewed-by: Aaron Durbin <adurbin(a)google.com>
See http://review.coreboot.org/3387 for details.
-gerrit
the following patch was just integrated into master:
commit a9bbdd39e420d7d99323a28e24636d1a849effa3
Author: Kyösti Mälkki <kyosti.malkki(a)gmail.com>
Date: Fri Aug 9 02:24:05 2013 +0300
usbdebug: Fix AMD cimx/sb700 cimx/sb800
These Kconfig entries were forgotten from the commit
that re-enabled usbdebug for these southbridges.
Change-Id: Ia17f1dd3340408da7c033c2c949404d2636bed44
Signed-off-by: Kyösti Mälkki <kyosti.malkki(a)gmail.com>
Reviewed-on: http://review.coreboot.org/3849
Tested-by: build bot (Jenkins)
Reviewed-by: Marc Jones <marc.jones(a)se-eng.com>
See http://review.coreboot.org/3849 for details.
-gerrit
the following patch was just integrated into master:
commit fd98c65b9d89e1ca665e25b6abf6d2019855e85a
Author: Kyösti Mälkki <kyosti.malkki(a)gmail.com>
Date: Fri Jul 26 08:50:53 2013 +0300
intel/sandybridge intel/bd82x6x: remove explicit pcie config accesses
Now that MMCONF_SUPPORT_DEFAULT is enabled by default remove
the pcie explicit accesses. The default config accesses use
MMIO.
Change-Id: I58c4b021ac87a035ac2ec2b6b110b75e6d263ab4
Signed-off-by: Kyösti Mälkki <kyosti.malkki(a)gmail.com>
Reviewed-on: http://review.coreboot.org/3810
Tested-by: build bot (Jenkins)
Reviewed-by: Aaron Durbin <adurbin(a)google.com>
See http://review.coreboot.org/3810 for details.
-gerrit
Gerd Hoffmann (kraxel(a)redhat.com) just uploaded a new patch set to gerrit, which you can find at http://review.coreboot.org/3850
-gerrit
commit 9969a0e1c14d898c0267272d81c33035c7ec39be
Author: Gerd Hoffmann <kraxel(a)redhat.com>
Date: Fri Aug 9 10:02:22 2013 +0200
qemu: fix ioapic reservation
The slightly hackish ioapic ressource reservation is needed for i440fx
emulation only, for q35 the ich9 southbridge driver handles this just
fine.
[ Side note: The i440fx chipset emulated by qemu is pimped up with alot
of stuff which never existed on real hardware, which leads
to tweaks like this one. ]
Change-Id: I06bf54cbc247ccf17aa9063fb7dee9def323c605
Signed-off-by: Gerd Hoffmann <kraxel(a)redhat.com>
---
src/mainboard/emulation/qemu-i440fx/northbridge.c | 22 ++++++++++++++--------
1 file changed, 14 insertions(+), 8 deletions(-)
diff --git a/src/mainboard/emulation/qemu-i440fx/northbridge.c b/src/mainboard/emulation/qemu-i440fx/northbridge.c
index a3c2f51..b58652d 100644
--- a/src/mainboard/emulation/qemu-i440fx/northbridge.c
+++ b/src/mainboard/emulation/qemu-i440fx/northbridge.c
@@ -35,6 +35,9 @@ static void cpu_pci_domain_set_resources(device_t dev)
static void cpu_pci_domain_read_resources(struct device *dev)
{
+ u16 nbid = pci_read_config16(dev_find_slot(0, 0), PCI_DEVICE_ID);
+ int i440fx = (nbid == 0x1237);
+// int q35 = (nbid == 0x29c0);
struct resource *res;
unsigned long tomk = 0, high;
int idx = 10;
@@ -59,14 +62,17 @@ static void cpu_pci_domain_read_resources(struct device *dev)
high_tables_size = HIGH_MEMORY_SIZE;
#endif
- /* Reserve space for the IOAPIC. This should be in the Southbridge,
- * but I couldn't tell which device to put it in. */
- res = new_resource(dev, 2);
- res->base = IO_APIC_ADDR;
- res->size = 0x100000UL;
- res->limit = 0xffffffffUL;
- res->flags = IORESOURCE_MEM | IORESOURCE_FIXED | IORESOURCE_STORED |
- IORESOURCE_ASSIGNED;
+ if (i440fx) {
+ /* Reserve space for the IOAPIC. This should be in
+ * the Southbridge, but I couldn't tell which device
+ * to put it in. */
+ res = new_resource(dev, 2);
+ res->base = IO_APIC_ADDR;
+ res->size = 0x100000UL;
+ res->limit = 0xffffffffUL;
+ res->flags = IORESOURCE_MEM | IORESOURCE_FIXED |
+ IORESOURCE_STORED | IORESOURCE_ASSIGNED;
+ }
/* Reserve space for the LAPIC. There's one in every processor, but
* the space only needs to be reserved once, so we do it here. */