mirror of
https://github.com/Divested-Mobile/DivestOS-Build.git
synced 2024-10-01 01:35:54 -04:00
497 lines
21 KiB
Diff
497 lines
21 KiB
Diff
|
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||
|
From: Wenhao Wang <wenhaowang@google.com>
|
||
|
Date: Wed, 2 Feb 2022 10:56:44 -0800
|
||
|
Subject: [PATCH] DO NOT MERGE Suppress notifications when device enter
|
||
|
lockdown
|
||
|
|
||
|
This CL makes the following modifcations:
|
||
|
1. Add LockPatternUtils.StrongAuthTracker to monitor
|
||
|
the lockdown mode status of the phone.
|
||
|
2. Call mListeners.notifyRemovedLocked with all the
|
||
|
notifications in the mNotificationList when entering
|
||
|
the lockdown mode.
|
||
|
3. Call mListeners.notifyPostedLocked with all the
|
||
|
notifications in the mNotificationList when exiting
|
||
|
the lockdown mode.
|
||
|
4. Dismiss the function calls of notifyPostedLocked,
|
||
|
notifyRemovedLocked, and notifyRankingUpdateLocked
|
||
|
during the lockdown mode.
|
||
|
|
||
|
The CL also adds corresponding tests.
|
||
|
|
||
|
Bug: 173721373
|
||
|
Test: atest NotificationManagerServiceTest
|
||
|
Test: atest NotificationListenersTest
|
||
|
Test: manually verify the paired device cannot receive
|
||
|
notifications when the host phone is in lockdown mode.
|
||
|
Ignore-AOSP-First: pending fix for a security issue.
|
||
|
|
||
|
Change-Id: I7e83544863eeadf8272b6ff8a9bb8136d6466203
|
||
|
Merged-In: I7e83544863eeadf8272b6ff8a9bb8136d6466203
|
||
|
(cherry picked from commit 3cb6842a053e236cc98d7616ba4433c31ffda3ac)
|
||
|
(cherry picked from commit 85c00b98a6cac8d7286a70300ceff509693818f2)
|
||
|
Merged-In: I7e83544863eeadf8272b6ff8a9bb8136d6466203
|
||
|
---
|
||
|
.../NotificationManagerService.java | 109 +++++++++++++-
|
||
|
.../tests/uiservicestests/AndroidManifest.xml | 1 +
|
||
|
.../NotificationListenersTest.java | 135 ++++++++++++++++++
|
||
|
.../NotificationManagerServiceTest.java | 66 +++++++++
|
||
|
4 files changed, 305 insertions(+), 6 deletions(-)
|
||
|
create mode 100644 services/tests/uiservicestests/src/com/android/server/notification/NotificationListenersTest.java
|
||
|
|
||
|
diff --git a/services/core/java/com/android/server/notification/NotificationManagerService.java b/services/core/java/com/android/server/notification/NotificationManagerService.java
|
||
|
index dd202a172d66..0dfc0ab0c3e0 100755
|
||
|
--- a/services/core/java/com/android/server/notification/NotificationManagerService.java
|
||
|
+++ b/services/core/java/com/android/server/notification/NotificationManagerService.java
|
||
|
@@ -181,6 +181,7 @@ import android.util.AtomicFile;
|
||
|
import android.util.Log;
|
||
|
import android.util.Slog;
|
||
|
import android.util.SparseArray;
|
||
|
+import android.util.SparseBooleanArray;
|
||
|
import android.util.TimeUtils;
|
||
|
import android.util.Xml;
|
||
|
import android.util.proto.ProtoOutputStream;
|
||
|
@@ -202,6 +203,7 @@ import com.android.internal.util.DumpUtils;
|
||
|
import com.android.internal.util.FastXmlSerializer;
|
||
|
import com.android.internal.util.Preconditions;
|
||
|
import com.android.internal.util.XmlUtils;
|
||
|
+import com.android.internal.widget.LockPatternUtils;
|
||
|
import com.android.server.DeviceIdleController;
|
||
|
import com.android.server.EventLogTags;
|
||
|
import com.android.server.LocalServices;
|
||
|
@@ -1272,6 +1274,54 @@ public class NotificationManagerService extends SystemService {
|
||
|
return out;
|
||
|
}
|
||
|
|
||
|
+ protected class StrongAuthTracker extends LockPatternUtils.StrongAuthTracker {
|
||
|
+
|
||
|
+ SparseBooleanArray mUserInLockDownMode = new SparseBooleanArray();
|
||
|
+ boolean mIsInLockDownMode = false;
|
||
|
+
|
||
|
+ StrongAuthTracker(Context context) {
|
||
|
+ super(context);
|
||
|
+ }
|
||
|
+
|
||
|
+ private boolean containsFlag(int haystack, int needle) {
|
||
|
+ return (haystack & needle) != 0;
|
||
|
+ }
|
||
|
+
|
||
|
+ public boolean isInLockDownMode() {
|
||
|
+ return mIsInLockDownMode;
|
||
|
+ }
|
||
|
+
|
||
|
+ @Override
|
||
|
+ public synchronized void onStrongAuthRequiredChanged(int userId) {
|
||
|
+ boolean userInLockDownModeNext = containsFlag(getStrongAuthForUser(userId),
|
||
|
+ STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN);
|
||
|
+ mUserInLockDownMode.put(userId, userInLockDownModeNext);
|
||
|
+ boolean isInLockDownModeNext = mUserInLockDownMode.indexOfValue(true) != -1;
|
||
|
+
|
||
|
+ if (mIsInLockDownMode == isInLockDownModeNext) {
|
||
|
+ return;
|
||
|
+ }
|
||
|
+
|
||
|
+ if (isInLockDownModeNext) {
|
||
|
+ cancelNotificationsWhenEnterLockDownMode();
|
||
|
+ }
|
||
|
+
|
||
|
+ // When the mIsInLockDownMode is true, both notifyPostedLocked and
|
||
|
+ // notifyRemovedLocked will be dismissed. So we shall call
|
||
|
+ // cancelNotificationsWhenEnterLockDownMode before we set mIsInLockDownMode
|
||
|
+ // as true and call postNotificationsWhenExitLockDownMode after we set
|
||
|
+ // mIsInLockDownMode as false.
|
||
|
+ mIsInLockDownMode = isInLockDownModeNext;
|
||
|
+
|
||
|
+ if (!isInLockDownModeNext) {
|
||
|
+ postNotificationsWhenExitLockDownMode();
|
||
|
+ }
|
||
|
+ }
|
||
|
+ }
|
||
|
+
|
||
|
+ private LockPatternUtils mLockPatternUtils;
|
||
|
+ private StrongAuthTracker mStrongAuthTracker;
|
||
|
+
|
||
|
public NotificationManagerService(Context context) {
|
||
|
super(context);
|
||
|
Notification.processWhitelistToken = WHITELIST_TOKEN;
|
||
|
@@ -1283,6 +1333,11 @@ public class NotificationManagerService extends SystemService {
|
||
|
mAudioManager = audioMananger;
|
||
|
}
|
||
|
|
||
|
+ @VisibleForTesting
|
||
|
+ void setStrongAuthTracker(StrongAuthTracker strongAuthTracker) {
|
||
|
+ mStrongAuthTracker = strongAuthTracker;
|
||
|
+ }
|
||
|
+
|
||
|
@VisibleForTesting
|
||
|
void setHints(int hints) {
|
||
|
mListenerHints = hints;
|
||
|
@@ -1435,6 +1490,8 @@ public class NotificationManagerService extends SystemService {
|
||
|
|
||
|
mHandler = new WorkerHandler(looper);
|
||
|
mRankingThread.start();
|
||
|
+ mLockPatternUtils = new LockPatternUtils(getContext());
|
||
|
+ mStrongAuthTracker = new StrongAuthTracker(getContext());
|
||
|
String[] extractorNames;
|
||
|
try {
|
||
|
extractorNames = resources.getStringArray(R.array.config_notificationSignalExtractors);
|
||
|
@@ -1563,7 +1620,8 @@ public class NotificationManagerService extends SystemService {
|
||
|
init(Looper.myLooper(),
|
||
|
AppGlobals.getPackageManager(), getContext().getPackageManager(),
|
||
|
getLocalService(LightsManager.class),
|
||
|
- new NotificationListeners(AppGlobals.getPackageManager()),
|
||
|
+ new NotificationListeners(getContext(), mNotificationLock, mUserProfiles,
|
||
|
+ AppGlobals.getPackageManager()),
|
||
|
new NotificationAssistants(getContext(), mNotificationLock, mUserProfiles,
|
||
|
AppGlobals.getPackageManager()),
|
||
|
new ConditionProviders(getContext(), mUserProfiles, AppGlobals.getPackageManager()),
|
||
|
@@ -1679,6 +1737,7 @@ public class NotificationManagerService extends SystemService {
|
||
|
mWindowManagerInternal = LocalServices.getService(WindowManagerInternal.class);
|
||
|
mKeyguardManager = getContext().getSystemService(KeyguardManager.class);
|
||
|
mZenModeHelper.onSystemReady();
|
||
|
+ mLockPatternUtils.registerStrongAuthTracker(mStrongAuthTracker);
|
||
|
} else if (phase == SystemService.PHASE_THIRD_PARTY_APPS_CAN_START) {
|
||
|
// This observer will force an update when observe is called, causing us to
|
||
|
// bind to listener services.
|
||
|
@@ -6342,6 +6401,29 @@ public class NotificationManagerService extends SystemService {
|
||
|
}
|
||
|
}
|
||
|
|
||
|
+ private void cancelNotificationsWhenEnterLockDownMode() {
|
||
|
+ synchronized (mNotificationLock) {
|
||
|
+ int numNotifications = mNotificationList.size();
|
||
|
+ for (int i = 0; i < numNotifications; i++) {
|
||
|
+ NotificationRecord rec = mNotificationList.get(i);
|
||
|
+ mListeners.notifyRemovedLocked(rec, REASON_CANCEL_ALL,
|
||
|
+ rec.getStats());
|
||
|
+ }
|
||
|
+
|
||
|
+ }
|
||
|
+ }
|
||
|
+
|
||
|
+ private void postNotificationsWhenExitLockDownMode() {
|
||
|
+ synchronized (mNotificationLock) {
|
||
|
+ int numNotifications = mNotificationList.size();
|
||
|
+ for (int i = 0; i < numNotifications; i++) {
|
||
|
+ NotificationRecord rec = mNotificationList.get(i);
|
||
|
+ mListeners.notifyPostedLocked(rec, rec);
|
||
|
+ }
|
||
|
+
|
||
|
+ }
|
||
|
+ }
|
||
|
+
|
||
|
private void updateNotificationPulse() {
|
||
|
synchronized (mNotificationLock) {
|
||
|
updateLightsLocked();
|
||
|
@@ -6502,6 +6584,10 @@ public class NotificationManagerService extends SystemService {
|
||
|
channels, overridePeople, snoozeCriteria, showBadge, userSentiment, hidden);
|
||
|
}
|
||
|
|
||
|
+ boolean isInLockDownMode() {
|
||
|
+ return mStrongAuthTracker.isInLockDownMode();
|
||
|
+ }
|
||
|
+
|
||
|
boolean hasCompanionDevice(ManagedServiceInfo info) {
|
||
|
if (mCompanionManager == null) {
|
||
|
mCompanionManager = getCompanionManager();
|
||
|
@@ -6730,9 +6816,9 @@ public class NotificationManagerService extends SystemService {
|
||
|
|
||
|
private final ArraySet<ManagedServiceInfo> mLightTrimListeners = new ArraySet<>();
|
||
|
|
||
|
- public NotificationListeners(IPackageManager pm) {
|
||
|
- super(getContext(), mNotificationLock, mUserProfiles, pm);
|
||
|
-
|
||
|
+ public NotificationListeners(Context context, Object lock, UserProfiles userProfiles,
|
||
|
+ IPackageManager pm) {
|
||
|
+ super(context, lock, userProfiles, pm);
|
||
|
}
|
||
|
|
||
|
@Override
|
||
|
@@ -6822,8 +6908,12 @@ public class NotificationManagerService extends SystemService {
|
||
|
* targetting <= O_MR1
|
||
|
*/
|
||
|
@GuardedBy("mNotificationLock")
|
||
|
- private void notifyPostedLocked(NotificationRecord r, NotificationRecord old,
|
||
|
+ void notifyPostedLocked(NotificationRecord r, NotificationRecord old,
|
||
|
boolean notifyAllListeners) {
|
||
|
+ if (isInLockDownMode()) {
|
||
|
+ return;
|
||
|
+ }
|
||
|
+
|
||
|
// Lazily initialized snapshots of the notification.
|
||
|
StatusBarNotification sbn = r.sbn;
|
||
|
StatusBarNotification oldSbn = (old != null) ? old.sbn : null;
|
||
|
@@ -6886,8 +6976,11 @@ public class NotificationManagerService extends SystemService {
|
||
|
@GuardedBy("mNotificationLock")
|
||
|
public void notifyRemovedLocked(NotificationRecord r, int reason,
|
||
|
NotificationStats notificationStats) {
|
||
|
- final StatusBarNotification sbn = r.sbn;
|
||
|
+ if (isInLockDownMode()) {
|
||
|
+ return;
|
||
|
+ }
|
||
|
|
||
|
+ final StatusBarNotification sbn = r.sbn;
|
||
|
// make a copy in case changes are made to the underlying Notification object
|
||
|
// NOTE: this copy is lightweight: it doesn't include heavyweight parts of the
|
||
|
// notification
|
||
|
@@ -6938,6 +7031,10 @@ public class NotificationManagerService extends SystemService {
|
||
|
*/
|
||
|
@GuardedBy("mNotificationLock")
|
||
|
public void notifyRankingUpdateLocked(List<NotificationRecord> changedHiddenNotifications) {
|
||
|
+ if (isInLockDownMode()) {
|
||
|
+ return;
|
||
|
+ }
|
||
|
+
|
||
|
boolean isHiddenRankingUpdate = changedHiddenNotifications != null
|
||
|
&& changedHiddenNotifications.size() > 0;
|
||
|
|
||
|
diff --git a/services/tests/uiservicestests/AndroidManifest.xml b/services/tests/uiservicestests/AndroidManifest.xml
|
||
|
index aa3135ff18da..4f81bfae9a7c 100644
|
||
|
--- a/services/tests/uiservicestests/AndroidManifest.xml
|
||
|
+++ b/services/tests/uiservicestests/AndroidManifest.xml
|
||
|
@@ -29,6 +29,7 @@
|
||
|
<uses-permission android:name="android.permission.DEVICE_POWER" />
|
||
|
<uses-permission android:name="android.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY" />
|
||
|
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
|
||
|
+ <uses-permission android:name="android.permission.ACCESS_KEYGUARD_SECURE_STORAGE" />
|
||
|
|
||
|
<application android:debuggable="true">
|
||
|
<uses-library android:name="android.test.runner" />
|
||
|
diff --git a/services/tests/uiservicestests/src/com/android/server/notification/NotificationListenersTest.java b/services/tests/uiservicestests/src/com/android/server/notification/NotificationListenersTest.java
|
||
|
new file mode 100644
|
||
|
index 000000000000..793739bfe8f5
|
||
|
--- /dev/null
|
||
|
+++ b/services/tests/uiservicestests/src/com/android/server/notification/NotificationListenersTest.java
|
||
|
@@ -0,0 +1,135 @@
|
||
|
+/*
|
||
|
+ * Copyright (C) 2022 The Android Open Source Project
|
||
|
+ *
|
||
|
+ * Licensed under the Apache License, Version 2.0 (the "License");
|
||
|
+ * you may not use this file except in compliance with the License.
|
||
|
+ * You may obtain a copy of the License at
|
||
|
+ *
|
||
|
+ * http://www.apache.org/licenses/LICENSE-2.0
|
||
|
+ *
|
||
|
+ * Unless required by applicable law or agreed to in writing, software
|
||
|
+ * distributed under the License is distributed on an "AS IS" BASIS,
|
||
|
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||
|
+ * See the License for the specific language governing permissions and
|
||
|
+ * limitations under the License.
|
||
|
+ */
|
||
|
+package com.android.server.notification;
|
||
|
+
|
||
|
+import static org.mockito.ArgumentMatchers.any;
|
||
|
+import static org.mockito.Mockito.doNothing;
|
||
|
+import static org.mockito.Mockito.mock;
|
||
|
+import static org.mockito.Mockito.never;
|
||
|
+import static org.mockito.Mockito.reset;
|
||
|
+import static org.mockito.Mockito.spy;
|
||
|
+import static org.mockito.Mockito.times;
|
||
|
+import static org.mockito.Mockito.verify;
|
||
|
+import static org.mockito.Mockito.when;
|
||
|
+
|
||
|
+import android.app.INotificationManager;
|
||
|
+import android.content.pm.IPackageManager;
|
||
|
+import android.content.pm.PackageManager;
|
||
|
+import android.service.notification.NotificationStats;
|
||
|
+import android.service.notification.StatusBarNotification;
|
||
|
+import android.testing.TestableContext;
|
||
|
+
|
||
|
+import com.android.server.UiServiceTestCase;
|
||
|
+
|
||
|
+import org.junit.Before;
|
||
|
+import org.junit.Test;
|
||
|
+import org.mockito.Mock;
|
||
|
+import org.mockito.MockitoAnnotations;
|
||
|
+import org.mockito.internal.util.reflection.FieldSetter;
|
||
|
+
|
||
|
+import java.util.List;
|
||
|
+
|
||
|
+public class NotificationListenersTest extends UiServiceTestCase {
|
||
|
+
|
||
|
+ @Mock
|
||
|
+ private PackageManager mPm;
|
||
|
+ @Mock
|
||
|
+ private IPackageManager miPm;
|
||
|
+
|
||
|
+ @Mock
|
||
|
+ NotificationManagerService mNm;
|
||
|
+ @Mock
|
||
|
+ private INotificationManager mINm;
|
||
|
+ private TestableContext mContext = spy(getContext());
|
||
|
+
|
||
|
+ NotificationManagerService.NotificationListeners mListeners;
|
||
|
+
|
||
|
+ @Before
|
||
|
+ public void setUp() throws Exception {
|
||
|
+ MockitoAnnotations.initMocks(this);
|
||
|
+ getContext().setMockPackageManager(mPm);
|
||
|
+ doNothing().when(mContext).sendBroadcastAsUser(any(), any(), any());
|
||
|
+
|
||
|
+ mListeners = spy(mNm.new NotificationListeners(
|
||
|
+ mContext, new Object(), mock(ManagedServices.UserProfiles.class), miPm));
|
||
|
+ when(mNm.getBinderService()).thenReturn(mINm);
|
||
|
+ }
|
||
|
+
|
||
|
+ @Test
|
||
|
+ public void testNotifyPostedLockedInLockdownMode() {
|
||
|
+ NotificationRecord r = mock(NotificationRecord.class);
|
||
|
+ NotificationRecord old = mock(NotificationRecord.class);
|
||
|
+
|
||
|
+ // before the lockdown mode
|
||
|
+ when(mNm.isInLockDownMode()).thenReturn(false);
|
||
|
+ mListeners.notifyPostedLocked(r, old, true);
|
||
|
+ mListeners.notifyPostedLocked(r, old, false);
|
||
|
+ verify(mListeners, times(2)).getServices();
|
||
|
+
|
||
|
+ // in the lockdown mode
|
||
|
+ reset(r);
|
||
|
+ reset(old);
|
||
|
+ reset(mListeners);
|
||
|
+ when(mNm.isInLockDownMode()).thenReturn(true);
|
||
|
+ mListeners.notifyPostedLocked(r, old, true);
|
||
|
+ mListeners.notifyPostedLocked(r, old, false);
|
||
|
+ verify(mListeners, never()).getServices();
|
||
|
+ }
|
||
|
+
|
||
|
+ @Test
|
||
|
+ public void testnotifyRankingUpdateLockedInLockdownMode() {
|
||
|
+ List chn = mock(List.class);
|
||
|
+
|
||
|
+ // before the lockdown mode
|
||
|
+ when(mNm.isInLockDownMode()).thenReturn(false);
|
||
|
+ mListeners.notifyRankingUpdateLocked(chn);
|
||
|
+ verify(chn, times(1)).size();
|
||
|
+
|
||
|
+ // in the lockdown mode
|
||
|
+ reset(chn);
|
||
|
+ when(mNm.isInLockDownMode()).thenReturn(true);
|
||
|
+ mListeners.notifyRankingUpdateLocked(chn);
|
||
|
+ verify(chn, never()).size();
|
||
|
+ }
|
||
|
+
|
||
|
+ @Test
|
||
|
+ public void testNotifyRemovedLockedInLockdownMode() throws NoSuchFieldException {
|
||
|
+ StatusBarNotification sbn = mock(StatusBarNotification.class);
|
||
|
+ NotificationRecord r = mock(NotificationRecord.class);
|
||
|
+ NotificationStats rs = mock(NotificationStats.class);
|
||
|
+ FieldSetter.setField(r,
|
||
|
+ NotificationRecord.class.getDeclaredField("sbn"),
|
||
|
+ sbn);
|
||
|
+ FieldSetter.setField(mNm,
|
||
|
+ NotificationManagerService.class.getDeclaredField("mHandler"),
|
||
|
+ mock(NotificationManagerService.WorkerHandler.class));
|
||
|
+
|
||
|
+ // before the lockdown mode
|
||
|
+ when(mNm.isInLockDownMode()).thenReturn(false);
|
||
|
+ mListeners.notifyRemovedLocked(r, 0, rs);
|
||
|
+ mListeners.notifyRemovedLocked(r, 0, rs);
|
||
|
+ verify(sbn, times(2)).cloneLight();
|
||
|
+
|
||
|
+ // in the lockdown mode
|
||
|
+ reset(sbn);
|
||
|
+ reset(r);
|
||
|
+ reset(rs);
|
||
|
+ when(mNm.isInLockDownMode()).thenReturn(true);
|
||
|
+ mListeners.notifyRemovedLocked(r, 0, rs);
|
||
|
+ mListeners.notifyRemovedLocked(r, 0, rs);
|
||
|
+ verify(sbn, never()).cloneLight();
|
||
|
+ }
|
||
|
+}
|
||
|
diff --git a/services/tests/uiservicestests/src/com/android/server/notification/NotificationManagerServiceTest.java b/services/tests/uiservicestests/src/com/android/server/notification/NotificationManagerServiceTest.java
|
||
|
index 420bfbc042ff..ed3406fc95b4 100644
|
||
|
--- a/services/tests/uiservicestests/src/com/android/server/notification/NotificationManagerServiceTest.java
|
||
|
+++ b/services/tests/uiservicestests/src/com/android/server/notification/NotificationManagerServiceTest.java
|
||
|
@@ -37,6 +37,9 @@ import static android.content.pm.PackageManager.PERMISSION_DENIED;
|
||
|
import static android.content.pm.PackageManager.PERMISSION_GRANTED;
|
||
|
import static android.os.Build.VERSION_CODES.O_MR1;
|
||
|
import static android.os.Build.VERSION_CODES.P;
|
||
|
+import static android.service.notification.NotificationListenerService.REASON_CANCEL_ALL;
|
||
|
+
|
||
|
+import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN;
|
||
|
|
||
|
import static junit.framework.Assert.assertEquals;
|
||
|
import static junit.framework.Assert.assertFalse;
|
||
|
@@ -233,6 +236,26 @@ public class NotificationManagerServiceTest extends UiServiceTestCase {
|
||
|
protected void reportUserInteraction(NotificationRecord r) {
|
||
|
return;
|
||
|
}
|
||
|
+
|
||
|
+ class StrongAuthTrackerFake extends NotificationManagerService.StrongAuthTracker {
|
||
|
+ private int mGetStrongAuthForUserReturnValue = 0;
|
||
|
+ StrongAuthTrackerFake(Context context) {
|
||
|
+ super(context);
|
||
|
+ }
|
||
|
+
|
||
|
+ public void setGetStrongAuthForUserReturnValue(int val) {
|
||
|
+ mGetStrongAuthForUserReturnValue = val;
|
||
|
+ }
|
||
|
+
|
||
|
+ @Override
|
||
|
+ public int getStrongAuthForUser(int userId) {
|
||
|
+ return mGetStrongAuthForUserReturnValue;
|
||
|
+ }
|
||
|
+ }
|
||
|
+ }
|
||
|
+
|
||
|
+ TestableNotificationManagerService.StrongAuthTrackerFake mStrongAuthTracker;
|
||
|
+
|
||
|
}
|
||
|
|
||
|
@Before
|
||
|
@@ -304,6 +327,9 @@ public class NotificationManagerServiceTest extends UiServiceTestCase {
|
||
|
}
|
||
|
mService.setAudioManager(mAudioManager);
|
||
|
|
||
|
+ mStrongAuthTracker = mService.new StrongAuthTrackerFake(mContext);
|
||
|
+ mService.setStrongAuthTracker(mStrongAuthTracker);
|
||
|
+
|
||
|
// Tests call directly into the Binder.
|
||
|
mBinderService = mService.getBinderService();
|
||
|
mInternalService = mService.getInternalService();
|
||
|
@@ -3261,4 +3287,44 @@ public class NotificationManagerServiceTest extends UiServiceTestCase {
|
||
|
mBinderService.areNotificationsEnabledForPackage(mContext.getPackageName(),
|
||
|
mUid + UserHandle.PER_USER_RANGE);
|
||
|
}
|
||
|
+
|
||
|
+ @Test
|
||
|
+ public void testStrongAuthTracker_isInLockDownMode() {
|
||
|
+ mStrongAuthTracker.setGetStrongAuthForUserReturnValue(
|
||
|
+ STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN);
|
||
|
+ mStrongAuthTracker.onStrongAuthRequiredChanged(mContext.getUserId());
|
||
|
+ assertTrue(mStrongAuthTracker.isInLockDownMode());
|
||
|
+ mStrongAuthTracker.setGetStrongAuthForUserReturnValue(0);
|
||
|
+ mStrongAuthTracker.onStrongAuthRequiredChanged(mContext.getUserId());
|
||
|
+ assertFalse(mStrongAuthTracker.isInLockDownMode());
|
||
|
+ }
|
||
|
+
|
||
|
+ @Test
|
||
|
+ public void testCancelAndPostNotificationsWhenEnterAndExitLockDownMode() {
|
||
|
+ // post 2 notifications from 2 packages
|
||
|
+ NotificationRecord pkgA = new NotificationRecord(mContext,
|
||
|
+ generateSbn("a", 1000, 9, 0), mTestNotificationChannel);
|
||
|
+ mService.addNotification(pkgA);
|
||
|
+ NotificationRecord pkgB = new NotificationRecord(mContext,
|
||
|
+ generateSbn("b", 1001, 9, 0), mTestNotificationChannel);
|
||
|
+ mService.addNotification(pkgB);
|
||
|
+
|
||
|
+ // when entering the lockdown mode, cancel the 2 notifications.
|
||
|
+ mStrongAuthTracker.setGetStrongAuthForUserReturnValue(
|
||
|
+ STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN);
|
||
|
+ mStrongAuthTracker.onStrongAuthRequiredChanged(mContext.getUserId());
|
||
|
+ assertTrue(mStrongAuthTracker.isInLockDownMode());
|
||
|
+
|
||
|
+ // the notifyRemovedLocked function is called twice due to REASON_LOCKDOWN.
|
||
|
+ ArgumentCaptor<Integer> captor = ArgumentCaptor.forClass(Integer.class);
|
||
|
+ verify(mListeners, times(2)).notifyRemovedLocked(any(), captor.capture(), any());
|
||
|
+ assertEquals(REASON_CANCEL_ALL, captor.getValue().intValue());
|
||
|
+
|
||
|
+ // exit lockdown mode.
|
||
|
+ mStrongAuthTracker.setGetStrongAuthForUserReturnValue(0);
|
||
|
+ mStrongAuthTracker.onStrongAuthRequiredChanged(mContext.getUserId());
|
||
|
+
|
||
|
+ // the notifyPostedLocked function is called twice.
|
||
|
+ verify(mListeners, times(2)).notifyPostedLocked(any(), any());
|
||
|
+ }
|
||
|
}
|