2

I had paused 50 processes (background here) using

kill -STOP

and then that shell window crashed (probably a GUI issue - I had just asked the configuration for help on scrolling options), and that seemed to cause the 50 processes to un-pause. (I was able to pause them again).

But why would the shell crashing cause the processes to un-pause? Shouldn't they remain paused until someone tells them to un-pause?

1 Answer 1

5

As a result of the termination of the shell, POSIX.1-2008 requires:

If the exit of the process causes a process group to become orphaned, and if any member of the newly-orphaned process group is stopped, then a SIGHUP signal followed by a SIGCONT signal shall be sent to each process in the newly-orphaned process group.

The default action on receipt of SIGHUP is to terminate the process. However, depending on the shell and how the process was started, as well as any signal handling set up by the process itself, SIGHUP may be ignored by the process. In that case the process will continue normal execution.

The assumption is that processes in a process group, running under a job control shell, will be manipulated by that shell as a group, and not by the user sending direct SIGSTOP and SIGCONT signals. POSIX.1-2008 explains:

...if the termination of a process causes a process group to become orphaned, processes within the group are disconnected from their job control shell, which no longer has any information on the existence of the process group. Stopped processes within the group would languish forever. In order to avoid this problem, newly orphaned process groups that contain stopped processes are sent a SIGHUP signal and a SIGCONT signal to indicate that they have been disconnected from their session. The SIGHUP signal causes the process group members to terminate unless they are catching or ignoring SIGHUP. Under most circumstances, all of the members of the process group are stopped if any of them are stopped.

A process could avoid this behavior by forking and creating its own session (setsid()), so that it would no longer be part of the session of the shell where it was started. It would then not be affected by job control within the shell, by the shell's termination, or by signals generated from the terminal.

2
  • The processes I had paused were calling other ruby scripts (some of which themselves called other C compiled programs). Could it have interpreted SIGHUP as applying to the sub-process? (My scripts didn't have any signal handling code, though) Jul 16, 2009 at 11:49
  • The SIGHUP and SIGCONT will be sent to all processes in the process group, which includes all of the sub-processes (unless they started their own new process group or session). You can check whether the process is ignoring SIGHUP -- on Linux grep SigIgn: /proc/<pid>/status and check bit with value 0x1; on Solaris use psig <pid>.
    – mark4o
    Jul 16, 2009 at 17:14

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .