From 12fdb4c9f41281da7753818ea4ce54d9a4ed8984 Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Fri, 30 Dec 2022 21:02:20 +0100 Subject: [PATCH] mac80211: fix receiving multicast packets on multiple sta interfaces Also fix MLO sta sdata link initialization Signed-off-by: Felix Fietkau --- ...x-initialization-of-rx-link-and-rx-l.patch | 56 ++++++++++--------- 1 file changed, 30 insertions(+), 26 deletions(-) diff --git a/package/kernel/mac80211/patches/subsys/307-wifi-mac80211-fix-initialization-of-rx-link-and-rx-l.patch b/package/kernel/mac80211/patches/subsys/307-wifi-mac80211-fix-initialization-of-rx-link-and-rx-l.patch index 857c1c84470..0201eeadb16 100644 --- a/package/kernel/mac80211/patches/subsys/307-wifi-mac80211-fix-initialization-of-rx-link-and-rx-l.patch +++ b/package/kernel/mac80211/patches/subsys/307-wifi-mac80211-fix-initialization-of-rx-link-and-rx-l.patch @@ -20,7 +20,7 @@ Signed-off-by: Felix Fietkau --- a/net/mac80211/rx.c +++ b/net/mac80211/rx.c -@@ -4067,6 +4067,56 @@ static void ieee80211_invoke_rx_handlers +@@ -4067,6 +4067,58 @@ static void ieee80211_invoke_rx_handlers #undef CALL_RXH } @@ -36,11 +36,15 @@ Signed-off-by: Felix Fietkau +static bool ieee80211_rx_data_set_link(struct ieee80211_rx_data *rx, + u8 link_id) +{ ++ rx->link_id = link_id; ++ rx->link = rcu_dereference(rx->sdata->link[link_id]); ++ ++ if (!rx->sta || !rx->sta->sta.mlo) ++ return rx->link; ++ + if (!ieee80211_rx_is_valid_sta_link_id(&rx->sta->sta, link_id)) + return false; + -+ rx->link_id = link_id; -+ rx->link = rcu_dereference(rx->sdata->link[link_id]); + rx->link_sta = rcu_dereference(rx->sta->link[link_id]); + + return rx->link && rx->link_sta; @@ -62,14 +66,12 @@ Signed-off-by: Felix Fietkau + if (!rx->sdata) + rx->sdata = sta->sdata; + rx->link_sta = &sta->deflink; -+ -+ if (link_id >= 0 && -+ !ieee80211_rx_data_set_link(rx, link_id)) -+ return false; + } + + if (link_id < 0) + rx->link = &rx->sdata->deflink; ++ else if (!ieee80211_rx_data_set_link(rx, link_id)) ++ return false; + + return true; +} @@ -77,7 +79,7 @@ Signed-off-by: Felix Fietkau /* * This function makes calls into the RX path, therefore * it has to be invoked under RCU read lock. -@@ -4075,16 +4125,19 @@ void ieee80211_release_reorder_timeout(s +@@ -4075,16 +4127,19 @@ void ieee80211_release_reorder_timeout(s { struct sk_buff_head frames; struct ieee80211_rx_data rx = { @@ -102,7 +104,7 @@ Signed-off-by: Felix Fietkau tid_agg_rx = rcu_dereference(sta->ampdu_mlme.tid_rx[tid]); if (!tid_agg_rx) -@@ -4104,10 +4157,6 @@ void ieee80211_release_reorder_timeout(s +@@ -4104,10 +4159,6 @@ void ieee80211_release_reorder_timeout(s }; drv_event_callback(rx.local, rx.sdata, &event); } @@ -113,7 +115,7 @@ Signed-off-by: Felix Fietkau ieee80211_rx_handlers(&rx, &frames); } -@@ -4123,7 +4172,6 @@ void ieee80211_mark_rx_ba_filtered_frame +@@ -4123,7 +4174,6 @@ void ieee80211_mark_rx_ba_filtered_frame /* This is OK -- must be QoS data frame */ .security_idx = tid, .seqno_idx = tid, @@ -121,7 +123,7 @@ Signed-off-by: Felix Fietkau }; int i, diff; -@@ -4134,10 +4182,8 @@ void ieee80211_mark_rx_ba_filtered_frame +@@ -4134,10 +4184,8 @@ void ieee80211_mark_rx_ba_filtered_frame sta = container_of(pubsta, struct sta_info, sta); @@ -134,7 +136,7 @@ Signed-off-by: Felix Fietkau rcu_read_lock(); tid_agg_rx = rcu_dereference(sta->ampdu_mlme.tid_rx[tid]); -@@ -4524,15 +4570,6 @@ void ieee80211_check_fast_rx_iface(struc +@@ -4524,15 +4572,6 @@ void ieee80211_check_fast_rx_iface(struc mutex_unlock(&local->sta_mtx); } @@ -150,7 +152,7 @@ Signed-off-by: Felix Fietkau static void ieee80211_rx_8023(struct ieee80211_rx_data *rx, struct ieee80211_fast_rx *fast_rx, int orig_len) -@@ -4643,7 +4680,6 @@ static bool ieee80211_invoke_fast_rx(str +@@ -4643,7 +4682,6 @@ static bool ieee80211_invoke_fast_rx(str struct sk_buff *skb = rx->skb; struct ieee80211_hdr *hdr = (void *)skb->data; struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb); @@ -158,7 +160,7 @@ Signed-off-by: Felix Fietkau int orig_len = skb->len; int hdrlen = ieee80211_hdrlen(hdr->frame_control); int snap_offs = hdrlen; -@@ -4655,7 +4691,6 @@ static bool ieee80211_invoke_fast_rx(str +@@ -4655,7 +4693,6 @@ static bool ieee80211_invoke_fast_rx(str u8 da[ETH_ALEN]; u8 sa[ETH_ALEN]; } addrs __aligned(2); @@ -166,7 +168,7 @@ Signed-off-by: Felix Fietkau struct ieee80211_sta_rx_stats *stats; /* for parallel-rx, we need to have DUP_VALIDATED, otherwise we write -@@ -4758,18 +4793,10 @@ static bool ieee80211_invoke_fast_rx(str +@@ -4758,18 +4795,10 @@ static bool ieee80211_invoke_fast_rx(str drop: dev_kfree_skb(skb); @@ -187,7 +189,7 @@ Signed-off-by: Felix Fietkau stats->dropped++; return true; -@@ -4787,8 +4814,8 @@ static bool ieee80211_prepare_and_rx_han +@@ -4787,8 +4816,8 @@ static bool ieee80211_prepare_and_rx_han struct ieee80211_local *local = rx->local; struct ieee80211_sub_if_data *sdata = rx->sdata; struct ieee80211_hdr *hdr = (void *)skb->data; @@ -198,7 +200,7 @@ Signed-off-by: Felix Fietkau rx->skb = skb; -@@ -4810,35 +4837,6 @@ static bool ieee80211_prepare_and_rx_han +@@ -4810,35 +4839,6 @@ static bool ieee80211_prepare_and_rx_han if (!ieee80211_accept_frame(rx)) return false; @@ -234,7 +236,7 @@ Signed-off-by: Felix Fietkau if (!consume) { struct skb_shared_hwtstamps *shwt; -@@ -4858,7 +4856,7 @@ static bool ieee80211_prepare_and_rx_han +@@ -4858,7 +4858,7 @@ static bool ieee80211_prepare_and_rx_han shwt->hwtstamp = skb_hwtstamps(skb)->hwtstamp; } @@ -243,7 +245,7 @@ Signed-off-by: Felix Fietkau /* translate to MLD addresses */ if (ether_addr_equal(link->conf->addr, hdr->addr1)) ether_addr_copy(hdr->addr1, rx->sdata->vif.addr); -@@ -4888,6 +4886,7 @@ static void __ieee80211_rx_handle_8023(s +@@ -4888,6 +4888,7 @@ static void __ieee80211_rx_handle_8023(s struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb); struct ieee80211_fast_rx *fast_rx; struct ieee80211_rx_data rx; @@ -251,7 +253,7 @@ Signed-off-by: Felix Fietkau memset(&rx, 0, sizeof(rx)); rx.skb = skb; -@@ -4904,12 +4903,8 @@ static void __ieee80211_rx_handle_8023(s +@@ -4904,12 +4905,8 @@ static void __ieee80211_rx_handle_8023(s if (!pubsta) goto drop; @@ -266,7 +268,7 @@ Signed-off-by: Felix Fietkau /* * TODO: Should the frame be dropped if the right link_id is not -@@ -4918,19 +4913,8 @@ static void __ieee80211_rx_handle_8023(s +@@ -4918,19 +4915,8 @@ static void __ieee80211_rx_handle_8023(s * link_id is used only for stats purpose and updating the stats on * the deflink is fine? */ @@ -288,7 +290,7 @@ Signed-off-by: Felix Fietkau fast_rx = rcu_dereference(rx.sta->fast_rx); if (!fast_rx) -@@ -4948,6 +4932,8 @@ static bool ieee80211_rx_for_interface(s +@@ -4948,6 +4934,8 @@ static bool ieee80211_rx_for_interface(s { struct link_sta_info *link_sta; struct ieee80211_hdr *hdr = (void *)skb->data; @@ -297,7 +299,7 @@ Signed-off-by: Felix Fietkau /* * Look up link station first, in case there's a -@@ -4957,24 +4943,19 @@ static bool ieee80211_rx_for_interface(s +@@ -4957,24 +4945,19 @@ static bool ieee80211_rx_for_interface(s */ link_sta = link_sta_info_get_bss(rx->sdata, hdr->addr2); if (link_sta) { @@ -330,7 +332,7 @@ Signed-off-by: Felix Fietkau return ieee80211_prepare_and_rx_handle(rx, skb, consume); } -@@ -5033,19 +5014,15 @@ static void __ieee80211_rx_handle_packet +@@ -5033,19 +5016,15 @@ static void __ieee80211_rx_handle_packet if (ieee80211_is_data(fc)) { struct sta_info *sta, *prev_sta; @@ -355,7 +357,7 @@ Signed-off-by: Felix Fietkau /* * In MLO connection, fetch the link_id using addr2 * when the driver does not pass link_id in status. -@@ -5063,7 +5040,7 @@ static void __ieee80211_rx_handle_packet +@@ -5063,7 +5042,7 @@ static void __ieee80211_rx_handle_packet if (!link_sta) goto out; @@ -364,7 +366,7 @@ Signed-off-by: Felix Fietkau } if (ieee80211_prepare_and_rx_handle(&rx, skb, true)) -@@ -5079,30 +5056,25 @@ static void __ieee80211_rx_handle_packet +@@ -5079,30 +5058,27 @@ static void __ieee80211_rx_handle_packet continue; } @@ -372,6 +374,7 @@ Signed-off-by: Felix Fietkau - !ieee80211_rx_is_valid_sta_link_id(&prev_sta->sta, - link_id)) || - (!status->link_valid && prev_sta->sta.mlo)) ++ rx.sdata = prev_sta->sdata; + if (!ieee80211_rx_data_set_sta(&rx, &prev_sta->sta, + link_id)) + goto out; @@ -392,6 +395,7 @@ Signed-off-by: Felix Fietkau - !ieee80211_rx_is_valid_sta_link_id(&prev_sta->sta, - link_id)) || - (!status->link_valid && prev_sta->sta.mlo)) ++ rx.sdata = prev_sta->sdata; + if (!ieee80211_rx_data_set_sta(&rx, &prev_sta->sta, + link_id)) goto out; -- 2.30.2