[ovs-dev] [PATCH v7 4/5] Add set tunnel support to execute_set_action
Simon Horman
horms at verge.net.au
Wed May 1 08:33:18 UTC 2013
Add set tunnel support to execute_set_action.
This also adds support for the user-space datapath
to honour such actions if they occur before recirculation,
which will be added by a subsequent patch.
This is in preparation for using execute_set_action()
to handle recirculation.
Signed-off-by: Simon Horman <horms at verge.net.au>
---
v7
* No change
v6
* First post
---
lib/dpif-netdev.c | 15 ++++++++++-----
lib/execute-actions.c | 25 +++++++++++++++++++------
lib/execute-actions.h | 1 +
lib/odp-util.c | 2 +-
lib/odp-util.h | 3 +++
5 files changed, 34 insertions(+), 12 deletions(-)
diff --git a/lib/dpif-netdev.c b/lib/dpif-netdev.c
index 6c55352..8f973e5 100644
--- a/lib/dpif-netdev.c
+++ b/lib/dpif-netdev.c
@@ -158,7 +158,8 @@ static void dp_netdev_execute_actions(struct dp_netdev *,
const struct nlattr *actions,
size_t actions_len,
uint32_t *skb_priority,
- uint32_t *skb_mark);
+ uint32_t *skb_mark,
+ struct flow_tnl *tun_key);
static struct dpif_netdev *
dpif_netdev_cast(const struct dpif *dpif)
@@ -941,10 +942,12 @@ dpif_netdev_execute(struct dpif *dpif, const struct dpif_execute *execute)
if (!error) {
uint32_t skb_priority = 0;
uint32_t skb_mark = 0;
+ struct flow_tnl tun_key;
+ memset(&tun_key, 0, sizeof tun_key);
dp_netdev_execute_actions(dp, ©, &key,
execute->actions, execute->actions_len,
- &skb_priority, &skb_mark);
+ &skb_priority, &skb_mark, &tun_key);
}
ofpbuf_uninit(©);
@@ -1035,6 +1038,7 @@ dp_netdev_port_input(struct dp_netdev *dp, struct dp_netdev_port *port,
struct flow key;
uint32_t skb_priority = 0;
uint32_t skb_mark = 0;
+ struct flow_tnl tun_key;
if (packet->size < ETH_HEADER_LEN) {
return;
@@ -1042,10 +1046,11 @@ dp_netdev_port_input(struct dp_netdev *dp, struct dp_netdev_port *port,
flow_extract(packet, 0, 0, NULL, port->port_no, &key);
flow = dp_netdev_lookup_flow(dp, &key);
if (flow) {
+ memset(&tun_key, 0, sizeof tun_key);
dp_netdev_flow_used(flow, packet);
dp_netdev_execute_actions(dp, packet, &key,
flow->actions, flow->actions_len,
- &skb_priority, &skb_mark);
+ &skb_priority, &skb_mark, &tun_key);
dp->n_hit++;
} else {
dp->n_missed++;
@@ -1167,10 +1172,10 @@ dp_netdev_execute_actions(struct dp_netdev *dp,
struct ofpbuf *packet, struct flow *key,
const struct nlattr *actions,
size_t actions_len, uint32_t *skb_priority,
- uint32_t *skb_mark)
+ uint32_t *skb_mark, struct flow_tnl *tun_key)
{
execute_actions(dp, packet, key, actions, actions_len, skb_priority,
- skb_mark, dp_netdev_output_port,
+ skb_mark, tun_key, dp_netdev_output_port,
dp_netdev_action_userspace);
}
diff --git a/lib/execute-actions.c b/lib/execute-actions.c
index 7f8f468..ca9c3ca 100644
--- a/lib/execute-actions.c
+++ b/lib/execute-actions.c
@@ -22,6 +22,7 @@
#include "execute-actions.h"
#include "netlink.h"
+#include "odp-util.h"
#include "packets.h"
#include "util.h"
@@ -36,8 +37,18 @@ eth_set_src_and_dst(struct ofpbuf *packet,
}
static void
+set_tunnel_action(const struct nlattr *a, struct flow_tnl *tun_key)
+{
+ enum odp_key_fitness fitness = tun_key_from_attr(a, tun_key);
+
+ memset(&tun_key, 0, sizeof tun_key);
+ ovs_assert(fitness != ODP_FIT_ERROR);
+}
+
+static void
execute_set_action(struct ofpbuf *packet, const struct nlattr *a,
- uint32_t *skb_priority, uint32_t *skb_mark)
+ uint32_t *skb_priority, uint32_t *skb_mark,
+ struct flow_tnl *tun_key)
{
enum ovs_key_attr type = nl_attr_type(a);
const struct ovs_key_ipv4 *ipv4_key;
@@ -47,7 +58,7 @@ execute_set_action(struct ofpbuf *packet, const struct nlattr *a,
switch (type) {
case OVS_KEY_ATTR_TUNNEL:
- /* not implemented */
+ set_tunnel_action(a, tun_key);
break;
case OVS_KEY_ATTR_PRIORITY:
@@ -108,7 +119,7 @@ execute_set_action(struct ofpbuf *packet, const struct nlattr *a,
static void
execute_sample(void *dp, struct ofpbuf *packet, struct flow *key,
const struct nlattr *action, uint32_t *skb_priority,
- uint32_t *skb_mark,
+ uint32_t *skb_mark, struct flow_tnl *tun_key,
void (*output)(void *dp, struct ofpbuf *packet,
uint32_t out_port),
void (*userspace)(void *dp, struct ofpbuf *packet,
@@ -141,13 +152,14 @@ execute_sample(void *dp, struct ofpbuf *packet, struct flow *key,
execute_actions(dp, packet, key, nl_attr_get(subactions),
nl_attr_get_size(subactions), skb_priority, skb_mark,
- output, userspace);
+ tun_key, output, userspace);
}
void
execute_actions(void *dp, struct ofpbuf *packet, struct flow *key,
const struct nlattr *actions, size_t actions_len,
uint32_t *skb_priority, uint32_t *skb_mark,
+ struct flow_tnl *tun_key,
void (*output)(void *dp, struct ofpbuf *packet,
uint32_t out_port),
void (*userspace)(void *dp, struct ofpbuf *packet,
@@ -191,11 +203,12 @@ execute_actions(void *dp, struct ofpbuf *packet, struct flow *key,
break;
case OVS_ACTION_ATTR_SET:
- execute_set_action(packet, nl_attr_get(a), skb_priority, skb_mark);
+ execute_set_action(packet, nl_attr_get(a), skb_priority, skb_mark,
+ tun_key);
break;
case OVS_ACTION_ATTR_SAMPLE:
- execute_sample(dp, packet, key, a, skb_priority, skb_mark,
+ execute_sample(dp, packet, key, a, skb_priority, skb_mark, tun_key,
output, userspace);
break;
diff --git a/lib/execute-actions.h b/lib/execute-actions.h
index 2dd4741..2c36f27 100644
--- a/lib/execute-actions.h
+++ b/lib/execute-actions.h
@@ -26,6 +26,7 @@ void
execute_actions(void *dp, struct ofpbuf *packet, struct flow *key,
const struct nlattr *actions, size_t actions_len,
uint32_t *skb_priority, uint32_t *skb_mark,
+ struct flow_tnl *tun_key,
void (*output)(void *dp, struct ofpbuf *packet,
uint32_t out_port),
void (*userspace)(void *dp, struct ofpbuf *packet,
diff --git a/lib/odp-util.c b/lib/odp-util.c
index ae09267..e868a9e 100644
--- a/lib/odp-util.c
+++ b/lib/odp-util.c
@@ -773,7 +773,7 @@ tunnel_key_attr_len(int type)
return -1;
}
-static enum odp_key_fitness
+enum odp_key_fitness
tun_key_from_attr(const struct nlattr *attr, struct flow_tnl *tun)
{
unsigned int left;
diff --git a/lib/odp-util.h b/lib/odp-util.h
index 0b34383..ccececf 100644
--- a/lib/odp-util.h
+++ b/lib/odp-util.h
@@ -87,6 +87,9 @@ struct odputil_keybuf {
uint32_t keybuf[DIV_ROUND_UP(ODPUTIL_FLOW_KEY_BYTES, 4)];
};
+enum odp_key_fitness
+tun_key_from_attr(const struct nlattr *attr, struct flow_tnl *tun);
+
void odp_flow_key_format(const struct nlattr *, size_t, struct ds *);
int odp_flow_key_from_string(const char *s, const struct simap *port_names,
struct ofpbuf *);
--
1.8.2.1
More information about the dev
mailing list