Expand description
Putting the terminal back when a signal ends proc.
watch turns the terminal’s raw mode on, switches to the alternate screen
and hides the cursor; a confirmation prompt hides the cursor and turns off
echo and line editing while it waits for a key. A normal end puts all of it
back. A signal does not run any of that: the process just dies, and the
shell is left typing nothing back and showing no cursor until stty sane.
While a Guard is alive, SIGINT, SIGTERM, SIGHUP and SIGQUIT (on Windows
Ctrl-C, Ctrl-Break and a closing console) are caught, the terminal is put
back, and proc ends by that same signal, so a shell reports 128 plus the
signal number (130 for Ctrl-C, 143 for SIGTERM, 129 for SIGHUP, 131 for
SIGQUIT) and knows a signal ended it: Ctrl-C stops a script’s loop. Windows
has no signals, so there proc exits with 130. A signal is how a person ends
a program, so it is not one of proc’s own exit codes, and nothing is printed.
The signal is not handled in the signal handler, which may not take a lock
or allocate: signal-hook only records it, and a thread of ours that waits
for it does the work. The thread is started by the first guard and then
stays, so a signal after a guard is gone also ends proc this way (nothing
is left to put back by then). While a guard is alive the calling thread
blocks these signals, so they are always taken by that thread and never
interrupt the one that is reading a key.
Ctrl+C typed into a prompt is not a signal (the terminal is in raw mode, so
the key arrives as a character and the prompt reports it as an interrupted
read): ctrl_c ends proc the same way.
Structs§
- Guard
- Keeps the terminal state in
NEEDSfor as long as it is alive
Functions§
- ctrl_c
- End proc as Ctrl+C does, status 130, after putting the terminal right. For a prompt that reports Ctrl+C as a key instead of the signal.
- protect_
prompt - From here until the guard is dropped, a signal shows the cursor and puts the line mode back to what it is now
- protect_
screen - From here until the guard is dropped, a signal puts the screen back: raw mode off, cursor shown, normal screen
- restore_
screen - Put the terminal back the way it was before
watch: raw mode off, cursor shown, normal screen. Every step is tried, whatever an earlier one did. - unblocked_
in_ child - Start
command’s child with no signal blocked. While a guard is alive this thread blocks the signals that end proc, and a child inherits the mask (the standard library keeps it), so anlsofthatwatchruns on a refresh could not be stopped by Ctrl-C, SIGTERM, SIGHUP or SIGQUIT.