[pkg-wpa-devel] r1266 - in /wpasupplicant/branches/upstream/current: patches/ src/common/ src/crypto/ src/drivers/ src/eap_common/ src/eap_peer/ src/eap_server/ src/rsn_supp/ src/tls/ wpa_supplicant/ wpa_supplicant/doc/docbook/ wpa_supplicant/wpa_gui-qt4/ wpa_supplicant/wpa_gui-qt4/icons/

kelmo-guest at users.alioth.debian.org kelmo-guest at users.alioth.debian.org
Wed Oct 8 21:24:05 UTC 2008


Author: kelmo-guest
Date: Wed Oct  8 21:24:04 2008
New Revision: 1266

URL: http://svn.debian.org/wsvn/?sc=1&rev=1266
Log:
[svn-upgrade] Integrating new upstream version, wpasupplicant (0.6.5~git.20081008.gb43f7c3)

Added:
    wpasupplicant/branches/upstream/current/patches/openssl-0.9.8i-tls-extensions.patch
    wpasupplicant/branches/upstream/current/src/drivers/radiotap.c
    wpasupplicant/branches/upstream/current/src/drivers/radiotap.h
    wpasupplicant/branches/upstream/current/src/drivers/radiotap_iter.h
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons.qrc
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/Makefile
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/README
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/wpa_gui.svg
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpa_gui.desktop
Removed:
    wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_background.8
    wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_cli.8
    wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_gui.8
    wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_passphrase.8
    wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_priv.8
    wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_supplicant.8
    wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_supplicant.conf.5
Modified:
    wpasupplicant/branches/upstream/current/patches/openssl-0.9.9-session-ticket.patch
    wpasupplicant/branches/upstream/current/src/common/defs.h
    wpasupplicant/branches/upstream/current/src/common/ieee802_11_defs.h
    wpasupplicant/branches/upstream/current/src/common/privsep_commands.h
    wpasupplicant/branches/upstream/current/src/common/wpa_common.c
    wpasupplicant/branches/upstream/current/src/common/wpa_common.h
    wpasupplicant/branches/upstream/current/src/crypto/tls_internal.c
    wpasupplicant/branches/upstream/current/src/drivers/driver.h
    wpasupplicant/branches/upstream/current/src/drivers/driver_ndis.c
    wpasupplicant/branches/upstream/current/src/drivers/driver_nl80211.c
    wpasupplicant/branches/upstream/current/src/drivers/driver_privsep.c
    wpasupplicant/branches/upstream/current/src/drivers/driver_ralink.c
    wpasupplicant/branches/upstream/current/src/drivers/driver_test.c
    wpasupplicant/branches/upstream/current/src/drivers/driver_wext.c
    wpasupplicant/branches/upstream/current/src/eap_common/eap_defs.h
    wpasupplicant/branches/upstream/current/src/eap_common/eap_gpsk_common.c
    wpasupplicant/branches/upstream/current/src/eap_common/eap_ttls.h
    wpasupplicant/branches/upstream/current/src/eap_peer/eap_config.h
    wpasupplicant/branches/upstream/current/src/eap_peer/eap_fast.c
    wpasupplicant/branches/upstream/current/src/eap_peer/eap_fast_pac.c
    wpasupplicant/branches/upstream/current/src/eap_peer/eap_gpsk.c
    wpasupplicant/branches/upstream/current/src/eap_peer/eap_ttls.c
    wpasupplicant/branches/upstream/current/src/eap_peer/tncc.c
    wpasupplicant/branches/upstream/current/src/eap_server/eap_fast.c
    wpasupplicant/branches/upstream/current/src/eap_server/eap_ttls.c
    wpasupplicant/branches/upstream/current/src/rsn_supp/peerkey.c
    wpasupplicant/branches/upstream/current/src/rsn_supp/peerkey.h
    wpasupplicant/branches/upstream/current/src/rsn_supp/pmksa_cache.c
    wpasupplicant/branches/upstream/current/src/rsn_supp/pmksa_cache.h
    wpasupplicant/branches/upstream/current/src/rsn_supp/preauth.c
    wpasupplicant/branches/upstream/current/src/rsn_supp/wpa.c
    wpasupplicant/branches/upstream/current/src/rsn_supp/wpa_ft.c
    wpasupplicant/branches/upstream/current/src/rsn_supp/wpa_ie.c
    wpasupplicant/branches/upstream/current/src/tls/tlsv1_client_read.c
    wpasupplicant/branches/upstream/current/src/tls/x509v3.c
    wpasupplicant/branches/upstream/current/wpa_supplicant/ChangeLog
    wpasupplicant/branches/upstream/current/wpa_supplicant/Makefile
    wpasupplicant/branches/upstream/current/wpa_supplicant/config.c
    wpasupplicant/branches/upstream/current/wpa_supplicant/config_file.c
    wpasupplicant/branches/upstream/current/wpa_supplicant/config_winreg.c
    wpasupplicant/branches/upstream/current/wpa_supplicant/ctrl_iface.c
    wpasupplicant/branches/upstream/current/wpa_supplicant/defconfig
    wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_gui.sgml
    wpasupplicant/branches/upstream/current/wpa_supplicant/events.c
    wpasupplicant/branches/upstream/current/wpa_supplicant/main_winsvc.c
    wpasupplicant/branches/upstream/current/wpa_supplicant/mlme.c
    wpasupplicant/branches/upstream/current/wpa_supplicant/scan.c
    wpasupplicant/branches/upstream/current/wpa_supplicant/win_example.reg
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/.gitignore
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/eventhistory.ui
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/main.cpp
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.cpp
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.h
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.ui
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/scanresults.ui
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/userdatarequest.ui
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpa_gui.pro
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.cpp
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.h
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.ui
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_priv.c
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant.c
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant.conf
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant_i.h
    wpasupplicant/branches/upstream/current/wpa_supplicant/wpas_glue.c

