[coreboot-gerrit] Patch set updated for coreboot: coreboot_tables: Extend serial port description

Leroy P Leahy (leroy.p.leahy@intel.com) gerrit at coreboot.org
Wed May 4 00:17:06 CEST 2016


Leroy P Leahy (leroy.p.leahy at intel.com) just uploaded a new patch set to gerrit, which you can find at https://review.coreboot.org/14111

-gerrit

commit 536c2760442ef3f3cac7a8eb10b3c847e85f944f
Author: Lee Leahy <leroy.p.leahy at intel.com>
Date:   Wed Mar 16 10:21:59 2016 -0700

    coreboot_tables: Extend serial port description
    
    Extend the serial port description to include the input clock frequency
    and an identifier for the serial port.
    
    Without the input frequency it is impossible for the payload to compute
    the baud-rate divisor without making an assumption about the frequency.
    This breaks down when the UART is able to support multiple input clock
    frequencies.
    
    Use weak functions to allow the platform to override the input clock
    frequency and the input clock divisor to enable coreboot to compute
    the proper baud-rate divisor.
    
    Add a payload specific ID field used by the payload to identify the
    console UART within the system.  A Kconfig value provides the default for this field to prevent breaking
    existing coreboot implementations.
    
    Currently the only payload to consume these new fields is the EDK-II
    CorebootPayloadPkg.
    
    Testing on Galileo:
    *  Edit the src/mainboard/intel/galileo/Makefile.inc file:
       *  Add "select ADD_FSP_PDAT_FILE"
       *  Add "select ADD_FSP_RAW_BIN"
       *  Add "select ADD_RMU_FILE"
    *  Place the FSP.bin file in the location specified by CONFIG_FSP_FILE
    *  Place the pdat.bin files in the location specified by
       CONFIG_FSP_PDAT_FILE
    *  Place the rmu.bin file in the location specified by CONFIG_RMU_FILE
    *  Build EDK2 CorebootPayloadPkg/CorebootPayloadPkgIa32.dsc to generate
       UEFIPAYLOAD.fd
    *  Load the SPI driver stack
    *  Testing is successful when CorebootPayloadPkg is able to properly
       initialize the serial port without using built-in values.
    
    Change-Id: I05a7e864afcd930916658e3efed53ff2efd403ec
    Signed-off-by: Lee Leahy <leroy.p.leahy at intel.com>
---
 payloads/libpayload/include/coreboot_tables.h     |  2 ++
 src/commonlib/include/commonlib/coreboot_tables.h |  8 ++++++++
 src/cpu/allwinner/a10/Kconfig                     |  1 +
 src/cpu/ti/am335x/Kconfig                         |  1 +
 src/drivers/uart/Kconfig                          | 21 +++++++++++++++++++++
 src/drivers/uart/oxpcie_early.c                   |  2 ++
 src/drivers/uart/pl011.c                          |  2 ++
 src/drivers/uart/uart8250io.c                     | 12 ++++--------
 src/drivers/uart/uart8250mem.c                    |  5 ++++-
 src/drivers/uart/util.c                           | 14 ++++++++++++++
 src/include/console/uart.h                        |  4 ++++
 src/lib/coreboot_table.c                          |  2 ++
 src/soc/imgtec/pistachio/Kconfig                  |  1 +
 src/soc/intel/apollolake/uart_early.c             |  6 ------
 src/soc/intel/quark/Kconfig                       |  6 ++++++
 src/soc/intel/skylake/uart_debug.c                | 11 -----------
 src/soc/marvell/armada38x/Kconfig                 |  1 +
 src/soc/nvidia/tegra132/Kconfig                   |  1 +
 src/southbridge/amd/pi/hudson/Kconfig             |  1 +
 19 files changed, 75 insertions(+), 26 deletions(-)

