aboutsummaryrefslogtreecommitdiffstats
path: root/package/kernel/mac80211/patches/320-v4.17-mac80211-support-A-MSDU-in-fast-rx.patch
diff options
context:
space:
mode:
Diffstat (limited to 'package/kernel/mac80211/patches/320-v4.17-mac80211-support-A-MSDU-in-fast-rx.patch')
-rw-r--r--package/kernel/mac80211/patches/320-v4.17-mac80211-support-A-MSDU-in-fast-rx.patch256
1 files changed, 0 insertions, 256 deletions
diff --git a/package/kernel/mac80211/patches/320-v4.17-mac80211-support-A-MSDU-in-fast-rx.patch b/package/kernel/mac80211/patches/320-v4.17-mac80211-support-A-MSDU-in-fast-rx.patch
deleted file mode 100644
index 3c6d342ff1..0000000000
--- a/package/kernel/mac80211/patches/320-v4.17-mac80211-support-A-MSDU-in-fast-rx.patch
+++ /dev/null
@@ -1,256 +0,0 @@
-From: Felix Fietkau <nbd@nbd.name>
-Date: Mon, 26 Feb 2018 22:09:29 +0100
-Subject: [PATCH] mac80211: support A-MSDU in fast-rx
-
-Only works if the IV was stripped from packets. Create a smaller
-variant of ieee80211_rx_h_amsdu, which bypasses checks already done
-within the fast-rx context.
-
-Signed-off-by: Felix Fietkau <nbd@nbd.name>
----
-
---- a/net/mac80211/rx.c
-+++ b/net/mac80211/rx.c
-@@ -2358,39 +2358,17 @@ ieee80211_deliver_skb(struct ieee80211_r
- }
-
- static ieee80211_rx_result debug_noinline
--ieee80211_rx_h_amsdu(struct ieee80211_rx_data *rx)
-+__ieee80211_rx_h_amsdu(struct ieee80211_rx_data *rx, u8 data_offset)
- {
- struct net_device *dev = rx->sdata->dev;
- struct sk_buff *skb = rx->skb;
- struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data;
- __le16 fc = hdr->frame_control;
- struct sk_buff_head frame_list;
-- struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(rx->skb);
- struct ethhdr ethhdr;
- const u8 *check_da = ethhdr.h_dest, *check_sa = ethhdr.h_source;
-
-- if (unlikely(!ieee80211_is_data(fc)))
-- return RX_CONTINUE;
--
-- if (unlikely(!ieee80211_is_data_present(fc)))
-- return RX_DROP_MONITOR;
--
-- if (!(status->rx_flags & IEEE80211_RX_AMSDU))
-- return RX_CONTINUE;
--
- if (unlikely(ieee80211_has_a4(hdr->frame_control))) {
-- switch (rx->sdata->vif.type) {
-- case NL80211_IFTYPE_AP_VLAN:
-- if (!rx->sdata->u.vlan.sta)
-- return RX_DROP_UNUSABLE;
-- break;
-- case NL80211_IFTYPE_STATION:
-- if (!rx->sdata->u.mgd.use_4addr)
-- return RX_DROP_UNUSABLE;
-- break;
-- default:
-- return RX_DROP_UNUSABLE;
-- }
- check_da = NULL;
- check_sa = NULL;
- } else switch (rx->sdata->vif.type) {
-@@ -2410,15 +2388,13 @@ ieee80211_rx_h_amsdu(struct ieee80211_rx
- break;
- }
-
-- if (is_multicast_ether_addr(hdr->addr1))
-- return RX_DROP_UNUSABLE;
--
- skb->dev = dev;
- __skb_queue_head_init(&frame_list);
-
- if (ieee80211_data_to_8023_exthdr(skb, &ethhdr,
- rx->sdata->vif.addr,
-- rx->sdata->vif.type))
-+ rx->sdata->vif.type,
-+ data_offset))
- return RX_DROP_UNUSABLE;
-
- ieee80211_amsdu_to_8023s(skb, &frame_list, dev->dev_addr,
-@@ -2440,6 +2416,44 @@ ieee80211_rx_h_amsdu(struct ieee80211_rx
- return RX_QUEUED;
- }
-
-+static ieee80211_rx_result debug_noinline
-+ieee80211_rx_h_amsdu(struct ieee80211_rx_data *rx)
-+{
-+ struct sk_buff *skb = rx->skb;
-+ struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb);
-+ struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data;
-+ __le16 fc = hdr->frame_control;
-+
-+ if (!(status->rx_flags & IEEE80211_RX_AMSDU))
-+ return RX_CONTINUE;
-+
-+ if (unlikely(!ieee80211_is_data(fc)))
-+ return RX_CONTINUE;
-+
-+ if (unlikely(!ieee80211_is_data_present(fc)))
-+ return RX_DROP_MONITOR;
-+
-+ if (unlikely(ieee80211_has_a4(hdr->frame_control))) {
-+ switch (rx->sdata->vif.type) {
-+ case NL80211_IFTYPE_AP_VLAN:
-+ if (!rx->sdata->u.vlan.sta)
-+ return RX_DROP_UNUSABLE;
-+ break;
-+ case NL80211_IFTYPE_STATION:
-+ if (!rx->sdata->u.mgd.use_4addr)
-+ return RX_DROP_UNUSABLE;
-+ break;
-+ default:
-+ return RX_DROP_UNUSABLE;
-+ }
-+ }
-+
-+ if (is_multicast_ether_addr(hdr->addr1))
-+ return RX_DROP_UNUSABLE;
-+
-+ return __ieee80211_rx_h_amsdu(rx, 0);
-+}
-+
- #ifdef CPTCFG_MAC80211_MESH
- static ieee80211_rx_result
- ieee80211_rx_h_mesh_fwding(struct ieee80211_rx_data *rx)
-@@ -3889,7 +3903,8 @@ static bool ieee80211_invoke_fast_rx(str
- struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb);
- struct sta_info *sta = rx->sta;
- int orig_len = skb->len;
-- int snap_offs = ieee80211_hdrlen(hdr->frame_control);
-+ int hdrlen = ieee80211_hdrlen(hdr->frame_control);
-+ int snap_offs = hdrlen;
- struct {
- u8 snap[sizeof(rfc1042_header)];
- __be16 proto;
-@@ -3920,10 +3935,6 @@ static bool ieee80211_invoke_fast_rx(str
- (status->flag & FAST_RX_CRYPT_FLAGS) != FAST_RX_CRYPT_FLAGS)
- return false;
-
-- /* we don't deal with A-MSDU deaggregation here */
-- if (status->rx_flags & IEEE80211_RX_AMSDU)
-- return false;
--
- if (unlikely(!ieee80211_is_data_present(hdr->frame_control)))
- return false;
-
-@@ -3955,21 +3966,24 @@ static bool ieee80211_invoke_fast_rx(str
- snap_offs += IEEE80211_CCMP_HDR_LEN;
- }
-
-- if (!pskb_may_pull(skb, snap_offs + sizeof(*payload)))
-- goto drop;
-- payload = (void *)(skb->data + snap_offs);
-+ if (!(status->rx_flags & IEEE80211_RX_AMSDU)) {
-+ if (!pskb_may_pull(skb, snap_offs + sizeof(*payload)))
-+ goto drop;
-
-- if (!ether_addr_equal(payload->snap, fast_rx->rfc1042_hdr))
-- return false;
-+ payload = (void *)(skb->data + snap_offs);
-
-- /* Don't handle these here since they require special code.
-- * Accept AARP and IPX even though they should come with a
-- * bridge-tunnel header - but if we get them this way then
-- * there's little point in discarding them.
-- */
-- if (unlikely(payload->proto == cpu_to_be16(ETH_P_TDLS) ||
-- payload->proto == fast_rx->control_port_protocol))
-- return false;
-+ if (!ether_addr_equal(payload->snap, fast_rx->rfc1042_hdr))
-+ return false;
-+
-+ /* Don't handle these here since they require special code.
-+ * Accept AARP and IPX even though they should come with a
-+ * bridge-tunnel header - but if we get them this way then
-+ * there's little point in discarding them.
-+ */
-+ if (unlikely(payload->proto == cpu_to_be16(ETH_P_TDLS) ||
-+ payload->proto == fast_rx->control_port_protocol))
-+ return false;
-+ }
-
- /* after this point, don't punt to the slowpath! */
-
-@@ -3983,12 +3997,6 @@ static bool ieee80211_invoke_fast_rx(str
- }
-
- /* statistics part of ieee80211_rx_h_sta_process() */
-- stats->last_rx = jiffies;
-- stats->last_rate = sta_stats_encode_rate(status);
--
-- stats->fragments++;
-- stats->packets++;
--
- if (!(status->flag & RX_FLAG_NO_SIGNAL_VAL)) {
- stats->last_signal = status->signal;
- if (!fast_rx->uses_rss)
-@@ -4017,6 +4025,20 @@ static bool ieee80211_invoke_fast_rx(str
- if (rx->key && !ieee80211_has_protected(hdr->frame_control))
- goto drop;
-
-+ if (status->rx_flags & IEEE80211_RX_AMSDU) {
-+ if (__ieee80211_rx_h_amsdu(rx, snap_offs - hdrlen) !=
-+ RX_QUEUED)
-+ goto drop;
-+
-+ return true;
-+ }
-+
-+ stats->last_rx = jiffies;
-+ stats->last_rate = sta_stats_encode_rate(status);
-+
-+ stats->fragments++;
-+ stats->packets++;
-+
- /* do the header conversion - first grab the addresses */
- ether_addr_copy(addrs.da, skb->data + fast_rx->da_offs);
- ether_addr_copy(addrs.sa, skb->data + fast_rx->sa_offs);
---- a/include/net/cfg80211.h
-+++ b/include/net/cfg80211.h
-@@ -4331,10 +4331,12 @@ unsigned int ieee80211_get_mesh_hdrlen(s
- * of it being pushed into the SKB
- * @addr: the device MAC address
- * @iftype: the virtual interface type
-+ * @data_offset: offset of payload after the 802.11 header
- * Return: 0 on success. Non-zero on error.
- */
- int ieee80211_data_to_8023_exthdr(struct sk_buff *skb, struct ethhdr *ehdr,
-- const u8 *addr, enum nl80211_iftype iftype);
-+ const u8 *addr, enum nl80211_iftype iftype,
-+ u8 data_offset);
-
- /**
- * ieee80211_data_to_8023 - convert an 802.11 data frame to 802.3
-@@ -4346,7 +4348,7 @@ int ieee80211_data_to_8023_exthdr(struct
- static inline int ieee80211_data_to_8023(struct sk_buff *skb, const u8 *addr,
- enum nl80211_iftype iftype)
- {
-- return ieee80211_data_to_8023_exthdr(skb, NULL, addr, iftype);
-+ return ieee80211_data_to_8023_exthdr(skb, NULL, addr, iftype, 0);
- }
-
- /**
---- a/net/wireless/util.c
-+++ b/net/wireless/util.c
-@@ -419,7 +419,8 @@ unsigned int ieee80211_get_mesh_hdrlen(s
- EXPORT_SYMBOL(ieee80211_get_mesh_hdrlen);
-
- int ieee80211_data_to_8023_exthdr(struct sk_buff *skb, struct ethhdr *ehdr,
-- const u8 *addr, enum nl80211_iftype iftype)
-+ const u8 *addr, enum nl80211_iftype iftype,
-+ u8 data_offset)
- {
- struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data;
- struct {
-@@ -433,7 +434,7 @@ int ieee80211_data_to_8023_exthdr(struct
- if (unlikely(!ieee80211_is_data_present(hdr->frame_control)))
- return -1;
-
-- hdrlen = ieee80211_hdrlen(hdr->frame_control);
-+ hdrlen = ieee80211_hdrlen(hdr->frame_control) + data_offset;
- if (skb->len < hdrlen + 8)
- return -1;
-