git: kernel - sigblockall()/sigunblockall() support (per thread shared page)

Matthew Dillon dillon at
Mon Nov 11 18:03:26 PST 2019

commit 64b5a8a550c3c782ab04d04d63723691ac054ffc
Author: Matthew Dillon <dillon at>
Date:   Mon Nov 11 17:06:55 2019 -0800

    kernel - sigblockall()/sigunblockall() support (per thread shared page)
    * Implement /dev/lpmap, a per-thread RW shared page between userland
      and the kernel.  Each thread in the process will receive a unique
      shared page for communication with the kernel when memory-mapping
      /dev/lpmap and can access varous variables via this map.
    * The current thread's TID is retained for both fork() and vfork().
      Previously it was only retained for vfork().  This avoids userland
      code confusion for any bits and pieces that are indexed based on the
    * Implement support for a per-thread block-all-signals feature that
      does not require any system calls (see next commit to libc).  The
      functions will be called sigblockall() and sigunblockall().
      The lpmap->blockallsigs variable prevents normal signals from being
      dispatched.  They will still be queued to the LWP as per normal.
      The behavior is not quite that of a signal mask when dealing with
      global signals.
      The low 31 bits represents a recursion counter, allowing recursive
      use of the functions.  The high bit (bit 31) is set by the kernel
      if a signal was prevented from being dispatched.  When userland decrements
      the counter to 0 (the low 31 bits), it can check and clear bit 31 and
      if found to be set userland can then make a dummy 'real' system call
      to cause pending signals to be delivered.
      Synchronous TRAPs (e.g. kernel-generated SIGFPE, SIGSEGV, etc) are not
      affected by this feature and will still be dispatched synchronously.
    * PThreads is expected to unmap the mapped page upon thread exit.
      The kernel will force-unmap the page upon thread exit if pthreads
      does not.
      XXX needs work - currently if the page has not been faulted in
      the kernel has no visbility into the mapping and will not unmap it,
      but neither will it get confused if the address is accessed.  To
      be fixed soon.  Because if we don't, programs using LWP primitives
      instead of pthreads might not realize that libc has mapped the page.
    * The TID is reset to 1 on a successful exec*()
    * On [v]fork(), if lpmap exists for the current thread, the kernel will
      copy the lpmap->blockallsigs value to the lpmap for the new thread
      in the new process.  This way sigblock*() state is retained across
      the [v]fork().
      This feature not only reduces code confusion in userland, it also
      allows [v]fork() to be implemented by the userland program in a way
      that ensures no signal races in either the parent or the new child
      process until it is ready for them.
    * The implementation leverages our vm_map_backing extents by having
      the per-thread memory mappings indexed within the lwp.  This allows
      the lwp to remove the mappings when it exits (since not doing so
      would result in a wild pmap entry and kernel memory disclosure).
    * The implementation currently delays instantiation of the mapped
      page(s) and some side structures until the first fault.
      XXX this will have to be changed.

Summary of changes:
 sys/kern/imgact_aout.c           |   7 +-
 sys/kern/imgact_elf.c            |   4 +-
 sys/kern/init_main.c             |   1 +
 sys/kern/kern_exec.c             |  27 +++++-
 sys/kern/kern_exit.c             |   6 ++
 sys/kern/kern_fork.c             |  42 +++++---
 sys/kern/kern_memio.c            | 202 ++++++++++++++++++++++++++-------------
 sys/kern/kern_proc.c             |  80 +++++++++++++++-
 sys/kern/kern_sig.c              |  15 ++-
 sys/kern/kern_slaballoc.c        |   3 +-
 sys/platform/pc64/x86_64/efirt.c |   3 +-
 sys/sys/device.h                 |   4 +-
 sys/sys/proc.h                   |   9 +-
 sys/sys/signal.h                 |   4 +
 sys/sys/signal2.h                |  53 +++++++++-
 sys/sys/signalvar.h              |   7 ++
 sys/sys/upmap.h                  |  50 ++++++++++
 sys/vm/vm_fault.c                |  12 ++-
 sys/vm/vm_kern.c                 |  18 ++--
 sys/vm/vm_map.c                  | 131 +++++++++++++++++--------
 sys/vm/vm_map.h                  |  30 +++++-
 sys/vm/vm_mmap.c                 |   5 +-
 22 files changed, 558 insertions(+), 155 deletions(-)

DragonFly BSD source repository

More information about the Commits mailing list