ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/gvpe/src/gvpectrl.C
Revision: 1.7
Committed: Thu Aug 7 17:54:27 2008 UTC (15 years, 9 months ago) by pcg
Content type: text/plain
Branch: MAIN
Changes since 1.6: +24 -14 lines
Log Message:
update to gplv3, finally

File Contents

# Content
1 /*
2 gvpectrl.C -- the main file for gvpectrl
3 Copyright (C) 1998-2002 Ivo Timmermans <ivo@o2w.nl>
4 2000-2002 Guus Sliepen <guus@sliepen.eu.org>
5 2003-2008 Marc Lehmann <gvpe@schmorp.de>
6
7 This file is part of GVPE.
8
9 GVPE is free software; you can redistribute it and/or modify it
10 under the terms of the GNU General Public License as published by the
11 Free Software Foundation; either version 3 of the License, or (at your
12 option) any later version.
13
14 This program is distributed in the hope that it will be useful, but
15 WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
17 Public License for more details.
18
19 You should have received a copy of the GNU General Public License along
20 with this program; if not, see <http://www.gnu.org/licenses/>.
21
22 Additional permission under GNU GPL version 3 section 7
23
24 If you modify this Program, or any covered work, by linking or
25 combining it with the OpenSSL project's OpenSSL library (or a modified
26 version of that library), containing parts covered by the terms of the
27 OpenSSL or SSLeay licenses, the licensors of this Program grant you
28 additional permission to convey the resulting work. Corresponding
29 Source for a non-source form of such a combination shall include the
30 source code for the parts of OpenSSL used as well as that of the
31 covered work.
32 */
33
34 #include "config.h"
35
36 #include <cstdio>
37 #include <cstring>
38 #include <cstdlib>
39
40 #include <errno.h>
41 #include <fcntl.h>
42 #include <getopt.h>
43 #include <signal.h>
44 #include <sys/stat.h>
45 #include <sys/types.h>
46 #include <unistd.h>
47 #include <signal.h>
48
49 #include <openssl/rand.h>
50 #include <openssl/rsa.h>
51 #include <openssl/pem.h>
52 #include <openssl/evp.h>
53
54 #include "pidfile.h"
55
56 #include "conf.h"
57 #include "slog.h"
58 #include "util.h"
59 #include "vpn.h"
60
61 /* If nonzero, display usage information and exit. */
62 static int show_help;
63
64 /* If nonzero, print the version on standard output and exit. */
65 static int show_version;
66
67 /* If nonzero, it will attempt to kill a running gvpe and exit. */
68 static int kill_gvpe;
69
70 /* If nonzero, it will attempt to kill a running gvpe and exit. */
71 static int show_config;
72
73 /* If nonzero, generate public/private keypair for this net. */
74 static int generate_keys;
75
76 static struct option const long_options[] =
77 {
78 {"config", required_argument, NULL, 'c'},
79 {"kill", optional_argument, NULL, 'k'},
80 {"help", no_argument, &show_help, 1},
81 {"version", no_argument, &show_version, 1},
82 {"generate-keys", no_argument, NULL, 'g'},
83 {"show-config", no_argument, &show_config, 's'},
84 {NULL, 0, NULL, 0}
85 };
86
87 static void
88 usage (int status)
89 {
90 if (status != 0)
91 fprintf (stderr, _("Try `%s --help\' for more information.\n"), get_identity ());
92 else
93 {
94 printf (_("Usage: %s [option]...\n\n"), get_identity ());
95 printf (_
96 (" -c, --config=DIR Read configuration options from DIR.\n"
97 " -k, --kill[=SIGNAL] Attempt to kill a running gvpe and exit.\n"
98 " -g, --generate-keys Generate public/private RSA keypair.\n"
99 " -s, --show-config Display the configuration information.\n"
100 " --help Display this help and exit.\n"
101 " --version Output version information and exit.\n\n"));
102 printf (_("Report bugs to <gvpe@schmorp.de>.\n"));
103 }
104
105 exit (status);
106 }
107
108 void
109 parse_options (int argc, char **argv, char **envp)
110 {
111 int r;
112 int option_index = 0;
113
114 while ((r =
115 getopt_long (argc, argv, "c:k::gs", long_options,
116 &option_index)) != EOF)
117 {
118 switch (r)
119 {
120 case 0: /* long option */
121 break;
122
123 case 'c': /* config file */
124 confbase = strdup (optarg);
125 break;
126
127 case 'k': /* kill old gvpes */
128 if (optarg)
129 {
130 if (!strcasecmp (optarg, "HUP"))
131 kill_gvpe = SIGHUP;
132 else if (!strcasecmp (optarg, "TERM"))
133 kill_gvpe = SIGTERM;
134 else if (!strcasecmp (optarg, "KILL"))
135 kill_gvpe = SIGKILL;
136 else if (!strcasecmp (optarg, "USR1"))
137 kill_gvpe = SIGUSR1;
138 else if (!strcasecmp (optarg, "USR2"))
139 kill_gvpe = SIGUSR2;
140 else if (!strcasecmp (optarg, "INT"))
141 kill_gvpe = SIGINT;
142 else if (!strcasecmp (optarg, "ALRM"))
143 kill_gvpe = SIGALRM;
144 else
145 {
146 kill_gvpe = atoi (optarg);
147
148 if (!kill_gvpe)
149 {
150 fprintf (stderr,
151 _
152 ("Invalid argument `%s'; SIGNAL must be a number or one of HUP, TERM, KILL, USR1, USR2, WINCH, INT or ALRM.\n"),
153 optarg);
154 usage (1);
155 }
156 }
157 }
158 else
159 kill_gvpe = SIGTERM;
160
161 break;
162
163 case 'g': /* generate public/private keypair */
164 generate_keys = RSA_KEYBITS;
165 break;
166
167 case 's':
168 show_config = 1;
169 break;
170
171 case '?':
172 usage (1);
173
174 default:
175 break;
176 }
177 }
178 }
179
180 /* This function prettyprints the key generation process */
181
182 void
183 indicator (int a, int b, void *p)
184 {
185 switch (a)
186 {
187 case 0:
188 fprintf (stderr, ".");
189 break;
190
191 case 1:
192 fprintf (stderr, "+");
193 break;
194
195 case 2:
196 fprintf (stderr, "-");
197 break;
198
199 case 3:
200 switch (b)
201 {
202 case 0:
203 fprintf (stderr, " p\n");
204 break;
205
206 case 1:
207 fprintf (stderr, " q\n");
208 break;
209
210 default:
211 fprintf (stderr, "?");
212 }
213 break;
214
215 default:
216 fprintf (stderr, "?");
217 }
218 }
219
220 /*
221 * generate public/private RSA keypairs for all hosts that don't have one.
222 */
223 int
224 keygen (int bits)
225 {
226 RSA *rsa_key;
227 FILE *f;
228 char *name = NULL;
229 char *fname;
230
231 asprintf (&fname, "%s/hostkeys", confbase);
232 mkdir (fname, 0700);
233 free (fname);
234
235 asprintf (&fname, "%s/pubkey", confbase);
236 mkdir (fname, 0700);
237 free (fname);
238
239 for (configuration::node_vector::iterator i = conf.nodes.begin (); i != conf.nodes.end (); ++i)
240 {
241 conf_node *node = *i;
242
243 asprintf (&fname, "%s/pubkey/%s", confbase, node->nodename);
244
245 f = fopen (fname, "a");
246
247 if (!f)
248 {
249 perror (fname);
250 exit (EXIT_FAILURE);
251 }
252
253 if (ftell (f))
254 {
255 fprintf (stderr, "'%s' already exists, skipping this node\n",
256 fname);
257 fclose (f);
258 continue;
259 }
260
261 fprintf (stderr, _("generating %d bits key for %s:\n"), bits,
262 node->nodename);
263
264 rsa_key = RSA_generate_key (bits, 0xFFFF, indicator, NULL);
265
266 if (!rsa_key)
267 {
268 fprintf (stderr, _("error during key generation!\n"));
269 return -1;
270 }
271 else
272 fprintf (stderr, _("Done.\n"));
273
274 require (PEM_write_RSAPublicKey (f, rsa_key));
275 fclose (f);
276 free (fname);
277
278 asprintf (&fname, "%s/hostkeys/%s", confbase, node->nodename);
279
280 f = fopen (fname, "a");
281 if (!f)
282 {
283 perror (fname);
284 exit (EXIT_FAILURE);
285 }
286
287 require (PEM_write_RSAPrivateKey (f, rsa_key, NULL, NULL, 0, NULL, NULL));
288 fclose (f);
289 free (fname);
290 }
291
292 return 0;
293 }
294
295 int
296 main (int argc, char **argv, char **envp)
297 {
298 set_identity (argv[0]);
299 log_to (LOGTO_STDERR);
300
301 setlocale (LC_ALL, "");
302 bindtextdomain (PACKAGE, LOCALEDIR);
303 textdomain (PACKAGE);
304
305 parse_options (argc, argv, envp);
306
307 if (show_version)
308 {
309 printf (_("%s version %s (built %s %s, protocol version %d.%d)\n"), get_identity (),
310 VERSION, __DATE__, __TIME__, PROTOCOL_MAJOR, PROTOCOL_MINOR);
311 printf (_("Built with kernel interface %s/%s.\n"), IFTYPE, IFSUBTYPE);
312 printf (_
313 ("Copyright (C) 2003 Marc Lehmann <gvpe@schmorp.de> and others.\n"
314 "See the AUTHORS file for a complete list.\n\n"
315 "vpe comes with ABSOLUTELY NO WARRANTY. This is free software,\n"
316 "and you are welcome to redistribute it under certain conditions;\n"
317 "see the file COPYING for details.\n"));
318
319 return 0;
320 }
321
322 if (show_help)
323 usage (0);
324
325 {
326 configuration_parser (conf, false, 0, 0);
327 }
328
329 if (generate_keys)
330 {
331 RAND_load_file ("/dev/urandom", 1024);
332 exit (keygen (generate_keys));
333 }
334
335 if (kill_gvpe)
336 exit (kill_other (kill_gvpe));
337
338 if (show_config)
339 {
340 conf.print ();
341 exit (EXIT_SUCCESS);
342 }
343
344 usage (1);
345 }