I would like to know the purpose of nohup
these days.
I ask because I read this
Nohup is short for “No Hangups.” It’s not a command that you run by itself. Nohup is a supplemental command that tells the Linux system not to stop another command once it has started. That means it’ll keep running until it’s done, even if the user that started it logs out. The syntax for nohup is simple and looks something like this:
nohup sh your-script.sh &
Notice the “&” at the end of the command. That moves the command to the background, freeing up the terminal that you’re working in.
Nohup works with just about any command that you run in the terminal. It can be run with custom scripts as well as standard system commands and command line utilities.
With using linux distributions such as SLES 11.4, or RHEL/CentOS 7.x, I can
- remote log in to linux over the network via SSH
- run the simple program below, or any other, doing
./a.out &
- log out of linux; type exit in the putty SSH terminal
- my sample program below, or any other including bash, csh, or tcsh shell scripts, run to completion just fine without the need for
nohup
- typing exit in putty to close an SSH session, I would think that qualifies as a logout?
Is there any purpose or value with nouhup
today? Is it a kernel >= 3.x thing? For however long I can remember (kernel >= 2.6) I've never used nohup
and have always just use &
with no problems.
Can someone give me a practical scenario where nohup
would be used?
#include <stdlib.h>
#include <stdio.h>
/*
sample C code, to print numbers to a file named zz.tmp
the numbers 0 to 29 over 30 seconds
*/
int main ( int argc, char *argv[] )
{
FILE *fp;
int i;
i = 0;
fp = fopen("zz.tmp", "w" );
while ( i < 30 )
{
fprintf( fp, "%d\n", i++ );
sleep( 1 );
}
fclose( fp );
return 0;
}
mysleep.sh
#!/bin/bash
sleep 1000
On Centos 7.7, optiplex pc login with keyboard & mouse, my account is bash. I do nohup ./mysleep.sh
and then control-z. When typing jobs
I see [1]+ Stopped nohup ./mysleep.sh
A ps -ef | grep mysleep
shows that process id existing, but if I close the terminal window via X in upper right corner, that process goes away so it seems nohup
is not working?
Best Answer
Sure. Assuming your shell is bash (see below why), instead of typing
exit
or^D
, type~.
at the beginning of a line, which will cause your ssh client to disconnect:You can use your program instead of
sleep
; and instead of disconnecting via~.
, you can kill your ssh client or crash the machine it runs on. You want your process to survive this? Usenohup
;-)Breaking the connection will cause the server process which manages its other end to exit, causing the kernel (any Unix/Linux kernel) to tear down the pseudo-terminal ssh had created, and to send a
SIGHUP
signal to the session leader (the bash shell), which according to the bash manual:Many people confuse this bash feature with a) the regular job control thing implemented by the kernel, which will only send a
SIGCONT
/SIGHUP
pair to the stopped, not to the running jobs [1] and b) another bash feature (shopt -s huponexit
) which causes a login bash shell to send aSIGHUP
to its jobs even when exiting normally (eg. viaexit
).[1] a stopped job is a job (= process group) which contains at least one stopped process. A process is stopped as an effect of the default action of a signal like
SIGTSTP
,SIGSTOP
,SIGTTIN
orSIGTTOU
. Processes which are "sleeping" on a blocking system call likeread
,nanosleep
,select
, etc are not considered stopped, but running.Why
nohup
may not always helpnohup
just sets the disposition ofSIGHUP
to ignore and does some redirections, it does not guarantee that the process will not be killed by other ways.a) If the
nohup ..
job is stopped, an interactive bash will also send it aSIGTERM
signal, not just aSIGHUP
/SIGCONT
pair:[terminated = sent a
SIGTERM
signal; this is another ksh/bash feature, not present in all shells]All this can be worked around by simple tricks like double-forks and by creating a new session with
setsid(1)
, butb)
systemd
may also "clean up" a logged-out session by forcefully killing (withSIGTERM
followed bySIGKILL
) any left-over processes if itsKillUserProcesses
setting is on, which is the default in some distros.