ibm-information-center/dist/eclipse/plugins/i5OS.ic.apis_5.4.0.1/sigactn.htm

1105 lines
33 KiB
HTML

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<meta name="Copyright" content="Copyright (c) 2006 by IBM Corporation">
<title>sigaction()--Examine and Change Signal Action</title>
<!-- All rights reserved. Licensed Materials Property of IBM -->
<!-- US Government Users Restricted Rights -->
<!-- Use, duplication or disclosure restricted by -->
<!-- GSA ADP Schedule Contract with IBM Corp. -->
<!-- Begin Header Records ========================================== -->
<!-- UNIX5 SCRIPT J converted by B2H R4.1 (346) (CMS) by V2KEA304 -->
<!-- at RCHVMW2 on 17 Feb 1999 at 11:05:09 -->
<!--End Header Records -->
<!-- Edited by Kersten Feb 02 -->
<!-- This file has undergone html cleanup May 2002 by JET -->
<link rel="stylesheet" type="text/css" href="../rzahg/ic.css">
</head>
<body>
<a name="Top_Of_Page"></a>
<!-- Java sync-link -->
<script type="text/javascript" language="Javascript" src="../rzahg/synch.js">
</script>
<h2>sigaction()--Examine and Change Signal Action</h2>
<div class="box" style="width: 60%;">
<br>
&nbsp;&nbsp;Syntax<br>
<pre>
#include &lt;signal.h&gt;
#include &lt;sys/signal.h&gt;
int sigaction( int <em>sig</em>, const struct sigaction <em>*act</em>,
struct sigaction <em>*oact</em> );
</pre>
<br>
&nbsp;&nbsp;Service Program Name: QPOSSRV1<br>
<!-- iddvc RMBR -->
<br>
&nbsp;&nbsp;Default Public Authority: *USE<br>
<!-- iddvc RMBR -->
<br>
&nbsp;&nbsp;Threadsafe: Yes<br>
<!-- iddvc RMBR -->
<br>
</div>
<p>The <strong>sigaction()</strong> function examines, changes, or both
examines and changes the action associated with a specific signal.</p>
<p>The <em>sig</em> argument must be one of the macros defined in the
&lt;<strong>sys/signal.h</strong>&gt; header file.</p>
<p>If <strong>sigaction()</strong> fails, the action for the signal <em>
sig</em> is not changed.</p>
<br>
<!-- Please NOTE: DO NOT DELETE THIS SECTION if this API has no authorities and locks. -->
<!-- Instead, use the commented out coding below to indicate NONE. -->
<h3>Authorities and Locks</h3>
<!-- Use this if there are no authorities and locks. -->
<p>None.</p>
<br>
<h3>Parameters</h3>
<dl>
<dt><strong><em>sig</em></strong></dt>
<dd>(Input) A signal from the list defined in <a href="#TBLSIGTBL1">Control
Signals Table</a> .<br>
<br>
</dd>
<dt><strong><em>*act</em></strong></dt>
<dd>(Input) A pointer to the <samp>sigaction</samp> structure that describes
the action to be taken for the signal. Can be NULL.
<p>If <em>act</em> is a NULL pointer, signal handling is unchanged. <strong>
sigaction()</strong> can be used to inquire about the current handling of
signal <em>sig</em>.</p>
<p>If <em>act</em> is not NULL, the action specified in the <samp>
sigaction</samp> structure becomes the new action associated with <em>
sig</em>.</p>
</dd>
<dt><strong><em>*oact</em></strong></dt>
<dd>(Output) A pointer to a storage location where <strong>sigaction()</strong>
can store a <samp>sigaction</samp> structure. This structure contains the
action currently associated with <em>sig</em>. Can be NULL.
<p>If <em>oact</em> is a NULL pointer, <strong>sigaction()</strong> does not
store this information.</p>
</dd>
</dl>
<p>The <strong>sigaction()</strong> function uses structures of the <samp>
sigaction</samp> type. The following is an example of a <samp>
sigaction()</samp> structure:</p>
<pre>
struct sigaction {
void (*sa_handler)(int);
sigset_t sa_mask;
int sa_flags;
void (*sa_sigaction)(int, siginfo_t *,void *);
};
</pre>
<p>The members of the <samp>sigaction</samp> structure are as follows:</p>
<table cellpadding="5" border>
<!-- cols="35 65" -->
<tr>
<th>Member name</th>
<th>Description</th>
</tr>
<tr>
<td align="left" valign="top"><em>void (*) (int) sa_handler</em></td>
<td align="left" valign="top">A pointer to the function assigned to handle the
signal. The value of this member also can be SIG_DFL (indicating the default
action) or SIG_IGN (indicating that the signal should be ignored).<br>
<br>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>sigset_t sa_mask</em></td>
<td align="left" valign="top">A signal set (set of signals) to be added to the
signal mask of the calling process before the signal-catching function <samp>
sa_handler</samp> is called. For more on signal sets, see <a href=
"sigpmsk.htm">sigprocmask()--Examine and Change Blocked Signals</a>. You cannot
use this mechanism to block the SIGKILL or SIGStop signals. If <samp>
sa_mask</samp> includes these signals, they are ignored and <strong>
sigaction()</strong> does not return an error.
<p><samp>sa_mask</samp> must be set by using one or more of the signal set
manipulation functions: <strong>sigemptyset()</strong>, <strong>
sigfillset()</strong>, <strong>sigaddset()</strong>, or <strong>
sigdelset()</strong></p>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>int sa_flags</em></td>
<td align="left" valign="top">A collection of flag bits that affect the
behavior of signals. The following flag bits can be set in <samp>
sa_flags</samp>:<br>
<br>
<table cellpadding="5">
<tr>
<td align="left" valign="top"><em>SA_NOCLDStop</em></td>
<td align="left" valign="top">If this flag is set, the system does not generate
a SIGCHLD signal when child processes stop. This is relevant only when the <em>
sig</em> argument of <strong>sigaction()</strong> is SIGCHLD.</td>
</tr>
<tr>
<td align="left" valign="top"><em>SA_NODEFER</em></td>
<td align="left" valign="top">If this flag is set and <em>sig</em>is caught,
<em>sig</em> is not added to the signal mask of the process on entry to the
signal catcher unless it is included in <strong>sa_mask</strong>. If this flag
is not set, <em>sig</em> is always added to the signal mask of the process on
entry to the signal catcher. This flag is supported for compatibility with
applications that use <strong>signal()</strong> to set the signal action.</td>
</tr>
<tr>
<td align="left" valign="top"><em>SA_RESETHAND</em></td>
<td align="left" valign="top">If this flag is set, the signal-handling action
for the signal is reset to SIG_DFL and the SA_SIGINFO flag is cleared on entry
to the signal-catching function. Otherwise, the signal-handling action is not
changed on entry to the signal-catching function. This flag is supported for
compatibility with applications that use <strong>signal()</strong> to set the
signal action.</td>
</tr>
<tr>
<td align="left" valign="top"><em>SA_SIGINFO</em></td>
<td align="left" valign="top">If this flag is not set and the signal is caught,
the signal-catching function identified by <samp>sa_handler</samp> is entered.
If this flag is set and the signal is caught, the signal-catching function
identified by <samp>sa_sigaction</samp> is entered.</td>
</tr>
</table>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>void (*) (int, siginfo_t *, void *)
sa_sigaction</em></td>
<td align="left" valign="top">A pointer to the function assigned to handle the
signal. If SA_SIGINFO is set, the signal-catching function identified by <samp>
sa_sigaction</samp> is entered with additional arguments and <samp>
sa_handler</samp> is ignored. If SA_SIGINFO is not set, <samp>
sa_sigaction</samp> is ignored. If <strong>sig_action()</strong> is called from
a program using data model LLP64, the parameters to <samp>sa_sigaction</samp>
must be declared as <samp>siginfo_t *__ptr128</samp> and <samp>void
*__ptr128</samp>.</td>
</tr>
</table>
<p>When a signal catcher installed by <strong>sigaction()</strong>, with the
SA_RESETHAND flag set off, catches a signal, the system calculates a new signal
mask by taking the union of the following:</p>
<ul>
<li>The current signal mask</li>
<li>The signals specified by <samp>sa_mask</samp></li>
<li>The signal that was just caught if the SA_NODEFER flag is set off</li>
</ul>
<p>This new mask stays in effect until the signal handler returns, or until
<strong>sigprocmask()</strong>, <strong>sigsuspend()</strong>, or <strong>
siglongjmp()</strong> is called. When the signal handler ends, the original
signal mask is restored.</p>
<p>After an action has been specified for a particular signal, it remains
installed until it is explicitly changed with another call to <strong>
sigaction()</strong>.</p>
<p>There are three types of actions that can be associated with a signal:
SIG_DFL, SIG_IGN, or a pointer to a function. Initially, all signals are set to
SIG_DFL or SIG_IGN. The actions prescribed by these values are as follows:</p>
<table cellpadding="5" border>
<!-- cols="35 65" -->
<tr>
<th>Action</th>
<th>Description</th>
</tr>
<tr>
<td align="left" valign="top"><em>SIG_DFL (signal-specific default
action)</em></td>
<td align="left" valign="top">
<ul>
<li>The default actions for the supported signals are specified in <a href=
"#TBLSIGTBL1">Control Signals Table</a><br>
<br>
</li>
<li>If the default action is to stop the process, that process is temporarily
suspended. When a process stops, a SIGCHLD signal is generated for its parent
process, unless the parent process has set the SA_NOCLDStop flag. While a
process is stopped, any additional signals sent to the process are not
delivered. The one exception is SIGKILL, which always ends the receiving
process. When the process resumes, any unblocked signals that were not
delivered are then delivered to it.<br>
<br>
</li>
<li>If the default action is to ignore the signal, setting a signal action to
SIG_DFL causes any pending signals for that signal to be discarded, whether or
not the signal is blocked.</li>
</ul>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>SIG_IGN (ignore signal)</em></td>
<td align="left" valign="top">
<ul>
<li>Delivery of the signal has no effect on the process. The behavior of a
process is undefined if it ignores a SIGFPE, SIGILL, or SIGSEGV signal that was
not generated by <strong>kill()</strong> or <strong>raise()</strong>.<br>
<br>
</li>
<li>If the default action is to ignore the signal, setting a signal action to
SIG_DFL causes any pending signals for that signal to be discarded, whether or
not the signal is blocked.<br>
<br>
</li>
<li>The signal action for the signals SIGKILL and SIGtop cannot be set to
SIG_IGN.</li>
</ul>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>Pointer to a function (catch
signal)</em></td>
<td align="left" valign="top">
<ul>
<li>On delivery of the signal, the receiving process runs the signal-catching
function. When the signal-catching function returns, the receiving process
resumes processing at the point at which it was interrupted.<br>
<br>
</li>
<li>If SA_SIGINFO is not set, the signal-catching function identified by <samp>
sa_handler</samp> is entered as follows:
<pre>
void <em>func</em>( int <em>signo</em> );
</pre>
where the following is true:<br>
<br>
<ul>
<li><em>func</em> is the specified signal-catching function.</li>
<li><em>signo</em> is the signal number of the signal being delivered.</li>
</ul>
<br>
</li>
<li>If SA_SIGINFO is set, the signal-catching function identified by <samp>
sa_sigaction</samp> is entered as follows:
<pre>
void <em>func</em>( int <em>signo</em>, siginfo_t <em>*info</em>, void <em>*context</em> );
</pre>
where the following is true:<br>
<br>
<ul>
<li><em>func</em> is the specified signal-catching function.</li>
<li><em>signo</em> is the signal number of the signal being delivered.</li>
<li><em>*info</em> points to an object of type <samp>siginfo_t</samp>
associated with the signal being delivered.</li>
<li><em>context</em> is set to the NULL pointer.</li>
</ul>
<br>
</li>
<li>The behavior of a process is undefined if it returns normally from a
signal-catching function for a SIGFPE, SIGILL, or SIGSEGV signal that was not
generated by <strong>kill()</strong> or <strong>raise()</strong>.<br>
<br>
</li>
<li>The signals SIGKILL and SIGStop cannot be caught.</li>
</ul>
</td>
</tr>
</table>
<p>The following is an example of the <samp>siginfo_t</samp> structure:</p>
<pre>
typedef struct siginfo_t {
int si_signo; /* Signal number */
int si_source : 1; /* Signal source */
int reserved1 : 15; /* Reserved (binary 0) */
short si_data_size; /* Size of additional signal
related data (if available) */
_MI_Time si_time; /* Time of signal */
struct {
char reserved2[2] /* Pad (reserved) */
char si_job[10]; /* Simple job name */
char si_user[10]; /* User name */
char si_jobno[6]; /* Job number */
char reserved3[4]; /* Pad (reserved) */
} si_QJN; /* Qualified job name */
int si_code; /* Cause of signal */
int si_errno; /* Error number */
pid_t si_pid; /* Process ID of sender */
uid_t si_uid; /* Real user ID of sender */
char si_data[1]; /* Additional signal related
data (if available) */
} siginfo_t;
</pre>
<p>The members of the <samp>siginfo_t</samp> structure are as follows:</p>
<table cellpadding="5">
<!-- cols="15 85" -->
<tr>
<td align="left" valign="top"><em>int si_signo</em></td>
<td align="left" valign="top">The system-generated signal number.<br>
<br>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>int si_source</em></td>
<td align="left" valign="top">Indicates whether the source of the signal is
being generated by the system or another process on the system. When the signal
source is another process, the members <samp>si_QJN</samp>, <samp>
si_pid</samp>, and <samp>si_uid</samp> contain valid data. When the signal
source is the system, those members are set to binary 0.<br>
<br>
</td>
</tr>
<tr>
<td align="left" valign="top" nowrap><em>short si_data_size</em></td>
<td align="left" valign="top">The length of <samp>si_errno</samp>, <samp>
si_code</samp>, <samp>si_pid</samp>, <samp>si_uid</samp>, and any additional
signal-related data. If this member is set to 0, this signal-related
information is not available.<br>
<br>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>struct si_QJN</em></td>
<td align="left" valign="top">The fully qualified i5/OS job name of the
process sending the signal.<br>
<br>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>int si_errno</em></td>
<td align="left" valign="top">If not zero, this member contains an <em>
errno</em> value associated with the signal, as defined in <strong>
&lt;errno.h&gt;</strong>.<br>
<br>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>int si_code</em></td>
<td align="left" valign="top">If not zero, this member contains a code
identifying the cause of the signal. Possible code values are defined in the
<strong>&lt;sys/signal.h&gt;</strong> header file.<br>
<br>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>pidt_t si_pid</em></td>
<td align="left" valign="top">The process ID of the process sending the
signal.<br>
<br>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>uid_t si_uid</em></td>
<td align="left" valign="top">The real user ID of the process sending the
signal.<br>
<br>
</td>
</tr>
<tr>
<td align="left" valign="top" nowrap><em>char si_data[1]</em></td>
<td align="left" valign="top">If present, the member contains any additional
signal-related data.</td>
</tr>
</table>
<br>
<br>
<h3><a name="TBLSIGTBL1">Control Signals Table</a></h3>
<p>See <a href="#DEFAULT">Default actions</a> for a description of the value
given.</p>
<table border cellpadding="5">
<!-- cols="15 15 70" -->
<tr>
<th align="left" valign="bottom">Value</th>
<th align="left" valign="bottom">Default Action</th>
<th align="left" valign="bottom">Meaning</th>
</tr>
<tr>
<td align="left" valign="top">SIGABRT</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Abnormal termination</td>
</tr>
<tr>
<td align="left" valign="top">SIGFPE</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Arithmetic exceptions that are not masked (for
example, overflow, division by zero, and incorrect operation)</td>
</tr>
<tr>
<td align="left" valign="top">SIGILL</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Detection of an incorrect function image</td>
</tr>
<tr>
<td align="left" valign="top">SIGINT</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Interactive attention</td>
</tr>
<tr>
<td align="left" valign="top">SIGSEGV</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Incorrect access to storage</td>
</tr>
<tr>
<td align="left" valign="top">SIGTERM</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Termination request sent to the program</td>
</tr>
<tr>
<td align="left" valign="top">SIGUSR1</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Intended for use by user applications</td>
</tr>
<tr>
<td align="left" valign="top">SIGUSR2</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Intended for use by user applications</td>
</tr>
<tr>
<td align="left" valign="top">SIGALRM</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">A timeout signal (sent by <strong>
alarm()</strong>)</td>
</tr>
<tr>
<td align="left" valign="top">SIGHUP</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">A controlling terminal is hung up, or the
controlling process ended</td>
</tr>
<tr>
<td align="left" valign="top">SIGKILL</td>
<td align="left" valign="top">1</td>
<td align="left" valign="top">A termination signal that cannot be caught or
ignored</td>
</tr>
<tr>
<td align="left" valign="top">SIGPIPE</td>
<td align="left" valign="top">3</td>
<td align="left" valign="top">A write to a pipe that is not being read</td>
</tr>
<tr>
<td align="left" valign="top">SIGQUIT</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">A quit signal for a terminal</td>
</tr>
<tr>
<td align="left" valign="top">SIGCHLD</td>
<td align="left" valign="top">3</td>
<td align="left" valign="top">An ended or stopped child process (SIGCLD is an
alias name for this signal)</td>
</tr>
<tr>
<td align="left" valign="top">SIGCONT</td>
<td align="left" valign="top">5</td>
<td align="left" valign="top">If stopped, continue</td>
</tr>
<tr>
<td align="left" valign="top">SIGStop</td>
<td align="left" valign="top">4</td>
<td align="left" valign="top">A stop signal that cannot be caught or
ignored</td>
</tr>
<tr>
<td align="left" valign="top">SIGTSTP</td>
<td align="left" valign="top">4</td>
<td align="left" valign="top">A stop signal for a terminal</td>
</tr>
<tr>
<td align="left" valign="top">SIGTTIN</td>
<td align="left" valign="top">4</td>
<td align="left" valign="top">A background process attempted to read from a
controlling terminal</td>
</tr>
<tr>
<td align="left" valign="top">SIGTTOU</td>
<td align="left" valign="top">4</td>
<td align="left" valign="top">A background process attempted to write to a
controlling terminal</td>
</tr>
<tr>
<td align="left" valign="top">SIGIO</td>
<td align="left" valign="top">3</td>
<td align="left" valign="top">Completion of input or output</td>
</tr>
<tr>
<td align="left" valign="top">SIGURG</td>
<td align="left" valign="top">3</td>
<td align="left" valign="top">High bandwidth data is available at a socket</td>
</tr>
<tr>
<td align="left" valign="top">SIGPOLL</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Pollable event</td>
</tr>
<tr>
<td align="left" valign="top">SIGBUS</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Specification exception</td>
</tr>
<tr>
<td align="left" valign="top">SIGPRE</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Programming exception</td>
</tr>
<tr>
<td align="left" valign="top">SIGSYS</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Bad system call</td>
</tr>
<tr>
<td align="left" valign="top">SIGTRAP</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Trace or breakpoint trap</td>
</tr>
<tr>
<td align="left" valign="top">SIGPROF</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Profiling timer expired</td>
</tr>
<tr>
<td align="left" valign="top">SIGVTALRM</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Virtual timer expired</td>
</tr>
<tr>
<td align="left" valign="top">SIGXCPU</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Processor time limit exceeded</td>
</tr>
<tr>
<td align="left" valign="top">SIGXFSZ</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">File size limit exceeded</td>
</tr>
<tr>
<td align="left" valign="top">SIGDANGER</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">System crash imminent</td>
</tr>
<tr>
<td align="left" valign="top">SIGPCANCEL</td>
<td align="left" valign="top">2</td>
<td align="left" valign="top">Thread termination signal that cannot be caught
or ignored</td>
</tr>
</table>
<h4><a name="DEFAULT">Default Actions:</a></h4>
<table cellpadding="5">
<!-- cols="5 95" -->
<tr>
<td align="left" valign="top"><em>1</em></td>
<td align="left" valign="top">End the process immediately.</td>
</tr>
<tr>
<td align="left" valign="top"><em>2</em></td>
<td align="left" valign="top">End the request.</td>
</tr>
<tr>
<td align="left" valign="top"><em>3</em></td>
<td align="left" valign="top">Ignore the signal.</td>
</tr>
<tr>
<td align="left" valign="top"><em>4</em></td>
<td align="left" valign="top">Stop the process.</td>
</tr>
<tr>
<td align="left" valign="top"><em>5</em></td>
<td align="left" valign="top">Continue the process if it is currently stopped.
Otherwise, ignore the signal.</td>
</tr>
</table>
<br>
<br>
<h3>Return Value</h3>
<table cellpadding="5">
<!-- cols="5 95" -->
<tr>
<td align="left" valign="top"><em>0</em></td>
<td align="left" valign="top"><strong>sigaction()</strong> was successful.</td>
</tr>
<tr>
<td align="left" valign="top"><em>-1</em></td>
<td align="left" valign="top"><strong>sigaction()</strong> was not successful.
The <em>errno</em> variable is set to indicate the error.</td>
</tr>
</table>
<br>
<br>
<h3>Error Conditions</h3>
<p>If <strong>sigaction()</strong> is not successful, <em>errno</em> usually
indicates one of the following errors. Under some conditions, <em>errno</em>
could indicate an error other than those listed here.</p>
<dl>
<dt><em>[EINVAL]</em></dt>
<dd>
<p>The value specified for the argument is not correct.</p>
<p>A function was passed incorrect argument values, or an operation was
attempted on an object and the operation specified is not supported for that
type of object.</p>
<p>An argument value is not valid, out of range, or NULL.</p>
</dd>
<dt><em>[ENOTSIGINIT]</em></dt>
<dd>
<p>Process not enabled for signals.</p>
<p>An attempt was made to call a signal function under one of the following
conditions:</p>
<ul>
<li>The signal function is being called for a process that is not enabled for
asynchronous signals.</li>
<li>The signal function is being called when the system signal controls have
not been initialized.</li>
</ul>
<br>
</dd>
</dl>
<br>
<h3>Usage Notes</h3>
<ol>
<li>When the <strong>sigaction</strong> function is used to change the action
associated with a specific signal, it enables a process for signals if the
process is not already enabled for signals. For details, see <a href=
"sigesig.htm">Qp0sEnableSignals()--Enable Process for Signals</a>. If the
system has not been enabled for signals, <strong>sigaction()</strong> is not
successful, and an [ENOTSIGINIT] error is returned.<br>
<br>
</li>
<li>The <strong>sigaction()</strong> function can be used to set the action for
a particular signal with the same semantics as a call to <strong>
signal()</strong>. The <samp>sigaction</samp> structure indicated by the
parameter <em>*act</em> should contain the following:<br>
<br>
<ul>
<li>A <samp>sa_handler</samp> equal to the <em>func</em> specified on <strong>
signal()</strong>.</li>
<li>A <samp>sa_mask</samp> containing the signal mask set by <strong>
sigemptyset()</strong>.</li>
<li>A <samp>sa_flag</samp> with the SA_RESETHAND flag set on.</li>
<li>A <samp>sa_flag</samp> with the SA_NODEFER flag set on.</li>
</ul>
<br>
</li>
<li>Some of the functions have been restricted to be serially reusable with
respect to asynchronous signals. That is, the library does not allow an
asynchronous signal to interrupt the processing of one of these functions until
it has completed.
<p>This restriction needs to be taken into consideration when a signal-catching
function is called asynchronously, because it causes the behavior of some of
the library functions to become unpredictable.</p>
<p>Because of this, when producing a strictly compliant POSIX application, only
the following functions should be assumed to be reentrant with respect to
asynchronous signals. Your signal-catching functions should be restricted to
using only these functions:</p>
<table cellpadding="10">
<tr>
<td align="left" valign="top"><strong>accept()</strong></td>
<td align="left" valign="top"><strong>access()</strong></td>
<td align="left" valign="top"><strong>alarm()</strong></td>
<td align="left" valign="top"><strong>chdir()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>chmod()</strong></td>
<td align="left" valign="top"><strong>chown()</strong></td>
<td align="left" valign="top"><strong>close()</strong></td>
<td align="left" valign="top"><strong>connect()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>creat()</strong></td>
<td align="left" valign="top"><strong>dup()</strong></td>
<td align="left" valign="top"><strong>dup2()</strong></td>
<td align="left" valign="top"><strong>fcntl()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>fstat()</strong></td>
<td align="left" valign="top"><strong>getegid()</strong></td>
<td align="left" valign="top"><strong>geteuid()</strong></td>
<td align="left" valign="top"><strong>getgid()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>getgroups()</strong></td>
<td align="left" valign="top"><strong>getpgrp()</strong></td>
<td align="left" valign="top"><strong>getpid()</strong></td>
<td align="left" valign="top"><strong>getppid()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>getuid()</strong></td>
<td align="left" valign="top"><strong>kill()</strong></td>
<td align="left" valign="top"><strong>link()</strong></td>
<td align="left" valign="top"><strong>lseek()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>mkdir()</strong></td>
<td align="left" valign="top"><strong>open()</strong></td>
<td align="left" valign="top"><strong>pathconf()</strong></td>
<td align="left" valign="top"><strong>pause()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>read()</strong></td>
<td align="left" valign="top"><strong>readv()</strong></td>
<td align="left" valign="top"><strong>recv()</strong></td>
<td align="left" valign="top"><strong>recvfrom()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>recvmsg()</strong></td>
<td align="left" valign="top"><strong>rename()</strong></td>
<td align="left" valign="top"><strong>rmdir()</strong></td>
<td align="left" valign="top"><strong>select()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>send()</strong></td>
<td align="left" valign="top"><strong>sendmsg()</strong></td>
<td align="left" valign="top"><strong>sendto()</strong></td>
<td align="left" valign="top"><strong>sigaction()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>sigaddset()</strong></td>
<td align="left" valign="top"><strong>sigdelset()</strong></td>
<td align="left" valign="top"><strong>sigemptyset()</strong></td>
<td align="left" valign="top"><strong>sigfillset()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>sigismember()</strong></td>
<td align="left" valign="top"><strong>sigpending()</strong></td>
<td align="left" valign="top"><strong>sigprocmask()</strong></td>
<td align="left" valign="top"><strong>sigsuspend()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>sigtimedwait()</strong></td>
<td align="left" valign="top"><strong>sigwait()</strong></td>
<td align="left" valign="top"><strong>sigwaitinfo()</strong></td>
<td align="left" valign="top"><strong>setitimer()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>sleep()</strong></td>
<td align="left" valign="top"><strong>stat()</strong></td>
<td align="left" valign="top"><strong>sysconf()</strong></td>
<td align="left" valign="top"><strong>time()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>times()</strong></td>
<td align="left" valign="top"><strong>umask()</strong></td>
<td align="left" valign="top"><strong>uname()</strong></td>
<td align="left" valign="top"><strong>unlink()</strong></td>
</tr>
<tr>
<td align="left" valign="top"><strong>utime()</strong></td>
<td align="left" valign="top"><strong>write()</strong></td>
<td align="left" valign="top"><strong>writev()</strong></td>
<td align="left" valign="top">&nbsp;</td>
</tr>
</table>
<p>In addition to the above functions, the macro versions of <strong>
getc()</strong> and <strong>putc()</strong> are not reentrant. However, the
library versions of these functions are reentrant.</p>
</li>
</ol>
<br>
<h3>Related Information</h3>
<ul>
<li>The &lt;<strong>signal.h</strong>&gt; file (see <a href="unix13.htm">Header
Files for UNIX-Type Functions</a>)<br>
<br>
</li>
<li><a href="sigkill.htm">kill()</a>--Send Signal to Process or Group of
Processes<br>
<br>
</li>
<li><a href="sigdsig.htm">Qp0sDisableSignals()</a>--Disable Process for
Signals<br>
<br>
</li>
<li><a href="sigesig.htm">Qp0sEnableSignals()</a>--Enable Process for
Signals<br>
<br>
</li>
<li><a href="sigpmsk.htm">sigprocmask()</a>--Examine and Change Blocked
Signals<br>
<br>
</li>
<li><a href="sigsusp.htm">sigsuspend()</a>--Wait for Signal</li>
</ul>
<br>
<h3>Example</h3>
<p>See <a href="../apiref/aboutapis.htm#codedisclaimer">Code disclaimer information</a>
for information pertaining to code examples.</p>
<p>The following example shows how signal catching functions can be established
using the <strong>sigaction()</strong> function:</p>
<pre>
#include &lt;signal.h&gt;
#include &lt;unistd.h&gt;
#include &lt;stdio.h&gt;
void check_mask( int sig, char *signame ) {
sigset_t sigset;
sigprocmask( SIG_SETMASK, NULL, &amp;sigset );
if( sigismember( &amp;sigset, sig ) )
printf( "the %s signal is blocked\n", signame );
else
printf( "the %s signal is unblocked\n", signame );
}
void catcher( int sig ) {
printf( "inside catcher() function\n" );
check_mask( SIGUSR1, "SIGUSR1" );
check_mask( SIGUSR2, "SIGUSR2" );
}
int main( int argc, char *argv[] ) {
struct sigaction sigact, old_sigact;
sigset_t sigset;
/*
* Set up an American National Standard C style signal handler
* by setting the signal mask to the empty signal set and
* using the do-not-defer signal, and reset the signal handler
* to the SIG_DFL signal flag options.
*/
sigemptyset( &amp;sigact.sa_mask );
sigact.sa_flags = 0;
sigact.sa_flags = sigact.sa_flags | SA_NODEFER | SA_RESETHAND;
sigact.sa_handler = catcher;
sigaction( SIGUSR1, &amp;sigact, NULL );
/*
* Send a signal to this program by using
* kill(getpid(), SIGUSR1)
* which is the equivalent of the American
* National Standard C raise(SIGUSR1)
* function call.
*/
printf( "raise SIGUSR1 signal\n" );
kill( getpid(), SIGUSR1 );
/*
* Get the current value of the signal handling action for
* SIGUSR1. The signal-catching function should have been
* reset to SIG_DFL
*/
sigaction( SIGUSR1, NULL, &amp;old_sigact );
if ( old_sigact.sa_handler != SIG_DFL )
printf( "signal handler was not reset\n" );
/*
* Reset the signal-handling action for SIGUSR1
*/
sigemptyset( &amp;sigact.sa_mask );
sigaddset( &amp;sigact.sa_mask, SIGUSR2 );
sigact.sa_flags = 0;
sigact.sa_handler = catcher;
sigaction( SIGUSR1, &amp;sigact, NULL );
printf( "raise SIGUSR1 signal\n" );
kill( getpid(), SIGUSR1 );
/*
* Get the current value of the signal-handling action for
* SIGUSR1. catcher() should still be the signal catching
* function.
*/
sigaction( SIGUSR1, NULL, &amp;old_sigact );
if( old_sigact.sa_handler != catcher )
printf( "signal handler was reset\n" );
return( 0 );
}
</pre>
<br>
<h3>Output:</h3>
<pre>
raise SIGUSR1 signal
inside catcher() function
the SIGUSR1 signal is unblocked
the SIGUSR2 signal is unblocked
raise SIGUSR1 signal
inside catcher() function
the SIGUSR1 signal is blocked
the SIGUSR2 signal is blocked
</pre>
<br>
<hr>
API introduced: V3R6
<hr>
<center>
<table cellpadding="2" cellspacing="2">
<tr align="center">
<td valign="middle" align="center"><a href="#Top_Of_Page">Top</a> | <a href=
"unix.htm">UNIX-Type APIs</a> | <a href="aplist.htm">APIs by category</a></td>
</tr>
</table>
</center>
</body>
</html>