diff options
author | Ingo Molnar <mingo@elte.hu> | 2008-07-11 04:46:50 -0400 |
---|---|---|
committer | Ingo Molnar <mingo@elte.hu> | 2008-07-11 04:46:50 -0400 |
commit | 0c81b2a1448bc6a2a9b2d6469fb0669fb4b25e5b (patch) | |
tree | 6f82579cae6d6e39fa9f837a3c349ded51e19d14 /drivers/net/wireless | |
parent | 0729fbf3bc70870370b4f43d652f05a468dc68b8 (diff) | |
parent | 70ff05554f91a1edda1f11684da1dbde09e2feea (diff) |
Merge branch 'linus' into core/rcu
Conflicts:
include/linux/rculist.h
kernel/rcupreempt.c
Signed-off-by: Ingo Molnar <mingo@elte.hu>
Diffstat (limited to 'drivers/net/wireless')
20 files changed, 157 insertions, 107 deletions
diff --git a/drivers/net/wireless/b43/leds.c b/drivers/net/wireless/b43/leds.c index 36a9c42df835..76f4c7bad8b8 100644 --- a/drivers/net/wireless/b43/leds.c +++ b/drivers/net/wireless/b43/leds.c | |||
@@ -72,6 +72,9 @@ static void b43_led_brightness_set(struct led_classdev *led_dev, | |||
72 | struct b43_wldev *dev = led->dev; | 72 | struct b43_wldev *dev = led->dev; |
73 | bool radio_enabled; | 73 | bool radio_enabled; |
74 | 74 | ||
75 | if (unlikely(b43_status(dev) < B43_STAT_INITIALIZED)) | ||
76 | return; | ||
77 | |||
75 | /* Checking the radio-enabled status here is slightly racy, | 78 | /* Checking the radio-enabled status here is slightly racy, |
76 | * but we want to avoid the locking overhead and we don't care | 79 | * but we want to avoid the locking overhead and we don't care |
77 | * whether the LED has the wrong state for a second. */ | 80 | * whether the LED has the wrong state for a second. */ |
diff --git a/drivers/net/wireless/b43/main.c b/drivers/net/wireless/b43/main.c index fa4b0d8b74a2..a70827793086 100644 --- a/drivers/net/wireless/b43/main.c +++ b/drivers/net/wireless/b43/main.c | |||
@@ -2883,12 +2883,11 @@ static int b43_op_tx(struct ieee80211_hw *hw, | |||
2883 | 2883 | ||
2884 | if (unlikely(skb->len < 2 + 2 + 6)) { | 2884 | if (unlikely(skb->len < 2 + 2 + 6)) { |
2885 | /* Too short, this can't be a valid frame. */ | 2885 | /* Too short, this can't be a valid frame. */ |
2886 | dev_kfree_skb_any(skb); | 2886 | goto drop_packet; |
2887 | return NETDEV_TX_OK; | ||
2888 | } | 2887 | } |
2889 | B43_WARN_ON(skb_shinfo(skb)->nr_frags); | 2888 | B43_WARN_ON(skb_shinfo(skb)->nr_frags); |
2890 | if (unlikely(!dev)) | 2889 | if (unlikely(!dev)) |
2891 | return NETDEV_TX_BUSY; | 2890 | goto drop_packet; |
2892 | 2891 | ||
2893 | /* Transmissions on seperate queues can run concurrently. */ | 2892 | /* Transmissions on seperate queues can run concurrently. */ |
2894 | read_lock_irqsave(&wl->tx_lock, flags); | 2893 | read_lock_irqsave(&wl->tx_lock, flags); |
@@ -2904,7 +2903,12 @@ static int b43_op_tx(struct ieee80211_hw *hw, | |||
2904 | read_unlock_irqrestore(&wl->tx_lock, flags); | 2903 | read_unlock_irqrestore(&wl->tx_lock, flags); |
2905 | 2904 | ||
2906 | if (unlikely(err)) | 2905 | if (unlikely(err)) |
2907 | return NETDEV_TX_BUSY; | 2906 | goto drop_packet; |
2907 | return NETDEV_TX_OK; | ||
2908 | |||
2909 | drop_packet: | ||
2910 | /* We can not transmit this packet. Drop it. */ | ||
2911 | dev_kfree_skb_any(skb); | ||
2908 | return NETDEV_TX_OK; | 2912 | return NETDEV_TX_OK; |
2909 | } | 2913 | } |
2910 | 2914 | ||
diff --git a/drivers/net/wireless/b43legacy/dma.c b/drivers/net/wireless/b43legacy/dma.c index c990f87b107a..93ddc1cbcc8b 100644 --- a/drivers/net/wireless/b43legacy/dma.c +++ b/drivers/net/wireless/b43legacy/dma.c | |||
@@ -876,6 +876,7 @@ struct b43legacy_dmaring *b43legacy_setup_dmaring(struct b43legacy_wldev *dev, | |||
876 | if (!ring) | 876 | if (!ring) |
877 | goto out; | 877 | goto out; |
878 | ring->type = type; | 878 | ring->type = type; |
879 | ring->dev = dev; | ||
879 | 880 | ||
880 | nr_slots = B43legacy_RXRING_SLOTS; | 881 | nr_slots = B43legacy_RXRING_SLOTS; |
881 | if (for_tx) | 882 | if (for_tx) |
@@ -922,7 +923,6 @@ struct b43legacy_dmaring *b43legacy_setup_dmaring(struct b43legacy_wldev *dev, | |||
922 | DMA_TO_DEVICE); | 923 | DMA_TO_DEVICE); |
923 | } | 924 | } |
924 | 925 | ||
925 | ring->dev = dev; | ||
926 | ring->nr_slots = nr_slots; | 926 | ring->nr_slots = nr_slots; |
927 | ring->mmio_base = b43legacy_dmacontroller_base(type, controller_index); | 927 | ring->mmio_base = b43legacy_dmacontroller_base(type, controller_index); |
928 | ring->index = controller_index; | 928 | ring->index = controller_index; |
diff --git a/drivers/net/wireless/b43legacy/main.c b/drivers/net/wireless/b43legacy/main.c index 204077c13870..3e612d0a13e8 100644 --- a/drivers/net/wireless/b43legacy/main.c +++ b/drivers/net/wireless/b43legacy/main.c | |||
@@ -2378,8 +2378,10 @@ static int b43legacy_op_tx(struct ieee80211_hw *hw, | |||
2378 | } else | 2378 | } else |
2379 | err = b43legacy_dma_tx(dev, skb, ctl); | 2379 | err = b43legacy_dma_tx(dev, skb, ctl); |
2380 | out: | 2380 | out: |
2381 | if (unlikely(err)) | 2381 | if (unlikely(err)) { |
2382 | return NETDEV_TX_BUSY; | 2382 | /* Drop the packet. */ |
2383 | dev_kfree_skb_any(skb); | ||
2384 | } | ||
2383 | return NETDEV_TX_OK; | 2385 | return NETDEV_TX_OK; |
2384 | } | 2386 | } |
2385 | 2387 | ||
diff --git a/drivers/net/wireless/hostap/hostap_80211_rx.c b/drivers/net/wireless/hostap/hostap_80211_rx.c index 4fd73809602e..020f450e9dba 100644 --- a/drivers/net/wireless/hostap/hostap_80211_rx.c +++ b/drivers/net/wireless/hostap/hostap_80211_rx.c | |||
@@ -64,7 +64,7 @@ int prism2_rx_80211(struct net_device *dev, struct sk_buff *skb, | |||
64 | int hdrlen, phdrlen, head_need, tail_need; | 64 | int hdrlen, phdrlen, head_need, tail_need; |
65 | u16 fc; | 65 | u16 fc; |
66 | int prism_header, ret; | 66 | int prism_header, ret; |
67 | struct ieee80211_hdr_4addr *hdr; | 67 | struct ieee80211_hdr_4addr *fhdr; |
68 | 68 | ||
69 | iface = netdev_priv(dev); | 69 | iface = netdev_priv(dev); |
70 | local = iface->local; | 70 | local = iface->local; |
@@ -83,8 +83,8 @@ int prism2_rx_80211(struct net_device *dev, struct sk_buff *skb, | |||
83 | phdrlen = 0; | 83 | phdrlen = 0; |
84 | } | 84 | } |
85 | 85 | ||
86 | hdr = (struct ieee80211_hdr_4addr *) skb->data; | 86 | fhdr = (struct ieee80211_hdr_4addr *) skb->data; |
87 | fc = le16_to_cpu(hdr->frame_ctl); | 87 | fc = le16_to_cpu(fhdr->frame_ctl); |
88 | 88 | ||
89 | if (type == PRISM2_RX_MGMT && (fc & IEEE80211_FCTL_VERS)) { | 89 | if (type == PRISM2_RX_MGMT && (fc & IEEE80211_FCTL_VERS)) { |
90 | printk(KERN_DEBUG "%s: dropped management frame with header " | 90 | printk(KERN_DEBUG "%s: dropped management frame with header " |
@@ -551,7 +551,7 @@ hostap_rx_frame_wds(local_info_t *local, struct ieee80211_hdr_4addr *hdr, | |||
551 | hdr->addr1[2] != 0xff || hdr->addr1[3] != 0xff || | 551 | hdr->addr1[2] != 0xff || hdr->addr1[3] != 0xff || |
552 | hdr->addr1[4] != 0xff || hdr->addr1[5] != 0xff)) { | 552 | hdr->addr1[4] != 0xff || hdr->addr1[5] != 0xff)) { |
553 | /* RA (or BSSID) is not ours - drop */ | 553 | /* RA (or BSSID) is not ours - drop */ |
554 | PDEBUG(DEBUG_EXTRA, "%s: received WDS frame with " | 554 | PDEBUG(DEBUG_EXTRA2, "%s: received WDS frame with " |
555 | "not own or broadcast %s=%s\n", | 555 | "not own or broadcast %s=%s\n", |
556 | local->dev->name, | 556 | local->dev->name, |
557 | fc & IEEE80211_FCTL_FROMDS ? "RA" : "BSSID", | 557 | fc & IEEE80211_FCTL_FROMDS ? "RA" : "BSSID", |
diff --git a/drivers/net/wireless/hostap/hostap_ap.c b/drivers/net/wireless/hostap/hostap_ap.c index 0acd9589c48c..ab981afd481d 100644 --- a/drivers/net/wireless/hostap/hostap_ap.c +++ b/drivers/net/wireless/hostap/hostap_ap.c | |||
@@ -1930,7 +1930,7 @@ static void handle_pspoll(local_info_t *local, | |||
1930 | PDEBUG(DEBUG_PS, " PSPOLL and AID[15:14] not set\n"); | 1930 | PDEBUG(DEBUG_PS, " PSPOLL and AID[15:14] not set\n"); |
1931 | return; | 1931 | return; |
1932 | } | 1932 | } |
1933 | aid &= ~BIT(15) & ~BIT(14); | 1933 | aid &= ~(BIT(15) | BIT(14)); |
1934 | if (aid == 0 || aid > MAX_AID_TABLE_SIZE) { | 1934 | if (aid == 0 || aid > MAX_AID_TABLE_SIZE) { |
1935 | PDEBUG(DEBUG_PS, " invalid aid=%d\n", aid); | 1935 | PDEBUG(DEBUG_PS, " invalid aid=%d\n", aid); |
1936 | return; | 1936 | return; |
diff --git a/drivers/net/wireless/hostap/hostap_cs.c b/drivers/net/wireless/hostap/hostap_cs.c index ed4317a17cbb..80039a0ae027 100644 --- a/drivers/net/wireless/hostap/hostap_cs.c +++ b/drivers/net/wireless/hostap/hostap_cs.c | |||
@@ -533,10 +533,10 @@ static void prism2_detach(struct pcmcia_device *link) | |||
533 | do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) | 533 | do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) |
534 | 534 | ||
535 | #define CFG_CHECK2(fn, retf) \ | 535 | #define CFG_CHECK2(fn, retf) \ |
536 | do { int ret = (retf); \ | 536 | do { int _ret = (retf); \ |
537 | if (ret != 0) { \ | 537 | if (_ret != 0) { \ |
538 | PDEBUG(DEBUG_EXTRA, "CardServices(" #fn ") returned %d\n", ret); \ | 538 | PDEBUG(DEBUG_EXTRA, "CardServices(" #fn ") returned %d\n", _ret); \ |
539 | cs_error(link, fn, ret); \ | 539 | cs_error(link, fn, _ret); \ |
540 | goto next_entry; \ | 540 | goto next_entry; \ |
541 | } \ | 541 | } \ |
542 | } while (0) | 542 | } while (0) |
diff --git a/drivers/net/wireless/hostap/hostap_hw.c b/drivers/net/wireless/hostap/hostap_hw.c index cdf90c40f11b..936f52e3d95c 100644 --- a/drivers/net/wireless/hostap/hostap_hw.c +++ b/drivers/net/wireless/hostap/hostap_hw.c | |||
@@ -2835,7 +2835,7 @@ static void hostap_passive_scan(unsigned long data) | |||
2835 | { | 2835 | { |
2836 | local_info_t *local = (local_info_t *) data; | 2836 | local_info_t *local = (local_info_t *) data; |
2837 | struct net_device *dev = local->dev; | 2837 | struct net_device *dev = local->dev; |
2838 | u16 channel; | 2838 | u16 chan; |
2839 | 2839 | ||
2840 | if (local->passive_scan_interval <= 0) | 2840 | if (local->passive_scan_interval <= 0) |
2841 | return; | 2841 | return; |
@@ -2872,11 +2872,11 @@ static void hostap_passive_scan(unsigned long data) | |||
2872 | 2872 | ||
2873 | printk(KERN_DEBUG "%s: passive scan channel %d\n", | 2873 | printk(KERN_DEBUG "%s: passive scan channel %d\n", |
2874 | dev->name, local->passive_scan_channel); | 2874 | dev->name, local->passive_scan_channel); |
2875 | channel = local->passive_scan_channel; | 2875 | chan = local->passive_scan_channel; |
2876 | local->passive_scan_state = PASSIVE_SCAN_WAIT; | 2876 | local->passive_scan_state = PASSIVE_SCAN_WAIT; |
2877 | local->passive_scan_timer.expires = jiffies + HZ / 10; | 2877 | local->passive_scan_timer.expires = jiffies + HZ / 10; |
2878 | } else { | 2878 | } else { |
2879 | channel = local->channel; | 2879 | chan = local->channel; |
2880 | local->passive_scan_state = PASSIVE_SCAN_LISTEN; | 2880 | local->passive_scan_state = PASSIVE_SCAN_LISTEN; |
2881 | local->passive_scan_timer.expires = jiffies + | 2881 | local->passive_scan_timer.expires = jiffies + |
2882 | local->passive_scan_interval * HZ; | 2882 | local->passive_scan_interval * HZ; |
@@ -2884,9 +2884,9 @@ static void hostap_passive_scan(unsigned long data) | |||
2884 | 2884 | ||
2885 | if (hfa384x_cmd_callback(dev, HFA384X_CMDCODE_TEST | | 2885 | if (hfa384x_cmd_callback(dev, HFA384X_CMDCODE_TEST | |
2886 | (HFA384X_TEST_CHANGE_CHANNEL << 8), | 2886 | (HFA384X_TEST_CHANGE_CHANNEL << 8), |
2887 | channel, NULL, 0)) | 2887 | chan, NULL, 0)) |
2888 | printk(KERN_ERR "%s: passive scan channel set %d " | 2888 | printk(KERN_ERR "%s: passive scan channel set %d " |
2889 | "failed\n", dev->name, channel); | 2889 | "failed\n", dev->name, chan); |
2890 | 2890 | ||
2891 | add_timer(&local->passive_scan_timer); | 2891 | add_timer(&local->passive_scan_timer); |
2892 | } | 2892 | } |
diff --git a/drivers/net/wireless/hostap/hostap_main.c b/drivers/net/wireless/hostap/hostap_main.c index f7aec9309d04..a38e85f334df 100644 --- a/drivers/net/wireless/hostap/hostap_main.c +++ b/drivers/net/wireless/hostap/hostap_main.c | |||
@@ -594,7 +594,8 @@ void hostap_dump_tx_header(const char *name, const struct hfa384x_tx_frame *tx) | |||
594 | } | 594 | } |
595 | 595 | ||
596 | 596 | ||
597 | int hostap_80211_header_parse(const struct sk_buff *skb, unsigned char *haddr) | 597 | static int hostap_80211_header_parse(const struct sk_buff *skb, |
598 | unsigned char *haddr) | ||
598 | { | 599 | { |
599 | struct hostap_interface *iface = netdev_priv(skb->dev); | 600 | struct hostap_interface *iface = netdev_priv(skb->dev); |
600 | local_info_t *local = iface->local; | 601 | local_info_t *local = iface->local; |
@@ -857,7 +858,6 @@ const struct header_ops hostap_80211_ops = { | |||
857 | .rebuild = eth_rebuild_header, | 858 | .rebuild = eth_rebuild_header, |
858 | .cache = eth_header_cache, | 859 | .cache = eth_header_cache, |
859 | .cache_update = eth_header_cache_update, | 860 | .cache_update = eth_header_cache_update, |
860 | |||
861 | .parse = hostap_80211_header_parse, | 861 | .parse = hostap_80211_header_parse, |
862 | }; | 862 | }; |
863 | EXPORT_SYMBOL(hostap_80211_ops); | 863 | EXPORT_SYMBOL(hostap_80211_ops); |
@@ -1150,7 +1150,6 @@ EXPORT_SYMBOL(hostap_set_roaming); | |||
1150 | EXPORT_SYMBOL(hostap_set_auth_algs); | 1150 | EXPORT_SYMBOL(hostap_set_auth_algs); |
1151 | EXPORT_SYMBOL(hostap_dump_rx_header); | 1151 | EXPORT_SYMBOL(hostap_dump_rx_header); |
1152 | EXPORT_SYMBOL(hostap_dump_tx_header); | 1152 | EXPORT_SYMBOL(hostap_dump_tx_header); |
1153 | EXPORT_SYMBOL(hostap_80211_header_parse); | ||
1154 | EXPORT_SYMBOL(hostap_80211_get_hdrlen); | 1153 | EXPORT_SYMBOL(hostap_80211_get_hdrlen); |
1155 | EXPORT_SYMBOL(hostap_get_stats); | 1154 | EXPORT_SYMBOL(hostap_get_stats); |
1156 | EXPORT_SYMBOL(hostap_setup_dev); | 1155 | EXPORT_SYMBOL(hostap_setup_dev); |
diff --git a/drivers/net/wireless/iwlwifi/iwl-3945.c b/drivers/net/wireless/iwlwifi/iwl-3945.c index 62a3d8f8563e..f5387a7a76c0 100644 --- a/drivers/net/wireless/iwlwifi/iwl-3945.c +++ b/drivers/net/wireless/iwlwifi/iwl-3945.c | |||
@@ -588,8 +588,12 @@ static void iwl3945_add_radiotap(struct iwl3945_priv *priv, | |||
588 | 588 | ||
589 | if (rate == -1) | 589 | if (rate == -1) |
590 | iwl3945_rt->rt_rate = 0; | 590 | iwl3945_rt->rt_rate = 0; |
591 | else | 591 | else { |
592 | if (stats->band == IEEE80211_BAND_5GHZ) | ||
593 | rate += IWL_FIRST_OFDM_RATE; | ||
594 | |||
592 | iwl3945_rt->rt_rate = iwl3945_rates[rate].ieee; | 595 | iwl3945_rt->rt_rate = iwl3945_rates[rate].ieee; |
596 | } | ||
593 | 597 | ||
594 | /* antenna number */ | 598 | /* antenna number */ |
595 | antenna = phy_flags_hw & RX_RES_PHY_FLAGS_ANTENNA_MSK; | 599 | antenna = phy_flags_hw & RX_RES_PHY_FLAGS_ANTENNA_MSK; |
diff --git a/drivers/net/wireless/iwlwifi/iwl-4965.c b/drivers/net/wireless/iwlwifi/iwl-4965.c index bf19eb8aafd0..de330ae0ca95 100644 --- a/drivers/net/wireless/iwlwifi/iwl-4965.c +++ b/drivers/net/wireless/iwlwifi/iwl-4965.c | |||
@@ -3528,8 +3528,12 @@ static void iwl4965_add_radiotap(struct iwl_priv *priv, | |||
3528 | 3528 | ||
3529 | if (rate == -1) | 3529 | if (rate == -1) |
3530 | iwl4965_rt->rt_rate = 0; | 3530 | iwl4965_rt->rt_rate = 0; |
3531 | else | 3531 | else { |
3532 | if (stats->band == IEEE80211_BAND_5GHZ) | ||
3533 | rate += IWL_FIRST_OFDM_RATE; | ||
3534 | |||
3532 | iwl4965_rt->rt_rate = iwl4965_rates[rate].ieee; | 3535 | iwl4965_rt->rt_rate = iwl4965_rates[rate].ieee; |
3536 | } | ||
3533 | 3537 | ||
3534 | /* | 3538 | /* |
3535 | * "antenna number" | 3539 | * "antenna number" |
diff --git a/drivers/net/wireless/iwlwifi/iwl3945-base.c b/drivers/net/wireless/iwlwifi/iwl3945-base.c index 13925b627e3b..6027e1119c3f 100644 --- a/drivers/net/wireless/iwlwifi/iwl3945-base.c +++ b/drivers/net/wireless/iwlwifi/iwl3945-base.c | |||
@@ -2227,7 +2227,10 @@ static int iwl3945_scan_initiate(struct iwl3945_priv *priv) | |||
2227 | } | 2227 | } |
2228 | 2228 | ||
2229 | IWL_DEBUG_INFO("Starting scan...\n"); | 2229 | IWL_DEBUG_INFO("Starting scan...\n"); |
2230 | priv->scan_bands = 2; | 2230 | if (priv->cfg->sku & IWL_SKU_G) |
2231 | priv->scan_bands |= BIT(IEEE80211_BAND_2GHZ); | ||
2232 | if (priv->cfg->sku & IWL_SKU_A) | ||
2233 | priv->scan_bands |= BIT(IEEE80211_BAND_5GHZ); | ||
2231 | set_bit(STATUS_SCANNING, &priv->status); | 2234 | set_bit(STATUS_SCANNING, &priv->status); |
2232 | priv->scan_start = jiffies; | 2235 | priv->scan_start = jiffies; |
2233 | priv->scan_pass_start = priv->scan_start; | 2236 | priv->scan_pass_start = priv->scan_start; |
@@ -3352,13 +3355,18 @@ static void iwl3945_rx_scan_complete_notif(struct iwl3945_priv *priv, | |||
3352 | cancel_delayed_work(&priv->scan_check); | 3355 | cancel_delayed_work(&priv->scan_check); |
3353 | 3356 | ||
3354 | IWL_DEBUG_INFO("Scan pass on %sGHz took %dms\n", | 3357 | IWL_DEBUG_INFO("Scan pass on %sGHz took %dms\n", |
3355 | (priv->scan_bands == 2) ? "2.4" : "5.2", | 3358 | (priv->scan_bands & BIT(IEEE80211_BAND_2GHZ)) ? |
3359 | "2.4" : "5.2", | ||
3356 | jiffies_to_msecs(elapsed_jiffies | 3360 | jiffies_to_msecs(elapsed_jiffies |
3357 | (priv->scan_pass_start, jiffies))); | 3361 | (priv->scan_pass_start, jiffies))); |
3358 | 3362 | ||
3359 | /* Remove this scanned band from the list | 3363 | /* Remove this scanned band from the list of pending |
3360 | * of pending bands to scan */ | 3364 | * bands to scan, band G precedes A in order of scanning |
3361 | priv->scan_bands--; | 3365 | * as seen in iwl3945_bg_request_scan */ |
3366 | if (priv->scan_bands & BIT(IEEE80211_BAND_2GHZ)) | ||
3367 | priv->scan_bands &= ~BIT(IEEE80211_BAND_2GHZ); | ||
3368 | else if (priv->scan_bands & BIT(IEEE80211_BAND_5GHZ)) | ||
3369 | priv->scan_bands &= ~BIT(IEEE80211_BAND_5GHZ); | ||
3362 | 3370 | ||
3363 | /* If a request to abort was given, or the scan did not succeed | 3371 | /* If a request to abort was given, or the scan did not succeed |
3364 | * then we reset the scan state machine and terminate, | 3372 | * then we reset the scan state machine and terminate, |
@@ -4972,7 +4980,7 @@ static int iwl3945_get_channels_for_scan(struct iwl3945_priv *priv, | |||
4972 | 4980 | ||
4973 | ch_info = iwl3945_get_channel_info(priv, band, scan_ch->channel); | 4981 | ch_info = iwl3945_get_channel_info(priv, band, scan_ch->channel); |
4974 | if (!is_channel_valid(ch_info)) { | 4982 | if (!is_channel_valid(ch_info)) { |
4975 | IWL_DEBUG_SCAN("Channel %d is INVALID for this SKU.\n", | 4983 | IWL_DEBUG_SCAN("Channel %d is INVALID for this band.\n", |
4976 | scan_ch->channel); | 4984 | scan_ch->channel); |
4977 | continue; | 4985 | continue; |
4978 | } | 4986 | } |
@@ -6315,21 +6323,16 @@ static void iwl3945_bg_request_scan(struct work_struct *data) | |||
6315 | 6323 | ||
6316 | /* flags + rate selection */ | 6324 | /* flags + rate selection */ |
6317 | 6325 | ||
6318 | switch (priv->scan_bands) { | 6326 | if (priv->scan_bands & BIT(IEEE80211_BAND_2GHZ)) { |
6319 | case 2: | ||
6320 | scan->flags = RXON_FLG_BAND_24G_MSK | RXON_FLG_AUTO_DETECT_MSK; | 6327 | scan->flags = RXON_FLG_BAND_24G_MSK | RXON_FLG_AUTO_DETECT_MSK; |
6321 | scan->tx_cmd.rate = IWL_RATE_1M_PLCP; | 6328 | scan->tx_cmd.rate = IWL_RATE_1M_PLCP; |
6322 | scan->good_CRC_th = 0; | 6329 | scan->good_CRC_th = 0; |
6323 | band = IEEE80211_BAND_2GHZ; | 6330 | band = IEEE80211_BAND_2GHZ; |
6324 | break; | 6331 | } else if (priv->scan_bands & BIT(IEEE80211_BAND_5GHZ)) { |
6325 | |||
6326 | case 1: | ||
6327 | scan->tx_cmd.rate = IWL_RATE_6M_PLCP; | 6332 | scan->tx_cmd.rate = IWL_RATE_6M_PLCP; |
6328 | scan->good_CRC_th = IWL_GOOD_CRC_TH; | 6333 | scan->good_CRC_th = IWL_GOOD_CRC_TH; |
6329 | band = IEEE80211_BAND_5GHZ; | 6334 | band = IEEE80211_BAND_5GHZ; |
6330 | break; | 6335 | } else { |
6331 | |||
6332 | default: | ||
6333 | IWL_WARNING("Invalid scan band count\n"); | 6336 | IWL_WARNING("Invalid scan band count\n"); |
6334 | goto done; | 6337 | goto done; |
6335 | } | 6338 | } |
@@ -6684,7 +6687,8 @@ static int iwl3945_mac_tx(struct ieee80211_hw *hw, struct sk_buff *skb, | |||
6684 | 6687 | ||
6685 | if (priv->iw_mode == IEEE80211_IF_TYPE_MNTR) { | 6688 | if (priv->iw_mode == IEEE80211_IF_TYPE_MNTR) { |
6686 | IWL_DEBUG_MAC80211("leave - monitor\n"); | 6689 | IWL_DEBUG_MAC80211("leave - monitor\n"); |
6687 | return -1; | 6690 | dev_kfree_skb_any(skb); |
6691 | return 0; | ||
6688 | } | 6692 | } |
6689 | 6693 | ||
6690 | IWL_DEBUG_TX("dev->xmit(%d bytes) at rate 0x%02x\n", skb->len, | 6694 | IWL_DEBUG_TX("dev->xmit(%d bytes) at rate 0x%02x\n", skb->len, |
@@ -6770,7 +6774,7 @@ static int iwl3945_mac_config(struct ieee80211_hw *hw, struct ieee80211_conf *co | |||
6770 | ch_info = iwl3945_get_channel_info(priv, conf->channel->band, | 6774 | ch_info = iwl3945_get_channel_info(priv, conf->channel->band, |
6771 | conf->channel->hw_value); | 6775 | conf->channel->hw_value); |
6772 | if (!is_channel_valid(ch_info)) { | 6776 | if (!is_channel_valid(ch_info)) { |
6773 | IWL_DEBUG_SCAN("Channel %d [%d] is INVALID for this SKU.\n", | 6777 | IWL_DEBUG_SCAN("Channel %d [%d] is INVALID for this band.\n", |
6774 | conf->channel->hw_value, conf->channel->band); | 6778 | conf->channel->hw_value, conf->channel->band); |
6775 | IWL_DEBUG_MAC80211("leave - invalid channel\n"); | 6779 | IWL_DEBUG_MAC80211("leave - invalid channel\n"); |
6776 | spin_unlock_irqrestore(&priv->lock, flags); | 6780 | spin_unlock_irqrestore(&priv->lock, flags); |
diff --git a/drivers/net/wireless/iwlwifi/iwl4965-base.c b/drivers/net/wireless/iwlwifi/iwl4965-base.c index 883b42f7e998..0bd55bb19739 100644 --- a/drivers/net/wireless/iwlwifi/iwl4965-base.c +++ b/drivers/net/wireless/iwlwifi/iwl4965-base.c | |||
@@ -1774,7 +1774,10 @@ static int iwl4965_scan_initiate(struct iwl_priv *priv) | |||
1774 | } | 1774 | } |
1775 | 1775 | ||
1776 | IWL_DEBUG_INFO("Starting scan...\n"); | 1776 | IWL_DEBUG_INFO("Starting scan...\n"); |
1777 | priv->scan_bands = 2; | 1777 | if (priv->cfg->sku & IWL_SKU_G) |
1778 | priv->scan_bands |= BIT(IEEE80211_BAND_2GHZ); | ||
1779 | if (priv->cfg->sku & IWL_SKU_A) | ||
1780 | priv->scan_bands |= BIT(IEEE80211_BAND_5GHZ); | ||
1778 | set_bit(STATUS_SCANNING, &priv->status); | 1781 | set_bit(STATUS_SCANNING, &priv->status); |
1779 | priv->scan_start = jiffies; | 1782 | priv->scan_start = jiffies; |
1780 | priv->scan_pass_start = priv->scan_start; | 1783 | priv->scan_pass_start = priv->scan_start; |
@@ -3023,8 +3026,9 @@ static void iwl4965_rx_reply_tx(struct iwl_priv *priv, | |||
3023 | 3026 | ||
3024 | IWL_DEBUG_TX_REPLY("Tx queue reclaim %d\n", index); | 3027 | IWL_DEBUG_TX_REPLY("Tx queue reclaim %d\n", index); |
3025 | if (index != -1) { | 3028 | if (index != -1) { |
3026 | int freed = iwl4965_tx_queue_reclaim(priv, txq_id, index); | ||
3027 | #ifdef CONFIG_IWL4965_HT | 3029 | #ifdef CONFIG_IWL4965_HT |
3030 | int freed = iwl4965_tx_queue_reclaim(priv, txq_id, index); | ||
3031 | |||
3028 | if (tid != MAX_TID_COUNT) | 3032 | if (tid != MAX_TID_COUNT) |
3029 | priv->stations[sta_id].tid[tid].tfds_in_queue -= freed; | 3033 | priv->stations[sta_id].tid[tid].tfds_in_queue -= freed; |
3030 | if (iwl4965_queue_space(&txq->q) > txq->q.low_mark && | 3034 | if (iwl4965_queue_space(&txq->q) > txq->q.low_mark && |
@@ -3276,13 +3280,18 @@ static void iwl4965_rx_scan_complete_notif(struct iwl_priv *priv, | |||
3276 | cancel_delayed_work(&priv->scan_check); | 3280 | cancel_delayed_work(&priv->scan_check); |
3277 | 3281 | ||
3278 | IWL_DEBUG_INFO("Scan pass on %sGHz took %dms\n", | 3282 | IWL_DEBUG_INFO("Scan pass on %sGHz took %dms\n", |
3279 | (priv->scan_bands == 2) ? "2.4" : "5.2", | 3283 | (priv->scan_bands & BIT(IEEE80211_BAND_2GHZ)) ? |
3284 | "2.4" : "5.2", | ||
3280 | jiffies_to_msecs(elapsed_jiffies | 3285 | jiffies_to_msecs(elapsed_jiffies |
3281 | (priv->scan_pass_start, jiffies))); | 3286 | (priv->scan_pass_start, jiffies))); |
3282 | 3287 | ||
3283 | /* Remove this scanned band from the list | 3288 | /* Remove this scanned band from the list of pending |
3284 | * of pending bands to scan */ | 3289 | * bands to scan, band G precedes A in order of scanning |
3285 | priv->scan_bands--; | 3290 | * as seen in iwl_bg_request_scan */ |
3291 | if (priv->scan_bands & BIT(IEEE80211_BAND_2GHZ)) | ||
3292 | priv->scan_bands &= ~BIT(IEEE80211_BAND_2GHZ); | ||
3293 | else if (priv->scan_bands & BIT(IEEE80211_BAND_5GHZ)) | ||
3294 | priv->scan_bands &= ~BIT(IEEE80211_BAND_5GHZ); | ||
3286 | 3295 | ||
3287 | /* If a request to abort was given, or the scan did not succeed | 3296 | /* If a request to abort was given, or the scan did not succeed |
3288 | * then we reset the scan state machine and terminate, | 3297 | * then we reset the scan state machine and terminate, |
@@ -3292,7 +3301,7 @@ static void iwl4965_rx_scan_complete_notif(struct iwl_priv *priv, | |||
3292 | clear_bit(STATUS_SCAN_ABORTING, &priv->status); | 3301 | clear_bit(STATUS_SCAN_ABORTING, &priv->status); |
3293 | } else { | 3302 | } else { |
3294 | /* If there are more bands on this scan pass reschedule */ | 3303 | /* If there are more bands on this scan pass reschedule */ |
3295 | if (priv->scan_bands > 0) | 3304 | if (priv->scan_bands) |
3296 | goto reschedule; | 3305 | goto reschedule; |
3297 | } | 3306 | } |
3298 | 3307 | ||
@@ -4635,10 +4644,9 @@ static int iwl4965_get_channels_for_scan(struct iwl_priv *priv, | |||
4635 | 4644 | ||
4636 | scan_ch->channel = ieee80211_frequency_to_channel(channels[i].center_freq); | 4645 | scan_ch->channel = ieee80211_frequency_to_channel(channels[i].center_freq); |
4637 | 4646 | ||
4638 | ch_info = iwl_get_channel_info(priv, band, | 4647 | ch_info = iwl_get_channel_info(priv, band, scan_ch->channel); |
4639 | scan_ch->channel); | ||
4640 | if (!is_channel_valid(ch_info)) { | 4648 | if (!is_channel_valid(ch_info)) { |
4641 | IWL_DEBUG_SCAN("Channel %d is INVALID for this SKU.\n", | 4649 | IWL_DEBUG_SCAN("Channel %d is INVALID for this band.\n", |
4642 | scan_ch->channel); | 4650 | scan_ch->channel); |
4643 | continue; | 4651 | continue; |
4644 | } | 4652 | } |
@@ -5830,8 +5838,7 @@ static void iwl4965_bg_request_scan(struct work_struct *data) | |||
5830 | scan->tx_cmd.stop_time.life_time = TX_CMD_LIFE_TIME_INFINITE; | 5838 | scan->tx_cmd.stop_time.life_time = TX_CMD_LIFE_TIME_INFINITE; |
5831 | 5839 | ||
5832 | 5840 | ||
5833 | switch (priv->scan_bands) { | 5841 | if (priv->scan_bands & BIT(IEEE80211_BAND_2GHZ)) { |
5834 | case 2: | ||
5835 | scan->flags = RXON_FLG_BAND_24G_MSK | RXON_FLG_AUTO_DETECT_MSK; | 5842 | scan->flags = RXON_FLG_BAND_24G_MSK | RXON_FLG_AUTO_DETECT_MSK; |
5836 | scan->tx_cmd.rate_n_flags = | 5843 | scan->tx_cmd.rate_n_flags = |
5837 | iwl4965_hw_set_rate_n_flags(IWL_RATE_1M_PLCP, | 5844 | iwl4965_hw_set_rate_n_flags(IWL_RATE_1M_PLCP, |
@@ -5839,17 +5846,13 @@ static void iwl4965_bg_request_scan(struct work_struct *data) | |||
5839 | 5846 | ||
5840 | scan->good_CRC_th = 0; | 5847 | scan->good_CRC_th = 0; |
5841 | band = IEEE80211_BAND_2GHZ; | 5848 | band = IEEE80211_BAND_2GHZ; |
5842 | break; | 5849 | } else if (priv->scan_bands & BIT(IEEE80211_BAND_5GHZ)) { |
5843 | |||
5844 | case 1: | ||
5845 | scan->tx_cmd.rate_n_flags = | 5850 | scan->tx_cmd.rate_n_flags = |
5846 | iwl4965_hw_set_rate_n_flags(IWL_RATE_6M_PLCP, | 5851 | iwl4965_hw_set_rate_n_flags(IWL_RATE_6M_PLCP, |
5847 | RATE_MCS_ANT_B_MSK); | 5852 | RATE_MCS_ANT_B_MSK); |
5848 | scan->good_CRC_th = IWL_GOOD_CRC_TH; | 5853 | scan->good_CRC_th = IWL_GOOD_CRC_TH; |
5849 | band = IEEE80211_BAND_5GHZ; | 5854 | band = IEEE80211_BAND_5GHZ; |
5850 | break; | 5855 | } else { |
5851 | |||
5852 | default: | ||
5853 | IWL_WARNING("Invalid scan band count\n"); | 5856 | IWL_WARNING("Invalid scan band count\n"); |
5854 | goto done; | 5857 | goto done; |
5855 | } | 5858 | } |
@@ -6234,7 +6237,8 @@ static int iwl4965_mac_tx(struct ieee80211_hw *hw, struct sk_buff *skb, | |||
6234 | 6237 | ||
6235 | if (priv->iw_mode == IEEE80211_IF_TYPE_MNTR) { | 6238 | if (priv->iw_mode == IEEE80211_IF_TYPE_MNTR) { |
6236 | IWL_DEBUG_MAC80211("leave - monitor\n"); | 6239 | IWL_DEBUG_MAC80211("leave - monitor\n"); |
6237 | return -1; | 6240 | dev_kfree_skb_any(skb); |
6241 | return 0; | ||
6238 | } | 6242 | } |
6239 | 6243 | ||
6240 | IWL_DEBUG_TX("dev->xmit(%d bytes) at rate 0x%02x\n", skb->len, | 6244 | IWL_DEBUG_TX("dev->xmit(%d bytes) at rate 0x%02x\n", skb->len, |
diff --git a/drivers/net/wireless/libertas/if_usb.c b/drivers/net/wireless/libertas/if_usb.c index 8032df72aaab..36288b29abf7 100644 --- a/drivers/net/wireless/libertas/if_usb.c +++ b/drivers/net/wireless/libertas/if_usb.c | |||
@@ -925,6 +925,7 @@ static struct usb_driver if_usb_driver = { | |||
925 | .id_table = if_usb_table, | 925 | .id_table = if_usb_table, |
926 | .suspend = if_usb_suspend, | 926 | .suspend = if_usb_suspend, |
927 | .resume = if_usb_resume, | 927 | .resume = if_usb_resume, |
928 | .reset_resume = if_usb_resume, | ||
928 | }; | 929 | }; |
929 | 930 | ||
930 | static int __init if_usb_init_module(void) | 931 | static int __init if_usb_init_module(void) |
diff --git a/drivers/net/wireless/prism54/islpci_eth.c b/drivers/net/wireless/prism54/islpci_eth.c index 762e85bef55d..e43bae97ed8f 100644 --- a/drivers/net/wireless/prism54/islpci_eth.c +++ b/drivers/net/wireless/prism54/islpci_eth.c | |||
@@ -290,7 +290,7 @@ islpci_monitor_rx(islpci_private *priv, struct sk_buff **skb) | |||
290 | 290 | ||
291 | avs->version = cpu_to_be32(P80211CAPTURE_VERSION); | 291 | avs->version = cpu_to_be32(P80211CAPTURE_VERSION); |
292 | avs->length = cpu_to_be32(sizeof (struct avs_80211_1_header)); | 292 | avs->length = cpu_to_be32(sizeof (struct avs_80211_1_header)); |
293 | avs->mactime = cpu_to_be64(le64_to_cpu(clock)); | 293 | avs->mactime = cpu_to_be64(clock); |
294 | avs->hosttime = cpu_to_be64(jiffies); | 294 | avs->hosttime = cpu_to_be64(jiffies); |
295 | avs->phytype = cpu_to_be32(6); /*OFDM: 6 for (g), 8 for (a) */ | 295 | avs->phytype = cpu_to_be32(6); /*OFDM: 6 for (g), 8 for (a) */ |
296 | avs->channel = cpu_to_be32(channel_of_freq(freq)); | 296 | avs->channel = cpu_to_be32(channel_of_freq(freq)); |
diff --git a/drivers/net/wireless/rt2x00/rt2500usb.c b/drivers/net/wireless/rt2x00/rt2500usb.c index fdbd0ef2be4b..61e59c17a60a 100644 --- a/drivers/net/wireless/rt2x00/rt2500usb.c +++ b/drivers/net/wireless/rt2x00/rt2500usb.c | |||
@@ -138,11 +138,8 @@ static void rt2500usb_bbp_write(struct rt2x00_dev *rt2x00dev, | |||
138 | * Wait until the BBP becomes ready. | 138 | * Wait until the BBP becomes ready. |
139 | */ | 139 | */ |
140 | reg = rt2500usb_bbp_check(rt2x00dev); | 140 | reg = rt2500usb_bbp_check(rt2x00dev); |
141 | if (rt2x00_get_field16(reg, PHY_CSR8_BUSY)) { | 141 | if (rt2x00_get_field16(reg, PHY_CSR8_BUSY)) |
142 | ERROR(rt2x00dev, "PHY_CSR8 register busy. Write failed.\n"); | 142 | goto exit_fail; |
143 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | ||
144 | return; | ||
145 | } | ||
146 | 143 | ||
147 | /* | 144 | /* |
148 | * Write the data into the BBP. | 145 | * Write the data into the BBP. |
@@ -155,6 +152,13 @@ static void rt2500usb_bbp_write(struct rt2x00_dev *rt2x00dev, | |||
155 | rt2500usb_register_write_lock(rt2x00dev, PHY_CSR7, reg); | 152 | rt2500usb_register_write_lock(rt2x00dev, PHY_CSR7, reg); |
156 | 153 | ||
157 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | 154 | mutex_unlock(&rt2x00dev->usb_cache_mutex); |
155 | |||
156 | return; | ||
157 | |||
158 | exit_fail: | ||
159 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | ||
160 | |||
161 | ERROR(rt2x00dev, "PHY_CSR8 register busy. Write failed.\n"); | ||
158 | } | 162 | } |
159 | 163 | ||
160 | static void rt2500usb_bbp_read(struct rt2x00_dev *rt2x00dev, | 164 | static void rt2500usb_bbp_read(struct rt2x00_dev *rt2x00dev, |
@@ -168,10 +172,8 @@ static void rt2500usb_bbp_read(struct rt2x00_dev *rt2x00dev, | |||
168 | * Wait until the BBP becomes ready. | 172 | * Wait until the BBP becomes ready. |
169 | */ | 173 | */ |
170 | reg = rt2500usb_bbp_check(rt2x00dev); | 174 | reg = rt2500usb_bbp_check(rt2x00dev); |
171 | if (rt2x00_get_field16(reg, PHY_CSR8_BUSY)) { | 175 | if (rt2x00_get_field16(reg, PHY_CSR8_BUSY)) |
172 | ERROR(rt2x00dev, "PHY_CSR8 register busy. Read failed.\n"); | 176 | goto exit_fail; |
173 | return; | ||
174 | } | ||
175 | 177 | ||
176 | /* | 178 | /* |
177 | * Write the request into the BBP. | 179 | * Write the request into the BBP. |
@@ -186,17 +188,21 @@ static void rt2500usb_bbp_read(struct rt2x00_dev *rt2x00dev, | |||
186 | * Wait until the BBP becomes ready. | 188 | * Wait until the BBP becomes ready. |
187 | */ | 189 | */ |
188 | reg = rt2500usb_bbp_check(rt2x00dev); | 190 | reg = rt2500usb_bbp_check(rt2x00dev); |
189 | if (rt2x00_get_field16(reg, PHY_CSR8_BUSY)) { | 191 | if (rt2x00_get_field16(reg, PHY_CSR8_BUSY)) |
190 | ERROR(rt2x00dev, "PHY_CSR8 register busy. Read failed.\n"); | 192 | goto exit_fail; |
191 | *value = 0xff; | ||
192 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | ||
193 | return; | ||
194 | } | ||
195 | 193 | ||
196 | rt2500usb_register_read_lock(rt2x00dev, PHY_CSR7, ®); | 194 | rt2500usb_register_read_lock(rt2x00dev, PHY_CSR7, ®); |
197 | *value = rt2x00_get_field16(reg, PHY_CSR7_DATA); | 195 | *value = rt2x00_get_field16(reg, PHY_CSR7_DATA); |
198 | 196 | ||
199 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | 197 | mutex_unlock(&rt2x00dev->usb_cache_mutex); |
198 | |||
199 | return; | ||
200 | |||
201 | exit_fail: | ||
202 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | ||
203 | |||
204 | ERROR(rt2x00dev, "PHY_CSR8 register busy. Read failed.\n"); | ||
205 | *value = 0xff; | ||
200 | } | 206 | } |
201 | 207 | ||
202 | static void rt2500usb_rf_write(struct rt2x00_dev *rt2x00dev, | 208 | static void rt2500usb_rf_write(struct rt2x00_dev *rt2x00dev, |
diff --git a/drivers/net/wireless/rt2x00/rt2x00.h b/drivers/net/wireless/rt2x00/rt2x00.h index 611d98320593..b4bf1e09cf9a 100644 --- a/drivers/net/wireless/rt2x00/rt2x00.h +++ b/drivers/net/wireless/rt2x00/rt2x00.h | |||
@@ -821,6 +821,7 @@ struct rt2x00_dev { | |||
821 | /* | 821 | /* |
822 | * Scheduled work. | 822 | * Scheduled work. |
823 | */ | 823 | */ |
824 | struct workqueue_struct *workqueue; | ||
824 | struct work_struct intf_work; | 825 | struct work_struct intf_work; |
825 | struct work_struct filter_work; | 826 | struct work_struct filter_work; |
826 | 827 | ||
diff --git a/drivers/net/wireless/rt2x00/rt2x00dev.c b/drivers/net/wireless/rt2x00/rt2x00dev.c index 2673d568bcac..c997d4f28ab3 100644 --- a/drivers/net/wireless/rt2x00/rt2x00dev.c +++ b/drivers/net/wireless/rt2x00/rt2x00dev.c | |||
@@ -75,7 +75,7 @@ static void rt2x00lib_start_link_tuner(struct rt2x00_dev *rt2x00dev) | |||
75 | 75 | ||
76 | rt2x00lib_reset_link_tuner(rt2x00dev); | 76 | rt2x00lib_reset_link_tuner(rt2x00dev); |
77 | 77 | ||
78 | queue_delayed_work(rt2x00dev->hw->workqueue, | 78 | queue_delayed_work(rt2x00dev->workqueue, |
79 | &rt2x00dev->link.work, LINK_TUNE_INTERVAL); | 79 | &rt2x00dev->link.work, LINK_TUNE_INTERVAL); |
80 | } | 80 | } |
81 | 81 | ||
@@ -137,14 +137,6 @@ void rt2x00lib_disable_radio(struct rt2x00_dev *rt2x00dev) | |||
137 | return; | 137 | return; |
138 | 138 | ||
139 | /* | 139 | /* |
140 | * Stop all scheduled work. | ||
141 | */ | ||
142 | if (work_pending(&rt2x00dev->intf_work)) | ||
143 | cancel_work_sync(&rt2x00dev->intf_work); | ||
144 | if (work_pending(&rt2x00dev->filter_work)) | ||
145 | cancel_work_sync(&rt2x00dev->filter_work); | ||
146 | |||
147 | /* | ||
148 | * Stop the TX queues. | 140 | * Stop the TX queues. |
149 | */ | 141 | */ |
150 | ieee80211_stop_queues(rt2x00dev->hw); | 142 | ieee80211_stop_queues(rt2x00dev->hw); |
@@ -398,8 +390,8 @@ static void rt2x00lib_link_tuner(struct work_struct *work) | |||
398 | * Increase tuner counter, and reschedule the next link tuner run. | 390 | * Increase tuner counter, and reschedule the next link tuner run. |
399 | */ | 391 | */ |
400 | rt2x00dev->link.count++; | 392 | rt2x00dev->link.count++; |
401 | queue_delayed_work(rt2x00dev->hw->workqueue, &rt2x00dev->link.work, | 393 | queue_delayed_work(rt2x00dev->workqueue, |
402 | LINK_TUNE_INTERVAL); | 394 | &rt2x00dev->link.work, LINK_TUNE_INTERVAL); |
403 | } | 395 | } |
404 | 396 | ||
405 | static void rt2x00lib_packetfilter_scheduled(struct work_struct *work) | 397 | static void rt2x00lib_packetfilter_scheduled(struct work_struct *work) |
@@ -433,6 +425,15 @@ static void rt2x00lib_intf_scheduled_iter(void *data, u8 *mac, | |||
433 | 425 | ||
434 | spin_unlock(&intf->lock); | 426 | spin_unlock(&intf->lock); |
435 | 427 | ||
428 | /* | ||
429 | * It is possible the radio was disabled while the work had been | ||
430 | * scheduled. If that happens we should return here immediately, | ||
431 | * note that in the spinlock protected area above the delayed_flags | ||
432 | * have been cleared correctly. | ||
433 | */ | ||
434 | if (!test_bit(DEVICE_ENABLED_RADIO, &rt2x00dev->flags)) | ||
435 | return; | ||
436 | |||
436 | if (delayed_flags & DELAYED_UPDATE_BEACON) { | 437 | if (delayed_flags & DELAYED_UPDATE_BEACON) { |
437 | skb = ieee80211_beacon_get(rt2x00dev->hw, vif, &control); | 438 | skb = ieee80211_beacon_get(rt2x00dev->hw, vif, &control); |
438 | if (skb && rt2x00dev->ops->hw->beacon_update(rt2x00dev->hw, | 439 | if (skb && rt2x00dev->ops->hw->beacon_update(rt2x00dev->hw, |
@@ -441,7 +442,7 @@ static void rt2x00lib_intf_scheduled_iter(void *data, u8 *mac, | |||
441 | } | 442 | } |
442 | 443 | ||
443 | if (delayed_flags & DELAYED_CONFIG_ERP) | 444 | if (delayed_flags & DELAYED_CONFIG_ERP) |
444 | rt2x00lib_config_erp(rt2x00dev, intf, &intf->conf); | 445 | rt2x00lib_config_erp(rt2x00dev, intf, &conf); |
445 | 446 | ||
446 | if (delayed_flags & DELAYED_LED_ASSOC) | 447 | if (delayed_flags & DELAYED_LED_ASSOC) |
447 | rt2x00leds_led_assoc(rt2x00dev, !!rt2x00dev->intf_associated); | 448 | rt2x00leds_led_assoc(rt2x00dev, !!rt2x00dev->intf_associated); |
@@ -487,7 +488,7 @@ void rt2x00lib_beacondone(struct rt2x00_dev *rt2x00dev) | |||
487 | rt2x00lib_beacondone_iter, | 488 | rt2x00lib_beacondone_iter, |
488 | rt2x00dev); | 489 | rt2x00dev); |
489 | 490 | ||
490 | queue_work(rt2x00dev->hw->workqueue, &rt2x00dev->intf_work); | 491 | queue_work(rt2x00dev->workqueue, &rt2x00dev->intf_work); |
491 | } | 492 | } |
492 | EXPORT_SYMBOL_GPL(rt2x00lib_beacondone); | 493 | EXPORT_SYMBOL_GPL(rt2x00lib_beacondone); |
493 | 494 | ||
@@ -1130,6 +1131,10 @@ int rt2x00lib_probe_dev(struct rt2x00_dev *rt2x00dev) | |||
1130 | /* | 1131 | /* |
1131 | * Initialize configuration work. | 1132 | * Initialize configuration work. |
1132 | */ | 1133 | */ |
1134 | rt2x00dev->workqueue = create_singlethread_workqueue("rt2x00lib"); | ||
1135 | if (!rt2x00dev->workqueue) | ||
1136 | goto exit; | ||
1137 | |||
1133 | INIT_WORK(&rt2x00dev->intf_work, rt2x00lib_intf_scheduled); | 1138 | INIT_WORK(&rt2x00dev->intf_work, rt2x00lib_intf_scheduled); |
1134 | INIT_WORK(&rt2x00dev->filter_work, rt2x00lib_packetfilter_scheduled); | 1139 | INIT_WORK(&rt2x00dev->filter_work, rt2x00lib_packetfilter_scheduled); |
1135 | INIT_DELAYED_WORK(&rt2x00dev->link.work, rt2x00lib_link_tuner); | 1140 | INIT_DELAYED_WORK(&rt2x00dev->link.work, rt2x00lib_link_tuner); |
@@ -1190,6 +1195,13 @@ void rt2x00lib_remove_dev(struct rt2x00_dev *rt2x00dev) | |||
1190 | rt2x00leds_unregister(rt2x00dev); | 1195 | rt2x00leds_unregister(rt2x00dev); |
1191 | 1196 | ||
1192 | /* | 1197 | /* |
1198 | * Stop all queued work. Note that most tasks will already be halted | ||
1199 | * during rt2x00lib_disable_radio() and rt2x00lib_uninitialize(). | ||
1200 | */ | ||
1201 | flush_workqueue(rt2x00dev->workqueue); | ||
1202 | destroy_workqueue(rt2x00dev->workqueue); | ||
1203 | |||
1204 | /* | ||
1193 | * Free ieee80211_hw memory. | 1205 | * Free ieee80211_hw memory. |
1194 | */ | 1206 | */ |
1195 | rt2x00lib_remove_hw(rt2x00dev); | 1207 | rt2x00lib_remove_hw(rt2x00dev); |
diff --git a/drivers/net/wireless/rt2x00/rt2x00mac.c b/drivers/net/wireless/rt2x00/rt2x00mac.c index 87e280a21971..9cb023edd2e9 100644 --- a/drivers/net/wireless/rt2x00/rt2x00mac.c +++ b/drivers/net/wireless/rt2x00/rt2x00mac.c | |||
@@ -428,7 +428,7 @@ void rt2x00mac_configure_filter(struct ieee80211_hw *hw, | |||
428 | if (!test_bit(DRIVER_REQUIRE_SCHEDULED, &rt2x00dev->flags)) | 428 | if (!test_bit(DRIVER_REQUIRE_SCHEDULED, &rt2x00dev->flags)) |
429 | rt2x00dev->ops->lib->config_filter(rt2x00dev, *total_flags); | 429 | rt2x00dev->ops->lib->config_filter(rt2x00dev, *total_flags); |
430 | else | 430 | else |
431 | queue_work(rt2x00dev->hw->workqueue, &rt2x00dev->filter_work); | 431 | queue_work(rt2x00dev->workqueue, &rt2x00dev->filter_work); |
432 | } | 432 | } |
433 | EXPORT_SYMBOL_GPL(rt2x00mac_configure_filter); | 433 | EXPORT_SYMBOL_GPL(rt2x00mac_configure_filter); |
434 | 434 | ||
@@ -509,7 +509,7 @@ void rt2x00mac_bss_info_changed(struct ieee80211_hw *hw, | |||
509 | memcpy(&intf->conf, bss_conf, sizeof(*bss_conf)); | 509 | memcpy(&intf->conf, bss_conf, sizeof(*bss_conf)); |
510 | if (delayed) { | 510 | if (delayed) { |
511 | intf->delayed_flags |= delayed; | 511 | intf->delayed_flags |= delayed; |
512 | queue_work(rt2x00dev->hw->workqueue, &rt2x00dev->intf_work); | 512 | queue_work(rt2x00dev->workqueue, &rt2x00dev->intf_work); |
513 | } | 513 | } |
514 | spin_unlock(&intf->lock); | 514 | spin_unlock(&intf->lock); |
515 | } | 515 | } |
diff --git a/drivers/net/wireless/rt2x00/rt73usb.c b/drivers/net/wireless/rt2x00/rt73usb.c index fff8386e816b..83cc0147f698 100644 --- a/drivers/net/wireless/rt2x00/rt73usb.c +++ b/drivers/net/wireless/rt2x00/rt73usb.c | |||
@@ -134,11 +134,8 @@ static void rt73usb_bbp_write(struct rt2x00_dev *rt2x00dev, | |||
134 | * Wait until the BBP becomes ready. | 134 | * Wait until the BBP becomes ready. |
135 | */ | 135 | */ |
136 | reg = rt73usb_bbp_check(rt2x00dev); | 136 | reg = rt73usb_bbp_check(rt2x00dev); |
137 | if (rt2x00_get_field32(reg, PHY_CSR3_BUSY)) { | 137 | if (rt2x00_get_field32(reg, PHY_CSR3_BUSY)) |
138 | ERROR(rt2x00dev, "PHY_CSR3 register busy. Write failed.\n"); | 138 | goto exit_fail; |
139 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | ||
140 | return; | ||
141 | } | ||
142 | 139 | ||
143 | /* | 140 | /* |
144 | * Write the data into the BBP. | 141 | * Write the data into the BBP. |
@@ -151,6 +148,13 @@ static void rt73usb_bbp_write(struct rt2x00_dev *rt2x00dev, | |||
151 | 148 | ||
152 | rt73usb_register_write_lock(rt2x00dev, PHY_CSR3, reg); | 149 | rt73usb_register_write_lock(rt2x00dev, PHY_CSR3, reg); |
153 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | 150 | mutex_unlock(&rt2x00dev->usb_cache_mutex); |
151 | |||
152 | return; | ||
153 | |||
154 | exit_fail: | ||
155 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | ||
156 | |||
157 | ERROR(rt2x00dev, "PHY_CSR3 register busy. Write failed.\n"); | ||
154 | } | 158 | } |
155 | 159 | ||
156 | static void rt73usb_bbp_read(struct rt2x00_dev *rt2x00dev, | 160 | static void rt73usb_bbp_read(struct rt2x00_dev *rt2x00dev, |
@@ -164,11 +168,8 @@ static void rt73usb_bbp_read(struct rt2x00_dev *rt2x00dev, | |||
164 | * Wait until the BBP becomes ready. | 168 | * Wait until the BBP becomes ready. |
165 | */ | 169 | */ |
166 | reg = rt73usb_bbp_check(rt2x00dev); | 170 | reg = rt73usb_bbp_check(rt2x00dev); |
167 | if (rt2x00_get_field32(reg, PHY_CSR3_BUSY)) { | 171 | if (rt2x00_get_field32(reg, PHY_CSR3_BUSY)) |
168 | ERROR(rt2x00dev, "PHY_CSR3 register busy. Read failed.\n"); | 172 | goto exit_fail; |
169 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | ||
170 | return; | ||
171 | } | ||
172 | 173 | ||
173 | /* | 174 | /* |
174 | * Write the request into the BBP. | 175 | * Write the request into the BBP. |
@@ -184,14 +185,19 @@ static void rt73usb_bbp_read(struct rt2x00_dev *rt2x00dev, | |||
184 | * Wait until the BBP becomes ready. | 185 | * Wait until the BBP becomes ready. |
185 | */ | 186 | */ |
186 | reg = rt73usb_bbp_check(rt2x00dev); | 187 | reg = rt73usb_bbp_check(rt2x00dev); |
187 | if (rt2x00_get_field32(reg, PHY_CSR3_BUSY)) { | 188 | if (rt2x00_get_field32(reg, PHY_CSR3_BUSY)) |
188 | ERROR(rt2x00dev, "PHY_CSR3 register busy. Read failed.\n"); | 189 | goto exit_fail; |
189 | *value = 0xff; | ||
190 | return; | ||
191 | } | ||
192 | 190 | ||
193 | *value = rt2x00_get_field32(reg, PHY_CSR3_VALUE); | 191 | *value = rt2x00_get_field32(reg, PHY_CSR3_VALUE); |
194 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | 192 | mutex_unlock(&rt2x00dev->usb_cache_mutex); |
193 | |||
194 | return; | ||
195 | |||
196 | exit_fail: | ||
197 | mutex_unlock(&rt2x00dev->usb_cache_mutex); | ||
198 | |||
199 | ERROR(rt2x00dev, "PHY_CSR3 register busy. Read failed.\n"); | ||
200 | *value = 0xff; | ||
195 | } | 201 | } |
196 | 202 | ||
197 | static void rt73usb_rf_write(struct rt2x00_dev *rt2x00dev, | 203 | static void rt73usb_rf_write(struct rt2x00_dev *rt2x00dev, |