Added: wpasupplicant/branches/upstream/current/patches/openssl-0.9.8i-tls-extensions.patch
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/patches/openssl-0.9.8i-tls-extensions.patch?rev=1266&op=file
==============================================================================
--- wpasupplicant/branches/upstream/current/patches/openssl-0.9.8i-tls-extensions.patch (added)
+++ wpasupplicant/branches/upstream/current/patches/openssl-0.9.8i-tls-extensions.patch Wed Oct  8 21:24:04 2008
@@ -1,0 +1,344 @@
+This patch adds support for TLS SessionTicket extension (RFC 5077) for
+the parts used by EAP-FAST (RFC 4851).
+
+This is based on the patch from Alexey Kobozev <akobozev at cisco.com>
+(sent to openssl-dev mailing list on Tue, 07 Jun 2005 15:40:58 +0300).
+
+OpenSSL 0.9.8i does not enable TLS extension support by default, so it
+will need to be enabled by adding enable-tlsext to config script
+command line.
+
+
+diff -upr openssl-0.9.8i.orig/ssl/s3_clnt.c openssl-0.9.8i/ssl/s3_clnt.c
+--- openssl-0.9.8i.orig/ssl/s3_clnt.c	2008-06-16 19:56:41.000000000 +0300
++++ openssl-0.9.8i/ssl/s3_clnt.c	2008-09-28 16:50:18.000000000 +0300
+@@ -759,6 +759,20 @@ int ssl3_get_server_hello(SSL *s)
+ 		goto f_err;
+ 		}
+ 
++#ifndef OPENSSL_NO_TLSEXT
++	/* check if we want to resume the session based on external pre-shared secret */
++	if (s->version >= TLS1_VERSION && s->tls_session_secret_cb)
++	{
++		SSL_CIPHER *pref_cipher=NULL;
++		s->session->master_key_length=sizeof(s->session->master_key);
++		if (s->tls_session_secret_cb(s, s->session->master_key, &s->session->master_key_length,
++			NULL, &pref_cipher, s->tls_session_secret_cb_arg))
++		{
++			s->session->cipher=pref_cipher ? pref_cipher : ssl_get_cipher_by_char(s,p+j);
++		}
++	}
++#endif /* OPENSSL_NO_TLSEXT */
++
+ 	if (j != 0 && j == s->session->session_id_length
+ 	    && memcmp(p,s->session->session_id,j) == 0)
+ 	    {
+@@ -2701,11 +2715,8 @@ static int ssl3_check_finished(SSL *s)
+ 	{
+ 	int ok;
+ 	long n;
+-	/* If we have no ticket or session ID is non-zero length (a match of
+-	 * a non-zero session length would never reach here) it cannot be a
+-	 * resumed session.
+-	 */
+-	if (!s->session->tlsext_tick || s->session->session_id_length)
++	/* If we have no ticket it cannot be a resumed session. */
++	if (!s->session->tlsext_tick)
+ 		return 1;
+ 	/* this function is called when we really expect a Certificate
+ 	 * message, so permit appropriate message length */
+diff -upr openssl-0.9.8i.orig/ssl/s3_srvr.c openssl-0.9.8i/ssl/s3_srvr.c
+--- openssl-0.9.8i.orig/ssl/s3_srvr.c	2008-09-14 21:16:09.000000000 +0300
++++ openssl-0.9.8i/ssl/s3_srvr.c	2008-09-28 16:50:18.000000000 +0300
+@@ -959,6 +959,59 @@ int ssl3_get_client_hello(SSL *s)
+ 			SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO,SSL_R_CLIENTHELLO_TLSEXT);
+ 			goto err;
+ 		}
++
++	/* Check if we want to use external pre-shared secret for this
++	 * handshake for not reused session only. We need to generate
++	 * server_random before calling tls_session_secret_cb in order to allow
++	 * SessionTicket processing to use it in key derivation. */
++	{
++		unsigned long Time;
++		unsigned char *pos;
++		Time=(unsigned long)time(NULL);			/* Time */
++		pos=s->s3->server_random;
++		l2n(Time,pos);
++		if (RAND_pseudo_bytes(pos,SSL3_RANDOM_SIZE-4) <= 0)
++		{
++			al=SSL_AD_INTERNAL_ERROR;
++			goto f_err;
++		}
++	}
++
++	if (!s->hit && s->version >= TLS1_VERSION && s->tls_session_secret_cb)
++	{
++		SSL_CIPHER *pref_cipher=NULL;
++
++		s->session->master_key_length=sizeof(s->session->master_key);
++		if(s->tls_session_secret_cb(s, s->session->master_key, &s->session->master_key_length, 
++			ciphers, &pref_cipher, s->tls_session_secret_cb_arg))
++		{
++			s->hit=1;
++			s->session->ciphers=ciphers;
++			s->session->verify_result=X509_V_OK;
++			
++			ciphers=NULL;
++			
++			/* check if some cipher was preferred by call back */
++			pref_cipher=pref_cipher ? pref_cipher : ssl3_choose_cipher(s, s->session->ciphers, SSL_get_ciphers(s));
++			if (pref_cipher == NULL)
++				{
++				al=SSL_AD_HANDSHAKE_FAILURE;
++				SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO,SSL_R_NO_SHARED_CIPHER);
++				goto f_err;
++				}
++
++			s->session->cipher=pref_cipher;
++
++			if (s->cipher_list)
++				sk_SSL_CIPHER_free(s->cipher_list);
++
++			if (s->cipher_list_by_id)
++				sk_SSL_CIPHER_free(s->cipher_list_by_id);
++
++			s->cipher_list = sk_SSL_CIPHER_dup(s->session->ciphers);
++			s->cipher_list_by_id = sk_SSL_CIPHER_dup(s->session->ciphers);
++		}
++	}
+ #endif
+ 	/* Worst case, we will use the NULL compression, but if we have other
+ 	 * options, we will now look for them.  We have i-1 compression
+@@ -1097,16 +1150,22 @@ int ssl3_send_server_hello(SSL *s)
+ 	unsigned char *buf;
+ 	unsigned char *p,*d;
+ 	int i,sl;
+-	unsigned long l,Time;
++	unsigned long l;
++#ifdef OPENSSL_NO_TLSEXT
++	unsigned long Time;
++#endif
+ 
+ 	if (s->state == SSL3_ST_SW_SRVR_HELLO_A)
+ 		{
+ 		buf=(unsigned char *)s->init_buf->data;
++#ifdef OPENSSL_NO_TLSEXT
+ 		p=s->s3->server_random;
++		/* Generate server_random if it was not needed previously */
+ 		Time=(unsigned long)time(NULL);			/* Time */
+ 		l2n(Time,p);
+ 		if (RAND_pseudo_bytes(p,SSL3_RANDOM_SIZE-4) <= 0)
+ 			return -1;
++#endif
+ 		/* Do the message type and length last */
+ 		d=p= &(buf[4]);
+ 
+diff -upr openssl-0.9.8i.orig/ssl/ssl_err.c openssl-0.9.8i/ssl/ssl_err.c
+--- openssl-0.9.8i.orig/ssl/ssl_err.c	2008-08-13 22:44:44.000000000 +0300
++++ openssl-0.9.8i/ssl/ssl_err.c	2008-09-28 16:50:18.000000000 +0300
+@@ -253,6 +253,7 @@ static ERR_STRING_DATA SSL_str_functs[]=
+ {ERR_FUNC(SSL_F_TLS1_ENC),	"TLS1_ENC"},
+ {ERR_FUNC(SSL_F_TLS1_SETUP_KEY_BLOCK),	"TLS1_SETUP_KEY_BLOCK"},
+ {ERR_FUNC(SSL_F_WRITE_PENDING),	"WRITE_PENDING"},
++{ERR_FUNC(SSL_F_SSL_SET_HELLO_EXTENSION), "SSL_set_hello_extension"},
+ {0,NULL}
+ 	};
+ 
+diff -upr openssl-0.9.8i.orig/ssl/ssl.h openssl-0.9.8i/ssl/ssl.h
+--- openssl-0.9.8i.orig/ssl/ssl.h	2008-08-13 22:44:44.000000000 +0300
++++ openssl-0.9.8i/ssl/ssl.h	2008-09-28 16:50:18.000000000 +0300
+@@ -344,6 +344,7 @@ extern "C" {
+  * 'struct ssl_st *' function parameters used to prototype callbacks
+  * in SSL_CTX. */
+ typedef struct ssl_st *ssl_crock_st;
++typedef struct tls_extension_st TLS_EXTENSION;
+ 
+ /* used to hold info on the particular ciphers used */
+ typedef struct ssl_cipher_st
+@@ -362,6 +363,8 @@ typedef struct ssl_cipher_st
+ 
+ DECLARE_STACK_OF(SSL_CIPHER)
+ 
++typedef int (*tls_session_secret_cb_fn)(SSL *s, void *secret, int *secret_len, STACK_OF(SSL_CIPHER) *peer_ciphers, SSL_CIPHER **cipher, void *arg);
++
+ /* Used to hold functions for SSLv2 or SSLv3/TLSv1 functions */
+ typedef struct ssl_method_st
+ 	{
+@@ -1034,6 +1037,14 @@ struct ssl_st
+ 
+ 	/* RFC4507 session ticket expected to be received or sent */
+ 	int tlsext_ticket_expected;
++
++	/* TLS extensions */
++	TLS_EXTENSION *tls_extension;
++
++	/* TLS pre-shared secret session resumption */
++	tls_session_secret_cb_fn tls_session_secret_cb;
++	void *tls_session_secret_cb_arg;
++
+ 	SSL_CTX * initial_ctx; /* initial ctx, used to store sessions */
+ #define session_ctx initial_ctx
+ #else
+@@ -1632,6 +1643,12 @@ void *SSL_COMP_get_compression_methods(v
+ int SSL_COMP_add_compression_method(int id,void *cm);
+ #endif
+ 
++/* TLS extensions functions */
++int SSL_set_hello_extension(SSL *s, int ext_type, void *ext_data, int ext_len);
++
++/* Pre-shared secret session resumption functions */
++int SSL_set_session_secret_cb(SSL *s, tls_session_secret_cb_fn tls_session_secret_cb, void *arg);
++
+ /* BEGIN ERROR CODES */
+ /* The following lines are auto generated by the script mkerr.pl. Any changes
+  * made after this point may be overwritten when the script is next run.
+@@ -1824,6 +1841,7 @@ void ERR_load_SSL_strings(void);
+ #define SSL_F_TLS1_ENC					 210
+ #define SSL_F_TLS1_SETUP_KEY_BLOCK			 211
+ #define SSL_F_WRITE_PENDING				 212
++#define SSL_F_SSL_SET_HELLO_EXTENSION			 213
+ 
+ /* Reason codes. */
+ #define SSL_R_APP_DATA_IN_HANDSHAKE			 100
+diff -upr openssl-0.9.8i.orig/ssl/ssl_sess.c openssl-0.9.8i/ssl/ssl_sess.c
+--- openssl-0.9.8i.orig/ssl/ssl_sess.c	2008-06-04 21:35:27.000000000 +0300
++++ openssl-0.9.8i/ssl/ssl_sess.c	2008-09-28 16:50:18.000000000 +0300
+@@ -707,6 +707,52 @@ long SSL_CTX_get_timeout(const SSL_CTX *
+ 	return(s->session_timeout);
+ 	}
+ 
++#ifndef OPENSSL_NO_TLSEXT
++int SSL_set_session_secret_cb(SSL *s, int (*tls_session_secret_cb)(SSL *s, void *secret, int *secret_len, 
++	STACK_OF(SSL_CIPHER) *peer_ciphers, SSL_CIPHER **cipher, void *arg), void *arg)
++{
++	if (s == NULL) return(0);
++	s->tls_session_secret_cb = tls_session_secret_cb;
++	s->tls_session_secret_cb_arg = arg;
++	return(1);
++}
++
++int SSL_set_hello_extension(SSL *s, int ext_type, void *ext_data, int ext_len)
++{
++	if(s->version >= TLS1_VERSION)
++	{
++		if(s->tls_extension)
++		{
++			OPENSSL_free(s->tls_extension);
++			s->tls_extension = NULL;
++		}
++
++		s->tls_extension = OPENSSL_malloc(sizeof(TLS_EXTENSION) + ext_len);
++		if(!s->tls_extension)
++		{
++			SSLerr(SSL_F_SSL_SET_HELLO_EXTENSION, ERR_R_MALLOC_FAILURE);
++			return 0;
++		}
++
++		s->tls_extension->type = ext_type;
++
++		if(ext_data)
++		{
++			s->tls_extension->length = ext_len;
++			s->tls_extension->data = s->tls_extension + 1;
++			memcpy(s->tls_extension->data, ext_data, ext_len);
++		} else {
++			s->tls_extension->length = 0;
++			s->tls_extension->data = NULL;
++		}
++
++		return 1;
++	}
++
++	return 0;
++}
++#endif /* OPENSSL_NO_TLSEXT */
++
+ typedef struct timeout_param_st
+ 	{
+ 	SSL_CTX *ctx;
+diff -upr openssl-0.9.8i.orig/ssl/t1_lib.c openssl-0.9.8i/ssl/t1_lib.c
+--- openssl-0.9.8i.orig/ssl/t1_lib.c	2008-09-04 01:13:04.000000000 +0300
++++ openssl-0.9.8i/ssl/t1_lib.c	2008-09-28 16:50:18.000000000 +0300
+@@ -106,6 +106,12 @@ int tls1_new(SSL *s)
+ 
+ void tls1_free(SSL *s)
+ 	{
++#ifndef OPENSSL_NO_TLSEXT
++	if(s->tls_extension)
++	{
++		OPENSSL_free(s->tls_extension);
++	}
++#endif
+ 	ssl3_free(s);
+ 	}
+ 
+@@ -175,8 +181,24 @@ unsigned char *ssl_add_clienthello_tlsex
+ 		int ticklen;
+ 		if (s->session && s->session->tlsext_tick)
+ 			ticklen = s->session->tlsext_ticklen;
++		else if (s->session && s->tls_extension &&
++			s->tls_extension->type == TLSEXT_TYPE_session_ticket &&
++			s->tls_extension->data)
++		{
++			ticklen = s->tls_extension->length;
++			s->session->tlsext_tick = OPENSSL_malloc(ticklen);
++			if (!s->session->tlsext_tick)
++				return NULL;
++			memcpy(s->session->tlsext_tick, s->tls_extension->data,
++			       ticklen);
++			s->session->tlsext_ticklen = ticklen;
++		}
+ 		else
+ 			ticklen = 0;
++		if (ticklen == 0 && s->tls_extension &&
++		    s->tls_extension->type == TLSEXT_TYPE_session_ticket &&
++		    s->tls_extension->data == NULL)
++			goto skip_ext;
+ 		/* Check for enough room 2 for extension type, 2 for len
+  		 * rest for ticket
+   		 */
+@@ -190,6 +212,7 @@ unsigned char *ssl_add_clienthello_tlsex
+ 			ret += ticklen;
+ 			}
+ 		}
++		skip_ext:
+ 
+ 	if (s->tlsext_status_type == TLSEXT_STATUSTYPE_ocsp)
+ 		{
+@@ -776,6 +799,8 @@ int tls1_process_ticket(SSL *s, unsigned
+ 				s->tlsext_ticket_expected = 1;
+ 				return 0;	/* Cache miss */
+ 				}
++			if (s->tls_session_secret_cb)
++				return 0;
+ 			return tls_decrypt_ticket(s, p, size, session_id, len,
+ 									ret);
+ 			}
+diff -upr openssl-0.9.8i.orig/ssl/tls1.h openssl-0.9.8i/ssl/tls1.h
+--- openssl-0.9.8i.orig/ssl/tls1.h	2008-04-30 19:11:33.000000000 +0300
++++ openssl-0.9.8i/ssl/tls1.h	2008-09-28 16:50:18.000000000 +0300
+@@ -398,6 +398,14 @@ SSL_CTX_callback_ctrl(ssl,SSL_CTRL_SET_T
+ #define TLS_MD_MASTER_SECRET_CONST    "\x6d\x61\x73\x74\x65\x72\x20\x73\x65\x63\x72\x65\x74"  /*master secret*/
+ #endif
+ 
++/* TLS extension struct */
++struct tls_extension_st
++{
++	unsigned short type;
++	unsigned short length;
++	void *data;
++};
++
+ #ifdef  __cplusplus
+ }
+ #endif
+diff -upr openssl-0.9.8i.orig/util/ssleay.num openssl-0.9.8i/util/ssleay.num
+--- openssl-0.9.8i.orig/util/ssleay.num	2008-06-05 13:57:21.000000000 +0300
++++ openssl-0.9.8i/util/ssleay.num	2008-09-28 16:50:57.000000000 +0300
+@@ -242,3 +242,5 @@ SSL_set_SSL_CTX                         
+ SSL_get_servername                      291	EXIST::FUNCTION:TLSEXT
+ SSL_get_servername_type                 292	EXIST::FUNCTION:TLSEXT
+ SSL_CTX_set_client_cert_engine          293	EXIST::FUNCTION:ENGINE
++SSL_set_hello_extension			305	EXIST::FUNCTION:TLSEXT
++SSL_set_session_secret_cb		306	EXIST::FUNCTION:TLSEXT

Modified: wpasupplicant/branches/upstream/current/patches/openssl-0.9.9-session-ticket.patch
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/patches/openssl-0.9.9-session-ticket.patch?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/patches/openssl-0.9.9-session-ticket.patch (original)
+++ wpasupplicant/branches/upstream/current/patches/openssl-0.9.9-session-ticket.patch Wed Oct  8 21:24:04 2008
@@ -6,10 +6,11 @@
 
 
 
-diff -upr openssl-SNAP-20080528.orig/ssl/s3_clnt.c openssl-SNAP-20080528/ssl/s3_clnt.c
---- openssl-SNAP-20080528.orig/ssl/s3_clnt.c	2008-04-29 21:00:17.000000000 +0300
-+++ openssl-SNAP-20080528/ssl/s3_clnt.c	2008-05-29 10:55:43.000000000 +0300
-@@ -785,6 +785,20 @@ int ssl3_get_server_hello(SSL *s)
+Index: openssl-SNAP-20080928/ssl/s3_clnt.c
+===================================================================
+--- openssl-SNAP-20080928.orig/ssl/s3_clnt.c
++++ openssl-SNAP-20080928/ssl/s3_clnt.c
+@@ -788,6 +788,20 @@ int ssl3_get_server_hello(SSL *s)
  		goto f_err;
  		}
  
@@ -30,7 +31,7 @@
  	if (j != 0 && j == s->session->session_id_length
  	    && memcmp(p,s->session->session_id,j) == 0)
  	    {
-@@ -2918,11 +2932,8 @@ static int ssl3_check_finished(SSL *s)
+@@ -2927,11 +2941,8 @@ static int ssl3_check_finished(SSL *s)
  	{
  	int ok;
  	long n;
@@ -44,10 +45,11 @@
  		return 1;
  	/* this function is called when we really expect a Certificate
  	 * message, so permit appropriate message length */
-diff -upr openssl-SNAP-20080528.orig/ssl/s3_srvr.c openssl-SNAP-20080528/ssl/s3_srvr.c
---- openssl-SNAP-20080528.orig/ssl/s3_srvr.c	2008-04-30 20:00:38.000000000 +0300
-+++ openssl-SNAP-20080528/ssl/s3_srvr.c	2008-05-29 10:49:25.000000000 +0300
-@@ -1004,6 +1004,59 @@ int ssl3_get_client_hello(SSL *s)
+Index: openssl-SNAP-20080928/ssl/s3_srvr.c
+===================================================================
+--- openssl-SNAP-20080928.orig/ssl/s3_srvr.c
++++ openssl-SNAP-20080928/ssl/s3_srvr.c
+@@ -1010,6 +1010,59 @@ int ssl3_get_client_hello(SSL *s)
  			SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO,SSL_R_CLIENTHELLO_TLSEXT);
  			goto err;
  		}
@@ -74,15 +76,15 @@
 +		SSL_CIPHER *pref_cipher=NULL;
 +
 +		s->session->master_key_length=sizeof(s->session->master_key);
-+		if(s->tls_session_secret_cb(s, s->session->master_key, &s->session->master_key_length, 
++		if(s->tls_session_secret_cb(s, s->session->master_key, &s->session->master_key_length,
 +			ciphers, &pref_cipher, s->tls_session_secret_cb_arg))
 +		{
 +			s->hit=1;
 +			s->session->ciphers=ciphers;
 +			s->session->verify_result=X509_V_OK;
-+			
++
 +			ciphers=NULL;
-+			
++
 +			/* check if some cipher was preferred by call back */
 +			pref_cipher=pref_cipher ? pref_cipher : ssl3_choose_cipher(s, s->session->ciphers, SSL_get_ciphers(s));
 +			if (pref_cipher == NULL)
@@ -107,7 +109,7 @@
  #endif
  
  	/* Worst case, we will use the NULL compression, but if we have other
-@@ -1130,16 +1183,22 @@ int ssl3_send_server_hello(SSL *s)
+@@ -1134,16 +1187,22 @@ int ssl3_send_server_hello(SSL *s)
  	unsigned char *buf;
  	unsigned char *p,*d;
  	int i,sl;
@@ -131,65 +133,11 @@
  		/* Do the message type and length last */
  		d=p= &(buf[4]);
  
-diff -upr openssl-SNAP-20080528.orig/ssl/ssl.h openssl-SNAP-20080528/ssl/ssl.h
---- openssl-SNAP-20080528.orig/ssl/ssl.h	2008-05-26 15:00:37.000000000 +0300
-+++ openssl-SNAP-20080528/ssl/ssl.h	2008-05-29 10:49:25.000000000 +0300
-@@ -354,6 +354,7 @@ extern "C" {
-  * 'struct ssl_st *' function parameters used to prototype callbacks
-  * in SSL_CTX. */
- typedef struct ssl_st *ssl_crock_st;
-+typedef struct tls_extension_st TLS_EXTENSION;
- 
- /* used to hold info on the particular ciphers used */
- typedef struct ssl_cipher_st
-@@ -380,6 +381,8 @@ DECLARE_STACK_OF(SSL_CIPHER)
- typedef struct ssl_st SSL;
- typedef struct ssl_ctx_st SSL_CTX;
- 
-+typedef int (*tls_session_secret_cb_fn)(SSL *s, void *secret, int *secret_len, STACK_OF(SSL_CIPHER) *peer_ciphers, SSL_CIPHER **cipher, void *arg);
-+
- /* Used to hold functions for SSLv2 or SSLv3/TLSv1 functions */
- typedef struct ssl_method_st
- 	{
-@@ -1128,6 +1131,13 @@ struct ssl_st
- 	void *tlsext_opaque_prf_input;
- 	size_t tlsext_opaque_prf_input_len;
- 
-+	/* TLS extensions */
-+	TLS_EXTENSION *tls_extension;
-+
-+	/* TLS pre-shared secret session resumption */
-+	tls_session_secret_cb_fn tls_session_secret_cb;
-+	void *tls_session_secret_cb_arg;
-+
- 	SSL_CTX * initial_ctx; /* initial ctx, used to store sessions */
- #define session_ctx initial_ctx
- #else
-@@ -1729,6 +1739,12 @@ void *SSL_COMP_get_compression_methods(v
- int SSL_COMP_add_compression_method(int id,void *cm);
- #endif
- 
-+/* TLS extensions functions */
-+int SSL_set_hello_extension(SSL *s, int ext_type, void *ext_data, int ext_len);
-+
-+/* Pre-shared secret session resumption functions */
-+int SSL_set_session_secret_cb(SSL *s, tls_session_secret_cb_fn tls_session_secret_cb, void *arg);
-+
- /* BEGIN ERROR CODES */
- /* The following lines are auto generated by the script mkerr.pl. Any changes
-  * made after this point may be overwritten when the script is next run.
-@@ -1928,6 +1944,7 @@ void ERR_load_SSL_strings(void);
- #define SSL_F_TLS1_PRF					 284
- #define SSL_F_TLS1_SETUP_KEY_BLOCK			 211
- #define SSL_F_WRITE_PENDING				 212
-+#define SSL_F_SSL_SET_HELLO_EXTENSION			 213
- 
- /* Reason codes. */
- #define SSL_R_APP_DATA_IN_HANDSHAKE			 100
-diff -upr openssl-SNAP-20080528.orig/ssl/ssl_err.c openssl-SNAP-20080528/ssl/ssl_err.c
---- openssl-SNAP-20080528.orig/ssl/ssl_err.c	2007-10-27 03:01:29.000000000 +0300
-+++ openssl-SNAP-20080528/ssl/ssl_err.c	2008-05-29 10:49:25.000000000 +0300
-@@ -260,6 +260,7 @@ static ERR_STRING_DATA SSL_str_functs[]=
+Index: openssl-SNAP-20080928/ssl/ssl_err.c
+===================================================================
+--- openssl-SNAP-20080928.orig/ssl/ssl_err.c
++++ openssl-SNAP-20080928/ssl/ssl_err.c
+@@ -263,6 +263,7 @@ static ERR_STRING_DATA SSL_str_functs[]=
  {ERR_FUNC(SSL_F_TLS1_PRF),	"tls1_prf"},
  {ERR_FUNC(SSL_F_TLS1_SETUP_KEY_BLOCK),	"TLS1_SETUP_KEY_BLOCK"},
  {ERR_FUNC(SSL_F_WRITE_PENDING),	"WRITE_PENDING"},
@@ -197,15 +145,72 @@
  {0,NULL}
  	};
  
-diff -upr openssl-SNAP-20080528.orig/ssl/ssl_sess.c openssl-SNAP-20080528/ssl/ssl_sess.c
---- openssl-SNAP-20080528.orig/ssl/ssl_sess.c	2008-05-26 15:00:37.000000000 +0300
-+++ openssl-SNAP-20080528/ssl/ssl_sess.c	2008-05-29 10:49:25.000000000 +0300
-@@ -831,6 +831,52 @@ long SSL_CTX_get_timeout(const SSL_CTX *
+Index: openssl-SNAP-20080928/ssl/ssl.h
+===================================================================
+--- openssl-SNAP-20080928.orig/ssl/ssl.h
++++ openssl-SNAP-20080928/ssl/ssl.h
+@@ -355,6 +355,7 @@ extern "C" {
+  * 'struct ssl_st *' function parameters used to prototype callbacks
+  * in SSL_CTX. */
+ typedef struct ssl_st *ssl_crock_st;
++typedef struct tls_extension_st TLS_EXTENSION;
+ 
+ /* used to hold info on the particular ciphers used */
+ typedef struct ssl_cipher_st
+@@ -378,6 +379,8 @@ typedef struct ssl_cipher_st
+ 
+ DECLARE_STACK_OF(SSL_CIPHER)
+ 
++typedef int (*tls_session_secret_cb_fn)(SSL *s, void *secret, int *secret_len, STACK_OF(SSL_CIPHER) *peer_ciphers, SSL_CIPHER **cipher, void *arg);
++
+ /* Used to hold functions for SSLv2 or SSLv3/TLSv1 functions */
+ typedef struct ssl_method_st
+ 	{
+@@ -1145,6 +1148,13 @@ struct ssl_st
+ 	void *tlsext_opaque_prf_input;
+ 	size_t tlsext_opaque_prf_input_len;
+ 
++	/* TLS extensions */
++	TLS_EXTENSION *tls_extension;
++
++	/* TLS pre-shared secret session resumption */
++	tls_session_secret_cb_fn tls_session_secret_cb;
++	void *tls_session_secret_cb_arg;
++
+ 	SSL_CTX * initial_ctx; /* initial ctx, used to store sessions */
+ #define session_ctx initial_ctx
+ #else
+@@ -1746,6 +1756,12 @@ void *SSL_COMP_get_compression_methods(v
+ int SSL_COMP_add_compression_method(int id,void *cm);
+ #endif
+ 
++/* TLS extensions functions */
++int SSL_set_hello_extension(SSL *s, int ext_type, void *ext_data, int ext_len);
++
++/* Pre-shared secret session resumption functions */
++int SSL_set_session_secret_cb(SSL *s, tls_session_secret_cb_fn tls_session_secret_cb, void *arg);
++
+ /* BEGIN ERROR CODES */
+ /* The following lines are auto generated by the script mkerr.pl. Any changes
+  * made after this point may be overwritten when the script is next run.
+@@ -1948,6 +1964,7 @@ void ERR_load_SSL_strings(void);
+ #define SSL_F_TLS1_PRF					 284
+ #define SSL_F_TLS1_SETUP_KEY_BLOCK			 211
+ #define SSL_F_WRITE_PENDING				 212
++#define SSL_F_SSL_SET_HELLO_EXTENSION			 213
+ 
+ /* Reason codes. */
+ #define SSL_R_APP_DATA_IN_HANDSHAKE			 100
+Index: openssl-SNAP-20080928/ssl/ssl_sess.c
+===================================================================
+--- openssl-SNAP-20080928.orig/ssl/ssl_sess.c
++++ openssl-SNAP-20080928/ssl/ssl_sess.c
+@@ -834,6 +834,52 @@ long SSL_CTX_get_timeout(const SSL_CTX *
  	return(s->session_timeout);
  	}
  
 +#ifndef OPENSSL_NO_TLSEXT
-+int SSL_set_session_secret_cb(SSL *s, int (*tls_session_secret_cb)(SSL *s, void *secret, int *secret_len, 
++int SSL_set_session_secret_cb(SSL *s, int (*tls_session_secret_cb)(SSL *s, void *secret, int *secret_len,
 +	STACK_OF(SSL_CIPHER) *peer_ciphers, SSL_CIPHER **cipher, void *arg), void *arg)
 +{
 +	if (s == NULL) return(0);
@@ -253,9 +258,10 @@
  typedef struct timeout_param_st
  	{
  	SSL_CTX *ctx;
-diff -upr openssl-SNAP-20080528.orig/ssl/t1_lib.c openssl-SNAP-20080528/ssl/t1_lib.c
---- openssl-SNAP-20080528.orig/ssl/t1_lib.c	2008-04-30 20:00:39.000000000 +0300
-+++ openssl-SNAP-20080528/ssl/t1_lib.c	2008-05-29 10:49:25.000000000 +0300
+Index: openssl-SNAP-20080928/ssl/t1_lib.c
+===================================================================
+--- openssl-SNAP-20080928.orig/ssl/t1_lib.c
++++ openssl-SNAP-20080928/ssl/t1_lib.c
 @@ -154,6 +154,12 @@ int tls1_new(SSL *s)
  
  void tls1_free(SSL *s)
@@ -302,18 +308,26 @@
  
  #ifdef TLSEXT_TYPE_opaque_prf_input
  	if (s->s3->client_opaque_prf_input != NULL)
-@@ -1427,6 +1450,8 @@ int tls1_process_ticket(SSL *s, unsigned
+@@ -1435,6 +1458,15 @@ int tls1_process_ticket(SSL *s, unsigned
  				s->tlsext_ticket_expected = 1;
  				return 0;	/* Cache miss */
  				}
 +			if (s->tls_session_secret_cb)
++				{
++				/* Indicate cache miss here and instead of
++				 * generating the session from ticket now,
++				 * trigger abbreviated handshake based on
++				 * external mechanism to calculate the master
++				 * secret later. */
 +				return 0;
++				}
  			return tls_decrypt_ticket(s, p, size, session_id, len,
  									ret);
  			}
-diff -upr openssl-SNAP-20080528.orig/ssl/tls1.h openssl-SNAP-20080528/ssl/tls1.h
---- openssl-SNAP-20080528.orig/ssl/tls1.h	2008-04-30 20:00:39.000000000 +0300
-+++ openssl-SNAP-20080528/ssl/tls1.h	2008-05-29 10:49:25.000000000 +0300
+Index: openssl-SNAP-20080928/ssl/tls1.h
+===================================================================
+--- openssl-SNAP-20080928.orig/ssl/tls1.h
++++ openssl-SNAP-20080928/ssl/tls1.h
 @@ -512,6 +512,14 @@ SSL_CTX_callback_ctrl(ssl,SSL_CTRL_SET_T
  #define TLS_MD_MASTER_SECRET_CONST    "\x6d\x61\x73\x74\x65\x72\x20\x73\x65\x63\x72\x65\x74"  /*master secret*/
  #endif
@@ -329,12 +343,13 @@
  #ifdef  __cplusplus
  }
  #endif
-diff -upr openssl-SNAP-20080528.orig/util/ssleay.num openssl-SNAP-20080528/util/ssleay.num
---- openssl-SNAP-20080528.orig/util/ssleay.num	2007-08-31 16:03:14.000000000 +0300
-+++ openssl-SNAP-20080528/util/ssleay.num	2008-05-29 10:49:25.000000000 +0300
-@@ -253,3 +253,5 @@ PEM_write_bio_SSL_SESSION               
- PEM_read_SSL_SESSION                    302	EXIST:!WIN16:FUNCTION:
- PEM_read_bio_SSL_SESSION                303	EXIST::FUNCTION:
- PEM_write_SSL_SESSION                   304	EXIST:!WIN16:FUNCTION:
-+SSL_set_hello_extension			305	EXIST::FUNCTION:TLSEXT
-+SSL_set_session_secret_cb		306	EXIST::FUNCTION:TLSEXT
+Index: openssl-SNAP-20080928/util/ssleay.num
+===================================================================
+--- openssl-SNAP-20080928.orig/util/ssleay.num
++++ openssl-SNAP-20080928/util/ssleay.num
+@@ -254,3 +254,5 @@ PEM_read_bio_SSL_SESSION                
+ SSL_CTX_set_psk_server_callback         303	EXIST::FUNCTION:PSK
+ SSL_get_psk_identity                    304	EXIST::FUNCTION:PSK
+ PEM_write_SSL_SESSION                   305	EXIST:!WIN16:FUNCTION:
++SSL_set_hello_extension			306	EXIST::FUNCTION:TLSEXT
++SSL_set_session_secret_cb		307	EXIST::FUNCTION:TLSEXT

Modified: wpasupplicant/branches/upstream/current/src/common/defs.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/common/defs.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/common/defs.h (original)
+++ wpasupplicant/branches/upstream/current/src/common/defs.h Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * WPA Supplicant - Common definitions
- * Copyright (c) 2004-2007, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2004-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -40,6 +40,35 @@
 #define WPA_KEY_MGMT_WPA_NONE BIT(4)
 #define WPA_KEY_MGMT_FT_IEEE8021X BIT(5)
 #define WPA_KEY_MGMT_FT_PSK BIT(6)
+#define WPA_KEY_MGMT_IEEE8021X_SHA256 BIT(7)
+#define WPA_KEY_MGMT_PSK_SHA256 BIT(8)
+
+static inline int wpa_key_mgmt_wpa_ieee8021x(int akm)
+{
+	return akm == WPA_KEY_MGMT_IEEE8021X ||
+		akm == WPA_KEY_MGMT_FT_IEEE8021X ||
+		akm == WPA_KEY_MGMT_IEEE8021X_SHA256;
+}
+
+static inline int wpa_key_mgmt_wpa_psk(int akm)
+{
+	return akm == WPA_KEY_MGMT_PSK ||
+		akm == WPA_KEY_MGMT_FT_PSK ||
+		akm == WPA_KEY_MGMT_PSK_SHA256;
+}
+
+static inline int wpa_key_mgmt_ft(int akm)
+{
+	return akm == WPA_KEY_MGMT_FT_PSK ||
+		akm == WPA_KEY_MGMT_FT_IEEE8021X;
+}
+
+static inline int wpa_key_mgmt_sha256(int akm)
+{
+	return akm == WPA_KEY_MGMT_PSK_SHA256 ||
+		akm == WPA_KEY_MGMT_IEEE8021X_SHA256;
+}
+
 
 #define WPA_PROTO_WPA BIT(0)
 #define WPA_PROTO_RSN BIT(1)
@@ -55,7 +84,8 @@
 	       CIPHER_WEP104 } wpa_cipher;
 typedef enum { KEY_MGMT_802_1X, KEY_MGMT_PSK, KEY_MGMT_NONE,
 	       KEY_MGMT_802_1X_NO_WPA, KEY_MGMT_WPA_NONE,
-	       KEY_MGMT_FT_802_1X, KEY_MGMT_FT_PSK
+	       KEY_MGMT_FT_802_1X, KEY_MGMT_FT_PSK,
+	       KEY_MGMT_802_1X_SHA256, KEY_MGMT_PSK_SHA256
 } wpa_key_mgmt;
 
 /**

Modified: wpasupplicant/branches/upstream/current/src/common/ieee802_11_defs.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/common/ieee802_11_defs.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/common/ieee802_11_defs.h (original)
+++ wpasupplicant/branches/upstream/current/src/common/ieee802_11_defs.h Wed Oct  8 21:24:04 2008
@@ -1,6 +1,7 @@
 /*
  * IEEE 802.11 Frame type definitions
  * Copyright (c) 2002-2007, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2007-2008 Intel Corporation
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -91,7 +92,7 @@
 #define WLAN_CAPABILITY_SHORT_SLOT_TIME BIT(10)
 #define WLAN_CAPABILITY_DSSS_OFDM BIT(13)
 
-/* Status codes */
+/* Status codes (IEEE 802.11-2007, 7.3.1.9, Table 7-23) */
 #define WLAN_STATUS_SUCCESS 0
 #define WLAN_STATUS_UNSPECIFIED_FAILURE 1
 #define WLAN_STATUS_CAPS_UNSUPPORTED 10
@@ -111,10 +112,12 @@
 #define WLAN_STATUS_SPEC_MGMT_REQUIRED 22
 #define WLAN_STATUS_PWR_CAPABILITY_NOT_VALID 23
 #define WLAN_STATUS_SUPPORTED_CHANNEL_NOT_VALID 24
-/* 802.11g */
+/* IEEE 802.11g */
 #define WLAN_STATUS_ASSOC_DENIED_NO_SHORT_SLOT_TIME 25
 #define WLAN_STATUS_ASSOC_DENIED_NO_ER_PBCC 26
 #define WLAN_STATUS_ASSOC_DENIED_NO_DSSS_OFDM 27
+/* IEEE 802.11w */
+#define WLAN_STATUS_ASSOC_REJECTED_TEMPORARILY 30
 /* IEEE 802.11i */
 #define WLAN_STATUS_INVALID_IE 40
 #define WLAN_STATUS_GROUP_CIPHER_NOT_VALID 41
@@ -135,7 +138,7 @@
 #define WLAN_STATUS_INVALID_MDIE 55
 #define WLAN_STATUS_INVALID_FTIE 56
 
-/* Reason codes */
+/* Reason codes (IEEE 802.11-2007, 7.3.1.7, Table 7-22) */
 #define WLAN_REASON_UNSPECIFIED 1
 #define WLAN_REASON_PREV_AUTH_NOT_VALID 2
 #define WLAN_REASON_DEAUTH_LEAVING 3
@@ -145,7 +148,7 @@
 #define WLAN_REASON_CLASS3_FRAME_FROM_NONASSOC_STA 7
 #define WLAN_REASON_DISASSOC_STA_HAS_LEFT 8
 #define WLAN_REASON_STA_REQ_ASSOC_WITHOUT_AUTH 9
-/* 802.11h */
+/* IEEE 802.11h */
 #define WLAN_REASON_PWR_CAPABILITY_NOT_VALID 10
 #define WLAN_REASON_SUPPORTED_CHANNEL_NOT_VALID 11
 /* IEEE 802.11i */
@@ -161,6 +164,9 @@
 #define WLAN_REASON_INVALID_RSN_IE_CAPAB 22
 #define WLAN_REASON_IEEE_802_1X_AUTH_FAILED 23
 #define WLAN_REASON_CIPHER_SUITE_REJECTED 24
+/* IEEE 802.11w */
+#define WLAN_REASON_INVALID_GROUP_MGMT_CIPHER 25
+#define WLAN_REASON_ROBUST_MGMT_FRAME_POLICY_VIOLATION 26
 
 
 /* Information Element IDs */
@@ -186,22 +192,38 @@
 #define WLAN_EID_IBSS_DFS 41
 /* EIDs defined by IEEE 802.11h - END */
 #define WLAN_EID_ERP_INFO 42
+#define WLAN_EID_HT_CAP 45
 #define WLAN_EID_RSN 48
 #define WLAN_EID_EXT_SUPP_RATES 50
 #define WLAN_EID_MOBILITY_DOMAIN 54
 #define WLAN_EID_FAST_BSS_TRANSITION 55
 #define WLAN_EID_TIMEOUT_INTERVAL 56
 #define WLAN_EID_RIC_DATA 57
+#define WLAN_EID_HT_OPERATION 61
+#define WLAN_EID_SECONDARY_CHANNEL_OFFSET 62
+#define WLAN_EID_20_40_BSS_COEXISTENCE 72
+#define WLAN_EID_20_40_BSS_INTOLERANT 73
+#define WLAN_EID_OVERLAPPING_BSS_SCAN_PARAMS 74
+#define WLAN_EID_MMIE 76
+#define WLAN_EID_ASSOC_COMEBACK_TIME 77
 #define WLAN_EID_VENDOR_SPECIFIC 221
 
 
-/* Action frame categories */
+/* Action frame categories (IEEE 802.11-2007, 7.3.1.11, Table 7-24) */
 #define WLAN_ACTION_SPECTRUM_MGMT 0
 #define WLAN_ACTION_QOS 1
 #define WLAN_ACTION_DLS 2
 #define WLAN_ACTION_BLOCK_ACK 3
 #define WLAN_ACTION_RADIO_MEASUREMENT 5
 #define WLAN_ACTION_FT 6
+#define WLAN_ACTION_PING 8
+#define WLAN_ACTION_WMM 17
+
+/* Ping Action frame (IEEE 802.11w/D6.0, 7.4.9) */
+#define WLAN_PING_REQUEST 0
+#define WLAN_PING_RESPONSE 1
+
+#define WLAN_PING_TRANS_ID_LEN 16
 
 
 #ifdef _MSC_VER
@@ -299,6 +321,14 @@
 					le16 status_code;
 					u8 variable[0]; /* FT Request */
 				} STRUCT_PACKED ft_action_resp;
+				struct {
+					u8 action;
+					u8 trans_id[WLAN_PING_TRANS_ID_LEN];
+				} STRUCT_PACKED ping_req;
+				struct {
+					u8 action; /* */
+					u8 trans_id[WLAN_PING_TRANS_ID_LEN];
+				} STRUCT_PACKED ping_resp;
 			} u;
 		} STRUCT_PACKED action;
 	} u;
@@ -312,4 +342,218 @@
 #define ERP_INFO_USE_PROTECTION BIT(1)
 #define ERP_INFO_BARKER_PREAMBLE_MODE BIT(2)
 
+
+/* HT Capability element */
+
+#define MIMO_PWR_DONT_SEND_MIMO_SEQS            0
+#define MIMO_PWR_NEED2PRECEDE_MIMO_SEQS_BY_RTS  1
+#define MIMO_PWR_NO_LIMIT_ON_MIMO_SEQS          3
+
+enum {
+	MAX_RX_AMPDU_FACTOR_8KB = 0,
+	MAX_RX_AMPDU_FACTOR_16KB,
+	MAX_RX_AMPDU_FACTOR_32KB,
+	MAX_RX_AMPDU_FACTOR_64KB
+};
+
+enum {
+	CALIBRATION_NOT_SUPPORTED = 0,
+	CALIBRATION_CANNOT_INIT,
+	CALIBRATION_CAN_INIT,
+	CALIBRATION_FULL_SUPPORT
+};
+
+enum {
+	MCS_FEEDBACK_NOT_PROVIDED = 0,
+	MCS_FEEDBACK_UNSOLICITED,
+	MCS_FEEDBACK_MRQ_RESPONSE
+};
+
+
+struct ieee80211_ht_capability {
+	le16 capabilities_info;
+	u8 mac_ht_params_info;
+	u8 supported_mcs_set[16];
+	le16 extended_ht_capability_info;
+	le32 tx_BF_capability_info;
+	u8 antenna_selection_info;
+} STRUCT_PACKED;
+
+
+struct ieee80211_ht_operation {
+	u8 control_chan;
+	u8 ht_param;
+	le16 operation_mode;
+	le16 stbc_param;
+	u8 basic_set[16];
+} STRUCT_PACKED;
+
+/* auxiliary bit manipulation macros FIXME: move it to common later... */
+#define SET_2BIT_U8(_ptr_, _shift_, _val_)				\
+	((*(_ptr_) &= ~(3 << (_shift_))),				\
+	 (*(_ptr_) |= (*(_ptr_) & (((u8)3) << (_shift_))) |		\
+		      (((u8)(_val_) & 3) << _shift_)))
+
+#define GET_2BIT_U8(_var_, _shift_)	\
+	(((_var_) & (((u8)3) << (_shift_))) >> (_shift_))
+
+#define SET_2BIT_LE16(_u16ptr_, _shift_, _val_)				\
+	((*(_u16ptr_) &= ~(3 << (_shift_))),				\
+	 (*(_u16ptr_) |= 						\
+		(((*(_u16ptr_)) & (((u16)3) << ((u16)_shift_))) |	\
+		(((u16)(_val_) & (u16)3) << (u16)(_shift_)))))
+
+#define GET_2BIT_LE16(_var_, _shift_)	\
+	(((_var_) & (((u16)3) << (_shift_))) >> (_shift_))
+
+#define SET_2BIT_LE32(_u32ptr_, _shift_, _val_)				\
+	((*(_u32ptr_) &= ~(3 << (_shift_))),				\
+	 (*(_u32ptr_) |= (((*(_u32ptr_)) & (((u32)3) << (_shift_))) |	\
+			(((u32)(_val_) & 3) << _shift_))))
+
+#define GET_2BIT_LE32(_var_, _shift_)	\
+	(((_var_) & (((u32)3) << (_shift_))) >> (_shift_))
+
+#define SET_3BIT_LE16(_u16ptr_, _shift_, _val_)				\
+	((*(_u16ptr_) &= ~(7 << (_shift_))),				\
+	(*(_u16ptr_) |= (((*(_u16ptr_)) & (((u16)7) << (_shift_))) |	\
+			(((u16)(_val_) & 7) << _shift_))))
+
+#define GET_3BIT_LE16(_var_, _shift_)	\
+	(((_var_) & (((u16)7) << (_shift_))) >> (_shift_))
+
+#define SET_3BIT_LE32(_u32ptr_, _shift_, _val_)				\
+	((*(_u32ptr_) &= ~(7 << (_shift_))),				\
+	 (*(_u32ptr_) |= (((*(_u32ptr_)) & (((u32)7) << (_shift_))) |	\
+			(((u32)(_val_) & 7) << _shift_))))
+
+#define GET_3BIT_LE32(_var_, _shift_)	\
+	(((_var_) & (((u32)7) << (_shift_))) >> (_shift_))
+
+
+#define HT_CAP_INFO_ADVANCED_CODDING_CAP	((u16) BIT(0))
+#define HT_CAP_INFO_SUPP_CHANNEL_WIDTH_SET	((u16) BIT(1))
+#define HT_CAP_INFO_MIMO_PWR_SAVE_OFFSET	2
+#define HT_CAP_INFO_GREEN_FIELD			((u16) BIT(4))
+#define HT_CAP_INFO_SHORT_GI20MHZ		((u16) BIT(5))
+#define HT_CAP_INFO_SHORT_GI40MHZ		((u16) BIT(6))
+#define HT_CAP_INFO_TX_STBC			((u16) BIT(7))
+#define HT_CAP_INFO_RX_STBC_OFFSET		8
+#define HT_CAP_INFO_DELAYED_BA			((u16) BIT(10))
+#define HT_CAP_INFO_MAX_AMSDU_SIZE		((u16) BIT(11))
+#define HT_CAP_INFO_DSSS_CCK40MHZ		((u16) BIT(12))
+#define HT_CAP_INFO_PSMP_SUPP			((u16) BIT(13))
+#define HT_CAP_INFO_STBC_CTRL_FRAME_SUPP	((u16) BIT(14))
+#define HT_CAP_INFO_LSIG_TXOP_PROTECT_SUPPORT	((u16) BIT(15))
+
+
+#define MAC_HT_PARAM_INFO_MAX_RX_AMPDU_FACTOR_OFFSET	0
+#define MAC_HT_PARAM_INFO_MAX_MPDU_DENSITY_OFFSET	2
+
+#define EXT_HT_CAP_INFO_PCO			((u16) BIT(0))
+#define EXT_HT_CAP_INFO_TRANS_TIME_OFFSET	1
+#define EXT_HT_CAP_INFO_MCS_FEEDBACK_OFFSET	8
+#define EXT_HT_CAP_INFO_HTC_SUPPORTED		((u16) BIT(10))
+#define EXT_HT_CAP_INFO_RD_RESPONDER		((u16) BIT(11))
+
+
+#define TX_BEAMFORM_CAP_TXBF_CAP ((u32) BIT(0))
+#define TX_BEAMFORM_CAP_RX_STAGGERED_SOUNDING_CAP ((u32) BIT(1))
+#define TX_BEAMFORM_CAP_TX_STAGGERED_SOUNDING_CAP ((u32) BIT(2))
+#define TX_BEAMFORM_CAP_RX_ZLF_CAP ((u32) BIT(3))
+#define TX_BEAMFORM_CAP_TX_ZLF_CAP ((u32) BIT(4))
+#define TX_BEAMFORM_CAP_IMPLICIT_ZLF_CAP ((u32) BIT(5))
+#define TX_BEAMFORM_CAP_CALIB_OFFSET 6
+#define TX_BEAMFORM_CAP_EXPLICIT_CSI_TXBF_CAP ((u32) BIT(8))
+#define TX_BEAMFORM_CAP_EXPLICIT_UNCOMPR_STEERING_MATRIX_CAP ((u32) BIT(9))
+#define TX_BEAMFORM_CAP_EXPLICIT_BF_CSI_FEEDBACK_CAP ((u32) BIT(10))
+#define TX_BEAMFORM_CAP_EXPLICIT_BF_CSI_FEEDBACK_OFFSET 11
+#define TX_BEAMFORM_CAP_EXPLICIT_UNCOMPR_STEERING_MATRIX_FEEDBACK_OFFSET 13
+#define TX_BEAMFORM_CAP_EXPLICIT_COMPRESSED_STEERING_MATRIX_FEEDBACK_OFFSET 15
+#define TX_BEAMFORM_CAP_MINIMAL_GROUPING_OFFSET 17
+#define TX_BEAMFORM_CAP_CSI_NUM_BEAMFORMER_ANT_OFFSET 19
+#define TX_BEAMFORM_CAP_UNCOMPRESSED_STEERING_MATRIX_BEAMFORMER_ANT_OFFSET 21
+#define TX_BEAMFORM_CAP_COMPRESSED_STEERING_MATRIX_BEAMFORMER_ANT_OFFSET 23
+#define TX_BEAMFORM_CAP_SCI_MAX_OF_ROWS_BEANFORMER_SUPPORTED_OFFSET 25
+
+
+#define ASEL_CAPABILITY_ASEL_CAPABLE ((u8) BIT(0))
+#define ASEL_CAPABILITY_EXPLICIT_CSI_FEEDBACK_BASED_TX_AS_CAP ((u8) BIT(1))
+#define ASEL_CAPABILITY_ANT_INDICES_FEEDBACK_BASED_TX_AS_CAP ((u8) BIT(2))
+#define ASEL_CAPABILITY_EXPLICIT_CSI_FEEDBACK_CAP ((u8) BIT(3))
+#define ASEL_CAPABILITY_ANT_INDICES_FEEDBACK_CAP ((u8) BIT(4))
+#define ASEL_CAPABILITY_RX_AS_CAP ((u8) BIT(5))
+#define ASEL_CAPABILITY_TX_SOUND_PPDUS_CAP ((u8) BIT(6))
+
+
+struct ht_cap_ie {
+	u8 id;
+	u8 length;
+	struct ieee80211_ht_capability data;
+} STRUCT_PACKED;
+
+
+#define EXT_CHNL_OFF_NONE   0
+#define EXT_CHNL_OFF_ABOVE  1
+#define EXT_CHNL_OFF_BELOW  3
+
+#define REC_TRANS_CHNL_WIDTH_20     0
+#define REC_TRANS_CHNL_WIDTH_ANY    1
+
+#define OP_MODE_PURE                    0
+#define OP_MODE_MAY_BE_LEGACY_STAS      1
+#define OP_MODE_20MHZ_HT_STA_ASSOCED    2
+#define OP_MODE_MIXED                   3
+
+#define HT_INFO_HT_PARAM_EXT_CHNL_OFF_OFFSET		0
+#define HT_INFO_HT_PARAM_REC_TRANS_CHNL_WIDTH		((u8) BIT(2))
+#define HT_INFO_HT_PARAM_RIFS_MODE			((u8) BIT(3))
+#define HT_INFO_HT_PARAM_CTRL_ACCESS_ONLY		((u8) BIT(4))
+#define HT_INFO_HT_PARAM_SRV_INTERVAL_GRANULARITY	((u8) BIT(5))
+
+#define HT_INFO_OPERATION_MODE_OP_MODE_MASK	\
+		((le16) (0x0001 | 0x0002))
+#define HT_INFO_OPERATION_MODE_OP_MODE_OFFSET		0
+#define HT_INFO_OPERATION_MODE_NON_GF_DEVS_PRESENT	((u8) BIT(2))
+#define HT_INFO_OPERATION_MODE_TRANSMIT_BURST_LIMIT	((u8) BIT(3))
+#define HT_INFO_OPERATION_MODE_NON_HT_STA_PRESENT	((u8) BIT(4))
+
+#define HT_INFO_STBC_PARAM_DUAL_BEACON			((u16) BIT(6))
+#define HT_INFO_STBC_PARAM_DUAL_STBC_PROTECT		((u16) BIT(7))
+#define HT_INFO_STBC_PARAM_SECONDARY_BCN		((u16) BIT(8))
+#define HT_INFO_STBC_PARAM_LSIG_TXOP_PROTECT_ALLOWED	((u16) BIT(9))
+#define HT_INFO_STBC_PARAM_PCO_ACTIVE			((u16) BIT(10))
+#define HT_INFO_STBC_PARAM_PCO_PHASE			((u16) BIT(11))
+
+
+/* Secondary channel offset element */
+#define SECONDARY_CHANNEL_OFFSET_NONE	0
+#define SECONDARY_CHANNEL_OFFSET_ABOVE	1
+#define SECONDARY_CHANNEL_OFFSET_BELOW	3
+struct secondary_channel_offset_ie {
+	u8 id;
+	u8 length;
+	u8 secondary_offset_offset;
+} STRUCT_PACKED;
+
+
+/* body of Recommended Transmit Channel Width action frame */
+#define CHANNEL_WIDTH_20	0
+#define CHANNEL_WIDTH_ANY	1
+struct recommended_tx_channel_width_action {
+	u8 category;
+	u8 action;
+	u8 channel_width;
+} STRUCT_PACKED;
+
+/* body of MIMO Power Save action frame */
+#define PWR_SAVE_MODE_STATIC	0
+#define PWR_SAVE_MODE_DYNAMIC	1
+struct mimo_pwr_save_action {
+	u8 category;
+	u8 action;
+	u8 enable;
+	u8 mode;
+} STRUCT_PACKED;
+
 #endif /* IEEE802_11_DEFS_H */

Modified: wpasupplicant/branches/upstream/current/src/common/privsep_commands.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/common/privsep_commands.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/common/privsep_commands.h (original)
+++ wpasupplicant/branches/upstream/current/src/common/privsep_commands.h Wed Oct  8 21:24:04 2008
@@ -30,6 +30,7 @@
 	PRIVSEP_CMD_L2_UNREGISTER,
 	PRIVSEP_CMD_L2_NOTIFY_AUTH_START,
 	PRIVSEP_CMD_L2_SEND,
+	PRIVSEP_CMD_SET_MODE,
 };
 
 struct privsep_cmd_associate

Modified: wpasupplicant/branches/upstream/current/src/common/wpa_common.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/common/wpa_common.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/common/wpa_common.c (original)
+++ wpasupplicant/branches/upstream/current/src/common/wpa_common.c Wed Oct  8 21:24:04 2008
@@ -79,6 +79,7 @@
  * @nonce2: SNonce or ANonce
  * @ptk: Buffer for pairwise transient key
  * @ptk_len: Length of PTK
+ * @use_sha256: Whether to use SHA256-based KDF
  *
  * IEEE Std 802.11i-2004 - 8.5.1.2 Pairwise key hierarchy
  * PTK = PRF-X(PMK, "Pairwise key expansion",
@@ -92,7 +93,7 @@
 void wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
 		    const u8 *addr1, const u8 *addr2,
 		    const u8 *nonce1, const u8 *nonce2,
-		    u8 *ptk, size_t ptk_len)
+		    u8 *ptk, size_t ptk_len, int use_sha256)
 {
 	u8 data[2 * ETH_ALEN + 2 * WPA_NONCE_LEN];
 
@@ -114,7 +115,14 @@
 			  WPA_NONCE_LEN);
 	}
 
-	sha1_prf(pmk, pmk_len, label, data, sizeof(data), ptk, ptk_len);
+#ifdef CONFIG_IEEE80211W
+	if (use_sha256)
+		sha256_prf(pmk, pmk_len, label, data, sizeof(data),
+			   ptk, ptk_len);
+	else
+#endif /* CONFIG_IEEE80211W */
+		sha1_prf(pmk, pmk_len, label, data, sizeof(data), ptk,
+			 ptk_len);
 
 	wpa_printf(MSG_DEBUG, "WPA: PTK derivation - A1=" MACSTR " A2=" MACSTR,
 		   MAC2STR(addr1), MAC2STR(addr2));
@@ -214,6 +222,12 @@
 	if (RSN_SELECTOR_GET(s) == RSN_AUTH_KEY_MGMT_FT_PSK)
 		return WPA_KEY_MGMT_FT_PSK;
 #endif /* CONFIG_IEEE80211R */
+#ifdef CONFIG_IEEE80211W
+	if (RSN_SELECTOR_GET(s) == RSN_AUTH_KEY_MGMT_802_1X_SHA256)
+		return WPA_KEY_MGMT_IEEE8021X_SHA256;
+	if (RSN_SELECTOR_GET(s) == RSN_AUTH_KEY_MGMT_PSK_SHA256)
+		return WPA_KEY_MGMT_PSK_SHA256;
+#endif /* CONFIG_IEEE80211W */
 	return 0;
 }
 #endif /* CONFIG_NO_WPA2 */
@@ -394,7 +408,7 @@
 /**
  * wpa_derive_pmk_r0 - Derive PMK-R0 and PMKR0Name
  *
- * IEEE 802.11r/D9.0 - 8.5.1.5.3
+ * IEEE Std 802.11r-2008 - 8.5.1.5.3
  */
 void wpa_derive_pmk_r0(const u8 *xxkey, size_t xxkey_len,
 		       const u8 *ssid, size_t ssid_len,
@@ -449,7 +463,7 @@
 /**
  * wpa_derive_pmk_r1_name - Derive PMKR1Name
  *
- * IEEE 802.11r/D9.0 - 8.5.1.5.4
+ * IEEE Std 802.11r-2008 - 8.5.1.5.4
  */
 void wpa_derive_pmk_r1_name(const u8 *pmk_r0_name, const u8 *r1kh_id,
 			    const u8 *s1kh_id, u8 *pmk_r1_name)
@@ -479,7 +493,7 @@
 /**
  * wpa_derive_pmk_r1 - Derive PMK-R1 and PMKR1Name from PMK-R0
  *
- * IEEE 802.11r/D9.0 - 8.5.1.5.4
+ * IEEE Std 802.11r-2008 - 8.5.1.5.4
  */
 void wpa_derive_pmk_r1(const u8 *pmk_r0, const u8 *pmk_r0_name,
 		       const u8 *r1kh_id, const u8 *s1kh_id,
@@ -504,7 +518,7 @@
 /**
  * wpa_pmk_r1_to_ptk - Derive PTK and PTKName from PMK-R1
  *
- * IEEE 802.11r/D9.0 - 8.5.1.5.5
+ * IEEE Std 802.11r-2008 - 8.5.1.5.5
  */
 void wpa_pmk_r1_to_ptk(const u8 *pmk_r1, const u8 *snonce, const u8 *anonce,
 		       const u8 *sta_addr, const u8 *bssid,

Modified: wpasupplicant/branches/upstream/current/src/common/wpa_common.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/common/wpa_common.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/common/wpa_common.h (original)
+++ wpasupplicant/branches/upstream/current/src/common/wpa_common.h Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * WPA definitions shared between hostapd and wpa_supplicant
- * Copyright (c) 2002-2007, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2002-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -54,6 +54,9 @@
 #define RSN_AUTH_KEY_MGMT_FT_802_1X RSN_SELECTOR(0x00, 0x0f, 0xac, 3)
 #define RSN_AUTH_KEY_MGMT_FT_PSK RSN_SELECTOR(0x00, 0x0f, 0xac, 4)
 #endif /* CONFIG_IEEE80211R */
+#define RSN_AUTH_KEY_MGMT_802_1X_SHA256 RSN_SELECTOR(0x00, 0x0f, 0xac, 5)
+#define RSN_AUTH_KEY_MGMT_PSK_SHA256 RSN_SELECTOR(0x00, 0x0f, 0xac, 6)
+
 #define RSN_CIPHER_SUITE_NONE RSN_SELECTOR(0x00, 0x0f, 0xac, 0)
 #define RSN_CIPHER_SUITE_WEP40 RSN_SELECTOR(0x00, 0x0f, 0xac, 1)
 #define RSN_CIPHER_SUITE_TKIP RSN_SELECTOR(0x00, 0x0f, 0xac, 2)
@@ -107,7 +110,11 @@
 
 /* IEEE 802.11, 7.3.2.25.3 RSN Capabilities */
 #define WPA_CAPABILITY_PREAUTH BIT(0)
-#define WPA_CAPABILITY_MGMT_FRAME_PROTECTION BIT(7)
+#define WPA_CAPABILITY_NO_PAIRWISE BIT(1)
+/* B2-B3: PTKSA Replay Counter */
+/* B4-B5: GTKSA Replay Counter */
+#define WPA_CAPABILITY_MFPR BIT(6)
+#define WPA_CAPABILITY_MFPC BIT(7)
 #define WPA_CAPABILITY_PEERKEY_ENABLED BIT(9)
 
 
@@ -273,6 +280,7 @@
 #define FTIE_SUBELEM_R1KH_ID 1
 #define FTIE_SUBELEM_GTK 2
 #define FTIE_SUBELEM_R0KH_ID 3
+#define FTIE_SUBELEM_IGTK 4
 
 #endif /* CONFIG_IEEE80211R */
 
@@ -286,7 +294,7 @@
 void wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
 		    const u8 *addr1, const u8 *addr2,
 		    const u8 *nonce1, const u8 *nonce2,
-		    u8 *ptk, size_t ptk_len);
+		    u8 *ptk, size_t ptk_len, int use_sha256);
 
 #ifdef CONFIG_IEEE80211R
 int wpa_ft_mic(const u8 *kck, const u8 *sta_addr, const u8 *ap_addr,

Modified: wpasupplicant/branches/upstream/current/src/crypto/tls_internal.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/crypto/tls_internal.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/crypto/tls_internal.c (original)
+++ wpasupplicant/branches/upstream/current/src/crypto/tls_internal.c Wed Oct  8 21:24:04 2008
@@ -366,8 +366,10 @@
 	wpa_printf(MSG_DEBUG, "TLS: %s(in_data=%p in_len=%lu)",
 		   __func__, in_data, (unsigned long) in_len);
 	out = tlsv1_server_handshake(conn->server, in_data, in_len, out_len);
-	if (out == NULL && tlsv1_server_established(conn->server))
+	if (out == NULL && tlsv1_server_established(conn->server)) {
 		out = os_malloc(1);
+		*out_len = 0;
+	}
 	return out;
 #else /* CONFIG_TLS_INTERNAL_SERVER */
 	return NULL;

Modified: wpasupplicant/branches/upstream/current/src/drivers/driver.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/drivers/driver.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/drivers/driver.h (original)
+++ wpasupplicant/branches/upstream/current/src/drivers/driver.h Wed Oct  8 21:24:04 2008
@@ -929,6 +929,20 @@
 	 * Returns: 0 on success, -1 on failure
 	 */
 	int (*set_probe_req_ie)(void *, const u8 *ies, size_t ies_len);
+
+ 	/**
+	 * set_mode - Request driver to set the operating mode
+	 * @priv: private driver interface data
+	 * @mode: Operation mode (infra/ibss) IEEE80211_MODE_*
+	 *
+	 * This handler will be called before any key configuration and call to
+	 * associate() handler in order to allow the operation mode to be
+	 * configured as early as possible. This information is also available
+	 * in associate() params and as such, some driver wrappers may not need
+	 * to implement set_mode() handler.
+	 * Returns: 0 on success, -1 on failure
+	 */
+	int (*set_mode)(void *priv, int mode);
 };
 
 /**

Modified: wpasupplicant/branches/upstream/current/src/drivers/driver_ndis.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/drivers/driver_ndis.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/drivers/driver_ndis.c (original)
+++ wpasupplicant/branches/upstream/current/src/drivers/driver_ndis.c Wed Oct  8 21:24:04 2008
@@ -1177,6 +1177,7 @@
 	struct wpa_driver_ndis_data *drv = priv;
 	NDIS_802_11_PMKID p;
 	struct ndis_pmkid_entry *pmkid, *prev;
+	int prev_authmode, ret;
 
 	if (drv->no_of_pmkid == 0)
 		return 0;
@@ -1189,12 +1190,25 @@
 		os_free(prev);
 	}
 
+	/*
+	 * Some drivers may refuse OID_802_11_PMKID if authMode is not set to
+	 * WPA2, so change authMode temporarily, if needed.
+	 */
+	prev_authmode = ndis_get_auth_mode(drv);
+	if (prev_authmode != Ndis802_11AuthModeWPA2)
+		ndis_set_auth_mode(drv, Ndis802_11AuthModeWPA2);
+
 	os_memset(&p, 0, sizeof(p));
 	p.Length = 8;
 	p.BSSIDInfoCount = 0;
 	wpa_hexdump(MSG_MSGDUMP, "NDIS: OID_802_11_PMKID (flush)",
 		    (char *) &p, 8);
-	return ndis_set_oid(drv, OID_802_11_PMKID, (char *) &p, 8);
+	ret = ndis_set_oid(drv, OID_802_11_PMKID, (char *) &p, 8);
+
+	if (prev_authmode != Ndis802_11AuthModeWPA2)
+		ndis_set_auth_mode(drv, prev_authmode);
+
+	return ret;
 }
 
 
@@ -2829,5 +2843,7 @@
 	NULL /* mlme_remove_sta */,
 	NULL /* update_ft_ies */,
 	NULL /* send_ft_action */,
-	wpa_driver_ndis_get_scan_results
+	wpa_driver_ndis_get_scan_results,
+	NULL /* set_probe_req_ie */,
+	NULL /* set_mode */
 };

Modified: wpasupplicant/branches/upstream/current/src/drivers/driver_nl80211.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/drivers/driver_nl80211.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/drivers/driver_nl80211.c (original)
+++ wpasupplicant/branches/upstream/current/src/drivers/driver_nl80211.c Wed Oct  8 21:24:04 2008
@@ -19,6 +19,12 @@
 #include <netlink/genl/family.h>
 #include <netlink/genl/ctrl.h>
 #include <linux/nl80211.h>
+#ifdef CONFIG_CLIENT_MLME
+#include <netpacket/packet.h>
+#include <linux/if_ether.h>
+#include "radiotap.h"
+#include "radiotap_iter.h"
+#endif /* CONFIG_CLIENT_MLME */
 
 #include "wireless_copy.h"
 #include "common.h"
@@ -47,6 +53,7 @@
 	int ioctl_sock;
 	char ifname[IFNAMSIZ + 1];
 	int ifindex;
+	int if_removed;
 	u8 *assoc_req_ies;
 	size_t assoc_req_ies_len;
 	u8 *assoc_resp_ies;
@@ -69,6 +76,11 @@
 	struct nl_cache *nl_cache;
 	struct nl_cb *nl_cb;
 	struct genl_family *nl80211;
+
+#ifdef CONFIG_CLIENT_MLME
+	int monitor_sock; /* socket for monitor */
+	int monitor_ifidx;
+#endif /* CONFIG_CLIENT_MLME */
 };
 
 
@@ -77,6 +89,65 @@
 static int wpa_driver_nl80211_set_mode(void *priv, int mode);
 static int wpa_driver_nl80211_flush_pmkid(void *priv);
 static int wpa_driver_nl80211_get_range(void *priv);
+static void
+wpa_driver_nl80211_finish_drv_init(struct wpa_driver_nl80211_data *drv);
+
+
+/* nl80211 code */
+static int ack_handler(struct nl_msg *msg, void *arg)
+{
+	int *err = arg;
+	*err = 0;
+	return NL_STOP;
+}
+
+static int finish_handler(struct nl_msg *msg, void *arg)
+{
+	return NL_SKIP;
+}
+
+static int error_handler(struct sockaddr_nl *nla, struct nlmsgerr *err,
+			 void *arg)
+{
+	int *ret = arg;
+	*ret = err->error;
+	return NL_SKIP;
+}
+
+static int send_and_recv_msgs(struct wpa_driver_nl80211_data *drv,
+			      struct nl_msg *msg,
+			      int (*valid_handler)(struct nl_msg *, void *),
+			      void *valid_data)
+{
+	struct nl_cb *cb;
+	int err = -ENOMEM;
+
+	cb = nl_cb_clone(drv->nl_cb);
+	if (!cb)
+		goto out;
+
+	err = nl_send_auto_complete(drv->nl_handle, msg);
+	if (err < 0)
+		goto out;
+
+	err = 1;
+
+	nl_cb_err(cb, NL_CB_CUSTOM, error_handler, &err);
+	nl_cb_set(cb, NL_CB_FINISH, NL_CB_CUSTOM, finish_handler, NULL);
+	nl_cb_set(cb, NL_CB_ACK, NL_CB_CUSTOM, ack_handler, &err);
+
+	if (valid_handler)
+		nl_cb_set(cb, NL_CB_VALID, NL_CB_CUSTOM,
+			  valid_handler, valid_data);
+
+	while (err > 0)
+		nl_recvmsgs(drv->nl_handle, cb);
+ out:
+	nl_cb_put(cb);
+	nlmsg_free(msg);
+	return err;
+}
+
 
 static int wpa_driver_nl80211_send_oper_ifla(
 	struct wpa_driver_nl80211_data *drv,
@@ -583,8 +654,9 @@
 }
 
 
-static void wpa_driver_nl80211_event_link(void *ctx, char *buf, size_t len,
-				       int del)
+static void wpa_driver_nl80211_event_link(struct wpa_driver_nl80211_data *drv,
+					  void *ctx, char *buf, size_t len,
+					  int del)
 {
 	union wpa_event_data event;
 
@@ -600,7 +672,65 @@
 		   event.interface_status.ifname,
 		   del ? "removed" : "added");
 
+	if (os_strcmp(drv->ifname, event.interface_status.ifname) == 0) {
+		if (del)
+			drv->if_removed = 1;
+		else
+			drv->if_removed = 0;
+	}
+
 	wpa_supplicant_event(ctx, EVENT_INTERFACE_STATUS, &event);
+}
+
+
+static int wpa_driver_nl80211_own_ifname(struct wpa_driver_nl80211_data *drv,
+					 struct nlmsghdr *h)
+{
+	struct ifinfomsg *ifi;
+	int attrlen, _nlmsg_len, rta_len;
+	struct rtattr *attr;
+
+	ifi = NLMSG_DATA(h);
+
+	_nlmsg_len = NLMSG_ALIGN(sizeof(struct ifinfomsg));
+
+	attrlen = h->nlmsg_len - _nlmsg_len;
+	if (attrlen < 0)
+		return 0;
+
+	attr = (struct rtattr *) (((char *) ifi) + _nlmsg_len);
+
+	rta_len = RTA_ALIGN(sizeof(struct rtattr));
+	while (RTA_OK(attr, attrlen)) {
+		if (attr->rta_type == IFLA_IFNAME) {
+			if (os_strcmp(((char *) attr) + rta_len, drv->ifname)
+			    == 0)
+				return 1;
+			else
+				break;
+		}
+		attr = RTA_NEXT(attr, attrlen);
+	}
+
+	return 0;
+}
+
+
+static int wpa_driver_nl80211_own_ifindex(struct wpa_driver_nl80211_data *drv,
+					  int ifindex, struct nlmsghdr *h)
+{
+	if (drv->ifindex == ifindex)
+		return 1;
+
+	if (drv->if_removed && wpa_driver_nl80211_own_ifname(drv, h)) {
+		drv->ifindex = if_nametoindex(drv->ifname);
+		wpa_printf(MSG_DEBUG, "nl80211: Update ifindex for a removed "
+			   "interface");
+		wpa_driver_nl80211_finish_drv_init(drv);
+		return 1;
+	}
+
+	return 0;
 }
 
 
@@ -617,7 +747,7 @@
 
 	ifi = NLMSG_DATA(h);
 
-	if (drv->ifindex != ifi->ifi_index) {
+	if (!wpa_driver_nl80211_own_ifindex(drv, ifi->ifi_index, h)) {
 		wpa_printf(MSG_DEBUG, "Ignore event for foreign ifindex %d",
 			   ifi->ifi_index);
 		return;
@@ -656,9 +786,10 @@
 				drv, ctx, ((char *) attr) + rta_len,
 				attr->rta_len - rta_len);
 		} else if (attr->rta_type == IFLA_IFNAME) {
-			wpa_driver_nl80211_event_link(ctx,
-						   ((char *) attr) + rta_len,
-						   attr->rta_len - rta_len, 0);
+			wpa_driver_nl80211_event_link(
+				drv, ctx,
+				((char *) attr) + rta_len,
+				attr->rta_len - rta_len, 0);
 		}
 		attr = RTA_NEXT(attr, attrlen);
 	}
@@ -689,9 +820,10 @@
 	rta_len = RTA_ALIGN(sizeof(struct rtattr));
 	while (RTA_OK(attr, attrlen)) {
 		if (attr->rta_type == IFLA_IFNAME) {
-			wpa_driver_nl80211_event_link(ctx,
-						   ((char *) attr) + rta_len,
-						   attr->rta_len - rta_len, 1);
+			wpa_driver_nl80211_event_link(
+				drv, ctx,
+				((char *) attr) + rta_len,
+				attr->rta_len - rta_len, 1);
 		}
 		attr = RTA_NEXT(attr, attrlen);
 	}
@@ -824,6 +956,258 @@
 }
 
 
