From 24b960c5c01dfc06832db9d6bf5e05b8ad333972 Mon Sep 17 00:00:00 2001 From: Larry Finger Date: Wed, 20 Jul 2022 15:20:33 -0500 Subject: [PATCH] rtl8188eu: Change some locking around rtw_get_sec_ie() Routine rtw_get_sec_ie() appears to suffer from a bug triggered under unusual circumstances. This bug is exposed by first sending a deauthentication frame and at the same time sending a much larger frame. After doing some debugging the cause of the lockup of the CPU was that while rtw_get_sec_ie() attempts to read the beacon frame sent by the router/AP, the size of the beacon is changed since it is a reference and not a copy. By having a "rogue" beacon frame being very large which isn't normal and not considered in the design, the computer was stuck in an endless CPU lockup. Routine translate_scan(), which calls rtw_get_sec_ie() is protected by a spinlock. Add that spinlock around other calls of the routine. Signed-off-by: Larry Finger --- core/rtw_ieee80211.c | 2 +- core/rtw_mlme_ext.c | 2 ++ core/rtw_wlan_util.c | 3 +++ core/rtw_xmit.c | 1 - 4 files changed, 6 insertions(+), 2 deletions(-) diff --git a/core/rtw_ieee80211.c b/core/rtw_ieee80211.c index fe21ae2..a149e49 100644 --- a/core/rtw_ieee80211.c +++ b/core/rtw_ieee80211.c @@ -658,7 +658,7 @@ int rtw_parse_wpa2_ie(u8 *rsn_ie, int rsn_ie_len, int *group_cipher, int *pairwi int rtw_get_sec_ie(u8 *in_ie, uint in_len, u8 *rsn_ie, u16 *rsn_len, u8 *wpa_ie, u16 *wpa_len) { u8 authmode, sec_idx; - int i; + u8 i; u8 wpa_oui[4] = {0x0, 0x50, 0xf2, 0x01}; uint cnt; diff --git a/core/rtw_mlme_ext.c b/core/rtw_mlme_ext.c index 1c9c448..53a729b 100644 --- a/core/rtw_mlme_ext.c +++ b/core/rtw_mlme_ext.c @@ -683,7 +683,9 @@ unsigned int OnBeacon(struct adapter *padapter, struct recv_frame *precv_frame) if (pbss) { if (collect_bss_info(padapter, precv_frame, pbss) == _SUCCESS) { update_network(&(pmlmepriv->cur_network.network), pbss, padapter, true); + spin_lock_bh(&padapter->mlmepriv.scanned_queue.lock); rtw_get_bcn_info(&(pmlmepriv->cur_network)); + spin_unlock_bh(&padapter->mlmepriv.scanned_queue.lock); } kfree(pbss); } diff --git a/core/rtw_wlan_util.c b/core/rtw_wlan_util.c index 8869e15..427dc6f 100644 --- a/core/rtw_wlan_util.c +++ b/core/rtw_wlan_util.c @@ -946,6 +946,7 @@ int rtw_check_bcn_info(struct adapter *Adapter, u8 *pframe, u32 packet_len) bssid->Length = sizeof(struct wlan_bssid_ex) - MAX_IE_SZ + len; + spin_lock_bh(&Adapter->mlmepriv.scanned_queue.lock); /* below is to copy the information element */ bssid->IELength = len; memcpy(bssid->IEs, (pframe + sizeof(struct rtw_ieee80211_hdr_3addr)), bssid->IELength); @@ -1047,6 +1048,7 @@ int rtw_check_bcn_info(struct adapter *Adapter, u8 *pframe, u32 packet_len) } rtw_get_sec_ie(bssid->IEs, bssid->IELength, NULL, &rsn_len, NULL, &wpa_len); + spin_unlock_bh(&Adapter->mlmepriv.scanned_queue.lock); if (rsn_len > 0) { encryp_protocol = ENCRYP_PROTOCOL_WPA2; @@ -1102,6 +1104,7 @@ int rtw_check_bcn_info(struct adapter *Adapter, u8 *pframe, u32 packet_len) return _SUCCESS; _mismatch: + spin_unlock_bh(&Adapter->mlmepriv.scanned_queue.lock); kfree(bssid); return _FAIL; diff --git a/core/rtw_xmit.c b/core/rtw_xmit.c index c5bc791..89eabae 100644 --- a/core/rtw_xmit.c +++ b/core/rtw_xmit.c @@ -218,7 +218,6 @@ s32 _rtw_init_xmit_priv(struct xmit_priv *pxmitpriv, struct adapter *padapter) pxmitpriv->ack_tx = false; _rtw_mutex_init(&pxmitpriv->ack_tx_mutex); rtw_sctx_init(&pxmitpriv->ack_tx_ops, 0); - rtw_hal_init_xmit_priv(padapter); exit: