diff options
author | John W. Linville <linville@tuxdriver.com> | 2010-10-15 16:11:56 -0400 |
---|---|---|
committer | John W. Linville <linville@tuxdriver.com> | 2010-10-15 16:11:56 -0400 |
commit | c64557d666eb62eb5f296c6b93bd0a5525ed1e36 (patch) | |
tree | 1e25cc32521d06ae876de18bb8e48b3cf9d30808 /net/mac80211 | |
parent | 1a63c353c856c9f6d44a533afb6ad6dbbcdea683 (diff) | |
parent | 0d91f22b75347d9503b17a42b6c74d3f7750acd6 (diff) | |
download | op-kernel-dev-c64557d666eb62eb5f296c6b93bd0a5525ed1e36.zip op-kernel-dev-c64557d666eb62eb5f296c6b93bd0a5525ed1e36.tar.gz |
Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/linville/wireless-next-2.6 into for-davem
Diffstat (limited to 'net/mac80211')
-rw-r--r-- | net/mac80211/cfg.c | 22 | ||||
-rw-r--r-- | net/mac80211/ht.c | 2 | ||||
-rw-r--r-- | net/mac80211/ieee80211_i.h | 4 | ||||
-rw-r--r-- | net/mac80211/iface.c | 9 | ||||
-rw-r--r-- | net/mac80211/main.c | 3 | ||||
-rw-r--r-- | net/mac80211/mesh_plink.c | 17 | ||||
-rw-r--r-- | net/mac80211/mlme.c | 18 | ||||
-rw-r--r-- | net/mac80211/rc80211_minstrel_ht.c | 7 | ||||
-rw-r--r-- | net/mac80211/rx.c | 24 | ||||
-rw-r--r-- | net/mac80211/wep.c | 8 |
10 files changed, 91 insertions, 23 deletions
diff --git a/net/mac80211/cfg.c b/net/mac80211/cfg.c index ecf9b71..18bd0e5 100644 --- a/net/mac80211/cfg.c +++ b/net/mac80211/cfg.c @@ -329,7 +329,8 @@ static void sta_set_sinfo(struct sta_info *sta, struct station_info *sinfo) STATION_INFO_TX_PACKETS | STATION_INFO_TX_RETRIES | STATION_INFO_TX_FAILED | - STATION_INFO_TX_BITRATE; + STATION_INFO_TX_BITRATE | + STATION_INFO_RX_DROP_MISC; sinfo->inactive_time = jiffies_to_msecs(jiffies - sta->last_rx); sinfo->rx_bytes = sta->rx_bytes; @@ -338,6 +339,7 @@ static void sta_set_sinfo(struct sta_info *sta, struct station_info *sinfo) sinfo->tx_packets = sta->tx_packets; sinfo->tx_retries = sta->tx_retry_count; sinfo->tx_failed = sta->tx_retry_failed; + sinfo->rx_dropped_misc = sta->rx_dropped; if ((sta->local->hw.flags & IEEE80211_HW_SIGNAL_DBM) || (sta->local->hw.flags & IEEE80211_HW_SIGNAL_UNSPEC)) { @@ -1602,6 +1604,23 @@ static int ieee80211_mgmt_tx(struct wiphy *wiphy, struct net_device *dev, return 0; } +static void ieee80211_mgmt_frame_register(struct wiphy *wiphy, + struct net_device *dev, + u16 frame_type, bool reg) +{ + struct ieee80211_local *local = wiphy_priv(wiphy); + + if (frame_type != (IEEE80211_FTYPE_MGMT | IEEE80211_STYPE_PROBE_REQ)) + return; + + if (reg) + local->probe_req_reg++; + else + local->probe_req_reg--; + + ieee80211_queue_work(&local->hw, &local->reconfig_filter); +} + struct cfg80211_ops mac80211_config_ops = { .add_virtual_intf = ieee80211_add_iface, .del_virtual_intf = ieee80211_del_iface, @@ -1653,4 +1672,5 @@ struct cfg80211_ops mac80211_config_ops = { .cancel_remain_on_channel = ieee80211_cancel_remain_on_channel, .mgmt_tx = ieee80211_mgmt_tx, .set_cqm_rssi_config = ieee80211_set_cqm_rssi_config, + .mgmt_frame_register = ieee80211_mgmt_frame_register, }; diff --git a/net/mac80211/ht.c b/net/mac80211/ht.c index 4214bb6..75d679d 100644 --- a/net/mac80211/ht.c +++ b/net/mac80211/ht.c @@ -291,6 +291,8 @@ void ieee80211_request_smps(struct ieee80211_vif *vif, if (WARN_ON(smps_mode == IEEE80211_SMPS_OFF)) smps_mode = IEEE80211_SMPS_AUTOMATIC; + sdata->u.mgd.driver_smps_mode = smps_mode; + ieee80211_queue_work(&sdata->local->hw, &sdata->u.mgd.request_smps_work); } diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h index f0610fa..b80c386 100644 --- a/net/mac80211/ieee80211_i.h +++ b/net/mac80211/ieee80211_i.h @@ -707,7 +707,9 @@ struct ieee80211_local { int open_count; int monitors, cooked_mntrs; /* number of interfaces with corresponding FIF_ flags */ - int fif_fcsfail, fif_plcpfail, fif_control, fif_other_bss, fif_pspoll; + int fif_fcsfail, fif_plcpfail, fif_control, fif_other_bss, fif_pspoll, + fif_probe_req; + int probe_req_reg; unsigned int filter_flags; /* FIF_* */ bool wiphy_ciphers_allocated; diff --git a/net/mac80211/iface.c b/net/mac80211/iface.c index e99d1b6..f9163b1 100644 --- a/net/mac80211/iface.c +++ b/net/mac80211/iface.c @@ -280,8 +280,11 @@ static int ieee80211_do_open(struct net_device *dev, bool coming_up) ieee80211_start_mesh(sdata); } else if (sdata->vif.type == NL80211_IFTYPE_AP) { local->fif_pspoll++; + local->fif_probe_req++; ieee80211_configure_filter(local); + } else if (sdata->vif.type == NL80211_IFTYPE_ADHOC) { + local->fif_probe_req++; } changed |= ieee80211_reset_erp_info(sdata); @@ -428,8 +431,12 @@ static void ieee80211_do_stop(struct ieee80211_sub_if_data *sdata, if (sdata->flags & IEEE80211_SDATA_PROMISC) atomic_dec(&local->iff_promiscs); - if (sdata->vif.type == NL80211_IFTYPE_AP) + if (sdata->vif.type == NL80211_IFTYPE_AP) { local->fif_pspoll--; + local->fif_probe_req--; + } else if (sdata->vif.type == NL80211_IFTYPE_ADHOC) { + local->fif_probe_req--; + } netif_addr_lock_bh(sdata->dev); spin_lock_bh(&local->filter_lock); diff --git a/net/mac80211/main.c b/net/mac80211/main.c index eb0f599..22bc42b 100644 --- a/net/mac80211/main.c +++ b/net/mac80211/main.c @@ -54,6 +54,9 @@ void ieee80211_configure_filter(struct ieee80211_local *local) if (local->monitors || local->scanning) new_flags |= FIF_BCN_PRBRESP_PROMISC; + if (local->fif_probe_req || local->probe_req_reg) + new_flags |= FIF_PROBE_REQ; + if (local->fif_fcsfail) new_flags |= FIF_FCSFAIL; diff --git a/net/mac80211/mesh_plink.c b/net/mac80211/mesh_plink.c index ea13a80..1c91f0f 100644 --- a/net/mac80211/mesh_plink.c +++ b/net/mac80211/mesh_plink.c @@ -412,7 +412,7 @@ void mesh_rx_plink_frame(struct ieee80211_sub_if_data *sdata, struct ieee80211_m enum plink_event event; enum plink_frame_type ftype; size_t baselen; - bool deactivated; + bool deactivated, matches_local = true; u8 ie_len; u8 *baseaddr; __le16 plid, llid, reason; @@ -487,6 +487,7 @@ void mesh_rx_plink_frame(struct ieee80211_sub_if_data *sdata, struct ieee80211_m /* Now we will figure out the appropriate event... */ event = PLINK_UNDEFINED; if (ftype != PLINK_CLOSE && (!mesh_matches_local(&elems, sdata))) { + matches_local = false; switch (ftype) { case PLINK_OPEN: event = OPN_RJCT; @@ -498,7 +499,15 @@ void mesh_rx_plink_frame(struct ieee80211_sub_if_data *sdata, struct ieee80211_m /* avoid warning */ break; } - spin_lock_bh(&sta->lock); + } + + if (!sta && !matches_local) { + rcu_read_unlock(); + reason = cpu_to_le16(MESH_CAPABILITY_POLICY_VIOLATION); + llid = 0; + mesh_plink_frame_tx(sdata, PLINK_CLOSE, mgmt->sa, llid, + plid, reason); + return; } else if (!sta) { /* ftype == PLINK_OPEN */ u32 rates; @@ -522,7 +531,7 @@ void mesh_rx_plink_frame(struct ieee80211_sub_if_data *sdata, struct ieee80211_m } event = OPN_ACPT; spin_lock_bh(&sta->lock); - } else { + } else if (matches_local) { spin_lock_bh(&sta->lock); switch (ftype) { case PLINK_OPEN: @@ -564,6 +573,8 @@ void mesh_rx_plink_frame(struct ieee80211_sub_if_data *sdata, struct ieee80211_m rcu_read_unlock(); return; } + } else { + spin_lock_bh(&sta->lock); } mpl_dbg("Mesh plink (peer, state, llid, plid, event): %pM %s %d %d %d\n", diff --git a/net/mac80211/mlme.c b/net/mac80211/mlme.c index 5695c94..a3a9421 100644 --- a/net/mac80211/mlme.c +++ b/net/mac80211/mlme.c @@ -1864,10 +1864,12 @@ void ieee80211_sta_work(struct ieee80211_sub_if_data *sdata) else if (ifmgd->probe_send_count < IEEE80211_MAX_PROBE_TRIES) { #ifdef CONFIG_MAC80211_VERBOSE_DEBUG - printk(KERN_DEBUG "No probe response from AP %pM" - " after %dms, try %d\n", bssid, - (1000 * IEEE80211_PROBE_WAIT)/HZ, - ifmgd->probe_send_count); + wiphy_debug(local->hw.wiphy, + "%s: No probe response from AP %pM" + " after %dms, try %d\n", + sdata->name, + bssid, (1000 * IEEE80211_PROBE_WAIT)/HZ, + ifmgd->probe_send_count); #endif ieee80211_mgd_probe_ap_send(sdata); } else { @@ -1877,9 +1879,11 @@ void ieee80211_sta_work(struct ieee80211_sub_if_data *sdata) */ ifmgd->flags &= ~(IEEE80211_STA_CONNECTION_POLL | IEEE80211_STA_BEACON_POLL); - printk(KERN_DEBUG "No probe response from AP %pM" - " after %dms, disconnecting.\n", - bssid, (1000 * IEEE80211_PROBE_WAIT)/HZ); + wiphy_debug(local->hw.wiphy, + "%s: No probe response from AP %pM" + " after %dms, disconnecting.\n", + sdata->name, + bssid, (1000 * IEEE80211_PROBE_WAIT)/HZ); ieee80211_set_disassoc(sdata, true, true); mutex_unlock(&ifmgd->mtx); mutex_lock(&local->mtx); diff --git a/net/mac80211/rc80211_minstrel_ht.c b/net/mac80211/rc80211_minstrel_ht.c index c5b4659..2a18d66 100644 --- a/net/mac80211/rc80211_minstrel_ht.c +++ b/net/mac80211/rc80211_minstrel_ht.c @@ -397,8 +397,9 @@ minstrel_ht_tx_status(void *priv, struct ieee80211_supported_band *sband, !(info->flags & IEEE80211_TX_STAT_AMPDU)) return; - if (!info->status.ampdu_len) { - info->status.ampdu_ack_len = 1; + if (!(info->flags & IEEE80211_TX_STAT_AMPDU)) { + info->status.ampdu_ack_len = + (info->flags & IEEE80211_TX_STAT_ACK ? 1 : 0); info->status.ampdu_len = 1; } @@ -426,7 +427,7 @@ minstrel_ht_tx_status(void *priv, struct ieee80211_supported_band *sband, group = minstrel_ht_get_group_idx(&ar[i]); rate = &mi->groups[group].rates[ar[i].idx % 8]; - if (last && (info->flags & IEEE80211_TX_STAT_ACK)) + if (last) rate->success += info->status.ampdu_ack_len; rate->attempts += ar[i].count * info->status.ampdu_len; diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c index b67221d..902b03ee 100644 --- a/net/mac80211/rx.c +++ b/net/mac80211/rx.c @@ -622,6 +622,26 @@ static void ieee80211_sta_reorder_release(struct ieee80211_hw *hw, tid_agg_rx->buf_size; } + /* + * Disable the reorder release timer for now. + * + * The current implementation lacks a proper locking scheme + * which would protect vital statistic and debug counters + * from being updated by two different but concurrent BHs. + * + * More information about the topic is available from: + * - thread: http://marc.info/?t=128635927000001 + * + * What was wrong: + * => http://marc.info/?l=linux-wireless&m=128636170811964 + * "Basically the thing is that until your patch, the data + * in the struct didn't actually need locking because it + * was accessed by the RX path only which is not concurrent." + * + * List of what needs to be fixed: + * => http://marc.info/?l=linux-wireless&m=128656352920957 + * + if (tid_agg_rx->stored_mpdu_num) { j = index = seq_sub(tid_agg_rx->head_seq_num, tid_agg_rx->ssn) % tid_agg_rx->buf_size; @@ -640,6 +660,10 @@ static void ieee80211_sta_reorder_release(struct ieee80211_hw *hw, } else { del_timer(&tid_agg_rx->reorder_timer); } + */ + +set_release_timer: + return; } /* diff --git a/net/mac80211/wep.c b/net/mac80211/wep.c index f27484c..2ff6d1e 100644 --- a/net/mac80211/wep.c +++ b/net/mac80211/wep.c @@ -222,7 +222,7 @@ static int ieee80211_wep_decrypt(struct ieee80211_local *local, struct ieee80211_key *key) { u32 klen; - u8 *rc4key; + u8 rc4key[3 + WLAN_KEY_LEN_WEP104]; u8 keyidx; struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; unsigned int hdrlen; @@ -245,10 +245,6 @@ static int ieee80211_wep_decrypt(struct ieee80211_local *local, klen = 3 + key->conf.keylen; - rc4key = kmalloc(klen, GFP_ATOMIC); - if (!rc4key) - return -1; - /* Prepend 24-bit IV to RC4 key */ memcpy(rc4key, skb->data + hdrlen, 3); @@ -260,8 +256,6 @@ static int ieee80211_wep_decrypt(struct ieee80211_local *local, len)) ret = -1; - kfree(rc4key); - /* Trim ICV */ skb_trim(skb, skb->len - WEP_ICV_LEN); |