ofproto-dpif: Fix "ofproto/trace" command.
[sliver-openvswitch.git] / ofproto / ofproto-dpif.c
index f5280ff..e93e2a7 100644 (file)
@@ -4634,8 +4634,11 @@ do_xlate_actions(const union ofp_action *in, size_t n_in,
             break;
 
         case OFPUTIL_OFPAT_SET_NW_TOS:
-            ctx->flow.nw_tos &= ~IP_DSCP_MASK;
-            ctx->flow.nw_tos |= ia->nw_tos.nw_tos & IP_DSCP_MASK;
+            /* OpenFlow 1.0 only supports IPv4. */
+            if (ctx->flow.dl_type == htons(ETH_TYPE_IP)) {
+                ctx->flow.nw_tos &= ~IP_DSCP_MASK;
+                ctx->flow.nw_tos |= ia->nw_tos.nw_tos & IP_DSCP_MASK;
+            }
             break;
 
         case OFPUTIL_OFPAT_SET_TP_SRC:
@@ -5534,15 +5537,24 @@ packet_out(struct ofproto *ofproto_, struct ofpbuf *packet,
                              ofproto->max_ports);
     if (!error) {
         struct odputil_keybuf keybuf;
-        struct action_xlate_ctx ctx;
         struct ofpbuf *odp_actions;
+        struct ofproto_push push;
         struct ofpbuf key;
 
         ofpbuf_use_stack(&key, &keybuf, sizeof keybuf);
         odp_flow_key_from_flow(&key, flow);
 
-        action_xlate_ctx_init(&ctx, ofproto, flow, flow->vlan_tci, 0, packet);
-        odp_actions = xlate_actions(&ctx, ofp_actions, n_ofp_actions);
+        action_xlate_ctx_init(&push.ctx, ofproto, flow, flow->vlan_tci, 0,
+                              packet);
+
+        /* Ensure that resubmits in 'ofp_actions' get accounted to their
+         * matching rules. */
+        push.packets = 1;
+        push.bytes = packet->size;
+        push.used = time_msec();
+        push.ctx.resubmit_hook = push_resubmit;
+
+        odp_actions = xlate_actions(&push.ctx, ofp_actions, n_ofp_actions);
         dpif_execute(ofproto->dpif, key.data, key.size,
                      odp_actions->data, odp_actions->size, packet);
         ofpbuf_delete(odp_actions);
@@ -5889,7 +5901,7 @@ ofproto_dpif_unixctl_init(void)
     unixctl_command_register(
         "ofproto/trace",
         "bridge {tun_id in_port packet | odp_flow [-generate]}",
-        2, 4, ofproto_unixctl_trace, NULL);
+        2, 5, ofproto_unixctl_trace, NULL);
     unixctl_command_register("fdb/flush", "bridge", 1, 1,
                              ofproto_unixctl_fdb_flush, NULL);
     unixctl_command_register("fdb/show", "bridge", 1, 1,