[U-Boot] [PATCH v3 0/3] RISC-V S-mode support

This patchset allows us runing u-boot in S-mode which is useful on platforms where M-mode runtime firmware is an independent firmware and u-boot is used as last stage OS bootloader.
The patchset based upon git://git.denx.de/u-boot-riscv.git and is tested on QEMU in both M-mode and S-mode.
For S-mode testing, we have used u-boot.bin as payload of latest BBL (at commit 6ebd0f2a46255d0c76dad3c05b16c1d154795d26) applied with following changes:
diff --git a/machine/emulation.c b/machine/emulation.c index 132e977..def75e1 100644 --- a/machine/emulation.c +++ b/machine/emulation.c @@ -162,6 +162,12 @@ static inline int emulate_read_csr(int num, uintptr_t mstatus, uintptr_t* result
switch (num) { + case CSR_MISA: + *result = read_csr(misa); + return 0; + case CSR_MHARTID: + *result = read_csr(mhartid); + return 0; case CSR_CYCLE: if (!((counteren >> (CSR_CYCLE - CSR_CYCLE)) & 1)) return -1;
Changes since v2: - Dropped 'default n" from RISCV_SMODE kconfig option - Replaced '-smode_' in defconfig names with '_smode_'
Changes since v1: - Rebased upon latest git://git.denx.de/u-boot-riscv.git - Add details in cover letter for running u-boot in S-mode using BBL
Anup Patel (3): riscv: Add kconfig option to run u-boot in S-mode riscv: qemu: Use different SYS_TEXT_BASE for S-mode riscv: Add S-mode defconfigs for QEMU virt machine
arch/riscv/Kconfig | 5 ++++ arch/riscv/cpu/start.S | 33 ++++++++++++++++++++++++++ board/emulation/qemu-riscv/Kconfig | 3 ++- board/emulation/qemu-riscv/MAINTAINERS | 2 ++ configs/qemu-riscv32_smode_defconfig | 10 ++++++++ configs/qemu-riscv64_smode_defconfig | 11 +++++++++ 6 files changed, 63 insertions(+), 1 deletion(-) create mode 100644 configs/qemu-riscv32_smode_defconfig create mode 100644 configs/qemu-riscv64_smode_defconfig

This patch adds kconfig option RISCV_SMODE to run u-boot in S-mode. When this opition is enabled we use s<xyz> CSRs instead of m<xyz> CSRs.
It is important to note that there is no equivalent S-mode CSR for misa and mhartid CSRs so we expect M-mode runtime firmware (BBL or equivalent) to emulate misa and mhartid CSR read.
In-future, we will have more patches to avoid accessing misa and mhartid CSRs from S-mode.
Signed-off-by: Anup Patel anup@brainfault.org Reviewed-by: Bin Meng bmeng.cn@gmail.com Tested-by: Bin Meng bmeng.cn@gmail.com --- arch/riscv/Kconfig | 5 +++++ arch/riscv/cpu/start.S | 33 +++++++++++++++++++++++++++++++++ 2 files changed, 38 insertions(+)
diff --git a/arch/riscv/Kconfig b/arch/riscv/Kconfig index 3e0af55e71..8f2139ff60 100644 --- a/arch/riscv/Kconfig +++ b/arch/riscv/Kconfig @@ -55,6 +55,11 @@ config RISCV_ISA_C config RISCV_ISA_A def_bool y
+config RISCV_SMODE + bool "Run in S-Mode" + help + Enable this option to build an U-Boot for RISC-V S-Mode + config 32BIT bool
diff --git a/arch/riscv/cpu/start.S b/arch/riscv/cpu/start.S index 5af189b338..e4276e8e19 100644 --- a/arch/riscv/cpu/start.S +++ b/arch/riscv/cpu/start.S @@ -39,10 +39,18 @@ _start: mv s1, a1
la t0, trap_entry +#ifdef CONFIG_RISCV_SMODE + csrw stvec, t0 +#else csrw mtvec, t0 +#endif
/* mask all interrupts */ +#ifdef CONFIG_RISCV_SMODE + csrw sie, zero +#else csrw mie, zero +#endif
/* Enable cache */ jal icache_enable @@ -164,7 +172,11 @@ fix_rela_dyn: */ la t0, trap_entry add t0, t0, t6 +#ifdef CONFIG_RISCV_SMODE + csrw stvec, t0 +#else csrw mtvec, t0 +#endif
clear_bss: la t0, __bss_start /* t0 <- rel __bss_start in FLASH */ @@ -236,17 +248,34 @@ trap_entry: SREG x29, 29*REGBYTES(sp) SREG x30, 30*REGBYTES(sp) SREG x31, 31*REGBYTES(sp) +#ifdef CONFIG_RISCV_SMODE + csrr a0, scause + csrr a1, sepc +#else csrr a0, mcause csrr a1, mepc +#endif mv a2, sp jal handle_trap +#ifdef CONFIG_RISCV_SMODE + csrw sepc, a0 +#else csrw mepc, a0 +#endif
+#ifdef CONFIG_RISCV_SMODE +/* + * Remain in S-mode after sret + */ + li t0, SSTATUS_SPP + csrs sstatus, t0 +#else /* * Remain in M-mode after mret */ li t0, MSTATUS_MPP csrs mstatus, t0 +#endif LREG x1, 1*REGBYTES(sp) LREG x2, 2*REGBYTES(sp) LREG x3, 3*REGBYTES(sp) @@ -279,4 +308,8 @@ trap_entry: LREG x30, 30*REGBYTES(sp) LREG x31, 31*REGBYTES(sp) addi sp, sp, 32*REGBYTES +#ifdef CONFIG_RISCV_SMODE + sret +#else mret +#endif

Hi Anup,
On Wed, 2018-11-21 at 09:11 +0530, Anup Patel wrote:
This patch adds kconfig option RISCV_SMODE to run u-boot in
nit: U-Boot (also in the first line of the commit message)
S-mode. When this opition is enabled we use s<xyz> CSRs instead of m<xyz> CSRs.
It is important to note that there is no equivalent S-mode CSR for misa and mhartid CSRs so we expect M-mode runtime firmware (BBL or equivalent) to emulate misa and mhartid CSR read.
In-future, we will have more patches to avoid accessing misa and mhartid CSRs from S-mode.
Signed-off-by: Anup Patel anup@brainfault.org Reviewed-by: Bin Meng bmeng.cn@gmail.com Tested-by: Bin Meng bmeng.cn@gmail.com
arch/riscv/Kconfig | 5 +++++ arch/riscv/cpu/start.S | 33 +++++++++++++++++++++++++++++++++ 2 files changed, 38 insertions(+)
diff --git a/arch/riscv/Kconfig b/arch/riscv/Kconfig index 3e0af55e71..8f2139ff60 100644 --- a/arch/riscv/Kconfig +++ b/arch/riscv/Kconfig @@ -55,6 +55,11 @@ config RISCV_ISA_C config RISCV_ISA_A def_bool y
+config RISCV_SMODE
- bool "Run in S-Mode"
- help
Enable this option to build an U-Boot for RISC-V S-Mode
nit: there should be no "an" here
config 32BIT bool
diff --git a/arch/riscv/cpu/start.S b/arch/riscv/cpu/start.S index 5af189b338..e4276e8e19 100644 --- a/arch/riscv/cpu/start.S +++ b/arch/riscv/cpu/start.S @@ -39,10 +39,18 @@ _start: mv s1, a1
la t0, trap_entry +#ifdef CONFIG_RISCV_SMODE
It might make the code more readable by using defines for the CSRs, which are set to the correct values at the start of start.S depending on if CONFIG_RISCV_SMODE is set (similar to what we do for the load and store instructions). This is just a thought, I think this way is perfectly fine as well. :)
Reviewed-by: Lukas Auer lukas.auer@aisec.fraunhofer.de
Thanks, Lukas
- csrw stvec, t0
+#else csrw mtvec, t0 +#endif
/* mask all interrupts */ +#ifdef CONFIG_RISCV_SMODE
- csrw sie, zero
+#else csrw mie, zero +#endif
/* Enable cache */ jal icache_enable @@ -164,7 +172,11 @@ fix_rela_dyn: */ la t0, trap_entry add t0, t0, t6 +#ifdef CONFIG_RISCV_SMODE
- csrw stvec, t0
+#else csrw mtvec, t0 +#endif
clear_bss: la t0, __bss_start /* t0 <- rel __bss_start in FLASH */ @@ -236,17 +248,34 @@ trap_entry: SREG x29, 29*REGBYTES(sp) SREG x30, 30*REGBYTES(sp) SREG x31, 31*REGBYTES(sp) +#ifdef CONFIG_RISCV_SMODE
- csrr a0, scause
- csrr a1, sepc
+#else csrr a0, mcause csrr a1, mepc +#endif mv a2, sp jal handle_trap +#ifdef CONFIG_RISCV_SMODE
- csrw sepc, a0
+#else csrw mepc, a0 +#endif
+#ifdef CONFIG_RISCV_SMODE +/*
- Remain in S-mode after sret
- */
- li t0, SSTATUS_SPP
- csrs sstatus, t0
+#else /*
- Remain in M-mode after mret
*/ li t0, MSTATUS_MPP csrs mstatus, t0 +#endif LREG x1, 1*REGBYTES(sp) LREG x2, 2*REGBYTES(sp) LREG x3, 3*REGBYTES(sp) @@ -279,4 +308,8 @@ trap_entry: LREG x30, 30*REGBYTES(sp) LREG x31, 31*REGBYTES(sp) addi sp, sp, 32*REGBYTES +#ifdef CONFIG_RISCV_SMODE
- sret
+#else mret +#endif

Hi Anup,
On Wed, 2018-11-21 at 13:47 +0000, Auer, Lukas wrote:
Hi Anup,
On Wed, 2018-11-21 at 09:11 +0530, Anup Patel wrote:
This patch adds kconfig option RISCV_SMODE to run u-boot in
nit: U-Boot (also in the first line of the commit message)
S-mode. When this opition is enabled we use s<xyz> CSRs instead of m<xyz> CSRs.
Can you also modify arch/riscv/lib/interrupts.c to test for the supervisor instead of the machine timer and external interrupts when CONFIG_RISCV_SMODE is set?
Thanks, Lukas
It is important to note that there is no equivalent S-mode CSR for misa and mhartid CSRs so we expect M-mode runtime firmware (BBL or equivalent) to emulate misa and mhartid CSR read.
In-future, we will have more patches to avoid accessing misa and mhartid CSRs from S-mode.
Signed-off-by: Anup Patel anup@brainfault.org Reviewed-by: Bin Meng bmeng.cn@gmail.com Tested-by: Bin Meng bmeng.cn@gmail.com
arch/riscv/Kconfig | 5 +++++ arch/riscv/cpu/start.S | 33 +++++++++++++++++++++++++++++++++ 2 files changed, 38 insertions(+)
diff --git a/arch/riscv/Kconfig b/arch/riscv/Kconfig index 3e0af55e71..8f2139ff60 100644 --- a/arch/riscv/Kconfig +++ b/arch/riscv/Kconfig @@ -55,6 +55,11 @@ config RISCV_ISA_C config RISCV_ISA_A def_bool y
+config RISCV_SMODE
- bool "Run in S-Mode"
- help
Enable this option to build an U-Boot for RISC-V S-Mode
nit: there should be no "an" here
config 32BIT bool
diff --git a/arch/riscv/cpu/start.S b/arch/riscv/cpu/start.S index 5af189b338..e4276e8e19 100644 --- a/arch/riscv/cpu/start.S +++ b/arch/riscv/cpu/start.S @@ -39,10 +39,18 @@ _start: mv s1, a1
la t0, trap_entry +#ifdef CONFIG_RISCV_SMODE
It might make the code more readable by using defines for the CSRs, which are set to the correct values at the start of start.S depending on if CONFIG_RISCV_SMODE is set (similar to what we do for the load and store instructions). This is just a thought, I think this way is perfectly fine as well. :)
Reviewed-by: Lukas Auer lukas.auer@aisec.fraunhofer.de
Thanks, Lukas
- csrw stvec, t0
+#else csrw mtvec, t0 +#endif
/* mask all interrupts */ +#ifdef CONFIG_RISCV_SMODE
- csrw sie, zero
+#else csrw mie, zero +#endif
/* Enable cache */ jal icache_enable @@ -164,7 +172,11 @@ fix_rela_dyn: */ la t0, trap_entry add t0, t0, t6 +#ifdef CONFIG_RISCV_SMODE
- csrw stvec, t0
+#else csrw mtvec, t0 +#endif
clear_bss: la t0, __bss_start /* t0 <- rel __bss_start in FLASH */ @@ -236,17 +248,34 @@ trap_entry: SREG x29, 29*REGBYTES(sp) SREG x30, 30*REGBYTES(sp) SREG x31, 31*REGBYTES(sp) +#ifdef CONFIG_RISCV_SMODE
- csrr a0, scause
- csrr a1, sepc
+#else csrr a0, mcause csrr a1, mepc +#endif mv a2, sp jal handle_trap +#ifdef CONFIG_RISCV_SMODE
- csrw sepc, a0
+#else csrw mepc, a0 +#endif
+#ifdef CONFIG_RISCV_SMODE +/*
- Remain in S-mode after sret
- */
- li t0, SSTATUS_SPP
- csrs sstatus, t0
+#else /*
- Remain in M-mode after mret
*/ li t0, MSTATUS_MPP csrs mstatus, t0 +#endif LREG x1, 1*REGBYTES(sp) LREG x2, 2*REGBYTES(sp) LREG x3, 3*REGBYTES(sp) @@ -279,4 +308,8 @@ trap_entry: LREG x30, 30*REGBYTES(sp) LREG x31, 31*REGBYTES(sp) addi sp, sp, 32*REGBYTES +#ifdef CONFIG_RISCV_SMODE
- sret
+#else mret +#endif
U-Boot mailing list U-Boot@lists.denx.de https://lists.denx.de/listinfo/u-boot

