@@ -142,6 +142,7 @@
#include <linux/net_namespace.h>
#include <linux/indirect_call_wrapper.h>
#include <net/devlink.h>
+#include <net/dsa.h>
#include "net-sysfs.h"
@@ -5951,6 +5952,7 @@ static gro_result_t napi_frags_finish(struct napi_struct *napi,
*/
static struct sk_buff *napi_frags_skb(struct napi_struct *napi)
{
+ struct net_device *dev = napi->dev;
struct sk_buff *skb = napi->skb;
const struct ethhdr *eth;
unsigned int hlen = sizeof(*eth);
@@ -5964,7 +5966,7 @@ static struct sk_buff *napi_frags_skb(struct napi_struct *napi)
eth = skb_gro_header_slow(skb, hlen, 0);
if (unlikely(!eth)) {
net_warn_ratelimited("%s: dropping impossible skb from %s\n",
- __func__, napi->dev->name);
+ __func__, dev->name);
napi_reuse_skb(napi, skb);
return NULL;
}
@@ -5978,10 +5980,13 @@ static struct sk_buff *napi_frags_skb(struct napi_struct *napi)
/*
* This works because the only protocols we care about don't require
- * special handling.
+ * special handling... except for DSA.
* We'll fix it up properly in napi_frags_finish()
*/
- skb->protocol = eth->h_proto;
+ if (unlikely(netdev_uses_dsa(dev)) && dsa_can_decode(skb, dev))
+ skb->protocol = htons(ETH_P_XDSA);
+ else
+ skb->protocol = eth->h_proto;
return skb;
}
Make napi_gro_frags() available for DSA-enabled device drivers by adding the same condition for them as the one in eth_type_trans(). Signed-off-by: Alexander Lobakin <alobakin@dlink.ru> --- net/core/dev.c | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-)