WPS: Fix Probe Request processing to handle missing attribute
[libeap.git] / src / wps / wps_registrar.c
1 /*
2  * Wi-Fi Protected Setup - Registrar
3  * Copyright (c) 2008-2009, 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 "utils/includes.h"
16
17 #include "utils/common.h"
18 #include "utils/base64.h"
19 #include "utils/eloop.h"
20 #include "utils/uuid.h"
21 #include "utils/list.h"
22 #include "crypto/crypto.h"
23 #include "crypto/sha256.h"
24 #include "common/ieee802_11_defs.h"
25 #include "wps_i.h"
26 #include "wps_dev_attr.h"
27 #include "wps_upnp.h"
28 #include "wps_upnp_i.h"
29
30 #define WPS_WORKAROUNDS
31
32 struct wps_uuid_pin {
33         struct dl_list list;
34         u8 uuid[WPS_UUID_LEN];
35         int wildcard_uuid;
36         u8 *pin;
37         size_t pin_len;
38 #define PIN_LOCKED BIT(0)
39 #define PIN_EXPIRES BIT(1)
40         int flags;
41         struct os_time expiration;
42 };
43
44
45 static void wps_free_pin(struct wps_uuid_pin *pin)
46 {
47         os_free(pin->pin);
48         os_free(pin);
49 }
50
51
52 static void wps_remove_pin(struct wps_uuid_pin *pin)
53 {
54         dl_list_del(&pin->list);
55         wps_free_pin(pin);
56 }
57
58
59 static void wps_free_pins(struct dl_list *pins)
60 {
61         struct wps_uuid_pin *pin, *prev;
62         dl_list_for_each_safe(pin, prev, pins, struct wps_uuid_pin, list)
63                 wps_remove_pin(pin);
64 }
65
66
67 struct wps_pbc_session {
68         struct wps_pbc_session *next;
69         u8 addr[ETH_ALEN];
70         u8 uuid_e[WPS_UUID_LEN];
71         struct os_time timestamp;
72 };
73
74
75 static void wps_free_pbc_sessions(struct wps_pbc_session *pbc)
76 {
77         struct wps_pbc_session *prev;
78
79         while (pbc) {
80                 prev = pbc;
81                 pbc = pbc->next;
82                 os_free(prev);
83         }
84 }
85
86
87 struct wps_registrar_device {
88         struct wps_registrar_device *next;
89         struct wps_device_data dev;
90         u8 uuid[WPS_UUID_LEN];
91 };
92
93
94 struct wps_registrar {
95         struct wps_context *wps;
96
97         int pbc;
98         int selected_registrar;
99
100         int (*new_psk_cb)(void *ctx, const u8 *mac_addr, const u8 *psk,
101                           size_t psk_len);
102         int (*set_ie_cb)(void *ctx, struct wpabuf *beacon_ie,
103                          struct wpabuf *probe_resp_ie);
104         void (*pin_needed_cb)(void *ctx, const u8 *uuid_e,
105                               const struct wps_device_data *dev);
106         void (*reg_success_cb)(void *ctx, const u8 *mac_addr,
107                                const u8 *uuid_e);
108         void (*set_sel_reg_cb)(void *ctx, int sel_reg, u16 dev_passwd_id,
109                                u16 sel_reg_config_methods);
110         void (*enrollee_seen_cb)(void *ctx, const u8 *addr, const u8 *uuid_e,
111                                  const u8 *pri_dev_type, u16 config_methods,
112                                  u16 dev_password_id, u8 request_type,
113                                  const char *dev_name);
114         void *cb_ctx;
115
116         struct dl_list pins;
117         struct wps_pbc_session *pbc_sessions;
118
119         int skip_cred_build;
120         struct wpabuf *extra_cred;
121         int disable_auto_conf;
122         int sel_reg_union;
123         int sel_reg_dev_password_id_override;
124         int sel_reg_config_methods_override;
125         int static_wep_only;
126
127         struct wps_registrar_device *devices;
128
129         int force_pbc_overlap;
130 };
131
132
133 static int wps_set_ie(struct wps_registrar *reg);
134 static void wps_registrar_pbc_timeout(void *eloop_ctx, void *timeout_ctx);
135 static void wps_registrar_set_selected_timeout(void *eloop_ctx,
136                                                void *timeout_ctx);
137
138
139 static void wps_free_devices(struct wps_registrar_device *dev)
140 {
141         struct wps_registrar_device *prev;
142
143         while (dev) {
144                 prev = dev;
145                 dev = dev->next;
146                 wps_device_data_free(&prev->dev);
147                 os_free(prev);
148         }
149 }
150
151
152 static struct wps_registrar_device * wps_device_get(struct wps_registrar *reg,
153                                                     const u8 *addr)
154 {
155         struct wps_registrar_device *dev;
156
157         for (dev = reg->devices; dev; dev = dev->next) {
158                 if (os_memcmp(dev->dev.mac_addr, addr, ETH_ALEN) == 0)
159                         return dev;
160         }
161         return NULL;
162 }
163
164
165 static void wps_device_clone_data(struct wps_device_data *dst,
166                                   struct wps_device_data *src)
167 {
168         os_memcpy(dst->mac_addr, src->mac_addr, ETH_ALEN);
169         os_memcpy(dst->pri_dev_type, src->pri_dev_type, WPS_DEV_TYPE_LEN);
170
171 #define WPS_STRDUP(n) \
172         os_free(dst->n); \
173         dst->n = src->n ? os_strdup(src->n) : NULL
174
175         WPS_STRDUP(device_name);
176         WPS_STRDUP(manufacturer);
177         WPS_STRDUP(model_name);
178         WPS_STRDUP(model_number);
179         WPS_STRDUP(serial_number);
180 #undef WPS_STRDUP
181 }
182
183
184 int wps_device_store(struct wps_registrar *reg,
185                      struct wps_device_data *dev, const u8 *uuid)
186 {
187         struct wps_registrar_device *d;
188
189         d = wps_device_get(reg, dev->mac_addr);
190         if (d == NULL) {
191                 d = os_zalloc(sizeof(*d));
192                 if (d == NULL)
193                         return -1;
194                 d->next = reg->devices;
195                 reg->devices = d;
196         }
197
198         wps_device_clone_data(&d->dev, dev);
199         os_memcpy(d->uuid, uuid, WPS_UUID_LEN);
200
201         return 0;
202 }
203
204
205 static void wps_registrar_add_pbc_session(struct wps_registrar *reg,
206                                           const u8 *addr, const u8 *uuid_e)
207 {
208         struct wps_pbc_session *pbc, *prev = NULL;
209         struct os_time now;
210
211         os_get_time(&now);
212
213         pbc = reg->pbc_sessions;
214         while (pbc) {
215                 if (os_memcmp(pbc->addr, addr, ETH_ALEN) == 0 &&
216                     os_memcmp(pbc->uuid_e, uuid_e, WPS_UUID_LEN) == 0) {
217                         if (prev)
218                                 prev->next = pbc->next;
219                         else
220                                 reg->pbc_sessions = pbc->next;
221                         break;
222                 }
223                 prev = pbc;
224                 pbc = pbc->next;
225         }
226
227         if (!pbc) {
228                 pbc = os_zalloc(sizeof(*pbc));
229                 if (pbc == NULL)
230                         return;
231                 os_memcpy(pbc->addr, addr, ETH_ALEN);
232                 if (uuid_e)
233                         os_memcpy(pbc->uuid_e, uuid_e, WPS_UUID_LEN);
234         }
235
236         pbc->next = reg->pbc_sessions;
237         reg->pbc_sessions = pbc;
238         pbc->timestamp = now;
239
240         /* remove entries that have timed out */
241         prev = pbc;
242         pbc = pbc->next;
243
244         while (pbc) {
245                 if (now.sec > pbc->timestamp.sec + WPS_PBC_WALK_TIME) {
246                         prev->next = NULL;
247                         wps_free_pbc_sessions(pbc);
248                         break;
249                 }
250                 prev = pbc;
251                 pbc = pbc->next;
252         }
253 }
254
255
256 static void wps_registrar_remove_pbc_session(struct wps_registrar *reg,
257                                              const u8 *addr, const u8 *uuid_e)
258 {
259         struct wps_pbc_session *pbc, *prev = NULL;
260
261         pbc = reg->pbc_sessions;
262         while (pbc) {
263                 if (os_memcmp(pbc->addr, addr, ETH_ALEN) == 0 &&
264                     os_memcmp(pbc->uuid_e, uuid_e, WPS_UUID_LEN) == 0) {
265                         if (prev)
266                                 prev->next = pbc->next;
267                         else
268                                 reg->pbc_sessions = pbc->next;
269                         os_free(pbc);
270                         break;
271                 }
272                 prev = pbc;
273                 pbc = pbc->next;
274         }
275 }
276
277
278 static int wps_registrar_pbc_overlap(struct wps_registrar *reg,
279                                      const u8 *addr, const u8 *uuid_e)
280 {
281         int count = 0;
282         struct wps_pbc_session *pbc;
283         struct os_time now;
284
285         os_get_time(&now);
286
287         for (pbc = reg->pbc_sessions; pbc; pbc = pbc->next) {
288                 if (now.sec > pbc->timestamp.sec + WPS_PBC_WALK_TIME)
289                         break;
290                 if (addr == NULL || os_memcmp(addr, pbc->addr, ETH_ALEN) ||
291                     uuid_e == NULL ||
292                     os_memcmp(uuid_e, pbc->uuid_e, WPS_UUID_LEN))
293                         count++;
294         }
295
296         if (addr || uuid_e)
297                 count++;
298
299         return count > 1 ? 1 : 0;
300 }
301
302
303 static int wps_build_wps_state(struct wps_context *wps, struct wpabuf *msg)
304 {
305         wpa_printf(MSG_DEBUG, "WPS:  * Wi-Fi Protected Setup State (%d)",
306                    wps->wps_state);
307         wpabuf_put_be16(msg, ATTR_WPS_STATE);
308         wpabuf_put_be16(msg, 1);
309         wpabuf_put_u8(msg, wps->wps_state);
310         return 0;
311 }
312
313
314 #ifdef CONFIG_WPS_UPNP
315 static void wps_registrar_free_pending_m2(struct wps_context *wps)
316 {
317         struct upnp_pending_message *p, *p2, *prev = NULL;
318         p = wps->upnp_msgs;
319         while (p) {
320                 if (p->type == WPS_M2 || p->type == WPS_M2D) {
321                         if (prev == NULL)
322                                 wps->upnp_msgs = p->next;
323                         else
324                                 prev->next = p->next;
325                         wpa_printf(MSG_DEBUG, "WPS UPnP: Drop pending M2/M2D");
326                         p2 = p;
327                         p = p->next;
328                         wpabuf_free(p2->msg);
329                         os_free(p2);
330                         continue;
331                 }
332                 prev = p;
333                 p = p->next;
334         }
335 }
336 #endif /* CONFIG_WPS_UPNP */
337
338
339 static int wps_build_ap_setup_locked(struct wps_context *wps,
340                                      struct wpabuf *msg)
341 {
342         if (wps->ap_setup_locked) {
343                 wpa_printf(MSG_DEBUG, "WPS:  * AP Setup Locked");
344                 wpabuf_put_be16(msg, ATTR_AP_SETUP_LOCKED);
345                 wpabuf_put_be16(msg, 1);
346                 wpabuf_put_u8(msg, 1);
347         }
348         return 0;
349 }
350
351
352 static int wps_build_selected_registrar(struct wps_registrar *reg,
353                                         struct wpabuf *msg)
354 {
355         if (!reg->sel_reg_union)
356                 return 0;
357         wpa_printf(MSG_DEBUG, "WPS:  * Selected Registrar");
358         wpabuf_put_be16(msg, ATTR_SELECTED_REGISTRAR);
359         wpabuf_put_be16(msg, 1);
360         wpabuf_put_u8(msg, 1);
361         return 0;
362 }
363
364
365 static int wps_build_sel_reg_dev_password_id(struct wps_registrar *reg,
366                                              struct wpabuf *msg)
367 {
368         u16 id = reg->pbc ? DEV_PW_PUSHBUTTON : DEV_PW_DEFAULT;
369         if (!reg->sel_reg_union)
370                 return 0;
371         if (reg->sel_reg_dev_password_id_override >= 0)
372                 id = reg->sel_reg_dev_password_id_override;
373         wpa_printf(MSG_DEBUG, "WPS:  * Device Password ID (%d)", id);
374         wpabuf_put_be16(msg, ATTR_DEV_PASSWORD_ID);
375         wpabuf_put_be16(msg, 2);
376         wpabuf_put_be16(msg, id);
377         return 0;
378 }
379
380
381 static int wps_build_sel_reg_config_methods(struct wps_registrar *reg,
382                                             struct wpabuf *msg)
383 {
384         u16 methods;
385         if (!reg->sel_reg_union)
386                 return 0;
387         methods = reg->wps->config_methods & ~WPS_CONFIG_PUSHBUTTON;
388         if (reg->pbc)
389                 methods |= WPS_CONFIG_PUSHBUTTON;
390         if (reg->sel_reg_config_methods_override >= 0)
391                 methods = reg->sel_reg_config_methods_override;
392         wpa_printf(MSG_DEBUG, "WPS:  * Selected Registrar Config Methods (%x)",
393                    methods);
394         wpabuf_put_be16(msg, ATTR_SELECTED_REGISTRAR_CONFIG_METHODS);
395         wpabuf_put_be16(msg, 2);
396         wpabuf_put_be16(msg, methods);
397         return 0;
398 }
399
400
401 static int wps_build_probe_config_methods(struct wps_registrar *reg,
402                                           struct wpabuf *msg)
403 {
404         u16 methods;
405         methods = 0;
406         wpa_printf(MSG_DEBUG, "WPS:  * Config Methods (%x)", methods);
407         wpabuf_put_be16(msg, ATTR_CONFIG_METHODS);
408         wpabuf_put_be16(msg, 2);
409         wpabuf_put_be16(msg, methods);
410         return 0;
411 }
412
413
414 static int wps_build_config_methods_r(struct wps_registrar *reg,
415                                       struct wpabuf *msg)
416 {
417         u16 methods;
418         methods = reg->wps->config_methods & ~WPS_CONFIG_PUSHBUTTON;
419         if (reg->pbc)
420                 methods |= WPS_CONFIG_PUSHBUTTON;
421         return wps_build_config_methods(msg, methods);
422 }
423
424
425 static int wps_build_resp_type(struct wps_registrar *reg, struct wpabuf *msg)
426 {
427         u8 resp = reg->wps->ap ? WPS_RESP_AP : WPS_RESP_REGISTRAR;
428         wpa_printf(MSG_DEBUG, "WPS:  * Response Type (%d)", resp);
429         wpabuf_put_be16(msg, ATTR_RESPONSE_TYPE);
430         wpabuf_put_be16(msg, 1);
431         wpabuf_put_u8(msg, resp);
432         return 0;
433 }
434
435
436 /**
437  * wps_registrar_init - Initialize WPS Registrar data
438  * @wps: Pointer to longterm WPS context
439  * @cfg: Registrar configuration
440  * Returns: Pointer to allocated Registrar data or %NULL on failure
441  *
442  * This function is used to initialize WPS Registrar functionality. It can be
443  * used for a single Registrar run (e.g., when run in a supplicant) or multiple
444  * runs (e.g., when run as an internal Registrar in an AP). Caller is
445  * responsible for freeing the returned data with wps_registrar_deinit() when
446  * Registrar functionality is not needed anymore.
447  */
448 struct wps_registrar *
449 wps_registrar_init(struct wps_context *wps,
450                    const struct wps_registrar_config *cfg)
451 {
452         struct wps_registrar *reg = os_zalloc(sizeof(*reg));
453         if (reg == NULL)
454                 return NULL;
455
456         dl_list_init(&reg->pins);
457         reg->wps = wps;
458         reg->new_psk_cb = cfg->new_psk_cb;
459         reg->set_ie_cb = cfg->set_ie_cb;
460         reg->pin_needed_cb = cfg->pin_needed_cb;
461         reg->reg_success_cb = cfg->reg_success_cb;
462         reg->set_sel_reg_cb = cfg->set_sel_reg_cb;
463         reg->enrollee_seen_cb = cfg->enrollee_seen_cb;
464         reg->cb_ctx = cfg->cb_ctx;
465         reg->skip_cred_build = cfg->skip_cred_build;
466         if (cfg->extra_cred) {
467                 reg->extra_cred = wpabuf_alloc_copy(cfg->extra_cred,
468                                                     cfg->extra_cred_len);
469                 if (reg->extra_cred == NULL) {
470                         os_free(reg);
471                         return NULL;
472                 }
473         }
474         reg->disable_auto_conf = cfg->disable_auto_conf;
475         reg->sel_reg_dev_password_id_override = -1;
476         reg->sel_reg_config_methods_override = -1;
477         reg->static_wep_only = cfg->static_wep_only;
478
479         if (wps_set_ie(reg)) {
480                 wps_registrar_deinit(reg);
481                 return NULL;
482         }
483
484         return reg;
485 }
486
487
488 /**
489  * wps_registrar_deinit - Deinitialize WPS Registrar data
490  * @reg: Registrar data from wps_registrar_init()
491  */
492 void wps_registrar_deinit(struct wps_registrar *reg)
493 {
494         if (reg == NULL)
495                 return;
496         eloop_cancel_timeout(wps_registrar_pbc_timeout, reg, NULL);
497         eloop_cancel_timeout(wps_registrar_set_selected_timeout, reg, NULL);
498         wps_free_pins(&reg->pins);
499         wps_free_pbc_sessions(reg->pbc_sessions);
500         wpabuf_free(reg->extra_cred);
501         wps_free_devices(reg->devices);
502         os_free(reg);
503 }
504
505
506 /**
507  * wps_registrar_add_pin - Configure a new PIN for Registrar
508  * @reg: Registrar data from wps_registrar_init()
509  * @uuid: UUID-E or %NULL for wildcard (any UUID)
510  * @pin: PIN (Device Password)
511  * @pin_len: Length of pin in octets
512  * @timeout: Time (in seconds) when the PIN will be invalidated; 0 = no timeout
513  * Returns: 0 on success, -1 on failure
514  */
515 int wps_registrar_add_pin(struct wps_registrar *reg, const u8 *uuid,
516                           const u8 *pin, size_t pin_len, int timeout)
517 {
518         struct wps_uuid_pin *p;
519
520         p = os_zalloc(sizeof(*p));
521         if (p == NULL)
522                 return -1;
523         if (uuid == NULL)
524                 p->wildcard_uuid = 1;
525         else
526                 os_memcpy(p->uuid, uuid, WPS_UUID_LEN);
527         p->pin = os_malloc(pin_len);
528         if (p->pin == NULL) {
529                 os_free(p);
530                 return -1;
531         }
532         os_memcpy(p->pin, pin, pin_len);
533         p->pin_len = pin_len;
534
535         if (timeout) {
536                 p->flags |= PIN_EXPIRES;
537                 os_get_time(&p->expiration);
538                 p->expiration.sec += timeout;
539         }
540
541         dl_list_add(&reg->pins, &p->list);
542
543         wpa_printf(MSG_DEBUG, "WPS: A new PIN configured (timeout=%d)",
544                    timeout);
545         wpa_hexdump(MSG_DEBUG, "WPS: UUID", uuid, WPS_UUID_LEN);
546         wpa_hexdump_ascii_key(MSG_DEBUG, "WPS: PIN", pin, pin_len);
547         reg->selected_registrar = 1;
548         reg->pbc = 0;
549         wps_registrar_selected_registrar_changed(reg);
550         eloop_cancel_timeout(wps_registrar_set_selected_timeout, reg, NULL);
551         eloop_register_timeout(WPS_PBC_WALK_TIME, 0,
552                                wps_registrar_set_selected_timeout,
553                                reg, NULL);
554
555         return 0;
556 }
557
558
559 static void wps_registrar_expire_pins(struct wps_registrar *reg)
560 {
561         struct wps_uuid_pin *pin, *prev;
562         struct os_time now;
563
564         os_get_time(&now);
565         dl_list_for_each_safe(pin, prev, &reg->pins, struct wps_uuid_pin, list)
566         {
567                 if ((pin->flags & PIN_EXPIRES) &&
568                     os_time_before(&pin->expiration, &now)) {
569                         wpa_hexdump(MSG_DEBUG, "WPS: Expired PIN for UUID",
570                                     pin->uuid, WPS_UUID_LEN);
571                         wps_remove_pin(pin);
572                 }
573         }
574 }
575
576
577 /**
578  * wps_registrar_invalidate_pin - Invalidate a PIN for a specific UUID-E
579  * @reg: Registrar data from wps_registrar_init()
580  * @uuid: UUID-E
581  * Returns: 0 on success, -1 on failure (e.g., PIN not found)
582  */
583 int wps_registrar_invalidate_pin(struct wps_registrar *reg, const u8 *uuid)
584 {
585         struct wps_uuid_pin *pin, *prev;
586
587         dl_list_for_each_safe(pin, prev, &reg->pins, struct wps_uuid_pin, list)
588         {
589                 if (os_memcmp(pin->uuid, uuid, WPS_UUID_LEN) == 0) {
590                         wpa_hexdump(MSG_DEBUG, "WPS: Invalidated PIN for UUID",
591                                     pin->uuid, WPS_UUID_LEN);
592                         wps_remove_pin(pin);
593                         return 0;
594                 }
595         }
596
597         return -1;
598 }
599
600
601 static const u8 * wps_registrar_get_pin(struct wps_registrar *reg,
602                                         const u8 *uuid, size_t *pin_len)
603 {
604         struct wps_uuid_pin *pin, *found = NULL;
605
606         wps_registrar_expire_pins(reg);
607
608         dl_list_for_each(pin, &reg->pins, struct wps_uuid_pin, list) {
609                 if (!pin->wildcard_uuid &&
610                     os_memcmp(pin->uuid, uuid, WPS_UUID_LEN) == 0) {
611                         found = pin;
612                         break;
613                 }
614         }
615
616         if (!found) {
617                 /* Check for wildcard UUIDs since none of the UUID-specific
618                  * PINs matched */
619                 dl_list_for_each(pin, &reg->pins, struct wps_uuid_pin, list) {
620                         if (pin->wildcard_uuid == 1) {
621                                 wpa_printf(MSG_DEBUG, "WPS: Found a wildcard "
622                                            "PIN. Assigned it for this UUID-E");
623                                 pin->wildcard_uuid = 2;
624                                 os_memcpy(pin->uuid, uuid, WPS_UUID_LEN);
625                                 found = pin;
626                                 break;
627                         }
628                 }
629         }
630
631         if (!found)
632                 return NULL;
633
634         /*
635          * Lock the PIN to avoid attacks based on concurrent re-use of the PIN
636          * that could otherwise avoid PIN invalidations.
637          */
638         if (found->flags & PIN_LOCKED) {
639                 wpa_printf(MSG_DEBUG, "WPS: Selected PIN locked - do not "
640                            "allow concurrent re-use");
641                 return NULL;
642         }
643         *pin_len = found->pin_len;
644         found->flags |= PIN_LOCKED;
645         return found->pin;
646 }
647
648
649 /**
650  * wps_registrar_unlock_pin - Unlock a PIN for a specific UUID-E
651  * @reg: Registrar data from wps_registrar_init()
652  * @uuid: UUID-E
653  * Returns: 0 on success, -1 on failure
654  *
655  * PINs are locked to enforce only one concurrent use. This function unlocks a
656  * PIN to allow it to be used again. If the specified PIN was configured using
657  * a wildcard UUID, it will be removed instead of allowing multiple uses.
658  */
659 int wps_registrar_unlock_pin(struct wps_registrar *reg, const u8 *uuid)
660 {
661         struct wps_uuid_pin *pin;
662
663         dl_list_for_each(pin, &reg->pins, struct wps_uuid_pin, list) {
664                 if (os_memcmp(pin->uuid, uuid, WPS_UUID_LEN) == 0) {
665                         if (pin->wildcard_uuid == 2) {
666                                 wpa_printf(MSG_DEBUG, "WPS: Invalidating used "
667                                            "wildcard PIN");
668                                 return wps_registrar_invalidate_pin(reg, uuid);
669                         }
670                         pin->flags &= ~PIN_LOCKED;
671                         return 0;
672                 }
673         }
674
675         return -1;
676 }
677
678
679 static void wps_registrar_stop_pbc(struct wps_registrar *reg)
680 {
681         reg->selected_registrar = 0;
682         reg->pbc = 0;
683         wps_registrar_selected_registrar_changed(reg);
684 }
685
686
687 static void wps_registrar_pbc_timeout(void *eloop_ctx, void *timeout_ctx)
688 {
689         struct wps_registrar *reg = eloop_ctx;
690
691         wpa_printf(MSG_DEBUG, "WPS: PBC timed out - disable PBC mode");
692         wps_pbc_timeout_event(reg->wps);
693         wps_registrar_stop_pbc(reg);
694 }
695
696
697 /**
698  * wps_registrar_button_pushed - Notify Registrar that AP button was pushed
699  * @reg: Registrar data from wps_registrar_init()
700  * Returns: 0 on success, -1 on failure
701  *
702  * This function is called on an AP when a push button is pushed to activate
703  * PBC mode. The PBC mode will be stopped after walk time (2 minutes) timeout
704  * or when a PBC registration is completed.
705  */
706 int wps_registrar_button_pushed(struct wps_registrar *reg)
707 {
708         if (wps_registrar_pbc_overlap(reg, NULL, NULL)) {
709                 wpa_printf(MSG_DEBUG, "WPS: PBC overlap - do not start PBC "
710                            "mode");
711                 wps_pbc_overlap_event(reg->wps);
712                 return -1;
713         }
714         wpa_printf(MSG_DEBUG, "WPS: Button pushed - PBC mode started");
715         reg->force_pbc_overlap = 0;
716         reg->selected_registrar = 1;
717         reg->pbc = 1;
718         wps_registrar_selected_registrar_changed(reg);
719
720         eloop_cancel_timeout(wps_registrar_pbc_timeout, reg, NULL);
721         eloop_register_timeout(WPS_PBC_WALK_TIME, 0, wps_registrar_pbc_timeout,
722                                reg, NULL);
723         return 0;
724 }
725
726
727 static void wps_registrar_pbc_completed(struct wps_registrar *reg)
728 {
729         wpa_printf(MSG_DEBUG, "WPS: PBC completed - stopping PBC mode");
730         eloop_cancel_timeout(wps_registrar_pbc_timeout, reg, NULL);
731         wps_registrar_stop_pbc(reg);
732 }
733
734
735 static void wps_registrar_pin_completed(struct wps_registrar *reg)
736 {
737         wpa_printf(MSG_DEBUG, "WPS: PIN completed using internal Registrar");
738         eloop_cancel_timeout(wps_registrar_set_selected_timeout, reg, NULL);
739         reg->selected_registrar = 0;
740         wps_registrar_selected_registrar_changed(reg);
741 }
742
743
744 /**
745  * wps_registrar_probe_req_rx - Notify Registrar of Probe Request
746  * @reg: Registrar data from wps_registrar_init()
747  * @addr: MAC address of the Probe Request sender
748  * @wps_data: WPS IE contents
749  *
750  * This function is called on an AP when a Probe Request with WPS IE is
751  * received. This is used to track PBC mode use and to detect possible overlap
752  * situation with other WPS APs.
753  */
754 void wps_registrar_probe_req_rx(struct wps_registrar *reg, const u8 *addr,
755                                 const struct wpabuf *wps_data)
756 {
757         struct wps_parse_attr attr;
758         u16 methods;
759
760         wpa_hexdump_buf(MSG_MSGDUMP,
761                         "WPS: Probe Request with WPS data received",
762                         wps_data);
763
764         if (wps_parse_msg(wps_data, &attr) < 0)
765                 return;
766         if (!wps_version_supported(attr.version)) {
767                 wpa_printf(MSG_DEBUG, "WPS: Unsupported ProbeReq WPS IE "
768                            "version 0x%x", attr.version ? *attr.version : 0);
769                 return;
770         }
771
772         if (attr.config_methods == NULL) {
773                 wpa_printf(MSG_DEBUG, "WPS: No Config Methods attribute in "
774                            "Probe Request");
775                 return;
776         }
777
778         if (reg->enrollee_seen_cb && attr.dev_password_id && attr.uuid_e &&
779             attr.primary_dev_type && attr.request_type) {
780                 char *dev_name = NULL;
781                 if (attr.dev_name) {
782                         dev_name = os_zalloc(attr.dev_name_len + 1);
783                         if (dev_name) {
784                                 os_memcpy(dev_name, attr.dev_name,
785                                           attr.dev_name_len);
786                         }
787                 }
788                 reg->enrollee_seen_cb(reg->cb_ctx, addr, attr.uuid_e,
789                                       attr.primary_dev_type,
790                                       WPA_GET_BE16(attr.config_methods),
791                                       WPA_GET_BE16(attr.dev_password_id),
792                                       *attr.request_type, dev_name);
793                 os_free(dev_name);
794         }
795
796         methods = WPA_GET_BE16(attr.config_methods);
797         if (!(methods & WPS_CONFIG_PUSHBUTTON))
798                 return; /* Not PBC */
799
800         wpa_printf(MSG_DEBUG, "WPS: Probe Request for PBC received from "
801                    MACSTR, MAC2STR(addr));
802         if (attr.uuid_e == NULL) {
803                 wpa_printf(MSG_DEBUG, "WPS: Invalid Probe Request WPS IE: No "
804                            "UUID-E included");
805                 return;
806         }
807
808         wps_registrar_add_pbc_session(reg, addr, attr.uuid_e);
809         if (wps_registrar_pbc_overlap(reg, addr, attr.uuid_e)) {
810                 wpa_printf(MSG_DEBUG, "WPS: PBC session overlap detected");
811                 reg->force_pbc_overlap = 1;
812                 wps_pbc_overlap_event(reg->wps);
813         }
814 }
815
816
817 static int wps_cb_new_psk(struct wps_registrar *reg, const u8 *mac_addr,
818                           const u8 *psk, size_t psk_len)
819 {
820         if (reg->new_psk_cb == NULL)
821                 return 0;
822
823         return reg->new_psk_cb(reg->cb_ctx, mac_addr, psk, psk_len);
824 }
825
826
827 static void wps_cb_pin_needed(struct wps_registrar *reg, const u8 *uuid_e,
828                               const struct wps_device_data *dev)
829 {
830         if (reg->pin_needed_cb == NULL)
831                 return;
832
833         reg->pin_needed_cb(reg->cb_ctx, uuid_e, dev);
834 }
835
836
837 static void wps_cb_reg_success(struct wps_registrar *reg, const u8 *mac_addr,
838                                const u8 *uuid_e)
839 {
840         if (reg->reg_success_cb == NULL)
841                 return;
842
843         reg->reg_success_cb(reg->cb_ctx, mac_addr, uuid_e);
844 }
845
846
847 static int wps_cb_set_ie(struct wps_registrar *reg, struct wpabuf *beacon_ie,
848                          struct wpabuf *probe_resp_ie)
849 {
850         return reg->set_ie_cb(reg->cb_ctx, beacon_ie, probe_resp_ie);
851 }
852
853
854 static void wps_cb_set_sel_reg(struct wps_registrar *reg)
855 {
856         u16 methods = 0;
857         if (reg->set_sel_reg_cb == NULL)
858                 return;
859
860         if (reg->selected_registrar) {
861                 methods = reg->wps->config_methods & ~WPS_CONFIG_PUSHBUTTON;
862                 if (reg->pbc)
863                         methods |= WPS_CONFIG_PUSHBUTTON;
864         }
865
866         reg->set_sel_reg_cb(reg->cb_ctx, reg->selected_registrar,
867                             reg->pbc ? DEV_PW_PUSHBUTTON : DEV_PW_DEFAULT,
868                             methods);
869 }
870
871
872 /* Encapsulate WPS IE data with one (or more, if needed) IE headers */
873 static struct wpabuf * wps_ie_encapsulate(struct wpabuf *data)
874 {
875         struct wpabuf *ie;
876         const u8 *pos, *end;
877
878         ie = wpabuf_alloc(wpabuf_len(data) + 100);
879         if (ie == NULL) {
880                 wpabuf_free(data);
881                 return NULL;
882         }
883
884         pos = wpabuf_head(data);
885         end = pos + wpabuf_len(data);
886
887         while (end > pos) {
888                 size_t frag_len = end - pos;
889                 if (frag_len > 251)
890                         frag_len = 251;
891                 wpabuf_put_u8(ie, WLAN_EID_VENDOR_SPECIFIC);
892                 wpabuf_put_u8(ie, 4 + frag_len);
893                 wpabuf_put_be32(ie, WPS_DEV_OUI_WFA);
894                 wpabuf_put_data(ie, pos, frag_len);
895                 pos += frag_len;
896         }
897
898         wpabuf_free(data);
899
900         return ie;
901 }
902
903
904 static int wps_set_ie(struct wps_registrar *reg)
905 {
906         struct wpabuf *beacon;
907         struct wpabuf *probe;
908
909         if (reg->set_ie_cb == NULL)
910                 return 0;
911
912         wpa_printf(MSG_DEBUG, "WPS: Build Beacon and Probe Response IEs");
913
914         beacon = wpabuf_alloc(300);
915         if (beacon == NULL)
916                 return -1;
917         probe = wpabuf_alloc(400);
918         if (probe == NULL) {
919                 wpabuf_free(beacon);
920                 return -1;
921         }
922
923         if (wps_build_version(beacon) ||
924             wps_build_wps_state(reg->wps, beacon) ||
925             wps_build_ap_setup_locked(reg->wps, beacon) ||
926             wps_build_selected_registrar(reg, beacon) ||
927             wps_build_sel_reg_dev_password_id(reg, beacon) ||
928             wps_build_sel_reg_config_methods(reg, beacon) ||
929             wps_build_version(probe) ||
930             wps_build_wps_state(reg->wps, probe) ||
931             wps_build_ap_setup_locked(reg->wps, probe) ||
932             wps_build_selected_registrar(reg, probe) ||
933             wps_build_sel_reg_dev_password_id(reg, probe) ||
934             wps_build_sel_reg_config_methods(reg, probe) ||
935             wps_build_resp_type(reg, probe) ||
936             wps_build_uuid_e(probe, reg->wps->uuid) ||
937             wps_build_device_attrs(&reg->wps->dev, probe) ||
938             wps_build_probe_config_methods(reg, probe) ||
939             wps_build_rf_bands(&reg->wps->dev, probe)) {
940                 wpabuf_free(beacon);
941                 wpabuf_free(probe);
942                 return -1;
943         }
944
945         beacon = wps_ie_encapsulate(beacon);
946         probe = wps_ie_encapsulate(probe);
947
948         if (!beacon || !probe) {
949                 wpabuf_free(beacon);
950                 wpabuf_free(probe);
951                 return -1;
952         }
953
954         if (reg->static_wep_only) {
955                 /*
956                  * Windows XP and Vista clients can get confused about
957                  * EAP-Identity/Request when they probe the network with
958                  * EAPOL-Start. In such a case, they may assume the network is
959                  * using IEEE 802.1X and prompt user for a certificate while
960                  * the correct (non-WPS) behavior would be to ask for the
961                  * static WEP key. As a workaround, use Microsoft Provisioning
962                  * IE to advertise that legacy 802.1X is not supported.
963                  */
964                 const u8 ms_wps[7] = {
965                         WLAN_EID_VENDOR_SPECIFIC, 5,
966                         /* Microsoft Provisioning IE (00:50:f2:5) */
967                         0x00, 0x50, 0xf2, 5,
968                         0x00 /* no legacy 802.1X or MS WPS */
969                 };
970                 wpa_printf(MSG_DEBUG, "WPS: Add Microsoft Provisioning IE "
971                            "into Beacon/Probe Response frames");
972                 wpabuf_put_data(beacon, ms_wps, sizeof(ms_wps));
973                 wpabuf_put_data(probe, ms_wps, sizeof(ms_wps));
974         }
975
976         return wps_cb_set_ie(reg, beacon, probe);
977 }
978
979
980 static int wps_get_dev_password(struct wps_data *wps)
981 {
982         const u8 *pin;
983         size_t pin_len = 0;
984
985         os_free(wps->dev_password);
986         wps->dev_password = NULL;
987
988         if (wps->pbc) {
989                 wpa_printf(MSG_DEBUG, "WPS: Use default PIN for PBC");
990                 pin = (const u8 *) "00000000";
991                 pin_len = 8;
992         } else {
993                 pin = wps_registrar_get_pin(wps->wps->registrar, wps->uuid_e,
994                                             &pin_len);
995         }
996         if (pin == NULL) {
997                 wpa_printf(MSG_DEBUG, "WPS: No Device Password available for "
998                            "the Enrollee");
999                 wps_cb_pin_needed(wps->wps->registrar, wps->uuid_e,
1000                                   &wps->peer_dev);
1001                 return -1;
1002         }
1003
1004         wps->dev_password = os_malloc(pin_len);
1005         if (wps->dev_password == NULL)
1006                 return -1;
1007         os_memcpy(wps->dev_password, pin, pin_len);
1008         wps->dev_password_len = pin_len;
1009
1010         return 0;
1011 }
1012
1013
1014 static int wps_build_uuid_r(struct wps_data *wps, struct wpabuf *msg)
1015 {
1016         wpa_printf(MSG_DEBUG, "WPS:  * UUID-R");
1017         wpabuf_put_be16(msg, ATTR_UUID_R);
1018         wpabuf_put_be16(msg, WPS_UUID_LEN);
1019         wpabuf_put_data(msg, wps->uuid_r, WPS_UUID_LEN);
1020         return 0;
1021 }
1022
1023
1024 static int wps_build_r_hash(struct wps_data *wps, struct wpabuf *msg)
1025 {
1026         u8 *hash;
1027         const u8 *addr[4];
1028         size_t len[4];
1029
1030         if (os_get_random(wps->snonce, 2 * WPS_SECRET_NONCE_LEN) < 0)
1031                 return -1;
1032         wpa_hexdump(MSG_DEBUG, "WPS: R-S1", wps->snonce, WPS_SECRET_NONCE_LEN);
1033         wpa_hexdump(MSG_DEBUG, "WPS: R-S2",
1034                     wps->snonce + WPS_SECRET_NONCE_LEN, WPS_SECRET_NONCE_LEN);
1035
1036         if (wps->dh_pubkey_e == NULL || wps->dh_pubkey_r == NULL) {
1037                 wpa_printf(MSG_DEBUG, "WPS: DH public keys not available for "
1038                            "R-Hash derivation");
1039                 return -1;
1040         }
1041
1042         wpa_printf(MSG_DEBUG, "WPS:  * R-Hash1");
1043         wpabuf_put_be16(msg, ATTR_R_HASH1);
1044         wpabuf_put_be16(msg, SHA256_MAC_LEN);
1045         hash = wpabuf_put(msg, SHA256_MAC_LEN);
1046         /* R-Hash1 = HMAC_AuthKey(R-S1 || PSK1 || PK_E || PK_R) */
1047         addr[0] = wps->snonce;
1048         len[0] = WPS_SECRET_NONCE_LEN;
1049         addr[1] = wps->psk1;
1050         len[1] = WPS_PSK_LEN;
1051         addr[2] = wpabuf_head(wps->dh_pubkey_e);
1052         len[2] = wpabuf_len(wps->dh_pubkey_e);
1053         addr[3] = wpabuf_head(wps->dh_pubkey_r);
1054         len[3] = wpabuf_len(wps->dh_pubkey_r);
1055         hmac_sha256_vector(wps->authkey, WPS_AUTHKEY_LEN, 4, addr, len, hash);
1056         wpa_hexdump(MSG_DEBUG, "WPS: R-Hash1", hash, SHA256_MAC_LEN);
1057
1058         wpa_printf(MSG_DEBUG, "WPS:  * R-Hash2");
1059         wpabuf_put_be16(msg, ATTR_R_HASH2);
1060         wpabuf_put_be16(msg, SHA256_MAC_LEN);
1061         hash = wpabuf_put(msg, SHA256_MAC_LEN);
1062         /* R-Hash2 = HMAC_AuthKey(R-S2 || PSK2 || PK_E || PK_R) */
1063         addr[0] = wps->snonce + WPS_SECRET_NONCE_LEN;
1064         addr[1] = wps->psk2;
1065         hmac_sha256_vector(wps->authkey, WPS_AUTHKEY_LEN, 4, addr, len, hash);
1066         wpa_hexdump(MSG_DEBUG, "WPS: R-Hash2", hash, SHA256_MAC_LEN);
1067
1068         return 0;
1069 }
1070
1071
1072 static int wps_build_r_snonce1(struct wps_data *wps, struct wpabuf *msg)
1073 {
1074         wpa_printf(MSG_DEBUG, "WPS:  * R-SNonce1");
1075         wpabuf_put_be16(msg, ATTR_R_SNONCE1);
1076         wpabuf_put_be16(msg, WPS_SECRET_NONCE_LEN);
1077         wpabuf_put_data(msg, wps->snonce, WPS_SECRET_NONCE_LEN);
1078         return 0;
1079 }
1080
1081
1082 static int wps_build_r_snonce2(struct wps_data *wps, struct wpabuf *msg)
1083 {
1084         wpa_printf(MSG_DEBUG, "WPS:  * R-SNonce2");
1085         wpabuf_put_be16(msg, ATTR_R_SNONCE2);
1086         wpabuf_put_be16(msg, WPS_SECRET_NONCE_LEN);
1087         wpabuf_put_data(msg, wps->snonce + WPS_SECRET_NONCE_LEN,
1088                         WPS_SECRET_NONCE_LEN);
1089         return 0;
1090 }
1091
1092
1093 static int wps_build_cred_network_idx(struct wpabuf *msg,
1094                                       const struct wps_credential *cred)
1095 {
1096         wpa_printf(MSG_DEBUG, "WPS:  * Network Index");
1097         wpabuf_put_be16(msg, ATTR_NETWORK_INDEX);
1098         wpabuf_put_be16(msg, 1);
1099         wpabuf_put_u8(msg, 1);
1100         return 0;
1101 }
1102
1103
1104 static int wps_build_cred_ssid(struct wpabuf *msg,
1105                                const struct wps_credential *cred)
1106 {
1107         wpa_printf(MSG_DEBUG, "WPS:  * SSID");
1108         wpabuf_put_be16(msg, ATTR_SSID);
1109         wpabuf_put_be16(msg, cred->ssid_len);
1110         wpabuf_put_data(msg, cred->ssid, cred->ssid_len);
1111         return 0;
1112 }
1113
1114
1115 static int wps_build_cred_auth_type(struct wpabuf *msg,
1116                                     const struct wps_credential *cred)
1117 {
1118         wpa_printf(MSG_DEBUG, "WPS:  * Authentication Type (0x%x)",
1119                    cred->auth_type);
1120         wpabuf_put_be16(msg, ATTR_AUTH_TYPE);
1121         wpabuf_put_be16(msg, 2);
1122         wpabuf_put_be16(msg, cred->auth_type);
1123         return 0;
1124 }
1125
1126
1127 static int wps_build_cred_encr_type(struct wpabuf *msg,
1128                                     const struct wps_credential *cred)
1129 {
1130         wpa_printf(MSG_DEBUG, "WPS:  * Encryption Type (0x%x)",
1131                    cred->encr_type);
1132         wpabuf_put_be16(msg, ATTR_ENCR_TYPE);
1133         wpabuf_put_be16(msg, 2);
1134         wpabuf_put_be16(msg, cred->encr_type);
1135         return 0;
1136 }
1137
1138
1139 static int wps_build_cred_network_key(struct wpabuf *msg,
1140                                       const struct wps_credential *cred)
1141 {
1142         wpa_printf(MSG_DEBUG, "WPS:  * Network Key (len=%d)",
1143                    (int) cred->key_len);
1144         wpabuf_put_be16(msg, ATTR_NETWORK_KEY);
1145         wpabuf_put_be16(msg, cred->key_len);
1146         wpabuf_put_data(msg, cred->key, cred->key_len);
1147         return 0;
1148 }
1149
1150
1151 static int wps_build_cred_mac_addr(struct wpabuf *msg,
1152                                    const struct wps_credential *cred)
1153 {
1154         wpa_printf(MSG_DEBUG, "WPS:  * MAC Address (" MACSTR ")",
1155                    MAC2STR(cred->mac_addr));
1156         wpabuf_put_be16(msg, ATTR_MAC_ADDR);
1157         wpabuf_put_be16(msg, ETH_ALEN);
1158         wpabuf_put_data(msg, cred->mac_addr, ETH_ALEN);
1159         return 0;
1160 }
1161
1162
1163 static int wps_build_credential(struct wpabuf *msg,
1164                                 const struct wps_credential *cred)
1165 {
1166         if (wps_build_cred_network_idx(msg, cred) ||
1167             wps_build_cred_ssid(msg, cred) ||
1168             wps_build_cred_auth_type(msg, cred) ||
1169             wps_build_cred_encr_type(msg, cred) ||
1170             wps_build_cred_network_key(msg, cred) ||
1171             wps_build_cred_mac_addr(msg, cred))
1172                 return -1;
1173         return 0;
1174 }
1175
1176
1177 int wps_build_cred(struct wps_data *wps, struct wpabuf *msg)
1178 {
1179         struct wpabuf *cred;
1180
1181         if (wps->wps->registrar->skip_cred_build)
1182                 goto skip_cred_build;
1183
1184         wpa_printf(MSG_DEBUG, "WPS:  * Credential");
1185         if (wps->use_cred) {
1186                 os_memcpy(&wps->cred, wps->use_cred, sizeof(wps->cred));
1187                 goto use_provided;
1188         }
1189         os_memset(&wps->cred, 0, sizeof(wps->cred));
1190
1191         os_memcpy(wps->cred.ssid, wps->wps->ssid, wps->wps->ssid_len);
1192         wps->cred.ssid_len = wps->wps->ssid_len;
1193
1194         /* Select the best authentication and encryption type */
1195         if (wps->auth_type & WPS_AUTH_WPA2PSK)
1196                 wps->auth_type = WPS_AUTH_WPA2PSK;
1197         else if (wps->auth_type & WPS_AUTH_WPAPSK)
1198                 wps->auth_type = WPS_AUTH_WPAPSK;
1199         else if (wps->auth_type & WPS_AUTH_OPEN)
1200                 wps->auth_type = WPS_AUTH_OPEN;
1201         else if (wps->auth_type & WPS_AUTH_SHARED)
1202                 wps->auth_type = WPS_AUTH_SHARED;
1203         else {
1204                 wpa_printf(MSG_DEBUG, "WPS: Unsupported auth_type 0x%x",
1205                            wps->auth_type);
1206                 return -1;
1207         }
1208         wps->cred.auth_type = wps->auth_type;
1209
1210         if (wps->auth_type == WPS_AUTH_WPA2PSK ||
1211             wps->auth_type == WPS_AUTH_WPAPSK) {
1212                 if (wps->encr_type & WPS_ENCR_AES)
1213                         wps->encr_type = WPS_ENCR_AES;
1214                 else if (wps->encr_type & WPS_ENCR_TKIP)
1215                         wps->encr_type = WPS_ENCR_TKIP;
1216                 else {
1217                         wpa_printf(MSG_DEBUG, "WPS: No suitable encryption "
1218                                    "type for WPA/WPA2");
1219                         return -1;
1220                 }
1221         } else {
1222                 if (wps->encr_type & WPS_ENCR_WEP)
1223                         wps->encr_type = WPS_ENCR_WEP;
1224                 else if (wps->encr_type & WPS_ENCR_NONE)
1225                         wps->encr_type = WPS_ENCR_NONE;
1226                 else {
1227                         wpa_printf(MSG_DEBUG, "WPS: No suitable encryption "
1228                                    "type for non-WPA/WPA2 mode");
1229                         return -1;
1230                 }
1231         }
1232         wps->cred.encr_type = wps->encr_type;
1233         /*
1234          * Set MAC address in the Credential to be the Enrollee's MAC address
1235          */
1236         os_memcpy(wps->cred.mac_addr, wps->mac_addr_e, ETH_ALEN);
1237
1238         if (wps->wps->wps_state == WPS_STATE_NOT_CONFIGURED && wps->wps->ap &&
1239             !wps->wps->registrar->disable_auto_conf) {
1240                 u8 r[16];
1241                 /* Generate a random passphrase */
1242                 if (os_get_random(r, sizeof(r)) < 0)
1243                         return -1;
1244                 os_free(wps->new_psk);
1245                 wps->new_psk = base64_encode(r, sizeof(r), &wps->new_psk_len);
1246                 if (wps->new_psk == NULL)
1247                         return -1;
1248                 wps->new_psk_len--; /* remove newline */
1249                 while (wps->new_psk_len &&
1250                        wps->new_psk[wps->new_psk_len - 1] == '=')
1251                         wps->new_psk_len--;
1252                 wpa_hexdump_ascii_key(MSG_DEBUG, "WPS: Generated passphrase",
1253                                       wps->new_psk, wps->new_psk_len);
1254                 os_memcpy(wps->cred.key, wps->new_psk, wps->new_psk_len);
1255                 wps->cred.key_len = wps->new_psk_len;
1256         } else if (wps->use_psk_key && wps->wps->psk_set) {
1257                 char hex[65];
1258                 wpa_printf(MSG_DEBUG, "WPS: Use PSK format for Network Key");
1259                 wpa_snprintf_hex(hex, sizeof(hex), wps->wps->psk, 32);
1260                 os_memcpy(wps->cred.key, hex, 32 * 2);
1261                 wps->cred.key_len = 32 * 2;
1262         } else if (wps->wps->network_key) {
1263                 os_memcpy(wps->cred.key, wps->wps->network_key,
1264                           wps->wps->network_key_len);
1265                 wps->cred.key_len = wps->wps->network_key_len;
1266         } else if (wps->auth_type & (WPS_AUTH_WPAPSK | WPS_AUTH_WPA2PSK)) {
1267                 char hex[65];
1268                 /* Generate a random per-device PSK */
1269                 os_free(wps->new_psk);
1270                 wps->new_psk_len = 32;
1271                 wps->new_psk = os_malloc(wps->new_psk_len);
1272                 if (wps->new_psk == NULL)
1273                         return -1;
1274                 if (os_get_random(wps->new_psk, wps->new_psk_len) < 0) {
1275                         os_free(wps->new_psk);
1276                         wps->new_psk = NULL;
1277                         return -1;
1278                 }
1279                 wpa_hexdump_key(MSG_DEBUG, "WPS: Generated per-device PSK",
1280                                 wps->new_psk, wps->new_psk_len);
1281                 wpa_snprintf_hex(hex, sizeof(hex), wps->new_psk,
1282                                  wps->new_psk_len);
1283                 os_memcpy(wps->cred.key, hex, wps->new_psk_len * 2);
1284                 wps->cred.key_len = wps->new_psk_len * 2;
1285         }
1286
1287 use_provided:
1288         cred = wpabuf_alloc(200);
1289         if (cred == NULL)
1290                 return -1;
1291
1292         if (wps_build_credential(cred, &wps->cred)) {
1293                 wpabuf_free(cred);
1294                 return -1;
1295         }
1296
1297         wpabuf_put_be16(msg, ATTR_CRED);
1298         wpabuf_put_be16(msg, wpabuf_len(cred));
1299         wpabuf_put_buf(msg, cred);
1300         wpabuf_free(cred);
1301
1302 skip_cred_build:
1303         if (wps->wps->registrar->extra_cred) {
1304                 wpa_printf(MSG_DEBUG, "WPS:  * Credential (pre-configured)");
1305                 wpabuf_put_buf(msg, wps->wps->registrar->extra_cred);
1306         }
1307
1308         return 0;
1309 }
1310
1311
1312 static int wps_build_ap_settings(struct wps_data *wps, struct wpabuf *msg)
1313 {
1314         wpa_printf(MSG_DEBUG, "WPS:  * AP Settings");
1315
1316         if (wps_build_credential(msg, &wps->cred))
1317                 return -1;
1318
1319         return 0;
1320 }
1321
1322
1323 static struct wpabuf * wps_build_m2(struct wps_data *wps)
1324 {
1325         struct wpabuf *msg;
1326
1327         if (os_get_random(wps->nonce_r, WPS_NONCE_LEN) < 0)
1328                 return NULL;
1329         wpa_hexdump(MSG_DEBUG, "WPS: Registrar Nonce",
1330                     wps->nonce_r, WPS_NONCE_LEN);
1331         wpa_hexdump(MSG_DEBUG, "WPS: UUID-R", wps->uuid_r, WPS_UUID_LEN);
1332
1333         wpa_printf(MSG_DEBUG, "WPS: Building Message M2");
1334         msg = wpabuf_alloc(1000);
1335         if (msg == NULL)
1336                 return NULL;
1337
1338         if (wps_build_version(msg) ||
1339             wps_build_msg_type(msg, WPS_M2) ||
1340             wps_build_enrollee_nonce(wps, msg) ||
1341             wps_build_registrar_nonce(wps, msg) ||
1342             wps_build_uuid_r(wps, msg) ||
1343             wps_build_public_key(wps, msg) ||
1344             wps_derive_keys(wps) ||
1345             wps_build_auth_type_flags(wps, msg) ||
1346             wps_build_encr_type_flags(wps, msg) ||
1347             wps_build_conn_type_flags(wps, msg) ||
1348             wps_build_config_methods_r(wps->wps->registrar, msg) ||
1349             wps_build_device_attrs(&wps->wps->dev, msg) ||
1350             wps_build_rf_bands(&wps->wps->dev, msg) ||
1351             wps_build_assoc_state(wps, msg) ||
1352             wps_build_config_error(msg, WPS_CFG_NO_ERROR) ||
1353             wps_build_dev_password_id(msg, wps->dev_pw_id) ||
1354             wps_build_os_version(&wps->wps->dev, msg) ||
1355             wps_build_authenticator(wps, msg)) {
1356                 wpabuf_free(msg);
1357                 return NULL;
1358         }
1359
1360         wps->state = RECV_M3;
1361         return msg;
1362 }
1363
1364
1365 static struct wpabuf * wps_build_m2d(struct wps_data *wps)
1366 {
1367         struct wpabuf *msg;
1368         u16 err = wps->config_error;
1369
1370         wpa_printf(MSG_DEBUG, "WPS: Building Message M2D");
1371         msg = wpabuf_alloc(1000);
1372         if (msg == NULL)
1373                 return NULL;
1374
1375         if (wps->wps->ap && wps->wps->ap_setup_locked &&
1376             err == WPS_CFG_NO_ERROR)
1377                 err = WPS_CFG_SETUP_LOCKED;
1378
1379         if (wps_build_version(msg) ||
1380             wps_build_msg_type(msg, WPS_M2D) ||
1381             wps_build_enrollee_nonce(wps, msg) ||
1382             wps_build_registrar_nonce(wps, msg) ||
1383             wps_build_uuid_r(wps, msg) ||
1384             wps_build_auth_type_flags(wps, msg) ||
1385             wps_build_encr_type_flags(wps, msg) ||
1386             wps_build_conn_type_flags(wps, msg) ||
1387             wps_build_config_methods_r(wps->wps->registrar, msg) ||
1388             wps_build_device_attrs(&wps->wps->dev, msg) ||
1389             wps_build_rf_bands(&wps->wps->dev, msg) ||
1390             wps_build_assoc_state(wps, msg) ||
1391             wps_build_config_error(msg, err) ||
1392             wps_build_os_version(&wps->wps->dev, msg)) {
1393                 wpabuf_free(msg);
1394                 return NULL;
1395         }
1396
1397         wps->state = RECV_M2D_ACK;
1398         return msg;
1399 }
1400
1401
1402 static struct wpabuf * wps_build_m4(struct wps_data *wps)
1403 {
1404         struct wpabuf *msg, *plain;
1405
1406         wpa_printf(MSG_DEBUG, "WPS: Building Message M4");
1407
1408         wps_derive_psk(wps, wps->dev_password, wps->dev_password_len);
1409
1410         plain = wpabuf_alloc(200);
1411         if (plain == NULL)
1412                 return NULL;
1413
1414         msg = wpabuf_alloc(1000);
1415         if (msg == NULL) {
1416                 wpabuf_free(plain);
1417                 return NULL;
1418         }
1419
1420         if (wps_build_version(msg) ||
1421             wps_build_msg_type(msg, WPS_M4) ||
1422             wps_build_enrollee_nonce(wps, msg) ||
1423             wps_build_r_hash(wps, msg) ||
1424             wps_build_r_snonce1(wps, plain) ||
1425             wps_build_key_wrap_auth(wps, plain) ||
1426             wps_build_encr_settings(wps, msg, plain) ||
1427             wps_build_authenticator(wps, msg)) {
1428                 wpabuf_free(plain);
1429                 wpabuf_free(msg);
1430                 return NULL;
1431         }
1432         wpabuf_free(plain);
1433
1434         wps->state = RECV_M5;
1435         return msg;
1436 }
1437
1438
1439 static struct wpabuf * wps_build_m6(struct wps_data *wps)
1440 {
1441         struct wpabuf *msg, *plain;
1442
1443         wpa_printf(MSG_DEBUG, "WPS: Building Message M6");
1444
1445         plain = wpabuf_alloc(200);
1446         if (plain == NULL)
1447                 return NULL;
1448
1449         msg = wpabuf_alloc(1000);
1450         if (msg == NULL) {
1451                 wpabuf_free(plain);
1452                 return NULL;
1453         }
1454
1455         if (wps_build_version(msg) ||
1456             wps_build_msg_type(msg, WPS_M6) ||
1457             wps_build_enrollee_nonce(wps, msg) ||
1458             wps_build_r_snonce2(wps, plain) ||
1459             wps_build_key_wrap_auth(wps, plain) ||
1460             wps_build_encr_settings(wps, msg, plain) ||
1461             wps_build_authenticator(wps, msg)) {
1462                 wpabuf_free(plain);
1463                 wpabuf_free(msg);
1464                 return NULL;
1465         }
1466         wpabuf_free(plain);
1467
1468         wps->wps_pin_revealed = 1;
1469         wps->state = RECV_M7;
1470         return msg;
1471 }
1472
1473
1474 static struct wpabuf * wps_build_m8(struct wps_data *wps)
1475 {
1476         struct wpabuf *msg, *plain;
1477
1478         wpa_printf(MSG_DEBUG, "WPS: Building Message M8");
1479
1480         plain = wpabuf_alloc(500);
1481         if (plain == NULL)
1482                 return NULL;
1483
1484         msg = wpabuf_alloc(1000);
1485         if (msg == NULL) {
1486                 wpabuf_free(plain);
1487                 return NULL;
1488         }
1489
1490         if (wps_build_version(msg) ||
1491             wps_build_msg_type(msg, WPS_M8) ||
1492             wps_build_enrollee_nonce(wps, msg) ||
1493             ((wps->wps->ap || wps->er) && wps_build_cred(wps, plain)) ||
1494             (!wps->wps->ap && !wps->er && wps_build_ap_settings(wps, plain)) ||
1495             wps_build_key_wrap_auth(wps, plain) ||
1496             wps_build_encr_settings(wps, msg, plain) ||
1497             wps_build_authenticator(wps, msg)) {
1498                 wpabuf_free(plain);
1499                 wpabuf_free(msg);
1500                 return NULL;
1501         }
1502         wpabuf_free(plain);
1503
1504         wps->state = RECV_DONE;
1505         return msg;
1506 }
1507
1508
1509 static struct wpabuf * wps_build_wsc_ack(struct wps_data *wps)
1510 {
1511         struct wpabuf *msg;
1512
1513         wpa_printf(MSG_DEBUG, "WPS: Building Message WSC_ACK");
1514
1515         msg = wpabuf_alloc(1000);
1516         if (msg == NULL)
1517                 return NULL;
1518
1519         if (wps_build_version(msg) ||
1520             wps_build_msg_type(msg, WPS_WSC_ACK) ||
1521             wps_build_enrollee_nonce(wps, msg) ||
1522             wps_build_registrar_nonce(wps, msg)) {
1523                 wpabuf_free(msg);
1524                 return NULL;
1525         }
1526
1527         return msg;
1528 }
1529
1530
1531 static struct wpabuf * wps_build_wsc_nack(struct wps_data *wps)
1532 {
1533         struct wpabuf *msg;
1534
1535         wpa_printf(MSG_DEBUG, "WPS: Building Message WSC_NACK");
1536
1537         msg = wpabuf_alloc(1000);
1538         if (msg == NULL)
1539                 return NULL;
1540
1541         if (wps_build_version(msg) ||
1542             wps_build_msg_type(msg, WPS_WSC_NACK) ||
1543             wps_build_enrollee_nonce(wps, msg) ||
1544             wps_build_registrar_nonce(wps, msg) ||
1545             wps_build_config_error(msg, wps->config_error)) {
1546                 wpabuf_free(msg);
1547                 return NULL;
1548         }
1549
1550         return msg;
1551 }
1552
1553
1554 struct wpabuf * wps_registrar_get_msg(struct wps_data *wps,
1555                                       enum wsc_op_code *op_code)
1556 {
1557         struct wpabuf *msg;
1558
1559 #ifdef CONFIG_WPS_UPNP
1560         if (wps->wps->wps_upnp) {
1561                 struct upnp_pending_message *p, *prev = NULL;
1562                 if (wps->ext_reg > 1)
1563                         wps_registrar_free_pending_m2(wps->wps);
1564                 p = wps->wps->upnp_msgs;
1565                 /* TODO: check pending message MAC address */
1566                 while (p && p->next) {
1567                         prev = p;
1568                         p = p->next;
1569                 }
1570                 if (p) {
1571                         wpa_printf(MSG_DEBUG, "WPS: Use pending message from "
1572                                    "UPnP");
1573                         if (prev)
1574                                 prev->next = NULL;
1575                         else
1576                                 wps->wps->upnp_msgs = NULL;
1577                         msg = p->msg;
1578                         switch (p->type) {
1579                         case WPS_WSC_ACK:
1580                                 *op_code = WSC_ACK;
1581                                 break;
1582                         case WPS_WSC_NACK:
1583                                 *op_code = WSC_NACK;
1584                                 break;
1585                         default:
1586                                 *op_code = WSC_MSG;
1587                                 break;
1588                         }
1589                         os_free(p);
1590                         if (wps->ext_reg == 0)
1591                                 wps->ext_reg = 1;
1592                         return msg;
1593                 }
1594         }
1595         if (wps->ext_reg) {
1596                 wpa_printf(MSG_DEBUG, "WPS: Using external Registrar, but no "
1597                            "pending message available");
1598                 return NULL;
1599         }
1600 #endif /* CONFIG_WPS_UPNP */
1601
1602         switch (wps->state) {
1603         case SEND_M2:
1604                 if (wps_get_dev_password(wps) < 0)
1605                         msg = wps_build_m2d(wps);
1606                 else
1607                         msg = wps_build_m2(wps);
1608                 *op_code = WSC_MSG;
1609                 break;
1610         case SEND_M2D:
1611                 msg = wps_build_m2d(wps);
1612                 *op_code = WSC_MSG;
1613                 break;
1614         case SEND_M4:
1615                 msg = wps_build_m4(wps);
1616                 *op_code = WSC_MSG;
1617                 break;
1618         case SEND_M6:
1619                 msg = wps_build_m6(wps);
1620                 *op_code = WSC_MSG;
1621                 break;
1622         case SEND_M8:
1623                 msg = wps_build_m8(wps);
1624                 *op_code = WSC_MSG;
1625                 break;
1626         case RECV_DONE:
1627                 msg = wps_build_wsc_ack(wps);
1628                 *op_code = WSC_ACK;
1629                 break;
1630         case SEND_WSC_NACK:
1631                 msg = wps_build_wsc_nack(wps);
1632                 *op_code = WSC_NACK;
1633                 break;
1634         default:
1635                 wpa_printf(MSG_DEBUG, "WPS: Unsupported state %d for building "
1636                            "a message", wps->state);
1637                 msg = NULL;
1638                 break;
1639         }
1640
1641         if (*op_code == WSC_MSG && msg) {
1642                 /* Save a copy of the last message for Authenticator derivation
1643                  */
1644                 wpabuf_free(wps->last_msg);
1645                 wps->last_msg = wpabuf_dup(msg);
1646         }
1647
1648         return msg;
1649 }
1650
1651
1652 static int wps_process_enrollee_nonce(struct wps_data *wps, const u8 *e_nonce)
1653 {
1654         if (e_nonce == NULL) {
1655                 wpa_printf(MSG_DEBUG, "WPS: No Enrollee Nonce received");
1656                 return -1;
1657         }
1658
1659         os_memcpy(wps->nonce_e, e_nonce, WPS_NONCE_LEN);
1660         wpa_hexdump(MSG_DEBUG, "WPS: Enrollee Nonce",
1661                     wps->nonce_e, WPS_NONCE_LEN);
1662
1663         return 0;
1664 }
1665
1666
1667 static int wps_process_registrar_nonce(struct wps_data *wps, const u8 *r_nonce)
1668 {
1669         if (r_nonce == NULL) {
1670                 wpa_printf(MSG_DEBUG, "WPS: No Registrar Nonce received");
1671                 return -1;
1672         }
1673
1674         if (os_memcmp(wps->nonce_r, r_nonce, WPS_NONCE_LEN) != 0) {
1675                 wpa_printf(MSG_DEBUG, "WPS: Invalid Registrar Nonce received");
1676                 return -1;
1677         }
1678
1679         return 0;
1680 }
1681
1682
1683 static int wps_process_uuid_e(struct wps_data *wps, const u8 *uuid_e)
1684 {
1685         if (uuid_e == NULL) {
1686                 wpa_printf(MSG_DEBUG, "WPS: No UUID-E received");
1687                 return -1;
1688         }
1689
1690         os_memcpy(wps->uuid_e, uuid_e, WPS_UUID_LEN);
1691         wpa_hexdump(MSG_DEBUG, "WPS: UUID-E", wps->uuid_e, WPS_UUID_LEN);
1692
1693         return 0;
1694 }
1695
1696
1697 static int wps_process_dev_password_id(struct wps_data *wps, const u8 *pw_id)
1698 {
1699         if (pw_id == NULL) {
1700                 wpa_printf(MSG_DEBUG, "WPS: No Device Password ID received");
1701                 return -1;
1702         }
1703
1704         wps->dev_pw_id = WPA_GET_BE16(pw_id);
1705         wpa_printf(MSG_DEBUG, "WPS: Device Password ID %d", wps->dev_pw_id);
1706
1707         return 0;
1708 }
1709
1710
1711 static int wps_process_e_hash1(struct wps_data *wps, const u8 *e_hash1)
1712 {
1713         if (e_hash1 == NULL) {
1714                 wpa_printf(MSG_DEBUG, "WPS: No E-Hash1 received");
1715                 return -1;
1716         }
1717
1718         os_memcpy(wps->peer_hash1, e_hash1, WPS_HASH_LEN);
1719         wpa_hexdump(MSG_DEBUG, "WPS: E-Hash1", wps->peer_hash1, WPS_HASH_LEN);
1720
1721         return 0;
1722 }
1723
1724
1725 static int wps_process_e_hash2(struct wps_data *wps, const u8 *e_hash2)
1726 {
1727         if (e_hash2 == NULL) {
1728                 wpa_printf(MSG_DEBUG, "WPS: No E-Hash2 received");
1729                 return -1;
1730         }
1731
1732         os_memcpy(wps->peer_hash2, e_hash2, WPS_HASH_LEN);
1733         wpa_hexdump(MSG_DEBUG, "WPS: E-Hash2", wps->peer_hash2, WPS_HASH_LEN);
1734
1735         return 0;
1736 }
1737
1738
1739 static int wps_process_e_snonce1(struct wps_data *wps, const u8 *e_snonce1)
1740 {
1741         u8 hash[SHA256_MAC_LEN];
1742         const u8 *addr[4];
1743         size_t len[4];
1744
1745         if (e_snonce1 == NULL) {
1746                 wpa_printf(MSG_DEBUG, "WPS: No E-SNonce1 received");
1747                 return -1;
1748         }
1749
1750         wpa_hexdump_key(MSG_DEBUG, "WPS: E-SNonce1", e_snonce1,
1751                         WPS_SECRET_NONCE_LEN);
1752
1753         /* E-Hash1 = HMAC_AuthKey(E-S1 || PSK1 || PK_E || PK_R) */
1754         addr[0] = e_snonce1;
1755         len[0] = WPS_SECRET_NONCE_LEN;
1756         addr[1] = wps->psk1;
1757         len[1] = WPS_PSK_LEN;
1758         addr[2] = wpabuf_head(wps->dh_pubkey_e);
1759         len[2] = wpabuf_len(wps->dh_pubkey_e);
1760         addr[3] = wpabuf_head(wps->dh_pubkey_r);
1761         len[3] = wpabuf_len(wps->dh_pubkey_r);
1762         hmac_sha256_vector(wps->authkey, WPS_AUTHKEY_LEN, 4, addr, len, hash);
1763
1764         if (os_memcmp(wps->peer_hash1, hash, WPS_HASH_LEN) != 0) {
1765                 wpa_printf(MSG_DEBUG, "WPS: E-Hash1 derived from E-S1 does "
1766                            "not match with the pre-committed value");
1767                 wps->config_error = WPS_CFG_DEV_PASSWORD_AUTH_FAILURE;
1768                 wps_pwd_auth_fail_event(wps->wps, 0, 1);
1769                 return -1;
1770         }
1771
1772         wpa_printf(MSG_DEBUG, "WPS: Enrollee proved knowledge of the first "
1773                    "half of the device password");
1774
1775         return 0;
1776 }
1777
1778
1779 static int wps_process_e_snonce2(struct wps_data *wps, const u8 *e_snonce2)
1780 {
1781         u8 hash[SHA256_MAC_LEN];
1782         const u8 *addr[4];
1783         size_t len[4];
1784
1785         if (e_snonce2 == NULL) {
1786                 wpa_printf(MSG_DEBUG, "WPS: No E-SNonce2 received");
1787                 return -1;
1788         }
1789
1790         wpa_hexdump_key(MSG_DEBUG, "WPS: E-SNonce2", e_snonce2,
1791                         WPS_SECRET_NONCE_LEN);
1792
1793         /* E-Hash2 = HMAC_AuthKey(E-S2 || PSK2 || PK_E || PK_R) */
1794         addr[0] = e_snonce2;
1795         len[0] = WPS_SECRET_NONCE_LEN;
1796         addr[1] = wps->psk2;
1797         len[1] = WPS_PSK_LEN;
1798         addr[2] = wpabuf_head(wps->dh_pubkey_e);
1799         len[2] = wpabuf_len(wps->dh_pubkey_e);
1800         addr[3] = wpabuf_head(wps->dh_pubkey_r);
1801         len[3] = wpabuf_len(wps->dh_pubkey_r);
1802         hmac_sha256_vector(wps->authkey, WPS_AUTHKEY_LEN, 4, addr, len, hash);
1803
1804         if (os_memcmp(wps->peer_hash2, hash, WPS_HASH_LEN) != 0) {
1805                 wpa_printf(MSG_DEBUG, "WPS: E-Hash2 derived from E-S2 does "
1806                            "not match with the pre-committed value");
1807                 wps_registrar_invalidate_pin(wps->wps->registrar, wps->uuid_e);
1808                 wps->config_error = WPS_CFG_DEV_PASSWORD_AUTH_FAILURE;
1809                 wps_pwd_auth_fail_event(wps->wps, 0, 2);
1810                 return -1;
1811         }
1812
1813         wpa_printf(MSG_DEBUG, "WPS: Enrollee proved knowledge of the second "
1814                    "half of the device password");
1815         wps->wps_pin_revealed = 0;
1816         wps_registrar_unlock_pin(wps->wps->registrar, wps->uuid_e);
1817
1818         return 0;
1819 }
1820
1821
1822 static int wps_process_mac_addr(struct wps_data *wps, const u8 *mac_addr)
1823 {
1824         if (mac_addr == NULL) {
1825                 wpa_printf(MSG_DEBUG, "WPS: No MAC Address received");
1826                 return -1;
1827         }
1828
1829         wpa_printf(MSG_DEBUG, "WPS: Enrollee MAC Address " MACSTR,
1830                    MAC2STR(mac_addr));
1831         os_memcpy(wps->mac_addr_e, mac_addr, ETH_ALEN);
1832         os_memcpy(wps->peer_dev.mac_addr, mac_addr, ETH_ALEN);
1833
1834         return 0;
1835 }
1836
1837
1838 static int wps_process_pubkey(struct wps_data *wps, const u8 *pk,
1839                               size_t pk_len)
1840 {
1841         if (pk == NULL || pk_len == 0) {
1842                 wpa_printf(MSG_DEBUG, "WPS: No Public Key received");
1843                 return -1;
1844         }
1845
1846 #ifdef CONFIG_WPS_OOB
1847         if (wps->wps->oob_conf.pubkey_hash != NULL) {
1848                 const u8 *addr[1];
1849                 u8 hash[WPS_HASH_LEN];
1850
1851                 addr[0] = pk;
1852                 sha256_vector(1, addr, &pk_len, hash);
1853                 if (os_memcmp(hash,
1854                               wpabuf_head(wps->wps->oob_conf.pubkey_hash),
1855                               WPS_OOB_PUBKEY_HASH_LEN) != 0) {
1856                         wpa_printf(MSG_ERROR, "WPS: Public Key hash error");
1857                         return -1;
1858                 }
1859         }
1860 #endif /* CONFIG_WPS_OOB */
1861
1862         wpabuf_free(wps->dh_pubkey_e);
1863         wps->dh_pubkey_e = wpabuf_alloc_copy(pk, pk_len);
1864         if (wps->dh_pubkey_e == NULL)
1865                 return -1;
1866
1867         return 0;
1868 }
1869
1870
1871 static int wps_process_auth_type_flags(struct wps_data *wps, const u8 *auth)
1872 {
1873         u16 auth_types;
1874
1875         if (auth == NULL) {
1876                 wpa_printf(MSG_DEBUG, "WPS: No Authentication Type flags "
1877                            "received");
1878                 return -1;
1879         }
1880
1881         auth_types = WPA_GET_BE16(auth);
1882
1883         wpa_printf(MSG_DEBUG, "WPS: Enrollee Authentication Type flags 0x%x",
1884                    auth_types);
1885         wps->auth_type = wps->wps->auth_types & auth_types;
1886         if (wps->auth_type == 0) {
1887                 wpa_printf(MSG_DEBUG, "WPS: No match in supported "
1888                            "authentication types (own 0x%x Enrollee 0x%x)",
1889                            wps->wps->auth_types, auth_types);
1890 #ifdef WPS_WORKAROUNDS
1891                 /*
1892                  * Some deployed implementations seem to advertise incorrect
1893                  * information in this attribute. For example, Linksys WRT350N
1894                  * seems to have a byteorder bug that breaks this negotiation.
1895                  * In order to interoperate with existing implementations,
1896                  * assume that the Enrollee supports everything we do.
1897                  */
1898                 wpa_printf(MSG_DEBUG, "WPS: Workaround - assume Enrollee "
1899                            "does not advertise supported authentication types "
1900                            "correctly");
1901                 wps->auth_type = wps->wps->auth_types;
1902 #else /* WPS_WORKAROUNDS */
1903                 return -1;
1904 #endif /* WPS_WORKAROUNDS */
1905         }
1906
1907         return 0;
1908 }
1909
1910
1911 static int wps_process_encr_type_flags(struct wps_data *wps, const u8 *encr)
1912 {
1913         u16 encr_types;
1914
1915         if (encr == NULL) {
1916                 wpa_printf(MSG_DEBUG, "WPS: No Encryption Type flags "
1917                            "received");
1918                 return -1;
1919         }
1920
1921         encr_types = WPA_GET_BE16(encr);
1922
1923         wpa_printf(MSG_DEBUG, "WPS: Enrollee Encryption Type flags 0x%x",
1924                    encr_types);
1925         wps->encr_type = wps->wps->encr_types & encr_types;
1926         if (wps->encr_type == 0) {
1927                 wpa_printf(MSG_DEBUG, "WPS: No match in supported "
1928                            "encryption types (own 0x%x Enrollee 0x%x)",
1929                            wps->wps->encr_types, encr_types);
1930 #ifdef WPS_WORKAROUNDS
1931                 /*
1932                  * Some deployed implementations seem to advertise incorrect
1933                  * information in this attribute. For example, Linksys WRT350N
1934                  * seems to have a byteorder bug that breaks this negotiation.
1935                  * In order to interoperate with existing implementations,
1936                  * assume that the Enrollee supports everything we do.
1937                  */
1938                 wpa_printf(MSG_DEBUG, "WPS: Workaround - assume Enrollee "
1939                            "does not advertise supported encryption types "
1940                            "correctly");
1941                 wps->encr_type = wps->wps->encr_types;
1942 #else /* WPS_WORKAROUNDS */
1943                 return -1;
1944 #endif /* WPS_WORKAROUNDS */
1945         }
1946
1947         return 0;
1948 }
1949
1950
1951 static int wps_process_conn_type_flags(struct wps_data *wps, const u8 *conn)
1952 {
1953         if (conn == NULL) {
1954                 wpa_printf(MSG_DEBUG, "WPS: No Connection Type flags "
1955                            "received");
1956                 return -1;
1957         }
1958
1959         wpa_printf(MSG_DEBUG, "WPS: Enrollee Connection Type flags 0x%x",
1960                    *conn);
1961
1962         return 0;
1963 }
1964
1965
1966 static int wps_process_config_methods(struct wps_data *wps, const u8 *methods)
1967 {
1968         u16 m;
1969
1970         if (methods == NULL) {
1971                 wpa_printf(MSG_DEBUG, "WPS: No Config Methods received");
1972                 return -1;
1973         }
1974
1975         m = WPA_GET_BE16(methods);
1976
1977         wpa_printf(MSG_DEBUG, "WPS: Enrollee Config Methods 0x%x"
1978                    "%s%s%s%s%s%s%s%s%s", m,
1979                    m & WPS_CONFIG_USBA ? " [USBA]" : "",
1980                    m & WPS_CONFIG_ETHERNET ? " [Ethernet]" : "",
1981                    m & WPS_CONFIG_LABEL ? " [Label]" : "",
1982                    m & WPS_CONFIG_DISPLAY ? " [Display]" : "",
1983                    m & WPS_CONFIG_EXT_NFC_TOKEN ? " [Ext NFC Token]" : "",
1984                    m & WPS_CONFIG_INT_NFC_TOKEN ? " [Int NFC Token]" : "",
1985                    m & WPS_CONFIG_NFC_INTERFACE ? " [NFC]" : "",
1986                    m & WPS_CONFIG_PUSHBUTTON ? " [PBC]" : "",
1987                    m & WPS_CONFIG_KEYPAD ? " [Keypad]" : "");
1988
1989         if (!(m & WPS_CONFIG_DISPLAY) && !wps->use_psk_key) {
1990                 /*
1991                  * The Enrollee does not have a display so it is unlikely to be
1992                  * able to show the passphrase to a user and as such, could
1993                  * benefit from receiving PSK to reduce key derivation time.
1994                  */
1995                 wpa_printf(MSG_DEBUG, "WPS: Prefer PSK format key due to "
1996                            "Enrollee not supporting display");
1997                 wps->use_psk_key = 1;
1998         }
1999
2000         return 0;
2001 }
2002
2003
2004 static int wps_process_wps_state(struct wps_data *wps, const u8 *state)
2005 {
2006         if (state == NULL) {
2007                 wpa_printf(MSG_DEBUG, "WPS: No Wi-Fi Protected Setup State "
2008                            "received");
2009                 return -1;
2010         }
2011
2012         wpa_printf(MSG_DEBUG, "WPS: Enrollee Wi-Fi Protected Setup State %d",
2013                    *state);
2014
2015         return 0;
2016 }
2017
2018
2019 static int wps_process_assoc_state(struct wps_data *wps, const u8 *assoc)
2020 {
2021         u16 a;
2022
2023         if (assoc == NULL) {
2024                 wpa_printf(MSG_DEBUG, "WPS: No Association State received");
2025                 return -1;
2026         }
2027
2028         a = WPA_GET_BE16(assoc);
2029         wpa_printf(MSG_DEBUG, "WPS: Enrollee Association State %d", a);
2030
2031         return 0;
2032 }
2033
2034
2035 static int wps_process_config_error(struct wps_data *wps, const u8 *err)
2036 {
2037         u16 e;
2038
2039         if (err == NULL) {
2040                 wpa_printf(MSG_DEBUG, "WPS: No Configuration Error received");
2041                 return -1;
2042         }
2043
2044         e = WPA_GET_BE16(err);
2045         wpa_printf(MSG_DEBUG, "WPS: Enrollee Configuration Error %d", e);
2046
2047         return 0;
2048 }
2049
2050
2051 static enum wps_process_res wps_process_m1(struct wps_data *wps,
2052                                            struct wps_parse_attr *attr)
2053 {
2054         wpa_printf(MSG_DEBUG, "WPS: Received M1");
2055
2056         if (wps->state != RECV_M1) {
2057                 wpa_printf(MSG_DEBUG, "WPS: Unexpected state (%d) for "
2058                            "receiving M1", wps->state);
2059                 return WPS_FAILURE;
2060         }
2061
2062         if (wps_process_uuid_e(wps, attr->uuid_e) ||
2063             wps_process_mac_addr(wps, attr->mac_addr) ||
2064             wps_process_enrollee_nonce(wps, attr->enrollee_nonce) ||
2065             wps_process_pubkey(wps, attr->public_key, attr->public_key_len) ||
2066             wps_process_auth_type_flags(wps, attr->auth_type_flags) ||
2067             wps_process_encr_type_flags(wps, attr->encr_type_flags) ||
2068             wps_process_conn_type_flags(wps, attr->conn_type_flags) ||
2069             wps_process_config_methods(wps, attr->config_methods) ||
2070             wps_process_wps_state(wps, attr->wps_state) ||
2071             wps_process_device_attrs(&wps->peer_dev, attr) ||
2072             wps_process_rf_bands(&wps->peer_dev, attr->rf_bands) ||
2073             wps_process_assoc_state(wps, attr->assoc_state) ||
2074             wps_process_dev_password_id(wps, attr->dev_password_id) ||
2075             wps_process_config_error(wps, attr->config_error) ||
2076             wps_process_os_version(&wps->peer_dev, attr->os_version))
2077                 return WPS_FAILURE;
2078
2079         if (wps->dev_pw_id < 0x10 &&
2080             wps->dev_pw_id != DEV_PW_DEFAULT &&
2081             wps->dev_pw_id != DEV_PW_USER_SPECIFIED &&
2082             wps->dev_pw_id != DEV_PW_MACHINE_SPECIFIED &&
2083             wps->dev_pw_id != DEV_PW_REGISTRAR_SPECIFIED &&
2084             (wps->dev_pw_id != DEV_PW_PUSHBUTTON ||
2085              !wps->wps->registrar->pbc)) {
2086                 wpa_printf(MSG_DEBUG, "WPS: Unsupported Device Password ID %d",
2087                            wps->dev_pw_id);
2088                 wps->state = SEND_M2D;
2089                 return WPS_CONTINUE;
2090         }
2091
2092 #ifdef CONFIG_WPS_OOB
2093         if (wps->dev_pw_id >= 0x10 &&
2094             wps->dev_pw_id != wps->wps->oob_dev_pw_id) {
2095                 wpa_printf(MSG_DEBUG, "WPS: OOB Device Password ID "
2096                            "%d mismatch", wps->dev_pw_id);
2097                 wps->state = SEND_M2D;
2098                 return WPS_CONTINUE;
2099         }
2100 #endif /* CONFIG_WPS_OOB */
2101
2102         if (wps->dev_pw_id == DEV_PW_PUSHBUTTON) {
2103                 if (wps->wps->registrar->force_pbc_overlap ||
2104                     wps_registrar_pbc_overlap(wps->wps->registrar,
2105                                               wps->mac_addr_e, wps->uuid_e)) {
2106                         wpa_printf(MSG_DEBUG, "WPS: PBC overlap - deny PBC "
2107                                    "negotiation");
2108                         wps->state = SEND_M2D;
2109                         wps->config_error = WPS_CFG_MULTIPLE_PBC_DETECTED;
2110                         wps_pbc_overlap_event(wps->wps);
2111                         wps->wps->registrar->force_pbc_overlap = 1;
2112                         return WPS_CONTINUE;
2113                 }
2114                 wps_registrar_add_pbc_session(wps->wps->registrar,
2115                                               wps->mac_addr_e, wps->uuid_e);
2116                 wps->pbc = 1;
2117         }
2118
2119         wps->state = SEND_M2;
2120         return WPS_CONTINUE;
2121 }
2122
2123
2124 static enum wps_process_res wps_process_m3(struct wps_data *wps,
2125                                            const struct wpabuf *msg,
2126                                            struct wps_parse_attr *attr)
2127 {
2128         wpa_printf(MSG_DEBUG, "WPS: Received M3");
2129
2130         if (wps->state != RECV_M3) {
2131                 wpa_printf(MSG_DEBUG, "WPS: Unexpected state (%d) for "
2132                            "receiving M3", wps->state);
2133                 wps->state = SEND_WSC_NACK;
2134                 return WPS_CONTINUE;
2135         }
2136
2137         if (wps->pbc && wps->wps->registrar->force_pbc_overlap) {
2138                 wpa_printf(MSG_DEBUG, "WPS: Reject negotiation due to PBC "
2139                            "session overlap");
2140                 wps->state = SEND_WSC_NACK;
2141                 wps->config_error = WPS_CFG_MULTIPLE_PBC_DETECTED;
2142                 return WPS_CONTINUE;
2143         }
2144
2145         if (wps_process_registrar_nonce(wps, attr->registrar_nonce) ||
2146             wps_process_authenticator(wps, attr->authenticator, msg) ||
2147             wps_process_e_hash1(wps, attr->e_hash1) ||
2148             wps_process_e_hash2(wps, attr->e_hash2)) {
2149                 wps->state = SEND_WSC_NACK;
2150                 return WPS_CONTINUE;
2151         }
2152
2153         wps->state = SEND_M4;
2154         return WPS_CONTINUE;
2155 }
2156
2157
2158 static enum wps_process_res wps_process_m5(struct wps_data *wps,
2159                                            const struct wpabuf *msg,
2160                                            struct wps_parse_attr *attr)
2161 {
2162         struct wpabuf *decrypted;
2163         struct wps_parse_attr eattr;
2164
2165         wpa_printf(MSG_DEBUG, "WPS: Received M5");
2166
2167         if (wps->state != RECV_M5) {
2168                 wpa_printf(MSG_DEBUG, "WPS: Unexpected state (%d) for "
2169                            "receiving M5", wps->state);
2170                 wps->state = SEND_WSC_NACK;
2171                 return WPS_CONTINUE;
2172         }
2173
2174         if (wps->pbc && wps->wps->registrar->force_pbc_overlap) {
2175                 wpa_printf(MSG_DEBUG, "WPS: Reject negotiation due to PBC "
2176                            "session overlap");
2177                 wps->state = SEND_WSC_NACK;
2178                 wps->config_error = WPS_CFG_MULTIPLE_PBC_DETECTED;
2179                 return WPS_CONTINUE;
2180         }
2181
2182         if (wps_process_registrar_nonce(wps, attr->registrar_nonce) ||
2183             wps_process_authenticator(wps, attr->authenticator, msg)) {
2184                 wps->state = SEND_WSC_NACK;
2185                 return WPS_CONTINUE;
2186         }
2187
2188         decrypted = wps_decrypt_encr_settings(wps, attr->encr_settings,
2189                                               attr->encr_settings_len);
2190         if (decrypted == NULL) {
2191                 wpa_printf(MSG_DEBUG, "WPS: Failed to decrypted Encrypted "
2192                            "Settings attribute");
2193                 wps->state = SEND_WSC_NACK;
2194                 return WPS_CONTINUE;
2195         }
2196
2197         wpa_printf(MSG_DEBUG, "WPS: Processing decrypted Encrypted Settings "
2198                    "attribute");
2199         if (wps_parse_msg(decrypted, &eattr) < 0 ||
2200             wps_process_key_wrap_auth(wps, decrypted, eattr.key_wrap_auth) ||
2201             wps_process_e_snonce1(wps, eattr.e_snonce1)) {
2202                 wpabuf_free(decrypted);
2203                 wps->state = SEND_WSC_NACK;
2204                 return WPS_CONTINUE;
2205         }
2206         wpabuf_free(decrypted);
2207
2208         wps->state = SEND_M6;
2209         return WPS_CONTINUE;
2210 }
2211
2212
2213 static void wps_sta_cred_cb(struct wps_data *wps)
2214 {
2215         /*
2216          * Update credential to only include a single authentication and
2217          * encryption type in case the AP configuration includes more than one
2218          * option.
2219          */
2220         if (wps->cred.auth_type & WPS_AUTH_WPA2PSK)
2221                 wps->cred.auth_type = WPS_AUTH_WPA2PSK;
2222         else if (wps->cred.auth_type & WPS_AUTH_WPAPSK)
2223                 wps->cred.auth_type = WPS_AUTH_WPAPSK;
2224         if (wps->cred.encr_type & WPS_ENCR_AES)
2225                 wps->cred.encr_type = WPS_ENCR_AES;
2226         else if (wps->cred.encr_type & WPS_ENCR_TKIP)
2227                 wps->cred.encr_type = WPS_ENCR_TKIP;
2228         wpa_printf(MSG_DEBUG, "WPS: Update local configuration based on the "
2229                    "AP configuration");
2230         if (wps->wps->cred_cb)
2231                 wps->wps->cred_cb(wps->wps->cb_ctx, &wps->cred);
2232 }
2233
2234
2235 static void wps_cred_update(struct wps_credential *dst,
2236                             struct wps_credential *src)
2237 {
2238         os_memcpy(dst->ssid, src->ssid, sizeof(dst->ssid));
2239         dst->ssid_len = src->ssid_len;
2240         dst->auth_type = src->auth_type;
2241         dst->encr_type = src->encr_type;
2242         dst->key_idx = src->key_idx;
2243         os_memcpy(dst->key, src->key, sizeof(dst->key));
2244         dst->key_len = src->key_len;
2245 }
2246
2247
2248 static int wps_process_ap_settings_r(struct wps_data *wps,
2249                                      struct wps_parse_attr *attr)
2250 {
2251         if (wps->wps->ap || wps->er)
2252                 return 0;
2253
2254         /* AP Settings Attributes in M7 when Enrollee is an AP */
2255         if (wps_process_ap_settings(attr, &wps->cred) < 0)
2256                 return -1;
2257
2258         wpa_printf(MSG_INFO, "WPS: Received old AP configuration from AP");
2259
2260         if (wps->new_ap_settings) {
2261                 wpa_printf(MSG_INFO, "WPS: Update AP configuration based on "
2262                            "new settings");
2263                 wps_cred_update(&wps->cred, wps->new_ap_settings);
2264                 return 0;
2265         } else {
2266                 /*
2267                  * Use the AP PIN only to receive the current AP settings, not
2268                  * to reconfigure the AP.
2269                  */
2270                 if (wps->ap_settings_cb) {
2271                         wps->ap_settings_cb(wps->ap_settings_cb_ctx,
2272                                             &wps->cred);
2273                         return 1;
2274                 }
2275                 wps_sta_cred_cb(wps);
2276                 return 1;
2277         }
2278 }
2279
2280
2281 static enum wps_process_res wps_process_m7(struct wps_data *wps,
2282                                            const struct wpabuf *msg,
2283                                            struct wps_parse_attr *attr)
2284 {
2285         struct wpabuf *decrypted;
2286         struct wps_parse_attr eattr;
2287
2288         wpa_printf(MSG_DEBUG, "WPS: Received M7");
2289
2290         if (wps->state != RECV_M7) {
2291                 wpa_printf(MSG_DEBUG, "WPS: Unexpected state (%d) for "
2292                            "receiving M7", wps->state);
2293                 wps->state = SEND_WSC_NACK;
2294                 return WPS_CONTINUE;
2295         }
2296
2297         if (wps->pbc && wps->wps->registrar->force_pbc_overlap) {
2298                 wpa_printf(MSG_DEBUG, "WPS: Reject negotiation due to PBC "
2299                            "session overlap");
2300                 wps->state = SEND_WSC_NACK;
2301                 wps->config_error = WPS_CFG_MULTIPLE_PBC_DETECTED;
2302                 return WPS_CONTINUE;
2303         }
2304
2305         if (wps_process_registrar_nonce(wps, attr->registrar_nonce) ||
2306             wps_process_authenticator(wps, attr->authenticator, msg)) {
2307                 wps->state = SEND_WSC_NACK;
2308                 return WPS_CONTINUE;
2309         }
2310
2311         decrypted = wps_decrypt_encr_settings(wps, attr->encr_settings,
2312                                               attr->encr_settings_len);
2313         if (decrypted == NULL) {
2314                 wpa_printf(MSG_DEBUG, "WPS: Failed to decrypt Encrypted "
2315                            "Settings attribute");
2316                 wps->state = SEND_WSC_NACK;
2317                 return WPS_CONTINUE;
2318         }
2319
2320         wpa_printf(MSG_DEBUG, "WPS: Processing decrypted Encrypted Settings "
2321                    "attribute");
2322         if (wps_parse_msg(decrypted, &eattr) < 0 ||
2323             wps_process_key_wrap_auth(wps, decrypted, eattr.key_wrap_auth) ||
2324             wps_process_e_snonce2(wps, eattr.e_snonce2) ||
2325             wps_process_ap_settings_r(wps, &eattr)) {
2326                 wpabuf_free(decrypted);
2327                 wps->state = SEND_WSC_NACK;
2328                 return WPS_CONTINUE;
2329         }
2330
2331         wpabuf_free(decrypted);
2332
2333         wps->state = SEND_M8;
2334         return WPS_CONTINUE;
2335 }
2336
2337
2338 static enum wps_process_res wps_process_wsc_msg(struct wps_data *wps,
2339                                                 const struct wpabuf *msg)
2340 {
2341         struct wps_parse_attr attr;
2342         enum wps_process_res ret = WPS_CONTINUE;
2343
2344         wpa_printf(MSG_DEBUG, "WPS: Received WSC_MSG");
2345
2346         if (wps_parse_msg(msg, &attr) < 0)
2347                 return WPS_FAILURE;
2348
2349         if (!wps_version_supported(attr.version)) {
2350                 wpa_printf(MSG_DEBUG, "WPS: Unsupported message version 0x%x",
2351                            attr.version ? *attr.version : 0);
2352                 return WPS_FAILURE;
2353         }
2354
2355         if (attr.msg_type == NULL) {
2356                 wpa_printf(MSG_DEBUG, "WPS: No Message Type attribute");
2357                 return WPS_FAILURE;
2358         }
2359
2360         if (*attr.msg_type != WPS_M1 &&
2361             (attr.registrar_nonce == NULL ||
2362              os_memcmp(wps->nonce_r, attr.registrar_nonce,
2363                        WPS_NONCE_LEN != 0))) {
2364                 wpa_printf(MSG_DEBUG, "WPS: Mismatch in registrar nonce");
2365                 return WPS_FAILURE;
2366         }
2367
2368         switch (*attr.msg_type) {
2369         case WPS_M1:
2370 #ifdef CONFIG_WPS_UPNP
2371                 if (wps->wps->wps_upnp && attr.mac_addr) {
2372                         /* Remove old pending messages when starting new run */
2373                         wps_free_pending_msgs(wps->wps->upnp_msgs);
2374                         wps->wps->upnp_msgs = NULL;
2375
2376                         upnp_wps_device_send_wlan_event(
2377                                 wps->wps->wps_upnp, attr.mac_addr,
2378                                 UPNP_WPS_WLANEVENT_TYPE_EAP, msg);
2379                 }
2380 #endif /* CONFIG_WPS_UPNP */
2381                 ret = wps_process_m1(wps, &attr);
2382                 break;
2383         case WPS_M3:
2384                 ret = wps_process_m3(wps, msg, &attr);
2385                 if (ret == WPS_FAILURE || wps->state == SEND_WSC_NACK)
2386                         wps_fail_event(wps->wps, WPS_M3);
2387                 break;
2388         case WPS_M5:
2389                 ret = wps_process_m5(wps, msg, &attr);
2390                 if (ret == WPS_FAILURE || wps->state == SEND_WSC_NACK)
2391                         wps_fail_event(wps->wps, WPS_M5);
2392                 break;
2393         case WPS_M7:
2394                 ret = wps_process_m7(wps, msg, &attr);
2395                 if (ret == WPS_FAILURE || wps->state == SEND_WSC_NACK)
2396                         wps_fail_event(wps->wps, WPS_M7);
2397                 break;
2398         default:
2399                 wpa_printf(MSG_DEBUG, "WPS: Unsupported Message Type %d",
2400                            *attr.msg_type);
2401                 return WPS_FAILURE;
2402         }
2403
2404         if (ret == WPS_CONTINUE) {
2405                 /* Save a copy of the last message for Authenticator derivation
2406                  */
2407                 wpabuf_free(wps->last_msg);
2408                 wps->last_msg = wpabuf_dup(msg);
2409         }
2410
2411         return ret;
2412 }
2413
2414
2415 static enum wps_process_res wps_process_wsc_ack(struct wps_data *wps,
2416                                                 const struct wpabuf *msg)
2417 {
2418         struct wps_parse_attr attr;
2419
2420         wpa_printf(MSG_DEBUG, "WPS: Received WSC_ACK");
2421
2422         if (wps_parse_msg(msg, &attr) < 0)
2423                 return WPS_FAILURE;
2424
2425         if (!wps_version_supported(attr.version)) {
2426                 wpa_printf(MSG_DEBUG, "WPS: Unsupported message version 0x%x",
2427                            attr.version ? *attr.version : 0);
2428                 return WPS_FAILURE;
2429         }
2430
2431         if (attr.msg_type == NULL) {
2432                 wpa_printf(MSG_DEBUG, "WPS: No Message Type attribute");
2433                 return WPS_FAILURE;
2434         }
2435
2436         if (*attr.msg_type != WPS_WSC_ACK) {
2437                 wpa_printf(MSG_DEBUG, "WPS: Invalid Message Type %d",
2438                            *attr.msg_type);
2439                 return WPS_FAILURE;
2440         }
2441
2442 #ifdef CONFIG_WPS_UPNP
2443         if (wps->wps->wps_upnp && wps->ext_reg && wps->state == RECV_M2D_ACK &&
2444             upnp_wps_subscribers(wps->wps->wps_upnp)) {
2445                 if (wps->wps->upnp_msgs)
2446                         return WPS_CONTINUE;
2447                 wpa_printf(MSG_DEBUG, "WPS: Wait for response from an "
2448                            "external Registrar");
2449                 return WPS_PENDING;
2450         }
2451 #endif /* CONFIG_WPS_UPNP */
2452
2453         if (attr.registrar_nonce == NULL ||
2454             os_memcmp(wps->nonce_r, attr.registrar_nonce, WPS_NONCE_LEN != 0))
2455         {
2456                 wpa_printf(MSG_DEBUG, "WPS: Mismatch in registrar nonce");
2457                 return WPS_FAILURE;
2458         }
2459
2460         if (attr.enrollee_nonce == NULL ||
2461             os_memcmp(wps->nonce_e, attr.enrollee_nonce, WPS_NONCE_LEN != 0)) {
2462                 wpa_printf(MSG_DEBUG, "WPS: Mismatch in enrollee nonce");
2463                 return WPS_FAILURE;
2464         }
2465
2466         if (wps->state == RECV_M2D_ACK) {
2467 #ifdef CONFIG_WPS_UPNP
2468                 if (wps->wps->wps_upnp &&
2469                     upnp_wps_subscribers(wps->wps->wps_upnp)) {
2470                         if (wps->wps->upnp_msgs)
2471                                 return WPS_CONTINUE;
2472                         if (wps->ext_reg == 0)
2473                                 wps->ext_reg = 1;
2474                         wpa_printf(MSG_DEBUG, "WPS: Wait for response from an "
2475                                    "external Registrar");
2476                         return WPS_PENDING;
2477                 }
2478 #endif /* CONFIG_WPS_UPNP */
2479
2480                 wpa_printf(MSG_DEBUG, "WPS: No more registrars available - "
2481                            "terminate negotiation");
2482         }
2483
2484         return WPS_FAILURE;
2485 }
2486
2487
2488 static enum wps_process_res wps_process_wsc_nack(struct wps_data *wps,
2489                                                  const struct wpabuf *msg)
2490 {
2491         struct wps_parse_attr attr;
2492         int old_state;
2493
2494         wpa_printf(MSG_DEBUG, "WPS: Received WSC_NACK");
2495
2496         old_state = wps->state;
2497         wps->state = SEND_WSC_NACK;
2498
2499         if (wps_parse_msg(msg, &attr) < 0)
2500                 return WPS_FAILURE;
2501
2502         if (!wps_version_supported(attr.version)) {
2503                 wpa_printf(MSG_DEBUG, "WPS: Unsupported message version 0x%x",
2504                            attr.version ? *attr.version : 0);
2505                 return WPS_FAILURE;
2506         }
2507
2508         if (attr.msg_type == NULL) {
2509                 wpa_printf(MSG_DEBUG, "WPS: No Message Type attribute");
2510                 return WPS_FAILURE;
2511         }
2512
2513         if (*attr.msg_type != WPS_WSC_NACK) {
2514                 wpa_printf(MSG_DEBUG, "WPS: Invalid Message Type %d",
2515                            *attr.msg_type);
2516                 return WPS_FAILURE;
2517         }
2518
2519 #ifdef CONFIG_WPS_UPNP
2520         if (wps->wps->wps_upnp && wps->ext_reg) {
2521                 wpa_printf(MSG_DEBUG, "WPS: Negotiation using external "
2522                            "Registrar terminated by the Enrollee");
2523                 return WPS_FAILURE;
2524         }
2525 #endif /* CONFIG_WPS_UPNP */
2526
2527         if (attr.registrar_nonce == NULL ||
2528             os_memcmp(wps->nonce_r, attr.registrar_nonce, WPS_NONCE_LEN != 0))
2529         {
2530                 wpa_printf(MSG_DEBUG, "WPS: Mismatch in registrar nonce");
2531                 return WPS_FAILURE;
2532         }
2533
2534         if (attr.enrollee_nonce == NULL ||
2535             os_memcmp(wps->nonce_e, attr.enrollee_nonce, WPS_NONCE_LEN != 0)) {
2536                 wpa_printf(MSG_DEBUG, "WPS: Mismatch in enrollee nonce");
2537                 return WPS_FAILURE;
2538         }
2539
2540         if (attr.config_error == NULL) {
2541                 wpa_printf(MSG_DEBUG, "WPS: No Configuration Error attribute "
2542                            "in WSC_NACK");
2543                 return WPS_FAILURE;
2544         }
2545
2546         wpa_printf(MSG_DEBUG, "WPS: Enrollee terminated negotiation with "
2547                    "Configuration Error %d", WPA_GET_BE16(attr.config_error));
2548
2549         switch (old_state) {
2550         case RECV_M3:
2551                 wps_fail_event(wps->wps, WPS_M2);
2552                 break;
2553         case RECV_M5:
2554                 wps_fail_event(wps->wps, WPS_M4);
2555                 break;
2556         case RECV_M7:
2557                 wps_fail_event(wps->wps, WPS_M6);
2558                 break;
2559         case RECV_DONE:
2560                 wps_fail_event(wps->wps, WPS_M8);
2561                 break;
2562         default:
2563                 break;
2564         }
2565
2566         return WPS_FAILURE;
2567 }
2568
2569
2570 static enum wps_process_res wps_process_wsc_done(struct wps_data *wps,
2571                                                  const struct wpabuf *msg)
2572 {
2573         struct wps_parse_attr attr;
2574
2575         wpa_printf(MSG_DEBUG, "WPS: Received WSC_Done");
2576
2577         if (wps->state != RECV_DONE &&
2578             (!wps->wps->wps_upnp || !wps->ext_reg)) {
2579                 wpa_printf(MSG_DEBUG, "WPS: Unexpected state (%d) for "
2580                            "receiving WSC_Done", wps->state);
2581                 return WPS_FAILURE;
2582         }
2583
2584         if (wps_parse_msg(msg, &attr) < 0)
2585                 return WPS_FAILURE;
2586
2587         if (!wps_version_supported(attr.version)) {
2588                 wpa_printf(MSG_DEBUG, "WPS: Unsupported message version 0x%x",
2589                            attr.version ? *attr.version : 0);
2590                 return WPS_FAILURE;
2591         }
2592
2593         if (attr.msg_type == NULL) {
2594                 wpa_printf(MSG_DEBUG, "WPS: No Message Type attribute");
2595                 return WPS_FAILURE;
2596         }
2597
2598         if (*attr.msg_type != WPS_WSC_DONE) {
2599                 wpa_printf(MSG_DEBUG, "WPS: Invalid Message Type %d",
2600                            *attr.msg_type);
2601                 return WPS_FAILURE;
2602         }
2603
2604 #ifdef CONFIG_WPS_UPNP
2605         if (wps->wps->wps_upnp && wps->ext_reg) {
2606                 wpa_printf(MSG_DEBUG, "WPS: Negotiation using external "
2607                            "Registrar completed successfully");
2608                 wps_device_store(wps->wps->registrar, &wps->peer_dev,
2609                                  wps->uuid_e);
2610                 return WPS_DONE;
2611         }
2612 #endif /* CONFIG_WPS_UPNP */
2613
2614         if (attr.registrar_nonce == NULL ||
2615             os_memcmp(wps->nonce_r, attr.registrar_nonce, WPS_NONCE_LEN != 0))
2616         {
2617                 wpa_printf(MSG_DEBUG, "WPS: Mismatch in registrar nonce");
2618                 return WPS_FAILURE;
2619         }
2620
2621         if (attr.enrollee_nonce == NULL ||
2622             os_memcmp(wps->nonce_e, attr.enrollee_nonce, WPS_NONCE_LEN != 0)) {
2623                 wpa_printf(MSG_DEBUG, "WPS: Mismatch in enrollee nonce");
2624                 return WPS_FAILURE;
2625         }
2626
2627         wpa_printf(MSG_DEBUG, "WPS: Negotiation completed successfully");
2628         wps_device_store(wps->wps->registrar, &wps->peer_dev,
2629                          wps->uuid_e);
2630
2631         if (wps->wps->wps_state == WPS_STATE_NOT_CONFIGURED && wps->new_psk &&
2632             wps->wps->ap && !wps->wps->registrar->disable_auto_conf) {
2633                 struct wps_credential cred;
2634
2635                 wpa_printf(MSG_DEBUG, "WPS: Moving to Configured state based "
2636                            "on first Enrollee connection");
2637
2638                 os_memset(&cred, 0, sizeof(cred));
2639                 os_memcpy(cred.ssid, wps->wps->ssid, wps->wps->ssid_len);
2640                 cred.ssid_len = wps->wps->ssid_len;
2641                 cred.auth_type = WPS_AUTH_WPAPSK | WPS_AUTH_WPA2PSK;
2642                 cred.encr_type = WPS_ENCR_TKIP | WPS_ENCR_AES;
2643                 os_memcpy(cred.key, wps->new_psk, wps->new_psk_len);
2644                 cred.key_len = wps->new_psk_len;
2645
2646                 wps->wps->wps_state = WPS_STATE_CONFIGURED;
2647                 wpa_hexdump_ascii_key(MSG_DEBUG,
2648                                       "WPS: Generated random passphrase",
2649                                       wps->new_psk, wps->new_psk_len);
2650                 if (wps->wps->cred_cb)
2651                         wps->wps->cred_cb(wps->wps->cb_ctx, &cred);
2652
2653                 os_free(wps->new_psk);
2654                 wps->new_psk = NULL;
2655         }
2656
2657         if (!wps->wps->ap && !wps->er)
2658                 wps_sta_cred_cb(wps);
2659
2660         if (wps->new_psk) {
2661                 if (wps_cb_new_psk(wps->wps->registrar, wps->mac_addr_e,
2662                                    wps->new_psk, wps->new_psk_len)) {
2663                         wpa_printf(MSG_DEBUG, "WPS: Failed to configure the "
2664                                    "new PSK");
2665                 }
2666                 os_free(wps->new_psk);
2667                 wps->new_psk = NULL;
2668         }
2669
2670         wps_cb_reg_success(wps->wps->registrar, wps->mac_addr_e, wps->uuid_e);
2671
2672         if (wps->pbc) {
2673                 wps_registrar_remove_pbc_session(wps->wps->registrar,
2674                                                  wps->mac_addr_e, wps->uuid_e);
2675                 wps_registrar_pbc_completed(wps->wps->registrar);
2676         } else {
2677                 wps_registrar_pin_completed(wps->wps->registrar);
2678         }
2679
2680         wps_success_event(wps->wps);
2681
2682         return WPS_DONE;
2683 }
2684
2685
2686 enum wps_process_res wps_registrar_process_msg(struct wps_data *wps,
2687                                                enum wsc_op_code op_code,
2688                                                const struct wpabuf *msg)
2689 {
2690         enum wps_process_res ret;
2691
2692         wpa_printf(MSG_DEBUG, "WPS: Processing received message (len=%lu "
2693                    "op_code=%d)",
2694                    (unsigned long) wpabuf_len(msg), op_code);
2695
2696 #ifdef CONFIG_WPS_UPNP
2697         if (wps->wps->wps_upnp && op_code == WSC_MSG && wps->ext_reg == 1) {
2698                 struct wps_parse_attr attr;
2699                 if (wps_parse_msg(msg, &attr) == 0 && attr.msg_type &&
2700                     *attr.msg_type == WPS_M3)
2701                         wps->ext_reg = 2; /* past M2/M2D phase */
2702         }
2703         if (wps->ext_reg > 1)
2704                 wps_registrar_free_pending_m2(wps->wps);
2705         if (wps->wps->wps_upnp && wps->ext_reg &&
2706             wps->wps->upnp_msgs == NULL &&
2707             (op_code == WSC_MSG || op_code == WSC_Done || op_code == WSC_NACK))
2708         {
2709                 struct wps_parse_attr attr;
2710                 int type;
2711                 if (wps_parse_msg(msg, &attr) < 0 || attr.msg_type == NULL)
2712                         type = -1;
2713                 else
2714                         type = *attr.msg_type;
2715                 wpa_printf(MSG_DEBUG, "WPS: Sending received message (type %d)"
2716                            " to external Registrar for processing", type);
2717                 upnp_wps_device_send_wlan_event(wps->wps->wps_upnp,
2718                                                 wps->mac_addr_e,
2719                                                 UPNP_WPS_WLANEVENT_TYPE_EAP,
2720                                                 msg);
2721                 if (op_code == WSC_MSG)
2722                         return WPS_PENDING;
2723         } else if (wps->wps->wps_upnp && wps->ext_reg && op_code == WSC_MSG) {
2724                 wpa_printf(MSG_DEBUG, "WPS: Skip internal processing - using "
2725                            "external Registrar");
2726                 return WPS_CONTINUE;
2727         }
2728 #endif /* CONFIG_WPS_UPNP */
2729
2730         switch (op_code) {
2731         case WSC_MSG:
2732                 return wps_process_wsc_msg(wps, msg);
2733         case WSC_ACK:
2734                 return wps_process_wsc_ack(wps, msg);
2735         case WSC_NACK:
2736                 return wps_process_wsc_nack(wps, msg);
2737         case WSC_Done:
2738                 ret = wps_process_wsc_done(wps, msg);
2739                 if (ret == WPS_FAILURE) {
2740                         wps->state = SEND_WSC_NACK;
2741                         wps_fail_event(wps->wps, WPS_WSC_DONE);
2742                 }
2743                 return ret;
2744         default:
2745                 wpa_printf(MSG_DEBUG, "WPS: Unsupported op_code %d", op_code);
2746                 return WPS_FAILURE;
2747         }
2748 }
2749
2750
2751 int wps_registrar_update_ie(struct wps_registrar *reg)
2752 {
2753         return wps_set_ie(reg);
2754 }
2755
2756
2757 static void wps_registrar_set_selected_timeout(void *eloop_ctx,
2758                                                void *timeout_ctx)
2759 {
2760         struct wps_registrar *reg = eloop_ctx;
2761
2762         wpa_printf(MSG_DEBUG, "WPS: Selected Registrar timeout - "
2763                    "unselect internal Registrar");
2764         reg->selected_registrar = 0;
2765         reg->pbc = 0;
2766         wps_registrar_selected_registrar_changed(reg);
2767 }
2768
2769
2770 #ifdef CONFIG_WPS_UPNP
2771 static void wps_registrar_sel_reg_add(struct wps_registrar *reg,
2772                                       struct subscription *s)
2773 {
2774         wpa_printf(MSG_DEBUG, "WPS: External Registrar selected (dev_pw_id=%d "
2775                    "config_methods=0x%x)",
2776                    s->dev_password_id, s->config_methods);
2777         reg->sel_reg_union = 1;
2778         if (reg->sel_reg_dev_password_id_override != DEV_PW_PUSHBUTTON)
2779                 reg->sel_reg_dev_password_id_override = s->dev_password_id;
2780         if (reg->sel_reg_config_methods_override == -1)
2781                 reg->sel_reg_config_methods_override = 0;
2782         reg->sel_reg_config_methods_override |= s->config_methods;
2783 }
2784 #endif /* CONFIG_WPS_UPNP */
2785
2786
2787 static void wps_registrar_sel_reg_union(struct wps_registrar *reg)
2788 {
2789 #ifdef CONFIG_WPS_UPNP
2790         struct subscription *s;
2791
2792         if (reg->wps->wps_upnp == NULL)
2793                 return;
2794
2795         dl_list_for_each(s, &reg->wps->wps_upnp->subscriptions,
2796                          struct subscription, list) {
2797                 struct subscr_addr *sa;
2798                 sa = dl_list_first(&s->addr_list, struct subscr_addr, list);
2799                 if (sa) {
2800                         wpa_printf(MSG_DEBUG, "WPS: External Registrar %s:%d",
2801                                    inet_ntoa(sa->saddr.sin_addr),
2802                                    ntohs(sa->saddr.sin_port));
2803                 }
2804                 if (s->selected_registrar)
2805                         wps_registrar_sel_reg_add(reg, s);
2806                 else
2807                         wpa_printf(MSG_DEBUG, "WPS: External Registrar not "
2808                                    "selected");
2809         }
2810 #endif /* CONFIG_WPS_UPNP */
2811 }
2812
2813
2814 /**
2815  * wps_registrar_selected_registrar_changed - SetSelectedRegistrar change
2816  * @reg: Registrar data from wps_registrar_init()
2817  *
2818  * This function is called when selected registrar state changes, e.g., when an
2819  * AP receives a SetSelectedRegistrar UPnP message.
2820  */
2821 void wps_registrar_selected_registrar_changed(struct wps_registrar *reg)
2822 {
2823         wpa_printf(MSG_DEBUG, "WPS: Selected registrar information changed");
2824
2825         reg->sel_reg_union = reg->selected_registrar;
2826         reg->sel_reg_dev_password_id_override = -1;
2827         reg->sel_reg_config_methods_override = -1;
2828         if (reg->selected_registrar) {
2829                 reg->sel_reg_config_methods_override =
2830                         reg->wps->config_methods & ~WPS_CONFIG_PUSHBUTTON;
2831                 if (reg->pbc) {
2832                         reg->sel_reg_dev_password_id_override =
2833                                 DEV_PW_PUSHBUTTON;
2834                         reg->sel_reg_config_methods_override |=
2835                                 WPS_CONFIG_PUSHBUTTON;
2836                 }
2837                 wpa_printf(MSG_DEBUG, "WPS: Internal Registrar selected "
2838                            "(pbc=%d)", reg->pbc);
2839         } else
2840                 wpa_printf(MSG_DEBUG, "WPS: Internal Registrar not selected");
2841
2842         wps_registrar_sel_reg_union(reg);
2843
2844         wps_set_ie(reg);
2845         wps_cb_set_sel_reg(reg);
2846 }
2847
2848
2849 int wps_registrar_get_info(struct wps_registrar *reg, const u8 *addr,
2850                            char *buf, size_t buflen)
2851 {
2852         struct wps_registrar_device *d;
2853         int len = 0, ret;
2854         char uuid[40];
2855         char devtype[WPS_DEV_TYPE_BUFSIZE];
2856
2857         d = wps_device_get(reg, addr);
2858         if (d == NULL)
2859                 return 0;
2860         if (uuid_bin2str(d->uuid, uuid, sizeof(uuid)))
2861                 return 0;
2862
2863         ret = os_snprintf(buf + len, buflen - len,
2864                           "wpsUuid=%s\n"
2865                           "wpsPrimaryDeviceType=%s\n"
2866                           "wpsDeviceName=%s\n"
2867                           "wpsManufacturer=%s\n"
2868                           "wpsModelName=%s\n"
2869                           "wpsModelNumber=%s\n"
2870                           "wpsSerialNumber=%s\n",
2871                           uuid,
2872                           wps_dev_type_bin2str(d->dev.pri_dev_type, devtype,
2873                                                sizeof(devtype)),
2874                           d->dev.device_name ? d->dev.device_name : "",
2875                           d->dev.manufacturer ? d->dev.manufacturer : "",
2876                           d->dev.model_name ? d->dev.model_name : "",
2877                           d->dev.model_number ? d->dev.model_number : "",
2878                           d->dev.serial_number ? d->dev.serial_number : "");
2879         if (ret < 0 || (size_t) ret >= buflen - len)
2880                 return len;
2881         len += ret;
2882
2883         return len;
2884 }