SignalKillSigval(), SignalKillSigval_r()

QNX SDP8.0C Library ReferenceAPIDeveloper

Send a signal to a process group, process, or thread

Synopsis:

#include <sys/neutrino.h>

int SignalKillSigval( uint32_t reserved,
                      pid_t pid,
                      int tid,
                      int signo,
                      int code,
                      const union sigval *sigval);

int SignalKillSigval_r( uint32_t reserved,
                        pid_t pid,
                        int tid,
                        int signo,
                        int code,
                        const union sigval *sigval);

Arguments:

reserved
Set this argument to zero.
pid
0, or the ID of the process to send the signal to; see below.
tid
0, or the ID of the thread to send the signal to; see below.
signo
The signal that you want to send. There are a total of 64 signals available. Of these, at least 8 are POSIX realtime signals that range from SIGRTMIN to SIGRTMAX. For a complete list of signals, see POSIX and QNX OS signals in the documentation for SignalAction(). Valid user signals range from 1 to (NSIG - 1).

You can OR the SIG_APPID flag into the signo argument. This tells SignalKillSigval() to send the signal to all the processes with an application ID that matches the pid argument.

If the signal terminates a process, the cleanup of the terminated process occurs by default at the priority of the thread that sent the signal. If you OR the SIG_TERMER_NOINHERIT flag (defined in <signal.h>) into signo, the cleanup occurs at the priority of the thread that received the signal.

code
The code that you want to send with the signal; see siginfo_t.
sigval
A pointer to a union sigval that contains a value that you want to send with the signal; see siginfo_t.

Library:

libc

Use the -l c option to qcc to link against this library. This library is usually included automatically.

Description:

The SignalKillSigval() and SignalKillSigval_r() kernel calls send the signal signo with the given code and the value specified by sigval to a process group, process, or thread.

Note:
In order to send signals to a process with a different real or effective user ID, your process must have the PROCMGR_AID_SIGNAL ability enabled. For more information, see procmgr_ability().

These functions are identical except in the way they indicate errors. See the Returns section for details.

If signo is zero, no signal is sent, but the validity of pid is checked; if tid is nonzero, it's also checked. You can use this as a test for existence.

SignalKillSigval() implements the capabilities of the POSIX functions kill(), sigqueue(), and pthread_kill() in one call. Consider using these functions instead of invoking these kernel calls directly.

The pid and tid determine the target of the signal, as follows:

pid tid target
= 0 Hit the process group of the caller
< 0 Hit a process group identified by -pid
> 0 = 0 Hit a single process identified by pid
> 0, and you've ORed SIG_APPID into the signo argument Hit all processes with the application ID identified by pid
> 0 > 0 Hit a single thread in process pid identified by tid

If the target is a thread, the signal is always delivered to exactly that thread. If the thread has the signal blocked—see SignalProcmask()—the signal remains pending on the thread.

If the target is a process, the signal is delivered to a thread that has the signal unblocked; see SignalProcmask(), SignalSuspend(), and SignalWaitinfo(). If multiple threads have the signal unblocked, only one thread is given the signal. Which thread receives the signal isn't deterministic. To make it deterministic, you can:

  • Have all threads except one block all signals; that thread handles all signals.

    Or:

  • Target the signals to specific threads.

If all threads have the signal blocked, it's made pending on the process. The first thread to unblock the signal receives the pending signal. If a signal is pending on a thread, it's never retargetted to the process or another thread, regardless of changes to the signal-blocked mask.

If the target is a process group, the signal is delivered as above to each process in the group.

A multithreaded application typically has one thread responsible for catching most or all signals. Threads that don't wish to be directly involved with signals block all signals in their mask.

The signal-blocked mask is maintained on a per-thread basis. The signal-ignore mask and signal handlers are maintained at the process level and are shared by all threads.

If multiple signals are delivered before the target can run and process the signals, the system queues them in priority order if the SA_SIGINFO bit was set for signo. Lower numbered signals have greater priority. If the SA_SIGINFO bit isn't set for signo, then at most one signal is queued at any time. Additional signals with the same signo replace existing ones. This is the default behavior for POSIX signal handlers installed using the old signal() function. The newer sigaction() function lets you control queuing or not on a per-signal basis. Signals with a code of SI_TIMER are never queued.

The code and value are always saved with the signal. This allows you to deliver data with the signal whether or not SA_SIGINFO has been set on the signo. If SA_SIGINFO is set, you can use signals to deliver small amounts of data without loss. If you wish to pass significant data, you may wish to consider using MsgSendPulse() and MsgSendv(), which deliver data with much greater efficiency.

When a thread receives a signal by a signal handler or SignalWaitinfo() call, it can retrieve the signo, code and value from a siginfo_t structure, which contains at least the following members:

int si_signo
The signal number.
int si_code
The signal code.
union sigval si_value
The signal value.

The value of si_code is limited to an 8-bit signed value as follows:

Value Description
-128 <= si_code <= 0 User values
0 < si_code <= 127 System values generated by the kernel

Some of the common user values defined by POSIX are:

  • SI_USER — the kill() function generated the signal.
  • SI_QUEUE — the sigqueue() function generated the signal.
  • SI_TIMER — a timer generated the signal.
  • SI_ASYNCIO — asynchronous I/O generated the signal.
  • SI_MESGQ — POSIX (not QNX OS) message queues generated the signal.

A successful return from this function means the signal has been delivered. What the process(es) or thread does with the signal isn't considered.

If a thread delivers signals that the receiving process has marked as queued faster than the receiver can consume them, the kernel may fail the call if it runs out of signal queue entries. If the signo, code, and value don't change, the kernel performs signal compression by saving an 8-bit count with each queued signal.

Blocking states

None.

Returns:

The only difference between these functions is the way they indicate errors:

SignalKillSigval()
If an error occurs, -1 is returned and sets errno. Any other value returned indicates success.
SignalKillSigval_r()
EOK is returned on success. This function does NOT set errno. If an error occurs, any value in the Errors section may be returned.

Errors:

EAGAIN
The kernel had insufficient resources to enqueue the signal.
EINVAL
The value of signo is less than 0 or greater than (_NSIG -1).
EPERM
The calling process doesn't have the required permission; see procmgr_ability().
ESRCH
The process or process group indicated by pid or thread indicated by tid doesn't exist.

Classification:

QNX OS

Safety:
Cancellation pointNo
Signal handlerYes
ThreadYes
Page updated: