Loading services/core/java/com/android/server/RescueParty.java +44 −6 Original line number Diff line number Diff line Loading @@ -56,6 +56,7 @@ import java.io.File; import java.util.ArrayList; import java.util.Arrays; import java.util.HashMap; import java.util.HashSet; import java.util.Iterator; import java.util.List; import java.util.Map; Loading Loading @@ -100,6 +101,10 @@ public class RescueParty { private static final String PROP_VIRTUAL_DEVICE = "ro.hardware.virtual_device"; private static final String PROP_DEVICE_CONFIG_DISABLE_FLAG = "persist.device_config.configuration.disable_rescue_party"; private static final String PROP_DISABLE_FACTORY_RESET_FLAG = "persist.device_config.configuration.disable_rescue_party_factory_reset"; // The DeviceConfig namespace containing all RescueParty switches. private static final String NAMESPACE_CONFIGURATION = "configuration"; private static final int PERSISTENT_MASK = ApplicationInfo.FLAG_PERSISTENT | ApplicationInfo.FLAG_SYSTEM; Loading Loading @@ -215,6 +220,10 @@ public class RescueParty { if (SettingsToPropertiesMapper.isNativeFlagsResetPerformed()) { String[] resetNativeCategories = SettingsToPropertiesMapper.getResetNativeCategories(); for (int i = 0; i < resetNativeCategories.length; i++) { // Don't let RescueParty reset the namespace for RescueParty switches. if (NAMESPACE_CONFIGURATION.equals(resetNativeCategories[i])) { continue; } DeviceConfig.resetToDefaults(Settings.RESET_MODE_TRUSTED_DEFAULTS, resetNativeCategories[i]); } Loading @@ -225,8 +234,10 @@ public class RescueParty { * Get the next rescue level. This indicates the next level of mitigation that may be taken. */ private static int getNextRescueLevel() { int maxRescueLevel = SystemProperties.getBoolean(PROP_DISABLE_FACTORY_RESET_FLAG, false) ? LEVEL_RESET_SETTINGS_TRUSTED_DEFAULTS : LEVEL_FACTORY_RESET; return MathUtils.constrain(SystemProperties.getInt(PROP_RESCUE_LEVEL, LEVEL_NONE) + 1, LEVEL_NONE, LEVEL_FACTORY_RESET); LEVEL_NONE, maxRescueLevel); } /** Loading Loading @@ -349,12 +360,30 @@ public class RescueParty { private static void resetDeviceConfig(Context context, int resetMode, @Nullable String failedPackage) { if (!shouldPerformScopedResets() || failedPackage == null) { DeviceConfig.resetToDefaults(resetMode, /*namespace=*/ null); resetAllAffectedNamespaces(context, resetMode); } else { performScopedReset(context, resetMode, failedPackage); } } private static void resetAllAffectedNamespaces(Context context, int resetMode) { RescuePartyObserver rescuePartyObserver = RescuePartyObserver.getInstance(context); Set<String> allAffectedNamespaces = rescuePartyObserver.getAllAffectedNamespaceSet(); Slog.w(TAG, "Performing reset for all affected namespaces: " + Arrays.toString(allAffectedNamespaces.toArray())); Iterator<String> it = allAffectedNamespaces.iterator(); while (it.hasNext()) { String namespace = it.next(); // Don't let RescueParty reset the namespace for RescueParty switches. if (NAMESPACE_CONFIGURATION.equals(namespace)) { continue; } DeviceConfig.resetToDefaults(resetMode, namespace); } } private static boolean shouldPerformScopedResets() { int rescueLevel = MathUtils.constrain( SystemProperties.getInt(PROP_RESCUE_LEVEL, LEVEL_NONE), Loading @@ -367,16 +396,21 @@ public class RescueParty { RescuePartyObserver rescuePartyObserver = RescuePartyObserver.getInstance(context); Set<String> affectedNamespaces = rescuePartyObserver.getAffectedNamespaceSet( failedPackage); if (affectedNamespaces == null) { DeviceConfig.resetToDefaults(resetMode, /*namespace=*/ null); } else { // If we can't find namespaces affected for current package, // skip this round of reset. if (affectedNamespaces != null) { Slog.w(TAG, "Performing scoped reset for package: " + failedPackage + ", affected namespaces: " + Arrays.toString(affectedNamespaces.toArray())); Iterator<String> it = affectedNamespaces.iterator(); while (it.hasNext()) { DeviceConfig.resetToDefaults(resetMode, it.next()); String namespace = it.next(); // Don't let RescueParty reset the namespace for RescueParty switches. if (NAMESPACE_CONFIGURATION.equals(namespace)) { continue; } DeviceConfig.resetToDefaults(resetMode, namespace); } } } Loading Loading @@ -514,6 +548,10 @@ public class RescueParty { return mCallingPackageNamespaceSetMap.get(failedPackage); } private synchronized Set<String> getAllAffectedNamespaceSet() { return new HashSet<String>(mNamespaceCallingPackageSetMap.keySet()); } private synchronized Set<String> getCallingPackagesSet(String namespace) { return mNamespaceCallingPackageSetMap.get(namespace); } Loading services/tests/mockingservicestests/src/com/android/server/RescuePartyTest.java +41 −9 Original line number Diff line number Diff line Loading @@ -27,9 +27,11 @@ import static com.android.dx.mockito.inline.extended.ExtendedMockito.when; import static com.android.server.RescueParty.LEVEL_FACTORY_RESET; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.mockito.ArgumentMatchers.eq; import static org.mockito.ArgumentMatchers.isNull; import static org.mockito.Mockito.never; import static org.mockito.Mockito.times; import android.content.ContentResolver; Loading Loading @@ -79,8 +81,11 @@ public class RescuePartyTest { private static final String CALLING_PACKAGE2 = "com.package.name2"; private static final String NAMESPACE1 = "namespace1"; private static final String NAMESPACE2 = "namespace2"; private static final String NAMESPACE3 = "namespace3"; private static final String PROP_DEVICE_CONFIG_DISABLE_FLAG = "persist.device_config.configuration.disable_rescue_party"; private static final String PROP_DISABLE_FACTORY_RESET_FLAG = "persist.device_config.configuration.disable_rescue_party_factory_reset"; private MockitoSession mSession; private HashMap<String, String> mSystemSettingsMap; Loading Loading @@ -183,27 +188,38 @@ public class RescuePartyTest { @Test public void testBootLoopDetectionWithExecutionForAllRescueLevels() { RescueParty.onSettingsProviderPublished(mMockContext); verify(() -> Settings.Config.registerMonitorCallback(eq(mMockContentResolver), mMonitorCallbackCaptor.capture())); noteBoot(); verifySettingsResets(Settings.RESET_MODE_UNTRUSTED_DEFAULTS, /*resetNamespaces=*/ null); assertEquals(RescueParty.LEVEL_RESET_SETTINGS_UNTRUSTED_DEFAULTS, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); // Record DeviceConfig accesses RescuePartyObserver observer = RescuePartyObserver.getInstance(mMockContext); RemoteCallback monitorCallback = mMonitorCallbackCaptor.getValue(); monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE1, NAMESPACE1)); monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE1, NAMESPACE2)); final String[] expectedAllResetNamespaces = new String[]{NAMESPACE1, NAMESPACE2}; noteBoot(); verifySettingsResets(Settings.RESET_MODE_UNTRUSTED_CHANGES, /*resetNamespaces=*/ null); verifySettingsResets(Settings.RESET_MODE_UNTRUSTED_CHANGES, expectedAllResetNamespaces); assertEquals(RescueParty.LEVEL_RESET_SETTINGS_UNTRUSTED_CHANGES, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); noteBoot(); verifySettingsResets(Settings.RESET_MODE_TRUSTED_DEFAULTS, /*resetNamespaces=*/ null); verifySettingsResets(Settings.RESET_MODE_TRUSTED_DEFAULTS, expectedAllResetNamespaces); assertEquals(RescueParty.LEVEL_RESET_SETTINGS_TRUSTED_DEFAULTS, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); noteBoot(); verify(() -> RecoverySystem.rebootPromptAndWipeUserData(mMockContext, RescueParty.TAG)); assertEquals(LEVEL_FACTORY_RESET, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); } Loading @@ -230,7 +246,6 @@ public class RescuePartyTest { notePersistentAppCrash(); verify(() -> RecoverySystem.rebootPromptAndWipeUserData(mMockContext, RescueParty.TAG)); assertEquals(LEVEL_FACTORY_RESET, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); } Loading @@ -247,6 +262,7 @@ public class RescuePartyTest { monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE1, NAMESPACE1)); monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE1, NAMESPACE2)); monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE2, NAMESPACE2)); monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE2, NAMESPACE3)); // Fake DeviceConfig value changes monitorCallback.sendResult(getConfigNamespaceUpdateBundle(NAMESPACE1)); verify(mMockPackageWatchdog).startObservingHealth(observer, Loading @@ -255,10 +271,15 @@ public class RescuePartyTest { verify(mMockPackageWatchdog, times(2)).startObservingHealth(eq(observer), mPackageListCaptor.capture(), eq(RescueParty.DEFAULT_OBSERVING_DURATION_MS)); monitorCallback.sendResult(getConfigNamespaceUpdateBundle(NAMESPACE3)); verify(mMockPackageWatchdog).startObservingHealth(observer, Arrays.asList(CALLING_PACKAGE2), RescueParty.DEFAULT_OBSERVING_DURATION_MS); assertTrue(mPackageListCaptor.getValue().containsAll( Arrays.asList(CALLING_PACKAGE1, CALLING_PACKAGE2))); // Perform and verify scoped resets final String[] expectedResetNamespaces = new String[]{NAMESPACE1, NAMESPACE2}; final String[] expectedAllResetNamespaces = new String[]{NAMESPACE1, NAMESPACE2, NAMESPACE3}; observer.execute(new VersionedPackage( CALLING_PACKAGE1, 1), PackageWatchdog.FAILURE_REASON_APP_CRASH); verifySettingsResets(Settings.RESET_MODE_UNTRUSTED_DEFAULTS, expectedResetNamespaces); Loading @@ -273,13 +294,12 @@ public class RescuePartyTest { observer.execute(new VersionedPackage( CALLING_PACKAGE1, 1), PackageWatchdog.FAILURE_REASON_APP_NOT_RESPONDING); verifySettingsResets(Settings.RESET_MODE_TRUSTED_DEFAULTS, /*resetNamespaces=*/null); verifySettingsResets(Settings.RESET_MODE_TRUSTED_DEFAULTS, expectedAllResetNamespaces); assertEquals(RescueParty.LEVEL_RESET_SETTINGS_TRUSTED_DEFAULTS, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); observer.execute(new VersionedPackage( CALLING_PACKAGE1, 1), PackageWatchdog.FAILURE_REASON_APP_CRASH); verify(() -> RecoverySystem.rebootPromptAndWipeUserData(mMockContext, RescueParty.TAG)); assertTrue(RescueParty.isAttemptingFactoryReset()); } Loading @@ -288,7 +308,6 @@ public class RescuePartyTest { for (int i = 0; i < LEVEL_FACTORY_RESET; i++) { noteBoot(); } verify(() -> RecoverySystem.rebootPromptAndWipeUserData(mMockContext, RescueParty.TAG)); assertTrue(RescueParty.isAttemptingFactoryReset()); } Loading Loading @@ -337,11 +356,24 @@ public class RescuePartyTest { assertEquals(RescuePartyObserver.getInstance(mMockContext).execute(sFailingPackage, PackageWatchdog.FAILURE_REASON_APP_NOT_RESPONDING), false); // Restore the property value initalized in SetUp() // Restore the property value initialized in SetUp() SystemProperties.set(RescueParty.PROP_ENABLE_RESCUE, Boolean.toString(true)); SystemProperties.set(PROP_DEVICE_CONFIG_DISABLE_FLAG, Boolean.toString(false)); } @Test public void testDisablingFactoryResetByDeviceConfigFlag() { SystemProperties.set(PROP_DISABLE_FACTORY_RESET_FLAG, Boolean.toString(true)); for (int i = 0; i < LEVEL_FACTORY_RESET; i++) { noteBoot(); } assertFalse(RescueParty.isAttemptingFactoryReset()); // Restore the property value initialized in SetUp() SystemProperties.set(PROP_DISABLE_FACTORY_RESET_FLAG, ""); } @Test public void testHealthCheckLevels() { RescuePartyObserver observer = RescuePartyObserver.getInstance(mMockContext); Loading Loading @@ -437,7 +469,7 @@ public class RescuePartyTest { eq(resetMode), anyInt())); // Verify DeviceConfig resets if (resetNamespaces == null) { verify(() -> DeviceConfig.resetToDefaults(resetMode, /*namespace=*/ null)); verify(() -> DeviceConfig.resetToDefaults(anyInt(), anyString()), never()); } else { for (String namespace : resetNamespaces) { verify(() -> DeviceConfig.resetToDefaults(resetMode, namespace)); Loading Loading
services/core/java/com/android/server/RescueParty.java +44 −6 Original line number Diff line number Diff line Loading @@ -56,6 +56,7 @@ import java.io.File; import java.util.ArrayList; import java.util.Arrays; import java.util.HashMap; import java.util.HashSet; import java.util.Iterator; import java.util.List; import java.util.Map; Loading Loading @@ -100,6 +101,10 @@ public class RescueParty { private static final String PROP_VIRTUAL_DEVICE = "ro.hardware.virtual_device"; private static final String PROP_DEVICE_CONFIG_DISABLE_FLAG = "persist.device_config.configuration.disable_rescue_party"; private static final String PROP_DISABLE_FACTORY_RESET_FLAG = "persist.device_config.configuration.disable_rescue_party_factory_reset"; // The DeviceConfig namespace containing all RescueParty switches. private static final String NAMESPACE_CONFIGURATION = "configuration"; private static final int PERSISTENT_MASK = ApplicationInfo.FLAG_PERSISTENT | ApplicationInfo.FLAG_SYSTEM; Loading Loading @@ -215,6 +220,10 @@ public class RescueParty { if (SettingsToPropertiesMapper.isNativeFlagsResetPerformed()) { String[] resetNativeCategories = SettingsToPropertiesMapper.getResetNativeCategories(); for (int i = 0; i < resetNativeCategories.length; i++) { // Don't let RescueParty reset the namespace for RescueParty switches. if (NAMESPACE_CONFIGURATION.equals(resetNativeCategories[i])) { continue; } DeviceConfig.resetToDefaults(Settings.RESET_MODE_TRUSTED_DEFAULTS, resetNativeCategories[i]); } Loading @@ -225,8 +234,10 @@ public class RescueParty { * Get the next rescue level. This indicates the next level of mitigation that may be taken. */ private static int getNextRescueLevel() { int maxRescueLevel = SystemProperties.getBoolean(PROP_DISABLE_FACTORY_RESET_FLAG, false) ? LEVEL_RESET_SETTINGS_TRUSTED_DEFAULTS : LEVEL_FACTORY_RESET; return MathUtils.constrain(SystemProperties.getInt(PROP_RESCUE_LEVEL, LEVEL_NONE) + 1, LEVEL_NONE, LEVEL_FACTORY_RESET); LEVEL_NONE, maxRescueLevel); } /** Loading Loading @@ -349,12 +360,30 @@ public class RescueParty { private static void resetDeviceConfig(Context context, int resetMode, @Nullable String failedPackage) { if (!shouldPerformScopedResets() || failedPackage == null) { DeviceConfig.resetToDefaults(resetMode, /*namespace=*/ null); resetAllAffectedNamespaces(context, resetMode); } else { performScopedReset(context, resetMode, failedPackage); } } private static void resetAllAffectedNamespaces(Context context, int resetMode) { RescuePartyObserver rescuePartyObserver = RescuePartyObserver.getInstance(context); Set<String> allAffectedNamespaces = rescuePartyObserver.getAllAffectedNamespaceSet(); Slog.w(TAG, "Performing reset for all affected namespaces: " + Arrays.toString(allAffectedNamespaces.toArray())); Iterator<String> it = allAffectedNamespaces.iterator(); while (it.hasNext()) { String namespace = it.next(); // Don't let RescueParty reset the namespace for RescueParty switches. if (NAMESPACE_CONFIGURATION.equals(namespace)) { continue; } DeviceConfig.resetToDefaults(resetMode, namespace); } } private static boolean shouldPerformScopedResets() { int rescueLevel = MathUtils.constrain( SystemProperties.getInt(PROP_RESCUE_LEVEL, LEVEL_NONE), Loading @@ -367,16 +396,21 @@ public class RescueParty { RescuePartyObserver rescuePartyObserver = RescuePartyObserver.getInstance(context); Set<String> affectedNamespaces = rescuePartyObserver.getAffectedNamespaceSet( failedPackage); if (affectedNamespaces == null) { DeviceConfig.resetToDefaults(resetMode, /*namespace=*/ null); } else { // If we can't find namespaces affected for current package, // skip this round of reset. if (affectedNamespaces != null) { Slog.w(TAG, "Performing scoped reset for package: " + failedPackage + ", affected namespaces: " + Arrays.toString(affectedNamespaces.toArray())); Iterator<String> it = affectedNamespaces.iterator(); while (it.hasNext()) { DeviceConfig.resetToDefaults(resetMode, it.next()); String namespace = it.next(); // Don't let RescueParty reset the namespace for RescueParty switches. if (NAMESPACE_CONFIGURATION.equals(namespace)) { continue; } DeviceConfig.resetToDefaults(resetMode, namespace); } } } Loading Loading @@ -514,6 +548,10 @@ public class RescueParty { return mCallingPackageNamespaceSetMap.get(failedPackage); } private synchronized Set<String> getAllAffectedNamespaceSet() { return new HashSet<String>(mNamespaceCallingPackageSetMap.keySet()); } private synchronized Set<String> getCallingPackagesSet(String namespace) { return mNamespaceCallingPackageSetMap.get(namespace); } Loading
services/tests/mockingservicestests/src/com/android/server/RescuePartyTest.java +41 −9 Original line number Diff line number Diff line Loading @@ -27,9 +27,11 @@ import static com.android.dx.mockito.inline.extended.ExtendedMockito.when; import static com.android.server.RescueParty.LEVEL_FACTORY_RESET; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.mockito.ArgumentMatchers.eq; import static org.mockito.ArgumentMatchers.isNull; import static org.mockito.Mockito.never; import static org.mockito.Mockito.times; import android.content.ContentResolver; Loading Loading @@ -79,8 +81,11 @@ public class RescuePartyTest { private static final String CALLING_PACKAGE2 = "com.package.name2"; private static final String NAMESPACE1 = "namespace1"; private static final String NAMESPACE2 = "namespace2"; private static final String NAMESPACE3 = "namespace3"; private static final String PROP_DEVICE_CONFIG_DISABLE_FLAG = "persist.device_config.configuration.disable_rescue_party"; private static final String PROP_DISABLE_FACTORY_RESET_FLAG = "persist.device_config.configuration.disable_rescue_party_factory_reset"; private MockitoSession mSession; private HashMap<String, String> mSystemSettingsMap; Loading Loading @@ -183,27 +188,38 @@ public class RescuePartyTest { @Test public void testBootLoopDetectionWithExecutionForAllRescueLevels() { RescueParty.onSettingsProviderPublished(mMockContext); verify(() -> Settings.Config.registerMonitorCallback(eq(mMockContentResolver), mMonitorCallbackCaptor.capture())); noteBoot(); verifySettingsResets(Settings.RESET_MODE_UNTRUSTED_DEFAULTS, /*resetNamespaces=*/ null); assertEquals(RescueParty.LEVEL_RESET_SETTINGS_UNTRUSTED_DEFAULTS, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); // Record DeviceConfig accesses RescuePartyObserver observer = RescuePartyObserver.getInstance(mMockContext); RemoteCallback monitorCallback = mMonitorCallbackCaptor.getValue(); monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE1, NAMESPACE1)); monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE1, NAMESPACE2)); final String[] expectedAllResetNamespaces = new String[]{NAMESPACE1, NAMESPACE2}; noteBoot(); verifySettingsResets(Settings.RESET_MODE_UNTRUSTED_CHANGES, /*resetNamespaces=*/ null); verifySettingsResets(Settings.RESET_MODE_UNTRUSTED_CHANGES, expectedAllResetNamespaces); assertEquals(RescueParty.LEVEL_RESET_SETTINGS_UNTRUSTED_CHANGES, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); noteBoot(); verifySettingsResets(Settings.RESET_MODE_TRUSTED_DEFAULTS, /*resetNamespaces=*/ null); verifySettingsResets(Settings.RESET_MODE_TRUSTED_DEFAULTS, expectedAllResetNamespaces); assertEquals(RescueParty.LEVEL_RESET_SETTINGS_TRUSTED_DEFAULTS, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); noteBoot(); verify(() -> RecoverySystem.rebootPromptAndWipeUserData(mMockContext, RescueParty.TAG)); assertEquals(LEVEL_FACTORY_RESET, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); } Loading @@ -230,7 +246,6 @@ public class RescuePartyTest { notePersistentAppCrash(); verify(() -> RecoverySystem.rebootPromptAndWipeUserData(mMockContext, RescueParty.TAG)); assertEquals(LEVEL_FACTORY_RESET, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); } Loading @@ -247,6 +262,7 @@ public class RescuePartyTest { monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE1, NAMESPACE1)); monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE1, NAMESPACE2)); monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE2, NAMESPACE2)); monitorCallback.sendResult(getConfigAccessBundle(CALLING_PACKAGE2, NAMESPACE3)); // Fake DeviceConfig value changes monitorCallback.sendResult(getConfigNamespaceUpdateBundle(NAMESPACE1)); verify(mMockPackageWatchdog).startObservingHealth(observer, Loading @@ -255,10 +271,15 @@ public class RescuePartyTest { verify(mMockPackageWatchdog, times(2)).startObservingHealth(eq(observer), mPackageListCaptor.capture(), eq(RescueParty.DEFAULT_OBSERVING_DURATION_MS)); monitorCallback.sendResult(getConfigNamespaceUpdateBundle(NAMESPACE3)); verify(mMockPackageWatchdog).startObservingHealth(observer, Arrays.asList(CALLING_PACKAGE2), RescueParty.DEFAULT_OBSERVING_DURATION_MS); assertTrue(mPackageListCaptor.getValue().containsAll( Arrays.asList(CALLING_PACKAGE1, CALLING_PACKAGE2))); // Perform and verify scoped resets final String[] expectedResetNamespaces = new String[]{NAMESPACE1, NAMESPACE2}; final String[] expectedAllResetNamespaces = new String[]{NAMESPACE1, NAMESPACE2, NAMESPACE3}; observer.execute(new VersionedPackage( CALLING_PACKAGE1, 1), PackageWatchdog.FAILURE_REASON_APP_CRASH); verifySettingsResets(Settings.RESET_MODE_UNTRUSTED_DEFAULTS, expectedResetNamespaces); Loading @@ -273,13 +294,12 @@ public class RescuePartyTest { observer.execute(new VersionedPackage( CALLING_PACKAGE1, 1), PackageWatchdog.FAILURE_REASON_APP_NOT_RESPONDING); verifySettingsResets(Settings.RESET_MODE_TRUSTED_DEFAULTS, /*resetNamespaces=*/null); verifySettingsResets(Settings.RESET_MODE_TRUSTED_DEFAULTS, expectedAllResetNamespaces); assertEquals(RescueParty.LEVEL_RESET_SETTINGS_TRUSTED_DEFAULTS, SystemProperties.getInt(RescueParty.PROP_RESCUE_LEVEL, RescueParty.LEVEL_NONE)); observer.execute(new VersionedPackage( CALLING_PACKAGE1, 1), PackageWatchdog.FAILURE_REASON_APP_CRASH); verify(() -> RecoverySystem.rebootPromptAndWipeUserData(mMockContext, RescueParty.TAG)); assertTrue(RescueParty.isAttemptingFactoryReset()); } Loading @@ -288,7 +308,6 @@ public class RescuePartyTest { for (int i = 0; i < LEVEL_FACTORY_RESET; i++) { noteBoot(); } verify(() -> RecoverySystem.rebootPromptAndWipeUserData(mMockContext, RescueParty.TAG)); assertTrue(RescueParty.isAttemptingFactoryReset()); } Loading Loading @@ -337,11 +356,24 @@ public class RescuePartyTest { assertEquals(RescuePartyObserver.getInstance(mMockContext).execute(sFailingPackage, PackageWatchdog.FAILURE_REASON_APP_NOT_RESPONDING), false); // Restore the property value initalized in SetUp() // Restore the property value initialized in SetUp() SystemProperties.set(RescueParty.PROP_ENABLE_RESCUE, Boolean.toString(true)); SystemProperties.set(PROP_DEVICE_CONFIG_DISABLE_FLAG, Boolean.toString(false)); } @Test public void testDisablingFactoryResetByDeviceConfigFlag() { SystemProperties.set(PROP_DISABLE_FACTORY_RESET_FLAG, Boolean.toString(true)); for (int i = 0; i < LEVEL_FACTORY_RESET; i++) { noteBoot(); } assertFalse(RescueParty.isAttemptingFactoryReset()); // Restore the property value initialized in SetUp() SystemProperties.set(PROP_DISABLE_FACTORY_RESET_FLAG, ""); } @Test public void testHealthCheckLevels() { RescuePartyObserver observer = RescuePartyObserver.getInstance(mMockContext); Loading Loading @@ -437,7 +469,7 @@ public class RescuePartyTest { eq(resetMode), anyInt())); // Verify DeviceConfig resets if (resetNamespaces == null) { verify(() -> DeviceConfig.resetToDefaults(resetMode, /*namespace=*/ null)); verify(() -> DeviceConfig.resetToDefaults(anyInt(), anyString()), never()); } else { for (String namespace : resetNamespaces) { verify(() -> DeviceConfig.resetToDefaults(resetMode, namespace)); Loading