diff --git a/payloads/libpayload/include/coreboot_tables.h b/payloads/libpayload/include/coreboot_tables.h
index 276f25f..06d1768 100644
--- a/payloads/libpayload/include/coreboot_tables.h
+++ b/payloads/libpayload/include/coreboot_tables.h
@@ -121,6 +121,8 @@ struct cb_serial {
 	u32 baseaddr;
 	u32 baud;
 	u32 regwidth;
+	u32 input_hertz;
+	u32 id;
 };
 
 #define CB_TAG_CONSOLE       0x00010
diff --git a/src/commonlib/include/commonlib/coreboot_tables.h b/src/commonlib/include/commonlib/coreboot_tables.h
index 5c28791..926930d 100644
--- a/src/commonlib/include/commonlib/coreboot_tables.h
+++ b/src/commonlib/include/commonlib/coreboot_tables.h
@@ -173,6 +173,14 @@ struct lb_serial {
 	uint32_t baseaddr;
 	uint32_t baud;
 	uint32_t regwidth;
+	/* Crystal or input frequency to the chip containing the UART.
+	 * Provide the board specific details to allow the payload to
+	 * initialize the chip containing the UART and make independent
+	 * decisions as to which dividers to select and their values
+	 * to eventually arrive at the desired console baud-rate. */
+	uint32_t input_hertz;
+	/* Payload specific value to identify the console UART */
+	uint32_t id;
 };
 
 #define LB_TAG_CONSOLE		0x0010
diff --git a/src/cpu/allwinner/a10/Kconfig b/src/cpu/allwinner/a10/Kconfig
index 814b69e..0e5aba9 100644
--- a/src/cpu/allwinner/a10/Kconfig
+++ b/src/cpu/allwinner/a10/Kconfig
@@ -13,5 +13,6 @@ config CPU_SPECIFIC_OPTIONS
 	select HAVE_MONOTONIC_TIMER
 	select HAVE_UART_SPECIAL
 	select BOOTBLOCK_CONSOLE
+	select UART_OVERRIDE_REFCLK
 
 endif # if CPU_ALLWINNER_A10
diff --git a/src/cpu/ti/am335x/Kconfig b/src/cpu/ti/am335x/Kconfig
index 8d3c691..f44c69d 100644
--- a/src/cpu/ti/am335x/Kconfig
+++ b/src/cpu/ti/am335x/Kconfig
@@ -7,5 +7,6 @@ config CPU_TI_AM335X
 	select HAVE_UART_SPECIAL
 	select BOOTBLOCK_CONSOLE
 	select GENERIC_UDELAY
+	select UART_OVERRIDE_REFCLK
 	bool
 	default n
diff --git a/src/drivers/uart/Kconfig b/src/drivers/uart/Kconfig
index f4ad011..051dd17 100644
--- a/src/drivers/uart/Kconfig
+++ b/src/drivers/uart/Kconfig
@@ -13,6 +13,20 @@ config DRIVERS_UART_8250IO
 config NO_UART_ON_SUPERIO
 	def_bool n
 
+config UART_OVERRIDE_REFCLK
+	boolean
+	default n
+	help
+	  Set to "y" when the platform overrides the uart_platform_refclk
+	  routine.
+
+config UART_OVERRIDE_INPUT_CLOCK_DIVIDER
+	boolean
+	default n
+	help
+	  Set to "y" when the platform overrides the uart_input_clock_divider
+	  routine.
+
 config DRIVERS_UART_8250MEM
 	bool
 	default n
@@ -32,6 +46,7 @@ config DRIVERS_UART_OXPCIE
 	depends on PCI
 	select DRIVERS_UART_8250MEM
 	select EARLY_PCI_BRIDGE
+	select UART_OVERRIDE_REFCLK
 	help
 	  Support for Oxford OXPCIe952 serial port PCIe cards.
 	  Currently only devices with the vendor ID 0x1415 and device ID
@@ -41,3 +56,9 @@ config DRIVERS_UART_PL011
 	bool
 	default n
 	select HAVE_UART_SPECIAL
