From 07abf2664225e7bd27dcd2f9f4f28410c0d5dc91 Mon Sep 17 00:00:00 2001 From: Andrew Ip Date: Sun, 29 Jun 2003 16:23:58 +0000 Subject: [PATCH] epia-m initial checkin --- src/mainboard/via/epia-m/README | 5 + src/mainboard/via/epia-m/STATUS | 27 + src/mainboard/via/epia-m/do_dumpdev.inc | 8 + src/mainboard/via/epia-m/do_dumpnorth.inc | 1 + src/mainboard/via/epia-m/do_ramtest.inc | 5 + src/mainboard/via/epia-m/dumpdev.inc | 65 +++ src/mainboard/via/epia-m/example.config | 31 ++ src/mainboard/via/epia-m/irq_tables.c | 46 ++ src/mainboard/via/epia-m/mainboard.c | 95 ++++ src/northbridge/via/vt8623/Config | 1 + src/northbridge/via/vt8623/northbridge.c | 106 ++++ src/northbridge/via/vt8623/raminit.inc | 163 ++++++ src/southbridge/via/vt8235/Config | 1 + src/southbridge/via/vt8235/setup_ethernet.inc | 14 + src/southbridge/via/vt8235/setup_ide.inc | 29 + src/southbridge/via/vt8235/southbridge.c | 505 ++++++++++++++++++ 16 files changed, 1102 insertions(+) create mode 100644 src/mainboard/via/epia-m/README create mode 100644 src/mainboard/via/epia-m/STATUS create mode 100644 src/mainboard/via/epia-m/do_dumpdev.inc create mode 100644 src/mainboard/via/epia-m/do_dumpnorth.inc create mode 100644 src/mainboard/via/epia-m/do_ramtest.inc create mode 100644 src/mainboard/via/epia-m/dumpdev.inc create mode 100644 src/mainboard/via/epia-m/example.config create mode 100644 src/mainboard/via/epia-m/irq_tables.c create mode 100644 src/mainboard/via/epia-m/mainboard.c create mode 100644 src/northbridge/via/vt8623/Config create mode 100644 src/northbridge/via/vt8623/northbridge.c create mode 100644 src/northbridge/via/vt8623/raminit.inc create mode 100644 src/southbridge/via/vt8235/Config create mode 100644 src/southbridge/via/vt8235/setup_ethernet.inc create mode 100644 src/southbridge/via/vt8235/setup_ide.inc create mode 100644 src/southbridge/via/vt8235/southbridge.c diff --git a/src/mainboard/via/epia-m/README b/src/mainboard/via/epia-m/README new file mode 100644 index 0000000000..d18ef73df3 --- /dev/null +++ b/src/mainboard/via/epia-m/README @@ -0,0 +1,5 @@ +To enable flash write, + +$ setpci -s 0:11.0 40.b=54 + +-Andrew diff --git a/src/mainboard/via/epia-m/STATUS b/src/mainboard/via/epia-m/STATUS new file mode 100644 index 0000000000..6c9d41ab10 --- /dev/null +++ b/src/mainboard/via/epia-m/STATUS @@ -0,0 +1,27 @@ +# These are keyword-value pairs. +# a : separates the keyword from the value +# the value is arbitrary text delimited by newline. +# continuation, if needed, will be via the \ at the end of a line +# comments are indicated by a '#' as the first character. +# the keywords are case-INSENSITIVE +owner: Andrew Ip +email: aip@cwlinux.com +#status: One of unsupported, unstable, stable +status: unstable +explanation: slow performance +flash-types: SST 39SF020A +payload-types: etherboot, memtest +# e.g. linux, plan 9, wince, etc. +OS-types: linux +# e.g. "Plan 9 interrupts don't work on this chipset" +OS-issues: +console-types: serial +# vga is unsupported, unstable, or stable +vga: unsupported +# Last-known-good follows the internationl date standard: day/month/year +last-known-good: 0/0/0000 +Comments: +Links: +Mainboard-revision: +# What other mainboards are like this one? List them here. +AKA: diff --git a/src/mainboard/via/epia-m/do_dumpdev.inc b/src/mainboard/via/epia-m/do_dumpdev.inc new file mode 100644 index 0000000000..6526381a40 --- /dev/null +++ b/src/mainboard/via/epia-m/do_dumpdev.inc @@ -0,0 +1,8 @@ + movl $0x0, %ecx + CALLSP(dumpdev) + + movl $CONFIG_ADDR(0,0x88,0), %ecx + CALLSP(dumpdev) + + movl $CONFIG_ADDR(0,0x89,0), %ecx + CALLSP(dumpdev) diff --git a/src/mainboard/via/epia-m/do_dumpnorth.inc b/src/mainboard/via/epia-m/do_dumpnorth.inc new file mode 100644 index 0000000000..abed7e6391 --- /dev/null +++ b/src/mainboard/via/epia-m/do_dumpnorth.inc @@ -0,0 +1 @@ + CALLSP(dumpnorth) diff --git a/src/mainboard/via/epia-m/do_ramtest.inc b/src/mainboard/via/epia-m/do_ramtest.inc new file mode 100644 index 0000000000..e22381e142 --- /dev/null +++ b/src/mainboard/via/epia-m/do_ramtest.inc @@ -0,0 +1,5 @@ + mov $0x00000000, %eax + mov $0x0009ffff, %ebx + mov $16, %ecx + + CALLSP(ramtest) diff --git a/src/mainboard/via/epia-m/dumpdev.inc b/src/mainboard/via/epia-m/dumpdev.inc new file mode 100644 index 0000000000..dea330900a --- /dev/null +++ b/src/mainboard/via/epia-m/dumpdev.inc @@ -0,0 +1,65 @@ + /* Dump the first 64 longs for devfn 0, bus 0 + * i.e. the north bridge. + */ + +#define CS_WRITE_BYTE(addr, byte) \ + movl $addr, %eax ; \ + movl $byte, %edx ; \ + PCI_WRITE_CONFIG_BYTE + +#define CS_WRITE_WORD(addr, word) \ + movl $addr, %eax ; \ + movl $word, %ecx ; \ + PCI_WRITE_CONFIG_WORD + +#define CS_WRITE_LONG(addr, dword) \ + movl $addr, %eax ; \ + movl $dword, %ecx ; \ + PCI_WRITE_CONFIG_DWORD + +#define DEVFN(device, function) (((device) << 3) + (function)) +#ifndef CONFIG_ADDR +#define CONFIG_ADDR(bus,devfn,where) (((bus) << 16) | ((devfn) << 8) | (where)) +#endif + + jmp dumpdev_skip + .section ".rom.data" + +dd_banner: .string "dump device: " +dd_ret: .string "\r\n" +dd_done: .string "Done.\r\n" +dd_before: .string "Before setting values: \r\n" +dd_after: .string "After setting values: \r\n" + .previous + +# expects device devfn in %ecx + +dumpdev: + mov %esp, %ebp + CONSOLE_INFO_TX_STRING($dd_banner) + CONSOLE_INFO_TX_HEX32(%ecx) + CONSOLE_INFO_TX_STRING($dd_ret) +# xorl %ecx, %ecx +1: + CONSOLE_INFO_TX_HEX8(%cl) + CONSOLE_INFO_TX_CHAR($':') + CONSOLE_INFO_TX_CHAR($' ') + +2: + movl %ecx, %eax + PCI_READ_CONFIG_BYTE + CONSOLE_INFO_TX_HEX8(%al) + CONSOLE_INFO_TX_CHAR($' ') + + incl %ecx + testb $0xf, %cl + jnz 2b + + CONSOLE_INFO_TX_CHAR($'\r') + CONSOLE_INFO_TX_CHAR($'\n') + cmpb $0, %cl + jne 1b + CONSOLE_INFO_TX_STRING($dd_done) + mov %ebp, %esp + RETSP +dumpdev_skip: diff --git a/src/mainboard/via/epia-m/example.config b/src/mainboard/via/epia-m/example.config new file mode 100644 index 0000000000..6e72081c87 --- /dev/null +++ b/src/mainboard/via/epia-m/example.config @@ -0,0 +1,31 @@ +# +# LinuxBIOS config file for: VIA epia mini-itx +# + +target /opt/cwlinux/buildrom/epia + +# via epia +mainboard via/epia + +# Enable Serial Console for debugging +option SERIAL_CONSOLE=1 +option TTYS0_BAUD=115200 +option DEFAULT_CONSOLE_LOGLEVEL=9 +option DEBUG=1 + +# Use 256KB Standard Flash as Normal BIOS +option RAMTEST=1 +option USE_GENERIC_ROM=1 +option STD_FLASH=1 +#option ZKERNEL_START=0xfffc0000 +option ROM_SIZE=262144 + +# payload size = 192KB +option PAYLOAD_SIZE=196608 + +# use ELF Loader to load Etherboot +option USE_ELF_BOOT=1 + +# Use Etherboot as our payload +payload /opt/cwlinux/etherboot/src/bin32/via-rhine.ebi + diff --git a/src/mainboard/via/epia-m/irq_tables.c b/src/mainboard/via/epia-m/irq_tables.c new file mode 100644 index 0000000000..63b79849c1 --- /dev/null +++ b/src/mainboard/via/epia-m/irq_tables.c @@ -0,0 +1,46 @@ +/* This file was generated by getpir.c, do not modify! + (but if you do, please run checkpir on it to verify) + Contains the IRQ Routing Table dumped directly from your memory , wich BIOS sets up + + Documentation at : http://www.microsoft.com/hwdev/busbios/PCIIRQ.HTM +*/ + +#include + +const struct irq_routing_table intel_irq_routing_table = { + PIRQ_SIGNATURE, /* u32 signature */ + PIRQ_VERSION, /* u16 version */ + 32+16*5, /* there can be total 5 devices on the bus */ + 0, /* Where the interrupt router lies (bus) */ + 0, /* Where the interrupt router lies (dev) */ + 0x1c20, /* IRQs devoted exclusively to PCI usage */ + 0, /* Vendor */ + 0, /* Device */ + 0, /* Crap (miniport) */ + { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, /* u8 rfu[11] */ +#if 0 + 0x58, /* u8 checksum , this hase to set to some value that would give 0 after the sum of all bytes for this structure (including checksum) */ + { + {0,0xa0, {{0x2, 0xdeb8}, {0x3, 0xdeb8}, {0x4, 0xdeb8}, {0x1, 0xdeb8}}, 0x1, 0}, + {0,0x98, {{0x1, 0xdeb8}, {0x2, 0xdeb8}, {0x3, 0xdeb8}, {0x4, 0xdeb8}}, 0x2, 0}, + {0,0x50, {{0x4, 0xdeb8}, {0x1, 0xdeb8}, {0x2, 0xdeb8}, {0x3, 0xdeb8}}, 0x3, 0}, + {0,0x68, {{0x2, 0xdeb8}, {0x3, 0xdeb8}, {0x4, 0xdeb8}, {0x1, 0xdeb8}}, 0x4, 0}, + {0,0x8, {{0x1, 0xdeb8}, {0x2, 0xdeb8}, {0x3, 0xdeb8}, {0x4, 0xdeb8}}, 0, 0}, + {0x50,0, {{0, 0}, {0, 0}, {0, 0}, {0, 0}}, 0, 0} + } +#else + 0xac, /* u8 checksum , this hase to set to some value that would give 0 after the sum of all bytes for this structure (including checksum) */ + { + /* ethernet */ + {0,0x90, {{0x3, 0xdeb8}, {0x4, 0xdeb8}, {0x2, 0xdeb8}, {0x1, 0xdeb8}}, 0x1, 0}, + /* usb */ + {0,0x80, {{0x2, 0xdeb8}, {0x3, 0xdeb8}, {0x4, 0xdeb8}, {0x1, 0xdeb8}}, 0x2, 0}, + /* pci */ + {0,0xa0, {{0x1, 0xdeb8}, {0x4, 0xdeb8}, {0x3, 0xdeb8}, {0x2, 0xdeb8}}, 0x3, 0}, + /* audio */ + {0,0x8d, {{0x4, 0xdeb8}, {0x3, 0xdeb8}, {0x2, 0xdeb8}, {0x1, 0xdeb8}}, 0x0, 0}, + /* 1394 */ + {0,0x68, {{0x4, 0xdeb8}, {0x3, 0xdeb8}, {0x2, 0xdeb8}, {0x1, 0xdeb8}}, 0x3, 0} + } +#endif +}; diff --git a/src/mainboard/via/epia-m/mainboard.c b/src/mainboard/via/epia-m/mainboard.c new file mode 100644 index 0000000000..578bccee36 --- /dev/null +++ b/src/mainboard/via/epia-m/mainboard.c @@ -0,0 +1,95 @@ +#include +#include +#include +#include + +#include + +//static const unsigned char usbIrqs[4] = { 11, 5, 10, 12 }; +static const unsigned char usbIrqs[4] = { 11, 12, 10, 5 }; +static const unsigned char enetIrqs[4] = { 11, 5, 10, 12 }; +//static const unsigned char slotIrqs[4] = { 10, 12, 5, 11 }; +static const unsigned char slotIrqs[4] = { 12, 10, 5, 11 }; +static const unsigned char firewireIrqs[4] = { 12, 10, 5, 11 }; + +/* + Our IDSEL mappings are as follows + PCI slot is AD31 (device 15) (00:14.0) + Southbridge is AD28 (device 12) (00:11.0) +*/ +static void pci_routing_fixup(void) +{ + struct pci_dev *dev; + + dev = pci_find_device(PCI_VENDOR_ID_VIA, 0x3177, 0); + if (dev != NULL) { + /* + * initialize PCI interupts - these assignments depend + * on the PCB routing of PINTA-D + * + * PINTA = IRQ11 + * PINTB = IRQ12 + * PINTC = IRQ10 + * PINTD = IRQ5 + */ + pci_write_config_byte(dev, 0x55, 0xb0); + pci_write_config_byte(dev, 0x56, 0xac); + pci_write_config_byte(dev, 0x57, 0x50); + + } +#if 1 + // firewire built into southbridge + printk_info("setting firewire\n"); + pci_assign_irqs(0, 0x0d, firewireIrqs); + + // Standard usb components + printk_info("setting usb\n"); + pci_assign_irqs(0, 0x10, usbIrqs); + + // Ethernet built into southbridge + printk_info("setting ethernet\n"); + pci_assign_irqs(0, 0x12, enetIrqs); + + // PCI slot + printk_info("setting pci slot\n"); + pci_assign_irqs(0, 0x14, slotIrqs); + +#endif + + printk_debug("4d0: 0x%02x\n", inb(0x4d0)); + printk_debug("4d1: 0x%02x\n", inb(0x4d1)); +#if 0 + outb(0, 0x4d0); + outb(0, 0x4d1); +#endif + printk_debug("4d0: 0x%02x\n", inb(0x4d0)); + printk_debug("4d1: 0x%02x\n", inb(0x4d1)); +} + + +void +mainboard_fixup() +{ + printk_info("Mainboard fixup\n"); + + northbridge_fixup(); + southbridge_fixup(); +} + +void +final_southbridge_fixup() +{ + printk_info("Southbridge fixup\n"); + + nvram_on(); +// keyboard_on(); + pci_routing_fixup(); +} + +void +final_mainboard_fixup() +{ + printk_info("Final mainboard fixup\n"); + final_southbridge_fixup(); +} + diff --git a/src/northbridge/via/vt8623/Config b/src/northbridge/via/vt8623/Config new file mode 100644 index 0000000000..5191cb272f --- /dev/null +++ b/src/northbridge/via/vt8623/Config @@ -0,0 +1 @@ +object northbridge.o diff --git a/src/northbridge/via/vt8623/northbridge.c b/src/northbridge/via/vt8623/northbridge.c new file mode 100644 index 0000000000..06fc86d8cf --- /dev/null +++ b/src/northbridge/via/vt8623/northbridge.c @@ -0,0 +1,106 @@ +#include +#include +#include +#include +#include + + +static unsigned long __sizeram(void) +{ + unsigned long totalmem; + unsigned char bank, mem, prevmem; + // fix me later -- there are two more banks at 0x56 and 0x57 + unsigned long firstbank = 0x5a, lastbank = 0x5d; + u8 sma_status, sma_size, sma_size_bits; + u8 val; + + struct pci_dev *pcidev; + + pcidev = pci_find_slot(0, PCI_DEVFN(0,0)); + + if (! pcidev) + return 0; + + pci_read_config_byte(pcidev, 0xe1, &sma_status); + sma_size_bits = (sma_status >> 4) & 0x07; + if (sma_size_bits > 7) + sma_size = 0; + else + sma_size = 0x01 << sma_size_bits; + + for(totalmem = mem = prevmem = 0, bank = firstbank; + bank <= lastbank; bank++) { + pci_read_config_byte(pcidev, bank, &mem); + // sanity check. If the mem value is < prevmem, + // that is an error, so skip this step. + if (mem < prevmem) { + printk_err("ERROR: bank 0x%x, mem 0x%x TOO SMALL\n", + bank, prevmem); + printk_err("Should be >= 0x%x\n", prevmem); + } else + totalmem += (mem - prevmem) * 16; + prevmem = mem; + } + + totalmem -= sma_size; + totalmem *= 1024; +#if 0 + printk_info("sizeram: returning 0x%x KB\n", totalmem); + printk_info("sizeram: NOT returning 0x%x KB\n", totalmem); + printk_info("sizeram: there are still some SPD problems ... \n"); + totalmem = 64 * 1024; + printk_info("sizeram: SO we return only 0x%x KB\n", totalmem); +#endif + return totalmem; +} + +struct mem_range *sizeram(void) +{ + static struct mem_range mem[3]; + mem[0].basek = 0; + mem[0].sizek = 640; + mem[1].basek = 1024; + mem[1].sizek = __sizeram(); + mem[2].basek = 0; + mem[2].sizek = 0; + if (mem[1].sizek == 0) { + mem[1].sizek = 64*1024; + } + mem[1].sizek -= mem[1].basek; + return mem; +} + +#ifdef HAVE_FRAMEBUFFER +void framebuffer_on() +{ + unsigned long devfn; + u16 command; + + devfn = PCI_DEVFN(0, 1); + pcibios_read_config_word(0, devfn, 0x3e, &command); + command |= 0x08; + pcibios_write_config_word(0, devfn, 0x3e, command); +} +#endif + +/* + * This fixup is based on capturing values from an Award bios. Without + * this fixup the DMA write performance is awful (i.e. hdparm -t /dev/hda is + * slower than normal, ethernet drops packets). + * Apparently these registers govern some sort of bus master behavior. + */ +void northbridge_fixup(void) +{ + struct pci_dev *pcidev = pci_find_slot(0, PCI_DEVFN(0,0)); + + if (pcidev) { + pci_write_config_byte(pcidev, 0x70, 0xc0); + pci_write_config_byte(pcidev, 0x71, 0x88); +// pci_write_config_byte(pcidev, 0x72, 0xec); +// pci_write_config_byte(pcidev, 0x73, 0x0c); +// pci_write_config_byte(pcidev, 0x74, 0x0e); + pci_write_config_byte(pcidev, 0x75, 0x01); + pci_write_config_byte(pcidev, 0x76, 0x52); + } +} + diff --git a/src/northbridge/via/vt8623/raminit.inc b/src/northbridge/via/vt8623/raminit.inc new file mode 100644 index 0000000000..632fea2c28 --- /dev/null +++ b/src/northbridge/via/vt8623/raminit.inc @@ -0,0 +1,163 @@ +/* + * raminit.inc: Setting registers to their recommended values for vt8633 + * + * + * Copyright 2002 Cwlinux Limited + * + * 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; either version 2 of the License, or + * (at your option) any later version. + * + * 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., 675 Mass Ave, Cambridge, MA 02139, USA. + * + */ + +#define loop200 $0x5000 +#define loop100 $0x2500 + +raminit: + intel_chip_post_macro(0x35) + + CS_WRITE($0x75, $0x08) + + /* since we only support epia-m at the moment, only ddr is supported */ + /* setup cpu */ + CS_WRITE($0x50, $0xc8) + CS_WRITE($0x51, $0xde) + CS_WRITE($0x52, $0xcf) + CS_WRITE($0x53, $0x88) + CS_WRITE($0x55, $0x07) + + /* DRAM MA Map Type */ + CS_WRITE($0x58, $0x71) + + /* DRAM bank 0 - 3 size = 512M */ + CS_WRITE($0x5a, $0x08) + CS_WRITE($0x5b, $0x08) + CS_WRITE($0x5c, $0x08) + CS_WRITE($0x5d, $0x08) + + /* set DRAM Timing for all banks */ + CS_WRITE($0x64, $0xe6) + + /* set DRAM type to DDR */ + CS_WRITE($0x60, $0x02) +#if 0 + CS_WRITE($0x61, $0xaa) + CS_WRITE($0x62, $0xaf) + CS_WRITE($0x63, $0xa0) +#endif + /* DRAM Arbitration Timer */ + CS_WRITE($0x65, $0x32) + CS_WRITE($0x66, $0x01) + CS_WRITE($0x68, $0x59) + + /* DRAM Frequency */ + CS_WRITE($0x54, $0xe0) + CS_WRITE($0x69, $0x2d) + + /* Enable CKE */ + CS_WRITE($0x6b, $0x10) + + /* Disable DRAM refresh */ + CS_WRITE($0x6a, $0x00) + + /* Set heavy drive */ + CS_WRITE($0x6d, $0x44) + + /* NOP Command Enable */ + CS_WRITE($0x6b, $0x01) + /* read a double word from any address of the dimm */ + movl %eax, %ds:(%esi) + DELAY(loop200) + + /* All bank Precharge Command Enable */ + CS_WRITE($0x6b, $0x02) + movl %eax, %ds:(%esi) + + /* MSR Enable */ + CS_WRITE($0x6b, $0x03) + /* read 0x2000h */ + movl $0x2000, %ecx + movl (%ecx), %eax +// movl $0x4002000, %ecx +// movl (%ecx), %eax + /* read 0x800h */ + movl $0x800, %ecx + movl (%ecx), %eax +// movl $0x4000800, %ecx +// movl (%ecx), %eax + + /* All banks Precharge Command Enable */ + CS_WRITE($0x6b, $0x02) + movl %eax, %ds:(%esi) + + /* CBR Cycle Enable */ + CS_WRITE($0x6b, $0x04) + /* Read 8 times */ + movl %eax, %ds:(%esi) + DELAY(loop100) + movl %eax, %ds:(%esi) + DELAY(loop100) + movl %eax, %ds:(%esi) + DELAY(loop100) + movl %eax, %ds:(%esi) + DELAY(loop100) + movl %eax, %ds:(%esi) + DELAY(loop100) + movl %eax, %ds:(%esi) + DELAY(loop100) + movl %eax, %ds:(%esi) + DELAY(loop100) + movl %eax, %ds:(%esi) + DELAY(loop100) + + /* MSR Enable */ + CS_WRITE($0x6b, $0x03) + /* 0x150 if CAS Latency 2 or 0x350 CAS Latency 2.5 */ + movl $0x350, %ecx + movl (%ecx), %eax +// movl $0x4000350, %ecx +// movl (%ecx), %eax + + /* Normal SDRAM Mode */ + CS_WRITE($0x6b, $0x58) + + /* Set the refreash rate */ + CS_WRITE($0x6a, $0x86) + + CS_WRITE($0x67, $0x39) + + /* pci */ + CS_WRITE($0x70, $0x82) + CS_WRITE($0x73, $0x01) + CS_WRITE($0x76, $0x50) + + CS_WRITE($0x71, $0xc8) + +#if 0 + CS_WRITE($0x80, $0x0f) + CS_WRITE($0x84, $0x80) + CS_WRITE($0x88, $0x02) + + CS_WRITE($0xb8, $0x8a) + CS_WRITE($0xe0, $0x81) + CS_WRITE($0xe1, $0xdd) + CS_WRITE($0xe2, $0x42) +#endif + /* graphics aperture base */ + CS_WRITE($0x13, $0xd0) + + CS_WRITE($0x56, $0x10) + CS_WRITE($0x57, $0x10) + + intel_chip_post_macro(0x36) + diff --git a/src/southbridge/via/vt8235/Config b/src/southbridge/via/vt8235/Config new file mode 100644 index 0000000000..094297c0ab --- /dev/null +++ b/src/southbridge/via/vt8235/Config @@ -0,0 +1 @@ +object southbridge.o diff --git a/src/southbridge/via/vt8235/setup_ethernet.inc b/src/southbridge/via/vt8235/setup_ethernet.inc new file mode 100644 index 0000000000..d20253a75f --- /dev/null +++ b/src/southbridge/via/vt8235/setup_ethernet.inc @@ -0,0 +1,14 @@ +/* + * This early setup is a handy place to enable the Ethernet if the user wants + * it. + */ +enable_eth: + movl $CONFIG_ADDR(0, SUPERIO_DEVFN, 0x50), %eax + PCI_READ_CONFIG_DWORD + + /* Turn on just the Ethernet and disable modem */ + orl $0x1080, %eax + mov %eax, %ecx + + movl $CONFIG_ADDR(0, SUPERIO_DEVFN, 0x50), %eax + PCI_WRITE_CONFIG_DWORD diff --git a/src/southbridge/via/vt8235/setup_ide.inc b/src/southbridge/via/vt8235/setup_ide.inc new file mode 100644 index 0000000000..e1403e15bb --- /dev/null +++ b/src/southbridge/via/vt8235/setup_ide.inc @@ -0,0 +1,29 @@ +config_ide: + movl $CONFIG_ADDR(0, 0x88, 0x50), %eax + movb $0x00, %dl + PCI_WRITE_CONFIG_BYTE + + movl $CONFIG_ADDR(0, 0x89, 0x04), %eax + movb $0x07, %dl + PCI_WRITE_CONFIG_BYTE + + movl $CONFIG_ADDR(0, 0x89, 0x40), %eax + movb $0x03, %dl + PCI_WRITE_CONFIG_BYTE + +// This early setup switches IDE into compatibility mode before PCI gets +// a chance to assign I/Os +#if (!ENABLE_IDE_NATIVE_MODE) + movl $CONFIG_ADDR(0, 0x89, 0x42), %eax +// movb $0x09, %dl + movb $0x00, %dl + PCI_WRITE_CONFIG_BYTE + + movl $CONFIG_ADDR(0, 0x89, 0x3c), %eax + movb $0x0e, %dl + PCI_WRITE_CONFIG_BYTE + + movl $CONFIG_ADDR(0, 0x89, 0x3d), %eax + movb $0x00, %dl + PCI_WRITE_CONFIG_BYTE +#endif diff --git a/src/southbridge/via/vt8235/southbridge.c b/src/southbridge/via/vt8235/southbridge.c new file mode 100644 index 0000000000..765f98e7cf --- /dev/null +++ b/src/southbridge/via/vt8235/southbridge.c @@ -0,0 +1,505 @@ +#include +#include +#include +#include +#include +#include + + +// #define IDE_NATIVE_MODE 1 + +void usb_on() +{ + unsigned char regval; + + /* Base 8235 controller */ + struct pci_dev *dev0 = pci_find_device(PCI_VENDOR_ID_VIA, \ + 0x3177, 0); + /* USB controller 1 */ + struct pci_dev *dev1 = pci_find_device(PCI_VENDOR_ID_VIA, \ + 0x3038, 0); + /* USB controller 2 */ + struct pci_dev *dev2 = pci_find_device(PCI_VENDOR_ID_VIA, \ + 0x3038, \ + dev1); + /* USB controller 3 */ + struct pci_dev *dev3 = pci_find_device(PCI_VENDOR_ID_VIA, \ + 0x3038, \ + dev2); +#if ENABLE_VT8235_USB + if(dev0) { + pci_read_config_byte(dev0, 0x50, ®val); + regval &= ~(0x36); + pci_write_config_byte(dev0, 0x50, regval); + } + + /* enable USB1 */ + if(dev1) { + pci_write_config_byte(dev1, 0x3c, 0x05); + pci_write_config_byte(dev1, 0x04, 0x07); + } + + /* enable USB2 */ + if(dev2) { + pci_write_config_byte(dev2, 0x3c, 0x05); + pci_write_config_byte(dev2, 0x04, 0x07); + } + + /* enable USB3 */ + if(dev3) { + pci_write_config_byte(dev3, 0x3c, 0x05); + pci_write_config_byte(dev3, 0x04, 0x07); + } + +#else + if(dev0) { + pci_read_config_byte(dev0, 0x50, ®val); + regval |= 0x36; + pci_write_config_byte(dev0, 0x50, regval); + } + + /* disable USB1 */ + if(dev1) { + pci_write_config_byte(dev1, 0x3c, 0x00); + pci_write_config_byte(dev1, 0x04, 0x00); + } + + /* disable USB2 */ + if(dev2) { + pci_write_config_byte(dev2, 0x3c, 0x00); + pci_write_config_byte(dev2, 0x04, 0x00); + } + + /* disable USB3 */ + if(dev3) { + pci_write_config_byte(dev3, 0x3c, 0x00); + pci_write_config_byte(dev3, 0x04, 0x00); + } +#endif +} + +void keyboard_on() +{ + unsigned char regval; + + /* Base 8235 controller */ + struct pci_dev *dev0 = pci_find_device(PCI_VENDOR_ID_VIA, \ + 0x3177, 0); + + if (dev0) { + pci_read_config_byte(dev0, 0x51, ®val); +// regval |= 0x0f; + /* !!!FIX let's try this */ + regval |= 0x1d; + pci_write_config_byte(dev0, 0x51, regval); + } + pc_keyboard_init(); + +} + +void nvram_on() +{ +} + + +/* + * Enable the ethernet device and turn off stepping (because it is integrated + * inside the southbridge) + */ +void ethernet_fixup() +{ + struct pci_dev *dev, *edev; + u8 byte; + + printk_info("Ethernet fixup\n"); + + edev = pci_find_device(PCI_VENDOR_ID_VIA, 0x3065, 0); + if (edev != NULL) { + printk_debug("Configuring VIA LAN\n"); +#if 0 + /* We don't need stepping - though the device supports it */ + pci_read_config_byte(edev, PCI_COMMAND, &byte); + byte &= ~PCI_COMMAND_WAIT; + pci_write_config_byte(edev, PCI_COMMAND, byte); + + /* turn on master and pio */ + pci_read_config_byte(edev, PCI_COMMAND, &byte); + byte = byte | PCI_COMMAND_MASTER|PCI_COMMAND_IO; + pci_write_config_byte(edev, PCI_COMMAND, byte); +#endif + } else { + printk_debug("VIA LAN not found\n"); + } +} + + +#if 1 +void southbridge_fixup() +{ + unsigned char enables; + struct pci_dev *dev0; + struct pci_dev *dev1; + struct pci_dev *devpwr; +#if 0 + /* Base 8235 controller */ + dev0 = pci_find_device(PCI_VENDOR_ID_VIA, 0x3177, 0); + /* IDE controller */ + dev1 = pci_find_device(PCI_VENDOR_ID_VIA, 0x0571, 0); + + /* Map 4MB of FLASH into the address space */ + pci_write_config_byte(dev0, 0x41, 0x7f); + + /* these follows award's values */ + pci_write_config_byte(dev0, 0x40, 0x45); + pci_write_config_byte(dev0, 0x42, 0xf0); + pci_write_config_byte(dev0, 0x4e, 0x0a); + pci_write_config_byte(dev0, 0x4f, 0x08); + pci_write_config_byte(dev0, 0x50, 0x81); + pci_write_config_byte(dev0, 0x51, 0x1d); +// pci_write_config_byte(dev0, 0x52, 0x09); + pci_write_config_byte(dev0, 0x53, 0x00); + pci_write_config_byte(dev0, 0x58, 0x20); + pci_write_config_byte(dev0, 0x5b, 0x00); + + /* ide */ + /* these follows award's values */ + pci_write_config_byte(dev1, 0x40, 0x03); + pci_write_config_byte(dev1, 0x41, 0xf2); + pci_write_config_byte(dev1, 0x42, 0x09); + pci_write_config_byte(dev1, 0x43, 0x05); + pci_write_config_byte(dev1, 0x44, 0x18); + pci_write_config_byte(dev1, 0x45, 0x1c); + pci_write_config_byte(dev1, 0x4b, 0xa8); + pci_write_config_byte(dev1, 0x4c, 0x3f); + pci_write_config_byte(dev1, 0x4f, 0x20); + + pci_write_config_byte(dev1, 0x50, 0x17); + pci_write_config_byte(dev1, 0x51, 0x17); + pci_write_config_byte(dev1, 0x52, 0x17); + pci_write_config_byte(dev1, 0x53, 0xe2); + pci_write_config_byte(dev1, 0x54, 0x0c); + pci_write_config_byte(dev1, 0x55, 0x03); + + /* Use compatability mode - per award bios */ + pci_write_config_dword(dev1, 0x10, 0x0); + pci_write_config_dword(dev1, 0x14, 0x0); + pci_write_config_dword(dev1, 0x18, 0x0); + pci_write_config_dword(dev1, 0x1c, 0x0); + + ethernet_fixup(); + + usb_on(); +#endif +} + +#else +void southbridge_fixup() +{ + unsigned char enables; + struct pci_dev *dev0; + struct pci_dev *dev1; + struct pci_dev *devpwr; + + /* Base 8235 controller */ + dev0 = pci_find_device(PCI_VENDOR_ID_VIA, 0x3177, 0); + /* IDE controller */ + dev1 = pci_find_device(PCI_VENDOR_ID_VIA, 0x0571, 0); + + /* enable the internal I/O decode */ +#if 0 + enables = pci_read_config_byte(dev0, 0x6C, &enables); + enables |= 0x80; + pci_write_config_byte(dev0, 0x6C, enables); +#endif + /* follow award */ + enables = pci_read_config_byte(dev0, 0x6C, &enables); + enables = 0x00; + pci_write_config_byte(dev0, 0x6C, enables); + + /* Map 4MB of FLASH into the address space */ + pci_write_config_byte(dev0, 0x41, 0x7f); + /* let's try 0x0 to see what's happen */ +// pci_write_config_byte(dev0, 0x41, 0x00); + + /* + * Set bit 6 of 0x40, because Award does it (IO recovery time) + * IMPORTANT FIX - EISA 0x4d0 decoding must be on so that PCI + * interrupts can be properly marked as level triggered. + */ + enables = pci_read_config_byte(dev0, 0x40, &enables); + enables |= 0x45; + pci_write_config_byte(dev0, 0x40, enables); + + /* Set 0x42 to 0xf0 to match Award bios */ + enables = pci_read_config_byte(dev0, 0x42, &enables); + enables |= 0xf0; + pci_write_config_byte(dev0, 0x42, enables); + + /* Set bit 3 of 0x4a, to match award (dummy pci request) */ +// enables = pci_read_config_byte(dev0, 0x4a, &enables); +// enables |= 0x08; +// pci_write_config_byte(dev0, 0x4a, enables); + + /* Set bit 3 of 0x4f to match award (use INIT# as cpu reset) */ + enables = pci_read_config_byte(dev0, 0x4f, &enables); + enables |= 0x08; + pci_write_config_byte(dev0, 0x4f, enables); + + /* Set 0x58 to 0x03 to match Award */ + pci_write_config_byte(dev0, 0x58, 0x03); +#if 0 + /* enable the ethernet/RTC */ + if(dev0) { + pci_read_config_byte(dev0, 0x51, &enables); + enables |= 0x18; + pci_write_config_byte(dev0, 0x51, enables); + } +#endif +#ifndef DISABLE_SOUTHBRIDGE_COM_PORTS + /* enable com1 and com2. */ + enables = pci_read_config_byte(dev0, 0x6e, &enables); + /* + * 0x80 is enable com port b, 0x10 is to make it com2, 0x8 is enable + * com port a as com1 + */ +#if 0 + enables = 0x80 | 0x10 | 0x8 ; + pci_write_config_byte(dev0, 0x6e, enables); +#endif + /* following award */ + enables = 0x00; + pci_write_config_byte(dev0, 0x6e, enables); + /* + * note: this is also a redo of some port of assembly, but we want + * everything up. + * set com1 to 115 kbaud + * not clear how to do this yet. + * forget it; done in assembly. + */ +#endif + + /* + * enable IDE, since Linux won't do it. + * First do some more things to devfn (17,0) + * note: this should already be cleared, according to the book. + */ + pci_read_config_byte(dev0, 0x50, &enables); + printk_debug("IDE enable in reg. 50 is 0x%x\n", enables); + enables &= ~8; // need manifest constant here! + printk_debug("set IDE reg. 50 to 0x%x\n", enables); + pci_write_config_byte(dev0, 0x50, enables); + + /* moved it to setupide.inc */ +#if 0 + /* set default interrupt values (IDE) */ + pci_read_config_byte(dev0, 0x4c, &enables); + printk_debug("IRQs in reg. 4c are 0x%x\n", enables & 0xf); + /* clear out whatever was there. */ + enables &= ~0xf; + enables = 44; + printk_debug("setting reg. 4c to 0x%x\n", enables); + pci_write_config_byte(dev0, 0x4c, enables); +#endif + +#if 1 + /* enable serial irq */ + pci_write_config_byte(dev0, 0x52, 0x09); + + /* dma */ + pci_write_config_byte(dev0, 0x53, 0x00); + + /* diskable dynamic clock stop */ + pci_write_config_byte(dev0, 0x5b, 0x00); + +// pci_write_config_byte(dev0, 0x6c, 0x00); +// pci_write_config_byte(dev0, 0x6e, 0x00); + + /* + * set up the serial port interrupts. + * com2 to 3, com1 to 4 + */ +// pci_write_config_byte(dev0, 0x46, 0x04); +// pci_write_config_byte(dev0, 0x47, 0x03); +#endif +#if 1 + /* + * IDE setup + */ +#if !(ENABLE_IDE_NATIVE_MODE) + /* + * Run the IDE controller in 'compatiblity mode - i.e. don't use PCI + * interrupts. Using PCI ints confuses linux for some reason. + */ + + pci_read_config_byte(dev1, 0x42, &enables); + printk_debug("enables in reg 0x42 0x%x\n", enables); + enables &= ~0xc0; + pci_write_config_byte(dev1, 0x42, enables); + pci_read_config_byte(dev1, 0x42, &enables); + printk_debug("enables in reg 0x42 read back as 0x%x\n", enables); +#endif + + pci_read_config_byte(dev1, 0x40, &enables); + printk_debug("enables in reg 0x40 0x%x\n", enables); + enables |= 3; + pci_write_config_byte(dev1, 0x40, enables); + pci_read_config_byte(dev1, 0x40, &enables); + printk_debug("enables in reg 0x40 read back as 0x%x\n", enables); + + /* Enable prefetch buffers */ + pci_read_config_byte(dev1, 0x41, &enables); + enables |= 0xf0; + pci_write_config_byte(dev1, 0x41, enables); + + /* Lower thresholds (cause award does it) */ + pci_read_config_byte(dev1, 0x43, &enables); + enables &= ~0x0f; + enables |= 0x05; + pci_write_config_byte(dev1, 0x43, enables); + + /* PIO read prefetch counter (cause award does it) */ + pci_write_config_byte(dev1, 0x44, 0x18); + + /* Use memory read multiple */ + pci_write_config_byte(dev1, 0x45, 0x1c); + + /* address decoding. */ + pci_read_config_byte(dev1, 0x9, &enables); + printk_debug("enables in reg 0x9 0x%x\n", enables); + /* by the book, set the low-order nibble to 0xa. */ +#if ENABLE_IDE_NATIVE_MODE + enables &= ~0xf; + /* cf/cg silicon needs an 'f' here. */ + enables |= 0xf; +#else + enables &= ~0x5; +#endif + + pci_write_config_byte(dev1, 0x9, enables); + pci_read_config_byte(dev1, 0x9, &enables); + printk_debug("enables in reg 0x9 read back as 0x%x\n", enables); + + /* standard bios sets master bit. */ + pci_read_config_byte(dev1, 0x4, &enables); + printk_debug("command in reg 0x4 0x%x\n", enables); + enables |= 5; +#if 1 + /* No need for stepping - kevinh@ispiri.com */ + enables &= ~0x80; +#endif + pci_write_config_byte(dev1, 0x4, enables); + pci_read_config_byte(dev1, 0x4, &enables); + printk_debug("command in reg 0x4 reads back as 0x%x\n", enables); + +#if (!ENABLE_IDE_NATIVE_MODE) + /* Use compatability mode - per award bios */ + pci_write_config_dword(dev1, 0x10, 0x0); + pci_write_config_dword(dev1, 0x14, 0x0); + pci_write_config_dword(dev1, 0x18, 0x0); + pci_write_config_dword(dev1, 0x1c, 0x0); + + /* Force interrupts to use compat mode - just like Award bios */ + /* !!! FIX moved it to ide_config.inc */ +#if 0 + pci_write_config_byte(dev1, 0x3d, 0x0); + pci_write_config_byte(dev1, 0x3c, 0xff); +#endif +#endif +#endif + + ethernet_fixup(); + + usb_on(); + +#if 0 + /* Start the rtc */ + rtc_init(0); +#endif +} +#endif + +#if 0 + pci_write_config_byte(dev1, 0x40, 0x0b); + pci_write_config_byte(dev1, 0x41, 0xf2); + pci_write_config_byte(dev1, 0x42, 0x09); + pci_write_config_byte(dev1, 0x43, 0x05); + pci_write_config_byte(dev1, 0x44, 0x18); + pci_write_config_byte(dev1, 0x45, 0x1c); + pci_write_config_byte(dev1, 0x4b, 0xa8); + pci_write_config_byte(dev1, 0x4c, 0x3f); + pci_write_config_byte(dev1, 0x4f, 0x20); + + pci_write_config_byte(dev1, 0x50, 0x17); + pci_write_config_byte(dev1, 0x51, 0x17); + pci_write_config_byte(dev1, 0x52, 0x17); + pci_write_config_byte(dev1, 0x53, 0xe2); + pci_write_config_byte(dev1, 0x54, 0x0c); + pci_write_config_byte(dev1, 0x55, 0x03); + + + pci_write_config_byte(dev0, 0x6C, 0x00); + pci_write_config_byte(dev0, 0x41, 0x7f); + + enables = pci_read_config_byte(dev0, 0x40, &enables); + enables |= 0x45; + pci_write_config_byte(dev0, 0x40, enables); + + enables = pci_read_config_byte(dev0, 0x42, &enables); + enables |= 0xf0; + pci_write_config_byte(dev0, 0x42, enables); + + enables = pci_read_config_byte(dev0, 0x4f, &enables); + enables |= 0x08; + pci_write_config_byte(dev0, 0x4f, enables); + + pci_write_config_byte(dev0, 0x58, 0x03); + + enables = pci_read_config_byte(dev0, 0x6e, &enables); + enables = 0x00; + pci_write_config_byte(dev0, 0x6e, enables); + + pci_read_config_byte(dev0, 0x50, &enables); + enables &= ~8; // need manifest constant here! + pci_write_config_byte(dev0, 0x50, enables); + + pci_write_config_byte(dev0, 0x52, 0x09); + pci_write_config_byte(dev0, 0x53, 0x00); + pci_write_config_byte(dev0, 0x5b, 0x00); + + pci_read_config_byte(dev1, 0x42, &enables); + enables &= ~0xc0; + pci_write_config_byte(dev1, 0x42, enables); + + pci_read_config_byte(dev1, 0x40, &enables); + enables |= 3; + pci_write_config_byte(dev1, 0x40, enables); + + pci_read_config_byte(dev1, 0x41, &enables); + enables |= 0xf0; + pci_write_config_byte(dev1, 0x41, enables); + + pci_read_config_byte(dev1, 0x43, &enables); + enables &= ~0x0f; + enables |= 0x05; + pci_write_config_byte(dev1, 0x43, enables); + + pci_write_config_byte(dev1, 0x44, 0x18); + + pci_write_config_byte(dev1, 0x45, 0x1c); + + pci_read_config_byte(dev1, 0x9, &enables); + enables &= ~0x5; + pci_write_config_byte(dev1, 0x9, enables); + + pci_read_config_byte(dev1, 0x4, &enables); + printk_debug("command in reg 0x4 0x%x\n", enables); + enables |= 5; + enables &= ~0x80; + + pci_write_config_byte(dev1, 0x4, enables); + + pci_write_config_dword(dev1, 0x10, 0x0); + pci_write_config_dword(dev1, 0x14, 0x0); + pci_write_config_dword(dev1, 0x18, 0x0); + pci_write_config_dword(dev1, 0x1c, 0x0); +#endif