Loading core/java/android/os/storage/StorageManager.java +3 −6 Original line number Diff line number Diff line Loading @@ -162,12 +162,9 @@ public class StorageManager { /** {@hide} */ public static final String PROP_SETTINGS_FUSE = FeatureFlagUtils.PERSIST_PREFIX + FeatureFlagUtils.SETTINGS_FUSE_FLAG; /** * Property that determines whether {@link OP_LEGACY_STORAGE} is sticky for * legacy apps. * @hide */ public static final String PROP_LEGACY_OP_STICKY = "persist.sys.legacy_storage_sticky"; /** {@hide} */ public static final String PROP_FORCED_SCOPED_STORAGE_WHITELIST = "forced_scoped_storage_whitelist"; /** {@hide} */ public static final String UUID_PRIVATE_INTERNAL = null; Loading services/core/java/com/android/server/StorageManagerService.java +4 −9 Original line number Diff line number Diff line Loading @@ -42,8 +42,8 @@ import static android.os.storage.OnObbStateChangeListener.ERROR_NOT_MOUNTED; import static android.os.storage.OnObbStateChangeListener.ERROR_PERMISSION_DENIED; import static android.os.storage.OnObbStateChangeListener.MOUNTED; import static android.os.storage.OnObbStateChangeListener.UNMOUNTED; import static android.os.storage.StorageManager.PROP_FORCED_SCOPED_STORAGE_WHITELIST; import static android.os.storage.StorageManager.PROP_FUSE; import static android.os.storage.StorageManager.PROP_LEGACY_OP_STICKY; import static android.os.storage.StorageManager.PROP_SETTINGS_FUSE; import static com.android.internal.util.XmlUtils.readIntAttribute; Loading Loading @@ -914,7 +914,6 @@ class StorageManagerService extends IStorageManager.Stub refreshIsolatedStorageSettings(); } }); updateLegacyStorageOpSticky(); // For now, simply clone property when it changes DeviceConfig.addOnPropertiesChangedListener(DeviceConfig.NAMESPACE_STORAGE_NATIVE_BOOT, mContext.getMainExecutor(), (properties) -> { Loading Loading @@ -1836,13 +1835,6 @@ class StorageManagerService extends IStorageManager.Stub } } private void updateLegacyStorageOpSticky() { final boolean propertyValue = DeviceConfig.getBoolean( DeviceConfig.NAMESPACE_STORAGE_NATIVE_BOOT, "legacy_storage_op_sticky", true); SystemProperties.set(PROP_LEGACY_OP_STICKY, propertyValue ? "true" : "false"); } private void start() { connectStoraged(); connectVold(); Loading Loading @@ -4442,6 +4434,9 @@ class StorageManagerService extends IStorageManager.Stub pw.println("Isolated storage, remote feature flag: " + Settings.Global.getInt(cr, Settings.Global.ISOLATED_STORAGE_REMOTE, 0)); pw.println("Isolated storage, resolved: " + StorageManager.hasIsolatedStorage()); pw.println("Forced scoped storage app list: " + DeviceConfig.getProperty(DeviceConfig.NAMESPACE_STORAGE_NATIVE_BOOT, PROP_FORCED_SCOPED_STORAGE_WHITELIST)); } synchronized (mObbMounts) { Loading services/core/java/com/android/server/policy/SoftRestrictedPermissionPolicy.java +22 −9 Original line number Diff line number Diff line Loading @@ -26,7 +26,6 @@ import static android.content.pm.PackageManager.FLAG_PERMISSION_RESTRICTION_INST import static android.content.pm.PackageManager.FLAG_PERMISSION_RESTRICTION_SYSTEM_EXEMPT; import static android.content.pm.PackageManager.FLAG_PERMISSION_RESTRICTION_UPGRADE_EXEMPT; import static android.content.pm.PackageManager.PERMISSION_GRANTED; import static android.os.storage.StorageManager.PROP_LEGACY_OP_STICKY; import static java.lang.Integer.min; Loading @@ -37,13 +36,17 @@ import android.content.Context; import android.content.pm.ApplicationInfo; import android.content.pm.PackageManager; import android.os.Build; import android.os.SystemProperties; import android.os.UserHandle; import android.os.storage.StorageManager; import android.os.storage.StorageManagerInternal; import android.provider.DeviceConfig; import com.android.server.LocalServices; import com.android.server.pm.parsing.pkg.AndroidPackage; import java.util.Arrays; import java.util.HashSet; /** * The behavior of soft restricted permissions is different for each permission. This class collects * the policies in one place. Loading @@ -65,8 +68,8 @@ public abstract class SoftRestrictedPermissionPolicy { } }; private static final boolean isLegacyStorageAppOpStickyGlobal = SystemProperties.getBoolean( PROP_LEGACY_OP_STICKY, /*defaultValue*/true); private static final HashSet<String> sForcedScopedStorageAppWhitelist = new HashSet<>( Arrays.asList(getForcedScopedStorageAppWhitelist())); /** * TargetSDK is per package. To make sure two apps int the same shared UID do not fight over Loading Loading @@ -141,12 +144,13 @@ public abstract class SoftRestrictedPermissionPolicy { shouldPreserveLegacyExternalStorage = pkg.hasPreserveLegacyExternalStorage() && smInternal.hasLegacyExternalStorage(appInfo.uid); targetSDK = getMinimumTargetSDK(context, appInfo, user); // LEGACY_STORAGE op is normally sticky for apps targetig <= Q. // However, this device can be configured to make it non-sticky. boolean isLegacyAppOpSticky = isLegacyStorageAppOpStickyGlobal && targetSDK <= Build.VERSION_CODES.Q; shouldApplyRestriction = (flags & FLAG_PERMISSION_APPLY_RESTRICTION) != 0 || (!isLegacyAppOpSticky && !shouldPreserveLegacyExternalStorage); || (targetSDK > Build.VERSION_CODES.Q && !shouldPreserveLegacyExternalStorage) // If the device is configured to force this app into scoped storage, // then we should apply the restriction || sForcedScopedStorageAppWhitelist.contains(appInfo.packageName); } else { isWhiteListed = false; shouldApplyRestriction = false; Loading Loading @@ -245,6 +249,15 @@ public abstract class SoftRestrictedPermissionPolicy { return false; } private static String[] getForcedScopedStorageAppWhitelist() { final String rawList = DeviceConfig.getString(DeviceConfig.NAMESPACE_STORAGE_NATIVE_BOOT, StorageManager.PROP_FORCED_SCOPED_STORAGE_WHITELIST, /*defaultValue*/""); if (rawList == null || rawList.equals("")) { return new String[0]; } return rawList.split(","); } /** * @return If the permission can be granted */ Loading Loading
core/java/android/os/storage/StorageManager.java +3 −6 Original line number Diff line number Diff line Loading @@ -162,12 +162,9 @@ public class StorageManager { /** {@hide} */ public static final String PROP_SETTINGS_FUSE = FeatureFlagUtils.PERSIST_PREFIX + FeatureFlagUtils.SETTINGS_FUSE_FLAG; /** * Property that determines whether {@link OP_LEGACY_STORAGE} is sticky for * legacy apps. * @hide */ public static final String PROP_LEGACY_OP_STICKY = "persist.sys.legacy_storage_sticky"; /** {@hide} */ public static final String PROP_FORCED_SCOPED_STORAGE_WHITELIST = "forced_scoped_storage_whitelist"; /** {@hide} */ public static final String UUID_PRIVATE_INTERNAL = null; Loading
services/core/java/com/android/server/StorageManagerService.java +4 −9 Original line number Diff line number Diff line Loading @@ -42,8 +42,8 @@ import static android.os.storage.OnObbStateChangeListener.ERROR_NOT_MOUNTED; import static android.os.storage.OnObbStateChangeListener.ERROR_PERMISSION_DENIED; import static android.os.storage.OnObbStateChangeListener.MOUNTED; import static android.os.storage.OnObbStateChangeListener.UNMOUNTED; import static android.os.storage.StorageManager.PROP_FORCED_SCOPED_STORAGE_WHITELIST; import static android.os.storage.StorageManager.PROP_FUSE; import static android.os.storage.StorageManager.PROP_LEGACY_OP_STICKY; import static android.os.storage.StorageManager.PROP_SETTINGS_FUSE; import static com.android.internal.util.XmlUtils.readIntAttribute; Loading Loading @@ -914,7 +914,6 @@ class StorageManagerService extends IStorageManager.Stub refreshIsolatedStorageSettings(); } }); updateLegacyStorageOpSticky(); // For now, simply clone property when it changes DeviceConfig.addOnPropertiesChangedListener(DeviceConfig.NAMESPACE_STORAGE_NATIVE_BOOT, mContext.getMainExecutor(), (properties) -> { Loading Loading @@ -1836,13 +1835,6 @@ class StorageManagerService extends IStorageManager.Stub } } private void updateLegacyStorageOpSticky() { final boolean propertyValue = DeviceConfig.getBoolean( DeviceConfig.NAMESPACE_STORAGE_NATIVE_BOOT, "legacy_storage_op_sticky", true); SystemProperties.set(PROP_LEGACY_OP_STICKY, propertyValue ? "true" : "false"); } private void start() { connectStoraged(); connectVold(); Loading Loading @@ -4442,6 +4434,9 @@ class StorageManagerService extends IStorageManager.Stub pw.println("Isolated storage, remote feature flag: " + Settings.Global.getInt(cr, Settings.Global.ISOLATED_STORAGE_REMOTE, 0)); pw.println("Isolated storage, resolved: " + StorageManager.hasIsolatedStorage()); pw.println("Forced scoped storage app list: " + DeviceConfig.getProperty(DeviceConfig.NAMESPACE_STORAGE_NATIVE_BOOT, PROP_FORCED_SCOPED_STORAGE_WHITELIST)); } synchronized (mObbMounts) { Loading
services/core/java/com/android/server/policy/SoftRestrictedPermissionPolicy.java +22 −9 Original line number Diff line number Diff line Loading @@ -26,7 +26,6 @@ import static android.content.pm.PackageManager.FLAG_PERMISSION_RESTRICTION_INST import static android.content.pm.PackageManager.FLAG_PERMISSION_RESTRICTION_SYSTEM_EXEMPT; import static android.content.pm.PackageManager.FLAG_PERMISSION_RESTRICTION_UPGRADE_EXEMPT; import static android.content.pm.PackageManager.PERMISSION_GRANTED; import static android.os.storage.StorageManager.PROP_LEGACY_OP_STICKY; import static java.lang.Integer.min; Loading @@ -37,13 +36,17 @@ import android.content.Context; import android.content.pm.ApplicationInfo; import android.content.pm.PackageManager; import android.os.Build; import android.os.SystemProperties; import android.os.UserHandle; import android.os.storage.StorageManager; import android.os.storage.StorageManagerInternal; import android.provider.DeviceConfig; import com.android.server.LocalServices; import com.android.server.pm.parsing.pkg.AndroidPackage; import java.util.Arrays; import java.util.HashSet; /** * The behavior of soft restricted permissions is different for each permission. This class collects * the policies in one place. Loading @@ -65,8 +68,8 @@ public abstract class SoftRestrictedPermissionPolicy { } }; private static final boolean isLegacyStorageAppOpStickyGlobal = SystemProperties.getBoolean( PROP_LEGACY_OP_STICKY, /*defaultValue*/true); private static final HashSet<String> sForcedScopedStorageAppWhitelist = new HashSet<>( Arrays.asList(getForcedScopedStorageAppWhitelist())); /** * TargetSDK is per package. To make sure two apps int the same shared UID do not fight over Loading Loading @@ -141,12 +144,13 @@ public abstract class SoftRestrictedPermissionPolicy { shouldPreserveLegacyExternalStorage = pkg.hasPreserveLegacyExternalStorage() && smInternal.hasLegacyExternalStorage(appInfo.uid); targetSDK = getMinimumTargetSDK(context, appInfo, user); // LEGACY_STORAGE op is normally sticky for apps targetig <= Q. // However, this device can be configured to make it non-sticky. boolean isLegacyAppOpSticky = isLegacyStorageAppOpStickyGlobal && targetSDK <= Build.VERSION_CODES.Q; shouldApplyRestriction = (flags & FLAG_PERMISSION_APPLY_RESTRICTION) != 0 || (!isLegacyAppOpSticky && !shouldPreserveLegacyExternalStorage); || (targetSDK > Build.VERSION_CODES.Q && !shouldPreserveLegacyExternalStorage) // If the device is configured to force this app into scoped storage, // then we should apply the restriction || sForcedScopedStorageAppWhitelist.contains(appInfo.packageName); } else { isWhiteListed = false; shouldApplyRestriction = false; Loading Loading @@ -245,6 +249,15 @@ public abstract class SoftRestrictedPermissionPolicy { return false; } private static String[] getForcedScopedStorageAppWhitelist() { final String rawList = DeviceConfig.getString(DeviceConfig.NAMESPACE_STORAGE_NATIVE_BOOT, StorageManager.PROP_FORCED_SCOPED_STORAGE_WHITELIST, /*defaultValue*/""); if (rawList == null || rawList.equals("")) { return new String[0]; } return rawList.split(","); } /** * @return If the permission can be granted */ Loading