brcm2708: add kernel 4.14 support
[openwrt/staging/chunkeey.git] / target / linux / brcm2708 / patches-4.14 / 950-0271-net-lan78xx-Add-support-for-VLAN-tag-stripping.patch
diff --git a/target/linux/brcm2708/patches-4.14/950-0271-net-lan78xx-Add-support-for-VLAN-tag-stripping.patch b/target/linux/brcm2708/patches-4.14/950-0271-net-lan78xx-Add-support-for-VLAN-tag-stripping.patch
new file mode 100644 (file)
index 0000000..e1e5500
--- /dev/null
@@ -0,0 +1,82 @@
+From 9d4c65d0e7ebfe20bd24e65d52b1df56e90d498e Mon Sep 17 00:00:00 2001
+From: Dave Stevenson <dave.stevenson@raspberrypi.org>
+Date: Tue, 10 Apr 2018 15:27:51 +0100
+Subject: [PATCH 271/454] net: lan78xx: Add support for VLAN tag stripping.
+
+The chip supports stripping the VLAN tag and reporting it
+in metadata. Implement this as it also appears to solve the
+issues observed in checksum computation.
+
+See #2458.
+
+Signed-off-by: Dave Stevenson <dave.stevenson@raspberrypi.org>
+---
+ drivers/net/usb/lan78xx.c | 22 ++++++++++++++++++++++
+ 1 file changed, 22 insertions(+)
+
+--- a/drivers/net/usb/lan78xx.c
++++ b/drivers/net/usb/lan78xx.c
+@@ -64,6 +64,7 @@
+ #define DEFAULT_RX_CSUM_ENABLE                (true)
+ #define DEFAULT_TSO_CSUM_ENABLE               (true)
+ #define DEFAULT_VLAN_FILTER_ENABLE    (true)
++#define DEFAULT_VLAN_RX_OFFLOAD               (true)
+ #define TX_OVERHEAD                   (8)
+ #define RXW_PADDING                   2
+@@ -2275,6 +2276,11 @@ static int lan78xx_set_features(struct n
+               pdata->rfe_ctl &= ~(RFE_CTL_ICMP_COE_ | RFE_CTL_IGMP_COE_);
+       }
++      if (features & NETIF_F_HW_VLAN_CTAG_RX)
++              pdata->rfe_ctl |= RFE_CTL_VLAN_STRIP_;
++      else
++              pdata->rfe_ctl &= ~RFE_CTL_VLAN_STRIP_;
++
+       if (features & NETIF_F_HW_VLAN_CTAG_FILTER)
+               pdata->rfe_ctl |= RFE_CTL_VLAN_FILTER_;
+       else
+@@ -2888,6 +2894,9 @@ static int lan78xx_bind(struct lan78xx_n
+       if (DEFAULT_TSO_CSUM_ENABLE)
+               dev->net->features |= NETIF_F_TSO | NETIF_F_TSO6 | NETIF_F_SG;
++      if (DEFAULT_VLAN_RX_OFFLOAD)
++              dev->net->features |= NETIF_F_HW_VLAN_CTAG_RX;
++
+       if (DEFAULT_VLAN_FILTER_ENABLE)
+               dev->net->features |= NETIF_F_HW_VLAN_CTAG_FILTER;
+@@ -2968,6 +2977,16 @@ static void lan78xx_rx_csum_offload(stru
+       }
+ }
++static void lan78xx_rx_vlan_offload(struct lan78xx_net *dev,
++                                  struct sk_buff *skb,
++                                  u32 rx_cmd_a, u32 rx_cmd_b)
++{
++      if ((dev->net->features & NETIF_F_HW_VLAN_CTAG_RX) &&
++          (rx_cmd_a & RX_CMD_A_FVTG_))
++              __vlan_hwaccel_put_tag(skb, htons(ETH_P_8021Q),
++                                     (rx_cmd_b & 0xffff));
++}
++
+ static void lan78xx_skb_return(struct lan78xx_net *dev, struct sk_buff *skb)
+ {
+       int             status;
+@@ -3032,6 +3051,8 @@ static int lan78xx_rx(struct lan78xx_net
+                       if (skb->len == size) {
+                               lan78xx_rx_csum_offload(dev, skb,
+                                                       rx_cmd_a, rx_cmd_b);
++                              lan78xx_rx_vlan_offload(dev, skb,
++                                                      rx_cmd_a, rx_cmd_b);
+                               skb_trim(skb, skb->len - 4); /* remove fcs */
+                               skb->truesize = size + sizeof(struct sk_buff);
+@@ -3050,6 +3071,7 @@ static int lan78xx_rx(struct lan78xx_net
+                       skb_set_tail_pointer(skb2, size);
+                       lan78xx_rx_csum_offload(dev, skb2, rx_cmd_a, rx_cmd_b);
++                      lan78xx_rx_vlan_offload(dev, skb2, rx_cmd_a, rx_cmd_b);
+                       skb_trim(skb2, skb2->len - 4); /* remove fcs */
+                       skb2->truesize = size + sizeof(struct sk_buff);