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