From f8cd68c6e2440f541c77c1e7e299aaca432c05c5 Mon Sep 17 00:00:00 2001 From: Hugh Chen Date: Thu, 28 Oct 2021 06:21:37 +0000 Subject: [PATCH] RESTRICT AUTOMERGE Fix make Bluetooth discoverable without additional permission - Only enable device can be discoverable when the user launch "Connected Devices settings" through settings and systemui Bug: 194695497 Test: make -j42 RunSettingsRoboTests and use test apk to manually test to verify the device is not discoversable when open "Connected settings" through test apk. Change-Id: Ia04ab759b737acf30b782f5c5831dd59f25fb257 (cherry picked from commit d3abbb9821dca627c49b15185109150c79597549) --- .../ConnectedDeviceDashboardFragment.java | 27 ++++++++++++++++++- ...iscoverableFooterPreferenceController.java | 17 +++++++++--- ...verableFooterPreferenceControllerTest.java | 27 +++++++++++++++++-- 3 files changed, 65 insertions(+), 6 deletions(-) diff --git a/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragment.java b/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragment.java index 482c45faa43..241648c3a09 100644 --- a/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragment.java +++ b/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragment.java @@ -16,9 +16,14 @@ package com.android.settings.connecteddevice; import android.app.Activity; +import android.app.ActivityManager; import android.content.Context; +import android.os.IBinder; +import android.os.RemoteException; import android.provider.SearchIndexableResource; import android.support.annotation.VisibleForTesting; +import android.text.TextUtils; +import android.util.Log; import com.android.internal.logging.nano.MetricsProto; import com.android.settings.R; @@ -36,6 +41,9 @@ import java.util.List; public class ConnectedDeviceDashboardFragment extends DashboardFragment { private static final String TAG = "ConnectedDeviceFrag"; + private static final String SETTINGS_PACKAGE_NAME = "com.android.settings"; + private static final String SYSTEMUI_PACKAGE_NAME = "com.android.systemui"; + private static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG); @VisibleForTesting static final String KEY_CONNECTED_DEVICES = "connected_device_list"; @@ -84,10 +92,27 @@ public class ConnectedDeviceDashboardFragment extends DashboardFragment { @Override public void onAttach(Context context) { super.onAttach(context); + + String callingAppPackageName = getCallingAppPackageName(getActivity().getActivityToken()); + if (DEBUG) { + Log.d(TAG, "onAttach() calling package name is : " + callingAppPackageName); + } use(AvailableMediaDeviceGroupController.class).init(this); use(ConnectedDeviceGroupController.class).init(this); use(PreviouslyConnectedDevicePreferenceController.class).init(this); - use(DiscoverableFooterPreferenceController.class).init(this); + use(DiscoverableFooterPreferenceController.class).init(this, + TextUtils.equals(SETTINGS_PACKAGE_NAME, callingAppPackageName) + || TextUtils.equals(SYSTEMUI_PACKAGE_NAME, callingAppPackageName)); + } + + private String getCallingAppPackageName(IBinder activityToken) { + String pkg = null; + try { + pkg = ActivityManager.getService().getLaunchedFromPackage(activityToken); + } catch (RemoteException e) { + Log.v(TAG, "Could not talk to activity manager.", e); + } + return pkg; } @VisibleForTesting diff --git a/src/com/android/settings/connecteddevice/DiscoverableFooterPreferenceController.java b/src/com/android/settings/connecteddevice/DiscoverableFooterPreferenceController.java index 6d2b7154b4c..eb8a9be5705 100644 --- a/src/com/android/settings/connecteddevice/DiscoverableFooterPreferenceController.java +++ b/src/com/android/settings/connecteddevice/DiscoverableFooterPreferenceController.java @@ -54,6 +54,7 @@ public class DiscoverableFooterPreferenceController extends BasePreferenceContro private LocalBluetoothManager mLocalManager; private LocalBluetoothAdapter mLocalAdapter; private AlwaysDiscoverable mAlwaysDiscoverable; + private boolean mIsAlwaysDiscoverable; public DiscoverableFooterPreferenceController(Context context) { super(context, KEY); @@ -79,8 +80,9 @@ public class DiscoverableFooterPreferenceController extends BasePreferenceContro }; } - public void init(DashboardFragment fragment) { + public void init(DashboardFragment fragment, boolean isAlwaysDiscoverable) { mFooterPreferenceMixin = new FooterPreferenceMixin(fragment, fragment.getLifecycle()); + mIsAlwaysDiscoverable = isAlwaysDiscoverable; } @VisibleForTesting @@ -91,6 +93,11 @@ public class DiscoverableFooterPreferenceController extends BasePreferenceContro mAlwaysDiscoverable = alwaysDiscoverable; } + @VisibleForTesting + void setAlwaysDiscoverable(boolean isAlwaysDiscoverable) { + mIsAlwaysDiscoverable = isAlwaysDiscoverable; + } + @Override public void displayPreference(PreferenceScreen screen) { super.displayPreference(screen); @@ -114,14 +121,18 @@ public class DiscoverableFooterPreferenceController extends BasePreferenceContro public void onResume() { mContext.registerReceiver(mBluetoothChangedReceiver, new IntentFilter(BluetoothAdapter.ACTION_STATE_CHANGED)); - mAlwaysDiscoverable.start(); + if (mIsAlwaysDiscoverable) { + mAlwaysDiscoverable.start(); + } updateFooterPreferenceTitle(mLocalAdapter.getState()); } @Override public void onPause() { mContext.unregisterReceiver(mBluetoothChangedReceiver); - mAlwaysDiscoverable.stop(); + if (mIsAlwaysDiscoverable) { + mAlwaysDiscoverable.stop(); + } } private void updateFooterPreferenceTitle (int bluetoothState) { diff --git a/tests/robotests/src/com/android/settings/connecteddevice/DiscoverableFooterPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/connecteddevice/DiscoverableFooterPreferenceControllerTest.java index 8cad0bfe70d..4b517b672d6 100644 --- a/tests/robotests/src/com/android/settings/connecteddevice/DiscoverableFooterPreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/connecteddevice/DiscoverableFooterPreferenceControllerTest.java @@ -17,6 +17,7 @@ package com.android.settings.connecteddevice; import static com.google.common.truth.Truth.assertThat; import static org.mockito.Mockito.doReturn; +import static org.mockito.Mockito.never; import static org.mockito.Mockito.spy; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; @@ -117,14 +118,17 @@ public class DiscoverableFooterPreferenceControllerTest { } @Test - public void onResume() { + public void onResume_setAlwaysDiscoverableAsTrue_shouldRegisterBluetoothChanged() { + mDiscoverableFooterPreferenceController.setAlwaysDiscoverable(true); mDiscoverableFooterPreferenceController.onResume(); + assertThat(getRegisteredBroadcastReceivers()).contains(mBluetoothChangedReceiver); verify(mAlwaysDiscoverable).start(); } @Test - public void onPause() { + public void onPause_setAlwaysDiscoverableAsTrue_shouldUnregisterBluetoothChanged() { + mDiscoverableFooterPreferenceController.setAlwaysDiscoverable(true); mDiscoverableFooterPreferenceController.onResume(); mDiscoverableFooterPreferenceController.onPause(); @@ -132,6 +136,25 @@ public class DiscoverableFooterPreferenceControllerTest { verify(mAlwaysDiscoverable).stop(); } + @Test + public void onResume_setAlwaysDiscoverableAsFalse_shouldNotRegisterBluetoothChanged() { + mDiscoverableFooterPreferenceController.setAlwaysDiscoverable(false); + mDiscoverableFooterPreferenceController.onResume(); + + assertThat(getRegisteredBroadcastReceivers()).contains(mBluetoothChangedReceiver); + verify(mAlwaysDiscoverable, never()).start(); + } + + @Test + public void onPause_setAlwaysDiscoverableAsFalse_shouldNotUnregisterBluetoothChanged() { + mDiscoverableFooterPreferenceController.setAlwaysDiscoverable(false); + mDiscoverableFooterPreferenceController.onResume(); + mDiscoverableFooterPreferenceController.onPause(); + + assertThat(getRegisteredBroadcastReceivers()).doesNotContain(mBluetoothChangedReceiver); + verify(mAlwaysDiscoverable, never()).stop(); + } + @Test public void onBluetoothStateChanged_bluetoothOn_updateTitle() { ShadowLocalBluetoothAdapter.setName(DEVICE_NAME);