[GNU Manual] [POSIX requirement] [Linux man] [FreeBSD man]
Summary
nohup - run a command immune to hangups
Lines of code: 233
Principal syscall: execvp()
Support syscalls: dup2(), open()
Options: 0 (version and help are combined with usage()
)
Alternated between shell script and utility. Included in V7 UNIX (1979) and probably earlier
Added to Shellutils in July 2003 [First version]
Number of revisions: 76 [Code Evolution]
- None
Setup
In main()
, the following variables and flags are defined to assist in flow control:
exit_status_failure
- Exit status to use in case of failureignoring_input
- Flag to redirect input (set if a tty)out_fd
- The output file descriptor after redirectionredirecting_stderr
- Flag to redirect stderr (set if tty)redirecting_stdout
- Flag to redirect output (set if tty)saved_stderr_fd
- Saves standard error in case of failurestdout_is_closed
- Flag set if output is invalid
In addition to the usual localization, nohup checks for the POSIXLY_CORRECT
environment flag to set the proper failure status as required by POSIX 2008
Parsing
Parsing nohup is limited to checking that no options are specified and verifying that some command is provided as an argument. Any argument provided is assumed to be a command. Invalid commands fail during execution
Parsing may fail if the user provides command line options or doesn't provide any command to execution. Usage is displayed in either case.
Execution
Continuing process execution after a session ends is an ancient issue for timesharing systems. The solution is to simply ignore SIGHUP (by default, programs abnormaly raise(SIGHUP)
). Disassocating a process from a user involves some extra housekeeping for standard streams. POSIX further requires a distinct failure status that distinguish between nohup failures and target execution failures. The overall flow looks like this:
- Redirect tty input to dev/null as write only to force an error on read
- Redirect tty output to nohup.out
- Redirect tty error - retained in case of
execvp()
failure dup2 (out_fd, STDERR_FILENO)
- Ignore SIGHUP
signal (SIGHUP, SIG_IGN);
- Execute target command
execvp (*cmd, cmd);
Under normal circumstances, the utility ends with execvp()
. Subsequent lines of code indicate failure.
Failure cases:
- Unable to redirect input, output, or error for a tty
- Unable to execute specified command