Add support for specifying subset of enabled frequencies to scan
[libeap.git] / src / drivers / driver_nl80211.c
1 /*
2  * WPA Supplicant - driver interaction with Linux nl80211/cfg80211
3  * Copyright (c) 2003-2008, Jouni Malinen <j@w1.fi>
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License version 2 as
7  * published by the Free Software Foundation.
8  *
9  * Alternatively, this software may be distributed under the terms of BSD
10  * license.
11  *
12  * See README and COPYING for more details.
13  */
14
15 #include "includes.h"
16 #include <sys/ioctl.h>
17 #include <net/if_arp.h>
18 #include <netlink/genl/genl.h>
19 #include <netlink/genl/family.h>
20 #include <netlink/genl/ctrl.h>
21 #include "nl80211_copy.h"
22 #include "wireless_copy.h"
23
24 #include "common.h"
25 #include "driver.h"
26 #include "eloop.h"
27 #include "ieee802_11_defs.h"
28
29 #ifndef IFF_LOWER_UP
30 #define IFF_LOWER_UP   0x10000         /* driver signals L1 up         */
31 #endif
32 #ifndef IFF_DORMANT
33 #define IFF_DORMANT    0x20000         /* driver signals dormant       */
34 #endif
35
36 #ifndef IF_OPER_DORMANT
37 #define IF_OPER_DORMANT 5
38 #endif
39 #ifndef IF_OPER_UP
40 #define IF_OPER_UP 6
41 #endif
42
43
44 #ifndef NO_WEXT_COMPAT
45 /*
46  * Fall back to WEXT association, if the kernel does not support nl80211 MLME
47  * commands. This is temporary backwards compatibility version that will be
48  * removed at some point.
49  */
50 #define WEXT_COMPAT
51 #endif /* NO_WEXT_COMPAT */
52
53
54 struct wpa_driver_nl80211_data {
55         void *ctx;
56         int wext_event_sock;
57         int ioctl_sock;
58         char ifname[IFNAMSIZ + 1];
59         int ifindex;
60         int if_removed;
61         struct wpa_driver_capa capa;
62         int has_capability;
63         int we_version_compiled;
64
65 #ifdef WEXT_COMPAT
66         u8 *assoc_req_ies;
67         size_t assoc_req_ies_len;
68         u8 *assoc_resp_ies;
69         size_t assoc_resp_ies_len;
70
71         /* for set_auth_alg fallback */
72         int use_crypt;
73         int auth_alg_fallback;
74 #endif /* WEXT_COMPAT */
75
76         int operstate;
77
78         char mlmedev[IFNAMSIZ + 1];
79
80         int scan_complete_events;
81
82         struct nl_handle *nl_handle;
83         struct nl_cache *nl_cache;
84         struct nl_cb *nl_cb;
85         struct genl_family *nl80211;
86
87         u8 bssid[ETH_ALEN];
88         int associated;
89         u8 ssid[32];
90         size_t ssid_len;
91 };
92
93
94 static void wpa_driver_nl80211_scan_timeout(void *eloop_ctx,
95                                             void *timeout_ctx);
96 static int wpa_driver_nl80211_set_mode(struct wpa_driver_nl80211_data *drv,
97                                        int mode);
98 #ifdef WEXT_COMPAT
99 static int wpa_driver_nl80211_flush_pmkid(void *priv);
100 #endif /* WEXT_COMPAT */
101 static int wpa_driver_nl80211_get_range(void *priv);
102 static int
103 wpa_driver_nl80211_finish_drv_init(struct wpa_driver_nl80211_data *drv);
104
105
106 /* nl80211 code */
107 static int ack_handler(struct nl_msg *msg, void *arg)
108 {
109         int *err = arg;
110         *err = 0;
111         return NL_STOP;
112 }
113
114 static int finish_handler(struct nl_msg *msg, void *arg)
115 {
116         int *ret = arg;
117         *ret = 0;
118         return NL_SKIP;
119 }
120
121 static int error_handler(struct sockaddr_nl *nla, struct nlmsgerr *err,
122                          void *arg)
123 {
124         int *ret = arg;
125         *ret = err->error;
126         return NL_SKIP;
127 }
128
129 static int send_and_recv_msgs(struct wpa_driver_nl80211_data *drv,
130                               struct nl_msg *msg,
131                               int (*valid_handler)(struct nl_msg *, void *),
132                               void *valid_data)
133 {
134         struct nl_cb *cb;
135         int err = -ENOMEM;
136
137         cb = nl_cb_clone(drv->nl_cb);
138         if (!cb)
139                 goto out;
140
141         err = nl_send_auto_complete(drv->nl_handle, msg);
142         if (err < 0)
143                 goto out;
144
145         err = 1;
146
147         nl_cb_err(cb, NL_CB_CUSTOM, error_handler, &err);
148         nl_cb_set(cb, NL_CB_FINISH, NL_CB_CUSTOM, finish_handler, &err);
149         nl_cb_set(cb, NL_CB_ACK, NL_CB_CUSTOM, ack_handler, &err);
150
151         if (valid_handler)
152                 nl_cb_set(cb, NL_CB_VALID, NL_CB_CUSTOM,
153                           valid_handler, valid_data);
154
155         while (err > 0)
156                 nl_recvmsgs(drv->nl_handle, cb);
157  out:
158         nl_cb_put(cb);
159         nlmsg_free(msg);
160         return err;
161 }
162
163
164 struct family_data {
165         const char *group;
166         int id;
167 };
168
169
170 static int family_handler(struct nl_msg *msg, void *arg)
171 {
172         struct family_data *res = arg;
173         struct nlattr *tb[CTRL_ATTR_MAX + 1];
174         struct genlmsghdr *gnlh = nlmsg_data(nlmsg_hdr(msg));
175         struct nlattr *mcgrp;
176         int i;
177
178         nla_parse(tb, CTRL_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
179                   genlmsg_attrlen(gnlh, 0), NULL);
180         if (!tb[CTRL_ATTR_MCAST_GROUPS])
181                 return NL_SKIP;
182
183         nla_for_each_nested(mcgrp, tb[CTRL_ATTR_MCAST_GROUPS], i) {
184                 struct nlattr *tb2[CTRL_ATTR_MCAST_GRP_MAX + 1];
185                 nla_parse(tb2, CTRL_ATTR_MCAST_GRP_MAX, nla_data(mcgrp),
186                           nla_len(mcgrp), NULL);
187                 if (!tb2[CTRL_ATTR_MCAST_GRP_NAME] ||
188                     !tb2[CTRL_ATTR_MCAST_GRP_ID] ||
189                     os_strncmp(nla_data(tb2[CTRL_ATTR_MCAST_GRP_NAME]),
190                                res->group,
191                                nla_len(tb2[CTRL_ATTR_MCAST_GRP_NAME])) != 0)
192                         continue;
193                 res->id = nla_get_u32(tb2[CTRL_ATTR_MCAST_GRP_ID]);
194                 break;
195         };
196
197         return NL_SKIP;
198 }
199
200
201 static int nl_get_multicast_id(struct wpa_driver_nl80211_data *drv,
202                                const char *family, const char *group)
203 {
204         struct nl_msg *msg;
205         int ret = -1;
206         struct family_data res = { group, -ENOENT };
207
208         msg = nlmsg_alloc();
209         if (!msg)
210                 return -ENOMEM;
211         genlmsg_put(msg, 0, 0, genl_ctrl_resolve(drv->nl_handle, "nlctrl"),
212                     0, 0, CTRL_CMD_GETFAMILY, 0);
213         NLA_PUT_STRING(msg, CTRL_ATTR_FAMILY_NAME, family);
214
215         ret = send_and_recv_msgs(drv, msg, family_handler, &res);
216         msg = NULL;
217         if (ret == 0)
218                 ret = res.id;
219
220 nla_put_failure:
221         nlmsg_free(msg);
222         return ret;
223 }
224
225
226 static int wpa_driver_nl80211_send_oper_ifla(
227         struct wpa_driver_nl80211_data *drv,
228         int linkmode, int operstate)
229 {
230         struct {
231                 struct nlmsghdr hdr;
232                 struct ifinfomsg ifinfo;
233                 char opts[16];
234         } req;
235         struct rtattr *rta;
236         static int nl_seq;
237         ssize_t ret;
238
239         os_memset(&req, 0, sizeof(req));
240
241         req.hdr.nlmsg_len = NLMSG_LENGTH(sizeof(struct ifinfomsg));
242         req.hdr.nlmsg_type = RTM_SETLINK;
243         req.hdr.nlmsg_flags = NLM_F_REQUEST;
244         req.hdr.nlmsg_seq = ++nl_seq;
245         req.hdr.nlmsg_pid = 0;
246
247         req.ifinfo.ifi_family = AF_UNSPEC;
248         req.ifinfo.ifi_type = 0;
249         req.ifinfo.ifi_index = drv->ifindex;
250         req.ifinfo.ifi_flags = 0;
251         req.ifinfo.ifi_change = 0;
252
253         if (linkmode != -1) {
254                 rta = (struct rtattr *)
255                         ((char *) &req + NLMSG_ALIGN(req.hdr.nlmsg_len));
256                 rta->rta_type = IFLA_LINKMODE;
257                 rta->rta_len = RTA_LENGTH(sizeof(char));
258                 *((char *) RTA_DATA(rta)) = linkmode;
259                 req.hdr.nlmsg_len = NLMSG_ALIGN(req.hdr.nlmsg_len) +
260                         RTA_LENGTH(sizeof(char));
261         }
262         if (operstate != -1) {
263                 rta = (struct rtattr *)
264                         ((char *) &req + NLMSG_ALIGN(req.hdr.nlmsg_len));
265                 rta->rta_type = IFLA_OPERSTATE;
266                 rta->rta_len = RTA_LENGTH(sizeof(char));
267                 *((char *) RTA_DATA(rta)) = operstate;
268                 req.hdr.nlmsg_len = NLMSG_ALIGN(req.hdr.nlmsg_len) +
269                         RTA_LENGTH(sizeof(char));
270         }
271
272         wpa_printf(MSG_DEBUG, "WEXT: Operstate: linkmode=%d, operstate=%d",
273                    linkmode, operstate);
274
275         ret = send(drv->wext_event_sock, &req, req.hdr.nlmsg_len, 0);
276         if (ret < 0) {
277                 wpa_printf(MSG_DEBUG, "WEXT: Sending operstate IFLA failed: "
278                            "%s (assume operstate is not supported)",
279                            strerror(errno));
280         }
281
282         return ret < 0 ? -1 : 0;
283 }
284
285
286 static int wpa_driver_nl80211_set_auth_param(
287         struct wpa_driver_nl80211_data *drv, int idx, u32 value)
288 {
289         struct iwreq iwr;
290         int ret = 0;
291
292         os_memset(&iwr, 0, sizeof(iwr));
293         os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
294         iwr.u.param.flags = idx & IW_AUTH_INDEX;
295         iwr.u.param.value = value;
296
297         if (ioctl(drv->ioctl_sock, SIOCSIWAUTH, &iwr) < 0) {
298                 if (errno != EOPNOTSUPP) {
299                         wpa_printf(MSG_DEBUG, "WEXT: SIOCSIWAUTH(param %d "
300                                    "value 0x%x) failed: %s)",
301                                    idx, value, strerror(errno));
302                 }
303                 ret = errno == EOPNOTSUPP ? -2 : -1;
304         }
305
306         return ret;
307 }
308
309
310 static int wpa_driver_nl80211_get_bssid(void *priv, u8 *bssid)
311 {
312         struct wpa_driver_nl80211_data *drv = priv;
313 #ifdef WEXT_COMPAT
314         if (!(drv->capa.flags & WPA_DRIVER_FLAGS_SME)) {
315                 struct iwreq iwr;
316                 int ret = 0;
317
318                 os_memset(&iwr, 0, sizeof(iwr));
319                 os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
320
321                 if (ioctl(drv->ioctl_sock, SIOCGIWAP, &iwr) < 0) {
322                         perror("ioctl[SIOCGIWAP]");
323                         ret = -1;
324                 }
325                 os_memcpy(bssid, iwr.u.ap_addr.sa_data, ETH_ALEN);
326
327                 return ret;
328         }
329 #endif /* WEXT_COMPAT */
330         if (!drv->associated)
331                 return -1;
332         os_memcpy(bssid, drv->bssid, ETH_ALEN);
333         return 0;
334 }
335
336
337 #ifdef WEXT_COMPAT
338 static int wpa_driver_nl80211_set_bssid(void *priv, const u8 *bssid)
339 {
340         struct wpa_driver_nl80211_data *drv = priv;
341         struct iwreq iwr;
342         int ret = 0;
343
344         os_memset(&iwr, 0, sizeof(iwr));
345         os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
346         iwr.u.ap_addr.sa_family = ARPHRD_ETHER;
347         if (bssid)
348                 os_memcpy(iwr.u.ap_addr.sa_data, bssid, ETH_ALEN);
349         else
350                 os_memset(iwr.u.ap_addr.sa_data, 0, ETH_ALEN);
351
352         if (ioctl(drv->ioctl_sock, SIOCSIWAP, &iwr) < 0) {
353                 perror("ioctl[SIOCSIWAP]");
354                 ret = -1;
355         }
356
357         return ret;
358 }
359 #endif /* WEXT_COMPAT */
360
361
362 static int wpa_driver_nl80211_get_ssid(void *priv, u8 *ssid)
363 {
364         struct wpa_driver_nl80211_data *drv = priv;
365 #ifdef WEXT_COMPAT
366         if (!(drv->capa.flags & WPA_DRIVER_FLAGS_SME)) {
367                 struct iwreq iwr;
368                 int ret = 0;
369
370                 os_memset(&iwr, 0, sizeof(iwr));
371                 os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
372                 iwr.u.essid.pointer = (caddr_t) ssid;
373                 iwr.u.essid.length = 32;
374
375                 if (ioctl(drv->ioctl_sock, SIOCGIWESSID, &iwr) < 0) {
376                         perror("ioctl[SIOCGIWESSID]");
377                         ret = -1;
378                 } else {
379                         ret = iwr.u.essid.length;
380                         if (ret > 32)
381                                 ret = 32;
382                         /*
383                          * Some drivers include nul termination in the SSID, so
384                          * let's remove it here before further processing.
385                          * WE-21 changes this to explicitly require the length
386                          * _not_ to include nul termination.
387                          */
388                         if (ret > 0 && ssid[ret - 1] == '\0' &&
389                             drv->we_version_compiled < 21)
390                                 ret--;
391                 }
392
393                 return ret;
394         }
395 #endif /* WEXT_COMPAT */
396         if (!drv->associated)
397                 return -1;
398         os_memcpy(ssid, drv->ssid, drv->ssid_len);
399         return drv->ssid_len;
400 }
401
402
403 #ifdef WEXT_COMPAT
404 static int wpa_driver_nl80211_set_ssid(void *priv, const u8 *ssid,
405                                        size_t ssid_len)
406 {
407         struct wpa_driver_nl80211_data *drv = priv;
408         struct iwreq iwr;
409         int ret = 0;
410         char buf[33];
411
412         if (ssid_len > 32)
413                 return -1;
414
415         os_memset(&iwr, 0, sizeof(iwr));
416         os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
417         /* flags: 1 = ESSID is active, 0 = not (promiscuous) */
418         iwr.u.essid.flags = (ssid_len != 0);
419         os_memset(buf, 0, sizeof(buf));
420         os_memcpy(buf, ssid, ssid_len);
421         iwr.u.essid.pointer = (caddr_t) buf;
422         if (drv->we_version_compiled < 21) {
423                 /* For historic reasons, set SSID length to include one extra
424                  * character, C string nul termination, even though SSID is
425                  * really an octet string that should not be presented as a C
426                  * string. Some Linux drivers decrement the length by one and
427                  * can thus end up missing the last octet of the SSID if the
428                  * length is not incremented here. WE-21 changes this to
429                  * explicitly require the length _not_ to include nul
430                  * termination. */
431                 if (ssid_len)
432                         ssid_len++;
433         }
434         iwr.u.essid.length = ssid_len;
435
436         if (ioctl(drv->ioctl_sock, SIOCSIWESSID, &iwr) < 0) {
437                 perror("ioctl[SIOCSIWESSID]");
438                 ret = -1;
439         }
440
441         return ret;
442 }
443
444
445 static int wpa_driver_nl80211_set_freq(void *priv, int freq)
446 {
447         struct wpa_driver_nl80211_data *drv = priv;
448         struct iwreq iwr;
449         int ret = 0;
450
451         os_memset(&iwr, 0, sizeof(iwr));
452         os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
453         iwr.u.freq.m = freq * 100000;
454         iwr.u.freq.e = 1;
455
456         if (ioctl(drv->ioctl_sock, SIOCSIWFREQ, &iwr) < 0) {
457                 perror("ioctl[SIOCSIWFREQ]");
458                 ret = -1;
459         }
460
461         return ret;
462 }
463
464
465 static void
466 wpa_driver_nl80211_event_wireless_custom(void *ctx, char *custom)
467 {
468         union wpa_event_data data;
469
470         wpa_printf(MSG_MSGDUMP, "WEXT: Custom wireless event: '%s'",
471                    custom);
472
473         os_memset(&data, 0, sizeof(data));
474         /* Host AP driver */
475         if (os_strncmp(custom, "MLME-MICHAELMICFAILURE.indication", 33) == 0) {
476                 data.michael_mic_failure.unicast =
477                         os_strstr(custom, " unicast ") != NULL;
478                 /* TODO: parse parameters(?) */
479                 wpa_supplicant_event(ctx, EVENT_MICHAEL_MIC_FAILURE, &data);
480         } else if (os_strncmp(custom, "ASSOCINFO(ReqIEs=", 17) == 0) {
481                 char *spos;
482                 int bytes;
483
484                 spos = custom + 17;
485
486                 bytes = strspn(spos, "0123456789abcdefABCDEF");
487                 if (!bytes || (bytes & 1))
488                         return;
489                 bytes /= 2;
490
491                 data.assoc_info.req_ies = os_malloc(bytes);
492                 if (data.assoc_info.req_ies == NULL)
493                         return;
494
495                 data.assoc_info.req_ies_len = bytes;
496                 hexstr2bin(spos, data.assoc_info.req_ies, bytes);
497
498                 spos += bytes * 2;
499
500                 data.assoc_info.resp_ies = NULL;
501                 data.assoc_info.resp_ies_len = 0;
502
503                 if (os_strncmp(spos, " RespIEs=", 9) == 0) {
504                         spos += 9;
505
506                         bytes = strspn(spos, "0123456789abcdefABCDEF");
507                         if (!bytes || (bytes & 1))
508                                 goto done;
509                         bytes /= 2;
510
511                         data.assoc_info.resp_ies = os_malloc(bytes);
512                         if (data.assoc_info.resp_ies == NULL)
513                                 goto done;
514
515                         data.assoc_info.resp_ies_len = bytes;
516                         hexstr2bin(spos, data.assoc_info.resp_ies, bytes);
517                 }
518
519                 wpa_supplicant_event(ctx, EVENT_ASSOCINFO, &data);
520
521         done:
522                 os_free(data.assoc_info.resp_ies);
523                 os_free(data.assoc_info.req_ies);
524 #ifdef CONFIG_PEERKEY
525         } else if (os_strncmp(custom, "STKSTART.request=", 17) == 0) {
526                 if (hwaddr_aton(custom + 17, data.stkstart.peer)) {
527                         wpa_printf(MSG_DEBUG, "WEXT: unrecognized "
528                                    "STKSTART.request '%s'", custom + 17);
529                         return;
530                 }
531                 wpa_supplicant_event(ctx, EVENT_STKSTART, &data);
532 #endif /* CONFIG_PEERKEY */
533         }
534 }
535 #endif /* WEXT_COMPAT */
536
537
538 static int wpa_driver_nl80211_event_wireless_michaelmicfailure(
539         void *ctx, const char *ev, size_t len)
540 {
541         const struct iw_michaelmicfailure *mic;
542         union wpa_event_data data;
543
544         if (len < sizeof(*mic))
545                 return -1;
546
547         mic = (const struct iw_michaelmicfailure *) ev;
548
549         wpa_printf(MSG_DEBUG, "Michael MIC failure wireless event: "
550                    "flags=0x%x src_addr=" MACSTR, mic->flags,
551                    MAC2STR(mic->src_addr.sa_data));
552
553         os_memset(&data, 0, sizeof(data));
554         data.michael_mic_failure.unicast = !(mic->flags & IW_MICFAILURE_GROUP);
555         wpa_supplicant_event(ctx, EVENT_MICHAEL_MIC_FAILURE, &data);
556
557         return 0;
558 }
559
560
561 #ifdef WEXT_COMPAT
562 static int wpa_driver_nl80211_event_wireless_pmkidcand(
563         struct wpa_driver_nl80211_data *drv, const char *ev, size_t len)
564 {
565         const struct iw_pmkid_cand *cand;
566         union wpa_event_data data;
567         const u8 *addr;
568
569         if (len < sizeof(*cand))
570                 return -1;
571
572         cand = (const struct iw_pmkid_cand *) ev;
573         addr = (const u8 *) cand->bssid.sa_data;
574
575         wpa_printf(MSG_DEBUG, "PMKID candidate wireless event: "
576                    "flags=0x%x index=%d bssid=" MACSTR, cand->flags,
577                    cand->index, MAC2STR(addr));
578
579         os_memset(&data, 0, sizeof(data));
580         os_memcpy(data.pmkid_candidate.bssid, addr, ETH_ALEN);
581         data.pmkid_candidate.index = cand->index;
582         data.pmkid_candidate.preauth = cand->flags & IW_PMKID_CAND_PREAUTH;
583         wpa_supplicant_event(drv->ctx, EVENT_PMKID_CANDIDATE, &data);
584
585         return 0;
586 }
587
588
589 static int wpa_driver_nl80211_event_wireless_assocreqie(
590         struct wpa_driver_nl80211_data *drv, const char *ev, int len)
591 {
592         if (len < 0)
593                 return -1;
594
595         wpa_hexdump(MSG_DEBUG, "AssocReq IE wireless event", (const u8 *) ev,
596                     len);
597         os_free(drv->assoc_req_ies);
598         drv->assoc_req_ies = os_malloc(len);
599         if (drv->assoc_req_ies == NULL) {
600                 drv->assoc_req_ies_len = 0;
601                 return -1;
602         }
603         os_memcpy(drv->assoc_req_ies, ev, len);
604         drv->assoc_req_ies_len = len;
605
606         return 0;
607 }
608
609
610 static int wpa_driver_nl80211_event_wireless_assocrespie(
611         struct wpa_driver_nl80211_data *drv, const char *ev, int len)
612 {
613         if (len < 0)
614                 return -1;
615
616         wpa_hexdump(MSG_DEBUG, "AssocResp IE wireless event", (const u8 *) ev,
617                     len);
618         os_free(drv->assoc_resp_ies);
619         drv->assoc_resp_ies = os_malloc(len);
620         if (drv->assoc_resp_ies == NULL) {
621                 drv->assoc_resp_ies_len = 0;
622                 return -1;
623         }
624         os_memcpy(drv->assoc_resp_ies, ev, len);
625         drv->assoc_resp_ies_len = len;
626
627         return 0;
628 }
629
630
631 static void wpa_driver_nl80211_event_assoc_ies(struct wpa_driver_nl80211_data *drv)
632 {
633         union wpa_event_data data;
634
635         if (drv->assoc_req_ies == NULL && drv->assoc_resp_ies == NULL)
636                 return;
637
638         os_memset(&data, 0, sizeof(data));
639         if (drv->assoc_req_ies) {
640                 data.assoc_info.req_ies = drv->assoc_req_ies;
641                 drv->assoc_req_ies = NULL;
642                 data.assoc_info.req_ies_len = drv->assoc_req_ies_len;
643         }
644         if (drv->assoc_resp_ies) {
645                 data.assoc_info.resp_ies = drv->assoc_resp_ies;
646                 drv->assoc_resp_ies = NULL;
647                 data.assoc_info.resp_ies_len = drv->assoc_resp_ies_len;
648         }
649
650         wpa_supplicant_event(drv->ctx, EVENT_ASSOCINFO, &data);
651
652         os_free(data.assoc_info.req_ies);
653         os_free(data.assoc_info.resp_ies);
654 }
655 #endif /* WEXT_COMPAT */
656
657
658 static void wpa_driver_nl80211_event_wireless(struct wpa_driver_nl80211_data *drv,
659                                            void *ctx, char *data, int len)
660 {
661         struct iw_event iwe_buf, *iwe = &iwe_buf;
662         char *pos, *end, *custom;
663 #ifdef WEXT_COMPAT
664         char *buf;
665 #endif /* WEXT_COMPAT */
666
667         pos = data;
668         end = data + len;
669
670         while (pos + IW_EV_LCP_LEN <= end) {
671                 /* Event data may be unaligned, so make a local, aligned copy
672                  * before processing. */
673                 os_memcpy(&iwe_buf, pos, IW_EV_LCP_LEN);
674                 wpa_printf(MSG_DEBUG, "Wireless event: cmd=0x%x len=%d",
675                            iwe->cmd, iwe->len);
676                 if (iwe->len <= IW_EV_LCP_LEN)
677                         return;
678
679                 custom = pos + IW_EV_POINT_LEN;
680                 if (drv->we_version_compiled > 18 &&
681                     (iwe->cmd == IWEVMICHAELMICFAILURE ||
682                      iwe->cmd == IWEVCUSTOM ||
683                      iwe->cmd == IWEVASSOCREQIE ||
684                      iwe->cmd == IWEVASSOCRESPIE ||
685                      iwe->cmd == IWEVPMKIDCAND)) {
686                         /* WE-19 removed the pointer from struct iw_point */
687                         char *dpos = (char *) &iwe_buf.u.data.length;
688                         int dlen = dpos - (char *) &iwe_buf;
689                         os_memcpy(dpos, pos + IW_EV_LCP_LEN,
690                                   sizeof(struct iw_event) - dlen);
691                 } else {
692                         os_memcpy(&iwe_buf, pos, sizeof(struct iw_event));
693                         custom += IW_EV_POINT_OFF;
694                 }
695
696                 switch (iwe->cmd) {
697 #ifdef WEXT_COMPAT
698                 case SIOCGIWAP:
699                         if (drv->capa.flags & WPA_DRIVER_FLAGS_SME)
700                                 break;
701                         wpa_printf(MSG_DEBUG, "Wireless event: new AP: "
702                                    MACSTR,
703                                    MAC2STR((u8 *) iwe->u.ap_addr.sa_data));
704                         if (is_zero_ether_addr(
705                                     (const u8 *) iwe->u.ap_addr.sa_data) ||
706                             os_memcmp(iwe->u.ap_addr.sa_data,
707                                       "\x44\x44\x44\x44\x44\x44", ETH_ALEN) ==
708                             0) {
709                                 os_free(drv->assoc_req_ies);
710                                 drv->assoc_req_ies = NULL;
711                                 os_free(drv->assoc_resp_ies);
712                                 drv->assoc_resp_ies = NULL;
713                                 wpa_supplicant_event(ctx, EVENT_DISASSOC,
714                                                      NULL);
715                         
716                         } else {
717                                 wpa_driver_nl80211_event_assoc_ies(drv);
718                                 wpa_supplicant_event(ctx, EVENT_ASSOC, NULL);
719                         }
720                         break;
721 #endif /* WEXT_COMPAT */
722                 case IWEVMICHAELMICFAILURE:
723                         wpa_driver_nl80211_event_wireless_michaelmicfailure(
724                                 ctx, custom, iwe->u.data.length);
725                         break;
726 #ifdef WEXT_COMPAT
727                 case IWEVCUSTOM:
728                         if (drv->capa.flags & WPA_DRIVER_FLAGS_SME)
729                                 break;
730                         if (custom + iwe->u.data.length > end)
731                                 return;
732                         buf = os_malloc(iwe->u.data.length + 1);
733                         if (buf == NULL)
734                                 return;
735                         os_memcpy(buf, custom, iwe->u.data.length);
736                         buf[iwe->u.data.length] = '\0';
737                         wpa_driver_nl80211_event_wireless_custom(ctx, buf);
738                         os_free(buf);
739                         break;
740                 case IWEVASSOCREQIE:
741                         if (drv->capa.flags & WPA_DRIVER_FLAGS_SME)
742                                 break;
743                         wpa_driver_nl80211_event_wireless_assocreqie(
744                                 drv, custom, iwe->u.data.length);
745                         break;
746                 case IWEVASSOCRESPIE:
747                         if (drv->capa.flags & WPA_DRIVER_FLAGS_SME)
748                                 break;
749                         wpa_driver_nl80211_event_wireless_assocrespie(
750                                 drv, custom, iwe->u.data.length);
751                         break;
752                 case IWEVPMKIDCAND:
753                         wpa_driver_nl80211_event_wireless_pmkidcand(
754                                 drv, custom, iwe->u.data.length);
755                         break;
756 #endif /* WEXT_COMPAT */
757                 }
758
759                 pos += iwe->len;
760         }
761 }
762
763
764 static void wpa_driver_nl80211_event_link(struct wpa_driver_nl80211_data *drv,
765                                           void *ctx, char *buf, size_t len,
766                                           int del)
767 {
768         union wpa_event_data event;
769
770         os_memset(&event, 0, sizeof(event));
771         if (len > sizeof(event.interface_status.ifname))
772                 len = sizeof(event.interface_status.ifname) - 1;
773         os_memcpy(event.interface_status.ifname, buf, len);
774         event.interface_status.ievent = del ? EVENT_INTERFACE_REMOVED :
775                 EVENT_INTERFACE_ADDED;
776
777         wpa_printf(MSG_DEBUG, "RTM_%sLINK, IFLA_IFNAME: Interface '%s' %s",
778                    del ? "DEL" : "NEW",
779                    event.interface_status.ifname,
780                    del ? "removed" : "added");
781
782         if (os_strcmp(drv->ifname, event.interface_status.ifname) == 0) {
783                 if (del)
784                         drv->if_removed = 1;
785                 else
786                         drv->if_removed = 0;
787         }
788
789         wpa_supplicant_event(ctx, EVENT_INTERFACE_STATUS, &event);
790 }
791
792
793 static int wpa_driver_nl80211_own_ifname(struct wpa_driver_nl80211_data *drv,
794                                          struct nlmsghdr *h)
795 {
796         struct ifinfomsg *ifi;
797         int attrlen, _nlmsg_len, rta_len;
798         struct rtattr *attr;
799
800         ifi = NLMSG_DATA(h);
801
802         _nlmsg_len = NLMSG_ALIGN(sizeof(struct ifinfomsg));
803
804         attrlen = h->nlmsg_len - _nlmsg_len;
805         if (attrlen < 0)
806                 return 0;
807
808         attr = (struct rtattr *) (((char *) ifi) + _nlmsg_len);
809
810         rta_len = RTA_ALIGN(sizeof(struct rtattr));
811         while (RTA_OK(attr, attrlen)) {
812                 if (attr->rta_type == IFLA_IFNAME) {
813                         if (os_strcmp(((char *) attr) + rta_len, drv->ifname)
814                             == 0)
815                                 return 1;
816                         else
817                                 break;
818                 }
819                 attr = RTA_NEXT(attr, attrlen);
820         }
821
822         return 0;
823 }
824
825
826 static int wpa_driver_nl80211_own_ifindex(struct wpa_driver_nl80211_data *drv,
827                                           int ifindex, struct nlmsghdr *h)
828 {
829         if (drv->ifindex == ifindex)
830                 return 1;
831
832         if (drv->if_removed && wpa_driver_nl80211_own_ifname(drv, h)) {
833                 drv->ifindex = if_nametoindex(drv->ifname);
834                 wpa_printf(MSG_DEBUG, "nl80211: Update ifindex for a removed "
835                            "interface");
836                 wpa_driver_nl80211_finish_drv_init(drv);
837                 return 1;
838         }
839
840         return 0;
841 }
842
843
844 static void wpa_driver_nl80211_event_rtm_newlink(struct wpa_driver_nl80211_data *drv,
845                                               void *ctx, struct nlmsghdr *h,
846                                               size_t len)
847 {
848         struct ifinfomsg *ifi;
849         int attrlen, _nlmsg_len, rta_len;
850         struct rtattr * attr;
851
852         if (len < sizeof(*ifi))
853                 return;
854
855         ifi = NLMSG_DATA(h);
856
857         if (!wpa_driver_nl80211_own_ifindex(drv, ifi->ifi_index, h)) {
858                 wpa_printf(MSG_DEBUG, "Ignore event for foreign ifindex %d",
859                            ifi->ifi_index);
860                 return;
861         }
862
863         wpa_printf(MSG_DEBUG, "RTM_NEWLINK: operstate=%d ifi_flags=0x%x "
864                    "(%s%s%s%s)",
865                    drv->operstate, ifi->ifi_flags,
866                    (ifi->ifi_flags & IFF_UP) ? "[UP]" : "",
867                    (ifi->ifi_flags & IFF_RUNNING) ? "[RUNNING]" : "",
868                    (ifi->ifi_flags & IFF_LOWER_UP) ? "[LOWER_UP]" : "",
869                    (ifi->ifi_flags & IFF_DORMANT) ? "[DORMANT]" : "");
870         /*
871          * Some drivers send the association event before the operup event--in
872          * this case, lifting operstate in wpa_driver_nl80211_set_operstate()
873          * fails. This will hit us when wpa_supplicant does not need to do
874          * IEEE 802.1X authentication
875          */
876         if (drv->operstate == 1 &&
877             (ifi->ifi_flags & (IFF_LOWER_UP | IFF_DORMANT)) == IFF_LOWER_UP &&
878             !(ifi->ifi_flags & IFF_RUNNING))
879                 wpa_driver_nl80211_send_oper_ifla(drv, -1, IF_OPER_UP);
880
881         _nlmsg_len = NLMSG_ALIGN(sizeof(struct ifinfomsg));
882
883         attrlen = h->nlmsg_len - _nlmsg_len;
884         if (attrlen < 0)
885                 return;
886
887         attr = (struct rtattr *) (((char *) ifi) + _nlmsg_len);
888
889         rta_len = RTA_ALIGN(sizeof(struct rtattr));
890         while (RTA_OK(attr, attrlen)) {
891                 if (attr->rta_type == IFLA_WIRELESS) {
892                         wpa_driver_nl80211_event_wireless(
893                                 drv, ctx, ((char *) attr) + rta_len,
894                                 attr->rta_len - rta_len);
895                 } else if (attr->rta_type == IFLA_IFNAME) {
896                         wpa_driver_nl80211_event_link(
897                                 drv, ctx,
898                                 ((char *) attr) + rta_len,
899                                 attr->rta_len - rta_len, 0);
900                 }
901                 attr = RTA_NEXT(attr, attrlen);
902         }
903 }
904
905
906 static void wpa_driver_nl80211_event_rtm_dellink(struct wpa_driver_nl80211_data *drv,
907                                               void *ctx, struct nlmsghdr *h,
908                                               size_t len)
909 {
910         struct ifinfomsg *ifi;
911         int attrlen, _nlmsg_len, rta_len;
912         struct rtattr * attr;
913
914         if (len < sizeof(*ifi))
915                 return;
916
917         ifi = NLMSG_DATA(h);
918
919         _nlmsg_len = NLMSG_ALIGN(sizeof(struct ifinfomsg));
920
921         attrlen = h->nlmsg_len - _nlmsg_len;
922         if (attrlen < 0)
923                 return;
924
925         attr = (struct rtattr *) (((char *) ifi) + _nlmsg_len);
926
927         rta_len = RTA_ALIGN(sizeof(struct rtattr));
928         while (RTA_OK(attr, attrlen)) {
929                 if (attr->rta_type == IFLA_IFNAME) {
930                         wpa_driver_nl80211_event_link(
931                                 drv, ctx,
932                                 ((char *) attr) + rta_len,
933                                 attr->rta_len - rta_len, 1);
934                 }
935                 attr = RTA_NEXT(attr, attrlen);
936         }
937 }
938
939
940 static void wpa_driver_nl80211_event_receive_wext(int sock, void *eloop_ctx,
941                                                   void *sock_ctx)
942 {
943         char buf[8192];
944         int left;
945         struct sockaddr_nl from;
946         socklen_t fromlen;
947         struct nlmsghdr *h;
948         int max_events = 10;
949
950 try_again:
951         fromlen = sizeof(from);
952         left = recvfrom(sock, buf, sizeof(buf), MSG_DONTWAIT,
953                         (struct sockaddr *) &from, &fromlen);
954         if (left < 0) {
955                 if (errno != EINTR && errno != EAGAIN)
956                         perror("recvfrom(netlink)");
957                 return;
958         }
959
960         h = (struct nlmsghdr *) buf;
961         while (left >= (int) sizeof(*h)) {
962                 int len, plen;
963
964                 len = h->nlmsg_len;
965                 plen = len - sizeof(*h);
966                 if (len > left || plen < 0) {
967                         wpa_printf(MSG_DEBUG, "Malformed netlink message: "
968                                    "len=%d left=%d plen=%d",
969                                    len, left, plen);
970                         break;
971                 }
972
973                 switch (h->nlmsg_type) {
974                 case RTM_NEWLINK:
975                         wpa_driver_nl80211_event_rtm_newlink(eloop_ctx, sock_ctx,
976                                                           h, plen);
977                         break;
978                 case RTM_DELLINK:
979                         wpa_driver_nl80211_event_rtm_dellink(eloop_ctx, sock_ctx,
980                                                           h, plen);
981                         break;
982                 }
983
984                 len = NLMSG_ALIGN(len);
985                 left -= len;
986                 h = (struct nlmsghdr *) ((char *) h + len);
987         }
988
989         if (left > 0) {
990                 wpa_printf(MSG_DEBUG, "%d extra bytes in the end of netlink "
991                            "message", left);
992         }
993
994         if (--max_events > 0) {
995                 /*
996                  * Try to receive all events in one eloop call in order to
997                  * limit race condition on cases where AssocInfo event, Assoc
998                  * event, and EAPOL frames are received more or less at the
999                  * same time. We want to process the event messages first
1000                  * before starting EAPOL processing.
1001                  */
1002                 goto try_again;
1003         }
1004 }
1005
1006
1007 static int no_seq_check(struct nl_msg *msg, void *arg)
1008 {
1009         return NL_OK;
1010 }
1011
1012
1013 static void mlme_event_auth(struct wpa_driver_nl80211_data *drv,
1014                             const u8 *frame, size_t len)
1015 {
1016         const struct ieee80211_mgmt *mgmt;
1017         union wpa_event_data event;
1018
1019         mgmt = (const struct ieee80211_mgmt *) frame;
1020         if (len < 24 + sizeof(mgmt->u.auth)) {
1021                 wpa_printf(MSG_DEBUG, "nl80211: Too short association event "
1022                            "frame");
1023                 return;
1024         }
1025
1026         os_memset(&event, 0, sizeof(event));
1027         os_memcpy(event.auth.peer, mgmt->sa, ETH_ALEN);
1028         event.auth.auth_type = le_to_host16(mgmt->u.auth.auth_alg);
1029         event.auth.status_code = le_to_host16(mgmt->u.auth.status_code);
1030         if (len > 24 + sizeof(mgmt->u.auth)) {
1031                 event.auth.ies = mgmt->u.auth.variable;
1032                 event.auth.ies_len = len - 24 - sizeof(mgmt->u.auth);
1033         }
1034
1035         wpa_supplicant_event(drv->ctx, EVENT_AUTH, &event);
1036 }
1037
1038
1039 static void mlme_event_assoc(struct wpa_driver_nl80211_data *drv,
1040                             const u8 *frame, size_t len)
1041 {
1042         const struct ieee80211_mgmt *mgmt;
1043         union wpa_event_data event;
1044         u16 status;
1045
1046         mgmt = (const struct ieee80211_mgmt *) frame;
1047         if (len < 24 + sizeof(mgmt->u.assoc_resp)) {
1048                 wpa_printf(MSG_DEBUG, "nl80211: Too short association event "
1049                            "frame");
1050                 return;
1051         }
1052
1053         status = le_to_host16(mgmt->u.assoc_resp.status_code);
1054         if (status != WLAN_STATUS_SUCCESS) {
1055                 wpa_printf(MSG_DEBUG, "nl80211: Association failed: status "
1056                            "code %d", status);
1057                 /* TODO: notify SME so that things like SA Query and comeback
1058                  * time can be implemented */
1059                 return;
1060         }
1061
1062         drv->associated = 1;
1063         os_memcpy(drv->bssid, mgmt->sa, ETH_ALEN);
1064
1065         os_memset(&event, 0, sizeof(event));
1066         if (len > 24 + sizeof(mgmt->u.assoc_resp)) {
1067                 event.assoc_info.resp_ies = (u8 *) mgmt->u.assoc_resp.variable;
1068                 event.assoc_info.resp_ies_len =
1069                         len - 24 - sizeof(mgmt->u.assoc_req);
1070         }
1071
1072         wpa_supplicant_event(drv->ctx, EVENT_ASSOC, &event);
1073 }
1074
1075
1076 static void mlme_event(struct wpa_driver_nl80211_data *drv,
1077                        enum nl80211_commands cmd, struct nlattr *frame)
1078 {
1079         if (frame == NULL) {
1080                 wpa_printf(MSG_DEBUG, "nl80211: MLME event %d without frame "
1081                            "data", cmd);
1082                 return;
1083         }
1084
1085         wpa_printf(MSG_DEBUG, "nl80211: MLME event %d", cmd);
1086         wpa_hexdump(MSG_MSGDUMP, "nl80211: MLME event frame",
1087                     nla_data(frame), nla_len(frame));
1088
1089         switch (cmd) {
1090         case NL80211_CMD_AUTHENTICATE:
1091                 mlme_event_auth(drv, nla_data(frame), nla_len(frame));
1092                 break;
1093         case NL80211_CMD_ASSOCIATE:
1094                 mlme_event_assoc(drv, nla_data(frame), nla_len(frame));
1095                 break;
1096         case NL80211_CMD_DEAUTHENTICATE:
1097                 drv->associated = 0;
1098                 wpa_supplicant_event(drv->ctx, EVENT_DEAUTH, NULL);
1099                 break;
1100         case NL80211_CMD_DISASSOCIATE:
1101                 drv->associated = 0;
1102                 wpa_supplicant_event(drv->ctx, EVENT_DISASSOC, NULL);
1103                 break;
1104         default:
1105                 break;
1106         }
1107 }
1108
1109
1110 static int process_event(struct nl_msg *msg, void *arg)
1111 {
1112         struct wpa_driver_nl80211_data *drv = arg;
1113         struct genlmsghdr *gnlh = nlmsg_data(nlmsg_hdr(msg));
1114         struct nlattr *tb[NL80211_ATTR_MAX + 1];
1115
1116         nla_parse(tb, NL80211_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
1117                   genlmsg_attrlen(gnlh, 0), NULL);
1118
1119         if (tb[NL80211_ATTR_IFINDEX]) {
1120                 int ifindex = nla_get_u32(tb[NL80211_ATTR_IFINDEX]);
1121                 if (ifindex != drv->ifindex) {
1122                         wpa_printf(MSG_DEBUG, "nl80211: Ignored event (cmd=%d)"
1123                                    " for foreign interface (ifindex %d)",
1124                                    gnlh->cmd, ifindex);
1125                         return NL_SKIP;
1126                 }
1127         }
1128
1129         switch (gnlh->cmd) {
1130         case NL80211_CMD_NEW_SCAN_RESULTS:
1131                 wpa_printf(MSG_DEBUG, "nl80211: New scan results available");
1132                 drv->scan_complete_events = 1;
1133                 eloop_cancel_timeout(wpa_driver_nl80211_scan_timeout, drv,
1134                                      drv->ctx);
1135                 wpa_supplicant_event(drv->ctx, EVENT_SCAN_RESULTS, NULL);
1136                 break;
1137         case NL80211_CMD_SCAN_ABORTED:
1138                 wpa_printf(MSG_DEBUG, "nl80211: Scan aborted");
1139                 /*
1140                  * Need to indicate that scan results are available in order
1141                  * not to make wpa_supplicant stop its scanning.
1142                  */
1143                 eloop_cancel_timeout(wpa_driver_nl80211_scan_timeout, drv,
1144                                      drv->ctx);
1145                 wpa_supplicant_event(drv->ctx, EVENT_SCAN_RESULTS, NULL);
1146                 break;
1147         case NL80211_CMD_AUTHENTICATE:
1148         case NL80211_CMD_ASSOCIATE:
1149         case NL80211_CMD_DEAUTHENTICATE:
1150         case NL80211_CMD_DISASSOCIATE:
1151                 mlme_event(drv, gnlh->cmd, tb[NL80211_ATTR_FRAME]);
1152                 break;
1153         default:
1154                 wpa_printf(MSG_DEBUG, "nl80211: Ignored unknown event "
1155                            "(cmd=%d)", gnlh->cmd);
1156                 break;
1157         }
1158
1159         return NL_SKIP;
1160 }
1161
1162
1163 static void wpa_driver_nl80211_event_receive(int sock, void *eloop_ctx,
1164                                              void *sock_ctx)
1165 {
1166         struct nl_cb *cb;
1167         struct wpa_driver_nl80211_data *drv = eloop_ctx;
1168
1169         wpa_printf(MSG_DEBUG, "nl80211: Event message available");
1170
1171         cb = nl_cb_clone(drv->nl_cb);
1172         if (!cb)
1173                 return;
1174         nl_cb_set(cb, NL_CB_SEQ_CHECK, NL_CB_CUSTOM, no_seq_check, NULL);
1175         nl_cb_set(cb, NL_CB_VALID, NL_CB_CUSTOM, process_event, drv);
1176         nl_recvmsgs(drv->nl_handle, cb);
1177         nl_cb_put(cb);
1178 }
1179
1180
1181 static int wpa_driver_nl80211_get_ifflags_ifname(struct wpa_driver_nl80211_data *drv,
1182                                               const char *ifname, int *flags)
1183 {
1184         struct ifreq ifr;
1185
1186         os_memset(&ifr, 0, sizeof(ifr));
1187         os_strlcpy(ifr.ifr_name, ifname, IFNAMSIZ);
1188         if (ioctl(drv->ioctl_sock, SIOCGIFFLAGS, (caddr_t) &ifr) < 0) {
1189                 perror("ioctl[SIOCGIFFLAGS]");
1190                 return -1;
1191         }
1192         *flags = ifr.ifr_flags & 0xffff;
1193         return 0;
1194 }
1195
1196
1197 /**
1198  * wpa_driver_nl80211_get_ifflags - Get interface flags (SIOCGIFFLAGS)
1199  * @drv: driver_nl80211 private data
1200  * @flags: Pointer to returned flags value
1201  * Returns: 0 on success, -1 on failure
1202  */
1203 static int wpa_driver_nl80211_get_ifflags(struct wpa_driver_nl80211_data *drv,
1204                                           int *flags)
1205 {
1206         return wpa_driver_nl80211_get_ifflags_ifname(drv, drv->ifname, flags);
1207 }
1208
1209
1210 static int wpa_driver_nl80211_set_ifflags_ifname(
1211         struct wpa_driver_nl80211_data *drv,
1212         const char *ifname, int flags)
1213 {
1214         struct ifreq ifr;
1215
1216         os_memset(&ifr, 0, sizeof(ifr));
1217         os_strlcpy(ifr.ifr_name, ifname, IFNAMSIZ);
1218         ifr.ifr_flags = flags & 0xffff;
1219         if (ioctl(drv->ioctl_sock, SIOCSIFFLAGS, (caddr_t) &ifr) < 0) {
1220                 perror("SIOCSIFFLAGS");
1221                 return -1;
1222         }
1223         return 0;
1224 }
1225
1226
1227 /**
1228  * wpa_driver_nl80211_set_ifflags - Set interface flags (SIOCSIFFLAGS)
1229  * @drv: driver_nl80211 private data
1230  * @flags: New value for flags
1231  * Returns: 0 on success, -1 on failure
1232  */
1233 static int wpa_driver_nl80211_set_ifflags(struct wpa_driver_nl80211_data *drv,
1234                                           int flags)
1235 {
1236         return wpa_driver_nl80211_set_ifflags_ifname(drv, drv->ifname, flags);
1237 }
1238
1239
1240 /**
1241  * wpa_driver_nl80211_set_country - ask nl80211 to set the regulatory domain
1242  * @priv: driver_nl80211 private data
1243  * @alpha2_arg: country to which to switch to
1244  * Returns: 0 on success, -1 on failure
1245  *
1246  * This asks nl80211 to set the regulatory domain for given
1247  * country ISO / IEC alpha2.
1248  */
1249 static int wpa_driver_nl80211_set_country(void *priv, const char *alpha2_arg)
1250 {
1251         struct wpa_driver_nl80211_data *drv = priv;
1252         char alpha2[3];
1253         struct nl_msg *msg;
1254
1255         msg = nlmsg_alloc();
1256         if (!msg)
1257                 goto nla_put_failure;
1258
1259         alpha2[0] = alpha2_arg[0];
1260         alpha2[1] = alpha2_arg[1];
1261         alpha2[2] = '\0';
1262
1263         genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
1264                     0, NL80211_CMD_REQ_SET_REG, 0);
1265
1266         NLA_PUT_STRING(msg, NL80211_ATTR_REG_ALPHA2, alpha2);
1267         if (send_and_recv_msgs(drv, msg, NULL, NULL))
1268                 return -EINVAL;
1269         return 0;
1270 nla_put_failure:
1271         return -EINVAL;
1272 }
1273
1274
1275 struct wiphy_info_data {
1276         int max_scan_ssids;
1277         int ap_supported;
1278 };
1279
1280
1281 static int wiphy_info_handler(struct nl_msg *msg, void *arg)
1282 {
1283         struct nlattr *tb[NL80211_ATTR_MAX + 1];
1284         struct genlmsghdr *gnlh = nlmsg_data(nlmsg_hdr(msg));
1285         struct wiphy_info_data *info = arg;
1286
1287         nla_parse(tb, NL80211_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
1288                   genlmsg_attrlen(gnlh, 0), NULL);
1289
1290         if (tb[NL80211_ATTR_MAX_NUM_SCAN_SSIDS])
1291                 info->max_scan_ssids =
1292                         nla_get_u8(tb[NL80211_ATTR_MAX_NUM_SCAN_SSIDS]);
1293
1294         if (tb[NL80211_ATTR_SUPPORTED_IFTYPES]) {
1295                 struct nlattr *nl_mode;
1296                 int i;
1297                 nla_for_each_nested(nl_mode,
1298                                     tb[NL80211_ATTR_SUPPORTED_IFTYPES], i) {
1299                         if (nl_mode->nla_type == NL80211_IFTYPE_AP) {
1300                                 info->ap_supported = 1;
1301                                 break;
1302                         }
1303                 }
1304         }
1305
1306         return NL_SKIP;
1307 }
1308
1309
1310 static int wpa_driver_nl80211_get_info(struct wpa_driver_nl80211_data *drv,
1311                                        struct wiphy_info_data *info)
1312 {
1313         struct nl_msg *msg;
1314
1315         os_memset(info, 0, sizeof(*info));
1316         msg = nlmsg_alloc();
1317         if (!msg)
1318                 return -1;
1319
1320         genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
1321                     0, NL80211_CMD_GET_WIPHY, 0);
1322
1323         NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
1324
1325         if (send_and_recv_msgs(drv, msg, wiphy_info_handler, info) == 0)
1326                 return 0;
1327         msg = NULL;
1328 nla_put_failure:
1329         nlmsg_free(msg);
1330         return -1;
1331 }
1332
1333
1334 static void wpa_driver_nl80211_capa(struct wpa_driver_nl80211_data *drv)
1335 {
1336         struct wiphy_info_data info;
1337         if (wpa_driver_nl80211_get_info(drv, &info))
1338                 return;
1339         drv->has_capability = 1;
1340         drv->capa.max_scan_ssids = info.max_scan_ssids;
1341         if (info.ap_supported)
1342                 drv->capa.flags |= WPA_DRIVER_FLAGS_AP;
1343 }
1344
1345
1346 /**
1347  * wpa_driver_nl80211_init - Initialize nl80211 driver interface
1348  * @ctx: context to be used when calling wpa_supplicant functions,
1349  * e.g., wpa_supplicant_event()
1350  * @ifname: interface name, e.g., wlan0
1351  * Returns: Pointer to private data, %NULL on failure
1352  */
1353 static void * wpa_driver_nl80211_init(void *ctx, const char *ifname)
1354 {
1355         int s, ret;
1356         struct sockaddr_nl local;
1357         struct wpa_driver_nl80211_data *drv;
1358
1359         drv = os_zalloc(sizeof(*drv));
1360         if (drv == NULL)
1361                 return NULL;
1362         drv->ctx = ctx;
1363         os_strlcpy(drv->ifname, ifname, sizeof(drv->ifname));
1364
1365         drv->nl_cb = nl_cb_alloc(NL_CB_DEFAULT);
1366         if (drv->nl_cb == NULL) {
1367                 wpa_printf(MSG_ERROR, "nl80211: Failed to allocate netlink "
1368                            "callbacks");
1369                 goto err1;
1370         }
1371
1372         drv->nl_handle = nl_handle_alloc_cb(drv->nl_cb);
1373         if (drv->nl_handle == NULL) {
1374                 wpa_printf(MSG_ERROR, "nl80211: Failed to allocate netlink "
1375                            "callbacks");
1376                 goto err2;
1377         }
1378
1379         if (genl_connect(drv->nl_handle)) {
1380                 wpa_printf(MSG_ERROR, "nl80211: Failed to connect to generic "
1381                            "netlink");
1382                 goto err3;
1383         }
1384
1385         drv->nl_cache = genl_ctrl_alloc_cache(drv->nl_handle);
1386         if (drv->nl_cache == NULL) {
1387                 wpa_printf(MSG_ERROR, "nl80211: Failed to allocate generic "
1388                            "netlink cache");
1389                 goto err3;
1390         }
1391
1392         drv->nl80211 = genl_ctrl_search_by_name(drv->nl_cache, "nl80211");
1393         if (drv->nl80211 == NULL) {
1394                 wpa_printf(MSG_ERROR, "nl80211: 'nl80211' generic netlink not "
1395                            "found");
1396                 goto err4;
1397         }
1398
1399         ret = nl_get_multicast_id(drv, "nl80211", "scan");
1400         if (ret >= 0)
1401                 ret = nl_socket_add_membership(drv->nl_handle, ret);
1402         if (ret < 0) {
1403                 wpa_printf(MSG_ERROR, "nl80211: Could not add multicast "
1404                            "membership for scan events: %d (%s)",
1405                            ret, strerror(-ret));
1406                 goto err4;
1407         }
1408
1409         ret = nl_get_multicast_id(drv, "nl80211", "mlme");
1410         if (ret >= 0)
1411                 ret = nl_socket_add_membership(drv->nl_handle, ret);
1412 #ifdef WEXT_COMPAT
1413         if (ret < 0) {
1414                 wpa_printf(MSG_DEBUG, "nl80211: Could not add multicast "
1415                            "membership for mlme events: %d (%s)",
1416                            ret, strerror(-ret));
1417                 /* Use WEXT for association request */
1418         } else
1419                 drv->capa.flags |= WPA_DRIVER_FLAGS_SME;
1420 #else /* WEXT_COMPAT */
1421         if (ret < 0) {
1422                 wpa_printf(MSG_ERROR, "nl80211: Could not add multicast "
1423                            "membership for mlme events: %d (%s)",
1424                            ret, strerror(-ret));
1425                 goto err4;
1426         }
1427         drv->capa.flags |= WPA_DRIVER_FLAGS_SME;
1428 #endif /* WEXT_COMPAT */
1429
1430         eloop_register_read_sock(nl_socket_get_fd(drv->nl_handle),
1431                                  wpa_driver_nl80211_event_receive, drv, ctx);
1432
1433         drv->ioctl_sock = socket(PF_INET, SOCK_DGRAM, 0);
1434         if (drv->ioctl_sock < 0) {
1435                 perror("socket(PF_INET,SOCK_DGRAM)");
1436                 goto err5;
1437         }
1438
1439         s = socket(PF_NETLINK, SOCK_RAW, NETLINK_ROUTE);
1440         if (s < 0) {
1441                 perror("socket(PF_NETLINK,SOCK_RAW,NETLINK_ROUTE)");
1442                 goto err6;
1443         }
1444
1445         os_memset(&local, 0, sizeof(local));
1446         local.nl_family = AF_NETLINK;
1447         local.nl_groups = RTMGRP_LINK;
1448         if (bind(s, (struct sockaddr *) &local, sizeof(local)) < 0) {
1449                 perror("bind(netlink)");
1450                 close(s);
1451                 goto err6;
1452         }
1453
1454         eloop_register_read_sock(s, wpa_driver_nl80211_event_receive_wext, drv,
1455                                  ctx);
1456         drv->wext_event_sock = s;
1457
1458         if (wpa_driver_nl80211_finish_drv_init(drv))
1459                 goto err7;
1460
1461         return drv;
1462
1463 err7:
1464         eloop_unregister_read_sock(drv->wext_event_sock);
1465         close(drv->wext_event_sock);
1466 err6:
1467         close(drv->ioctl_sock);
1468 err5:
1469         genl_family_put(drv->nl80211);
1470 err4:
1471         nl_cache_free(drv->nl_cache);
1472 err3:
1473         nl_handle_destroy(drv->nl_handle);
1474 err2:
1475         nl_cb_put(drv->nl_cb);
1476 err1:
1477         os_free(drv);
1478         return NULL;
1479 }
1480
1481
1482 static int
1483 wpa_driver_nl80211_finish_drv_init(struct wpa_driver_nl80211_data *drv)
1484 {
1485         int flags;
1486
1487         drv->ifindex = if_nametoindex(drv->ifname);
1488
1489         if (wpa_driver_nl80211_set_mode(drv, 0) < 0) {
1490                 wpa_printf(MSG_DEBUG, "nl80211: Could not configure driver to "
1491                            "use managed mode");
1492         }
1493
1494         if (wpa_driver_nl80211_get_ifflags(drv, &flags) != 0) {
1495                 wpa_printf(MSG_ERROR, "Could not get interface '%s' flags",
1496                            drv->ifname);
1497                 return -1;
1498         }
1499         if (!(flags & IFF_UP)) {
1500                 if (wpa_driver_nl80211_set_ifflags(drv, flags | IFF_UP) != 0) {
1501                         wpa_printf(MSG_ERROR, "Could not set interface '%s' "
1502                                    "UP", drv->ifname);
1503                         return -1;
1504                 }
1505         }
1506
1507 #ifdef WEXT_COMPAT
1508         /*
1509          * Make sure that the driver does not have any obsolete PMKID entries.
1510          */
1511         wpa_driver_nl80211_flush_pmkid(drv);
1512 #endif /* WEXT_COMPAT */
1513
1514         wpa_driver_nl80211_get_range(drv);
1515
1516         wpa_driver_nl80211_capa(drv);
1517
1518         wpa_driver_nl80211_send_oper_ifla(drv, 1, IF_OPER_DORMANT);
1519
1520         return 0;
1521 }
1522
1523
1524 /**
1525  * wpa_driver_nl80211_deinit - Deinitialize nl80211 driver interface
1526  * @priv: Pointer to private nl80211 data from wpa_driver_nl80211_init()
1527  *
1528  * Shut down driver interface and processing of driver events. Free
1529  * private data buffer if one was allocated in wpa_driver_nl80211_init().
1530  */
1531 static void wpa_driver_nl80211_deinit(void *priv)
1532 {
1533         struct wpa_driver_nl80211_data *drv = priv;
1534         int flags;
1535
1536         eloop_cancel_timeout(wpa_driver_nl80211_scan_timeout, drv, drv->ctx);
1537
1538 #ifdef WEXT_COMPAT
1539         /*
1540          * Clear possibly configured driver parameters in order to make it
1541          * easier to use the driver after wpa_supplicant has been terminated.
1542          */
1543         (void) wpa_driver_nl80211_set_bssid(drv,
1544                                          (u8 *) "\x00\x00\x00\x00\x00\x00");
1545 #endif /* WEXT_COMPAT */
1546         wpa_driver_nl80211_set_auth_param(drv, IW_AUTH_DROP_UNENCRYPTED, 0);
1547
1548         wpa_driver_nl80211_send_oper_ifla(priv, 0, IF_OPER_UP);
1549
1550         eloop_unregister_read_sock(drv->wext_event_sock);
1551
1552         if (wpa_driver_nl80211_get_ifflags(drv, &flags) == 0)
1553                 (void) wpa_driver_nl80211_set_ifflags(drv, flags & ~IFF_UP);
1554         wpa_driver_nl80211_set_mode(drv, 0);
1555
1556         close(drv->wext_event_sock);
1557         close(drv->ioctl_sock);
1558 #ifdef WEXT_COMPAT
1559         os_free(drv->assoc_req_ies);
1560         os_free(drv->assoc_resp_ies);
1561 #endif /* WEXT_COMPAT */
1562
1563         eloop_unregister_read_sock(nl_socket_get_fd(drv->nl_handle));
1564         genl_family_put(drv->nl80211);
1565         nl_cache_free(drv->nl_cache);
1566         nl_handle_destroy(drv->nl_handle);
1567         nl_cb_put(drv->nl_cb);
1568
1569         os_free(drv);
1570 }
1571
1572
1573 /**
1574  * wpa_driver_nl80211_scan_timeout - Scan timeout to report scan completion
1575  * @eloop_ctx: Unused
1576  * @timeout_ctx: ctx argument given to wpa_driver_nl80211_init()
1577  *
1578  * This function can be used as registered timeout when starting a scan to
1579  * generate a scan completed event if the driver does not report this.
1580  */
1581 static void wpa_driver_nl80211_scan_timeout(void *eloop_ctx, void *timeout_ctx)
1582 {
1583         wpa_printf(MSG_DEBUG, "Scan timeout - try to get results");
1584         wpa_supplicant_event(timeout_ctx, EVENT_SCAN_RESULTS, NULL);
1585 }
1586
1587
1588 /**
1589  * wpa_driver_nl80211_scan - Request the driver to initiate scan
1590  * @priv: Pointer to private wext data from wpa_driver_nl80211_init()
1591  * @params: Scan parameters
1592  * Returns: 0 on success, -1 on failure
1593  */
1594 static int wpa_driver_nl80211_scan(void *priv,
1595                                    struct wpa_driver_scan_params *params)
1596 {
1597         struct wpa_driver_nl80211_data *drv = priv;
1598         int ret = 0, timeout;
1599         struct nl_msg *msg, *ssids, *freqs;
1600         size_t i;
1601
1602         msg = nlmsg_alloc();
1603         ssids = nlmsg_alloc();
1604         freqs = nlmsg_alloc();
1605         if (!msg || !ssids || !freqs) {
1606                 nlmsg_free(msg);
1607                 nlmsg_free(ssids);
1608                 nlmsg_free(freqs);
1609                 return -1;
1610         }
1611
1612         genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0, 0,
1613                     NL80211_CMD_TRIGGER_SCAN, 0);
1614
1615         NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
1616
1617         for (i = 0; i < params->num_ssids; i++) {
1618                 NLA_PUT(ssids, i + 1, params->ssids[i].ssid_len,
1619                         params->ssids[i].ssid);
1620         }
1621         if (params->num_ssids)
1622                 nla_put_nested(msg, NL80211_ATTR_SCAN_SSIDS, ssids);
1623
1624         if (params->extra_ies) {
1625                 NLA_PUT(msg, NL80211_ATTR_IE, params->extra_ies_len,
1626                         params->extra_ies);
1627         }
1628
1629         if (params->freqs) {
1630                 for (i = 0; params->freqs[i]; i++)
1631                         NLA_PUT_U32(freqs, i + 1, params->freqs[i]);
1632                 nla_put_nested(msg, NL80211_ATTR_SCAN_FREQUENCIES, freqs);
1633         }
1634
1635         ret = send_and_recv_msgs(drv, msg, NULL, NULL);
1636         msg = NULL;
1637         if (ret) {
1638                 wpa_printf(MSG_DEBUG, "nl80211: Scan trigger failed: ret=%d "
1639                            "(%s)", ret, strerror(-ret));
1640                 goto nla_put_failure;
1641         }
1642
1643         /* Not all drivers generate "scan completed" wireless event, so try to
1644          * read results after a timeout. */
1645         timeout = 10;
1646         if (drv->scan_complete_events) {
1647                 /*
1648                  * The driver seems to deliver events to notify when scan is
1649                  * complete, so use longer timeout to avoid race conditions
1650                  * with scanning and following association request.
1651                  */
1652                 timeout = 30;
1653         }
1654         wpa_printf(MSG_DEBUG, "Scan requested (ret=%d) - scan timeout %d "
1655                    "seconds", ret, timeout);
1656         eloop_cancel_timeout(wpa_driver_nl80211_scan_timeout, drv, drv->ctx);
1657         eloop_register_timeout(timeout, 0, wpa_driver_nl80211_scan_timeout,
1658                                drv, drv->ctx);
1659
1660 nla_put_failure:
1661         nlmsg_free(ssids);
1662         nlmsg_free(msg);
1663         nlmsg_free(freqs);
1664         return ret;
1665 }
1666
1667
1668 static int bss_info_handler(struct nl_msg *msg, void *arg)
1669 {
1670         struct nlattr *tb[NL80211_ATTR_MAX + 1];
1671         struct genlmsghdr *gnlh = nlmsg_data(nlmsg_hdr(msg));
1672         struct nlattr *bss[NL80211_BSS_MAX + 1];
1673         static struct nla_policy bss_policy[NL80211_BSS_MAX + 1] = {
1674                 [NL80211_BSS_BSSID] = { .type = NLA_UNSPEC },
1675                 [NL80211_BSS_FREQUENCY] = { .type = NLA_U32 },
1676                 [NL80211_BSS_TSF] = { .type = NLA_U64 },
1677                 [NL80211_BSS_BEACON_INTERVAL] = { .type = NLA_U16 },
1678                 [NL80211_BSS_CAPABILITY] = { .type = NLA_U16 },
1679                 [NL80211_BSS_INFORMATION_ELEMENTS] = { .type = NLA_UNSPEC },
1680                 [NL80211_BSS_SIGNAL_MBM] = { .type = NLA_U32 },
1681                 [NL80211_BSS_SIGNAL_UNSPEC] = { .type = NLA_U8 },
1682         };
1683         struct wpa_scan_results *res = arg;
1684         struct wpa_scan_res **tmp;
1685         struct wpa_scan_res *r;
1686         const u8 *ie;
1687         size_t ie_len;
1688
1689         nla_parse(tb, NL80211_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
1690                   genlmsg_attrlen(gnlh, 0), NULL);
1691         if (!tb[NL80211_ATTR_BSS])
1692                 return NL_SKIP;
1693         if (nla_parse_nested(bss, NL80211_BSS_MAX, tb[NL80211_ATTR_BSS],
1694                              bss_policy))
1695                 return NL_SKIP;
1696         if (bss[NL80211_BSS_INFORMATION_ELEMENTS]) {
1697                 ie = nla_data(bss[NL80211_BSS_INFORMATION_ELEMENTS]);
1698                 ie_len = nla_len(bss[NL80211_BSS_INFORMATION_ELEMENTS]);
1699         } else {
1700                 ie = NULL;
1701                 ie_len = 0;
1702         }
1703
1704         r = os_zalloc(sizeof(*r) + ie_len);
1705         if (r == NULL)
1706                 return NL_SKIP;
1707         if (bss[NL80211_BSS_BSSID])
1708                 os_memcpy(r->bssid, nla_data(bss[NL80211_BSS_BSSID]),
1709                           ETH_ALEN);
1710         if (bss[NL80211_BSS_FREQUENCY])
1711                 r->freq = nla_get_u32(bss[NL80211_BSS_FREQUENCY]);
1712         if (bss[NL80211_BSS_BEACON_INTERVAL])
1713                 r->beacon_int = nla_get_u16(bss[NL80211_BSS_BEACON_INTERVAL]);
1714         if (bss[NL80211_BSS_CAPABILITY])
1715                 r->caps = nla_get_u16(bss[NL80211_BSS_CAPABILITY]);
1716         r->flags |= WPA_SCAN_NOISE_INVALID;
1717         if (bss[NL80211_BSS_SIGNAL_MBM]) {
1718                 r->level = nla_get_u32(bss[NL80211_BSS_SIGNAL_MBM]);
1719                 r->level /= 100; /* mBm to dBm */
1720                 r->flags |= WPA_SCAN_LEVEL_DBM | WPA_SCAN_QUAL_INVALID;
1721         } else if (bss[NL80211_BSS_SIGNAL_UNSPEC]) {
1722                 r->level = nla_get_u8(bss[NL80211_BSS_SIGNAL_UNSPEC]);
1723                 r->flags |= WPA_SCAN_LEVEL_INVALID;
1724         } else
1725                 r->flags |= WPA_SCAN_LEVEL_INVALID | WPA_SCAN_QUAL_INVALID;
1726         if (bss[NL80211_BSS_TSF])
1727                 r->tsf = nla_get_u64(bss[NL80211_BSS_TSF]);
1728         r->ie_len = ie_len;
1729         if (ie)
1730                 os_memcpy(r + 1, ie, ie_len);
1731
1732         tmp = os_realloc(res->res,
1733                          (res->num + 1) * sizeof(struct wpa_scan_res *));
1734         if (tmp == NULL) {
1735                 os_free(r);
1736                 return NL_SKIP;
1737         }
1738         tmp[res->num++] = r;
1739         res->res = tmp;
1740
1741         return NL_SKIP;
1742 }
1743
1744
1745 /**
1746  * wpa_driver_nl80211_get_scan_results - Fetch the latest scan results
1747  * @priv: Pointer to private wext data from wpa_driver_nl80211_init()
1748  * Returns: Scan results on success, -1 on failure
1749  */
1750 static struct wpa_scan_results *
1751 wpa_driver_nl80211_get_scan_results(void *priv)
1752 {
1753         struct wpa_driver_nl80211_data *drv = priv;
1754         struct nl_msg *msg;
1755         struct wpa_scan_results *res;
1756         int ret;
1757
1758         res = os_zalloc(sizeof(*res));
1759         if (res == NULL)
1760                 return 0;
1761         msg = nlmsg_alloc();
1762         if (!msg)
1763                 goto nla_put_failure;
1764
1765         genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0, NLM_F_DUMP,
1766                     NL80211_CMD_GET_SCAN, 0);
1767         NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
1768
1769         ret = send_and_recv_msgs(drv, msg, bss_info_handler, res);
1770         msg = NULL;
1771         if (ret == 0) {
1772                 wpa_printf(MSG_DEBUG, "Received scan results (%lu BSSes)",
1773                            (unsigned long) res->num);
1774                 return res;
1775         }
1776         wpa_printf(MSG_DEBUG, "nl80211: Scan result fetch failed: ret=%d "
1777                    "(%s)", ret, strerror(-ret));
1778 nla_put_failure:
1779         nlmsg_free(msg);
1780         wpa_scan_results_free(res);
1781         return NULL;
1782 }
1783
1784
1785 static int wpa_driver_nl80211_get_range(void *priv)
1786 {
1787         struct wpa_driver_nl80211_data *drv = priv;
1788         struct iw_range *range;
1789         struct iwreq iwr;
1790         int minlen;
1791         size_t buflen;
1792
1793         /*
1794          * Use larger buffer than struct iw_range in order to allow the
1795          * structure to grow in the future.
1796          */
1797         buflen = sizeof(struct iw_range) + 500;
1798         range = os_zalloc(buflen);
1799         if (range == NULL)
1800                 return -1;
1801
1802         os_memset(&iwr, 0, sizeof(iwr));
1803         os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
1804         iwr.u.data.pointer = (caddr_t) range;
1805         iwr.u.data.length = buflen;
1806
1807         minlen = ((char *) &range->enc_capa) - (char *) range +
1808                 sizeof(range->enc_capa);
1809
1810         if (ioctl(drv->ioctl_sock, SIOCGIWRANGE, &iwr) < 0) {
1811                 perror("ioctl[SIOCGIWRANGE]");
1812                 os_free(range);
1813                 return -1;
1814         } else if (iwr.u.data.length >= minlen &&
1815                    range->we_version_compiled >= 18) {
1816                 wpa_printf(MSG_DEBUG, "SIOCGIWRANGE: WE(compiled)=%d "
1817                            "WE(source)=%d enc_capa=0x%x",
1818                            range->we_version_compiled,
1819                            range->we_version_source,
1820                            range->enc_capa);
1821                 drv->has_capability = 1;
1822                 drv->we_version_compiled = range->we_version_compiled;
1823                 if (range->enc_capa & IW_ENC_CAPA_WPA) {
1824                         drv->capa.key_mgmt |= WPA_DRIVER_CAPA_KEY_MGMT_WPA |
1825                                 WPA_DRIVER_CAPA_KEY_MGMT_WPA_PSK;
1826                 }
1827                 if (range->enc_capa & IW_ENC_CAPA_WPA2) {
1828                         drv->capa.key_mgmt |= WPA_DRIVER_CAPA_KEY_MGMT_WPA2 |
1829                                 WPA_DRIVER_CAPA_KEY_MGMT_WPA2_PSK;
1830                 }
1831                 drv->capa.enc |= WPA_DRIVER_CAPA_ENC_WEP40 |
1832                         WPA_DRIVER_CAPA_ENC_WEP104;
1833                 if (range->enc_capa & IW_ENC_CAPA_CIPHER_TKIP)
1834                         drv->capa.enc |= WPA_DRIVER_CAPA_ENC_TKIP;
1835                 if (range->enc_capa & IW_ENC_CAPA_CIPHER_CCMP)
1836                         drv->capa.enc |= WPA_DRIVER_CAPA_ENC_CCMP;
1837                 wpa_printf(MSG_DEBUG, "  capabilities: key_mgmt 0x%x enc 0x%x",
1838                            drv->capa.key_mgmt, drv->capa.enc);
1839         } else {
1840                 wpa_printf(MSG_DEBUG, "SIOCGIWRANGE: too old (short) data - "
1841                            "assuming WPA is not supported");
1842         }
1843
1844         os_free(range);
1845         return 0;
1846 }
1847
1848
1849 #ifdef WEXT_COMPAT
1850 static int wpa_driver_nl80211_set_wpa(void *priv, int enabled)
1851 {
1852         struct wpa_driver_nl80211_data *drv = priv;
1853         if (drv->capa.flags & WPA_DRIVER_FLAGS_SME)
1854                 return 0;
1855         wpa_printf(MSG_DEBUG, "%s", __FUNCTION__);
1856
1857         return wpa_driver_nl80211_set_auth_param(drv, IW_AUTH_WPA_ENABLED,
1858                                               enabled);
1859 }
1860 #endif /* WEXT_COMPAT */
1861
1862
1863 static int wpa_driver_nl80211_set_key(void *priv, wpa_alg alg,
1864                                       const u8 *addr, int key_idx,
1865                                       int set_tx, const u8 *seq,
1866                                       size_t seq_len,
1867                                       const u8 *key, size_t key_len)
1868 {
1869         struct wpa_driver_nl80211_data *drv = priv;
1870         int err;
1871         struct nl_msg *msg;
1872
1873         wpa_printf(MSG_DEBUG, "%s: alg=%d addr=%p key_idx=%d set_tx=%d "
1874                    "seq_len=%lu key_len=%lu",
1875                    __func__, alg, addr, key_idx, set_tx,
1876                    (unsigned long) seq_len, (unsigned long) key_len);
1877
1878         msg = nlmsg_alloc();
1879         if (msg == NULL)
1880                 return -1;
1881
1882         if (alg == WPA_ALG_NONE) {
1883                 genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0, 0,
1884                             NL80211_CMD_DEL_KEY, 0);
1885         } else {
1886                 genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0, 0,
1887                             NL80211_CMD_NEW_KEY, 0);
1888                 NLA_PUT(msg, NL80211_ATTR_KEY_DATA, key_len, key);
1889                 switch (alg) {
1890                 case WPA_ALG_WEP:
1891                         if (key_len == 5)
1892                                 NLA_PUT_U32(msg, NL80211_ATTR_KEY_CIPHER,
1893                                             0x000FAC01);
1894                         else
1895                                 NLA_PUT_U32(msg, NL80211_ATTR_KEY_CIPHER,
1896                                             0x000FAC05);
1897                         break;
1898                 case WPA_ALG_TKIP:
1899                         NLA_PUT_U32(msg, NL80211_ATTR_KEY_CIPHER, 0x000FAC02);
1900                         break;
1901                 case WPA_ALG_CCMP:
1902                         NLA_PUT_U32(msg, NL80211_ATTR_KEY_CIPHER, 0x000FAC04);
1903                         break;
1904                 default:
1905                         nlmsg_free(msg);
1906                         return -1;
1907                 }
1908         }
1909
1910         if (addr && os_memcmp(addr, "\xff\xff\xff\xff\xff\xff", ETH_ALEN) != 0)
1911         {
1912                 wpa_printf(MSG_DEBUG, "   addr=" MACSTR, MAC2STR(addr));
1913                 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, addr);
1914         }
1915         NLA_PUT_U8(msg, NL80211_ATTR_KEY_IDX, key_idx);
1916         NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
1917
1918         err = send_and_recv_msgs(drv, msg, NULL, NULL);
1919         if (err) {
1920                 wpa_printf(MSG_DEBUG, "nl80211: set_key failed; err=%d", err);
1921                 return -1;
1922         }
1923
1924         if (set_tx && alg != WPA_ALG_NONE) {
1925                 msg = nlmsg_alloc();
1926                 if (msg == NULL)
1927                         return -1;
1928
1929                 genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
1930                             0, NL80211_CMD_SET_KEY, 0);
1931                 NLA_PUT_U8(msg, NL80211_ATTR_KEY_IDX, key_idx);
1932                 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
1933                 NLA_PUT_FLAG(msg, NL80211_ATTR_KEY_DEFAULT);
1934
1935                 err = send_and_recv_msgs(drv, msg, NULL, NULL);
1936                 if (err) {
1937                         wpa_printf(MSG_DEBUG, "nl80211: set default key "
1938                                    "failed; err=%d", err);
1939                         return -1;
1940                 }
1941         }
1942
1943         return 0;
1944
1945 nla_put_failure:
1946         return -ENOBUFS;
1947 }
1948
1949
1950 #ifdef WEXT_COMPAT
1951 static int wpa_driver_nl80211_set_countermeasures(void *priv,
1952                                                int enabled)
1953 {
1954         struct wpa_driver_nl80211_data *drv = priv;
1955         if (drv->capa.flags & WPA_DRIVER_FLAGS_SME)
1956                 return 0;
1957         wpa_printf(MSG_DEBUG, "%s", __FUNCTION__);
1958         return wpa_driver_nl80211_set_auth_param(drv,
1959                                               IW_AUTH_TKIP_COUNTERMEASURES,
1960                                               enabled);
1961 }
1962 #endif /* WEXT_COMPAT */
1963
1964
1965 #ifdef WEXT_COMPAT
1966 static int wpa_driver_nl80211_mlme_wext(struct wpa_driver_nl80211_data *drv,
1967                                         const u8 *addr, int cmd,
1968                                         int reason_code)
1969 {
1970         struct iwreq iwr;
1971         struct iw_mlme mlme;
1972         int ret = 0;
1973
1974         os_memset(&iwr, 0, sizeof(iwr));
1975         os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
1976         os_memset(&mlme, 0, sizeof(mlme));
1977         mlme.cmd = cmd;
1978         mlme.reason_code = reason_code;
1979         mlme.addr.sa_family = ARPHRD_ETHER;
1980         os_memcpy(mlme.addr.sa_data, addr, ETH_ALEN);
1981         iwr.u.data.pointer = (caddr_t) &mlme;
1982         iwr.u.data.length = sizeof(mlme);
1983
1984         if (ioctl(drv->ioctl_sock, SIOCSIWMLME, &iwr) < 0) {
1985                 perror("ioctl[SIOCSIWMLME]");
1986                 ret = -1;
1987         }
1988
1989         return ret;
1990 }
1991 #endif /* WEXT_COMPAT */
1992
1993
1994 static int wpa_driver_nl80211_mlme(struct wpa_driver_nl80211_data *drv,
1995                                    const u8 *addr, int cmd, u16 reason_code)
1996 {
1997         int ret = -1;
1998         struct nl_msg *msg;
1999
2000         msg = nlmsg_alloc();
2001         if (!msg)
2002                 return -1;
2003
2004         genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0, 0, cmd, 0);
2005
2006         NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
2007         NLA_PUT_U16(msg, NL80211_ATTR_REASON_CODE, reason_code);
2008         NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, addr);
2009
2010         ret = send_and_recv_msgs(drv, msg, NULL, NULL);
2011         msg = NULL;
2012         if (ret) {
2013                 wpa_printf(MSG_DEBUG, "nl80211: MLME command failed: ret=%d "
2014                            "(%s)", ret, strerror(-ret));
2015                 goto nla_put_failure;
2016         }
2017         ret = 0;
2018
2019 nla_put_failure:
2020         nlmsg_free(msg);
2021         return ret;
2022 }
2023
2024
2025 static int wpa_driver_nl80211_deauthenticate(void *priv, const u8 *addr,
2026                                              int reason_code)
2027 {
2028         struct wpa_driver_nl80211_data *drv = priv;
2029         wpa_printf(MSG_DEBUG, "%s", __func__);
2030 #ifdef WEXT_COMPAT
2031         if (!(drv->capa.flags & WPA_DRIVER_FLAGS_SME))
2032                 return wpa_driver_nl80211_mlme_wext(drv, addr, IW_MLME_DEAUTH,
2033                                                     reason_code);
2034 #endif /* WEXT_COMPAT */
2035
2036         return wpa_driver_nl80211_mlme(drv, addr, NL80211_CMD_DEAUTHENTICATE,
2037                                        reason_code);
2038 }
2039
2040
2041 static int wpa_driver_nl80211_disassociate(void *priv, const u8 *addr,
2042                                            int reason_code)
2043 {
2044         struct wpa_driver_nl80211_data *drv = priv;
2045         wpa_printf(MSG_DEBUG, "%s", __func__);
2046 #ifdef WEXT_COMPAT
2047         if (!(drv->capa.flags & WPA_DRIVER_FLAGS_SME))
2048                 return wpa_driver_nl80211_mlme_wext(drv, addr,
2049                                                     IW_MLME_DISASSOC,
2050                                                     reason_code);
2051 #endif /* WEXT_COMPAT */
2052         return wpa_driver_nl80211_mlme(drv, addr, NL80211_CMD_DISASSOCIATE,
2053                                        reason_code);
2054 }
2055
2056
2057 #ifdef WEXT_COMPAT
2058 static int wpa_driver_nl80211_set_gen_ie(void *priv, const u8 *ie,
2059                                       size_t ie_len)
2060 {
2061         struct wpa_driver_nl80211_data *drv = priv;
2062         struct iwreq iwr;
2063         int ret = 0;
2064
2065         if (drv->capa.flags & WPA_DRIVER_FLAGS_SME)
2066                 return 0;
2067         os_memset(&iwr, 0, sizeof(iwr));
2068         os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
2069         iwr.u.data.pointer = (caddr_t) ie;
2070         iwr.u.data.length = ie_len;
2071
2072         if (ioctl(drv->ioctl_sock, SIOCSIWGENIE, &iwr) < 0) {
2073                 perror("ioctl[SIOCSIWGENIE]");
2074                 ret = -1;
2075         }
2076
2077         return ret;
2078 }
2079
2080
2081 static int wpa_driver_nl80211_cipher2wext(int cipher)
2082 {
2083         switch (cipher) {
2084         case CIPHER_NONE:
2085                 return IW_AUTH_CIPHER_NONE;
2086         case CIPHER_WEP40:
2087                 return IW_AUTH_CIPHER_WEP40;
2088         case CIPHER_TKIP:
2089                 return IW_AUTH_CIPHER_TKIP;
2090         case CIPHER_CCMP:
2091                 return IW_AUTH_CIPHER_CCMP;
2092         case CIPHER_WEP104:
2093                 return IW_AUTH_CIPHER_WEP104;
2094         default:
2095                 return 0;
2096         }
2097 }
2098
2099
2100 static int wpa_driver_nl80211_keymgmt2wext(int keymgmt)
2101 {
2102         switch (keymgmt) {
2103         case KEY_MGMT_802_1X:
2104         case KEY_MGMT_802_1X_NO_WPA:
2105                 return IW_AUTH_KEY_MGMT_802_1X;
2106         case KEY_MGMT_PSK:
2107                 return IW_AUTH_KEY_MGMT_PSK;
2108         default:
2109                 return 0;
2110         }
2111 }
2112
2113
2114 static int
2115 wpa_driver_nl80211_auth_alg_fallback(struct wpa_driver_nl80211_data *drv,
2116                                   struct wpa_driver_associate_params *params)
2117 {
2118         struct iwreq iwr;
2119         int ret = 0;
2120
2121         wpa_printf(MSG_DEBUG, "WEXT: Driver did not support "
2122                    "SIOCSIWAUTH for AUTH_ALG, trying SIOCSIWENCODE");
2123
2124         os_memset(&iwr, 0, sizeof(iwr));
2125         os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
2126         /* Just changing mode, not actual keys */
2127         iwr.u.encoding.flags = 0;
2128         iwr.u.encoding.pointer = (caddr_t) NULL;
2129         iwr.u.encoding.length = 0;
2130
2131         /*
2132          * Note: IW_ENCODE_{OPEN,RESTRICTED} can be interpreted to mean two
2133          * different things. Here they are used to indicate Open System vs.
2134          * Shared Key authentication algorithm. However, some drivers may use
2135          * them to select between open/restricted WEP encrypted (open = allow
2136          * both unencrypted and encrypted frames; restricted = only allow
2137          * encrypted frames).
2138          */
2139
2140         if (!drv->use_crypt) {
2141                 iwr.u.encoding.flags |= IW_ENCODE_DISABLED;
2142         } else {
2143                 if (params->auth_alg & AUTH_ALG_OPEN_SYSTEM)
2144                         iwr.u.encoding.flags |= IW_ENCODE_OPEN;
2145                 if (params->auth_alg & AUTH_ALG_SHARED_KEY)
2146                         iwr.u.encoding.flags |= IW_ENCODE_RESTRICTED;
2147         }
2148
2149         if (ioctl(drv->ioctl_sock, SIOCSIWENCODE, &iwr) < 0) {
2150                 perror("ioctl[SIOCSIWENCODE]");
2151                 ret = -1;
2152         }
2153
2154         return ret;
2155 }
2156
2157
2158 static int wpa_driver_nl80211_set_auth_alg(struct wpa_driver_nl80211_data *drv,
2159                                            int auth_alg)
2160 {
2161         int algs = 0, res;
2162
2163         if (auth_alg & AUTH_ALG_OPEN_SYSTEM)
2164                 algs |= IW_AUTH_ALG_OPEN_SYSTEM;
2165         if (auth_alg & AUTH_ALG_SHARED_KEY)
2166                 algs |= IW_AUTH_ALG_SHARED_KEY;
2167         if (auth_alg & AUTH_ALG_LEAP)
2168                 algs |= IW_AUTH_ALG_LEAP;
2169         if (algs == 0) {
2170                 /* at least one algorithm should be set */
2171                 algs = IW_AUTH_ALG_OPEN_SYSTEM;
2172         }
2173
2174         res = wpa_driver_nl80211_set_auth_param(drv, IW_AUTH_80211_AUTH_ALG,
2175                                              algs);
2176         drv->auth_alg_fallback = res == -2;
2177         return res;
2178 }
2179
2180
2181 static int wpa_driver_nl80211_associate_wext(
2182         void *priv, struct wpa_driver_associate_params *params)
2183 {
2184         struct wpa_driver_nl80211_data *drv = priv;
2185         int ret = 0;
2186         int allow_unencrypted_eapol;
2187         int value;
2188
2189         wpa_printf(MSG_DEBUG, "%s", __FUNCTION__);
2190
2191         wpa_driver_nl80211_set_mode(drv, params->mode);
2192         wpa_driver_nl80211_set_auth_alg(drv, params->auth_alg);
2193
2194         /*
2195          * If the driver did not support SIOCSIWAUTH, fallback to
2196          * SIOCSIWENCODE here.
2197          */
2198         if (drv->auth_alg_fallback &&
2199             wpa_driver_nl80211_auth_alg_fallback(drv, params) < 0)
2200                 ret = -1;
2201
2202         if (!params->bssid &&
2203             wpa_driver_nl80211_set_bssid(drv, NULL) < 0)
2204                 ret = -1;
2205
2206         /* TODO: should consider getting wpa version and cipher/key_mgmt suites
2207          * from configuration, not from here, where only the selected suite is
2208          * available */
2209         if (wpa_driver_nl80211_set_gen_ie(drv, params->wpa_ie, params->wpa_ie_len)
2210             < 0)
2211                 ret = -1;
2212         if (params->wpa_ie == NULL || params->wpa_ie_len == 0)
2213                 value = IW_AUTH_WPA_VERSION_DISABLED;
2214         else if (params->wpa_ie[0] == WLAN_EID_RSN)
2215                 value = IW_AUTH_WPA_VERSION_WPA2;
2216         else
2217                 value = IW_AUTH_WPA_VERSION_WPA;
2218         if (wpa_driver_nl80211_set_auth_param(drv,
2219                                            IW_AUTH_WPA_VERSION, value) < 0)
2220                 ret = -1;
2221         value = wpa_driver_nl80211_cipher2wext(params->pairwise_suite);
2222         if (wpa_driver_nl80211_set_auth_param(drv,
2223                                            IW_AUTH_CIPHER_PAIRWISE, value) < 0)
2224                 ret = -1;
2225         value = wpa_driver_nl80211_cipher2wext(params->group_suite);
2226         if (wpa_driver_nl80211_set_auth_param(drv,
2227                                            IW_AUTH_CIPHER_GROUP, value) < 0)
2228                 ret = -1;
2229         value = wpa_driver_nl80211_keymgmt2wext(params->key_mgmt_suite);
2230         if (wpa_driver_nl80211_set_auth_param(drv,
2231                                            IW_AUTH_KEY_MGMT, value) < 0)
2232                 ret = -1;
2233         value = params->key_mgmt_suite != KEY_MGMT_NONE ||
2234                 params->pairwise_suite != CIPHER_NONE ||
2235                 params->group_suite != CIPHER_NONE ||
2236                 params->wpa_ie_len;
2237         if (wpa_driver_nl80211_set_auth_param(drv,
2238                                            IW_AUTH_PRIVACY_INVOKED, value) < 0)
2239                 ret = -1;
2240
2241         /* Allow unencrypted EAPOL messages even if pairwise keys are set when
2242          * not using WPA. IEEE 802.1X specifies that these frames are not
2243          * encrypted, but WPA encrypts them when pairwise keys are in use. */
2244         if (params->key_mgmt_suite == KEY_MGMT_802_1X ||
2245             params->key_mgmt_suite == KEY_MGMT_PSK)
2246                 allow_unencrypted_eapol = 0;
2247         else
2248                 allow_unencrypted_eapol = 1;
2249         
2250         if (wpa_driver_nl80211_set_auth_param(drv,
2251                                            IW_AUTH_RX_UNENCRYPTED_EAPOL,
2252                                            allow_unencrypted_eapol) < 0)
2253                 ret = -1;
2254         if (params->freq && wpa_driver_nl80211_set_freq(drv, params->freq) < 0)
2255                 ret = -1;
2256         if (wpa_driver_nl80211_set_ssid(drv, params->ssid, params->ssid_len) < 0)
2257                 ret = -1;
2258         if (params->bssid &&
2259             wpa_driver_nl80211_set_bssid(drv, params->bssid) < 0)
2260                 ret = -1;
2261
2262         return ret;
2263 }
2264 #endif /* WEXT_COMPAT */
2265
2266
2267 static int wpa_driver_nl80211_authenticate(
2268         void *priv, struct wpa_driver_auth_params *params)
2269 {
2270         struct wpa_driver_nl80211_data *drv = priv;
2271         int ret = -1;
2272         struct nl_msg *msg;
2273         enum nl80211_auth_type type;
2274
2275         drv->associated = 0;
2276
2277         msg = nlmsg_alloc();
2278         if (!msg)
2279                 return -1;
2280
2281         wpa_printf(MSG_DEBUG, "nl80211: Authenticate (ifindex=%d)",
2282                    drv->ifindex);
2283         genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0, 0,
2284                     NL80211_CMD_AUTHENTICATE, 0);
2285
2286         NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
2287         if (params->bssid) {
2288                 wpa_printf(MSG_DEBUG, "  * bssid=" MACSTR,
2289                            MAC2STR(params->bssid));
2290                 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, params->bssid);
2291         }
2292         if (params->freq) {
2293                 wpa_printf(MSG_DEBUG, "  * freq=%d", params->freq);
2294                 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY_FREQ, params->freq);
2295         }
2296         if (params->ssid) {
2297                 wpa_hexdump_ascii(MSG_DEBUG, "  * SSID",
2298                                   params->ssid, params->ssid_len);
2299                 NLA_PUT(msg, NL80211_ATTR_SSID, params->ssid_len,
2300                         params->ssid);
2301         }
2302         wpa_hexdump(MSG_DEBUG, "  * IEs", params->ie, params->ie_len);
2303         if (params->ie)
2304                 NLA_PUT(msg, NL80211_ATTR_IE, params->ie_len, params->ie);
2305         /*
2306          * TODO: if multiple auth_alg options enabled, try them one by one if
2307          * the AP rejects authentication due to unknown auth alg
2308          */
2309         if (params->auth_alg & AUTH_ALG_OPEN_SYSTEM)
2310                 type = NL80211_AUTHTYPE_OPEN_SYSTEM;
2311         else if (params->auth_alg & AUTH_ALG_SHARED_KEY)
2312                 type = NL80211_AUTHTYPE_SHARED_KEY;
2313         else if (params->auth_alg & AUTH_ALG_LEAP)
2314                 type = NL80211_AUTHTYPE_NETWORK_EAP;
2315         else if (params->auth_alg & AUTH_ALG_FT)
2316                 type = NL80211_AUTHTYPE_FT;
2317         else
2318                 goto nla_put_failure;
2319         wpa_printf(MSG_DEBUG, "  * Auth Type %d", type);
2320         NLA_PUT_U32(msg, NL80211_ATTR_AUTH_TYPE, type);
2321
2322         ret = send_and_recv_msgs(drv, msg, NULL, NULL);
2323         msg = NULL;
2324         if (ret) {
2325                 wpa_printf(MSG_DEBUG, "nl80211: MLME command failed: ret=%d "
2326                            "(%s)", ret, strerror(-ret));
2327                 goto nla_put_failure;
2328         }
2329         ret = 0;
2330         wpa_printf(MSG_DEBUG, "nl80211: Authentication request send "
2331                    "successfully");
2332
2333 nla_put_failure:
2334         nlmsg_free(msg);
2335         return ret;
2336 }
2337
2338
2339 #ifdef CONFIG_AP
2340 static int wpa_driver_nl80211_set_freq2(
2341         struct wpa_driver_nl80211_data *drv,
2342         struct wpa_driver_associate_params *params)
2343 {
2344         struct nl_msg *msg;
2345
2346         msg = nlmsg_alloc();
2347         if (!msg)
2348                 return -1;
2349
2350         genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0, 0,
2351                     NL80211_CMD_SET_WIPHY, 0);
2352
2353         NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
2354
2355         /* TODO: proper channel configuration */
2356         NLA_PUT_U32(msg, NL80211_ATTR_WIPHY_FREQ, 2437);
2357
2358         if (send_and_recv_msgs(drv, msg, NULL, NULL) == 0)
2359                 return 0;
2360 nla_put_failure:
2361         return -1;
2362 }
2363
2364
2365 static int wpa_driver_nl80211_ap(struct wpa_driver_nl80211_data *drv,
2366                                  struct wpa_driver_associate_params *params)
2367 {
2368         if (wpa_driver_nl80211_set_mode(drv, params->mode) ||
2369             wpa_driver_nl80211_set_freq2(drv, params))
2370                 return -1;
2371
2372         /* TODO: setup monitor interface (and add code somewhere to remove this
2373          * when AP mode is stopped; associate with mode != 2 or drv_deinit) */
2374         /* TODO: setup beacon */
2375
2376         return 0;
2377 }
2378 #endif /* CONFIG_AP */
2379
2380
2381 static int wpa_driver_nl80211_associate(
2382         void *priv, struct wpa_driver_associate_params *params)
2383 {
2384         struct wpa_driver_nl80211_data *drv = priv;
2385         int ret = -1;
2386         struct nl_msg *msg;
2387
2388 #ifdef CONFIG_AP
2389         if (params->mode == 2)
2390                 return wpa_driver_nl80211_ap(drv, params);
2391 #endif /* CONFIG_AP */
2392
2393         wpa_driver_nl80211_set_auth_param(drv, IW_AUTH_DROP_UNENCRYPTED,
2394                                           params->drop_unencrypted);
2395
2396 #ifdef WEXT_COMPAT
2397         if (!(drv->capa.flags & WPA_DRIVER_FLAGS_SME))
2398                 return wpa_driver_nl80211_associate_wext(drv, params);
2399 #endif /* WEXT_COMPAT */
2400
2401         drv->associated = 0;
2402
2403         msg = nlmsg_alloc();
2404         if (!msg)
2405                 return -1;
2406
2407         wpa_printf(MSG_DEBUG, "nl80211: Associate (ifindex=%d)",
2408                    drv->ifindex);
2409         genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0, 0,
2410                     NL80211_CMD_ASSOCIATE, 0);
2411
2412         NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
2413         if (params->bssid) {
2414                 wpa_printf(MSG_DEBUG, "  * bssid=" MACSTR,
2415                            MAC2STR(params->bssid));
2416                 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, params->bssid);
2417         }
2418         if (params->freq) {
2419                 wpa_printf(MSG_DEBUG, "  * freq=%d", params->freq);
2420                 NLA_PUT_U32(msg, NL80211_ATTR_WIPHY_FREQ, params->freq);
2421         }
2422         if (params->ssid) {
2423                 wpa_hexdump_ascii(MSG_DEBUG, "  * SSID",
2424                                   params->ssid, params->ssid_len);
2425                 NLA_PUT(msg, NL80211_ATTR_SSID, params->ssid_len,
2426                         params->ssid);
2427                 if (params->ssid_len > sizeof(drv->ssid))
2428                         goto nla_put_failure;
2429                 os_memcpy(drv->ssid, params->ssid, params->ssid_len);
2430                 drv->ssid_len = params->ssid_len;
2431         }
2432         wpa_hexdump(MSG_DEBUG, "  * IEs", params->wpa_ie, params->wpa_ie_len);
2433         if (params->wpa_ie)
2434                 NLA_PUT(msg, NL80211_ATTR_IE, params->wpa_ie_len,
2435                         params->wpa_ie);
2436
2437         ret = send_and_recv_msgs(drv, msg, NULL, NULL);
2438         msg = NULL;
2439         if (ret) {
2440                 wpa_printf(MSG_DEBUG, "nl80211: MLME command failed: ret=%d "
2441                            "(%s)", ret, strerror(-ret));
2442                 goto nla_put_failure;
2443         }
2444         ret = 0;
2445         wpa_printf(MSG_DEBUG, "nl80211: Association request send "
2446                    "successfully");
2447
2448 nla_put_failure:
2449         nlmsg_free(msg);
2450         return ret;
2451 }
2452
2453
2454 /**
2455  * wpa_driver_nl80211_set_mode - Set wireless mode (infra/adhoc), SIOCSIWMODE
2456  * @drv: Pointer to private driver data from wpa_driver_nl80211_init()
2457  * @mode: 0 = infra/BSS (associate with an AP), 1 = adhoc/IBSS
2458  * Returns: 0 on success, -1 on failure
2459  */
2460 static int wpa_driver_nl80211_set_mode(struct wpa_driver_nl80211_data *drv,
2461                                        int mode)
2462 {
2463         int ret = -1, flags;
2464         struct nl_msg *msg;
2465         int nlmode;
2466
2467         switch (mode) {
2468         case 0:
2469                 nlmode = NL80211_IFTYPE_STATION;
2470                 break;
2471         case 1:
2472                 nlmode = NL80211_IFTYPE_ADHOC;
2473                 break;
2474         case 2:
2475                 nlmode = NL80211_IFTYPE_AP;
2476                 break;
2477         default:
2478                 return -1;
2479         }
2480
2481         msg = nlmsg_alloc();
2482         if (!msg)
2483                 return -1;
2484
2485         genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
2486                     0, NL80211_CMD_SET_INTERFACE, 0);
2487         NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
2488         NLA_PUT_U32(msg, NL80211_ATTR_IFTYPE, nlmode);
2489
2490         ret = send_and_recv_msgs(drv, msg, NULL, NULL);
2491         if (!ret)
2492                 return 0;
2493         else
2494                 goto try_again;
2495
2496 nla_put_failure:
2497         wpa_printf(MSG_ERROR, "nl80211: Failed to set interface mode: %d (%s)",
2498                    ret, strerror(-ret));
2499         return -1;
2500
2501 try_again:
2502         /* mac80211 doesn't allow mode changes while the device is up, so
2503          * take the device down, try to set the mode again, and bring the
2504          * device back up.
2505          */
2506         if (wpa_driver_nl80211_get_ifflags(drv, &flags) == 0) {
2507                 (void) wpa_driver_nl80211_set_ifflags(drv, flags & ~IFF_UP);
2508
2509                 /* Try to set the mode again while the interface is down */
2510                 msg = nlmsg_alloc();
2511                 if (!msg)
2512                         return -1;
2513
2514                 genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
2515                             0, NL80211_CMD_SET_INTERFACE, 0);
2516                 NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
2517                 NLA_PUT_U32(msg, NL80211_ATTR_IFTYPE, nlmode);
2518                 ret = send_and_recv_msgs(drv, msg, NULL, NULL);
2519                 if (ret) {
2520                         wpa_printf(MSG_ERROR, "Failed to set interface %s "
2521                                    "mode(try_again): %d (%s)",
2522                                    drv->ifname, ret, strerror(-ret));
2523                 }
2524
2525                 /* Ignore return value of get_ifflags to ensure that the device
2526                  * is always up like it was before this function was called.
2527                  */
2528                 (void) wpa_driver_nl80211_get_ifflags(drv, &flags);
2529                 (void) wpa_driver_nl80211_set_ifflags(drv, flags | IFF_UP);
2530         }
2531
2532         return ret;
2533 }
2534
2535
2536 #ifdef WEXT_COMPAT
2537
2538 static int wpa_driver_nl80211_pmksa(struct wpa_driver_nl80211_data *drv,
2539                                  u32 cmd, const u8 *bssid, const u8 *pmkid)
2540 {
2541         struct iwreq iwr;
2542         struct iw_pmksa pmksa;
2543         int ret = 0;
2544
2545         os_memset(&iwr, 0, sizeof(iwr));
2546         os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
2547         os_memset(&pmksa, 0, sizeof(pmksa));
2548         pmksa.cmd = cmd;
2549         pmksa.bssid.sa_family = ARPHRD_ETHER;
2550         if (bssid)
2551                 os_memcpy(pmksa.bssid.sa_data, bssid, ETH_ALEN);
2552         if (pmkid)
2553                 os_memcpy(pmksa.pmkid, pmkid, IW_PMKID_LEN);
2554         iwr.u.data.pointer = (caddr_t) &pmksa;
2555         iwr.u.data.length = sizeof(pmksa);
2556
2557         if (ioctl(drv->ioctl_sock, SIOCSIWPMKSA, &iwr) < 0) {
2558                 if (errno != EOPNOTSUPP)
2559                         perror("ioctl[SIOCSIWPMKSA]");
2560                 ret = -1;
2561         }
2562
2563         return ret;
2564 }
2565
2566
2567 static int wpa_driver_nl80211_add_pmkid(void *priv, const u8 *bssid,
2568                                      const u8 *pmkid)
2569 {
2570         struct wpa_driver_nl80211_data *drv = priv;
2571         return wpa_driver_nl80211_pmksa(drv, IW_PMKSA_ADD, bssid, pmkid);
2572 }
2573
2574
2575 static int wpa_driver_nl80211_remove_pmkid(void *priv, const u8 *bssid,
2576                                         const u8 *pmkid)
2577 {
2578         struct wpa_driver_nl80211_data *drv = priv;
2579         return wpa_driver_nl80211_pmksa(drv, IW_PMKSA_REMOVE, bssid, pmkid);
2580 }
2581
2582
2583 static int wpa_driver_nl80211_flush_pmkid(void *priv)
2584 {
2585         struct wpa_driver_nl80211_data *drv = priv;
2586         return wpa_driver_nl80211_pmksa(drv, IW_PMKSA_FLUSH, NULL, NULL);
2587 }
2588
2589 #endif /* WEXT_COMPAT */
2590
2591
2592 static int wpa_driver_nl80211_get_capa(void *priv,
2593                                        struct wpa_driver_capa *capa)
2594 {
2595         struct wpa_driver_nl80211_data *drv = priv;
2596         if (!drv->has_capability)
2597                 return -1;
2598         os_memcpy(capa, &drv->capa, sizeof(*capa));
2599         return 0;
2600 }
2601
2602
2603 static int wpa_driver_nl80211_set_operstate(void *priv, int state)
2604 {
2605         struct wpa_driver_nl80211_data *drv = priv;
2606
2607         wpa_printf(MSG_DEBUG, "%s: operstate %d->%d (%s)",
2608                    __func__, drv->operstate, state, state ? "UP" : "DORMANT");
2609         drv->operstate = state;
2610         return wpa_driver_nl80211_send_oper_ifla(
2611                 drv, -1, state ? IF_OPER_UP : IF_OPER_DORMANT);
2612 }
2613
2614
2615 const struct wpa_driver_ops wpa_driver_nl80211_ops = {
2616         .name = "nl80211",
2617         .desc = "Linux nl80211/cfg80211",
2618         .get_bssid = wpa_driver_nl80211_get_bssid,
2619         .get_ssid = wpa_driver_nl80211_get_ssid,
2620         .set_key = wpa_driver_nl80211_set_key,
2621         .scan2 = wpa_driver_nl80211_scan,
2622         .get_scan_results2 = wpa_driver_nl80211_get_scan_results,
2623         .deauthenticate = wpa_driver_nl80211_deauthenticate,
2624         .disassociate = wpa_driver_nl80211_disassociate,
2625         .authenticate = wpa_driver_nl80211_authenticate,
2626         .associate = wpa_driver_nl80211_associate,
2627         .init = wpa_driver_nl80211_init,
2628         .deinit = wpa_driver_nl80211_deinit,
2629         .get_capa = wpa_driver_nl80211_get_capa,
2630         .set_operstate = wpa_driver_nl80211_set_operstate,
2631         .set_country = wpa_driver_nl80211_set_country,
2632 #ifdef WEXT_COMPAT
2633         .set_wpa = wpa_driver_nl80211_set_wpa,
2634         .set_countermeasures = wpa_driver_nl80211_set_countermeasures,
2635         .add_pmkid = wpa_driver_nl80211_add_pmkid,
2636         .remove_pmkid = wpa_driver_nl80211_remove_pmkid,
2637         .flush_pmkid = wpa_driver_nl80211_flush_pmkid,
2638 #endif /* WEXT_COMPAT */
2639 };