1526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt/*
2526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt * WPA Supplicant - test code for pre-authentication
3526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt * Copyright (c) 2003-2007, Jouni Malinen <j@w1.fi>
4526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt *
5526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt * This program is free software; you can redistribute it and/or modify
6526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt * it under the terms of the GNU General Public License version 2 as
7526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt * published by the Free Software Foundation.
8526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt *
9526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt * Alternatively, this software may be distributed under the terms of BSD
10526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt * license.
11526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt *
12526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt * See README and COPYING for more details.
13526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt *
14526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt * IEEE 802.1X Supplicant test code (to be used in place of wpa_supplicant.c.
15526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt * Not used in production version.
16526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt */
17526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
18526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "includes.h"
19526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include <assert.h>
20526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
21526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "common.h"
22526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "config.h"
23526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "eapol_supp/eapol_supp_sm.h"
24526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "eloop.h"
25526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "wpa.h"
26526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "eap_peer/eap.h"
27526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "wpa_supplicant_i.h"
28526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "l2_packet/l2_packet.h"
29526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "ctrl_iface.h"
30526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "pcsc_funcs.h"
31526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "preauth.h"
32526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt#include "pmksa_cache.h"
33526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
34526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
35526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtextern int wpa_debug_level;
36526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtextern int wpa_debug_show_keys;
37526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
38526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstruct wpa_driver_ops *wpa_supplicant_drivers[] = { NULL };
39526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
40526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
41526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstruct preauth_test_data {
42526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	int auth_timed_out;
43526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt};
44526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
45526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
46526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic void _wpa_supplicant_disassociate(void *wpa_s, int reason_code)
47526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
48526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_supplicant_disassociate(wpa_s, reason_code);
49526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
50526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
51526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
52526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic void _wpa_supplicant_deauthenticate(void *wpa_s, int reason_code)
53526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
54526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_supplicant_deauthenticate(wpa_s, reason_code);
55526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
56526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
57526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
58526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic u8 * wpa_alloc_eapol(const struct wpa_supplicant *wpa_s, u8 type,
59526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt			    const void *data, u16 data_len,
60526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt			    size_t *msg_len, void **data_pos)
61526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
62526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct ieee802_1x_hdr *hdr;
63526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
64526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	*msg_len = sizeof(*hdr) + data_len;
65526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	hdr = os_malloc(*msg_len);
66526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (hdr == NULL)
67526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		return NULL;
68526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
69526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	hdr->version = wpa_s->conf->eapol_version;
70526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	hdr->type = type;
71526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	hdr->length = htons(data_len);
72526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
73526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (data)
74526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		os_memcpy(hdr + 1, data, data_len);
75526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	else
76526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		os_memset(hdr + 1, 0, data_len);
77526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
78526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (data_pos)
79526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		*data_pos = hdr + 1;
80526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
81526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return (u8 *) hdr;
82526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
83526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
84526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
85526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic u8 * _wpa_alloc_eapol(void *wpa_s, u8 type,
86526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt			     const void *data, u16 data_len,
87526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt			     size_t *msg_len, void **data_pos)
88526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
89526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return wpa_alloc_eapol(wpa_s, type, data, data_len, msg_len, data_pos);
90526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
91526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
92526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
93526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic void _wpa_supplicant_set_state(void *ctx, wpa_states state)
94526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
95526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct wpa_supplicant *wpa_s = ctx;
96526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_s->wpa_state = state;
97526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
98526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
99526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
100526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic wpa_states _wpa_supplicant_get_state(void *ctx)
101526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
102526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct wpa_supplicant *wpa_s = ctx;
103526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return wpa_s->wpa_state;
104526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
105526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
106526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
107526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic int wpa_ether_send(void *wpa_s, const u8 *dest, u16 proto,
108526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt			  const u8 *buf, size_t len)
109526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
110526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	printf("%s - not implemented\n", __func__);
111526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return -1;
112526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
113526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
114526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
115526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic void * wpa_supplicant_get_network_ctx(void *wpa_s)
116526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
117526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return wpa_supplicant_get_ssid(wpa_s);
118526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
119526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
120526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
121526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic void _wpa_supplicant_cancel_auth_timeout(void *wpa_s)
122526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
123526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_supplicant_cancel_auth_timeout(wpa_s);
124526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
125526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
126526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
127526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic int wpa_supplicant_get_beacon_ie(void *wpa_s)
128526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
129526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	printf("%s - not implemented\n", __func__);
130526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return -1;
131526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
132526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
133526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
134526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic int wpa_supplicant_get_bssid(void *wpa_s, u8 *bssid)
135526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
136526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	printf("%s - not implemented\n", __func__);
137526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return -1;
138526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
139526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
140526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
141526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic int wpa_supplicant_set_key(void *wpa_s, wpa_alg alg,
142526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt				  const u8 *addr, int key_idx, int set_tx,
143526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt				  const u8 *seq, size_t seq_len,
144526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt				  const u8 *key, size_t key_len)
145526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
146526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	printf("%s - not implemented\n", __func__);
147526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return -1;
148526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
149526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
150526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
151526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic int wpa_supplicant_mlme_setprotection(void *wpa_s, const u8 *addr,
152526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt					     int protection_type,
153526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt					     int key_type)
154526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
155526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	printf("%s - not implemented\n", __func__);
156526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return -1;
157526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
158526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
159526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
160526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic int wpa_supplicant_add_pmkid(void *wpa_s,
161526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt				    const u8 *bssid, const u8 *pmkid)
162526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
163526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	printf("%s - not implemented\n", __func__);
164526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return -1;
165526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
166526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
167526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
168526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic int wpa_supplicant_remove_pmkid(void *wpa_s,
169526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt				       const u8 *bssid, const u8 *pmkid)
170526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
171526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	printf("%s - not implemented\n", __func__);
172526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return -1;
173526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
174526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
175526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
176526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic void wpa_supplicant_set_config_blob(void *ctx,
177526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt					   struct wpa_config_blob *blob)
178526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
179526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct wpa_supplicant *wpa_s = ctx;
180526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_config_set_blob(wpa_s->conf, blob);
181526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
182526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
183526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
184526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic const struct wpa_config_blob *
185526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtwpa_supplicant_get_config_blob(void *ctx, const char *name)
186526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
187526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct wpa_supplicant *wpa_s = ctx;
188526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return wpa_config_get_blob(wpa_s->conf, name);
189526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
190526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
191526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
192526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic void test_eapol_clean(struct wpa_supplicant *wpa_s)
193526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
194526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	rsn_preauth_deinit(wpa_s->wpa);
195526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	pmksa_candidate_free(wpa_s->wpa);
196526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_sm_deinit(wpa_s->wpa);
197526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	scard_deinit(wpa_s->scard);
198526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (wpa_s->ctrl_iface) {
199526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		wpa_supplicant_ctrl_iface_deinit(wpa_s->ctrl_iface);
200526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		wpa_s->ctrl_iface = NULL;
201526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	}
202526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_config_free(wpa_s->conf);
203526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
204526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
205526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
206526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic void eapol_test_timeout(void *eloop_ctx, void *timeout_ctx)
207526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
208526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct preauth_test_data *p = eloop_ctx;
209526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	printf("EAPOL test timed out\n");
210526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	p->auth_timed_out = 1;
211526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	eloop_terminate();
212526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
213526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
214526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
215526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic void eapol_test_poll(void *eloop_ctx, void *timeout_ctx)
216526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
217526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct wpa_supplicant *wpa_s = eloop_ctx;
218526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (!rsn_preauth_in_progress(wpa_s->wpa))
219526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		eloop_terminate();
220526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	else {
221526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		eloop_register_timeout(0, 100000, eapol_test_poll, eloop_ctx,
222526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt				       timeout_ctx);
223526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	}
224526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
225526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
226526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
227526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic struct wpa_driver_ops dummy_driver;
228526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
229526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
230526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic void wpa_init_conf(struct wpa_supplicant *wpa_s, const char *ifname)
231526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
232526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct l2_packet_data *l2;
233526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct wpa_sm_ctx *ctx;
234526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
235526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	os_memset(&dummy_driver, 0, sizeof(dummy_driver));
236526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_s->driver = &dummy_driver;
237526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
238526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx = os_zalloc(sizeof(*ctx));
239526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	assert(ctx != NULL);
240526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
241526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->ctx = wpa_s;
242526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->set_state = _wpa_supplicant_set_state;
243526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->get_state = _wpa_supplicant_get_state;
244526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->deauthenticate = _wpa_supplicant_deauthenticate;
245526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->disassociate = _wpa_supplicant_disassociate;
246526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->set_key = wpa_supplicant_set_key;
247526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->get_network_ctx = wpa_supplicant_get_network_ctx;
248526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->get_bssid = wpa_supplicant_get_bssid;
249526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->ether_send = wpa_ether_send;
250526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->get_beacon_ie = wpa_supplicant_get_beacon_ie;
251526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->alloc_eapol = _wpa_alloc_eapol;
252526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->cancel_auth_timeout = _wpa_supplicant_cancel_auth_timeout;
253526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->add_pmkid = wpa_supplicant_add_pmkid;
254526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->remove_pmkid = wpa_supplicant_remove_pmkid;
255526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->set_config_blob = wpa_supplicant_set_config_blob;
256526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->get_config_blob = wpa_supplicant_get_config_blob;
257526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	ctx->mlme_setprotection = wpa_supplicant_mlme_setprotection;
258526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
259526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_s->wpa = wpa_sm_init(ctx);
260526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	assert(wpa_s->wpa != NULL);
261526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_sm_set_param(wpa_s->wpa, WPA_PARAM_PROTO, WPA_PROTO_RSN);
262526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
263526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	os_strlcpy(wpa_s->ifname, ifname, sizeof(wpa_s->ifname));
264526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_sm_set_ifname(wpa_s->wpa, wpa_s->ifname, NULL);
265526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
266526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	l2 = l2_packet_init(wpa_s->ifname, NULL, ETH_P_RSN_PREAUTH, NULL,
267526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt			    NULL, 0);
268526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	assert(l2 != NULL);
269526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (l2_packet_get_own_addr(l2, wpa_s->own_addr)) {
270526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		wpa_printf(MSG_WARNING, "Failed to get own L2 address\n");
271526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		exit(-1);
272526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	}
273526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	l2_packet_deinit(l2);
274526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_sm_set_own_addr(wpa_s->wpa, wpa_s->own_addr);
275526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
276526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
277526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
278526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtstatic void eapol_test_terminate(int sig, void *eloop_ctx,
279526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt				 void *signal_ctx)
280526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
281526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct wpa_supplicant *wpa_s = eloop_ctx;
282526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_msg(wpa_s, MSG_INFO, "Signal %d received - terminating", sig);
283526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	eloop_terminate();
284526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
285526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
286526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
287526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidtint main(int argc, char *argv[])
288526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt{
289526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct wpa_supplicant wpa_s;
290526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	int ret = 1;
291526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	u8 bssid[ETH_ALEN];
292526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	struct preauth_test_data preauth_test;
293526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
294526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (os_program_init())
295526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		return -1;
296526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
297526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	os_memset(&preauth_test, 0, sizeof(preauth_test));
298526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
299526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_debug_level = 0;
300526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_debug_show_keys = 1;
301526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
302526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (argc != 4) {
303526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		printf("usage: preauth_test <conf> <target MAC address> "
304526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		       "<ifname>\n");
305526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		return -1;
306526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	}
307526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
308526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (hwaddr_aton(argv[2], bssid)) {
309526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		printf("Failed to parse target address '%s'.\n", argv[2]);
310526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		return -1;
311526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	}
312526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
313526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (eap_peer_register_methods()) {
314526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		wpa_printf(MSG_ERROR, "Failed to register EAP methods");
315526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		return -1;
316526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	}
317526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
318526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (eloop_init(&wpa_s)) {
319526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		wpa_printf(MSG_ERROR, "Failed to initialize event loop");
320526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		return -1;
321526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	}
322526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
323526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	os_memset(&wpa_s, 0, sizeof(wpa_s));
324526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_s.conf = wpa_config_read(argv[1]);
325526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (wpa_s.conf == NULL) {
326526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		printf("Failed to parse configuration file '%s'.\n", argv[1]);
327526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		return -1;
328526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	}
329526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (wpa_s.conf->ssid == NULL) {
330526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		printf("No networks defined.\n");
331526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		return -1;
332526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	}
333526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
334526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_init_conf(&wpa_s, argv[3]);
335526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	wpa_s.ctrl_iface = wpa_supplicant_ctrl_iface_init(&wpa_s);
336526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (wpa_s.ctrl_iface == NULL) {
337526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		printf("Failed to initialize control interface '%s'.\n"
338526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		       "You may have another preauth_test process already "
339526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		       "running or the file was\n"
340526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		       "left by an unclean termination of preauth_test in "
341526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		       "which case you will need\n"
342526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		       "to manually remove this file before starting "
343526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		       "preauth_test again.\n",
344526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		       wpa_s.conf->ctrl_interface);
345526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		return -1;
346526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	}
347526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (wpa_supplicant_scard_init(&wpa_s, wpa_s.conf->ssid))
348526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		return -1;
349526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
350526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (rsn_preauth_init(wpa_s.wpa, bssid, &wpa_s.conf->ssid->eap))
351526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		return -1;
352526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
353526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	eloop_register_timeout(30, 0, eapol_test_timeout, &preauth_test, NULL);
354526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	eloop_register_timeout(0, 100000, eapol_test_poll, &wpa_s, NULL);
355526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	eloop_register_signal_terminate(eapol_test_terminate, NULL);
356526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	eloop_register_signal_reconfig(eapol_test_terminate, NULL);
357526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	eloop_run();
358526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
359526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	if (preauth_test.auth_timed_out)
360526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		ret = -2;
361526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	else {
362526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt		ret = pmksa_cache_set_current(wpa_s.wpa, NULL, bssid, NULL, 0)
363526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt			? 0 : -3;
364526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	}
365526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
366526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	test_eapol_clean(&wpa_s);
367526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
368526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	eap_peer_unregister_methods();
369526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
370526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	eloop_destroy();
371526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
372526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	os_program_deinit();
373526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt
374526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt	return ret;
375526fc2a7dc09b4450086cdec313a5c44d36b10fdDmitry Shmidt}
376