@@ -31,6 +31,7 @@ gen_se_header=
enable_dump=no
page_size=
earlycon=
+console=
efi=
efi_direct=
@@ -78,7 +79,7 @@ usage() {
4k [default], 16k, 64k for arm64.
4k [default], 64k for ppc64.
--earlycon=EARLYCON
- Specify the UART name, type and address (optional).
+ Specify the UART name, type and address used for the earlycon (optional).
The specified address will overwrite the UART address set by
the --target option. EARLYCON can be one of (case sensitive):
uart[8250],mmio,ADDR
@@ -89,6 +90,9 @@ usage() {
Specify a PL011 compatible UART at address ADDR. Supported
register stride is 32 bit only.
(arm/arm64 and riscv32/riscv64 only)
+ --console=CONSOLE
+ Specify the device used for output (optional).
+ sbi Use SBI DBCN (riscv only)
--[enable|disable]-efi Boot and run from UEFI (disabled by default, x86_64 and arm64 only)
--[enable|disable]-werror
Select whether to compile with the -Werror compiler flag
@@ -175,6 +179,9 @@ while [[ $optno -le $argc ]]; do
--earlycon)
earlycon="$arg"
;;
+ --console)
+ console="$arg"
+ ;;
--enable-efi)
efi=y
;;
@@ -503,10 +510,8 @@ cat <<EOF >> lib/config.h
EOF
elif [ "$arch" = "riscv32" ] || [ "$arch" = "riscv64" ]; then
-cat <<EOF >> lib/config.h
-
-#define CONFIG_UART_EARLY_BASE ${uart_early_addr}
-
-EOF
+ echo "#define CONFIG_UART_EARLY_BASE ${uart_early_addr}" >> lib/config.h
+ [ "$console" = "sbi" ] && echo "#define CONFIG_SBI_CONSOLE" >> lib/config.h
+ echo >> lib/config.h
fi
echo "#endif" >> lib/config.h
@@ -6,6 +6,7 @@
* Copyright (C) 2023, Ventana Micro Systems Inc., Andrew Jones <ajones@ventanamicro.com>
*/
#include <libcflat.h>
+#include <bitops.h>
#include <config.h>
#include <devicetree.h>
#include <asm/io.h>
@@ -29,6 +30,7 @@ static u32 uart0_reg_shift = 1;
static u32 uart0_reg_width = 1;
static struct spinlock uart_lock;
+#ifndef CONFIG_SBI_CONSOLE
static u32 uart0_read(u32 num)
{
u32 offset = num << uart0_reg_shift;
@@ -52,6 +54,7 @@ static void uart0_write(u32 num, u32 val)
else
writel(val, uart0_base + offset);
}
+#endif
static void uart0_init_fdt(void)
{
@@ -113,6 +116,18 @@ void io_init(void)
}
}
+#ifdef CONFIG_SBI_CONSOLE
+void puts(const char *s)
+{
+ phys_addr_t addr = virt_to_phys((void *)s);
+ unsigned long hi = upper_32_bits(addr);
+ unsigned long lo = lower_32_bits(addr);
+
+ spin_lock(&uart_lock);
+ sbi_ecall(SBI_EXT_DBCN, SBI_EXT_DBCN_CONSOLE_WRITE, strlen(s), lo, hi, 0, 0, 0);
+ spin_unlock(&uart_lock);
+}
+#else
void puts(const char *s)
{
spin_lock(&uart_lock);
@@ -123,6 +138,7 @@ void puts(const char *s)
}
spin_unlock(&uart_lock);
}
+#endif
/*
* Defining halt to take 'code' as an argument guarantees that it will
We don't want to add support for lots of UARTs nor lots of support for UARTs. Thankfully SBI may have the DBCN extension, allowing us to use that instead when our simple UART support is insufficient. Signed-off-by: Andrew Jones <andrew.jones@linux.dev> --- configure | 17 +++++++++++------ lib/riscv/io.c | 16 ++++++++++++++++ 2 files changed, 27 insertions(+), 6 deletions(-)