+ mutable->flags = nla_get_u32(a[OVS_TUNNEL_ATTR_FLAGS]) & TNL_F_PUBLIC;
+
+ port_key_set_net(&mutable->key, net);
+ mutable->key.daddr = nla_get_be32(a[OVS_TUNNEL_ATTR_DST_IPV4]);
+ if (a[OVS_TUNNEL_ATTR_SRC_IPV4]) {
+ if (ipv4_is_multicast(mutable->key.daddr))
+ return -EINVAL;
+ mutable->key.saddr = nla_get_be32(a[OVS_TUNNEL_ATTR_SRC_IPV4]);
+ }
+
+ if (a[OVS_TUNNEL_ATTR_TOS]) {
+ mutable->tos = nla_get_u8(a[OVS_TUNNEL_ATTR_TOS]);
+ if (mutable->tos != RT_TOS(mutable->tos))
+ return -EINVAL;
+ }
+
+ if (a[OVS_TUNNEL_ATTR_TTL])
+ mutable->ttl = nla_get_u8(a[OVS_TUNNEL_ATTR_TTL]);
+
+ mutable->key.tunnel_type = tnl_ops->tunnel_type;
+ if (!a[OVS_TUNNEL_ATTR_IN_KEY]) {
+ mutable->key.tunnel_type |= TNL_T_KEY_MATCH;
+ mutable->flags |= TNL_F_IN_KEY_MATCH;
+ } else {
+ mutable->key.tunnel_type |= TNL_T_KEY_EXACT;
+ mutable->key.in_key = nla_get_be64(a[OVS_TUNNEL_ATTR_IN_KEY]);
+ }
+
+ if (!a[OVS_TUNNEL_ATTR_OUT_KEY])
+ mutable->flags |= TNL_F_OUT_KEY_ACTION;
+ else
+ mutable->out_key = nla_get_be64(a[OVS_TUNNEL_ATTR_OUT_KEY]);
+
+ mutable->tunnel_hlen = tnl_ops->hdr_len(mutable);