+
+config UART_DEVICE_ID
+	hex
+	default 0
+	help
+	  ID to help the payload identify the proper UART
diff --git a/src/drivers/uart/oxpcie_early.c b/src/drivers/uart/oxpcie_early.c
index eb91d31..479408b 100644
--- a/src/drivers/uart/oxpcie_early.c
+++ b/src/drivers/uart/oxpcie_early.c
@@ -92,6 +92,8 @@ void uart_fill_lb(void *data)
 	serial.baseaddr = uart_platform_base(CONFIG_UART_FOR_CONSOLE);
 	serial.baud = default_baudrate();
 	serial.regwidth = 1;
+	serial.input_hertz = uart_platform_refclk();
+	serial.id = CONFIG_UART_DEVICE_ID;
 	lb_add_serial(&serial, data);
 
 	lb_add_console(LB_TAG_CONSOLE_SERIAL8250MEM, data);
diff --git a/src/drivers/uart/pl011.c b/src/drivers/uart/pl011.c
index aa55c68..915273b 100644
--- a/src/drivers/uart/pl011.c
+++ b/src/drivers/uart/pl011.c
@@ -48,6 +48,8 @@ void uart_fill_lb(void *data)
 	serial.baseaddr = uart_platform_base(CONFIG_UART_FOR_CONSOLE);
 	serial.baud = default_baudrate();
 	serial.regwidth = 1;
+	serial.input_hertz = uart_platform_refclk();
+	serial.id = CONFIG_UART_DEVICE_ID;
 	lb_add_serial(&serial, data);
 
 	lb_add_console(LB_TAG_CONSOLE_SERIAL8250MEM, data);
diff --git a/src/drivers/uart/uart8250io.c b/src/drivers/uart/uart8250io.c
index 63bc42f..c83c2d2 100644
--- a/src/drivers/uart/uart8250io.c
+++ b/src/drivers/uart/uart8250io.c
@@ -27,12 +27,6 @@
 
 /* Should support 8250, 16450, 16550, 16550A type UARTs */
 
-/* Nominal values only, good for the range of choices Kconfig offers for
- * set of standard baudrates.
- */
-#define BAUDRATE_REFCLK		(115200)
-#define BAUDRATE_OVERSAMPLE	(1)
-
 /* Expected character delay at 1200bps is 9ms for a working UART
  * and no flow-control. Assume UART as stuck if shift register
  * or FIFO takes more than 50ms per character to appear empty.
@@ -111,8 +105,8 @@ uintptr_t uart_platform_base(int idx)
 void uart_init(int idx)
 {
 	unsigned int div;
-	div = uart_baudrate_divisor(default_baudrate(), BAUDRATE_REFCLK,
-		BAUDRATE_OVERSAMPLE);
+	div = uart_baudrate_divisor(default_baudrate(), uart_platform_refclk(),
+		uart_input_clock_divider());
 	uart8250_init(uart_platform_base(idx), div);
 }
 
@@ -139,6 +133,8 @@ void uart_fill_lb(void *data)
 	serial.baseaddr = uart_platform_base(CONFIG_UART_FOR_CONSOLE);
 	serial.baud = default_baudrate();
 	serial.regwidth = 1;
+	serial.input_hertz = uart_platform_refclk();
+	serial.id = CONFIG_UART_DEVICE_ID;
 	lb_add_serial(&serial, data);
 
 	lb_add_console(LB_TAG_CONSOLE_SERIAL8250, data);
diff --git a/src/drivers/uart/uart8250mem.c b/src/drivers/uart/uart8250mem.c
index 278ddb8..3fdb511 100644
--- a/src/drivers/uart/uart8250mem.c
+++ b/src/drivers/uart/uart8250mem.c
@@ -117,7 +117,8 @@ void uart_init(int idx)
 		return;
 
 	unsigned int div;
-	div = uart_baudrate_divisor(default_baudrate(), uart_platform_refclk(), 16);
+	div = uart_baudrate_divisor(default_baudrate(),
+		uart_platform_refclk(), uart_input_clock_divider());
 	uart8250_mem_init(base, div);
 }
 
@@ -156,6 +157,8 @@ void uart_fill_lb(void *data)
 		serial.regwidth = sizeof(uint32_t);
 	else
 		serial.regwidth = sizeof(uint8_t);
+	serial.input_hertz = uart_platform_refclk();
+	serial.id = CONFIG_UART_DEVICE_ID;
 	lb_add_serial(&serial, data);
 
 	lb_add_console(LB_TAG_CONSOLE_SERIAL8250MEM, data);
diff --git a/src/drivers/uart/util.c b/src/drivers/uart/util.c
index 4121f60..0082575 100644
--- a/src/drivers/uart/util.c
+++ b/src/drivers/uart/util.c
@@ -42,3 +42,17 @@ unsigned int uart_baudrate_divisor(unsigned int baudrate,
 {
 	return (1 + (2 * refclk) / (baudrate * oversample)) / 2;
 }
+
+# if !IS_ENABLED(CONFIG_UART_OVERRIDE_REFCLK)
+unsigned int uart_platform_refclk(void)
+{
+	return 115200 * 16;
+}
+#endif
+
+# if !IS_ENABLED(CONFIG_UART_OVERRIDE_INPUT_CLOCK_DIVIDER)
+unsigned int uart_input_clock_divider(void)
+{
+	return 16;
+}
+#endif
diff --git a/src/include/console/uart.h b/src/include/console/uart.h
index 8458086..a3d650b 100644
--- a/src/include/console/uart.h
+++ b/src/include/console/uart.h
@@ -35,6 +35,10 @@ unsigned int default_baudrate(void);
 unsigned int uart_baudrate_divisor(unsigned int baudrate,
 	unsigned int refclk, unsigned int oversample);
 
+/* Returns the oversample divisor multiplied by any other divisors that act
+ * on the input clock
+ */
+unsigned int uart_input_clock_divider(void);
 
 void uart_init(int idx);
 void uart_tx_byte(int idx, unsigned char data);
