Date: Sun, 28 Jul 1996 22:36:01 +0000 () From: James Raynard <fqueries@jraynard.demon.co.uk> To: Gordon Beck <gordon@galisant.demon.co.uk> Cc: questions@freebsd.org Subject: Re: killing child processes Message-ID: <199607282236.WAA03556@jraynard.demon.co.uk> In-Reply-To: <838578160snx@galisant.demon.co.uk> from "Gordon Beck" at Jul 28, 96 11:22:40 am
next in thread | previous in thread | raw e-mail | index | archive | help
> > > I have a monitor daemon which forks and runs an application. > > > If the application dies then the daemon get to know about it. > However, if the daemon dies or is killed, then the child continues to run. Yep, this is normal behaviour - the child becomes a child of init instead of its original parent. > I had expected the child to get a SIGHUP, which it is not blocking. > However, I think that SIGHUP is only generated if the daemon is > a process group leader and had a control terminal whose TGRP matched > the process group (?). > > > If a daemon process issues setpgrp then it can on longer acquire a control > terminal(?), which is cache 22. >From what I understand of it, this sounds like you're expecting the SVR3 behaviour, where a "process group" corresponds loosely to all the commands started in a login session. FreeBSD follows POSIX, where a "process group" corresponds to a job and the login session is referred to as a "session" (the difference is necessary to add support for BSD-style job control). Under FreeBSD, logging in creates a new session, whose controlling terminal is whichever one you logged in to. Every time you type a command at the shell's command prompt, it forms a new process group:- $ ls # A process group $ prog1 | prog2 # Another process group $ prog3 | prog4 & # A process group in the background Each process group has a process group ID which is equal to the PID of the first process in the job. They will also have a session ID, which is the same for all processes in a login session unless a program calls setsid() to detach itself from the controlling terminal. Such a process will start a new session, with its own session ID, and will be the session leader. It can acquire a new controlling terminal simply by opening one (either a real terminal or a pseudo-terminal for a network connection). If the controlling terminal is lost for some reason (eg user logging out or a dropped connection on a dialup link), SIGHUP is sent only to the session leader for that terminal, unlike SVR3 where it was sent to every process attached to the terminal. Typically, this will be the user's login shell or something like a PPP process which should know how to do the right thing. setpgrp() has been superseded on FreeBSD by POSIX's setpgid(), which is mainly used by shells to implement job control. > Anyone have clues/pointers/source code for a general or specific solution > to this problem The only circumstances I know where a child is signalled by a parent terminating is if the child is stopped; in this case, it receives a SIGHUP followed by a SIGCONT. to verify this, change the 'if (0)' to 'if(1)' in the example below (loosely adapted from "Advanced Programming in the Unix Environment" by Stevens). If the child is not stopped, the best way to inform the child of the parent's impending demise is probably for the parent to send it a signal. #include <sys/types.h> #include <errno.h> #include <fcntl.h> #include <signal.h> #include <stdio.h> #include <unistd.h> static void sig_hup(int); int main() { pid_t pid; if ((pid = fork()) < 0) perror("fork"); else if (pid > 0) { /* parent */ setsid(); sleep(10); exit(0); } else { /* child */ signal(SIGHUP, sig_hup); if (0) kill(getpid(), SIGTSTP); /* stop ourselves */ else sleep(20); exit(0); } } void sig_hup(int signo) { printf("SIGHUP received, pid = %ld\n", (unsigned long)getpid()); }
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?199607282236.WAA03556>