@@ -444,6 +444,8 @@ static int ieee80211_scan_state_decision(struct ieee80211_local *local,
bool tx_empty = true;
bool bad_latency;
bool listen_int_exceeded;
+ /* accounts for PM_QOS_NETWORK_LATENCY and dtim period */
+ bool latency_dtim_period_exceeded = false;
unsigned long min_beacon_int = 0;
struct ieee80211_sub_if_data *sdata;
struct ieee80211_channel *next_chan;
@@ -466,6 +468,7 @@ static int ieee80211_scan_state_decision(struct ieee80211_local *local,
if (sdata->vif.type == NL80211_IFTYPE_STATION) {
if (sdata->u.mgd.associated) {
+
associated = true;
if (sdata->vif.bss_conf.beacon_int <
@@ -511,8 +514,16 @@ static int ieee80211_scan_state_decision(struct ieee80211_local *local,
usecs_to_jiffies(min_beacon_int * 1024) *
local->hw.conf.listen_interval);
+ if (associated && local->hw.conf.max_sleep_period) {
+ latency_dtim_period_exceeded = time_after(jiffies +
+ ieee80211_scan_get_channel_time(next_chan),
+ local->leave_oper_channel_time +
+ usecs_to_jiffies(min_beacon_int * 1024) *
+ local->hw.conf.max_sleep_period);
+ }
+
if (associated && ( !tx_empty || bad_latency ||
- listen_int_exceeded))
+ listen_int_exceeded || latency_dtim_period_exceeded))
local->next_scan_state = SCAN_ENTER_OPER_CHANNEL;
else
local->next_scan_state = SCAN_SET_CHANNEL;