+ nla_total_size(1) /* OVS_TUNNEL_KEY_ATTR_TTL */
+ nla_total_size(0) /* OVS_TUNNEL_KEY_ATTR_DONT_FRAGMENT */
+ nla_total_size(0) /* OVS_TUNNEL_KEY_ATTR_CSUM */
+ + nla_total_size(0) /* OVS_TUNNEL_KEY_ATTR_OAM */
+ nla_total_size(4) /* OVS_KEY_ATTR_IN_PORT */
+ nla_total_size(4) /* OVS_KEY_ATTR_SKB_MARK */
+ nla_total_size(4) /* OVS_KEY_ATTR_DP_HASH */
[OVS_TUNNEL_KEY_ATTR_TTL] = 1,
[OVS_TUNNEL_KEY_ATTR_DONT_FRAGMENT] = 0,
[OVS_TUNNEL_KEY_ATTR_CSUM] = 0,
+ [OVS_TUNNEL_KEY_ATTR_OAM] = 0,
};
if (type > OVS_TUNNEL_KEY_ATTR_MAX) {
case OVS_TUNNEL_KEY_ATTR_CSUM:
tun_flags |= TUNNEL_CSUM;
break;
+ case OVS_TUNNEL_KEY_ATTR_OAM:
+ tun_flags |= TUNNEL_OAM;
+ break;
default:
return -EINVAL;
}
if ((output->tun_flags & TUNNEL_CSUM) &&
nla_put_flag(skb, OVS_TUNNEL_KEY_ATTR_CSUM))
return -EMSGSIZE;
+ if ((output->tun_flags & TUNNEL_OAM) &&
+ nla_put_flag(skb, OVS_TUNNEL_KEY_ATTR_OAM))
+ return -EMSGSIZE;
nla_nest_end(skb, nla);
return 0;
int iptunnel_pull_header(struct sk_buff *skb, int hdr_len, __be16 inner_proto);
#endif
+
+/* Not yet upstream */
+#define TUNNEL_OAM __cpu_to_be16(0x0200)
+
#endif /* __NET_IP_TUNNELS_H */
OVS_TUNNEL_KEY_ATTR_TTL, /* u8 Tunnel IP TTL. */
OVS_TUNNEL_KEY_ATTR_DONT_FRAGMENT, /* No argument, set DF. */
OVS_TUNNEL_KEY_ATTR_CSUM, /* No argument. CSUM packet. */
+ OVS_TUNNEL_KEY_ATTR_OAM, /* No argument, OAM frame. */
__OVS_TUNNEL_KEY_ATTR_MAX
};
return "csum";
case FLOW_TNL_F_KEY:
return "key";
+ case FLOW_TNL_F_OAM:
+ return "oam";
default:
return NULL;
}
#define FLOW_TNL_F_DONT_FRAGMENT (1 << 0)
#define FLOW_TNL_F_CSUM (1 << 1)
#define FLOW_TNL_F_KEY (1 << 2)
+#define FLOW_TNL_F_OAM (1 << 3)
const char *flow_tun_flag_to_string(uint32_t flags);
case OVS_TUNNEL_KEY_ATTR_TTL: return 1;
case OVS_TUNNEL_KEY_ATTR_DONT_FRAGMENT: return 0;
case OVS_TUNNEL_KEY_ATTR_CSUM: return 0;
+ case OVS_TUNNEL_KEY_ATTR_OAM: return 0;
case __OVS_TUNNEL_KEY_ATTR_MAX:
return -1;
}
case OVS_TUNNEL_KEY_ATTR_CSUM:
tun->flags |= FLOW_TNL_F_CSUM;
break;
+ case OVS_TUNNEL_KEY_ATTR_OAM:
+ tun->flags |= FLOW_TNL_F_OAM;
+ break;
default:
/* Allow this to show up as unexpected, if there are unknown
* tunnel attribute, eventually resulting in ODP_FIT_TOO_MUCH. */
if (tun_key->flags & FLOW_TNL_F_CSUM) {
nl_msg_put_flag(a, OVS_TUNNEL_KEY_ATTR_CSUM);
}
+ if (tun_key->flags & FLOW_TNL_F_OAM) {
+ nl_msg_put_flag(a, OVS_TUNNEL_KEY_ATTR_OAM);
+ }
nl_msg_end_nested(a, tun_key_ofs);
}
odp_tun_key_from_attr(ma, &tun_mask);
if (tun_mask.flags == (FLOW_TNL_F_KEY
| FLOW_TNL_F_DONT_FRAGMENT
- | FLOW_TNL_F_CSUM)) {
+ | FLOW_TNL_F_CSUM
+ | FLOW_TNL_F_OAM)) {
/* The flags are exact match, check the remaining fields. */
tun_mask.flags = 0xffff;
is_exact = is_all_ones((uint8_t *)&tun_mask,
* - OVS_TUNNEL_KEY_ATTR_TTL 1 3 4 8
* - OVS_TUNNEL_KEY_ATTR_DONT_FRAGMENT 0 -- 4 4
* - OVS_TUNNEL_KEY_ATTR_CSUM 0 -- 4 4
+ * - OVS_TUNNEL_KEY_ATTR_OAM 0 -- 4 4
* OVS_KEY_ATTR_IN_PORT 4 -- 4 8
* OVS_KEY_ATTR_SKB_MARK 4 -- 4 8
* OVS_KEY_ATTR_DP_HASH 4 -- 4 8
* OVS_KEY_ATTR_ICMPV6 2 2 4 8
* OVS_KEY_ATTR_ND 28 -- 4 32
* ----------------------------------------------------------
- * total 224
+ * total 228
*
* We include some slack space in case the calculation isn't quite right or we
* add another field and forget to adjust this value.