SIGACTION
Section: Linux Programmer's Manual (2)
Updated: 2009-07-25
Index
JM Home Page
roff page
名前
sigaction - シグナルの動作の確認と変更
書式
#include <signal.h>
int sigaction(int signum, const struct sigaction *act,
struct sigaction *oldact);
glibc 向けの機能検査マクロの要件
(feature_test_macros(7)
参照):
sigaction():
_POSIX_C_SOURCE >= 1 || _XOPEN_SOURCE || _POSIX_SOURCE
説明
sigaction()
システムコールは、特定のシグナルを受信した際の
プロセスの動作を変更するのに使用される
(シグナルの概要については
signal(7)
を参照)。
signum
には、
SIGKILL
と
SIGSTOP
以外の有効なシグナルをどれでも指定できる。
act
が NULL 以外であれば、シグナル
signum
の新しい動作 (action) として
act
が設定される。
oldact
が NULL でなければ、今までの動作が
oldact
に格納される。
sigaction
構造体は以下のような感じに定義される。
struct sigaction {
void (*sa_handler)(int);
void (*sa_sigaction)(int, siginfo_t *, void *);
sigset_t sa_mask;
int sa_flags;
void (*sa_restorer)(void);
};
アーキテクチャによっては共用体 (union) が用いられており、その場合には
sa_handler
と
sa_sigaction
の両方を同時に割り当てることはできない。
sa_restorer
要素は廃止予定であり使用すべきではない。
POSIX には
sa_restorer
要素に関する規定はない。
sa_handler
は
signum
に対応する動作を指定するもので、
デフォルトの動作を行う
SIG_DFL、
そのシグナルを無視する
SIG_IGN、
シグナルハンドラ関数へのポインタが設定できる。
シグナルハンドラ関数の引き数は一つであり、シグナル番号が引き数として
渡される。
sa_flags
に
SA_SIGINFO
が指定された場合、
(sa_handler
ではなく)
sa_sigaction
により
signum
に対応するシグナルハンドル関数が指定される。
指定される関数は、最初の引き数としてシグナル番号を、
二番目の引き数として
siginfo_t
へのポインタを、三番目の引き数として (void * にキャストした)
ucontext_t
へのポインタを受けとる。
sa_mask
は、シグナル・ハンドラ実行中に禁止 (block) すべきシグナルのマスクを指定する
(ハンドラ実行中のシグナルの禁止は、シグナル・ハンドラが起動されたスレッド
のシグナルのマスクに追加することで行われる)。
さらに、
SA_NODEFER
フラグが指定されていない場合は、ハンドラを起動するきっかけとなる
シグナルにも
sa_mask
が適用される。
sa_flags
はシグナル・ハンドラの動作を変更するためのフラグの集合を指定する。
sa_flags
には、以下に示すフラグの (0 個以上の) 論理和をとったものを指定する。
-
- SA_NOCLDSTOP
-
signum
が
SIGCHLD
の場合、
子プロセスが停止したり
(子プロセスが
SIGSTOP, SIGTSTP, SIGTTIN, SIGTTOU
を受けたとき) 再開したり (子プロセスが
SIGCONT
を受けたとき) したときに
SIGCHLD
の通知を受けない。
このフラグは、
SIGCHLD
に対してハンドラを設定する際にのみ意味を持つ。
- SA_NOCLDWAIT (Linux 2.6 以降)
-
(Linux 2.6 以降)
signum
が
SIGCHLD
の場合、子プロセスが終了したときに
子プロセスをゾンビプロセスに変化させない
(waitpid(2)
も参照)。
このフラグは、
SIGCHLD
に対してハンドラを設定する際、もしくはそのシグナルの処理方法を
SIG_DFL
に設定する際にのみ意味を持つ。
SIGCHLD
に対してハンドラを設定する際に
SA_NOCLDWAIT
フラグをセットした場合、
子プロセスが終了した際に
SIGCHLD
シグナルが生成されるかどうかは、
POSIX.1 では規定されていない。
Linux では、この状況で
SIGCHLD
シグナルは生成される。
いくつかの他の実装では生成されない。
- SA_NODEFER
-
それ自身のシグナル・ハンドラーの内部にいる時でも
そのシグナルをマスクしないようにする。
このフラグはシグナルハンドラを設定する際にのみ意味を持つ。
SA_NOMASK
はこのフラグと同じ意味だが、廃止されており、非標準である。
- SA_ONSTACK
-
sigaltstack(2)
で提供される別のシグナル・スタックでシグナルハンドラを呼び出す。
別のシグナル・スタックが利用可能でなければ、デフォルトのスタックが
使用される。
このフラグはシグナルハンドラを設定する際にのみ意味を持つ。
- SA_RESETHAND
-
シグナルハンドラが呼ばれる度に、シグナルの動作をデフォルトに戻す。
このフラグはシグナルハンドラを設定する際にのみ意味を持つ。
SA_ONESHOT
はこのフラグと同じ意味だが、廃止されており、非標準である。
- SA_RESTART
-
いくつかのシステムコールをシグナルの通知の前後で再開できるようにして、
BSD シグナル方式 (semantics) と互換性のある動作を提供する。
このフラグはシグナルハンドラを設定する際にのみ意味を持つ。
signal(7)
に書かれているシステムコールの再開に関する議論を参照のこと。
- SA_SIGINFO (Linux 2.2 以降)
-
シグナルハンドラは一つではなく、三つの引き数を持つ。この場合は
sa_handler
のかわりに
sa_sigaction
を設定しなければならない
このフラグはシグナルハンドラを設定する際にのみ意味を持つ。
sa_sigaction
のパラメータ
siginfo_t
は以下の要素を持つ構造体である:
siginfo_t {
int si_signo; /* Signal number */
int si_errno; /* An errno value */
int si_code; /* Signal code */
int si_trapno; /* Trap number that caused
hardware-generated signal
(unused on most architectures) */
pid_t si_pid; /* Sending process ID */
uid_t si_uid; /* Real user ID of sending process */
int si_status; /* Exit value or signal */
clock_t si_utime; /* User time consumed */
clock_t si_stime; /* System time consumed */
sigval_t si_value; /* Signal value */
int si_int; /* POSIX.1b signal */
void *si_ptr; /* POSIX.1b signal */
int si_overrun; /* Timer overrun count; POSIX.1b timers */
int si_timerid; /* Timer ID; POSIX.1b timers */
void *si_addr; /* Memory location which caused fault */
int si_band; /* Band event */
int si_fd; /* File descriptor */
}
si_signo, si_errno, si_code
は全てのシグナルに対して定義されている
(si_errno
は Linux では一般的には使用されない)。
構造体の残りの部分は、共用体 (union) になっているかもしれない。
その場合は該当するシグナルにおいて意味のあるフィールドのみを読み込む
ことができる。
- *
-
POSIX.1b シグナルと
SIGCHLD
は
si_pid と si_uid
を設定する。
- *
-
POSIX.1b タイマ (Linux 2.6 以降) は
si_overrun
と
si_timerid
を設定する。
si_timerid
フィールドはカーネルがタイマを特定するのに使用する内部 ID であり、
timer_create(2)
が返すタイマ ID と同じではない。
- *
-
SIGCHLD
は
si_status, si_utime, si_stime
を設定する。
(getrusage(2)
や
time(2)
と異なり) フィールド
si_utime
と
si_stime
には wait 待ちの子プロセスにより使用された時間は含まれない。
2.6 より前と 2.6.27 以降のカーネルでは、
これらのフィールドに格納される CPU 時間の単位は
sysconf(_SC_CLK_TCK)
である。
2.6.27 より前の 2.6 系のカーネルでは、バグがあり、
これらのフィールドの CPU 時間の単位が
(カーネルのコンフィグで指定される) システムの jiffy であった
(time(7)
参照)。
- *
-
si_int と si_ptr
は POSIX.1b シグナルの送信者によって指定される。
詳細は
sigqueue(2)
を参照のこと。
- *
-
SIGILL,
SIGFPE,
SIGSEGV,
SIGBUS
は
si_addr
にエラーが発生したアドレスを設定する。
SIGPOLL は
si_band と si_fd
を設定する。
si_code
は、そのシグナルが送信された理由を示す値である (ビットマスクではない)。
以下のリストに、どのシグナルの場合でも
si_code
に入りうる値を、シグナルが生成された理由とともに記載する。
-
- SI_USER
-
kill(2)
または
raise(3)
- SI_KERNEL
-
カーネルにより送信された
- SI_QUEUE
-
sigqueue(2)
- SI_TIMER
-
POSIX タイマが満了した
- SI_MESGQ
-
POSIX メッセージキューの状態が変化した (Linux 2.6.6 以降)。
mq_notify(3)参照。
- SI_ASYNCIO
-
非同期 IO (AIO) が完了した
- SI_SIGIO
-
キューイングされた SIGIO
- SI_TKILL
-
tkill(2)
または
tgkill(2)
(Linux 2.4.19 以降)
SIGILL
シグナルの場合、
si_code
には以下の値を指定できる:
-
- ILL_ILLOPC
-
不正な命令コード (opcode)
- ILL_ILLOPN
-
不正なオペランド
- ILL_ILLADR
-
不正なアドレッシングモード
- ILL_ILLTRP
-
不正なトラップ
- ILL_PRVOPC
-
特権が必要な命令コード (opcode)
- ILL_PRVREG
-
特権が必要なレジスタ
- ILL_COPROC
-
コプロセッサのエラー
- ILL_BADSTK
-
内部スタックエラー
SIGFPE
シグナルの場合、
si_code
には以下の値を指定できる:
-
- FPE_INTDIV
-
整数の 0 による除算
- FPE_INTOVF
-
整数のオーバーフロー
- FPE_FLTDIV
-
浮動小数点の 0 による除算
- FPE_FLTOVF
-
浮動小数点のオーバーフロー
- FPE_FLTUND
-
浮動小数点のアンダーフロー
- FPE_FLTRES
-
浮動小数点の不正確な演算結果 (inexact result)
- FPE_FLTINV
-
浮動小数点の不正な操作
- FPE_FLTSUB
-
範囲外の添字 (subscript)
SIGSEGV
シグナルの場合、
si_code
には以下の値を指定できる:
-
- SEGV_MAPERR
-
オブジェクトにマッピングされていないアドレス
- SEGV_ACCERR
-
マッピングされたオブジェクトに対するアクセス許可がない
SIGBUS
シグナルの場合、
si_code
には以下の値を指定できる:
-
- BUS_ADRALN
-
不正なアドレス・アライメント (alignment)
- BUS_ADRERR
-
存在しない物理アドレス
- BUS_OBJERR
-
オブジェクト固有のハードウェアエラー
SIGTRAP
シグナルの場合、
si_code
には以下の値を指定できる:
-
- TRAP_BRKPT
-
プロセスのブレークポイント
- TRAP_TRACE
-
プロセスのトレース・トラップ
SIGCHLD
シグナルの場合、
si_code
には以下の値を指定できる:
-
- CLD_EXITED
-
子プロセスが終了した (exited)
- CLD_KILLED
-
子プロセスが kill された
- CLD_DUMPED
-
子プロセスが異常終了した
- CLD_TRAPPED
-
トレース対象の子プロセスがトラップを上げた
- CLD_STOPPED
-
子プロセスが停止 (stop) した
- CLD_CONTINUED
-
停止していた子プロセスが再開した (Linux 2.6.9 以降)
SIGPOLL
シグナルの場合、
si_code
には以下の値を指定できる:
-
- POLL_IN
-
入力データが利用可能
- POLL_OUT
-
出力バッファが利用可能
- POLL_MSG
-
入力メッセージが利用可能
- POLL_ERR
-
I/O エラー
- POLL_PRI
-
高優先の入力が利用可能
- POLL_HUP
-
デバイスが接続されていない
返り値
sigaction()
は成功すれば 0 を返し、エラーならば -1 を返す。
エラー
- EFAULT
-
act か oldact
が指しているメモリが正しいプロセスのアドレス空間にない。
- EINVAL
-
無効なシグナルが指定された。補足 (catch) したり無視したりできない
シグナルである
SIGKILL や SIGSTOP
に対する動作を変更しようとした場合にも発生する。
準拠
POSIX.1-2001, SVr4.
注意
fork(2)
経由で作成された子プロセスは、親プロセスのシグナルの処理方法の
コピーを継承する。
execve(2)
の前後で、ハンドラが設定されているシグナルの処理方法はデフォルトにリセットされ、
無視が設定されているシグナルの処理方法は変更されずそのままとなる。
POSIX では、
kill(2)
や
raise(3)
関数で生成できないシグナル
SIGFPE,
SIGILL,
SIGSEGV
を無視 (ignore) した場合、その後の動作は未定義である。
ゼロによる整数割り算の結果は未定義となる。
アーキテクチャーによっては、このとき
SIGFPE
シグナルが生成される。
(同様に負の最大整数を -1 で割ると
SIGFPE
が生成されるかもしれない)
このシグナルを無視すると無限ループに陥るかもしれない。
POSIX.1-1990 では
SIGCHLD
に
SIG_IGN
を設定することを認めていない。
POSIX.1-2001 では認められており、
SIGCHLD
を無視することでゾンビプロセスの生成を防止することができる
(wait(2)
を参照)。
さらに、BSD と SystemV では
SIGCHLD
を無視した際の動作が異なっている。
そのため、完全に移植性がある方法で、終了した子プロセスがゾンビにならないこと
を保証するには、
SIGCHLD
シグナルを補足し、
wait(2)
などを実行するしかない。
POSIX.1-1990 の仕様では
SA_NOCLDSTOP
のみが定義されている。
POSIX.1-2001 では
SA_NOCLDWAIT,
SA_RESETHAND,
SA_NODEFER,
SA_SIGINFO
が追加された。
Unix の古い実装で動かすアプリケーションで、
他の
sa_flags
フラグを使用すると移植性が下がる。
SA_RESETHAND
フラグは SVr4 の同じ名前のフラグと互換性がある。
SA_NODEFER
フラグは 1.3.9 以降のカーネルでは同じ名前の SVr4 のフラグと互換性がある。
ぞれ以前の Linux カーネルの実装では、このフラグを設定しているシグナル
だけでなく、どのシグナルでも受けることを許していた (実際には
sa_mask
の設定により無効にできる)。
sigaction()
の二番目の引き数に NULL を指定して呼び出すと、現在のシグナルハンドラを確認する
ことができる。また、二番目と三番目の引き数を NULL にて呼び出すことで、
指定されたシグナルが現在のマシンで使えるかどうかチェックできる。
SIGKILL
や
SIGSTOP
を
(sa_mask
に指定して) 禁止することはできない。
禁止しようとしても黙って無視される。
シグナル集合の操作に関する詳細は
sigsetops(3)
を参照すること。
シグナルハンドラ内から安全に呼び出すことができる、
async-signal-safe functions (非同期シングルで安全な関数) の
リストについては
signal(7)
を参照。
非公式
SA_SIGINFO
が導入される前は、
struct sigcontext
型の二番目の引き数と一緒に
sa_handler
を使用することで、
いくつかの追加の情報を入手することができた。
詳細についてはカーネルソースの関連部分を見てほしい。
現在はこの使用法は廃止されている。
バグ
2.6.13 以前のカーネルでは、
sa_flags
に
SA_NODEFER
を指定した場合、
ハンドラが実行中に配送されたシグナル自身がマスクされなくなるだけでなく、
sa_mask
に指定されたシグナルもマスクされなくなる。
このバグは、カーネル 2.6.14 で修正された。
例
mprotect(2)
参照。
関連項目
kill(1),
kill(2),
killpg(2),
pause(2),
sigaltstack(2),
signal(2),
signalfd(2),
sigpending(2),
sigprocmask(2),
sigqueue(2),
sigsuspend(2),
wait(2),
raise(3),
siginterrupt(3),
sigsetops(3),
sigvec(3),
core(5),
signal(7)
Index
- 名前
-
- 書式
-
- 説明
-
- 返り値
-
- エラー
-
- 準拠
-
- 注意
-
- 非公式
-
- バグ
-
- 例
-
- 関連項目
-
This document was created by
man2html,
using the manual pages.
Time: 03:26:55 GMT, April 25, 2010