Commit 8c1a90aa authored by Matthew Vick's avatar Matthew Vick Committed by Jeff Kirsher

fm10k: Modify tunnel length header check when offloading

The FM10000 host interface can only support up to 184 bytes when
performing tunnel offloads. Because of this, a check was added to
prevent the driver from attempting to feed a header to the hardware too
big for it to parse. Make this check a little more robust by calculating
the inner L4 header length based on whether it is TCP or UDP.

Cc: Joe Stringer <joestringer@nicira.com>
Signed-off-by: default avatarMatthew Vick <matthew.vick@intel.com>
Tested-by: default avatarKrishneil Singh <Krishneil.k.singh@intel.com>
Signed-off-by: default avatarJeff Kirsher <jeffrey.t.kirsher@intel.com>
parent b898441f
...@@ -711,10 +711,6 @@ static struct ethhdr *fm10k_gre_is_nvgre(struct sk_buff *skb) ...@@ -711,10 +711,6 @@ static struct ethhdr *fm10k_gre_is_nvgre(struct sk_buff *skb)
if (nvgre_hdr->flags & FM10K_NVGRE_RESERVED0_FLAGS) if (nvgre_hdr->flags & FM10K_NVGRE_RESERVED0_FLAGS)
return NULL; return NULL;
/* verify protocol is transparent Ethernet bridging */
if (nvgre_hdr->proto != htons(ETH_P_TEB))
return NULL;
/* report start of ethernet header */ /* report start of ethernet header */
if (nvgre_hdr->flags & NVGRE_TNI) if (nvgre_hdr->flags & NVGRE_TNI)
return (struct ethhdr *)(nvgre_hdr + 1); return (struct ethhdr *)(nvgre_hdr + 1);
...@@ -724,13 +720,11 @@ static struct ethhdr *fm10k_gre_is_nvgre(struct sk_buff *skb) ...@@ -724,13 +720,11 @@ static struct ethhdr *fm10k_gre_is_nvgre(struct sk_buff *skb)
static __be16 fm10k_tx_encap_offload(struct sk_buff *skb) static __be16 fm10k_tx_encap_offload(struct sk_buff *skb)
{ {
u8 l4_hdr = 0, inner_l4_hdr = 0, inner_l4_hlen;
struct ethhdr *eth_hdr; struct ethhdr *eth_hdr;
u8 l4_hdr = 0;
/* fm10k supports 184 octets of outer+inner headers. Minus 20 for inner L4. */ if (skb->inner_protocol_type != ENCAP_TYPE_ETHER ||
#define FM10K_MAX_ENCAP_TRANSPORT_OFFSET 164 skb->inner_protocol != htons(ETH_P_TEB))
if (skb_inner_transport_header(skb) - skb_mac_header(skb) >
FM10K_MAX_ENCAP_TRANSPORT_OFFSET)
return 0; return 0;
switch (vlan_get_protocol(skb)) { switch (vlan_get_protocol(skb)) {
...@@ -760,12 +754,33 @@ static __be16 fm10k_tx_encap_offload(struct sk_buff *skb) ...@@ -760,12 +754,33 @@ static __be16 fm10k_tx_encap_offload(struct sk_buff *skb)
switch (eth_hdr->h_proto) { switch (eth_hdr->h_proto) {
case htons(ETH_P_IP): case htons(ETH_P_IP):
inner_l4_hdr = inner_ip_hdr(skb)->protocol;
break;
case htons(ETH_P_IPV6): case htons(ETH_P_IPV6):
inner_l4_hdr = inner_ipv6_hdr(skb)->nexthdr;
break; break;
default: default:
return 0; return 0;
} }
switch (inner_l4_hdr) {
case IPPROTO_TCP:
inner_l4_hlen = inner_tcp_hdrlen(skb);
break;
case IPPROTO_UDP:
inner_l4_hlen = 8;
break;
default:
return 0;
}
/* The hardware allows tunnel offloads only if the combined inner and
* outer header is 184 bytes or less
*/
if (skb_inner_transport_header(skb) + inner_l4_hlen -
skb_mac_header(skb) > FM10K_TUNNEL_HEADER_LENGTH)
return 0;
return eth_hdr->h_proto; return eth_hdr->h_proto;
} }
......
...@@ -356,6 +356,9 @@ struct fm10k_hw; ...@@ -356,6 +356,9 @@ struct fm10k_hw;
#define FM10K_QUEUE_DISABLE_TIMEOUT 100 #define FM10K_QUEUE_DISABLE_TIMEOUT 100
#define FM10K_RESET_TIMEOUT 150 #define FM10K_RESET_TIMEOUT 150
/* Maximum supported combined inner and outer header length for encapsulation */
#define FM10K_TUNNEL_HEADER_LENGTH 184
/* VF registers */ /* VF registers */
#define FM10K_VFCTRL 0x00000 #define FM10K_VFCTRL 0x00000
#define FM10K_VFCTRL_RST 0x00000008 #define FM10K_VFCTRL_RST 0x00000008
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment