Merge "Handle EAP authentication failure" into honeycomb

This commit is contained in:
Irfan Sheriff
2011-01-19 17:58:19 -08:00
committed by Android (Google) Code Review
3 changed files with 44 additions and 31 deletions

View File

@@ -31,7 +31,7 @@ import android.util.Log;
* Tracks the state changes in supplicant and provides functionality * Tracks the state changes in supplicant and provides functionality
* that is based on these state changes: * that is based on these state changes:
* - detect a failed WPA handshake that loops indefinitely * - detect a failed WPA handshake that loops indefinitely
* - password failure handling * - authentication failure handling
*/ */
class SupplicantStateTracker extends HierarchicalStateMachine { class SupplicantStateTracker extends HierarchicalStateMachine {
@@ -39,14 +39,14 @@ class SupplicantStateTracker extends HierarchicalStateMachine {
private static final boolean DBG = false; private static final boolean DBG = false;
private WifiStateMachine mWifiStateMachine; private WifiStateMachine mWifiStateMachine;
private int mPasswordFailuresCount = 0; private int mAuthenticationFailuresCount = 0;
/* Indicates authentication failure in supplicant broadcast. /* Indicates authentication failure in supplicant broadcast.
* TODO: enhance auth failure reporting to include notification * TODO: enhance auth failure reporting to include notification
* for all type of failures: EAP, WPS & WPA networks */ * for all type of failures: EAP, WPS & WPA networks */
private boolean mAuthFailureInSupplicantBroadcast = false; private boolean mAuthFailureInSupplicantBroadcast = false;
/* Maximum retries on a password failure notification */ /* Maximum retries on a authentication failure notification */
private static final int MAX_RETRIES_ON_PASSWORD_FAILURE = 2; private static final int MAX_RETRIES_ON_AUTHENTICATION_FAILURE = 2;
/* Tracks if networks have been disabled during a connection */ /* Tracks if networks have been disabled during a connection */
private boolean mNetworksDisabledDuringConnect = false; private boolean mNetworksDisabledDuringConnect = false;
@@ -155,8 +155,8 @@ class SupplicantStateTracker extends HierarchicalStateMachine {
public boolean processMessage(Message message) { public boolean processMessage(Message message) {
if (DBG) Log.d(TAG, getName() + message.toString() + "\n"); if (DBG) Log.d(TAG, getName() + message.toString() + "\n");
switch (message.what) { switch (message.what) {
case WifiStateMachine.PASSWORD_MAY_BE_INCORRECT_EVENT: case WifiStateMachine.AUTHENTICATION_FAILURE_EVENT:
mPasswordFailuresCount++; mAuthenticationFailuresCount++;
mAuthFailureInSupplicantBroadcast = true; mAuthFailureInSupplicantBroadcast = true;
break; break;
case WifiStateMachine.SUPPLICANT_STATE_CHANGE_EVENT: case WifiStateMachine.SUPPLICANT_STATE_CHANGE_EVENT:
@@ -206,18 +206,17 @@ class SupplicantStateTracker extends HierarchicalStateMachine {
@Override @Override
public void enter() { public void enter() {
if (DBG) Log.d(TAG, getName() + "\n"); if (DBG) Log.d(TAG, getName() + "\n");
/* If a disconnect event happens after password key failure /* If a disconnect event happens after authentication failure
* exceeds maximum retries, disable the network * exceeds maximum retries, disable the network
*/ */
Message message = getCurrentMessage(); Message message = getCurrentMessage();
StateChangeResult stateChangeResult = (StateChangeResult) message.obj; StateChangeResult stateChangeResult = (StateChangeResult) message.obj;
if (mPasswordFailuresCount >= MAX_RETRIES_ON_PASSWORD_FAILURE) { if (mAuthenticationFailuresCount >= MAX_RETRIES_ON_AUTHENTICATION_FAILURE) {
Log.d(TAG, "Failed to authenticate, disabling network " + Log.d(TAG, "Failed to authenticate, disabling network " +
stateChangeResult.networkId); stateChangeResult.networkId);
handleNetworkConnectionFailure(stateChangeResult.networkId); handleNetworkConnectionFailure(stateChangeResult.networkId);
mPasswordFailuresCount = 0; mAuthenticationFailuresCount = 0;
} }
} }
} }
@@ -282,8 +281,8 @@ class SupplicantStateTracker extends HierarchicalStateMachine {
@Override @Override
public void enter() { public void enter() {
if (DBG) Log.d(TAG, getName() + "\n"); if (DBG) Log.d(TAG, getName() + "\n");
/* Reset password failure count */ /* Reset authentication failure count */
mPasswordFailuresCount = 0; mAuthenticationFailuresCount = 0;
if (mNetworksDisabledDuringConnect) { if (mNetworksDisabledDuringConnect) {
WifiConfigStore.enableAllNetworks(); WifiConfigStore.enableAllNetworks();
mNetworksDisabledDuringConnect = false; mNetworksDisabledDuringConnect = false;

View File

@@ -42,7 +42,8 @@ public class WifiMonitor {
private static final int LINK_SPEED = 5; private static final int LINK_SPEED = 5;
private static final int TERMINATING = 6; private static final int TERMINATING = 6;
private static final int DRIVER_STATE = 7; private static final int DRIVER_STATE = 7;
private static final int UNKNOWN = 8; private static final int EAP_FAILURE = 8;
private static final int UNKNOWN = 9;
/** All events coming from the supplicant start with this prefix */ /** All events coming from the supplicant start with this prefix */
private static final String eventPrefix = "CTRL-EVENT-"; private static final String eventPrefix = "CTRL-EVENT-";
@@ -110,6 +111,17 @@ public class WifiMonitor {
* <code>state</code> is either STARTED or STOPPED * <code>state</code> is either STARTED or STOPPED
*/ */
private static final String driverStateEvent = "DRIVER-STATE"; private static final String driverStateEvent = "DRIVER-STATE";
/**
* <pre>
* CTRL-EVENT-EAP-FAILURE EAP authentication failed
* </pre>
*/
private static final String eapFailureEvent = "EAP-FAILURE";
/**
* This indicates an authentication failure on EAP FAILURE event
*/
private static final String eapAuthFailure = "EAP authentication failed";
/** /**
* Regex pattern for extracting an Ethernet-style MAC address from a string. * Regex pattern for extracting an Ethernet-style MAC address from a string.
@@ -176,7 +188,7 @@ public class WifiMonitor {
if (!eventStr.startsWith(eventPrefix)) { if (!eventStr.startsWith(eventPrefix)) {
if (eventStr.startsWith(wpaEventPrefix) && if (eventStr.startsWith(wpaEventPrefix) &&
0 < eventStr.indexOf(passwordKeyMayBeIncorrectEvent)) { 0 < eventStr.indexOf(passwordKeyMayBeIncorrectEvent)) {
handlePasswordKeyMayBeIncorrect(); mWifiStateMachine.notifyAuthenticationFailure();
} else if (eventStr.startsWith(wpsOverlapEvent)) { } else if (eventStr.startsWith(wpsOverlapEvent)) {
mWifiStateMachine.notifyWpsOverlap(); mWifiStateMachine.notifyWpsOverlap();
} }
@@ -207,16 +219,17 @@ public class WifiMonitor {
event = LINK_SPEED; event = LINK_SPEED;
else if (eventName.equals(terminatingEvent)) else if (eventName.equals(terminatingEvent))
event = TERMINATING; event = TERMINATING;
else if (eventName.equals(driverStateEvent)) { else if (eventName.equals(driverStateEvent))
event = DRIVER_STATE; event = DRIVER_STATE;
} else if (eventName.equals(eapFailureEvent))
event = EAP_FAILURE;
else else
event = UNKNOWN; event = UNKNOWN;
String eventData = eventStr; String eventData = eventStr;
if (event == DRIVER_STATE || event == LINK_SPEED) if (event == DRIVER_STATE || event == LINK_SPEED)
eventData = eventData.split(" ")[1]; eventData = eventData.split(" ")[1];
else if (event == STATE_CHANGE) { else if (event == STATE_CHANGE || event == EAP_FAILURE) {
int ind = eventStr.indexOf(" "); int ind = eventStr.indexOf(" ");
if (ind != -1) { if (ind != -1) {
eventData = eventStr.substring(ind + 1); eventData = eventStr.substring(ind + 1);
@@ -261,6 +274,10 @@ public class WifiMonitor {
// notify and exit // notify and exit
mWifiStateMachine.notifySupplicantLost(); mWifiStateMachine.notifySupplicantLost();
break; break;
} else if (event == EAP_FAILURE) {
if (eventData.startsWith(eapAuthFailure)) {
mWifiStateMachine.notifyAuthenticationFailure();
}
} else { } else {
handleEvent(event, eventData); handleEvent(event, eventData);
} }
@@ -284,10 +301,6 @@ public class WifiMonitor {
return false; return false;
} }
private void handlePasswordKeyMayBeIncorrect() {
mWifiStateMachine.notifyPasswordKeyMayBeIncorrect();
}
private void handleDriverEvent(String state) { private void handleDriverEvent(String state) {
if (state == null) { if (state == null) {
return; return;

View File

@@ -212,8 +212,8 @@ public class WifiStateMachine extends HierarchicalStateMachine {
static final int SCAN_RESULTS_EVENT = 38; static final int SCAN_RESULTS_EVENT = 38;
/* Supplicate state changed */ /* Supplicate state changed */
static final int SUPPLICANT_STATE_CHANGE_EVENT = 39; static final int SUPPLICANT_STATE_CHANGE_EVENT = 39;
/* Password may be incorrect */ /* Password failure and EAP authentication failure */
static final int PASSWORD_MAY_BE_INCORRECT_EVENT = 40; static final int AUTHENTICATION_FAILURE_EVENT = 40;
/* WPS overlap detected */ /* WPS overlap detected */
static final int WPS_OVERLAP_EVENT = 41; static final int WPS_OVERLAP_EVENT = 41;
@@ -1383,11 +1383,12 @@ public class WifiStateMachine extends HierarchicalStateMachine {
} }
/** /**
* Send the tracker a notification that a user-entered password key * Send the tracker a notification that a user provided
* may be incorrect (i.e., caused authentication to fail). * configuration caused authentication failure - this could
* be a password failure or a EAP authentication failure
*/ */
void notifyPasswordKeyMayBeIncorrect() { void notifyAuthenticationFailure() {
sendMessage(PASSWORD_MAY_BE_INCORRECT_EVENT); sendMessage(AUTHENTICATION_FAILURE_EVENT);
} }
/** /**
@@ -1515,7 +1516,7 @@ public class WifiStateMachine extends HierarchicalStateMachine {
case NETWORK_DISCONNECTION_EVENT: case NETWORK_DISCONNECTION_EVENT:
case SCAN_RESULTS_EVENT: case SCAN_RESULTS_EVENT:
case SUPPLICANT_STATE_CHANGE_EVENT: case SUPPLICANT_STATE_CHANGE_EVENT:
case PASSWORD_MAY_BE_INCORRECT_EVENT: case AUTHENTICATION_FAILURE_EVENT:
case WPS_OVERLAP_EVENT: case WPS_OVERLAP_EVENT:
case CMD_BLACKLIST_NETWORK: case CMD_BLACKLIST_NETWORK:
case CMD_CLEAR_BLACKLIST: case CMD_CLEAR_BLACKLIST:
@@ -2067,7 +2068,7 @@ public class WifiStateMachine extends HierarchicalStateMachine {
case SUPPLICANT_STATE_CHANGE_EVENT: case SUPPLICANT_STATE_CHANGE_EVENT:
case NETWORK_CONNECTION_EVENT: case NETWORK_CONNECTION_EVENT:
case NETWORK_DISCONNECTION_EVENT: case NETWORK_DISCONNECTION_EVENT:
case PASSWORD_MAY_BE_INCORRECT_EVENT: case AUTHENTICATION_FAILURE_EVENT:
case WPS_OVERLAP_EVENT: case WPS_OVERLAP_EVENT:
case CMD_SET_SCAN_TYPE: case CMD_SET_SCAN_TYPE:
case CMD_SET_HIGH_PERF_MODE: case CMD_SET_HIGH_PERF_MODE:
@@ -2300,8 +2301,8 @@ public class WifiStateMachine extends HierarchicalStateMachine {
if (DBG) Log.d(TAG, getName() + message.toString() + "\n"); if (DBG) Log.d(TAG, getName() + message.toString() + "\n");
StateChangeResult stateChangeResult; StateChangeResult stateChangeResult;
switch(message.what) { switch(message.what) {
case PASSWORD_MAY_BE_INCORRECT_EVENT: case AUTHENTICATION_FAILURE_EVENT:
mSupplicantStateTracker.sendMessage(PASSWORD_MAY_BE_INCORRECT_EVENT); mSupplicantStateTracker.sendMessage(AUTHENTICATION_FAILURE_EVENT);
break; break;
case WPS_OVERLAP_EVENT: case WPS_OVERLAP_EVENT:
/* We just need to broadcast the error */ /* We just need to broadcast the error */