diff options
author | Ronald G. Minnich <rminnich@gmail.com> | 2006-10-18 15:23:28 +0000 |
---|---|---|
committer | Ronald G. Minnich <rminnich@gmail.com> | 2006-10-18 15:23:28 +0000 |
commit | 31101c9201a536146ac70429e1bd73502ad24527 (patch) | |
tree | e834a9860cecc42a107317b546842eb109905789 /src/mainboard/olpc/btest/mainboard.c | |
parent | 0a3f60775baa549d559b9b89c4777efd43e0c81c (diff) |
add the btest mainboard
git-svn-id: svn://svn.coreboot.org/coreboot/trunk@2459 2b7e53f0-3cfb-0310-b3e9-8179ed1497e1
Diffstat (limited to 'src/mainboard/olpc/btest/mainboard.c')
-rw-r--r-- | src/mainboard/olpc/btest/mainboard.c | 109 |
1 files changed, 109 insertions, 0 deletions
diff --git a/src/mainboard/olpc/btest/mainboard.c b/src/mainboard/olpc/btest/mainboard.c new file mode 100644 index 0000000000..35826cb24d --- /dev/null +++ b/src/mainboard/olpc/btest/mainboard.c @@ -0,0 +1,109 @@ +#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 <pc80/mc146818rtc.h> +#include "chip.h" +#include "../southbridge/amd/cs5536/cs5536_smbus2.h" + +/* Borrowed from mc146818rtc.c */ + +#define CMOS_READ(addr) ({ \ + outb((addr),RTC_PORT(0)); \ + inb(RTC_PORT(1)); \ + }) + +#define CMOS_WRITE(val, addr) ({ \ + outb((addr),RTC_PORT(0)); \ + outb((val),RTC_PORT(1)); \ + }) + +static void write_bit(unsigned char val) { + + unsigned char byte = CMOS_READ(440 / 8); + + /* Don't change it if its already set */ + + if ((byte & 1) == (val & 1)) + return; + + byte &= ~1; + byte |= val & 1; + CMOS_WRITE(val, 440/8); +} + +static unsigned short _getsmbusbase(void) { + unsigned devfn = PCI_DEVFN(0xf, 0); + device_t dev = dev_find_slot(0x0, devfn); + unsigned long addr = pci_read_config32(dev, PCI_BASE_ADDRESS_0); + + return (unsigned short) (addr & ~1); +} + +static void init_dcon(void) { + + int ret = 1; + unsigned short rev = 0; + unsigned short iobase = _getsmbusbase(); + + printk_debug("CHECKING FOR DCON (%x)\n", iobase); + + /* Get the IO base for the SMBUS */ + + rev = do_smbus_read_word(iobase, 0x0D << 1, 0x00); + + if (rev & 0xDC00) { + printk_debug("DCON FOUND - REV %x\n", rev); + + /* Enable the DCON */ + ret = do_smbus_write_word(iobase, 0x0D << 1, 0x01, 0x0069); + if (ret != 0) + printk_debug("DCON ENABLE FAILED\n", ret); + } + else + printk_debug("DCON NOT FOUND (%x)\n", rev); + + write_bit(rev > 0 ? 1 : 0); +} + +static void init(struct device *dev) { +/* + unsigned bus = 0; + unsigned devfn = PCI_DEVFN(0xf, 4); + device_t usb = NULL; + unsigned char usbirq = 0xa; +*/ + + printk_debug("OLPC BTEST ENTER %s\n", __FUNCTION__); + +#if 0 + /* I can't think of any reason NOT to just set this. If it turns out we want this to be + * conditional we can make it a config variable later. + */ + + printk_debug("%s (%x,%x)SET USB PCI interrupt line to %d\n", + __FUNCTION__, bus, devfn, usbirq); + usb = dev_find_slot(bus, devfn); + if (! usb){ + printk_err("Could not find USB\n"); + } else { + pci_write_config8(usb, PCI_INTERRUPT_LINE, usbirq); + } +#endif + + init_dcon(); + printk_debug("OLPC BTEST EXIT %s\n", __FUNCTION__); +} + +static void enable_dev(struct device *dev) +{ + dev->ops->init = init; +} + +struct chip_operations mainboard_olpc_btest_ops = { + CHIP_NAME("olpc btest mainboard ") + .enable_dev = enable_dev, + +}; |