dfeed6782b18722a5df18d5ff7667e976906bf2c
[oweals/gnunet.git] / contrib / timeout_watchdog.c
1 /*
2      This file is part of GNUnet
3      (C) 2010 Christian Grothoff (and other contributing authors)
4
5      GNUnet is free software; you can redistribute it and/or modify
6      it under the terms of the GNU General Public License as published
7      by the Free Software Foundation; either version 2, or (at your
8      option) any later version.
9
10      GNUnet is distributed in the hope that it will be useful, but
11      WITHOUT ANY WARRANTY; without even the implied warranty of
12      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13      General Public License for more details.
14
15      You should have received a copy of the GNU General Public License
16      along with GNUnet; see the file COPYING.  If not, write to the
17      Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18      Boston, MA 02111-1307, USA.
19 */
20
21 /**
22  * @file contrib/timeout_watchdog.c
23  * @brief small tool starting a child process, waiting that it terminates or killing it after a given timeout period
24  * @author Matthias Wachs
25  */
26
27 #include "signal.h"
28 #include "stdio.h"
29 #include "stdlib.h"
30 #include <unistd.h>
31 #include <wait.h>
32
33 static int child_died;
34 static pid_t child;
35
36 void sigchld_handler(int val)
37 {
38   int status = 0;
39   int ret = 0;
40   
41   waitpid (child, &status, 0);
42   if (WIFEXITED(status) == 1)
43   {
44     ret = WEXITSTATUS(status);
45     printf("Test process exited with result %u\n", ret);
46   }
47   if (WIFSIGNALED(status) == 1)
48   {
49     printf("Test process was signaled %u\n", WTERMSIG(status));
50     ret = WTERMSIG(status);
51   }   
52   exit(ret);  
53 }
54
55 void sigint_handler(int val)
56
57   printf("Killing test process\n");
58   kill(0, val);
59   exit(1);
60 }
61
62
63 int main(int argc, char *argv[])
64 {
65 int timeout = 0;
66 int remain = 0;
67 int ret = 0;
68
69 if (argc < 3)
70 {  
71   printf("arg 1: timeout in sec., arg 2: executable, arg<n> arguments\n");     
72   exit(1);
73 }
74
75 timeout = atoi(argv[1]);
76
77 if (timeout == 0)
78   timeout = 600;   
79
80
81 char ** arguments = &argv[3];
82
83 pid_t gpid = getpgid(0);
84 signal(SIGCHLD, sigchld_handler);
85 signal(SIGABRT, sigint_handler);
86 signal(SIGKILL, sigint_handler);
87 signal(SIGILL,  sigint_handler);
88 signal(SIGSEGV, sigint_handler);
89 signal(SIGINT,  sigint_handler);
90 signal(SIGTERM, sigint_handler);
91
92 child = fork();
93 if (child==0)
94 {
95    printf("Starting test process `%s'\n",argv[2],arguments);
96    setpgid(0,gpid);
97    execvp(argv[2],&argv[2]);
98    printf("Test process `%s' could not be started\n",argv[2]);
99    exit(1);
100 }
101 if (child > 0)
102 {
103   sleep(timeout);
104   printf("Timeout, killing all test processes\n");
105   kill(0,SIGABRT);
106   exit(1);
107 }  
108 }
109
110 /* end of timeout_watchdog.c */