From 75afe491ad68a8317d601594f368dd6895d9fd79 Mon Sep 17 00:00:00 2001 From: Ville Juven Date: Thu, 24 Feb 2022 09:12:51 +0200 Subject: [PATCH] RISC-V: Prepare for CONFIG_BUILD_KERNEL - Thread context prior to system call needs to be preserved - Allocate a kernel heap --- arch/risc-v/include/irq.h | 4 +- .../src/common/riscv_schedulesigaction.c | 4 +- arch/risc-v/src/common/riscv_swint.c | 41 ++++++++++++------- arch/risc-v/src/mpfs/Make.defs | 9 ++-- arch/risc-v/src/mpfs/mpfs_allocateheap.c | 9 ++-- arch/risc-v/src/mpfs/mpfs_irq.c | 2 +- binfmt/binfmt_execmodule.c | 2 +- sched/init/nx_start.c | 1 + 8 files changed, 44 insertions(+), 28 deletions(-) diff --git a/arch/risc-v/include/irq.h b/arch/risc-v/include/irq.h index 89e172f747a..a8a3bb4db31 100644 --- a/arch/risc-v/include/irq.h +++ b/arch/risc-v/include/irq.h @@ -471,7 +471,7 @@ struct xcpt_syscall_s { uintptr_t sysreturn; /* The return PC */ -#ifdef CONFIG_BUILD_PROTECTED +#ifndef CONFIG_BUILD_FLAT uintptr_t int_ctx; /* Interrupt context (i.e. mstatus) */ #endif }; @@ -501,7 +501,7 @@ struct xcptcontext uintptr_t saved_epc; /* Trampoline PC */ uintptr_t saved_int_ctx; /* Interrupt context with interrupts disabled. */ -#ifdef CONFIG_BUILD_PROTECTED +#ifndef CONFIG_BUILD_FLAT /* This is the saved address to use when returning from a user-space * signal handler. */ diff --git a/arch/risc-v/src/common/riscv_schedulesigaction.c b/arch/risc-v/src/common/riscv_schedulesigaction.c index 0c3e73a39c6..0b5ef29483f 100644 --- a/arch/risc-v/src/common/riscv_schedulesigaction.c +++ b/arch/risc-v/src/common/riscv_schedulesigaction.c @@ -138,7 +138,7 @@ void up_schedule_sigaction(struct tcb_s *tcb, sig_deliver_t sigdeliver) int_ctx = CURRENT_REGS[REG_INT_CTX]; int_ctx &= ~MSTATUS_MPIE; -#ifdef CONFIG_BUILD_PROTECTED +#ifndef CONFIG_BUILD_FLAT int_ctx |= MSTATUS_MPPM; #endif @@ -303,7 +303,7 @@ void up_schedule_sigaction(struct tcb_s *tcb, sig_deliver_t sigdeliver) int_ctx = CURRENT_REGS[REG_INT_CTX]; int_ctx &= ~MSTATUS_MPIE; -#ifdef CONFIG_BUILD_PROTECTED +#ifndef CONFIG_BUILD_FLAT int_ctx |= MSTATUS_MPPM; #endif diff --git a/arch/risc-v/src/common/riscv_swint.c b/arch/risc-v/src/common/riscv_swint.c index 9882d669c04..95d20e86a3a 100644 --- a/arch/risc-v/src/common/riscv_swint.c +++ b/arch/risc-v/src/common/riscv_swint.c @@ -276,8 +276,8 @@ int riscv_swint(int irq, void *context, void *arg) */ regs[REG_EPC] = rtcb->xcp.syscall[index].sysreturn; -#ifdef CONFIG_BUILD_PROTECTED - regs[REG_INT_CTX] = rtcb->xcp.syscall[index].int_ctx; +#ifndef CONFIG_BUILD_FLAT + regs[REG_INT_CTX] = rtcb->xcp.syscall[index].int_ctx; #endif /* The return value must be in A0-A1. @@ -313,19 +313,27 @@ int riscv_swint(int irq, void *context, void *arg) * A3 = argv */ -#ifdef CONFIG_BUILD_PROTECTED +#ifndef CONFIG_BUILD_FLAT case SYS_task_start: { /* Set up to return to the user-space task start-up function in * unprivileged mode. */ - regs[REG_EPC] = (uintptr_t)USERSPACE->task_startup & ~1; +#if defined (CONFIG_BUILD_PROTECTED) + /* Use the nxtask_startup trampoline function */ + regs[REG_EPC] = (uintptr_t)USERSPACE->task_startup & ~1; regs[REG_A0] = regs[REG_A1]; /* Task entry */ regs[REG_A1] = regs[REG_A2]; /* argc */ regs[REG_A2] = regs[REG_A3]; /* argv */ +#else + /* Start the user task directly */ + regs[REG_EPC] = (uintptr_t)regs[REG_A1] & ~1; + regs[REG_A0] = regs[REG_A2]; /* argc */ + regs[REG_A1] = regs[REG_A3]; /* argv */ +#endif regs[REG_INT_CTX] &= ~MSTATUS_MPPM; /* User mode */ } break; @@ -377,7 +385,7 @@ int riscv_swint(int irq, void *context, void *arg) * R4 = ucontext */ -#ifdef CONFIG_BUILD_PROTECTED +#ifndef CONFIG_BUILD_FLAT case SYS_signal_handler: { struct tcb_s *rtcb = nxsched_self(); @@ -391,17 +399,22 @@ int riscv_swint(int irq, void *context, void *arg) * unprivileged mode. */ - regs[REG_EPC] = (uintptr_t)USERSPACE->signal_handler & ~1; - regs[REG_INT_CTX] &= ~MSTATUS_MPPM; /* User mode */ +#if defined (CONFIG_BUILD_PROTECTED) + regs[REG_EPC] = (uintptr_t)USERSPACE->signal_handler & ~1; +#else + regs[REG_EPC] = + (uintptr_t)ARCH_DATA_RESERVE->ar_sigtramp & ~1; +#endif + regs[REG_INT_CTX] &= ~MSTATUS_MPPM; /* User mode */ /* Change the parameter ordering to match the expectation of struct * userpace_s signal_handler. */ - regs[REG_A0] = regs[REG_A1]; /* sighand */ - regs[REG_A1] = regs[REG_A2]; /* signal */ - regs[REG_A2] = regs[REG_A3]; /* info */ - regs[REG_A3] = regs[REG_A4]; /* ucontext */ + regs[REG_A0] = regs[REG_A1]; /* sighand */ + regs[REG_A1] = regs[REG_A2]; /* signal */ + regs[REG_A2] = regs[REG_A3]; /* info */ + regs[REG_A3] = regs[REG_A4]; /* ucontext */ } break; #endif @@ -415,7 +428,7 @@ int riscv_swint(int irq, void *context, void *arg) * R0 = SYS_signal_handler_return */ -#ifdef CONFIG_BUILD_PROTECTED +#ifndef CONFIG_BUILD_FLAT case SYS_signal_handler_return: { struct tcb_s *rtcb = nxsched_self(); @@ -455,7 +468,7 @@ int riscv_swint(int irq, void *context, void *arg) /* Setup to return to dispatch_syscall in privileged mode. */ rtcb->xcp.syscall[index].sysreturn = regs[REG_EPC]; -#ifdef CONFIG_BUILD_PROTECTED +#ifndef CONFIG_BUILD_FLAT rtcb->xcp.syscall[index].int_ctx = regs[REG_INT_CTX]; #endif @@ -463,7 +476,7 @@ int riscv_swint(int irq, void *context, void *arg) regs[REG_EPC] = (uintptr_t)dispatch_syscall & ~1; -#ifdef CONFIG_BUILD_PROTECTED +#ifndef CONFIG_BUILD_FLAT regs[REG_INT_CTX] |= MSTATUS_MPPM; /* Machine mode */ #endif diff --git a/arch/risc-v/src/mpfs/Make.defs b/arch/risc-v/src/mpfs/Make.defs index 5a6ecdfcf45..827e27466af 100755 --- a/arch/risc-v/src/mpfs/Make.defs +++ b/arch/risc-v/src/mpfs/Make.defs @@ -63,13 +63,14 @@ CHIP_CSRCS += mpfs_dma.c endif ifeq ($(CONFIG_BUILD_PROTECTED),y) +CHIP_CSRCS += mpfs_userspace.c +CMN_UASRCS += riscv_signal_handler.S +endif + +ifneq ($(CONFIG_BUILD_FLAT),y) CMN_CSRCS += riscv_task_start.c CMN_CSRCS += riscv_pthread_start.c CMN_CSRCS += riscv_signal_dispatch.c - -CMN_UASRCS += riscv_signal_handler.S - -CHIP_CSRCS += mpfs_userspace.c endif ifeq ($(CONFIG_ARCH_USE_MPU),y) diff --git a/arch/risc-v/src/mpfs/mpfs_allocateheap.c b/arch/risc-v/src/mpfs/mpfs_allocateheap.c index 40dbb85e2c2..f0e225cea2c 100755 --- a/arch/risc-v/src/mpfs/mpfs_allocateheap.c +++ b/arch/risc-v/src/mpfs/mpfs_allocateheap.c @@ -75,7 +75,7 @@ * Kernel heap Size determined by CONFIG_MM_KERNEL_HEAPSIZE * ****************************************************************************/ - +#ifndef CONFIG_BUILD_KERNEL void up_allocate_heap(void **heap_start, size_t *heap_size) { #if defined(CONFIG_BUILD_PROTECTED) && defined(CONFIG_MM_KERNEL_HEAP) @@ -100,8 +100,9 @@ void up_allocate_heap(void **heap_start, size_t *heap_size) *heap_start = (void *)g_idle_topstack; *heap_size = KRAM_END - g_idle_topstack; -#endif +#endif /* CONFIG_BUILD_PROTECTED && CONFIG_MM_KERNEL_HEAP */ } +#endif /* CONFIG_BUILD_KERNEL */ /**************************************************************************** * Name: up_allocate_kheap @@ -113,7 +114,7 @@ void up_allocate_heap(void **heap_start, size_t *heap_size) * ****************************************************************************/ -#if defined(CONFIG_BUILD_PROTECTED) && defined(CONFIG_MM_KERNEL_HEAP) +#if !defined(CONFIG_BUILD_FLAT) && defined(CONFIG_MM_KERNEL_HEAP) void up_allocate_kheap(void **heap_start, size_t *heap_size) { /* Return the kernel heap settings. */ @@ -121,7 +122,7 @@ void up_allocate_kheap(void **heap_start, size_t *heap_size) *heap_start = (void *)g_idle_topstack; *heap_size = KRAM_END - g_idle_topstack; } -#endif +#endif /* !CONFIG_BUILD_FLAT && CONFIG_MM_KERNEL_HEAP */ /**************************************************************************** * Name: up_addregion diff --git a/arch/risc-v/src/mpfs/mpfs_irq.c b/arch/risc-v/src/mpfs/mpfs_irq.c index 3fb8c176668..f7bf10a6819 100755 --- a/arch/risc-v/src/mpfs/mpfs_irq.c +++ b/arch/risc-v/src/mpfs/mpfs_irq.c @@ -107,7 +107,7 @@ void up_irqinitialize(void) irq_attach(RISCV_IRQ_ECALLM, riscv_swint, NULL); -#ifdef CONFIG_BUILD_PROTECTED +#ifndef CONFIG_BUILD_FLAT irq_attach(RISCV_IRQ_ECALLU, riscv_swint, NULL); #endif diff --git a/binfmt/binfmt_execmodule.c b/binfmt/binfmt_execmodule.c index 8af73eda3ad..61b41cbf01d 100644 --- a/binfmt/binfmt_execmodule.c +++ b/binfmt/binfmt_execmodule.c @@ -189,7 +189,7 @@ int exec_module(FAR const struct binary_s *binp, goto errout_with_addrenv; } -#if defined(CONFIG_ARCH_ADDRENV) && defined(CONFIG_BUILD_KERNEL) +#if defined(CONFIG_ARCH_ADDRENV) && defined(CONFIG_ARCH_KERNEL_STACK) /* Allocate the kernel stack */ ret = up_addrenv_kstackalloc(&tcb->cmn); diff --git a/sched/init/nx_start.c b/sched/init/nx_start.c index ba8a2399644..939c8fb187c 100644 --- a/sched/init/nx_start.c +++ b/sched/init/nx_start.c @@ -38,6 +38,7 @@ #include #include #include +#include #include #include #include