On Thu, Nov 22, 2018 at 3:41 AM Auer, Lukas lukas.auer@aisec.fraunhofer.de wrote:
Hi Anup,
On Wed, 2018-11-21 at 13:47 +0000, Auer, Lukas wrote:
Hi Anup,
On Wed, 2018-11-21 at 09:11 +0530, Anup Patel wrote:
This patch adds kconfig option RISCV_SMODE to run u-boot in
nit: U-Boot (also in the first line of the commit message)
S-mode. When this opition is enabled we use s<xyz> CSRs instead of m<xyz> CSRs.
Can you also modify arch/riscv/lib/interrupts.c to test for the supervisor instead of the machine timer and external interrupts when CONFIG_RISCV_SMODE is set?
Sure, will do.
Regards, Anup

On Tue, 20 Nov 2018 19:41:10 PST (-0800), anup@brainfault.org wrote:
This patch adds kconfig option RISCV_SMODE to run u-boot in S-mode. When this opition is enabled we use s<xyz> CSRs instead of m<xyz> CSRs.
It is important to note that there is no equivalent S-mode CSR for misa and mhartid CSRs so we expect M-mode runtime firmware (BBL or equivalent) to emulate misa and mhartid CSR read.
In-future, we will have more patches to avoid accessing misa and mhartid CSRs from S-mode.
Ya, I don't like this. Our current boot protocol puts mhartid in a1 upon entering the supervisor, and allows the detection of misa via a device tree pointer provided in a0.
As long as everyone agrees this isn't what we're actually looking for then I'm fine with the patch, I just don't want to end up requiring this "M mode emulates some CSRs for S mode" interface. Since we don't have an actual platform spec we've got to be careful to avoid a bunch of defacto interfaces that we'll need to support later.
Signed-off-by: Anup Patel anup@brainfault.org Reviewed-by: Bin Meng bmeng.cn@gmail.com Tested-by: Bin Meng bmeng.cn@gmail.com
arch/riscv/Kconfig | 5 +++++ arch/riscv/cpu/start.S | 33 +++++++++++++++++++++++++++++++++ 2 files changed, 38 insertions(+)
diff --git a/arch/riscv/Kconfig b/arch/riscv/Kconfig index 3e0af55e71..8f2139ff60 100644 --- a/arch/riscv/Kconfig +++ b/arch/riscv/Kconfig @@ -55,6 +55,11 @@ config RISCV_ISA_C config RISCV_ISA_A def_bool y
+config RISCV_SMODE
- bool "Run in S-Mode"
- help
Enable this option to build an U-Boot for RISC-V S-Mode
config 32BIT bool
diff --git a/arch/riscv/cpu/start.S b/arch/riscv/cpu/start.S index 5af189b338..e4276e8e19 100644 --- a/arch/riscv/cpu/start.S +++ b/arch/riscv/cpu/start.S @@ -39,10 +39,18 @@ _start: mv s1, a1
la t0, trap_entry +#ifdef CONFIG_RISCV_SMODE
- csrw stvec, t0
+#else csrw mtvec, t0 +#endif
/* mask all interrupts */ +#ifdef CONFIG_RISCV_SMODE
- csrw sie, zero
+#else csrw mie, zero +#endif
/* Enable cache */ jal icache_enable @@ -164,7 +172,11 @@ fix_rela_dyn: */ la t0, trap_entry add t0, t0, t6 +#ifdef CONFIG_RISCV_SMODE
- csrw stvec, t0
+#else csrw mtvec, t0 +#endif
clear_bss: la t0, __bss_start /* t0 <- rel __bss_start in FLASH */ @@ -236,17 +248,34 @@ trap_entry: SREG x29, 29*REGBYTES(sp) SREG x30, 30*REGBYTES(sp) SREG x31, 31*REGBYTES(sp) +#ifdef CONFIG_RISCV_SMODE
- csrr a0, scause
- csrr a1, sepc
+#else csrr a0, mcause csrr a1, mepc +#endif mv a2, sp jal handle_trap +#ifdef CONFIG_RISCV_SMODE
- csrw sepc, a0
+#else csrw mepc, a0 +#endif
+#ifdef CONFIG_RISCV_SMODE +/*
- Remain in S-mode after sret
- */
- li t0, SSTATUS_SPP
- csrs sstatus, t0
+#else /*
- Remain in M-mode after mret
*/ li t0, MSTATUS_MPP csrs mstatus, t0 +#endif LREG x1, 1*REGBYTES(sp) LREG x2, 2*REGBYTES(sp) LREG x3, 3*REGBYTES(sp) @@ -279,4 +308,8 @@ trap_entry: LREG x30, 30*REGBYTES(sp) LREG x31, 31*REGBYTES(sp) addi sp, sp, 32*REGBYTES +#ifdef CONFIG_RISCV_SMODE
- sret
+#else mret +#endif

