Next: , Previous: , Up: linux   [Index]


7.6 Accepting signals through file descriptors

The signalfd API transforms interprocess signals into file descriptor events, this way we can code event loops using select or epoll and a uniform interface for signal and input/output events. For the full documentation see the signalfd(2) manual page. The following bindings are exported by the (vicare linux) library.

Function: signalfd fd mask flags

Interface to the C function signalfd(). Create a file descriptor that can be used to accept interprocess signals. If successful return a fixnum representing the file descriptor, else raise an exception.

fd can be either a fixnum representing the file descriptor or -1 to request a new, unspecified, file descriptor; if fd is the return value of a previous call to signalfd: this call replaces the signal set previously specified.

mask must be a Scheme vector of fixnums representing the signal numbers to be accepted. Notice that these signals should have been blocked.

flags can be the fixnum zero or an OR combination (fxior) of the constants: SFD_CLOEXEC, SFD_NONBLOCK.

Function: read-signalfd-siginfo fd

Attempt to read from the file descriptor fd a single instance of struct signalfd_siginfo: if successful return the result as an instance of struct-signalfd-siginfo; if no signal is pending, and fd is non–blocking, return #f; if an error occurs raise an exception.

Struct Type: struct-signalfd-siginfo

Structure type mirroring the C language struct signalfd_siginfo. It has the following fields:

ssi_signo       ssi_errno       ssi_code
ssi_pid         ssi_uid         ssi_fd
ssi_tid         ssi_band        ssi_overrun
ssi_trapno      ssi_status      ssi_int
ssi_ptr         ssi_utime       ssi_stime
ssi_addr
make-struct-signalfd-siginfo: signo errno code pid uid fd tid band overrun trapno status int ptr utime stime addr

Build and return a new instance of struct-signalfd-siginfo.

Function: struct-signalfd-siginfo? obj

Return #t if obj is an instance of struct-signalfd-siginfo, else return #f.

Function: struct-signalfd-siginfo-ssi_signo info
Function: struct-signalfd-siginfo-ssi_errno info
Function: struct-signalfd-siginfo-ssi_code info
Function: struct-signalfd-siginfo-ssi_pid info
Function: struct-signalfd-siginfo-ssi_uid info
Function: struct-signalfd-siginfo-ssi_fd info
Function: struct-signalfd-siginfo-ssi_tid info
Function: struct-signalfd-siginfo-ssi_band info
Function: struct-signalfd-siginfo-ssi_overrun info
Function: struct-signalfd-siginfo-ssi_trapno info
Function: struct-signalfd-siginfo-ssi_status info
Function: struct-signalfd-siginfo-ssi_int info
Function: struct-signalfd-siginfo-ssi_ptr info
Function: struct-signalfd-siginfo-ssi_utime info
Function: struct-signalfd-siginfo-ssi_stime info
Function: struct-signalfd-siginfo-ssi_addr info

Accessors for the fields of a struct-signalfd-siginfo.

In the following examples we use signal-bub-init, from (vicare posix), to block all the signals. Let’s say no signal is pending:

#!r6rs
(import (vicare)
  (prefix (vicare linux) lx.)
  (prefix (vicare posix) px.)
  (vicare platform constants))

(px.signal-bub-init)
(let* ((mask  (vector SIGUSR1 SIGUSR2)
       (flags (fxior SFD_CLOEXEC SFD_NONBLOCK)))
       (fd    (lx.signalfd -1 mask flags)))
  (lx.read-signalfd-siginfo fd))
⇒ #f

now we raise a single signal:

#!r6rs
(import (vicare)
  (prefix (vicare linux) lx.)
  (prefix (vicare posix) px.)
  (vicare platform constants))

(px.signal-bub-init)
(let* ((mask  (vector SIGUSR1 SIGUSR2)
       (flags (fxior SFD_CLOEXEC SFD_NONBLOCK)))
       (fd    (lx.signalfd -1 mask flags)))
  (px.raise SIGUSR1)
  (let ((info (lx.read-signalfd-siginfo fd))
        (done (lx.read-signalfd-siginfo fd)))

    (lx.struct-signalfd-siginfo-ssi_signo info)
    ⇒ SIGUSR1

    done))
⇒ #f

now we raise two signals:

#!r6rs
(import (vicare)
  (prefix (vicare linux) lx.)
  (prefix (vicare posix) px.)
  (vicare platform constants))

(px.signal-bub-init)
(let* ((mask  (vector SIGUSR1 SIGUSR2)
       (flags (fxior SFD_CLOEXEC SFD_NONBLOCK)))
       (fd    (lx.signalfd -1 mask flags)))
  (px.raise SIGUSR1)
  (px.raise SIGUSR2)
  (let ((info1 (lx.read-signalfd-siginfo fd))
        (info2 (lx.read-signalfd-siginfo fd))
        (done  (lx.read-signalfd-siginfo fd)))
    (lx.struct-signalfd-siginfo-ssi_signo info1)
    ⇒ SIGUSR1

    (lx.struct-signalfd-siginfo-ssi_signo info2)
    ⇒ SIGUSR2

    done))
⇒ #f

Next: , Previous: , Up: linux   [Index]