(icmp->icmp6_type == ND_NEIGHBOR_SOLICIT ||
icmp->icmp6_type == ND_NEIGHBOR_ADVERT)) {
- *nd_target = data_try_pull(datap, sizep, sizeof *nd_target);
+ *nd_target = data_try_pull(datap, sizep, sizeof **nd_target);
if (OVS_UNLIKELY(!*nd_target)) {
return false;
}
miniflow_push_be16(mf, tp_src, htons(icmp->icmp_type));
miniflow_push_be16(mf, tp_dst, htons(icmp->icmp_code));
}
+ } else if (OVS_LIKELY(nw_proto == IPPROTO_IGMP)) {
+ if (OVS_LIKELY(size >= IGMP_HEADER_LEN)) {
+ const struct igmp_header *igmp = data;
+
+ miniflow_push_be16(mf, tp_src, htons(igmp->igmp_type));
+ miniflow_push_be16(mf, tp_dst, htons(igmp->igmp_code));
+ miniflow_push_be32(mf, igmp_group_ip4,
+ get_16aligned_be32(&igmp->group));
+ }
} else if (OVS_LIKELY(nw_proto == IPPROTO_ICMPV6)) {
if (OVS_LIKELY(size >= sizeof(struct icmp6_hdr))) {
const struct in6_addr *nd_target = NULL;
memset(arp_buf, 0, sizeof arp_buf);
if (OVS_LIKELY(parse_icmpv6(&data, &size, icmp, &nd_target,
arp_buf))) {
+ miniflow_push_words(mf, arp_sha, arp_buf,
+ ETH_ADDR_LEN * 2 / 4);
if (nd_target) {
miniflow_push_words(mf, nd_target, nd_target,
sizeof *nd_target / 4);
}
- miniflow_push_words(mf, arp_sha, arp_buf,
- ETH_ADDR_LEN * 2 / 4);
miniflow_push_be16(mf, tp_src, htons(icmp->icmp6_type));
miniflow_push_be16(mf, tp_dst, htons(icmp->icmp6_code));
}
void
flow_get_metadata(const struct flow *flow, struct flow_metadata *fmd)
{
- BUILD_ASSERT_DECL(FLOW_WC_SEQ == 26);
+ BUILD_ASSERT_DECL(FLOW_WC_SEQ == 27);
fmd->dp_hash = flow->dp_hash;
fmd->recirc_id = flow->recirc_id;
return "csum";
case FLOW_TNL_F_KEY:
return "key";
+ case FLOW_TNL_F_OAM:
+ return "oam";
default:
return NULL;
}
flow->mpls_lse[0] = set_mpls_lse_values(ttl, tc, 1, htonl(label));
/* Clear all L3 and L4 fields. */
- BUILD_ASSERT(FLOW_WC_SEQ == 26);
+ BUILD_ASSERT(FLOW_WC_SEQ == 27);
memset((char *) flow + FLOW_SEGMENT_2_ENDS_AT, 0,
sizeof(struct flow) - FLOW_SEGMENT_2_ENDS_AT);
}
icmp->icmp_type = ntohs(flow->tp_src);
icmp->icmp_code = ntohs(flow->tp_dst);
icmp->icmp_csum = csum(icmp, ICMP_HEADER_LEN);
+ } else if (flow->nw_proto == IPPROTO_IGMP) {
+ struct igmp_header *igmp;
+
+ l4_len = sizeof *igmp;
+ igmp = ofpbuf_put_zeros(b, l4_len);
+ igmp->igmp_type = ntohs(flow->tp_src);
+ igmp->igmp_code = ntohs(flow->tp_dst);
+ put_16aligned_be32(&igmp->group, flow->igmp_group_ip4);
+ igmp->igmp_csum = csum(igmp, IGMP_HEADER_LEN);
} else if (flow->nw_proto == IPPROTO_ICMPV6) {
struct icmp6_hdr *icmp;
l4_len = flow_compose_l4(b, flow);
+ ip = ofpbuf_l3(b);
ip->ip_tot_len = htons(b->l4_ofs - b->l3_ofs + l4_len);
ip->ip_csum = csum(ip, sizeof *ip);
} else if (flow->dl_type == htons(ETH_TYPE_IPV6)) {
l4_len = flow_compose_l4(b, flow);
+ nh = ofpbuf_l3(b);
nh->ip6_plen = htons(l4_len);
} else if (flow->dl_type == htons(ETH_TYPE_ARP) ||
flow->dl_type == htons(ETH_TYPE_RARP)) {
if (OVS_LIKELY(a_map == b_map)) {
int count = miniflow_n_values(a);
- while (count--) {
- if (*ap++ != *bp++) {
- return false;
- }
- }
+ return !memcmp(ap, bp, count * sizeof *ap);
} else {
uint64_t map;