CrackOps
Interview PrepTracksLinuxAWS LabSoonInterview RoomSoon
Sign inStart free
CrackOps

Interview prep for the people who keep production up.

[email protected]
ProductInterview PrepTracksDashboardInterview Room
RolesDevOpsSREPlatformCloud
CompanyAboutContactPrivacyTerms
© CrackOps
Linux / Process Management / nohup

nohup

Keep a command running after you log out

Beginneressentialsignalsshell

nohup runs a command immune to SIGHUP, the hangup signal sent when your terminal or SSH session goes away, and redirects its output to nohup.out if it was going to the terminal. Combined with &, it's the quickest way to start a long job that survives logout.

Syntaxnohup COMMAND [ARG]... [> FILE 2>&1] &

Watch it run

A data import takes two hours and you don't want to keep your laptop connected the whole time.

devops@devops-lab: ~/app — zsh — 96×28
➜ ~/app
Step 1 of 4
nohup ./import.sh --full &

bash prints the job number and PID. nohup reports that stdin is now cut off and that stdout, which was the terminal, now goes to nohup.out in the current directory.

Anatomy of a command

$
commandnohup

Sets SIGHUP to ignored, fixes up stdin/stdout/stderr if they are a terminal, then execs the command.

How it works

When a terminal goes away (you close the window, SSH drops, you log out with jobs still attached), the kernel sends SIGHUP to the session leader, your shell, and bash passes SIGHUP on to its jobs. The default action of SIGHUP is to terminate. nohup calls signal(SIGHUP, SIG_IGN) and then execs your command; an ignored signal stays ignored across exec, so the hangup has no effect. It also tidies the file descriptors: if stdin is a terminal it is replaced with an unreadable descriptor, if stdout is a terminal output goes to ./nohup.out (or $HOME/nohup.out if the current directory isn't writable), and if stderr is a terminal it follows stdout. After you log out, the process is orphaned and reparented to PID 1. nohup doesn't put the command in the background (that's &), and a program can undo it by installing its own SIGHUP handler.

When the session hangs up, SIGHUP travels from the terminal to bash and on to its jobs; nohup makes a job ignore it.

SSHptySIGHUPSIGHUPreparentkeeps writingYour laptopssh clientsshdpty /dev/pts/0bashsession leader./import.sh &SIGHUP defaultnohup importSIGHUP ignoredstdout -> filesystemdPID 1nohup.outstdout + stderr
1/7
Two jobs in one session

You SSH in. sshd gives bash a pseudo-terminal; bash is the session leader. You start one job with plain & and one with nohup ... &.

← → to step

Options you'll actually use

nohup CMD &Ignore SIGHUP and run in the background
> file 2>&1Choose the output file instead of nohup.out
nohup.outCreated in the current directory (or $HOME) when stdout is a terminal
exit 127 / 126Command not found / found but not executable
disown -h %1Alternative for an already running job: bash won't send it SIGHUP
setsid CMDAlternative: run in a new session with no controlling terminal

Common mistakes

nohup ./long-job.sh without &

nohup doesn't background anything; your prompt is blocked, and Ctrl-C (SIGINT, not SIGHUP) still kills the job.

nohup ./long-job.sh > job.log 2>&1 &
Letting several jobs append to the same nohup.out

Output from unrelated jobs interleaves in one file that grows forever in whatever directory you were in.

Give each job its own log: > import.log 2>&1
Using nohup to run a production service

Nothing restarts it when it crashes or the box reboots, there's no log rotation, and it's invisible to systemctl.

A systemd unit (Restart=on-failure), or systemd-run for one-offs
Relying on nohup on hosts with systemd-logind KillUserProcesses=yes

logind kills every process in the user's session scope on logout, ignored SIGHUP or not.

systemd-run --user --unit=import ./import.sh, plus loginctl enable-linger

Interview questions

Practice

Try these on a Linux machine of your own. Each task has a hint and a solution.

  1. 1

    Start `sleep 1000` with nohup in the background and check that its SIGHUP is ignored.

  2. 2

    Run `nohup ls -l /etc` in your home directory, then find where the output went.

  3. 3

    Start `sleep 600` with nohup in the background, logging stdout and stderr to ~/job.log.

  4. 4

    Send SIGHUP to the nohup'd sleep and confirm it's still running. Then stop it properly.

Related commands

bgResume a stopped job in the backgroundjobsList the shell's background and stopped jobskillSend a signal to a processsystemctlStart, stop, enable and inspect systemd services
PreviousreniceNextdf
Linux / Process Management / nohup

nohup

Keep a command running after you log out

Beginneressentialsignalsshell

nohup runs a command immune to SIGHUP, the hangup signal sent when your terminal or SSH session goes away, and redirects its output to nohup.out if it was going to the terminal. Combined with &, it's the quickest way to start a long job that survives logout.

Syntaxnohup COMMAND [ARG]... [> FILE 2>&1] &

Watch it run

A data import takes two hours and you don't want to keep your laptop connected the whole time.

devops@devops-lab: ~/app — zsh — 96×28
➜ ~/app
Step 1 of 4
nohup ./import.sh --full &

bash prints the job number and PID. nohup reports that stdin is now cut off and that stdout, which was the terminal, now goes to nohup.out in the current directory.

Anatomy of a command

$
commandnohup

Sets SIGHUP to ignored, fixes up stdin/stdout/stderr if they are a terminal, then execs the command.

How it works

When a terminal goes away (you close the window, SSH drops, you log out with jobs still attached), the kernel sends SIGHUP to the session leader, your shell, and bash passes SIGHUP on to its jobs. The default action of SIGHUP is to terminate. nohup calls signal(SIGHUP, SIG_IGN) and then execs your command; an ignored signal stays ignored across exec, so the hangup has no effect. It also tidies the file descriptors: if stdin is a terminal it is replaced with an unreadable descriptor, if stdout is a terminal output goes to ./nohup.out (or $HOME/nohup.out if the current directory isn't writable), and if stderr is a terminal it follows stdout. After you log out, the process is orphaned and reparented to PID 1. nohup doesn't put the command in the background (that's &), and a program can undo it by installing its own SIGHUP handler.

When the session hangs up, SIGHUP travels from the terminal to bash and on to its jobs; nohup makes a job ignore it.

SSHptySIGHUPSIGHUPreparentkeeps writingYour laptopssh clientsshdpty /dev/pts/0bashsession leader./import.sh &SIGHUP defaultnohup importSIGHUP ignoredstdout -> filesystemdPID 1nohup.outstdout + stderr
1/7
Two jobs in one session

You SSH in. sshd gives bash a pseudo-terminal; bash is the session leader. You start one job with plain & and one with nohup ... &.

← → to step

Options you'll actually use

nohup CMD &Ignore SIGHUP and run in the background
> file 2>&1Choose the output file instead of nohup.out
nohup.outCreated in the current directory (or $HOME) when stdout is a terminal
exit 127 / 126Command not found / found but not executable
disown -h %1Alternative for an already running job: bash won't send it SIGHUP
setsid CMDAlternative: run in a new session with no controlling terminal

Common mistakes

nohup ./long-job.sh without &

nohup doesn't background anything; your prompt is blocked, and Ctrl-C (SIGINT, not SIGHUP) still kills the job.

nohup ./long-job.sh > job.log 2>&1 &
Letting several jobs append to the same nohup.out

Output from unrelated jobs interleaves in one file that grows forever in whatever directory you were in.

Give each job its own log: > import.log 2>&1
Using nohup to run a production service

Nothing restarts it when it crashes or the box reboots, there's no log rotation, and it's invisible to systemctl.

A systemd unit (Restart=on-failure), or systemd-run for one-offs
Relying on nohup on hosts with systemd-logind KillUserProcesses=yes

logind kills every process in the user's session scope on logout, ignored SIGHUP or not.

systemd-run --user --unit=import ./import.sh, plus loginctl enable-linger

Interview questions

Practice

Try these on a Linux machine of your own. Each task has a hint and a solution.

  1. 1

    Start `sleep 1000` with nohup in the background and check that its SIGHUP is ignored.

  2. 2

    Run `nohup ls -l /etc` in your home directory, then find where the output went.

  3. 3

    Start `sleep 600` with nohup in the background, logging stdout and stderr to ~/job.log.

  4. 4

    Send SIGHUP to the nohup'd sleep and confirm it's still running. Then stop it properly.

Related commands

bgResume a stopped job in the backgroundjobsList the shell's background and stopped jobskillSend a signal to a processsystemctlStart, stop, enable and inspect systemd services
PreviousreniceNextdf