aboutsummaryrefslogtreecommitdiffstats
path: root/net/wireless
diff options
context:
space:
mode:
authorJohannes Berg <johannes@sipsolutions.net>2009-11-02 07:32:03 -0500
committerJohn W. Linville <linville@tuxdriver.com>2009-11-02 15:43:29 -0500
commit584991dccfd347cd2e1675ab262998f6c335d3c0 (patch)
tree0cb52e1f06e587561f0e06e1beae7de7faaf5528 /net/wireless
parent6c085227bd7168fd84976479218f81bf35b5acd7 (diff)
cfg80211: validate scan channels
Currently it is possible to request a scan on only disabled channels, which could be problematic for some drivers. Reject such scans, and also ignore disabled channels that are given. This resuls in the scan begin/end event only including channels that are actually used. This makes the mac80211 check for disabled channels superfluous. At the same time, remove the no-IBSS check from mac80211 -- nothing says that we should not find any networks on channels that cannot be used for an IBSS, even when operating in IBSS mode. Signed-off-by: Johannes Berg <johannes@sipsolutions.net> Signed-off-by: John W. Linville <linville@tuxdriver.com>
Diffstat (limited to 'net/wireless')
-rw-r--r--net/wireless/nl80211.c34
-rw-r--r--net/wireless/scan.c6
2 files changed, 33 insertions, 7 deletions
diff --git a/net/wireless/nl80211.c b/net/wireless/nl80211.c
index f48394126bf9..8ed62b6c172b 100644
--- a/net/wireless/nl80211.c
+++ b/net/wireless/nl80211.c
@@ -2988,7 +2988,6 @@ static int nl80211_trigger_scan(struct sk_buff *skb, struct genl_info *info)
2988 goto out; 2988 goto out;
2989 } 2989 }
2990 2990
2991 request->n_channels = n_channels;
2992 if (n_ssids) 2991 if (n_ssids)
2993 request->ssids = (void *)&request->channels[n_channels]; 2992 request->ssids = (void *)&request->channels[n_channels];
2994 request->n_ssids = n_ssids; 2993 request->n_ssids = n_ssids;
@@ -2999,32 +2998,53 @@ static int nl80211_trigger_scan(struct sk_buff *skb, struct genl_info *info)
2999 request->ie = (void *)(request->channels + n_channels); 2998 request->ie = (void *)(request->channels + n_channels);
3000 } 2999 }
3001 3000
3001 i = 0;
3002 if (info->attrs[NL80211_ATTR_SCAN_FREQUENCIES]) { 3002 if (info->attrs[NL80211_ATTR_SCAN_FREQUENCIES]) {
3003 /* user specified, bail out if channel not found */ 3003 /* user specified, bail out if channel not found */
3004 request->n_channels = n_channels;
3005 i = 0;
3006 nla_for_each_nested(attr, info->attrs[NL80211_ATTR_SCAN_FREQUENCIES], tmp) { 3004 nla_for_each_nested(attr, info->attrs[NL80211_ATTR_SCAN_FREQUENCIES], tmp) {
3007 request->channels[i] = ieee80211_get_channel(wiphy, nla_get_u32(attr)); 3005 struct ieee80211_channel *chan;
3008 if (!request->channels[i]) { 3006
3007 chan = ieee80211_get_channel(wiphy, nla_get_u32(attr));
3008
3009 if (!chan) {
3009 err = -EINVAL; 3010 err = -EINVAL;
3010 goto out_free; 3011 goto out_free;
3011 } 3012 }
3013
3014 /* ignore disabled channels */
3015 if (chan->flags & IEEE80211_CHAN_DISABLED)
3016 continue;
3017
3018 request->channels[i] = chan;
3012 i++; 3019 i++;
3013 } 3020 }
3014 } else { 3021 } else {
3015 /* all channels */ 3022 /* all channels */
3016 i = 0;
3017 for (band = 0; band < IEEE80211_NUM_BANDS; band++) { 3023 for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
3018 int j; 3024 int j;
3019 if (!wiphy->bands[band]) 3025 if (!wiphy->bands[band])
3020 continue; 3026 continue;
3021 for (j = 0; j < wiphy->bands[band]->n_channels; j++) { 3027 for (j = 0; j < wiphy->bands[band]->n_channels; j++) {
3022 request->channels[i] = &wiphy->bands[band]->channels[j]; 3028 struct ieee80211_channel *chan;
3029
3030 chan = &wiphy->bands[band]->channels[j];
3031
3032 if (chan->flags & IEEE80211_CHAN_DISABLED)
3033 continue;
3034
3035 request->channels[i] = chan;
3023 i++; 3036 i++;
3024 } 3037 }
3025 } 3038 }
3026 } 3039 }
3027 3040
3041 if (!i) {
3042 err = -EINVAL;
3043 goto out_free;
3044 }
3045
3046 request->n_channels = i;
3047
3028 i = 0; 3048 i = 0;
3029 if (info->attrs[NL80211_ATTR_SCAN_SSIDS]) { 3049 if (info->attrs[NL80211_ATTR_SCAN_SSIDS]) {
3030 nla_for_each_nested(attr, info->attrs[NL80211_ATTR_SCAN_SSIDS], tmp) { 3050 nla_for_each_nested(attr, info->attrs[NL80211_ATTR_SCAN_SSIDS], tmp) {
diff --git a/net/wireless/scan.c b/net/wireless/scan.c
index 2e8c515f3c5c..e2d344ff6745 100644
--- a/net/wireless/scan.c
+++ b/net/wireless/scan.c
@@ -650,9 +650,15 @@ int cfg80211_wext_siwscan(struct net_device *dev,
650 i = 0; 650 i = 0;
651 for (band = 0; band < IEEE80211_NUM_BANDS; band++) { 651 for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
652 int j; 652 int j;
653
653 if (!wiphy->bands[band]) 654 if (!wiphy->bands[band])
654 continue; 655 continue;
656
655 for (j = 0; j < wiphy->bands[band]->n_channels; j++) { 657 for (j = 0; j < wiphy->bands[band]->n_channels; j++) {
658 /* ignore disabled channels */
659 if (wiphy->bands[band]->channels[j].flags &
660 IEEE80211_CHAN_DISABLED)
661 continue;
656 662
657 /* If we have a wireless request structure and the 663 /* If we have a wireless request structure and the
658 * wireless request specifies frequencies, then search 664 * wireless request specifies frequencies, then search