diff --git a/src/lib/coreboot_table.c b/src/lib/coreboot_table.c
index 4dbac19..5482660 100644
--- a/src/lib/coreboot_table.c
+++ b/src/lib/coreboot_table.c
@@ -119,6 +119,8 @@ void lb_add_serial(struct lb_serial *new_serial, void *data)
 	serial->baseaddr = new_serial->baseaddr;
 	serial->baud = new_serial->baud;
 	serial->regwidth = new_serial->regwidth;
+	serial->input_hertz = new_serial->input_hertz;
+	serial->id = new_serial->id;
 }
 
 void lb_add_console(uint16_t consoletype, void *data)
diff --git a/src/soc/imgtec/pistachio/Kconfig b/src/soc/imgtec/pistachio/Kconfig
index 5ea6b95..da33cc5 100644
--- a/src/soc/imgtec/pistachio/Kconfig
+++ b/src/soc/imgtec/pistachio/Kconfig
@@ -25,6 +25,7 @@ config CPU_IMGTEC_PISTACHIO
 	select SPI_ATOMIC_SEQUENCING
 	select GENERIC_GPIO_LIB
 	select HAVE_HARD_RESET
+	select UART_OVERRIDE_REFCLK
 	bool
 
 if CPU_IMGTEC_PISTACHIO
diff --git a/src/soc/intel/apollolake/uart_early.c b/src/soc/intel/apollolake/uart_early.c
index e8dfeda..0e53060 100644
--- a/src/soc/intel/apollolake/uart_early.c
+++ b/src/soc/intel/apollolake/uart_early.c
@@ -68,12 +68,6 @@ uintptr_t uart_platform_base(int idx)
 	return (CONFIG_CONSOLE_UART_BASE_ADDRESS);
 }
 
