Skip to contentSkip to conversation

rockchip: Use the standard debug UART on rockchip

PATCH New Simon Glass 3 participants 12 messages Dec 14, 2015 – Dec 19, 2015

Subsystems (3)
lore
Share & tools
lore
#0 lore raw

cover rockchip: Use the standard debug UART on rockchip

The RK3036 has only 8KB of RAM available for SPL. At present it uses its own debug UART code.

By allowing the ns16550 driver to provide a debug UART without providing a full serial driver, we can enable a UART with a very small overhead. This requires addition Kconfig options. The debug UART supports printhex8(), printascii() and a few other functions.

The root driver and uclass are pulled in by this series, but their size is very small. It would possible to drop these by disabling CONFIG_DM_SERIAL. However the ns16550 driver makes this hard, due to it supporting operation without driver model, and operating differently in this case.

Simon Glass (3):
dm: serial: Allow the UART driver to be dropped from the image
dm: ns16550: Allow the driver to be omitted if requested
rockchip: Use the debug UART on rk3036

 arch/arm/mach-rockchip/Makefile           |  1 -
 arch/arm/mach-rockchip/rk3036-board-spl.c |  9 ++++-
 arch/arm/mach-rockchip/rk_early_print.c   | 63 -------------------------------
 configs/evb-rk3036_defconfig              |  6 +++
 drivers/serial/Kconfig                    | 20 ++++++++++
 drivers/serial/ns16550.c                  |  2 +
 drivers/serial/serial-uclass.c            |  2 +
 include/configs/rk3036_common.h           |  2 +
 8 files changed, 40 insertions(+), 65 deletions(-)
 delete mode 100644 arch/arm/mach-rockchip/rk_early_print.c
Signature · 1 line
2.6.0.rc2.230.g3dd15c0
#1 lore raw

PATCH 1/3 dm: serial: Allow the UART driver to be dropped from the image

In very very space-constrained devices even the full UART driver is too large. In this case the debug UART can still be used in some cases.

Add options to enable the UART driver in SPL and U-Boot proper. Enable both options by default.

---

 drivers/serial/Kconfig         | 20 ++++++++++++++++++++
 drivers/serial/serial-uclass.c |  2 ++
 2 files changed, 22 insertions(+)
drivers/serial/Kconfig +20 -0
index 1fc287e..04541c9 100644
@@ -15,6 +15,26 @@ config REQUIRE_SERIAL_CONSOLE
 	  during serial port initialization (default y). Set this to n on
 	  boards which have no debug serial port whatsoever.
 
+config SERIAL_PRESENT
+	bool "Provide a serial driver"
+	depends on DM_SERIAL
+	default y
+	help
+	  In very space-constrained devices even the full UART driver is too
+	  large. In this case the debug UART can still be used in some cases.
+	  This option enables the full UART in U-Boot, so if is it disabled,
+	  the full UART driver will be omitted, thus saving space.
+
+config SPL_SERIAL_PRESENT
+	bool "Provide a serial driver in SPL"
+	depends on DM_SERIAL
+	default y
+	help
+	  In very space-constrained devices even the full UART driver is too
+	  large. In this case the debug UART can still be used in some cases.
+	  This option enables the full UART in SPL, so if is it disabled,
+	  the full UART driver will be omitted, thus saving space.
+
 config DM_SERIAL
 	bool "Enable Driver Model for serial drivers"
 	depends on DM
drivers/serial/serial-uclass.c +2 -0
index 4bf9a5c..95c3b91 100644
@@ -287,6 +287,7 @@ static int on_baudrate(const char *name, const char *value, enum env_op op,
 }
 U_BOOT_ENV_CALLBACK(baudrate, on_baudrate);
 
