From 1eb85ef5407e27b35dcec8a34eda23d3e39ddaa6 Mon Sep 17 00:00:00 2001 From: Ethan Jackson Date: Tue, 20 Dec 2011 15:31:34 -0800 Subject: [PATCH] ovs-ofctl: Support daemonization for monitor and snoop. This will ease implementation of future unit tests. Signed-off-by: Ethan Jackson --- NEWS | 2 ++ manpages.mk | 2 ++ utilities/ovs-ofctl.8.in | 11 +++++++ utilities/ovs-ofctl.c | 62 ++++++++++++++++++++++++++++++++++++++-- 4 files changed, 74 insertions(+), 3 deletions(-) diff --git a/NEWS b/NEWS index 675e4c4f..332d7403 100644 --- a/NEWS +++ b/NEWS @@ -3,6 +3,8 @@ port-v1.4.0 - OpenFlow: - Added support for querying, modifying, and deleting flows based on flow cookie when using NXM. + - ovs-ofctl: + - Added daemonization support to the monitor and snoop commands. v1.4.0 - xx xxx xxxx diff --git a/manpages.mk b/manpages.mk index 48f2db5f..14bb41f0 100644 --- a/manpages.mk +++ b/manpages.mk @@ -121,11 +121,13 @@ lib/vlog.man: utilities/ovs-ofctl.8: \ utilities/ovs-ofctl.8.in \ lib/common.man \ + lib/daemon.man \ lib/ssl.man \ lib/vconn-active.man \ lib/vlog.man utilities/ovs-ofctl.8.in: lib/common.man: +lib/daemon.man: lib/ssl.man: lib/vconn-active.man: lib/vlog.man: diff --git a/utilities/ovs-ofctl.8.in b/utilities/ovs-ofctl.8.in index 45574b4d..6c78c68f 100644 --- a/utilities/ovs-ofctl.8.in +++ b/utilities/ovs-ofctl.8.in @@ -1054,11 +1054,22 @@ flow format, \fBovs\-ofctl\fR will report a fatal error. Increases the verbosity of OpenFlow messages printed and logged by \fBovs\-ofctl\fR commands. Specify this option more than once to increase verbosity further. +. +.ds DD \ +\fBovs\-ofctl\fR detaches only when executing the \fBmonitor\fR or \ +\fBsnoop\fR commands. +.so lib/daemon.man .SS "Public Key Infrastructure Options" .so lib/ssl.man .so lib/vlog.man .so lib/common.man . +.SH "RUNTIME MANAGEMENT COMMANDS" +\fBovs\-appctl\fR(8) can send commands to a running \fBovs\-ofctl\fR process. +The currently supported commands only apply when executing the \fBmonitor\fR or +\fBsnoop\fR commands and are described below. +.IP "\fBexit\fR" +Causes \fBovs\-ofctl\fR to gracefully terminate. .SH EXAMPLES . The following examples assume that \fBovs\-vswitchd\fR has a bridge diff --git a/utilities/ovs-ofctl.c b/utilities/ovs-ofctl.c index 7b20ba09..044f74cc 100644 --- a/utilities/ovs-ofctl.c +++ b/utilities/ovs-ofctl.c @@ -30,6 +30,7 @@ #include "byte-order.h" #include "classifier.h" #include "command-line.h" +#include "daemon.h" #include "compiler.h" #include "dirs.h" #include "dynamic-string.h" @@ -43,9 +44,11 @@ #include "ofproto/ofproto.h" #include "openflow/nicira-ext.h" #include "openflow/openflow.h" +#include "poll-loop.h" #include "random.h" #include "stream-ssl.h" #include "timeval.h" +#include "unixctl.h" #include "util.h" #include "vconn.h" #include "vlog.h" @@ -87,6 +90,7 @@ parse_options(int argc, char *argv[]) enum { OPT_STRICT = UCHAR_MAX + 1, OPT_READD, + DAEMON_OPTION_ENUMS, VLOG_OPTION_ENUMS }; static struct option long_options[] = { @@ -97,6 +101,7 @@ parse_options(int argc, char *argv[]) {"more", no_argument, NULL, 'm'}, {"help", no_argument, NULL, 'h'}, {"version", no_argument, NULL, 'V'}, + DAEMON_LONG_OPTIONS, VLOG_LONG_OPTIONS, STREAM_SSL_LONG_OPTIONS, {NULL, 0, NULL, 0}, @@ -149,6 +154,7 @@ parse_options(int argc, char *argv[]) readd = true; break; + DAEMON_OPTION_HANDLERS VLOG_OPTION_HANDLERS STREAM_SSL_OPTION_HANDLERS @@ -193,6 +199,7 @@ usage(void) "where SWITCH or TARGET is an active OpenFlow connection method.\n", program_name, program_name); vconn_usage(true, false, false); + daemon_usage(); vlog_usage(); printf("\nOther options:\n" " --strict use strict match for flow commands\n" @@ -205,6 +212,15 @@ usage(void) exit(EXIT_SUCCESS); } +static void +ofctl_exit(struct unixctl_conn *conn, int argc OVS_UNUSED, + const char *argv[] OVS_UNUSED, void *exiting_) +{ + bool *exiting = exiting_; + *exiting = true; + unixctl_command_reply(conn, 200, ""); +} + static void run(int retval, const char *message, ...) PRINTF_FORMAT(2, 3); @@ -752,11 +768,51 @@ do_del_flows(int argc, char *argv[]) static void monitor_vconn(struct vconn *vconn) { + struct unixctl_server *server; + bool exiting = false; + int error, fd; + + /* Daemonization will close stderr but we really want to keep it, so make a + * copy. */ + fd = dup(STDERR_FILENO); + + daemonize_start(); + error = unixctl_server_create(NULL, &server); + if (error) { + ovs_fatal(error, "failed to create unixctl server"); + } + unixctl_command_register("exit", "", 0, 0, ofctl_exit, &exiting); + daemonize_complete(); + + /* Now get stderr back. */ + dup2(fd, STDERR_FILENO); + for (;;) { struct ofpbuf *b; - run(vconn_recv_block(vconn, &b), "vconn_recv"); - ofp_print(stderr, b->data, b->size, verbosity + 2); - ofpbuf_delete(b); + int retval; + + unixctl_server_run(server); + + for (;;) { + retval = vconn_recv(vconn, &b); + if (retval == EAGAIN) { + break; + } + + run(retval, "vconn_recv"); + ofp_print(stderr, b->data, b->size, verbosity + 2); + ofpbuf_delete(b); + } + + if (exiting) { + break; + } + + vconn_run(vconn); + vconn_run_wait(vconn); + vconn_recv_wait(vconn); + unixctl_server_wait(server); + poll_block(); } } -- 2.30.2