Must a Process Group Have a Running Leader Process

Must a process group have a running leader process?

There is no succeeding leader: once a process group leader exits, the group loses leadership. Nothing requires a process group to have a leader, it's perfectly fine not to have one, and you can still send signals to every element in the group with kill(2).

What exactly happens when the leader exits depends on the status of the processes in the group and whether or not the group classifies as an orphaned process group.

First, let's see what is an orphaned group.

POSIX defines an orphaned process group as a group in which the parent of each process belonging to that group is either a member of that same group or is part of another session.

In other words, a process group is not orphaned as long as at least one process in the group has a parent in a different process group but in the same session.

This definition may seem odd at first, but there is a rationale behind this, which will (hopefully) be clear in a moment.

So why is it important to know if a group is orphaned? Because of processes that are stopped. If a process group is orphaned, and there is at least one process in that group that is stopped (e.g. it was suspended with SIGSTOP or SIGTSTP), then POSIX.1 requires that every process in the orphaned group be sent SIGHUP followed by SIGCONT. The reason for doing this is to avoid having the process stopped forever: consider the case where the session leader and the process group leader exit, and the group is left with a stopped process. Since the parent is in another session, it doesn't have permission to send it SIGCONT, so the process would never run again.

OTOH, if the parent is in the same session but in a different group, then there is a chance that it will signal the stopped process with SIGCONT, so the group is not considered orphaned and there is no need to forcefully wake up stopped processes.

Can the first argument to setpgid() be a session leader or a group leader?

This behavior is specified by POSIX (which means it applies to everything calling itself "Unix", not just Linux). http://pubs.opengroup.org/onlinepubs/9699919799/functions/setpgid.html says:

ERRORS
[EPERM] The process indicated by the pid argument is a session leader.

The spec doesn't say why this rule exists, but I believe the rationale stated by dbush is correct: a session leader must always be a process group leader; if it could move into another process group, it would cease to be a process group leader, violating the invariant.

However, a process that is only a process group leader, not a session leader, may put itself into another process group (ceasing to be a process group leader) and may then take itself back out of the process group and become a process group leader again. Job control shells actually have to do this under some circumstances: note the bit at the bottom of the RATIONALE section of the spec

One non-obvious use of setpgid() is to allow a job control shell to return itself to its original process group (the one in effect when the job control shell was executed). A job control shell does this before returning control back to its parent when it is terminating or suspending itself as a way of restoring its job control "state" back to what its parent would expect.

POSIX doesn't explain why the job control shell would have changed its process group in the first place, but the GNU C Library manual section on implementing job control fills in the gap:

When a shell program that normally performs job control is started, it has to be careful in case it has been invoked from another shell that is already doing its own job control.

A subshell that runs interactively has to ensure that it has been placed in the foreground by its parent shell before it can enable job control itself.

[...]

Once the subshell has been placed into the foreground by its parent shell, it can enable its own job control. It does this by calling setpgid to put itself into its own process group, and then calling tcsetpgrp to place this process group into the foreground.

And then, of course, it has to undo that again if the subshell is suspended (e.g. Bash has a suspend builtin that does this).

Also notice that a job control shell does not establish itself as a session leader, even if it's not a subshell of anything. The session is initialized by whatever program is responsible for setting up the controlling terminal; that program is typically the parent and pre-exec identity of the outermost shell running in the terminal. For instance, xterm calls setsid after opening a pseudoterminal and forking, but before exec-ing the program that will run in that terminal window.

how to get the process group leader of a thread

To access group leader information of a thread you can use "current->group_leader". In Linux, threads are just another process but shares "memory" group_leader.

Pthread function calls "clone" system call with CLONE_VM.

why SIGHUP signal not received when becoming an Orphaned Process Group

That document section is talking specifically about the loss of a controlling terminal of a process that had one—usually by a modem hangup, or the virtual equivalent (ending an ssh session, etc). (I think the phrasing in the document could be improved here). When you use setsid() here, you give up access to the controlling terminal by the time setsid() returns, so there is no controlling terminal to lose from there forward.

You could open() a tty device (such as a pty slave) to gain a controlling terminal (note that you may have to do some additional operation as well—FreeBSD requires a TIOCSCTTY ioctl), then lose it again, and then you should get the SIGHUP signal.

Does Linux allow process group ids to be reassigned to processes?

Not a problem, because fork guarantees:

The child process ID also shall not match any active process group ID.

And fork is the only way to create new processes.



Related Topics



Leave a reply



Submit