Loading core/java/android/server/BluetoothAdapterStateMachine.java +75 −3 Original line number Diff line number Diff line Loading @@ -109,6 +109,8 @@ final class BluetoothAdapterStateMachine extends StateMachine { private static final int DEVICES_DISCONNECT_TIMEOUT = 104; // Prepare Bluetooth timeout happens private static final int PREPARE_BLUETOOTH_TIMEOUT = 105; // Bluetooth Powerdown timeout happens private static final int POWER_DOWN_TIMEOUT = 106; private Context mContext; private BluetoothService mBluetoothService; Loading @@ -129,6 +131,8 @@ final class BluetoothAdapterStateMachine extends StateMachine { private static final int PREPARE_BLUETOOTH_TIMEOUT_TIME = 10000; private static final int POWER_DOWN_TIMEOUT_TIME = 5000; BluetoothAdapterStateMachine(Context context, BluetoothService bluetoothService, BluetoothAdapter bluetoothAdapter) { super(TAG); Loading Loading @@ -386,6 +390,11 @@ final class BluetoothAdapterStateMachine extends StateMachine { break; case USER_TURN_OFF: // ignore break; case POWER_STATE_CHANGED: if ((Boolean) message.obj) { recoverStateMachine(TURN_HOT, null); } break; default: return NOT_HANDLED; } Loading Loading @@ -420,14 +429,27 @@ final class BluetoothAdapterStateMachine extends StateMachine { } break; case POWER_STATE_CHANGED: removeMessages(POWER_DOWN_TIMEOUT); if (!((Boolean) message.obj)) { if (mPublicState == BluetoothAdapter.STATE_TURNING_OFF) { transitionTo(mHotOff); finishSwitchingOff(); } } else { if (mPublicState != BluetoothAdapter.STATE_TURNING_ON) { if (mContext.getResources().getBoolean (com.android.internal.R.bool.config_bluetooth_adapter_quick_switch)) { recoverStateMachine(TURN_HOT, null); } else { recoverStateMachine(TURN_COLD, null); } } } break; case ALL_DEVICES_DISCONNECTED: removeMessages(DEVICES_DISCONNECT_TIMEOUT); mBluetoothService.switchConnectable(false); sendMessageDelayed(POWER_DOWN_TIMEOUT, POWER_DOWN_TIMEOUT_TIME); break; case DEVICES_DISCONNECT_TIMEOUT: sendMessage(ALL_DEVICES_DISCONNECTED); Loading @@ -439,6 +461,17 @@ final class BluetoothAdapterStateMachine extends StateMachine { deferMessage(obtainMessage(TURN_HOT)); } break; case POWER_DOWN_TIMEOUT: transitionTo(mHotOff); finishSwitchingOff(); // reset the hardware for error recovery Log.e(TAG, "Devices failed to power down, reseting..."); deferMessage(obtainMessage(TURN_COLD)); if (mContext.getResources().getBoolean (com.android.internal.R.bool.config_bluetooth_adapter_quick_switch)) { deferMessage(obtainMessage(TURN_HOT)); } break; case USER_TURN_ON: case AIRPLANE_MODE_OFF: case AIRPLANE_MODE_ON: Loading Loading @@ -501,6 +534,7 @@ final class BluetoothAdapterStateMachine extends StateMachine { DEVICES_DISCONNECT_TIMEOUT_TIME); } else { mBluetoothService.switchConnectable(false); sendMessageDelayed(POWER_DOWN_TIMEOUT, POWER_DOWN_TIMEOUT_TIME); } // we turn all the way to PowerOff with AIRPLANE_MODE_ON Loading @@ -520,6 +554,12 @@ final class BluetoothAdapterStateMachine extends StateMachine { case PER_PROCESS_TURN_OFF: perProcessCallback(false, (IBluetoothStateChangeCallback)message.obj); break; case POWER_STATE_CHANGED: if ((Boolean) message.obj) { // reset the state machine and send it TURN_ON_CONTINUE message recoverStateMachine(USER_TURN_ON, false); } break; default: return NOT_HANDLED; } Loading @@ -540,7 +580,7 @@ final class BluetoothAdapterStateMachine extends StateMachine { if (what == PER_PROCESS_TURN_ON) { isTurningOn = true; } else if (what == PER_PROCESS_TURN_OFF) { } else if (what == USER_TURN_OFF) { isTurningOn = false; } else { Log.e(TAG, "enter PerProcessState: wrong msg: " + what); Loading Loading @@ -568,12 +608,31 @@ final class BluetoothAdapterStateMachine extends StateMachine { } break; case POWER_STATE_CHANGED: removeMessages(POWER_DOWN_TIMEOUT); if (!((Boolean) message.obj)) { transitionTo(mHotOff); if (!mContext.getResources().getBoolean (com.android.internal.R.bool.config_bluetooth_adapter_quick_switch)) { deferMessage(obtainMessage(TURN_COLD)); } } else { if (!isTurningOn) { recoverStateMachine(TURN_COLD, null); for (IBluetoothStateChangeCallback c: mBluetoothService.getApplicationStateChangeCallbacks()) { perProcessCallback(false, c); deferMessage(obtainMessage(PER_PROCESS_TURN_ON, c)); } } } break; case POWER_DOWN_TIMEOUT: transitionTo(mHotOff); Log.e(TAG, "Power-down timed out, resetting..."); deferMessage(obtainMessage(TURN_COLD)); if (mContext.getResources().getBoolean (com.android.internal.R.bool.config_bluetooth_adapter_quick_switch)) { deferMessage(obtainMessage(TURN_HOT)); } break; case USER_TURN_ON: Loading Loading @@ -616,10 +675,12 @@ final class BluetoothAdapterStateMachine extends StateMachine { perProcessCallback(false, (IBluetoothStateChangeCallback)message.obj); if (mBluetoothService.isApplicationStateChangeTrackerEmpty()) { mBluetoothService.switchConnectable(false); sendMessageDelayed(POWER_DOWN_TIMEOUT, POWER_DOWN_TIMEOUT_TIME); } break; case AIRPLANE_MODE_ON: mBluetoothService.switchConnectable(false); sendMessageDelayed(POWER_DOWN_TIMEOUT, POWER_DOWN_TIMEOUT_TIME); allProcessesCallback(false); // we turn all the way to PowerOff with AIRPLANE_MODE_ON deferMessage(obtainMessage(AIRPLANE_MODE_ON)); Loading Loading @@ -699,6 +760,17 @@ final class BluetoothAdapterStateMachine extends StateMachine { mContext.sendBroadcast(intent, BluetoothService.BLUETOOTH_PERM); } /** * bluetoothd has crashed and recovered, the adapter state machine has to * reset itself and try to return to previous state */ private void recoverStateMachine(int what, Object obj) { Log.e(TAG, "Get unexpected power on event, reset with: " + what); transitionTo(mHotOff); deferMessage(obtainMessage(TURN_COLD)); deferMessage(obtainMessage(what, obj)); } private void dump(PrintWriter pw) { IState currentState = getCurrentState(); if (currentState == mPowerOff) { Loading core/java/android/server/BluetoothEventLoop.java +2 −17 Original line number Diff line number Diff line Loading @@ -59,9 +59,8 @@ class BluetoothEventLoop { // from remote device when Android is in Suspend state. private PowerManager.WakeLock mWakeLock; private static final int EVENT_RESTART_BLUETOOTH = 1; private static final int EVENT_PAIRING_CONSENT_DELAYED_ACCEPT = 2; private static final int EVENT_AGENT_CANCEL = 3; private static final int EVENT_PAIRING_CONSENT_DELAYED_ACCEPT = 1; private static final int EVENT_AGENT_CANCEL = 2; private static final int CREATE_DEVICE_ALREADY_EXISTS = 1; private static final int CREATE_DEVICE_SUCCESS = 0; Loading @@ -75,9 +74,6 @@ class BluetoothEventLoop { public void handleMessage(Message msg) { String address = null; switch (msg.what) { case EVENT_RESTART_BLUETOOTH: mBluetoothService.restart(); break; case EVENT_PAIRING_CONSENT_DELAYED_ACCEPT: address = (String)msg.obj; if (address != null) { Loading Loading @@ -375,9 +371,6 @@ class BluetoothEventLoop { } else if (name.equals("Powered")) { mBluetoothState.sendMessage(BluetoothAdapterStateMachine.POWER_STATE_CHANGED, propValues[1].equals("true") ? new Boolean(true) : new Boolean(false)); // bluetoothd has restarted, re-read all our properties. // Note: bluez only sends this property change when it restarts. onRestartRequired(); } else if (name.equals("DiscoverableTimeout")) { adapterProperties.setProperty(name, propValues[1]); } Loading Loading @@ -1033,14 +1026,6 @@ class BluetoothEventLoop { mBluetoothService.onHealthDeviceChannelChanged(devicePath, channelPath, exists); } private void onRestartRequired() { if (mBluetoothService.isEnabled()) { Log.e(TAG, "*** A serious error occurred (did bluetoothd crash?) - " + "restarting Bluetooth ***"); mHandler.sendEmptyMessage(EVENT_RESTART_BLUETOOTH); } } private static void log(String msg) { Log.d(TAG, msg); } Loading core/java/android/server/BluetoothService.java +0 −21 Original line number Diff line number Diff line Loading @@ -95,7 +95,6 @@ public class BluetoothService extends IBluetooth.Stub { private boolean mIsAirplaneSensitive; private boolean mIsAirplaneToggleable; private BluetoothAdapterStateMachine mBluetoothState; private boolean mRestart = false; // need to call enable() after disable() private int[] mAdapterSdpHandles; private ParcelUuid[] mAdapterUuids; Loading Loading @@ -429,11 +428,6 @@ public class BluetoothService extends IBluetooth.Stub { } finally { Binder.restoreCallingIdentity(ident); } if (mRestart) { mRestart = false; enable(); } } /** Loading @@ -456,10 +450,6 @@ public class BluetoothService extends IBluetooth.Stub { // the adapter property could be changed before event loop is stoped, clear it again mAdapterProperties.clear(); disableNative(); if (mRestart) { mRestart = false; enable(); } } /** Bring up BT and persist BT on in settings */ Loading Loading @@ -500,17 +490,6 @@ public class BluetoothService extends IBluetooth.Stub { return true; } /** Forcibly restart Bluetooth if it is on */ /* package */ synchronized void restart() { if (getBluetoothStateInternal() != BluetoothAdapter.STATE_ON) { return; } mRestart = true; if (!disable(false)) { mRestart = false; } } private final Handler mHandler = new Handler() { @Override public void handleMessage(Message msg) { Loading Loading
core/java/android/server/BluetoothAdapterStateMachine.java +75 −3 Original line number Diff line number Diff line Loading @@ -109,6 +109,8 @@ final class BluetoothAdapterStateMachine extends StateMachine { private static final int DEVICES_DISCONNECT_TIMEOUT = 104; // Prepare Bluetooth timeout happens private static final int PREPARE_BLUETOOTH_TIMEOUT = 105; // Bluetooth Powerdown timeout happens private static final int POWER_DOWN_TIMEOUT = 106; private Context mContext; private BluetoothService mBluetoothService; Loading @@ -129,6 +131,8 @@ final class BluetoothAdapterStateMachine extends StateMachine { private static final int PREPARE_BLUETOOTH_TIMEOUT_TIME = 10000; private static final int POWER_DOWN_TIMEOUT_TIME = 5000; BluetoothAdapterStateMachine(Context context, BluetoothService bluetoothService, BluetoothAdapter bluetoothAdapter) { super(TAG); Loading Loading @@ -386,6 +390,11 @@ final class BluetoothAdapterStateMachine extends StateMachine { break; case USER_TURN_OFF: // ignore break; case POWER_STATE_CHANGED: if ((Boolean) message.obj) { recoverStateMachine(TURN_HOT, null); } break; default: return NOT_HANDLED; } Loading Loading @@ -420,14 +429,27 @@ final class BluetoothAdapterStateMachine extends StateMachine { } break; case POWER_STATE_CHANGED: removeMessages(POWER_DOWN_TIMEOUT); if (!((Boolean) message.obj)) { if (mPublicState == BluetoothAdapter.STATE_TURNING_OFF) { transitionTo(mHotOff); finishSwitchingOff(); } } else { if (mPublicState != BluetoothAdapter.STATE_TURNING_ON) { if (mContext.getResources().getBoolean (com.android.internal.R.bool.config_bluetooth_adapter_quick_switch)) { recoverStateMachine(TURN_HOT, null); } else { recoverStateMachine(TURN_COLD, null); } } } break; case ALL_DEVICES_DISCONNECTED: removeMessages(DEVICES_DISCONNECT_TIMEOUT); mBluetoothService.switchConnectable(false); sendMessageDelayed(POWER_DOWN_TIMEOUT, POWER_DOWN_TIMEOUT_TIME); break; case DEVICES_DISCONNECT_TIMEOUT: sendMessage(ALL_DEVICES_DISCONNECTED); Loading @@ -439,6 +461,17 @@ final class BluetoothAdapterStateMachine extends StateMachine { deferMessage(obtainMessage(TURN_HOT)); } break; case POWER_DOWN_TIMEOUT: transitionTo(mHotOff); finishSwitchingOff(); // reset the hardware for error recovery Log.e(TAG, "Devices failed to power down, reseting..."); deferMessage(obtainMessage(TURN_COLD)); if (mContext.getResources().getBoolean (com.android.internal.R.bool.config_bluetooth_adapter_quick_switch)) { deferMessage(obtainMessage(TURN_HOT)); } break; case USER_TURN_ON: case AIRPLANE_MODE_OFF: case AIRPLANE_MODE_ON: Loading Loading @@ -501,6 +534,7 @@ final class BluetoothAdapterStateMachine extends StateMachine { DEVICES_DISCONNECT_TIMEOUT_TIME); } else { mBluetoothService.switchConnectable(false); sendMessageDelayed(POWER_DOWN_TIMEOUT, POWER_DOWN_TIMEOUT_TIME); } // we turn all the way to PowerOff with AIRPLANE_MODE_ON Loading @@ -520,6 +554,12 @@ final class BluetoothAdapterStateMachine extends StateMachine { case PER_PROCESS_TURN_OFF: perProcessCallback(false, (IBluetoothStateChangeCallback)message.obj); break; case POWER_STATE_CHANGED: if ((Boolean) message.obj) { // reset the state machine and send it TURN_ON_CONTINUE message recoverStateMachine(USER_TURN_ON, false); } break; default: return NOT_HANDLED; } Loading @@ -540,7 +580,7 @@ final class BluetoothAdapterStateMachine extends StateMachine { if (what == PER_PROCESS_TURN_ON) { isTurningOn = true; } else if (what == PER_PROCESS_TURN_OFF) { } else if (what == USER_TURN_OFF) { isTurningOn = false; } else { Log.e(TAG, "enter PerProcessState: wrong msg: " + what); Loading Loading @@ -568,12 +608,31 @@ final class BluetoothAdapterStateMachine extends StateMachine { } break; case POWER_STATE_CHANGED: removeMessages(POWER_DOWN_TIMEOUT); if (!((Boolean) message.obj)) { transitionTo(mHotOff); if (!mContext.getResources().getBoolean (com.android.internal.R.bool.config_bluetooth_adapter_quick_switch)) { deferMessage(obtainMessage(TURN_COLD)); } } else { if (!isTurningOn) { recoverStateMachine(TURN_COLD, null); for (IBluetoothStateChangeCallback c: mBluetoothService.getApplicationStateChangeCallbacks()) { perProcessCallback(false, c); deferMessage(obtainMessage(PER_PROCESS_TURN_ON, c)); } } } break; case POWER_DOWN_TIMEOUT: transitionTo(mHotOff); Log.e(TAG, "Power-down timed out, resetting..."); deferMessage(obtainMessage(TURN_COLD)); if (mContext.getResources().getBoolean (com.android.internal.R.bool.config_bluetooth_adapter_quick_switch)) { deferMessage(obtainMessage(TURN_HOT)); } break; case USER_TURN_ON: Loading Loading @@ -616,10 +675,12 @@ final class BluetoothAdapterStateMachine extends StateMachine { perProcessCallback(false, (IBluetoothStateChangeCallback)message.obj); if (mBluetoothService.isApplicationStateChangeTrackerEmpty()) { mBluetoothService.switchConnectable(false); sendMessageDelayed(POWER_DOWN_TIMEOUT, POWER_DOWN_TIMEOUT_TIME); } break; case AIRPLANE_MODE_ON: mBluetoothService.switchConnectable(false); sendMessageDelayed(POWER_DOWN_TIMEOUT, POWER_DOWN_TIMEOUT_TIME); allProcessesCallback(false); // we turn all the way to PowerOff with AIRPLANE_MODE_ON deferMessage(obtainMessage(AIRPLANE_MODE_ON)); Loading Loading @@ -699,6 +760,17 @@ final class BluetoothAdapterStateMachine extends StateMachine { mContext.sendBroadcast(intent, BluetoothService.BLUETOOTH_PERM); } /** * bluetoothd has crashed and recovered, the adapter state machine has to * reset itself and try to return to previous state */ private void recoverStateMachine(int what, Object obj) { Log.e(TAG, "Get unexpected power on event, reset with: " + what); transitionTo(mHotOff); deferMessage(obtainMessage(TURN_COLD)); deferMessage(obtainMessage(what, obj)); } private void dump(PrintWriter pw) { IState currentState = getCurrentState(); if (currentState == mPowerOff) { Loading
core/java/android/server/BluetoothEventLoop.java +2 −17 Original line number Diff line number Diff line Loading @@ -59,9 +59,8 @@ class BluetoothEventLoop { // from remote device when Android is in Suspend state. private PowerManager.WakeLock mWakeLock; private static final int EVENT_RESTART_BLUETOOTH = 1; private static final int EVENT_PAIRING_CONSENT_DELAYED_ACCEPT = 2; private static final int EVENT_AGENT_CANCEL = 3; private static final int EVENT_PAIRING_CONSENT_DELAYED_ACCEPT = 1; private static final int EVENT_AGENT_CANCEL = 2; private static final int CREATE_DEVICE_ALREADY_EXISTS = 1; private static final int CREATE_DEVICE_SUCCESS = 0; Loading @@ -75,9 +74,6 @@ class BluetoothEventLoop { public void handleMessage(Message msg) { String address = null; switch (msg.what) { case EVENT_RESTART_BLUETOOTH: mBluetoothService.restart(); break; case EVENT_PAIRING_CONSENT_DELAYED_ACCEPT: address = (String)msg.obj; if (address != null) { Loading Loading @@ -375,9 +371,6 @@ class BluetoothEventLoop { } else if (name.equals("Powered")) { mBluetoothState.sendMessage(BluetoothAdapterStateMachine.POWER_STATE_CHANGED, propValues[1].equals("true") ? new Boolean(true) : new Boolean(false)); // bluetoothd has restarted, re-read all our properties. // Note: bluez only sends this property change when it restarts. onRestartRequired(); } else if (name.equals("DiscoverableTimeout")) { adapterProperties.setProperty(name, propValues[1]); } Loading Loading @@ -1033,14 +1026,6 @@ class BluetoothEventLoop { mBluetoothService.onHealthDeviceChannelChanged(devicePath, channelPath, exists); } private void onRestartRequired() { if (mBluetoothService.isEnabled()) { Log.e(TAG, "*** A serious error occurred (did bluetoothd crash?) - " + "restarting Bluetooth ***"); mHandler.sendEmptyMessage(EVENT_RESTART_BLUETOOTH); } } private static void log(String msg) { Log.d(TAG, msg); } Loading
core/java/android/server/BluetoothService.java +0 −21 Original line number Diff line number Diff line Loading @@ -95,7 +95,6 @@ public class BluetoothService extends IBluetooth.Stub { private boolean mIsAirplaneSensitive; private boolean mIsAirplaneToggleable; private BluetoothAdapterStateMachine mBluetoothState; private boolean mRestart = false; // need to call enable() after disable() private int[] mAdapterSdpHandles; private ParcelUuid[] mAdapterUuids; Loading Loading @@ -429,11 +428,6 @@ public class BluetoothService extends IBluetooth.Stub { } finally { Binder.restoreCallingIdentity(ident); } if (mRestart) { mRestart = false; enable(); } } /** Loading @@ -456,10 +450,6 @@ public class BluetoothService extends IBluetooth.Stub { // the adapter property could be changed before event loop is stoped, clear it again mAdapterProperties.clear(); disableNative(); if (mRestart) { mRestart = false; enable(); } } /** Bring up BT and persist BT on in settings */ Loading Loading @@ -500,17 +490,6 @@ public class BluetoothService extends IBluetooth.Stub { return true; } /** Forcibly restart Bluetooth if it is on */ /* package */ synchronized void restart() { if (getBluetoothStateInternal() != BluetoothAdapter.STATE_ON) { return; } mRestart = true; if (!disable(false)) { mRestart = false; } } private final Handler mHandler = new Handler() { @Override public void handleMessage(Message msg) { Loading