+#ifdef CONFIG_CLIENT_MLME
+
+static int nl80211_set_vif(struct wpa_driver_nl80211_data *drv,
+			   int drop_unencrypted, int userspace_mlme)
+{
+#ifdef NL80211_CMD_SET_VIF
+	struct nl_msg *msg;
+	int ret = -1;
+
+	msg = nlmsg_alloc();
+	if (!msg)
+		return -ENOMEM;
+
+	genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0, 0,
+		    NL80211_CMD_SET_VIF, 0);
+
+	if (drop_unencrypted >= 0)
+		NLA_PUT_U8(msg, NL80211_ATTR_VIF_DROP_UNENCRYPTED,
+			   drop_unencrypted);
+	if (userspace_mlme >= 0)
+		NLA_PUT_U8(msg, NL80211_ATTR_VIF_USERSPACE_MLME,
+			   userspace_mlme);
+
+	ret = 0;
+
+	NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
+
+	ret = send_and_recv_msgs(drv, msg, NULL, NULL);
+	return ret;
+
+nla_put_failure:
+	return -ENOBUFS;
+#else /* NL80211_CMD_SET_VIF */
+	return -1;
+#endif /* NL80211_CMD_SET_VIF */
+}
+
+
+static int wpa_driver_nl80211_set_userspace_mlme(
+	struct wpa_driver_nl80211_data *drv, int enabled)
+{
+	return nl80211_set_vif(drv, -1, enabled);
+}
+
+
+static void nl80211_remove_iface(struct wpa_driver_nl80211_data *drv,
+				 int ifidx)
+{
+	struct nl_msg *msg;
+
+	msg = nlmsg_alloc();
+	if (!msg)
+		goto nla_put_failure;
+
+	genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
+		    0, NL80211_CMD_DEL_INTERFACE, 0);
+	NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, ifidx);
+	if (send_and_recv_msgs(drv, msg, NULL, NULL) == 0)
+		return;
+nla_put_failure:
+	wpa_printf(MSG_ERROR, "nl80211: Failed to remove interface.");
+}
+
+
+static int nl80211_create_iface(struct wpa_driver_nl80211_data *drv,
+				const char *ifname, enum nl80211_iftype iftype)
+{
+	struct nl_msg *msg, *flags = NULL;
+	int ifidx, err;
+	int ret = -ENOBUFS;
+
+	msg = nlmsg_alloc();
+	if (!msg)
+		return -1;
+
+	genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
+		    0, NL80211_CMD_NEW_INTERFACE, 0);
+	NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, if_nametoindex(drv->ifname));
+	NLA_PUT_STRING(msg, NL80211_ATTR_IFNAME, ifname);
+	NLA_PUT_U32(msg, NL80211_ATTR_IFTYPE, iftype);
+
+	if (iftype == NL80211_IFTYPE_MONITOR) {
+		flags = nlmsg_alloc();
+		if (!flags)
+			goto nla_put_failure;
+
+		NLA_PUT_FLAG(flags, NL80211_MNTR_FLAG_COOK_FRAMES);
+
+		err = nla_put_nested(msg, NL80211_ATTR_MNTR_FLAGS, flags);
+
+		nlmsg_free(flags);
+
+		if (err)
+			goto nla_put_failure;
+	}
+
+	ret = send_and_recv_msgs(drv, msg, NULL, NULL);
+	if (ret) {
+	nla_put_failure:
+		wpa_printf(MSG_ERROR, "nl80211: Failed to create interface %d",
+			   ret);
+		return ret;
+	}
+
+	ifidx = if_nametoindex(ifname);
+	if (ifidx <= 0)
+		return -1;
+
+	return ifidx;
+}
+
+
+static void handle_monitor_read(int sock, void *eloop_ctx, void *sock_ctx)
+{
+	struct wpa_driver_nl80211_data *drv = eloop_ctx;
+	int len;
+	unsigned char buf[3000];
+	struct ieee80211_radiotap_iterator iter;
+	int ret;
+	int injected = 0, failed = 0, rxflags = 0;
+	struct ieee80211_rx_status rx_status;
+
+	len = recv(sock, buf, sizeof(buf), 0);
+	if (len < 0) {
+		perror("recv");
+		return;
+	}
+
+	if (ieee80211_radiotap_iterator_init(&iter, (void *) buf, len)) {
+		wpa_printf(MSG_DEBUG, "nl80211: received invalid radiotap "
+			   "frame");
+		return;
+	}
+
+	os_memset(&rx_status, 0, sizeof(rx_status));
+
+	while (1) {
+		ret = ieee80211_radiotap_iterator_next(&iter);
+		if (ret == -ENOENT)
+			break;
+		if (ret) {
+			wpa_printf(MSG_DEBUG, "nl80211: received invalid "
+				   "radiotap frame (%d)", ret);
+			return;
+		}
+		switch (iter.this_arg_index) {
+		case IEEE80211_RADIOTAP_FLAGS:
+			if (*iter.this_arg & IEEE80211_RADIOTAP_F_FCS)
+				len -= 4;
+			break;
+		case IEEE80211_RADIOTAP_RX_FLAGS:
+			rxflags = 1;
+			break;
+		case IEEE80211_RADIOTAP_TX_FLAGS:
+			injected = 1;
+			failed = le_to_host16((*(u16 *) iter.this_arg)) &
+				IEEE80211_RADIOTAP_F_TX_FAIL;
+			break;
+		case IEEE80211_RADIOTAP_DATA_RETRIES:
+			break;
+		case IEEE80211_RADIOTAP_CHANNEL:
+			/* TODO convert from freq/flags to channel number
+			 * rx_status.channel = XXX;
+			*/
+			break;
+		case IEEE80211_RADIOTAP_RATE:
+			break;
+		case IEEE80211_RADIOTAP_DB_ANTSIGNAL:
+			rx_status.ssi = *iter.this_arg;
+			break;
+		}
+	}
+
+	if (rxflags && injected)
+		return;
+
+	if (!injected) {
+		wpa_supplicant_sta_rx(drv->ctx, buf + iter.max_length,
+				      len - iter.max_length, &rx_status);
+	} else if (failed) {
+		/* TX failure callback */
+	} else {
+		/* TX success (ACK) callback */
+	}
+}
+
+
+static int wpa_driver_nl80211_create_monitor_interface(
+	struct wpa_driver_nl80211_data *drv)
+{
+	char buf[IFNAMSIZ];
+	struct sockaddr_ll ll;
+	int optval, flags;
+	socklen_t optlen;
+
+	os_snprintf(buf, IFNAMSIZ, "mon.%s", drv->ifname);
+	buf[IFNAMSIZ - 1] = '\0';
+
+	drv->monitor_ifidx =
+		nl80211_create_iface(drv, buf, NL80211_IFTYPE_MONITOR);
+
+	if (drv->monitor_ifidx < 0)
+		return -1;
+
+	if (wpa_driver_nl80211_get_ifflags_ifname(drv, buf, &flags) != 0 ||
+	    wpa_driver_nl80211_set_ifflags_ifname(drv, buf, flags | IFF_UP) !=
+	    0) {
+		wpa_printf(MSG_ERROR, "nl80211: Could not set interface '%s' "
+			   "UP", buf);
+		goto error;
+	}
+
+	os_memset(&ll, 0, sizeof(ll));
+	ll.sll_family = AF_PACKET;
+	ll.sll_ifindex = drv->monitor_ifidx;
+	drv->monitor_sock = socket(PF_PACKET, SOCK_RAW, htons(ETH_P_ALL));
+	if (drv->monitor_sock < 0) {
+		perror("socket[PF_PACKET,SOCK_RAW]");
+		goto error;
+	}
+
+	if (bind(drv->monitor_sock, (struct sockaddr *) &ll,
+		 sizeof(ll)) < 0) {
+		perror("monitor socket bind");
+		goto error;
+	}
+
+	optlen = sizeof(optval);
+	optval = 20;
+	if (setsockopt
+	    (drv->monitor_sock, SOL_SOCKET, SO_PRIORITY, &optval, optlen)) {
+		perror("Failed to set socket priority");
+		goto error;
+	}
+
+	if (eloop_register_read_sock(drv->monitor_sock, handle_monitor_read,
+				     drv, NULL)) {
+		wpa_printf(MSG_ERROR, "nl80211: Could not register monitor "
+			   "read socket");
+		goto error;
+	}
+
+	return 0;
+
+ error:
+	nl80211_remove_iface(drv, drv->monitor_ifidx);
+	return -1;
+}
+
+#endif /* CONFIG_CLIENT_MLME */
+
+
 /**
  * wpa_driver_nl80211_init - Initialize WE driver interface
  * @ctx: context to be used when calling wpa_supplicant functions,
@@ -833,7 +1217,7 @@
  */
 void * wpa_driver_nl80211_init(void *ctx, const char *ifname)
 {
-	int s, flags;
+	int s;
 	struct sockaddr_nl local;
 	struct wpa_driver_nl80211_data *drv;
 
@@ -901,6 +1285,31 @@
 	eloop_register_read_sock(s, wpa_driver_nl80211_event_receive, drv,
 				 ctx);
 	drv->event_sock = s;
+
+	wpa_driver_nl80211_finish_drv_init(drv);
+
+	return drv;
+
+err6:
+	close(drv->ioctl_sock);
+err5:
+	genl_family_put(drv->nl80211);
+err4:
+	nl_cache_free(drv->nl_cache);
+err3:
+	nl_handle_destroy(drv->nl_handle);
+err2:
+	nl_cb_put(drv->nl_cb);
+err1:
+	os_free(drv);
+	return NULL;
+}
+
+
+static void
+wpa_driver_nl80211_finish_drv_init(struct wpa_driver_nl80211_data *drv)
+{
+	int flags;
 
 	if (wpa_driver_nl80211_get_ifflags(drv, &flags) != 0)
 		printf("Could not get interface '%s' flags\n", drv->ifname);
@@ -936,22 +1345,6 @@
 	drv->ifindex = if_nametoindex(drv->ifname);
 
 	wpa_driver_nl80211_send_oper_ifla(drv, 1, IF_OPER_DORMANT);
-
-	return drv;
-
-err6:
-	close(drv->ioctl_sock);
-err5:
-	genl_family_put(drv->nl80211);
-err4:
-	nl_cache_free(drv->nl_cache);
-err3:
-	nl_handle_destroy(drv->nl_handle);
-err2:
-	nl_cb_put(drv->nl_cb);
-err1:
-	os_free(drv);
-	return NULL;
 }
 
 
@@ -966,6 +1359,17 @@
 {
 	struct wpa_driver_nl80211_data *drv = priv;
 	int flags;
+
+#ifdef CONFIG_CLIENT_MLME
+	if (drv->monitor_sock >= 0) {
+		eloop_unregister_read_sock(drv->monitor_sock);
+		close(drv->monitor_sock);
+	}
+	if (drv->monitor_ifidx > 0)
+		nl80211_remove_iface(drv, drv->monitor_ifidx);
+	if (drv->capa.flags & WPA_DRIVER_FLAGS_USER_SPACE_MLME)
+		wpa_driver_nl80211_set_userspace_mlme(drv, 0);
+#endif /* CONFIG_CLIENT_MLME */
 
 	eloop_cancel_timeout(wpa_driver_nl80211_scan_timeout, drv, drv->ctx);
 
@@ -1252,6 +1656,9 @@
 	char *genie, *gpos, *gend;
 	u8 *tmp;
 
+	if (iwe->u.data.length == 0)
+		return;
+
 	gpos = genie = custom;
 	gend = genie + iwe->u.data.length;
 	if (gend > end) {
@@ -1284,7 +1691,7 @@
 		int bytes;
 		spos = custom + 7;
 		bytes = custom + clen - spos;
-		if (bytes & 1)
+		if (bytes & 1 || bytes == 0)
 			return;
 		bytes /= 2;
 		tmp = os_realloc(res->ie, res->ie_len + bytes);
@@ -1298,7 +1705,7 @@
 		int bytes;
 		spos = custom + 7;
 		bytes = custom + clen - spos;
-		if (bytes & 1)
+		if (bytes & 1 || bytes == 0)
 			return;
 		bytes /= 2;
 		tmp = os_realloc(res->ie, res->ie_len + bytes);
@@ -1584,7 +1991,7 @@
 				      const u8 *key, size_t key_len)
 {
 	struct wpa_driver_nl80211_data *drv = priv;
-	int ret = -1, err;
+	int err;
 	struct nl_msg *msg;
 
 	wpa_printf(MSG_DEBUG, "%s: alg=%d addr=%p key_idx=%d set_tx=%d "
@@ -1632,16 +2039,13 @@
 	NLA_PUT_U8(msg, NL80211_ATTR_KEY_IDX, key_idx);
 	NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
 
-	err = 0;
-	if (nl_send_auto_complete(drv->nl_handle, msg) < 0 ||
-	    (err = nl_wait_for_ack(drv->nl_handle)) < 0) {
+	err = send_and_recv_msgs(drv, msg, NULL, NULL);
+	if (err) {
 		wpa_printf(MSG_DEBUG, "nl80211: set_key failed; err=%d", err);
-		nlmsg_free(msg);
 		return -1;
 	}
 
 	if (set_tx && alg != WPA_ALG_NONE) {
-		nlmsg_free(msg);
 		msg = nlmsg_alloc();
 		if (msg == NULL)
 			return -1;
@@ -1652,21 +2056,18 @@
 		NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
 		NLA_PUT_FLAG(msg, NL80211_ATTR_KEY_DEFAULT);
 
-		err = 0;
-		if (nl_send_auto_complete(drv->nl_handle, msg) < 0 ||
-		    (err = nl_wait_for_ack(drv->nl_handle)) < 0) {
+		err = send_and_recv_msgs(drv, msg, NULL, NULL);
+		if (err) {
 			wpa_printf(MSG_DEBUG, "nl80211: set default key "
 				   "failed; err=%d", err);
-			nlmsg_free(msg);
 			return -1;
 		}
 	}
 
-	ret = 0;
+	return 0;
 
 nla_put_failure:
-	nlmsg_free(msg);
-	return ret;
+	return -ENOBUFS;
 }
 
 
@@ -1857,8 +2258,6 @@
 	    wpa_driver_nl80211_set_bssid(drv, NULL) < 0)
 		ret = -1;
 
-	if (wpa_driver_nl80211_set_mode(drv, params->mode) < 0)
-		ret = -1;
 	/* TODO: should consider getting wpa version and cipher/key_mgmt suites
 	 * from configuration, not from here, where only the selected suite is
 	 * available */
@@ -1961,17 +2360,17 @@
 	genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
 		    0, NL80211_CMD_SET_INTERFACE, 0);
 	NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
-	NLA_PUT_U32(msg, NL80211_ATTR_IFTYPE, NL80211_IFTYPE_AP);
-
-	if (nl_send_auto_complete(drv->nl_handle, msg) < 0 ||
-	    nl_wait_for_ack(drv->nl_handle) < 0)
+	NLA_PUT_U32(msg, NL80211_ATTR_IFTYPE,
+		    mode ? NL80211_IFTYPE_ADHOC : NL80211_IFTYPE_STATION);
+
+	ret = send_and_recv_msgs(drv, msg, NULL, NULL);
+	if (!ret)
+		return 0;
+	else
 		goto try_again;
 
-	nlmsg_free(msg);
-	return 0;
-
 nla_put_failure:
-	nlmsg_free(msg);
+	wpa_printf(MSG_ERROR, "nl80211: Failed to set interface mode");
 	return -1;
 
 try_again:
@@ -1983,12 +2382,21 @@
 		(void) wpa_driver_nl80211_set_ifflags(drv, flags & ~IFF_UP);
 
 		/* Try to set the mode again while the interface is down */
-		if (nl_send_auto_complete(drv->nl_handle, msg) < 0 ||
-		    nl_wait_for_ack(drv->nl_handle) < 0) {
+		msg = nlmsg_alloc();
+		if (!msg)
+			return -1;
+
+		genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
+			    0, NL80211_CMD_SET_INTERFACE, 0);
+		NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
+		NLA_PUT_U32(msg, NL80211_ATTR_IFTYPE,
+			    mode ? NL80211_IFTYPE_ADHOC :
+			    NL80211_IFTYPE_STATION);
+		ret = send_and_recv_msgs(drv, msg, NULL, NULL);
+		if (ret) {
 			wpa_printf(MSG_ERROR, "Failed to set interface %s "
 				   "mode", drv->ifname);
-		} else
-			ret = 0;
+		}
 
 		/* Ignore return value of get_ifflags to ensure that the device
 		 * is always up like it was before this function was called.
@@ -1997,7 +2405,6 @@
 		(void) wpa_driver_nl80211_set_ifflags(drv, flags | IFF_UP);
 	}
 
-	nlmsg_free(msg);
 	return ret;
 }
 
@@ -2075,6 +2482,354 @@
 	return wpa_driver_nl80211_send_oper_ifla(
 		drv, -1, state ? IF_OPER_UP : IF_OPER_DORMANT);
 }
+
+
+#ifdef CONFIG_CLIENT_MLME
+static int wpa_driver_nl80211_open_mlme(struct wpa_driver_nl80211_data *drv)
+{
+	if (wpa_driver_nl80211_set_userspace_mlme(drv, 1) < 0) {
+		wpa_printf(MSG_ERROR, "nl80211: Failed to enable userspace "
+			   "MLME");
+		return -1;
+	}
+	if (wpa_driver_nl80211_create_monitor_interface(drv)) {
+		wpa_printf(MSG_ERROR, "nl80211: Failed to create monitor "
+			   "interface");
+		return -1;
+	}
+	return 0;
+}
+#endif /* CONFIG_CLIENT_MLME */
+
+
+static int wpa_driver_nl80211_set_param(void *priv, const char *param)
+{
+#ifdef CONFIG_CLIENT_MLME
+	struct wpa_driver_nl80211_data *drv = priv;
+
+	if (param == NULL)
+		return 0;
+
+	wpa_printf(MSG_DEBUG, "%s: param='%s'", __func__, param);
+
+	if (os_strstr(param, "use_mlme=1")) {
+		wpa_printf(MSG_DEBUG, "nl80211: Using user space MLME");
+		drv->capa.flags |= WPA_DRIVER_FLAGS_USER_SPACE_MLME;
+
+		if (wpa_driver_nl80211_open_mlme(drv))
+			return -1;
+	}
+#endif /* CONFIG_CLIENT_MLME */
+
+	return 0;
+}
+
+
+#ifdef CONFIG_CLIENT_MLME
+
+struct phy_info_arg {
+	u16 *num_modes;
+	struct wpa_hw_modes *modes;
+};
+
+
+static int phy_info_handler(struct nl_msg *msg, void *arg)
+{
+	struct nlattr *tb_msg[NL80211_ATTR_MAX + 1];
+	struct genlmsghdr *gnlh = nlmsg_data(nlmsg_hdr(msg));
+	struct phy_info_arg *phy_info = arg;
+
+	struct nlattr *tb_band[NL80211_BAND_ATTR_MAX + 1];
+
+	struct nlattr *tb_freq[NL80211_FREQUENCY_ATTR_MAX + 1];
+	static struct nla_policy freq_policy[NL80211_FREQUENCY_ATTR_MAX + 1]
+		= {
+		[NL80211_FREQUENCY_ATTR_FREQ] = { .type = NLA_U32 },
+		[NL80211_FREQUENCY_ATTR_DISABLED] = { .type = NLA_FLAG },
+		[NL80211_FREQUENCY_ATTR_PASSIVE_SCAN] = { .type = NLA_FLAG },
+		[NL80211_FREQUENCY_ATTR_NO_IBSS] = { .type = NLA_FLAG },
+		[NL80211_FREQUENCY_ATTR_RADAR] = { .type = NLA_FLAG },
+	};
+
+	struct nlattr *tb_rate[NL80211_BITRATE_ATTR_MAX + 1];
+	static struct nla_policy rate_policy[NL80211_BITRATE_ATTR_MAX + 1] = {
+		[NL80211_BITRATE_ATTR_RATE] = { .type = NLA_U32 },
+		[NL80211_BITRATE_ATTR_2GHZ_SHORTPREAMBLE] =
+		{ .type = NLA_FLAG },
+	};
+
+	struct nlattr *nl_band;
+	struct nlattr *nl_freq;
+	struct nlattr *nl_rate;
+	int rem_band, rem_freq, rem_rate;
+	struct wpa_hw_modes *mode;
+	int idx, mode_is_set;
+
+	nla_parse(tb_msg, NL80211_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
+		  genlmsg_attrlen(gnlh, 0), NULL);
+
+	if (!tb_msg[NL80211_ATTR_WIPHY_BANDS])
+		return NL_SKIP;
+
+	nla_for_each_nested(nl_band, tb_msg[NL80211_ATTR_WIPHY_BANDS],
+			    rem_band) {
+		mode = os_realloc(phy_info->modes,
+				  (*phy_info->num_modes + 1) * sizeof(*mode));
+		if (!mode)
+			return NL_SKIP;
+		phy_info->modes = mode;
+
+		mode_is_set = 0;
+
+		mode = &phy_info->modes[*(phy_info->num_modes)];
+		os_memset(mode, 0, sizeof(*mode));
+		*(phy_info->num_modes) += 1;
+
+		nla_parse(tb_band, NL80211_BAND_ATTR_MAX, nla_data(nl_band),
+			  nla_len(nl_band), NULL);
+
+		nla_for_each_nested(nl_freq, tb_band[NL80211_BAND_ATTR_FREQS],
+				    rem_freq) {
+			nla_parse(tb_freq, NL80211_FREQUENCY_ATTR_MAX,
+				  nla_data(nl_freq), nla_len(nl_freq),
+				  freq_policy);
+			if (!tb_freq[NL80211_FREQUENCY_ATTR_FREQ])
+				continue;
+			mode->num_channels++;
+		}
+
+		mode->channels = os_zalloc(mode->num_channels *
+					   sizeof(struct wpa_channel_data));
+		if (!mode->channels)
+			return NL_SKIP;
+
+		idx = 0;
+
+		nla_for_each_nested(nl_freq, tb_band[NL80211_BAND_ATTR_FREQS],
+				    rem_freq) {
+			nla_parse(tb_freq, NL80211_FREQUENCY_ATTR_MAX,
+				  nla_data(nl_freq), nla_len(nl_freq),
+				  freq_policy);
+			if (!tb_freq[NL80211_FREQUENCY_ATTR_FREQ])
+				continue;
+
+			mode->channels[idx].freq = nla_get_u32(
+				tb_freq[NL80211_FREQUENCY_ATTR_FREQ]);
+			mode->channels[idx].flag |= WPA_CHAN_W_SCAN |
+				WPA_CHAN_W_ACTIVE_SCAN |
+				WPA_CHAN_W_IBSS;
+
+			if (!mode_is_set) {
+				/* crude heuristic */
+				if (mode->channels[idx].freq < 4000)
+					mode->mode = WPA_MODE_IEEE80211B;
+				else
+					mode->mode = WPA_MODE_IEEE80211A;
+				mode_is_set = 1;
+			}
+
+			/* crude heuristic */
+			if (mode->channels[idx].freq < 4000) {
+				if (mode->channels[idx].freq == 2848)
+					mode->channels[idx].chan = 14;
+				else
+					mode->channels[idx].chan =
+						(mode->channels[idx].freq -
+						 2407) / 5;
+			} else
+				mode->channels[idx].chan =
+					mode->channels[idx].freq / 5 - 1000;
+
+			if (tb_freq[NL80211_FREQUENCY_ATTR_DISABLED])
+				mode->channels[idx].flag &= ~WPA_CHAN_W_SCAN;
+			if (tb_freq[NL80211_FREQUENCY_ATTR_PASSIVE_SCAN])
+				mode->channels[idx].flag &=
+					~WPA_CHAN_W_ACTIVE_SCAN;
+			if (tb_freq[NL80211_FREQUENCY_ATTR_NO_IBSS])
+				mode->channels[idx].flag &= ~WPA_CHAN_W_IBSS;
+			idx++;
+		}
+
+		nla_for_each_nested(nl_rate, tb_band[NL80211_BAND_ATTR_RATES],
+				    rem_rate) {
+			nla_parse(tb_rate, NL80211_BITRATE_ATTR_MAX,
+				  nla_data(nl_rate), nla_len(nl_rate),
+				  rate_policy);
+			if (!tb_rate[NL80211_BITRATE_ATTR_RATE])
+				continue;
+			mode->num_rates++;
+		}
+
+		mode->rates = os_zalloc(mode->num_rates *
+					sizeof(struct wpa_rate_data));
+		if (!mode->rates)
+			return NL_SKIP;
+
+		idx = 0;
+
+		nla_for_each_nested(nl_rate, tb_band[NL80211_BAND_ATTR_RATES],
+				    rem_rate) {
+			nla_parse(tb_rate, NL80211_BITRATE_ATTR_MAX,
+				  nla_data(nl_rate), nla_len(nl_rate),
+				  rate_policy);
+			if (!tb_rate[NL80211_BITRATE_ATTR_RATE])
+				continue;
+			mode->rates[idx].rate = nla_get_u32(
+				tb_rate[NL80211_BITRATE_ATTR_RATE]);
+
+			/* crude heuristic */
+			if (mode->mode == WPA_MODE_IEEE80211B &&
+			    mode->rates[idx].rate > 200)
+				mode->mode = WPA_MODE_IEEE80211G;
+
+			if (tb_rate[NL80211_BITRATE_ATTR_2GHZ_SHORTPREAMBLE])
+				mode->rates[idx].flags |= WPA_RATE_PREAMBLE2;
+
+			idx++;
+		}
+	}
+
+	return NL_SKIP;
+}
+
+
+static struct wpa_hw_modes *
+wpa_driver_nl80211_get_hw_feature_data(void *priv, u16 *num_modes, u16 *flags)
+{
+	struct wpa_driver_nl80211_data *drv = priv;
+	struct nl_msg *msg;
+	struct phy_info_arg result = {
+		.num_modes = num_modes,
+		.modes = NULL,
+	};
+
+	*num_modes = 0;
+	*flags = 0;
+
+	msg = nlmsg_alloc();
+	if (!msg)
+		return NULL;
+
+	genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
+		    0, NL80211_CMD_GET_WIPHY, 0);
+
+	NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
+
+	if (send_and_recv_msgs(drv, msg, phy_info_handler, &result) == 0)
+		return result.modes;
+nla_put_failure:
+	return NULL;
+}
+
+
+static int wpa_driver_nl80211_set_channel(void *priv, wpa_hw_mode phymode,
+					  int chan, int freq)
+{
+	return wpa_driver_nl80211_set_freq(priv, freq);
+}
+
+
+static int wpa_driver_nl80211_send_mlme(void *priv, const u8 *data,
+					size_t data_len)
+{
+	struct wpa_driver_nl80211_data *drv = priv;
+	__u8 rtap_hdr[] = {
+		0x00, 0x00, /* radiotap version */
+		0x0e, 0x00, /* radiotap length */
+		0x02, 0xc0, 0x00, 0x00, /* bmap: flags, tx and rx flags */
+		0x0c,       /* F_WEP | F_FRAG (encrypt/fragment if required) */
+		0x00,       /* padding */
+		0x00, 0x00, /* RX and TX flags to indicate that */
+		0x00, 0x00, /* this is the injected frame directly */
+	};
+	struct iovec iov[2] = {
+		{
+			.iov_base = &rtap_hdr,
+			.iov_len = sizeof(rtap_hdr),
+		},
+		{
+			.iov_base = (void *) data,
+			.iov_len = data_len,
+		}
+	};
+	struct msghdr msg = {
+		.msg_name = NULL,
+		.msg_namelen = 0,
+		.msg_iov = iov,
+		.msg_iovlen = 2,
+		.msg_control = NULL,
+		.msg_controllen = 0,
+		.msg_flags = 0,
+	};
+
+	if (sendmsg(drv->monitor_sock, &msg, 0) < 0) {
+		perror("send[MLME]");
+		return -1;
+	}
+
+	return 0;
+}
+
+
+static int wpa_driver_nl80211_mlme_add_sta(void *priv, const u8 *addr,
+					   const u8 *supp_rates,
+					   size_t supp_rates_len)
+{
+	struct wpa_driver_nl80211_data *drv = priv;
+	struct nl_msg *msg;
+	int ret = -1;
+
+	msg = nlmsg_alloc();
+	if (!msg)
+		return -ENOMEM;
+
+	genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
+		    0, NL80211_CMD_NEW_STATION, 0);
+
+	NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
+	NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, addr);
+	/* TODO: Get proper Association ID and listen interval */
+	NLA_PUT_U16(msg, NL80211_ATTR_STA_AID, 1);
+	NLA_PUT(msg, NL80211_ATTR_STA_SUPPORTED_RATES, supp_rates_len,
+		supp_rates);
+	NLA_PUT_U16(msg, NL80211_ATTR_STA_LISTEN_INTERVAL, 1);
+
+	ret = send_and_recv_msgs(drv, msg, NULL, NULL);
+	/* ignore EEXIST, this happens if a STA associates while associated */
+	if (ret == -EEXIST || ret >= 0)
+		ret = 0;
+
+nla_put_failure:
+	return ret;
+}
+
+
+static int wpa_driver_nl80211_mlme_remove_sta(void *priv, const u8 *addr)
+{
+	struct wpa_driver_nl80211_data *drv = priv;
+	struct nl_msg *msg;
+	int ret = -1;
+
+	msg = nlmsg_alloc();
+	if (!msg)
+		return -ENOMEM;
+
+	genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0,
+		    0, NL80211_CMD_DEL_STATION, 0);
+
+	NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
+	NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, addr);
+
+	ret = 0;
+
+	ret = send_and_recv_msgs(drv, msg, NULL, NULL);
+	return ret;
+
+nla_put_failure:
+	return -ENOBUFS;
+}
+
+#endif /* CONFIG_CLIENT_MLME */
 
 
 const struct wpa_driver_ops wpa_driver_nl80211_ops = {
@@ -2090,13 +2845,24 @@
 	.get_scan_results2 = wpa_driver_nl80211_get_scan_results,
 	.deauthenticate = wpa_driver_nl80211_deauthenticate,
 	.disassociate = wpa_driver_nl80211_disassociate,
+	.set_mode = wpa_driver_nl80211_set_mode,
 	.associate = wpa_driver_nl80211_associate,
 	.set_auth_alg = wpa_driver_nl80211_set_auth_alg,
 	.init = wpa_driver_nl80211_init,
 	.deinit = wpa_driver_nl80211_deinit,
+	.set_param = wpa_driver_nl80211_set_param,
 	.add_pmkid = wpa_driver_nl80211_add_pmkid,
 	.remove_pmkid = wpa_driver_nl80211_remove_pmkid,
 	.flush_pmkid = wpa_driver_nl80211_flush_pmkid,
 	.get_capa = wpa_driver_nl80211_get_capa,
 	.set_operstate = wpa_driver_nl80211_set_operstate,
+#ifdef CONFIG_CLIENT_MLME
+	.get_hw_feature_data = wpa_driver_nl80211_get_hw_feature_data,
+	.set_channel = wpa_driver_nl80211_set_channel,
+	.set_ssid = wpa_driver_nl80211_set_ssid,
+	.set_bssid = wpa_driver_nl80211_set_bssid,
+	.send_mlme = wpa_driver_nl80211_send_mlme,
+	.mlme_add_sta = wpa_driver_nl80211_mlme_add_sta,
+	.mlme_remove_sta = wpa_driver_nl80211_mlme_remove_sta,
+#endif /* CONFIG_CLIENT_MLME */
 };

