diff options
author | Felix Fietkau <nbd@nbd.name> | 2022-05-06 15:49:58 +0200 |
---|---|---|
committer | Felix Fietkau <nbd@nbd.name> | 2022-05-06 21:47:53 +0200 |
commit | b5f25d43b7e8eb78bde9659b3ecb651ee5e2f5be (patch) | |
tree | 473672e3c43b13450888c01135141c15b6aa4084 /target/linux/generic/pending-5.10 | |
parent | 726ef8ba2dbe4d4a693c4d9300bc69e234e6d67d (diff) | |
download | upstream-b5f25d43b7e8eb78bde9659b3ecb651ee5e2f5be.tar.gz upstream-b5f25d43b7e8eb78bde9659b3ecb651ee5e2f5be.tar.bz2 upstream-b5f25d43b7e8eb78bde9659b3ecb651ee5e2f5be.zip |
kernel: backport flow offload fixes to 5.10
Signed-off-by: Felix Fietkau <nbd@nbd.name>
Diffstat (limited to 'target/linux/generic/pending-5.10')
4 files changed, 181 insertions, 0 deletions
diff --git a/target/linux/generic/pending-5.10/704-00-netfilter-flowtable-fix-excessive-hw-offload-attempt.patch b/target/linux/generic/pending-5.10/704-00-netfilter-flowtable-fix-excessive-hw-offload-attempt.patch new file mode 100644 index 0000000000..c15f090f71 --- /dev/null +++ b/target/linux/generic/pending-5.10/704-00-netfilter-flowtable-fix-excessive-hw-offload-attempt.patch @@ -0,0 +1,27 @@ +From: Felix Fietkau <nbd@nbd.name> +Date: Fri, 6 May 2022 12:37:23 +0200 +Subject: [PATCH] netfilter: flowtable: fix excessive hw offload attempts + after failure + +If a flow cannot be offloaded, the code currently repeatedly tries again as +quickly as possible, which can significantly increase system load. +Fix this by limiting flow timeout update and hardware offload retry to once +per second. + +Signed-off-by: Felix Fietkau <nbd@nbd.name> +--- + +--- a/net/netfilter/nf_flow_table_core.c ++++ b/net/netfilter/nf_flow_table_core.c +@@ -331,8 +331,10 @@ void flow_offload_refresh(struct nf_flow + u32 timeout; + + timeout = nf_flowtable_time_stamp + flow_offload_get_timeout(flow); +- if (READ_ONCE(flow->timeout) != timeout) ++ if (timeout - READ_ONCE(flow->timeout) > HZ) + WRITE_ONCE(flow->timeout, timeout); ++ else ++ return; + + if (likely(!nf_flowtable_hw_offload(flow_table))) + return; diff --git a/target/linux/generic/pending-5.10/704-01-netfilter-nft_flow_offload-skip-dst-neigh-lookup-for.patch b/target/linux/generic/pending-5.10/704-01-netfilter-nft_flow_offload-skip-dst-neigh-lookup-for.patch new file mode 100644 index 0000000000..6683a53f76 --- /dev/null +++ b/target/linux/generic/pending-5.10/704-01-netfilter-nft_flow_offload-skip-dst-neigh-lookup-for.patch @@ -0,0 +1,64 @@ +From: Felix Fietkau <nbd@nbd.name> +Date: Fri, 6 May 2022 12:43:58 +0200 +Subject: [PATCH] netfilter: nft_flow_offload: skip dst neigh lookup for + ppp devices + +The dst entry does not contain a valid hardware address, so skip the lookup +in order to avoid running into errors here. +The proper hardware address is filled in from nft_dev_path_info + +Signed-off-by: Felix Fietkau <nbd@nbd.name> +--- + +--- a/net/netfilter/nft_flow_offload.c ++++ b/net/netfilter/nft_flow_offload.c +@@ -36,6 +36,15 @@ static void nft_default_forward_path(str + route->tuple[dir].xmit_type = nft_xmit_type(dst_cache); + } + ++static bool nft_is_valid_ether_device(const struct net_device *dev) ++{ ++ if (!dev || (dev->flags & IFF_LOOPBACK) || dev->type != ARPHRD_ETHER || ++ dev->addr_len != ETH_ALEN || !is_valid_ether_addr(dev->dev_addr)) ++ return false; ++ ++ return true; ++} ++ + static int nft_dev_fill_forward_path(const struct nf_flow_route *route, + const struct dst_entry *dst_cache, + const struct nf_conn *ct, +@@ -47,6 +56,9 @@ static int nft_dev_fill_forward_path(con + struct neighbour *n; + u8 nud_state; + ++ if (!nft_is_valid_ether_device(dev)) ++ goto out; ++ + n = dst_neigh_lookup(dst_cache, daddr); + if (!n) + return -1; +@@ -60,6 +72,7 @@ static int nft_dev_fill_forward_path(con + if (!(nud_state & NUD_VALID)) + return -1; + ++out: + return dev_fill_forward_path(dev, ha, stack); + } + +@@ -78,15 +91,6 @@ struct nft_forward_info { + enum flow_offload_xmit_type xmit_type; + }; + +-static bool nft_is_valid_ether_device(const struct net_device *dev) +-{ +- if (!dev || (dev->flags & IFF_LOOPBACK) || dev->type != ARPHRD_ETHER || +- dev->addr_len != ETH_ALEN || !is_valid_ether_addr(dev->dev_addr)) +- return false; +- +- return true; +-} +- + static void nft_dev_path_info(const struct net_device_path_stack *stack, + struct nft_forward_info *info, + unsigned char *ha, struct nf_flowtable *flowtable) diff --git a/target/linux/generic/pending-5.10/704-02-net-fix-dev_fill_forward_path-with-pppoe-bridge.patch b/target/linux/generic/pending-5.10/704-02-net-fix-dev_fill_forward_path-with-pppoe-bridge.patch new file mode 100644 index 0000000000..04698f6d80 --- /dev/null +++ b/target/linux/generic/pending-5.10/704-02-net-fix-dev_fill_forward_path-with-pppoe-bridge.patch @@ -0,0 +1,66 @@ +From: Felix Fietkau <nbd@nbd.name> +Date: Fri, 6 May 2022 13:54:44 +0200 +Subject: [PATCH] net: fix dev_fill_forward_path with pppoe + bridge + +When calling dev_fill_forward_path on a pppoe device, the provided destination +address is invalid. In order for the bridge fdb lookup to succeed, the pppoe +code needs to update ctx->daddr to the correct value. +Fix this by storing the address inside struct net_device_path_ctx + +Signed-off-by: Felix Fietkau <nbd@nbd.name> +--- + +--- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c ++++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c +@@ -91,7 +91,6 @@ mtk_flow_get_wdma_info(struct net_device + { + struct net_device_path_ctx ctx = { + .dev = dev, +- .daddr = addr, + }; + struct net_device_path path = {}; + +@@ -101,6 +100,7 @@ mtk_flow_get_wdma_info(struct net_device + if (!dev->netdev_ops->ndo_fill_forward_path) + return -1; + ++ memcpy(ctx.daddr, addr, sizeof(ctx.daddr)); + if (dev->netdev_ops->ndo_fill_forward_path(&ctx, &path)) + return -1; + +--- a/drivers/net/ppp/pppoe.c ++++ b/drivers/net/ppp/pppoe.c +@@ -988,6 +988,7 @@ static int pppoe_fill_forward_path(struc + path->encap.proto = htons(ETH_P_PPP_SES); + path->encap.id = be16_to_cpu(po->num); + memcpy(path->encap.h_dest, po->pppoe_pa.remote, ETH_ALEN); ++ memcpy(ctx->daddr, po->pppoe_pa.remote, ETH_ALEN); + path->dev = ctx->dev; + ctx->dev = dev; + +--- a/include/linux/netdevice.h ++++ b/include/linux/netdevice.h +@@ -878,7 +878,7 @@ struct net_device_path_stack { + + struct net_device_path_ctx { + const struct net_device *dev; +- const u8 *daddr; ++ u8 daddr[ETH_ALEN]; + + int num_vlans; + struct { +--- a/net/core/dev.c ++++ b/net/core/dev.c +@@ -863,11 +863,11 @@ int dev_fill_forward_path(const struct n + const struct net_device *last_dev; + struct net_device_path_ctx ctx = { + .dev = dev, +- .daddr = daddr, + }; + struct net_device_path *path; + int ret = 0; + ++ memcpy(ctx.daddr, daddr, sizeof(ctx.daddr)); + stack->num_paths = 0; + while (ctx.dev && ctx.dev->netdev_ops->ndo_fill_forward_path) { + last_dev = ctx.dev; diff --git a/target/linux/generic/pending-5.10/704-03-netfilter-nft_flow_offload-fix-offload-with-pppoe-vl.patch b/target/linux/generic/pending-5.10/704-03-netfilter-nft_flow_offload-fix-offload-with-pppoe-vl.patch new file mode 100644 index 0000000000..1e0dc9957d --- /dev/null +++ b/target/linux/generic/pending-5.10/704-03-netfilter-nft_flow_offload-fix-offload-with-pppoe-vl.patch @@ -0,0 +1,24 @@ +From: Felix Fietkau <nbd@nbd.name> +Date: Fri, 6 May 2022 15:15:06 +0200 +Subject: [PATCH] netfilter: nft_flow_offload: fix offload with pppoe + + vlan + +When running a combination of PPPoE on top of a VLAN, we need to set +info->outdev to the PPPoE device, otherwise PPPoE encap is skipped +during software offload. + +Signed-off-by: Felix Fietkau <nbd@nbd.name> +--- + +--- a/net/netfilter/nft_flow_offload.c ++++ b/net/netfilter/nft_flow_offload.c +@@ -123,7 +123,8 @@ static void nft_dev_path_info(const stru + info->indev = NULL; + break; + } +- info->outdev = path->dev; ++ if (!info->outdev) ++ info->outdev = path->dev; + info->encap[info->num_encaps].id = path->encap.id; + info->encap[info->num_encaps].proto = path->encap.proto; + info->num_encaps++; |