[U-Boot] [PATCH v5 1/4] riscv: Add kconfig option to run U-Boot in S-mode

Rick Chen rickchen36 at gmail.com
Tue Nov 27 06:40:55 UTC 2018


> > Subject: [PATCH v5 1/4] riscv: Add kconfig option to run U-Boot in S-mode
> >
> > 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 at brainfault.org>
> > Reviewed-by: Bin Meng <bmeng.cn at gmail.com>
> > Tested-by: Bin Meng <bmeng.cn at gmail.com>
> > Reviewed-by: Lukas Auer <lukas.auer at aisec.fraunhofer.de>
> > ---
> >  arch/riscv/Kconfig                |  5 +++++
> >  arch/riscv/cpu/start.S            | 33 ++++++++++++++++++++++++++++
> >  arch/riscv/include/asm/encoding.h |  2 ++
> >  arch/riscv/lib/interrupts.c       | 36 +++++++++++++++++++++++--------
> >  4 files changed, 67 insertions(+), 9 deletions(-)
> >
> > diff --git a/arch/riscv/Kconfig b/arch/riscv/Kconfig index 3e0af55e71..732a357a99
> > 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 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
> > 15e1b8199a..704190f946 100644
> > --- a/arch/riscv/cpu/start.S
> > +++ b/arch/riscv/cpu/start.S
> > @@ -41,10 +41,18 @@ _start:
> >       li      t0, CONFIG_SYS_SDRAM_BASE
> >       SREG    a2, 0(t0)
> >       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
> > @@ -166,7 +174,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 */
> > @@ -238,17 +250,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

It only the difference between s and m in csr.
The code seem to be duplicate too much.
Can you implement it in macro ?
or consider to separate it in different .S file

It may too complex to maintain in the future.

B.R
Rick


> >       LREG    x1, 1*REGBYTES(sp)
> >       LREG    x2, 2*REGBYTES(sp)
> >       LREG    x3, 3*REGBYTES(sp)
> > @@ -281,4 +310,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
> > diff --git a/arch/riscv/include/asm/encoding.h
> > b/arch/riscv/include/asm/encoding.h
> > index 9ea50ce640..153f5af2ff 100644
> > --- a/arch/riscv/include/asm/encoding.h
> > +++ b/arch/riscv/include/asm/encoding.h
> > @@ -143,6 +143,8 @@
> >  # define MCAUSE_CAUSE MCAUSE32_CAUSE
> >  #endif
> >
> > +#define SCAUSE_INT MCAUSE_INT
> > +
> >  #define RISCV_PGSHIFT 12
> >  #define RISCV_PGSIZE BIT(RISCV_PGSHIFT)
> >
> > diff --git a/arch/riscv/lib/interrupts.c b/arch/riscv/lib/interrupts.c index
> > 903a1c4cd5..8793f233d0 100644
> > --- a/arch/riscv/lib/interrupts.c
> > +++ b/arch/riscv/lib/interrupts.c
> > @@ -34,17 +34,35 @@ int disable_interrupts(void)
> >       return 0;
> >  }
> >
> > -ulong handle_trap(ulong mcause, ulong epc, struct pt_regs *regs)
> > +ulong handle_trap(ulong cause, ulong epc, struct pt_regs *regs)
> >  {
> > -     ulong is_int;
> > +     ulong is_irq, irq;
> >
> > -     is_int = (mcause & MCAUSE_INT);
> > -     if ((is_int) && ((mcause & MCAUSE_CAUSE)  == IRQ_M_EXT))
> > -             external_interrupt(0);  /* handle_m_ext_interrupt */
> > -     else if ((is_int) && ((mcause & MCAUSE_CAUSE)  == IRQ_M_TIMER))
> > -             timer_interrupt(0);     /* handle_m_timer_interrupt */
> > -     else
> > -             _exit_trap(mcause, epc, regs);
> > +#ifdef CONFIG_RISCV_SMODE
> > +     is_irq = (cause & SCAUSE_INT);
> > +     irq = (cause & ~SCAUSE_INT);
> > +#else
> > +     is_irq = (cause & MCAUSE_INT);
> > +     irq = (cause & ~MCAUSE_INT);
> > +#endif
> > +
> > +     if (is_irq) {
> > +             switch (irq) {
> > +             case IRQ_M_EXT:
> > +             case IRQ_S_EXT:
> > +                     external_interrupt(0);  /* handle external interrupt */
> > +                     break;
> > +             case IRQ_M_TIMER:
> > +             case IRQ_S_TIMER:
> > +                     timer_interrupt(0);     /* handle timer interrupt */
> > +                     break;
> > +             default:
> > +                     _exit_trap(cause, epc, regs);
> > +                     break;
> > +             };
> > +     } else {
> > +             _exit_trap(cause, epc, regs);
> > +     }
> >
> >       return epc;
> >  }
> > --
> > 2.17.1
>


More information about the U-Boot mailing list