@peccul is peccu

(love peccu '(emacs lisp cat outdoor bicycle mac linux coffee))

bashスクリプトでシグナルを受け取った時にどのシグナルだったかを知る

bashシェルスクリプトがなぜか正常終了しない時に、シグナルが飛んできていないか確認したかった。

これを参考に全てのシグナルに対してtrapさせてみた。

stackoverflow.com

trapに関してはこの辺りが参考になると思う。

qiita.com

#!/bin/bash

# https://stackoverflow.com/a/9256709/514411
trap_with_arg() {
    func="$1" ; shift
    for sig ; do
        trap "$func $sig" "$sig"
    done
}
func_trap() {
    echo Trapped: $1
}
trap_with_arg func_trap HUP INT QUIT ILL TRAP ABRT BUS FPE KILL USR1 SEGV USR2 PIPE ALRM TERM STKFLT CHLD CONT STOP TSTP TTIN TTOU URG XCPU XFSZ VTALRM PROF WINCH IO PWR SYS RTMIN RTMIN+1 RTMIN+2 RTMIN+3 RTMIN+4 RTMIN+5 RTMIN+6 RTMIN+7 RTMIN+8 RTMIN+9 RTMIN+10 RTMIN+11 RTMIN+12 RTMIN+13 RTMIN+14 RTMIN+15 RTMAX-14 RTMAX-13 RTMAX-12 RTMAX-11 RTMAX-10 RTMAX-9 RTMAX-8 RTMAX-7 RTMAX-6 RTMAX-5 RTMAX-4 RTMAX-3 RTMAX-2 RTMAX-1 RTMAX

read

これを実行して C-c を押すと Trapped: INT など出力されると思う。

シグナルの一覧やman pageの抜粋もついでに。

# trap -l
#  1) SIGHUP       2) SIGINT       3) SIGQUIT      4) SIGILL
#  5) SIGTRAP      6) SIGABRT      7) SIGBUS       8) SIGFPE
#  9) SIGKILL     10) SIGUSR1     11) SIGSEGV     12) SIGUSR2
# 13) SIGPIPE     14) SIGALRM     15) SIGTERM     16) SIGSTKFLT
# 17) SIGCHLD     18) SIGCONT     19) SIGSTOP     20) SIGTSTP
# 21) SIGTTIN     22) SIGTTOU     23) SIGURG      24) SIGXCPU
# 25) SIGXFSZ     26) SIGVTALRM   27) SIGPROF     28) SIGWINCH
# 29) SIGIO       30) SIGPWR      31) SIGSYS      34) SIGRTMIN
# 35) SIGRTMIN+1  36) SIGRTMIN+2  37) SIGRTMIN+3  38) SIGRTMIN+4
# 39) SIGRTMIN+5  40) SIGRTMIN+6  41) SIGRTMIN+7  42) SIGRTMIN+8
# 43) SIGRTMIN+9  44) SIGRTMIN+10 45) SIGRTMIN+11 46) SIGRTMIN+12
# 47) SIGRTMIN+13 48) SIGRTMIN+14 49) SIGRTMIN+15 50) SIGRTMAX-14
# 51) SIGRTMAX-13 52) SIGRTMAX-12 53) SIGRTMAX-11 54) SIGRTMAX-10
# 55) SIGRTMAX-9  56) SIGRTMAX-8  57) SIGRTMAX-7  58) SIGRTMAX-6
# 59) SIGRTMAX-5  60) SIGRTMAX-4  61) SIGRTMAX-3  62) SIGRTMAX-2
# 63) SIGRTMAX-1  64) SIGRTMAX

# kill [-s sigspec | -n signum | -sigspec] [pid | jobspec] ...
# kill -l [sigspec | exit_status]
#        Send the signal named by sigspec or signum to the processes named by pid or jobspec.  sigspec is either a case-insensitive signal name such as SIGKILL (with or without the SIG  prefix)
#        or a signal number; signum is a signal number.  If sigspec is not present, then SIGTERM is assumed.  An argument of -l lists the signal names.  If any arguments are supplied when -l is
#        given, the names of the signals corresponding to the arguments are listed, and the return status is 0.  The exit_status argument to -l is a number specifying either a signal number  or
#        the exit status of a process terminated by a signal.  kill returns true if at least one signal was successfully sent, or false if an error occurs or an invalid option is encountered.

# trap [-lp] [[arg] sigspec ...]
#        The command arg is to be read and executed when the shell receives signal(s) sigspec.  If arg is absent (and there is a single sigspec) or -, each specified  signal  is  reset  to  its
#        original  disposition  (the  value  it  had  upon entrance to the shell).  If arg is the null string the signal specified by each sigspec is ignored by the shell and by the commands it
#        invokes.  If arg is not present and -p has been supplied, then the trap commands associated with each sigspec are displayed.  If no arguments are supplied or if only -p is given,  trap
#        prints the list of commands associated with each signal.  The -l option causes the shell to print a list of signal names and their corresponding numbers.  Each sigspec is either a sig‐
#        nal name defined in <signal.h>, or a signal number.  Signal names are case insensitive and the SIG prefix is optional.

#        If a sigspec is EXIT (0) the command arg is executed on exit from the shell.  If a sigspec is DEBUG, the command arg is executed before every simple command, for command, case command,
#        select  command,  every arithmetic for command, and before the first command executes in a shell function (see SHELL GRAMMAR above).  Refer to the description of the extdebug option to
#        the shopt builtin for details of its effect on the DEBUG trap.  If a sigspec is RETURN, the command arg is executed each time a shell function or a script executed with the . or source
#        builtins finishes executing.

#        If  a sigspec is ERR, the command arg is executed whenever a simple command has a non-zero exit status, subject to the following conditions.  The ERR trap is not executed if the failed
#        command is part of the command list immediately following a while or until keyword, part of the test in an if statement, part of a command executed in a && or || list, or if  the  com‐
#        mand's return value is being inverted via !.  These are the same conditions obeyed by the errexit option.

#        Signals  ignored  upon  entry  to the shell cannot be trapped, reset or listed.  Trapped signals that are not being ignored are reset to their original values in a subshell or subshell
#        environment when one is created.  The return status is false if any sigspec is invalid; otherwise trap returns true.