Hi Palmer,
On Wed, 2018-11-21 at 08:28 -0800, Palmer Dabbelt wrote:
On Tue, 20 Nov 2018 19:41:10 PST (-0800), anup@brainfault.org wrote:
This patch adds kconfig option RISCV_SMODE to run u-boot in S-mode. When this opition is enabled we use s<xyz> CSRs instead of m<xyz> CSRs.
It is important to note that there is no equivalent S-mode CSR for misa and mhartid CSRs so we expect M-mode runtime firmware (BBL or equivalent) to emulate misa and mhartid CSR read.
In-future, we will have more patches to avoid accessing misa and mhartid CSRs from S-mode.
Ya, I don't like this. Our current boot protocol puts mhartid in a1 upon entering the supervisor, and allows the detection of misa via a device tree pointer provided in a0.
As long as everyone agrees this isn't what we're actually looking for then I'm fine with the patch, I just don't want to end up requiring this "M mode emulates some CSRs for S mode" interface. Since we don't have an actual platform spec we've got to be careful to avoid a bunch of defacto interfaces that we'll need to support later.
I agree with you. We actually won't need the CSR emulation of misa and mhartid for long. With Bin's recent patch series [1], the ISA string is read from the device tree, replacing the use of misa. mhartid is only used to pass the hart id to the kernel. I am going to replace it in a patch series I am working on. So the interface should just be temporary.
Thanks, Lukas
[1]: https://patchwork.ozlabs.org/project/uboot/list/?series=75644
Signed-off-by: Anup Patel anup@brainfault.org Reviewed-by: Bin Meng bmeng.cn@gmail.com Tested-by: Bin Meng bmeng.cn@gmail.com
arch/riscv/Kconfig | 5 +++++ arch/riscv/cpu/start.S | 33 +++++++++++++++++++++++++++++++++ 2 files changed, 38 insertions(+)
diff --git a/arch/riscv/Kconfig b/arch/riscv/Kconfig index 3e0af55e71..8f2139ff60 100644 --- a/arch/riscv/Kconfig +++ b/arch/riscv/Kconfig @@ -55,6 +55,11 @@ config RISCV_ISA_C config RISCV_ISA_A def_bool y
+config RISCV_SMODE
- bool "Run in S-Mode"
- help
Enable this option to build an U-Boot for RISC-V S-Mode
config 32BIT bool
diff --git a/arch/riscv/cpu/start.S b/arch/riscv/cpu/start.S index 5af189b338..e4276e8e19 100644 --- a/arch/riscv/cpu/start.S +++ b/arch/riscv/cpu/start.S @@ -39,10 +39,18 @@ _start: mv s1, a1
la t0, trap_entry +#ifdef CONFIG_RISCV_SMODE
- csrw stvec, t0
+#else csrw mtvec, t0 +#endif
/* mask all interrupts */ +#ifdef CONFIG_RISCV_SMODE
- csrw sie, zero
+#else csrw mie, zero +#endif
/* Enable cache */ jal icache_enable @@ -164,7 +172,11 @@ fix_rela_dyn: */ la t0, trap_entry add t0, t0, t6 +#ifdef CONFIG_RISCV_SMODE
- csrw stvec, t0
+#else csrw mtvec, t0 +#endif
clear_bss: la t0, __bss_start /* t0 <- rel __bss_start in FLASH */ @@ -236,17 +248,34 @@ trap_entry: SREG x29, 29*REGBYTES(sp) SREG x30, 30*REGBYTES(sp) SREG x31, 31*REGBYTES(sp) +#ifdef CONFIG_RISCV_SMODE
- csrr a0, scause
- csrr a1, sepc
+#else csrr a0, mcause csrr a1, mepc +#endif mv a2, sp jal handle_trap +#ifdef CONFIG_RISCV_SMODE
- csrw sepc, a0
+#else csrw mepc, a0 +#endif
+#ifdef CONFIG_RISCV_SMODE +/*
- Remain in S-mode after sret
- */
- li t0, SSTATUS_SPP
- csrs sstatus, t0
+#else /*
- Remain in M-mode after mret
*/ li t0, MSTATUS_MPP csrs mstatus, t0 +#endif LREG x1, 1*REGBYTES(sp) LREG x2, 2*REGBYTES(sp) LREG x3, 3*REGBYTES(sp) @@ -279,4 +308,8 @@ trap_entry: LREG x30, 30*REGBYTES(sp) LREG x31, 31*REGBYTES(sp) addi sp, sp, 32*REGBYTES +#ifdef CONFIG_RISCV_SMODE
- sret
+#else mret +#endif