Modified: wpasupplicant/branches/upstream/current/src/drivers/driver_privsep.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/drivers/driver_privsep.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/drivers/driver_privsep.c (original)
+++ wpasupplicant/branches/upstream/current/src/drivers/driver_privsep.c Wed Oct  8 21:24:04 2008
@@ -723,6 +723,15 @@
 	struct wpa_driver_privsep_data *drv = priv;
 	wpa_printf(MSG_DEBUG, "%s", __func__);
 	return drv->own_addr;
+}
+
+
+static int wpa_driver_privsep_set_mode(void *priv, int mode)
+{
+	struct wpa_driver_privsep_data *drv = priv;
+	wpa_printf(MSG_DEBUG, "%s mode=%d", __func__, mode);
+	return wpa_priv_cmd(drv, PRIVSEP_CMD_SET_MODE, &mode, sizeof(mode),
+			    NULL, NULL);
 }
 
 
@@ -763,7 +772,9 @@
 	NULL /* mlme_remove_sta */,
 	NULL /* update_ft_ies */,
 	NULL /* send_ft_action */,
-	wpa_driver_privsep_get_scan_results2
+	wpa_driver_privsep_get_scan_results2,
+	NULL /* set_probe_req_ie */,
+	wpa_driver_privsep_set_mode
 };
 
 

Modified: wpasupplicant/branches/upstream/current/src/drivers/driver_ralink.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/drivers/driver_ralink.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/drivers/driver_ralink.c (original)
+++ wpasupplicant/branches/upstream/current/src/drivers/driver_ralink.c Wed Oct  8 21:24:04 2008
@@ -288,8 +288,9 @@
 	os_memset(&event, 0, sizeof(event));
 	for (i = 0; i < pmkid->NumCandidates; i++) {
 		PMKID_CANDIDATE *p = &pmkid->CandidateList[i];
-		wpa_printf(MSG_DEBUG, "RALINK: %d: " MACSTR " Flags 0x%x",
-			   i, MAC2STR(p->BSSID), (int) p->Flags);
+		wpa_printf(MSG_DEBUG, "RALINK: %lu: " MACSTR " Flags 0x%x",
+			   (unsigned long) i, MAC2STR(p->BSSID),
+			   (int) p->Flags);
 		os_memcpy(event.pmkid_candidate.bssid, p->BSSID, ETH_ALEN);
 		event.pmkid_candidate.index = i;
 		event.pmkid_candidate.preauth =

Modified: wpasupplicant/branches/upstream/current/src/drivers/driver_test.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/drivers/driver_test.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/drivers/driver_test.c (original)
+++ wpasupplicant/branches/upstream/current/src/drivers/driver_test.c Wed Oct  8 21:24:04 2008
@@ -453,9 +453,11 @@
 				 socklen_t fromlen,
 				 const u8 *data, size_t data_len)
 {
+#ifdef CONFIG_CLIENT_MLME
 	struct ieee80211_rx_status rx_status;
 	os_memset(&rx_status, 0, sizeof(rx_status));
 	wpa_supplicant_sta_rx(drv->ctx, data, data_len, &rx_status);
+#endif /* CONFIG_CLIENT_MLME */
 }
 
 
@@ -982,5 +984,6 @@
 	NULL /* update_ft_ies */,
 	NULL /* send_ft_action */,
 	wpa_driver_test_get_scan_results2,
-	NULL /* set_probe_req_ie */
+	NULL /* set_probe_req_ie */,
+	NULL /* set_mode */
 };

Modified: wpasupplicant/branches/upstream/current/src/drivers/driver_wext.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/drivers/driver_wext.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/drivers/driver_wext.c (original)
+++ wpasupplicant/branches/upstream/current/src/drivers/driver_wext.c Wed Oct  8 21:24:04 2008
@@ -652,12 +652,20 @@
 			}
 			break;
 		case IWEVMICHAELMICFAILURE:
+			if (custom + iwe->u.data.length > end) {
+				wpa_printf(MSG_DEBUG, "WEXT: Invalid "
+					   "IWEVMICHAELMICFAILURE length");
+				return;
+			}
 			wpa_driver_wext_event_wireless_michaelmicfailure(
 				ctx, custom, iwe->u.data.length);
 			break;
 		case IWEVCUSTOM:
-			if (custom + iwe->u.data.length > end)
+			if (custom + iwe->u.data.length > end) {
+				wpa_printf(MSG_DEBUG, "WEXT: Invalid "
+					   "IWEVCUSTOM length");
 				return;
+			}
 			buf = os_malloc(iwe->u.data.length + 1);
 			if (buf == NULL)
 				return;
@@ -673,14 +681,29 @@
 			wpa_supplicant_event(ctx, EVENT_SCAN_RESULTS, NULL);
 			break;
 		case IWEVASSOCREQIE:
+			if (custom + iwe->u.data.length > end) {
+				wpa_printf(MSG_DEBUG, "WEXT: Invalid "
+					   "IWEVASSOCREQIE length");
+				return;
+			}
 			wpa_driver_wext_event_wireless_assocreqie(
 				drv, custom, iwe->u.data.length);
 			break;
 		case IWEVASSOCRESPIE:
+			if (custom + iwe->u.data.length > end) {
+				wpa_printf(MSG_DEBUG, "WEXT: Invalid "
+					   "IWEVASSOCRESPIE length");
+				return;
+			}
 			wpa_driver_wext_event_wireless_assocrespie(
 				drv, custom, iwe->u.data.length);
 			break;
 		case IWEVPMKIDCAND:
+			if (custom + iwe->u.data.length > end) {
+				wpa_printf(MSG_DEBUG, "WEXT: Invalid "
+					   "IWEVPMKIDCAND length");
+				return;
+			}
 			wpa_driver_wext_event_wireless_pmkidcand(
 				drv, custom, iwe->u.data.length);
 			break;
@@ -1447,6 +1470,9 @@
 	char *genie, *gpos, *gend;
 	u8 *tmp;
 
+	if (iwe->u.data.length == 0)
+		return;
+
 	gpos = genie = custom;
 	gend = genie + iwe->u.data.length;
 	if (gend > end) {
@@ -1479,7 +1505,7 @@
 		int bytes;
 		spos = custom + 7;
 		bytes = custom + clen - spos;
-		if (bytes & 1)
+		if (bytes & 1 || bytes == 0)
 			return;
 		bytes /= 2;
 		tmp = os_realloc(res->ie, res->ie_len + bytes);
@@ -1493,7 +1519,7 @@
 		int bytes;
 		spos = custom + 7;
 		bytes = custom + clen - spos;
-		if (bytes & 1)
+		if (bytes & 1 || bytes == 0)
 			return;
 		bytes /= 2;
 		tmp = os_realloc(res->ie, res->ie_len + bytes);
@@ -2180,8 +2206,6 @@
 	    wpa_driver_wext_set_bssid(drv, NULL) < 0)
 		ret = -1;
 
-	if (wpa_driver_wext_set_mode(drv, params->mode) < 0)
-		ret = -1;
 	/* TODO: should consider getting wpa version and cipher/key_mgmt suites
 	 * from configuration, not from here, where only the selected suite is
 	 * available */
@@ -2756,6 +2780,7 @@
 	.get_scan_results2 = wpa_driver_wext_get_scan_results,
 	.deauthenticate = wpa_driver_wext_deauthenticate,
 	.disassociate = wpa_driver_wext_disassociate,
+	.set_mode = wpa_driver_wext_set_mode,
 	.associate = wpa_driver_wext_associate,
 	.set_auth_alg = wpa_driver_wext_set_auth_alg,
 	.init = wpa_driver_wext_init,

Added: wpasupplicant/branches/upstream/current/src/drivers/radiotap.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/drivers/radiotap.c?rev=1266&op=file
==============================================================================
--- wpasupplicant/branches/upstream/current/src/drivers/radiotap.c (added)
+++ wpasupplicant/branches/upstream/current/src/drivers/radiotap.c Wed Oct  8 21:24:04 2008
@@ -1,0 +1,287 @@
+/*
+ * Radiotap parser
+ *
+ * Copyright 2007		Andy Green <andy at warmcat.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ *
+ * Alternatively, this software may be distributed under the terms of BSD
+ * license.
+ *
+ * See README and COPYING for more details.
+ *
+ *
+ * Modified for userspace by Johannes Berg <johannes at sipsolutions.net>
+ * I only modified some things on top to ease syncing should bugs be found.
+ */
+
+#include "includes.h"
+
+#include "common.h"
+#include "radiotap_iter.h"
+
+#define le16_to_cpu		le_to_host16
+#define le32_to_cpu		le_to_host32
+#define __le32			uint32_t
+#define ulong			unsigned long
+#define unlikely(cond)		(cond)
+#define get_unaligned(p)					\
+({								\
+	struct packed_dummy_struct {				\
+		typeof(*(p)) __val;				\
+	} __attribute__((packed)) *__ptr = (void *) (p);	\
+								\
+	__ptr->__val;						\
+})
+
+/* function prototypes and related defs are in radiotap_iter.h */
+
+/**
+ * ieee80211_radiotap_iterator_init - radiotap parser iterator initialization
+ * @iterator: radiotap_iterator to initialize
+ * @radiotap_header: radiotap header to parse
+ * @max_length: total length we can parse into (eg, whole packet length)
+ *
+ * Returns: 0 or a negative error code if there is a problem.
+ *
+ * This function initializes an opaque iterator struct which can then
+ * be passed to ieee80211_radiotap_iterator_next() to visit every radiotap
+ * argument which is present in the header.  It knows about extended
+ * present headers and handles them.
+ *
+ * How to use:
+ * call __ieee80211_radiotap_iterator_init() to init a semi-opaque iterator
+ * struct ieee80211_radiotap_iterator (no need to init the struct beforehand)
+ * checking for a good 0 return code.  Then loop calling
+ * __ieee80211_radiotap_iterator_next()... it returns either 0,
+ * -ENOENT if there are no more args to parse, or -EINVAL if there is a problem.
+ * The iterator's @this_arg member points to the start of the argument
+ * associated with the current argument index that is present, which can be
+ * found in the iterator's @this_arg_index member.  This arg index corresponds
+ * to the IEEE80211_RADIOTAP_... defines.
+ *
+ * Radiotap header length:
+ * You can find the CPU-endian total radiotap header length in
+ * iterator->max_length after executing ieee80211_radiotap_iterator_init()
+ * successfully.
+ *
+ * Alignment Gotcha:
+ * You must take care when dereferencing iterator.this_arg
+ * for multibyte types... the pointer is not aligned.  Use
+ * get_unaligned((type *)iterator.this_arg) to dereference
+ * iterator.this_arg for type "type" safely on all arches.
+ *
+ * Example code:
+ * See Documentation/networking/radiotap-headers.txt
+ */
+
+int ieee80211_radiotap_iterator_init(
+    struct ieee80211_radiotap_iterator *iterator,
+    struct ieee80211_radiotap_header *radiotap_header,
+    int max_length)
+{
+	/* Linux only supports version 0 radiotap format */
+	if (radiotap_header->it_version)
+		return -EINVAL;
+
+	/* sanity check for allowed length and radiotap length field */
+	if (max_length < le16_to_cpu(get_unaligned(&radiotap_header->it_len)))
+		return -EINVAL;
+
+	iterator->rtheader = radiotap_header;
+	iterator->max_length = le16_to_cpu(get_unaligned(
+						&radiotap_header->it_len));
+	iterator->arg_index = 0;
+	iterator->bitmap_shifter = le32_to_cpu(get_unaligned(
+						&radiotap_header->it_present));
+	iterator->arg = (u8 *)radiotap_header + sizeof(*radiotap_header);
+	iterator->this_arg = NULL;
+
+	/* find payload start allowing for extended bitmap(s) */
+
+	if (unlikely(iterator->bitmap_shifter & (1<<IEEE80211_RADIOTAP_EXT))) {
+		while (le32_to_cpu(get_unaligned((__le32 *)iterator->arg)) &
+				   (1<<IEEE80211_RADIOTAP_EXT)) {
+			iterator->arg += sizeof(u32);
+
+			/*
+			 * check for insanity where the present bitmaps
+			 * keep claiming to extend up to or even beyond the
+			 * stated radiotap header length
+			 */
+
+			if (((ulong)iterator->arg - (ulong)iterator->rtheader)
+			    > (ulong)iterator->max_length)
+				return -EINVAL;
+		}
+
+		iterator->arg += sizeof(u32);
+
+		/*
+		 * no need to check again for blowing past stated radiotap
+		 * header length, because ieee80211_radiotap_iterator_next
+		 * checks it before it is dereferenced
+		 */
+	}
+
+	/* we are all initialized happily */
+
+	return 0;
+}
+
+
+/**
+ * ieee80211_radiotap_iterator_next - return next radiotap parser iterator arg
+ * @iterator: radiotap_iterator to move to next arg (if any)
+ *
+ * Returns: 0 if there is an argument to handle,
+ * -ENOENT if there are no more args or -EINVAL
+ * if there is something else wrong.
+ *
+ * This function provides the next radiotap arg index (IEEE80211_RADIOTAP_*)
+ * in @this_arg_index and sets @this_arg to point to the
+ * payload for the field.  It takes care of alignment handling and extended
+ * present fields.  @this_arg can be changed by the caller (eg,
+ * incremented to move inside a compound argument like
+ * IEEE80211_RADIOTAP_CHANNEL).  The args pointed to are in
+ * little-endian format whatever the endianess of your CPU.
+ *
+ * Alignment Gotcha:
+ * You must take care when dereferencing iterator.this_arg
+ * for multibyte types... the pointer is not aligned.  Use
+ * get_unaligned((type *)iterator.this_arg) to dereference
+ * iterator.this_arg for type "type" safely on all arches.
+ */
+
+int ieee80211_radiotap_iterator_next(
+    struct ieee80211_radiotap_iterator *iterator)
+{
+
+	/*
+	 * small length lookup table for all radiotap types we heard of
+	 * starting from b0 in the bitmap, so we can walk the payload
+	 * area of the radiotap header
+	 *
+	 * There is a requirement to pad args, so that args
+	 * of a given length must begin at a boundary of that length
+	 * -- but note that compound args are allowed (eg, 2 x u16
+	 * for IEEE80211_RADIOTAP_CHANNEL) so total arg length is not
+	 * a reliable indicator of alignment requirement.
+	 *
+	 * upper nybble: content alignment for arg
+	 * lower nybble: content length for arg
+	 */
+
+	static const u8 rt_sizes[] = {
+		[IEEE80211_RADIOTAP_TSFT] = 0x88,
+		[IEEE80211_RADIOTAP_FLAGS] = 0x11,
+		[IEEE80211_RADIOTAP_RATE] = 0x11,
+		[IEEE80211_RADIOTAP_CHANNEL] = 0x24,
+		[IEEE80211_RADIOTAP_FHSS] = 0x22,
+		[IEEE80211_RADIOTAP_DBM_ANTSIGNAL] = 0x11,
+		[IEEE80211_RADIOTAP_DBM_ANTNOISE] = 0x11,
+		[IEEE80211_RADIOTAP_LOCK_QUALITY] = 0x22,
+		[IEEE80211_RADIOTAP_TX_ATTENUATION] = 0x22,
+		[IEEE80211_RADIOTAP_DB_TX_ATTENUATION] = 0x22,
+		[IEEE80211_RADIOTAP_DBM_TX_POWER] = 0x11,
+		[IEEE80211_RADIOTAP_ANTENNA] = 0x11,
+		[IEEE80211_RADIOTAP_DB_ANTSIGNAL] = 0x11,
+		[IEEE80211_RADIOTAP_DB_ANTNOISE] = 0x11,
+		[IEEE80211_RADIOTAP_RX_FLAGS] = 0x22,
+		[IEEE80211_RADIOTAP_TX_FLAGS] = 0x22,
+		[IEEE80211_RADIOTAP_RTS_RETRIES] = 0x11,
+		[IEEE80211_RADIOTAP_DATA_RETRIES] = 0x11,
+		/*
+		 * add more here as they are defined in
+		 * include/net/ieee80211_radiotap.h
+		 */
+	};
+
+	/*
+	 * for every radiotap entry we can at
+	 * least skip (by knowing the length)...
+	 */
+
+	while (iterator->arg_index < (int) sizeof(rt_sizes)) {
+		int hit = 0;
+		int pad;
+
+		if (!(iterator->bitmap_shifter & 1))
+			goto next_entry; /* arg not present */
+
+		/*
+		 * arg is present, account for alignment padding
+		 *  8-bit args can be at any alignment
+		 * 16-bit args must start on 16-bit boundary
+		 * 32-bit args must start on 32-bit boundary
+		 * 64-bit args must start on 64-bit boundary
+		 *
+		 * note that total arg size can differ from alignment of
+		 * elements inside arg, so we use upper nybble of length
+		 * table to base alignment on
+		 *
+		 * also note: these alignments are ** relative to the
+		 * start of the radiotap header **.  There is no guarantee
+		 * that the radiotap header itself is aligned on any
+		 * kind of boundary.
+		 *
+		 * the above is why get_unaligned() is used to dereference
+		 * multibyte elements from the radiotap area
+		 */
+
+		pad = (((ulong)iterator->arg) -
+			((ulong)iterator->rtheader)) &
+			((rt_sizes[iterator->arg_index] >> 4) - 1);
+
+		if (pad)
+			iterator->arg +=
+				(rt_sizes[iterator->arg_index] >> 4) - pad;
+
+		/*
+		 * this is what we will return to user, but we need to
+		 * move on first so next call has something fresh to test
+		 */
+		iterator->this_arg_index = iterator->arg_index;
+		iterator->this_arg = iterator->arg;
+		hit = 1;
+
+		/* internally move on the size of this arg */
+		iterator->arg += rt_sizes[iterator->arg_index] & 0x0f;
+
+		/*
+		 * check for insanity where we are given a bitmap that
+		 * claims to have more arg content than the length of the
+		 * radiotap section.  We will normally end up equalling this
+		 * max_length on the last arg, never exceeding it.
+		 */
+
+		if (((ulong)iterator->arg - (ulong)iterator->rtheader) >
+		    (ulong) iterator->max_length)
+			return -EINVAL;
+
+	next_entry:
+		iterator->arg_index++;
+		if (unlikely((iterator->arg_index & 31) == 0)) {
+			/* completed current u32 bitmap */
+			if (iterator->bitmap_shifter & 1) {
+				/* b31 was set, there is more */
+				/* move to next u32 bitmap */
+				iterator->bitmap_shifter = le32_to_cpu(
+					get_unaligned(iterator->next_bitmap));
+				iterator->next_bitmap++;
+			} else
+				/* no more bitmaps: end */
+				iterator->arg_index = sizeof(rt_sizes);
+		} else /* just try the next bit */
+			iterator->bitmap_shifter >>= 1;
+
+		/* if we found a valid arg earlier, return it now */
+		if (hit)
+			return 0;
+	}
+
+	/* we don't know how to handle any more args, we're done */
+	return -ENOENT;
+}

Added: wpasupplicant/branches/upstream/current/src/drivers/radiotap.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/drivers/radiotap.h?rev=1266&op=file
==============================================================================
--- wpasupplicant/branches/upstream/current/src/drivers/radiotap.h (added)
+++ wpasupplicant/branches/upstream/current/src/drivers/radiotap.h Wed Oct  8 21:24:04 2008
@@ -1,0 +1,242 @@
+/* $FreeBSD: src/sys/net80211/ieee80211_radiotap.h,v 1.5 2005/01/22 20:12:05 sam Exp $ */
+/* $NetBSD: ieee80211_radiotap.h,v 1.11 2005/06/22 06:16:02 dyoung Exp $ */
+
+/*-
+ * Copyright (c) 2003, 2004 David Young.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. The name of David Young may not be used to endorse or promote
+ *    products derived from this software without specific prior
+ *    written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY DAVID YOUNG ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+ * PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL DAVID
+ * YOUNG BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
+ * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
+ * OF SUCH DAMAGE.
+ */
+
+/*
+ * Modifications to fit into the linux IEEE 802.11 stack,
+ * Mike Kershaw (dragorn at kismetwireless.net)
+ */
+
+#ifndef IEEE80211RADIOTAP_H
+#define IEEE80211RADIOTAP_H
+
+#include <stdint.h>
+
+/* Base version of the radiotap packet header data */
+#define PKTHDR_RADIOTAP_VERSION		0
+
+/* A generic radio capture format is desirable. There is one for
+ * Linux, but it is neither rigidly defined (there were not even
+ * units given for some fields) nor easily extensible.
+ *
+ * I suggest the following extensible radio capture format. It is
+ * based on a bitmap indicating which fields are present.
+ *
+ * I am trying to describe precisely what the application programmer
+ * should expect in the following, and for that reason I tell the
+ * units and origin of each measurement (where it applies), or else I
+ * use sufficiently weaselly language ("is a monotonically nondecreasing
+ * function of...") that I cannot set false expectations for lawyerly
+ * readers.
+ */
+
+/* The radio capture header precedes the 802.11 header.
+ * All data in the header is little endian on all platforms.
+ */
+struct ieee80211_radiotap_header {
+	uint8_t it_version;	/* Version 0. Only increases
+				 * for drastic changes,
+				 * introduction of compatible
+				 * new fields does not count.
+				 */
+	uint8_t it_pad;
+	uint16_t it_len;	/* length of the whole
+				 * header in bytes, including
+				 * it_version, it_pad,
+				 * it_len, and data fields.
+				 */
+	uint32_t it_present;	/* A bitmap telling which
+				 * fields are present. Set bit 31
+				 * (0x80000000) to extend the
+				 * bitmap by another 32 bits.
+				 * Additional extensions are made
+				 * by setting bit 31.
+				 */
+};
+
+/* Name                                 Data type    Units
+ * ----                                 ---------    -----
+ *
+ * IEEE80211_RADIOTAP_TSFT              __le64       microseconds
+ *
+ *      Value in microseconds of the MAC's 64-bit 802.11 Time
+ *      Synchronization Function timer when the first bit of the
+ *      MPDU arrived at the MAC. For received frames, only.
+ *
+ * IEEE80211_RADIOTAP_CHANNEL           2 x uint16_t   MHz, bitmap
+ *
+ *      Tx/Rx frequency in MHz, followed by flags (see below).
+ *
+ * IEEE80211_RADIOTAP_FHSS              uint16_t       see below
+ *
+ *      For frequency-hopping radios, the hop set (first byte)
+ *      and pattern (second byte).
+ *
+ * IEEE80211_RADIOTAP_RATE              u8           500kb/s
+ *
+ *      Tx/Rx data rate
+ *
+ * IEEE80211_RADIOTAP_DBM_ANTSIGNAL     s8           decibels from
+ *                                                   one milliwatt (dBm)
+ *
+ *      RF signal power at the antenna, decibel difference from
+ *      one milliwatt.
+ *
+ * IEEE80211_RADIOTAP_DBM_ANTNOISE      s8           decibels from
+ *                                                   one milliwatt (dBm)
+ *
+ *      RF noise power at the antenna, decibel difference from one
+ *      milliwatt.
+ *
+ * IEEE80211_RADIOTAP_DB_ANTSIGNAL      u8           decibel (dB)
+ *
+ *      RF signal power at the antenna, decibel difference from an
+ *      arbitrary, fixed reference.
+ *
+ * IEEE80211_RADIOTAP_DB_ANTNOISE       u8           decibel (dB)
+ *
+ *      RF noise power at the antenna, decibel difference from an
+ *      arbitrary, fixed reference point.
+ *
+ * IEEE80211_RADIOTAP_LOCK_QUALITY      uint16_t       unitless
+ *
+ *      Quality of Barker code lock. Unitless. Monotonically
+ *      nondecreasing with "better" lock strength. Called "Signal
+ *      Quality" in datasheets.  (Is there a standard way to measure
+ *      this?)
+ *
+ * IEEE80211_RADIOTAP_TX_ATTENUATION    uint16_t       unitless
+ *
+ *      Transmit power expressed as unitless distance from max
+ *      power set at factory calibration.  0 is max power.
+ *      Monotonically nondecreasing with lower power levels.
+ *
+ * IEEE80211_RADIOTAP_DB_TX_ATTENUATION uint16_t       decibels (dB)
+ *
+ *      Transmit power expressed as decibel distance from max power
+ *      set at factory calibration.  0 is max power.  Monotonically
+ *      nondecreasing with lower power levels.
+ *
+ * IEEE80211_RADIOTAP_DBM_TX_POWER      s8           decibels from
+ *                                                   one milliwatt (dBm)
+ *
+ *      Transmit power expressed as dBm (decibels from a 1 milliwatt
+ *      reference). This is the absolute power level measured at
+ *      the antenna port.
+ *
+ * IEEE80211_RADIOTAP_FLAGS             u8           bitmap
+ *
+ *      Properties of transmitted and received frames. See flags
+ *      defined below.
+ *
+ * IEEE80211_RADIOTAP_ANTENNA           u8           antenna index
+ *
+ *      Unitless indication of the Rx/Tx antenna for this packet.
+ *      The first antenna is antenna 0.
+ *
+ * IEEE80211_RADIOTAP_RX_FLAGS          uint16_t       bitmap
+ *
+ *     Properties of received frames. See flags defined below.
+ *
+ * IEEE80211_RADIOTAP_TX_FLAGS          uint16_t       bitmap
+ *
+ *     Properties of transmitted frames. See flags defined below.
+ *
+ * IEEE80211_RADIOTAP_RTS_RETRIES       u8           data
+ *
+ *     Number of rts retries a transmitted frame used.
+ *
+ * IEEE80211_RADIOTAP_DATA_RETRIES      u8           data
+ *
+ *     Number of unicast retries a transmitted frame used.
+ *
+ */
+enum ieee80211_radiotap_type {
+	IEEE80211_RADIOTAP_TSFT = 0,
+	IEEE80211_RADIOTAP_FLAGS = 1,
+	IEEE80211_RADIOTAP_RATE = 2,
+	IEEE80211_RADIOTAP_CHANNEL = 3,
+	IEEE80211_RADIOTAP_FHSS = 4,
+	IEEE80211_RADIOTAP_DBM_ANTSIGNAL = 5,
+	IEEE80211_RADIOTAP_DBM_ANTNOISE = 6,
+	IEEE80211_RADIOTAP_LOCK_QUALITY = 7,
+	IEEE80211_RADIOTAP_TX_ATTENUATION = 8,
+	IEEE80211_RADIOTAP_DB_TX_ATTENUATION = 9,
+	IEEE80211_RADIOTAP_DBM_TX_POWER = 10,
+	IEEE80211_RADIOTAP_ANTENNA = 11,
+	IEEE80211_RADIOTAP_DB_ANTSIGNAL = 12,
+	IEEE80211_RADIOTAP_DB_ANTNOISE = 13,
+	IEEE80211_RADIOTAP_RX_FLAGS = 14,
+	IEEE80211_RADIOTAP_TX_FLAGS = 15,
+	IEEE80211_RADIOTAP_RTS_RETRIES = 16,
+	IEEE80211_RADIOTAP_DATA_RETRIES = 17,
+	IEEE80211_RADIOTAP_EXT = 31
+};
+
+/* Channel flags. */
+#define	IEEE80211_CHAN_TURBO	0x0010	/* Turbo channel */
+#define	IEEE80211_CHAN_CCK	0x0020	/* CCK channel */
+#define	IEEE80211_CHAN_OFDM	0x0040	/* OFDM channel */
+#define	IEEE80211_CHAN_2GHZ	0x0080	/* 2 GHz spectrum channel. */
+#define	IEEE80211_CHAN_5GHZ	0x0100	/* 5 GHz spectrum channel */
+#define	IEEE80211_CHAN_PASSIVE	0x0200	/* Only passive scan allowed */
+#define	IEEE80211_CHAN_DYN	0x0400	/* Dynamic CCK-OFDM channel */
+#define	IEEE80211_CHAN_GFSK	0x0800	/* GFSK channel (FHSS PHY) */
+
+/* For IEEE80211_RADIOTAP_FLAGS */
+#define	IEEE80211_RADIOTAP_F_CFP	0x01	/* sent/received
+						 * during CFP
+						 */
+#define	IEEE80211_RADIOTAP_F_SHORTPRE	0x02	/* sent/received
+						 * with short
+						 * preamble
+						 */
+#define	IEEE80211_RADIOTAP_F_WEP	0x04	/* sent/received
+						 * with WEP encryption
+						 */
+#define	IEEE80211_RADIOTAP_F_FRAG	0x08	/* sent/received
+						 * with fragmentation
+						 */
+#define	IEEE80211_RADIOTAP_F_FCS	0x10	/* frame includes FCS */
+#define	IEEE80211_RADIOTAP_F_DATAPAD	0x20	/* frame has padding between
+						 * 802.11 header and payload
+						 * (to 32-bit boundary)
+						 */
+/* For IEEE80211_RADIOTAP_RX_FLAGS */
+#define IEEE80211_RADIOTAP_F_RX_BADFCS	0x0001	/* frame failed crc check */
+
+/* For IEEE80211_RADIOTAP_TX_FLAGS */
+#define IEEE80211_RADIOTAP_F_TX_FAIL	0x0001	/* failed due to excessive
+						 * retries */
+#define IEEE80211_RADIOTAP_F_TX_CTS	0x0002	/* used cts 'protection' */
+#define IEEE80211_RADIOTAP_F_TX_RTS	0x0004	/* used rts/cts handshake */
+
+#endif				/* IEEE80211_RADIOTAP_H */

Added: wpasupplicant/branches/upstream/current/src/drivers/radiotap_iter.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/drivers/radiotap_iter.h?rev=1266&op=file
==============================================================================
--- wpasupplicant/branches/upstream/current/src/drivers/radiotap_iter.h (added)
+++ wpasupplicant/branches/upstream/current/src/drivers/radiotap_iter.h Wed Oct  8 21:24:04 2008
@@ -1,0 +1,41 @@
+#ifndef __RADIOTAP_ITER_H
+#define __RADIOTAP_ITER_H
+
+#include "radiotap.h"
+
+/* Radiotap header iteration
+ *   implemented in radiotap.c
+ */
+/**
+ * struct ieee80211_radiotap_iterator - tracks walk thru present radiotap args
+ * @rtheader: pointer to the radiotap header we are walking through
+ * @max_length: length of radiotap header in cpu byte ordering
+ * @this_arg_index: IEEE80211_RADIOTAP_... index of current arg
+ * @this_arg: pointer to current radiotap arg
+ * @arg_index: internal next argument index
+ * @arg: internal next argument pointer
+ * @next_bitmap: internal pointer to next present u32
+ * @bitmap_shifter: internal shifter for curr u32 bitmap, b0 set == arg present
+ */
+
+struct ieee80211_radiotap_iterator {
+	struct ieee80211_radiotap_header *rtheader;
+	int max_length;
+	int this_arg_index;
+	unsigned char *this_arg;
+
+	int arg_index;
+	unsigned char *arg;
+	uint32_t *next_bitmap;
+	uint32_t bitmap_shifter;
+};
+
+extern int ieee80211_radiotap_iterator_init(
+   struct ieee80211_radiotap_iterator *iterator,
+   struct ieee80211_radiotap_header *radiotap_header,
+   int max_length);
+
+extern int ieee80211_radiotap_iterator_next(
+   struct ieee80211_radiotap_iterator *iterator);
+
+#endif /* __RADIOTAP_ITER_H */

Modified: wpasupplicant/branches/upstream/current/src/eap_common/eap_defs.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/eap_common/eap_defs.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/eap_common/eap_defs.h (original)
+++ wpasupplicant/branches/upstream/current/src/eap_common/eap_defs.h Wed Oct  8 21:24:04 2008
@@ -53,7 +53,7 @@
 	EAP_TYPE_TLS = 13 /* RFC 2716 */,
 	EAP_TYPE_LEAP = 17 /* Cisco proprietary */,
 	EAP_TYPE_SIM = 18 /* RFC 4186 */,
-	EAP_TYPE_TTLS = 21 /* draft-ietf-pppext-eap-ttls-02.txt */,
+	EAP_TYPE_TTLS = 21 /* RFC 5281 */,
 	EAP_TYPE_AKA = 23 /* RFC 4187 */,
 	EAP_TYPE_PEAP = 25 /* draft-josefsson-pppext-eap-tls-eap-06.txt */,
 	EAP_TYPE_MSCHAPV2 = 26 /* draft-kamath-pppext-eap-mschapv2-00.txt */,

