Skip to content

Commit

Permalink
iwlwifi: mvm: update SMPS when BT gets active
Browse files Browse the repository at this point in the history
When BT traffic load gets higher, we want to avoid using the
shared antenna. In order to do so, we need to tell the AP
that we don't support MIMO any more, or at least not all
the time: in short, use the SMPS to achieve this.

Signed-off-by: Emmanuel Grumbach <emmanuel.grumbach@intel.com>
Signed-off-by: Johannes Berg <johannes.berg@intel.com>
  • Loading branch information
Emmanuel Grumbach authored and Johannes Berg committed Mar 6, 2013
1 parent f421f9c commit 7da052b
Showing 1 changed file with 52 additions and 0 deletions.
52 changes: 52 additions & 0 deletions drivers/net/wireless/iwlwifi/mvm/bt-coex.c
Original file line number Diff line number Diff line change
Expand Up @@ -242,12 +242,60 @@ int iwl_send_bt_init_conf(struct iwl_mvm *mvm)
sizeof(cmd), &cmd);
}

struct iwl_bt_notif_iterator_data {
struct iwl_mvm *mvm;
struct iwl_bt_coex_profile_notif *notif;
};

static void iwl_mvm_bt_notif_iterator(void *_data, u8 *mac,
struct ieee80211_vif *vif)
{
struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
struct iwl_bt_notif_iterator_data *data = _data;
struct ieee80211_chanctx_conf *chanctx_conf;
enum ieee80211_smps_mode smps_mode;
enum ieee80211_band band;

if (vif->type != NL80211_IFTYPE_STATION)
return;

rcu_read_lock();
chanctx_conf = rcu_dereference(vif->chanctx_conf);
if (chanctx_conf && chanctx_conf->def.chan)
band = chanctx_conf->def.chan->band;
else
band = -1;
rcu_read_unlock();

if (band != IEEE80211_BAND_2GHZ)
return;

smps_mode = IEEE80211_SMPS_AUTOMATIC;

if (data->notif->bt_status)
smps_mode = IEEE80211_SMPS_DYNAMIC;

if (data->notif->bt_traffic_load)
smps_mode = IEEE80211_SMPS_STATIC;

IWL_DEBUG_COEX(data->mvm,
"mac %d: bt_status %d traffic_load %d smps_req %d\n",
mvmvif->id, data->notif->bt_status,
data->notif->bt_traffic_load, smps_mode);

ieee80211_request_smps(vif, smps_mode);
}

int iwl_mvm_rx_bt_coex_notif(struct iwl_mvm *mvm,
struct iwl_rx_cmd_buffer *rxb,
struct iwl_device_cmd *dev_cmd)
{
struct iwl_rx_packet *pkt = rxb_addr(rxb);
struct iwl_bt_coex_profile_notif *notif = (void *)pkt->data;
struct iwl_bt_notif_iterator_data data = {
.mvm = mvm,
.notif = notif,
};
struct iwl_bt_coex_cmd cmd = {};
enum iwl_bt_kill_msk bt_kill_msk;

Expand All @@ -259,6 +307,10 @@ int iwl_mvm_rx_bt_coex_notif(struct iwl_mvm *mvm,
notif->bt_agg_traffic_load);
IWL_DEBUG_COEX(mvm, "\tBT ci compliance %d\n", notif->bt_ci_compliance);

ieee80211_iterate_active_interfaces_atomic(
mvm->hw, IEEE80211_IFACE_ITER_NORMAL,
iwl_mvm_bt_notif_iterator, &data);

/* Low latency BT profile is active: give higher prio to BT */
if (BT_MBOX_MSG(notif, 3, SCO_STATE) ||
BT_MBOX_MSG(notif, 3, A2DP_STATE) ||
Expand Down

0 comments on commit 7da052b

Please sign in to comment.