diff options
-rw-r--r-- | drivers/net/wireless/iwmc3200wifi/iwm.h | 2 | ||||
-rw-r--r-- | drivers/net/wireless/iwmc3200wifi/main.c | 18 | ||||
-rw-r--r-- | drivers/net/wireless/iwmc3200wifi/rx.c | 29 |
3 files changed, 40 insertions, 9 deletions
diff --git a/drivers/net/wireless/iwmc3200wifi/iwm.h b/drivers/net/wireless/iwmc3200wifi/iwm.h index 74964ee93bb7..f5c2d6f3fd43 100644 --- a/drivers/net/wireless/iwmc3200wifi/iwm.h +++ b/drivers/net/wireless/iwmc3200wifi/iwm.h | |||
@@ -178,6 +178,7 @@ struct iwm_key { | |||
178 | #define IWM_STATUS_SCAN_ABORTING 2 | 178 | #define IWM_STATUS_SCAN_ABORTING 2 |
179 | #define IWM_STATUS_SME_CONNECTING 3 | 179 | #define IWM_STATUS_SME_CONNECTING 3 |
180 | #define IWM_STATUS_ASSOCIATED 4 | 180 | #define IWM_STATUS_ASSOCIATED 4 |
181 | #define IWM_STATUS_RESETTING 5 | ||
181 | 182 | ||
182 | struct iwm_tx_queue { | 183 | struct iwm_tx_queue { |
183 | int id; | 184 | int id; |
@@ -317,6 +318,7 @@ int iwm_mode_to_nl80211_iftype(int mode); | |||
317 | int iwm_priv_init(struct iwm_priv *iwm); | 318 | int iwm_priv_init(struct iwm_priv *iwm); |
318 | void iwm_priv_deinit(struct iwm_priv *iwm); | 319 | void iwm_priv_deinit(struct iwm_priv *iwm); |
319 | void iwm_reset(struct iwm_priv *iwm); | 320 | void iwm_reset(struct iwm_priv *iwm); |
321 | void iwm_resetting(struct iwm_priv *iwm); | ||
320 | void iwm_tx_credit_init_pools(struct iwm_priv *iwm, | 322 | void iwm_tx_credit_init_pools(struct iwm_priv *iwm, |
321 | struct iwm_umac_notif_alive *alive); | 323 | struct iwm_umac_notif_alive *alive); |
322 | int iwm_tx_credit_alloc(struct iwm_priv *iwm, int id, int nb); | 324 | int iwm_tx_credit_alloc(struct iwm_priv *iwm, int id, int nb); |
diff --git a/drivers/net/wireless/iwmc3200wifi/main.c b/drivers/net/wireless/iwmc3200wifi/main.c index fc7fce44a9d7..6a5b76acb645 100644 --- a/drivers/net/wireless/iwmc3200wifi/main.c +++ b/drivers/net/wireless/iwmc3200wifi/main.c | |||
@@ -187,7 +187,8 @@ static void iwm_reset_worker(struct work_struct *work) | |||
187 | memcpy(iwm->umac_profile, profile, sizeof(*profile)); | 187 | memcpy(iwm->umac_profile, profile, sizeof(*profile)); |
188 | iwm_send_mlme_profile(iwm); | 188 | iwm_send_mlme_profile(iwm); |
189 | kfree(profile); | 189 | kfree(profile); |
190 | } | 190 | } else |
191 | clear_bit(IWM_STATUS_RESETTING, &iwm->status); | ||
191 | 192 | ||
192 | out: | 193 | out: |
193 | mutex_unlock(&iwm->mutex); | 194 | mutex_unlock(&iwm->mutex); |
@@ -200,7 +201,7 @@ static void iwm_watchdog(unsigned long data) | |||
200 | IWM_WARN(iwm, "Watchdog expired: UMAC stalls!\n"); | 201 | IWM_WARN(iwm, "Watchdog expired: UMAC stalls!\n"); |
201 | 202 | ||
202 | if (modparam_reset) | 203 | if (modparam_reset) |
203 | schedule_work(&iwm->reset_worker); | 204 | iwm_resetting(iwm); |
204 | } | 205 | } |
205 | 206 | ||
206 | int iwm_priv_init(struct iwm_priv *iwm) | 207 | int iwm_priv_init(struct iwm_priv *iwm) |
@@ -284,7 +285,11 @@ void iwm_reset(struct iwm_priv *iwm) | |||
284 | if (test_bit(IWM_STATUS_READY, &iwm->status)) | 285 | if (test_bit(IWM_STATUS_READY, &iwm->status)) |
285 | iwm_target_reset(iwm); | 286 | iwm_target_reset(iwm); |
286 | 287 | ||
287 | iwm->status = 0; | 288 | if (test_bit(IWM_STATUS_RESETTING, &iwm->status)) { |
289 | iwm->status = 0; | ||
290 | set_bit(IWM_STATUS_RESETTING, &iwm->status); | ||
291 | } else | ||
292 | iwm->status = 0; | ||
288 | iwm->scan_id = 1; | 293 | iwm->scan_id = 1; |
289 | 294 | ||
290 | list_for_each_entry_safe(notif, next, &iwm->pending_notif, pending) { | 295 | list_for_each_entry_safe(notif, next, &iwm->pending_notif, pending) { |
@@ -300,6 +305,13 @@ void iwm_reset(struct iwm_priv *iwm) | |||
300 | iwm_link_off(iwm); | 305 | iwm_link_off(iwm); |
301 | } | 306 | } |
302 | 307 | ||
308 | void iwm_resetting(struct iwm_priv *iwm) | ||
309 | { | ||
310 | set_bit(IWM_STATUS_RESETTING, &iwm->status); | ||
311 | |||
312 | schedule_work(&iwm->reset_worker); | ||
313 | } | ||
314 | |||
303 | /* | 315 | /* |
304 | * Notification code: | 316 | * Notification code: |
305 | * | 317 | * |
diff --git a/drivers/net/wireless/iwmc3200wifi/rx.c b/drivers/net/wireless/iwmc3200wifi/rx.c index 2daa58633e6f..14950b147f91 100644 --- a/drivers/net/wireless/iwmc3200wifi/rx.c +++ b/drivers/net/wireless/iwmc3200wifi/rx.c | |||
@@ -118,6 +118,8 @@ static int iwm_ntf_error(struct iwm_priv *iwm, u8 *buf, | |||
118 | IWM_ERR(iwm, "\tLMAC status: 0x%x\n", le32_to_cpu(fw_err->lmac_status)); | 118 | IWM_ERR(iwm, "\tLMAC status: 0x%x\n", le32_to_cpu(fw_err->lmac_status)); |
119 | IWM_ERR(iwm, "\tSDIO status: 0x%x\n", le32_to_cpu(fw_err->sdio_status)); | 119 | IWM_ERR(iwm, "\tSDIO status: 0x%x\n", le32_to_cpu(fw_err->sdio_status)); |
120 | 120 | ||
121 | iwm_resetting(iwm); | ||
122 | |||
121 | return 0; | 123 | return 0; |
122 | } | 124 | } |
123 | 125 | ||
@@ -528,11 +530,19 @@ static int iwm_mlme_assoc_complete(struct iwm_priv *iwm, u8 *buf, | |||
528 | if (iwm->conf.mode == UMAC_MODE_IBSS) | 530 | if (iwm->conf.mode == UMAC_MODE_IBSS) |
529 | goto ibss; | 531 | goto ibss; |
530 | 532 | ||
531 | cfg80211_connect_result(iwm_to_ndev(iwm), | 533 | if (!test_bit(IWM_STATUS_RESETTING, &iwm->status)) |
534 | cfg80211_connect_result(iwm_to_ndev(iwm), | ||
535 | complete->bssid, | ||
536 | iwm->req_ie, iwm->req_ie_len, | ||
537 | iwm->resp_ie, iwm->resp_ie_len, | ||
538 | WLAN_STATUS_SUCCESS, | ||
539 | GFP_KERNEL); | ||
540 | else | ||
541 | cfg80211_roamed(iwm_to_ndev(iwm), | ||
532 | complete->bssid, | 542 | complete->bssid, |
533 | iwm->req_ie, iwm->req_ie_len, | 543 | iwm->req_ie, iwm->req_ie_len, |
534 | iwm->resp_ie, iwm->resp_ie_len, | 544 | iwm->resp_ie, iwm->resp_ie_len, |
535 | WLAN_STATUS_SUCCESS, GFP_KERNEL); | 545 | GFP_KERNEL); |
536 | break; | 546 | break; |
537 | case UMAC_ASSOC_COMPLETE_FAILURE: | 547 | case UMAC_ASSOC_COMPLETE_FAILURE: |
538 | clear_bit(IWM_STATUS_ASSOCIATED, &iwm->status); | 548 | clear_bit(IWM_STATUS_ASSOCIATED, &iwm->status); |
@@ -551,19 +561,26 @@ static int iwm_mlme_assoc_complete(struct iwm_priv *iwm, u8 *buf, | |||
551 | if (iwm->conf.mode == UMAC_MODE_IBSS) | 561 | if (iwm->conf.mode == UMAC_MODE_IBSS) |
552 | goto ibss; | 562 | goto ibss; |
553 | 563 | ||
554 | cfg80211_connect_result(iwm_to_ndev(iwm), complete->bssid, | 564 | if (!test_bit(IWM_STATUS_RESETTING, &iwm->status)) |
555 | NULL, 0, NULL, 0, | 565 | cfg80211_connect_result(iwm_to_ndev(iwm), |
556 | WLAN_STATUS_UNSPECIFIED_FAILURE, | 566 | complete->bssid, |
557 | GFP_KERNEL); | 567 | NULL, 0, NULL, 0, |
568 | WLAN_STATUS_UNSPECIFIED_FAILURE, | ||
569 | GFP_KERNEL); | ||
570 | else | ||
571 | cfg80211_disconnected(iwm_to_ndev(iwm), 0, NULL, 0, | ||
572 | GFP_KERNEL); | ||
558 | break; | 573 | break; |
559 | default: | 574 | default: |
560 | break; | 575 | break; |
561 | } | 576 | } |
562 | 577 | ||
578 | clear_bit(IWM_STATUS_RESETTING, &iwm->status); | ||
563 | return 0; | 579 | return 0; |
564 | 580 | ||
565 | ibss: | 581 | ibss: |
566 | cfg80211_ibss_joined(iwm_to_ndev(iwm), iwm->bssid, GFP_KERNEL); | 582 | cfg80211_ibss_joined(iwm_to_ndev(iwm), iwm->bssid, GFP_KERNEL); |
583 | clear_bit(IWM_STATUS_RESETTING, &iwm->status); | ||
567 | return 0; | 584 | return 0; |
568 | } | 585 | } |
569 | 586 | ||