diff --git a/arch/risc-v/include/syscall.h b/arch/risc-v/include/syscall.h index f5a14a1a8d0..5598b5d27d0 100644 --- a/arch/risc-v/include/syscall.h +++ b/arch/risc-v/include/syscall.h @@ -65,14 +65,14 @@ /* SYS call 1: * - * void riscv_fullcontextrestore(uintptr_t *restoreregs) noreturn_function; + * void riscv_fullcontextrestore() noreturn_function; */ #define SYS_restore_context (1) /* SYS call 2: * - * void riscv_switchcontext(uintptr_t **saveregs, uintptr_t *restoreregs); + * void riscv_switchcontext(); */ #define SYS_switch_context (2) diff --git a/arch/risc-v/src/common/riscv_exit.c b/arch/risc-v/src/common/riscv_exit.c index fb521e564cd..820ead73f5b 100644 --- a/arch/risc-v/src/common/riscv_exit.c +++ b/arch/risc-v/src/common/riscv_exit.c @@ -54,25 +54,17 @@ void up_exit(int status) { - struct tcb_s *tcb = this_task(); - /* Destroy the task at the head of the ready to run list. */ nxtask_exit(); - /* Now, perform the context switch to the new ready-to-run task at the - * head of the list. - */ - - tcb = this_task(); - /* Scheduler parameters will update inside syscall */ g_running_tasks[this_cpu()] = NULL; /* Then switch contexts */ - riscv_fullcontextrestore(tcb); + riscv_fullcontextrestore(); /* riscv_fullcontextrestore() should not return but could if the software * interrupts are disabled. diff --git a/arch/risc-v/src/common/riscv_internal.h b/arch/risc-v/src/common/riscv_internal.h index a24245c69ad..ffc565c7402 100644 --- a/arch/risc-v/src/common/riscv_internal.h +++ b/arch/risc-v/src/common/riscv_internal.h @@ -486,36 +486,37 @@ void riscv_jump_to_user(uintptr_t entry, uintreg_t a0, uintreg_t a1, * Name: riscv_fullcontextrestore * * Description: - * Restores the full context of the next task. - * - * Parameters: - * next - Pointer to the next task control block. + * Restores the full context. * * Returned Value: * None * ****************************************************************************/ -#define riscv_fullcontextrestore(next) \ - sys_call1(SYS_restore_context, (uintptr_t)next) +#define riscv_fullcontextrestore() \ + do \ + { \ + sys_call0(SYS_restore_context); \ + } \ + while (1) /**************************************************************************** * Name: riscv_switchcontext * * Description: - * Switches the context from the previous task to the next task. - * - * Parameters: - * prev - Pointer to the previous task control block. - * next - Pointer to the next task control block. + * Switches the context. * * Returned Value: * None * ****************************************************************************/ -#define riscv_switchcontext(prev, next) \ - sys_call2(SYS_switch_context, (uintptr_t)prev, (uintptr_t)next) +#define riscv_switchcontext() \ + do \ + { \ + sys_call0(SYS_switch_context); \ + } \ + while (0) #undef EXTERN #ifdef __cplusplus diff --git a/arch/risc-v/src/common/riscv_sigdeliver.c b/arch/risc-v/src/common/riscv_sigdeliver.c index 3d8e8f88415..81c73a6dd86 100644 --- a/arch/risc-v/src/common/riscv_sigdeliver.c +++ b/arch/risc-v/src/common/riscv_sigdeliver.c @@ -167,5 +167,5 @@ retry: g_running_tasks[this_cpu()] = NULL; rtcb->xcp.regs = regs; - riscv_fullcontextrestore(rtcb); + riscv_fullcontextrestore(); } diff --git a/arch/risc-v/src/common/riscv_swint.c b/arch/risc-v/src/common/riscv_swint.c index ead2e9ed429..f28857a525c 100644 --- a/arch/risc-v/src/common/riscv_swint.c +++ b/arch/risc-v/src/common/riscv_swint.c @@ -148,7 +148,8 @@ uintptr_t dispatch_syscall(unsigned int nbr, uintptr_t parm1, int riscv_swint(int irq, void *context, void *arg) { uintreg_t *regs = (uintreg_t *)context; - uintreg_t *new_regs = regs; + struct tcb_s *tcb = this_task(); + int cpu = this_cpu(); /* Software interrupt 0 is invoked with REG_A0 (REG_X10) = system call * command and REG_A1-6 = variable number of @@ -164,51 +165,18 @@ int riscv_swint(int irq, void *context, void *arg) switch (regs[REG_A0]) { - /* A0=SYS_restore_context: This a restore context command: - * - * void - * void riscv_fullcontextrestore(struct tcb_s *prev) noreturn_function; - * - * At this point, the following values are saved in context: - * - * A0 = SYS_restore_context - * A1 = next - */ - case SYS_restore_context: { - struct tcb_s *next = (struct tcb_s *)(uintptr_t)regs[REG_A1]; - - DEBUGASSERT(regs[REG_A1] != 0); - new_regs = next->xcp.regs; - riscv_restorecontext(next); + riscv_restorecontext(tcb); + restore_critical_section(tcb, cpu); } break; - /* A0=SYS_switch_context: This a switch context command: - * - * void - * riscv_switchcontext(struct tcb_s *prev, struct tcb_s *next); - * - * At this point, the following values are saved in context: - * - * A0 = SYS_switch_context - * A1 = prev - * A2 = next - * - * In this case, we save the context registers to the save register - * area referenced by the saved contents of R5. - */ - case SYS_switch_context: { - struct tcb_s *prev = (struct tcb_s *)(uintptr_t)regs[REG_A1]; - struct tcb_s *next = (struct tcb_s *)(uintptr_t)regs[REG_A2]; - - DEBUGASSERT(regs[REG_A1] != 0 && regs[REG_A2] != 0); - riscv_savecontext(prev); - new_regs = next->xcp.regs; - riscv_restorecontext(next); + riscv_savecontext(g_running_tasks[cpu]); + riscv_restorecontext(tcb); + restore_critical_section(tcb, cpu); } break; @@ -342,21 +310,17 @@ int riscv_swint(int irq, void *context, void *arg) * switch */ - if (regs != new_regs) - { - restore_critical_section(this_task(), this_cpu()); - #ifdef CONFIG_DEBUG_SYSCALL_INFO + if (cmd <= SYS_switch_context) + { svcinfo("SWInt Return: Context switch!\n"); - up_dump_register(new_regs); -#endif + up_dump_register(tcb.xcp.regs); } else { -#ifdef CONFIG_DEBUG_SYSCALL_INFO svcinfo("SWInt Return: %" PRIxPTR "\n", regs[REG_A0]); -#endif } +#endif return OK; } diff --git a/arch/risc-v/src/common/riscv_switchcontext.c b/arch/risc-v/src/common/riscv_switchcontext.c index 16252b8a2ad..5eb2f35072a 100644 --- a/arch/risc-v/src/common/riscv_switchcontext.c +++ b/arch/risc-v/src/common/riscv_switchcontext.c @@ -80,7 +80,7 @@ void up_switch_context(struct tcb_s *tcb, struct tcb_s *rtcb) { /* Then switch contexts */ - riscv_switchcontext(rtcb, tcb); + riscv_switchcontext(); /* riscv_switchcontext forces a context switch to the task at the * head of the ready-to-run list. It does not 'return' in the