X-Git-Url: https://git.tcpdump.org/tcpdump/blobdiff_plain/c1c3c77463d592cc576eaa491e604752044ca55a..568927a2bce300035cf25e9cd387986f4a72b10c:/print-openflow-1.0.c diff --git a/print-openflow-1.0.c b/print-openflow-1.0.c index 8cfc00c3..e50c06e6 100644 --- a/print-openflow-1.0.c +++ b/print-openflow-1.0.c @@ -14,7 +14,7 @@ * * ep -- the pointer to the end of the captured frame * They return either the pointer to the next not-yet-decoded part of the frame * or the value of ep, which means the current frame processing is over as it - * has been fully decoded or is malformed or truncated. This way it is possible + * has been fully decoded or is invalid or truncated. This way it is possible * to chain and nest such functions uniformly to decode an OF1.0 message, which * consists of several layers of nested structures. * @@ -56,11 +56,13 @@ * POSSIBILITY OF SUCH DAMAGE. */ +/* \summary: OpenFlow protocol version 1.0 printer */ + #ifdef HAVE_CONFIG_H #include "config.h" #endif -#include +#include #include "netdissect.h" #include "extract.h" @@ -72,7 +74,6 @@ #include "openflow.h" static const char tstr[] = " [|openflow]"; -static const char cstr[] = " (corrupt)"; #define OFPT_HELLO 0x00 #define OFPT_ERROR 0x01 @@ -122,13 +123,13 @@ static const struct tok ofpt_str[] = { { 0, NULL } }; -#define OFPPC_PORT_DOWN (1 << 0) -#define OFPPC_NO_STP (1 << 1) -#define OFPPC_NO_RECV (1 << 2) -#define OFPPC_NO_RECV_STP (1 << 3) -#define OFPPC_NO_FLOOD (1 << 4) -#define OFPPC_NO_FWD (1 << 5) -#define OFPPC_NO_PACKET_IN (1 << 6) +#define OFPPC_PORT_DOWN (1U <<0) +#define OFPPC_NO_STP (1U <<1) +#define OFPPC_NO_RECV (1U <<2) +#define OFPPC_NO_RECV_STP (1U <<3) +#define OFPPC_NO_FLOOD (1U <<4) +#define OFPPC_NO_FWD (1U <<5) +#define OFPPC_NO_PACKET_IN (1U <<6) static const struct tok ofppc_bm[] = { { OFPPC_PORT_DOWN, "PORT_DOWN" }, { OFPPC_NO_STP, "NO_STP" }, @@ -143,12 +144,12 @@ static const struct tok ofppc_bm[] = { OFPPC_NO_RECV_STP | OFPPC_NO_FLOOD | OFPPC_NO_FWD | \ OFPPC_NO_PACKET_IN)) -#define OFPPS_LINK_DOWN (1 << 0) -#define OFPPS_STP_LISTEN (0 << 8) -#define OFPPS_STP_LEARN (1 << 8) -#define OFPPS_STP_FORWARD (2 << 8) -#define OFPPS_STP_BLOCK (3 << 8) -#define OFPPS_STP_MASK (3 << 8) +#define OFPPS_LINK_DOWN (1U << 0) +#define OFPPS_STP_LISTEN (0U << 8) +#define OFPPS_STP_LEARN (1U << 8) +#define OFPPS_STP_FORWARD (2U << 8) +#define OFPPS_STP_BLOCK (3U << 8) +#define OFPPS_STP_MASK (3U << 8) static const struct tok ofpps_bm[] = { { OFPPS_LINK_DOWN, "LINK_DOWN" }, { OFPPS_STP_LISTEN, "STP_LISTEN" }, @@ -160,15 +161,15 @@ static const struct tok ofpps_bm[] = { #define OFPPS_U (~(OFPPS_LINK_DOWN | OFPPS_STP_LISTEN | OFPPS_STP_LEARN | \ OFPPS_STP_FORWARD | OFPPS_STP_BLOCK)) -#define OFPP_MAX 0xff00 -#define OFPP_IN_PORT 0xfff8 -#define OFPP_TABLE 0xfff9 -#define OFPP_NORMAL 0xfffa -#define OFPP_FLOOD 0xfffb -#define OFPP_ALL 0xfffc -#define OFPP_CONTROLLER 0xfffd -#define OFPP_LOCAL 0xfffe -#define OFPP_NONE 0xffff +#define OFPP_MAX 0xff00U +#define OFPP_IN_PORT 0xfff8U +#define OFPP_TABLE 0xfff9U +#define OFPP_NORMAL 0xfffaU +#define OFPP_FLOOD 0xfffbU +#define OFPP_ALL 0xfffcU +#define OFPP_CONTROLLER 0xfffdU +#define OFPP_LOCAL 0xfffeU +#define OFPP_NONE 0xffffU static const struct tok ofpp_str[] = { { OFPP_MAX, "MAX" }, { OFPP_IN_PORT, "IN_PORT" }, @@ -182,18 +183,18 @@ static const struct tok ofpp_str[] = { { 0, NULL } }; -#define OFPPF_10MB_HD (1 << 0) -#define OFPPF_10MB_FD (1 << 1) -#define OFPPF_100MB_HD (1 << 2) -#define OFPPF_100MB_FD (1 << 3) -#define OFPPF_1GB_HD (1 << 4) -#define OFPPF_1GB_FD (1 << 5) -#define OFPPF_10GB_FD (1 << 6) -#define OFPPF_COPPER (1 << 7) -#define OFPPF_FIBER (1 << 8) -#define OFPPF_AUTONEG (1 << 9) -#define OFPPF_PAUSE (1 << 10) -#define OFPPF_PAUSE_ASYM (1 << 11) +#define OFPPF_10MB_HD (1U << 0) +#define OFPPF_10MB_FD (1U << 1) +#define OFPPF_100MB_HD (1U << 2) +#define OFPPF_100MB_FD (1U << 3) +#define OFPPF_1GB_HD (1U << 4) +#define OFPPF_1GB_FD (1U << 5) +#define OFPPF_10GB_FD (1U << 6) +#define OFPPF_COPPER (1U << 7) +#define OFPPF_FIBER (1U << 8) +#define OFPPF_AUTONEG (1U << 9) +#define OFPPF_PAUSE (1U <<10) +#define OFPPF_PAUSE_ASYM (1U <<11) static const struct tok ofppf_bm[] = { { OFPPF_10MB_HD, "10MB_HD" }, { OFPPF_10MB_FD, "10MB_FD" }, @@ -222,23 +223,23 @@ static const struct tok ofpqt_str[] = { { 0, NULL } }; -#define OFPFW_IN_PORT (1 << 0) -#define OFPFW_DL_VLAN (1 << 1) -#define OFPFW_DL_SRC (1 << 2) -#define OFPFW_DL_DST (1 << 3) -#define OFPFW_DL_TYPE (1 << 4) -#define OFPFW_NW_PROTO (1 << 5) -#define OFPFW_TP_SRC (1 << 6) -#define OFPFW_TP_DST (1 << 7) +#define OFPFW_IN_PORT (1U <<0) +#define OFPFW_DL_VLAN (1U <<1) +#define OFPFW_DL_SRC (1U <<2) +#define OFPFW_DL_DST (1U <<3) +#define OFPFW_DL_TYPE (1U <<4) +#define OFPFW_NW_PROTO (1U <<5) +#define OFPFW_TP_SRC (1U <<6) +#define OFPFW_TP_DST (1U <<7) #define OFPFW_NW_SRC_SHIFT 8 #define OFPFW_NW_SRC_BITS 6 -#define OFPFW_NW_SRC_MASK (((1 << OFPFW_NW_SRC_BITS) - 1) << OFPFW_NW_SRC_SHIFT) +#define OFPFW_NW_SRC_MASK (((1U < len) - goto corrupt; + goto invalid; /* pad */ ND_TCHECK2(*cp, 4); cp += 4; @@ -1278,8 +1279,8 @@ next_property: } /* while */ return cp; -corrupt: /* skip the rest of queue properties */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the rest of queue properties */ + ND_PRINT((ndo, "%s", istr)); ND_TCHECK2(*cp0, len0); return cp0 + len0; trunc: @@ -1298,7 +1299,7 @@ of10_queues_print(netdissect_options *ndo, while (len) { if (len < OF_PACKET_QUEUE_LEN) - goto corrupt; + goto invalid; /* queue_id */ ND_TCHECK2(*cp, 4); ND_PRINT((ndo, "\n\t queue_id %u", EXTRACT_32BITS(cp))); @@ -1309,7 +1310,7 @@ of10_queues_print(netdissect_options *ndo, cp += 2; ND_PRINT((ndo, ", len %u", desclen)); if (desclen < OF_PACKET_QUEUE_LEN || desclen > len) - goto corrupt; + goto invalid; /* pad */ ND_TCHECK2(*cp, 2); cp += 2; @@ -1326,8 +1327,8 @@ next_queue: } /* while */ return cp; -corrupt: /* skip the rest of queues */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the rest of queues */ + ND_PRINT((ndo, "%s", istr)); ND_TCHECK2(*cp0, len0); return cp0 + len0; trunc: @@ -1453,7 +1454,7 @@ of10_actions_print(netdissect_options *ndo, u_char alen_bogus = 0, skip = 0; if (len < OF_ACTION_HEADER_LEN) - goto corrupt; + goto invalid; /* type */ ND_TCHECK2(*cp, 2); type = EXTRACT_16BITS(cp); @@ -1466,7 +1467,7 @@ of10_actions_print(netdissect_options *ndo, ND_PRINT((ndo, ", len %u", alen)); /* On action size underrun/overrun skip the rest of the action list. */ if (alen < OF_ACTION_HEADER_LEN || alen > len) - goto corrupt; + goto invalid; /* On action size inappropriate for the given type or invalid type just skip * the current action, as the basic length constraint has been met. */ switch (type) { @@ -1597,8 +1598,8 @@ next_action: } /* while */ return cp; -corrupt: /* skip the rest of actions */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the rest of actions */ + ND_PRINT((ndo, "%s", istr)); ND_TCHECK2(*cp0, len0); return cp0 + len0; trunc: @@ -1765,12 +1766,12 @@ of10_stats_request_print(netdissect_options *ndo, case OFPST_DESC: case OFPST_TABLE: if (len) - goto corrupt; + goto invalid; return cp; case OFPST_FLOW: case OFPST_AGGREGATE: if (len != OF_FLOW_STATS_REQUEST_LEN) - goto corrupt; + goto invalid; /* match */ if (ep == (cp = of10_match_print(ndo, "\n\t ", cp, ep))) return ep; /* end of snapshot */ @@ -1787,7 +1788,7 @@ of10_stats_request_print(netdissect_options *ndo, return cp + 2; case OFPST_PORT: if (len != OF_PORT_STATS_REQUEST_LEN) - goto corrupt; + goto invalid; /* port_no */ ND_TCHECK2(*cp, 2); ND_PRINT((ndo, "\n\t port_no %s", tok2str(ofpp_str, "%u", EXTRACT_16BITS(cp)))); @@ -1797,7 +1798,7 @@ of10_stats_request_print(netdissect_options *ndo, return cp + 6; case OFPST_QUEUE: if (len != OF_QUEUE_STATS_REQUEST_LEN) - goto corrupt; + goto invalid; /* port_no */ ND_TCHECK2(*cp, 2); ND_PRINT((ndo, "\n\t port_no %s", tok2str(ofpp_str, "%u", EXTRACT_16BITS(cp)))); @@ -1814,8 +1815,8 @@ of10_stats_request_print(netdissect_options *ndo, } return cp; -corrupt: /* skip the message body */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the message body */ + ND_PRINT((ndo, "%s", istr)); ND_TCHECK2(*cp0, len0); return cp0 + len0; trunc: @@ -1829,7 +1830,7 @@ of10_desc_stats_reply_print(netdissect_options *ndo, const u_char *cp, const u_char *ep, const u_int len) { if (len != OF_DESC_STATS_LEN) - goto corrupt; + goto invalid; /* mfr_desc */ ND_TCHECK2(*cp, DESC_STR_LEN); ND_PRINT((ndo, "\n\t mfr_desc '")); @@ -1861,8 +1862,8 @@ of10_desc_stats_reply_print(netdissect_options *ndo, ND_PRINT((ndo, "'")); return cp + DESC_STR_LEN; -corrupt: /* skip the message body */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the message body */ + ND_PRINT((ndo, "%s", istr)); ND_TCHECK2(*cp, len); return cp + len; trunc: @@ -1881,13 +1882,13 @@ of10_flow_stats_reply_print(netdissect_options *ndo, while (len) { if (len < OF_FLOW_STATS_LEN) - goto corrupt; + goto invalid; /* length */ ND_TCHECK2(*cp, 2); entry_len = EXTRACT_16BITS(cp); ND_PRINT((ndo, "\n\t length %u", entry_len)); if (entry_len < OF_FLOW_STATS_LEN || entry_len > len) - goto corrupt; + goto invalid; cp += 2; /* table_id */ ND_TCHECK2(*cp, 1); @@ -1942,8 +1943,8 @@ of10_flow_stats_reply_print(netdissect_options *ndo, } /* while */ return cp; -corrupt: /* skip the rest of flow statistics entries */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the rest of flow statistics entries */ + ND_PRINT((ndo, "%s", istr)); ND_TCHECK2(*cp0, len0); return cp0 + len0; trunc: @@ -1958,7 +1959,7 @@ of10_aggregate_stats_reply_print(netdissect_options *ndo, const u_int len) { if (len != OF_AGGREGATE_STATS_REPLY_LEN) - goto corrupt; + goto invalid; /* packet_count */ ND_TCHECK2(*cp, 8); ND_PRINT((ndo, "\n\t packet_count %" PRIu64, EXTRACT_64BITS(cp))); @@ -1975,8 +1976,8 @@ of10_aggregate_stats_reply_print(netdissect_options *ndo, ND_TCHECK2(*cp, 4); return cp + 4; -corrupt: /* skip the message body */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the message body */ + ND_PRINT((ndo, "%s", istr)); ND_TCHECK2(*cp, len); return cp + len; trunc: @@ -1994,7 +1995,7 @@ of10_table_stats_reply_print(netdissect_options *ndo, while (len) { if (len < OF_TABLE_STATS_LEN) - goto corrupt; + goto invalid; /* table_id */ ND_TCHECK2(*cp, 1); ND_PRINT((ndo, "\n\t table_id %s", tok2str(tableid_str, "%u", *cp))); @@ -2034,8 +2035,8 @@ of10_table_stats_reply_print(netdissect_options *ndo, } /* while */ return cp; -corrupt: /* skip the undersized trailing data */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the undersized trailing data */ + ND_PRINT((ndo, "%s", istr)); ND_TCHECK2(*cp0, len0); return cp0 + len0; trunc: @@ -2053,7 +2054,7 @@ of10_port_stats_reply_print(netdissect_options *ndo, while (len) { if (len < OF_PORT_STATS_LEN) - goto corrupt; + goto invalid; /* port_no */ ND_TCHECK2(*cp, 2); ND_PRINT((ndo, "\n\t port_no %s", tok2str(ofpp_str, "%u", EXTRACT_16BITS(cp)))); @@ -2119,8 +2120,8 @@ next_port: } /* while */ return cp; -corrupt: /* skip the undersized trailing data */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the undersized trailing data */ + ND_PRINT((ndo, "%s", istr)); ND_TCHECK2(*cp0, len0); return cp0 + len0; trunc: @@ -2138,7 +2139,7 @@ of10_queue_stats_reply_print(netdissect_options *ndo, while (len) { if (len < OF_QUEUE_STATS_LEN) - goto corrupt; + goto invalid; /* port_no */ ND_TCHECK2(*cp, 2); ND_PRINT((ndo, "\n\t port_no %s", tok2str(ofpp_str, "%u", EXTRACT_16BITS(cp)))); @@ -2167,8 +2168,8 @@ of10_queue_stats_reply_print(netdissect_options *ndo, } /* while */ return cp; -corrupt: /* skip the undersized trailing data */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the undersized trailing data */ + ND_PRINT((ndo, "%s", istr)); ND_TCHECK2(*cp0, len0); return cp0 + len0; trunc: @@ -2238,15 +2239,15 @@ of10_packet_out_print(netdissect_options *ndo, actions_len = EXTRACT_16BITS(cp); cp += 2; if (actions_len > len - OF_PACKET_OUT_LEN) - goto corrupt; + goto invalid; /* actions */ if (ep == (cp = of10_actions_print(ndo, "\n\t ", cp, ep, actions_len))) return ep; /* end of snapshot */ /* data */ return of10_packet_data_print(ndo, cp, ep, len - OF_PACKET_OUT_LEN - actions_len); -corrupt: /* skip the rest of the message body */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the rest of the message body */ + ND_PRINT((ndo, "%s", istr)); ND_TCHECK2(*cp0, len0); return cp0 + len0; trunc: @@ -2386,7 +2387,7 @@ of10_header_body_print(netdissect_options *ndo, * possible, check that message length meets the constraint, in remaining * cases check that the length is OK to begin decoding and leave any final * verification up to a lower-layer function. When the current message is - * corrupt, proceed to the next message. */ + * invalid, proceed to the next message. */ /* [OF10] Section 5.1 */ ND_PRINT((ndo, "\n\tversion 1.0, type %s, length %u, xid 0x%08x", @@ -2398,14 +2399,14 @@ of10_header_body_print(netdissect_options *ndo, case OFPT_BARRIER_REQUEST: /* [OF10] Section 5.3.7 */ case OFPT_BARRIER_REPLY: /* ibid */ if (len != OF_HEADER_LEN) - goto corrupt; + goto invalid; break; /* OpenFlow header and fixed-size message body. */ case OFPT_SET_CONFIG: /* [OF10] Section 5.3.2 */ case OFPT_GET_CONFIG_REPLY: /* ibid */ if (len != OF_SWITCH_CONFIG_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; /* flags */ @@ -2418,13 +2419,13 @@ of10_header_body_print(netdissect_options *ndo, return cp + 2; case OFPT_PORT_MOD: if (len != OF_PORT_MOD_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; return of10_port_mod_print(ndo, cp, ep); case OFPT_QUEUE_GET_CONFIG_REQUEST: /* [OF10] Section 5.3.4 */ if (len != OF_QUEUE_GET_CONFIG_REQUEST_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; /* port */ @@ -2436,13 +2437,13 @@ of10_header_body_print(netdissect_options *ndo, return cp + 2; case OFPT_FLOW_REMOVED: if (len != OF_FLOW_REMOVED_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; return of10_flow_removed_print(ndo, cp, ep); case OFPT_PORT_STATUS: /* [OF10] Section 5.4.3 */ if (len != OF_PORT_STATUS_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; /* reason */ @@ -2458,7 +2459,7 @@ of10_header_body_print(netdissect_options *ndo, /* OpenFlow header, fixed-size message body and n * fixed-size data units. */ case OFPT_FEATURES_REPLY: if (len < OF_SWITCH_FEATURES_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; return of10_features_reply_print(ndo, cp, ep, len); @@ -2474,21 +2475,21 @@ of10_header_body_print(netdissect_options *ndo, /* OpenFlow header, fixed-size message body and variable-size data. */ case OFPT_ERROR: if (len < OF_ERROR_MSG_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; return of10_error_print(ndo, cp, ep, len); case OFPT_VENDOR: /* [OF10] Section 5.5.4 */ if (len < OF_VENDOR_HEADER_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; return of10_vendor_message_print(ndo, cp, ep, len - OF_HEADER_LEN); case OFPT_PACKET_IN: /* 2 mock octets count in OF_PACKET_IN_LEN but not in len */ if (len < OF_PACKET_IN_LEN - 2) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; return of10_packet_in_print(ndo, cp, ep, len); @@ -2498,7 +2499,7 @@ of10_header_body_print(netdissect_options *ndo, /* c. OpenFlow header, fixed-size message body and variable-size data. */ case OFPT_STATS_REQUEST: if (len < OF_STATS_REQUEST_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; return of10_stats_request_print(ndo, cp, ep, len); @@ -2509,7 +2510,7 @@ of10_header_body_print(netdissect_options *ndo, /* d. OpenFlow header, fixed-size message body and variable-size data. */ case OFPT_STATS_REPLY: if (len < OF_STATS_REPLY_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; return of10_stats_reply_print(ndo, cp, ep, len); @@ -2517,7 +2518,7 @@ of10_header_body_print(netdissect_options *ndo, /* OpenFlow header and n * variable-size data units and variable-size data. */ case OFPT_PACKET_OUT: if (len < OF_PACKET_OUT_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; return of10_packet_out_print(ndo, cp, ep, len); @@ -2525,7 +2526,7 @@ of10_header_body_print(netdissect_options *ndo, /* OpenFlow header, fixed-size message body and n * variable-size data units. */ case OFPT_FLOW_MOD: if (len < OF_FLOW_MOD_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; return of10_flow_mod_print(ndo, cp, ep, len); @@ -2533,7 +2534,7 @@ of10_header_body_print(netdissect_options *ndo, /* OpenFlow header, fixed-size message body and n * variable-size data units. */ case OFPT_QUEUE_GET_CONFIG_REPLY: /* [OF10] Section 5.3.4 */ if (len < OF_QUEUE_GET_CONFIG_REPLY_LEN) - goto corrupt; + goto invalid; if (ndo->ndo_vflag < 1) goto next_message; /* port */ @@ -2548,8 +2549,8 @@ of10_header_body_print(netdissect_options *ndo, } /* switch (type) */ goto next_message; -corrupt: /* skip the message body */ - ND_PRINT((ndo, "%s", cstr)); +invalid: /* skip the message body */ + ND_PRINT((ndo, "%s", istr)); next_message: ND_TCHECK2(*cp0, len0 - OF_HEADER_LEN); return cp0 + len0 - OF_HEADER_LEN;