2 * Amanda, The Advanced Maryland Automatic Network Disk Archiver
3 * Copyright (c) 1991-1998 University of Maryland at College Park
6 * Permission to use, copy, modify, distribute, and sell this software and its
7 * documentation for any purpose is hereby granted without fee, provided that
8 * the above copyright notice appear in all copies and that both that
9 * copyright notice and this permission notice appear in supporting
10 * documentation, and that the name of U.M. not be used in advertising or
11 * publicity pertaining to distribution of the software without specific,
12 * written prior permission. U.M. makes no representations about the
13 * suitability of this software for any purpose. It is provided "as is"
14 * without express or implied warranty.
16 * U.M. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL U.M.
18 * BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
19 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
20 * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
21 * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
23 * Authors: the Amanda Development Team. Its members are listed in a
24 * file named AUTHORS, in the root directory of this distribution.
27 * $Id: killpgrp.c,v 1.8.4.2.4.1 2002/10/27 14:31:18 martinea Exp $
29 * if it is the process group leader, it kills all processes in its
30 * process group when it is killed itself.
37 #define AM_GETPGRP() getpgrp()
39 #define AM_GETPGRP() getpgrp(getpid())
42 /* we cannot check it, so let us assume it is ok */
43 #define AM_GETPGRP() getpid()
46 int main P((int argc, char **argv));
47 static void term_kill_soft P((int sig));
48 static void term_kill_hard P((int sig));
57 for(fd = 3; fd < FD_SETSIZE; fd++) {
59 * Make sure nobody spoofs us with a lot of extra open files
60 * that would cause an open we do to get a very high file
61 * descriptor, which in turn might be used as an index into
62 * an array (e.g. an fd_set).
69 set_pname("killpgrp");
72 dbprintf(("%s: version %s\n", argv[0], version()));
74 if(client_uid == (uid_t) -1) {
75 error("error [cannot find user %s in passwd file]", CLIENT_LOGIN);
79 if (getuid() != client_uid) {
80 error("error [must be invoked by %s]", CLIENT_LOGIN);
84 error("error [must be setuid root]");
86 #endif /* FORCE_USERID */
88 #if !defined (DONT_SUID_ROOT)
92 if (AM_GETPGRP() != getpid()) {
93 error("error [must be the process group leader]");
96 signal(SIGTERM, term_kill_soft);
98 while (getchar() != EOF) {
105 if (wait(&status) != -1)
107 if (errno != EINTR) {
108 error("error [wait() failed: %s]", strerror(errno));
113 dbprintf(("child process exited with status %d\n", WEXITSTATUS(status)));
115 return WEXITSTATUS(status);
118 static void term_kill_soft(sig)
121 pid_t dumppid = getpid();
124 signal(SIGTERM, SIG_IGN);
125 signal(SIGALRM, term_kill_hard);
128 * First, try to kill the dump process nicely. If it ignores us
129 * for three seconds, hit it harder.
131 dbprintf(("sending SIGTERM to process group %ld\n", (long) dumppid));
132 killerr = kill(-dumppid, SIGTERM);
134 dbprintf(("kill failed: %s\n", strerror(errno)));
138 static void term_kill_hard(sig)
141 pid_t dumppid = getpid();
144 dbprintf(("it won\'t die with SIGTERM, but SIGKILL should do\n"));
145 dbprintf(("do\'t expect any further output, this will be suicide\n"));
146 killerr = kill(-dumppid, SIGKILL);
147 /* should never reach this point, but so what? */
149 dbprintf(("kill failed: %s\n", strerror(errno)));
150 dbprintf(("waiting until child terminates\n"));