]> www.infradead.org Git - users/jedix/linux-maple.git/commitdiff
ixgbe: ixgbe_atr() compute l4_proto only if non-paged data has network/transport...
authorSowmini Varadhan <sowmini.varadhan@oracle.com>
Mon, 24 Oct 2016 22:36:39 +0000 (15:36 -0700)
committerChuck Anderson <chuck.anderson@oracle.com>
Sat, 25 Feb 2017 05:48:14 +0000 (21:48 -0800)
Orabug: 24568240

For some Tx paths (e.g., tpacket_snd()), ixgbe_atr may be
passed down an sk_buff that has the network and transport
header in the paged data, so it needs to make sure these
headers are available in the headlen bytes to calculate the
l4_proto.

This patch expect that network and transport headers are
already available in the non-paged header dat.  The assumption
is that the caller has set this up if l4_proto based Tx
steering is desired.

Signed-off-by: Sowmini Varadhan <sowmini.varadhan@oracle.com>
Reviewed-by: Alexander Duyck <alexander.h.duyck@intel.com>
Tested-by: Krishneil Singh <krishneil.k.singh@intel.com>
Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
(cherry picked from commit 9f3c7504fa005e2aab5ba9e1f2d8b4f4fcc6c077)
Signed-off-by: Brian Maly <brian.maly@oracle.com>
Conflicts:
drivers/net/ethernet/intel/ixgbe/ixgbe_main.c

drivers/net/ethernet/intel/ixgbe/ixgbe_main.c

index ac0013936a072a5af8d693806f5c7918b8e93e32..a0654b14d66b2283d5bda376f86a8b308cccbef6 100644 (file)
@@ -7675,11 +7675,17 @@ static void ixgbe_atr(struct ixgbe_ring *ring,
        skb = first->skb;
        hdr.network = skb_network_header(skb);
 #ifdef CONFIG_IXGBE_VXLAN
+       if (unlikely(hdr.network <= skb->data))
+               return;
        if (skb->encapsulation &&
            first->protocol == htons(ETH_P_IP) &&
            hdr.ipv4->protocol == IPPROTO_UDP) {
                struct ixgbe_adapter *adapter = q_vector->adapter;
 
+               if (unlikely(skb_tail_pointer(skb) < hdr.network +
+                            VXLAN_HEADROOM))
+                       return;
+
                /* verify the port is recognized as VXLAN */
                if (adapter->vxlan_port &&
                    udp_hdr(skb)->dest == adapter->vxlan_port)
@@ -7687,6 +7693,12 @@ static void ixgbe_atr(struct ixgbe_ring *ring,
        }
 #endif /* CONFIG_IXGBE_VXLAN */
 
+       /* Make sure we have at least [minimum IPv4 header + TCP]
+        * or [IPv6 header] bytes
+        */
+       if (unlikely(skb_tail_pointer(skb) < hdr.network + 40))
+               return;
+
        /* Currently only IPv4/IPv6 with TCP is supported */
        switch (hdr.ipv4->version) {
        case IPVERSION:
@@ -7706,6 +7718,10 @@ static void ixgbe_atr(struct ixgbe_ring *ring,
        if (l4_proto != IPPROTO_TCP)
                return;
 
+       if (unlikely(skb_tail_pointer(skb) < hdr.network +
+                    hlen + sizeof(struct tcphdr)))
+               return;
+
        th = (struct tcphdr *)(hdr.network + hlen);
 
        /* skip this packet since the socket is closing */