On Wed, 21 Nov 2018 14:06:00 PST (-0800), lukas.auer@aisec.fraunhofer.de wrote:
Hi Palmer,
On Wed, 2018-11-21 at 08:28 -0800, Palmer Dabbelt wrote:
On Tue, 20 Nov 2018 19:41:10 PST (-0800), anup@brainfault.org wrote:
This patch adds kconfig option RISCV_SMODE to run u-boot in S-mode. When this opition is enabled we use s<xyz> CSRs instead of m<xyz> CSRs.
It is important to note that there is no equivalent S-mode CSR for misa and mhartid CSRs so we expect M-mode runtime firmware (BBL or equivalent) to emulate misa and mhartid CSR read.
In-future, we will have more patches to avoid accessing misa and mhartid CSRs from S-mode.
Ya, I don't like this. Our current boot protocol puts mhartid in a1 upon entering the supervisor, and allows the detection of misa via a device tree pointer provided in a0.
As long as everyone agrees this isn't what we're actually looking for then I'm fine with the patch, I just don't want to end up requiring this "M mode emulates some CSRs for S mode" interface. Since we don't have an actual platform spec we've got to be careful to avoid a bunch of defacto interfaces that we'll need to support later.
I agree with you. We actually won't need the CSR emulation of misa and mhartid for long. With Bin's recent patch series [1], the ISA string is read from the device tree, replacing the use of misa. mhartid is only used to pass the hart id to the kernel. I am going to replace it in a patch series I am working on. So the interface should just be temporary.
Great, thanks!
Thanks, Lukas
Signed-off-by: Anup Patel anup@brainfault.org Reviewed-by: Bin Meng bmeng.cn@gmail.com Tested-by: Bin Meng bmeng.cn@gmail.com
arch/riscv/Kconfig | 5 +++++ arch/riscv/cpu/start.S | 33 +++++++++++++++++++++++++++++++++ 2 files changed, 38 insertions(+)
diff --git a/arch/riscv/Kconfig b/arch/riscv/Kconfig index 3e0af55e71..8f2139ff60 100644 --- a/arch/riscv/Kconfig +++ b/arch/riscv/Kconfig @@ -55,6 +55,11 @@ config RISCV_ISA_C config RISCV_ISA_A def_bool y
+config RISCV_SMODE
- bool "Run in S-Mode"
- help
Enable this option to build an U-Boot for RISC-V S-Mode
config 32BIT bool
diff --git a/arch/riscv/cpu/start.S b/arch/riscv/cpu/start.S index 5af189b338..e4276e8e19 100644 --- a/arch/riscv/cpu/start.S +++ b/arch/riscv/cpu/start.S @@ -39,10 +39,18 @@ _start: mv s1, a1
la t0, trap_entry +#ifdef CONFIG_RISCV_SMODE
- csrw stvec, t0
+#else csrw mtvec, t0 +#endif
/* mask all interrupts */ +#ifdef CONFIG_RISCV_SMODE
- csrw sie, zero
+#else csrw mie, zero +#endif
/* Enable cache */ jal icache_enable @@ -164,7 +172,11 @@ fix_rela_dyn: */ la t0, trap_entry add t0, t0, t6 +#ifdef CONFIG_RISCV_SMODE
- csrw stvec, t0
+#else csrw mtvec, t0 +#endif
clear_bss: la t0, __bss_start /* t0 <- rel __bss_start in FLASH */ @@ -236,17 +248,34 @@ trap_entry: SREG x29, 29*REGBYTES(sp) SREG x30, 30*REGBYTES(sp) SREG x31, 31*REGBYTES(sp) +#ifdef CONFIG_RISCV_SMODE
- csrr a0, scause
- csrr a1, sepc
+#else csrr a0, mcause csrr a1, mepc +#endif mv a2, sp jal handle_trap +#ifdef CONFIG_RISCV_SMODE
- csrw sepc, a0
+#else csrw mepc, a0 +#endif
+#ifdef CONFIG_RISCV_SMODE +/*
- Remain in S-mode after sret
- */
- li t0, SSTATUS_SPP
- csrs sstatus, t0
+#else /*
- Remain in M-mode after mret
*/ li t0, MSTATUS_MPP csrs mstatus, t0 +#endif LREG x1, 1*REGBYTES(sp) LREG x2, 2*REGBYTES(sp) LREG x3, 3*REGBYTES(sp) @@ -279,4 +308,8 @@ trap_entry: LREG x30, 30*REGBYTES(sp) LREG x31, 31*REGBYTES(sp) addi sp, sp, 32*REGBYTES +#ifdef CONFIG_RISCV_SMODE
- sret
+#else mret +#endif

