Penguin

In Unix you can run "jobs", suspend them, run them in the background, or bring them to the foreground.

The commands for this are:

jobs

This command will list all of the active jobs. Some switches you may like to try include:

  • jobs -r will display running jobs only.
  • jobs -s will display stopped jobs only.

bg

bg <JOB_SPEC> moves the job into the background.

Note : if the job is currently in the foreground you will first have to suspend it using Ctrl-z (SIGTSTP)

Note : To start an application in the background append & to the end of your command.

  • ping www.gooogle.co.nz &

fg

fg <JOB_SPEC> moves the stopped or backgrounded job into the foreground.

kill

kill %<JOB_SPEC> sends a signal to a job.

Note : you can use use kill -l to list the possible signals you could send.

bg,fg and kill are not limited to jobids.

We can also specify the start or part of the job command.

For example: If a job command consisted of ping www.google.co.nz, then these commands are valid.

  • kill %ping
  • kill %?google
  • fg ping
  • bg ?goo

These will work as long as you don't supply an ambiguous job_spec. Notice that, only kill requires the % so that it knows we are providing it with a JOB_SPEC rather than a process id.

How this works

Internally each command line (job) gets it's own ProcessGroup assigned to it by the shell when it creates the job using setsid(2). While the command is running in the foreground it recieves any signals from the tty layer (such as SIGTSTP, SIGINT, SIGQUIT, SIGHUP etc).

If you press ^Z the ProcessGroup gets sent a SIGTSTP. If the process(es) ignore the SIGTSTP, this is converted by the kernel into a SIGSTOP. When a process recieves a SIGSTOP it's parent (the shell) will get notified (via a SIGCHLD), and will mark that job as being "Stopped".

When you type "fg" or "bg", then the process is started with a SIGCONT, and in the case of fg, tcsetpgrp(3) is called to make that ProcessGroup the new foreground ProcessGroup.

When the shell recieves a SIGHUP (presumably from the terminal going away), then it will send a SIGHUP to each job. If a job is also "Stopped" then the shell will also send it a SIGCONT. Depending on your shell, exiting the shell with ^D, "exit", "logout","exit 0" etc may or may not cause jobs to recieve the SIGHUP.

The disown builtin may be used to remove a process group from the shells list of jobs, so when the shell exits it doesn't send that process a SIGHUP.