This is an automated email from the ASF dual-hosted git repository.

xiaoxiang781216 pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx.git

commit 03fd785795e1d1dfa2613b07d25185bb4c8bf1ad
Author: Marco Casaroli <[email protected]>
AuthorDate: Wed Oct 28 10:36:36 2026 +0100

    arch/risc-v: Refuse reserved user system calls without full signals.
    
    Commit fd57ce76957 ("arch/risc-v: refuse reserved syscalls from user
    mode") reads tcb->xcp.sigreturn, but struct xcptcontext has that field
    only with CONFIG_ENABLE_ALL_SIGNALS.  A protected or kernel build with
    CONFIG_ENABLE_PARTIAL_SIGNALS or CONFIG_DISABLE_ALL_SIGNALS does not
    compile:
    
      riscv_doirq.c:82:20: error: 'struct xcptcontext' has no member named
      'sigreturn'
    
    Without full signals the kernel dispatches no user signal handler, so
    no SYS_signal_handler_return from user mode is valid: refuse all
    reserved system calls from user mode in that case.
    
    Assisted-by: Claude Code:claude-opus-5-5
    Signed-off-by: Marco Casaroli <[email protected]>
---
 arch/risc-v/src/common/riscv_doirq.c | 17 ++++++++++++++---
 1 file changed, 14 insertions(+), 3 deletions(-)

diff --git a/arch/risc-v/src/common/riscv_doirq.c 
b/arch/risc-v/src/common/riscv_doirq.c
index 93677f6e1cf..19515f8333d 100644
--- a/arch/risc-v/src/common/riscv_doirq.c
+++ b/arch/risc-v/src/common/riscv_doirq.c
@@ -26,6 +26,7 @@
 
 #include <nuttx/config.h>
 
+#include <stdbool.h>
 #include <stdint.h>
 #include <assert.h>
 #include <errno.h>
@@ -43,6 +44,18 @@
  * Pre-processor Definitions
  ****************************************************************************/
 
+/* From user mode, the only reserved system call that is allowed is the
+ * return from a signal handler that the kernel dispatched.  Without full
+ * signal support the kernel dispatches no handler, so none is allowed.
+ */
+
+#ifdef CONFIG_ENABLE_ALL_SIGNALS
+#  define USER_SIGRETURN(tcb, cmd) \
+     ((cmd) == SYS_signal_handler_return && (tcb)->xcp.sigreturn != 0)
+#else
+#  define USER_SIGRETURN(tcb, cmd) false
+#endif
+
 /****************************************************************************
  * Public Data
  ****************************************************************************/
@@ -77,9 +90,7 @@ uintreg_t *riscv_doirq(int irq, uintreg_t *regs)
       regs[REG_EPC] += 4;
 
 #ifndef CONFIG_BUILD_FLAT
-      if (irq == RISCV_IRQ_ECALLU &&
-          (regs[REG_A0] != SYS_signal_handler_return ||
-           tcb->xcp.sigreturn == 0))
+      if (irq == RISCV_IRQ_ECALLU && !USER_SIGRETURN(tcb, regs[REG_A0]))
         {
           regs[REG_A0] = -ENOSYS;
           board_autoled_off(LED_INIRQ);

Reply via email to