update sliver-ovs to new ovsdb syntax
[sliver-openvswitch.git] / ofproto / ofproto-dpif.c
index f8a1912..2d42c83 100644 (file)
@@ -404,6 +404,10 @@ static void update_moving_averages(struct dpif_backer *backer);
  * for debugging the asynchronous flow_mod implementation.) */
 static bool clogged;
 
+/* By default, flows in the datapath are wildcarded (megaflows).  They
+ * may be disabled with the "ovs-appctl dpif/disable-megaflows" command. */
+static bool enable_megaflows = true;
+
 /* All existing ofproto_dpif instances, indexed by ->up.name. */
 static struct hmap all_ofproto_dpifs = HMAP_INITIALIZER(&all_ofproto_dpifs);
 
@@ -932,7 +936,7 @@ open_dpif_backer(const char *type, struct dpif_backer **backerp)
     free(backer_name);
     if (error) {
         VLOG_ERR("failed to open datapath of type %s: %s", type,
-                 strerror(error));
+                 ovs_strerror(error));
         free(backer);
         return error;
     }
@@ -979,7 +983,7 @@ open_dpif_backer(const char *type, struct dpif_backer **backerp)
     error = dpif_recv_set(backer->dpif, backer->recv_set_enable);
     if (error) {
         VLOG_ERR("failed to listen on datapath of type %s: %s",
-                 type, strerror(error));
+                 type, ovs_strerror(error));
         close_dpif_backer(backer);
         return error;
     }
@@ -2472,7 +2476,7 @@ send_pdu_cb(void *port_, const void *pdu, size_t pdu_size)
     } else {
         VLOG_ERR_RL(&rl, "port %s: cannot obtain Ethernet address of iface "
                     "%s (%s)", port->bundle->name,
-                    netdev_get_name(port->up.netdev), strerror(error));
+                    netdev_get_name(port->up.netdev), ovs_strerror(error));
     }
 }
 
@@ -2511,7 +2515,7 @@ bundle_send_learning_packets(struct ofbundle *bundle)
         static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(1, 5);
         VLOG_WARN_RL(&rl, "bond %s: %d errors sending %d gratuitous learning "
                      "packets, last error was: %s",
-                     bundle->name, n_errors, n_packets, strerror(error));
+                     bundle->name, n_errors, n_packets, ovs_strerror(error));
     } else {
         VLOG_DBG("bond %s: sent %d gratuitous learning packets",
                  bundle->name, n_packets);
@@ -3476,8 +3480,10 @@ handle_flow_miss_with_facet(struct flow_miss *miss, struct facet *facet,
         subfacet->path = want_path;
 
         ofpbuf_use_stack(&op->mask, &op->maskbuf, sizeof op->maskbuf);
-        odp_flow_key_from_mask(&op->mask, &facet->xout.wc.masks,
-                               &miss->flow, UINT32_MAX);
+        if (enable_megaflows) {
+            odp_flow_key_from_mask(&op->mask, &facet->xout.wc.masks,
+                                   &miss->flow, UINT32_MAX);
+        }
 
         op->xout_garbage = false;
         op->dpif_op.type = DPIF_OP_FLOW_PUT;
@@ -3587,8 +3593,8 @@ drop_key_clear(struct dpif_backer *backer)
         if (error && !VLOG_DROP_WARN(&rl)) {
             struct ds ds = DS_EMPTY_INITIALIZER;
             odp_flow_key_format(drop_key->key, drop_key->key_len, &ds);
-            VLOG_WARN("Failed to delete drop key (%s) (%s)", strerror(error),
-                      ds_cstr(&ds));
+            VLOG_WARN("Failed to delete drop key (%s) (%s)",
+                      ovs_strerror(error), ds_cstr(&ds));
             ds_destroy(&ds);
         }
 
@@ -5064,8 +5070,10 @@ subfacet_install(struct subfacet *subfacet, const struct ofpbuf *odp_actions,
     }
 
     ofpbuf_use_stack(&mask, &maskbuf, sizeof maskbuf);
-    odp_flow_key_from_mask(&mask, &facet->xout.wc.masks,
-                           &facet->flow, UINT32_MAX);
+    if (enable_megaflows) {
+        odp_flow_key_from_mask(&mask, &facet->xout.wc.masks,
+                               &facet->flow, UINT32_MAX);
+    }
 
     ret = dpif_flow_put(subfacet->backer->dpif, flags, subfacet->key,
                         subfacet->key_len,  mask.data, mask.size,
@@ -5414,7 +5422,7 @@ send_packet(const struct ofport_dpif *ofport, struct ofpbuf *packet)
     if (error) {
         VLOG_WARN_RL(&rl, "%s: failed to send packet on port %s (%s)",
                      ofproto->up.name, netdev_get_name(ofport->up.netdev),
-                     strerror(error));
+                     ovs_strerror(error));
     }
 
     ofproto->stats.tx_packets++;
@@ -6388,6 +6396,48 @@ ofproto_unixctl_dpif_dump_megaflows(struct unixctl_conn *conn,
     ds_destroy(&ds);
 }
 
+/* Disable using the megaflows.
+ *
+ * This command is only needed for advanced debugging, so it's not
+ * documented in the man page. */
+static void
+ofproto_unixctl_dpif_disable_megaflows(struct unixctl_conn *conn,
+                                       int argc OVS_UNUSED,
+                                       const char *argv[] OVS_UNUSED,
+                                       void *aux OVS_UNUSED)
+{
+    struct ofproto_dpif *ofproto;
+
+    enable_megaflows = false;
+
+    HMAP_FOR_EACH (ofproto, all_ofproto_dpifs_node, &all_ofproto_dpifs) {
+        flush(&ofproto->up);
+    }
+
+    unixctl_command_reply(conn, "megaflows disabled");
+}
+
+/* Re-enable using megaflows.
+ *
+ * This command is only needed for advanced debugging, so it's not
+ * documented in the man page. */
+static void
+ofproto_unixctl_dpif_enable_megaflows(struct unixctl_conn *conn,
+                                      int argc OVS_UNUSED,
+                                      const char *argv[] OVS_UNUSED,
+                                      void *aux OVS_UNUSED)
+{
+    struct ofproto_dpif *ofproto;
+
+    enable_megaflows = true;
+
+    HMAP_FOR_EACH (ofproto, all_ofproto_dpifs_node, &all_ofproto_dpifs) {
+        flush(&ofproto->up);
+    }
+
+    unixctl_command_reply(conn, "megaflows enabled");
+}
+
 static void
 ofproto_unixctl_dpif_dump_flows(struct unixctl_conn *conn,
                                 int argc OVS_UNUSED, const char *argv[],
@@ -6501,6 +6551,10 @@ ofproto_dpif_unixctl_init(void)
                              ofproto_unixctl_dpif_del_flows, NULL);
     unixctl_command_register("dpif/dump-megaflows", "bridge", 1, 1,
                              ofproto_unixctl_dpif_dump_megaflows, NULL);
+    unixctl_command_register("dpif/disable-megaflows", "", 0, 0,
+                             ofproto_unixctl_dpif_disable_megaflows, NULL);
+    unixctl_command_register("dpif/enable-megaflows", "", 0, 0,
+                             ofproto_unixctl_dpif_enable_megaflows, NULL);
 }
 \f
 /* Linux VLAN device support (e.g. "eth0.10" for VLAN 10.)