All of lore.kernel.org
 help / color / mirror / Atom feed
From: Helge Deller <deller@kernel.org>
To: qemu-devel@nongnu.org
Cc: Pierrick Bouvier <pierrick.bouvier@oss.qualcomm.com>,
	Laurent Vivier <laurent@vivier.eu>,
	Yoshinori Sato <yoshinori.sato@nifty.com>,
	Max Filippov <jcmvbkbc@gmail.com>, Helge Deller <deller@gmx.de>,
	Matt Turner <mattst88@gmail.com>,
	Mark Cave-Ayland <mark.cave-ayland@ilande.co.uk>
Subject: [PATCH 06/10] linux-user/sparc: call block_signals() before set_sigmask() in setcontext
Date: Sun,  7 Jun 2026 16:03:52 +0200	[thread overview]
Message-ID: <20260607140356.10702-7-deller@kernel.org> (raw)
In-Reply-To: <20260607140356.10702-1-deller@kernel.org>

From: Matt Turner <mattst88@gmail.com>

sparc64_set_context() emulates the kernel's `ta 0x6f` trap by calling
set_sigmask() to install the mask supplied via the user's ucontext_t.
The contract of set_sigmask() (see its comment in linux-user/signal.c)
is that the caller must have first called block_signals(), which sets
TaskState::signal_pending.

Without block_signals(), if a guest signal is pending-and-blocked at
the time setcontext is invoked and the new mask unblocks it,
signal_pending stays 0 and the post-trap process_pending_signals()
call in linux-user/sparc/cpu_loop.c never enters its while loop, so
the now-deliverable signal is left undelivered indefinitely.

This affects programs that use getcontext/setcontext to swap signal
masks, including libunwind's unw_resume() out of a signal handler:
without this fix, the test program below loops forever printing
"calling setcontext" instead of delivering the pending SIGUSR2.

  #define _GNU_SOURCE
  #include <ucontext.h>
  #include <signal.h>
  #include <stdio.h>
  #include <unistd.h>
  static int got;
  static void h(int s) { got = 1; }
  int main(void) {
      signal(SIGUSR2, h);
      sigset_t m; sigemptyset(&m); sigaddset(&m, SIGUSR2);
      sigprocmask(SIG_BLOCK, &m, NULL);
      kill(getpid(), SIGUSR2);
      ucontext_t uc;
      getcontext(&uc);
      if (got) return 0;
      uc.uc_sigmask.__val[0] = 0;
      setcontext(&uc);
      return 1;
  }

The 32-bit sparc do_sigreturn / do_rt_sigreturn paths already get
block_signals() from the rt_sigreturn syscall wrapper in
linux-user/syscall.c, so only sparc64_set_context (invoked directly
from cpu_loop) needs the addition.

Signed-off-by: Matt Turner <mattst88@gmail.com>
Cc: Mark Cave-Ayland <mark.cave-ayland@ilande.co.uk>
Signed-off-by: Helge Deller <deller@gmx.de>
---
 linux-user/sparc/signal.c | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/linux-user/sparc/signal.c b/linux-user/sparc/signal.c
index fda5508c48..ba692c3123 100644
--- a/linux-user/sparc/signal.c
+++ b/linux-user/sparc/signal.c
@@ -619,6 +619,15 @@ void sparc64_set_context(CPUSPARCState *env)
             }
         }
         target_to_host_sigset_internal(&set, &target_set);
+        /*
+         * set_sigmask() requires the caller to have first called
+         * block_signals() so that process_pending_signals() is guaranteed
+         * to run after the mask change.  Without this, a guest signal that
+         * is pending-and-blocked at setcontext time is left undelivered
+         * even after its mask bit is cleared, because signal_pending stays
+         * 0 and the post-trap process_pending_signals() loop never enters.
+         */
+        block_signals();
         set_sigmask(&set);
     }
     env->pc = pc;
-- 
2.54.0



  parent reply	other threads:[~2026-06-07 14:05 UTC|newest]

Thread overview: 14+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-06-07 14:03 [PATCH 00/10] linux-user patches for alpha, sparc, sh4 and xtensa Helge Deller
2026-06-07 14:03 ` [PATCH 01/10] linux-user: implement fsmount(2) series of syscalls Helge Deller
2026-06-07 14:03 ` [PATCH 02/10] linux-user/strace: add fsmount " Helge Deller
2026-06-07 14:03 ` [PATCH 03/10] linux-user/alpha: add coredump support Helge Deller
2026-06-07 15:30   ` Richard Henderson
2026-06-07 14:03 ` [PATCH 04/10] linux-user/sparc: " Helge Deller
2026-06-07 14:03 ` [PATCH 05/10] linux-user/sparc: restore L/I registers from RSA in sparc64_set_context Helge Deller
2026-06-07 14:03 ` Helge Deller [this message]
2026-06-07 14:03 ` [PATCH 07/10] linux-user/sparc: flush register windows before core dump Helge Deller
2026-06-07 14:03 ` [PATCH 08/10] target/sh4: decode_gusa: recognize add#imm with prior mov Rm, Rn Helge Deller
2026-06-07 14:03 ` [PATCH 09/10] linux-user/xtensa: restore FP rounding mode on sigreturn Helge Deller
2026-06-07 20:06   ` Max Filippov
2026-06-07 14:03 ` [PATCH 10/10] target/xtensa: add cpu_set_fcr/fsr helpers to sync fp_status Helge Deller
2026-06-07 20:26   ` Max Filippov

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20260607140356.10702-7-deller@kernel.org \
    --to=deller@kernel.org \
    --cc=deller@gmx.de \
    --cc=jcmvbkbc@gmail.com \
    --cc=laurent@vivier.eu \
    --cc=mark.cave-ayland@ilande.co.uk \
    --cc=mattst88@gmail.com \
    --cc=pierrick.bouvier@oss.qualcomm.com \
    --cc=qemu-devel@nongnu.org \
    --cc=yoshinori.sato@nifty.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.