tunnel: Generate datapath flows for tunneled packets dropped due to ECN.
authorJustin Pettit <jpettit@nicira.com>
Wed, 13 Feb 2013 22:08:15 +0000 (14:08 -0800)
committerJustin Pettit <jpettit@nicira.com>
Wed, 6 Mar 2013 21:55:29 +0000 (13:55 -0800)
Move the check for whether tunneled packets should be dropped due to
congestion encountered (CE) when the encapsulated packet is not ECN
capable (non-ECT).  This also adds some additional tests for ECN
handling on tunnel decapsulation.

Signed-off-by: Justin Pettit <jpettit@nicira.com>
ofproto/ofproto-dpif.c
ofproto/tunnel.c
tests/tunnel.at

index 5522b9e..8111891 100644 (file)
@@ -6272,6 +6272,20 @@ may_receive(const struct ofport_dpif *port, struct action_xlate_ctx *ctx)
     return true;
 }
 
+static bool
+tunnel_ecn_ok(struct action_xlate_ctx *ctx)
+{
+    if (is_ip_any(&ctx->base_flow)
+        && (ctx->base_flow.tunnel.ip_tos & IP_ECN_MASK) == IP_ECN_CE
+        && (ctx->base_flow.nw_tos & IP_ECN_MASK) == IP_ECN_NOT_ECT) {
+        VLOG_WARN_RL(&rl, "dropping tunnel packet marked ECN CE but is not ECN"
+                     " capable");
+        return false;
+    }
+
+    return true;
+}
+
 static void
 do_xlate_actions(const struct ofpact *ofpacts, size_t ofpacts_len,
                  struct action_xlate_ctx *ctx)
@@ -6590,7 +6604,7 @@ xlate_actions(struct action_xlate_ctx *ctx,
 
         add_sflow_action(ctx);
 
-        if (!in_port || may_receive(in_port, ctx)) {
+        if (tunnel_ecn_ok(ctx) && (!in_port || may_receive(in_port, ctx))) {
             do_xlate_actions(ofpacts, ofpacts_len, ctx);
 
             /* We've let OFPP_NORMAL and the learning action look at the
index afe7221..8287937 100644 (file)
@@ -197,14 +197,6 @@ tnl_port_receive(struct flow *flow)
         return NULL;
     }
 
-    if (is_ip_any(flow)
-        && ((flow->tunnel.ip_tos & IP_ECN_MASK) == IP_ECN_CE)
-        && (flow->nw_tos & IP_ECN_MASK) == IP_ECN_NOT_ECT) {
-        VLOG_WARN_RL(&rl, "dropping tunnel packet marked ECN CE but is not ECN"
-                     " capable");
-        return NULL;
-    }
-
     if (!VLOG_DROP_DBG(&dbg_rl)) {
         pre_flow_str = flow_to_string(flow);
     }
index a6e889a..fa019ee 100644 (file)
@@ -87,11 +87,30 @@ br0 (dummy@ovs-dummy):
        p2 2/2: (dummy)
 ])
 
+dnl Tunnel CE and encapsulated packet CE
+AT_CHECK([ovs-appctl ofproto/trace br0 'tunnel(tun_id=0x0,src=1.1.1.1,dst=2.2.2.2,tos=0x3,ttl=64,flags()),in_port(1),eth(src=50:54:00:00:00:05,dst=50:54:00:00:00:07),eth_type(0x0800),ipv4(src=192.168.0.1,dst=192.168.0.2,proto=6,tos=3,ttl=64,frag=no),tcp(src=8,dst=9)'], [0], [stdout])
+AT_CHECK([tail -1 stdout], [0],
+  [Datapath actions: 2
+])
+
+dnl Tunnel CE and encapsulated packet ECT(1)
 AT_CHECK([ovs-appctl ofproto/trace br0 'tunnel(tun_id=0x0,src=1.1.1.1,dst=2.2.2.2,tos=0x3,ttl=64,flags()),in_port(1),eth(src=50:54:00:00:00:05,dst=50:54:00:00:00:07),eth_type(0x0800),ipv4(src=192.168.0.1,dst=192.168.0.2,proto=6,tos=1,ttl=64,frag=no),tcp(src=8,dst=9)'], [0], [stdout])
 AT_CHECK([tail -1 stdout], [0],
   [Datapath actions: 2
 ])
-OVS_VSWITCHD_STOP
+
+dnl Tunnel CE and encapsulated packet ECT(2)
+AT_CHECK([ovs-appctl ofproto/trace br0 'tunnel(tun_id=0x0,src=1.1.1.1,dst=2.2.2.2,tos=0x3,ttl=64,flags()),in_port(1),eth(src=50:54:00:00:00:05,dst=50:54:00:00:00:07),eth_type(0x0800),ipv4(src=192.168.0.1,dst=192.168.0.2,proto=6,tos=2,ttl=64,frag=no),tcp(src=8,dst=9)'], [0], [stdout])
+AT_CHECK([tail -1 stdout], [0],
+  [Datapath actions: 2
+])
+
+dnl Tunnel CE and encapsulated packet Non-ECT
+AT_CHECK([ovs-appctl ofproto/trace br0 'tunnel(tun_id=0x0,src=1.1.1.1,dst=2.2.2.2,tos=0x3,ttl=64,flags()),in_port(1),eth(src=50:54:00:00:00:05,dst=50:54:00:00:00:07),eth_type(0x0800),ipv4(src=192.168.0.1,dst=192.168.0.2,proto=6,tos=0,ttl=64,frag=no),tcp(src=8,dst=9)'], [0], [stdout])
+AT_CHECK([tail -1 stdout], [0],
+  [Datapath actions: drop
+])
+OVS_VSWITCHD_STOP(["/dropping tunnel packet marked ECN CE but is not ECN capable/d"])
 AT_CLEANUP
 
 AT_SETUP([tunnel - output])