Message ID | c614e69342eea7a5ce27f7a0e550ab3147afa592.1675779308.git.oleksii.kurochko@gmail.com (mailing list archive) |
---|---|
State | Superseded |
Headers | show |
Series | RISCV basic exception handling implementation | expand |
On Wed, Feb 8, 2023 at 12:47 AM Oleksii Kurochko <oleksii.kurochko@gmail.com> wrote: > > The patch introduces an implementation of basic exception handlers: > - to save/restore context > - to handle an exception itself. The handler calls wait_for_interrupt > now, nothing more. > > Signed-off-by: Oleksii Kurochko <oleksii.kurochko@gmail.com> Reviewed-by: Alistair Francis <alistair.francis@wdc.com> Alistair > --- > Changes in V3: > - Nothing changed > --- > Changes in V2: > - Refactor entry.S to start using of defines introduced in asm_offsets.C > - Rename {__,}handle_exception to handle_trap() and do_trap() to be more > consistent with RISC-V spec. > - Wrap handle_trap() to ENTRY(). > --- > xen/arch/riscv/Makefile | 2 + > xen/arch/riscv/entry.S | 94 ++++++++++++++++++++++++++++++ > xen/arch/riscv/include/asm/traps.h | 13 +++++ > xen/arch/riscv/traps.c | 13 +++++ > 4 files changed, 122 insertions(+) > create mode 100644 xen/arch/riscv/entry.S > create mode 100644 xen/arch/riscv/include/asm/traps.h > create mode 100644 xen/arch/riscv/traps.c > > diff --git a/xen/arch/riscv/Makefile b/xen/arch/riscv/Makefile > index 1a4f1a6015..443f6bf15f 100644 > --- a/xen/arch/riscv/Makefile > +++ b/xen/arch/riscv/Makefile > @@ -1,7 +1,9 @@ > obj-$(CONFIG_EARLY_PRINTK) += early_printk.o > +obj-y += entry.o > obj-$(CONFIG_RISCV_64) += riscv64/ > obj-y += sbi.o > obj-y += setup.o > +obj-y += traps.o > > $(TARGET): $(TARGET)-syms > $(OBJCOPY) -O binary -S $< $@ > diff --git a/xen/arch/riscv/entry.S b/xen/arch/riscv/entry.S > new file mode 100644 > index 0000000000..0be543f8e0 > --- /dev/null > +++ b/xen/arch/riscv/entry.S > @@ -0,0 +1,94 @@ > +#include <asm/asm.h> > +#include <asm/asm-offsets.h> > +#include <asm/processor.h> > +#include <asm/riscv_encoding.h> > +#include <asm/traps.h> > + > +/* WIP: only works while interrupting Xen context */ > +ENTRY(handle_trap) > + > + /* Exceptions from xen */ > +save_to_stack: > + /* Save context to stack */ > + REG_S sp, (CPU_USER_REGS_SP - CPU_USER_REGS_SIZE) (sp) > + addi sp, sp, -CPU_USER_REGS_SIZE > + REG_S t0, CPU_USER_REGS_T0(sp) > + > + /* Save registers */ > + REG_S ra, CPU_USER_REGS_RA(sp) > + REG_S gp, CPU_USER_REGS_GP(sp) > + REG_S t1, CPU_USER_REGS_T1(sp) > + REG_S t2, CPU_USER_REGS_T2(sp) > + REG_S s0, CPU_USER_REGS_S0(sp) > + REG_S s1, CPU_USER_REGS_S1(sp) > + REG_S a0, CPU_USER_REGS_A0(sp) > + REG_S a1, CPU_USER_REGS_A1(sp) > + REG_S a2, CPU_USER_REGS_A2(sp) > + REG_S a3, CPU_USER_REGS_A3(sp) > + REG_S a4, CPU_USER_REGS_A4(sp) > + REG_S a5, CPU_USER_REGS_A5(sp) > + REG_S a6, CPU_USER_REGS_A6(sp) > + REG_S a7, CPU_USER_REGS_A7(sp) > + REG_S s2, CPU_USER_REGS_S2(sp) > + REG_S s3, CPU_USER_REGS_S3(sp) > + REG_S s4, CPU_USER_REGS_S4(sp) > + REG_S s5, CPU_USER_REGS_S5(sp) > + REG_S s6, CPU_USER_REGS_S6(sp) > + REG_S s7, CPU_USER_REGS_S7(sp) > + REG_S s8, CPU_USER_REGS_S8(sp) > + REG_S s9, CPU_USER_REGS_S9(sp) > + REG_S s10,CPU_USER_REGS_S10(sp) > + REG_S s11,CPU_USER_REGS_S11(sp) > + REG_S t3, CPU_USER_REGS_T3(sp) > + REG_S t4, CPU_USER_REGS_T4(sp) > + REG_S t5, CPU_USER_REGS_T5(sp) > + REG_S t6, CPU_USER_REGS_T6(sp) > + csrr t0, CSR_SEPC > + REG_S t0, CPU_USER_REGS_SEPC(sp) > + csrr t0, CSR_SSTATUS > + REG_S t0, CPU_USER_REGS_SSTATUS(sp) > + > + mv a0, sp > + jal do_trap > + > +restore_registers: > + /* Restore stack_cpu_regs */ > + REG_L t0, CPU_USER_REGS_SEPC(sp) > + csrw CSR_SEPC, t0 > + REG_L t0, CPU_USER_REGS_SSTATUS(sp) > + csrw CSR_SSTATUS, t0 > + > + REG_L ra, CPU_USER_REGS_RA(sp) > + REG_L gp, CPU_USER_REGS_GP(sp) > + REG_L t0, CPU_USER_REGS_T0(sp) > + REG_L t1, CPU_USER_REGS_T1(sp) > + REG_L t2, CPU_USER_REGS_T2(sp) > + REG_L s0, CPU_USER_REGS_S0(sp) > + REG_L s1, CPU_USER_REGS_S1(sp) > + REG_L a0, CPU_USER_REGS_A0(sp) > + REG_L a1, CPU_USER_REGS_A1(sp) > + REG_L a2, CPU_USER_REGS_A2(sp) > + REG_L a3, CPU_USER_REGS_A3(sp) > + REG_L a4, CPU_USER_REGS_A4(sp) > + REG_L a5, CPU_USER_REGS_A5(sp) > + REG_L a6, CPU_USER_REGS_A6(sp) > + REG_L a7, CPU_USER_REGS_A7(sp) > + REG_L s2, CPU_USER_REGS_S2(sp) > + REG_L s3, CPU_USER_REGS_S3(sp) > + REG_L s4, CPU_USER_REGS_S4(sp) > + REG_L s5, CPU_USER_REGS_S5(sp) > + REG_L s6, CPU_USER_REGS_S6(sp) > + REG_L s7, CPU_USER_REGS_S7(sp) > + REG_L s8, CPU_USER_REGS_S8(sp) > + REG_L s9, CPU_USER_REGS_S9(sp) > + REG_L s10, CPU_USER_REGS_S10(sp) > + REG_L s11, CPU_USER_REGS_S11(sp) > + REG_L t3, CPU_USER_REGS_T3(sp) > + REG_L t4, CPU_USER_REGS_T4(sp) > + REG_L t5, CPU_USER_REGS_T5(sp) > + REG_L t6, CPU_USER_REGS_T6(sp) > + > + /* Restore sp */ > + REG_L sp, CPU_USER_REGS_SP(sp) > + > + sret > diff --git a/xen/arch/riscv/include/asm/traps.h b/xen/arch/riscv/include/asm/traps.h > new file mode 100644 > index 0000000000..f3fb6b25d1 > --- /dev/null > +++ b/xen/arch/riscv/include/asm/traps.h > @@ -0,0 +1,13 @@ > +#ifndef __ASM_TRAPS_H__ > +#define __ASM_TRAPS_H__ > + > +#include <asm/processor.h> > + > +#ifndef __ASSEMBLY__ > + > +void do_trap(struct cpu_user_regs *cpu_regs); > +void handle_trap(void); > + > +#endif /* __ASSEMBLY__ */ > + > +#endif /* __ASM_TRAPS_H__ */ > diff --git a/xen/arch/riscv/traps.c b/xen/arch/riscv/traps.c > new file mode 100644 > index 0000000000..ccd3593f5a > --- /dev/null > +++ b/xen/arch/riscv/traps.c > @@ -0,0 +1,13 @@ > +/* SPDX-License-Identifier: GPL-2.0-or-later */ > +/* > + * Copyright (C) 2023 Vates > + * > + * RISC-V Trap handlers > + */ > +#include <asm/processor.h> > +#include <asm/traps.h> > + > +void do_trap(struct cpu_user_regs *cpu_regs) > +{ > + die(); > +} > -- > 2.39.0 > >
diff --git a/xen/arch/riscv/Makefile b/xen/arch/riscv/Makefile index 1a4f1a6015..443f6bf15f 100644 --- a/xen/arch/riscv/Makefile +++ b/xen/arch/riscv/Makefile @@ -1,7 +1,9 @@ obj-$(CONFIG_EARLY_PRINTK) += early_printk.o +obj-y += entry.o obj-$(CONFIG_RISCV_64) += riscv64/ obj-y += sbi.o obj-y += setup.o +obj-y += traps.o $(TARGET): $(TARGET)-syms $(OBJCOPY) -O binary -S $< $@ diff --git a/xen/arch/riscv/entry.S b/xen/arch/riscv/entry.S new file mode 100644 index 0000000000..0be543f8e0 --- /dev/null +++ b/xen/arch/riscv/entry.S @@ -0,0 +1,94 @@ +#include <asm/asm.h> +#include <asm/asm-offsets.h> +#include <asm/processor.h> +#include <asm/riscv_encoding.h> +#include <asm/traps.h> + +/* WIP: only works while interrupting Xen context */ +ENTRY(handle_trap) + + /* Exceptions from xen */ +save_to_stack: + /* Save context to stack */ + REG_S sp, (CPU_USER_REGS_SP - CPU_USER_REGS_SIZE) (sp) + addi sp, sp, -CPU_USER_REGS_SIZE + REG_S t0, CPU_USER_REGS_T0(sp) + + /* Save registers */ + REG_S ra, CPU_USER_REGS_RA(sp) + REG_S gp, CPU_USER_REGS_GP(sp) + REG_S t1, CPU_USER_REGS_T1(sp) + REG_S t2, CPU_USER_REGS_T2(sp) + REG_S s0, CPU_USER_REGS_S0(sp) + REG_S s1, CPU_USER_REGS_S1(sp) + REG_S a0, CPU_USER_REGS_A0(sp) + REG_S a1, CPU_USER_REGS_A1(sp) + REG_S a2, CPU_USER_REGS_A2(sp) + REG_S a3, CPU_USER_REGS_A3(sp) + REG_S a4, CPU_USER_REGS_A4(sp) + REG_S a5, CPU_USER_REGS_A5(sp) + REG_S a6, CPU_USER_REGS_A6(sp) + REG_S a7, CPU_USER_REGS_A7(sp) + REG_S s2, CPU_USER_REGS_S2(sp) + REG_S s3, CPU_USER_REGS_S3(sp) + REG_S s4, CPU_USER_REGS_S4(sp) + REG_S s5, CPU_USER_REGS_S5(sp) + REG_S s6, CPU_USER_REGS_S6(sp) + REG_S s7, CPU_USER_REGS_S7(sp) + REG_S s8, CPU_USER_REGS_S8(sp) + REG_S s9, CPU_USER_REGS_S9(sp) + REG_S s10,CPU_USER_REGS_S10(sp) + REG_S s11,CPU_USER_REGS_S11(sp) + REG_S t3, CPU_USER_REGS_T3(sp) + REG_S t4, CPU_USER_REGS_T4(sp) + REG_S t5, CPU_USER_REGS_T5(sp) + REG_S t6, CPU_USER_REGS_T6(sp) + csrr t0, CSR_SEPC + REG_S t0, CPU_USER_REGS_SEPC(sp) + csrr t0, CSR_SSTATUS + REG_S t0, CPU_USER_REGS_SSTATUS(sp) + + mv a0, sp + jal do_trap + +restore_registers: + /* Restore stack_cpu_regs */ + REG_L t0, CPU_USER_REGS_SEPC(sp) + csrw CSR_SEPC, t0 + REG_L t0, CPU_USER_REGS_SSTATUS(sp) + csrw CSR_SSTATUS, t0 + + REG_L ra, CPU_USER_REGS_RA(sp) + REG_L gp, CPU_USER_REGS_GP(sp) + REG_L t0, CPU_USER_REGS_T0(sp) + REG_L t1, CPU_USER_REGS_T1(sp) + REG_L t2, CPU_USER_REGS_T2(sp) + REG_L s0, CPU_USER_REGS_S0(sp) + REG_L s1, CPU_USER_REGS_S1(sp) + REG_L a0, CPU_USER_REGS_A0(sp) + REG_L a1, CPU_USER_REGS_A1(sp) + REG_L a2, CPU_USER_REGS_A2(sp) + REG_L a3, CPU_USER_REGS_A3(sp) + REG_L a4, CPU_USER_REGS_A4(sp) + REG_L a5, CPU_USER_REGS_A5(sp) + REG_L a6, CPU_USER_REGS_A6(sp) + REG_L a7, CPU_USER_REGS_A7(sp) + REG_L s2, CPU_USER_REGS_S2(sp) + REG_L s3, CPU_USER_REGS_S3(sp) + REG_L s4, CPU_USER_REGS_S4(sp) + REG_L s5, CPU_USER_REGS_S5(sp) + REG_L s6, CPU_USER_REGS_S6(sp) + REG_L s7, CPU_USER_REGS_S7(sp) + REG_L s8, CPU_USER_REGS_S8(sp) + REG_L s9, CPU_USER_REGS_S9(sp) + REG_L s10, CPU_USER_REGS_S10(sp) + REG_L s11, CPU_USER_REGS_S11(sp) + REG_L t3, CPU_USER_REGS_T3(sp) + REG_L t4, CPU_USER_REGS_T4(sp) + REG_L t5, CPU_USER_REGS_T5(sp) + REG_L t6, CPU_USER_REGS_T6(sp) + + /* Restore sp */ + REG_L sp, CPU_USER_REGS_SP(sp) + + sret diff --git a/xen/arch/riscv/include/asm/traps.h b/xen/arch/riscv/include/asm/traps.h new file mode 100644 index 0000000000..f3fb6b25d1 --- /dev/null +++ b/xen/arch/riscv/include/asm/traps.h @@ -0,0 +1,13 @@ +#ifndef __ASM_TRAPS_H__ +#define __ASM_TRAPS_H__ + +#include <asm/processor.h> + +#ifndef __ASSEMBLY__ + +void do_trap(struct cpu_user_regs *cpu_regs); +void handle_trap(void); + +#endif /* __ASSEMBLY__ */ + +#endif /* __ASM_TRAPS_H__ */ diff --git a/xen/arch/riscv/traps.c b/xen/arch/riscv/traps.c new file mode 100644 index 0000000000..ccd3593f5a --- /dev/null +++ b/xen/arch/riscv/traps.c @@ -0,0 +1,13 @@ +/* SPDX-License-Identifier: GPL-2.0-or-later */ +/* + * Copyright (C) 2023 Vates + * + * RISC-V Trap handlers + */ +#include <asm/processor.h> +#include <asm/traps.h> + +void do_trap(struct cpu_user_regs *cpu_regs) +{ + die(); +}
The patch introduces an implementation of basic exception handlers: - to save/restore context - to handle an exception itself. The handler calls wait_for_interrupt now, nothing more. Signed-off-by: Oleksii Kurochko <oleksii.kurochko@gmail.com> --- Changes in V3: - Nothing changed --- Changes in V2: - Refactor entry.S to start using of defines introduced in asm_offsets.C - Rename {__,}handle_exception to handle_trap() and do_trap() to be more consistent with RISC-V spec. - Wrap handle_trap() to ENTRY(). --- xen/arch/riscv/Makefile | 2 + xen/arch/riscv/entry.S | 94 ++++++++++++++++++++++++++++++ xen/arch/riscv/include/asm/traps.h | 13 +++++ xen/arch/riscv/traps.c | 13 +++++ 4 files changed, 122 insertions(+) create mode 100644 xen/arch/riscv/entry.S create mode 100644 xen/arch/riscv/include/asm/traps.h create mode 100644 xen/arch/riscv/traps.c