]> git.proxmox.com Git - mirror_ubuntu-eoan-kernel.git/blame - net/wireless/nl80211.c
MAINTAINERS: add entry for include/linux/iw_handler.h
[mirror_ubuntu-eoan-kernel.git] / net / wireless / nl80211.c
CommitLineData
55682965
JB
1/*
2 * This is the new netlink-based wireless configuration interface.
3 *
026331c4 4 * Copyright 2006-2010 Johannes Berg <johannes@sipsolutions.net>
55682965
JB
5 */
6
7#include <linux/if.h>
8#include <linux/module.h>
9#include <linux/err.h>
55682965
JB
10#include <linux/list.h>
11#include <linux/if_ether.h>
12#include <linux/ieee80211.h>
13#include <linux/nl80211.h>
14#include <linux/rtnetlink.h>
15#include <linux/netlink.h>
2a519311 16#include <linux/etherdevice.h>
463d0183 17#include <net/net_namespace.h>
55682965
JB
18#include <net/genetlink.h>
19#include <net/cfg80211.h>
463d0183 20#include <net/sock.h>
55682965
JB
21#include "core.h"
22#include "nl80211.h"
b2e1b302 23#include "reg.h"
55682965
JB
24
25/* the netlink family */
26static struct genl_family nl80211_fam = {
27 .id = GENL_ID_GENERATE, /* don't bother with a hardcoded ID */
28 .name = "nl80211", /* have users key off the name instead */
29 .hdrsize = 0, /* no private header */
30 .version = 1, /* no particular meaning now */
31 .maxattr = NL80211_ATTR_MAX,
463d0183 32 .netnsok = true,
55682965
JB
33};
34
79c97e97 35/* internal helper: get rdev and dev */
463d0183 36static int get_rdev_dev_by_info_ifindex(struct genl_info *info,
79c97e97 37 struct cfg80211_registered_device **rdev,
55682965
JB
38 struct net_device **dev)
39{
463d0183 40 struct nlattr **attrs = info->attrs;
55682965
JB
41 int ifindex;
42
bba95fef 43 if (!attrs[NL80211_ATTR_IFINDEX])
55682965
JB
44 return -EINVAL;
45
bba95fef 46 ifindex = nla_get_u32(attrs[NL80211_ATTR_IFINDEX]);
463d0183 47 *dev = dev_get_by_index(genl_info_net(info), ifindex);
55682965
JB
48 if (!*dev)
49 return -ENODEV;
50
463d0183 51 *rdev = cfg80211_get_dev_from_ifindex(genl_info_net(info), ifindex);
79c97e97 52 if (IS_ERR(*rdev)) {
55682965 53 dev_put(*dev);
79c97e97 54 return PTR_ERR(*rdev);
55682965
JB
55 }
56
57 return 0;
58}
59
60/* policy for the attributes */
b54452b0 61static const struct nla_policy nl80211_policy[NL80211_ATTR_MAX+1] = {
55682965
JB
62 [NL80211_ATTR_WIPHY] = { .type = NLA_U32 },
63 [NL80211_ATTR_WIPHY_NAME] = { .type = NLA_NUL_STRING,
079e24ed 64 .len = 20-1 },
31888487 65 [NL80211_ATTR_WIPHY_TXQ_PARAMS] = { .type = NLA_NESTED },
72bdcf34 66 [NL80211_ATTR_WIPHY_FREQ] = { .type = NLA_U32 },
094d05dc 67 [NL80211_ATTR_WIPHY_CHANNEL_TYPE] = { .type = NLA_U32 },
b9a5f8ca
JM
68 [NL80211_ATTR_WIPHY_RETRY_SHORT] = { .type = NLA_U8 },
69 [NL80211_ATTR_WIPHY_RETRY_LONG] = { .type = NLA_U8 },
70 [NL80211_ATTR_WIPHY_FRAG_THRESHOLD] = { .type = NLA_U32 },
71 [NL80211_ATTR_WIPHY_RTS_THRESHOLD] = { .type = NLA_U32 },
81077e82 72 [NL80211_ATTR_WIPHY_COVERAGE_CLASS] = { .type = NLA_U8 },
55682965
JB
73
74 [NL80211_ATTR_IFTYPE] = { .type = NLA_U32 },
75 [NL80211_ATTR_IFINDEX] = { .type = NLA_U32 },
76 [NL80211_ATTR_IFNAME] = { .type = NLA_NUL_STRING, .len = IFNAMSIZ-1 },
41ade00f
JB
77
78 [NL80211_ATTR_MAC] = { .type = NLA_BINARY, .len = ETH_ALEN },
3e5d7649 79 [NL80211_ATTR_PREV_BSSID] = { .type = NLA_BINARY, .len = ETH_ALEN },
41ade00f 80
b9454e83 81 [NL80211_ATTR_KEY] = { .type = NLA_NESTED, },
41ade00f
JB
82 [NL80211_ATTR_KEY_DATA] = { .type = NLA_BINARY,
83 .len = WLAN_MAX_KEY_LEN },
84 [NL80211_ATTR_KEY_IDX] = { .type = NLA_U8 },
85 [NL80211_ATTR_KEY_CIPHER] = { .type = NLA_U32 },
86 [NL80211_ATTR_KEY_DEFAULT] = { .type = NLA_FLAG },
9f26a952 87 [NL80211_ATTR_KEY_SEQ] = { .type = NLA_BINARY, .len = 8 },
ed1b6cc7
JB
88
89 [NL80211_ATTR_BEACON_INTERVAL] = { .type = NLA_U32 },
90 [NL80211_ATTR_DTIM_PERIOD] = { .type = NLA_U32 },
91 [NL80211_ATTR_BEACON_HEAD] = { .type = NLA_BINARY,
92 .len = IEEE80211_MAX_DATA_LEN },
93 [NL80211_ATTR_BEACON_TAIL] = { .type = NLA_BINARY,
94 .len = IEEE80211_MAX_DATA_LEN },
5727ef1b
JB
95 [NL80211_ATTR_STA_AID] = { .type = NLA_U16 },
96 [NL80211_ATTR_STA_FLAGS] = { .type = NLA_NESTED },
97 [NL80211_ATTR_STA_LISTEN_INTERVAL] = { .type = NLA_U16 },
98 [NL80211_ATTR_STA_SUPPORTED_RATES] = { .type = NLA_BINARY,
99 .len = NL80211_MAX_SUPP_RATES },
2ec600d6 100 [NL80211_ATTR_STA_PLINK_ACTION] = { .type = NLA_U8 },
5727ef1b 101 [NL80211_ATTR_STA_VLAN] = { .type = NLA_U32 },
0a9542ee 102 [NL80211_ATTR_MNTR_FLAGS] = { /* NLA_NESTED can't be empty */ },
2ec600d6
LCC
103 [NL80211_ATTR_MESH_ID] = { .type = NLA_BINARY,
104 .len = IEEE80211_MAX_MESH_ID_LEN },
105 [NL80211_ATTR_MPATH_NEXT_HOP] = { .type = NLA_U32 },
9f1ba906 106
b2e1b302
LR
107 [NL80211_ATTR_REG_ALPHA2] = { .type = NLA_STRING, .len = 2 },
108 [NL80211_ATTR_REG_RULES] = { .type = NLA_NESTED },
109
9f1ba906
JM
110 [NL80211_ATTR_BSS_CTS_PROT] = { .type = NLA_U8 },
111 [NL80211_ATTR_BSS_SHORT_PREAMBLE] = { .type = NLA_U8 },
112 [NL80211_ATTR_BSS_SHORT_SLOT_TIME] = { .type = NLA_U8 },
90c97a04
JM
113 [NL80211_ATTR_BSS_BASIC_RATES] = { .type = NLA_BINARY,
114 .len = NL80211_MAX_SUPP_RATES },
36aedc90 115
93da9cc1 116 [NL80211_ATTR_MESH_PARAMS] = { .type = NLA_NESTED },
117
36aedc90
JM
118 [NL80211_ATTR_HT_CAPABILITY] = { .type = NLA_BINARY,
119 .len = NL80211_HT_CAPABILITY_LEN },
9aed3cc1
JM
120
121 [NL80211_ATTR_MGMT_SUBTYPE] = { .type = NLA_U8 },
122 [NL80211_ATTR_IE] = { .type = NLA_BINARY,
123 .len = IEEE80211_MAX_DATA_LEN },
2a519311
JB
124 [NL80211_ATTR_SCAN_FREQUENCIES] = { .type = NLA_NESTED },
125 [NL80211_ATTR_SCAN_SSIDS] = { .type = NLA_NESTED },
636a5d36
JM
126
127 [NL80211_ATTR_SSID] = { .type = NLA_BINARY,
128 .len = IEEE80211_MAX_SSID_LEN },
129 [NL80211_ATTR_AUTH_TYPE] = { .type = NLA_U32 },
130 [NL80211_ATTR_REASON_CODE] = { .type = NLA_U16 },
04a773ad 131 [NL80211_ATTR_FREQ_FIXED] = { .type = NLA_FLAG },
1965c853 132 [NL80211_ATTR_TIMED_OUT] = { .type = NLA_FLAG },
dc6382ce 133 [NL80211_ATTR_USE_MFP] = { .type = NLA_U32 },
eccb8e8f
JB
134 [NL80211_ATTR_STA_FLAGS2] = {
135 .len = sizeof(struct nl80211_sta_flag_update),
136 },
3f77316c 137 [NL80211_ATTR_CONTROL_PORT] = { .type = NLA_FLAG },
b23aa676
SO
138 [NL80211_ATTR_PRIVACY] = { .type = NLA_FLAG },
139 [NL80211_ATTR_CIPHER_SUITE_GROUP] = { .type = NLA_U32 },
140 [NL80211_ATTR_WPA_VERSIONS] = { .type = NLA_U32 },
463d0183 141 [NL80211_ATTR_PID] = { .type = NLA_U32 },
8b787643 142 [NL80211_ATTR_4ADDR] = { .type = NLA_U8 },
67fbb16b
SO
143 [NL80211_ATTR_PMKID] = { .type = NLA_BINARY,
144 .len = WLAN_PMKID_LEN },
9588bbd5
JM
145 [NL80211_ATTR_DURATION] = { .type = NLA_U32 },
146 [NL80211_ATTR_COOKIE] = { .type = NLA_U64 },
13ae75b1 147 [NL80211_ATTR_TX_RATES] = { .type = NLA_NESTED },
026331c4
JM
148 [NL80211_ATTR_FRAME] = { .type = NLA_BINARY,
149 .len = IEEE80211_MAX_DATA_LEN },
150 [NL80211_ATTR_FRAME_MATCH] = { .type = NLA_BINARY, },
ffb9eb3d 151 [NL80211_ATTR_PS_STATE] = { .type = NLA_U32 },
d6dc1a38 152 [NL80211_ATTR_CQM] = { .type = NLA_NESTED, },
d5cdfacb 153 [NL80211_ATTR_LOCAL_STATE_CHANGE] = { .type = NLA_FLAG },
55682965
JB
154};
155
b9454e83 156/* policy for the attributes */
b54452b0 157static const struct nla_policy nl80211_key_policy[NL80211_KEY_MAX + 1] = {
fffd0934 158 [NL80211_KEY_DATA] = { .type = NLA_BINARY, .len = WLAN_MAX_KEY_LEN },
b9454e83
JB
159 [NL80211_KEY_IDX] = { .type = NLA_U8 },
160 [NL80211_KEY_CIPHER] = { .type = NLA_U32 },
161 [NL80211_KEY_SEQ] = { .type = NLA_BINARY, .len = 8 },
162 [NL80211_KEY_DEFAULT] = { .type = NLA_FLAG },
163 [NL80211_KEY_DEFAULT_MGMT] = { .type = NLA_FLAG },
164};
165
a043897a
HS
166/* ifidx get helper */
167static int nl80211_get_ifidx(struct netlink_callback *cb)
168{
169 int res;
170
171 res = nlmsg_parse(cb->nlh, GENL_HDRLEN + nl80211_fam.hdrsize,
172 nl80211_fam.attrbuf, nl80211_fam.maxattr,
173 nl80211_policy);
174 if (res)
175 return res;
176
177 if (!nl80211_fam.attrbuf[NL80211_ATTR_IFINDEX])
178 return -EINVAL;
179
180 res = nla_get_u32(nl80211_fam.attrbuf[NL80211_ATTR_IFINDEX]);
181 if (!res)
182 return -EINVAL;
183 return res;
184}
185
f4a11bb0
JB
186/* IE validation */
187static bool is_valid_ie_attr(const struct nlattr *attr)
188{
189 const u8 *pos;
190 int len;
191
192 if (!attr)
193 return true;
194
195 pos = nla_data(attr);
196 len = nla_len(attr);
197
198 while (len) {
199 u8 elemlen;
200
201 if (len < 2)
202 return false;
203 len -= 2;
204
205 elemlen = pos[1];
206 if (elemlen > len)
207 return false;
208
209 len -= elemlen;
210 pos += 2 + elemlen;
211 }
212
213 return true;
214}
215
55682965
JB
216/* message building helper */
217static inline void *nl80211hdr_put(struct sk_buff *skb, u32 pid, u32 seq,
218 int flags, u8 cmd)
219{
220 /* since there is no private header just add the generic one */
221 return genlmsg_put(skb, pid, seq, &nl80211_fam, flags, cmd);
222}
223
5dab3b8a
LR
224static int nl80211_msg_put_channel(struct sk_buff *msg,
225 struct ieee80211_channel *chan)
226{
227 NLA_PUT_U32(msg, NL80211_FREQUENCY_ATTR_FREQ,
228 chan->center_freq);
229
230 if (chan->flags & IEEE80211_CHAN_DISABLED)
231 NLA_PUT_FLAG(msg, NL80211_FREQUENCY_ATTR_DISABLED);
232 if (chan->flags & IEEE80211_CHAN_PASSIVE_SCAN)
233 NLA_PUT_FLAG(msg, NL80211_FREQUENCY_ATTR_PASSIVE_SCAN);
234 if (chan->flags & IEEE80211_CHAN_NO_IBSS)
235 NLA_PUT_FLAG(msg, NL80211_FREQUENCY_ATTR_NO_IBSS);
236 if (chan->flags & IEEE80211_CHAN_RADAR)
237 NLA_PUT_FLAG(msg, NL80211_FREQUENCY_ATTR_RADAR);
238
239 NLA_PUT_U32(msg, NL80211_FREQUENCY_ATTR_MAX_TX_POWER,
240 DBM_TO_MBM(chan->max_power));
241
242 return 0;
243
244 nla_put_failure:
245 return -ENOBUFS;
246}
247
55682965
JB
248/* netlink command implementations */
249
b9454e83
JB
250struct key_parse {
251 struct key_params p;
252 int idx;
253 bool def, defmgmt;
254};
255
256static int nl80211_parse_key_new(struct nlattr *key, struct key_parse *k)
257{
258 struct nlattr *tb[NL80211_KEY_MAX + 1];
259 int err = nla_parse_nested(tb, NL80211_KEY_MAX, key,
260 nl80211_key_policy);
261 if (err)
262 return err;
263
264 k->def = !!tb[NL80211_KEY_DEFAULT];
265 k->defmgmt = !!tb[NL80211_KEY_DEFAULT_MGMT];
266
267 if (tb[NL80211_KEY_IDX])
268 k->idx = nla_get_u8(tb[NL80211_KEY_IDX]);
269
270 if (tb[NL80211_KEY_DATA]) {
271 k->p.key = nla_data(tb[NL80211_KEY_DATA]);
272 k->p.key_len = nla_len(tb[NL80211_KEY_DATA]);
273 }
274
275 if (tb[NL80211_KEY_SEQ]) {
276 k->p.seq = nla_data(tb[NL80211_KEY_SEQ]);
277 k->p.seq_len = nla_len(tb[NL80211_KEY_SEQ]);
278 }
279
280 if (tb[NL80211_KEY_CIPHER])
281 k->p.cipher = nla_get_u32(tb[NL80211_KEY_CIPHER]);
282
283 return 0;
284}
285
286static int nl80211_parse_key_old(struct genl_info *info, struct key_parse *k)
287{
288 if (info->attrs[NL80211_ATTR_KEY_DATA]) {
289 k->p.key = nla_data(info->attrs[NL80211_ATTR_KEY_DATA]);
290 k->p.key_len = nla_len(info->attrs[NL80211_ATTR_KEY_DATA]);
291 }
292
293 if (info->attrs[NL80211_ATTR_KEY_SEQ]) {
294 k->p.seq = nla_data(info->attrs[NL80211_ATTR_KEY_SEQ]);
295 k->p.seq_len = nla_len(info->attrs[NL80211_ATTR_KEY_SEQ]);
296 }
297
298 if (info->attrs[NL80211_ATTR_KEY_IDX])
299 k->idx = nla_get_u8(info->attrs[NL80211_ATTR_KEY_IDX]);
300
301 if (info->attrs[NL80211_ATTR_KEY_CIPHER])
302 k->p.cipher = nla_get_u32(info->attrs[NL80211_ATTR_KEY_CIPHER]);
303
304 k->def = !!info->attrs[NL80211_ATTR_KEY_DEFAULT];
305 k->defmgmt = !!info->attrs[NL80211_ATTR_KEY_DEFAULT_MGMT];
306
307 return 0;
308}
309
310static int nl80211_parse_key(struct genl_info *info, struct key_parse *k)
311{
312 int err;
313
314 memset(k, 0, sizeof(*k));
315 k->idx = -1;
316
317 if (info->attrs[NL80211_ATTR_KEY])
318 err = nl80211_parse_key_new(info->attrs[NL80211_ATTR_KEY], k);
319 else
320 err = nl80211_parse_key_old(info, k);
321
322 if (err)
323 return err;
324
325 if (k->def && k->defmgmt)
326 return -EINVAL;
327
328 if (k->idx != -1) {
329 if (k->defmgmt) {
330 if (k->idx < 4 || k->idx > 5)
331 return -EINVAL;
332 } else if (k->def) {
333 if (k->idx < 0 || k->idx > 3)
334 return -EINVAL;
335 } else {
336 if (k->idx < 0 || k->idx > 5)
337 return -EINVAL;
338 }
339 }
340
341 return 0;
342}
343
fffd0934
JB
344static struct cfg80211_cached_keys *
345nl80211_parse_connkeys(struct cfg80211_registered_device *rdev,
346 struct nlattr *keys)
347{
348 struct key_parse parse;
349 struct nlattr *key;
350 struct cfg80211_cached_keys *result;
351 int rem, err, def = 0;
352
353 result = kzalloc(sizeof(*result), GFP_KERNEL);
354 if (!result)
355 return ERR_PTR(-ENOMEM);
356
357 result->def = -1;
358 result->defmgmt = -1;
359
360 nla_for_each_nested(key, keys, rem) {
361 memset(&parse, 0, sizeof(parse));
362 parse.idx = -1;
363
364 err = nl80211_parse_key_new(key, &parse);
365 if (err)
366 goto error;
367 err = -EINVAL;
368 if (!parse.p.key)
369 goto error;
370 if (parse.idx < 0 || parse.idx > 4)
371 goto error;
372 if (parse.def) {
373 if (def)
374 goto error;
375 def = 1;
376 result->def = parse.idx;
377 } else if (parse.defmgmt)
378 goto error;
379 err = cfg80211_validate_key_settings(rdev, &parse.p,
380 parse.idx, NULL);
381 if (err)
382 goto error;
383 result->params[parse.idx].cipher = parse.p.cipher;
384 result->params[parse.idx].key_len = parse.p.key_len;
385 result->params[parse.idx].key = result->data[parse.idx];
386 memcpy(result->data[parse.idx], parse.p.key, parse.p.key_len);
387 }
388
389 return result;
390 error:
391 kfree(result);
392 return ERR_PTR(err);
393}
394
395static int nl80211_key_allowed(struct wireless_dev *wdev)
396{
397 ASSERT_WDEV_LOCK(wdev);
398
399 if (!netif_running(wdev->netdev))
400 return -ENETDOWN;
401
402 switch (wdev->iftype) {
403 case NL80211_IFTYPE_AP:
404 case NL80211_IFTYPE_AP_VLAN:
405 break;
406 case NL80211_IFTYPE_ADHOC:
407 if (!wdev->current_bss)
408 return -ENOLINK;
409 break;
410 case NL80211_IFTYPE_STATION:
411 if (wdev->sme_state != CFG80211_SME_CONNECTED)
412 return -ENOLINK;
413 break;
414 default:
415 return -EINVAL;
416 }
417
418 return 0;
419}
420
55682965
JB
421static int nl80211_send_wiphy(struct sk_buff *msg, u32 pid, u32 seq, int flags,
422 struct cfg80211_registered_device *dev)
423{
424 void *hdr;
ee688b00
JB
425 struct nlattr *nl_bands, *nl_band;
426 struct nlattr *nl_freqs, *nl_freq;
427 struct nlattr *nl_rates, *nl_rate;
f59ac048 428 struct nlattr *nl_modes;
8fdc621d 429 struct nlattr *nl_cmds;
ee688b00
JB
430 enum ieee80211_band band;
431 struct ieee80211_channel *chan;
432 struct ieee80211_rate *rate;
433 int i;
f59ac048 434 u16 ifmodes = dev->wiphy.interface_modes;
55682965
JB
435
436 hdr = nl80211hdr_put(msg, pid, seq, flags, NL80211_CMD_NEW_WIPHY);
437 if (!hdr)
438 return -1;
439
b5850a7a 440 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, dev->wiphy_idx);
55682965 441 NLA_PUT_STRING(msg, NL80211_ATTR_WIPHY_NAME, wiphy_name(&dev->wiphy));
b9a5f8ca 442
f5ea9120
JB
443 NLA_PUT_U32(msg, NL80211_ATTR_GENERATION,
444 cfg80211_rdev_list_generation);
445
b9a5f8ca
JM
446 NLA_PUT_U8(msg, NL80211_ATTR_WIPHY_RETRY_SHORT,
447 dev->wiphy.retry_short);
448 NLA_PUT_U8(msg, NL80211_ATTR_WIPHY_RETRY_LONG,
449 dev->wiphy.retry_long);
450 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY_FRAG_THRESHOLD,
451 dev->wiphy.frag_threshold);
452 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY_RTS_THRESHOLD,
453 dev->wiphy.rts_threshold);
81077e82
LT
454 NLA_PUT_U8(msg, NL80211_ATTR_WIPHY_COVERAGE_CLASS,
455 dev->wiphy.coverage_class);
b9a5f8ca 456
2a519311
JB
457 NLA_PUT_U8(msg, NL80211_ATTR_MAX_NUM_SCAN_SSIDS,
458 dev->wiphy.max_scan_ssids);
18a83659
JB
459 NLA_PUT_U16(msg, NL80211_ATTR_MAX_SCAN_IE_LEN,
460 dev->wiphy.max_scan_ie_len);
ee688b00 461
25e47c18
JB
462 NLA_PUT(msg, NL80211_ATTR_CIPHER_SUITES,
463 sizeof(u32) * dev->wiphy.n_cipher_suites,
464 dev->wiphy.cipher_suites);
465
67fbb16b
SO
466 NLA_PUT_U8(msg, NL80211_ATTR_MAX_NUM_PMKIDS,
467 dev->wiphy.max_num_pmkids);
468
f59ac048
LR
469 nl_modes = nla_nest_start(msg, NL80211_ATTR_SUPPORTED_IFTYPES);
470 if (!nl_modes)
471 goto nla_put_failure;
472
473 i = 0;
474 while (ifmodes) {
475 if (ifmodes & 1)
476 NLA_PUT_FLAG(msg, i);
477 ifmodes >>= 1;
478 i++;
479 }
480
481 nla_nest_end(msg, nl_modes);
482
ee688b00
JB
483 nl_bands = nla_nest_start(msg, NL80211_ATTR_WIPHY_BANDS);
484 if (!nl_bands)
485 goto nla_put_failure;
486
487 for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
488 if (!dev->wiphy.bands[band])
489 continue;
490
491 nl_band = nla_nest_start(msg, band);
492 if (!nl_band)
493 goto nla_put_failure;
494
d51626df
JB
495 /* add HT info */
496 if (dev->wiphy.bands[band]->ht_cap.ht_supported) {
497 NLA_PUT(msg, NL80211_BAND_ATTR_HT_MCS_SET,
498 sizeof(dev->wiphy.bands[band]->ht_cap.mcs),
499 &dev->wiphy.bands[band]->ht_cap.mcs);
500 NLA_PUT_U16(msg, NL80211_BAND_ATTR_HT_CAPA,
501 dev->wiphy.bands[band]->ht_cap.cap);
502 NLA_PUT_U8(msg, NL80211_BAND_ATTR_HT_AMPDU_FACTOR,
503 dev->wiphy.bands[band]->ht_cap.ampdu_factor);
504 NLA_PUT_U8(msg, NL80211_BAND_ATTR_HT_AMPDU_DENSITY,
505 dev->wiphy.bands[band]->ht_cap.ampdu_density);
506 }
507
ee688b00
JB
508 /* add frequencies */
509 nl_freqs = nla_nest_start(msg, NL80211_BAND_ATTR_FREQS);
510 if (!nl_freqs)
511 goto nla_put_failure;
512
513 for (i = 0; i < dev->wiphy.bands[band]->n_channels; i++) {
514 nl_freq = nla_nest_start(msg, i);
515 if (!nl_freq)
516 goto nla_put_failure;
517
518 chan = &dev->wiphy.bands[band]->channels[i];
5dab3b8a
LR
519
520 if (nl80211_msg_put_channel(msg, chan))
521 goto nla_put_failure;
e2f367f2 522
ee688b00
JB
523 nla_nest_end(msg, nl_freq);
524 }
525
526 nla_nest_end(msg, nl_freqs);
527
528 /* add bitrates */
529 nl_rates = nla_nest_start(msg, NL80211_BAND_ATTR_RATES);
530 if (!nl_rates)
531 goto nla_put_failure;
532
533 for (i = 0; i < dev->wiphy.bands[band]->n_bitrates; i++) {
534 nl_rate = nla_nest_start(msg, i);
535 if (!nl_rate)
536 goto nla_put_failure;
537
538 rate = &dev->wiphy.bands[band]->bitrates[i];
539 NLA_PUT_U32(msg, NL80211_BITRATE_ATTR_RATE,
540 rate->bitrate);
541 if (rate->flags & IEEE80211_RATE_SHORT_PREAMBLE)
542 NLA_PUT_FLAG(msg,
543 NL80211_BITRATE_ATTR_2GHZ_SHORTPREAMBLE);
544
545 nla_nest_end(msg, nl_rate);
546 }
547
548 nla_nest_end(msg, nl_rates);
549
550 nla_nest_end(msg, nl_band);
551 }
552 nla_nest_end(msg, nl_bands);
553
8fdc621d
JB
554 nl_cmds = nla_nest_start(msg, NL80211_ATTR_SUPPORTED_COMMANDS);
555 if (!nl_cmds)
556 goto nla_put_failure;
557
558 i = 0;
559#define CMD(op, n) \
560 do { \
561 if (dev->ops->op) { \
562 i++; \
563 NLA_PUT_U32(msg, i, NL80211_CMD_ ## n); \
564 } \
565 } while (0)
566
567 CMD(add_virtual_intf, NEW_INTERFACE);
568 CMD(change_virtual_intf, SET_INTERFACE);
569 CMD(add_key, NEW_KEY);
570 CMD(add_beacon, NEW_BEACON);
571 CMD(add_station, NEW_STATION);
572 CMD(add_mpath, NEW_MPATH);
573 CMD(set_mesh_params, SET_MESH_PARAMS);
574 CMD(change_bss, SET_BSS);
636a5d36
JM
575 CMD(auth, AUTHENTICATE);
576 CMD(assoc, ASSOCIATE);
577 CMD(deauth, DEAUTHENTICATE);
578 CMD(disassoc, DISASSOCIATE);
04a773ad 579 CMD(join_ibss, JOIN_IBSS);
67fbb16b
SO
580 CMD(set_pmksa, SET_PMKSA);
581 CMD(del_pmksa, DEL_PMKSA);
582 CMD(flush_pmksa, FLUSH_PMKSA);
9588bbd5 583 CMD(remain_on_channel, REMAIN_ON_CHANNEL);
13ae75b1 584 CMD(set_bitrate_mask, SET_TX_BITRATE_MASK);
026331c4 585 CMD(action, ACTION);
5be83de5 586 if (dev->wiphy.flags & WIPHY_FLAG_NETNS_OK) {
463d0183
JB
587 i++;
588 NLA_PUT_U32(msg, i, NL80211_CMD_SET_WIPHY_NETNS);
589 }
8fdc621d
JB
590
591#undef CMD
b23aa676 592
6829c878 593 if (dev->ops->connect || dev->ops->auth) {
b23aa676
SO
594 i++;
595 NLA_PUT_U32(msg, i, NL80211_CMD_CONNECT);
596 }
597
6829c878 598 if (dev->ops->disconnect || dev->ops->deauth) {
b23aa676
SO
599 i++;
600 NLA_PUT_U32(msg, i, NL80211_CMD_DISCONNECT);
601 }
602
8fdc621d
JB
603 nla_nest_end(msg, nl_cmds);
604
55682965
JB
605 return genlmsg_end(msg, hdr);
606
607 nla_put_failure:
bc3ed28c
TG
608 genlmsg_cancel(msg, hdr);
609 return -EMSGSIZE;
55682965
JB
610}
611
612static int nl80211_dump_wiphy(struct sk_buff *skb, struct netlink_callback *cb)
613{
614 int idx = 0;
615 int start = cb->args[0];
616 struct cfg80211_registered_device *dev;
617
a1794390 618 mutex_lock(&cfg80211_mutex);
79c97e97 619 list_for_each_entry(dev, &cfg80211_rdev_list, list) {
463d0183
JB
620 if (!net_eq(wiphy_net(&dev->wiphy), sock_net(skb->sk)))
621 continue;
b4637271 622 if (++idx <= start)
55682965
JB
623 continue;
624 if (nl80211_send_wiphy(skb, NETLINK_CB(cb->skb).pid,
625 cb->nlh->nlmsg_seq, NLM_F_MULTI,
b4637271
JV
626 dev) < 0) {
627 idx--;
55682965 628 break;
b4637271 629 }
55682965 630 }
a1794390 631 mutex_unlock(&cfg80211_mutex);
55682965
JB
632
633 cb->args[0] = idx;
634
635 return skb->len;
636}
637
638static int nl80211_get_wiphy(struct sk_buff *skb, struct genl_info *info)
639{
640 struct sk_buff *msg;
641 struct cfg80211_registered_device *dev;
642
643 dev = cfg80211_get_dev_from_info(info);
644 if (IS_ERR(dev))
645 return PTR_ERR(dev);
646
fd2120ca 647 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
55682965
JB
648 if (!msg)
649 goto out_err;
650
651 if (nl80211_send_wiphy(msg, info->snd_pid, info->snd_seq, 0, dev) < 0)
652 goto out_free;
653
4d0c8aea 654 cfg80211_unlock_rdev(dev);
55682965 655
134e6375 656 return genlmsg_reply(msg, info);
55682965
JB
657
658 out_free:
659 nlmsg_free(msg);
660 out_err:
4d0c8aea 661 cfg80211_unlock_rdev(dev);
55682965
JB
662 return -ENOBUFS;
663}
664
31888487
JM
665static const struct nla_policy txq_params_policy[NL80211_TXQ_ATTR_MAX + 1] = {
666 [NL80211_TXQ_ATTR_QUEUE] = { .type = NLA_U8 },
667 [NL80211_TXQ_ATTR_TXOP] = { .type = NLA_U16 },
668 [NL80211_TXQ_ATTR_CWMIN] = { .type = NLA_U16 },
669 [NL80211_TXQ_ATTR_CWMAX] = { .type = NLA_U16 },
670 [NL80211_TXQ_ATTR_AIFS] = { .type = NLA_U8 },
671};
672
673static int parse_txq_params(struct nlattr *tb[],
674 struct ieee80211_txq_params *txq_params)
675{
676 if (!tb[NL80211_TXQ_ATTR_QUEUE] || !tb[NL80211_TXQ_ATTR_TXOP] ||
677 !tb[NL80211_TXQ_ATTR_CWMIN] || !tb[NL80211_TXQ_ATTR_CWMAX] ||
678 !tb[NL80211_TXQ_ATTR_AIFS])
679 return -EINVAL;
680
681 txq_params->queue = nla_get_u8(tb[NL80211_TXQ_ATTR_QUEUE]);
682 txq_params->txop = nla_get_u16(tb[NL80211_TXQ_ATTR_TXOP]);
683 txq_params->cwmin = nla_get_u16(tb[NL80211_TXQ_ATTR_CWMIN]);
684 txq_params->cwmax = nla_get_u16(tb[NL80211_TXQ_ATTR_CWMAX]);
685 txq_params->aifs = nla_get_u8(tb[NL80211_TXQ_ATTR_AIFS]);
686
687 return 0;
688}
689
55682965
JB
690static int nl80211_set_wiphy(struct sk_buff *skb, struct genl_info *info)
691{
692 struct cfg80211_registered_device *rdev;
31888487
JM
693 int result = 0, rem_txq_params = 0;
694 struct nlattr *nl_txq_params;
b9a5f8ca
JM
695 u32 changed;
696 u8 retry_short = 0, retry_long = 0;
697 u32 frag_threshold = 0, rts_threshold = 0;
81077e82 698 u8 coverage_class = 0;
55682965 699
4bbf4d56 700 rtnl_lock();
55682965 701
4bbf4d56
JB
702 mutex_lock(&cfg80211_mutex);
703
79c97e97 704 rdev = __cfg80211_rdev_from_info(info);
4bbf4d56 705 if (IS_ERR(rdev)) {
1f5fc70a 706 mutex_unlock(&cfg80211_mutex);
4bbf4d56
JB
707 result = PTR_ERR(rdev);
708 goto unlock;
709 }
710
711 mutex_lock(&rdev->mtx);
712
713 if (info->attrs[NL80211_ATTR_WIPHY_NAME])
31888487
JM
714 result = cfg80211_dev_rename(
715 rdev, nla_data(info->attrs[NL80211_ATTR_WIPHY_NAME]));
4bbf4d56
JB
716
717 mutex_unlock(&cfg80211_mutex);
718
719 if (result)
720 goto bad_res;
31888487
JM
721
722 if (info->attrs[NL80211_ATTR_WIPHY_TXQ_PARAMS]) {
723 struct ieee80211_txq_params txq_params;
724 struct nlattr *tb[NL80211_TXQ_ATTR_MAX + 1];
725
726 if (!rdev->ops->set_txq_params) {
727 result = -EOPNOTSUPP;
728 goto bad_res;
729 }
730
731 nla_for_each_nested(nl_txq_params,
732 info->attrs[NL80211_ATTR_WIPHY_TXQ_PARAMS],
733 rem_txq_params) {
734 nla_parse(tb, NL80211_TXQ_ATTR_MAX,
735 nla_data(nl_txq_params),
736 nla_len(nl_txq_params),
737 txq_params_policy);
738 result = parse_txq_params(tb, &txq_params);
739 if (result)
740 goto bad_res;
741
742 result = rdev->ops->set_txq_params(&rdev->wiphy,
743 &txq_params);
744 if (result)
745 goto bad_res;
746 }
747 }
55682965 748
72bdcf34 749 if (info->attrs[NL80211_ATTR_WIPHY_FREQ]) {
094d05dc 750 enum nl80211_channel_type channel_type = NL80211_CHAN_NO_HT;
294196ab 751 u32 freq;
72bdcf34 752
306d6112
JB
753 result = -EINVAL;
754
094d05dc
S
755 if (info->attrs[NL80211_ATTR_WIPHY_CHANNEL_TYPE]) {
756 channel_type = nla_get_u32(info->attrs[
757 NL80211_ATTR_WIPHY_CHANNEL_TYPE]);
758 if (channel_type != NL80211_CHAN_NO_HT &&
759 channel_type != NL80211_CHAN_HT20 &&
760 channel_type != NL80211_CHAN_HT40PLUS &&
761 channel_type != NL80211_CHAN_HT40MINUS)
72bdcf34 762 goto bad_res;
72bdcf34
JM
763 }
764
765 freq = nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]);
306d6112 766
59bbb6f7 767 mutex_lock(&rdev->devlist_mtx);
4b181144 768 result = rdev_set_freq(rdev, NULL, freq, channel_type);
59bbb6f7 769 mutex_unlock(&rdev->devlist_mtx);
72bdcf34
JM
770 if (result)
771 goto bad_res;
772 }
773
b9a5f8ca
JM
774 changed = 0;
775
776 if (info->attrs[NL80211_ATTR_WIPHY_RETRY_SHORT]) {
777 retry_short = nla_get_u8(
778 info->attrs[NL80211_ATTR_WIPHY_RETRY_SHORT]);
779 if (retry_short == 0) {
780 result = -EINVAL;
781 goto bad_res;
782 }
783 changed |= WIPHY_PARAM_RETRY_SHORT;
784 }
785
786 if (info->attrs[NL80211_ATTR_WIPHY_RETRY_LONG]) {
787 retry_long = nla_get_u8(
788 info->attrs[NL80211_ATTR_WIPHY_RETRY_LONG]);
789 if (retry_long == 0) {
790 result = -EINVAL;
791 goto bad_res;
792 }
793 changed |= WIPHY_PARAM_RETRY_LONG;
794 }
795
796 if (info->attrs[NL80211_ATTR_WIPHY_FRAG_THRESHOLD]) {
797 frag_threshold = nla_get_u32(
798 info->attrs[NL80211_ATTR_WIPHY_FRAG_THRESHOLD]);
799 if (frag_threshold < 256) {
800 result = -EINVAL;
801 goto bad_res;
802 }
803 if (frag_threshold != (u32) -1) {
804 /*
805 * Fragments (apart from the last one) are required to
806 * have even length. Make the fragmentation code
807 * simpler by stripping LSB should someone try to use
808 * odd threshold value.
809 */
810 frag_threshold &= ~0x1;
811 }
812 changed |= WIPHY_PARAM_FRAG_THRESHOLD;
813 }
814
815 if (info->attrs[NL80211_ATTR_WIPHY_RTS_THRESHOLD]) {
816 rts_threshold = nla_get_u32(
817 info->attrs[NL80211_ATTR_WIPHY_RTS_THRESHOLD]);
818 changed |= WIPHY_PARAM_RTS_THRESHOLD;
819 }
820
81077e82
LT
821 if (info->attrs[NL80211_ATTR_WIPHY_COVERAGE_CLASS]) {
822 coverage_class = nla_get_u8(
823 info->attrs[NL80211_ATTR_WIPHY_COVERAGE_CLASS]);
824 changed |= WIPHY_PARAM_COVERAGE_CLASS;
825 }
826
b9a5f8ca
JM
827 if (changed) {
828 u8 old_retry_short, old_retry_long;
829 u32 old_frag_threshold, old_rts_threshold;
81077e82 830 u8 old_coverage_class;
b9a5f8ca
JM
831
832 if (!rdev->ops->set_wiphy_params) {
833 result = -EOPNOTSUPP;
834 goto bad_res;
835 }
836
837 old_retry_short = rdev->wiphy.retry_short;
838 old_retry_long = rdev->wiphy.retry_long;
839 old_frag_threshold = rdev->wiphy.frag_threshold;
840 old_rts_threshold = rdev->wiphy.rts_threshold;
81077e82 841 old_coverage_class = rdev->wiphy.coverage_class;
b9a5f8ca
JM
842
843 if (changed & WIPHY_PARAM_RETRY_SHORT)
844 rdev->wiphy.retry_short = retry_short;
845 if (changed & WIPHY_PARAM_RETRY_LONG)
846 rdev->wiphy.retry_long = retry_long;
847 if (changed & WIPHY_PARAM_FRAG_THRESHOLD)
848 rdev->wiphy.frag_threshold = frag_threshold;
849 if (changed & WIPHY_PARAM_RTS_THRESHOLD)
850 rdev->wiphy.rts_threshold = rts_threshold;
81077e82
LT
851 if (changed & WIPHY_PARAM_COVERAGE_CLASS)
852 rdev->wiphy.coverage_class = coverage_class;
b9a5f8ca
JM
853
854 result = rdev->ops->set_wiphy_params(&rdev->wiphy, changed);
855 if (result) {
856 rdev->wiphy.retry_short = old_retry_short;
857 rdev->wiphy.retry_long = old_retry_long;
858 rdev->wiphy.frag_threshold = old_frag_threshold;
859 rdev->wiphy.rts_threshold = old_rts_threshold;
81077e82 860 rdev->wiphy.coverage_class = old_coverage_class;
b9a5f8ca
JM
861 }
862 }
72bdcf34 863
306d6112 864 bad_res:
4bbf4d56
JB
865 mutex_unlock(&rdev->mtx);
866 unlock:
867 rtnl_unlock();
55682965
JB
868 return result;
869}
870
871
872static int nl80211_send_iface(struct sk_buff *msg, u32 pid, u32 seq, int flags,
d726405a 873 struct cfg80211_registered_device *rdev,
55682965
JB
874 struct net_device *dev)
875{
876 void *hdr;
877
878 hdr = nl80211hdr_put(msg, pid, seq, flags, NL80211_CMD_NEW_INTERFACE);
879 if (!hdr)
880 return -1;
881
882 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, dev->ifindex);
d726405a 883 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
55682965 884 NLA_PUT_STRING(msg, NL80211_ATTR_IFNAME, dev->name);
60719ffd 885 NLA_PUT_U32(msg, NL80211_ATTR_IFTYPE, dev->ieee80211_ptr->iftype);
f5ea9120
JB
886
887 NLA_PUT_U32(msg, NL80211_ATTR_GENERATION,
888 rdev->devlist_generation ^
889 (cfg80211_rdev_list_generation << 2));
890
55682965
JB
891 return genlmsg_end(msg, hdr);
892
893 nla_put_failure:
bc3ed28c
TG
894 genlmsg_cancel(msg, hdr);
895 return -EMSGSIZE;
55682965
JB
896}
897
898static int nl80211_dump_interface(struct sk_buff *skb, struct netlink_callback *cb)
899{
900 int wp_idx = 0;
901 int if_idx = 0;
902 int wp_start = cb->args[0];
903 int if_start = cb->args[1];
f5ea9120 904 struct cfg80211_registered_device *rdev;
55682965
JB
905 struct wireless_dev *wdev;
906
a1794390 907 mutex_lock(&cfg80211_mutex);
f5ea9120
JB
908 list_for_each_entry(rdev, &cfg80211_rdev_list, list) {
909 if (!net_eq(wiphy_net(&rdev->wiphy), sock_net(skb->sk)))
463d0183 910 continue;
bba95fef
JB
911 if (wp_idx < wp_start) {
912 wp_idx++;
55682965 913 continue;
bba95fef 914 }
55682965
JB
915 if_idx = 0;
916
f5ea9120
JB
917 mutex_lock(&rdev->devlist_mtx);
918 list_for_each_entry(wdev, &rdev->netdev_list, list) {
bba95fef
JB
919 if (if_idx < if_start) {
920 if_idx++;
55682965 921 continue;
bba95fef 922 }
55682965
JB
923 if (nl80211_send_iface(skb, NETLINK_CB(cb->skb).pid,
924 cb->nlh->nlmsg_seq, NLM_F_MULTI,
f5ea9120
JB
925 rdev, wdev->netdev) < 0) {
926 mutex_unlock(&rdev->devlist_mtx);
bba95fef
JB
927 goto out;
928 }
929 if_idx++;
55682965 930 }
f5ea9120 931 mutex_unlock(&rdev->devlist_mtx);
bba95fef
JB
932
933 wp_idx++;
55682965 934 }
bba95fef 935 out:
a1794390 936 mutex_unlock(&cfg80211_mutex);
55682965
JB
937
938 cb->args[0] = wp_idx;
939 cb->args[1] = if_idx;
940
941 return skb->len;
942}
943
944static int nl80211_get_interface(struct sk_buff *skb, struct genl_info *info)
945{
946 struct sk_buff *msg;
947 struct cfg80211_registered_device *dev;
948 struct net_device *netdev;
949 int err;
950
463d0183 951 err = get_rdev_dev_by_info_ifindex(info, &dev, &netdev);
55682965
JB
952 if (err)
953 return err;
954
fd2120ca 955 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
55682965
JB
956 if (!msg)
957 goto out_err;
958
d726405a
JB
959 if (nl80211_send_iface(msg, info->snd_pid, info->snd_seq, 0,
960 dev, netdev) < 0)
55682965
JB
961 goto out_free;
962
963 dev_put(netdev);
4d0c8aea 964 cfg80211_unlock_rdev(dev);
55682965 965
134e6375 966 return genlmsg_reply(msg, info);
55682965
JB
967
968 out_free:
969 nlmsg_free(msg);
970 out_err:
971 dev_put(netdev);
4d0c8aea 972 cfg80211_unlock_rdev(dev);
55682965
JB
973 return -ENOBUFS;
974}
975
66f7ac50
MW
976static const struct nla_policy mntr_flags_policy[NL80211_MNTR_FLAG_MAX + 1] = {
977 [NL80211_MNTR_FLAG_FCSFAIL] = { .type = NLA_FLAG },
978 [NL80211_MNTR_FLAG_PLCPFAIL] = { .type = NLA_FLAG },
979 [NL80211_MNTR_FLAG_CONTROL] = { .type = NLA_FLAG },
980 [NL80211_MNTR_FLAG_OTHER_BSS] = { .type = NLA_FLAG },
981 [NL80211_MNTR_FLAG_COOK_FRAMES] = { .type = NLA_FLAG },
982};
983
984static int parse_monitor_flags(struct nlattr *nla, u32 *mntrflags)
985{
986 struct nlattr *flags[NL80211_MNTR_FLAG_MAX + 1];
987 int flag;
988
989 *mntrflags = 0;
990
991 if (!nla)
992 return -EINVAL;
993
994 if (nla_parse_nested(flags, NL80211_MNTR_FLAG_MAX,
995 nla, mntr_flags_policy))
996 return -EINVAL;
997
998 for (flag = 1; flag <= NL80211_MNTR_FLAG_MAX; flag++)
999 if (flags[flag])
1000 *mntrflags |= (1<<flag);
1001
1002 return 0;
1003}
1004
9bc383de 1005static int nl80211_valid_4addr(struct cfg80211_registered_device *rdev,
ad4bb6f8
JB
1006 struct net_device *netdev, u8 use_4addr,
1007 enum nl80211_iftype iftype)
9bc383de 1008{
ad4bb6f8
JB
1009 if (!use_4addr) {
1010 if (netdev && netdev->br_port)
1011 return -EBUSY;
9bc383de 1012 return 0;
ad4bb6f8 1013 }
9bc383de
JB
1014
1015 switch (iftype) {
1016 case NL80211_IFTYPE_AP_VLAN:
1017 if (rdev->wiphy.flags & WIPHY_FLAG_4ADDR_AP)
1018 return 0;
1019 break;
1020 case NL80211_IFTYPE_STATION:
1021 if (rdev->wiphy.flags & WIPHY_FLAG_4ADDR_STATION)
1022 return 0;
1023 break;
1024 default:
1025 break;
1026 }
1027
1028 return -EOPNOTSUPP;
1029}
1030
55682965
JB
1031static int nl80211_set_interface(struct sk_buff *skb, struct genl_info *info)
1032{
79c97e97 1033 struct cfg80211_registered_device *rdev;
2ec600d6 1034 struct vif_params params;
e36d56b6 1035 int err;
04a773ad 1036 enum nl80211_iftype otype, ntype;
55682965 1037 struct net_device *dev;
92ffe055 1038 u32 _flags, *flags = NULL;
ac7f9cfa 1039 bool change = false;
55682965 1040
2ec600d6
LCC
1041 memset(&params, 0, sizeof(params));
1042
3b85875a
JB
1043 rtnl_lock();
1044
463d0183 1045 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
55682965 1046 if (err)
3b85875a
JB
1047 goto unlock_rtnl;
1048
04a773ad 1049 otype = ntype = dev->ieee80211_ptr->iftype;
55682965 1050
723b038d 1051 if (info->attrs[NL80211_ATTR_IFTYPE]) {
ac7f9cfa 1052 ntype = nla_get_u32(info->attrs[NL80211_ATTR_IFTYPE]);
04a773ad 1053 if (otype != ntype)
ac7f9cfa 1054 change = true;
04a773ad 1055 if (ntype > NL80211_IFTYPE_MAX) {
ac7f9cfa 1056 err = -EINVAL;
723b038d 1057 goto unlock;
ac7f9cfa 1058 }
723b038d
JB
1059 }
1060
92ffe055 1061 if (info->attrs[NL80211_ATTR_MESH_ID]) {
04a773ad 1062 if (ntype != NL80211_IFTYPE_MESH_POINT) {
92ffe055
JB
1063 err = -EINVAL;
1064 goto unlock;
1065 }
2ec600d6
LCC
1066 params.mesh_id = nla_data(info->attrs[NL80211_ATTR_MESH_ID]);
1067 params.mesh_id_len = nla_len(info->attrs[NL80211_ATTR_MESH_ID]);
ac7f9cfa 1068 change = true;
2ec600d6
LCC
1069 }
1070
8b787643
FF
1071 if (info->attrs[NL80211_ATTR_4ADDR]) {
1072 params.use_4addr = !!nla_get_u8(info->attrs[NL80211_ATTR_4ADDR]);
1073 change = true;
ad4bb6f8 1074 err = nl80211_valid_4addr(rdev, dev, params.use_4addr, ntype);
9bc383de
JB
1075 if (err)
1076 goto unlock;
8b787643
FF
1077 } else {
1078 params.use_4addr = -1;
1079 }
1080
92ffe055 1081 if (info->attrs[NL80211_ATTR_MNTR_FLAGS]) {
04a773ad 1082 if (ntype != NL80211_IFTYPE_MONITOR) {
92ffe055
JB
1083 err = -EINVAL;
1084 goto unlock;
1085 }
1086 err = parse_monitor_flags(info->attrs[NL80211_ATTR_MNTR_FLAGS],
1087 &_flags);
ac7f9cfa
JB
1088 if (err)
1089 goto unlock;
1090
1091 flags = &_flags;
1092 change = true;
92ffe055 1093 }
3b85875a 1094
ac7f9cfa 1095 if (change)
3d54d255 1096 err = cfg80211_change_iface(rdev, dev, ntype, flags, &params);
ac7f9cfa
JB
1097 else
1098 err = 0;
60719ffd 1099
9bc383de
JB
1100 if (!err && params.use_4addr != -1)
1101 dev->ieee80211_ptr->use_4addr = params.use_4addr;
1102
55682965 1103 unlock:
e36d56b6 1104 dev_put(dev);
79c97e97 1105 cfg80211_unlock_rdev(rdev);
3b85875a
JB
1106 unlock_rtnl:
1107 rtnl_unlock();
55682965
JB
1108 return err;
1109}
1110
1111static int nl80211_new_interface(struct sk_buff *skb, struct genl_info *info)
1112{
79c97e97 1113 struct cfg80211_registered_device *rdev;
2ec600d6 1114 struct vif_params params;
55682965
JB
1115 int err;
1116 enum nl80211_iftype type = NL80211_IFTYPE_UNSPECIFIED;
66f7ac50 1117 u32 flags;
55682965 1118
2ec600d6
LCC
1119 memset(&params, 0, sizeof(params));
1120
55682965
JB
1121 if (!info->attrs[NL80211_ATTR_IFNAME])
1122 return -EINVAL;
1123
1124 if (info->attrs[NL80211_ATTR_IFTYPE]) {
1125 type = nla_get_u32(info->attrs[NL80211_ATTR_IFTYPE]);
1126 if (type > NL80211_IFTYPE_MAX)
1127 return -EINVAL;
1128 }
1129
3b85875a
JB
1130 rtnl_lock();
1131
79c97e97
JB
1132 rdev = cfg80211_get_dev_from_info(info);
1133 if (IS_ERR(rdev)) {
1134 err = PTR_ERR(rdev);
3b85875a
JB
1135 goto unlock_rtnl;
1136 }
55682965 1137
79c97e97
JB
1138 if (!rdev->ops->add_virtual_intf ||
1139 !(rdev->wiphy.interface_modes & (1 << type))) {
55682965
JB
1140 err = -EOPNOTSUPP;
1141 goto unlock;
1142 }
1143
2ec600d6
LCC
1144 if (type == NL80211_IFTYPE_MESH_POINT &&
1145 info->attrs[NL80211_ATTR_MESH_ID]) {
1146 params.mesh_id = nla_data(info->attrs[NL80211_ATTR_MESH_ID]);
1147 params.mesh_id_len = nla_len(info->attrs[NL80211_ATTR_MESH_ID]);
1148 }
1149
9bc383de 1150 if (info->attrs[NL80211_ATTR_4ADDR]) {
8b787643 1151 params.use_4addr = !!nla_get_u8(info->attrs[NL80211_ATTR_4ADDR]);
ad4bb6f8 1152 err = nl80211_valid_4addr(rdev, NULL, params.use_4addr, type);
9bc383de
JB
1153 if (err)
1154 goto unlock;
1155 }
8b787643 1156
66f7ac50
MW
1157 err = parse_monitor_flags(type == NL80211_IFTYPE_MONITOR ?
1158 info->attrs[NL80211_ATTR_MNTR_FLAGS] : NULL,
1159 &flags);
79c97e97 1160 err = rdev->ops->add_virtual_intf(&rdev->wiphy,
66f7ac50 1161 nla_data(info->attrs[NL80211_ATTR_IFNAME]),
2ec600d6 1162 type, err ? NULL : &flags, &params);
2ec600d6 1163
55682965 1164 unlock:
79c97e97 1165 cfg80211_unlock_rdev(rdev);
3b85875a
JB
1166 unlock_rtnl:
1167 rtnl_unlock();
55682965
JB
1168 return err;
1169}
1170
1171static int nl80211_del_interface(struct sk_buff *skb, struct genl_info *info)
1172{
79c97e97 1173 struct cfg80211_registered_device *rdev;
463d0183 1174 int err;
55682965
JB
1175 struct net_device *dev;
1176
3b85875a
JB
1177 rtnl_lock();
1178
463d0183 1179 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
55682965 1180 if (err)
3b85875a 1181 goto unlock_rtnl;
55682965 1182
79c97e97 1183 if (!rdev->ops->del_virtual_intf) {
55682965
JB
1184 err = -EOPNOTSUPP;
1185 goto out;
1186 }
1187
463d0183 1188 err = rdev->ops->del_virtual_intf(&rdev->wiphy, dev);
55682965
JB
1189
1190 out:
79c97e97 1191 cfg80211_unlock_rdev(rdev);
463d0183 1192 dev_put(dev);
3b85875a
JB
1193 unlock_rtnl:
1194 rtnl_unlock();
55682965
JB
1195 return err;
1196}
1197
41ade00f
JB
1198struct get_key_cookie {
1199 struct sk_buff *msg;
1200 int error;
b9454e83 1201 int idx;
41ade00f
JB
1202};
1203
1204static void get_key_callback(void *c, struct key_params *params)
1205{
b9454e83 1206 struct nlattr *key;
41ade00f
JB
1207 struct get_key_cookie *cookie = c;
1208
1209 if (params->key)
1210 NLA_PUT(cookie->msg, NL80211_ATTR_KEY_DATA,
1211 params->key_len, params->key);
1212
1213 if (params->seq)
1214 NLA_PUT(cookie->msg, NL80211_ATTR_KEY_SEQ,
1215 params->seq_len, params->seq);
1216
1217 if (params->cipher)
1218 NLA_PUT_U32(cookie->msg, NL80211_ATTR_KEY_CIPHER,
1219 params->cipher);
1220
b9454e83
JB
1221 key = nla_nest_start(cookie->msg, NL80211_ATTR_KEY);
1222 if (!key)
1223 goto nla_put_failure;
1224
1225 if (params->key)
1226 NLA_PUT(cookie->msg, NL80211_KEY_DATA,
1227 params->key_len, params->key);
1228
1229 if (params->seq)
1230 NLA_PUT(cookie->msg, NL80211_KEY_SEQ,
1231 params->seq_len, params->seq);
1232
1233 if (params->cipher)
1234 NLA_PUT_U32(cookie->msg, NL80211_KEY_CIPHER,
1235 params->cipher);
1236
1237 NLA_PUT_U8(cookie->msg, NL80211_ATTR_KEY_IDX, cookie->idx);
1238
1239 nla_nest_end(cookie->msg, key);
1240
41ade00f
JB
1241 return;
1242 nla_put_failure:
1243 cookie->error = 1;
1244}
1245
1246static int nl80211_get_key(struct sk_buff *skb, struct genl_info *info)
1247{
79c97e97 1248 struct cfg80211_registered_device *rdev;
41ade00f
JB
1249 int err;
1250 struct net_device *dev;
1251 u8 key_idx = 0;
1252 u8 *mac_addr = NULL;
1253 struct get_key_cookie cookie = {
1254 .error = 0,
1255 };
1256 void *hdr;
1257 struct sk_buff *msg;
1258
1259 if (info->attrs[NL80211_ATTR_KEY_IDX])
1260 key_idx = nla_get_u8(info->attrs[NL80211_ATTR_KEY_IDX]);
1261
3cfcf6ac 1262 if (key_idx > 5)
41ade00f
JB
1263 return -EINVAL;
1264
1265 if (info->attrs[NL80211_ATTR_MAC])
1266 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
1267
3b85875a
JB
1268 rtnl_lock();
1269
463d0183 1270 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
41ade00f 1271 if (err)
3b85875a 1272 goto unlock_rtnl;
41ade00f 1273
79c97e97 1274 if (!rdev->ops->get_key) {
41ade00f
JB
1275 err = -EOPNOTSUPP;
1276 goto out;
1277 }
1278
fd2120ca 1279 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
41ade00f
JB
1280 if (!msg) {
1281 err = -ENOMEM;
1282 goto out;
1283 }
1284
1285 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0,
1286 NL80211_CMD_NEW_KEY);
1287
1288 if (IS_ERR(hdr)) {
1289 err = PTR_ERR(hdr);
6c95e2a2 1290 goto free_msg;
41ade00f
JB
1291 }
1292
1293 cookie.msg = msg;
b9454e83 1294 cookie.idx = key_idx;
41ade00f
JB
1295
1296 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, dev->ifindex);
1297 NLA_PUT_U8(msg, NL80211_ATTR_KEY_IDX, key_idx);
1298 if (mac_addr)
1299 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, mac_addr);
1300
79c97e97 1301 err = rdev->ops->get_key(&rdev->wiphy, dev, key_idx, mac_addr,
41ade00f 1302 &cookie, get_key_callback);
41ade00f
JB
1303
1304 if (err)
6c95e2a2 1305 goto free_msg;
41ade00f
JB
1306
1307 if (cookie.error)
1308 goto nla_put_failure;
1309
1310 genlmsg_end(msg, hdr);
134e6375 1311 err = genlmsg_reply(msg, info);
41ade00f
JB
1312 goto out;
1313
1314 nla_put_failure:
1315 err = -ENOBUFS;
6c95e2a2 1316 free_msg:
41ade00f
JB
1317 nlmsg_free(msg);
1318 out:
79c97e97 1319 cfg80211_unlock_rdev(rdev);
41ade00f 1320 dev_put(dev);
3b85875a
JB
1321 unlock_rtnl:
1322 rtnl_unlock();
1323
41ade00f
JB
1324 return err;
1325}
1326
1327static int nl80211_set_key(struct sk_buff *skb, struct genl_info *info)
1328{
79c97e97 1329 struct cfg80211_registered_device *rdev;
b9454e83 1330 struct key_parse key;
41ade00f
JB
1331 int err;
1332 struct net_device *dev;
3cfcf6ac
JM
1333 int (*func)(struct wiphy *wiphy, struct net_device *netdev,
1334 u8 key_index);
41ade00f 1335
b9454e83
JB
1336 err = nl80211_parse_key(info, &key);
1337 if (err)
1338 return err;
41ade00f 1339
b9454e83 1340 if (key.idx < 0)
41ade00f
JB
1341 return -EINVAL;
1342
b9454e83
JB
1343 /* only support setting default key */
1344 if (!key.def && !key.defmgmt)
41ade00f
JB
1345 return -EINVAL;
1346
3b85875a
JB
1347 rtnl_lock();
1348
463d0183 1349 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
41ade00f 1350 if (err)
3b85875a 1351 goto unlock_rtnl;
41ade00f 1352
b9454e83 1353 if (key.def)
79c97e97 1354 func = rdev->ops->set_default_key;
3cfcf6ac 1355 else
79c97e97 1356 func = rdev->ops->set_default_mgmt_key;
3cfcf6ac
JM
1357
1358 if (!func) {
41ade00f
JB
1359 err = -EOPNOTSUPP;
1360 goto out;
1361 }
1362
fffd0934
JB
1363 wdev_lock(dev->ieee80211_ptr);
1364 err = nl80211_key_allowed(dev->ieee80211_ptr);
1365 if (!err)
1366 err = func(&rdev->wiphy, dev, key.idx);
1367
3d23e349 1368#ifdef CONFIG_CFG80211_WEXT
08645126 1369 if (!err) {
79c97e97 1370 if (func == rdev->ops->set_default_key)
b9454e83 1371 dev->ieee80211_ptr->wext.default_key = key.idx;
08645126 1372 else
b9454e83 1373 dev->ieee80211_ptr->wext.default_mgmt_key = key.idx;
08645126
JB
1374 }
1375#endif
fffd0934 1376 wdev_unlock(dev->ieee80211_ptr);
41ade00f
JB
1377
1378 out:
79c97e97 1379 cfg80211_unlock_rdev(rdev);
41ade00f 1380 dev_put(dev);
3b85875a
JB
1381
1382 unlock_rtnl:
1383 rtnl_unlock();
1384
41ade00f
JB
1385 return err;
1386}
1387
1388static int nl80211_new_key(struct sk_buff *skb, struct genl_info *info)
1389{
79c97e97 1390 struct cfg80211_registered_device *rdev;
fffd0934 1391 int err;
41ade00f 1392 struct net_device *dev;
b9454e83 1393 struct key_parse key;
41ade00f
JB
1394 u8 *mac_addr = NULL;
1395
b9454e83
JB
1396 err = nl80211_parse_key(info, &key);
1397 if (err)
1398 return err;
41ade00f 1399
b9454e83 1400 if (!key.p.key)
41ade00f
JB
1401 return -EINVAL;
1402
41ade00f
JB
1403 if (info->attrs[NL80211_ATTR_MAC])
1404 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
1405
3b85875a
JB
1406 rtnl_lock();
1407
463d0183 1408 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
41ade00f 1409 if (err)
3b85875a 1410 goto unlock_rtnl;
41ade00f 1411
fffd0934
JB
1412 if (!rdev->ops->add_key) {
1413 err = -EOPNOTSUPP;
25e47c18
JB
1414 goto out;
1415 }
1416
fffd0934
JB
1417 if (cfg80211_validate_key_settings(rdev, &key.p, key.idx, mac_addr)) {
1418 err = -EINVAL;
41ade00f
JB
1419 goto out;
1420 }
1421
fffd0934
JB
1422 wdev_lock(dev->ieee80211_ptr);
1423 err = nl80211_key_allowed(dev->ieee80211_ptr);
1424 if (!err)
1425 err = rdev->ops->add_key(&rdev->wiphy, dev, key.idx,
1426 mac_addr, &key.p);
1427 wdev_unlock(dev->ieee80211_ptr);
41ade00f
JB
1428
1429 out:
79c97e97 1430 cfg80211_unlock_rdev(rdev);
41ade00f 1431 dev_put(dev);
3b85875a
JB
1432 unlock_rtnl:
1433 rtnl_unlock();
1434
41ade00f
JB
1435 return err;
1436}
1437
1438static int nl80211_del_key(struct sk_buff *skb, struct genl_info *info)
1439{
79c97e97 1440 struct cfg80211_registered_device *rdev;
41ade00f
JB
1441 int err;
1442 struct net_device *dev;
41ade00f 1443 u8 *mac_addr = NULL;
b9454e83 1444 struct key_parse key;
41ade00f 1445
b9454e83
JB
1446 err = nl80211_parse_key(info, &key);
1447 if (err)
1448 return err;
41ade00f
JB
1449
1450 if (info->attrs[NL80211_ATTR_MAC])
1451 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
1452
3b85875a
JB
1453 rtnl_lock();
1454
463d0183 1455 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
41ade00f 1456 if (err)
3b85875a 1457 goto unlock_rtnl;
41ade00f 1458
79c97e97 1459 if (!rdev->ops->del_key) {
41ade00f
JB
1460 err = -EOPNOTSUPP;
1461 goto out;
1462 }
1463
fffd0934
JB
1464 wdev_lock(dev->ieee80211_ptr);
1465 err = nl80211_key_allowed(dev->ieee80211_ptr);
1466 if (!err)
1467 err = rdev->ops->del_key(&rdev->wiphy, dev, key.idx, mac_addr);
41ade00f 1468
3d23e349 1469#ifdef CONFIG_CFG80211_WEXT
08645126 1470 if (!err) {
b9454e83 1471 if (key.idx == dev->ieee80211_ptr->wext.default_key)
08645126 1472 dev->ieee80211_ptr->wext.default_key = -1;
b9454e83 1473 else if (key.idx == dev->ieee80211_ptr->wext.default_mgmt_key)
08645126
JB
1474 dev->ieee80211_ptr->wext.default_mgmt_key = -1;
1475 }
1476#endif
fffd0934 1477 wdev_unlock(dev->ieee80211_ptr);
08645126 1478
41ade00f 1479 out:
79c97e97 1480 cfg80211_unlock_rdev(rdev);
41ade00f 1481 dev_put(dev);
3b85875a
JB
1482
1483 unlock_rtnl:
1484 rtnl_unlock();
1485
41ade00f
JB
1486 return err;
1487}
1488
ed1b6cc7
JB
1489static int nl80211_addset_beacon(struct sk_buff *skb, struct genl_info *info)
1490{
1491 int (*call)(struct wiphy *wiphy, struct net_device *dev,
1492 struct beacon_parameters *info);
79c97e97 1493 struct cfg80211_registered_device *rdev;
ed1b6cc7
JB
1494 int err;
1495 struct net_device *dev;
1496 struct beacon_parameters params;
1497 int haveinfo = 0;
1498
f4a11bb0
JB
1499 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_BEACON_TAIL]))
1500 return -EINVAL;
1501
3b85875a
JB
1502 rtnl_lock();
1503
463d0183 1504 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
ed1b6cc7 1505 if (err)
3b85875a 1506 goto unlock_rtnl;
ed1b6cc7 1507
eec60b03
JM
1508 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP) {
1509 err = -EOPNOTSUPP;
1510 goto out;
1511 }
1512
ed1b6cc7
JB
1513 switch (info->genlhdr->cmd) {
1514 case NL80211_CMD_NEW_BEACON:
1515 /* these are required for NEW_BEACON */
1516 if (!info->attrs[NL80211_ATTR_BEACON_INTERVAL] ||
1517 !info->attrs[NL80211_ATTR_DTIM_PERIOD] ||
1518 !info->attrs[NL80211_ATTR_BEACON_HEAD]) {
1519 err = -EINVAL;
1520 goto out;
1521 }
1522
79c97e97 1523 call = rdev->ops->add_beacon;
ed1b6cc7
JB
1524 break;
1525 case NL80211_CMD_SET_BEACON:
79c97e97 1526 call = rdev->ops->set_beacon;
ed1b6cc7
JB
1527 break;
1528 default:
1529 WARN_ON(1);
1530 err = -EOPNOTSUPP;
1531 goto out;
1532 }
1533
1534 if (!call) {
1535 err = -EOPNOTSUPP;
1536 goto out;
1537 }
1538
1539 memset(&params, 0, sizeof(params));
1540
1541 if (info->attrs[NL80211_ATTR_BEACON_INTERVAL]) {
1542 params.interval =
1543 nla_get_u32(info->attrs[NL80211_ATTR_BEACON_INTERVAL]);
1544 haveinfo = 1;
1545 }
1546
1547 if (info->attrs[NL80211_ATTR_DTIM_PERIOD]) {
1548 params.dtim_period =
1549 nla_get_u32(info->attrs[NL80211_ATTR_DTIM_PERIOD]);
1550 haveinfo = 1;
1551 }
1552
1553 if (info->attrs[NL80211_ATTR_BEACON_HEAD]) {
1554 params.head = nla_data(info->attrs[NL80211_ATTR_BEACON_HEAD]);
1555 params.head_len =
1556 nla_len(info->attrs[NL80211_ATTR_BEACON_HEAD]);
1557 haveinfo = 1;
1558 }
1559
1560 if (info->attrs[NL80211_ATTR_BEACON_TAIL]) {
1561 params.tail = nla_data(info->attrs[NL80211_ATTR_BEACON_TAIL]);
1562 params.tail_len =
1563 nla_len(info->attrs[NL80211_ATTR_BEACON_TAIL]);
1564 haveinfo = 1;
1565 }
1566
1567 if (!haveinfo) {
1568 err = -EINVAL;
1569 goto out;
1570 }
1571
79c97e97 1572 err = call(&rdev->wiphy, dev, &params);
ed1b6cc7
JB
1573
1574 out:
79c97e97 1575 cfg80211_unlock_rdev(rdev);
ed1b6cc7 1576 dev_put(dev);
3b85875a
JB
1577 unlock_rtnl:
1578 rtnl_unlock();
1579
ed1b6cc7
JB
1580 return err;
1581}
1582
1583static int nl80211_del_beacon(struct sk_buff *skb, struct genl_info *info)
1584{
79c97e97 1585 struct cfg80211_registered_device *rdev;
ed1b6cc7
JB
1586 int err;
1587 struct net_device *dev;
1588
3b85875a
JB
1589 rtnl_lock();
1590
463d0183 1591 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
ed1b6cc7 1592 if (err)
3b85875a 1593 goto unlock_rtnl;
ed1b6cc7 1594
79c97e97 1595 if (!rdev->ops->del_beacon) {
ed1b6cc7
JB
1596 err = -EOPNOTSUPP;
1597 goto out;
1598 }
1599
eec60b03
JM
1600 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP) {
1601 err = -EOPNOTSUPP;
1602 goto out;
1603 }
79c97e97 1604 err = rdev->ops->del_beacon(&rdev->wiphy, dev);
ed1b6cc7
JB
1605
1606 out:
79c97e97 1607 cfg80211_unlock_rdev(rdev);
ed1b6cc7 1608 dev_put(dev);
3b85875a
JB
1609 unlock_rtnl:
1610 rtnl_unlock();
1611
ed1b6cc7
JB
1612 return err;
1613}
1614
5727ef1b
JB
1615static const struct nla_policy sta_flags_policy[NL80211_STA_FLAG_MAX + 1] = {
1616 [NL80211_STA_FLAG_AUTHORIZED] = { .type = NLA_FLAG },
1617 [NL80211_STA_FLAG_SHORT_PREAMBLE] = { .type = NLA_FLAG },
1618 [NL80211_STA_FLAG_WME] = { .type = NLA_FLAG },
0e46724a 1619 [NL80211_STA_FLAG_MFP] = { .type = NLA_FLAG },
5727ef1b
JB
1620};
1621
eccb8e8f
JB
1622static int parse_station_flags(struct genl_info *info,
1623 struct station_parameters *params)
5727ef1b
JB
1624{
1625 struct nlattr *flags[NL80211_STA_FLAG_MAX + 1];
eccb8e8f 1626 struct nlattr *nla;
5727ef1b
JB
1627 int flag;
1628
eccb8e8f
JB
1629 /*
1630 * Try parsing the new attribute first so userspace
1631 * can specify both for older kernels.
1632 */
1633 nla = info->attrs[NL80211_ATTR_STA_FLAGS2];
1634 if (nla) {
1635 struct nl80211_sta_flag_update *sta_flags;
1636
1637 sta_flags = nla_data(nla);
1638 params->sta_flags_mask = sta_flags->mask;
1639 params->sta_flags_set = sta_flags->set;
1640 if ((params->sta_flags_mask |
1641 params->sta_flags_set) & BIT(__NL80211_STA_FLAG_INVALID))
1642 return -EINVAL;
1643 return 0;
1644 }
1645
1646 /* if present, parse the old attribute */
5727ef1b 1647
eccb8e8f 1648 nla = info->attrs[NL80211_ATTR_STA_FLAGS];
5727ef1b
JB
1649 if (!nla)
1650 return 0;
1651
1652 if (nla_parse_nested(flags, NL80211_STA_FLAG_MAX,
1653 nla, sta_flags_policy))
1654 return -EINVAL;
1655
eccb8e8f
JB
1656 params->sta_flags_mask = (1 << __NL80211_STA_FLAG_AFTER_LAST) - 1;
1657 params->sta_flags_mask &= ~1;
5727ef1b
JB
1658
1659 for (flag = 1; flag <= NL80211_STA_FLAG_MAX; flag++)
1660 if (flags[flag])
eccb8e8f 1661 params->sta_flags_set |= (1<<flag);
5727ef1b
JB
1662
1663 return 0;
1664}
1665
fd5b74dc
JB
1666static int nl80211_send_station(struct sk_buff *msg, u32 pid, u32 seq,
1667 int flags, struct net_device *dev,
98b62183 1668 const u8 *mac_addr, struct station_info *sinfo)
fd5b74dc
JB
1669{
1670 void *hdr;
420e7fab
HR
1671 struct nlattr *sinfoattr, *txrate;
1672 u16 bitrate;
fd5b74dc
JB
1673
1674 hdr = nl80211hdr_put(msg, pid, seq, flags, NL80211_CMD_NEW_STATION);
1675 if (!hdr)
1676 return -1;
1677
1678 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, dev->ifindex);
1679 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, mac_addr);
1680
f5ea9120
JB
1681 NLA_PUT_U32(msg, NL80211_ATTR_GENERATION, sinfo->generation);
1682
2ec600d6
LCC
1683 sinfoattr = nla_nest_start(msg, NL80211_ATTR_STA_INFO);
1684 if (!sinfoattr)
fd5b74dc 1685 goto nla_put_failure;
2ec600d6
LCC
1686 if (sinfo->filled & STATION_INFO_INACTIVE_TIME)
1687 NLA_PUT_U32(msg, NL80211_STA_INFO_INACTIVE_TIME,
1688 sinfo->inactive_time);
1689 if (sinfo->filled & STATION_INFO_RX_BYTES)
1690 NLA_PUT_U32(msg, NL80211_STA_INFO_RX_BYTES,
1691 sinfo->rx_bytes);
1692 if (sinfo->filled & STATION_INFO_TX_BYTES)
1693 NLA_PUT_U32(msg, NL80211_STA_INFO_TX_BYTES,
1694 sinfo->tx_bytes);
1695 if (sinfo->filled & STATION_INFO_LLID)
1696 NLA_PUT_U16(msg, NL80211_STA_INFO_LLID,
1697 sinfo->llid);
1698 if (sinfo->filled & STATION_INFO_PLID)
1699 NLA_PUT_U16(msg, NL80211_STA_INFO_PLID,
1700 sinfo->plid);
1701 if (sinfo->filled & STATION_INFO_PLINK_STATE)
1702 NLA_PUT_U8(msg, NL80211_STA_INFO_PLINK_STATE,
1703 sinfo->plink_state);
420e7fab
HR
1704 if (sinfo->filled & STATION_INFO_SIGNAL)
1705 NLA_PUT_U8(msg, NL80211_STA_INFO_SIGNAL,
1706 sinfo->signal);
1707 if (sinfo->filled & STATION_INFO_TX_BITRATE) {
1708 txrate = nla_nest_start(msg, NL80211_STA_INFO_TX_BITRATE);
1709 if (!txrate)
1710 goto nla_put_failure;
1711
254416aa
JL
1712 /* cfg80211_calculate_bitrate will return 0 for mcs >= 32 */
1713 bitrate = cfg80211_calculate_bitrate(&sinfo->txrate);
420e7fab
HR
1714 if (bitrate > 0)
1715 NLA_PUT_U16(msg, NL80211_RATE_INFO_BITRATE, bitrate);
2ec600d6 1716
420e7fab
HR
1717 if (sinfo->txrate.flags & RATE_INFO_FLAGS_MCS)
1718 NLA_PUT_U8(msg, NL80211_RATE_INFO_MCS,
1719 sinfo->txrate.mcs);
1720 if (sinfo->txrate.flags & RATE_INFO_FLAGS_40_MHZ_WIDTH)
1721 NLA_PUT_FLAG(msg, NL80211_RATE_INFO_40_MHZ_WIDTH);
1722 if (sinfo->txrate.flags & RATE_INFO_FLAGS_SHORT_GI)
1723 NLA_PUT_FLAG(msg, NL80211_RATE_INFO_SHORT_GI);
1724
1725 nla_nest_end(msg, txrate);
1726 }
98c8a60a
JM
1727 if (sinfo->filled & STATION_INFO_RX_PACKETS)
1728 NLA_PUT_U32(msg, NL80211_STA_INFO_RX_PACKETS,
1729 sinfo->rx_packets);
1730 if (sinfo->filled & STATION_INFO_TX_PACKETS)
1731 NLA_PUT_U32(msg, NL80211_STA_INFO_TX_PACKETS,
1732 sinfo->tx_packets);
2ec600d6 1733 nla_nest_end(msg, sinfoattr);
fd5b74dc
JB
1734
1735 return genlmsg_end(msg, hdr);
1736
1737 nla_put_failure:
bc3ed28c
TG
1738 genlmsg_cancel(msg, hdr);
1739 return -EMSGSIZE;
fd5b74dc
JB
1740}
1741
2ec600d6 1742static int nl80211_dump_station(struct sk_buff *skb,
bba95fef 1743 struct netlink_callback *cb)
2ec600d6 1744{
2ec600d6
LCC
1745 struct station_info sinfo;
1746 struct cfg80211_registered_device *dev;
bba95fef 1747 struct net_device *netdev;
2ec600d6 1748 u8 mac_addr[ETH_ALEN];
bba95fef
JB
1749 int ifidx = cb->args[0];
1750 int sta_idx = cb->args[1];
2ec600d6 1751 int err;
2ec600d6 1752
a043897a
HS
1753 if (!ifidx)
1754 ifidx = nl80211_get_ifidx(cb);
1755 if (ifidx < 0)
1756 return ifidx;
2ec600d6 1757
3b85875a
JB
1758 rtnl_lock();
1759
463d0183 1760 netdev = __dev_get_by_index(sock_net(skb->sk), ifidx);
3b85875a
JB
1761 if (!netdev) {
1762 err = -ENODEV;
1763 goto out_rtnl;
1764 }
2ec600d6 1765
463d0183 1766 dev = cfg80211_get_dev_from_ifindex(sock_net(skb->sk), ifidx);
bba95fef
JB
1767 if (IS_ERR(dev)) {
1768 err = PTR_ERR(dev);
3b85875a 1769 goto out_rtnl;
bba95fef
JB
1770 }
1771
1772 if (!dev->ops->dump_station) {
eec60b03 1773 err = -EOPNOTSUPP;
bba95fef
JB
1774 goto out_err;
1775 }
1776
bba95fef
JB
1777 while (1) {
1778 err = dev->ops->dump_station(&dev->wiphy, netdev, sta_idx,
1779 mac_addr, &sinfo);
1780 if (err == -ENOENT)
1781 break;
1782 if (err)
3b85875a 1783 goto out_err;
bba95fef
JB
1784
1785 if (nl80211_send_station(skb,
1786 NETLINK_CB(cb->skb).pid,
1787 cb->nlh->nlmsg_seq, NLM_F_MULTI,
1788 netdev, mac_addr,
1789 &sinfo) < 0)
1790 goto out;
1791
1792 sta_idx++;
1793 }
1794
1795
1796 out:
1797 cb->args[1] = sta_idx;
1798 err = skb->len;
bba95fef 1799 out_err:
4d0c8aea 1800 cfg80211_unlock_rdev(dev);
3b85875a
JB
1801 out_rtnl:
1802 rtnl_unlock();
bba95fef
JB
1803
1804 return err;
2ec600d6 1805}
fd5b74dc 1806
5727ef1b
JB
1807static int nl80211_get_station(struct sk_buff *skb, struct genl_info *info)
1808{
79c97e97 1809 struct cfg80211_registered_device *rdev;
fd5b74dc
JB
1810 int err;
1811 struct net_device *dev;
2ec600d6 1812 struct station_info sinfo;
fd5b74dc
JB
1813 struct sk_buff *msg;
1814 u8 *mac_addr = NULL;
1815
2ec600d6 1816 memset(&sinfo, 0, sizeof(sinfo));
fd5b74dc
JB
1817
1818 if (!info->attrs[NL80211_ATTR_MAC])
1819 return -EINVAL;
1820
1821 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
1822
3b85875a
JB
1823 rtnl_lock();
1824
463d0183 1825 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
fd5b74dc 1826 if (err)
3b85875a 1827 goto out_rtnl;
fd5b74dc 1828
79c97e97 1829 if (!rdev->ops->get_station) {
fd5b74dc
JB
1830 err = -EOPNOTSUPP;
1831 goto out;
1832 }
1833
79c97e97 1834 err = rdev->ops->get_station(&rdev->wiphy, dev, mac_addr, &sinfo);
2ec600d6
LCC
1835 if (err)
1836 goto out;
1837
fd2120ca 1838 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
fd5b74dc
JB
1839 if (!msg)
1840 goto out;
1841
1842 if (nl80211_send_station(msg, info->snd_pid, info->snd_seq, 0,
2ec600d6 1843 dev, mac_addr, &sinfo) < 0)
fd5b74dc
JB
1844 goto out_free;
1845
134e6375 1846 err = genlmsg_reply(msg, info);
fd5b74dc
JB
1847 goto out;
1848
1849 out_free:
1850 nlmsg_free(msg);
fd5b74dc 1851 out:
79c97e97 1852 cfg80211_unlock_rdev(rdev);
fd5b74dc 1853 dev_put(dev);
3b85875a
JB
1854 out_rtnl:
1855 rtnl_unlock();
1856
fd5b74dc 1857 return err;
5727ef1b
JB
1858}
1859
1860/*
c258d2de 1861 * Get vlan interface making sure it is running and on the right wiphy.
5727ef1b 1862 */
463d0183 1863static int get_vlan(struct genl_info *info,
5727ef1b
JB
1864 struct cfg80211_registered_device *rdev,
1865 struct net_device **vlan)
1866{
463d0183 1867 struct nlattr *vlanattr = info->attrs[NL80211_ATTR_STA_VLAN];
5727ef1b
JB
1868 *vlan = NULL;
1869
1870 if (vlanattr) {
463d0183
JB
1871 *vlan = dev_get_by_index(genl_info_net(info),
1872 nla_get_u32(vlanattr));
5727ef1b
JB
1873 if (!*vlan)
1874 return -ENODEV;
1875 if (!(*vlan)->ieee80211_ptr)
1876 return -EINVAL;
1877 if ((*vlan)->ieee80211_ptr->wiphy != &rdev->wiphy)
1878 return -EINVAL;
c258d2de
FF
1879 if (!netif_running(*vlan))
1880 return -ENETDOWN;
5727ef1b
JB
1881 }
1882 return 0;
1883}
1884
1885static int nl80211_set_station(struct sk_buff *skb, struct genl_info *info)
1886{
79c97e97 1887 struct cfg80211_registered_device *rdev;
5727ef1b
JB
1888 int err;
1889 struct net_device *dev;
1890 struct station_parameters params;
1891 u8 *mac_addr = NULL;
1892
1893 memset(&params, 0, sizeof(params));
1894
1895 params.listen_interval = -1;
1896
1897 if (info->attrs[NL80211_ATTR_STA_AID])
1898 return -EINVAL;
1899
1900 if (!info->attrs[NL80211_ATTR_MAC])
1901 return -EINVAL;
1902
1903 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
1904
1905 if (info->attrs[NL80211_ATTR_STA_SUPPORTED_RATES]) {
1906 params.supported_rates =
1907 nla_data(info->attrs[NL80211_ATTR_STA_SUPPORTED_RATES]);
1908 params.supported_rates_len =
1909 nla_len(info->attrs[NL80211_ATTR_STA_SUPPORTED_RATES]);
1910 }
1911
1912 if (info->attrs[NL80211_ATTR_STA_LISTEN_INTERVAL])
1913 params.listen_interval =
1914 nla_get_u16(info->attrs[NL80211_ATTR_STA_LISTEN_INTERVAL]);
1915
36aedc90
JM
1916 if (info->attrs[NL80211_ATTR_HT_CAPABILITY])
1917 params.ht_capa =
1918 nla_data(info->attrs[NL80211_ATTR_HT_CAPABILITY]);
1919
eccb8e8f 1920 if (parse_station_flags(info, &params))
5727ef1b
JB
1921 return -EINVAL;
1922
2ec600d6
LCC
1923 if (info->attrs[NL80211_ATTR_STA_PLINK_ACTION])
1924 params.plink_action =
1925 nla_get_u8(info->attrs[NL80211_ATTR_STA_PLINK_ACTION]);
1926
3b85875a
JB
1927 rtnl_lock();
1928
463d0183 1929 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
5727ef1b 1930 if (err)
3b85875a 1931 goto out_rtnl;
5727ef1b 1932
463d0183 1933 err = get_vlan(info, rdev, &params.vlan);
a97f4424 1934 if (err)
034d655e 1935 goto out;
a97f4424
JB
1936
1937 /* validate settings */
1938 err = 0;
1939
1940 switch (dev->ieee80211_ptr->iftype) {
1941 case NL80211_IFTYPE_AP:
1942 case NL80211_IFTYPE_AP_VLAN:
1943 /* disallow mesh-specific things */
1944 if (params.plink_action)
1945 err = -EINVAL;
1946 break;
1947 case NL80211_IFTYPE_STATION:
1948 /* disallow everything but AUTHORIZED flag */
1949 if (params.plink_action)
1950 err = -EINVAL;
1951 if (params.vlan)
1952 err = -EINVAL;
1953 if (params.supported_rates)
1954 err = -EINVAL;
1955 if (params.ht_capa)
1956 err = -EINVAL;
1957 if (params.listen_interval >= 0)
1958 err = -EINVAL;
1959 if (params.sta_flags_mask & ~BIT(NL80211_STA_FLAG_AUTHORIZED))
1960 err = -EINVAL;
1961 break;
1962 case NL80211_IFTYPE_MESH_POINT:
1963 /* disallow things mesh doesn't support */
1964 if (params.vlan)
1965 err = -EINVAL;
1966 if (params.ht_capa)
1967 err = -EINVAL;
1968 if (params.listen_interval >= 0)
1969 err = -EINVAL;
1970 if (params.supported_rates)
1971 err = -EINVAL;
1972 if (params.sta_flags_mask)
1973 err = -EINVAL;
1974 break;
1975 default:
1976 err = -EINVAL;
034d655e
JB
1977 }
1978
5727ef1b
JB
1979 if (err)
1980 goto out;
1981
79c97e97 1982 if (!rdev->ops->change_station) {
5727ef1b
JB
1983 err = -EOPNOTSUPP;
1984 goto out;
1985 }
1986
79c97e97 1987 err = rdev->ops->change_station(&rdev->wiphy, dev, mac_addr, &params);
5727ef1b
JB
1988
1989 out:
1990 if (params.vlan)
1991 dev_put(params.vlan);
79c97e97 1992 cfg80211_unlock_rdev(rdev);
5727ef1b 1993 dev_put(dev);
3b85875a
JB
1994 out_rtnl:
1995 rtnl_unlock();
1996
5727ef1b
JB
1997 return err;
1998}
1999
2000static int nl80211_new_station(struct sk_buff *skb, struct genl_info *info)
2001{
79c97e97 2002 struct cfg80211_registered_device *rdev;
5727ef1b
JB
2003 int err;
2004 struct net_device *dev;
2005 struct station_parameters params;
2006 u8 *mac_addr = NULL;
2007
2008 memset(&params, 0, sizeof(params));
2009
2010 if (!info->attrs[NL80211_ATTR_MAC])
2011 return -EINVAL;
2012
5727ef1b
JB
2013 if (!info->attrs[NL80211_ATTR_STA_LISTEN_INTERVAL])
2014 return -EINVAL;
2015
2016 if (!info->attrs[NL80211_ATTR_STA_SUPPORTED_RATES])
2017 return -EINVAL;
2018
0e956c13
TLSC
2019 if (!info->attrs[NL80211_ATTR_STA_AID])
2020 return -EINVAL;
2021
5727ef1b
JB
2022 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
2023 params.supported_rates =
2024 nla_data(info->attrs[NL80211_ATTR_STA_SUPPORTED_RATES]);
2025 params.supported_rates_len =
2026 nla_len(info->attrs[NL80211_ATTR_STA_SUPPORTED_RATES]);
2027 params.listen_interval =
2028 nla_get_u16(info->attrs[NL80211_ATTR_STA_LISTEN_INTERVAL]);
51b50fbe 2029
0e956c13
TLSC
2030 params.aid = nla_get_u16(info->attrs[NL80211_ATTR_STA_AID]);
2031 if (!params.aid || params.aid > IEEE80211_MAX_AID)
2032 return -EINVAL;
51b50fbe 2033
36aedc90
JM
2034 if (info->attrs[NL80211_ATTR_HT_CAPABILITY])
2035 params.ht_capa =
2036 nla_data(info->attrs[NL80211_ATTR_HT_CAPABILITY]);
5727ef1b 2037
eccb8e8f 2038 if (parse_station_flags(info, &params))
5727ef1b
JB
2039 return -EINVAL;
2040
3b85875a
JB
2041 rtnl_lock();
2042
463d0183 2043 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
5727ef1b 2044 if (err)
3b85875a 2045 goto out_rtnl;
5727ef1b 2046
0e956c13
TLSC
2047 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP &&
2048 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP_VLAN) {
2049 err = -EINVAL;
2050 goto out;
2051 }
2052
463d0183 2053 err = get_vlan(info, rdev, &params.vlan);
a97f4424 2054 if (err)
e80cf853 2055 goto out;
a97f4424
JB
2056
2057 /* validate settings */
2058 err = 0;
2059
79c97e97 2060 if (!rdev->ops->add_station) {
5727ef1b
JB
2061 err = -EOPNOTSUPP;
2062 goto out;
2063 }
2064
35a8efe1
JM
2065 if (!netif_running(dev)) {
2066 err = -ENETDOWN;
2067 goto out;
2068 }
2069
79c97e97 2070 err = rdev->ops->add_station(&rdev->wiphy, dev, mac_addr, &params);
5727ef1b
JB
2071
2072 out:
2073 if (params.vlan)
2074 dev_put(params.vlan);
79c97e97 2075 cfg80211_unlock_rdev(rdev);
5727ef1b 2076 dev_put(dev);
3b85875a
JB
2077 out_rtnl:
2078 rtnl_unlock();
2079
5727ef1b
JB
2080 return err;
2081}
2082
2083static int nl80211_del_station(struct sk_buff *skb, struct genl_info *info)
2084{
79c97e97 2085 struct cfg80211_registered_device *rdev;
5727ef1b
JB
2086 int err;
2087 struct net_device *dev;
2088 u8 *mac_addr = NULL;
2089
2090 if (info->attrs[NL80211_ATTR_MAC])
2091 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
2092
3b85875a
JB
2093 rtnl_lock();
2094
463d0183 2095 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
5727ef1b 2096 if (err)
3b85875a 2097 goto out_rtnl;
5727ef1b 2098
e80cf853 2099 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP &&
d5d9de02
MP
2100 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP_VLAN &&
2101 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT) {
e80cf853
JB
2102 err = -EINVAL;
2103 goto out;
2104 }
2105
79c97e97 2106 if (!rdev->ops->del_station) {
5727ef1b
JB
2107 err = -EOPNOTSUPP;
2108 goto out;
2109 }
2110
79c97e97 2111 err = rdev->ops->del_station(&rdev->wiphy, dev, mac_addr);
5727ef1b
JB
2112
2113 out:
79c97e97 2114 cfg80211_unlock_rdev(rdev);
5727ef1b 2115 dev_put(dev);
3b85875a
JB
2116 out_rtnl:
2117 rtnl_unlock();
2118
5727ef1b
JB
2119 return err;
2120}
2121
2ec600d6
LCC
2122static int nl80211_send_mpath(struct sk_buff *msg, u32 pid, u32 seq,
2123 int flags, struct net_device *dev,
2124 u8 *dst, u8 *next_hop,
2125 struct mpath_info *pinfo)
2126{
2127 void *hdr;
2128 struct nlattr *pinfoattr;
2129
2130 hdr = nl80211hdr_put(msg, pid, seq, flags, NL80211_CMD_NEW_STATION);
2131 if (!hdr)
2132 return -1;
2133
2134 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, dev->ifindex);
2135 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, dst);
2136 NLA_PUT(msg, NL80211_ATTR_MPATH_NEXT_HOP, ETH_ALEN, next_hop);
2137
f5ea9120
JB
2138 NLA_PUT_U32(msg, NL80211_ATTR_GENERATION, pinfo->generation);
2139
2ec600d6
LCC
2140 pinfoattr = nla_nest_start(msg, NL80211_ATTR_MPATH_INFO);
2141 if (!pinfoattr)
2142 goto nla_put_failure;
2143 if (pinfo->filled & MPATH_INFO_FRAME_QLEN)
2144 NLA_PUT_U32(msg, NL80211_MPATH_INFO_FRAME_QLEN,
2145 pinfo->frame_qlen);
d19b3bf6
RP
2146 if (pinfo->filled & MPATH_INFO_SN)
2147 NLA_PUT_U32(msg, NL80211_MPATH_INFO_SN,
2148 pinfo->sn);
2ec600d6
LCC
2149 if (pinfo->filled & MPATH_INFO_METRIC)
2150 NLA_PUT_U32(msg, NL80211_MPATH_INFO_METRIC,
2151 pinfo->metric);
2152 if (pinfo->filled & MPATH_INFO_EXPTIME)
2153 NLA_PUT_U32(msg, NL80211_MPATH_INFO_EXPTIME,
2154 pinfo->exptime);
2155 if (pinfo->filled & MPATH_INFO_FLAGS)
2156 NLA_PUT_U8(msg, NL80211_MPATH_INFO_FLAGS,
2157 pinfo->flags);
2158 if (pinfo->filled & MPATH_INFO_DISCOVERY_TIMEOUT)
2159 NLA_PUT_U32(msg, NL80211_MPATH_INFO_DISCOVERY_TIMEOUT,
2160 pinfo->discovery_timeout);
2161 if (pinfo->filled & MPATH_INFO_DISCOVERY_RETRIES)
2162 NLA_PUT_U8(msg, NL80211_MPATH_INFO_DISCOVERY_RETRIES,
2163 pinfo->discovery_retries);
2164
2165 nla_nest_end(msg, pinfoattr);
2166
2167 return genlmsg_end(msg, hdr);
2168
2169 nla_put_failure:
bc3ed28c
TG
2170 genlmsg_cancel(msg, hdr);
2171 return -EMSGSIZE;
2ec600d6
LCC
2172}
2173
2174static int nl80211_dump_mpath(struct sk_buff *skb,
bba95fef 2175 struct netlink_callback *cb)
2ec600d6 2176{
2ec600d6
LCC
2177 struct mpath_info pinfo;
2178 struct cfg80211_registered_device *dev;
bba95fef 2179 struct net_device *netdev;
2ec600d6
LCC
2180 u8 dst[ETH_ALEN];
2181 u8 next_hop[ETH_ALEN];
bba95fef
JB
2182 int ifidx = cb->args[0];
2183 int path_idx = cb->args[1];
2ec600d6 2184 int err;
2ec600d6 2185
a043897a
HS
2186 if (!ifidx)
2187 ifidx = nl80211_get_ifidx(cb);
2188 if (ifidx < 0)
2189 return ifidx;
bba95fef 2190
3b85875a
JB
2191 rtnl_lock();
2192
463d0183 2193 netdev = __dev_get_by_index(sock_net(skb->sk), ifidx);
3b85875a
JB
2194 if (!netdev) {
2195 err = -ENODEV;
2196 goto out_rtnl;
2197 }
bba95fef 2198
463d0183 2199 dev = cfg80211_get_dev_from_ifindex(sock_net(skb->sk), ifidx);
bba95fef
JB
2200 if (IS_ERR(dev)) {
2201 err = PTR_ERR(dev);
3b85875a 2202 goto out_rtnl;
bba95fef
JB
2203 }
2204
2205 if (!dev->ops->dump_mpath) {
eec60b03 2206 err = -EOPNOTSUPP;
bba95fef
JB
2207 goto out_err;
2208 }
2209
eec60b03
JM
2210 if (netdev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT) {
2211 err = -EOPNOTSUPP;
0448b5fc 2212 goto out_err;
eec60b03
JM
2213 }
2214
bba95fef
JB
2215 while (1) {
2216 err = dev->ops->dump_mpath(&dev->wiphy, netdev, path_idx,
2217 dst, next_hop, &pinfo);
2218 if (err == -ENOENT)
2ec600d6 2219 break;
bba95fef 2220 if (err)
3b85875a 2221 goto out_err;
2ec600d6 2222
bba95fef
JB
2223 if (nl80211_send_mpath(skb, NETLINK_CB(cb->skb).pid,
2224 cb->nlh->nlmsg_seq, NLM_F_MULTI,
2225 netdev, dst, next_hop,
2226 &pinfo) < 0)
2227 goto out;
2ec600d6 2228
bba95fef 2229 path_idx++;
2ec600d6 2230 }
2ec600d6 2231
2ec600d6 2232
bba95fef
JB
2233 out:
2234 cb->args[1] = path_idx;
2235 err = skb->len;
bba95fef 2236 out_err:
4d0c8aea 2237 cfg80211_unlock_rdev(dev);
3b85875a
JB
2238 out_rtnl:
2239 rtnl_unlock();
bba95fef
JB
2240
2241 return err;
2ec600d6
LCC
2242}
2243
2244static int nl80211_get_mpath(struct sk_buff *skb, struct genl_info *info)
2245{
79c97e97 2246 struct cfg80211_registered_device *rdev;
2ec600d6
LCC
2247 int err;
2248 struct net_device *dev;
2249 struct mpath_info pinfo;
2250 struct sk_buff *msg;
2251 u8 *dst = NULL;
2252 u8 next_hop[ETH_ALEN];
2253
2254 memset(&pinfo, 0, sizeof(pinfo));
2255
2256 if (!info->attrs[NL80211_ATTR_MAC])
2257 return -EINVAL;
2258
2259 dst = nla_data(info->attrs[NL80211_ATTR_MAC]);
2260
3b85875a
JB
2261 rtnl_lock();
2262
463d0183 2263 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2ec600d6 2264 if (err)
3b85875a 2265 goto out_rtnl;
2ec600d6 2266
79c97e97 2267 if (!rdev->ops->get_mpath) {
2ec600d6
LCC
2268 err = -EOPNOTSUPP;
2269 goto out;
2270 }
2271
eec60b03
JM
2272 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT) {
2273 err = -EOPNOTSUPP;
2274 goto out;
2275 }
2276
79c97e97 2277 err = rdev->ops->get_mpath(&rdev->wiphy, dev, dst, next_hop, &pinfo);
2ec600d6
LCC
2278 if (err)
2279 goto out;
2280
fd2120ca 2281 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2ec600d6
LCC
2282 if (!msg)
2283 goto out;
2284
2285 if (nl80211_send_mpath(msg, info->snd_pid, info->snd_seq, 0,
2286 dev, dst, next_hop, &pinfo) < 0)
2287 goto out_free;
2288
134e6375 2289 err = genlmsg_reply(msg, info);
2ec600d6
LCC
2290 goto out;
2291
2292 out_free:
2293 nlmsg_free(msg);
2ec600d6 2294 out:
79c97e97 2295 cfg80211_unlock_rdev(rdev);
2ec600d6 2296 dev_put(dev);
3b85875a
JB
2297 out_rtnl:
2298 rtnl_unlock();
2299
2ec600d6
LCC
2300 return err;
2301}
2302
2303static int nl80211_set_mpath(struct sk_buff *skb, struct genl_info *info)
2304{
79c97e97 2305 struct cfg80211_registered_device *rdev;
2ec600d6
LCC
2306 int err;
2307 struct net_device *dev;
2308 u8 *dst = NULL;
2309 u8 *next_hop = NULL;
2310
2311 if (!info->attrs[NL80211_ATTR_MAC])
2312 return -EINVAL;
2313
2314 if (!info->attrs[NL80211_ATTR_MPATH_NEXT_HOP])
2315 return -EINVAL;
2316
2317 dst = nla_data(info->attrs[NL80211_ATTR_MAC]);
2318 next_hop = nla_data(info->attrs[NL80211_ATTR_MPATH_NEXT_HOP]);
2319
3b85875a
JB
2320 rtnl_lock();
2321
463d0183 2322 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2ec600d6 2323 if (err)
3b85875a 2324 goto out_rtnl;
2ec600d6 2325
79c97e97 2326 if (!rdev->ops->change_mpath) {
2ec600d6
LCC
2327 err = -EOPNOTSUPP;
2328 goto out;
2329 }
2330
eec60b03
JM
2331 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT) {
2332 err = -EOPNOTSUPP;
2333 goto out;
2334 }
2335
35a8efe1
JM
2336 if (!netif_running(dev)) {
2337 err = -ENETDOWN;
2338 goto out;
2339 }
2340
79c97e97 2341 err = rdev->ops->change_mpath(&rdev->wiphy, dev, dst, next_hop);
2ec600d6
LCC
2342
2343 out:
79c97e97 2344 cfg80211_unlock_rdev(rdev);
2ec600d6 2345 dev_put(dev);
3b85875a
JB
2346 out_rtnl:
2347 rtnl_unlock();
2348
2ec600d6
LCC
2349 return err;
2350}
2351static int nl80211_new_mpath(struct sk_buff *skb, struct genl_info *info)
2352{
79c97e97 2353 struct cfg80211_registered_device *rdev;
2ec600d6
LCC
2354 int err;
2355 struct net_device *dev;
2356 u8 *dst = NULL;
2357 u8 *next_hop = NULL;
2358
2359 if (!info->attrs[NL80211_ATTR_MAC])
2360 return -EINVAL;
2361
2362 if (!info->attrs[NL80211_ATTR_MPATH_NEXT_HOP])
2363 return -EINVAL;
2364
2365 dst = nla_data(info->attrs[NL80211_ATTR_MAC]);
2366 next_hop = nla_data(info->attrs[NL80211_ATTR_MPATH_NEXT_HOP]);
2367
3b85875a
JB
2368 rtnl_lock();
2369
463d0183 2370 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2ec600d6 2371 if (err)
3b85875a 2372 goto out_rtnl;
2ec600d6 2373
79c97e97 2374 if (!rdev->ops->add_mpath) {
2ec600d6
LCC
2375 err = -EOPNOTSUPP;
2376 goto out;
2377 }
2378
eec60b03
JM
2379 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT) {
2380 err = -EOPNOTSUPP;
2381 goto out;
2382 }
2383
35a8efe1
JM
2384 if (!netif_running(dev)) {
2385 err = -ENETDOWN;
2386 goto out;
2387 }
2388
79c97e97 2389 err = rdev->ops->add_mpath(&rdev->wiphy, dev, dst, next_hop);
2ec600d6
LCC
2390
2391 out:
79c97e97 2392 cfg80211_unlock_rdev(rdev);
2ec600d6 2393 dev_put(dev);
3b85875a
JB
2394 out_rtnl:
2395 rtnl_unlock();
2396
2ec600d6
LCC
2397 return err;
2398}
2399
2400static int nl80211_del_mpath(struct sk_buff *skb, struct genl_info *info)
2401{
79c97e97 2402 struct cfg80211_registered_device *rdev;
2ec600d6
LCC
2403 int err;
2404 struct net_device *dev;
2405 u8 *dst = NULL;
2406
2407 if (info->attrs[NL80211_ATTR_MAC])
2408 dst = nla_data(info->attrs[NL80211_ATTR_MAC]);
2409
3b85875a
JB
2410 rtnl_lock();
2411
463d0183 2412 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2ec600d6 2413 if (err)
3b85875a 2414 goto out_rtnl;
2ec600d6 2415
79c97e97 2416 if (!rdev->ops->del_mpath) {
2ec600d6
LCC
2417 err = -EOPNOTSUPP;
2418 goto out;
2419 }
2420
79c97e97 2421 err = rdev->ops->del_mpath(&rdev->wiphy, dev, dst);
2ec600d6
LCC
2422
2423 out:
79c97e97 2424 cfg80211_unlock_rdev(rdev);
2ec600d6 2425 dev_put(dev);
3b85875a
JB
2426 out_rtnl:
2427 rtnl_unlock();
2428
2ec600d6
LCC
2429 return err;
2430}
2431
9f1ba906
JM
2432static int nl80211_set_bss(struct sk_buff *skb, struct genl_info *info)
2433{
79c97e97 2434 struct cfg80211_registered_device *rdev;
9f1ba906
JM
2435 int err;
2436 struct net_device *dev;
2437 struct bss_parameters params;
2438
2439 memset(&params, 0, sizeof(params));
2440 /* default to not changing parameters */
2441 params.use_cts_prot = -1;
2442 params.use_short_preamble = -1;
2443 params.use_short_slot_time = -1;
2444
2445 if (info->attrs[NL80211_ATTR_BSS_CTS_PROT])
2446 params.use_cts_prot =
2447 nla_get_u8(info->attrs[NL80211_ATTR_BSS_CTS_PROT]);
2448 if (info->attrs[NL80211_ATTR_BSS_SHORT_PREAMBLE])
2449 params.use_short_preamble =
2450 nla_get_u8(info->attrs[NL80211_ATTR_BSS_SHORT_PREAMBLE]);
2451 if (info->attrs[NL80211_ATTR_BSS_SHORT_SLOT_TIME])
2452 params.use_short_slot_time =
2453 nla_get_u8(info->attrs[NL80211_ATTR_BSS_SHORT_SLOT_TIME]);
90c97a04
JM
2454 if (info->attrs[NL80211_ATTR_BSS_BASIC_RATES]) {
2455 params.basic_rates =
2456 nla_data(info->attrs[NL80211_ATTR_BSS_BASIC_RATES]);
2457 params.basic_rates_len =
2458 nla_len(info->attrs[NL80211_ATTR_BSS_BASIC_RATES]);
2459 }
9f1ba906 2460
3b85875a
JB
2461 rtnl_lock();
2462
463d0183 2463 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
9f1ba906 2464 if (err)
3b85875a 2465 goto out_rtnl;
9f1ba906 2466
79c97e97 2467 if (!rdev->ops->change_bss) {
9f1ba906
JM
2468 err = -EOPNOTSUPP;
2469 goto out;
2470 }
2471
eec60b03
JM
2472 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP) {
2473 err = -EOPNOTSUPP;
2474 goto out;
2475 }
2476
79c97e97 2477 err = rdev->ops->change_bss(&rdev->wiphy, dev, &params);
9f1ba906
JM
2478
2479 out:
79c97e97 2480 cfg80211_unlock_rdev(rdev);
9f1ba906 2481 dev_put(dev);
3b85875a
JB
2482 out_rtnl:
2483 rtnl_unlock();
2484
9f1ba906
JM
2485 return err;
2486}
2487
b54452b0 2488static const struct nla_policy reg_rule_policy[NL80211_REG_RULE_ATTR_MAX + 1] = {
b2e1b302
LR
2489 [NL80211_ATTR_REG_RULE_FLAGS] = { .type = NLA_U32 },
2490 [NL80211_ATTR_FREQ_RANGE_START] = { .type = NLA_U32 },
2491 [NL80211_ATTR_FREQ_RANGE_END] = { .type = NLA_U32 },
2492 [NL80211_ATTR_FREQ_RANGE_MAX_BW] = { .type = NLA_U32 },
2493 [NL80211_ATTR_POWER_RULE_MAX_ANT_GAIN] = { .type = NLA_U32 },
2494 [NL80211_ATTR_POWER_RULE_MAX_EIRP] = { .type = NLA_U32 },
2495};
2496
2497static int parse_reg_rule(struct nlattr *tb[],
2498 struct ieee80211_reg_rule *reg_rule)
2499{
2500 struct ieee80211_freq_range *freq_range = &reg_rule->freq_range;
2501 struct ieee80211_power_rule *power_rule = &reg_rule->power_rule;
2502
2503 if (!tb[NL80211_ATTR_REG_RULE_FLAGS])
2504 return -EINVAL;
2505 if (!tb[NL80211_ATTR_FREQ_RANGE_START])
2506 return -EINVAL;
2507 if (!tb[NL80211_ATTR_FREQ_RANGE_END])
2508 return -EINVAL;
2509 if (!tb[NL80211_ATTR_FREQ_RANGE_MAX_BW])
2510 return -EINVAL;
2511 if (!tb[NL80211_ATTR_POWER_RULE_MAX_EIRP])
2512 return -EINVAL;
2513
2514 reg_rule->flags = nla_get_u32(tb[NL80211_ATTR_REG_RULE_FLAGS]);
2515
2516 freq_range->start_freq_khz =
2517 nla_get_u32(tb[NL80211_ATTR_FREQ_RANGE_START]);
2518 freq_range->end_freq_khz =
2519 nla_get_u32(tb[NL80211_ATTR_FREQ_RANGE_END]);
2520 freq_range->max_bandwidth_khz =
2521 nla_get_u32(tb[NL80211_ATTR_FREQ_RANGE_MAX_BW]);
2522
2523 power_rule->max_eirp =
2524 nla_get_u32(tb[NL80211_ATTR_POWER_RULE_MAX_EIRP]);
2525
2526 if (tb[NL80211_ATTR_POWER_RULE_MAX_ANT_GAIN])
2527 power_rule->max_antenna_gain =
2528 nla_get_u32(tb[NL80211_ATTR_POWER_RULE_MAX_ANT_GAIN]);
2529
2530 return 0;
2531}
2532
2533static int nl80211_req_set_reg(struct sk_buff *skb, struct genl_info *info)
2534{
2535 int r;
2536 char *data = NULL;
2537
80778f18
LR
2538 /*
2539 * You should only get this when cfg80211 hasn't yet initialized
2540 * completely when built-in to the kernel right between the time
2541 * window between nl80211_init() and regulatory_init(), if that is
2542 * even possible.
2543 */
2544 mutex_lock(&cfg80211_mutex);
2545 if (unlikely(!cfg80211_regdomain)) {
fe33eb39
LR
2546 mutex_unlock(&cfg80211_mutex);
2547 return -EINPROGRESS;
80778f18 2548 }
fe33eb39 2549 mutex_unlock(&cfg80211_mutex);
80778f18 2550
fe33eb39
LR
2551 if (!info->attrs[NL80211_ATTR_REG_ALPHA2])
2552 return -EINVAL;
b2e1b302
LR
2553
2554 data = nla_data(info->attrs[NL80211_ATTR_REG_ALPHA2]);
2555
fe33eb39
LR
2556 r = regulatory_hint_user(data);
2557
b2e1b302
LR
2558 return r;
2559}
2560
93da9cc1 2561static int nl80211_get_mesh_params(struct sk_buff *skb,
2562 struct genl_info *info)
2563{
79c97e97 2564 struct cfg80211_registered_device *rdev;
93da9cc1 2565 struct mesh_config cur_params;
2566 int err;
2567 struct net_device *dev;
2568 void *hdr;
2569 struct nlattr *pinfoattr;
2570 struct sk_buff *msg;
2571
3b85875a
JB
2572 rtnl_lock();
2573
93da9cc1 2574 /* Look up our device */
463d0183 2575 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
93da9cc1 2576 if (err)
3b85875a 2577 goto out_rtnl;
93da9cc1 2578
79c97e97 2579 if (!rdev->ops->get_mesh_params) {
f3f92586
JM
2580 err = -EOPNOTSUPP;
2581 goto out;
2582 }
2583
93da9cc1 2584 /* Get the mesh params */
79c97e97 2585 err = rdev->ops->get_mesh_params(&rdev->wiphy, dev, &cur_params);
93da9cc1 2586 if (err)
2587 goto out;
2588
2589 /* Draw up a netlink message to send back */
fd2120ca 2590 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
93da9cc1 2591 if (!msg) {
2592 err = -ENOBUFS;
2593 goto out;
2594 }
2595 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0,
2596 NL80211_CMD_GET_MESH_PARAMS);
2597 if (!hdr)
2598 goto nla_put_failure;
2599 pinfoattr = nla_nest_start(msg, NL80211_ATTR_MESH_PARAMS);
2600 if (!pinfoattr)
2601 goto nla_put_failure;
2602 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, dev->ifindex);
2603 NLA_PUT_U16(msg, NL80211_MESHCONF_RETRY_TIMEOUT,
2604 cur_params.dot11MeshRetryTimeout);
2605 NLA_PUT_U16(msg, NL80211_MESHCONF_CONFIRM_TIMEOUT,
2606 cur_params.dot11MeshConfirmTimeout);
2607 NLA_PUT_U16(msg, NL80211_MESHCONF_HOLDING_TIMEOUT,
2608 cur_params.dot11MeshHoldingTimeout);
2609 NLA_PUT_U16(msg, NL80211_MESHCONF_MAX_PEER_LINKS,
2610 cur_params.dot11MeshMaxPeerLinks);
2611 NLA_PUT_U8(msg, NL80211_MESHCONF_MAX_RETRIES,
2612 cur_params.dot11MeshMaxRetries);
2613 NLA_PUT_U8(msg, NL80211_MESHCONF_TTL,
2614 cur_params.dot11MeshTTL);
2615 NLA_PUT_U8(msg, NL80211_MESHCONF_AUTO_OPEN_PLINKS,
2616 cur_params.auto_open_plinks);
2617 NLA_PUT_U8(msg, NL80211_MESHCONF_HWMP_MAX_PREQ_RETRIES,
2618 cur_params.dot11MeshHWMPmaxPREQretries);
2619 NLA_PUT_U32(msg, NL80211_MESHCONF_PATH_REFRESH_TIME,
2620 cur_params.path_refresh_time);
2621 NLA_PUT_U16(msg, NL80211_MESHCONF_MIN_DISCOVERY_TIMEOUT,
2622 cur_params.min_discovery_timeout);
2623 NLA_PUT_U32(msg, NL80211_MESHCONF_HWMP_ACTIVE_PATH_TIMEOUT,
2624 cur_params.dot11MeshHWMPactivePathTimeout);
2625 NLA_PUT_U16(msg, NL80211_MESHCONF_HWMP_PREQ_MIN_INTERVAL,
2626 cur_params.dot11MeshHWMPpreqMinInterval);
2627 NLA_PUT_U16(msg, NL80211_MESHCONF_HWMP_NET_DIAM_TRVS_TIME,
2628 cur_params.dot11MeshHWMPnetDiameterTraversalTime);
63c5723b
RP
2629 NLA_PUT_U8(msg, NL80211_MESHCONF_HWMP_ROOTMODE,
2630 cur_params.dot11MeshHWMPRootMode);
93da9cc1 2631 nla_nest_end(msg, pinfoattr);
2632 genlmsg_end(msg, hdr);
134e6375 2633 err = genlmsg_reply(msg, info);
93da9cc1 2634 goto out;
2635
3b85875a 2636 nla_put_failure:
93da9cc1 2637 genlmsg_cancel(msg, hdr);
2638 err = -EMSGSIZE;
3b85875a 2639 out:
93da9cc1 2640 /* Cleanup */
79c97e97 2641 cfg80211_unlock_rdev(rdev);
93da9cc1 2642 dev_put(dev);
3b85875a
JB
2643 out_rtnl:
2644 rtnl_unlock();
2645
93da9cc1 2646 return err;
2647}
2648
2649#define FILL_IN_MESH_PARAM_IF_SET(table, cfg, param, mask, attr_num, nla_fn) \
2650do {\
2651 if (table[attr_num]) {\
2652 cfg.param = nla_fn(table[attr_num]); \
2653 mask |= (1 << (attr_num - 1)); \
2654 } \
2655} while (0);\
2656
b54452b0 2657static const struct nla_policy nl80211_meshconf_params_policy[NL80211_MESHCONF_ATTR_MAX+1] = {
93da9cc1 2658 [NL80211_MESHCONF_RETRY_TIMEOUT] = { .type = NLA_U16 },
2659 [NL80211_MESHCONF_CONFIRM_TIMEOUT] = { .type = NLA_U16 },
2660 [NL80211_MESHCONF_HOLDING_TIMEOUT] = { .type = NLA_U16 },
2661 [NL80211_MESHCONF_MAX_PEER_LINKS] = { .type = NLA_U16 },
2662 [NL80211_MESHCONF_MAX_RETRIES] = { .type = NLA_U8 },
2663 [NL80211_MESHCONF_TTL] = { .type = NLA_U8 },
2664 [NL80211_MESHCONF_AUTO_OPEN_PLINKS] = { .type = NLA_U8 },
2665
2666 [NL80211_MESHCONF_HWMP_MAX_PREQ_RETRIES] = { .type = NLA_U8 },
2667 [NL80211_MESHCONF_PATH_REFRESH_TIME] = { .type = NLA_U32 },
2668 [NL80211_MESHCONF_MIN_DISCOVERY_TIMEOUT] = { .type = NLA_U16 },
2669 [NL80211_MESHCONF_HWMP_ACTIVE_PATH_TIMEOUT] = { .type = NLA_U32 },
2670 [NL80211_MESHCONF_HWMP_PREQ_MIN_INTERVAL] = { .type = NLA_U16 },
2671 [NL80211_MESHCONF_HWMP_NET_DIAM_TRVS_TIME] = { .type = NLA_U16 },
2672};
2673
2674static int nl80211_set_mesh_params(struct sk_buff *skb, struct genl_info *info)
2675{
2676 int err;
2677 u32 mask;
79c97e97 2678 struct cfg80211_registered_device *rdev;
93da9cc1 2679 struct net_device *dev;
2680 struct mesh_config cfg;
2681 struct nlattr *tb[NL80211_MESHCONF_ATTR_MAX + 1];
2682 struct nlattr *parent_attr;
2683
2684 parent_attr = info->attrs[NL80211_ATTR_MESH_PARAMS];
2685 if (!parent_attr)
2686 return -EINVAL;
2687 if (nla_parse_nested(tb, NL80211_MESHCONF_ATTR_MAX,
2688 parent_attr, nl80211_meshconf_params_policy))
2689 return -EINVAL;
2690
3b85875a
JB
2691 rtnl_lock();
2692
463d0183 2693 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
93da9cc1 2694 if (err)
3b85875a 2695 goto out_rtnl;
93da9cc1 2696
79c97e97 2697 if (!rdev->ops->set_mesh_params) {
f3f92586
JM
2698 err = -EOPNOTSUPP;
2699 goto out;
2700 }
2701
93da9cc1 2702 /* This makes sure that there aren't more than 32 mesh config
2703 * parameters (otherwise our bitfield scheme would not work.) */
2704 BUILD_BUG_ON(NL80211_MESHCONF_ATTR_MAX > 32);
2705
2706 /* Fill in the params struct */
2707 mask = 0;
2708 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, dot11MeshRetryTimeout,
2709 mask, NL80211_MESHCONF_RETRY_TIMEOUT, nla_get_u16);
2710 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, dot11MeshConfirmTimeout,
2711 mask, NL80211_MESHCONF_CONFIRM_TIMEOUT, nla_get_u16);
2712 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, dot11MeshHoldingTimeout,
2713 mask, NL80211_MESHCONF_HOLDING_TIMEOUT, nla_get_u16);
2714 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, dot11MeshMaxPeerLinks,
2715 mask, NL80211_MESHCONF_MAX_PEER_LINKS, nla_get_u16);
2716 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, dot11MeshMaxRetries,
2717 mask, NL80211_MESHCONF_MAX_RETRIES, nla_get_u8);
2718 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, dot11MeshTTL,
2719 mask, NL80211_MESHCONF_TTL, nla_get_u8);
2720 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, auto_open_plinks,
2721 mask, NL80211_MESHCONF_AUTO_OPEN_PLINKS, nla_get_u8);
2722 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, dot11MeshHWMPmaxPREQretries,
2723 mask, NL80211_MESHCONF_HWMP_MAX_PREQ_RETRIES,
2724 nla_get_u8);
2725 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, path_refresh_time,
2726 mask, NL80211_MESHCONF_PATH_REFRESH_TIME, nla_get_u32);
2727 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, min_discovery_timeout,
2728 mask, NL80211_MESHCONF_MIN_DISCOVERY_TIMEOUT,
2729 nla_get_u16);
2730 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, dot11MeshHWMPactivePathTimeout,
2731 mask, NL80211_MESHCONF_HWMP_ACTIVE_PATH_TIMEOUT,
2732 nla_get_u32);
2733 FILL_IN_MESH_PARAM_IF_SET(tb, cfg, dot11MeshHWMPpreqMinInterval,
2734 mask, NL80211_MESHCONF_HWMP_PREQ_MIN_INTERVAL,
2735 nla_get_u16);
2736 FILL_IN_MESH_PARAM_IF_SET(tb, cfg,
2737 dot11MeshHWMPnetDiameterTraversalTime,
2738 mask, NL80211_MESHCONF_HWMP_NET_DIAM_TRVS_TIME,
2739 nla_get_u16);
63c5723b
RP
2740 FILL_IN_MESH_PARAM_IF_SET(tb, cfg,
2741 dot11MeshHWMPRootMode, mask,
2742 NL80211_MESHCONF_HWMP_ROOTMODE,
2743 nla_get_u8);
93da9cc1 2744
2745 /* Apply changes */
79c97e97 2746 err = rdev->ops->set_mesh_params(&rdev->wiphy, dev, &cfg, mask);
93da9cc1 2747
f3f92586 2748 out:
93da9cc1 2749 /* cleanup */
79c97e97 2750 cfg80211_unlock_rdev(rdev);
93da9cc1 2751 dev_put(dev);
3b85875a
JB
2752 out_rtnl:
2753 rtnl_unlock();
2754
93da9cc1 2755 return err;
2756}
2757
2758#undef FILL_IN_MESH_PARAM_IF_SET
2759
f130347c
LR
2760static int nl80211_get_reg(struct sk_buff *skb, struct genl_info *info)
2761{
2762 struct sk_buff *msg;
2763 void *hdr = NULL;
2764 struct nlattr *nl_reg_rules;
2765 unsigned int i;
2766 int err = -EINVAL;
2767
a1794390 2768 mutex_lock(&cfg80211_mutex);
f130347c
LR
2769
2770 if (!cfg80211_regdomain)
2771 goto out;
2772
fd2120ca 2773 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
f130347c
LR
2774 if (!msg) {
2775 err = -ENOBUFS;
2776 goto out;
2777 }
2778
2779 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0,
2780 NL80211_CMD_GET_REG);
2781 if (!hdr)
2782 goto nla_put_failure;
2783
2784 NLA_PUT_STRING(msg, NL80211_ATTR_REG_ALPHA2,
2785 cfg80211_regdomain->alpha2);
2786
2787 nl_reg_rules = nla_nest_start(msg, NL80211_ATTR_REG_RULES);
2788 if (!nl_reg_rules)
2789 goto nla_put_failure;
2790
2791 for (i = 0; i < cfg80211_regdomain->n_reg_rules; i++) {
2792 struct nlattr *nl_reg_rule;
2793 const struct ieee80211_reg_rule *reg_rule;
2794 const struct ieee80211_freq_range *freq_range;
2795 const struct ieee80211_power_rule *power_rule;
2796
2797 reg_rule = &cfg80211_regdomain->reg_rules[i];
2798 freq_range = &reg_rule->freq_range;
2799 power_rule = &reg_rule->power_rule;
2800
2801 nl_reg_rule = nla_nest_start(msg, i);
2802 if (!nl_reg_rule)
2803 goto nla_put_failure;
2804
2805 NLA_PUT_U32(msg, NL80211_ATTR_REG_RULE_FLAGS,
2806 reg_rule->flags);
2807 NLA_PUT_U32(msg, NL80211_ATTR_FREQ_RANGE_START,
2808 freq_range->start_freq_khz);
2809 NLA_PUT_U32(msg, NL80211_ATTR_FREQ_RANGE_END,
2810 freq_range->end_freq_khz);
2811 NLA_PUT_U32(msg, NL80211_ATTR_FREQ_RANGE_MAX_BW,
2812 freq_range->max_bandwidth_khz);
2813 NLA_PUT_U32(msg, NL80211_ATTR_POWER_RULE_MAX_ANT_GAIN,
2814 power_rule->max_antenna_gain);
2815 NLA_PUT_U32(msg, NL80211_ATTR_POWER_RULE_MAX_EIRP,
2816 power_rule->max_eirp);
2817
2818 nla_nest_end(msg, nl_reg_rule);
2819 }
2820
2821 nla_nest_end(msg, nl_reg_rules);
2822
2823 genlmsg_end(msg, hdr);
134e6375 2824 err = genlmsg_reply(msg, info);
f130347c
LR
2825 goto out;
2826
2827nla_put_failure:
2828 genlmsg_cancel(msg, hdr);
2829 err = -EMSGSIZE;
2830out:
a1794390 2831 mutex_unlock(&cfg80211_mutex);
f130347c
LR
2832 return err;
2833}
2834
b2e1b302
LR
2835static int nl80211_set_reg(struct sk_buff *skb, struct genl_info *info)
2836{
2837 struct nlattr *tb[NL80211_REG_RULE_ATTR_MAX + 1];
2838 struct nlattr *nl_reg_rule;
2839 char *alpha2 = NULL;
2840 int rem_reg_rules = 0, r = 0;
2841 u32 num_rules = 0, rule_idx = 0, size_of_regd;
2842 struct ieee80211_regdomain *rd = NULL;
2843
2844 if (!info->attrs[NL80211_ATTR_REG_ALPHA2])
2845 return -EINVAL;
2846
2847 if (!info->attrs[NL80211_ATTR_REG_RULES])
2848 return -EINVAL;
2849
2850 alpha2 = nla_data(info->attrs[NL80211_ATTR_REG_ALPHA2]);
2851
2852 nla_for_each_nested(nl_reg_rule, info->attrs[NL80211_ATTR_REG_RULES],
2853 rem_reg_rules) {
2854 num_rules++;
2855 if (num_rules > NL80211_MAX_SUPP_REG_RULES)
4776c6e7 2856 return -EINVAL;
b2e1b302
LR
2857 }
2858
61405e97
LR
2859 mutex_lock(&cfg80211_mutex);
2860
d0e18f83
LR
2861 if (!reg_is_valid_request(alpha2)) {
2862 r = -EINVAL;
2863 goto bad_reg;
2864 }
b2e1b302
LR
2865
2866 size_of_regd = sizeof(struct ieee80211_regdomain) +
2867 (num_rules * sizeof(struct ieee80211_reg_rule));
2868
2869 rd = kzalloc(size_of_regd, GFP_KERNEL);
d0e18f83
LR
2870 if (!rd) {
2871 r = -ENOMEM;
2872 goto bad_reg;
2873 }
b2e1b302
LR
2874
2875 rd->n_reg_rules = num_rules;
2876 rd->alpha2[0] = alpha2[0];
2877 rd->alpha2[1] = alpha2[1];
2878
2879 nla_for_each_nested(nl_reg_rule, info->attrs[NL80211_ATTR_REG_RULES],
2880 rem_reg_rules) {
2881 nla_parse(tb, NL80211_REG_RULE_ATTR_MAX,
2882 nla_data(nl_reg_rule), nla_len(nl_reg_rule),
2883 reg_rule_policy);
2884 r = parse_reg_rule(tb, &rd->reg_rules[rule_idx]);
2885 if (r)
2886 goto bad_reg;
2887
2888 rule_idx++;
2889
d0e18f83
LR
2890 if (rule_idx > NL80211_MAX_SUPP_REG_RULES) {
2891 r = -EINVAL;
b2e1b302 2892 goto bad_reg;
d0e18f83 2893 }
b2e1b302
LR
2894 }
2895
2896 BUG_ON(rule_idx != num_rules);
2897
b2e1b302 2898 r = set_regdom(rd);
61405e97 2899
a1794390 2900 mutex_unlock(&cfg80211_mutex);
d0e18f83 2901
b2e1b302
LR
2902 return r;
2903
d2372b31 2904 bad_reg:
61405e97 2905 mutex_unlock(&cfg80211_mutex);
b2e1b302 2906 kfree(rd);
d0e18f83 2907 return r;
b2e1b302
LR
2908}
2909
83f5e2cf
JB
2910static int validate_scan_freqs(struct nlattr *freqs)
2911{
2912 struct nlattr *attr1, *attr2;
2913 int n_channels = 0, tmp1, tmp2;
2914
2915 nla_for_each_nested(attr1, freqs, tmp1) {
2916 n_channels++;
2917 /*
2918 * Some hardware has a limited channel list for
2919 * scanning, and it is pretty much nonsensical
2920 * to scan for a channel twice, so disallow that
2921 * and don't require drivers to check that the
2922 * channel list they get isn't longer than what
2923 * they can scan, as long as they can scan all
2924 * the channels they registered at once.
2925 */
2926 nla_for_each_nested(attr2, freqs, tmp2)
2927 if (attr1 != attr2 &&
2928 nla_get_u32(attr1) == nla_get_u32(attr2))
2929 return 0;
2930 }
2931
2932 return n_channels;
2933}
2934
2a519311
JB
2935static int nl80211_trigger_scan(struct sk_buff *skb, struct genl_info *info)
2936{
79c97e97 2937 struct cfg80211_registered_device *rdev;
2a519311
JB
2938 struct net_device *dev;
2939 struct cfg80211_scan_request *request;
2940 struct cfg80211_ssid *ssid;
2941 struct ieee80211_channel *channel;
2942 struct nlattr *attr;
2943 struct wiphy *wiphy;
83f5e2cf 2944 int err, tmp, n_ssids = 0, n_channels, i;
2a519311 2945 enum ieee80211_band band;
70692ad2 2946 size_t ie_len;
2a519311 2947
f4a11bb0
JB
2948 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_IE]))
2949 return -EINVAL;
2950
3b85875a
JB
2951 rtnl_lock();
2952
463d0183 2953 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2a519311 2954 if (err)
3b85875a 2955 goto out_rtnl;
2a519311 2956
79c97e97 2957 wiphy = &rdev->wiphy;
2a519311 2958
79c97e97 2959 if (!rdev->ops->scan) {
2a519311
JB
2960 err = -EOPNOTSUPP;
2961 goto out;
2962 }
2963
35a8efe1
JM
2964 if (!netif_running(dev)) {
2965 err = -ENETDOWN;
2966 goto out;
2967 }
2968
79c97e97 2969 if (rdev->scan_req) {
2a519311 2970 err = -EBUSY;
3b85875a 2971 goto out;
2a519311
JB
2972 }
2973
2974 if (info->attrs[NL80211_ATTR_SCAN_FREQUENCIES]) {
83f5e2cf
JB
2975 n_channels = validate_scan_freqs(
2976 info->attrs[NL80211_ATTR_SCAN_FREQUENCIES]);
2a519311
JB
2977 if (!n_channels) {
2978 err = -EINVAL;
3b85875a 2979 goto out;
2a519311
JB
2980 }
2981 } else {
83f5e2cf
JB
2982 n_channels = 0;
2983
2a519311
JB
2984 for (band = 0; band < IEEE80211_NUM_BANDS; band++)
2985 if (wiphy->bands[band])
2986 n_channels += wiphy->bands[band]->n_channels;
2987 }
2988
2989 if (info->attrs[NL80211_ATTR_SCAN_SSIDS])
2990 nla_for_each_nested(attr, info->attrs[NL80211_ATTR_SCAN_SSIDS], tmp)
2991 n_ssids++;
2992
2993 if (n_ssids > wiphy->max_scan_ssids) {
2994 err = -EINVAL;
3b85875a 2995 goto out;
2a519311
JB
2996 }
2997
70692ad2
JM
2998 if (info->attrs[NL80211_ATTR_IE])
2999 ie_len = nla_len(info->attrs[NL80211_ATTR_IE]);
3000 else
3001 ie_len = 0;
3002
18a83659
JB
3003 if (ie_len > wiphy->max_scan_ie_len) {
3004 err = -EINVAL;
3005 goto out;
3006 }
3007
2a519311
JB
3008 request = kzalloc(sizeof(*request)
3009 + sizeof(*ssid) * n_ssids
70692ad2
JM
3010 + sizeof(channel) * n_channels
3011 + ie_len, GFP_KERNEL);
2a519311
JB
3012 if (!request) {
3013 err = -ENOMEM;
3b85875a 3014 goto out;
2a519311
JB
3015 }
3016
2a519311 3017 if (n_ssids)
5ba63533 3018 request->ssids = (void *)&request->channels[n_channels];
2a519311 3019 request->n_ssids = n_ssids;
70692ad2
JM
3020 if (ie_len) {
3021 if (request->ssids)
3022 request->ie = (void *)(request->ssids + n_ssids);
3023 else
3024 request->ie = (void *)(request->channels + n_channels);
3025 }
2a519311 3026
584991dc 3027 i = 0;
2a519311
JB
3028 if (info->attrs[NL80211_ATTR_SCAN_FREQUENCIES]) {
3029 /* user specified, bail out if channel not found */
2a519311 3030 nla_for_each_nested(attr, info->attrs[NL80211_ATTR_SCAN_FREQUENCIES], tmp) {
584991dc
JB
3031 struct ieee80211_channel *chan;
3032
3033 chan = ieee80211_get_channel(wiphy, nla_get_u32(attr));
3034
3035 if (!chan) {
2a519311
JB
3036 err = -EINVAL;
3037 goto out_free;
3038 }
584991dc
JB
3039
3040 /* ignore disabled channels */
3041 if (chan->flags & IEEE80211_CHAN_DISABLED)
3042 continue;
3043
3044 request->channels[i] = chan;
2a519311
JB
3045 i++;
3046 }
3047 } else {
3048 /* all channels */
2a519311
JB
3049 for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
3050 int j;
3051 if (!wiphy->bands[band])
3052 continue;
3053 for (j = 0; j < wiphy->bands[band]->n_channels; j++) {
584991dc
JB
3054 struct ieee80211_channel *chan;
3055
3056 chan = &wiphy->bands[band]->channels[j];
3057
3058 if (chan->flags & IEEE80211_CHAN_DISABLED)
3059 continue;
3060
3061 request->channels[i] = chan;
2a519311
JB
3062 i++;
3063 }
3064 }
3065 }
3066
584991dc
JB
3067 if (!i) {
3068 err = -EINVAL;
3069 goto out_free;
3070 }
3071
3072 request->n_channels = i;
3073
2a519311
JB
3074 i = 0;
3075 if (info->attrs[NL80211_ATTR_SCAN_SSIDS]) {
3076 nla_for_each_nested(attr, info->attrs[NL80211_ATTR_SCAN_SSIDS], tmp) {
3077 if (request->ssids[i].ssid_len > IEEE80211_MAX_SSID_LEN) {
3078 err = -EINVAL;
3079 goto out_free;
3080 }
3081 memcpy(request->ssids[i].ssid, nla_data(attr), nla_len(attr));
3082 request->ssids[i].ssid_len = nla_len(attr);
3083 i++;
3084 }
3085 }
3086
70692ad2
JM
3087 if (info->attrs[NL80211_ATTR_IE]) {
3088 request->ie_len = nla_len(info->attrs[NL80211_ATTR_IE]);
de95a54b
JB
3089 memcpy((void *)request->ie,
3090 nla_data(info->attrs[NL80211_ATTR_IE]),
70692ad2
JM
3091 request->ie_len);
3092 }
3093
463d0183 3094 request->dev = dev;
79c97e97 3095 request->wiphy = &rdev->wiphy;
2a519311 3096
79c97e97
JB
3097 rdev->scan_req = request;
3098 err = rdev->ops->scan(&rdev->wiphy, dev, request);
2a519311 3099
463d0183 3100 if (!err) {
79c97e97 3101 nl80211_send_scan_start(rdev, dev);
463d0183
JB
3102 dev_hold(dev);
3103 }
a538e2d5 3104
2a519311
JB
3105 out_free:
3106 if (err) {
79c97e97 3107 rdev->scan_req = NULL;
2a519311
JB
3108 kfree(request);
3109 }
2a519311 3110 out:
79c97e97 3111 cfg80211_unlock_rdev(rdev);
2a519311 3112 dev_put(dev);
3b85875a
JB
3113 out_rtnl:
3114 rtnl_unlock();
3115
2a519311
JB
3116 return err;
3117}
3118
3119static int nl80211_send_bss(struct sk_buff *msg, u32 pid, u32 seq, int flags,
3120 struct cfg80211_registered_device *rdev,
48ab905d
JB
3121 struct wireless_dev *wdev,
3122 struct cfg80211_internal_bss *intbss)
2a519311 3123{
48ab905d 3124 struct cfg80211_bss *res = &intbss->pub;
2a519311
JB
3125 void *hdr;
3126 struct nlattr *bss;
48ab905d
JB
3127 int i;
3128
3129 ASSERT_WDEV_LOCK(wdev);
2a519311
JB
3130
3131 hdr = nl80211hdr_put(msg, pid, seq, flags,
3132 NL80211_CMD_NEW_SCAN_RESULTS);
3133 if (!hdr)
3134 return -1;
3135
f5ea9120 3136 NLA_PUT_U32(msg, NL80211_ATTR_GENERATION, rdev->bss_generation);
48ab905d 3137 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, wdev->netdev->ifindex);
2a519311
JB
3138
3139 bss = nla_nest_start(msg, NL80211_ATTR_BSS);
3140 if (!bss)
3141 goto nla_put_failure;
3142 if (!is_zero_ether_addr(res->bssid))
3143 NLA_PUT(msg, NL80211_BSS_BSSID, ETH_ALEN, res->bssid);
3144 if (res->information_elements && res->len_information_elements)
3145 NLA_PUT(msg, NL80211_BSS_INFORMATION_ELEMENTS,
3146 res->len_information_elements,
3147 res->information_elements);
34a6eddb
JM
3148 if (res->beacon_ies && res->len_beacon_ies &&
3149 res->beacon_ies != res->information_elements)
3150 NLA_PUT(msg, NL80211_BSS_BEACON_IES,
3151 res->len_beacon_ies, res->beacon_ies);
2a519311
JB
3152 if (res->tsf)
3153 NLA_PUT_U64(msg, NL80211_BSS_TSF, res->tsf);
3154 if (res->beacon_interval)
3155 NLA_PUT_U16(msg, NL80211_BSS_BEACON_INTERVAL, res->beacon_interval);
3156 NLA_PUT_U16(msg, NL80211_BSS_CAPABILITY, res->capability);
3157 NLA_PUT_U32(msg, NL80211_BSS_FREQUENCY, res->channel->center_freq);
7c89606e
HS
3158 NLA_PUT_U32(msg, NL80211_BSS_SEEN_MS_AGO,
3159 jiffies_to_msecs(jiffies - intbss->ts));
2a519311 3160
77965c97 3161 switch (rdev->wiphy.signal_type) {
2a519311
JB
3162 case CFG80211_SIGNAL_TYPE_MBM:
3163 NLA_PUT_U32(msg, NL80211_BSS_SIGNAL_MBM, res->signal);
3164 break;
3165 case CFG80211_SIGNAL_TYPE_UNSPEC:
3166 NLA_PUT_U8(msg, NL80211_BSS_SIGNAL_UNSPEC, res->signal);
3167 break;
3168 default:
3169 break;
3170 }
3171
48ab905d
JB
3172 switch (wdev->iftype) {
3173 case NL80211_IFTYPE_STATION:
3174 if (intbss == wdev->current_bss)
3175 NLA_PUT_U32(msg, NL80211_BSS_STATUS,
3176 NL80211_BSS_STATUS_ASSOCIATED);
3177 else for (i = 0; i < MAX_AUTH_BSSES; i++) {
3178 if (intbss != wdev->auth_bsses[i])
3179 continue;
3180 NLA_PUT_U32(msg, NL80211_BSS_STATUS,
3181 NL80211_BSS_STATUS_AUTHENTICATED);
3182 break;
3183 }
3184 break;
3185 case NL80211_IFTYPE_ADHOC:
3186 if (intbss == wdev->current_bss)
3187 NLA_PUT_U32(msg, NL80211_BSS_STATUS,
3188 NL80211_BSS_STATUS_IBSS_JOINED);
3189 break;
3190 default:
3191 break;
3192 }
3193
2a519311
JB
3194 nla_nest_end(msg, bss);
3195
3196 return genlmsg_end(msg, hdr);
3197
3198 nla_put_failure:
3199 genlmsg_cancel(msg, hdr);
3200 return -EMSGSIZE;
3201}
3202
3203static int nl80211_dump_scan(struct sk_buff *skb,
3204 struct netlink_callback *cb)
3205{
48ab905d
JB
3206 struct cfg80211_registered_device *rdev;
3207 struct net_device *dev;
2a519311 3208 struct cfg80211_internal_bss *scan;
48ab905d 3209 struct wireless_dev *wdev;
2a519311
JB
3210 int ifidx = cb->args[0];
3211 int start = cb->args[1], idx = 0;
3212 int err;
3213
a043897a
HS
3214 if (!ifidx)
3215 ifidx = nl80211_get_ifidx(cb);
3216 if (ifidx < 0)
3217 return ifidx;
3218 cb->args[0] = ifidx;
2a519311 3219
463d0183 3220 dev = dev_get_by_index(sock_net(skb->sk), ifidx);
48ab905d 3221 if (!dev)
2a519311
JB
3222 return -ENODEV;
3223
463d0183 3224 rdev = cfg80211_get_dev_from_ifindex(sock_net(skb->sk), ifidx);
48ab905d
JB
3225 if (IS_ERR(rdev)) {
3226 err = PTR_ERR(rdev);
2a519311
JB
3227 goto out_put_netdev;
3228 }
3229
48ab905d 3230 wdev = dev->ieee80211_ptr;
2a519311 3231
48ab905d
JB
3232 wdev_lock(wdev);
3233 spin_lock_bh(&rdev->bss_lock);
3234 cfg80211_bss_expire(rdev);
3235
3236 list_for_each_entry(scan, &rdev->bss_list, list) {
2a519311
JB
3237 if (++idx <= start)
3238 continue;
3239 if (nl80211_send_bss(skb,
3240 NETLINK_CB(cb->skb).pid,
3241 cb->nlh->nlmsg_seq, NLM_F_MULTI,
48ab905d 3242 rdev, wdev, scan) < 0) {
2a519311
JB
3243 idx--;
3244 goto out;
3245 }
3246 }
3247
3248 out:
48ab905d
JB
3249 spin_unlock_bh(&rdev->bss_lock);
3250 wdev_unlock(wdev);
2a519311
JB
3251
3252 cb->args[1] = idx;
3253 err = skb->len;
48ab905d 3254 cfg80211_unlock_rdev(rdev);
2a519311 3255 out_put_netdev:
48ab905d 3256 dev_put(dev);
2a519311
JB
3257
3258 return err;
3259}
3260
61fa713c
HS
3261static int nl80211_send_survey(struct sk_buff *msg, u32 pid, u32 seq,
3262 int flags, struct net_device *dev,
3263 struct survey_info *survey)
3264{
3265 void *hdr;
3266 struct nlattr *infoattr;
3267
3268 /* Survey without a channel doesn't make sense */
3269 if (!survey->channel)
3270 return -EINVAL;
3271
3272 hdr = nl80211hdr_put(msg, pid, seq, flags,
3273 NL80211_CMD_NEW_SURVEY_RESULTS);
3274 if (!hdr)
3275 return -ENOMEM;
3276
3277 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, dev->ifindex);
3278
3279 infoattr = nla_nest_start(msg, NL80211_ATTR_SURVEY_INFO);
3280 if (!infoattr)
3281 goto nla_put_failure;
3282
3283 NLA_PUT_U32(msg, NL80211_SURVEY_INFO_FREQUENCY,
3284 survey->channel->center_freq);
3285 if (survey->filled & SURVEY_INFO_NOISE_DBM)
3286 NLA_PUT_U8(msg, NL80211_SURVEY_INFO_NOISE,
3287 survey->noise);
3288
3289 nla_nest_end(msg, infoattr);
3290
3291 return genlmsg_end(msg, hdr);
3292
3293 nla_put_failure:
3294 genlmsg_cancel(msg, hdr);
3295 return -EMSGSIZE;
3296}
3297
3298static int nl80211_dump_survey(struct sk_buff *skb,
3299 struct netlink_callback *cb)
3300{
3301 struct survey_info survey;
3302 struct cfg80211_registered_device *dev;
3303 struct net_device *netdev;
3304 int ifidx = cb->args[0];
3305 int survey_idx = cb->args[1];
3306 int res;
3307
3308 if (!ifidx)
3309 ifidx = nl80211_get_ifidx(cb);
3310 if (ifidx < 0)
3311 return ifidx;
3312 cb->args[0] = ifidx;
3313
3314 rtnl_lock();
3315
3316 netdev = __dev_get_by_index(sock_net(skb->sk), ifidx);
3317 if (!netdev) {
3318 res = -ENODEV;
3319 goto out_rtnl;
3320 }
3321
3322 dev = cfg80211_get_dev_from_ifindex(sock_net(skb->sk), ifidx);
3323 if (IS_ERR(dev)) {
3324 res = PTR_ERR(dev);
3325 goto out_rtnl;
3326 }
3327
3328 if (!dev->ops->dump_survey) {
3329 res = -EOPNOTSUPP;
3330 goto out_err;
3331 }
3332
3333 while (1) {
3334 res = dev->ops->dump_survey(&dev->wiphy, netdev, survey_idx,
3335 &survey);
3336 if (res == -ENOENT)
3337 break;
3338 if (res)
3339 goto out_err;
3340
3341 if (nl80211_send_survey(skb,
3342 NETLINK_CB(cb->skb).pid,
3343 cb->nlh->nlmsg_seq, NLM_F_MULTI,
3344 netdev,
3345 &survey) < 0)
3346 goto out;
3347 survey_idx++;
3348 }
3349
3350 out:
3351 cb->args[1] = survey_idx;
3352 res = skb->len;
3353 out_err:
3354 cfg80211_unlock_rdev(dev);
3355 out_rtnl:
3356 rtnl_unlock();
3357
3358 return res;
3359}
3360
255e737e
JM
3361static bool nl80211_valid_auth_type(enum nl80211_auth_type auth_type)
3362{
b23aa676
SO
3363 return auth_type <= NL80211_AUTHTYPE_MAX;
3364}
3365
3366static bool nl80211_valid_wpa_versions(u32 wpa_versions)
3367{
3368 return !(wpa_versions & ~(NL80211_WPA_VERSION_1 |
3369 NL80211_WPA_VERSION_2));
3370}
3371
3372static bool nl80211_valid_akm_suite(u32 akm)
3373{
3374 return akm == WLAN_AKM_SUITE_8021X ||
3375 akm == WLAN_AKM_SUITE_PSK;
3376}
3377
3378static bool nl80211_valid_cipher_suite(u32 cipher)
3379{
3380 return cipher == WLAN_CIPHER_SUITE_WEP40 ||
3381 cipher == WLAN_CIPHER_SUITE_WEP104 ||
3382 cipher == WLAN_CIPHER_SUITE_TKIP ||
3383 cipher == WLAN_CIPHER_SUITE_CCMP ||
3384 cipher == WLAN_CIPHER_SUITE_AES_CMAC;
255e737e
JM
3385}
3386
b23aa676 3387
636a5d36
JM
3388static int nl80211_authenticate(struct sk_buff *skb, struct genl_info *info)
3389{
79c97e97 3390 struct cfg80211_registered_device *rdev;
636a5d36 3391 struct net_device *dev;
19957bb3
JB
3392 struct ieee80211_channel *chan;
3393 const u8 *bssid, *ssid, *ie = NULL;
3394 int err, ssid_len, ie_len = 0;
3395 enum nl80211_auth_type auth_type;
fffd0934 3396 struct key_parse key;
d5cdfacb 3397 bool local_state_change;
636a5d36 3398
f4a11bb0
JB
3399 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_IE]))
3400 return -EINVAL;
3401
3402 if (!info->attrs[NL80211_ATTR_MAC])
3403 return -EINVAL;
3404
1778092e
JM
3405 if (!info->attrs[NL80211_ATTR_AUTH_TYPE])
3406 return -EINVAL;
3407
19957bb3
JB
3408 if (!info->attrs[NL80211_ATTR_SSID])
3409 return -EINVAL;
3410
3411 if (!info->attrs[NL80211_ATTR_WIPHY_FREQ])
3412 return -EINVAL;
3413
fffd0934
JB
3414 err = nl80211_parse_key(info, &key);
3415 if (err)
3416 return err;
3417
3418 if (key.idx >= 0) {
3419 if (!key.p.key || !key.p.key_len)
3420 return -EINVAL;
3421 if ((key.p.cipher != WLAN_CIPHER_SUITE_WEP40 ||
3422 key.p.key_len != WLAN_KEY_LEN_WEP40) &&
3423 (key.p.cipher != WLAN_CIPHER_SUITE_WEP104 ||
3424 key.p.key_len != WLAN_KEY_LEN_WEP104))
3425 return -EINVAL;
3426 if (key.idx > 4)
3427 return -EINVAL;
3428 } else {
3429 key.p.key_len = 0;
3430 key.p.key = NULL;
3431 }
3432
636a5d36
JM
3433 rtnl_lock();
3434
463d0183 3435 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
636a5d36
JM
3436 if (err)
3437 goto unlock_rtnl;
3438
79c97e97 3439 if (!rdev->ops->auth) {
636a5d36
JM
3440 err = -EOPNOTSUPP;
3441 goto out;
3442 }
3443
eec60b03
JM
3444 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
3445 err = -EOPNOTSUPP;
3446 goto out;
3447 }
3448
35a8efe1
JM
3449 if (!netif_running(dev)) {
3450 err = -ENETDOWN;
3451 goto out;
3452 }
3453
19957bb3 3454 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
79c97e97 3455 chan = ieee80211_get_channel(&rdev->wiphy,
19957bb3
JB
3456 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]));
3457 if (!chan || (chan->flags & IEEE80211_CHAN_DISABLED)) {
3458 err = -EINVAL;
3459 goto out;
636a5d36
JM
3460 }
3461
19957bb3
JB
3462 ssid = nla_data(info->attrs[NL80211_ATTR_SSID]);
3463 ssid_len = nla_len(info->attrs[NL80211_ATTR_SSID]);
636a5d36
JM
3464
3465 if (info->attrs[NL80211_ATTR_IE]) {
19957bb3
JB
3466 ie = nla_data(info->attrs[NL80211_ATTR_IE]);
3467 ie_len = nla_len(info->attrs[NL80211_ATTR_IE]);
636a5d36
JM
3468 }
3469
19957bb3
JB
3470 auth_type = nla_get_u32(info->attrs[NL80211_ATTR_AUTH_TYPE]);
3471 if (!nl80211_valid_auth_type(auth_type)) {
1778092e
JM
3472 err = -EINVAL;
3473 goto out;
636a5d36
JM
3474 }
3475
d5cdfacb
JM
3476 local_state_change = !!info->attrs[NL80211_ATTR_LOCAL_STATE_CHANGE];
3477
79c97e97 3478 err = cfg80211_mlme_auth(rdev, dev, chan, auth_type, bssid,
fffd0934 3479 ssid, ssid_len, ie, ie_len,
d5cdfacb
JM
3480 key.p.key, key.p.key_len, key.idx,
3481 local_state_change);
636a5d36
JM
3482
3483out:
79c97e97 3484 cfg80211_unlock_rdev(rdev);
636a5d36
JM
3485 dev_put(dev);
3486unlock_rtnl:
3487 rtnl_unlock();
3488 return err;
3489}
3490
b23aa676 3491static int nl80211_crypto_settings(struct genl_info *info,
3dc27d25
JB
3492 struct cfg80211_crypto_settings *settings,
3493 int cipher_limit)
b23aa676 3494{
c0b2bbd8
JB
3495 memset(settings, 0, sizeof(*settings));
3496
b23aa676
SO
3497 settings->control_port = info->attrs[NL80211_ATTR_CONTROL_PORT];
3498
3499 if (info->attrs[NL80211_ATTR_CIPHER_SUITES_PAIRWISE]) {
3500 void *data;
3501 int len, i;
3502
3503 data = nla_data(info->attrs[NL80211_ATTR_CIPHER_SUITES_PAIRWISE]);
3504 len = nla_len(info->attrs[NL80211_ATTR_CIPHER_SUITES_PAIRWISE]);
3505 settings->n_ciphers_pairwise = len / sizeof(u32);
3506
3507 if (len % sizeof(u32))
3508 return -EINVAL;
3509
3dc27d25 3510 if (settings->n_ciphers_pairwise > cipher_limit)
b23aa676
SO
3511 return -EINVAL;
3512
3513 memcpy(settings->ciphers_pairwise, data, len);
3514
3515 for (i = 0; i < settings->n_ciphers_pairwise; i++)
3516 if (!nl80211_valid_cipher_suite(
3517 settings->ciphers_pairwise[i]))
3518 return -EINVAL;
3519 }
3520
3521 if (info->attrs[NL80211_ATTR_CIPHER_SUITE_GROUP]) {
3522 settings->cipher_group =
3523 nla_get_u32(info->attrs[NL80211_ATTR_CIPHER_SUITE_GROUP]);
3524 if (!nl80211_valid_cipher_suite(settings->cipher_group))
3525 return -EINVAL;
3526 }
3527
3528 if (info->attrs[NL80211_ATTR_WPA_VERSIONS]) {
3529 settings->wpa_versions =
3530 nla_get_u32(info->attrs[NL80211_ATTR_WPA_VERSIONS]);
3531 if (!nl80211_valid_wpa_versions(settings->wpa_versions))
3532 return -EINVAL;
3533 }
3534
3535 if (info->attrs[NL80211_ATTR_AKM_SUITES]) {
3536 void *data;
3537 int len, i;
3538
3539 data = nla_data(info->attrs[NL80211_ATTR_AKM_SUITES]);
3540 len = nla_len(info->attrs[NL80211_ATTR_AKM_SUITES]);
3541 settings->n_akm_suites = len / sizeof(u32);
3542
3543 if (len % sizeof(u32))
3544 return -EINVAL;
3545
3546 memcpy(settings->akm_suites, data, len);
3547
3548 for (i = 0; i < settings->n_ciphers_pairwise; i++)
3549 if (!nl80211_valid_akm_suite(settings->akm_suites[i]))
3550 return -EINVAL;
3551 }
3552
3553 return 0;
3554}
3555
636a5d36
JM
3556static int nl80211_associate(struct sk_buff *skb, struct genl_info *info)
3557{
19957bb3 3558 struct cfg80211_registered_device *rdev;
636a5d36 3559 struct net_device *dev;
27e310c9 3560 struct wireless_dev *wdev;
19957bb3 3561 struct cfg80211_crypto_settings crypto;
59bbb6f7 3562 struct ieee80211_channel *chan, *fixedchan;
3e5d7649 3563 const u8 *bssid, *ssid, *ie = NULL, *prev_bssid = NULL;
19957bb3
JB
3564 int err, ssid_len, ie_len = 0;
3565 bool use_mfp = false;
636a5d36 3566
f4a11bb0
JB
3567 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_IE]))
3568 return -EINVAL;
3569
3570 if (!info->attrs[NL80211_ATTR_MAC] ||
19957bb3
JB
3571 !info->attrs[NL80211_ATTR_SSID] ||
3572 !info->attrs[NL80211_ATTR_WIPHY_FREQ])
f4a11bb0
JB
3573 return -EINVAL;
3574
636a5d36
JM
3575 rtnl_lock();
3576
463d0183 3577 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
636a5d36
JM
3578 if (err)
3579 goto unlock_rtnl;
3580
19957bb3 3581 if (!rdev->ops->assoc) {
636a5d36
JM
3582 err = -EOPNOTSUPP;
3583 goto out;
3584 }
3585
eec60b03
JM
3586 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
3587 err = -EOPNOTSUPP;
3588 goto out;
3589 }
3590
35a8efe1
JM
3591 if (!netif_running(dev)) {
3592 err = -ENETDOWN;
3593 goto out;
3594 }
3595
19957bb3 3596 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
636a5d36 3597
19957bb3
JB
3598 chan = ieee80211_get_channel(&rdev->wiphy,
3599 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]));
3600 if (!chan || (chan->flags & IEEE80211_CHAN_DISABLED)) {
3601 err = -EINVAL;
3602 goto out;
636a5d36
JM
3603 }
3604
59bbb6f7 3605 mutex_lock(&rdev->devlist_mtx);
27e310c9
JM
3606 wdev = dev->ieee80211_ptr;
3607 fixedchan = rdev_fixed_channel(rdev, wdev);
59bbb6f7
JB
3608 if (fixedchan && chan != fixedchan) {
3609 err = -EBUSY;
3610 mutex_unlock(&rdev->devlist_mtx);
3611 goto out;
3612 }
3613 mutex_unlock(&rdev->devlist_mtx);
3614
19957bb3
JB
3615 ssid = nla_data(info->attrs[NL80211_ATTR_SSID]);
3616 ssid_len = nla_len(info->attrs[NL80211_ATTR_SSID]);
636a5d36
JM
3617
3618 if (info->attrs[NL80211_ATTR_IE]) {
19957bb3
JB
3619 ie = nla_data(info->attrs[NL80211_ATTR_IE]);
3620 ie_len = nla_len(info->attrs[NL80211_ATTR_IE]);
636a5d36
JM
3621 }
3622
dc6382ce 3623 if (info->attrs[NL80211_ATTR_USE_MFP]) {
4f5dadce 3624 enum nl80211_mfp mfp =
dc6382ce 3625 nla_get_u32(info->attrs[NL80211_ATTR_USE_MFP]);
4f5dadce 3626 if (mfp == NL80211_MFP_REQUIRED)
19957bb3 3627 use_mfp = true;
4f5dadce 3628 else if (mfp != NL80211_MFP_NO) {
dc6382ce
JM
3629 err = -EINVAL;
3630 goto out;
3631 }
3632 }
3633
3e5d7649
JB
3634 if (info->attrs[NL80211_ATTR_PREV_BSSID])
3635 prev_bssid = nla_data(info->attrs[NL80211_ATTR_PREV_BSSID]);
3636
3dc27d25 3637 err = nl80211_crypto_settings(info, &crypto, 1);
b23aa676 3638 if (!err)
3e5d7649
JB
3639 err = cfg80211_mlme_assoc(rdev, dev, chan, bssid, prev_bssid,
3640 ssid, ssid_len, ie, ie_len, use_mfp,
19957bb3 3641 &crypto);
636a5d36
JM
3642
3643out:
4d0c8aea 3644 cfg80211_unlock_rdev(rdev);
636a5d36
JM
3645 dev_put(dev);
3646unlock_rtnl:
3647 rtnl_unlock();
3648 return err;
3649}
3650
3651static int nl80211_deauthenticate(struct sk_buff *skb, struct genl_info *info)
3652{
79c97e97 3653 struct cfg80211_registered_device *rdev;
636a5d36 3654 struct net_device *dev;
19957bb3
JB
3655 const u8 *ie = NULL, *bssid;
3656 int err, ie_len = 0;
3657 u16 reason_code;
d5cdfacb 3658 bool local_state_change;
636a5d36 3659
f4a11bb0
JB
3660 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_IE]))
3661 return -EINVAL;
3662
3663 if (!info->attrs[NL80211_ATTR_MAC])
3664 return -EINVAL;
3665
3666 if (!info->attrs[NL80211_ATTR_REASON_CODE])
3667 return -EINVAL;
3668
636a5d36
JM
3669 rtnl_lock();
3670
463d0183 3671 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
636a5d36
JM
3672 if (err)
3673 goto unlock_rtnl;
3674
79c97e97 3675 if (!rdev->ops->deauth) {
636a5d36
JM
3676 err = -EOPNOTSUPP;
3677 goto out;
3678 }
3679
eec60b03
JM
3680 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
3681 err = -EOPNOTSUPP;
3682 goto out;
3683 }
3684
35a8efe1
JM
3685 if (!netif_running(dev)) {
3686 err = -ENETDOWN;
3687 goto out;
3688 }
3689
19957bb3 3690 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
636a5d36 3691
19957bb3
JB
3692 reason_code = nla_get_u16(info->attrs[NL80211_ATTR_REASON_CODE]);
3693 if (reason_code == 0) {
f4a11bb0
JB
3694 /* Reason Code 0 is reserved */
3695 err = -EINVAL;
3696 goto out;
255e737e 3697 }
636a5d36
JM
3698
3699 if (info->attrs[NL80211_ATTR_IE]) {
19957bb3
JB
3700 ie = nla_data(info->attrs[NL80211_ATTR_IE]);
3701 ie_len = nla_len(info->attrs[NL80211_ATTR_IE]);
636a5d36
JM
3702 }
3703
d5cdfacb
JM
3704 local_state_change = !!info->attrs[NL80211_ATTR_LOCAL_STATE_CHANGE];
3705
3706 err = cfg80211_mlme_deauth(rdev, dev, bssid, ie, ie_len, reason_code,
3707 local_state_change);
636a5d36
JM
3708
3709out:
79c97e97 3710 cfg80211_unlock_rdev(rdev);
636a5d36
JM
3711 dev_put(dev);
3712unlock_rtnl:
3713 rtnl_unlock();
3714 return err;
3715}
3716
3717static int nl80211_disassociate(struct sk_buff *skb, struct genl_info *info)
3718{
79c97e97 3719 struct cfg80211_registered_device *rdev;
636a5d36 3720 struct net_device *dev;
19957bb3
JB
3721 const u8 *ie = NULL, *bssid;
3722 int err, ie_len = 0;
3723 u16 reason_code;
d5cdfacb 3724 bool local_state_change;
636a5d36 3725
f4a11bb0
JB
3726 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_IE]))
3727 return -EINVAL;
3728
3729 if (!info->attrs[NL80211_ATTR_MAC])
3730 return -EINVAL;
3731
3732 if (!info->attrs[NL80211_ATTR_REASON_CODE])
3733 return -EINVAL;
3734
636a5d36
JM
3735 rtnl_lock();
3736
463d0183 3737 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
636a5d36
JM
3738 if (err)
3739 goto unlock_rtnl;
3740
79c97e97 3741 if (!rdev->ops->disassoc) {
636a5d36
JM
3742 err = -EOPNOTSUPP;
3743 goto out;
3744 }
3745
eec60b03
JM
3746 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
3747 err = -EOPNOTSUPP;
3748 goto out;
3749 }
3750
35a8efe1
JM
3751 if (!netif_running(dev)) {
3752 err = -ENETDOWN;
3753 goto out;
3754 }
3755
19957bb3 3756 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
636a5d36 3757
19957bb3
JB
3758 reason_code = nla_get_u16(info->attrs[NL80211_ATTR_REASON_CODE]);
3759 if (reason_code == 0) {
f4a11bb0
JB
3760 /* Reason Code 0 is reserved */
3761 err = -EINVAL;
3762 goto out;
255e737e 3763 }
636a5d36
JM
3764
3765 if (info->attrs[NL80211_ATTR_IE]) {
19957bb3
JB
3766 ie = nla_data(info->attrs[NL80211_ATTR_IE]);
3767 ie_len = nla_len(info->attrs[NL80211_ATTR_IE]);
636a5d36
JM
3768 }
3769
d5cdfacb
JM
3770 local_state_change = !!info->attrs[NL80211_ATTR_LOCAL_STATE_CHANGE];
3771
3772 err = cfg80211_mlme_disassoc(rdev, dev, bssid, ie, ie_len, reason_code,
3773 local_state_change);
636a5d36
JM
3774
3775out:
79c97e97 3776 cfg80211_unlock_rdev(rdev);
636a5d36
JM
3777 dev_put(dev);
3778unlock_rtnl:
3779 rtnl_unlock();
3780 return err;
3781}
3782
04a773ad
JB
3783static int nl80211_join_ibss(struct sk_buff *skb, struct genl_info *info)
3784{
79c97e97 3785 struct cfg80211_registered_device *rdev;
04a773ad
JB
3786 struct net_device *dev;
3787 struct cfg80211_ibss_params ibss;
3788 struct wiphy *wiphy;
fffd0934 3789 struct cfg80211_cached_keys *connkeys = NULL;
04a773ad
JB
3790 int err;
3791
8e30bc55
JB
3792 memset(&ibss, 0, sizeof(ibss));
3793
04a773ad
JB
3794 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_IE]))
3795 return -EINVAL;
3796
3797 if (!info->attrs[NL80211_ATTR_WIPHY_FREQ] ||
3798 !info->attrs[NL80211_ATTR_SSID] ||
3799 !nla_len(info->attrs[NL80211_ATTR_SSID]))
3800 return -EINVAL;
3801
8e30bc55
JB
3802 ibss.beacon_interval = 100;
3803
3804 if (info->attrs[NL80211_ATTR_BEACON_INTERVAL]) {
3805 ibss.beacon_interval =
3806 nla_get_u32(info->attrs[NL80211_ATTR_BEACON_INTERVAL]);
3807 if (ibss.beacon_interval < 1 || ibss.beacon_interval > 10000)
3808 return -EINVAL;
3809 }
3810
04a773ad
JB
3811 rtnl_lock();
3812
463d0183 3813 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
04a773ad
JB
3814 if (err)
3815 goto unlock_rtnl;
3816
79c97e97 3817 if (!rdev->ops->join_ibss) {
04a773ad
JB
3818 err = -EOPNOTSUPP;
3819 goto out;
3820 }
3821
3822 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_ADHOC) {
3823 err = -EOPNOTSUPP;
3824 goto out;
3825 }
3826
3827 if (!netif_running(dev)) {
3828 err = -ENETDOWN;
3829 goto out;
3830 }
3831
79c97e97 3832 wiphy = &rdev->wiphy;
04a773ad
JB
3833
3834 if (info->attrs[NL80211_ATTR_MAC])
3835 ibss.bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
3836 ibss.ssid = nla_data(info->attrs[NL80211_ATTR_SSID]);
3837 ibss.ssid_len = nla_len(info->attrs[NL80211_ATTR_SSID]);
3838
3839 if (info->attrs[NL80211_ATTR_IE]) {
3840 ibss.ie = nla_data(info->attrs[NL80211_ATTR_IE]);
3841 ibss.ie_len = nla_len(info->attrs[NL80211_ATTR_IE]);
3842 }
3843
3844 ibss.channel = ieee80211_get_channel(wiphy,
3845 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]));
3846 if (!ibss.channel ||
3847 ibss.channel->flags & IEEE80211_CHAN_NO_IBSS ||
3848 ibss.channel->flags & IEEE80211_CHAN_DISABLED) {
3849 err = -EINVAL;
3850 goto out;
3851 }
3852
3853 ibss.channel_fixed = !!info->attrs[NL80211_ATTR_FREQ_FIXED];
fffd0934
JB
3854 ibss.privacy = !!info->attrs[NL80211_ATTR_PRIVACY];
3855
3856 if (ibss.privacy && info->attrs[NL80211_ATTR_KEYS]) {
3857 connkeys = nl80211_parse_connkeys(rdev,
3858 info->attrs[NL80211_ATTR_KEYS]);
3859 if (IS_ERR(connkeys)) {
3860 err = PTR_ERR(connkeys);
3861 connkeys = NULL;
3862 goto out;
3863 }
3864 }
04a773ad 3865
fffd0934 3866 err = cfg80211_join_ibss(rdev, dev, &ibss, connkeys);
04a773ad
JB
3867
3868out:
79c97e97 3869 cfg80211_unlock_rdev(rdev);
04a773ad
JB
3870 dev_put(dev);
3871unlock_rtnl:
fffd0934
JB
3872 if (err)
3873 kfree(connkeys);
04a773ad
JB
3874 rtnl_unlock();
3875 return err;
3876}
3877
3878static int nl80211_leave_ibss(struct sk_buff *skb, struct genl_info *info)
3879{
79c97e97 3880 struct cfg80211_registered_device *rdev;
04a773ad
JB
3881 struct net_device *dev;
3882 int err;
3883
3884 rtnl_lock();
3885
463d0183 3886 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
04a773ad
JB
3887 if (err)
3888 goto unlock_rtnl;
3889
79c97e97 3890 if (!rdev->ops->leave_ibss) {
04a773ad
JB
3891 err = -EOPNOTSUPP;
3892 goto out;
3893 }
3894
3895 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_ADHOC) {
3896 err = -EOPNOTSUPP;
3897 goto out;
3898 }
3899
3900 if (!netif_running(dev)) {
3901 err = -ENETDOWN;
3902 goto out;
3903 }
3904
79c97e97 3905 err = cfg80211_leave_ibss(rdev, dev, false);
04a773ad
JB
3906
3907out:
79c97e97 3908 cfg80211_unlock_rdev(rdev);
04a773ad
JB
3909 dev_put(dev);
3910unlock_rtnl:
3911 rtnl_unlock();
3912 return err;
3913}
3914
aff89a9b
JB
3915#ifdef CONFIG_NL80211_TESTMODE
3916static struct genl_multicast_group nl80211_testmode_mcgrp = {
3917 .name = "testmode",
3918};
3919
3920static int nl80211_testmode_do(struct sk_buff *skb, struct genl_info *info)
3921{
3922 struct cfg80211_registered_device *rdev;
3923 int err;
3924
3925 if (!info->attrs[NL80211_ATTR_TESTDATA])
3926 return -EINVAL;
3927
3928 rtnl_lock();
3929
3930 rdev = cfg80211_get_dev_from_info(info);
3931 if (IS_ERR(rdev)) {
3932 err = PTR_ERR(rdev);
3933 goto unlock_rtnl;
3934 }
3935
3936 err = -EOPNOTSUPP;
3937 if (rdev->ops->testmode_cmd) {
3938 rdev->testmode_info = info;
3939 err = rdev->ops->testmode_cmd(&rdev->wiphy,
3940 nla_data(info->attrs[NL80211_ATTR_TESTDATA]),
3941 nla_len(info->attrs[NL80211_ATTR_TESTDATA]));
3942 rdev->testmode_info = NULL;
3943 }
3944
4d0c8aea 3945 cfg80211_unlock_rdev(rdev);
aff89a9b
JB
3946
3947 unlock_rtnl:
3948 rtnl_unlock();
3949 return err;
3950}
3951
3952static struct sk_buff *
3953__cfg80211_testmode_alloc_skb(struct cfg80211_registered_device *rdev,
3954 int approxlen, u32 pid, u32 seq, gfp_t gfp)
3955{
3956 struct sk_buff *skb;
3957 void *hdr;
3958 struct nlattr *data;
3959
3960 skb = nlmsg_new(approxlen + 100, gfp);
3961 if (!skb)
3962 return NULL;
3963
3964 hdr = nl80211hdr_put(skb, pid, seq, 0, NL80211_CMD_TESTMODE);
3965 if (!hdr) {
3966 kfree_skb(skb);
3967 return NULL;
3968 }
3969
3970 NLA_PUT_U32(skb, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
3971 data = nla_nest_start(skb, NL80211_ATTR_TESTDATA);
3972
3973 ((void **)skb->cb)[0] = rdev;
3974 ((void **)skb->cb)[1] = hdr;
3975 ((void **)skb->cb)[2] = data;
3976
3977 return skb;
3978
3979 nla_put_failure:
3980 kfree_skb(skb);
3981 return NULL;
3982}
3983
3984struct sk_buff *cfg80211_testmode_alloc_reply_skb(struct wiphy *wiphy,
3985 int approxlen)
3986{
3987 struct cfg80211_registered_device *rdev = wiphy_to_dev(wiphy);
3988
3989 if (WARN_ON(!rdev->testmode_info))
3990 return NULL;
3991
3992 return __cfg80211_testmode_alloc_skb(rdev, approxlen,
3993 rdev->testmode_info->snd_pid,
3994 rdev->testmode_info->snd_seq,
3995 GFP_KERNEL);
3996}
3997EXPORT_SYMBOL(cfg80211_testmode_alloc_reply_skb);
3998
3999int cfg80211_testmode_reply(struct sk_buff *skb)
4000{
4001 struct cfg80211_registered_device *rdev = ((void **)skb->cb)[0];
4002 void *hdr = ((void **)skb->cb)[1];
4003 struct nlattr *data = ((void **)skb->cb)[2];
4004
4005 if (WARN_ON(!rdev->testmode_info)) {
4006 kfree_skb(skb);
4007 return -EINVAL;
4008 }
4009
4010 nla_nest_end(skb, data);
4011 genlmsg_end(skb, hdr);
4012 return genlmsg_reply(skb, rdev->testmode_info);
4013}
4014EXPORT_SYMBOL(cfg80211_testmode_reply);
4015
4016struct sk_buff *cfg80211_testmode_alloc_event_skb(struct wiphy *wiphy,
4017 int approxlen, gfp_t gfp)
4018{
4019 struct cfg80211_registered_device *rdev = wiphy_to_dev(wiphy);
4020
4021 return __cfg80211_testmode_alloc_skb(rdev, approxlen, 0, 0, gfp);
4022}
4023EXPORT_SYMBOL(cfg80211_testmode_alloc_event_skb);
4024
4025void cfg80211_testmode_event(struct sk_buff *skb, gfp_t gfp)
4026{
4027 void *hdr = ((void **)skb->cb)[1];
4028 struct nlattr *data = ((void **)skb->cb)[2];
4029
4030 nla_nest_end(skb, data);
4031 genlmsg_end(skb, hdr);
4032 genlmsg_multicast(skb, 0, nl80211_testmode_mcgrp.id, gfp);
4033}
4034EXPORT_SYMBOL(cfg80211_testmode_event);
4035#endif
4036
b23aa676
SO
4037static int nl80211_connect(struct sk_buff *skb, struct genl_info *info)
4038{
79c97e97 4039 struct cfg80211_registered_device *rdev;
b23aa676
SO
4040 struct net_device *dev;
4041 struct cfg80211_connect_params connect;
4042 struct wiphy *wiphy;
fffd0934 4043 struct cfg80211_cached_keys *connkeys = NULL;
b23aa676
SO
4044 int err;
4045
4046 memset(&connect, 0, sizeof(connect));
4047
4048 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_IE]))
4049 return -EINVAL;
4050
4051 if (!info->attrs[NL80211_ATTR_SSID] ||
4052 !nla_len(info->attrs[NL80211_ATTR_SSID]))
4053 return -EINVAL;
4054
4055 if (info->attrs[NL80211_ATTR_AUTH_TYPE]) {
4056 connect.auth_type =
4057 nla_get_u32(info->attrs[NL80211_ATTR_AUTH_TYPE]);
4058 if (!nl80211_valid_auth_type(connect.auth_type))
4059 return -EINVAL;
4060 } else
4061 connect.auth_type = NL80211_AUTHTYPE_AUTOMATIC;
4062
4063 connect.privacy = info->attrs[NL80211_ATTR_PRIVACY];
4064
3dc27d25
JB
4065 err = nl80211_crypto_settings(info, &connect.crypto,
4066 NL80211_MAX_NR_CIPHER_SUITES);
b23aa676
SO
4067 if (err)
4068 return err;
4069 rtnl_lock();
4070
463d0183 4071 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
b23aa676
SO
4072 if (err)
4073 goto unlock_rtnl;
4074
4075 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
4076 err = -EOPNOTSUPP;
4077 goto out;
4078 }
4079
4080 if (!netif_running(dev)) {
4081 err = -ENETDOWN;
4082 goto out;
4083 }
4084
79c97e97 4085 wiphy = &rdev->wiphy;
b23aa676 4086
b23aa676
SO
4087 if (info->attrs[NL80211_ATTR_MAC])
4088 connect.bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
4089 connect.ssid = nla_data(info->attrs[NL80211_ATTR_SSID]);
4090 connect.ssid_len = nla_len(info->attrs[NL80211_ATTR_SSID]);
4091
4092 if (info->attrs[NL80211_ATTR_IE]) {
4093 connect.ie = nla_data(info->attrs[NL80211_ATTR_IE]);
4094 connect.ie_len = nla_len(info->attrs[NL80211_ATTR_IE]);
4095 }
4096
4097 if (info->attrs[NL80211_ATTR_WIPHY_FREQ]) {
4098 connect.channel =
4099 ieee80211_get_channel(wiphy,
4100 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]));
4101 if (!connect.channel ||
4102 connect.channel->flags & IEEE80211_CHAN_DISABLED) {
4103 err = -EINVAL;
4104 goto out;
4105 }
4106 }
4107
fffd0934
JB
4108 if (connect.privacy && info->attrs[NL80211_ATTR_KEYS]) {
4109 connkeys = nl80211_parse_connkeys(rdev,
4110 info->attrs[NL80211_ATTR_KEYS]);
4111 if (IS_ERR(connkeys)) {
4112 err = PTR_ERR(connkeys);
4113 connkeys = NULL;
4114 goto out;
4115 }
4116 }
4117
4118 err = cfg80211_connect(rdev, dev, &connect, connkeys);
b23aa676
SO
4119
4120out:
79c97e97 4121 cfg80211_unlock_rdev(rdev);
b23aa676
SO
4122 dev_put(dev);
4123unlock_rtnl:
fffd0934
JB
4124 if (err)
4125 kfree(connkeys);
b23aa676
SO
4126 rtnl_unlock();
4127 return err;
4128}
4129
4130static int nl80211_disconnect(struct sk_buff *skb, struct genl_info *info)
4131{
79c97e97 4132 struct cfg80211_registered_device *rdev;
b23aa676
SO
4133 struct net_device *dev;
4134 int err;
4135 u16 reason;
4136
4137 if (!info->attrs[NL80211_ATTR_REASON_CODE])
4138 reason = WLAN_REASON_DEAUTH_LEAVING;
4139 else
4140 reason = nla_get_u16(info->attrs[NL80211_ATTR_REASON_CODE]);
4141
4142 if (reason == 0)
4143 return -EINVAL;
4144
4145 rtnl_lock();
4146
463d0183 4147 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
b23aa676
SO
4148 if (err)
4149 goto unlock_rtnl;
4150
4151 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
4152 err = -EOPNOTSUPP;
4153 goto out;
4154 }
4155
4156 if (!netif_running(dev)) {
4157 err = -ENETDOWN;
4158 goto out;
4159 }
4160
79c97e97 4161 err = cfg80211_disconnect(rdev, dev, reason, true);
b23aa676
SO
4162
4163out:
79c97e97 4164 cfg80211_unlock_rdev(rdev);
b23aa676
SO
4165 dev_put(dev);
4166unlock_rtnl:
4167 rtnl_unlock();
4168 return err;
4169}
4170
463d0183
JB
4171static int nl80211_wiphy_netns(struct sk_buff *skb, struct genl_info *info)
4172{
4173 struct cfg80211_registered_device *rdev;
4174 struct net *net;
4175 int err;
4176 u32 pid;
4177
4178 if (!info->attrs[NL80211_ATTR_PID])
4179 return -EINVAL;
4180
4181 pid = nla_get_u32(info->attrs[NL80211_ATTR_PID]);
4182
4183 rtnl_lock();
4184
4185 rdev = cfg80211_get_dev_from_info(info);
4186 if (IS_ERR(rdev)) {
4187 err = PTR_ERR(rdev);
8a8e05e5 4188 goto out_rtnl;
463d0183
JB
4189 }
4190
4191 net = get_net_ns_by_pid(pid);
4192 if (IS_ERR(net)) {
4193 err = PTR_ERR(net);
4194 goto out;
4195 }
4196
4197 err = 0;
4198
4199 /* check if anything to do */
4200 if (net_eq(wiphy_net(&rdev->wiphy), net))
4201 goto out_put_net;
4202
4203 err = cfg80211_switch_netns(rdev, net);
4204 out_put_net:
4205 put_net(net);
4206 out:
4207 cfg80211_unlock_rdev(rdev);
8a8e05e5 4208 out_rtnl:
463d0183
JB
4209 rtnl_unlock();
4210 return err;
4211}
4212
67fbb16b
SO
4213static int nl80211_setdel_pmksa(struct sk_buff *skb, struct genl_info *info)
4214{
4215 struct cfg80211_registered_device *rdev;
4216 int (*rdev_ops)(struct wiphy *wiphy, struct net_device *dev,
4217 struct cfg80211_pmksa *pmksa) = NULL;
4218 int err;
4219 struct net_device *dev;
4220 struct cfg80211_pmksa pmksa;
4221
4222 memset(&pmksa, 0, sizeof(struct cfg80211_pmksa));
4223
4224 if (!info->attrs[NL80211_ATTR_MAC])
4225 return -EINVAL;
4226
4227 if (!info->attrs[NL80211_ATTR_PMKID])
4228 return -EINVAL;
4229
4230 rtnl_lock();
4231
4232 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4233 if (err)
4234 goto out_rtnl;
4235
4236 pmksa.pmkid = nla_data(info->attrs[NL80211_ATTR_PMKID]);
4237 pmksa.bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
4238
4239 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
4240 err = -EOPNOTSUPP;
4241 goto out;
4242 }
4243
4244 switch (info->genlhdr->cmd) {
4245 case NL80211_CMD_SET_PMKSA:
4246 rdev_ops = rdev->ops->set_pmksa;
4247 break;
4248 case NL80211_CMD_DEL_PMKSA:
4249 rdev_ops = rdev->ops->del_pmksa;
4250 break;
4251 default:
4252 WARN_ON(1);
4253 break;
4254 }
4255
4256 if (!rdev_ops) {
4257 err = -EOPNOTSUPP;
4258 goto out;
4259 }
4260
4261 err = rdev_ops(&rdev->wiphy, dev, &pmksa);
4262
4263 out:
4264 cfg80211_unlock_rdev(rdev);
4265 dev_put(dev);
4266 out_rtnl:
4267 rtnl_unlock();
4268
4269 return err;
4270}
4271
4272static int nl80211_flush_pmksa(struct sk_buff *skb, struct genl_info *info)
4273{
4274 struct cfg80211_registered_device *rdev;
4275 int err;
4276 struct net_device *dev;
4277
4278 rtnl_lock();
4279
4280 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4281 if (err)
4282 goto out_rtnl;
4283
4284 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
4285 err = -EOPNOTSUPP;
4286 goto out;
4287 }
4288
4289 if (!rdev->ops->flush_pmksa) {
4290 err = -EOPNOTSUPP;
4291 goto out;
4292 }
4293
4294 err = rdev->ops->flush_pmksa(&rdev->wiphy, dev);
4295
4296 out:
4297 cfg80211_unlock_rdev(rdev);
4298 dev_put(dev);
4299 out_rtnl:
4300 rtnl_unlock();
4301
4302 return err;
4303
4304}
4305
9588bbd5
JM
4306static int nl80211_remain_on_channel(struct sk_buff *skb,
4307 struct genl_info *info)
4308{
4309 struct cfg80211_registered_device *rdev;
4310 struct net_device *dev;
4311 struct ieee80211_channel *chan;
4312 struct sk_buff *msg;
4313 void *hdr;
4314 u64 cookie;
4315 enum nl80211_channel_type channel_type = NL80211_CHAN_NO_HT;
4316 u32 freq, duration;
4317 int err;
4318
4319 if (!info->attrs[NL80211_ATTR_WIPHY_FREQ] ||
4320 !info->attrs[NL80211_ATTR_DURATION])
4321 return -EINVAL;
4322
4323 duration = nla_get_u32(info->attrs[NL80211_ATTR_DURATION]);
4324
4325 /*
4326 * We should be on that channel for at least one jiffie,
4327 * and more than 5 seconds seems excessive.
4328 */
4329 if (!duration || !msecs_to_jiffies(duration) || duration > 5000)
4330 return -EINVAL;
4331
4332 rtnl_lock();
4333
4334 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4335 if (err)
4336 goto unlock_rtnl;
4337
4338 if (!rdev->ops->remain_on_channel) {
4339 err = -EOPNOTSUPP;
4340 goto out;
4341 }
4342
4343 if (!netif_running(dev)) {
4344 err = -ENETDOWN;
4345 goto out;
4346 }
4347
4348 if (info->attrs[NL80211_ATTR_WIPHY_CHANNEL_TYPE]) {
4349 channel_type = nla_get_u32(
4350 info->attrs[NL80211_ATTR_WIPHY_CHANNEL_TYPE]);
4351 if (channel_type != NL80211_CHAN_NO_HT &&
4352 channel_type != NL80211_CHAN_HT20 &&
4353 channel_type != NL80211_CHAN_HT40PLUS &&
4354 channel_type != NL80211_CHAN_HT40MINUS)
4355 err = -EINVAL;
4356 goto out;
4357 }
4358
4359 freq = nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]);
4360 chan = rdev_freq_to_chan(rdev, freq, channel_type);
4361 if (chan == NULL) {
4362 err = -EINVAL;
4363 goto out;
4364 }
4365
4366 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4367 if (!msg) {
4368 err = -ENOMEM;
4369 goto out;
4370 }
4371
4372 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0,
4373 NL80211_CMD_REMAIN_ON_CHANNEL);
4374
4375 if (IS_ERR(hdr)) {
4376 err = PTR_ERR(hdr);
4377 goto free_msg;
4378 }
4379
4380 err = rdev->ops->remain_on_channel(&rdev->wiphy, dev, chan,
4381 channel_type, duration, &cookie);
4382
4383 if (err)
4384 goto free_msg;
4385
4386 NLA_PUT_U64(msg, NL80211_ATTR_COOKIE, cookie);
4387
4388 genlmsg_end(msg, hdr);
4389 err = genlmsg_reply(msg, info);
4390 goto out;
4391
4392 nla_put_failure:
4393 err = -ENOBUFS;
4394 free_msg:
4395 nlmsg_free(msg);
4396 out:
4397 cfg80211_unlock_rdev(rdev);
4398 dev_put(dev);
4399 unlock_rtnl:
4400 rtnl_unlock();
4401 return err;
4402}
4403
4404static int nl80211_cancel_remain_on_channel(struct sk_buff *skb,
4405 struct genl_info *info)
4406{
4407 struct cfg80211_registered_device *rdev;
4408 struct net_device *dev;
4409 u64 cookie;
4410 int err;
4411
4412 if (!info->attrs[NL80211_ATTR_COOKIE])
4413 return -EINVAL;
4414
4415 rtnl_lock();
4416
4417 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4418 if (err)
4419 goto unlock_rtnl;
4420
4421 if (!rdev->ops->cancel_remain_on_channel) {
4422 err = -EOPNOTSUPP;
4423 goto out;
4424 }
4425
4426 if (!netif_running(dev)) {
4427 err = -ENETDOWN;
4428 goto out;
4429 }
4430
4431 cookie = nla_get_u64(info->attrs[NL80211_ATTR_COOKIE]);
4432
4433 err = rdev->ops->cancel_remain_on_channel(&rdev->wiphy, dev, cookie);
4434
4435 out:
4436 cfg80211_unlock_rdev(rdev);
4437 dev_put(dev);
4438 unlock_rtnl:
4439 rtnl_unlock();
4440 return err;
4441}
4442
13ae75b1
JM
4443static u32 rateset_to_mask(struct ieee80211_supported_band *sband,
4444 u8 *rates, u8 rates_len)
4445{
4446 u8 i;
4447 u32 mask = 0;
4448
4449 for (i = 0; i < rates_len; i++) {
4450 int rate = (rates[i] & 0x7f) * 5;
4451 int ridx;
4452 for (ridx = 0; ridx < sband->n_bitrates; ridx++) {
4453 struct ieee80211_rate *srate =
4454 &sband->bitrates[ridx];
4455 if (rate == srate->bitrate) {
4456 mask |= 1 << ridx;
4457 break;
4458 }
4459 }
4460 if (ridx == sband->n_bitrates)
4461 return 0; /* rate not found */
4462 }
4463
4464 return mask;
4465}
4466
b54452b0 4467static const struct nla_policy nl80211_txattr_policy[NL80211_TXRATE_MAX + 1] = {
13ae75b1
JM
4468 [NL80211_TXRATE_LEGACY] = { .type = NLA_BINARY,
4469 .len = NL80211_MAX_SUPP_RATES },
4470};
4471
4472static int nl80211_set_tx_bitrate_mask(struct sk_buff *skb,
4473 struct genl_info *info)
4474{
4475 struct nlattr *tb[NL80211_TXRATE_MAX + 1];
4476 struct cfg80211_registered_device *rdev;
4477 struct cfg80211_bitrate_mask mask;
4478 int err, rem, i;
4479 struct net_device *dev;
4480 struct nlattr *tx_rates;
4481 struct ieee80211_supported_band *sband;
4482
4483 if (info->attrs[NL80211_ATTR_TX_RATES] == NULL)
4484 return -EINVAL;
4485
4486 rtnl_lock();
4487
4488 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4489 if (err)
4490 goto unlock_rtnl;
4491
4492 if (!rdev->ops->set_bitrate_mask) {
4493 err = -EOPNOTSUPP;
4494 goto unlock;
4495 }
4496
4497 memset(&mask, 0, sizeof(mask));
4498 /* Default to all rates enabled */
4499 for (i = 0; i < IEEE80211_NUM_BANDS; i++) {
4500 sband = rdev->wiphy.bands[i];
4501 mask.control[i].legacy =
4502 sband ? (1 << sband->n_bitrates) - 1 : 0;
4503 }
4504
4505 /*
4506 * The nested attribute uses enum nl80211_band as the index. This maps
4507 * directly to the enum ieee80211_band values used in cfg80211.
4508 */
4509 nla_for_each_nested(tx_rates, info->attrs[NL80211_ATTR_TX_RATES], rem)
4510 {
4511 enum ieee80211_band band = nla_type(tx_rates);
4512 if (band < 0 || band >= IEEE80211_NUM_BANDS) {
4513 err = -EINVAL;
4514 goto unlock;
4515 }
4516 sband = rdev->wiphy.bands[band];
4517 if (sband == NULL) {
4518 err = -EINVAL;
4519 goto unlock;
4520 }
4521 nla_parse(tb, NL80211_TXRATE_MAX, nla_data(tx_rates),
4522 nla_len(tx_rates), nl80211_txattr_policy);
4523 if (tb[NL80211_TXRATE_LEGACY]) {
4524 mask.control[band].legacy = rateset_to_mask(
4525 sband,
4526 nla_data(tb[NL80211_TXRATE_LEGACY]),
4527 nla_len(tb[NL80211_TXRATE_LEGACY]));
4528 if (mask.control[band].legacy == 0) {
4529 err = -EINVAL;
4530 goto unlock;
4531 }
4532 }
4533 }
4534
4535 err = rdev->ops->set_bitrate_mask(&rdev->wiphy, dev, NULL, &mask);
4536
4537 unlock:
4538 dev_put(dev);
4539 cfg80211_unlock_rdev(rdev);
4540 unlock_rtnl:
4541 rtnl_unlock();
4542 return err;
4543}
4544
026331c4
JM
4545static int nl80211_register_action(struct sk_buff *skb, struct genl_info *info)
4546{
4547 struct cfg80211_registered_device *rdev;
4548 struct net_device *dev;
4549 int err;
4550
4551 if (!info->attrs[NL80211_ATTR_FRAME_MATCH])
4552 return -EINVAL;
4553
4554 if (nla_len(info->attrs[NL80211_ATTR_FRAME_MATCH]) < 1)
4555 return -EINVAL;
4556
4557 rtnl_lock();
4558
4559 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4560 if (err)
4561 goto unlock_rtnl;
4562
4563 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
4564 err = -EOPNOTSUPP;
4565 goto out;
4566 }
4567
4568 /* not much point in registering if we can't reply */
4569 if (!rdev->ops->action) {
4570 err = -EOPNOTSUPP;
4571 goto out;
4572 }
4573
4574 err = cfg80211_mlme_register_action(dev->ieee80211_ptr, info->snd_pid,
4575 nla_data(info->attrs[NL80211_ATTR_FRAME_MATCH]),
4576 nla_len(info->attrs[NL80211_ATTR_FRAME_MATCH]));
4577 out:
4578 cfg80211_unlock_rdev(rdev);
4579 dev_put(dev);
4580 unlock_rtnl:
4581 rtnl_unlock();
4582 return err;
4583}
4584
4585static int nl80211_action(struct sk_buff *skb, struct genl_info *info)
4586{
4587 struct cfg80211_registered_device *rdev;
4588 struct net_device *dev;
4589 struct ieee80211_channel *chan;
4590 enum nl80211_channel_type channel_type = NL80211_CHAN_NO_HT;
4591 u32 freq;
4592 int err;
4593 void *hdr;
4594 u64 cookie;
4595 struct sk_buff *msg;
4596
4597 if (!info->attrs[NL80211_ATTR_FRAME] ||
4598 !info->attrs[NL80211_ATTR_WIPHY_FREQ])
4599 return -EINVAL;
4600
4601 rtnl_lock();
4602
4603 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4604 if (err)
4605 goto unlock_rtnl;
4606
4607 if (!rdev->ops->action) {
4608 err = -EOPNOTSUPP;
4609 goto out;
4610 }
4611
4612 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
4613 err = -EOPNOTSUPP;
4614 goto out;
4615 }
4616
4617 if (!netif_running(dev)) {
4618 err = -ENETDOWN;
4619 goto out;
4620 }
4621
4622 if (info->attrs[NL80211_ATTR_WIPHY_CHANNEL_TYPE]) {
4623 channel_type = nla_get_u32(
4624 info->attrs[NL80211_ATTR_WIPHY_CHANNEL_TYPE]);
4625 if (channel_type != NL80211_CHAN_NO_HT &&
4626 channel_type != NL80211_CHAN_HT20 &&
4627 channel_type != NL80211_CHAN_HT40PLUS &&
4628 channel_type != NL80211_CHAN_HT40MINUS)
4629 err = -EINVAL;
4630 goto out;
4631 }
4632
4633 freq = nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]);
4634 chan = rdev_freq_to_chan(rdev, freq, channel_type);
4635 if (chan == NULL) {
4636 err = -EINVAL;
4637 goto out;
4638 }
4639
4640 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4641 if (!msg) {
4642 err = -ENOMEM;
4643 goto out;
4644 }
4645
4646 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0,
4647 NL80211_CMD_ACTION);
4648
4649 if (IS_ERR(hdr)) {
4650 err = PTR_ERR(hdr);
4651 goto free_msg;
4652 }
4653 err = cfg80211_mlme_action(rdev, dev, chan, channel_type,
4654 nla_data(info->attrs[NL80211_ATTR_FRAME]),
4655 nla_len(info->attrs[NL80211_ATTR_FRAME]),
4656 &cookie);
4657 if (err)
4658 goto free_msg;
4659
4660 NLA_PUT_U64(msg, NL80211_ATTR_COOKIE, cookie);
4661
4662 genlmsg_end(msg, hdr);
4663 err = genlmsg_reply(msg, info);
4664 goto out;
4665
4666 nla_put_failure:
4667 err = -ENOBUFS;
4668 free_msg:
4669 nlmsg_free(msg);
4670 out:
4671 cfg80211_unlock_rdev(rdev);
4672 dev_put(dev);
4673unlock_rtnl:
4674 rtnl_unlock();
4675 return err;
4676}
4677
ffb9eb3d
KV
4678static int nl80211_set_power_save(struct sk_buff *skb, struct genl_info *info)
4679{
4680 struct cfg80211_registered_device *rdev;
4681 struct wireless_dev *wdev;
4682 struct net_device *dev;
4683 u8 ps_state;
4684 bool state;
4685 int err;
4686
4687 if (!info->attrs[NL80211_ATTR_PS_STATE]) {
4688 err = -EINVAL;
4689 goto out;
4690 }
4691
4692 ps_state = nla_get_u32(info->attrs[NL80211_ATTR_PS_STATE]);
4693
4694 if (ps_state != NL80211_PS_DISABLED && ps_state != NL80211_PS_ENABLED) {
4695 err = -EINVAL;
4696 goto out;
4697 }
4698
4699 rtnl_lock();
4700
4701 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4702 if (err)
4703 goto unlock_rdev;
4704
4705 wdev = dev->ieee80211_ptr;
4706
4707 if (!rdev->ops->set_power_mgmt) {
4708 err = -EOPNOTSUPP;
4709 goto unlock_rdev;
4710 }
4711
4712 state = (ps_state == NL80211_PS_ENABLED) ? true : false;
4713
4714 if (state == wdev->ps)
4715 goto unlock_rdev;
4716
4717 wdev->ps = state;
4718
4719 if (rdev->ops->set_power_mgmt(wdev->wiphy, dev, wdev->ps,
4720 wdev->ps_timeout))
4721 /* assume this means it's off */
4722 wdev->ps = false;
4723
4724unlock_rdev:
4725 cfg80211_unlock_rdev(rdev);
4726 dev_put(dev);
4727 rtnl_unlock();
4728
4729out:
4730 return err;
4731}
4732
4733static int nl80211_get_power_save(struct sk_buff *skb, struct genl_info *info)
4734{
4735 struct cfg80211_registered_device *rdev;
4736 enum nl80211_ps_state ps_state;
4737 struct wireless_dev *wdev;
4738 struct net_device *dev;
4739 struct sk_buff *msg;
4740 void *hdr;
4741 int err;
4742
4743 rtnl_lock();
4744
4745 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4746 if (err)
4747 goto unlock_rtnl;
4748
4749 wdev = dev->ieee80211_ptr;
4750
4751 if (!rdev->ops->set_power_mgmt) {
4752 err = -EOPNOTSUPP;
4753 goto out;
4754 }
4755
4756 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4757 if (!msg) {
4758 err = -ENOMEM;
4759 goto out;
4760 }
4761
4762 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0,
4763 NL80211_CMD_GET_POWER_SAVE);
4764 if (!hdr) {
4765 err = -ENOMEM;
4766 goto free_msg;
4767 }
4768
4769 if (wdev->ps)
4770 ps_state = NL80211_PS_ENABLED;
4771 else
4772 ps_state = NL80211_PS_DISABLED;
4773
4774 NLA_PUT_U32(msg, NL80211_ATTR_PS_STATE, ps_state);
4775
4776 genlmsg_end(msg, hdr);
4777 err = genlmsg_reply(msg, info);
4778 goto out;
4779
4780nla_put_failure:
4781 err = -ENOBUFS;
4782
4783free_msg:
4784 nlmsg_free(msg);
4785
4786out:
4787 cfg80211_unlock_rdev(rdev);
4788 dev_put(dev);
4789
4790unlock_rtnl:
4791 rtnl_unlock();
4792
4793 return err;
4794}
4795
d6dc1a38
JO
4796static struct nla_policy
4797nl80211_attr_cqm_policy[NL80211_ATTR_CQM_MAX + 1] __read_mostly = {
4798 [NL80211_ATTR_CQM_RSSI_THOLD] = { .type = NLA_U32 },
4799 [NL80211_ATTR_CQM_RSSI_HYST] = { .type = NLA_U32 },
4800 [NL80211_ATTR_CQM_RSSI_THRESHOLD_EVENT] = { .type = NLA_U32 },
4801};
4802
4803static int nl80211_set_cqm_rssi(struct genl_info *info,
4804 s32 threshold, u32 hysteresis)
4805{
4806 struct cfg80211_registered_device *rdev;
4807 struct wireless_dev *wdev;
4808 struct net_device *dev;
4809 int err;
4810
4811 if (threshold > 0)
4812 return -EINVAL;
4813
4814 rtnl_lock();
4815
4816 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4817 if (err)
4818 goto unlock_rdev;
4819
4820 wdev = dev->ieee80211_ptr;
4821
4822 if (!rdev->ops->set_cqm_rssi_config) {
4823 err = -EOPNOTSUPP;
4824 goto unlock_rdev;
4825 }
4826
4827 if (wdev->iftype != NL80211_IFTYPE_STATION) {
4828 err = -EOPNOTSUPP;
4829 goto unlock_rdev;
4830 }
4831
4832 err = rdev->ops->set_cqm_rssi_config(wdev->wiphy, dev,
4833 threshold, hysteresis);
4834
4835unlock_rdev:
4836 cfg80211_unlock_rdev(rdev);
4837 dev_put(dev);
4838 rtnl_unlock();
4839
4840 return err;
4841}
4842
4843static int nl80211_set_cqm(struct sk_buff *skb, struct genl_info *info)
4844{
4845 struct nlattr *attrs[NL80211_ATTR_CQM_MAX + 1];
4846 struct nlattr *cqm;
4847 int err;
4848
4849 cqm = info->attrs[NL80211_ATTR_CQM];
4850 if (!cqm) {
4851 err = -EINVAL;
4852 goto out;
4853 }
4854
4855 err = nla_parse_nested(attrs, NL80211_ATTR_CQM_MAX, cqm,
4856 nl80211_attr_cqm_policy);
4857 if (err)
4858 goto out;
4859
4860 if (attrs[NL80211_ATTR_CQM_RSSI_THOLD] &&
4861 attrs[NL80211_ATTR_CQM_RSSI_HYST]) {
4862 s32 threshold;
4863 u32 hysteresis;
4864 threshold = nla_get_u32(attrs[NL80211_ATTR_CQM_RSSI_THOLD]);
4865 hysteresis = nla_get_u32(attrs[NL80211_ATTR_CQM_RSSI_HYST]);
4866 err = nl80211_set_cqm_rssi(info, threshold, hysteresis);
4867 } else
4868 err = -EINVAL;
4869
4870out:
4871 return err;
4872}
4873
55682965
JB
4874static struct genl_ops nl80211_ops[] = {
4875 {
4876 .cmd = NL80211_CMD_GET_WIPHY,
4877 .doit = nl80211_get_wiphy,
4878 .dumpit = nl80211_dump_wiphy,
4879 .policy = nl80211_policy,
4880 /* can be retrieved by unprivileged users */
4881 },
4882 {
4883 .cmd = NL80211_CMD_SET_WIPHY,
4884 .doit = nl80211_set_wiphy,
4885 .policy = nl80211_policy,
4886 .flags = GENL_ADMIN_PERM,
4887 },
4888 {
4889 .cmd = NL80211_CMD_GET_INTERFACE,
4890 .doit = nl80211_get_interface,
4891 .dumpit = nl80211_dump_interface,
4892 .policy = nl80211_policy,
4893 /* can be retrieved by unprivileged users */
4894 },
4895 {
4896 .cmd = NL80211_CMD_SET_INTERFACE,
4897 .doit = nl80211_set_interface,
4898 .policy = nl80211_policy,
4899 .flags = GENL_ADMIN_PERM,
4900 },
4901 {
4902 .cmd = NL80211_CMD_NEW_INTERFACE,
4903 .doit = nl80211_new_interface,
4904 .policy = nl80211_policy,
4905 .flags = GENL_ADMIN_PERM,
4906 },
4907 {
4908 .cmd = NL80211_CMD_DEL_INTERFACE,
4909 .doit = nl80211_del_interface,
4910 .policy = nl80211_policy,
41ade00f
JB
4911 .flags = GENL_ADMIN_PERM,
4912 },
4913 {
4914 .cmd = NL80211_CMD_GET_KEY,
4915 .doit = nl80211_get_key,
4916 .policy = nl80211_policy,
4917 .flags = GENL_ADMIN_PERM,
4918 },
4919 {
4920 .cmd = NL80211_CMD_SET_KEY,
4921 .doit = nl80211_set_key,
4922 .policy = nl80211_policy,
4923 .flags = GENL_ADMIN_PERM,
4924 },
4925 {
4926 .cmd = NL80211_CMD_NEW_KEY,
4927 .doit = nl80211_new_key,
4928 .policy = nl80211_policy,
4929 .flags = GENL_ADMIN_PERM,
4930 },
4931 {
4932 .cmd = NL80211_CMD_DEL_KEY,
4933 .doit = nl80211_del_key,
4934 .policy = nl80211_policy,
55682965
JB
4935 .flags = GENL_ADMIN_PERM,
4936 },
ed1b6cc7
JB
4937 {
4938 .cmd = NL80211_CMD_SET_BEACON,
4939 .policy = nl80211_policy,
4940 .flags = GENL_ADMIN_PERM,
4941 .doit = nl80211_addset_beacon,
4942 },
4943 {
4944 .cmd = NL80211_CMD_NEW_BEACON,
4945 .policy = nl80211_policy,
4946 .flags = GENL_ADMIN_PERM,
4947 .doit = nl80211_addset_beacon,
4948 },
4949 {
4950 .cmd = NL80211_CMD_DEL_BEACON,
4951 .policy = nl80211_policy,
4952 .flags = GENL_ADMIN_PERM,
4953 .doit = nl80211_del_beacon,
4954 },
5727ef1b
JB
4955 {
4956 .cmd = NL80211_CMD_GET_STATION,
4957 .doit = nl80211_get_station,
2ec600d6 4958 .dumpit = nl80211_dump_station,
5727ef1b 4959 .policy = nl80211_policy,
5727ef1b
JB
4960 },
4961 {
4962 .cmd = NL80211_CMD_SET_STATION,
4963 .doit = nl80211_set_station,
4964 .policy = nl80211_policy,
4965 .flags = GENL_ADMIN_PERM,
4966 },
4967 {
4968 .cmd = NL80211_CMD_NEW_STATION,
4969 .doit = nl80211_new_station,
4970 .policy = nl80211_policy,
4971 .flags = GENL_ADMIN_PERM,
4972 },
4973 {
4974 .cmd = NL80211_CMD_DEL_STATION,
4975 .doit = nl80211_del_station,
4976 .policy = nl80211_policy,
2ec600d6
LCC
4977 .flags = GENL_ADMIN_PERM,
4978 },
4979 {
4980 .cmd = NL80211_CMD_GET_MPATH,
4981 .doit = nl80211_get_mpath,
4982 .dumpit = nl80211_dump_mpath,
4983 .policy = nl80211_policy,
4984 .flags = GENL_ADMIN_PERM,
4985 },
4986 {
4987 .cmd = NL80211_CMD_SET_MPATH,
4988 .doit = nl80211_set_mpath,
4989 .policy = nl80211_policy,
4990 .flags = GENL_ADMIN_PERM,
4991 },
4992 {
4993 .cmd = NL80211_CMD_NEW_MPATH,
4994 .doit = nl80211_new_mpath,
4995 .policy = nl80211_policy,
4996 .flags = GENL_ADMIN_PERM,
4997 },
4998 {
4999 .cmd = NL80211_CMD_DEL_MPATH,
5000 .doit = nl80211_del_mpath,
5001 .policy = nl80211_policy,
9f1ba906
JM
5002 .flags = GENL_ADMIN_PERM,
5003 },
5004 {
5005 .cmd = NL80211_CMD_SET_BSS,
5006 .doit = nl80211_set_bss,
5007 .policy = nl80211_policy,
b2e1b302
LR
5008 .flags = GENL_ADMIN_PERM,
5009 },
f130347c
LR
5010 {
5011 .cmd = NL80211_CMD_GET_REG,
5012 .doit = nl80211_get_reg,
5013 .policy = nl80211_policy,
5014 /* can be retrieved by unprivileged users */
5015 },
b2e1b302
LR
5016 {
5017 .cmd = NL80211_CMD_SET_REG,
5018 .doit = nl80211_set_reg,
5019 .policy = nl80211_policy,
5020 .flags = GENL_ADMIN_PERM,
5021 },
5022 {
5023 .cmd = NL80211_CMD_REQ_SET_REG,
5024 .doit = nl80211_req_set_reg,
5025 .policy = nl80211_policy,
93da9cc1 5026 .flags = GENL_ADMIN_PERM,
5027 },
5028 {
5029 .cmd = NL80211_CMD_GET_MESH_PARAMS,
5030 .doit = nl80211_get_mesh_params,
5031 .policy = nl80211_policy,
5032 /* can be retrieved by unprivileged users */
5033 },
5034 {
5035 .cmd = NL80211_CMD_SET_MESH_PARAMS,
5036 .doit = nl80211_set_mesh_params,
5037 .policy = nl80211_policy,
9aed3cc1
JM
5038 .flags = GENL_ADMIN_PERM,
5039 },
2a519311
JB
5040 {
5041 .cmd = NL80211_CMD_TRIGGER_SCAN,
5042 .doit = nl80211_trigger_scan,
5043 .policy = nl80211_policy,
5044 .flags = GENL_ADMIN_PERM,
5045 },
5046 {
5047 .cmd = NL80211_CMD_GET_SCAN,
5048 .policy = nl80211_policy,
5049 .dumpit = nl80211_dump_scan,
5050 },
636a5d36
JM
5051 {
5052 .cmd = NL80211_CMD_AUTHENTICATE,
5053 .doit = nl80211_authenticate,
5054 .policy = nl80211_policy,
5055 .flags = GENL_ADMIN_PERM,
5056 },
5057 {
5058 .cmd = NL80211_CMD_ASSOCIATE,
5059 .doit = nl80211_associate,
5060 .policy = nl80211_policy,
5061 .flags = GENL_ADMIN_PERM,
5062 },
5063 {
5064 .cmd = NL80211_CMD_DEAUTHENTICATE,
5065 .doit = nl80211_deauthenticate,
5066 .policy = nl80211_policy,
5067 .flags = GENL_ADMIN_PERM,
5068 },
5069 {
5070 .cmd = NL80211_CMD_DISASSOCIATE,
5071 .doit = nl80211_disassociate,
5072 .policy = nl80211_policy,
5073 .flags = GENL_ADMIN_PERM,
5074 },
04a773ad
JB
5075 {
5076 .cmd = NL80211_CMD_JOIN_IBSS,
5077 .doit = nl80211_join_ibss,
5078 .policy = nl80211_policy,
5079 .flags = GENL_ADMIN_PERM,
5080 },
5081 {
5082 .cmd = NL80211_CMD_LEAVE_IBSS,
5083 .doit = nl80211_leave_ibss,
5084 .policy = nl80211_policy,
5085 .flags = GENL_ADMIN_PERM,
5086 },
aff89a9b
JB
5087#ifdef CONFIG_NL80211_TESTMODE
5088 {
5089 .cmd = NL80211_CMD_TESTMODE,
5090 .doit = nl80211_testmode_do,
5091 .policy = nl80211_policy,
5092 .flags = GENL_ADMIN_PERM,
5093 },
5094#endif
b23aa676
SO
5095 {
5096 .cmd = NL80211_CMD_CONNECT,
5097 .doit = nl80211_connect,
5098 .policy = nl80211_policy,
5099 .flags = GENL_ADMIN_PERM,
5100 },
5101 {
5102 .cmd = NL80211_CMD_DISCONNECT,
5103 .doit = nl80211_disconnect,
5104 .policy = nl80211_policy,
5105 .flags = GENL_ADMIN_PERM,
5106 },
463d0183
JB
5107 {
5108 .cmd = NL80211_CMD_SET_WIPHY_NETNS,
5109 .doit = nl80211_wiphy_netns,
5110 .policy = nl80211_policy,
5111 .flags = GENL_ADMIN_PERM,
5112 },
61fa713c
HS
5113 {
5114 .cmd = NL80211_CMD_GET_SURVEY,
5115 .policy = nl80211_policy,
5116 .dumpit = nl80211_dump_survey,
5117 },
67fbb16b
SO
5118 {
5119 .cmd = NL80211_CMD_SET_PMKSA,
5120 .doit = nl80211_setdel_pmksa,
5121 .policy = nl80211_policy,
5122 .flags = GENL_ADMIN_PERM,
5123 },
5124 {
5125 .cmd = NL80211_CMD_DEL_PMKSA,
5126 .doit = nl80211_setdel_pmksa,
5127 .policy = nl80211_policy,
5128 .flags = GENL_ADMIN_PERM,
5129 },
5130 {
5131 .cmd = NL80211_CMD_FLUSH_PMKSA,
5132 .doit = nl80211_flush_pmksa,
5133 .policy = nl80211_policy,
5134 .flags = GENL_ADMIN_PERM,
5135 },
9588bbd5
JM
5136 {
5137 .cmd = NL80211_CMD_REMAIN_ON_CHANNEL,
5138 .doit = nl80211_remain_on_channel,
5139 .policy = nl80211_policy,
5140 .flags = GENL_ADMIN_PERM,
5141 },
5142 {
5143 .cmd = NL80211_CMD_CANCEL_REMAIN_ON_CHANNEL,
5144 .doit = nl80211_cancel_remain_on_channel,
5145 .policy = nl80211_policy,
5146 .flags = GENL_ADMIN_PERM,
5147 },
13ae75b1
JM
5148 {
5149 .cmd = NL80211_CMD_SET_TX_BITRATE_MASK,
5150 .doit = nl80211_set_tx_bitrate_mask,
5151 .policy = nl80211_policy,
5152 .flags = GENL_ADMIN_PERM,
5153 },
026331c4
JM
5154 {
5155 .cmd = NL80211_CMD_REGISTER_ACTION,
5156 .doit = nl80211_register_action,
5157 .policy = nl80211_policy,
5158 .flags = GENL_ADMIN_PERM,
5159 },
5160 {
5161 .cmd = NL80211_CMD_ACTION,
5162 .doit = nl80211_action,
5163 .policy = nl80211_policy,
5164 .flags = GENL_ADMIN_PERM,
5165 },
ffb9eb3d
KV
5166 {
5167 .cmd = NL80211_CMD_SET_POWER_SAVE,
5168 .doit = nl80211_set_power_save,
5169 .policy = nl80211_policy,
5170 .flags = GENL_ADMIN_PERM,
5171 },
5172 {
5173 .cmd = NL80211_CMD_GET_POWER_SAVE,
5174 .doit = nl80211_get_power_save,
5175 .policy = nl80211_policy,
5176 /* can be retrieved by unprivileged users */
5177 },
d6dc1a38
JO
5178 {
5179 .cmd = NL80211_CMD_SET_CQM,
5180 .doit = nl80211_set_cqm,
5181 .policy = nl80211_policy,
5182 .flags = GENL_ADMIN_PERM,
5183 },
55682965 5184};
9588bbd5 5185
6039f6d2
JM
5186static struct genl_multicast_group nl80211_mlme_mcgrp = {
5187 .name = "mlme",
5188};
55682965
JB
5189
5190/* multicast groups */
5191static struct genl_multicast_group nl80211_config_mcgrp = {
5192 .name = "config",
5193};
2a519311
JB
5194static struct genl_multicast_group nl80211_scan_mcgrp = {
5195 .name = "scan",
5196};
73d54c9e
LR
5197static struct genl_multicast_group nl80211_regulatory_mcgrp = {
5198 .name = "regulatory",
5199};
55682965
JB
5200
5201/* notification functions */
5202
5203void nl80211_notify_dev_rename(struct cfg80211_registered_device *rdev)
5204{
5205 struct sk_buff *msg;
5206
fd2120ca 5207 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
55682965
JB
5208 if (!msg)
5209 return;
5210
5211 if (nl80211_send_wiphy(msg, 0, 0, 0, rdev) < 0) {
5212 nlmsg_free(msg);
5213 return;
5214 }
5215
463d0183
JB
5216 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5217 nl80211_config_mcgrp.id, GFP_KERNEL);
55682965
JB
5218}
5219
362a415d
JB
5220static int nl80211_add_scan_req(struct sk_buff *msg,
5221 struct cfg80211_registered_device *rdev)
5222{
5223 struct cfg80211_scan_request *req = rdev->scan_req;
5224 struct nlattr *nest;
5225 int i;
5226
667503dd
JB
5227 ASSERT_RDEV_LOCK(rdev);
5228
362a415d
JB
5229 if (WARN_ON(!req))
5230 return 0;
5231
5232 nest = nla_nest_start(msg, NL80211_ATTR_SCAN_SSIDS);
5233 if (!nest)
5234 goto nla_put_failure;
5235 for (i = 0; i < req->n_ssids; i++)
5236 NLA_PUT(msg, i, req->ssids[i].ssid_len, req->ssids[i].ssid);
5237 nla_nest_end(msg, nest);
5238
5239 nest = nla_nest_start(msg, NL80211_ATTR_SCAN_FREQUENCIES);
5240 if (!nest)
5241 goto nla_put_failure;
5242 for (i = 0; i < req->n_channels; i++)
5243 NLA_PUT_U32(msg, i, req->channels[i]->center_freq);
5244 nla_nest_end(msg, nest);
5245
5246 if (req->ie)
5247 NLA_PUT(msg, NL80211_ATTR_IE, req->ie_len, req->ie);
5248
5249 return 0;
5250 nla_put_failure:
5251 return -ENOBUFS;
5252}
5253
a538e2d5
JB
5254static int nl80211_send_scan_msg(struct sk_buff *msg,
5255 struct cfg80211_registered_device *rdev,
5256 struct net_device *netdev,
5257 u32 pid, u32 seq, int flags,
5258 u32 cmd)
2a519311
JB
5259{
5260 void *hdr;
5261
5262 hdr = nl80211hdr_put(msg, pid, seq, flags, cmd);
5263 if (!hdr)
5264 return -1;
5265
b5850a7a 5266 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
2a519311
JB
5267 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5268
362a415d
JB
5269 /* ignore errors and send incomplete event anyway */
5270 nl80211_add_scan_req(msg, rdev);
2a519311
JB
5271
5272 return genlmsg_end(msg, hdr);
5273
5274 nla_put_failure:
5275 genlmsg_cancel(msg, hdr);
5276 return -EMSGSIZE;
5277}
5278
a538e2d5
JB
5279void nl80211_send_scan_start(struct cfg80211_registered_device *rdev,
5280 struct net_device *netdev)
5281{
5282 struct sk_buff *msg;
5283
5284 msg = nlmsg_new(NLMSG_GOODSIZE, GFP_KERNEL);
5285 if (!msg)
5286 return;
5287
5288 if (nl80211_send_scan_msg(msg, rdev, netdev, 0, 0, 0,
5289 NL80211_CMD_TRIGGER_SCAN) < 0) {
5290 nlmsg_free(msg);
5291 return;
5292 }
5293
463d0183
JB
5294 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5295 nl80211_scan_mcgrp.id, GFP_KERNEL);
a538e2d5
JB
5296}
5297
2a519311
JB
5298void nl80211_send_scan_done(struct cfg80211_registered_device *rdev,
5299 struct net_device *netdev)
5300{
5301 struct sk_buff *msg;
5302
fd2120ca 5303 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2a519311
JB
5304 if (!msg)
5305 return;
5306
a538e2d5
JB
5307 if (nl80211_send_scan_msg(msg, rdev, netdev, 0, 0, 0,
5308 NL80211_CMD_NEW_SCAN_RESULTS) < 0) {
2a519311
JB
5309 nlmsg_free(msg);
5310 return;
5311 }
5312
463d0183
JB
5313 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5314 nl80211_scan_mcgrp.id, GFP_KERNEL);
2a519311
JB
5315}
5316
5317void nl80211_send_scan_aborted(struct cfg80211_registered_device *rdev,
5318 struct net_device *netdev)
5319{
5320 struct sk_buff *msg;
5321
fd2120ca 5322 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2a519311
JB
5323 if (!msg)
5324 return;
5325
a538e2d5
JB
5326 if (nl80211_send_scan_msg(msg, rdev, netdev, 0, 0, 0,
5327 NL80211_CMD_SCAN_ABORTED) < 0) {
2a519311
JB
5328 nlmsg_free(msg);
5329 return;
5330 }
5331
463d0183
JB
5332 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5333 nl80211_scan_mcgrp.id, GFP_KERNEL);
2a519311
JB
5334}
5335
73d54c9e
LR
5336/*
5337 * This can happen on global regulatory changes or device specific settings
5338 * based on custom world regulatory domains.
5339 */
5340void nl80211_send_reg_change_event(struct regulatory_request *request)
5341{
5342 struct sk_buff *msg;
5343 void *hdr;
5344
fd2120ca 5345 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
73d54c9e
LR
5346 if (!msg)
5347 return;
5348
5349 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_REG_CHANGE);
5350 if (!hdr) {
5351 nlmsg_free(msg);
5352 return;
5353 }
5354
5355 /* Userspace can always count this one always being set */
5356 NLA_PUT_U8(msg, NL80211_ATTR_REG_INITIATOR, request->initiator);
5357
5358 if (request->alpha2[0] == '0' && request->alpha2[1] == '0')
5359 NLA_PUT_U8(msg, NL80211_ATTR_REG_TYPE,
5360 NL80211_REGDOM_TYPE_WORLD);
5361 else if (request->alpha2[0] == '9' && request->alpha2[1] == '9')
5362 NLA_PUT_U8(msg, NL80211_ATTR_REG_TYPE,
5363 NL80211_REGDOM_TYPE_CUSTOM_WORLD);
5364 else if ((request->alpha2[0] == '9' && request->alpha2[1] == '8') ||
5365 request->intersect)
5366 NLA_PUT_U8(msg, NL80211_ATTR_REG_TYPE,
5367 NL80211_REGDOM_TYPE_INTERSECTION);
5368 else {
5369 NLA_PUT_U8(msg, NL80211_ATTR_REG_TYPE,
5370 NL80211_REGDOM_TYPE_COUNTRY);
5371 NLA_PUT_STRING(msg, NL80211_ATTR_REG_ALPHA2, request->alpha2);
5372 }
5373
5374 if (wiphy_idx_valid(request->wiphy_idx))
5375 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, request->wiphy_idx);
5376
5377 if (genlmsg_end(msg, hdr) < 0) {
5378 nlmsg_free(msg);
5379 return;
5380 }
5381
bc43b28c 5382 rcu_read_lock();
463d0183 5383 genlmsg_multicast_allns(msg, 0, nl80211_regulatory_mcgrp.id,
bc43b28c
JB
5384 GFP_ATOMIC);
5385 rcu_read_unlock();
73d54c9e
LR
5386
5387 return;
5388
5389nla_put_failure:
5390 genlmsg_cancel(msg, hdr);
5391 nlmsg_free(msg);
5392}
5393
6039f6d2
JM
5394static void nl80211_send_mlme_event(struct cfg80211_registered_device *rdev,
5395 struct net_device *netdev,
5396 const u8 *buf, size_t len,
e6d6e342 5397 enum nl80211_commands cmd, gfp_t gfp)
6039f6d2
JM
5398{
5399 struct sk_buff *msg;
5400 void *hdr;
5401
e6d6e342 5402 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, gfp);
6039f6d2
JM
5403 if (!msg)
5404 return;
5405
5406 hdr = nl80211hdr_put(msg, 0, 0, 0, cmd);
5407 if (!hdr) {
5408 nlmsg_free(msg);
5409 return;
5410 }
5411
5412 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
5413 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5414 NLA_PUT(msg, NL80211_ATTR_FRAME, len, buf);
5415
5416 if (genlmsg_end(msg, hdr) < 0) {
5417 nlmsg_free(msg);
5418 return;
5419 }
5420
463d0183
JB
5421 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5422 nl80211_mlme_mcgrp.id, gfp);
6039f6d2
JM
5423 return;
5424
5425 nla_put_failure:
5426 genlmsg_cancel(msg, hdr);
5427 nlmsg_free(msg);
5428}
5429
5430void nl80211_send_rx_auth(struct cfg80211_registered_device *rdev,
e6d6e342
JB
5431 struct net_device *netdev, const u8 *buf,
5432 size_t len, gfp_t gfp)
6039f6d2
JM
5433{
5434 nl80211_send_mlme_event(rdev, netdev, buf, len,
e6d6e342 5435 NL80211_CMD_AUTHENTICATE, gfp);
6039f6d2
JM
5436}
5437
5438void nl80211_send_rx_assoc(struct cfg80211_registered_device *rdev,
5439 struct net_device *netdev, const u8 *buf,
e6d6e342 5440 size_t len, gfp_t gfp)
6039f6d2 5441{
e6d6e342
JB
5442 nl80211_send_mlme_event(rdev, netdev, buf, len,
5443 NL80211_CMD_ASSOCIATE, gfp);
6039f6d2
JM
5444}
5445
53b46b84 5446void nl80211_send_deauth(struct cfg80211_registered_device *rdev,
e6d6e342
JB
5447 struct net_device *netdev, const u8 *buf,
5448 size_t len, gfp_t gfp)
6039f6d2
JM
5449{
5450 nl80211_send_mlme_event(rdev, netdev, buf, len,
e6d6e342 5451 NL80211_CMD_DEAUTHENTICATE, gfp);
6039f6d2
JM
5452}
5453
53b46b84
JM
5454void nl80211_send_disassoc(struct cfg80211_registered_device *rdev,
5455 struct net_device *netdev, const u8 *buf,
e6d6e342 5456 size_t len, gfp_t gfp)
6039f6d2
JM
5457{
5458 nl80211_send_mlme_event(rdev, netdev, buf, len,
e6d6e342 5459 NL80211_CMD_DISASSOCIATE, gfp);
6039f6d2
JM
5460}
5461
1b06bb40
LR
5462static void nl80211_send_mlme_timeout(struct cfg80211_registered_device *rdev,
5463 struct net_device *netdev, int cmd,
e6d6e342 5464 const u8 *addr, gfp_t gfp)
1965c853
JM
5465{
5466 struct sk_buff *msg;
5467 void *hdr;
5468
e6d6e342 5469 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, gfp);
1965c853
JM
5470 if (!msg)
5471 return;
5472
5473 hdr = nl80211hdr_put(msg, 0, 0, 0, cmd);
5474 if (!hdr) {
5475 nlmsg_free(msg);
5476 return;
5477 }
5478
5479 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
5480 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5481 NLA_PUT_FLAG(msg, NL80211_ATTR_TIMED_OUT);
5482 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, addr);
5483
5484 if (genlmsg_end(msg, hdr) < 0) {
5485 nlmsg_free(msg);
5486 return;
5487 }
5488
463d0183
JB
5489 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5490 nl80211_mlme_mcgrp.id, gfp);
1965c853
JM
5491 return;
5492
5493 nla_put_failure:
5494 genlmsg_cancel(msg, hdr);
5495 nlmsg_free(msg);
5496}
5497
5498void nl80211_send_auth_timeout(struct cfg80211_registered_device *rdev,
e6d6e342
JB
5499 struct net_device *netdev, const u8 *addr,
5500 gfp_t gfp)
1965c853
JM
5501{
5502 nl80211_send_mlme_timeout(rdev, netdev, NL80211_CMD_AUTHENTICATE,
e6d6e342 5503 addr, gfp);
1965c853
JM
5504}
5505
5506void nl80211_send_assoc_timeout(struct cfg80211_registered_device *rdev,
e6d6e342
JB
5507 struct net_device *netdev, const u8 *addr,
5508 gfp_t gfp)
1965c853 5509{
e6d6e342
JB
5510 nl80211_send_mlme_timeout(rdev, netdev, NL80211_CMD_ASSOCIATE,
5511 addr, gfp);
1965c853
JM
5512}
5513
b23aa676
SO
5514void nl80211_send_connect_result(struct cfg80211_registered_device *rdev,
5515 struct net_device *netdev, const u8 *bssid,
5516 const u8 *req_ie, size_t req_ie_len,
5517 const u8 *resp_ie, size_t resp_ie_len,
5518 u16 status, gfp_t gfp)
5519{
5520 struct sk_buff *msg;
5521 void *hdr;
5522
5523 msg = nlmsg_new(NLMSG_GOODSIZE, gfp);
5524 if (!msg)
5525 return;
5526
5527 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_CONNECT);
5528 if (!hdr) {
5529 nlmsg_free(msg);
5530 return;
5531 }
5532
5533 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
5534 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5535 if (bssid)
5536 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, bssid);
5537 NLA_PUT_U16(msg, NL80211_ATTR_STATUS_CODE, status);
5538 if (req_ie)
5539 NLA_PUT(msg, NL80211_ATTR_REQ_IE, req_ie_len, req_ie);
5540 if (resp_ie)
5541 NLA_PUT(msg, NL80211_ATTR_RESP_IE, resp_ie_len, resp_ie);
5542
5543 if (genlmsg_end(msg, hdr) < 0) {
5544 nlmsg_free(msg);
5545 return;
5546 }
5547
463d0183
JB
5548 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5549 nl80211_mlme_mcgrp.id, gfp);
b23aa676
SO
5550 return;
5551
5552 nla_put_failure:
5553 genlmsg_cancel(msg, hdr);
5554 nlmsg_free(msg);
5555
5556}
5557
5558void nl80211_send_roamed(struct cfg80211_registered_device *rdev,
5559 struct net_device *netdev, const u8 *bssid,
5560 const u8 *req_ie, size_t req_ie_len,
5561 const u8 *resp_ie, size_t resp_ie_len, gfp_t gfp)
5562{
5563 struct sk_buff *msg;
5564 void *hdr;
5565
5566 msg = nlmsg_new(NLMSG_GOODSIZE, gfp);
5567 if (!msg)
5568 return;
5569
5570 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_ROAM);
5571 if (!hdr) {
5572 nlmsg_free(msg);
5573 return;
5574 }
5575
5576 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
5577 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5578 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, bssid);
5579 if (req_ie)
5580 NLA_PUT(msg, NL80211_ATTR_REQ_IE, req_ie_len, req_ie);
5581 if (resp_ie)
5582 NLA_PUT(msg, NL80211_ATTR_RESP_IE, resp_ie_len, resp_ie);
5583
5584 if (genlmsg_end(msg, hdr) < 0) {
5585 nlmsg_free(msg);
5586 return;
5587 }
5588
463d0183
JB
5589 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5590 nl80211_mlme_mcgrp.id, gfp);
b23aa676
SO
5591 return;
5592
5593 nla_put_failure:
5594 genlmsg_cancel(msg, hdr);
5595 nlmsg_free(msg);
5596
5597}
5598
5599void nl80211_send_disconnected(struct cfg80211_registered_device *rdev,
5600 struct net_device *netdev, u16 reason,
667503dd 5601 const u8 *ie, size_t ie_len, bool from_ap)
b23aa676
SO
5602{
5603 struct sk_buff *msg;
5604 void *hdr;
5605
667503dd 5606 msg = nlmsg_new(NLMSG_GOODSIZE, GFP_KERNEL);
b23aa676
SO
5607 if (!msg)
5608 return;
5609
5610 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_DISCONNECT);
5611 if (!hdr) {
5612 nlmsg_free(msg);
5613 return;
5614 }
5615
5616 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
5617 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5618 if (from_ap && reason)
5619 NLA_PUT_U16(msg, NL80211_ATTR_REASON_CODE, reason);
5620 if (from_ap)
5621 NLA_PUT_FLAG(msg, NL80211_ATTR_DISCONNECTED_BY_AP);
5622 if (ie)
5623 NLA_PUT(msg, NL80211_ATTR_IE, ie_len, ie);
5624
5625 if (genlmsg_end(msg, hdr) < 0) {
5626 nlmsg_free(msg);
5627 return;
5628 }
5629
463d0183
JB
5630 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5631 nl80211_mlme_mcgrp.id, GFP_KERNEL);
b23aa676
SO
5632 return;
5633
5634 nla_put_failure:
5635 genlmsg_cancel(msg, hdr);
5636 nlmsg_free(msg);
5637
5638}
5639
04a773ad
JB
5640void nl80211_send_ibss_bssid(struct cfg80211_registered_device *rdev,
5641 struct net_device *netdev, const u8 *bssid,
5642 gfp_t gfp)
5643{
5644 struct sk_buff *msg;
5645 void *hdr;
5646
fd2120ca 5647 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, gfp);
04a773ad
JB
5648 if (!msg)
5649 return;
5650
5651 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_JOIN_IBSS);
5652 if (!hdr) {
5653 nlmsg_free(msg);
5654 return;
5655 }
5656
5657 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
5658 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5659 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, bssid);
5660
5661 if (genlmsg_end(msg, hdr) < 0) {
5662 nlmsg_free(msg);
5663 return;
5664 }
5665
463d0183
JB
5666 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5667 nl80211_mlme_mcgrp.id, gfp);
04a773ad
JB
5668 return;
5669
5670 nla_put_failure:
5671 genlmsg_cancel(msg, hdr);
5672 nlmsg_free(msg);
5673}
5674
a3b8b056
JM
5675void nl80211_michael_mic_failure(struct cfg80211_registered_device *rdev,
5676 struct net_device *netdev, const u8 *addr,
5677 enum nl80211_key_type key_type, int key_id,
e6d6e342 5678 const u8 *tsc, gfp_t gfp)
a3b8b056
JM
5679{
5680 struct sk_buff *msg;
5681 void *hdr;
5682
e6d6e342 5683 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, gfp);
a3b8b056
JM
5684 if (!msg)
5685 return;
5686
5687 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_MICHAEL_MIC_FAILURE);
5688 if (!hdr) {
5689 nlmsg_free(msg);
5690 return;
5691 }
5692
5693 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
5694 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5695 if (addr)
5696 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, addr);
5697 NLA_PUT_U32(msg, NL80211_ATTR_KEY_TYPE, key_type);
5698 NLA_PUT_U8(msg, NL80211_ATTR_KEY_IDX, key_id);
5699 if (tsc)
5700 NLA_PUT(msg, NL80211_ATTR_KEY_SEQ, 6, tsc);
5701
5702 if (genlmsg_end(msg, hdr) < 0) {
5703 nlmsg_free(msg);
5704 return;
5705 }
5706
463d0183
JB
5707 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5708 nl80211_mlme_mcgrp.id, gfp);
a3b8b056
JM
5709 return;
5710
5711 nla_put_failure:
5712 genlmsg_cancel(msg, hdr);
5713 nlmsg_free(msg);
5714}
5715
6bad8766
LR
5716void nl80211_send_beacon_hint_event(struct wiphy *wiphy,
5717 struct ieee80211_channel *channel_before,
5718 struct ieee80211_channel *channel_after)
5719{
5720 struct sk_buff *msg;
5721 void *hdr;
5722 struct nlattr *nl_freq;
5723
fd2120ca 5724 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_ATOMIC);
6bad8766
LR
5725 if (!msg)
5726 return;
5727
5728 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_REG_BEACON_HINT);
5729 if (!hdr) {
5730 nlmsg_free(msg);
5731 return;
5732 }
5733
5734 /*
5735 * Since we are applying the beacon hint to a wiphy we know its
5736 * wiphy_idx is valid
5737 */
5738 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, get_wiphy_idx(wiphy));
5739
5740 /* Before */
5741 nl_freq = nla_nest_start(msg, NL80211_ATTR_FREQ_BEFORE);
5742 if (!nl_freq)
5743 goto nla_put_failure;
5744 if (nl80211_msg_put_channel(msg, channel_before))
5745 goto nla_put_failure;
5746 nla_nest_end(msg, nl_freq);
5747
5748 /* After */
5749 nl_freq = nla_nest_start(msg, NL80211_ATTR_FREQ_AFTER);
5750 if (!nl_freq)
5751 goto nla_put_failure;
5752 if (nl80211_msg_put_channel(msg, channel_after))
5753 goto nla_put_failure;
5754 nla_nest_end(msg, nl_freq);
5755
5756 if (genlmsg_end(msg, hdr) < 0) {
5757 nlmsg_free(msg);
5758 return;
5759 }
5760
463d0183
JB
5761 rcu_read_lock();
5762 genlmsg_multicast_allns(msg, 0, nl80211_regulatory_mcgrp.id,
5763 GFP_ATOMIC);
5764 rcu_read_unlock();
6bad8766
LR
5765
5766 return;
5767
5768nla_put_failure:
5769 genlmsg_cancel(msg, hdr);
5770 nlmsg_free(msg);
5771}
5772
9588bbd5
JM
5773static void nl80211_send_remain_on_chan_event(
5774 int cmd, struct cfg80211_registered_device *rdev,
5775 struct net_device *netdev, u64 cookie,
5776 struct ieee80211_channel *chan,
5777 enum nl80211_channel_type channel_type,
5778 unsigned int duration, gfp_t gfp)
5779{
5780 struct sk_buff *msg;
5781 void *hdr;
5782
5783 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, gfp);
5784 if (!msg)
5785 return;
5786
5787 hdr = nl80211hdr_put(msg, 0, 0, 0, cmd);
5788 if (!hdr) {
5789 nlmsg_free(msg);
5790 return;
5791 }
5792
5793 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
5794 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5795 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY_FREQ, chan->center_freq);
5796 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY_CHANNEL_TYPE, channel_type);
5797 NLA_PUT_U64(msg, NL80211_ATTR_COOKIE, cookie);
5798
5799 if (cmd == NL80211_CMD_REMAIN_ON_CHANNEL)
5800 NLA_PUT_U32(msg, NL80211_ATTR_DURATION, duration);
5801
5802 if (genlmsg_end(msg, hdr) < 0) {
5803 nlmsg_free(msg);
5804 return;
5805 }
5806
5807 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5808 nl80211_mlme_mcgrp.id, gfp);
5809 return;
5810
5811 nla_put_failure:
5812 genlmsg_cancel(msg, hdr);
5813 nlmsg_free(msg);
5814}
5815
5816void nl80211_send_remain_on_channel(struct cfg80211_registered_device *rdev,
5817 struct net_device *netdev, u64 cookie,
5818 struct ieee80211_channel *chan,
5819 enum nl80211_channel_type channel_type,
5820 unsigned int duration, gfp_t gfp)
5821{
5822 nl80211_send_remain_on_chan_event(NL80211_CMD_REMAIN_ON_CHANNEL,
5823 rdev, netdev, cookie, chan,
5824 channel_type, duration, gfp);
5825}
5826
5827void nl80211_send_remain_on_channel_cancel(
5828 struct cfg80211_registered_device *rdev, struct net_device *netdev,
5829 u64 cookie, struct ieee80211_channel *chan,
5830 enum nl80211_channel_type channel_type, gfp_t gfp)
5831{
5832 nl80211_send_remain_on_chan_event(NL80211_CMD_CANCEL_REMAIN_ON_CHANNEL,
5833 rdev, netdev, cookie, chan,
5834 channel_type, 0, gfp);
5835}
5836
98b62183
JB
5837void nl80211_send_sta_event(struct cfg80211_registered_device *rdev,
5838 struct net_device *dev, const u8 *mac_addr,
5839 struct station_info *sinfo, gfp_t gfp)
5840{
5841 struct sk_buff *msg;
5842
5843 msg = nlmsg_new(NLMSG_GOODSIZE, gfp);
5844 if (!msg)
5845 return;
5846
5847 if (nl80211_send_station(msg, 0, 0, 0, dev, mac_addr, sinfo) < 0) {
5848 nlmsg_free(msg);
5849 return;
5850 }
5851
5852 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5853 nl80211_mlme_mcgrp.id, gfp);
5854}
5855
026331c4
JM
5856int nl80211_send_action(struct cfg80211_registered_device *rdev,
5857 struct net_device *netdev, u32 nlpid,
5858 int freq, const u8 *buf, size_t len, gfp_t gfp)
5859{
5860 struct sk_buff *msg;
5861 void *hdr;
5862 int err;
5863
5864 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, gfp);
5865 if (!msg)
5866 return -ENOMEM;
5867
5868 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_ACTION);
5869 if (!hdr) {
5870 nlmsg_free(msg);
5871 return -ENOMEM;
5872 }
5873
5874 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
5875 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5876 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY_FREQ, freq);
5877 NLA_PUT(msg, NL80211_ATTR_FRAME, len, buf);
5878
5879 err = genlmsg_end(msg, hdr);
5880 if (err < 0) {
5881 nlmsg_free(msg);
5882 return err;
5883 }
5884
5885 err = genlmsg_unicast(wiphy_net(&rdev->wiphy), msg, nlpid);
5886 if (err < 0)
5887 return err;
5888 return 0;
5889
5890 nla_put_failure:
5891 genlmsg_cancel(msg, hdr);
5892 nlmsg_free(msg);
5893 return -ENOBUFS;
5894}
5895
5896void nl80211_send_action_tx_status(struct cfg80211_registered_device *rdev,
5897 struct net_device *netdev, u64 cookie,
5898 const u8 *buf, size_t len, bool ack,
5899 gfp_t gfp)
5900{
5901 struct sk_buff *msg;
5902 void *hdr;
5903
5904 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, gfp);
5905 if (!msg)
5906 return;
5907
5908 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_ACTION_TX_STATUS);
5909 if (!hdr) {
5910 nlmsg_free(msg);
5911 return;
5912 }
5913
5914 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
5915 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5916 NLA_PUT(msg, NL80211_ATTR_FRAME, len, buf);
5917 NLA_PUT_U64(msg, NL80211_ATTR_COOKIE, cookie);
5918 if (ack)
5919 NLA_PUT_FLAG(msg, NL80211_ATTR_ACK);
5920
5921 if (genlmsg_end(msg, hdr) < 0) {
5922 nlmsg_free(msg);
5923 return;
5924 }
5925
5926 genlmsg_multicast(msg, 0, nl80211_mlme_mcgrp.id, gfp);
5927 return;
5928
5929 nla_put_failure:
5930 genlmsg_cancel(msg, hdr);
5931 nlmsg_free(msg);
5932}
5933
d6dc1a38
JO
5934void
5935nl80211_send_cqm_rssi_notify(struct cfg80211_registered_device *rdev,
5936 struct net_device *netdev,
5937 enum nl80211_cqm_rssi_threshold_event rssi_event,
5938 gfp_t gfp)
5939{
5940 struct sk_buff *msg;
5941 struct nlattr *pinfoattr;
5942 void *hdr;
5943
5944 msg = nlmsg_new(NLMSG_GOODSIZE, gfp);
5945 if (!msg)
5946 return;
5947
5948 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_NOTIFY_CQM);
5949 if (!hdr) {
5950 nlmsg_free(msg);
5951 return;
5952 }
5953
5954 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx);
5955 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, netdev->ifindex);
5956
5957 pinfoattr = nla_nest_start(msg, NL80211_ATTR_CQM);
5958 if (!pinfoattr)
5959 goto nla_put_failure;
5960
5961 NLA_PUT_U32(msg, NL80211_ATTR_CQM_RSSI_THRESHOLD_EVENT,
5962 rssi_event);
5963
5964 nla_nest_end(msg, pinfoattr);
5965
5966 if (genlmsg_end(msg, hdr) < 0) {
5967 nlmsg_free(msg);
5968 return;
5969 }
5970
5971 genlmsg_multicast_netns(wiphy_net(&rdev->wiphy), msg, 0,
5972 nl80211_mlme_mcgrp.id, gfp);
5973 return;
5974
5975 nla_put_failure:
5976 genlmsg_cancel(msg, hdr);
5977 nlmsg_free(msg);
5978}
5979
026331c4
JM
5980static int nl80211_netlink_notify(struct notifier_block * nb,
5981 unsigned long state,
5982 void *_notify)
5983{
5984 struct netlink_notify *notify = _notify;
5985 struct cfg80211_registered_device *rdev;
5986 struct wireless_dev *wdev;
5987
5988 if (state != NETLINK_URELEASE)
5989 return NOTIFY_DONE;
5990
5991 rcu_read_lock();
5992
5993 list_for_each_entry_rcu(rdev, &cfg80211_rdev_list, list)
5994 list_for_each_entry_rcu(wdev, &rdev->netdev_list, list)
5995 cfg80211_mlme_unregister_actions(wdev, notify->pid);
5996
5997 rcu_read_unlock();
5998
5999 return NOTIFY_DONE;
6000}
6001
6002static struct notifier_block nl80211_netlink_notifier = {
6003 .notifier_call = nl80211_netlink_notify,
6004};
6005
55682965
JB
6006/* initialisation/exit functions */
6007
6008int nl80211_init(void)
6009{
0d63cbb5 6010 int err;
55682965 6011
0d63cbb5
MM
6012 err = genl_register_family_with_ops(&nl80211_fam,
6013 nl80211_ops, ARRAY_SIZE(nl80211_ops));
55682965
JB
6014 if (err)
6015 return err;
6016
55682965
JB
6017 err = genl_register_mc_group(&nl80211_fam, &nl80211_config_mcgrp);
6018 if (err)
6019 goto err_out;
6020
2a519311
JB
6021 err = genl_register_mc_group(&nl80211_fam, &nl80211_scan_mcgrp);
6022 if (err)
6023 goto err_out;
6024
73d54c9e
LR
6025 err = genl_register_mc_group(&nl80211_fam, &nl80211_regulatory_mcgrp);
6026 if (err)
6027 goto err_out;
6028
6039f6d2
JM
6029 err = genl_register_mc_group(&nl80211_fam, &nl80211_mlme_mcgrp);
6030 if (err)
6031 goto err_out;
6032
aff89a9b
JB
6033#ifdef CONFIG_NL80211_TESTMODE
6034 err = genl_register_mc_group(&nl80211_fam, &nl80211_testmode_mcgrp);
6035 if (err)
6036 goto err_out;
6037#endif
6038
026331c4
JM
6039 err = netlink_register_notifier(&nl80211_netlink_notifier);
6040 if (err)
6041 goto err_out;
6042
55682965
JB
6043 return 0;
6044 err_out:
6045 genl_unregister_family(&nl80211_fam);
6046 return err;
6047}
6048
6049void nl80211_exit(void)
6050{
026331c4 6051 netlink_unregister_notifier(&nl80211_netlink_notifier);
55682965
JB
6052 genl_unregister_family(&nl80211_fam);
6053}