summaryrefslogtreecommitdiff
path: root/sbin
diff options
context:
space:
mode:
authorHakan Olsson <ho@cvs.openbsd.org>2001-08-24 13:53:03 +0000
committerHakan Olsson <ho@cvs.openbsd.org>2001-08-24 13:53:03 +0000
commitffd9f36de8f104da26e86600920ad2e556c3a0d1 (patch)
tree77a9bab1204582b1fe8085a1be75c1d1d77e92da /sbin
parentb554fbe8f5bec59f02042217e029891f2a22d05a (diff)
Send DELETE notifications for all active SAs when we shut down the daemon.
This "clean" shutdown happens on SIGTERM ('kill <pid>') or if a 'Q' command is input to the fifo UI. Suggested by <Ghislaine.Labouret@hsc.fr>.
Diffstat (limited to 'sbin')
-rw-r--r--sbin/isakmpd/isakmpd.c96
-rw-r--r--sbin/isakmpd/ui.c33
2 files changed, 114 insertions, 15 deletions
diff --git a/sbin/isakmpd/isakmpd.c b/sbin/isakmpd/isakmpd.c
index 6dc3054a3e2..29d410048f6 100644
--- a/sbin/isakmpd/isakmpd.c
+++ b/sbin/isakmpd/isakmpd.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: isakmpd.c,v 1.35 2001/08/23 23:11:02 angelos Exp $ */
+/* $OpenBSD: isakmpd.c,v 1.36 2001/08/24 13:53:02 ho Exp $ */
/* $EOM: isakmpd.c,v 1.54 2000/10/05 09:28:22 niklas Exp $ */
/*
@@ -54,6 +54,7 @@
#include "init.h"
#include "libcrypto.h"
#include "log.h"
+#include "sa.h"
#include "timer.h"
#include "transport.h"
#include "udp.h"
@@ -87,6 +88,20 @@ static int sighupped = 0;
static int sigusr1ed = 0;
static char *report_file = "/var/run/isakmpd.report";
+/*
+ * If we receive a USR2 signal, this flag gets set to show we need to
+ * rehash our SA soft expiration timers to a uniform distribution.
+ * XXX Perhaps this is a really bad idea?
+ */
+static int sigusr2ed = 0;
+
+/*
+ * If we recieve a TERM signal, perform a "clean shutdown" of the daemon.
+ * This includes to send DELETE notifications for all our active SAs.
+ */
+static int sigtermed = 0;
+void daemon_shutdown_now (int);
+
/* The default path of the PID file. */
static char *pid_file = "/var/run/isakmpd.pid";
@@ -95,13 +110,6 @@ static char *pid_file = "/var/run/isakmpd.pid";
static char *pcap_file = 0;
#endif
-/*
- * If we receive a USR2 signal, this flag gets set to show we need to
- * rehash our SA soft expiration timers to a uniform distribution.
- * XXX Perhaps this is a really bad idea?
- */
-static int sigusr2ed = 0;
-
static void
usage (void)
{
@@ -318,6 +326,61 @@ sigusr2 (int sig)
sigusr2ed = 1;
}
+static int
+phase2_sa_check (struct sa *sa, void *arg)
+{
+ return sa->phase == 2;
+}
+
+static void
+daemon_shutdown (void)
+{
+ /* Perform a (protocol-wise) clean shutdown of the daemon. */
+ struct sa *sa;
+ static int msg_counter = 0;
+
+ if (sigtermed == 1)
+ {
+ log_print ("isakmpd: shutting down...");
+
+ /* Delete all active phase 2 SAs. */
+ while ((sa = sa_find (phase2_sa_check, NULL)))
+ {
+ /* Each DELETE is another (outgoing) message. */
+ msg_counter++;
+ sa_delete (sa, 1);
+ }
+
+ /*
+ * As there may have been other messages queued before these, we
+ * add a 'grace factor' to make sure all the DELETEs actually get
+ * sent before we shut down. The select() loop will just spin
+ * a number of more times before we actually do the exit.
+ */
+ msg_counter = ++msg_counter * 2;
+
+ /* XXX Phase 1, transports, timers, exchanges, connections, ...? */
+ }
+ else if (sigtermed >= msg_counter)
+ {
+ /* Goodbye. */
+#ifdef USE_DEBUG
+ log_packet_stop ();
+#endif
+ log_print ("isakmpd: exit");
+ exit (0);
+ }
+
+ sigtermed++;
+}
+
+/* called on SIGTERM */
+void
+daemon_shutdown_now (int sig)
+{
+ sigtermed = 1;
+}
+
/* Write pid file. */
static void
write_pid_file (void)
@@ -367,6 +430,9 @@ main (int argc, char *argv[])
/* Rehash soft expiration timers on USR2 reception. */
signal (SIGUSR2, sigusr2);
+ /* Do a clean daemon shutdown on TERM reception. */
+ signal (SIGTERM, daemon_shutdown_now);
+
#ifdef USE_DEBUG
/* If we wanted IKE packet capture to file, initialize it now. */
if (pcap_file != 0)
@@ -397,6 +463,20 @@ main (int argc, char *argv[])
if (sigusr2ed)
rehash_timers ();
+ /*
+ * and if someone set 'sigtermed' (SIGTERM or via the UI), this
+ * indicated we should start a shutdown of the daemon.
+ *
+ * Note: Since _one_ message is sent per iteration of this enclosing
+ * while-loop, and we want to send a number of DELETE notifications,
+ * we must loop atleast this number of times. The daemon_shutdown()
+ * function starts by queueing the DELETEs, all other calls just
+ * increments the 'sigtermed' variable until it reaches a "safe"
+ * value, and the daemon exits.
+ */
+ if (sigtermed)
+ daemon_shutdown ();
+
/* Setup the descriptors to look for incoming messages at. */
memset (rfds, 0, mask_size);
n = transport_fd_set (rfds);
diff --git a/sbin/isakmpd/ui.c b/sbin/isakmpd/ui.c
index dc5f74b59a0..3b3ae1e99a7 100644
--- a/sbin/isakmpd/ui.c
+++ b/sbin/isakmpd/ui.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ui.c,v 1.20 2001/07/06 14:37:12 ho Exp $ */
+/* $OpenBSD: ui.c,v 1.21 2001/08/24 13:53:02 ho Exp $ */
/* $EOM: ui.c,v 1.43 2000/10/05 09:25:12 niklas Exp $ */
/*
@@ -59,6 +59,9 @@
#define BUF_SZ 256
+/* from isakmpd.c */
+void daemon_shutdown_now (int);
+
char *ui_fifo = FIFO;
int ui_socket;
@@ -257,6 +260,18 @@ ui_packetlog (char *cmd)
}
#endif /* USE_DEBUG */
+static void
+ui_shutdown_daemon (char *cmd)
+{
+ if (strlen (cmd) == 1)
+ {
+ log_print ("ui_shutdown_daemon: received shutdown command");
+ daemon_shutdown_now (0);
+ }
+ else
+ log_print ("ui_shutdown_daemon: command \"%s\" malformed", cmd);
+}
+
/* Report SAs and ongoing exchanges. */
void
ui_report (char *cmd)
@@ -298,6 +313,16 @@ ui_handle_command (char *line)
break;
#endif
+#ifdef USE_DEBUG
+ case 'p':
+ ui_packetlog (line);
+ break;
+#endif
+
+ case 'Q':
+ ui_shutdown_daemon (line);
+ break;
+
case 'r':
ui_report (line);
break;
@@ -306,12 +331,6 @@ ui_handle_command (char *line)
ui_teardown (line);
break;
-#ifdef USE_DEBUG
- case 'p':
- ui_packetlog (line);
- break;
-#endif
-
default:
log_print ("ui_handle_messages: unrecognized command: '%c'", line[0]);
}