summaryrefslogtreecommitdiff
path: root/tests/test-sflow.c
diff options
context:
space:
mode:
authorNeil McKee <neil.mckee@inmon.com>2014-06-27 11:19:59 -0700
committerBen Pfaff <blp@nicira.com>2014-11-11 13:28:40 -0800
commit50b9699fe49b66de64d0d0b1803bb13e95ca2c2e (patch)
tree97b6c4d020511efe85a9f6f6596d6a1e03e26f86 /tests/test-sflow.c
parentafc63bb4bc0692af8bfa16d2a573b8b3bce52895 (diff)
downloadopenvswitch-50b9699fe49b66de64d0d0b1803bb13e95ca2c2e.tar.gz
sflow: Export LAG, PORTNAME, and OPENFLOWPORT information also.
Export standard sFlow LAG, PORTNAME and OPENFLOWPORT structures with each counter-sample. Add unit-test for sFlow-LAG. Adjust other unit-tests to accommodate these new annotations. The sFlow-LAG structures are important for topology discovery, for troubleshooting LAG instability, and for correctly combining sFlow feeds from multiple sources. The OPENFLOWPORT and PORTNAME structures are important for systems that aim to combine sFlow monitoring with OpenFlow controls, as they provide straightforward mapping (1) between sFlow agent IP and OpenFlow datapath-id, and (2) between interface name,ifIndex and OpenFlow port number. Signed-off-by: Neil McKee <neil.mckee@inmon.com> Signed-off-by: Ben Pfaff <blp@nicira.com>
Diffstat (limited to 'tests/test-sflow.c')
-rw-r--r--tests/test-sflow.c138
1 files changed, 138 insertions, 0 deletions
diff --git a/tests/test-sflow.c b/tests/test-sflow.c
index c84a9fa12..c37288f7e 100644
--- a/tests/test-sflow.c
+++ b/tests/test-sflow.c
@@ -54,8 +54,18 @@ static unixctl_cb_func test_sflow_exit;
/* Structure element tag numbers. */
#define SFLOW_TAG_CTR_IFCOUNTERS 1
+#define SFLOW_TAG_CTR_LACPCOUNTERS 7
+#define SFLOW_TAG_CTR_OPENFLOWPORT 1004
+#define SFLOW_TAG_CTR_PORTNAME 1005
#define SFLOW_TAG_PKT_HEADER 1
#define SFLOW_TAG_PKT_SWITCH 1001
+#define SFLOW_TAG_PKT_TUNNEL4_OUT 1023
+#define SFLOW_TAG_PKT_TUNNEL4_IN 1024
+#define SFLOW_TAG_PKT_TUNNEL_VNI_OUT 1029
+#define SFLOW_TAG_PKT_TUNNEL_VNI_IN 1030
+
+/* string sizes */
+#define SFL_MAX_PORTNAME_LEN 255
struct sflow_addr {
enum {
@@ -99,7 +109,14 @@ struct sflow_xdr {
struct {
uint32_t HEADER;
uint32_t SWITCH;
+ uint32_t TUNNEL4_OUT;
+ uint32_t TUNNEL4_IN;
+ uint32_t TUNNEL_VNI_OUT;
+ uint32_t TUNNEL_VNI_IN;
uint32_t IFCOUNTERS;
+ uint32_t LACPCOUNTERS;
+ uint32_t OPENFLOWPORT;
+ uint32_t PORTNAME;
} offset;
/* Flow sample fields. */
@@ -221,6 +238,63 @@ process_counter_sample(struct sflow_xdr *x)
printf(" promiscuous=%"PRIu32, sflowxdr_next(x));
printf("\n");
}
+ if (x->offset.LACPCOUNTERS) {
+ uint8_t *mac;
+ union {
+ ovs_be32 all;
+ struct {
+ uint8_t actorAdmin;
+ uint8_t actorOper;
+ uint8_t partnerAdmin;
+ uint8_t partnerOper;
+ } v;
+ } state;
+
+ sflowxdr_setc(x, x->offset.LACPCOUNTERS);
+ printf("LACPCOUNTERS");
+ mac = (uint8_t *)sflowxdr_str(x);
+ printf(" sysID="ETH_ADDR_FMT, ETH_ADDR_ARGS(mac));
+ sflowxdr_skip(x, 2);
+ mac = (uint8_t *)sflowxdr_str(x);
+ printf(" partnerID="ETH_ADDR_FMT, ETH_ADDR_ARGS(mac));
+ sflowxdr_skip(x, 2);
+ printf(" aggID=%"PRIu32, sflowxdr_next(x));
+ state.all = sflowxdr_next_n(x);
+ printf(" actorAdmin=0x%"PRIx32, state.v.actorAdmin);
+ printf(" actorOper=0x%"PRIx32, state.v.actorOper);
+ printf(" partnerAdmin=0x%"PRIx32, state.v.partnerAdmin);
+ printf(" partnerOper=0x%"PRIx32, state.v.partnerOper);
+ printf(" LACPUDsRx=%"PRIu32, sflowxdr_next(x));
+ printf(" markerPDUsRx=%"PRIu32, sflowxdr_next(x));
+ printf(" markerRespPDUsRx=%"PRIu32, sflowxdr_next(x));
+ printf(" unknownRx=%"PRIu32, sflowxdr_next(x));
+ printf(" illegalRx=%"PRIu32, sflowxdr_next(x));
+ printf(" LACPUDsTx=%"PRIu32, sflowxdr_next(x));
+ printf(" markerPDUsTx=%"PRIu32, sflowxdr_next(x));
+ printf(" markerRespPDUsTx=%"PRIu32, sflowxdr_next(x));
+ printf("\n");
+ }
+ if (x->offset.OPENFLOWPORT) {
+ sflowxdr_setc(x, x->offset.OPENFLOWPORT);
+ printf("OPENFLOWPORT");
+ printf(" datapath_id=%"PRIu64, sflowxdr_next_int64(x));
+ printf(" port_no=%"PRIu32, sflowxdr_next(x));
+ printf("\n");
+ }
+ if (x->offset.PORTNAME) {
+ uint32_t pnLen;
+ const char *pnBytes;
+ char portName[SFL_MAX_PORTNAME_LEN + 1];
+ sflowxdr_setc(x, x->offset.PORTNAME);
+ printf("PORTNAME");
+ pnLen = sflowxdr_next(x);
+ SFLOWXDR_assert(x, (pnLen <= SFL_MAX_PORTNAME_LEN));
+ pnBytes = sflowxdr_str(x);
+ memcpy(portName, pnBytes, pnLen);
+ portName[pnLen] = '\0';
+ printf(" portName=%s", portName);
+ printf("\n");
+ }
}
static char
@@ -251,6 +325,25 @@ print_hex(const char *a, int len, char *buf, int bufLen)
return b;
}
+static void
+print_struct_ipv4(struct sflow_xdr *x, const char *prefix)
+{
+ ovs_be32 src, dst;
+
+ printf(" %s_length=%"PRIu32, prefix, sflowxdr_next(x));
+ printf(" %s_protocol=%"PRIu32, prefix, sflowxdr_next(x));
+
+ src = sflowxdr_next_n(x);
+ dst = sflowxdr_next_n(x);
+ printf(" %s_src="IP_FMT, prefix, IP_ARGS(src));
+ printf(" %s_dst="IP_FMT, prefix, IP_ARGS(dst));
+
+ printf(" %s_src_port=%"PRIu32, prefix, sflowxdr_next(x));
+ printf(" %s_dst_port=%"PRIu32, prefix, sflowxdr_next(x));
+ printf(" %s_tcp_flags=%"PRIu32, prefix, sflowxdr_next(x));
+ printf(" %s_tos=%"PRIu32, prefix, sflowxdr_next(x));
+}
+
#define SFLOW_HEX_SCRATCH 1024
static void
@@ -266,6 +359,26 @@ process_flow_sample(struct sflow_xdr *x)
x->agentIPStr, x->dsClass, x->dsIndex);
printf(" fsSeqNo=%"PRIu32, x->fsSeqNo);
+ if (x->offset.TUNNEL4_IN) {
+ sflowxdr_setc(x, x->offset.TUNNEL4_IN);
+ print_struct_ipv4(x, "tunnel4_in");
+ }
+
+ if (x->offset.TUNNEL4_OUT) {
+ sflowxdr_setc(x, x->offset.TUNNEL4_OUT);
+ print_struct_ipv4(x, "tunnel4_out");
+ }
+
+ if (x->offset.TUNNEL_VNI_IN) {
+ sflowxdr_setc(x, x->offset.TUNNEL_VNI_IN);
+ printf( " tunnel_in_vni=%"PRIu32, sflowxdr_next(x));
+ }
+
+ if (x->offset.TUNNEL_VNI_OUT) {
+ sflowxdr_setc(x, x->offset.TUNNEL_VNI_OUT);
+ printf( " tunnel_out_vni=%"PRIu32, sflowxdr_next(x));
+ }
+
if (x->offset.SWITCH) {
sflowxdr_setc(x, x->offset.SWITCH);
printf(" in_vlan=%"PRIu32, sflowxdr_next(x));
@@ -372,6 +485,15 @@ process_datagram(struct sflow_xdr *x)
case SFLOW_TAG_CTR_IFCOUNTERS:
sflowxdr_mark_unique(x, &x->offset.IFCOUNTERS);
break;
+ case SFLOW_TAG_CTR_LACPCOUNTERS:
+ sflowxdr_mark_unique(x, &x->offset.LACPCOUNTERS);
+ break;
+ case SFLOW_TAG_CTR_PORTNAME:
+ sflowxdr_mark_unique(x, &x->offset.PORTNAME);
+ break;
+ case SFLOW_TAG_CTR_OPENFLOWPORT:
+ sflowxdr_mark_unique(x, &x->offset.OPENFLOWPORT);
+ break;
/* Add others here... */
}
@@ -440,6 +562,22 @@ process_datagram(struct sflow_xdr *x)
sflowxdr_mark_unique(x, &x->offset.SWITCH);
break;
+ case SFLOW_TAG_PKT_TUNNEL4_OUT:
+ sflowxdr_mark_unique(x, &x->offset.TUNNEL4_OUT);
+ break;
+
+ case SFLOW_TAG_PKT_TUNNEL4_IN:
+ sflowxdr_mark_unique(x, &x->offset.TUNNEL4_IN);
+ break;
+
+ case SFLOW_TAG_PKT_TUNNEL_VNI_OUT:
+ sflowxdr_mark_unique(x, &x->offset.TUNNEL_VNI_OUT);
+ break;
+
+ case SFLOW_TAG_PKT_TUNNEL_VNI_IN:
+ sflowxdr_mark_unique(x, &x->offset.TUNNEL_VNI_IN);
+ break;
+
/* Add others here... */
}