immortalwrt-VIKINGYFY/package/kernel/mac80211/patches/nss/subsys/657-mac80211-Avoid-encapsulation-of-EAPOL-frames-if-OFFL.patch
2025-12-09 20:09:13 +08:00

205 lines
7.5 KiB
Diff
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

From f2c96599c02eb0d47602d000fe0f40358c10c892 Mon Sep 17 00:00:00 2001
From: Aaradhana Sahu <quic_aarasahu@quicinc.com>
Date: Fri, 26 Aug 2022 17:54:37 +0530
Subject: [PATCH] mac80211: Avoid encapsulation of EAPOL frames if OFFLOAD_ENCAP is enabled
EAP Frames over NL80211 Control port are 802.11 Native WiFi
encapsulated by default, but for a vdev operating in 802.3, when FW doesnt
advertise WMI_SERVICE_EAPOL_OVER_NWIFI, it cannot accept an 802.11
Native WiFi frame.
Allow EAP Frames over NL80211 Control port to be passed as 802.3
if vif has IEEE80211_OFFLOAD_ENCAP_ENABLED set.
Signed-off-by: Rameshkumar Sundaram <quic_ramess@quicinc.com>
Signed-off-by: Aaradhana Sahu <quic_aarasahu@quicinc.com>
---
net/mac80211/ieee80211_i.h | 5 ++++
net/mac80211/tx.c | 58 ++++++++++++++++++++++++++------------
2 files changed, 45 insertions(+), 18 deletions(-)
--- a/net/mac80211/ieee80211_i.h
+++ b/net/mac80211/ieee80211_i.h
@@ -2167,6 +2167,11 @@ netdev_tx_t ieee80211_subif_start_xmit(s
struct net_device *dev);
netdev_tx_t ieee80211_subif_start_xmit_8023(struct sk_buff *skb,
struct net_device *dev);
+netdev_tx_t __ieee80211_subif_start_xmit_8023(struct sk_buff *skb,
+ struct net_device *dev,
+ u32 info_flags,
+ u32 ctrl_flags,
+ u64 *cookie);
void __ieee80211_subif_start_xmit(struct sk_buff *skb,
struct net_device *dev,
u32 info_flags,
--- a/net/mac80211/tx.c
+++ b/net/mac80211/tx.c
@@ -40,7 +40,8 @@
static void ieee80211_8023_xmit(struct ieee80211_sub_if_data *sdata,
struct net_device *dev, struct sta_info *sta,
- struct ieee80211_key *key, struct sk_buff *skb);
+ struct ieee80211_key *key, struct sk_buff *skb,
+ u32 info_flags, u32 ctrl_flags, u64 *cookie);
/* misc utils */
static __le16 ieee80211_duration(struct ieee80211_tx_data *tx,
@@ -4347,7 +4348,7 @@ void __ieee80211_subif_start_xmit(struct
!is_multicast_ether_addr(skb->data)) {
if (sta)
key = rcu_dereference(sta->ptk[sta->ptk_idx]);
- ieee80211_8023_xmit(sdata, dev, sta, key, skb);
+ ieee80211_8023_xmit(sdata, dev, sta, key, skb, info_flags, ctrl_flags, cookie);
rcu_read_unlock();
return;
}
@@ -4393,7 +4394,7 @@ void __ieee80211_subif_start_xmit(struct
if (info->flags & IEEE80211_TX_CTL_HW_80211_ENCAP) {
if (sta)
key = rcu_dereference(sta->ptk[sta->ptk_idx]);
- ieee80211_8023_xmit(sdata, dev, sta, key, skb);
+ ieee80211_8023_xmit(sdata, dev, sta, key, skb, info_flags, ctrl_flags, cookie);
} else {
dev_sw_netstats_tx_add(dev, 1, skb->len);
ieee80211_xmit(sdata, sta, skb);
@@ -4695,7 +4696,8 @@ static bool ieee80211_tx_8023(struct iee
static void ieee80211_8023_xmit(struct ieee80211_sub_if_data *sdata,
struct net_device *dev, struct sta_info *sta,
- struct ieee80211_key *key, struct sk_buff *skb)
+ struct ieee80211_key *key, struct sk_buff *skb,
+ u32 info_flags, u32 ctrl_flags, u64 *cookie)
{
struct ieee80211_tx_info *info;
struct ethhdr *ehdr = (struct ethhdr *)skb->data;
@@ -4751,6 +4753,7 @@ static void ieee80211_8023_xmit(struct i
info = IEEE80211_SKB_CB(skb);
memset(info, 0, sizeof(*info));
+ info->flags |= info_flags;
info->hw_queue = sdata->vif.hw_queue[queue];
if (sdata->vif.type == NL80211_IFTYPE_AP_VLAN &&
@@ -4771,10 +4774,11 @@ static void ieee80211_8023_xmit(struct i
memcpy(IEEE80211_SKB_CB(seg), info, sizeof(*info));
}
- if (unlikely(sk_requests_wifi_status(skb->sk) &&
- !ieee80211_hw_check(&local->hw, SUPPORTS_NSS_OFFLOAD))) {
+ if (unlikely((sk_requests_wifi_status(skb->sk) ||
+ ((ctrl_flags & IEEE80211_TX_CTL_REQ_TX_STATUS) && !multicast)) &&
+ !ieee80211_hw_check(&local->hw, SUPPORTS_NSS_OFFLOAD))) {
info->status_data = ieee80211_store_ack_skb(local, skb,
- &info->flags, NULL);
+ &info->flags, cookie);
if (info->status_data)
info->status_data_idr = 1;
}
@@ -4797,7 +4801,8 @@ out_free:
void ieee80211_8023_xmit_ap(struct ieee80211_sub_if_data *sdata,
struct net_device *dev, struct sta_info *sta,
- struct ieee80211_key *key, struct sk_buff *skb)
+ struct ieee80211_key *key, struct sk_buff *skb,
+ u32 info_flags, u32 ctrl_flags, u64 *cookie)
{
struct ieee80211_tx_info *info;
struct ieee80211_local *local = sdata->local;
@@ -4806,6 +4811,9 @@ void ieee80211_8023_xmit_ap(struct ieee8
unsigned long flags;
int q;
u16 q_map;
+ struct ethhdr *ehdr = (struct ethhdr *)skb->data;
+ unsigned char *ra = ehdr->h_dest;
+ bool multicast = is_multicast_ether_addr(ra);
/*
* If the skb is shared we need to obtain our own copy.
@@ -4817,11 +4825,12 @@ void ieee80211_8023_xmit_ap(struct ieee8
info = IEEE80211_SKB_CB(skb);
memset(info, 0, sizeof(*info));
+ info->flags |= info_flags;
- if (unlikely(skb->sk &&
- skb_shinfo(skb)->tx_flags & SKBTX_WIFI_STATUS))
+ if (unlikely(sk_requests_wifi_status(skb->sk) ||
+ ((ctrl_flags & IEEE80211_TX_CTL_REQ_TX_STATUS) && !multicast)))
info->status_data = ieee80211_store_ack_skb(local, skb,
- &info->flags, NULL);
+ &info->flags, cookie);
info->flags |= IEEE80211_TX_CTL_HW_80211_ENCAP;
info->control.vif = &sdata->vif;
@@ -4855,14 +4864,23 @@ void ieee80211_8023_xmit_ap(struct ieee8
drv_tx(local, &control, skb);
}
-
netdev_tx_t ieee80211_subif_start_xmit_8023(struct sk_buff *skb,
struct net_device *dev)
{
+ return __ieee80211_subif_start_xmit_8023(skb, dev, 0, 0, NULL);
+}
+
+netdev_tx_t __ieee80211_subif_start_xmit_8023(struct sk_buff *skb,
+ struct net_device *dev,
+ u32 info_flags,
+ u32 ctrl_flags,
+ u64 *cookie)
+{
struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
struct ethhdr *ehdr = (struct ethhdr *)skb->data;
struct ieee80211_key *key = NULL;
struct sta_info *sta;
+ bool is_eapol;
#ifdef CPTCFG_MAC80211_NSS_SUPPORT
ieee80211_xmit_nss_fixup(skb, dev);
@@ -4878,14 +4896,15 @@ netdev_tx_t ieee80211_subif_start_xmit_8
kfree_skb(skb);
goto out;
}
+ is_eapol = (sdata->control_port_protocol == ehdr->h_proto);
if (ieee80211_hw_check(&sdata->local->hw, SUPPORTS_NSS_OFFLOAD)) {
if (unlikely(IS_ERR_OR_NULL(sta) || !sta->uploaded))
sta = NULL;
goto tx_offload;
} else if (unlikely(IS_ERR_OR_NULL(sta) || !sta->uploaded ||
- !test_sta_flag(sta, WLAN_STA_AUTHORIZED) ||
- sdata->control_port_protocol == ehdr->h_proto))
+ (!test_sta_flag(sta, WLAN_STA_AUTHORIZED) && !is_eapol) ||
+ (is_eapol && !(sdata->vif.offload_flags & IEEE80211_OFFLOAD_ENCAP_ENABLED))))
goto skip_offload;
key = rcu_dereference(sta->ptk[sta->ptk_idx]);
@@ -4896,13 +4915,13 @@ netdev_tx_t ieee80211_subif_start_xmit_8
goto skip_offload;
if (sdata->vif.type == NL80211_IFTYPE_AP) {
- ieee80211_8023_xmit_ap(sdata, dev, sta, key, skb);
+ ieee80211_8023_xmit_ap(sdata, dev, sta, key, skb, info_flags, ctrl_flags, cookie);
goto out;
}
sk_pacing_shift_update(skb->sk, sdata->local->hw.tx_sk_pacing_shift);
tx_offload:
- ieee80211_8023_xmit(sdata, dev, sta, key, skb);
+ ieee80211_8023_xmit(sdata, dev, sta, key, skb, info_flags, ctrl_flags, cookie);
goto out;
skip_offload:
@@ -6602,7 +6621,10 @@ int ieee80211_tx_control_port(struct wip
start_xmit:
local_bh_disable();
- __ieee80211_subif_start_xmit(skb, skb->dev, flags, ctrl_flags, cookie);
+ if (sdata->vif.offload_flags & IEEE80211_OFFLOAD_ENCAP_ENABLED)
+ __ieee80211_subif_start_xmit_8023(skb, skb->dev, flags, ctrl_flags, cookie);
+ else
+ __ieee80211_subif_start_xmit(skb, skb->dev, flags, ctrl_flags, cookie);
local_bh_enable();
return 0;