Bump kernel support for datapath module to include 3.12. Make use of native vxlan kernel module for Linux >= 3.12 or if the kernel in use supports the required vxlan functions. Make use of native iptunnels capability for Linux >= 3.12. Note: ipv6 enablement with vxlan is not supported by this change. Signed-off-by: James Page --- FAQ | 2 +- NEWS | 2 +- acinclude.m4 | 5 +++-- datapath/linux/compat/include/net/ip_tunnels.h | 8 +++++++- datapath/linux/compat/include/net/vxlan.h | 10 +++++++++- datapath/linux/compat/ip_tunnels_core.c | 6 +++++- datapath/linux/compat/vxlan.c | 8 ++++++-- datapath/vport-gre.c | 2 +- datapath/vport-lisp.c | 2 +- datapath/vport-vxlan.c | 2 +- 10 files changed, 35 insertions(+), 12 deletions(-) diff --git a/FAQ b/FAQ index 75d9e6b..bbb13c4 100644 --- a/FAQ +++ b/FAQ @@ -148,7 +148,7 @@ A: The following table lists the Linux kernel versions against which the 1.10.x 2.6.18 to 3.8 1.11.x 2.6.18 to 3.8 2.0.x 2.6.32 to 3.10 - 2.1.x 2.6.32 to 3.11 + 2.1.x 2.6.32 to 3.12 Open vSwitch userspace should also work with the Linux kernel module built into Linux 3.3 and later. diff --git a/NEWS b/NEWS index 515a236..01c9d75 100644 --- a/NEWS +++ b/NEWS @@ -46,7 +46,7 @@ v2.1.0 - xx xxx xxxx number. - ovs-vswitchd.conf.db.5 man page will contain graphviz/dot diagram only if graphviz package was installed at the build time. - - Support for Linux kernels up to 3.11 + - Support for Linux kernels up to 3.12 - ovs-dpctl: The "show" command also displays mega flow mask stats. - ovs-ofctl: diff --git a/acinclude.m4 b/acinclude.m4 index 8ff5828..d62e295 100644 --- a/acinclude.m4 +++ b/acinclude.m4 @@ -134,10 +134,10 @@ AC_DEFUN([OVS_CHECK_LINUX], [ AC_MSG_RESULT([$kversion]) if test "$version" -ge 3; then - if test "$version" = 3 && test "$patchlevel" -le 11; then + if test "$version" = 3 && test "$patchlevel" -le 12; then : # Linux 3.x else - AC_ERROR([Linux kernel in $KBUILD is version $kversion, but version newer than 3.11.x is not supported]) + AC_ERROR([Linux kernel in $KBUILD is version $kversion, but version newer than 3.12.x is not supported]) fi else if test "$version" -le 1 || test "$patchlevel" -le 5 || test "$sublevel" -le 31; then @@ -275,6 +275,7 @@ AC_DEFUN([OVS_CHECK_LINUX_COMPAT], [ OVS_GREP_IFELSE([$KSRC/include/net/genetlink.h], [parallel_ops]) OVS_GREP_IFELSE([$KSRC/include/net/gre.h], [gre_cisco_register]) + OVS_GREP_IFELSE([$KSRC/include/net/vxlan.h], [vxlan_sock_add]) OVS_GREP_IFELSE([$KSRC/include/net/netlink.h], [nla_get_be16]) OVS_GREP_IFELSE([$KSRC/include/net/netlink.h], [nla_put_be16]) OVS_GREP_IFELSE([$KSRC/include/net/netlink.h], [nla_put_be32]) diff --git a/datapath/linux/compat/include/net/ip_tunnels.h b/datapath/linux/compat/include/net/ip_tunnels.h index a786aa9..7f63266 100644 --- a/datapath/linux/compat/include/net/ip_tunnels.h +++ b/datapath/linux/compat/include/net/ip_tunnels.h @@ -11,6 +11,10 @@ #include #include +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,12,0) +#include_next +#else + #define TUNNEL_CSUM __cpu_to_be16(0x01) #define TUNNEL_ROUTING __cpu_to_be16(0x02) #define TUNNEL_KEY __cpu_to_be16(0x04) @@ -34,7 +38,9 @@ struct tnl_ptk_info { int iptunnel_xmit(struct rtable *rt, struct sk_buff *skb, __be32 src, __be32 dst, __u8 proto, - __u8 tos, __u8 ttl, __be16 df); + __u8 tos, __u8 ttl, __be16 df, bool xnet); int iptunnel_pull_header(struct sk_buff *skb, int hdr_len, __be16 inner_proto); + +#endif /* LINUX_VERSION_CODE >= KERNEL_VERSION(3,12,0) */ #endif /* __NET_IP_TUNNELS_H */ diff --git a/datapath/linux/compat/include/net/vxlan.h b/datapath/linux/compat/include/net/vxlan.h index 3ac816b..0608598 100644 --- a/datapath/linux/compat/include/net/vxlan.h +++ b/datapath/linux/compat/include/net/vxlan.h @@ -5,6 +5,13 @@ #include #include +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,12,0) || \ + defined(HAVE_VXLAN_SOCK_ADD) +#include_next +#endif + +#ifndef HAVE_VXLAN_SOCK_ADD + struct vxlan_sock; typedef void (vxlan_rcv_t)(struct vxlan_sock *vs, struct sk_buff *skb, __be32 key); @@ -20,7 +27,7 @@ struct vxlan_sock { struct vxlan_sock *vxlan_sock_add(struct net *net, __be16 port, vxlan_rcv_t *rcv, void *data, - bool no_share); + bool no_share, bool ipv6); void vxlan_sock_release(struct vxlan_sock *vs); @@ -31,4 +38,5 @@ int vxlan_xmit_skb(struct vxlan_sock *vs, __be16 vxlan_src_port(__u16 port_min, __u16 port_max, struct sk_buff *skb); +#endif /* HAVE_VXLAN_SOCK_ADD */ #endif diff --git a/datapath/linux/compat/ip_tunnels_core.c b/datapath/linux/compat/ip_tunnels_core.c index 66d5e02..3dad15d 100644 --- a/datapath/linux/compat/ip_tunnels_core.c +++ b/datapath/linux/compat/ip_tunnels_core.c @@ -34,10 +34,12 @@ #include "compat.h" #include "gso.h" +#if LINUX_VERSION_CODE < KERNEL_VERSION(3,12,0) + int iptunnel_xmit(struct rtable *rt, struct sk_buff *skb, __be32 src, __be32 dst, __u8 proto, - __u8 tos, __u8 ttl, __be16 df) + __u8 tos, __u8 ttl, __be16 df, bool xnet) { int pkt_len = skb->len; struct iphdr *iph; @@ -108,3 +110,5 @@ int iptunnel_pull_header(struct sk_buff *skb, int hdr_len, __be16 inner_proto) skb->pkt_type = PACKET_HOST; return 0; } + +#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(3,12,0) */ diff --git a/datapath/linux/compat/vxlan.c b/datapath/linux/compat/vxlan.c index 64877e0..83f7a96 100644 --- a/datapath/linux/compat/vxlan.c +++ b/datapath/linux/compat/vxlan.c @@ -56,6 +56,8 @@ #include "gso.h" #include "vlan.h" +#ifndef HAVE_VXLAN_SOCK_ADD + #define VXLAN_HLEN (sizeof(struct udphdr) + sizeof(struct vxlanhdr)) #define VXLAN_FLAGS 0x08000000 /* struct vxlanhdr.vx_flags required value. */ @@ -223,7 +225,7 @@ int vxlan_xmit_skb(struct vxlan_sock *vs, if (err) return err; - return iptunnel_xmit(rt, skb, src, dst, IPPROTO_UDP, tos, ttl, df); + return iptunnel_xmit(rt, skb, src, dst, IPPROTO_UDP, tos, ttl, df, false); } static void rcu_free_vs(struct rcu_head *rcu) @@ -298,7 +300,7 @@ static struct vxlan_sock *vxlan_socket_create(struct net *net, __be16 port, struct vxlan_sock *vxlan_sock_add(struct net *net, __be16 port, vxlan_rcv_t *rcv, void *data, - bool no_share) + bool no_share, bool ipv6) { return vxlan_socket_create(net, port, rcv, data); } @@ -310,3 +312,5 @@ void vxlan_sock_release(struct vxlan_sock *vs) queue_work(system_wq, &vs->del_work); } + +#endif /* HAVE_VXLAN_SOCK_ADD */ diff --git a/datapath/vport-gre.c b/datapath/vport-gre.c index 8737b63..8613756 100644 --- a/datapath/vport-gre.c +++ b/datapath/vport-gre.c @@ -178,7 +178,7 @@ static int __send(struct vport *vport, struct sk_buff *skb, return iptunnel_xmit(rt, skb, saddr, OVS_CB(skb)->tun_key->ipv4_dst, IPPROTO_GRE, OVS_CB(skb)->tun_key->ipv4_tos, - OVS_CB(skb)->tun_key->ipv4_ttl, df); + OVS_CB(skb)->tun_key->ipv4_ttl, df, false); err_free_rt: ip_rt_put(rt); error: diff --git a/datapath/vport-lisp.c b/datapath/vport-lisp.c index c2698ae..a441540 100644 --- a/datapath/vport-lisp.c +++ b/datapath/vport-lisp.c @@ -463,7 +463,7 @@ static int lisp_send(struct vport *vport, struct sk_buff *skb) sent_len = iptunnel_xmit(rt, skb, saddr, OVS_CB(skb)->tun_key->ipv4_dst, IPPROTO_UDP, OVS_CB(skb)->tun_key->ipv4_tos, - OVS_CB(skb)->tun_key->ipv4_ttl, df); + OVS_CB(skb)->tun_key->ipv4_ttl, df, false); return sent_len > 0 ? sent_len + network_offset : sent_len; diff --git a/datapath/vport-vxlan.c b/datapath/vport-vxlan.c index ab2b6f7..d264785 100644 --- a/datapath/vport-vxlan.c +++ b/datapath/vport-vxlan.c @@ -124,7 +124,7 @@ static struct vport *vxlan_tnl_create(const struct vport_parms *parms) vxlan_port = vxlan_vport(vport); strncpy(vxlan_port->name, parms->name, IFNAMSIZ); - vs = vxlan_sock_add(net, htons(dst_port), vxlan_rcv, vport, true); + vs = vxlan_sock_add(net, htons(dst_port), vxlan_rcv, vport, true, false); if (IS_ERR(vs)) { ovs_vport_free(vport); return (void *)vs; -- 1.8.5.2