diff options
author | Johannes Berg <johannes.berg@intel.com> | 2014-09-08 10:42:54 -0400 |
---|---|---|
committer | Emmanuel Grumbach <emmanuel.grumbach@intel.com> | 2014-09-14 05:56:40 -0400 |
commit | b2b7875bfb6c69bb708b61c5f745491d240161a1 (patch) | |
tree | 96a4defff20dfee2724407355493b9705f7a5667 | |
parent | bbab758279a14556e6ccb17b1f98935634eeb8d5 (diff) |
iwlwifi: mvm: don't update quota in firmware too often
When updating quota in the firmware, it has to reset quite a bit
of internal state, which apparently can have an adverse impact on
its operation.
Avoid that by only updating the quota command when there are any
signification changes, i.e. added/removed bindings or changes in
quota that are bigger than 8 TU within a binding.
Signed-off-by: Johannes Berg <johannes.berg@intel.com>
Signed-off-by: Emmanuel Grumbach <emmanuel.grumbach@intel.com>
-rw-r--r-- | drivers/net/wireless/iwlwifi/mvm/constants.h | 1 | ||||
-rw-r--r-- | drivers/net/wireless/iwlwifi/mvm/fw.c | 3 | ||||
-rw-r--r-- | drivers/net/wireless/iwlwifi/mvm/mvm.h | 2 | ||||
-rw-r--r-- | drivers/net/wireless/iwlwifi/mvm/quota.c | 33 |
4 files changed, 33 insertions, 6 deletions
diff --git a/drivers/net/wireless/iwlwifi/mvm/constants.h b/drivers/net/wireless/iwlwifi/mvm/constants.h index cb48656a8eaf..118108929a87 100644 --- a/drivers/net/wireless/iwlwifi/mvm/constants.h +++ b/drivers/net/wireless/iwlwifi/mvm/constants.h | |||
@@ -87,5 +87,6 @@ | |||
87 | #define IWL_MVM_BT_COEX_CORUNNING 1 | 87 | #define IWL_MVM_BT_COEX_CORUNNING 1 |
88 | #define IWL_MVM_BT_COEX_MPLUT 1 | 88 | #define IWL_MVM_BT_COEX_MPLUT 1 |
89 | #define IWL_MVM_FW_MCAST_FILTER_PASS_ALL 0 | 89 | #define IWL_MVM_FW_MCAST_FILTER_PASS_ALL 0 |
90 | #define IWL_MVM_QUOTA_THRESHOLD 8 | ||
90 | 91 | ||
91 | #endif /* __MVM_CONSTANTS_H */ | 92 | #endif /* __MVM_CONSTANTS_H */ |
diff --git a/drivers/net/wireless/iwlwifi/mvm/fw.c b/drivers/net/wireless/iwlwifi/mvm/fw.c index 21d606028ca6..23fd711a67e4 100644 --- a/drivers/net/wireless/iwlwifi/mvm/fw.c +++ b/drivers/net/wireless/iwlwifi/mvm/fw.c | |||
@@ -454,6 +454,9 @@ int iwl_mvm_up(struct iwl_mvm *mvm) | |||
454 | for (i = 0; i < IWL_MVM_STATION_COUNT; i++) | 454 | for (i = 0; i < IWL_MVM_STATION_COUNT; i++) |
455 | RCU_INIT_POINTER(mvm->fw_id_to_mac_id[i], NULL); | 455 | RCU_INIT_POINTER(mvm->fw_id_to_mac_id[i], NULL); |
456 | 456 | ||
457 | /* reset quota debouncing buffer - 0xff will yield invalid data */ | ||
458 | memset(&mvm->last_quota_cmd, 0xff, sizeof(mvm->last_quota_cmd)); | ||
459 | |||
457 | /* Add auxiliary station for scanning */ | 460 | /* Add auxiliary station for scanning */ |
458 | ret = iwl_mvm_add_aux_sta(mvm); | 461 | ret = iwl_mvm_add_aux_sta(mvm); |
459 | if (ret) | 462 | if (ret) |
diff --git a/drivers/net/wireless/iwlwifi/mvm/mvm.h b/drivers/net/wireless/iwlwifi/mvm/mvm.h index e292de96e09a..f05b7d7bcae3 100644 --- a/drivers/net/wireless/iwlwifi/mvm/mvm.h +++ b/drivers/net/wireless/iwlwifi/mvm/mvm.h | |||
@@ -709,6 +709,8 @@ struct iwl_mvm { | |||
709 | */ | 709 | */ |
710 | bool temperature_test; /* Debug test temperature is enabled */ | 710 | bool temperature_test; /* Debug test temperature is enabled */ |
711 | 711 | ||
712 | struct iwl_time_quota_cmd last_quota_cmd; | ||
713 | |||
712 | #ifdef CONFIG_NL80211_TESTMODE | 714 | #ifdef CONFIG_NL80211_TESTMODE |
713 | u32 noa_duration; | 715 | u32 noa_duration; |
714 | struct ieee80211_vif *noa_vif; | 716 | struct ieee80211_vif *noa_vif; |
diff --git a/drivers/net/wireless/iwlwifi/mvm/quota.c b/drivers/net/wireless/iwlwifi/mvm/quota.c index 5fd502db03d1..1eab2f2fee5d 100644 --- a/drivers/net/wireless/iwlwifi/mvm/quota.c +++ b/drivers/net/wireless/iwlwifi/mvm/quota.c | |||
@@ -175,12 +175,14 @@ int iwl_mvm_update_quotas(struct iwl_mvm *mvm, | |||
175 | struct ieee80211_vif *disabled_vif) | 175 | struct ieee80211_vif *disabled_vif) |
176 | { | 176 | { |
177 | struct iwl_time_quota_cmd cmd = {}; | 177 | struct iwl_time_quota_cmd cmd = {}; |
178 | int i, idx, ret, num_active_macs, quota, quota_rem, n_non_lowlat; | 178 | int i, idx, err, num_active_macs, quota, quota_rem, n_non_lowlat; |
179 | struct iwl_mvm_quota_iterator_data data = { | 179 | struct iwl_mvm_quota_iterator_data data = { |
180 | .n_interfaces = {}, | 180 | .n_interfaces = {}, |
181 | .colors = { -1, -1, -1, -1 }, | 181 | .colors = { -1, -1, -1, -1 }, |
182 | .disabled_vif = disabled_vif, | 182 | .disabled_vif = disabled_vif, |
183 | }; | 183 | }; |
184 | struct iwl_time_quota_cmd *last = &mvm->last_quota_cmd; | ||
185 | bool send = false; | ||
184 | 186 | ||
185 | lockdep_assert_held(&mvm->mutex); | 187 | lockdep_assert_held(&mvm->mutex); |
186 | 188 | ||
@@ -293,15 +295,34 @@ int iwl_mvm_update_quotas(struct iwl_mvm *mvm, | |||
293 | 295 | ||
294 | /* check that we have non-zero quota for all valid bindings */ | 296 | /* check that we have non-zero quota for all valid bindings */ |
295 | for (i = 0; i < MAX_BINDINGS; i++) { | 297 | for (i = 0; i < MAX_BINDINGS; i++) { |
298 | if (cmd.quotas[i].id_and_color != last->quotas[i].id_and_color) | ||
299 | send = true; | ||
300 | if (cmd.quotas[i].max_duration != last->quotas[i].max_duration) | ||
301 | send = true; | ||
302 | if (abs((int)le32_to_cpu(cmd.quotas[i].quota) - | ||
303 | (int)le32_to_cpu(last->quotas[i].quota)) | ||
304 | > IWL_MVM_QUOTA_THRESHOLD) | ||
305 | send = true; | ||
296 | if (cmd.quotas[i].id_and_color == cpu_to_le32(FW_CTXT_INVALID)) | 306 | if (cmd.quotas[i].id_and_color == cpu_to_le32(FW_CTXT_INVALID)) |
297 | continue; | 307 | continue; |
298 | WARN_ONCE(cmd.quotas[i].quota == 0, | 308 | WARN_ONCE(cmd.quotas[i].quota == 0, |
299 | "zero quota on binding %d\n", i); | 309 | "zero quota on binding %d\n", i); |
300 | } | 310 | } |
301 | 311 | ||
302 | ret = iwl_mvm_send_cmd_pdu(mvm, TIME_QUOTA_CMD, 0, | 312 | if (send) { |
303 | sizeof(cmd), &cmd); | 313 | err = iwl_mvm_send_cmd_pdu(mvm, TIME_QUOTA_CMD, 0, |
304 | if (ret) | 314 | sizeof(cmd), &cmd); |
305 | IWL_ERR(mvm, "Failed to send quota: %d\n", ret); | 315 | } else { |
306 | return ret; | 316 | /* don't send a practically unchanged command, the firmware has |
317 | * to re-initialize a lot of state and that can have an adverse | ||
318 | * impact on it | ||
319 | */ | ||
320 | err = 0; | ||
321 | } | ||
322 | |||
323 | if (err) | ||
324 | IWL_ERR(mvm, "Failed to send quota: %d\n", err); | ||
325 | else | ||
326 | mvm->last_quota_cmd = cmd; | ||
327 | return err; | ||
307 | } | 328 | } |