aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorMattias Nissler <mattias.nissler@gmx.de>2008-08-29 15:05:21 -0400
committerJohn W. Linville <linville@tuxdriver.com>2008-08-29 16:24:11 -0400
commit2575c11d6ee7266f0f035e55c5056b36597cd336 (patch)
treeecbe0d61936b31c2c8d072194576d2299f736714 /drivers
parent3ee54a07d34fd9b5c34bb1488113fb32be58e38f (diff)
rt2x00: Only configure hardware when radio is enabled
Some hardware configuration registers such as antenna and channel configuration can only be written when the radio is enabled. Previously, we didn't consider this, so some configuration items could be set inconsistently after reenabling the radio. This patch changes the config() handler to only reprogram the hardware when the radio is enabled. Configuration changes that are made while the radio is off are postponed until the radio is switched back on. We also leave the radio turned off during initialization and only enable it when requested by mac80211. This allows us to get rid of the DIRTY_CONFIG flag, because the device is now guaranteed to be completely initialized when brought up by mac80211. Signed-off-by: Mattias Nissler <mattias.nissler@gmx.de> Signed-off-by: Ivo van Doorn <IvDoorn@gmail.com> Signed-off-by: John W. Linville <linville@tuxdriver.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/net/wireless/rt2x00/rt2x00.h1
-rw-r--r--drivers/net/wireless/rt2x00/rt2x00dev.c10
-rw-r--r--drivers/net/wireless/rt2x00/rt2x00mac.c50
3 files changed, 25 insertions, 36 deletions
diff --git a/drivers/net/wireless/rt2x00/rt2x00.h b/drivers/net/wireless/rt2x00/rt2x00.h
index 08095bf3f8f..5e4f783345a 100644
--- a/drivers/net/wireless/rt2x00/rt2x00.h
+++ b/drivers/net/wireless/rt2x00/rt2x00.h
@@ -636,7 +636,6 @@ enum rt2x00_flags {
636 DEVICE_STATE_STARTED_SUSPEND, 636 DEVICE_STATE_STARTED_SUSPEND,
637 DEVICE_STATE_ENABLED_RADIO, 637 DEVICE_STATE_ENABLED_RADIO,
638 DEVICE_STATE_DISABLED_RADIO_HW, 638 DEVICE_STATE_DISABLED_RADIO_HW,
639 DEVICE_STATE_DIRTY_CONFIG,
640 639
641 /* 640 /*
642 * Driver requirements 641 * Driver requirements
diff --git a/drivers/net/wireless/rt2x00/rt2x00dev.c b/drivers/net/wireless/rt2x00/rt2x00dev.c
index 330ab77902f..5278ae2e374 100644
--- a/drivers/net/wireless/rt2x00/rt2x00dev.c
+++ b/drivers/net/wireless/rt2x00/rt2x00dev.c
@@ -1014,21 +1014,11 @@ int rt2x00lib_start(struct rt2x00_dev *rt2x00dev)
1014 if (retval) 1014 if (retval)
1015 return retval; 1015 return retval;
1016 1016
1017 /*
1018 * Enable radio.
1019 */
1020 retval = rt2x00lib_enable_radio(rt2x00dev);
1021 if (retval) {
1022 rt2x00lib_uninitialize(rt2x00dev);
1023 return retval;
1024 }
1025
1026 rt2x00dev->intf_ap_count = 0; 1017 rt2x00dev->intf_ap_count = 0;
1027 rt2x00dev->intf_sta_count = 0; 1018 rt2x00dev->intf_sta_count = 0;
1028 rt2x00dev->intf_associated = 0; 1019 rt2x00dev->intf_associated = 0;
1029 1020
1030 set_bit(DEVICE_STATE_STARTED, &rt2x00dev->flags); 1021 set_bit(DEVICE_STATE_STARTED, &rt2x00dev->flags);
1031 set_bit(DEVICE_STATE_DIRTY_CONFIG, &rt2x00dev->flags);
1032 1022
1033 return 0; 1023 return 0;
1034} 1024}
diff --git a/drivers/net/wireless/rt2x00/rt2x00mac.c b/drivers/net/wireless/rt2x00/rt2x00mac.c
index 11be8957b5c..64292c227c9 100644
--- a/drivers/net/wireless/rt2x00/rt2x00mac.c
+++ b/drivers/net/wireless/rt2x00/rt2x00mac.c
@@ -338,7 +338,8 @@ EXPORT_SYMBOL_GPL(rt2x00mac_remove_interface);
338int rt2x00mac_config(struct ieee80211_hw *hw, struct ieee80211_conf *conf) 338int rt2x00mac_config(struct ieee80211_hw *hw, struct ieee80211_conf *conf)
339{ 339{
340 struct rt2x00_dev *rt2x00dev = hw->priv; 340 struct rt2x00_dev *rt2x00dev = hw->priv;
341 int force_reconfig; 341 int radio_on;
342 int status;
342 343
343 /* 344 /*
344 * Mac80211 might be calling this function while we are trying 345 * Mac80211 might be calling this function while we are trying
@@ -348,35 +349,34 @@ int rt2x00mac_config(struct ieee80211_hw *hw, struct ieee80211_conf *conf)
348 return 0; 349 return 0;
349 350
350 /* 351 /*
351 * Check if we need to disable the radio, 352 * Only change device state when the radio is enabled. It does not
352 * if this is not the case, at least the RX must be disabled. 353 * matter what parameters we have configured when the radio is disabled
354 * because we won't be able to send or receive anyway. Also note that
355 * some configuration parameters (e.g. channel and antenna values) can
356 * only be set when the radio is enabled.
353 */ 357 */
354 if (test_bit(DEVICE_STATE_ENABLED_RADIO, &rt2x00dev->flags)) { 358 radio_on = test_bit(DEVICE_STATE_ENABLED_RADIO, &rt2x00dev->flags);
355 if (!conf->radio_enabled) 359 if (conf->radio_enabled) {
356 rt2x00lib_disable_radio(rt2x00dev); 360 /* For programming the values, we have to turn RX off */
357 else 361 rt2x00lib_toggle_rx(rt2x00dev, STATE_RADIO_RX_OFF);
358 rt2x00lib_toggle_rx(rt2x00dev, STATE_RADIO_RX_OFF);
359 }
360 362
361 /* 363 /* Enable the radio */
362 * When the DEVICE_DIRTY_CONFIG flag is set, the device has recently 364 status = rt2x00lib_enable_radio(rt2x00dev);
363 * been started and the configuration must be forced upon the hardware. 365 if (unlikely(status))
364 * Otherwise registers will not be intialized correctly and could 366 return status;
365 * result in non-working hardware because essential registers aren't
366 * initialized.
367 */
368 force_reconfig =
369 test_and_clear_bit(DEVICE_STATE_DIRTY_CONFIG, &rt2x00dev->flags);
370 367
371 rt2x00lib_config(rt2x00dev, conf, force_reconfig); 368 /*
369 * When we've just turned on the radio, we want to reprogram
370 * everything to ensure a consistent state
371 */
372 rt2x00lib_config(rt2x00dev, conf, !radio_on);
372 373
373 /* 374 /* Turn RX back on */
374 * Reenable RX only if the radio should be on.
375 */
376 if (test_bit(DEVICE_STATE_ENABLED_RADIO, &rt2x00dev->flags))
377 rt2x00lib_toggle_rx(rt2x00dev, STATE_RADIO_RX_ON); 375 rt2x00lib_toggle_rx(rt2x00dev, STATE_RADIO_RX_ON);
378 else if (conf->radio_enabled) 376 } else {
379 return rt2x00lib_enable_radio(rt2x00dev); 377 /* Disable the radio */
378 rt2x00lib_disable_radio(rt2x00dev);
379 }
380 380
381 return 0; 381 return 0;
382} 382}