1 /* 2 * Copyright (C) 2021 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.server.permission.access 18 19 import android.content.pm.PermissionGroupInfo 20 import com.android.server.SystemConfig 21 import com.android.server.permission.access.immutable.* // ktlint-disable no-wildcard-imports 22 import com.android.server.permission.access.permission.Permission 23 import com.android.server.pm.permission.PermissionAllowlist 24 import com.android.server.pm.pkg.PackageState 25 26 private typealias ExternalStateReference = MutableReference<ExternalState, MutableExternalState> 27 28 private typealias SystemStateReference = MutableReference<SystemState, MutableSystemState> 29 30 typealias UserStates = IntReferenceMap<UserState, MutableUserState> 31 32 typealias MutableUserStates = MutableIntReferenceMap<UserState, MutableUserState> 33 34 private typealias UserStatesReference = MutableReference<UserStates, MutableUserStates> 35 36 sealed class AccessState( 37 internal val externalStateReference: ExternalStateReference, 38 internal val systemStateReference: SystemStateReference, 39 internal val userStatesReference: UserStatesReference 40 ) : Immutable<MutableAccessState> { 41 val externalState: ExternalState 42 get() = externalStateReference.get() 43 44 val systemState: SystemState 45 get() = systemStateReference.get() 46 47 val userStates: UserStates 48 get() = userStatesReference.get() 49 toMutablenull50 override fun toMutable(): MutableAccessState = MutableAccessState(this) 51 } 52 53 class MutableAccessState 54 private constructor( 55 externalStateReference: ExternalStateReference, 56 systemStateReference: SystemStateReference, 57 userStatesReference: UserStatesReference 58 ) : AccessState(externalStateReference, systemStateReference, userStatesReference) { 59 constructor() : 60 this( 61 ExternalStateReference(MutableExternalState()), 62 SystemStateReference(MutableSystemState()), 63 UserStatesReference(MutableUserStates()) 64 ) 65 66 internal constructor( 67 accessState: AccessState 68 ) : this( 69 accessState.externalStateReference.toImmutable(), 70 accessState.systemStateReference.toImmutable(), 71 accessState.userStatesReference.toImmutable() 72 ) 73 74 fun mutateExternalState(): MutableExternalState = externalStateReference.mutate() 75 76 fun mutateSystemState(writeMode: Int = WriteMode.ASYNCHRONOUS): MutableSystemState = 77 systemStateReference.mutate().apply { requestWriteMode(writeMode) } 78 79 fun mutateUserStatesNoWrite(): MutableUserStates = userStatesReference.mutate() 80 81 fun mutateUserState(userId: Int, writeMode: Int = WriteMode.ASYNCHRONOUS): MutableUserState? = 82 mutateUserStatesNoWrite().mutate(userId)?.apply { requestWriteMode(writeMode) } 83 84 fun mutateUserStateAt(index: Int, writeMode: Int = WriteMode.ASYNCHRONOUS): MutableUserState = 85 mutateUserStatesNoWrite().mutateAt(index).apply { requestWriteMode(writeMode) } 86 } 87 88 private typealias UserIdsReference = MutableReference<IntSet, MutableIntSet> 89 90 typealias AppIdPackageNames = IntReferenceMap<IndexedListSet<String>, MutableIndexedListSet<String>> 91 92 typealias MutableAppIdPackageNames = 93 MutableIntReferenceMap<IndexedListSet<String>, MutableIndexedListSet<String>> 94 95 private typealias AppIdPackageNamesReference = 96 MutableReference<AppIdPackageNames, MutableAppIdPackageNames> 97 98 sealed class ExternalState( 99 val userIdsReference: UserIdsReference, 100 packageStates: Map<String, PackageState>, 101 disabledSystemPackageStates: Map<String, PackageState>, 102 val appIdPackageNamesReference: AppIdPackageNamesReference, 103 knownPackages: IntMap<Array<String>>, 104 isLeanback: Boolean, 105 configPermissions: Map<String, SystemConfig.PermissionEntry>, 106 privilegedPermissionAllowlistPackages: IndexedListSet<String>, 107 permissionAllowlist: PermissionAllowlist, 108 implicitToSourcePermissions: IndexedMap<String, IndexedListSet<String>>, 109 isSystemReady: Boolean 110 ) : Immutable<MutableExternalState> { 111 val userIds: IntSet 112 get() = userIdsReference.get() 113 114 var packageStates: Map<String, PackageState> = packageStates 115 protected set 116 117 var disabledSystemPackageStates: Map<String, PackageState> = disabledSystemPackageStates 118 protected set 119 120 val appIdPackageNames: AppIdPackageNames 121 get() = appIdPackageNamesReference.get() 122 123 var knownPackages: IntMap<Array<String>> = knownPackages 124 protected set 125 126 var isLeanback: Boolean = isLeanback 127 protected set 128 129 var configPermissions: Map<String, SystemConfig.PermissionEntry> = configPermissions 130 protected set 131 132 var privilegedPermissionAllowlistPackages: IndexedListSet<String> = 133 privilegedPermissionAllowlistPackages 134 protected set 135 136 var permissionAllowlist: PermissionAllowlist = permissionAllowlist 137 protected set 138 139 var implicitToSourcePermissions: IndexedMap<String, IndexedListSet<String>> = 140 implicitToSourcePermissions 141 protected set 142 143 var isSystemReady: Boolean = isSystemReady 144 protected set 145 toMutablenull146 override fun toMutable(): MutableExternalState = MutableExternalState(this) 147 } 148 149 class MutableExternalState 150 private constructor( 151 userIdsReference: UserIdsReference, 152 packageStates: Map<String, PackageState>, 153 disabledSystemPackageStates: Map<String, PackageState>, 154 appIdPackageNamesReference: AppIdPackageNamesReference, 155 knownPackages: IntMap<Array<String>>, 156 isLeanback: Boolean, 157 configPermissions: Map<String, SystemConfig.PermissionEntry>, 158 privilegedPermissionAllowlistPackages: IndexedListSet<String>, 159 permissionAllowlist: PermissionAllowlist, 160 implicitToSourcePermissions: IndexedMap<String, IndexedListSet<String>>, 161 isSystemReady: Boolean 162 ) : 163 ExternalState( 164 userIdsReference, 165 packageStates, 166 disabledSystemPackageStates, 167 appIdPackageNamesReference, 168 knownPackages, 169 isLeanback, 170 configPermissions, 171 privilegedPermissionAllowlistPackages, 172 permissionAllowlist, 173 implicitToSourcePermissions, 174 isSystemReady 175 ) { 176 constructor() : 177 this( 178 UserIdsReference(MutableIntSet()), 179 emptyMap(), 180 emptyMap(), 181 AppIdPackageNamesReference(MutableAppIdPackageNames()), 182 MutableIntMap(), 183 false, 184 emptyMap(), 185 MutableIndexedListSet(), 186 PermissionAllowlist(), 187 MutableIndexedMap(), 188 false 189 ) 190 191 internal constructor( 192 externalState: ExternalState 193 ) : this( 194 externalState.userIdsReference.toImmutable(), 195 externalState.packageStates, 196 externalState.disabledSystemPackageStates, 197 externalState.appIdPackageNamesReference.toImmutable(), 198 externalState.knownPackages, 199 externalState.isLeanback, 200 externalState.configPermissions, 201 externalState.privilegedPermissionAllowlistPackages, 202 externalState.permissionAllowlist, 203 externalState.implicitToSourcePermissions, 204 externalState.isSystemReady 205 ) 206 207 fun mutateUserIds(): MutableIntSet = userIdsReference.mutate() 208 209 @JvmName("setPackageStatesPublic") 210 fun setPackageStates(packageStates: Map<String, PackageState>) { 211 this.packageStates = packageStates 212 } 213 214 @JvmName("setDisabledSystemPackageStatesPublic") 215 fun setDisabledSystemPackageStates(disabledSystemPackageStates: Map<String, PackageState>) { 216 this.disabledSystemPackageStates = disabledSystemPackageStates 217 } 218 219 fun mutateAppIdPackageNames(): MutableAppIdPackageNames = appIdPackageNamesReference.mutate() 220 221 @JvmName("setKnownPackagesPublic") 222 fun setKnownPackages(knownPackages: IntMap<Array<String>>) { 223 this.knownPackages = knownPackages 224 } 225 226 @JvmName("setLeanbackPublic") 227 fun setLeanback(isLeanback: Boolean) { 228 this.isLeanback = isLeanback 229 } 230 231 @JvmName("setConfigPermissionsPublic") 232 fun setConfigPermissions(configPermissions: Map<String, SystemConfig.PermissionEntry>) { 233 this.configPermissions = configPermissions 234 } 235 236 @JvmName("setPrivilegedPermissionAllowlistPackagesPublic") 237 fun setPrivilegedPermissionAllowlistPackages( 238 privilegedPermissionAllowlistPackages: IndexedListSet<String> 239 ) { 240 this.privilegedPermissionAllowlistPackages = privilegedPermissionAllowlistPackages 241 } 242 243 @JvmName("setPermissionAllowlistPublic") 244 fun setPermissionAllowlist(permissionAllowlist: PermissionAllowlist) { 245 this.permissionAllowlist = permissionAllowlist 246 } 247 248 @JvmName("setImplicitToSourcePermissionsPublic") 249 fun setImplicitToSourcePermissions( 250 implicitToSourcePermissions: IndexedMap<String, IndexedListSet<String>> 251 ) { 252 this.implicitToSourcePermissions = implicitToSourcePermissions 253 } 254 255 @JvmName("setSystemReadyPublic") 256 fun setSystemReady(isSystemReady: Boolean) { 257 this.isSystemReady = isSystemReady 258 } 259 } 260 261 private typealias PermissionGroupsReference = 262 MutableReference< 263 IndexedMap<String, PermissionGroupInfo>, MutableIndexedMap<String, PermissionGroupInfo> 264 > 265 266 private typealias PermissionTreesReference = 267 MutableReference<IndexedMap<String, Permission>, MutableIndexedMap<String, Permission>> 268 269 private typealias PermissionsReference = 270 MutableReference<IndexedMap<String, Permission>, MutableIndexedMap<String, Permission>> 271 272 sealed class SystemState( 273 val permissionGroupsReference: PermissionGroupsReference, 274 val permissionTreesReference: PermissionTreesReference, 275 val permissionsReference: PermissionsReference, 276 writeMode: Int 277 ) : WritableState, Immutable<MutableSystemState> { 278 val permissionGroups: IndexedMap<String, PermissionGroupInfo> 279 get() = permissionGroupsReference.get() 280 281 val permissionTrees: IndexedMap<String, Permission> 282 get() = permissionTreesReference.get() 283 284 val permissions: IndexedMap<String, Permission> 285 get() = permissionsReference.get() 286 287 override var writeMode: Int = writeMode 288 protected set 289 toMutablenull290 override fun toMutable(): MutableSystemState = MutableSystemState(this) 291 } 292 293 class MutableSystemState 294 private constructor( 295 permissionGroupsReference: PermissionGroupsReference, 296 permissionTreesReference: PermissionTreesReference, 297 permissionsReference: PermissionsReference, 298 writeMode: Int 299 ) : 300 SystemState( 301 permissionGroupsReference, 302 permissionTreesReference, 303 permissionsReference, 304 writeMode 305 ), 306 MutableWritableState { 307 constructor() : 308 this( 309 PermissionGroupsReference(MutableIndexedMap()), 310 PermissionTreesReference(MutableIndexedMap()), 311 PermissionsReference(MutableIndexedMap()), 312 WriteMode.NONE 313 ) 314 315 internal constructor( 316 systemState: SystemState 317 ) : this( 318 systemState.permissionGroupsReference.toImmutable(), 319 systemState.permissionTreesReference.toImmutable(), 320 systemState.permissionsReference.toImmutable(), 321 WriteMode.NONE 322 ) 323 324 fun mutatePermissionGroups(): MutableIndexedMap<String, PermissionGroupInfo> = 325 permissionGroupsReference.mutate() 326 327 fun mutatePermissionTrees(): MutableIndexedMap<String, Permission> = 328 permissionTreesReference.mutate() 329 330 fun mutatePermissions(): MutableIndexedMap<String, Permission> = permissionsReference.mutate() 331 332 override fun requestWriteMode(writeMode: Int) { 333 this.writeMode = maxOf(this.writeMode, writeMode) 334 } 335 } 336 337 private typealias PackageVersionsReference = 338 MutableReference<IndexedMap<String, Int>, MutableIndexedMap<String, Int>> 339 340 typealias AppIdPermissionFlags = 341 IntReferenceMap<IndexedMap<String, Int>, MutableIndexedMap<String, Int>> 342 343 typealias MutableAppIdPermissionFlags = 344 MutableIntReferenceMap<IndexedMap<String, Int>, MutableIndexedMap<String, Int>> 345 346 private typealias AppIdPermissionFlagsReference = 347 MutableReference<AppIdPermissionFlags, MutableAppIdPermissionFlags> 348 349 typealias DevicePermissionFlags = 350 IndexedReferenceMap<String, IndexedMap<String, Int>, MutableIndexedMap<String, Int>> 351 352 typealias MutableDevicePermissionFlags = 353 MutableIndexedReferenceMap<String, IndexedMap<String, Int>, MutableIndexedMap<String, Int>> 354 355 typealias AppIdDevicePermissionFlags = 356 IntReferenceMap<DevicePermissionFlags, MutableDevicePermissionFlags> 357 358 typealias MutableAppIdDevicePermissionFlags = 359 MutableIntReferenceMap<DevicePermissionFlags, MutableDevicePermissionFlags> 360 361 private typealias AppIdDevicePermissionFlagsReference = 362 MutableReference<AppIdDevicePermissionFlags, MutableAppIdDevicePermissionFlags> 363 364 typealias AppIdAppOpModes = IntReferenceMap<IndexedMap<String, Int>, MutableIndexedMap<String, Int>> 365 366 typealias MutableAppIdAppOpModes = 367 MutableIntReferenceMap<IndexedMap<String, Int>, MutableIndexedMap<String, Int>> 368 369 private typealias AppIdAppOpModesReference = 370 MutableReference<AppIdAppOpModes, MutableAppIdAppOpModes> 371 372 typealias PackageAppOpModes = 373 IndexedReferenceMap<String, IndexedMap<String, Int>, MutableIndexedMap<String, Int>> 374 375 typealias MutablePackageAppOpModes = 376 MutableIndexedReferenceMap<String, IndexedMap<String, Int>, MutableIndexedMap<String, Int>> 377 378 private typealias PackageAppOpModesReference = 379 MutableReference<PackageAppOpModes, MutablePackageAppOpModes> 380 381 sealed class UserState( 382 internal val packageVersionsReference: PackageVersionsReference, 383 internal val appIdPermissionFlagsReference: AppIdPermissionFlagsReference, 384 internal val appIdDevicePermissionFlagsReference: AppIdDevicePermissionFlagsReference, 385 internal val appIdAppOpModesReference: AppIdAppOpModesReference, 386 internal val packageAppOpModesReference: PackageAppOpModesReference, 387 defaultPermissionGrantFingerprint: String?, 388 writeMode: Int 389 ) : WritableState, Immutable<MutableUserState> { 390 val packageVersions: IndexedMap<String, Int> 391 get() = packageVersionsReference.get() 392 393 val appIdPermissionFlags: AppIdPermissionFlags 394 get() = appIdPermissionFlagsReference.get() 395 396 val appIdDevicePermissionFlags: AppIdDevicePermissionFlags 397 get() = appIdDevicePermissionFlagsReference.get() 398 399 val appIdAppOpModes: AppIdAppOpModes 400 get() = appIdAppOpModesReference.get() 401 402 val packageAppOpModes: PackageAppOpModes 403 get() = packageAppOpModesReference.get() 404 405 var defaultPermissionGrantFingerprint: String? = defaultPermissionGrantFingerprint 406 protected set 407 408 override var writeMode: Int = writeMode 409 protected set 410 toMutablenull411 override fun toMutable(): MutableUserState = MutableUserState(this) 412 } 413 414 class MutableUserState 415 private constructor( 416 packageVersionsReference: PackageVersionsReference, 417 appIdPermissionFlagsReference: AppIdPermissionFlagsReference, 418 appIdDevicePermissionFlagsReference: AppIdDevicePermissionFlagsReference, 419 appIdAppOpModesReference: AppIdAppOpModesReference, 420 packageAppOpModesReference: PackageAppOpModesReference, 421 defaultPermissionGrantFingerprint: String?, 422 writeMode: Int 423 ) : 424 UserState( 425 packageVersionsReference, 426 appIdPermissionFlagsReference, 427 appIdDevicePermissionFlagsReference, 428 appIdAppOpModesReference, 429 packageAppOpModesReference, 430 defaultPermissionGrantFingerprint, 431 writeMode 432 ), 433 MutableWritableState { 434 constructor() : 435 this( 436 PackageVersionsReference(MutableIndexedMap<String, Int>()), 437 AppIdPermissionFlagsReference(MutableAppIdPermissionFlags()), 438 AppIdDevicePermissionFlagsReference(MutableAppIdDevicePermissionFlags()), 439 AppIdAppOpModesReference(MutableAppIdAppOpModes()), 440 PackageAppOpModesReference(MutablePackageAppOpModes()), 441 null, 442 WriteMode.NONE 443 ) 444 445 internal constructor( 446 userState: UserState 447 ) : this( 448 userState.packageVersionsReference.toImmutable(), 449 userState.appIdPermissionFlagsReference.toImmutable(), 450 userState.appIdDevicePermissionFlagsReference.toImmutable(), 451 userState.appIdAppOpModesReference.toImmutable(), 452 userState.packageAppOpModesReference.toImmutable(), 453 userState.defaultPermissionGrantFingerprint, 454 WriteMode.NONE 455 ) 456 457 fun mutatePackageVersions(): MutableIndexedMap<String, Int> = packageVersionsReference.mutate() 458 459 fun mutateAppIdPermissionFlags(): MutableAppIdPermissionFlags = 460 appIdPermissionFlagsReference.mutate() 461 462 fun mutateAppIdDevicePermissionFlags(): MutableAppIdDevicePermissionFlags = 463 appIdDevicePermissionFlagsReference.mutate() 464 465 fun mutateAppIdAppOpModes(): MutableAppIdAppOpModes = appIdAppOpModesReference.mutate() 466 467 fun mutatePackageAppOpModes(): MutablePackageAppOpModes = packageAppOpModesReference.mutate() 468 469 @JvmName("setDefaultPermissionGrantFingerprintPublic") 470 fun setDefaultPermissionGrantFingerprint(defaultPermissionGrantFingerprint: String?) { 471 this.defaultPermissionGrantFingerprint = defaultPermissionGrantFingerprint 472 } 473 474 override fun requestWriteMode(writeMode: Int) { 475 this.writeMode = maxOf(this.writeMode, writeMode) 476 } 477 } 478 479 object WriteMode { 480 const val NONE = 0 481 const val ASYNCHRONOUS = 1 482 const val SYNCHRONOUS = 2 483 } 484 485 interface WritableState { 486 val writeMode: Int 487 } 488 489 interface MutableWritableState : WritableState { requestWriteModenull490 fun requestWriteMode(writeMode: Int) 491 } 492 493 open class GetStateScope(val state: AccessState) 494 495 class MutateStateScope(val oldState: AccessState, val newState: MutableAccessState) : 496 GetStateScope(newState) 497