diff options
Diffstat (limited to 'drivers/net/wireless/ath/ath9k/init.c')
-rw-r--r-- | drivers/net/wireless/ath/ath9k/init.c | 162 |
1 files changed, 78 insertions, 84 deletions
diff --git a/drivers/net/wireless/ath/ath9k/init.c b/drivers/net/wireless/ath/ath9k/init.c index 14b8ab386daf..b0e5e716b167 100644 --- a/drivers/net/wireless/ath/ath9k/init.c +++ b/drivers/net/wireless/ath/ath9k/init.c | |||
@@ -37,9 +37,18 @@ int led_blink; | |||
37 | module_param_named(blink, led_blink, int, 0444); | 37 | module_param_named(blink, led_blink, int, 0444); |
38 | MODULE_PARM_DESC(blink, "Enable LED blink on activity"); | 38 | MODULE_PARM_DESC(blink, "Enable LED blink on activity"); |
39 | 39 | ||
40 | static int ath9k_btcoex_enable; | ||
41 | module_param_named(btcoex_enable, ath9k_btcoex_enable, int, 0444); | ||
42 | MODULE_PARM_DESC(btcoex_enable, "Enable wifi-BT coexistence"); | ||
43 | |||
44 | int ath9k_pm_qos_value = ATH9K_PM_QOS_DEFAULT_VALUE; | ||
45 | module_param_named(pmqos, ath9k_pm_qos_value, int, S_IRUSR | S_IRGRP | S_IROTH); | ||
46 | MODULE_PARM_DESC(pmqos, "User specified PM-QOS value"); | ||
47 | |||
40 | /* We use the hw_value as an index into our private channel structure */ | 48 | /* We use the hw_value as an index into our private channel structure */ |
41 | 49 | ||
42 | #define CHAN2G(_freq, _idx) { \ | 50 | #define CHAN2G(_freq, _idx) { \ |
51 | .band = IEEE80211_BAND_2GHZ, \ | ||
43 | .center_freq = (_freq), \ | 52 | .center_freq = (_freq), \ |
44 | .hw_value = (_idx), \ | 53 | .hw_value = (_idx), \ |
45 | .max_power = 20, \ | 54 | .max_power = 20, \ |
@@ -206,7 +215,9 @@ static void setup_ht_cap(struct ath_softc *sc, | |||
206 | ht_info->ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K; | 215 | ht_info->ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K; |
207 | ht_info->ampdu_density = IEEE80211_HT_MPDU_DENSITY_8; | 216 | ht_info->ampdu_density = IEEE80211_HT_MPDU_DENSITY_8; |
208 | 217 | ||
209 | if (AR_SREV_9300_20_OR_LATER(ah)) | 218 | if (AR_SREV_9485(ah)) |
219 | max_streams = 1; | ||
220 | else if (AR_SREV_9300_20_OR_LATER(ah)) | ||
210 | max_streams = 3; | 221 | max_streams = 3; |
211 | else | 222 | else |
212 | max_streams = 2; | 223 | max_streams = 2; |
@@ -222,9 +233,9 @@ static void setup_ht_cap(struct ath_softc *sc, | |||
222 | tx_streams = ath9k_cmn_count_streams(common->tx_chainmask, max_streams); | 233 | tx_streams = ath9k_cmn_count_streams(common->tx_chainmask, max_streams); |
223 | rx_streams = ath9k_cmn_count_streams(common->rx_chainmask, max_streams); | 234 | rx_streams = ath9k_cmn_count_streams(common->rx_chainmask, max_streams); |
224 | 235 | ||
225 | ath_print(common, ATH_DBG_CONFIG, | 236 | ath_dbg(common, ATH_DBG_CONFIG, |
226 | "TX streams %d, RX streams: %d\n", | 237 | "TX streams %d, RX streams: %d\n", |
227 | tx_streams, rx_streams); | 238 | tx_streams, rx_streams); |
228 | 239 | ||
229 | if (tx_streams != rx_streams) { | 240 | if (tx_streams != rx_streams) { |
230 | ht_info->mcs.tx_params |= IEEE80211_HT_MCS_TX_RX_DIFF; | 241 | ht_info->mcs.tx_params |= IEEE80211_HT_MCS_TX_RX_DIFF; |
@@ -267,8 +278,8 @@ int ath_descdma_setup(struct ath_softc *sc, struct ath_descdma *dd, | |||
267 | struct ath_buf *bf; | 278 | struct ath_buf *bf; |
268 | int i, bsize, error, desc_len; | 279 | int i, bsize, error, desc_len; |
269 | 280 | ||
270 | ath_print(common, ATH_DBG_CONFIG, "%s DMA: %u buffers %u desc/buf\n", | 281 | ath_dbg(common, ATH_DBG_CONFIG, "%s DMA: %u buffers %u desc/buf\n", |
271 | name, nbuf, ndesc); | 282 | name, nbuf, ndesc); |
272 | 283 | ||
273 | INIT_LIST_HEAD(head); | 284 | INIT_LIST_HEAD(head); |
274 | 285 | ||
@@ -279,8 +290,7 @@ int ath_descdma_setup(struct ath_softc *sc, struct ath_descdma *dd, | |||
279 | 290 | ||
280 | /* ath_desc must be a multiple of DWORDs */ | 291 | /* ath_desc must be a multiple of DWORDs */ |
281 | if ((desc_len % 4) != 0) { | 292 | if ((desc_len % 4) != 0) { |
282 | ath_print(common, ATH_DBG_FATAL, | 293 | ath_err(common, "ath_desc not DWORD aligned\n"); |
283 | "ath_desc not DWORD aligned\n"); | ||
284 | BUG_ON((desc_len % 4) != 0); | 294 | BUG_ON((desc_len % 4) != 0); |
285 | error = -ENOMEM; | 295 | error = -ENOMEM; |
286 | goto fail; | 296 | goto fail; |
@@ -314,9 +324,9 @@ int ath_descdma_setup(struct ath_softc *sc, struct ath_descdma *dd, | |||
314 | goto fail; | 324 | goto fail; |
315 | } | 325 | } |
316 | ds = (u8 *) dd->dd_desc; | 326 | ds = (u8 *) dd->dd_desc; |
317 | ath_print(common, ATH_DBG_CONFIG, "%s DMA map: %p (%u) -> %llx (%u)\n", | 327 | ath_dbg(common, ATH_DBG_CONFIG, "%s DMA map: %p (%u) -> %llx (%u)\n", |
318 | name, ds, (u32) dd->dd_desc_len, | 328 | name, ds, (u32) dd->dd_desc_len, |
319 | ito64(dd->dd_desc_paddr), /*XXX*/(u32) dd->dd_desc_len); | 329 | ito64(dd->dd_desc_paddr), /*XXX*/(u32) dd->dd_desc_len); |
320 | 330 | ||
321 | /* allocate buffers */ | 331 | /* allocate buffers */ |
322 | bsize = sizeof(struct ath_buf) * nbuf; | 332 | bsize = sizeof(struct ath_buf) * nbuf; |
@@ -370,9 +380,9 @@ static void ath9k_init_crypto(struct ath_softc *sc) | |||
370 | /* Get the hardware key cache size. */ | 380 | /* Get the hardware key cache size. */ |
371 | common->keymax = sc->sc_ah->caps.keycache_size; | 381 | common->keymax = sc->sc_ah->caps.keycache_size; |
372 | if (common->keymax > ATH_KEYMAX) { | 382 | if (common->keymax > ATH_KEYMAX) { |
373 | ath_print(common, ATH_DBG_ANY, | 383 | ath_dbg(common, ATH_DBG_ANY, |
374 | "Warning, using only %u entries in %u key cache\n", | 384 | "Warning, using only %u entries in %u key cache\n", |
375 | ATH_KEYMAX, common->keymax); | 385 | ATH_KEYMAX, common->keymax); |
376 | common->keymax = ATH_KEYMAX; | 386 | common->keymax = ATH_KEYMAX; |
377 | } | 387 | } |
378 | 388 | ||
@@ -395,7 +405,8 @@ static void ath9k_init_crypto(struct ath_softc *sc) | |||
395 | 405 | ||
396 | static int ath9k_init_btcoex(struct ath_softc *sc) | 406 | static int ath9k_init_btcoex(struct ath_softc *sc) |
397 | { | 407 | { |
398 | int r, qnum; | 408 | struct ath_txq *txq; |
409 | int r; | ||
399 | 410 | ||
400 | switch (sc->sc_ah->btcoex_hw.scheme) { | 411 | switch (sc->sc_ah->btcoex_hw.scheme) { |
401 | case ATH_BTCOEX_CFG_NONE: | 412 | case ATH_BTCOEX_CFG_NONE: |
@@ -408,8 +419,8 @@ static int ath9k_init_btcoex(struct ath_softc *sc) | |||
408 | r = ath_init_btcoex_timer(sc); | 419 | r = ath_init_btcoex_timer(sc); |
409 | if (r) | 420 | if (r) |
410 | return -1; | 421 | return -1; |
411 | qnum = sc->tx.hwq_map[WME_AC_BE]; | 422 | txq = sc->tx.txq_map[WME_AC_BE]; |
412 | ath9k_hw_init_btcoex_hw(sc->sc_ah, qnum); | 423 | ath9k_hw_init_btcoex_hw(sc->sc_ah, txq->axq_qnum); |
413 | sc->btcoex.bt_stomp_type = ATH_BTCOEX_STOMP_LOW; | 424 | sc->btcoex.bt_stomp_type = ATH_BTCOEX_STOMP_LOW; |
414 | break; | 425 | break; |
415 | default: | 426 | default: |
@@ -422,59 +433,18 @@ static int ath9k_init_btcoex(struct ath_softc *sc) | |||
422 | 433 | ||
423 | static int ath9k_init_queues(struct ath_softc *sc) | 434 | static int ath9k_init_queues(struct ath_softc *sc) |
424 | { | 435 | { |
425 | struct ath_common *common = ath9k_hw_common(sc->sc_ah); | ||
426 | int i = 0; | 436 | int i = 0; |
427 | 437 | ||
428 | for (i = 0; i < ARRAY_SIZE(sc->tx.hwq_map); i++) | ||
429 | sc->tx.hwq_map[i] = -1; | ||
430 | |||
431 | sc->beacon.beaconq = ath9k_hw_beaconq_setup(sc->sc_ah); | 438 | sc->beacon.beaconq = ath9k_hw_beaconq_setup(sc->sc_ah); |
432 | if (sc->beacon.beaconq == -1) { | ||
433 | ath_print(common, ATH_DBG_FATAL, | ||
434 | "Unable to setup a beacon xmit queue\n"); | ||
435 | goto err; | ||
436 | } | ||
437 | |||
438 | sc->beacon.cabq = ath_txq_setup(sc, ATH9K_TX_QUEUE_CAB, 0); | 439 | sc->beacon.cabq = ath_txq_setup(sc, ATH9K_TX_QUEUE_CAB, 0); |
439 | if (sc->beacon.cabq == NULL) { | ||
440 | ath_print(common, ATH_DBG_FATAL, | ||
441 | "Unable to setup CAB xmit queue\n"); | ||
442 | goto err; | ||
443 | } | ||
444 | 440 | ||
445 | sc->config.cabqReadytime = ATH_CABQ_READY_TIME; | 441 | sc->config.cabqReadytime = ATH_CABQ_READY_TIME; |
446 | ath_cabq_update(sc); | 442 | ath_cabq_update(sc); |
447 | 443 | ||
448 | if (!ath_tx_setup(sc, WME_AC_BK)) { | 444 | for (i = 0; i < WME_NUM_AC; i++) |
449 | ath_print(common, ATH_DBG_FATAL, | 445 | sc->tx.txq_map[i] = ath_txq_setup(sc, ATH9K_TX_QUEUE_DATA, i); |
450 | "Unable to setup xmit queue for BK traffic\n"); | ||
451 | goto err; | ||
452 | } | ||
453 | |||
454 | if (!ath_tx_setup(sc, WME_AC_BE)) { | ||
455 | ath_print(common, ATH_DBG_FATAL, | ||
456 | "Unable to setup xmit queue for BE traffic\n"); | ||
457 | goto err; | ||
458 | } | ||
459 | if (!ath_tx_setup(sc, WME_AC_VI)) { | ||
460 | ath_print(common, ATH_DBG_FATAL, | ||
461 | "Unable to setup xmit queue for VI traffic\n"); | ||
462 | goto err; | ||
463 | } | ||
464 | if (!ath_tx_setup(sc, WME_AC_VO)) { | ||
465 | ath_print(common, ATH_DBG_FATAL, | ||
466 | "Unable to setup xmit queue for VO traffic\n"); | ||
467 | goto err; | ||
468 | } | ||
469 | 446 | ||
470 | return 0; | 447 | return 0; |
471 | |||
472 | err: | ||
473 | for (i = 0; i < ATH9K_NUM_TX_QUEUES; i++) | ||
474 | if (ATH_TXQ_SETUP(sc, i)) | ||
475 | ath_tx_cleanupq(sc, &sc->tx.txq[i]); | ||
476 | |||
477 | return -EIO; | ||
478 | } | 448 | } |
479 | 449 | ||
480 | static int ath9k_init_channels_rates(struct ath_softc *sc) | 450 | static int ath9k_init_channels_rates(struct ath_softc *sc) |
@@ -570,6 +540,9 @@ static int ath9k_init_softc(u16 devid, struct ath_softc *sc, u16 subsysid, | |||
570 | ah->hw_version.subsysid = subsysid; | 540 | ah->hw_version.subsysid = subsysid; |
571 | sc->sc_ah = ah; | 541 | sc->sc_ah = ah; |
572 | 542 | ||
543 | if (!sc->dev->platform_data) | ||
544 | ah->ah_flags |= AH_USE_EEPROM; | ||
545 | |||
573 | common = ath9k_hw_common(ah); | 546 | common = ath9k_hw_common(ah); |
574 | common->ops = &ath9k_common_ops; | 547 | common->ops = &ath9k_common_ops; |
575 | common->bus_ops = bus_ops; | 548 | common->bus_ops = bus_ops; |
@@ -577,10 +550,10 @@ static int ath9k_init_softc(u16 devid, struct ath_softc *sc, u16 subsysid, | |||
577 | common->hw = sc->hw; | 550 | common->hw = sc->hw; |
578 | common->priv = sc; | 551 | common->priv = sc; |
579 | common->debug_mask = ath9k_debug; | 552 | common->debug_mask = ath9k_debug; |
553 | common->btcoex_enabled = ath9k_btcoex_enable == 1; | ||
580 | spin_lock_init(&common->cc_lock); | 554 | spin_lock_init(&common->cc_lock); |
581 | 555 | ||
582 | spin_lock_init(&sc->wiphy_lock); | 556 | spin_lock_init(&sc->wiphy_lock); |
583 | spin_lock_init(&sc->sc_resetlock); | ||
584 | spin_lock_init(&sc->sc_serial_rw); | 557 | spin_lock_init(&sc->sc_serial_rw); |
585 | spin_lock_init(&sc->sc_pm_lock); | 558 | spin_lock_init(&sc->sc_pm_lock); |
586 | mutex_init(&sc->mutex); | 559 | mutex_init(&sc->mutex); |
@@ -600,13 +573,6 @@ static int ath9k_init_softc(u16 devid, struct ath_softc *sc, u16 subsysid, | |||
600 | if (ret) | 573 | if (ret) |
601 | goto err_hw; | 574 | goto err_hw; |
602 | 575 | ||
603 | ret = ath9k_init_debug(ah); | ||
604 | if (ret) { | ||
605 | ath_print(common, ATH_DBG_FATAL, | ||
606 | "Unable to create debugfs files\n"); | ||
607 | goto err_debug; | ||
608 | } | ||
609 | |||
610 | ret = ath9k_init_queues(sc); | 576 | ret = ath9k_init_queues(sc); |
611 | if (ret) | 577 | if (ret) |
612 | goto err_queues; | 578 | goto err_queues; |
@@ -629,8 +595,6 @@ err_btcoex: | |||
629 | if (ATH_TXQ_SETUP(sc, i)) | 595 | if (ATH_TXQ_SETUP(sc, i)) |
630 | ath_tx_cleanupq(sc, &sc->tx.txq[i]); | 596 | ath_tx_cleanupq(sc, &sc->tx.txq[i]); |
631 | err_queues: | 597 | err_queues: |
632 | ath9k_exit_debug(ah); | ||
633 | err_debug: | ||
634 | ath9k_hw_deinit(ah); | 598 | ath9k_hw_deinit(ah); |
635 | err_hw: | 599 | err_hw: |
636 | tasklet_kill(&sc->intr_tq); | 600 | tasklet_kill(&sc->intr_tq); |
@@ -642,6 +606,37 @@ err_hw: | |||
642 | return ret; | 606 | return ret; |
643 | } | 607 | } |
644 | 608 | ||
609 | static void ath9k_init_band_txpower(struct ath_softc *sc, int band) | ||
610 | { | ||
611 | struct ieee80211_supported_band *sband; | ||
612 | struct ieee80211_channel *chan; | ||
613 | struct ath_hw *ah = sc->sc_ah; | ||
614 | struct ath_regulatory *reg = ath9k_hw_regulatory(ah); | ||
615 | int i; | ||
616 | |||
617 | sband = &sc->sbands[band]; | ||
618 | for (i = 0; i < sband->n_channels; i++) { | ||
619 | chan = &sband->channels[i]; | ||
620 | ah->curchan = &ah->channels[chan->hw_value]; | ||
621 | ath9k_cmn_update_ichannel(ah->curchan, chan, NL80211_CHAN_HT20); | ||
622 | ath9k_hw_set_txpowerlimit(ah, MAX_RATE_POWER, true); | ||
623 | chan->max_power = reg->max_power_level / 2; | ||
624 | } | ||
625 | } | ||
626 | |||
627 | static void ath9k_init_txpower_limits(struct ath_softc *sc) | ||
628 | { | ||
629 | struct ath_hw *ah = sc->sc_ah; | ||
630 | struct ath9k_channel *curchan = ah->curchan; | ||
631 | |||
632 | if (ah->caps.hw_caps & ATH9K_HW_CAP_2GHZ) | ||
633 | ath9k_init_band_txpower(sc, IEEE80211_BAND_2GHZ); | ||
634 | if (ah->caps.hw_caps & ATH9K_HW_CAP_5GHZ) | ||
635 | ath9k_init_band_txpower(sc, IEEE80211_BAND_5GHZ); | ||
636 | |||
637 | ah->curchan = curchan; | ||
638 | } | ||
639 | |||
645 | void ath9k_set_hw_capab(struct ath_softc *sc, struct ieee80211_hw *hw) | 640 | void ath9k_set_hw_capab(struct ath_softc *sc, struct ieee80211_hw *hw) |
646 | { | 641 | { |
647 | struct ath_common *common = ath9k_hw_common(sc->sc_ah); | 642 | struct ath_common *common = ath9k_hw_common(sc->sc_ah); |
@@ -652,7 +647,8 @@ void ath9k_set_hw_capab(struct ath_softc *sc, struct ieee80211_hw *hw) | |||
652 | IEEE80211_HW_SUPPORTS_PS | | 647 | IEEE80211_HW_SUPPORTS_PS | |
653 | IEEE80211_HW_PS_NULLFUNC_STACK | | 648 | IEEE80211_HW_PS_NULLFUNC_STACK | |
654 | IEEE80211_HW_SPECTRUM_MGMT | | 649 | IEEE80211_HW_SPECTRUM_MGMT | |
655 | IEEE80211_HW_REPORTS_TX_ACK_STATUS; | 650 | IEEE80211_HW_REPORTS_TX_ACK_STATUS | |
651 | IEEE80211_HW_NEED_DTIM_PERIOD; | ||
656 | 652 | ||
657 | if (sc->sc_ah->caps.hw_caps & ATH9K_HW_CAP_HT) | 653 | if (sc->sc_ah->caps.hw_caps & ATH9K_HW_CAP_HT) |
658 | hw->flags |= IEEE80211_HW_AMPDU_AGGREGATION; | 654 | hw->flags |= IEEE80211_HW_AMPDU_AGGREGATION; |
@@ -705,6 +701,7 @@ int ath9k_init_device(u16 devid, struct ath_softc *sc, u16 subsysid, | |||
705 | const struct ath_bus_ops *bus_ops) | 701 | const struct ath_bus_ops *bus_ops) |
706 | { | 702 | { |
707 | struct ieee80211_hw *hw = sc->hw; | 703 | struct ieee80211_hw *hw = sc->hw; |
704 | struct ath_wiphy *aphy = hw->priv; | ||
708 | struct ath_common *common; | 705 | struct ath_common *common; |
709 | struct ath_hw *ah; | 706 | struct ath_hw *ah; |
710 | int error = 0; | 707 | int error = 0; |
@@ -737,11 +734,19 @@ int ath9k_init_device(u16 devid, struct ath_softc *sc, u16 subsysid, | |||
737 | if (error != 0) | 734 | if (error != 0) |
738 | goto error_rx; | 735 | goto error_rx; |
739 | 736 | ||
737 | ath9k_init_txpower_limits(sc); | ||
738 | |||
740 | /* Register with mac80211 */ | 739 | /* Register with mac80211 */ |
741 | error = ieee80211_register_hw(hw); | 740 | error = ieee80211_register_hw(hw); |
742 | if (error) | 741 | if (error) |
743 | goto error_register; | 742 | goto error_register; |
744 | 743 | ||
744 | error = ath9k_init_debug(ah); | ||
745 | if (error) { | ||
746 | ath_err(common, "Unable to create debugfs files\n"); | ||
747 | goto error_world; | ||
748 | } | ||
749 | |||
745 | /* Handle world regulatory */ | 750 | /* Handle world regulatory */ |
746 | if (!ath_is_world_regd(reg)) { | 751 | if (!ath_is_world_regd(reg)) { |
747 | error = regulatory_hint(hw->wiphy, reg->alpha2); | 752 | error = regulatory_hint(hw->wiphy, reg->alpha2); |
@@ -754,6 +759,7 @@ int ath9k_init_device(u16 devid, struct ath_softc *sc, u16 subsysid, | |||
754 | INIT_WORK(&sc->chan_work, ath9k_wiphy_chan_work); | 759 | INIT_WORK(&sc->chan_work, ath9k_wiphy_chan_work); |
755 | INIT_DELAYED_WORK(&sc->wiphy_work, ath9k_wiphy_work); | 760 | INIT_DELAYED_WORK(&sc->wiphy_work, ath9k_wiphy_work); |
756 | sc->wiphy_scheduler_int = msecs_to_jiffies(500); | 761 | sc->wiphy_scheduler_int = msecs_to_jiffies(500); |
762 | aphy->last_rssi = ATH_RSSI_DUMMY_MARKER; | ||
757 | 763 | ||
758 | ath_init_leds(sc); | 764 | ath_init_leds(sc); |
759 | ath_start_rfkill_poll(sc); | 765 | ath_start_rfkill_poll(sc); |
@@ -799,7 +805,6 @@ static void ath9k_deinit_softc(struct ath_softc *sc) | |||
799 | if (ATH_TXQ_SETUP(sc, i)) | 805 | if (ATH_TXQ_SETUP(sc, i)) |
800 | ath_tx_cleanupq(sc, &sc->tx.txq[i]); | 806 | ath_tx_cleanupq(sc, &sc->tx.txq[i]); |
801 | 807 | ||
802 | ath9k_exit_debug(sc->sc_ah); | ||
803 | ath9k_hw_deinit(sc->sc_ah); | 808 | ath9k_hw_deinit(sc->sc_ah); |
804 | 809 | ||
805 | tasklet_kill(&sc->intr_tq); | 810 | tasklet_kill(&sc->intr_tq); |
@@ -866,20 +871,12 @@ static int __init ath9k_init(void) | |||
866 | goto err_out; | 871 | goto err_out; |
867 | } | 872 | } |
868 | 873 | ||
869 | error = ath9k_debug_create_root(); | ||
870 | if (error) { | ||
871 | printk(KERN_ERR | ||
872 | "ath9k: Unable to create debugfs root: %d\n", | ||
873 | error); | ||
874 | goto err_rate_unregister; | ||
875 | } | ||
876 | |||
877 | error = ath_pci_init(); | 874 | error = ath_pci_init(); |
878 | if (error < 0) { | 875 | if (error < 0) { |
879 | printk(KERN_ERR | 876 | printk(KERN_ERR |
880 | "ath9k: No PCI devices found, driver not installed.\n"); | 877 | "ath9k: No PCI devices found, driver not installed.\n"); |
881 | error = -ENODEV; | 878 | error = -ENODEV; |
882 | goto err_remove_root; | 879 | goto err_rate_unregister; |
883 | } | 880 | } |
884 | 881 | ||
885 | error = ath_ahb_init(); | 882 | error = ath_ahb_init(); |
@@ -893,8 +890,6 @@ static int __init ath9k_init(void) | |||
893 | err_pci_exit: | 890 | err_pci_exit: |
894 | ath_pci_exit(); | 891 | ath_pci_exit(); |
895 | 892 | ||
896 | err_remove_root: | ||
897 | ath9k_debug_remove_root(); | ||
898 | err_rate_unregister: | 893 | err_rate_unregister: |
899 | ath_rate_control_unregister(); | 894 | ath_rate_control_unregister(); |
900 | err_out: | 895 | err_out: |
@@ -906,7 +901,6 @@ static void __exit ath9k_exit(void) | |||
906 | { | 901 | { |
907 | ath_ahb_exit(); | 902 | ath_ahb_exit(); |
908 | ath_pci_exit(); | 903 | ath_pci_exit(); |
909 | ath9k_debug_remove_root(); | ||
910 | ath_rate_control_unregister(); | 904 | ath_rate_control_unregister(); |
911 | printk(KERN_INFO "%s: Driver unloaded\n", dev_info); | 905 | printk(KERN_INFO "%s: Driver unloaded\n", dev_info); |
912 | } | 906 | } |