diff options
Diffstat (limited to 'wifi/java/android')
-rw-r--r-- | wifi/java/android/net/wifi/IWifiManager.aidl | 2 | ||||
-rw-r--r-- | wifi/java/android/net/wifi/WifiManager.java | 2 | ||||
-rw-r--r-- | wifi/java/android/net/wifi/WifiMonitor.java | 20 | ||||
-rw-r--r-- | wifi/java/android/net/wifi/WifiNative.java | 13 | ||||
-rw-r--r-- | wifi/java/android/net/wifi/WifiStateTracker.java | 125 |
5 files changed, 113 insertions, 49 deletions
diff --git a/wifi/java/android/net/wifi/IWifiManager.aidl b/wifi/java/android/net/wifi/IWifiManager.aidl index e454cae..f9a0845 100644 --- a/wifi/java/android/net/wifi/IWifiManager.aidl +++ b/wifi/java/android/net/wifi/IWifiManager.aidl @@ -54,7 +54,7 @@ interface IWifiManager boolean setWifiEnabled(boolean enable); - int getWifiState(); + int getWifiEnabledState(); int getNumAllowedChannels(); diff --git a/wifi/java/android/net/wifi/WifiManager.java b/wifi/java/android/net/wifi/WifiManager.java index db989d0..483e0fa 100644 --- a/wifi/java/android/net/wifi/WifiManager.java +++ b/wifi/java/android/net/wifi/WifiManager.java @@ -605,7 +605,7 @@ public class WifiManager { */ public int getWifiState() { try { - return mService.getWifiState(); + return mService.getWifiEnabledState(); } catch (RemoteException e) { return WIFI_STATE_UNKNOWN; } diff --git a/wifi/java/android/net/wifi/WifiMonitor.java b/wifi/java/android/net/wifi/WifiMonitor.java index 8c9e5fa..1799560 100644 --- a/wifi/java/android/net/wifi/WifiMonitor.java +++ b/wifi/java/android/net/wifi/WifiMonitor.java @@ -150,19 +150,17 @@ public class WifiMonitor { String eventStr = WifiNative.waitForEvent(); - if (Config.LOGD) { - // Skip logging the common but mostly uninteresting scan-results event - if (eventStr.indexOf(scanResultsEvent) == -1) { - Log.v(TAG, "Event [" + eventStr +"]"); - } - } if (eventStr == null) { continue; - } else if (!eventStr.startsWith(eventPrefix)) { - if (eventStr.startsWith(wpaEventPrefix)) { - if (0 < eventStr.indexOf(passwordKeyMayBeIncorrectEvent)) { - handlePasswordKeyMayBeIncorrect(); - } + } + + // Skip logging the common but mostly uninteresting scan-results event + if (Config.LOGD && eventStr.indexOf(scanResultsEvent) == -1) { + Log.v(TAG, "Event [" + eventStr + "]"); + } + if (!eventStr.startsWith(eventPrefix)) { + if (eventStr.startsWith(wpaEventPrefix) && 0 < eventStr.indexOf(passwordKeyMayBeIncorrectEvent)) { + handlePasswordKeyMayBeIncorrect(); } continue; } diff --git a/wifi/java/android/net/wifi/WifiNative.java b/wifi/java/android/net/wifi/WifiNative.java index 49021cd..2a47a71 100644 --- a/wifi/java/android/net/wifi/WifiNative.java +++ b/wifi/java/android/net/wifi/WifiNative.java @@ -89,6 +89,19 @@ public class WifiNative { public native static boolean stopDriverCommand(); + /** + * Start filtering out multicast packets, to reduce battery consumption + * that would result from processing them, only to discard them. + * @return {@code true} if the operation succeeded, {@code false} otherwise + */ + public native static boolean startPacketFiltering(); + + /** + * Stop filtering out multicast packets. + * @return {@code true} if the operation succeeded, {@code false} otherwise + */ + public native static boolean stopPacketFiltering(); + public native static boolean setPowerModeCommand(int mode); public native static boolean setNumAllowedChannelsCommand(int numChannels); diff --git a/wifi/java/android/net/wifi/WifiStateTracker.java b/wifi/java/android/net/wifi/WifiStateTracker.java index 9b96da0..0e70f8b 100644 --- a/wifi/java/android/net/wifi/WifiStateTracker.java +++ b/wifi/java/android/net/wifi/WifiStateTracker.java @@ -16,6 +16,7 @@ package android.net.wifi; +import android.app.ActivityManagerNative; import android.net.NetworkInfo; import android.net.NetworkStateTracker; import android.net.DhcpInfo; @@ -159,7 +160,16 @@ public class WifiStateTracker extends NetworkStateTracker { private boolean mHaveIPAddress; private boolean mObtainingIPAddress; private boolean mTornDownByConnMgr; + /** + * A DISCONNECT event has been received, but processing it + * is being deferred. + */ private boolean mDisconnectPending; + /** + * An operation has been performed as a result of which we expect the next event + * will be a DISCONNECT. + */ + private boolean mDisconnectExpected; private DhcpHandler mDhcpTarget; private DhcpInfo mDhcpInfo; private int mLastSignalLevel = -1; @@ -379,8 +389,11 @@ public class WifiStateTracker extends NetworkStateTracker { */ public synchronized boolean isAvailable() { /* - * TODO: Should we also look at scan results to see whether we're - * in range of any access points? + * TODO: Need to also look at scan results to see whether we're + * in range of any access points. If we have scan results that + * are no more than N seconds old, use those, otherwise, initiate + * a scan and wait for the results. This only matters if we + * allow mobile to be the preferred network. */ SupplicantState suppState = mWifiInfo.getSupplicantState(); return suppState != SupplicantState.UNINITIALIZED && @@ -653,14 +666,25 @@ public class WifiStateTracker extends NetworkStateTracker { mLastSsid = mWifiInfo.getSSID(); configureInterface(); } - intent = new Intent(WifiManager.SUPPLICANT_CONNECTION_CHANGE_ACTION); - intent.putExtra(WifiManager.EXTRA_SUPPLICANT_CONNECTED, true); - mContext.sendBroadcast(intent); + if (ActivityManagerNative.isSystemReady()) { + intent = new Intent(WifiManager.SUPPLICANT_CONNECTION_CHANGE_ACTION); + intent.putExtra(WifiManager.EXTRA_SUPPLICANT_CONNECTED, true); + mContext.sendBroadcast(intent); + } if (supplState == SupplicantState.COMPLETED && mHaveIPAddress) { setDetailedState(DetailedState.CONNECTED); } else { setDetailedState(WifiInfo.getDetailedStateOf(supplState)); } + /* + * Filter out multicast packets. This saves battery power, since + * the CPU doesn't have to spend time processing packets that + * are going to end up being thrown away. Obviously, if we + * ever want to support multicast, this will have to change. + */ + synchronized (this) { + WifiNative.startPacketFiltering(); + } break; case EVENT_SUPPLICANT_DISCONNECT: @@ -689,13 +713,18 @@ public class WifiStateTracker extends NetworkStateTracker { mDhcpTarget = null; } mContext.removeStickyBroadcast(new Intent(WifiManager.NETWORK_STATE_CHANGED_ACTION)); - intent = new Intent(WifiManager.SUPPLICANT_CONNECTION_CHANGE_ACTION); - intent.putExtra(WifiManager.EXTRA_SUPPLICANT_CONNECTED, false); - mContext.sendBroadcast(intent); + if (ActivityManagerNative.isSystemReady()) { + intent = new Intent(WifiManager.SUPPLICANT_CONNECTION_CHANGE_ACTION); + intent.putExtra(WifiManager.EXTRA_SUPPLICANT_CONNECTED, false); + mContext.sendBroadcast(intent); + } setDetailedState(DetailedState.DISCONNECTED); setSupplicantState(SupplicantState.UNINITIALIZED); mHaveIPAddress = false; mObtainingIPAddress = false; + if (died) { + mWM.setWifiEnabled(false); + } break; case EVENT_SUPPLICANT_STATE_CHANGED: @@ -749,13 +778,12 @@ public class WifiStateTracker extends NetworkStateTracker { setSupplicantState(newState); if (newState == SupplicantState.DORMANT) { DetailedState newDetailedState; - if (!mIsScanOnly) { - newDetailedState = DetailedState.FAILED; - } else { + if (mIsScanOnly || mRunState == RUN_STATE_STOPPING) { newDetailedState = DetailedState.IDLE; + } else { + newDetailedState = DetailedState.FAILED; } handleDisconnectedState(newDetailedState); - sendNetworkStateChangeBroadcast(); if (mRunState == RUN_STATE_RUNNING && !mIsScanOnly) { sendEmptyMessageDelayed(EVENT_DEFERRED_RECONNECT, RECONNECT_DELAY_MSECS); } else if (mRunState == RUN_STATE_STOPPING) { @@ -768,9 +796,8 @@ public class WifiStateTracker extends NetworkStateTracker { } } } else if (newState == SupplicantState.DISCONNECTED) { - if (isDriverStopped()) { + if (isDriverStopped() || mDisconnectExpected) { handleDisconnectedState(DetailedState.DISCONNECTED); - sendNetworkStateChangeBroadcast(); } else { scheduleDisconnect(); } @@ -788,7 +815,9 @@ public class WifiStateTracker extends NetworkStateTracker { } } + mDisconnectExpected = false; intent = new Intent(WifiManager.SUPPLICANT_STATE_CHANGED_ACTION); + intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT); intent.putExtra(WifiManager.EXTRA_NEW_STATE, (Parcelable)newState); if (failedToAuthenticate) { if (LOCAL_LOGD) Log.d(TAG, "Failed to authenticate, disabling network " + networkId); @@ -872,7 +901,7 @@ public class WifiStateTracker extends NetworkStateTracker { * The connection is fully configured as far as link-level * connectivity is concerned, but we may still need to obtain * an IP address. But do this only if we are connecting to - * a different access point than we were connected to previously. + * a different network than we were connected to previously. */ if (wasDisconnectPending) { DetailedState saveState = getNetworkInfo().getDetailedState(); @@ -890,11 +919,13 @@ public class WifiStateTracker extends NetworkStateTracker { setDetailedState(DetailedState.OBTAINING_IPADDR); } } - sendNetworkStateChangeBroadcast(); + sendNetworkStateChangeBroadcast(mWifiInfo.getBSSID()); break; case EVENT_SCAN_RESULTS_AVAILABLE: - mContext.sendBroadcast(new Intent(WifiManager.SCAN_RESULTS_AVAILABLE_ACTION)); + if (ActivityManagerNative.isSystemReady()) { + mContext.sendBroadcast(new Intent(WifiManager.SCAN_RESULTS_AVAILABLE_ACTION)); + } sendScanResultsAvailable(); /** * On receiving the first scan results after connecting to @@ -956,7 +987,7 @@ public class WifiStateTracker extends NetworkStateTracker { mLastSignalLevel = -1; // force update of signal strength if (mNetworkInfo.getDetailedState() != DetailedState.CONNECTED) { setDetailedState(DetailedState.CONNECTED); - sendNetworkStateChangeBroadcast(); + sendNetworkStateChangeBroadcast(mWifiInfo.getBSSID()); } else { mTarget.sendEmptyMessage(EVENT_CONFIGURATION_CHANGED); } @@ -1083,16 +1114,13 @@ public class WifiStateTracker extends NetworkStateTracker { if (mDisconnectPending) { cancelDisconnect(); } - Intent intent = new Intent(WifiManager.NETWORK_STATE_CHANGED_ACTION); - intent.putExtra(WifiManager.EXTRA_NETWORK_INFO, mNetworkInfo); - if (mLastBssid != null) - intent.putExtra(WifiManager.EXTRA_BSSID, mLastBssid); + mDisconnectExpected = false; + resetInterface(); + setDetailedState(newState); + sendNetworkStateChangeBroadcast(mLastBssid); mWifiInfo.setBSSID(null); mLastBssid = null; mLastSsid = null; - resetInterface(); - mContext.sendStickyBroadcast(intent); - setDetailedState(newState); mDisconnectPending = false; } @@ -1246,16 +1274,19 @@ public class WifiStateTracker extends NetworkStateTracker { } private void sendRssiChangeBroadcast(final int newRssi) { - Intent intent = new Intent(WifiManager.RSSI_CHANGED_ACTION); - intent.putExtra(WifiManager.EXTRA_NEW_RSSI, newRssi); - mContext.sendBroadcast(intent); + if (ActivityManagerNative.isSystemReady()) { + Intent intent = new Intent(WifiManager.RSSI_CHANGED_ACTION); + intent.putExtra(WifiManager.EXTRA_NEW_RSSI, newRssi); + mContext.sendBroadcast(intent); + } } - private void sendNetworkStateChangeBroadcast() { + private void sendNetworkStateChangeBroadcast(String bssid) { Intent intent = new Intent(WifiManager.NETWORK_STATE_CHANGED_ACTION); + intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT); intent.putExtra(WifiManager.EXTRA_NETWORK_INFO, mNetworkInfo); - if (mWifiInfo.getBSSID() != null) - intent.putExtra(WifiManager.EXTRA_BSSID, mWifiInfo.getBSSID()); + if (bssid != null) + intent.putExtra(WifiManager.EXTRA_BSSID, bssid); mContext.sendStickyBroadcast(intent); } @@ -1292,11 +1323,28 @@ public class WifiStateTracker extends NetworkStateTracker { } public synchronized boolean disconnectAndStop() { - // Take down any open network notifications - setNotificationVisible(false, 0, false, 0); + if (mRunState != RUN_STATE_STOPPING && mRunState != RUN_STATE_STOPPED) { + // Take down any open network notifications + setNotificationVisible(false, 0, false, 0); - mRunState = RUN_STATE_STOPPING; - return WifiNative.disconnectCommand(); + mRunState = RUN_STATE_STOPPING; + return WifiNative.disconnectCommand(); + } else { + /* + * The "driver-stop" wake lock normally is released from the + * connectivity manager after the mobile data connection has + * been established, or after a timeout period, if that never + * happens. Because WifiService.updateWifiState() can get called + * multiple times, we can end up acquiring the wake lock and calling + * disconnectAndStop() even when a disconnect or stop operation + * is already in progress. In that case, we want to ignore the + * disconnectAndStop request and release the (ref-counted) wake + * lock, so that eventually, when the mobile data connection is + * established, the ref count will drop to zero. + */ + releaseWakeLock(); + } + return true; } public synchronized boolean restart() { @@ -1309,6 +1357,10 @@ public class WifiStateTracker extends NetworkStateTracker { return true; } + public synchronized boolean removeNetwork(int networkId) { + return mDisconnectExpected = WifiNative.removeNetworkCommand(networkId); + } + public boolean setRadio(boolean turnOn) { return mWM.setWifiEnabled(turnOn); } @@ -1468,8 +1520,9 @@ public class WifiStateTracker extends NetworkStateTracker { @Override public String toString() { StringBuffer sb = new StringBuffer(); + sb.append("interface ").append(mInterfaceName). + append(" runState=").append(mRunState).append(LS); sb.append(mWifiInfo).append(LS); - sb.append("interface ").append(mInterfaceName).append(LS); sb.append(mDhcpInfo).append(LS); sb.append("haveIpAddress=").append(mHaveIPAddress). append(", obtainingIpAddress=").append(mObtainingIPAddress). |