diff options
-rw-r--r-- | drivers/net/wireless/b43legacy/b43legacy.h | 11 | ||||
-rw-r--r-- | drivers/net/wireless/b43legacy/main.c | 16 | ||||
-rw-r--r-- | drivers/net/wireless/b43legacy/phy.c | 14 | ||||
-rw-r--r-- | drivers/net/wireless/b43legacy/radio.c | 39 |
4 files changed, 61 insertions, 19 deletions
diff --git a/drivers/net/wireless/b43legacy/b43legacy.h b/drivers/net/wireless/b43legacy/b43legacy.h index 34a6277051a1..746de2ff498c 100644 --- a/drivers/net/wireless/b43legacy/b43legacy.h +++ b/drivers/net/wireless/b43legacy/b43legacy.h | |||
@@ -411,7 +411,6 @@ struct b43legacy_phy { | |||
411 | u8 calibrated:1; | 411 | u8 calibrated:1; |
412 | u8 radio_rev; /* Radio revision */ | 412 | u8 radio_rev; /* Radio revision */ |
413 | 413 | ||
414 | bool radio_on; /* Radio switched on/off */ | ||
415 | bool locked; /* Only used in b43legacy_phy_{un}lock() */ | 414 | bool locked; /* Only used in b43legacy_phy_{un}lock() */ |
416 | bool dyn_tssi_tbl; /* tssi2dbm is kmalloc()ed. */ | 415 | bool dyn_tssi_tbl; /* tssi2dbm is kmalloc()ed. */ |
417 | 416 | ||
@@ -420,6 +419,16 @@ struct b43legacy_phy { | |||
420 | bool aci_wlan_automatic; | 419 | bool aci_wlan_automatic; |
421 | bool aci_hw_rssi; | 420 | bool aci_hw_rssi; |
422 | 421 | ||
422 | /* Radio switched on/off */ | ||
423 | bool radio_on; | ||
424 | struct { | ||
425 | /* Values saved when turning the radio off. | ||
426 | * They are needed when turning it on again. */ | ||
427 | bool valid; | ||
428 | u16 rfover; | ||
429 | u16 rfoverval; | ||
430 | } radio_off_context; | ||
431 | |||
423 | u16 minlowsig[2]; | 432 | u16 minlowsig[2]; |
424 | u16 minlowsigpos[2]; | 433 | u16 minlowsigpos[2]; |
425 | 434 | ||
diff --git a/drivers/net/wireless/b43legacy/main.c b/drivers/net/wireless/b43legacy/main.c index 61b94218094b..3e935d0d4b80 100644 --- a/drivers/net/wireless/b43legacy/main.c +++ b/drivers/net/wireless/b43legacy/main.c | |||
@@ -2660,6 +2660,22 @@ static int b43legacy_dev_config(struct ieee80211_hw *hw, | |||
2660 | b43legacy_set_beacon_int(dev, conf->beacon_int); | 2660 | b43legacy_set_beacon_int(dev, conf->beacon_int); |
2661 | 2661 | ||
2662 | 2662 | ||
2663 | if (!!conf->radio_enabled != phy->radio_on) { | ||
2664 | if (conf->radio_enabled) { | ||
2665 | b43legacy_radio_turn_on(dev); | ||
2666 | b43legacyinfo(dev->wl, "Radio turned on by software\n"); | ||
2667 | if (!dev->radio_hw_enable) | ||
2668 | b43legacyinfo(dev->wl, "The hardware RF-kill" | ||
2669 | " button still turns the radio" | ||
2670 | " physically off. Press the" | ||
2671 | " button to turn it on.\n"); | ||
2672 | } else { | ||
2673 | b43legacy_radio_turn_off(dev); | ||
2674 | b43legacyinfo(dev->wl, "Radio turned off by" | ||
2675 | " software\n"); | ||
2676 | } | ||
2677 | } | ||
2678 | |||
2663 | spin_lock_irqsave(&wl->irq_lock, flags); | 2679 | spin_lock_irqsave(&wl->irq_lock, flags); |
2664 | b43legacy_interrupt_enable(dev, savedirqs); | 2680 | b43legacy_interrupt_enable(dev, savedirqs); |
2665 | mmiowb(); | 2681 | mmiowb(); |
diff --git a/drivers/net/wireless/b43legacy/phy.c b/drivers/net/wireless/b43legacy/phy.c index f9edbd5f3009..22a4b3d0186d 100644 --- a/drivers/net/wireless/b43legacy/phy.c +++ b/drivers/net/wireless/b43legacy/phy.c | |||
@@ -462,12 +462,7 @@ static void b43legacy_phy_initb2(struct b43legacy_wldev *dev) | |||
462 | val -= 0x0202; | 462 | val -= 0x0202; |
463 | } | 463 | } |
464 | b43legacy_phy_write(dev, 0x03E4, 0x3000); | 464 | b43legacy_phy_write(dev, 0x03E4, 0x3000); |
465 | if (phy->channel == 0xFF) | 465 | b43legacy_radio_selectchannel(dev, phy->channel, 0); |
466 | b43legacy_radio_selectchannel(dev, | ||
467 | B43legacy_RADIO_DEFAULT_CHANNEL_BG, | ||
468 | 0); | ||
469 | else | ||
470 | b43legacy_radio_selectchannel(dev, phy->channel, 0); | ||
471 | if (phy->radio_ver != 0x2050) { | 466 | if (phy->radio_ver != 0x2050) { |
472 | b43legacy_radio_write16(dev, 0x0075, 0x0080); | 467 | b43legacy_radio_write16(dev, 0x0075, 0x0080); |
473 | b43legacy_radio_write16(dev, 0x0079, 0x0081); | 468 | b43legacy_radio_write16(dev, 0x0079, 0x0081); |
@@ -516,12 +511,7 @@ static void b43legacy_phy_initb4(struct b43legacy_wldev *dev) | |||
516 | val -= 0x0202; | 511 | val -= 0x0202; |
517 | } | 512 | } |
518 | b43legacy_phy_write(dev, 0x03E4, 0x3000); | 513 | b43legacy_phy_write(dev, 0x03E4, 0x3000); |
519 | if (phy->channel == 0xFF) | 514 | b43legacy_radio_selectchannel(dev, phy->channel, 0); |
520 | b43legacy_radio_selectchannel(dev, | ||
521 | B43legacy_RADIO_DEFAULT_CHANNEL_BG, | ||
522 | 0); | ||
523 | else | ||
524 | b43legacy_radio_selectchannel(dev, phy->channel, 0); | ||
525 | if (phy->radio_ver != 0x2050) { | 515 | if (phy->radio_ver != 0x2050) { |
526 | b43legacy_radio_write16(dev, 0x0075, 0x0080); | 516 | b43legacy_radio_write16(dev, 0x0075, 0x0080); |
527 | b43legacy_radio_write16(dev, 0x0079, 0x0081); | 517 | b43legacy_radio_write16(dev, 0x0079, 0x0081); |
diff --git a/drivers/net/wireless/b43legacy/radio.c b/drivers/net/wireless/b43legacy/radio.c index 2a11ee63f400..54067f082825 100644 --- a/drivers/net/wireless/b43legacy/radio.c +++ b/drivers/net/wireless/b43legacy/radio.c | |||
@@ -1767,6 +1767,17 @@ int b43legacy_radio_selectchannel(struct b43legacy_wldev *dev, | |||
1767 | { | 1767 | { |
1768 | struct b43legacy_phy *phy = &dev->phy; | 1768 | struct b43legacy_phy *phy = &dev->phy; |
1769 | 1769 | ||
1770 | if (channel == 0xFF) { | ||
1771 | switch (phy->type) { | ||
1772 | case B43legacy_PHYTYPE_B: | ||
1773 | case B43legacy_PHYTYPE_G: | ||
1774 | channel = B43legacy_RADIO_DEFAULT_CHANNEL_BG; | ||
1775 | break; | ||
1776 | default: | ||
1777 | B43legacy_WARN_ON(1); | ||
1778 | } | ||
1779 | } | ||
1780 | |||
1770 | /* TODO: Check if channel is valid - return -EINVAL if not */ | 1781 | /* TODO: Check if channel is valid - return -EINVAL if not */ |
1771 | if (synthetic_pu_workaround) | 1782 | if (synthetic_pu_workaround) |
1772 | b43legacy_synth_pu_workaround(dev, channel); | 1783 | b43legacy_synth_pu_workaround(dev, channel); |
@@ -2070,6 +2081,7 @@ void b43legacy_radio_turn_on(struct b43legacy_wldev *dev) | |||
2070 | { | 2081 | { |
2071 | struct b43legacy_phy *phy = &dev->phy; | 2082 | struct b43legacy_phy *phy = &dev->phy; |
2072 | int err; | 2083 | int err; |
2084 | u8 channel; | ||
2073 | 2085 | ||
2074 | might_sleep(); | 2086 | might_sleep(); |
2075 | 2087 | ||
@@ -2083,15 +2095,24 @@ void b43legacy_radio_turn_on(struct b43legacy_wldev *dev) | |||
2083 | b43legacy_phy_write(dev, 0x0015, 0xCC00); | 2095 | b43legacy_phy_write(dev, 0x0015, 0xCC00); |
2084 | b43legacy_phy_write(dev, 0x0015, | 2096 | b43legacy_phy_write(dev, 0x0015, |
2085 | (phy->gmode ? 0x00C0 : 0x0000)); | 2097 | (phy->gmode ? 0x00C0 : 0x0000)); |
2098 | if (phy->radio_off_context.valid) { | ||
2099 | /* Restore the RFover values. */ | ||
2100 | b43legacy_phy_write(dev, B43legacy_PHY_RFOVER, | ||
2101 | phy->radio_off_context.rfover); | ||
2102 | b43legacy_phy_write(dev, B43legacy_PHY_RFOVERVAL, | ||
2103 | phy->radio_off_context.rfoverval); | ||
2104 | phy->radio_off_context.valid = 0; | ||
2105 | } | ||
2106 | channel = phy->channel; | ||
2086 | err = b43legacy_radio_selectchannel(dev, | 2107 | err = b43legacy_radio_selectchannel(dev, |
2087 | B43legacy_RADIO_DEFAULT_CHANNEL_BG, 1); | 2108 | B43legacy_RADIO_DEFAULT_CHANNEL_BG, 1); |
2088 | B43legacy_WARN_ON(err != 0); | 2109 | err |= b43legacy_radio_selectchannel(dev, channel, 0); |
2110 | B43legacy_WARN_ON(err); | ||
2089 | break; | 2111 | break; |
2090 | default: | 2112 | default: |
2091 | B43legacy_BUG_ON(1); | 2113 | B43legacy_BUG_ON(1); |
2092 | } | 2114 | } |
2093 | phy->radio_on = 1; | 2115 | phy->radio_on = 1; |
2094 | b43legacydbg(dev->wl, "Radio turned on\n"); | ||
2095 | b43legacy_leds_update(dev, 0); | 2116 | b43legacy_leds_update(dev, 0); |
2096 | } | 2117 | } |
2097 | 2118 | ||
@@ -2100,10 +2121,16 @@ void b43legacy_radio_turn_off(struct b43legacy_wldev *dev) | |||
2100 | struct b43legacy_phy *phy = &dev->phy; | 2121 | struct b43legacy_phy *phy = &dev->phy; |
2101 | 2122 | ||
2102 | if (phy->type == B43legacy_PHYTYPE_G && dev->dev->id.revision >= 5) { | 2123 | if (phy->type == B43legacy_PHYTYPE_G && dev->dev->id.revision >= 5) { |
2103 | b43legacy_phy_write(dev, 0x0811, b43legacy_phy_read(dev, 0x0811) | 2124 | u16 rfover, rfoverval; |
2104 | | 0x008C); | 2125 | |
2105 | b43legacy_phy_write(dev, 0x0812, b43legacy_phy_read(dev, 0x0812) | 2126 | rfover = b43legacy_phy_read(dev, B43legacy_PHY_RFOVER); |
2106 | & 0xFF73); | 2127 | rfoverval = b43legacy_phy_read(dev, B43legacy_PHY_RFOVERVAL); |
2128 | phy->radio_off_context.rfover = rfover; | ||
2129 | phy->radio_off_context.rfoverval = rfoverval; | ||
2130 | phy->radio_off_context.valid = 1; | ||
2131 | b43legacy_phy_write(dev, B43legacy_PHY_RFOVER, rfover | 0x008C); | ||
2132 | b43legacy_phy_write(dev, B43legacy_PHY_RFOVERVAL, | ||
2133 | rfoverval & 0xFF73); | ||
2107 | } else | 2134 | } else |
2108 | b43legacy_phy_write(dev, 0x0015, 0xAA00); | 2135 | b43legacy_phy_write(dev, 0x0015, 0xAA00); |
2109 | phy->radio_on = 0; | 2136 | phy->radio_on = 0; |