From 692dbcb7ad24315830da903d5360fc59b0267cee Mon Sep 17 00:00:00 2001 From: Alexandros Couloumbis Date: Thu, 3 Sep 2020 22:20:23 +0300 Subject: [PATCH] mac80211: add back support for kernel-4.4 (need to move patches-4.4/subsys to patches/subsys directory --- .../patches-4.4/subsys/999-kernel_4-4.patch | 90 +++++++++ ...unction-for-running-rx-without-passi.patch | 180 ++++++++++++++++++ 2 files changed, 270 insertions(+) create mode 100644 package/kernel/mac80211/patches-4.4/subsys/999-kernel_4-4.patch create mode 100644 package/kernel/mac80211/patches-4.4/subsys/999-revert_307-mac80211-add-a-function-for-running-rx-without-passi.patch diff --git a/package/kernel/mac80211/patches-4.4/subsys/999-kernel_4-4.patch b/package/kernel/mac80211/patches-4.4/subsys/999-kernel_4-4.patch new file mode 100644 index 0000000000..a60bb25fa8 --- /dev/null +++ b/package/kernel/mac80211/patches-4.4/subsys/999-kernel_4-4.patch @@ -0,0 +1,90 @@ +--- a/backport-include/linux/skbuff.h ++++ b/backport-include/linux/skbuff.h +@@ -379,7 +379,8 @@ static inline struct sk_buff *__skb_peek + return list_->next; + } + +-#if !LINUX_VERSION_IN_RANGE(4,19,10, 4,20,0) ++#if !LINUX_VERSION_IN_RANGE(4,19,10, 4,20,0) && \ ++ LINUX_VERSION_IS_GEQ(4,9,0) + static inline void skb_mark_not_on_list(struct sk_buff *skb) + { + skb->next = NULL; +--- a/backport-include/linux/netdevice.h ++++ b/backport-include/linux/netdevice.h +@@ -372,7 +372,8 @@ static inline int _bp_netdev_upper_dev_l + macro_dispatcher(netdev_upper_dev_link, __VA_ARGS__)(__VA_ARGS__) + #endif + +-#if LINUX_VERSION_IS_LESS(4,19,0) ++#if LINUX_VERSION_IS_LESS(4,19,0) && \ ++ LINUX_VERSION_IS_GEQ(4,9,0) + static inline void netif_receive_skb_list(struct list_head *head) + { + struct sk_buff *skb, *next; +--- a/net/mac80211/tx.c ++++ b/net/mac80211/tx.c +@@ -3980,7 +3980,7 @@ void __ieee80211_subif_start_xmit(struct + goto out_free; + } + } +- ++#if LINUX_VERSION_IS_GEQ(4,9,0) + skb_list_walk_safe(skb, skb, next) { + skb_mark_not_on_list(skb); + +@@ -3998,6 +3998,28 @@ void __ieee80211_subif_start_xmit(struct + + ieee80211_xmit(sdata, sta, skb, 0); + } ++#else ++ next = skb; ++ while (next) { ++ skb = next; ++ next = skb->next; ++ ++ skb->prev = NULL; ++ skb->next = NULL; ++ ++ if (skb->protocol == sdata->control_port_protocol) ++ ctrl_flags |= IEEE80211_TX_CTRL_SKIP_MPATH_LOOKUP; ++ ++ skb = ieee80211_build_hdr(sdata, skb, info_flags, ++ sta, ctrl_flags, cookie); ++ if (IS_ERR(skb)) ++ goto out; ++ ++ ieee80211_tx_stats(dev, skb->len); ++ ++ ieee80211_xmit(sdata, sta, skb, 0); ++ } ++#endif + goto out; + out_free: + kfree_skb(skb); +--- a/net/mac80211/status.c ++++ b/net/mac80211/status.c +@@ -1053,9 +1053,11 @@ static void __ieee80211_tx_status(struct + * with this test... + */ + if (!local->monitors && (!send_to_cooked || !local->cooked_mntrs)) { ++#if LINUX_VERSION_IS_GEQ(4,9,0) + if (status->free_list) + list_add_tail(&skb->list, status->free_list); + else ++#endif + dev_kfree_skb(skb); + return; + } +@@ -1185,9 +1187,11 @@ free: + return; + + ieee80211_report_used_skb(local, skb, false); ++#if LINUX_VERSION_IS_GEQ(4,9,0) + if (status->free_list) + list_add_tail(&skb->list, status->free_list); + else ++#endif + dev_kfree_skb(skb); + } + EXPORT_SYMBOL(ieee80211_tx_status_ext); diff --git a/package/kernel/mac80211/patches-4.4/subsys/999-revert_307-mac80211-add-a-function-for-running-rx-without-passi.patch b/package/kernel/mac80211/patches-4.4/subsys/999-revert_307-mac80211-add-a-function-for-running-rx-without-passi.patch new file mode 100644 index 0000000000..a3a128c957 --- /dev/null +++ b/package/kernel/mac80211/patches-4.4/subsys/999-revert_307-mac80211-add-a-function-for-running-rx-without-passi.patch @@ -0,0 +1,180 @@ +diff --git a/include/net/mac80211.h b/include/net/mac80211.h +index 3af80e0..e215e9f 100644 +--- a/include/net/mac80211.h ++++ b/include/net/mac80211.h +@@ -4394,31 +4394,6 @@ void ieee80211_free_hw(struct ieee80211_hw *hw); + */ + void ieee80211_restart_hw(struct ieee80211_hw *hw); + +-/** +- * ieee80211_rx_list - receive frame and store processed skbs in a list +- * +- * Use this function to hand received frames to mac80211. The receive +- * buffer in @skb must start with an IEEE 802.11 header. In case of a +- * paged @skb is used, the driver is recommended to put the ieee80211 +- * header of the frame on the linear part of the @skb to avoid memory +- * allocation and/or memcpy by the stack. +- * +- * This function may not be called in IRQ context. Calls to this function +- * for a single hardware must be synchronized against each other. Calls to +- * this function, ieee80211_rx_ni() and ieee80211_rx_irqsafe() may not be +- * mixed for a single hardware. Must not run concurrently with +- * ieee80211_tx_status() or ieee80211_tx_status_ni(). +- * +- * This function must be called with BHs disabled and RCU read lock +- * +- * @hw: the hardware this frame came in on +- * @sta: the station the frame was received from, or %NULL +- * @skb: the buffer to receive, owned by mac80211 after this call +- * @list: the destination list +- */ +-void ieee80211_rx_list(struct ieee80211_hw *hw, struct ieee80211_sta *sta, +- struct sk_buff *skb, struct list_head *list); +- + /** + * ieee80211_rx_napi - receive frame from NAPI context + * +diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h +index b460547..35b0fe0 100644 +--- a/net/mac80211/ieee80211_i.h ++++ b/net/mac80211/ieee80211_i.h +@@ -218,7 +218,7 @@ enum ieee80211_rx_flags { + }; + + struct ieee80211_rx_data { +- struct list_head *list; ++ struct napi_struct *napi; + struct sk_buff *skb; + struct ieee80211_local *local; + struct ieee80211_sub_if_data *sdata; +diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c +index fc93b5f..ecb5af6 100644 +--- a/net/mac80211/rx.c ++++ b/net/mac80211/rx.c +@@ -2575,8 +2575,8 @@ static void ieee80211_deliver_skb_to_local_stack(struct sk_buff *skb, + memset(skb->cb, 0, sizeof(skb->cb)); + + /* deliver to local stack */ +- if (rx->list) +- list_add_tail(&skb->list, rx->list); ++ if (rx->napi) ++ napi_gro_receive(rx->napi, skb); + else + netif_receive_skb(skb); + } +@@ -3866,6 +3866,7 @@ void ieee80211_release_reorder_timeout(struct sta_info *sta, int tid) + /* This is OK -- must be QoS data frame */ + .security_idx = tid, + .seqno_idx = tid, ++ .napi = NULL, /* must be NULL to not have races */ + }; + struct tid_ampdu_rx *tid_agg_rx; + +@@ -4469,8 +4470,8 @@ static bool ieee80211_invoke_fast_rx(struct ieee80211_rx_data *rx, + /* deliver to local stack */ + skb->protocol = eth_type_trans(skb, fast_rx->dev); + memset(skb->cb, 0, sizeof(skb->cb)); +- if (rx->list) +- list_add_tail(&skb->list, rx->list); ++ if (rx->napi) ++ napi_gro_receive(rx->napi, skb); + else + netif_receive_skb(skb); + +@@ -4537,7 +4538,7 @@ static bool ieee80211_prepare_and_rx_handle(struct ieee80211_rx_data *rx, + static void __ieee80211_rx_handle_packet(struct ieee80211_hw *hw, + struct ieee80211_sta *pubsta, + struct sk_buff *skb, +- struct list_head *list) ++ struct napi_struct *napi) + { + struct ieee80211_local *local = hw_to_local(hw); + struct ieee80211_sub_if_data *sdata; +@@ -4552,7 +4553,7 @@ static void __ieee80211_rx_handle_packet(struct ieee80211_hw *hw, + memset(&rx, 0, sizeof(rx)); + rx.skb = skb; + rx.local = local; +- rx.list = list; ++ rx.napi = napi; + + if (ieee80211_is_data(fc) || ieee80211_is_mgmt(fc)) + I802_DEBUG_INC(local->dot11ReceivedFragmentCount); +@@ -4660,8 +4661,8 @@ static void __ieee80211_rx_handle_packet(struct ieee80211_hw *hw, + * This is the receive path handler. It is called by a low level driver when an + * 802.11 MPDU is received from the hardware. + */ +-void ieee80211_rx_list(struct ieee80211_hw *hw, struct ieee80211_sta *pubsta, +- struct sk_buff *skb, struct list_head *list) ++void ieee80211_rx_napi(struct ieee80211_hw *hw, struct ieee80211_sta *pubsta, ++ struct sk_buff *skb, struct napi_struct *napi) + { + struct ieee80211_local *local = hw_to_local(hw); + struct ieee80211_rate *rate = NULL; +@@ -4752,6 +4753,13 @@ void ieee80211_rx_list(struct ieee80211_hw *hw, struct ieee80211_sta *pubsta, + + status->rx_flags = 0; + ++ /* ++ * key references and virtual interfaces are protected using RCU ++ * and this requires that we are in a read-side RCU section during ++ * receive processing ++ */ ++ rcu_read_lock(); ++ + /* + * Frames with failed FCS/PLCP checksum are not returned, + * all other frames are returned without radiotap header +@@ -4759,47 +4767,23 @@ void ieee80211_rx_list(struct ieee80211_hw *hw, struct ieee80211_sta *pubsta, + * Also, frames with less than 16 bytes are dropped. + */ + skb = ieee80211_rx_monitor(local, skb, rate); +- if (!skb) ++ if (!skb) { ++ rcu_read_unlock(); + return; ++ } + + ieee80211_tpt_led_trig_rx(local, + ((struct ieee80211_hdr *)skb->data)->frame_control, + skb->len); + +- __ieee80211_rx_handle_packet(hw, pubsta, skb, list); ++ __ieee80211_rx_handle_packet(hw, pubsta, skb, napi); ++ ++ rcu_read_unlock(); + + return; + drop: + kfree_skb(skb); + } +-EXPORT_SYMBOL(ieee80211_rx_list); +- +-void ieee80211_rx_napi(struct ieee80211_hw *hw, struct ieee80211_sta *pubsta, +- struct sk_buff *skb, struct napi_struct *napi) +-{ +- struct sk_buff *tmp; +- LIST_HEAD(list); +- +- +- /* +- * key references and virtual interfaces are protected using RCU +- * and this requires that we are in a read-side RCU section during +- * receive processing +- */ +- rcu_read_lock(); +- ieee80211_rx_list(hw, pubsta, skb, &list); +- rcu_read_unlock(); +- +- if (!napi) { +- netif_receive_skb_list(&list); +- return; +- } +- +- list_for_each_entry_safe(skb, tmp, &list, list) { +- skb_list_del_init(skb); +- napi_gro_receive(napi, skb); +- } +-} + EXPORT_SYMBOL(ieee80211_rx_napi); + + /* This is a version of the rx handler that can be called from hard irq -- 2.35.1