mac80211: Use monitor configuration flags
[safe/jmp/linux-2.6] / net / mac80211 / cfg.c
1 /*
2  * mac80211 configuration hooks for cfg80211
3  *
4  * Copyright 2006, 2007 Johannes Berg <johannes@sipsolutions.net>
5  *
6  * This file is GPLv2 as found in COPYING.
7  */
8
9 #include <linux/ieee80211.h>
10 #include <linux/nl80211.h>
11 #include <linux/rtnetlink.h>
12 #include <net/net_namespace.h>
13 #include <linux/rcupdate.h>
14 #include <net/cfg80211.h>
15 #include "ieee80211_i.h"
16 #include "cfg.h"
17 #include "ieee80211_rate.h"
18
19 static enum ieee80211_if_types
20 nl80211_type_to_mac80211_type(enum nl80211_iftype type)
21 {
22         switch (type) {
23         case NL80211_IFTYPE_UNSPECIFIED:
24                 return IEEE80211_IF_TYPE_STA;
25         case NL80211_IFTYPE_ADHOC:
26                 return IEEE80211_IF_TYPE_IBSS;
27         case NL80211_IFTYPE_STATION:
28                 return IEEE80211_IF_TYPE_STA;
29         case NL80211_IFTYPE_MONITOR:
30                 return IEEE80211_IF_TYPE_MNTR;
31         default:
32                 return IEEE80211_IF_TYPE_INVALID;
33         }
34 }
35
36 static int ieee80211_add_iface(struct wiphy *wiphy, char *name,
37                                enum nl80211_iftype type, u32 *flags)
38 {
39         struct ieee80211_local *local = wiphy_priv(wiphy);
40         enum ieee80211_if_types itype;
41         struct net_device *dev;
42         struct ieee80211_sub_if_data *sdata;
43         int err;
44
45         if (unlikely(local->reg_state != IEEE80211_DEV_REGISTERED))
46                 return -ENODEV;
47
48         itype = nl80211_type_to_mac80211_type(type);
49         if (itype == IEEE80211_IF_TYPE_INVALID)
50                 return -EINVAL;
51
52         err = ieee80211_if_add(local->mdev, name, &dev, itype);
53         if (err || itype != IEEE80211_IF_TYPE_MNTR || !flags)
54                 return err;
55
56         sdata = IEEE80211_DEV_TO_SUB_IF(dev);
57         sdata->u.mntr_flags = *flags;
58         return 0;
59 }
60
61 static int ieee80211_del_iface(struct wiphy *wiphy, int ifindex)
62 {
63         struct ieee80211_local *local = wiphy_priv(wiphy);
64         struct net_device *dev;
65         char *name;
66
67         if (unlikely(local->reg_state != IEEE80211_DEV_REGISTERED))
68                 return -ENODEV;
69
70         /* we're under RTNL */
71         dev = __dev_get_by_index(&init_net, ifindex);
72         if (!dev)
73                 return 0;
74
75         name = dev->name;
76
77         return ieee80211_if_remove(local->mdev, name, -1);
78 }
79
80 static int ieee80211_change_iface(struct wiphy *wiphy, int ifindex,
81                                   enum nl80211_iftype type, u32 *flags)
82 {
83         struct ieee80211_local *local = wiphy_priv(wiphy);
84         struct net_device *dev;
85         enum ieee80211_if_types itype;
86         struct ieee80211_sub_if_data *sdata;
87
88         if (unlikely(local->reg_state != IEEE80211_DEV_REGISTERED))
89                 return -ENODEV;
90
91         /* we're under RTNL */
92         dev = __dev_get_by_index(&init_net, ifindex);
93         if (!dev)
94                 return -ENODEV;
95
96         if (netif_running(dev))
97                 return -EBUSY;
98
99         itype = nl80211_type_to_mac80211_type(type);
100         if (itype == IEEE80211_IF_TYPE_INVALID)
101                 return -EINVAL;
102
103         sdata = IEEE80211_DEV_TO_SUB_IF(dev);
104
105         if (sdata->vif.type == IEEE80211_IF_TYPE_VLAN)
106                 return -EOPNOTSUPP;
107
108         ieee80211_if_reinit(dev);
109         ieee80211_if_set_type(dev, itype);
110
111         if (sdata->vif.type != IEEE80211_IF_TYPE_MNTR || !flags)
112                 return 0;
113
114         sdata->u.mntr_flags = *flags;
115         return 0;
116 }
117
118 static int ieee80211_add_key(struct wiphy *wiphy, struct net_device *dev,
119                              u8 key_idx, u8 *mac_addr,
120                              struct key_params *params)
121 {
122         struct ieee80211_sub_if_data *sdata;
123         struct sta_info *sta = NULL;
124         enum ieee80211_key_alg alg;
125         int ret;
126
127         sdata = IEEE80211_DEV_TO_SUB_IF(dev);
128
129         switch (params->cipher) {
130         case WLAN_CIPHER_SUITE_WEP40:
131         case WLAN_CIPHER_SUITE_WEP104:
132                 alg = ALG_WEP;
133                 break;
134         case WLAN_CIPHER_SUITE_TKIP:
135                 alg = ALG_TKIP;
136                 break;
137         case WLAN_CIPHER_SUITE_CCMP:
138                 alg = ALG_CCMP;
139                 break;
140         default:
141                 return -EINVAL;
142         }
143
144         if (mac_addr) {
145                 sta = sta_info_get(sdata->local, mac_addr);
146                 if (!sta)
147                         return -ENOENT;
148         }
149
150         ret = 0;
151         if (!ieee80211_key_alloc(sdata, sta, alg, key_idx,
152                                  params->key_len, params->key))
153                 ret = -ENOMEM;
154
155         if (sta)
156                 sta_info_put(sta);
157
158         return ret;
159 }
160
161 static int ieee80211_del_key(struct wiphy *wiphy, struct net_device *dev,
162                              u8 key_idx, u8 *mac_addr)
163 {
164         struct ieee80211_sub_if_data *sdata;
165         struct sta_info *sta;
166         int ret;
167
168         sdata = IEEE80211_DEV_TO_SUB_IF(dev);
169
170         if (mac_addr) {
171                 sta = sta_info_get(sdata->local, mac_addr);
172                 if (!sta)
173                         return -ENOENT;
174
175                 ret = 0;
176                 if (sta->key)
177                         ieee80211_key_free(sta->key);
178                 else
179                         ret = -ENOENT;
180
181                 sta_info_put(sta);
182                 return ret;
183         }
184
185         if (!sdata->keys[key_idx])
186                 return -ENOENT;
187
188         ieee80211_key_free(sdata->keys[key_idx]);
189
190         return 0;
191 }
192
193 static int ieee80211_get_key(struct wiphy *wiphy, struct net_device *dev,
194                              u8 key_idx, u8 *mac_addr, void *cookie,
195                              void (*callback)(void *cookie,
196                                               struct key_params *params))
197 {
198         struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
199         struct sta_info *sta = NULL;
200         u8 seq[6] = {0};
201         struct key_params params;
202         struct ieee80211_key *key;
203         u32 iv32;
204         u16 iv16;
205         int err = -ENOENT;
206
207         if (mac_addr) {
208                 sta = sta_info_get(sdata->local, mac_addr);
209                 if (!sta)
210                         goto out;
211
212                 key = sta->key;
213         } else
214                 key = sdata->keys[key_idx];
215
216         if (!key)
217                 goto out;
218
219         memset(&params, 0, sizeof(params));
220
221         switch (key->conf.alg) {
222         case ALG_TKIP:
223                 params.cipher = WLAN_CIPHER_SUITE_TKIP;
224
225                 iv32 = key->u.tkip.iv32;
226                 iv16 = key->u.tkip.iv16;
227
228                 if (key->flags & KEY_FLAG_UPLOADED_TO_HARDWARE &&
229                     sdata->local->ops->get_tkip_seq)
230                         sdata->local->ops->get_tkip_seq(
231                                 local_to_hw(sdata->local),
232                                 key->conf.hw_key_idx,
233                                 &iv32, &iv16);
234
235                 seq[0] = iv16 & 0xff;
236                 seq[1] = (iv16 >> 8) & 0xff;
237                 seq[2] = iv32 & 0xff;
238                 seq[3] = (iv32 >> 8) & 0xff;
239                 seq[4] = (iv32 >> 16) & 0xff;
240                 seq[5] = (iv32 >> 24) & 0xff;
241                 params.seq = seq;
242                 params.seq_len = 6;
243                 break;
244         case ALG_CCMP:
245                 params.cipher = WLAN_CIPHER_SUITE_CCMP;
246                 seq[0] = key->u.ccmp.tx_pn[5];
247                 seq[1] = key->u.ccmp.tx_pn[4];
248                 seq[2] = key->u.ccmp.tx_pn[3];
249                 seq[3] = key->u.ccmp.tx_pn[2];
250                 seq[4] = key->u.ccmp.tx_pn[1];
251                 seq[5] = key->u.ccmp.tx_pn[0];
252                 params.seq = seq;
253                 params.seq_len = 6;
254                 break;
255         case ALG_WEP:
256                 if (key->conf.keylen == 5)
257                         params.cipher = WLAN_CIPHER_SUITE_WEP40;
258                 else
259                         params.cipher = WLAN_CIPHER_SUITE_WEP104;
260                 break;
261         }
262
263         params.key = key->conf.key;
264         params.key_len = key->conf.keylen;
265
266         callback(cookie, &params);
267         err = 0;
268
269  out:
270         if (sta)
271                 sta_info_put(sta);
272         return err;
273 }
274
275 static int ieee80211_config_default_key(struct wiphy *wiphy,
276                                         struct net_device *dev,
277                                         u8 key_idx)
278 {
279         struct ieee80211_sub_if_data *sdata;
280
281         sdata = IEEE80211_DEV_TO_SUB_IF(dev);
282         ieee80211_set_default_key(sdata, key_idx);
283
284         return 0;
285 }
286
287 static int ieee80211_get_station(struct wiphy *wiphy, struct net_device *dev,
288                                  u8 *mac, struct station_stats *stats)
289 {
290         struct ieee80211_local *local = wdev_priv(dev->ieee80211_ptr);
291         struct sta_info *sta;
292
293         sta = sta_info_get(local, mac);
294         if (!sta)
295                 return -ENOENT;
296
297         /* XXX: verify sta->dev == dev */
298
299         stats->filled = STATION_STAT_INACTIVE_TIME |
300                         STATION_STAT_RX_BYTES |
301                         STATION_STAT_TX_BYTES;
302
303         stats->inactive_time = jiffies_to_msecs(jiffies - sta->last_rx);
304         stats->rx_bytes = sta->rx_bytes;
305         stats->tx_bytes = sta->tx_bytes;
306
307         sta_info_put(sta);
308
309         return 0;
310 }
311
312 /*
313  * This handles both adding a beacon and setting new beacon info
314  */
315 static int ieee80211_config_beacon(struct ieee80211_sub_if_data *sdata,
316                                    struct beacon_parameters *params)
317 {
318         struct beacon_data *new, *old;
319         int new_head_len, new_tail_len;
320         int size;
321         int err = -EINVAL;
322
323         old = sdata->u.ap.beacon;
324
325         /* head must not be zero-length */
326         if (params->head && !params->head_len)
327                 return -EINVAL;
328
329         /*
330          * This is a kludge. beacon interval should really be part
331          * of the beacon information.
332          */
333         if (params->interval) {
334                 sdata->local->hw.conf.beacon_int = params->interval;
335                 if (ieee80211_hw_config(sdata->local))
336                         return -EINVAL;
337                 /*
338                  * We updated some parameter so if below bails out
339                  * it's not an error.
340                  */
341                 err = 0;
342         }
343
344         /* Need to have a beacon head if we don't have one yet */
345         if (!params->head && !old)
346                 return err;
347
348         /* sorry, no way to start beaconing without dtim period */
349         if (!params->dtim_period && !old)
350                 return err;
351
352         /* new or old head? */
353         if (params->head)
354                 new_head_len = params->head_len;
355         else
356                 new_head_len = old->head_len;
357
358         /* new or old tail? */
359         if (params->tail || !old)
360                 /* params->tail_len will be zero for !params->tail */
361                 new_tail_len = params->tail_len;
362         else
363                 new_tail_len = old->tail_len;
364
365         size = sizeof(*new) + new_head_len + new_tail_len;
366
367         new = kzalloc(size, GFP_KERNEL);
368         if (!new)
369                 return -ENOMEM;
370
371         /* start filling the new info now */
372
373         /* new or old dtim period? */
374         if (params->dtim_period)
375                 new->dtim_period = params->dtim_period;
376         else
377                 new->dtim_period = old->dtim_period;
378
379         /*
380          * pointers go into the block we allocated,
381          * memory is | beacon_data | head | tail |
382          */
383         new->head = ((u8 *) new) + sizeof(*new);
384         new->tail = new->head + new_head_len;
385         new->head_len = new_head_len;
386         new->tail_len = new_tail_len;
387
388         /* copy in head */
389         if (params->head)
390                 memcpy(new->head, params->head, new_head_len);
391         else
392                 memcpy(new->head, old->head, new_head_len);
393
394         /* copy in optional tail */
395         if (params->tail)
396                 memcpy(new->tail, params->tail, new_tail_len);
397         else
398                 if (old)
399                         memcpy(new->tail, old->tail, new_tail_len);
400
401         rcu_assign_pointer(sdata->u.ap.beacon, new);
402
403         synchronize_rcu();
404
405         kfree(old);
406
407         return ieee80211_if_config_beacon(sdata->dev);
408 }
409
410 static int ieee80211_add_beacon(struct wiphy *wiphy, struct net_device *dev,
411                                 struct beacon_parameters *params)
412 {
413         struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
414         struct beacon_data *old;
415
416         if (sdata->vif.type != IEEE80211_IF_TYPE_AP)
417                 return -EINVAL;
418
419         old = sdata->u.ap.beacon;
420
421         if (old)
422                 return -EALREADY;
423
424         return ieee80211_config_beacon(sdata, params);
425 }
426
427 static int ieee80211_set_beacon(struct wiphy *wiphy, struct net_device *dev,
428                                 struct beacon_parameters *params)
429 {
430         struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
431         struct beacon_data *old;
432
433         if (sdata->vif.type != IEEE80211_IF_TYPE_AP)
434                 return -EINVAL;
435
436         old = sdata->u.ap.beacon;
437
438         if (!old)
439                 return -ENOENT;
440
441         return ieee80211_config_beacon(sdata, params);
442 }
443
444 static int ieee80211_del_beacon(struct wiphy *wiphy, struct net_device *dev)
445 {
446         struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
447         struct beacon_data *old;
448
449         if (sdata->vif.type != IEEE80211_IF_TYPE_AP)
450                 return -EINVAL;
451
452         old = sdata->u.ap.beacon;
453
454         if (!old)
455                 return -ENOENT;
456
457         rcu_assign_pointer(sdata->u.ap.beacon, NULL);
458         synchronize_rcu();
459         kfree(old);
460
461         return ieee80211_if_config_beacon(dev);
462 }
463
464 /* Layer 2 Update frame (802.2 Type 1 LLC XID Update response) */
465 struct iapp_layer2_update {
466         u8 da[ETH_ALEN];        /* broadcast */
467         u8 sa[ETH_ALEN];        /* STA addr */
468         __be16 len;             /* 6 */
469         u8 dsap;                /* 0 */
470         u8 ssap;                /* 0 */
471         u8 control;
472         u8 xid_info[3];
473 } __attribute__ ((packed));
474
475 static void ieee80211_send_layer2_update(struct sta_info *sta)
476 {
477         struct iapp_layer2_update *msg;
478         struct sk_buff *skb;
479
480         /* Send Level 2 Update Frame to update forwarding tables in layer 2
481          * bridge devices */
482
483         skb = dev_alloc_skb(sizeof(*msg));
484         if (!skb)
485                 return;
486         msg = (struct iapp_layer2_update *)skb_put(skb, sizeof(*msg));
487
488         /* 802.2 Type 1 Logical Link Control (LLC) Exchange Identifier (XID)
489          * Update response frame; IEEE Std 802.2-1998, 5.4.1.2.1 */
490
491         memset(msg->da, 0xff, ETH_ALEN);
492         memcpy(msg->sa, sta->addr, ETH_ALEN);
493         msg->len = htons(6);
494         msg->dsap = 0;
495         msg->ssap = 0x01;       /* NULL LSAP, CR Bit: Response */
496         msg->control = 0xaf;    /* XID response lsb.1111F101.
497                                  * F=0 (no poll command; unsolicited frame) */
498         msg->xid_info[0] = 0x81;        /* XID format identifier */
499         msg->xid_info[1] = 1;   /* LLC types/classes: Type 1 LLC */
500         msg->xid_info[2] = 0;   /* XID sender's receive window size (RW) */
501
502         skb->dev = sta->dev;
503         skb->protocol = eth_type_trans(skb, sta->dev);
504         memset(skb->cb, 0, sizeof(skb->cb));
505         netif_rx(skb);
506 }
507
508 static void sta_apply_parameters(struct ieee80211_local *local,
509                                  struct sta_info *sta,
510                                  struct station_parameters *params)
511 {
512         u32 rates;
513         int i, j;
514         struct ieee80211_supported_band *sband;
515
516         if (params->station_flags & STATION_FLAG_CHANGED) {
517                 sta->flags &= ~WLAN_STA_AUTHORIZED;
518                 if (params->station_flags & STATION_FLAG_AUTHORIZED)
519                         sta->flags |= WLAN_STA_AUTHORIZED;
520
521                 sta->flags &= ~WLAN_STA_SHORT_PREAMBLE;
522                 if (params->station_flags & STATION_FLAG_SHORT_PREAMBLE)
523                         sta->flags |= WLAN_STA_SHORT_PREAMBLE;
524
525                 sta->flags &= ~WLAN_STA_WME;
526                 if (params->station_flags & STATION_FLAG_WME)
527                         sta->flags |= WLAN_STA_WME;
528         }
529
530         if (params->aid) {
531                 sta->aid = params->aid;
532                 if (sta->aid > IEEE80211_MAX_AID)
533                         sta->aid = 0; /* XXX: should this be an error? */
534         }
535
536         if (params->listen_interval >= 0)
537                 sta->listen_interval = params->listen_interval;
538
539         if (params->supported_rates) {
540                 rates = 0;
541                 sband = local->hw.wiphy->bands[local->oper_channel->band];
542
543                 for (i = 0; i < params->supported_rates_len; i++) {
544                         int rate = (params->supported_rates[i] & 0x7f) * 5;
545                         for (j = 0; j < sband->n_bitrates; j++) {
546                                 if (sband->bitrates[j].bitrate == rate)
547                                         rates |= BIT(j);
548                         }
549                 }
550                 sta->supp_rates[local->oper_channel->band] = rates;
551         }
552 }
553
554 static int ieee80211_add_station(struct wiphy *wiphy, struct net_device *dev,
555                                  u8 *mac, struct station_parameters *params)
556 {
557         struct ieee80211_local *local = wdev_priv(dev->ieee80211_ptr);
558         struct sta_info *sta;
559         struct ieee80211_sub_if_data *sdata;
560
561         /* Prevent a race with changing the rate control algorithm */
562         if (!netif_running(dev))
563                 return -ENETDOWN;
564
565         /* XXX: get sta belonging to dev */
566         sta = sta_info_get(local, mac);
567         if (sta) {
568                 sta_info_put(sta);
569                 return -EEXIST;
570         }
571
572         if (params->vlan) {
573                 sdata = IEEE80211_DEV_TO_SUB_IF(params->vlan);
574
575                 if (sdata->vif.type != IEEE80211_IF_TYPE_VLAN ||
576                     sdata->vif.type != IEEE80211_IF_TYPE_AP)
577                         return -EINVAL;
578         } else
579                 sdata = IEEE80211_DEV_TO_SUB_IF(dev);
580
581         sta = sta_info_add(local, dev, mac, GFP_KERNEL);
582         if (!sta)
583                 return -ENOMEM;
584
585         sta->dev = sdata->dev;
586         if (sdata->vif.type == IEEE80211_IF_TYPE_VLAN ||
587             sdata->vif.type == IEEE80211_IF_TYPE_AP)
588                 ieee80211_send_layer2_update(sta);
589
590         sta->flags = WLAN_STA_AUTH | WLAN_STA_ASSOC;
591
592         sta_apply_parameters(local, sta, params);
593
594         rate_control_rate_init(sta, local);
595
596         sta_info_put(sta);
597
598         return 0;
599 }
600
601 static int ieee80211_del_station(struct wiphy *wiphy, struct net_device *dev,
602                                  u8 *mac)
603 {
604         struct ieee80211_local *local = wdev_priv(dev->ieee80211_ptr);
605         struct sta_info *sta;
606
607         if (mac) {
608                 /* XXX: get sta belonging to dev */
609                 sta = sta_info_get(local, mac);
610                 if (!sta)
611                         return -ENOENT;
612
613                 sta_info_free(sta);
614                 sta_info_put(sta);
615         } else
616                 sta_info_flush(local, dev);
617
618         return 0;
619 }
620
621 static int ieee80211_change_station(struct wiphy *wiphy,
622                                     struct net_device *dev,
623                                     u8 *mac,
624                                     struct station_parameters *params)
625 {
626         struct ieee80211_local *local = wdev_priv(dev->ieee80211_ptr);
627         struct sta_info *sta;
628         struct ieee80211_sub_if_data *vlansdata;
629
630         /* XXX: get sta belonging to dev */
631         sta = sta_info_get(local, mac);
632         if (!sta)
633                 return -ENOENT;
634
635         if (params->vlan && params->vlan != sta->dev) {
636                 vlansdata = IEEE80211_DEV_TO_SUB_IF(params->vlan);
637
638                 if (vlansdata->vif.type != IEEE80211_IF_TYPE_VLAN ||
639                     vlansdata->vif.type != IEEE80211_IF_TYPE_AP)
640                         return -EINVAL;
641
642                 sta->dev = params->vlan;
643                 ieee80211_send_layer2_update(sta);
644         }
645
646         sta_apply_parameters(local, sta, params);
647
648         sta_info_put(sta);
649
650         return 0;
651 }
652
653 struct cfg80211_ops mac80211_config_ops = {
654         .add_virtual_intf = ieee80211_add_iface,
655         .del_virtual_intf = ieee80211_del_iface,
656         .change_virtual_intf = ieee80211_change_iface,
657         .add_key = ieee80211_add_key,
658         .del_key = ieee80211_del_key,
659         .get_key = ieee80211_get_key,
660         .set_default_key = ieee80211_config_default_key,
661         .add_beacon = ieee80211_add_beacon,
662         .set_beacon = ieee80211_set_beacon,
663         .del_beacon = ieee80211_del_beacon,
664         .add_station = ieee80211_add_station,
665         .del_station = ieee80211_del_station,
666         .change_station = ieee80211_change_station,
667         .get_station = ieee80211_get_station,
668 };