From: Ethan Jackson Date: Fri, 25 Mar 2011 22:30:33 +0000 (-0700) Subject: cfm: Create new cfm/show appctl command. X-Git-Url: https://pintos-os.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=20c8e9710834ab38c2d557f10ac54ceba2d85b18;p=openvswitch cfm: Create new cfm/show appctl command. This will be useful for debugging CFM problems in the future. --- diff --git a/lib/cfm.c b/lib/cfm.c index ce1269ba..9d9b1bd0 100644 --- a/lib/cfm.c +++ b/lib/cfm.c @@ -21,6 +21,7 @@ #include #include +#include "dynamic-string.h" #include "flow.h" #include "hash.h" #include "hmap.h" @@ -81,7 +82,7 @@ ms_to_ccm_interval(int interval_ms) } static struct cfm_internal * -cfm_to_internal(struct cfm *cfm) +cfm_to_internal(const struct cfm *cfm) { return CONTAINER_OF(cfm, struct cfm_internal, cfm); } @@ -450,3 +451,40 @@ cfm_process_heartbeat(struct cfm *cfm, const struct ofpbuf *p) } } } + +static void +put_remote_mp(struct ds *ds, const char *header, + const struct remote_mp *rmp) +{ + ds_put_format(ds, "%s %"PRIu16": %s\n", header, rmp->mpid, + rmp->fault ? "fault" : ""); + ds_put_format(ds, "\ttime since CCM rx: %lldms\n", + time_msec() - rmp->recv_time); +} + +void +cfm_dump_ds(const struct cfm *cfm, struct ds *ds) +{ + const struct cfm_internal *cfmi = cfm_to_internal(cfm); + long long int now = time_msec(); + struct remote_mp *rmp; + + ds_put_format(ds, "MPID %"PRIu16": %s\n", cfm->mpid, + cfm->fault ? "fault" : ""); + + ds_put_format(ds, "\tinterval: %dms\n", cfmi->ccm_interval_ms); + ds_put_format(ds, "\ttime since CCM tx: %lldms\n", now - cfmi->ccm_sent); + ds_put_format(ds, "\ttime since fault check: %lldms\n", + now - cfmi->fault_check); + ds_put_format(ds, "\tunexpected remote MAIDS: %s\n", + !hmap_is_empty(&cfmi->x_remote_maids) ? "true" : "false"); + + ds_put_cstr(ds, "\n"); + HMAP_FOR_EACH (rmp, node, &cfm->remote_mps) { + put_remote_mp(ds, "Remote MPID", rmp); + } + + HMAP_FOR_EACH (rmp, node, &cfmi->x_remote_mps) { + put_remote_mp(ds, "Unexpected Remote MPID", rmp); + } +} diff --git a/lib/cfm.h b/lib/cfm.h index e4bb6dff..e8dd3a6b 100644 --- a/lib/cfm.h +++ b/lib/cfm.h @@ -24,6 +24,7 @@ struct flow; struct ofpbuf; +struct ds; /* Ethernet destination address of CCM packets. */ static const uint8_t eth_addr_ccm[6] OVS_UNUSED @@ -106,4 +107,6 @@ bool cfm_should_process_flow(const struct flow *); void cfm_process_heartbeat(struct cfm *, const struct ofpbuf *packet); +void cfm_dump_ds(const struct cfm *, struct ds *); + #endif /* cfm.h */ diff --git a/vswitchd/bridge.c b/vswitchd/bridge.c index fed5d71d..9660aef9 100644 --- a/vswitchd/bridge.c +++ b/vswitchd/bridge.c @@ -267,6 +267,7 @@ static uint64_t bridge_pick_datapath_id(struct bridge *, static uint64_t dpid_from_hash(const void *, size_t nbytes); static unixctl_cb_func bridge_unixctl_fdb_show; +static unixctl_cb_func cfm_unixctl_show; static unixctl_cb_func qos_unixctl_show; static void bond_init(void); @@ -345,6 +346,7 @@ bridge_init(const char *remote) /* Register unixctl commands. */ unixctl_command_register("fdb/show", bridge_unixctl_fdb_show, NULL); + unixctl_command_register("cfm/show", cfm_unixctl_show, NULL); unixctl_command_register("qos/show", qos_unixctl_show, NULL); unixctl_command_register("bridge/dump-flows", bridge_unixctl_dump_flows, NULL); @@ -1515,6 +1517,33 @@ bridge_unixctl_fdb_show(struct unixctl_conn *conn, ds_destroy(&ds); } +/* CFM unixctl user interface functions. */ +static void +cfm_unixctl_show(struct unixctl_conn *conn, + const char *args, void *aux OVS_UNUSED) +{ + struct ds ds = DS_EMPTY_INITIALIZER; + struct iface *iface; + const struct cfm *cfm; + + iface = iface_find(args); + if (!iface) { + unixctl_command_reply(conn, 501, "no such interface"); + return; + } + + cfm = ofproto_iface_get_cfm(iface->port->bridge->ofproto, iface->dp_ifidx); + + if (!cfm) { + unixctl_command_reply(conn, 501, "CFM not enabled"); + return; + } + + cfm_dump_ds(cfm, &ds); + unixctl_command_reply(conn, 200, ds_cstr(&ds)); + ds_destroy(&ds); +} + /* QoS unixctl user interface functions. */ struct qos_unixctl_show_cbdata { diff --git a/vswitchd/ovs-vswitchd.8.in b/vswitchd/ovs-vswitchd.8.in index f62f93f6..4c02f8a4 100644 --- a/vswitchd/ovs-vswitchd.8.in +++ b/vswitchd/ovs-vswitchd.8.in @@ -116,6 +116,9 @@ Causes \fBovs\-vswitchd\fR to gracefully terminate. .IP "\fBqos/show\fR \fIinterface\fR" Queries the kernel for Quality of Service configuration and statistics associated with the given \fIinterface\fR. +.IP "\fBcfm/show\fR \fIinterface\fR" +Displays detailed information about Connectivity Fault Management +configured on \fIinterface\fR. .SS "BRIDGE COMMANDS" These commands manage bridges. .IP "\fBfdb/show\fR \fIbridge\fR"