-unsigned int uart_platform_refclk(void)
-{
-	/* That's within 0.5% of the actual value we've set earlier */
-	return 115200 * 16;
-}
-
 static const struct pad_config uart_gpios[] = {
 	PAD_CFG_NF(GPIO_42, NATIVE, DEEP, NF1),		/* UART1 RX */
 	PAD_CFG_NF(GPIO_43, NATIVE, DEEP, NF1),		/* UART1 TX */
diff --git a/src/soc/intel/quark/Kconfig b/src/soc/intel/quark/Kconfig
index 8485aa3..ce7315a 100644
--- a/src/soc/intel/quark/Kconfig
+++ b/src/soc/intel/quark/Kconfig
@@ -30,6 +30,7 @@ config CPU_SPECIFIC_OPTIONS
 	select SOC_INTEL_COMMON
 	select SOC_SETS_MTRRS
 	select TSC_CONSTANT_RATE
+	select UART_OVERRIDE_REFCLK
 	select UDELAY_TSC
 	select UNCOMPRESSED_RAMSTAGE
 	select USE_MARCH_586
@@ -60,6 +61,11 @@ config TTYS0_LCS
 	depends on ENABLE_BUILTIN_HSUART1
 	default 3
 
+config UART_DEVICE_ID
+	hex
+	depends on ENABLE_BUILTIN_HSUART1
+	default 0x09368086
+
 #####
 # Debug support
 #     The following options provide debug support for the Quark coreboot
diff --git a/src/soc/intel/skylake/uart_debug.c b/src/soc/intel/skylake/uart_debug.c
index c463bea..f3d576b 100644
--- a/src/soc/intel/skylake/uart_debug.c
+++ b/src/soc/intel/skylake/uart_debug.c
@@ -18,17 +18,6 @@
 #include <soc/iomap.h>
 #include <soc/serialio.h>
 
-unsigned int uart_platform_refclk(void)
-{
-	/*
-	 * Set M and N divisor inputs and enable clock.
-	 * Main reference frequency to UART is:
-	 *  120MHz * M / N = 120MHz * 48 / 3125 = 1843200Hz
-	 * The different order below is to handle integer math overflow.
-	 */
-	return 120 * MHz / SIO_REG_PPR_CLOCK_N_DIV * SIO_REG_PPR_CLOCK_M_DIV;
-}
-
 uintptr_t uart_platform_base(int idx)
 {
 	/* Same base address for all debug port usage. In reality UART2
diff --git a/src/soc/marvell/armada38x/Kconfig b/src/soc/marvell/armada38x/Kconfig
index 6754a0f..ed8cbe8 100644
--- a/src/soc/marvell/armada38x/Kconfig
+++ b/src/soc/marvell/armada38x/Kconfig
@@ -10,6 +10,7 @@ config SOC_MARVELL_ARMADA38X
 	select RETURN_FROM_VERSTAGE
 	select BOOTBLOCK_CUSTOM
 	select GENERIC_UDELAY
+	select UART_OVERRIDE_REFCLK
 
 if SOC_MARVELL_ARMADA38X
 
diff --git a/src/soc/nvidia/tegra132/Kconfig b/src/soc/nvidia/tegra132/Kconfig
index 502e7c4..08ed475 100644
--- a/src/soc/nvidia/tegra132/Kconfig
+++ b/src/soc/nvidia/tegra132/Kconfig
@@ -13,6 +13,7 @@ config SOC_NVIDIA_TEGRA132
 	select HAVE_HARD_RESET
 	select HAVE_UART_SPECIAL
 	select GENERIC_GPIO_LIB
+	select UART_OVERRIDE_REFCLK
 
 if SOC_NVIDIA_TEGRA132
 
diff --git a/src/southbridge/amd/pi/hudson/Kconfig b/src/southbridge/amd/pi/hudson/Kconfig
index aa55339..8fe3b2d 100644
--- a/src/southbridge/amd/pi/hudson/Kconfig
+++ b/src/southbridge/amd/pi/hudson/Kconfig
@@ -235,6 +235,7 @@ config HUDSON_UART
 	select DRIVERS_UART_8250MEM
 	select DRIVERS_UART_8250MEM_32
 	select NO_UART_ON_SUPERIO
+	select UART_OVERRIDE_REFCLK
 	help
 	  There are two UART controllers in Kern.
 	  The UART registers are memory-mapped. UART



More information about the coreboot-gerrit mailing list