[ovs-dev] [PATCH net-next] NSH(Network Service Header) implementation

pravin shelar pshelar at ovn.org
Tue Jun 7 00:45:08 UTC 2016


On Mon, Jun 6, 2016 at 2:34 AM, Yi Yang <yi.y.yang at intel.com> wrote:
> IETF defined NSH(Network Service Header) for Service
> Function Chaining, this is an IETF draft
>
> https://tools.ietf.org/html/draft-ietf-sfc-nsh-05
>
> It will be a IETF standard shortly, this patch implemented
> NSH for Open vSwitch.
>
> Signed-off-by: Johnson Li <johnson.li at intel.com>
> Signed-off-by: Yi Yang <yi.y.yang at intel.com>
> ---
>  drivers/net/vxlan.c              |   7 ++
>  include/net/nsh.h                | 117 +++++++++++++++++++++++
>  include/uapi/linux/openvswitch.h |  32 +++++++
>  net/openvswitch/actions.c        |  68 +++++++++++++
>  net/openvswitch/flow.c           |  45 ++++++++-
>  net/openvswitch/flow.h           |  15 +++
>  net/openvswitch/flow_netlink.c   | 202 ++++++++++++++++++++++++++++++++++++++-
>  net/openvswitch/vport-netdev.c   |   3 +-
>  net/openvswitch/vport-vxlan.c    |  15 +++
>  9 files changed, 501 insertions(+), 3 deletions(-)
>  create mode 100644 include/net/nsh.h
>

...
...
> diff --git a/net/openvswitch/actions.c b/net/openvswitch/actions.c
> index 9a3eb7a..38e787c 100644
> --- a/net/openvswitch/actions.c
> +++ b/net/openvswitch/actions.c
> @@ -29,6 +29,7 @@
>  #include <linux/in6.h>
>  #include <linux/if_arp.h>
>  #include <linux/if_vlan.h>
> +#include <linux/if_ether.h>
>
>  #include <net/dst.h>
>  #include <net/ip.h>
> @@ -38,6 +39,7 @@
>  #include <net/dsfield.h>
>  #include <net/mpls.h>
>  #include <net/sctp/checksum.h>
> +#include <net/nsh.h>
>
>  #include "datapath.h"
>  #include "flow.h"
> @@ -259,6 +261,64 @@ static int push_vlan(struct sk_buff *skb, struct sw_flow_key *key,
>                              ntohs(vlan->vlan_tci) & ~VLAN_TAG_PRESENT);
>  }
>
...
...
> +
> +static int push_nsh(struct sk_buff *skb, struct sw_flow_key *key,
> +                   const struct ovs_action_push_nsh *nsh)
> +{
> +       if (nsh->len > 0 && nsh->len <= 256) {
> +               struct nsh_hdr *nsh_hdr = NULL;
> +
> +               if (skb_cow_head(skb, nsh->len) < 0)
> +                       return -ENOMEM;
> +
> +               skb_push(skb, nsh->len);
> +               nsh_hdr = (struct nsh_hdr *)(skb->data);
> +               memcpy(nsh_hdr, nsh->header, nsh->len);
> +
> +               if (!skb->inner_protocol)
> +                       skb_set_inner_protocol(skb, skb->protocol);
> +
> +               skb->protocol = htons(ETH_P_NSH); /* 0x894F */
> +               key->eth.type = htons(ETH_P_NSH);
> +       } else {
> +               return -EINVAL;
> +       }
> +
> +       return 0;
> +}

Networking stack or OVS can not handle arbitrary skb-protocol. For
example what happens if OVS has push vlan action or it sends this nsh
packet to net device which can not handle nsh packet? Even networking
stack can not parse such packet for handling offloads in software.
...

> diff --git a/net/openvswitch/vport-vxlan.c b/net/openvswitch/vport-vxlan.c
> index 5eb7694..3d060c4 100644
> --- a/net/openvswitch/vport-vxlan.c
> +++ b/net/openvswitch/vport-vxlan.c
> @@ -52,6 +52,18 @@ static int vxlan_get_options(const struct vport *vport, struct sk_buff *skb)
>                         return -EMSGSIZE;
>
>                 nla_nest_end(skb, exts);
> +       } else if (vxlan->flags & VXLAN_F_GPE) {
> +               struct nlattr *exts;
> +
> +               exts = nla_nest_start(skb, OVS_TUNNEL_ATTR_EXTENSION);
> +               if (!exts)
> +                       return -EMSGSIZE;
> +
> +               if (vxlan->flags & VXLAN_F_GPE &&
> +                   nla_put_flag(skb, OVS_VXLAN_EXT_GPE))
> +                       return -EMSGSIZE;
> +
> +               nla_nest_end(skb, exts);
>         }
>
>         return 0;
> @@ -59,6 +71,7 @@ static int vxlan_get_options(const struct vport *vport, struct sk_buff *skb)
>
>  static const struct nla_policy exts_policy[OVS_VXLAN_EXT_MAX + 1] = {
>         [OVS_VXLAN_EXT_GBP]     = { .type = NLA_FLAG, },
> +       [OVS_VXLAN_EXT_GPE]     = { .type = NLA_FLAG, },
>  };
>
>  static int vxlan_configure_exts(struct vport *vport, struct nlattr *attr,
> @@ -76,6 +89,8 @@ static int vxlan_configure_exts(struct vport *vport, struct nlattr *attr,
>
>         if (exts[OVS_VXLAN_EXT_GBP])
>                 conf->flags |= VXLAN_F_GBP;
> +       else if (exts[OVS_VXLAN_EXT_GPE])
> +               conf->flags |= VXLAN_F_GPE;
>
This is compatibility code, no need to add new features to this code.
Now we should be directly using net devices.



More information about the dev mailing list