/*
- * Copyright (c) 2009, 2010, 2011, 2012, 2013, 2014, 2015 Nicira, Inc.
+ * Copyright (c) 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016 Nicira, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
match->flow.tunnel.ip_dst = dst & mask;
}
+void
+match_set_tun_ipv6_src(struct match *match, const struct in6_addr *src)
+{
+ match->flow.tunnel.ipv6_src = *src;
+ match->wc.masks.tunnel.ipv6_src = in6addr_exact;
+}
+
+void
+match_set_tun_ipv6_src_masked(struct match *match, const struct in6_addr *src,
+ const struct in6_addr *mask)
+{
+ match->flow.tunnel.ipv6_src = ipv6_addr_bitand(src, mask);
+ match->wc.masks.tunnel.ipv6_src = *mask;
+}
+
+void
+match_set_tun_ipv6_dst(struct match *match, const struct in6_addr *dst)
+{
+ match->flow.tunnel.ipv6_dst = *dst;
+ match->wc.masks.tunnel.ipv6_dst = in6addr_exact;
+}
+
+void
+match_set_tun_ipv6_dst_masked(struct match *match, const struct in6_addr *dst,
+ const struct in6_addr *mask)
+{
+ match->flow.tunnel.ipv6_dst = ipv6_addr_bitand(dst, mask);
+ match->wc.masks.tunnel.ipv6_dst = *mask;
+}
+
void
match_set_tun_ttl(struct match *match, uint8_t ttl)
{
match->wc.masks.ct_zone = UINT16_MAX;
}
+void
+match_set_ct_mark(struct match *match, uint32_t ct_mark)
+{
+ match_set_ct_mark_masked(match, ct_mark, UINT32_MAX);
+}
+
+void
+match_set_ct_mark_masked(struct match *match, uint32_t ct_mark,
+ uint32_t mask)
+{
+ match->flow.ct_mark = ct_mark & mask;
+ match->wc.masks.ct_mark = mask;
+}
+
+void
+match_set_ct_label(struct match *match, ovs_u128 ct_label)
+{
+ ovs_u128 mask;
+
+ mask.u64.lo = UINT64_MAX;
+ mask.u64.hi = UINT64_MAX;
+ match_set_ct_label_masked(match, ct_label, mask);
+}
+
+void
+match_set_ct_label_masked(struct match *match, ovs_u128 value, ovs_u128 mask)
+{
+ match->flow.ct_label.u64.lo = value.u64.lo & mask.u64.lo;
+ match->flow.ct_label.u64.hi = value.u64.hi & mask.u64.hi;
+ match->wc.masks.ct_label = mask;
+}
+
void
match_set_dl_type(struct match *match, ovs_be16 dl_type)
{
flow_set_mpls_bos(&match->flow, idx, mpls_bos);
}
+/* Modifies 'match' so that the TTL of MPLS label 'idx' is wildcarded. */
+void
+match_set_any_mpls_ttl(struct match *match, int idx)
+{
+ match->wc.masks.mpls_lse[idx] &= ~htonl(MPLS_TTL_MASK);
+ flow_set_mpls_ttl(&match->flow, idx, 0);
+}
+
+/* Modifies 'match' so that it matches only packets in which the TTL of MPLS
+ * label 'idx' equals 'mpls_ttl'. */
+void
+match_set_mpls_ttl(struct match *match, int idx, uint8_t mpls_ttl)
+{
+ match->wc.masks.mpls_lse[idx] |= htonl(MPLS_TTL_MASK);
+ flow_set_mpls_ttl(&match->flow, idx, mpls_ttl);
+}
+
/* Modifies 'match' so that the MPLS LSE is wildcarded. */
void
match_set_any_mpls_lse(struct match *match, int idx)
{
if (!ipv6_mask_is_any(netmask)) {
ds_put_format(s, "%s=", name);
- print_ipv6_masked(s, addr, netmask);
+ ipv6_format_masked(addr, netmask, s);
ds_put_char(s, ',');
}
}
format_be64_masked(s, "tun_id", tnl->tun_id, wc->masks.tunnel.tun_id);
format_ip_netmask(s, "tun_src", tnl->ip_src, wc->masks.tunnel.ip_src);
format_ip_netmask(s, "tun_dst", tnl->ip_dst, wc->masks.tunnel.ip_dst);
+ format_ipv6_netmask(s, "tun_ipv6_src", &tnl->ipv6_src,
+ &wc->masks.tunnel.ipv6_src);
+ format_ipv6_netmask(s, "tun_ipv6_dst", &tnl->ipv6_dst,
+ &wc->masks.tunnel.ipv6_dst);
if (wc->masks.tunnel.gbp_id) {
format_be16_masked(s, "tun_gbp_id", tnl->gbp_id,
tun_metadata_match_format(s, match);
}
+static void
+format_ct_label_masked(struct ds *s, const ovs_u128 *key, const ovs_u128 *mask)
+{
+ if (!ovs_u128_is_zero(mask)) {
+ ovs_be128 value = hton128(*key);
+ ds_put_format(s, "ct_label=");
+ ds_put_hex(s, &value, sizeof value);
+ if (!is_all_ones(mask, sizeof(*mask))) {
+ value = hton128(*mask);
+ ds_put_char(s, '/');
+ ds_put_hex(s, &value, sizeof value);
+ }
+ ds_put_char(s, ',');
+ }
+}
+
/* Appends a string representation of 'match' to 's'. If 'priority' is
* different from OFP_DEFAULT_PRIORITY, includes it in 's'. */
void
int i;
- BUILD_ASSERT_DECL(FLOW_WC_SEQ == 34);
+ BUILD_ASSERT_DECL(FLOW_WC_SEQ == 35);
if (priority != OFP_DEFAULT_PRIORITY) {
ds_put_format(s, "priority=%d,", priority);
format_uint16_masked(s, "ct_zone", f->ct_zone, wc->masks.ct_zone);
}
+ if (wc->masks.ct_mark) {
+ format_uint32_masked(s, "ct_mark", f->ct_mark, wc->masks.ct_mark);
+ }
+
+ if (!ovs_u128_is_zero(&wc->masks.ct_label)) {
+ format_ct_label_masked(s, &f->ct_label, &wc->masks.ct_label);
+ }
+
if (wc->masks.dl_type) {
skip_type = true;
if (f->dl_type == htons(ETH_TYPE_IP)) {