aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/vxlan.c
diff options
context:
space:
mode:
authorPravin B Shelar <pshelar@nicira.com>2013-08-19 14:22:54 -0400
committerDavid S. Miller <davem@davemloft.net>2013-08-20 03:15:43 -0400
commit7ce04758279514ca1d8ebfe322508a4a430fe2c8 (patch)
tree80a10950fd4925fda6149dbe724360938652a86e /drivers/net/vxlan.c
parent9c2e24e16fbccf6cc1102442acc4a629f79615a7 (diff)
vxlan: Restructure vxlan receive.
Use iptunnel_pull_header() for better code sharing. Signed-off-by: Pravin B Shelar <pshelar@nicira.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/vxlan.c')
-rw-r--r--drivers/net/vxlan.c22
1 files changed, 7 insertions, 15 deletions
diff --git a/drivers/net/vxlan.c b/drivers/net/vxlan.c
index b784ee668a4e..1afb9795105f 100644
--- a/drivers/net/vxlan.c
+++ b/drivers/net/vxlan.c
@@ -57,6 +57,7 @@
57#define VXLAN_VID_MASK (VXLAN_N_VID - 1) 57#define VXLAN_VID_MASK (VXLAN_N_VID - 1)
58/* IP header + UDP + VXLAN + Ethernet header */ 58/* IP header + UDP + VXLAN + Ethernet header */
59#define VXLAN_HEADROOM (20 + 8 + 8 + 14) 59#define VXLAN_HEADROOM (20 + 8 + 8 + 14)
60#define VXLAN_HLEN (sizeof(struct udphdr) + sizeof(struct vxlanhdr))
60 61
61#define VXLAN_FLAGS 0x08000000 /* struct vxlanhdr.vx_flags required value. */ 62#define VXLAN_FLAGS 0x08000000 /* struct vxlanhdr.vx_flags required value. */
62 63
@@ -868,15 +869,12 @@ static int vxlan_udp_encap_recv(struct sock *sk, struct sk_buff *skb)
868 __u32 vni; 869 __u32 vni;
869 int err; 870 int err;
870 871
871 /* pop off outer UDP header */
872 __skb_pull(skb, sizeof(struct udphdr));
873
874 /* Need Vxlan and inner Ethernet header to be present */ 872 /* Need Vxlan and inner Ethernet header to be present */
875 if (!pskb_may_pull(skb, sizeof(struct vxlanhdr))) 873 if (!pskb_may_pull(skb, VXLAN_HLEN))
876 goto error; 874 goto error;
877 875
878 /* Drop packets with reserved bits set */ 876 /* Return packets with reserved bits set */
879 vxh = (struct vxlanhdr *) skb->data; 877 vxh = (struct vxlanhdr *)(udp_hdr(skb) + 1);
880 if (vxh->vx_flags != htonl(VXLAN_FLAGS) || 878 if (vxh->vx_flags != htonl(VXLAN_FLAGS) ||
881 (vxh->vx_vni & htonl(0xff))) { 879 (vxh->vx_vni & htonl(0xff))) {
882 netdev_dbg(skb->dev, "invalid vxlan flags=%#x vni=%#x\n", 880 netdev_dbg(skb->dev, "invalid vxlan flags=%#x vni=%#x\n",
@@ -884,8 +882,6 @@ static int vxlan_udp_encap_recv(struct sock *sk, struct sk_buff *skb)
884 goto error; 882 goto error;
885 } 883 }
886 884
887 __skb_pull(skb, sizeof(struct vxlanhdr));
888
889 /* Is this VNI defined? */ 885 /* Is this VNI defined? */
890 vni = ntohl(vxh->vx_vni) >> 8; 886 vni = ntohl(vxh->vx_vni) >> 8;
891 port = inet_sk(sk)->inet_sport; 887 port = inet_sk(sk)->inet_sport;
@@ -896,7 +892,7 @@ static int vxlan_udp_encap_recv(struct sock *sk, struct sk_buff *skb)
896 goto drop; 892 goto drop;
897 } 893 }
898 894
899 if (!pskb_may_pull(skb, ETH_HLEN)) { 895 if (iptunnel_pull_header(skb, VXLAN_HLEN, htons(ETH_P_TEB))) {
900 vxlan->dev->stats.rx_length_errors++; 896 vxlan->dev->stats.rx_length_errors++;
901 vxlan->dev->stats.rx_errors++; 897 vxlan->dev->stats.rx_errors++;
902 goto drop; 898 goto drop;
@@ -904,8 +900,6 @@ static int vxlan_udp_encap_recv(struct sock *sk, struct sk_buff *skb)
904 900
905 skb_reset_mac_header(skb); 901 skb_reset_mac_header(skb);
906 902
907 /* Re-examine inner Ethernet packet */
908 oip = ip_hdr(skb);
909 skb->protocol = eth_type_trans(skb, vxlan->dev); 903 skb->protocol = eth_type_trans(skb, vxlan->dev);
910 904
911 /* Ignore packet loops (and multicast echo) */ 905 /* Ignore packet loops (and multicast echo) */
@@ -913,11 +907,12 @@ static int vxlan_udp_encap_recv(struct sock *sk, struct sk_buff *skb)
913 vxlan->dev->dev_addr) == 0) 907 vxlan->dev->dev_addr) == 0)
914 goto drop; 908 goto drop;
915 909
910 /* Re-examine inner Ethernet packet */
911 oip = ip_hdr(skb);
916 if ((vxlan->flags & VXLAN_F_LEARN) && 912 if ((vxlan->flags & VXLAN_F_LEARN) &&
917 vxlan_snoop(skb->dev, oip->saddr, eth_hdr(skb)->h_source)) 913 vxlan_snoop(skb->dev, oip->saddr, eth_hdr(skb)->h_source))
918 goto drop; 914 goto drop;
919 915
920 __skb_tunnel_rx(skb, vxlan->dev);
921 skb_reset_network_header(skb); 916 skb_reset_network_header(skb);
922 917
923 /* If the NIC driver gave us an encapsulated packet with 918 /* If the NIC driver gave us an encapsulated packet with
@@ -953,9 +948,6 @@ static int vxlan_udp_encap_recv(struct sock *sk, struct sk_buff *skb)
953 948
954 return 0; 949 return 0;
955error: 950error:
956 /* Put UDP header back */
957 __skb_push(skb, sizeof(struct udphdr));
958
959 return 1; 951 return 1;
960drop: 952drop:
961 /* Consume bad packet */ 953 /* Consume bad packet */