Author: oxygene Date: Tue Feb 9 11:22:33 2010 New Revision: 5097 URL: http://tracker.coreboot.org/trac/coreboot/changeset/5097
Log: Port of CS5536 early UART setup from v3. Permit early setup of COM2
Signed-off-by: Edwin Beasant edwin_beasant@virtensys.com Acked-by: Patrick Georgi patrick.georgi@coresystems.de
Modified: trunk/src/mainboard/amd/norwich/romstage.c trunk/src/mainboard/olpc/btest/romstage.c trunk/src/mainboard/olpc/rev_a/romstage.c trunk/src/southbridge/amd/cs5536/cs5536.c trunk/src/southbridge/amd/cs5536/cs5536_early_setup.c
Modified: trunk/src/mainboard/amd/norwich/romstage.c ============================================================================== --- trunk/src/mainboard/amd/norwich/romstage.c Mon Feb 8 19:30:41 2010 (r5096) +++ trunk/src/mainboard/amd/norwich/romstage.c Tue Feb 9 11:22:33 2010 (r5097) @@ -115,7 +115,7 @@ * up later... */ /* If debug. real setup done in chipset init via Config.lb. */ - cs5536_setup_onchipuart(); + cs5536_setup_onchipuart(1); mb_gpio_init(); uart_init(); console_init();
Modified: trunk/src/mainboard/olpc/btest/romstage.c ============================================================================== --- trunk/src/mainboard/olpc/btest/romstage.c Mon Feb 8 19:30:41 2010 (r5096) +++ trunk/src/mainboard/olpc/btest/romstage.c Tue Feb 9 11:22:33 2010 (r5097) @@ -177,7 +177,7 @@ * it is counting on some early MSR setup * for cs5536 */ - cs5536_setup_onchipuart(); + cs5536_setup_onchipuart(1); gpio_init(); uart_init(); console_init();
Modified: trunk/src/mainboard/olpc/rev_a/romstage.c ============================================================================== --- trunk/src/mainboard/olpc/rev_a/romstage.c Mon Feb 8 19:30:41 2010 (r5096) +++ trunk/src/mainboard/olpc/rev_a/romstage.c Tue Feb 9 11:22:33 2010 (r5097) @@ -177,7 +177,7 @@ * it is counting on some early MSR setup * for cs5536 */ - cs5536_setup_onchipuart(); + cs5536_setup_onchipuart(1); gpio_init(); uart_init(); console_init();
Modified: trunk/src/southbridge/amd/cs5536/cs5536.c ============================================================================== --- trunk/src/southbridge/amd/cs5536/cs5536.c Mon Feb 8 19:30:41 2010 (r5096) +++ trunk/src/southbridge/amd/cs5536/cs5536.c Tue Feb 9 11:22:33 2010 (r5097) @@ -247,38 +247,45 @@
isa_dma_init(); } +
+/** + * Depending on settings in the config struct, enable COM1 or COM2 or both. + * + * If the enable is NOT set, the UARTs are explicitly disabled, which is + * required if (e.g.) there is a Super I/O attached that does COM1 or COM2. + * + * @param sb Southbridge config structure. + */ static void uarts_init(struct southbridge_amd_cs5536_config *sb) { msr_t msr; - uint16_t addr; - uint32_t gpio_addr; + u16 addr = 0; + u32 gpio_addr; device_t dev; - + dev = dev_find_device(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_CS5536_ISA, 0); gpio_addr = pci_read_config32(dev, PCI_BASE_ADDRESS_1); - gpio_addr &= ~1; /* clear IO bit */ - printk_debug("GPIO_ADDR: %08X\n", gpio_addr); + gpio_addr &= ~1; /* Clear I/O bit */ + printk(BIOS_DEBUG, "GPIO_ADDR: %08X\n", gpio_addr);
- /* This could be extended to support IR modes */ + /* This could be extended to support IR modes. */
/* COM1 */ if (sb->com1_enable) { - /* Set the address */ + printk(BIOS_SPEW, "uarts_init: enable COM1\n"); + /* Set the address. */ switch (sb->com1_address) { case 0x3F8: addr = 7; break; - case 0x3E8: addr = 6; break; - case 0x2F8: addr = 5; break; - case 0x2E8: addr = 4; break; @@ -287,13 +294,13 @@ msr.lo |= addr << 16; wrmsr(MDD_LEG_IO, msr);
- /* Set the IRQ */ + /* Set the IRQ. */ msr = rdmsr(MDD_IRQM_YHIGH); msr.lo |= sb->com1_irq << 24; wrmsr(MDD_IRQM_YHIGH, msr);
/* GPIO8 - UART1_TX */ - /* Set: Output Enable (0x4) */ + /* Set: Output Enable (0x4) */ outl(GPIOL_8_SET, gpio_addr + GPIOL_OUTPUT_ENABLE); /* Set: OUTAUX1 Select (0x10) */ outl(GPIOL_8_SET, gpio_addr + GPIOL_OUT_AUX1_SELECT); @@ -301,28 +308,31 @@ /* GPIO9 - UART1_RX */ /* Set: Input Enable (0x20) */ outl(GPIOL_9_SET, gpio_addr + GPIOL_INPUT_ENABLE); - /* Set: INAUX1 Select (0x34) */ + /* Set: INAUX1 Select (0x34) */ outl(GPIOL_9_SET, gpio_addr + GPIOL_IN_AUX1_SELECT);
- /* Set: GPIO 8 + 9 Pull Up (0x18) */ + /* Set: GPIO 8 + 9 Pull Up (0x18) */ outl(GPIOL_8_SET | GPIOL_9_SET, gpio_addr + GPIOL_PULLUP_ENABLE);
- /* enable COM1 */ - /* Bit 1 = device enable Bit 4 = allow access to the upper banks */ + /* Enable COM1. + * + * Bit 1 = device enable + * Bit 4 = allow access to the upper banks + */ msr.lo = (1 << 4) | (1 << 1); msr.hi = 0; wrmsr(MDD_UART1_CONF, msr); - } else { - /* Reset and disable COM1 */ + /* Reset and disable COM1. */ + printk(BIOS_SPEW, "uarts_init: disable COM1\n"); msr = rdmsr(MDD_UART1_CONF); - msr.lo = 1; // reset + msr.lo = 1; /* Reset */ wrmsr(MDD_UART1_CONF, msr); - msr.lo = 0; // disabled + msr.lo = 0; /* Disabled */ wrmsr(MDD_UART1_CONF, msr);
- /* Disable the IRQ */ + /* Disable the IRQ. */ msr = rdmsr(MDD_LEG_IO); msr.lo &= ~(0xF << 16); wrmsr(MDD_LEG_IO, msr); @@ -330,19 +340,17 @@
/* COM2 */ if (sb->com2_enable) { + printk(BIOS_SPEW, "uarts_init: enable COM2\n"); switch (sb->com2_address) { case 0x3F8: addr = 7; break; - case 0x3E8: addr = 6; break; - case 0x2F8: addr = 5; break; - case 0x2E8: addr = 4; break; @@ -350,11 +358,13 @@ msr = rdmsr(MDD_LEG_IO); msr.lo |= addr << 20; wrmsr(MDD_LEG_IO, msr); + printk(BIOS_SPEW, "uarts_init: wrote COM2 address 0x%x\n", sb->com2_address);
- /* Set the IRQ */ + /* Set the IRQ. */ msr = rdmsr(MDD_IRQM_YHIGH); msr.lo |= sb->com2_irq << 28; wrmsr(MDD_IRQM_YHIGH, msr); + printk(BIOS_SPEW, "uarts_init: set COM2 irq\n");
/* GPIO3 - UART2_RX */ /* Set: Input Enable (0x20) */ @@ -365,34 +375,42 @@ /* GPIO4 - UART2_TX */ /* Set: Output Enable (0x4) */ outl(GPIOL_4_SET, gpio_addr + GPIOL_OUTPUT_ENABLE); + printk(BIOS_SPEW, "uarts_init: set output enable\n"); /* Set: OUTAUX1 Select (0x10) */ outl(GPIOL_4_SET, gpio_addr + GPIOL_OUT_AUX1_SELECT); + printk(BIOS_SPEW, "uarts_init: set OUTAUX1\n");
- /* Set: GPIO 3 and 4 Pull Up (0x18) */ + /* Set: GPIO 3 + 4 Pull Up (0x18) */ outl(GPIOL_3_SET | GPIOL_4_SET, gpio_addr + GPIOL_PULLUP_ENABLE); + printk(BIOS_SPEW, "uarts_init: set pullup COM2\n");
- /* enable COM2 */ - /* Bit 1 = device enable Bit 4 = allow access to the upper banks */ + /* Enable COM2. + * + * Bit 1 = device enable + * Bit 4 = allow access to the upper banks + */ msr.lo = (1 << 4) | (1 << 1); msr.hi = 0; wrmsr(MDD_UART2_CONF, msr); - + printk(BIOS_SPEW, "uarts_init: COM2 enabled\n"); } else { - /* Reset and disable COM2 */ + printk(BIOS_SPEW, "uarts_init: disable COM2\n"); + /* Reset and disable COM2. */ msr = rdmsr(MDD_UART2_CONF); - msr.lo = 1; // reset + msr.lo = 1; /* Reset */ wrmsr(MDD_UART2_CONF, msr); - msr.lo = 0; // disabled + msr.lo = 0; /* Disabled */ wrmsr(MDD_UART2_CONF, msr);
- /* Disable the IRQ */ + /* Disable the IRQ. */ msr = rdmsr(MDD_LEG_IO); msr.lo &= ~(0xF << 20); wrmsr(MDD_LEG_IO, msr); } }
+ #define HCCPARAMS 0x08 #define IPREG04 0xA0 #define USB_HCCPW_SET (1 << 1)
Modified: trunk/src/southbridge/amd/cs5536/cs5536_early_setup.c ============================================================================== --- trunk/src/southbridge/amd/cs5536/cs5536_early_setup.c Mon Feb 8 19:30:41 2010 (r5096) +++ trunk/src/southbridge/amd/cs5536/cs5536_early_setup.c Tue Feb 9 11:22:33 2010 (r5097) @@ -153,47 +153,98 @@ wrmsr(GLPCI_SB_CTRL, msr); }
-/* see page 412 of the cs5536 companion book */ -static void cs5536_setup_onchipuart(void) +/** + * Enable the on-chip UART. + * + * See page 412 of the AMD Geode CS5536 Companion Device data book. + */ +void cs5536_setup_onchipuart1(void) { msr_t msr;
/* Setup early for polling only mode. - * 1. Eanble GPIO 8 to OUT_AUX1, 9 to IN_AUX1 + * 1. Enable GPIO 8 to OUT_AUX1, 9 to IN_AUX1. * GPIO LBAR + 0x04, LBAR + 0x10, LBAR + 0x20, LBAR + 34 - * 2. Enable UART IO space in MDD + * 2. Enable UART I/O space in MDD. * MSR 0x51400014 bit 18:16 - * 3. Enable UART controller + * 3. Enable UART controller. * MSR 0x5140003A bit 0, 1 */
/* GPIO8 - UART1_TX */ - /* Set: Output Enable (0x4) */ + /* Set: Output Enable (0x4) */ outl(GPIOL_8_SET, GPIO_IO_BASE + GPIOL_OUTPUT_ENABLE); /* Set: OUTAUX1 Select (0x10) */ outl(GPIOL_8_SET, GPIO_IO_BASE + GPIOL_OUT_AUX1_SELECT);
/* GPIO9 - UART1_RX */ - /* Set: Input Enable (0x20) */ + /* Set: Input Enable (0x20) */ outl(GPIOL_9_SET, GPIO_IO_BASE + GPIOL_INPUT_ENABLE); - /* Set: INAUX1 Select (0x34) */ + /* Set: INAUX1 Select (0x34) */ outl(GPIOL_9_SET, GPIO_IO_BASE + GPIOL_IN_AUX1_SELECT);
- /* set address to 3F8 */ + /* Set address to 0x3F8. */ msr = rdmsr(MDD_LEG_IO); msr.lo |= 0x7 << 16; wrmsr(MDD_LEG_IO, msr);
- /* Bit 1 = DEVEN (device enable) - * Bit 4 = EN_BANKS (allow access to the upper banks + /* Bit 1 = DEVEN (device enable) + * Bit 4 = EN_BANKS (allow access to the upper banks) */ msr.lo = (1 << 4) | (1 << 1); msr.hi = 0;
- /* enable COM1 */ + /* Enable COM1. */ wrmsr(MDD_UART1_CONF, msr); }
+void cs5536_setup_onchipuart2(void) +{ + msr_t msr; + + /* GPIO4 - UART2_TX */ + /* Set: Output Enable (0x4) */ + outl(GPIOL_4_SET, GPIO_IO_BASE + GPIOL_OUTPUT_ENABLE); + /* Set: OUTAUX1 Select (0x10) */ + outl(GPIOL_4_SET, GPIO_IO_BASE + GPIOL_OUT_AUX1_SELECT); + /* GPIO4 - UART2_RX */ + /* Set: Input Enable (0x20) */ + outl(GPIOL_3_SET, GPIO_IO_BASE + GPIOL_INPUT_ENABLE); + /* Set: INAUX1 Select (0x34) */ + outl(GPIOL_3_SET, GPIO_IO_BASE + GPIOL_IN_AUX1_SELECT); + + /* Set: GPIO 3 + 3 Pull Up (0x18) */ + outl(GPIOL_3_SET | GPIOL_4_SET, + GPIO_IO_BASE + GPIOL_PULLUP_ENABLE); + + /* set address to 2F8 */ + msr = rdmsr(MDD_LEG_IO); + msr.lo |= 0x5 << 20; + wrmsr(MDD_LEG_IO, msr); + + /* Bit 1 = DEVEN (device enable) + * Bit 4 = EN_BANKS (allow access to the upper banks + */ + msr.lo = (1 << 4) | (1 << 1); + msr.hi = 0; + + /* enable COM2 */ + wrmsr(MDD_UART2_CONF, msr); +} + +void cs5536_setup_onchipuart(int uart) +{ + switch (uart) { + case 1: + cs5536_setup_onchipuart1(); + break; + case 2: + cs5536_setup_onchipuart2(); + break; + } +} + + /* note: you can't do prints in here in most cases, * and we don't want to hang on serial, so they are * commented out
repository service wrote:
+++ trunk/src/mainboard/amd/norwich/romstage.c Tue Feb 9 11:22:33 2010 (r5097)
..
- cs5536_setup_onchipuart();
- cs5536_setup_onchipuart(1);
+++ trunk/src/southbridge/amd/cs5536/cs5536_early_setup.c Tue Feb 9 11:22:33 2010 (r5097)
..
+void cs5536_setup_onchipuart(int uart) +{
- switch (uart) {
- case 1:
cs5536_setup_onchipuart1();
break;
- case 2:
cs5536_setup_onchipuart2();
break;
- }
+}
If you have an opportunity to revisit this then I think it would be nicer to just remove this extra function and call the actual setup functions directly.
//Peter
No problem, I'll see what I can do :-) Edwin
-----Original Message----- From: coreboot-bounces@coreboot.org [mailto:coreboot-bounces@coreboot.org] On Behalf Of Peter Stuge Sent: 09 February 2010 10:40 To: coreboot@coreboot.org Subject: Re: [coreboot] [commit] r5097 - in trunk/src: mainboard/amd/norwich mainboard/olpc/btest mainboard/olpc/rev_a southbridge/amd/cs5536
repository service wrote:
+++ trunk/src/mainboard/amd/norwich/romstage.c Tue Feb 9 11:22:33 2010 (r5097)
..
cs5536_setup_onchipuart();
cs5536_setup_onchipuart(1);
+++ trunk/src/southbridge/amd/cs5536/cs5536_early_setup.c Tue Feb 9 11:22:33 2010 (r5097)
..
+void cs5536_setup_onchipuart(int uart) +{
switch (uart) {
case 1:
cs5536_setup_onchipuart1();
break;
case 2:
cs5536_setup_onchipuart2();
break;
}
+}
If you have an opportunity to revisit this then I think it would be nicer to just remove this extra function and call the actual setup functions directly.
//Peter
-- coreboot mailing list: coreboot@coreboot.org http://www.coreboot.org/mailman/listinfo/coreboot
Am 09.02.2010 11:40, schrieb Peter Stuge:
If you have an opportunity to revisit this then I think it would be nicer to just remove this extra function and call the actual setup functions directly.
I like it that way - we could even make that a CMOS variable that way. If boards call cs5536_setup_onchipuart[12]() directly, they'll have to do this decision in each board that chooses to behave that way.
It might still be feasible to refactor those functions some more, but the interface is sane, in my opinion.
Patrick
On Tue, Feb 9, 2010 at 4:10 AM, Patrick Georgi patrick@georgi-clan.de wrote:
I like it that way - we could even make that a CMOS variable that way. If boards call cs5536_setup_onchipuart[12]() directly, they'll have to do this decision in each board that chooses to behave that way.
It might still be feasible to refactor those functions some more, but the interface is sane, in my opinion.
I agree here.
ron