From 02bc0086071b5faff260566b4d3713861703eee3 Mon Sep 17 00:00:00 2001 From: Wei Wang Date: Mon, 9 Nov 2015 19:45:53 -0800 Subject: [PATCH] Properly handle registration timeout in BLE. Bug:25384098 Change-Id: I7877f6368c4982fcd91e68810c4da0ab7b5fc6b7 --- .../bluetooth/le/BluetoothLeAdvertiser.java | 19 ++++++++++---- .../bluetooth/le/BluetoothLeScanner.java | 25 +++++++++++-------- 2 files changed, 28 insertions(+), 16 deletions(-) diff --git a/core/java/android/bluetooth/le/BluetoothLeAdvertiser.java b/core/java/android/bluetooth/le/BluetoothLeAdvertiser.java index eaf20d8e19b3f..d468bd416edae 100644 --- a/core/java/android/bluetooth/le/BluetoothLeAdvertiser.java +++ b/core/java/android/bluetooth/le/BluetoothLeAdvertiser.java @@ -237,8 +237,8 @@ public final class BluetoothLeAdvertiser { private final IBluetoothGatt mBluetoothGatt; // mClientIf 0: not registered - // -1: scan stopped - // >0: registered and scan started + // -1: advertise stopped or registration timeout + // >0: registered and advertising started private int mClientIf; private boolean mIsAdvertising = false; @@ -268,6 +268,10 @@ public final class BluetoothLeAdvertiser { if (mClientIf > 0 && mIsAdvertising) { mLeAdvertisers.put(mAdvertiseCallback, this); } else if (mClientIf <= 0) { + + // Registration timeout, reset mClientIf to -1 so no subsequent operations can + // proceed. + if (mClientIf == 0) mClientIf = -1; // Post internal error if registration failed. postStartFailure(mAdvertiseCallback, AdvertiseCallback.ADVERTISE_FAILED_INTERNAL_ERROR); @@ -308,10 +312,15 @@ public final class BluetoothLeAdvertiser { Log.d(TAG, "onClientRegistered() - status=" + status + " clientIf=" + clientIf); synchronized (this) { if (status == BluetoothGatt.GATT_SUCCESS) { - mClientIf = clientIf; try { - mBluetoothGatt.startMultiAdvertising(mClientIf, mAdvertisement, - mScanResponse, mSettings); + if (mClientIf == -1) { + // Registration succeeds after timeout, unregister client. + mBluetoothGatt.unregisterClient(clientIf); + } else { + mClientIf = clientIf; + mBluetoothGatt.startMultiAdvertising(mClientIf, mAdvertisement, + mScanResponse, mSettings); + } return; } catch (RemoteException e) { Log.e(TAG, "failed to start advertising", e); diff --git a/core/java/android/bluetooth/le/BluetoothLeScanner.java b/core/java/android/bluetooth/le/BluetoothLeScanner.java index 03449ccec3556..5715ff87242d1 100644 --- a/core/java/android/bluetooth/le/BluetoothLeScanner.java +++ b/core/java/android/bluetooth/le/BluetoothLeScanner.java @@ -278,7 +278,7 @@ public final class BluetoothLeScanner { private List> mResultStorages; // mLeHandle 0: not registered - // -1: scan stopped + // -1: scan stopped or registration failed // > 0: registered and scan started private int mClientIf; @@ -310,6 +310,9 @@ public final class BluetoothLeScanner { if (mClientIf > 0) { mLeScanClients.put(mScanCallback, this); } else { + // Registration timed out or got exception, reset clientIf to -1 so no + // subsequent operations can proceed. + if (mClientIf == 0) mClientIf = -1; postCallbackError(mScanCallback, ScanCallback.SCAN_FAILED_APPLICATION_REGISTRATION_FAILED); } @@ -352,19 +355,19 @@ public final class BluetoothLeScanner { @Override public void onClientRegistered(int status, int clientIf) { Log.d(TAG, "onClientRegistered() - status=" + status + - " clientIf=" + clientIf); + " clientIf=" + clientIf + " mClientIf=" + mClientIf); synchronized (this) { - if (mClientIf == -1) { - if (DBG) Log.d(TAG, "onClientRegistered LE scan canceled"); - } - if (status == BluetoothGatt.GATT_SUCCESS) { - mClientIf = clientIf; try { - mBluetoothGatt.startScan(mClientIf, false, mSettings, mFilters, - mWorkSource, mResultStorages, - ActivityThread.currentOpPackageName()); - + if (mClientIf == -1) { + // Registration succeeds after timeout, unregister client. + mBluetoothGatt.unregisterClient(clientIf); + } else { + mClientIf = clientIf; + mBluetoothGatt.startScan(mClientIf, false, mSettings, mFilters, + mWorkSource, mResultStorages, + ActivityThread.currentOpPackageName()); + } } catch (RemoteException e) { Log.e(TAG, "fail to start le scan: " + e); mClientIf = -1;