On Wed, Nov 21, 2018 at 9:58 PM Palmer Dabbelt palmer@sifive.com wrote:
On Tue, 20 Nov 2018 19:41:10 PST (-0800), anup@brainfault.org wrote:
This patch adds kconfig option RISCV_SMODE to run u-boot in S-mode. When this opition is enabled we use s<xyz> CSRs instead of m<xyz> CSRs.
It is important to note that there is no equivalent S-mode CSR for misa and mhartid CSRs so we expect M-mode runtime firmware (BBL or equivalent) to emulate misa and mhartid CSR read.
In-future, we will have more patches to avoid accessing misa and mhartid CSRs from S-mode.
Ya, I don't like this. Our current boot protocol puts mhartid in a1 upon entering the supervisor, and allows the detection of misa via a device tree pointer provided in a0.
As long as everyone agrees this isn't what we're actually looking for then I'm fine with the patch, I just don't want to end up requiring this "M mode emulates some CSRs for S mode" interface. Since we don't have an actual platform spec we've got to be careful to avoid a bunch of defacto interfaces that we'll need to support later.
Yes, it's a temporary thingy to emulate misa and mhartid in BBL.
Eventually, U-Boot will be fixed to avoid direct access of misa and mhartid.
Regards, Anup

Hi Palmer,
On Thu, Nov 22, 2018 at 12:28 AM Palmer Dabbelt palmer@sifive.com wrote:
On Tue, 20 Nov 2018 19:41:10 PST (-0800), anup@brainfault.org wrote:
This patch adds kconfig option RISCV_SMODE to run u-boot in S-mode. When this opition is enabled we use s<xyz> CSRs instead of m<xyz> CSRs.
It is important to note that there is no equivalent S-mode CSR for misa and mhartid CSRs so we expect M-mode runtime firmware (BBL or equivalent) to emulate misa and mhartid CSR read.
In-future, we will have more patches to avoid accessing misa and mhartid CSRs from S-mode.
Ya, I don't like this. Our current boot protocol puts mhartid in a1 upon entering the supervisor, and allows the detection of misa via a device tree pointer provided in a0.
As Anup mentioned in the commit message, the read of mhartid in *S-mode* should be fixed in future patches. We still need it for M-mode.
As long as everyone agrees this isn't what we're actually looking for then I'm fine with the patch, I just don't want to end up requiring this "M mode emulates some CSRs for S mode" interface. Since we don't have an actual platform spec we've got to be careful to avoid a bunch of defacto interfaces that we'll need to support later.
Agreed.
Regards, Bin

