1 /* <lambda>null2 * Copyright (C) 2019 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.permissioncontroller.permission.model.livedatatypes 18 19 import android.Manifest 20 import android.Manifest.permission.ACCESS_COARSE_LOCATION 21 import android.os.Build 22 import android.os.UserHandle 23 24 /** 25 * A lightweight version of the AppPermissionGroup data structure. Represents information about a 26 * package, and all permissions in a particular permission group this package requests. 27 * 28 * @param packageInfo Information about the package 29 * @param permGroupInfo Information about the permission group 30 * @param allPermissions The permissions in the permission group that the package requests 31 * (including restricted ones). 32 * @param hasInstallToRuntimeSplit If this group contains a permission that was previously an 33 * install permission, but is currently a runtime permission 34 * @param specialLocationGrant If this package is the location provider, or the extra location 35 * package, then the grant state of the group is not determined by the grant state of individual 36 * permissions, but by other system properties 37 */ 38 data class LightAppPermGroup( 39 val packageInfo: LightPackageInfo, 40 val permGroupInfo: LightPermGroupInfo, 41 val allPermissions: Map<String, LightPermission>, 42 val hasInstallToRuntimeSplit: Boolean, 43 val specialLocationGrant: Boolean? 44 ) { 45 constructor( 46 pI: LightPackageInfo, 47 pGI: LightPermGroupInfo, 48 perms: Map<String, LightPermission> 49 ) : this(pI, pGI, perms, false, null) 50 51 /** 52 * All unrestricted permissions. Usually restricted permissions are ignored 53 */ 54 val permissions: Map<String, LightPermission> = 55 allPermissions.filter { (_, permission) -> !permission.isRestricted } 56 57 /** 58 * The package name of this group 59 */ 60 val packageName = packageInfo.packageName 61 62 /** 63 * The permission group name of this group 64 */ 65 val permGroupName = permGroupInfo.name 66 67 /** 68 * The current userHandle of this AppPermGroup. 69 */ 70 val userHandle: UserHandle = UserHandle.getUserHandleForUid(packageInfo.uid) 71 72 /** 73 * The names of all background permissions in the permission group which are requested by the 74 * package. 75 */ 76 val backgroundPermNames = permissions.mapNotNull { it.value.backgroundPermission } 77 78 /** 79 * All foreground permissions in the permission group which are requested by the package. 80 */ 81 val foregroundPermNames get() = permissions.mapNotNull { (name, _) -> 82 if (name !in backgroundPermNames) name else null 83 } 84 85 val foreground = AppPermSubGroup(permissions.filter { it.key in foregroundPermNames }, 86 packageInfo, specialLocationGrant) 87 88 val background = AppPermSubGroup(permissions.filter { it.key in backgroundPermNames }, 89 packageInfo, specialLocationGrant) 90 91 /** 92 * Whether or not this App Permission Group has a permission which has a background mode 93 */ 94 val hasPermWithBackgroundMode = backgroundPermNames.isNotEmpty() 95 96 /** 97 * Whether or not this App Permission Group requests a background permission 98 */ 99 val hasBackgroundGroup = backgroundPermNames.any { permissions.contains(it) } 100 101 /** 102 * Whether this App Permission Group's background and foreground permissions are fixed by policy 103 */ 104 val isPolicyFullyFixed = foreground.isPolicyFixed && (!hasBackgroundGroup || 105 background.isPolicyFixed) 106 107 /** 108 * Whether this App Permission Group's background permissions are fixed by the system or policy 109 */ 110 val isBackgroundFixed = background.isPolicyFixed || background.isSystemFixed 111 112 /** 113 * Whether this App Permission Group's foreground permissions are fixed by the system or policy 114 */ 115 val isForegroundFixed = foreground.isPolicyFixed || foreground.isSystemFixed 116 117 /** 118 * Whether or not this group supports runtime permissions 119 */ 120 val supportsRuntimePerms = packageInfo.targetSdkVersion >= Build.VERSION_CODES.M 121 122 /** 123 * Whether this App Permission Group is one-time. 2 cases: 124 * 1. If the perm group is not LOCATION, check if any of the permissions is one-time and none of 125 * the granted permissions are not one-time. 126 * 2. If the perm group is LOCATION, check if ACCESS_COARSE_LOCATION is one-time. 127 */ 128 val isOneTime = (permGroupName != Manifest.permission_group.LOCATION && 129 permissions.any { it.value.isOneTime } && 130 permissions.none { !it.value.isOneTime && it.value.isGrantedIncludingAppOp }) || 131 (permGroupName == Manifest.permission_group.LOCATION && 132 permissions[ACCESS_COARSE_LOCATION]?.isOneTime == true) 133 134 /** 135 * Whether any permissions in this group are granted by default (pregrant) 136 */ 137 val isGrantedByDefault = foreground.isGrantedByDefault || background.isGrantedByDefault 138 139 /** 140 * Whether any permissions in this group are granted by being a role holder 141 */ 142 val isGrantedByRole = foreground.isGrantedByRole || background.isGrantedByRole 143 144 /** 145 * Whether any of the permission (foreground/background) is fixed by the system 146 */ 147 val isSystemFixed = foreground.isSystemFixed || background.isSystemFixed 148 149 /** 150 * Whether any of the permission (foreground/background) in this group requires a review 151 */ 152 val isReviewRequired = foreground.isReviewRequired || background.isReviewRequired 153 154 /** 155 * Whether any of the permission (foreground/background) is granted in this permission group 156 */ 157 var isGranted = foreground.isGranted || background.isGranted 158 159 /** 160 * Whether any permissions in this group are user sensitive 161 */ 162 val isUserSensitive = permissions.any { it.value.isUserSensitive } 163 164 /** 165 * Whether any permissions in this group are revoke-when-requested 166 */ 167 val isRevokeWhenRequested = permissions.any { it.value.isRevokeWhenRequested } 168 169 /** 170 * Whether any of this App Permission Groups permissions are fixed by the user 171 */ 172 val isUserFixed = foreground.isUserFixed || background.isUserFixed 173 174 /** 175 * Whether any of this App Permission Group's permissions are set by the user 176 */ 177 val isUserSet = foreground.isUserSet || background.isUserSet 178 179 /** 180 * A subset of the AppPermissionGroup, representing either the background or foreground permissions 181 * of the full group. 182 * 183 * @param permissions The permissions contained within this subgroup, a subset of those contained 184 * in the full group 185 * @param specialLocationGrant Whether this is a special location package 186 */ 187 data class AppPermSubGroup internal constructor( 188 private val permissions: Map<String, LightPermission>, 189 private val packageInfo: LightPackageInfo, 190 private val specialLocationGrant: Boolean? 191 ) { 192 /** 193 * Whether any of this App Permission SubGroup's permissions are granted 194 */ 195 val isGranted = specialLocationGrant ?: permissions.any { it.value.isGrantedIncludingAppOp } 196 197 /** 198 * Whether this App Permission SubGroup should be treated as granted. This means either: 199 * 1) At least one permission was granted excluding auto-granted permissions (i.e., granted 200 * during install time with flag RevokeWhenRequested.) Or, 201 * 2) All permissions were auto-granted (all permissions are all granted and all 202 * RevokeWhenRequested.) 203 */ 204 val isGrantedExcludingRWROrAllRWR = specialLocationGrant ?: (permissions 205 .any { it.value.isGrantedIncludingAppOp && !it.value.isRevokeWhenRequested } || 206 permissions.all { it.value.isGrantedIncludingAppOp && it.value.isRevokeWhenRequested }) 207 208 /** 209 * Whether any of this App Permission SubGroup's permissions are granted by default 210 */ 211 val isGrantedByDefault = permissions.any { it.value.isGrantedByDefault } 212 213 /** 214 * Whether at least one of this App Permission SubGroup's permissions is one-time and 215 * none of the granted permissions are not one-time. 216 */ 217 val isOneTime = permissions.any { it.value.isOneTime } && 218 permissions.none { it.value.isGrantedIncludingAppOp && !it.value.isOneTime } 219 220 /** 221 * Whether any of this App Permission Subgroup's foreground permissions are fixed by policy 222 */ 223 val isPolicyFixed = permissions.any { it.value.isPolicyFixed } 224 225 /** 226 * Whether any of this App Permission Subgroup's permissions are fixed by the system 227 */ 228 val isSystemFixed = permissions.any { it.value.isSystemFixed } 229 230 /** 231 * Whether any of this App Permission Subgroup's permissions are fixed by the user 232 */ 233 val isUserFixed = permissions.any { it.value.isUserFixed } 234 235 /** 236 * Whether any of this App Permission Subgroup's permissions are set by the user 237 */ 238 val isUserSet = permissions.any { it.value.isUserSet } 239 240 /** 241 * whether review is required or not for the permission group 242 */ 243 val isReviewRequired = permissions.any { it.value.isReviewRequired } 244 245 /** 246 * Whether any of this App Permission Subgroup's permissions are set by the role of this app 247 */ 248 val isGrantedByRole = permissions.any { it.value.isGrantedByRole } 249 250 private val hasPreRuntimePerm = permissions.any { (_, perm) -> !perm.isRuntimeOnly } 251 252 private val hasInstantPerm = permissions.any { (_, perm) -> perm.isInstantPerm } 253 254 /** 255 * Whether or not any permissions in this App Permission Subgroup can be granted 256 */ 257 val isGrantable = (!packageInfo.isInstantApp || hasInstantPerm) && 258 (packageInfo.targetSdkVersion >= Build.VERSION_CODES.M || hasPreRuntimePerm) 259 } 260 }