[ovs-dev] [PATCH v7 4/5] userspace: add layer 3 support to packet metadata
Lorand Jakab
lojakab at cisco.com
Fri Nov 14 13:51:48 UTC 2014
This is needed for sending a packet back to the datapath after a miss upcall
was processed. The presence of a layer 2 packet is signaled by adding
OVS_KEY_ATTR_ETHERNET to the packet metadata sent with the ovs_packet netlink
message.
Signed-off-by: Lorand Jakab <lojakab at cisco.com>
---
lib/flow.c | 1 +
lib/flow.h | 2 ++
lib/odp-util.c | 14 +++++++++++++-
lib/packets.h | 1 +
4 files changed, 17 insertions(+), 1 deletion(-)
diff --git a/lib/flow.c b/lib/flow.c
index b46a483..d69e2f7 100644
--- a/lib/flow.c
+++ b/lib/flow.c
@@ -727,6 +727,7 @@ flow_get_metadata(const struct flow *flow, struct flow_metadata *fmd)
memcpy(fmd->regs, flow->regs, sizeof fmd->regs);
fmd->pkt_mark = flow->pkt_mark;
fmd->in_port = flow->in_port.ofp_port;
+ fmd->base_layer = flow->base_layer;
}
char *
diff --git a/lib/flow.h b/lib/flow.h
index 637f847..a4326a2 100644
--- a/lib/flow.h
+++ b/lib/flow.h
@@ -201,6 +201,7 @@ struct flow_metadata {
uint32_t regs[FLOW_N_REGS]; /* Registers. */
uint32_t pkt_mark; /* Packet mark. */
ofp_port_t in_port; /* OpenFlow port or zero. */
+ uint32_t base_layer; /* Fields start at this layer */
};
void flow_extract(struct ofpbuf *, const struct pkt_metadata *md,
@@ -718,6 +719,7 @@ pkt_metadata_from_flow(const struct flow *flow)
md.skb_priority = flow->skb_priority;
md.pkt_mark = flow->pkt_mark;
md.in_port = flow->in_port;
+ md.base_layer = flow->base_layer;
return md;
}
diff --git a/lib/odp-util.c b/lib/odp-util.c
index a0ad73e..291f3b4 100644
--- a/lib/odp-util.c
+++ b/lib/odp-util.c
@@ -3065,6 +3065,8 @@ odp_flow_key_from_mask(struct ofpbuf *buf, const struct flow *mask,
void
odp_key_from_pkt_metadata(struct ofpbuf *buf, const struct pkt_metadata *md)
{
+ struct ovs_key_ethernet *eth_key;
+
nl_msg_put_u32(buf, OVS_KEY_ATTR_PRIORITY, md->skb_priority);
if (md->tunnel.ip_dst) {
@@ -3078,6 +3080,12 @@ odp_key_from_pkt_metadata(struct ofpbuf *buf, const struct pkt_metadata *md)
if (md->in_port.odp_port != ODPP_NONE) {
nl_msg_put_odp_port(buf, OVS_KEY_ATTR_IN_PORT, md->in_port.odp_port);
}
+
+ /* Add unintialized OVS_KEY_ATTR_ETHERNET for layer 2 packets; lack of
+ * this key attribute signals layer 3 packet */
+ if (md->base_layer == LAYER_2) {
+ nl_msg_put_unspec_uninit(buf, OVS_KEY_ATTR_ETHERNET, sizeof *eth_key);
+ }
}
/* Generate packet metadata from the given ODP flow key. */
@@ -3089,10 +3097,12 @@ odp_key_to_pkt_metadata(const struct nlattr *key, size_t key_len,
size_t left;
uint32_t wanted_attrs = 1u << OVS_KEY_ATTR_PRIORITY |
1u << OVS_KEY_ATTR_SKB_MARK | 1u << OVS_KEY_ATTR_TUNNEL |
- 1u << OVS_KEY_ATTR_IN_PORT;
+ 1u << OVS_KEY_ATTR_IN_PORT | 1u << OVS_KEY_ATTR_ETHERNET;
*md = PKT_METADATA_INITIALIZER(ODPP_NONE);
+ md->base_layer = LAYER_3;
+
NL_ATTR_FOR_EACH (nla, left, key, key_len) {
uint16_t type = nl_attr_type(nla);
size_t len = nl_attr_get_size(nla);
@@ -3134,6 +3144,8 @@ odp_key_to_pkt_metadata(const struct nlattr *key, size_t key_len,
md->in_port.odp_port = nl_attr_get_odp_port(nla);
wanted_attrs &= ~(1u << OVS_KEY_ATTR_IN_PORT);
break;
+ case OVS_KEY_ATTR_ETHERNET:
+ md->base_layer = LAYER_2;
default:
break;
}
diff --git a/lib/packets.h b/lib/packets.h
index 1435af5..406ae60 100644
--- a/lib/packets.h
+++ b/lib/packets.h
@@ -62,6 +62,7 @@ struct pkt_metadata {
uint32_t skb_priority; /* Packet priority for QoS. */
uint32_t pkt_mark; /* Packet mark. */
union flow_in_port in_port; /* Input port. */
+ uint32_t base_layer; /* Packet starts at this layer */
};
#define PKT_METADATA_INITIALIZER(PORT) \
--
1.9.3 (Apple Git-50)
More information about the dev
mailing list