When u-boot runs in S-mode, the M-mode runtime firmware (BBL or equivalent) uses memory range in 0x80000000 to 0x80200000. Due to this, we cannot use 0x80000000 as SYS_TEXT_BASE when running in S-mode. Instead for S-mode, we use 0x80200000 as SYS_TEXT_BASE.
Even Linux RISC-V kernel ignores/reserves memory range 0x80000000 to 0x80200000 because it runs in S-mode.
Signed-off-by: Anup Patel anup@brainfault.org Reviewed-by: Bin Meng bmeng.cn@gmail.com Tested-by: Bin Meng bmeng.cn@gmail.com --- board/emulation/qemu-riscv/Kconfig | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/board/emulation/qemu-riscv/Kconfig b/board/emulation/qemu-riscv/Kconfig index 33ca253432..56bb5337d4 100644 --- a/board/emulation/qemu-riscv/Kconfig +++ b/board/emulation/qemu-riscv/Kconfig @@ -13,7 +13,8 @@ config SYS_CONFIG_NAME default "qemu-riscv"
config SYS_TEXT_BASE - default 0x80000000 + default 0x80000000 if !RISCV_SMODE + default 0x80200000 if RISCV_SMODE
config BOARD_SPECIFIC_OPTIONS # dummy def_bool y

