From 83b991afff40e12a8b6756af06a472842edb1a66 Mon Sep 17 00:00:00 2001 From: Eric Biederman Date: Sat, 11 Oct 2003 06:20:25 +0000 Subject: - O2, enums, and switch statements work in romcc - Support for compiling romcc on non x86 platforms - new romc options -msse and -mmmx for specifying extra registers to use - Bug fixes to device the device disable/enable framework and an amd8111 implementation - Move the link specification to the chip specification instead of the path - Allow specifying devices with internal bridges. - Initial via epia support - Opteron errata fixes git-svn-id: svn://svn.coreboot.org/coreboot/trunk@1200 2b7e53f0-3cfb-0310-b3e9-8179ed1497e1 --- src/southbridge/amd/amd8111/Config.lb | 4 ++ src/southbridge/amd/amd8111/amd8111.c | 56 +++++++++++++++++++++++ src/southbridge/amd/amd8111/amd8111.h | 12 +++++ src/southbridge/amd/amd8111/amd8111_ac97.c | 41 +++++++++++++++++ src/southbridge/amd/amd8111/amd8111_acpi.c | 26 ++++++++++- src/southbridge/amd/amd8111/amd8111_early_smbus.c | 14 ++++-- src/southbridge/amd/amd8111/amd8111_ide.c | 1 + src/southbridge/amd/amd8111/amd8111_lpc.c | 18 ++++---- src/southbridge/amd/amd8111/amd8111_nic.c | 25 ++++++++++ src/southbridge/amd/amd8111/amd8111_usb.c | 2 + src/southbridge/amd/amd8111/amd8111_usb2.c | 7 +-- src/southbridge/amd/amd8131/amd8131_bridge.c | 19 ++++---- 12 files changed, 199 insertions(+), 26 deletions(-) create mode 100644 src/southbridge/amd/amd8111/amd8111.c create mode 100644 src/southbridge/amd/amd8111/amd8111.h create mode 100644 src/southbridge/amd/amd8111/amd8111_ac97.c create mode 100644 src/southbridge/amd/amd8111/amd8111_nic.c (limited to 'src/southbridge/amd') diff --git a/src/southbridge/amd/amd8111/Config.lb b/src/southbridge/amd/amd8111/Config.lb index f8f38a9964..904b0995b5 100644 --- a/src/southbridge/amd/amd8111/Config.lb +++ b/src/southbridge/amd/amd8111/Config.lb @@ -1,5 +1,9 @@ +config amd8111.h +driver amd8111.o driver amd8111_usb.o driver amd8111_lpc.o driver amd8111_ide.o driver amd8111_acpi.o driver amd8111_usb2.o +#driver amd8111_ac97.o +#driver amd8111_nic.o diff --git a/src/southbridge/amd/amd8111/amd8111.c b/src/southbridge/amd/amd8111/amd8111.c new file mode 100644 index 0000000000..8dde5f13c6 --- /dev/null +++ b/src/southbridge/amd/amd8111/amd8111.c @@ -0,0 +1,56 @@ +#include +#include +#include +#include +#include +#include "amd8111.h" + +void amd8111_enable(device_t dev) +{ + device_t lpc_dev; + device_t bus_dev; + unsigned index; + uint16_t reg_old, reg; + + /* See if we are on the behind the amd8111 pci bridge */ + bus_dev = dev->bus->dev; + if ((bus_dev->vendor == PCI_VENDOR_ID_AMD) && + (bus_dev->device == PCI_DEVICE_ID_AMD_8111_PCI)) { + unsigned devfn; + devfn = bus_dev->path.u.pci.devfn + (1 << 3); + lpc_dev = dev_find_slot(bus_dev->bus->secondary, devfn); + index = ((dev->path.u.pci.devfn & ~7) >> 3) + 8; + } else { + unsigned devfn; + devfn = (dev->path.u.pci.devfn) & ~7; + lpc_dev = dev_find_slot(dev->bus->secondary, devfn); + index = dev->path.u.pci.devfn & 7; + } + if ((!lpc_dev) || (index >= 16) || + (lpc_dev->vendor != PCI_VENDOR_ID_AMD) || + (lpc_dev->device != PCI_DEVICE_ID_AMD_8111_ISA)) { + return; + } + + reg = reg_old = pci_read_config16(lpc_dev, 0x48); + reg &= ~(1 << index); + if (dev->enable) { + reg |= (1 << index); + } + if (reg != reg_old) { +#if 1 + printk_warning("amd8111_enable dev: %s", dev_path(dev)); + printk_warning(" lpc_dev: %s index: %d reg: %04x -> %04x ", + dev_path(lpc_dev), index, reg_old, reg); +#endif + pci_write_config16(lpc_dev, 0x48, reg); +#if 1 + printk_warning("done\n"); +#endif + } +} + +struct chip_control southbridge_amd_amd8111_control = { + .name = "AMD 8111", + .enable_dev = amd8111_enable, +}; diff --git a/src/southbridge/amd/amd8111/amd8111.h b/src/southbridge/amd/amd8111/amd8111.h new file mode 100644 index 0000000000..10e152954f --- /dev/null +++ b/src/southbridge/amd/amd8111/amd8111.h @@ -0,0 +1,12 @@ +#ifndef AMD8111_H +#define AMD8111_H + +struct southbridge_amd_amd8111_config +{ +}; +struct chip_control; +extern struct chip_control southbridge_amd_amd8111_control; + +void amd8111_enable(device_t dev); + +#endif /* AMD8111_H */ diff --git a/src/southbridge/amd/amd8111/amd8111_ac97.c b/src/southbridge/amd/amd8111/amd8111_ac97.c new file mode 100644 index 0000000000..63a0e1264e --- /dev/null +++ b/src/southbridge/amd/amd8111/amd8111_ac97.c @@ -0,0 +1,41 @@ +/* + * (C) 2003 Linux Networx + */ +#include +#include +#include +#include +#include +#include "amd8111.h" + + +static struct device_operations ac97audio_ops = { + .read_resources = pci_dev_read_resources, + .set_resources = pci_dev_set_resources, + .enable_resources = pci_dev_enable_resources, + .enable = amd8111_enable, + .init = 0, + .scan_bus = 0, +}; + +static struct pci_driver ac97audio_driver __pci_driver = { + .ops = &ac97audio_ops, + .vendor = PCI_VENDOR_ID_AMD, + .device = 0x746D, +}; + + +static struct device_operations ac97modem_ops = { + .read_resources = pci_dev_read_resources, + .set_resources = pci_dev_set_resources, + .enable_resources = pci_dev_enable_resources, + .enable = amd8111_enable, + .init = 0, + .scan_bus = 0, +}; + +static struct pci_driver ac97modem_driver __pci_driver = { + .ops = &ac97modem_ops, + .vendor = PCI_VENDOR_ID_AMD, + .device = 0x746E, +}; diff --git a/src/southbridge/amd/amd8111/amd8111_acpi.c b/src/southbridge/amd/amd8111/amd8111_acpi.c index 5fa6fdce29..3a5a594f57 100644 --- a/src/southbridge/amd/amd8111/amd8111_acpi.c +++ b/src/southbridge/amd/amd8111/amd8111_acpi.c @@ -3,11 +3,23 @@ #include #include #include +#include +#include "amd8111.h" + +#define PREVIOUS_POWER_STATE 0x43 +#define MAINBOARD_POWER_OFF 0 +#define MAINBOARD_POWER_ON 1 + +#ifndef MAINBOARD_POWER_ON_AFTER_POWER_FAIL +#define MAINBOARD_POWER_ON_AFTER_POWER_FAIL MAINBOARD_POWER_ON +#endif + static void acpi_init(struct device *dev) { uint8_t byte; uint16_t word; + int on; #if 0 printk_debug("ACPI: disabling NMI watchdog.. "); @@ -35,6 +47,15 @@ static void acpi_init(struct device *dev) pci_write_config_dword(dev, 0x60, 0x06800000); printk_debug("done.\n"); #endif + on = MAINBOARD_POWER_ON_AFTER_POWER_FAIL; + get_option(&on, "power_on_after_fail"); + byte = pci_read_config8(dev, PREVIOUS_POWER_STATE); + byte &= ~0x40; + if (!on) { + byte |= 0x40; + } + pci_write_config8(dev, PREVIOUS_POWER_STATE, byte); + printk_info("set power %s after power fail\n", on?"on":"off"); } @@ -42,8 +63,9 @@ static struct device_operations acpi_ops = { .read_resources = pci_dev_read_resources, .set_resources = pci_dev_set_resources, .enable_resources = pci_dev_enable_resources, - .init = acpi_init, - .scan_bus = 0, + .init = acpi_init, + .scan_bus = 0, + .enable = amd8111_enable, }; static struct pci_driver acpi_driver __pci_driver = { diff --git a/src/southbridge/amd/amd8111/amd8111_early_smbus.c b/src/southbridge/amd/amd8111/amd8111_early_smbus.c index e0aaa05ff4..b9f142dc8e 100644 --- a/src/southbridge/amd/amd8111/amd8111_early_smbus.c +++ b/src/southbridge/amd/amd8111/amd8111_early_smbus.c @@ -21,6 +21,8 @@ static void enable_smbus(void) pci_write_config32(dev, 0x58, SMBUS_IO_BASE | 1); enable = pci_read_config8(dev, 0x41); pci_write_config8(dev, 0x41, enable | (1 << 7)); + /* clear any lingering errors, so the transaction will run */ + outw(inw(SMBUS_IO_BASE + SMBGSTATUS), SMBUS_IO_BASE + SMBGSTATUS); } @@ -40,8 +42,12 @@ static int smbus_wait_until_ready(void) if ((val & 0x800) == 0) { break; } + if(loops == (SMBUS_TIMEOUT / 2)) { + outw(inw(SMBUS_IO_BASE + SMBGSTATUS), + SMBUS_IO_BASE + SMBGSTATUS); + } } while(--loops); - return loops?0:-1; + return loops?0:-2; } static int smbus_wait_until_done(void) @@ -57,7 +63,7 @@ static int smbus_wait_until_done(void) break; } } while(--loops); - return loops?0:-1; + return loops?0:-3; } static int smbus_read_byte(unsigned device, unsigned address) @@ -67,7 +73,7 @@ static int smbus_read_byte(unsigned device, unsigned address) unsigned char byte; if (smbus_wait_until_ready() < 0) { - return -1; + return -2; } /* setup transaction */ @@ -93,7 +99,7 @@ static int smbus_read_byte(unsigned device, unsigned address) /* poll for transaction completion */ if (smbus_wait_until_done() < 0) { - return -1; + return -3; } global_status_register = inw(SMBUS_IO_BASE + SMBGSTATUS); diff --git a/src/southbridge/amd/amd8111/amd8111_ide.c b/src/southbridge/amd/amd8111/amd8111_ide.c index 11f795b0bb..4502bb3c45 100644 --- a/src/southbridge/amd/amd8111/amd8111_ide.c +++ b/src/southbridge/amd/amd8111/amd8111_ide.c @@ -3,6 +3,7 @@ #include #include #include +#include "amd8111.h" static void ide_init(struct device *dev) { diff --git a/src/southbridge/amd/amd8111/amd8111_lpc.c b/src/southbridge/amd/amd8111/amd8111_lpc.c index b0c1672f5d..437ed2e877 100644 --- a/src/southbridge/amd/amd8111/amd8111_lpc.c +++ b/src/southbridge/amd/amd8111/amd8111_lpc.c @@ -6,6 +6,8 @@ #include #include #include +#include +#include "amd8111.h" struct ioapicreg { @@ -87,7 +89,6 @@ static void setup_ioapic(void) static void lpc_init(struct device *dev) { uint8_t byte; - uint16_t word; int pwr_on=-1; printk_debug("lpc_init\n"); @@ -100,14 +101,7 @@ static void lpc_init(struct device *dev) /* posted memory write enable */ byte = pci_read_config8(dev, 0x46); - pci_write_config8(dev, 0x46, byte | (1<<0)); - -//BY LYH - /* Disable AC97 and Ethernet */ - word = pci_read_config16(dev, 0x48); - pci_write_config16(dev, 0x48, word & ~((1<<5)|(1<<6)|(1<<9))); -//BY LYH END - + pci_write_config8(dev, 0x46, byte | (1<<0)); /* power after power fail */ byte = pci_read_config8(dev, 0x43); @@ -118,6 +112,10 @@ static void lpc_init(struct device *dev) } pci_write_config8(dev, 0x43, byte); + /* Enable Port 92 fast reset */ + byte = pci_read_config8(dev, 0x41); + byte |= (1 << 5); + pci_write_config8(dev, 0x41, byte); } @@ -159,6 +157,7 @@ static struct device_operations lpc_ops = { .enable_resources = pci_dev_enable_resources, .init = lpc_init, .scan_bus = walk_static_devices, + .enable = amd8111_enable, }; static struct pci_driver lpc_driver __pci_driver = { @@ -166,3 +165,4 @@ static struct pci_driver lpc_driver __pci_driver = { .vendor = PCI_VENDOR_ID_AMD, .device = PCI_DEVICE_ID_AMD_8111_ISA, }; + diff --git a/src/southbridge/amd/amd8111/amd8111_nic.c b/src/southbridge/amd/amd8111/amd8111_nic.c new file mode 100644 index 0000000000..b3792086a5 --- /dev/null +++ b/src/southbridge/amd/amd8111/amd8111_nic.c @@ -0,0 +1,25 @@ +/* + * (C) 2003 Linux Networx + */ +#include +#include +#include +#include +#include +#include "amd8111.h" + + +static struct device_operations nic_ops = { + .read_resources = pci_dev_read_resources, + .set_resources = pci_dev_set_resources, + .enable_resources = pci_dev_enable_resources, + .enable = amd8111_enable, + .init = 0, + .scan_bus = 0, +}; + +static struct pci_driver nic_driver __pci_driver = { + .ops = &nic_ops, + .vendor = PCI_VENDOR_ID_AMD, + .device = 0x7462, +}; diff --git a/src/southbridge/amd/amd8111/amd8111_usb.c b/src/southbridge/amd/amd8111/amd8111_usb.c index cfef06dee2..46cfabbcda 100644 --- a/src/southbridge/amd/amd8111/amd8111_usb.c +++ b/src/southbridge/amd/amd8111/amd8111_usb.c @@ -3,6 +3,7 @@ #include #include #include +#include "amd8111.h" static void usb_init(struct device *dev) { @@ -25,6 +26,7 @@ static struct device_operations usb_ops = { .enable_resources = pci_dev_enable_resources, .init = usb_init, .scan_bus = 0, + .enable = amd8111_enable, }; static struct pci_driver usb_driver __pci_driver = { diff --git a/src/southbridge/amd/amd8111/amd8111_usb2.c b/src/southbridge/amd/amd8111/amd8111_usb2.c index 924e0e6109..15ed69b0f1 100644 --- a/src/southbridge/amd/amd8111/amd8111_usb2.c +++ b/src/southbridge/amd/amd8111/amd8111_usb2.c @@ -7,6 +7,7 @@ #include #include #include +#include "amd8111.h" static void usb2_init(struct device *dev) { @@ -23,17 +24,17 @@ static void usb2_init(struct device *dev) } -static struct device_operations usb_ops = { +static struct device_operations usb2_ops = { .read_resources = pci_dev_read_resources, .set_resources = pci_dev_set_resources, .enable_resources = pci_dev_enable_resources, .init = usb2_init, .scan_bus = 0, + .enable = amd8111_enable, }; static struct pci_driver usb2_driver __pci_driver = { - .ops = &usb_ops, + .ops = &usb2_ops, .vendor = PCI_VENDOR_ID_AMD, .device = PCI_DEVICE_ID_AMD_8111_USB2, }; - diff --git a/src/southbridge/amd/amd8131/amd8131_bridge.c b/src/southbridge/amd/amd8131/amd8131_bridge.c index dccf962fbd..9d28de4f32 100644 --- a/src/southbridge/amd/amd8131/amd8131_bridge.c +++ b/src/southbridge/amd/amd8131/amd8131_bridge.c @@ -29,6 +29,17 @@ static void pcix_init(device_t dev) word = pci_read_config16(dev, 0xe8); word = 0x0404; pci_write_config16(dev, 0xe8, word); + + /* Set discard unrequested prefetch data */ + word = pci_read_config16(dev, 0x4c); + word |= 1; + pci_write_config16(dev, 0x4c, word); + + /* Set split transaction limits */ + word = pci_read_config16(dev, 0xa8); + pci_write_config16(dev, 0xaa, word); + word = pci_read_config16(dev, 0xac); + pci_write_config16(dev, 0xae, word); return; } @@ -58,14 +69,6 @@ static void ioapic_enable(device_t dev) value &= ~((1 << 1) | (1 << 0)); } pci_write_config32(dev, 0x44, value); - -//BY LYH - value = pci_read_config32(dev, 0x4); - value |= 6; - pci_write_config32(dev, 0x4, value); -//BY LYH END - - } static struct device_operations ioapic_ops = { -- cgit v1.2.3