Linux 内核 3.3 未向已连接的接入点注册丢失的信标

Linux Kernel 3.3 not registering missed beacons with connected Access Point

我正在使用 linux 内核 3.3(抱歉,我无法升级我的内核!)并且正在尝试使用 wpa_cli 实用程序来监控我的 WiFi 连接状态。我正在使用 Edimax WiFi 加密狗连接到无线接入点。

我希望看到这样的内容:

# wpa_cli status
Selected interface 'wlan0'
wpa_state=SCANNING
ip_address=XXX.XXX.XXX.XXX
address=XX:XX:XX:XX:XX:XX

或相同的东西,但 wpa_state=COMPLETED,取决于我的连接状态。

解析此文本输出让我可以查看我的无线连接是否处于活动状态或正在扫描。但是,我注意到在关闭我的接入点电源后 wpa_state=COMPLETED 仍在 returned。使用命令:

# iwlist wlan0 scanning

强制扫描,wpa_state 偶尔会正确,但通常 (99%) 不正确。

这是我的 /etc/wpa_supplicant.conf:

ctrl_interface=/var/run/wpa_supplicant
ap_scan=1
country=US


network={
    ssid="myssid"
    psk="mypsk"
    key_mgmt=WPA-PSK
    eap=
}

经过一些调查,我相信发生了一些奇怪的事情导致内核 return AP 列表的缓存版本。我正在使用 RTL8192cu 驱动程序。我已经看过this issue,和我的不一样

我认为问题可能出在内核的某个地方。在文件 net/mac80211/scan.c 中,在函数 ieee80211_scan_rx 的第 214 行,我看到来自我的 AP BSSbssid 出现(当 AP 有电时)并通过 ieee80211_rx_bss_put (here)。此时,它在扫描结果中被 returned 并且 wpa_supplicant 导致内核中的 MLME 层验证并与该 AP 连接。然而,在断开 AP 电源后,我从未看到 MLME 层放弃它 atomic_t 保持在 BSS 上。这导致 BSS 永远不会在函数中取消链接 cfg80211_bss_expire 在扫描结束时 (cfg80211_wext_giwscan),在文件 net/wireless/scan.c 的第 205 行 (here).

具体来说,我想知道为什么用于 "hold" a BSS 的原子在从 AP 移除电源时不会减少 - 导致 linux 错过足够的信标断开?或者,是否有一些配置 wpa_supplicant 我需要添加以使 MLME 内核层递减它保留在 BSS 上,或者这显然是内核错误?

我已经试过了:

# wpa_cli bss_expire_age 10
# wpa_cli bss_expire_count 2

并没有解决我的问题。

所以经过大量挖掘,我发现问题是因为内核的 rtlwifi 驱动程序。对我来说,看起来 rtl8192cu 驱动程序应该通过调用函数 ieee80211_beacon_loss 来负责处理丢失的信标,但该调用无处可寻。我在 rtlwifi 驱动程序中删除了对 IEEE80211_HW_BEACON_FILTER 的支持,问题已得到解决。

patch is essentially the same changes that I made, and the comments in this file 是我得出这个答案的部分原因。