119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff/* 219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * Copyright (C) 2010 The Android Open Source Project 319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * 419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * Licensed under the Apache License, Version 2.0 (the "License"); 519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * you may not use this file except in compliance with the License. 619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * You may obtain a copy of the License at 719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * 819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * http://www.apache.org/licenses/LICENSE-2.0 919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * 1019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * Unless required by applicable law or agreed to in writing, software 1119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * distributed under the License is distributed on an "AS IS" BASIS, 1219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * See the License for the specific language governing permissions and 1419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * limitations under the License. 1519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff */ 1619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 1719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriffpackage android.net.wifi; 1819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 1964c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Savilleimport com.android.internal.util.State; 2064c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Savilleimport com.android.internal.util.StateMachine; 2119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 2255bc5f3e0408bcb5a39a6732de0b2d1aa99a55berepo syncimport android.net.wifi.StateChangeResult; 2319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriffimport android.content.Context; 2419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriffimport android.content.Intent; 2519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriffimport android.os.Handler; 2619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriffimport android.os.Message; 2719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriffimport android.os.Parcelable; 285ac72a29593ab9a20337a2225df52bdf4754be02Dianne Hackbornimport android.os.UserHandle; 2919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriffimport android.util.Log; 3019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 3119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff/** 3219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * Tracks the state changes in supplicant and provides functionality 3319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * that is based on these state changes: 3419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * - detect a failed WPA handshake that loops indefinitely 35b98d878f43748a64c68ffe05ce64c5b7c72fe922Irfan Sheriff * - authentication failure handling 3619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff */ 3764c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Savilleclass SupplicantStateTracker extends StateMachine { 3819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 3919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff private static final String TAG = "SupplicantStateTracker"; 4019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff private static final boolean DBG = false; 4119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 4219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff private WifiStateMachine mWifiStateMachine; 43fc7f95abcda6fa35c175f9225358ea75c22952abIrfan Sheriff private WifiConfigStore mWifiConfigStore; 44b98d878f43748a64c68ffe05ce64c5b7c72fe922Irfan Sheriff private int mAuthenticationFailuresCount = 0; 4519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff /* Indicates authentication failure in supplicant broadcast. 4619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * TODO: enhance auth failure reporting to include notification 4719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * for all type of failures: EAP, WPS & WPA networks */ 4819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff private boolean mAuthFailureInSupplicantBroadcast = false; 4919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 50b98d878f43748a64c68ffe05ce64c5b7c72fe922Irfan Sheriff /* Maximum retries on a authentication failure notification */ 51b98d878f43748a64c68ffe05ce64c5b7c72fe922Irfan Sheriff private static final int MAX_RETRIES_ON_AUTHENTICATION_FAILURE = 2; 5219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 538e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff /* Tracks if networks have been disabled during a connection */ 548e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff private boolean mNetworksDisabledDuringConnect = false; 558e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff 5619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff private Context mContext; 5719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 5864c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville private State mUninitializedState = new UninitializedState(); 5964c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville private State mDefaultState = new DefaultState(); 6064c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville private State mInactiveState = new InactiveState(); 6164c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville private State mDisconnectState = new DisconnectedState(); 6264c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville private State mScanState = new ScanState(); 6364c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville private State mHandshakeState = new HandshakeState(); 6464c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville private State mCompletedState = new CompletedState(); 6564c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville private State mDormantState = new DormantState(); 6619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 67fc7f95abcda6fa35c175f9225358ea75c22952abIrfan Sheriff public SupplicantStateTracker(Context c, WifiStateMachine wsm, WifiConfigStore wcs, Handler t) { 68fc7f95abcda6fa35c175f9225358ea75c22952abIrfan Sheriff super(TAG, t.getLooper()); 6919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 70fc7f95abcda6fa35c175f9225358ea75c22952abIrfan Sheriff mContext = c; 7119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff mWifiStateMachine = wsm; 72fc7f95abcda6fa35c175f9225358ea75c22952abIrfan Sheriff mWifiConfigStore = wcs; 7319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff addState(mDefaultState); 7419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff addState(mUninitializedState, mDefaultState); 7519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff addState(mInactiveState, mDefaultState); 7619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff addState(mDisconnectState, mDefaultState); 7719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff addState(mScanState, mDefaultState); 7819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff addState(mHandshakeState, mDefaultState); 7919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff addState(mCompletedState, mDefaultState); 8019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff addState(mDormantState, mDefaultState); 8119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 8219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff setInitialState(mUninitializedState); 8319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 8419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff //start the state machine 8519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff start(); 8619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 8719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 888e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff private void handleNetworkConnectionFailure(int netId) { 898e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff /* If other networks disabled during connection, enable them */ 908e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff if (mNetworksDisabledDuringConnect) { 91fc7f95abcda6fa35c175f9225358ea75c22952abIrfan Sheriff mWifiConfigStore.enableAllNetworks(); 928e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff mNetworksDisabledDuringConnect = false; 938e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff } 948e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff /* Disable failed network */ 95fc7f95abcda6fa35c175f9225358ea75c22952abIrfan Sheriff mWifiConfigStore.disableNetwork(netId, WifiConfiguration.DISABLED_AUTH_FAILURE); 968e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff } 978e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff 9819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff private void transitionOnSupplicantStateChange(StateChangeResult stateChangeResult) { 9919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff SupplicantState supState = (SupplicantState) stateChangeResult.state; 10019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 10119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, "Supplicant state: " + supState.toString() + "\n"); 10219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 10319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff switch (supState) { 104319da8c4c59be36fe2e221a0aba230ef6b77a14fIrfan Sheriff case DISCONNECTED: 10519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff transitionTo(mDisconnectState); 10619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 107319da8c4c59be36fe2e221a0aba230ef6b77a14fIrfan Sheriff case INTERFACE_DISABLED: 108319da8c4c59be36fe2e221a0aba230ef6b77a14fIrfan Sheriff //we should have received a disconnection already, do nothing 109319da8c4c59be36fe2e221a0aba230ef6b77a14fIrfan Sheriff break; 11019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff case SCANNING: 11119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff transitionTo(mScanState); 11219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 113319da8c4c59be36fe2e221a0aba230ef6b77a14fIrfan Sheriff case AUTHENTICATING: 11419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff case ASSOCIATING: 11519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff case ASSOCIATED: 11619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff case FOUR_WAY_HANDSHAKE: 11719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff case GROUP_HANDSHAKE: 11819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff transitionTo(mHandshakeState); 11919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 12019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff case COMPLETED: 12119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff transitionTo(mCompletedState); 12219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 12319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff case DORMANT: 12419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff transitionTo(mDormantState); 12519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 12619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff case INACTIVE: 12719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff transitionTo(mInactiveState); 12819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 12919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff case UNINITIALIZED: 13019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff case INVALID: 13119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff transitionTo(mUninitializedState); 13219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 13319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff default: 13419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff Log.e(TAG, "Unknown supplicant state " + supState); 13519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 13619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 13719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 13819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 139b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff private void sendSupplicantStateChangedBroadcast(SupplicantState state, boolean failedAuth) { 14019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff Intent intent = new Intent(WifiManager.SUPPLICANT_STATE_CHANGED_ACTION); 14119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT 14219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff | Intent.FLAG_RECEIVER_REPLACE_PENDING); 143b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff intent.putExtra(WifiManager.EXTRA_NEW_STATE, (Parcelable) state); 14419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (failedAuth) { 14519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff intent.putExtra( 14619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff WifiManager.EXTRA_SUPPLICANT_ERROR, 14719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff WifiManager.ERROR_AUTHENTICATING); 14819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 1495ac72a29593ab9a20337a2225df52bdf4754be02Dianne Hackborn mContext.sendStickyBroadcastAsUser(intent, UserHandle.ALL); 15019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 15119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 15219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff /******************************************************** 15319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * HSM states 15419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff *******************************************************/ 15519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 15664c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville class DefaultState extends State { 15719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff @Override 15819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff public void enter() { 15919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, getName() + "\n"); 16019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 16119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff @Override 16219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff public boolean processMessage(Message message) { 16319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, getName() + message.toString() + "\n"); 16419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff switch (message.what) { 16555bc5f3e0408bcb5a39a6732de0b2d1aa99a55berepo sync case WifiMonitor.AUTHENTICATION_FAILURE_EVENT: 166b98d878f43748a64c68ffe05ce64c5b7c72fe922Irfan Sheriff mAuthenticationFailuresCount++; 16719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff mAuthFailureInSupplicantBroadcast = true; 16819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 16955bc5f3e0408bcb5a39a6732de0b2d1aa99a55berepo sync case WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT: 17019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff StateChangeResult stateChangeResult = (StateChangeResult) message.obj; 171b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff SupplicantState state = stateChangeResult.state; 172b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff sendSupplicantStateChangedBroadcast(state, mAuthFailureInSupplicantBroadcast); 17319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff mAuthFailureInSupplicantBroadcast = false; 17419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff transitionOnSupplicantStateChange(stateChangeResult); 17519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 176b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff case WifiStateMachine.CMD_RESET_SUPPLICANT_STATE: 177b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff transitionTo(mUninitializedState); 178b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff break; 179d3975a917799b85cacaf382b65c5832813066b51Irfan Sheriff case WifiManager.CONNECT_NETWORK: 1808e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff mNetworksDisabledDuringConnect = true; 1818e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff break; 18219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff default: 18319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff Log.e(TAG, "Ignoring " + message); 18419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 18519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 18619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff return HANDLED; 18719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 18819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 18919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 190b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff /* 191b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff * This indicates that the supplicant state as seen 192b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff * by the framework is not initialized yet. We are 193b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff * in this state right after establishing a control 194b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff * channel connection before any supplicant events 195b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff * or after we have lost the control channel 196b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff * connection to the supplicant 197b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff */ 19864c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville class UninitializedState extends State { 19919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff @Override 20019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff public void enter() { 20119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, getName() + "\n"); 20219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 20319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 20419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 20564c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville class InactiveState extends State { 20619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff @Override 20719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff public void enter() { 20819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, getName() + "\n"); 20919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 21019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 21119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 21264c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville class DisconnectedState extends State { 21319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff @Override 21419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff public void enter() { 21519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, getName() + "\n"); 216b98d878f43748a64c68ffe05ce64c5b7c72fe922Irfan Sheriff /* If a disconnect event happens after authentication failure 21719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * exceeds maximum retries, disable the network 21819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff */ 21919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff Message message = getCurrentMessage(); 22019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff StateChangeResult stateChangeResult = (StateChangeResult) message.obj; 22119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 222b98d878f43748a64c68ffe05ce64c5b7c72fe922Irfan Sheriff if (mAuthenticationFailuresCount >= MAX_RETRIES_ON_AUTHENTICATION_FAILURE) { 22319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff Log.d(TAG, "Failed to authenticate, disabling network " + 22419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff stateChangeResult.networkId); 2258e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff handleNetworkConnectionFailure(stateChangeResult.networkId); 226b98d878f43748a64c68ffe05ce64c5b7c72fe922Irfan Sheriff mAuthenticationFailuresCount = 0; 22719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 22819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 22919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 23019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 23164c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville class ScanState extends State { 23219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff @Override 23319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff public void enter() { 23419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, getName() + "\n"); 23519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 23619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 23719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 23864c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville class HandshakeState extends State { 23919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff /** 24019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * The max number of the WPA supplicant loop iterations before we 24119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff * decide that the loop should be terminated: 24219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff */ 24319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff private static final int MAX_SUPPLICANT_LOOP_ITERATIONS = 4; 24419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff private int mLoopDetectIndex; 24519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff private int mLoopDetectCount; 24619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 24719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff @Override 24819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff public void enter() { 24919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, getName() + "\n"); 25019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff mLoopDetectIndex = 0; 25119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff mLoopDetectCount = 0; 25219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 25319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff @Override 25419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff public boolean processMessage(Message message) { 25519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, getName() + message.toString() + "\n"); 25619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff switch (message.what) { 25755bc5f3e0408bcb5a39a6732de0b2d1aa99a55berepo sync case WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT: 25819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff StateChangeResult stateChangeResult = (StateChangeResult) message.obj; 259b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff SupplicantState state = stateChangeResult.state; 260319da8c4c59be36fe2e221a0aba230ef6b77a14fIrfan Sheriff if (SupplicantState.isHandshakeState(state)) { 26119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (mLoopDetectIndex > state.ordinal()) { 26219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff mLoopDetectCount++; 26319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 26419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (mLoopDetectCount > MAX_SUPPLICANT_LOOP_ITERATIONS) { 26519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff Log.d(TAG, "Supplicant loop detected, disabling network " + 26619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff stateChangeResult.networkId); 2678e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff handleNetworkConnectionFailure(stateChangeResult.networkId); 26819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 26919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff mLoopDetectIndex = state.ordinal(); 270b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff sendSupplicantStateChangedBroadcast(state, 27119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff mAuthFailureInSupplicantBroadcast); 27219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } else { 27319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff //Have the DefaultState handle the transition 27419d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff return NOT_HANDLED; 27519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 27619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 27719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff default: 27819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff return NOT_HANDLED; 27919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 28019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff return HANDLED; 28119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 28219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 28319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 28464c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville class CompletedState extends State { 28519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff @Override 28619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff public void enter() { 28719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, getName() + "\n"); 288b98d878f43748a64c68ffe05ce64c5b7c72fe922Irfan Sheriff /* Reset authentication failure count */ 289b98d878f43748a64c68ffe05ce64c5b7c72fe922Irfan Sheriff mAuthenticationFailuresCount = 0; 2908e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff if (mNetworksDisabledDuringConnect) { 291fc7f95abcda6fa35c175f9225358ea75c22952abIrfan Sheriff mWifiConfigStore.enableAllNetworks(); 2928e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff mNetworksDisabledDuringConnect = false; 2938e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff } 2948e86b89860114386e6c43f55fc034a26798b73e2Irfan Sheriff } 29519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff @Override 29619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff public boolean processMessage(Message message) { 29719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, getName() + message.toString() + "\n"); 29819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff switch(message.what) { 29955bc5f3e0408bcb5a39a6732de0b2d1aa99a55berepo sync case WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT: 30019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff StateChangeResult stateChangeResult = (StateChangeResult) message.obj; 301b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff SupplicantState state = stateChangeResult.state; 302b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff sendSupplicantStateChangedBroadcast(state, mAuthFailureInSupplicantBroadcast); 303319da8c4c59be36fe2e221a0aba230ef6b77a14fIrfan Sheriff /* Ignore any connecting state in completed state. Group re-keying 304319da8c4c59be36fe2e221a0aba230ef6b77a14fIrfan Sheriff * events and other auth events that do not affect connectivity are 305319da8c4c59be36fe2e221a0aba230ef6b77a14fIrfan Sheriff * ignored 306319da8c4c59be36fe2e221a0aba230ef6b77a14fIrfan Sheriff */ 307319da8c4c59be36fe2e221a0aba230ef6b77a14fIrfan Sheriff if (SupplicantState.isConnecting(state)) { 30819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 30919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 31019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff transitionOnSupplicantStateChange(stateChangeResult); 31119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff break; 312b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff case WifiStateMachine.CMD_RESET_SUPPLICANT_STATE: 313b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff sendSupplicantStateChangedBroadcast(SupplicantState.DISCONNECTED, false); 314b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff transitionTo(mUninitializedState); 315b45e726bf5df9650e8a67a7c05bf2f41f414c07dIrfan Sheriff break; 31619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff default: 31719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff return NOT_HANDLED; 31819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 31919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff return HANDLED; 32019d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 32119d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 32219d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff 32319d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff //TODO: remove after getting rid of the state in supplicant 32464c42cae4482fe0157e977b8ddd0f2c2436b3f31Wink Saville class DormantState extends State { 32519d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff @Override 32619d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff public void enter() { 32719d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff if (DBG) Log.d(TAG, getName() + "\n"); 32819d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 32919d245b792e1d941fbba9b04ae20ce9d6e6e18f8Irfan Sheriff } 3306bb7652b47b7c3068fa5e20a20263e651180c856Irfan Sheriff} 331