Use a wrapper function for ieee802_1x_receive() to avoid ieee802_1x.h
[mech_eap.git] / hostapd / driver_test.c
1 /*
2  * hostapd / Driver interface for development testing
3  * Copyright (c) 2004-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/un.h>
17 #include <dirent.h>
18
19 #include "hostapd.h"
20 #include "driver.h"
21 #include "sha1.h"
22 #include "eloop.h"
23 #include "wpa.h"
24 #include "l2_packet/l2_packet.h"
25 #include "ieee802_11.h"
26 #include "hw_features.h"
27 #include "wps_hostapd.h"
28
29
30 struct test_client_socket {
31         struct test_client_socket *next;
32         u8 addr[ETH_ALEN];
33         struct sockaddr_un un;
34         socklen_t unlen;
35         struct test_driver_bss *bss;
36 };
37
38 struct test_driver_bss {
39         struct test_driver_bss *next;
40         char ifname[IFNAMSIZ + 1];
41         u8 bssid[ETH_ALEN];
42         u8 *ie;
43         size_t ielen;
44         u8 *wps_beacon_ie;
45         size_t wps_beacon_ie_len;
46         u8 *wps_probe_resp_ie;
47         size_t wps_probe_resp_ie_len;
48         u8 ssid[32];
49         size_t ssid_len;
50         int privacy;
51 };
52
53 struct test_driver_data {
54         struct hostapd_data *hapd;
55         struct test_client_socket *cli;
56         int test_socket;
57         struct test_driver_bss *bss;
58         char *socket_dir;
59         char *own_socket_path;
60         int udp_port;
61 };
62
63
64 static void test_driver_free_bss(struct test_driver_bss *bss)
65 {
66         free(bss->ie);
67         free(bss->wps_beacon_ie);
68         free(bss->wps_probe_resp_ie);
69         free(bss);
70 }
71
72
73 static void test_driver_free_priv(struct test_driver_data *drv)
74 {
75         struct test_driver_bss *bss, *prev;
76
77         if (drv == NULL)
78                 return;
79
80         bss = drv->bss;
81         while (bss) {
82                 prev = bss;
83                 bss = bss->next;
84                 test_driver_free_bss(prev);
85         }
86         free(drv->own_socket_path);
87         free(drv->socket_dir);
88         free(drv);
89 }
90
91
92 static struct test_client_socket *
93 test_driver_get_cli(struct test_driver_data *drv, struct sockaddr_un *from,
94                     socklen_t fromlen)
95 {
96         struct test_client_socket *cli = drv->cli;
97
98         while (cli) {
99                 if (cli->unlen == fromlen &&
100                     strncmp(cli->un.sun_path, from->sun_path,
101                             fromlen - sizeof(cli->un.sun_family)) == 0)
102                         return cli;
103                 cli = cli->next;
104         }
105
106         return NULL;
107 }
108
109
110 static int test_driver_send_eapol(void *priv, const u8 *addr, const u8 *data,
111                                   size_t data_len, int encrypt,
112                                   const u8 *own_addr)
113 {
114         struct test_driver_data *drv = priv;
115         struct test_client_socket *cli;
116         struct msghdr msg;
117         struct iovec io[3];
118         struct l2_ethhdr eth;
119
120         if (drv->test_socket < 0)
121                 return -1;
122
123         cli = drv->cli;
124         while (cli) {
125                 if (memcmp(cli->addr, addr, ETH_ALEN) == 0)
126                         break;
127                 cli = cli->next;
128         }
129
130         if (!cli) {
131                 wpa_printf(MSG_DEBUG, "%s: no destination client entry",
132                            __func__);
133                 return -1;
134         }
135
136         memcpy(eth.h_dest, addr, ETH_ALEN);
137         memcpy(eth.h_source, own_addr, ETH_ALEN);
138         eth.h_proto = host_to_be16(ETH_P_EAPOL);
139
140         io[0].iov_base = "EAPOL ";
141         io[0].iov_len = 6;
142         io[1].iov_base = &eth;
143         io[1].iov_len = sizeof(eth);
144         io[2].iov_base = (u8 *) data;
145         io[2].iov_len = data_len;
146
147         memset(&msg, 0, sizeof(msg));
148         msg.msg_iov = io;
149         msg.msg_iovlen = 3;
150         msg.msg_name = &cli->un;
151         msg.msg_namelen = cli->unlen;
152         return sendmsg(drv->test_socket, &msg, 0);
153 }
154
155
156 static int test_driver_send_ether(void *priv, const u8 *dst, const u8 *src,
157                                   u16 proto, const u8 *data, size_t data_len)
158 {
159         struct test_driver_data *drv = priv;
160         struct msghdr msg;
161         struct iovec io[3];
162         struct l2_ethhdr eth;
163         char desttxt[30];
164         struct sockaddr_un addr;
165         struct dirent *dent;
166         DIR *dir;
167         int ret = 0, broadcast = 0, count = 0;
168
169         if (drv->test_socket < 0 || drv->socket_dir == NULL) {
170                 wpa_printf(MSG_DEBUG, "%s: invalid parameters (sock=%d "
171                            "socket_dir=%p)",
172                            __func__, drv->test_socket, drv->socket_dir);
173                 return -1;
174         }
175
176         broadcast = memcmp(dst, "\xff\xff\xff\xff\xff\xff", ETH_ALEN) == 0;
177         snprintf(desttxt, sizeof(desttxt), MACSTR, MAC2STR(dst));
178
179         memcpy(eth.h_dest, dst, ETH_ALEN);
180         memcpy(eth.h_source, src, ETH_ALEN);
181         eth.h_proto = host_to_be16(proto);
182
183         io[0].iov_base = "ETHER ";
184         io[0].iov_len = 6;
185         io[1].iov_base = &eth;
186         io[1].iov_len = sizeof(eth);
187         io[2].iov_base = (u8 *) data;
188         io[2].iov_len = data_len;
189
190         memset(&msg, 0, sizeof(msg));
191         msg.msg_iov = io;
192         msg.msg_iovlen = 3;
193
194         dir = opendir(drv->socket_dir);
195         if (dir == NULL) {
196                 perror("test_driver: opendir");
197                 return -1;
198         }
199         while ((dent = readdir(dir))) {
200 #ifdef _DIRENT_HAVE_D_TYPE
201                 /* Skip the file if it is not a socket. Also accept
202                  * DT_UNKNOWN (0) in case the C library or underlying file
203                  * system does not support d_type. */
204                 if (dent->d_type != DT_SOCK && dent->d_type != DT_UNKNOWN)
205                         continue;
206 #endif /* _DIRENT_HAVE_D_TYPE */
207                 if (strcmp(dent->d_name, ".") == 0 ||
208                     strcmp(dent->d_name, "..") == 0)
209                         continue;
210
211                 memset(&addr, 0, sizeof(addr));
212                 addr.sun_family = AF_UNIX;
213                 snprintf(addr.sun_path, sizeof(addr.sun_path), "%s/%s",
214                          drv->socket_dir, dent->d_name);
215
216                 if (strcmp(addr.sun_path, drv->own_socket_path) == 0)
217                         continue;
218                 if (!broadcast && strstr(dent->d_name, desttxt) == NULL)
219                         continue;
220
221                 wpa_printf(MSG_DEBUG, "%s: Send ether frame to %s",
222                            __func__, dent->d_name);
223
224                 msg.msg_name = &addr;
225                 msg.msg_namelen = sizeof(addr);
226                 ret = sendmsg(drv->test_socket, &msg, 0);
227                 if (ret < 0)
228                         perror("driver_test: sendmsg");
229                 count++;
230         }
231         closedir(dir);
232
233         if (!broadcast && count == 0) {
234                 wpa_printf(MSG_DEBUG, "%s: Destination " MACSTR " not found",
235                            __func__, MAC2STR(dst));
236                 return -1;
237         }
238
239         return ret;
240 }
241
242
243 static int test_driver_send_mgmt_frame(void *priv, const void *buf,
244                                        size_t len, int flags)
245 {
246         struct test_driver_data *drv = priv;
247         struct msghdr msg;
248         struct iovec io[2];
249         const u8 *dest;
250         int ret = 0, broadcast = 0;
251         char desttxt[30];
252         struct sockaddr_un addr;
253         struct dirent *dent;
254         DIR *dir;
255         struct ieee80211_hdr *hdr;
256         u16 fc;
257
258         if (drv->test_socket < 0 || len < 10 || drv->socket_dir == NULL) {
259                 wpa_printf(MSG_DEBUG, "%s: invalid parameters (sock=%d len=%lu"
260                            " socket_dir=%p)",
261                            __func__, drv->test_socket, (unsigned long) len,
262                            drv->socket_dir);
263                 return -1;
264         }
265
266         dest = buf;
267         dest += 4;
268         broadcast = memcmp(dest, "\xff\xff\xff\xff\xff\xff", ETH_ALEN) == 0;
269         snprintf(desttxt, sizeof(desttxt), MACSTR, MAC2STR(dest));
270
271         io[0].iov_base = "MLME ";
272         io[0].iov_len = 5;
273         io[1].iov_base = (void *) buf;
274         io[1].iov_len = len;
275
276         memset(&msg, 0, sizeof(msg));
277         msg.msg_iov = io;
278         msg.msg_iovlen = 2;
279
280         dir = opendir(drv->socket_dir);
281         if (dir == NULL) {
282                 perror("test_driver: opendir");
283                 return -1;
284         }
285         while ((dent = readdir(dir))) {
286 #ifdef _DIRENT_HAVE_D_TYPE
287                 /* Skip the file if it is not a socket. Also accept
288                  * DT_UNKNOWN (0) in case the C library or underlying file
289                  * system does not support d_type. */
290                 if (dent->d_type != DT_SOCK && dent->d_type != DT_UNKNOWN)
291                         continue;
292 #endif /* _DIRENT_HAVE_D_TYPE */
293                 if (strcmp(dent->d_name, ".") == 0 ||
294                     strcmp(dent->d_name, "..") == 0)
295                         continue;
296
297                 memset(&addr, 0, sizeof(addr));
298                 addr.sun_family = AF_UNIX;
299                 snprintf(addr.sun_path, sizeof(addr.sun_path), "%s/%s",
300                          drv->socket_dir, dent->d_name);
301
302                 if (strcmp(addr.sun_path, drv->own_socket_path) == 0)
303                         continue;
304                 if (!broadcast && strstr(dent->d_name, desttxt) == NULL)
305                         continue;
306
307                 wpa_printf(MSG_DEBUG, "%s: Send management frame to %s",
308                            __func__, dent->d_name);
309
310                 msg.msg_name = &addr;
311                 msg.msg_namelen = sizeof(addr);
312                 ret = sendmsg(drv->test_socket, &msg, 0);
313                 if (ret < 0)
314                         perror("driver_test: sendmsg");
315         }
316         closedir(dir);
317
318         hdr = (struct ieee80211_hdr *) buf;
319         fc = le_to_host16(hdr->frame_control);
320         ieee802_11_mgmt_cb(drv->hapd, (u8 *) buf, len, WLAN_FC_GET_STYPE(fc),
321                            ret >= 0);
322
323         return ret;
324 }
325
326
327 static void test_driver_scan(struct test_driver_data *drv,
328                              struct sockaddr_un *from, socklen_t fromlen,
329                              char *data)
330 {
331         char buf[512], *pos, *end;
332         int ret;
333         struct test_driver_bss *bss;
334         u8 sa[ETH_ALEN];
335         u8 ie[512];
336         size_t ielen;
337
338         /* data: optional [ ' ' | STA-addr | ' ' | IEs(hex) ] */
339
340         wpa_printf(MSG_DEBUG, "test_driver: SCAN");
341
342         if (*data) {
343                 if (*data != ' ' ||
344                     hwaddr_aton(data + 1, sa)) {
345                         wpa_printf(MSG_DEBUG, "test_driver: Unexpected SCAN "
346                                    "command format");
347                         return;
348                 }
349
350                 data += 18;
351                 while (*data == ' ')
352                         data++;
353                 ielen = os_strlen(data) / 2;
354                 if (ielen > sizeof(ie))
355                         ielen = sizeof(ie);
356                 if (hexstr2bin(data, ie, ielen) < 0)
357                         ielen = 0;
358
359                 wpa_printf(MSG_DEBUG, "test_driver: Scan from " MACSTR,
360                            MAC2STR(sa));
361                 wpa_hexdump(MSG_MSGDUMP, "test_driver: scan IEs", ie, ielen);
362
363                 hostapd_wps_probe_req_rx(drv->hapd, sa, ie, ielen);
364         }
365
366         for (bss = drv->bss; bss; bss = bss->next) {
367                 pos = buf;
368                 end = buf + sizeof(buf);
369
370                 /* reply: SCANRESP BSSID SSID IEs */
371                 ret = snprintf(pos, end - pos, "SCANRESP " MACSTR " ",
372                                MAC2STR(bss->bssid));
373                 if (ret < 0 || ret >= end - pos)
374                         return;
375                 pos += ret;
376                 pos += wpa_snprintf_hex(pos, end - pos,
377                                         bss->ssid, bss->ssid_len);
378                 ret = snprintf(pos, end - pos, " ");
379                 if (ret < 0 || ret >= end - pos)
380                         return;
381                 pos += ret;
382                 pos += wpa_snprintf_hex(pos, end - pos, bss->ie, bss->ielen);
383                 pos += wpa_snprintf_hex(pos, end - pos, bss->wps_probe_resp_ie,
384                                         bss->wps_probe_resp_ie_len);
385
386                 if (bss->privacy) {
387                         ret = snprintf(pos, end - pos, " PRIVACY");
388                         if (ret < 0 || ret >= end - pos)
389                                 return;
390                         pos += ret;
391                 }
392
393                 sendto(drv->test_socket, buf, pos - buf, 0,
394                        (struct sockaddr *) from, fromlen);
395         }
396 }
397
398
399 static struct hostapd_data * test_driver_get_hapd(struct test_driver_data *drv,
400                                                   struct test_driver_bss *bss)
401 {
402         struct hostapd_iface *iface = drv->hapd->iface;
403         struct hostapd_data *hapd = NULL;
404         size_t i;
405
406         if (bss == NULL) {
407                 wpa_printf(MSG_DEBUG, "%s: bss == NULL", __func__);
408                 return NULL;
409         }
410
411         for (i = 0; i < iface->num_bss; i++) {
412                 hapd = iface->bss[i];
413                 if (memcmp(hapd->own_addr, bss->bssid, ETH_ALEN) == 0)
414                         break;
415         }
416         if (i == iface->num_bss) {
417                 wpa_printf(MSG_DEBUG, "%s: no matching interface entry found "
418                            "for BSSID " MACSTR, __func__, MAC2STR(bss->bssid));
419                 return NULL;
420         }
421
422         return hapd;
423 }
424
425
426 static int test_driver_new_sta(struct test_driver_data *drv,
427                                struct test_driver_bss *bss, const u8 *addr,
428                                const u8 *ie, size_t ielen)
429 {
430         struct hostapd_data *hapd;
431
432         hapd = test_driver_get_hapd(drv, bss);
433         if (hapd == NULL)
434                 return -1;
435
436         return hostapd_notif_assoc(hapd, addr, ie, ielen);
437 }
438
439
440 static void test_driver_assoc(struct test_driver_data *drv,
441                               struct sockaddr_un *from, socklen_t fromlen,
442                               char *data)
443 {
444         struct test_client_socket *cli;
445         u8 ie[256], ssid[32];
446         size_t ielen, ssid_len = 0;
447         char *pos, *pos2, cmd[50];
448         struct test_driver_bss *bss;
449
450         /* data: STA-addr SSID(hex) IEs(hex) */
451
452         cli = os_zalloc(sizeof(*cli));
453         if (cli == NULL)
454                 return;
455
456         if (hwaddr_aton(data, cli->addr)) {
457                 printf("test_socket: Invalid MAC address '%s' in ASSOC\n",
458                        data);
459                 free(cli);
460                 return;
461         }
462         pos = data + 17;
463         while (*pos == ' ')
464                 pos++;
465         pos2 = strchr(pos, ' ');
466         ielen = 0;
467         if (pos2) {
468                 ssid_len = (pos2 - pos) / 2;
469                 if (hexstr2bin(pos, ssid, ssid_len) < 0) {
470                         wpa_printf(MSG_DEBUG, "%s: Invalid SSID", __func__);
471                         free(cli);
472                         return;
473                 }
474                 wpa_hexdump_ascii(MSG_DEBUG, "test_driver_assoc: SSID",
475                                   ssid, ssid_len);
476
477                 pos = pos2 + 1;
478                 ielen = strlen(pos) / 2;
479                 if (ielen > sizeof(ie))
480                         ielen = sizeof(ie);
481                 if (hexstr2bin(pos, ie, ielen) < 0)
482                         ielen = 0;
483         }
484
485         for (bss = drv->bss; bss; bss = bss->next) {
486                 if (bss->ssid_len == ssid_len &&
487                     memcmp(bss->ssid, ssid, ssid_len) == 0)
488                         break;
489         }
490         if (bss == NULL) {
491                 wpa_printf(MSG_DEBUG, "%s: No matching SSID found from "
492                            "configured BSSes", __func__);
493                 free(cli);
494                 return;
495         }
496
497         cli->bss = bss;
498         memcpy(&cli->un, from, sizeof(cli->un));
499         cli->unlen = fromlen;
500         cli->next = drv->cli;
501         drv->cli = cli;
502         wpa_hexdump_ascii(MSG_DEBUG, "test_socket: ASSOC sun_path",
503                           (const u8 *) cli->un.sun_path,
504                           cli->unlen - sizeof(cli->un.sun_family));
505
506         snprintf(cmd, sizeof(cmd), "ASSOCRESP " MACSTR " 0",
507                  MAC2STR(bss->bssid));
508         sendto(drv->test_socket, cmd, strlen(cmd), 0,
509                (struct sockaddr *) from, fromlen);
510
511         if (test_driver_new_sta(drv, bss, cli->addr, ie, ielen) < 0) {
512                 wpa_printf(MSG_DEBUG, "test_driver: failed to add new STA");
513         }
514 }
515
516
517 static void test_driver_disassoc(struct test_driver_data *drv,
518                                  struct sockaddr_un *from, socklen_t fromlen)
519 {
520         struct test_client_socket *cli;
521
522         cli = test_driver_get_cli(drv, from, fromlen);
523         if (!cli)
524                 return;
525
526         hostapd_notif_disassoc(drv->hapd, cli->addr);
527 }
528
529
530 static void test_driver_eapol(struct test_driver_data *drv,
531                               struct sockaddr_un *from, socklen_t fromlen,
532                               u8 *data, size_t datalen)
533 {
534         struct test_client_socket *cli;
535         if (datalen > 14) {
536                 u8 *proto = data + 2 * ETH_ALEN;
537                 /* Skip Ethernet header */
538                 wpa_printf(MSG_DEBUG, "test_driver: dst=" MACSTR " src="
539                            MACSTR " proto=%04x",
540                            MAC2STR(data), MAC2STR(data + ETH_ALEN),
541                            WPA_GET_BE16(proto));
542                 data += 14;
543                 datalen -= 14;
544         }
545         cli = test_driver_get_cli(drv, from, fromlen);
546         if (cli) {
547                 struct hostapd_data *hapd;
548                 hapd = test_driver_get_hapd(drv, cli->bss);
549                 if (hapd == NULL)
550                         return;
551                 hostapd_eapol_receive(hapd, cli->addr, data, datalen);
552         } else {
553                 wpa_printf(MSG_DEBUG, "test_socket: EAPOL from unknown "
554                            "client");
555         }
556 }
557
558
559 static void test_driver_ether(struct test_driver_data *drv,
560                               struct sockaddr_un *from, socklen_t fromlen,
561                               u8 *data, size_t datalen)
562 {
563         struct l2_ethhdr *eth;
564
565         if (datalen < sizeof(*eth))
566                 return;
567
568         eth = (struct l2_ethhdr *) data;
569         wpa_printf(MSG_DEBUG, "test_driver: RX ETHER dst=" MACSTR " src="
570                    MACSTR " proto=%04x",
571                    MAC2STR(eth->h_dest), MAC2STR(eth->h_source),
572                    be_to_host16(eth->h_proto));
573
574 #ifdef CONFIG_IEEE80211R
575         if (be_to_host16(eth->h_proto) == ETH_P_RRB) {
576                 wpa_ft_rrb_rx(drv->hapd->wpa_auth, eth->h_source,
577                               data + sizeof(*eth), datalen - sizeof(*eth));
578         }
579 #endif /* CONFIG_IEEE80211R */
580 }
581
582
583 static void test_driver_mlme(struct test_driver_data *drv,
584                              struct sockaddr_un *from, socklen_t fromlen,
585                              u8 *data, size_t datalen)
586 {
587         struct ieee80211_hdr *hdr;
588         u16 fc;
589
590         hdr = (struct ieee80211_hdr *) data;
591
592         if (test_driver_get_cli(drv, from, fromlen) == NULL && datalen >= 16) {
593                 struct test_client_socket *cli;
594                 cli = os_zalloc(sizeof(*cli));
595                 if (cli == NULL)
596                         return;
597                 wpa_printf(MSG_DEBUG, "Adding client entry for " MACSTR,
598                            MAC2STR(hdr->addr2));
599                 memcpy(cli->addr, hdr->addr2, ETH_ALEN);
600                 memcpy(&cli->un, from, sizeof(cli->un));
601                 cli->unlen = fromlen;
602                 cli->next = drv->cli;
603                 drv->cli = cli;
604         }
605
606         wpa_hexdump(MSG_MSGDUMP, "test_driver_mlme: received frame",
607                     data, datalen);
608         fc = le_to_host16(hdr->frame_control);
609         if (WLAN_FC_GET_TYPE(fc) != WLAN_FC_TYPE_MGMT) {
610                 wpa_printf(MSG_ERROR, "%s: received non-mgmt frame",
611                            __func__);
612                 return;
613         }
614         ieee802_11_mgmt(drv->hapd, data, datalen, WLAN_FC_GET_STYPE(fc), NULL);
615 }
616
617
618 static void test_driver_receive_unix(int sock, void *eloop_ctx, void *sock_ctx)
619 {
620         struct test_driver_data *drv = eloop_ctx;
621         char buf[2000];
622         int res;
623         struct sockaddr_un from;
624         socklen_t fromlen = sizeof(from);
625
626         res = recvfrom(sock, buf, sizeof(buf) - 1, 0,
627                        (struct sockaddr *) &from, &fromlen);
628         if (res < 0) {
629                 perror("recvfrom(test_socket)");
630                 return;
631         }
632         buf[res] = '\0';
633
634         wpa_printf(MSG_DEBUG, "test_driver: received %u bytes", res);
635
636         if (strncmp(buf, "SCAN", 4) == 0) {
637                 test_driver_scan(drv, &from, fromlen, buf + 4);
638         } else if (strncmp(buf, "ASSOC ", 6) == 0) {
639                 test_driver_assoc(drv, &from, fromlen, buf + 6);
640         } else if (strcmp(buf, "DISASSOC") == 0) {
641                 test_driver_disassoc(drv, &from, fromlen);
642         } else if (strncmp(buf, "EAPOL ", 6) == 0) {
643                 test_driver_eapol(drv, &from, fromlen, (u8 *) buf + 6,
644                                   res - 6);
645         } else if (strncmp(buf, "ETHER ", 6) == 0) {
646                 test_driver_ether(drv, &from, fromlen, (u8 *) buf + 6,
647                                   res - 6);
648         } else if (strncmp(buf, "MLME ", 5) == 0) {
649                 test_driver_mlme(drv, &from, fromlen, (u8 *) buf + 5, res - 5);
650         } else {
651                 wpa_hexdump_ascii(MSG_DEBUG, "Unknown test_socket command",
652                                   (u8 *) buf, res);
653         }
654 }
655
656
657 static struct test_driver_bss *
658 test_driver_get_bss(struct test_driver_data *drv, const char *ifname)
659 {
660         struct test_driver_bss *bss;
661
662         for (bss = drv->bss; bss; bss = bss->next) {
663                 if (strcmp(bss->ifname, ifname) == 0)
664                         return bss;
665         }
666         return NULL;
667 }
668
669
670 static int test_driver_set_generic_elem(const char *ifname, void *priv,
671                                         const u8 *elem, size_t elem_len)
672 {
673         struct test_driver_data *drv = priv;
674         struct test_driver_bss *bss;
675
676         bss = test_driver_get_bss(drv, ifname);
677         if (bss == NULL)
678                 return -1;
679
680         free(bss->ie);
681
682         if (elem == NULL) {
683                 bss->ie = NULL;
684                 bss->ielen = 0;
685                 return 0;
686         }
687
688         bss->ie = malloc(elem_len);
689         if (bss->ie == NULL) {
690                 bss->ielen = 0;
691                 return -1;
692         }
693
694         memcpy(bss->ie, elem, elem_len);
695         bss->ielen = elem_len;
696         return 0;
697 }
698
699
700 static int test_driver_set_wps_beacon_ie(const char *ifname, void *priv,
701                                          const u8 *ie, size_t len)
702 {
703         struct test_driver_data *drv = priv;
704         struct test_driver_bss *bss;
705
706         wpa_hexdump(MSG_DEBUG, "test_driver: Beacon WPS IE", ie, len);
707         bss = test_driver_get_bss(drv, ifname);
708         if (bss == NULL)
709                 return -1;
710
711         free(bss->wps_beacon_ie);
712
713         if (ie == NULL) {
714                 bss->wps_beacon_ie = NULL;
715                 bss->wps_beacon_ie_len = 0;
716                 return 0;
717         }
718
719         bss->wps_beacon_ie = malloc(len);
720         if (bss->wps_beacon_ie == NULL) {
721                 bss->wps_beacon_ie_len = 0;
722                 return -1;
723         }
724
725         memcpy(bss->wps_beacon_ie, ie, len);
726         bss->wps_beacon_ie_len = len;
727         return 0;
728 }
729
730
731 static int test_driver_set_wps_probe_resp_ie(const char *ifname, void *priv,
732                                              const u8 *ie, size_t len)
733 {
734         struct test_driver_data *drv = priv;
735         struct test_driver_bss *bss;
736
737         wpa_hexdump(MSG_DEBUG, "test_driver: ProbeResp WPS IE", ie, len);
738         bss = test_driver_get_bss(drv, ifname);
739         if (bss == NULL)
740                 return -1;
741
742         free(bss->wps_probe_resp_ie);
743
744         if (ie == NULL) {
745                 bss->wps_probe_resp_ie = NULL;
746                 bss->wps_probe_resp_ie_len = 0;
747                 return 0;
748         }
749
750         bss->wps_probe_resp_ie = malloc(len);
751         if (bss->wps_probe_resp_ie == NULL) {
752                 bss->wps_probe_resp_ie_len = 0;
753                 return -1;
754         }
755
756         memcpy(bss->wps_probe_resp_ie, ie, len);
757         bss->wps_probe_resp_ie_len = len;
758         return 0;
759 }
760
761
762 static int test_driver_sta_deauth(void *priv, const u8 *addr, int reason)
763 {
764         struct test_driver_data *drv = priv;
765         struct test_client_socket *cli;
766
767         if (drv->test_socket < 0)
768                 return -1;
769
770         cli = drv->cli;
771         while (cli) {
772                 if (memcmp(cli->addr, addr, ETH_ALEN) == 0)
773                         break;
774                 cli = cli->next;
775         }
776
777         if (!cli)
778                 return -1;
779
780         return sendto(drv->test_socket, "DEAUTH", 6, 0,
781                       (struct sockaddr *) &cli->un, cli->unlen);
782 }
783
784
785 static int test_driver_sta_disassoc(void *priv, const u8 *addr, int reason)
786 {
787         struct test_driver_data *drv = priv;
788         struct test_client_socket *cli;
789
790         if (drv->test_socket < 0)
791                 return -1;
792
793         cli = drv->cli;
794         while (cli) {
795                 if (memcmp(cli->addr, addr, ETH_ALEN) == 0)
796                         break;
797                 cli = cli->next;
798         }
799
800         if (!cli)
801                 return -1;
802
803         return sendto(drv->test_socket, "DISASSOC", 8, 0,
804                       (struct sockaddr *) &cli->un, cli->unlen);
805 }
806
807
808 static struct hostapd_hw_modes *
809 test_driver_get_hw_feature_data(void *priv, u16 *num_modes, u16 *flags)
810 {
811         struct hostapd_hw_modes *modes;
812
813         *num_modes = 3;
814         *flags = 0;
815         modes = os_zalloc(*num_modes * sizeof(struct hostapd_hw_modes));
816         if (modes == NULL)
817                 return NULL;
818         modes[0].mode = HOSTAPD_MODE_IEEE80211G;
819         modes[0].num_channels = 1;
820         modes[0].num_rates = 1;
821         modes[0].channels = os_zalloc(sizeof(struct hostapd_channel_data));
822         modes[0].rates = os_zalloc(sizeof(struct hostapd_rate_data));
823         if (modes[0].channels == NULL || modes[0].rates == NULL) {
824                 hostapd_free_hw_features(modes, *num_modes);
825                 return NULL;
826         }
827         modes[0].channels[0].chan = 1;
828         modes[0].channels[0].freq = 2412;
829         modes[0].channels[0].flag = 0;
830         modes[0].rates[0].rate = 10;
831         modes[0].rates[0].flags = HOSTAPD_RATE_BASIC | HOSTAPD_RATE_SUPPORTED |
832                 HOSTAPD_RATE_CCK | HOSTAPD_RATE_MANDATORY;
833
834         modes[1].mode = HOSTAPD_MODE_IEEE80211B;
835         modes[1].num_channels = 1;
836         modes[1].num_rates = 1;
837         modes[1].channels = os_zalloc(sizeof(struct hostapd_channel_data));
838         modes[1].rates = os_zalloc(sizeof(struct hostapd_rate_data));
839         if (modes[1].channels == NULL || modes[1].rates == NULL) {
840                 hostapd_free_hw_features(modes, *num_modes);
841                 return NULL;
842         }
843         modes[1].channels[0].chan = 1;
844         modes[1].channels[0].freq = 2412;
845         modes[1].channels[0].flag = 0;
846         modes[1].rates[0].rate = 10;
847         modes[1].rates[0].flags = HOSTAPD_RATE_BASIC | HOSTAPD_RATE_SUPPORTED |
848                 HOSTAPD_RATE_CCK | HOSTAPD_RATE_MANDATORY;
849
850         modes[2].mode = HOSTAPD_MODE_IEEE80211A;
851         modes[2].num_channels = 1;
852         modes[2].num_rates = 1;
853         modes[2].channels = os_zalloc(sizeof(struct hostapd_channel_data));
854         modes[2].rates = os_zalloc(sizeof(struct hostapd_rate_data));
855         if (modes[2].channels == NULL || modes[2].rates == NULL) {
856                 hostapd_free_hw_features(modes, *num_modes);
857                 return NULL;
858         }
859         modes[2].channels[0].chan = 60;
860         modes[2].channels[0].freq = 5300;
861         modes[2].channels[0].flag = 0;
862         modes[2].rates[0].rate = 60;
863         modes[2].rates[0].flags = HOSTAPD_RATE_BASIC | HOSTAPD_RATE_SUPPORTED |
864                 HOSTAPD_RATE_MANDATORY;
865
866         return modes;
867 }
868
869
870 static int test_driver_bss_add(void *priv, const char *ifname, const u8 *bssid)
871 {
872         struct test_driver_data *drv = priv;
873         struct test_driver_bss *bss;
874
875         wpa_printf(MSG_DEBUG, "%s(ifname=%s bssid=" MACSTR ")",
876                    __func__, ifname, MAC2STR(bssid));
877
878         bss = os_zalloc(sizeof(*bss));
879         if (bss == NULL)
880                 return -1;
881
882         os_strlcpy(bss->ifname, ifname, IFNAMSIZ);
883         memcpy(bss->bssid, bssid, ETH_ALEN);
884
885         bss->next = drv->bss;
886         drv->bss = bss;
887
888         return 0;
889 }
890
891
892 static int test_driver_bss_remove(void *priv, const char *ifname)
893 {
894         struct test_driver_data *drv = priv;
895         struct test_driver_bss *bss, *prev;
896         struct test_client_socket *cli, *prev_c;
897
898         wpa_printf(MSG_DEBUG, "%s(ifname=%s)", __func__, ifname);
899
900         for (prev = NULL, bss = drv->bss; bss; prev = bss, bss = bss->next) {
901                 if (strcmp(bss->ifname, ifname) != 0)
902                         continue;
903
904                 if (prev)
905                         prev->next = bss->next;
906                 else
907                         drv->bss = bss->next;
908
909                 for (prev_c = NULL, cli = drv->cli; cli;
910                      prev_c = cli, cli = cli->next) {
911                         if (cli->bss != bss)
912                                 continue;
913                         if (prev_c)
914                                 prev_c->next = cli->next;
915                         else
916                                 drv->cli = cli->next;
917                         free(cli);
918                         break;
919                 }
920
921                 test_driver_free_bss(bss);
922                 return 0;
923         }
924
925         return -1;
926 }
927
928
929 static int test_driver_if_add(const char *iface, void *priv,
930                               enum hostapd_driver_if_type type, char *ifname,
931                               const u8 *addr)
932 {
933         wpa_printf(MSG_DEBUG, "%s(iface=%s type=%d ifname=%s)",
934                    __func__, iface, type, ifname);
935         return 0;
936 }
937
938
939 static int test_driver_if_update(void *priv, enum hostapd_driver_if_type type,
940                                  char *ifname, const u8 *addr)
941 {
942         wpa_printf(MSG_DEBUG, "%s(type=%d ifname=%s)", __func__, type, ifname);
943         return 0;
944 }
945
946
947 static int test_driver_if_remove(void *priv, enum hostapd_driver_if_type type,
948                                  const char *ifname, const u8 *addr)
949 {
950         wpa_printf(MSG_DEBUG, "%s(type=%d ifname=%s)", __func__, type, ifname);
951         return 0;
952 }
953
954
955 static int test_driver_valid_bss_mask(void *priv, const u8 *addr,
956                                       const u8 *mask)
957 {
958         return 0;
959 }
960
961
962 static int test_driver_set_ssid(const char *ifname, void *priv, const u8 *buf,
963                                 int len)
964 {
965         struct test_driver_data *drv = priv;
966         struct test_driver_bss *bss;
967
968         wpa_printf(MSG_DEBUG, "%s(ifname=%s)", __func__, ifname);
969         wpa_hexdump_ascii(MSG_DEBUG, "test_driver_set_ssid: SSID", buf, len);
970
971         for (bss = drv->bss; bss; bss = bss->next) {
972                 if (strcmp(bss->ifname, ifname) != 0)
973                         continue;
974
975                 if (len < 0 || (size_t) len > sizeof(bss->ssid))
976                         return -1;
977
978                 memcpy(bss->ssid, buf, len);
979                 bss->ssid_len = len;
980
981                 return 0;
982         }
983
984         return -1;
985 }
986
987
988 static int test_driver_set_privacy(const char *ifname, void *priv, int enabled)
989 {
990         struct test_driver_data *drv = priv;
991         struct test_driver_bss *bss;
992
993         wpa_printf(MSG_DEBUG, "%s(ifname=%s enabled=%d)",
994                    __func__, ifname, enabled);
995
996         for (bss = drv->bss; bss; bss = bss->next) {
997                 if (strcmp(bss->ifname, ifname) != 0)
998                         continue;
999
1000                 bss->privacy = enabled;
1001
1002                 return 0;
1003         }
1004
1005         return -1;
1006 }
1007
1008
1009 static int test_driver_set_encryption(const char *iface, void *priv,
1010                                       const char *alg, const u8 *addr, int idx,
1011                                       const u8 *key, size_t key_len, int txkey)
1012 {
1013         wpa_printf(MSG_DEBUG, "%s(iface=%s alg=%s idx=%d txkey=%d)",
1014                    __func__, iface, alg, idx, txkey);
1015         if (addr)
1016                 wpa_printf(MSG_DEBUG, "   addr=" MACSTR, MAC2STR(addr));
1017         if (key)
1018                 wpa_hexdump_key(MSG_DEBUG, "   key", key, key_len);
1019         return 0;
1020 }
1021
1022
1023 static int test_driver_set_sta_vlan(void *priv, const u8 *addr,
1024                                     const char *ifname, int vlan_id)
1025 {
1026         wpa_printf(MSG_DEBUG, "%s(addr=" MACSTR " ifname=%s vlan_id=%d)",
1027                    __func__, MAC2STR(addr), ifname, vlan_id);
1028         return 0;
1029 }
1030
1031
1032 static int test_driver_sta_add(const char *ifname, void *priv, const u8 *addr,
1033                                u16 aid, u16 capability, u8 *supp_rates,
1034                                size_t supp_rates_len, int flags,
1035                                u16 listen_interval)
1036 {
1037         struct test_driver_data *drv = priv;
1038         struct test_client_socket *cli;
1039         struct test_driver_bss *bss;
1040
1041         wpa_printf(MSG_DEBUG, "%s(ifname=%s addr=" MACSTR " aid=%d "
1042                    "capability=0x%x flags=0x%x listen_interval=%d)",
1043                    __func__, ifname, MAC2STR(addr), aid, capability, flags,
1044                    listen_interval);
1045         wpa_hexdump(MSG_DEBUG, "test_driver_sta_add - supp_rates",
1046                     supp_rates, supp_rates_len);
1047
1048         cli = drv->cli;
1049         while (cli) {
1050                 if (memcmp(cli->addr, addr, ETH_ALEN) == 0)
1051                         break;
1052                 cli = cli->next;
1053         }
1054         if (!cli) {
1055                 wpa_printf(MSG_DEBUG, "%s: no matching client entry",
1056                            __func__);
1057                 return -1;
1058         }
1059
1060         for (bss = drv->bss; bss; bss = bss->next) {
1061                 if (strcmp(ifname, bss->ifname) == 0)
1062                         break;
1063         }
1064         if (bss == NULL) {
1065                 wpa_printf(MSG_DEBUG, "%s: No matching interface found from "
1066                            "configured BSSes", __func__);
1067                 return -1;
1068         }
1069
1070         cli->bss = bss;
1071
1072         return 0;
1073 }
1074
1075
1076 static void * test_driver_init(struct hostapd_data *hapd)
1077 {
1078         struct test_driver_data *drv;
1079         struct sockaddr_un addr_un;
1080         struct sockaddr_in addr_in;
1081         struct sockaddr *addr;
1082         socklen_t alen;
1083
1084         drv = os_zalloc(sizeof(struct test_driver_data));
1085         if (drv == NULL) {
1086                 printf("Could not allocate memory for test driver data\n");
1087                 return NULL;
1088         }
1089         drv->bss = os_zalloc(sizeof(*drv->bss));
1090         if (drv->bss == NULL) {
1091                 printf("Could not allocate memory for test driver BSS data\n");
1092                 free(drv);
1093                 return NULL;
1094         }
1095
1096         drv->hapd = hapd;
1097
1098         /* Generate a MAC address to help testing with multiple APs */
1099         hapd->own_addr[0] = 0x02; /* locally administered */
1100         sha1_prf((const u8 *) hapd->conf->iface, strlen(hapd->conf->iface),
1101                  "hostapd test bssid generation",
1102                  (const u8 *) hapd->conf->ssid.ssid, hapd->conf->ssid.ssid_len,
1103                  hapd->own_addr + 1, ETH_ALEN - 1);
1104
1105         os_strlcpy(drv->bss->ifname, hapd->conf->iface, IFNAMSIZ);
1106         memcpy(drv->bss->bssid, hapd->own_addr, ETH_ALEN);
1107
1108         if (hapd->conf->test_socket) {
1109                 if (strlen(hapd->conf->test_socket) >=
1110                     sizeof(addr_un.sun_path)) {
1111                         printf("Too long test_socket path\n");
1112                         test_driver_free_priv(drv);
1113                         return NULL;
1114                 }
1115                 if (strncmp(hapd->conf->test_socket, "DIR:", 4) == 0) {
1116                         size_t len = strlen(hapd->conf->test_socket) + 30;
1117                         drv->socket_dir = strdup(hapd->conf->test_socket + 4);
1118                         drv->own_socket_path = malloc(len);
1119                         if (drv->own_socket_path) {
1120                                 snprintf(drv->own_socket_path, len,
1121                                          "%s/AP-" MACSTR,
1122                                          hapd->conf->test_socket + 4,
1123                                          MAC2STR(hapd->own_addr));
1124                         }
1125                 } else if (strncmp(hapd->conf->test_socket, "UDP:", 4) == 0) {
1126                         drv->udp_port = atoi(hapd->conf->test_socket + 4);
1127                 } else {
1128                         drv->own_socket_path = strdup(hapd->conf->test_socket);
1129                 }
1130                 if (drv->own_socket_path == NULL && drv->udp_port == 0) {
1131                         test_driver_free_priv(drv);
1132                         return NULL;
1133                 }
1134
1135                 drv->test_socket = socket(drv->udp_port ? PF_INET : PF_UNIX,
1136                                           SOCK_DGRAM, 0);
1137                 if (drv->test_socket < 0) {
1138                         perror("socket");
1139                         test_driver_free_priv(drv);
1140                         return NULL;
1141                 }
1142
1143                 if (drv->udp_port) {
1144                         os_memset(&addr_in, 0, sizeof(addr_in));
1145                         addr_in.sin_family = AF_INET;
1146                         addr_in.sin_port = htons(drv->udp_port);
1147                         addr = (struct sockaddr *) &addr_in;
1148                         alen = sizeof(addr_in);
1149                 } else {
1150                         os_memset(&addr_un, 0, sizeof(addr_un));
1151                         addr_un.sun_family = AF_UNIX;
1152                         os_strlcpy(addr_un.sun_path, drv->own_socket_path,
1153                                    sizeof(addr_un.sun_path));
1154                         addr = (struct sockaddr *) &addr_un;
1155                         alen = sizeof(addr_un);
1156                 }
1157                 if (bind(drv->test_socket, addr, alen) < 0) {
1158                         perror("bind(PF_UNIX)");
1159                         close(drv->test_socket);
1160                         if (drv->own_socket_path)
1161                                 unlink(drv->own_socket_path);
1162                         test_driver_free_priv(drv);
1163                         return NULL;
1164                 }
1165                 eloop_register_read_sock(drv->test_socket,
1166                                          test_driver_receive_unix, drv, NULL);
1167         } else
1168                 drv->test_socket = -1;
1169
1170         return drv;
1171 }
1172
1173
1174 static void test_driver_deinit(void *priv)
1175 {
1176         struct test_driver_data *drv = priv;
1177         struct test_client_socket *cli, *prev;
1178
1179         cli = drv->cli;
1180         while (cli) {
1181                 prev = cli;
1182                 cli = cli->next;
1183                 free(prev);
1184         }
1185
1186         if (drv->test_socket >= 0) {
1187                 eloop_unregister_read_sock(drv->test_socket);
1188                 close(drv->test_socket);
1189                 if (drv->own_socket_path)
1190                         unlink(drv->own_socket_path);
1191         }
1192
1193         /* There should be only one BSS remaining at this point. */
1194         if (drv->bss == NULL)
1195                 wpa_printf(MSG_ERROR, "%s: drv->bss == NULL", __func__);
1196         else if (drv->bss->next)
1197                 wpa_printf(MSG_ERROR, "%s: drv->bss->next != NULL", __func__);
1198
1199         test_driver_free_priv(drv);
1200 }
1201
1202
1203 const struct wpa_driver_ops wpa_driver_test_ops = {
1204         .name = "test",
1205         .init = test_driver_init,
1206         .deinit = test_driver_deinit,
1207         .send_eapol = test_driver_send_eapol,
1208         .send_mgmt_frame = test_driver_send_mgmt_frame,
1209         .set_generic_elem = test_driver_set_generic_elem,
1210         .sta_deauth = test_driver_sta_deauth,
1211         .sta_disassoc = test_driver_sta_disassoc,
1212         .get_hw_feature_data = test_driver_get_hw_feature_data,
1213         .bss_add = test_driver_bss_add,
1214         .bss_remove = test_driver_bss_remove,
1215         .if_add = test_driver_if_add,
1216         .if_update = test_driver_if_update,
1217         .if_remove = test_driver_if_remove,
1218         .valid_bss_mask = test_driver_valid_bss_mask,
1219         .set_ssid = test_driver_set_ssid,
1220         .set_privacy = test_driver_set_privacy,
1221         .set_encryption = test_driver_set_encryption,
1222         .set_sta_vlan = test_driver_set_sta_vlan,
1223         .sta_add = test_driver_sta_add,
1224         .send_ether = test_driver_send_ether,
1225         .set_wps_beacon_ie = test_driver_set_wps_beacon_ie,
1226         .set_wps_probe_resp_ie = test_driver_set_wps_probe_resp_ie,
1227 };