14

Use trap to capture signals like this:

i=-1;while((++i<33));
do
    trap "echo $i >> log.txt" $i;
done

And close the terminal by force.

The content in log.txt is then (under redhat linux):

1

18

1

17

0

Where these signals from?

fireworks2
  • 315
  • 2
  • 10

2 Answers2

14

The first signal is SIGHUP; that gets sent to all processes in the process group when the terminal disconnects (hangs up - hence HUP).

The second signal is SIGCONT (thanks, SiegeX, for the numbers). This is slightly surprising; it suggests you had a job stopped in the background which had to be allowed to run again.

The third signal is another SIGHUP. This was likely sent to ensure that the continued process got its turn to exit, but was sent to the whole process group. (See the POSIX standard for information on process groups, etc.).

The fourth signals is a SIGCHLD, indicating that a child process died and the corpse is available (well, the status is available).

The final signal, 0, is the shells internal pseudo-signal indicating that it is exiting.

You can do:

trap 'echo Bye' 0

to echo 'Bye' when the shell exits under control for any reason. You chose to echo the signal number to the file instead. Since the shell exits at this point, that is the last signal message that is seen. Its parent process should get a SIGCHLD signal because the shell died.


FWIW, on MacOS X 10.6.7, I ran your test. There isn't a signal 32 on MacOS X, and some of the mappings are different, and the sequence of signals sent is also different:

$ i=-1;while((++i<33));
> do
>     trap "echo $i >> log.txt" $i;
> done
-sh: trap: 32: invalid signal specification
$ trap
trap -- 'echo 0 >> log.txt' EXIT
trap -- 'echo 1 >> log.txt' HUP
trap -- 'echo 2 >> log.txt' INT
trap -- 'echo 3 >> log.txt' QUIT
trap -- 'echo 4 >> log.txt' ILL
trap -- 'echo 5 >> log.txt' TRAP
trap -- 'echo 6 >> log.txt' ABRT
trap -- 'echo 7 >> log.txt' EMT
trap -- 'echo 8 >> log.txt' FPE
trap -- 'echo 9 >> log.txt' KILL
trap -- 'echo 10 >> log.txt' BUS
trap -- 'echo 11 >> log.txt' SEGV
trap -- 'echo 12 >> log.txt' SYS
trap -- 'echo 13 >> log.txt' PIPE
trap -- 'echo 14 >> log.txt' ALRM
trap -- 'echo 15 >> log.txt' TERM
trap -- 'echo 16 >> log.txt' URG
trap -- 'echo 17 >> log.txt' STOP
trap -- 'echo 19 >> log.txt' CONT
trap -- 'echo 20 >> log.txt' CHLD
trap -- 'echo 23 >> log.txt' IO
trap -- 'echo 24 >> log.txt' XCPU
trap -- 'echo 25 >> log.txt' XFSZ
trap -- 'echo 26 >> log.txt' VTALRM
trap -- 'echo 27 >> log.txt' PROF
trap -- 'echo 28 >> log.txt' WINCH
trap -- 'echo 29 >> log.txt' INFO
trap -- 'echo 30 >> log.txt' USR1
trap -- 'echo 31 >> log.txt' USR2
$

The signals captured in one run were:

2
1
20
0

In a second run, I got:

20
1
20
0

The SIGINT first is surprising -- I don't think I can explain that unless it simply means an incomplete write of some sort (it should have read 20 but the SIGHUP caused a problem). I'm not sure that I can explain the SIGCHLD signals either; the SIGHUP and 'exit' trap are as before.

To some extent, though, the signals are system specific - or so it seems. The SIGHUP is common and constant, though.

Jonathan Leffler
  • 730,956
  • 141
  • 904
  • 1,278
  • thanks. "it suggests you had a job stopped in the background which had to be allowed to run again." But I've run "pstree -p" to ensure that no job was stopped in the background. – fireworks2 Apr 05 '11 at 07:04
  • @fireworks2: then I don't know why the signal was sent - I wasn't sure in the first place, but it seemed like a semi-plausible sequence to explain your observations. – Jonathan Leffler Apr 05 '11 at 07:57
  • 1
    +1 for a good attempt at explaining what's going on cause I have no f'n clue. – SiegeX Apr 05 '11 at 23:56
  • 1
    @SiegeX - thanks; that makes four of us: you, me, my schizophrenic other self, and the OP. – Jonathan Leffler Apr 06 '11 at 00:01
  • 1
    @Leffler: You are right, the result really differs in different OS, and that makes it even harder to explain thoroughly. I did the test under suse-linux, and the signals are "SIGCONT - SIGHUP - EXIT". Yet one thing is for sure, SIGHUP is sent to shell when terminal is closed. – fireworks2 Apr 06 '11 at 13:58
  • Any reason why you're not listening for 18, 21 and 22? – GKFX May 27 '17 at 13:52
  • 1
    @GKFX: Probably, I hadn't noticed that signals 18, 21, 22 are absent from the output. The signals correspond (on a Mac) to `SIGTSTP`, `SIGTTIN`, `SIGTTOU`. The shell silently refuses to set a trap for them, probably because it uses the signals itself and doesn't want to let the user preempt its own handling of them. (Note that signals from 16 upwards are somewhat platform-specific — compare the signals for Mac in my answer with those for Linux in the answer below. Those up to 15 are essentially the same across all systems, mainly because they were the signals defined in 7th Edition Unix.) – Jonathan Leffler May 27 '17 at 15:11
6

If you're asking what each of the signals are, use kill -l

$ kill -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

Note that a kill -0 <PID> does nothing other than return an exit code to indicate if a signal can be sent to the PID

SiegeX
  • 135,741
  • 24
  • 144
  • 154