+#if CONFIG_IS_ENABLED(SERIAL_PRESENT)
 static int serial_post_probe(struct udevice *dev)
 {
 	struct dm_serial_ops *ops = serial_get_ops(dev);
@@ -356,3 +357,4 @@ UCLASS_DRIVER(serial) = {
 	.pre_remove	= serial_pre_remove,
 	.per_device_auto_alloc_size = sizeof(struct serial_dev_priv),
 };
+#endif
Signature · 1 line
2.6.0.rc2.230.g3dd15c0
#2 lore raw

PATCH 1/3 dm: serial: Allow the UART driver to be dropped from the image

Hi Simon,

Quoted 58 lines · Simon Glass

In very very space-constrained devices even the full UART driver is too large. In this case the debug UART can still be used in some cases.

Add options to enable the UART driver in SPL and U-Boot proper. Enable both options by default.

---

  drivers/serial/Kconfig         | 20 ++++++++++++++++++++
  drivers/serial/serial-uclass.c |  2 ++
  2 files changed, 22 insertions(+)
drivers/serial/Kconfig +20 -0
index 1fc287e..04541c9 100644
@@ -15,6 +15,26 @@ config REQUIRE_SERIAL_CONSOLE
  	  during serial port initialization (default y). Set this to n on
  	  boards which have no debug serial port whatsoever.
 
+config SERIAL_PRESENT
+	bool "Provide a serial driver"
+	depends on DM_SERIAL
+	default y
+	help
+	  In very space-constrained devices even the full UART driver is too
+	  large. In this case the debug UART can still be used in some cases.
+	  This option enables the full UART in U-Boot, so if is it disabled,
+	  the full UART driver will be omitted, thus saving space.
+
+config SPL_SERIAL_PRESENT
+	bool "Provide a serial driver in SPL"
+	depends on DM_SERIAL
+	default y
+	help
+	  In very space-constrained devices even the full UART driver is too
+	  large. In this case the debug UART can still be used in some cases.
+	  This option enables the full UART in SPL, so if is it disabled,
+	  the full UART driver will be omitted, thus saving space.
+
  config DM_SERIAL
  	bool "Enable Driver Model for serial drivers"
  	depends on DM
drivers/serial/serial-uclass.c +1 -0
index 4bf9a5c..95c3b91 100644
@@ -287,6 +287,7 @@ static int on_baudrate(const char *name, const char *value, enum env_op op,
  }
  U_BOOT_ENV_CALLBACK(baudrate, on_baudrate);
 
+#if CONFIG_IS_ENABLED(SERIAL_PRESENT)
  static int serial_post_probe(struct udevice *dev)
  {
  	struct dm_serial_ops *ops = serial_get_ops(dev);

drivers/serial/serial-uclass.c UCLASS_DRIVER(serial) = { · line 360

Quoted 4 lines
drivers/serial/serial-uclass.c +1 -0
@@ -356,3 +357,4 @@ UCLASS_DRIVER(serial) = {
  	.pre_remove	= serial_pre_remove,
  	.per_device_auto_alloc_size = sizeof(struct serial_dev_priv),
  };
+#endif
#3 lore raw

PATCH 1/3 dm: serial: Allow the UART driver to be dropped from the image

In reply to Simon Glass
Quoted 6 lines · Simon Glass

In very very space-constrained devices even the full UART driver is too large. In this case the debug UART can still be used in some cases.

Add options to enable the UART driver in SPL and U-Boot proper. Enable both options by default.

Quoted 7 lines

---

 drivers/serial/Kconfig         | 20 ++++++++++++++++++++
 drivers/serial/serial-uclass.c |  2 ++
 2 files changed, 22 insertions(+)

[snip]

Due to a build warning, added an #ifdef around serial_stub_putc() for cm_t43, and:

Applied to u-boot-dm/next.

#4 lore raw

PATCH 2/3 dm: ns16550: Allow the driver to be omitted if requested

In reply to Simon Glass

Allow the ns16550 debug UART to be used without the full driver.

---

 drivers/serial/ns16550.c | 2 ++
 1 file changed, 2 insertions(+)
drivers/serial/ns16550.c +2 -0
index 3fab3f1..2025423 100644
@@ -440,6 +440,7 @@ static const struct udevice_id ns16550_serial_ids[] = {
 };
 #endif
 
+#if CONFIG_IS_ENABLED(SERIAL_PRESENT)
 U_BOOT_DRIVER(ns16550_serial) = {
 	.name	= "ns16550_serial",
 	.id	= UCLASS_SERIAL,
@@ -453,4 +454,5 @@ U_BOOT_DRIVER(ns16550_serial) = {
 	.ops	= &ns16550_serial_ops,
 	.flags	= DM_FLAG_PRE_RELOC,
 };
+#endif
 #endif /* CONFIG_DM_SERIAL */
Signature · 1 line
2.6.0.rc2.230.g3dd15c0
#5 lore raw

PATCH 2/3 dm: ns16550: Allow the driver to be omitted if requested

Hi Simon,

Quoted 22 lines · Simon Glass

Allow the ns16550 debug UART to be used without the full driver.

---

  drivers/serial/ns16550.c | 2 ++
  1 file changed, 2 insertions(+)
drivers/serial/ns16550.c +1 -0
index 3fab3f1..2025423 100644
@@ -440,6 +440,7 @@ static const struct udevice_id ns16550_serial_ids[] = {
  };
  #endif
 
+#if CONFIG_IS_ENABLED(SERIAL_PRESENT)
  U_BOOT_DRIVER(ns16550_serial) = {
  	.name	= "ns16550_serial",
  	.id	= UCLASS_SERIAL,

drivers/serial/ns16550.c U_BOOT_DRIVER(ns16550_serial) = { · line 458

Quoted 5 lines
drivers/serial/ns16550.c +1 -0
@@ -453,4 +454,5 @@ U_BOOT_DRIVER(ns16550_serial) = {
  	.ops	= &ns16550_serial_ops,
  	.flags	= DM_FLAG_PRE_RELOC,
  };
+#endif
  #endif /* CONFIG_DM_SERIAL */
#6 lore raw

PATCH 2/3 dm: ns16550: Allow the driver to be omitted if requested

Applied to u-boot-dm/next.

#7 lore raw

PATCH 3/3 rockchip: Use the debug UART on rk3036

In reply to Simon Glass

Rather than using a new debug UART implementation, use the standard one provided by U-Boot.

---

 arch/arm/mach-rockchip/Makefile           |  1 -
 arch/arm/mach-rockchip/rk3036-board-spl.c |  9 ++++-
 arch/arm/mach-rockchip/rk_early_print.c   | 63 -------------------------------
 configs/evb-rk3036_defconfig              |  6 +++
 include/configs/rk3036_common.h           |  2 +
 5 files changed, 16 insertions(+), 65 deletions(-)
 delete mode 100644 arch/arm/mach-rockchip/rk_early_print.c
arch/arm/mach-rockchip/Makefile +0 -1
index b703c3c..1cc4a96 100644
@@ -11,7 +11,6 @@ else
 obj-$(CONFIG_ROCKCHIP_RK3288) += board.o
 endif
 obj-y += rk_timer.o
-obj-y += rk_early_print.o
 obj-$(CONFIG_$(SPL_)ROCKCHIP_COMMON) += common.o
 obj-$(CONFIG_ROCKCHIP_RK3288) += rk3288/
 obj-$(CONFIG_ROCKCHIP_RK3036) += rk3036/
arch/arm/mach-rockchip/rk3036-board-spl.c +8 -1
index 3a1491c..8015481 100644
@@ -5,6 +5,7 @@
  */
 
 #include <common.h>
+#include <debug_uart.h>
 #include <asm/io.h>
 #include <asm/arch/grf_rk3036.h>
 #include <asm/arch/hardware.h>
@@ -34,7 +35,7 @@ void board_init_f(ulong dummy)
 		     GPIO1C2_MASK << GPIO1C2_SHIFT,
 		     GPIO1C3_UART2_SOUT << GPIO1C3_SHIFT |
 		     GPIO1C2_UART2_SIN << GPIO1C2_SHIFT);
-	rk_uart_init((void *)DEBUG_UART_BASE);
+	debug_uart_init();
 #endif
 	rockchip_timer_init();
 	sdram_init();
@@ -53,3 +54,9 @@ void board_init_r(gd_t *id, ulong dest_addr)
 	while (1)
 		;
 }
+
+void hang(void)
+{
+	while (1)
+		;
+}
arch/arm/mach-rockchip/rk_early_print.c deleted +0 -63

63 lines not on this page · raw message

configs/evb-rk3036_defconfig +6 -0
index 2e915ff..c196bd6 100644
@@ -24,3 +24,9 @@ CONFIG_DM_MMC=y
 CONFIG_USE_PRIVATE_LIBGCC=y
 CONFIG_CMD_DHRYSTONE=y
 CONFIG_ERRNO_STR=y
+CONFIG_DEBUG_UART=y
+CONFIG_DEBUG_UART_NS16550=y
+CONFIG_DEBUG_UART_BASE=0x20068000
+CONFIG_DEBUG_UART_CLOCK=24000000
+CONFIG_DEBUG_UART_SHIFT=2
+# CONFIG_SPL_SERIAL_PRESENT is not set
include/configs/rk3036_common.h +2 -0
index f753e68..d22ea74 100644
@@ -24,6 +24,8 @@
 #define CONFIG_SYS_TIMER_BASE		0x200440a0 /* TIMER5 */
 #define CONFIG_SYS_TIMER_COUNTER	(CONFIG_SYS_TIMER_BASE + 8)
 
+#define CONFIG_SPL_SERIAL_SUPPORT
+
 #define CONFIG_SYS_NS16550
 #define CONFIG_SYS_NS16550_MEM32
 
Signature · 1 line
2.6.0.rc2.230.g3dd15c0
#8 lore raw

PATCH 3/3 rockchip: Use the debug UART on rk3036

Hi Simon,

Quoted 145 lines · Simon Glass

Rather than using a new debug UART implementation, use the standard one provided by U-Boot.

---

  arch/arm/mach-rockchip/Makefile           |  1 -
  arch/arm/mach-rockchip/rk3036-board-spl.c |  9 ++++-
  arch/arm/mach-rockchip/rk_early_print.c   | 63 -------------------------------
  configs/evb-rk3036_defconfig              |  6 +++
  include/configs/rk3036_common.h           |  2 +
  5 files changed, 16 insertions(+), 65 deletions(-)

delete mode 100644 arch/arm/mach-rockchip/rk_early_print.c

arch/arm/mach-rockchip/Makefile +0 -1
index b703c3c..1cc4a96 100644
@@ -11,7 +11,6 @@ else
  obj-$(CONFIG_ROCKCHIP_RK3288) += board.o
  endif
  obj-y += rk_timer.o
-obj-y += rk_early_print.o
  obj-$(CONFIG_$(SPL_)ROCKCHIP_COMMON) += common.o
  obj-$(CONFIG_ROCKCHIP_RK3288) += rk3288/
  obj-$(CONFIG_ROCKCHIP_RK3036) += rk3036/
arch/arm/mach-rockchip/rk3036-board-spl.c +8 -1
index 3a1491c..8015481 100644
@@ -5,6 +5,7 @@
   */
 
  #include <common.h>
+#include <debug_uart.h>
  #include <asm/io.h>
  #include <asm/arch/grf_rk3036.h>
  #include <asm/arch/hardware.h>
@@ -34,7 +35,7 @@ void board_init_f(ulong dummy)
  		     GPIO1C2_MASK << GPIO1C2_SHIFT,
  		     GPIO1C3_UART2_SOUT << GPIO1C3_SHIFT |
  		     GPIO1C2_UART2_SIN << GPIO1C2_SHIFT);
-	rk_uart_init((void *)DEBUG_UART_BASE);
+	debug_uart_init();
  #endif
  	rockchip_timer_init();
  	sdram_init();
@@ -53,3 +54,9 @@ void board_init_r(gd_t *id, ulong dest_addr)
  	while (1)
  		;
  }
+
+void hang(void)
+{
+	while (1)
+		;
+}
arch/arm/mach-rockchip/rk_early_print.c deleted +0 -63
deleted file mode 100644
index a1c14b0..0000000
@@ -1,63 +0,0 @@
-/*
- * (C) Copyright 2015 Rockchip Electronics Co., Ltd
- *
- * SPDX-License-Identifier:     GPL-2.0+
- */
-
-#include <asm/io.h>
-#include <asm/arch/uart.h>
-#include <common.h>
-
-static struct rk_uart *uart_ptr;
-
-static void uart_wrtie_byte(char byte)
-{
-	writel(byte, &uart_ptr->rbr);
-	while (!(readl(&uart_ptr->lsr) & 0x40))
-		;
-}
-
-void print(char *s)
-{
-	while (*s) {
-		if (*s == '\n')
-			uart_wrtie_byte('\r');
-	    uart_wrtie_byte(*s);
-	    s++;
-	}
-}
-
-void print_hex(unsigned int n)
-{
-	int i;
-	int temp;
-
-	uart_wrtie_byte('0');
-	uart_wrtie_byte('x');
-
-	for (i = 8; i > 0; i--) {
-		temp = (n >> (i - 1) * 4) & 0x0f;
-		if (temp < 10)
-			uart_wrtie_byte((char)(temp + '0'));
-		else
-			uart_wrtie_byte((char)(temp - 10 + 'a'));
-	}
-	uart_wrtie_byte('\n');
-	uart_wrtie_byte('\r');
-}
-
-/*
- * TODO: since rk3036 only 4K sram to use in SPL, for saving space,
- * we implement uart driver this way, we should convert this to use
- * ns16550 driver in future, which support DEBUG_UART in the standard way
- */
-void rk_uart_init(void *base)
-{
-	uart_ptr = (struct rk_uart *)base;
-	writel(0x83, &uart_ptr->lcr);
-	writel(0x0d, &uart_ptr->rbr);
-	writel(0x03, &uart_ptr->lcr);
-
-	/* fifo enable, sfe is shadow register of FCR[0] */
-	writel(0x01, &uart_ptr->sfe);
-}
configs/evb-rk3036_defconfig +6 -0
index 2e915ff..c196bd6 100644
@@ -24,3 +24,9 @@ CONFIG_DM_MMC=y
  CONFIG_USE_PRIVATE_LIBGCC=y
  CONFIG_CMD_DHRYSTONE=y
  CONFIG_ERRNO_STR=y
+CONFIG_DEBUG_UART=y
+CONFIG_DEBUG_UART_NS16550=y
+CONFIG_DEBUG_UART_BASE=0x20068000
+CONFIG_DEBUG_UART_CLOCK=24000000
+CONFIG_DEBUG_UART_SHIFT=2
+# CONFIG_SPL_SERIAL_PRESENT is not set
include/configs/rk3036_common.h +0 -0
index f753e68..d22ea74 100644

include/configs/rk3036_common.h line 31

Quoted 8 lines
include/configs/rk3036_common.h +2 -0
@@ -24,6 +24,8 @@
  #define CONFIG_SYS_TIMER_BASE		0x200440a0 /* TIMER5 */
  #define CONFIG_SYS_TIMER_COUNTER	(CONFIG_SYS_TIMER_BASE + 8)
 
+#define CONFIG_SPL_SERIAL_SUPPORT
+
  #define CONFIG_SYS_NS16550
  #define CONFIG_SYS_NS16550_MEM32
 
#9 lore raw

PATCH 3/3 rockchip: Use the debug UART on rk3036

Applied to u-boot-dm/next.

#10 lore raw

cover rockchip: Use the standard debug UART on rockchip

In reply to Simon Glass

Hi Simon.

Thank you for updating this series patch, i have verified it in
evb-rk3036 board,
it worked.

Quoted 30 lines · Simon Glass

The RK3036 has only 8KB of RAM available for SPL. At present it uses its own debug UART code.

By allowing the ns16550 driver to provide a debug UART without providing a full serial driver, we can enable a UART with a very small overhead. This requires addition Kconfig options. The debug UART supports printhex8(), printascii() and a few other functions.

The root driver and uclass are pulled in by this series, but their size is very small. It would possible to drop these by disabling CONFIG_DM_SERIAL. However the ns16550 driver makes this hard, due to it supporting operation without driver model, and operating differently in this case.

Simon Glass (3):
dm: serial: Allow the UART driver to be dropped from the image
dm: ns16550: Allow the driver to be omitted if requested
rockchip: Use the debug UART on rk3036

  arch/arm/mach-rockchip/Makefile           |  1 -
  arch/arm/mach-rockchip/rk3036-board-spl.c |  9 ++++-
  arch/arm/mach-rockchip/rk_early_print.c   | 63 -------------------------------
  configs/evb-rk3036_defconfig              |  6 +++
  drivers/serial/Kconfig                    | 20 ++++++++++
  drivers/serial/ns16550.c                  |  2 +
  drivers/serial/serial-uclass.c            |  2 +
  include/configs/rk3036_common.h           |  2 +
  8 files changed, 40 insertions(+), 65 deletions(-)

delete mode 100644 arch/arm/mach-rockchip/rk_early_print.c

Signature · 1 line
Lin Huang
#11 lore raw

cover rockchip: Use the standard debug UART on rockchip

HI Lin,

Quoted 6 lines · hl

Hi Simon.

Thank you for updating this series patch, i have verified it in
evb-rk3036 board,
it worked.

Great, thanks!

Quoted 37 lines · Simon Glass
Quoted 31 lines

The RK3036 has only 8KB of RAM available for SPL. At present it uses its own
debug UART code.

By allowing the ns16550 driver to provide a debug UART without providing a full serial driver, we can enable a UART with a very small overhead. This requires addition Kconfig options. The debug UART supports printhex8(), printascii() and a few other functions.

The root driver and uclass are pulled in by this series, but their size is very small. It would possible to drop these by disabling CONFIG_DM_SERIAL. However the ns16550 driver makes this hard, due to it supporting operation without driver model, and operating differently in this case.

Simon Glass (3):
dm: serial: Allow the UART driver to be dropped from the image
dm: ns16550: Allow the driver to be omitted if requested
rockchip: Use the debug UART on rk3036

  arch/arm/mach-rockchip/Makefile           |  1 -
  arch/arm/mach-rockchip/rk3036-board-spl.c |  9 ++++-
  arch/arm/mach-rockchip/rk_early_print.c   | 63
-------------------------------
  configs/evb-rk3036_defconfig              |  6 +++
  drivers/serial/Kconfig                    | 20 ++++++++++
  drivers/serial/ns16550.c                  |  2 +
  drivers/serial/serial-uclass.c            |  2 +
  include/configs/rk3036_common.h           |  2 +
  8 files changed, 40 insertions(+), 65 deletions(-)
Quoted 2 lines

delete mode 100644 arch/arm/mach-rockchip/rk_early_print.c

Quoted 4 lines

--
Lin Huang

Regards,
Simon