[ovs-dev] [nxm 26/42] ofproto: Make flow format specific to an OpenFlow connection.

Ben Pfaff blp at nicira.com
Thu Oct 28 17:27:57 UTC 2010


Until now the flow format has been a global property of an ofproto.
This is no longer appropriate, because the Nicira Extended Match
flow format that upcoming commits will add is not compatible with
OpenFlow 1.0-only controllers.  This commit changes the flow format
to a property of an individual OpenFlow connection.connection
---
 ofproto/ofproto.c |   55 ++++++++++++++++++++++++++++------------------------
 1 files changed, 30 insertions(+), 25 deletions(-)

diff --git a/ofproto/ofproto.c b/ofproto/ofproto.c
index 509f15a..735b1e0 100644
--- a/ofproto/ofproto.c
+++ b/ofproto/ofproto.c
@@ -210,6 +210,7 @@ struct ofconn {
     struct list node;           /* In struct ofproto's "all_conns" list. */
     struct rconn *rconn;        /* OpenFlow connection. */
     enum ofconn_type type;      /* Type. */
+    int flow_format;            /* One of NXFF_*. */
 
     /* OFPT_PACKET_IN related data. */
     struct rconn_packet_counter *packet_in_counter; /* # queued on 'rconn'. */
@@ -290,7 +291,6 @@ struct ofproto {
     bool need_revalidate;
     long long int next_expiration;
     struct tag_set revalidate_set;
-    int flow_format;            /* One of NXFF_*. */
 
     /* OpenFlow connections. */
     struct hmap controllers;   /* Controller "struct ofconn"s. */
@@ -398,7 +398,6 @@ ofproto_create(const char *datapath, const char *datapath_type,
     p->need_revalidate = false;
     p->next_expiration = time_msec() + 1000;
     tag_set_init(&p->revalidate_set);
-    p->flow_format = NXFF_OPENFLOW10;
 
     /* Initialize OpenFlow connections. */
     list_init(&p->all_conns);
@@ -1637,6 +1636,7 @@ ofconn_create(struct ofproto *p, struct rconn *rconn, enum ofconn_type type)
     list_push_back(&p->all_conns, &ofconn->node);
     ofconn->rconn = rconn;
     ofconn->type = type;
+    ofconn->flow_format = NXFF_OPENFLOW10;
     ofconn->role = NX_ROLE_OTHER;
     ofconn->packet_in_counter = rconn_packet_counter_create ();
     ofconn->pktbuf = NULL;
@@ -3069,7 +3069,7 @@ handle_table_stats_request(struct ofproto *p, struct ofconn *ofconn,
     ots = append_stats_reply(sizeof *ots, ofconn, &msg);
     memset(ots, 0, sizeof *ots);
     strcpy(ots->name, "classifier");
-    ots->wildcards = (p->flow_format == NXFF_OPENFLOW10
+    ots->wildcards = (ofconn->flow_format == NXFF_OPENFLOW10
                       ? htonl(OFPFW_ALL) : htonl(OVSFW_ALL));
     ots->max_entries = htonl(1024 * 1024);
     ots->active_count = htonl(n_rules);
@@ -3227,7 +3227,7 @@ flow_stats_cb(struct cls_rule *rule_, void *cbdata_)
     ofs->table_id = 0;
     ofs->pad = 0;
     flow_to_match(&rule->cr.flow, rule->cr.wc.wildcards,
-                  cbdata->ofproto->flow_format, &ofs->match);
+                  cbdata->ofconn->flow_format, &ofs->match);
     ofs->duration_sec = htonl(sec);
     ofs->duration_nsec = htonl(msec * 1000000);
     ofs->cookie = rule->flow_cookie;
@@ -3267,7 +3267,7 @@ handle_flow_stats_request(struct ofproto *p, struct ofconn *ofconn,
     cbdata.ofconn = ofconn;
     cbdata.out_port = fsr->out_port;
     cbdata.msg = start_stats_reply(osr, 1024);
-    cls_rule_from_match(&fsr->match, 0, p->flow_format, 0, &target);
+    cls_rule_from_match(&fsr->match, 0, ofconn->flow_format, 0, &target);
     classifier_for_each_match(&p->cls, &target,
                               table_id_to_include(fsr->table_id),
                               flow_stats_cb, &cbdata);
@@ -3297,7 +3297,7 @@ flow_stats_ds_cb(struct cls_rule *rule_, void *cbdata_)
 
     query_stats(cbdata->ofproto, rule, &packet_count, &byte_count);
     flow_to_match(&rule->cr.flow, rule->cr.wc.wildcards,
-                  cbdata->ofproto->flow_format, &match);
+                  NXFF_OPENFLOW10, &match);
 
     ds_put_format(results, "duration=%llds, ",
                   (time_msec() - rule->created) / 1000);
@@ -3381,7 +3381,7 @@ handle_aggregate_stats_request(struct ofproto *p, struct ofconn *ofconn,
     cbdata.packet_count = 0;
     cbdata.byte_count = 0;
     cbdata.n_flows = 0;
-    cls_rule_from_match(&asr->match, 0, p->flow_format, 0, &target);
+    cls_rule_from_match(&asr->match, 0, ofconn->flow_format, 0, &target);
     classifier_for_each_match(&p->cls, &target,
                               table_id_to_include(asr->table_id),
                               aggregate_stats_cb, &cbdata);
@@ -3580,7 +3580,7 @@ add_flow(struct ofproto *p, struct ofconn *ofconn,
         struct cls_rule cr;
 
         cls_rule_from_match(&ofm->match, ntohs(ofm->priority),
-                            p->flow_format, ofm->cookie, &cr);
+                            ofconn->flow_format, ofm->cookie, &cr);
         if (classifier_rule_overlaps(&p->cls, &cr)) {
             return ofp_mkerr(OFPET_FLOW_MOD_FAILED, OFPFMFC_OVERLAP);
         }
@@ -3591,7 +3591,7 @@ add_flow(struct ofproto *p, struct ofconn *ofconn,
                        ntohs(ofm->hard_timeout),  ofm->cookie,
                        ofm->flags & htons(OFPFF_SEND_FLOW_REM));
     cls_rule_from_match(&ofm->match, ntohs(ofm->priority),
-                        p->flow_format, ofm->cookie, &rule->cr);
+                        ofconn->flow_format, ofm->cookie, &rule->cr);
 
     error = 0;
     if (ofm->buffer_id != htonl(UINT32_MAX)) {
@@ -3607,12 +3607,13 @@ add_flow(struct ofproto *p, struct ofconn *ofconn,
 }
 
 static struct rule *
-find_flow_strict(struct ofproto *p, const struct ofp_flow_mod *ofm)
+find_flow_strict(struct ofproto *p, struct ofconn *ofconn,
+                 const struct ofp_flow_mod *ofm)
 {
     struct cls_rule target;
 
     cls_rule_from_match(&ofm->match, ntohs(ofm->priority),
-                        p->flow_format, ofm->cookie, &target);
+                        ofconn->flow_format, ofm->cookie, &target);
     return rule_from_cls_rule(classifier_find_rule_exactly(&p->cls, &target));
 }
 
@@ -3671,7 +3672,8 @@ modify_flows_loose(struct ofproto *p, struct ofconn *ofconn,
     cbdata.n_actions = n_actions;
     cbdata.match = NULL;
 
-    cls_rule_from_match(&ofm->match, 0, p->flow_format, ofm->cookie, &target);
+    cls_rule_from_match(&ofm->match, 0, ofconn->flow_format,
+                        ofm->cookie, &target);
 
     classifier_for_each_match(&p->cls, &target, CLS_INC_ALL,
                               modify_flows_cb, &cbdata);
@@ -3695,7 +3697,7 @@ static int
 modify_flow_strict(struct ofproto *p, struct ofconn *ofconn,
                    struct ofp_flow_mod *ofm, size_t n_actions)
 {
-    struct rule *rule = find_flow_strict(p, ofm);
+    struct rule *rule = find_flow_strict(p, ofconn, ofm);
     if (rule && !rule_is_hidden(rule)) {
         modify_flow(p, ofm, n_actions, rule);
         return send_buffered_packet(p, ofconn, rule, ofm);
@@ -3764,7 +3766,8 @@ static void delete_flow(struct ofproto *, struct rule *, ovs_be16 out_port);
 
 /* Implements OFPFC_DELETE. */
 static void
-delete_flows_loose(struct ofproto *p, const struct ofp_flow_mod *ofm)
+delete_flows_loose(struct ofproto *p, struct ofconn *ofconn,
+                   const struct ofp_flow_mod *ofm)
 {
     struct delete_flows_cbdata cbdata;
     struct cls_rule target;
@@ -3772,7 +3775,8 @@ delete_flows_loose(struct ofproto *p, const struct ofp_flow_mod *ofm)
     cbdata.ofproto = p;
     cbdata.out_port = ofm->out_port;
 
-    cls_rule_from_match(&ofm->match, 0, p->flow_format, ofm->cookie, &target);
+    cls_rule_from_match(&ofm->match, 0, ofconn->flow_format,
+                        ofm->cookie, &target);
 
     classifier_for_each_match(&p->cls, &target, CLS_INC_ALL,
                               delete_flows_cb, &cbdata);
@@ -3780,9 +3784,10 @@ delete_flows_loose(struct ofproto *p, const struct ofp_flow_mod *ofm)
 
 /* Implements OFPFC_DELETE_STRICT. */
 static void
-delete_flow_strict(struct ofproto *p, struct ofp_flow_mod *ofm)
+delete_flow_strict(struct ofproto *p, struct ofconn *ofconn,
+                   struct ofp_flow_mod *ofm)
 {
-    struct rule *rule = find_flow_strict(p, ofm);
+    struct rule *rule = find_flow_strict(p, ofconn, ofm);
     if (rule) {
         delete_flow(p, rule, ofm->out_port);
     }
@@ -3887,11 +3892,11 @@ handle_flow_mod(struct ofproto *p, struct ofconn *ofconn,
         return modify_flow_strict(p, ofconn, ofm, n_actions);
 
     case OFPFC_DELETE:
-        delete_flows_loose(p, ofm);
+        delete_flows_loose(p, ofconn, ofm);
         return 0;
 
     case OFPFC_DELETE_STRICT:
-        delete_flow_strict(p, ofm);
+        delete_flow_strict(p, ofconn, ofm);
         return 0;
 
     default:
@@ -3900,7 +3905,7 @@ handle_flow_mod(struct ofproto *p, struct ofconn *ofconn,
 }
 
 static int
-handle_tun_id_from_cookie(struct ofproto *p, struct nxt_tun_id_cookie *msg)
+handle_tun_id_from_cookie(struct ofconn *ofconn, struct nxt_tun_id_cookie *msg)
 {
     int error;
 
@@ -3909,7 +3914,7 @@ handle_tun_id_from_cookie(struct ofproto *p, struct nxt_tun_id_cookie *msg)
         return error;
     }
 
-    p->flow_format = msg->set ? NXFF_TUN_ID_FROM_COOKIE : NXFF_OPENFLOW10;
+    ofconn->flow_format = msg->set ? NXFF_TUN_ID_FROM_COOKIE : NXFF_OPENFLOW10;
     return 0;
 }
 
@@ -3992,7 +3997,7 @@ handle_vendor(struct ofproto *p, struct ofconn *ofconn, void *msg)
                                             msg);
 
     case NXT_TUN_ID_FROM_COOKIE:
-        return handle_tun_id_from_cookie(p, msg);
+        return handle_tun_id_from_cookie(ofconn, msg);
 
     case NXT_ROLE_REQUEST:
         return handle_role_request(p, ofconn, msg);
@@ -4515,7 +4520,7 @@ revalidate_rule(struct ofproto *p, struct rule *rule)
 }
 
 static struct ofpbuf *
-compose_flow_removed(struct ofproto *p, const struct rule *rule,
+compose_flow_removed(struct ofconn *ofconn, const struct rule *rule,
                      long long int now, uint8_t reason)
 {
     struct ofp_flow_removed *ofr;
@@ -4525,7 +4530,7 @@ compose_flow_removed(struct ofproto *p, const struct rule *rule,
     uint32_t msec = tdiff - (sec * 1000);
 
     ofr = make_openflow(sizeof *ofr, OFPT_FLOW_REMOVED, &buf);
-    flow_to_match(&rule->cr.flow, rule->cr.wc.wildcards, p->flow_format,
+    flow_to_match(&rule->cr.flow, rule->cr.wc.wildcards, ofconn->flow_format,
                   &ofr->match);
     ofr->cookie = rule->flow_cookie;
     ofr->priority = htons(rule->cr.priority);
@@ -4563,7 +4568,7 @@ send_flow_removed(struct ofproto *p, struct rule *rule,
             continue;
         }
 
-        msg = compose_flow_removed(p, rule, now, reason);
+        msg = compose_flow_removed(ofconn, rule, now, reason);
         queue_tx(msg, ofconn, ofconn->reply_counter);
     }
 }
-- 
1.7.1





More information about the dev mailing list