aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless/b43legacy/main.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/wireless/b43legacy/main.c')
-rw-r--r--drivers/net/wireless/b43legacy/main.c111
1 files changed, 99 insertions, 12 deletions
diff --git a/drivers/net/wireless/b43legacy/main.c b/drivers/net/wireless/b43legacy/main.c
index 6c8eb4d2519..c1324e31d2f 100644
--- a/drivers/net/wireless/b43legacy/main.c
+++ b/drivers/net/wireless/b43legacy/main.c
@@ -576,13 +576,11 @@ static void b43legacy_set_slot_time(struct b43legacy_wldev *dev,
576static void b43legacy_short_slot_timing_enable(struct b43legacy_wldev *dev) 576static void b43legacy_short_slot_timing_enable(struct b43legacy_wldev *dev)
577{ 577{
578 b43legacy_set_slot_time(dev, 9); 578 b43legacy_set_slot_time(dev, 9);
579 dev->short_slot = 1;
580} 579}
581 580
582static void b43legacy_short_slot_timing_disable(struct b43legacy_wldev *dev) 581static void b43legacy_short_slot_timing_disable(struct b43legacy_wldev *dev)
583{ 582{
584 b43legacy_set_slot_time(dev, 20); 583 b43legacy_set_slot_time(dev, 20);
585 dev->short_slot = 0;
586} 584}
587 585
588/* Enable a Generic IRQ. "mask" is the mask of which IRQs to enable. 586/* Enable a Generic IRQ. "mask" is the mask of which IRQs to enable.
@@ -2608,16 +2606,6 @@ static int b43legacy_op_dev_config(struct ieee80211_hw *hw,
2608 if (conf->channel->hw_value != phy->channel) 2606 if (conf->channel->hw_value != phy->channel)
2609 b43legacy_radio_selectchannel(dev, conf->channel->hw_value, 0); 2607 b43legacy_radio_selectchannel(dev, conf->channel->hw_value, 0);
2610 2608
2611 /* Enable/Disable ShortSlot timing. */
2612 if ((!!(conf->flags & IEEE80211_CONF_SHORT_SLOT_TIME))
2613 != dev->short_slot) {
2614 B43legacy_WARN_ON(phy->type != B43legacy_PHYTYPE_G);
2615 if (conf->flags & IEEE80211_CONF_SHORT_SLOT_TIME)
2616 b43legacy_short_slot_timing_enable(dev);
2617 else
2618 b43legacy_short_slot_timing_disable(dev);
2619 }
2620
2621 dev->wl->radiotap_enabled = !!(conf->flags & IEEE80211_CONF_RADIOTAP); 2609 dev->wl->radiotap_enabled = !!(conf->flags & IEEE80211_CONF_RADIOTAP);
2622 2610
2623 /* Adjust the desired TX power level. */ 2611 /* Adjust the desired TX power level. */
@@ -2662,6 +2650,104 @@ out_unlock_mutex:
2662 return err; 2650 return err;
2663} 2651}
2664 2652
2653static void b43legacy_update_basic_rates(struct b43legacy_wldev *dev, u64 brates)
2654{
2655 struct ieee80211_supported_band *sband =
2656 dev->wl->hw->wiphy->bands[IEEE80211_BAND_2GHZ];
2657 struct ieee80211_rate *rate;
2658 int i;
2659 u16 basic, direct, offset, basic_offset, rateptr;
2660
2661 for (i = 0; i < sband->n_bitrates; i++) {
2662 rate = &sband->bitrates[i];
2663
2664 if (b43legacy_is_cck_rate(rate->hw_value)) {
2665 direct = B43legacy_SHM_SH_CCKDIRECT;
2666 basic = B43legacy_SHM_SH_CCKBASIC;
2667 offset = b43legacy_plcp_get_ratecode_cck(rate->hw_value);
2668 offset &= 0xF;
2669 } else {
2670 direct = B43legacy_SHM_SH_OFDMDIRECT;
2671 basic = B43legacy_SHM_SH_OFDMBASIC;
2672 offset = b43legacy_plcp_get_ratecode_ofdm(rate->hw_value);
2673 offset &= 0xF;
2674 }
2675
2676 rate = ieee80211_get_response_rate(sband, brates, rate->bitrate);
2677
2678 if (b43legacy_is_cck_rate(rate->hw_value)) {
2679 basic_offset = b43legacy_plcp_get_ratecode_cck(rate->hw_value);
2680 basic_offset &= 0xF;
2681 } else {
2682 basic_offset = b43legacy_plcp_get_ratecode_ofdm(rate->hw_value);
2683 basic_offset &= 0xF;
2684 }
2685
2686 /*
2687 * Get the pointer that we need to point to
2688 * from the direct map
2689 */
2690 rateptr = b43legacy_shm_read16(dev, B43legacy_SHM_SHARED,
2691 direct + 2 * basic_offset);
2692 /* and write it to the basic map */
2693 b43legacy_shm_write16(dev, B43legacy_SHM_SHARED,
2694 basic + 2 * offset, rateptr);
2695 }
2696}
2697
2698static void b43legacy_op_bss_info_changed(struct ieee80211_hw *hw,
2699 struct ieee80211_vif *vif,
2700 struct ieee80211_bss_conf *conf,
2701 u32 changed)
2702{
2703 struct b43legacy_wl *wl = hw_to_b43legacy_wl(hw);
2704 struct b43legacy_wldev *dev;
2705 struct b43legacy_phy *phy;
2706 unsigned long flags;
2707 u32 savedirqs;
2708
2709 mutex_lock(&wl->mutex);
2710
2711 dev = wl->current_dev;
2712 phy = &dev->phy;
2713
2714 /* Disable IRQs while reconfiguring the device.
2715 * This makes it possible to drop the spinlock throughout
2716 * the reconfiguration process. */
2717 spin_lock_irqsave(&wl->irq_lock, flags);
2718 if (b43legacy_status(dev) < B43legacy_STAT_STARTED) {
2719 spin_unlock_irqrestore(&wl->irq_lock, flags);
2720 goto out_unlock_mutex;
2721 }
2722 savedirqs = b43legacy_interrupt_disable(dev, B43legacy_IRQ_ALL);
2723 spin_unlock_irqrestore(&wl->irq_lock, flags);
2724 b43legacy_synchronize_irq(dev);
2725
2726 b43legacy_mac_suspend(dev);
2727
2728 if (changed & BSS_CHANGED_BASIC_RATES)
2729 b43legacy_update_basic_rates(dev, conf->basic_rates);
2730
2731 if (changed & BSS_CHANGED_ERP_SLOT) {
2732 if (conf->use_short_slot)
2733 b43legacy_short_slot_timing_enable(dev);
2734 else
2735 b43legacy_short_slot_timing_disable(dev);
2736 }
2737
2738 b43legacy_mac_enable(dev);
2739
2740 spin_lock_irqsave(&wl->irq_lock, flags);
2741 b43legacy_interrupt_enable(dev, savedirqs);
2742 /* XXX: why? */
2743 mmiowb();
2744 spin_unlock_irqrestore(&wl->irq_lock, flags);
2745 out_unlock_mutex:
2746 mutex_unlock(&wl->mutex);
2747
2748 return;
2749}
2750
2665static void b43legacy_op_configure_filter(struct ieee80211_hw *hw, 2751static void b43legacy_op_configure_filter(struct ieee80211_hw *hw,
2666 unsigned int changed, 2752 unsigned int changed,
2667 unsigned int *fflags, 2753 unsigned int *fflags,
@@ -3370,6 +3456,7 @@ static const struct ieee80211_ops b43legacy_hw_ops = {
3370 .add_interface = b43legacy_op_add_interface, 3456 .add_interface = b43legacy_op_add_interface,
3371 .remove_interface = b43legacy_op_remove_interface, 3457 .remove_interface = b43legacy_op_remove_interface,
3372 .config = b43legacy_op_dev_config, 3458 .config = b43legacy_op_dev_config,
3459 .bss_info_changed = b43legacy_op_bss_info_changed,
3373 .config_interface = b43legacy_op_config_interface, 3460 .config_interface = b43legacy_op_config_interface,
3374 .configure_filter = b43legacy_op_configure_filter, 3461 .configure_filter = b43legacy_op_configure_filter,
3375 .get_stats = b43legacy_op_get_stats, 3462 .get_stats = b43legacy_op_get_stats,