Modified: wpasupplicant/branches/upstream/current/src/eap_common/eap_gpsk_common.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/eap_common/eap_gpsk_common.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/eap_common/eap_gpsk_common.c (original)
+++ wpasupplicant/branches/upstream/current/src/eap_common/eap_gpsk_common.c Wed Oct  8 21:24:04 2008
@@ -123,7 +123,7 @@
 {
 	u8 mk[32], *pos, *data;
 	size_t data_len, mk_len;
-	int (*gkdf)(const u8 *psk, const u8 *data, size_t data_len,
+	int (*gkdf)(const u8 *_psk, const u8 *_data, size_t _data_len,
 		    u8 *buf, size_t len);
 
 	gkdf = NULL;
@@ -377,8 +377,8 @@
 				    const u8 *data, size_t len, u8 *mic)
 {
 	if (sk_len != 16) {
-		wpa_printf(MSG_DEBUG, "EAP-GPSK: Invalid SK length %d for "
-			   "AES-CMAC MIC", sk_len);
+		wpa_printf(MSG_DEBUG, "EAP-GPSK: Invalid SK length %lu for "
+			   "AES-CMAC MIC", (unsigned long) sk_len);
 		return -1;
 	}
 

Modified: wpasupplicant/branches/upstream/current/src/eap_common/eap_ttls.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/eap_common/eap_ttls.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/eap_common/eap_ttls.h (original)
+++ wpasupplicant/branches/upstream/current/src/eap_common/eap_ttls.h Wed Oct  8 21:24:04 2008
@@ -1,5 +1,5 @@
 /*
- * EAP server/peer: EAP-TTLS (draft-ietf-pppext-eap-ttls-03.txt)
+ * EAP server/peer: EAP-TTLS (RFC 5281)
  * Copyright (c) 2004-2007, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify

Modified: wpasupplicant/branches/upstream/current/src/eap_peer/eap_config.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/eap_peer/eap_config.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/eap_peer/eap_config.h (original)
+++ wpasupplicant/branches/upstream/current/src/eap_peer/eap_config.h Wed Oct  8 21:24:04 2008
@@ -348,7 +348,7 @@
 	 * number of PAC entries to store in a PAC list (default: 10).
 	 *
 	 * fast_pac_format=binary option can be used to select binary format
-	 * for storing PAC entires in order to save some space (the default
+	 * for storing PAC entries in order to save some space (the default
 	 * text format uses about 2.5 times the size of minimal binary format).
 	 *
 	 * crypto_binding option can be used to control PEAPv0 cryptobinding

Modified: wpasupplicant/branches/upstream/current/src/eap_peer/eap_fast.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/eap_peer/eap_fast.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/eap_peer/eap_fast.c (original)
+++ wpasupplicant/branches/upstream/current/src/eap_peer/eap_fast.c Wed Oct  8 21:24:04 2008
@@ -506,6 +506,8 @@
 	buf = wpabuf_alloc(sizeof(*result));
 	if (buf == NULL)
 		return NULL;
+	wpa_printf(MSG_DEBUG, "EAP-FAST: Add %sResult TLV(status=%d)",
+		   intermediate ? "Intermediate " : "", status);
 	result = wpabuf_put(buf, sizeof(*result));
 	result->tlv_type = host_to_be16(EAP_TLV_TYPE_MANDATORY |
 					(intermediate ?
@@ -527,12 +529,7 @@
 	if (buf == NULL)
 		return NULL;
 
-	res = wpabuf_put(buf, sizeof(*res));
-	res->tlv_type = host_to_be16(EAP_TLV_RESULT_TLV |
-				     EAP_TLV_TYPE_MANDATORY);
-	res->length = host_to_be16(sizeof(*res) - sizeof(struct eap_tlv_hdr));
-	res->status = host_to_be16(EAP_TLV_RESULT_SUCCESS);
-
+	wpa_printf(MSG_DEBUG, "EAP-FAST: Add PAC TLV (ack)");
 	ack = wpabuf_put(buf, sizeof(*ack));
 	ack->tlv_type = host_to_be16(EAP_TLV_PAC_TLV |
 				     EAP_TLV_TYPE_MANDATORY);

Modified: wpasupplicant/branches/upstream/current/src/eap_peer/eap_fast_pac.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/eap_peer/eap_fast_pac.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/eap_peer/eap_fast_pac.c (original)
+++ wpasupplicant/branches/upstream/current/src/eap_peer/eap_fast_pac.c Wed Oct  8 21:24:04 2008
@@ -834,8 +834,8 @@
 	if (blob == NULL)
 		os_free(buf);
 
-	wpa_printf(MSG_DEBUG, "EAP-FAST: Read %d PAC entries from '%s' (bin)",
-		   count, pac_file);
+	wpa_printf(MSG_DEBUG, "EAP-FAST: Read %lu PAC entries from '%s' (bin)",
+		   (unsigned long) count, pac_file);
 
 	return 0;
 
@@ -909,8 +909,8 @@
 		return -1;
 	}
 
-	wpa_printf(MSG_DEBUG, "EAP-FAST: Wrote %d PAC entries into '%s' (bin)",
-		   count, pac_file);
+	wpa_printf(MSG_DEBUG, "EAP-FAST: Wrote %lu PAC entries into '%s' "
+		   "(bin)", (unsigned long) count, pac_file);
 
 	return 0;
 }

Modified: wpasupplicant/branches/upstream/current/src/eap_peer/eap_gpsk.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/eap_peer/eap_gpsk.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/eap_peer/eap_gpsk.c (original)
+++ wpasupplicant/branches/upstream/current/src/eap_peer/eap_gpsk.c Wed Oct  8 21:24:04 2008
@@ -238,8 +238,8 @@
 		return NULL;
 	}
 	if (*list_len == 0 || (*list_len % sizeof(struct eap_gpsk_csuite))) {
-		wpa_printf(MSG_DEBUG, "EAP-GPSK: Invalid CSuite_List len %d",
-			   *list_len);
+		wpa_printf(MSG_DEBUG, "EAP-GPSK: Invalid CSuite_List len %lu",
+			   (unsigned long) *list_len);
 		return NULL;
 	}
 	*list = pos;
@@ -521,7 +521,9 @@
 	miclen = eap_gpsk_mic_len(data->vendor, data->specifier);
 	if (end - pos < (int) miclen) {
 		wpa_printf(MSG_DEBUG, "EAP-GPSK: Message too short for MIC "
-			   "(left=%d miclen=%d)", end - pos, miclen);
+			   "(left=%lu miclen=%lu)",
+			   (unsigned long) (end - pos),
+			   (unsigned long) miclen);
 		return NULL;
 	}
 	if (eap_gpsk_compute_mic(data->sk, data->sk_len, data->vendor,
@@ -572,8 +574,9 @@
 		return NULL;
 	}
 	if (pos != end) {
-		wpa_printf(MSG_DEBUG, "EAP-GPSK: Ignored %d bytes of extra "
-			   "data in the end of GPSK-2", end - pos);
+		wpa_printf(MSG_DEBUG, "EAP-GPSK: Ignored %lu bytes of extra "
+			   "data in the end of GPSK-2",
+			   (unsigned long) (end - pos));
 	}
 
 	resp = eap_gpsk_send_gpsk_4(data, eap_get_id(reqData));

Modified: wpasupplicant/branches/upstream/current/src/eap_peer/eap_ttls.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/eap_peer/eap_ttls.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/eap_peer/eap_ttls.c (original)
+++ wpasupplicant/branches/upstream/current/src/eap_peer/eap_ttls.c Wed Oct  8 21:24:04 2008
@@ -1,5 +1,5 @@
 /*
- * EAP peer method: EAP-TTLS (draft-ietf-pppext-eap-ttls-03.txt)
+ * EAP peer method: EAP-TTLS (RFC 5281)
  * Copyright (c) 2004-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
@@ -27,7 +27,7 @@
 
 
 /* Maximum supported TTLS version
- * 0 = draft-ietf-pppext-eap-ttls-03.txt / draft-funk-eap-ttls-v0-00.txt
+ * 0 = RFC 5281
  * 1 = draft-funk-eap-ttls-v1-00.txt
  */
 #ifndef EAP_TTLS_VERSION
@@ -1810,10 +1810,10 @@
 		if (eap_ttls_process_start(sm, data, flags, ret) < 0)
 			return NULL;
 
-		/* draft-ietf-pppext-eap-ttls-03.txt, Ch. 8.1:
-		 * EAP-TTLS Start packet may, in a future specification, be
-		 * allowed to contain data. Client based on this draft version
-		 * must ignore such data but must not reject the Start packet.
+		/* RFC 5281, Ch. 9.2:
+		 * "This packet MAY contain additional information in the form
+		 * of AVPs, which may provide useful hints to the client"
+		 * For now, ignore any potential extra data.
 		 */
 		left = 0;
 	} else if (!data->ssl_initialized) {

Modified: wpasupplicant/branches/upstream/current/src/eap_peer/tncc.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/eap_peer/tncc.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/eap_peer/tncc.c (original)
+++ wpasupplicant/branches/upstream/current/src/eap_peer/tncc.c Wed Oct  8 21:24:04 2008
@@ -93,6 +93,18 @@
 #define TNC_TNCCS_PREFERREDLANGUAGE		0x00000003
 #define TNC_TNCCS_REASONSTRINGS			0x00000004
 
+
+/* IF-TNCCS-SOH - SSoH and SSoHR Attributes */
+enum {
+	SSOH_MS_MACHINE_INVENTORY = 1,
+	SSOH_MS_QUARANTINE_STATE = 2,
+	SSOH_MS_PACKET_INFO = 3,
+	SSOH_MS_SYSTEMGENERATED_IDS = 4,
+	SSOH_MS_MACHINENAME = 5,
+	SSOH_MS_CORRELATIONID = 6,
+	SSOH_MS_INSTALLED_SHVS = 7,
+	SSOH_MS_MACHINE_INVENTORY_EX = 8
+};
 
 struct tnc_if_imc {
 	struct tnc_if_imc *next;
@@ -1212,6 +1224,8 @@
 	u8 *tlv_len, *tlv_len2, *outer_len, *inner_len, *ssoh_len, *end;
 	u8 correlation_id[24];
 	int ver = 2;
+	/* TODO: get correct name */
+	char *machinename = "wpa_supplicant at w1.fi";
 
 	if (os_get_random(correlation_id, sizeof(correlation_id)))
 		return NULL;
@@ -1257,15 +1271,50 @@
 	wpabuf_put_be16(buf, EAP_TLV_VENDOR_SPECIFIC_TLV);
 	ssoh_len = wpabuf_put(buf, 2);
 	wpabuf_put_be32(buf, EAP_VENDOR_MICROSOFT); /* IANA SMI Code */
-	/* TODO: MS-Machine-Inventory */
-	/* TODO: MS-Quarantine-State */
+
 	/* MS-Packet-Info */
-	wpabuf_put_u8(buf, 0x03);
+	wpabuf_put_u8(buf, SSOH_MS_PACKET_INFO);
+	/* FIX: What is correct value here? IF-TNCCS-SOH v1.0 r8 claims this
+	 * field to be: Reserved(4 bits) r(1 bit) Vers(3 bits), but Windows XP
+	 * SP3 seems to be sending 0x11 for SSoH, i.e., r(request/response) bit
+	 * would not be in the specified location.
+	 */
 	wpabuf_put_u8(buf, 0x11); /* r=request, vers=1 */
-	/* TODO: MS-MachineName */
+
+	/* MS-Machine-Inventory */
+	/* TODO: get correct values; 0 = not applicable for OS */
+	wpabuf_put_u8(buf, SSOH_MS_MACHINE_INVENTORY);
+	wpabuf_put_be32(buf, 0); /* osVersionMajor */
+	wpabuf_put_be32(buf, 0); /* osVersionMinor */
+	wpabuf_put_be32(buf, 0); /* osVersionBuild */
+	wpabuf_put_be16(buf, 0); /* spVersionMajor */
+	wpabuf_put_be16(buf, 0); /* spVersionMinor */
+	wpabuf_put_be16(buf, 0); /* procArch */
+
+	/* MS-MachineName */
+	wpabuf_put_u8(buf, SSOH_MS_MACHINENAME);
+	wpabuf_put_be16(buf, os_strlen(machinename) + 1);
+	wpabuf_put_data(buf, machinename, os_strlen(machinename) + 1);
+
 	/* MS-CorrelationId */
-	wpabuf_put_u8(buf, 0x06);
+	wpabuf_put_u8(buf, SSOH_MS_CORRELATIONID);
 	wpabuf_put_data(buf, correlation_id, sizeof(correlation_id));
+
+	/* MS-Quarantine-State */
+	wpabuf_put_u8(buf, SSOH_MS_QUARANTINE_STATE);
+	wpabuf_put_be16(buf, 1); /* Flags: ExtState=0, f=0, qState=1 */
+	wpabuf_put_be32(buf, 0xffffffff); /* ProbTime (hi) */
+	wpabuf_put_be32(buf, 0xffffffff); /* ProbTime (lo) */
+	wpabuf_put_be16(buf, 1); /* urlLenInBytes */
+	wpabuf_put_u8(buf, 0); /* null termination for the url */
+
+	/* MS-Machine-Inventory-Ex */
+	wpabuf_put_u8(buf, SSOH_MS_MACHINE_INVENTORY_EX);
+	wpabuf_put_be32(buf, 0); /* Reserved
+				  * (note: Windows XP SP3 uses 0xdecafbad) */
+	wpabuf_put_u8(buf, 1); /* ProductType: Client */
+
+	/* Update SSoH Length */
 	end = wpabuf_put(buf, 0);
 	WPA_PUT_BE16(ssoh_len, end - ssoh_len - 2);
 

Modified: wpasupplicant/branches/upstream/current/src/eap_server/eap_fast.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/eap_server/eap_fast.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/eap_server/eap_fast.c (original)
+++ wpasupplicant/branches/upstream/current/src/eap_server/eap_fast.c Wed Oct  8 21:24:04 2008
@@ -685,7 +685,7 @@
 	}
 
 	pac_len = pos - pac_buf;
-	if (pac_len % 8) {
+	while (pac_len % 8) {
 		*pos++ = PAC_OPAQUE_TYPE_PAD;
 		pac_len++;
 	}

Modified: wpasupplicant/branches/upstream/current/src/eap_server/eap_ttls.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/eap_server/eap_ttls.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/eap_server/eap_ttls.c (original)
+++ wpasupplicant/branches/upstream/current/src/eap_server/eap_ttls.c Wed Oct  8 21:24:04 2008
@@ -1,5 +1,5 @@
 /*
- * hostapd / EAP-TTLS (draft-ietf-pppext-eap-ttls-05.txt)
+ * hostapd / EAP-TTLS (RFC 5281)
  * Copyright (c) 2004-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
@@ -25,7 +25,7 @@
 
 
 /* Maximum supported TTLS version
- * 0 = draft-ietf-pppext-eap-ttls-03.txt / draft-funk-eap-ttls-v0-00.txt
+ * 0 = RFC 5281
  * 1 = draft-funk-eap-ttls-v1-00.txt
  */
 #ifndef EAP_TTLS_VERSION
@@ -991,7 +991,13 @@
 				sm->user_eap_method_index++].method;
 			wpa_printf(MSG_DEBUG, "EAP-TTLS: try EAP type %d",
 				   next_type);
-			eap_ttls_phase2_eap_init(sm, data, next_type);
+			if (eap_ttls_phase2_eap_init(sm, data, next_type)) {
+				wpa_printf(MSG_DEBUG, "EAP-TTLS: Failed to "
+					   "initialize EAP type %d",
+					   next_type);
+				eap_ttls_state(data, FAILURE);
+				return;
+			}
 		} else {
 			eap_ttls_state(data, FAILURE);
 		}
@@ -1061,7 +1067,11 @@
 		break;
 	}
 
-	eap_ttls_phase2_eap_init(sm, data, next_type);
+	if (eap_ttls_phase2_eap_init(sm, data, next_type)) {
+		wpa_printf(MSG_DEBUG, "EAP-TTLS: Failed to initialize EAP "
+			   "type %d", next_type);
+		eap_ttls_state(data, FAILURE);
+	}
 }
 
 

Modified: wpasupplicant/branches/upstream/current/src/rsn_supp/peerkey.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/rsn_supp/peerkey.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/rsn_supp/peerkey.c (original)
+++ wpasupplicant/branches/upstream/current/src/rsn_supp/peerkey.c Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * WPA Supplicant - PeerKey for Direct Link Setup (DLS)
- * Copyright (c) 2006-2007, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2006-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -18,6 +18,7 @@
 
 #include "common.h"
 #include "sha1.h"
+#include "sha256.h"
 #include "eloop.h"
 #include "wpa.h"
 #include "wpa_i.h"
@@ -239,15 +240,19 @@
 	/* TODO: find existing entry and if found, use that instead of adding
 	 * a new one; how to handle the case where both ends initiate at the
 	 * same time? */
-	peerkey = os_malloc(sizeof(*peerkey));
+	peerkey = os_zalloc(sizeof(*peerkey));
 	if (peerkey == NULL)
 		return -1;
-	os_memset(peerkey, 0, sizeof(*peerkey));
 	os_memcpy(peerkey->addr, kde.mac_addr, ETH_ALEN);
 	os_memcpy(peerkey->inonce, key->key_nonce, WPA_NONCE_LEN);
 	os_memcpy(peerkey->rsnie_i, kde.rsn_ie, kde.rsn_ie_len);
 	peerkey->rsnie_i_len = kde.rsn_ie_len;
 	peerkey->cipher = cipher;
+#ifdef CONFIG_IEEE80211W
+	if (ie.key_mgmt & (WPA_KEY_MGMT_IEEE8021X_SHA256 |
+			   WPA_KEY_MGMT_PSK_SHA256))
+		peerkey->use_sha256 = 1;
+#endif /* CONFIG_IEEE80211W */
 
 	if (os_get_random(peerkey->pnonce, WPA_NONCE_LEN)) {
 		wpa_msg(sm->ctx->ctx, MSG_WARNING,
@@ -294,18 +299,20 @@
  * @mac_p: Peer MAC address
  * @inonce: Initiator Nonce
  * @mac_i: Initiator MAC address
+ * @use_sha256: Whether to use SHA256-based KDF
  *
  * 8.5.1.4 Station to station (STK) key hierarchy
  * SMKID = HMAC-SHA1-128(SMK, "SMK Name" || PNonce || MAC_P || INonce || MAC_I)
  */
 static void rsn_smkid(const u8 *smk, const u8 *pnonce, const u8 *mac_p,
-		      const u8 *inonce, const u8 *mac_i, u8 *smkid)
+		      const u8 *inonce, const u8 *mac_i, u8 *smkid,
+		      int use_sha256)
 {
 	char *title = "SMK Name";
 	const u8 *addr[5];
 	const size_t len[5] = { 8, WPA_NONCE_LEN, ETH_ALEN, WPA_NONCE_LEN,
 				ETH_ALEN };
-	unsigned char hash[SHA1_MAC_LEN];
+	unsigned char hash[SHA256_MAC_LEN];
 
 	addr[0] = (u8 *) title;
 	addr[1] = pnonce;
@@ -313,7 +320,12 @@
 	addr[3] = inonce;
 	addr[4] = mac_i;
 
-	hmac_sha1_vector(smk, PMK_LEN, 5, addr, len, hash);
+#ifdef CONFIG_IEEE80211W
+	if (use_sha256)
+		hmac_sha256_vector(smk, PMK_LEN, 5, addr, len, hash);
+	else
+#endif /* CONFIG_IEEE80211W */
+		hmac_sha1_vector(smk, PMK_LEN, 5, addr, len, hash);
 	os_memcpy(smkid, hash, PMKID_LEN);
 }
 
@@ -578,11 +590,13 @@
 
 	if (peerkey->initiator) {
 		rsn_smkid(peerkey->smk, peerkey->pnonce, peerkey->addr,
-			  peerkey->inonce, sm->own_addr, peerkey->smkid);
+			  peerkey->inonce, sm->own_addr, peerkey->smkid,
+			  peerkey->use_sha256);
 		wpa_supplicant_send_stk_1_of_4(sm, peerkey);
 	} else {
 		rsn_smkid(peerkey->smk, peerkey->pnonce, sm->own_addr,
-			  peerkey->inonce, peerkey->addr, peerkey->smkid);
+			  peerkey->inonce, peerkey->addr, peerkey->smkid,
+			  peerkey->use_sha256);
 	}
 	wpa_hexdump(MSG_DEBUG, "RSN: SMKID", peerkey->smkid, PMKID_LEN);
 
@@ -695,7 +709,8 @@
 	wpa_pmk_to_ptk(peerkey->smk, PMK_LEN, "Peer key expansion",
 		       sm->own_addr, peerkey->addr,
 		       peerkey->pnonce, key->key_nonce,
-		       (u8 *) stk, sizeof(*stk));
+		       (u8 *) stk, sizeof(*stk),
+		       peerkey->use_sha256);
 	/* Supplicant: swap tx/rx Mic keys */
 	os_memcpy(buf, stk->u.auth.tx_mic_key, 8);
 	os_memcpy(stk->u.auth.tx_mic_key, stk->u.auth.rx_mic_key, 8);
@@ -927,7 +942,8 @@
 		wpa_pmk_to_ptk(peerkey->smk, PMK_LEN, "Peer key expansion",
 			       sm->own_addr, peerkey->addr,
 			       peerkey->inonce, key->key_nonce,
-			       (u8 *) &peerkey->stk, sizeof(peerkey->stk));
+			       (u8 *) &peerkey->stk, sizeof(peerkey->stk),
+			       peerkey->use_sha256);
 		peerkey->stk_set = 1;
 	}
 
@@ -1016,12 +1032,15 @@
 
 	/* TODO: find existing entry and if found, use that instead of adding
 	 * a new one */
-	peerkey = os_malloc(sizeof(*peerkey));
+	peerkey = os_zalloc(sizeof(*peerkey));
 	if (peerkey == NULL)
 		return -1;
-	os_memset(peerkey, 0, sizeof(*peerkey));
 	peerkey->initiator = 1;
 	os_memcpy(peerkey->addr, peer, ETH_ALEN);
+#ifdef CONFIG_IEEE80211W
+	if (wpa_key_mgmt_sha256(sm->key_mgmt))
+		peerkey->use_sha256 = 1;
+#endif /* CONFIG_IEEE80211W */
 
 	/* SMK M1:
 	 * EAPOL-Key(S=1, M=1, A=0, I=0, K=0, SM=1, KeyRSC=0, Nonce=INonce,

Modified: wpasupplicant/branches/upstream/current/src/rsn_supp/peerkey.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/rsn_supp/peerkey.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/rsn_supp/peerkey.h (original)
+++ wpasupplicant/branches/upstream/current/src/rsn_supp/peerkey.h Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * WPA Supplicant - PeerKey for Direct Link Setup (DLS)
- * Copyright (c) 2006, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2006-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -34,6 +34,7 @@
 	int cipher; /* Selected cipher (WPA_CIPHER_*) */
 	u8 replay_counter[WPA_REPLAY_COUNTER_LEN];
 	int replay_counter_set;
+	int use_sha256; /* whether AKMP indicate SHA256-based derivations */
 
 	struct wpa_ptk stk, tstk;
 	int stk_set, tstk_set;

Modified: wpasupplicant/branches/upstream/current/src/rsn_supp/pmksa_cache.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/rsn_supp/pmksa_cache.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/rsn_supp/pmksa_cache.c (original)
+++ wpasupplicant/branches/upstream/current/src/rsn_supp/pmksa_cache.c Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * WPA Supplicant - RSN PMKSA cache
- * Copyright (c) 2004-2006, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2004-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -18,6 +18,7 @@
 #include "wpa.h"
 #include "eloop.h"
 #include "sha1.h"
+#include "sha256.h"
 #include "wpa_i.h"
 #include "eapol_supp/eapol_supp_sm.h"
 #include "pmksa_cache.h"
@@ -43,23 +44,29 @@
  * @pmk_len: Length of pmk in bytes
  * @aa: Authenticator address
  * @spa: Supplicant address
+ * @use_sha256: Whether to use SHA256-based KDF
  *
  * IEEE Std 802.11i-2004 - 8.5.1.2 Pairwise key hierarchy
  * PMKID = HMAC-SHA1-128(PMK, "PMK Name" || AA || SPA)
  */
-void rsn_pmkid(const u8 *pmk, size_t pmk_len, const u8 *aa, const u8 *spa,
-	       u8 *pmkid)
+static void rsn_pmkid(const u8 *pmk, size_t pmk_len, const u8 *aa,
+		      const u8 *spa, u8 *pmkid, int use_sha256)
 {
 	char *title = "PMK Name";
 	const u8 *addr[3];
 	const size_t len[3] = { 8, ETH_ALEN, ETH_ALEN };
-	unsigned char hash[SHA1_MAC_LEN];
+	unsigned char hash[SHA256_MAC_LEN];
 
 	addr[0] = (u8 *) title;
 	addr[1] = aa;
 	addr[2] = spa;
 
-	hmac_sha1_vector(pmk, pmk_len, 3, addr, len, hash);
+#ifdef CONFIG_IEEE80211W
+	if (use_sha256)
+		hmac_sha256_vector(pmk, pmk_len, 3, addr, len, hash);
+	else
+#endif /* CONFIG_IEEE80211W */
+		hmac_sha1_vector(pmk, pmk_len, 3, addr, len, hash);
 	os_memcpy(pmkid, hash, PMKID_LEN);
 }
 
@@ -145,6 +152,7 @@
  * @aa: Authenticator address
  * @spa: Supplicant address
  * @network_ctx: Network configuration context for this PMK
+ * @akmp: WPA_KEY_MGMT_* used in key derivation
  * Returns: Pointer to the added PMKSA cache entry or %NULL on error
  *
  * This function create a PMKSA entry for a new PMK and adds it to the PMKSA
@@ -154,7 +162,7 @@
  */
 struct rsn_pmksa_cache_entry *
 pmksa_cache_add(struct rsn_pmksa_cache *pmksa, const u8 *pmk, size_t pmk_len,
-		const u8 *aa, const u8 *spa, void *network_ctx)
+		const u8 *aa, const u8 *spa, void *network_ctx, int akmp)
 {
 	struct rsn_pmksa_cache_entry *entry, *pos, *prev;
 	struct os_time now;
@@ -167,12 +175,13 @@
 		return NULL;
 	os_memcpy(entry->pmk, pmk, pmk_len);
 	entry->pmk_len = pmk_len;
-	rsn_pmkid(pmk, pmk_len, aa, spa, entry->pmkid);
+	rsn_pmkid(pmk, pmk_len, aa, spa, entry->pmkid,
+		  wpa_key_mgmt_sha256(akmp));
 	os_get_time(&now);
 	entry->expiration = now.sec + pmksa->sm->dot11RSNAConfigPMKLifetime;
 	entry->reauth_time = now.sec + pmksa->sm->dot11RSNAConfigPMKLifetime *
 		pmksa->sm->dot11RSNAConfigPMKReauthThreshold / 100;
-	entry->akmp = WPA_KEY_MGMT_IEEE8021X;
+	entry->akmp = akmp;
 	os_memcpy(entry->aa, aa, ETH_ALEN);
 	entry->network_ctx = network_ctx;
 
@@ -324,7 +333,7 @@
 
 	new_entry = pmksa_cache_add(pmksa, old_entry->pmk, old_entry->pmk_len,
 				    aa, pmksa->sm->own_addr,
-				    old_entry->network_ctx);
+				    old_entry->network_ctx, old_entry->akmp);
 	if (new_entry == NULL)
 		return NULL;
 

Modified: wpasupplicant/branches/upstream/current/src/rsn_supp/pmksa_cache.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/rsn_supp/pmksa_cache.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/rsn_supp/pmksa_cache.h (original)
+++ wpasupplicant/branches/upstream/current/src/rsn_supp/pmksa_cache.h Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * wpa_supplicant - WPA2/RSN PMKSA cache functions
- * Copyright (c) 2003-2006, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2003-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -56,7 +56,7 @@
 int pmksa_cache_list(struct wpa_sm *sm, char *buf, size_t len);
 struct rsn_pmksa_cache_entry *
 pmksa_cache_add(struct rsn_pmksa_cache *pmksa, const u8 *pmk, size_t pmk_len,
-		const u8 *aa, const u8 *spa, void *network_ctx);
+		const u8 *aa, const u8 *spa, void *network_ctx, int akmp);
 void pmksa_cache_notify_reconfig(struct rsn_pmksa_cache *pmksa);
 struct rsn_pmksa_cache_entry * pmksa_cache_get_current(struct wpa_sm *sm);
 void pmksa_cache_clear_current(struct wpa_sm *sm);
@@ -100,7 +100,7 @@
 
 static inline struct rsn_pmksa_cache_entry *
 pmksa_cache_add(struct rsn_pmksa_cache *pmksa, const u8 *pmk, size_t pmk_len,
-		const u8 *aa, const u8 *spa, void *network_ctx)
+		const u8 *aa, const u8 *spa, void *network_ctx, int akmp)
 {
 	return NULL;
 }

Modified: wpasupplicant/branches/upstream/current/src/rsn_supp/preauth.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/rsn_supp/preauth.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/rsn_supp/preauth.c (original)
+++ wpasupplicant/branches/upstream/current/src/rsn_supp/preauth.c Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * WPA Supplicant - RSN pre-authentication
- * Copyright (c) 2003-2007, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2003-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -104,7 +104,8 @@
 			sm->pmk_len = pmk_len;
 			pmksa_cache_add(sm->pmksa, pmk, pmk_len,
 					sm->preauth_bssid, sm->own_addr,
-					sm->network_ctx);
+					sm->network_ctx,
+					WPA_KEY_MGMT_IEEE8021X);
 		} else {
 			wpa_msg(sm->ctx->ctx, MSG_INFO, "RSN: failed to get "
 				"master session key from pre-auth EAPOL state "
@@ -304,7 +305,8 @@
 	if (sm->preauth_eapol ||
 	    sm->proto != WPA_PROTO_RSN ||
 	    wpa_sm_get_state(sm) != WPA_COMPLETED ||
-	    sm->key_mgmt != WPA_KEY_MGMT_IEEE8021X) {
+	    (sm->key_mgmt != WPA_KEY_MGMT_IEEE8021X &&
+	     sm->key_mgmt != WPA_KEY_MGMT_IEEE8021X_SHA256)) {
 		wpa_msg(sm->ctx->ctx, MSG_DEBUG, "RSN: not in suitable state "
 			"for new pre-authentication");
 		return; /* invalid state for new pre-auth */

Modified: wpasupplicant/branches/upstream/current/src/rsn_supp/wpa.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/rsn_supp/wpa.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/rsn_supp/wpa.c (original)
+++ wpasupplicant/branches/upstream/current/src/rsn_supp/wpa.c Wed Oct  8 21:24:04 2008
@@ -77,6 +77,12 @@
 	case WPA_KEY_MGMT_FT_PSK:
 		return "FT-PSK";
 #endif /* CONFIG_IEEE80211R */
+#ifdef CONFIG_IEEE80211W
+	case WPA_KEY_MGMT_IEEE8021X_SHA256:
+		return "WPA2-EAP-SHA256";
+	case WPA_KEY_MGMT_PSK_SHA256:
+		return "WPA2-PSK-SHA256";
+#endif /* CONFIG_IEEE80211W */
 	default:
 		return "UNKNOWN";
 	}
@@ -140,8 +146,7 @@
 	int key_info, ver;
 	u8 bssid[ETH_ALEN], *rbuf;
 
-	if (sm->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X ||
-	    sm->key_mgmt == WPA_KEY_MGMT_FT_PSK)
+	if (wpa_key_mgmt_ft(sm->key_mgmt) || wpa_key_mgmt_sha256(sm->key_mgmt))
 		ver = WPA_KEY_INFO_TYPE_AES_128_CMAC;
 	else if (sm->pairwise_cipher == WPA_CIPHER_CCMP)
 		ver = WPA_KEY_INFO_TYPE_HMAC_SHA1_AES;
@@ -216,8 +221,7 @@
 #ifdef CONFIG_IEEE80211R
 		sm->xxkey_len = 0;
 #endif /* CONFIG_IEEE80211R */
-	} else if ((sm->key_mgmt == WPA_KEY_MGMT_IEEE8021X ||
-		    sm->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X) && sm->eapol) {
+	} else if (wpa_key_mgmt_wpa_ieee8021x(sm->key_mgmt) && sm->eapol) {
 		int res, pmk_len;
 		pmk_len = PMK_LEN;
 		res = eapol_sm_get_key(sm->eapol, sm->pmk, PMK_LEN);
@@ -244,7 +248,8 @@
 					"machines", sm->pmk, pmk_len);
 			sm->pmk_len = pmk_len;
 			pmksa_cache_add(sm->pmksa, sm->pmk, pmk_len, src_addr,
-					sm->own_addr, sm->network_ctx);
+					sm->own_addr, sm->network_ctx,
+					sm->key_mgmt);
 			if (!sm->cur_pmksa && pmkid &&
 			    pmksa_cache_get(sm->pmksa, src_addr, pmkid)) {
 				wpa_printf(MSG_DEBUG, "RSN: the new PMK "
@@ -268,8 +273,7 @@
 		}
 	}
 
-	if (abort_cached && (sm->key_mgmt == WPA_KEY_MGMT_IEEE8021X ||
-			     sm->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X)) {
+	if (abort_cached && wpa_key_mgmt_wpa_ieee8021x(sm->key_mgmt)) {
 		/* Send EAPOL-Start to trigger full EAP authentication. */
 		u8 *buf;
 		size_t buflen;
@@ -356,14 +360,14 @@
 			  struct wpa_ptk *ptk)
 {
 #ifdef CONFIG_IEEE80211R
-	if (sm->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X ||
-	    sm->key_mgmt == WPA_KEY_MGMT_FT_PSK)
+	if (wpa_key_mgmt_ft(sm->key_mgmt))
 		return wpa_derive_ptk_ft(sm, src_addr, key, ptk);
 #endif /* CONFIG_IEEE80211R */
 
 	wpa_pmk_to_ptk(sm->pmk, sm->pmk_len, "Pairwise key expansion",
 		       sm->own_addr, sm->bssid, sm->snonce, key->key_nonce,
-		       (u8 *) ptk, sizeof(*ptk));
+		       (u8 *) ptk, sizeof(*ptk),
+		       wpa_key_mgmt_sha256(sm->key_mgmt));
 	return 0;
 }
 
@@ -458,8 +462,7 @@
 			sm, addr, MLME_SETPROTECTION_PROTECT_TYPE_RX_TX,
 			MLME_SETPROTECTION_KEY_TYPE_PAIRWISE);
 		eapol_sm_notify_portValid(sm->eapol, TRUE);
-		if (sm->key_mgmt == WPA_KEY_MGMT_PSK ||
-		    sm->key_mgmt == WPA_KEY_MGMT_FT_PSK)
+		if (wpa_key_mgmt_wpa_psk(sm->key_mgmt))
 			eapol_sm_notify_eap_success(sm->eapol, TRUE);
 		/*
 		 * Start preauthentication after a short wait to avoid a
@@ -478,8 +481,7 @@
 	}
 
 #ifdef CONFIG_IEEE80211R
-	if (sm->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X ||
-	    sm->key_mgmt == WPA_KEY_MGMT_FT_PSK) {
+	if (wpa_key_mgmt_ft(sm->key_mgmt)) {
 		/* Prepare for the next transition */
 		wpa_ft_prepare_auth_request(sm);
 	}
@@ -834,8 +836,7 @@
 	}
 
 #ifdef CONFIG_IEEE80211R
