diff options
| author | Andy Zhou <azhou@nicira.com> | 2014-10-03 18:35:28 -0400 |
|---|---|---|
| committer | David S. Miller <davem@davemloft.net> | 2014-10-06 00:32:20 -0400 |
| commit | 0b5e8b8eeae40bae6ad7c7e91c97c3c0d0e57882 (patch) | |
| tree | 1e3263634ab52faac57459120033776cf1a08542 | |
| parent | c259c132ad284576ab44308d5d17ea6a16c971b5 (diff) | |
net: Add Geneve tunneling protocol driver
This adds a device level support for Geneve -- Generic Network
Virtualization Encapsulation. The protocol is documented at
http://tools.ietf.org/html/draft-gross-geneve-01
Only protocol layer Geneve support is provided by this driver.
Openvswitch can be used for configuring, set up and tear down
functional Geneve tunnels.
Signed-off-by: Jesse Gross <jesse@nicira.com>
Signed-off-by: Andy Zhou <azhou@nicira.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
| -rw-r--r-- | include/net/geneve.h | 91 | ||||
| -rw-r--r-- | include/net/ip_tunnels.h | 2 | ||||
| -rw-r--r-- | net/ipv4/Kconfig | 14 | ||||
| -rw-r--r-- | net/ipv4/Makefile | 1 | ||||
| -rw-r--r-- | net/ipv4/geneve.c | 373 |
5 files changed, 481 insertions, 0 deletions
diff --git a/include/net/geneve.h b/include/net/geneve.h new file mode 100644 index 000000000000..ce98865318bf --- /dev/null +++ b/include/net/geneve.h | |||
| @@ -0,0 +1,91 @@ | |||
| 1 | #ifndef __NET_GENEVE_H | ||
| 2 | #define __NET_GENEVE_H 1 | ||
| 3 | |||
| 4 | #include <net/udp_tunnel.h> | ||
| 5 | |||
| 6 | struct geneve_sock; | ||
| 7 | |||
| 8 | typedef void (geneve_rcv_t)(struct geneve_sock *gs, struct sk_buff *skb); | ||
| 9 | |||
| 10 | struct geneve_sock { | ||
| 11 | struct hlist_node hlist; | ||
| 12 | geneve_rcv_t *rcv; | ||
| 13 | void *rcv_data; | ||
| 14 | struct work_struct del_work; | ||
| 15 | struct socket *sock; | ||
| 16 | struct rcu_head rcu; | ||
| 17 | atomic_t refcnt; | ||
| 18 | struct udp_offload udp_offloads; | ||
| 19 | }; | ||
| 20 | |||
| 21 | /* Geneve Header: | ||
| 22 | * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | ||
| 23 | * |Ver| Opt Len |O|C| Rsvd. | Protocol Type | | ||
| 24 | * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | ||
| 25 | * | Virtual Network Identifier (VNI) | Reserved | | ||
| 26 | * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | ||
| 27 | * | Variable Length Options | | ||
| 28 | * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | ||
| 29 | * | ||
| 30 | * Option Header: | ||
| 31 | * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | ||
| 32 | * | Option Class | Type |R|R|R| Length | | ||
| 33 | * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | ||
| 34 | * | Variable Option Data | | ||
| 35 | * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | ||
| 36 | */ | ||
| 37 | |||
| 38 | struct geneve_opt { | ||
| 39 | __be16 opt_class; | ||
| 40 | u8 type; | ||
| 41 | #ifdef __LITTLE_ENDIAN_BITFIELD | ||
| 42 | u8 length:5; | ||
| 43 | u8 r3:1; | ||
| 44 | u8 r2:1; | ||
| 45 | u8 r1:1; | ||
| 46 | #else | ||
| 47 | u8 r1:1; | ||
| 48 | u8 r2:1; | ||
| 49 | u8 r3:1; | ||
| 50 | u8 length:5; | ||
| 51 | #endif | ||
| 52 | u8 opt_data[]; | ||
| 53 | }; | ||
| 54 | |||
| 55 | #define GENEVE_CRIT_OPT_TYPE (1 << 7) | ||
| 56 | |||
| 57 | struct genevehdr { | ||
| 58 | #ifdef __LITTLE_ENDIAN_BITFIELD | ||
| 59 | u8 opt_len:6; | ||
| 60 | u8 ver:2; | ||
| 61 | u8 rsvd1:6; | ||
| 62 | u8 critical:1; | ||
| 63 | u8 oam:1; | ||
| 64 | #else | ||
| 65 | u8 ver:2; | ||
| 66 | u8 opt_len:6; | ||
| 67 | u8 oam:1; | ||
| 68 | u8 critical:1; | ||
| 69 | u8 rsvd1:6; | ||
| 70 | #endif | ||
| 71 | __be16 proto_type; | ||
| 72 | u8 vni[3]; | ||
| 73 | u8 rsvd2; | ||
| 74 | struct geneve_opt options[]; | ||
| 75 | }; | ||
| 76 | |||
| 77 | #define GENEVE_VER 0 | ||
| 78 | #define GENEVE_BASE_HLEN (sizeof(struct udphdr) + sizeof(struct genevehdr)) | ||
| 79 | |||
| 80 | struct geneve_sock *geneve_sock_add(struct net *net, __be16 port, | ||
| 81 | geneve_rcv_t *rcv, void *data, | ||
| 82 | bool no_share, bool ipv6); | ||
| 83 | |||
| 84 | void geneve_sock_release(struct geneve_sock *vs); | ||
| 85 | |||
| 86 | int geneve_xmit_skb(struct geneve_sock *gs, struct rtable *rt, | ||
| 87 | struct sk_buff *skb, __be32 src, __be32 dst, __u8 tos, | ||
| 88 | __u8 ttl, __be16 df, __be16 src_port, __be16 dst_port, | ||
| 89 | __be16 tun_flags, u8 vni[3], u8 opt_len, u8 *opt, | ||
| 90 | bool xnet); | ||
| 91 | #endif | ||
diff --git a/include/net/ip_tunnels.h b/include/net/ip_tunnels.h index 7f538ba6e267..a9ce1556d773 100644 --- a/include/net/ip_tunnels.h +++ b/include/net/ip_tunnels.h | |||
| @@ -95,6 +95,8 @@ struct ip_tunnel { | |||
| 95 | #define TUNNEL_VERSION __cpu_to_be16(0x40) | 95 | #define TUNNEL_VERSION __cpu_to_be16(0x40) |
| 96 | #define TUNNEL_NO_KEY __cpu_to_be16(0x80) | 96 | #define TUNNEL_NO_KEY __cpu_to_be16(0x80) |
| 97 | #define TUNNEL_DONT_FRAGMENT __cpu_to_be16(0x0100) | 97 | #define TUNNEL_DONT_FRAGMENT __cpu_to_be16(0x0100) |
| 98 | #define TUNNEL_OAM __cpu_to_be16(0x0200) | ||
| 99 | #define TUNNEL_CRIT_OPT __cpu_to_be16(0x0400) | ||
| 98 | 100 | ||
| 99 | struct tnl_ptk_info { | 101 | struct tnl_ptk_info { |
| 100 | __be16 flags; | 102 | __be16 flags; |
diff --git a/net/ipv4/Kconfig b/net/ipv4/Kconfig index 69fb37854449..c2035447e649 100644 --- a/net/ipv4/Kconfig +++ b/net/ipv4/Kconfig | |||
| @@ -453,6 +453,20 @@ config TCP_CONG_BIC | |||
| 453 | increase provides TCP friendliness. | 453 | increase provides TCP friendliness. |
| 454 | See http://www.csc.ncsu.edu/faculty/rhee/export/bitcp/ | 454 | See http://www.csc.ncsu.edu/faculty/rhee/export/bitcp/ |
| 455 | 455 | ||
| 456 | config GENEVE | ||
| 457 | tristate "Generic Network Virtualization Encapsulation (Geneve)" | ||
| 458 | depends on INET | ||
| 459 | select NET_IP_TUNNEL | ||
| 460 | select NET_UDP_TUNNEL | ||
| 461 | ---help--- | ||
| 462 | This allows one to create Geneve virtual interfaces that provide | ||
| 463 | Layer 2 Networks over Layer 3 Networks. Geneve is often used | ||
| 464 | to tunnel virtual network infrastructure in virtualized environments. | ||
| 465 | For more information see: | ||
| 466 | http://tools.ietf.org/html/draft-gross-geneve-01 | ||
| 467 | |||
| 468 | To compile this driver as a module, choose M here: the module | ||
| 469 | |||
| 456 | config TCP_CONG_CUBIC | 470 | config TCP_CONG_CUBIC |
| 457 | tristate "CUBIC TCP" | 471 | tristate "CUBIC TCP" |
| 458 | default y | 472 | default y |
diff --git a/net/ipv4/Makefile b/net/ipv4/Makefile index d8105787c199..518c04ed666e 100644 --- a/net/ipv4/Makefile +++ b/net/ipv4/Makefile | |||
| @@ -56,6 +56,7 @@ obj-$(CONFIG_TCP_CONG_YEAH) += tcp_yeah.o | |||
| 56 | obj-$(CONFIG_TCP_CONG_ILLINOIS) += tcp_illinois.o | 56 | obj-$(CONFIG_TCP_CONG_ILLINOIS) += tcp_illinois.o |
| 57 | obj-$(CONFIG_MEMCG_KMEM) += tcp_memcontrol.o | 57 | obj-$(CONFIG_MEMCG_KMEM) += tcp_memcontrol.o |
| 58 | obj-$(CONFIG_NETLABEL) += cipso_ipv4.o | 58 | obj-$(CONFIG_NETLABEL) += cipso_ipv4.o |
| 59 | obj-$(CONFIG_GENEVE) += geneve.o | ||
| 59 | 60 | ||
| 60 | obj-$(CONFIG_XFRM) += xfrm4_policy.o xfrm4_state.o xfrm4_input.o \ | 61 | obj-$(CONFIG_XFRM) += xfrm4_policy.o xfrm4_state.o xfrm4_input.o \ |
| 61 | xfrm4_output.o xfrm4_protocol.o | 62 | xfrm4_output.o xfrm4_protocol.o |
diff --git a/net/ipv4/geneve.c b/net/ipv4/geneve.c new file mode 100644 index 000000000000..f008c5515f48 --- /dev/null +++ b/net/ipv4/geneve.c | |||
| @@ -0,0 +1,373 @@ | |||
| 1 | /* | ||
| 2 | * Geneve: Generic Network Virtualization Encapsulation | ||
| 3 | * | ||
| 4 | * Copyright (c) 2014 Nicira, Inc. | ||
| 5 | * | ||
| 6 | * This program is free software; you can redistribute it and/or | ||
| 7 | * modify it under the terms of the GNU General Public License | ||
| 8 | * as published by the Free Software Foundation; either version | ||
| 9 | * 2 of the License, or (at your option) any later version. | ||
| 10 | */ | ||
| 11 | |||
| 12 | #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt | ||
| 13 | |||
| 14 | #include <linux/kernel.h> | ||
| 15 | #include <linux/types.h> | ||
| 16 | #include <linux/module.h> | ||
| 17 | #include <linux/errno.h> | ||
| 18 | #include <linux/slab.h> | ||
| 19 | #include <linux/skbuff.h> | ||
| 20 | #include <linux/rculist.h> | ||
| 21 | #include <linux/netdevice.h> | ||
| 22 | #include <linux/in.h> | ||
| 23 | #include <linux/ip.h> | ||
| 24 | #include <linux/udp.h> | ||
| 25 | #include <linux/igmp.h> | ||
| 26 | #include <linux/etherdevice.h> | ||
| 27 | #include <linux/if_ether.h> | ||
| 28 | #include <linux/if_vlan.h> | ||
| 29 | #include <linux/hash.h> | ||
| 30 | #include <linux/ethtool.h> | ||
| 31 | #include <net/arp.h> | ||
| 32 | #include <net/ndisc.h> | ||
| 33 | #include <net/ip.h> | ||
| 34 | #include <net/ip_tunnels.h> | ||
| 35 | #include <net/icmp.h> | ||
| 36 | #include <net/udp.h> | ||
| 37 | #include <net/rtnetlink.h> | ||
| 38 | #include <net/route.h> | ||
| 39 | #include <net/dsfield.h> | ||
| 40 | #include <net/inet_ecn.h> | ||
| 41 | #include <net/net_namespace.h> | ||
| 42 | #include <net/netns/generic.h> | ||
| 43 | #include <net/geneve.h> | ||
| 44 | #include <net/protocol.h> | ||
| 45 | #include <net/udp_tunnel.h> | ||
| 46 | #if IS_ENABLED(CONFIG_IPV6) | ||
| 47 | #include <net/ipv6.h> | ||
| 48 | #include <net/addrconf.h> | ||
| 49 | #include <net/ip6_tunnel.h> | ||
| 50 | #include <net/ip6_checksum.h> | ||
| 51 | #endif | ||
| 52 | |||
| 53 | #define PORT_HASH_BITS 8 | ||
