summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAlexander Duyck <aduyck@mirantis.com>2016-01-25 19:32:54 -0800
committerJeff Kirsher <jeffrey.t.kirsher@intel.com>2016-02-18 15:57:26 -0800
commitffcc55c0c2a85835a4ac080bc1053c3a277b88e2 (patch)
treede460ef041fc9c7f5fcb14bf41affb6189771630
parentf608e6a60fc85e4f261daab5e7aac6225e2120d6 (diff)
downloadop-kernel-dev-ffcc55c0c2a85835a4ac080bc1053c3a277b88e2.zip
op-kernel-dev-ffcc55c0c2a85835a4ac080bc1053c3a277b88e2.tar.gz
i40e: Add support for ATR w/ IPv6 extension headers
This patch updates the code for determining the L4 protocol and L3 header length so that when IPv6 extension headers are being used we can determine the offset and type of the L4 protocol. Signed-off-by: Alexander Duyck <aduyck@mirantis.com> Tested-by: Andrew Bowers <andrewx.bowers@intel.com> Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
-rw-r--r--drivers/net/ethernet/intel/i40e/i40e_txrx.c28
1 files changed, 13 insertions, 15 deletions
diff --git a/drivers/net/ethernet/intel/i40e/i40e_txrx.c b/drivers/net/ethernet/intel/i40e/i40e_txrx.c
index 159fb6e..1d3afa7 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_txrx.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_txrx.c
@@ -2044,7 +2044,7 @@ static void i40e_atr(struct i40e_ring *tx_ring, struct sk_buff *skb,
struct tcphdr *th;
unsigned int hlen;
u32 flex_ptype, dtype_cmd;
- u8 l4_proto;
+ int l4_proto;
u16 i;
/* make sure ATR is enabled */
@@ -2062,25 +2062,23 @@ static void i40e_atr(struct i40e_ring *tx_ring, struct sk_buff *skb,
if (!(tx_flags & (I40E_TX_FLAGS_IPV4 | I40E_TX_FLAGS_IPV6)))
return;
- if (!(tx_flags & I40E_TX_FLAGS_UDP_TUNNEL)) {
- /* snag network header to get L4 type and address */
- hdr.network = skb_network_header(skb);
+ /* snag network header to get L4 type and address */
+ hdr.network = (tx_flags & I40E_TX_FLAGS_UDP_TUNNEL) ?
+ skb_inner_network_header(skb) : skb_network_header(skb);
+ /* Note: tx_flags gets modified to reflect inner protocols in
+ * tx_enable_csum function if encap is enabled.
+ */
+ if (tx_flags & I40E_TX_FLAGS_IPV4) {
/* access ihl as u8 to avoid unaligned access on ia64 */
- if (tx_flags & I40E_TX_FLAGS_IPV4)
- hlen = (hdr.network[0] & 0x0F) << 2;
- else
- hlen = sizeof(struct ipv6hdr);
+ hlen = (hdr.network[0] & 0x0F) << 2;
+ l4_proto = hdr.ipv4->protocol;
} else {
- hdr.network = skb_inner_network_header(skb);
- hlen = skb_inner_network_header_len(skb);
+ hlen = hdr.network - skb->data;
+ l4_proto = ipv6_find_hdr(skb, &hlen, IPPROTO_TCP, NULL, NULL);
+ hlen -= hdr.network - skb->data;
}
- /* Note: tx_flags gets modified to reflect inner protocols in
- * tx_enable_csum function if encap is enabled.
- */
- l4_proto = (tx_flags & I40E_TX_FLAGS_IPV4) ? hdr.ipv4->protocol :
- hdr.ipv6->nexthdr;
if (l4_proto != IPPROTO_TCP)
return;
OpenPOWER on IntegriCloud