-	if (sm->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X ||
-	    sm->key_mgmt == WPA_KEY_MGMT_FT_PSK) {
+	if (wpa_key_mgmt_ft(sm->key_mgmt)) {
 		struct rsn_mdie *mdie;
 		/* TODO: verify that full MDIE matches with the one from scan
 		 * results, not only mobility domain */
@@ -1463,8 +1464,7 @@
 	}
 
 #ifdef CONFIG_IEEE80211R
-	if (sm->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X ||
-	    sm->key_mgmt == WPA_KEY_MGMT_FT_PSK) {
+	if (wpa_key_mgmt_ft(sm->key_mgmt)) {
 		/* IEEE 802.11r uses a new key_info type (AES-128-CMAC). */
 		if (ver != WPA_KEY_INFO_TYPE_AES_128_CMAC) {
 			wpa_printf(MSG_INFO, "FT: AP did not use "
@@ -1473,6 +1473,15 @@
 		}
 	} else
 #endif /* CONFIG_IEEE80211R */
+#ifdef CONFIG_IEEE80211W
+	if (wpa_key_mgmt_sha256(sm->key_mgmt)) {
+		if (ver != WPA_KEY_INFO_TYPE_AES_128_CMAC) {
+			wpa_printf(MSG_INFO, "WPA: AP did not use the "
+				   "negotiated AES-128-CMAC.");
+			goto out;
+		}
+	} else
+#endif /* CONFIG_IEEE80211W */
 	if (sm->pairwise_cipher == WPA_CIPHER_CCMP &&
 	    ver != WPA_KEY_INFO_TYPE_HMAC_SHA1_AES) {
 		wpa_printf(MSG_INFO, "WPA: CCMP is used, but EAPOL-Key "
@@ -1651,6 +1660,12 @@
 	case WPA_KEY_MGMT_FT_PSK:
 		return RSN_AUTH_KEY_MGMT_FT_PSK;
 #endif /* CONFIG_IEEE80211R */
+#ifdef CONFIG_IEEE80211W
+	case WPA_KEY_MGMT_IEEE8021X_SHA256:
+		return RSN_AUTH_KEY_MGMT_802_1X_SHA256;
+	case WPA_KEY_MGMT_PSK_SHA256:
+		return RSN_AUTH_KEY_MGMT_PSK_SHA256;
+#endif /* CONFIG_IEEE80211W */
 	case WPA_KEY_MGMT_WPA_NONE:
 		return WPA_AUTH_KEY_MGMT_NONE;
 	default:
@@ -1708,10 +1723,8 @@
 	} else
 		pmkid_txt[0] = '\0';
 
-	if ((sm->key_mgmt == WPA_KEY_MGMT_PSK ||
-	     sm->key_mgmt == WPA_KEY_MGMT_IEEE8021X ||
-	     sm->key_mgmt == WPA_KEY_MGMT_FT_PSK ||
-	     sm->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X) &&
+	if ((wpa_key_mgmt_wpa_psk(sm->key_mgmt) ||
+	     wpa_key_mgmt_wpa_ieee8021x(sm->key_mgmt)) &&
 	    sm->proto == WPA_PROTO_RSN)
 		rsna = 1;
 	else

Modified: wpasupplicant/branches/upstream/current/src/rsn_supp/wpa_ft.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/rsn_supp/wpa_ft.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/rsn_supp/wpa_ft.c (original)
+++ wpasupplicant/branches/upstream/current/src/rsn_supp/wpa_ft.c Wed Oct  8 21:24:04 2008
@@ -193,7 +193,7 @@
 	capab = 0;
 #ifdef CONFIG_IEEE80211W
 	if (sm->mgmt_group_cipher == WPA_CIPHER_AES_128_CMAC)
-		capab |= WPA_CAPABILITY_MGMT_FRAME_PROTECTION;
+		capab |= WPA_CAPABILITY_MFPC;
 #endif /* CONFIG_IEEE80211W */
 	WPA_PUT_LE16(pos, capab);
 	pos += 2;
@@ -243,7 +243,7 @@
 
 	if (kck) {
 		/*
-		 * IEEE 802.11r/D9.0, 11A.8.4
+		 * IEEE Std 802.11r-2008, 11A.8.4
 		 * MIC shall be calculated over:
 		 * non-AP STA MAC address
 		 * Target AP MAC address
@@ -286,6 +286,8 @@
 	const u8 *rsn_pmkid;
 	const u8 *tie;
 	size_t tie_len;
+	const u8 *igtk;
+	size_t igtk_len;
 };
 
 
@@ -323,6 +325,12 @@
 			parse->r0kh_id = pos + 2;
 			parse->r0kh_id_len = pos[1];
 			break;
+#ifdef CONFIG_IEEE80211W
+		case FTIE_SUBELEM_IGTK:
+			parse->igtk = pos + 2;
+			parse->igtk_len = pos[1];
+			break;
+#endif /* CONFIG_IEEE80211W */
 		}
 
 		pos += 2 + pos[1];
@@ -581,122 +589,30 @@
 }
 
 
-int wpa_ft_validate_reassoc_resp(struct wpa_sm *sm, const u8 *ies,
-				 size_t ies_len, const u8 *src_addr)
-{
-	struct wpa_ft_ies parse;
-	struct rsn_mdie *mdie;
-	struct rsn_ftie *ftie;
-	size_t count, gtk_len, keylen, rsc_len;
-	u8 mic[16];
+static int wpa_ft_process_gtk_subelem(struct wpa_sm *sm, const u8 *gtk_elem,
+				      size_t gtk_elem_len)
+{
 	u8 gtk[32];
 	int keyidx;
 	wpa_alg alg;
-
-	wpa_hexdump(MSG_DEBUG, "FT: Response IEs", ies, ies_len);
-
-	if (sm->key_mgmt != WPA_KEY_MGMT_FT_IEEE8021X &&
-	    sm->key_mgmt != WPA_KEY_MGMT_FT_PSK) {
-		wpa_printf(MSG_DEBUG, "FT: Reject FT IEs since FT is not "
-			   "enabled for this connection");
-		return -1;
-	}
-
-	if (wpa_ft_parse_ies(ies, ies_len, &parse) < 0) {
-		wpa_printf(MSG_DEBUG, "FT: Failed to parse IEs");
-		return -1;
-	}
-
-	mdie = (struct rsn_mdie *) parse.mdie;
-	if (mdie == NULL || parse.mdie_len < sizeof(*mdie) ||
-	    os_memcmp(mdie->mobility_domain, sm->mobility_domain,
-		      MOBILITY_DOMAIN_ID_LEN) != 0) {
-		wpa_printf(MSG_DEBUG, "FT: Invalid MDIE");
-		return -1;
-	}
-
-	ftie = (struct rsn_ftie *) parse.ftie;
-	if (ftie == NULL || parse.ftie_len < sizeof(*ftie)) {
-		wpa_printf(MSG_DEBUG, "FT: Invalid FTIE");
-		return -1;
-	}
-
-	if (parse.r0kh_id == NULL) {
-		wpa_printf(MSG_DEBUG, "FT: No R0KH-ID subelem in FTIE");
-		return -1;
-	}
-
-	if (parse.r0kh_id_len != sm->r0kh_id_len ||
-	    os_memcmp(parse.r0kh_id, sm->r0kh_id, parse.r0kh_id_len) != 0) {
-		wpa_printf(MSG_DEBUG, "FT: R0KH-ID in FTIE did not match with "
-			   "the current R0KH-ID");
-		wpa_hexdump(MSG_DEBUG, "FT: R0KH-ID in FTIE",
-			    parse.r0kh_id, parse.r0kh_id_len);
-		wpa_hexdump(MSG_DEBUG, "FT: The current R0KH-ID",
-			    sm->r0kh_id, sm->r0kh_id_len);
-		return -1;
-	}
-
-	if (parse.r1kh_id == NULL) {
-		wpa_printf(MSG_DEBUG, "FT: No R1KH-ID subelem in FTIE");
-		return -1;
-	}
-
-	if (os_memcmp(parse.r1kh_id, sm->r1kh_id, FT_R1KH_ID_LEN) != 0) {
-		wpa_printf(MSG_DEBUG, "FT: Unknown R1KH-ID used in "
-			   "ReassocResp");
-		return -1;
-	}
-
-	if (parse.rsn_pmkid == NULL ||
-	    os_memcmp(parse.rsn_pmkid, sm->pmk_r1_name, WPA_PMK_NAME_LEN)) {
-		wpa_printf(MSG_DEBUG, "FT: No matching PMKR1Name (PMKID) in "
-			   "RSNIE (pmkid=%d)", !!parse.rsn_pmkid);
-		return -1;
-	}
-
-	count = 3;
-	if (parse.tie)
-		count++;
-
-	if (ftie->mic_control[1] != count) {
-		wpa_printf(MSG_DEBUG, "FT: Unexpected IE count in FTIE (%d)",
-			   ftie->mic_control[1]);
-		return -1;
-	}
-
-	if (wpa_ft_mic(sm->ptk.kck, sm->own_addr, src_addr, 6,
-		       parse.mdie - 2, parse.mdie_len + 2,
-		       parse.ftie - 2, parse.ftie_len + 2,
-		       parse.rsn - 2, parse.rsn_len + 2, NULL, 0,
-		       mic) < 0) {
-		wpa_printf(MSG_DEBUG, "FT: Failed to calculate MIC");
-		return -1;
-	}
-
-	if (os_memcmp(mic, ftie->mic, 16) != 0) {
-		wpa_printf(MSG_DEBUG, "FT: Invalid MIC in FTIE");
-		wpa_hexdump(MSG_MSGDUMP, "FT: Received MIC", ftie->mic, 16);
-		wpa_hexdump(MSG_MSGDUMP, "FT: Calculated MIC", mic, 16);
-		return -1;
-	}
-
-	if (parse.gtk == NULL) {
+	size_t gtk_len, keylen, rsc_len;
+
+	if (gtk_elem == NULL) {
 		wpa_printf(MSG_DEBUG, "FT: No GTK included in FTIE");
 		return 0;
 	}
 
 	wpa_hexdump_key(MSG_DEBUG, "FT: Received GTK in Reassoc Resp",
-			parse.gtk, parse.gtk_len);
-
-	if (parse.gtk_len < 10 + 24 || (parse.gtk_len - 10) % 8 ||
-	    parse.gtk_len - 18 > sizeof(gtk)) {
+			gtk_elem, gtk_elem_len);
+
+	if (gtk_elem_len < 10 + 24 || (gtk_elem_len - 10) % 8 ||
+	    gtk_elem_len - 18 > sizeof(gtk)) {
 		wpa_printf(MSG_DEBUG, "FT: Invalid GTK sub-elem "
-			   "length %lu", (unsigned long) parse.gtk_len);
-		return -1;
-	}
-	gtk_len = parse.gtk_len - 18;
-	if (aes_unwrap(sm->ptk.kek, gtk_len / 8, parse.gtk + 10, gtk)) {
+			   "length %lu", (unsigned long) gtk_elem_len);
+		return -1;
+	}
+	gtk_len = gtk_elem_len - 18;
+	if (aes_unwrap(sm->ptk.kek, gtk_len / 8, gtk_elem + 10, gtk)) {
 		wpa_printf(MSG_WARNING, "FT: AES unwrap failed - could not "
 			   "decrypt GTK");
 		return -1;
@@ -736,23 +652,180 @@
 
 	/* Key Info[1] | Key Length[1] | RSC[8] | Key[5..32]. */
 
-	keyidx = parse.gtk[0] & 0x03;
-
-	if (parse.gtk[1] != keylen) {
+	keyidx = gtk_elem[0] & 0x03;
+
+	if (gtk_elem[1] != keylen) {
 		wpa_printf(MSG_DEBUG, "FT: GTK length mismatch: received %d "
 			   "negotiated %lu",
-			   parse.gtk[1], (unsigned long) keylen);
+			   gtk_elem[1], (unsigned long) keylen);
 		return -1;
 	}
 
 	wpa_hexdump_key(MSG_DEBUG, "FT: GTK from Reassoc Resp", gtk, keylen);
 	if (wpa_sm_set_key(sm, alg, (u8 *) "\xff\xff\xff\xff\xff\xff",
-			   keyidx, 0, parse.gtk + 2, rsc_len, gtk, keylen) < 0)
-	{
+			   keyidx, 0, gtk_elem + 2, rsc_len, gtk, keylen) <
+	    0) {
 		wpa_printf(MSG_WARNING, "WPA: Failed to set GTK to the "
 			   "driver.");
 		return -1;
 	}
+
+	return 0;
+}
+
+
+#ifdef CONFIG_IEEE80211W
+static int wpa_ft_process_igtk_subelem(struct wpa_sm *sm, const u8 *igtk_elem,
+				       size_t igtk_elem_len)
+{
+	u8 igtk[WPA_IGTK_LEN];
+	u16 keyidx;
+
+	if (sm->mgmt_group_cipher != WPA_CIPHER_AES_128_CMAC)
+		return 0;
+
+	if (igtk_elem == NULL) {
+		wpa_printf(MSG_DEBUG, "FT: No IGTK included in FTIE");
+		return 0;
+	}
+
+	wpa_hexdump_key(MSG_DEBUG, "FT: Received IGTK in Reassoc Resp",
+			igtk_elem, igtk_elem_len);
+
+	if (igtk_elem_len != 2 + 6 + 24) {
+		wpa_printf(MSG_DEBUG, "FT: Invalid IGTK sub-elem "
+			   "length %lu", (unsigned long) igtk_elem_len);
+		return -1;
+	}
+	if (aes_unwrap(sm->ptk.kek, WPA_IGTK_LEN / 8, igtk_elem + 8, igtk)) {
+		wpa_printf(MSG_WARNING, "FT: AES unwrap failed - could not "
+			   "decrypt IGTK");
+		return -1;
+	}
+
+	/* KeyID[2] | PN[6] | Key[16+8] */
+
+	keyidx = WPA_GET_LE16(igtk_elem);
+
+	wpa_hexdump_key(MSG_DEBUG, "FT: IGTK from Reassoc Resp", igtk,
+			WPA_IGTK_LEN);
+	if (wpa_sm_set_key(sm, WPA_ALG_IGTK, (u8 *) "\xff\xff\xff\xff\xff\xff",
+			   keyidx, 0, igtk_elem + 2, 6, igtk, WPA_IGTK_LEN) <
+	    0) {
+		wpa_printf(MSG_WARNING, "WPA: Failed to set IGTK to the "
+			   "driver.");
+		return -1;
+	}
+
+	return 0;
+}
+#endif /* CONFIG_IEEE80211W */
+
+
+int wpa_ft_validate_reassoc_resp(struct wpa_sm *sm, const u8 *ies,
+				 size_t ies_len, const u8 *src_addr)
+{
+	struct wpa_ft_ies parse;
+	struct rsn_mdie *mdie;
+	struct rsn_ftie *ftie;
+	size_t count;
+	u8 mic[16];
+
+	wpa_hexdump(MSG_DEBUG, "FT: Response IEs", ies, ies_len);
+
+	if (sm->key_mgmt != WPA_KEY_MGMT_FT_IEEE8021X &&
+	    sm->key_mgmt != WPA_KEY_MGMT_FT_PSK) {
+		wpa_printf(MSG_DEBUG, "FT: Reject FT IEs since FT is not "
+			   "enabled for this connection");
+		return -1;
+	}
+
+	if (wpa_ft_parse_ies(ies, ies_len, &parse) < 0) {
+		wpa_printf(MSG_DEBUG, "FT: Failed to parse IEs");
+		return -1;
+	}
+
+	mdie = (struct rsn_mdie *) parse.mdie;
+	if (mdie == NULL || parse.mdie_len < sizeof(*mdie) ||
+	    os_memcmp(mdie->mobility_domain, sm->mobility_domain,
+		      MOBILITY_DOMAIN_ID_LEN) != 0) {
+		wpa_printf(MSG_DEBUG, "FT: Invalid MDIE");
+		return -1;
+	}
+
+	ftie = (struct rsn_ftie *) parse.ftie;
+	if (ftie == NULL || parse.ftie_len < sizeof(*ftie)) {
+		wpa_printf(MSG_DEBUG, "FT: Invalid FTIE");
+		return -1;
+	}
+
+	if (parse.r0kh_id == NULL) {
+		wpa_printf(MSG_DEBUG, "FT: No R0KH-ID subelem in FTIE");
+		return -1;
+	}
+
+	if (parse.r0kh_id_len != sm->r0kh_id_len ||
+	    os_memcmp(parse.r0kh_id, sm->r0kh_id, parse.r0kh_id_len) != 0) {
+		wpa_printf(MSG_DEBUG, "FT: R0KH-ID in FTIE did not match with "
+			   "the current R0KH-ID");
+		wpa_hexdump(MSG_DEBUG, "FT: R0KH-ID in FTIE",
+			    parse.r0kh_id, parse.r0kh_id_len);
+		wpa_hexdump(MSG_DEBUG, "FT: The current R0KH-ID",
+			    sm->r0kh_id, sm->r0kh_id_len);
+		return -1;
+	}
+
+	if (parse.r1kh_id == NULL) {
+		wpa_printf(MSG_DEBUG, "FT: No R1KH-ID subelem in FTIE");
+		return -1;
+	}
+
+	if (os_memcmp(parse.r1kh_id, sm->r1kh_id, FT_R1KH_ID_LEN) != 0) {
+		wpa_printf(MSG_DEBUG, "FT: Unknown R1KH-ID used in "
+			   "ReassocResp");
+		return -1;
+	}
+
+	if (parse.rsn_pmkid == NULL ||
+	    os_memcmp(parse.rsn_pmkid, sm->pmk_r1_name, WPA_PMK_NAME_LEN)) {
+		wpa_printf(MSG_DEBUG, "FT: No matching PMKR1Name (PMKID) in "
+			   "RSNIE (pmkid=%d)", !!parse.rsn_pmkid);
+		return -1;
+	}
+
+	count = 3;
+	if (parse.tie)
+		count++;
+
+	if (ftie->mic_control[1] != count) {
+		wpa_printf(MSG_DEBUG, "FT: Unexpected IE count in FTIE (%d)",
+			   ftie->mic_control[1]);
+		return -1;
+	}
+
+	if (wpa_ft_mic(sm->ptk.kck, sm->own_addr, src_addr, 6,
+		       parse.mdie - 2, parse.mdie_len + 2,
+		       parse.ftie - 2, parse.ftie_len + 2,
+		       parse.rsn - 2, parse.rsn_len + 2, NULL, 0,
+		       mic) < 0) {
+		wpa_printf(MSG_DEBUG, "FT: Failed to calculate MIC");
+		return -1;
+	}
+
+	if (os_memcmp(mic, ftie->mic, 16) != 0) {
+		wpa_printf(MSG_DEBUG, "FT: Invalid MIC in FTIE");
+		wpa_hexdump(MSG_MSGDUMP, "FT: Received MIC", ftie->mic, 16);
+		wpa_hexdump(MSG_MSGDUMP, "FT: Calculated MIC", mic, 16);
+		return -1;
+	}
+
+	if (wpa_ft_process_gtk_subelem(sm, parse.gtk, parse.gtk_len) < 0)
+		return -1;
+
+#ifdef CONFIG_IEEE80211W
+	if (wpa_ft_process_igtk_subelem(sm, parse.igtk, parse.igtk_len) < 0)
+		return -1;
+#endif /* CONFIG_IEEE80211W */
 
 	return 0;
 }

Modified: wpasupplicant/branches/upstream/current/src/rsn_supp/wpa_ie.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/rsn_supp/wpa_ie.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/rsn_supp/wpa_ie.c (original)
+++ wpasupplicant/branches/upstream/current/src/rsn_supp/wpa_ie.c Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * wpa_supplicant - WPA/RSN IE and KDE processing
- * Copyright (c) 2003-2007, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2003-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -316,6 +316,12 @@
 	} else if (key_mgmt == WPA_KEY_MGMT_FT_PSK) {
 		RSN_SELECTOR_PUT(pos, RSN_AUTH_KEY_MGMT_FT_PSK);
 #endif /* CONFIG_IEEE80211R */
+#ifdef CONFIG_IEEE80211W
+	} else if (key_mgmt == WPA_KEY_MGMT_IEEE8021X_SHA256) {
+		RSN_SELECTOR_PUT(pos, RSN_AUTH_KEY_MGMT_802_1X_SHA256);
+	} else if (key_mgmt == WPA_KEY_MGMT_PSK_SHA256) {
+		RSN_SELECTOR_PUT(pos, RSN_AUTH_KEY_MGMT_PSK_SHA256);
+#endif /* CONFIG_IEEE80211W */
 	} else {
 		wpa_printf(MSG_WARNING, "Invalid key management type (%d).",
 			   key_mgmt);
@@ -327,7 +333,7 @@
 	capab = 0;
 #ifdef CONFIG_IEEE80211W
 	if (mgmt_group_cipher == WPA_CIPHER_AES_128_CMAC)
-		capab |= WPA_CAPABILITY_MGMT_FRAME_PROTECTION;
+		capab |= WPA_CAPABILITY_MFPC;
 #endif /* CONFIG_IEEE80211W */
 	WPA_PUT_LE16(pos, capab);
 	pos += 2;

Modified: wpasupplicant/branches/upstream/current/src/tls/tlsv1_client_read.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/tls/tlsv1_client_read.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/tls/tlsv1_client_read.c (original)
+++ wpasupplicant/branches/upstream/current/src/tls/tlsv1_client_read.c Wed Oct  8 21:24:04 2008
@@ -422,8 +422,8 @@
 	conn->dh_p_len = WPA_GET_BE16(pos);
 	pos += 2;
 	if (conn->dh_p_len == 0 || end - pos < (int) conn->dh_p_len) {
-		wpa_printf(MSG_DEBUG, "TLSv1: Invalid dh_p length %d",
-			   conn->dh_p_len);
+		wpa_printf(MSG_DEBUG, "TLSv1: Invalid dh_p length %lu",
+			   (unsigned long) conn->dh_p_len);
 		goto fail;
 	}
 	conn->dh_p = os_malloc(conn->dh_p_len);

Modified: wpasupplicant/branches/upstream/current/src/tls/x509v3.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/src/tls/x509v3.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/src/tls/x509v3.c (original)
+++ wpasupplicant/branches/upstream/current/src/tls/x509v3.c Wed Oct  8 21:24:04 2008
@@ -1185,6 +1185,21 @@
 }
 
 
+static int x509_sha256_oid(struct asn1_oid *oid)
+{
+	return oid->len == 9 &&
+		oid->oid[0] == 2 /* joint-iso-itu-t */ &&
+		oid->oid[1] == 16 /* country */ &&
+		oid->oid[2] == 840 /* us */ &&
+		oid->oid[3] == 1 /* organization */ &&
+		oid->oid[4] == 101 /* gov */ &&
+		oid->oid[5] == 3 /* csor */ &&
+		oid->oid[6] == 4 /* nistAlgorithm */ &&
+		oid->oid[7] == 2 /* hashAlgs */ &&
+		oid->oid[8] == 1 /* sha256 */;
+}
+
+
 /**
  * x509_certificate_parse - Parse a X.509 certificate in DER format
  * @buf: Pointer to the X.509 certificate in DER format
@@ -1309,7 +1324,7 @@
 	size_t data_len;
 	struct asn1_hdr hdr;
 	struct asn1_oid oid;
-	u8 hash[20];
+	u8 hash[32];
 	size_t hash_len;
 
 	if (!x509_pkcs_oid(&cert->signature.oid) ||
@@ -1408,6 +1423,19 @@
 		goto skip_digest_oid;
 	}
 
+	if (x509_sha256_oid(&oid)) {
+		if (cert->signature.oid.oid[6] !=
+		    11 /* sha2561WithRSAEncryption */) {
+			wpa_printf(MSG_DEBUG, "X509: digestAlgorithm SHA256 "
+				   "does not match with certificate "
+				   "signatureAlgorithm (%lu)",
+				   cert->signature.oid.oid[6]);
+			os_free(data);
+			return -1;
+		}
+		goto skip_digest_oid;
+	}
+
 	if (!x509_digest_oid(&oid)) {
 		wpa_printf(MSG_DEBUG, "X509: Unrecognized digestAlgorithm");
 		os_free(data);
@@ -1466,8 +1494,20 @@
 		wpa_hexdump(MSG_MSGDUMP, "X509: Certificate hash (SHA1)",
 			    hash, hash_len);
 		break;
+	case 11: /* sha256WithRSAEncryption */
+#ifdef NEED_SHA256
+		sha256_vector(1, &cert->tbs_cert_start, &cert->tbs_cert_len,
+			      hash);
+		hash_len = 32;
+		wpa_hexdump(MSG_MSGDUMP, "X509: Certificate hash (SHA256)",
+			    hash, hash_len);
+		break;
+#else /* NEED_SHA256 */
+		wpa_printf(MSG_INFO, "X509: SHA256 support disabled");
+		os_free(data);
+		return -1;
+#endif /* NEED_SHA256 */
 	case 2: /* md2WithRSAEncryption */
-	case 11: /* sha256WithRSAEncryption */
 	case 12: /* sha384WithRSAEncryption */
 	case 13: /* sha512WithRSAEncryption */
 	default:

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/ChangeLog
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/ChangeLog?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/ChangeLog (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/ChangeLog Wed Oct  8 21:24:04 2008
@@ -1,4 +1,15 @@
 ChangeLog for wpa_supplicant
+
+????-??-?? - v0.6.5
+	* added support for SHA-256 as X.509 certificate digest when using the
+	  internal X.509/TLSv1 implementation
+	* updated management frame protection to use IEEE 802.11w/D6.0
+	* added support for using SHA256-based stronger key derivation for WPA2
+	  (IEEE 802.11w)
+	* fixed FT (IEEE 802.11r) authentication after a failed association to
+	  use correct FTIE
+	* added support for configuring Phase 2 (inner/tunneled) authentication
+	  method with wpa_gui-qt4
 
 2008-08-10 - v0.6.4
 	* added support for EAP Sequences in EAP-FAST Phase 2

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/Makefile
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/Makefile?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/Makefile (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/Makefile Wed Oct  8 21:24:04 2008
@@ -131,6 +131,9 @@
 CFLAGS += -DCONFIG_DRIVER_NL80211
 OBJS_d += ../src/drivers/driver_nl80211.o
 LIBS += -lnl
+ifdef CONFIG_CLIENT_MLME
+OBJS_d += ../src/drivers/radiotap.o
+endif
 endif
 
 ifdef CONFIG_DRIVER_PRISM54
@@ -773,8 +776,14 @@
 NEED_SHA256=y
 endif
 
+ifdef CONFIG_IEEE80211W
+CFLAGS += -DCONFIG_IEEE80211W
+NEED_SHA256=y
+endif
+
 ifdef NEED_SHA256
 OBJS += ../src/crypto/sha256.o
+CFLAGS += -DNEED_SHA256
 endif
 
 ifdef CONFIG_WIRELESS_EXTENSION
@@ -856,11 +865,6 @@
 
 ifdef CONFIG_PEERKEY
 CFLAGS += -DCONFIG_PEERKEY
-endif
-
-ifdef CONFIG_IEEE80211W
-CFLAGS += -DCONFIG_IEEE80211W
-NEED_SHA256=y
 endif
 
 ifdef CONFIG_IEEE80211R
@@ -1033,6 +1037,7 @@
 	../src/crypto/crypto_$(CONFIG_CRYPTO).o \
 	../src/crypto/md5.o ../src/crypto/sha1.o ../src/crypto/aes.o \
 	../src/crypto/rc4.o ../src/crypto/des.o ../src/crypto/aes_wrap.o \
+	../src/crypto/sha256.o \
 	../src/tls/bignum.o ../src/tls/rsa.o
 test_x509v3: $(OBJSx)
 	$(LDO) $(LDFLAGS) -o test_x509v3 $(OBJSx)

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/config.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/config.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/config.c (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/config.c Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * WPA Supplicant / Configuration parser and common functions
- * Copyright (c) 2003-2007, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2003-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -95,6 +95,14 @@
 	size_t res_len, *dst_len;
 	char **dst, *tmp;
 
+	if (os_strcmp(value, "NULL") == 0) {
+		wpa_printf(MSG_DEBUG, "Unset configuration string '%s'",
+			   data->name);
+		tmp = NULL;
+		res_len = 0;
+		goto set;
+	}
+
 	tmp = wpa_config_parse_string(value, &res_len);
 	if (tmp == NULL) {
 		wpa_printf(MSG_ERROR, "Line %d: failed to parse %s '%s'.",
@@ -127,6 +135,7 @@
 		return -1;
 	}
 
+set:
 	dst = (char **) (((u8 *) ssid) + (long) data->param1);
 	dst_len = (size_t *) (((u8 *) ssid) + (long) data->param2);
 	os_free(*dst);
@@ -500,6 +509,12 @@
 		else if (os_strcmp(start, "FT-EAP") == 0)
 			val |= WPA_KEY_MGMT_FT_IEEE8021X;
 #endif /* CONFIG_IEEE80211R */
+#ifdef CONFIG_IEEE80211W
+		else if (os_strcmp(start, "WPA-PSK-SHA256") == 0)
+			val |= WPA_KEY_MGMT_PSK_SHA256;
+		else if (os_strcmp(start, "WPA-EAP-SHA256") == 0)
+			val |= WPA_KEY_MGMT_IEEE8021X_SHA256;
+#endif /* CONFIG_IEEE80211W */
 		else {
 			wpa_printf(MSG_ERROR, "Line %d: invalid key_mgmt '%s'",
 				   line, start);
@@ -595,6 +610,16 @@
 		pos += os_snprintf(pos, end - pos, "%sFT-EAP",
 				   pos == buf ? "" : " ");
 #endif /* CONFIG_IEEE80211R */
+
+#ifdef CONFIG_IEEE80211W
+	if (ssid->key_mgmt & WPA_KEY_MGMT_PSK_SHA256)
+		pos += os_snprintf(pos, end - pos, "%sWPA-PSK-SHA256",
+				   pos == buf ? "" : " ");
+
+	if (ssid->key_mgmt & WPA_KEY_MGMT_IEEE8021X_SHA256)
+		pos += os_snprintf(pos, end - pos, "%sWPA-EAP-SHA256",
+				   pos == buf ? "" : " ");
+#endif /* CONFIG_IEEE80211W */
 
 	return buf;
 }
@@ -990,6 +1015,14 @@
 				     const char *value)
 {
 	u8 *hash;
+
+	if (os_strcmp(value, "NULL") == 0) {
+		wpa_printf(MSG_DEBUG, "Unset configuration string 'password'");
+		os_free(ssid->eap.password);
+		ssid->eap.password = NULL;
+		ssid->eap.password_len = 0;
+		return 0;
+	}
 
 	if (os_strncmp(value, "hash:", 5) != 0) {
 		char *tmp;

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/config_file.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/config_file.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/config_file.c (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/config_file.c Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * WPA Supplicant / Configuration backend: text file
- * Copyright (c) 2003-2007, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2003-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -104,7 +104,8 @@
 		wpa_config_update_psk(ssid);
 	}
 
-	if ((ssid->key_mgmt & (WPA_KEY_MGMT_PSK | WPA_KEY_MGMT_FT_PSK)) &&
+	if ((ssid->key_mgmt & (WPA_KEY_MGMT_PSK | WPA_KEY_MGMT_FT_PSK |
+			       WPA_KEY_MGMT_PSK_SHA256)) &&
 	    !ssid->psk_set) {
 		wpa_printf(MSG_ERROR, "Line %d: WPA-PSK accepted for key "
 			   "management, but no PSK configured.", line);

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/config_winreg.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/config_winreg.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/config_winreg.c (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/config_winreg.c Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * WPA Supplicant / Configuration backend: Windows registry
- * Copyright (c) 2003-2006, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2003-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -264,7 +264,8 @@
 		wpa_config_update_psk(ssid);
 	}
 
-	if ((ssid->key_mgmt & (WPA_KEY_MGMT_PSK | WPA_KEY_MGMT_FT_PSK)) &&
+	if ((ssid->key_mgmt & (WPA_KEY_MGMT_PSK | WPA_KEY_MGMT_FT_PSK |
+			       WPA_KEY_MGMT_PSK_SHA256)) &&
 	    !ssid->psk_set) {
 		wpa_printf(MSG_ERROR, "WPA-PSK accepted for key management, "
 			   "but no PSK configured for network '" TSTR "'.",

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/ctrl_iface.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/ctrl_iface.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/ctrl_iface.c (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/ctrl_iface.c Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * WPA Supplicant / Control interface (shared code for all backends)
- * Copyright (c) 2004-2007, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2004-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -285,9 +285,8 @@
 		pos += ret;
 	}
 
-	if (wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X ||
-	    wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA ||
-	    wpa_s->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X) {
+	if (wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt) ||
+	    wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA) {
 		res = eapol_sm_get_status(wpa_s->eapol, pos, end - pos,
 					  verbose);
 		if (res >= 0)
@@ -493,6 +492,24 @@
 		first = 0;
 	}
 #endif /* CONFIG_IEEE80211R */
+#ifdef CONFIG_IEEE80211W
+	if (data.key_mgmt & WPA_KEY_MGMT_IEEE8021X_SHA256) {
+		ret = os_snprintf(pos, end - pos, "%sEAP-SHA256",
+				  first ? "" : "+");
+		if (ret < 0 || ret >= end - pos)
+			return pos;
+		pos += ret;
+		first = 0;
+	}
+	if (data.key_mgmt & WPA_KEY_MGMT_PSK_SHA256) {
+		ret = os_snprintf(pos, end - pos, "%sPSK-SHA256",
+				  first ? "" : "+");
+		if (ret < 0 || ret >= end - pos)
+			return pos;
+		pos += ret;
+		first = 0;
+	}
+#endif /* CONFIG_IEEE80211W */
 
 	pos = wpa_supplicant_cipher_txt(pos, end, data.pairwise_cipher);
 

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/defconfig
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/defconfig?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/defconfig (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/defconfig Wed Oct  8 21:24:04 2008
@@ -353,10 +353,7 @@
 #WIRELESS_DEV=/usr/src/wireless-dev
 #CFLAGS += -I$(WIRELESS_DEV)/net/mac80211
 
-# IEEE 802.11r/D4.1 (Fast BSS Transition)
-# This enables an experimental implementation of a draft version of
-# IEEE 802.11r. This draft is still subject to change, so it should be noted
-# that this version may not comply with the final standard.
+# IEEE Std 802.11r-2008 (Fast BSS Transition)
 #CONFIG_IEEE80211R=y
 
 # Add support for writing debug log to a file (/tmp/wpa_supplicant-log-#.txt)

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_gui.sgml
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_gui.sgml?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_gui.sgml (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/doc/docbook/wpa_gui.sgml Wed Oct  8 21:24:04 2008
@@ -16,6 +16,7 @@
       <command>wpa_gui</command>
       <arg>-p <replaceable>path to ctrl sockets</replaceable></arg>
       <arg>-i <replaceable>ifname</replaceable></arg>
+      <arg>-t</arg>
     </cmdsynopsis>
   </refsynopsisdiv>
 
@@ -48,6 +49,14 @@
 	configured. By default, choose the first interface found with
 	a control socket in the socket path.</para></listitem>
       </varlistentry>
+
+      <varlistentry>
+	<term>-t</term>
+
+        <listitem><para>Start program in the system tray only (if the window
+	manager supports it). By default the main status window is
+	shown.</para></listitem>
+      </varlistentry>
     </variablelist>
   </refsect1>
   <refsect1>

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/events.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/events.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/events.c (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/events.c Wed Oct  8 21:24:04 2008
@@ -58,8 +58,9 @@
 		   "AP");
 	if (ssid->key_mgmt & (WPA_KEY_MGMT_PSK | WPA_KEY_MGMT_IEEE8021X |
 			      WPA_KEY_MGMT_WPA_NONE |
-			      WPA_KEY_MGMT_FT_PSK | WPA_KEY_MGMT_FT_IEEE8021X))
-	{
+			      WPA_KEY_MGMT_FT_PSK | WPA_KEY_MGMT_FT_IEEE8021X |
+			      WPA_KEY_MGMT_PSK_SHA256 |
+			      WPA_KEY_MGMT_IEEE8021X_SHA256)) {
 		u8 wpa_ie[80];
 		size_t wpa_ie_len = sizeof(wpa_ie);
 		wpa_supplicant_set_suites(wpa_s, NULL, ssid,
@@ -99,8 +100,7 @@
 	os_memset(wpa_s->pending_bssid, 0, ETH_ALEN);
 	eapol_sm_notify_portEnabled(wpa_s->eapol, FALSE);
 	eapol_sm_notify_portValid(wpa_s->eapol, FALSE);
-	if (wpa_s->key_mgmt == WPA_KEY_MGMT_PSK ||
-	    wpa_s->key_mgmt == WPA_KEY_MGMT_FT_PSK)
+	if (wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt))
 		eapol_sm_notify_eap_success(wpa_s->eapol, FALSE);
 	wpa_s->ap_ies_from_associnfo = 0;
 }
@@ -309,8 +309,8 @@
 		}
 
 #ifdef CONFIG_IEEE80211W
-		if (!(ie.capabilities & WPA_CAPABILITY_MGMT_FRAME_PROTECTION)
-		    && ssid->ieee80211w == IEEE80211W_REQUIRED) {
+		if (!(ie.capabilities & WPA_CAPABILITY_MFPC) &&
+		    ssid->ieee80211w == IEEE80211W_REQUIRED) {
 			wpa_printf(MSG_DEBUG, "   skip RSN IE - no mgmt frame "
 				   "protection");
 			break;
@@ -365,23 +365,18 @@
 
 
 static struct wpa_scan_res *
-wpa_supplicant_select_bss(struct wpa_supplicant *wpa_s, struct wpa_ssid *group,
-			  struct wpa_ssid **selected_ssid)
+wpa_supplicant_select_bss_wpa(struct wpa_supplicant *wpa_s,
+			      struct wpa_ssid *group,
+			      struct wpa_ssid **selected_ssid)
 {
 	struct wpa_ssid *ssid;
-	struct wpa_scan_res *bss, *selected = NULL;
+	struct wpa_scan_res *bss;
 	size_t i;
 	struct wpa_blacklist *e;
 	const u8 *ie;
 
-	wpa_printf(MSG_DEBUG, "Selecting BSS from priority group %d",
-		   group->priority);
-
-	bss = NULL;
-	ssid = NULL;
-	/* First, try to find WPA-enabled AP */
 	wpa_printf(MSG_DEBUG, "Try to find WPA-enabled AP");
-	for (i = 0; i < wpa_s->scan_res->num && !selected; i++) {
+	for (i = 0; i < wpa_s->scan_res->num; i++) {
 		const u8 *ssid_;
 		u8 wpa_ie_len, rsn_ie_len, ssid_len;
 		bss = wpa_s->scan_res->res[i];
@@ -401,6 +396,7 @@
 			   (int) i, MAC2STR(bss->bssid),
 			   wpa_ssid_txt(ssid_, ssid_len),
 			   wpa_ie_len, rsn_ie_len, bss->caps);
+
 		e = wpa_blacklist_get(wpa_s, bss->bssid);
 		if (e && e->count > 1) {
 			wpa_printf(MSG_DEBUG, "   skip - blacklisted");
@@ -417,12 +413,14 @@
 				wpa_printf(MSG_DEBUG, "   skip - disabled");
 				continue;
 			}
+
 			if (ssid_len != ssid->ssid_len ||
 			    os_memcmp(ssid_, ssid->ssid, ssid_len) != 0) {
 				wpa_printf(MSG_DEBUG, "   skip - "
 					   "SSID mismatch");
 				continue;
 			}
+
 			if (ssid->bssid_set &&
 			    os_memcmp(bss->bssid, ssid->bssid, ETH_ALEN) != 0)
 			{
@@ -430,22 +428,36 @@
 					   "BSSID mismatch");
 				continue;
 			}
-			if (wpa_supplicant_ssid_bss_match(ssid, bss)) {
-				selected = bss;
-				*selected_ssid = ssid;
-				wpa_printf(MSG_DEBUG, "   selected WPA AP "
-					   MACSTR " ssid='%s'",
-					   MAC2STR(bss->bssid),
-					   wpa_ssid_txt(ssid_, ssid_len));
-				break;
-			}
-		}
-	}
-
-	/* If no WPA-enabled AP found, try to find non-WPA AP, if configuration
-	 * allows this. */
+
+			if (!wpa_supplicant_ssid_bss_match(ssid, bss))
+				continue;
+
+			wpa_printf(MSG_DEBUG, "   selected WPA AP "
+				   MACSTR " ssid='%s'",
+				   MAC2STR(bss->bssid),
+				   wpa_ssid_txt(ssid_, ssid_len));
+			*selected_ssid = ssid;
+			return bss;
+		}
+	}
+
+	return NULL;
+}
+
+
+static struct wpa_scan_res *
+wpa_supplicant_select_bss_non_wpa(struct wpa_supplicant *wpa_s,
+				  struct wpa_ssid *group,
+				  struct wpa_ssid **selected_ssid)
+{
+	struct wpa_ssid *ssid;
+	struct wpa_scan_res *bss;
+	size_t i;
+	struct wpa_blacklist *e;
+	const u8 *ie;
+
 	wpa_printf(MSG_DEBUG, "Try to find non-WPA AP");
-	for (i = 0; i < wpa_s->scan_res->num && !selected; i++) {
+	for (i = 0; i < wpa_s->scan_res->num; i++) {
 		const u8 *ssid_;
 		u8 wpa_ie_len, rsn_ie_len, ssid_len;
 		bss = wpa_s->scan_res->res[i];
@@ -465,16 +477,19 @@
 			   (int) i, MAC2STR(bss->bssid),
 			   wpa_ssid_txt(ssid_, ssid_len),
 			   wpa_ie_len, rsn_ie_len, bss->caps);
+
 		e = wpa_blacklist_get(wpa_s, bss->bssid);
 		if (e && e->count > 1) {
 			wpa_printf(MSG_DEBUG, "   skip - blacklisted");
 			continue;
 		}
+
 		for (ssid = group; ssid; ssid = ssid->pnext) {
 			if (ssid->disabled) {
 				wpa_printf(MSG_DEBUG, "   skip - disabled");
 				continue;
 			}
+
 			if (ssid->ssid_len != 0 &&
 			    (ssid_len != ssid->ssid_len ||
 			     os_memcmp(ssid_, ssid->ssid, ssid_len) != 0)) {
@@ -500,7 +515,10 @@
 			}
 
 			if ((ssid->key_mgmt & 
-			     (WPA_KEY_MGMT_IEEE8021X | WPA_KEY_MGMT_PSK)) &&
+			     (WPA_KEY_MGMT_IEEE8021X | WPA_KEY_MGMT_PSK |
+			      WPA_KEY_MGMT_FT_IEEE8021X | WPA_KEY_MGMT_FT_PSK |
+			      WPA_KEY_MGMT_IEEE8021X_SHA256 |
+			      WPA_KEY_MGMT_PSK_SHA256)) &&
 			    (wpa_ie_len != 0 || rsn_ie_len != 0)) {
 				wpa_printf(MSG_DEBUG, "   skip - "
 					   "WPA network");
@@ -519,17 +537,36 @@
 				continue;
 			}
 
-			selected = bss;
-			*selected_ssid = ssid;
 			wpa_printf(MSG_DEBUG, "   selected non-WPA AP "
 				   MACSTR " ssid='%s'",
 				   MAC2STR(bss->bssid),
 				   wpa_ssid_txt(ssid_, ssid_len));
-			break;
-		}
-	}
-
-	return selected;
+			*selected_ssid = ssid;
+			return bss;
+		}
+	}
+
+	return NULL;
+}
+
+
+static struct wpa_scan_res *
+wpa_supplicant_select_bss(struct wpa_supplicant *wpa_s, struct wpa_ssid *group,
+			  struct wpa_ssid **selected_ssid)
+{
+	struct wpa_scan_res *selected;
+
+	wpa_printf(MSG_DEBUG, "Selecting BSS from priority group %d",
+		   group->priority);
+
+	/* First, try to find WPA-enabled AP */
+	selected = wpa_supplicant_select_bss_wpa(wpa_s, group, selected_ssid);
+	if (selected)
+		return selected;
+
+	/* If no WPA-enabled AP found, try to find non-WPA AP, if configuration
+	 * allows this. */
+	return wpa_supplicant_select_bss_non_wpa(wpa_s, group, selected_ssid);
 }
 
 
@@ -548,9 +585,18 @@
 		goto req_scan;
 	}
 
-	wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_SCAN_RESULTS);
-
-	wpa_supplicant_dbus_notify_scan_results(wpa_s);
+	/*
+	 * Don't post the results if this was the initial cached
+	 * and there were no results.
+	 */
+	if (wpa_s->scan_res_tried == 1 && wpa_s->conf->ap_scan == 1 &&
+	    wpa_s->scan_res->num == 0) {
+		wpa_msg(wpa_s, MSG_DEBUG, "Cached scan results are "
+			"empty - not posting");
+	} else {
+		wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_SCAN_RESULTS);
+		wpa_supplicant_dbus_notify_scan_results(wpa_s);
+	}
 
 	if (wpa_s->conf->ap_scan == 2 || wpa_s->disconnected)
 		return;
@@ -750,8 +796,7 @@
 		eapol_sm_notify_portEnabled(wpa_s->eapol, FALSE);
 		eapol_sm_notify_portValid(wpa_s->eapol, FALSE);
 	}
-	if (wpa_s->key_mgmt == WPA_KEY_MGMT_PSK ||
-	    wpa_s->key_mgmt == WPA_KEY_MGMT_FT_PSK || ft_completed)
+	if (wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt) || ft_completed)
 		eapol_sm_notify_eap_success(wpa_s->eapol, FALSE);
 	/* 802.1X::portControl = Auto */
 	eapol_sm_notify_portEnabled(wpa_s->eapol, TRUE);
@@ -767,8 +812,7 @@
 	wpa_supplicant_cancel_scan(wpa_s);
 
 	if (wpa_s->driver_4way_handshake &&
-	    (wpa_s->key_mgmt == WPA_KEY_MGMT_PSK ||
-	     wpa_s->key_mgmt == WPA_KEY_MGMT_FT_PSK)) {
+	    wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt)) {
 		/*
 		 * We are done; the driver will take care of RSN 4-way
 		 * handshake.
@@ -797,8 +841,7 @@
 	}
 
 	if (wpa_s->wpa_state == WPA_4WAY_HANDSHAKE &&
-	    (wpa_s->key_mgmt == WPA_KEY_MGMT_PSK ||
-	     wpa_s->key_mgmt == WPA_KEY_MGMT_FT_PSK)) {
+	    wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt)) {
 		wpa_msg(wpa_s, MSG_INFO, "WPA: 4-Way Handshake failed - "
 			"pre-shared key may be incorrect");
 	}

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/main_winsvc.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/main_winsvc.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/main_winsvc.c (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/main_winsvc.c Wed Oct  8 21:24:04 2008
@@ -162,6 +162,13 @@
 	}
 
 	buflen = sizeof(val);
+	ret = RegQueryValueEx(hk, TEXT("debug_timestamp"), NULL, NULL,
+			      (LPBYTE) &val, &buflen);
+	if (ret == ERROR_SUCCESS && buflen == sizeof(val)) {
+		params.wpa_debug_timestamp = val;
+	}
+
+	buflen = sizeof(val);
 	ret = RegQueryValueEx(hk, TEXT("debug_use_file"), NULL, NULL,
 			      (LPBYTE) &val, &buflen);
 	if (ret == ERROR_SUCCESS && buflen == sizeof(val) && val) {

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/mlme.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/mlme.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/mlme.c (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/mlme.c Wed Oct  8 21:24:04 2008
@@ -129,6 +129,8 @@
 	u8 mdie_len;
 	u8 *ftie;
 	u8 ftie_len;
+	u8 *assoc_comeback;
+	u8 assoc_comeback_len;
 };
 
 typedef enum { ParseOK = 0, ParseUnknown = 1, ParseFailed = -1 } ParseRes;
@@ -231,6 +233,10 @@
 			elems->ftie = pos;
 			elems->ftie_len = elen;
 			break;
+		case WLAN_EID_ASSOC_COMEBACK_TIME:
+			elems->assoc_comeback = pos;
+			elems->assoc_comeback_len = elen;
+			break;
 		default:
 #if 0
 			wpa_printf(MSG_MSGDUMP "MLME: IEEE 802.11 element "
@@ -840,8 +846,6 @@
 	supp_rates[1] = 0;
 	for (i = 0; i < wpa_s->mlme.num_curr_rates; i++) {
 		struct wpa_rate_data *rate = &wpa_s->mlme.curr_rates[i];
-		if (!(rate->flags & WPA_RATE_SUPPORTED))
-			continue;
 		if (esupp_rates) {
 			pos = buf + len;
 			len++;
@@ -851,6 +855,7 @@
 			esupp_rates[0] = WLAN_EID_EXT_SUPP_RATES;
 			esupp_rates[1] = 1;
 			pos = &esupp_rates[2];
+			len += 3;
 		} else {
 			pos = buf + len;
 			len++;
@@ -1232,16 +1237,32 @@
 		   reassoc ? "Rea" : "A", MAC2STR(mgmt->sa),
 		   capab_info, status_code, aid);
 
-	if (status_code != WLAN_STATUS_SUCCESS) {
-		wpa_printf(MSG_DEBUG, "MLME: AP denied association (code=%d)",
-			   status_code);
-		return;
-	}
-
 	pos = mgmt->u.assoc_resp.variable;
 	if (ieee802_11_parse_elems(pos, len - (pos - (u8 *) mgmt), &elems)
 	    == ParseFailed) {
 		wpa_printf(MSG_DEBUG, "MLME: failed to parse AssocResp");
+		return;
+	}
+
+	if (status_code != WLAN_STATUS_SUCCESS) {
+		wpa_printf(MSG_DEBUG, "MLME: AP denied association (code=%d)",
+			   status_code);
+#ifdef CONFIG_IEEE80211W
+		if (status_code == WLAN_STATUS_ASSOC_REJECTED_TEMPORARILY &&
+		    elems.assoc_comeback && elems.assoc_comeback_len == 4) {
+			u32 tu, ms;
+			tu = WPA_GET_LE32(elems.assoc_comeback);
+			ms = tu * 1024 / 1000;
+			wpa_printf(MSG_DEBUG, "MLME: AP rejected association "
+				   "temporarily; comeback duration %u TU "
+				   "(%u ms)", tu, ms);
+			if (ms > IEEE80211_ASSOC_TIMEOUT) {
+				wpa_printf(MSG_DEBUG, "MLME: Update timer "
+					   "based on comeback duration");
+				ieee80211_reschedule_timer(wpa_s, ms);
+			}
+		}
+#endif /* CONFIG_IEEE80211W */
 		return;
 	}
 
@@ -1815,6 +1836,7 @@
 }
 
 
+#ifdef CONFIG_IEEE80211R
 static void ieee80211_rx_mgmt_ft_action(struct wpa_supplicant *wpa_s,
 					struct ieee80211_mgmt *mgmt,
 					size_t len,
@@ -1874,6 +1896,78 @@
 	os_memcpy(wpa_s->bssid, target_ap_addr, ETH_ALEN);
 	ieee80211_associate(wpa_s);
 }
+#endif /* CONFIG_IEEE80211R */
+
+
+#ifdef CONFIG_IEEE80211W
+
+/* MLME-PING.response */
+static int ieee80211_sta_send_ping_resp(struct wpa_supplicant *wpa_s,
+					const u8 *addr, const u8 *trans_id)
+{
+	struct ieee80211_mgmt *mgmt;
+	int res;
+	size_t len;
+
+	mgmt = os_zalloc(sizeof(*mgmt));
+	if (mgmt == NULL) {
+		wpa_printf(MSG_DEBUG, "MLME: Failed to allocate buffer for "
+			   "ping action frame");
+		return -1;
+	}
+
+	len = 24;
+	os_memcpy(mgmt->da, addr, ETH_ALEN);
+	os_memcpy(mgmt->sa, wpa_s->own_addr, ETH_ALEN);
+	os_memcpy(mgmt->bssid, wpa_s->bssid, ETH_ALEN);
+	mgmt->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT,
+					   WLAN_FC_STYPE_ACTION);
+	mgmt->u.action.category = WLAN_ACTION_PING;
+	mgmt->u.action.u.ping_resp.action = WLAN_PING_RESPONSE;
+	os_memcpy(mgmt->u.action.u.ping_resp.trans_id, trans_id,
+		  WLAN_PING_TRANS_ID_LEN);
+	len += 1 + sizeof(mgmt->u.action.u.ping_resp);
+
+	res = ieee80211_sta_tx(wpa_s, (u8 *) mgmt, len);
+	os_free(mgmt);
+
+	return res;
+}
+
+
+static void ieee80211_rx_mgmt_ping_action(
+	struct wpa_supplicant *wpa_s, struct ieee80211_mgmt *mgmt, size_t len,
+	struct ieee80211_rx_status *rx_status)
+{
+	if (len < 24 + 1 + sizeof(mgmt->u.action.u.ping_req)) {
+		wpa_printf(MSG_DEBUG, "MLME: Too short Ping Action frame");
+		return;
+	}
+
+	if (mgmt->u.action.u.ping_req.action != WLAN_PING_REQUEST) {
+		wpa_printf(MSG_DEBUG, "MLME: Unexpected Ping Action %d",
+			   mgmt->u.action.u.ping_req.action);
+		return;
+	}
+
+	if (os_memcmp(mgmt->sa, wpa_s->bssid, ETH_ALEN) != 0) {
+		wpa_printf(MSG_DEBUG, "MLME: Ignore ping from unknown source "
+			   MACSTR, MAC2STR(mgmt->sa));
+		return;
+	}
+
+	if (wpa_s->mlme.state == IEEE80211_ASSOCIATE) {
+		wpa_printf(MSG_DEBUG, "MLME: Ignore ping request during "
+			   "association process");
+		return;
+	}
+
+	wpa_printf(MSG_DEBUG, "MLME: Replying to ping request");
+	ieee80211_sta_send_ping_resp(wpa_s, mgmt->sa,
+				     mgmt->u.action.u.ping_req.trans_id);
+}
+
+#endif /* CONFIG_IEEE80211W */
 
 
 static void ieee80211_rx_mgmt_action(struct wpa_supplicant *wpa_s,
@@ -1886,11 +1980,22 @@
 	if (len < 25)
 		return;
 
-	if (mgmt->u.action.category == WLAN_ACTION_FT)
+	switch (mgmt->u.action.category) {
+#ifdef CONFIG_IEEE80211R
+	case WLAN_ACTION_FT:
 		ieee80211_rx_mgmt_ft_action(wpa_s, mgmt, len, rx_status);
-	else
+		break;
+#endif /* CONFIG_IEEE80211R */
+#ifdef CONFIG_IEEE80211W
+	case WLAN_ACTION_PING:
+		ieee80211_rx_mgmt_ping_action(wpa_s, mgmt, len, rx_status);
+		break;
+#endif /* CONFIG_IEEE80211W */
+	default:
 		wpa_printf(MSG_DEBUG, "MLME: unknown Action Category %d",
 			   mgmt->u.action.category);
+		break;
+	}
 }
 
 