On Wed, 2018-11-21 at 09:11 +0530, Anup Patel wrote:
When u-boot runs in S-mode, the M-mode runtime firmware (BBL or equivalent) uses memory range in 0x80000000 to 0x80200000. Due to this, we cannot use 0x80000000 as SYS_TEXT_BASE when running in S-mode. Instead for S-mode, we use 0x80200000 as SYS_TEXT_BASE.
Even Linux RISC-V kernel ignores/reserves memory range 0x80000000 to 0x80200000 because it runs in S-mode.
Signed-off-by: Anup Patel anup@brainfault.org Reviewed-by: Bin Meng bmeng.cn@gmail.com Tested-by: Bin Meng bmeng.cn@gmail.com
board/emulation/qemu-riscv/Kconfig | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
Reviewed-by: Lukas Auer lukas.auer@aisec.fraunhofer.de

This patch adds S-mode defconfigs for QEMU virt machine so that we can run u-boot in S-mode on QEMU using M-mode runtime firmware (BBL or equivalent).
Signed-off-by: Anup Patel anup@brainfault.org Reviewed-by: Bin Meng bmeng.cn@gmail.com Tested-by: Bin Meng bmeng.cn@gmail.com --- board/emulation/qemu-riscv/MAINTAINERS | 2 ++ configs/qemu-riscv32_smode_defconfig | 10 ++++++++++ configs/qemu-riscv64_smode_defconfig | 11 +++++++++++ 3 files changed, 23 insertions(+) create mode 100644 configs/qemu-riscv32_smode_defconfig create mode 100644 configs/qemu-riscv64_smode_defconfig
diff --git a/board/emulation/qemu-riscv/MAINTAINERS b/board/emulation/qemu-riscv/MAINTAINERS index 3c6eb4f844..c701c83d77 100644 --- a/board/emulation/qemu-riscv/MAINTAINERS +++ b/board/emulation/qemu-riscv/MAINTAINERS @@ -4,4 +4,6 @@ S: Maintained F: board/emulation/qemu-riscv/ F: include/configs/qemu-riscv.h F: configs/qemu-riscv32_defconfig +F: configs/qemu-riscv32_smode_defconfig F: configs/qemu-riscv64_defconfig +F: configs/qemu-riscv64_smode_defconfig diff --git a/configs/qemu-riscv32_smode_defconfig b/configs/qemu-riscv32_smode_defconfig new file mode 100644 index 0000000000..0a84ec1874 --- /dev/null +++ b/configs/qemu-riscv32_smode_defconfig @@ -0,0 +1,10 @@ +CONFIG_RISCV=y +CONFIG_TARGET_QEMU_VIRT=y +CONFIG_RISCV_SMODE=y +CONFIG_DISTRO_DEFAULTS=y +CONFIG_NR_DRAM_BANKS=1 +CONFIG_FIT=y +CONFIG_DISPLAY_CPUINFO=y +CONFIG_DISPLAY_BOARDINFO=y +# CONFIG_CMD_MII is not set +CONFIG_OF_PRIOR_STAGE=y diff --git a/configs/qemu-riscv64_smode_defconfig b/configs/qemu-riscv64_smode_defconfig new file mode 100644 index 0000000000..b012443370 --- /dev/null +++ b/configs/qemu-riscv64_smode_defconfig @@ -0,0 +1,11 @@ +CONFIG_RISCV=y +CONFIG_TARGET_QEMU_VIRT=y +CONFIG_ARCH_RV64I=y +CONFIG_RISCV_SMODE=y +CONFIG_DISTRO_DEFAULTS=y +CONFIG_NR_DRAM_BANKS=1 +CONFIG_FIT=y +CONFIG_DISPLAY_CPUINFO=y +CONFIG_DISPLAY_BOARDINFO=y +# CONFIG_CMD_MII is not set +CONFIG_OF_PRIOR_STAGE=y

On Wed, 2018-11-21 at 09:11 +0530, Anup Patel wrote:
This patch adds S-mode defconfigs for QEMU virt machine so that we can run u-boot in S-mode on QEMU using M-mode runtime firmware (BBL or equivalent).
Signed-off-by: Anup Patel anup@brainfault.org Reviewed-by: Bin Meng bmeng.cn@gmail.com Tested-by: Bin Meng bmeng.cn@gmail.com
board/emulation/qemu-riscv/MAINTAINERS | 2 ++ configs/qemu-riscv32_smode_defconfig | 10 ++++++++++ configs/qemu-riscv64_smode_defconfig | 11 +++++++++++ 3 files changed, 23 insertions(+) create mode 100644 configs/qemu-riscv32_smode_defconfig create mode 100644 configs/qemu-riscv64_smode_defconfig
Reviewed-by: Lukas Auer lukas.auer@aisec.fraunhofer.de
participants (4)
-
Anup Patel
-
Auer, Lukas
-
Bin Meng
-
Palmer Dabbelt