[ovs-dev] [PATCH 41/63] ofp-util: Allow decoding of Open Flow 1.2 Flow Statistics Response Messages

Simon Horman horms at verge.net.au
Wed Jun 27 08:20:17 UTC 2012


Signed-off-by: Simon Horman <horms at verge.net.au>

---

v5
* Manual rebase
* Use padded_match_len parameter of ofputil_pull_ofp12_match()
  to obtain the length of a match. Using the remaining
  length of the message only works for the last flow.

v4
* Don't explicitly pill the pad of the header of the message.
  This is now handled ofputil_pull_stats_msg()
* Use OFPST11_FLOW as the message code, it already exists and
  seems appropriate as struct ofp11_flow_stats is used.
* Log a warning if match parsing fails
* Log a warning if instruction parsing fails
* Correct length passed to ofpacts_pull_openflow11_instructions()

v3
* Initial post
---
 lib/ofp-util.c | 45 ++++++++++++++++++++++++++++++++++++++++++++-
 1 file changed, 44 insertions(+), 1 deletion(-)

diff --git a/lib/ofp-util.c b/lib/ofp-util.c
index 615e5f5..6b7f4cb 100644
--- a/lib/ofp-util.c
+++ b/lib/ofp-util.c
@@ -962,6 +962,7 @@ static const struct ofputil_msg_type ofputil_msg_types[] = {
     }
     OFPST12_REPLY(OFPST_DESC, OFPST_DESC,
                   sizeof(struct ofp_desc_stats), 0),
+    OFPST12_REPLY(OFPST11_FLOW, OFPST_FLOW, 0, 1),
     OFPST12_REPLY(OFPST_PORT_DESC, OFPST_PORT_DESC,
                   0, sizeof(struct ofp11_port)),
 #undef OFPST12_REPLY
@@ -2184,9 +2185,10 @@ ofputil_decode_flow_stats_reply(struct ofputil_flow_stats *fs,
                                 struct ofpbuf *ofpacts)
 {
     const struct ofputil_msg_type *type;
+    const struct ofp_header *oh = msg->l2 ? msg->l2 : msg->data;
     int code;
 
-    ofputil_decode_msg_type(msg->l2 ? msg->l2 : msg->data, &type);
+    ofputil_decode_msg_type(oh, &type);
     code = ofputil_msg_type_code(type);
     if (!msg->l2) {
         msg->l2 = msg->data;
@@ -2195,6 +2197,47 @@ ofputil_decode_flow_stats_reply(struct ofputil_flow_stats *fs,
 
     if (!msg->size) {
         return EOF;
+    } else if (code == OFPUTIL_OFPST11_FLOW_REPLY) {
+        const struct ofp11_flow_stats *ofs;
+        size_t length;
+        uint16_t padded_match_len;
+
+        ofs = ofpbuf_try_pull(msg, sizeof *ofs);
+        if (!ofs) {
+            VLOG_WARN_RL(&bad_ofmsg_rl, "OFPST_FLOW reply has %zu leftover "
+                         "bytes at end", msg->size);
+            return EINVAL;
+        }
+
+        length = ntohs(ofs->length);
+        if (length < sizeof *ofs) {
+            VLOG_WARN_RL(&bad_ofmsg_rl, "OFPST_FLOW reply claims invalid "
+                         "length %zu", length);
+            return EINVAL;
+        }
+
+        if (ofputil_pull_ofp12_match(msg, ntohs(ofs->priority), &fs->rule,
+                                     NULL, NULL, &padded_match_len)) {
+            VLOG_WARN_RL(&bad_ofmsg_rl, "OFPST_FLOW reply bad match");
+            return EINVAL;
+        }
+
+        if (ofpacts_pull_openflow11_instructions(msg, length - sizeof *ofs -
+                                                 padded_match_len, ofpacts)) {
+            VLOG_WARN_RL(&bad_ofmsg_rl, "OFPST_FLOW reply bad instructions");
+            return EINVAL;
+        }
+
+        fs->table_id = ofs->table_id;
+        fs->duration_sec = ntohl(ofs->duration_sec);
+        fs->duration_nsec = ntohl(ofs->duration_nsec);
+        fs->idle_timeout = ntohs(ofs->idle_timeout);
+        fs->hard_timeout = ntohs(ofs->hard_timeout);
+        fs->idle_age = -1;
+        fs->hard_age = -1;
+        fs->cookie = ofs->cookie;
+        fs->packet_count = ntohll(ofs->packet_count);
+        fs->byte_count = ntohll(ofs->byte_count);
     } else if (code == OFPUTIL_OFPST10_FLOW_REPLY) {
         const struct ofp10_flow_stats *ofs;
         size_t length;
-- 
1.7.10.2.484.gcd07cc5




More information about the dev mailing list