@@ -3018,8 +3123,8 @@
 	len += 1 + sizeof(mgmt->u.action.u.ft_action_req) + ies_len;
 
 	wpa_printf(MSG_DEBUG, "MLME: Send FT Action Frame: Action=%d "
-		   "Target AP=" MACSTR " body_len=%d",
-		   action, MAC2STR(target_ap), ies_len);
+		   "Target AP=" MACSTR " body_len=%lu",
+		   action, MAC2STR(target_ap), (unsigned long) ies_len);
 
 	res = ieee80211_sta_tx(wpa_s, buf, len);
 	os_free(buf);

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/scan.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/scan.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/scan.c (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/scan.c Wed Oct  8 21:24:04 2008
@@ -137,6 +137,7 @@
 	if (wpa_s->scan_res_tried == 0 && wpa_s->conf->ap_scan == 1 &&
 	    !wpa_s->use_client_mlme) {
 		wpa_s->scan_res_tried++;
+		wpa_s->scan_req = scan_req;
 		wpa_printf(MSG_DEBUG, "Trying to get current scan results "
 			   "first without requesting a new scan to speed up "
 			   "initial association");

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/win_example.reg
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/win_example.reg?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/win_example.reg (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/win_example.reg Wed Oct  8 21:24:04 2008
@@ -3,12 +3,14 @@
 [HKEY_LOCAL_MACHINE\SOFTWARE\wpa_supplicant]
 "debug_level"=dword:00000000
 "debug_show_keys"=dword:00000001
+"debug_timestamp"=dword:00000000
 "debug_use_file"=dword:00000000
 
 [HKEY_LOCAL_MACHINE\SOFTWARE\wpa_supplicant\configs]
 
 [HKEY_LOCAL_MACHINE\SOFTWARE\wpa_supplicant\configs\test]
 "ap_scan"=dword:00000002
+"update_config"=dword:00000001
 
 [HKEY_LOCAL_MACHINE\SOFTWARE\wpa_supplicant\configs\test\blobs]
 "testblob"=hex:01,02,03,04,05

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/.gitignore
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/.gitignore?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/.gitignore (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/.gitignore Wed Oct  8 21:24:04 2008
@@ -3,3 +3,4 @@
 .ui
 Makefile
 wpa_gui
+qrc_icons.cpp

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/eventhistory.ui
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/eventhistory.ui?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/eventhistory.ui (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/eventhistory.ui Wed Oct  8 21:24:04 2008
@@ -52,7 +52,7 @@
   </layout>
  </widget>
  <layoutdefault spacing="6" margin="11" />
- <pixmapfunction>qPixmapFromMimeSource</pixmapfunction>
+ <pixmapfunction></pixmapfunction>
  <includes>
   <include location="local" >wpamsg.h</include>
  </includes>

Added: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons.qrc
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons.qrc?rev=1266&op=file
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons.qrc (added)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons.qrc Wed Oct  8 21:24:04 2008
@@ -1,0 +1,5 @@
+<RCC>
+ <qresource prefix="/icons" >
+  <file alias="wpa_gui.svg">icons/wpa_gui.svg</file>
+ </qresource>
+</RCC>

Added: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/Makefile
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/Makefile?rev=1266&op=file
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/Makefile (added)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/Makefile Wed Oct  8 21:24:04 2008
@@ -1,0 +1,23 @@
+#!/usr/bin/make -f
+
+NAME  := wpa_gui
+SVG   := $(NAME).svg
+SIZES := 16x16 22x22 32x32 48x48 64x64 128x128
+ICONS := $(addsuffix .png,$(SIZES))
+ICONS += $(addsuffix .xpm,16x16 32x32)
+
+all: $(ICONS)
+
+%.png:
+	mkdir -p hicolor/$(@:.png=)/apps/
+	inkscape $(SVG) --without-gui \
+		--export-width=$(word 1,$(subst x, ,$(@:.png=)))  \
+	        --export-height=$(word 2,$(subst x, ,$(@:.png=))) \
+		--export-png=hicolor/$(@:.png=)/apps/$(NAME).png
+
+%.xpm:
+	mkdir -p pixmaps/
+	convert hicolor/$(@:.xpm=)/apps/$(NAME).png pixmaps/$@
+
+clean:
+	$(RM) -r pixmaps hicolor

Added: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/README
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/README?rev=1266&op=file
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/README (added)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/README Wed Oct  8 21:24:04 2008
@@ -1,0 +1,7 @@
+Copyright (c) 2008 Bernard Gray <bernard.gray at gmail.com>
+
+The wpa_gui icon is licensed under the GPL version 2. Alternatively, the icon
+may be distributed under the terms of BSD license.
+
+To convert the svg icon to other formats, make sure inkscape and imagemagick
+are installed and use `make' to create various sized png and xpm icons.

Added: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/wpa_gui.svg
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/wpa_gui.svg?rev=1266&op=file
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/wpa_gui.svg (added)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/icons/wpa_gui.svg Wed Oct  8 21:24:04 2008
@@ -1,0 +1,256 @@
+<?xml version="1.0" encoding="UTF-8" standalone="no"?>
+<!-- Created with Inkscape (http://www.inkscape.org/) -->
+<svg
+   xmlns:dc="http://purl.org/dc/elements/1.1/"
+   xmlns:cc="http://creativecommons.org/ns#"
+   xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
+   xmlns:svg="http://www.w3.org/2000/svg"
+   xmlns="http://www.w3.org/2000/svg"
+   xmlns:xlink="http://www.w3.org/1999/xlink"
+   xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
+   xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
+   version="1.0"
+   width="128"
+   height="128"
+   id="svg2"
+   sodipodi:version="0.32"
+   inkscape:version="0.46"
+   sodipodi:docname="wpa_gui.svg"
+   inkscape:output_extension="org.inkscape.output.svg.inkscape">
+  <metadata
+     id="metadata47">
+    <rdf:RDF>
+      <cc:Work
+         rdf:about="">
+        <dc:format>image/svg+xml</dc:format>
+        <dc:type
+           rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
+      </cc:Work>
+    </rdf:RDF>
+  </metadata>
+  <sodipodi:namedview
+     inkscape:window-height="771"
+     inkscape:window-width="640"
+     inkscape:pageshadow="2"
+     inkscape:pageopacity="0.0"
+     guidetolerance="10.0"
+     gridtolerance="10.0"
+     objecttolerance="10.0"
+     borderopacity="1.0"
+     bordercolor="#666666"
+     pagecolor="#ffffff"
+     id="base"
+     showgrid="false"
+     inkscape:zoom="4.2421875"
+     inkscape:cx="64"
+     inkscape:cy="64"
+     inkscape:window-x="634"
+     inkscape:window-y="0"
+     inkscape:current-layer="svg2" />
+  <defs
+     id="defs4">
+    <inkscape:perspective
+       sodipodi:type="inkscape:persp3d"
+       inkscape:vp_x="0 : 64 : 1"
+       inkscape:vp_y="0 : 1000 : 0"
+       inkscape:vp_z="128 : 64 : 1"
+       inkscape:persp3d-origin="64 : 42.666667 : 1"
+       id="perspective49" />
+    <linearGradient
+       id="linearGradient39133">
+      <stop
+         id="stop39135"
+         style="stop-color:#252525;stop-opacity:1"
+         offset="0" />
+      <stop
+         id="stop39137"
+         style="stop-color:#515151;stop-opacity:1"
+         offset="0" />
+      <stop
+         id="stop39139"
+         style="stop-color:#878787;stop-opacity:1"
+         offset="0.28677997" />
+      <stop
+         id="stop39141"
+         style="stop-color:#000000;stop-opacity:1"
+         offset="0.92151743" />
+      <stop
+         id="stop39143"
+         style="stop-color:#ffffff;stop-opacity:0.73786408"
+         offset="1" />
+    </linearGradient>
+    <linearGradient
+       id="linearGradient39119">
+      <stop
+         id="stop39121"
+         style="stop-color:#ffffff;stop-opacity:0.82905984"
+         offset="0" />
+      <stop
+         id="stop39123"
+         style="stop-color:#ffffff;stop-opacity:0"
+         offset="1" />
+    </linearGradient>
+    <linearGradient
+       id="linearGradient39106">
+      <stop
+         id="stop39108"
+         style="stop-color:#ffffff;stop-opacity:1"
+         offset="0" />
+      <stop
+         id="stop39110"
+         style="stop-color:#a8a8a8;stop-opacity:0"
+         offset="1" />
+    </linearGradient>
+    <linearGradient
+       id="linearGradient39094">
+      <stop
+         id="stop39096"
+         style="stop-color:#000000;stop-opacity:1"
+         offset="0" />
+      <stop
+         id="stop39098"
+         style="stop-color:#333333;stop-opacity:1"
+         offset="1" />
+    </linearGradient>
+    <linearGradient
+       id="linearGradient39062">
+      <stop
+         id="stop39064"
+         style="stop-color:#252525;stop-opacity:1"
+         offset="0" />
+      <stop
+         id="stop39086"
+         style="stop-color:#515151;stop-opacity:1"
+         offset="0.21101321" />
+      <stop
+         id="stop39088"
+         style="stop-color:#878787;stop-opacity:1"
+         offset="0.75" />
+      <stop
+         id="stop39090"
+         style="stop-color:#6c6c6c;stop-opacity:1"
+         offset="0.875" />
+      <stop
+         id="stop39066"
+         style="stop-color:#1e1e1e;stop-opacity:1"
+         offset="1" />
+    </linearGradient>
+    <linearGradient
+       x1="4"
+       y1="40"
+       x2="124"
+       y2="60"
+       id="linearGradient39068"
+       xlink:href="#linearGradient39062"
+       gradientUnits="userSpaceOnUse" />
+    <radialGradient
+       cx="100.70589"
+       cy="96"
+       r="60"
+       fx="158.07428"
+       fy="95.718063"
+       id="radialGradient39100"
+       xlink:href="#linearGradient39094"
+       gradientUnits="userSpaceOnUse"
+       gradientTransform="matrix(2.7837903e-8,-1,0.99999999,-2.1864248e-6,-32.000004,164.7061)" />
+    <radialGradient
+       cx="100.44444"
+       cy="34.363636"
+       r="32"
+       fx="83.18"
+       fy="34.228985"
+       id="radialGradient39104"
+       xlink:href="#linearGradient39106"
+       gradientUnits="userSpaceOnUse"
+       gradientTransform="matrix(3.1472435e-6,1.0227273,-0.87499999,-9.5061964e-8,94.067865,-4.7272712)" />
+    <radialGradient
+       cx="75.999977"
+       cy="-2.7730541"
+       r="48"
+       fx="55.266491"
+       fy="-2.5338216"
+       id="radialGradient39125"
+       xlink:href="#linearGradient39119"
+       gradientUnits="userSpaceOnUse"
+       gradientTransform="matrix(0,0.83333324,-1.6666667,2.518705e-6,59.378243,-35.333302)" />
+    <radialGradient
+       cx="64.066589"
+       cy="63.713329"
+       r="60"
+       fx="64.066589"
+       fy="63.713329"
+       id="radialGradient39131"
+       xlink:href="#linearGradient39133"
+       gradientUnits="userSpaceOnUse"
+       gradientTransform="matrix(1.1333333,5.1768857e-8,5.2556881e-6,1.1666667,-8.6091298,-10.332226)" />
+    <filter
+       id="filter39153">
+      <feGaussianBlur
+         id="feGaussianBlur39155"
+         stdDeviation="2.28"
+         inkscape:collect="always" />
+    </filter>
+    <filter
+       id="filter39159">
+      <feGaussianBlur
+         inkscape:collect="always"
+         stdDeviation="1.68"
+         id="feGaussianBlur39161" />
+    </filter>
+  </defs>
+  <g
+     id="layer1"
+     style="display:inline">
+    <path
+       d="M 29,4 C 15.147058,4 4,15.14706 4,29 l 0,70 c 0,13.85294 11.147058,25 25,25 l 70,0 c 13.85294,0 25,-11.14706 25,-25 l 0,-70 C 124,15.14706 112.85294,4 99,4 L 29,4 z"
+       id="path39151"
+       style="opacity:1;fill:#000000;fill-opacity:1;stroke:none;filter:url(#filter39153)" />
+    <path
+       d="M 29,4 C 15.147058,4 4,15.14706 4,29 l 0,70 c 0,13.85294 11.147058,25 25,25 l 70,0 c 13.85294,0 25,-11.14706 25,-25 l 0,-70 C 124,15.14706 112.85294,4 99,4 L 29,4 z"
+       id="path39157"
+       style="opacity:1;fill:#000000;fill-opacity:1;stroke:none;filter:url(#filter39159)" />
+    <rect
+       width="120"
+       height="120"
+       ry="25.00531"
+       x="4"
+       y="0"
+       id="rect2573"
+       style="opacity:1;fill:url(#radialGradient39100);fill-opacity:1;stroke:none" />
+    <path
+       d="M 29,0 C 15.147058,0 4,11.14706 4,25 l 0,70 c 0,13.85294 11.147058,25 25,25 l 70,0 c 13.85294,0 25,-11.14706 25,-25 l 0,-70 C 124,11.14706 112.85294,0 99,0 L 29,0 z"
+       id="path39127"
+       style="opacity:0.20512821;fill:url(#radialGradient39131);fill-opacity:1;stroke:none" />
+    <path
+       d="m 44,68 40,0 12,40 c -20,7.27273 -44,7.27273 -64,0 L 44,68 z"
+       id="path39102"
+       style="opacity:0.53418801;fill:url(#radialGradient39104);fill-opacity:1;stroke:none" />
+    <path
+       d="M 25.339207,12 C 52,8 76,8 102.66079,12 107.83471,12 112,16.165286 112,21.339207 L 116,52 C 100,73.339207 28,73.339207 12,52 L 16,21.339207 C 16,16.165286 20.165286,12 25.339207,12 z"
+       id="rect39116"
+       style="opacity:0.92307691;fill:url(#radialGradient39125);fill-opacity:1;stroke:none" />
+    <path
+       d="M 29,8 C 15.147058,8 4,19.14706 4,33 l 0,70 c 0,13.85294 11.147058,25 25,25 l 70,0 c 13.85294,0 25,-11.14706 25,-25 l 0,-70 C 124,19.14706 112.85294,8 99,8 L 29,8 z"
+       id="path39147"
+       style="opacity:0.20512821;fill:#000000;fill-opacity:1;stroke:none" />
+    <path
+       d="M 29,0 C 15.147058,0 4,11.147058 4,25 l 0,70 c 0,13.85294 11.147058,25 25,25 l 70,0 c 13.85294,0 25,-11.14706 25,-25 l 0,-70 C 124,11.147058 112.85294,0 99,0 L 29,0 z m 0,4 70,0 c 11.70613,0 21,9.293869 21,21 l 0,70 c 0,11.70613 -9.29387,21 -21,21 l -70,0 C 17.293869,116 8,106.70613 8,95 L 8,25 C 8,13.293869 17.293869,4 29,4 z"
+       id="rect39029"
+       style="opacity:1;fill:url(#linearGradient39068);fill-opacity:1;stroke:none" />
+    <path
+       d="M 66.35081,74.771345 A 36,36 0 1 1 54.34964,35.777782"
+       transform="matrix(-0.16680323,0.53082142,-0.53082142,-0.16680323,103.31027,53.117897)"
+       id="path3351"
+       style="opacity:1;fill:none;stroke:#ffffff;stroke-width:21.56673813;stroke-linecap:round;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
+    <path
+       d="m 36,56 a 4,4 0 1 1 -8,0 4,4 0 1 1 8,0 z"
+       transform="matrix(1.4851301,0,0,1.4851301,16.475837,-23.948973)"
+       id="path3353"
+       style="opacity:1;fill:#ffffff;fill-opacity:1;stroke:none" />
+    <path
+       d="M 66.35081,74.771345 A 36,36 0 1 1 54.34964,35.777782"
+       transform="matrix(-0.35033273,1.1148712,-1.1148712,-0.35033273,146.5624,46.88078)"
+       id="path2622"
+       style="opacity:1;fill:none;stroke:#ffffff;stroke-width:10.26852894;stroke-linecap:round;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
+  </g>
+</svg>

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/main.cpp
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/main.cpp?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/main.cpp (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/main.cpp Wed Oct  8 21:24:04 2008
@@ -32,8 +32,6 @@
 	}
 #endif /* CONFIG_NATIVE_WINDOWS */
 
-	w.show();
-	app.connect(&app, SIGNAL(lastWindowClosed()), &app, SLOT(quit()));
 	ret = app.exec();
 
 #ifdef CONFIG_NATIVE_WINDOWS

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.cpp
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.cpp?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.cpp (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.cpp Wed Oct  8 21:24:04 2008
@@ -41,6 +41,8 @@
 	connect(encrSelect, SIGNAL(activated(const QString &)), this,
 		SLOT(encrChanged(const QString &)));
 	connect(removeButton, SIGNAL(clicked()), this, SLOT(removeNetwork()));
+	connect(eapSelect, SIGNAL(activated(int)), this,
+		SLOT(eapChanged(int)));
 
 	wpagui = NULL;
 	new_network = false;
@@ -107,6 +109,9 @@
 	identityEdit->setEnabled(eap);
 	passwordEdit->setEnabled(eap);
 	cacertEdit->setEnabled(eap);
+	phase2Select->setEnabled(eap);
+	if (eap)
+		eapChanged(eapSelect->currentIndex());
 
 	while (encrSelect->count())
 		encrSelect->removeItem(0);
@@ -123,6 +128,48 @@
 	}
 
 	wepEnabled(sel == AUTH_IEEE8021X);
+}
+
+
+void NetworkConfig::eapChanged(int sel)
+{
+	QString prev_val = phase2Select->currentText();
+	while (phase2Select->count())
+		phase2Select->removeItem(0);
+
+	QStringList inner;
+	inner << "PEAP" << "TTLS" << "FAST";
+	if (!inner.contains(eapSelect->itemText(sel)))
+		return;
+
+	phase2Select->addItem("[ any ]");
+
+	/* Add special cases based on outer method */
+	if (eapSelect->currentText().compare("TTLS") == 0) {
+		phase2Select->addItem("PAP");
+		phase2Select->addItem("CHAP");
+		phase2Select->addItem("MSCHAP");
+		phase2Select->addItem("MSCHAPv2");
+	} else if (eapSelect->currentText().compare("FAST") == 0)
+		phase2Select->addItem("GTC(auth) + MSCHAPv2(prov)");
+
+	/* Add all enabled EAP methods that can be used in the tunnel */
+	int i;
+	QStringList allowed;
+	allowed << "MSCHAPV2" << "MD5" << "GTC" << "TLS" << "OTP" << "SIM"
+		<< "AKA";
+	for (i = 0; i < eapSelect->count(); i++) {
+		if (allowed.contains(eapSelect->itemText(i))) {
+			phase2Select->addItem("EAP-" + eapSelect->itemText(i));
+		}
+	}
+
+	for (i = 0; i < phase2Select->count(); i++) {
+		if (phase2Select->itemText(i).compare(prev_val) == 0) {
+			phase2Select->setCurrentIndex(i);
+			break;
+		}
+	}
 }
 
 
@@ -230,24 +277,81 @@
 		setNetworkParam(id, "psk",
 				pskEdit->text().toAscii().constData(),
 				psklen != 64);
-	if (eapSelect->isEnabled())
-		setNetworkParam(id, "eap",
-				eapSelect->currentText().toAscii().constData(),
-				false);
-	if (identityEdit->isEnabled())
+	if (eapSelect->isEnabled()) {
+		const char *eap =
+			eapSelect->currentText().toAscii().constData();
+		setNetworkParam(id, "eap", eap, false);
+		if (strcmp(eap, "SIM") == 0 || strcmp(eap, "AKA") == 0)
+			setNetworkParam(id, "pcsc", "", true);
+		else
+			setNetworkParam(id, "pcsc", "NULL", false);
+	}
+	if (phase2Select->isEnabled()) {
+		QString eap = eapSelect->currentText();
+		QString inner = phase2Select->currentText();
+		char phase2[32];
+		phase2[0] = '\0';
+		if (eap.compare("PEAP") == 0) {
+			if (inner.startsWith("EAP-"))
+				snprintf(phase2, sizeof(phase2), "auth=%s",
+					 inner.right(inner.size() - 4).
+					 toAscii().constData());
+		} else if (eap.compare("TTLS") == 0) {
+			if (inner.startsWith("EAP-"))
+				snprintf(phase2, sizeof(phase2), "autheap=%s",
+					 inner.right(inner.size() - 4).
+					 toAscii().constData());
+			else
+				snprintf(phase2, sizeof(phase2), "auth=%s",
+					 inner.toAscii().constData());
+		} else if (eap.compare("FAST") == 0) {
+			char *provisioning = NULL;
+			if (inner.startsWith("EAP-")) {
+				snprintf(phase2, sizeof(phase2), "auth=%s",
+					 inner.right(inner.size() - 4).
+					 toAscii().constData());
+				provisioning = "fast_provisioning=2";
+			} else if (inner.compare("GTC(auth) + MSCHAPv2(prov)")
+				   == 0) {
+				snprintf(phase2, sizeof(phase2),
+					 "auth=GTC auth=MSCHAPV2");
+				provisioning = "fast_provisioning=1";
+			}
+			if (provisioning) {
+				char blob[32];
+				setNetworkParam(id, "phase1", provisioning,
+						true);
+				snprintf(blob, sizeof(blob),
+					 "blob://fast-pac-%d", id);
+				setNetworkParam(id, "pac_file", blob, true);
+			}
+		}
+		if (phase2[0])
+			setNetworkParam(id, "phase2", phase2, true);
+		else
+			setNetworkParam(id, "phase2", "NULL", false);
+	} else
+		setNetworkParam(id, "phase2", "NULL", false);
+	if (identityEdit->isEnabled() && identityEdit->text().length() > 0)
 		setNetworkParam(id, "identity",
 				identityEdit->text().toAscii().constData(),
 				true);
-	if (passwordEdit->isEnabled() &&
+	else
+		setNetworkParam(id, "identity", "NULL", false);
+	if (passwordEdit->isEnabled() && passwordEdit->text().length() > 0 &&
 	    strcmp(passwordEdit->text().toAscii().constData(),
 		   WPA_GUI_KEY_DATA) != 0)
 		setNetworkParam(id, "password",
 				passwordEdit->text().toAscii().constData(),
 				true);
-	if (cacertEdit->isEnabled())
+	else if (passwordEdit->text().length() == 0)
+		setNetworkParam(id, "password", "NULL", false);
+	if (cacertEdit->isEnabled() && cacertEdit->text().length() > 0)
 		setNetworkParam(id, "ca_cert",
 				cacertEdit->text().toAscii().constData(),
 				true);
+	else
+		setNetworkParam(id, "ca_cert", "NULL", false);
 	writeWepKey(id, wep0Edit, 0);
 	writeWepKey(id, wep1Edit, 1);
 	writeWepKey(id, wep2Edit, 2);
@@ -262,10 +366,12 @@
 	else if (wep3Radio->isEnabled() && wep3Radio->isChecked())
 		setNetworkParam(id, "wep_tx_keyidx", "3", false);
 
-	if (idstrEdit->isEnabled())
+	if (idstrEdit->isEnabled() && idstrEdit->text().length() > 0)
 		setNetworkParam(id, "id_str",
 				idstrEdit->text().toAscii().constData(),
 				true);
+	else
+		setNetworkParam(id, "id_str", "NULL", false);
 
 	if (prioritySpinBox->isEnabled()) {
 		QString prio;
@@ -481,6 +587,7 @@
 		cacertEdit->setText(reply + 1);
 	}
 
+	enum { NO_INNER, PEAP_INNER, TTLS_INNER, FAST_INNER } eap = NO_INNER;
 	snprintf(cmd, sizeof(cmd), "GET_NETWORK %d eap", network_id);
 	reply_len = sizeof(reply) - 1;
 	if (wpagui->ctrlRequest(cmd, reply, &reply_len) >= 0 &&
@@ -489,8 +596,68 @@
 		for (i = 0; i < eapSelect->count(); i++) {
 			if (eapSelect->itemText(i).compare(reply) == 0) {
 				eapSelect->setCurrentIndex(i);
+				if (strcmp(reply, "PEAP") == 0)
+					eap = PEAP_INNER;
+				else if (strcmp(reply, "TTLS") == 0)
+					eap = TTLS_INNER;
+				else if (strcmp(reply, "FAST") == 0)
+					eap = FAST_INNER;
 				break;
 			}
+		}
+	}
+
+	if (eap != NO_INNER) {
+		snprintf(cmd, sizeof(cmd), "GET_NETWORK %d phase2",
+			 network_id);
+		reply_len = sizeof(reply) - 1;
+		if (wpagui->ctrlRequest(cmd, reply, &reply_len) >= 0 &&
+		    reply_len >= 1) {
+			reply[reply_len] = '\0';
+			eapChanged(eapSelect->currentIndex());
+		} else
+			eap = NO_INNER;
+	}
+
+	char *val;
+	val = reply + 1;
+	while (*(val + 1))
+		val++;
+	if (*val == '"')
+		*val = '\0';
+
+	switch (eap) {
+	case PEAP_INNER:
+		if (strncmp(reply, "\"auth=", 6))
+			break;
+		val = reply + 2;
+		memcpy(val, "EAP-", 4);
+		break;
+	case TTLS_INNER:
+		if (strncmp(reply, "\"autheap=", 9) == 0) {
+			val = reply + 5;
+			memcpy(val, "EAP-", 4);
+		} else if (strncmp(reply, "\"auth=", 6) == 0)
+			val = reply + 6;
+		break;
+	case FAST_INNER:
+		if (strncmp(reply, "\"auth=", 6))
+			break;
+		if (strcmp(reply + 6, "GTC auth=MSCHAPV2") == 0) {
+			val = "GTC(auth) + MSCHAPv2(prov)";
+			break;
+		}
+		val = reply + 2;
+		memcpy(val, "EAP-", 4);
+		break;
+	case NO_INNER:
+		break;
+	}
+
+	for (i = 0; i < phase2Select->count(); i++) {
+		if (phase2Select->itemText(i).compare(val) == 0) {
+			phase2Select->setCurrentIndex(i);
+			break;
 		}
 	}
 

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.h (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.h Wed Oct  8 21:24:04 2008
@@ -42,6 +42,7 @@
 	virtual void encrChanged(const QString &sel);
 	virtual void writeWepKey(int network_id, QLineEdit *edit, int id);
 	virtual void removeNetwork();
+	virtual void eapChanged(int sel);
 
 protected slots:
 	virtual void languageChange();

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.ui
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.ui?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.ui (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/networkconfig.ui Wed Oct  8 21:24:04 2008
@@ -6,7 +6,7 @@
     <x>0</x>
     <y>0</y>
     <width>410</width>
-    <height>510</height>
+    <height>534</height>
    </rect>
   </property>
   <property name="windowTitle" >
@@ -329,6 +329,20 @@
            </property>
           </widget>
          </item>
+         <item row="1" column="0" >
+          <widget class="QLabel" name="phase2Label" >
+           <property name="text" >
+            <string>Inner auth</string>
+           </property>
+          </widget>
+         </item>
+         <item row="1" column="1" >
+          <widget class="QComboBox" name="phase2Select" >
+           <property name="enabled" >
+            <bool>false</bool>
+           </property>
+          </widget>
+         </item>
         </layout>
        </widget>
       </item>
@@ -368,7 +382,7 @@
   </layout>
  </widget>
  <layoutdefault spacing="6" margin="11" />
- <pixmapfunction>qPixmapFromMimeSource</pixmapfunction>
+ <pixmapfunction></pixmapfunction>
  <tabstops>
   <tabstop>ssidEdit</tabstop>
   <tabstop>authSelect</tabstop>
@@ -388,6 +402,7 @@
   <tabstop>wep3Edit</tabstop>
   <tabstop>idstrEdit</tabstop>
   <tabstop>prioritySpinBox</tabstop>
+  <tabstop>phase2Select</tabstop>
   <tabstop>addButton</tabstop>
   <tabstop>removeButton</tabstop>
   <tabstop>cancelButton</tabstop>

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/scanresults.ui
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/scanresults.ui?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/scanresults.ui (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/scanresults.ui Wed Oct  8 21:24:04 2008
@@ -88,7 +88,7 @@
   </layout>
  </widget>
  <layoutdefault spacing="6" margin="11" />
- <pixmapfunction>qPixmapFromMimeSource</pixmapfunction>
+ <pixmapfunction></pixmapfunction>
  <resources/>
  <connections/>
 </ui>

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/userdatarequest.ui
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/userdatarequest.ui?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/userdatarequest.ui (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/userdatarequest.ui Wed Oct  8 21:24:04 2008
@@ -105,5 +105,5 @@
     </layout>
   </widget>
   <layoutdefault spacing="6" margin="11" />
-  <pixmapfunction>qPixmapFromMimeSource</pixmapfunction>
+  <pixmapfunction></pixmapfunction>
 </ui>

Added: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpa_gui.desktop
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpa_gui.desktop?rev=1266&op=file
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpa_gui.desktop (added)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpa_gui.desktop Wed Oct  8 21:24:04 2008
@@ -1,0 +1,10 @@
+[Desktop Entry]
+Version=1.0
+Name=wpa_gui
+Comment=Graphical user interface for wpa_supplicant
+Exec=wpa_gui
+Icon=wpa_gui
+GenericName=wpa_supplicant user interface
+Terminal=false
+Type=Application
+Categories=Qt;Network;

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpa_gui.pro
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpa_gui.pro?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpa_gui.pro (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpa_gui.pro Wed Oct  8 21:24:04 2008
@@ -36,6 +36,8 @@
 	networkconfig.cpp \
 	../../src/common/wpa_ctrl.c
 
+RESOURCES += icons.qrc
+
 FORMS	= wpagui.ui \
 	eventhistory.ui \
 	scanresults.ui \

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.cpp
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.cpp?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.cpp (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.cpp Wed Oct  8 21:24:04 2008
@@ -37,7 +37,7 @@
 		SLOT(eventHistory()));
 	connect(fileSaveConfigAction, SIGNAL(triggered()), this,
 		SLOT(saveConfig()));
-	connect(fileExitAction, SIGNAL(triggered()), this, SLOT(close()));
+	connect(fileExitAction, SIGNAL(triggered()), qApp, SLOT(quit()));
 	connect(networkAddAction, SIGNAL(triggered()), this,
 		SLOT(addNetwork()));
 	connect(networkEditAction, SIGNAL(triggered()), this,
@@ -79,6 +79,8 @@
 	eh = NULL;
 	scanres = NULL;
 	udr = NULL;
+	tray_icon = NULL;
+	startInTray = false;
 	ctrl_iface = NULL;
 	ctrl_conn = NULL;
 	monitor_conn = NULL;
@@ -87,6 +89,11 @@
 
 	parse_argv();
 
+	if (QSystemTrayIcon::isSystemTrayAvailable())
+		createTrayIcon(startInTray);
+	else
+		show();
+
 	textStatus->setText("connecting to wpa_supplicant");
 	timer = new QTimer(this);
 	connect(timer, SIGNAL(timeout()), SLOT(ping()));
@@ -154,7 +161,7 @@
 {
 	int c;
 	for (;;) {
-		c = getopt(qApp->argc(), qApp->argv(), "i:p:");
+		c = getopt(qApp->argc(), qApp->argv(), "i:p:t");
 		if (c < 0)
 			break;
 		switch (c) {
@@ -165,6 +172,9 @@
 		case 'p':
 			free(ctrl_iface_dir);
 			ctrl_iface_dir = strdup(optarg);
+			break;
+		case 't':
+			startInTray = true;
 			break;
 		}
 	}
@@ -710,6 +720,14 @@
 		processCtrlReq(pos + strlen(WPA_CTRL_REQ));
 	else if (str_match(pos, WPA_EVENT_SCAN_RESULTS) && scanres)
 		scanres->updateResults();
+	else if (str_match(pos, WPA_EVENT_DISCONNECTED))
+		showTrayMessage(QSystemTrayIcon::Information, 3,
+				"Disconnected from network.");
+	else if (str_match(pos, WPA_EVENT_CONNECTED)) {
+		showTrayMessage(QSystemTrayIcon::Information, 3,
+				"Connection to network established.");
+		QTimer::singleShot(5 * 1000, this, SLOT(showTrayStatus()));
+	}
 }
 
 
@@ -1070,6 +1088,141 @@
 }
 
 
+void WpaGui::createTrayIcon(bool trayOnly)
+{
+	QApplication::setQuitOnLastWindowClosed(false);
+
+	tray_icon = new QSystemTrayIcon(this);
+	tray_icon->setToolTip(qAppName() + " - wpa_supplicant user interface");
+	tray_icon->setIcon(QIcon(":/icons/wpa_gui.svg"));
+
+	connect(tray_icon,
+		SIGNAL(activated(QSystemTrayIcon::ActivationReason)),
+		this, SLOT(trayActivated(QSystemTrayIcon::ActivationReason)));
+
+	ackTrayIcon = false;
+
+	tray_menu = new QMenu(this);
+
+	disconnectAction = new QAction("&Disconnect", this);
+	reconnectAction = new QAction("Re&connect", this);
+	connect(disconnectAction, SIGNAL(triggered()), this,
+		SLOT(disconnect()));
+	connect(reconnectAction, SIGNAL(triggered()), this,
+		SLOT(connectB()));
+	tray_menu->addAction(disconnectAction);
+	tray_menu->addAction(reconnectAction);
+	tray_menu->addSeparator();
+
+	eventAction = new QAction("&Event History", this);
+	scanAction = new QAction("Scan &Results", this);
+	statAction = new QAction("S&tatus", this);
+	connect(eventAction, SIGNAL(triggered()), this, SLOT(eventHistory()));
+	connect(scanAction, SIGNAL(triggered()), this, SLOT(scan()));
+	connect(statAction, SIGNAL(triggered()), this, SLOT(showTrayStatus()));
+	tray_menu->addAction(eventAction);
+	tray_menu->addAction(scanAction);
+	tray_menu->addAction(statAction);
+	tray_menu->addSeparator();
+
+	showAction = new QAction("&Show Window", this);
+	hideAction = new QAction("&Hide Window", this);
+	quitAction = new QAction("&Quit", this);
+	connect(showAction, SIGNAL(triggered()), this, SLOT(show()));
+	connect(hideAction, SIGNAL(triggered()), this, SLOT(hide()));
+	connect(quitAction, SIGNAL(triggered()), qApp, SLOT(quit()));
+	tray_menu->addAction(showAction);
+	tray_menu->addAction(hideAction);
+	tray_menu->addSeparator();
+	tray_menu->addAction(quitAction);
+
+	tray_icon->setContextMenu(tray_menu);
+
+	tray_icon->show();
+
+	if (!trayOnly)
+		show();
+}
+
+
+void WpaGui::showTrayMessage(QSystemTrayIcon::MessageIcon type, int sec,
+			     const QString & msg)
+{
+	if (!QSystemTrayIcon::supportsMessages())
+		return;
+
+	if (isVisible() || !tray_icon || !tray_icon->isVisible())
+		return;
+
+	tray_icon->showMessage(qAppName(), msg, type, sec * 1000);
+}
+
+
+void WpaGui::trayActivated(QSystemTrayIcon::ActivationReason how)
+ {
+	switch (how) {
+	/* use close() here instead of hide() and allow the
+	 * custom closeEvent handler take care of children */
+	case QSystemTrayIcon::Trigger:
+		ackTrayIcon = true;
+		if (isVisible())
+			close();
+		else
+			show();
+		break;
+	case QSystemTrayIcon::MiddleClick:
+		showTrayStatus();
+		break;
+	default:
+		break;
+	}
+}
+
+
+void WpaGui::showTrayStatus()
+{
+	char buf[2048];
+	size_t len;
+
+	len = sizeof(buf) - 1;
+	if (ctrlRequest("STATUS", buf, &len) < 0)
+		return;
+	buf[len] = '\0';
+
+	QString msg, status(buf);
+
+	QStringList lines = status.split(QRegExp("\\n"));
+	for (QStringList::Iterator it = lines.begin();
+	     it != lines.end(); it++) {
+		int pos = (*it).indexOf('=') + 1;
+		if (pos < 1)
+			continue;
+
+		if ((*it).startsWith("bssid="))
+			msg.append("BSSID:\t" + (*it).mid(pos) + "\n");
+		else if ((*it).startsWith("ssid="))
+			msg.append("SSID: \t" + (*it).mid(pos) + "\n");
+		else if ((*it).startsWith("pairwise_cipher="))
+			msg.append("PAIR: \t" + (*it).mid(pos) + "\n");
+		else if ((*it).startsWith("group_cipher="))
+			msg.append("GROUP:\t" + (*it).mid(pos) + "\n");
+		else if ((*it).startsWith("key_mgmt="))
+			msg.append("AUTH: \t" + (*it).mid(pos) + "\n");
+		else if ((*it).startsWith("wpa_state="))
+			msg.append("STATE:\t" + (*it).mid(pos) + "\n");
+		else if ((*it).startsWith("ip_address="))
+			msg.append("IP:   \t" + (*it).mid(pos) + "\n");
+		else if ((*it).startsWith("Supplicant PAE state="))
+			msg.append("PAE:  \t" + (*it).mid(pos) + "\n");
+		else if ((*it).startsWith("EAP state="))
+			msg.append("EAP:  \t" + (*it).mid(pos) + "\n");
+	}
+
+	if (!msg.isEmpty())
+		showTrayMessage(QSystemTrayIcon::Information, 10, msg);
+}
+
+
 void WpaGui::closeEvent(QCloseEvent *event)
 {
 	if (eh) {
@@ -1090,5 +1243,21 @@
 		udr = NULL;
 	}
 
+	if (tray_icon && !ackTrayIcon) {
+		/* give user a visual hint that the tray icon exists */
+		if (QSystemTrayIcon::supportsMessages()) {
+			hide();
+			showTrayMessage(QSystemTrayIcon::Information, 3,
+					qAppName() + " will keep running in "
+					"the system tray.");
+		} else {
+			QMessageBox::information(this, qAppName() + " systray",
+						 "The program will keep "
+						 "running in the system "
+						 "tray.");
+		}
+		ackTrayIcon = true;
+	}
+
 	event->accept();
 }

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.h (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.h Wed Oct  8 21:24:04 2008
@@ -15,6 +15,7 @@
 #ifndef WPAGUI_H
 #define WPAGUI_H
 
+#include <QSystemTrayIcon>
 #include <QObject>
 #include "ui_wpagui.h"
 
@@ -67,9 +68,13 @@
 	virtual void updateNetworkDisabledStatus();
 	virtual void enableListedNetwork(bool);
 	virtual void disableListedNetwork(bool);
+	virtual void showTrayMessage(QSystemTrayIcon::MessageIcon type,
+				     int sec, const QString &msg);
+	virtual void showTrayStatus();
 
 protected slots:
 	virtual void languageChange();
+	virtual void trayActivated(QSystemTrayIcon::ActivationReason how);
 	virtual void closeEvent(QCloseEvent *event);
 
 private:
@@ -85,6 +90,19 @@
 	char *ctrl_iface_dir;
 	struct wpa_ctrl *monitor_conn;
 	UserDataRequest *udr;
+	QAction *disconnectAction;
+	QAction *reconnectAction;
+	QAction *eventAction;
+	QAction *scanAction;
+	QAction *statAction;
+	QAction *showAction;
+	QAction *hideAction;
+	QAction *quitAction;
+	QMenu *tray_menu;
+	QSystemTrayIcon *tray_icon;
+	void createTrayIcon(bool);
+	bool ackTrayIcon;
+	bool startInTray;
 
 	int openCtrlConnection(const char *ifname);
 };

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.ui
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.ui?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.ui (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_gui-qt4/wpagui.ui Wed Oct  8 21:24:04 2008
@@ -11,6 +11,10 @@
   </property>
   <property name="windowTitle" >
    <string>wpa_gui</string>
+  </property>
+  <property name="windowIcon" >
+   <iconset resource="icons.qrc" >
+    <normaloff>:/icons/wpa_gui.svg</normaloff>:/icons/wpa_gui.svg</iconset>
   </property>
   <widget class="QWidget" name="widget" >
    <layout class="QGridLayout" >
@@ -406,7 +410,7 @@
   </action>
  </widget>
  <layoutdefault spacing="6" margin="11" />
- <pixmapfunction>qPixmapFromMimeSource</pixmapfunction>
+ <pixmapfunction></pixmapfunction>
  <includes>
   <include location="global" >qtimer.h</include>
   <include location="global" >qsocketnotifier.h</include>
@@ -414,6 +418,8 @@
   <include location="local" >eventhistory.h</include>
   <include location="local" >scanresults.h</include>
  </includes>
- <resources/>
+ <resources>
+  <include location="icons.qrc" />
+ </resources>
  <connections/>
 </ui>

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_priv.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_priv.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_priv.c (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_priv.c Wed Oct  8 21:24:04 2008
@@ -564,6 +564,17 @@
 }
 
 
+static void wpa_priv_cmd_set_mode(struct wpa_priv_interface *iface,
+				  void *buf, size_t len)
+{
+	if (iface->drv_priv == NULL || iface->driver->set_mode == NULL ||
+	    len != sizeof(int))
+		return;
+
+	iface->driver->set_mode(iface->drv_priv, *((int *) buf));
+}
+
+
 static void wpa_priv_receive(int sock, void *eloop_ctx, void *sock_ctx)
 {
 	struct wpa_priv_interface *iface = eloop_ctx;
@@ -634,6 +645,9 @@
 		break;
 	case PRIVSEP_CMD_L2_SEND:
 		wpa_priv_cmd_l2_send(iface, &from, cmd_buf, cmd_len);
+		break;
+	case PRIVSEP_CMD_SET_MODE:
+		wpa_priv_cmd_set_mode(iface, cmd_buf, cmd_len);
 		break;
 	}
 }

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant.c (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant.c Wed Oct  8 21:24:04 2008
@@ -251,8 +251,7 @@
 	struct eapol_config eapol_conf;
 	struct wpa_ssid *ssid = wpa_s->current_ssid;
 
-	if (wpa_s->key_mgmt == WPA_KEY_MGMT_PSK ||
-	    wpa_s->key_mgmt == WPA_KEY_MGMT_FT_PSK) {
+	if (wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt)) {
 		eapol_sm_notify_eap_success(wpa_s->eapol, FALSE);
 		eapol_sm_notify_eap_fail(wpa_s->eapol, FALSE);
 	}
@@ -282,8 +281,8 @@
 	if (wpa_s->conf)
 		eapol_conf.fast_reauth = wpa_s->conf->fast_reauth;
 	eapol_conf.workaround = ssid->eap_workaround;
-	eapol_conf.eap_disabled = wpa_s->key_mgmt != WPA_KEY_MGMT_IEEE8021X &&
-		wpa_s->key_mgmt != WPA_KEY_MGMT_FT_IEEE8021X &&
+	eapol_conf.eap_disabled =
+		!wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt) &&
 		wpa_s->key_mgmt != WPA_KEY_MGMT_IEEE8021X_NO_WPA;
 	eapol_sm_notify_config(wpa_s->eapol, &ssid->eap, &eapol_conf);
 #endif /* IEEE8021X_EAPOL */
@@ -562,8 +561,7 @@
 	 * TODO: should notify EAPOL SM about changes in opensc_engine_path,
 	 * pkcs11_engine_path, pkcs11_module_path.
 	 */
-	if (wpa_s->key_mgmt == WPA_KEY_MGMT_PSK ||
-	    wpa_s->key_mgmt == WPA_KEY_MGMT_FT_PSK) {
+	if (wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt)) {
 		/*
 		 * Clear forced success to clear EAP state for next
 		 * authentication.
@@ -634,6 +632,10 @@
 		return KEY_MGMT_FT_802_1X;
 	case WPA_KEY_MGMT_FT_PSK:
 		return KEY_MGMT_FT_PSK;
+	case WPA_KEY_MGMT_IEEE8021X_SHA256:
+		return KEY_MGMT_802_1X_SHA256;
+	case WPA_KEY_MGMT_PSK_SHA256:
+		return KEY_MGMT_PSK_SHA256;
 	case WPA_KEY_MGMT_PSK:
 	default:
 		return KEY_MGMT_PSK;
@@ -676,7 +678,7 @@
 	}
 
 #ifdef CONFIG_IEEE80211W
-	if (!(ie->capabilities & WPA_CAPABILITY_MGMT_FRAME_PROTECTION) &&
+	if (!(ie->capabilities & WPA_CAPABILITY_MFPC) &&
 	    ssid->ieee80211w == IEEE80211W_REQUIRED) {
 		wpa_msg(wpa_s, MSG_INFO, "WPA: Driver associated with an AP "
 			"that does not support management frame protection - "
@@ -822,6 +824,16 @@
 		wpa_s->key_mgmt = WPA_KEY_MGMT_FT_PSK;
 		wpa_msg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT FT/PSK");
 #endif /* CONFIG_IEEE80211R */
+#ifdef CONFIG_IEEE80211W
+	} else if (sel & WPA_KEY_MGMT_IEEE8021X_SHA256) {
+		wpa_s->key_mgmt = WPA_KEY_MGMT_IEEE8021X_SHA256;
+		wpa_msg(wpa_s, MSG_DEBUG,
+			"WPA: using KEY_MGMT 802.1X with SHA256");
+	} else if (sel & WPA_KEY_MGMT_PSK_SHA256) {
+		wpa_s->key_mgmt = WPA_KEY_MGMT_PSK_SHA256;
+		wpa_msg(wpa_s, MSG_DEBUG,
+			"WPA: using KEY_MGMT PSK with SHA256");
+#endif /* CONFIG_IEEE80211W */
 	} else if (sel & WPA_KEY_MGMT_IEEE8021X) {
 		wpa_s->key_mgmt = WPA_KEY_MGMT_IEEE8021X;
 		wpa_msg(wpa_s, MSG_DEBUG, "WPA: using KEY_MGMT 802.1X");
@@ -845,7 +857,7 @@
 #ifdef CONFIG_IEEE80211W
 	sel = ie.mgmt_group_cipher;
 	if (ssid->ieee80211w == NO_IEEE80211W ||
-	    !(ie.capabilities & WPA_CAPABILITY_MGMT_FRAME_PROTECTION))
+	    !(ie.capabilities & WPA_CAPABILITY_MFPC))
 		sel = 0;
 	if (sel & WPA_CIPHER_AES_128_CMAC) {
 		wpa_s->mgmt_group_cipher = WPA_CIPHER_AES_128_CMAC;
@@ -864,7 +876,8 @@
 		return -1;
 	}
 
-	if (ssid->key_mgmt & (WPA_KEY_MGMT_PSK | WPA_KEY_MGMT_FT_PSK))
+	if (ssid->key_mgmt &
+	    (WPA_KEY_MGMT_PSK | WPA_KEY_MGMT_FT_PSK | WPA_KEY_MGMT_PSK_SHA256))
 		wpa_sm_set_pmk(wpa_s->wpa, ssid->psk, PMK_LEN);
 	else
 		wpa_sm_set_pmk_from_pmksa(wpa_s->wpa);
@@ -910,6 +923,10 @@
 		if (ie && ie[1] >= MOBILITY_DOMAIN_ID_LEN)
 			md = ie + 2;
 		wpa_sm_set_ft_params(wpa_s->wpa, md, NULL, 0, NULL);
+		if (md) {
+			/* Prepare for the next transition */
+			wpa_ft_prepare_auth_request(wpa_s->wpa);
+		}
 #endif /* CONFIG_IEEE80211R */
 	} else {
 		wpa_msg(wpa_s, MSG_INFO, "Trying to associate with SSID '%s'",
@@ -921,6 +938,11 @@
 	/* Starting new association, so clear the possibly used WPA IE from the
 	 * previous association. */
 	wpa_sm_set_assoc_wpa_ie(wpa_s->wpa, NULL, 0);
+
+	if (wpa_drv_set_mode(wpa_s, ssid->mode)) {
+		wpa_printf(MSG_WARNING, "Failed to set operating mode");
+		assoc_failed = 1;
+	}
 
 #ifdef IEEE8021X_EAPOL
 	if (ssid->key_mgmt & WPA_KEY_MGMT_IEEE8021X_NO_WPA) {
@@ -950,7 +972,9 @@
 		    wpa_scan_get_ie(bss, WLAN_EID_RSN)) &&
 	    (ssid->key_mgmt & (WPA_KEY_MGMT_IEEE8021X | WPA_KEY_MGMT_PSK |
 			       WPA_KEY_MGMT_FT_IEEE8021X |
-			       WPA_KEY_MGMT_FT_PSK))) {
+			       WPA_KEY_MGMT_FT_PSK |
+			       WPA_KEY_MGMT_IEEE8021X_SHA256 |
+			       WPA_KEY_MGMT_PSK_SHA256))) {
 		int try_opportunistic;
 		try_opportunistic = ssid->proactive_key_caching &&
 			(ssid->proto & WPA_PROTO_RSN);
@@ -968,7 +992,8 @@
 	} else if (ssid->key_mgmt &
 		   (WPA_KEY_MGMT_PSK | WPA_KEY_MGMT_IEEE8021X |
 		    WPA_KEY_MGMT_WPA_NONE | WPA_KEY_MGMT_FT_PSK |
-		    WPA_KEY_MGMT_FT_IEEE8021X)) {
+		    WPA_KEY_MGMT_FT_IEEE8021X | WPA_KEY_MGMT_PSK_SHA256 |
+		    WPA_KEY_MGMT_IEEE8021X_SHA256)) {
 		wpa_ie_len = sizeof(wpa_ie);
 		if (wpa_supplicant_set_suites(wpa_s, NULL, ssid,
 					      wpa_ie, &wpa_ie_len)) {
@@ -1428,15 +1453,13 @@
 
 	if (wpa_s->eapol_received == 0 &&
 	    (!wpa_s->driver_4way_handshake ||
-	     (wpa_s->key_mgmt != WPA_KEY_MGMT_PSK &&
-	      wpa_s->key_mgmt != WPA_KEY_MGMT_FT_PSK) ||
+	     !wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt) ||
 	     wpa_s->wpa_state != WPA_COMPLETED)) {
 		/* Timeout for completing IEEE 802.1X and WPA authentication */
 		wpa_supplicant_req_auth_timeout(
 			wpa_s,
-			(wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X ||
-			 wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA ||
-			 wpa_s->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X) ?
+			(wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt) ||
+			 wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA) ?
 			70 : 10, 0);
 	}
 	wpa_s->eapol_received++;
@@ -1454,15 +1477,13 @@
 	 * still sent to the current BSSID (if available), though. */
 
 	os_memcpy(wpa_s->last_eapol_src, src_addr, ETH_ALEN);
-	if (wpa_s->key_mgmt != WPA_KEY_MGMT_PSK &&
-	    wpa_s->key_mgmt != WPA_KEY_MGMT_FT_PSK &&
+	if (!wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt) &&
 	    eapol_sm_rx_eapol(wpa_s->eapol, src_addr, buf, len) > 0)
 		return;
 	wpa_drv_poll(wpa_s);
 	if (!wpa_s->driver_4way_handshake)
 		wpa_sm_rx_eapol(wpa_s->wpa, src_addr, buf, len);
-	else if (wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X ||
-		 wpa_s->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X) {
+	else if (wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt)) {
 		/*
 		 * Set portValid = TRUE here since we are going to skip 4-way
 		 * handshake processing which would normally set portValid. We

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant.conf
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant.conf?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant.conf (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant.conf Wed Oct  8 21:24:04 2008
@@ -211,6 +211,8 @@
 # IEEE8021X = IEEE 802.1X using EAP authentication and (optionally) dynamically
 #	generated WEP keys
 # NONE = WPA is not used; plaintext or static WEP could be used
+# WPA-PSK-SHA256 = Like WPA-PSK but using stronger SHA256-based algorithms
+# WPA-EAP-SHA256 = Like WPA-EAP but using stronger SHA256-based algorithms
 # If not set, this defaults to: WPA-PSK WPA-EAP
 #
 # auth_alg: list of allowed IEEE 802.11 authentication algorithms
@@ -434,7 +436,7 @@
 #	fast_max_pac_list_len=<num> option can be used to set the maximum
 #		number of PAC entries to store in a PAC list (default: 10)
 #	fast_pac_format=binary option can be used to select binary format for
-#		storing PAC entires in order to save some space (the default
+#		storing PAC entries in order to save some space (the default
 #		text format uses about 2.5 times the size of minimal binary
 #		format)
 #

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant_i.h
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant_i.h?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant_i.h (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpa_supplicant_i.h Wed Oct  8 21:24:04 2008
@@ -448,6 +448,14 @@
 	return 0;
 }
 
+static inline int wpa_drv_set_mode(struct wpa_supplicant *wpa_s, int mode)
+{
+	if (wpa_s->driver->set_mode) {
+		return wpa_s->driver->set_mode(wpa_s->drv_priv, mode);
+	}
+	return 0;
+}
+
 static inline int wpa_drv_associate(struct wpa_supplicant *wpa_s,
 				    struct wpa_driver_associate_params *params)
 {

Modified: wpasupplicant/branches/upstream/current/wpa_supplicant/wpas_glue.c
URL: http://svn.debian.org/wsvn/wpasupplicant/branches/upstream/current/wpa_supplicant/wpas_glue.c?rev=1266&op=diff
==============================================================================
--- wpasupplicant/branches/upstream/current/wpa_supplicant/wpas_glue.c (original)
+++ wpasupplicant/branches/upstream/current/wpa_supplicant/wpas_glue.c Wed Oct  8 21:24:04 2008
@@ -1,6 +1,6 @@
 /*
  * WPA Supplicant - Glue code to setup EAPOL and RSN modules
- * Copyright (c) 2003-2007, Jouni Malinen <j at w1.fi>
+ * Copyright (c) 2003-2008, Jouni Malinen <j at w1.fi>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -36,6 +36,13 @@
 {
 	struct wpa_supplicant *wpa_s = ctx;
 	wpa_config_set_blob(wpa_s->conf, blob);
+	if (wpa_s->conf->update_config) {
+		int ret = wpa_config_write(wpa_s->confname, wpa_s->conf);
+		if (ret) {
+			wpa_printf(MSG_DEBUG, "Failed to update config after "
+				   "blob set");
+		}
+	}
 }
 
 
@@ -122,8 +129,7 @@
 	/* TODO: could add l2_packet_sendmsg that allows fragments to avoid
 	 * extra copy here */
 
-	if (wpa_s->key_mgmt == WPA_KEY_MGMT_PSK ||
-	    wpa_s->key_mgmt == WPA_KEY_MGMT_FT_PSK ||
+	if (wpa_key_mgmt_wpa_psk(wpa_s->key_mgmt) ||
 	    wpa_s->key_mgmt == WPA_KEY_MGMT_NONE) {
 		/* Current SSID is not using IEEE 802.1X/EAP, so drop possible
 		 * EAPOL frames (mainly, EAPOL-Start) from EAPOL state
@@ -222,11 +228,19 @@
 	wpa_printf(MSG_DEBUG, "EAPOL authentication completed %ssuccessfully",
 		   success ? "" : "un");
 
+	if (!success) {
+		/*
+		 * Make sure we do not get stuck here waiting for long EAPOL
+		 * timeout if the AP does not disconnect in case of
+		 * authentication failure.
+		 */
+		wpa_supplicant_req_auth_timeout(wpa_s, 2, 0);
+	}
+
 	if (!success || !wpa_s->driver_4way_handshake)
 		return;
 
-	if (wpa_s->key_mgmt != WPA_KEY_MGMT_IEEE8021X &&
-	    wpa_s->key_mgmt != WPA_KEY_MGMT_FT_IEEE8021X)
+	if (!wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt))
 		return;
 
 	wpa_printf(MSG_DEBUG, "Configure PMK for driver-based RSN 4-way "
@@ -265,8 +279,7 @@
 {
 	struct wpa_supplicant *wpa_s = ctx;
 	wpa_msg(wpa_s, MSG_DEBUG, "WPA: EAPOL processing complete");
-	if (wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X ||
-	    wpa_s->key_mgmt == WPA_KEY_MGMT_FT_IEEE8021X) {
+	if (wpa_key_mgmt_wpa_ieee8021x(wpa_s->key_mgmt)) {
 		wpa_supplicant_set_state(wpa_s, WPA_4WAY_HANDSHAKE);
 	} else {
 		wpa_supplicant_cancel_auth_timeout(wpa_s);




More information about the Pkg-wpa-devel mailing list