summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--services/companion/java/com/android/server/companion/CompanionDeviceManagerService.java20
-rw-r--r--services/companion/java/com/android/server/companion/presence/BluetoothCompanionDeviceConnectionListener.java54
-rw-r--r--services/companion/java/com/android/server/companion/presence/CompanionDevicePresenceMonitor.java21
3 files changed, 85 insertions, 10 deletions
diff --git a/services/companion/java/com/android/server/companion/CompanionDeviceManagerService.java b/services/companion/java/com/android/server/companion/CompanionDeviceManagerService.java
index 0172eaf03fa7..c8db662a7f49 100644
--- a/services/companion/java/com/android/server/companion/CompanionDeviceManagerService.java
+++ b/services/companion/java/com/android/server/companion/CompanionDeviceManagerService.java
@@ -54,6 +54,7 @@ import android.app.ActivityManagerInternal;
import android.app.AppOpsManager;
import android.app.NotificationManager;
import android.app.PendingIntent;
+import android.bluetooth.BluetoothDevice;
import android.companion.AssociationInfo;
import android.companion.AssociationRequest;
import android.companion.DeviceNotAssociatedException;
@@ -234,7 +235,7 @@ public class CompanionDeviceManagerService extends SystemService {
loadAssociationsFromDisk();
mAssociationStore.registerListener(mAssociationStoreChangeListener);
- mDevicePresenceMonitor = new CompanionDevicePresenceMonitor(
+ mDevicePresenceMonitor = new CompanionDevicePresenceMonitor(mUserManager,
mAssociationStore, mDevicePresenceCallback);
mAssociationRequestsProcessor = new AssociationRequestsProcessor(
@@ -322,6 +323,23 @@ public class CompanionDeviceManagerService extends SystemService {
MINUTES.toMillis(10));
}
+ @Override
+ public void onUserUnlocked(@NonNull TargetUser user) {
+ // Notify and bind the app after the phone is unlocked.
+ final int userId = user.getUserIdentifier();
+ final Set<BluetoothDevice> blueToothDevices =
+ mDevicePresenceMonitor.getPendingConnectedDevices().get(userId);
+ if (blueToothDevices != null) {
+ for (BluetoothDevice bluetoothDevice : blueToothDevices) {
+ for (AssociationInfo ai:
+ mAssociationStore.getAssociationsByAddress(bluetoothDevice.getAddress())) {
+ Slog.i(TAG, "onUserUnlocked, device id( " + ai.getId() + " ) is connected");
+ mDevicePresenceMonitor.onBluetoothCompanionDeviceConnected(ai.getId());
+ }
+ }
+ }
+ }
+
@NonNull
AssociationInfo getAssociationWithCallerChecks(
@UserIdInt int userId, @NonNull String packageName, @NonNull String macAddress) {
diff --git a/services/companion/java/com/android/server/companion/presence/BluetoothCompanionDeviceConnectionListener.java b/services/companion/java/com/android/server/companion/presence/BluetoothCompanionDeviceConnectionListener.java
index f6b99b551ecb..a5410e448c7b 100644
--- a/services/companion/java/com/android/server/companion/presence/BluetoothCompanionDeviceConnectionListener.java
+++ b/services/companion/java/com/android/server/companion/presence/BluetoothCompanionDeviceConnectionListener.java
@@ -27,17 +27,24 @@ import android.companion.AssociationInfo;
import android.net.MacAddress;
import android.os.Handler;
import android.os.HandlerExecutor;
+import android.os.UserHandle;
+import android.os.UserManager;
import android.util.Log;
+import android.util.Slog;
+import android.util.SparseArray;
+import com.android.internal.annotations.GuardedBy;
import com.android.server.companion.AssociationStore;
import java.util.Arrays;
import java.util.HashMap;
+import java.util.HashSet;
import java.util.List;
import java.util.Map;
+import java.util.Set;
@SuppressLint("LongLogTag")
-class BluetoothCompanionDeviceConnectionListener
+public class BluetoothCompanionDeviceConnectionListener
extends BluetoothAdapter.BluetoothConnectionCallback
implements AssociationStore.OnChangeListener {
private static final String TAG = "CDM_BluetoothCompanionDeviceConnectionListener";
@@ -48,15 +55,25 @@ class BluetoothCompanionDeviceConnectionListener
void onBluetoothCompanionDeviceDisconnected(int associationId);
}
+ private final UserManager mUserManager;
private final @NonNull AssociationStore mAssociationStore;
private final @NonNull Callback mCallback;
/** A set of ALL connected BT device (not only companion.) */
private final @NonNull Map<MacAddress, BluetoothDevice> mAllConnectedDevices = new HashMap<>();
- BluetoothCompanionDeviceConnectionListener(@NonNull AssociationStore associationStore,
- @NonNull Callback callback) {
+ /**
+ * A structure hold the connected BT devices that are pending to be reported to the companion
+ * app when the user unlocks the local device per userId.
+ */
+ @GuardedBy("mPendingConnectedDevices")
+ @NonNull
+ final SparseArray<Set<BluetoothDevice>> mPendingConnectedDevices = new SparseArray<>();
+
+ BluetoothCompanionDeviceConnectionListener(UserManager userManager,
+ @NonNull AssociationStore associationStore, @NonNull Callback callback) {
mAssociationStore = associationStore;
mCallback = callback;
+ mUserManager = userManager;
}
public void init(@NonNull BluetoothAdapter btAdapter) {
@@ -76,12 +93,26 @@ class BluetoothCompanionDeviceConnectionListener
if (DEBUG) Log.i(TAG, "onDevice_Connected() " + btDeviceToString(device));
final MacAddress macAddress = MacAddress.fromString(device.getAddress());
+ final int userId = UserHandle.myUserId();
+
if (mAllConnectedDevices.put(macAddress, device) != null) {
if (DEBUG) Log.w(TAG, "Device " + btDeviceToString(device) + " is already connected.");
return;
}
+ // Try to bind and notify the app after the phone is unlocked.
+ if (!mUserManager.isUserUnlockingOrUnlocked(UserHandle.myUserId())) {
+ Slog.i(TAG, "Current user is not in unlocking or unlocked stage yet. Notify "
+ + "the application when the phone is unlocked");
+ synchronized (mPendingConnectedDevices) {
+ Set<BluetoothDevice> bluetoothDevices = mPendingConnectedDevices.get(
+ userId, new HashSet<>());
+ bluetoothDevices.add(device);
+ mPendingConnectedDevices.put(userId, bluetoothDevices);
+ }
- onDeviceConnectivityChanged(device, true);
+ } else {
+ onDeviceConnectivityChanged(device, true);
+ }
}
/**
@@ -98,6 +129,8 @@ class BluetoothCompanionDeviceConnectionListener
}
final MacAddress macAddress = MacAddress.fromString(device.getAddress());
+ final int userId = UserHandle.myUserId();
+
if (mAllConnectedDevices.remove(macAddress) == null) {
if (DEBUG) {
Log.w(TAG, "The device wasn't tracked as connected " + btDeviceToString(device));
@@ -105,6 +138,19 @@ class BluetoothCompanionDeviceConnectionListener
return;
}
+ // Do not need to report the connectivity since the user is not unlock the phone so
+ // that cdm is not bind with the app yet.
+ if (!mUserManager.isUserUnlockingOrUnlocked(userId)) {
+ synchronized (mPendingConnectedDevices) {
+ Set<BluetoothDevice> bluetoothDevices = mPendingConnectedDevices.get(userId);
+ if (bluetoothDevices != null) {
+ bluetoothDevices.remove(device);
+ }
+ }
+
+ return;
+ }
+
onDeviceConnectivityChanged(device, false);
}
diff --git a/services/companion/java/com/android/server/companion/presence/CompanionDevicePresenceMonitor.java b/services/companion/java/com/android/server/companion/presence/CompanionDevicePresenceMonitor.java
index 4010be922b2c..f6e9415a2a7e 100644
--- a/services/companion/java/com/android/server/companion/presence/CompanionDevicePresenceMonitor.java
+++ b/services/companion/java/com/android/server/companion/presence/CompanionDevicePresenceMonitor.java
@@ -23,13 +23,16 @@ import android.annotation.NonNull;
import android.annotation.SuppressLint;
import android.annotation.TestApi;
import android.bluetooth.BluetoothAdapter;
+import android.bluetooth.BluetoothDevice;
import android.companion.AssociationInfo;
import android.content.Context;
import android.os.Binder;
import android.os.Handler;
import android.os.Looper;
import android.os.Message;
+import android.os.UserManager;
import android.util.Log;
+import android.util.SparseArray;
import com.android.server.companion.AssociationStore;
@@ -86,13 +89,12 @@ public class CompanionDevicePresenceMonitor implements AssociationStore.OnChange
private final SimulatedDevicePresenceSchedulerHelper mSchedulerHelper =
new SimulatedDevicePresenceSchedulerHelper();
- public CompanionDevicePresenceMonitor(@NonNull AssociationStore associationStore,
- @NonNull Callback callback) {
+ public CompanionDevicePresenceMonitor(UserManager userManager,
+ @NonNull AssociationStore associationStore, @NonNull Callback callback) {
mAssociationStore = associationStore;
mCallback = callback;
-
- mBtConnectionListener = new BluetoothCompanionDeviceConnectionListener(associationStore,
- /* BluetoothCompanionDeviceConnectionListener.Callback */ this);
+ mBtConnectionListener = new BluetoothCompanionDeviceConnectionListener(userManager,
+ associationStore, /* BluetoothCompanionDeviceConnectionListener.Callback */ this);
mBleScanner = new BleCompanionDeviceScanner(associationStore,
/* BleCompanionDeviceScanner.Callback */ this);
}
@@ -298,6 +300,15 @@ public class CompanionDevicePresenceMonitor implements AssociationStore.OnChange
// what's needed.
}
+ /**
+ * Return a set of devices that pending to report connectivity
+ */
+ public SparseArray<Set<BluetoothDevice>> getPendingConnectedDevices() {
+ synchronized (mBtConnectionListener.mPendingConnectedDevices) {
+ return mBtConnectionListener.mPendingConnectedDevices;
+ }
+ }
+
private static void enforceCallerShellOrRoot() {
final int callingUid = Binder.getCallingUid();
if (callingUid == SHELL_UID || callingUid == ROOT_UID) return;