diff options
6 files changed, 357 insertions, 120 deletions
diff --git a/api/system-current.txt b/api/system-current.txt index 588686a38489..75b1f921d3ae 100755 --- a/api/system-current.txt +++ b/api/system-current.txt @@ -126,6 +126,7 @@ package android { field @Deprecated public static final String MODIFY_NETWORK_ACCOUNTING = "android.permission.MODIFY_NETWORK_ACCOUNTING"; field public static final String MODIFY_PARENTAL_CONTROLS = "android.permission.MODIFY_PARENTAL_CONTROLS"; field public static final String MODIFY_QUIET_MODE = "android.permission.MODIFY_QUIET_MODE"; + field public static final String MODIFY_SETTINGS_OVERRIDEABLE_BY_RESTORE = "android.permission.MODIFY_SETTINGS_OVERRIDEABLE_BY_RESTORE"; field public static final String MOVE_PACKAGE = "android.permission.MOVE_PACKAGE"; field public static final String NETWORK_AIRPLANE_MODE = "android.permission.NETWORK_AIRPLANE_MODE"; field public static final String NETWORK_CARRIER_PROVISIONING = "android.permission.NETWORK_CARRIER_PROVISIONING"; @@ -7935,6 +7936,10 @@ package android.provider { field public static final int VOLUME_HUSH_VIBRATE = 1; // 0x1 } + public static final class Settings.System extends android.provider.Settings.NameValueTable { + method @RequiresPermission(android.Manifest.permission.MODIFY_SETTINGS_OVERRIDEABLE_BY_RESTORE) public static boolean putString(@NonNull android.content.ContentResolver, @NonNull String, @Nullable String, boolean); + } + public static interface Telephony.CarrierColumns extends android.provider.BaseColumns { field @NonNull public static final android.net.Uri CONTENT_URI; field public static final String EXPIRATION_TIME = "expiration_time"; diff --git a/core/java/android/provider/Settings.java b/core/java/android/provider/Settings.java index 9ee4cc30949d..bc1eb987ba40 100644 --- a/core/java/android/provider/Settings.java +++ b/core/java/android/provider/Settings.java @@ -95,6 +95,7 @@ import java.util.Set; * The Settings provider contains global system-level device preferences. */ public final class Settings { + private static final boolean DEFAULT_OVERRIDEABLE_BY_RESTORE = false; // Intent actions for Settings @@ -2108,6 +2109,11 @@ public final class Settings { */ public static final String CALL_METHOD_FLAGS_KEY = "_flags"; + /** + * @hide - String argument extra to the fast-path call()-based requests + */ + public static final String CALL_METHOD_OVERRIDEABLE_BY_RESTORE_KEY = "_overrideable_by_restore"; + /** @hide - Private call() method to write to 'system' table */ public static final String CALL_METHOD_PUT_SYSTEM = "PUT_system"; @@ -2476,7 +2482,8 @@ public final class Settings { } public boolean putStringForUser(ContentResolver cr, String name, String value, - String tag, boolean makeDefault, final int userHandle) { + String tag, boolean makeDefault, final int userHandle, + boolean overrideableByRestore) { try { Bundle arg = new Bundle(); arg.putString(Settings.NameValueTable.VALUE, value); @@ -2487,6 +2494,9 @@ public final class Settings { if (makeDefault) { arg.putBoolean(CALL_METHOD_MAKE_DEFAULT_KEY, true); } + if (overrideableByRestore) { + arg.putBoolean(CALL_METHOD_OVERRIDEABLE_BY_RESTORE_KEY, true); + } IContentProvider cp = mProviderHolder.getProvider(cr); cp.call(cr.getPackageName(), cr.getFeatureId(), mProviderHolder.mUri.getAuthority(), mCallSetCommand, name, arg); @@ -3037,10 +3047,36 @@ public final class Settings { return putStringForUser(resolver, name, value, resolver.getUserId()); } + /** + * Store a name/value pair into the database. Values written by this method will be + * overridden if a restore happens in the future. + * + * @param resolver to access the database with + * @param name to store + * @param value to associate with the name + * + * @return true if the value was set, false on database errors + * + * @hide + */ + @RequiresPermission(Manifest.permission.MODIFY_SETTINGS_OVERRIDEABLE_BY_RESTORE) + @SystemApi + public static boolean putString(@NonNull ContentResolver resolver, + @NonNull String name, @Nullable String value, boolean overrideableByRestore) { + return putStringForUser(resolver, name, value, resolver.getUserId(), + overrideableByRestore); + } + /** @hide */ @UnsupportedAppUsage public static boolean putStringForUser(ContentResolver resolver, String name, String value, int userHandle) { + return putStringForUser(resolver, name, value, userHandle, + DEFAULT_OVERRIDEABLE_BY_RESTORE); + } + + private static boolean putStringForUser(ContentResolver resolver, String name, String value, + int userHandle, boolean overrideableByRestore) { if (MOVED_TO_SECURE.contains(name)) { Log.w(TAG, "Setting " + name + " has moved from android.provider.Settings.System" + " to android.provider.Settings.Secure, value is unchanged."); @@ -3051,7 +3087,8 @@ public final class Settings { + " to android.provider.Settings.Global, value is unchanged."); return false; } - return sNameValueCache.putStringForUser(resolver, name, value, null, false, userHandle); + return sNameValueCache.putStringForUser(resolver, name, value, null, false, userHandle, + overrideableByRestore); } /** @@ -3375,7 +3412,7 @@ public final class Settings { // need to store the adjusted configuration as the initial settings. Settings.System.putStringForUser( cr, SYSTEM_LOCALES, outConfig.getLocales().toLanguageTags(), - userHandle); + userHandle, DEFAULT_OVERRIDEABLE_BY_RESTORE); } } } @@ -3408,7 +3445,8 @@ public final class Settings { int userHandle) { return Settings.System.putFloatForUser(cr, FONT_SCALE, config.fontScale, userHandle) && Settings.System.putStringForUser( - cr, SYSTEM_LOCALES, config.getLocales().toLanguageTags(), userHandle); + cr, SYSTEM_LOCALES, config.getLocales().toLanguageTags(), userHandle, + DEFAULT_OVERRIDEABLE_BY_RESTORE); } /** @hide */ @@ -5211,6 +5249,24 @@ public final class Settings { } /** + * Store a name/value pair into the database. Values written by this method will be + * overridden if a restore happens in the future. + * + * @param resolver to access the database with + * @param name to store + * @param value to associate with the name + * @return true if the value was set, false on database errors + * + * @hide + */ + @RequiresPermission(Manifest.permission.MODIFY_SETTINGS_OVERRIDEABLE_BY_RESTORE) + public static boolean putString(ContentResolver resolver, String name, + String value, boolean overrideableByRestore) { + return putStringForUser(resolver, name, value, /* tag */ null, /* makeDefault */ false, + resolver.getUserId(), overrideableByRestore); + } + + /** * Store a name/value pair into the database. * @param resolver to access the database with * @param name to store @@ -5225,22 +5281,23 @@ public final class Settings { @UnsupportedAppUsage public static boolean putStringForUser(ContentResolver resolver, String name, String value, int userHandle) { - return putStringForUser(resolver, name, value, null, false, userHandle); + return putStringForUser(resolver, name, value, null, false, userHandle, + DEFAULT_OVERRIDEABLE_BY_RESTORE); } /** @hide */ @UnsupportedAppUsage public static boolean putStringForUser(@NonNull ContentResolver resolver, @NonNull String name, @Nullable String value, @Nullable String tag, - boolean makeDefault, @UserIdInt int userHandle) { + boolean makeDefault, @UserIdInt int userHandle, boolean overrideableByRestore) { if (MOVED_TO_GLOBAL.contains(name)) { Log.w(TAG, "Setting " + name + " has moved from android.provider.Settings.Secure" + " to android.provider.Settings.Global"); return Global.putStringForUser(resolver, name, value, - tag, makeDefault, userHandle); + tag, makeDefault, userHandle, DEFAULT_OVERRIDEABLE_BY_RESTORE); } return sNameValueCache.putStringForUser(resolver, name, value, tag, - makeDefault, userHandle); + makeDefault, userHandle, overrideableByRestore); } /** @@ -5289,7 +5346,7 @@ public final class Settings { @NonNull String name, @Nullable String value, @Nullable String tag, boolean makeDefault) { return putStringForUser(resolver, name, value, tag, makeDefault, - resolver.getUserId()); + resolver.getUserId(), DEFAULT_OVERRIDEABLE_BY_RESTORE); } /** @@ -12972,7 +13029,29 @@ public final class Settings { */ public static boolean putString(ContentResolver resolver, String name, String value) { - return putStringForUser(resolver, name, value, null, false, resolver.getUserId()); + return putStringForUser(resolver, name, value, null, false, resolver.getUserId(), + DEFAULT_OVERRIDEABLE_BY_RESTORE); + } + + /** + * Store a name/value pair into the database. + * + * @param resolver to access the database with + * @param name to store + * @param value to associate with the name + * @param tag to associated with the setting. + * @param makeDefault whether to make the value the default one. + * @param overrideableByRestore whether restore can override this value + * @return true if the value was set, false on database errors + * + * @hide + */ + @RequiresPermission(Manifest.permission.MODIFY_SETTINGS_OVERRIDEABLE_BY_RESTORE) + public static boolean putString(@NonNull ContentResolver resolver, + @NonNull String name, @Nullable String value, @Nullable String tag, + boolean makeDefault, boolean overrideableByRestore) { + return putStringForUser(resolver, name, value, tag, makeDefault, + resolver.getUserId(), overrideableByRestore); } /** @@ -13021,7 +13100,7 @@ public final class Settings { @NonNull String name, @Nullable String value, @Nullable String tag, boolean makeDefault) { return putStringForUser(resolver, name, value, tag, makeDefault, - resolver.getUserId()); + resolver.getUserId(), DEFAULT_OVERRIDEABLE_BY_RESTORE); } /** @@ -13083,13 +13162,14 @@ public final class Settings { @UnsupportedAppUsage public static boolean putStringForUser(ContentResolver resolver, String name, String value, int userHandle) { - return putStringForUser(resolver, name, value, null, false, userHandle); + return putStringForUser(resolver, name, value, null, false, userHandle, + DEFAULT_OVERRIDEABLE_BY_RESTORE); } /** @hide */ public static boolean putStringForUser(@NonNull ContentResolver resolver, @NonNull String name, @Nullable String value, @Nullable String tag, - boolean makeDefault, @UserIdInt int userHandle) { + boolean makeDefault, @UserIdInt int userHandle, boolean overrideableByRestore) { if (LOCAL_LOGV) { Log.v(TAG, "Global.putString(name=" + name + ", value=" + value + " for " + userHandle); @@ -13099,10 +13179,10 @@ public final class Settings { Log.w(TAG, "Setting " + name + " has moved from android.provider.Settings.Global" + " to android.provider.Settings.Secure, value is unchanged."); return Secure.putStringForUser(resolver, name, value, tag, - makeDefault, userHandle); + makeDefault, userHandle, overrideableByRestore); } return sNameValueCache.putStringForUser(resolver, name, value, tag, - makeDefault, userHandle); + makeDefault, userHandle, overrideableByRestore); } /** @@ -13969,7 +14049,8 @@ public final class Settings { static boolean putString(@NonNull ContentResolver resolver, @NonNull String namespace, @NonNull String name, @Nullable String value, boolean makeDefault) { return sNameValueCache.putStringForUser(resolver, createCompositeName(namespace, name), - value, null, makeDefault, resolver.getUserId()); + value, null, makeDefault, resolver.getUserId(), + DEFAULT_OVERRIDEABLE_BY_RESTORE); } /** diff --git a/core/res/AndroidManifest.xml b/core/res/AndroidManifest.xml index a808ed8fcc81..f4ee50eeabe3 100644 --- a/core/res/AndroidManifest.xml +++ b/core/res/AndroidManifest.xml @@ -3967,6 +3967,13 @@ <permission android:name="android.permission.BACKUP" android:protectionLevel="signature|privileged" /> + <!-- @SystemApi Allows an application to make modifications to device settings such that these + modifications will be overridden by settings restore.. + <p>Not for use by third-party applications. + @hide --> + <permission android:name="android.permission.MODIFY_SETTINGS_OVERRIDEABLE_BY_RESTORE" + android:protectionLevel="signature|setup" /> + <!-- @SystemApi Allows application to manage {@link android.security.keystore.recovery.RecoveryController}. <p>Not for use by third-party applications. diff --git a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java index 1e0c1d877f67..3bcc4aa947fa 100644 --- a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java +++ b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java @@ -366,7 +366,9 @@ public class SettingsProvider extends ContentProvider { String value = getSettingValue(args); String tag = getSettingTag(args); final boolean makeDefault = getSettingMakeDefault(args); - insertGlobalSetting(name, value, tag, makeDefault, requestingUserId, false); + final boolean overrideableByRestore = getSettingOverrideableByRestore(args); + insertGlobalSetting(name, value, tag, makeDefault, requestingUserId, false, + overrideableByRestore); break; } @@ -374,13 +376,16 @@ public class SettingsProvider extends ContentProvider { String value = getSettingValue(args); String tag = getSettingTag(args); final boolean makeDefault = getSettingMakeDefault(args); - insertSecureSetting(name, value, tag, makeDefault, requestingUserId, false); + final boolean overrideableByRestore = getSettingOverrideableByRestore(args); + insertSecureSetting(name, value, tag, makeDefault, requestingUserId, false, + overrideableByRestore); break; } case Settings.CALL_METHOD_PUT_SYSTEM: { String value = getSettingValue(args); - insertSystemSetting(name, value, requestingUserId); + boolean overrideableByRestore = getSettingOverrideableByRestore(args); + insertSystemSetting(name, value, requestingUserId, overrideableByRestore); break; } @@ -575,20 +580,23 @@ public class SettingsProvider extends ContentProvider { switch (table) { case TABLE_GLOBAL: { if (insertGlobalSetting(name, value, null, false, - UserHandle.getCallingUserId(), false)) { + UserHandle.getCallingUserId(), false, + /* overrideableByRestore */ false)) { return Uri.withAppendedPath(Settings.Global.CONTENT_URI, name); } } break; case TABLE_SECURE: { if (insertSecureSetting(name, value, null, false, - UserHandle.getCallingUserId(), false)) { + UserHandle.getCallingUserId(), false, + /* overrideableByRestore */ false)) { return Uri.withAppendedPath(Settings.Secure.CONTENT_URI, name); } } break; case TABLE_SYSTEM: { - if (insertSystemSetting(name, value, UserHandle.getCallingUserId())) { + if (insertSystemSetting(name, value, UserHandle.getCallingUserId(), + /* overridableByRestore */ false)) { return Uri.withAppendedPath(Settings.System.CONTENT_URI, name); } } break; @@ -1074,7 +1082,8 @@ public class SettingsProvider extends ContentProvider { case MUTATION_OPERATION_INSERT: { return mSettingsRegistry.insertSettingLocked(SETTINGS_TYPE_CONFIG, UserHandle.USER_SYSTEM, name, value, null, makeDefault, true, - resolveCallingPackage(), false, null); + resolveCallingPackage(), false, null, + /* overrideableByRestore */ false); } case MUTATION_OPERATION_DELETE: { @@ -1178,14 +1187,15 @@ public class SettingsProvider extends ContentProvider { } private boolean insertGlobalSetting(String name, String value, String tag, - boolean makeDefault, int requestingUserId, boolean forceNotify) { + boolean makeDefault, int requestingUserId, boolean forceNotify, + boolean overrideableByRestore) { if (DEBUG) { Slog.v(LOG_TAG, "insertGlobalSetting(" + name + ", " + value + ", " + ", " + tag + ", " + makeDefault + ", " + requestingUserId + ", " + forceNotify + ")"); } return mutateGlobalSetting(name, value, tag, makeDefault, requestingUserId, - MUTATION_OPERATION_INSERT, forceNotify, 0); + MUTATION_OPERATION_INSERT, forceNotify, 0, overrideableByRestore); } private boolean deleteGlobalSetting(String name, int requestingUserId, boolean forceNotify) { @@ -1220,6 +1230,15 @@ public class SettingsProvider extends ContentProvider { private boolean mutateGlobalSetting(String name, String value, String tag, boolean makeDefault, int requestingUserId, int operation, boolean forceNotify, int mode) { + // overrideableByRestore = false as by default settings values shouldn't be overrideable by + // restore. + return mutateGlobalSetting(name, value, tag, makeDefault, requestingUserId, operation, + forceNotify, mode, /* overrideableByRestore */ false); + } + + private boolean mutateGlobalSetting(String name, String value, String tag, + boolean makeDefault, int requestingUserId, int operation, boolean forceNotify, + int mode, boolean overrideableByRestore) { // Make sure the caller can change the settings - treated as secure. enforceWritePermission(Manifest.permission.WRITE_SECURE_SETTINGS); @@ -1238,7 +1257,8 @@ public class SettingsProvider extends ContentProvider { case MUTATION_OPERATION_INSERT: { return mSettingsRegistry.insertSettingLocked(SETTINGS_TYPE_GLOBAL, UserHandle.USER_SYSTEM, name, value, tag, makeDefault, - getCallingPackage(), forceNotify, CRITICAL_GLOBAL_SETTINGS); + getCallingPackage(), forceNotify, + CRITICAL_GLOBAL_SETTINGS, overrideableByRestore); } case MUTATION_OPERATION_DELETE: { @@ -1474,7 +1494,7 @@ public class SettingsProvider extends ContentProvider { ) { @Override public boolean update(String value, boolean setDefault, String packageName, - String tag, boolean forceNonSystemPackage) { + String tag, boolean forceNonSystemPackage, boolean overrideableByRestore) { Slog.wtf(LOG_TAG, "update shouldn't be called on this instance."); return false; } @@ -1483,14 +1503,15 @@ public class SettingsProvider extends ContentProvider { } private boolean insertSecureSetting(String name, String value, String tag, - boolean makeDefault, int requestingUserId, boolean forceNotify) { + boolean makeDefault, int requestingUserId, boolean forceNotify, + boolean overrideableByRestore) { if (DEBUG) { Slog.v(LOG_TAG, "insertSecureSetting(" + name + ", " + value + ", " + ", " + tag + ", " + makeDefault + ", " + requestingUserId + ", " + forceNotify + ")"); } return mutateSecureSetting(name, value, tag, makeDefault, requestingUserId, - MUTATION_OPERATION_INSERT, forceNotify, 0); + MUTATION_OPERATION_INSERT, forceNotify, 0, overrideableByRestore); } private boolean deleteSecureSetting(String name, int requestingUserId, boolean forceNotify) { @@ -1528,6 +1549,15 @@ public class SettingsProvider extends ContentProvider { private boolean mutateSecureSetting(String name, String value, String tag, boolean makeDefault, int requestingUserId, int operation, boolean forceNotify, int mode) { + // overrideableByRestore = false as by default settings values shouldn't be overrideable by + // restore. + return mutateSecureSetting(name, value, tag, makeDefault, requestingUserId, operation, + forceNotify, mode, /* overrideableByRestore */ false); + } + + private boolean mutateSecureSetting(String name, String value, String tag, + boolean makeDefault, int requestingUserId, int operation, boolean forceNotify, + int mode, boolean overrideableByRestore) { // Make sure the caller can change the settings. enforceWritePermission(Manifest.permission.WRITE_SECURE_SETTINGS); @@ -1560,7 +1590,8 @@ public class SettingsProvider extends ContentProvider { case MUTATION_OPERATION_INSERT: { return mSettingsRegistry.insertSettingLocked(SETTINGS_TYPE_SECURE, owningUserId, name, value, tag, makeDefault, - getCallingPackage(), forceNotify, CRITICAL_SECURE_SETTINGS); + getCallingPackage(), forceNotify, CRITICAL_SECURE_SETTINGS, + overrideableByRestore); } case MUTATION_OPERATION_DELETE: { @@ -1636,13 +1667,15 @@ public class SettingsProvider extends ContentProvider { } } - private boolean insertSystemSetting(String name, String value, int requestingUserId) { + private boolean insertSystemSetting(String name, String value, int requestingUserId, + boolean overrideableByRestore) { if (DEBUG) { Slog.v(LOG_TAG, "insertSystemSetting(" + name + ", " + value + ", " + requestingUserId + ")"); } - return mutateSystemSetting(name, value, requestingUserId, MUTATION_OPERATION_INSERT); + return mutateSystemSetting(name, value, requestingUserId, MUTATION_OPERATION_INSERT, + overrideableByRestore); } private boolean deleteSystemSetting(String name, int requestingUserId) { @@ -1662,8 +1695,15 @@ public class SettingsProvider extends ContentProvider { return mutateSystemSetting(name, value, requestingUserId, MUTATION_OPERATION_UPDATE); } - private boolean mutateSystemSetting(String name, String value, int runAsUserId, - int operation) { + private boolean mutateSystemSetting(String name, String value, int runAsUserId, int operation) { + // overrideableByRestore = false as by default settings values shouldn't be overrideable by + // restore. + return mutateSystemSetting(name, value, runAsUserId, operation, + /* overrideableByRestore */ false); + } + + private boolean mutateSystemSetting(String name, String value, int runAsUserId, int operation, + boolean overrideableByRestore) { if (!hasWriteSecureSettingsPermission()) { // If the caller doesn't hold WRITE_SECURE_SETTINGS, we verify whether this // operation is allowed for the calling package through appops. @@ -1713,7 +1753,7 @@ public class SettingsProvider extends ContentProvider { validateSystemSettingValue(name, value); return mSettingsRegistry.insertSettingLocked(SETTINGS_TYPE_SYSTEM, owningUserId, name, value, null, false, getCallingPackage(), - false, null); + false, null, overrideableByRestore); } case MUTATION_OPERATION_DELETE: { @@ -2050,7 +2090,8 @@ public class SettingsProvider extends ContentProvider { } return mSettingsRegistry.insertSettingLocked(SETTINGS_TYPE_SECURE, owningUserId, Settings.Secure.LOCATION_PROVIDERS_ALLOWED, newProviders, tag, - makeDefault, getCallingPackage(), forceNotify, CRITICAL_SECURE_SETTINGS); + makeDefault, getCallingPackage(), forceNotify, CRITICAL_SECURE_SETTINGS, + /* overrideableByRestore */ false); } private static void warnOrThrowForUndesiredSecureSettingsMutationForTargetSdk( @@ -2144,6 +2185,10 @@ public class SettingsProvider extends ContentProvider { return (args != null) && args.getBoolean(Settings.CALL_METHOD_MAKE_DEFAULT_KEY); } + private static boolean getSettingOverrideableByRestore(Bundle args) { + return (args != null) && args.getBoolean(Settings.CALL_METHOD_OVERRIDEABLE_BY_RESTORE_KEY); + } + private static int getResetModeEnforcingPermission(Bundle args) { final int mode = (args != null) ? args.getInt(Settings.CALL_METHOD_RESET_MODE_KEY) : 0; switch (mode) { @@ -2641,21 +2686,21 @@ public class SettingsProvider extends ContentProvider { public boolean insertSettingLocked(int type, int userId, String name, String value, String tag, boolean makeDefault, String packageName, boolean forceNotify, - Set<String> criticalSettings) { + Set<String> criticalSettings, boolean overrideableByRestore) { return insertSettingLocked(type, userId, name, value, tag, makeDefault, false, - packageName, forceNotify, criticalSettings); + packageName, forceNotify, criticalSettings, overrideableByRestore); } public boolean insertSettingLocked(int type, int userId, String name, String value, String tag, boolean makeDefault, boolean forceNonSystemPackage, String packageName, - boolean forceNotify, Set<String> criticalSettings) { + boolean forceNotify, Set<String> criticalSettings, boolean overrideableByRestore) { final int key = makeKey(type, userId); boolean success = false; SettingsState settingsState = peekSettingsStateLocked(key); if (settingsState != null) { success = settingsState.insertSettingLocked(name, value, - tag, makeDefault, forceNonSystemPackage, packageName); + tag, makeDefault, forceNonSystemPackage, packageName, overrideableByRestore); } if (success && criticalSettings != null && criticalSettings.contains(name)) { @@ -3390,6 +3435,10 @@ public class SettingsProvider extends ContentProvider { * for this user from the old to the new version. When you add a new * upgrade step you *must* update SETTINGS_VERSION. * + * All settings modifications should be made through + * {@link SettingsState#insertSettingOverrideableByRestoreLocked(String, String, String, + * boolean, String)} so that restore can override those values if needed. + * * This is an example of moving a setting from secure to global. * * // v119: Example settings changes. @@ -3435,7 +3484,8 @@ public class SettingsProvider extends ContentProvider { // v120: Add double tap to wake setting. if (currentVersion == 119) { SettingsState secureSettings = getSecureSettingsLocked(userId); - secureSettings.insertSettingLocked(Settings.Secure.DOUBLE_TAP_TO_WAKE, + secureSettings.insertSettingOverrideableByRestoreLocked( + Settings.Secure.DOUBLE_TAP_TO_WAKE, getContext().getResources().getBoolean( R.bool.def_double_tap_to_wake) ? "1" : "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); @@ -3460,7 +3510,7 @@ public class SettingsProvider extends ContentProvider { Settings.Secure.NFC_PAYMENT_DEFAULT_COMPONENT); if (defaultComponent != null && !defaultComponent.isEmpty() && currentSetting.isNull()) { - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.NFC_PAYMENT_DEFAULT_COMPONENT, defaultComponent, null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -3475,7 +3525,7 @@ public class SettingsProvider extends ContentProvider { Setting currentSetting = globalSettings.getSettingLocked( Settings.Global.ADD_USERS_WHEN_LOCKED); if (currentSetting.isNull()) { - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Settings.Global.ADD_USERS_WHEN_LOCKED, getContext().getResources().getBoolean( R.bool.def_add_users_from_lockscreen) ? "1" : "0", @@ -3489,8 +3539,9 @@ public class SettingsProvider extends ContentProvider { final SettingsState globalSettings = getGlobalSettingsLocked(); String defaultDisabledProfiles = (getContext().getResources().getString( R.string.def_bluetooth_disabled_profiles)); - globalSettings.insertSettingLocked(Settings.Global.BLUETOOTH_DISABLED_PROFILES, - defaultDisabledProfiles, null, true, SettingsState.SYSTEM_PACKAGE_NAME); + globalSettings.insertSettingOverrideableByRestoreLocked( + Settings.Global.BLUETOOTH_DISABLED_PROFILES, defaultDisabledProfiles, + null, true, SettingsState.SYSTEM_PACKAGE_NAME); currentVersion = 124; } @@ -3501,7 +3552,7 @@ public class SettingsProvider extends ContentProvider { Setting currentSetting = secureSettings.getSettingLocked( Settings.Secure.SHOW_IME_WITH_HARD_KEYBOARD); if (currentSetting.isNull()) { - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.SHOW_IME_WITH_HARD_KEYBOARD, getContext().getResources().getBoolean( R.bool.def_show_ime_with_hard_keyboard) ? "1" : "0", @@ -3530,7 +3581,7 @@ public class SettingsProvider extends ContentProvider { b.append(c.flattenToString()); start = false; } - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.ENABLED_VR_LISTENERS, b.toString(), null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -3550,7 +3601,7 @@ public class SettingsProvider extends ContentProvider { Settings.Secure.LOCK_SCREEN_SHOW_NOTIFICATIONS); if (!showNotifications.isNull()) { final SettingsState secureSettings = getSecureSettingsLocked(userId); - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.LOCK_SCREEN_SHOW_NOTIFICATIONS, showNotifications.getValue(), null, true, SettingsState.SYSTEM_PACKAGE_NAME); @@ -3560,7 +3611,7 @@ public class SettingsProvider extends ContentProvider { Settings.Secure.LOCK_SCREEN_ALLOW_PRIVATE_NOTIFICATIONS); if (!allowPrivate.isNull()) { final SettingsState secureSettings = getSecureSettingsLocked(userId); - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.LOCK_SCREEN_ALLOW_PRIVATE_NOTIFICATIONS, allowPrivate.getValue(), null, true, SettingsState.SYSTEM_PACKAGE_NAME); @@ -3587,7 +3638,7 @@ public class SettingsProvider extends ContentProvider { final String oldValue = systemSecureSettings.getSettingLocked( Settings.Secure.LONG_PRESS_TIMEOUT).getValue(); if (TextUtils.equals("500", oldValue)) { - systemSecureSettings.insertSettingLocked( + systemSecureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.LONG_PRESS_TIMEOUT, String.valueOf(getContext().getResources().getInteger( R.integer.def_long_press_timeout_millis)), @@ -3603,10 +3654,12 @@ public class SettingsProvider extends ContentProvider { getSettingLocked(Settings.Secure.DOZE_ENABLED).getValue()); if (dozeExplicitlyDisabled) { - secureSettings.insertSettingLocked(Settings.Secure.DOZE_PICK_UP_GESTURE, - "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); - secureSettings.insertSettingLocked(Settings.Secure.DOZE_DOUBLE_TAP_GESTURE, - "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); + secureSettings.insertSettingOverrideableByRestoreLocked( + Settings.Secure.DOZE_PICK_UP_GESTURE, "0", null, true, + SettingsState.SYSTEM_PACKAGE_NAME); + secureSettings.insertSettingOverrideableByRestoreLocked( + Settings.Secure.DOZE_DOUBLE_TAP_GESTURE, "0", null, true, + SettingsState.SYSTEM_PACKAGE_NAME); } currentVersion = 131; } @@ -3617,7 +3670,7 @@ public class SettingsProvider extends ContentProvider { final String oldValue = systemSecureSettings.getSettingLocked( Settings.Secure.MULTI_PRESS_TIMEOUT).getValue(); if (TextUtils.equals(null, oldValue)) { - systemSecureSettings.insertSettingLocked( + systemSecureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.MULTI_PRESS_TIMEOUT, String.valueOf(getContext().getResources().getInteger( R.integer.def_multi_press_timeout_millis)), @@ -3632,7 +3685,7 @@ public class SettingsProvider extends ContentProvider { final SettingsState systemSecureSettings = getSecureSettingsLocked(userId); String defaultSyncParentSounds = (getContext().getResources() .getBoolean(R.bool.def_sync_parent_sounds) ? "1" : "0"); - systemSecureSettings.insertSettingLocked( + systemSecureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.SYNC_PARENT_SOUNDS, defaultSyncParentSounds, null, true, SettingsState.SYSTEM_PACKAGE_NAME); currentVersion = 133; @@ -3645,9 +3698,9 @@ public class SettingsProvider extends ContentProvider { .isNull()) { String defaultEndButtonBehavior = Integer.toString(getContext() .getResources().getInteger(R.integer.def_end_button_behavior)); - systemSettings.insertSettingLocked(Settings.System.END_BUTTON_BEHAVIOR, - defaultEndButtonBehavior, null, true, - SettingsState.SYSTEM_PACKAGE_NAME); + systemSettings.insertSettingOverrideableByRestoreLocked( + Settings.System.END_BUTTON_BEHAVIOR, defaultEndButtonBehavior, null, + true, SettingsState.SYSTEM_PACKAGE_NAME); } currentVersion = 134; } @@ -3705,8 +3758,8 @@ public class SettingsProvider extends ContentProvider { if (ssaid.isNull() || ssaid.getValue() == null) { // Android Id doesn't exist for this package so create it. - ssaidSettings.insertSettingLocked(uid, legacySsaid, null, true, - info.packageName); + ssaidSettings.insertSettingOverrideableByRestoreLocked(uid, + legacySsaid, null, true, info.packageName); if (DEBUG) { Slog.d(LOG_TAG, "Keep the legacy ssaid for uid=" + uid); } @@ -3726,13 +3779,14 @@ public class SettingsProvider extends ContentProvider { && secureSetting.getSettingLocked( Settings.Secure.INSTALL_NON_MARKET_APPS).getValue().equals("0")) { - secureSetting.insertSettingLocked(Settings.Secure.INSTALL_NON_MARKET_APPS, - "1", null, true, SettingsState.SYSTEM_PACKAGE_NAME); + secureSetting.insertSettingOverrideableByRestoreLocked( + Settings.Secure.INSTALL_NON_MARKET_APPS, "1", null, true, + SettingsState.SYSTEM_PACKAGE_NAME); // For managed profiles with profile owners, DevicePolicyManagerService // may want to set the user restriction in this case - secureSetting.insertSettingLocked( - Settings.Secure.UNKNOWN_SOURCES_DEFAULT_REVERSED, "1", null, true, - SettingsState.SYSTEM_PACKAGE_NAME); + secureSetting.insertSettingOverrideableByRestoreLocked( + Settings.Secure.UNKNOWN_SOURCES_DEFAULT_REVERSED, "1", null, + true, SettingsState.SYSTEM_PACKAGE_NAME); } currentVersion = 138; } @@ -3773,7 +3827,7 @@ public class SettingsProvider extends ContentProvider { Setting currentSetting = globalSettings.getSettingLocked( Settings.Global.WIFI_WAKEUP_ENABLED); if (currentSetting.isNull()) { - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Settings.Global.WIFI_WAKEUP_ENABLED, getContext().getResources().getBoolean( R.bool.def_wifi_wakeup_enabled) ? "1" : "0", @@ -3795,8 +3849,9 @@ public class SettingsProvider extends ContentProvider { if (defaultValue != null) { Slog.d(LOG_TAG, "Setting [" + defaultValue + "] as Autofill Service " + "for user " + userId); - secureSettings.insertSettingLocked(Settings.Secure.AUTOFILL_SERVICE, - defaultValue, null, true, SettingsState.SYSTEM_PACKAGE_NAME); + secureSettings.insertSettingOverrideableByRestoreLocked( + Settings.Secure.AUTOFILL_SERVICE, defaultValue, null, true, + SettingsState.SYSTEM_PACKAGE_NAME); } } @@ -3847,7 +3902,7 @@ public class SettingsProvider extends ContentProvider { final Setting currentSetting = globalSettings.getSettingLocked( Global.DEFAULT_RESTRICT_BACKGROUND_DATA); if (currentSetting.isNull()) { - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Global.DEFAULT_RESTRICT_BACKGROUND_DATA, getContext().getResources().getBoolean( R.bool.def_restrict_background_data) ? "1" : "0", @@ -3866,7 +3921,7 @@ public class SettingsProvider extends ContentProvider { final String defaultValue = getContext().getResources().getString( R.string.def_backup_manager_constants); if (!TextUtils.isEmpty(defaultValue)) { - systemSecureSettings.insertSettingLocked( + systemSecureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.BACKUP_MANAGER_CONSTANTS, defaultValue, null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -3880,7 +3935,7 @@ public class SettingsProvider extends ContentProvider { final Setting currentSetting = globalSettings.getSettingLocked( Settings.Global.MOBILE_DATA_ALWAYS_ON); if (currentSetting.isNull()) { - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Settings.Global.MOBILE_DATA_ALWAYS_ON, getContext().getResources().getBoolean( R.bool.def_mobile_data_always_on) ? "1" : "0", @@ -3916,7 +3971,7 @@ public class SettingsProvider extends ContentProvider { if (showNotificationBadges.isNull()) { final boolean defaultValue = getContext().getResources().getBoolean( com.android.internal.R.bool.config_notificationBadging); - systemSecureSettings.insertSettingLocked( + systemSecureSettings.insertSettingOverrideableByRestoreLocked( Secure.NOTIFICATION_BADGING, defaultValue ? "1" : "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); @@ -3933,7 +3988,7 @@ public class SettingsProvider extends ContentProvider { final String defaultValue = getContext().getResources().getString( R.string.def_backup_local_transport_parameters); if (!TextUtils.isEmpty(defaultValue)) { - systemSecureSettings.insertSettingLocked( + systemSecureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.BACKUP_LOCAL_TRANSPORT_PARAMETERS, defaultValue, null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -3956,7 +4011,7 @@ public class SettingsProvider extends ContentProvider { if (currentSetting.isNull()) { String defaultZenDuration = Integer.toString(getContext() .getResources().getInteger(R.integer.def_zen_duration)); - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Global.ZEN_DURATION, defaultZenDuration, null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -3972,7 +4027,7 @@ public class SettingsProvider extends ContentProvider { final String defaultValue = getContext().getResources().getString( R.string.def_backup_agent_timeout_parameters); if (!TextUtils.isEmpty(defaultValue)) { - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Settings.Global.BACKUP_AGENT_TIMEOUT_PARAMETERS, defaultValue, null, true, SettingsState.SYSTEM_PACKAGE_NAME); @@ -4001,7 +4056,7 @@ public class SettingsProvider extends ContentProvider { Settings.Secure.LOCK_SCREEN_SHOW_NOTIFICATIONS); // The default value is "1", check if user has turned it off. if ("0".equals(showNotifications.getValue())) { - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.LOCK_SCREEN_ALLOW_PRIVATE_NOTIFICATIONS, "0", null /* tag */, false /* makeDefault */, SettingsState.SYSTEM_PACKAGE_NAME); @@ -4022,7 +4077,7 @@ public class SettingsProvider extends ContentProvider { String oldValue = globalSettings.getSettingLocked( Global.MAX_SOUND_TRIGGER_DETECTION_SERVICE_OPS_PER_DAY).getValue(); if (TextUtils.equals(null, oldValue)) { - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Settings.Global.MAX_SOUND_TRIGGER_DETECTION_SERVICE_OPS_PER_DAY, Integer.toString(getContext().getResources().getInteger( R.integer.def_max_sound_trigger_detection_service_ops_per_day)), @@ -4032,7 +4087,7 @@ public class SettingsProvider extends ContentProvider { oldValue = globalSettings.getSettingLocked( Global.SOUND_TRIGGER_DETECTION_SERVICE_OP_TIMEOUT).getValue(); if (TextUtils.equals(null, oldValue)) { - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Settings.Global.SOUND_TRIGGER_DETECTION_SERVICE_OP_TIMEOUT, Integer.toString(getContext().getResources().getInteger( R.integer.def_sound_trigger_detection_service_op_timeout)), @@ -4047,7 +4102,7 @@ public class SettingsProvider extends ContentProvider { final Setting currentSetting = secureSettings.getSettingLocked( Secure.VOLUME_HUSH_GESTURE); if (currentSetting.isNull()) { - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.VOLUME_HUSH_GESTURE, Integer.toString(Secure.VOLUME_HUSH_VIBRATE), null, true, SettingsState.SYSTEM_PACKAGE_NAME); @@ -4068,7 +4123,7 @@ public class SettingsProvider extends ContentProvider { final Setting currentSetting = settings.getSettingLocked( Global.MAX_SOUND_TRIGGER_DETECTION_SERVICE_OPS_PER_DAY); if (currentSetting.isDefaultFromSystem()) { - settings.insertSettingLocked( + settings.insertSettingOverrideableByRestoreLocked( Settings.Global.MAX_SOUND_TRIGGER_DETECTION_SERVICE_OPS_PER_DAY, Integer.toString(getContext().getResources().getInteger( R.integer @@ -4097,7 +4152,7 @@ public class SettingsProvider extends ContentProvider { Setting currentHushUsedSetting = secureSettings.getSettingLocked( Secure.HUSH_GESTURE_USED); if (currentHushUsedSetting.isNull()) { - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.HUSH_GESTURE_USED, "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4105,7 +4160,7 @@ public class SettingsProvider extends ContentProvider { Setting currentRingerToggleCountSetting = secureSettings.getSettingLocked( Secure.MANUAL_RINGER_TOGGLE_COUNT); if (currentRingerToggleCountSetting.isNull()) { - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Settings.Secure.MANUAL_RINGER_TOGGLE_COUNT, "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4124,7 +4179,7 @@ public class SettingsProvider extends ContentProvider { final Setting currentSetting = systemSettings.getSettingLocked( Settings.System.VIBRATE_WHEN_RINGING); if (currentSetting.isNull()) { - systemSettings.insertSettingLocked( + systemSettings.insertSettingOverrideableByRestoreLocked( Settings.System.VIBRATE_WHEN_RINGING, getContext().getResources().getBoolean( R.bool.def_vibrate_when_ringing) ? "1" : "0", @@ -4148,18 +4203,18 @@ public class SettingsProvider extends ContentProvider { // ZEN_DURATION if (!globalZenDuration.isNull()) { - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.ZEN_DURATION, globalZenDuration.getValue(), null, false, SettingsState.SYSTEM_PACKAGE_NAME); // set global zen duration setting to null since it's deprecated - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Global.ZEN_DURATION, null, null, true, SettingsState.SYSTEM_PACKAGE_NAME); } else if (secureZenDuration.isNull()) { String defaultZenDuration = Integer.toString(getContext() .getResources().getInteger(R.integer.def_zen_duration)); - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.ZEN_DURATION, defaultZenDuration, null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4168,7 +4223,7 @@ public class SettingsProvider extends ContentProvider { final Setting currentShowZenSettingSuggestion = secureSettings.getSettingLocked( Secure.SHOW_ZEN_SETTINGS_SUGGESTION); if (currentShowZenSettingSuggestion.isNull()) { - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.SHOW_ZEN_SETTINGS_SUGGESTION, "1", null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4177,7 +4232,7 @@ public class SettingsProvider extends ContentProvider { final Setting currentUpdatedSetting = secureSettings.getSettingLocked( Secure.ZEN_SETTINGS_UPDATED); if (currentUpdatedSetting.isNull()) { - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.ZEN_SETTINGS_UPDATED, "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4186,7 +4241,7 @@ public class SettingsProvider extends ContentProvider { final Setting currentSettingSuggestionViewed = secureSettings.getSettingLocked( Secure.ZEN_SETTINGS_SUGGESTION_VIEWED); if (currentSettingSuggestionViewed.isNull()) { - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.ZEN_SETTINGS_SUGGESTION_VIEWED, "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4209,20 +4264,20 @@ public class SettingsProvider extends ContentProvider { if (!globalChargingSoundEnabled.isNull()) { if (secureChargingSoundsEnabled.isNull()) { - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.CHARGING_SOUNDS_ENABLED, globalChargingSoundEnabled.getValue(), null, false, SettingsState.SYSTEM_PACKAGE_NAME); } // set global charging_sounds_enabled setting to null since it's deprecated - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Global.CHARGING_SOUNDS_ENABLED, null, null, true, SettingsState.SYSTEM_PACKAGE_NAME); } else if (secureChargingSoundsEnabled.isNull()) { String defChargingSoundsEnabled = getContext().getResources() .getBoolean(R.bool.def_charging_sounds_enabled) ? "1" : "0"; - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.CHARGING_SOUNDS_ENABLED, defChargingSoundsEnabled, null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4234,7 +4289,7 @@ public class SettingsProvider extends ContentProvider { if (secureChargingVibrationEnabled.isNull()) { String defChargingVibrationEnabled = getContext().getResources() .getBoolean(R.bool.def_charging_vibration_enabled) ? "1" : "0"; - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.CHARGING_VIBRATION_ENABLED, defChargingVibrationEnabled, null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4254,7 +4309,7 @@ public class SettingsProvider extends ContentProvider { currentSetting.getValue()); if ((currentSettingIntegerValue & (1 << AudioManager.STREAM_VOICE_CALL)) == 0) { - systemSettings.insertSettingLocked( + systemSettings.insertSettingOverrideableByRestoreLocked( Settings.System.MUTE_STREAMS_AFFECTED, Integer.toString( currentSettingIntegerValue @@ -4295,7 +4350,7 @@ public class SettingsProvider extends ContentProvider { ? Secure.LOCATION_MODE_ON : Secure.LOCATION_MODE_OFF; } - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.LOCATION_MODE, Integer.toString(defLocationMode), null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4317,7 +4372,7 @@ public class SettingsProvider extends ContentProvider { Setting currentRampingRingerSetting = globalSettings.getSettingLocked( Settings.Global.APPLY_RAMPING_RINGER); if (currentRampingRingerSetting.isNull()) { - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Settings.Global.APPLY_RAMPING_RINGER, getContext().getResources().getBoolean( R.bool.def_apply_ramping_ringer) ? "1" : "0", null, @@ -4343,7 +4398,7 @@ public class SettingsProvider extends ContentProvider { if (!notificationVibrationIntensity.isNull() && ringVibrationIntensity.isNull()) { - systemSettings.insertSettingLocked( + systemSettings.insertSettingOverrideableByRestoreLocked( Settings.System.RING_VIBRATION_INTENSITY, notificationVibrationIntensity.getValue(), null , true, SettingsState.SYSTEM_PACKAGE_NAME); @@ -4387,7 +4442,7 @@ public class SettingsProvider extends ContentProvider { if (awareEnabled.isNull()) { final boolean defAwareEnabled = getContext().getResources().getBoolean( R.bool.def_aware_enabled); - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.AWARE_ENABLED, defAwareEnabled ? "1" : "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4407,7 +4462,7 @@ public class SettingsProvider extends ContentProvider { if (skipGesture.isNull()) { final boolean defSkipGesture = getContext().getResources().getBoolean( R.bool.def_skip_gesture); - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.SKIP_GESTURE, defSkipGesture ? "1" : "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4418,7 +4473,7 @@ public class SettingsProvider extends ContentProvider { if (silenceGesture.isNull()) { final boolean defSilenceGesture = getContext().getResources().getBoolean( R.bool.def_silence_gesture); - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.SILENCE_GESTURE, defSilenceGesture ? "1" : "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4446,7 +4501,7 @@ public class SettingsProvider extends ContentProvider { if (awareLockEnabled.isNull()) { final boolean defAwareLockEnabled = getContext().getResources().getBoolean( R.bool.def_aware_lock_enabled); - secureSettings.insertSettingLocked( + secureSettings.insertSettingOverrideableByRestoreLocked( Secure.AWARE_LOCK_ENABLED, defAwareLockEnabled ? "1" : "0", null, true, SettingsState.SYSTEM_PACKAGE_NAME); } @@ -4466,7 +4521,7 @@ public class SettingsProvider extends ContentProvider { currentSetting.getValue()); if ((currentSettingIntegerValue & (1 << AudioManager.STREAM_BLUETOOTH_SCO)) == 0) { - systemSettings.insertSettingLocked( + systemSettings.insertSettingOverrideableByRestoreLocked( Settings.System.MUTE_STREAMS_AFFECTED, Integer.toString( currentSettingIntegerValue @@ -4512,13 +4567,13 @@ public class SettingsProvider extends ContentProvider { if (oldValueWireless == null || TextUtils.equals(oldValueWireless, defaultValueWired)) { if (!TextUtils.isEmpty(defaultValueWireless)) { - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Global.WIRELESS_CHARGING_STARTED_SOUND, defaultValueWireless, null /* tag */, true /* makeDefault */, SettingsState.SYSTEM_PACKAGE_NAME); } else if (!TextUtils.isEmpty(defaultValueWired)) { // if the wireless sound is empty, use the wired charging sound - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Global.WIRELESS_CHARGING_STARTED_SOUND, defaultValueWired, null /* tag */, true /* makeDefault */, SettingsState.SYSTEM_PACKAGE_NAME); @@ -4527,7 +4582,7 @@ public class SettingsProvider extends ContentProvider { // wired charging sound if (oldValueWired == null && !TextUtils.isEmpty(defaultValueWired)) { - globalSettings.insertSettingLocked( + globalSettings.insertSettingOverrideableByRestoreLocked( Global.CHARGING_STARTED_SOUND, defaultValueWired, null /* tag */, true /* makeDefault */, SettingsState.SYSTEM_PACKAGE_NAME); @@ -4539,8 +4594,8 @@ public class SettingsProvider extends ContentProvider { // Version 184: Reset the default for Global Settings: NOTIFICATION_BUBBLES // This is originally set in version 182, however, the default value changed // so this step is to ensure the value is updated to the correct default. - getGlobalSettingsLocked().insertSettingLocked(Global.NOTIFICATION_BUBBLES, - getContext().getResources().getBoolean( + getGlobalSettingsLocked().insertSettingOverrideableByRestoreLocked( + Global.NOTIFICATION_BUBBLES, getContext().getResources().getBoolean( R.bool.def_notification_bubbles) ? "1" : "0", null /* tag */, true /* makeDefault */, SettingsState.SYSTEM_PACKAGE_NAME); @@ -4590,7 +4645,7 @@ public class SettingsProvider extends ContentProvider { final boolean systemSet = SettingsState.isSystemPackage(getContext(), setting.getPackageName(), callingUid, userId); if (systemSet) { - settings.insertSettingLocked(name, setting.getValue(), + settings.insertSettingOverrideableByRestoreLocked(name, setting.getValue(), setting.getTag(), true, setting.getPackageName()); } else if (setting.getDefaultValue() != null && setting.isDefaultFromSystem()) { // We had a bug where changes by non-system packages were marked diff --git a/packages/SettingsProvider/src/com/android/providers/settings/SettingsState.java b/packages/SettingsProvider/src/com/android/providers/settings/SettingsState.java index 96db538e51e2..db18213a3599 100644 --- a/packages/SettingsProvider/src/com/android/providers/settings/SettingsState.java +++ b/packages/SettingsProvider/src/com/android/providers/settings/SettingsState.java @@ -390,15 +390,25 @@ final class SettingsState { // The settings provider must hold its lock when calling here. @GuardedBy("mLock") + public boolean insertSettingOverrideableByRestoreLocked(String name, String value, String tag, + boolean makeDefault, String packageName) { + return insertSettingLocked(name, value, tag, makeDefault, false, packageName, + /* overrideableByRestore */ true); + } + + // The settings provider must hold its lock when calling here. + @GuardedBy("mLock") public boolean insertSettingLocked(String name, String value, String tag, boolean makeDefault, String packageName) { - return insertSettingLocked(name, value, tag, makeDefault, false, packageName); + return insertSettingLocked(name, value, tag, makeDefault, false, packageName, + /* overrideableByRestore */ false); } // The settings provider must hold its lock when calling here. @GuardedBy("mLock") public boolean insertSettingLocked(String name, String value, String tag, - boolean makeDefault, boolean forceNonSystemPackage, String packageName) { + boolean makeDefault, boolean forceNonSystemPackage, String packageName, + boolean overrideableByRestore) { if (TextUtils.isEmpty(name)) { return false; } @@ -409,7 +419,8 @@ final class SettingsState { Setting newState; if (oldState != null) { - if (!oldState.update(value, makeDefault, packageName, tag, forceNonSystemPackage)) { + if (!oldState.update(value, makeDefault, packageName, tag, forceNonSystemPackage, + overrideableByRestore)) { return false; } newState = oldState; @@ -497,7 +508,8 @@ final class SettingsState { changedKeys.add(key); // key was added } else if (state.value != value) { oldValue = state.value; - state.update(value, false, packageName, null, true); + state.update(value, false, packageName, null, true, + /* overrideableByRestore */ false); changedKeys.add(key); // key was updated } else { // this key/value already exists, no change and no logging necessary @@ -1144,7 +1156,7 @@ final class SettingsState { private String tag; // Whether the default is set by the system private boolean defaultFromSystem; - // Whether the value of this setting will be preserved when restore happens.. + // Whether the value of this setting will be preserved when restore happens. private boolean isValuePreservedInRestore; public Setting(Setting other) { @@ -1155,17 +1167,22 @@ final class SettingsState { id = other.id; defaultFromSystem = other.defaultFromSystem; tag = other.tag; + isValuePreservedInRestore = other.isValuePreservedInRestore; } public Setting(String name, String value, boolean makeDefault, String packageName, String tag) { this.name = name; - update(value, makeDefault, packageName, tag, false); + // overrideableByRestore = true as the first initialization isn't considered a + // modification. + update(value, makeDefault, packageName, tag, false, + /* overrideableByRestore */ true); } public Setting(String name, String value, String defaultValue, String packageName, String tag, boolean fromSystem, String id) { - this(name, value, defaultValue, packageName, tag, fromSystem, id, false); + this(name, value, defaultValue, packageName, tag, fromSystem, id, + /* isOverrideableByRestore */ false); } Setting(String name, String value, String defaultValue, @@ -1234,7 +1251,9 @@ final class SettingsState { /** @return whether the value changed */ public boolean reset() { - return update(this.defaultValue, false, packageName, null, true); + // overrideableByRestore = true as resetting to default value isn't considered a + // modification. + return update(this.defaultValue, false, packageName, null, true, true); } public boolean isTransient() { @@ -1246,7 +1265,7 @@ final class SettingsState { } public boolean update(String value, boolean setDefault, String packageName, String tag, - boolean forceNonSystemPackage) { + boolean forceNonSystemPackage, boolean overrideableByRestore) { if (NULL_VALUE.equals(value)) { value = null; } @@ -1279,17 +1298,22 @@ final class SettingsState { } } + // isValuePreservedInRestore shouldn't change back to false if it has been set to true. + boolean isPreserved = this.isValuePreservedInRestore || !overrideableByRestore; + // Is something gonna change? if (Objects.equals(value, this.value) && Objects.equals(defaultValue, this.defaultValue) && Objects.equals(packageName, this.packageName) && Objects.equals(tag, this.tag) - && defaultFromSystem == this.defaultFromSystem) { + && defaultFromSystem == this.defaultFromSystem + && isPreserved == this.isValuePreservedInRestore) { return false; } init(name, value, tag, defaultValue, packageName, defaultFromSystem, - String.valueOf(mNextId++), /* isValuePreservedInRestore */ true); + String.valueOf(mNextId++), isPreserved); + return true; } diff --git a/packages/SettingsProvider/test/src/com/android/providers/settings/SettingsStateTest.java b/packages/SettingsProvider/test/src/com/android/providers/settings/SettingsStateTest.java index 918b2af2f148..b855d87fc214 100644 --- a/packages/SettingsProvider/test/src/com/android/providers/settings/SettingsStateTest.java +++ b/packages/SettingsProvider/test/src/com/android/providers/settings/SettingsStateTest.java @@ -46,6 +46,18 @@ public class SettingsStateTest extends AndroidTestCase { "\uD800ab\uDC00 " + // broken surrogate pairs "日本語"; + private static final String TEST_PACKAGE = "package"; + private static final String SETTING_NAME = "test_setting"; + + private final Object mLock = new Object(); + + private File mSettingsFile; + + @Override + protected void setUp() { + mSettingsFile = new File(getContext().getCacheDir(), "setting.xml"); + mSettingsFile.delete(); + } public void testIsBinary() { assertFalse(SettingsState.isBinary(" abc 日本語")); @@ -182,4 +194,57 @@ public class SettingsStateTest extends AndroidTestCase { assertEquals("p2", s.getPackageName()); } } + + public void testInitializeSetting_preserveFlagNotSet() { + SettingsState settingsWriter = getSettingStateObject(); + settingsWriter.insertSettingLocked(SETTING_NAME, "1", null, false, TEST_PACKAGE); + settingsWriter.persistSyncLocked(); + + SettingsState settingsReader = getSettingStateObject(); + assertFalse(settingsReader.getSettingLocked(SETTING_NAME).isValuePreservedInRestore()); + } + + public void testModifySetting_preserveFlagSet() { + SettingsState settingsWriter = getSettingStateObject(); + settingsWriter.insertSettingLocked(SETTING_NAME, "1", null, false, TEST_PACKAGE); + settingsWriter.insertSettingLocked(SETTING_NAME, "2", null, false, TEST_PACKAGE); + settingsWriter.persistSyncLocked(); + + SettingsState settingsReader = getSettingStateObject(); + assertTrue(settingsReader.getSettingLocked(SETTING_NAME).isValuePreservedInRestore()); + } + + public void testModifySettingOverrideableByRestore_preserveFlagNotSet() { + SettingsState settingsWriter = getSettingStateObject(); + settingsWriter.insertSettingLocked(SETTING_NAME, "1", null, false, TEST_PACKAGE); + settingsWriter.insertSettingLocked(SETTING_NAME, "2", null, false, false, TEST_PACKAGE, + /* overrideableByRestore */ true); + settingsWriter.persistSyncLocked(); + + SettingsState settingsReader = getSettingStateObject(); + assertFalse(settingsReader.getSettingLocked(SETTING_NAME).isValuePreservedInRestore()); + } + + public void testModifySettingOverrideableByRestore_preserveFlagAlreadySet_flagValueUnchanged() { + SettingsState settingsWriter = getSettingStateObject(); + // Init the setting. + settingsWriter.insertSettingLocked(SETTING_NAME, "1", null, false, TEST_PACKAGE); + // This modification will set isValuePreservedInRestore = true. + settingsWriter.insertSettingLocked(SETTING_NAME, "1", null, false, TEST_PACKAGE); + // This modification shouldn't change the value of isValuePreservedInRestore since it's + // already been set to true. + settingsWriter.insertSettingLocked(SETTING_NAME, "2", null, false, false, TEST_PACKAGE, + /* overrideableByRestore */ true); + settingsWriter.persistSyncLocked(); + + SettingsState settingsReader = getSettingStateObject(); + assertTrue(settingsReader.getSettingLocked(SETTING_NAME).isValuePreservedInRestore()); + } + + private SettingsState getSettingStateObject() { + SettingsState settingsState = new SettingsState(getContext(), mLock, mSettingsFile, 1, + SettingsState.MAX_BYTES_PER_APP_PACKAGE_UNLIMITED, Looper.getMainLooper()); + settingsState.setVersionLocked(SettingsState.SETTINGS_VERSION_NEW_ENCODING); + return settingsState; + } } |