iwmc3200wifi: use cfg80211_roamed to send roam event
The device sends connection terminated and [re]association success
(or failure) events when roaming occours. The patch uses
cfg80211_roamed instead of cfg80211_connect_result to notify SME
for roaming.
Signed-off-by: Zhu Yi <yi.zhu@intel.com>
Signed-off-by: Samuel Ortiz <sameo@linux.intel.com>
Signed-off-by: John W. Linville <linville@tuxdriver.com>
diff --git a/drivers/net/wireless/iwmc3200wifi/cfg80211.c b/drivers/net/wireless/iwmc3200wifi/cfg80211.c
index 2784b08..a56a2b0 100644
--- a/drivers/net/wireless/iwmc3200wifi/cfg80211.c
+++ b/drivers/net/wireless/iwmc3200wifi/cfg80211.c
@@ -673,7 +673,7 @@
IWM_DBG_WEXT(iwm, DBG, "Active: %d\n", iwm->umac_profile_active);
if (iwm->umac_profile_active)
- return iwm_invalidate_mlme_profile(iwm);
+ iwm_invalidate_mlme_profile(iwm);
return 0;
}
diff --git a/drivers/net/wireless/iwmc3200wifi/commands.c b/drivers/net/wireless/iwmc3200wifi/commands.c
index a68a2af..23b52fa 100644
--- a/drivers/net/wireless/iwmc3200wifi/commands.c
+++ b/drivers/net/wireless/iwmc3200wifi/commands.c
@@ -756,6 +756,7 @@
return ret;
}
+ set_bit(IWM_STATUS_SME_CONNECTING, &iwm->status);
return 0;
}
diff --git a/drivers/net/wireless/iwmc3200wifi/iwm.h b/drivers/net/wireless/iwmc3200wifi/iwm.h
index 7a51bc3..f054cc8 100644
--- a/drivers/net/wireless/iwmc3200wifi/iwm.h
+++ b/drivers/net/wireless/iwmc3200wifi/iwm.h
@@ -175,7 +175,7 @@
#define IWM_STATUS_READY 0
#define IWM_STATUS_SCANNING 1
#define IWM_STATUS_SCAN_ABORTING 2
-#define IWM_STATUS_ASSOCIATING 3
+#define IWM_STATUS_SME_CONNECTING 3
#define IWM_STATUS_ASSOCIATED 4
struct iwm_tx_queue {
diff --git a/drivers/net/wireless/iwmc3200wifi/rx.c b/drivers/net/wireless/iwmc3200wifi/rx.c
index 86079a1..9e6f2cd 100644
--- a/drivers/net/wireless/iwmc3200wifi/rx.c
+++ b/drivers/net/wireless/iwmc3200wifi/rx.c
@@ -487,8 +487,6 @@
start = (struct iwm_umac_notif_assoc_start *)buf;
- set_bit(IWM_STATUS_ASSOCIATING, &iwm->status);
-
IWM_DBG_MLME(iwm, INFO, "Association with %pM Started, reason: %d\n",
start->bssid, le32_to_cpu(start->roam_reason));
@@ -507,14 +505,23 @@
IWM_DBG_MLME(iwm, INFO, "Association with %pM completed, status: %d\n",
complete->bssid, complete->status);
- clear_bit(IWM_STATUS_ASSOCIATING, &iwm->status);
-
switch (le32_to_cpu(complete->status)) {
case UMAC_ASSOC_COMPLETE_SUCCESS:
set_bit(IWM_STATUS_ASSOCIATED, &iwm->status);
memcpy(iwm->bssid, complete->bssid, ETH_ALEN);
iwm->channel = complete->channel;
+ /* Internal roaming state, avoid notifying SME. */
+ if (!test_and_clear_bit(IWM_STATUS_SME_CONNECTING, &iwm->status)
+ && iwm->conf.mode == UMAC_MODE_BSS) {
+ cfg80211_roamed(iwm_to_ndev(iwm),
+ complete->bssid,
+ iwm->req_ie, iwm->req_ie_len,
+ iwm->resp_ie, iwm->resp_ie_len,
+ GFP_KERNEL);
+ break;
+ }
+
iwm_link_on(iwm);
if (iwm->conf.mode == UMAC_MODE_IBSS)
@@ -531,6 +538,11 @@
memset(iwm->bssid, 0, ETH_ALEN);
iwm->channel = 0;
+ /* Internal roaming state, avoid notifying SME. */
+ if (!test_and_clear_bit(IWM_STATUS_SME_CONNECTING, &iwm->status)
+ && iwm->conf.mode == UMAC_MODE_BSS)
+ break;
+
iwm_link_off(iwm);
if (iwm->conf.mode == UMAC_MODE_IBSS)
@@ -540,6 +552,7 @@
NULL, 0, NULL, 0,
WLAN_STATUS_UNSPECIFIED_FAILURE,
GFP_KERNEL);
+ break;
default:
break;
}
@@ -562,7 +575,7 @@
IWM_DBG_MLME(iwm, INFO, "Profile Invalidated. Reason: %d\n",
le32_to_cpu(invalid->reason));
- clear_bit(IWM_STATUS_ASSOCIATING, &iwm->status);
+ clear_bit(IWM_STATUS_SME_CONNECTING, &iwm->status);
clear_bit(IWM_STATUS_ASSOCIATED, &iwm->status);
iwm->umac_profile_active = 0;
@@ -813,7 +826,8 @@
iwm->resp_ie = kmemdup(mgt->u.reassoc_resp.variable,
iwm->resp_ie_len, GFP_KERNEL);
} else {
- IWM_ERR(iwm, "Unsupported management frame");
+ IWM_ERR(iwm, "Unsupported management frame: 0x%x",
+ cpu_to_le16(mgt->frame_control));
return 0;
}