PackageManagerService.java revision d96953ad7ab13ec988585dcb93a2a3e2120b23f5
1/* 2 * Copyright (C) 2006 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 17package com.android.server.pm; 18 19import static android.Manifest.permission.DELETE_PACKAGES; 20import static android.Manifest.permission.INSTALL_PACKAGES; 21import static android.Manifest.permission.MANAGE_PROFILE_AND_DEVICE_OWNERS; 22import static android.Manifest.permission.READ_EXTERNAL_STORAGE; 23import static android.Manifest.permission.REQUEST_DELETE_PACKAGES; 24import static android.Manifest.permission.WRITE_EXTERNAL_STORAGE; 25import static android.Manifest.permission.WRITE_MEDIA_STORAGE; 26import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_DEFAULT; 27import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_DISABLED; 28import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED; 29import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_DISABLED_USER; 30import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_ENABLED; 31import static android.content.pm.PackageManager.DELETE_KEEP_DATA; 32import static android.content.pm.PackageManager.FLAG_PERMISSION_GRANTED_BY_DEFAULT; 33import static android.content.pm.PackageManager.FLAG_PERMISSION_POLICY_FIXED; 34import static android.content.pm.PackageManager.FLAG_PERMISSION_REVIEW_REQUIRED; 35import static android.content.pm.PackageManager.FLAG_PERMISSION_REVOKE_ON_UPGRADE; 36import static android.content.pm.PackageManager.FLAG_PERMISSION_SYSTEM_FIXED; 37import static android.content.pm.PackageManager.FLAG_PERMISSION_USER_FIXED; 38import static android.content.pm.PackageManager.FLAG_PERMISSION_USER_SET; 39import static android.content.pm.PackageManager.INSTALL_EXTERNAL; 40import static android.content.pm.PackageManager.INSTALL_FAILED_ALREADY_EXISTS; 41import static android.content.pm.PackageManager.INSTALL_FAILED_CONFLICTING_PROVIDER; 42import static android.content.pm.PackageManager.INSTALL_FAILED_DUPLICATE_PACKAGE; 43import static android.content.pm.PackageManager.INSTALL_FAILED_DUPLICATE_PERMISSION; 44import static android.content.pm.PackageManager.INSTALL_FAILED_INSTANT_APP_INVALID; 45import static android.content.pm.PackageManager.INSTALL_FAILED_INSUFFICIENT_STORAGE; 46import static android.content.pm.PackageManager.INSTALL_FAILED_INTERNAL_ERROR; 47import static android.content.pm.PackageManager.INSTALL_FAILED_INVALID_APK; 48import static android.content.pm.PackageManager.INSTALL_FAILED_INVALID_INSTALL_LOCATION; 49import static android.content.pm.PackageManager.INSTALL_FAILED_MISSING_SHARED_LIBRARY; 50import static android.content.pm.PackageManager.INSTALL_FAILED_PACKAGE_CHANGED; 51import static android.content.pm.PackageManager.INSTALL_FAILED_REPLACE_COULDNT_DELETE; 52import static android.content.pm.PackageManager.INSTALL_FAILED_SANDBOX_VERSION_DOWNGRADE; 53import static android.content.pm.PackageManager.INSTALL_FAILED_SHARED_USER_INCOMPATIBLE; 54import static android.content.pm.PackageManager.INSTALL_FAILED_TEST_ONLY; 55import static android.content.pm.PackageManager.INSTALL_FAILED_UPDATE_INCOMPATIBLE; 56import static android.content.pm.PackageManager.INSTALL_FAILED_USER_RESTRICTED; 57import static android.content.pm.PackageManager.INSTALL_FAILED_VERSION_DOWNGRADE; 58import static android.content.pm.PackageManager.INSTALL_FORWARD_LOCK; 59import static android.content.pm.PackageManager.INSTALL_INTERNAL; 60import static android.content.pm.PackageManager.INSTALL_PARSE_FAILED_INCONSISTENT_CERTIFICATES; 61import static android.content.pm.PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS; 62import static android.content.pm.PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS_ASK; 63import static android.content.pm.PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ASK; 64import static android.content.pm.PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_NEVER; 65import static android.content.pm.PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED; 66import static android.content.pm.PackageManager.MATCH_ALL; 67import static android.content.pm.PackageManager.MATCH_ANY_USER; 68import static android.content.pm.PackageManager.MATCH_DEBUG_TRIAGED_MISSING; 69import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_AWARE; 70import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_UNAWARE; 71import static android.content.pm.PackageManager.MATCH_DISABLED_COMPONENTS; 72import static android.content.pm.PackageManager.MATCH_FACTORY_ONLY; 73import static android.content.pm.PackageManager.MATCH_KNOWN_PACKAGES; 74import static android.content.pm.PackageManager.MATCH_SYSTEM_ONLY; 75import static android.content.pm.PackageManager.MATCH_UNINSTALLED_PACKAGES; 76import static android.content.pm.PackageManager.MOVE_FAILED_3RD_PARTY_NOT_ALLOWED_ON_INTERNAL; 77import static android.content.pm.PackageManager.MOVE_FAILED_DEVICE_ADMIN; 78import static android.content.pm.PackageManager.MOVE_FAILED_DOESNT_EXIST; 79import static android.content.pm.PackageManager.MOVE_FAILED_INTERNAL_ERROR; 80import static android.content.pm.PackageManager.MOVE_FAILED_LOCKED_USER; 81import static android.content.pm.PackageManager.MOVE_FAILED_OPERATION_PENDING; 82import static android.content.pm.PackageManager.MOVE_FAILED_SYSTEM_PACKAGE; 83import static android.content.pm.PackageManager.PERMISSION_DENIED; 84import static android.content.pm.PackageManager.PERMISSION_GRANTED; 85import static android.content.pm.PackageParser.PARSE_IS_PRIVILEGED; 86import static android.content.pm.PackageParser.isApkFile; 87import static android.os.Trace.TRACE_TAG_PACKAGE_MANAGER; 88import static android.os.storage.StorageManager.FLAG_STORAGE_CE; 89import static android.os.storage.StorageManager.FLAG_STORAGE_DE; 90import static android.system.OsConstants.O_CREAT; 91import static android.system.OsConstants.O_RDWR; 92 93import static com.android.internal.app.IntentForwarderActivity.FORWARD_INTENT_TO_MANAGED_PROFILE; 94import static com.android.internal.app.IntentForwarderActivity.FORWARD_INTENT_TO_PARENT; 95import static com.android.internal.content.NativeLibraryHelper.LIB64_DIR_NAME; 96import static com.android.internal.content.NativeLibraryHelper.LIB_DIR_NAME; 97import static com.android.internal.util.ArrayUtils.appendInt; 98import static com.android.server.pm.InstructionSets.getAppDexInstructionSets; 99import static com.android.server.pm.InstructionSets.getDexCodeInstructionSet; 100import static com.android.server.pm.InstructionSets.getDexCodeInstructionSets; 101import static com.android.server.pm.InstructionSets.getPreferredInstructionSet; 102import static com.android.server.pm.InstructionSets.getPrimaryInstructionSet; 103import static com.android.server.pm.PackageManagerServiceCompilerMapping.getCompilerFilterForReason; 104import static com.android.server.pm.PackageManagerServiceCompilerMapping.getDefaultCompilerFilter; 105import static com.android.server.pm.PermissionsState.PERMISSION_OPERATION_FAILURE; 106import static com.android.server.pm.PermissionsState.PERMISSION_OPERATION_SUCCESS; 107import static com.android.server.pm.PermissionsState.PERMISSION_OPERATION_SUCCESS_GIDS_CHANGED; 108 109import static dalvik.system.DexFile.getNonProfileGuidedCompilerFilter; 110 111import android.Manifest; 112import android.annotation.IntDef; 113import android.annotation.NonNull; 114import android.annotation.Nullable; 115import android.app.ActivityManager; 116import android.app.AppOpsManager; 117import android.app.IActivityManager; 118import android.app.ResourcesManager; 119import android.app.admin.IDevicePolicyManager; 120import android.app.admin.SecurityLog; 121import android.app.backup.IBackupManager; 122import android.content.BroadcastReceiver; 123import android.content.ComponentName; 124import android.content.ContentResolver; 125import android.content.Context; 126import android.content.IIntentReceiver; 127import android.content.Intent; 128import android.content.IntentFilter; 129import android.content.IntentSender; 130import android.content.IntentSender.SendIntentException; 131import android.content.ServiceConnection; 132import android.content.pm.ActivityInfo; 133import android.content.pm.ApplicationInfo; 134import android.content.pm.AppsQueryHelper; 135import android.content.pm.AuxiliaryResolveInfo; 136import android.content.pm.ChangedPackages; 137import android.content.pm.ComponentInfo; 138import android.content.pm.FallbackCategoryProvider; 139import android.content.pm.FeatureInfo; 140import android.content.pm.IDexModuleRegisterCallback; 141import android.content.pm.IOnPermissionsChangeListener; 142import android.content.pm.IPackageDataObserver; 143import android.content.pm.IPackageDeleteObserver; 144import android.content.pm.IPackageDeleteObserver2; 145import android.content.pm.IPackageInstallObserver2; 146import android.content.pm.IPackageInstaller; 147import android.content.pm.IPackageManager; 148import android.content.pm.IPackageManagerNative; 149import android.content.pm.IPackageMoveObserver; 150import android.content.pm.IPackageStatsObserver; 151import android.content.pm.InstantAppInfo; 152import android.content.pm.InstantAppRequest; 153import android.content.pm.InstantAppResolveInfo; 154import android.content.pm.InstrumentationInfo; 155import android.content.pm.IntentFilterVerificationInfo; 156import android.content.pm.KeySet; 157import android.content.pm.PackageCleanItem; 158import android.content.pm.PackageInfo; 159import android.content.pm.PackageInfoLite; 160import android.content.pm.PackageInstaller; 161import android.content.pm.PackageManager; 162import android.content.pm.PackageManager.LegacyPackageDeleteObserver; 163import android.content.pm.PackageManagerInternal; 164import android.content.pm.PackageParser; 165import android.content.pm.PackageParser.ActivityIntentInfo; 166import android.content.pm.PackageParser.PackageLite; 167import android.content.pm.PackageParser.PackageParserException; 168import android.content.pm.PackageStats; 169import android.content.pm.PackageUserState; 170import android.content.pm.ParceledListSlice; 171import android.content.pm.PermissionGroupInfo; 172import android.content.pm.PermissionInfo; 173import android.content.pm.ProviderInfo; 174import android.content.pm.ResolveInfo; 175import android.content.pm.ServiceInfo; 176import android.content.pm.SharedLibraryInfo; 177import android.content.pm.Signature; 178import android.content.pm.UserInfo; 179import android.content.pm.VerifierDeviceIdentity; 180import android.content.pm.VerifierInfo; 181import android.content.pm.VersionedPackage; 182import android.content.res.Resources; 183import android.database.ContentObserver; 184import android.graphics.Bitmap; 185import android.hardware.display.DisplayManager; 186import android.net.Uri; 187import android.os.Binder; 188import android.os.Build; 189import android.os.Bundle; 190import android.os.Debug; 191import android.os.Environment; 192import android.os.Environment.UserEnvironment; 193import android.os.FileUtils; 194import android.os.Handler; 195import android.os.IBinder; 196import android.os.Looper; 197import android.os.Message; 198import android.os.Parcel; 199import android.os.ParcelFileDescriptor; 200import android.os.PatternMatcher; 201import android.os.Process; 202import android.os.RemoteCallbackList; 203import android.os.RemoteException; 204import android.os.ResultReceiver; 205import android.os.SELinux; 206import android.os.ServiceManager; 207import android.os.ShellCallback; 208import android.os.SystemClock; 209import android.os.SystemProperties; 210import android.os.Trace; 211import android.os.UserHandle; 212import android.os.UserManager; 213import android.os.UserManagerInternal; 214import android.os.storage.IStorageManager; 215import android.os.storage.StorageEventListener; 216import android.os.storage.StorageManager; 217import android.os.storage.StorageManagerInternal; 218import android.os.storage.VolumeInfo; 219import android.os.storage.VolumeRecord; 220import android.provider.Settings.Global; 221import android.provider.Settings.Secure; 222import android.security.KeyStore; 223import android.security.SystemKeyStore; 224import android.service.pm.PackageServiceDumpProto; 225import android.system.ErrnoException; 226import android.system.Os; 227import android.text.TextUtils; 228import android.text.format.DateUtils; 229import android.util.ArrayMap; 230import android.util.ArraySet; 231import android.util.Base64; 232import android.util.TimingsTraceLog; 233import android.util.DisplayMetrics; 234import android.util.EventLog; 235import android.util.ExceptionUtils; 236import android.util.Log; 237import android.util.LogPrinter; 238import android.util.MathUtils; 239import android.util.PackageUtils; 240import android.util.Pair; 241import android.util.PrintStreamPrinter; 242import android.util.Slog; 243import android.util.SparseArray; 244import android.util.SparseBooleanArray; 245import android.util.SparseIntArray; 246import android.util.Xml; 247import android.util.jar.StrictJarFile; 248import android.util.proto.ProtoOutputStream; 249import android.view.Display; 250 251import com.android.internal.R; 252import com.android.internal.annotations.GuardedBy; 253import com.android.internal.app.IMediaContainerService; 254import com.android.internal.app.ResolverActivity; 255import com.android.internal.content.NativeLibraryHelper; 256import com.android.internal.content.PackageHelper; 257import com.android.internal.logging.MetricsLogger; 258import com.android.internal.logging.nano.MetricsProto.MetricsEvent; 259import com.android.internal.os.IParcelFileDescriptorFactory; 260import com.android.internal.os.RoSystemProperties; 261import com.android.internal.os.SomeArgs; 262import com.android.internal.os.Zygote; 263import com.android.internal.telephony.CarrierAppUtils; 264import com.android.internal.util.ArrayUtils; 265import com.android.internal.util.ConcurrentUtils; 266import com.android.internal.util.DumpUtils; 267import com.android.internal.util.FastPrintWriter; 268import com.android.internal.util.FastXmlSerializer; 269import com.android.internal.util.IndentingPrintWriter; 270import com.android.internal.util.Preconditions; 271import com.android.internal.util.XmlUtils; 272import com.android.server.AttributeCache; 273import com.android.server.DeviceIdleController; 274import com.android.server.EventLogTags; 275import com.android.server.FgThread; 276import com.android.server.IntentResolver; 277import com.android.server.LocalServices; 278import com.android.server.LockGuard; 279import com.android.server.ServiceThread; 280import com.android.server.SystemConfig; 281import com.android.server.SystemServerInitThreadPool; 282import com.android.server.Watchdog; 283import com.android.server.net.NetworkPolicyManagerInternal; 284import com.android.server.pm.Installer.InstallerException; 285import com.android.server.pm.PermissionsState.PermissionState; 286import com.android.server.pm.Settings.DatabaseVersion; 287import com.android.server.pm.Settings.VersionInfo; 288import com.android.server.pm.dex.DexManager; 289import com.android.server.pm.dex.DexoptOptions; 290import com.android.server.pm.dex.PackageDexUsage; 291import com.android.server.storage.DeviceStorageMonitorInternal; 292 293import dalvik.system.CloseGuard; 294import dalvik.system.DexFile; 295import dalvik.system.VMRuntime; 296 297import libcore.io.IoUtils; 298import libcore.io.Streams; 299import libcore.util.EmptyArray; 300 301import org.xmlpull.v1.XmlPullParser; 302import org.xmlpull.v1.XmlPullParserException; 303import org.xmlpull.v1.XmlSerializer; 304 305import java.io.BufferedOutputStream; 306import java.io.BufferedReader; 307import java.io.ByteArrayInputStream; 308import java.io.ByteArrayOutputStream; 309import java.io.File; 310import java.io.FileDescriptor; 311import java.io.FileInputStream; 312import java.io.FileOutputStream; 313import java.io.FileReader; 314import java.io.FilenameFilter; 315import java.io.IOException; 316import java.io.InputStream; 317import java.io.OutputStream; 318import java.io.PrintWriter; 319import java.lang.annotation.Retention; 320import java.lang.annotation.RetentionPolicy; 321import java.nio.charset.StandardCharsets; 322import java.security.DigestInputStream; 323import java.security.MessageDigest; 324import java.security.NoSuchAlgorithmException; 325import java.security.PublicKey; 326import java.security.SecureRandom; 327import java.security.cert.Certificate; 328import java.security.cert.CertificateEncodingException; 329import java.security.cert.CertificateException; 330import java.text.SimpleDateFormat; 331import java.util.ArrayList; 332import java.util.Arrays; 333import java.util.Collection; 334import java.util.Collections; 335import java.util.Comparator; 336import java.util.Date; 337import java.util.HashMap; 338import java.util.HashSet; 339import java.util.Iterator; 340import java.util.List; 341import java.util.Map; 342import java.util.Objects; 343import java.util.Set; 344import java.util.concurrent.CountDownLatch; 345import java.util.concurrent.Future; 346import java.util.concurrent.TimeUnit; 347import java.util.concurrent.atomic.AtomicBoolean; 348import java.util.concurrent.atomic.AtomicInteger; 349import java.util.zip.GZIPInputStream; 350 351/** 352 * Keep track of all those APKs everywhere. 353 * <p> 354 * Internally there are two important locks: 355 * <ul> 356 * <li>{@link #mPackages} is used to guard all in-memory parsed package details 357 * and other related state. It is a fine-grained lock that should only be held 358 * momentarily, as it's one of the most contended locks in the system. 359 * <li>{@link #mInstallLock} is used to guard all {@code installd} access, whose 360 * operations typically involve heavy lifting of application data on disk. Since 361 * {@code installd} is single-threaded, and it's operations can often be slow, 362 * this lock should never be acquired while already holding {@link #mPackages}. 363 * Conversely, it's safe to acquire {@link #mPackages} momentarily while already 364 * holding {@link #mInstallLock}. 365 * </ul> 366 * Many internal methods rely on the caller to hold the appropriate locks, and 367 * this contract is expressed through method name suffixes: 368 * <ul> 369 * <li>fooLI(): the caller must hold {@link #mInstallLock} 370 * <li>fooLIF(): the caller must hold {@link #mInstallLock} and the package 371 * being modified must be frozen 372 * <li>fooLPr(): the caller must hold {@link #mPackages} for reading 373 * <li>fooLPw(): the caller must hold {@link #mPackages} for writing 374 * </ul> 375 * <p> 376 * Because this class is very central to the platform's security; please run all 377 * CTS and unit tests whenever making modifications: 378 * 379 * <pre> 380 * $ runtest -c android.content.pm.PackageManagerTests frameworks-core 381 * $ cts-tradefed run commandAndExit cts -m CtsAppSecurityHostTestCases 382 * </pre> 383 */ 384public class PackageManagerService extends IPackageManager.Stub 385 implements PackageSender { 386 static final String TAG = "PackageManager"; 387 static final boolean DEBUG_SETTINGS = false; 388 static final boolean DEBUG_PREFERRED = false; 389 static final boolean DEBUG_UPGRADE = false; 390 static final boolean DEBUG_DOMAIN_VERIFICATION = false; 391 private static final boolean DEBUG_BACKUP = false; 392 private static final boolean DEBUG_INSTALL = false; 393 private static final boolean DEBUG_REMOVE = false; 394 private static final boolean DEBUG_BROADCASTS = false; 395 private static final boolean DEBUG_SHOW_INFO = false; 396 private static final boolean DEBUG_PACKAGE_INFO = false; 397 private static final boolean DEBUG_INTENT_MATCHING = false; 398 private static final boolean DEBUG_PACKAGE_SCANNING = false; 399 private static final boolean DEBUG_VERIFY = false; 400 private static final boolean DEBUG_FILTERS = false; 401 private static final boolean DEBUG_PERMISSIONS = false; 402 private static final boolean DEBUG_SHARED_LIBRARIES = false; 403 private static final boolean DEBUG_COMPRESSION = Build.IS_DEBUGGABLE; 404 405 // Debug output for dexopting. This is shared between PackageManagerService, OtaDexoptService 406 // and PackageDexOptimizer. All these classes have their own flag to allow switching a single 407 // user, but by default initialize to this. 408 public static final boolean DEBUG_DEXOPT = false; 409 410 private static final boolean DEBUG_ABI_SELECTION = false; 411 private static final boolean DEBUG_EPHEMERAL = Build.IS_DEBUGGABLE; 412 private static final boolean DEBUG_TRIAGED_MISSING = false; 413 private static final boolean DEBUG_APP_DATA = false; 414 415 /** REMOVE. According to Svet, this was only used to reset permissions during development. */ 416 static final boolean CLEAR_RUNTIME_PERMISSIONS_ON_UPGRADE = false; 417 418 private static final boolean HIDE_EPHEMERAL_APIS = false; 419 420 private static final boolean ENABLE_FREE_CACHE_V2 = 421 SystemProperties.getBoolean("fw.free_cache_v2", true); 422 423 private static final int RADIO_UID = Process.PHONE_UID; 424 private static final int LOG_UID = Process.LOG_UID; 425 private static final int NFC_UID = Process.NFC_UID; 426 private static final int BLUETOOTH_UID = Process.BLUETOOTH_UID; 427 private static final int SHELL_UID = Process.SHELL_UID; 428 429 // Cap the size of permission trees that 3rd party apps can define 430 private static final int MAX_PERMISSION_TREE_FOOTPRINT = 32768; // characters of text 431 432 // Suffix used during package installation when copying/moving 433 // package apks to install directory. 434 private static final String INSTALL_PACKAGE_SUFFIX = "-"; 435 436 static final int SCAN_NO_DEX = 1<<1; 437 static final int SCAN_FORCE_DEX = 1<<2; 438 static final int SCAN_UPDATE_SIGNATURE = 1<<3; 439 static final int SCAN_NEW_INSTALL = 1<<4; 440 static final int SCAN_UPDATE_TIME = 1<<5; 441 static final int SCAN_BOOTING = 1<<6; 442 static final int SCAN_TRUSTED_OVERLAY = 1<<7; 443 static final int SCAN_DELETE_DATA_ON_FAILURES = 1<<8; 444 static final int SCAN_REPLACING = 1<<9; 445 static final int SCAN_REQUIRE_KNOWN = 1<<10; 446 static final int SCAN_MOVE = 1<<11; 447 static final int SCAN_INITIAL = 1<<12; 448 static final int SCAN_CHECK_ONLY = 1<<13; 449 static final int SCAN_DONT_KILL_APP = 1<<14; 450 static final int SCAN_IGNORE_FROZEN = 1<<15; 451 static final int SCAN_FIRST_BOOT_OR_UPGRADE = 1<<16; 452 static final int SCAN_AS_INSTANT_APP = 1<<17; 453 static final int SCAN_AS_FULL_APP = 1<<18; 454 static final int SCAN_AS_VIRTUAL_PRELOAD = 1<<19; 455 /** Should not be with the scan flags */ 456 static final int FLAGS_REMOVE_CHATTY = 1<<31; 457 458 private static final String STATIC_SHARED_LIB_DELIMITER = "_"; 459 /** Extension of the compressed packages */ 460 private final static String COMPRESSED_EXTENSION = ".gz"; 461 /** Suffix of stub packages on the system partition */ 462 private final static String STUB_SUFFIX = "-Stub"; 463 464 private static final int[] EMPTY_INT_ARRAY = new int[0]; 465 466 private static final int TYPE_UNKNOWN = 0; 467 private static final int TYPE_ACTIVITY = 1; 468 private static final int TYPE_RECEIVER = 2; 469 private static final int TYPE_SERVICE = 3; 470 private static final int TYPE_PROVIDER = 4; 471 @IntDef(prefix = { "TYPE_" }, value = { 472 TYPE_UNKNOWN, 473 TYPE_ACTIVITY, 474 TYPE_RECEIVER, 475 TYPE_SERVICE, 476 TYPE_PROVIDER, 477 }) 478 @Retention(RetentionPolicy.SOURCE) 479 public @interface ComponentType {} 480 481 /** 482 * Timeout (in milliseconds) after which the watchdog should declare that 483 * our handler thread is wedged. The usual default for such things is one 484 * minute but we sometimes do very lengthy I/O operations on this thread, 485 * such as installing multi-gigabyte applications, so ours needs to be longer. 486 */ 487 static final long WATCHDOG_TIMEOUT = 1000*60*10; // ten minutes 488 489 /** 490 * Wall-clock timeout (in milliseconds) after which we *require* that an fstrim 491 * be run on this device. We use the value in the Settings.Global.MANDATORY_FSTRIM_INTERVAL 492 * settings entry if available, otherwise we use the hardcoded default. If it's been 493 * more than this long since the last fstrim, we force one during the boot sequence. 494 * 495 * This backstops other fstrim scheduling: if the device is alive at midnight+idle, 496 * one gets run at the next available charging+idle time. This final mandatory 497 * no-fstrim check kicks in only of the other scheduling criteria is never met. 498 */ 499 private static final long DEFAULT_MANDATORY_FSTRIM_INTERVAL = 3 * DateUtils.DAY_IN_MILLIS; 500 501 /** 502 * Whether verification is enabled by default. 503 */ 504 private static final boolean DEFAULT_VERIFY_ENABLE = true; 505 506 /** 507 * The default maximum time to wait for the verification agent to return in 508 * milliseconds. 509 */ 510 private static final long DEFAULT_VERIFICATION_TIMEOUT = 10 * 1000; 511 512 /** 513 * The default response for package verification timeout. 514 * 515 * This can be either PackageManager.VERIFICATION_ALLOW or 516 * PackageManager.VERIFICATION_REJECT. 517 */ 518 private static final int DEFAULT_VERIFICATION_RESPONSE = PackageManager.VERIFICATION_ALLOW; 519 520 static final String PLATFORM_PACKAGE_NAME = "android"; 521 522 static final String DEFAULT_CONTAINER_PACKAGE = "com.android.defcontainer"; 523 524 static final ComponentName DEFAULT_CONTAINER_COMPONENT = new ComponentName( 525 DEFAULT_CONTAINER_PACKAGE, 526 "com.android.defcontainer.DefaultContainerService"); 527 528 private static final String KILL_APP_REASON_GIDS_CHANGED = 529 "permission grant or revoke changed gids"; 530 531 private static final String KILL_APP_REASON_PERMISSIONS_REVOKED = 532 "permissions revoked"; 533 534 private static final String PACKAGE_MIME_TYPE = "application/vnd.android.package-archive"; 535 536 private static final String PACKAGE_SCHEME = "package"; 537 538 private static final String VENDOR_OVERLAY_DIR = "/vendor/overlay"; 539 540 /** Permission grant: not grant the permission. */ 541 private static final int GRANT_DENIED = 1; 542 543 /** Permission grant: grant the permission as an install permission. */ 544 private static final int GRANT_INSTALL = 2; 545 546 /** Permission grant: grant the permission as a runtime one. */ 547 private static final int GRANT_RUNTIME = 3; 548 549 /** Permission grant: grant as runtime a permission that was granted as an install time one. */ 550 private static final int GRANT_UPGRADE = 4; 551 552 /** Canonical intent used to identify what counts as a "web browser" app */ 553 private static final Intent sBrowserIntent; 554 static { 555 sBrowserIntent = new Intent(); 556 sBrowserIntent.setAction(Intent.ACTION_VIEW); 557 sBrowserIntent.addCategory(Intent.CATEGORY_BROWSABLE); 558 sBrowserIntent.setData(Uri.parse("http:")); 559 } 560 561 /** 562 * The set of all protected actions [i.e. those actions for which a high priority 563 * intent filter is disallowed]. 564 */ 565 private static final Set<String> PROTECTED_ACTIONS = new ArraySet<>(); 566 static { 567 PROTECTED_ACTIONS.add(Intent.ACTION_SEND); 568 PROTECTED_ACTIONS.add(Intent.ACTION_SENDTO); 569 PROTECTED_ACTIONS.add(Intent.ACTION_SEND_MULTIPLE); 570 PROTECTED_ACTIONS.add(Intent.ACTION_VIEW); 571 } 572 573 // Compilation reasons. 574 public static final int REASON_FIRST_BOOT = 0; 575 public static final int REASON_BOOT = 1; 576 public static final int REASON_INSTALL = 2; 577 public static final int REASON_BACKGROUND_DEXOPT = 3; 578 public static final int REASON_AB_OTA = 4; 579 public static final int REASON_INACTIVE_PACKAGE_DOWNGRADE = 5; 580 public static final int REASON_SHARED = 6; 581 582 public static final int REASON_LAST = REASON_SHARED; 583 584 /** All dangerous permission names in the same order as the events in MetricsEvent */ 585 private static final List<String> ALL_DANGEROUS_PERMISSIONS = Arrays.asList( 586 Manifest.permission.READ_CALENDAR, 587 Manifest.permission.WRITE_CALENDAR, 588 Manifest.permission.CAMERA, 589 Manifest.permission.READ_CONTACTS, 590 Manifest.permission.WRITE_CONTACTS, 591 Manifest.permission.GET_ACCOUNTS, 592 Manifest.permission.ACCESS_FINE_LOCATION, 593 Manifest.permission.ACCESS_COARSE_LOCATION, 594 Manifest.permission.RECORD_AUDIO, 595 Manifest.permission.READ_PHONE_STATE, 596 Manifest.permission.CALL_PHONE, 597 Manifest.permission.READ_CALL_LOG, 598 Manifest.permission.WRITE_CALL_LOG, 599 Manifest.permission.ADD_VOICEMAIL, 600 Manifest.permission.USE_SIP, 601 Manifest.permission.PROCESS_OUTGOING_CALLS, 602 Manifest.permission.READ_CELL_BROADCASTS, 603 Manifest.permission.BODY_SENSORS, 604 Manifest.permission.SEND_SMS, 605 Manifest.permission.RECEIVE_SMS, 606 Manifest.permission.READ_SMS, 607 Manifest.permission.RECEIVE_WAP_PUSH, 608 Manifest.permission.RECEIVE_MMS, 609 Manifest.permission.READ_EXTERNAL_STORAGE, 610 Manifest.permission.WRITE_EXTERNAL_STORAGE, 611 Manifest.permission.READ_PHONE_NUMBERS, 612 Manifest.permission.ANSWER_PHONE_CALLS); 613 614 615 /** 616 * Version number for the package parser cache. Increment this whenever the format or 617 * extent of cached data changes. See {@code PackageParser#setCacheDir}. 618 */ 619 private static final String PACKAGE_PARSER_CACHE_VERSION = "1"; 620 621 /** 622 * Whether the package parser cache is enabled. 623 */ 624 private static final boolean DEFAULT_PACKAGE_PARSER_CACHE_ENABLED = true; 625 626 final ServiceThread mHandlerThread; 627 628 final PackageHandler mHandler; 629 630 private final ProcessLoggingHandler mProcessLoggingHandler; 631 632 /** 633 * Messages for {@link #mHandler} that need to wait for system ready before 634 * being dispatched. 635 */ 636 private ArrayList<Message> mPostSystemReadyMessages; 637 638 final int mSdkVersion = Build.VERSION.SDK_INT; 639 640 final Context mContext; 641 final boolean mFactoryTest; 642 final boolean mOnlyCore; 643 final DisplayMetrics mMetrics; 644 final int mDefParseFlags; 645 final String[] mSeparateProcesses; 646 final boolean mIsUpgrade; 647 final boolean mIsPreNUpgrade; 648 final boolean mIsPreNMR1Upgrade; 649 650 // Have we told the Activity Manager to whitelist the default container service by uid yet? 651 @GuardedBy("mPackages") 652 boolean mDefaultContainerWhitelisted = false; 653 654 @GuardedBy("mPackages") 655 private boolean mDexOptDialogShown; 656 657 /** The location for ASEC container files on internal storage. */ 658 final String mAsecInternalPath; 659 660 // Used for privilege escalation. MUST NOT BE CALLED WITH mPackages 661 // LOCK HELD. Can be called with mInstallLock held. 662 @GuardedBy("mInstallLock") 663 final Installer mInstaller; 664 665 /** Directory where installed third-party apps stored */ 666 final File mAppInstallDir; 667 668 /** 669 * Directory to which applications installed internally have their 670 * 32 bit native libraries copied. 671 */ 672 private File mAppLib32InstallDir; 673 674 // Directory containing the private parts (e.g. code and non-resource assets) of forward-locked 675 // apps. 676 final File mDrmAppPrivateInstallDir; 677 678 // ---------------------------------------------------------------- 679 680 // Lock for state used when installing and doing other long running 681 // operations. Methods that must be called with this lock held have 682 // the suffix "LI". 683 final Object mInstallLock = new Object(); 684 685 // ---------------------------------------------------------------- 686 687 // Keys are String (package name), values are Package. This also serves 688 // as the lock for the global state. Methods that must be called with 689 // this lock held have the prefix "LP". 690 @GuardedBy("mPackages") 691 final ArrayMap<String, PackageParser.Package> mPackages = 692 new ArrayMap<String, PackageParser.Package>(); 693 694 final ArrayMap<String, Set<String>> mKnownCodebase = 695 new ArrayMap<String, Set<String>>(); 696 697 // Keys are isolated uids and values are the uid of the application 698 // that created the isolated proccess. 699 @GuardedBy("mPackages") 700 final SparseIntArray mIsolatedOwners = new SparseIntArray(); 701 702 /** 703 * Tracks new system packages [received in an OTA] that we expect to 704 * find updated user-installed versions. Keys are package name, values 705 * are package location. 706 */ 707 final private ArrayMap<String, File> mExpectingBetter = new ArrayMap<>(); 708 /** 709 * Tracks high priority intent filters for protected actions. During boot, certain 710 * filter actions are protected and should never be allowed to have a high priority 711 * intent filter for them. However, there is one, and only one exception -- the 712 * setup wizard. It must be able to define a high priority intent filter for these 713 * actions to ensure there are no escapes from the wizard. We need to delay processing 714 * of these during boot as we need to look at all of the system packages in order 715 * to know which component is the setup wizard. 716 */ 717 private final List<PackageParser.ActivityIntentInfo> mProtectedFilters = new ArrayList<>(); 718 /** 719 * Whether or not processing protected filters should be deferred. 720 */ 721 private boolean mDeferProtectedFilters = true; 722 723 /** 724 * Tracks existing system packages prior to receiving an OTA. Keys are package name. 725 */ 726 final private ArraySet<String> mExistingSystemPackages = new ArraySet<>(); 727 /** 728 * Whether or not system app permissions should be promoted from install to runtime. 729 */ 730 boolean mPromoteSystemApps; 731 732 @GuardedBy("mPackages") 733 final Settings mSettings; 734 735 /** 736 * Set of package names that are currently "frozen", which means active 737 * surgery is being done on the code/data for that package. The platform 738 * will refuse to launch frozen packages to avoid race conditions. 739 * 740 * @see PackageFreezer 741 */ 742 @GuardedBy("mPackages") 743 final ArraySet<String> mFrozenPackages = new ArraySet<>(); 744 745 final ProtectedPackages mProtectedPackages; 746 747 @GuardedBy("mLoadedVolumes") 748 final ArraySet<String> mLoadedVolumes = new ArraySet<>(); 749 750 boolean mFirstBoot; 751 752 PackageManagerInternal.ExternalSourcesPolicy mExternalSourcesPolicy; 753 754 // System configuration read by SystemConfig. 755 final int[] mGlobalGids; 756 final SparseArray<ArraySet<String>> mSystemPermissions; 757 @GuardedBy("mAvailableFeatures") 758 final ArrayMap<String, FeatureInfo> mAvailableFeatures; 759 760 // If mac_permissions.xml was found for seinfo labeling. 761 boolean mFoundPolicyFile; 762 763 private final InstantAppRegistry mInstantAppRegistry; 764 765 @GuardedBy("mPackages") 766 int mChangedPackagesSequenceNumber; 767 /** 768 * List of changed [installed, removed or updated] packages. 769 * mapping from user id -> sequence number -> package name 770 */ 771 @GuardedBy("mPackages") 772 final SparseArray<SparseArray<String>> mChangedPackages = new SparseArray<>(); 773 /** 774 * The sequence number of the last change to a package. 775 * mapping from user id -> package name -> sequence number 776 */ 777 @GuardedBy("mPackages") 778 final SparseArray<Map<String, Integer>> mChangedPackagesSequenceNumbers = new SparseArray<>(); 779 780 class PackageParserCallback implements PackageParser.Callback { 781 @Override public final boolean hasFeature(String feature) { 782 return PackageManagerService.this.hasSystemFeature(feature, 0); 783 } 784 785 final List<PackageParser.Package> getStaticOverlayPackagesLocked( 786 Collection<PackageParser.Package> allPackages, String targetPackageName) { 787 List<PackageParser.Package> overlayPackages = null; 788 for (PackageParser.Package p : allPackages) { 789 if (targetPackageName.equals(p.mOverlayTarget) && p.mIsStaticOverlay) { 790 if (overlayPackages == null) { 791 overlayPackages = new ArrayList<PackageParser.Package>(); 792 } 793 overlayPackages.add(p); 794 } 795 } 796 if (overlayPackages != null) { 797 Comparator<PackageParser.Package> cmp = new Comparator<PackageParser.Package>() { 798 public int compare(PackageParser.Package p1, PackageParser.Package p2) { 799 return p1.mOverlayPriority - p2.mOverlayPriority; 800 } 801 }; 802 Collections.sort(overlayPackages, cmp); 803 } 804 return overlayPackages; 805 } 806 807 final String[] getStaticOverlayPathsLocked(Collection<PackageParser.Package> allPackages, 808 String targetPackageName, String targetPath) { 809 if ("android".equals(targetPackageName)) { 810 // Static RROs targeting to "android", ie framework-res.apk, are already applied by 811 // native AssetManager. 812 return null; 813 } 814 List<PackageParser.Package> overlayPackages = 815 getStaticOverlayPackagesLocked(allPackages, targetPackageName); 816 if (overlayPackages == null || overlayPackages.isEmpty()) { 817 return null; 818 } 819 List<String> overlayPathList = null; 820 for (PackageParser.Package overlayPackage : overlayPackages) { 821 if (targetPath == null) { 822 if (overlayPathList == null) { 823 overlayPathList = new ArrayList<String>(); 824 } 825 overlayPathList.add(overlayPackage.baseCodePath); 826 continue; 827 } 828 829 try { 830 // Creates idmaps for system to parse correctly the Android manifest of the 831 // target package. 832 // 833 // OverlayManagerService will update each of them with a correct gid from its 834 // target package app id. 835 mInstaller.idmap(targetPath, overlayPackage.baseCodePath, 836 UserHandle.getSharedAppGid( 837 UserHandle.getUserGid(UserHandle.USER_SYSTEM))); 838 if (overlayPathList == null) { 839 overlayPathList = new ArrayList<String>(); 840 } 841 overlayPathList.add(overlayPackage.baseCodePath); 842 } catch (InstallerException e) { 843 Slog.e(TAG, "Failed to generate idmap for " + targetPath + " and " + 844 overlayPackage.baseCodePath); 845 } 846 } 847 return overlayPathList == null ? null : overlayPathList.toArray(new String[0]); 848 } 849 850 String[] getStaticOverlayPaths(String targetPackageName, String targetPath) { 851 synchronized (mPackages) { 852 return getStaticOverlayPathsLocked( 853 mPackages.values(), targetPackageName, targetPath); 854 } 855 } 856 857 @Override public final String[] getOverlayApks(String targetPackageName) { 858 return getStaticOverlayPaths(targetPackageName, null); 859 } 860 861 @Override public final String[] getOverlayPaths(String targetPackageName, 862 String targetPath) { 863 return getStaticOverlayPaths(targetPackageName, targetPath); 864 } 865 }; 866 867 class ParallelPackageParserCallback extends PackageParserCallback { 868 List<PackageParser.Package> mOverlayPackages = null; 869 870 void findStaticOverlayPackages() { 871 synchronized (mPackages) { 872 for (PackageParser.Package p : mPackages.values()) { 873 if (p.mIsStaticOverlay) { 874 if (mOverlayPackages == null) { 875 mOverlayPackages = new ArrayList<PackageParser.Package>(); 876 } 877 mOverlayPackages.add(p); 878 } 879 } 880 } 881 } 882 883 @Override 884 synchronized String[] getStaticOverlayPaths(String targetPackageName, String targetPath) { 885 // We can trust mOverlayPackages without holding mPackages because package uninstall 886 // can't happen while running parallel parsing. 887 // Moreover holding mPackages on each parsing thread causes dead-lock. 888 return mOverlayPackages == null ? null : 889 getStaticOverlayPathsLocked(mOverlayPackages, targetPackageName, targetPath); 890 } 891 } 892 893 final PackageParser.Callback mPackageParserCallback = new PackageParserCallback(); 894 final ParallelPackageParserCallback mParallelPackageParserCallback = 895 new ParallelPackageParserCallback(); 896 897 public static final class SharedLibraryEntry { 898 public final @Nullable String path; 899 public final @Nullable String apk; 900 public final @NonNull SharedLibraryInfo info; 901 902 SharedLibraryEntry(String _path, String _apk, String name, int version, int type, 903 String declaringPackageName, int declaringPackageVersionCode) { 904 path = _path; 905 apk = _apk; 906 info = new SharedLibraryInfo(name, version, type, new VersionedPackage( 907 declaringPackageName, declaringPackageVersionCode), null); 908 } 909 } 910 911 // Currently known shared libraries. 912 final ArrayMap<String, SparseArray<SharedLibraryEntry>> mSharedLibraries = new ArrayMap<>(); 913 final ArrayMap<String, SparseArray<SharedLibraryEntry>> mStaticLibsByDeclaringPackage = 914 new ArrayMap<>(); 915 916 // All available activities, for your resolving pleasure. 917 final ActivityIntentResolver mActivities = 918 new ActivityIntentResolver(); 919 920 // All available receivers, for your resolving pleasure. 921 final ActivityIntentResolver mReceivers = 922 new ActivityIntentResolver(); 923 924 // All available services, for your resolving pleasure. 925 final ServiceIntentResolver mServices = new ServiceIntentResolver(); 926 927 // All available providers, for your resolving pleasure. 928 final ProviderIntentResolver mProviders = new ProviderIntentResolver(); 929 930 // Mapping from provider base names (first directory in content URI codePath) 931 // to the provider information. 932 final ArrayMap<String, PackageParser.Provider> mProvidersByAuthority = 933 new ArrayMap<String, PackageParser.Provider>(); 934 935 // Mapping from instrumentation class names to info about them. 936 final ArrayMap<ComponentName, PackageParser.Instrumentation> mInstrumentation = 937 new ArrayMap<ComponentName, PackageParser.Instrumentation>(); 938 939 // Mapping from permission names to info about them. 940 final ArrayMap<String, PackageParser.PermissionGroup> mPermissionGroups = 941 new ArrayMap<String, PackageParser.PermissionGroup>(); 942 943 // Packages whose data we have transfered into another package, thus 944 // should no longer exist. 945 final ArraySet<String> mTransferedPackages = new ArraySet<String>(); 946 947 // Broadcast actions that are only available to the system. 948 @GuardedBy("mProtectedBroadcasts") 949 final ArraySet<String> mProtectedBroadcasts = new ArraySet<>(); 950 951 /** List of packages waiting for verification. */ 952 final SparseArray<PackageVerificationState> mPendingVerification 953 = new SparseArray<PackageVerificationState>(); 954 955 /** Set of packages associated with each app op permission. */ 956 final ArrayMap<String, ArraySet<String>> mAppOpPermissionPackages = new ArrayMap<>(); 957 958 final PackageInstallerService mInstallerService; 959 960 private final PackageDexOptimizer mPackageDexOptimizer; 961 // DexManager handles the usage of dex files (e.g. secondary files, whether or not a package 962 // is used by other apps). 963 private final DexManager mDexManager; 964 965 private AtomicInteger mNextMoveId = new AtomicInteger(); 966 private final MoveCallbacks mMoveCallbacks; 967 968 private final OnPermissionChangeListeners mOnPermissionChangeListeners; 969 970 // Cache of users who need badging. 971 SparseBooleanArray mUserNeedsBadging = new SparseBooleanArray(); 972 973 /** Token for keys in mPendingVerification. */ 974 private int mPendingVerificationToken = 0; 975 976 volatile boolean mSystemReady; 977 volatile boolean mSafeMode; 978 volatile boolean mHasSystemUidErrors; 979 private volatile boolean mEphemeralAppsDisabled; 980 981 ApplicationInfo mAndroidApplication; 982 final ActivityInfo mResolveActivity = new ActivityInfo(); 983 final ResolveInfo mResolveInfo = new ResolveInfo(); 984 ComponentName mResolveComponentName; 985 PackageParser.Package mPlatformPackage; 986 ComponentName mCustomResolverComponentName; 987 988 boolean mResolverReplaced = false; 989 990 private final @Nullable ComponentName mIntentFilterVerifierComponent; 991 private final @Nullable IntentFilterVerifier<ActivityIntentInfo> mIntentFilterVerifier; 992 993 private int mIntentFilterVerificationToken = 0; 994 995 /** The service connection to the ephemeral resolver */ 996 final EphemeralResolverConnection mInstantAppResolverConnection; 997 /** Component used to show resolver settings for Instant Apps */ 998 final ComponentName mInstantAppResolverSettingsComponent; 999 1000 /** Activity used to install instant applications */ 1001 ActivityInfo mInstantAppInstallerActivity; 1002 final ResolveInfo mInstantAppInstallerInfo = new ResolveInfo(); 1003 1004 final SparseArray<IntentFilterVerificationState> mIntentFilterVerificationStates 1005 = new SparseArray<IntentFilterVerificationState>(); 1006 1007 final DefaultPermissionGrantPolicy mDefaultPermissionPolicy; 1008 1009 // List of packages names to keep cached, even if they are uninstalled for all users 1010 private List<String> mKeepUninstalledPackages; 1011 1012 private UserManagerInternal mUserManagerInternal; 1013 1014 private DeviceIdleController.LocalService mDeviceIdleController; 1015 1016 private File mCacheDir; 1017 1018 private ArraySet<String> mPrivappPermissionsViolations; 1019 1020 private Future<?> mPrepareAppDataFuture; 1021 1022 private static class IFVerificationParams { 1023 PackageParser.Package pkg; 1024 boolean replacing; 1025 int userId; 1026 int verifierUid; 1027 1028 public IFVerificationParams(PackageParser.Package _pkg, boolean _replacing, 1029 int _userId, int _verifierUid) { 1030 pkg = _pkg; 1031 replacing = _replacing; 1032 userId = _userId; 1033 replacing = _replacing; 1034 verifierUid = _verifierUid; 1035 } 1036 } 1037 1038 private interface IntentFilterVerifier<T extends IntentFilter> { 1039 boolean addOneIntentFilterVerification(int verifierId, int userId, int verificationId, 1040 T filter, String packageName); 1041 void startVerifications(int userId); 1042 void receiveVerificationResponse(int verificationId); 1043 } 1044 1045 private class IntentVerifierProxy implements IntentFilterVerifier<ActivityIntentInfo> { 1046 private Context mContext; 1047 private ComponentName mIntentFilterVerifierComponent; 1048 private ArrayList<Integer> mCurrentIntentFilterVerifications = new ArrayList<Integer>(); 1049 1050 public IntentVerifierProxy(Context context, ComponentName verifierComponent) { 1051 mContext = context; 1052 mIntentFilterVerifierComponent = verifierComponent; 1053 } 1054 1055 private String getDefaultScheme() { 1056 return IntentFilter.SCHEME_HTTPS; 1057 } 1058 1059 @Override 1060 public void startVerifications(int userId) { 1061 // Launch verifications requests 1062 int count = mCurrentIntentFilterVerifications.size(); 1063 for (int n=0; n<count; n++) { 1064 int verificationId = mCurrentIntentFilterVerifications.get(n); 1065 final IntentFilterVerificationState ivs = 1066 mIntentFilterVerificationStates.get(verificationId); 1067 1068 String packageName = ivs.getPackageName(); 1069 1070 ArrayList<PackageParser.ActivityIntentInfo> filters = ivs.getFilters(); 1071 final int filterCount = filters.size(); 1072 ArraySet<String> domainsSet = new ArraySet<>(); 1073 for (int m=0; m<filterCount; m++) { 1074 PackageParser.ActivityIntentInfo filter = filters.get(m); 1075 domainsSet.addAll(filter.getHostsList()); 1076 } 1077 synchronized (mPackages) { 1078 if (mSettings.createIntentFilterVerificationIfNeededLPw( 1079 packageName, domainsSet) != null) { 1080 scheduleWriteSettingsLocked(); 1081 } 1082 } 1083 sendVerificationRequest(verificationId, ivs); 1084 } 1085 mCurrentIntentFilterVerifications.clear(); 1086 } 1087 1088 private void sendVerificationRequest(int verificationId, IntentFilterVerificationState ivs) { 1089 Intent verificationIntent = new Intent(Intent.ACTION_INTENT_FILTER_NEEDS_VERIFICATION); 1090 verificationIntent.putExtra( 1091 PackageManager.EXTRA_INTENT_FILTER_VERIFICATION_ID, 1092 verificationId); 1093 verificationIntent.putExtra( 1094 PackageManager.EXTRA_INTENT_FILTER_VERIFICATION_URI_SCHEME, 1095 getDefaultScheme()); 1096 verificationIntent.putExtra( 1097 PackageManager.EXTRA_INTENT_FILTER_VERIFICATION_HOSTS, 1098 ivs.getHostsString()); 1099 verificationIntent.putExtra( 1100 PackageManager.EXTRA_INTENT_FILTER_VERIFICATION_PACKAGE_NAME, 1101 ivs.getPackageName()); 1102 verificationIntent.setComponent(mIntentFilterVerifierComponent); 1103 verificationIntent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 1104 1105 DeviceIdleController.LocalService idleController = getDeviceIdleController(); 1106 idleController.addPowerSaveTempWhitelistApp(Process.myUid(), 1107 mIntentFilterVerifierComponent.getPackageName(), getVerificationTimeout(), 1108 UserHandle.USER_SYSTEM, true, "intent filter verifier"); 1109 1110 mContext.sendBroadcastAsUser(verificationIntent, UserHandle.SYSTEM); 1111 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, 1112 "Sending IntentFilter verification broadcast"); 1113 } 1114 1115 public void receiveVerificationResponse(int verificationId) { 1116 IntentFilterVerificationState ivs = mIntentFilterVerificationStates.get(verificationId); 1117 1118 final boolean verified = ivs.isVerified(); 1119 1120 ArrayList<PackageParser.ActivityIntentInfo> filters = ivs.getFilters(); 1121 final int count = filters.size(); 1122 if (DEBUG_DOMAIN_VERIFICATION) { 1123 Slog.i(TAG, "Received verification response " + verificationId 1124 + " for " + count + " filters, verified=" + verified); 1125 } 1126 for (int n=0; n<count; n++) { 1127 PackageParser.ActivityIntentInfo filter = filters.get(n); 1128 filter.setVerified(verified); 1129 1130 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, "IntentFilter " + filter.toString() 1131 + " verified with result:" + verified + " and hosts:" 1132 + ivs.getHostsString()); 1133 } 1134 1135 mIntentFilterVerificationStates.remove(verificationId); 1136 1137 final String packageName = ivs.getPackageName(); 1138 IntentFilterVerificationInfo ivi = null; 1139 1140 synchronized (mPackages) { 1141 ivi = mSettings.getIntentFilterVerificationLPr(packageName); 1142 } 1143 if (ivi == null) { 1144 Slog.w(TAG, "IntentFilterVerificationInfo not found for verificationId:" 1145 + verificationId + " packageName:" + packageName); 1146 return; 1147 } 1148 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, 1149 "Updating IntentFilterVerificationInfo for package " + packageName 1150 +" verificationId:" + verificationId); 1151 1152 synchronized (mPackages) { 1153 if (verified) { 1154 ivi.setStatus(INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS); 1155 } else { 1156 ivi.setStatus(INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ASK); 1157 } 1158 scheduleWriteSettingsLocked(); 1159 1160 final int userId = ivs.getUserId(); 1161 if (userId != UserHandle.USER_ALL) { 1162 final int userStatus = 1163 mSettings.getIntentFilterVerificationStatusLPr(packageName, userId); 1164 1165 int updatedStatus = INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED; 1166 boolean needUpdate = false; 1167 1168 // We cannot override the STATUS_ALWAYS / STATUS_NEVER states if they have 1169 // already been set by the User thru the Disambiguation dialog 1170 switch (userStatus) { 1171 case INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED: 1172 if (verified) { 1173 updatedStatus = INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS; 1174 } else { 1175 updatedStatus = INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ASK; 1176 } 1177 needUpdate = true; 1178 break; 1179 1180 case INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ASK: 1181 if (verified) { 1182 updatedStatus = INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS; 1183 needUpdate = true; 1184 } 1185 break; 1186 1187 default: 1188 // Nothing to do 1189 } 1190 1191 if (needUpdate) { 1192 mSettings.updateIntentFilterVerificationStatusLPw( 1193 packageName, updatedStatus, userId); 1194 scheduleWritePackageRestrictionsLocked(userId); 1195 } 1196 } 1197 } 1198 } 1199 1200 @Override 1201 public boolean addOneIntentFilterVerification(int verifierUid, int userId, int verificationId, 1202 ActivityIntentInfo filter, String packageName) { 1203 if (!hasValidDomains(filter)) { 1204 return false; 1205 } 1206 IntentFilterVerificationState ivs = mIntentFilterVerificationStates.get(verificationId); 1207 if (ivs == null) { 1208 ivs = createDomainVerificationState(verifierUid, userId, verificationId, 1209 packageName); 1210 } 1211 if (DEBUG_DOMAIN_VERIFICATION) { 1212 Slog.d(TAG, "Adding verification filter for " + packageName + ": " + filter); 1213 } 1214 ivs.addFilter(filter); 1215 return true; 1216 } 1217 1218 private IntentFilterVerificationState createDomainVerificationState(int verifierUid, 1219 int userId, int verificationId, String packageName) { 1220 IntentFilterVerificationState ivs = new IntentFilterVerificationState( 1221 verifierUid, userId, packageName); 1222 ivs.setPendingState(); 1223 synchronized (mPackages) { 1224 mIntentFilterVerificationStates.append(verificationId, ivs); 1225 mCurrentIntentFilterVerifications.add(verificationId); 1226 } 1227 return ivs; 1228 } 1229 } 1230 1231 private static boolean hasValidDomains(ActivityIntentInfo filter) { 1232 return filter.hasCategory(Intent.CATEGORY_BROWSABLE) 1233 && (filter.hasDataScheme(IntentFilter.SCHEME_HTTP) || 1234 filter.hasDataScheme(IntentFilter.SCHEME_HTTPS)); 1235 } 1236 1237 // Set of pending broadcasts for aggregating enable/disable of components. 1238 static class PendingPackageBroadcasts { 1239 // for each user id, a map of <package name -> components within that package> 1240 final SparseArray<ArrayMap<String, ArrayList<String>>> mUidMap; 1241 1242 public PendingPackageBroadcasts() { 1243 mUidMap = new SparseArray<ArrayMap<String, ArrayList<String>>>(2); 1244 } 1245 1246 public ArrayList<String> get(int userId, String packageName) { 1247 ArrayMap<String, ArrayList<String>> packages = getOrAllocate(userId); 1248 return packages.get(packageName); 1249 } 1250 1251 public void put(int userId, String packageName, ArrayList<String> components) { 1252 ArrayMap<String, ArrayList<String>> packages = getOrAllocate(userId); 1253 packages.put(packageName, components); 1254 } 1255 1256 public void remove(int userId, String packageName) { 1257 ArrayMap<String, ArrayList<String>> packages = mUidMap.get(userId); 1258 if (packages != null) { 1259 packages.remove(packageName); 1260 } 1261 } 1262 1263 public void remove(int userId) { 1264 mUidMap.remove(userId); 1265 } 1266 1267 public int userIdCount() { 1268 return mUidMap.size(); 1269 } 1270 1271 public int userIdAt(int n) { 1272 return mUidMap.keyAt(n); 1273 } 1274 1275 public ArrayMap<String, ArrayList<String>> packagesForUserId(int userId) { 1276 return mUidMap.get(userId); 1277 } 1278 1279 public int size() { 1280 // total number of pending broadcast entries across all userIds 1281 int num = 0; 1282 for (int i = 0; i< mUidMap.size(); i++) { 1283 num += mUidMap.valueAt(i).size(); 1284 } 1285 return num; 1286 } 1287 1288 public void clear() { 1289 mUidMap.clear(); 1290 } 1291 1292 private ArrayMap<String, ArrayList<String>> getOrAllocate(int userId) { 1293 ArrayMap<String, ArrayList<String>> map = mUidMap.get(userId); 1294 if (map == null) { 1295 map = new ArrayMap<String, ArrayList<String>>(); 1296 mUidMap.put(userId, map); 1297 } 1298 return map; 1299 } 1300 } 1301 final PendingPackageBroadcasts mPendingBroadcasts = new PendingPackageBroadcasts(); 1302 1303 // Service Connection to remote media container service to copy 1304 // package uri's from external media onto secure containers 1305 // or internal storage. 1306 private IMediaContainerService mContainerService = null; 1307 1308 static final int SEND_PENDING_BROADCAST = 1; 1309 static final int MCS_BOUND = 3; 1310 static final int END_COPY = 4; 1311 static final int INIT_COPY = 5; 1312 static final int MCS_UNBIND = 6; 1313 static final int START_CLEANING_PACKAGE = 7; 1314 static final int FIND_INSTALL_LOC = 8; 1315 static final int POST_INSTALL = 9; 1316 static final int MCS_RECONNECT = 10; 1317 static final int MCS_GIVE_UP = 11; 1318 static final int UPDATED_MEDIA_STATUS = 12; 1319 static final int WRITE_SETTINGS = 13; 1320 static final int WRITE_PACKAGE_RESTRICTIONS = 14; 1321 static final int PACKAGE_VERIFIED = 15; 1322 static final int CHECK_PENDING_VERIFICATION = 16; 1323 static final int START_INTENT_FILTER_VERIFICATIONS = 17; 1324 static final int INTENT_FILTER_VERIFIED = 18; 1325 static final int WRITE_PACKAGE_LIST = 19; 1326 static final int INSTANT_APP_RESOLUTION_PHASE_TWO = 20; 1327 1328 static final int WRITE_SETTINGS_DELAY = 10*1000; // 10 seconds 1329 1330 // Delay time in millisecs 1331 static final int BROADCAST_DELAY = 10 * 1000; 1332 1333 private static final long DEFAULT_UNUSED_STATIC_SHARED_LIB_MIN_CACHE_PERIOD = 1334 2 * 60 * 60 * 1000L; /* two hours */ 1335 1336 static UserManagerService sUserManager; 1337 1338 // Stores a list of users whose package restrictions file needs to be updated 1339 private ArraySet<Integer> mDirtyUsers = new ArraySet<Integer>(); 1340 1341 final private DefaultContainerConnection mDefContainerConn = 1342 new DefaultContainerConnection(); 1343 class DefaultContainerConnection implements ServiceConnection { 1344 public void onServiceConnected(ComponentName name, IBinder service) { 1345 if (DEBUG_SD_INSTALL) Log.i(TAG, "onServiceConnected"); 1346 final IMediaContainerService imcs = IMediaContainerService.Stub 1347 .asInterface(Binder.allowBlocking(service)); 1348 mHandler.sendMessage(mHandler.obtainMessage(MCS_BOUND, imcs)); 1349 } 1350 1351 public void onServiceDisconnected(ComponentName name) { 1352 if (DEBUG_SD_INSTALL) Log.i(TAG, "onServiceDisconnected"); 1353 } 1354 } 1355 1356 // Recordkeeping of restore-after-install operations that are currently in flight 1357 // between the Package Manager and the Backup Manager 1358 static class PostInstallData { 1359 public InstallArgs args; 1360 public PackageInstalledInfo res; 1361 1362 PostInstallData(InstallArgs _a, PackageInstalledInfo _r) { 1363 args = _a; 1364 res = _r; 1365 } 1366 } 1367 1368 final SparseArray<PostInstallData> mRunningInstalls = new SparseArray<PostInstallData>(); 1369 int mNextInstallToken = 1; // nonzero; will be wrapped back to 1 when ++ overflows 1370 1371 // XML tags for backup/restore of various bits of state 1372 private static final String TAG_PREFERRED_BACKUP = "pa"; 1373 private static final String TAG_DEFAULT_APPS = "da"; 1374 private static final String TAG_INTENT_FILTER_VERIFICATION = "iv"; 1375 1376 private static final String TAG_PERMISSION_BACKUP = "perm-grant-backup"; 1377 private static final String TAG_ALL_GRANTS = "rt-grants"; 1378 private static final String TAG_GRANT = "grant"; 1379 private static final String ATTR_PACKAGE_NAME = "pkg"; 1380 1381 private static final String TAG_PERMISSION = "perm"; 1382 private static final String ATTR_PERMISSION_NAME = "name"; 1383 private static final String ATTR_IS_GRANTED = "g"; 1384 private static final String ATTR_USER_SET = "set"; 1385 private static final String ATTR_USER_FIXED = "fixed"; 1386 private static final String ATTR_REVOKE_ON_UPGRADE = "rou"; 1387 1388 // System/policy permission grants are not backed up 1389 private static final int SYSTEM_RUNTIME_GRANT_MASK = 1390 FLAG_PERMISSION_POLICY_FIXED 1391 | FLAG_PERMISSION_SYSTEM_FIXED 1392 | FLAG_PERMISSION_GRANTED_BY_DEFAULT; 1393 1394 // And we back up these user-adjusted states 1395 private static final int USER_RUNTIME_GRANT_MASK = 1396 FLAG_PERMISSION_USER_SET 1397 | FLAG_PERMISSION_USER_FIXED 1398 | FLAG_PERMISSION_REVOKE_ON_UPGRADE; 1399 1400 final @Nullable String mRequiredVerifierPackage; 1401 final @NonNull String mRequiredInstallerPackage; 1402 final @NonNull String mRequiredUninstallerPackage; 1403 final @Nullable String mSetupWizardPackage; 1404 final @Nullable String mStorageManagerPackage; 1405 final @NonNull String mServicesSystemSharedLibraryPackageName; 1406 final @NonNull String mSharedSystemSharedLibraryPackageName; 1407 1408 final boolean mPermissionReviewRequired; 1409 1410 private final PackageUsage mPackageUsage = new PackageUsage(); 1411 private final CompilerStats mCompilerStats = new CompilerStats(); 1412 1413 class PackageHandler extends Handler { 1414 private boolean mBound = false; 1415 final ArrayList<HandlerParams> mPendingInstalls = 1416 new ArrayList<HandlerParams>(); 1417 1418 private boolean connectToService() { 1419 if (DEBUG_SD_INSTALL) Log.i(TAG, "Trying to bind to" + 1420 " DefaultContainerService"); 1421 Intent service = new Intent().setComponent(DEFAULT_CONTAINER_COMPONENT); 1422 Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); 1423 if (mContext.bindServiceAsUser(service, mDefContainerConn, 1424 Context.BIND_AUTO_CREATE, UserHandle.SYSTEM)) { 1425 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); 1426 mBound = true; 1427 return true; 1428 } 1429 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); 1430 return false; 1431 } 1432 1433 private void disconnectService() { 1434 mContainerService = null; 1435 mBound = false; 1436 Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); 1437 mContext.unbindService(mDefContainerConn); 1438 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); 1439 } 1440 1441 PackageHandler(Looper looper) { 1442 super(looper); 1443 } 1444 1445 public void handleMessage(Message msg) { 1446 try { 1447 doHandleMessage(msg); 1448 } finally { 1449 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); 1450 } 1451 } 1452 1453 void doHandleMessage(Message msg) { 1454 switch (msg.what) { 1455 case INIT_COPY: { 1456 HandlerParams params = (HandlerParams) msg.obj; 1457 int idx = mPendingInstalls.size(); 1458 if (DEBUG_INSTALL) Slog.i(TAG, "init_copy idx=" + idx + ": " + params); 1459 // If a bind was already initiated we dont really 1460 // need to do anything. The pending install 1461 // will be processed later on. 1462 if (!mBound) { 1463 Trace.asyncTraceBegin(TRACE_TAG_PACKAGE_MANAGER, "bindingMCS", 1464 System.identityHashCode(mHandler)); 1465 // If this is the only one pending we might 1466 // have to bind to the service again. 1467 if (!connectToService()) { 1468 Slog.e(TAG, "Failed to bind to media container service"); 1469 params.serviceError(); 1470 Trace.asyncTraceEnd(TRACE_TAG_PACKAGE_MANAGER, "bindingMCS", 1471 System.identityHashCode(mHandler)); 1472 if (params.traceMethod != null) { 1473 Trace.asyncTraceEnd(TRACE_TAG_PACKAGE_MANAGER, params.traceMethod, 1474 params.traceCookie); 1475 } 1476 return; 1477 } else { 1478 // Once we bind to the service, the first 1479 // pending request will be processed. 1480 mPendingInstalls.add(idx, params); 1481 } 1482 } else { 1483 mPendingInstalls.add(idx, params); 1484 // Already bound to the service. Just make 1485 // sure we trigger off processing the first request. 1486 if (idx == 0) { 1487 mHandler.sendEmptyMessage(MCS_BOUND); 1488 } 1489 } 1490 break; 1491 } 1492 case MCS_BOUND: { 1493 if (DEBUG_INSTALL) Slog.i(TAG, "mcs_bound"); 1494 if (msg.obj != null) { 1495 mContainerService = (IMediaContainerService) msg.obj; 1496 Trace.asyncTraceEnd(TRACE_TAG_PACKAGE_MANAGER, "bindingMCS", 1497 System.identityHashCode(mHandler)); 1498 } 1499 if (mContainerService == null) { 1500 if (!mBound) { 1501 // Something seriously wrong since we are not bound and we are not 1502 // waiting for connection. Bail out. 1503 Slog.e(TAG, "Cannot bind to media container service"); 1504 for (HandlerParams params : mPendingInstalls) { 1505 // Indicate service bind error 1506 params.serviceError(); 1507 Trace.asyncTraceEnd(TRACE_TAG_PACKAGE_MANAGER, "queueInstall", 1508 System.identityHashCode(params)); 1509 if (params.traceMethod != null) { 1510 Trace.asyncTraceEnd(TRACE_TAG_PACKAGE_MANAGER, 1511 params.traceMethod, params.traceCookie); 1512 } 1513 return; 1514 } 1515 mPendingInstalls.clear(); 1516 } else { 1517 Slog.w(TAG, "Waiting to connect to media container service"); 1518 } 1519 } else if (mPendingInstalls.size() > 0) { 1520 HandlerParams params = mPendingInstalls.get(0); 1521 if (params != null) { 1522 Trace.asyncTraceEnd(TRACE_TAG_PACKAGE_MANAGER, "queueInstall", 1523 System.identityHashCode(params)); 1524 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "startCopy"); 1525 if (params.startCopy()) { 1526 // We are done... look for more work or to 1527 // go idle. 1528 if (DEBUG_SD_INSTALL) Log.i(TAG, 1529 "Checking for more work or unbind..."); 1530 // Delete pending install 1531 if (mPendingInstalls.size() > 0) { 1532 mPendingInstalls.remove(0); 1533 } 1534 if (mPendingInstalls.size() == 0) { 1535 if (mBound) { 1536 if (DEBUG_SD_INSTALL) Log.i(TAG, 1537 "Posting delayed MCS_UNBIND"); 1538 removeMessages(MCS_UNBIND); 1539 Message ubmsg = obtainMessage(MCS_UNBIND); 1540 // Unbind after a little delay, to avoid 1541 // continual thrashing. 1542 sendMessageDelayed(ubmsg, 10000); 1543 } 1544 } else { 1545 // There are more pending requests in queue. 1546 // Just post MCS_BOUND message to trigger processing 1547 // of next pending install. 1548 if (DEBUG_SD_INSTALL) Log.i(TAG, 1549 "Posting MCS_BOUND for next work"); 1550 mHandler.sendEmptyMessage(MCS_BOUND); 1551 } 1552 } 1553 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 1554 } 1555 } else { 1556 // Should never happen ideally. 1557 Slog.w(TAG, "Empty queue"); 1558 } 1559 break; 1560 } 1561 case MCS_RECONNECT: { 1562 if (DEBUG_INSTALL) Slog.i(TAG, "mcs_reconnect"); 1563 if (mPendingInstalls.size() > 0) { 1564 if (mBound) { 1565 disconnectService(); 1566 } 1567 if (!connectToService()) { 1568 Slog.e(TAG, "Failed to bind to media container service"); 1569 for (HandlerParams params : mPendingInstalls) { 1570 // Indicate service bind error 1571 params.serviceError(); 1572 Trace.asyncTraceEnd(TRACE_TAG_PACKAGE_MANAGER, "queueInstall", 1573 System.identityHashCode(params)); 1574 } 1575 mPendingInstalls.clear(); 1576 } 1577 } 1578 break; 1579 } 1580 case MCS_UNBIND: { 1581 // If there is no actual work left, then time to unbind. 1582 if (DEBUG_INSTALL) Slog.i(TAG, "mcs_unbind"); 1583 1584 if (mPendingInstalls.size() == 0 && mPendingVerification.size() == 0) { 1585 if (mBound) { 1586 if (DEBUG_INSTALL) Slog.i(TAG, "calling disconnectService()"); 1587 1588 disconnectService(); 1589 } 1590 } else if (mPendingInstalls.size() > 0) { 1591 // There are more pending requests in queue. 1592 // Just post MCS_BOUND message to trigger processing 1593 // of next pending install. 1594 mHandler.sendEmptyMessage(MCS_BOUND); 1595 } 1596 1597 break; 1598 } 1599 case MCS_GIVE_UP: { 1600 if (DEBUG_INSTALL) Slog.i(TAG, "mcs_giveup too many retries"); 1601 HandlerParams params = mPendingInstalls.remove(0); 1602 Trace.asyncTraceEnd(TRACE_TAG_PACKAGE_MANAGER, "queueInstall", 1603 System.identityHashCode(params)); 1604 break; 1605 } 1606 case SEND_PENDING_BROADCAST: { 1607 String packages[]; 1608 ArrayList<String> components[]; 1609 int size = 0; 1610 int uids[]; 1611 Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); 1612 synchronized (mPackages) { 1613 if (mPendingBroadcasts == null) { 1614 return; 1615 } 1616 size = mPendingBroadcasts.size(); 1617 if (size <= 0) { 1618 // Nothing to be done. Just return 1619 return; 1620 } 1621 packages = new String[size]; 1622 components = new ArrayList[size]; 1623 uids = new int[size]; 1624 int i = 0; // filling out the above arrays 1625 1626 for (int n = 0; n < mPendingBroadcasts.userIdCount(); n++) { 1627 int packageUserId = mPendingBroadcasts.userIdAt(n); 1628 Iterator<Map.Entry<String, ArrayList<String>>> it 1629 = mPendingBroadcasts.packagesForUserId(packageUserId) 1630 .entrySet().iterator(); 1631 while (it.hasNext() && i < size) { 1632 Map.Entry<String, ArrayList<String>> ent = it.next(); 1633 packages[i] = ent.getKey(); 1634 components[i] = ent.getValue(); 1635 PackageSetting ps = mSettings.mPackages.get(ent.getKey()); 1636 uids[i] = (ps != null) 1637 ? UserHandle.getUid(packageUserId, ps.appId) 1638 : -1; 1639 i++; 1640 } 1641 } 1642 size = i; 1643 mPendingBroadcasts.clear(); 1644 } 1645 // Send broadcasts 1646 for (int i = 0; i < size; i++) { 1647 sendPackageChangedBroadcast(packages[i], true, components[i], uids[i]); 1648 } 1649 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); 1650 break; 1651 } 1652 case START_CLEANING_PACKAGE: { 1653 Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); 1654 final String packageName = (String)msg.obj; 1655 final int userId = msg.arg1; 1656 final boolean andCode = msg.arg2 != 0; 1657 synchronized (mPackages) { 1658 if (userId == UserHandle.USER_ALL) { 1659 int[] users = sUserManager.getUserIds(); 1660 for (int user : users) { 1661 mSettings.addPackageToCleanLPw( 1662 new PackageCleanItem(user, packageName, andCode)); 1663 } 1664 } else { 1665 mSettings.addPackageToCleanLPw( 1666 new PackageCleanItem(userId, packageName, andCode)); 1667 } 1668 } 1669 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); 1670 startCleaningPackages(); 1671 } break; 1672 case POST_INSTALL: { 1673 if (DEBUG_INSTALL) Log.v(TAG, "Handling post-install for " + msg.arg1); 1674 1675 PostInstallData data = mRunningInstalls.get(msg.arg1); 1676 final boolean didRestore = (msg.arg2 != 0); 1677 mRunningInstalls.delete(msg.arg1); 1678 1679 if (data != null) { 1680 InstallArgs args = data.args; 1681 PackageInstalledInfo parentRes = data.res; 1682 1683 final boolean grantPermissions = (args.installFlags 1684 & PackageManager.INSTALL_GRANT_RUNTIME_PERMISSIONS) != 0; 1685 final boolean killApp = (args.installFlags 1686 & PackageManager.INSTALL_DONT_KILL_APP) == 0; 1687 final boolean virtualPreload = ((args.installFlags 1688 & PackageManager.INSTALL_VIRTUAL_PRELOAD) != 0); 1689 final String[] grantedPermissions = args.installGrantPermissions; 1690 1691 // Handle the parent package 1692 handlePackagePostInstall(parentRes, grantPermissions, killApp, 1693 virtualPreload, grantedPermissions, didRestore, 1694 args.installerPackageName, args.observer); 1695 1696 // Handle the child packages 1697 final int childCount = (parentRes.addedChildPackages != null) 1698 ? parentRes.addedChildPackages.size() : 0; 1699 for (int i = 0; i < childCount; i++) { 1700 PackageInstalledInfo childRes = parentRes.addedChildPackages.valueAt(i); 1701 handlePackagePostInstall(childRes, grantPermissions, killApp, 1702 virtualPreload, grantedPermissions, false /*didRestore*/, 1703 args.installerPackageName, args.observer); 1704 } 1705 1706 // Log tracing if needed 1707 if (args.traceMethod != null) { 1708 Trace.asyncTraceEnd(TRACE_TAG_PACKAGE_MANAGER, args.traceMethod, 1709 args.traceCookie); 1710 } 1711 } else { 1712 Slog.e(TAG, "Bogus post-install token " + msg.arg1); 1713 } 1714 1715 Trace.asyncTraceEnd(TRACE_TAG_PACKAGE_MANAGER, "postInstall", msg.arg1); 1716 } break; 1717 case UPDATED_MEDIA_STATUS: { 1718 if (DEBUG_SD_INSTALL) Log.i(TAG, "Got message UPDATED_MEDIA_STATUS"); 1719 boolean reportStatus = msg.arg1 == 1; 1720 boolean doGc = msg.arg2 == 1; 1721 if (DEBUG_SD_INSTALL) Log.i(TAG, "reportStatus=" + reportStatus + ", doGc = " + doGc); 1722 if (doGc) { 1723 // Force a gc to clear up stale containers. 1724 Runtime.getRuntime().gc(); 1725 } 1726 if (msg.obj != null) { 1727 @SuppressWarnings("unchecked") 1728 Set<AsecInstallArgs> args = (Set<AsecInstallArgs>) msg.obj; 1729 if (DEBUG_SD_INSTALL) Log.i(TAG, "Unloading all containers"); 1730 // Unload containers 1731 unloadAllContainers(args); 1732 } 1733 if (reportStatus) { 1734 try { 1735 if (DEBUG_SD_INSTALL) Log.i(TAG, 1736 "Invoking StorageManagerService call back"); 1737 PackageHelper.getStorageManager().finishMediaUpdate(); 1738 } catch (RemoteException e) { 1739 Log.e(TAG, "StorageManagerService not running?"); 1740 } 1741 } 1742 } break; 1743 case WRITE_SETTINGS: { 1744 Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); 1745 synchronized (mPackages) { 1746 removeMessages(WRITE_SETTINGS); 1747 removeMessages(WRITE_PACKAGE_RESTRICTIONS); 1748 mSettings.writeLPr(); 1749 mDirtyUsers.clear(); 1750 } 1751 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); 1752 } break; 1753 case WRITE_PACKAGE_RESTRICTIONS: { 1754 Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); 1755 synchronized (mPackages) { 1756 removeMessages(WRITE_PACKAGE_RESTRICTIONS); 1757 for (int userId : mDirtyUsers) { 1758 mSettings.writePackageRestrictionsLPr(userId); 1759 } 1760 mDirtyUsers.clear(); 1761 } 1762 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); 1763 } break; 1764 case WRITE_PACKAGE_LIST: { 1765 Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); 1766 synchronized (mPackages) { 1767 removeMessages(WRITE_PACKAGE_LIST); 1768 mSettings.writePackageListLPr(msg.arg1); 1769 } 1770 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); 1771 } break; 1772 case CHECK_PENDING_VERIFICATION: { 1773 final int verificationId = msg.arg1; 1774 final PackageVerificationState state = mPendingVerification.get(verificationId); 1775 1776 if ((state != null) && !state.timeoutExtended()) { 1777 final InstallArgs args = state.getInstallArgs(); 1778 final Uri originUri = Uri.fromFile(args.origin.resolvedFile); 1779 1780 Slog.i(TAG, "Verification timed out for " + originUri); 1781 mPendingVerification.remove(verificationId); 1782 1783 int ret = PackageManager.INSTALL_FAILED_VERIFICATION_FAILURE; 1784 1785 final UserHandle user = args.getUser(); 1786 if (getDefaultVerificationResponse(user) 1787 == PackageManager.VERIFICATION_ALLOW) { 1788 Slog.i(TAG, "Continuing with installation of " + originUri); 1789 state.setVerifierResponse(Binder.getCallingUid(), 1790 PackageManager.VERIFICATION_ALLOW_WITHOUT_SUFFICIENT); 1791 broadcastPackageVerified(verificationId, originUri, 1792 PackageManager.VERIFICATION_ALLOW, user); 1793 try { 1794 ret = args.copyApk(mContainerService, true); 1795 } catch (RemoteException e) { 1796 Slog.e(TAG, "Could not contact the ContainerService"); 1797 } 1798 } else { 1799 broadcastPackageVerified(verificationId, originUri, 1800 PackageManager.VERIFICATION_REJECT, user); 1801 } 1802 1803 Trace.asyncTraceEnd( 1804 TRACE_TAG_PACKAGE_MANAGER, "verification", verificationId); 1805 1806 processPendingInstall(args, ret); 1807 mHandler.sendEmptyMessage(MCS_UNBIND); 1808 } 1809 break; 1810 } 1811 case PACKAGE_VERIFIED: { 1812 final int verificationId = msg.arg1; 1813 1814 final PackageVerificationState state = mPendingVerification.get(verificationId); 1815 if (state == null) { 1816 Slog.w(TAG, "Invalid verification token " + verificationId + " received"); 1817 break; 1818 } 1819 1820 final PackageVerificationResponse response = (PackageVerificationResponse) msg.obj; 1821 1822 state.setVerifierResponse(response.callerUid, response.code); 1823 1824 if (state.isVerificationComplete()) { 1825 mPendingVerification.remove(verificationId); 1826 1827 final InstallArgs args = state.getInstallArgs(); 1828 final Uri originUri = Uri.fromFile(args.origin.resolvedFile); 1829 1830 int ret; 1831 if (state.isInstallAllowed()) { 1832 ret = PackageManager.INSTALL_FAILED_INTERNAL_ERROR; 1833 broadcastPackageVerified(verificationId, originUri, 1834 response.code, state.getInstallArgs().getUser()); 1835 try { 1836 ret = args.copyApk(mContainerService, true); 1837 } catch (RemoteException e) { 1838 Slog.e(TAG, "Could not contact the ContainerService"); 1839 } 1840 } else { 1841 ret = PackageManager.INSTALL_FAILED_VERIFICATION_FAILURE; 1842 } 1843 1844 Trace.asyncTraceEnd( 1845 TRACE_TAG_PACKAGE_MANAGER, "verification", verificationId); 1846 1847 processPendingInstall(args, ret); 1848 mHandler.sendEmptyMessage(MCS_UNBIND); 1849 } 1850 1851 break; 1852 } 1853 case START_INTENT_FILTER_VERIFICATIONS: { 1854 IFVerificationParams params = (IFVerificationParams) msg.obj; 1855 verifyIntentFiltersIfNeeded(params.userId, params.verifierUid, 1856 params.replacing, params.pkg); 1857 break; 1858 } 1859 case INTENT_FILTER_VERIFIED: { 1860 final int verificationId = msg.arg1; 1861 1862 final IntentFilterVerificationState state = mIntentFilterVerificationStates.get( 1863 verificationId); 1864 if (state == null) { 1865 Slog.w(TAG, "Invalid IntentFilter verification token " 1866 + verificationId + " received"); 1867 break; 1868 } 1869 1870 final int userId = state.getUserId(); 1871 1872 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, 1873 "Processing IntentFilter verification with token:" 1874 + verificationId + " and userId:" + userId); 1875 1876 final IntentFilterVerificationResponse response = 1877 (IntentFilterVerificationResponse) msg.obj; 1878 1879 state.setVerifierResponse(response.callerUid, response.code); 1880 1881 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, 1882 "IntentFilter verification with token:" + verificationId 1883 + " and userId:" + userId 1884 + " is settings verifier response with response code:" 1885 + response.code); 1886 1887 if (response.code == PackageManager.INTENT_FILTER_VERIFICATION_FAILURE) { 1888 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, "Domains failing verification: " 1889 + response.getFailedDomainsString()); 1890 } 1891 1892 if (state.isVerificationComplete()) { 1893 mIntentFilterVerifier.receiveVerificationResponse(verificationId); 1894 } else { 1895 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, 1896 "IntentFilter verification with token:" + verificationId 1897 + " was not said to be complete"); 1898 } 1899 1900 break; 1901 } 1902 case INSTANT_APP_RESOLUTION_PHASE_TWO: { 1903 InstantAppResolver.doInstantAppResolutionPhaseTwo(mContext, 1904 mInstantAppResolverConnection, 1905 (InstantAppRequest) msg.obj, 1906 mInstantAppInstallerActivity, 1907 mHandler); 1908 } 1909 } 1910 } 1911 } 1912 1913 private void handlePackagePostInstall(PackageInstalledInfo res, boolean grantPermissions, 1914 boolean killApp, boolean virtualPreload, String[] grantedPermissions, 1915 boolean launchedForRestore, String installerPackage, 1916 IPackageInstallObserver2 installObserver) { 1917 if (res.returnCode == PackageManager.INSTALL_SUCCEEDED) { 1918 // Send the removed broadcasts 1919 if (res.removedInfo != null) { 1920 res.removedInfo.sendPackageRemovedBroadcasts(killApp); 1921 } 1922 1923 // Now that we successfully installed the package, grant runtime 1924 // permissions if requested before broadcasting the install. Also 1925 // for legacy apps in permission review mode we clear the permission 1926 // review flag which is used to emulate runtime permissions for 1927 // legacy apps. 1928 if (grantPermissions) { 1929 grantRequestedRuntimePermissions(res.pkg, res.newUsers, grantedPermissions); 1930 } 1931 1932 final boolean update = res.removedInfo != null 1933 && res.removedInfo.removedPackage != null; 1934 final String installerPackageName = 1935 res.installerPackageName != null 1936 ? res.installerPackageName 1937 : res.removedInfo != null 1938 ? res.removedInfo.installerPackageName 1939 : null; 1940 1941 // If this is the first time we have child packages for a disabled privileged 1942 // app that had no children, we grant requested runtime permissions to the new 1943 // children if the parent on the system image had them already granted. 1944 if (res.pkg.parentPackage != null) { 1945 synchronized (mPackages) { 1946 grantRuntimePermissionsGrantedToDisabledPrivSysPackageParentLPw(res.pkg); 1947 } 1948 } 1949 1950 synchronized (mPackages) { 1951 mInstantAppRegistry.onPackageInstalledLPw(res.pkg, res.newUsers); 1952 } 1953 1954 final String packageName = res.pkg.applicationInfo.packageName; 1955 1956 // Determine the set of users who are adding this package for 1957 // the first time vs. those who are seeing an update. 1958 int[] firstUsers = EMPTY_INT_ARRAY; 1959 int[] updateUsers = EMPTY_INT_ARRAY; 1960 final boolean allNewUsers = res.origUsers == null || res.origUsers.length == 0; 1961 final PackageSetting ps = (PackageSetting) res.pkg.mExtras; 1962 for (int newUser : res.newUsers) { 1963 if (ps.getInstantApp(newUser)) { 1964 continue; 1965 } 1966 if (allNewUsers) { 1967 firstUsers = ArrayUtils.appendInt(firstUsers, newUser); 1968 continue; 1969 } 1970 boolean isNew = true; 1971 for (int origUser : res.origUsers) { 1972 if (origUser == newUser) { 1973 isNew = false; 1974 break; 1975 } 1976 } 1977 if (isNew) { 1978 firstUsers = ArrayUtils.appendInt(firstUsers, newUser); 1979 } else { 1980 updateUsers = ArrayUtils.appendInt(updateUsers, newUser); 1981 } 1982 } 1983 1984 // Send installed broadcasts if the package is not a static shared lib. 1985 if (res.pkg.staticSharedLibName == null) { 1986 mProcessLoggingHandler.invalidateProcessLoggingBaseApkHash(res.pkg.baseCodePath); 1987 1988 // Send added for users that see the package for the first time 1989 // sendPackageAddedForNewUsers also deals with system apps 1990 int appId = UserHandle.getAppId(res.uid); 1991 boolean isSystem = res.pkg.applicationInfo.isSystemApp(); 1992 sendPackageAddedForNewUsers(packageName, isSystem || virtualPreload, 1993 virtualPreload /*startReceiver*/, appId, firstUsers); 1994 1995 // Send added for users that don't see the package for the first time 1996 Bundle extras = new Bundle(1); 1997 extras.putInt(Intent.EXTRA_UID, res.uid); 1998 if (update) { 1999 extras.putBoolean(Intent.EXTRA_REPLACING, true); 2000 } 2001 sendPackageBroadcast(Intent.ACTION_PACKAGE_ADDED, packageName, 2002 extras, 0 /*flags*/, 2003 null /*targetPackage*/, null /*finishedReceiver*/, updateUsers); 2004 if (installerPackageName != null) { 2005 sendPackageBroadcast(Intent.ACTION_PACKAGE_ADDED, packageName, 2006 extras, 0 /*flags*/, 2007 installerPackageName, null /*finishedReceiver*/, updateUsers); 2008 } 2009 2010 // Send replaced for users that don't see the package for the first time 2011 if (update) { 2012 sendPackageBroadcast(Intent.ACTION_PACKAGE_REPLACED, 2013 packageName, extras, 0 /*flags*/, 2014 null /*targetPackage*/, null /*finishedReceiver*/, 2015 updateUsers); 2016 if (installerPackageName != null) { 2017 sendPackageBroadcast(Intent.ACTION_PACKAGE_REPLACED, packageName, 2018 extras, 0 /*flags*/, 2019 installerPackageName, null /*finishedReceiver*/, updateUsers); 2020 } 2021 sendPackageBroadcast(Intent.ACTION_MY_PACKAGE_REPLACED, 2022 null /*package*/, null /*extras*/, 0 /*flags*/, 2023 packageName /*targetPackage*/, 2024 null /*finishedReceiver*/, updateUsers); 2025 } else if (launchedForRestore && !isSystemApp(res.pkg)) { 2026 // First-install and we did a restore, so we're responsible for the 2027 // first-launch broadcast. 2028 if (DEBUG_BACKUP) { 2029 Slog.i(TAG, "Post-restore of " + packageName 2030 + " sending FIRST_LAUNCH in " + Arrays.toString(firstUsers)); 2031 } 2032 sendFirstLaunchBroadcast(packageName, installerPackage, firstUsers); 2033 } 2034 2035 // Send broadcast package appeared if forward locked/external for all users 2036 // treat asec-hosted packages like removable media on upgrade 2037 if (res.pkg.isForwardLocked() || isExternal(res.pkg)) { 2038 if (DEBUG_INSTALL) { 2039 Slog.i(TAG, "upgrading pkg " + res.pkg 2040 + " is ASEC-hosted -> AVAILABLE"); 2041 } 2042 final int[] uidArray = new int[]{res.pkg.applicationInfo.uid}; 2043 ArrayList<String> pkgList = new ArrayList<>(1); 2044 pkgList.add(packageName); 2045 sendResourcesChangedBroadcast(true, true, pkgList, uidArray, null); 2046 } 2047 } 2048 2049 // Work that needs to happen on first install within each user 2050 if (firstUsers != null && firstUsers.length > 0) { 2051 synchronized (mPackages) { 2052 for (int userId : firstUsers) { 2053 // If this app is a browser and it's newly-installed for some 2054 // users, clear any default-browser state in those users. The 2055 // app's nature doesn't depend on the user, so we can just check 2056 // its browser nature in any user and generalize. 2057 if (packageIsBrowser(packageName, userId)) { 2058 mSettings.setDefaultBrowserPackageNameLPw(null, userId); 2059 } 2060 2061 // We may also need to apply pending (restored) runtime 2062 // permission grants within these users. 2063 mSettings.applyPendingPermissionGrantsLPw(packageName, userId); 2064 } 2065 } 2066 } 2067 2068 // Log current value of "unknown sources" setting 2069 EventLog.writeEvent(EventLogTags.UNKNOWN_SOURCES_ENABLED, 2070 getUnknownSourcesSettings()); 2071 2072 // Remove the replaced package's older resources safely now 2073 // We delete after a gc for applications on sdcard. 2074 if (res.removedInfo != null && res.removedInfo.args != null) { 2075 Runtime.getRuntime().gc(); 2076 synchronized (mInstallLock) { 2077 res.removedInfo.args.doPostDeleteLI(true); 2078 } 2079 } else { 2080 // Force a gc to clear up things. Ask for a background one, it's fine to go on 2081 // and not block here. 2082 VMRuntime.getRuntime().requestConcurrentGC(); 2083 } 2084 2085 // Notify DexManager that the package was installed for new users. 2086 // The updated users should already be indexed and the package code paths 2087 // should not change. 2088 // Don't notify the manager for ephemeral apps as they are not expected to 2089 // survive long enough to benefit of background optimizations. 2090 for (int userId : firstUsers) { 2091 PackageInfo info = getPackageInfo(packageName, /*flags*/ 0, userId); 2092 // There's a race currently where some install events may interleave with an uninstall. 2093 // This can lead to package info being null (b/36642664). 2094 if (info != null) { 2095 mDexManager.notifyPackageInstalled(info, userId); 2096 } 2097 } 2098 } 2099 2100 // If someone is watching installs - notify them 2101 if (installObserver != null) { 2102 try { 2103 Bundle extras = extrasForInstallResult(res); 2104 installObserver.onPackageInstalled(res.name, res.returnCode, 2105 res.returnMsg, extras); 2106 } catch (RemoteException e) { 2107 Slog.i(TAG, "Observer no longer exists."); 2108 } 2109 } 2110 } 2111 2112 private void grantRuntimePermissionsGrantedToDisabledPrivSysPackageParentLPw( 2113 PackageParser.Package pkg) { 2114 if (pkg.parentPackage == null) { 2115 return; 2116 } 2117 if (pkg.requestedPermissions == null) { 2118 return; 2119 } 2120 final PackageSetting disabledSysParentPs = mSettings 2121 .getDisabledSystemPkgLPr(pkg.parentPackage.packageName); 2122 if (disabledSysParentPs == null || disabledSysParentPs.pkg == null 2123 || !disabledSysParentPs.isPrivileged() 2124 || (disabledSysParentPs.childPackageNames != null 2125 && !disabledSysParentPs.childPackageNames.isEmpty())) { 2126 return; 2127 } 2128 final int[] allUserIds = sUserManager.getUserIds(); 2129 final int permCount = pkg.requestedPermissions.size(); 2130 for (int i = 0; i < permCount; i++) { 2131 String permission = pkg.requestedPermissions.get(i); 2132 BasePermission bp = mSettings.mPermissions.get(permission); 2133 if (bp == null || !(bp.isRuntime() || bp.isDevelopment())) { 2134 continue; 2135 } 2136 for (int userId : allUserIds) { 2137 if (disabledSysParentPs.getPermissionsState().hasRuntimePermission( 2138 permission, userId)) { 2139 grantRuntimePermission(pkg.packageName, permission, userId); 2140 } 2141 } 2142 } 2143 } 2144 2145 private StorageEventListener mStorageListener = new StorageEventListener() { 2146 @Override 2147 public void onVolumeStateChanged(VolumeInfo vol, int oldState, int newState) { 2148 if (vol.type == VolumeInfo.TYPE_PRIVATE) { 2149 if (vol.state == VolumeInfo.STATE_MOUNTED) { 2150 final String volumeUuid = vol.getFsUuid(); 2151 2152 // Clean up any users or apps that were removed or recreated 2153 // while this volume was missing 2154 sUserManager.reconcileUsers(volumeUuid); 2155 reconcileApps(volumeUuid); 2156 2157 // Clean up any install sessions that expired or were 2158 // cancelled while this volume was missing 2159 mInstallerService.onPrivateVolumeMounted(volumeUuid); 2160 2161 loadPrivatePackages(vol); 2162 2163 } else if (vol.state == VolumeInfo.STATE_EJECTING) { 2164 unloadPrivatePackages(vol); 2165 } 2166 } 2167 2168 if (vol.type == VolumeInfo.TYPE_PUBLIC && vol.isPrimary()) { 2169 if (vol.state == VolumeInfo.STATE_MOUNTED) { 2170 updateExternalMediaStatus(true, false); 2171 } else if (vol.state == VolumeInfo.STATE_EJECTING) { 2172 updateExternalMediaStatus(false, false); 2173 } 2174 } 2175 } 2176 2177 @Override 2178 public void onVolumeForgotten(String fsUuid) { 2179 if (TextUtils.isEmpty(fsUuid)) { 2180 Slog.e(TAG, "Forgetting internal storage is probably a mistake; ignoring"); 2181 return; 2182 } 2183 2184 // Remove any apps installed on the forgotten volume 2185 synchronized (mPackages) { 2186 final List<PackageSetting> packages = mSettings.getVolumePackagesLPr(fsUuid); 2187 for (PackageSetting ps : packages) { 2188 Slog.d(TAG, "Destroying " + ps.name + " because volume was forgotten"); 2189 deletePackageVersioned(new VersionedPackage(ps.name, 2190 PackageManager.VERSION_CODE_HIGHEST), 2191 new LegacyPackageDeleteObserver(null).getBinder(), 2192 UserHandle.USER_SYSTEM, PackageManager.DELETE_ALL_USERS); 2193 // Try very hard to release any references to this package 2194 // so we don't risk the system server being killed due to 2195 // open FDs 2196 AttributeCache.instance().removePackage(ps.name); 2197 } 2198 2199 mSettings.onVolumeForgotten(fsUuid); 2200 mSettings.writeLPr(); 2201 } 2202 } 2203 }; 2204 2205 private void grantRequestedRuntimePermissions(PackageParser.Package pkg, int[] userIds, 2206 String[] grantedPermissions) { 2207 for (int userId : userIds) { 2208 grantRequestedRuntimePermissionsForUser(pkg, userId, grantedPermissions); 2209 } 2210 } 2211 2212 private void grantRequestedRuntimePermissionsForUser(PackageParser.Package pkg, int userId, 2213 String[] grantedPermissions) { 2214 PackageSetting ps = (PackageSetting) pkg.mExtras; 2215 if (ps == null) { 2216 return; 2217 } 2218 2219 PermissionsState permissionsState = ps.getPermissionsState(); 2220 2221 final int immutableFlags = PackageManager.FLAG_PERMISSION_SYSTEM_FIXED 2222 | PackageManager.FLAG_PERMISSION_POLICY_FIXED; 2223 2224 final boolean supportsRuntimePermissions = pkg.applicationInfo.targetSdkVersion 2225 >= Build.VERSION_CODES.M; 2226 2227 final boolean instantApp = isInstantApp(pkg.packageName, userId); 2228 2229 for (String permission : pkg.requestedPermissions) { 2230 final BasePermission bp; 2231 synchronized (mPackages) { 2232 bp = mSettings.mPermissions.get(permission); 2233 } 2234 if (bp != null && (bp.isRuntime() || bp.isDevelopment()) 2235 && (!instantApp || bp.isInstant()) 2236 && (supportsRuntimePermissions || !bp.isRuntimeOnly()) 2237 && (grantedPermissions == null 2238 || ArrayUtils.contains(grantedPermissions, permission))) { 2239 final int flags = permissionsState.getPermissionFlags(permission, userId); 2240 if (supportsRuntimePermissions) { 2241 // Installer cannot change immutable permissions. 2242 if ((flags & immutableFlags) == 0) { 2243 grantRuntimePermission(pkg.packageName, permission, userId); 2244 } 2245 } else if (mPermissionReviewRequired) { 2246 // In permission review mode we clear the review flag when we 2247 // are asked to install the app with all permissions granted. 2248 if ((flags & PackageManager.FLAG_PERMISSION_REVIEW_REQUIRED) != 0) { 2249 updatePermissionFlags(permission, pkg.packageName, 2250 PackageManager.FLAG_PERMISSION_REVIEW_REQUIRED, 0, userId); 2251 } 2252 } 2253 } 2254 } 2255 } 2256 2257 Bundle extrasForInstallResult(PackageInstalledInfo res) { 2258 Bundle extras = null; 2259 switch (res.returnCode) { 2260 case PackageManager.INSTALL_FAILED_DUPLICATE_PERMISSION: { 2261 extras = new Bundle(); 2262 extras.putString(PackageManager.EXTRA_FAILURE_EXISTING_PERMISSION, 2263 res.origPermission); 2264 extras.putString(PackageManager.EXTRA_FAILURE_EXISTING_PACKAGE, 2265 res.origPackage); 2266 break; 2267 } 2268 case PackageManager.INSTALL_SUCCEEDED: { 2269 extras = new Bundle(); 2270 extras.putBoolean(Intent.EXTRA_REPLACING, 2271 res.removedInfo != null && res.removedInfo.removedPackage != null); 2272 break; 2273 } 2274 } 2275 return extras; 2276 } 2277 2278 void scheduleWriteSettingsLocked() { 2279 if (!mHandler.hasMessages(WRITE_SETTINGS)) { 2280 mHandler.sendEmptyMessageDelayed(WRITE_SETTINGS, WRITE_SETTINGS_DELAY); 2281 } 2282 } 2283 2284 void scheduleWritePackageListLocked(int userId) { 2285 if (!mHandler.hasMessages(WRITE_PACKAGE_LIST)) { 2286 Message msg = mHandler.obtainMessage(WRITE_PACKAGE_LIST); 2287 msg.arg1 = userId; 2288 mHandler.sendMessageDelayed(msg, WRITE_SETTINGS_DELAY); 2289 } 2290 } 2291 2292 void scheduleWritePackageRestrictionsLocked(UserHandle user) { 2293 final int userId = user == null ? UserHandle.USER_ALL : user.getIdentifier(); 2294 scheduleWritePackageRestrictionsLocked(userId); 2295 } 2296 2297 void scheduleWritePackageRestrictionsLocked(int userId) { 2298 final int[] userIds = (userId == UserHandle.USER_ALL) 2299 ? sUserManager.getUserIds() : new int[]{userId}; 2300 for (int nextUserId : userIds) { 2301 if (!sUserManager.exists(nextUserId)) return; 2302 mDirtyUsers.add(nextUserId); 2303 if (!mHandler.hasMessages(WRITE_PACKAGE_RESTRICTIONS)) { 2304 mHandler.sendEmptyMessageDelayed(WRITE_PACKAGE_RESTRICTIONS, WRITE_SETTINGS_DELAY); 2305 } 2306 } 2307 } 2308 2309 public static PackageManagerService main(Context context, Installer installer, 2310 boolean factoryTest, boolean onlyCore) { 2311 // Self-check for initial settings. 2312 PackageManagerServiceCompilerMapping.checkProperties(); 2313 2314 PackageManagerService m = new PackageManagerService(context, installer, 2315 factoryTest, onlyCore); 2316 m.enableSystemUserPackages(); 2317 ServiceManager.addService("package", m); 2318 final PackageManagerNative pmn = m.new PackageManagerNative(); 2319 ServiceManager.addService("package_native", pmn); 2320 return m; 2321 } 2322 2323 private void enableSystemUserPackages() { 2324 if (!UserManager.isSplitSystemUser()) { 2325 return; 2326 } 2327 // For system user, enable apps based on the following conditions: 2328 // - app is whitelisted or belong to one of these groups: 2329 // -- system app which has no launcher icons 2330 // -- system app which has INTERACT_ACROSS_USERS permission 2331 // -- system IME app 2332 // - app is not in the blacklist 2333 AppsQueryHelper queryHelper = new AppsQueryHelper(this); 2334 Set<String> enableApps = new ArraySet<>(); 2335 enableApps.addAll(queryHelper.queryApps(AppsQueryHelper.GET_NON_LAUNCHABLE_APPS 2336 | AppsQueryHelper.GET_APPS_WITH_INTERACT_ACROSS_USERS_PERM 2337 | AppsQueryHelper.GET_IMES, /* systemAppsOnly */ true, UserHandle.SYSTEM)); 2338 ArraySet<String> wlApps = SystemConfig.getInstance().getSystemUserWhitelistedApps(); 2339 enableApps.addAll(wlApps); 2340 enableApps.addAll(queryHelper.queryApps(AppsQueryHelper.GET_REQUIRED_FOR_SYSTEM_USER, 2341 /* systemAppsOnly */ false, UserHandle.SYSTEM)); 2342 ArraySet<String> blApps = SystemConfig.getInstance().getSystemUserBlacklistedApps(); 2343 enableApps.removeAll(blApps); 2344 Log.i(TAG, "Applications installed for system user: " + enableApps); 2345 List<String> allAps = queryHelper.queryApps(0, /* systemAppsOnly */ false, 2346 UserHandle.SYSTEM); 2347 final int allAppsSize = allAps.size(); 2348 synchronized (mPackages) { 2349 for (int i = 0; i < allAppsSize; i++) { 2350 String pName = allAps.get(i); 2351 PackageSetting pkgSetting = mSettings.mPackages.get(pName); 2352 // Should not happen, but we shouldn't be failing if it does 2353 if (pkgSetting == null) { 2354 continue; 2355 } 2356 boolean install = enableApps.contains(pName); 2357 if (pkgSetting.getInstalled(UserHandle.USER_SYSTEM) != install) { 2358 Log.i(TAG, (install ? "Installing " : "Uninstalling ") + pName 2359 + " for system user"); 2360 pkgSetting.setInstalled(install, UserHandle.USER_SYSTEM); 2361 } 2362 } 2363 scheduleWritePackageRestrictionsLocked(UserHandle.USER_SYSTEM); 2364 } 2365 } 2366 2367 private static void getDefaultDisplayMetrics(Context context, DisplayMetrics metrics) { 2368 DisplayManager displayManager = (DisplayManager) context.getSystemService( 2369 Context.DISPLAY_SERVICE); 2370 displayManager.getDisplay(Display.DEFAULT_DISPLAY).getMetrics(metrics); 2371 } 2372 2373 /** 2374 * Requests that files preopted on a secondary system partition be copied to the data partition 2375 * if possible. Note that the actual copying of the files is accomplished by init for security 2376 * reasons. This simply requests that the copy takes place and awaits confirmation of its 2377 * completion. See platform/system/extras/cppreopt/ for the implementation of the actual copy. 2378 */ 2379 private static void requestCopyPreoptedFiles() { 2380 final int WAIT_TIME_MS = 100; 2381 final String CP_PREOPT_PROPERTY = "sys.cppreopt"; 2382 if (SystemProperties.getInt("ro.cp_system_other_odex", 0) == 1) { 2383 SystemProperties.set(CP_PREOPT_PROPERTY, "requested"); 2384 // We will wait for up to 100 seconds. 2385 final long timeStart = SystemClock.uptimeMillis(); 2386 final long timeEnd = timeStart + 100 * 1000; 2387 long timeNow = timeStart; 2388 while (!SystemProperties.get(CP_PREOPT_PROPERTY).equals("finished")) { 2389 try { 2390 Thread.sleep(WAIT_TIME_MS); 2391 } catch (InterruptedException e) { 2392 // Do nothing 2393 } 2394 timeNow = SystemClock.uptimeMillis(); 2395 if (timeNow > timeEnd) { 2396 SystemProperties.set(CP_PREOPT_PROPERTY, "timed-out"); 2397 Slog.wtf(TAG, "cppreopt did not finish!"); 2398 break; 2399 } 2400 } 2401 2402 Slog.i(TAG, "cppreopts took " + (timeNow - timeStart) + " ms"); 2403 } 2404 } 2405 2406 public PackageManagerService(Context context, Installer installer, 2407 boolean factoryTest, boolean onlyCore) { 2408 LockGuard.installLock(mPackages, LockGuard.INDEX_PACKAGES); 2409 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "create package manager"); 2410 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_PMS_START, 2411 SystemClock.uptimeMillis()); 2412 2413 if (mSdkVersion <= 0) { 2414 Slog.w(TAG, "**** ro.build.version.sdk not set!"); 2415 } 2416 2417 mContext = context; 2418 2419 mPermissionReviewRequired = context.getResources().getBoolean( 2420 R.bool.config_permissionReviewRequired); 2421 2422 mFactoryTest = factoryTest; 2423 mOnlyCore = onlyCore; 2424 mMetrics = new DisplayMetrics(); 2425 mSettings = new Settings(mPackages); 2426 mSettings.addSharedUserLPw("android.uid.system", Process.SYSTEM_UID, 2427 ApplicationInfo.FLAG_SYSTEM, ApplicationInfo.PRIVATE_FLAG_PRIVILEGED); 2428 mSettings.addSharedUserLPw("android.uid.phone", RADIO_UID, 2429 ApplicationInfo.FLAG_SYSTEM, ApplicationInfo.PRIVATE_FLAG_PRIVILEGED); 2430 mSettings.addSharedUserLPw("android.uid.log", LOG_UID, 2431 ApplicationInfo.FLAG_SYSTEM, ApplicationInfo.PRIVATE_FLAG_PRIVILEGED); 2432 mSettings.addSharedUserLPw("android.uid.nfc", NFC_UID, 2433 ApplicationInfo.FLAG_SYSTEM, ApplicationInfo.PRIVATE_FLAG_PRIVILEGED); 2434 mSettings.addSharedUserLPw("android.uid.bluetooth", BLUETOOTH_UID, 2435 ApplicationInfo.FLAG_SYSTEM, ApplicationInfo.PRIVATE_FLAG_PRIVILEGED); 2436 mSettings.addSharedUserLPw("android.uid.shell", SHELL_UID, 2437 ApplicationInfo.FLAG_SYSTEM, ApplicationInfo.PRIVATE_FLAG_PRIVILEGED); 2438 2439 String separateProcesses = SystemProperties.get("debug.separate_processes"); 2440 if (separateProcesses != null && separateProcesses.length() > 0) { 2441 if ("*".equals(separateProcesses)) { 2442 mDefParseFlags = PackageParser.PARSE_IGNORE_PROCESSES; 2443 mSeparateProcesses = null; 2444 Slog.w(TAG, "Running with debug.separate_processes: * (ALL)"); 2445 } else { 2446 mDefParseFlags = 0; 2447 mSeparateProcesses = separateProcesses.split(","); 2448 Slog.w(TAG, "Running with debug.separate_processes: " 2449 + separateProcesses); 2450 } 2451 } else { 2452 mDefParseFlags = 0; 2453 mSeparateProcesses = null; 2454 } 2455 2456 mInstaller = installer; 2457 mPackageDexOptimizer = new PackageDexOptimizer(installer, mInstallLock, context, 2458 "*dexopt*"); 2459 mDexManager = new DexManager(this, mPackageDexOptimizer, installer, mInstallLock); 2460 mMoveCallbacks = new MoveCallbacks(FgThread.get().getLooper()); 2461 2462 mOnPermissionChangeListeners = new OnPermissionChangeListeners( 2463 FgThread.get().getLooper()); 2464 2465 getDefaultDisplayMetrics(context, mMetrics); 2466 2467 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "get system config"); 2468 SystemConfig systemConfig = SystemConfig.getInstance(); 2469 mGlobalGids = systemConfig.getGlobalGids(); 2470 mSystemPermissions = systemConfig.getSystemPermissions(); 2471 mAvailableFeatures = systemConfig.getAvailableFeatures(); 2472 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 2473 2474 mProtectedPackages = new ProtectedPackages(mContext); 2475 2476 synchronized (mInstallLock) { 2477 // writer 2478 synchronized (mPackages) { 2479 mHandlerThread = new ServiceThread(TAG, 2480 Process.THREAD_PRIORITY_BACKGROUND, true /*allowIo*/); 2481 mHandlerThread.start(); 2482 mHandler = new PackageHandler(mHandlerThread.getLooper()); 2483 mProcessLoggingHandler = new ProcessLoggingHandler(); 2484 Watchdog.getInstance().addThread(mHandler, WATCHDOG_TIMEOUT); 2485 2486 mDefaultPermissionPolicy = new DefaultPermissionGrantPolicy(this); 2487 mInstantAppRegistry = new InstantAppRegistry(this); 2488 2489 File dataDir = Environment.getDataDirectory(); 2490 mAppInstallDir = new File(dataDir, "app"); 2491 mAppLib32InstallDir = new File(dataDir, "app-lib"); 2492 mAsecInternalPath = new File(dataDir, "app-asec").getPath(); 2493 mDrmAppPrivateInstallDir = new File(dataDir, "app-private"); 2494 sUserManager = new UserManagerService(context, this, 2495 new UserDataPreparer(mInstaller, mInstallLock, mContext, mOnlyCore), mPackages); 2496 2497 // Propagate permission configuration in to package manager. 2498 ArrayMap<String, SystemConfig.PermissionEntry> permConfig 2499 = systemConfig.getPermissions(); 2500 for (int i=0; i<permConfig.size(); i++) { 2501 SystemConfig.PermissionEntry perm = permConfig.valueAt(i); 2502 BasePermission bp = mSettings.mPermissions.get(perm.name); 2503 if (bp == null) { 2504 bp = new BasePermission(perm.name, "android", BasePermission.TYPE_BUILTIN); 2505 mSettings.mPermissions.put(perm.name, bp); 2506 } 2507 if (perm.gids != null) { 2508 bp.setGids(perm.gids, perm.perUser); 2509 } 2510 } 2511 2512 ArrayMap<String, String> libConfig = systemConfig.getSharedLibraries(); 2513 final int builtInLibCount = libConfig.size(); 2514 for (int i = 0; i < builtInLibCount; i++) { 2515 String name = libConfig.keyAt(i); 2516 String path = libConfig.valueAt(i); 2517 addSharedLibraryLPw(path, null, name, SharedLibraryInfo.VERSION_UNDEFINED, 2518 SharedLibraryInfo.TYPE_BUILTIN, PLATFORM_PACKAGE_NAME, 0); 2519 } 2520 2521 mFoundPolicyFile = SELinuxMMAC.readInstallPolicy(); 2522 2523 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "read user settings"); 2524 mFirstBoot = !mSettings.readLPw(sUserManager.getUsers(false)); 2525 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 2526 2527 // Clean up orphaned packages for which the code path doesn't exist 2528 // and they are an update to a system app - caused by bug/32321269 2529 final int packageSettingCount = mSettings.mPackages.size(); 2530 for (int i = packageSettingCount - 1; i >= 0; i--) { 2531 PackageSetting ps = mSettings.mPackages.valueAt(i); 2532 if (!isExternal(ps) && (ps.codePath == null || !ps.codePath.exists()) 2533 && mSettings.getDisabledSystemPkgLPr(ps.name) != null) { 2534 mSettings.mPackages.removeAt(i); 2535 mSettings.enableSystemPackageLPw(ps.name); 2536 } 2537 } 2538 2539 if (mFirstBoot) { 2540 requestCopyPreoptedFiles(); 2541 } 2542 2543 String customResolverActivity = Resources.getSystem().getString( 2544 R.string.config_customResolverActivity); 2545 if (TextUtils.isEmpty(customResolverActivity)) { 2546 customResolverActivity = null; 2547 } else { 2548 mCustomResolverComponentName = ComponentName.unflattenFromString( 2549 customResolverActivity); 2550 } 2551 2552 long startTime = SystemClock.uptimeMillis(); 2553 2554 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_PMS_SYSTEM_SCAN_START, 2555 startTime); 2556 2557 final String bootClassPath = System.getenv("BOOTCLASSPATH"); 2558 final String systemServerClassPath = System.getenv("SYSTEMSERVERCLASSPATH"); 2559 2560 if (bootClassPath == null) { 2561 Slog.w(TAG, "No BOOTCLASSPATH found!"); 2562 } 2563 2564 if (systemServerClassPath == null) { 2565 Slog.w(TAG, "No SYSTEMSERVERCLASSPATH found!"); 2566 } 2567 2568 File frameworkDir = new File(Environment.getRootDirectory(), "framework"); 2569 2570 final VersionInfo ver = mSettings.getInternalVersion(); 2571 mIsUpgrade = !Build.FINGERPRINT.equals(ver.fingerprint); 2572 if (mIsUpgrade) { 2573 logCriticalInfo(Log.INFO, 2574 "Upgrading from " + ver.fingerprint + " to " + Build.FINGERPRINT); 2575 } 2576 2577 // when upgrading from pre-M, promote system app permissions from install to runtime 2578 mPromoteSystemApps = 2579 mIsUpgrade && ver.sdkVersion <= Build.VERSION_CODES.LOLLIPOP_MR1; 2580 2581 // When upgrading from pre-N, we need to handle package extraction like first boot, 2582 // as there is no profiling data available. 2583 mIsPreNUpgrade = mIsUpgrade && ver.sdkVersion < Build.VERSION_CODES.N; 2584 2585 mIsPreNMR1Upgrade = mIsUpgrade && ver.sdkVersion < Build.VERSION_CODES.N_MR1; 2586 2587 // save off the names of pre-existing system packages prior to scanning; we don't 2588 // want to automatically grant runtime permissions for new system apps 2589 if (mPromoteSystemApps) { 2590 Iterator<PackageSetting> pkgSettingIter = mSettings.mPackages.values().iterator(); 2591 while (pkgSettingIter.hasNext()) { 2592 PackageSetting ps = pkgSettingIter.next(); 2593 if (isSystemApp(ps)) { 2594 mExistingSystemPackages.add(ps.name); 2595 } 2596 } 2597 } 2598 2599 mCacheDir = preparePackageParserCache(mIsUpgrade); 2600 2601 // Set flag to monitor and not change apk file paths when 2602 // scanning install directories. 2603 int scanFlags = SCAN_BOOTING | SCAN_INITIAL; 2604 2605 if (mIsUpgrade || mFirstBoot) { 2606 scanFlags = scanFlags | SCAN_FIRST_BOOT_OR_UPGRADE; 2607 } 2608 2609 // Collect vendor overlay packages. (Do this before scanning any apps.) 2610 // For security and version matching reason, only consider 2611 // overlay packages if they reside in the right directory. 2612 scanDirTracedLI(new File(VENDOR_OVERLAY_DIR), mDefParseFlags 2613 | PackageParser.PARSE_IS_SYSTEM 2614 | PackageParser.PARSE_IS_SYSTEM_DIR 2615 | PackageParser.PARSE_TRUSTED_OVERLAY, scanFlags | SCAN_TRUSTED_OVERLAY, 0); 2616 2617 mParallelPackageParserCallback.findStaticOverlayPackages(); 2618 2619 // Find base frameworks (resource packages without code). 2620 scanDirTracedLI(frameworkDir, mDefParseFlags 2621 | PackageParser.PARSE_IS_SYSTEM 2622 | PackageParser.PARSE_IS_SYSTEM_DIR 2623 | PackageParser.PARSE_IS_PRIVILEGED, 2624 scanFlags | SCAN_NO_DEX, 0); 2625 2626 // Collected privileged system packages. 2627 final File privilegedAppDir = new File(Environment.getRootDirectory(), "priv-app"); 2628 scanDirTracedLI(privilegedAppDir, mDefParseFlags 2629 | PackageParser.PARSE_IS_SYSTEM 2630 | PackageParser.PARSE_IS_SYSTEM_DIR 2631 | PackageParser.PARSE_IS_PRIVILEGED, scanFlags, 0); 2632 2633 // Collect ordinary system packages. 2634 final File systemAppDir = new File(Environment.getRootDirectory(), "app"); 2635 scanDirTracedLI(systemAppDir, mDefParseFlags 2636 | PackageParser.PARSE_IS_SYSTEM 2637 | PackageParser.PARSE_IS_SYSTEM_DIR, scanFlags, 0); 2638 2639 // Collect all vendor packages. 2640 File vendorAppDir = new File("/vendor/app"); 2641 try { 2642 vendorAppDir = vendorAppDir.getCanonicalFile(); 2643 } catch (IOException e) { 2644 // failed to look up canonical path, continue with original one 2645 } 2646 scanDirTracedLI(vendorAppDir, mDefParseFlags 2647 | PackageParser.PARSE_IS_SYSTEM 2648 | PackageParser.PARSE_IS_SYSTEM_DIR, scanFlags, 0); 2649 2650 // Collect all OEM packages. 2651 final File oemAppDir = new File(Environment.getOemDirectory(), "app"); 2652 scanDirTracedLI(oemAppDir, mDefParseFlags 2653 | PackageParser.PARSE_IS_SYSTEM 2654 | PackageParser.PARSE_IS_SYSTEM_DIR, scanFlags, 0); 2655 2656 // Prune any system packages that no longer exist. 2657 final List<String> possiblyDeletedUpdatedSystemApps = new ArrayList<>(); 2658 // Stub packages must either be replaced with full versions in the /data 2659 // partition or be disabled. 2660 final List<String> stubSystemApps = new ArrayList<>(); 2661 if (!mOnlyCore) { 2662 // do this first before mucking with mPackages for the "expecting better" case 2663 final Iterator<PackageParser.Package> pkgIterator = mPackages.values().iterator(); 2664 while (pkgIterator.hasNext()) { 2665 final PackageParser.Package pkg = pkgIterator.next(); 2666 if (pkg.isStub) { 2667 stubSystemApps.add(pkg.packageName); 2668 } 2669 } 2670 2671 final Iterator<PackageSetting> psit = mSettings.mPackages.values().iterator(); 2672 while (psit.hasNext()) { 2673 PackageSetting ps = psit.next(); 2674 2675 /* 2676 * If this is not a system app, it can't be a 2677 * disable system app. 2678 */ 2679 if ((ps.pkgFlags & ApplicationInfo.FLAG_SYSTEM) == 0) { 2680 continue; 2681 } 2682 2683 /* 2684 * If the package is scanned, it's not erased. 2685 */ 2686 final PackageParser.Package scannedPkg = mPackages.get(ps.name); 2687 if (scannedPkg != null) { 2688 /* 2689 * If the system app is both scanned and in the 2690 * disabled packages list, then it must have been 2691 * added via OTA. Remove it from the currently 2692 * scanned package so the previously user-installed 2693 * application can be scanned. 2694 */ 2695 if (mSettings.isDisabledSystemPackageLPr(ps.name)) { 2696 logCriticalInfo(Log.WARN, "Expecting better updated system app for " 2697 + ps.name + "; removing system app. Last known codePath=" 2698 + ps.codePathString + ", installStatus=" + ps.installStatus 2699 + ", versionCode=" + ps.versionCode + "; scanned versionCode=" 2700 + scannedPkg.mVersionCode); 2701 removePackageLI(scannedPkg, true); 2702 mExpectingBetter.put(ps.name, ps.codePath); 2703 } 2704 2705 continue; 2706 } 2707 2708 if (!mSettings.isDisabledSystemPackageLPr(ps.name)) { 2709 psit.remove(); 2710 logCriticalInfo(Log.WARN, "System package " + ps.name 2711 + " no longer exists; it's data will be wiped"); 2712 // Actual deletion of code and data will be handled by later 2713 // reconciliation step 2714 } else { 2715 // we still have a disabled system package, but, it still might have 2716 // been removed. check the code path still exists and check there's 2717 // still a package. the latter can happen if an OTA keeps the same 2718 // code path, but, changes the package name. 2719 final PackageSetting disabledPs = 2720 mSettings.getDisabledSystemPkgLPr(ps.name); 2721 if (disabledPs.codePath == null || !disabledPs.codePath.exists() 2722 || disabledPs.pkg == null) { 2723 possiblyDeletedUpdatedSystemApps.add(ps.name); 2724 } 2725 } 2726 } 2727 } 2728 2729 //look for any incomplete package installations 2730 ArrayList<PackageSetting> deletePkgsList = mSettings.getListOfIncompleteInstallPackagesLPr(); 2731 for (int i = 0; i < deletePkgsList.size(); i++) { 2732 // Actual deletion of code and data will be handled by later 2733 // reconciliation step 2734 final String packageName = deletePkgsList.get(i).name; 2735 logCriticalInfo(Log.WARN, "Cleaning up incompletely installed app: " + packageName); 2736 synchronized (mPackages) { 2737 mSettings.removePackageLPw(packageName); 2738 } 2739 } 2740 2741 //delete tmp files 2742 deleteTempPackageFiles(); 2743 2744 final int cachedSystemApps = PackageParser.sCachedPackageReadCount.get(); 2745 2746 // Remove any shared userIDs that have no associated packages 2747 mSettings.pruneSharedUsersLPw(); 2748 final long systemScanTime = SystemClock.uptimeMillis() - startTime; 2749 final int systemPackagesCount = mPackages.size(); 2750 Slog.i(TAG, "Finished scanning system apps. Time: " + systemScanTime 2751 + " ms, packageCount: " + systemPackagesCount 2752 + " , timePerPackage: " 2753 + (systemPackagesCount == 0 ? 0 : systemScanTime / systemPackagesCount) 2754 + " , cached: " + cachedSystemApps); 2755 if (mIsUpgrade && systemPackagesCount > 0) { 2756 MetricsLogger.histogram(null, "ota_package_manager_system_app_avg_scan_time", 2757 ((int) systemScanTime) / systemPackagesCount); 2758 } 2759 if (!mOnlyCore) { 2760 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_PMS_DATA_SCAN_START, 2761 SystemClock.uptimeMillis()); 2762 scanDirTracedLI(mAppInstallDir, 0, scanFlags | SCAN_REQUIRE_KNOWN, 0); 2763 2764 scanDirTracedLI(mDrmAppPrivateInstallDir, mDefParseFlags 2765 | PackageParser.PARSE_FORWARD_LOCK, 2766 scanFlags | SCAN_REQUIRE_KNOWN, 0); 2767 2768 // Remove disable package settings for updated system apps that were 2769 // removed via an OTA. If the update is no longer present, remove the 2770 // app completely. Otherwise, revoke their system privileges. 2771 for (String deletedAppName : possiblyDeletedUpdatedSystemApps) { 2772 PackageParser.Package deletedPkg = mPackages.get(deletedAppName); 2773 mSettings.removeDisabledSystemPackageLPw(deletedAppName); 2774 2775 final String msg; 2776 if (deletedPkg == null) { 2777 // should have found an update, but, we didn't; remove everything 2778 msg = "Updated system package " + deletedAppName 2779 + " no longer exists; removing its data"; 2780 // Actual deletion of code and data will be handled by later 2781 // reconciliation step 2782 } else { 2783 // found an update; revoke system privileges 2784 msg = "Updated system package + " + deletedAppName 2785 + " no longer exists; revoking system privileges"; 2786 2787 // Don't do anything if a stub is removed from the system image. If 2788 // we were to remove the uncompressed version from the /data partition, 2789 // this is where it'd be done. 2790 2791 final PackageSetting deletedPs = mSettings.mPackages.get(deletedAppName); 2792 deletedPkg.applicationInfo.flags &= ~ApplicationInfo.FLAG_SYSTEM; 2793 deletedPs.pkgFlags &= ~ApplicationInfo.FLAG_SYSTEM; 2794 } 2795 logCriticalInfo(Log.WARN, msg); 2796 } 2797 2798 /* 2799 * Make sure all system apps that we expected to appear on 2800 * the userdata partition actually showed up. If they never 2801 * appeared, crawl back and revive the system version. 2802 */ 2803 for (int i = 0; i < mExpectingBetter.size(); i++) { 2804 final String packageName = mExpectingBetter.keyAt(i); 2805 if (!mPackages.containsKey(packageName)) { 2806 final File scanFile = mExpectingBetter.valueAt(i); 2807 2808 logCriticalInfo(Log.WARN, "Expected better " + packageName 2809 + " but never showed up; reverting to system"); 2810 2811 int reparseFlags = mDefParseFlags; 2812 if (FileUtils.contains(privilegedAppDir, scanFile)) { 2813 reparseFlags = PackageParser.PARSE_IS_SYSTEM 2814 | PackageParser.PARSE_IS_SYSTEM_DIR 2815 | PackageParser.PARSE_IS_PRIVILEGED; 2816 } else if (FileUtils.contains(systemAppDir, scanFile)) { 2817 reparseFlags = PackageParser.PARSE_IS_SYSTEM 2818 | PackageParser.PARSE_IS_SYSTEM_DIR; 2819 } else if (FileUtils.contains(vendorAppDir, scanFile)) { 2820 reparseFlags = PackageParser.PARSE_IS_SYSTEM 2821 | PackageParser.PARSE_IS_SYSTEM_DIR; 2822 } else if (FileUtils.contains(oemAppDir, scanFile)) { 2823 reparseFlags = PackageParser.PARSE_IS_SYSTEM 2824 | PackageParser.PARSE_IS_SYSTEM_DIR; 2825 } else { 2826 Slog.e(TAG, "Ignoring unexpected fallback path " + scanFile); 2827 continue; 2828 } 2829 2830 mSettings.enableSystemPackageLPw(packageName); 2831 2832 try { 2833 scanPackageTracedLI(scanFile, reparseFlags, scanFlags, 0, null); 2834 } catch (PackageManagerException e) { 2835 Slog.e(TAG, "Failed to parse original system package: " 2836 + e.getMessage()); 2837 } 2838 } 2839 } 2840 2841 // Uncompress and install any stubbed system applications. 2842 // This must be done last to ensure all stubs are replaced or disabled. 2843 decompressSystemApplications(stubSystemApps, scanFlags); 2844 2845 final int cachedNonSystemApps = PackageParser.sCachedPackageReadCount.get() 2846 - cachedSystemApps; 2847 2848 final long dataScanTime = SystemClock.uptimeMillis() - systemScanTime - startTime; 2849 final int dataPackagesCount = mPackages.size() - systemPackagesCount; 2850 Slog.i(TAG, "Finished scanning non-system apps. Time: " + dataScanTime 2851 + " ms, packageCount: " + dataPackagesCount 2852 + " , timePerPackage: " 2853 + (dataPackagesCount == 0 ? 0 : dataScanTime / dataPackagesCount) 2854 + " , cached: " + cachedNonSystemApps); 2855 if (mIsUpgrade && dataPackagesCount > 0) { 2856 MetricsLogger.histogram(null, "ota_package_manager_data_app_avg_scan_time", 2857 ((int) dataScanTime) / dataPackagesCount); 2858 } 2859 } 2860 mExpectingBetter.clear(); 2861 2862 // Resolve the storage manager. 2863 mStorageManagerPackage = getStorageManagerPackageName(); 2864 2865 // Resolve protected action filters. Only the setup wizard is allowed to 2866 // have a high priority filter for these actions. 2867 mSetupWizardPackage = getSetupWizardPackageName(); 2868 if (mProtectedFilters.size() > 0) { 2869 if (DEBUG_FILTERS && mSetupWizardPackage == null) { 2870 Slog.i(TAG, "No setup wizard;" 2871 + " All protected intents capped to priority 0"); 2872 } 2873 for (ActivityIntentInfo filter : mProtectedFilters) { 2874 if (filter.activity.info.packageName.equals(mSetupWizardPackage)) { 2875 if (DEBUG_FILTERS) { 2876 Slog.i(TAG, "Found setup wizard;" 2877 + " allow priority " + filter.getPriority() + ";" 2878 + " package: " + filter.activity.info.packageName 2879 + " activity: " + filter.activity.className 2880 + " priority: " + filter.getPriority()); 2881 } 2882 // skip setup wizard; allow it to keep the high priority filter 2883 continue; 2884 } 2885 if (DEBUG_FILTERS) { 2886 Slog.i(TAG, "Protected action; cap priority to 0;" 2887 + " package: " + filter.activity.info.packageName 2888 + " activity: " + filter.activity.className 2889 + " origPrio: " + filter.getPriority()); 2890 } 2891 filter.setPriority(0); 2892 } 2893 } 2894 mDeferProtectedFilters = false; 2895 mProtectedFilters.clear(); 2896 2897 // Now that we know all of the shared libraries, update all clients to have 2898 // the correct library paths. 2899 updateAllSharedLibrariesLPw(null); 2900 2901 for (SharedUserSetting setting : mSettings.getAllSharedUsersLPw()) { 2902 // NOTE: We ignore potential failures here during a system scan (like 2903 // the rest of the commands above) because there's precious little we 2904 // can do about it. A settings error is reported, though. 2905 adjustCpuAbisForSharedUserLPw(setting.packages, null /*scannedPackage*/); 2906 } 2907 2908 // Now that we know all the packages we are keeping, 2909 // read and update their last usage times. 2910 mPackageUsage.read(mPackages); 2911 mCompilerStats.read(); 2912 2913 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_PMS_SCAN_END, 2914 SystemClock.uptimeMillis()); 2915 Slog.i(TAG, "Time to scan packages: " 2916 + ((SystemClock.uptimeMillis()-startTime)/1000f) 2917 + " seconds"); 2918 2919 // If the platform SDK has changed since the last time we booted, 2920 // we need to re-grant app permission to catch any new ones that 2921 // appear. This is really a hack, and means that apps can in some 2922 // cases get permissions that the user didn't initially explicitly 2923 // allow... it would be nice to have some better way to handle 2924 // this situation. 2925 int updateFlags = UPDATE_PERMISSIONS_ALL; 2926 if (ver.sdkVersion != mSdkVersion) { 2927 Slog.i(TAG, "Platform changed from " + ver.sdkVersion + " to " 2928 + mSdkVersion + "; regranting permissions for internal storage"); 2929 updateFlags |= UPDATE_PERMISSIONS_REPLACE_PKG | UPDATE_PERMISSIONS_REPLACE_ALL; 2930 } 2931 updatePermissionsLPw(null, null, StorageManager.UUID_PRIVATE_INTERNAL, updateFlags); 2932 ver.sdkVersion = mSdkVersion; 2933 2934 // If this is the first boot or an update from pre-M, and it is a normal 2935 // boot, then we need to initialize the default preferred apps across 2936 // all defined users. 2937 if (!onlyCore && (mPromoteSystemApps || mFirstBoot)) { 2938 for (UserInfo user : sUserManager.getUsers(true)) { 2939 mSettings.applyDefaultPreferredAppsLPw(this, user.id); 2940 applyFactoryDefaultBrowserLPw(user.id); 2941 primeDomainVerificationsLPw(user.id); 2942 } 2943 } 2944 2945 // Prepare storage for system user really early during boot, 2946 // since core system apps like SettingsProvider and SystemUI 2947 // can't wait for user to start 2948 final int storageFlags; 2949 if (StorageManager.isFileEncryptedNativeOrEmulated()) { 2950 storageFlags = StorageManager.FLAG_STORAGE_DE; 2951 } else { 2952 storageFlags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE; 2953 } 2954 List<String> deferPackages = reconcileAppsDataLI(StorageManager.UUID_PRIVATE_INTERNAL, 2955 UserHandle.USER_SYSTEM, storageFlags, true /* migrateAppData */, 2956 true /* onlyCoreApps */); 2957 mPrepareAppDataFuture = SystemServerInitThreadPool.get().submit(() -> { 2958 TimingsTraceLog traceLog = new TimingsTraceLog("SystemServerTimingAsync", 2959 Trace.TRACE_TAG_PACKAGE_MANAGER); 2960 traceLog.traceBegin("AppDataFixup"); 2961 try { 2962 mInstaller.fixupAppData(StorageManager.UUID_PRIVATE_INTERNAL, 2963 StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE); 2964 } catch (InstallerException e) { 2965 Slog.w(TAG, "Trouble fixing GIDs", e); 2966 } 2967 traceLog.traceEnd(); 2968 2969 traceLog.traceBegin("AppDataPrepare"); 2970 if (deferPackages == null || deferPackages.isEmpty()) { 2971 return; 2972 } 2973 int count = 0; 2974 for (String pkgName : deferPackages) { 2975 PackageParser.Package pkg = null; 2976 synchronized (mPackages) { 2977 PackageSetting ps = mSettings.getPackageLPr(pkgName); 2978 if (ps != null && ps.getInstalled(UserHandle.USER_SYSTEM)) { 2979 pkg = ps.pkg; 2980 } 2981 } 2982 if (pkg != null) { 2983 synchronized (mInstallLock) { 2984 prepareAppDataAndMigrateLIF(pkg, UserHandle.USER_SYSTEM, storageFlags, 2985 true /* maybeMigrateAppData */); 2986 } 2987 count++; 2988 } 2989 } 2990 traceLog.traceEnd(); 2991 Slog.i(TAG, "Deferred reconcileAppsData finished " + count + " packages"); 2992 }, "prepareAppData"); 2993 2994 // If this is first boot after an OTA, and a normal boot, then 2995 // we need to clear code cache directories. 2996 // Note that we do *not* clear the application profiles. These remain valid 2997 // across OTAs and are used to drive profile verification (post OTA) and 2998 // profile compilation (without waiting to collect a fresh set of profiles). 2999 if (mIsUpgrade && !onlyCore) { 3000 Slog.i(TAG, "Build fingerprint changed; clearing code caches"); 3001 for (int i = 0; i < mSettings.mPackages.size(); i++) { 3002 final PackageSetting ps = mSettings.mPackages.valueAt(i); 3003 if (Objects.equals(StorageManager.UUID_PRIVATE_INTERNAL, ps.volumeUuid)) { 3004 // No apps are running this early, so no need to freeze 3005 clearAppDataLIF(ps.pkg, UserHandle.USER_ALL, 3006 StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE 3007 | Installer.FLAG_CLEAR_CODE_CACHE_ONLY); 3008 } 3009 } 3010 ver.fingerprint = Build.FINGERPRINT; 3011 } 3012 3013 checkDefaultBrowser(); 3014 3015 // clear only after permissions and other defaults have been updated 3016 mExistingSystemPackages.clear(); 3017 mPromoteSystemApps = false; 3018 3019 // All the changes are done during package scanning. 3020 ver.databaseVersion = Settings.CURRENT_DATABASE_VERSION; 3021 3022 // can downgrade to reader 3023 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "write settings"); 3024 mSettings.writeLPr(); 3025 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 3026 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_PMS_READY, 3027 SystemClock.uptimeMillis()); 3028 3029 if (!mOnlyCore) { 3030 mRequiredVerifierPackage = getRequiredButNotReallyRequiredVerifierLPr(); 3031 mRequiredInstallerPackage = getRequiredInstallerLPr(); 3032 mRequiredUninstallerPackage = getRequiredUninstallerLPr(); 3033 mIntentFilterVerifierComponent = getIntentFilterVerifierComponentNameLPr(); 3034 if (mIntentFilterVerifierComponent != null) { 3035 mIntentFilterVerifier = new IntentVerifierProxy(mContext, 3036 mIntentFilterVerifierComponent); 3037 } else { 3038 mIntentFilterVerifier = null; 3039 } 3040 mServicesSystemSharedLibraryPackageName = getRequiredSharedLibraryLPr( 3041 PackageManager.SYSTEM_SHARED_LIBRARY_SERVICES, 3042 SharedLibraryInfo.VERSION_UNDEFINED); 3043 mSharedSystemSharedLibraryPackageName = getRequiredSharedLibraryLPr( 3044 PackageManager.SYSTEM_SHARED_LIBRARY_SHARED, 3045 SharedLibraryInfo.VERSION_UNDEFINED); 3046 } else { 3047 mRequiredVerifierPackage = null; 3048 mRequiredInstallerPackage = null; 3049 mRequiredUninstallerPackage = null; 3050 mIntentFilterVerifierComponent = null; 3051 mIntentFilterVerifier = null; 3052 mServicesSystemSharedLibraryPackageName = null; 3053 mSharedSystemSharedLibraryPackageName = null; 3054 } 3055 3056 mInstallerService = new PackageInstallerService(context, this); 3057 final Pair<ComponentName, String> instantAppResolverComponent = 3058 getInstantAppResolverLPr(); 3059 if (instantAppResolverComponent != null) { 3060 if (DEBUG_EPHEMERAL) { 3061 Slog.d(TAG, "Set ephemeral resolver: " + instantAppResolverComponent); 3062 } 3063 mInstantAppResolverConnection = new EphemeralResolverConnection( 3064 mContext, instantAppResolverComponent.first, 3065 instantAppResolverComponent.second); 3066 mInstantAppResolverSettingsComponent = 3067 getInstantAppResolverSettingsLPr(instantAppResolverComponent.first); 3068 } else { 3069 mInstantAppResolverConnection = null; 3070 mInstantAppResolverSettingsComponent = null; 3071 } 3072 updateInstantAppInstallerLocked(null); 3073 3074 // Read and update the usage of dex files. 3075 // Do this at the end of PM init so that all the packages have their 3076 // data directory reconciled. 3077 // At this point we know the code paths of the packages, so we can validate 3078 // the disk file and build the internal cache. 3079 // The usage file is expected to be small so loading and verifying it 3080 // should take a fairly small time compare to the other activities (e.g. package 3081 // scanning). 3082 final Map<Integer, List<PackageInfo>> userPackages = new HashMap<>(); 3083 final int[] currentUserIds = UserManagerService.getInstance().getUserIds(); 3084 for (int userId : currentUserIds) { 3085 userPackages.put(userId, getInstalledPackages(/*flags*/ 0, userId).getList()); 3086 } 3087 mDexManager.load(userPackages); 3088 if (mIsUpgrade) { 3089 MetricsLogger.histogram(null, "ota_package_manager_init_time", 3090 (int) (SystemClock.uptimeMillis() - startTime)); 3091 } 3092 } // synchronized (mPackages) 3093 } // synchronized (mInstallLock) 3094 3095 // Now after opening every single application zip, make sure they 3096 // are all flushed. Not really needed, but keeps things nice and 3097 // tidy. 3098 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "GC"); 3099 Runtime.getRuntime().gc(); 3100 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 3101 3102 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "loadFallbacks"); 3103 FallbackCategoryProvider.loadFallbacks(); 3104 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 3105 3106 // The initial scanning above does many calls into installd while 3107 // holding the mPackages lock, but we're mostly interested in yelling 3108 // once we have a booted system. 3109 mInstaller.setWarnIfHeld(mPackages); 3110 3111 // Expose private service for system components to use. 3112 LocalServices.addService(PackageManagerInternal.class, new PackageManagerInternalImpl()); 3113 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 3114 } 3115 3116 /** 3117 * Uncompress and install stub applications. 3118 * <p>In order to save space on the system partition, some applications are shipped in a 3119 * compressed form. In addition the compressed bits for the full application, the 3120 * system image contains a tiny stub comprised of only the Android manifest. 3121 * <p>During the first boot, attempt to uncompress and install the full application. If 3122 * the application can't be installed for any reason, disable the stub and prevent 3123 * uncompressing the full application during future boots. 3124 * <p>In order to forcefully attempt an installation of a full application, go to app 3125 * settings and enable the application. 3126 */ 3127 private void decompressSystemApplications(@NonNull List<String> stubSystemApps, int scanFlags) { 3128 for (int i = stubSystemApps.size() - 1; i >= 0; --i) { 3129 final String pkgName = stubSystemApps.get(i); 3130 // skip if the system package is already disabled 3131 if (mSettings.isDisabledSystemPackageLPr(pkgName)) { 3132 stubSystemApps.remove(i); 3133 continue; 3134 } 3135 // skip if the package isn't installed (?!); this should never happen 3136 final PackageParser.Package pkg = mPackages.get(pkgName); 3137 if (pkg == null) { 3138 stubSystemApps.remove(i); 3139 continue; 3140 } 3141 // skip if the package has been disabled by the user 3142 final PackageSetting ps = mSettings.mPackages.get(pkgName); 3143 if (ps != null) { 3144 final int enabledState = ps.getEnabled(UserHandle.USER_SYSTEM); 3145 if (enabledState == PackageManager.COMPONENT_ENABLED_STATE_DISABLED_USER) { 3146 stubSystemApps.remove(i); 3147 continue; 3148 } 3149 } 3150 3151 if (DEBUG_COMPRESSION) { 3152 Slog.i(TAG, "Uncompressing system stub; pkg: " + pkgName); 3153 } 3154 3155 // uncompress the binary to its eventual destination on /data 3156 final File scanFile = decompressPackage(pkg); 3157 if (scanFile == null) { 3158 continue; 3159 } 3160 3161 // install the package to replace the stub on /system 3162 try { 3163 mSettings.disableSystemPackageLPw(pkgName, true /*replaced*/); 3164 removePackageLI(pkg, true /*chatty*/); 3165 scanPackageTracedLI(scanFile, 0 /*reparseFlags*/, scanFlags, 0, null); 3166 ps.setEnabled(PackageManager.COMPONENT_ENABLED_STATE_DEFAULT, 3167 UserHandle.USER_SYSTEM, "android"); 3168 stubSystemApps.remove(i); 3169 continue; 3170 } catch (PackageManagerException e) { 3171 Slog.e(TAG, "Failed to parse uncompressed system package: " + e.getMessage()); 3172 } 3173 3174 // any failed attempt to install the package will be cleaned up later 3175 } 3176 3177 // disable any stub still left; these failed to install the full application 3178 for (int i = stubSystemApps.size() - 1; i >= 0; --i) { 3179 final String pkgName = stubSystemApps.get(i); 3180 final PackageSetting ps = mSettings.mPackages.get(pkgName); 3181 ps.setEnabled(PackageManager.COMPONENT_ENABLED_STATE_DISABLED, 3182 UserHandle.USER_SYSTEM, "android"); 3183 logCriticalInfo(Log.ERROR, "Stub disabled; pkg: " + pkgName); 3184 } 3185 } 3186 3187 private int decompressFile(File srcFile, File dstFile) throws ErrnoException { 3188 if (DEBUG_COMPRESSION) { 3189 Slog.i(TAG, "Decompress file" 3190 + "; src: " + srcFile.getAbsolutePath() 3191 + ", dst: " + dstFile.getAbsolutePath()); 3192 } 3193 try ( 3194 InputStream fileIn = new GZIPInputStream(new FileInputStream(srcFile)); 3195 OutputStream fileOut = new FileOutputStream(dstFile, false /*append*/); 3196 ) { 3197 Streams.copy(fileIn, fileOut); 3198 Os.chmod(dstFile.getAbsolutePath(), 0644); 3199 return PackageManager.INSTALL_SUCCEEDED; 3200 } catch (IOException e) { 3201 logCriticalInfo(Log.ERROR, "Failed to decompress file" 3202 + "; src: " + srcFile.getAbsolutePath() 3203 + ", dst: " + dstFile.getAbsolutePath()); 3204 } 3205 return PackageManager.INSTALL_FAILED_INTERNAL_ERROR; 3206 } 3207 3208 private File[] getCompressedFiles(String codePath) { 3209 final File stubCodePath = new File(codePath); 3210 final String stubName = stubCodePath.getName(); 3211 3212 // The layout of a compressed package on a given partition is as follows : 3213 // 3214 // Compressed artifacts: 3215 // 3216 // /partition/ModuleName/foo.gz 3217 // /partation/ModuleName/bar.gz 3218 // 3219 // Stub artifact: 3220 // 3221 // /partition/ModuleName-Stub/ModuleName-Stub.apk 3222 // 3223 // In other words, stub is on the same partition as the compressed artifacts 3224 // and in a directory that's suffixed with "-Stub". 3225 int idx = stubName.lastIndexOf(STUB_SUFFIX); 3226 if (idx < 0 || (stubName.length() != (idx + STUB_SUFFIX.length()))) { 3227 return null; 3228 } 3229 3230 final File stubParentDir = stubCodePath.getParentFile(); 3231 if (stubParentDir == null) { 3232 Slog.e(TAG, "Unable to determine stub parent dir for codePath: " + codePath); 3233 return null; 3234 } 3235 3236 final File compressedPath = new File(stubParentDir, stubName.substring(0, idx)); 3237 final File[] files = compressedPath.listFiles(new FilenameFilter() { 3238 @Override 3239 public boolean accept(File dir, String name) { 3240 return name.toLowerCase().endsWith(COMPRESSED_EXTENSION); 3241 } 3242 }); 3243 3244 if (DEBUG_COMPRESSION && files != null && files.length > 0) { 3245 Slog.i(TAG, "getCompressedFiles[" + codePath + "]: " + Arrays.toString(files)); 3246 } 3247 3248 return files; 3249 } 3250 3251 private boolean compressedFileExists(String codePath) { 3252 final File[] compressedFiles = getCompressedFiles(codePath); 3253 return compressedFiles != null && compressedFiles.length > 0; 3254 } 3255 3256 /** 3257 * Decompresses the given package on the system image onto 3258 * the /data partition. 3259 * @return The directory the package was decompressed into. Otherwise, {@code null}. 3260 */ 3261 private File decompressPackage(PackageParser.Package pkg) { 3262 final File[] compressedFiles = getCompressedFiles(pkg.codePath); 3263 if (compressedFiles == null || compressedFiles.length == 0) { 3264 if (DEBUG_COMPRESSION) { 3265 Slog.i(TAG, "No files to decompress: " + pkg.baseCodePath); 3266 } 3267 return null; 3268 } 3269 final File dstCodePath = 3270 getNextCodePath(Environment.getDataAppDirectory(null), pkg.packageName); 3271 int ret = PackageManager.INSTALL_SUCCEEDED; 3272 try { 3273 Os.mkdir(dstCodePath.getAbsolutePath(), 0755); 3274 Os.chmod(dstCodePath.getAbsolutePath(), 0755); 3275 for (File srcFile : compressedFiles) { 3276 final String srcFileName = srcFile.getName(); 3277 final String dstFileName = srcFileName.substring( 3278 0, srcFileName.length() - COMPRESSED_EXTENSION.length()); 3279 final File dstFile = new File(dstCodePath, dstFileName); 3280 ret = decompressFile(srcFile, dstFile); 3281 if (ret != PackageManager.INSTALL_SUCCEEDED) { 3282 logCriticalInfo(Log.ERROR, "Failed to decompress" 3283 + "; pkg: " + pkg.packageName 3284 + ", file: " + dstFileName); 3285 break; 3286 } 3287 } 3288 } catch (ErrnoException e) { 3289 logCriticalInfo(Log.ERROR, "Failed to decompress" 3290 + "; pkg: " + pkg.packageName 3291 + ", err: " + e.errno); 3292 } 3293 if (ret == PackageManager.INSTALL_SUCCEEDED) { 3294 final File libraryRoot = new File(dstCodePath, LIB_DIR_NAME); 3295 NativeLibraryHelper.Handle handle = null; 3296 try { 3297 handle = NativeLibraryHelper.Handle.create(dstCodePath); 3298 ret = NativeLibraryHelper.copyNativeBinariesWithOverride(handle, libraryRoot, 3299 null /*abiOverride*/); 3300 } catch (IOException e) { 3301 logCriticalInfo(Log.ERROR, "Failed to extract native libraries" 3302 + "; pkg: " + pkg.packageName); 3303 ret = PackageManager.INSTALL_FAILED_INTERNAL_ERROR; 3304 } finally { 3305 IoUtils.closeQuietly(handle); 3306 } 3307 } 3308 if (ret != PackageManager.INSTALL_SUCCEEDED) { 3309 if (dstCodePath == null || !dstCodePath.exists()) { 3310 return null; 3311 } 3312 removeCodePathLI(dstCodePath); 3313 return null; 3314 } 3315 3316 return dstCodePath; 3317 } 3318 3319 private void updateInstantAppInstallerLocked(String modifiedPackage) { 3320 // we're only interested in updating the installer appliction when 1) it's not 3321 // already set or 2) the modified package is the installer 3322 if (mInstantAppInstallerActivity != null 3323 && !mInstantAppInstallerActivity.getComponentName().getPackageName() 3324 .equals(modifiedPackage)) { 3325 return; 3326 } 3327 setUpInstantAppInstallerActivityLP(getInstantAppInstallerLPr()); 3328 } 3329 3330 private static File preparePackageParserCache(boolean isUpgrade) { 3331 if (!DEFAULT_PACKAGE_PARSER_CACHE_ENABLED) { 3332 return null; 3333 } 3334 3335 // Disable package parsing on eng builds to allow for faster incremental development. 3336 if (Build.IS_ENG) { 3337 return null; 3338 } 3339 3340 if (SystemProperties.getBoolean("pm.boot.disable_package_cache", false)) { 3341 Slog.i(TAG, "Disabling package parser cache due to system property."); 3342 return null; 3343 } 3344 3345 // The base directory for the package parser cache lives under /data/system/. 3346 final File cacheBaseDir = FileUtils.createDir(Environment.getDataSystemDirectory(), 3347 "package_cache"); 3348 if (cacheBaseDir == null) { 3349 return null; 3350 } 3351 3352 // If this is a system upgrade scenario, delete the contents of the package cache dir. 3353 // This also serves to "GC" unused entries when the package cache version changes (which 3354 // can only happen during upgrades). 3355 if (isUpgrade) { 3356 FileUtils.deleteContents(cacheBaseDir); 3357 } 3358 3359 3360 // Return the versioned package cache directory. This is something like 3361 // "/data/system/package_cache/1" 3362 File cacheDir = FileUtils.createDir(cacheBaseDir, PACKAGE_PARSER_CACHE_VERSION); 3363 3364 // The following is a workaround to aid development on non-numbered userdebug 3365 // builds or cases where "adb sync" is used on userdebug builds. If we detect that 3366 // the system partition is newer. 3367 // 3368 // NOTE: When no BUILD_NUMBER is set by the build system, it defaults to a build 3369 // that starts with "eng." to signify that this is an engineering build and not 3370 // destined for release. 3371 if (Build.IS_USERDEBUG && Build.VERSION.INCREMENTAL.startsWith("eng.")) { 3372 Slog.w(TAG, "Wiping cache directory because the system partition changed."); 3373 3374 // Heuristic: If the /system directory has been modified recently due to an "adb sync" 3375 // or a regular make, then blow away the cache. Note that mtimes are *NOT* reliable 3376 // in general and should not be used for production changes. In this specific case, 3377 // we know that they will work. 3378 File frameworkDir = new File(Environment.getRootDirectory(), "framework"); 3379 if (cacheDir.lastModified() < frameworkDir.lastModified()) { 3380 FileUtils.deleteContents(cacheBaseDir); 3381 cacheDir = FileUtils.createDir(cacheBaseDir, PACKAGE_PARSER_CACHE_VERSION); 3382 } 3383 } 3384 3385 return cacheDir; 3386 } 3387 3388 @Override 3389 public boolean isFirstBoot() { 3390 // allow instant applications 3391 return mFirstBoot; 3392 } 3393 3394 @Override 3395 public boolean isOnlyCoreApps() { 3396 // allow instant applications 3397 return mOnlyCore; 3398 } 3399 3400 @Override 3401 public boolean isUpgrade() { 3402 // allow instant applications 3403 return mIsUpgrade; 3404 } 3405 3406 private @Nullable String getRequiredButNotReallyRequiredVerifierLPr() { 3407 final Intent intent = new Intent(Intent.ACTION_PACKAGE_NEEDS_VERIFICATION); 3408 3409 final List<ResolveInfo> matches = queryIntentReceiversInternal(intent, PACKAGE_MIME_TYPE, 3410 MATCH_SYSTEM_ONLY | MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE, 3411 UserHandle.USER_SYSTEM, false /*allowDynamicSplits*/); 3412 if (matches.size() == 1) { 3413 return matches.get(0).getComponentInfo().packageName; 3414 } else if (matches.size() == 0) { 3415 Log.e(TAG, "There should probably be a verifier, but, none were found"); 3416 return null; 3417 } 3418 throw new RuntimeException("There must be exactly one verifier; found " + matches); 3419 } 3420 3421 private @NonNull String getRequiredSharedLibraryLPr(String name, int version) { 3422 synchronized (mPackages) { 3423 SharedLibraryEntry libraryEntry = getSharedLibraryEntryLPr(name, version); 3424 if (libraryEntry == null) { 3425 throw new IllegalStateException("Missing required shared library:" + name); 3426 } 3427 return libraryEntry.apk; 3428 } 3429 } 3430 3431 private @NonNull String getRequiredInstallerLPr() { 3432 final Intent intent = new Intent(Intent.ACTION_INSTALL_PACKAGE); 3433 intent.addCategory(Intent.CATEGORY_DEFAULT); 3434 intent.setDataAndType(Uri.fromFile(new File("foo.apk")), PACKAGE_MIME_TYPE); 3435 3436 final List<ResolveInfo> matches = queryIntentActivitiesInternal(intent, PACKAGE_MIME_TYPE, 3437 MATCH_SYSTEM_ONLY | MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE, 3438 UserHandle.USER_SYSTEM); 3439 if (matches.size() == 1) { 3440 ResolveInfo resolveInfo = matches.get(0); 3441 if (!resolveInfo.activityInfo.applicationInfo.isPrivilegedApp()) { 3442 throw new RuntimeException("The installer must be a privileged app"); 3443 } 3444 return matches.get(0).getComponentInfo().packageName; 3445 } else { 3446 throw new RuntimeException("There must be exactly one installer; found " + matches); 3447 } 3448 } 3449 3450 private @NonNull String getRequiredUninstallerLPr() { 3451 final Intent intent = new Intent(Intent.ACTION_UNINSTALL_PACKAGE); 3452 intent.addCategory(Intent.CATEGORY_DEFAULT); 3453 intent.setData(Uri.fromParts(PACKAGE_SCHEME, "foo.bar", null)); 3454 3455 final ResolveInfo resolveInfo = resolveIntent(intent, null, 3456 MATCH_SYSTEM_ONLY | MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE, 3457 UserHandle.USER_SYSTEM); 3458 if (resolveInfo == null || 3459 mResolveActivity.name.equals(resolveInfo.getComponentInfo().name)) { 3460 throw new RuntimeException("There must be exactly one uninstaller; found " 3461 + resolveInfo); 3462 } 3463 return resolveInfo.getComponentInfo().packageName; 3464 } 3465 3466 private @NonNull ComponentName getIntentFilterVerifierComponentNameLPr() { 3467 final Intent intent = new Intent(Intent.ACTION_INTENT_FILTER_NEEDS_VERIFICATION); 3468 3469 final List<ResolveInfo> matches = queryIntentReceiversInternal(intent, PACKAGE_MIME_TYPE, 3470 MATCH_SYSTEM_ONLY | MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE, 3471 UserHandle.USER_SYSTEM, false /*allowDynamicSplits*/); 3472 ResolveInfo best = null; 3473 final int N = matches.size(); 3474 for (int i = 0; i < N; i++) { 3475 final ResolveInfo cur = matches.get(i); 3476 final String packageName = cur.getComponentInfo().packageName; 3477 if (checkPermission(android.Manifest.permission.INTENT_FILTER_VERIFICATION_AGENT, 3478 packageName, UserHandle.USER_SYSTEM) != PackageManager.PERMISSION_GRANTED) { 3479 continue; 3480 } 3481 3482 if (best == null || cur.priority > best.priority) { 3483 best = cur; 3484 } 3485 } 3486 3487 if (best != null) { 3488 return best.getComponentInfo().getComponentName(); 3489 } 3490 Slog.w(TAG, "Intent filter verifier not found"); 3491 return null; 3492 } 3493 3494 @Override 3495 public @Nullable ComponentName getInstantAppResolverComponent() { 3496 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 3497 return null; 3498 } 3499 synchronized (mPackages) { 3500 final Pair<ComponentName, String> instantAppResolver = getInstantAppResolverLPr(); 3501 if (instantAppResolver == null) { 3502 return null; 3503 } 3504 return instantAppResolver.first; 3505 } 3506 } 3507 3508 private @Nullable Pair<ComponentName, String> getInstantAppResolverLPr() { 3509 final String[] packageArray = 3510 mContext.getResources().getStringArray(R.array.config_ephemeralResolverPackage); 3511 if (packageArray.length == 0 && !Build.IS_DEBUGGABLE) { 3512 if (DEBUG_EPHEMERAL) { 3513 Slog.d(TAG, "Ephemeral resolver NOT found; empty package list"); 3514 } 3515 return null; 3516 } 3517 3518 final int callingUid = Binder.getCallingUid(); 3519 final int resolveFlags = 3520 MATCH_DIRECT_BOOT_AWARE 3521 | MATCH_DIRECT_BOOT_UNAWARE 3522 | (!Build.IS_DEBUGGABLE ? MATCH_SYSTEM_ONLY : 0); 3523 String actionName = Intent.ACTION_RESOLVE_INSTANT_APP_PACKAGE; 3524 final Intent resolverIntent = new Intent(actionName); 3525 List<ResolveInfo> resolvers = queryIntentServicesInternal(resolverIntent, null, 3526 resolveFlags, UserHandle.USER_SYSTEM, callingUid, false /*includeInstantApps*/); 3527 // temporarily look for the old action 3528 if (resolvers.size() == 0) { 3529 if (DEBUG_EPHEMERAL) { 3530 Slog.d(TAG, "Ephemeral resolver not found with new action; try old one"); 3531 } 3532 actionName = Intent.ACTION_RESOLVE_EPHEMERAL_PACKAGE; 3533 resolverIntent.setAction(actionName); 3534 resolvers = queryIntentServicesInternal(resolverIntent, null, 3535 resolveFlags, UserHandle.USER_SYSTEM, callingUid, false /*includeInstantApps*/); 3536 } 3537 final int N = resolvers.size(); 3538 if (N == 0) { 3539 if (DEBUG_EPHEMERAL) { 3540 Slog.d(TAG, "Ephemeral resolver NOT found; no matching intent filters"); 3541 } 3542 return null; 3543 } 3544 3545 final Set<String> possiblePackages = new ArraySet<>(Arrays.asList(packageArray)); 3546 for (int i = 0; i < N; i++) { 3547 final ResolveInfo info = resolvers.get(i); 3548 3549 if (info.serviceInfo == null) { 3550 continue; 3551 } 3552 3553 final String packageName = info.serviceInfo.packageName; 3554 if (!possiblePackages.contains(packageName) && !Build.IS_DEBUGGABLE) { 3555 if (DEBUG_EPHEMERAL) { 3556 Slog.d(TAG, "Ephemeral resolver not in allowed package list;" 3557 + " pkg: " + packageName + ", info:" + info); 3558 } 3559 continue; 3560 } 3561 3562 if (DEBUG_EPHEMERAL) { 3563 Slog.v(TAG, "Ephemeral resolver found;" 3564 + " pkg: " + packageName + ", info:" + info); 3565 } 3566 return new Pair<>(new ComponentName(packageName, info.serviceInfo.name), actionName); 3567 } 3568 if (DEBUG_EPHEMERAL) { 3569 Slog.v(TAG, "Ephemeral resolver NOT found"); 3570 } 3571 return null; 3572 } 3573 3574 private @Nullable ActivityInfo getInstantAppInstallerLPr() { 3575 final Intent intent = new Intent(Intent.ACTION_INSTALL_INSTANT_APP_PACKAGE); 3576 intent.addCategory(Intent.CATEGORY_DEFAULT); 3577 intent.setDataAndType(Uri.fromFile(new File("foo.apk")), PACKAGE_MIME_TYPE); 3578 3579 final int resolveFlags = 3580 MATCH_DIRECT_BOOT_AWARE 3581 | MATCH_DIRECT_BOOT_UNAWARE 3582 | (!Build.IS_DEBUGGABLE ? MATCH_SYSTEM_ONLY : 0); 3583 List<ResolveInfo> matches = queryIntentActivitiesInternal(intent, PACKAGE_MIME_TYPE, 3584 resolveFlags, UserHandle.USER_SYSTEM); 3585 // temporarily look for the old action 3586 if (matches.isEmpty()) { 3587 if (DEBUG_EPHEMERAL) { 3588 Slog.d(TAG, "Ephemeral installer not found with new action; try old one"); 3589 } 3590 intent.setAction(Intent.ACTION_INSTALL_EPHEMERAL_PACKAGE); 3591 matches = queryIntentActivitiesInternal(intent, PACKAGE_MIME_TYPE, 3592 resolveFlags, UserHandle.USER_SYSTEM); 3593 } 3594 Iterator<ResolveInfo> iter = matches.iterator(); 3595 while (iter.hasNext()) { 3596 final ResolveInfo rInfo = iter.next(); 3597 final PackageSetting ps = mSettings.mPackages.get(rInfo.activityInfo.packageName); 3598 if (ps != null) { 3599 final PermissionsState permissionsState = ps.getPermissionsState(); 3600 if (permissionsState.hasPermission(Manifest.permission.INSTALL_PACKAGES, 0)) { 3601 continue; 3602 } 3603 } 3604 iter.remove(); 3605 } 3606 if (matches.size() == 0) { 3607 return null; 3608 } else if (matches.size() == 1) { 3609 return (ActivityInfo) matches.get(0).getComponentInfo(); 3610 } else { 3611 throw new RuntimeException( 3612 "There must be at most one ephemeral installer; found " + matches); 3613 } 3614 } 3615 3616 private @Nullable ComponentName getInstantAppResolverSettingsLPr( 3617 @NonNull ComponentName resolver) { 3618 final Intent intent = new Intent(Intent.ACTION_INSTANT_APP_RESOLVER_SETTINGS) 3619 .addCategory(Intent.CATEGORY_DEFAULT) 3620 .setPackage(resolver.getPackageName()); 3621 final int resolveFlags = MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE; 3622 List<ResolveInfo> matches = queryIntentActivitiesInternal(intent, null, resolveFlags, 3623 UserHandle.USER_SYSTEM); 3624 // temporarily look for the old action 3625 if (matches.isEmpty()) { 3626 if (DEBUG_EPHEMERAL) { 3627 Slog.d(TAG, "Ephemeral resolver settings not found with new action; try old one"); 3628 } 3629 intent.setAction(Intent.ACTION_EPHEMERAL_RESOLVER_SETTINGS); 3630 matches = queryIntentActivitiesInternal(intent, null, resolveFlags, 3631 UserHandle.USER_SYSTEM); 3632 } 3633 if (matches.isEmpty()) { 3634 return null; 3635 } 3636 return matches.get(0).getComponentInfo().getComponentName(); 3637 } 3638 3639 private void primeDomainVerificationsLPw(int userId) { 3640 if (DEBUG_DOMAIN_VERIFICATION) { 3641 Slog.d(TAG, "Priming domain verifications in user " + userId); 3642 } 3643 3644 SystemConfig systemConfig = SystemConfig.getInstance(); 3645 ArraySet<String> packages = systemConfig.getLinkedApps(); 3646 3647 for (String packageName : packages) { 3648 PackageParser.Package pkg = mPackages.get(packageName); 3649 if (pkg != null) { 3650 if (!pkg.isSystemApp()) { 3651 Slog.w(TAG, "Non-system app '" + packageName + "' in sysconfig <app-link>"); 3652 continue; 3653 } 3654 3655 ArraySet<String> domains = null; 3656 for (PackageParser.Activity a : pkg.activities) { 3657 for (ActivityIntentInfo filter : a.intents) { 3658 if (hasValidDomains(filter)) { 3659 if (domains == null) { 3660 domains = new ArraySet<String>(); 3661 } 3662 domains.addAll(filter.getHostsList()); 3663 } 3664 } 3665 } 3666 3667 if (domains != null && domains.size() > 0) { 3668 if (DEBUG_DOMAIN_VERIFICATION) { 3669 Slog.v(TAG, " + " + packageName); 3670 } 3671 // 'Undefined' in the global IntentFilterVerificationInfo, i.e. the usual 3672 // state w.r.t. the formal app-linkage "no verification attempted" state; 3673 // and then 'always' in the per-user state actually used for intent resolution. 3674 final IntentFilterVerificationInfo ivi; 3675 ivi = mSettings.createIntentFilterVerificationIfNeededLPw(packageName, domains); 3676 ivi.setStatus(INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED); 3677 mSettings.updateIntentFilterVerificationStatusLPw(packageName, 3678 INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS, userId); 3679 } else { 3680 Slog.w(TAG, "Sysconfig <app-link> package '" + packageName 3681 + "' does not handle web links"); 3682 } 3683 } else { 3684 Slog.w(TAG, "Unknown package " + packageName + " in sysconfig <app-link>"); 3685 } 3686 } 3687 3688 scheduleWritePackageRestrictionsLocked(userId); 3689 scheduleWriteSettingsLocked(); 3690 } 3691 3692 private void applyFactoryDefaultBrowserLPw(int userId) { 3693 // The default browser app's package name is stored in a string resource, 3694 // with a product-specific overlay used for vendor customization. 3695 String browserPkg = mContext.getResources().getString( 3696 com.android.internal.R.string.default_browser); 3697 if (!TextUtils.isEmpty(browserPkg)) { 3698 // non-empty string => required to be a known package 3699 PackageSetting ps = mSettings.mPackages.get(browserPkg); 3700 if (ps == null) { 3701 Slog.e(TAG, "Product default browser app does not exist: " + browserPkg); 3702 browserPkg = null; 3703 } else { 3704 mSettings.setDefaultBrowserPackageNameLPw(browserPkg, userId); 3705 } 3706 } 3707 3708 // Nothing valid explicitly set? Make the factory-installed browser the explicit 3709 // default. If there's more than one, just leave everything alone. 3710 if (browserPkg == null) { 3711 calculateDefaultBrowserLPw(userId); 3712 } 3713 } 3714 3715 private void calculateDefaultBrowserLPw(int userId) { 3716 List<String> allBrowsers = resolveAllBrowserApps(userId); 3717 final String browserPkg = (allBrowsers.size() == 1) ? allBrowsers.get(0) : null; 3718 mSettings.setDefaultBrowserPackageNameLPw(browserPkg, userId); 3719 } 3720 3721 private List<String> resolveAllBrowserApps(int userId) { 3722 // Resolve the canonical browser intent and check that the handleAllWebDataURI boolean is set 3723 List<ResolveInfo> list = queryIntentActivitiesInternal(sBrowserIntent, null, 3724 PackageManager.MATCH_ALL, userId); 3725 3726 final int count = list.size(); 3727 List<String> result = new ArrayList<String>(count); 3728 for (int i=0; i<count; i++) { 3729 ResolveInfo info = list.get(i); 3730 if (info.activityInfo == null 3731 || !info.handleAllWebDataURI 3732 || (info.activityInfo.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM) == 0 3733 || result.contains(info.activityInfo.packageName)) { 3734 continue; 3735 } 3736 result.add(info.activityInfo.packageName); 3737 } 3738 3739 return result; 3740 } 3741 3742 private boolean packageIsBrowser(String packageName, int userId) { 3743 List<ResolveInfo> list = queryIntentActivitiesInternal(sBrowserIntent, null, 3744 PackageManager.MATCH_ALL, userId); 3745 final int N = list.size(); 3746 for (int i = 0; i < N; i++) { 3747 ResolveInfo info = list.get(i); 3748 if (packageName.equals(info.activityInfo.packageName)) { 3749 return true; 3750 } 3751 } 3752 return false; 3753 } 3754 3755 private void checkDefaultBrowser() { 3756 final int myUserId = UserHandle.myUserId(); 3757 final String packageName = getDefaultBrowserPackageName(myUserId); 3758 if (packageName != null) { 3759 PackageInfo info = getPackageInfo(packageName, 0, myUserId); 3760 if (info == null) { 3761 Slog.w(TAG, "Default browser no longer installed: " + packageName); 3762 synchronized (mPackages) { 3763 applyFactoryDefaultBrowserLPw(myUserId); // leaves ambiguous when > 1 3764 } 3765 } 3766 } 3767 } 3768 3769 @Override 3770 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 3771 throws RemoteException { 3772 try { 3773 return super.onTransact(code, data, reply, flags); 3774 } catch (RuntimeException e) { 3775 if (!(e instanceof SecurityException) && !(e instanceof IllegalArgumentException)) { 3776 Slog.wtf(TAG, "Package Manager Crash", e); 3777 } 3778 throw e; 3779 } 3780 } 3781 3782 static int[] appendInts(int[] cur, int[] add) { 3783 if (add == null) return cur; 3784 if (cur == null) return add; 3785 final int N = add.length; 3786 for (int i=0; i<N; i++) { 3787 cur = appendInt(cur, add[i]); 3788 } 3789 return cur; 3790 } 3791 3792 /** 3793 * Returns whether or not a full application can see an instant application. 3794 * <p> 3795 * Currently, there are three cases in which this can occur: 3796 * <ol> 3797 * <li>The calling application is a "special" process. The special 3798 * processes are {@link Process#SYSTEM_UID}, {@link Process#SHELL_UID} 3799 * and {@code 0}</li> 3800 * <li>The calling application has the permission 3801 * {@link android.Manifest.permission#ACCESS_INSTANT_APPS}</li> 3802 * <li>The calling application is the default launcher on the 3803 * system partition.</li> 3804 * </ol> 3805 */ 3806 private boolean canViewInstantApps(int callingUid, int userId) { 3807 if (callingUid == Process.SYSTEM_UID 3808 || callingUid == Process.SHELL_UID 3809 || callingUid == Process.ROOT_UID) { 3810 return true; 3811 } 3812 if (mContext.checkCallingOrSelfPermission( 3813 android.Manifest.permission.ACCESS_INSTANT_APPS) == PERMISSION_GRANTED) { 3814 return true; 3815 } 3816 if (mContext.checkCallingOrSelfPermission( 3817 android.Manifest.permission.VIEW_INSTANT_APPS) == PERMISSION_GRANTED) { 3818 final ComponentName homeComponent = getDefaultHomeActivity(userId); 3819 if (homeComponent != null 3820 && isCallerSameApp(homeComponent.getPackageName(), callingUid)) { 3821 return true; 3822 } 3823 } 3824 return false; 3825 } 3826 3827 private PackageInfo generatePackageInfo(PackageSetting ps, int flags, int userId) { 3828 if (!sUserManager.exists(userId)) return null; 3829 if (ps == null) { 3830 return null; 3831 } 3832 PackageParser.Package p = ps.pkg; 3833 if (p == null) { 3834 return null; 3835 } 3836 final int callingUid = Binder.getCallingUid(); 3837 // Filter out ephemeral app metadata: 3838 // * The system/shell/root can see metadata for any app 3839 // * An installed app can see metadata for 1) other installed apps 3840 // and 2) ephemeral apps that have explicitly interacted with it 3841 // * Ephemeral apps can only see their own data and exposed installed apps 3842 // * Holding a signature permission allows seeing instant apps 3843 if (filterAppAccessLPr(ps, callingUid, userId)) { 3844 return null; 3845 } 3846 3847 final PermissionsState permissionsState = ps.getPermissionsState(); 3848 3849 // Compute GIDs only if requested 3850 final int[] gids = (flags & PackageManager.GET_GIDS) == 0 3851 ? EMPTY_INT_ARRAY : permissionsState.computeGids(userId); 3852 // Compute granted permissions only if package has requested permissions 3853 final Set<String> permissions = ArrayUtils.isEmpty(p.requestedPermissions) 3854 ? Collections.<String>emptySet() : permissionsState.getPermissions(userId); 3855 final PackageUserState state = ps.readUserState(userId); 3856 3857 if ((flags & MATCH_UNINSTALLED_PACKAGES) != 0 3858 && ps.isSystem()) { 3859 flags |= MATCH_ANY_USER; 3860 } 3861 3862 PackageInfo packageInfo = PackageParser.generatePackageInfo(p, gids, flags, 3863 ps.firstInstallTime, ps.lastUpdateTime, permissions, state, userId); 3864 3865 if (packageInfo == null) { 3866 return null; 3867 } 3868 3869 packageInfo.packageName = packageInfo.applicationInfo.packageName = 3870 resolveExternalPackageNameLPr(p); 3871 3872 return packageInfo; 3873 } 3874 3875 @Override 3876 public void checkPackageStartable(String packageName, int userId) { 3877 final int callingUid = Binder.getCallingUid(); 3878 if (getInstantAppPackageName(callingUid) != null) { 3879 throw new SecurityException("Instant applications don't have access to this method"); 3880 } 3881 final boolean userKeyUnlocked = StorageManager.isUserKeyUnlocked(userId); 3882 synchronized (mPackages) { 3883 final PackageSetting ps = mSettings.mPackages.get(packageName); 3884 if (ps == null || filterAppAccessLPr(ps, callingUid, userId)) { 3885 throw new SecurityException("Package " + packageName + " was not found!"); 3886 } 3887 3888 if (!ps.getInstalled(userId)) { 3889 throw new SecurityException( 3890 "Package " + packageName + " was not installed for user " + userId + "!"); 3891 } 3892 3893 if (mSafeMode && !ps.isSystem()) { 3894 throw new SecurityException("Package " + packageName + " not a system app!"); 3895 } 3896 3897 if (mFrozenPackages.contains(packageName)) { 3898 throw new SecurityException("Package " + packageName + " is currently frozen!"); 3899 } 3900 3901 if (!userKeyUnlocked && !ps.pkg.applicationInfo.isEncryptionAware()) { 3902 throw new SecurityException("Package " + packageName + " is not encryption aware!"); 3903 } 3904 } 3905 } 3906 3907 @Override 3908 public boolean isPackageAvailable(String packageName, int userId) { 3909 if (!sUserManager.exists(userId)) return false; 3910 final int callingUid = Binder.getCallingUid(); 3911 enforceCrossUserPermission(callingUid, userId, 3912 false /*requireFullPermission*/, false /*checkShell*/, "is package available"); 3913 synchronized (mPackages) { 3914 PackageParser.Package p = mPackages.get(packageName); 3915 if (p != null) { 3916 final PackageSetting ps = (PackageSetting) p.mExtras; 3917 if (filterAppAccessLPr(ps, callingUid, userId)) { 3918 return false; 3919 } 3920 if (ps != null) { 3921 final PackageUserState state = ps.readUserState(userId); 3922 if (state != null) { 3923 return PackageParser.isAvailable(state); 3924 } 3925 } 3926 } 3927 } 3928 return false; 3929 } 3930 3931 @Override 3932 public PackageInfo getPackageInfo(String packageName, int flags, int userId) { 3933 return getPackageInfoInternal(packageName, PackageManager.VERSION_CODE_HIGHEST, 3934 flags, Binder.getCallingUid(), userId); 3935 } 3936 3937 @Override 3938 public PackageInfo getPackageInfoVersioned(VersionedPackage versionedPackage, 3939 int flags, int userId) { 3940 return getPackageInfoInternal(versionedPackage.getPackageName(), 3941 versionedPackage.getVersionCode(), flags, Binder.getCallingUid(), userId); 3942 } 3943 3944 /** 3945 * Important: The provided filterCallingUid is used exclusively to filter out packages 3946 * that can be seen based on user state. It's typically the original caller uid prior 3947 * to clearing. Because it can only be provided by trusted code, it's value can be 3948 * trusted and will be used as-is; unlike userId which will be validated by this method. 3949 */ 3950 private PackageInfo getPackageInfoInternal(String packageName, int versionCode, 3951 int flags, int filterCallingUid, int userId) { 3952 if (!sUserManager.exists(userId)) return null; 3953 flags = updateFlagsForPackage(flags, userId, packageName); 3954 enforceCrossUserPermission(Binder.getCallingUid(), userId, 3955 false /* requireFullPermission */, false /* checkShell */, "get package info"); 3956 3957 // reader 3958 synchronized (mPackages) { 3959 // Normalize package name to handle renamed packages and static libs 3960 packageName = resolveInternalPackageNameLPr(packageName, versionCode); 3961 3962 final boolean matchFactoryOnly = (flags & MATCH_FACTORY_ONLY) != 0; 3963 if (matchFactoryOnly) { 3964 final PackageSetting ps = mSettings.getDisabledSystemPkgLPr(packageName); 3965 if (ps != null) { 3966 if (filterSharedLibPackageLPr(ps, filterCallingUid, userId, flags)) { 3967 return null; 3968 } 3969 if (filterAppAccessLPr(ps, filterCallingUid, userId)) { 3970 return null; 3971 } 3972 return generatePackageInfo(ps, flags, userId); 3973 } 3974 } 3975 3976 PackageParser.Package p = mPackages.get(packageName); 3977 if (matchFactoryOnly && p != null && !isSystemApp(p)) { 3978 return null; 3979 } 3980 if (DEBUG_PACKAGE_INFO) 3981 Log.v(TAG, "getPackageInfo " + packageName + ": " + p); 3982 if (p != null) { 3983 final PackageSetting ps = (PackageSetting) p.mExtras; 3984 if (filterSharedLibPackageLPr(ps, filterCallingUid, userId, flags)) { 3985 return null; 3986 } 3987 if (ps != null && filterAppAccessLPr(ps, filterCallingUid, userId)) { 3988 return null; 3989 } 3990 return generatePackageInfo((PackageSetting)p.mExtras, flags, userId); 3991 } 3992 if (!matchFactoryOnly && (flags & MATCH_KNOWN_PACKAGES) != 0) { 3993 final PackageSetting ps = mSettings.mPackages.get(packageName); 3994 if (ps == null) return null; 3995 if (filterSharedLibPackageLPr(ps, filterCallingUid, userId, flags)) { 3996 return null; 3997 } 3998 if (filterAppAccessLPr(ps, filterCallingUid, userId)) { 3999 return null; 4000 } 4001 return generatePackageInfo(ps, flags, userId); 4002 } 4003 } 4004 return null; 4005 } 4006 4007 private boolean isComponentVisibleToInstantApp(@Nullable ComponentName component) { 4008 if (isComponentVisibleToInstantApp(component, TYPE_ACTIVITY)) { 4009 return true; 4010 } 4011 if (isComponentVisibleToInstantApp(component, TYPE_SERVICE)) { 4012 return true; 4013 } 4014 if (isComponentVisibleToInstantApp(component, TYPE_PROVIDER)) { 4015 return true; 4016 } 4017 return false; 4018 } 4019 4020 private boolean isComponentVisibleToInstantApp( 4021 @Nullable ComponentName component, @ComponentType int type) { 4022 if (type == TYPE_ACTIVITY) { 4023 final PackageParser.Activity activity = mActivities.mActivities.get(component); 4024 return activity != null 4025 ? (activity.info.flags & ActivityInfo.FLAG_VISIBLE_TO_INSTANT_APP) != 0 4026 : false; 4027 } else if (type == TYPE_RECEIVER) { 4028 final PackageParser.Activity activity = mReceivers.mActivities.get(component); 4029 return activity != null 4030 ? (activity.info.flags & ActivityInfo.FLAG_VISIBLE_TO_INSTANT_APP) != 0 4031 : false; 4032 } else if (type == TYPE_SERVICE) { 4033 final PackageParser.Service service = mServices.mServices.get(component); 4034 return service != null 4035 ? (service.info.flags & ServiceInfo.FLAG_VISIBLE_TO_INSTANT_APP) != 0 4036 : false; 4037 } else if (type == TYPE_PROVIDER) { 4038 final PackageParser.Provider provider = mProviders.mProviders.get(component); 4039 return provider != null 4040 ? (provider.info.flags & ProviderInfo.FLAG_VISIBLE_TO_INSTANT_APP) != 0 4041 : false; 4042 } else if (type == TYPE_UNKNOWN) { 4043 return isComponentVisibleToInstantApp(component); 4044 } 4045 return false; 4046 } 4047 4048 /** 4049 * Returns whether or not access to the application should be filtered. 4050 * <p> 4051 * Access may be limited based upon whether the calling or target applications 4052 * are instant applications. 4053 * 4054 * @see #canAccessInstantApps(int) 4055 */ 4056 private boolean filterAppAccessLPr(@Nullable PackageSetting ps, int callingUid, 4057 @Nullable ComponentName component, @ComponentType int componentType, int userId) { 4058 // if we're in an isolated process, get the real calling UID 4059 if (Process.isIsolated(callingUid)) { 4060 callingUid = mIsolatedOwners.get(callingUid); 4061 } 4062 final String instantAppPkgName = getInstantAppPackageName(callingUid); 4063 final boolean callerIsInstantApp = instantAppPkgName != null; 4064 if (ps == null) { 4065 if (callerIsInstantApp) { 4066 // pretend the application exists, but, needs to be filtered 4067 return true; 4068 } 4069 return false; 4070 } 4071 // if the target and caller are the same application, don't filter 4072 if (isCallerSameApp(ps.name, callingUid)) { 4073 return false; 4074 } 4075 if (callerIsInstantApp) { 4076 // request for a specific component; if it hasn't been explicitly exposed, filter 4077 if (component != null) { 4078 return !isComponentVisibleToInstantApp(component, componentType); 4079 } 4080 // request for application; if no components have been explicitly exposed, filter 4081 return ps.getInstantApp(userId) || !ps.pkg.visibleToInstantApps; 4082 } 4083 if (ps.getInstantApp(userId)) { 4084 // caller can see all components of all instant applications, don't filter 4085 if (canViewInstantApps(callingUid, userId)) { 4086 return false; 4087 } 4088 // request for a specific instant application component, filter 4089 if (component != null) { 4090 return true; 4091 } 4092 // request for an instant application; if the caller hasn't been granted access, filter 4093 return !mInstantAppRegistry.isInstantAccessGranted( 4094 userId, UserHandle.getAppId(callingUid), ps.appId); 4095 } 4096 return false; 4097 } 4098 4099 /** 4100 * @see #filterAppAccessLPr(PackageSetting, int, ComponentName, boolean, int) 4101 */ 4102 private boolean filterAppAccessLPr(@Nullable PackageSetting ps, int callingUid, int userId) { 4103 return filterAppAccessLPr(ps, callingUid, null, TYPE_UNKNOWN, userId); 4104 } 4105 4106 private boolean filterSharedLibPackageLPr(@Nullable PackageSetting ps, int uid, int userId, 4107 int flags) { 4108 // Callers can access only the libs they depend on, otherwise they need to explicitly 4109 // ask for the shared libraries given the caller is allowed to access all static libs. 4110 if ((flags & PackageManager.MATCH_STATIC_SHARED_LIBRARIES) != 0) { 4111 // System/shell/root get to see all static libs 4112 final int appId = UserHandle.getAppId(uid); 4113 if (appId == Process.SYSTEM_UID || appId == Process.SHELL_UID 4114 || appId == Process.ROOT_UID) { 4115 return false; 4116 } 4117 } 4118 4119 // No package means no static lib as it is always on internal storage 4120 if (ps == null || ps.pkg == null || !ps.pkg.applicationInfo.isStaticSharedLibrary()) { 4121 return false; 4122 } 4123 4124 final SharedLibraryEntry libEntry = getSharedLibraryEntryLPr(ps.pkg.staticSharedLibName, 4125 ps.pkg.staticSharedLibVersion); 4126 if (libEntry == null) { 4127 return false; 4128 } 4129 4130 final int resolvedUid = UserHandle.getUid(userId, UserHandle.getAppId(uid)); 4131 final String[] uidPackageNames = getPackagesForUid(resolvedUid); 4132 if (uidPackageNames == null) { 4133 return true; 4134 } 4135 4136 for (String uidPackageName : uidPackageNames) { 4137 if (ps.name.equals(uidPackageName)) { 4138 return false; 4139 } 4140 PackageSetting uidPs = mSettings.getPackageLPr(uidPackageName); 4141 if (uidPs != null) { 4142 final int index = ArrayUtils.indexOf(uidPs.usesStaticLibraries, 4143 libEntry.info.getName()); 4144 if (index < 0) { 4145 continue; 4146 } 4147 if (uidPs.pkg.usesStaticLibrariesVersions[index] == libEntry.info.getVersion()) { 4148 return false; 4149 } 4150 } 4151 } 4152 return true; 4153 } 4154 4155 @Override 4156 public String[] currentToCanonicalPackageNames(String[] names) { 4157 final int callingUid = Binder.getCallingUid(); 4158 if (getInstantAppPackageName(callingUid) != null) { 4159 return names; 4160 } 4161 final String[] out = new String[names.length]; 4162 // reader 4163 synchronized (mPackages) { 4164 final int callingUserId = UserHandle.getUserId(callingUid); 4165 final boolean canViewInstantApps = canViewInstantApps(callingUid, callingUserId); 4166 for (int i=names.length-1; i>=0; i--) { 4167 final PackageSetting ps = mSettings.mPackages.get(names[i]); 4168 boolean translateName = false; 4169 if (ps != null && ps.realName != null) { 4170 final boolean targetIsInstantApp = ps.getInstantApp(callingUserId); 4171 translateName = !targetIsInstantApp 4172 || canViewInstantApps 4173 || mInstantAppRegistry.isInstantAccessGranted(callingUserId, 4174 UserHandle.getAppId(callingUid), ps.appId); 4175 } 4176 out[i] = translateName ? ps.realName : names[i]; 4177 } 4178 } 4179 return out; 4180 } 4181 4182 @Override 4183 public String[] canonicalToCurrentPackageNames(String[] names) { 4184 final int callingUid = Binder.getCallingUid(); 4185 if (getInstantAppPackageName(callingUid) != null) { 4186 return names; 4187 } 4188 final String[] out = new String[names.length]; 4189 // reader 4190 synchronized (mPackages) { 4191 final int callingUserId = UserHandle.getUserId(callingUid); 4192 final boolean canViewInstantApps = canViewInstantApps(callingUid, callingUserId); 4193 for (int i=names.length-1; i>=0; i--) { 4194 final String cur = mSettings.getRenamedPackageLPr(names[i]); 4195 boolean translateName = false; 4196 if (cur != null) { 4197 final PackageSetting ps = mSettings.mPackages.get(names[i]); 4198 final boolean targetIsInstantApp = 4199 ps != null && ps.getInstantApp(callingUserId); 4200 translateName = !targetIsInstantApp 4201 || canViewInstantApps 4202 || mInstantAppRegistry.isInstantAccessGranted(callingUserId, 4203 UserHandle.getAppId(callingUid), ps.appId); 4204 } 4205 out[i] = translateName ? cur : names[i]; 4206 } 4207 } 4208 return out; 4209 } 4210 4211 @Override 4212 public int getPackageUid(String packageName, int flags, int userId) { 4213 if (!sUserManager.exists(userId)) return -1; 4214 final int callingUid = Binder.getCallingUid(); 4215 flags = updateFlagsForPackage(flags, userId, packageName); 4216 enforceCrossUserPermission(callingUid, userId, 4217 false /*requireFullPermission*/, false /*checkShell*/, "getPackageUid"); 4218 4219 // reader 4220 synchronized (mPackages) { 4221 final PackageParser.Package p = mPackages.get(packageName); 4222 if (p != null && p.isMatch(flags)) { 4223 PackageSetting ps = (PackageSetting) p.mExtras; 4224 if (filterAppAccessLPr(ps, callingUid, userId)) { 4225 return -1; 4226 } 4227 return UserHandle.getUid(userId, p.applicationInfo.uid); 4228 } 4229 if ((flags & MATCH_KNOWN_PACKAGES) != 0) { 4230 final PackageSetting ps = mSettings.mPackages.get(packageName); 4231 if (ps != null && ps.isMatch(flags) 4232 && !filterAppAccessLPr(ps, callingUid, userId)) { 4233 return UserHandle.getUid(userId, ps.appId); 4234 } 4235 } 4236 } 4237 4238 return -1; 4239 } 4240 4241 @Override 4242 public int[] getPackageGids(String packageName, int flags, int userId) { 4243 if (!sUserManager.exists(userId)) return null; 4244 final int callingUid = Binder.getCallingUid(); 4245 flags = updateFlagsForPackage(flags, userId, packageName); 4246 enforceCrossUserPermission(callingUid, userId, 4247 false /*requireFullPermission*/, false /*checkShell*/, "getPackageGids"); 4248 4249 // reader 4250 synchronized (mPackages) { 4251 final PackageParser.Package p = mPackages.get(packageName); 4252 if (p != null && p.isMatch(flags)) { 4253 PackageSetting ps = (PackageSetting) p.mExtras; 4254 if (filterAppAccessLPr(ps, callingUid, userId)) { 4255 return null; 4256 } 4257 // TODO: Shouldn't this be checking for package installed state for userId and 4258 // return null? 4259 return ps.getPermissionsState().computeGids(userId); 4260 } 4261 if ((flags & MATCH_KNOWN_PACKAGES) != 0) { 4262 final PackageSetting ps = mSettings.mPackages.get(packageName); 4263 if (ps != null && ps.isMatch(flags) 4264 && !filterAppAccessLPr(ps, callingUid, userId)) { 4265 return ps.getPermissionsState().computeGids(userId); 4266 } 4267 } 4268 } 4269 4270 return null; 4271 } 4272 4273 static PermissionInfo generatePermissionInfo(BasePermission bp, int flags) { 4274 if (bp.perm != null) { 4275 return PackageParser.generatePermissionInfo(bp.perm, flags); 4276 } 4277 PermissionInfo pi = new PermissionInfo(); 4278 pi.name = bp.name; 4279 pi.packageName = bp.sourcePackage; 4280 pi.nonLocalizedLabel = bp.name; 4281 pi.protectionLevel = bp.protectionLevel; 4282 return pi; 4283 } 4284 4285 @Override 4286 public PermissionInfo getPermissionInfo(String name, String packageName, int flags) { 4287 final int callingUid = Binder.getCallingUid(); 4288 if (getInstantAppPackageName(callingUid) != null) { 4289 return null; 4290 } 4291 // reader 4292 synchronized (mPackages) { 4293 final BasePermission p = mSettings.mPermissions.get(name); 4294 if (p == null) { 4295 return null; 4296 } 4297 // If the caller is an app that targets pre 26 SDK drop protection flags. 4298 PermissionInfo permissionInfo = generatePermissionInfo(p, flags); 4299 if (permissionInfo != null) { 4300 final int protectionLevel = adjustPermissionProtectionFlagsLPr( 4301 permissionInfo.protectionLevel, packageName, callingUid); 4302 if (permissionInfo.protectionLevel != protectionLevel) { 4303 // If we return different protection level, don't use the cached info 4304 if (p.perm != null && p.perm.info == permissionInfo) { 4305 permissionInfo = new PermissionInfo(permissionInfo); 4306 } 4307 permissionInfo.protectionLevel = protectionLevel; 4308 } 4309 } 4310 return permissionInfo; 4311 } 4312 } 4313 4314 private int adjustPermissionProtectionFlagsLPr(int protectionLevel, 4315 String packageName, int uid) { 4316 // Signature permission flags area always reported 4317 final int protectionLevelMasked = protectionLevel 4318 & (PermissionInfo.PROTECTION_NORMAL 4319 | PermissionInfo.PROTECTION_DANGEROUS 4320 | PermissionInfo.PROTECTION_SIGNATURE); 4321 if (protectionLevelMasked == PermissionInfo.PROTECTION_SIGNATURE) { 4322 return protectionLevel; 4323 } 4324 4325 // System sees all flags. 4326 final int appId = UserHandle.getAppId(uid); 4327 if (appId == Process.SYSTEM_UID || appId == Process.ROOT_UID 4328 || appId == Process.SHELL_UID) { 4329 return protectionLevel; 4330 } 4331 4332 // Normalize package name to handle renamed packages and static libs 4333 packageName = resolveInternalPackageNameLPr(packageName, 4334 PackageManager.VERSION_CODE_HIGHEST); 4335 4336 // Apps that target O see flags for all protection levels. 4337 final PackageSetting ps = mSettings.mPackages.get(packageName); 4338 if (ps == null) { 4339 return protectionLevel; 4340 } 4341 if (ps.appId != appId) { 4342 return protectionLevel; 4343 } 4344 4345 final PackageParser.Package pkg = mPackages.get(packageName); 4346 if (pkg == null) { 4347 return protectionLevel; 4348 } 4349 if (pkg.applicationInfo.targetSdkVersion < Build.VERSION_CODES.O) { 4350 return protectionLevelMasked; 4351 } 4352 4353 return protectionLevel; 4354 } 4355 4356 @Override 4357 public @Nullable ParceledListSlice<PermissionInfo> queryPermissionsByGroup(String group, 4358 int flags) { 4359 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 4360 return null; 4361 } 4362 // reader 4363 synchronized (mPackages) { 4364 if (group != null && !mPermissionGroups.containsKey(group)) { 4365 // This is thrown as NameNotFoundException 4366 return null; 4367 } 4368 4369 ArrayList<PermissionInfo> out = new ArrayList<PermissionInfo>(10); 4370 for (BasePermission p : mSettings.mPermissions.values()) { 4371 if (group == null) { 4372 if (p.perm == null || p.perm.info.group == null) { 4373 out.add(generatePermissionInfo(p, flags)); 4374 } 4375 } else { 4376 if (p.perm != null && group.equals(p.perm.info.group)) { 4377 out.add(PackageParser.generatePermissionInfo(p.perm, flags)); 4378 } 4379 } 4380 } 4381 return new ParceledListSlice<>(out); 4382 } 4383 } 4384 4385 @Override 4386 public PermissionGroupInfo getPermissionGroupInfo(String name, int flags) { 4387 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 4388 return null; 4389 } 4390 // reader 4391 synchronized (mPackages) { 4392 return PackageParser.generatePermissionGroupInfo( 4393 mPermissionGroups.get(name), flags); 4394 } 4395 } 4396 4397 @Override 4398 public @NonNull ParceledListSlice<PermissionGroupInfo> getAllPermissionGroups(int flags) { 4399 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 4400 return ParceledListSlice.emptyList(); 4401 } 4402 // reader 4403 synchronized (mPackages) { 4404 final int N = mPermissionGroups.size(); 4405 ArrayList<PermissionGroupInfo> out 4406 = new ArrayList<PermissionGroupInfo>(N); 4407 for (PackageParser.PermissionGroup pg : mPermissionGroups.values()) { 4408 out.add(PackageParser.generatePermissionGroupInfo(pg, flags)); 4409 } 4410 return new ParceledListSlice<>(out); 4411 } 4412 } 4413 4414 private ApplicationInfo generateApplicationInfoFromSettingsLPw(String packageName, int flags, 4415 int filterCallingUid, int userId) { 4416 if (!sUserManager.exists(userId)) return null; 4417 PackageSetting ps = mSettings.mPackages.get(packageName); 4418 if (ps != null) { 4419 if (filterSharedLibPackageLPr(ps, filterCallingUid, userId, flags)) { 4420 return null; 4421 } 4422 if (filterAppAccessLPr(ps, filterCallingUid, userId)) { 4423 return null; 4424 } 4425 if (ps.pkg == null) { 4426 final PackageInfo pInfo = generatePackageInfo(ps, flags, userId); 4427 if (pInfo != null) { 4428 return pInfo.applicationInfo; 4429 } 4430 return null; 4431 } 4432 ApplicationInfo ai = PackageParser.generateApplicationInfo(ps.pkg, flags, 4433 ps.readUserState(userId), userId); 4434 if (ai != null) { 4435 ai.packageName = resolveExternalPackageNameLPr(ps.pkg); 4436 } 4437 return ai; 4438 } 4439 return null; 4440 } 4441 4442 @Override 4443 public ApplicationInfo getApplicationInfo(String packageName, int flags, int userId) { 4444 return getApplicationInfoInternal(packageName, flags, Binder.getCallingUid(), userId); 4445 } 4446 4447 /** 4448 * Important: The provided filterCallingUid is used exclusively to filter out applications 4449 * that can be seen based on user state. It's typically the original caller uid prior 4450 * to clearing. Because it can only be provided by trusted code, it's value can be 4451 * trusted and will be used as-is; unlike userId which will be validated by this method. 4452 */ 4453 private ApplicationInfo getApplicationInfoInternal(String packageName, int flags, 4454 int filterCallingUid, int userId) { 4455 if (!sUserManager.exists(userId)) return null; 4456 flags = updateFlagsForApplication(flags, userId, packageName); 4457 enforceCrossUserPermission(Binder.getCallingUid(), userId, 4458 false /* requireFullPermission */, false /* checkShell */, "get application info"); 4459 4460 // writer 4461 synchronized (mPackages) { 4462 // Normalize package name to handle renamed packages and static libs 4463 packageName = resolveInternalPackageNameLPr(packageName, 4464 PackageManager.VERSION_CODE_HIGHEST); 4465 4466 PackageParser.Package p = mPackages.get(packageName); 4467 if (DEBUG_PACKAGE_INFO) Log.v( 4468 TAG, "getApplicationInfo " + packageName 4469 + ": " + p); 4470 if (p != null) { 4471 PackageSetting ps = mSettings.mPackages.get(packageName); 4472 if (ps == null) return null; 4473 if (filterSharedLibPackageLPr(ps, filterCallingUid, userId, flags)) { 4474 return null; 4475 } 4476 if (filterAppAccessLPr(ps, filterCallingUid, userId)) { 4477 return null; 4478 } 4479 // Note: isEnabledLP() does not apply here - always return info 4480 ApplicationInfo ai = PackageParser.generateApplicationInfo( 4481 p, flags, ps.readUserState(userId), userId); 4482 if (ai != null) { 4483 ai.packageName = resolveExternalPackageNameLPr(p); 4484 } 4485 return ai; 4486 } 4487 if ("android".equals(packageName)||"system".equals(packageName)) { 4488 return mAndroidApplication; 4489 } 4490 if ((flags & MATCH_KNOWN_PACKAGES) != 0) { 4491 // Already generates the external package name 4492 return generateApplicationInfoFromSettingsLPw(packageName, 4493 flags, filterCallingUid, userId); 4494 } 4495 } 4496 return null; 4497 } 4498 4499 private String normalizePackageNameLPr(String packageName) { 4500 String normalizedPackageName = mSettings.getRenamedPackageLPr(packageName); 4501 return normalizedPackageName != null ? normalizedPackageName : packageName; 4502 } 4503 4504 @Override 4505 public void deletePreloadsFileCache() { 4506 if (!UserHandle.isSameApp(Binder.getCallingUid(), Process.SYSTEM_UID)) { 4507 throw new SecurityException("Only system or settings may call deletePreloadsFileCache"); 4508 } 4509 File dir = Environment.getDataPreloadsFileCacheDirectory(); 4510 Slog.i(TAG, "Deleting preloaded file cache " + dir); 4511 FileUtils.deleteContents(dir); 4512 } 4513 4514 @Override 4515 public void freeStorageAndNotify(final String volumeUuid, final long freeStorageSize, 4516 final int storageFlags, final IPackageDataObserver observer) { 4517 mContext.enforceCallingOrSelfPermission( 4518 android.Manifest.permission.CLEAR_APP_CACHE, null); 4519 mHandler.post(() -> { 4520 boolean success = false; 4521 try { 4522 freeStorage(volumeUuid, freeStorageSize, storageFlags); 4523 success = true; 4524 } catch (IOException e) { 4525 Slog.w(TAG, e); 4526 } 4527 if (observer != null) { 4528 try { 4529 observer.onRemoveCompleted(null, success); 4530 } catch (RemoteException e) { 4531 Slog.w(TAG, e); 4532 } 4533 } 4534 }); 4535 } 4536 4537 @Override 4538 public void freeStorage(final String volumeUuid, final long freeStorageSize, 4539 final int storageFlags, final IntentSender pi) { 4540 mContext.enforceCallingOrSelfPermission( 4541 android.Manifest.permission.CLEAR_APP_CACHE, TAG); 4542 mHandler.post(() -> { 4543 boolean success = false; 4544 try { 4545 freeStorage(volumeUuid, freeStorageSize, storageFlags); 4546 success = true; 4547 } catch (IOException e) { 4548 Slog.w(TAG, e); 4549 } 4550 if (pi != null) { 4551 try { 4552 pi.sendIntent(null, success ? 1 : 0, null, null, null); 4553 } catch (SendIntentException e) { 4554 Slog.w(TAG, e); 4555 } 4556 } 4557 }); 4558 } 4559 4560 /** 4561 * Blocking call to clear various types of cached data across the system 4562 * until the requested bytes are available. 4563 */ 4564 public void freeStorage(String volumeUuid, long bytes, int storageFlags) throws IOException { 4565 final StorageManager storage = mContext.getSystemService(StorageManager.class); 4566 final File file = storage.findPathForUuid(volumeUuid); 4567 if (file.getUsableSpace() >= bytes) return; 4568 4569 if (ENABLE_FREE_CACHE_V2) { 4570 final boolean internalVolume = Objects.equals(StorageManager.UUID_PRIVATE_INTERNAL, 4571 volumeUuid); 4572 final boolean aggressive = (storageFlags 4573 & StorageManager.FLAG_ALLOCATE_AGGRESSIVE) != 0; 4574 final long reservedBytes = storage.getStorageCacheBytes(file, storageFlags); 4575 4576 // 1. Pre-flight to determine if we have any chance to succeed 4577 // 2. Consider preloaded data (after 1w honeymoon, unless aggressive) 4578 if (internalVolume && (aggressive || SystemProperties 4579 .getBoolean("persist.sys.preloads.file_cache_expired", false))) { 4580 deletePreloadsFileCache(); 4581 if (file.getUsableSpace() >= bytes) return; 4582 } 4583 4584 // 3. Consider parsed APK data (aggressive only) 4585 if (internalVolume && aggressive) { 4586 FileUtils.deleteContents(mCacheDir); 4587 if (file.getUsableSpace() >= bytes) return; 4588 } 4589 4590 // 4. Consider cached app data (above quotas) 4591 try { 4592 mInstaller.freeCache(volumeUuid, bytes, reservedBytes, 4593 Installer.FLAG_FREE_CACHE_V2); 4594 } catch (InstallerException ignored) { 4595 } 4596 if (file.getUsableSpace() >= bytes) return; 4597 4598 // 5. Consider shared libraries with refcount=0 and age>min cache period 4599 if (internalVolume && pruneUnusedStaticSharedLibraries(bytes, 4600 android.provider.Settings.Global.getLong(mContext.getContentResolver(), 4601 Global.UNUSED_STATIC_SHARED_LIB_MIN_CACHE_PERIOD, 4602 DEFAULT_UNUSED_STATIC_SHARED_LIB_MIN_CACHE_PERIOD))) { 4603 return; 4604 } 4605 4606 // 6. Consider dexopt output (aggressive only) 4607 // TODO: Implement 4608 4609 // 7. Consider installed instant apps unused longer than min cache period 4610 if (internalVolume && mInstantAppRegistry.pruneInstalledInstantApps(bytes, 4611 android.provider.Settings.Global.getLong(mContext.getContentResolver(), 4612 Global.INSTALLED_INSTANT_APP_MIN_CACHE_PERIOD, 4613 InstantAppRegistry.DEFAULT_INSTALLED_INSTANT_APP_MIN_CACHE_PERIOD))) { 4614 return; 4615 } 4616 4617 // 8. Consider cached app data (below quotas) 4618 try { 4619 mInstaller.freeCache(volumeUuid, bytes, reservedBytes, 4620 Installer.FLAG_FREE_CACHE_V2 | Installer.FLAG_FREE_CACHE_V2_DEFY_QUOTA); 4621 } catch (InstallerException ignored) { 4622 } 4623 if (file.getUsableSpace() >= bytes) return; 4624 4625 // 9. Consider DropBox entries 4626 // TODO: Implement 4627 4628 // 10. Consider instant meta-data (uninstalled apps) older that min cache period 4629 if (internalVolume && mInstantAppRegistry.pruneUninstalledInstantApps(bytes, 4630 android.provider.Settings.Global.getLong(mContext.getContentResolver(), 4631 Global.UNINSTALLED_INSTANT_APP_MIN_CACHE_PERIOD, 4632 InstantAppRegistry.DEFAULT_UNINSTALLED_INSTANT_APP_MIN_CACHE_PERIOD))) { 4633 return; 4634 } 4635 } else { 4636 try { 4637 mInstaller.freeCache(volumeUuid, bytes, 0, 0); 4638 } catch (InstallerException ignored) { 4639 } 4640 if (file.getUsableSpace() >= bytes) return; 4641 } 4642 4643 throw new IOException("Failed to free " + bytes + " on storage device at " + file); 4644 } 4645 4646 private boolean pruneUnusedStaticSharedLibraries(long neededSpace, long maxCachePeriod) 4647 throws IOException { 4648 final StorageManager storage = mContext.getSystemService(StorageManager.class); 4649 final File volume = storage.findPathForUuid(StorageManager.UUID_PRIVATE_INTERNAL); 4650 4651 List<VersionedPackage> packagesToDelete = null; 4652 final long now = System.currentTimeMillis(); 4653 4654 synchronized (mPackages) { 4655 final int[] allUsers = sUserManager.getUserIds(); 4656 final int libCount = mSharedLibraries.size(); 4657 for (int i = 0; i < libCount; i++) { 4658 final SparseArray<SharedLibraryEntry> versionedLib = mSharedLibraries.valueAt(i); 4659 if (versionedLib == null) { 4660 continue; 4661 } 4662 final int versionCount = versionedLib.size(); 4663 for (int j = 0; j < versionCount; j++) { 4664 SharedLibraryInfo libInfo = versionedLib.valueAt(j).info; 4665 // Skip packages that are not static shared libs. 4666 if (!libInfo.isStatic()) { 4667 break; 4668 } 4669 // Important: We skip static shared libs used for some user since 4670 // in such a case we need to keep the APK on the device. The check for 4671 // a lib being used for any user is performed by the uninstall call. 4672 final VersionedPackage declaringPackage = libInfo.getDeclaringPackage(); 4673 // Resolve the package name - we use synthetic package names internally 4674 final String internalPackageName = resolveInternalPackageNameLPr( 4675 declaringPackage.getPackageName(), declaringPackage.getVersionCode()); 4676 final PackageSetting ps = mSettings.getPackageLPr(internalPackageName); 4677 // Skip unused static shared libs cached less than the min period 4678 // to prevent pruning a lib needed by a subsequently installed package. 4679 if (ps == null || now - ps.lastUpdateTime < maxCachePeriod) { 4680 continue; 4681 } 4682 if (packagesToDelete == null) { 4683 packagesToDelete = new ArrayList<>(); 4684 } 4685 packagesToDelete.add(new VersionedPackage(internalPackageName, 4686 declaringPackage.getVersionCode())); 4687 } 4688 } 4689 } 4690 4691 if (packagesToDelete != null) { 4692 final int packageCount = packagesToDelete.size(); 4693 for (int i = 0; i < packageCount; i++) { 4694 final VersionedPackage pkgToDelete = packagesToDelete.get(i); 4695 // Delete the package synchronously (will fail of the lib used for any user). 4696 if (deletePackageX(pkgToDelete.getPackageName(), pkgToDelete.getVersionCode(), 4697 UserHandle.USER_SYSTEM, PackageManager.DELETE_ALL_USERS) 4698 == PackageManager.DELETE_SUCCEEDED) { 4699 if (volume.getUsableSpace() >= neededSpace) { 4700 return true; 4701 } 4702 } 4703 } 4704 } 4705 4706 return false; 4707 } 4708 4709 /** 4710 * Update given flags based on encryption status of current user. 4711 */ 4712 private int updateFlags(int flags, int userId) { 4713 if ((flags & (PackageManager.MATCH_DIRECT_BOOT_UNAWARE 4714 | PackageManager.MATCH_DIRECT_BOOT_AWARE)) != 0) { 4715 // Caller expressed an explicit opinion about what encryption 4716 // aware/unaware components they want to see, so fall through and 4717 // give them what they want 4718 } else { 4719 // Caller expressed no opinion, so match based on user state 4720 if (getUserManagerInternal().isUserUnlockingOrUnlocked(userId)) { 4721 flags |= PackageManager.MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE; 4722 } else { 4723 flags |= PackageManager.MATCH_DIRECT_BOOT_AWARE; 4724 } 4725 } 4726 return flags; 4727 } 4728 4729 private UserManagerInternal getUserManagerInternal() { 4730 if (mUserManagerInternal == null) { 4731 mUserManagerInternal = LocalServices.getService(UserManagerInternal.class); 4732 } 4733 return mUserManagerInternal; 4734 } 4735 4736 private DeviceIdleController.LocalService getDeviceIdleController() { 4737 if (mDeviceIdleController == null) { 4738 mDeviceIdleController = 4739 LocalServices.getService(DeviceIdleController.LocalService.class); 4740 } 4741 return mDeviceIdleController; 4742 } 4743 4744 /** 4745 * Update given flags when being used to request {@link PackageInfo}. 4746 */ 4747 private int updateFlagsForPackage(int flags, int userId, Object cookie) { 4748 final boolean isCallerSystemUser = UserHandle.getCallingUserId() == UserHandle.USER_SYSTEM; 4749 boolean triaged = true; 4750 if ((flags & (PackageManager.GET_ACTIVITIES | PackageManager.GET_RECEIVERS 4751 | PackageManager.GET_SERVICES | PackageManager.GET_PROVIDERS)) != 0) { 4752 // Caller is asking for component details, so they'd better be 4753 // asking for specific encryption matching behavior, or be triaged 4754 if ((flags & (PackageManager.MATCH_DIRECT_BOOT_UNAWARE 4755 | PackageManager.MATCH_DIRECT_BOOT_AWARE 4756 | PackageManager.MATCH_DEBUG_TRIAGED_MISSING)) == 0) { 4757 triaged = false; 4758 } 4759 } 4760 if ((flags & (PackageManager.MATCH_UNINSTALLED_PACKAGES 4761 | PackageManager.MATCH_SYSTEM_ONLY 4762 | PackageManager.MATCH_DEBUG_TRIAGED_MISSING)) == 0) { 4763 triaged = false; 4764 } 4765 if ((flags & PackageManager.MATCH_ANY_USER) != 0) { 4766 enforceCrossUserPermission(Binder.getCallingUid(), userId, false, false, 4767 "MATCH_ANY_USER flag requires INTERACT_ACROSS_USERS permission at " 4768 + Debug.getCallers(5)); 4769 } else if ((flags & PackageManager.MATCH_UNINSTALLED_PACKAGES) != 0 && isCallerSystemUser 4770 && sUserManager.hasManagedProfile(UserHandle.USER_SYSTEM)) { 4771 // If the caller wants all packages and has a restricted profile associated with it, 4772 // then match all users. This is to make sure that launchers that need to access work 4773 // profile apps don't start breaking. TODO: Remove this hack when launchers stop using 4774 // MATCH_UNINSTALLED_PACKAGES to query apps in other profiles. b/31000380 4775 flags |= PackageManager.MATCH_ANY_USER; 4776 } 4777 if (DEBUG_TRIAGED_MISSING && (Binder.getCallingUid() == Process.SYSTEM_UID) && !triaged) { 4778 Log.w(TAG, "Caller hasn't been triaged for missing apps; they asked about " + cookie 4779 + " with flags 0x" + Integer.toHexString(flags), new Throwable()); 4780 } 4781 return updateFlags(flags, userId); 4782 } 4783 4784 /** 4785 * Update given flags when being used to request {@link ApplicationInfo}. 4786 */ 4787 private int updateFlagsForApplication(int flags, int userId, Object cookie) { 4788 return updateFlagsForPackage(flags, userId, cookie); 4789 } 4790 4791 /** 4792 * Update given flags when being used to request {@link ComponentInfo}. 4793 */ 4794 private int updateFlagsForComponent(int flags, int userId, Object cookie) { 4795 if (cookie instanceof Intent) { 4796 if ((((Intent) cookie).getFlags() & Intent.FLAG_DEBUG_TRIAGED_MISSING) != 0) { 4797 flags |= PackageManager.MATCH_DEBUG_TRIAGED_MISSING; 4798 } 4799 } 4800 4801 boolean triaged = true; 4802 // Caller is asking for component details, so they'd better be 4803 // asking for specific encryption matching behavior, or be triaged 4804 if ((flags & (PackageManager.MATCH_DIRECT_BOOT_UNAWARE 4805 | PackageManager.MATCH_DIRECT_BOOT_AWARE 4806 | PackageManager.MATCH_DEBUG_TRIAGED_MISSING)) == 0) { 4807 triaged = false; 4808 } 4809 if (DEBUG_TRIAGED_MISSING && (Binder.getCallingUid() == Process.SYSTEM_UID) && !triaged) { 4810 Log.w(TAG, "Caller hasn't been triaged for missing apps; they asked about " + cookie 4811 + " with flags 0x" + Integer.toHexString(flags), new Throwable()); 4812 } 4813 4814 return updateFlags(flags, userId); 4815 } 4816 4817 /** 4818 * Update given intent when being used to request {@link ResolveInfo}. 4819 */ 4820 private Intent updateIntentForResolve(Intent intent) { 4821 if (intent.getSelector() != null) { 4822 intent = intent.getSelector(); 4823 } 4824 if (DEBUG_PREFERRED) { 4825 intent.addFlags(Intent.FLAG_DEBUG_LOG_RESOLUTION); 4826 } 4827 return intent; 4828 } 4829 4830 /** 4831 * Update given flags when being used to request {@link ResolveInfo}. 4832 * <p>Instant apps are resolved specially, depending upon context. Minimally, 4833 * {@code}flags{@code} must have the {@link PackageManager#MATCH_INSTANT} 4834 * flag set. However, this flag is only honoured in three circumstances: 4835 * <ul> 4836 * <li>when called from a system process</li> 4837 * <li>when the caller holds the permission {@code android.permission.ACCESS_INSTANT_APPS}</li> 4838 * <li>when resolution occurs to start an activity with a {@code android.intent.action.VIEW} 4839 * action and a {@code android.intent.category.BROWSABLE} category</li> 4840 * </ul> 4841 */ 4842 int updateFlagsForResolve(int flags, int userId, Intent intent, int callingUid) { 4843 return updateFlagsForResolve(flags, userId, intent, callingUid, 4844 false /*wantInstantApps*/, false /*onlyExposedExplicitly*/); 4845 } 4846 int updateFlagsForResolve(int flags, int userId, Intent intent, int callingUid, 4847 boolean wantInstantApps) { 4848 return updateFlagsForResolve(flags, userId, intent, callingUid, 4849 wantInstantApps, false /*onlyExposedExplicitly*/); 4850 } 4851 int updateFlagsForResolve(int flags, int userId, Intent intent, int callingUid, 4852 boolean wantInstantApps, boolean onlyExposedExplicitly) { 4853 // Safe mode means we shouldn't match any third-party components 4854 if (mSafeMode) { 4855 flags |= PackageManager.MATCH_SYSTEM_ONLY; 4856 } 4857 if (getInstantAppPackageName(callingUid) != null) { 4858 // But, ephemeral apps see both ephemeral and exposed, non-ephemeral components 4859 if (onlyExposedExplicitly) { 4860 flags |= PackageManager.MATCH_EXPLICITLY_VISIBLE_ONLY; 4861 } 4862 flags |= PackageManager.MATCH_VISIBLE_TO_INSTANT_APP_ONLY; 4863 flags |= PackageManager.MATCH_INSTANT; 4864 } else { 4865 final boolean wantMatchInstant = (flags & PackageManager.MATCH_INSTANT) != 0; 4866 final boolean allowMatchInstant = 4867 (wantInstantApps 4868 && Intent.ACTION_VIEW.equals(intent.getAction()) 4869 && hasWebURI(intent)) 4870 || (wantMatchInstant && canViewInstantApps(callingUid, userId)); 4871 flags &= ~(PackageManager.MATCH_VISIBLE_TO_INSTANT_APP_ONLY 4872 | PackageManager.MATCH_EXPLICITLY_VISIBLE_ONLY); 4873 if (!allowMatchInstant) { 4874 flags &= ~PackageManager.MATCH_INSTANT; 4875 } 4876 } 4877 return updateFlagsForComponent(flags, userId, intent /*cookie*/); 4878 } 4879 4880 @Override 4881 public ActivityInfo getActivityInfo(ComponentName component, int flags, int userId) { 4882 return getActivityInfoInternal(component, flags, Binder.getCallingUid(), userId); 4883 } 4884 4885 /** 4886 * Important: The provided filterCallingUid is used exclusively to filter out activities 4887 * that can be seen based on user state. It's typically the original caller uid prior 4888 * to clearing. Because it can only be provided by trusted code, it's value can be 4889 * trusted and will be used as-is; unlike userId which will be validated by this method. 4890 */ 4891 private ActivityInfo getActivityInfoInternal(ComponentName component, int flags, 4892 int filterCallingUid, int userId) { 4893 if (!sUserManager.exists(userId)) return null; 4894 flags = updateFlagsForComponent(flags, userId, component); 4895 enforceCrossUserPermission(Binder.getCallingUid(), userId, 4896 false /* requireFullPermission */, false /* checkShell */, "get activity info"); 4897 synchronized (mPackages) { 4898 PackageParser.Activity a = mActivities.mActivities.get(component); 4899 4900 if (DEBUG_PACKAGE_INFO) Log.v(TAG, "getActivityInfo " + component + ": " + a); 4901 if (a != null && mSettings.isEnabledAndMatchLPr(a.info, flags, userId)) { 4902 PackageSetting ps = mSettings.mPackages.get(component.getPackageName()); 4903 if (ps == null) return null; 4904 if (filterAppAccessLPr(ps, filterCallingUid, component, TYPE_ACTIVITY, userId)) { 4905 return null; 4906 } 4907 return PackageParser.generateActivityInfo( 4908 a, flags, ps.readUserState(userId), userId); 4909 } 4910 if (mResolveComponentName.equals(component)) { 4911 return PackageParser.generateActivityInfo( 4912 mResolveActivity, flags, new PackageUserState(), userId); 4913 } 4914 } 4915 return null; 4916 } 4917 4918 @Override 4919 public boolean activitySupportsIntent(ComponentName component, Intent intent, 4920 String resolvedType) { 4921 synchronized (mPackages) { 4922 if (component.equals(mResolveComponentName)) { 4923 // The resolver supports EVERYTHING! 4924 return true; 4925 } 4926 final int callingUid = Binder.getCallingUid(); 4927 final int callingUserId = UserHandle.getUserId(callingUid); 4928 PackageParser.Activity a = mActivities.mActivities.get(component); 4929 if (a == null) { 4930 return false; 4931 } 4932 PackageSetting ps = mSettings.mPackages.get(component.getPackageName()); 4933 if (ps == null) { 4934 return false; 4935 } 4936 if (filterAppAccessLPr(ps, callingUid, component, TYPE_ACTIVITY, callingUserId)) { 4937 return false; 4938 } 4939 for (int i=0; i<a.intents.size(); i++) { 4940 if (a.intents.get(i).match(intent.getAction(), resolvedType, intent.getScheme(), 4941 intent.getData(), intent.getCategories(), TAG) >= 0) { 4942 return true; 4943 } 4944 } 4945 return false; 4946 } 4947 } 4948 4949 @Override 4950 public ActivityInfo getReceiverInfo(ComponentName component, int flags, int userId) { 4951 if (!sUserManager.exists(userId)) return null; 4952 final int callingUid = Binder.getCallingUid(); 4953 flags = updateFlagsForComponent(flags, userId, component); 4954 enforceCrossUserPermission(callingUid, userId, 4955 false /* requireFullPermission */, false /* checkShell */, "get receiver info"); 4956 synchronized (mPackages) { 4957 PackageParser.Activity a = mReceivers.mActivities.get(component); 4958 if (DEBUG_PACKAGE_INFO) Log.v( 4959 TAG, "getReceiverInfo " + component + ": " + a); 4960 if (a != null && mSettings.isEnabledAndMatchLPr(a.info, flags, userId)) { 4961 PackageSetting ps = mSettings.mPackages.get(component.getPackageName()); 4962 if (ps == null) return null; 4963 if (filterAppAccessLPr(ps, callingUid, component, TYPE_RECEIVER, userId)) { 4964 return null; 4965 } 4966 return PackageParser.generateActivityInfo( 4967 a, flags, ps.readUserState(userId), userId); 4968 } 4969 } 4970 return null; 4971 } 4972 4973 @Override 4974 public ParceledListSlice<SharedLibraryInfo> getSharedLibraries(String packageName, 4975 int flags, int userId) { 4976 if (!sUserManager.exists(userId)) return null; 4977 Preconditions.checkArgumentNonnegative(userId, "userId must be >= 0"); 4978 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 4979 return null; 4980 } 4981 4982 flags = updateFlagsForPackage(flags, userId, null); 4983 4984 final boolean canSeeStaticLibraries = 4985 mContext.checkCallingOrSelfPermission(INSTALL_PACKAGES) 4986 == PERMISSION_GRANTED 4987 || mContext.checkCallingOrSelfPermission(DELETE_PACKAGES) 4988 == PERMISSION_GRANTED 4989 || canRequestPackageInstallsInternal(packageName, 4990 PackageManager.MATCH_STATIC_SHARED_LIBRARIES, userId, 4991 false /* throwIfPermNotDeclared*/) 4992 || mContext.checkCallingOrSelfPermission(REQUEST_DELETE_PACKAGES) 4993 == PERMISSION_GRANTED; 4994 4995 synchronized (mPackages) { 4996 List<SharedLibraryInfo> result = null; 4997 4998 final int libCount = mSharedLibraries.size(); 4999 for (int i = 0; i < libCount; i++) { 5000 SparseArray<SharedLibraryEntry> versionedLib = mSharedLibraries.valueAt(i); 5001 if (versionedLib == null) { 5002 continue; 5003 } 5004 5005 final int versionCount = versionedLib.size(); 5006 for (int j = 0; j < versionCount; j++) { 5007 SharedLibraryInfo libInfo = versionedLib.valueAt(j).info; 5008 if (!canSeeStaticLibraries && libInfo.isStatic()) { 5009 break; 5010 } 5011 final long identity = Binder.clearCallingIdentity(); 5012 try { 5013 PackageInfo packageInfo = getPackageInfoVersioned( 5014 libInfo.getDeclaringPackage(), flags 5015 | PackageManager.MATCH_STATIC_SHARED_LIBRARIES, userId); 5016 if (packageInfo == null) { 5017 continue; 5018 } 5019 } finally { 5020 Binder.restoreCallingIdentity(identity); 5021 } 5022 5023 SharedLibraryInfo resLibInfo = new SharedLibraryInfo(libInfo.getName(), 5024 libInfo.getVersion(), libInfo.getType(), 5025 libInfo.getDeclaringPackage(), getPackagesUsingSharedLibraryLPr(libInfo, 5026 flags, userId)); 5027 5028 if (result == null) { 5029 result = new ArrayList<>(); 5030 } 5031 result.add(resLibInfo); 5032 } 5033 } 5034 5035 return result != null ? new ParceledListSlice<>(result) : null; 5036 } 5037 } 5038 5039 private List<VersionedPackage> getPackagesUsingSharedLibraryLPr( 5040 SharedLibraryInfo libInfo, int flags, int userId) { 5041 List<VersionedPackage> versionedPackages = null; 5042 final int packageCount = mSettings.mPackages.size(); 5043 for (int i = 0; i < packageCount; i++) { 5044 PackageSetting ps = mSettings.mPackages.valueAt(i); 5045 5046 if (ps == null) { 5047 continue; 5048 } 5049 5050 if (!ps.getUserState().get(userId).isAvailable(flags)) { 5051 continue; 5052 } 5053 5054 final String libName = libInfo.getName(); 5055 if (libInfo.isStatic()) { 5056 final int libIdx = ArrayUtils.indexOf(ps.usesStaticLibraries, libName); 5057 if (libIdx < 0) { 5058 continue; 5059 } 5060 if (ps.usesStaticLibrariesVersions[libIdx] != libInfo.getVersion()) { 5061 continue; 5062 } 5063 if (versionedPackages == null) { 5064 versionedPackages = new ArrayList<>(); 5065 } 5066 // If the dependent is a static shared lib, use the public package name 5067 String dependentPackageName = ps.name; 5068 if (ps.pkg != null && ps.pkg.applicationInfo.isStaticSharedLibrary()) { 5069 dependentPackageName = ps.pkg.manifestPackageName; 5070 } 5071 versionedPackages.add(new VersionedPackage(dependentPackageName, ps.versionCode)); 5072 } else if (ps.pkg != null) { 5073 if (ArrayUtils.contains(ps.pkg.usesLibraries, libName) 5074 || ArrayUtils.contains(ps.pkg.usesOptionalLibraries, libName)) { 5075 if (versionedPackages == null) { 5076 versionedPackages = new ArrayList<>(); 5077 } 5078 versionedPackages.add(new VersionedPackage(ps.name, ps.versionCode)); 5079 } 5080 } 5081 } 5082 5083 return versionedPackages; 5084 } 5085 5086 @Override 5087 public ServiceInfo getServiceInfo(ComponentName component, int flags, int userId) { 5088 if (!sUserManager.exists(userId)) return null; 5089 final int callingUid = Binder.getCallingUid(); 5090 flags = updateFlagsForComponent(flags, userId, component); 5091 enforceCrossUserPermission(callingUid, userId, 5092 false /* requireFullPermission */, false /* checkShell */, "get service info"); 5093 synchronized (mPackages) { 5094 PackageParser.Service s = mServices.mServices.get(component); 5095 if (DEBUG_PACKAGE_INFO) Log.v( 5096 TAG, "getServiceInfo " + component + ": " + s); 5097 if (s != null && mSettings.isEnabledAndMatchLPr(s.info, flags, userId)) { 5098 PackageSetting ps = mSettings.mPackages.get(component.getPackageName()); 5099 if (ps == null) return null; 5100 if (filterAppAccessLPr(ps, callingUid, component, TYPE_SERVICE, userId)) { 5101 return null; 5102 } 5103 return PackageParser.generateServiceInfo( 5104 s, flags, ps.readUserState(userId), userId); 5105 } 5106 } 5107 return null; 5108 } 5109 5110 @Override 5111 public ProviderInfo getProviderInfo(ComponentName component, int flags, int userId) { 5112 if (!sUserManager.exists(userId)) return null; 5113 final int callingUid = Binder.getCallingUid(); 5114 flags = updateFlagsForComponent(flags, userId, component); 5115 enforceCrossUserPermission(callingUid, userId, 5116 false /* requireFullPermission */, false /* checkShell */, "get provider info"); 5117 synchronized (mPackages) { 5118 PackageParser.Provider p = mProviders.mProviders.get(component); 5119 if (DEBUG_PACKAGE_INFO) Log.v( 5120 TAG, "getProviderInfo " + component + ": " + p); 5121 if (p != null && mSettings.isEnabledAndMatchLPr(p.info, flags, userId)) { 5122 PackageSetting ps = mSettings.mPackages.get(component.getPackageName()); 5123 if (ps == null) return null; 5124 if (filterAppAccessLPr(ps, callingUid, component, TYPE_PROVIDER, userId)) { 5125 return null; 5126 } 5127 return PackageParser.generateProviderInfo( 5128 p, flags, ps.readUserState(userId), userId); 5129 } 5130 } 5131 return null; 5132 } 5133 5134 @Override 5135 public String[] getSystemSharedLibraryNames() { 5136 // allow instant applications 5137 synchronized (mPackages) { 5138 Set<String> libs = null; 5139 final int libCount = mSharedLibraries.size(); 5140 for (int i = 0; i < libCount; i++) { 5141 SparseArray<SharedLibraryEntry> versionedLib = mSharedLibraries.valueAt(i); 5142 if (versionedLib == null) { 5143 continue; 5144 } 5145 final int versionCount = versionedLib.size(); 5146 for (int j = 0; j < versionCount; j++) { 5147 SharedLibraryEntry libEntry = versionedLib.valueAt(j); 5148 if (!libEntry.info.isStatic()) { 5149 if (libs == null) { 5150 libs = new ArraySet<>(); 5151 } 5152 libs.add(libEntry.info.getName()); 5153 break; 5154 } 5155 PackageSetting ps = mSettings.getPackageLPr(libEntry.apk); 5156 if (ps != null && !filterSharedLibPackageLPr(ps, Binder.getCallingUid(), 5157 UserHandle.getUserId(Binder.getCallingUid()), 5158 PackageManager.MATCH_STATIC_SHARED_LIBRARIES)) { 5159 if (libs == null) { 5160 libs = new ArraySet<>(); 5161 } 5162 libs.add(libEntry.info.getName()); 5163 break; 5164 } 5165 } 5166 } 5167 5168 if (libs != null) { 5169 String[] libsArray = new String[libs.size()]; 5170 libs.toArray(libsArray); 5171 return libsArray; 5172 } 5173 5174 return null; 5175 } 5176 } 5177 5178 @Override 5179 public @NonNull String getServicesSystemSharedLibraryPackageName() { 5180 // allow instant applications 5181 synchronized (mPackages) { 5182 return mServicesSystemSharedLibraryPackageName; 5183 } 5184 } 5185 5186 @Override 5187 public @NonNull String getSharedSystemSharedLibraryPackageName() { 5188 // allow instant applications 5189 synchronized (mPackages) { 5190 return mSharedSystemSharedLibraryPackageName; 5191 } 5192 } 5193 5194 private void updateSequenceNumberLP(PackageSetting pkgSetting, int[] userList) { 5195 for (int i = userList.length - 1; i >= 0; --i) { 5196 final int userId = userList[i]; 5197 // don't add instant app to the list of updates 5198 if (pkgSetting.getInstantApp(userId)) { 5199 continue; 5200 } 5201 SparseArray<String> changedPackages = mChangedPackages.get(userId); 5202 if (changedPackages == null) { 5203 changedPackages = new SparseArray<>(); 5204 mChangedPackages.put(userId, changedPackages); 5205 } 5206 Map<String, Integer> sequenceNumbers = mChangedPackagesSequenceNumbers.get(userId); 5207 if (sequenceNumbers == null) { 5208 sequenceNumbers = new HashMap<>(); 5209 mChangedPackagesSequenceNumbers.put(userId, sequenceNumbers); 5210 } 5211 final Integer sequenceNumber = sequenceNumbers.get(pkgSetting.name); 5212 if (sequenceNumber != null) { 5213 changedPackages.remove(sequenceNumber); 5214 } 5215 changedPackages.put(mChangedPackagesSequenceNumber, pkgSetting.name); 5216 sequenceNumbers.put(pkgSetting.name, mChangedPackagesSequenceNumber); 5217 } 5218 mChangedPackagesSequenceNumber++; 5219 } 5220 5221 @Override 5222 public ChangedPackages getChangedPackages(int sequenceNumber, int userId) { 5223 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 5224 return null; 5225 } 5226 synchronized (mPackages) { 5227 if (sequenceNumber >= mChangedPackagesSequenceNumber) { 5228 return null; 5229 } 5230 final SparseArray<String> changedPackages = mChangedPackages.get(userId); 5231 if (changedPackages == null) { 5232 return null; 5233 } 5234 final List<String> packageNames = 5235 new ArrayList<>(mChangedPackagesSequenceNumber - sequenceNumber); 5236 for (int i = sequenceNumber; i < mChangedPackagesSequenceNumber; i++) { 5237 final String packageName = changedPackages.get(i); 5238 if (packageName != null) { 5239 packageNames.add(packageName); 5240 } 5241 } 5242 return packageNames.isEmpty() 5243 ? null : new ChangedPackages(mChangedPackagesSequenceNumber, packageNames); 5244 } 5245 } 5246 5247 @Override 5248 public @NonNull ParceledListSlice<FeatureInfo> getSystemAvailableFeatures() { 5249 // allow instant applications 5250 ArrayList<FeatureInfo> res; 5251 synchronized (mAvailableFeatures) { 5252 res = new ArrayList<>(mAvailableFeatures.size() + 1); 5253 res.addAll(mAvailableFeatures.values()); 5254 } 5255 final FeatureInfo fi = new FeatureInfo(); 5256 fi.reqGlEsVersion = SystemProperties.getInt("ro.opengles.version", 5257 FeatureInfo.GL_ES_VERSION_UNDEFINED); 5258 res.add(fi); 5259 5260 return new ParceledListSlice<>(res); 5261 } 5262 5263 @Override 5264 public boolean hasSystemFeature(String name, int version) { 5265 // allow instant applications 5266 synchronized (mAvailableFeatures) { 5267 final FeatureInfo feat = mAvailableFeatures.get(name); 5268 if (feat == null) { 5269 return false; 5270 } else { 5271 return feat.version >= version; 5272 } 5273 } 5274 } 5275 5276 @Override 5277 public int checkPermission(String permName, String pkgName, int userId) { 5278 if (!sUserManager.exists(userId)) { 5279 return PackageManager.PERMISSION_DENIED; 5280 } 5281 final int callingUid = Binder.getCallingUid(); 5282 5283 synchronized (mPackages) { 5284 final PackageParser.Package p = mPackages.get(pkgName); 5285 if (p != null && p.mExtras != null) { 5286 final PackageSetting ps = (PackageSetting) p.mExtras; 5287 if (filterAppAccessLPr(ps, callingUid, userId)) { 5288 return PackageManager.PERMISSION_DENIED; 5289 } 5290 final boolean instantApp = ps.getInstantApp(userId); 5291 final PermissionsState permissionsState = ps.getPermissionsState(); 5292 if (permissionsState.hasPermission(permName, userId)) { 5293 if (instantApp) { 5294 BasePermission bp = mSettings.mPermissions.get(permName); 5295 if (bp != null && bp.isInstant()) { 5296 return PackageManager.PERMISSION_GRANTED; 5297 } 5298 } else { 5299 return PackageManager.PERMISSION_GRANTED; 5300 } 5301 } 5302 // Special case: ACCESS_FINE_LOCATION permission includes ACCESS_COARSE_LOCATION 5303 if (Manifest.permission.ACCESS_COARSE_LOCATION.equals(permName) && permissionsState 5304 .hasPermission(Manifest.permission.ACCESS_FINE_LOCATION, userId)) { 5305 return PackageManager.PERMISSION_GRANTED; 5306 } 5307 } 5308 } 5309 5310 return PackageManager.PERMISSION_DENIED; 5311 } 5312 5313 @Override 5314 public int checkUidPermission(String permName, int uid) { 5315 final int callingUid = Binder.getCallingUid(); 5316 final int callingUserId = UserHandle.getUserId(callingUid); 5317 final boolean isCallerInstantApp = getInstantAppPackageName(callingUid) != null; 5318 final boolean isUidInstantApp = getInstantAppPackageName(uid) != null; 5319 final int userId = UserHandle.getUserId(uid); 5320 if (!sUserManager.exists(userId)) { 5321 return PackageManager.PERMISSION_DENIED; 5322 } 5323 5324 synchronized (mPackages) { 5325 Object obj = mSettings.getUserIdLPr(UserHandle.getAppId(uid)); 5326 if (obj != null) { 5327 if (obj instanceof SharedUserSetting) { 5328 if (isCallerInstantApp) { 5329 return PackageManager.PERMISSION_DENIED; 5330 } 5331 } else if (obj instanceof PackageSetting) { 5332 final PackageSetting ps = (PackageSetting) obj; 5333 if (filterAppAccessLPr(ps, callingUid, callingUserId)) { 5334 return PackageManager.PERMISSION_DENIED; 5335 } 5336 } 5337 final SettingBase settingBase = (SettingBase) obj; 5338 final PermissionsState permissionsState = settingBase.getPermissionsState(); 5339 if (permissionsState.hasPermission(permName, userId)) { 5340 if (isUidInstantApp) { 5341 BasePermission bp = mSettings.mPermissions.get(permName); 5342 if (bp != null && bp.isInstant()) { 5343 return PackageManager.PERMISSION_GRANTED; 5344 } 5345 } else { 5346 return PackageManager.PERMISSION_GRANTED; 5347 } 5348 } 5349 // Special case: ACCESS_FINE_LOCATION permission includes ACCESS_COARSE_LOCATION 5350 if (Manifest.permission.ACCESS_COARSE_LOCATION.equals(permName) && permissionsState 5351 .hasPermission(Manifest.permission.ACCESS_FINE_LOCATION, userId)) { 5352 return PackageManager.PERMISSION_GRANTED; 5353 } 5354 } else { 5355 ArraySet<String> perms = mSystemPermissions.get(uid); 5356 if (perms != null) { 5357 if (perms.contains(permName)) { 5358 return PackageManager.PERMISSION_GRANTED; 5359 } 5360 if (Manifest.permission.ACCESS_COARSE_LOCATION.equals(permName) && perms 5361 .contains(Manifest.permission.ACCESS_FINE_LOCATION)) { 5362 return PackageManager.PERMISSION_GRANTED; 5363 } 5364 } 5365 } 5366 } 5367 5368 return PackageManager.PERMISSION_DENIED; 5369 } 5370 5371 @Override 5372 public boolean isPermissionRevokedByPolicy(String permission, String packageName, int userId) { 5373 if (UserHandle.getCallingUserId() != userId) { 5374 mContext.enforceCallingPermission( 5375 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, 5376 "isPermissionRevokedByPolicy for user " + userId); 5377 } 5378 5379 if (checkPermission(permission, packageName, userId) 5380 == PackageManager.PERMISSION_GRANTED) { 5381 return false; 5382 } 5383 5384 final int callingUid = Binder.getCallingUid(); 5385 if (getInstantAppPackageName(callingUid) != null) { 5386 if (!isCallerSameApp(packageName, callingUid)) { 5387 return false; 5388 } 5389 } else { 5390 if (isInstantApp(packageName, userId)) { 5391 return false; 5392 } 5393 } 5394 5395 final long identity = Binder.clearCallingIdentity(); 5396 try { 5397 final int flags = getPermissionFlags(permission, packageName, userId); 5398 return (flags & PackageManager.FLAG_PERMISSION_POLICY_FIXED) != 0; 5399 } finally { 5400 Binder.restoreCallingIdentity(identity); 5401 } 5402 } 5403 5404 @Override 5405 public String getPermissionControllerPackageName() { 5406 synchronized (mPackages) { 5407 return mRequiredInstallerPackage; 5408 } 5409 } 5410 5411 /** 5412 * Checks if the request is from the system or an app that has INTERACT_ACROSS_USERS 5413 * or INTERACT_ACROSS_USERS_FULL permissions, if the userid is not for the caller. 5414 * @param checkShell whether to prevent shell from access if there's a debugging restriction 5415 * @param message the message to log on security exception 5416 */ 5417 void enforceCrossUserPermission(int callingUid, int userId, boolean requireFullPermission, 5418 boolean checkShell, String message) { 5419 if (userId < 0) { 5420 throw new IllegalArgumentException("Invalid userId " + userId); 5421 } 5422 if (checkShell) { 5423 enforceShellRestriction(UserManager.DISALLOW_DEBUGGING_FEATURES, callingUid, userId); 5424 } 5425 if (userId == UserHandle.getUserId(callingUid)) return; 5426 if (callingUid != Process.SYSTEM_UID && callingUid != 0) { 5427 if (requireFullPermission) { 5428 mContext.enforceCallingOrSelfPermission( 5429 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, message); 5430 } else { 5431 try { 5432 mContext.enforceCallingOrSelfPermission( 5433 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, message); 5434 } catch (SecurityException se) { 5435 mContext.enforceCallingOrSelfPermission( 5436 android.Manifest.permission.INTERACT_ACROSS_USERS, message); 5437 } 5438 } 5439 } 5440 } 5441 5442 void enforceShellRestriction(String restriction, int callingUid, int userHandle) { 5443 if (callingUid == Process.SHELL_UID) { 5444 if (userHandle >= 0 5445 && sUserManager.hasUserRestriction(restriction, userHandle)) { 5446 throw new SecurityException("Shell does not have permission to access user " 5447 + userHandle); 5448 } else if (userHandle < 0) { 5449 Slog.e(TAG, "Unable to check shell permission for user " + userHandle + "\n\t" 5450 + Debug.getCallers(3)); 5451 } 5452 } 5453 } 5454 5455 private BasePermission findPermissionTreeLP(String permName) { 5456 for(BasePermission bp : mSettings.mPermissionTrees.values()) { 5457 if (permName.startsWith(bp.name) && 5458 permName.length() > bp.name.length() && 5459 permName.charAt(bp.name.length()) == '.') { 5460 return bp; 5461 } 5462 } 5463 return null; 5464 } 5465 5466 private BasePermission checkPermissionTreeLP(String permName) { 5467 if (permName != null) { 5468 BasePermission bp = findPermissionTreeLP(permName); 5469 if (bp != null) { 5470 if (bp.uid == UserHandle.getAppId(Binder.getCallingUid())) { 5471 return bp; 5472 } 5473 throw new SecurityException("Calling uid " 5474 + Binder.getCallingUid() 5475 + " is not allowed to add to permission tree " 5476 + bp.name + " owned by uid " + bp.uid); 5477 } 5478 } 5479 throw new SecurityException("No permission tree found for " + permName); 5480 } 5481 5482 static boolean compareStrings(CharSequence s1, CharSequence s2) { 5483 if (s1 == null) { 5484 return s2 == null; 5485 } 5486 if (s2 == null) { 5487 return false; 5488 } 5489 if (s1.getClass() != s2.getClass()) { 5490 return false; 5491 } 5492 return s1.equals(s2); 5493 } 5494 5495 static boolean comparePermissionInfos(PermissionInfo pi1, PermissionInfo pi2) { 5496 if (pi1.icon != pi2.icon) return false; 5497 if (pi1.logo != pi2.logo) return false; 5498 if (pi1.protectionLevel != pi2.protectionLevel) return false; 5499 if (!compareStrings(pi1.name, pi2.name)) return false; 5500 if (!compareStrings(pi1.nonLocalizedLabel, pi2.nonLocalizedLabel)) return false; 5501 // We'll take care of setting this one. 5502 if (!compareStrings(pi1.packageName, pi2.packageName)) return false; 5503 // These are not currently stored in settings. 5504 //if (!compareStrings(pi1.group, pi2.group)) return false; 5505 //if (!compareStrings(pi1.nonLocalizedDescription, pi2.nonLocalizedDescription)) return false; 5506 //if (pi1.labelRes != pi2.labelRes) return false; 5507 //if (pi1.descriptionRes != pi2.descriptionRes) return false; 5508 return true; 5509 } 5510 5511 int permissionInfoFootprint(PermissionInfo info) { 5512 int size = info.name.length(); 5513 if (info.nonLocalizedLabel != null) size += info.nonLocalizedLabel.length(); 5514 if (info.nonLocalizedDescription != null) size += info.nonLocalizedDescription.length(); 5515 return size; 5516 } 5517 5518 int calculateCurrentPermissionFootprintLocked(BasePermission tree) { 5519 int size = 0; 5520 for (BasePermission perm : mSettings.mPermissions.values()) { 5521 if (perm.uid == tree.uid) { 5522 size += perm.name.length() + permissionInfoFootprint(perm.perm.info); 5523 } 5524 } 5525 return size; 5526 } 5527 5528 void enforcePermissionCapLocked(PermissionInfo info, BasePermission tree) { 5529 // We calculate the max size of permissions defined by this uid and throw 5530 // if that plus the size of 'info' would exceed our stated maximum. 5531 if (tree.uid != Process.SYSTEM_UID) { 5532 final int curTreeSize = calculateCurrentPermissionFootprintLocked(tree); 5533 if (curTreeSize + permissionInfoFootprint(info) > MAX_PERMISSION_TREE_FOOTPRINT) { 5534 throw new SecurityException("Permission tree size cap exceeded"); 5535 } 5536 } 5537 } 5538 5539 boolean addPermissionLocked(PermissionInfo info, boolean async) { 5540 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 5541 throw new SecurityException("Instant apps can't add permissions"); 5542 } 5543 if (info.labelRes == 0 && info.nonLocalizedLabel == null) { 5544 throw new SecurityException("Label must be specified in permission"); 5545 } 5546 BasePermission tree = checkPermissionTreeLP(info.name); 5547 BasePermission bp = mSettings.mPermissions.get(info.name); 5548 boolean added = bp == null; 5549 boolean changed = true; 5550 int fixedLevel = PermissionInfo.fixProtectionLevel(info.protectionLevel); 5551 if (added) { 5552 enforcePermissionCapLocked(info, tree); 5553 bp = new BasePermission(info.name, tree.sourcePackage, 5554 BasePermission.TYPE_DYNAMIC); 5555 } else if (bp.type != BasePermission.TYPE_DYNAMIC) { 5556 throw new SecurityException( 5557 "Not allowed to modify non-dynamic permission " 5558 + info.name); 5559 } else { 5560 if (bp.protectionLevel == fixedLevel 5561 && bp.perm.owner.equals(tree.perm.owner) 5562 && bp.uid == tree.uid 5563 && comparePermissionInfos(bp.perm.info, info)) { 5564 changed = false; 5565 } 5566 } 5567 bp.protectionLevel = fixedLevel; 5568 info = new PermissionInfo(info); 5569 info.protectionLevel = fixedLevel; 5570 bp.perm = new PackageParser.Permission(tree.perm.owner, info); 5571 bp.perm.info.packageName = tree.perm.info.packageName; 5572 bp.uid = tree.uid; 5573 if (added) { 5574 mSettings.mPermissions.put(info.name, bp); 5575 } 5576 if (changed) { 5577 if (!async) { 5578 mSettings.writeLPr(); 5579 } else { 5580 scheduleWriteSettingsLocked(); 5581 } 5582 } 5583 return added; 5584 } 5585 5586 @Override 5587 public boolean addPermission(PermissionInfo info) { 5588 synchronized (mPackages) { 5589 return addPermissionLocked(info, false); 5590 } 5591 } 5592 5593 @Override 5594 public boolean addPermissionAsync(PermissionInfo info) { 5595 synchronized (mPackages) { 5596 return addPermissionLocked(info, true); 5597 } 5598 } 5599 5600 @Override 5601 public void removePermission(String name) { 5602 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 5603 throw new SecurityException("Instant applications don't have access to this method"); 5604 } 5605 synchronized (mPackages) { 5606 checkPermissionTreeLP(name); 5607 BasePermission bp = mSettings.mPermissions.get(name); 5608 if (bp != null) { 5609 if (bp.type != BasePermission.TYPE_DYNAMIC) { 5610 throw new SecurityException( 5611 "Not allowed to modify non-dynamic permission " 5612 + name); 5613 } 5614 mSettings.mPermissions.remove(name); 5615 mSettings.writeLPr(); 5616 } 5617 } 5618 } 5619 5620 private static void enforceDeclaredAsUsedAndRuntimeOrDevelopmentPermission( 5621 PackageParser.Package pkg, BasePermission bp) { 5622 int index = pkg.requestedPermissions.indexOf(bp.name); 5623 if (index == -1) { 5624 throw new SecurityException("Package " + pkg.packageName 5625 + " has not requested permission " + bp.name); 5626 } 5627 if (!bp.isRuntime() && !bp.isDevelopment()) { 5628 throw new SecurityException("Permission " + bp.name 5629 + " is not a changeable permission type"); 5630 } 5631 } 5632 5633 @Override 5634 public void grantRuntimePermission(String packageName, String name, final int userId) { 5635 grantRuntimePermission(packageName, name, userId, false /* Only if not fixed by policy */); 5636 } 5637 5638 private void grantRuntimePermission(String packageName, String name, final int userId, 5639 boolean overridePolicy) { 5640 if (!sUserManager.exists(userId)) { 5641 Log.e(TAG, "No such user:" + userId); 5642 return; 5643 } 5644 final int callingUid = Binder.getCallingUid(); 5645 5646 mContext.enforceCallingOrSelfPermission( 5647 android.Manifest.permission.GRANT_RUNTIME_PERMISSIONS, 5648 "grantRuntimePermission"); 5649 5650 enforceCrossUserPermission(callingUid, userId, 5651 true /* requireFullPermission */, true /* checkShell */, 5652 "grantRuntimePermission"); 5653 5654 final int uid; 5655 final PackageSetting ps; 5656 5657 synchronized (mPackages) { 5658 final PackageParser.Package pkg = mPackages.get(packageName); 5659 if (pkg == null) { 5660 throw new IllegalArgumentException("Unknown package: " + packageName); 5661 } 5662 final BasePermission bp = mSettings.mPermissions.get(name); 5663 if (bp == null) { 5664 throw new IllegalArgumentException("Unknown permission: " + name); 5665 } 5666 ps = (PackageSetting) pkg.mExtras; 5667 if (ps == null 5668 || filterAppAccessLPr(ps, callingUid, userId)) { 5669 throw new IllegalArgumentException("Unknown package: " + packageName); 5670 } 5671 5672 enforceDeclaredAsUsedAndRuntimeOrDevelopmentPermission(pkg, bp); 5673 5674 // If a permission review is required for legacy apps we represent 5675 // their permissions as always granted runtime ones since we need 5676 // to keep the review required permission flag per user while an 5677 // install permission's state is shared across all users. 5678 if (mPermissionReviewRequired 5679 && pkg.applicationInfo.targetSdkVersion < Build.VERSION_CODES.M 5680 && bp.isRuntime()) { 5681 return; 5682 } 5683 5684 uid = UserHandle.getUid(userId, pkg.applicationInfo.uid); 5685 5686 final PermissionsState permissionsState = ps.getPermissionsState(); 5687 5688 final int flags = permissionsState.getPermissionFlags(name, userId); 5689 if ((flags & PackageManager.FLAG_PERMISSION_SYSTEM_FIXED) != 0) { 5690 throw new SecurityException("Cannot grant system fixed permission " 5691 + name + " for package " + packageName); 5692 } 5693 if (!overridePolicy && (flags & PackageManager.FLAG_PERMISSION_POLICY_FIXED) != 0) { 5694 throw new SecurityException("Cannot grant policy fixed permission " 5695 + name + " for package " + packageName); 5696 } 5697 5698 if (bp.isDevelopment()) { 5699 // Development permissions must be handled specially, since they are not 5700 // normal runtime permissions. For now they apply to all users. 5701 if (permissionsState.grantInstallPermission(bp) != 5702 PermissionsState.PERMISSION_OPERATION_FAILURE) { 5703 scheduleWriteSettingsLocked(); 5704 } 5705 return; 5706 } 5707 5708 if (ps.getInstantApp(userId) && !bp.isInstant()) { 5709 throw new SecurityException("Cannot grant non-ephemeral permission" 5710 + name + " for package " + packageName); 5711 } 5712 5713 if (pkg.applicationInfo.targetSdkVersion < Build.VERSION_CODES.M) { 5714 Slog.w(TAG, "Cannot grant runtime permission to a legacy app"); 5715 return; 5716 } 5717 5718 final int result = permissionsState.grantRuntimePermission(bp, userId); 5719 switch (result) { 5720 case PermissionsState.PERMISSION_OPERATION_FAILURE: { 5721 return; 5722 } 5723 5724 case PermissionsState.PERMISSION_OPERATION_SUCCESS_GIDS_CHANGED: { 5725 final int appId = UserHandle.getAppId(pkg.applicationInfo.uid); 5726 mHandler.post(new Runnable() { 5727 @Override 5728 public void run() { 5729 killUid(appId, userId, KILL_APP_REASON_GIDS_CHANGED); 5730 } 5731 }); 5732 } 5733 break; 5734 } 5735 5736 if (bp.isRuntime()) { 5737 logPermissionGranted(mContext, name, packageName); 5738 } 5739 5740 mOnPermissionChangeListeners.onPermissionsChanged(uid); 5741 5742 // Not critical if that is lost - app has to request again. 5743 mSettings.writeRuntimePermissionsForUserLPr(userId, false); 5744 } 5745 5746 // Only need to do this if user is initialized. Otherwise it's a new user 5747 // and there are no processes running as the user yet and there's no need 5748 // to make an expensive call to remount processes for the changed permissions. 5749 if (READ_EXTERNAL_STORAGE.equals(name) 5750 || WRITE_EXTERNAL_STORAGE.equals(name)) { 5751 final long token = Binder.clearCallingIdentity(); 5752 try { 5753 if (sUserManager.isInitialized(userId)) { 5754 StorageManagerInternal storageManagerInternal = LocalServices.getService( 5755 StorageManagerInternal.class); 5756 storageManagerInternal.onExternalStoragePolicyChanged(uid, packageName); 5757 } 5758 } finally { 5759 Binder.restoreCallingIdentity(token); 5760 } 5761 } 5762 } 5763 5764 @Override 5765 public void revokeRuntimePermission(String packageName, String name, int userId) { 5766 revokeRuntimePermission(packageName, name, userId, false /* Only if not fixed by policy */); 5767 } 5768 5769 private void revokeRuntimePermission(String packageName, String name, int userId, 5770 boolean overridePolicy) { 5771 if (!sUserManager.exists(userId)) { 5772 Log.e(TAG, "No such user:" + userId); 5773 return; 5774 } 5775 5776 mContext.enforceCallingOrSelfPermission( 5777 android.Manifest.permission.REVOKE_RUNTIME_PERMISSIONS, 5778 "revokeRuntimePermission"); 5779 5780 enforceCrossUserPermission(Binder.getCallingUid(), userId, 5781 true /* requireFullPermission */, true /* checkShell */, 5782 "revokeRuntimePermission"); 5783 5784 final int appId; 5785 5786 synchronized (mPackages) { 5787 final PackageParser.Package pkg = mPackages.get(packageName); 5788 if (pkg == null) { 5789 throw new IllegalArgumentException("Unknown package: " + packageName); 5790 } 5791 final PackageSetting ps = (PackageSetting) pkg.mExtras; 5792 if (ps == null 5793 || filterAppAccessLPr(ps, Binder.getCallingUid(), userId)) { 5794 throw new IllegalArgumentException("Unknown package: " + packageName); 5795 } 5796 final BasePermission bp = mSettings.mPermissions.get(name); 5797 if (bp == null) { 5798 throw new IllegalArgumentException("Unknown permission: " + name); 5799 } 5800 5801 enforceDeclaredAsUsedAndRuntimeOrDevelopmentPermission(pkg, bp); 5802 5803 // If a permission review is required for legacy apps we represent 5804 // their permissions as always granted runtime ones since we need 5805 // to keep the review required permission flag per user while an 5806 // install permission's state is shared across all users. 5807 if (mPermissionReviewRequired 5808 && pkg.applicationInfo.targetSdkVersion < Build.VERSION_CODES.M 5809 && bp.isRuntime()) { 5810 return; 5811 } 5812 5813 final PermissionsState permissionsState = ps.getPermissionsState(); 5814 5815 final int flags = permissionsState.getPermissionFlags(name, userId); 5816 if ((flags & PackageManager.FLAG_PERMISSION_SYSTEM_FIXED) != 0) { 5817 throw new SecurityException("Cannot revoke system fixed permission " 5818 + name + " for package " + packageName); 5819 } 5820 if (!overridePolicy && (flags & PackageManager.FLAG_PERMISSION_POLICY_FIXED) != 0) { 5821 throw new SecurityException("Cannot revoke policy fixed permission " 5822 + name + " for package " + packageName); 5823 } 5824 5825 if (bp.isDevelopment()) { 5826 // Development permissions must be handled specially, since they are not 5827 // normal runtime permissions. For now they apply to all users. 5828 if (permissionsState.revokeInstallPermission(bp) != 5829 PermissionsState.PERMISSION_OPERATION_FAILURE) { 5830 scheduleWriteSettingsLocked(); 5831 } 5832 return; 5833 } 5834 5835 if (permissionsState.revokeRuntimePermission(bp, userId) == 5836 PermissionsState.PERMISSION_OPERATION_FAILURE) { 5837 return; 5838 } 5839 5840 if (bp.isRuntime()) { 5841 logPermissionRevoked(mContext, name, packageName); 5842 } 5843 5844 mOnPermissionChangeListeners.onPermissionsChanged(pkg.applicationInfo.uid); 5845 5846 // Critical, after this call app should never have the permission. 5847 mSettings.writeRuntimePermissionsForUserLPr(userId, true); 5848 5849 appId = UserHandle.getAppId(pkg.applicationInfo.uid); 5850 } 5851 5852 killUid(appId, userId, KILL_APP_REASON_PERMISSIONS_REVOKED); 5853 } 5854 5855 /** 5856 * Get the first event id for the permission. 5857 * 5858 * <p>There are four events for each permission: <ul> 5859 * <li>Request permission: first id + 0</li> 5860 * <li>Grant permission: first id + 1</li> 5861 * <li>Request for permission denied: first id + 2</li> 5862 * <li>Revoke permission: first id + 3</li> 5863 * </ul></p> 5864 * 5865 * @param name name of the permission 5866 * 5867 * @return The first event id for the permission 5868 */ 5869 private static int getBaseEventId(@NonNull String name) { 5870 int eventIdIndex = ALL_DANGEROUS_PERMISSIONS.indexOf(name); 5871 5872 if (eventIdIndex == -1) { 5873 if (AppOpsManager.permissionToOpCode(name) == AppOpsManager.OP_NONE 5874 || Build.IS_USER) { 5875 Log.i(TAG, "Unknown permission " + name); 5876 5877 return MetricsEvent.ACTION_PERMISSION_REQUEST_UNKNOWN; 5878 } else { 5879 // Most likely #ALL_DANGEROUS_PERMISSIONS needs to be updated. 5880 // 5881 // Also update 5882 // - EventLogger#ALL_DANGEROUS_PERMISSIONS 5883 // - metrics_constants.proto 5884 throw new IllegalStateException("Unknown permission " + name); 5885 } 5886 } 5887 5888 return MetricsEvent.ACTION_PERMISSION_REQUEST_READ_CALENDAR + eventIdIndex * 4; 5889 } 5890 5891 /** 5892 * Log that a permission was revoked. 5893 * 5894 * @param context Context of the caller 5895 * @param name name of the permission 5896 * @param packageName package permission if for 5897 */ 5898 private static void logPermissionRevoked(@NonNull Context context, @NonNull String name, 5899 @NonNull String packageName) { 5900 MetricsLogger.action(context, getBaseEventId(name) + 3, packageName); 5901 } 5902 5903 /** 5904 * Log that a permission request was granted. 5905 * 5906 * @param context Context of the caller 5907 * @param name name of the permission 5908 * @param packageName package permission if for 5909 */ 5910 private static void logPermissionGranted(@NonNull Context context, @NonNull String name, 5911 @NonNull String packageName) { 5912 MetricsLogger.action(context, getBaseEventId(name) + 1, packageName); 5913 } 5914 5915 @Override 5916 public void resetRuntimePermissions() { 5917 mContext.enforceCallingOrSelfPermission( 5918 android.Manifest.permission.REVOKE_RUNTIME_PERMISSIONS, 5919 "revokeRuntimePermission"); 5920 5921 int callingUid = Binder.getCallingUid(); 5922 if (callingUid != Process.SYSTEM_UID && callingUid != 0) { 5923 mContext.enforceCallingOrSelfPermission( 5924 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, 5925 "resetRuntimePermissions"); 5926 } 5927 5928 synchronized (mPackages) { 5929 updatePermissionsLPw(null, null, UPDATE_PERMISSIONS_ALL); 5930 for (int userId : UserManagerService.getInstance().getUserIds()) { 5931 final int packageCount = mPackages.size(); 5932 for (int i = 0; i < packageCount; i++) { 5933 PackageParser.Package pkg = mPackages.valueAt(i); 5934 if (!(pkg.mExtras instanceof PackageSetting)) { 5935 continue; 5936 } 5937 PackageSetting ps = (PackageSetting) pkg.mExtras; 5938 resetUserChangesToRuntimePermissionsAndFlagsLPw(ps, userId); 5939 } 5940 } 5941 } 5942 } 5943 5944 @Override 5945 public int getPermissionFlags(String name, String packageName, int userId) { 5946 if (!sUserManager.exists(userId)) { 5947 return 0; 5948 } 5949 5950 enforceGrantRevokeRuntimePermissionPermissions("getPermissionFlags"); 5951 5952 final int callingUid = Binder.getCallingUid(); 5953 enforceCrossUserPermission(callingUid, userId, 5954 true /* requireFullPermission */, false /* checkShell */, 5955 "getPermissionFlags"); 5956 5957 synchronized (mPackages) { 5958 final PackageParser.Package pkg = mPackages.get(packageName); 5959 if (pkg == null) { 5960 return 0; 5961 } 5962 final BasePermission bp = mSettings.mPermissions.get(name); 5963 if (bp == null) { 5964 return 0; 5965 } 5966 final PackageSetting ps = (PackageSetting) pkg.mExtras; 5967 if (ps == null 5968 || filterAppAccessLPr(ps, callingUid, userId)) { 5969 return 0; 5970 } 5971 PermissionsState permissionsState = ps.getPermissionsState(); 5972 return permissionsState.getPermissionFlags(name, userId); 5973 } 5974 } 5975 5976 @Override 5977 public void updatePermissionFlags(String name, String packageName, int flagMask, 5978 int flagValues, int userId) { 5979 if (!sUserManager.exists(userId)) { 5980 return; 5981 } 5982 5983 enforceGrantRevokeRuntimePermissionPermissions("updatePermissionFlags"); 5984 5985 final int callingUid = Binder.getCallingUid(); 5986 enforceCrossUserPermission(callingUid, userId, 5987 true /* requireFullPermission */, true /* checkShell */, 5988 "updatePermissionFlags"); 5989 5990 // Only the system can change these flags and nothing else. 5991 if (getCallingUid() != Process.SYSTEM_UID) { 5992 flagMask &= ~PackageManager.FLAG_PERMISSION_SYSTEM_FIXED; 5993 flagValues &= ~PackageManager.FLAG_PERMISSION_SYSTEM_FIXED; 5994 flagMask &= ~PackageManager.FLAG_PERMISSION_GRANTED_BY_DEFAULT; 5995 flagValues &= ~PackageManager.FLAG_PERMISSION_GRANTED_BY_DEFAULT; 5996 flagValues &= ~PackageManager.FLAG_PERMISSION_REVIEW_REQUIRED; 5997 } 5998 5999 synchronized (mPackages) { 6000 final PackageParser.Package pkg = mPackages.get(packageName); 6001 if (pkg == null) { 6002 throw new IllegalArgumentException("Unknown package: " + packageName); 6003 } 6004 final PackageSetting ps = (PackageSetting) pkg.mExtras; 6005 if (ps == null 6006 || filterAppAccessLPr(ps, callingUid, userId)) { 6007 throw new IllegalArgumentException("Unknown package: " + packageName); 6008 } 6009 6010 final BasePermission bp = mSettings.mPermissions.get(name); 6011 if (bp == null) { 6012 throw new IllegalArgumentException("Unknown permission: " + name); 6013 } 6014 6015 PermissionsState permissionsState = ps.getPermissionsState(); 6016 6017 boolean hadState = permissionsState.getRuntimePermissionState(name, userId) != null; 6018 6019 if (permissionsState.updatePermissionFlags(bp, userId, flagMask, flagValues)) { 6020 // Install and runtime permissions are stored in different places, 6021 // so figure out what permission changed and persist the change. 6022 if (permissionsState.getInstallPermissionState(name) != null) { 6023 scheduleWriteSettingsLocked(); 6024 } else if (permissionsState.getRuntimePermissionState(name, userId) != null 6025 || hadState) { 6026 mSettings.writeRuntimePermissionsForUserLPr(userId, false); 6027 } 6028 } 6029 } 6030 } 6031 6032 /** 6033 * Update the permission flags for all packages and runtime permissions of a user in order 6034 * to allow device or profile owner to remove POLICY_FIXED. 6035 */ 6036 @Override 6037 public void updatePermissionFlagsForAllApps(int flagMask, int flagValues, int userId) { 6038 if (!sUserManager.exists(userId)) { 6039 return; 6040 } 6041 6042 enforceGrantRevokeRuntimePermissionPermissions("updatePermissionFlagsForAllApps"); 6043 6044 enforceCrossUserPermission(Binder.getCallingUid(), userId, 6045 true /* requireFullPermission */, true /* checkShell */, 6046 "updatePermissionFlagsForAllApps"); 6047 6048 // Only the system can change system fixed flags. 6049 if (getCallingUid() != Process.SYSTEM_UID) { 6050 flagMask &= ~PackageManager.FLAG_PERMISSION_SYSTEM_FIXED; 6051 flagValues &= ~PackageManager.FLAG_PERMISSION_SYSTEM_FIXED; 6052 } 6053 6054 synchronized (mPackages) { 6055 boolean changed = false; 6056 final int packageCount = mPackages.size(); 6057 for (int pkgIndex = 0; pkgIndex < packageCount; pkgIndex++) { 6058 final PackageParser.Package pkg = mPackages.valueAt(pkgIndex); 6059 final PackageSetting ps = (PackageSetting) pkg.mExtras; 6060 if (ps == null) { 6061 continue; 6062 } 6063 PermissionsState permissionsState = ps.getPermissionsState(); 6064 changed |= permissionsState.updatePermissionFlagsForAllPermissions( 6065 userId, flagMask, flagValues); 6066 } 6067 if (changed) { 6068 mSettings.writeRuntimePermissionsForUserLPr(userId, false); 6069 } 6070 } 6071 } 6072 6073 private void enforceGrantRevokeRuntimePermissionPermissions(String message) { 6074 if (mContext.checkCallingOrSelfPermission(Manifest.permission.GRANT_RUNTIME_PERMISSIONS) 6075 != PackageManager.PERMISSION_GRANTED 6076 && mContext.checkCallingOrSelfPermission(Manifest.permission.REVOKE_RUNTIME_PERMISSIONS) 6077 != PackageManager.PERMISSION_GRANTED) { 6078 throw new SecurityException(message + " requires " 6079 + Manifest.permission.GRANT_RUNTIME_PERMISSIONS + " or " 6080 + Manifest.permission.REVOKE_RUNTIME_PERMISSIONS); 6081 } 6082 } 6083 6084 @Override 6085 public boolean shouldShowRequestPermissionRationale(String permissionName, 6086 String packageName, int userId) { 6087 if (UserHandle.getCallingUserId() != userId) { 6088 mContext.enforceCallingPermission( 6089 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, 6090 "canShowRequestPermissionRationale for user " + userId); 6091 } 6092 6093 final int uid = getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, userId); 6094 if (UserHandle.getAppId(getCallingUid()) != UserHandle.getAppId(uid)) { 6095 return false; 6096 } 6097 6098 if (checkPermission(permissionName, packageName, userId) 6099 == PackageManager.PERMISSION_GRANTED) { 6100 return false; 6101 } 6102 6103 final int flags; 6104 6105 final long identity = Binder.clearCallingIdentity(); 6106 try { 6107 flags = getPermissionFlags(permissionName, 6108 packageName, userId); 6109 } finally { 6110 Binder.restoreCallingIdentity(identity); 6111 } 6112 6113 final int fixedFlags = PackageManager.FLAG_PERMISSION_SYSTEM_FIXED 6114 | PackageManager.FLAG_PERMISSION_POLICY_FIXED 6115 | PackageManager.FLAG_PERMISSION_USER_FIXED; 6116 6117 if ((flags & fixedFlags) != 0) { 6118 return false; 6119 } 6120 6121 return (flags & PackageManager.FLAG_PERMISSION_USER_SET) != 0; 6122 } 6123 6124 @Override 6125 public void addOnPermissionsChangeListener(IOnPermissionsChangeListener listener) { 6126 mContext.enforceCallingOrSelfPermission( 6127 Manifest.permission.OBSERVE_GRANT_REVOKE_PERMISSIONS, 6128 "addOnPermissionsChangeListener"); 6129 6130 synchronized (mPackages) { 6131 mOnPermissionChangeListeners.addListenerLocked(listener); 6132 } 6133 } 6134 6135 @Override 6136 public void removeOnPermissionsChangeListener(IOnPermissionsChangeListener listener) { 6137 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 6138 throw new SecurityException("Instant applications don't have access to this method"); 6139 } 6140 synchronized (mPackages) { 6141 mOnPermissionChangeListeners.removeListenerLocked(listener); 6142 } 6143 } 6144 6145 @Override 6146 public boolean isProtectedBroadcast(String actionName) { 6147 // allow instant applications 6148 synchronized (mProtectedBroadcasts) { 6149 if (mProtectedBroadcasts.contains(actionName)) { 6150 return true; 6151 } else if (actionName != null) { 6152 // TODO: remove these terrible hacks 6153 if (actionName.startsWith("android.net.netmon.lingerExpired") 6154 || actionName.startsWith("com.android.server.sip.SipWakeupTimer") 6155 || actionName.startsWith("com.android.internal.telephony.data-reconnect") 6156 || actionName.startsWith("android.net.netmon.launchCaptivePortalApp")) { 6157 return true; 6158 } 6159 } 6160 } 6161 return false; 6162 } 6163 6164 @Override 6165 public int checkSignatures(String pkg1, String pkg2) { 6166 synchronized (mPackages) { 6167 final PackageParser.Package p1 = mPackages.get(pkg1); 6168 final PackageParser.Package p2 = mPackages.get(pkg2); 6169 if (p1 == null || p1.mExtras == null 6170 || p2 == null || p2.mExtras == null) { 6171 return PackageManager.SIGNATURE_UNKNOWN_PACKAGE; 6172 } 6173 final int callingUid = Binder.getCallingUid(); 6174 final int callingUserId = UserHandle.getUserId(callingUid); 6175 final PackageSetting ps1 = (PackageSetting) p1.mExtras; 6176 final PackageSetting ps2 = (PackageSetting) p2.mExtras; 6177 if (filterAppAccessLPr(ps1, callingUid, callingUserId) 6178 || filterAppAccessLPr(ps2, callingUid, callingUserId)) { 6179 return PackageManager.SIGNATURE_UNKNOWN_PACKAGE; 6180 } 6181 return compareSignatures(p1.mSignatures, p2.mSignatures); 6182 } 6183 } 6184 6185 @Override 6186 public int checkUidSignatures(int uid1, int uid2) { 6187 final int callingUid = Binder.getCallingUid(); 6188 final int callingUserId = UserHandle.getUserId(callingUid); 6189 final boolean isCallerInstantApp = getInstantAppPackageName(callingUid) != null; 6190 // Map to base uids. 6191 uid1 = UserHandle.getAppId(uid1); 6192 uid2 = UserHandle.getAppId(uid2); 6193 // reader 6194 synchronized (mPackages) { 6195 Signature[] s1; 6196 Signature[] s2; 6197 Object obj = mSettings.getUserIdLPr(uid1); 6198 if (obj != null) { 6199 if (obj instanceof SharedUserSetting) { 6200 if (isCallerInstantApp) { 6201 return PackageManager.SIGNATURE_UNKNOWN_PACKAGE; 6202 } 6203 s1 = ((SharedUserSetting)obj).signatures.mSignatures; 6204 } else if (obj instanceof PackageSetting) { 6205 final PackageSetting ps = (PackageSetting) obj; 6206 if (filterAppAccessLPr(ps, callingUid, callingUserId)) { 6207 return PackageManager.SIGNATURE_UNKNOWN_PACKAGE; 6208 } 6209 s1 = ps.signatures.mSignatures; 6210 } else { 6211 return PackageManager.SIGNATURE_UNKNOWN_PACKAGE; 6212 } 6213 } else { 6214 return PackageManager.SIGNATURE_UNKNOWN_PACKAGE; 6215 } 6216 obj = mSettings.getUserIdLPr(uid2); 6217 if (obj != null) { 6218 if (obj instanceof SharedUserSetting) { 6219 if (isCallerInstantApp) { 6220 return PackageManager.SIGNATURE_UNKNOWN_PACKAGE; 6221 } 6222 s2 = ((SharedUserSetting)obj).signatures.mSignatures; 6223 } else if (obj instanceof PackageSetting) { 6224 final PackageSetting ps = (PackageSetting) obj; 6225 if (filterAppAccessLPr(ps, callingUid, callingUserId)) { 6226 return PackageManager.SIGNATURE_UNKNOWN_PACKAGE; 6227 } 6228 s2 = ps.signatures.mSignatures; 6229 } else { 6230 return PackageManager.SIGNATURE_UNKNOWN_PACKAGE; 6231 } 6232 } else { 6233 return PackageManager.SIGNATURE_UNKNOWN_PACKAGE; 6234 } 6235 return compareSignatures(s1, s2); 6236 } 6237 } 6238 6239 /** 6240 * This method should typically only be used when granting or revoking 6241 * permissions, since the app may immediately restart after this call. 6242 * <p> 6243 * If you're doing surgery on app code/data, use {@link PackageFreezer} to 6244 * guard your work against the app being relaunched. 6245 */ 6246 private void killUid(int appId, int userId, String reason) { 6247 final long identity = Binder.clearCallingIdentity(); 6248 try { 6249 IActivityManager am = ActivityManager.getService(); 6250 if (am != null) { 6251 try { 6252 am.killUid(appId, userId, reason); 6253 } catch (RemoteException e) { 6254 /* ignore - same process */ 6255 } 6256 } 6257 } finally { 6258 Binder.restoreCallingIdentity(identity); 6259 } 6260 } 6261 6262 /** 6263 * Compares two sets of signatures. Returns: 6264 * <br /> 6265 * {@link PackageManager#SIGNATURE_NEITHER_SIGNED}: if both signature sets are null, 6266 * <br /> 6267 * {@link PackageManager#SIGNATURE_FIRST_NOT_SIGNED}: if the first signature set is null, 6268 * <br /> 6269 * {@link PackageManager#SIGNATURE_SECOND_NOT_SIGNED}: if the second signature set is null, 6270 * <br /> 6271 * {@link PackageManager#SIGNATURE_MATCH}: if the two signature sets are identical, 6272 * <br /> 6273 * {@link PackageManager#SIGNATURE_NO_MATCH}: if the two signature sets differ. 6274 */ 6275 static int compareSignatures(Signature[] s1, Signature[] s2) { 6276 if (s1 == null) { 6277 return s2 == null 6278 ? PackageManager.SIGNATURE_NEITHER_SIGNED 6279 : PackageManager.SIGNATURE_FIRST_NOT_SIGNED; 6280 } 6281 6282 if (s2 == null) { 6283 return PackageManager.SIGNATURE_SECOND_NOT_SIGNED; 6284 } 6285 6286 if (s1.length != s2.length) { 6287 return PackageManager.SIGNATURE_NO_MATCH; 6288 } 6289 6290 // Since both signature sets are of size 1, we can compare without HashSets. 6291 if (s1.length == 1) { 6292 return s1[0].equals(s2[0]) ? 6293 PackageManager.SIGNATURE_MATCH : 6294 PackageManager.SIGNATURE_NO_MATCH; 6295 } 6296 6297 ArraySet<Signature> set1 = new ArraySet<Signature>(); 6298 for (Signature sig : s1) { 6299 set1.add(sig); 6300 } 6301 ArraySet<Signature> set2 = new ArraySet<Signature>(); 6302 for (Signature sig : s2) { 6303 set2.add(sig); 6304 } 6305 // Make sure s2 contains all signatures in s1. 6306 if (set1.equals(set2)) { 6307 return PackageManager.SIGNATURE_MATCH; 6308 } 6309 return PackageManager.SIGNATURE_NO_MATCH; 6310 } 6311 6312 /** 6313 * If the database version for this type of package (internal storage or 6314 * external storage) is less than the version where package signatures 6315 * were updated, return true. 6316 */ 6317 private boolean isCompatSignatureUpdateNeeded(PackageParser.Package scannedPkg) { 6318 final VersionInfo ver = getSettingsVersionForPackage(scannedPkg); 6319 return ver.databaseVersion < DatabaseVersion.SIGNATURE_END_ENTITY; 6320 } 6321 6322 /** 6323 * Used for backward compatibility to make sure any packages with 6324 * certificate chains get upgraded to the new style. {@code existingSigs} 6325 * will be in the old format (since they were stored on disk from before the 6326 * system upgrade) and {@code scannedSigs} will be in the newer format. 6327 */ 6328 private int compareSignaturesCompat(PackageSignatures existingSigs, 6329 PackageParser.Package scannedPkg) { 6330 if (!isCompatSignatureUpdateNeeded(scannedPkg)) { 6331 return PackageManager.SIGNATURE_NO_MATCH; 6332 } 6333 6334 ArraySet<Signature> existingSet = new ArraySet<Signature>(); 6335 for (Signature sig : existingSigs.mSignatures) { 6336 existingSet.add(sig); 6337 } 6338 ArraySet<Signature> scannedCompatSet = new ArraySet<Signature>(); 6339 for (Signature sig : scannedPkg.mSignatures) { 6340 try { 6341 Signature[] chainSignatures = sig.getChainSignatures(); 6342 for (Signature chainSig : chainSignatures) { 6343 scannedCompatSet.add(chainSig); 6344 } 6345 } catch (CertificateEncodingException e) { 6346 scannedCompatSet.add(sig); 6347 } 6348 } 6349 /* 6350 * Make sure the expanded scanned set contains all signatures in the 6351 * existing one. 6352 */ 6353 if (scannedCompatSet.equals(existingSet)) { 6354 // Migrate the old signatures to the new scheme. 6355 existingSigs.assignSignatures(scannedPkg.mSignatures); 6356 // The new KeySets will be re-added later in the scanning process. 6357 synchronized (mPackages) { 6358 mSettings.mKeySetManagerService.removeAppKeySetDataLPw(scannedPkg.packageName); 6359 } 6360 return PackageManager.SIGNATURE_MATCH; 6361 } 6362 return PackageManager.SIGNATURE_NO_MATCH; 6363 } 6364 6365 private boolean isRecoverSignatureUpdateNeeded(PackageParser.Package scannedPkg) { 6366 final VersionInfo ver = getSettingsVersionForPackage(scannedPkg); 6367 return ver.databaseVersion < DatabaseVersion.SIGNATURE_MALFORMED_RECOVER; 6368 } 6369 6370 private int compareSignaturesRecover(PackageSignatures existingSigs, 6371 PackageParser.Package scannedPkg) { 6372 if (!isRecoverSignatureUpdateNeeded(scannedPkg)) { 6373 return PackageManager.SIGNATURE_NO_MATCH; 6374 } 6375 6376 String msg = null; 6377 try { 6378 if (Signature.areEffectiveMatch(existingSigs.mSignatures, scannedPkg.mSignatures)) { 6379 logCriticalInfo(Log.INFO, "Recovered effectively matching certificates for " 6380 + scannedPkg.packageName); 6381 return PackageManager.SIGNATURE_MATCH; 6382 } 6383 } catch (CertificateException e) { 6384 msg = e.getMessage(); 6385 } 6386 6387 logCriticalInfo(Log.INFO, 6388 "Failed to recover certificates for " + scannedPkg.packageName + ": " + msg); 6389 return PackageManager.SIGNATURE_NO_MATCH; 6390 } 6391 6392 @Override 6393 public List<String> getAllPackages() { 6394 final int callingUid = Binder.getCallingUid(); 6395 final int callingUserId = UserHandle.getUserId(callingUid); 6396 synchronized (mPackages) { 6397 if (canViewInstantApps(callingUid, callingUserId)) { 6398 return new ArrayList<String>(mPackages.keySet()); 6399 } 6400 final String instantAppPkgName = getInstantAppPackageName(callingUid); 6401 final List<String> result = new ArrayList<>(); 6402 if (instantAppPkgName != null) { 6403 // caller is an instant application; filter unexposed applications 6404 for (PackageParser.Package pkg : mPackages.values()) { 6405 if (!pkg.visibleToInstantApps) { 6406 continue; 6407 } 6408 result.add(pkg.packageName); 6409 } 6410 } else { 6411 // caller is a normal application; filter instant applications 6412 for (PackageParser.Package pkg : mPackages.values()) { 6413 final PackageSetting ps = 6414 pkg.mExtras != null ? (PackageSetting) pkg.mExtras : null; 6415 if (ps != null 6416 && ps.getInstantApp(callingUserId) 6417 && !mInstantAppRegistry.isInstantAccessGranted( 6418 callingUserId, UserHandle.getAppId(callingUid), ps.appId)) { 6419 continue; 6420 } 6421 result.add(pkg.packageName); 6422 } 6423 } 6424 return result; 6425 } 6426 } 6427 6428 @Override 6429 public String[] getPackagesForUid(int uid) { 6430 final int callingUid = Binder.getCallingUid(); 6431 final boolean isCallerInstantApp = getInstantAppPackageName(callingUid) != null; 6432 final int userId = UserHandle.getUserId(uid); 6433 uid = UserHandle.getAppId(uid); 6434 // reader 6435 synchronized (mPackages) { 6436 Object obj = mSettings.getUserIdLPr(uid); 6437 if (obj instanceof SharedUserSetting) { 6438 if (isCallerInstantApp) { 6439 return null; 6440 } 6441 final SharedUserSetting sus = (SharedUserSetting) obj; 6442 final int N = sus.packages.size(); 6443 String[] res = new String[N]; 6444 final Iterator<PackageSetting> it = sus.packages.iterator(); 6445 int i = 0; 6446 while (it.hasNext()) { 6447 PackageSetting ps = it.next(); 6448 if (ps.getInstalled(userId)) { 6449 res[i++] = ps.name; 6450 } else { 6451 res = ArrayUtils.removeElement(String.class, res, res[i]); 6452 } 6453 } 6454 return res; 6455 } else if (obj instanceof PackageSetting) { 6456 final PackageSetting ps = (PackageSetting) obj; 6457 if (ps.getInstalled(userId) && !filterAppAccessLPr(ps, callingUid, userId)) { 6458 return new String[]{ps.name}; 6459 } 6460 } 6461 } 6462 return null; 6463 } 6464 6465 @Override 6466 public String getNameForUid(int uid) { 6467 final int callingUid = Binder.getCallingUid(); 6468 if (getInstantAppPackageName(callingUid) != null) { 6469 return null; 6470 } 6471 synchronized (mPackages) { 6472 Object obj = mSettings.getUserIdLPr(UserHandle.getAppId(uid)); 6473 if (obj instanceof SharedUserSetting) { 6474 final SharedUserSetting sus = (SharedUserSetting) obj; 6475 return sus.name + ":" + sus.userId; 6476 } else if (obj instanceof PackageSetting) { 6477 final PackageSetting ps = (PackageSetting) obj; 6478 if (filterAppAccessLPr(ps, callingUid, UserHandle.getUserId(callingUid))) { 6479 return null; 6480 } 6481 return ps.name; 6482 } 6483 return null; 6484 } 6485 } 6486 6487 @Override 6488 public String[] getNamesForUids(int[] uids) { 6489 if (uids == null || uids.length == 0) { 6490 return null; 6491 } 6492 final int callingUid = Binder.getCallingUid(); 6493 if (getInstantAppPackageName(callingUid) != null) { 6494 return null; 6495 } 6496 final String[] names = new String[uids.length]; 6497 synchronized (mPackages) { 6498 for (int i = uids.length - 1; i >= 0; i--) { 6499 final int uid = uids[i]; 6500 Object obj = mSettings.getUserIdLPr(UserHandle.getAppId(uid)); 6501 if (obj instanceof SharedUserSetting) { 6502 final SharedUserSetting sus = (SharedUserSetting) obj; 6503 names[i] = "shared:" + sus.name; 6504 } else if (obj instanceof PackageSetting) { 6505 final PackageSetting ps = (PackageSetting) obj; 6506 if (filterAppAccessLPr(ps, callingUid, UserHandle.getUserId(callingUid))) { 6507 names[i] = null; 6508 } else { 6509 names[i] = ps.name; 6510 } 6511 } else { 6512 names[i] = null; 6513 } 6514 } 6515 } 6516 return names; 6517 } 6518 6519 @Override 6520 public int getUidForSharedUser(String sharedUserName) { 6521 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 6522 return -1; 6523 } 6524 if (sharedUserName == null) { 6525 return -1; 6526 } 6527 // reader 6528 synchronized (mPackages) { 6529 SharedUserSetting suid; 6530 try { 6531 suid = mSettings.getSharedUserLPw(sharedUserName, 0, 0, false); 6532 if (suid != null) { 6533 return suid.userId; 6534 } 6535 } catch (PackageManagerException ignore) { 6536 // can't happen, but, still need to catch it 6537 } 6538 return -1; 6539 } 6540 } 6541 6542 @Override 6543 public int getFlagsForUid(int uid) { 6544 final int callingUid = Binder.getCallingUid(); 6545 if (getInstantAppPackageName(callingUid) != null) { 6546 return 0; 6547 } 6548 synchronized (mPackages) { 6549 Object obj = mSettings.getUserIdLPr(UserHandle.getAppId(uid)); 6550 if (obj instanceof SharedUserSetting) { 6551 final SharedUserSetting sus = (SharedUserSetting) obj; 6552 return sus.pkgFlags; 6553 } else if (obj instanceof PackageSetting) { 6554 final PackageSetting ps = (PackageSetting) obj; 6555 if (filterAppAccessLPr(ps, callingUid, UserHandle.getUserId(callingUid))) { 6556 return 0; 6557 } 6558 return ps.pkgFlags; 6559 } 6560 } 6561 return 0; 6562 } 6563 6564 @Override 6565 public int getPrivateFlagsForUid(int uid) { 6566 final int callingUid = Binder.getCallingUid(); 6567 if (getInstantAppPackageName(callingUid) != null) { 6568 return 0; 6569 } 6570 synchronized (mPackages) { 6571 Object obj = mSettings.getUserIdLPr(UserHandle.getAppId(uid)); 6572 if (obj instanceof SharedUserSetting) { 6573 final SharedUserSetting sus = (SharedUserSetting) obj; 6574 return sus.pkgPrivateFlags; 6575 } else if (obj instanceof PackageSetting) { 6576 final PackageSetting ps = (PackageSetting) obj; 6577 if (filterAppAccessLPr(ps, callingUid, UserHandle.getUserId(callingUid))) { 6578 return 0; 6579 } 6580 return ps.pkgPrivateFlags; 6581 } 6582 } 6583 return 0; 6584 } 6585 6586 @Override 6587 public boolean isUidPrivileged(int uid) { 6588 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 6589 return false; 6590 } 6591 uid = UserHandle.getAppId(uid); 6592 // reader 6593 synchronized (mPackages) { 6594 Object obj = mSettings.getUserIdLPr(uid); 6595 if (obj instanceof SharedUserSetting) { 6596 final SharedUserSetting sus = (SharedUserSetting) obj; 6597 final Iterator<PackageSetting> it = sus.packages.iterator(); 6598 while (it.hasNext()) { 6599 if (it.next().isPrivileged()) { 6600 return true; 6601 } 6602 } 6603 } else if (obj instanceof PackageSetting) { 6604 final PackageSetting ps = (PackageSetting) obj; 6605 return ps.isPrivileged(); 6606 } 6607 } 6608 return false; 6609 } 6610 6611 @Override 6612 public String[] getAppOpPermissionPackages(String permissionName) { 6613 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 6614 return null; 6615 } 6616 synchronized (mPackages) { 6617 ArraySet<String> pkgs = mAppOpPermissionPackages.get(permissionName); 6618 if (pkgs == null) { 6619 return null; 6620 } 6621 return pkgs.toArray(new String[pkgs.size()]); 6622 } 6623 } 6624 6625 @Override 6626 public ResolveInfo resolveIntent(Intent intent, String resolvedType, 6627 int flags, int userId) { 6628 return resolveIntentInternal( 6629 intent, resolvedType, flags, userId, false /*includeInstantApps*/); 6630 } 6631 6632 private ResolveInfo resolveIntentInternal(Intent intent, String resolvedType, 6633 int flags, int userId, boolean resolveForStart) { 6634 try { 6635 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "resolveIntent"); 6636 6637 if (!sUserManager.exists(userId)) return null; 6638 final int callingUid = Binder.getCallingUid(); 6639 flags = updateFlagsForResolve(flags, userId, intent, callingUid, resolveForStart); 6640 enforceCrossUserPermission(callingUid, userId, 6641 false /*requireFullPermission*/, false /*checkShell*/, "resolve intent"); 6642 6643 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "queryIntentActivities"); 6644 final List<ResolveInfo> query = queryIntentActivitiesInternal(intent, resolvedType, 6645 flags, callingUid, userId, resolveForStart, true /*allowDynamicSplits*/); 6646 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 6647 6648 final ResolveInfo bestChoice = 6649 chooseBestActivity(intent, resolvedType, flags, query, userId); 6650 return bestChoice; 6651 } finally { 6652 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 6653 } 6654 } 6655 6656 @Override 6657 public ResolveInfo findPersistentPreferredActivity(Intent intent, int userId) { 6658 if (!UserHandle.isSameApp(Binder.getCallingUid(), Process.SYSTEM_UID)) { 6659 throw new SecurityException( 6660 "findPersistentPreferredActivity can only be run by the system"); 6661 } 6662 if (!sUserManager.exists(userId)) { 6663 return null; 6664 } 6665 final int callingUid = Binder.getCallingUid(); 6666 intent = updateIntentForResolve(intent); 6667 final String resolvedType = intent.resolveTypeIfNeeded(mContext.getContentResolver()); 6668 final int flags = updateFlagsForResolve( 6669 0, userId, intent, callingUid, false /*includeInstantApps*/); 6670 final List<ResolveInfo> query = queryIntentActivitiesInternal(intent, resolvedType, flags, 6671 userId); 6672 synchronized (mPackages) { 6673 return findPersistentPreferredActivityLP(intent, resolvedType, flags, query, false, 6674 userId); 6675 } 6676 } 6677 6678 @Override 6679 public void setLastChosenActivity(Intent intent, String resolvedType, int flags, 6680 IntentFilter filter, int match, ComponentName activity) { 6681 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 6682 return; 6683 } 6684 final int userId = UserHandle.getCallingUserId(); 6685 if (DEBUG_PREFERRED) { 6686 Log.v(TAG, "setLastChosenActivity intent=" + intent 6687 + " resolvedType=" + resolvedType 6688 + " flags=" + flags 6689 + " filter=" + filter 6690 + " match=" + match 6691 + " activity=" + activity); 6692 filter.dump(new PrintStreamPrinter(System.out), " "); 6693 } 6694 intent.setComponent(null); 6695 final List<ResolveInfo> query = queryIntentActivitiesInternal(intent, resolvedType, flags, 6696 userId); 6697 // Find any earlier preferred or last chosen entries and nuke them 6698 findPreferredActivity(intent, resolvedType, 6699 flags, query, 0, false, true, false, userId); 6700 // Add the new activity as the last chosen for this filter 6701 addPreferredActivityInternal(filter, match, null, activity, false, userId, 6702 "Setting last chosen"); 6703 } 6704 6705 @Override 6706 public ResolveInfo getLastChosenActivity(Intent intent, String resolvedType, int flags) { 6707 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 6708 return null; 6709 } 6710 final int userId = UserHandle.getCallingUserId(); 6711 if (DEBUG_PREFERRED) Log.v(TAG, "Querying last chosen activity for " + intent); 6712 final List<ResolveInfo> query = queryIntentActivitiesInternal(intent, resolvedType, flags, 6713 userId); 6714 return findPreferredActivity(intent, resolvedType, flags, query, 0, 6715 false, false, false, userId); 6716 } 6717 6718 /** 6719 * Returns whether or not instant apps have been disabled remotely. 6720 */ 6721 private boolean isEphemeralDisabled() { 6722 return mEphemeralAppsDisabled; 6723 } 6724 6725 private boolean isInstantAppAllowed( 6726 Intent intent, List<ResolveInfo> resolvedActivities, int userId, 6727 boolean skipPackageCheck) { 6728 if (mInstantAppResolverConnection == null) { 6729 return false; 6730 } 6731 if (mInstantAppInstallerActivity == null) { 6732 return false; 6733 } 6734 if (intent.getComponent() != null) { 6735 return false; 6736 } 6737 if ((intent.getFlags() & Intent.FLAG_IGNORE_EPHEMERAL) != 0) { 6738 return false; 6739 } 6740 if (!skipPackageCheck && intent.getPackage() != null) { 6741 return false; 6742 } 6743 final boolean isWebUri = hasWebURI(intent); 6744 if (!isWebUri || intent.getData().getHost() == null) { 6745 return false; 6746 } 6747 // Deny ephemeral apps if the user chose _ALWAYS or _ALWAYS_ASK for intent resolution. 6748 // Or if there's already an ephemeral app installed that handles the action 6749 synchronized (mPackages) { 6750 final int count = (resolvedActivities == null ? 0 : resolvedActivities.size()); 6751 for (int n = 0; n < count; n++) { 6752 final ResolveInfo info = resolvedActivities.get(n); 6753 final String packageName = info.activityInfo.packageName; 6754 final PackageSetting ps = mSettings.mPackages.get(packageName); 6755 if (ps != null) { 6756 // only check domain verification status if the app is not a browser 6757 if (!info.handleAllWebDataURI) { 6758 // Try to get the status from User settings first 6759 final long packedStatus = getDomainVerificationStatusLPr(ps, userId); 6760 final int status = (int) (packedStatus >> 32); 6761 if (status == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS 6762 || status == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS_ASK) { 6763 if (DEBUG_EPHEMERAL) { 6764 Slog.v(TAG, "DENY instant app;" 6765 + " pkg: " + packageName + ", status: " + status); 6766 } 6767 return false; 6768 } 6769 } 6770 if (ps.getInstantApp(userId)) { 6771 if (DEBUG_EPHEMERAL) { 6772 Slog.v(TAG, "DENY instant app installed;" 6773 + " pkg: " + packageName); 6774 } 6775 return false; 6776 } 6777 } 6778 } 6779 } 6780 // We've exhausted all ways to deny ephemeral application; let the system look for them. 6781 return true; 6782 } 6783 6784 private void requestInstantAppResolutionPhaseTwo(AuxiliaryResolveInfo responseObj, 6785 Intent origIntent, String resolvedType, String callingPackage, 6786 Bundle verificationBundle, int userId) { 6787 final Message msg = mHandler.obtainMessage(INSTANT_APP_RESOLUTION_PHASE_TWO, 6788 new InstantAppRequest(responseObj, origIntent, resolvedType, 6789 callingPackage, userId, verificationBundle, false /*resolveForStart*/)); 6790 mHandler.sendMessage(msg); 6791 } 6792 6793 private ResolveInfo chooseBestActivity(Intent intent, String resolvedType, 6794 int flags, List<ResolveInfo> query, int userId) { 6795 if (query != null) { 6796 final int N = query.size(); 6797 if (N == 1) { 6798 return query.get(0); 6799 } else if (N > 1) { 6800 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 6801 // If there is more than one activity with the same priority, 6802 // then let the user decide between them. 6803 ResolveInfo r0 = query.get(0); 6804 ResolveInfo r1 = query.get(1); 6805 if (DEBUG_INTENT_MATCHING || debug) { 6806 Slog.v(TAG, r0.activityInfo.name + "=" + r0.priority + " vs " 6807 + r1.activityInfo.name + "=" + r1.priority); 6808 } 6809 // If the first activity has a higher priority, or a different 6810 // default, then it is always desirable to pick it. 6811 if (r0.priority != r1.priority 6812 || r0.preferredOrder != r1.preferredOrder 6813 || r0.isDefault != r1.isDefault) { 6814 return query.get(0); 6815 } 6816 // If we have saved a preference for a preferred activity for 6817 // this Intent, use that. 6818 ResolveInfo ri = findPreferredActivity(intent, resolvedType, 6819 flags, query, r0.priority, true, false, debug, userId); 6820 if (ri != null) { 6821 return ri; 6822 } 6823 // If we have an ephemeral app, use it 6824 for (int i = 0; i < N; i++) { 6825 ri = query.get(i); 6826 if (ri.activityInfo.applicationInfo.isInstantApp()) { 6827 final String packageName = ri.activityInfo.packageName; 6828 final PackageSetting ps = mSettings.mPackages.get(packageName); 6829 final long packedStatus = getDomainVerificationStatusLPr(ps, userId); 6830 final int status = (int)(packedStatus >> 32); 6831 if (status != INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS_ASK) { 6832 return ri; 6833 } 6834 } 6835 } 6836 ri = new ResolveInfo(mResolveInfo); 6837 ri.activityInfo = new ActivityInfo(ri.activityInfo); 6838 ri.activityInfo.labelRes = ResolverActivity.getLabelRes(intent.getAction()); 6839 // If all of the options come from the same package, show the application's 6840 // label and icon instead of the generic resolver's. 6841 // Some calls like Intent.resolveActivityInfo query the ResolveInfo from here 6842 // and then throw away the ResolveInfo itself, meaning that the caller loses 6843 // the resolvePackageName. Therefore the activityInfo.labelRes above provides 6844 // a fallback for this case; we only set the target package's resources on 6845 // the ResolveInfo, not the ActivityInfo. 6846 final String intentPackage = intent.getPackage(); 6847 if (!TextUtils.isEmpty(intentPackage) && allHavePackage(query, intentPackage)) { 6848 final ApplicationInfo appi = query.get(0).activityInfo.applicationInfo; 6849 ri.resolvePackageName = intentPackage; 6850 if (userNeedsBadging(userId)) { 6851 ri.noResourceId = true; 6852 } else { 6853 ri.icon = appi.icon; 6854 } 6855 ri.iconResourceId = appi.icon; 6856 ri.labelRes = appi.labelRes; 6857 } 6858 ri.activityInfo.applicationInfo = new ApplicationInfo( 6859 ri.activityInfo.applicationInfo); 6860 if (userId != 0) { 6861 ri.activityInfo.applicationInfo.uid = UserHandle.getUid(userId, 6862 UserHandle.getAppId(ri.activityInfo.applicationInfo.uid)); 6863 } 6864 // Make sure that the resolver is displayable in car mode 6865 if (ri.activityInfo.metaData == null) ri.activityInfo.metaData = new Bundle(); 6866 ri.activityInfo.metaData.putBoolean(Intent.METADATA_DOCK_HOME, true); 6867 return ri; 6868 } 6869 } 6870 return null; 6871 } 6872 6873 /** 6874 * Return true if the given list is not empty and all of its contents have 6875 * an activityInfo with the given package name. 6876 */ 6877 private boolean allHavePackage(List<ResolveInfo> list, String packageName) { 6878 if (ArrayUtils.isEmpty(list)) { 6879 return false; 6880 } 6881 for (int i = 0, N = list.size(); i < N; i++) { 6882 final ResolveInfo ri = list.get(i); 6883 final ActivityInfo ai = ri != null ? ri.activityInfo : null; 6884 if (ai == null || !packageName.equals(ai.packageName)) { 6885 return false; 6886 } 6887 } 6888 return true; 6889 } 6890 6891 private ResolveInfo findPersistentPreferredActivityLP(Intent intent, String resolvedType, 6892 int flags, List<ResolveInfo> query, boolean debug, int userId) { 6893 final int N = query.size(); 6894 PersistentPreferredIntentResolver ppir = mSettings.mPersistentPreferredActivities 6895 .get(userId); 6896 // Get the list of persistent preferred activities that handle the intent 6897 if (DEBUG_PREFERRED || debug) Slog.v(TAG, "Looking for presistent preferred activities..."); 6898 List<PersistentPreferredActivity> pprefs = ppir != null 6899 ? ppir.queryIntent(intent, resolvedType, 6900 (flags & PackageManager.MATCH_DEFAULT_ONLY) != 0, 6901 userId) 6902 : null; 6903 if (pprefs != null && pprefs.size() > 0) { 6904 final int M = pprefs.size(); 6905 for (int i=0; i<M; i++) { 6906 final PersistentPreferredActivity ppa = pprefs.get(i); 6907 if (DEBUG_PREFERRED || debug) { 6908 Slog.v(TAG, "Checking PersistentPreferredActivity ds=" 6909 + (ppa.countDataSchemes() > 0 ? ppa.getDataScheme(0) : "<none>") 6910 + "\n component=" + ppa.mComponent); 6911 ppa.dump(new LogPrinter(Log.VERBOSE, TAG, Log.LOG_ID_SYSTEM), " "); 6912 } 6913 final ActivityInfo ai = getActivityInfo(ppa.mComponent, 6914 flags | MATCH_DISABLED_COMPONENTS, userId); 6915 if (DEBUG_PREFERRED || debug) { 6916 Slog.v(TAG, "Found persistent preferred activity:"); 6917 if (ai != null) { 6918 ai.dump(new LogPrinter(Log.VERBOSE, TAG, Log.LOG_ID_SYSTEM), " "); 6919 } else { 6920 Slog.v(TAG, " null"); 6921 } 6922 } 6923 if (ai == null) { 6924 // This previously registered persistent preferred activity 6925 // component is no longer known. Ignore it and do NOT remove it. 6926 continue; 6927 } 6928 for (int j=0; j<N; j++) { 6929 final ResolveInfo ri = query.get(j); 6930 if (!ri.activityInfo.applicationInfo.packageName 6931 .equals(ai.applicationInfo.packageName)) { 6932 continue; 6933 } 6934 if (!ri.activityInfo.name.equals(ai.name)) { 6935 continue; 6936 } 6937 // Found a persistent preference that can handle the intent. 6938 if (DEBUG_PREFERRED || debug) { 6939 Slog.v(TAG, "Returning persistent preferred activity: " + 6940 ri.activityInfo.packageName + "/" + ri.activityInfo.name); 6941 } 6942 return ri; 6943 } 6944 } 6945 } 6946 return null; 6947 } 6948 6949 // TODO: handle preferred activities missing while user has amnesia 6950 ResolveInfo findPreferredActivity(Intent intent, String resolvedType, int flags, 6951 List<ResolveInfo> query, int priority, boolean always, 6952 boolean removeMatches, boolean debug, int userId) { 6953 if (!sUserManager.exists(userId)) return null; 6954 final int callingUid = Binder.getCallingUid(); 6955 flags = updateFlagsForResolve( 6956 flags, userId, intent, callingUid, false /*includeInstantApps*/); 6957 intent = updateIntentForResolve(intent); 6958 // writer 6959 synchronized (mPackages) { 6960 // Try to find a matching persistent preferred activity. 6961 ResolveInfo pri = findPersistentPreferredActivityLP(intent, resolvedType, flags, query, 6962 debug, userId); 6963 6964 // If a persistent preferred activity matched, use it. 6965 if (pri != null) { 6966 return pri; 6967 } 6968 6969 PreferredIntentResolver pir = mSettings.mPreferredActivities.get(userId); 6970 // Get the list of preferred activities that handle the intent 6971 if (DEBUG_PREFERRED || debug) Slog.v(TAG, "Looking for preferred activities..."); 6972 List<PreferredActivity> prefs = pir != null 6973 ? pir.queryIntent(intent, resolvedType, 6974 (flags & PackageManager.MATCH_DEFAULT_ONLY) != 0, 6975 userId) 6976 : null; 6977 if (prefs != null && prefs.size() > 0) { 6978 boolean changed = false; 6979 try { 6980 // First figure out how good the original match set is. 6981 // We will only allow preferred activities that came 6982 // from the same match quality. 6983 int match = 0; 6984 6985 if (DEBUG_PREFERRED || debug) Slog.v(TAG, "Figuring out best match..."); 6986 6987 final int N = query.size(); 6988 for (int j=0; j<N; j++) { 6989 final ResolveInfo ri = query.get(j); 6990 if (DEBUG_PREFERRED || debug) Slog.v(TAG, "Match for " + ri.activityInfo 6991 + ": 0x" + Integer.toHexString(match)); 6992 if (ri.match > match) { 6993 match = ri.match; 6994 } 6995 } 6996 6997 if (DEBUG_PREFERRED || debug) Slog.v(TAG, "Best match: 0x" 6998 + Integer.toHexString(match)); 6999 7000 match &= IntentFilter.MATCH_CATEGORY_MASK; 7001 final int M = prefs.size(); 7002 for (int i=0; i<M; i++) { 7003 final PreferredActivity pa = prefs.get(i); 7004 if (DEBUG_PREFERRED || debug) { 7005 Slog.v(TAG, "Checking PreferredActivity ds=" 7006 + (pa.countDataSchemes() > 0 ? pa.getDataScheme(0) : "<none>") 7007 + "\n component=" + pa.mPref.mComponent); 7008 pa.dump(new LogPrinter(Log.VERBOSE, TAG, Log.LOG_ID_SYSTEM), " "); 7009 } 7010 if (pa.mPref.mMatch != match) { 7011 if (DEBUG_PREFERRED || debug) Slog.v(TAG, "Skipping bad match " 7012 + Integer.toHexString(pa.mPref.mMatch)); 7013 continue; 7014 } 7015 // If it's not an "always" type preferred activity and that's what we're 7016 // looking for, skip it. 7017 if (always && !pa.mPref.mAlways) { 7018 if (DEBUG_PREFERRED || debug) Slog.v(TAG, "Skipping mAlways=false entry"); 7019 continue; 7020 } 7021 final ActivityInfo ai = getActivityInfo( 7022 pa.mPref.mComponent, flags | MATCH_DISABLED_COMPONENTS 7023 | MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE, 7024 userId); 7025 if (DEBUG_PREFERRED || debug) { 7026 Slog.v(TAG, "Found preferred activity:"); 7027 if (ai != null) { 7028 ai.dump(new LogPrinter(Log.VERBOSE, TAG, Log.LOG_ID_SYSTEM), " "); 7029 } else { 7030 Slog.v(TAG, " null"); 7031 } 7032 } 7033 if (ai == null) { 7034 // This previously registered preferred activity 7035 // component is no longer known. Most likely an update 7036 // to the app was installed and in the new version this 7037 // component no longer exists. Clean it up by removing 7038 // it from the preferred activities list, and skip it. 7039 Slog.w(TAG, "Removing dangling preferred activity: " 7040 + pa.mPref.mComponent); 7041 pir.removeFilter(pa); 7042 changed = true; 7043 continue; 7044 } 7045 for (int j=0; j<N; j++) { 7046 final ResolveInfo ri = query.get(j); 7047 if (!ri.activityInfo.applicationInfo.packageName 7048 .equals(ai.applicationInfo.packageName)) { 7049 continue; 7050 } 7051 if (!ri.activityInfo.name.equals(ai.name)) { 7052 continue; 7053 } 7054 7055 if (removeMatches) { 7056 pir.removeFilter(pa); 7057 changed = true; 7058 if (DEBUG_PREFERRED) { 7059 Slog.v(TAG, "Removing match " + pa.mPref.mComponent); 7060 } 7061 break; 7062 } 7063 7064 // Okay we found a previously set preferred or last chosen app. 7065 // If the result set is different from when this 7066 // was created, and is not a subset of the preferred set, we need to 7067 // clear it and re-ask the user their preference, if we're looking for 7068 // an "always" type entry. 7069 if (always && !pa.mPref.sameSet(query)) { 7070 if (pa.mPref.isSuperset(query)) { 7071 // some components of the set are no longer present in 7072 // the query, but the preferred activity can still be reused 7073 if (DEBUG_PREFERRED) { 7074 Slog.i(TAG, "Result set changed, but PreferredActivity is" 7075 + " still valid as only non-preferred components" 7076 + " were removed for " + intent + " type " 7077 + resolvedType); 7078 } 7079 // remove obsolete components and re-add the up-to-date filter 7080 PreferredActivity freshPa = new PreferredActivity(pa, 7081 pa.mPref.mMatch, 7082 pa.mPref.discardObsoleteComponents(query), 7083 pa.mPref.mComponent, 7084 pa.mPref.mAlways); 7085 pir.removeFilter(pa); 7086 pir.addFilter(freshPa); 7087 changed = true; 7088 } else { 7089 Slog.i(TAG, 7090 "Result set changed, dropping preferred activity for " 7091 + intent + " type " + resolvedType); 7092 if (DEBUG_PREFERRED) { 7093 Slog.v(TAG, "Removing preferred activity since set changed " 7094 + pa.mPref.mComponent); 7095 } 7096 pir.removeFilter(pa); 7097 // Re-add the filter as a "last chosen" entry (!always) 7098 PreferredActivity lastChosen = new PreferredActivity( 7099 pa, pa.mPref.mMatch, null, pa.mPref.mComponent, false); 7100 pir.addFilter(lastChosen); 7101 changed = true; 7102 return null; 7103 } 7104 } 7105 7106 // Yay! Either the set matched or we're looking for the last chosen 7107 if (DEBUG_PREFERRED || debug) Slog.v(TAG, "Returning preferred activity: " 7108 + ri.activityInfo.packageName + "/" + ri.activityInfo.name); 7109 return ri; 7110 } 7111 } 7112 } finally { 7113 if (changed) { 7114 if (DEBUG_PREFERRED) { 7115 Slog.v(TAG, "Preferred activity bookkeeping changed; writing restrictions"); 7116 } 7117 scheduleWritePackageRestrictionsLocked(userId); 7118 } 7119 } 7120 } 7121 } 7122 if (DEBUG_PREFERRED || debug) Slog.v(TAG, "No preferred activity to return"); 7123 return null; 7124 } 7125 7126 /* 7127 * Returns if intent can be forwarded from the sourceUserId to the targetUserId 7128 */ 7129 @Override 7130 public boolean canForwardTo(Intent intent, String resolvedType, int sourceUserId, 7131 int targetUserId) { 7132 mContext.enforceCallingOrSelfPermission( 7133 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, null); 7134 List<CrossProfileIntentFilter> matches = 7135 getMatchingCrossProfileIntentFilters(intent, resolvedType, sourceUserId); 7136 if (matches != null) { 7137 int size = matches.size(); 7138 for (int i = 0; i < size; i++) { 7139 if (matches.get(i).getTargetUserId() == targetUserId) return true; 7140 } 7141 } 7142 if (hasWebURI(intent)) { 7143 // cross-profile app linking works only towards the parent. 7144 final int callingUid = Binder.getCallingUid(); 7145 final UserInfo parent = getProfileParent(sourceUserId); 7146 synchronized(mPackages) { 7147 int flags = updateFlagsForResolve(0, parent.id, intent, callingUid, 7148 false /*includeInstantApps*/); 7149 CrossProfileDomainInfo xpDomainInfo = getCrossProfileDomainPreferredLpr( 7150 intent, resolvedType, flags, sourceUserId, parent.id); 7151 return xpDomainInfo != null; 7152 } 7153 } 7154 return false; 7155 } 7156 7157 private UserInfo getProfileParent(int userId) { 7158 final long identity = Binder.clearCallingIdentity(); 7159 try { 7160 return sUserManager.getProfileParent(userId); 7161 } finally { 7162 Binder.restoreCallingIdentity(identity); 7163 } 7164 } 7165 7166 private List<CrossProfileIntentFilter> getMatchingCrossProfileIntentFilters(Intent intent, 7167 String resolvedType, int userId) { 7168 CrossProfileIntentResolver resolver = mSettings.mCrossProfileIntentResolvers.get(userId); 7169 if (resolver != null) { 7170 return resolver.queryIntent(intent, resolvedType, false /*defaultOnly*/, userId); 7171 } 7172 return null; 7173 } 7174 7175 @Override 7176 public @NonNull ParceledListSlice<ResolveInfo> queryIntentActivities(Intent intent, 7177 String resolvedType, int flags, int userId) { 7178 try { 7179 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "queryIntentActivities"); 7180 7181 return new ParceledListSlice<>( 7182 queryIntentActivitiesInternal(intent, resolvedType, flags, userId)); 7183 } finally { 7184 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 7185 } 7186 } 7187 7188 /** 7189 * Returns the package name of the calling Uid if it's an instant app. If it isn't 7190 * instant, returns {@code null}. 7191 */ 7192 private String getInstantAppPackageName(int callingUid) { 7193 synchronized (mPackages) { 7194 // If the caller is an isolated app use the owner's uid for the lookup. 7195 if (Process.isIsolated(callingUid)) { 7196 callingUid = mIsolatedOwners.get(callingUid); 7197 } 7198 final int appId = UserHandle.getAppId(callingUid); 7199 final Object obj = mSettings.getUserIdLPr(appId); 7200 if (obj instanceof PackageSetting) { 7201 final PackageSetting ps = (PackageSetting) obj; 7202 final boolean isInstantApp = ps.getInstantApp(UserHandle.getUserId(callingUid)); 7203 return isInstantApp ? ps.pkg.packageName : null; 7204 } 7205 } 7206 return null; 7207 } 7208 7209 private @NonNull List<ResolveInfo> queryIntentActivitiesInternal(Intent intent, 7210 String resolvedType, int flags, int userId) { 7211 return queryIntentActivitiesInternal( 7212 intent, resolvedType, flags, Binder.getCallingUid(), userId, 7213 false /*resolveForStart*/, true /*allowDynamicSplits*/); 7214 } 7215 7216 private @NonNull List<ResolveInfo> queryIntentActivitiesInternal(Intent intent, 7217 String resolvedType, int flags, int filterCallingUid, int userId, 7218 boolean resolveForStart, boolean allowDynamicSplits) { 7219 if (!sUserManager.exists(userId)) return Collections.emptyList(); 7220 final String instantAppPkgName = getInstantAppPackageName(filterCallingUid); 7221 enforceCrossUserPermission(Binder.getCallingUid(), userId, 7222 false /* requireFullPermission */, false /* checkShell */, 7223 "query intent activities"); 7224 final String pkgName = intent.getPackage(); 7225 ComponentName comp = intent.getComponent(); 7226 if (comp == null) { 7227 if (intent.getSelector() != null) { 7228 intent = intent.getSelector(); 7229 comp = intent.getComponent(); 7230 } 7231 } 7232 7233 flags = updateFlagsForResolve(flags, userId, intent, filterCallingUid, resolveForStart, 7234 comp != null || pkgName != null /*onlyExposedExplicitly*/); 7235 if (comp != null) { 7236 final List<ResolveInfo> list = new ArrayList<ResolveInfo>(1); 7237 final ActivityInfo ai = getActivityInfo(comp, flags, userId); 7238 if (ai != null) { 7239 // When specifying an explicit component, we prevent the activity from being 7240 // used when either 1) the calling package is normal and the activity is within 7241 // an ephemeral application or 2) the calling package is ephemeral and the 7242 // activity is not visible to ephemeral applications. 7243 final boolean matchInstantApp = 7244 (flags & PackageManager.MATCH_INSTANT) != 0; 7245 final boolean matchVisibleToInstantAppOnly = 7246 (flags & PackageManager.MATCH_VISIBLE_TO_INSTANT_APP_ONLY) != 0; 7247 final boolean matchExplicitlyVisibleOnly = 7248 (flags & PackageManager.MATCH_EXPLICITLY_VISIBLE_ONLY) != 0; 7249 final boolean isCallerInstantApp = 7250 instantAppPkgName != null; 7251 final boolean isTargetSameInstantApp = 7252 comp.getPackageName().equals(instantAppPkgName); 7253 final boolean isTargetInstantApp = 7254 (ai.applicationInfo.privateFlags 7255 & ApplicationInfo.PRIVATE_FLAG_INSTANT) != 0; 7256 final boolean isTargetVisibleToInstantApp = 7257 (ai.flags & ActivityInfo.FLAG_VISIBLE_TO_INSTANT_APP) != 0; 7258 final boolean isTargetExplicitlyVisibleToInstantApp = 7259 isTargetVisibleToInstantApp 7260 && (ai.flags & ActivityInfo.FLAG_IMPLICITLY_VISIBLE_TO_INSTANT_APP) == 0; 7261 final boolean isTargetHiddenFromInstantApp = 7262 !isTargetVisibleToInstantApp 7263 || (matchExplicitlyVisibleOnly && !isTargetExplicitlyVisibleToInstantApp); 7264 final boolean blockResolution = 7265 !isTargetSameInstantApp 7266 && ((!matchInstantApp && !isCallerInstantApp && isTargetInstantApp) 7267 || (matchVisibleToInstantAppOnly && isCallerInstantApp 7268 && isTargetHiddenFromInstantApp)); 7269 if (!blockResolution) { 7270 final ResolveInfo ri = new ResolveInfo(); 7271 ri.activityInfo = ai; 7272 list.add(ri); 7273 } 7274 } 7275 return applyPostResolutionFilter( 7276 list, instantAppPkgName, allowDynamicSplits, filterCallingUid, userId); 7277 } 7278 7279 // reader 7280 boolean sortResult = false; 7281 boolean addEphemeral = false; 7282 List<ResolveInfo> result; 7283 final boolean ephemeralDisabled = isEphemeralDisabled(); 7284 synchronized (mPackages) { 7285 if (pkgName == null) { 7286 List<CrossProfileIntentFilter> matchingFilters = 7287 getMatchingCrossProfileIntentFilters(intent, resolvedType, userId); 7288 // Check for results that need to skip the current profile. 7289 ResolveInfo xpResolveInfo = querySkipCurrentProfileIntents(matchingFilters, intent, 7290 resolvedType, flags, userId); 7291 if (xpResolveInfo != null) { 7292 List<ResolveInfo> xpResult = new ArrayList<ResolveInfo>(1); 7293 xpResult.add(xpResolveInfo); 7294 return applyPostResolutionFilter( 7295 filterIfNotSystemUser(xpResult, userId), instantAppPkgName, 7296 allowDynamicSplits, filterCallingUid, userId); 7297 } 7298 7299 // Check for results in the current profile. 7300 result = filterIfNotSystemUser(mActivities.queryIntent( 7301 intent, resolvedType, flags, userId), userId); 7302 addEphemeral = !ephemeralDisabled 7303 && isInstantAppAllowed(intent, result, userId, false /*skipPackageCheck*/); 7304 // Check for cross profile results. 7305 boolean hasNonNegativePriorityResult = hasNonNegativePriority(result); 7306 xpResolveInfo = queryCrossProfileIntents( 7307 matchingFilters, intent, resolvedType, flags, userId, 7308 hasNonNegativePriorityResult); 7309 if (xpResolveInfo != null && isUserEnabled(xpResolveInfo.targetUserId)) { 7310 boolean isVisibleToUser = filterIfNotSystemUser( 7311 Collections.singletonList(xpResolveInfo), userId).size() > 0; 7312 if (isVisibleToUser) { 7313 result.add(xpResolveInfo); 7314 sortResult = true; 7315 } 7316 } 7317 if (hasWebURI(intent)) { 7318 CrossProfileDomainInfo xpDomainInfo = null; 7319 final UserInfo parent = getProfileParent(userId); 7320 if (parent != null) { 7321 xpDomainInfo = getCrossProfileDomainPreferredLpr(intent, resolvedType, 7322 flags, userId, parent.id); 7323 } 7324 if (xpDomainInfo != null) { 7325 if (xpResolveInfo != null) { 7326 // If we didn't remove it, the cross-profile ResolveInfo would be twice 7327 // in the result. 7328 result.remove(xpResolveInfo); 7329 } 7330 if (result.size() == 0 && !addEphemeral) { 7331 // No result in current profile, but found candidate in parent user. 7332 // And we are not going to add emphemeral app, so we can return the 7333 // result straight away. 7334 result.add(xpDomainInfo.resolveInfo); 7335 return applyPostResolutionFilter(result, instantAppPkgName, 7336 allowDynamicSplits, filterCallingUid, userId); 7337 } 7338 } else if (result.size() <= 1 && !addEphemeral) { 7339 // No result in parent user and <= 1 result in current profile, and we 7340 // are not going to add emphemeral app, so we can return the result without 7341 // further processing. 7342 return applyPostResolutionFilter(result, instantAppPkgName, 7343 allowDynamicSplits, filterCallingUid, userId); 7344 } 7345 // We have more than one candidate (combining results from current and parent 7346 // profile), so we need filtering and sorting. 7347 result = filterCandidatesWithDomainPreferredActivitiesLPr( 7348 intent, flags, result, xpDomainInfo, userId); 7349 sortResult = true; 7350 } 7351 } else { 7352 final PackageParser.Package pkg = mPackages.get(pkgName); 7353 result = null; 7354 if (pkg != null) { 7355 result = filterIfNotSystemUser( 7356 mActivities.queryIntentForPackage( 7357 intent, resolvedType, flags, pkg.activities, userId), 7358 userId); 7359 } 7360 if (result == null || result.size() == 0) { 7361 // the caller wants to resolve for a particular package; however, there 7362 // were no installed results, so, try to find an ephemeral result 7363 addEphemeral = !ephemeralDisabled 7364 && isInstantAppAllowed( 7365 intent, null /*result*/, userId, true /*skipPackageCheck*/); 7366 if (result == null) { 7367 result = new ArrayList<>(); 7368 } 7369 } 7370 } 7371 } 7372 if (addEphemeral) { 7373 result = maybeAddInstantAppInstaller( 7374 result, intent, resolvedType, flags, userId, resolveForStart); 7375 } 7376 if (sortResult) { 7377 Collections.sort(result, mResolvePrioritySorter); 7378 } 7379 return applyPostResolutionFilter( 7380 result, instantAppPkgName, allowDynamicSplits, filterCallingUid, userId); 7381 } 7382 7383 private List<ResolveInfo> maybeAddInstantAppInstaller(List<ResolveInfo> result, Intent intent, 7384 String resolvedType, int flags, int userId, boolean resolveForStart) { 7385 // first, check to see if we've got an instant app already installed 7386 final boolean alreadyResolvedLocally = (flags & PackageManager.MATCH_INSTANT) != 0; 7387 ResolveInfo localInstantApp = null; 7388 boolean blockResolution = false; 7389 if (!alreadyResolvedLocally) { 7390 final List<ResolveInfo> instantApps = mActivities.queryIntent(intent, resolvedType, 7391 flags 7392 | PackageManager.GET_RESOLVED_FILTER 7393 | PackageManager.MATCH_INSTANT 7394 | PackageManager.MATCH_VISIBLE_TO_INSTANT_APP_ONLY, 7395 userId); 7396 for (int i = instantApps.size() - 1; i >= 0; --i) { 7397 final ResolveInfo info = instantApps.get(i); 7398 final String packageName = info.activityInfo.packageName; 7399 final PackageSetting ps = mSettings.mPackages.get(packageName); 7400 if (ps.getInstantApp(userId)) { 7401 final long packedStatus = getDomainVerificationStatusLPr(ps, userId); 7402 final int status = (int)(packedStatus >> 32); 7403 final int linkGeneration = (int)(packedStatus & 0xFFFFFFFF); 7404 if (status == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_NEVER) { 7405 // there's a local instant application installed, but, the user has 7406 // chosen to never use it; skip resolution and don't acknowledge 7407 // an instant application is even available 7408 if (DEBUG_EPHEMERAL) { 7409 Slog.v(TAG, "Instant app marked to never run; pkg: " + packageName); 7410 } 7411 blockResolution = true; 7412 break; 7413 } else { 7414 // we have a locally installed instant application; skip resolution 7415 // but acknowledge there's an instant application available 7416 if (DEBUG_EPHEMERAL) { 7417 Slog.v(TAG, "Found installed instant app; pkg: " + packageName); 7418 } 7419 localInstantApp = info; 7420 break; 7421 } 7422 } 7423 } 7424 } 7425 // no app installed, let's see if one's available 7426 AuxiliaryResolveInfo auxiliaryResponse = null; 7427 if (!blockResolution) { 7428 if (localInstantApp == null) { 7429 // we don't have an instant app locally, resolve externally 7430 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "resolveEphemeral"); 7431 final InstantAppRequest requestObject = new InstantAppRequest( 7432 null /*responseObj*/, intent /*origIntent*/, resolvedType, 7433 null /*callingPackage*/, userId, null /*verificationBundle*/, 7434 resolveForStart); 7435 auxiliaryResponse = 7436 InstantAppResolver.doInstantAppResolutionPhaseOne( 7437 mContext, mInstantAppResolverConnection, requestObject); 7438 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 7439 } else { 7440 // we have an instant application locally, but, we can't admit that since 7441 // callers shouldn't be able to determine prior browsing. create a dummy 7442 // auxiliary response so the downstream code behaves as if there's an 7443 // instant application available externally. when it comes time to start 7444 // the instant application, we'll do the right thing. 7445 final ApplicationInfo ai = localInstantApp.activityInfo.applicationInfo; 7446 auxiliaryResponse = new AuxiliaryResolveInfo( 7447 ai.packageName, null /*splitName*/, null /*failureActivity*/, 7448 ai.versionCode, null /*failureIntent*/); 7449 } 7450 } 7451 if (auxiliaryResponse != null) { 7452 if (DEBUG_EPHEMERAL) { 7453 Slog.v(TAG, "Adding ephemeral installer to the ResolveInfo list"); 7454 } 7455 final ResolveInfo ephemeralInstaller = new ResolveInfo(mInstantAppInstallerInfo); 7456 final PackageSetting ps = 7457 mSettings.mPackages.get(mInstantAppInstallerActivity.packageName); 7458 if (ps != null) { 7459 ephemeralInstaller.activityInfo = PackageParser.generateActivityInfo( 7460 mInstantAppInstallerActivity, 0, ps.readUserState(userId), userId); 7461 ephemeralInstaller.activityInfo.launchToken = auxiliaryResponse.token; 7462 ephemeralInstaller.auxiliaryInfo = auxiliaryResponse; 7463 // make sure this resolver is the default 7464 ephemeralInstaller.isDefault = true; 7465 ephemeralInstaller.match = IntentFilter.MATCH_CATEGORY_SCHEME_SPECIFIC_PART 7466 | IntentFilter.MATCH_ADJUSTMENT_NORMAL; 7467 // add a non-generic filter 7468 ephemeralInstaller.filter = new IntentFilter(intent.getAction()); 7469 ephemeralInstaller.filter.addDataPath( 7470 intent.getData().getPath(), PatternMatcher.PATTERN_LITERAL); 7471 ephemeralInstaller.isInstantAppAvailable = true; 7472 result.add(ephemeralInstaller); 7473 } 7474 } 7475 return result; 7476 } 7477 7478 private static class CrossProfileDomainInfo { 7479 /* ResolveInfo for IntentForwarderActivity to send the intent to the other profile */ 7480 ResolveInfo resolveInfo; 7481 /* Best domain verification status of the activities found in the other profile */ 7482 int bestDomainVerificationStatus; 7483 } 7484 7485 private CrossProfileDomainInfo getCrossProfileDomainPreferredLpr(Intent intent, 7486 String resolvedType, int flags, int sourceUserId, int parentUserId) { 7487 if (!sUserManager.hasUserRestriction(UserManager.ALLOW_PARENT_PROFILE_APP_LINKING, 7488 sourceUserId)) { 7489 return null; 7490 } 7491 List<ResolveInfo> resultTargetUser = mActivities.queryIntent(intent, 7492 resolvedType, flags, parentUserId); 7493 7494 if (resultTargetUser == null || resultTargetUser.isEmpty()) { 7495 return null; 7496 } 7497 CrossProfileDomainInfo result = null; 7498 int size = resultTargetUser.size(); 7499 for (int i = 0; i < size; i++) { 7500 ResolveInfo riTargetUser = resultTargetUser.get(i); 7501 // Intent filter verification is only for filters that specify a host. So don't return 7502 // those that handle all web uris. 7503 if (riTargetUser.handleAllWebDataURI) { 7504 continue; 7505 } 7506 String packageName = riTargetUser.activityInfo.packageName; 7507 PackageSetting ps = mSettings.mPackages.get(packageName); 7508 if (ps == null) { 7509 continue; 7510 } 7511 long verificationState = getDomainVerificationStatusLPr(ps, parentUserId); 7512 int status = (int)(verificationState >> 32); 7513 if (result == null) { 7514 result = new CrossProfileDomainInfo(); 7515 result.resolveInfo = createForwardingResolveInfoUnchecked(new IntentFilter(), 7516 sourceUserId, parentUserId); 7517 result.bestDomainVerificationStatus = status; 7518 } else { 7519 result.bestDomainVerificationStatus = bestDomainVerificationStatus(status, 7520 result.bestDomainVerificationStatus); 7521 } 7522 } 7523 // Don't consider matches with status NEVER across profiles. 7524 if (result != null && result.bestDomainVerificationStatus 7525 == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_NEVER) { 7526 return null; 7527 } 7528 return result; 7529 } 7530 7531 /** 7532 * Verification statuses are ordered from the worse to the best, except for 7533 * INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_NEVER, which is the worse. 7534 */ 7535 private int bestDomainVerificationStatus(int status1, int status2) { 7536 if (status1 == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_NEVER) { 7537 return status2; 7538 } 7539 if (status2 == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_NEVER) { 7540 return status1; 7541 } 7542 return (int) MathUtils.max(status1, status2); 7543 } 7544 7545 private boolean isUserEnabled(int userId) { 7546 long callingId = Binder.clearCallingIdentity(); 7547 try { 7548 UserInfo userInfo = sUserManager.getUserInfo(userId); 7549 return userInfo != null && userInfo.isEnabled(); 7550 } finally { 7551 Binder.restoreCallingIdentity(callingId); 7552 } 7553 } 7554 7555 /** 7556 * Filter out activities with systemUserOnly flag set, when current user is not System. 7557 * 7558 * @return filtered list 7559 */ 7560 private List<ResolveInfo> filterIfNotSystemUser(List<ResolveInfo> resolveInfos, int userId) { 7561 if (userId == UserHandle.USER_SYSTEM) { 7562 return resolveInfos; 7563 } 7564 for (int i = resolveInfos.size() - 1; i >= 0; i--) { 7565 ResolveInfo info = resolveInfos.get(i); 7566 if ((info.activityInfo.flags & ActivityInfo.FLAG_SYSTEM_USER_ONLY) != 0) { 7567 resolveInfos.remove(i); 7568 } 7569 } 7570 return resolveInfos; 7571 } 7572 7573 /** 7574 * Filters out ephemeral activities. 7575 * <p>When resolving for an ephemeral app, only activities that 1) are defined in the 7576 * ephemeral app or 2) marked with {@code visibleToEphemeral} are returned. 7577 * 7578 * @param resolveInfos The pre-filtered list of resolved activities 7579 * @param ephemeralPkgName The ephemeral package name. If {@code null}, no filtering 7580 * is performed. 7581 * @return A filtered list of resolved activities. 7582 */ 7583 private List<ResolveInfo> applyPostResolutionFilter(List<ResolveInfo> resolveInfos, 7584 String ephemeralPkgName, boolean allowDynamicSplits, int filterCallingUid, int userId) { 7585 for (int i = resolveInfos.size() - 1; i >= 0; i--) { 7586 final ResolveInfo info = resolveInfos.get(i); 7587 // allow activities that are defined in the provided package 7588 if (allowDynamicSplits 7589 && info.activityInfo.splitName != null 7590 && !ArrayUtils.contains(info.activityInfo.applicationInfo.splitNames, 7591 info.activityInfo.splitName)) { 7592 if (mInstantAppInstallerInfo == null) { 7593 if (DEBUG_INSTALL) { 7594 Slog.v(TAG, "No installer - not adding it to the ResolveInfo list"); 7595 } 7596 resolveInfos.remove(i); 7597 continue; 7598 } 7599 // requested activity is defined in a split that hasn't been installed yet. 7600 // add the installer to the resolve list 7601 if (DEBUG_INSTALL) { 7602 Slog.v(TAG, "Adding installer to the ResolveInfo list"); 7603 } 7604 final ResolveInfo installerInfo = new ResolveInfo(mInstantAppInstallerInfo); 7605 final ComponentName installFailureActivity = findInstallFailureActivity( 7606 info.activityInfo.packageName, filterCallingUid, userId); 7607 installerInfo.auxiliaryInfo = new AuxiliaryResolveInfo( 7608 info.activityInfo.packageName, info.activityInfo.splitName, 7609 installFailureActivity, 7610 info.activityInfo.applicationInfo.versionCode, 7611 null /*failureIntent*/); 7612 installerInfo.match = IntentFilter.MATCH_CATEGORY_SCHEME_SPECIFIC_PART 7613 | IntentFilter.MATCH_ADJUSTMENT_NORMAL; 7614 // add a non-generic filter 7615 installerInfo.filter = new IntentFilter(); 7616 7617 // This resolve info may appear in the chooser UI, so let us make it 7618 // look as the one it replaces as far as the user is concerned which 7619 // requires loading the correct label and icon for the resolve info. 7620 installerInfo.resolvePackageName = info.getComponentInfo().packageName; 7621 installerInfo.labelRes = info.resolveLabelResId(); 7622 installerInfo.icon = info.resolveIconResId(); 7623 7624 // propagate priority/preferred order/default 7625 installerInfo.priority = info.priority; 7626 installerInfo.preferredOrder = info.preferredOrder; 7627 installerInfo.isDefault = info.isDefault; 7628 resolveInfos.set(i, installerInfo); 7629 continue; 7630 } 7631 // caller is a full app, don't need to apply any other filtering 7632 if (ephemeralPkgName == null) { 7633 continue; 7634 } else if (ephemeralPkgName.equals(info.activityInfo.packageName)) { 7635 // caller is same app; don't need to apply any other filtering 7636 continue; 7637 } 7638 // allow activities that have been explicitly exposed to ephemeral apps 7639 final boolean isEphemeralApp = info.activityInfo.applicationInfo.isInstantApp(); 7640 if (!isEphemeralApp 7641 && ((info.activityInfo.flags & ActivityInfo.FLAG_VISIBLE_TO_INSTANT_APP) != 0)) { 7642 continue; 7643 } 7644 resolveInfos.remove(i); 7645 } 7646 return resolveInfos; 7647 } 7648 7649 /** 7650 * Returns the activity component that can handle install failures. 7651 * <p>By default, the instant application installer handles failures. However, an 7652 * application may want to handle failures on its own. Applications do this by 7653 * creating an activity with an intent filter that handles the action 7654 * {@link Intent#ACTION_INSTALL_FAILURE}. 7655 */ 7656 private @Nullable ComponentName findInstallFailureActivity( 7657 String packageName, int filterCallingUid, int userId) { 7658 final Intent failureActivityIntent = new Intent(Intent.ACTION_INSTALL_FAILURE); 7659 failureActivityIntent.setPackage(packageName); 7660 // IMPORTANT: disallow dynamic splits to avoid an infinite loop 7661 final List<ResolveInfo> result = queryIntentActivitiesInternal( 7662 failureActivityIntent, null /*resolvedType*/, 0 /*flags*/, filterCallingUid, userId, 7663 false /*resolveForStart*/, false /*allowDynamicSplits*/); 7664 final int NR = result.size(); 7665 if (NR > 0) { 7666 for (int i = 0; i < NR; i++) { 7667 final ResolveInfo info = result.get(i); 7668 if (info.activityInfo.splitName != null) { 7669 continue; 7670 } 7671 return new ComponentName(packageName, info.activityInfo.name); 7672 } 7673 } 7674 return null; 7675 } 7676 7677 /** 7678 * @param resolveInfos list of resolve infos in descending priority order 7679 * @return if the list contains a resolve info with non-negative priority 7680 */ 7681 private boolean hasNonNegativePriority(List<ResolveInfo> resolveInfos) { 7682 return resolveInfos.size() > 0 && resolveInfos.get(0).priority >= 0; 7683 } 7684 7685 private static boolean hasWebURI(Intent intent) { 7686 if (intent.getData() == null) { 7687 return false; 7688 } 7689 final String scheme = intent.getScheme(); 7690 if (TextUtils.isEmpty(scheme)) { 7691 return false; 7692 } 7693 return scheme.equals(IntentFilter.SCHEME_HTTP) || scheme.equals(IntentFilter.SCHEME_HTTPS); 7694 } 7695 7696 private List<ResolveInfo> filterCandidatesWithDomainPreferredActivitiesLPr(Intent intent, 7697 int matchFlags, List<ResolveInfo> candidates, CrossProfileDomainInfo xpDomainInfo, 7698 int userId) { 7699 final boolean debug = (intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0; 7700 7701 if (DEBUG_PREFERRED || DEBUG_DOMAIN_VERIFICATION) { 7702 Slog.v(TAG, "Filtering results with preferred activities. Candidates count: " + 7703 candidates.size()); 7704 } 7705 7706 ArrayList<ResolveInfo> result = new ArrayList<ResolveInfo>(); 7707 ArrayList<ResolveInfo> alwaysList = new ArrayList<ResolveInfo>(); 7708 ArrayList<ResolveInfo> undefinedList = new ArrayList<ResolveInfo>(); 7709 ArrayList<ResolveInfo> alwaysAskList = new ArrayList<ResolveInfo>(); 7710 ArrayList<ResolveInfo> neverList = new ArrayList<ResolveInfo>(); 7711 ArrayList<ResolveInfo> matchAllList = new ArrayList<ResolveInfo>(); 7712 7713 synchronized (mPackages) { 7714 final int count = candidates.size(); 7715 // First, try to use linked apps. Partition the candidates into four lists: 7716 // one for the final results, one for the "do not use ever", one for "undefined status" 7717 // and finally one for "browser app type". 7718 for (int n=0; n<count; n++) { 7719 ResolveInfo info = candidates.get(n); 7720 String packageName = info.activityInfo.packageName; 7721 PackageSetting ps = mSettings.mPackages.get(packageName); 7722 if (ps != null) { 7723 // Add to the special match all list (Browser use case) 7724 if (info.handleAllWebDataURI) { 7725 matchAllList.add(info); 7726 continue; 7727 } 7728 // Try to get the status from User settings first 7729 long packedStatus = getDomainVerificationStatusLPr(ps, userId); 7730 int status = (int)(packedStatus >> 32); 7731 int linkGeneration = (int)(packedStatus & 0xFFFFFFFF); 7732 if (status == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS) { 7733 if (DEBUG_DOMAIN_VERIFICATION || debug) { 7734 Slog.i(TAG, " + always: " + info.activityInfo.packageName 7735 + " : linkgen=" + linkGeneration); 7736 } 7737 // Use link-enabled generation as preferredOrder, i.e. 7738 // prefer newly-enabled over earlier-enabled. 7739 info.preferredOrder = linkGeneration; 7740 alwaysList.add(info); 7741 } else if (status == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_NEVER) { 7742 if (DEBUG_DOMAIN_VERIFICATION || debug) { 7743 Slog.i(TAG, " + never: " + info.activityInfo.packageName); 7744 } 7745 neverList.add(info); 7746 } else if (status == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS_ASK) { 7747 if (DEBUG_DOMAIN_VERIFICATION || debug) { 7748 Slog.i(TAG, " + always-ask: " + info.activityInfo.packageName); 7749 } 7750 alwaysAskList.add(info); 7751 } else if (status == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED || 7752 status == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ASK) { 7753 if (DEBUG_DOMAIN_VERIFICATION || debug) { 7754 Slog.i(TAG, " + ask: " + info.activityInfo.packageName); 7755 } 7756 undefinedList.add(info); 7757 } 7758 } 7759 } 7760 7761 // We'll want to include browser possibilities in a few cases 7762 boolean includeBrowser = false; 7763 7764 // First try to add the "always" resolution(s) for the current user, if any 7765 if (alwaysList.size() > 0) { 7766 result.addAll(alwaysList); 7767 } else { 7768 // Add all undefined apps as we want them to appear in the disambiguation dialog. 7769 result.addAll(undefinedList); 7770 // Maybe add one for the other profile. 7771 if (xpDomainInfo != null && ( 7772 xpDomainInfo.bestDomainVerificationStatus 7773 != INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_NEVER)) { 7774 result.add(xpDomainInfo.resolveInfo); 7775 } 7776 includeBrowser = true; 7777 } 7778 7779 // The presence of any 'always ask' alternatives means we'll also offer browsers. 7780 // If there were 'always' entries their preferred order has been set, so we also 7781 // back that off to make the alternatives equivalent 7782 if (alwaysAskList.size() > 0) { 7783 for (ResolveInfo i : result) { 7784 i.preferredOrder = 0; 7785 } 7786 result.addAll(alwaysAskList); 7787 includeBrowser = true; 7788 } 7789 7790 if (includeBrowser) { 7791 // Also add browsers (all of them or only the default one) 7792 if (DEBUG_DOMAIN_VERIFICATION) { 7793 Slog.v(TAG, " ...including browsers in candidate set"); 7794 } 7795 if ((matchFlags & MATCH_ALL) != 0) { 7796 result.addAll(matchAllList); 7797 } else { 7798 // Browser/generic handling case. If there's a default browser, go straight 7799 // to that (but only if there is no other higher-priority match). 7800 final String defaultBrowserPackageName = getDefaultBrowserPackageName(userId); 7801 int maxMatchPrio = 0; 7802 ResolveInfo defaultBrowserMatch = null; 7803 final int numCandidates = matchAllList.size(); 7804 for (int n = 0; n < numCandidates; n++) { 7805 ResolveInfo info = matchAllList.get(n); 7806 // track the highest overall match priority... 7807 if (info.priority > maxMatchPrio) { 7808 maxMatchPrio = info.priority; 7809 } 7810 // ...and the highest-priority default browser match 7811 if (info.activityInfo.packageName.equals(defaultBrowserPackageName)) { 7812 if (defaultBrowserMatch == null 7813 || (defaultBrowserMatch.priority < info.priority)) { 7814 if (debug) { 7815 Slog.v(TAG, "Considering default browser match " + info); 7816 } 7817 defaultBrowserMatch = info; 7818 } 7819 } 7820 } 7821 if (defaultBrowserMatch != null 7822 && defaultBrowserMatch.priority >= maxMatchPrio 7823 && !TextUtils.isEmpty(defaultBrowserPackageName)) 7824 { 7825 if (debug) { 7826 Slog.v(TAG, "Default browser match " + defaultBrowserMatch); 7827 } 7828 result.add(defaultBrowserMatch); 7829 } else { 7830 result.addAll(matchAllList); 7831 } 7832 } 7833 7834 // If there is nothing selected, add all candidates and remove the ones that the user 7835 // has explicitly put into the INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_NEVER state 7836 if (result.size() == 0) { 7837 result.addAll(candidates); 7838 result.removeAll(neverList); 7839 } 7840 } 7841 } 7842 if (DEBUG_PREFERRED || DEBUG_DOMAIN_VERIFICATION) { 7843 Slog.v(TAG, "Filtered results with preferred activities. New candidates count: " + 7844 result.size()); 7845 for (ResolveInfo info : result) { 7846 Slog.v(TAG, " + " + info.activityInfo); 7847 } 7848 } 7849 return result; 7850 } 7851 7852 // Returns a packed value as a long: 7853 // 7854 // high 'int'-sized word: link status: undefined/ask/never/always. 7855 // low 'int'-sized word: relative priority among 'always' results. 7856 private long getDomainVerificationStatusLPr(PackageSetting ps, int userId) { 7857 long result = ps.getDomainVerificationStatusForUser(userId); 7858 // if none available, get the master status 7859 if (result >> 32 == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED) { 7860 if (ps.getIntentFilterVerificationInfo() != null) { 7861 result = ((long)ps.getIntentFilterVerificationInfo().getStatus()) << 32; 7862 } 7863 } 7864 return result; 7865 } 7866 7867 private ResolveInfo querySkipCurrentProfileIntents( 7868 List<CrossProfileIntentFilter> matchingFilters, Intent intent, String resolvedType, 7869 int flags, int sourceUserId) { 7870 if (matchingFilters != null) { 7871 int size = matchingFilters.size(); 7872 for (int i = 0; i < size; i ++) { 7873 CrossProfileIntentFilter filter = matchingFilters.get(i); 7874 if ((filter.getFlags() & PackageManager.SKIP_CURRENT_PROFILE) != 0) { 7875 // Checking if there are activities in the target user that can handle the 7876 // intent. 7877 ResolveInfo resolveInfo = createForwardingResolveInfo(filter, intent, 7878 resolvedType, flags, sourceUserId); 7879 if (resolveInfo != null) { 7880 return resolveInfo; 7881 } 7882 } 7883 } 7884 } 7885 return null; 7886 } 7887 7888 // Return matching ResolveInfo in target user if any. 7889 private ResolveInfo queryCrossProfileIntents( 7890 List<CrossProfileIntentFilter> matchingFilters, Intent intent, String resolvedType, 7891 int flags, int sourceUserId, boolean matchInCurrentProfile) { 7892 if (matchingFilters != null) { 7893 // Two {@link CrossProfileIntentFilter}s can have the same targetUserId and 7894 // match the same intent. For performance reasons, it is better not to 7895 // run queryIntent twice for the same userId 7896 SparseBooleanArray alreadyTriedUserIds = new SparseBooleanArray(); 7897 int size = matchingFilters.size(); 7898 for (int i = 0; i < size; i++) { 7899 CrossProfileIntentFilter filter = matchingFilters.get(i); 7900 int targetUserId = filter.getTargetUserId(); 7901 boolean skipCurrentProfile = 7902 (filter.getFlags() & PackageManager.SKIP_CURRENT_PROFILE) != 0; 7903 boolean skipCurrentProfileIfNoMatchFound = 7904 (filter.getFlags() & PackageManager.ONLY_IF_NO_MATCH_FOUND) != 0; 7905 if (!skipCurrentProfile && !alreadyTriedUserIds.get(targetUserId) 7906 && (!skipCurrentProfileIfNoMatchFound || !matchInCurrentProfile)) { 7907 // Checking if there are activities in the target user that can handle the 7908 // intent. 7909 ResolveInfo resolveInfo = createForwardingResolveInfo(filter, intent, 7910 resolvedType, flags, sourceUserId); 7911 if (resolveInfo != null) return resolveInfo; 7912 alreadyTriedUserIds.put(targetUserId, true); 7913 } 7914 } 7915 } 7916 return null; 7917 } 7918 7919 /** 7920 * If the filter's target user can handle the intent and is enabled: returns a ResolveInfo that 7921 * will forward the intent to the filter's target user. 7922 * Otherwise, returns null. 7923 */ 7924 private ResolveInfo createForwardingResolveInfo(CrossProfileIntentFilter filter, Intent intent, 7925 String resolvedType, int flags, int sourceUserId) { 7926 int targetUserId = filter.getTargetUserId(); 7927 List<ResolveInfo> resultTargetUser = mActivities.queryIntent(intent, 7928 resolvedType, flags, targetUserId); 7929 if (resultTargetUser != null && isUserEnabled(targetUserId)) { 7930 // If all the matches in the target profile are suspended, return null. 7931 for (int i = resultTargetUser.size() - 1; i >= 0; i--) { 7932 if ((resultTargetUser.get(i).activityInfo.applicationInfo.flags 7933 & ApplicationInfo.FLAG_SUSPENDED) == 0) { 7934 return createForwardingResolveInfoUnchecked(filter, sourceUserId, 7935 targetUserId); 7936 } 7937 } 7938 } 7939 return null; 7940 } 7941 7942 private ResolveInfo createForwardingResolveInfoUnchecked(IntentFilter filter, 7943 int sourceUserId, int targetUserId) { 7944 ResolveInfo forwardingResolveInfo = new ResolveInfo(); 7945 long ident = Binder.clearCallingIdentity(); 7946 boolean targetIsProfile; 7947 try { 7948 targetIsProfile = sUserManager.getUserInfo(targetUserId).isManagedProfile(); 7949 } finally { 7950 Binder.restoreCallingIdentity(ident); 7951 } 7952 String className; 7953 if (targetIsProfile) { 7954 className = FORWARD_INTENT_TO_MANAGED_PROFILE; 7955 } else { 7956 className = FORWARD_INTENT_TO_PARENT; 7957 } 7958 ComponentName forwardingActivityComponentName = new ComponentName( 7959 mAndroidApplication.packageName, className); 7960 ActivityInfo forwardingActivityInfo = getActivityInfo(forwardingActivityComponentName, 0, 7961 sourceUserId); 7962 if (!targetIsProfile) { 7963 forwardingActivityInfo.showUserIcon = targetUserId; 7964 forwardingResolveInfo.noResourceId = true; 7965 } 7966 forwardingResolveInfo.activityInfo = forwardingActivityInfo; 7967 forwardingResolveInfo.priority = 0; 7968 forwardingResolveInfo.preferredOrder = 0; 7969 forwardingResolveInfo.match = 0; 7970 forwardingResolveInfo.isDefault = true; 7971 forwardingResolveInfo.filter = filter; 7972 forwardingResolveInfo.targetUserId = targetUserId; 7973 return forwardingResolveInfo; 7974 } 7975 7976 @Override 7977 public @NonNull ParceledListSlice<ResolveInfo> queryIntentActivityOptions(ComponentName caller, 7978 Intent[] specifics, String[] specificTypes, Intent intent, 7979 String resolvedType, int flags, int userId) { 7980 return new ParceledListSlice<>(queryIntentActivityOptionsInternal(caller, specifics, 7981 specificTypes, intent, resolvedType, flags, userId)); 7982 } 7983 7984 private @NonNull List<ResolveInfo> queryIntentActivityOptionsInternal(ComponentName caller, 7985 Intent[] specifics, String[] specificTypes, Intent intent, 7986 String resolvedType, int flags, int userId) { 7987 if (!sUserManager.exists(userId)) return Collections.emptyList(); 7988 final int callingUid = Binder.getCallingUid(); 7989 flags = updateFlagsForResolve(flags, userId, intent, callingUid, 7990 false /*includeInstantApps*/); 7991 enforceCrossUserPermission(callingUid, userId, 7992 false /*requireFullPermission*/, false /*checkShell*/, 7993 "query intent activity options"); 7994 final String resultsAction = intent.getAction(); 7995 7996 final List<ResolveInfo> results = queryIntentActivitiesInternal(intent, resolvedType, flags 7997 | PackageManager.GET_RESOLVED_FILTER, userId); 7998 7999 if (DEBUG_INTENT_MATCHING) { 8000 Log.v(TAG, "Query " + intent + ": " + results); 8001 } 8002 8003 int specificsPos = 0; 8004 int N; 8005 8006 // todo: note that the algorithm used here is O(N^2). This 8007 // isn't a problem in our current environment, but if we start running 8008 // into situations where we have more than 5 or 10 matches then this 8009 // should probably be changed to something smarter... 8010 8011 // First we go through and resolve each of the specific items 8012 // that were supplied, taking care of removing any corresponding 8013 // duplicate items in the generic resolve list. 8014 if (specifics != null) { 8015 for (int i=0; i<specifics.length; i++) { 8016 final Intent sintent = specifics[i]; 8017 if (sintent == null) { 8018 continue; 8019 } 8020 8021 if (DEBUG_INTENT_MATCHING) { 8022 Log.v(TAG, "Specific #" + i + ": " + sintent); 8023 } 8024 8025 String action = sintent.getAction(); 8026 if (resultsAction != null && resultsAction.equals(action)) { 8027 // If this action was explicitly requested, then don't 8028 // remove things that have it. 8029 action = null; 8030 } 8031 8032 ResolveInfo ri = null; 8033 ActivityInfo ai = null; 8034 8035 ComponentName comp = sintent.getComponent(); 8036 if (comp == null) { 8037 ri = resolveIntent( 8038 sintent, 8039 specificTypes != null ? specificTypes[i] : null, 8040 flags, userId); 8041 if (ri == null) { 8042 continue; 8043 } 8044 if (ri == mResolveInfo) { 8045 // ACK! Must do something better with this. 8046 } 8047 ai = ri.activityInfo; 8048 comp = new ComponentName(ai.applicationInfo.packageName, 8049 ai.name); 8050 } else { 8051 ai = getActivityInfo(comp, flags, userId); 8052 if (ai == null) { 8053 continue; 8054 } 8055 } 8056 8057 // Look for any generic query activities that are duplicates 8058 // of this specific one, and remove them from the results. 8059 if (DEBUG_INTENT_MATCHING) Log.v(TAG, "Specific #" + i + ": " + ai); 8060 N = results.size(); 8061 int j; 8062 for (j=specificsPos; j<N; j++) { 8063 ResolveInfo sri = results.get(j); 8064 if ((sri.activityInfo.name.equals(comp.getClassName()) 8065 && sri.activityInfo.applicationInfo.packageName.equals( 8066 comp.getPackageName())) 8067 || (action != null && sri.filter.matchAction(action))) { 8068 results.remove(j); 8069 if (DEBUG_INTENT_MATCHING) Log.v( 8070 TAG, "Removing duplicate item from " + j 8071 + " due to specific " + specificsPos); 8072 if (ri == null) { 8073 ri = sri; 8074 } 8075 j--; 8076 N--; 8077 } 8078 } 8079 8080 // Add this specific item to its proper place. 8081 if (ri == null) { 8082 ri = new ResolveInfo(); 8083 ri.activityInfo = ai; 8084 } 8085 results.add(specificsPos, ri); 8086 ri.specificIndex = i; 8087 specificsPos++; 8088 } 8089 } 8090 8091 // Now we go through the remaining generic results and remove any 8092 // duplicate actions that are found here. 8093 N = results.size(); 8094 for (int i=specificsPos; i<N-1; i++) { 8095 final ResolveInfo rii = results.get(i); 8096 if (rii.filter == null) { 8097 continue; 8098 } 8099 8100 // Iterate over all of the actions of this result's intent 8101 // filter... typically this should be just one. 8102 final Iterator<String> it = rii.filter.actionsIterator(); 8103 if (it == null) { 8104 continue; 8105 } 8106 while (it.hasNext()) { 8107 final String action = it.next(); 8108 if (resultsAction != null && resultsAction.equals(action)) { 8109 // If this action was explicitly requested, then don't 8110 // remove things that have it. 8111 continue; 8112 } 8113 for (int j=i+1; j<N; j++) { 8114 final ResolveInfo rij = results.get(j); 8115 if (rij.filter != null && rij.filter.hasAction(action)) { 8116 results.remove(j); 8117 if (DEBUG_INTENT_MATCHING) Log.v( 8118 TAG, "Removing duplicate item from " + j 8119 + " due to action " + action + " at " + i); 8120 j--; 8121 N--; 8122 } 8123 } 8124 } 8125 8126 // If the caller didn't request filter information, drop it now 8127 // so we don't have to marshall/unmarshall it. 8128 if ((flags&PackageManager.GET_RESOLVED_FILTER) == 0) { 8129 rii.filter = null; 8130 } 8131 } 8132 8133 // Filter out the caller activity if so requested. 8134 if (caller != null) { 8135 N = results.size(); 8136 for (int i=0; i<N; i++) { 8137 ActivityInfo ainfo = results.get(i).activityInfo; 8138 if (caller.getPackageName().equals(ainfo.applicationInfo.packageName) 8139 && caller.getClassName().equals(ainfo.name)) { 8140 results.remove(i); 8141 break; 8142 } 8143 } 8144 } 8145 8146 // If the caller didn't request filter information, 8147 // drop them now so we don't have to 8148 // marshall/unmarshall it. 8149 if ((flags&PackageManager.GET_RESOLVED_FILTER) == 0) { 8150 N = results.size(); 8151 for (int i=0; i<N; i++) { 8152 results.get(i).filter = null; 8153 } 8154 } 8155 8156 if (DEBUG_INTENT_MATCHING) Log.v(TAG, "Result: " + results); 8157 return results; 8158 } 8159 8160 @Override 8161 public @NonNull ParceledListSlice<ResolveInfo> queryIntentReceivers(Intent intent, 8162 String resolvedType, int flags, int userId) { 8163 return new ParceledListSlice<>( 8164 queryIntentReceiversInternal(intent, resolvedType, flags, userId, 8165 false /*allowDynamicSplits*/)); 8166 } 8167 8168 private @NonNull List<ResolveInfo> queryIntentReceiversInternal(Intent intent, 8169 String resolvedType, int flags, int userId, boolean allowDynamicSplits) { 8170 if (!sUserManager.exists(userId)) return Collections.emptyList(); 8171 final int callingUid = Binder.getCallingUid(); 8172 enforceCrossUserPermission(callingUid, userId, 8173 false /*requireFullPermission*/, false /*checkShell*/, 8174 "query intent receivers"); 8175 final String instantAppPkgName = getInstantAppPackageName(callingUid); 8176 flags = updateFlagsForResolve(flags, userId, intent, callingUid, 8177 false /*includeInstantApps*/); 8178 ComponentName comp = intent.getComponent(); 8179 if (comp == null) { 8180 if (intent.getSelector() != null) { 8181 intent = intent.getSelector(); 8182 comp = intent.getComponent(); 8183 } 8184 } 8185 if (comp != null) { 8186 final List<ResolveInfo> list = new ArrayList<ResolveInfo>(1); 8187 final ActivityInfo ai = getReceiverInfo(comp, flags, userId); 8188 if (ai != null) { 8189 // When specifying an explicit component, we prevent the activity from being 8190 // used when either 1) the calling package is normal and the activity is within 8191 // an instant application or 2) the calling package is ephemeral and the 8192 // activity is not visible to instant applications. 8193 final boolean matchInstantApp = 8194 (flags & PackageManager.MATCH_INSTANT) != 0; 8195 final boolean matchVisibleToInstantAppOnly = 8196 (flags & PackageManager.MATCH_VISIBLE_TO_INSTANT_APP_ONLY) != 0; 8197 final boolean matchExplicitlyVisibleOnly = 8198 (flags & PackageManager.MATCH_EXPLICITLY_VISIBLE_ONLY) != 0; 8199 final boolean isCallerInstantApp = 8200 instantAppPkgName != null; 8201 final boolean isTargetSameInstantApp = 8202 comp.getPackageName().equals(instantAppPkgName); 8203 final boolean isTargetInstantApp = 8204 (ai.applicationInfo.privateFlags 8205 & ApplicationInfo.PRIVATE_FLAG_INSTANT) != 0; 8206 final boolean isTargetVisibleToInstantApp = 8207 (ai.flags & ActivityInfo.FLAG_VISIBLE_TO_INSTANT_APP) != 0; 8208 final boolean isTargetExplicitlyVisibleToInstantApp = 8209 isTargetVisibleToInstantApp 8210 && (ai.flags & ActivityInfo.FLAG_IMPLICITLY_VISIBLE_TO_INSTANT_APP) == 0; 8211 final boolean isTargetHiddenFromInstantApp = 8212 !isTargetVisibleToInstantApp 8213 || (matchExplicitlyVisibleOnly && !isTargetExplicitlyVisibleToInstantApp); 8214 final boolean blockResolution = 8215 !isTargetSameInstantApp 8216 && ((!matchInstantApp && !isCallerInstantApp && isTargetInstantApp) 8217 || (matchVisibleToInstantAppOnly && isCallerInstantApp 8218 && isTargetHiddenFromInstantApp)); 8219 if (!blockResolution) { 8220 ResolveInfo ri = new ResolveInfo(); 8221 ri.activityInfo = ai; 8222 list.add(ri); 8223 } 8224 } 8225 return applyPostResolutionFilter( 8226 list, instantAppPkgName, allowDynamicSplits, callingUid, userId); 8227 } 8228 8229 // reader 8230 synchronized (mPackages) { 8231 String pkgName = intent.getPackage(); 8232 if (pkgName == null) { 8233 final List<ResolveInfo> result = 8234 mReceivers.queryIntent(intent, resolvedType, flags, userId); 8235 return applyPostResolutionFilter( 8236 result, instantAppPkgName, allowDynamicSplits, callingUid, userId); 8237 } 8238 final PackageParser.Package pkg = mPackages.get(pkgName); 8239 if (pkg != null) { 8240 final List<ResolveInfo> result = mReceivers.queryIntentForPackage( 8241 intent, resolvedType, flags, pkg.receivers, userId); 8242 return applyPostResolutionFilter( 8243 result, instantAppPkgName, allowDynamicSplits, callingUid, userId); 8244 } 8245 return Collections.emptyList(); 8246 } 8247 } 8248 8249 @Override 8250 public ResolveInfo resolveService(Intent intent, String resolvedType, int flags, int userId) { 8251 final int callingUid = Binder.getCallingUid(); 8252 return resolveServiceInternal(intent, resolvedType, flags, userId, callingUid); 8253 } 8254 8255 private ResolveInfo resolveServiceInternal(Intent intent, String resolvedType, int flags, 8256 int userId, int callingUid) { 8257 if (!sUserManager.exists(userId)) return null; 8258 flags = updateFlagsForResolve( 8259 flags, userId, intent, callingUid, false /*includeInstantApps*/); 8260 List<ResolveInfo> query = queryIntentServicesInternal( 8261 intent, resolvedType, flags, userId, callingUid, false /*includeInstantApps*/); 8262 if (query != null) { 8263 if (query.size() >= 1) { 8264 // If there is more than one service with the same priority, 8265 // just arbitrarily pick the first one. 8266 return query.get(0); 8267 } 8268 } 8269 return null; 8270 } 8271 8272 @Override 8273 public @NonNull ParceledListSlice<ResolveInfo> queryIntentServices(Intent intent, 8274 String resolvedType, int flags, int userId) { 8275 final int callingUid = Binder.getCallingUid(); 8276 return new ParceledListSlice<>(queryIntentServicesInternal( 8277 intent, resolvedType, flags, userId, callingUid, false /*includeInstantApps*/)); 8278 } 8279 8280 private @NonNull List<ResolveInfo> queryIntentServicesInternal(Intent intent, 8281 String resolvedType, int flags, int userId, int callingUid, 8282 boolean includeInstantApps) { 8283 if (!sUserManager.exists(userId)) return Collections.emptyList(); 8284 enforceCrossUserPermission(callingUid, userId, 8285 false /*requireFullPermission*/, false /*checkShell*/, 8286 "query intent receivers"); 8287 final String instantAppPkgName = getInstantAppPackageName(callingUid); 8288 flags = updateFlagsForResolve(flags, userId, intent, callingUid, includeInstantApps); 8289 ComponentName comp = intent.getComponent(); 8290 if (comp == null) { 8291 if (intent.getSelector() != null) { 8292 intent = intent.getSelector(); 8293 comp = intent.getComponent(); 8294 } 8295 } 8296 if (comp != null) { 8297 final List<ResolveInfo> list = new ArrayList<ResolveInfo>(1); 8298 final ServiceInfo si = getServiceInfo(comp, flags, userId); 8299 if (si != null) { 8300 // When specifying an explicit component, we prevent the service from being 8301 // used when either 1) the service is in an instant application and the 8302 // caller is not the same instant application or 2) the calling package is 8303 // ephemeral and the activity is not visible to ephemeral applications. 8304 final boolean matchInstantApp = 8305 (flags & PackageManager.MATCH_INSTANT) != 0; 8306 final boolean matchVisibleToInstantAppOnly = 8307 (flags & PackageManager.MATCH_VISIBLE_TO_INSTANT_APP_ONLY) != 0; 8308 final boolean isCallerInstantApp = 8309 instantAppPkgName != null; 8310 final boolean isTargetSameInstantApp = 8311 comp.getPackageName().equals(instantAppPkgName); 8312 final boolean isTargetInstantApp = 8313 (si.applicationInfo.privateFlags 8314 & ApplicationInfo.PRIVATE_FLAG_INSTANT) != 0; 8315 final boolean isTargetHiddenFromInstantApp = 8316 (si.flags & ServiceInfo.FLAG_VISIBLE_TO_INSTANT_APP) == 0; 8317 final boolean blockResolution = 8318 !isTargetSameInstantApp 8319 && ((!matchInstantApp && !isCallerInstantApp && isTargetInstantApp) 8320 || (matchVisibleToInstantAppOnly && isCallerInstantApp 8321 && isTargetHiddenFromInstantApp)); 8322 if (!blockResolution) { 8323 final ResolveInfo ri = new ResolveInfo(); 8324 ri.serviceInfo = si; 8325 list.add(ri); 8326 } 8327 } 8328 return list; 8329 } 8330 8331 // reader 8332 synchronized (mPackages) { 8333 String pkgName = intent.getPackage(); 8334 if (pkgName == null) { 8335 return applyPostServiceResolutionFilter( 8336 mServices.queryIntent(intent, resolvedType, flags, userId), 8337 instantAppPkgName); 8338 } 8339 final PackageParser.Package pkg = mPackages.get(pkgName); 8340 if (pkg != null) { 8341 return applyPostServiceResolutionFilter( 8342 mServices.queryIntentForPackage(intent, resolvedType, flags, pkg.services, 8343 userId), 8344 instantAppPkgName); 8345 } 8346 return Collections.emptyList(); 8347 } 8348 } 8349 8350 private List<ResolveInfo> applyPostServiceResolutionFilter(List<ResolveInfo> resolveInfos, 8351 String instantAppPkgName) { 8352 if (instantAppPkgName == null) { 8353 return resolveInfos; 8354 } 8355 for (int i = resolveInfos.size() - 1; i >= 0; i--) { 8356 final ResolveInfo info = resolveInfos.get(i); 8357 final boolean isEphemeralApp = info.serviceInfo.applicationInfo.isInstantApp(); 8358 // allow services that are defined in the provided package 8359 if (isEphemeralApp && instantAppPkgName.equals(info.serviceInfo.packageName)) { 8360 if (info.serviceInfo.splitName != null 8361 && !ArrayUtils.contains(info.serviceInfo.applicationInfo.splitNames, 8362 info.serviceInfo.splitName)) { 8363 // requested service is defined in a split that hasn't been installed yet. 8364 // add the installer to the resolve list 8365 if (DEBUG_EPHEMERAL) { 8366 Slog.v(TAG, "Adding ephemeral installer to the ResolveInfo list"); 8367 } 8368 final ResolveInfo installerInfo = new ResolveInfo(mInstantAppInstallerInfo); 8369 installerInfo.auxiliaryInfo = new AuxiliaryResolveInfo( 8370 info.serviceInfo.packageName, info.serviceInfo.splitName, 8371 null /*failureActivity*/, info.serviceInfo.applicationInfo.versionCode, 8372 null /*failureIntent*/); 8373 // make sure this resolver is the default 8374 installerInfo.isDefault = true; 8375 installerInfo.match = IntentFilter.MATCH_CATEGORY_SCHEME_SPECIFIC_PART 8376 | IntentFilter.MATCH_ADJUSTMENT_NORMAL; 8377 // add a non-generic filter 8378 installerInfo.filter = new IntentFilter(); 8379 // load resources from the correct package 8380 installerInfo.resolvePackageName = info.getComponentInfo().packageName; 8381 resolveInfos.set(i, installerInfo); 8382 } 8383 continue; 8384 } 8385 // allow services that have been explicitly exposed to ephemeral apps 8386 if (!isEphemeralApp 8387 && ((info.serviceInfo.flags & ServiceInfo.FLAG_VISIBLE_TO_INSTANT_APP) != 0)) { 8388 continue; 8389 } 8390 resolveInfos.remove(i); 8391 } 8392 return resolveInfos; 8393 } 8394 8395 @Override 8396 public @NonNull ParceledListSlice<ResolveInfo> queryIntentContentProviders(Intent intent, 8397 String resolvedType, int flags, int userId) { 8398 return new ParceledListSlice<>( 8399 queryIntentContentProvidersInternal(intent, resolvedType, flags, userId)); 8400 } 8401 8402 private @NonNull List<ResolveInfo> queryIntentContentProvidersInternal( 8403 Intent intent, String resolvedType, int flags, int userId) { 8404 if (!sUserManager.exists(userId)) return Collections.emptyList(); 8405 final int callingUid = Binder.getCallingUid(); 8406 final String instantAppPkgName = getInstantAppPackageName(callingUid); 8407 flags = updateFlagsForResolve(flags, userId, intent, callingUid, 8408 false /*includeInstantApps*/); 8409 ComponentName comp = intent.getComponent(); 8410 if (comp == null) { 8411 if (intent.getSelector() != null) { 8412 intent = intent.getSelector(); 8413 comp = intent.getComponent(); 8414 } 8415 } 8416 if (comp != null) { 8417 final List<ResolveInfo> list = new ArrayList<ResolveInfo>(1); 8418 final ProviderInfo pi = getProviderInfo(comp, flags, userId); 8419 if (pi != null) { 8420 // When specifying an explicit component, we prevent the provider from being 8421 // used when either 1) the provider is in an instant application and the 8422 // caller is not the same instant application or 2) the calling package is an 8423 // instant application and the provider is not visible to instant applications. 8424 final boolean matchInstantApp = 8425 (flags & PackageManager.MATCH_INSTANT) != 0; 8426 final boolean matchVisibleToInstantAppOnly = 8427 (flags & PackageManager.MATCH_VISIBLE_TO_INSTANT_APP_ONLY) != 0; 8428 final boolean isCallerInstantApp = 8429 instantAppPkgName != null; 8430 final boolean isTargetSameInstantApp = 8431 comp.getPackageName().equals(instantAppPkgName); 8432 final boolean isTargetInstantApp = 8433 (pi.applicationInfo.privateFlags 8434 & ApplicationInfo.PRIVATE_FLAG_INSTANT) != 0; 8435 final boolean isTargetHiddenFromInstantApp = 8436 (pi.flags & ProviderInfo.FLAG_VISIBLE_TO_INSTANT_APP) == 0; 8437 final boolean blockResolution = 8438 !isTargetSameInstantApp 8439 && ((!matchInstantApp && !isCallerInstantApp && isTargetInstantApp) 8440 || (matchVisibleToInstantAppOnly && isCallerInstantApp 8441 && isTargetHiddenFromInstantApp)); 8442 if (!blockResolution) { 8443 final ResolveInfo ri = new ResolveInfo(); 8444 ri.providerInfo = pi; 8445 list.add(ri); 8446 } 8447 } 8448 return list; 8449 } 8450 8451 // reader 8452 synchronized (mPackages) { 8453 String pkgName = intent.getPackage(); 8454 if (pkgName == null) { 8455 return applyPostContentProviderResolutionFilter( 8456 mProviders.queryIntent(intent, resolvedType, flags, userId), 8457 instantAppPkgName); 8458 } 8459 final PackageParser.Package pkg = mPackages.get(pkgName); 8460 if (pkg != null) { 8461 return applyPostContentProviderResolutionFilter( 8462 mProviders.queryIntentForPackage( 8463 intent, resolvedType, flags, pkg.providers, userId), 8464 instantAppPkgName); 8465 } 8466 return Collections.emptyList(); 8467 } 8468 } 8469 8470 private List<ResolveInfo> applyPostContentProviderResolutionFilter( 8471 List<ResolveInfo> resolveInfos, String instantAppPkgName) { 8472 if (instantAppPkgName == null) { 8473 return resolveInfos; 8474 } 8475 for (int i = resolveInfos.size() - 1; i >= 0; i--) { 8476 final ResolveInfo info = resolveInfos.get(i); 8477 final boolean isEphemeralApp = info.providerInfo.applicationInfo.isInstantApp(); 8478 // allow providers that are defined in the provided package 8479 if (isEphemeralApp && instantAppPkgName.equals(info.providerInfo.packageName)) { 8480 if (info.providerInfo.splitName != null 8481 && !ArrayUtils.contains(info.providerInfo.applicationInfo.splitNames, 8482 info.providerInfo.splitName)) { 8483 // requested provider is defined in a split that hasn't been installed yet. 8484 // add the installer to the resolve list 8485 if (DEBUG_EPHEMERAL) { 8486 Slog.v(TAG, "Adding ephemeral installer to the ResolveInfo list"); 8487 } 8488 final ResolveInfo installerInfo = new ResolveInfo(mInstantAppInstallerInfo); 8489 installerInfo.auxiliaryInfo = new AuxiliaryResolveInfo( 8490 info.providerInfo.packageName, info.providerInfo.splitName, 8491 null /*failureActivity*/, info.providerInfo.applicationInfo.versionCode, 8492 null /*failureIntent*/); 8493 // make sure this resolver is the default 8494 installerInfo.isDefault = true; 8495 installerInfo.match = IntentFilter.MATCH_CATEGORY_SCHEME_SPECIFIC_PART 8496 | IntentFilter.MATCH_ADJUSTMENT_NORMAL; 8497 // add a non-generic filter 8498 installerInfo.filter = new IntentFilter(); 8499 // load resources from the correct package 8500 installerInfo.resolvePackageName = info.getComponentInfo().packageName; 8501 resolveInfos.set(i, installerInfo); 8502 } 8503 continue; 8504 } 8505 // allow providers that have been explicitly exposed to instant applications 8506 if (!isEphemeralApp 8507 && ((info.providerInfo.flags & ProviderInfo.FLAG_VISIBLE_TO_INSTANT_APP) != 0)) { 8508 continue; 8509 } 8510 resolveInfos.remove(i); 8511 } 8512 return resolveInfos; 8513 } 8514 8515 @Override 8516 public ParceledListSlice<PackageInfo> getInstalledPackages(int flags, int userId) { 8517 final int callingUid = Binder.getCallingUid(); 8518 if (getInstantAppPackageName(callingUid) != null) { 8519 return ParceledListSlice.emptyList(); 8520 } 8521 if (!sUserManager.exists(userId)) return ParceledListSlice.emptyList(); 8522 flags = updateFlagsForPackage(flags, userId, null); 8523 final boolean listUninstalled = (flags & MATCH_KNOWN_PACKAGES) != 0; 8524 enforceCrossUserPermission(callingUid, userId, 8525 true /* requireFullPermission */, false /* checkShell */, 8526 "get installed packages"); 8527 8528 // writer 8529 synchronized (mPackages) { 8530 ArrayList<PackageInfo> list; 8531 if (listUninstalled) { 8532 list = new ArrayList<>(mSettings.mPackages.size()); 8533 for (PackageSetting ps : mSettings.mPackages.values()) { 8534 if (filterSharedLibPackageLPr(ps, callingUid, userId, flags)) { 8535 continue; 8536 } 8537 if (filterAppAccessLPr(ps, callingUid, userId)) { 8538 continue; 8539 } 8540 final PackageInfo pi = generatePackageInfo(ps, flags, userId); 8541 if (pi != null) { 8542 list.add(pi); 8543 } 8544 } 8545 } else { 8546 list = new ArrayList<>(mPackages.size()); 8547 for (PackageParser.Package p : mPackages.values()) { 8548 final PackageSetting ps = (PackageSetting) p.mExtras; 8549 if (filterSharedLibPackageLPr(ps, callingUid, userId, flags)) { 8550 continue; 8551 } 8552 if (filterAppAccessLPr(ps, callingUid, userId)) { 8553 continue; 8554 } 8555 final PackageInfo pi = generatePackageInfo((PackageSetting) 8556 p.mExtras, flags, userId); 8557 if (pi != null) { 8558 list.add(pi); 8559 } 8560 } 8561 } 8562 8563 return new ParceledListSlice<>(list); 8564 } 8565 } 8566 8567 private void addPackageHoldingPermissions(ArrayList<PackageInfo> list, PackageSetting ps, 8568 String[] permissions, boolean[] tmp, int flags, int userId) { 8569 int numMatch = 0; 8570 final PermissionsState permissionsState = ps.getPermissionsState(); 8571 for (int i=0; i<permissions.length; i++) { 8572 final String permission = permissions[i]; 8573 if (permissionsState.hasPermission(permission, userId)) { 8574 tmp[i] = true; 8575 numMatch++; 8576 } else { 8577 tmp[i] = false; 8578 } 8579 } 8580 if (numMatch == 0) { 8581 return; 8582 } 8583 final PackageInfo pi = generatePackageInfo(ps, flags, userId); 8584 8585 // The above might return null in cases of uninstalled apps or install-state 8586 // skew across users/profiles. 8587 if (pi != null) { 8588 if ((flags&PackageManager.GET_PERMISSIONS) == 0) { 8589 if (numMatch == permissions.length) { 8590 pi.requestedPermissions = permissions; 8591 } else { 8592 pi.requestedPermissions = new String[numMatch]; 8593 numMatch = 0; 8594 for (int i=0; i<permissions.length; i++) { 8595 if (tmp[i]) { 8596 pi.requestedPermissions[numMatch] = permissions[i]; 8597 numMatch++; 8598 } 8599 } 8600 } 8601 } 8602 list.add(pi); 8603 } 8604 } 8605 8606 @Override 8607 public ParceledListSlice<PackageInfo> getPackagesHoldingPermissions( 8608 String[] permissions, int flags, int userId) { 8609 if (!sUserManager.exists(userId)) return ParceledListSlice.emptyList(); 8610 flags = updateFlagsForPackage(flags, userId, permissions); 8611 enforceCrossUserPermission(Binder.getCallingUid(), userId, 8612 true /* requireFullPermission */, false /* checkShell */, 8613 "get packages holding permissions"); 8614 final boolean listUninstalled = (flags & MATCH_KNOWN_PACKAGES) != 0; 8615 8616 // writer 8617 synchronized (mPackages) { 8618 ArrayList<PackageInfo> list = new ArrayList<PackageInfo>(); 8619 boolean[] tmpBools = new boolean[permissions.length]; 8620 if (listUninstalled) { 8621 for (PackageSetting ps : mSettings.mPackages.values()) { 8622 addPackageHoldingPermissions(list, ps, permissions, tmpBools, flags, 8623 userId); 8624 } 8625 } else { 8626 for (PackageParser.Package pkg : mPackages.values()) { 8627 PackageSetting ps = (PackageSetting)pkg.mExtras; 8628 if (ps != null) { 8629 addPackageHoldingPermissions(list, ps, permissions, tmpBools, flags, 8630 userId); 8631 } 8632 } 8633 } 8634 8635 return new ParceledListSlice<PackageInfo>(list); 8636 } 8637 } 8638 8639 @Override 8640 public ParceledListSlice<ApplicationInfo> getInstalledApplications(int flags, int userId) { 8641 final int callingUid = Binder.getCallingUid(); 8642 if (getInstantAppPackageName(callingUid) != null) { 8643 return ParceledListSlice.emptyList(); 8644 } 8645 if (!sUserManager.exists(userId)) return ParceledListSlice.emptyList(); 8646 flags = updateFlagsForApplication(flags, userId, null); 8647 final boolean listUninstalled = (flags & MATCH_KNOWN_PACKAGES) != 0; 8648 8649 // writer 8650 synchronized (mPackages) { 8651 ArrayList<ApplicationInfo> list; 8652 if (listUninstalled) { 8653 list = new ArrayList<>(mSettings.mPackages.size()); 8654 for (PackageSetting ps : mSettings.mPackages.values()) { 8655 ApplicationInfo ai; 8656 int effectiveFlags = flags; 8657 if (ps.isSystem()) { 8658 effectiveFlags |= PackageManager.MATCH_ANY_USER; 8659 } 8660 if (ps.pkg != null) { 8661 if (filterSharedLibPackageLPr(ps, callingUid, userId, flags)) { 8662 continue; 8663 } 8664 if (filterAppAccessLPr(ps, callingUid, userId)) { 8665 continue; 8666 } 8667 ai = PackageParser.generateApplicationInfo(ps.pkg, effectiveFlags, 8668 ps.readUserState(userId), userId); 8669 if (ai != null) { 8670 ai.packageName = resolveExternalPackageNameLPr(ps.pkg); 8671 } 8672 } else { 8673 // Shared lib filtering done in generateApplicationInfoFromSettingsLPw 8674 // and already converts to externally visible package name 8675 ai = generateApplicationInfoFromSettingsLPw(ps.name, 8676 callingUid, effectiveFlags, userId); 8677 } 8678 if (ai != null) { 8679 list.add(ai); 8680 } 8681 } 8682 } else { 8683 list = new ArrayList<>(mPackages.size()); 8684 for (PackageParser.Package p : mPackages.values()) { 8685 if (p.mExtras != null) { 8686 PackageSetting ps = (PackageSetting) p.mExtras; 8687 if (filterSharedLibPackageLPr(ps, Binder.getCallingUid(), userId, flags)) { 8688 continue; 8689 } 8690 if (filterAppAccessLPr(ps, callingUid, userId)) { 8691 continue; 8692 } 8693 ApplicationInfo ai = PackageParser.generateApplicationInfo(p, flags, 8694 ps.readUserState(userId), userId); 8695 if (ai != null) { 8696 ai.packageName = resolveExternalPackageNameLPr(p); 8697 list.add(ai); 8698 } 8699 } 8700 } 8701 } 8702 8703 return new ParceledListSlice<>(list); 8704 } 8705 } 8706 8707 @Override 8708 public ParceledListSlice<InstantAppInfo> getInstantApps(int userId) { 8709 if (HIDE_EPHEMERAL_APIS || isEphemeralDisabled()) { 8710 return null; 8711 } 8712 if (!canViewInstantApps(Binder.getCallingUid(), userId)) { 8713 mContext.enforceCallingOrSelfPermission(Manifest.permission.ACCESS_INSTANT_APPS, 8714 "getEphemeralApplications"); 8715 } 8716 enforceCrossUserPermission(Binder.getCallingUid(), userId, 8717 true /* requireFullPermission */, false /* checkShell */, 8718 "getEphemeralApplications"); 8719 synchronized (mPackages) { 8720 List<InstantAppInfo> instantApps = mInstantAppRegistry 8721 .getInstantAppsLPr(userId); 8722 if (instantApps != null) { 8723 return new ParceledListSlice<>(instantApps); 8724 } 8725 } 8726 return null; 8727 } 8728 8729 @Override 8730 public boolean isInstantApp(String packageName, int userId) { 8731 enforceCrossUserPermission(Binder.getCallingUid(), userId, 8732 true /* requireFullPermission */, false /* checkShell */, 8733 "isInstantApp"); 8734 if (HIDE_EPHEMERAL_APIS || isEphemeralDisabled()) { 8735 return false; 8736 } 8737 8738 synchronized (mPackages) { 8739 int callingUid = Binder.getCallingUid(); 8740 if (Process.isIsolated(callingUid)) { 8741 callingUid = mIsolatedOwners.get(callingUid); 8742 } 8743 final PackageSetting ps = mSettings.mPackages.get(packageName); 8744 PackageParser.Package pkg = mPackages.get(packageName); 8745 final boolean returnAllowed = 8746 ps != null 8747 && (isCallerSameApp(packageName, callingUid) 8748 || canViewInstantApps(callingUid, userId) 8749 || mInstantAppRegistry.isInstantAccessGranted( 8750 userId, UserHandle.getAppId(callingUid), ps.appId)); 8751 if (returnAllowed) { 8752 return ps.getInstantApp(userId); 8753 } 8754 } 8755 return false; 8756 } 8757 8758 @Override 8759 public byte[] getInstantAppCookie(String packageName, int userId) { 8760 if (HIDE_EPHEMERAL_APIS || isEphemeralDisabled()) { 8761 return null; 8762 } 8763 8764 enforceCrossUserPermission(Binder.getCallingUid(), userId, 8765 true /* requireFullPermission */, false /* checkShell */, 8766 "getInstantAppCookie"); 8767 if (!isCallerSameApp(packageName, Binder.getCallingUid())) { 8768 return null; 8769 } 8770 synchronized (mPackages) { 8771 return mInstantAppRegistry.getInstantAppCookieLPw( 8772 packageName, userId); 8773 } 8774 } 8775 8776 @Override 8777 public boolean setInstantAppCookie(String packageName, byte[] cookie, int userId) { 8778 if (HIDE_EPHEMERAL_APIS || isEphemeralDisabled()) { 8779 return true; 8780 } 8781 8782 enforceCrossUserPermission(Binder.getCallingUid(), userId, 8783 true /* requireFullPermission */, true /* checkShell */, 8784 "setInstantAppCookie"); 8785 if (!isCallerSameApp(packageName, Binder.getCallingUid())) { 8786 return false; 8787 } 8788 synchronized (mPackages) { 8789 return mInstantAppRegistry.setInstantAppCookieLPw( 8790 packageName, cookie, userId); 8791 } 8792 } 8793 8794 @Override 8795 public Bitmap getInstantAppIcon(String packageName, int userId) { 8796 if (HIDE_EPHEMERAL_APIS || isEphemeralDisabled()) { 8797 return null; 8798 } 8799 8800 if (!canViewInstantApps(Binder.getCallingUid(), userId)) { 8801 mContext.enforceCallingOrSelfPermission(Manifest.permission.ACCESS_INSTANT_APPS, 8802 "getInstantAppIcon"); 8803 } 8804 enforceCrossUserPermission(Binder.getCallingUid(), userId, 8805 true /* requireFullPermission */, false /* checkShell */, 8806 "getInstantAppIcon"); 8807 8808 synchronized (mPackages) { 8809 return mInstantAppRegistry.getInstantAppIconLPw( 8810 packageName, userId); 8811 } 8812 } 8813 8814 private boolean isCallerSameApp(String packageName, int uid) { 8815 PackageParser.Package pkg = mPackages.get(packageName); 8816 return pkg != null 8817 && UserHandle.getAppId(uid) == pkg.applicationInfo.uid; 8818 } 8819 8820 @Override 8821 public @NonNull ParceledListSlice<ApplicationInfo> getPersistentApplications(int flags) { 8822 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 8823 return ParceledListSlice.emptyList(); 8824 } 8825 return new ParceledListSlice<>(getPersistentApplicationsInternal(flags)); 8826 } 8827 8828 private @NonNull List<ApplicationInfo> getPersistentApplicationsInternal(int flags) { 8829 final ArrayList<ApplicationInfo> finalList = new ArrayList<ApplicationInfo>(); 8830 8831 // reader 8832 synchronized (mPackages) { 8833 final Iterator<PackageParser.Package> i = mPackages.values().iterator(); 8834 final int userId = UserHandle.getCallingUserId(); 8835 while (i.hasNext()) { 8836 final PackageParser.Package p = i.next(); 8837 if (p.applicationInfo == null) continue; 8838 8839 final boolean matchesUnaware = ((flags & MATCH_DIRECT_BOOT_UNAWARE) != 0) 8840 && !p.applicationInfo.isDirectBootAware(); 8841 final boolean matchesAware = ((flags & MATCH_DIRECT_BOOT_AWARE) != 0) 8842 && p.applicationInfo.isDirectBootAware(); 8843 8844 if ((p.applicationInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0 8845 && (!mSafeMode || isSystemApp(p)) 8846 && (matchesUnaware || matchesAware)) { 8847 PackageSetting ps = mSettings.mPackages.get(p.packageName); 8848 if (ps != null) { 8849 ApplicationInfo ai = PackageParser.generateApplicationInfo(p, flags, 8850 ps.readUserState(userId), userId); 8851 if (ai != null) { 8852 finalList.add(ai); 8853 } 8854 } 8855 } 8856 } 8857 } 8858 8859 return finalList; 8860 } 8861 8862 @Override 8863 public ProviderInfo resolveContentProvider(String name, int flags, int userId) { 8864 if (!sUserManager.exists(userId)) return null; 8865 flags = updateFlagsForComponent(flags, userId, name); 8866 final String instantAppPkgName = getInstantAppPackageName(Binder.getCallingUid()); 8867 // reader 8868 synchronized (mPackages) { 8869 final PackageParser.Provider provider = mProvidersByAuthority.get(name); 8870 PackageSetting ps = provider != null 8871 ? mSettings.mPackages.get(provider.owner.packageName) 8872 : null; 8873 if (ps != null) { 8874 final boolean isInstantApp = ps.getInstantApp(userId); 8875 // normal application; filter out instant application provider 8876 if (instantAppPkgName == null && isInstantApp) { 8877 return null; 8878 } 8879 // instant application; filter out other instant applications 8880 if (instantAppPkgName != null 8881 && isInstantApp 8882 && !provider.owner.packageName.equals(instantAppPkgName)) { 8883 return null; 8884 } 8885 // instant application; filter out non-exposed provider 8886 if (instantAppPkgName != null 8887 && !isInstantApp 8888 && (provider.info.flags & ProviderInfo.FLAG_VISIBLE_TO_INSTANT_APP) == 0) { 8889 return null; 8890 } 8891 // provider not enabled 8892 if (!mSettings.isEnabledAndMatchLPr(provider.info, flags, userId)) { 8893 return null; 8894 } 8895 return PackageParser.generateProviderInfo( 8896 provider, flags, ps.readUserState(userId), userId); 8897 } 8898 return null; 8899 } 8900 } 8901 8902 /** 8903 * @deprecated 8904 */ 8905 @Deprecated 8906 public void querySyncProviders(List<String> outNames, List<ProviderInfo> outInfo) { 8907 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 8908 return; 8909 } 8910 // reader 8911 synchronized (mPackages) { 8912 final Iterator<Map.Entry<String, PackageParser.Provider>> i = mProvidersByAuthority 8913 .entrySet().iterator(); 8914 final int userId = UserHandle.getCallingUserId(); 8915 while (i.hasNext()) { 8916 Map.Entry<String, PackageParser.Provider> entry = i.next(); 8917 PackageParser.Provider p = entry.getValue(); 8918 PackageSetting ps = mSettings.mPackages.get(p.owner.packageName); 8919 8920 if (ps != null && p.syncable 8921 && (!mSafeMode || (p.info.applicationInfo.flags 8922 &ApplicationInfo.FLAG_SYSTEM) != 0)) { 8923 ProviderInfo info = PackageParser.generateProviderInfo(p, 0, 8924 ps.readUserState(userId), userId); 8925 if (info != null) { 8926 outNames.add(entry.getKey()); 8927 outInfo.add(info); 8928 } 8929 } 8930 } 8931 } 8932 } 8933 8934 @Override 8935 public @NonNull ParceledListSlice<ProviderInfo> queryContentProviders(String processName, 8936 int uid, int flags, String metaDataKey) { 8937 final int callingUid = Binder.getCallingUid(); 8938 final int userId = processName != null ? UserHandle.getUserId(uid) 8939 : UserHandle.getCallingUserId(); 8940 if (!sUserManager.exists(userId)) return ParceledListSlice.emptyList(); 8941 flags = updateFlagsForComponent(flags, userId, processName); 8942 ArrayList<ProviderInfo> finalList = null; 8943 // reader 8944 synchronized (mPackages) { 8945 final Iterator<PackageParser.Provider> i = mProviders.mProviders.values().iterator(); 8946 while (i.hasNext()) { 8947 final PackageParser.Provider p = i.next(); 8948 PackageSetting ps = mSettings.mPackages.get(p.owner.packageName); 8949 if (ps != null && p.info.authority != null 8950 && (processName == null 8951 || (p.info.processName.equals(processName) 8952 && UserHandle.isSameApp(p.info.applicationInfo.uid, uid))) 8953 && mSettings.isEnabledAndMatchLPr(p.info, flags, userId)) { 8954 8955 // See PM.queryContentProviders()'s javadoc for why we have the metaData 8956 // parameter. 8957 if (metaDataKey != null 8958 && (p.metaData == null || !p.metaData.containsKey(metaDataKey))) { 8959 continue; 8960 } 8961 final ComponentName component = 8962 new ComponentName(p.info.packageName, p.info.name); 8963 if (filterAppAccessLPr(ps, callingUid, component, TYPE_PROVIDER, userId)) { 8964 continue; 8965 } 8966 if (finalList == null) { 8967 finalList = new ArrayList<ProviderInfo>(3); 8968 } 8969 ProviderInfo info = PackageParser.generateProviderInfo(p, flags, 8970 ps.readUserState(userId), userId); 8971 if (info != null) { 8972 finalList.add(info); 8973 } 8974 } 8975 } 8976 } 8977 8978 if (finalList != null) { 8979 Collections.sort(finalList, mProviderInitOrderSorter); 8980 return new ParceledListSlice<ProviderInfo>(finalList); 8981 } 8982 8983 return ParceledListSlice.emptyList(); 8984 } 8985 8986 @Override 8987 public InstrumentationInfo getInstrumentationInfo(ComponentName component, int flags) { 8988 // reader 8989 synchronized (mPackages) { 8990 final int callingUid = Binder.getCallingUid(); 8991 final int callingUserId = UserHandle.getUserId(callingUid); 8992 final PackageSetting ps = mSettings.mPackages.get(component.getPackageName()); 8993 if (ps == null) return null; 8994 if (filterAppAccessLPr(ps, callingUid, component, TYPE_UNKNOWN, callingUserId)) { 8995 return null; 8996 } 8997 final PackageParser.Instrumentation i = mInstrumentation.get(component); 8998 return PackageParser.generateInstrumentationInfo(i, flags); 8999 } 9000 } 9001 9002 @Override 9003 public @NonNull ParceledListSlice<InstrumentationInfo> queryInstrumentation( 9004 String targetPackage, int flags) { 9005 final int callingUid = Binder.getCallingUid(); 9006 final int callingUserId = UserHandle.getUserId(callingUid); 9007 final PackageSetting ps = mSettings.mPackages.get(targetPackage); 9008 if (filterAppAccessLPr(ps, callingUid, callingUserId)) { 9009 return ParceledListSlice.emptyList(); 9010 } 9011 return new ParceledListSlice<>(queryInstrumentationInternal(targetPackage, flags)); 9012 } 9013 9014 private @NonNull List<InstrumentationInfo> queryInstrumentationInternal(String targetPackage, 9015 int flags) { 9016 ArrayList<InstrumentationInfo> finalList = new ArrayList<InstrumentationInfo>(); 9017 9018 // reader 9019 synchronized (mPackages) { 9020 final Iterator<PackageParser.Instrumentation> i = mInstrumentation.values().iterator(); 9021 while (i.hasNext()) { 9022 final PackageParser.Instrumentation p = i.next(); 9023 if (targetPackage == null 9024 || targetPackage.equals(p.info.targetPackage)) { 9025 InstrumentationInfo ii = PackageParser.generateInstrumentationInfo(p, 9026 flags); 9027 if (ii != null) { 9028 finalList.add(ii); 9029 } 9030 } 9031 } 9032 } 9033 9034 return finalList; 9035 } 9036 9037 private void scanDirTracedLI(File dir, final int parseFlags, int scanFlags, long currentTime) { 9038 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "scanDir [" + dir.getAbsolutePath() + "]"); 9039 try { 9040 scanDirLI(dir, parseFlags, scanFlags, currentTime); 9041 } finally { 9042 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 9043 } 9044 } 9045 9046 private void scanDirLI(File dir, int parseFlags, int scanFlags, long currentTime) { 9047 final File[] files = dir.listFiles(); 9048 if (ArrayUtils.isEmpty(files)) { 9049 Log.d(TAG, "No files in app dir " + dir); 9050 return; 9051 } 9052 9053 if (DEBUG_PACKAGE_SCANNING) { 9054 Log.d(TAG, "Scanning app dir " + dir + " scanFlags=" + scanFlags 9055 + " flags=0x" + Integer.toHexString(parseFlags)); 9056 } 9057 ParallelPackageParser parallelPackageParser = new ParallelPackageParser( 9058 mSeparateProcesses, mOnlyCore, mMetrics, mCacheDir, 9059 mParallelPackageParserCallback); 9060 9061 // Submit files for parsing in parallel 9062 int fileCount = 0; 9063 for (File file : files) { 9064 final boolean isPackage = (isApkFile(file) || file.isDirectory()) 9065 && !PackageInstallerService.isStageName(file.getName()); 9066 if (!isPackage) { 9067 // Ignore entries which are not packages 9068 continue; 9069 } 9070 parallelPackageParser.submit(file, parseFlags); 9071 fileCount++; 9072 } 9073 9074 // Process results one by one 9075 for (; fileCount > 0; fileCount--) { 9076 ParallelPackageParser.ParseResult parseResult = parallelPackageParser.take(); 9077 Throwable throwable = parseResult.throwable; 9078 int errorCode = PackageManager.INSTALL_SUCCEEDED; 9079 9080 if (throwable == null) { 9081 // Static shared libraries have synthetic package names 9082 if (parseResult.pkg.applicationInfo.isStaticSharedLibrary()) { 9083 renameStaticSharedLibraryPackage(parseResult.pkg); 9084 } 9085 try { 9086 if (errorCode == PackageManager.INSTALL_SUCCEEDED) { 9087 scanPackageLI(parseResult.pkg, parseResult.scanFile, parseFlags, scanFlags, 9088 currentTime, null); 9089 } 9090 } catch (PackageManagerException e) { 9091 errorCode = e.error; 9092 Slog.w(TAG, "Failed to scan " + parseResult.scanFile + ": " + e.getMessage()); 9093 } 9094 } else if (throwable instanceof PackageParser.PackageParserException) { 9095 PackageParser.PackageParserException e = (PackageParser.PackageParserException) 9096 throwable; 9097 errorCode = e.error; 9098 Slog.w(TAG, "Failed to parse " + parseResult.scanFile + ": " + e.getMessage()); 9099 } else { 9100 throw new IllegalStateException("Unexpected exception occurred while parsing " 9101 + parseResult.scanFile, throwable); 9102 } 9103 9104 // Delete invalid userdata apps 9105 if ((parseFlags & PackageParser.PARSE_IS_SYSTEM) == 0 && 9106 errorCode == PackageManager.INSTALL_FAILED_INVALID_APK) { 9107 logCriticalInfo(Log.WARN, 9108 "Deleting invalid package at " + parseResult.scanFile); 9109 removeCodePathLI(parseResult.scanFile); 9110 } 9111 } 9112 parallelPackageParser.close(); 9113 } 9114 9115 private static File getSettingsProblemFile() { 9116 File dataDir = Environment.getDataDirectory(); 9117 File systemDir = new File(dataDir, "system"); 9118 File fname = new File(systemDir, "uiderrors.txt"); 9119 return fname; 9120 } 9121 9122 static void reportSettingsProblem(int priority, String msg) { 9123 logCriticalInfo(priority, msg); 9124 } 9125 9126 public static void logCriticalInfo(int priority, String msg) { 9127 Slog.println(priority, TAG, msg); 9128 EventLogTags.writePmCriticalInfo(msg); 9129 try { 9130 File fname = getSettingsProblemFile(); 9131 FileOutputStream out = new FileOutputStream(fname, true); 9132 PrintWriter pw = new FastPrintWriter(out); 9133 SimpleDateFormat formatter = new SimpleDateFormat(); 9134 String dateString = formatter.format(new Date(System.currentTimeMillis())); 9135 pw.println(dateString + ": " + msg); 9136 pw.close(); 9137 FileUtils.setPermissions( 9138 fname.toString(), 9139 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IROTH, 9140 -1, -1); 9141 } catch (java.io.IOException e) { 9142 } 9143 } 9144 9145 private long getLastModifiedTime(PackageParser.Package pkg, File srcFile) { 9146 if (srcFile.isDirectory()) { 9147 final File baseFile = new File(pkg.baseCodePath); 9148 long maxModifiedTime = baseFile.lastModified(); 9149 if (pkg.splitCodePaths != null) { 9150 for (int i = pkg.splitCodePaths.length - 1; i >=0; --i) { 9151 final File splitFile = new File(pkg.splitCodePaths[i]); 9152 maxModifiedTime = Math.max(maxModifiedTime, splitFile.lastModified()); 9153 } 9154 } 9155 return maxModifiedTime; 9156 } 9157 return srcFile.lastModified(); 9158 } 9159 9160 private void collectCertificatesLI(PackageSetting ps, PackageParser.Package pkg, File srcFile, 9161 final int policyFlags) throws PackageManagerException { 9162 // When upgrading from pre-N MR1, verify the package time stamp using the package 9163 // directory and not the APK file. 9164 final long lastModifiedTime = mIsPreNMR1Upgrade 9165 ? new File(pkg.codePath).lastModified() : getLastModifiedTime(pkg, srcFile); 9166 if (ps != null 9167 && ps.codePath.equals(srcFile) 9168 && ps.timeStamp == lastModifiedTime 9169 && !isCompatSignatureUpdateNeeded(pkg) 9170 && !isRecoverSignatureUpdateNeeded(pkg)) { 9171 long mSigningKeySetId = ps.keySetData.getProperSigningKeySet(); 9172 KeySetManagerService ksms = mSettings.mKeySetManagerService; 9173 ArraySet<PublicKey> signingKs; 9174 synchronized (mPackages) { 9175 signingKs = ksms.getPublicKeysFromKeySetLPr(mSigningKeySetId); 9176 } 9177 if (ps.signatures.mSignatures != null 9178 && ps.signatures.mSignatures.length != 0 9179 && signingKs != null) { 9180 // Optimization: reuse the existing cached certificates 9181 // if the package appears to be unchanged. 9182 pkg.mSignatures = ps.signatures.mSignatures; 9183 pkg.mSigningKeys = signingKs; 9184 return; 9185 } 9186 9187 Slog.w(TAG, "PackageSetting for " + ps.name 9188 + " is missing signatures. Collecting certs again to recover them."); 9189 } else { 9190 Slog.i(TAG, srcFile.toString() + " changed; collecting certs"); 9191 } 9192 9193 try { 9194 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "collectCertificates"); 9195 PackageParser.collectCertificates(pkg, policyFlags); 9196 } catch (PackageParserException e) { 9197 throw PackageManagerException.from(e); 9198 } finally { 9199 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 9200 } 9201 } 9202 9203 /** 9204 * Traces a package scan. 9205 * @see #scanPackageLI(File, int, int, long, UserHandle) 9206 */ 9207 private PackageParser.Package scanPackageTracedLI(File scanFile, final int parseFlags, 9208 int scanFlags, long currentTime, UserHandle user) throws PackageManagerException { 9209 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "scanPackage [" + scanFile.toString() + "]"); 9210 try { 9211 return scanPackageLI(scanFile, parseFlags, scanFlags, currentTime, user); 9212 } finally { 9213 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 9214 } 9215 } 9216 9217 /** 9218 * Scans a package and returns the newly parsed package. 9219 * Returns {@code null} in case of errors and the error code is stored in mLastScanError 9220 */ 9221 private PackageParser.Package scanPackageLI(File scanFile, int parseFlags, int scanFlags, 9222 long currentTime, UserHandle user) throws PackageManagerException { 9223 if (DEBUG_INSTALL) Slog.d(TAG, "Parsing: " + scanFile); 9224 PackageParser pp = new PackageParser(); 9225 pp.setSeparateProcesses(mSeparateProcesses); 9226 pp.setOnlyCoreApps(mOnlyCore); 9227 pp.setDisplayMetrics(mMetrics); 9228 pp.setCallback(mPackageParserCallback); 9229 9230 if ((scanFlags & SCAN_TRUSTED_OVERLAY) != 0) { 9231 parseFlags |= PackageParser.PARSE_TRUSTED_OVERLAY; 9232 } 9233 9234 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "parsePackage"); 9235 final PackageParser.Package pkg; 9236 try { 9237 pkg = pp.parsePackage(scanFile, parseFlags); 9238 } catch (PackageParserException e) { 9239 throw PackageManagerException.from(e); 9240 } finally { 9241 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 9242 } 9243 9244 // Static shared libraries have synthetic package names 9245 if (pkg.applicationInfo.isStaticSharedLibrary()) { 9246 renameStaticSharedLibraryPackage(pkg); 9247 } 9248 9249 return scanPackageLI(pkg, scanFile, parseFlags, scanFlags, currentTime, user); 9250 } 9251 9252 /** 9253 * Scans a package and returns the newly parsed package. 9254 * @throws PackageManagerException on a parse error. 9255 */ 9256 private PackageParser.Package scanPackageLI(PackageParser.Package pkg, File scanFile, 9257 final int policyFlags, int scanFlags, long currentTime, @Nullable UserHandle user) 9258 throws PackageManagerException { 9259 // If the package has children and this is the first dive in the function 9260 // we scan the package with the SCAN_CHECK_ONLY flag set to see whether all 9261 // packages (parent and children) would be successfully scanned before the 9262 // actual scan since scanning mutates internal state and we want to atomically 9263 // install the package and its children. 9264 if ((scanFlags & SCAN_CHECK_ONLY) == 0) { 9265 if (pkg.childPackages != null && pkg.childPackages.size() > 0) { 9266 scanFlags |= SCAN_CHECK_ONLY; 9267 } 9268 } else { 9269 scanFlags &= ~SCAN_CHECK_ONLY; 9270 } 9271 9272 // Scan the parent 9273 PackageParser.Package scannedPkg = scanPackageInternalLI(pkg, scanFile, policyFlags, 9274 scanFlags, currentTime, user); 9275 9276 // Scan the children 9277 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 9278 for (int i = 0; i < childCount; i++) { 9279 PackageParser.Package childPackage = pkg.childPackages.get(i); 9280 scanPackageInternalLI(childPackage, scanFile, policyFlags, scanFlags, 9281 currentTime, user); 9282 } 9283 9284 9285 if ((scanFlags & SCAN_CHECK_ONLY) != 0) { 9286 return scanPackageLI(pkg, scanFile, policyFlags, scanFlags, currentTime, user); 9287 } 9288 9289 return scannedPkg; 9290 } 9291 9292 /** 9293 * Scans a package and returns the newly parsed package. 9294 * @throws PackageManagerException on a parse error. 9295 */ 9296 private PackageParser.Package scanPackageInternalLI(PackageParser.Package pkg, File scanFile, 9297 int policyFlags, int scanFlags, long currentTime, @Nullable UserHandle user) 9298 throws PackageManagerException { 9299 PackageSetting ps = null; 9300 PackageSetting updatedPkg; 9301 // reader 9302 synchronized (mPackages) { 9303 // Look to see if we already know about this package. 9304 String oldName = mSettings.getRenamedPackageLPr(pkg.packageName); 9305 if (pkg.mOriginalPackages != null && pkg.mOriginalPackages.contains(oldName)) { 9306 // This package has been renamed to its original name. Let's 9307 // use that. 9308 ps = mSettings.getPackageLPr(oldName); 9309 } 9310 // If there was no original package, see one for the real package name. 9311 if (ps == null) { 9312 ps = mSettings.getPackageLPr(pkg.packageName); 9313 } 9314 // Check to see if this package could be hiding/updating a system 9315 // package. Must look for it either under the original or real 9316 // package name depending on our state. 9317 updatedPkg = mSettings.getDisabledSystemPkgLPr(ps != null ? ps.name : pkg.packageName); 9318 if (DEBUG_INSTALL && updatedPkg != null) Slog.d(TAG, "updatedPkg = " + updatedPkg); 9319 9320 // If this is a package we don't know about on the system partition, we 9321 // may need to remove disabled child packages on the system partition 9322 // or may need to not add child packages if the parent apk is updated 9323 // on the data partition and no longer defines this child package. 9324 if ((policyFlags & PackageParser.PARSE_IS_SYSTEM) != 0) { 9325 // If this is a parent package for an updated system app and this system 9326 // app got an OTA update which no longer defines some of the child packages 9327 // we have to prune them from the disabled system packages. 9328 PackageSetting disabledPs = mSettings.getDisabledSystemPkgLPr(pkg.packageName); 9329 if (disabledPs != null) { 9330 final int scannedChildCount = (pkg.childPackages != null) 9331 ? pkg.childPackages.size() : 0; 9332 final int disabledChildCount = disabledPs.childPackageNames != null 9333 ? disabledPs.childPackageNames.size() : 0; 9334 for (int i = 0; i < disabledChildCount; i++) { 9335 String disabledChildPackageName = disabledPs.childPackageNames.get(i); 9336 boolean disabledPackageAvailable = false; 9337 for (int j = 0; j < scannedChildCount; j++) { 9338 PackageParser.Package childPkg = pkg.childPackages.get(j); 9339 if (childPkg.packageName.equals(disabledChildPackageName)) { 9340 disabledPackageAvailable = true; 9341 break; 9342 } 9343 } 9344 if (!disabledPackageAvailable) { 9345 mSettings.removeDisabledSystemPackageLPw(disabledChildPackageName); 9346 } 9347 } 9348 } 9349 } 9350 } 9351 9352 final boolean isUpdatedPkg = updatedPkg != null; 9353 final boolean isUpdatedSystemPkg = isUpdatedPkg 9354 && (policyFlags & PackageParser.PARSE_IS_SYSTEM) != 0; 9355 boolean isUpdatedPkgBetter = false; 9356 // First check if this is a system package that may involve an update 9357 if (isUpdatedSystemPkg) { 9358 // If new package is not located in "/system/priv-app" (e.g. due to an OTA), 9359 // it needs to drop FLAG_PRIVILEGED. 9360 if (locationIsPrivileged(scanFile)) { 9361 updatedPkg.pkgPrivateFlags |= ApplicationInfo.PRIVATE_FLAG_PRIVILEGED; 9362 } else { 9363 updatedPkg.pkgPrivateFlags &= ~ApplicationInfo.PRIVATE_FLAG_PRIVILEGED; 9364 } 9365 9366 if (ps != null && !ps.codePath.equals(scanFile)) { 9367 // The path has changed from what was last scanned... check the 9368 // version of the new path against what we have stored to determine 9369 // what to do. 9370 if (DEBUG_INSTALL) Slog.d(TAG, "Path changing from " + ps.codePath); 9371 if (pkg.mVersionCode <= ps.versionCode) { 9372 // The system package has been updated and the code path does not match 9373 // Ignore entry. Skip it. 9374 if (DEBUG_INSTALL) Slog.i(TAG, "Package " + ps.name + " at " + scanFile 9375 + " ignored: updated version " + ps.versionCode 9376 + " better than this " + pkg.mVersionCode); 9377 if (!updatedPkg.codePath.equals(scanFile)) { 9378 Slog.w(PackageManagerService.TAG, "Code path for hidden system pkg " 9379 + ps.name + " changing from " + updatedPkg.codePathString 9380 + " to " + scanFile); 9381 updatedPkg.codePath = scanFile; 9382 updatedPkg.codePathString = scanFile.toString(); 9383 updatedPkg.resourcePath = scanFile; 9384 updatedPkg.resourcePathString = scanFile.toString(); 9385 } 9386 updatedPkg.pkg = pkg; 9387 updatedPkg.versionCode = pkg.mVersionCode; 9388 9389 // Update the disabled system child packages to point to the package too. 9390 final int childCount = updatedPkg.childPackageNames != null 9391 ? updatedPkg.childPackageNames.size() : 0; 9392 for (int i = 0; i < childCount; i++) { 9393 String childPackageName = updatedPkg.childPackageNames.get(i); 9394 PackageSetting updatedChildPkg = mSettings.getDisabledSystemPkgLPr( 9395 childPackageName); 9396 if (updatedChildPkg != null) { 9397 updatedChildPkg.pkg = pkg; 9398 updatedChildPkg.versionCode = pkg.mVersionCode; 9399 } 9400 } 9401 } else { 9402 // The current app on the system partition is better than 9403 // what we have updated to on the data partition; switch 9404 // back to the system partition version. 9405 // At this point, its safely assumed that package installation for 9406 // apps in system partition will go through. If not there won't be a working 9407 // version of the app 9408 // writer 9409 synchronized (mPackages) { 9410 // Just remove the loaded entries from package lists. 9411 mPackages.remove(ps.name); 9412 } 9413 9414 logCriticalInfo(Log.WARN, "Package " + ps.name + " at " + scanFile 9415 + " reverting from " + ps.codePathString 9416 + ": new version " + pkg.mVersionCode 9417 + " better than installed " + ps.versionCode); 9418 9419 InstallArgs args = createInstallArgsForExisting(packageFlagsToInstallFlags(ps), 9420 ps.codePathString, ps.resourcePathString, getAppDexInstructionSets(ps)); 9421 synchronized (mInstallLock) { 9422 args.cleanUpResourcesLI(); 9423 } 9424 synchronized (mPackages) { 9425 mSettings.enableSystemPackageLPw(ps.name); 9426 } 9427 isUpdatedPkgBetter = true; 9428 } 9429 } 9430 } 9431 9432 String resourcePath = null; 9433 String baseResourcePath = null; 9434 if ((policyFlags & PackageParser.PARSE_FORWARD_LOCK) != 0 && !isUpdatedPkgBetter) { 9435 if (ps != null && ps.resourcePathString != null) { 9436 resourcePath = ps.resourcePathString; 9437 baseResourcePath = ps.resourcePathString; 9438 } else { 9439 // Should not happen at all. Just log an error. 9440 Slog.e(TAG, "Resource path not set for package " + pkg.packageName); 9441 } 9442 } else { 9443 resourcePath = pkg.codePath; 9444 baseResourcePath = pkg.baseCodePath; 9445 } 9446 9447 // Set application objects path explicitly. 9448 pkg.setApplicationVolumeUuid(pkg.volumeUuid); 9449 pkg.setApplicationInfoCodePath(pkg.codePath); 9450 pkg.setApplicationInfoBaseCodePath(pkg.baseCodePath); 9451 pkg.setApplicationInfoSplitCodePaths(pkg.splitCodePaths); 9452 pkg.setApplicationInfoResourcePath(resourcePath); 9453 pkg.setApplicationInfoBaseResourcePath(baseResourcePath); 9454 pkg.setApplicationInfoSplitResourcePaths(pkg.splitCodePaths); 9455 9456 // throw an exception if we have an update to a system application, but, it's not more 9457 // recent than the package we've already scanned 9458 if (isUpdatedSystemPkg && !isUpdatedPkgBetter) { 9459 // Set CPU Abis to application info. 9460 if ((scanFlags & SCAN_FIRST_BOOT_OR_UPGRADE) != 0) { 9461 final String cpuAbiOverride = deriveAbiOverride(pkg.cpuAbiOverride, updatedPkg); 9462 derivePackageAbi(pkg, scanFile, cpuAbiOverride, false, mAppLib32InstallDir); 9463 } else { 9464 pkg.applicationInfo.primaryCpuAbi = updatedPkg.primaryCpuAbiString; 9465 pkg.applicationInfo.secondaryCpuAbi = updatedPkg.secondaryCpuAbiString; 9466 } 9467 9468 throw new PackageManagerException(Log.WARN, "Package " + ps.name + " at " 9469 + scanFile + " ignored: updated version " + ps.versionCode 9470 + " better than this " + pkg.mVersionCode); 9471 } 9472 9473 if (isUpdatedPkg) { 9474 // An updated system app will not have the PARSE_IS_SYSTEM flag set 9475 // initially 9476 policyFlags |= PackageParser.PARSE_IS_SYSTEM; 9477 9478 // An updated privileged app will not have the PARSE_IS_PRIVILEGED 9479 // flag set initially 9480 if ((updatedPkg.pkgPrivateFlags & ApplicationInfo.PRIVATE_FLAG_PRIVILEGED) != 0) { 9481 policyFlags |= PackageParser.PARSE_IS_PRIVILEGED; 9482 } 9483 } 9484 9485 // Verify certificates against what was last scanned 9486 collectCertificatesLI(ps, pkg, scanFile, policyFlags); 9487 9488 /* 9489 * A new system app appeared, but we already had a non-system one of the 9490 * same name installed earlier. 9491 */ 9492 boolean shouldHideSystemApp = false; 9493 if (!isUpdatedPkg && ps != null 9494 && (policyFlags & PackageParser.PARSE_IS_SYSTEM_DIR) != 0 && !isSystemApp(ps)) { 9495 /* 9496 * Check to make sure the signatures match first. If they don't, 9497 * wipe the installed application and its data. 9498 */ 9499 if (compareSignatures(ps.signatures.mSignatures, pkg.mSignatures) 9500 != PackageManager.SIGNATURE_MATCH) { 9501 logCriticalInfo(Log.WARN, "Package " + ps.name + " appeared on system, but" 9502 + " signatures don't match existing userdata copy; removing"); 9503 try (PackageFreezer freezer = freezePackage(pkg.packageName, 9504 "scanPackageInternalLI")) { 9505 deletePackageLIF(pkg.packageName, null, true, null, 0, null, false, null); 9506 } 9507 ps = null; 9508 } else { 9509 /* 9510 * If the newly-added system app is an older version than the 9511 * already installed version, hide it. It will be scanned later 9512 * and re-added like an update. 9513 */ 9514 if (pkg.mVersionCode <= ps.versionCode) { 9515 shouldHideSystemApp = true; 9516 logCriticalInfo(Log.INFO, "Package " + ps.name + " appeared at " + scanFile 9517 + " but new version " + pkg.mVersionCode + " better than installed " 9518 + ps.versionCode + "; hiding system"); 9519 } else { 9520 /* 9521 * The newly found system app is a newer version that the 9522 * one previously installed. Simply remove the 9523 * already-installed application and replace it with our own 9524 * while keeping the application data. 9525 */ 9526 logCriticalInfo(Log.WARN, "Package " + ps.name + " at " + scanFile 9527 + " reverting from " + ps.codePathString + ": new version " 9528 + pkg.mVersionCode + " better than installed " + ps.versionCode); 9529 InstallArgs args = createInstallArgsForExisting(packageFlagsToInstallFlags(ps), 9530 ps.codePathString, ps.resourcePathString, getAppDexInstructionSets(ps)); 9531 synchronized (mInstallLock) { 9532 args.cleanUpResourcesLI(); 9533 } 9534 } 9535 } 9536 } 9537 9538 // The apk is forward locked (not public) if its code and resources 9539 // are kept in different files. (except for app in either system or 9540 // vendor path). 9541 // TODO grab this value from PackageSettings 9542 if ((policyFlags & PackageParser.PARSE_IS_SYSTEM_DIR) == 0) { 9543 if (ps != null && !ps.codePath.equals(ps.resourcePath)) { 9544 policyFlags |= PackageParser.PARSE_FORWARD_LOCK; 9545 } 9546 } 9547 9548 final int userId = ((user == null) ? 0 : user.getIdentifier()); 9549 if (ps != null && ps.getInstantApp(userId)) { 9550 scanFlags |= SCAN_AS_INSTANT_APP; 9551 } 9552 if (ps != null && ps.getVirtulalPreload(userId)) { 9553 scanFlags |= SCAN_AS_VIRTUAL_PRELOAD; 9554 } 9555 9556 // Note that we invoke the following method only if we are about to unpack an application 9557 PackageParser.Package scannedPkg = scanPackageLI(pkg, policyFlags, scanFlags 9558 | SCAN_UPDATE_SIGNATURE, currentTime, user); 9559 9560 /* 9561 * If the system app should be overridden by a previously installed 9562 * data, hide the system app now and let the /data/app scan pick it up 9563 * again. 9564 */ 9565 if (shouldHideSystemApp) { 9566 synchronized (mPackages) { 9567 mSettings.disableSystemPackageLPw(pkg.packageName, true); 9568 } 9569 } 9570 9571 return scannedPkg; 9572 } 9573 9574 private void renameStaticSharedLibraryPackage(PackageParser.Package pkg) { 9575 // Derive the new package synthetic package name 9576 pkg.setPackageName(pkg.packageName + STATIC_SHARED_LIB_DELIMITER 9577 + pkg.staticSharedLibVersion); 9578 } 9579 9580 private static String fixProcessName(String defProcessName, 9581 String processName) { 9582 if (processName == null) { 9583 return defProcessName; 9584 } 9585 return processName; 9586 } 9587 9588 private void verifySignaturesLP(PackageSetting pkgSetting, PackageParser.Package pkg) 9589 throws PackageManagerException { 9590 if (pkgSetting.signatures.mSignatures != null) { 9591 // Already existing package. Make sure signatures match 9592 boolean match = compareSignatures(pkgSetting.signatures.mSignatures, pkg.mSignatures) 9593 == PackageManager.SIGNATURE_MATCH; 9594 if (!match) { 9595 match = compareSignaturesCompat(pkgSetting.signatures, pkg) 9596 == PackageManager.SIGNATURE_MATCH; 9597 } 9598 if (!match) { 9599 match = compareSignaturesRecover(pkgSetting.signatures, pkg) 9600 == PackageManager.SIGNATURE_MATCH; 9601 } 9602 if (!match) { 9603 throw new PackageManagerException(INSTALL_FAILED_UPDATE_INCOMPATIBLE, "Package " 9604 + pkg.packageName + " signatures do not match the " 9605 + "previously installed version; ignoring!"); 9606 } 9607 } 9608 9609 // Check for shared user signatures 9610 if (pkgSetting.sharedUser != null && pkgSetting.sharedUser.signatures.mSignatures != null) { 9611 // Already existing package. Make sure signatures match 9612 boolean match = compareSignatures(pkgSetting.sharedUser.signatures.mSignatures, 9613 pkg.mSignatures) == PackageManager.SIGNATURE_MATCH; 9614 if (!match) { 9615 match = compareSignaturesCompat(pkgSetting.sharedUser.signatures, pkg) 9616 == PackageManager.SIGNATURE_MATCH; 9617 } 9618 if (!match) { 9619 match = compareSignaturesRecover(pkgSetting.sharedUser.signatures, pkg) 9620 == PackageManager.SIGNATURE_MATCH; 9621 } 9622 if (!match) { 9623 throw new PackageManagerException(INSTALL_FAILED_SHARED_USER_INCOMPATIBLE, 9624 "Package " + pkg.packageName 9625 + " has no signatures that match those in shared user " 9626 + pkgSetting.sharedUser.name + "; ignoring!"); 9627 } 9628 } 9629 } 9630 9631 /** 9632 * Enforces that only the system UID or root's UID can call a method exposed 9633 * via Binder. 9634 * 9635 * @param message used as message if SecurityException is thrown 9636 * @throws SecurityException if the caller is not system or root 9637 */ 9638 private static final void enforceSystemOrRoot(String message) { 9639 final int uid = Binder.getCallingUid(); 9640 if (uid != Process.SYSTEM_UID && uid != Process.ROOT_UID) { 9641 throw new SecurityException(message); 9642 } 9643 } 9644 9645 @Override 9646 public void performFstrimIfNeeded() { 9647 enforceSystemOrRoot("Only the system can request fstrim"); 9648 9649 // Before everything else, see whether we need to fstrim. 9650 try { 9651 IStorageManager sm = PackageHelper.getStorageManager(); 9652 if (sm != null) { 9653 boolean doTrim = false; 9654 final long interval = android.provider.Settings.Global.getLong( 9655 mContext.getContentResolver(), 9656 android.provider.Settings.Global.FSTRIM_MANDATORY_INTERVAL, 9657 DEFAULT_MANDATORY_FSTRIM_INTERVAL); 9658 if (interval > 0) { 9659 final long timeSinceLast = System.currentTimeMillis() - sm.lastMaintenance(); 9660 if (timeSinceLast > interval) { 9661 doTrim = true; 9662 Slog.w(TAG, "No disk maintenance in " + timeSinceLast 9663 + "; running immediately"); 9664 } 9665 } 9666 if (doTrim) { 9667 final boolean dexOptDialogShown; 9668 synchronized (mPackages) { 9669 dexOptDialogShown = mDexOptDialogShown; 9670 } 9671 if (!isFirstBoot() && dexOptDialogShown) { 9672 try { 9673 ActivityManager.getService().showBootMessage( 9674 mContext.getResources().getString( 9675 R.string.android_upgrading_fstrim), true); 9676 } catch (RemoteException e) { 9677 } 9678 } 9679 sm.runMaintenance(); 9680 } 9681 } else { 9682 Slog.e(TAG, "storageManager service unavailable!"); 9683 } 9684 } catch (RemoteException e) { 9685 // Can't happen; StorageManagerService is local 9686 } 9687 } 9688 9689 @Override 9690 public void updatePackagesIfNeeded() { 9691 enforceSystemOrRoot("Only the system can request package update"); 9692 9693 // We need to re-extract after an OTA. 9694 boolean causeUpgrade = isUpgrade(); 9695 9696 // First boot or factory reset. 9697 // Note: we also handle devices that are upgrading to N right now as if it is their 9698 // first boot, as they do not have profile data. 9699 boolean causeFirstBoot = isFirstBoot() || mIsPreNUpgrade; 9700 9701 // We need to re-extract after a pruned cache, as AoT-ed files will be out of date. 9702 boolean causePrunedCache = VMRuntime.didPruneDalvikCache(); 9703 9704 if (!causeUpgrade && !causeFirstBoot && !causePrunedCache) { 9705 return; 9706 } 9707 9708 List<PackageParser.Package> pkgs; 9709 synchronized (mPackages) { 9710 pkgs = PackageManagerServiceUtils.getPackagesForDexopt(mPackages.values(), this); 9711 } 9712 9713 final long startTime = System.nanoTime(); 9714 final int[] stats = performDexOptUpgrade(pkgs, mIsPreNUpgrade /* showDialog */, 9715 getCompilerFilterForReason(causeFirstBoot ? REASON_FIRST_BOOT : REASON_BOOT), 9716 false /* bootComplete */); 9717 9718 final int elapsedTimeSeconds = 9719 (int) TimeUnit.NANOSECONDS.toSeconds(System.nanoTime() - startTime); 9720 9721 MetricsLogger.histogram(mContext, "opt_dialog_num_dexopted", stats[0]); 9722 MetricsLogger.histogram(mContext, "opt_dialog_num_skipped", stats[1]); 9723 MetricsLogger.histogram(mContext, "opt_dialog_num_failed", stats[2]); 9724 MetricsLogger.histogram(mContext, "opt_dialog_num_total", getOptimizablePackages().size()); 9725 MetricsLogger.histogram(mContext, "opt_dialog_time_s", elapsedTimeSeconds); 9726 } 9727 9728 /* 9729 * Return the prebuilt profile path given a package base code path. 9730 */ 9731 private static String getPrebuildProfilePath(PackageParser.Package pkg) { 9732 return pkg.baseCodePath + ".prof"; 9733 } 9734 9735 /** 9736 * Performs dexopt on the set of packages in {@code packages} and returns an int array 9737 * containing statistics about the invocation. The array consists of three elements, 9738 * which are (in order) {@code numberOfPackagesOptimized}, {@code numberOfPackagesSkipped} 9739 * and {@code numberOfPackagesFailed}. 9740 */ 9741 private int[] performDexOptUpgrade(List<PackageParser.Package> pkgs, boolean showDialog, 9742 final String compilerFilter, boolean bootComplete) { 9743 9744 int numberOfPackagesVisited = 0; 9745 int numberOfPackagesOptimized = 0; 9746 int numberOfPackagesSkipped = 0; 9747 int numberOfPackagesFailed = 0; 9748 final int numberOfPackagesToDexopt = pkgs.size(); 9749 9750 for (PackageParser.Package pkg : pkgs) { 9751 numberOfPackagesVisited++; 9752 9753 boolean useProfileForDexopt = false; 9754 9755 if ((isFirstBoot() || isUpgrade()) && isSystemApp(pkg)) { 9756 // Copy over initial preopt profiles since we won't get any JIT samples for methods 9757 // that are already compiled. 9758 File profileFile = new File(getPrebuildProfilePath(pkg)); 9759 // Copy profile if it exists. 9760 if (profileFile.exists()) { 9761 try { 9762 // We could also do this lazily before calling dexopt in 9763 // PackageDexOptimizer to prevent this happening on first boot. The issue 9764 // is that we don't have a good way to say "do this only once". 9765 if (!mInstaller.copySystemProfile(profileFile.getAbsolutePath(), 9766 pkg.applicationInfo.uid, pkg.packageName)) { 9767 Log.e(TAG, "Installer failed to copy system profile!"); 9768 } else { 9769 // Disabled as this causes speed-profile compilation during first boot 9770 // even if things are already compiled. 9771 // useProfileForDexopt = true; 9772 } 9773 } catch (Exception e) { 9774 Log.e(TAG, "Failed to copy profile " + profileFile.getAbsolutePath() + " ", 9775 e); 9776 } 9777 } else { 9778 PackageSetting disabledPs = mSettings.getDisabledSystemPkgLPr(pkg.packageName); 9779 // Handle compressed APKs in this path. Only do this for stubs with profiles to 9780 // minimize the number off apps being speed-profile compiled during first boot. 9781 // The other paths will not change the filter. 9782 if (disabledPs != null && disabledPs.pkg.isStub) { 9783 // The package is the stub one, remove the stub suffix to get the normal 9784 // package and APK names. 9785 String systemProfilePath = 9786 getPrebuildProfilePath(disabledPs.pkg).replace(STUB_SUFFIX, ""); 9787 profileFile = new File(systemProfilePath); 9788 // If we have a profile for a compressed APK, copy it to the reference 9789 // location. 9790 // Note that copying the profile here will cause it to override the 9791 // reference profile every OTA even though the existing reference profile 9792 // may have more data. We can't copy during decompression since the 9793 // directories are not set up at that point. 9794 if (profileFile.exists()) { 9795 try { 9796 // We could also do this lazily before calling dexopt in 9797 // PackageDexOptimizer to prevent this happening on first boot. The 9798 // issue is that we don't have a good way to say "do this only 9799 // once". 9800 if (!mInstaller.copySystemProfile(profileFile.getAbsolutePath(), 9801 pkg.applicationInfo.uid, pkg.packageName)) { 9802 Log.e(TAG, "Failed to copy system profile for stub package!"); 9803 } else { 9804 useProfileForDexopt = true; 9805 } 9806 } catch (Exception e) { 9807 Log.e(TAG, "Failed to copy profile " + 9808 profileFile.getAbsolutePath() + " ", e); 9809 } 9810 } 9811 } 9812 } 9813 } 9814 9815 if (!PackageDexOptimizer.canOptimizePackage(pkg)) { 9816 if (DEBUG_DEXOPT) { 9817 Log.i(TAG, "Skipping update of of non-optimizable app " + pkg.packageName); 9818 } 9819 numberOfPackagesSkipped++; 9820 continue; 9821 } 9822 9823 if (DEBUG_DEXOPT) { 9824 Log.i(TAG, "Updating app " + numberOfPackagesVisited + " of " + 9825 numberOfPackagesToDexopt + ": " + pkg.packageName); 9826 } 9827 9828 if (showDialog) { 9829 try { 9830 ActivityManager.getService().showBootMessage( 9831 mContext.getResources().getString(R.string.android_upgrading_apk, 9832 numberOfPackagesVisited, numberOfPackagesToDexopt), true); 9833 } catch (RemoteException e) { 9834 } 9835 synchronized (mPackages) { 9836 mDexOptDialogShown = true; 9837 } 9838 } 9839 9840 String pkgCompilerFilter = compilerFilter; 9841 if (useProfileForDexopt) { 9842 // Use background dexopt mode to try and use the profile. Note that this does not 9843 // guarantee usage of the profile. 9844 pkgCompilerFilter = 9845 PackageManagerServiceCompilerMapping.getCompilerFilterForReason( 9846 PackageManagerService.REASON_BACKGROUND_DEXOPT); 9847 } 9848 9849 // checkProfiles is false to avoid merging profiles during boot which 9850 // might interfere with background compilation (b/28612421). 9851 // Unfortunately this will also means that "pm.dexopt.boot=speed-profile" will 9852 // behave differently than "pm.dexopt.bg-dexopt=speed-profile" but that's a 9853 // trade-off worth doing to save boot time work. 9854 int dexoptFlags = bootComplete ? DexoptOptions.DEXOPT_BOOT_COMPLETE : 0; 9855 int primaryDexOptStaus = performDexOptTraced(new DexoptOptions( 9856 pkg.packageName, 9857 pkgCompilerFilter, 9858 dexoptFlags)); 9859 9860 switch (primaryDexOptStaus) { 9861 case PackageDexOptimizer.DEX_OPT_PERFORMED: 9862 numberOfPackagesOptimized++; 9863 break; 9864 case PackageDexOptimizer.DEX_OPT_SKIPPED: 9865 numberOfPackagesSkipped++; 9866 break; 9867 case PackageDexOptimizer.DEX_OPT_FAILED: 9868 numberOfPackagesFailed++; 9869 break; 9870 default: 9871 Log.e(TAG, "Unexpected dexopt return code " + primaryDexOptStaus); 9872 break; 9873 } 9874 } 9875 9876 return new int[] { numberOfPackagesOptimized, numberOfPackagesSkipped, 9877 numberOfPackagesFailed }; 9878 } 9879 9880 @Override 9881 public void notifyPackageUse(String packageName, int reason) { 9882 synchronized (mPackages) { 9883 final int callingUid = Binder.getCallingUid(); 9884 final int callingUserId = UserHandle.getUserId(callingUid); 9885 if (getInstantAppPackageName(callingUid) != null) { 9886 if (!isCallerSameApp(packageName, callingUid)) { 9887 return; 9888 } 9889 } else { 9890 if (isInstantApp(packageName, callingUserId)) { 9891 return; 9892 } 9893 } 9894 notifyPackageUseLocked(packageName, reason); 9895 } 9896 } 9897 9898 private void notifyPackageUseLocked(String packageName, int reason) { 9899 final PackageParser.Package p = mPackages.get(packageName); 9900 if (p == null) { 9901 return; 9902 } 9903 p.mLastPackageUsageTimeInMills[reason] = System.currentTimeMillis(); 9904 } 9905 9906 @Override 9907 public void notifyDexLoad(String loadingPackageName, List<String> classLoaderNames, 9908 List<String> classPaths, String loaderIsa) { 9909 int userId = UserHandle.getCallingUserId(); 9910 ApplicationInfo ai = getApplicationInfo(loadingPackageName, /*flags*/ 0, userId); 9911 if (ai == null) { 9912 Slog.w(TAG, "Loading a package that does not exist for the calling user. package=" 9913 + loadingPackageName + ", user=" + userId); 9914 return; 9915 } 9916 mDexManager.notifyDexLoad(ai, classLoaderNames, classPaths, loaderIsa, userId); 9917 } 9918 9919 @Override 9920 public void registerDexModule(String packageName, String dexModulePath, boolean isSharedModule, 9921 IDexModuleRegisterCallback callback) { 9922 int userId = UserHandle.getCallingUserId(); 9923 ApplicationInfo ai = getApplicationInfo(packageName, /*flags*/ 0, userId); 9924 DexManager.RegisterDexModuleResult result; 9925 if (ai == null) { 9926 Slog.w(TAG, "Registering a dex module for a package that does not exist for the" + 9927 " calling user. package=" + packageName + ", user=" + userId); 9928 result = new DexManager.RegisterDexModuleResult(false, "Package not installed"); 9929 } else { 9930 result = mDexManager.registerDexModule(ai, dexModulePath, isSharedModule, userId); 9931 } 9932 9933 if (callback != null) { 9934 mHandler.post(() -> { 9935 try { 9936 callback.onDexModuleRegistered(dexModulePath, result.success, result.message); 9937 } catch (RemoteException e) { 9938 Slog.w(TAG, "Failed to callback after module registration " + dexModulePath, e); 9939 } 9940 }); 9941 } 9942 } 9943 9944 /** 9945 * Ask the package manager to perform a dex-opt with the given compiler filter. 9946 * 9947 * Note: exposed only for the shell command to allow moving packages explicitly to a 9948 * definite state. 9949 */ 9950 @Override 9951 public boolean performDexOptMode(String packageName, 9952 boolean checkProfiles, String targetCompilerFilter, boolean force, 9953 boolean bootComplete, String splitName) { 9954 int flags = (checkProfiles ? DexoptOptions.DEXOPT_CHECK_FOR_PROFILES_UPDATES : 0) | 9955 (force ? DexoptOptions.DEXOPT_FORCE : 0) | 9956 (bootComplete ? DexoptOptions.DEXOPT_BOOT_COMPLETE : 0); 9957 return performDexOpt(new DexoptOptions(packageName, targetCompilerFilter, 9958 splitName, flags)); 9959 } 9960 9961 /** 9962 * Ask the package manager to perform a dex-opt with the given compiler filter on the 9963 * secondary dex files belonging to the given package. 9964 * 9965 * Note: exposed only for the shell command to allow moving packages explicitly to a 9966 * definite state. 9967 */ 9968 @Override 9969 public boolean performDexOptSecondary(String packageName, String compilerFilter, 9970 boolean force) { 9971 int flags = DexoptOptions.DEXOPT_ONLY_SECONDARY_DEX | 9972 DexoptOptions.DEXOPT_CHECK_FOR_PROFILES_UPDATES | 9973 DexoptOptions.DEXOPT_BOOT_COMPLETE | 9974 (force ? DexoptOptions.DEXOPT_FORCE : 0); 9975 return performDexOpt(new DexoptOptions(packageName, compilerFilter, flags)); 9976 } 9977 9978 /*package*/ boolean performDexOpt(DexoptOptions options) { 9979 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 9980 return false; 9981 } else if (isInstantApp(options.getPackageName(), UserHandle.getCallingUserId())) { 9982 return false; 9983 } 9984 9985 if (options.isDexoptOnlySecondaryDex()) { 9986 return mDexManager.dexoptSecondaryDex(options); 9987 } else { 9988 int dexoptStatus = performDexOptWithStatus(options); 9989 return dexoptStatus != PackageDexOptimizer.DEX_OPT_FAILED; 9990 } 9991 } 9992 9993 /** 9994 * Perform dexopt on the given package and return one of following result: 9995 * {@link PackageDexOptimizer#DEX_OPT_SKIPPED} 9996 * {@link PackageDexOptimizer#DEX_OPT_PERFORMED} 9997 * {@link PackageDexOptimizer#DEX_OPT_FAILED} 9998 */ 9999 /* package */ int performDexOptWithStatus(DexoptOptions options) { 10000 return performDexOptTraced(options); 10001 } 10002 10003 private int performDexOptTraced(DexoptOptions options) { 10004 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "dexopt"); 10005 try { 10006 return performDexOptInternal(options); 10007 } finally { 10008 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 10009 } 10010 } 10011 10012 // Run dexopt on a given package. Returns true if dexopt did not fail, i.e. 10013 // if the package can now be considered up to date for the given filter. 10014 private int performDexOptInternal(DexoptOptions options) { 10015 PackageParser.Package p; 10016 synchronized (mPackages) { 10017 p = mPackages.get(options.getPackageName()); 10018 if (p == null) { 10019 // Package could not be found. Report failure. 10020 return PackageDexOptimizer.DEX_OPT_FAILED; 10021 } 10022 mPackageUsage.maybeWriteAsync(mPackages); 10023 mCompilerStats.maybeWriteAsync(); 10024 } 10025 long callingId = Binder.clearCallingIdentity(); 10026 try { 10027 synchronized (mInstallLock) { 10028 return performDexOptInternalWithDependenciesLI(p, options); 10029 } 10030 } finally { 10031 Binder.restoreCallingIdentity(callingId); 10032 } 10033 } 10034 10035 public ArraySet<String> getOptimizablePackages() { 10036 ArraySet<String> pkgs = new ArraySet<String>(); 10037 synchronized (mPackages) { 10038 for (PackageParser.Package p : mPackages.values()) { 10039 if (PackageDexOptimizer.canOptimizePackage(p)) { 10040 pkgs.add(p.packageName); 10041 } 10042 } 10043 } 10044 return pkgs; 10045 } 10046 10047 private int performDexOptInternalWithDependenciesLI(PackageParser.Package p, 10048 DexoptOptions options) { 10049 // Select the dex optimizer based on the force parameter. 10050 // Note: The force option is rarely used (cmdline input for testing, mostly), so it's OK to 10051 // allocate an object here. 10052 PackageDexOptimizer pdo = options.isForce() 10053 ? new PackageDexOptimizer.ForcedUpdatePackageDexOptimizer(mPackageDexOptimizer) 10054 : mPackageDexOptimizer; 10055 10056 // Dexopt all dependencies first. Note: we ignore the return value and march on 10057 // on errors. 10058 // Note that we are going to call performDexOpt on those libraries as many times as 10059 // they are referenced in packages. When we do a batch of performDexOpt (for example 10060 // at boot, or background job), the passed 'targetCompilerFilter' stays the same, 10061 // and the first package that uses the library will dexopt it. The 10062 // others will see that the compiled code for the library is up to date. 10063 Collection<PackageParser.Package> deps = findSharedNonSystemLibraries(p); 10064 final String[] instructionSets = getAppDexInstructionSets(p.applicationInfo); 10065 if (!deps.isEmpty()) { 10066 DexoptOptions libraryOptions = new DexoptOptions(options.getPackageName(), 10067 options.getCompilerFilter(), options.getSplitName(), 10068 options.getFlags() | DexoptOptions.DEXOPT_AS_SHARED_LIBRARY); 10069 for (PackageParser.Package depPackage : deps) { 10070 // TODO: Analyze and investigate if we (should) profile libraries. 10071 pdo.performDexOpt(depPackage, null /* sharedLibraries */, instructionSets, 10072 getOrCreateCompilerPackageStats(depPackage), 10073 mDexManager.getPackageUseInfoOrDefault(depPackage.packageName), libraryOptions); 10074 } 10075 } 10076 return pdo.performDexOpt(p, p.usesLibraryFiles, instructionSets, 10077 getOrCreateCompilerPackageStats(p), 10078 mDexManager.getPackageUseInfoOrDefault(p.packageName), options); 10079 } 10080 10081 /** 10082 * Reconcile the information we have about the secondary dex files belonging to 10083 * {@code packagName} and the actual dex files. For all dex files that were 10084 * deleted, update the internal records and delete the generated oat files. 10085 */ 10086 @Override 10087 public void reconcileSecondaryDexFiles(String packageName) { 10088 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 10089 return; 10090 } else if (isInstantApp(packageName, UserHandle.getCallingUserId())) { 10091 return; 10092 } 10093 mDexManager.reconcileSecondaryDexFiles(packageName); 10094 } 10095 10096 // TODO(calin): this is only needed for BackgroundDexOptService. Find a cleaner way to inject 10097 // a reference there. 10098 /*package*/ DexManager getDexManager() { 10099 return mDexManager; 10100 } 10101 10102 /** 10103 * Execute the background dexopt job immediately. 10104 */ 10105 @Override 10106 public boolean runBackgroundDexoptJob() { 10107 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 10108 return false; 10109 } 10110 return BackgroundDexOptService.runIdleOptimizationsNow(this, mContext); 10111 } 10112 10113 List<PackageParser.Package> findSharedNonSystemLibraries(PackageParser.Package p) { 10114 if (p.usesLibraries != null || p.usesOptionalLibraries != null 10115 || p.usesStaticLibraries != null) { 10116 ArrayList<PackageParser.Package> retValue = new ArrayList<>(); 10117 Set<String> collectedNames = new HashSet<>(); 10118 findSharedNonSystemLibrariesRecursive(p, retValue, collectedNames); 10119 10120 retValue.remove(p); 10121 10122 return retValue; 10123 } else { 10124 return Collections.emptyList(); 10125 } 10126 } 10127 10128 private void findSharedNonSystemLibrariesRecursive(PackageParser.Package p, 10129 ArrayList<PackageParser.Package> collected, Set<String> collectedNames) { 10130 if (!collectedNames.contains(p.packageName)) { 10131 collectedNames.add(p.packageName); 10132 collected.add(p); 10133 10134 if (p.usesLibraries != null) { 10135 findSharedNonSystemLibrariesRecursive(p.usesLibraries, 10136 null, collected, collectedNames); 10137 } 10138 if (p.usesOptionalLibraries != null) { 10139 findSharedNonSystemLibrariesRecursive(p.usesOptionalLibraries, 10140 null, collected, collectedNames); 10141 } 10142 if (p.usesStaticLibraries != null) { 10143 findSharedNonSystemLibrariesRecursive(p.usesStaticLibraries, 10144 p.usesStaticLibrariesVersions, collected, collectedNames); 10145 } 10146 } 10147 } 10148 10149 private void findSharedNonSystemLibrariesRecursive(ArrayList<String> libs, int[] versions, 10150 ArrayList<PackageParser.Package> collected, Set<String> collectedNames) { 10151 final int libNameCount = libs.size(); 10152 for (int i = 0; i < libNameCount; i++) { 10153 String libName = libs.get(i); 10154 int version = (versions != null && versions.length == libNameCount) 10155 ? versions[i] : PackageManager.VERSION_CODE_HIGHEST; 10156 PackageParser.Package libPkg = findSharedNonSystemLibrary(libName, version); 10157 if (libPkg != null) { 10158 findSharedNonSystemLibrariesRecursive(libPkg, collected, collectedNames); 10159 } 10160 } 10161 } 10162 10163 private PackageParser.Package findSharedNonSystemLibrary(String name, int version) { 10164 synchronized (mPackages) { 10165 SharedLibraryEntry libEntry = getSharedLibraryEntryLPr(name, version); 10166 if (libEntry != null) { 10167 return mPackages.get(libEntry.apk); 10168 } 10169 return null; 10170 } 10171 } 10172 10173 private SharedLibraryEntry getSharedLibraryEntryLPr(String name, int version) { 10174 SparseArray<SharedLibraryEntry> versionedLib = mSharedLibraries.get(name); 10175 if (versionedLib == null) { 10176 return null; 10177 } 10178 return versionedLib.get(version); 10179 } 10180 10181 private SharedLibraryEntry getLatestSharedLibraVersionLPr(PackageParser.Package pkg) { 10182 SparseArray<SharedLibraryEntry> versionedLib = mSharedLibraries.get( 10183 pkg.staticSharedLibName); 10184 if (versionedLib == null) { 10185 return null; 10186 } 10187 int previousLibVersion = -1; 10188 final int versionCount = versionedLib.size(); 10189 for (int i = 0; i < versionCount; i++) { 10190 final int libVersion = versionedLib.keyAt(i); 10191 if (libVersion < pkg.staticSharedLibVersion) { 10192 previousLibVersion = Math.max(previousLibVersion, libVersion); 10193 } 10194 } 10195 if (previousLibVersion >= 0) { 10196 return versionedLib.get(previousLibVersion); 10197 } 10198 return null; 10199 } 10200 10201 public void shutdown() { 10202 mPackageUsage.writeNow(mPackages); 10203 mCompilerStats.writeNow(); 10204 mDexManager.writePackageDexUsageNow(); 10205 } 10206 10207 @Override 10208 public void dumpProfiles(String packageName) { 10209 PackageParser.Package pkg; 10210 synchronized (mPackages) { 10211 pkg = mPackages.get(packageName); 10212 if (pkg == null) { 10213 throw new IllegalArgumentException("Unknown package: " + packageName); 10214 } 10215 } 10216 /* Only the shell, root, or the app user should be able to dump profiles. */ 10217 int callingUid = Binder.getCallingUid(); 10218 if (callingUid != Process.SHELL_UID && 10219 callingUid != Process.ROOT_UID && 10220 callingUid != pkg.applicationInfo.uid) { 10221 throw new SecurityException("dumpProfiles"); 10222 } 10223 10224 synchronized (mInstallLock) { 10225 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "dump profiles"); 10226 final int sharedGid = UserHandle.getSharedAppGid(pkg.applicationInfo.uid); 10227 try { 10228 List<String> allCodePaths = pkg.getAllCodePathsExcludingResourceOnly(); 10229 String codePaths = TextUtils.join(";", allCodePaths); 10230 mInstaller.dumpProfiles(sharedGid, packageName, codePaths); 10231 } catch (InstallerException e) { 10232 Slog.w(TAG, "Failed to dump profiles", e); 10233 } 10234 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 10235 } 10236 } 10237 10238 @Override 10239 public void forceDexOpt(String packageName) { 10240 enforceSystemOrRoot("forceDexOpt"); 10241 10242 PackageParser.Package pkg; 10243 synchronized (mPackages) { 10244 pkg = mPackages.get(packageName); 10245 if (pkg == null) { 10246 throw new IllegalArgumentException("Unknown package: " + packageName); 10247 } 10248 } 10249 10250 synchronized (mInstallLock) { 10251 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "dexopt"); 10252 10253 // Whoever is calling forceDexOpt wants a compiled package. 10254 // Don't use profiles since that may cause compilation to be skipped. 10255 final int res = performDexOptInternalWithDependenciesLI( 10256 pkg, 10257 new DexoptOptions(packageName, 10258 getDefaultCompilerFilter(), 10259 DexoptOptions.DEXOPT_FORCE | DexoptOptions.DEXOPT_BOOT_COMPLETE)); 10260 10261 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 10262 if (res != PackageDexOptimizer.DEX_OPT_PERFORMED) { 10263 throw new IllegalStateException("Failed to dexopt: " + res); 10264 } 10265 } 10266 } 10267 10268 private boolean verifyPackageUpdateLPr(PackageSetting oldPkg, PackageParser.Package newPkg) { 10269 if ((oldPkg.pkgFlags&ApplicationInfo.FLAG_SYSTEM) == 0) { 10270 Slog.w(TAG, "Unable to update from " + oldPkg.name 10271 + " to " + newPkg.packageName 10272 + ": old package not in system partition"); 10273 return false; 10274 } else if (mPackages.get(oldPkg.name) != null) { 10275 Slog.w(TAG, "Unable to update from " + oldPkg.name 10276 + " to " + newPkg.packageName 10277 + ": old package still exists"); 10278 return false; 10279 } 10280 return true; 10281 } 10282 10283 void removeCodePathLI(File codePath) { 10284 if (codePath.isDirectory()) { 10285 try { 10286 mInstaller.rmPackageDir(codePath.getAbsolutePath()); 10287 } catch (InstallerException e) { 10288 Slog.w(TAG, "Failed to remove code path", e); 10289 } 10290 } else { 10291 codePath.delete(); 10292 } 10293 } 10294 10295 private int[] resolveUserIds(int userId) { 10296 return (userId == UserHandle.USER_ALL) ? sUserManager.getUserIds() : new int[] { userId }; 10297 } 10298 10299 private void clearAppDataLIF(PackageParser.Package pkg, int userId, int flags) { 10300 if (pkg == null) { 10301 Slog.wtf(TAG, "Package was null!", new Throwable()); 10302 return; 10303 } 10304 clearAppDataLeafLIF(pkg, userId, flags); 10305 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 10306 for (int i = 0; i < childCount; i++) { 10307 clearAppDataLeafLIF(pkg.childPackages.get(i), userId, flags); 10308 } 10309 } 10310 10311 private void clearAppDataLeafLIF(PackageParser.Package pkg, int userId, int flags) { 10312 final PackageSetting ps; 10313 synchronized (mPackages) { 10314 ps = mSettings.mPackages.get(pkg.packageName); 10315 } 10316 for (int realUserId : resolveUserIds(userId)) { 10317 final long ceDataInode = (ps != null) ? ps.getCeDataInode(realUserId) : 0; 10318 try { 10319 mInstaller.clearAppData(pkg.volumeUuid, pkg.packageName, realUserId, flags, 10320 ceDataInode); 10321 } catch (InstallerException e) { 10322 Slog.w(TAG, String.valueOf(e)); 10323 } 10324 } 10325 } 10326 10327 private void destroyAppDataLIF(PackageParser.Package pkg, int userId, int flags) { 10328 if (pkg == null) { 10329 Slog.wtf(TAG, "Package was null!", new Throwable()); 10330 return; 10331 } 10332 destroyAppDataLeafLIF(pkg, userId, flags); 10333 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 10334 for (int i = 0; i < childCount; i++) { 10335 destroyAppDataLeafLIF(pkg.childPackages.get(i), userId, flags); 10336 } 10337 } 10338 10339 private void destroyAppDataLeafLIF(PackageParser.Package pkg, int userId, int flags) { 10340 final PackageSetting ps; 10341 synchronized (mPackages) { 10342 ps = mSettings.mPackages.get(pkg.packageName); 10343 } 10344 for (int realUserId : resolveUserIds(userId)) { 10345 final long ceDataInode = (ps != null) ? ps.getCeDataInode(realUserId) : 0; 10346 try { 10347 mInstaller.destroyAppData(pkg.volumeUuid, pkg.packageName, realUserId, flags, 10348 ceDataInode); 10349 } catch (InstallerException e) { 10350 Slog.w(TAG, String.valueOf(e)); 10351 } 10352 mDexManager.notifyPackageDataDestroyed(pkg.packageName, userId); 10353 } 10354 } 10355 10356 private void destroyAppProfilesLIF(PackageParser.Package pkg, int userId) { 10357 if (pkg == null) { 10358 Slog.wtf(TAG, "Package was null!", new Throwable()); 10359 return; 10360 } 10361 destroyAppProfilesLeafLIF(pkg); 10362 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 10363 for (int i = 0; i < childCount; i++) { 10364 destroyAppProfilesLeafLIF(pkg.childPackages.get(i)); 10365 } 10366 } 10367 10368 private void destroyAppProfilesLeafLIF(PackageParser.Package pkg) { 10369 try { 10370 mInstaller.destroyAppProfiles(pkg.packageName); 10371 } catch (InstallerException e) { 10372 Slog.w(TAG, String.valueOf(e)); 10373 } 10374 } 10375 10376 private void clearAppProfilesLIF(PackageParser.Package pkg, int userId) { 10377 if (pkg == null) { 10378 Slog.wtf(TAG, "Package was null!", new Throwable()); 10379 return; 10380 } 10381 clearAppProfilesLeafLIF(pkg); 10382 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 10383 for (int i = 0; i < childCount; i++) { 10384 clearAppProfilesLeafLIF(pkg.childPackages.get(i)); 10385 } 10386 } 10387 10388 private void clearAppProfilesLeafLIF(PackageParser.Package pkg) { 10389 try { 10390 mInstaller.clearAppProfiles(pkg.packageName); 10391 } catch (InstallerException e) { 10392 Slog.w(TAG, String.valueOf(e)); 10393 } 10394 } 10395 10396 private void setInstallAndUpdateTime(PackageParser.Package pkg, long firstInstallTime, 10397 long lastUpdateTime) { 10398 // Set parent install/update time 10399 PackageSetting ps = (PackageSetting) pkg.mExtras; 10400 if (ps != null) { 10401 ps.firstInstallTime = firstInstallTime; 10402 ps.lastUpdateTime = lastUpdateTime; 10403 } 10404 // Set children install/update time 10405 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 10406 for (int i = 0; i < childCount; i++) { 10407 PackageParser.Package childPkg = pkg.childPackages.get(i); 10408 ps = (PackageSetting) childPkg.mExtras; 10409 if (ps != null) { 10410 ps.firstInstallTime = firstInstallTime; 10411 ps.lastUpdateTime = lastUpdateTime; 10412 } 10413 } 10414 } 10415 10416 private void addSharedLibraryLPr(ArraySet<String> usesLibraryFiles, SharedLibraryEntry file, 10417 PackageParser.Package changingLib) { 10418 if (file.path != null) { 10419 usesLibraryFiles.add(file.path); 10420 return; 10421 } 10422 PackageParser.Package p = mPackages.get(file.apk); 10423 if (changingLib != null && changingLib.packageName.equals(file.apk)) { 10424 // If we are doing this while in the middle of updating a library apk, 10425 // then we need to make sure to use that new apk for determining the 10426 // dependencies here. (We haven't yet finished committing the new apk 10427 // to the package manager state.) 10428 if (p == null || p.packageName.equals(changingLib.packageName)) { 10429 p = changingLib; 10430 } 10431 } 10432 if (p != null) { 10433 usesLibraryFiles.addAll(p.getAllCodePaths()); 10434 if (p.usesLibraryFiles != null) { 10435 Collections.addAll(usesLibraryFiles, p.usesLibraryFiles); 10436 } 10437 } 10438 } 10439 10440 private void updateSharedLibrariesLPr(PackageParser.Package pkg, 10441 PackageParser.Package changingLib) throws PackageManagerException { 10442 if (pkg == null) { 10443 return; 10444 } 10445 ArraySet<String> usesLibraryFiles = null; 10446 if (pkg.usesLibraries != null) { 10447 usesLibraryFiles = addSharedLibrariesLPw(pkg.usesLibraries, 10448 null, null, pkg.packageName, changingLib, true, 10449 pkg.applicationInfo.targetSdkVersion, null); 10450 } 10451 if (pkg.usesStaticLibraries != null) { 10452 usesLibraryFiles = addSharedLibrariesLPw(pkg.usesStaticLibraries, 10453 pkg.usesStaticLibrariesVersions, pkg.usesStaticLibrariesCertDigests, 10454 pkg.packageName, changingLib, true, 10455 pkg.applicationInfo.targetSdkVersion, usesLibraryFiles); 10456 } 10457 if (pkg.usesOptionalLibraries != null) { 10458 usesLibraryFiles = addSharedLibrariesLPw(pkg.usesOptionalLibraries, 10459 null, null, pkg.packageName, changingLib, false, 10460 pkg.applicationInfo.targetSdkVersion, usesLibraryFiles); 10461 } 10462 if (!ArrayUtils.isEmpty(usesLibraryFiles)) { 10463 pkg.usesLibraryFiles = usesLibraryFiles.toArray(new String[usesLibraryFiles.size()]); 10464 } else { 10465 pkg.usesLibraryFiles = null; 10466 } 10467 } 10468 10469 private ArraySet<String> addSharedLibrariesLPw(@NonNull List<String> requestedLibraries, 10470 @Nullable int[] requiredVersions, @Nullable String[][] requiredCertDigests, 10471 @NonNull String packageName, @Nullable PackageParser.Package changingLib, 10472 boolean required, int targetSdk, @Nullable ArraySet<String> outUsedLibraries) 10473 throws PackageManagerException { 10474 final int libCount = requestedLibraries.size(); 10475 for (int i = 0; i < libCount; i++) { 10476 final String libName = requestedLibraries.get(i); 10477 final int libVersion = requiredVersions != null ? requiredVersions[i] 10478 : SharedLibraryInfo.VERSION_UNDEFINED; 10479 final SharedLibraryEntry libEntry = getSharedLibraryEntryLPr(libName, libVersion); 10480 if (libEntry == null) { 10481 if (required) { 10482 throw new PackageManagerException(INSTALL_FAILED_MISSING_SHARED_LIBRARY, 10483 "Package " + packageName + " requires unavailable shared library " 10484 + libName + "; failing!"); 10485 } else if (DEBUG_SHARED_LIBRARIES) { 10486 Slog.i(TAG, "Package " + packageName 10487 + " desires unavailable shared library " 10488 + libName + "; ignoring!"); 10489 } 10490 } else { 10491 if (requiredVersions != null && requiredCertDigests != null) { 10492 if (libEntry.info.getVersion() != requiredVersions[i]) { 10493 throw new PackageManagerException(INSTALL_FAILED_MISSING_SHARED_LIBRARY, 10494 "Package " + packageName + " requires unavailable static shared" 10495 + " library " + libName + " version " 10496 + libEntry.info.getVersion() + "; failing!"); 10497 } 10498 10499 PackageParser.Package libPkg = mPackages.get(libEntry.apk); 10500 if (libPkg == null) { 10501 throw new PackageManagerException(INSTALL_FAILED_MISSING_SHARED_LIBRARY, 10502 "Package " + packageName + " requires unavailable static shared" 10503 + " library; failing!"); 10504 } 10505 10506 final String[] expectedCertDigests = requiredCertDigests[i]; 10507 // For apps targeting O MR1 we require explicit enumeration of all certs. 10508 final String[] libCertDigests = (targetSdk > Build.VERSION_CODES.O) 10509 ? PackageUtils.computeSignaturesSha256Digests(libPkg.mSignatures) 10510 : PackageUtils.computeSignaturesSha256Digests( 10511 new Signature[]{libPkg.mSignatures[0]}); 10512 10513 // Take a shortcut if sizes don't match. Note that if an app doesn't 10514 // target O we don't parse the "additional-certificate" tags similarly 10515 // how we only consider all certs only for apps targeting O (see above). 10516 // Therefore, the size check is safe to make. 10517 if (expectedCertDigests.length != libCertDigests.length) { 10518 throw new PackageManagerException(INSTALL_FAILED_MISSING_SHARED_LIBRARY, 10519 "Package " + packageName + " requires differently signed" + 10520 " static sDexLoadReporter.java:45.19hared library; failing!"); 10521 } 10522 10523 // Use a predictable order as signature order may vary 10524 Arrays.sort(libCertDigests); 10525 Arrays.sort(expectedCertDigests); 10526 10527 final int certCount = libCertDigests.length; 10528 for (int j = 0; j < certCount; j++) { 10529 if (!libCertDigests[j].equalsIgnoreCase(expectedCertDigests[j])) { 10530 throw new PackageManagerException(INSTALL_FAILED_MISSING_SHARED_LIBRARY, 10531 "Package " + packageName + " requires differently signed" + 10532 " static shared library; failing!"); 10533 } 10534 } 10535 } 10536 10537 if (outUsedLibraries == null) { 10538 outUsedLibraries = new ArraySet<>(); 10539 } 10540 addSharedLibraryLPr(outUsedLibraries, libEntry, changingLib); 10541 } 10542 } 10543 return outUsedLibraries; 10544 } 10545 10546 private static boolean hasString(List<String> list, List<String> which) { 10547 if (list == null) { 10548 return false; 10549 } 10550 for (int i=list.size()-1; i>=0; i--) { 10551 for (int j=which.size()-1; j>=0; j--) { 10552 if (which.get(j).equals(list.get(i))) { 10553 return true; 10554 } 10555 } 10556 } 10557 return false; 10558 } 10559 10560 private ArrayList<PackageParser.Package> updateAllSharedLibrariesLPw( 10561 PackageParser.Package changingPkg) { 10562 ArrayList<PackageParser.Package> res = null; 10563 for (PackageParser.Package pkg : mPackages.values()) { 10564 if (changingPkg != null 10565 && !hasString(pkg.usesLibraries, changingPkg.libraryNames) 10566 && !hasString(pkg.usesOptionalLibraries, changingPkg.libraryNames) 10567 && !ArrayUtils.contains(pkg.usesStaticLibraries, 10568 changingPkg.staticSharedLibName)) { 10569 return null; 10570 } 10571 if (res == null) { 10572 res = new ArrayList<>(); 10573 } 10574 res.add(pkg); 10575 try { 10576 updateSharedLibrariesLPr(pkg, changingPkg); 10577 } catch (PackageManagerException e) { 10578 // If a system app update or an app and a required lib missing we 10579 // delete the package and for updated system apps keep the data as 10580 // it is better for the user to reinstall than to be in an limbo 10581 // state. Also libs disappearing under an app should never happen 10582 // - just in case. 10583 if (!pkg.isSystemApp() || pkg.isUpdatedSystemApp()) { 10584 final int flags = pkg.isUpdatedSystemApp() 10585 ? PackageManager.DELETE_KEEP_DATA : 0; 10586 deletePackageLIF(pkg.packageName, null, true, sUserManager.getUserIds(), 10587 flags , null, true, null); 10588 } 10589 Slog.e(TAG, "updateAllSharedLibrariesLPw failed: " + e.getMessage()); 10590 } 10591 } 10592 return res; 10593 } 10594 10595 /** 10596 * Derive the value of the {@code cpuAbiOverride} based on the provided 10597 * value and an optional stored value from the package settings. 10598 */ 10599 private static String deriveAbiOverride(String abiOverride, PackageSetting settings) { 10600 String cpuAbiOverride = null; 10601 10602 if (NativeLibraryHelper.CLEAR_ABI_OVERRIDE.equals(abiOverride)) { 10603 cpuAbiOverride = null; 10604 } else if (abiOverride != null) { 10605 cpuAbiOverride = abiOverride; 10606 } else if (settings != null) { 10607 cpuAbiOverride = settings.cpuAbiOverrideString; 10608 } 10609 10610 return cpuAbiOverride; 10611 } 10612 10613 private PackageParser.Package scanPackageTracedLI(PackageParser.Package pkg, 10614 final int policyFlags, int scanFlags, long currentTime, @Nullable UserHandle user) 10615 throws PackageManagerException { 10616 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "scanPackage"); 10617 // If the package has children and this is the first dive in the function 10618 // we recursively scan the package with the SCAN_CHECK_ONLY flag set to see 10619 // whether all packages (parent and children) would be successfully scanned 10620 // before the actual scan since scanning mutates internal state and we want 10621 // to atomically install the package and its children. 10622 if ((scanFlags & SCAN_CHECK_ONLY) == 0) { 10623 if (pkg.childPackages != null && pkg.childPackages.size() > 0) { 10624 scanFlags |= SCAN_CHECK_ONLY; 10625 } 10626 } else { 10627 scanFlags &= ~SCAN_CHECK_ONLY; 10628 } 10629 10630 final PackageParser.Package scannedPkg; 10631 try { 10632 // Scan the parent 10633 scannedPkg = scanPackageLI(pkg, policyFlags, scanFlags, currentTime, user); 10634 // Scan the children 10635 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 10636 for (int i = 0; i < childCount; i++) { 10637 PackageParser.Package childPkg = pkg.childPackages.get(i); 10638 scanPackageLI(childPkg, policyFlags, 10639 scanFlags, currentTime, user); 10640 } 10641 } finally { 10642 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 10643 } 10644 10645 if ((scanFlags & SCAN_CHECK_ONLY) != 0) { 10646 return scanPackageTracedLI(pkg, policyFlags, scanFlags, currentTime, user); 10647 } 10648 10649 return scannedPkg; 10650 } 10651 10652 private PackageParser.Package scanPackageLI(PackageParser.Package pkg, final int policyFlags, 10653 int scanFlags, long currentTime, @Nullable UserHandle user) 10654 throws PackageManagerException { 10655 boolean success = false; 10656 try { 10657 final PackageParser.Package res = scanPackageDirtyLI(pkg, policyFlags, scanFlags, 10658 currentTime, user); 10659 success = true; 10660 return res; 10661 } finally { 10662 if (!success && (scanFlags & SCAN_DELETE_DATA_ON_FAILURES) != 0) { 10663 // DELETE_DATA_ON_FAILURES is only used by frozen paths 10664 destroyAppDataLIF(pkg, UserHandle.USER_ALL, 10665 StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE); 10666 destroyAppProfilesLIF(pkg, UserHandle.USER_ALL); 10667 } 10668 } 10669 } 10670 10671 /** 10672 * Returns {@code true} if the given file contains code. Otherwise {@code false}. 10673 */ 10674 private static boolean apkHasCode(String fileName) { 10675 StrictJarFile jarFile = null; 10676 try { 10677 jarFile = new StrictJarFile(fileName, 10678 false /*verify*/, false /*signatureSchemeRollbackProtectionsEnforced*/); 10679 return jarFile.findEntry("classes.dex") != null; 10680 } catch (IOException ignore) { 10681 } finally { 10682 try { 10683 if (jarFile != null) { 10684 jarFile.close(); 10685 } 10686 } catch (IOException ignore) {} 10687 } 10688 return false; 10689 } 10690 10691 /** 10692 * Enforces code policy for the package. This ensures that if an APK has 10693 * declared hasCode="true" in its manifest that the APK actually contains 10694 * code. 10695 * 10696 * @throws PackageManagerException If bytecode could not be found when it should exist 10697 */ 10698 private static void assertCodePolicy(PackageParser.Package pkg) 10699 throws PackageManagerException { 10700 final boolean shouldHaveCode = 10701 (pkg.applicationInfo.flags & ApplicationInfo.FLAG_HAS_CODE) != 0; 10702 if (shouldHaveCode && !apkHasCode(pkg.baseCodePath)) { 10703 throw new PackageManagerException(INSTALL_FAILED_INVALID_APK, 10704 "Package " + pkg.baseCodePath + " code is missing"); 10705 } 10706 10707 if (!ArrayUtils.isEmpty(pkg.splitCodePaths)) { 10708 for (int i = 0; i < pkg.splitCodePaths.length; i++) { 10709 final boolean splitShouldHaveCode = 10710 (pkg.splitFlags[i] & ApplicationInfo.FLAG_HAS_CODE) != 0; 10711 if (splitShouldHaveCode && !apkHasCode(pkg.splitCodePaths[i])) { 10712 throw new PackageManagerException(INSTALL_FAILED_INVALID_APK, 10713 "Package " + pkg.splitCodePaths[i] + " code is missing"); 10714 } 10715 } 10716 } 10717 } 10718 10719 private PackageParser.Package scanPackageDirtyLI(PackageParser.Package pkg, 10720 final int policyFlags, final int scanFlags, long currentTime, @Nullable UserHandle user) 10721 throws PackageManagerException { 10722 if (DEBUG_PACKAGE_SCANNING) { 10723 if ((policyFlags & PackageParser.PARSE_CHATTY) != 0) 10724 Log.d(TAG, "Scanning package " + pkg.packageName); 10725 } 10726 10727 applyPolicy(pkg, policyFlags); 10728 10729 assertPackageIsValid(pkg, policyFlags, scanFlags); 10730 10731 // Initialize package source and resource directories 10732 final File scanFile = new File(pkg.codePath); 10733 final File destCodeFile = new File(pkg.applicationInfo.getCodePath()); 10734 final File destResourceFile = new File(pkg.applicationInfo.getResourcePath()); 10735 10736 SharedUserSetting suid = null; 10737 PackageSetting pkgSetting = null; 10738 10739 // Getting the package setting may have a side-effect, so if we 10740 // are only checking if scan would succeed, stash a copy of the 10741 // old setting to restore at the end. 10742 PackageSetting nonMutatedPs = null; 10743 10744 // We keep references to the derived CPU Abis from settings in oder to reuse 10745 // them in the case where we're not upgrading or booting for the first time. 10746 String primaryCpuAbiFromSettings = null; 10747 String secondaryCpuAbiFromSettings = null; 10748 10749 // writer 10750 synchronized (mPackages) { 10751 if (pkg.mSharedUserId != null) { 10752 // SIDE EFFECTS; may potentially allocate a new shared user 10753 suid = mSettings.getSharedUserLPw( 10754 pkg.mSharedUserId, 0 /*pkgFlags*/, 0 /*pkgPrivateFlags*/, true /*create*/); 10755 if (DEBUG_PACKAGE_SCANNING) { 10756 if ((policyFlags & PackageParser.PARSE_CHATTY) != 0) 10757 Log.d(TAG, "Shared UserID " + pkg.mSharedUserId + " (uid=" + suid.userId 10758 + "): packages=" + suid.packages); 10759 } 10760 } 10761 10762 // Check if we are renaming from an original package name. 10763 PackageSetting origPackage = null; 10764 String realName = null; 10765 if (pkg.mOriginalPackages != null) { 10766 // This package may need to be renamed to a previously 10767 // installed name. Let's check on that... 10768 final String renamed = mSettings.getRenamedPackageLPr(pkg.mRealPackage); 10769 if (pkg.mOriginalPackages.contains(renamed)) { 10770 // This package had originally been installed as the 10771 // original name, and we have already taken care of 10772 // transitioning to the new one. Just update the new 10773 // one to continue using the old name. 10774 realName = pkg.mRealPackage; 10775 if (!pkg.packageName.equals(renamed)) { 10776 // Callers into this function may have already taken 10777 // care of renaming the package; only do it here if 10778 // it is not already done. 10779 pkg.setPackageName(renamed); 10780 } 10781 } else { 10782 for (int i=pkg.mOriginalPackages.size()-1; i>=0; i--) { 10783 if ((origPackage = mSettings.getPackageLPr( 10784 pkg.mOriginalPackages.get(i))) != null) { 10785 // We do have the package already installed under its 10786 // original name... should we use it? 10787 if (!verifyPackageUpdateLPr(origPackage, pkg)) { 10788 // New package is not compatible with original. 10789 origPackage = null; 10790 continue; 10791 } else if (origPackage.sharedUser != null) { 10792 // Make sure uid is compatible between packages. 10793 if (!origPackage.sharedUser.name.equals(pkg.mSharedUserId)) { 10794 Slog.w(TAG, "Unable to migrate data from " + origPackage.name 10795 + " to " + pkg.packageName + ": old uid " 10796 + origPackage.sharedUser.name 10797 + " differs from " + pkg.mSharedUserId); 10798 origPackage = null; 10799 continue; 10800 } 10801 // TODO: Add case when shared user id is added [b/28144775] 10802 } else { 10803 if (DEBUG_UPGRADE) Log.v(TAG, "Renaming new package " 10804 + pkg.packageName + " to old name " + origPackage.name); 10805 } 10806 break; 10807 } 10808 } 10809 } 10810 } 10811 10812 if (mTransferedPackages.contains(pkg.packageName)) { 10813 Slog.w(TAG, "Package " + pkg.packageName 10814 + " was transferred to another, but its .apk remains"); 10815 } 10816 10817 // See comments in nonMutatedPs declaration 10818 if ((scanFlags & SCAN_CHECK_ONLY) != 0) { 10819 PackageSetting foundPs = mSettings.getPackageLPr(pkg.packageName); 10820 if (foundPs != null) { 10821 nonMutatedPs = new PackageSetting(foundPs); 10822 } 10823 } 10824 10825 if ((scanFlags & SCAN_FIRST_BOOT_OR_UPGRADE) == 0) { 10826 PackageSetting foundPs = mSettings.getPackageLPr(pkg.packageName); 10827 if (foundPs != null) { 10828 primaryCpuAbiFromSettings = foundPs.primaryCpuAbiString; 10829 secondaryCpuAbiFromSettings = foundPs.secondaryCpuAbiString; 10830 } 10831 } 10832 10833 pkgSetting = mSettings.getPackageLPr(pkg.packageName); 10834 if (pkgSetting != null && pkgSetting.sharedUser != suid) { 10835 PackageManagerService.reportSettingsProblem(Log.WARN, 10836 "Package " + pkg.packageName + " shared user changed from " 10837 + (pkgSetting.sharedUser != null 10838 ? pkgSetting.sharedUser.name : "<nothing>") 10839 + " to " 10840 + (suid != null ? suid.name : "<nothing>") 10841 + "; replacing with new"); 10842 pkgSetting = null; 10843 } 10844 final PackageSetting oldPkgSetting = 10845 pkgSetting == null ? null : new PackageSetting(pkgSetting); 10846 final PackageSetting disabledPkgSetting = 10847 mSettings.getDisabledSystemPkgLPr(pkg.packageName); 10848 10849 String[] usesStaticLibraries = null; 10850 if (pkg.usesStaticLibraries != null) { 10851 usesStaticLibraries = new String[pkg.usesStaticLibraries.size()]; 10852 pkg.usesStaticLibraries.toArray(usesStaticLibraries); 10853 } 10854 10855 if (pkgSetting == null) { 10856 final String parentPackageName = (pkg.parentPackage != null) 10857 ? pkg.parentPackage.packageName : null; 10858 final boolean instantApp = (scanFlags & SCAN_AS_INSTANT_APP) != 0; 10859 final boolean virtualPreload = (scanFlags & SCAN_AS_VIRTUAL_PRELOAD) != 0; 10860 // REMOVE SharedUserSetting from method; update in a separate call 10861 pkgSetting = Settings.createNewSetting(pkg.packageName, origPackage, 10862 disabledPkgSetting, realName, suid, destCodeFile, destResourceFile, 10863 pkg.applicationInfo.nativeLibraryRootDir, pkg.applicationInfo.primaryCpuAbi, 10864 pkg.applicationInfo.secondaryCpuAbi, pkg.mVersionCode, 10865 pkg.applicationInfo.flags, pkg.applicationInfo.privateFlags, user, 10866 true /*allowInstall*/, instantApp, virtualPreload, 10867 parentPackageName, pkg.getChildPackageNames(), 10868 UserManagerService.getInstance(), usesStaticLibraries, 10869 pkg.usesStaticLibrariesVersions); 10870 // SIDE EFFECTS; updates system state; move elsewhere 10871 if (origPackage != null) { 10872 mSettings.addRenamedPackageLPw(pkg.packageName, origPackage.name); 10873 } 10874 mSettings.addUserToSettingLPw(pkgSetting); 10875 } else { 10876 // REMOVE SharedUserSetting from method; update in a separate call. 10877 // 10878 // TODO(narayan): This update is bogus. nativeLibraryDir & primaryCpuAbi, 10879 // secondaryCpuAbi are not known at this point so we always update them 10880 // to null here, only to reset them at a later point. 10881 Settings.updatePackageSetting(pkgSetting, disabledPkgSetting, suid, destCodeFile, 10882 pkg.applicationInfo.nativeLibraryDir, pkg.applicationInfo.primaryCpuAbi, 10883 pkg.applicationInfo.secondaryCpuAbi, pkg.applicationInfo.flags, 10884 pkg.applicationInfo.privateFlags, pkg.getChildPackageNames(), 10885 UserManagerService.getInstance(), usesStaticLibraries, 10886 pkg.usesStaticLibrariesVersions); 10887 } 10888 // SIDE EFFECTS; persists system state to files on disk; move elsewhere 10889 mSettings.writeUserRestrictionsLPw(pkgSetting, oldPkgSetting); 10890 10891 // SIDE EFFECTS; modifies system state; move elsewhere 10892 if (pkgSetting.origPackage != null) { 10893 // If we are first transitioning from an original package, 10894 // fix up the new package's name now. We need to do this after 10895 // looking up the package under its new name, so getPackageLP 10896 // can take care of fiddling things correctly. 10897 pkg.setPackageName(origPackage.name); 10898 10899 // File a report about this. 10900 String msg = "New package " + pkgSetting.realName 10901 + " renamed to replace old package " + pkgSetting.name; 10902 reportSettingsProblem(Log.WARN, msg); 10903 10904 // Make a note of it. 10905 if ((scanFlags & SCAN_CHECK_ONLY) == 0) { 10906 mTransferedPackages.add(origPackage.name); 10907 } 10908 10909 // No longer need to retain this. 10910 pkgSetting.origPackage = null; 10911 } 10912 10913 // SIDE EFFECTS; modifies system state; move elsewhere 10914 if ((scanFlags & SCAN_CHECK_ONLY) == 0 && realName != null) { 10915 // Make a note of it. 10916 mTransferedPackages.add(pkg.packageName); 10917 } 10918 10919 if (mSettings.isDisabledSystemPackageLPr(pkg.packageName)) { 10920 pkg.applicationInfo.flags |= ApplicationInfo.FLAG_UPDATED_SYSTEM_APP; 10921 } 10922 10923 if ((scanFlags & SCAN_BOOTING) == 0 10924 && (policyFlags & PackageParser.PARSE_IS_SYSTEM_DIR) == 0) { 10925 // Check all shared libraries and map to their actual file path. 10926 // We only do this here for apps not on a system dir, because those 10927 // are the only ones that can fail an install due to this. We 10928 // will take care of the system apps by updating all of their 10929 // library paths after the scan is done. Also during the initial 10930 // scan don't update any libs as we do this wholesale after all 10931 // apps are scanned to avoid dependency based scanning. 10932 updateSharedLibrariesLPr(pkg, null); 10933 } 10934 10935 if (mFoundPolicyFile) { 10936 SELinuxMMAC.assignSeInfoValue(pkg); 10937 } 10938 pkg.applicationInfo.uid = pkgSetting.appId; 10939 pkg.mExtras = pkgSetting; 10940 10941 10942 // Static shared libs have same package with different versions where 10943 // we internally use a synthetic package name to allow multiple versions 10944 // of the same package, therefore we need to compare signatures against 10945 // the package setting for the latest library version. 10946 PackageSetting signatureCheckPs = pkgSetting; 10947 if (pkg.applicationInfo.isStaticSharedLibrary()) { 10948 SharedLibraryEntry libraryEntry = getLatestSharedLibraVersionLPr(pkg); 10949 if (libraryEntry != null) { 10950 signatureCheckPs = mSettings.getPackageLPr(libraryEntry.apk); 10951 } 10952 } 10953 10954 if (shouldCheckUpgradeKeySetLP(signatureCheckPs, scanFlags)) { 10955 if (checkUpgradeKeySetLP(signatureCheckPs, pkg)) { 10956 // We just determined the app is signed correctly, so bring 10957 // over the latest parsed certs. 10958 pkgSetting.signatures.mSignatures = pkg.mSignatures; 10959 } else { 10960 if ((policyFlags & PackageParser.PARSE_IS_SYSTEM_DIR) == 0) { 10961 throw new PackageManagerException(INSTALL_FAILED_UPDATE_INCOMPATIBLE, 10962 "Package " + pkg.packageName + " upgrade keys do not match the " 10963 + "previously installed version"); 10964 } else { 10965 pkgSetting.signatures.mSignatures = pkg.mSignatures; 10966 String msg = "System package " + pkg.packageName 10967 + " signature changed; retaining data."; 10968 reportSettingsProblem(Log.WARN, msg); 10969 } 10970 } 10971 } else { 10972 try { 10973 // SIDE EFFECTS; compareSignaturesCompat() changes KeysetManagerService 10974 verifySignaturesLP(signatureCheckPs, pkg); 10975 // We just determined the app is signed correctly, so bring 10976 // over the latest parsed certs. 10977 pkgSetting.signatures.mSignatures = pkg.mSignatures; 10978 } catch (PackageManagerException e) { 10979 if ((policyFlags & PackageParser.PARSE_IS_SYSTEM_DIR) == 0) { 10980 throw e; 10981 } 10982 // The signature has changed, but this package is in the system 10983 // image... let's recover! 10984 pkgSetting.signatures.mSignatures = pkg.mSignatures; 10985 // However... if this package is part of a shared user, but it 10986 // doesn't match the signature of the shared user, let's fail. 10987 // What this means is that you can't change the signatures 10988 // associated with an overall shared user, which doesn't seem all 10989 // that unreasonable. 10990 if (signatureCheckPs.sharedUser != null) { 10991 if (compareSignatures(signatureCheckPs.sharedUser.signatures.mSignatures, 10992 pkg.mSignatures) != PackageManager.SIGNATURE_MATCH) { 10993 throw new PackageManagerException( 10994 INSTALL_PARSE_FAILED_INCONSISTENT_CERTIFICATES, 10995 "Signature mismatch for shared user: " 10996 + pkgSetting.sharedUser); 10997 } 10998 } 10999 // File a report about this. 11000 String msg = "System package " + pkg.packageName 11001 + " signature changed; retaining data."; 11002 reportSettingsProblem(Log.WARN, msg); 11003 } 11004 } 11005 11006 if ((scanFlags & SCAN_CHECK_ONLY) == 0 && pkg.mAdoptPermissions != null) { 11007 // This package wants to adopt ownership of permissions from 11008 // another package. 11009 for (int i = pkg.mAdoptPermissions.size() - 1; i >= 0; i--) { 11010 final String origName = pkg.mAdoptPermissions.get(i); 11011 final PackageSetting orig = mSettings.getPackageLPr(origName); 11012 if (orig != null) { 11013 if (verifyPackageUpdateLPr(orig, pkg)) { 11014 Slog.i(TAG, "Adopting permissions from " + origName + " to " 11015 + pkg.packageName); 11016 // SIDE EFFECTS; updates permissions system state; move elsewhere 11017 mSettings.transferPermissionsLPw(origName, pkg.packageName); 11018 } 11019 } 11020 } 11021 } 11022 } 11023 11024 pkg.applicationInfo.processName = fixProcessName( 11025 pkg.applicationInfo.packageName, 11026 pkg.applicationInfo.processName); 11027 11028 if (pkg != mPlatformPackage) { 11029 // Get all of our default paths setup 11030 pkg.applicationInfo.initForUser(UserHandle.USER_SYSTEM); 11031 } 11032 11033 final String cpuAbiOverride = deriveAbiOverride(pkg.cpuAbiOverride, pkgSetting); 11034 11035 if ((scanFlags & SCAN_NEW_INSTALL) == 0) { 11036 if ((scanFlags & SCAN_FIRST_BOOT_OR_UPGRADE) != 0) { 11037 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "derivePackageAbi"); 11038 final boolean extractNativeLibs = !pkg.isLibrary(); 11039 derivePackageAbi(pkg, scanFile, cpuAbiOverride, extractNativeLibs, 11040 mAppLib32InstallDir); 11041 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 11042 11043 // Some system apps still use directory structure for native libraries 11044 // in which case we might end up not detecting abi solely based on apk 11045 // structure. Try to detect abi based on directory structure. 11046 if (isSystemApp(pkg) && !pkg.isUpdatedSystemApp() && 11047 pkg.applicationInfo.primaryCpuAbi == null) { 11048 setBundledAppAbisAndRoots(pkg, pkgSetting); 11049 setNativeLibraryPaths(pkg, mAppLib32InstallDir); 11050 } 11051 } else { 11052 // This is not a first boot or an upgrade, don't bother deriving the 11053 // ABI during the scan. Instead, trust the value that was stored in the 11054 // package setting. 11055 pkg.applicationInfo.primaryCpuAbi = primaryCpuAbiFromSettings; 11056 pkg.applicationInfo.secondaryCpuAbi = secondaryCpuAbiFromSettings; 11057 11058 setNativeLibraryPaths(pkg, mAppLib32InstallDir); 11059 11060 if (DEBUG_ABI_SELECTION) { 11061 Slog.i(TAG, "Using ABIS and native lib paths from settings : " + 11062 pkg.packageName + " " + pkg.applicationInfo.primaryCpuAbi + ", " + 11063 pkg.applicationInfo.secondaryCpuAbi); 11064 } 11065 } 11066 } else { 11067 if ((scanFlags & SCAN_MOVE) != 0) { 11068 // We haven't run dex-opt for this move (since we've moved the compiled output too) 11069 // but we already have this packages package info in the PackageSetting. We just 11070 // use that and derive the native library path based on the new codepath. 11071 pkg.applicationInfo.primaryCpuAbi = pkgSetting.primaryCpuAbiString; 11072 pkg.applicationInfo.secondaryCpuAbi = pkgSetting.secondaryCpuAbiString; 11073 } 11074 11075 // Set native library paths again. For moves, the path will be updated based on the 11076 // ABIs we've determined above. For non-moves, the path will be updated based on the 11077 // ABIs we determined during compilation, but the path will depend on the final 11078 // package path (after the rename away from the stage path). 11079 setNativeLibraryPaths(pkg, mAppLib32InstallDir); 11080 } 11081 11082 // This is a special case for the "system" package, where the ABI is 11083 // dictated by the zygote configuration (and init.rc). We should keep track 11084 // of this ABI so that we can deal with "normal" applications that run under 11085 // the same UID correctly. 11086 if (mPlatformPackage == pkg) { 11087 pkg.applicationInfo.primaryCpuAbi = VMRuntime.getRuntime().is64Bit() ? 11088 Build.SUPPORTED_64_BIT_ABIS[0] : Build.SUPPORTED_32_BIT_ABIS[0]; 11089 } 11090 11091 // If there's a mismatch between the abi-override in the package setting 11092 // and the abiOverride specified for the install. Warn about this because we 11093 // would've already compiled the app without taking the package setting into 11094 // account. 11095 if ((scanFlags & SCAN_NO_DEX) == 0 && (scanFlags & SCAN_NEW_INSTALL) != 0) { 11096 if (cpuAbiOverride == null && pkgSetting.cpuAbiOverrideString != null) { 11097 Slog.w(TAG, "Ignoring persisted ABI override " + cpuAbiOverride + 11098 " for package " + pkg.packageName); 11099 } 11100 } 11101 11102 pkgSetting.primaryCpuAbiString = pkg.applicationInfo.primaryCpuAbi; 11103 pkgSetting.secondaryCpuAbiString = pkg.applicationInfo.secondaryCpuAbi; 11104 pkgSetting.cpuAbiOverrideString = cpuAbiOverride; 11105 11106 // Copy the derived override back to the parsed package, so that we can 11107 // update the package settings accordingly. 11108 pkg.cpuAbiOverride = cpuAbiOverride; 11109 11110 if (DEBUG_ABI_SELECTION) { 11111 Slog.d(TAG, "Resolved nativeLibraryRoot for " + pkg.applicationInfo.packageName 11112 + " to root=" + pkg.applicationInfo.nativeLibraryRootDir + ", isa=" 11113 + pkg.applicationInfo.nativeLibraryRootRequiresIsa); 11114 } 11115 11116 // Push the derived path down into PackageSettings so we know what to 11117 // clean up at uninstall time. 11118 pkgSetting.legacyNativeLibraryPathString = pkg.applicationInfo.nativeLibraryRootDir; 11119 11120 if (DEBUG_ABI_SELECTION) { 11121 Log.d(TAG, "Abis for package[" + pkg.packageName + "] are" + 11122 " primary=" + pkg.applicationInfo.primaryCpuAbi + 11123 " secondary=" + pkg.applicationInfo.secondaryCpuAbi); 11124 } 11125 11126 // SIDE EFFECTS; removes DEX files from disk; move elsewhere 11127 if ((scanFlags & SCAN_BOOTING) == 0 && pkgSetting.sharedUser != null) { 11128 // We don't do this here during boot because we can do it all 11129 // at once after scanning all existing packages. 11130 // 11131 // We also do this *before* we perform dexopt on this package, so that 11132 // we can avoid redundant dexopts, and also to make sure we've got the 11133 // code and package path correct. 11134 adjustCpuAbisForSharedUserLPw(pkgSetting.sharedUser.packages, pkg); 11135 } 11136 11137 if (mFactoryTest && pkg.requestedPermissions.contains( 11138 android.Manifest.permission.FACTORY_TEST)) { 11139 pkg.applicationInfo.flags |= ApplicationInfo.FLAG_FACTORY_TEST; 11140 } 11141 11142 if (isSystemApp(pkg)) { 11143 pkgSetting.isOrphaned = true; 11144 } 11145 11146 // Take care of first install / last update times. 11147 final long scanFileTime = getLastModifiedTime(pkg, scanFile); 11148 if (currentTime != 0) { 11149 if (pkgSetting.firstInstallTime == 0) { 11150 pkgSetting.firstInstallTime = pkgSetting.lastUpdateTime = currentTime; 11151 } else if ((scanFlags & SCAN_UPDATE_TIME) != 0) { 11152 pkgSetting.lastUpdateTime = currentTime; 11153 } 11154 } else if (pkgSetting.firstInstallTime == 0) { 11155 // We need *something*. Take time time stamp of the file. 11156 pkgSetting.firstInstallTime = pkgSetting.lastUpdateTime = scanFileTime; 11157 } else if ((policyFlags & PackageParser.PARSE_IS_SYSTEM_DIR) != 0) { 11158 if (scanFileTime != pkgSetting.timeStamp) { 11159 // A package on the system image has changed; consider this 11160 // to be an update. 11161 pkgSetting.lastUpdateTime = scanFileTime; 11162 } 11163 } 11164 pkgSetting.setTimeStamp(scanFileTime); 11165 11166 if ((scanFlags & SCAN_CHECK_ONLY) != 0) { 11167 if (nonMutatedPs != null) { 11168 synchronized (mPackages) { 11169 mSettings.mPackages.put(nonMutatedPs.name, nonMutatedPs); 11170 } 11171 } 11172 } else { 11173 final int userId = user == null ? 0 : user.getIdentifier(); 11174 // Modify state for the given package setting 11175 commitPackageSettings(pkg, pkgSetting, user, scanFlags, 11176 (policyFlags & PackageParser.PARSE_CHATTY) != 0 /*chatty*/); 11177 if (pkgSetting.getInstantApp(userId)) { 11178 mInstantAppRegistry.addInstantAppLPw(userId, pkgSetting.appId); 11179 } 11180 } 11181 return pkg; 11182 } 11183 11184 /** 11185 * Applies policy to the parsed package based upon the given policy flags. 11186 * Ensures the package is in a good state. 11187 * <p> 11188 * Implementation detail: This method must NOT have any side effect. It would 11189 * ideally be static, but, it requires locks to read system state. 11190 */ 11191 private void applyPolicy(PackageParser.Package pkg, int policyFlags) { 11192 if ((policyFlags&PackageParser.PARSE_IS_SYSTEM) != 0) { 11193 pkg.applicationInfo.flags |= ApplicationInfo.FLAG_SYSTEM; 11194 if (pkg.applicationInfo.isDirectBootAware()) { 11195 // we're direct boot aware; set for all components 11196 for (PackageParser.Service s : pkg.services) { 11197 s.info.encryptionAware = s.info.directBootAware = true; 11198 } 11199 for (PackageParser.Provider p : pkg.providers) { 11200 p.info.encryptionAware = p.info.directBootAware = true; 11201 } 11202 for (PackageParser.Activity a : pkg.activities) { 11203 a.info.encryptionAware = a.info.directBootAware = true; 11204 } 11205 for (PackageParser.Activity r : pkg.receivers) { 11206 r.info.encryptionAware = r.info.directBootAware = true; 11207 } 11208 } 11209 if (compressedFileExists(pkg.codePath)) { 11210 pkg.isStub = true; 11211 } 11212 } else { 11213 // Only allow system apps to be flagged as core apps. 11214 pkg.coreApp = false; 11215 // clear flags not applicable to regular apps 11216 pkg.applicationInfo.privateFlags &= 11217 ~ApplicationInfo.PRIVATE_FLAG_DEFAULT_TO_DEVICE_PROTECTED_STORAGE; 11218 pkg.applicationInfo.privateFlags &= 11219 ~ApplicationInfo.PRIVATE_FLAG_DIRECT_BOOT_AWARE; 11220 } 11221 pkg.mTrustedOverlay = (policyFlags&PackageParser.PARSE_TRUSTED_OVERLAY) != 0; 11222 11223 if ((policyFlags&PackageParser.PARSE_IS_PRIVILEGED) != 0) { 11224 pkg.applicationInfo.privateFlags |= ApplicationInfo.PRIVATE_FLAG_PRIVILEGED; 11225 } 11226 11227 if (!isSystemApp(pkg)) { 11228 // Only system apps can use these features. 11229 pkg.mOriginalPackages = null; 11230 pkg.mRealPackage = null; 11231 pkg.mAdoptPermissions = null; 11232 } 11233 } 11234 11235 /** 11236 * Asserts the parsed package is valid according to the given policy. If the 11237 * package is invalid, for whatever reason, throws {@link PackageManagerException}. 11238 * <p> 11239 * Implementation detail: This method must NOT have any side effects. It would 11240 * ideally be static, but, it requires locks to read system state. 11241 * 11242 * @throws PackageManagerException If the package fails any of the validation checks 11243 */ 11244 private void assertPackageIsValid(PackageParser.Package pkg, int policyFlags, int scanFlags) 11245 throws PackageManagerException { 11246 if ((policyFlags & PackageParser.PARSE_ENFORCE_CODE) != 0) { 11247 assertCodePolicy(pkg); 11248 } 11249 11250 if (pkg.applicationInfo.getCodePath() == null || 11251 pkg.applicationInfo.getResourcePath() == null) { 11252 // Bail out. The resource and code paths haven't been set. 11253 throw new PackageManagerException(INSTALL_FAILED_INVALID_APK, 11254 "Code and resource paths haven't been set correctly"); 11255 } 11256 11257 // Make sure we're not adding any bogus keyset info 11258 KeySetManagerService ksms = mSettings.mKeySetManagerService; 11259 ksms.assertScannedPackageValid(pkg); 11260 11261 synchronized (mPackages) { 11262 // The special "android" package can only be defined once 11263 if (pkg.packageName.equals("android")) { 11264 if (mAndroidApplication != null) { 11265 Slog.w(TAG, "*************************************************"); 11266 Slog.w(TAG, "Core android package being redefined. Skipping."); 11267 Slog.w(TAG, " codePath=" + pkg.codePath); 11268 Slog.w(TAG, "*************************************************"); 11269 throw new PackageManagerException(INSTALL_FAILED_DUPLICATE_PACKAGE, 11270 "Core android package being redefined. Skipping."); 11271 } 11272 } 11273 11274 // A package name must be unique; don't allow duplicates 11275 if (mPackages.containsKey(pkg.packageName)) { 11276 throw new PackageManagerException(INSTALL_FAILED_DUPLICATE_PACKAGE, 11277 "Application package " + pkg.packageName 11278 + " already installed. Skipping duplicate."); 11279 } 11280 11281 if (pkg.applicationInfo.isStaticSharedLibrary()) { 11282 // Static libs have a synthetic package name containing the version 11283 // but we still want the base name to be unique. 11284 if (mPackages.containsKey(pkg.manifestPackageName)) { 11285 throw new PackageManagerException( 11286 "Duplicate static shared lib provider package"); 11287 } 11288 11289 // Static shared libraries should have at least O target SDK 11290 if (pkg.applicationInfo.targetSdkVersion < Build.VERSION_CODES.O) { 11291 throw new PackageManagerException( 11292 "Packages declaring static-shared libs must target O SDK or higher"); 11293 } 11294 11295 // Package declaring static a shared lib cannot be instant apps 11296 if ((scanFlags & SCAN_AS_INSTANT_APP) != 0) { 11297 throw new PackageManagerException( 11298 "Packages declaring static-shared libs cannot be instant apps"); 11299 } 11300 11301 // Package declaring static a shared lib cannot be renamed since the package 11302 // name is synthetic and apps can't code around package manager internals. 11303 if (!ArrayUtils.isEmpty(pkg.mOriginalPackages)) { 11304 throw new PackageManagerException( 11305 "Packages declaring static-shared libs cannot be renamed"); 11306 } 11307 11308 // Package declaring static a shared lib cannot declare child packages 11309 if (!ArrayUtils.isEmpty(pkg.childPackages)) { 11310 throw new PackageManagerException( 11311 "Packages declaring static-shared libs cannot have child packages"); 11312 } 11313 11314 // Package declaring static a shared lib cannot declare dynamic libs 11315 if (!ArrayUtils.isEmpty(pkg.libraryNames)) { 11316 throw new PackageManagerException( 11317 "Packages declaring static-shared libs cannot declare dynamic libs"); 11318 } 11319 11320 // Package declaring static a shared lib cannot declare shared users 11321 if (pkg.mSharedUserId != null) { 11322 throw new PackageManagerException( 11323 "Packages declaring static-shared libs cannot declare shared users"); 11324 } 11325 11326 // Static shared libs cannot declare activities 11327 if (!pkg.activities.isEmpty()) { 11328 throw new PackageManagerException( 11329 "Static shared libs cannot declare activities"); 11330 } 11331 11332 // Static shared libs cannot declare services 11333 if (!pkg.services.isEmpty()) { 11334 throw new PackageManagerException( 11335 "Static shared libs cannot declare services"); 11336 } 11337 11338 // Static shared libs cannot declare providers 11339 if (!pkg.providers.isEmpty()) { 11340 throw new PackageManagerException( 11341 "Static shared libs cannot declare content providers"); 11342 } 11343 11344 // Static shared libs cannot declare receivers 11345 if (!pkg.receivers.isEmpty()) { 11346 throw new PackageManagerException( 11347 "Static shared libs cannot declare broadcast receivers"); 11348 } 11349 11350 // Static shared libs cannot declare permission groups 11351 if (!pkg.permissionGroups.isEmpty()) { 11352 throw new PackageManagerException( 11353 "Static shared libs cannot declare permission groups"); 11354 } 11355 11356 // Static shared libs cannot declare permissions 11357 if (!pkg.permissions.isEmpty()) { 11358 throw new PackageManagerException( 11359 "Static shared libs cannot declare permissions"); 11360 } 11361 11362 // Static shared libs cannot declare protected broadcasts 11363 if (pkg.protectedBroadcasts != null) { 11364 throw new PackageManagerException( 11365 "Static shared libs cannot declare protected broadcasts"); 11366 } 11367 11368 // Static shared libs cannot be overlay targets 11369 if (pkg.mOverlayTarget != null) { 11370 throw new PackageManagerException( 11371 "Static shared libs cannot be overlay targets"); 11372 } 11373 11374 // The version codes must be ordered as lib versions 11375 int minVersionCode = Integer.MIN_VALUE; 11376 int maxVersionCode = Integer.MAX_VALUE; 11377 11378 SparseArray<SharedLibraryEntry> versionedLib = mSharedLibraries.get( 11379 pkg.staticSharedLibName); 11380 if (versionedLib != null) { 11381 final int versionCount = versionedLib.size(); 11382 for (int i = 0; i < versionCount; i++) { 11383 SharedLibraryInfo libInfo = versionedLib.valueAt(i).info; 11384 final int libVersionCode = libInfo.getDeclaringPackage() 11385 .getVersionCode(); 11386 if (libInfo.getVersion() < pkg.staticSharedLibVersion) { 11387 minVersionCode = Math.max(minVersionCode, libVersionCode + 1); 11388 } else if (libInfo.getVersion() > pkg.staticSharedLibVersion) { 11389 maxVersionCode = Math.min(maxVersionCode, libVersionCode - 1); 11390 } else { 11391 minVersionCode = maxVersionCode = libVersionCode; 11392 break; 11393 } 11394 } 11395 } 11396 if (pkg.mVersionCode < minVersionCode || pkg.mVersionCode > maxVersionCode) { 11397 throw new PackageManagerException("Static shared" 11398 + " lib version codes must be ordered as lib versions"); 11399 } 11400 } 11401 11402 // Only privileged apps and updated privileged apps can add child packages. 11403 if (pkg.childPackages != null && !pkg.childPackages.isEmpty()) { 11404 if ((policyFlags & PARSE_IS_PRIVILEGED) == 0) { 11405 throw new PackageManagerException("Only privileged apps can add child " 11406 + "packages. Ignoring package " + pkg.packageName); 11407 } 11408 final int childCount = pkg.childPackages.size(); 11409 for (int i = 0; i < childCount; i++) { 11410 PackageParser.Package childPkg = pkg.childPackages.get(i); 11411 if (mSettings.hasOtherDisabledSystemPkgWithChildLPr(pkg.packageName, 11412 childPkg.packageName)) { 11413 throw new PackageManagerException("Can't override child of " 11414 + "another disabled app. Ignoring package " + pkg.packageName); 11415 } 11416 } 11417 } 11418 11419 // If we're only installing presumed-existing packages, require that the 11420 // scanned APK is both already known and at the path previously established 11421 // for it. Previously unknown packages we pick up normally, but if we have an 11422 // a priori expectation about this package's install presence, enforce it. 11423 // With a singular exception for new system packages. When an OTA contains 11424 // a new system package, we allow the codepath to change from a system location 11425 // to the user-installed location. If we don't allow this change, any newer, 11426 // user-installed version of the application will be ignored. 11427 if ((scanFlags & SCAN_REQUIRE_KNOWN) != 0) { 11428 if (mExpectingBetter.containsKey(pkg.packageName)) { 11429 logCriticalInfo(Log.WARN, 11430 "Relax SCAN_REQUIRE_KNOWN requirement for package " + pkg.packageName); 11431 } else { 11432 PackageSetting known = mSettings.getPackageLPr(pkg.packageName); 11433 if (known != null) { 11434 if (DEBUG_PACKAGE_SCANNING) { 11435 Log.d(TAG, "Examining " + pkg.codePath 11436 + " and requiring known paths " + known.codePathString 11437 + " & " + known.resourcePathString); 11438 } 11439 if (!pkg.applicationInfo.getCodePath().equals(known.codePathString) 11440 || !pkg.applicationInfo.getResourcePath().equals( 11441 known.resourcePathString)) { 11442 throw new PackageManagerException(INSTALL_FAILED_PACKAGE_CHANGED, 11443 "Application package " + pkg.packageName 11444 + " found at " + pkg.applicationInfo.getCodePath() 11445 + " but expected at " + known.codePathString 11446 + "; ignoring."); 11447 } 11448 } else { 11449 throw new PackageManagerException(INSTALL_FAILED_INVALID_INSTALL_LOCATION, 11450 "Application package " + pkg.packageName 11451 + " not found; ignoring."); 11452 } 11453 } 11454 } 11455 11456 // Verify that this new package doesn't have any content providers 11457 // that conflict with existing packages. Only do this if the 11458 // package isn't already installed, since we don't want to break 11459 // things that are installed. 11460 if ((scanFlags & SCAN_NEW_INSTALL) != 0) { 11461 final int N = pkg.providers.size(); 11462 int i; 11463 for (i=0; i<N; i++) { 11464 PackageParser.Provider p = pkg.providers.get(i); 11465 if (p.info.authority != null) { 11466 String names[] = p.info.authority.split(";"); 11467 for (int j = 0; j < names.length; j++) { 11468 if (mProvidersByAuthority.containsKey(names[j])) { 11469 PackageParser.Provider other = mProvidersByAuthority.get(names[j]); 11470 final String otherPackageName = 11471 ((other != null && other.getComponentName() != null) ? 11472 other.getComponentName().getPackageName() : "?"); 11473 throw new PackageManagerException( 11474 INSTALL_FAILED_CONFLICTING_PROVIDER, 11475 "Can't install because provider name " + names[j] 11476 + " (in package " + pkg.applicationInfo.packageName 11477 + ") is already used by " + otherPackageName); 11478 } 11479 } 11480 } 11481 } 11482 } 11483 } 11484 } 11485 11486 private boolean addSharedLibraryLPw(String path, String apk, String name, int version, 11487 int type, String declaringPackageName, int declaringVersionCode) { 11488 SparseArray<SharedLibraryEntry> versionedLib = mSharedLibraries.get(name); 11489 if (versionedLib == null) { 11490 versionedLib = new SparseArray<>(); 11491 mSharedLibraries.put(name, versionedLib); 11492 if (type == SharedLibraryInfo.TYPE_STATIC) { 11493 mStaticLibsByDeclaringPackage.put(declaringPackageName, versionedLib); 11494 } 11495 } else if (versionedLib.indexOfKey(version) >= 0) { 11496 return false; 11497 } 11498 SharedLibraryEntry libEntry = new SharedLibraryEntry(path, apk, name, 11499 version, type, declaringPackageName, declaringVersionCode); 11500 versionedLib.put(version, libEntry); 11501 return true; 11502 } 11503 11504 private boolean removeSharedLibraryLPw(String name, int version) { 11505 SparseArray<SharedLibraryEntry> versionedLib = mSharedLibraries.get(name); 11506 if (versionedLib == null) { 11507 return false; 11508 } 11509 final int libIdx = versionedLib.indexOfKey(version); 11510 if (libIdx < 0) { 11511 return false; 11512 } 11513 SharedLibraryEntry libEntry = versionedLib.valueAt(libIdx); 11514 versionedLib.remove(version); 11515 if (versionedLib.size() <= 0) { 11516 mSharedLibraries.remove(name); 11517 if (libEntry.info.getType() == SharedLibraryInfo.TYPE_STATIC) { 11518 mStaticLibsByDeclaringPackage.remove(libEntry.info.getDeclaringPackage() 11519 .getPackageName()); 11520 } 11521 } 11522 return true; 11523 } 11524 11525 /** 11526 * Adds a scanned package to the system. When this method is finished, the package will 11527 * be available for query, resolution, etc... 11528 */ 11529 private void commitPackageSettings(PackageParser.Package pkg, PackageSetting pkgSetting, 11530 UserHandle user, int scanFlags, boolean chatty) throws PackageManagerException { 11531 final String pkgName = pkg.packageName; 11532 if (mCustomResolverComponentName != null && 11533 mCustomResolverComponentName.getPackageName().equals(pkg.packageName)) { 11534 setUpCustomResolverActivity(pkg); 11535 } 11536 11537 if (pkg.packageName.equals("android")) { 11538 synchronized (mPackages) { 11539 if ((scanFlags & SCAN_CHECK_ONLY) == 0) { 11540 // Set up information for our fall-back user intent resolution activity. 11541 mPlatformPackage = pkg; 11542 pkg.mVersionCode = mSdkVersion; 11543 mAndroidApplication = pkg.applicationInfo; 11544 if (!mResolverReplaced) { 11545 mResolveActivity.applicationInfo = mAndroidApplication; 11546 mResolveActivity.name = ResolverActivity.class.getName(); 11547 mResolveActivity.packageName = mAndroidApplication.packageName; 11548 mResolveActivity.processName = "system:ui"; 11549 mResolveActivity.launchMode = ActivityInfo.LAUNCH_MULTIPLE; 11550 mResolveActivity.documentLaunchMode = ActivityInfo.DOCUMENT_LAUNCH_NEVER; 11551 mResolveActivity.flags = ActivityInfo.FLAG_EXCLUDE_FROM_RECENTS; 11552 mResolveActivity.theme = R.style.Theme_Material_Dialog_Alert; 11553 mResolveActivity.exported = true; 11554 mResolveActivity.enabled = true; 11555 mResolveActivity.resizeMode = ActivityInfo.RESIZE_MODE_RESIZEABLE; 11556 mResolveActivity.configChanges = ActivityInfo.CONFIG_SCREEN_SIZE 11557 | ActivityInfo.CONFIG_SMALLEST_SCREEN_SIZE 11558 | ActivityInfo.CONFIG_SCREEN_LAYOUT 11559 | ActivityInfo.CONFIG_ORIENTATION 11560 | ActivityInfo.CONFIG_KEYBOARD 11561 | ActivityInfo.CONFIG_KEYBOARD_HIDDEN; 11562 mResolveInfo.activityInfo = mResolveActivity; 11563 mResolveInfo.priority = 0; 11564 mResolveInfo.preferredOrder = 0; 11565 mResolveInfo.match = 0; 11566 mResolveComponentName = new ComponentName( 11567 mAndroidApplication.packageName, mResolveActivity.name); 11568 } 11569 } 11570 } 11571 } 11572 11573 ArrayList<PackageParser.Package> clientLibPkgs = null; 11574 // writer 11575 synchronized (mPackages) { 11576 boolean hasStaticSharedLibs = false; 11577 11578 // Any app can add new static shared libraries 11579 if (pkg.staticSharedLibName != null) { 11580 // Static shared libs don't allow renaming as they have synthetic package 11581 // names to allow install of multiple versions, so use name from manifest. 11582 if (addSharedLibraryLPw(null, pkg.packageName, pkg.staticSharedLibName, 11583 pkg.staticSharedLibVersion, SharedLibraryInfo.TYPE_STATIC, 11584 pkg.manifestPackageName, pkg.mVersionCode)) { 11585 hasStaticSharedLibs = true; 11586 } else { 11587 Slog.w(TAG, "Package " + pkg.packageName + " library " 11588 + pkg.staticSharedLibName + " already exists; skipping"); 11589 } 11590 // Static shared libs cannot be updated once installed since they 11591 // use synthetic package name which includes the version code, so 11592 // not need to update other packages's shared lib dependencies. 11593 } 11594 11595 if (!hasStaticSharedLibs 11596 && (pkg.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 11597 // Only system apps can add new dynamic shared libraries. 11598 if (pkg.libraryNames != null) { 11599 for (int i = 0; i < pkg.libraryNames.size(); i++) { 11600 String name = pkg.libraryNames.get(i); 11601 boolean allowed = false; 11602 if (pkg.isUpdatedSystemApp()) { 11603 // New library entries can only be added through the 11604 // system image. This is important to get rid of a lot 11605 // of nasty edge cases: for example if we allowed a non- 11606 // system update of the app to add a library, then uninstalling 11607 // the update would make the library go away, and assumptions 11608 // we made such as through app install filtering would now 11609 // have allowed apps on the device which aren't compatible 11610 // with it. Better to just have the restriction here, be 11611 // conservative, and create many fewer cases that can negatively 11612 // impact the user experience. 11613 final PackageSetting sysPs = mSettings 11614 .getDisabledSystemPkgLPr(pkg.packageName); 11615 if (sysPs.pkg != null && sysPs.pkg.libraryNames != null) { 11616 for (int j = 0; j < sysPs.pkg.libraryNames.size(); j++) { 11617 if (name.equals(sysPs.pkg.libraryNames.get(j))) { 11618 allowed = true; 11619 break; 11620 } 11621 } 11622 } 11623 } else { 11624 allowed = true; 11625 } 11626 if (allowed) { 11627 if (!addSharedLibraryLPw(null, pkg.packageName, name, 11628 SharedLibraryInfo.VERSION_UNDEFINED, 11629 SharedLibraryInfo.TYPE_DYNAMIC, 11630 pkg.packageName, pkg.mVersionCode)) { 11631 Slog.w(TAG, "Package " + pkg.packageName + " library " 11632 + name + " already exists; skipping"); 11633 } 11634 } else { 11635 Slog.w(TAG, "Package " + pkg.packageName + " declares lib " 11636 + name + " that is not declared on system image; skipping"); 11637 } 11638 } 11639 11640 if ((scanFlags & SCAN_BOOTING) == 0) { 11641 // If we are not booting, we need to update any applications 11642 // that are clients of our shared library. If we are booting, 11643 // this will all be done once the scan is complete. 11644 clientLibPkgs = updateAllSharedLibrariesLPw(pkg); 11645 } 11646 } 11647 } 11648 } 11649 11650 if ((scanFlags & SCAN_BOOTING) != 0) { 11651 // No apps can run during boot scan, so they don't need to be frozen 11652 } else if ((scanFlags & SCAN_DONT_KILL_APP) != 0) { 11653 // Caller asked to not kill app, so it's probably not frozen 11654 } else if ((scanFlags & SCAN_IGNORE_FROZEN) != 0) { 11655 // Caller asked us to ignore frozen check for some reason; they 11656 // probably didn't know the package name 11657 } else { 11658 // We're doing major surgery on this package, so it better be frozen 11659 // right now to keep it from launching 11660 checkPackageFrozen(pkgName); 11661 } 11662 11663 // Also need to kill any apps that are dependent on the library. 11664 if (clientLibPkgs != null) { 11665 for (int i=0; i<clientLibPkgs.size(); i++) { 11666 PackageParser.Package clientPkg = clientLibPkgs.get(i); 11667 killApplication(clientPkg.applicationInfo.packageName, 11668 clientPkg.applicationInfo.uid, "update lib"); 11669 } 11670 } 11671 11672 // writer 11673 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "updateSettings"); 11674 11675 synchronized (mPackages) { 11676 // We don't expect installation to fail beyond this point 11677 11678 // Add the new setting to mSettings 11679 mSettings.insertPackageSettingLPw(pkgSetting, pkg); 11680 // Add the new setting to mPackages 11681 mPackages.put(pkg.applicationInfo.packageName, pkg); 11682 // Make sure we don't accidentally delete its data. 11683 final Iterator<PackageCleanItem> iter = mSettings.mPackagesToBeCleaned.iterator(); 11684 while (iter.hasNext()) { 11685 PackageCleanItem item = iter.next(); 11686 if (pkgName.equals(item.packageName)) { 11687 iter.remove(); 11688 } 11689 } 11690 11691 // Add the package's KeySets to the global KeySetManagerService 11692 KeySetManagerService ksms = mSettings.mKeySetManagerService; 11693 ksms.addScannedPackageLPw(pkg); 11694 11695 int N = pkg.providers.size(); 11696 StringBuilder r = null; 11697 int i; 11698 for (i=0; i<N; i++) { 11699 PackageParser.Provider p = pkg.providers.get(i); 11700 p.info.processName = fixProcessName(pkg.applicationInfo.processName, 11701 p.info.processName); 11702 mProviders.addProvider(p); 11703 p.syncable = p.info.isSyncable; 11704 if (p.info.authority != null) { 11705 String names[] = p.info.authority.split(";"); 11706 p.info.authority = null; 11707 for (int j = 0; j < names.length; j++) { 11708 if (j == 1 && p.syncable) { 11709 // We only want the first authority for a provider to possibly be 11710 // syncable, so if we already added this provider using a different 11711 // authority clear the syncable flag. We copy the provider before 11712 // changing it because the mProviders object contains a reference 11713 // to a provider that we don't want to change. 11714 // Only do this for the second authority since the resulting provider 11715 // object can be the same for all future authorities for this provider. 11716 p = new PackageParser.Provider(p); 11717 p.syncable = false; 11718 } 11719 if (!mProvidersByAuthority.containsKey(names[j])) { 11720 mProvidersByAuthority.put(names[j], p); 11721 if (p.info.authority == null) { 11722 p.info.authority = names[j]; 11723 } else { 11724 p.info.authority = p.info.authority + ";" + names[j]; 11725 } 11726 if (DEBUG_PACKAGE_SCANNING) { 11727 if (chatty) 11728 Log.d(TAG, "Registered content provider: " + names[j] 11729 + ", className = " + p.info.name + ", isSyncable = " 11730 + p.info.isSyncable); 11731 } 11732 } else { 11733 PackageParser.Provider other = mProvidersByAuthority.get(names[j]); 11734 Slog.w(TAG, "Skipping provider name " + names[j] + 11735 " (in package " + pkg.applicationInfo.packageName + 11736 "): name already used by " 11737 + ((other != null && other.getComponentName() != null) 11738 ? other.getComponentName().getPackageName() : "?")); 11739 } 11740 } 11741 } 11742 if (chatty) { 11743 if (r == null) { 11744 r = new StringBuilder(256); 11745 } else { 11746 r.append(' '); 11747 } 11748 r.append(p.info.name); 11749 } 11750 } 11751 if (r != null) { 11752 if (DEBUG_PACKAGE_SCANNING) Log.d(TAG, " Providers: " + r); 11753 } 11754 11755 N = pkg.services.size(); 11756 r = null; 11757 for (i=0; i<N; i++) { 11758 PackageParser.Service s = pkg.services.get(i); 11759 s.info.processName = fixProcessName(pkg.applicationInfo.processName, 11760 s.info.processName); 11761 mServices.addService(s); 11762 if (chatty) { 11763 if (r == null) { 11764 r = new StringBuilder(256); 11765 } else { 11766 r.append(' '); 11767 } 11768 r.append(s.info.name); 11769 } 11770 } 11771 if (r != null) { 11772 if (DEBUG_PACKAGE_SCANNING) Log.d(TAG, " Services: " + r); 11773 } 11774 11775 N = pkg.receivers.size(); 11776 r = null; 11777 for (i=0; i<N; i++) { 11778 PackageParser.Activity a = pkg.receivers.get(i); 11779 a.info.processName = fixProcessName(pkg.applicationInfo.processName, 11780 a.info.processName); 11781 mReceivers.addActivity(a, "receiver"); 11782 if (chatty) { 11783 if (r == null) { 11784 r = new StringBuilder(256); 11785 } else { 11786 r.append(' '); 11787 } 11788 r.append(a.info.name); 11789 } 11790 } 11791 if (r != null) { 11792 if (DEBUG_PACKAGE_SCANNING) Log.d(TAG, " Receivers: " + r); 11793 } 11794 11795 N = pkg.activities.size(); 11796 r = null; 11797 for (i=0; i<N; i++) { 11798 PackageParser.Activity a = pkg.activities.get(i); 11799 a.info.processName = fixProcessName(pkg.applicationInfo.processName, 11800 a.info.processName); 11801 mActivities.addActivity(a, "activity"); 11802 if (chatty) { 11803 if (r == null) { 11804 r = new StringBuilder(256); 11805 } else { 11806 r.append(' '); 11807 } 11808 r.append(a.info.name); 11809 } 11810 } 11811 if (r != null) { 11812 if (DEBUG_PACKAGE_SCANNING) Log.d(TAG, " Activities: " + r); 11813 } 11814 11815 N = pkg.permissionGroups.size(); 11816 r = null; 11817 for (i=0; i<N; i++) { 11818 PackageParser.PermissionGroup pg = pkg.permissionGroups.get(i); 11819 PackageParser.PermissionGroup cur = mPermissionGroups.get(pg.info.name); 11820 final String curPackageName = cur == null ? null : cur.info.packageName; 11821 // Dont allow ephemeral apps to define new permission groups. 11822 if ((scanFlags & SCAN_AS_INSTANT_APP) != 0) { 11823 Slog.w(TAG, "Permission group " + pg.info.name + " from package " 11824 + pg.info.packageName 11825 + " ignored: instant apps cannot define new permission groups."); 11826 continue; 11827 } 11828 final boolean isPackageUpdate = pg.info.packageName.equals(curPackageName); 11829 if (cur == null || isPackageUpdate) { 11830 mPermissionGroups.put(pg.info.name, pg); 11831 if (chatty) { 11832 if (r == null) { 11833 r = new StringBuilder(256); 11834 } else { 11835 r.append(' '); 11836 } 11837 if (isPackageUpdate) { 11838 r.append("UPD:"); 11839 } 11840 r.append(pg.info.name); 11841 } 11842 } else { 11843 Slog.w(TAG, "Permission group " + pg.info.name + " from package " 11844 + pg.info.packageName + " ignored: original from " 11845 + cur.info.packageName); 11846 if (chatty) { 11847 if (r == null) { 11848 r = new StringBuilder(256); 11849 } else { 11850 r.append(' '); 11851 } 11852 r.append("DUP:"); 11853 r.append(pg.info.name); 11854 } 11855 } 11856 } 11857 if (r != null) { 11858 if (DEBUG_PACKAGE_SCANNING) Log.d(TAG, " Permission Groups: " + r); 11859 } 11860 11861 N = pkg.permissions.size(); 11862 r = null; 11863 for (i=0; i<N; i++) { 11864 PackageParser.Permission p = pkg.permissions.get(i); 11865 11866 // Dont allow ephemeral apps to define new permissions. 11867 if ((scanFlags & SCAN_AS_INSTANT_APP) != 0) { 11868 Slog.w(TAG, "Permission " + p.info.name + " from package " 11869 + p.info.packageName 11870 + " ignored: instant apps cannot define new permissions."); 11871 continue; 11872 } 11873 11874 // Assume by default that we did not install this permission into the system. 11875 p.info.flags &= ~PermissionInfo.FLAG_INSTALLED; 11876 11877 // Now that permission groups have a special meaning, we ignore permission 11878 // groups for legacy apps to prevent unexpected behavior. In particular, 11879 // permissions for one app being granted to someone just because they happen 11880 // to be in a group defined by another app (before this had no implications). 11881 if (pkg.applicationInfo.targetSdkVersion > Build.VERSION_CODES.LOLLIPOP_MR1) { 11882 p.group = mPermissionGroups.get(p.info.group); 11883 // Warn for a permission in an unknown group. 11884 if (DEBUG_PERMISSIONS && p.info.group != null && p.group == null) { 11885 Slog.i(TAG, "Permission " + p.info.name + " from package " 11886 + p.info.packageName + " in an unknown group " + p.info.group); 11887 } 11888 } 11889 11890 ArrayMap<String, BasePermission> permissionMap = 11891 p.tree ? mSettings.mPermissionTrees 11892 : mSettings.mPermissions; 11893 BasePermission bp = permissionMap.get(p.info.name); 11894 11895 // Allow system apps to redefine non-system permissions 11896 if (bp != null && !Objects.equals(bp.sourcePackage, p.info.packageName)) { 11897 final boolean currentOwnerIsSystem = (bp.perm != null 11898 && isSystemApp(bp.perm.owner)); 11899 if (isSystemApp(p.owner)) { 11900 if (bp.type == BasePermission.TYPE_BUILTIN && bp.perm == null) { 11901 // It's a built-in permission and no owner, take ownership now 11902 bp.packageSetting = pkgSetting; 11903 bp.perm = p; 11904 bp.uid = pkg.applicationInfo.uid; 11905 bp.sourcePackage = p.info.packageName; 11906 p.info.flags |= PermissionInfo.FLAG_INSTALLED; 11907 } else if (!currentOwnerIsSystem) { 11908 String msg = "New decl " + p.owner + " of permission " 11909 + p.info.name + " is system; overriding " + bp.sourcePackage; 11910 reportSettingsProblem(Log.WARN, msg); 11911 bp = null; 11912 } 11913 } 11914 } 11915 11916 if (bp == null) { 11917 bp = new BasePermission(p.info.name, p.info.packageName, 11918 BasePermission.TYPE_NORMAL); 11919 permissionMap.put(p.info.name, bp); 11920 } 11921 11922 if (bp.perm == null) { 11923 if (bp.sourcePackage == null 11924 || bp.sourcePackage.equals(p.info.packageName)) { 11925 BasePermission tree = findPermissionTreeLP(p.info.name); 11926 if (tree == null 11927 || tree.sourcePackage.equals(p.info.packageName)) { 11928 bp.packageSetting = pkgSetting; 11929 bp.perm = p; 11930 bp.uid = pkg.applicationInfo.uid; 11931 bp.sourcePackage = p.info.packageName; 11932 p.info.flags |= PermissionInfo.FLAG_INSTALLED; 11933 if (chatty) { 11934 if (r == null) { 11935 r = new StringBuilder(256); 11936 } else { 11937 r.append(' '); 11938 } 11939 r.append(p.info.name); 11940 } 11941 } else { 11942 Slog.w(TAG, "Permission " + p.info.name + " from package " 11943 + p.info.packageName + " ignored: base tree " 11944 + tree.name + " is from package " 11945 + tree.sourcePackage); 11946 } 11947 } else { 11948 Slog.w(TAG, "Permission " + p.info.name + " from package " 11949 + p.info.packageName + " ignored: original from " 11950 + bp.sourcePackage); 11951 } 11952 } else if (chatty) { 11953 if (r == null) { 11954 r = new StringBuilder(256); 11955 } else { 11956 r.append(' '); 11957 } 11958 r.append("DUP:"); 11959 r.append(p.info.name); 11960 } 11961 if (bp.perm == p) { 11962 bp.protectionLevel = p.info.protectionLevel; 11963 } 11964 } 11965 11966 if (r != null) { 11967 if (DEBUG_PACKAGE_SCANNING) Log.d(TAG, " Permissions: " + r); 11968 } 11969 11970 N = pkg.instrumentation.size(); 11971 r = null; 11972 for (i=0; i<N; i++) { 11973 PackageParser.Instrumentation a = pkg.instrumentation.get(i); 11974 a.info.packageName = pkg.applicationInfo.packageName; 11975 a.info.sourceDir = pkg.applicationInfo.sourceDir; 11976 a.info.publicSourceDir = pkg.applicationInfo.publicSourceDir; 11977 a.info.splitNames = pkg.splitNames; 11978 a.info.splitSourceDirs = pkg.applicationInfo.splitSourceDirs; 11979 a.info.splitPublicSourceDirs = pkg.applicationInfo.splitPublicSourceDirs; 11980 a.info.splitDependencies = pkg.applicationInfo.splitDependencies; 11981 a.info.dataDir = pkg.applicationInfo.dataDir; 11982 a.info.deviceProtectedDataDir = pkg.applicationInfo.deviceProtectedDataDir; 11983 a.info.credentialProtectedDataDir = pkg.applicationInfo.credentialProtectedDataDir; 11984 a.info.nativeLibraryDir = pkg.applicationInfo.nativeLibraryDir; 11985 a.info.secondaryNativeLibraryDir = pkg.applicationInfo.secondaryNativeLibraryDir; 11986 mInstrumentation.put(a.getComponentName(), a); 11987 if (chatty) { 11988 if (r == null) { 11989 r = new StringBuilder(256); 11990 } else { 11991 r.append(' '); 11992 } 11993 r.append(a.info.name); 11994 } 11995 } 11996 if (r != null) { 11997 if (DEBUG_PACKAGE_SCANNING) Log.d(TAG, " Instrumentation: " + r); 11998 } 11999 12000 if (pkg.protectedBroadcasts != null) { 12001 N = pkg.protectedBroadcasts.size(); 12002 synchronized (mProtectedBroadcasts) { 12003 for (i = 0; i < N; i++) { 12004 mProtectedBroadcasts.add(pkg.protectedBroadcasts.get(i)); 12005 } 12006 } 12007 } 12008 } 12009 12010 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 12011 } 12012 12013 /** 12014 * Derive the ABI of a non-system package located at {@code scanFile}. This information 12015 * is derived purely on the basis of the contents of {@code scanFile} and 12016 * {@code cpuAbiOverride}. 12017 * 12018 * If {@code extractLibs} is true, native libraries are extracted from the app if required. 12019 */ 12020 private static void derivePackageAbi(PackageParser.Package pkg, File scanFile, 12021 String cpuAbiOverride, boolean extractLibs, 12022 File appLib32InstallDir) 12023 throws PackageManagerException { 12024 // Give ourselves some initial paths; we'll come back for another 12025 // pass once we've determined ABI below. 12026 setNativeLibraryPaths(pkg, appLib32InstallDir); 12027 12028 // We would never need to extract libs for forward-locked and external packages, 12029 // since the container service will do it for us. We shouldn't attempt to 12030 // extract libs from system app when it was not updated. 12031 if (pkg.isForwardLocked() || pkg.applicationInfo.isExternalAsec() || 12032 (isSystemApp(pkg) && !pkg.isUpdatedSystemApp())) { 12033 extractLibs = false; 12034 } 12035 12036 final String nativeLibraryRootStr = pkg.applicationInfo.nativeLibraryRootDir; 12037 final boolean useIsaSpecificSubdirs = pkg.applicationInfo.nativeLibraryRootRequiresIsa; 12038 12039 NativeLibraryHelper.Handle handle = null; 12040 try { 12041 handle = NativeLibraryHelper.Handle.create(pkg); 12042 // TODO(multiArch): This can be null for apps that didn't go through the 12043 // usual installation process. We can calculate it again, like we 12044 // do during install time. 12045 // 12046 // TODO(multiArch): Why do we need to rescan ASEC apps again ? It seems totally 12047 // unnecessary. 12048 final File nativeLibraryRoot = new File(nativeLibraryRootStr); 12049 12050 // Null out the abis so that they can be recalculated. 12051 pkg.applicationInfo.primaryCpuAbi = null; 12052 pkg.applicationInfo.secondaryCpuAbi = null; 12053 if (isMultiArch(pkg.applicationInfo)) { 12054 // Warn if we've set an abiOverride for multi-lib packages.. 12055 // By definition, we need to copy both 32 and 64 bit libraries for 12056 // such packages. 12057 if (pkg.cpuAbiOverride != null 12058 && !NativeLibraryHelper.CLEAR_ABI_OVERRIDE.equals(pkg.cpuAbiOverride)) { 12059 Slog.w(TAG, "Ignoring abiOverride for multi arch application."); 12060 } 12061 12062 int abi32 = PackageManager.NO_NATIVE_LIBRARIES; 12063 int abi64 = PackageManager.NO_NATIVE_LIBRARIES; 12064 if (Build.SUPPORTED_32_BIT_ABIS.length > 0) { 12065 if (extractLibs) { 12066 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "copyNativeBinaries"); 12067 abi32 = NativeLibraryHelper.copyNativeBinariesForSupportedAbi(handle, 12068 nativeLibraryRoot, Build.SUPPORTED_32_BIT_ABIS, 12069 useIsaSpecificSubdirs); 12070 } else { 12071 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "findSupportedAbi"); 12072 abi32 = NativeLibraryHelper.findSupportedAbi(handle, Build.SUPPORTED_32_BIT_ABIS); 12073 } 12074 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 12075 } 12076 12077 // Shared library native code should be in the APK zip aligned 12078 if (abi32 >= 0 && pkg.isLibrary() && extractLibs) { 12079 throw new PackageManagerException(INSTALL_FAILED_INTERNAL_ERROR, 12080 "Shared library native lib extraction not supported"); 12081 } 12082 12083 maybeThrowExceptionForMultiArchCopy( 12084 "Error unpackaging 32 bit native libs for multiarch app.", abi32); 12085 12086 if (Build.SUPPORTED_64_BIT_ABIS.length > 0) { 12087 if (extractLibs) { 12088 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "copyNativeBinaries"); 12089 abi64 = NativeLibraryHelper.copyNativeBinariesForSupportedAbi(handle, 12090 nativeLibraryRoot, Build.SUPPORTED_64_BIT_ABIS, 12091 useIsaSpecificSubdirs); 12092 } else { 12093 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "findSupportedAbi"); 12094 abi64 = NativeLibraryHelper.findSupportedAbi(handle, Build.SUPPORTED_64_BIT_ABIS); 12095 } 12096 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 12097 } 12098 12099 maybeThrowExceptionForMultiArchCopy( 12100 "Error unpackaging 64 bit native libs for multiarch app.", abi64); 12101 12102 if (abi64 >= 0) { 12103 // Shared library native libs should be in the APK zip aligned 12104 if (extractLibs && pkg.isLibrary()) { 12105 throw new PackageManagerException(INSTALL_FAILED_INTERNAL_ERROR, 12106 "Shared library native lib extraction not supported"); 12107 } 12108 pkg.applicationInfo.primaryCpuAbi = Build.SUPPORTED_64_BIT_ABIS[abi64]; 12109 } 12110 12111 if (abi32 >= 0) { 12112 final String abi = Build.SUPPORTED_32_BIT_ABIS[abi32]; 12113 if (abi64 >= 0) { 12114 if (pkg.use32bitAbi) { 12115 pkg.applicationInfo.secondaryCpuAbi = pkg.applicationInfo.primaryCpuAbi; 12116 pkg.applicationInfo.primaryCpuAbi = abi; 12117 } else { 12118 pkg.applicationInfo.secondaryCpuAbi = abi; 12119 } 12120 } else { 12121 pkg.applicationInfo.primaryCpuAbi = abi; 12122 } 12123 } 12124 } else { 12125 String[] abiList = (cpuAbiOverride != null) ? 12126 new String[] { cpuAbiOverride } : Build.SUPPORTED_ABIS; 12127 12128 // Enable gross and lame hacks for apps that are built with old 12129 // SDK tools. We must scan their APKs for renderscript bitcode and 12130 // not launch them if it's present. Don't bother checking on devices 12131 // that don't have 64 bit support. 12132 boolean needsRenderScriptOverride = false; 12133 if (Build.SUPPORTED_64_BIT_ABIS.length > 0 && cpuAbiOverride == null && 12134 NativeLibraryHelper.hasRenderscriptBitcode(handle)) { 12135 abiList = Build.SUPPORTED_32_BIT_ABIS; 12136 needsRenderScriptOverride = true; 12137 } 12138 12139 final int copyRet; 12140 if (extractLibs) { 12141 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "copyNativeBinaries"); 12142 copyRet = NativeLibraryHelper.copyNativeBinariesForSupportedAbi(handle, 12143 nativeLibraryRoot, abiList, useIsaSpecificSubdirs); 12144 } else { 12145 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "findSupportedAbi"); 12146 copyRet = NativeLibraryHelper.findSupportedAbi(handle, abiList); 12147 } 12148 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 12149 12150 if (copyRet < 0 && copyRet != PackageManager.NO_NATIVE_LIBRARIES) { 12151 throw new PackageManagerException(INSTALL_FAILED_INTERNAL_ERROR, 12152 "Error unpackaging native libs for app, errorCode=" + copyRet); 12153 } 12154 12155 if (copyRet >= 0) { 12156 // Shared libraries that have native libs must be multi-architecture 12157 if (pkg.isLibrary()) { 12158 throw new PackageManagerException(INSTALL_FAILED_INTERNAL_ERROR, 12159 "Shared library with native libs must be multiarch"); 12160 } 12161 pkg.applicationInfo.primaryCpuAbi = abiList[copyRet]; 12162 } else if (copyRet == PackageManager.NO_NATIVE_LIBRARIES && cpuAbiOverride != null) { 12163 pkg.applicationInfo.primaryCpuAbi = cpuAbiOverride; 12164 } else if (needsRenderScriptOverride) { 12165 pkg.applicationInfo.primaryCpuAbi = abiList[0]; 12166 } 12167 } 12168 } catch (IOException ioe) { 12169 Slog.e(TAG, "Unable to get canonical file " + ioe.toString()); 12170 } finally { 12171 IoUtils.closeQuietly(handle); 12172 } 12173 12174 // Now that we've calculated the ABIs and determined if it's an internal app, 12175 // we will go ahead and populate the nativeLibraryPath. 12176 setNativeLibraryPaths(pkg, appLib32InstallDir); 12177 } 12178 12179 /** 12180 * Adjusts ABIs for a set of packages belonging to a shared user so that they all match. 12181 * i.e, so that all packages can be run inside a single process if required. 12182 * 12183 * Optionally, callers can pass in a parsed package via {@code newPackage} in which case 12184 * this function will either try and make the ABI for all packages in {@code packagesForUser} 12185 * match {@code scannedPackage} or will update the ABI of {@code scannedPackage} to match 12186 * the ABI selected for {@code packagesForUser}. This variant is used when installing or 12187 * updating a package that belongs to a shared user. 12188 * 12189 * NOTE: We currently only match for the primary CPU abi string. Matching the secondary 12190 * adds unnecessary complexity. 12191 */ 12192 private void adjustCpuAbisForSharedUserLPw(Set<PackageSetting> packagesForUser, 12193 PackageParser.Package scannedPackage) { 12194 String requiredInstructionSet = null; 12195 if (scannedPackage != null && scannedPackage.applicationInfo.primaryCpuAbi != null) { 12196 requiredInstructionSet = VMRuntime.getInstructionSet( 12197 scannedPackage.applicationInfo.primaryCpuAbi); 12198 } 12199 12200 PackageSetting requirer = null; 12201 for (PackageSetting ps : packagesForUser) { 12202 // If packagesForUser contains scannedPackage, we skip it. This will happen 12203 // when scannedPackage is an update of an existing package. Without this check, 12204 // we will never be able to change the ABI of any package belonging to a shared 12205 // user, even if it's compatible with other packages. 12206 if (scannedPackage == null || !scannedPackage.packageName.equals(ps.name)) { 12207 if (ps.primaryCpuAbiString == null) { 12208 continue; 12209 } 12210 12211 final String instructionSet = VMRuntime.getInstructionSet(ps.primaryCpuAbiString); 12212 if (requiredInstructionSet != null && !instructionSet.equals(requiredInstructionSet)) { 12213 // We have a mismatch between instruction sets (say arm vs arm64) warn about 12214 // this but there's not much we can do. 12215 String errorMessage = "Instruction set mismatch, " 12216 + ((requirer == null) ? "[caller]" : requirer) 12217 + " requires " + requiredInstructionSet + " whereas " + ps 12218 + " requires " + instructionSet; 12219 Slog.w(TAG, errorMessage); 12220 } 12221 12222 if (requiredInstructionSet == null) { 12223 requiredInstructionSet = instructionSet; 12224 requirer = ps; 12225 } 12226 } 12227 } 12228 12229 if (requiredInstructionSet != null) { 12230 String adjustedAbi; 12231 if (requirer != null) { 12232 // requirer != null implies that either scannedPackage was null or that scannedPackage 12233 // did not require an ABI, in which case we have to adjust scannedPackage to match 12234 // the ABI of the set (which is the same as requirer's ABI) 12235 adjustedAbi = requirer.primaryCpuAbiString; 12236 if (scannedPackage != null) { 12237 scannedPackage.applicationInfo.primaryCpuAbi = adjustedAbi; 12238 } 12239 } else { 12240 // requirer == null implies that we're updating all ABIs in the set to 12241 // match scannedPackage. 12242 adjustedAbi = scannedPackage.applicationInfo.primaryCpuAbi; 12243 } 12244 12245 for (PackageSetting ps : packagesForUser) { 12246 if (scannedPackage == null || !scannedPackage.packageName.equals(ps.name)) { 12247 if (ps.primaryCpuAbiString != null) { 12248 continue; 12249 } 12250 12251 ps.primaryCpuAbiString = adjustedAbi; 12252 if (ps.pkg != null && ps.pkg.applicationInfo != null && 12253 !TextUtils.equals(adjustedAbi, ps.pkg.applicationInfo.primaryCpuAbi)) { 12254 ps.pkg.applicationInfo.primaryCpuAbi = adjustedAbi; 12255 if (DEBUG_ABI_SELECTION) { 12256 Slog.i(TAG, "Adjusting ABI for " + ps.name + " to " + adjustedAbi 12257 + " (requirer=" 12258 + (requirer != null ? requirer.pkg : "null") 12259 + ", scannedPackage=" 12260 + (scannedPackage != null ? scannedPackage : "null") 12261 + ")"); 12262 } 12263 try { 12264 mInstaller.rmdex(ps.codePathString, 12265 getDexCodeInstructionSet(getPreferredInstructionSet())); 12266 } catch (InstallerException ignored) { 12267 } 12268 } 12269 } 12270 } 12271 } 12272 } 12273 12274 private void setUpCustomResolverActivity(PackageParser.Package pkg) { 12275 synchronized (mPackages) { 12276 mResolverReplaced = true; 12277 // Set up information for custom user intent resolution activity. 12278 mResolveActivity.applicationInfo = pkg.applicationInfo; 12279 mResolveActivity.name = mCustomResolverComponentName.getClassName(); 12280 mResolveActivity.packageName = pkg.applicationInfo.packageName; 12281 mResolveActivity.processName = pkg.applicationInfo.packageName; 12282 mResolveActivity.launchMode = ActivityInfo.LAUNCH_MULTIPLE; 12283 mResolveActivity.flags = ActivityInfo.FLAG_EXCLUDE_FROM_RECENTS | 12284 ActivityInfo.FLAG_FINISH_ON_CLOSE_SYSTEM_DIALOGS; 12285 mResolveActivity.theme = 0; 12286 mResolveActivity.exported = true; 12287 mResolveActivity.enabled = true; 12288 mResolveInfo.activityInfo = mResolveActivity; 12289 mResolveInfo.priority = 0; 12290 mResolveInfo.preferredOrder = 0; 12291 mResolveInfo.match = 0; 12292 mResolveComponentName = mCustomResolverComponentName; 12293 Slog.i(TAG, "Replacing default ResolverActivity with custom activity: " + 12294 mResolveComponentName); 12295 } 12296 } 12297 12298 private void setUpInstantAppInstallerActivityLP(ActivityInfo installerActivity) { 12299 if (installerActivity == null) { 12300 if (DEBUG_EPHEMERAL) { 12301 Slog.d(TAG, "Clear ephemeral installer activity"); 12302 } 12303 mInstantAppInstallerActivity = null; 12304 return; 12305 } 12306 12307 if (DEBUG_EPHEMERAL) { 12308 Slog.d(TAG, "Set ephemeral installer activity: " 12309 + installerActivity.getComponentName()); 12310 } 12311 // Set up information for ephemeral installer activity 12312 mInstantAppInstallerActivity = installerActivity; 12313 mInstantAppInstallerActivity.flags |= ActivityInfo.FLAG_EXCLUDE_FROM_RECENTS 12314 | ActivityInfo.FLAG_FINISH_ON_CLOSE_SYSTEM_DIALOGS; 12315 mInstantAppInstallerActivity.exported = true; 12316 mInstantAppInstallerActivity.enabled = true; 12317 mInstantAppInstallerInfo.activityInfo = mInstantAppInstallerActivity; 12318 mInstantAppInstallerInfo.priority = 0; 12319 mInstantAppInstallerInfo.preferredOrder = 1; 12320 mInstantAppInstallerInfo.isDefault = true; 12321 mInstantAppInstallerInfo.match = IntentFilter.MATCH_CATEGORY_SCHEME_SPECIFIC_PART 12322 | IntentFilter.MATCH_ADJUSTMENT_NORMAL; 12323 } 12324 12325 private static String calculateBundledApkRoot(final String codePathString) { 12326 final File codePath = new File(codePathString); 12327 final File codeRoot; 12328 if (FileUtils.contains(Environment.getRootDirectory(), codePath)) { 12329 codeRoot = Environment.getRootDirectory(); 12330 } else if (FileUtils.contains(Environment.getOemDirectory(), codePath)) { 12331 codeRoot = Environment.getOemDirectory(); 12332 } else if (FileUtils.contains(Environment.getVendorDirectory(), codePath)) { 12333 codeRoot = Environment.getVendorDirectory(); 12334 } else { 12335 // Unrecognized code path; take its top real segment as the apk root: 12336 // e.g. /something/app/blah.apk => /something 12337 try { 12338 File f = codePath.getCanonicalFile(); 12339 File parent = f.getParentFile(); // non-null because codePath is a file 12340 File tmp; 12341 while ((tmp = parent.getParentFile()) != null) { 12342 f = parent; 12343 parent = tmp; 12344 } 12345 codeRoot = f; 12346 Slog.w(TAG, "Unrecognized code path " 12347 + codePath + " - using " + codeRoot); 12348 } catch (IOException e) { 12349 // Can't canonicalize the code path -- shenanigans? 12350 Slog.w(TAG, "Can't canonicalize code path " + codePath); 12351 return Environment.getRootDirectory().getPath(); 12352 } 12353 } 12354 return codeRoot.getPath(); 12355 } 12356 12357 /** 12358 * Derive and set the location of native libraries for the given package, 12359 * which varies depending on where and how the package was installed. 12360 */ 12361 private static void setNativeLibraryPaths(PackageParser.Package pkg, File appLib32InstallDir) { 12362 final ApplicationInfo info = pkg.applicationInfo; 12363 final String codePath = pkg.codePath; 12364 final File codeFile = new File(codePath); 12365 final boolean bundledApp = info.isSystemApp() && !info.isUpdatedSystemApp(); 12366 final boolean asecApp = info.isForwardLocked() || info.isExternalAsec(); 12367 12368 info.nativeLibraryRootDir = null; 12369 info.nativeLibraryRootRequiresIsa = false; 12370 info.nativeLibraryDir = null; 12371 info.secondaryNativeLibraryDir = null; 12372 12373 if (isApkFile(codeFile)) { 12374 // Monolithic install 12375 if (bundledApp) { 12376 // If "/system/lib64/apkname" exists, assume that is the per-package 12377 // native library directory to use; otherwise use "/system/lib/apkname". 12378 final String apkRoot = calculateBundledApkRoot(info.sourceDir); 12379 final boolean is64Bit = VMRuntime.is64BitInstructionSet( 12380 getPrimaryInstructionSet(info)); 12381 12382 // This is a bundled system app so choose the path based on the ABI. 12383 // if it's a 64 bit abi, use lib64 otherwise use lib32. Note that this 12384 // is just the default path. 12385 final String apkName = deriveCodePathName(codePath); 12386 final String libDir = is64Bit ? LIB64_DIR_NAME : LIB_DIR_NAME; 12387 info.nativeLibraryRootDir = Environment.buildPath(new File(apkRoot), libDir, 12388 apkName).getAbsolutePath(); 12389 12390 if (info.secondaryCpuAbi != null) { 12391 final String secondaryLibDir = is64Bit ? LIB_DIR_NAME : LIB64_DIR_NAME; 12392 info.secondaryNativeLibraryDir = Environment.buildPath(new File(apkRoot), 12393 secondaryLibDir, apkName).getAbsolutePath(); 12394 } 12395 } else if (asecApp) { 12396 info.nativeLibraryRootDir = new File(codeFile.getParentFile(), LIB_DIR_NAME) 12397 .getAbsolutePath(); 12398 } else { 12399 final String apkName = deriveCodePathName(codePath); 12400 info.nativeLibraryRootDir = new File(appLib32InstallDir, apkName) 12401 .getAbsolutePath(); 12402 } 12403 12404 info.nativeLibraryRootRequiresIsa = false; 12405 info.nativeLibraryDir = info.nativeLibraryRootDir; 12406 } else { 12407 // Cluster install 12408 info.nativeLibraryRootDir = new File(codeFile, LIB_DIR_NAME).getAbsolutePath(); 12409 info.nativeLibraryRootRequiresIsa = true; 12410 12411 info.nativeLibraryDir = new File(info.nativeLibraryRootDir, 12412 getPrimaryInstructionSet(info)).getAbsolutePath(); 12413 12414 if (info.secondaryCpuAbi != null) { 12415 info.secondaryNativeLibraryDir = new File(info.nativeLibraryRootDir, 12416 VMRuntime.getInstructionSet(info.secondaryCpuAbi)).getAbsolutePath(); 12417 } 12418 } 12419 } 12420 12421 /** 12422 * Calculate the abis and roots for a bundled app. These can uniquely 12423 * be determined from the contents of the system partition, i.e whether 12424 * it contains 64 or 32 bit shared libraries etc. We do not validate any 12425 * of this information, and instead assume that the system was built 12426 * sensibly. 12427 */ 12428 private static void setBundledAppAbisAndRoots(PackageParser.Package pkg, 12429 PackageSetting pkgSetting) { 12430 final String apkName = deriveCodePathName(pkg.applicationInfo.getCodePath()); 12431 12432 // If "/system/lib64/apkname" exists, assume that is the per-package 12433 // native library directory to use; otherwise use "/system/lib/apkname". 12434 final String apkRoot = calculateBundledApkRoot(pkg.applicationInfo.sourceDir); 12435 setBundledAppAbi(pkg, apkRoot, apkName); 12436 // pkgSetting might be null during rescan following uninstall of updates 12437 // to a bundled app, so accommodate that possibility. The settings in 12438 // that case will be established later from the parsed package. 12439 // 12440 // If the settings aren't null, sync them up with what we've just derived. 12441 // note that apkRoot isn't stored in the package settings. 12442 if (pkgSetting != null) { 12443 pkgSetting.primaryCpuAbiString = pkg.applicationInfo.primaryCpuAbi; 12444 pkgSetting.secondaryCpuAbiString = pkg.applicationInfo.secondaryCpuAbi; 12445 } 12446 } 12447 12448 /** 12449 * Deduces the ABI of a bundled app and sets the relevant fields on the 12450 * parsed pkg object. 12451 * 12452 * @param apkRoot the root of the installed apk, something like {@code /system} or {@code /oem} 12453 * under which system libraries are installed. 12454 * @param apkName the name of the installed package. 12455 */ 12456 private static void setBundledAppAbi(PackageParser.Package pkg, String apkRoot, String apkName) { 12457 final File codeFile = new File(pkg.codePath); 12458 12459 final boolean has64BitLibs; 12460 final boolean has32BitLibs; 12461 if (isApkFile(codeFile)) { 12462 // Monolithic install 12463 has64BitLibs = (new File(apkRoot, new File(LIB64_DIR_NAME, apkName).getPath())).exists(); 12464 has32BitLibs = (new File(apkRoot, new File(LIB_DIR_NAME, apkName).getPath())).exists(); 12465 } else { 12466 // Cluster install 12467 final File rootDir = new File(codeFile, LIB_DIR_NAME); 12468 if (!ArrayUtils.isEmpty(Build.SUPPORTED_64_BIT_ABIS) 12469 && !TextUtils.isEmpty(Build.SUPPORTED_64_BIT_ABIS[0])) { 12470 final String isa = VMRuntime.getInstructionSet(Build.SUPPORTED_64_BIT_ABIS[0]); 12471 has64BitLibs = (new File(rootDir, isa)).exists(); 12472 } else { 12473 has64BitLibs = false; 12474 } 12475 if (!ArrayUtils.isEmpty(Build.SUPPORTED_32_BIT_ABIS) 12476 && !TextUtils.isEmpty(Build.SUPPORTED_32_BIT_ABIS[0])) { 12477 final String isa = VMRuntime.getInstructionSet(Build.SUPPORTED_32_BIT_ABIS[0]); 12478 has32BitLibs = (new File(rootDir, isa)).exists(); 12479 } else { 12480 has32BitLibs = false; 12481 } 12482 } 12483 12484 if (has64BitLibs && !has32BitLibs) { 12485 // The package has 64 bit libs, but not 32 bit libs. Its primary 12486 // ABI should be 64 bit. We can safely assume here that the bundled 12487 // native libraries correspond to the most preferred ABI in the list. 12488 12489 pkg.applicationInfo.primaryCpuAbi = Build.SUPPORTED_64_BIT_ABIS[0]; 12490 pkg.applicationInfo.secondaryCpuAbi = null; 12491 } else if (has32BitLibs && !has64BitLibs) { 12492 // The package has 32 bit libs but not 64 bit libs. Its primary 12493 // ABI should be 32 bit. 12494 12495 pkg.applicationInfo.primaryCpuAbi = Build.SUPPORTED_32_BIT_ABIS[0]; 12496 pkg.applicationInfo.secondaryCpuAbi = null; 12497 } else if (has32BitLibs && has64BitLibs) { 12498 // The application has both 64 and 32 bit bundled libraries. We check 12499 // here that the app declares multiArch support, and warn if it doesn't. 12500 // 12501 // We will be lenient here and record both ABIs. The primary will be the 12502 // ABI that's higher on the list, i.e, a device that's configured to prefer 12503 // 64 bit apps will see a 64 bit primary ABI, 12504 12505 if ((pkg.applicationInfo.flags & ApplicationInfo.FLAG_MULTIARCH) == 0) { 12506 Slog.e(TAG, "Package " + pkg + " has multiple bundled libs, but is not multiarch."); 12507 } 12508 12509 if (VMRuntime.is64BitInstructionSet(getPreferredInstructionSet())) { 12510 pkg.applicationInfo.primaryCpuAbi = Build.SUPPORTED_64_BIT_ABIS[0]; 12511 pkg.applicationInfo.secondaryCpuAbi = Build.SUPPORTED_32_BIT_ABIS[0]; 12512 } else { 12513 pkg.applicationInfo.primaryCpuAbi = Build.SUPPORTED_32_BIT_ABIS[0]; 12514 pkg.applicationInfo.secondaryCpuAbi = Build.SUPPORTED_64_BIT_ABIS[0]; 12515 } 12516 } else { 12517 pkg.applicationInfo.primaryCpuAbi = null; 12518 pkg.applicationInfo.secondaryCpuAbi = null; 12519 } 12520 } 12521 12522 private void killApplication(String pkgName, int appId, String reason) { 12523 killApplication(pkgName, appId, UserHandle.USER_ALL, reason); 12524 } 12525 12526 private void killApplication(String pkgName, int appId, int userId, String reason) { 12527 // Request the ActivityManager to kill the process(only for existing packages) 12528 // so that we do not end up in a confused state while the user is still using the older 12529 // version of the application while the new one gets installed. 12530 final long token = Binder.clearCallingIdentity(); 12531 try { 12532 IActivityManager am = ActivityManager.getService(); 12533 if (am != null) { 12534 try { 12535 am.killApplication(pkgName, appId, userId, reason); 12536 } catch (RemoteException e) { 12537 } 12538 } 12539 } finally { 12540 Binder.restoreCallingIdentity(token); 12541 } 12542 } 12543 12544 private void removePackageLI(PackageParser.Package pkg, boolean chatty) { 12545 // Remove the parent package setting 12546 PackageSetting ps = (PackageSetting) pkg.mExtras; 12547 if (ps != null) { 12548 removePackageLI(ps, chatty); 12549 } 12550 // Remove the child package setting 12551 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 12552 for (int i = 0; i < childCount; i++) { 12553 PackageParser.Package childPkg = pkg.childPackages.get(i); 12554 ps = (PackageSetting) childPkg.mExtras; 12555 if (ps != null) { 12556 removePackageLI(ps, chatty); 12557 } 12558 } 12559 } 12560 12561 void removePackageLI(PackageSetting ps, boolean chatty) { 12562 if (DEBUG_INSTALL) { 12563 if (chatty) 12564 Log.d(TAG, "Removing package " + ps.name); 12565 } 12566 12567 // writer 12568 synchronized (mPackages) { 12569 mPackages.remove(ps.name); 12570 final PackageParser.Package pkg = ps.pkg; 12571 if (pkg != null) { 12572 cleanPackageDataStructuresLILPw(pkg, chatty); 12573 } 12574 } 12575 } 12576 12577 void removeInstalledPackageLI(PackageParser.Package pkg, boolean chatty) { 12578 if (DEBUG_INSTALL) { 12579 if (chatty) 12580 Log.d(TAG, "Removing package " + pkg.applicationInfo.packageName); 12581 } 12582 12583 // writer 12584 synchronized (mPackages) { 12585 // Remove the parent package 12586 mPackages.remove(pkg.applicationInfo.packageName); 12587 cleanPackageDataStructuresLILPw(pkg, chatty); 12588 12589 // Remove the child packages 12590 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 12591 for (int i = 0; i < childCount; i++) { 12592 PackageParser.Package childPkg = pkg.childPackages.get(i); 12593 mPackages.remove(childPkg.applicationInfo.packageName); 12594 cleanPackageDataStructuresLILPw(childPkg, chatty); 12595 } 12596 } 12597 } 12598 12599 void cleanPackageDataStructuresLILPw(PackageParser.Package pkg, boolean chatty) { 12600 int N = pkg.providers.size(); 12601 StringBuilder r = null; 12602 int i; 12603 for (i=0; i<N; i++) { 12604 PackageParser.Provider p = pkg.providers.get(i); 12605 mProviders.removeProvider(p); 12606 if (p.info.authority == null) { 12607 12608 /* There was another ContentProvider with this authority when 12609 * this app was installed so this authority is null, 12610 * Ignore it as we don't have to unregister the provider. 12611 */ 12612 continue; 12613 } 12614 String names[] = p.info.authority.split(";"); 12615 for (int j = 0; j < names.length; j++) { 12616 if (mProvidersByAuthority.get(names[j]) == p) { 12617 mProvidersByAuthority.remove(names[j]); 12618 if (DEBUG_REMOVE) { 12619 if (chatty) 12620 Log.d(TAG, "Unregistered content provider: " + names[j] 12621 + ", className = " + p.info.name + ", isSyncable = " 12622 + p.info.isSyncable); 12623 } 12624 } 12625 } 12626 if (DEBUG_REMOVE && chatty) { 12627 if (r == null) { 12628 r = new StringBuilder(256); 12629 } else { 12630 r.append(' '); 12631 } 12632 r.append(p.info.name); 12633 } 12634 } 12635 if (r != null) { 12636 if (DEBUG_REMOVE) Log.d(TAG, " Providers: " + r); 12637 } 12638 12639 N = pkg.services.size(); 12640 r = null; 12641 for (i=0; i<N; i++) { 12642 PackageParser.Service s = pkg.services.get(i); 12643 mServices.removeService(s); 12644 if (chatty) { 12645 if (r == null) { 12646 r = new StringBuilder(256); 12647 } else { 12648 r.append(' '); 12649 } 12650 r.append(s.info.name); 12651 } 12652 } 12653 if (r != null) { 12654 if (DEBUG_REMOVE) Log.d(TAG, " Services: " + r); 12655 } 12656 12657 N = pkg.receivers.size(); 12658 r = null; 12659 for (i=0; i<N; i++) { 12660 PackageParser.Activity a = pkg.receivers.get(i); 12661 mReceivers.removeActivity(a, "receiver"); 12662 if (DEBUG_REMOVE && chatty) { 12663 if (r == null) { 12664 r = new StringBuilder(256); 12665 } else { 12666 r.append(' '); 12667 } 12668 r.append(a.info.name); 12669 } 12670 } 12671 if (r != null) { 12672 if (DEBUG_REMOVE) Log.d(TAG, " Receivers: " + r); 12673 } 12674 12675 N = pkg.activities.size(); 12676 r = null; 12677 for (i=0; i<N; i++) { 12678 PackageParser.Activity a = pkg.activities.get(i); 12679 mActivities.removeActivity(a, "activity"); 12680 if (DEBUG_REMOVE && chatty) { 12681 if (r == null) { 12682 r = new StringBuilder(256); 12683 } else { 12684 r.append(' '); 12685 } 12686 r.append(a.info.name); 12687 } 12688 } 12689 if (r != null) { 12690 if (DEBUG_REMOVE) Log.d(TAG, " Activities: " + r); 12691 } 12692 12693 N = pkg.permissions.size(); 12694 r = null; 12695 for (i=0; i<N; i++) { 12696 PackageParser.Permission p = pkg.permissions.get(i); 12697 BasePermission bp = mSettings.mPermissions.get(p.info.name); 12698 if (bp == null) { 12699 bp = mSettings.mPermissionTrees.get(p.info.name); 12700 } 12701 if (bp != null && bp.perm == p) { 12702 bp.perm = null; 12703 if (DEBUG_REMOVE && chatty) { 12704 if (r == null) { 12705 r = new StringBuilder(256); 12706 } else { 12707 r.append(' '); 12708 } 12709 r.append(p.info.name); 12710 } 12711 } 12712 if ((p.info.protectionLevel&PermissionInfo.PROTECTION_FLAG_APPOP) != 0) { 12713 ArraySet<String> appOpPkgs = mAppOpPermissionPackages.get(p.info.name); 12714 if (appOpPkgs != null) { 12715 appOpPkgs.remove(pkg.packageName); 12716 } 12717 } 12718 } 12719 if (r != null) { 12720 if (DEBUG_REMOVE) Log.d(TAG, " Permissions: " + r); 12721 } 12722 12723 N = pkg.requestedPermissions.size(); 12724 r = null; 12725 for (i=0; i<N; i++) { 12726 String perm = pkg.requestedPermissions.get(i); 12727 BasePermission bp = mSettings.mPermissions.get(perm); 12728 if (bp != null && (bp.protectionLevel&PermissionInfo.PROTECTION_FLAG_APPOP) != 0) { 12729 ArraySet<String> appOpPkgs = mAppOpPermissionPackages.get(perm); 12730 if (appOpPkgs != null) { 12731 appOpPkgs.remove(pkg.packageName); 12732 if (appOpPkgs.isEmpty()) { 12733 mAppOpPermissionPackages.remove(perm); 12734 } 12735 } 12736 } 12737 } 12738 if (r != null) { 12739 if (DEBUG_REMOVE) Log.d(TAG, " Permissions: " + r); 12740 } 12741 12742 N = pkg.instrumentation.size(); 12743 r = null; 12744 for (i=0; i<N; i++) { 12745 PackageParser.Instrumentation a = pkg.instrumentation.get(i); 12746 mInstrumentation.remove(a.getComponentName()); 12747 if (DEBUG_REMOVE && chatty) { 12748 if (r == null) { 12749 r = new StringBuilder(256); 12750 } else { 12751 r.append(' '); 12752 } 12753 r.append(a.info.name); 12754 } 12755 } 12756 if (r != null) { 12757 if (DEBUG_REMOVE) Log.d(TAG, " Instrumentation: " + r); 12758 } 12759 12760 r = null; 12761 if ((pkg.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 12762 // Only system apps can hold shared libraries. 12763 if (pkg.libraryNames != null) { 12764 for (i = 0; i < pkg.libraryNames.size(); i++) { 12765 String name = pkg.libraryNames.get(i); 12766 if (removeSharedLibraryLPw(name, 0)) { 12767 if (DEBUG_REMOVE && chatty) { 12768 if (r == null) { 12769 r = new StringBuilder(256); 12770 } else { 12771 r.append(' '); 12772 } 12773 r.append(name); 12774 } 12775 } 12776 } 12777 } 12778 } 12779 12780 r = null; 12781 12782 // Any package can hold static shared libraries. 12783 if (pkg.staticSharedLibName != null) { 12784 if (removeSharedLibraryLPw(pkg.staticSharedLibName, pkg.staticSharedLibVersion)) { 12785 if (DEBUG_REMOVE && chatty) { 12786 if (r == null) { 12787 r = new StringBuilder(256); 12788 } else { 12789 r.append(' '); 12790 } 12791 r.append(pkg.staticSharedLibName); 12792 } 12793 } 12794 } 12795 12796 if (r != null) { 12797 if (DEBUG_REMOVE) Log.d(TAG, " Libraries: " + r); 12798 } 12799 } 12800 12801 private static boolean hasPermission(PackageParser.Package pkgInfo, String perm) { 12802 for (int i=pkgInfo.permissions.size()-1; i>=0; i--) { 12803 if (pkgInfo.permissions.get(i).info.name.equals(perm)) { 12804 return true; 12805 } 12806 } 12807 return false; 12808 } 12809 12810 static final int UPDATE_PERMISSIONS_ALL = 1<<0; 12811 static final int UPDATE_PERMISSIONS_REPLACE_PKG = 1<<1; 12812 static final int UPDATE_PERMISSIONS_REPLACE_ALL = 1<<2; 12813 12814 private void updatePermissionsLPw(PackageParser.Package pkg, int flags) { 12815 // Update the parent permissions 12816 updatePermissionsLPw(pkg.packageName, pkg, flags); 12817 // Update the child permissions 12818 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 12819 for (int i = 0; i < childCount; i++) { 12820 PackageParser.Package childPkg = pkg.childPackages.get(i); 12821 updatePermissionsLPw(childPkg.packageName, childPkg, flags); 12822 } 12823 } 12824 12825 private void updatePermissionsLPw(String changingPkg, PackageParser.Package pkgInfo, 12826 int flags) { 12827 final String volumeUuid = (pkgInfo != null) ? getVolumeUuidForPackage(pkgInfo) : null; 12828 updatePermissionsLPw(changingPkg, pkgInfo, volumeUuid, flags); 12829 } 12830 12831 private void updatePermissionsLPw(String changingPkg, 12832 PackageParser.Package pkgInfo, String replaceVolumeUuid, int flags) { 12833 // Make sure there are no dangling permission trees. 12834 Iterator<BasePermission> it = mSettings.mPermissionTrees.values().iterator(); 12835 while (it.hasNext()) { 12836 final BasePermission bp = it.next(); 12837 if (bp.packageSetting == null) { 12838 // We may not yet have parsed the package, so just see if 12839 // we still know about its settings. 12840 bp.packageSetting = mSettings.mPackages.get(bp.sourcePackage); 12841 } 12842 if (bp.packageSetting == null) { 12843 Slog.w(TAG, "Removing dangling permission tree: " + bp.name 12844 + " from package " + bp.sourcePackage); 12845 it.remove(); 12846 } else if (changingPkg != null && changingPkg.equals(bp.sourcePackage)) { 12847 if (pkgInfo == null || !hasPermission(pkgInfo, bp.name)) { 12848 Slog.i(TAG, "Removing old permission tree: " + bp.name 12849 + " from package " + bp.sourcePackage); 12850 flags |= UPDATE_PERMISSIONS_ALL; 12851 it.remove(); 12852 } 12853 } 12854 } 12855 12856 // Make sure all dynamic permissions have been assigned to a package, 12857 // and make sure there are no dangling permissions. 12858 it = mSettings.mPermissions.values().iterator(); 12859 while (it.hasNext()) { 12860 final BasePermission bp = it.next(); 12861 if (bp.type == BasePermission.TYPE_DYNAMIC) { 12862 if (DEBUG_SETTINGS) Log.v(TAG, "Dynamic permission: name=" 12863 + bp.name + " pkg=" + bp.sourcePackage 12864 + " info=" + bp.pendingInfo); 12865 if (bp.packageSetting == null && bp.pendingInfo != null) { 12866 final BasePermission tree = findPermissionTreeLP(bp.name); 12867 if (tree != null && tree.perm != null) { 12868 bp.packageSetting = tree.packageSetting; 12869 bp.perm = new PackageParser.Permission(tree.perm.owner, 12870 new PermissionInfo(bp.pendingInfo)); 12871 bp.perm.info.packageName = tree.perm.info.packageName; 12872 bp.perm.info.name = bp.name; 12873 bp.uid = tree.uid; 12874 } 12875 } 12876 } 12877 if (bp.packageSetting == null) { 12878 // We may not yet have parsed the package, so just see if 12879 // we still know about its settings. 12880 bp.packageSetting = mSettings.mPackages.get(bp.sourcePackage); 12881 } 12882 if (bp.packageSetting == null) { 12883 Slog.w(TAG, "Removing dangling permission: " + bp.name 12884 + " from package " + bp.sourcePackage); 12885 it.remove(); 12886 } else if (changingPkg != null && changingPkg.equals(bp.sourcePackage)) { 12887 if (pkgInfo == null || !hasPermission(pkgInfo, bp.name)) { 12888 Slog.i(TAG, "Removing old permission: " + bp.name 12889 + " from package " + bp.sourcePackage); 12890 flags |= UPDATE_PERMISSIONS_ALL; 12891 it.remove(); 12892 } 12893 } 12894 } 12895 12896 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "grantPermissions"); 12897 // Now update the permissions for all packages, in particular 12898 // replace the granted permissions of the system packages. 12899 if ((flags&UPDATE_PERMISSIONS_ALL) != 0) { 12900 for (PackageParser.Package pkg : mPackages.values()) { 12901 if (pkg != pkgInfo) { 12902 // Only replace for packages on requested volume 12903 final String volumeUuid = getVolumeUuidForPackage(pkg); 12904 final boolean replace = ((flags & UPDATE_PERMISSIONS_REPLACE_ALL) != 0) 12905 && Objects.equals(replaceVolumeUuid, volumeUuid); 12906 grantPermissionsLPw(pkg, replace, changingPkg); 12907 } 12908 } 12909 } 12910 12911 if (pkgInfo != null) { 12912 // Only replace for packages on requested volume 12913 final String volumeUuid = getVolumeUuidForPackage(pkgInfo); 12914 final boolean replace = ((flags & UPDATE_PERMISSIONS_REPLACE_PKG) != 0) 12915 && Objects.equals(replaceVolumeUuid, volumeUuid); 12916 grantPermissionsLPw(pkgInfo, replace, changingPkg); 12917 } 12918 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 12919 } 12920 12921 private void grantPermissionsLPw(PackageParser.Package pkg, boolean replace, 12922 String packageOfInterest) { 12923 // IMPORTANT: There are two types of permissions: install and runtime. 12924 // Install time permissions are granted when the app is installed to 12925 // all device users and users added in the future. Runtime permissions 12926 // are granted at runtime explicitly to specific users. Normal and signature 12927 // protected permissions are install time permissions. Dangerous permissions 12928 // are install permissions if the app's target SDK is Lollipop MR1 or older, 12929 // otherwise they are runtime permissions. This function does not manage 12930 // runtime permissions except for the case an app targeting Lollipop MR1 12931 // being upgraded to target a newer SDK, in which case dangerous permissions 12932 // are transformed from install time to runtime ones. 12933 12934 final PackageSetting ps = (PackageSetting) pkg.mExtras; 12935 if (ps == null) { 12936 return; 12937 } 12938 12939 PermissionsState permissionsState = ps.getPermissionsState(); 12940 PermissionsState origPermissions = permissionsState; 12941 12942 final int[] currentUserIds = UserManagerService.getInstance().getUserIds(); 12943 12944 boolean runtimePermissionsRevoked = false; 12945 int[] changedRuntimePermissionUserIds = EMPTY_INT_ARRAY; 12946 12947 boolean changedInstallPermission = false; 12948 12949 if (replace) { 12950 ps.installPermissionsFixed = false; 12951 if (!ps.isSharedUser()) { 12952 origPermissions = new PermissionsState(permissionsState); 12953 permissionsState.reset(); 12954 } else { 12955 // We need to know only about runtime permission changes since the 12956 // calling code always writes the install permissions state but 12957 // the runtime ones are written only if changed. The only cases of 12958 // changed runtime permissions here are promotion of an install to 12959 // runtime and revocation of a runtime from a shared user. 12960 changedRuntimePermissionUserIds = revokeUnusedSharedUserPermissionsLPw( 12961 ps.sharedUser, UserManagerService.getInstance().getUserIds()); 12962 if (!ArrayUtils.isEmpty(changedRuntimePermissionUserIds)) { 12963 runtimePermissionsRevoked = true; 12964 } 12965 } 12966 } 12967 12968 permissionsState.setGlobalGids(mGlobalGids); 12969 12970 final int N = pkg.requestedPermissions.size(); 12971 for (int i=0; i<N; i++) { 12972 final String name = pkg.requestedPermissions.get(i); 12973 final BasePermission bp = mSettings.mPermissions.get(name); 12974 final boolean appSupportsRuntimePermissions = pkg.applicationInfo.targetSdkVersion 12975 >= Build.VERSION_CODES.M; 12976 12977 if (DEBUG_INSTALL) { 12978 Log.i(TAG, "Package " + pkg.packageName + " checking " + name + ": " + bp); 12979 } 12980 12981 if (bp == null || bp.packageSetting == null) { 12982 if (packageOfInterest == null || packageOfInterest.equals(pkg.packageName)) { 12983 if (DEBUG_PERMISSIONS) { 12984 Slog.i(TAG, "Unknown permission " + name 12985 + " in package " + pkg.packageName); 12986 } 12987 } 12988 continue; 12989 } 12990 12991 12992 // Limit ephemeral apps to ephemeral allowed permissions. 12993 if (pkg.applicationInfo.isInstantApp() && !bp.isInstant()) { 12994 if (DEBUG_PERMISSIONS) { 12995 Log.i(TAG, "Denying non-ephemeral permission " + bp.name + " for package " 12996 + pkg.packageName); 12997 } 12998 continue; 12999 } 13000 13001 if (bp.isRuntimeOnly() && !appSupportsRuntimePermissions) { 13002 if (DEBUG_PERMISSIONS) { 13003 Log.i(TAG, "Denying runtime-only permission " + bp.name + " for package " 13004 + pkg.packageName); 13005 } 13006 continue; 13007 } 13008 13009 final String perm = bp.name; 13010 boolean allowedSig = false; 13011 int grant = GRANT_DENIED; 13012 13013 // Keep track of app op permissions. 13014 if ((bp.protectionLevel & PermissionInfo.PROTECTION_FLAG_APPOP) != 0) { 13015 ArraySet<String> pkgs = mAppOpPermissionPackages.get(bp.name); 13016 if (pkgs == null) { 13017 pkgs = new ArraySet<>(); 13018 mAppOpPermissionPackages.put(bp.name, pkgs); 13019 } 13020 pkgs.add(pkg.packageName); 13021 } 13022 13023 final int level = bp.protectionLevel & PermissionInfo.PROTECTION_MASK_BASE; 13024 switch (level) { 13025 case PermissionInfo.PROTECTION_NORMAL: { 13026 // For all apps normal permissions are install time ones. 13027 grant = GRANT_INSTALL; 13028 } break; 13029 13030 case PermissionInfo.PROTECTION_DANGEROUS: { 13031 // If a permission review is required for legacy apps we represent 13032 // their permissions as always granted runtime ones since we need 13033 // to keep the review required permission flag per user while an 13034 // install permission's state is shared across all users. 13035 if (!appSupportsRuntimePermissions && !mPermissionReviewRequired) { 13036 // For legacy apps dangerous permissions are install time ones. 13037 grant = GRANT_INSTALL; 13038 } else if (origPermissions.hasInstallPermission(bp.name)) { 13039 // For legacy apps that became modern, install becomes runtime. 13040 grant = GRANT_UPGRADE; 13041 } else if (mPromoteSystemApps 13042 && isSystemApp(ps) 13043 && mExistingSystemPackages.contains(ps.name)) { 13044 // For legacy system apps, install becomes runtime. 13045 // We cannot check hasInstallPermission() for system apps since those 13046 // permissions were granted implicitly and not persisted pre-M. 13047 grant = GRANT_UPGRADE; 13048 } else { 13049 // For modern apps keep runtime permissions unchanged. 13050 grant = GRANT_RUNTIME; 13051 } 13052 } break; 13053 13054 case PermissionInfo.PROTECTION_SIGNATURE: { 13055 // For all apps signature permissions are install time ones. 13056 allowedSig = grantSignaturePermission(perm, pkg, bp, origPermissions); 13057 if (allowedSig) { 13058 grant = GRANT_INSTALL; 13059 } 13060 } break; 13061 } 13062 13063 if (DEBUG_PERMISSIONS) { 13064 Slog.i(TAG, "Granting permission " + perm + " to package " + pkg.packageName); 13065 } 13066 13067 if (grant != GRANT_DENIED) { 13068 if (!isSystemApp(ps) && ps.installPermissionsFixed) { 13069 // If this is an existing, non-system package, then 13070 // we can't add any new permissions to it. 13071 if (!allowedSig && !origPermissions.hasInstallPermission(perm)) { 13072 // Except... if this is a permission that was added 13073 // to the platform (note: need to only do this when 13074 // updating the platform). 13075 if (!isNewPlatformPermissionForPackage(perm, pkg)) { 13076 grant = GRANT_DENIED; 13077 } 13078 } 13079 } 13080 13081 switch (grant) { 13082 case GRANT_INSTALL: { 13083 // Revoke this as runtime permission to handle the case of 13084 // a runtime permission being downgraded to an install one. 13085 // Also in permission review mode we keep dangerous permissions 13086 // for legacy apps 13087 for (int userId : UserManagerService.getInstance().getUserIds()) { 13088 if (origPermissions.getRuntimePermissionState( 13089 bp.name, userId) != null) { 13090 // Revoke the runtime permission and clear the flags. 13091 origPermissions.revokeRuntimePermission(bp, userId); 13092 origPermissions.updatePermissionFlags(bp, userId, 13093 PackageManager.MASK_PERMISSION_FLAGS, 0); 13094 // If we revoked a permission permission, we have to write. 13095 changedRuntimePermissionUserIds = ArrayUtils.appendInt( 13096 changedRuntimePermissionUserIds, userId); 13097 } 13098 } 13099 // Grant an install permission. 13100 if (permissionsState.grantInstallPermission(bp) != 13101 PermissionsState.PERMISSION_OPERATION_FAILURE) { 13102 changedInstallPermission = true; 13103 } 13104 } break; 13105 13106 case GRANT_RUNTIME: { 13107 // Grant previously granted runtime permissions. 13108 for (int userId : UserManagerService.getInstance().getUserIds()) { 13109 PermissionState permissionState = origPermissions 13110 .getRuntimePermissionState(bp.name, userId); 13111 int flags = permissionState != null 13112 ? permissionState.getFlags() : 0; 13113 if (origPermissions.hasRuntimePermission(bp.name, userId)) { 13114 // Don't propagate the permission in a permission review mode if 13115 // the former was revoked, i.e. marked to not propagate on upgrade. 13116 // Note that in a permission review mode install permissions are 13117 // represented as constantly granted runtime ones since we need to 13118 // keep a per user state associated with the permission. Also the 13119 // revoke on upgrade flag is no longer applicable and is reset. 13120 final boolean revokeOnUpgrade = (flags & PackageManager 13121 .FLAG_PERMISSION_REVOKE_ON_UPGRADE) != 0; 13122 if (revokeOnUpgrade) { 13123 flags &= ~PackageManager.FLAG_PERMISSION_REVOKE_ON_UPGRADE; 13124 // Since we changed the flags, we have to write. 13125 changedRuntimePermissionUserIds = ArrayUtils.appendInt( 13126 changedRuntimePermissionUserIds, userId); 13127 } 13128 if (!mPermissionReviewRequired || !revokeOnUpgrade) { 13129 if (permissionsState.grantRuntimePermission(bp, userId) == 13130 PermissionsState.PERMISSION_OPERATION_FAILURE) { 13131 // If we cannot put the permission as it was, 13132 // we have to write. 13133 changedRuntimePermissionUserIds = ArrayUtils.appendInt( 13134 changedRuntimePermissionUserIds, userId); 13135 } 13136 } 13137 13138 // If the app supports runtime permissions no need for a review. 13139 if (mPermissionReviewRequired 13140 && appSupportsRuntimePermissions 13141 && (flags & PackageManager 13142 .FLAG_PERMISSION_REVIEW_REQUIRED) != 0) { 13143 flags &= ~PackageManager.FLAG_PERMISSION_REVIEW_REQUIRED; 13144 // Since we changed the flags, we have to write. 13145 changedRuntimePermissionUserIds = ArrayUtils.appendInt( 13146 changedRuntimePermissionUserIds, userId); 13147 } 13148 } else if (mPermissionReviewRequired 13149 && !appSupportsRuntimePermissions) { 13150 // For legacy apps that need a permission review, every new 13151 // runtime permission is granted but it is pending a review. 13152 // We also need to review only platform defined runtime 13153 // permissions as these are the only ones the platform knows 13154 // how to disable the API to simulate revocation as legacy 13155 // apps don't expect to run with revoked permissions. 13156 if (PLATFORM_PACKAGE_NAME.equals(bp.sourcePackage)) { 13157 if ((flags & FLAG_PERMISSION_REVIEW_REQUIRED) == 0) { 13158 flags |= FLAG_PERMISSION_REVIEW_REQUIRED; 13159 // We changed the flags, hence have to write. 13160 changedRuntimePermissionUserIds = ArrayUtils.appendInt( 13161 changedRuntimePermissionUserIds, userId); 13162 } 13163 } 13164 if (permissionsState.grantRuntimePermission(bp, userId) 13165 != PermissionsState.PERMISSION_OPERATION_FAILURE) { 13166 // We changed the permission, hence have to write. 13167 changedRuntimePermissionUserIds = ArrayUtils.appendInt( 13168 changedRuntimePermissionUserIds, userId); 13169 } 13170 } 13171 // Propagate the permission flags. 13172 permissionsState.updatePermissionFlags(bp, userId, flags, flags); 13173 } 13174 } break; 13175 13176 case GRANT_UPGRADE: { 13177 // Grant runtime permissions for a previously held install permission. 13178 PermissionState permissionState = origPermissions 13179 .getInstallPermissionState(bp.name); 13180 final int flags = permissionState != null ? permissionState.getFlags() : 0; 13181 13182 if (origPermissions.revokeInstallPermission(bp) 13183 != PermissionsState.PERMISSION_OPERATION_FAILURE) { 13184 // We will be transferring the permission flags, so clear them. 13185 origPermissions.updatePermissionFlags(bp, UserHandle.USER_ALL, 13186 PackageManager.MASK_PERMISSION_FLAGS, 0); 13187 changedInstallPermission = true; 13188 } 13189 13190 // If the permission is not to be promoted to runtime we ignore it and 13191 // also its other flags as they are not applicable to install permissions. 13192 if ((flags & PackageManager.FLAG_PERMISSION_REVOKE_ON_UPGRADE) == 0) { 13193 for (int userId : currentUserIds) { 13194 if (permissionsState.grantRuntimePermission(bp, userId) != 13195 PermissionsState.PERMISSION_OPERATION_FAILURE) { 13196 // Transfer the permission flags. 13197 permissionsState.updatePermissionFlags(bp, userId, 13198 flags, flags); 13199 // If we granted the permission, we have to write. 13200 changedRuntimePermissionUserIds = ArrayUtils.appendInt( 13201 changedRuntimePermissionUserIds, userId); 13202 } 13203 } 13204 } 13205 } break; 13206 13207 default: { 13208 if (packageOfInterest == null 13209 || packageOfInterest.equals(pkg.packageName)) { 13210 if (DEBUG_PERMISSIONS) { 13211 Slog.i(TAG, "Not granting permission " + perm 13212 + " to package " + pkg.packageName 13213 + " because it was previously installed without"); 13214 } 13215 } 13216 } break; 13217 } 13218 } else { 13219 if (permissionsState.revokeInstallPermission(bp) != 13220 PermissionsState.PERMISSION_OPERATION_FAILURE) { 13221 // Also drop the permission flags. 13222 permissionsState.updatePermissionFlags(bp, UserHandle.USER_ALL, 13223 PackageManager.MASK_PERMISSION_FLAGS, 0); 13224 changedInstallPermission = true; 13225 Slog.i(TAG, "Un-granting permission " + perm 13226 + " from package " + pkg.packageName 13227 + " (protectionLevel=" + bp.protectionLevel 13228 + " flags=0x" + Integer.toHexString(pkg.applicationInfo.flags) 13229 + ")"); 13230 } else if ((bp.protectionLevel&PermissionInfo.PROTECTION_FLAG_APPOP) == 0) { 13231 // Don't print warning for app op permissions, since it is fine for them 13232 // not to be granted, there is a UI for the user to decide. 13233 if (DEBUG_PERMISSIONS 13234 && (packageOfInterest == null 13235 || packageOfInterest.equals(pkg.packageName))) { 13236 Slog.i(TAG, "Not granting permission " + perm 13237 + " to package " + pkg.packageName 13238 + " (protectionLevel=" + bp.protectionLevel 13239 + " flags=0x" + Integer.toHexString(pkg.applicationInfo.flags) 13240 + ")"); 13241 } 13242 } 13243 } 13244 } 13245 13246 if ((changedInstallPermission || replace) && !ps.installPermissionsFixed && 13247 !isSystemApp(ps) || isUpdatedSystemApp(ps)){ 13248 // This is the first that we have heard about this package, so the 13249 // permissions we have now selected are fixed until explicitly 13250 // changed. 13251 ps.installPermissionsFixed = true; 13252 } 13253 13254 // Persist the runtime permissions state for users with changes. If permissions 13255 // were revoked because no app in the shared user declares them we have to 13256 // write synchronously to avoid losing runtime permissions state. 13257 for (int userId : changedRuntimePermissionUserIds) { 13258 mSettings.writeRuntimePermissionsForUserLPr(userId, runtimePermissionsRevoked); 13259 } 13260 } 13261 13262 private boolean isNewPlatformPermissionForPackage(String perm, PackageParser.Package pkg) { 13263 boolean allowed = false; 13264 final int NP = PackageParser.NEW_PERMISSIONS.length; 13265 for (int ip=0; ip<NP; ip++) { 13266 final PackageParser.NewPermissionInfo npi 13267 = PackageParser.NEW_PERMISSIONS[ip]; 13268 if (npi.name.equals(perm) 13269 && pkg.applicationInfo.targetSdkVersion < npi.sdkVersion) { 13270 allowed = true; 13271 Log.i(TAG, "Auto-granting " + perm + " to old pkg " 13272 + pkg.packageName); 13273 break; 13274 } 13275 } 13276 return allowed; 13277 } 13278 13279 private boolean grantSignaturePermission(String perm, PackageParser.Package pkg, 13280 BasePermission bp, PermissionsState origPermissions) { 13281 boolean privilegedPermission = (bp.protectionLevel 13282 & PermissionInfo.PROTECTION_FLAG_PRIVILEGED) != 0; 13283 boolean privappPermissionsDisable = 13284 RoSystemProperties.CONTROL_PRIVAPP_PERMISSIONS_DISABLE; 13285 boolean platformPermission = PLATFORM_PACKAGE_NAME.equals(bp.sourcePackage); 13286 boolean platformPackage = PLATFORM_PACKAGE_NAME.equals(pkg.packageName); 13287 if (!privappPermissionsDisable && privilegedPermission && pkg.isPrivilegedApp() 13288 && !platformPackage && platformPermission) { 13289 final ArraySet<String> allowedPermissions = SystemConfig.getInstance() 13290 .getPrivAppPermissions(pkg.packageName); 13291 final boolean whitelisted = 13292 allowedPermissions != null && allowedPermissions.contains(perm); 13293 if (!whitelisted) { 13294 Slog.w(TAG, "Privileged permission " + perm + " for package " 13295 + pkg.packageName + " - not in privapp-permissions whitelist"); 13296 // Only report violations for apps on system image 13297 if (!mSystemReady && !pkg.isUpdatedSystemApp()) { 13298 // it's only a reportable violation if the permission isn't explicitly denied 13299 final ArraySet<String> deniedPermissions = SystemConfig.getInstance() 13300 .getPrivAppDenyPermissions(pkg.packageName); 13301 final boolean permissionViolation = 13302 deniedPermissions == null || !deniedPermissions.contains(perm); 13303 if (permissionViolation) { 13304 if (mPrivappPermissionsViolations == null) { 13305 mPrivappPermissionsViolations = new ArraySet<>(); 13306 } 13307 mPrivappPermissionsViolations.add(pkg.packageName + ": " + perm); 13308 } else { 13309 return false; 13310 } 13311 } 13312 if (RoSystemProperties.CONTROL_PRIVAPP_PERMISSIONS_ENFORCE) { 13313 return false; 13314 } 13315 } 13316 } 13317 boolean allowed = (compareSignatures( 13318 bp.packageSetting.signatures.mSignatures, pkg.mSignatures) 13319 == PackageManager.SIGNATURE_MATCH) 13320 || (compareSignatures(mPlatformPackage.mSignatures, pkg.mSignatures) 13321 == PackageManager.SIGNATURE_MATCH); 13322 if (!allowed && privilegedPermission) { 13323 if (isSystemApp(pkg)) { 13324 // For updated system applications, a system permission 13325 // is granted only if it had been defined by the original application. 13326 if (pkg.isUpdatedSystemApp()) { 13327 final PackageSetting sysPs = mSettings 13328 .getDisabledSystemPkgLPr(pkg.packageName); 13329 if (sysPs != null && sysPs.getPermissionsState().hasInstallPermission(perm)) { 13330 // If the original was granted this permission, we take 13331 // that grant decision as read and propagate it to the 13332 // update. 13333 if (sysPs.isPrivileged()) { 13334 allowed = true; 13335 } 13336 } else { 13337 // The system apk may have been updated with an older 13338 // version of the one on the data partition, but which 13339 // granted a new system permission that it didn't have 13340 // before. In this case we do want to allow the app to 13341 // now get the new permission if the ancestral apk is 13342 // privileged to get it. 13343 if (sysPs != null && sysPs.pkg != null && sysPs.isPrivileged()) { 13344 for (int j = 0; j < sysPs.pkg.requestedPermissions.size(); j++) { 13345 if (perm.equals(sysPs.pkg.requestedPermissions.get(j))) { 13346 allowed = true; 13347 break; 13348 } 13349 } 13350 } 13351 // Also if a privileged parent package on the system image or any of 13352 // its children requested a privileged permission, the updated child 13353 // packages can also get the permission. 13354 if (pkg.parentPackage != null) { 13355 final PackageSetting disabledSysParentPs = mSettings 13356 .getDisabledSystemPkgLPr(pkg.parentPackage.packageName); 13357 if (disabledSysParentPs != null && disabledSysParentPs.pkg != null 13358 && disabledSysParentPs.isPrivileged()) { 13359 if (isPackageRequestingPermission(disabledSysParentPs.pkg, perm)) { 13360 allowed = true; 13361 } else if (disabledSysParentPs.pkg.childPackages != null) { 13362 final int count = disabledSysParentPs.pkg.childPackages.size(); 13363 for (int i = 0; i < count; i++) { 13364 PackageParser.Package disabledSysChildPkg = 13365 disabledSysParentPs.pkg.childPackages.get(i); 13366 if (isPackageRequestingPermission(disabledSysChildPkg, 13367 perm)) { 13368 allowed = true; 13369 break; 13370 } 13371 } 13372 } 13373 } 13374 } 13375 } 13376 } else { 13377 allowed = isPrivilegedApp(pkg); 13378 } 13379 } 13380 } 13381 if (!allowed) { 13382 if (!allowed && (bp.protectionLevel 13383 & PermissionInfo.PROTECTION_FLAG_PRE23) != 0 13384 && pkg.applicationInfo.targetSdkVersion < Build.VERSION_CODES.M) { 13385 // If this was a previously normal/dangerous permission that got moved 13386 // to a system permission as part of the runtime permission redesign, then 13387 // we still want to blindly grant it to old apps. 13388 allowed = true; 13389 } 13390 if (!allowed && (bp.protectionLevel & PermissionInfo.PROTECTION_FLAG_INSTALLER) != 0 13391 && pkg.packageName.equals(mRequiredInstallerPackage)) { 13392 // If this permission is to be granted to the system installer and 13393 // this app is an installer, then it gets the permission. 13394 allowed = true; 13395 } 13396 if (!allowed && (bp.protectionLevel & PermissionInfo.PROTECTION_FLAG_VERIFIER) != 0 13397 && pkg.packageName.equals(mRequiredVerifierPackage)) { 13398 // If this permission is to be granted to the system verifier and 13399 // this app is a verifier, then it gets the permission. 13400 allowed = true; 13401 } 13402 if (!allowed && (bp.protectionLevel 13403 & PermissionInfo.PROTECTION_FLAG_PREINSTALLED) != 0 13404 && isSystemApp(pkg)) { 13405 // Any pre-installed system app is allowed to get this permission. 13406 allowed = true; 13407 } 13408 if (!allowed && (bp.protectionLevel 13409 & PermissionInfo.PROTECTION_FLAG_DEVELOPMENT) != 0) { 13410 // For development permissions, a development permission 13411 // is granted only if it was already granted. 13412 allowed = origPermissions.hasInstallPermission(perm); 13413 } 13414 if (!allowed && (bp.protectionLevel & PermissionInfo.PROTECTION_FLAG_SETUP) != 0 13415 && pkg.packageName.equals(mSetupWizardPackage)) { 13416 // If this permission is to be granted to the system setup wizard and 13417 // this app is a setup wizard, then it gets the permission. 13418 allowed = true; 13419 } 13420 } 13421 return allowed; 13422 } 13423 13424 private boolean isPackageRequestingPermission(PackageParser.Package pkg, String permission) { 13425 final int permCount = pkg.requestedPermissions.size(); 13426 for (int j = 0; j < permCount; j++) { 13427 String requestedPermission = pkg.requestedPermissions.get(j); 13428 if (permission.equals(requestedPermission)) { 13429 return true; 13430 } 13431 } 13432 return false; 13433 } 13434 13435 final class ActivityIntentResolver 13436 extends IntentResolver<PackageParser.ActivityIntentInfo, ResolveInfo> { 13437 public List<ResolveInfo> queryIntent(Intent intent, String resolvedType, 13438 boolean defaultOnly, int userId) { 13439 if (!sUserManager.exists(userId)) return null; 13440 mFlags = (defaultOnly ? PackageManager.MATCH_DEFAULT_ONLY : 0); 13441 return super.queryIntent(intent, resolvedType, defaultOnly, userId); 13442 } 13443 13444 public List<ResolveInfo> queryIntent(Intent intent, String resolvedType, int flags, 13445 int userId) { 13446 if (!sUserManager.exists(userId)) return null; 13447 mFlags = flags; 13448 return super.queryIntent(intent, resolvedType, 13449 (flags & PackageManager.MATCH_DEFAULT_ONLY) != 0, 13450 userId); 13451 } 13452 13453 public List<ResolveInfo> queryIntentForPackage(Intent intent, String resolvedType, 13454 int flags, ArrayList<PackageParser.Activity> packageActivities, int userId) { 13455 if (!sUserManager.exists(userId)) return null; 13456 if (packageActivities == null) { 13457 return null; 13458 } 13459 mFlags = flags; 13460 final boolean defaultOnly = (flags & PackageManager.MATCH_DEFAULT_ONLY) != 0; 13461 final int N = packageActivities.size(); 13462 ArrayList<PackageParser.ActivityIntentInfo[]> listCut = 13463 new ArrayList<PackageParser.ActivityIntentInfo[]>(N); 13464 13465 ArrayList<PackageParser.ActivityIntentInfo> intentFilters; 13466 for (int i = 0; i < N; ++i) { 13467 intentFilters = packageActivities.get(i).intents; 13468 if (intentFilters != null && intentFilters.size() > 0) { 13469 PackageParser.ActivityIntentInfo[] array = 13470 new PackageParser.ActivityIntentInfo[intentFilters.size()]; 13471 intentFilters.toArray(array); 13472 listCut.add(array); 13473 } 13474 } 13475 return super.queryIntentFromList(intent, resolvedType, defaultOnly, listCut, userId); 13476 } 13477 13478 /** 13479 * Finds a privileged activity that matches the specified activity names. 13480 */ 13481 private PackageParser.Activity findMatchingActivity( 13482 List<PackageParser.Activity> activityList, ActivityInfo activityInfo) { 13483 for (PackageParser.Activity sysActivity : activityList) { 13484 if (sysActivity.info.name.equals(activityInfo.name)) { 13485 return sysActivity; 13486 } 13487 if (sysActivity.info.name.equals(activityInfo.targetActivity)) { 13488 return sysActivity; 13489 } 13490 if (sysActivity.info.targetActivity != null) { 13491 if (sysActivity.info.targetActivity.equals(activityInfo.name)) { 13492 return sysActivity; 13493 } 13494 if (sysActivity.info.targetActivity.equals(activityInfo.targetActivity)) { 13495 return sysActivity; 13496 } 13497 } 13498 } 13499 return null; 13500 } 13501 13502 public class IterGenerator<E> { 13503 public Iterator<E> generate(ActivityIntentInfo info) { 13504 return null; 13505 } 13506 } 13507 13508 public class ActionIterGenerator extends IterGenerator<String> { 13509 @Override 13510 public Iterator<String> generate(ActivityIntentInfo info) { 13511 return info.actionsIterator(); 13512 } 13513 } 13514 13515 public class CategoriesIterGenerator extends IterGenerator<String> { 13516 @Override 13517 public Iterator<String> generate(ActivityIntentInfo info) { 13518 return info.categoriesIterator(); 13519 } 13520 } 13521 13522 public class SchemesIterGenerator extends IterGenerator<String> { 13523 @Override 13524 public Iterator<String> generate(ActivityIntentInfo info) { 13525 return info.schemesIterator(); 13526 } 13527 } 13528 13529 public class AuthoritiesIterGenerator extends IterGenerator<IntentFilter.AuthorityEntry> { 13530 @Override 13531 public Iterator<IntentFilter.AuthorityEntry> generate(ActivityIntentInfo info) { 13532 return info.authoritiesIterator(); 13533 } 13534 } 13535 13536 /** 13537 * <em>WARNING</em> for performance reasons, the passed in intentList WILL BE 13538 * MODIFIED. Do not pass in a list that should not be changed. 13539 */ 13540 private <T> void getIntentListSubset(List<ActivityIntentInfo> intentList, 13541 IterGenerator<T> generator, Iterator<T> searchIterator) { 13542 // loop through the set of actions; every one must be found in the intent filter 13543 while (searchIterator.hasNext()) { 13544 // we must have at least one filter in the list to consider a match 13545 if (intentList.size() == 0) { 13546 break; 13547 } 13548 13549 final T searchAction = searchIterator.next(); 13550 13551 // loop through the set of intent filters 13552 final Iterator<ActivityIntentInfo> intentIter = intentList.iterator(); 13553 while (intentIter.hasNext()) { 13554 final ActivityIntentInfo intentInfo = intentIter.next(); 13555 boolean selectionFound = false; 13556 13557 // loop through the intent filter's selection criteria; at least one 13558 // of them must match the searched criteria 13559 final Iterator<T> intentSelectionIter = generator.generate(intentInfo); 13560 while (intentSelectionIter != null && intentSelectionIter.hasNext()) { 13561 final T intentSelection = intentSelectionIter.next(); 13562 if (intentSelection != null && intentSelection.equals(searchAction)) { 13563 selectionFound = true; 13564 break; 13565 } 13566 } 13567 13568 // the selection criteria wasn't found in this filter's set; this filter 13569 // is not a potential match 13570 if (!selectionFound) { 13571 intentIter.remove(); 13572 } 13573 } 13574 } 13575 } 13576 13577 private boolean isProtectedAction(ActivityIntentInfo filter) { 13578 final Iterator<String> actionsIter = filter.actionsIterator(); 13579 while (actionsIter != null && actionsIter.hasNext()) { 13580 final String filterAction = actionsIter.next(); 13581 if (PROTECTED_ACTIONS.contains(filterAction)) { 13582 return true; 13583 } 13584 } 13585 return false; 13586 } 13587 13588 /** 13589 * Adjusts the priority of the given intent filter according to policy. 13590 * <p> 13591 * <ul> 13592 * <li>The priority for non privileged applications is capped to '0'</li> 13593 * <li>The priority for protected actions on privileged applications is capped to '0'</li> 13594 * <li>The priority for unbundled updates to privileged applications is capped to the 13595 * priority defined on the system partition</li> 13596 * </ul> 13597 * <p> 13598 * <em>NOTE:</em> There is one exception. For security reasons, the setup wizard is 13599 * allowed to obtain any priority on any action. 13600 */ 13601 private void adjustPriority( 13602 List<PackageParser.Activity> systemActivities, ActivityIntentInfo intent) { 13603 // nothing to do; priority is fine as-is 13604 if (intent.getPriority() <= 0) { 13605 return; 13606 } 13607 13608 final ActivityInfo activityInfo = intent.activity.info; 13609 final ApplicationInfo applicationInfo = activityInfo.applicationInfo; 13610 13611 final boolean privilegedApp = 13612 ((applicationInfo.privateFlags & ApplicationInfo.PRIVATE_FLAG_PRIVILEGED) != 0); 13613 if (!privilegedApp) { 13614 // non-privileged applications can never define a priority >0 13615 if (DEBUG_FILTERS) { 13616 Slog.i(TAG, "Non-privileged app; cap priority to 0;" 13617 + " package: " + applicationInfo.packageName 13618 + " activity: " + intent.activity.className 13619 + " origPrio: " + intent.getPriority()); 13620 } 13621 intent.setPriority(0); 13622 return; 13623 } 13624 13625 if (systemActivities == null) { 13626 // the system package is not disabled; we're parsing the system partition 13627 if (isProtectedAction(intent)) { 13628 if (mDeferProtectedFilters) { 13629 // We can't deal with these just yet. No component should ever obtain a 13630 // >0 priority for a protected actions, with ONE exception -- the setup 13631 // wizard. The setup wizard, however, cannot be known until we're able to 13632 // query it for the category CATEGORY_SETUP_WIZARD. Which we can't do 13633 // until all intent filters have been processed. Chicken, meet egg. 13634 // Let the filter temporarily have a high priority and rectify the 13635 // priorities after all system packages have been scanned. 13636 mProtectedFilters.add(intent); 13637 if (DEBUG_FILTERS) { 13638 Slog.i(TAG, "Protected action; save for later;" 13639 + " package: " + applicationInfo.packageName 13640 + " activity: " + intent.activity.className 13641 + " origPrio: " + intent.getPriority()); 13642 } 13643 return; 13644 } else { 13645 if (DEBUG_FILTERS && mSetupWizardPackage == null) { 13646 Slog.i(TAG, "No setup wizard;" 13647 + " All protected intents capped to priority 0"); 13648 } 13649 if (intent.activity.info.packageName.equals(mSetupWizardPackage)) { 13650 if (DEBUG_FILTERS) { 13651 Slog.i(TAG, "Found setup wizard;" 13652 + " allow priority " + intent.getPriority() + ";" 13653 + " package: " + intent.activity.info.packageName 13654 + " activity: " + intent.activity.className 13655 + " priority: " + intent.getPriority()); 13656 } 13657 // setup wizard gets whatever it wants 13658 return; 13659 } 13660 if (DEBUG_FILTERS) { 13661 Slog.i(TAG, "Protected action; cap priority to 0;" 13662 + " package: " + intent.activity.info.packageName 13663 + " activity: " + intent.activity.className 13664 + " origPrio: " + intent.getPriority()); 13665 } 13666 intent.setPriority(0); 13667 return; 13668 } 13669 } 13670 // privileged apps on the system image get whatever priority they request 13671 return; 13672 } 13673 13674 // privileged app unbundled update ... try to find the same activity 13675 final PackageParser.Activity foundActivity = 13676 findMatchingActivity(systemActivities, activityInfo); 13677 if (foundActivity == null) { 13678 // this is a new activity; it cannot obtain >0 priority 13679 if (DEBUG_FILTERS) { 13680 Slog.i(TAG, "New activity; cap priority to 0;" 13681 + " package: " + applicationInfo.packageName 13682 + " activity: " + intent.activity.className 13683 + " origPrio: " + intent.getPriority()); 13684 } 13685 intent.setPriority(0); 13686 return; 13687 } 13688 13689 // found activity, now check for filter equivalence 13690 13691 // a shallow copy is enough; we modify the list, not its contents 13692 final List<ActivityIntentInfo> intentListCopy = 13693 new ArrayList<>(foundActivity.intents); 13694 final List<ActivityIntentInfo> foundFilters = findFilters(intent); 13695 13696 // find matching action subsets 13697 final Iterator<String> actionsIterator = intent.actionsIterator(); 13698 if (actionsIterator != null) { 13699 getIntentListSubset( 13700 intentListCopy, new ActionIterGenerator(), actionsIterator); 13701 if (intentListCopy.size() == 0) { 13702 // no more intents to match; we're not equivalent 13703 if (DEBUG_FILTERS) { 13704 Slog.i(TAG, "Mismatched action; cap priority to 0;" 13705 + " package: " + applicationInfo.packageName 13706 + " activity: " + intent.activity.className 13707 + " origPrio: " + intent.getPriority()); 13708 } 13709 intent.setPriority(0); 13710 return; 13711 } 13712 } 13713 13714 // find matching category subsets 13715 final Iterator<String> categoriesIterator = intent.categoriesIterator(); 13716 if (categoriesIterator != null) { 13717 getIntentListSubset(intentListCopy, new CategoriesIterGenerator(), 13718 categoriesIterator); 13719 if (intentListCopy.size() == 0) { 13720 // no more intents to match; we're not equivalent 13721 if (DEBUG_FILTERS) { 13722 Slog.i(TAG, "Mismatched category; cap priority to 0;" 13723 + " package: " + applicationInfo.packageName 13724 + " activity: " + intent.activity.className 13725 + " origPrio: " + intent.getPriority()); 13726 } 13727 intent.setPriority(0); 13728 return; 13729 } 13730 } 13731 13732 // find matching schemes subsets 13733 final Iterator<String> schemesIterator = intent.schemesIterator(); 13734 if (schemesIterator != null) { 13735 getIntentListSubset(intentListCopy, new SchemesIterGenerator(), 13736 schemesIterator); 13737 if (intentListCopy.size() == 0) { 13738 // no more intents to match; we're not equivalent 13739 if (DEBUG_FILTERS) { 13740 Slog.i(TAG, "Mismatched scheme; cap priority to 0;" 13741 + " package: " + applicationInfo.packageName 13742 + " activity: " + intent.activity.className 13743 + " origPrio: " + intent.getPriority()); 13744 } 13745 intent.setPriority(0); 13746 return; 13747 } 13748 } 13749 13750 // find matching authorities subsets 13751 final Iterator<IntentFilter.AuthorityEntry> 13752 authoritiesIterator = intent.authoritiesIterator(); 13753 if (authoritiesIterator != null) { 13754 getIntentListSubset(intentListCopy, 13755 new AuthoritiesIterGenerator(), 13756 authoritiesIterator); 13757 if (intentListCopy.size() == 0) { 13758 // no more intents to match; we're not equivalent 13759 if (DEBUG_FILTERS) { 13760 Slog.i(TAG, "Mismatched authority; cap priority to 0;" 13761 + " package: " + applicationInfo.packageName 13762 + " activity: " + intent.activity.className 13763 + " origPrio: " + intent.getPriority()); 13764 } 13765 intent.setPriority(0); 13766 return; 13767 } 13768 } 13769 13770 // we found matching filter(s); app gets the max priority of all intents 13771 int cappedPriority = 0; 13772 for (int i = intentListCopy.size() - 1; i >= 0; --i) { 13773 cappedPriority = Math.max(cappedPriority, intentListCopy.get(i).getPriority()); 13774 } 13775 if (intent.getPriority() > cappedPriority) { 13776 if (DEBUG_FILTERS) { 13777 Slog.i(TAG, "Found matching filter(s);" 13778 + " cap priority to " + cappedPriority + ";" 13779 + " package: " + applicationInfo.packageName 13780 + " activity: " + intent.activity.className 13781 + " origPrio: " + intent.getPriority()); 13782 } 13783 intent.setPriority(cappedPriority); 13784 return; 13785 } 13786 // all this for nothing; the requested priority was <= what was on the system 13787 } 13788 13789 public final void addActivity(PackageParser.Activity a, String type) { 13790 mActivities.put(a.getComponentName(), a); 13791 if (DEBUG_SHOW_INFO) 13792 Log.v( 13793 TAG, " " + type + " " + 13794 (a.info.nonLocalizedLabel != null ? a.info.nonLocalizedLabel : a.info.name) + ":"); 13795 if (DEBUG_SHOW_INFO) 13796 Log.v(TAG, " Class=" + a.info.name); 13797 final int NI = a.intents.size(); 13798 for (int j=0; j<NI; j++) { 13799 PackageParser.ActivityIntentInfo intent = a.intents.get(j); 13800 if ("activity".equals(type)) { 13801 final PackageSetting ps = 13802 mSettings.getDisabledSystemPkgLPr(intent.activity.info.packageName); 13803 final List<PackageParser.Activity> systemActivities = 13804 ps != null && ps.pkg != null ? ps.pkg.activities : null; 13805 adjustPriority(systemActivities, intent); 13806 } 13807 if (DEBUG_SHOW_INFO) { 13808 Log.v(TAG, " IntentFilter:"); 13809 intent.dump(new LogPrinter(Log.VERBOSE, TAG), " "); 13810 } 13811 if (!intent.debugCheck()) { 13812 Log.w(TAG, "==> For Activity " + a.info.name); 13813 } 13814 addFilter(intent); 13815 } 13816 } 13817 13818 public final void removeActivity(PackageParser.Activity a, String type) { 13819 mActivities.remove(a.getComponentName()); 13820 if (DEBUG_SHOW_INFO) { 13821 Log.v(TAG, " " + type + " " 13822 + (a.info.nonLocalizedLabel != null ? a.info.nonLocalizedLabel 13823 : a.info.name) + ":"); 13824 Log.v(TAG, " Class=" + a.info.name); 13825 } 13826 final int NI = a.intents.size(); 13827 for (int j=0; j<NI; j++) { 13828 PackageParser.ActivityIntentInfo intent = a.intents.get(j); 13829 if (DEBUG_SHOW_INFO) { 13830 Log.v(TAG, " IntentFilter:"); 13831 intent.dump(new LogPrinter(Log.VERBOSE, TAG), " "); 13832 } 13833 removeFilter(intent); 13834 } 13835 } 13836 13837 @Override 13838 protected boolean allowFilterResult( 13839 PackageParser.ActivityIntentInfo filter, List<ResolveInfo> dest) { 13840 ActivityInfo filterAi = filter.activity.info; 13841 for (int i=dest.size()-1; i>=0; i--) { 13842 ActivityInfo destAi = dest.get(i).activityInfo; 13843 if (destAi.name == filterAi.name 13844 && destAi.packageName == filterAi.packageName) { 13845 return false; 13846 } 13847 } 13848 return true; 13849 } 13850 13851 @Override 13852 protected ActivityIntentInfo[] newArray(int size) { 13853 return new ActivityIntentInfo[size]; 13854 } 13855 13856 @Override 13857 protected boolean isFilterStopped(PackageParser.ActivityIntentInfo filter, int userId) { 13858 if (!sUserManager.exists(userId)) return true; 13859 PackageParser.Package p = filter.activity.owner; 13860 if (p != null) { 13861 PackageSetting ps = (PackageSetting)p.mExtras; 13862 if (ps != null) { 13863 // System apps are never considered stopped for purposes of 13864 // filtering, because there may be no way for the user to 13865 // actually re-launch them. 13866 return (ps.pkgFlags&ApplicationInfo.FLAG_SYSTEM) == 0 13867 && ps.getStopped(userId); 13868 } 13869 } 13870 return false; 13871 } 13872 13873 @Override 13874 protected boolean isPackageForFilter(String packageName, 13875 PackageParser.ActivityIntentInfo info) { 13876 return packageName.equals(info.activity.owner.packageName); 13877 } 13878 13879 @Override 13880 protected ResolveInfo newResult(PackageParser.ActivityIntentInfo info, 13881 int match, int userId) { 13882 if (!sUserManager.exists(userId)) return null; 13883 if (!mSettings.isEnabledAndMatchLPr(info.activity.info, mFlags, userId)) { 13884 return null; 13885 } 13886 final PackageParser.Activity activity = info.activity; 13887 PackageSetting ps = (PackageSetting) activity.owner.mExtras; 13888 if (ps == null) { 13889 return null; 13890 } 13891 final PackageUserState userState = ps.readUserState(userId); 13892 ActivityInfo ai = 13893 PackageParser.generateActivityInfo(activity, mFlags, userState, userId); 13894 if (ai == null) { 13895 return null; 13896 } 13897 final boolean matchExplicitlyVisibleOnly = 13898 (mFlags & PackageManager.MATCH_EXPLICITLY_VISIBLE_ONLY) != 0; 13899 final boolean matchVisibleToInstantApp = 13900 (mFlags & PackageManager.MATCH_VISIBLE_TO_INSTANT_APP_ONLY) != 0; 13901 final boolean componentVisible = 13902 matchVisibleToInstantApp 13903 && info.isVisibleToInstantApp() 13904 && (!matchExplicitlyVisibleOnly || info.isExplicitlyVisibleToInstantApp()); 13905 final boolean matchInstantApp = (mFlags & PackageManager.MATCH_INSTANT) != 0; 13906 // throw out filters that aren't visible to ephemeral apps 13907 if (matchVisibleToInstantApp && !(componentVisible || userState.instantApp)) { 13908 return null; 13909 } 13910 // throw out instant app filters if we're not explicitly requesting them 13911 if (!matchInstantApp && userState.instantApp) { 13912 return null; 13913 } 13914 // throw out instant app filters if updates are available; will trigger 13915 // instant app resolution 13916 if (userState.instantApp && ps.isUpdateAvailable()) { 13917 return null; 13918 } 13919 final ResolveInfo res = new ResolveInfo(); 13920 res.activityInfo = ai; 13921 if ((mFlags&PackageManager.GET_RESOLVED_FILTER) != 0) { 13922 res.filter = info; 13923 } 13924 if (info != null) { 13925 res.handleAllWebDataURI = info.handleAllWebDataURI(); 13926 } 13927 res.priority = info.getPriority(); 13928 res.preferredOrder = activity.owner.mPreferredOrder; 13929 //System.out.println("Result: " + res.activityInfo.className + 13930 // " = " + res.priority); 13931 res.match = match; 13932 res.isDefault = info.hasDefault; 13933 res.labelRes = info.labelRes; 13934 res.nonLocalizedLabel = info.nonLocalizedLabel; 13935 if (userNeedsBadging(userId)) { 13936 res.noResourceId = true; 13937 } else { 13938 res.icon = info.icon; 13939 } 13940 res.iconResourceId = info.icon; 13941 res.system = res.activityInfo.applicationInfo.isSystemApp(); 13942 res.isInstantAppAvailable = userState.instantApp; 13943 return res; 13944 } 13945 13946 @Override 13947 protected void sortResults(List<ResolveInfo> results) { 13948 Collections.sort(results, mResolvePrioritySorter); 13949 } 13950 13951 @Override 13952 protected void dumpFilter(PrintWriter out, String prefix, 13953 PackageParser.ActivityIntentInfo filter) { 13954 out.print(prefix); out.print( 13955 Integer.toHexString(System.identityHashCode(filter.activity))); 13956 out.print(' '); 13957 filter.activity.printComponentShortName(out); 13958 out.print(" filter "); 13959 out.println(Integer.toHexString(System.identityHashCode(filter))); 13960 } 13961 13962 @Override 13963 protected Object filterToLabel(PackageParser.ActivityIntentInfo filter) { 13964 return filter.activity; 13965 } 13966 13967 protected void dumpFilterLabel(PrintWriter out, String prefix, Object label, int count) { 13968 PackageParser.Activity activity = (PackageParser.Activity)label; 13969 out.print(prefix); out.print( 13970 Integer.toHexString(System.identityHashCode(activity))); 13971 out.print(' '); 13972 activity.printComponentShortName(out); 13973 if (count > 1) { 13974 out.print(" ("); out.print(count); out.print(" filters)"); 13975 } 13976 out.println(); 13977 } 13978 13979 // Keys are String (activity class name), values are Activity. 13980 private final ArrayMap<ComponentName, PackageParser.Activity> mActivities 13981 = new ArrayMap<ComponentName, PackageParser.Activity>(); 13982 private int mFlags; 13983 } 13984 13985 private final class ServiceIntentResolver 13986 extends IntentResolver<PackageParser.ServiceIntentInfo, ResolveInfo> { 13987 public List<ResolveInfo> queryIntent(Intent intent, String resolvedType, 13988 boolean defaultOnly, int userId) { 13989 mFlags = defaultOnly ? PackageManager.MATCH_DEFAULT_ONLY : 0; 13990 return super.queryIntent(intent, resolvedType, defaultOnly, userId); 13991 } 13992 13993 public List<ResolveInfo> queryIntent(Intent intent, String resolvedType, int flags, 13994 int userId) { 13995 if (!sUserManager.exists(userId)) return null; 13996 mFlags = flags; 13997 return super.queryIntent(intent, resolvedType, 13998 (flags & PackageManager.MATCH_DEFAULT_ONLY) != 0, 13999 userId); 14000 } 14001 14002 public List<ResolveInfo> queryIntentForPackage(Intent intent, String resolvedType, 14003 int flags, ArrayList<PackageParser.Service> packageServices, int userId) { 14004 if (!sUserManager.exists(userId)) return null; 14005 if (packageServices == null) { 14006 return null; 14007 } 14008 mFlags = flags; 14009 final boolean defaultOnly = (flags&PackageManager.MATCH_DEFAULT_ONLY) != 0; 14010 final int N = packageServices.size(); 14011 ArrayList<PackageParser.ServiceIntentInfo[]> listCut = 14012 new ArrayList<PackageParser.ServiceIntentInfo[]>(N); 14013 14014 ArrayList<PackageParser.ServiceIntentInfo> intentFilters; 14015 for (int i = 0; i < N; ++i) { 14016 intentFilters = packageServices.get(i).intents; 14017 if (intentFilters != null && intentFilters.size() > 0) { 14018 PackageParser.ServiceIntentInfo[] array = 14019 new PackageParser.ServiceIntentInfo[intentFilters.size()]; 14020 intentFilters.toArray(array); 14021 listCut.add(array); 14022 } 14023 } 14024 return super.queryIntentFromList(intent, resolvedType, defaultOnly, listCut, userId); 14025 } 14026 14027 public final void addService(PackageParser.Service s) { 14028 mServices.put(s.getComponentName(), s); 14029 if (DEBUG_SHOW_INFO) { 14030 Log.v(TAG, " " 14031 + (s.info.nonLocalizedLabel != null 14032 ? s.info.nonLocalizedLabel : s.info.name) + ":"); 14033 Log.v(TAG, " Class=" + s.info.name); 14034 } 14035 final int NI = s.intents.size(); 14036 int j; 14037 for (j=0; j<NI; j++) { 14038 PackageParser.ServiceIntentInfo intent = s.intents.get(j); 14039 if (DEBUG_SHOW_INFO) { 14040 Log.v(TAG, " IntentFilter:"); 14041 intent.dump(new LogPrinter(Log.VERBOSE, TAG), " "); 14042 } 14043 if (!intent.debugCheck()) { 14044 Log.w(TAG, "==> For Service " + s.info.name); 14045 } 14046 addFilter(intent); 14047 } 14048 } 14049 14050 public final void removeService(PackageParser.Service s) { 14051 mServices.remove(s.getComponentName()); 14052 if (DEBUG_SHOW_INFO) { 14053 Log.v(TAG, " " + (s.info.nonLocalizedLabel != null 14054 ? s.info.nonLocalizedLabel : s.info.name) + ":"); 14055 Log.v(TAG, " Class=" + s.info.name); 14056 } 14057 final int NI = s.intents.size(); 14058 int j; 14059 for (j=0; j<NI; j++) { 14060 PackageParser.ServiceIntentInfo intent = s.intents.get(j); 14061 if (DEBUG_SHOW_INFO) { 14062 Log.v(TAG, " IntentFilter:"); 14063 intent.dump(new LogPrinter(Log.VERBOSE, TAG), " "); 14064 } 14065 removeFilter(intent); 14066 } 14067 } 14068 14069 @Override 14070 protected boolean allowFilterResult( 14071 PackageParser.ServiceIntentInfo filter, List<ResolveInfo> dest) { 14072 ServiceInfo filterSi = filter.service.info; 14073 for (int i=dest.size()-1; i>=0; i--) { 14074 ServiceInfo destAi = dest.get(i).serviceInfo; 14075 if (destAi.name == filterSi.name 14076 && destAi.packageName == filterSi.packageName) { 14077 return false; 14078 } 14079 } 14080 return true; 14081 } 14082 14083 @Override 14084 protected PackageParser.ServiceIntentInfo[] newArray(int size) { 14085 return new PackageParser.ServiceIntentInfo[size]; 14086 } 14087 14088 @Override 14089 protected boolean isFilterStopped(PackageParser.ServiceIntentInfo filter, int userId) { 14090 if (!sUserManager.exists(userId)) return true; 14091 PackageParser.Package p = filter.service.owner; 14092 if (p != null) { 14093 PackageSetting ps = (PackageSetting)p.mExtras; 14094 if (ps != null) { 14095 // System apps are never considered stopped for purposes of 14096 // filtering, because there may be no way for the user to 14097 // actually re-launch them. 14098 return (ps.pkgFlags & ApplicationInfo.FLAG_SYSTEM) == 0 14099 && ps.getStopped(userId); 14100 } 14101 } 14102 return false; 14103 } 14104 14105 @Override 14106 protected boolean isPackageForFilter(String packageName, 14107 PackageParser.ServiceIntentInfo info) { 14108 return packageName.equals(info.service.owner.packageName); 14109 } 14110 14111 @Override 14112 protected ResolveInfo newResult(PackageParser.ServiceIntentInfo filter, 14113 int match, int userId) { 14114 if (!sUserManager.exists(userId)) return null; 14115 final PackageParser.ServiceIntentInfo info = (PackageParser.ServiceIntentInfo)filter; 14116 if (!mSettings.isEnabledAndMatchLPr(info.service.info, mFlags, userId)) { 14117 return null; 14118 } 14119 final PackageParser.Service service = info.service; 14120 PackageSetting ps = (PackageSetting) service.owner.mExtras; 14121 if (ps == null) { 14122 return null; 14123 } 14124 final PackageUserState userState = ps.readUserState(userId); 14125 ServiceInfo si = PackageParser.generateServiceInfo(service, mFlags, 14126 userState, userId); 14127 if (si == null) { 14128 return null; 14129 } 14130 final boolean matchVisibleToInstantApp = 14131 (mFlags & PackageManager.MATCH_VISIBLE_TO_INSTANT_APP_ONLY) != 0; 14132 final boolean isInstantApp = (mFlags & PackageManager.MATCH_INSTANT) != 0; 14133 // throw out filters that aren't visible to ephemeral apps 14134 if (matchVisibleToInstantApp 14135 && !(info.isVisibleToInstantApp() || userState.instantApp)) { 14136 return null; 14137 } 14138 // throw out ephemeral filters if we're not explicitly requesting them 14139 if (!isInstantApp && userState.instantApp) { 14140 return null; 14141 } 14142 // throw out instant app filters if updates are available; will trigger 14143 // instant app resolution 14144 if (userState.instantApp && ps.isUpdateAvailable()) { 14145 return null; 14146 } 14147 final ResolveInfo res = new ResolveInfo(); 14148 res.serviceInfo = si; 14149 if ((mFlags&PackageManager.GET_RESOLVED_FILTER) != 0) { 14150 res.filter = filter; 14151 } 14152 res.priority = info.getPriority(); 14153 res.preferredOrder = service.owner.mPreferredOrder; 14154 res.match = match; 14155 res.isDefault = info.hasDefault; 14156 res.labelRes = info.labelRes; 14157 res.nonLocalizedLabel = info.nonLocalizedLabel; 14158 res.icon = info.icon; 14159 res.system = res.serviceInfo.applicationInfo.isSystemApp(); 14160 return res; 14161 } 14162 14163 @Override 14164 protected void sortResults(List<ResolveInfo> results) { 14165 Collections.sort(results, mResolvePrioritySorter); 14166 } 14167 14168 @Override 14169 protected void dumpFilter(PrintWriter out, String prefix, 14170 PackageParser.ServiceIntentInfo filter) { 14171 out.print(prefix); out.print( 14172 Integer.toHexString(System.identityHashCode(filter.service))); 14173 out.print(' '); 14174 filter.service.printComponentShortName(out); 14175 out.print(" filter "); 14176 out.println(Integer.toHexString(System.identityHashCode(filter))); 14177 } 14178 14179 @Override 14180 protected Object filterToLabel(PackageParser.ServiceIntentInfo filter) { 14181 return filter.service; 14182 } 14183 14184 protected void dumpFilterLabel(PrintWriter out, String prefix, Object label, int count) { 14185 PackageParser.Service service = (PackageParser.Service)label; 14186 out.print(prefix); out.print( 14187 Integer.toHexString(System.identityHashCode(service))); 14188 out.print(' '); 14189 service.printComponentShortName(out); 14190 if (count > 1) { 14191 out.print(" ("); out.print(count); out.print(" filters)"); 14192 } 14193 out.println(); 14194 } 14195 14196// List<ResolveInfo> filterEnabled(List<ResolveInfo> resolveInfoList) { 14197// final Iterator<ResolveInfo> i = resolveInfoList.iterator(); 14198// final List<ResolveInfo> retList = Lists.newArrayList(); 14199// while (i.hasNext()) { 14200// final ResolveInfo resolveInfo = (ResolveInfo) i; 14201// if (isEnabledLP(resolveInfo.serviceInfo)) { 14202// retList.add(resolveInfo); 14203// } 14204// } 14205// return retList; 14206// } 14207 14208 // Keys are String (activity class name), values are Activity. 14209 private final ArrayMap<ComponentName, PackageParser.Service> mServices 14210 = new ArrayMap<ComponentName, PackageParser.Service>(); 14211 private int mFlags; 14212 } 14213 14214 private final class ProviderIntentResolver 14215 extends IntentResolver<PackageParser.ProviderIntentInfo, ResolveInfo> { 14216 public List<ResolveInfo> queryIntent(Intent intent, String resolvedType, 14217 boolean defaultOnly, int userId) { 14218 mFlags = defaultOnly ? PackageManager.MATCH_DEFAULT_ONLY : 0; 14219 return super.queryIntent(intent, resolvedType, defaultOnly, userId); 14220 } 14221 14222 public List<ResolveInfo> queryIntent(Intent intent, String resolvedType, int flags, 14223 int userId) { 14224 if (!sUserManager.exists(userId)) 14225 return null; 14226 mFlags = flags; 14227 return super.queryIntent(intent, resolvedType, 14228 (flags & PackageManager.MATCH_DEFAULT_ONLY) != 0, 14229 userId); 14230 } 14231 14232 public List<ResolveInfo> queryIntentForPackage(Intent intent, String resolvedType, 14233 int flags, ArrayList<PackageParser.Provider> packageProviders, int userId) { 14234 if (!sUserManager.exists(userId)) 14235 return null; 14236 if (packageProviders == null) { 14237 return null; 14238 } 14239 mFlags = flags; 14240 final boolean defaultOnly = (flags & PackageManager.MATCH_DEFAULT_ONLY) != 0; 14241 final int N = packageProviders.size(); 14242 ArrayList<PackageParser.ProviderIntentInfo[]> listCut = 14243 new ArrayList<PackageParser.ProviderIntentInfo[]>(N); 14244 14245 ArrayList<PackageParser.ProviderIntentInfo> intentFilters; 14246 for (int i = 0; i < N; ++i) { 14247 intentFilters = packageProviders.get(i).intents; 14248 if (intentFilters != null && intentFilters.size() > 0) { 14249 PackageParser.ProviderIntentInfo[] array = 14250 new PackageParser.ProviderIntentInfo[intentFilters.size()]; 14251 intentFilters.toArray(array); 14252 listCut.add(array); 14253 } 14254 } 14255 return super.queryIntentFromList(intent, resolvedType, defaultOnly, listCut, userId); 14256 } 14257 14258 public final void addProvider(PackageParser.Provider p) { 14259 if (mProviders.containsKey(p.getComponentName())) { 14260 Slog.w(TAG, "Provider " + p.getComponentName() + " already defined; ignoring"); 14261 return; 14262 } 14263 14264 mProviders.put(p.getComponentName(), p); 14265 if (DEBUG_SHOW_INFO) { 14266 Log.v(TAG, " " 14267 + (p.info.nonLocalizedLabel != null 14268 ? p.info.nonLocalizedLabel : p.info.name) + ":"); 14269 Log.v(TAG, " Class=" + p.info.name); 14270 } 14271 final int NI = p.intents.size(); 14272 int j; 14273 for (j = 0; j < NI; j++) { 14274 PackageParser.ProviderIntentInfo intent = p.intents.get(j); 14275 if (DEBUG_SHOW_INFO) { 14276 Log.v(TAG, " IntentFilter:"); 14277 intent.dump(new LogPrinter(Log.VERBOSE, TAG), " "); 14278 } 14279 if (!intent.debugCheck()) { 14280 Log.w(TAG, "==> For Provider " + p.info.name); 14281 } 14282 addFilter(intent); 14283 } 14284 } 14285 14286 public final void removeProvider(PackageParser.Provider p) { 14287 mProviders.remove(p.getComponentName()); 14288 if (DEBUG_SHOW_INFO) { 14289 Log.v(TAG, " " + (p.info.nonLocalizedLabel != null 14290 ? p.info.nonLocalizedLabel : p.info.name) + ":"); 14291 Log.v(TAG, " Class=" + p.info.name); 14292 } 14293 final int NI = p.intents.size(); 14294 int j; 14295 for (j = 0; j < NI; j++) { 14296 PackageParser.ProviderIntentInfo intent = p.intents.get(j); 14297 if (DEBUG_SHOW_INFO) { 14298 Log.v(TAG, " IntentFilter:"); 14299 intent.dump(new LogPrinter(Log.VERBOSE, TAG), " "); 14300 } 14301 removeFilter(intent); 14302 } 14303 } 14304 14305 @Override 14306 protected boolean allowFilterResult( 14307 PackageParser.ProviderIntentInfo filter, List<ResolveInfo> dest) { 14308 ProviderInfo filterPi = filter.provider.info; 14309 for (int i = dest.size() - 1; i >= 0; i--) { 14310 ProviderInfo destPi = dest.get(i).providerInfo; 14311 if (destPi.name == filterPi.name 14312 && destPi.packageName == filterPi.packageName) { 14313 return false; 14314 } 14315 } 14316 return true; 14317 } 14318 14319 @Override 14320 protected PackageParser.ProviderIntentInfo[] newArray(int size) { 14321 return new PackageParser.ProviderIntentInfo[size]; 14322 } 14323 14324 @Override 14325 protected boolean isFilterStopped(PackageParser.ProviderIntentInfo filter, int userId) { 14326 if (!sUserManager.exists(userId)) 14327 return true; 14328 PackageParser.Package p = filter.provider.owner; 14329 if (p != null) { 14330 PackageSetting ps = (PackageSetting) p.mExtras; 14331 if (ps != null) { 14332 // System apps are never considered stopped for purposes of 14333 // filtering, because there may be no way for the user to 14334 // actually re-launch them. 14335 return (ps.pkgFlags & ApplicationInfo.FLAG_SYSTEM) == 0 14336 && ps.getStopped(userId); 14337 } 14338 } 14339 return false; 14340 } 14341 14342 @Override 14343 protected boolean isPackageForFilter(String packageName, 14344 PackageParser.ProviderIntentInfo info) { 14345 return packageName.equals(info.provider.owner.packageName); 14346 } 14347 14348 @Override 14349 protected ResolveInfo newResult(PackageParser.ProviderIntentInfo filter, 14350 int match, int userId) { 14351 if (!sUserManager.exists(userId)) 14352 return null; 14353 final PackageParser.ProviderIntentInfo info = filter; 14354 if (!mSettings.isEnabledAndMatchLPr(info.provider.info, mFlags, userId)) { 14355 return null; 14356 } 14357 final PackageParser.Provider provider = info.provider; 14358 PackageSetting ps = (PackageSetting) provider.owner.mExtras; 14359 if (ps == null) { 14360 return null; 14361 } 14362 final PackageUserState userState = ps.readUserState(userId); 14363 final boolean matchVisibleToInstantApp = 14364 (mFlags & PackageManager.MATCH_VISIBLE_TO_INSTANT_APP_ONLY) != 0; 14365 final boolean isInstantApp = (mFlags & PackageManager.MATCH_INSTANT) != 0; 14366 // throw out filters that aren't visible to instant applications 14367 if (matchVisibleToInstantApp 14368 && !(info.isVisibleToInstantApp() || userState.instantApp)) { 14369 return null; 14370 } 14371 // throw out instant application filters if we're not explicitly requesting them 14372 if (!isInstantApp && userState.instantApp) { 14373 return null; 14374 } 14375 // throw out instant application filters if updates are available; will trigger 14376 // instant application resolution 14377 if (userState.instantApp && ps.isUpdateAvailable()) { 14378 return null; 14379 } 14380 ProviderInfo pi = PackageParser.generateProviderInfo(provider, mFlags, 14381 userState, userId); 14382 if (pi == null) { 14383 return null; 14384 } 14385 final ResolveInfo res = new ResolveInfo(); 14386 res.providerInfo = pi; 14387 if ((mFlags & PackageManager.GET_RESOLVED_FILTER) != 0) { 14388 res.filter = filter; 14389 } 14390 res.priority = info.getPriority(); 14391 res.preferredOrder = provider.owner.mPreferredOrder; 14392 res.match = match; 14393 res.isDefault = info.hasDefault; 14394 res.labelRes = info.labelRes; 14395 res.nonLocalizedLabel = info.nonLocalizedLabel; 14396 res.icon = info.icon; 14397 res.system = res.providerInfo.applicationInfo.isSystemApp(); 14398 return res; 14399 } 14400 14401 @Override 14402 protected void sortResults(List<ResolveInfo> results) { 14403 Collections.sort(results, mResolvePrioritySorter); 14404 } 14405 14406 @Override 14407 protected void dumpFilter(PrintWriter out, String prefix, 14408 PackageParser.ProviderIntentInfo filter) { 14409 out.print(prefix); 14410 out.print( 14411 Integer.toHexString(System.identityHashCode(filter.provider))); 14412 out.print(' '); 14413 filter.provider.printComponentShortName(out); 14414 out.print(" filter "); 14415 out.println(Integer.toHexString(System.identityHashCode(filter))); 14416 } 14417 14418 @Override 14419 protected Object filterToLabel(PackageParser.ProviderIntentInfo filter) { 14420 return filter.provider; 14421 } 14422 14423 protected void dumpFilterLabel(PrintWriter out, String prefix, Object label, int count) { 14424 PackageParser.Provider provider = (PackageParser.Provider)label; 14425 out.print(prefix); out.print( 14426 Integer.toHexString(System.identityHashCode(provider))); 14427 out.print(' '); 14428 provider.printComponentShortName(out); 14429 if (count > 1) { 14430 out.print(" ("); out.print(count); out.print(" filters)"); 14431 } 14432 out.println(); 14433 } 14434 14435 private final ArrayMap<ComponentName, PackageParser.Provider> mProviders 14436 = new ArrayMap<ComponentName, PackageParser.Provider>(); 14437 private int mFlags; 14438 } 14439 14440 static final class EphemeralIntentResolver 14441 extends IntentResolver<AuxiliaryResolveInfo, AuxiliaryResolveInfo> { 14442 /** 14443 * The result that has the highest defined order. Ordering applies on a 14444 * per-package basis. Mapping is from package name to Pair of order and 14445 * EphemeralResolveInfo. 14446 * <p> 14447 * NOTE: This is implemented as a field variable for convenience and efficiency. 14448 * By having a field variable, we're able to track filter ordering as soon as 14449 * a non-zero order is defined. Otherwise, multiple loops across the result set 14450 * would be needed to apply ordering. If the intent resolver becomes re-entrant, 14451 * this needs to be contained entirely within {@link #filterResults}. 14452 */ 14453 final ArrayMap<String, Pair<Integer, InstantAppResolveInfo>> mOrderResult = new ArrayMap<>(); 14454 14455 @Override 14456 protected AuxiliaryResolveInfo[] newArray(int size) { 14457 return new AuxiliaryResolveInfo[size]; 14458 } 14459 14460 @Override 14461 protected boolean isPackageForFilter(String packageName, AuxiliaryResolveInfo responseObj) { 14462 return true; 14463 } 14464 14465 @Override 14466 protected AuxiliaryResolveInfo newResult(AuxiliaryResolveInfo responseObj, int match, 14467 int userId) { 14468 if (!sUserManager.exists(userId)) { 14469 return null; 14470 } 14471 final String packageName = responseObj.resolveInfo.getPackageName(); 14472 final Integer order = responseObj.getOrder(); 14473 final Pair<Integer, InstantAppResolveInfo> lastOrderResult = 14474 mOrderResult.get(packageName); 14475 // ordering is enabled and this item's order isn't high enough 14476 if (lastOrderResult != null && lastOrderResult.first >= order) { 14477 return null; 14478 } 14479 final InstantAppResolveInfo res = responseObj.resolveInfo; 14480 if (order > 0) { 14481 // non-zero order, enable ordering 14482 mOrderResult.put(packageName, new Pair<>(order, res)); 14483 } 14484 return responseObj; 14485 } 14486 14487 @Override 14488 protected void filterResults(List<AuxiliaryResolveInfo> results) { 14489 // only do work if ordering is enabled [most of the time it won't be] 14490 if (mOrderResult.size() == 0) { 14491 return; 14492 } 14493 int resultSize = results.size(); 14494 for (int i = 0; i < resultSize; i++) { 14495 final InstantAppResolveInfo info = results.get(i).resolveInfo; 14496 final String packageName = info.getPackageName(); 14497 final Pair<Integer, InstantAppResolveInfo> savedInfo = mOrderResult.get(packageName); 14498 if (savedInfo == null) { 14499 // package doesn't having ordering 14500 continue; 14501 } 14502 if (savedInfo.second == info) { 14503 // circled back to the highest ordered item; remove from order list 14504 mOrderResult.remove(packageName); 14505 if (mOrderResult.size() == 0) { 14506 // no more ordered items 14507 break; 14508 } 14509 continue; 14510 } 14511 // item has a worse order, remove it from the result list 14512 results.remove(i); 14513 resultSize--; 14514 i--; 14515 } 14516 } 14517 } 14518 14519 private static final Comparator<ResolveInfo> mResolvePrioritySorter = 14520 new Comparator<ResolveInfo>() { 14521 public int compare(ResolveInfo r1, ResolveInfo r2) { 14522 int v1 = r1.priority; 14523 int v2 = r2.priority; 14524 //System.out.println("Comparing: q1=" + q1 + " q2=" + q2); 14525 if (v1 != v2) { 14526 return (v1 > v2) ? -1 : 1; 14527 } 14528 v1 = r1.preferredOrder; 14529 v2 = r2.preferredOrder; 14530 if (v1 != v2) { 14531 return (v1 > v2) ? -1 : 1; 14532 } 14533 if (r1.isDefault != r2.isDefault) { 14534 return r1.isDefault ? -1 : 1; 14535 } 14536 v1 = r1.match; 14537 v2 = r2.match; 14538 //System.out.println("Comparing: m1=" + m1 + " m2=" + m2); 14539 if (v1 != v2) { 14540 return (v1 > v2) ? -1 : 1; 14541 } 14542 if (r1.system != r2.system) { 14543 return r1.system ? -1 : 1; 14544 } 14545 if (r1.activityInfo != null) { 14546 return r1.activityInfo.packageName.compareTo(r2.activityInfo.packageName); 14547 } 14548 if (r1.serviceInfo != null) { 14549 return r1.serviceInfo.packageName.compareTo(r2.serviceInfo.packageName); 14550 } 14551 if (r1.providerInfo != null) { 14552 return r1.providerInfo.packageName.compareTo(r2.providerInfo.packageName); 14553 } 14554 return 0; 14555 } 14556 }; 14557 14558 private static final Comparator<ProviderInfo> mProviderInitOrderSorter = 14559 new Comparator<ProviderInfo>() { 14560 public int compare(ProviderInfo p1, ProviderInfo p2) { 14561 final int v1 = p1.initOrder; 14562 final int v2 = p2.initOrder; 14563 return (v1 > v2) ? -1 : ((v1 < v2) ? 1 : 0); 14564 } 14565 }; 14566 14567 public void sendPackageBroadcast(final String action, final String pkg, final Bundle extras, 14568 final int flags, final String targetPkg, final IIntentReceiver finishedReceiver, 14569 final int[] userIds) { 14570 mHandler.post(new Runnable() { 14571 @Override 14572 public void run() { 14573 try { 14574 final IActivityManager am = ActivityManager.getService(); 14575 if (am == null) return; 14576 final int[] resolvedUserIds; 14577 if (userIds == null) { 14578 resolvedUserIds = am.getRunningUserIds(); 14579 } else { 14580 resolvedUserIds = userIds; 14581 } 14582 for (int id : resolvedUserIds) { 14583 final Intent intent = new Intent(action, 14584 pkg != null ? Uri.fromParts(PACKAGE_SCHEME, pkg, null) : null); 14585 if (extras != null) { 14586 intent.putExtras(extras); 14587 } 14588 if (targetPkg != null) { 14589 intent.setPackage(targetPkg); 14590 } 14591 // Modify the UID when posting to other users 14592 int uid = intent.getIntExtra(Intent.EXTRA_UID, -1); 14593 if (uid > 0 && UserHandle.getUserId(uid) != id) { 14594 uid = UserHandle.getUid(id, UserHandle.getAppId(uid)); 14595 intent.putExtra(Intent.EXTRA_UID, uid); 14596 } 14597 intent.putExtra(Intent.EXTRA_USER_HANDLE, id); 14598 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT | flags); 14599 if (DEBUG_BROADCASTS) { 14600 RuntimeException here = new RuntimeException("here"); 14601 here.fillInStackTrace(); 14602 Slog.d(TAG, "Sending to user " + id + ": " 14603 + intent.toShortString(false, true, false, false) 14604 + " " + intent.getExtras(), here); 14605 } 14606 am.broadcastIntent(null, intent, null, finishedReceiver, 14607 0, null, null, null, android.app.AppOpsManager.OP_NONE, 14608 null, finishedReceiver != null, false, id); 14609 } 14610 } catch (RemoteException ex) { 14611 } 14612 } 14613 }); 14614 } 14615 14616 /** 14617 * Check if the external storage media is available. This is true if there 14618 * is a mounted external storage medium or if the external storage is 14619 * emulated. 14620 */ 14621 private boolean isExternalMediaAvailable() { 14622 return mMediaMounted || Environment.isExternalStorageEmulated(); 14623 } 14624 14625 @Override 14626 public PackageCleanItem nextPackageToClean(PackageCleanItem lastPackage) { 14627 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 14628 return null; 14629 } 14630 // writer 14631 synchronized (mPackages) { 14632 if (!isExternalMediaAvailable()) { 14633 // If the external storage is no longer mounted at this point, 14634 // the caller may not have been able to delete all of this 14635 // packages files and can not delete any more. Bail. 14636 return null; 14637 } 14638 final ArrayList<PackageCleanItem> pkgs = mSettings.mPackagesToBeCleaned; 14639 if (lastPackage != null) { 14640 pkgs.remove(lastPackage); 14641 } 14642 if (pkgs.size() > 0) { 14643 return pkgs.get(0); 14644 } 14645 } 14646 return null; 14647 } 14648 14649 void schedulePackageCleaning(String packageName, int userId, boolean andCode) { 14650 final Message msg = mHandler.obtainMessage(START_CLEANING_PACKAGE, 14651 userId, andCode ? 1 : 0, packageName); 14652 if (mSystemReady) { 14653 msg.sendToTarget(); 14654 } else { 14655 if (mPostSystemReadyMessages == null) { 14656 mPostSystemReadyMessages = new ArrayList<>(); 14657 } 14658 mPostSystemReadyMessages.add(msg); 14659 } 14660 } 14661 14662 void startCleaningPackages() { 14663 // reader 14664 if (!isExternalMediaAvailable()) { 14665 return; 14666 } 14667 synchronized (mPackages) { 14668 if (mSettings.mPackagesToBeCleaned.isEmpty()) { 14669 return; 14670 } 14671 } 14672 Intent intent = new Intent(PackageManager.ACTION_CLEAN_EXTERNAL_STORAGE); 14673 intent.setComponent(DEFAULT_CONTAINER_COMPONENT); 14674 IActivityManager am = ActivityManager.getService(); 14675 if (am != null) { 14676 int dcsUid = -1; 14677 synchronized (mPackages) { 14678 if (!mDefaultContainerWhitelisted) { 14679 mDefaultContainerWhitelisted = true; 14680 PackageSetting ps = mSettings.mPackages.get(DEFAULT_CONTAINER_PACKAGE); 14681 dcsUid = UserHandle.getUid(UserHandle.USER_SYSTEM, ps.appId); 14682 } 14683 } 14684 try { 14685 if (dcsUid > 0) { 14686 am.backgroundWhitelistUid(dcsUid); 14687 } 14688 am.startService(null, intent, null, false, mContext.getOpPackageName(), 14689 UserHandle.USER_SYSTEM); 14690 } catch (RemoteException e) { 14691 } 14692 } 14693 } 14694 14695 @Override 14696 public void installPackageAsUser(String originPath, IPackageInstallObserver2 observer, 14697 int installFlags, String installerPackageName, int userId) { 14698 mContext.enforceCallingOrSelfPermission(android.Manifest.permission.INSTALL_PACKAGES, null); 14699 14700 final int callingUid = Binder.getCallingUid(); 14701 enforceCrossUserPermission(callingUid, userId, 14702 true /* requireFullPermission */, true /* checkShell */, "installPackageAsUser"); 14703 14704 if (isUserRestricted(userId, UserManager.DISALLOW_INSTALL_APPS)) { 14705 try { 14706 if (observer != null) { 14707 observer.onPackageInstalled("", INSTALL_FAILED_USER_RESTRICTED, null, null); 14708 } 14709 } catch (RemoteException re) { 14710 } 14711 return; 14712 } 14713 14714 if ((callingUid == Process.SHELL_UID) || (callingUid == Process.ROOT_UID)) { 14715 installFlags |= PackageManager.INSTALL_FROM_ADB; 14716 14717 } else { 14718 // Caller holds INSTALL_PACKAGES permission, so we're less strict 14719 // about installerPackageName. 14720 14721 installFlags &= ~PackageManager.INSTALL_FROM_ADB; 14722 installFlags &= ~PackageManager.INSTALL_ALL_USERS; 14723 } 14724 14725 UserHandle user; 14726 if ((installFlags & PackageManager.INSTALL_ALL_USERS) != 0) { 14727 user = UserHandle.ALL; 14728 } else { 14729 user = new UserHandle(userId); 14730 } 14731 14732 // Only system components can circumvent runtime permissions when installing. 14733 if ((installFlags & PackageManager.INSTALL_GRANT_RUNTIME_PERMISSIONS) != 0 14734 && mContext.checkCallingOrSelfPermission(Manifest.permission 14735 .INSTALL_GRANT_RUNTIME_PERMISSIONS) == PackageManager.PERMISSION_DENIED) { 14736 throw new SecurityException("You need the " 14737 + "android.permission.INSTALL_GRANT_RUNTIME_PERMISSIONS permission " 14738 + "to use the PackageManager.INSTALL_GRANT_RUNTIME_PERMISSIONS flag"); 14739 } 14740 14741 if ((installFlags & PackageManager.INSTALL_FORWARD_LOCK) != 0 14742 || (installFlags & PackageManager.INSTALL_EXTERNAL) != 0) { 14743 throw new IllegalArgumentException( 14744 "New installs into ASEC containers no longer supported"); 14745 } 14746 14747 final File originFile = new File(originPath); 14748 final OriginInfo origin = OriginInfo.fromUntrustedFile(originFile); 14749 14750 final Message msg = mHandler.obtainMessage(INIT_COPY); 14751 final VerificationInfo verificationInfo = new VerificationInfo( 14752 null /*originatingUri*/, null /*referrer*/, -1 /*originatingUid*/, callingUid); 14753 final InstallParams params = new InstallParams(origin, null /*moveInfo*/, observer, 14754 installFlags, installerPackageName, null /*volumeUuid*/, verificationInfo, user, 14755 null /*packageAbiOverride*/, null /*grantedPermissions*/, 14756 null /*certificates*/, PackageManager.INSTALL_REASON_UNKNOWN); 14757 params.setTraceMethod("installAsUser").setTraceCookie(System.identityHashCode(params)); 14758 msg.obj = params; 14759 14760 Trace.asyncTraceBegin(TRACE_TAG_PACKAGE_MANAGER, "installAsUser", 14761 System.identityHashCode(msg.obj)); 14762 Trace.asyncTraceBegin(TRACE_TAG_PACKAGE_MANAGER, "queueInstall", 14763 System.identityHashCode(msg.obj)); 14764 14765 mHandler.sendMessage(msg); 14766 } 14767 14768 14769 /** 14770 * Ensure that the install reason matches what we know about the package installer (e.g. whether 14771 * it is acting on behalf on an enterprise or the user). 14772 * 14773 * Note that the ordering of the conditionals in this method is important. The checks we perform 14774 * are as follows, in this order: 14775 * 14776 * 1) If the install is being performed by a system app, we can trust the app to have set the 14777 * install reason correctly. Thus, we pass through the install reason unchanged, no matter 14778 * what it is. 14779 * 2) If the install is being performed by a device or profile owner app, the install reason 14780 * should be enterprise policy. However, we cannot be sure that the device or profile owner 14781 * set the install reason correctly. If the app targets an older SDK version where install 14782 * reasons did not exist yet, or if the app author simply forgot, the install reason may be 14783 * unset or wrong. Thus, we force the install reason to be enterprise policy. 14784 * 3) In all other cases, the install is being performed by a regular app that is neither part 14785 * of the system nor a device or profile owner. We have no reason to believe that this app is 14786 * acting on behalf of the enterprise admin. Thus, we check whether the install reason was 14787 * set to enterprise policy and if so, change it to unknown instead. 14788 */ 14789 private int fixUpInstallReason(String installerPackageName, int installerUid, 14790 int installReason) { 14791 if (checkUidPermission(android.Manifest.permission.INSTALL_PACKAGES, installerUid) 14792 == PERMISSION_GRANTED) { 14793 // If the install is being performed by a system app, we trust that app to have set the 14794 // install reason correctly. 14795 return installReason; 14796 } 14797 14798 final IDevicePolicyManager dpm = IDevicePolicyManager.Stub.asInterface( 14799 ServiceManager.getService(Context.DEVICE_POLICY_SERVICE)); 14800 if (dpm != null) { 14801 ComponentName owner = null; 14802 try { 14803 owner = dpm.getDeviceOwnerComponent(true /* callingUserOnly */); 14804 if (owner == null) { 14805 owner = dpm.getProfileOwner(UserHandle.getUserId(installerUid)); 14806 } 14807 } catch (RemoteException e) { 14808 } 14809 if (owner != null && owner.getPackageName().equals(installerPackageName)) { 14810 // If the install is being performed by a device or profile owner, the install 14811 // reason should be enterprise policy. 14812 return PackageManager.INSTALL_REASON_POLICY; 14813 } 14814 } 14815 14816 if (installReason == PackageManager.INSTALL_REASON_POLICY) { 14817 // If the install is being performed by a regular app (i.e. neither system app nor 14818 // device or profile owner), we have no reason to believe that the app is acting on 14819 // behalf of an enterprise. If the app set the install reason to enterprise policy, 14820 // change it to unknown instead. 14821 return PackageManager.INSTALL_REASON_UNKNOWN; 14822 } 14823 14824 // If the install is being performed by a regular app and the install reason was set to any 14825 // value but enterprise policy, leave the install reason unchanged. 14826 return installReason; 14827 } 14828 14829 void installStage(String packageName, File stagedDir, String stagedCid, 14830 IPackageInstallObserver2 observer, PackageInstaller.SessionParams sessionParams, 14831 String installerPackageName, int installerUid, UserHandle user, 14832 Certificate[][] certificates) { 14833 if (DEBUG_EPHEMERAL) { 14834 if ((sessionParams.installFlags & PackageManager.INSTALL_INSTANT_APP) != 0) { 14835 Slog.d(TAG, "Ephemeral install of " + packageName); 14836 } 14837 } 14838 final VerificationInfo verificationInfo = new VerificationInfo( 14839 sessionParams.originatingUri, sessionParams.referrerUri, 14840 sessionParams.originatingUid, installerUid); 14841 14842 final OriginInfo origin; 14843 if (stagedDir != null) { 14844 origin = OriginInfo.fromStagedFile(stagedDir); 14845 } else { 14846 origin = OriginInfo.fromStagedContainer(stagedCid); 14847 } 14848 14849 final Message msg = mHandler.obtainMessage(INIT_COPY); 14850 final int installReason = fixUpInstallReason(installerPackageName, installerUid, 14851 sessionParams.installReason); 14852 final InstallParams params = new InstallParams(origin, null, observer, 14853 sessionParams.installFlags, installerPackageName, sessionParams.volumeUuid, 14854 verificationInfo, user, sessionParams.abiOverride, 14855 sessionParams.grantedRuntimePermissions, certificates, installReason); 14856 params.setTraceMethod("installStage").setTraceCookie(System.identityHashCode(params)); 14857 msg.obj = params; 14858 14859 Trace.asyncTraceBegin(TRACE_TAG_PACKAGE_MANAGER, "installStage", 14860 System.identityHashCode(msg.obj)); 14861 Trace.asyncTraceBegin(TRACE_TAG_PACKAGE_MANAGER, "queueInstall", 14862 System.identityHashCode(msg.obj)); 14863 14864 mHandler.sendMessage(msg); 14865 } 14866 14867 private void sendPackageAddedForUser(String packageName, PackageSetting pkgSetting, 14868 int userId) { 14869 final boolean isSystem = isSystemApp(pkgSetting) || isUpdatedSystemApp(pkgSetting); 14870 sendPackageAddedForNewUsers(packageName, isSystem /*sendBootCompleted*/, 14871 false /*startReceiver*/, pkgSetting.appId, userId); 14872 14873 // Send a session commit broadcast 14874 final PackageInstaller.SessionInfo info = new PackageInstaller.SessionInfo(); 14875 info.installReason = pkgSetting.getInstallReason(userId); 14876 info.appPackageName = packageName; 14877 sendSessionCommitBroadcast(info, userId); 14878 } 14879 14880 public void sendPackageAddedForNewUsers(String packageName, boolean sendBootCompleted, 14881 boolean includeStopped, int appId, int... userIds) { 14882 if (ArrayUtils.isEmpty(userIds)) { 14883 return; 14884 } 14885 Bundle extras = new Bundle(1); 14886 // Set to UID of the first user, EXTRA_UID is automatically updated in sendPackageBroadcast 14887 extras.putInt(Intent.EXTRA_UID, UserHandle.getUid(userIds[0], appId)); 14888 14889 sendPackageBroadcast(Intent.ACTION_PACKAGE_ADDED, 14890 packageName, extras, 0, null, null, userIds); 14891 if (sendBootCompleted) { 14892 mHandler.post(() -> { 14893 for (int userId : userIds) { 14894 sendBootCompletedBroadcastToSystemApp( 14895 packageName, includeStopped, userId); 14896 } 14897 } 14898 ); 14899 } 14900 } 14901 14902 /** 14903 * The just-installed/enabled app is bundled on the system, so presumed to be able to run 14904 * automatically without needing an explicit launch. 14905 * Send it a LOCKED_BOOT_COMPLETED/BOOT_COMPLETED if it would ordinarily have gotten ones. 14906 */ 14907 private void sendBootCompletedBroadcastToSystemApp(String packageName, boolean includeStopped, 14908 int userId) { 14909 // If user is not running, the app didn't miss any broadcast 14910 if (!mUserManagerInternal.isUserRunning(userId)) { 14911 return; 14912 } 14913 final IActivityManager am = ActivityManager.getService(); 14914 try { 14915 // Deliver LOCKED_BOOT_COMPLETED first 14916 Intent lockedBcIntent = new Intent(Intent.ACTION_LOCKED_BOOT_COMPLETED) 14917 .setPackage(packageName); 14918 if (includeStopped) { 14919 lockedBcIntent.addFlags(Intent.FLAG_INCLUDE_STOPPED_PACKAGES); 14920 } 14921 final String[] requiredPermissions = {Manifest.permission.RECEIVE_BOOT_COMPLETED}; 14922 am.broadcastIntent(null, lockedBcIntent, null, null, 0, null, null, requiredPermissions, 14923 android.app.AppOpsManager.OP_NONE, null, false, false, userId); 14924 14925 // Deliver BOOT_COMPLETED only if user is unlocked 14926 if (mUserManagerInternal.isUserUnlockingOrUnlocked(userId)) { 14927 Intent bcIntent = new Intent(Intent.ACTION_BOOT_COMPLETED).setPackage(packageName); 14928 if (includeStopped) { 14929 bcIntent.addFlags(Intent.FLAG_INCLUDE_STOPPED_PACKAGES); 14930 } 14931 am.broadcastIntent(null, bcIntent, null, null, 0, null, null, requiredPermissions, 14932 android.app.AppOpsManager.OP_NONE, null, false, false, userId); 14933 } 14934 } catch (RemoteException e) { 14935 throw e.rethrowFromSystemServer(); 14936 } 14937 } 14938 14939 @Override 14940 public boolean setApplicationHiddenSettingAsUser(String packageName, boolean hidden, 14941 int userId) { 14942 mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MANAGE_USERS, null); 14943 PackageSetting pkgSetting; 14944 final int callingUid = Binder.getCallingUid(); 14945 enforceCrossUserPermission(callingUid, userId, 14946 true /* requireFullPermission */, true /* checkShell */, 14947 "setApplicationHiddenSetting for user " + userId); 14948 14949 if (hidden && isPackageDeviceAdmin(packageName, userId)) { 14950 Slog.w(TAG, "Not hiding package " + packageName + ": has active device admin"); 14951 return false; 14952 } 14953 14954 long callingId = Binder.clearCallingIdentity(); 14955 try { 14956 boolean sendAdded = false; 14957 boolean sendRemoved = false; 14958 // writer 14959 synchronized (mPackages) { 14960 pkgSetting = mSettings.mPackages.get(packageName); 14961 if (pkgSetting == null) { 14962 return false; 14963 } 14964 if (filterAppAccessLPr(pkgSetting, callingUid, userId)) { 14965 return false; 14966 } 14967 // Do not allow "android" is being disabled 14968 if ("android".equals(packageName)) { 14969 Slog.w(TAG, "Cannot hide package: android"); 14970 return false; 14971 } 14972 // Cannot hide static shared libs as they are considered 14973 // a part of the using app (emulating static linking). Also 14974 // static libs are installed always on internal storage. 14975 PackageParser.Package pkg = mPackages.get(packageName); 14976 if (pkg != null && pkg.staticSharedLibName != null) { 14977 Slog.w(TAG, "Cannot hide package: " + packageName 14978 + " providing static shared library: " 14979 + pkg.staticSharedLibName); 14980 return false; 14981 } 14982 // Only allow protected packages to hide themselves. 14983 if (hidden && !UserHandle.isSameApp(callingUid, pkgSetting.appId) 14984 && mProtectedPackages.isPackageStateProtected(userId, packageName)) { 14985 Slog.w(TAG, "Not hiding protected package: " + packageName); 14986 return false; 14987 } 14988 14989 if (pkgSetting.getHidden(userId) != hidden) { 14990 pkgSetting.setHidden(hidden, userId); 14991 mSettings.writePackageRestrictionsLPr(userId); 14992 if (hidden) { 14993 sendRemoved = true; 14994 } else { 14995 sendAdded = true; 14996 } 14997 } 14998 } 14999 if (sendAdded) { 15000 sendPackageAddedForUser(packageName, pkgSetting, userId); 15001 return true; 15002 } 15003 if (sendRemoved) { 15004 killApplication(packageName, UserHandle.getUid(userId, pkgSetting.appId), 15005 "hiding pkg"); 15006 sendApplicationHiddenForUser(packageName, pkgSetting, userId); 15007 return true; 15008 } 15009 } finally { 15010 Binder.restoreCallingIdentity(callingId); 15011 } 15012 return false; 15013 } 15014 15015 private void sendApplicationHiddenForUser(String packageName, PackageSetting pkgSetting, 15016 int userId) { 15017 final PackageRemovedInfo info = new PackageRemovedInfo(this); 15018 info.removedPackage = packageName; 15019 info.installerPackageName = pkgSetting.installerPackageName; 15020 info.removedUsers = new int[] {userId}; 15021 info.broadcastUsers = new int[] {userId}; 15022 info.uid = UserHandle.getUid(userId, pkgSetting.appId); 15023 info.sendPackageRemovedBroadcasts(true /*killApp*/); 15024 } 15025 15026 private void sendPackagesSuspendedForUser(String[] pkgList, int userId, boolean suspended) { 15027 if (pkgList.length > 0) { 15028 Bundle extras = new Bundle(1); 15029 extras.putStringArray(Intent.EXTRA_CHANGED_PACKAGE_LIST, pkgList); 15030 15031 sendPackageBroadcast( 15032 suspended ? Intent.ACTION_PACKAGES_SUSPENDED 15033 : Intent.ACTION_PACKAGES_UNSUSPENDED, 15034 null, extras, Intent.FLAG_RECEIVER_REGISTERED_ONLY, null, null, 15035 new int[] {userId}); 15036 } 15037 } 15038 15039 /** 15040 * Returns true if application is not found or there was an error. Otherwise it returns 15041 * the hidden state of the package for the given user. 15042 */ 15043 @Override 15044 public boolean getApplicationHiddenSettingAsUser(String packageName, int userId) { 15045 mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MANAGE_USERS, null); 15046 final int callingUid = Binder.getCallingUid(); 15047 enforceCrossUserPermission(callingUid, userId, 15048 true /* requireFullPermission */, false /* checkShell */, 15049 "getApplicationHidden for user " + userId); 15050 PackageSetting ps; 15051 long callingId = Binder.clearCallingIdentity(); 15052 try { 15053 // writer 15054 synchronized (mPackages) { 15055 ps = mSettings.mPackages.get(packageName); 15056 if (ps == null) { 15057 return true; 15058 } 15059 if (filterAppAccessLPr(ps, callingUid, userId)) { 15060 return true; 15061 } 15062 return ps.getHidden(userId); 15063 } 15064 } finally { 15065 Binder.restoreCallingIdentity(callingId); 15066 } 15067 } 15068 15069 /** 15070 * @hide 15071 */ 15072 @Override 15073 public int installExistingPackageAsUser(String packageName, int userId, int installFlags, 15074 int installReason) { 15075 mContext.enforceCallingOrSelfPermission(android.Manifest.permission.INSTALL_PACKAGES, 15076 null); 15077 PackageSetting pkgSetting; 15078 final int callingUid = Binder.getCallingUid(); 15079 enforceCrossUserPermission(callingUid, userId, 15080 true /* requireFullPermission */, true /* checkShell */, 15081 "installExistingPackage for user " + userId); 15082 if (isUserRestricted(userId, UserManager.DISALLOW_INSTALL_APPS)) { 15083 return PackageManager.INSTALL_FAILED_USER_RESTRICTED; 15084 } 15085 15086 long callingId = Binder.clearCallingIdentity(); 15087 try { 15088 boolean installed = false; 15089 final boolean instantApp = 15090 (installFlags & PackageManager.INSTALL_INSTANT_APP) != 0; 15091 final boolean fullApp = 15092 (installFlags & PackageManager.INSTALL_FULL_APP) != 0; 15093 15094 // writer 15095 synchronized (mPackages) { 15096 pkgSetting = mSettings.mPackages.get(packageName); 15097 if (pkgSetting == null) { 15098 return PackageManager.INSTALL_FAILED_INVALID_URI; 15099 } 15100 if (!canViewInstantApps(callingUid, UserHandle.getUserId(callingUid))) { 15101 // only allow the existing package to be used if it's installed as a full 15102 // application for at least one user 15103 boolean installAllowed = false; 15104 for (int checkUserId : sUserManager.getUserIds()) { 15105 installAllowed = !pkgSetting.getInstantApp(checkUserId); 15106 if (installAllowed) { 15107 break; 15108 } 15109 } 15110 if (!installAllowed) { 15111 return PackageManager.INSTALL_FAILED_INVALID_URI; 15112 } 15113 } 15114 if (!pkgSetting.getInstalled(userId)) { 15115 pkgSetting.setInstalled(true, userId); 15116 pkgSetting.setHidden(false, userId); 15117 pkgSetting.setInstallReason(installReason, userId); 15118 mSettings.writePackageRestrictionsLPr(userId); 15119 mSettings.writeKernelMappingLPr(pkgSetting); 15120 installed = true; 15121 } else if (fullApp && pkgSetting.getInstantApp(userId)) { 15122 // upgrade app from instant to full; we don't allow app downgrade 15123 installed = true; 15124 } 15125 setInstantAppForUser(pkgSetting, userId, instantApp, fullApp); 15126 } 15127 15128 if (installed) { 15129 if (pkgSetting.pkg != null) { 15130 synchronized (mInstallLock) { 15131 // We don't need to freeze for a brand new install 15132 prepareAppDataAfterInstallLIF(pkgSetting.pkg); 15133 } 15134 } 15135 sendPackageAddedForUser(packageName, pkgSetting, userId); 15136 synchronized (mPackages) { 15137 updateSequenceNumberLP(pkgSetting, new int[]{ userId }); 15138 } 15139 } 15140 } finally { 15141 Binder.restoreCallingIdentity(callingId); 15142 } 15143 15144 return PackageManager.INSTALL_SUCCEEDED; 15145 } 15146 15147 void setInstantAppForUser(PackageSetting pkgSetting, int userId, 15148 boolean instantApp, boolean fullApp) { 15149 // no state specified; do nothing 15150 if (!instantApp && !fullApp) { 15151 return; 15152 } 15153 if (userId != UserHandle.USER_ALL) { 15154 if (instantApp && !pkgSetting.getInstantApp(userId)) { 15155 pkgSetting.setInstantApp(true /*instantApp*/, userId); 15156 } else if (fullApp && pkgSetting.getInstantApp(userId)) { 15157 pkgSetting.setInstantApp(false /*instantApp*/, userId); 15158 } 15159 } else { 15160 for (int currentUserId : sUserManager.getUserIds()) { 15161 if (instantApp && !pkgSetting.getInstantApp(currentUserId)) { 15162 pkgSetting.setInstantApp(true /*instantApp*/, currentUserId); 15163 } else if (fullApp && pkgSetting.getInstantApp(currentUserId)) { 15164 pkgSetting.setInstantApp(false /*instantApp*/, currentUserId); 15165 } 15166 } 15167 } 15168 } 15169 15170 boolean isUserRestricted(int userId, String restrictionKey) { 15171 Bundle restrictions = sUserManager.getUserRestrictions(userId); 15172 if (restrictions.getBoolean(restrictionKey, false)) { 15173 Log.w(TAG, "User is restricted: " + restrictionKey); 15174 return true; 15175 } 15176 return false; 15177 } 15178 15179 @Override 15180 public String[] setPackagesSuspendedAsUser(String[] packageNames, boolean suspended, 15181 int userId) { 15182 mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MANAGE_USERS, null); 15183 final int callingUid = Binder.getCallingUid(); 15184 enforceCrossUserPermission(callingUid, userId, 15185 true /* requireFullPermission */, true /* checkShell */, 15186 "setPackagesSuspended for user " + userId); 15187 15188 if (ArrayUtils.isEmpty(packageNames)) { 15189 return packageNames; 15190 } 15191 15192 // List of package names for whom the suspended state has changed. 15193 List<String> changedPackages = new ArrayList<>(packageNames.length); 15194 // List of package names for whom the suspended state is not set as requested in this 15195 // method. 15196 List<String> unactionedPackages = new ArrayList<>(packageNames.length); 15197 long callingId = Binder.clearCallingIdentity(); 15198 try { 15199 for (int i = 0; i < packageNames.length; i++) { 15200 String packageName = packageNames[i]; 15201 boolean changed = false; 15202 final int appId; 15203 synchronized (mPackages) { 15204 final PackageSetting pkgSetting = mSettings.mPackages.get(packageName); 15205 if (pkgSetting == null 15206 || filterAppAccessLPr(pkgSetting, callingUid, userId)) { 15207 Slog.w(TAG, "Could not find package setting for package \"" + packageName 15208 + "\". Skipping suspending/un-suspending."); 15209 unactionedPackages.add(packageName); 15210 continue; 15211 } 15212 appId = pkgSetting.appId; 15213 if (pkgSetting.getSuspended(userId) != suspended) { 15214 if (!canSuspendPackageForUserLocked(packageName, userId)) { 15215 unactionedPackages.add(packageName); 15216 continue; 15217 } 15218 pkgSetting.setSuspended(suspended, userId); 15219 mSettings.writePackageRestrictionsLPr(userId); 15220 changed = true; 15221 changedPackages.add(packageName); 15222 } 15223 } 15224 15225 if (changed && suspended) { 15226 killApplication(packageName, UserHandle.getUid(userId, appId), 15227 "suspending package"); 15228 } 15229 } 15230 } finally { 15231 Binder.restoreCallingIdentity(callingId); 15232 } 15233 15234 if (!changedPackages.isEmpty()) { 15235 sendPackagesSuspendedForUser(changedPackages.toArray( 15236 new String[changedPackages.size()]), userId, suspended); 15237 } 15238 15239 return unactionedPackages.toArray(new String[unactionedPackages.size()]); 15240 } 15241 15242 @Override 15243 public boolean isPackageSuspendedForUser(String packageName, int userId) { 15244 final int callingUid = Binder.getCallingUid(); 15245 enforceCrossUserPermission(callingUid, userId, 15246 true /* requireFullPermission */, false /* checkShell */, 15247 "isPackageSuspendedForUser for user " + userId); 15248 synchronized (mPackages) { 15249 final PackageSetting ps = mSettings.mPackages.get(packageName); 15250 if (ps == null || filterAppAccessLPr(ps, callingUid, userId)) { 15251 throw new IllegalArgumentException("Unknown target package: " + packageName); 15252 } 15253 return ps.getSuspended(userId); 15254 } 15255 } 15256 15257 private boolean canSuspendPackageForUserLocked(String packageName, int userId) { 15258 if (isPackageDeviceAdmin(packageName, userId)) { 15259 Slog.w(TAG, "Cannot suspend/un-suspend package \"" + packageName 15260 + "\": has an active device admin"); 15261 return false; 15262 } 15263 15264 String activeLauncherPackageName = getActiveLauncherPackageName(userId); 15265 if (packageName.equals(activeLauncherPackageName)) { 15266 Slog.w(TAG, "Cannot suspend/un-suspend package \"" + packageName 15267 + "\": contains the active launcher"); 15268 return false; 15269 } 15270 15271 if (packageName.equals(mRequiredInstallerPackage)) { 15272 Slog.w(TAG, "Cannot suspend/un-suspend package \"" + packageName 15273 + "\": required for package installation"); 15274 return false; 15275 } 15276 15277 if (packageName.equals(mRequiredUninstallerPackage)) { 15278 Slog.w(TAG, "Cannot suspend/un-suspend package \"" + packageName 15279 + "\": required for package uninstallation"); 15280 return false; 15281 } 15282 15283 if (packageName.equals(mRequiredVerifierPackage)) { 15284 Slog.w(TAG, "Cannot suspend/un-suspend package \"" + packageName 15285 + "\": required for package verification"); 15286 return false; 15287 } 15288 15289 if (packageName.equals(getDefaultDialerPackageName(userId))) { 15290 Slog.w(TAG, "Cannot suspend/un-suspend package \"" + packageName 15291 + "\": is the default dialer"); 15292 return false; 15293 } 15294 15295 if (mProtectedPackages.isPackageStateProtected(userId, packageName)) { 15296 Slog.w(TAG, "Cannot suspend/un-suspend package \"" + packageName 15297 + "\": protected package"); 15298 return false; 15299 } 15300 15301 // Cannot suspend static shared libs as they are considered 15302 // a part of the using app (emulating static linking). Also 15303 // static libs are installed always on internal storage. 15304 PackageParser.Package pkg = mPackages.get(packageName); 15305 if (pkg != null && pkg.applicationInfo.isStaticSharedLibrary()) { 15306 Slog.w(TAG, "Cannot suspend package: " + packageName 15307 + " providing static shared library: " 15308 + pkg.staticSharedLibName); 15309 return false; 15310 } 15311 15312 return true; 15313 } 15314 15315 private String getActiveLauncherPackageName(int userId) { 15316 Intent intent = new Intent(Intent.ACTION_MAIN); 15317 intent.addCategory(Intent.CATEGORY_HOME); 15318 ResolveInfo resolveInfo = resolveIntent( 15319 intent, 15320 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 15321 PackageManager.MATCH_DEFAULT_ONLY, 15322 userId); 15323 15324 return resolveInfo == null ? null : resolveInfo.activityInfo.packageName; 15325 } 15326 15327 private String getDefaultDialerPackageName(int userId) { 15328 synchronized (mPackages) { 15329 return mSettings.getDefaultDialerPackageNameLPw(userId); 15330 } 15331 } 15332 15333 @Override 15334 public void verifyPendingInstall(int id, int verificationCode) throws RemoteException { 15335 mContext.enforceCallingOrSelfPermission( 15336 android.Manifest.permission.PACKAGE_VERIFICATION_AGENT, 15337 "Only package verification agents can verify applications"); 15338 15339 final Message msg = mHandler.obtainMessage(PACKAGE_VERIFIED); 15340 final PackageVerificationResponse response = new PackageVerificationResponse( 15341 verificationCode, Binder.getCallingUid()); 15342 msg.arg1 = id; 15343 msg.obj = response; 15344 mHandler.sendMessage(msg); 15345 } 15346 15347 @Override 15348 public void extendVerificationTimeout(int id, int verificationCodeAtTimeout, 15349 long millisecondsToDelay) { 15350 mContext.enforceCallingOrSelfPermission( 15351 android.Manifest.permission.PACKAGE_VERIFICATION_AGENT, 15352 "Only package verification agents can extend verification timeouts"); 15353 15354 final PackageVerificationState state = mPendingVerification.get(id); 15355 final PackageVerificationResponse response = new PackageVerificationResponse( 15356 verificationCodeAtTimeout, Binder.getCallingUid()); 15357 15358 if (millisecondsToDelay > PackageManager.MAXIMUM_VERIFICATION_TIMEOUT) { 15359 millisecondsToDelay = PackageManager.MAXIMUM_VERIFICATION_TIMEOUT; 15360 } 15361 if (millisecondsToDelay < 0) { 15362 millisecondsToDelay = 0; 15363 } 15364 if ((verificationCodeAtTimeout != PackageManager.VERIFICATION_ALLOW) 15365 && (verificationCodeAtTimeout != PackageManager.VERIFICATION_REJECT)) { 15366 verificationCodeAtTimeout = PackageManager.VERIFICATION_REJECT; 15367 } 15368 15369 if ((state != null) && !state.timeoutExtended()) { 15370 state.extendTimeout(); 15371 15372 final Message msg = mHandler.obtainMessage(PACKAGE_VERIFIED); 15373 msg.arg1 = id; 15374 msg.obj = response; 15375 mHandler.sendMessageDelayed(msg, millisecondsToDelay); 15376 } 15377 } 15378 15379 private void broadcastPackageVerified(int verificationId, Uri packageUri, 15380 int verificationCode, UserHandle user) { 15381 final Intent intent = new Intent(Intent.ACTION_PACKAGE_VERIFIED); 15382 intent.setDataAndType(packageUri, PACKAGE_MIME_TYPE); 15383 intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION); 15384 intent.putExtra(PackageManager.EXTRA_VERIFICATION_ID, verificationId); 15385 intent.putExtra(PackageManager.EXTRA_VERIFICATION_RESULT, verificationCode); 15386 15387 mContext.sendBroadcastAsUser(intent, user, 15388 android.Manifest.permission.PACKAGE_VERIFICATION_AGENT); 15389 } 15390 15391 private ComponentName matchComponentForVerifier(String packageName, 15392 List<ResolveInfo> receivers) { 15393 ActivityInfo targetReceiver = null; 15394 15395 final int NR = receivers.size(); 15396 for (int i = 0; i < NR; i++) { 15397 final ResolveInfo info = receivers.get(i); 15398 if (info.activityInfo == null) { 15399 continue; 15400 } 15401 15402 if (packageName.equals(info.activityInfo.packageName)) { 15403 targetReceiver = info.activityInfo; 15404 break; 15405 } 15406 } 15407 15408 if (targetReceiver == null) { 15409 return null; 15410 } 15411 15412 return new ComponentName(targetReceiver.packageName, targetReceiver.name); 15413 } 15414 15415 private List<ComponentName> matchVerifiers(PackageInfoLite pkgInfo, 15416 List<ResolveInfo> receivers, final PackageVerificationState verificationState) { 15417 if (pkgInfo.verifiers.length == 0) { 15418 return null; 15419 } 15420 15421 final int N = pkgInfo.verifiers.length; 15422 final List<ComponentName> sufficientVerifiers = new ArrayList<ComponentName>(N + 1); 15423 for (int i = 0; i < N; i++) { 15424 final VerifierInfo verifierInfo = pkgInfo.verifiers[i]; 15425 15426 final ComponentName comp = matchComponentForVerifier(verifierInfo.packageName, 15427 receivers); 15428 if (comp == null) { 15429 continue; 15430 } 15431 15432 final int verifierUid = getUidForVerifier(verifierInfo); 15433 if (verifierUid == -1) { 15434 continue; 15435 } 15436 15437 if (DEBUG_VERIFY) { 15438 Slog.d(TAG, "Added sufficient verifier " + verifierInfo.packageName 15439 + " with the correct signature"); 15440 } 15441 sufficientVerifiers.add(comp); 15442 verificationState.addSufficientVerifier(verifierUid); 15443 } 15444 15445 return sufficientVerifiers; 15446 } 15447 15448 private int getUidForVerifier(VerifierInfo verifierInfo) { 15449 synchronized (mPackages) { 15450 final PackageParser.Package pkg = mPackages.get(verifierInfo.packageName); 15451 if (pkg == null) { 15452 return -1; 15453 } else if (pkg.mSignatures.length != 1) { 15454 Slog.i(TAG, "Verifier package " + verifierInfo.packageName 15455 + " has more than one signature; ignoring"); 15456 return -1; 15457 } 15458 15459 /* 15460 * If the public key of the package's signature does not match 15461 * our expected public key, then this is a different package and 15462 * we should skip. 15463 */ 15464 15465 final byte[] expectedPublicKey; 15466 try { 15467 final Signature verifierSig = pkg.mSignatures[0]; 15468 final PublicKey publicKey = verifierSig.getPublicKey(); 15469 expectedPublicKey = publicKey.getEncoded(); 15470 } catch (CertificateException e) { 15471 return -1; 15472 } 15473 15474 final byte[] actualPublicKey = verifierInfo.publicKey.getEncoded(); 15475 15476 if (!Arrays.equals(actualPublicKey, expectedPublicKey)) { 15477 Slog.i(TAG, "Verifier package " + verifierInfo.packageName 15478 + " does not have the expected public key; ignoring"); 15479 return -1; 15480 } 15481 15482 return pkg.applicationInfo.uid; 15483 } 15484 } 15485 15486 @Override 15487 public void finishPackageInstall(int token, boolean didLaunch) { 15488 enforceSystemOrRoot("Only the system is allowed to finish installs"); 15489 15490 if (DEBUG_INSTALL) { 15491 Slog.v(TAG, "BM finishing package install for " + token); 15492 } 15493 Trace.asyncTraceEnd(TRACE_TAG_PACKAGE_MANAGER, "restore", token); 15494 15495 final Message msg = mHandler.obtainMessage(POST_INSTALL, token, didLaunch ? 1 : 0); 15496 mHandler.sendMessage(msg); 15497 } 15498 15499 /** 15500 * Get the verification agent timeout. Used for both the APK verifier and the 15501 * intent filter verifier. 15502 * 15503 * @return verification timeout in milliseconds 15504 */ 15505 private long getVerificationTimeout() { 15506 return android.provider.Settings.Global.getLong(mContext.getContentResolver(), 15507 android.provider.Settings.Global.PACKAGE_VERIFIER_TIMEOUT, 15508 DEFAULT_VERIFICATION_TIMEOUT); 15509 } 15510 15511 /** 15512 * Get the default verification agent response code. 15513 * 15514 * @return default verification response code 15515 */ 15516 private int getDefaultVerificationResponse(UserHandle user) { 15517 if (sUserManager.hasUserRestriction(UserManager.ENSURE_VERIFY_APPS, user.getIdentifier())) { 15518 return PackageManager.VERIFICATION_REJECT; 15519 } 15520 return android.provider.Settings.Global.getInt(mContext.getContentResolver(), 15521 android.provider.Settings.Global.PACKAGE_VERIFIER_DEFAULT_RESPONSE, 15522 DEFAULT_VERIFICATION_RESPONSE); 15523 } 15524 15525 /** 15526 * Check whether or not package verification has been enabled. 15527 * 15528 * @return true if verification should be performed 15529 */ 15530 private boolean isVerificationEnabled(int userId, int installFlags, int installerUid) { 15531 if (!DEFAULT_VERIFY_ENABLE) { 15532 return false; 15533 } 15534 15535 boolean ensureVerifyAppsEnabled = isUserRestricted(userId, UserManager.ENSURE_VERIFY_APPS); 15536 15537 // Check if installing from ADB 15538 if ((installFlags & PackageManager.INSTALL_FROM_ADB) != 0) { 15539 // Do not run verification in a test harness environment 15540 if (ActivityManager.isRunningInTestHarness()) { 15541 return false; 15542 } 15543 if (ensureVerifyAppsEnabled) { 15544 return true; 15545 } 15546 // Check if the developer does not want package verification for ADB installs 15547 if (android.provider.Settings.Global.getInt(mContext.getContentResolver(), 15548 android.provider.Settings.Global.PACKAGE_VERIFIER_INCLUDE_ADB, 1) == 0) { 15549 return false; 15550 } 15551 } else { 15552 // only when not installed from ADB, skip verification for instant apps when 15553 // the installer and verifier are the same. 15554 if ((installFlags & PackageManager.INSTALL_INSTANT_APP) != 0) { 15555 if (mInstantAppInstallerActivity != null 15556 && mInstantAppInstallerActivity.packageName.equals( 15557 mRequiredVerifierPackage)) { 15558 try { 15559 mContext.getSystemService(AppOpsManager.class) 15560 .checkPackage(installerUid, mRequiredVerifierPackage); 15561 if (DEBUG_VERIFY) { 15562 Slog.i(TAG, "disable verification for instant app"); 15563 } 15564 return false; 15565 } catch (SecurityException ignore) { } 15566 } 15567 } 15568 } 15569 15570 if (ensureVerifyAppsEnabled) { 15571 return true; 15572 } 15573 15574 return android.provider.Settings.Global.getInt(mContext.getContentResolver(), 15575 android.provider.Settings.Global.PACKAGE_VERIFIER_ENABLE, 1) == 1; 15576 } 15577 15578 @Override 15579 public void verifyIntentFilter(int id, int verificationCode, List<String> failedDomains) 15580 throws RemoteException { 15581 mContext.enforceCallingOrSelfPermission( 15582 Manifest.permission.INTENT_FILTER_VERIFICATION_AGENT, 15583 "Only intentfilter verification agents can verify applications"); 15584 15585 final Message msg = mHandler.obtainMessage(INTENT_FILTER_VERIFIED); 15586 final IntentFilterVerificationResponse response = new IntentFilterVerificationResponse( 15587 Binder.getCallingUid(), verificationCode, failedDomains); 15588 msg.arg1 = id; 15589 msg.obj = response; 15590 mHandler.sendMessage(msg); 15591 } 15592 15593 @Override 15594 public int getIntentVerificationStatus(String packageName, int userId) { 15595 final int callingUid = Binder.getCallingUid(); 15596 if (UserHandle.getUserId(callingUid) != userId) { 15597 mContext.enforceCallingOrSelfPermission( 15598 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, 15599 "getIntentVerificationStatus" + userId); 15600 } 15601 if (getInstantAppPackageName(callingUid) != null) { 15602 return INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED; 15603 } 15604 synchronized (mPackages) { 15605 final PackageSetting ps = mSettings.mPackages.get(packageName); 15606 if (ps == null 15607 || filterAppAccessLPr(ps, callingUid, UserHandle.getUserId(callingUid))) { 15608 return INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED; 15609 } 15610 return mSettings.getIntentFilterVerificationStatusLPr(packageName, userId); 15611 } 15612 } 15613 15614 @Override 15615 public boolean updateIntentVerificationStatus(String packageName, int status, int userId) { 15616 mContext.enforceCallingOrSelfPermission( 15617 android.Manifest.permission.SET_PREFERRED_APPLICATIONS, null); 15618 15619 boolean result = false; 15620 synchronized (mPackages) { 15621 final PackageSetting ps = mSettings.mPackages.get(packageName); 15622 if (filterAppAccessLPr(ps, Binder.getCallingUid(), UserHandle.getCallingUserId())) { 15623 return false; 15624 } 15625 result = mSettings.updateIntentFilterVerificationStatusLPw(packageName, status, userId); 15626 } 15627 if (result) { 15628 scheduleWritePackageRestrictionsLocked(userId); 15629 } 15630 return result; 15631 } 15632 15633 @Override 15634 public @NonNull ParceledListSlice<IntentFilterVerificationInfo> getIntentFilterVerifications( 15635 String packageName) { 15636 final int callingUid = Binder.getCallingUid(); 15637 if (getInstantAppPackageName(callingUid) != null) { 15638 return ParceledListSlice.emptyList(); 15639 } 15640 synchronized (mPackages) { 15641 final PackageSetting ps = mSettings.mPackages.get(packageName); 15642 if (filterAppAccessLPr(ps, callingUid, UserHandle.getUserId(callingUid))) { 15643 return ParceledListSlice.emptyList(); 15644 } 15645 return new ParceledListSlice<>(mSettings.getIntentFilterVerificationsLPr(packageName)); 15646 } 15647 } 15648 15649 @Override 15650 public @NonNull ParceledListSlice<IntentFilter> getAllIntentFilters(String packageName) { 15651 if (TextUtils.isEmpty(packageName)) { 15652 return ParceledListSlice.emptyList(); 15653 } 15654 final int callingUid = Binder.getCallingUid(); 15655 final int callingUserId = UserHandle.getUserId(callingUid); 15656 synchronized (mPackages) { 15657 PackageParser.Package pkg = mPackages.get(packageName); 15658 if (pkg == null || pkg.activities == null) { 15659 return ParceledListSlice.emptyList(); 15660 } 15661 if (pkg.mExtras == null) { 15662 return ParceledListSlice.emptyList(); 15663 } 15664 final PackageSetting ps = (PackageSetting) pkg.mExtras; 15665 if (filterAppAccessLPr(ps, callingUid, callingUserId)) { 15666 return ParceledListSlice.emptyList(); 15667 } 15668 final int count = pkg.activities.size(); 15669 ArrayList<IntentFilter> result = new ArrayList<>(); 15670 for (int n=0; n<count; n++) { 15671 PackageParser.Activity activity = pkg.activities.get(n); 15672 if (activity.intents != null && activity.intents.size() > 0) { 15673 result.addAll(activity.intents); 15674 } 15675 } 15676 return new ParceledListSlice<>(result); 15677 } 15678 } 15679 15680 @Override 15681 public boolean setDefaultBrowserPackageName(String packageName, int userId) { 15682 mContext.enforceCallingOrSelfPermission( 15683 android.Manifest.permission.SET_PREFERRED_APPLICATIONS, null); 15684 if (UserHandle.getCallingUserId() != userId) { 15685 mContext.enforceCallingOrSelfPermission( 15686 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, null); 15687 } 15688 15689 synchronized (mPackages) { 15690 boolean result = mSettings.setDefaultBrowserPackageNameLPw(packageName, userId); 15691 if (packageName != null) { 15692 mDefaultPermissionPolicy.grantDefaultPermissionsToDefaultBrowserLPr( 15693 packageName, userId); 15694 } 15695 return result; 15696 } 15697 } 15698 15699 @Override 15700 public String getDefaultBrowserPackageName(int userId) { 15701 if (UserHandle.getCallingUserId() != userId) { 15702 mContext.enforceCallingOrSelfPermission( 15703 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, null); 15704 } 15705 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 15706 return null; 15707 } 15708 synchronized (mPackages) { 15709 return mSettings.getDefaultBrowserPackageNameLPw(userId); 15710 } 15711 } 15712 15713 /** 15714 * Get the "allow unknown sources" setting. 15715 * 15716 * @return the current "allow unknown sources" setting 15717 */ 15718 private int getUnknownSourcesSettings() { 15719 return android.provider.Settings.Secure.getInt(mContext.getContentResolver(), 15720 android.provider.Settings.Secure.INSTALL_NON_MARKET_APPS, 15721 -1); 15722 } 15723 15724 @Override 15725 public void setInstallerPackageName(String targetPackage, String installerPackageName) { 15726 final int callingUid = Binder.getCallingUid(); 15727 if (getInstantAppPackageName(callingUid) != null) { 15728 return; 15729 } 15730 // writer 15731 synchronized (mPackages) { 15732 PackageSetting targetPackageSetting = mSettings.mPackages.get(targetPackage); 15733 if (targetPackageSetting == null 15734 || filterAppAccessLPr( 15735 targetPackageSetting, callingUid, UserHandle.getUserId(callingUid))) { 15736 throw new IllegalArgumentException("Unknown target package: " + targetPackage); 15737 } 15738 15739 PackageSetting installerPackageSetting; 15740 if (installerPackageName != null) { 15741 installerPackageSetting = mSettings.mPackages.get(installerPackageName); 15742 if (installerPackageSetting == null) { 15743 throw new IllegalArgumentException("Unknown installer package: " 15744 + installerPackageName); 15745 } 15746 } else { 15747 installerPackageSetting = null; 15748 } 15749 15750 Signature[] callerSignature; 15751 Object obj = mSettings.getUserIdLPr(callingUid); 15752 if (obj != null) { 15753 if (obj instanceof SharedUserSetting) { 15754 callerSignature = ((SharedUserSetting)obj).signatures.mSignatures; 15755 } else if (obj instanceof PackageSetting) { 15756 callerSignature = ((PackageSetting)obj).signatures.mSignatures; 15757 } else { 15758 throw new SecurityException("Bad object " + obj + " for uid " + callingUid); 15759 } 15760 } else { 15761 throw new SecurityException("Unknown calling UID: " + callingUid); 15762 } 15763 15764 // Verify: can't set installerPackageName to a package that is 15765 // not signed with the same cert as the caller. 15766 if (installerPackageSetting != null) { 15767 if (compareSignatures(callerSignature, 15768 installerPackageSetting.signatures.mSignatures) 15769 != PackageManager.SIGNATURE_MATCH) { 15770 throw new SecurityException( 15771 "Caller does not have same cert as new installer package " 15772 + installerPackageName); 15773 } 15774 } 15775 15776 // Verify: if target already has an installer package, it must 15777 // be signed with the same cert as the caller. 15778 if (targetPackageSetting.installerPackageName != null) { 15779 PackageSetting setting = mSettings.mPackages.get( 15780 targetPackageSetting.installerPackageName); 15781 // If the currently set package isn't valid, then it's always 15782 // okay to change it. 15783 if (setting != null) { 15784 if (compareSignatures(callerSignature, 15785 setting.signatures.mSignatures) 15786 != PackageManager.SIGNATURE_MATCH) { 15787 throw new SecurityException( 15788 "Caller does not have same cert as old installer package " 15789 + targetPackageSetting.installerPackageName); 15790 } 15791 } 15792 } 15793 15794 // Okay! 15795 targetPackageSetting.installerPackageName = installerPackageName; 15796 if (installerPackageName != null) { 15797 mSettings.mInstallerPackages.add(installerPackageName); 15798 } 15799 scheduleWriteSettingsLocked(); 15800 } 15801 } 15802 15803 @Override 15804 public void setApplicationCategoryHint(String packageName, int categoryHint, 15805 String callerPackageName) { 15806 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 15807 throw new SecurityException("Instant applications don't have access to this method"); 15808 } 15809 mContext.getSystemService(AppOpsManager.class).checkPackage(Binder.getCallingUid(), 15810 callerPackageName); 15811 synchronized (mPackages) { 15812 PackageSetting ps = mSettings.mPackages.get(packageName); 15813 if (ps == null) { 15814 throw new IllegalArgumentException("Unknown target package " + packageName); 15815 } 15816 if (filterAppAccessLPr(ps, Binder.getCallingUid(), UserHandle.getCallingUserId())) { 15817 throw new IllegalArgumentException("Unknown target package " + packageName); 15818 } 15819 if (!Objects.equals(callerPackageName, ps.installerPackageName)) { 15820 throw new IllegalArgumentException("Calling package " + callerPackageName 15821 + " is not installer for " + packageName); 15822 } 15823 15824 if (ps.categoryHint != categoryHint) { 15825 ps.categoryHint = categoryHint; 15826 scheduleWriteSettingsLocked(); 15827 } 15828 } 15829 } 15830 15831 private void processPendingInstall(final InstallArgs args, final int currentStatus) { 15832 // Queue up an async operation since the package installation may take a little while. 15833 mHandler.post(new Runnable() { 15834 public void run() { 15835 mHandler.removeCallbacks(this); 15836 // Result object to be returned 15837 PackageInstalledInfo res = new PackageInstalledInfo(); 15838 res.setReturnCode(currentStatus); 15839 res.uid = -1; 15840 res.pkg = null; 15841 res.removedInfo = null; 15842 if (res.returnCode == PackageManager.INSTALL_SUCCEEDED) { 15843 args.doPreInstall(res.returnCode); 15844 synchronized (mInstallLock) { 15845 installPackageTracedLI(args, res); 15846 } 15847 args.doPostInstall(res.returnCode, res.uid); 15848 } 15849 15850 // A restore should be performed at this point if (a) the install 15851 // succeeded, (b) the operation is not an update, and (c) the new 15852 // package has not opted out of backup participation. 15853 final boolean update = res.removedInfo != null 15854 && res.removedInfo.removedPackage != null; 15855 final int flags = (res.pkg == null) ? 0 : res.pkg.applicationInfo.flags; 15856 boolean doRestore = !update 15857 && ((flags & ApplicationInfo.FLAG_ALLOW_BACKUP) != 0); 15858 15859 // Set up the post-install work request bookkeeping. This will be used 15860 // and cleaned up by the post-install event handling regardless of whether 15861 // there's a restore pass performed. Token values are >= 1. 15862 int token; 15863 if (mNextInstallToken < 0) mNextInstallToken = 1; 15864 token = mNextInstallToken++; 15865 15866 PostInstallData data = new PostInstallData(args, res); 15867 mRunningInstalls.put(token, data); 15868 if (DEBUG_INSTALL) Log.v(TAG, "+ starting restore round-trip " + token); 15869 15870 if (res.returnCode == PackageManager.INSTALL_SUCCEEDED && doRestore) { 15871 // Pass responsibility to the Backup Manager. It will perform a 15872 // restore if appropriate, then pass responsibility back to the 15873 // Package Manager to run the post-install observer callbacks 15874 // and broadcasts. 15875 IBackupManager bm = IBackupManager.Stub.asInterface( 15876 ServiceManager.getService(Context.BACKUP_SERVICE)); 15877 if (bm != null) { 15878 if (DEBUG_INSTALL) Log.v(TAG, "token " + token 15879 + " to BM for possible restore"); 15880 Trace.asyncTraceBegin(TRACE_TAG_PACKAGE_MANAGER, "restore", token); 15881 try { 15882 // TODO: http://b/22388012 15883 if (bm.isBackupServiceActive(UserHandle.USER_SYSTEM)) { 15884 bm.restoreAtInstall(res.pkg.applicationInfo.packageName, token); 15885 } else { 15886 doRestore = false; 15887 } 15888 } catch (RemoteException e) { 15889 // can't happen; the backup manager is local 15890 } catch (Exception e) { 15891 Slog.e(TAG, "Exception trying to enqueue restore", e); 15892 doRestore = false; 15893 } 15894 } else { 15895 Slog.e(TAG, "Backup Manager not found!"); 15896 doRestore = false; 15897 } 15898 } 15899 15900 if (!doRestore) { 15901 // No restore possible, or the Backup Manager was mysteriously not 15902 // available -- just fire the post-install work request directly. 15903 if (DEBUG_INSTALL) Log.v(TAG, "No restore - queue post-install for " + token); 15904 15905 Trace.asyncTraceBegin(TRACE_TAG_PACKAGE_MANAGER, "postInstall", token); 15906 15907 Message msg = mHandler.obtainMessage(POST_INSTALL, token, 0); 15908 mHandler.sendMessage(msg); 15909 } 15910 } 15911 }); 15912 } 15913 15914 /** 15915 * Callback from PackageSettings whenever an app is first transitioned out of the 15916 * 'stopped' state. Normally we just issue the broadcast, but we can't do that if 15917 * the app was "launched" for a restoreAtInstall operation. Therefore we check 15918 * here whether the app is the target of an ongoing install, and only send the 15919 * broadcast immediately if it is not in that state. If it *is* undergoing a restore, 15920 * the first-launch broadcast will be sent implicitly on that basis in POST_INSTALL 15921 * handling. 15922 */ 15923 void notifyFirstLaunch(final String pkgName, final String installerPackage, final int userId) { 15924 // Serialize this with the rest of the install-process message chain. In the 15925 // restore-at-install case, this Runnable will necessarily run before the 15926 // POST_INSTALL message is processed, so the contents of mRunningInstalls 15927 // are coherent. In the non-restore case, the app has already completed install 15928 // and been launched through some other means, so it is not in a problematic 15929 // state for observers to see the FIRST_LAUNCH signal. 15930 mHandler.post(new Runnable() { 15931 @Override 15932 public void run() { 15933 for (int i = 0; i < mRunningInstalls.size(); i++) { 15934 final PostInstallData data = mRunningInstalls.valueAt(i); 15935 if (data.res.returnCode != PackageManager.INSTALL_SUCCEEDED) { 15936 continue; 15937 } 15938 if (pkgName.equals(data.res.pkg.applicationInfo.packageName)) { 15939 // right package; but is it for the right user? 15940 for (int uIndex = 0; uIndex < data.res.newUsers.length; uIndex++) { 15941 if (userId == data.res.newUsers[uIndex]) { 15942 if (DEBUG_BACKUP) { 15943 Slog.i(TAG, "Package " + pkgName 15944 + " being restored so deferring FIRST_LAUNCH"); 15945 } 15946 return; 15947 } 15948 } 15949 } 15950 } 15951 // didn't find it, so not being restored 15952 if (DEBUG_BACKUP) { 15953 Slog.i(TAG, "Package " + pkgName + " sending normal FIRST_LAUNCH"); 15954 } 15955 sendFirstLaunchBroadcast(pkgName, installerPackage, new int[] {userId}); 15956 } 15957 }); 15958 } 15959 15960 private void sendFirstLaunchBroadcast(String pkgName, String installerPkg, int[] userIds) { 15961 sendPackageBroadcast(Intent.ACTION_PACKAGE_FIRST_LAUNCH, pkgName, null, 0, 15962 installerPkg, null, userIds); 15963 } 15964 15965 private abstract class HandlerParams { 15966 private static final int MAX_RETRIES = 4; 15967 15968 /** 15969 * Number of times startCopy() has been attempted and had a non-fatal 15970 * error. 15971 */ 15972 private int mRetries = 0; 15973 15974 /** User handle for the user requesting the information or installation. */ 15975 private final UserHandle mUser; 15976 String traceMethod; 15977 int traceCookie; 15978 15979 HandlerParams(UserHandle user) { 15980 mUser = user; 15981 } 15982 15983 UserHandle getUser() { 15984 return mUser; 15985 } 15986 15987 HandlerParams setTraceMethod(String traceMethod) { 15988 this.traceMethod = traceMethod; 15989 return this; 15990 } 15991 15992 HandlerParams setTraceCookie(int traceCookie) { 15993 this.traceCookie = traceCookie; 15994 return this; 15995 } 15996 15997 final boolean startCopy() { 15998 boolean res; 15999 try { 16000 if (DEBUG_INSTALL) Slog.i(TAG, "startCopy " + mUser + ": " + this); 16001 16002 if (++mRetries > MAX_RETRIES) { 16003 Slog.w(TAG, "Failed to invoke remote methods on default container service. Giving up"); 16004 mHandler.sendEmptyMessage(MCS_GIVE_UP); 16005 handleServiceError(); 16006 return false; 16007 } else { 16008 handleStartCopy(); 16009 res = true; 16010 } 16011 } catch (RemoteException e) { 16012 if (DEBUG_INSTALL) Slog.i(TAG, "Posting install MCS_RECONNECT"); 16013 mHandler.sendEmptyMessage(MCS_RECONNECT); 16014 res = false; 16015 } 16016 handleReturnCode(); 16017 return res; 16018 } 16019 16020 final void serviceError() { 16021 if (DEBUG_INSTALL) Slog.i(TAG, "serviceError"); 16022 handleServiceError(); 16023 handleReturnCode(); 16024 } 16025 16026 abstract void handleStartCopy() throws RemoteException; 16027 abstract void handleServiceError(); 16028 abstract void handleReturnCode(); 16029 } 16030 16031 private static void clearDirectory(IMediaContainerService mcs, File[] paths) { 16032 for (File path : paths) { 16033 try { 16034 mcs.clearDirectory(path.getAbsolutePath()); 16035 } catch (RemoteException e) { 16036 } 16037 } 16038 } 16039 16040 static class OriginInfo { 16041 /** 16042 * Location where install is coming from, before it has been 16043 * copied/renamed into place. This could be a single monolithic APK 16044 * file, or a cluster directory. This location may be untrusted. 16045 */ 16046 final File file; 16047 final String cid; 16048 16049 /** 16050 * Flag indicating that {@link #file} or {@link #cid} has already been 16051 * staged, meaning downstream users don't need to defensively copy the 16052 * contents. 16053 */ 16054 final boolean staged; 16055 16056 /** 16057 * Flag indicating that {@link #file} or {@link #cid} is an already 16058 * installed app that is being moved. 16059 */ 16060 final boolean existing; 16061 16062 final String resolvedPath; 16063 final File resolvedFile; 16064 16065 static OriginInfo fromNothing() { 16066 return new OriginInfo(null, null, false, false); 16067 } 16068 16069 static OriginInfo fromUntrustedFile(File file) { 16070 return new OriginInfo(file, null, false, false); 16071 } 16072 16073 static OriginInfo fromExistingFile(File file) { 16074 return new OriginInfo(file, null, false, true); 16075 } 16076 16077 static OriginInfo fromStagedFile(File file) { 16078 return new OriginInfo(file, null, true, false); 16079 } 16080 16081 static OriginInfo fromStagedContainer(String cid) { 16082 return new OriginInfo(null, cid, true, false); 16083 } 16084 16085 private OriginInfo(File file, String cid, boolean staged, boolean existing) { 16086 this.file = file; 16087 this.cid = cid; 16088 this.staged = staged; 16089 this.existing = existing; 16090 16091 if (cid != null) { 16092 resolvedPath = PackageHelper.getSdDir(cid); 16093 resolvedFile = new File(resolvedPath); 16094 } else if (file != null) { 16095 resolvedPath = file.getAbsolutePath(); 16096 resolvedFile = file; 16097 } else { 16098 resolvedPath = null; 16099 resolvedFile = null; 16100 } 16101 } 16102 } 16103 16104 static class MoveInfo { 16105 final int moveId; 16106 final String fromUuid; 16107 final String toUuid; 16108 final String packageName; 16109 final String dataAppName; 16110 final int appId; 16111 final String seinfo; 16112 final int targetSdkVersion; 16113 16114 public MoveInfo(int moveId, String fromUuid, String toUuid, String packageName, 16115 String dataAppName, int appId, String seinfo, int targetSdkVersion) { 16116 this.moveId = moveId; 16117 this.fromUuid = fromUuid; 16118 this.toUuid = toUuid; 16119 this.packageName = packageName; 16120 this.dataAppName = dataAppName; 16121 this.appId = appId; 16122 this.seinfo = seinfo; 16123 this.targetSdkVersion = targetSdkVersion; 16124 } 16125 } 16126 16127 static class VerificationInfo { 16128 /** A constant used to indicate that a uid value is not present. */ 16129 public static final int NO_UID = -1; 16130 16131 /** URI referencing where the package was downloaded from. */ 16132 final Uri originatingUri; 16133 16134 /** HTTP referrer URI associated with the originatingURI. */ 16135 final Uri referrer; 16136 16137 /** UID of the application that the install request originated from. */ 16138 final int originatingUid; 16139 16140 /** UID of application requesting the install */ 16141 final int installerUid; 16142 16143 VerificationInfo(Uri originatingUri, Uri referrer, int originatingUid, int installerUid) { 16144 this.originatingUri = originatingUri; 16145 this.referrer = referrer; 16146 this.originatingUid = originatingUid; 16147 this.installerUid = installerUid; 16148 } 16149 } 16150 16151 class InstallParams extends HandlerParams { 16152 final OriginInfo origin; 16153 final MoveInfo move; 16154 final IPackageInstallObserver2 observer; 16155 int installFlags; 16156 final String installerPackageName; 16157 final String volumeUuid; 16158 private InstallArgs mArgs; 16159 private int mRet; 16160 final String packageAbiOverride; 16161 final String[] grantedRuntimePermissions; 16162 final VerificationInfo verificationInfo; 16163 final Certificate[][] certificates; 16164 final int installReason; 16165 16166 InstallParams(OriginInfo origin, MoveInfo move, IPackageInstallObserver2 observer, 16167 int installFlags, String installerPackageName, String volumeUuid, 16168 VerificationInfo verificationInfo, UserHandle user, String packageAbiOverride, 16169 String[] grantedPermissions, Certificate[][] certificates, int installReason) { 16170 super(user); 16171 this.origin = origin; 16172 this.move = move; 16173 this.observer = observer; 16174 this.installFlags = installFlags; 16175 this.installerPackageName = installerPackageName; 16176 this.volumeUuid = volumeUuid; 16177 this.verificationInfo = verificationInfo; 16178 this.packageAbiOverride = packageAbiOverride; 16179 this.grantedRuntimePermissions = grantedPermissions; 16180 this.certificates = certificates; 16181 this.installReason = installReason; 16182 } 16183 16184 @Override 16185 public String toString() { 16186 return "InstallParams{" + Integer.toHexString(System.identityHashCode(this)) 16187 + " file=" + origin.file + " cid=" + origin.cid + "}"; 16188 } 16189 16190 private int installLocationPolicy(PackageInfoLite pkgLite) { 16191 String packageName = pkgLite.packageName; 16192 int installLocation = pkgLite.installLocation; 16193 boolean onSd = (installFlags & PackageManager.INSTALL_EXTERNAL) != 0; 16194 // reader 16195 synchronized (mPackages) { 16196 // Currently installed package which the new package is attempting to replace or 16197 // null if no such package is installed. 16198 PackageParser.Package installedPkg = mPackages.get(packageName); 16199 // Package which currently owns the data which the new package will own if installed. 16200 // If an app is unstalled while keeping data (e.g., adb uninstall -k), installedPkg 16201 // will be null whereas dataOwnerPkg will contain information about the package 16202 // which was uninstalled while keeping its data. 16203 PackageParser.Package dataOwnerPkg = installedPkg; 16204 if (dataOwnerPkg == null) { 16205 PackageSetting ps = mSettings.mPackages.get(packageName); 16206 if (ps != null) { 16207 dataOwnerPkg = ps.pkg; 16208 } 16209 } 16210 16211 if (dataOwnerPkg != null) { 16212 // If installed, the package will get access to data left on the device by its 16213 // predecessor. As a security measure, this is permited only if this is not a 16214 // version downgrade or if the predecessor package is marked as debuggable and 16215 // a downgrade is explicitly requested. 16216 // 16217 // On debuggable platform builds, downgrades are permitted even for 16218 // non-debuggable packages to make testing easier. Debuggable platform builds do 16219 // not offer security guarantees and thus it's OK to disable some security 16220 // mechanisms to make debugging/testing easier on those builds. However, even on 16221 // debuggable builds downgrades of packages are permitted only if requested via 16222 // installFlags. This is because we aim to keep the behavior of debuggable 16223 // platform builds as close as possible to the behavior of non-debuggable 16224 // platform builds. 16225 final boolean downgradeRequested = 16226 (installFlags & PackageManager.INSTALL_ALLOW_DOWNGRADE) != 0; 16227 final boolean packageDebuggable = 16228 (dataOwnerPkg.applicationInfo.flags 16229 & ApplicationInfo.FLAG_DEBUGGABLE) != 0; 16230 final boolean downgradePermitted = 16231 (downgradeRequested) && ((Build.IS_DEBUGGABLE) || (packageDebuggable)); 16232 if (!downgradePermitted) { 16233 try { 16234 checkDowngrade(dataOwnerPkg, pkgLite); 16235 } catch (PackageManagerException e) { 16236 Slog.w(TAG, "Downgrade detected: " + e.getMessage()); 16237 return PackageHelper.RECOMMEND_FAILED_VERSION_DOWNGRADE; 16238 } 16239 } 16240 } 16241 16242 if (installedPkg != null) { 16243 if ((installFlags & PackageManager.INSTALL_REPLACE_EXISTING) != 0) { 16244 // Check for updated system application. 16245 if ((installedPkg.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 16246 if (onSd) { 16247 Slog.w(TAG, "Cannot install update to system app on sdcard"); 16248 return PackageHelper.RECOMMEND_FAILED_INVALID_LOCATION; 16249 } 16250 return PackageHelper.RECOMMEND_INSTALL_INTERNAL; 16251 } else { 16252 if (onSd) { 16253 // Install flag overrides everything. 16254 return PackageHelper.RECOMMEND_INSTALL_EXTERNAL; 16255 } 16256 // If current upgrade specifies particular preference 16257 if (installLocation == PackageInfo.INSTALL_LOCATION_INTERNAL_ONLY) { 16258 // Application explicitly specified internal. 16259 return PackageHelper.RECOMMEND_INSTALL_INTERNAL; 16260 } else if (installLocation == PackageInfo.INSTALL_LOCATION_PREFER_EXTERNAL) { 16261 // App explictly prefers external. Let policy decide 16262 } else { 16263 // Prefer previous location 16264 if (isExternal(installedPkg)) { 16265 return PackageHelper.RECOMMEND_INSTALL_EXTERNAL; 16266 } 16267 return PackageHelper.RECOMMEND_INSTALL_INTERNAL; 16268 } 16269 } 16270 } else { 16271 // Invalid install. Return error code 16272 return PackageHelper.RECOMMEND_FAILED_ALREADY_EXISTS; 16273 } 16274 } 16275 } 16276 // All the special cases have been taken care of. 16277 // Return result based on recommended install location. 16278 if (onSd) { 16279 return PackageHelper.RECOMMEND_INSTALL_EXTERNAL; 16280 } 16281 return pkgLite.recommendedInstallLocation; 16282 } 16283 16284 /* 16285 * Invoke remote method to get package information and install 16286 * location values. Override install location based on default 16287 * policy if needed and then create install arguments based 16288 * on the install location. 16289 */ 16290 public void handleStartCopy() throws RemoteException { 16291 int ret = PackageManager.INSTALL_SUCCEEDED; 16292 16293 // If we're already staged, we've firmly committed to an install location 16294 if (origin.staged) { 16295 if (origin.file != null) { 16296 installFlags |= PackageManager.INSTALL_INTERNAL; 16297 installFlags &= ~PackageManager.INSTALL_EXTERNAL; 16298 } else if (origin.cid != null) { 16299 installFlags |= PackageManager.INSTALL_EXTERNAL; 16300 installFlags &= ~PackageManager.INSTALL_INTERNAL; 16301 } else { 16302 throw new IllegalStateException("Invalid stage location"); 16303 } 16304 } 16305 16306 final boolean onSd = (installFlags & PackageManager.INSTALL_EXTERNAL) != 0; 16307 final boolean onInt = (installFlags & PackageManager.INSTALL_INTERNAL) != 0; 16308 final boolean ephemeral = (installFlags & PackageManager.INSTALL_INSTANT_APP) != 0; 16309 PackageInfoLite pkgLite = null; 16310 16311 if (onInt && onSd) { 16312 // Check if both bits are set. 16313 Slog.w(TAG, "Conflicting flags specified for installing on both internal and external"); 16314 ret = PackageManager.INSTALL_FAILED_INVALID_INSTALL_LOCATION; 16315 } else if (onSd && ephemeral) { 16316 Slog.w(TAG, "Conflicting flags specified for installing ephemeral on external"); 16317 ret = PackageManager.INSTALL_FAILED_INVALID_INSTALL_LOCATION; 16318 } else { 16319 pkgLite = mContainerService.getMinimalPackageInfo(origin.resolvedPath, installFlags, 16320 packageAbiOverride); 16321 16322 if (DEBUG_EPHEMERAL && ephemeral) { 16323 Slog.v(TAG, "pkgLite for install: " + pkgLite); 16324 } 16325 16326 /* 16327 * If we have too little free space, try to free cache 16328 * before giving up. 16329 */ 16330 if (!origin.staged && pkgLite.recommendedInstallLocation 16331 == PackageHelper.RECOMMEND_FAILED_INSUFFICIENT_STORAGE) { 16332 // TODO: focus freeing disk space on the target device 16333 final StorageManager storage = StorageManager.from(mContext); 16334 final long lowThreshold = storage.getStorageLowBytes( 16335 Environment.getDataDirectory()); 16336 16337 final long sizeBytes = mContainerService.calculateInstalledSize( 16338 origin.resolvedPath, isForwardLocked(), packageAbiOverride); 16339 16340 try { 16341 mInstaller.freeCache(null, sizeBytes + lowThreshold, 0, 0); 16342 pkgLite = mContainerService.getMinimalPackageInfo(origin.resolvedPath, 16343 installFlags, packageAbiOverride); 16344 } catch (InstallerException e) { 16345 Slog.w(TAG, "Failed to free cache", e); 16346 } 16347 16348 /* 16349 * The cache free must have deleted the file we 16350 * downloaded to install. 16351 * 16352 * TODO: fix the "freeCache" call to not delete 16353 * the file we care about. 16354 */ 16355 if (pkgLite.recommendedInstallLocation 16356 == PackageHelper.RECOMMEND_FAILED_INVALID_URI) { 16357 pkgLite.recommendedInstallLocation 16358 = PackageHelper.RECOMMEND_FAILED_INSUFFICIENT_STORAGE; 16359 } 16360 } 16361 } 16362 16363 if (ret == PackageManager.INSTALL_SUCCEEDED) { 16364 int loc = pkgLite.recommendedInstallLocation; 16365 if (loc == PackageHelper.RECOMMEND_FAILED_INVALID_LOCATION) { 16366 ret = PackageManager.INSTALL_FAILED_INVALID_INSTALL_LOCATION; 16367 } else if (loc == PackageHelper.RECOMMEND_FAILED_ALREADY_EXISTS) { 16368 ret = PackageManager.INSTALL_FAILED_ALREADY_EXISTS; 16369 } else if (loc == PackageHelper.RECOMMEND_FAILED_INSUFFICIENT_STORAGE) { 16370 ret = PackageManager.INSTALL_FAILED_INSUFFICIENT_STORAGE; 16371 } else if (loc == PackageHelper.RECOMMEND_FAILED_INVALID_APK) { 16372 ret = PackageManager.INSTALL_FAILED_INVALID_APK; 16373 } else if (loc == PackageHelper.RECOMMEND_FAILED_INVALID_URI) { 16374 ret = PackageManager.INSTALL_FAILED_INVALID_URI; 16375 } else if (loc == PackageHelper.RECOMMEND_MEDIA_UNAVAILABLE) { 16376 ret = PackageManager.INSTALL_FAILED_MEDIA_UNAVAILABLE; 16377 } else { 16378 // Override with defaults if needed. 16379 loc = installLocationPolicy(pkgLite); 16380 if (loc == PackageHelper.RECOMMEND_FAILED_VERSION_DOWNGRADE) { 16381 ret = PackageManager.INSTALL_FAILED_VERSION_DOWNGRADE; 16382 } else if (!onSd && !onInt) { 16383 // Override install location with flags 16384 if (loc == PackageHelper.RECOMMEND_INSTALL_EXTERNAL) { 16385 // Set the flag to install on external media. 16386 installFlags |= PackageManager.INSTALL_EXTERNAL; 16387 installFlags &= ~PackageManager.INSTALL_INTERNAL; 16388 } else if (loc == PackageHelper.RECOMMEND_INSTALL_EPHEMERAL) { 16389 if (DEBUG_EPHEMERAL) { 16390 Slog.v(TAG, "...setting INSTALL_EPHEMERAL install flag"); 16391 } 16392 installFlags |= PackageManager.INSTALL_INSTANT_APP; 16393 installFlags &= ~(PackageManager.INSTALL_EXTERNAL 16394 |PackageManager.INSTALL_INTERNAL); 16395 } else { 16396 // Make sure the flag for installing on external 16397 // media is unset 16398 installFlags |= PackageManager.INSTALL_INTERNAL; 16399 installFlags &= ~PackageManager.INSTALL_EXTERNAL; 16400 } 16401 } 16402 } 16403 } 16404 16405 final InstallArgs args = createInstallArgs(this); 16406 mArgs = args; 16407 16408 if (ret == PackageManager.INSTALL_SUCCEEDED) { 16409 // TODO: http://b/22976637 16410 // Apps installed for "all" users use the device owner to verify the app 16411 UserHandle verifierUser = getUser(); 16412 if (verifierUser == UserHandle.ALL) { 16413 verifierUser = UserHandle.SYSTEM; 16414 } 16415 16416 /* 16417 * Determine if we have any installed package verifiers. If we 16418 * do, then we'll defer to them to verify the packages. 16419 */ 16420 final int requiredUid = mRequiredVerifierPackage == null ? -1 16421 : getPackageUid(mRequiredVerifierPackage, MATCH_DEBUG_TRIAGED_MISSING, 16422 verifierUser.getIdentifier()); 16423 final int installerUid = 16424 verificationInfo == null ? -1 : verificationInfo.installerUid; 16425 if (!origin.existing && requiredUid != -1 16426 && isVerificationEnabled( 16427 verifierUser.getIdentifier(), installFlags, installerUid)) { 16428 final Intent verification = new Intent( 16429 Intent.ACTION_PACKAGE_NEEDS_VERIFICATION); 16430 verification.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 16431 verification.setDataAndType(Uri.fromFile(new File(origin.resolvedPath)), 16432 PACKAGE_MIME_TYPE); 16433 verification.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION); 16434 16435 // Query all live verifiers based on current user state 16436 final List<ResolveInfo> receivers = queryIntentReceiversInternal(verification, 16437 PACKAGE_MIME_TYPE, 0, verifierUser.getIdentifier(), 16438 false /*allowDynamicSplits*/); 16439 16440 if (DEBUG_VERIFY) { 16441 Slog.d(TAG, "Found " + receivers.size() + " verifiers for intent " 16442 + verification.toString() + " with " + pkgLite.verifiers.length 16443 + " optional verifiers"); 16444 } 16445 16446 final int verificationId = mPendingVerificationToken++; 16447 16448 verification.putExtra(PackageManager.EXTRA_VERIFICATION_ID, verificationId); 16449 16450 verification.putExtra(PackageManager.EXTRA_VERIFICATION_INSTALLER_PACKAGE, 16451 installerPackageName); 16452 16453 verification.putExtra(PackageManager.EXTRA_VERIFICATION_INSTALL_FLAGS, 16454 installFlags); 16455 16456 verification.putExtra(PackageManager.EXTRA_VERIFICATION_PACKAGE_NAME, 16457 pkgLite.packageName); 16458 16459 verification.putExtra(PackageManager.EXTRA_VERIFICATION_VERSION_CODE, 16460 pkgLite.versionCode); 16461 16462 if (verificationInfo != null) { 16463 if (verificationInfo.originatingUri != null) { 16464 verification.putExtra(Intent.EXTRA_ORIGINATING_URI, 16465 verificationInfo.originatingUri); 16466 } 16467 if (verificationInfo.referrer != null) { 16468 verification.putExtra(Intent.EXTRA_REFERRER, 16469 verificationInfo.referrer); 16470 } 16471 if (verificationInfo.originatingUid >= 0) { 16472 verification.putExtra(Intent.EXTRA_ORIGINATING_UID, 16473 verificationInfo.originatingUid); 16474 } 16475 if (verificationInfo.installerUid >= 0) { 16476 verification.putExtra(PackageManager.EXTRA_VERIFICATION_INSTALLER_UID, 16477 verificationInfo.installerUid); 16478 } 16479 } 16480 16481 final PackageVerificationState verificationState = new PackageVerificationState( 16482 requiredUid, args); 16483 16484 mPendingVerification.append(verificationId, verificationState); 16485 16486 final List<ComponentName> sufficientVerifiers = matchVerifiers(pkgLite, 16487 receivers, verificationState); 16488 16489 DeviceIdleController.LocalService idleController = getDeviceIdleController(); 16490 final long idleDuration = getVerificationTimeout(); 16491 16492 /* 16493 * If any sufficient verifiers were listed in the package 16494 * manifest, attempt to ask them. 16495 */ 16496 if (sufficientVerifiers != null) { 16497 final int N = sufficientVerifiers.size(); 16498 if (N == 0) { 16499 Slog.i(TAG, "Additional verifiers required, but none installed."); 16500 ret = PackageManager.INSTALL_FAILED_VERIFICATION_FAILURE; 16501 } else { 16502 for (int i = 0; i < N; i++) { 16503 final ComponentName verifierComponent = sufficientVerifiers.get(i); 16504 idleController.addPowerSaveTempWhitelistApp(Process.myUid(), 16505 verifierComponent.getPackageName(), idleDuration, 16506 verifierUser.getIdentifier(), false, "package verifier"); 16507 16508 final Intent sufficientIntent = new Intent(verification); 16509 sufficientIntent.setComponent(verifierComponent); 16510 mContext.sendBroadcastAsUser(sufficientIntent, verifierUser); 16511 } 16512 } 16513 } 16514 16515 final ComponentName requiredVerifierComponent = matchComponentForVerifier( 16516 mRequiredVerifierPackage, receivers); 16517 if (ret == PackageManager.INSTALL_SUCCEEDED 16518 && mRequiredVerifierPackage != null) { 16519 Trace.asyncTraceBegin( 16520 TRACE_TAG_PACKAGE_MANAGER, "verification", verificationId); 16521 /* 16522 * Send the intent to the required verification agent, 16523 * but only start the verification timeout after the 16524 * target BroadcastReceivers have run. 16525 */ 16526 verification.setComponent(requiredVerifierComponent); 16527 idleController.addPowerSaveTempWhitelistApp(Process.myUid(), 16528 mRequiredVerifierPackage, idleDuration, 16529 verifierUser.getIdentifier(), false, "package verifier"); 16530 mContext.sendOrderedBroadcastAsUser(verification, verifierUser, 16531 android.Manifest.permission.PACKAGE_VERIFICATION_AGENT, 16532 new BroadcastReceiver() { 16533 @Override 16534 public void onReceive(Context context, Intent intent) { 16535 final Message msg = mHandler 16536 .obtainMessage(CHECK_PENDING_VERIFICATION); 16537 msg.arg1 = verificationId; 16538 mHandler.sendMessageDelayed(msg, getVerificationTimeout()); 16539 } 16540 }, null, 0, null, null); 16541 16542 /* 16543 * We don't want the copy to proceed until verification 16544 * succeeds, so null out this field. 16545 */ 16546 mArgs = null; 16547 } 16548 } else { 16549 /* 16550 * No package verification is enabled, so immediately start 16551 * the remote call to initiate copy using temporary file. 16552 */ 16553 ret = args.copyApk(mContainerService, true); 16554 } 16555 } 16556 16557 mRet = ret; 16558 } 16559 16560 @Override 16561 void handleReturnCode() { 16562 // If mArgs is null, then MCS couldn't be reached. When it 16563 // reconnects, it will try again to install. At that point, this 16564 // will succeed. 16565 if (mArgs != null) { 16566 processPendingInstall(mArgs, mRet); 16567 } 16568 } 16569 16570 @Override 16571 void handleServiceError() { 16572 mArgs = createInstallArgs(this); 16573 mRet = PackageManager.INSTALL_FAILED_INTERNAL_ERROR; 16574 } 16575 16576 public boolean isForwardLocked() { 16577 return (installFlags & PackageManager.INSTALL_FORWARD_LOCK) != 0; 16578 } 16579 } 16580 16581 /** 16582 * Used during creation of InstallArgs 16583 * 16584 * @param installFlags package installation flags 16585 * @return true if should be installed on external storage 16586 */ 16587 private static boolean installOnExternalAsec(int installFlags) { 16588 if ((installFlags & PackageManager.INSTALL_INTERNAL) != 0) { 16589 return false; 16590 } 16591 if ((installFlags & PackageManager.INSTALL_EXTERNAL) != 0) { 16592 return true; 16593 } 16594 return false; 16595 } 16596 16597 /** 16598 * Used during creation of InstallArgs 16599 * 16600 * @param installFlags package installation flags 16601 * @return true if should be installed as forward locked 16602 */ 16603 private static boolean installForwardLocked(int installFlags) { 16604 return (installFlags & PackageManager.INSTALL_FORWARD_LOCK) != 0; 16605 } 16606 16607 private InstallArgs createInstallArgs(InstallParams params) { 16608 if (params.move != null) { 16609 return new MoveInstallArgs(params); 16610 } else if (installOnExternalAsec(params.installFlags) || params.isForwardLocked()) { 16611 return new AsecInstallArgs(params); 16612 } else { 16613 return new FileInstallArgs(params); 16614 } 16615 } 16616 16617 /** 16618 * Create args that describe an existing installed package. Typically used 16619 * when cleaning up old installs, or used as a move source. 16620 */ 16621 private InstallArgs createInstallArgsForExisting(int installFlags, String codePath, 16622 String resourcePath, String[] instructionSets) { 16623 final boolean isInAsec; 16624 if (installOnExternalAsec(installFlags)) { 16625 /* Apps on SD card are always in ASEC containers. */ 16626 isInAsec = true; 16627 } else if (installForwardLocked(installFlags) 16628 && !codePath.startsWith(mDrmAppPrivateInstallDir.getAbsolutePath())) { 16629 /* 16630 * Forward-locked apps are only in ASEC containers if they're the 16631 * new style 16632 */ 16633 isInAsec = true; 16634 } else { 16635 isInAsec = false; 16636 } 16637 16638 if (isInAsec) { 16639 return new AsecInstallArgs(codePath, instructionSets, 16640 installOnExternalAsec(installFlags), installForwardLocked(installFlags)); 16641 } else { 16642 return new FileInstallArgs(codePath, resourcePath, instructionSets); 16643 } 16644 } 16645 16646 static abstract class InstallArgs { 16647 /** @see InstallParams#origin */ 16648 final OriginInfo origin; 16649 /** @see InstallParams#move */ 16650 final MoveInfo move; 16651 16652 final IPackageInstallObserver2 observer; 16653 // Always refers to PackageManager flags only 16654 final int installFlags; 16655 final String installerPackageName; 16656 final String volumeUuid; 16657 final UserHandle user; 16658 final String abiOverride; 16659 final String[] installGrantPermissions; 16660 /** If non-null, drop an async trace when the install completes */ 16661 final String traceMethod; 16662 final int traceCookie; 16663 final Certificate[][] certificates; 16664 final int installReason; 16665 16666 // The list of instruction sets supported by this app. This is currently 16667 // only used during the rmdex() phase to clean up resources. We can get rid of this 16668 // if we move dex files under the common app path. 16669 /* nullable */ String[] instructionSets; 16670 16671 InstallArgs(OriginInfo origin, MoveInfo move, IPackageInstallObserver2 observer, 16672 int installFlags, String installerPackageName, String volumeUuid, 16673 UserHandle user, String[] instructionSets, 16674 String abiOverride, String[] installGrantPermissions, 16675 String traceMethod, int traceCookie, Certificate[][] certificates, 16676 int installReason) { 16677 this.origin = origin; 16678 this.move = move; 16679 this.installFlags = installFlags; 16680 this.observer = observer; 16681 this.installerPackageName = installerPackageName; 16682 this.volumeUuid = volumeUuid; 16683 this.user = user; 16684 this.instructionSets = instructionSets; 16685 this.abiOverride = abiOverride; 16686 this.installGrantPermissions = installGrantPermissions; 16687 this.traceMethod = traceMethod; 16688 this.traceCookie = traceCookie; 16689 this.certificates = certificates; 16690 this.installReason = installReason; 16691 } 16692 16693 abstract int copyApk(IMediaContainerService imcs, boolean temp) throws RemoteException; 16694 abstract int doPreInstall(int status); 16695 16696 /** 16697 * Rename package into final resting place. All paths on the given 16698 * scanned package should be updated to reflect the rename. 16699 */ 16700 abstract boolean doRename(int status, PackageParser.Package pkg, String oldCodePath); 16701 abstract int doPostInstall(int status, int uid); 16702 16703 /** @see PackageSettingBase#codePathString */ 16704 abstract String getCodePath(); 16705 /** @see PackageSettingBase#resourcePathString */ 16706 abstract String getResourcePath(); 16707 16708 // Need installer lock especially for dex file removal. 16709 abstract void cleanUpResourcesLI(); 16710 abstract boolean doPostDeleteLI(boolean delete); 16711 16712 /** 16713 * Called before the source arguments are copied. This is used mostly 16714 * for MoveParams when it needs to read the source file to put it in the 16715 * destination. 16716 */ 16717 int doPreCopy() { 16718 return PackageManager.INSTALL_SUCCEEDED; 16719 } 16720 16721 /** 16722 * Called after the source arguments are copied. This is used mostly for 16723 * MoveParams when it needs to read the source file to put it in the 16724 * destination. 16725 */ 16726 int doPostCopy(int uid) { 16727 return PackageManager.INSTALL_SUCCEEDED; 16728 } 16729 16730 protected boolean isFwdLocked() { 16731 return (installFlags & PackageManager.INSTALL_FORWARD_LOCK) != 0; 16732 } 16733 16734 protected boolean isExternalAsec() { 16735 return (installFlags & PackageManager.INSTALL_EXTERNAL) != 0; 16736 } 16737 16738 protected boolean isEphemeral() { 16739 return (installFlags & PackageManager.INSTALL_INSTANT_APP) != 0; 16740 } 16741 16742 UserHandle getUser() { 16743 return user; 16744 } 16745 } 16746 16747 void removeDexFiles(List<String> allCodePaths, String[] instructionSets) { 16748 if (!allCodePaths.isEmpty()) { 16749 if (instructionSets == null) { 16750 throw new IllegalStateException("instructionSet == null"); 16751 } 16752 String[] dexCodeInstructionSets = getDexCodeInstructionSets(instructionSets); 16753 for (String codePath : allCodePaths) { 16754 for (String dexCodeInstructionSet : dexCodeInstructionSets) { 16755 try { 16756 mInstaller.rmdex(codePath, dexCodeInstructionSet); 16757 } catch (InstallerException ignored) { 16758 } 16759 } 16760 } 16761 } 16762 } 16763 16764 /** 16765 * Logic to handle installation of non-ASEC applications, including copying 16766 * and renaming logic. 16767 */ 16768 class FileInstallArgs extends InstallArgs { 16769 private File codeFile; 16770 private File resourceFile; 16771 16772 // Example topology: 16773 // /data/app/com.example/base.apk 16774 // /data/app/com.example/split_foo.apk 16775 // /data/app/com.example/lib/arm/libfoo.so 16776 // /data/app/com.example/lib/arm64/libfoo.so 16777 // /data/app/com.example/dalvik/arm/base.apk@classes.dex 16778 16779 /** New install */ 16780 FileInstallArgs(InstallParams params) { 16781 super(params.origin, params.move, params.observer, params.installFlags, 16782 params.installerPackageName, params.volumeUuid, 16783 params.getUser(), null /*instructionSets*/, params.packageAbiOverride, 16784 params.grantedRuntimePermissions, 16785 params.traceMethod, params.traceCookie, params.certificates, 16786 params.installReason); 16787 if (isFwdLocked()) { 16788 throw new IllegalArgumentException("Forward locking only supported in ASEC"); 16789 } 16790 } 16791 16792 /** Existing install */ 16793 FileInstallArgs(String codePath, String resourcePath, String[] instructionSets) { 16794 super(OriginInfo.fromNothing(), null, null, 0, null, null, null, instructionSets, 16795 null, null, null, 0, null /*certificates*/, 16796 PackageManager.INSTALL_REASON_UNKNOWN); 16797 this.codeFile = (codePath != null) ? new File(codePath) : null; 16798 this.resourceFile = (resourcePath != null) ? new File(resourcePath) : null; 16799 } 16800 16801 int copyApk(IMediaContainerService imcs, boolean temp) throws RemoteException { 16802 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "copyApk"); 16803 try { 16804 return doCopyApk(imcs, temp); 16805 } finally { 16806 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 16807 } 16808 } 16809 16810 private int doCopyApk(IMediaContainerService imcs, boolean temp) throws RemoteException { 16811 if (origin.staged) { 16812 if (DEBUG_INSTALL) Slog.d(TAG, origin.file + " already staged; skipping copy"); 16813 codeFile = origin.file; 16814 resourceFile = origin.file; 16815 return PackageManager.INSTALL_SUCCEEDED; 16816 } 16817 16818 try { 16819 final boolean isEphemeral = (installFlags & PackageManager.INSTALL_INSTANT_APP) != 0; 16820 final File tempDir = 16821 mInstallerService.allocateStageDirLegacy(volumeUuid, isEphemeral); 16822 codeFile = tempDir; 16823 resourceFile = tempDir; 16824 } catch (IOException e) { 16825 Slog.w(TAG, "Failed to create copy file: " + e); 16826 return PackageManager.INSTALL_FAILED_INSUFFICIENT_STORAGE; 16827 } 16828 16829 final IParcelFileDescriptorFactory target = new IParcelFileDescriptorFactory.Stub() { 16830 @Override 16831 public ParcelFileDescriptor open(String name, int mode) throws RemoteException { 16832 if (!FileUtils.isValidExtFilename(name)) { 16833 throw new IllegalArgumentException("Invalid filename: " + name); 16834 } 16835 try { 16836 final File file = new File(codeFile, name); 16837 final FileDescriptor fd = Os.open(file.getAbsolutePath(), 16838 O_RDWR | O_CREAT, 0644); 16839 Os.chmod(file.getAbsolutePath(), 0644); 16840 return new ParcelFileDescriptor(fd); 16841 } catch (ErrnoException e) { 16842 throw new RemoteException("Failed to open: " + e.getMessage()); 16843 } 16844 } 16845 }; 16846 16847 int ret = PackageManager.INSTALL_SUCCEEDED; 16848 ret = imcs.copyPackage(origin.file.getAbsolutePath(), target); 16849 if (ret != PackageManager.INSTALL_SUCCEEDED) { 16850 Slog.e(TAG, "Failed to copy package"); 16851 return ret; 16852 } 16853 16854 final File libraryRoot = new File(codeFile, LIB_DIR_NAME); 16855 NativeLibraryHelper.Handle handle = null; 16856 try { 16857 handle = NativeLibraryHelper.Handle.create(codeFile); 16858 ret = NativeLibraryHelper.copyNativeBinariesWithOverride(handle, libraryRoot, 16859 abiOverride); 16860 } catch (IOException e) { 16861 Slog.e(TAG, "Copying native libraries failed", e); 16862 ret = PackageManager.INSTALL_FAILED_INTERNAL_ERROR; 16863 } finally { 16864 IoUtils.closeQuietly(handle); 16865 } 16866 16867 return ret; 16868 } 16869 16870 int doPreInstall(int status) { 16871 if (status != PackageManager.INSTALL_SUCCEEDED) { 16872 cleanUp(); 16873 } 16874 return status; 16875 } 16876 16877 boolean doRename(int status, PackageParser.Package pkg, String oldCodePath) { 16878 if (status != PackageManager.INSTALL_SUCCEEDED) { 16879 cleanUp(); 16880 return false; 16881 } 16882 16883 final File targetDir = codeFile.getParentFile(); 16884 final File beforeCodeFile = codeFile; 16885 final File afterCodeFile = getNextCodePath(targetDir, pkg.packageName); 16886 16887 if (DEBUG_INSTALL) Slog.d(TAG, "Renaming " + beforeCodeFile + " to " + afterCodeFile); 16888 try { 16889 Os.rename(beforeCodeFile.getAbsolutePath(), afterCodeFile.getAbsolutePath()); 16890 } catch (ErrnoException e) { 16891 Slog.w(TAG, "Failed to rename", e); 16892 return false; 16893 } 16894 16895 if (!SELinux.restoreconRecursive(afterCodeFile)) { 16896 Slog.w(TAG, "Failed to restorecon"); 16897 return false; 16898 } 16899 16900 // Reflect the rename internally 16901 codeFile = afterCodeFile; 16902 resourceFile = afterCodeFile; 16903 16904 // Reflect the rename in scanned details 16905 pkg.setCodePath(afterCodeFile.getAbsolutePath()); 16906 pkg.setBaseCodePath(FileUtils.rewriteAfterRename(beforeCodeFile, 16907 afterCodeFile, pkg.baseCodePath)); 16908 pkg.setSplitCodePaths(FileUtils.rewriteAfterRename(beforeCodeFile, 16909 afterCodeFile, pkg.splitCodePaths)); 16910 16911 // Reflect the rename in app info 16912 pkg.setApplicationVolumeUuid(pkg.volumeUuid); 16913 pkg.setApplicationInfoCodePath(pkg.codePath); 16914 pkg.setApplicationInfoBaseCodePath(pkg.baseCodePath); 16915 pkg.setApplicationInfoSplitCodePaths(pkg.splitCodePaths); 16916 pkg.setApplicationInfoResourcePath(pkg.codePath); 16917 pkg.setApplicationInfoBaseResourcePath(pkg.baseCodePath); 16918 pkg.setApplicationInfoSplitResourcePaths(pkg.splitCodePaths); 16919 16920 return true; 16921 } 16922 16923 int doPostInstall(int status, int uid) { 16924 if (status != PackageManager.INSTALL_SUCCEEDED) { 16925 cleanUp(); 16926 } 16927 return status; 16928 } 16929 16930 @Override 16931 String getCodePath() { 16932 return (codeFile != null) ? codeFile.getAbsolutePath() : null; 16933 } 16934 16935 @Override 16936 String getResourcePath() { 16937 return (resourceFile != null) ? resourceFile.getAbsolutePath() : null; 16938 } 16939 16940 private boolean cleanUp() { 16941 if (codeFile == null || !codeFile.exists()) { 16942 return false; 16943 } 16944 16945 removeCodePathLI(codeFile); 16946 16947 if (resourceFile != null && !FileUtils.contains(codeFile, resourceFile)) { 16948 resourceFile.delete(); 16949 } 16950 16951 return true; 16952 } 16953 16954 void cleanUpResourcesLI() { 16955 // Try enumerating all code paths before deleting 16956 List<String> allCodePaths = Collections.EMPTY_LIST; 16957 if (codeFile != null && codeFile.exists()) { 16958 try { 16959 final PackageLite pkg = PackageParser.parsePackageLite(codeFile, 0); 16960 allCodePaths = pkg.getAllCodePaths(); 16961 } catch (PackageParserException e) { 16962 // Ignored; we tried our best 16963 } 16964 } 16965 16966 cleanUp(); 16967 removeDexFiles(allCodePaths, instructionSets); 16968 } 16969 16970 boolean doPostDeleteLI(boolean delete) { 16971 // XXX err, shouldn't we respect the delete flag? 16972 cleanUpResourcesLI(); 16973 return true; 16974 } 16975 } 16976 16977 private boolean isAsecExternal(String cid) { 16978 final String asecPath = PackageHelper.getSdFilesystem(cid); 16979 return !asecPath.startsWith(mAsecInternalPath); 16980 } 16981 16982 private static void maybeThrowExceptionForMultiArchCopy(String message, int copyRet) throws 16983 PackageManagerException { 16984 if (copyRet < 0) { 16985 if (copyRet != PackageManager.NO_NATIVE_LIBRARIES && 16986 copyRet != PackageManager.INSTALL_FAILED_NO_MATCHING_ABIS) { 16987 throw new PackageManagerException(copyRet, message); 16988 } 16989 } 16990 } 16991 16992 /** 16993 * Extract the StorageManagerService "container ID" from the full code path of an 16994 * .apk. 16995 */ 16996 static String cidFromCodePath(String fullCodePath) { 16997 int eidx = fullCodePath.lastIndexOf("/"); 16998 String subStr1 = fullCodePath.substring(0, eidx); 16999 int sidx = subStr1.lastIndexOf("/"); 17000 return subStr1.substring(sidx+1, eidx); 17001 } 17002 17003 /** 17004 * Logic to handle installation of ASEC applications, including copying and 17005 * renaming logic. 17006 */ 17007 class AsecInstallArgs extends InstallArgs { 17008 static final String RES_FILE_NAME = "pkg.apk"; 17009 static final String PUBLIC_RES_FILE_NAME = "res.zip"; 17010 17011 String cid; 17012 String packagePath; 17013 String resourcePath; 17014 17015 /** New install */ 17016 AsecInstallArgs(InstallParams params) { 17017 super(params.origin, params.move, params.observer, params.installFlags, 17018 params.installerPackageName, params.volumeUuid, 17019 params.getUser(), null /* instruction sets */, params.packageAbiOverride, 17020 params.grantedRuntimePermissions, 17021 params.traceMethod, params.traceCookie, params.certificates, 17022 params.installReason); 17023 } 17024 17025 /** Existing install */ 17026 AsecInstallArgs(String fullCodePath, String[] instructionSets, 17027 boolean isExternal, boolean isForwardLocked) { 17028 super(OriginInfo.fromNothing(), null, null, (isExternal ? INSTALL_EXTERNAL : 0) 17029 | (isForwardLocked ? INSTALL_FORWARD_LOCK : 0), null, null, null, 17030 instructionSets, null, null, null, 0, null /*certificates*/, 17031 PackageManager.INSTALL_REASON_UNKNOWN); 17032 // Hackily pretend we're still looking at a full code path 17033 if (!fullCodePath.endsWith(RES_FILE_NAME)) { 17034 fullCodePath = new File(fullCodePath, RES_FILE_NAME).getAbsolutePath(); 17035 } 17036 17037 // Extract cid from fullCodePath 17038 int eidx = fullCodePath.lastIndexOf("/"); 17039 String subStr1 = fullCodePath.substring(0, eidx); 17040 int sidx = subStr1.lastIndexOf("/"); 17041 cid = subStr1.substring(sidx+1, eidx); 17042 setMountPath(subStr1); 17043 } 17044 17045 AsecInstallArgs(String cid, String[] instructionSets, boolean isForwardLocked) { 17046 super(OriginInfo.fromNothing(), null, null, (isAsecExternal(cid) ? INSTALL_EXTERNAL : 0) 17047 | (isForwardLocked ? INSTALL_FORWARD_LOCK : 0), null, null, null, 17048 instructionSets, null, null, null, 0, null /*certificates*/, 17049 PackageManager.INSTALL_REASON_UNKNOWN); 17050 this.cid = cid; 17051 setMountPath(PackageHelper.getSdDir(cid)); 17052 } 17053 17054 void createCopyFile() { 17055 cid = mInstallerService.allocateExternalStageCidLegacy(); 17056 } 17057 17058 int copyApk(IMediaContainerService imcs, boolean temp) throws RemoteException { 17059 if (origin.staged && origin.cid != null) { 17060 if (DEBUG_INSTALL) Slog.d(TAG, origin.cid + " already staged; skipping copy"); 17061 cid = origin.cid; 17062 setMountPath(PackageHelper.getSdDir(cid)); 17063 return PackageManager.INSTALL_SUCCEEDED; 17064 } 17065 17066 if (temp) { 17067 createCopyFile(); 17068 } else { 17069 /* 17070 * Pre-emptively destroy the container since it's destroyed if 17071 * copying fails due to it existing anyway. 17072 */ 17073 PackageHelper.destroySdDir(cid); 17074 } 17075 17076 final String newMountPath = imcs.copyPackageToContainer( 17077 origin.file.getAbsolutePath(), cid, getEncryptKey(), isExternalAsec(), 17078 isFwdLocked(), deriveAbiOverride(abiOverride, null /* settings */)); 17079 17080 if (newMountPath != null) { 17081 setMountPath(newMountPath); 17082 return PackageManager.INSTALL_SUCCEEDED; 17083 } else { 17084 return PackageManager.INSTALL_FAILED_CONTAINER_ERROR; 17085 } 17086 } 17087 17088 @Override 17089 String getCodePath() { 17090 return packagePath; 17091 } 17092 17093 @Override 17094 String getResourcePath() { 17095 return resourcePath; 17096 } 17097 17098 int doPreInstall(int status) { 17099 if (status != PackageManager.INSTALL_SUCCEEDED) { 17100 // Destroy container 17101 PackageHelper.destroySdDir(cid); 17102 } else { 17103 boolean mounted = PackageHelper.isContainerMounted(cid); 17104 if (!mounted) { 17105 String newMountPath = PackageHelper.mountSdDir(cid, getEncryptKey(), 17106 Process.SYSTEM_UID); 17107 if (newMountPath != null) { 17108 setMountPath(newMountPath); 17109 } else { 17110 return PackageManager.INSTALL_FAILED_CONTAINER_ERROR; 17111 } 17112 } 17113 } 17114 return status; 17115 } 17116 17117 boolean doRename(int status, PackageParser.Package pkg, String oldCodePath) { 17118 String newCacheId = getNextCodePath(oldCodePath, pkg.packageName, "/" + RES_FILE_NAME); 17119 String newMountPath = null; 17120 if (PackageHelper.isContainerMounted(cid)) { 17121 // Unmount the container 17122 if (!PackageHelper.unMountSdDir(cid)) { 17123 Slog.i(TAG, "Failed to unmount " + cid + " before renaming"); 17124 return false; 17125 } 17126 } 17127 if (!PackageHelper.renameSdDir(cid, newCacheId)) { 17128 Slog.e(TAG, "Failed to rename " + cid + " to " + newCacheId + 17129 " which might be stale. Will try to clean up."); 17130 // Clean up the stale container and proceed to recreate. 17131 if (!PackageHelper.destroySdDir(newCacheId)) { 17132 Slog.e(TAG, "Very strange. Cannot clean up stale container " + newCacheId); 17133 return false; 17134 } 17135 // Successfully cleaned up stale container. Try to rename again. 17136 if (!PackageHelper.renameSdDir(cid, newCacheId)) { 17137 Slog.e(TAG, "Failed to rename " + cid + " to " + newCacheId 17138 + " inspite of cleaning it up."); 17139 return false; 17140 } 17141 } 17142 if (!PackageHelper.isContainerMounted(newCacheId)) { 17143 Slog.w(TAG, "Mounting container " + newCacheId); 17144 newMountPath = PackageHelper.mountSdDir(newCacheId, 17145 getEncryptKey(), Process.SYSTEM_UID); 17146 } else { 17147 newMountPath = PackageHelper.getSdDir(newCacheId); 17148 } 17149 if (newMountPath == null) { 17150 Slog.w(TAG, "Failed to get cache path for " + newCacheId); 17151 return false; 17152 } 17153 Log.i(TAG, "Succesfully renamed " + cid + 17154 " to " + newCacheId + 17155 " at new path: " + newMountPath); 17156 cid = newCacheId; 17157 17158 final File beforeCodeFile = new File(packagePath); 17159 setMountPath(newMountPath); 17160 final File afterCodeFile = new File(packagePath); 17161 17162 // Reflect the rename in scanned details 17163 pkg.setCodePath(afterCodeFile.getAbsolutePath()); 17164 pkg.setBaseCodePath(FileUtils.rewriteAfterRename(beforeCodeFile, 17165 afterCodeFile, pkg.baseCodePath)); 17166 pkg.setSplitCodePaths(FileUtils.rewriteAfterRename(beforeCodeFile, 17167 afterCodeFile, pkg.splitCodePaths)); 17168 17169 // Reflect the rename in app info 17170 pkg.setApplicationVolumeUuid(pkg.volumeUuid); 17171 pkg.setApplicationInfoCodePath(pkg.codePath); 17172 pkg.setApplicationInfoBaseCodePath(pkg.baseCodePath); 17173 pkg.setApplicationInfoSplitCodePaths(pkg.splitCodePaths); 17174 pkg.setApplicationInfoResourcePath(pkg.codePath); 17175 pkg.setApplicationInfoBaseResourcePath(pkg.baseCodePath); 17176 pkg.setApplicationInfoSplitResourcePaths(pkg.splitCodePaths); 17177 17178 return true; 17179 } 17180 17181 private void setMountPath(String mountPath) { 17182 final File mountFile = new File(mountPath); 17183 17184 final File monolithicFile = new File(mountFile, RES_FILE_NAME); 17185 if (monolithicFile.exists()) { 17186 packagePath = monolithicFile.getAbsolutePath(); 17187 if (isFwdLocked()) { 17188 resourcePath = new File(mountFile, PUBLIC_RES_FILE_NAME).getAbsolutePath(); 17189 } else { 17190 resourcePath = packagePath; 17191 } 17192 } else { 17193 packagePath = mountFile.getAbsolutePath(); 17194 resourcePath = packagePath; 17195 } 17196 } 17197 17198 int doPostInstall(int status, int uid) { 17199 if (status != PackageManager.INSTALL_SUCCEEDED) { 17200 cleanUp(); 17201 } else { 17202 final int groupOwner; 17203 final String protectedFile; 17204 if (isFwdLocked()) { 17205 groupOwner = UserHandle.getSharedAppGid(uid); 17206 protectedFile = RES_FILE_NAME; 17207 } else { 17208 groupOwner = -1; 17209 protectedFile = null; 17210 } 17211 17212 if (uid < Process.FIRST_APPLICATION_UID 17213 || !PackageHelper.fixSdPermissions(cid, groupOwner, protectedFile)) { 17214 Slog.e(TAG, "Failed to finalize " + cid); 17215 PackageHelper.destroySdDir(cid); 17216 return PackageManager.INSTALL_FAILED_CONTAINER_ERROR; 17217 } 17218 17219 boolean mounted = PackageHelper.isContainerMounted(cid); 17220 if (!mounted) { 17221 PackageHelper.mountSdDir(cid, getEncryptKey(), Process.myUid()); 17222 } 17223 } 17224 return status; 17225 } 17226 17227 private void cleanUp() { 17228 if (DEBUG_SD_INSTALL) Slog.i(TAG, "cleanUp"); 17229 17230 // Destroy secure container 17231 PackageHelper.destroySdDir(cid); 17232 } 17233 17234 private List<String> getAllCodePaths() { 17235 final File codeFile = new File(getCodePath()); 17236 if (codeFile != null && codeFile.exists()) { 17237 try { 17238 final PackageLite pkg = PackageParser.parsePackageLite(codeFile, 0); 17239 return pkg.getAllCodePaths(); 17240 } catch (PackageParserException e) { 17241 // Ignored; we tried our best 17242 } 17243 } 17244 return Collections.EMPTY_LIST; 17245 } 17246 17247 void cleanUpResourcesLI() { 17248 // Enumerate all code paths before deleting 17249 cleanUpResourcesLI(getAllCodePaths()); 17250 } 17251 17252 private void cleanUpResourcesLI(List<String> allCodePaths) { 17253 cleanUp(); 17254 removeDexFiles(allCodePaths, instructionSets); 17255 } 17256 17257 String getPackageName() { 17258 return getAsecPackageName(cid); 17259 } 17260 17261 boolean doPostDeleteLI(boolean delete) { 17262 if (DEBUG_SD_INSTALL) Slog.i(TAG, "doPostDeleteLI() del=" + delete); 17263 final List<String> allCodePaths = getAllCodePaths(); 17264 boolean mounted = PackageHelper.isContainerMounted(cid); 17265 if (mounted) { 17266 // Unmount first 17267 if (PackageHelper.unMountSdDir(cid)) { 17268 mounted = false; 17269 } 17270 } 17271 if (!mounted && delete) { 17272 cleanUpResourcesLI(allCodePaths); 17273 } 17274 return !mounted; 17275 } 17276 17277 @Override 17278 int doPreCopy() { 17279 if (isFwdLocked()) { 17280 if (!PackageHelper.fixSdPermissions(cid, getPackageUid(DEFAULT_CONTAINER_PACKAGE, 17281 MATCH_SYSTEM_ONLY, UserHandle.USER_SYSTEM), RES_FILE_NAME)) { 17282 return PackageManager.INSTALL_FAILED_CONTAINER_ERROR; 17283 } 17284 } 17285 17286 return PackageManager.INSTALL_SUCCEEDED; 17287 } 17288 17289 @Override 17290 int doPostCopy(int uid) { 17291 if (isFwdLocked()) { 17292 if (uid < Process.FIRST_APPLICATION_UID 17293 || !PackageHelper.fixSdPermissions(cid, UserHandle.getSharedAppGid(uid), 17294 RES_FILE_NAME)) { 17295 Slog.e(TAG, "Failed to finalize " + cid); 17296 PackageHelper.destroySdDir(cid); 17297 return PackageManager.INSTALL_FAILED_CONTAINER_ERROR; 17298 } 17299 } 17300 17301 return PackageManager.INSTALL_SUCCEEDED; 17302 } 17303 } 17304 17305 /** 17306 * Logic to handle movement of existing installed applications. 17307 */ 17308 class MoveInstallArgs extends InstallArgs { 17309 private File codeFile; 17310 private File resourceFile; 17311 17312 /** New install */ 17313 MoveInstallArgs(InstallParams params) { 17314 super(params.origin, params.move, params.observer, params.installFlags, 17315 params.installerPackageName, params.volumeUuid, 17316 params.getUser(), null /* instruction sets */, params.packageAbiOverride, 17317 params.grantedRuntimePermissions, 17318 params.traceMethod, params.traceCookie, params.certificates, 17319 params.installReason); 17320 } 17321 17322 int copyApk(IMediaContainerService imcs, boolean temp) { 17323 if (DEBUG_INSTALL) Slog.d(TAG, "Moving " + move.packageName + " from " 17324 + move.fromUuid + " to " + move.toUuid); 17325 synchronized (mInstaller) { 17326 try { 17327 mInstaller.moveCompleteApp(move.fromUuid, move.toUuid, move.packageName, 17328 move.dataAppName, move.appId, move.seinfo, move.targetSdkVersion); 17329 } catch (InstallerException e) { 17330 Slog.w(TAG, "Failed to move app", e); 17331 return PackageManager.INSTALL_FAILED_INTERNAL_ERROR; 17332 } 17333 } 17334 17335 codeFile = new File(Environment.getDataAppDirectory(move.toUuid), move.dataAppName); 17336 resourceFile = codeFile; 17337 if (DEBUG_INSTALL) Slog.d(TAG, "codeFile after move is " + codeFile); 17338 17339 return PackageManager.INSTALL_SUCCEEDED; 17340 } 17341 17342 int doPreInstall(int status) { 17343 if (status != PackageManager.INSTALL_SUCCEEDED) { 17344 cleanUp(move.toUuid); 17345 } 17346 return status; 17347 } 17348 17349 boolean doRename(int status, PackageParser.Package pkg, String oldCodePath) { 17350 if (status != PackageManager.INSTALL_SUCCEEDED) { 17351 cleanUp(move.toUuid); 17352 return false; 17353 } 17354 17355 // Reflect the move in app info 17356 pkg.setApplicationVolumeUuid(pkg.volumeUuid); 17357 pkg.setApplicationInfoCodePath(pkg.codePath); 17358 pkg.setApplicationInfoBaseCodePath(pkg.baseCodePath); 17359 pkg.setApplicationInfoSplitCodePaths(pkg.splitCodePaths); 17360 pkg.setApplicationInfoResourcePath(pkg.codePath); 17361 pkg.setApplicationInfoBaseResourcePath(pkg.baseCodePath); 17362 pkg.setApplicationInfoSplitResourcePaths(pkg.splitCodePaths); 17363 17364 return true; 17365 } 17366 17367 int doPostInstall(int status, int uid) { 17368 if (status == PackageManager.INSTALL_SUCCEEDED) { 17369 cleanUp(move.fromUuid); 17370 } else { 17371 cleanUp(move.toUuid); 17372 } 17373 return status; 17374 } 17375 17376 @Override 17377 String getCodePath() { 17378 return (codeFile != null) ? codeFile.getAbsolutePath() : null; 17379 } 17380 17381 @Override 17382 String getResourcePath() { 17383 return (resourceFile != null) ? resourceFile.getAbsolutePath() : null; 17384 } 17385 17386 private boolean cleanUp(String volumeUuid) { 17387 final File codeFile = new File(Environment.getDataAppDirectory(volumeUuid), 17388 move.dataAppName); 17389 Slog.d(TAG, "Cleaning up " + move.packageName + " on " + volumeUuid); 17390 final int[] userIds = sUserManager.getUserIds(); 17391 synchronized (mInstallLock) { 17392 // Clean up both app data and code 17393 // All package moves are frozen until finished 17394 for (int userId : userIds) { 17395 try { 17396 mInstaller.destroyAppData(volumeUuid, move.packageName, userId, 17397 StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE, 0); 17398 } catch (InstallerException e) { 17399 Slog.w(TAG, String.valueOf(e)); 17400 } 17401 } 17402 removeCodePathLI(codeFile); 17403 } 17404 return true; 17405 } 17406 17407 void cleanUpResourcesLI() { 17408 throw new UnsupportedOperationException(); 17409 } 17410 17411 boolean doPostDeleteLI(boolean delete) { 17412 throw new UnsupportedOperationException(); 17413 } 17414 } 17415 17416 static String getAsecPackageName(String packageCid) { 17417 int idx = packageCid.lastIndexOf("-"); 17418 if (idx == -1) { 17419 return packageCid; 17420 } 17421 return packageCid.substring(0, idx); 17422 } 17423 17424 // Utility method used to create code paths based on package name and available index. 17425 private static String getNextCodePath(String oldCodePath, String prefix, String suffix) { 17426 String idxStr = ""; 17427 int idx = 1; 17428 // Fall back to default value of idx=1 if prefix is not 17429 // part of oldCodePath 17430 if (oldCodePath != null) { 17431 String subStr = oldCodePath; 17432 // Drop the suffix right away 17433 if (suffix != null && subStr.endsWith(suffix)) { 17434 subStr = subStr.substring(0, subStr.length() - suffix.length()); 17435 } 17436 // If oldCodePath already contains prefix find out the 17437 // ending index to either increment or decrement. 17438 int sidx = subStr.lastIndexOf(prefix); 17439 if (sidx != -1) { 17440 subStr = subStr.substring(sidx + prefix.length()); 17441 if (subStr != null) { 17442 if (subStr.startsWith(INSTALL_PACKAGE_SUFFIX)) { 17443 subStr = subStr.substring(INSTALL_PACKAGE_SUFFIX.length()); 17444 } 17445 try { 17446 idx = Integer.parseInt(subStr); 17447 if (idx <= 1) { 17448 idx++; 17449 } else { 17450 idx--; 17451 } 17452 } catch(NumberFormatException e) { 17453 } 17454 } 17455 } 17456 } 17457 idxStr = INSTALL_PACKAGE_SUFFIX + Integer.toString(idx); 17458 return prefix + idxStr; 17459 } 17460 17461 private File getNextCodePath(File targetDir, String packageName) { 17462 File result; 17463 SecureRandom random = new SecureRandom(); 17464 byte[] bytes = new byte[16]; 17465 do { 17466 random.nextBytes(bytes); 17467 String suffix = Base64.encodeToString(bytes, Base64.URL_SAFE | Base64.NO_WRAP); 17468 result = new File(targetDir, packageName + "-" + suffix); 17469 } while (result.exists()); 17470 return result; 17471 } 17472 17473 // Utility method that returns the relative package path with respect 17474 // to the installation directory. Like say for /data/data/com.test-1.apk 17475 // string com.test-1 is returned. 17476 static String deriveCodePathName(String codePath) { 17477 if (codePath == null) { 17478 return null; 17479 } 17480 final File codeFile = new File(codePath); 17481 final String name = codeFile.getName(); 17482 if (codeFile.isDirectory()) { 17483 return name; 17484 } else if (name.endsWith(".apk") || name.endsWith(".tmp")) { 17485 final int lastDot = name.lastIndexOf('.'); 17486 return name.substring(0, lastDot); 17487 } else { 17488 Slog.w(TAG, "Odd, " + codePath + " doesn't look like an APK"); 17489 return null; 17490 } 17491 } 17492 17493 static class PackageInstalledInfo { 17494 String name; 17495 int uid; 17496 // The set of users that originally had this package installed. 17497 int[] origUsers; 17498 // The set of users that now have this package installed. 17499 int[] newUsers; 17500 PackageParser.Package pkg; 17501 int returnCode; 17502 String returnMsg; 17503 String installerPackageName; 17504 PackageRemovedInfo removedInfo; 17505 ArrayMap<String, PackageInstalledInfo> addedChildPackages; 17506 17507 public void setError(int code, String msg) { 17508 setReturnCode(code); 17509 setReturnMessage(msg); 17510 Slog.w(TAG, msg); 17511 } 17512 17513 public void setError(String msg, PackageParserException e) { 17514 setReturnCode(e.error); 17515 setReturnMessage(ExceptionUtils.getCompleteMessage(msg, e)); 17516 final int childCount = (addedChildPackages != null) ? addedChildPackages.size() : 0; 17517 for (int i = 0; i < childCount; i++) { 17518 addedChildPackages.valueAt(i).setError(msg, e); 17519 } 17520 Slog.w(TAG, msg, e); 17521 } 17522 17523 public void setError(String msg, PackageManagerException e) { 17524 returnCode = e.error; 17525 setReturnMessage(ExceptionUtils.getCompleteMessage(msg, e)); 17526 final int childCount = (addedChildPackages != null) ? addedChildPackages.size() : 0; 17527 for (int i = 0; i < childCount; i++) { 17528 addedChildPackages.valueAt(i).setError(msg, e); 17529 } 17530 Slog.w(TAG, msg, e); 17531 } 17532 17533 public void setReturnCode(int returnCode) { 17534 this.returnCode = returnCode; 17535 final int childCount = (addedChildPackages != null) ? addedChildPackages.size() : 0; 17536 for (int i = 0; i < childCount; i++) { 17537 addedChildPackages.valueAt(i).returnCode = returnCode; 17538 } 17539 } 17540 17541 private void setReturnMessage(String returnMsg) { 17542 this.returnMsg = returnMsg; 17543 final int childCount = (addedChildPackages != null) ? addedChildPackages.size() : 0; 17544 for (int i = 0; i < childCount; i++) { 17545 addedChildPackages.valueAt(i).returnMsg = returnMsg; 17546 } 17547 } 17548 17549 // In some error cases we want to convey more info back to the observer 17550 String origPackage; 17551 String origPermission; 17552 } 17553 17554 /* 17555 * Install a non-existing package. 17556 */ 17557 private void installNewPackageLIF(PackageParser.Package pkg, final int policyFlags, 17558 int scanFlags, UserHandle user, String installerPackageName, String volumeUuid, 17559 PackageInstalledInfo res, int installReason) { 17560 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "installNewPackage"); 17561 17562 // Remember this for later, in case we need to rollback this install 17563 String pkgName = pkg.packageName; 17564 17565 if (DEBUG_INSTALL) Slog.d(TAG, "installNewPackageLI: " + pkg); 17566 17567 synchronized(mPackages) { 17568 final String renamedPackage = mSettings.getRenamedPackageLPr(pkgName); 17569 if (renamedPackage != null) { 17570 // A package with the same name is already installed, though 17571 // it has been renamed to an older name. The package we 17572 // are trying to install should be installed as an update to 17573 // the existing one, but that has not been requested, so bail. 17574 res.setError(INSTALL_FAILED_ALREADY_EXISTS, "Attempt to re-install " + pkgName 17575 + " without first uninstalling package running as " 17576 + renamedPackage); 17577 return; 17578 } 17579 if (mPackages.containsKey(pkgName)) { 17580 // Don't allow installation over an existing package with the same name. 17581 res.setError(INSTALL_FAILED_ALREADY_EXISTS, "Attempt to re-install " + pkgName 17582 + " without first uninstalling."); 17583 return; 17584 } 17585 } 17586 17587 try { 17588 PackageParser.Package newPackage = scanPackageTracedLI(pkg, policyFlags, scanFlags, 17589 System.currentTimeMillis(), user); 17590 17591 updateSettingsLI(newPackage, installerPackageName, null, res, user, installReason); 17592 17593 if (res.returnCode == PackageManager.INSTALL_SUCCEEDED) { 17594 prepareAppDataAfterInstallLIF(newPackage); 17595 17596 } else { 17597 // Remove package from internal structures, but keep around any 17598 // data that might have already existed 17599 deletePackageLIF(pkgName, UserHandle.ALL, false, null, 17600 PackageManager.DELETE_KEEP_DATA, res.removedInfo, true, null); 17601 } 17602 } catch (PackageManagerException e) { 17603 res.setError("Package couldn't be installed in " + pkg.codePath, e); 17604 } 17605 17606 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 17607 } 17608 17609 private boolean shouldCheckUpgradeKeySetLP(PackageSetting oldPs, int scanFlags) { 17610 // Can't rotate keys during boot or if sharedUser. 17611 if (oldPs == null || (scanFlags&SCAN_INITIAL) != 0 || oldPs.sharedUser != null 17612 || !oldPs.keySetData.isUsingUpgradeKeySets()) { 17613 return false; 17614 } 17615 // app is using upgradeKeySets; make sure all are valid 17616 KeySetManagerService ksms = mSettings.mKeySetManagerService; 17617 long[] upgradeKeySets = oldPs.keySetData.getUpgradeKeySets(); 17618 for (int i = 0; i < upgradeKeySets.length; i++) { 17619 if (!ksms.isIdValidKeySetId(upgradeKeySets[i])) { 17620 Slog.wtf(TAG, "Package " 17621 + (oldPs.name != null ? oldPs.name : "<null>") 17622 + " contains upgrade-key-set reference to unknown key-set: " 17623 + upgradeKeySets[i] 17624 + " reverting to signatures check."); 17625 return false; 17626 } 17627 } 17628 return true; 17629 } 17630 17631 private boolean checkUpgradeKeySetLP(PackageSetting oldPS, PackageParser.Package newPkg) { 17632 // Upgrade keysets are being used. Determine if new package has a superset of the 17633 // required keys. 17634 long[] upgradeKeySets = oldPS.keySetData.getUpgradeKeySets(); 17635 KeySetManagerService ksms = mSettings.mKeySetManagerService; 17636 for (int i = 0; i < upgradeKeySets.length; i++) { 17637 Set<PublicKey> upgradeSet = ksms.getPublicKeysFromKeySetLPr(upgradeKeySets[i]); 17638 if (upgradeSet != null && newPkg.mSigningKeys.containsAll(upgradeSet)) { 17639 return true; 17640 } 17641 } 17642 return false; 17643 } 17644 17645 private static void updateDigest(MessageDigest digest, File file) throws IOException { 17646 try (DigestInputStream digestStream = 17647 new DigestInputStream(new FileInputStream(file), digest)) { 17648 while (digestStream.read() != -1) {} // nothing to do; just plow through the file 17649 } 17650 } 17651 17652 private void replacePackageLIF(PackageParser.Package pkg, final int policyFlags, int scanFlags, 17653 UserHandle user, String installerPackageName, PackageInstalledInfo res, 17654 int installReason) { 17655 final boolean isInstantApp = (scanFlags & SCAN_AS_INSTANT_APP) != 0; 17656 17657 final PackageParser.Package oldPackage; 17658 final PackageSetting ps; 17659 final String pkgName = pkg.packageName; 17660 final int[] allUsers; 17661 final int[] installedUsers; 17662 17663 synchronized(mPackages) { 17664 oldPackage = mPackages.get(pkgName); 17665 if (DEBUG_INSTALL) Slog.d(TAG, "replacePackageLI: new=" + pkg + ", old=" + oldPackage); 17666 17667 // don't allow upgrade to target a release SDK from a pre-release SDK 17668 final boolean oldTargetsPreRelease = oldPackage.applicationInfo.targetSdkVersion 17669 == android.os.Build.VERSION_CODES.CUR_DEVELOPMENT; 17670 final boolean newTargetsPreRelease = pkg.applicationInfo.targetSdkVersion 17671 == android.os.Build.VERSION_CODES.CUR_DEVELOPMENT; 17672 if (oldTargetsPreRelease 17673 && !newTargetsPreRelease 17674 && ((policyFlags & PackageParser.PARSE_FORCE_SDK) == 0)) { 17675 Slog.w(TAG, "Can't install package targeting released sdk"); 17676 res.setReturnCode(PackageManager.INSTALL_FAILED_UPDATE_INCOMPATIBLE); 17677 return; 17678 } 17679 17680 ps = mSettings.mPackages.get(pkgName); 17681 17682 // verify signatures are valid 17683 if (shouldCheckUpgradeKeySetLP(ps, scanFlags)) { 17684 if (!checkUpgradeKeySetLP(ps, pkg)) { 17685 res.setError(INSTALL_FAILED_UPDATE_INCOMPATIBLE, 17686 "New package not signed by keys specified by upgrade-keysets: " 17687 + pkgName); 17688 return; 17689 } 17690 } else { 17691 // default to original signature matching 17692 if (compareSignatures(oldPackage.mSignatures, pkg.mSignatures) 17693 != PackageManager.SIGNATURE_MATCH) { 17694 res.setError(INSTALL_FAILED_UPDATE_INCOMPATIBLE, 17695 "New package has a different signature: " + pkgName); 17696 return; 17697 } 17698 } 17699 17700 // don't allow a system upgrade unless the upgrade hash matches 17701 if (oldPackage.restrictUpdateHash != null && oldPackage.isSystemApp()) { 17702 byte[] digestBytes = null; 17703 try { 17704 final MessageDigest digest = MessageDigest.getInstance("SHA-512"); 17705 updateDigest(digest, new File(pkg.baseCodePath)); 17706 if (!ArrayUtils.isEmpty(pkg.splitCodePaths)) { 17707 for (String path : pkg.splitCodePaths) { 17708 updateDigest(digest, new File(path)); 17709 } 17710 } 17711 digestBytes = digest.digest(); 17712 } catch (NoSuchAlgorithmException | IOException e) { 17713 res.setError(INSTALL_FAILED_INVALID_APK, 17714 "Could not compute hash: " + pkgName); 17715 return; 17716 } 17717 if (!Arrays.equals(oldPackage.restrictUpdateHash, digestBytes)) { 17718 res.setError(INSTALL_FAILED_INVALID_APK, 17719 "New package fails restrict-update check: " + pkgName); 17720 return; 17721 } 17722 // retain upgrade restriction 17723 pkg.restrictUpdateHash = oldPackage.restrictUpdateHash; 17724 } 17725 17726 // Check for shared user id changes 17727 String invalidPackageName = 17728 getParentOrChildPackageChangedSharedUser(oldPackage, pkg); 17729 if (invalidPackageName != null) { 17730 res.setError(INSTALL_FAILED_SHARED_USER_INCOMPATIBLE, 17731 "Package " + invalidPackageName + " tried to change user " 17732 + oldPackage.mSharedUserId); 17733 return; 17734 } 17735 17736 // In case of rollback, remember per-user/profile install state 17737 allUsers = sUserManager.getUserIds(); 17738 installedUsers = ps.queryInstalledUsers(allUsers, true); 17739 17740 // don't allow an upgrade from full to ephemeral 17741 if (isInstantApp) { 17742 if (user == null || user.getIdentifier() == UserHandle.USER_ALL) { 17743 for (int currentUser : allUsers) { 17744 if (!ps.getInstantApp(currentUser)) { 17745 // can't downgrade from full to instant 17746 Slog.w(TAG, "Can't replace full app with instant app: " + pkgName 17747 + " for user: " + currentUser); 17748 res.setReturnCode(PackageManager.INSTALL_FAILED_INSTANT_APP_INVALID); 17749 return; 17750 } 17751 } 17752 } else if (!ps.getInstantApp(user.getIdentifier())) { 17753 // can't downgrade from full to instant 17754 Slog.w(TAG, "Can't replace full app with instant app: " + pkgName 17755 + " for user: " + user.getIdentifier()); 17756 res.setReturnCode(PackageManager.INSTALL_FAILED_INSTANT_APP_INVALID); 17757 return; 17758 } 17759 } 17760 } 17761 17762 // Update what is removed 17763 res.removedInfo = new PackageRemovedInfo(this); 17764 res.removedInfo.uid = oldPackage.applicationInfo.uid; 17765 res.removedInfo.removedPackage = oldPackage.packageName; 17766 res.removedInfo.installerPackageName = ps.installerPackageName; 17767 res.removedInfo.isStaticSharedLib = pkg.staticSharedLibName != null; 17768 res.removedInfo.isUpdate = true; 17769 res.removedInfo.origUsers = installedUsers; 17770 res.removedInfo.installReasons = new SparseArray<>(installedUsers.length); 17771 for (int i = 0; i < installedUsers.length; i++) { 17772 final int userId = installedUsers[i]; 17773 res.removedInfo.installReasons.put(userId, ps.getInstallReason(userId)); 17774 } 17775 17776 final int childCount = (oldPackage.childPackages != null) 17777 ? oldPackage.childPackages.size() : 0; 17778 for (int i = 0; i < childCount; i++) { 17779 boolean childPackageUpdated = false; 17780 PackageParser.Package childPkg = oldPackage.childPackages.get(i); 17781 final PackageSetting childPs = mSettings.getPackageLPr(childPkg.packageName); 17782 if (res.addedChildPackages != null) { 17783 PackageInstalledInfo childRes = res.addedChildPackages.get(childPkg.packageName); 17784 if (childRes != null) { 17785 childRes.removedInfo.uid = childPkg.applicationInfo.uid; 17786 childRes.removedInfo.removedPackage = childPkg.packageName; 17787 if (childPs != null) { 17788 childRes.removedInfo.installerPackageName = childPs.installerPackageName; 17789 } 17790 childRes.removedInfo.isUpdate = true; 17791 childRes.removedInfo.installReasons = res.removedInfo.installReasons; 17792 childPackageUpdated = true; 17793 } 17794 } 17795 if (!childPackageUpdated) { 17796 PackageRemovedInfo childRemovedRes = new PackageRemovedInfo(this); 17797 childRemovedRes.removedPackage = childPkg.packageName; 17798 if (childPs != null) { 17799 childRemovedRes.installerPackageName = childPs.installerPackageName; 17800 } 17801 childRemovedRes.isUpdate = false; 17802 childRemovedRes.dataRemoved = true; 17803 synchronized (mPackages) { 17804 if (childPs != null) { 17805 childRemovedRes.origUsers = childPs.queryInstalledUsers(allUsers, true); 17806 } 17807 } 17808 if (res.removedInfo.removedChildPackages == null) { 17809 res.removedInfo.removedChildPackages = new ArrayMap<>(); 17810 } 17811 res.removedInfo.removedChildPackages.put(childPkg.packageName, childRemovedRes); 17812 } 17813 } 17814 17815 boolean sysPkg = (isSystemApp(oldPackage)); 17816 if (sysPkg) { 17817 // Set the system/privileged flags as needed 17818 final boolean privileged = 17819 (oldPackage.applicationInfo.privateFlags 17820 & ApplicationInfo.PRIVATE_FLAG_PRIVILEGED) != 0; 17821 final int systemPolicyFlags = policyFlags 17822 | PackageParser.PARSE_IS_SYSTEM 17823 | (privileged ? PackageParser.PARSE_IS_PRIVILEGED : 0); 17824 17825 replaceSystemPackageLIF(oldPackage, pkg, systemPolicyFlags, scanFlags, 17826 user, allUsers, installerPackageName, res, installReason); 17827 } else { 17828 replaceNonSystemPackageLIF(oldPackage, pkg, policyFlags, scanFlags, 17829 user, allUsers, installerPackageName, res, installReason); 17830 } 17831 } 17832 17833 @Override 17834 public List<String> getPreviousCodePaths(String packageName) { 17835 final int callingUid = Binder.getCallingUid(); 17836 final List<String> result = new ArrayList<>(); 17837 if (getInstantAppPackageName(callingUid) != null) { 17838 return result; 17839 } 17840 final PackageSetting ps = mSettings.mPackages.get(packageName); 17841 if (ps != null 17842 && ps.oldCodePaths != null 17843 && !filterAppAccessLPr(ps, callingUid, UserHandle.getUserId(callingUid))) { 17844 result.addAll(ps.oldCodePaths); 17845 } 17846 return result; 17847 } 17848 17849 private void replaceNonSystemPackageLIF(PackageParser.Package deletedPackage, 17850 PackageParser.Package pkg, final int policyFlags, int scanFlags, UserHandle user, 17851 int[] allUsers, String installerPackageName, PackageInstalledInfo res, 17852 int installReason) { 17853 if (DEBUG_INSTALL) Slog.d(TAG, "replaceNonSystemPackageLI: new=" + pkg + ", old=" 17854 + deletedPackage); 17855 17856 String pkgName = deletedPackage.packageName; 17857 boolean deletedPkg = true; 17858 boolean addedPkg = false; 17859 boolean updatedSettings = false; 17860 final boolean killApp = (scanFlags & SCAN_DONT_KILL_APP) == 0; 17861 final int deleteFlags = PackageManager.DELETE_KEEP_DATA 17862 | (killApp ? 0 : PackageManager.DELETE_DONT_KILL_APP); 17863 17864 final long origUpdateTime = (pkg.mExtras != null) 17865 ? ((PackageSetting)pkg.mExtras).lastUpdateTime : 0; 17866 17867 // First delete the existing package while retaining the data directory 17868 if (!deletePackageLIF(pkgName, null, true, allUsers, deleteFlags, 17869 res.removedInfo, true, pkg)) { 17870 // If the existing package wasn't successfully deleted 17871 res.setError(INSTALL_FAILED_REPLACE_COULDNT_DELETE, "replaceNonSystemPackageLI"); 17872 deletedPkg = false; 17873 } else { 17874 // Successfully deleted the old package; proceed with replace. 17875 17876 // If deleted package lived in a container, give users a chance to 17877 // relinquish resources before killing. 17878 if (deletedPackage.isForwardLocked() || isExternal(deletedPackage)) { 17879 if (DEBUG_INSTALL) { 17880 Slog.i(TAG, "upgrading pkg " + deletedPackage + " is ASEC-hosted -> UNAVAILABLE"); 17881 } 17882 final int[] uidArray = new int[] { deletedPackage.applicationInfo.uid }; 17883 final ArrayList<String> pkgList = new ArrayList<String>(1); 17884 pkgList.add(deletedPackage.applicationInfo.packageName); 17885 sendResourcesChangedBroadcast(false, true, pkgList, uidArray, null); 17886 } 17887 17888 clearAppDataLIF(pkg, UserHandle.USER_ALL, StorageManager.FLAG_STORAGE_DE 17889 | StorageManager.FLAG_STORAGE_CE | Installer.FLAG_CLEAR_CODE_CACHE_ONLY); 17890 clearAppProfilesLIF(deletedPackage, UserHandle.USER_ALL); 17891 17892 try { 17893 final PackageParser.Package newPackage = scanPackageTracedLI(pkg, policyFlags, 17894 scanFlags | SCAN_UPDATE_TIME, System.currentTimeMillis(), user); 17895 updateSettingsLI(newPackage, installerPackageName, allUsers, res, user, 17896 installReason); 17897 17898 // Update the in-memory copy of the previous code paths. 17899 PackageSetting ps = mSettings.mPackages.get(pkgName); 17900 if (!killApp) { 17901 if (ps.oldCodePaths == null) { 17902 ps.oldCodePaths = new ArraySet<>(); 17903 } 17904 Collections.addAll(ps.oldCodePaths, deletedPackage.baseCodePath); 17905 if (deletedPackage.splitCodePaths != null) { 17906 Collections.addAll(ps.oldCodePaths, deletedPackage.splitCodePaths); 17907 } 17908 } else { 17909 ps.oldCodePaths = null; 17910 } 17911 if (ps.childPackageNames != null) { 17912 for (int i = ps.childPackageNames.size() - 1; i >= 0; --i) { 17913 final String childPkgName = ps.childPackageNames.get(i); 17914 final PackageSetting childPs = mSettings.mPackages.get(childPkgName); 17915 childPs.oldCodePaths = ps.oldCodePaths; 17916 } 17917 } 17918 // set instant app status, but, only if it's explicitly specified 17919 final boolean instantApp = (scanFlags & SCAN_AS_INSTANT_APP) != 0; 17920 final boolean fullApp = (scanFlags & SCAN_AS_FULL_APP) != 0; 17921 setInstantAppForUser(ps, user.getIdentifier(), instantApp, fullApp); 17922 prepareAppDataAfterInstallLIF(newPackage); 17923 addedPkg = true; 17924 mDexManager.notifyPackageUpdated(newPackage.packageName, 17925 newPackage.baseCodePath, newPackage.splitCodePaths); 17926 } catch (PackageManagerException e) { 17927 res.setError("Package couldn't be installed in " + pkg.codePath, e); 17928 } 17929 } 17930 17931 if (res.returnCode != PackageManager.INSTALL_SUCCEEDED) { 17932 if (DEBUG_INSTALL) Slog.d(TAG, "Install failed, rolling pack: " + pkgName); 17933 17934 // Revert all internal state mutations and added folders for the failed install 17935 if (addedPkg) { 17936 deletePackageLIF(pkgName, null, true, allUsers, deleteFlags, 17937 res.removedInfo, true, null); 17938 } 17939 17940 // Restore the old package 17941 if (deletedPkg) { 17942 if (DEBUG_INSTALL) Slog.d(TAG, "Install failed, reinstalling: " + deletedPackage); 17943 File restoreFile = new File(deletedPackage.codePath); 17944 // Parse old package 17945 boolean oldExternal = isExternal(deletedPackage); 17946 int oldParseFlags = mDefParseFlags | PackageParser.PARSE_CHATTY | 17947 (deletedPackage.isForwardLocked() ? PackageParser.PARSE_FORWARD_LOCK : 0) | 17948 (oldExternal ? PackageParser.PARSE_EXTERNAL_STORAGE : 0); 17949 int oldScanFlags = SCAN_UPDATE_SIGNATURE | SCAN_UPDATE_TIME; 17950 try { 17951 scanPackageTracedLI(restoreFile, oldParseFlags, oldScanFlags, origUpdateTime, 17952 null); 17953 } catch (PackageManagerException e) { 17954 Slog.e(TAG, "Failed to restore package : " + pkgName + " after failed upgrade: " 17955 + e.getMessage()); 17956 return; 17957 } 17958 17959 synchronized (mPackages) { 17960 // Ensure the installer package name up to date 17961 setInstallerPackageNameLPw(deletedPackage, installerPackageName); 17962 17963 // Update permissions for restored package 17964 updatePermissionsLPw(deletedPackage, UPDATE_PERMISSIONS_ALL); 17965 17966 mSettings.writeLPr(); 17967 } 17968 17969 Slog.i(TAG, "Successfully restored package : " + pkgName + " after failed upgrade"); 17970 } 17971 } else { 17972 synchronized (mPackages) { 17973 PackageSetting ps = mSettings.getPackageLPr(pkg.packageName); 17974 if (ps != null) { 17975 res.removedInfo.removedForAllUsers = mPackages.get(ps.name) == null; 17976 if (res.removedInfo.removedChildPackages != null) { 17977 final int childCount = res.removedInfo.removedChildPackages.size(); 17978 // Iterate in reverse as we may modify the collection 17979 for (int i = childCount - 1; i >= 0; i--) { 17980 String childPackageName = res.removedInfo.removedChildPackages.keyAt(i); 17981 if (res.addedChildPackages.containsKey(childPackageName)) { 17982 res.removedInfo.removedChildPackages.removeAt(i); 17983 } else { 17984 PackageRemovedInfo childInfo = res.removedInfo 17985 .removedChildPackages.valueAt(i); 17986 childInfo.removedForAllUsers = mPackages.get( 17987 childInfo.removedPackage) == null; 17988 } 17989 } 17990 } 17991 } 17992 } 17993 } 17994 } 17995 17996 private void replaceSystemPackageLIF(PackageParser.Package deletedPackage, 17997 PackageParser.Package pkg, final int policyFlags, int scanFlags, UserHandle user, 17998 int[] allUsers, String installerPackageName, PackageInstalledInfo res, 17999 int installReason) { 18000 if (DEBUG_INSTALL) Slog.d(TAG, "replaceSystemPackageLI: new=" + pkg 18001 + ", old=" + deletedPackage); 18002 18003 final boolean disabledSystem; 18004 18005 // Remove existing system package 18006 removePackageLI(deletedPackage, true); 18007 18008 synchronized (mPackages) { 18009 disabledSystem = disableSystemPackageLPw(deletedPackage, pkg); 18010 } 18011 if (!disabledSystem) { 18012 // We didn't need to disable the .apk as a current system package, 18013 // which means we are replacing another update that is already 18014 // installed. We need to make sure to delete the older one's .apk. 18015 res.removedInfo.args = createInstallArgsForExisting(0, 18016 deletedPackage.applicationInfo.getCodePath(), 18017 deletedPackage.applicationInfo.getResourcePath(), 18018 getAppDexInstructionSets(deletedPackage.applicationInfo)); 18019 } else { 18020 res.removedInfo.args = null; 18021 } 18022 18023 // Successfully disabled the old package. Now proceed with re-installation 18024 clearAppDataLIF(pkg, UserHandle.USER_ALL, StorageManager.FLAG_STORAGE_DE 18025 | StorageManager.FLAG_STORAGE_CE | Installer.FLAG_CLEAR_CODE_CACHE_ONLY); 18026 clearAppProfilesLIF(deletedPackage, UserHandle.USER_ALL); 18027 18028 res.setReturnCode(PackageManager.INSTALL_SUCCEEDED); 18029 pkg.setApplicationInfoFlags(ApplicationInfo.FLAG_UPDATED_SYSTEM_APP, 18030 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP); 18031 18032 PackageParser.Package newPackage = null; 18033 try { 18034 // Add the package to the internal data structures 18035 newPackage = scanPackageTracedLI(pkg, policyFlags, scanFlags, 0, user); 18036 18037 // Set the update and install times 18038 PackageSetting deletedPkgSetting = (PackageSetting) deletedPackage.mExtras; 18039 setInstallAndUpdateTime(newPackage, deletedPkgSetting.firstInstallTime, 18040 System.currentTimeMillis()); 18041 18042 // Update the package dynamic state if succeeded 18043 if (res.returnCode == PackageManager.INSTALL_SUCCEEDED) { 18044 // Now that the install succeeded make sure we remove data 18045 // directories for any child package the update removed. 18046 final int deletedChildCount = (deletedPackage.childPackages != null) 18047 ? deletedPackage.childPackages.size() : 0; 18048 final int newChildCount = (newPackage.childPackages != null) 18049 ? newPackage.childPackages.size() : 0; 18050 for (int i = 0; i < deletedChildCount; i++) { 18051 PackageParser.Package deletedChildPkg = deletedPackage.childPackages.get(i); 18052 boolean childPackageDeleted = true; 18053 for (int j = 0; j < newChildCount; j++) { 18054 PackageParser.Package newChildPkg = newPackage.childPackages.get(j); 18055 if (deletedChildPkg.packageName.equals(newChildPkg.packageName)) { 18056 childPackageDeleted = false; 18057 break; 18058 } 18059 } 18060 if (childPackageDeleted) { 18061 PackageSetting ps = mSettings.getDisabledSystemPkgLPr( 18062 deletedChildPkg.packageName); 18063 if (ps != null && res.removedInfo.removedChildPackages != null) { 18064 PackageRemovedInfo removedChildRes = res.removedInfo 18065 .removedChildPackages.get(deletedChildPkg.packageName); 18066 removePackageDataLIF(ps, allUsers, removedChildRes, 0, false); 18067 removedChildRes.removedForAllUsers = mPackages.get(ps.name) == null; 18068 } 18069 } 18070 } 18071 18072 updateSettingsLI(newPackage, installerPackageName, allUsers, res, user, 18073 installReason); 18074 prepareAppDataAfterInstallLIF(newPackage); 18075 18076 mDexManager.notifyPackageUpdated(newPackage.packageName, 18077 newPackage.baseCodePath, newPackage.splitCodePaths); 18078 } 18079 } catch (PackageManagerException e) { 18080 res.setReturnCode(INSTALL_FAILED_INTERNAL_ERROR); 18081 res.setError("Package couldn't be installed in " + pkg.codePath, e); 18082 } 18083 18084 if (res.returnCode != PackageManager.INSTALL_SUCCEEDED) { 18085 // Re installation failed. Restore old information 18086 // Remove new pkg information 18087 if (newPackage != null) { 18088 removeInstalledPackageLI(newPackage, true); 18089 } 18090 // Add back the old system package 18091 try { 18092 scanPackageTracedLI(deletedPackage, policyFlags, SCAN_UPDATE_SIGNATURE, 0, user); 18093 } catch (PackageManagerException e) { 18094 Slog.e(TAG, "Failed to restore original package: " + e.getMessage()); 18095 } 18096 18097 synchronized (mPackages) { 18098 if (disabledSystem) { 18099 enableSystemPackageLPw(deletedPackage); 18100 } 18101 18102 // Ensure the installer package name up to date 18103 setInstallerPackageNameLPw(deletedPackage, installerPackageName); 18104 18105 // Update permissions for restored package 18106 updatePermissionsLPw(deletedPackage, UPDATE_PERMISSIONS_ALL); 18107 18108 mSettings.writeLPr(); 18109 } 18110 18111 Slog.i(TAG, "Successfully restored package : " + deletedPackage.packageName 18112 + " after failed upgrade"); 18113 } 18114 } 18115 18116 /** 18117 * Checks whether the parent or any of the child packages have a change shared 18118 * user. For a package to be a valid update the shred users of the parent and 18119 * the children should match. We may later support changing child shared users. 18120 * @param oldPkg The updated package. 18121 * @param newPkg The update package. 18122 * @return The shared user that change between the versions. 18123 */ 18124 private String getParentOrChildPackageChangedSharedUser(PackageParser.Package oldPkg, 18125 PackageParser.Package newPkg) { 18126 // Check parent shared user 18127 if (!Objects.equals(oldPkg.mSharedUserId, newPkg.mSharedUserId)) { 18128 return newPkg.packageName; 18129 } 18130 // Check child shared users 18131 final int oldChildCount = (oldPkg.childPackages != null) ? oldPkg.childPackages.size() : 0; 18132 final int newChildCount = (newPkg.childPackages != null) ? newPkg.childPackages.size() : 0; 18133 for (int i = 0; i < newChildCount; i++) { 18134 PackageParser.Package newChildPkg = newPkg.childPackages.get(i); 18135 // If this child was present, did it have the same shared user? 18136 for (int j = 0; j < oldChildCount; j++) { 18137 PackageParser.Package oldChildPkg = oldPkg.childPackages.get(j); 18138 if (newChildPkg.packageName.equals(oldChildPkg.packageName) 18139 && !Objects.equals(newChildPkg.mSharedUserId, oldChildPkg.mSharedUserId)) { 18140 return newChildPkg.packageName; 18141 } 18142 } 18143 } 18144 return null; 18145 } 18146 18147 private void removeNativeBinariesLI(PackageSetting ps) { 18148 // Remove the lib path for the parent package 18149 if (ps != null) { 18150 NativeLibraryHelper.removeNativeBinariesLI(ps.legacyNativeLibraryPathString); 18151 // Remove the lib path for the child packages 18152 final int childCount = (ps.childPackageNames != null) ? ps.childPackageNames.size() : 0; 18153 for (int i = 0; i < childCount; i++) { 18154 PackageSetting childPs = null; 18155 synchronized (mPackages) { 18156 childPs = mSettings.getPackageLPr(ps.childPackageNames.get(i)); 18157 } 18158 if (childPs != null) { 18159 NativeLibraryHelper.removeNativeBinariesLI(childPs 18160 .legacyNativeLibraryPathString); 18161 } 18162 } 18163 } 18164 } 18165 18166 private void enableSystemPackageLPw(PackageParser.Package pkg) { 18167 // Enable the parent package 18168 mSettings.enableSystemPackageLPw(pkg.packageName); 18169 // Enable the child packages 18170 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 18171 for (int i = 0; i < childCount; i++) { 18172 PackageParser.Package childPkg = pkg.childPackages.get(i); 18173 mSettings.enableSystemPackageLPw(childPkg.packageName); 18174 } 18175 } 18176 18177 private boolean disableSystemPackageLPw(PackageParser.Package oldPkg, 18178 PackageParser.Package newPkg) { 18179 // Disable the parent package (parent always replaced) 18180 boolean disabled = mSettings.disableSystemPackageLPw(oldPkg.packageName, true); 18181 // Disable the child packages 18182 final int childCount = (oldPkg.childPackages != null) ? oldPkg.childPackages.size() : 0; 18183 for (int i = 0; i < childCount; i++) { 18184 PackageParser.Package childPkg = oldPkg.childPackages.get(i); 18185 final boolean replace = newPkg.hasChildPackage(childPkg.packageName); 18186 disabled |= mSettings.disableSystemPackageLPw(childPkg.packageName, replace); 18187 } 18188 return disabled; 18189 } 18190 18191 private void setInstallerPackageNameLPw(PackageParser.Package pkg, 18192 String installerPackageName) { 18193 // Enable the parent package 18194 mSettings.setInstallerPackageName(pkg.packageName, installerPackageName); 18195 // Enable the child packages 18196 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 18197 for (int i = 0; i < childCount; i++) { 18198 PackageParser.Package childPkg = pkg.childPackages.get(i); 18199 mSettings.setInstallerPackageName(childPkg.packageName, installerPackageName); 18200 } 18201 } 18202 18203 private int[] revokeUnusedSharedUserPermissionsLPw(SharedUserSetting su, int[] allUserIds) { 18204 // Collect all used permissions in the UID 18205 ArraySet<String> usedPermissions = new ArraySet<>(); 18206 final int packageCount = su.packages.size(); 18207 for (int i = 0; i < packageCount; i++) { 18208 PackageSetting ps = su.packages.valueAt(i); 18209 if (ps.pkg == null) { 18210 continue; 18211 } 18212 final int requestedPermCount = ps.pkg.requestedPermissions.size(); 18213 for (int j = 0; j < requestedPermCount; j++) { 18214 String permission = ps.pkg.requestedPermissions.get(j); 18215 BasePermission bp = mSettings.mPermissions.get(permission); 18216 if (bp != null) { 18217 usedPermissions.add(permission); 18218 } 18219 } 18220 } 18221 18222 PermissionsState permissionsState = su.getPermissionsState(); 18223 // Prune install permissions 18224 List<PermissionState> installPermStates = permissionsState.getInstallPermissionStates(); 18225 final int installPermCount = installPermStates.size(); 18226 for (int i = installPermCount - 1; i >= 0; i--) { 18227 PermissionState permissionState = installPermStates.get(i); 18228 if (!usedPermissions.contains(permissionState.getName())) { 18229 BasePermission bp = mSettings.mPermissions.get(permissionState.getName()); 18230 if (bp != null) { 18231 permissionsState.revokeInstallPermission(bp); 18232 permissionsState.updatePermissionFlags(bp, UserHandle.USER_ALL, 18233 PackageManager.MASK_PERMISSION_FLAGS, 0); 18234 } 18235 } 18236 } 18237 18238 int[] runtimePermissionChangedUserIds = EmptyArray.INT; 18239 18240 // Prune runtime permissions 18241 for (int userId : allUserIds) { 18242 List<PermissionState> runtimePermStates = permissionsState 18243 .getRuntimePermissionStates(userId); 18244 final int runtimePermCount = runtimePermStates.size(); 18245 for (int i = runtimePermCount - 1; i >= 0; i--) { 18246 PermissionState permissionState = runtimePermStates.get(i); 18247 if (!usedPermissions.contains(permissionState.getName())) { 18248 BasePermission bp = mSettings.mPermissions.get(permissionState.getName()); 18249 if (bp != null) { 18250 permissionsState.revokeRuntimePermission(bp, userId); 18251 permissionsState.updatePermissionFlags(bp, userId, 18252 PackageManager.MASK_PERMISSION_FLAGS, 0); 18253 runtimePermissionChangedUserIds = ArrayUtils.appendInt( 18254 runtimePermissionChangedUserIds, userId); 18255 } 18256 } 18257 } 18258 } 18259 18260 return runtimePermissionChangedUserIds; 18261 } 18262 18263 private void updateSettingsLI(PackageParser.Package newPackage, String installerPackageName, 18264 int[] allUsers, PackageInstalledInfo res, UserHandle user, int installReason) { 18265 // Update the parent package setting 18266 updateSettingsInternalLI(newPackage, installerPackageName, allUsers, res.origUsers, 18267 res, user, installReason); 18268 // Update the child packages setting 18269 final int childCount = (newPackage.childPackages != null) 18270 ? newPackage.childPackages.size() : 0; 18271 for (int i = 0; i < childCount; i++) { 18272 PackageParser.Package childPackage = newPackage.childPackages.get(i); 18273 PackageInstalledInfo childRes = res.addedChildPackages.get(childPackage.packageName); 18274 updateSettingsInternalLI(childPackage, installerPackageName, allUsers, 18275 childRes.origUsers, childRes, user, installReason); 18276 } 18277 } 18278 18279 private void updateSettingsInternalLI(PackageParser.Package newPackage, 18280 String installerPackageName, int[] allUsers, int[] installedForUsers, 18281 PackageInstalledInfo res, UserHandle user, int installReason) { 18282 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "updateSettings"); 18283 18284 String pkgName = newPackage.packageName; 18285 synchronized (mPackages) { 18286 //write settings. the installStatus will be incomplete at this stage. 18287 //note that the new package setting would have already been 18288 //added to mPackages. It hasn't been persisted yet. 18289 mSettings.setInstallStatus(pkgName, PackageSettingBase.PKG_INSTALL_INCOMPLETE); 18290 // TODO: Remove this write? It's also written at the end of this method 18291 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "writeSettings"); 18292 mSettings.writeLPr(); 18293 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 18294 } 18295 18296 if (DEBUG_INSTALL) Slog.d(TAG, "New package installed in " + newPackage.codePath); 18297 synchronized (mPackages) { 18298 updatePermissionsLPw(newPackage.packageName, newPackage, 18299 UPDATE_PERMISSIONS_REPLACE_PKG | (newPackage.permissions.size() > 0 18300 ? UPDATE_PERMISSIONS_ALL : 0)); 18301 // For system-bundled packages, we assume that installing an upgraded version 18302 // of the package implies that the user actually wants to run that new code, 18303 // so we enable the package. 18304 PackageSetting ps = mSettings.mPackages.get(pkgName); 18305 final int userId = user.getIdentifier(); 18306 if (ps != null) { 18307 if (isSystemApp(newPackage)) { 18308 if (DEBUG_INSTALL) { 18309 Slog.d(TAG, "Implicitly enabling system package on upgrade: " + pkgName); 18310 } 18311 // Enable system package for requested users 18312 if (res.origUsers != null) { 18313 for (int origUserId : res.origUsers) { 18314 if (userId == UserHandle.USER_ALL || userId == origUserId) { 18315 ps.setEnabled(COMPONENT_ENABLED_STATE_DEFAULT, 18316 origUserId, installerPackageName); 18317 } 18318 } 18319 } 18320 // Also convey the prior install/uninstall state 18321 if (allUsers != null && installedForUsers != null) { 18322 for (int currentUserId : allUsers) { 18323 final boolean installed = ArrayUtils.contains( 18324 installedForUsers, currentUserId); 18325 if (DEBUG_INSTALL) { 18326 Slog.d(TAG, " user " + currentUserId + " => " + installed); 18327 } 18328 ps.setInstalled(installed, currentUserId); 18329 } 18330 // these install state changes will be persisted in the 18331 // upcoming call to mSettings.writeLPr(). 18332 } 18333 } 18334 // It's implied that when a user requests installation, they want the app to be 18335 // installed and enabled. 18336 if (userId != UserHandle.USER_ALL) { 18337 ps.setInstalled(true, userId); 18338 ps.setEnabled(COMPONENT_ENABLED_STATE_DEFAULT, userId, installerPackageName); 18339 } 18340 18341 // When replacing an existing package, preserve the original install reason for all 18342 // users that had the package installed before. 18343 final Set<Integer> previousUserIds = new ArraySet<>(); 18344 if (res.removedInfo != null && res.removedInfo.installReasons != null) { 18345 final int installReasonCount = res.removedInfo.installReasons.size(); 18346 for (int i = 0; i < installReasonCount; i++) { 18347 final int previousUserId = res.removedInfo.installReasons.keyAt(i); 18348 final int previousInstallReason = res.removedInfo.installReasons.valueAt(i); 18349 ps.setInstallReason(previousInstallReason, previousUserId); 18350 previousUserIds.add(previousUserId); 18351 } 18352 } 18353 18354 // Set install reason for users that are having the package newly installed. 18355 if (userId == UserHandle.USER_ALL) { 18356 for (int currentUserId : sUserManager.getUserIds()) { 18357 if (!previousUserIds.contains(currentUserId)) { 18358 ps.setInstallReason(installReason, currentUserId); 18359 } 18360 } 18361 } else if (!previousUserIds.contains(userId)) { 18362 ps.setInstallReason(installReason, userId); 18363 } 18364 mSettings.writeKernelMappingLPr(ps); 18365 } 18366 res.name = pkgName; 18367 res.uid = newPackage.applicationInfo.uid; 18368 res.pkg = newPackage; 18369 mSettings.setInstallStatus(pkgName, PackageSettingBase.PKG_INSTALL_COMPLETE); 18370 mSettings.setInstallerPackageName(pkgName, installerPackageName); 18371 res.setReturnCode(PackageManager.INSTALL_SUCCEEDED); 18372 //to update install status 18373 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "writeSettings"); 18374 mSettings.writeLPr(); 18375 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 18376 } 18377 18378 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 18379 } 18380 18381 private void installPackageTracedLI(InstallArgs args, PackageInstalledInfo res) { 18382 try { 18383 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "installPackage"); 18384 installPackageLI(args, res); 18385 } finally { 18386 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 18387 } 18388 } 18389 18390 private void installPackageLI(InstallArgs args, PackageInstalledInfo res) { 18391 final int installFlags = args.installFlags; 18392 final String installerPackageName = args.installerPackageName; 18393 final String volumeUuid = args.volumeUuid; 18394 final File tmpPackageFile = new File(args.getCodePath()); 18395 final boolean forwardLocked = ((installFlags & PackageManager.INSTALL_FORWARD_LOCK) != 0); 18396 final boolean onExternal = (((installFlags & PackageManager.INSTALL_EXTERNAL) != 0) 18397 || (args.volumeUuid != null)); 18398 final boolean instantApp = ((installFlags & PackageManager.INSTALL_INSTANT_APP) != 0); 18399 final boolean fullApp = ((installFlags & PackageManager.INSTALL_FULL_APP) != 0); 18400 final boolean forceSdk = ((installFlags & PackageManager.INSTALL_FORCE_SDK) != 0); 18401 final boolean virtualPreload = 18402 ((installFlags & PackageManager.INSTALL_VIRTUAL_PRELOAD) != 0); 18403 boolean replace = false; 18404 int scanFlags = SCAN_NEW_INSTALL | SCAN_UPDATE_SIGNATURE; 18405 if (args.move != null) { 18406 // moving a complete application; perform an initial scan on the new install location 18407 scanFlags |= SCAN_INITIAL; 18408 } 18409 if ((installFlags & PackageManager.INSTALL_DONT_KILL_APP) != 0) { 18410 scanFlags |= SCAN_DONT_KILL_APP; 18411 } 18412 if (instantApp) { 18413 scanFlags |= SCAN_AS_INSTANT_APP; 18414 } 18415 if (fullApp) { 18416 scanFlags |= SCAN_AS_FULL_APP; 18417 } 18418 if (virtualPreload) { 18419 scanFlags |= SCAN_AS_VIRTUAL_PRELOAD; 18420 } 18421 18422 // Result object to be returned 18423 res.setReturnCode(PackageManager.INSTALL_SUCCEEDED); 18424 res.installerPackageName = installerPackageName; 18425 18426 if (DEBUG_INSTALL) Slog.d(TAG, "installPackageLI: path=" + tmpPackageFile); 18427 18428 // Sanity check 18429 if (instantApp && (forwardLocked || onExternal)) { 18430 Slog.i(TAG, "Incompatible ephemeral install; fwdLocked=" + forwardLocked 18431 + " external=" + onExternal); 18432 res.setReturnCode(PackageManager.INSTALL_FAILED_INSTANT_APP_INVALID); 18433 return; 18434 } 18435 18436 // Retrieve PackageSettings and parse package 18437 final int parseFlags = mDefParseFlags | PackageParser.PARSE_CHATTY 18438 | PackageParser.PARSE_ENFORCE_CODE 18439 | (forwardLocked ? PackageParser.PARSE_FORWARD_LOCK : 0) 18440 | (onExternal ? PackageParser.PARSE_EXTERNAL_STORAGE : 0) 18441 | (instantApp ? PackageParser.PARSE_IS_EPHEMERAL : 0) 18442 | (forceSdk ? PackageParser.PARSE_FORCE_SDK : 0); 18443 PackageParser pp = new PackageParser(); 18444 pp.setSeparateProcesses(mSeparateProcesses); 18445 pp.setDisplayMetrics(mMetrics); 18446 pp.setCallback(mPackageParserCallback); 18447 18448 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "parsePackage"); 18449 final PackageParser.Package pkg; 18450 try { 18451 pkg = pp.parsePackage(tmpPackageFile, parseFlags); 18452 } catch (PackageParserException e) { 18453 res.setError("Failed parse during installPackageLI", e); 18454 return; 18455 } finally { 18456 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 18457 } 18458 18459 // Instant apps must have target SDK >= O and have targetSanboxVersion >= 2 18460 if (instantApp && pkg.applicationInfo.targetSdkVersion <= Build.VERSION_CODES.N_MR1) { 18461 Slog.w(TAG, "Instant app package " + pkg.packageName + " does not target O"); 18462 res.setError(INSTALL_FAILED_SANDBOX_VERSION_DOWNGRADE, 18463 "Instant app package must target O"); 18464 return; 18465 } 18466 if (instantApp && pkg.applicationInfo.targetSandboxVersion != 2) { 18467 Slog.w(TAG, "Instant app package " + pkg.packageName 18468 + " does not target targetSandboxVersion 2"); 18469 res.setError(INSTALL_FAILED_SANDBOX_VERSION_DOWNGRADE, 18470 "Instant app package must use targetSanboxVersion 2"); 18471 return; 18472 } 18473 18474 if (pkg.applicationInfo.isStaticSharedLibrary()) { 18475 // Static shared libraries have synthetic package names 18476 renameStaticSharedLibraryPackage(pkg); 18477 18478 // No static shared libs on external storage 18479 if (onExternal) { 18480 Slog.i(TAG, "Static shared libs can only be installed on internal storage."); 18481 res.setError(INSTALL_FAILED_INVALID_INSTALL_LOCATION, 18482 "Packages declaring static-shared libs cannot be updated"); 18483 return; 18484 } 18485 } 18486 18487 // If we are installing a clustered package add results for the children 18488 if (pkg.childPackages != null) { 18489 synchronized (mPackages) { 18490 final int childCount = pkg.childPackages.size(); 18491 for (int i = 0; i < childCount; i++) { 18492 PackageParser.Package childPkg = pkg.childPackages.get(i); 18493 PackageInstalledInfo childRes = new PackageInstalledInfo(); 18494 childRes.setReturnCode(PackageManager.INSTALL_SUCCEEDED); 18495 childRes.pkg = childPkg; 18496 childRes.name = childPkg.packageName; 18497 PackageSetting childPs = mSettings.getPackageLPr(childPkg.packageName); 18498 if (childPs != null) { 18499 childRes.origUsers = childPs.queryInstalledUsers( 18500 sUserManager.getUserIds(), true); 18501 } 18502 if ((mPackages.containsKey(childPkg.packageName))) { 18503 childRes.removedInfo = new PackageRemovedInfo(this); 18504 childRes.removedInfo.removedPackage = childPkg.packageName; 18505 childRes.removedInfo.installerPackageName = childPs.installerPackageName; 18506 } 18507 if (res.addedChildPackages == null) { 18508 res.addedChildPackages = new ArrayMap<>(); 18509 } 18510 res.addedChildPackages.put(childPkg.packageName, childRes); 18511 } 18512 } 18513 } 18514 18515 // If package doesn't declare API override, mark that we have an install 18516 // time CPU ABI override. 18517 if (TextUtils.isEmpty(pkg.cpuAbiOverride)) { 18518 pkg.cpuAbiOverride = args.abiOverride; 18519 } 18520 18521 String pkgName = res.name = pkg.packageName; 18522 if ((pkg.applicationInfo.flags&ApplicationInfo.FLAG_TEST_ONLY) != 0) { 18523 if ((installFlags & PackageManager.INSTALL_ALLOW_TEST) == 0) { 18524 res.setError(INSTALL_FAILED_TEST_ONLY, "installPackageLI"); 18525 return; 18526 } 18527 } 18528 18529 try { 18530 // either use what we've been given or parse directly from the APK 18531 if (args.certificates != null) { 18532 try { 18533 PackageParser.populateCertificates(pkg, args.certificates); 18534 } catch (PackageParserException e) { 18535 // there was something wrong with the certificates we were given; 18536 // try to pull them from the APK 18537 PackageParser.collectCertificates(pkg, parseFlags); 18538 } 18539 } else { 18540 PackageParser.collectCertificates(pkg, parseFlags); 18541 } 18542 } catch (PackageParserException e) { 18543 res.setError("Failed collect during installPackageLI", e); 18544 return; 18545 } 18546 18547 // Get rid of all references to package scan path via parser. 18548 pp = null; 18549 String oldCodePath = null; 18550 boolean systemApp = false; 18551 synchronized (mPackages) { 18552 // Check if installing already existing package 18553 if ((installFlags & PackageManager.INSTALL_REPLACE_EXISTING) != 0) { 18554 String oldName = mSettings.getRenamedPackageLPr(pkgName); 18555 if (pkg.mOriginalPackages != null 18556 && pkg.mOriginalPackages.contains(oldName) 18557 && mPackages.containsKey(oldName)) { 18558 // This package is derived from an original package, 18559 // and this device has been updating from that original 18560 // name. We must continue using the original name, so 18561 // rename the new package here. 18562 pkg.setPackageName(oldName); 18563 pkgName = pkg.packageName; 18564 replace = true; 18565 if (DEBUG_INSTALL) Slog.d(TAG, "Replacing existing renamed package: oldName=" 18566 + oldName + " pkgName=" + pkgName); 18567 } else if (mPackages.containsKey(pkgName)) { 18568 // This package, under its official name, already exists 18569 // on the device; we should replace it. 18570 replace = true; 18571 if (DEBUG_INSTALL) Slog.d(TAG, "Replace existing pacakge: " + pkgName); 18572 } 18573 18574 // Child packages are installed through the parent package 18575 if (pkg.parentPackage != null) { 18576 res.setError(PackageManager.INSTALL_PARSE_FAILED_BAD_PACKAGE_NAME, 18577 "Package " + pkg.packageName + " is child of package " 18578 + pkg.parentPackage.parentPackage + ". Child packages " 18579 + "can be updated only through the parent package."); 18580 return; 18581 } 18582 18583 if (replace) { 18584 // Prevent apps opting out from runtime permissions 18585 PackageParser.Package oldPackage = mPackages.get(pkgName); 18586 final int oldTargetSdk = oldPackage.applicationInfo.targetSdkVersion; 18587 final int newTargetSdk = pkg.applicationInfo.targetSdkVersion; 18588 if (oldTargetSdk > Build.VERSION_CODES.LOLLIPOP_MR1 18589 && newTargetSdk <= Build.VERSION_CODES.LOLLIPOP_MR1) { 18590 res.setError(PackageManager.INSTALL_FAILED_PERMISSION_MODEL_DOWNGRADE, 18591 "Package " + pkg.packageName + " new target SDK " + newTargetSdk 18592 + " doesn't support runtime permissions but the old" 18593 + " target SDK " + oldTargetSdk + " does."); 18594 return; 18595 } 18596 // Prevent apps from downgrading their targetSandbox. 18597 final int oldTargetSandbox = oldPackage.applicationInfo.targetSandboxVersion; 18598 final int newTargetSandbox = pkg.applicationInfo.targetSandboxVersion; 18599 if (oldTargetSandbox == 2 && newTargetSandbox != 2) { 18600 res.setError(PackageManager.INSTALL_FAILED_SANDBOX_VERSION_DOWNGRADE, 18601 "Package " + pkg.packageName + " new target sandbox " 18602 + newTargetSandbox + " is incompatible with the previous value of" 18603 + oldTargetSandbox + "."); 18604 return; 18605 } 18606 18607 // Prevent installing of child packages 18608 if (oldPackage.parentPackage != null) { 18609 res.setError(PackageManager.INSTALL_PARSE_FAILED_BAD_PACKAGE_NAME, 18610 "Package " + pkg.packageName + " is child of package " 18611 + oldPackage.parentPackage + ". Child packages " 18612 + "can be updated only through the parent package."); 18613 return; 18614 } 18615 } 18616 } 18617 18618 PackageSetting ps = mSettings.mPackages.get(pkgName); 18619 if (ps != null) { 18620 if (DEBUG_INSTALL) Slog.d(TAG, "Existing package: " + ps); 18621 18622 // Static shared libs have same package with different versions where 18623 // we internally use a synthetic package name to allow multiple versions 18624 // of the same package, therefore we need to compare signatures against 18625 // the package setting for the latest library version. 18626 PackageSetting signatureCheckPs = ps; 18627 if (pkg.applicationInfo.isStaticSharedLibrary()) { 18628 SharedLibraryEntry libraryEntry = getLatestSharedLibraVersionLPr(pkg); 18629 if (libraryEntry != null) { 18630 signatureCheckPs = mSettings.getPackageLPr(libraryEntry.apk); 18631 } 18632 } 18633 18634 // Quick sanity check that we're signed correctly if updating; 18635 // we'll check this again later when scanning, but we want to 18636 // bail early here before tripping over redefined permissions. 18637 if (shouldCheckUpgradeKeySetLP(signatureCheckPs, scanFlags)) { 18638 if (!checkUpgradeKeySetLP(signatureCheckPs, pkg)) { 18639 res.setError(INSTALL_FAILED_UPDATE_INCOMPATIBLE, "Package " 18640 + pkg.packageName + " upgrade keys do not match the " 18641 + "previously installed version"); 18642 return; 18643 } 18644 } else { 18645 try { 18646 verifySignaturesLP(signatureCheckPs, pkg); 18647 } catch (PackageManagerException e) { 18648 res.setError(e.error, e.getMessage()); 18649 return; 18650 } 18651 } 18652 18653 oldCodePath = mSettings.mPackages.get(pkgName).codePathString; 18654 if (ps.pkg != null && ps.pkg.applicationInfo != null) { 18655 systemApp = (ps.pkg.applicationInfo.flags & 18656 ApplicationInfo.FLAG_SYSTEM) != 0; 18657 } 18658 res.origUsers = ps.queryInstalledUsers(sUserManager.getUserIds(), true); 18659 } 18660 18661 int N = pkg.permissions.size(); 18662 for (int i = N-1; i >= 0; i--) { 18663 PackageParser.Permission perm = pkg.permissions.get(i); 18664 BasePermission bp = mSettings.mPermissions.get(perm.info.name); 18665 18666 // Don't allow anyone but the system to define ephemeral permissions. 18667 if ((perm.info.protectionLevel & PermissionInfo.PROTECTION_FLAG_INSTANT) != 0 18668 && !systemApp) { 18669 Slog.w(TAG, "Non-System package " + pkg.packageName 18670 + " attempting to delcare ephemeral permission " 18671 + perm.info.name + "; Removing ephemeral."); 18672 perm.info.protectionLevel &= ~PermissionInfo.PROTECTION_FLAG_INSTANT; 18673 } 18674 // Check whether the newly-scanned package wants to define an already-defined perm 18675 if (bp != null) { 18676 // If the defining package is signed with our cert, it's okay. This 18677 // also includes the "updating the same package" case, of course. 18678 // "updating same package" could also involve key-rotation. 18679 final boolean sigsOk; 18680 if (bp.sourcePackage.equals(pkg.packageName) 18681 && (bp.packageSetting instanceof PackageSetting) 18682 && (shouldCheckUpgradeKeySetLP((PackageSetting) bp.packageSetting, 18683 scanFlags))) { 18684 sigsOk = checkUpgradeKeySetLP((PackageSetting) bp.packageSetting, pkg); 18685 } else { 18686 sigsOk = compareSignatures(bp.packageSetting.signatures.mSignatures, 18687 pkg.mSignatures) == PackageManager.SIGNATURE_MATCH; 18688 } 18689 if (!sigsOk) { 18690 // If the owning package is the system itself, we log but allow 18691 // install to proceed; we fail the install on all other permission 18692 // redefinitions. 18693 if (!bp.sourcePackage.equals("android")) { 18694 res.setError(INSTALL_FAILED_DUPLICATE_PERMISSION, "Package " 18695 + pkg.packageName + " attempting to redeclare permission " 18696 + perm.info.name + " already owned by " + bp.sourcePackage); 18697 res.origPermission = perm.info.name; 18698 res.origPackage = bp.sourcePackage; 18699 return; 18700 } else { 18701 Slog.w(TAG, "Package " + pkg.packageName 18702 + " attempting to redeclare system permission " 18703 + perm.info.name + "; ignoring new declaration"); 18704 pkg.permissions.remove(i); 18705 } 18706 } else if (!PLATFORM_PACKAGE_NAME.equals(pkg.packageName)) { 18707 // Prevent apps to change protection level to dangerous from any other 18708 // type as this would allow a privilege escalation where an app adds a 18709 // normal/signature permission in other app's group and later redefines 18710 // it as dangerous leading to the group auto-grant. 18711 if ((perm.info.protectionLevel & PermissionInfo.PROTECTION_MASK_BASE) 18712 == PermissionInfo.PROTECTION_DANGEROUS) { 18713 if (bp != null && !bp.isRuntime()) { 18714 Slog.w(TAG, "Package " + pkg.packageName + " trying to change a " 18715 + "non-runtime permission " + perm.info.name 18716 + " to runtime; keeping old protection level"); 18717 perm.info.protectionLevel = bp.protectionLevel; 18718 } 18719 } 18720 } 18721 } 18722 } 18723 } 18724 18725 if (systemApp) { 18726 if (onExternal) { 18727 // Abort update; system app can't be replaced with app on sdcard 18728 res.setError(INSTALL_FAILED_INVALID_INSTALL_LOCATION, 18729 "Cannot install updates to system apps on sdcard"); 18730 return; 18731 } else if (instantApp) { 18732 // Abort update; system app can't be replaced with an instant app 18733 res.setError(INSTALL_FAILED_INSTANT_APP_INVALID, 18734 "Cannot update a system app with an instant app"); 18735 return; 18736 } 18737 } 18738 18739 if (args.move != null) { 18740 // We did an in-place move, so dex is ready to roll 18741 scanFlags |= SCAN_NO_DEX; 18742 scanFlags |= SCAN_MOVE; 18743 18744 synchronized (mPackages) { 18745 final PackageSetting ps = mSettings.mPackages.get(pkgName); 18746 if (ps == null) { 18747 res.setError(INSTALL_FAILED_INTERNAL_ERROR, 18748 "Missing settings for moved package " + pkgName); 18749 } 18750 18751 // We moved the entire application as-is, so bring over the 18752 // previously derived ABI information. 18753 pkg.applicationInfo.primaryCpuAbi = ps.primaryCpuAbiString; 18754 pkg.applicationInfo.secondaryCpuAbi = ps.secondaryCpuAbiString; 18755 } 18756 18757 } else if (!forwardLocked && !pkg.applicationInfo.isExternalAsec()) { 18758 // Enable SCAN_NO_DEX flag to skip dexopt at a later stage 18759 scanFlags |= SCAN_NO_DEX; 18760 18761 try { 18762 String abiOverride = (TextUtils.isEmpty(pkg.cpuAbiOverride) ? 18763 args.abiOverride : pkg.cpuAbiOverride); 18764 final boolean extractNativeLibs = !pkg.isLibrary(); 18765 derivePackageAbi(pkg, new File(pkg.codePath), abiOverride, 18766 extractNativeLibs, mAppLib32InstallDir); 18767 } catch (PackageManagerException pme) { 18768 Slog.e(TAG, "Error deriving application ABI", pme); 18769 res.setError(INSTALL_FAILED_INTERNAL_ERROR, "Error deriving application ABI"); 18770 return; 18771 } 18772 18773 // Shared libraries for the package need to be updated. 18774 synchronized (mPackages) { 18775 try { 18776 updateSharedLibrariesLPr(pkg, null); 18777 } catch (PackageManagerException e) { 18778 Slog.e(TAG, "updateAllSharedLibrariesLPw failed: " + e.getMessage()); 18779 } 18780 } 18781 } 18782 18783 if (!args.doRename(res.returnCode, pkg, oldCodePath)) { 18784 res.setError(INSTALL_FAILED_INSUFFICIENT_STORAGE, "Failed rename"); 18785 return; 18786 } 18787 18788 // Verify if we need to dexopt the app. 18789 // 18790 // NOTE: it is *important* to call dexopt after doRename which will sync the 18791 // package data from PackageParser.Package and its corresponding ApplicationInfo. 18792 // 18793 // We only need to dexopt if the package meets ALL of the following conditions: 18794 // 1) it is not forward locked. 18795 // 2) it is not on on an external ASEC container. 18796 // 3) it is not an instant app or if it is then dexopt is enabled via gservices. 18797 // 18798 // Note that we do not dexopt instant apps by default. dexopt can take some time to 18799 // complete, so we skip this step during installation. Instead, we'll take extra time 18800 // the first time the instant app starts. It's preferred to do it this way to provide 18801 // continuous progress to the useur instead of mysteriously blocking somewhere in the 18802 // middle of running an instant app. The default behaviour can be overridden 18803 // via gservices. 18804 final boolean performDexopt = !forwardLocked 18805 && !pkg.applicationInfo.isExternalAsec() 18806 && (!instantApp || Global.getInt(mContext.getContentResolver(), 18807 Global.INSTANT_APP_DEXOPT_ENABLED, 0) != 0); 18808 18809 if (performDexopt) { 18810 Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "dexopt"); 18811 // Do not run PackageDexOptimizer through the local performDexOpt 18812 // method because `pkg` may not be in `mPackages` yet. 18813 // 18814 // Also, don't fail application installs if the dexopt step fails. 18815 DexoptOptions dexoptOptions = new DexoptOptions(pkg.packageName, 18816 REASON_INSTALL, 18817 DexoptOptions.DEXOPT_BOOT_COMPLETE); 18818 mPackageDexOptimizer.performDexOpt(pkg, pkg.usesLibraryFiles, 18819 null /* instructionSets */, 18820 getOrCreateCompilerPackageStats(pkg), 18821 mDexManager.getPackageUseInfoOrDefault(pkg.packageName), 18822 dexoptOptions); 18823 Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); 18824 } 18825 18826 // Notify BackgroundDexOptService that the package has been changed. 18827 // If this is an update of a package which used to fail to compile, 18828 // BackgroundDexOptService will remove it from its blacklist. 18829 // TODO: Layering violation 18830 BackgroundDexOptService.notifyPackageChanged(pkg.packageName); 18831 18832 startIntentFilterVerifications(args.user.getIdentifier(), replace, pkg); 18833 18834 try (PackageFreezer freezer = freezePackageForInstall(pkgName, installFlags, 18835 "installPackageLI")) { 18836 if (replace) { 18837 if (pkg.applicationInfo.isStaticSharedLibrary()) { 18838 // Static libs have a synthetic package name containing the version 18839 // and cannot be updated as an update would get a new package name, 18840 // unless this is the exact same version code which is useful for 18841 // development. 18842 PackageParser.Package existingPkg = mPackages.get(pkg.packageName); 18843 if (existingPkg != null && existingPkg.mVersionCode != pkg.mVersionCode) { 18844 res.setError(INSTALL_FAILED_DUPLICATE_PACKAGE, "Packages declaring " 18845 + "static-shared libs cannot be updated"); 18846 return; 18847 } 18848 } 18849 replacePackageLIF(pkg, parseFlags, scanFlags | SCAN_REPLACING, args.user, 18850 installerPackageName, res, args.installReason); 18851 } else { 18852 installNewPackageLIF(pkg, parseFlags, scanFlags | SCAN_DELETE_DATA_ON_FAILURES, 18853 args.user, installerPackageName, volumeUuid, res, args.installReason); 18854 } 18855 } 18856 18857 synchronized (mPackages) { 18858 final PackageSetting ps = mSettings.mPackages.get(pkgName); 18859 if (ps != null) { 18860 res.newUsers = ps.queryInstalledUsers(sUserManager.getUserIds(), true); 18861 ps.setUpdateAvailable(false /*updateAvailable*/); 18862 } 18863 18864 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 18865 for (int i = 0; i < childCount; i++) { 18866 PackageParser.Package childPkg = pkg.childPackages.get(i); 18867 PackageInstalledInfo childRes = res.addedChildPackages.get(childPkg.packageName); 18868 PackageSetting childPs = mSettings.getPackageLPr(childPkg.packageName); 18869 if (childPs != null) { 18870 childRes.newUsers = childPs.queryInstalledUsers( 18871 sUserManager.getUserIds(), true); 18872 } 18873 } 18874 18875 if (res.returnCode == PackageManager.INSTALL_SUCCEEDED) { 18876 updateSequenceNumberLP(ps, res.newUsers); 18877 updateInstantAppInstallerLocked(pkgName); 18878 } 18879 } 18880 } 18881 18882 private void startIntentFilterVerifications(int userId, boolean replacing, 18883 PackageParser.Package pkg) { 18884 if (mIntentFilterVerifierComponent == null) { 18885 Slog.w(TAG, "No IntentFilter verification will not be done as " 18886 + "there is no IntentFilterVerifier available!"); 18887 return; 18888 } 18889 18890 final int verifierUid = getPackageUid( 18891 mIntentFilterVerifierComponent.getPackageName(), 18892 MATCH_DEBUG_TRIAGED_MISSING, 18893 (userId == UserHandle.USER_ALL) ? UserHandle.USER_SYSTEM : userId); 18894 18895 Message msg = mHandler.obtainMessage(START_INTENT_FILTER_VERIFICATIONS); 18896 msg.obj = new IFVerificationParams(pkg, replacing, userId, verifierUid); 18897 mHandler.sendMessage(msg); 18898 18899 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 18900 for (int i = 0; i < childCount; i++) { 18901 PackageParser.Package childPkg = pkg.childPackages.get(i); 18902 msg = mHandler.obtainMessage(START_INTENT_FILTER_VERIFICATIONS); 18903 msg.obj = new IFVerificationParams(childPkg, replacing, userId, verifierUid); 18904 mHandler.sendMessage(msg); 18905 } 18906 } 18907 18908 private void verifyIntentFiltersIfNeeded(int userId, int verifierUid, boolean replacing, 18909 PackageParser.Package pkg) { 18910 int size = pkg.activities.size(); 18911 if (size == 0) { 18912 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, 18913 "No activity, so no need to verify any IntentFilter!"); 18914 return; 18915 } 18916 18917 final boolean hasDomainURLs = hasDomainURLs(pkg); 18918 if (!hasDomainURLs) { 18919 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, 18920 "No domain URLs, so no need to verify any IntentFilter!"); 18921 return; 18922 } 18923 18924 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, "Checking for userId:" + userId 18925 + " if any IntentFilter from the " + size 18926 + " Activities needs verification ..."); 18927 18928 int count = 0; 18929 final String packageName = pkg.packageName; 18930 18931 synchronized (mPackages) { 18932 // If this is a new install and we see that we've already run verification for this 18933 // package, we have nothing to do: it means the state was restored from backup. 18934 if (!replacing) { 18935 IntentFilterVerificationInfo ivi = 18936 mSettings.getIntentFilterVerificationLPr(packageName); 18937 if (ivi != null) { 18938 if (DEBUG_DOMAIN_VERIFICATION) { 18939 Slog.i(TAG, "Package " + packageName+ " already verified: status=" 18940 + ivi.getStatusString()); 18941 } 18942 return; 18943 } 18944 } 18945 18946 // If any filters need to be verified, then all need to be. 18947 boolean needToVerify = false; 18948 for (PackageParser.Activity a : pkg.activities) { 18949 for (ActivityIntentInfo filter : a.intents) { 18950 if (filter.needsVerification() && needsNetworkVerificationLPr(filter)) { 18951 if (DEBUG_DOMAIN_VERIFICATION) { 18952 Slog.d(TAG, "Intent filter needs verification, so processing all filters"); 18953 } 18954 needToVerify = true; 18955 break; 18956 } 18957 } 18958 } 18959 18960 if (needToVerify) { 18961 final int verificationId = mIntentFilterVerificationToken++; 18962 for (PackageParser.Activity a : pkg.activities) { 18963 for (ActivityIntentInfo filter : a.intents) { 18964 if (filter.handlesWebUris(true) && needsNetworkVerificationLPr(filter)) { 18965 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, 18966 "Verification needed for IntentFilter:" + filter.toString()); 18967 mIntentFilterVerifier.addOneIntentFilterVerification( 18968 verifierUid, userId, verificationId, filter, packageName); 18969 count++; 18970 } 18971 } 18972 } 18973 } 18974 } 18975 18976 if (count > 0) { 18977 if (DEBUG_DOMAIN_VERIFICATION) Slog.d(TAG, "Starting " + count 18978 + " IntentFilter verification" + (count > 1 ? "s" : "") 18979 + " for userId:" + userId); 18980 mIntentFilterVerifier.startVerifications(userId); 18981 } else { 18982 if (DEBUG_DOMAIN_VERIFICATION) { 18983 Slog.d(TAG, "No filters or not all autoVerify for " + packageName); 18984 } 18985 } 18986 } 18987 18988 private boolean needsNetworkVerificationLPr(ActivityIntentInfo filter) { 18989 final ComponentName cn = filter.activity.getComponentName(); 18990 final String packageName = cn.getPackageName(); 18991 18992 IntentFilterVerificationInfo ivi = mSettings.getIntentFilterVerificationLPr( 18993 packageName); 18994 if (ivi == null) { 18995 return true; 18996 } 18997 int status = ivi.getStatus(); 18998 switch (status) { 18999 case INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED: 19000 case INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ASK: 19001 return true; 19002 19003 default: 19004 // Nothing to do 19005 return false; 19006 } 19007 } 19008 19009 private static boolean isMultiArch(ApplicationInfo info) { 19010 return (info.flags & ApplicationInfo.FLAG_MULTIARCH) != 0; 19011 } 19012 19013 private static boolean isExternal(PackageParser.Package pkg) { 19014 return (pkg.applicationInfo.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0; 19015 } 19016 19017 private static boolean isExternal(PackageSetting ps) { 19018 return (ps.pkgFlags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0; 19019 } 19020 19021 private static boolean isSystemApp(PackageParser.Package pkg) { 19022 return (pkg.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 19023 } 19024 19025 private static boolean isPrivilegedApp(PackageParser.Package pkg) { 19026 return (pkg.applicationInfo.privateFlags & ApplicationInfo.PRIVATE_FLAG_PRIVILEGED) != 0; 19027 } 19028 19029 private static boolean hasDomainURLs(PackageParser.Package pkg) { 19030 return (pkg.applicationInfo.privateFlags & ApplicationInfo.PRIVATE_FLAG_HAS_DOMAIN_URLS) != 0; 19031 } 19032 19033 private static boolean isSystemApp(PackageSetting ps) { 19034 return (ps.pkgFlags & ApplicationInfo.FLAG_SYSTEM) != 0; 19035 } 19036 19037 private static boolean isUpdatedSystemApp(PackageSetting ps) { 19038 return (ps.pkgFlags & ApplicationInfo.FLAG_UPDATED_SYSTEM_APP) != 0; 19039 } 19040 19041 private int packageFlagsToInstallFlags(PackageSetting ps) { 19042 int installFlags = 0; 19043 if (isExternal(ps) && TextUtils.isEmpty(ps.volumeUuid)) { 19044 // This existing package was an external ASEC install when we have 19045 // the external flag without a UUID 19046 installFlags |= PackageManager.INSTALL_EXTERNAL; 19047 } 19048 if (ps.isForwardLocked()) { 19049 installFlags |= PackageManager.INSTALL_FORWARD_LOCK; 19050 } 19051 return installFlags; 19052 } 19053 19054 private String getVolumeUuidForPackage(PackageParser.Package pkg) { 19055 if (isExternal(pkg)) { 19056 if (TextUtils.isEmpty(pkg.volumeUuid)) { 19057 return StorageManager.UUID_PRIMARY_PHYSICAL; 19058 } else { 19059 return pkg.volumeUuid; 19060 } 19061 } else { 19062 return StorageManager.UUID_PRIVATE_INTERNAL; 19063 } 19064 } 19065 19066 private VersionInfo getSettingsVersionForPackage(PackageParser.Package pkg) { 19067 if (isExternal(pkg)) { 19068 if (TextUtils.isEmpty(pkg.volumeUuid)) { 19069 return mSettings.getExternalVersion(); 19070 } else { 19071 return mSettings.findOrCreateVersion(pkg.volumeUuid); 19072 } 19073 } else { 19074 return mSettings.getInternalVersion(); 19075 } 19076 } 19077 19078 private void deleteTempPackageFiles() { 19079 final FilenameFilter filter = new FilenameFilter() { 19080 public boolean accept(File dir, String name) { 19081 return name.startsWith("vmdl") && name.endsWith(".tmp"); 19082 } 19083 }; 19084 for (File file : mDrmAppPrivateInstallDir.listFiles(filter)) { 19085 file.delete(); 19086 } 19087 } 19088 19089 @Override 19090 public void deletePackageAsUser(String packageName, int versionCode, 19091 IPackageDeleteObserver observer, int userId, int flags) { 19092 deletePackageVersioned(new VersionedPackage(packageName, versionCode), 19093 new LegacyPackageDeleteObserver(observer).getBinder(), userId, flags); 19094 } 19095 19096 @Override 19097 public void deletePackageVersioned(VersionedPackage versionedPackage, 19098 final IPackageDeleteObserver2 observer, final int userId, final int deleteFlags) { 19099 final int callingUid = Binder.getCallingUid(); 19100 mContext.enforceCallingOrSelfPermission( 19101 android.Manifest.permission.DELETE_PACKAGES, null); 19102 final boolean canViewInstantApps = canViewInstantApps(callingUid, userId); 19103 Preconditions.checkNotNull(versionedPackage); 19104 Preconditions.checkNotNull(observer); 19105 Preconditions.checkArgumentInRange(versionedPackage.getVersionCode(), 19106 PackageManager.VERSION_CODE_HIGHEST, 19107 Integer.MAX_VALUE, "versionCode must be >= -1"); 19108 19109 final String packageName = versionedPackage.getPackageName(); 19110 final int versionCode = versionedPackage.getVersionCode(); 19111 final String internalPackageName; 19112 synchronized (mPackages) { 19113 // Normalize package name to handle renamed packages and static libs 19114 internalPackageName = resolveInternalPackageNameLPr(versionedPackage.getPackageName(), 19115 versionedPackage.getVersionCode()); 19116 } 19117 19118 final int uid = Binder.getCallingUid(); 19119 if (!isOrphaned(internalPackageName) 19120 && !isCallerAllowedToSilentlyUninstall(uid, internalPackageName)) { 19121 try { 19122 final Intent intent = new Intent(Intent.ACTION_UNINSTALL_PACKAGE); 19123 intent.setData(Uri.fromParts(PACKAGE_SCHEME, packageName, null)); 19124 intent.putExtra(PackageInstaller.EXTRA_CALLBACK, observer.asBinder()); 19125 observer.onUserActionRequired(intent); 19126 } catch (RemoteException re) { 19127 } 19128 return; 19129 } 19130 final boolean deleteAllUsers = (deleteFlags & PackageManager.DELETE_ALL_USERS) != 0; 19131 final int[] users = deleteAllUsers ? sUserManager.getUserIds() : new int[]{ userId }; 19132 if (UserHandle.getUserId(uid) != userId || (deleteAllUsers && users.length > 1)) { 19133 mContext.enforceCallingOrSelfPermission( 19134 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, 19135 "deletePackage for user " + userId); 19136 } 19137 19138 if (isUserRestricted(userId, UserManager.DISALLOW_UNINSTALL_APPS)) { 19139 try { 19140 observer.onPackageDeleted(packageName, 19141 PackageManager.DELETE_FAILED_USER_RESTRICTED, null); 19142 } catch (RemoteException re) { 19143 } 19144 return; 19145 } 19146 19147 if (!deleteAllUsers && getBlockUninstallForUser(internalPackageName, userId)) { 19148 try { 19149 observer.onPackageDeleted(packageName, 19150 PackageManager.DELETE_FAILED_OWNER_BLOCKED, null); 19151 } catch (RemoteException re) { 19152 } 19153 return; 19154 } 19155 19156 if (DEBUG_REMOVE) { 19157 Slog.d(TAG, "deletePackageAsUser: pkg=" + internalPackageName + " user=" + userId 19158 + " deleteAllUsers: " + deleteAllUsers + " version=" 19159 + (versionCode == PackageManager.VERSION_CODE_HIGHEST 19160 ? "VERSION_CODE_HIGHEST" : versionCode)); 19161 } 19162 // Queue up an async operation since the package deletion may take a little while. 19163 mHandler.post(new Runnable() { 19164 public void run() { 19165 mHandler.removeCallbacks(this); 19166 int returnCode; 19167 final PackageSetting ps = mSettings.mPackages.get(internalPackageName); 19168 boolean doDeletePackage = true; 19169 if (ps != null) { 19170 final boolean targetIsInstantApp = 19171 ps.getInstantApp(UserHandle.getUserId(callingUid)); 19172 doDeletePackage = !targetIsInstantApp 19173 || canViewInstantApps; 19174 } 19175 if (doDeletePackage) { 19176 if (!deleteAllUsers) { 19177 returnCode = deletePackageX(internalPackageName, versionCode, 19178 userId, deleteFlags); 19179 } else { 19180 int[] blockUninstallUserIds = getBlockUninstallForUsers( 19181 internalPackageName, users); 19182 // If nobody is blocking uninstall, proceed with delete for all users 19183 if (ArrayUtils.isEmpty(blockUninstallUserIds)) { 19184 returnCode = deletePackageX(internalPackageName, versionCode, 19185 userId, deleteFlags); 19186 } else { 19187 // Otherwise uninstall individually for users with blockUninstalls=false 19188 final int userFlags = deleteFlags & ~PackageManager.DELETE_ALL_USERS; 19189 for (int userId : users) { 19190 if (!ArrayUtils.contains(blockUninstallUserIds, userId)) { 19191 returnCode = deletePackageX(internalPackageName, versionCode, 19192 userId, userFlags); 19193 if (returnCode != PackageManager.DELETE_SUCCEEDED) { 19194 Slog.w(TAG, "Package delete failed for user " + userId 19195 + ", returnCode " + returnCode); 19196 } 19197 } 19198 } 19199 // The app has only been marked uninstalled for certain users. 19200 // We still need to report that delete was blocked 19201 returnCode = PackageManager.DELETE_FAILED_OWNER_BLOCKED; 19202 } 19203 } 19204 } else { 19205 returnCode = PackageManager.DELETE_FAILED_INTERNAL_ERROR; 19206 } 19207 try { 19208 observer.onPackageDeleted(packageName, returnCode, null); 19209 } catch (RemoteException e) { 19210 Log.i(TAG, "Observer no longer exists."); 19211 } //end catch 19212 } //end run 19213 }); 19214 } 19215 19216 private String resolveExternalPackageNameLPr(PackageParser.Package pkg) { 19217 if (pkg.staticSharedLibName != null) { 19218 return pkg.manifestPackageName; 19219 } 19220 return pkg.packageName; 19221 } 19222 19223 private String resolveInternalPackageNameLPr(String packageName, int versionCode) { 19224 // Handle renamed packages 19225 String normalizedPackageName = mSettings.getRenamedPackageLPr(packageName); 19226 packageName = normalizedPackageName != null ? normalizedPackageName : packageName; 19227 19228 // Is this a static library? 19229 SparseArray<SharedLibraryEntry> versionedLib = 19230 mStaticLibsByDeclaringPackage.get(packageName); 19231 if (versionedLib == null || versionedLib.size() <= 0) { 19232 return packageName; 19233 } 19234 19235 // Figure out which lib versions the caller can see 19236 SparseIntArray versionsCallerCanSee = null; 19237 final int callingAppId = UserHandle.getAppId(Binder.getCallingUid()); 19238 if (callingAppId != Process.SYSTEM_UID && callingAppId != Process.SHELL_UID 19239 && callingAppId != Process.ROOT_UID) { 19240 versionsCallerCanSee = new SparseIntArray(); 19241 String libName = versionedLib.valueAt(0).info.getName(); 19242 String[] uidPackages = getPackagesForUid(Binder.getCallingUid()); 19243 if (uidPackages != null) { 19244 for (String uidPackage : uidPackages) { 19245 PackageSetting ps = mSettings.getPackageLPr(uidPackage); 19246 final int libIdx = ArrayUtils.indexOf(ps.usesStaticLibraries, libName); 19247 if (libIdx >= 0) { 19248 final int libVersion = ps.usesStaticLibrariesVersions[libIdx]; 19249 versionsCallerCanSee.append(libVersion, libVersion); 19250 } 19251 } 19252 } 19253 } 19254 19255 // Caller can see nothing - done 19256 if (versionsCallerCanSee != null && versionsCallerCanSee.size() <= 0) { 19257 return packageName; 19258 } 19259 19260 // Find the version the caller can see and the app version code 19261 SharedLibraryEntry highestVersion = null; 19262 final int versionCount = versionedLib.size(); 19263 for (int i = 0; i < versionCount; i++) { 19264 SharedLibraryEntry libEntry = versionedLib.valueAt(i); 19265 if (versionsCallerCanSee != null && versionsCallerCanSee.indexOfKey( 19266 libEntry.info.getVersion()) < 0) { 19267 continue; 19268 } 19269 final int libVersionCode = libEntry.info.getDeclaringPackage().getVersionCode(); 19270 if (versionCode != PackageManager.VERSION_CODE_HIGHEST) { 19271 if (libVersionCode == versionCode) { 19272 return libEntry.apk; 19273 } 19274 } else if (highestVersion == null) { 19275 highestVersion = libEntry; 19276 } else if (libVersionCode > highestVersion.info 19277 .getDeclaringPackage().getVersionCode()) { 19278 highestVersion = libEntry; 19279 } 19280 } 19281 19282 if (highestVersion != null) { 19283 return highestVersion.apk; 19284 } 19285 19286 return packageName; 19287 } 19288 19289 boolean isCallerVerifier(int callingUid) { 19290 final int callingUserId = UserHandle.getUserId(callingUid); 19291 return mRequiredVerifierPackage != null && 19292 callingUid == getPackageUid(mRequiredVerifierPackage, 0, callingUserId); 19293 } 19294 19295 private boolean isCallerAllowedToSilentlyUninstall(int callingUid, String pkgName) { 19296 if (callingUid == Process.SHELL_UID || callingUid == Process.ROOT_UID 19297 || UserHandle.getAppId(callingUid) == Process.SYSTEM_UID) { 19298 return true; 19299 } 19300 final int callingUserId = UserHandle.getUserId(callingUid); 19301 // If the caller installed the pkgName, then allow it to silently uninstall. 19302 if (callingUid == getPackageUid(getInstallerPackageName(pkgName), 0, callingUserId)) { 19303 return true; 19304 } 19305 19306 // Allow package verifier to silently uninstall. 19307 if (mRequiredVerifierPackage != null && 19308 callingUid == getPackageUid(mRequiredVerifierPackage, 0, callingUserId)) { 19309 return true; 19310 } 19311 19312 // Allow package uninstaller to silently uninstall. 19313 if (mRequiredUninstallerPackage != null && 19314 callingUid == getPackageUid(mRequiredUninstallerPackage, 0, callingUserId)) { 19315 return true; 19316 } 19317 19318 // Allow storage manager to silently uninstall. 19319 if (mStorageManagerPackage != null && 19320 callingUid == getPackageUid(mStorageManagerPackage, 0, callingUserId)) { 19321 return true; 19322 } 19323 19324 // Allow caller having MANAGE_PROFILE_AND_DEVICE_OWNERS permission to silently 19325 // uninstall for device owner provisioning. 19326 if (checkUidPermission(MANAGE_PROFILE_AND_DEVICE_OWNERS, callingUid) 19327 == PERMISSION_GRANTED) { 19328 return true; 19329 } 19330 19331 return false; 19332 } 19333 19334 private int[] getBlockUninstallForUsers(String packageName, int[] userIds) { 19335 int[] result = EMPTY_INT_ARRAY; 19336 for (int userId : userIds) { 19337 if (getBlockUninstallForUser(packageName, userId)) { 19338 result = ArrayUtils.appendInt(result, userId); 19339 } 19340 } 19341 return result; 19342 } 19343 19344 @Override 19345 public boolean isPackageDeviceAdminOnAnyUser(String packageName) { 19346 final int callingUid = Binder.getCallingUid(); 19347 if (getInstantAppPackageName(callingUid) != null 19348 && !isCallerSameApp(packageName, callingUid)) { 19349 return false; 19350 } 19351 return isPackageDeviceAdmin(packageName, UserHandle.USER_ALL); 19352 } 19353 19354 private boolean isPackageDeviceAdmin(String packageName, int userId) { 19355 IDevicePolicyManager dpm = IDevicePolicyManager.Stub.asInterface( 19356 ServiceManager.getService(Context.DEVICE_POLICY_SERVICE)); 19357 try { 19358 if (dpm != null) { 19359 final ComponentName deviceOwnerComponentName = dpm.getDeviceOwnerComponent( 19360 /* callingUserOnly =*/ false); 19361 final String deviceOwnerPackageName = deviceOwnerComponentName == null ? null 19362 : deviceOwnerComponentName.getPackageName(); 19363 // Does the package contains the device owner? 19364 // TODO Do we have to do it even if userId != UserHandle.USER_ALL? Otherwise, 19365 // this check is probably not needed, since DO should be registered as a device 19366 // admin on some user too. (Original bug for this: b/17657954) 19367 if (packageName.equals(deviceOwnerPackageName)) { 19368 return true; 19369 } 19370 // Does it contain a device admin for any user? 19371 int[] users; 19372 if (userId == UserHandle.USER_ALL) { 19373 users = sUserManager.getUserIds(); 19374 } else { 19375 users = new int[]{userId}; 19376 } 19377 for (int i = 0; i < users.length; ++i) { 19378 if (dpm.packageHasActiveAdmins(packageName, users[i])) { 19379 return true; 19380 } 19381 } 19382 } 19383 } catch (RemoteException e) { 19384 } 19385 return false; 19386 } 19387 19388 private boolean shouldKeepUninstalledPackageLPr(String packageName) { 19389 return mKeepUninstalledPackages != null && mKeepUninstalledPackages.contains(packageName); 19390 } 19391 19392 /** 19393 * This method is an internal method that could be get invoked either 19394 * to delete an installed package or to clean up a failed installation. 19395 * After deleting an installed package, a broadcast is sent to notify any 19396 * listeners that the package has been removed. For cleaning up a failed 19397 * installation, the broadcast is not necessary since the package's 19398 * installation wouldn't have sent the initial broadcast either 19399 * The key steps in deleting a package are 19400 * deleting the package information in internal structures like mPackages, 19401 * deleting the packages base directories through installd 19402 * updating mSettings to reflect current status 19403 * persisting settings for later use 19404 * sending a broadcast if necessary 19405 */ 19406 int deletePackageX(String packageName, int versionCode, int userId, int deleteFlags) { 19407 final PackageRemovedInfo info = new PackageRemovedInfo(this); 19408 final boolean res; 19409 19410 final int removeUser = (deleteFlags & PackageManager.DELETE_ALL_USERS) != 0 19411 ? UserHandle.USER_ALL : userId; 19412 19413 if (isPackageDeviceAdmin(packageName, removeUser)) { 19414 Slog.w(TAG, "Not removing package " + packageName + ": has active device admin"); 19415 return PackageManager.DELETE_FAILED_DEVICE_POLICY_MANAGER; 19416 } 19417 19418 PackageSetting uninstalledPs = null; 19419 PackageParser.Package pkg = null; 19420 19421 // for the uninstall-updates case and restricted profiles, remember the per- 19422 // user handle installed state 19423 int[] allUsers; 19424 synchronized (mPackages) { 19425 uninstalledPs = mSettings.mPackages.get(packageName); 19426 if (uninstalledPs == null) { 19427 Slog.w(TAG, "Not removing non-existent package " + packageName); 19428 return PackageManager.DELETE_FAILED_INTERNAL_ERROR; 19429 } 19430 19431 if (versionCode != PackageManager.VERSION_CODE_HIGHEST 19432 && uninstalledPs.versionCode != versionCode) { 19433 Slog.w(TAG, "Not removing package " + packageName + " with versionCode " 19434 + uninstalledPs.versionCode + " != " + versionCode); 19435 return PackageManager.DELETE_FAILED_INTERNAL_ERROR; 19436 } 19437 19438 // Static shared libs can be declared by any package, so let us not 19439 // allow removing a package if it provides a lib others depend on. 19440 pkg = mPackages.get(packageName); 19441 19442 allUsers = sUserManager.getUserIds(); 19443 19444 if (pkg != null && pkg.staticSharedLibName != null) { 19445 SharedLibraryEntry libEntry = getSharedLibraryEntryLPr(pkg.staticSharedLibName, 19446 pkg.staticSharedLibVersion); 19447 if (libEntry != null) { 19448 for (int currUserId : allUsers) { 19449 if (removeUser != UserHandle.USER_ALL && removeUser != currUserId) { 19450 continue; 19451 } 19452 List<VersionedPackage> libClientPackages = getPackagesUsingSharedLibraryLPr( 19453 libEntry.info, 0, currUserId); 19454 if (!ArrayUtils.isEmpty(libClientPackages)) { 19455 Slog.w(TAG, "Not removing package " + pkg.manifestPackageName 19456 + " hosting lib " + libEntry.info.getName() + " version " 19457 + libEntry.info.getVersion() + " used by " + libClientPackages 19458 + " for user " + currUserId); 19459 return PackageManager.DELETE_FAILED_USED_SHARED_LIBRARY; 19460 } 19461 } 19462 } 19463 } 19464 19465 info.origUsers = uninstalledPs.queryInstalledUsers(allUsers, true); 19466 } 19467 19468 final int freezeUser; 19469 if (isUpdatedSystemApp(uninstalledPs) 19470 && ((deleteFlags & PackageManager.DELETE_SYSTEM_APP) == 0)) { 19471 // We're downgrading a system app, which will apply to all users, so 19472 // freeze them all during the downgrade 19473 freezeUser = UserHandle.USER_ALL; 19474 } else { 19475 freezeUser = removeUser; 19476 } 19477 19478 synchronized (mInstallLock) { 19479 if (DEBUG_REMOVE) Slog.d(TAG, "deletePackageX: pkg=" + packageName + " user=" + userId); 19480 try (PackageFreezer freezer = freezePackageForDelete(packageName, freezeUser, 19481 deleteFlags, "deletePackageX")) { 19482 res = deletePackageLIF(packageName, UserHandle.of(removeUser), true, allUsers, 19483 deleteFlags | FLAGS_REMOVE_CHATTY, info, true, null); 19484 } 19485 synchronized (mPackages) { 19486 if (res) { 19487 if (pkg != null) { 19488 mInstantAppRegistry.onPackageUninstalledLPw(pkg, info.removedUsers); 19489 } 19490 updateSequenceNumberLP(uninstalledPs, info.removedUsers); 19491 updateInstantAppInstallerLocked(packageName); 19492 } 19493 } 19494 } 19495 19496 if (res) { 19497 final boolean killApp = (deleteFlags & PackageManager.DELETE_DONT_KILL_APP) == 0; 19498 info.sendPackageRemovedBroadcasts(killApp); 19499 info.sendSystemPackageUpdatedBroadcasts(); 19500 info.sendSystemPackageAppearedBroadcasts(); 19501 } 19502 // Force a gc here. 19503 Runtime.getRuntime().gc(); 19504 // Delete the resources here after sending the broadcast to let 19505 // other processes clean up before deleting resources. 19506 if (info.args != null) { 19507 synchronized (mInstallLock) { 19508 info.args.doPostDeleteLI(true); 19509 } 19510 } 19511 19512 return res ? PackageManager.DELETE_SUCCEEDED : PackageManager.DELETE_FAILED_INTERNAL_ERROR; 19513 } 19514 19515 static class PackageRemovedInfo { 19516 final PackageSender packageSender; 19517 String removedPackage; 19518 String installerPackageName; 19519 int uid = -1; 19520 int removedAppId = -1; 19521 int[] origUsers; 19522 int[] removedUsers = null; 19523 int[] broadcastUsers = null; 19524 SparseArray<Integer> installReasons; 19525 boolean isRemovedPackageSystemUpdate = false; 19526 boolean isUpdate; 19527 boolean dataRemoved; 19528 boolean removedForAllUsers; 19529 boolean isStaticSharedLib; 19530 // Clean up resources deleted packages. 19531 InstallArgs args = null; 19532 ArrayMap<String, PackageRemovedInfo> removedChildPackages; 19533 ArrayMap<String, PackageInstalledInfo> appearedChildPackages; 19534 19535 PackageRemovedInfo(PackageSender packageSender) { 19536 this.packageSender = packageSender; 19537 } 19538 19539 void sendPackageRemovedBroadcasts(boolean killApp) { 19540 sendPackageRemovedBroadcastInternal(killApp); 19541 final int childCount = removedChildPackages != null ? removedChildPackages.size() : 0; 19542 for (int i = 0; i < childCount; i++) { 19543 PackageRemovedInfo childInfo = removedChildPackages.valueAt(i); 19544 childInfo.sendPackageRemovedBroadcastInternal(killApp); 19545 } 19546 } 19547 19548 void sendSystemPackageUpdatedBroadcasts() { 19549 if (isRemovedPackageSystemUpdate) { 19550 sendSystemPackageUpdatedBroadcastsInternal(); 19551 final int childCount = (removedChildPackages != null) 19552 ? removedChildPackages.size() : 0; 19553 for (int i = 0; i < childCount; i++) { 19554 PackageRemovedInfo childInfo = removedChildPackages.valueAt(i); 19555 if (childInfo.isRemovedPackageSystemUpdate) { 19556 childInfo.sendSystemPackageUpdatedBroadcastsInternal(); 19557 } 19558 } 19559 } 19560 } 19561 19562 void sendSystemPackageAppearedBroadcasts() { 19563 final int packageCount = (appearedChildPackages != null) 19564 ? appearedChildPackages.size() : 0; 19565 for (int i = 0; i < packageCount; i++) { 19566 PackageInstalledInfo installedInfo = appearedChildPackages.valueAt(i); 19567 packageSender.sendPackageAddedForNewUsers(installedInfo.name, 19568 true /*sendBootCompleted*/, false /*startReceiver*/, 19569 UserHandle.getAppId(installedInfo.uid), installedInfo.newUsers); 19570 } 19571 } 19572 19573 private void sendSystemPackageUpdatedBroadcastsInternal() { 19574 Bundle extras = new Bundle(2); 19575 extras.putInt(Intent.EXTRA_UID, removedAppId >= 0 ? removedAppId : uid); 19576 extras.putBoolean(Intent.EXTRA_REPLACING, true); 19577 packageSender.sendPackageBroadcast(Intent.ACTION_PACKAGE_ADDED, 19578 removedPackage, extras, 0, null /*targetPackage*/, null, null); 19579 packageSender.sendPackageBroadcast(Intent.ACTION_PACKAGE_REPLACED, 19580 removedPackage, extras, 0, null /*targetPackage*/, null, null); 19581 packageSender.sendPackageBroadcast(Intent.ACTION_MY_PACKAGE_REPLACED, 19582 null, null, 0, removedPackage, null, null); 19583 if (installerPackageName != null) { 19584 packageSender.sendPackageBroadcast(Intent.ACTION_PACKAGE_ADDED, 19585 removedPackage, extras, 0 /*flags*/, 19586 installerPackageName, null, null); 19587 packageSender.sendPackageBroadcast(Intent.ACTION_PACKAGE_REPLACED, 19588 removedPackage, extras, 0 /*flags*/, 19589 installerPackageName, null, null); 19590 } 19591 } 19592 19593 private void sendPackageRemovedBroadcastInternal(boolean killApp) { 19594 // Don't send static shared library removal broadcasts as these 19595 // libs are visible only the the apps that depend on them an one 19596 // cannot remove the library if it has a dependency. 19597 if (isStaticSharedLib) { 19598 return; 19599 } 19600 Bundle extras = new Bundle(2); 19601 extras.putInt(Intent.EXTRA_UID, removedAppId >= 0 ? removedAppId : uid); 19602 extras.putBoolean(Intent.EXTRA_DATA_REMOVED, dataRemoved); 19603 extras.putBoolean(Intent.EXTRA_DONT_KILL_APP, !killApp); 19604 if (isUpdate || isRemovedPackageSystemUpdate) { 19605 extras.putBoolean(Intent.EXTRA_REPLACING, true); 19606 } 19607 extras.putBoolean(Intent.EXTRA_REMOVED_FOR_ALL_USERS, removedForAllUsers); 19608 if (removedPackage != null) { 19609 packageSender.sendPackageBroadcast(Intent.ACTION_PACKAGE_REMOVED, 19610 removedPackage, extras, 0, null /*targetPackage*/, null, broadcastUsers); 19611 if (installerPackageName != null) { 19612 packageSender.sendPackageBroadcast(Intent.ACTION_PACKAGE_REMOVED, 19613 removedPackage, extras, 0 /*flags*/, 19614 installerPackageName, null, broadcastUsers); 19615 } 19616 if (dataRemoved && !isRemovedPackageSystemUpdate) { 19617 packageSender.sendPackageBroadcast(Intent.ACTION_PACKAGE_FULLY_REMOVED, 19618 removedPackage, extras, 19619 Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND, 19620 null, null, broadcastUsers); 19621 } 19622 } 19623 if (removedAppId >= 0) { 19624 packageSender.sendPackageBroadcast(Intent.ACTION_UID_REMOVED, 19625 null, extras, Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND, 19626 null, null, broadcastUsers); 19627 } 19628 } 19629 19630 void populateUsers(int[] userIds, PackageSetting deletedPackageSetting) { 19631 removedUsers = userIds; 19632 if (removedUsers == null) { 19633 broadcastUsers = null; 19634 return; 19635 } 19636 19637 broadcastUsers = EMPTY_INT_ARRAY; 19638 for (int i = userIds.length - 1; i >= 0; --i) { 19639 final int userId = userIds[i]; 19640 if (deletedPackageSetting.getInstantApp(userId)) { 19641 continue; 19642 } 19643 broadcastUsers = ArrayUtils.appendInt(broadcastUsers, userId); 19644 } 19645 } 19646 } 19647 19648 /* 19649 * This method deletes the package from internal data structures. If the DONT_DELETE_DATA 19650 * flag is not set, the data directory is removed as well. 19651 * make sure this flag is set for partially installed apps. If not its meaningless to 19652 * delete a partially installed application. 19653 */ 19654 private void removePackageDataLIF(PackageSetting ps, int[] allUserHandles, 19655 PackageRemovedInfo outInfo, int flags, boolean writeSettings) { 19656 String packageName = ps.name; 19657 if (DEBUG_REMOVE) Slog.d(TAG, "removePackageDataLI: " + ps); 19658 // Retrieve object to delete permissions for shared user later on 19659 final PackageParser.Package deletedPkg; 19660 final PackageSetting deletedPs; 19661 // reader 19662 synchronized (mPackages) { 19663 deletedPkg = mPackages.get(packageName); 19664 deletedPs = mSettings.mPackages.get(packageName); 19665 if (outInfo != null) { 19666 outInfo.removedPackage = packageName; 19667 outInfo.installerPackageName = ps.installerPackageName; 19668 outInfo.isStaticSharedLib = deletedPkg != null 19669 && deletedPkg.staticSharedLibName != null; 19670 outInfo.populateUsers(deletedPs == null ? null 19671 : deletedPs.queryInstalledUsers(sUserManager.getUserIds(), true), deletedPs); 19672 } 19673 } 19674 19675 removePackageLI(ps, (flags & FLAGS_REMOVE_CHATTY) != 0); 19676 19677 if ((flags & PackageManager.DELETE_KEEP_DATA) == 0) { 19678 final PackageParser.Package resolvedPkg; 19679 if (deletedPkg != null) { 19680 resolvedPkg = deletedPkg; 19681 } else { 19682 // We don't have a parsed package when it lives on an ejected 19683 // adopted storage device, so fake something together 19684 resolvedPkg = new PackageParser.Package(ps.name); 19685 resolvedPkg.setVolumeUuid(ps.volumeUuid); 19686 } 19687 destroyAppDataLIF(resolvedPkg, UserHandle.USER_ALL, 19688 StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE); 19689 destroyAppProfilesLIF(resolvedPkg, UserHandle.USER_ALL); 19690 if (outInfo != null) { 19691 outInfo.dataRemoved = true; 19692 } 19693 schedulePackageCleaning(packageName, UserHandle.USER_ALL, true); 19694 } 19695 19696 int removedAppId = -1; 19697 19698 // writer 19699 synchronized (mPackages) { 19700 boolean installedStateChanged = false; 19701 if (deletedPs != null) { 19702 if ((flags&PackageManager.DELETE_KEEP_DATA) == 0) { 19703 clearIntentFilterVerificationsLPw(deletedPs.name, UserHandle.USER_ALL); 19704 clearDefaultBrowserIfNeeded(packageName); 19705 mSettings.mKeySetManagerService.removeAppKeySetDataLPw(packageName); 19706 removedAppId = mSettings.removePackageLPw(packageName); 19707 if (outInfo != null) { 19708 outInfo.removedAppId = removedAppId; 19709 } 19710 updatePermissionsLPw(deletedPs.name, null, 0); 19711 if (deletedPs.sharedUser != null) { 19712 // Remove permissions associated with package. Since runtime 19713 // permissions are per user we have to kill the removed package 19714 // or packages running under the shared user of the removed 19715 // package if revoking the permissions requested only by the removed 19716 // package is successful and this causes a change in gids. 19717 for (int userId : UserManagerService.getInstance().getUserIds()) { 19718 final int userIdToKill = mSettings.updateSharedUserPermsLPw(deletedPs, 19719 userId); 19720 if (userIdToKill == UserHandle.USER_ALL 19721 || userIdToKill >= UserHandle.USER_SYSTEM) { 19722 // If gids changed for this user, kill all affected packages. 19723 mHandler.post(new Runnable() { 19724 @Override 19725 public void run() { 19726 // This has to happen with no lock held. 19727 killApplication(deletedPs.name, deletedPs.appId, 19728 KILL_APP_REASON_GIDS_CHANGED); 19729 } 19730 }); 19731 break; 19732 } 19733 } 19734 } 19735 clearPackagePreferredActivitiesLPw(deletedPs.name, UserHandle.USER_ALL); 19736 } 19737 // make sure to preserve per-user disabled state if this removal was just 19738 // a downgrade of a system app to the factory package 19739 if (allUserHandles != null && outInfo != null && outInfo.origUsers != null) { 19740 if (DEBUG_REMOVE) { 19741 Slog.d(TAG, "Propagating install state across downgrade"); 19742 } 19743 for (int userId : allUserHandles) { 19744 final boolean installed = ArrayUtils.contains(outInfo.origUsers, userId); 19745 if (DEBUG_REMOVE) { 19746 Slog.d(TAG, " user " + userId + " => " + installed); 19747 } 19748 if (installed != ps.getInstalled(userId)) { 19749 installedStateChanged = true; 19750 } 19751 ps.setInstalled(installed, userId); 19752 } 19753 } 19754 } 19755 // can downgrade to reader 19756 if (writeSettings) { 19757 // Save settings now 19758 mSettings.writeLPr(); 19759 } 19760 if (installedStateChanged) { 19761 mSettings.writeKernelMappingLPr(ps); 19762 } 19763 } 19764 if (removedAppId != -1) { 19765 // A user ID was deleted here. Go through all users and remove it 19766 // from KeyStore. 19767 removeKeystoreDataIfNeeded(UserHandle.USER_ALL, removedAppId); 19768 } 19769 } 19770 19771 static boolean locationIsPrivileged(File path) { 19772 try { 19773 final String privilegedAppDir = new File(Environment.getRootDirectory(), "priv-app") 19774 .getCanonicalPath(); 19775 return path.getCanonicalPath().startsWith(privilegedAppDir); 19776 } catch (IOException e) { 19777 Slog.e(TAG, "Unable to access code path " + path); 19778 } 19779 return false; 19780 } 19781 19782 /* 19783 * Tries to delete system package. 19784 */ 19785 private boolean deleteSystemPackageLIF(PackageParser.Package deletedPkg, 19786 PackageSetting deletedPs, int[] allUserHandles, int flags, PackageRemovedInfo outInfo, 19787 boolean writeSettings) { 19788 if (deletedPs.parentPackageName != null) { 19789 Slog.w(TAG, "Attempt to delete child system package " + deletedPkg.packageName); 19790 return false; 19791 } 19792 19793 final boolean applyUserRestrictions 19794 = (allUserHandles != null) && (outInfo.origUsers != null); 19795 final PackageSetting disabledPs; 19796 // Confirm if the system package has been updated 19797 // An updated system app can be deleted. This will also have to restore 19798 // the system pkg from system partition 19799 // reader 19800 synchronized (mPackages) { 19801 disabledPs = mSettings.getDisabledSystemPkgLPr(deletedPs.name); 19802 } 19803 19804 if (DEBUG_REMOVE) Slog.d(TAG, "deleteSystemPackageLI: newPs=" + deletedPkg.packageName 19805 + " disabledPs=" + disabledPs); 19806 19807 if (disabledPs == null) { 19808 Slog.w(TAG, "Attempt to delete unknown system package "+ deletedPkg.packageName); 19809 return false; 19810 } else if (DEBUG_REMOVE) { 19811 Slog.d(TAG, "Deleting system pkg from data partition"); 19812 } 19813 19814 if (DEBUG_REMOVE) { 19815 if (applyUserRestrictions) { 19816 Slog.d(TAG, "Remembering install states:"); 19817 for (int userId : allUserHandles) { 19818 final boolean finstalled = ArrayUtils.contains(outInfo.origUsers, userId); 19819 Slog.d(TAG, " u=" + userId + " inst=" + finstalled); 19820 } 19821 } 19822 } 19823 19824 // Delete the updated package 19825 outInfo.isRemovedPackageSystemUpdate = true; 19826 if (outInfo.removedChildPackages != null) { 19827 final int childCount = (deletedPs.childPackageNames != null) 19828 ? deletedPs.childPackageNames.size() : 0; 19829 for (int i = 0; i < childCount; i++) { 19830 String childPackageName = deletedPs.childPackageNames.get(i); 19831 if (disabledPs.childPackageNames != null && disabledPs.childPackageNames 19832 .contains(childPackageName)) { 19833 PackageRemovedInfo childInfo = outInfo.removedChildPackages.get( 19834 childPackageName); 19835 if (childInfo != null) { 19836 childInfo.isRemovedPackageSystemUpdate = true; 19837 } 19838 } 19839 } 19840 } 19841 19842 if (disabledPs.versionCode < deletedPs.versionCode) { 19843 // Delete data for downgrades 19844 flags &= ~PackageManager.DELETE_KEEP_DATA; 19845 } else { 19846 // Preserve data by setting flag 19847 flags |= PackageManager.DELETE_KEEP_DATA; 19848 } 19849 19850 boolean ret = deleteInstalledPackageLIF(deletedPs, true, flags, allUserHandles, 19851 outInfo, writeSettings, disabledPs.pkg); 19852 if (!ret) { 19853 return false; 19854 } 19855 19856 // writer 19857 synchronized (mPackages) { 19858 // NOTE: The system package always needs to be enabled; even if it's for 19859 // a compressed stub. If we don't, installing the system package fails 19860 // during scan [scanning checks the disabled packages]. We will reverse 19861 // this later, after we've "installed" the stub. 19862 // Reinstate the old system package 19863 enableSystemPackageLPw(disabledPs.pkg); 19864 // Remove any native libraries from the upgraded package. 19865 removeNativeBinariesLI(deletedPs); 19866 } 19867 19868 // Install the system package 19869 if (DEBUG_REMOVE) Slog.d(TAG, "Re-installing system package: " + disabledPs); 19870 try { 19871 installPackageFromSystemLIF(disabledPs.codePath, false /*isPrivileged*/, allUserHandles, 19872 outInfo.origUsers, deletedPs.getPermissionsState(), writeSettings); 19873 } catch (PackageManagerException e) { 19874 Slog.w(TAG, "Failed to restore system package:" + deletedPkg.packageName + ": " 19875 + e.getMessage()); 19876 return false; 19877 } finally { 19878 if (disabledPs.pkg.isStub) { 19879 mSettings.disableSystemPackageLPw(disabledPs.name, true /*replaced*/); 19880 } 19881 } 19882 return true; 19883 } 19884 19885 /** 19886 * Installs a package that's already on the system partition. 19887 */ 19888 private PackageParser.Package installPackageFromSystemLIF(@NonNull File codePath, 19889 boolean isPrivileged, @Nullable int[] allUserHandles, @Nullable int[] origUserHandles, 19890 @Nullable PermissionsState origPermissionState, boolean writeSettings) 19891 throws PackageManagerException { 19892 int parseFlags = mDefParseFlags 19893 | PackageParser.PARSE_MUST_BE_APK 19894 | PackageParser.PARSE_IS_SYSTEM 19895 | PackageParser.PARSE_IS_SYSTEM_DIR; 19896 if (isPrivileged || locationIsPrivileged(codePath)) { 19897 parseFlags |= PackageParser.PARSE_IS_PRIVILEGED; 19898 } 19899 19900 final PackageParser.Package newPkg = 19901 scanPackageTracedLI(codePath, parseFlags, 0 /*scanFlags*/, 0 /*currentTime*/, null); 19902 19903 try { 19904 // update shared libraries for the newly re-installed system package 19905 updateSharedLibrariesLPr(newPkg, null); 19906 } catch (PackageManagerException e) { 19907 Slog.e(TAG, "updateAllSharedLibrariesLPw failed: " + e.getMessage()); 19908 } 19909 19910 prepareAppDataAfterInstallLIF(newPkg); 19911 19912 // writer 19913 synchronized (mPackages) { 19914 PackageSetting ps = mSettings.mPackages.get(newPkg.packageName); 19915 19916 // Propagate the permissions state as we do not want to drop on the floor 19917 // runtime permissions. The update permissions method below will take 19918 // care of removing obsolete permissions and grant install permissions. 19919 if (origPermissionState != null) { 19920 ps.getPermissionsState().copyFrom(origPermissionState); 19921 } 19922 updatePermissionsLPw(newPkg.packageName, newPkg, 19923 UPDATE_PERMISSIONS_ALL | UPDATE_PERMISSIONS_REPLACE_PKG); 19924 19925 final boolean applyUserRestrictions 19926 = (allUserHandles != null) && (origUserHandles != null); 19927 if (applyUserRestrictions) { 19928 boolean installedStateChanged = false; 19929 if (DEBUG_REMOVE) { 19930 Slog.d(TAG, "Propagating install state across reinstall"); 19931 } 19932 for (int userId : allUserHandles) { 19933 final boolean installed = ArrayUtils.contains(origUserHandles, userId); 19934 if (DEBUG_REMOVE) { 19935 Slog.d(TAG, " user " + userId + " => " + installed); 19936 } 19937 if (installed != ps.getInstalled(userId)) { 19938 installedStateChanged = true; 19939 } 19940 ps.setInstalled(installed, userId); 19941 19942 mSettings.writeRuntimePermissionsForUserLPr(userId, false); 19943 } 19944 // Regardless of writeSettings we need to ensure that this restriction 19945 // state propagation is persisted 19946 mSettings.writeAllUsersPackageRestrictionsLPr(); 19947 if (installedStateChanged) { 19948 mSettings.writeKernelMappingLPr(ps); 19949 } 19950 } 19951 // can downgrade to reader here 19952 if (writeSettings) { 19953 mSettings.writeLPr(); 19954 } 19955 } 19956 return newPkg; 19957 } 19958 19959 private boolean deleteInstalledPackageLIF(PackageSetting ps, 19960 boolean deleteCodeAndResources, int flags, int[] allUserHandles, 19961 PackageRemovedInfo outInfo, boolean writeSettings, 19962 PackageParser.Package replacingPackage) { 19963 synchronized (mPackages) { 19964 if (outInfo != null) { 19965 outInfo.uid = ps.appId; 19966 } 19967 19968 if (outInfo != null && outInfo.removedChildPackages != null) { 19969 final int childCount = (ps.childPackageNames != null) 19970 ? ps.childPackageNames.size() : 0; 19971 for (int i = 0; i < childCount; i++) { 19972 String childPackageName = ps.childPackageNames.get(i); 19973 PackageSetting childPs = mSettings.mPackages.get(childPackageName); 19974 if (childPs == null) { 19975 return false; 19976 } 19977 PackageRemovedInfo childInfo = outInfo.removedChildPackages.get( 19978 childPackageName); 19979 if (childInfo != null) { 19980 childInfo.uid = childPs.appId; 19981 } 19982 } 19983 } 19984 } 19985 19986 // Delete package data from internal structures and also remove data if flag is set 19987 removePackageDataLIF(ps, allUserHandles, outInfo, flags, writeSettings); 19988 19989 // Delete the child packages data 19990 final int childCount = (ps.childPackageNames != null) ? ps.childPackageNames.size() : 0; 19991 for (int i = 0; i < childCount; i++) { 19992 PackageSetting childPs; 19993 synchronized (mPackages) { 19994 childPs = mSettings.getPackageLPr(ps.childPackageNames.get(i)); 19995 } 19996 if (childPs != null) { 19997 PackageRemovedInfo childOutInfo = (outInfo != null 19998 && outInfo.removedChildPackages != null) 19999 ? outInfo.removedChildPackages.get(childPs.name) : null; 20000 final int deleteFlags = (flags & DELETE_KEEP_DATA) != 0 20001 && (replacingPackage != null 20002 && !replacingPackage.hasChildPackage(childPs.name)) 20003 ? flags & ~DELETE_KEEP_DATA : flags; 20004 removePackageDataLIF(childPs, allUserHandles, childOutInfo, 20005 deleteFlags, writeSettings); 20006 } 20007 } 20008 20009 // Delete application code and resources only for parent packages 20010 if (ps.parentPackageName == null) { 20011 if (deleteCodeAndResources && (outInfo != null)) { 20012 outInfo.args = createInstallArgsForExisting(packageFlagsToInstallFlags(ps), 20013 ps.codePathString, ps.resourcePathString, getAppDexInstructionSets(ps)); 20014 if (DEBUG_SD_INSTALL) Slog.i(TAG, "args=" + outInfo.args); 20015 } 20016 } 20017 20018 return true; 20019 } 20020 20021 @Override 20022 public boolean setBlockUninstallForUser(String packageName, boolean blockUninstall, 20023 int userId) { 20024 mContext.enforceCallingOrSelfPermission( 20025 android.Manifest.permission.DELETE_PACKAGES, null); 20026 synchronized (mPackages) { 20027 // Cannot block uninstall of static shared libs as they are 20028 // considered a part of the using app (emulating static linking). 20029 // Also static libs are installed always on internal storage. 20030 PackageParser.Package pkg = mPackages.get(packageName); 20031 if (pkg != null && pkg.staticSharedLibName != null) { 20032 Slog.w(TAG, "Cannot block uninstall of package: " + packageName 20033 + " providing static shared library: " + pkg.staticSharedLibName); 20034 return false; 20035 } 20036 mSettings.setBlockUninstallLPw(userId, packageName, blockUninstall); 20037 mSettings.writePackageRestrictionsLPr(userId); 20038 } 20039 return true; 20040 } 20041 20042 @Override 20043 public boolean getBlockUninstallForUser(String packageName, int userId) { 20044 synchronized (mPackages) { 20045 final PackageSetting ps = mSettings.mPackages.get(packageName); 20046 if (ps == null || filterAppAccessLPr(ps, Binder.getCallingUid(), userId)) { 20047 return false; 20048 } 20049 return mSettings.getBlockUninstallLPr(userId, packageName); 20050 } 20051 } 20052 20053 @Override 20054 public boolean setRequiredForSystemUser(String packageName, boolean systemUserApp) { 20055 enforceSystemOrRoot("setRequiredForSystemUser can only be run by the system or root"); 20056 synchronized (mPackages) { 20057 PackageSetting ps = mSettings.mPackages.get(packageName); 20058 if (ps == null) { 20059 Log.w(TAG, "Package doesn't exist: " + packageName); 20060 return false; 20061 } 20062 if (systemUserApp) { 20063 ps.pkgPrivateFlags |= ApplicationInfo.PRIVATE_FLAG_REQUIRED_FOR_SYSTEM_USER; 20064 } else { 20065 ps.pkgPrivateFlags &= ~ApplicationInfo.PRIVATE_FLAG_REQUIRED_FOR_SYSTEM_USER; 20066 } 20067 mSettings.writeLPr(); 20068 } 20069 return true; 20070 } 20071 20072 /* 20073 * This method handles package deletion in general 20074 */ 20075 private boolean deletePackageLIF(String packageName, UserHandle user, 20076 boolean deleteCodeAndResources, int[] allUserHandles, int flags, 20077 PackageRemovedInfo outInfo, boolean writeSettings, 20078 PackageParser.Package replacingPackage) { 20079 if (packageName == null) { 20080 Slog.w(TAG, "Attempt to delete null packageName."); 20081 return false; 20082 } 20083 20084 if (DEBUG_REMOVE) Slog.d(TAG, "deletePackageLI: " + packageName + " user " + user); 20085 20086 PackageSetting ps; 20087 synchronized (mPackages) { 20088 ps = mSettings.mPackages.get(packageName); 20089 if (ps == null) { 20090 Slog.w(TAG, "Package named '" + packageName + "' doesn't exist."); 20091 return false; 20092 } 20093 20094 if (ps.parentPackageName != null && (!isSystemApp(ps) 20095 || (flags & PackageManager.DELETE_SYSTEM_APP) != 0)) { 20096 if (DEBUG_REMOVE) { 20097 Slog.d(TAG, "Uninstalled child package:" + packageName + " for user:" 20098 + ((user == null) ? UserHandle.USER_ALL : user)); 20099 } 20100 final int removedUserId = (user != null) ? user.getIdentifier() 20101 : UserHandle.USER_ALL; 20102 if (!clearPackageStateForUserLIF(ps, removedUserId, outInfo)) { 20103 return false; 20104 } 20105 markPackageUninstalledForUserLPw(ps, user); 20106 scheduleWritePackageRestrictionsLocked(user); 20107 return true; 20108 } 20109 } 20110 20111 if (((!isSystemApp(ps) || (flags&PackageManager.DELETE_SYSTEM_APP) != 0) && user != null 20112 && user.getIdentifier() != UserHandle.USER_ALL)) { 20113 // The caller is asking that the package only be deleted for a single 20114 // user. To do this, we just mark its uninstalled state and delete 20115 // its data. If this is a system app, we only allow this to happen if 20116 // they have set the special DELETE_SYSTEM_APP which requests different 20117 // semantics than normal for uninstalling system apps. 20118 markPackageUninstalledForUserLPw(ps, user); 20119 20120 if (!isSystemApp(ps)) { 20121 // Do not uninstall the APK if an app should be cached 20122 boolean keepUninstalledPackage = shouldKeepUninstalledPackageLPr(packageName); 20123 if (ps.isAnyInstalled(sUserManager.getUserIds()) || keepUninstalledPackage) { 20124 // Other user still have this package installed, so all 20125 // we need to do is clear this user's data and save that 20126 // it is uninstalled. 20127 if (DEBUG_REMOVE) Slog.d(TAG, "Still installed by other users"); 20128 if (!clearPackageStateForUserLIF(ps, user.getIdentifier(), outInfo)) { 20129 return false; 20130 } 20131 scheduleWritePackageRestrictionsLocked(user); 20132 return true; 20133 } else { 20134 // We need to set it back to 'installed' so the uninstall 20135 // broadcasts will be sent correctly. 20136 if (DEBUG_REMOVE) Slog.d(TAG, "Not installed by other users, full delete"); 20137 ps.setInstalled(true, user.getIdentifier()); 20138 mSettings.writeKernelMappingLPr(ps); 20139 } 20140 } else { 20141 // This is a system app, so we assume that the 20142 // other users still have this package installed, so all 20143 // we need to do is clear this user's data and save that 20144 // it is uninstalled. 20145 if (DEBUG_REMOVE) Slog.d(TAG, "Deleting system app"); 20146 if (!clearPackageStateForUserLIF(ps, user.getIdentifier(), outInfo)) { 20147 return false; 20148 } 20149 scheduleWritePackageRestrictionsLocked(user); 20150 return true; 20151 } 20152 } 20153 20154 // If we are deleting a composite package for all users, keep track 20155 // of result for each child. 20156 if (ps.childPackageNames != null && outInfo != null) { 20157 synchronized (mPackages) { 20158 final int childCount = ps.childPackageNames.size(); 20159 outInfo.removedChildPackages = new ArrayMap<>(childCount); 20160 for (int i = 0; i < childCount; i++) { 20161 String childPackageName = ps.childPackageNames.get(i); 20162 PackageRemovedInfo childInfo = new PackageRemovedInfo(this); 20163 childInfo.removedPackage = childPackageName; 20164 childInfo.installerPackageName = ps.installerPackageName; 20165 outInfo.removedChildPackages.put(childPackageName, childInfo); 20166 PackageSetting childPs = mSettings.getPackageLPr(childPackageName); 20167 if (childPs != null) { 20168 childInfo.origUsers = childPs.queryInstalledUsers(allUserHandles, true); 20169 } 20170 } 20171 } 20172 } 20173 20174 boolean ret = false; 20175 if (isSystemApp(ps)) { 20176 if (DEBUG_REMOVE) Slog.d(TAG, "Removing system package: " + ps.name); 20177 // When an updated system application is deleted we delete the existing resources 20178 // as well and fall back to existing code in system partition 20179 ret = deleteSystemPackageLIF(ps.pkg, ps, allUserHandles, flags, outInfo, writeSettings); 20180 } else { 20181 if (DEBUG_REMOVE) Slog.d(TAG, "Removing non-system package: " + ps.name); 20182 ret = deleteInstalledPackageLIF(ps, deleteCodeAndResources, flags, allUserHandles, 20183 outInfo, writeSettings, replacingPackage); 20184 } 20185 20186 // Take a note whether we deleted the package for all users 20187 if (outInfo != null) { 20188 outInfo.removedForAllUsers = mPackages.get(ps.name) == null; 20189 if (outInfo.removedChildPackages != null) { 20190 synchronized (mPackages) { 20191 final int childCount = outInfo.removedChildPackages.size(); 20192 for (int i = 0; i < childCount; i++) { 20193 PackageRemovedInfo childInfo = outInfo.removedChildPackages.valueAt(i); 20194 if (childInfo != null) { 20195 childInfo.removedForAllUsers = mPackages.get( 20196 childInfo.removedPackage) == null; 20197 } 20198 } 20199 } 20200 } 20201 // If we uninstalled an update to a system app there may be some 20202 // child packages that appeared as they are declared in the system 20203 // app but were not declared in the update. 20204 if (isSystemApp(ps)) { 20205 synchronized (mPackages) { 20206 PackageSetting updatedPs = mSettings.getPackageLPr(ps.name); 20207 final int childCount = (updatedPs.childPackageNames != null) 20208 ? updatedPs.childPackageNames.size() : 0; 20209 for (int i = 0; i < childCount; i++) { 20210 String childPackageName = updatedPs.childPackageNames.get(i); 20211 if (outInfo.removedChildPackages == null 20212 || outInfo.removedChildPackages.indexOfKey(childPackageName) < 0) { 20213 PackageSetting childPs = mSettings.getPackageLPr(childPackageName); 20214 if (childPs == null) { 20215 continue; 20216 } 20217 PackageInstalledInfo installRes = new PackageInstalledInfo(); 20218 installRes.name = childPackageName; 20219 installRes.newUsers = childPs.queryInstalledUsers(allUserHandles, true); 20220 installRes.pkg = mPackages.get(childPackageName); 20221 installRes.uid = childPs.pkg.applicationInfo.uid; 20222 if (outInfo.appearedChildPackages == null) { 20223 outInfo.appearedChildPackages = new ArrayMap<>(); 20224 } 20225 outInfo.appearedChildPackages.put(childPackageName, installRes); 20226 } 20227 } 20228 } 20229 } 20230 } 20231 20232 return ret; 20233 } 20234 20235 private void markPackageUninstalledForUserLPw(PackageSetting ps, UserHandle user) { 20236 final int[] userIds = (user == null || user.getIdentifier() == UserHandle.USER_ALL) 20237 ? sUserManager.getUserIds() : new int[] {user.getIdentifier()}; 20238 for (int nextUserId : userIds) { 20239 if (DEBUG_REMOVE) { 20240 Slog.d(TAG, "Marking package:" + ps.name + " uninstalled for user:" + nextUserId); 20241 } 20242 ps.setUserState(nextUserId, 0, COMPONENT_ENABLED_STATE_DEFAULT, 20243 false /*installed*/, 20244 true /*stopped*/, 20245 true /*notLaunched*/, 20246 false /*hidden*/, 20247 false /*suspended*/, 20248 false /*instantApp*/, 20249 false /*virtualPreload*/, 20250 null /*lastDisableAppCaller*/, 20251 null /*enabledComponents*/, 20252 null /*disabledComponents*/, 20253 ps.readUserState(nextUserId).domainVerificationStatus, 20254 0, PackageManager.INSTALL_REASON_UNKNOWN); 20255 } 20256 mSettings.writeKernelMappingLPr(ps); 20257 } 20258 20259 private boolean clearPackageStateForUserLIF(PackageSetting ps, int userId, 20260 PackageRemovedInfo outInfo) { 20261 final PackageParser.Package pkg; 20262 synchronized (mPackages) { 20263 pkg = mPackages.get(ps.name); 20264 } 20265 20266 final int[] userIds = (userId == UserHandle.USER_ALL) ? sUserManager.getUserIds() 20267 : new int[] {userId}; 20268 for (int nextUserId : userIds) { 20269 if (DEBUG_REMOVE) { 20270 Slog.d(TAG, "Updating package:" + ps.name + " install state for user:" 20271 + nextUserId); 20272 } 20273 20274 destroyAppDataLIF(pkg, userId, 20275 StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE); 20276 destroyAppProfilesLIF(pkg, userId); 20277 clearDefaultBrowserIfNeededForUser(ps.name, userId); 20278 removeKeystoreDataIfNeeded(nextUserId, ps.appId); 20279 schedulePackageCleaning(ps.name, nextUserId, false); 20280 synchronized (mPackages) { 20281 if (clearPackagePreferredActivitiesLPw(ps.name, nextUserId)) { 20282 scheduleWritePackageRestrictionsLocked(nextUserId); 20283 } 20284 resetUserChangesToRuntimePermissionsAndFlagsLPw(ps, nextUserId); 20285 } 20286 } 20287 20288 if (outInfo != null) { 20289 outInfo.removedPackage = ps.name; 20290 outInfo.installerPackageName = ps.installerPackageName; 20291 outInfo.isStaticSharedLib = pkg != null && pkg.staticSharedLibName != null; 20292 outInfo.removedAppId = ps.appId; 20293 outInfo.removedUsers = userIds; 20294 outInfo.broadcastUsers = userIds; 20295 } 20296 20297 return true; 20298 } 20299 20300 private final class ClearStorageConnection implements ServiceConnection { 20301 IMediaContainerService mContainerService; 20302 20303 @Override 20304 public void onServiceConnected(ComponentName name, IBinder service) { 20305 synchronized (this) { 20306 mContainerService = IMediaContainerService.Stub 20307 .asInterface(Binder.allowBlocking(service)); 20308 notifyAll(); 20309 } 20310 } 20311 20312 @Override 20313 public void onServiceDisconnected(ComponentName name) { 20314 } 20315 } 20316 20317 private void clearExternalStorageDataSync(String packageName, int userId, boolean allData) { 20318 if (DEFAULT_CONTAINER_PACKAGE.equals(packageName)) return; 20319 20320 final boolean mounted; 20321 if (Environment.isExternalStorageEmulated()) { 20322 mounted = true; 20323 } else { 20324 final String status = Environment.getExternalStorageState(); 20325 20326 mounted = status.equals(Environment.MEDIA_MOUNTED) 20327 || status.equals(Environment.MEDIA_MOUNTED_READ_ONLY); 20328 } 20329 20330 if (!mounted) { 20331 return; 20332 } 20333 20334 final Intent containerIntent = new Intent().setComponent(DEFAULT_CONTAINER_COMPONENT); 20335 int[] users; 20336 if (userId == UserHandle.USER_ALL) { 20337 users = sUserManager.getUserIds(); 20338 } else { 20339 users = new int[] { userId }; 20340 } 20341 final ClearStorageConnection conn = new ClearStorageConnection(); 20342 if (mContext.bindServiceAsUser( 20343 containerIntent, conn, Context.BIND_AUTO_CREATE, UserHandle.SYSTEM)) { 20344 try { 20345 for (int curUser : users) { 20346 long timeout = SystemClock.uptimeMillis() + 5000; 20347 synchronized (conn) { 20348 long now; 20349 while (conn.mContainerService == null && 20350 (now = SystemClock.uptimeMillis()) < timeout) { 20351 try { 20352 conn.wait(timeout - now); 20353 } catch (InterruptedException e) { 20354 } 20355 } 20356 } 20357 if (conn.mContainerService == null) { 20358 return; 20359 } 20360 20361 final UserEnvironment userEnv = new UserEnvironment(curUser); 20362 clearDirectory(conn.mContainerService, 20363 userEnv.buildExternalStorageAppCacheDirs(packageName)); 20364 if (allData) { 20365 clearDirectory(conn.mContainerService, 20366 userEnv.buildExternalStorageAppDataDirs(packageName)); 20367 clearDirectory(conn.mContainerService, 20368 userEnv.buildExternalStorageAppMediaDirs(packageName)); 20369 } 20370 } 20371 } finally { 20372 mContext.unbindService(conn); 20373 } 20374 } 20375 } 20376 20377 @Override 20378 public void clearApplicationProfileData(String packageName) { 20379 enforceSystemOrRoot("Only the system can clear all profile data"); 20380 20381 final PackageParser.Package pkg; 20382 synchronized (mPackages) { 20383 pkg = mPackages.get(packageName); 20384 } 20385 20386 try (PackageFreezer freezer = freezePackage(packageName, "clearApplicationProfileData")) { 20387 synchronized (mInstallLock) { 20388 clearAppProfilesLIF(pkg, UserHandle.USER_ALL); 20389 } 20390 } 20391 } 20392 20393 @Override 20394 public void clearApplicationUserData(final String packageName, 20395 final IPackageDataObserver observer, final int userId) { 20396 mContext.enforceCallingOrSelfPermission( 20397 android.Manifest.permission.CLEAR_APP_USER_DATA, null); 20398 20399 final int callingUid = Binder.getCallingUid(); 20400 enforceCrossUserPermission(callingUid, userId, 20401 true /* requireFullPermission */, false /* checkShell */, "clear application data"); 20402 20403 final PackageSetting ps = mSettings.getPackageLPr(packageName); 20404 final boolean filterApp = (ps != null && filterAppAccessLPr(ps, callingUid, userId)); 20405 if (!filterApp && mProtectedPackages.isPackageDataProtected(userId, packageName)) { 20406 throw new SecurityException("Cannot clear data for a protected package: " 20407 + packageName); 20408 } 20409 // Queue up an async operation since the package deletion may take a little while. 20410 mHandler.post(new Runnable() { 20411 public void run() { 20412 mHandler.removeCallbacks(this); 20413 final boolean succeeded; 20414 if (!filterApp) { 20415 try (PackageFreezer freezer = freezePackage(packageName, 20416 "clearApplicationUserData")) { 20417 synchronized (mInstallLock) { 20418 succeeded = clearApplicationUserDataLIF(packageName, userId); 20419 } 20420 clearExternalStorageDataSync(packageName, userId, true); 20421 synchronized (mPackages) { 20422 mInstantAppRegistry.deleteInstantApplicationMetadataLPw( 20423 packageName, userId); 20424 } 20425 } 20426 if (succeeded) { 20427 // invoke DeviceStorageMonitor's update method to clear any notifications 20428 DeviceStorageMonitorInternal dsm = LocalServices 20429 .getService(DeviceStorageMonitorInternal.class); 20430 if (dsm != null) { 20431 dsm.checkMemory(); 20432 } 20433 } 20434 } else { 20435 succeeded = false; 20436 } 20437 if (observer != null) { 20438 try { 20439 observer.onRemoveCompleted(packageName, succeeded); 20440 } catch (RemoteException e) { 20441 Log.i(TAG, "Observer no longer exists."); 20442 } 20443 } //end if observer 20444 } //end run 20445 }); 20446 } 20447 20448 private boolean clearApplicationUserDataLIF(String packageName, int userId) { 20449 if (packageName == null) { 20450 Slog.w(TAG, "Attempt to delete null packageName."); 20451 return false; 20452 } 20453 20454 // Try finding details about the requested package 20455 PackageParser.Package pkg; 20456 synchronized (mPackages) { 20457 pkg = mPackages.get(packageName); 20458 if (pkg == null) { 20459 final PackageSetting ps = mSettings.mPackages.get(packageName); 20460 if (ps != null) { 20461 pkg = ps.pkg; 20462 } 20463 } 20464 20465 if (pkg == null) { 20466 Slog.w(TAG, "Package named '" + packageName + "' doesn't exist."); 20467 return false; 20468 } 20469 20470 PackageSetting ps = (PackageSetting) pkg.mExtras; 20471 resetUserChangesToRuntimePermissionsAndFlagsLPw(ps, userId); 20472 } 20473 20474 clearAppDataLIF(pkg, userId, 20475 StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE); 20476 20477 final int appId = UserHandle.getAppId(pkg.applicationInfo.uid); 20478 removeKeystoreDataIfNeeded(userId, appId); 20479 20480 UserManagerInternal umInternal = getUserManagerInternal(); 20481 final int flags; 20482 if (umInternal.isUserUnlockingOrUnlocked(userId)) { 20483 flags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE; 20484 } else if (umInternal.isUserRunning(userId)) { 20485 flags = StorageManager.FLAG_STORAGE_DE; 20486 } else { 20487 flags = 0; 20488 } 20489 prepareAppDataContentsLIF(pkg, userId, flags); 20490 20491 return true; 20492 } 20493 20494 /** 20495 * Reverts user permission state changes (permissions and flags) in 20496 * all packages for a given user. 20497 * 20498 * @param userId The device user for which to do a reset. 20499 */ 20500 private void resetUserChangesToRuntimePermissionsAndFlagsLPw(int userId) { 20501 final int packageCount = mPackages.size(); 20502 for (int i = 0; i < packageCount; i++) { 20503 PackageParser.Package pkg = mPackages.valueAt(i); 20504 PackageSetting ps = (PackageSetting) pkg.mExtras; 20505 resetUserChangesToRuntimePermissionsAndFlagsLPw(ps, userId); 20506 } 20507 } 20508 20509 private void resetNetworkPolicies(int userId) { 20510 LocalServices.getService(NetworkPolicyManagerInternal.class).resetUserState(userId); 20511 } 20512 20513 /** 20514 * Reverts user permission state changes (permissions and flags). 20515 * 20516 * @param ps The package for which to reset. 20517 * @param userId The device user for which to do a reset. 20518 */ 20519 private void resetUserChangesToRuntimePermissionsAndFlagsLPw( 20520 final PackageSetting ps, final int userId) { 20521 if (ps.pkg == null) { 20522 return; 20523 } 20524 20525 // These are flags that can change base on user actions. 20526 final int userSettableMask = FLAG_PERMISSION_USER_SET 20527 | FLAG_PERMISSION_USER_FIXED 20528 | FLAG_PERMISSION_REVOKE_ON_UPGRADE 20529 | FLAG_PERMISSION_REVIEW_REQUIRED; 20530 20531 final int policyOrSystemFlags = FLAG_PERMISSION_SYSTEM_FIXED 20532 | FLAG_PERMISSION_POLICY_FIXED; 20533 20534 boolean writeInstallPermissions = false; 20535 boolean writeRuntimePermissions = false; 20536 20537 final int permissionCount = ps.pkg.requestedPermissions.size(); 20538 for (int i = 0; i < permissionCount; i++) { 20539 String permission = ps.pkg.requestedPermissions.get(i); 20540 20541 BasePermission bp = mSettings.mPermissions.get(permission); 20542 if (bp == null) { 20543 continue; 20544 } 20545 20546 // If shared user we just reset the state to which only this app contributed. 20547 if (ps.sharedUser != null) { 20548 boolean used = false; 20549 final int packageCount = ps.sharedUser.packages.size(); 20550 for (int j = 0; j < packageCount; j++) { 20551 PackageSetting pkg = ps.sharedUser.packages.valueAt(j); 20552 if (pkg.pkg != null && !pkg.pkg.packageName.equals(ps.pkg.packageName) 20553 && pkg.pkg.requestedPermissions.contains(permission)) { 20554 used = true; 20555 break; 20556 } 20557 } 20558 if (used) { 20559 continue; 20560 } 20561 } 20562 20563 PermissionsState permissionsState = ps.getPermissionsState(); 20564 20565 final int oldFlags = permissionsState.getPermissionFlags(bp.name, userId); 20566 20567 // Always clear the user settable flags. 20568 final boolean hasInstallState = permissionsState.getInstallPermissionState( 20569 bp.name) != null; 20570 // If permission review is enabled and this is a legacy app, mark the 20571 // permission as requiring a review as this is the initial state. 20572 int flags = 0; 20573 if (mPermissionReviewRequired 20574 && ps.pkg.applicationInfo.targetSdkVersion < Build.VERSION_CODES.M) { 20575 flags |= FLAG_PERMISSION_REVIEW_REQUIRED; 20576 } 20577 if (permissionsState.updatePermissionFlags(bp, userId, userSettableMask, flags)) { 20578 if (hasInstallState) { 20579 writeInstallPermissions = true; 20580 } else { 20581 writeRuntimePermissions = true; 20582 } 20583 } 20584 20585 // Below is only runtime permission handling. 20586 if (!bp.isRuntime()) { 20587 continue; 20588 } 20589 20590 // Never clobber system or policy. 20591 if ((oldFlags & policyOrSystemFlags) != 0) { 20592 continue; 20593 } 20594 20595 // If this permission was granted by default, make sure it is. 20596 if ((oldFlags & FLAG_PERMISSION_GRANTED_BY_DEFAULT) != 0) { 20597 if (permissionsState.grantRuntimePermission(bp, userId) 20598 != PERMISSION_OPERATION_FAILURE) { 20599 writeRuntimePermissions = true; 20600 } 20601 // If permission review is enabled the permissions for a legacy apps 20602 // are represented as constantly granted runtime ones, so don't revoke. 20603 } else if ((flags & FLAG_PERMISSION_REVIEW_REQUIRED) == 0) { 20604 // Otherwise, reset the permission. 20605 final int revokeResult = permissionsState.revokeRuntimePermission(bp, userId); 20606 switch (revokeResult) { 20607 case PERMISSION_OPERATION_SUCCESS: 20608 case PERMISSION_OPERATION_SUCCESS_GIDS_CHANGED: { 20609 writeRuntimePermissions = true; 20610 final int appId = ps.appId; 20611 mHandler.post(new Runnable() { 20612 @Override 20613 public void run() { 20614 killUid(appId, userId, KILL_APP_REASON_PERMISSIONS_REVOKED); 20615 } 20616 }); 20617 } break; 20618 } 20619 } 20620 } 20621 20622 // Synchronously write as we are taking permissions away. 20623 if (writeRuntimePermissions) { 20624 mSettings.writeRuntimePermissionsForUserLPr(userId, true); 20625 } 20626 20627 // Synchronously write as we are taking permissions away. 20628 if (writeInstallPermissions) { 20629 mSettings.writeLPr(); 20630 } 20631 } 20632 20633 /** 20634 * Remove entries from the keystore daemon. Will only remove it if the 20635 * {@code appId} is valid. 20636 */ 20637 private static void removeKeystoreDataIfNeeded(int userId, int appId) { 20638 if (appId < 0) { 20639 return; 20640 } 20641 20642 final KeyStore keyStore = KeyStore.getInstance(); 20643 if (keyStore != null) { 20644 if (userId == UserHandle.USER_ALL) { 20645 for (final int individual : sUserManager.getUserIds()) { 20646 keyStore.clearUid(UserHandle.getUid(individual, appId)); 20647 } 20648 } else { 20649 keyStore.clearUid(UserHandle.getUid(userId, appId)); 20650 } 20651 } else { 20652 Slog.w(TAG, "Could not contact keystore to clear entries for app id " + appId); 20653 } 20654 } 20655 20656 @Override 20657 public void deleteApplicationCacheFiles(final String packageName, 20658 final IPackageDataObserver observer) { 20659 final int userId = UserHandle.getCallingUserId(); 20660 deleteApplicationCacheFilesAsUser(packageName, userId, observer); 20661 } 20662 20663 @Override 20664 public void deleteApplicationCacheFilesAsUser(final String packageName, final int userId, 20665 final IPackageDataObserver observer) { 20666 final int callingUid = Binder.getCallingUid(); 20667 mContext.enforceCallingOrSelfPermission( 20668 android.Manifest.permission.DELETE_CACHE_FILES, null); 20669 enforceCrossUserPermission(callingUid, userId, 20670 /* requireFullPermission= */ true, /* checkShell= */ false, 20671 "delete application cache files"); 20672 final int hasAccessInstantApps = mContext.checkCallingOrSelfPermission( 20673 android.Manifest.permission.ACCESS_INSTANT_APPS); 20674 20675 final PackageParser.Package pkg; 20676 synchronized (mPackages) { 20677 pkg = mPackages.get(packageName); 20678 } 20679 20680 // Queue up an async operation since the package deletion may take a little while. 20681 mHandler.post(new Runnable() { 20682 public void run() { 20683 final PackageSetting ps = pkg == null ? null : (PackageSetting) pkg.mExtras; 20684 boolean doClearData = true; 20685 if (ps != null) { 20686 final boolean targetIsInstantApp = 20687 ps.getInstantApp(UserHandle.getUserId(callingUid)); 20688 doClearData = !targetIsInstantApp 20689 || hasAccessInstantApps == PackageManager.PERMISSION_GRANTED; 20690 } 20691 if (doClearData) { 20692 synchronized (mInstallLock) { 20693 final int flags = StorageManager.FLAG_STORAGE_DE 20694 | StorageManager.FLAG_STORAGE_CE; 20695 // We're only clearing cache files, so we don't care if the 20696 // app is unfrozen and still able to run 20697 clearAppDataLIF(pkg, userId, flags | Installer.FLAG_CLEAR_CACHE_ONLY); 20698 clearAppDataLIF(pkg, userId, flags | Installer.FLAG_CLEAR_CODE_CACHE_ONLY); 20699 } 20700 clearExternalStorageDataSync(packageName, userId, false); 20701 } 20702 if (observer != null) { 20703 try { 20704 observer.onRemoveCompleted(packageName, true); 20705 } catch (RemoteException e) { 20706 Log.i(TAG, "Observer no longer exists."); 20707 } 20708 } 20709 } 20710 }); 20711 } 20712 20713 @Override 20714 public void getPackageSizeInfo(final String packageName, int userHandle, 20715 final IPackageStatsObserver observer) { 20716 throw new UnsupportedOperationException( 20717 "Shame on you for calling the hidden API getPackageSizeInfo(). Shame!"); 20718 } 20719 20720 private boolean getPackageSizeInfoLI(String packageName, int userId, PackageStats stats) { 20721 final PackageSetting ps; 20722 synchronized (mPackages) { 20723 ps = mSettings.mPackages.get(packageName); 20724 if (ps == null) { 20725 Slog.w(TAG, "Failed to find settings for " + packageName); 20726 return false; 20727 } 20728 } 20729 20730 final String[] packageNames = { packageName }; 20731 final long[] ceDataInodes = { ps.getCeDataInode(userId) }; 20732 final String[] codePaths = { ps.codePathString }; 20733 20734 try { 20735 mInstaller.getAppSize(ps.volumeUuid, packageNames, userId, 0, 20736 ps.appId, ceDataInodes, codePaths, stats); 20737 20738 // For now, ignore code size of packages on system partition 20739 if (isSystemApp(ps) && !isUpdatedSystemApp(ps)) { 20740 stats.codeSize = 0; 20741 } 20742 20743 // External clients expect these to be tracked separately 20744 stats.dataSize -= stats.cacheSize; 20745 20746 } catch (InstallerException e) { 20747 Slog.w(TAG, String.valueOf(e)); 20748 return false; 20749 } 20750 20751 return true; 20752 } 20753 20754 private int getUidTargetSdkVersionLockedLPr(int uid) { 20755 Object obj = mSettings.getUserIdLPr(uid); 20756 if (obj instanceof SharedUserSetting) { 20757 final SharedUserSetting sus = (SharedUserSetting) obj; 20758 int vers = Build.VERSION_CODES.CUR_DEVELOPMENT; 20759 final Iterator<PackageSetting> it = sus.packages.iterator(); 20760 while (it.hasNext()) { 20761 final PackageSetting ps = it.next(); 20762 if (ps.pkg != null) { 20763 int v = ps.pkg.applicationInfo.targetSdkVersion; 20764 if (v < vers) vers = v; 20765 } 20766 } 20767 return vers; 20768 } else if (obj instanceof PackageSetting) { 20769 final PackageSetting ps = (PackageSetting) obj; 20770 if (ps.pkg != null) { 20771 return ps.pkg.applicationInfo.targetSdkVersion; 20772 } 20773 } 20774 return Build.VERSION_CODES.CUR_DEVELOPMENT; 20775 } 20776 20777 @Override 20778 public void addPreferredActivity(IntentFilter filter, int match, 20779 ComponentName[] set, ComponentName activity, int userId) { 20780 addPreferredActivityInternal(filter, match, set, activity, true, userId, 20781 "Adding preferred"); 20782 } 20783 20784 private void addPreferredActivityInternal(IntentFilter filter, int match, 20785 ComponentName[] set, ComponentName activity, boolean always, int userId, 20786 String opname) { 20787 // writer 20788 int callingUid = Binder.getCallingUid(); 20789 enforceCrossUserPermission(callingUid, userId, 20790 true /* requireFullPermission */, false /* checkShell */, "add preferred activity"); 20791 if (filter.countActions() == 0) { 20792 Slog.w(TAG, "Cannot set a preferred activity with no filter actions"); 20793 return; 20794 } 20795 synchronized (mPackages) { 20796 if (mContext.checkCallingOrSelfPermission( 20797 android.Manifest.permission.SET_PREFERRED_APPLICATIONS) 20798 != PackageManager.PERMISSION_GRANTED) { 20799 if (getUidTargetSdkVersionLockedLPr(callingUid) 20800 < Build.VERSION_CODES.FROYO) { 20801 Slog.w(TAG, "Ignoring addPreferredActivity() from uid " 20802 + callingUid); 20803 return; 20804 } 20805 mContext.enforceCallingOrSelfPermission( 20806 android.Manifest.permission.SET_PREFERRED_APPLICATIONS, null); 20807 } 20808 20809 PreferredIntentResolver pir = mSettings.editPreferredActivitiesLPw(userId); 20810 Slog.i(TAG, opname + " activity " + activity.flattenToShortString() + " for user " 20811 + userId + ":"); 20812 filter.dump(new LogPrinter(Log.INFO, TAG), " "); 20813 pir.addFilter(new PreferredActivity(filter, match, set, activity, always)); 20814 scheduleWritePackageRestrictionsLocked(userId); 20815 postPreferredActivityChangedBroadcast(userId); 20816 } 20817 } 20818 20819 private void postPreferredActivityChangedBroadcast(int userId) { 20820 mHandler.post(() -> { 20821 final IActivityManager am = ActivityManager.getService(); 20822 if (am == null) { 20823 return; 20824 } 20825 20826 final Intent intent = new Intent(Intent.ACTION_PREFERRED_ACTIVITY_CHANGED); 20827 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 20828 try { 20829 am.broadcastIntent(null, intent, null, null, 20830 0, null, null, null, android.app.AppOpsManager.OP_NONE, 20831 null, false, false, userId); 20832 } catch (RemoteException e) { 20833 } 20834 }); 20835 } 20836 20837 @Override 20838 public void replacePreferredActivity(IntentFilter filter, int match, 20839 ComponentName[] set, ComponentName activity, int userId) { 20840 if (filter.countActions() != 1) { 20841 throw new IllegalArgumentException( 20842 "replacePreferredActivity expects filter to have only 1 action."); 20843 } 20844 if (filter.countDataAuthorities() != 0 20845 || filter.countDataPaths() != 0 20846 || filter.countDataSchemes() > 1 20847 || filter.countDataTypes() != 0) { 20848 throw new IllegalArgumentException( 20849 "replacePreferredActivity expects filter to have no data authorities, " + 20850 "paths, or types; and at most one scheme."); 20851 } 20852 20853 final int callingUid = Binder.getCallingUid(); 20854 enforceCrossUserPermission(callingUid, userId, 20855 true /* requireFullPermission */, false /* checkShell */, 20856 "replace preferred activity"); 20857 synchronized (mPackages) { 20858 if (mContext.checkCallingOrSelfPermission( 20859 android.Manifest.permission.SET_PREFERRED_APPLICATIONS) 20860 != PackageManager.PERMISSION_GRANTED) { 20861 if (getUidTargetSdkVersionLockedLPr(callingUid) 20862 < Build.VERSION_CODES.FROYO) { 20863 Slog.w(TAG, "Ignoring replacePreferredActivity() from uid " 20864 + Binder.getCallingUid()); 20865 return; 20866 } 20867 mContext.enforceCallingOrSelfPermission( 20868 android.Manifest.permission.SET_PREFERRED_APPLICATIONS, null); 20869 } 20870 20871 PreferredIntentResolver pir = mSettings.mPreferredActivities.get(userId); 20872 if (pir != null) { 20873 // Get all of the existing entries that exactly match this filter. 20874 ArrayList<PreferredActivity> existing = pir.findFilters(filter); 20875 if (existing != null && existing.size() == 1) { 20876 PreferredActivity cur = existing.get(0); 20877 if (DEBUG_PREFERRED) { 20878 Slog.i(TAG, "Checking replace of preferred:"); 20879 filter.dump(new LogPrinter(Log.INFO, TAG), " "); 20880 if (!cur.mPref.mAlways) { 20881 Slog.i(TAG, " -- CUR; not mAlways!"); 20882 } else { 20883 Slog.i(TAG, " -- CUR: mMatch=" + cur.mPref.mMatch); 20884 Slog.i(TAG, " -- CUR: mSet=" 20885 + Arrays.toString(cur.mPref.mSetComponents)); 20886 Slog.i(TAG, " -- CUR: mComponent=" + cur.mPref.mShortComponent); 20887 Slog.i(TAG, " -- NEW: mMatch=" 20888 + (match&IntentFilter.MATCH_CATEGORY_MASK)); 20889 Slog.i(TAG, " -- CUR: mSet=" + Arrays.toString(set)); 20890 Slog.i(TAG, " -- CUR: mComponent=" + activity.flattenToShortString()); 20891 } 20892 } 20893 if (cur.mPref.mAlways && cur.mPref.mComponent.equals(activity) 20894 && cur.mPref.mMatch == (match&IntentFilter.MATCH_CATEGORY_MASK) 20895 && cur.mPref.sameSet(set)) { 20896 // Setting the preferred activity to what it happens to be already 20897 if (DEBUG_PREFERRED) { 20898 Slog.i(TAG, "Replacing with same preferred activity " 20899 + cur.mPref.mShortComponent + " for user " 20900 + userId + ":"); 20901 filter.dump(new LogPrinter(Log.INFO, TAG), " "); 20902 } 20903 return; 20904 } 20905 } 20906 20907 if (existing != null) { 20908 if (DEBUG_PREFERRED) { 20909 Slog.i(TAG, existing.size() + " existing preferred matches for:"); 20910 filter.dump(new LogPrinter(Log.INFO, TAG), " "); 20911 } 20912 for (int i = 0; i < existing.size(); i++) { 20913 PreferredActivity pa = existing.get(i); 20914 if (DEBUG_PREFERRED) { 20915 Slog.i(TAG, "Removing existing preferred activity " 20916 + pa.mPref.mComponent + ":"); 20917 pa.dump(new LogPrinter(Log.INFO, TAG), " "); 20918 } 20919 pir.removeFilter(pa); 20920 } 20921 } 20922 } 20923 addPreferredActivityInternal(filter, match, set, activity, true, userId, 20924 "Replacing preferred"); 20925 } 20926 } 20927 20928 @Override 20929 public void clearPackagePreferredActivities(String packageName) { 20930 final int callingUid = Binder.getCallingUid(); 20931 if (getInstantAppPackageName(callingUid) != null) { 20932 return; 20933 } 20934 // writer 20935 synchronized (mPackages) { 20936 PackageParser.Package pkg = mPackages.get(packageName); 20937 if (pkg == null || pkg.applicationInfo.uid != callingUid) { 20938 if (mContext.checkCallingOrSelfPermission( 20939 android.Manifest.permission.SET_PREFERRED_APPLICATIONS) 20940 != PackageManager.PERMISSION_GRANTED) { 20941 if (getUidTargetSdkVersionLockedLPr(callingUid) 20942 < Build.VERSION_CODES.FROYO) { 20943 Slog.w(TAG, "Ignoring clearPackagePreferredActivities() from uid " 20944 + callingUid); 20945 return; 20946 } 20947 mContext.enforceCallingOrSelfPermission( 20948 android.Manifest.permission.SET_PREFERRED_APPLICATIONS, null); 20949 } 20950 } 20951 final PackageSetting ps = mSettings.getPackageLPr(packageName); 20952 if (ps != null 20953 && filterAppAccessLPr(ps, callingUid, UserHandle.getUserId(callingUid))) { 20954 return; 20955 } 20956 int user = UserHandle.getCallingUserId(); 20957 if (clearPackagePreferredActivitiesLPw(packageName, user)) { 20958 scheduleWritePackageRestrictionsLocked(user); 20959 } 20960 } 20961 } 20962 20963 /** This method takes a specific user id as well as UserHandle.USER_ALL. */ 20964 boolean clearPackagePreferredActivitiesLPw(String packageName, int userId) { 20965 ArrayList<PreferredActivity> removed = null; 20966 boolean changed = false; 20967 for (int i=0; i<mSettings.mPreferredActivities.size(); i++) { 20968 final int thisUserId = mSettings.mPreferredActivities.keyAt(i); 20969 PreferredIntentResolver pir = mSettings.mPreferredActivities.valueAt(i); 20970 if (userId != UserHandle.USER_ALL && userId != thisUserId) { 20971 continue; 20972 } 20973 Iterator<PreferredActivity> it = pir.filterIterator(); 20974 while (it.hasNext()) { 20975 PreferredActivity pa = it.next(); 20976 // Mark entry for removal only if it matches the package name 20977 // and the entry is of type "always". 20978 if (packageName == null || 20979 (pa.mPref.mComponent.getPackageName().equals(packageName) 20980 && pa.mPref.mAlways)) { 20981 if (removed == null) { 20982 removed = new ArrayList<PreferredActivity>(); 20983 } 20984 removed.add(pa); 20985 } 20986 } 20987 if (removed != null) { 20988 for (int j=0; j<removed.size(); j++) { 20989 PreferredActivity pa = removed.get(j); 20990 pir.removeFilter(pa); 20991 } 20992 changed = true; 20993 } 20994 } 20995 if (changed) { 20996 postPreferredActivityChangedBroadcast(userId); 20997 } 20998 return changed; 20999 } 21000 21001 /** This method takes a specific user id as well as UserHandle.USER_ALL. */ 21002 private void clearIntentFilterVerificationsLPw(int userId) { 21003 final int packageCount = mPackages.size(); 21004 for (int i = 0; i < packageCount; i++) { 21005 PackageParser.Package pkg = mPackages.valueAt(i); 21006 clearIntentFilterVerificationsLPw(pkg.packageName, userId); 21007 } 21008 } 21009 21010 /** This method takes a specific user id as well as UserHandle.USER_ALL. */ 21011 void clearIntentFilterVerificationsLPw(String packageName, int userId) { 21012 if (userId == UserHandle.USER_ALL) { 21013 if (mSettings.removeIntentFilterVerificationLPw(packageName, 21014 sUserManager.getUserIds())) { 21015 for (int oneUserId : sUserManager.getUserIds()) { 21016 scheduleWritePackageRestrictionsLocked(oneUserId); 21017 } 21018 } 21019 } else { 21020 if (mSettings.removeIntentFilterVerificationLPw(packageName, userId)) { 21021 scheduleWritePackageRestrictionsLocked(userId); 21022 } 21023 } 21024 } 21025 21026 /** Clears state for all users, and touches intent filter verification policy */ 21027 void clearDefaultBrowserIfNeeded(String packageName) { 21028 for (int oneUserId : sUserManager.getUserIds()) { 21029 clearDefaultBrowserIfNeededForUser(packageName, oneUserId); 21030 } 21031 } 21032 21033 private void clearDefaultBrowserIfNeededForUser(String packageName, int userId) { 21034 final String defaultBrowserPackageName = getDefaultBrowserPackageName(userId); 21035 if (!TextUtils.isEmpty(defaultBrowserPackageName)) { 21036 if (packageName.equals(defaultBrowserPackageName)) { 21037 setDefaultBrowserPackageName(null, userId); 21038 } 21039 } 21040 } 21041 21042 @Override 21043 public void resetApplicationPreferences(int userId) { 21044 mContext.enforceCallingOrSelfPermission( 21045 android.Manifest.permission.SET_PREFERRED_APPLICATIONS, null); 21046 final long identity = Binder.clearCallingIdentity(); 21047 // writer 21048 try { 21049 synchronized (mPackages) { 21050 clearPackagePreferredActivitiesLPw(null, userId); 21051 mSettings.applyDefaultPreferredAppsLPw(this, userId); 21052 // TODO: We have to reset the default SMS and Phone. This requires 21053 // significant refactoring to keep all default apps in the package 21054 // manager (cleaner but more work) or have the services provide 21055 // callbacks to the package manager to request a default app reset. 21056 applyFactoryDefaultBrowserLPw(userId); 21057 clearIntentFilterVerificationsLPw(userId); 21058 primeDomainVerificationsLPw(userId); 21059 resetUserChangesToRuntimePermissionsAndFlagsLPw(userId); 21060 scheduleWritePackageRestrictionsLocked(userId); 21061 } 21062 resetNetworkPolicies(userId); 21063 } finally { 21064 Binder.restoreCallingIdentity(identity); 21065 } 21066 } 21067 21068 @Override 21069 public int getPreferredActivities(List<IntentFilter> outFilters, 21070 List<ComponentName> outActivities, String packageName) { 21071 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 21072 return 0; 21073 } 21074 int num = 0; 21075 final int userId = UserHandle.getCallingUserId(); 21076 // reader 21077 synchronized (mPackages) { 21078 PreferredIntentResolver pir = mSettings.mPreferredActivities.get(userId); 21079 if (pir != null) { 21080 final Iterator<PreferredActivity> it = pir.filterIterator(); 21081 while (it.hasNext()) { 21082 final PreferredActivity pa = it.next(); 21083 if (packageName == null 21084 || (pa.mPref.mComponent.getPackageName().equals(packageName) 21085 && pa.mPref.mAlways)) { 21086 if (outFilters != null) { 21087 outFilters.add(new IntentFilter(pa)); 21088 } 21089 if (outActivities != null) { 21090 outActivities.add(pa.mPref.mComponent); 21091 } 21092 } 21093 } 21094 } 21095 } 21096 21097 return num; 21098 } 21099 21100 @Override 21101 public void addPersistentPreferredActivity(IntentFilter filter, ComponentName activity, 21102 int userId) { 21103 int callingUid = Binder.getCallingUid(); 21104 if (callingUid != Process.SYSTEM_UID) { 21105 throw new SecurityException( 21106 "addPersistentPreferredActivity can only be run by the system"); 21107 } 21108 if (filter.countActions() == 0) { 21109 Slog.w(TAG, "Cannot set a preferred activity with no filter actions"); 21110 return; 21111 } 21112 synchronized (mPackages) { 21113 Slog.i(TAG, "Adding persistent preferred activity " + activity + " for user " + userId + 21114 ":"); 21115 filter.dump(new LogPrinter(Log.INFO, TAG), " "); 21116 mSettings.editPersistentPreferredActivitiesLPw(userId).addFilter( 21117 new PersistentPreferredActivity(filter, activity)); 21118 scheduleWritePackageRestrictionsLocked(userId); 21119 postPreferredActivityChangedBroadcast(userId); 21120 } 21121 } 21122 21123 @Override 21124 public void clearPackagePersistentPreferredActivities(String packageName, int userId) { 21125 int callingUid = Binder.getCallingUid(); 21126 if (callingUid != Process.SYSTEM_UID) { 21127 throw new SecurityException( 21128 "clearPackagePersistentPreferredActivities can only be run by the system"); 21129 } 21130 ArrayList<PersistentPreferredActivity> removed = null; 21131 boolean changed = false; 21132 synchronized (mPackages) { 21133 for (int i=0; i<mSettings.mPersistentPreferredActivities.size(); i++) { 21134 final int thisUserId = mSettings.mPersistentPreferredActivities.keyAt(i); 21135 PersistentPreferredIntentResolver ppir = mSettings.mPersistentPreferredActivities 21136 .valueAt(i); 21137 if (userId != thisUserId) { 21138 continue; 21139 } 21140 Iterator<PersistentPreferredActivity> it = ppir.filterIterator(); 21141 while (it.hasNext()) { 21142 PersistentPreferredActivity ppa = it.next(); 21143 // Mark entry for removal only if it matches the package name. 21144 if (ppa.mComponent.getPackageName().equals(packageName)) { 21145 if (removed == null) { 21146 removed = new ArrayList<PersistentPreferredActivity>(); 21147 } 21148 removed.add(ppa); 21149 } 21150 } 21151 if (removed != null) { 21152 for (int j=0; j<removed.size(); j++) { 21153 PersistentPreferredActivity ppa = removed.get(j); 21154 ppir.removeFilter(ppa); 21155 } 21156 changed = true; 21157 } 21158 } 21159 21160 if (changed) { 21161 scheduleWritePackageRestrictionsLocked(userId); 21162 postPreferredActivityChangedBroadcast(userId); 21163 } 21164 } 21165 } 21166 21167 /** 21168 * Common machinery for picking apart a restored XML blob and passing 21169 * it to a caller-supplied functor to be applied to the running system. 21170 */ 21171 private void restoreFromXml(XmlPullParser parser, int userId, 21172 String expectedStartTag, BlobXmlRestorer functor) 21173 throws IOException, XmlPullParserException { 21174 int type; 21175 while ((type = parser.next()) != XmlPullParser.START_TAG 21176 && type != XmlPullParser.END_DOCUMENT) { 21177 } 21178 if (type != XmlPullParser.START_TAG) { 21179 // oops didn't find a start tag?! 21180 if (DEBUG_BACKUP) { 21181 Slog.e(TAG, "Didn't find start tag during restore"); 21182 } 21183 return; 21184 } 21185Slog.v(TAG, ":: restoreFromXml() : got to tag " + parser.getName()); 21186 // this is supposed to be TAG_PREFERRED_BACKUP 21187 if (!expectedStartTag.equals(parser.getName())) { 21188 if (DEBUG_BACKUP) { 21189 Slog.e(TAG, "Found unexpected tag " + parser.getName()); 21190 } 21191 return; 21192 } 21193 21194 // skip interfering stuff, then we're aligned with the backing implementation 21195 while ((type = parser.next()) == XmlPullParser.TEXT) { } 21196Slog.v(TAG, ":: stepped forward, applying functor at tag " + parser.getName()); 21197 functor.apply(parser, userId); 21198 } 21199 21200 private interface BlobXmlRestorer { 21201 public void apply(XmlPullParser parser, int userId) throws IOException, XmlPullParserException; 21202 } 21203 21204 /** 21205 * Non-Binder method, support for the backup/restore mechanism: write the 21206 * full set of preferred activities in its canonical XML format. Returns the 21207 * XML output as a byte array, or null if there is none. 21208 */ 21209 @Override 21210 public byte[] getPreferredActivityBackup(int userId) { 21211 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 21212 throw new SecurityException("Only the system may call getPreferredActivityBackup()"); 21213 } 21214 21215 ByteArrayOutputStream dataStream = new ByteArrayOutputStream(); 21216 try { 21217 final XmlSerializer serializer = new FastXmlSerializer(); 21218 serializer.setOutput(dataStream, StandardCharsets.UTF_8.name()); 21219 serializer.startDocument(null, true); 21220 serializer.startTag(null, TAG_PREFERRED_BACKUP); 21221 21222 synchronized (mPackages) { 21223 mSettings.writePreferredActivitiesLPr(serializer, userId, true); 21224 } 21225 21226 serializer.endTag(null, TAG_PREFERRED_BACKUP); 21227 serializer.endDocument(); 21228 serializer.flush(); 21229 } catch (Exception e) { 21230 if (DEBUG_BACKUP) { 21231 Slog.e(TAG, "Unable to write preferred activities for backup", e); 21232 } 21233 return null; 21234 } 21235 21236 return dataStream.toByteArray(); 21237 } 21238 21239 @Override 21240 public void restorePreferredActivities(byte[] backup, int userId) { 21241 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 21242 throw new SecurityException("Only the system may call restorePreferredActivities()"); 21243 } 21244 21245 try { 21246 final XmlPullParser parser = Xml.newPullParser(); 21247 parser.setInput(new ByteArrayInputStream(backup), StandardCharsets.UTF_8.name()); 21248 restoreFromXml(parser, userId, TAG_PREFERRED_BACKUP, 21249 new BlobXmlRestorer() { 21250 @Override 21251 public void apply(XmlPullParser parser, int userId) 21252 throws XmlPullParserException, IOException { 21253 synchronized (mPackages) { 21254 mSettings.readPreferredActivitiesLPw(parser, userId); 21255 } 21256 } 21257 } ); 21258 } catch (Exception e) { 21259 if (DEBUG_BACKUP) { 21260 Slog.e(TAG, "Exception restoring preferred activities: " + e.getMessage()); 21261 } 21262 } 21263 } 21264 21265 /** 21266 * Non-Binder method, support for the backup/restore mechanism: write the 21267 * default browser (etc) settings in its canonical XML format. Returns the default 21268 * browser XML representation as a byte array, or null if there is none. 21269 */ 21270 @Override 21271 public byte[] getDefaultAppsBackup(int userId) { 21272 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 21273 throw new SecurityException("Only the system may call getDefaultAppsBackup()"); 21274 } 21275 21276 ByteArrayOutputStream dataStream = new ByteArrayOutputStream(); 21277 try { 21278 final XmlSerializer serializer = new FastXmlSerializer(); 21279 serializer.setOutput(dataStream, StandardCharsets.UTF_8.name()); 21280 serializer.startDocument(null, true); 21281 serializer.startTag(null, TAG_DEFAULT_APPS); 21282 21283 synchronized (mPackages) { 21284 mSettings.writeDefaultAppsLPr(serializer, userId); 21285 } 21286 21287 serializer.endTag(null, TAG_DEFAULT_APPS); 21288 serializer.endDocument(); 21289 serializer.flush(); 21290 } catch (Exception e) { 21291 if (DEBUG_BACKUP) { 21292 Slog.e(TAG, "Unable to write default apps for backup", e); 21293 } 21294 return null; 21295 } 21296 21297 return dataStream.toByteArray(); 21298 } 21299 21300 @Override 21301 public void restoreDefaultApps(byte[] backup, int userId) { 21302 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 21303 throw new SecurityException("Only the system may call restoreDefaultApps()"); 21304 } 21305 21306 try { 21307 final XmlPullParser parser = Xml.newPullParser(); 21308 parser.setInput(new ByteArrayInputStream(backup), StandardCharsets.UTF_8.name()); 21309 restoreFromXml(parser, userId, TAG_DEFAULT_APPS, 21310 new BlobXmlRestorer() { 21311 @Override 21312 public void apply(XmlPullParser parser, int userId) 21313 throws XmlPullParserException, IOException { 21314 synchronized (mPackages) { 21315 mSettings.readDefaultAppsLPw(parser, userId); 21316 } 21317 } 21318 } ); 21319 } catch (Exception e) { 21320 if (DEBUG_BACKUP) { 21321 Slog.e(TAG, "Exception restoring default apps: " + e.getMessage()); 21322 } 21323 } 21324 } 21325 21326 @Override 21327 public byte[] getIntentFilterVerificationBackup(int userId) { 21328 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 21329 throw new SecurityException("Only the system may call getIntentFilterVerificationBackup()"); 21330 } 21331 21332 ByteArrayOutputStream dataStream = new ByteArrayOutputStream(); 21333 try { 21334 final XmlSerializer serializer = new FastXmlSerializer(); 21335 serializer.setOutput(dataStream, StandardCharsets.UTF_8.name()); 21336 serializer.startDocument(null, true); 21337 serializer.startTag(null, TAG_INTENT_FILTER_VERIFICATION); 21338 21339 synchronized (mPackages) { 21340 mSettings.writeAllDomainVerificationsLPr(serializer, userId); 21341 } 21342 21343 serializer.endTag(null, TAG_INTENT_FILTER_VERIFICATION); 21344 serializer.endDocument(); 21345 serializer.flush(); 21346 } catch (Exception e) { 21347 if (DEBUG_BACKUP) { 21348 Slog.e(TAG, "Unable to write default apps for backup", e); 21349 } 21350 return null; 21351 } 21352 21353 return dataStream.toByteArray(); 21354 } 21355 21356 @Override 21357 public void restoreIntentFilterVerification(byte[] backup, int userId) { 21358 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 21359 throw new SecurityException("Only the system may call restorePreferredActivities()"); 21360 } 21361 21362 try { 21363 final XmlPullParser parser = Xml.newPullParser(); 21364 parser.setInput(new ByteArrayInputStream(backup), StandardCharsets.UTF_8.name()); 21365 restoreFromXml(parser, userId, TAG_INTENT_FILTER_VERIFICATION, 21366 new BlobXmlRestorer() { 21367 @Override 21368 public void apply(XmlPullParser parser, int userId) 21369 throws XmlPullParserException, IOException { 21370 synchronized (mPackages) { 21371 mSettings.readAllDomainVerificationsLPr(parser, userId); 21372 mSettings.writeLPr(); 21373 } 21374 } 21375 } ); 21376 } catch (Exception e) { 21377 if (DEBUG_BACKUP) { 21378 Slog.e(TAG, "Exception restoring preferred activities: " + e.getMessage()); 21379 } 21380 } 21381 } 21382 21383 @Override 21384 public byte[] getPermissionGrantBackup(int userId) { 21385 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 21386 throw new SecurityException("Only the system may call getPermissionGrantBackup()"); 21387 } 21388 21389 ByteArrayOutputStream dataStream = new ByteArrayOutputStream(); 21390 try { 21391 final XmlSerializer serializer = new FastXmlSerializer(); 21392 serializer.setOutput(dataStream, StandardCharsets.UTF_8.name()); 21393 serializer.startDocument(null, true); 21394 serializer.startTag(null, TAG_PERMISSION_BACKUP); 21395 21396 synchronized (mPackages) { 21397 serializeRuntimePermissionGrantsLPr(serializer, userId); 21398 } 21399 21400 serializer.endTag(null, TAG_PERMISSION_BACKUP); 21401 serializer.endDocument(); 21402 serializer.flush(); 21403 } catch (Exception e) { 21404 if (DEBUG_BACKUP) { 21405 Slog.e(TAG, "Unable to write default apps for backup", e); 21406 } 21407 return null; 21408 } 21409 21410 return dataStream.toByteArray(); 21411 } 21412 21413 @Override 21414 public void restorePermissionGrants(byte[] backup, int userId) { 21415 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 21416 throw new SecurityException("Only the system may call restorePermissionGrants()"); 21417 } 21418 21419 try { 21420 final XmlPullParser parser = Xml.newPullParser(); 21421 parser.setInput(new ByteArrayInputStream(backup), StandardCharsets.UTF_8.name()); 21422 restoreFromXml(parser, userId, TAG_PERMISSION_BACKUP, 21423 new BlobXmlRestorer() { 21424 @Override 21425 public void apply(XmlPullParser parser, int userId) 21426 throws XmlPullParserException, IOException { 21427 synchronized (mPackages) { 21428 processRestoredPermissionGrantsLPr(parser, userId); 21429 } 21430 } 21431 } ); 21432 } catch (Exception e) { 21433 if (DEBUG_BACKUP) { 21434 Slog.e(TAG, "Exception restoring preferred activities: " + e.getMessage()); 21435 } 21436 } 21437 } 21438 21439 private void serializeRuntimePermissionGrantsLPr(XmlSerializer serializer, final int userId) 21440 throws IOException { 21441 serializer.startTag(null, TAG_ALL_GRANTS); 21442 21443 final int N = mSettings.mPackages.size(); 21444 for (int i = 0; i < N; i++) { 21445 final PackageSetting ps = mSettings.mPackages.valueAt(i); 21446 boolean pkgGrantsKnown = false; 21447 21448 PermissionsState packagePerms = ps.getPermissionsState(); 21449 21450 for (PermissionState state : packagePerms.getRuntimePermissionStates(userId)) { 21451 final int grantFlags = state.getFlags(); 21452 // only look at grants that are not system/policy fixed 21453 if ((grantFlags & SYSTEM_RUNTIME_GRANT_MASK) == 0) { 21454 final boolean isGranted = state.isGranted(); 21455 // And only back up the user-twiddled state bits 21456 if (isGranted || (grantFlags & USER_RUNTIME_GRANT_MASK) != 0) { 21457 final String packageName = mSettings.mPackages.keyAt(i); 21458 if (!pkgGrantsKnown) { 21459 serializer.startTag(null, TAG_GRANT); 21460 serializer.attribute(null, ATTR_PACKAGE_NAME, packageName); 21461 pkgGrantsKnown = true; 21462 } 21463 21464 final boolean userSet = 21465 (grantFlags & FLAG_PERMISSION_USER_SET) != 0; 21466 final boolean userFixed = 21467 (grantFlags & FLAG_PERMISSION_USER_FIXED) != 0; 21468 final boolean revoke = 21469 (grantFlags & FLAG_PERMISSION_REVOKE_ON_UPGRADE) != 0; 21470 21471 serializer.startTag(null, TAG_PERMISSION); 21472 serializer.attribute(null, ATTR_PERMISSION_NAME, state.getName()); 21473 if (isGranted) { 21474 serializer.attribute(null, ATTR_IS_GRANTED, "true"); 21475 } 21476 if (userSet) { 21477 serializer.attribute(null, ATTR_USER_SET, "true"); 21478 } 21479 if (userFixed) { 21480 serializer.attribute(null, ATTR_USER_FIXED, "true"); 21481 } 21482 if (revoke) { 21483 serializer.attribute(null, ATTR_REVOKE_ON_UPGRADE, "true"); 21484 } 21485 serializer.endTag(null, TAG_PERMISSION); 21486 } 21487 } 21488 } 21489 21490 if (pkgGrantsKnown) { 21491 serializer.endTag(null, TAG_GRANT); 21492 } 21493 } 21494 21495 serializer.endTag(null, TAG_ALL_GRANTS); 21496 } 21497 21498 private void processRestoredPermissionGrantsLPr(XmlPullParser parser, int userId) 21499 throws XmlPullParserException, IOException { 21500 String pkgName = null; 21501 int outerDepth = parser.getDepth(); 21502 int type; 21503 while ((type = parser.next()) != XmlPullParser.END_DOCUMENT 21504 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) { 21505 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) { 21506 continue; 21507 } 21508 21509 final String tagName = parser.getName(); 21510 if (tagName.equals(TAG_GRANT)) { 21511 pkgName = parser.getAttributeValue(null, ATTR_PACKAGE_NAME); 21512 if (DEBUG_BACKUP) { 21513 Slog.v(TAG, "+++ Restoring grants for package " + pkgName); 21514 } 21515 } else if (tagName.equals(TAG_PERMISSION)) { 21516 21517 final boolean isGranted = "true".equals(parser.getAttributeValue(null, ATTR_IS_GRANTED)); 21518 final String permName = parser.getAttributeValue(null, ATTR_PERMISSION_NAME); 21519 21520 int newFlagSet = 0; 21521 if ("true".equals(parser.getAttributeValue(null, ATTR_USER_SET))) { 21522 newFlagSet |= FLAG_PERMISSION_USER_SET; 21523 } 21524 if ("true".equals(parser.getAttributeValue(null, ATTR_USER_FIXED))) { 21525 newFlagSet |= FLAG_PERMISSION_USER_FIXED; 21526 } 21527 if ("true".equals(parser.getAttributeValue(null, ATTR_REVOKE_ON_UPGRADE))) { 21528 newFlagSet |= FLAG_PERMISSION_REVOKE_ON_UPGRADE; 21529 } 21530 if (DEBUG_BACKUP) { 21531 Slog.v(TAG, " + Restoring grant: pkg=" + pkgName + " perm=" + permName 21532 + " granted=" + isGranted + " bits=0x" + Integer.toHexString(newFlagSet)); 21533 } 21534 final PackageSetting ps = mSettings.mPackages.get(pkgName); 21535 if (ps != null) { 21536 // Already installed so we apply the grant immediately 21537 if (DEBUG_BACKUP) { 21538 Slog.v(TAG, " + already installed; applying"); 21539 } 21540 PermissionsState perms = ps.getPermissionsState(); 21541 BasePermission bp = mSettings.mPermissions.get(permName); 21542 if (bp != null) { 21543 if (isGranted) { 21544 perms.grantRuntimePermission(bp, userId); 21545 } 21546 if (newFlagSet != 0) { 21547 perms.updatePermissionFlags(bp, userId, USER_RUNTIME_GRANT_MASK, newFlagSet); 21548 } 21549 } 21550 } else { 21551 // Need to wait for post-restore install to apply the grant 21552 if (DEBUG_BACKUP) { 21553 Slog.v(TAG, " - not yet installed; saving for later"); 21554 } 21555 mSettings.processRestoredPermissionGrantLPr(pkgName, permName, 21556 isGranted, newFlagSet, userId); 21557 } 21558 } else { 21559 PackageManagerService.reportSettingsProblem(Log.WARN, 21560 "Unknown element under <" + TAG_PERMISSION_BACKUP + ">: " + tagName); 21561 XmlUtils.skipCurrentTag(parser); 21562 } 21563 } 21564 21565 scheduleWriteSettingsLocked(); 21566 mSettings.writeRuntimePermissionsForUserLPr(userId, false); 21567 } 21568 21569 @Override 21570 public void addCrossProfileIntentFilter(IntentFilter intentFilter, String ownerPackage, 21571 int sourceUserId, int targetUserId, int flags) { 21572 mContext.enforceCallingOrSelfPermission( 21573 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, null); 21574 int callingUid = Binder.getCallingUid(); 21575 enforceOwnerRights(ownerPackage, callingUid); 21576 enforceShellRestriction(UserManager.DISALLOW_DEBUGGING_FEATURES, callingUid, sourceUserId); 21577 if (intentFilter.countActions() == 0) { 21578 Slog.w(TAG, "Cannot set a crossProfile intent filter with no filter actions"); 21579 return; 21580 } 21581 synchronized (mPackages) { 21582 CrossProfileIntentFilter newFilter = new CrossProfileIntentFilter(intentFilter, 21583 ownerPackage, targetUserId, flags); 21584 CrossProfileIntentResolver resolver = 21585 mSettings.editCrossProfileIntentResolverLPw(sourceUserId); 21586 ArrayList<CrossProfileIntentFilter> existing = resolver.findFilters(intentFilter); 21587 // We have all those whose filter is equal. Now checking if the rest is equal as well. 21588 if (existing != null) { 21589 int size = existing.size(); 21590 for (int i = 0; i < size; i++) { 21591 if (newFilter.equalsIgnoreFilter(existing.get(i))) { 21592 return; 21593 } 21594 } 21595 } 21596 resolver.addFilter(newFilter); 21597 scheduleWritePackageRestrictionsLocked(sourceUserId); 21598 } 21599 } 21600 21601 @Override 21602 public void clearCrossProfileIntentFilters(int sourceUserId, String ownerPackage) { 21603 mContext.enforceCallingOrSelfPermission( 21604 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, null); 21605 final int callingUid = Binder.getCallingUid(); 21606 enforceOwnerRights(ownerPackage, callingUid); 21607 enforceShellRestriction(UserManager.DISALLOW_DEBUGGING_FEATURES, callingUid, sourceUserId); 21608 synchronized (mPackages) { 21609 CrossProfileIntentResolver resolver = 21610 mSettings.editCrossProfileIntentResolverLPw(sourceUserId); 21611 ArraySet<CrossProfileIntentFilter> set = 21612 new ArraySet<CrossProfileIntentFilter>(resolver.filterSet()); 21613 for (CrossProfileIntentFilter filter : set) { 21614 if (filter.getOwnerPackage().equals(ownerPackage)) { 21615 resolver.removeFilter(filter); 21616 } 21617 } 21618 scheduleWritePackageRestrictionsLocked(sourceUserId); 21619 } 21620 } 21621 21622 // Enforcing that callingUid is owning pkg on userId 21623 private void enforceOwnerRights(String pkg, int callingUid) { 21624 // The system owns everything. 21625 if (UserHandle.getAppId(callingUid) == Process.SYSTEM_UID) { 21626 return; 21627 } 21628 final int callingUserId = UserHandle.getUserId(callingUid); 21629 PackageInfo pi = getPackageInfo(pkg, 0, callingUserId); 21630 if (pi == null) { 21631 throw new IllegalArgumentException("Unknown package " + pkg + " on user " 21632 + callingUserId); 21633 } 21634 if (!UserHandle.isSameApp(pi.applicationInfo.uid, callingUid)) { 21635 throw new SecurityException("Calling uid " + callingUid 21636 + " does not own package " + pkg); 21637 } 21638 } 21639 21640 @Override 21641 public ComponentName getHomeActivities(List<ResolveInfo> allHomeCandidates) { 21642 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 21643 return null; 21644 } 21645 return getHomeActivitiesAsUser(allHomeCandidates, UserHandle.getCallingUserId()); 21646 } 21647 21648 public void sendSessionCommitBroadcast(PackageInstaller.SessionInfo sessionInfo, int userId) { 21649 UserManagerService ums = UserManagerService.getInstance(); 21650 if (ums != null) { 21651 final UserInfo parent = ums.getProfileParent(userId); 21652 final int launcherUid = (parent != null) ? parent.id : userId; 21653 final ComponentName launcherComponent = getDefaultHomeActivity(launcherUid); 21654 if (launcherComponent != null) { 21655 Intent launcherIntent = new Intent(PackageInstaller.ACTION_SESSION_COMMITTED) 21656 .putExtra(PackageInstaller.EXTRA_SESSION, sessionInfo) 21657 .putExtra(Intent.EXTRA_USER, UserHandle.of(userId)) 21658 .setPackage(launcherComponent.getPackageName()); 21659 mContext.sendBroadcastAsUser(launcherIntent, UserHandle.of(launcherUid)); 21660 } 21661 } 21662 } 21663 21664 /** 21665 * Report the 'Home' activity which is currently set as "always use this one". If non is set 21666 * then reports the most likely home activity or null if there are more than one. 21667 */ 21668 private ComponentName getDefaultHomeActivity(int userId) { 21669 List<ResolveInfo> allHomeCandidates = new ArrayList<>(); 21670 ComponentName cn = getHomeActivitiesAsUser(allHomeCandidates, userId); 21671 if (cn != null) { 21672 return cn; 21673 } 21674 21675 // Find the launcher with the highest priority and return that component if there are no 21676 // other home activity with the same priority. 21677 int lastPriority = Integer.MIN_VALUE; 21678 ComponentName lastComponent = null; 21679 final int size = allHomeCandidates.size(); 21680 for (int i = 0; i < size; i++) { 21681 final ResolveInfo ri = allHomeCandidates.get(i); 21682 if (ri.priority > lastPriority) { 21683 lastComponent = ri.activityInfo.getComponentName(); 21684 lastPriority = ri.priority; 21685 } else if (ri.priority == lastPriority) { 21686 // Two components found with same priority. 21687 lastComponent = null; 21688 } 21689 } 21690 return lastComponent; 21691 } 21692 21693 private Intent getHomeIntent() { 21694 Intent intent = new Intent(Intent.ACTION_MAIN); 21695 intent.addCategory(Intent.CATEGORY_HOME); 21696 intent.addCategory(Intent.CATEGORY_DEFAULT); 21697 return intent; 21698 } 21699 21700 private IntentFilter getHomeFilter() { 21701 IntentFilter filter = new IntentFilter(Intent.ACTION_MAIN); 21702 filter.addCategory(Intent.CATEGORY_HOME); 21703 filter.addCategory(Intent.CATEGORY_DEFAULT); 21704 return filter; 21705 } 21706 21707 ComponentName getHomeActivitiesAsUser(List<ResolveInfo> allHomeCandidates, 21708 int userId) { 21709 Intent intent = getHomeIntent(); 21710 List<ResolveInfo> list = queryIntentActivitiesInternal(intent, null, 21711 PackageManager.GET_META_DATA, userId); 21712 ResolveInfo preferred = findPreferredActivity(intent, null, 0, list, 0, 21713 true, false, false, userId); 21714 21715 allHomeCandidates.clear(); 21716 if (list != null) { 21717 for (ResolveInfo ri : list) { 21718 allHomeCandidates.add(ri); 21719 } 21720 } 21721 return (preferred == null || preferred.activityInfo == null) 21722 ? null 21723 : new ComponentName(preferred.activityInfo.packageName, 21724 preferred.activityInfo.name); 21725 } 21726 21727 @Override 21728 public void setHomeActivity(ComponentName comp, int userId) { 21729 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 21730 return; 21731 } 21732 ArrayList<ResolveInfo> homeActivities = new ArrayList<>(); 21733 getHomeActivitiesAsUser(homeActivities, userId); 21734 21735 boolean found = false; 21736 21737 final int size = homeActivities.size(); 21738 final ComponentName[] set = new ComponentName[size]; 21739 for (int i = 0; i < size; i++) { 21740 final ResolveInfo candidate = homeActivities.get(i); 21741 final ActivityInfo info = candidate.activityInfo; 21742 final ComponentName activityName = new ComponentName(info.packageName, info.name); 21743 set[i] = activityName; 21744 if (!found && activityName.equals(comp)) { 21745 found = true; 21746 } 21747 } 21748 if (!found) { 21749 throw new IllegalArgumentException("Component " + comp + " cannot be home on user " 21750 + userId); 21751 } 21752 replacePreferredActivity(getHomeFilter(), IntentFilter.MATCH_CATEGORY_EMPTY, 21753 set, comp, userId); 21754 } 21755 21756 private @Nullable String getSetupWizardPackageName() { 21757 final Intent intent = new Intent(Intent.ACTION_MAIN); 21758 intent.addCategory(Intent.CATEGORY_SETUP_WIZARD); 21759 21760 final List<ResolveInfo> matches = queryIntentActivitiesInternal(intent, null, 21761 MATCH_SYSTEM_ONLY | MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE 21762 | MATCH_DISABLED_COMPONENTS, 21763 UserHandle.myUserId()); 21764 if (matches.size() == 1) { 21765 return matches.get(0).getComponentInfo().packageName; 21766 } else { 21767 Slog.e(TAG, "There should probably be exactly one setup wizard; found " + matches.size() 21768 + ": matches=" + matches); 21769 return null; 21770 } 21771 } 21772 21773 private @Nullable String getStorageManagerPackageName() { 21774 final Intent intent = new Intent(StorageManager.ACTION_MANAGE_STORAGE); 21775 21776 final List<ResolveInfo> matches = queryIntentActivitiesInternal(intent, null, 21777 MATCH_SYSTEM_ONLY | MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE 21778 | MATCH_DISABLED_COMPONENTS, 21779 UserHandle.myUserId()); 21780 if (matches.size() == 1) { 21781 return matches.get(0).getComponentInfo().packageName; 21782 } else { 21783 Slog.e(TAG, "There should probably be exactly one storage manager; found " 21784 + matches.size() + ": matches=" + matches); 21785 return null; 21786 } 21787 } 21788 21789 @Override 21790 public void setApplicationEnabledSetting(String appPackageName, 21791 int newState, int flags, int userId, String callingPackage) { 21792 if (!sUserManager.exists(userId)) return; 21793 if (callingPackage == null) { 21794 callingPackage = Integer.toString(Binder.getCallingUid()); 21795 } 21796 setEnabledSetting(appPackageName, null, newState, flags, userId, callingPackage); 21797 } 21798 21799 @Override 21800 public void setUpdateAvailable(String packageName, boolean updateAvailable) { 21801 mContext.enforceCallingOrSelfPermission(android.Manifest.permission.INSTALL_PACKAGES, null); 21802 synchronized (mPackages) { 21803 final PackageSetting pkgSetting = mSettings.mPackages.get(packageName); 21804 if (pkgSetting != null) { 21805 pkgSetting.setUpdateAvailable(updateAvailable); 21806 } 21807 } 21808 } 21809 21810 @Override 21811 public void setComponentEnabledSetting(ComponentName componentName, 21812 int newState, int flags, int userId) { 21813 if (!sUserManager.exists(userId)) return; 21814 setEnabledSetting(componentName.getPackageName(), 21815 componentName.getClassName(), newState, flags, userId, null); 21816 } 21817 21818 private void setEnabledSetting(final String packageName, String className, int newState, 21819 final int flags, int userId, String callingPackage) { 21820 if (!(newState == COMPONENT_ENABLED_STATE_DEFAULT 21821 || newState == COMPONENT_ENABLED_STATE_ENABLED 21822 || newState == COMPONENT_ENABLED_STATE_DISABLED 21823 || newState == COMPONENT_ENABLED_STATE_DISABLED_USER 21824 || newState == COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED)) { 21825 throw new IllegalArgumentException("Invalid new component state: " 21826 + newState); 21827 } 21828 PackageSetting pkgSetting; 21829 final int callingUid = Binder.getCallingUid(); 21830 final int permission; 21831 if (callingUid == Process.SYSTEM_UID) { 21832 permission = PackageManager.PERMISSION_GRANTED; 21833 } else { 21834 permission = mContext.checkCallingOrSelfPermission( 21835 android.Manifest.permission.CHANGE_COMPONENT_ENABLED_STATE); 21836 } 21837 enforceCrossUserPermission(callingUid, userId, 21838 false /* requireFullPermission */, true /* checkShell */, "set enabled"); 21839 final boolean allowedByPermission = (permission == PackageManager.PERMISSION_GRANTED); 21840 boolean sendNow = false; 21841 boolean isApp = (className == null); 21842 final boolean isCallerInstantApp = (getInstantAppPackageName(callingUid) != null); 21843 String componentName = isApp ? packageName : className; 21844 int packageUid = -1; 21845 ArrayList<String> components; 21846 21847 // reader 21848 synchronized (mPackages) { 21849 pkgSetting = mSettings.mPackages.get(packageName); 21850 if (pkgSetting == null) { 21851 if (!isCallerInstantApp) { 21852 if (className == null) { 21853 throw new IllegalArgumentException("Unknown package: " + packageName); 21854 } 21855 throw new IllegalArgumentException( 21856 "Unknown component: " + packageName + "/" + className); 21857 } else { 21858 // throw SecurityException to prevent leaking package information 21859 throw new SecurityException( 21860 "Attempt to change component state; " 21861 + "pid=" + Binder.getCallingPid() 21862 + ", uid=" + callingUid 21863 + (className == null 21864 ? ", package=" + packageName 21865 : ", component=" + packageName + "/" + className)); 21866 } 21867 } 21868 } 21869 21870 // Limit who can change which apps 21871 if (!UserHandle.isSameApp(callingUid, pkgSetting.appId)) { 21872 // Don't allow apps that don't have permission to modify other apps 21873 if (!allowedByPermission 21874 || filterAppAccessLPr(pkgSetting, callingUid, userId)) { 21875 throw new SecurityException( 21876 "Attempt to change component state; " 21877 + "pid=" + Binder.getCallingPid() 21878 + ", uid=" + callingUid 21879 + (className == null 21880 ? ", package=" + packageName 21881 : ", component=" + packageName + "/" + className)); 21882 } 21883 // Don't allow changing protected packages. 21884 if (mProtectedPackages.isPackageStateProtected(userId, packageName)) { 21885 throw new SecurityException("Cannot disable a protected package: " + packageName); 21886 } 21887 } 21888 21889 synchronized (mPackages) { 21890 if (callingUid == Process.SHELL_UID 21891 && (pkgSetting.pkgFlags & ApplicationInfo.FLAG_TEST_ONLY) == 0) { 21892 // Shell can only change whole packages between ENABLED and DISABLED_USER states 21893 // unless it is a test package. 21894 int oldState = pkgSetting.getEnabled(userId); 21895 if (className == null 21896 && 21897 (oldState == COMPONENT_ENABLED_STATE_DISABLED_USER 21898 || oldState == COMPONENT_ENABLED_STATE_DEFAULT 21899 || oldState == COMPONENT_ENABLED_STATE_ENABLED) 21900 && 21901 (newState == COMPONENT_ENABLED_STATE_DISABLED_USER 21902 || newState == COMPONENT_ENABLED_STATE_DEFAULT 21903 || newState == COMPONENT_ENABLED_STATE_ENABLED)) { 21904 // ok 21905 } else { 21906 throw new SecurityException( 21907 "Shell cannot change component state for " + packageName + "/" 21908 + className + " to " + newState); 21909 } 21910 } 21911 } 21912 if (className == null) { 21913 // We're dealing with an application/package level state change 21914 synchronized (mPackages) { 21915 if (pkgSetting.getEnabled(userId) == newState) { 21916 // Nothing to do 21917 return; 21918 } 21919 } 21920 // If we're enabling a system stub, there's a little more work to do. 21921 // Prior to enabling the package, we need to decompress the APK(s) to the 21922 // data partition and then replace the version on the system partition. 21923 final PackageParser.Package deletedPkg = pkgSetting.pkg; 21924 final boolean isSystemStub = deletedPkg.isStub 21925 && deletedPkg.isSystemApp(); 21926 if (isSystemStub 21927 && (newState == PackageManager.COMPONENT_ENABLED_STATE_DEFAULT 21928 || newState == PackageManager.COMPONENT_ENABLED_STATE_ENABLED)) { 21929 final File codePath = decompressPackage(deletedPkg); 21930 if (codePath == null) { 21931 Slog.e(TAG, "couldn't decompress pkg: " + pkgSetting.name); 21932 return; 21933 } 21934 // TODO remove direct parsing of the package object during internal cleanup 21935 // of scan package 21936 // We need to call parse directly here for no other reason than we need 21937 // the new package in order to disable the old one [we use the information 21938 // for some internal optimization to optionally create a new package setting 21939 // object on replace]. However, we can't get the package from the scan 21940 // because the scan modifies live structures and we need to remove the 21941 // old [system] package from the system before a scan can be attempted. 21942 // Once scan is indempotent we can remove this parse and use the package 21943 // object we scanned, prior to adding it to package settings. 21944 final PackageParser pp = new PackageParser(); 21945 pp.setSeparateProcesses(mSeparateProcesses); 21946 pp.setDisplayMetrics(mMetrics); 21947 pp.setCallback(mPackageParserCallback); 21948 final PackageParser.Package tmpPkg; 21949 try { 21950 final int parseFlags = mDefParseFlags 21951 | PackageParser.PARSE_MUST_BE_APK 21952 | PackageParser.PARSE_IS_SYSTEM 21953 | PackageParser.PARSE_IS_SYSTEM_DIR; 21954 tmpPkg = pp.parsePackage(codePath, parseFlags); 21955 } catch (PackageParserException e) { 21956 Slog.w(TAG, "Failed to parse compressed system package:" + pkgSetting.name, e); 21957 return; 21958 } 21959 synchronized (mInstallLock) { 21960 // Disable the stub and remove any package entries 21961 removePackageLI(deletedPkg, true); 21962 synchronized (mPackages) { 21963 disableSystemPackageLPw(deletedPkg, tmpPkg); 21964 } 21965 final PackageParser.Package newPkg; 21966 try (PackageFreezer freezer = 21967 freezePackage(deletedPkg.packageName, "setEnabledSetting")) { 21968 final int parseFlags = mDefParseFlags | PackageParser.PARSE_CHATTY 21969 | PackageParser.PARSE_ENFORCE_CODE; 21970 newPkg = scanPackageTracedLI(codePath, parseFlags, 0 /*scanFlags*/, 21971 0 /*currentTime*/, null /*user*/); 21972 prepareAppDataAfterInstallLIF(newPkg); 21973 synchronized (mPackages) { 21974 try { 21975 updateSharedLibrariesLPr(newPkg, null); 21976 } catch (PackageManagerException e) { 21977 Slog.e(TAG, "updateAllSharedLibrariesLPw failed: ", e); 21978 } 21979 updatePermissionsLPw(newPkg.packageName, newPkg, 21980 UPDATE_PERMISSIONS_ALL | UPDATE_PERMISSIONS_REPLACE_PKG); 21981 mSettings.writeLPr(); 21982 } 21983 } catch (PackageManagerException e) { 21984 // Whoops! Something went wrong; try to roll back to the stub 21985 Slog.w(TAG, "Failed to install compressed system package:" 21986 + pkgSetting.name, e); 21987 // Remove the failed install 21988 removeCodePathLI(codePath); 21989 21990 // Install the system package 21991 try (PackageFreezer freezer = 21992 freezePackage(deletedPkg.packageName, "setEnabledSetting")) { 21993 synchronized (mPackages) { 21994 // NOTE: The system package always needs to be enabled; even 21995 // if it's for a compressed stub. If we don't, installing the 21996 // system package fails during scan [scanning checks the disabled 21997 // packages]. We will reverse this later, after we've "installed" 21998 // the stub. 21999 // This leaves us in a fragile state; the stub should never be 22000 // enabled, so, cross your fingers and hope nothing goes wrong 22001 // until we can disable the package later. 22002 enableSystemPackageLPw(deletedPkg); 22003 } 22004 installPackageFromSystemLIF(new File(deletedPkg.codePath), 22005 false /*isPrivileged*/, null /*allUserHandles*/, 22006 null /*origUserHandles*/, null /*origPermissionsState*/, 22007 true /*writeSettings*/); 22008 } catch (PackageManagerException pme) { 22009 Slog.w(TAG, "Failed to restore system package:" 22010 + deletedPkg.packageName, pme); 22011 } finally { 22012 synchronized (mPackages) { 22013 mSettings.disableSystemPackageLPw( 22014 deletedPkg.packageName, true /*replaced*/); 22015 mSettings.writeLPr(); 22016 } 22017 } 22018 return; 22019 } 22020 clearAppDataLIF(newPkg, UserHandle.USER_ALL, FLAG_STORAGE_DE 22021 | FLAG_STORAGE_CE | Installer.FLAG_CLEAR_CODE_CACHE_ONLY); 22022 clearAppProfilesLIF(newPkg, UserHandle.USER_ALL); 22023 mDexManager.notifyPackageUpdated(newPkg.packageName, 22024 newPkg.baseCodePath, newPkg.splitCodePaths); 22025 } 22026 } 22027 if (newState == PackageManager.COMPONENT_ENABLED_STATE_DEFAULT 22028 || newState == PackageManager.COMPONENT_ENABLED_STATE_ENABLED) { 22029 // Don't care about who enables an app. 22030 callingPackage = null; 22031 } 22032 synchronized (mPackages) { 22033 pkgSetting.setEnabled(newState, userId, callingPackage); 22034 } 22035 } else { 22036 synchronized (mPackages) { 22037 // We're dealing with a component level state change 22038 // First, verify that this is a valid class name. 22039 PackageParser.Package pkg = pkgSetting.pkg; 22040 if (pkg == null || !pkg.hasComponentClassName(className)) { 22041 if (pkg != null && 22042 pkg.applicationInfo.targetSdkVersion >= 22043 Build.VERSION_CODES.JELLY_BEAN) { 22044 throw new IllegalArgumentException("Component class " + className 22045 + " does not exist in " + packageName); 22046 } else { 22047 Slog.w(TAG, "Failed setComponentEnabledSetting: component class " 22048 + className + " does not exist in " + packageName); 22049 } 22050 } 22051 switch (newState) { 22052 case COMPONENT_ENABLED_STATE_ENABLED: 22053 if (!pkgSetting.enableComponentLPw(className, userId)) { 22054 return; 22055 } 22056 break; 22057 case COMPONENT_ENABLED_STATE_DISABLED: 22058 if (!pkgSetting.disableComponentLPw(className, userId)) { 22059 return; 22060 } 22061 break; 22062 case COMPONENT_ENABLED_STATE_DEFAULT: 22063 if (!pkgSetting.restoreComponentLPw(className, userId)) { 22064 return; 22065 } 22066 break; 22067 default: 22068 Slog.e(TAG, "Invalid new component state: " + newState); 22069 return; 22070 } 22071 } 22072 } 22073 synchronized (mPackages) { 22074 scheduleWritePackageRestrictionsLocked(userId); 22075 updateSequenceNumberLP(pkgSetting, new int[] { userId }); 22076 final long callingId = Binder.clearCallingIdentity(); 22077 try { 22078 updateInstantAppInstallerLocked(packageName); 22079 } finally { 22080 Binder.restoreCallingIdentity(callingId); 22081 } 22082 components = mPendingBroadcasts.get(userId, packageName); 22083 final boolean newPackage = components == null; 22084 if (newPackage) { 22085 components = new ArrayList<String>(); 22086 } 22087 if (!components.contains(componentName)) { 22088 components.add(componentName); 22089 } 22090 if ((flags&PackageManager.DONT_KILL_APP) == 0) { 22091 sendNow = true; 22092 // Purge entry from pending broadcast list if another one exists already 22093 // since we are sending one right away. 22094 mPendingBroadcasts.remove(userId, packageName); 22095 } else { 22096 if (newPackage) { 22097 mPendingBroadcasts.put(userId, packageName, components); 22098 } 22099 if (!mHandler.hasMessages(SEND_PENDING_BROADCAST)) { 22100 // Schedule a message 22101 mHandler.sendEmptyMessageDelayed(SEND_PENDING_BROADCAST, BROADCAST_DELAY); 22102 } 22103 } 22104 } 22105 22106 long callingId = Binder.clearCallingIdentity(); 22107 try { 22108 if (sendNow) { 22109 packageUid = UserHandle.getUid(userId, pkgSetting.appId); 22110 sendPackageChangedBroadcast(packageName, 22111 (flags&PackageManager.DONT_KILL_APP) != 0, components, packageUid); 22112 } 22113 } finally { 22114 Binder.restoreCallingIdentity(callingId); 22115 } 22116 } 22117 22118 @Override 22119 public void flushPackageRestrictionsAsUser(int userId) { 22120 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 22121 return; 22122 } 22123 if (!sUserManager.exists(userId)) { 22124 return; 22125 } 22126 enforceCrossUserPermission(Binder.getCallingUid(), userId, false /* requireFullPermission*/, 22127 false /* checkShell */, "flushPackageRestrictions"); 22128 synchronized (mPackages) { 22129 mSettings.writePackageRestrictionsLPr(userId); 22130 mDirtyUsers.remove(userId); 22131 if (mDirtyUsers.isEmpty()) { 22132 mHandler.removeMessages(WRITE_PACKAGE_RESTRICTIONS); 22133 } 22134 } 22135 } 22136 22137 private void sendPackageChangedBroadcast(String packageName, 22138 boolean killFlag, ArrayList<String> componentNames, int packageUid) { 22139 if (DEBUG_INSTALL) 22140 Log.v(TAG, "Sending package changed: package=" + packageName + " components=" 22141 + componentNames); 22142 Bundle extras = new Bundle(4); 22143 extras.putString(Intent.EXTRA_CHANGED_COMPONENT_NAME, componentNames.get(0)); 22144 String nameList[] = new String[componentNames.size()]; 22145 componentNames.toArray(nameList); 22146 extras.putStringArray(Intent.EXTRA_CHANGED_COMPONENT_NAME_LIST, nameList); 22147 extras.putBoolean(Intent.EXTRA_DONT_KILL_APP, killFlag); 22148 extras.putInt(Intent.EXTRA_UID, packageUid); 22149 // If this is not reporting a change of the overall package, then only send it 22150 // to registered receivers. We don't want to launch a swath of apps for every 22151 // little component state change. 22152 final int flags = !componentNames.contains(packageName) 22153 ? Intent.FLAG_RECEIVER_REGISTERED_ONLY : 0; 22154 sendPackageBroadcast(Intent.ACTION_PACKAGE_CHANGED, packageName, extras, flags, null, null, 22155 new int[] {UserHandle.getUserId(packageUid)}); 22156 } 22157 22158 @Override 22159 public void setPackageStoppedState(String packageName, boolean stopped, int userId) { 22160 if (!sUserManager.exists(userId)) return; 22161 final int callingUid = Binder.getCallingUid(); 22162 if (getInstantAppPackageName(callingUid) != null) { 22163 return; 22164 } 22165 final int permission = mContext.checkCallingOrSelfPermission( 22166 android.Manifest.permission.CHANGE_COMPONENT_ENABLED_STATE); 22167 final boolean allowedByPermission = (permission == PackageManager.PERMISSION_GRANTED); 22168 enforceCrossUserPermission(callingUid, userId, 22169 true /* requireFullPermission */, true /* checkShell */, "stop package"); 22170 // writer 22171 synchronized (mPackages) { 22172 final PackageSetting ps = mSettings.mPackages.get(packageName); 22173 if (!filterAppAccessLPr(ps, callingUid, userId) 22174 && mSettings.setPackageStoppedStateLPw(this, packageName, stopped, 22175 allowedByPermission, callingUid, userId)) { 22176 scheduleWritePackageRestrictionsLocked(userId); 22177 } 22178 } 22179 } 22180 22181 @Override 22182 public String getInstallerPackageName(String packageName) { 22183 final int callingUid = Binder.getCallingUid(); 22184 if (getInstantAppPackageName(callingUid) != null) { 22185 return null; 22186 } 22187 // reader 22188 synchronized (mPackages) { 22189 final PackageSetting ps = mSettings.mPackages.get(packageName); 22190 if (filterAppAccessLPr(ps, callingUid, UserHandle.getUserId(callingUid))) { 22191 return null; 22192 } 22193 return mSettings.getInstallerPackageNameLPr(packageName); 22194 } 22195 } 22196 22197 public boolean isOrphaned(String packageName) { 22198 // reader 22199 synchronized (mPackages) { 22200 return mSettings.isOrphaned(packageName); 22201 } 22202 } 22203 22204 @Override 22205 public int getApplicationEnabledSetting(String packageName, int userId) { 22206 if (!sUserManager.exists(userId)) return COMPONENT_ENABLED_STATE_DISABLED; 22207 int callingUid = Binder.getCallingUid(); 22208 enforceCrossUserPermission(callingUid, userId, 22209 false /* requireFullPermission */, false /* checkShell */, "get enabled"); 22210 // reader 22211 synchronized (mPackages) { 22212 if (filterAppAccessLPr(mSettings.getPackageLPr(packageName), callingUid, userId)) { 22213 return COMPONENT_ENABLED_STATE_DISABLED; 22214 } 22215 return mSettings.getApplicationEnabledSettingLPr(packageName, userId); 22216 } 22217 } 22218 22219 @Override 22220 public int getComponentEnabledSetting(ComponentName component, int userId) { 22221 if (!sUserManager.exists(userId)) return COMPONENT_ENABLED_STATE_DISABLED; 22222 int callingUid = Binder.getCallingUid(); 22223 enforceCrossUserPermission(callingUid, userId, 22224 false /*requireFullPermission*/, false /*checkShell*/, "getComponentEnabled"); 22225 synchronized (mPackages) { 22226 if (filterAppAccessLPr(mSettings.getPackageLPr(component.getPackageName()), callingUid, 22227 component, TYPE_UNKNOWN, userId)) { 22228 return COMPONENT_ENABLED_STATE_DISABLED; 22229 } 22230 return mSettings.getComponentEnabledSettingLPr(component, userId); 22231 } 22232 } 22233 22234 @Override 22235 public void enterSafeMode() { 22236 enforceSystemOrRoot("Only the system can request entering safe mode"); 22237 22238 if (!mSystemReady) { 22239 mSafeMode = true; 22240 } 22241 } 22242 22243 @Override 22244 public void systemReady() { 22245 enforceSystemOrRoot("Only the system can claim the system is ready"); 22246 22247 mSystemReady = true; 22248 final ContentResolver resolver = mContext.getContentResolver(); 22249 ContentObserver co = new ContentObserver(mHandler) { 22250 @Override 22251 public void onChange(boolean selfChange) { 22252 mEphemeralAppsDisabled = 22253 (Global.getInt(resolver, Global.ENABLE_EPHEMERAL_FEATURE, 1) == 0) || 22254 (Secure.getInt(resolver, Secure.INSTANT_APPS_ENABLED, 1) == 0); 22255 } 22256 }; 22257 mContext.getContentResolver().registerContentObserver(android.provider.Settings.Global 22258 .getUriFor(Global.ENABLE_EPHEMERAL_FEATURE), 22259 false, co, UserHandle.USER_SYSTEM); 22260 mContext.getContentResolver().registerContentObserver(android.provider.Settings.Global 22261 .getUriFor(Secure.INSTANT_APPS_ENABLED), false, co, UserHandle.USER_SYSTEM); 22262 co.onChange(true); 22263 22264 // Disable any carrier apps. We do this very early in boot to prevent the apps from being 22265 // disabled after already being started. 22266 CarrierAppUtils.disableCarrierAppsUntilPrivileged(mContext.getOpPackageName(), this, 22267 mContext.getContentResolver(), UserHandle.USER_SYSTEM); 22268 22269 // Read the compatibilty setting when the system is ready. 22270 boolean compatibilityModeEnabled = android.provider.Settings.Global.getInt( 22271 mContext.getContentResolver(), 22272 android.provider.Settings.Global.COMPATIBILITY_MODE, 1) == 1; 22273 PackageParser.setCompatibilityModeEnabled(compatibilityModeEnabled); 22274 if (DEBUG_SETTINGS) { 22275 Log.d(TAG, "compatibility mode:" + compatibilityModeEnabled); 22276 } 22277 22278 int[] grantPermissionsUserIds = EMPTY_INT_ARRAY; 22279 22280 synchronized (mPackages) { 22281 // Verify that all of the preferred activity components actually 22282 // exist. It is possible for applications to be updated and at 22283 // that point remove a previously declared activity component that 22284 // had been set as a preferred activity. We try to clean this up 22285 // the next time we encounter that preferred activity, but it is 22286 // possible for the user flow to never be able to return to that 22287 // situation so here we do a sanity check to make sure we haven't 22288 // left any junk around. 22289 ArrayList<PreferredActivity> removed = new ArrayList<PreferredActivity>(); 22290 for (int i=0; i<mSettings.mPreferredActivities.size(); i++) { 22291 PreferredIntentResolver pir = mSettings.mPreferredActivities.valueAt(i); 22292 removed.clear(); 22293 for (PreferredActivity pa : pir.filterSet()) { 22294 if (mActivities.mActivities.get(pa.mPref.mComponent) == null) { 22295 removed.add(pa); 22296 } 22297 } 22298 if (removed.size() > 0) { 22299 for (int r=0; r<removed.size(); r++) { 22300 PreferredActivity pa = removed.get(r); 22301 Slog.w(TAG, "Removing dangling preferred activity: " 22302 + pa.mPref.mComponent); 22303 pir.removeFilter(pa); 22304 } 22305 mSettings.writePackageRestrictionsLPr( 22306 mSettings.mPreferredActivities.keyAt(i)); 22307 } 22308 } 22309 22310 for (int userId : UserManagerService.getInstance().getUserIds()) { 22311 if (!mSettings.areDefaultRuntimePermissionsGrantedLPr(userId)) { 22312 grantPermissionsUserIds = ArrayUtils.appendInt( 22313 grantPermissionsUserIds, userId); 22314 } 22315 } 22316 } 22317 sUserManager.systemReady(); 22318 22319 // If we upgraded grant all default permissions before kicking off. 22320 for (int userId : grantPermissionsUserIds) { 22321 mDefaultPermissionPolicy.grantDefaultPermissions(userId); 22322 } 22323 22324 // If we did not grant default permissions, we preload from this the 22325 // default permission exceptions lazily to ensure we don't hit the 22326 // disk on a new user creation. 22327 if (grantPermissionsUserIds == EMPTY_INT_ARRAY) { 22328 mDefaultPermissionPolicy.scheduleReadDefaultPermissionExceptions(); 22329 } 22330 22331 // Kick off any messages waiting for system ready 22332 if (mPostSystemReadyMessages != null) { 22333 for (Message msg : mPostSystemReadyMessages) { 22334 msg.sendToTarget(); 22335 } 22336 mPostSystemReadyMessages = null; 22337 } 22338 22339 // Watch for external volumes that come and go over time 22340 final StorageManager storage = mContext.getSystemService(StorageManager.class); 22341 storage.registerListener(mStorageListener); 22342 22343 mInstallerService.systemReady(); 22344 mPackageDexOptimizer.systemReady(); 22345 22346 StorageManagerInternal StorageManagerInternal = LocalServices.getService( 22347 StorageManagerInternal.class); 22348 StorageManagerInternal.addExternalStoragePolicy( 22349 new StorageManagerInternal.ExternalStorageMountPolicy() { 22350 @Override 22351 public int getMountMode(int uid, String packageName) { 22352 if (Process.isIsolated(uid)) { 22353 return Zygote.MOUNT_EXTERNAL_NONE; 22354 } 22355 if (checkUidPermission(WRITE_MEDIA_STORAGE, uid) == PERMISSION_GRANTED) { 22356 return Zygote.MOUNT_EXTERNAL_DEFAULT; 22357 } 22358 if (checkUidPermission(READ_EXTERNAL_STORAGE, uid) == PERMISSION_DENIED) { 22359 return Zygote.MOUNT_EXTERNAL_DEFAULT; 22360 } 22361 if (checkUidPermission(WRITE_EXTERNAL_STORAGE, uid) == PERMISSION_DENIED) { 22362 return Zygote.MOUNT_EXTERNAL_READ; 22363 } 22364 return Zygote.MOUNT_EXTERNAL_WRITE; 22365 } 22366 22367 @Override 22368 public boolean hasExternalStorage(int uid, String packageName) { 22369 return true; 22370 } 22371 }); 22372 22373 // Now that we're mostly running, clean up stale users and apps 22374 sUserManager.reconcileUsers(StorageManager.UUID_PRIVATE_INTERNAL); 22375 reconcileApps(StorageManager.UUID_PRIVATE_INTERNAL); 22376 22377 if (mPrivappPermissionsViolations != null) { 22378 Slog.wtf(TAG,"Signature|privileged permissions not in " 22379 + "privapp-permissions whitelist: " + mPrivappPermissionsViolations); 22380 mPrivappPermissionsViolations = null; 22381 } 22382 } 22383 22384 public void waitForAppDataPrepared() { 22385 if (mPrepareAppDataFuture == null) { 22386 return; 22387 } 22388 ConcurrentUtils.waitForFutureNoInterrupt(mPrepareAppDataFuture, "wait for prepareAppData"); 22389 mPrepareAppDataFuture = null; 22390 } 22391 22392 @Override 22393 public boolean isSafeMode() { 22394 // allow instant applications 22395 return mSafeMode; 22396 } 22397 22398 @Override 22399 public boolean hasSystemUidErrors() { 22400 // allow instant applications 22401 return mHasSystemUidErrors; 22402 } 22403 22404 static String arrayToString(int[] array) { 22405 StringBuffer buf = new StringBuffer(128); 22406 buf.append('['); 22407 if (array != null) { 22408 for (int i=0; i<array.length; i++) { 22409 if (i > 0) buf.append(", "); 22410 buf.append(array[i]); 22411 } 22412 } 22413 buf.append(']'); 22414 return buf.toString(); 22415 } 22416 22417 static class DumpState { 22418 public static final int DUMP_LIBS = 1 << 0; 22419 public static final int DUMP_FEATURES = 1 << 1; 22420 public static final int DUMP_ACTIVITY_RESOLVERS = 1 << 2; 22421 public static final int DUMP_SERVICE_RESOLVERS = 1 << 3; 22422 public static final int DUMP_RECEIVER_RESOLVERS = 1 << 4; 22423 public static final int DUMP_CONTENT_RESOLVERS = 1 << 5; 22424 public static final int DUMP_PERMISSIONS = 1 << 6; 22425 public static final int DUMP_PACKAGES = 1 << 7; 22426 public static final int DUMP_SHARED_USERS = 1 << 8; 22427 public static final int DUMP_MESSAGES = 1 << 9; 22428 public static final int DUMP_PROVIDERS = 1 << 10; 22429 public static final int DUMP_VERIFIERS = 1 << 11; 22430 public static final int DUMP_PREFERRED = 1 << 12; 22431 public static final int DUMP_PREFERRED_XML = 1 << 13; 22432 public static final int DUMP_KEYSETS = 1 << 14; 22433 public static final int DUMP_VERSION = 1 << 15; 22434 public static final int DUMP_INSTALLS = 1 << 16; 22435 public static final int DUMP_INTENT_FILTER_VERIFIERS = 1 << 17; 22436 public static final int DUMP_DOMAIN_PREFERRED = 1 << 18; 22437 public static final int DUMP_FROZEN = 1 << 19; 22438 public static final int DUMP_DEXOPT = 1 << 20; 22439 public static final int DUMP_COMPILER_STATS = 1 << 21; 22440 public static final int DUMP_CHANGES = 1 << 22; 22441 public static final int DUMP_VOLUMES = 1 << 23; 22442 22443 public static final int OPTION_SHOW_FILTERS = 1 << 0; 22444 22445 private int mTypes; 22446 22447 private int mOptions; 22448 22449 private boolean mTitlePrinted; 22450 22451 private SharedUserSetting mSharedUser; 22452 22453 public boolean isDumping(int type) { 22454 if (mTypes == 0 && type != DUMP_PREFERRED_XML) { 22455 return true; 22456 } 22457 22458 return (mTypes & type) != 0; 22459 } 22460 22461 public void setDump(int type) { 22462 mTypes |= type; 22463 } 22464 22465 public boolean isOptionEnabled(int option) { 22466 return (mOptions & option) != 0; 22467 } 22468 22469 public void setOptionEnabled(int option) { 22470 mOptions |= option; 22471 } 22472 22473 public boolean onTitlePrinted() { 22474 final boolean printed = mTitlePrinted; 22475 mTitlePrinted = true; 22476 return printed; 22477 } 22478 22479 public boolean getTitlePrinted() { 22480 return mTitlePrinted; 22481 } 22482 22483 public void setTitlePrinted(boolean enabled) { 22484 mTitlePrinted = enabled; 22485 } 22486 22487 public SharedUserSetting getSharedUser() { 22488 return mSharedUser; 22489 } 22490 22491 public void setSharedUser(SharedUserSetting user) { 22492 mSharedUser = user; 22493 } 22494 } 22495 22496 @Override 22497 public void onShellCommand(FileDescriptor in, FileDescriptor out, 22498 FileDescriptor err, String[] args, ShellCallback callback, 22499 ResultReceiver resultReceiver) { 22500 (new PackageManagerShellCommand(this)).exec( 22501 this, in, out, err, args, callback, resultReceiver); 22502 } 22503 22504 @Override 22505 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 22506 if (!DumpUtils.checkDumpAndUsageStatsPermission(mContext, TAG, pw)) return; 22507 22508 DumpState dumpState = new DumpState(); 22509 boolean fullPreferred = false; 22510 boolean checkin = false; 22511 22512 String packageName = null; 22513 ArraySet<String> permissionNames = null; 22514 22515 int opti = 0; 22516 while (opti < args.length) { 22517 String opt = args[opti]; 22518 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 22519 break; 22520 } 22521 opti++; 22522 22523 if ("-a".equals(opt)) { 22524 // Right now we only know how to print all. 22525 } else if ("-h".equals(opt)) { 22526 pw.println("Package manager dump options:"); 22527 pw.println(" [-h] [-f] [--checkin] [cmd] ..."); 22528 pw.println(" --checkin: dump for a checkin"); 22529 pw.println(" -f: print details of intent filters"); 22530 pw.println(" -h: print this help"); 22531 pw.println(" cmd may be one of:"); 22532 pw.println(" l[ibraries]: list known shared libraries"); 22533 pw.println(" f[eatures]: list device features"); 22534 pw.println(" k[eysets]: print known keysets"); 22535 pw.println(" r[esolvers] [activity|service|receiver|content]: dump intent resolvers"); 22536 pw.println(" perm[issions]: dump permissions"); 22537 pw.println(" permission [name ...]: dump declaration and use of given permission"); 22538 pw.println(" pref[erred]: print preferred package settings"); 22539 pw.println(" preferred-xml [--full]: print preferred package settings as xml"); 22540 pw.println(" prov[iders]: dump content providers"); 22541 pw.println(" p[ackages]: dump installed packages"); 22542 pw.println(" s[hared-users]: dump shared user IDs"); 22543 pw.println(" m[essages]: print collected runtime messages"); 22544 pw.println(" v[erifiers]: print package verifier info"); 22545 pw.println(" d[omain-preferred-apps]: print domains preferred apps"); 22546 pw.println(" i[ntent-filter-verifiers]|ifv: print intent filter verifier info"); 22547 pw.println(" version: print database version info"); 22548 pw.println(" write: write current settings now"); 22549 pw.println(" installs: details about install sessions"); 22550 pw.println(" check-permission <permission> <package> [<user>]: does pkg hold perm?"); 22551 pw.println(" dexopt: dump dexopt state"); 22552 pw.println(" compiler-stats: dump compiler statistics"); 22553 pw.println(" enabled-overlays: dump list of enabled overlay packages"); 22554 pw.println(" <package.name>: info about given package"); 22555 return; 22556 } else if ("--checkin".equals(opt)) { 22557 checkin = true; 22558 } else if ("-f".equals(opt)) { 22559 dumpState.setOptionEnabled(DumpState.OPTION_SHOW_FILTERS); 22560 } else if ("--proto".equals(opt)) { 22561 dumpProto(fd); 22562 return; 22563 } else { 22564 pw.println("Unknown argument: " + opt + "; use -h for help"); 22565 } 22566 } 22567 22568 // Is the caller requesting to dump a particular piece of data? 22569 if (opti < args.length) { 22570 String cmd = args[opti]; 22571 opti++; 22572 // Is this a package name? 22573 if ("android".equals(cmd) || cmd.contains(".")) { 22574 packageName = cmd; 22575 // When dumping a single package, we always dump all of its 22576 // filter information since the amount of data will be reasonable. 22577 dumpState.setOptionEnabled(DumpState.OPTION_SHOW_FILTERS); 22578 } else if ("check-permission".equals(cmd)) { 22579 if (opti >= args.length) { 22580 pw.println("Error: check-permission missing permission argument"); 22581 return; 22582 } 22583 String perm = args[opti]; 22584 opti++; 22585 if (opti >= args.length) { 22586 pw.println("Error: check-permission missing package argument"); 22587 return; 22588 } 22589 22590 String pkg = args[opti]; 22591 opti++; 22592 int user = UserHandle.getUserId(Binder.getCallingUid()); 22593 if (opti < args.length) { 22594 try { 22595 user = Integer.parseInt(args[opti]); 22596 } catch (NumberFormatException e) { 22597 pw.println("Error: check-permission user argument is not a number: " 22598 + args[opti]); 22599 return; 22600 } 22601 } 22602 22603 // Normalize package name to handle renamed packages and static libs 22604 pkg = resolveInternalPackageNameLPr(pkg, PackageManager.VERSION_CODE_HIGHEST); 22605 22606 pw.println(checkPermission(perm, pkg, user)); 22607 return; 22608 } else if ("l".equals(cmd) || "libraries".equals(cmd)) { 22609 dumpState.setDump(DumpState.DUMP_LIBS); 22610 } else if ("f".equals(cmd) || "features".equals(cmd)) { 22611 dumpState.setDump(DumpState.DUMP_FEATURES); 22612 } else if ("r".equals(cmd) || "resolvers".equals(cmd)) { 22613 if (opti >= args.length) { 22614 dumpState.setDump(DumpState.DUMP_ACTIVITY_RESOLVERS 22615 | DumpState.DUMP_SERVICE_RESOLVERS 22616 | DumpState.DUMP_RECEIVER_RESOLVERS 22617 | DumpState.DUMP_CONTENT_RESOLVERS); 22618 } else { 22619 while (opti < args.length) { 22620 String name = args[opti]; 22621 if ("a".equals(name) || "activity".equals(name)) { 22622 dumpState.setDump(DumpState.DUMP_ACTIVITY_RESOLVERS); 22623 } else if ("s".equals(name) || "service".equals(name)) { 22624 dumpState.setDump(DumpState.DUMP_SERVICE_RESOLVERS); 22625 } else if ("r".equals(name) || "receiver".equals(name)) { 22626 dumpState.setDump(DumpState.DUMP_RECEIVER_RESOLVERS); 22627 } else if ("c".equals(name) || "content".equals(name)) { 22628 dumpState.setDump(DumpState.DUMP_CONTENT_RESOLVERS); 22629 } else { 22630 pw.println("Error: unknown resolver table type: " + name); 22631 return; 22632 } 22633 opti++; 22634 } 22635 } 22636 } else if ("perm".equals(cmd) || "permissions".equals(cmd)) { 22637 dumpState.setDump(DumpState.DUMP_PERMISSIONS); 22638 } else if ("permission".equals(cmd)) { 22639 if (opti >= args.length) { 22640 pw.println("Error: permission requires permission name"); 22641 return; 22642 } 22643 permissionNames = new ArraySet<>(); 22644 while (opti < args.length) { 22645 permissionNames.add(args[opti]); 22646 opti++; 22647 } 22648 dumpState.setDump(DumpState.DUMP_PERMISSIONS 22649 | DumpState.DUMP_PACKAGES | DumpState.DUMP_SHARED_USERS); 22650 } else if ("pref".equals(cmd) || "preferred".equals(cmd)) { 22651 dumpState.setDump(DumpState.DUMP_PREFERRED); 22652 } else if ("preferred-xml".equals(cmd)) { 22653 dumpState.setDump(DumpState.DUMP_PREFERRED_XML); 22654 if (opti < args.length && "--full".equals(args[opti])) { 22655 fullPreferred = true; 22656 opti++; 22657 } 22658 } else if ("d".equals(cmd) || "domain-preferred-apps".equals(cmd)) { 22659 dumpState.setDump(DumpState.DUMP_DOMAIN_PREFERRED); 22660 } else if ("p".equals(cmd) || "packages".equals(cmd)) { 22661 dumpState.setDump(DumpState.DUMP_PACKAGES); 22662 } else if ("s".equals(cmd) || "shared-users".equals(cmd)) { 22663 dumpState.setDump(DumpState.DUMP_SHARED_USERS); 22664 } else if ("prov".equals(cmd) || "providers".equals(cmd)) { 22665 dumpState.setDump(DumpState.DUMP_PROVIDERS); 22666 } else if ("m".equals(cmd) || "messages".equals(cmd)) { 22667 dumpState.setDump(DumpState.DUMP_MESSAGES); 22668 } else if ("v".equals(cmd) || "verifiers".equals(cmd)) { 22669 dumpState.setDump(DumpState.DUMP_VERIFIERS); 22670 } else if ("i".equals(cmd) || "ifv".equals(cmd) 22671 || "intent-filter-verifiers".equals(cmd)) { 22672 dumpState.setDump(DumpState.DUMP_INTENT_FILTER_VERIFIERS); 22673 } else if ("version".equals(cmd)) { 22674 dumpState.setDump(DumpState.DUMP_VERSION); 22675 } else if ("k".equals(cmd) || "keysets".equals(cmd)) { 22676 dumpState.setDump(DumpState.DUMP_KEYSETS); 22677 } else if ("installs".equals(cmd)) { 22678 dumpState.setDump(DumpState.DUMP_INSTALLS); 22679 } else if ("frozen".equals(cmd)) { 22680 dumpState.setDump(DumpState.DUMP_FROZEN); 22681 } else if ("volumes".equals(cmd)) { 22682 dumpState.setDump(DumpState.DUMP_VOLUMES); 22683 } else if ("dexopt".equals(cmd)) { 22684 dumpState.setDump(DumpState.DUMP_DEXOPT); 22685 } else if ("compiler-stats".equals(cmd)) { 22686 dumpState.setDump(DumpState.DUMP_COMPILER_STATS); 22687 } else if ("changes".equals(cmd)) { 22688 dumpState.setDump(DumpState.DUMP_CHANGES); 22689 } else if ("write".equals(cmd)) { 22690 synchronized (mPackages) { 22691 mSettings.writeLPr(); 22692 pw.println("Settings written."); 22693 return; 22694 } 22695 } 22696 } 22697 22698 if (checkin) { 22699 pw.println("vers,1"); 22700 } 22701 22702 // reader 22703 synchronized (mPackages) { 22704 if (dumpState.isDumping(DumpState.DUMP_VERSION) && packageName == null) { 22705 if (!checkin) { 22706 if (dumpState.onTitlePrinted()) 22707 pw.println(); 22708 pw.println("Database versions:"); 22709 mSettings.dumpVersionLPr(new IndentingPrintWriter(pw, " ")); 22710 } 22711 } 22712 22713 if (dumpState.isDumping(DumpState.DUMP_VERIFIERS) && packageName == null) { 22714 if (!checkin) { 22715 if (dumpState.onTitlePrinted()) 22716 pw.println(); 22717 pw.println("Verifiers:"); 22718 pw.print(" Required: "); 22719 pw.print(mRequiredVerifierPackage); 22720 pw.print(" (uid="); 22721 pw.print(getPackageUid(mRequiredVerifierPackage, MATCH_DEBUG_TRIAGED_MISSING, 22722 UserHandle.USER_SYSTEM)); 22723 pw.println(")"); 22724 } else if (mRequiredVerifierPackage != null) { 22725 pw.print("vrfy,"); pw.print(mRequiredVerifierPackage); 22726 pw.print(","); 22727 pw.println(getPackageUid(mRequiredVerifierPackage, MATCH_DEBUG_TRIAGED_MISSING, 22728 UserHandle.USER_SYSTEM)); 22729 } 22730 } 22731 22732 if (dumpState.isDumping(DumpState.DUMP_INTENT_FILTER_VERIFIERS) && 22733 packageName == null) { 22734 if (mIntentFilterVerifierComponent != null) { 22735 String verifierPackageName = mIntentFilterVerifierComponent.getPackageName(); 22736 if (!checkin) { 22737 if (dumpState.onTitlePrinted()) 22738 pw.println(); 22739 pw.println("Intent Filter Verifier:"); 22740 pw.print(" Using: "); 22741 pw.print(verifierPackageName); 22742 pw.print(" (uid="); 22743 pw.print(getPackageUid(verifierPackageName, MATCH_DEBUG_TRIAGED_MISSING, 22744 UserHandle.USER_SYSTEM)); 22745 pw.println(")"); 22746 } else if (verifierPackageName != null) { 22747 pw.print("ifv,"); pw.print(verifierPackageName); 22748 pw.print(","); 22749 pw.println(getPackageUid(verifierPackageName, MATCH_DEBUG_TRIAGED_MISSING, 22750 UserHandle.USER_SYSTEM)); 22751 } 22752 } else { 22753 pw.println(); 22754 pw.println("No Intent Filter Verifier available!"); 22755 } 22756 } 22757 22758 if (dumpState.isDumping(DumpState.DUMP_LIBS) && packageName == null) { 22759 boolean printedHeader = false; 22760 final Iterator<String> it = mSharedLibraries.keySet().iterator(); 22761 while (it.hasNext()) { 22762 String libName = it.next(); 22763 SparseArray<SharedLibraryEntry> versionedLib = mSharedLibraries.get(libName); 22764 if (versionedLib == null) { 22765 continue; 22766 } 22767 final int versionCount = versionedLib.size(); 22768 for (int i = 0; i < versionCount; i++) { 22769 SharedLibraryEntry libEntry = versionedLib.valueAt(i); 22770 if (!checkin) { 22771 if (!printedHeader) { 22772 if (dumpState.onTitlePrinted()) 22773 pw.println(); 22774 pw.println("Libraries:"); 22775 printedHeader = true; 22776 } 22777 pw.print(" "); 22778 } else { 22779 pw.print("lib,"); 22780 } 22781 pw.print(libEntry.info.getName()); 22782 if (libEntry.info.isStatic()) { 22783 pw.print(" version=" + libEntry.info.getVersion()); 22784 } 22785 if (!checkin) { 22786 pw.print(" -> "); 22787 } 22788 if (libEntry.path != null) { 22789 pw.print(" (jar) "); 22790 pw.print(libEntry.path); 22791 } else { 22792 pw.print(" (apk) "); 22793 pw.print(libEntry.apk); 22794 } 22795 pw.println(); 22796 } 22797 } 22798 } 22799 22800 if (dumpState.isDumping(DumpState.DUMP_FEATURES) && packageName == null) { 22801 if (dumpState.onTitlePrinted()) 22802 pw.println(); 22803 if (!checkin) { 22804 pw.println("Features:"); 22805 } 22806 22807 synchronized (mAvailableFeatures) { 22808 for (FeatureInfo feat : mAvailableFeatures.values()) { 22809 if (checkin) { 22810 pw.print("feat,"); 22811 pw.print(feat.name); 22812 pw.print(","); 22813 pw.println(feat.version); 22814 } else { 22815 pw.print(" "); 22816 pw.print(feat.name); 22817 if (feat.version > 0) { 22818 pw.print(" version="); 22819 pw.print(feat.version); 22820 } 22821 pw.println(); 22822 } 22823 } 22824 } 22825 } 22826 22827 if (!checkin && dumpState.isDumping(DumpState.DUMP_ACTIVITY_RESOLVERS)) { 22828 if (mActivities.dump(pw, dumpState.getTitlePrinted() ? "\nActivity Resolver Table:" 22829 : "Activity Resolver Table:", " ", packageName, 22830 dumpState.isOptionEnabled(DumpState.OPTION_SHOW_FILTERS), true)) { 22831 dumpState.setTitlePrinted(true); 22832 } 22833 } 22834 if (!checkin && dumpState.isDumping(DumpState.DUMP_RECEIVER_RESOLVERS)) { 22835 if (mReceivers.dump(pw, dumpState.getTitlePrinted() ? "\nReceiver Resolver Table:" 22836 : "Receiver Resolver Table:", " ", packageName, 22837 dumpState.isOptionEnabled(DumpState.OPTION_SHOW_FILTERS), true)) { 22838 dumpState.setTitlePrinted(true); 22839 } 22840 } 22841 if (!checkin && dumpState.isDumping(DumpState.DUMP_SERVICE_RESOLVERS)) { 22842 if (mServices.dump(pw, dumpState.getTitlePrinted() ? "\nService Resolver Table:" 22843 : "Service Resolver Table:", " ", packageName, 22844 dumpState.isOptionEnabled(DumpState.OPTION_SHOW_FILTERS), true)) { 22845 dumpState.setTitlePrinted(true); 22846 } 22847 } 22848 if (!checkin && dumpState.isDumping(DumpState.DUMP_CONTENT_RESOLVERS)) { 22849 if (mProviders.dump(pw, dumpState.getTitlePrinted() ? "\nProvider Resolver Table:" 22850 : "Provider Resolver Table:", " ", packageName, 22851 dumpState.isOptionEnabled(DumpState.OPTION_SHOW_FILTERS), true)) { 22852 dumpState.setTitlePrinted(true); 22853 } 22854 } 22855 22856 if (!checkin && dumpState.isDumping(DumpState.DUMP_PREFERRED)) { 22857 for (int i=0; i<mSettings.mPreferredActivities.size(); i++) { 22858 PreferredIntentResolver pir = mSettings.mPreferredActivities.valueAt(i); 22859 int user = mSettings.mPreferredActivities.keyAt(i); 22860 if (pir.dump(pw, 22861 dumpState.getTitlePrinted() 22862 ? "\nPreferred Activities User " + user + ":" 22863 : "Preferred Activities User " + user + ":", " ", 22864 packageName, true, false)) { 22865 dumpState.setTitlePrinted(true); 22866 } 22867 } 22868 } 22869 22870 if (!checkin && dumpState.isDumping(DumpState.DUMP_PREFERRED_XML)) { 22871 pw.flush(); 22872 FileOutputStream fout = new FileOutputStream(fd); 22873 BufferedOutputStream str = new BufferedOutputStream(fout); 22874 XmlSerializer serializer = new FastXmlSerializer(); 22875 try { 22876 serializer.setOutput(str, StandardCharsets.UTF_8.name()); 22877 serializer.startDocument(null, true); 22878 serializer.setFeature( 22879 "http://xmlpull.org/v1/doc/features.html#indent-output", true); 22880 mSettings.writePreferredActivitiesLPr(serializer, 0, fullPreferred); 22881 serializer.endDocument(); 22882 serializer.flush(); 22883 } catch (IllegalArgumentException e) { 22884 pw.println("Failed writing: " + e); 22885 } catch (IllegalStateException e) { 22886 pw.println("Failed writing: " + e); 22887 } catch (IOException e) { 22888 pw.println("Failed writing: " + e); 22889 } 22890 } 22891 22892 if (!checkin 22893 && dumpState.isDumping(DumpState.DUMP_DOMAIN_PREFERRED) 22894 && packageName == null) { 22895 pw.println(); 22896 int count = mSettings.mPackages.size(); 22897 if (count == 0) { 22898 pw.println("No applications!"); 22899 pw.println(); 22900 } else { 22901 final String prefix = " "; 22902 Collection<PackageSetting> allPackageSettings = mSettings.mPackages.values(); 22903 if (allPackageSettings.size() == 0) { 22904 pw.println("No domain preferred apps!"); 22905 pw.println(); 22906 } else { 22907 pw.println("App verification status:"); 22908 pw.println(); 22909 count = 0; 22910 for (PackageSetting ps : allPackageSettings) { 22911 IntentFilterVerificationInfo ivi = ps.getIntentFilterVerificationInfo(); 22912 if (ivi == null || ivi.getPackageName() == null) continue; 22913 pw.println(prefix + "Package: " + ivi.getPackageName()); 22914 pw.println(prefix + "Domains: " + ivi.getDomainsString()); 22915 pw.println(prefix + "Status: " + ivi.getStatusString()); 22916 pw.println(); 22917 count++; 22918 } 22919 if (count == 0) { 22920 pw.println(prefix + "No app verification established."); 22921 pw.println(); 22922 } 22923 for (int userId : sUserManager.getUserIds()) { 22924 pw.println("App linkages for user " + userId + ":"); 22925 pw.println(); 22926 count = 0; 22927 for (PackageSetting ps : allPackageSettings) { 22928 final long status = ps.getDomainVerificationStatusForUser(userId); 22929 if (status >> 32 == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED 22930 && !DEBUG_DOMAIN_VERIFICATION) { 22931 continue; 22932 } 22933 pw.println(prefix + "Package: " + ps.name); 22934 pw.println(prefix + "Domains: " + dumpDomainString(ps.name)); 22935 String statusStr = IntentFilterVerificationInfo. 22936 getStatusStringFromValue(status); 22937 pw.println(prefix + "Status: " + statusStr); 22938 pw.println(); 22939 count++; 22940 } 22941 if (count == 0) { 22942 pw.println(prefix + "No configured app linkages."); 22943 pw.println(); 22944 } 22945 } 22946 } 22947 } 22948 } 22949 22950 if (!checkin && dumpState.isDumping(DumpState.DUMP_PERMISSIONS)) { 22951 mSettings.dumpPermissionsLPr(pw, packageName, permissionNames, dumpState); 22952 if (packageName == null && permissionNames == null) { 22953 for (int iperm=0; iperm<mAppOpPermissionPackages.size(); iperm++) { 22954 if (iperm == 0) { 22955 if (dumpState.onTitlePrinted()) 22956 pw.println(); 22957 pw.println("AppOp Permissions:"); 22958 } 22959 pw.print(" AppOp Permission "); 22960 pw.print(mAppOpPermissionPackages.keyAt(iperm)); 22961 pw.println(":"); 22962 ArraySet<String> pkgs = mAppOpPermissionPackages.valueAt(iperm); 22963 for (int ipkg=0; ipkg<pkgs.size(); ipkg++) { 22964 pw.print(" "); pw.println(pkgs.valueAt(ipkg)); 22965 } 22966 } 22967 } 22968 } 22969 22970 if (!checkin && dumpState.isDumping(DumpState.DUMP_PROVIDERS)) { 22971 boolean printedSomething = false; 22972 for (PackageParser.Provider p : mProviders.mProviders.values()) { 22973 if (packageName != null && !packageName.equals(p.info.packageName)) { 22974 continue; 22975 } 22976 if (!printedSomething) { 22977 if (dumpState.onTitlePrinted()) 22978 pw.println(); 22979 pw.println("Registered ContentProviders:"); 22980 printedSomething = true; 22981 } 22982 pw.print(" "); p.printComponentShortName(pw); pw.println(":"); 22983 pw.print(" "); pw.println(p.toString()); 22984 } 22985 printedSomething = false; 22986 for (Map.Entry<String, PackageParser.Provider> entry : 22987 mProvidersByAuthority.entrySet()) { 22988 PackageParser.Provider p = entry.getValue(); 22989 if (packageName != null && !packageName.equals(p.info.packageName)) { 22990 continue; 22991 } 22992 if (!printedSomething) { 22993 if (dumpState.onTitlePrinted()) 22994 pw.println(); 22995 pw.println("ContentProvider Authorities:"); 22996 printedSomething = true; 22997 } 22998 pw.print(" ["); pw.print(entry.getKey()); pw.println("]:"); 22999 pw.print(" "); pw.println(p.toString()); 23000 if (p.info != null && p.info.applicationInfo != null) { 23001 final String appInfo = p.info.applicationInfo.toString(); 23002 pw.print(" applicationInfo="); pw.println(appInfo); 23003 } 23004 } 23005 } 23006 23007 if (!checkin && dumpState.isDumping(DumpState.DUMP_KEYSETS)) { 23008 mSettings.mKeySetManagerService.dumpLPr(pw, packageName, dumpState); 23009 } 23010 23011 if (dumpState.isDumping(DumpState.DUMP_PACKAGES)) { 23012 mSettings.dumpPackagesLPr(pw, packageName, permissionNames, dumpState, checkin); 23013 } 23014 23015 if (dumpState.isDumping(DumpState.DUMP_SHARED_USERS)) { 23016 mSettings.dumpSharedUsersLPr(pw, packageName, permissionNames, dumpState, checkin); 23017 } 23018 23019 if (dumpState.isDumping(DumpState.DUMP_CHANGES)) { 23020 if (dumpState.onTitlePrinted()) pw.println(); 23021 pw.println("Package Changes:"); 23022 pw.print(" Sequence number="); pw.println(mChangedPackagesSequenceNumber); 23023 final int K = mChangedPackages.size(); 23024 for (int i = 0; i < K; i++) { 23025 final SparseArray<String> changes = mChangedPackages.valueAt(i); 23026 pw.print(" User "); pw.print(mChangedPackages.keyAt(i)); pw.println(":"); 23027 final int N = changes.size(); 23028 if (N == 0) { 23029 pw.print(" "); pw.println("No packages changed"); 23030 } else { 23031 for (int j = 0; j < N; j++) { 23032 final String pkgName = changes.valueAt(j); 23033 final int sequenceNumber = changes.keyAt(j); 23034 pw.print(" "); 23035 pw.print("seq="); 23036 pw.print(sequenceNumber); 23037 pw.print(", package="); 23038 pw.println(pkgName); 23039 } 23040 } 23041 } 23042 } 23043 23044 if (!checkin && dumpState.isDumping(DumpState.DUMP_PERMISSIONS) && packageName == null) { 23045 mSettings.dumpRestoredPermissionGrantsLPr(pw, dumpState); 23046 } 23047 23048 if (!checkin && dumpState.isDumping(DumpState.DUMP_FROZEN) && packageName == null) { 23049 // XXX should handle packageName != null by dumping only install data that 23050 // the given package is involved with. 23051 if (dumpState.onTitlePrinted()) pw.println(); 23052 23053 final IndentingPrintWriter ipw = new IndentingPrintWriter(pw, " ", 120); 23054 ipw.println(); 23055 ipw.println("Frozen packages:"); 23056 ipw.increaseIndent(); 23057 if (mFrozenPackages.size() == 0) { 23058 ipw.println("(none)"); 23059 } else { 23060 for (int i = 0; i < mFrozenPackages.size(); i++) { 23061 ipw.println(mFrozenPackages.valueAt(i)); 23062 } 23063 } 23064 ipw.decreaseIndent(); 23065 } 23066 23067 if (!checkin && dumpState.isDumping(DumpState.DUMP_VOLUMES) && packageName == null) { 23068 if (dumpState.onTitlePrinted()) pw.println(); 23069 23070 final IndentingPrintWriter ipw = new IndentingPrintWriter(pw, " ", 120); 23071 ipw.println(); 23072 ipw.println("Loaded volumes:"); 23073 ipw.increaseIndent(); 23074 if (mLoadedVolumes.size() == 0) { 23075 ipw.println("(none)"); 23076 } else { 23077 for (int i = 0; i < mLoadedVolumes.size(); i++) { 23078 ipw.println(mLoadedVolumes.valueAt(i)); 23079 } 23080 } 23081 ipw.decreaseIndent(); 23082 } 23083 23084 if (!checkin && dumpState.isDumping(DumpState.DUMP_DEXOPT)) { 23085 if (dumpState.onTitlePrinted()) pw.println(); 23086 dumpDexoptStateLPr(pw, packageName); 23087 } 23088 23089 if (!checkin && dumpState.isDumping(DumpState.DUMP_COMPILER_STATS)) { 23090 if (dumpState.onTitlePrinted()) pw.println(); 23091 dumpCompilerStatsLPr(pw, packageName); 23092 } 23093 23094 if (!checkin && dumpState.isDumping(DumpState.DUMP_MESSAGES) && packageName == null) { 23095 if (dumpState.onTitlePrinted()) pw.println(); 23096 mSettings.dumpReadMessagesLPr(pw, dumpState); 23097 23098 pw.println(); 23099 pw.println("Package warning messages:"); 23100 BufferedReader in = null; 23101 String line = null; 23102 try { 23103 in = new BufferedReader(new FileReader(getSettingsProblemFile())); 23104 while ((line = in.readLine()) != null) { 23105 if (line.contains("ignored: updated version")) continue; 23106 pw.println(line); 23107 } 23108 } catch (IOException ignored) { 23109 } finally { 23110 IoUtils.closeQuietly(in); 23111 } 23112 } 23113 23114 if (checkin && dumpState.isDumping(DumpState.DUMP_MESSAGES)) { 23115 BufferedReader in = null; 23116 String line = null; 23117 try { 23118 in = new BufferedReader(new FileReader(getSettingsProblemFile())); 23119 while ((line = in.readLine()) != null) { 23120 if (line.contains("ignored: updated version")) continue; 23121 pw.print("msg,"); 23122 pw.println(line); 23123 } 23124 } catch (IOException ignored) { 23125 } finally { 23126 IoUtils.closeQuietly(in); 23127 } 23128 } 23129 } 23130 23131 // PackageInstaller should be called outside of mPackages lock 23132 if (!checkin && dumpState.isDumping(DumpState.DUMP_INSTALLS) && packageName == null) { 23133 // XXX should handle packageName != null by dumping only install data that 23134 // the given package is involved with. 23135 if (dumpState.onTitlePrinted()) pw.println(); 23136 mInstallerService.dump(new IndentingPrintWriter(pw, " ", 120)); 23137 } 23138 } 23139 23140 private void dumpProto(FileDescriptor fd) { 23141 final ProtoOutputStream proto = new ProtoOutputStream(fd); 23142 23143 synchronized (mPackages) { 23144 final long requiredVerifierPackageToken = 23145 proto.start(PackageServiceDumpProto.REQUIRED_VERIFIER_PACKAGE); 23146 proto.write(PackageServiceDumpProto.PackageShortProto.NAME, mRequiredVerifierPackage); 23147 proto.write( 23148 PackageServiceDumpProto.PackageShortProto.UID, 23149 getPackageUid( 23150 mRequiredVerifierPackage, 23151 MATCH_DEBUG_TRIAGED_MISSING, 23152 UserHandle.USER_SYSTEM)); 23153 proto.end(requiredVerifierPackageToken); 23154 23155 if (mIntentFilterVerifierComponent != null) { 23156 String verifierPackageName = mIntentFilterVerifierComponent.getPackageName(); 23157 final long verifierPackageToken = 23158 proto.start(PackageServiceDumpProto.VERIFIER_PACKAGE); 23159 proto.write(PackageServiceDumpProto.PackageShortProto.NAME, verifierPackageName); 23160 proto.write( 23161 PackageServiceDumpProto.PackageShortProto.UID, 23162 getPackageUid( 23163 verifierPackageName, 23164 MATCH_DEBUG_TRIAGED_MISSING, 23165 UserHandle.USER_SYSTEM)); 23166 proto.end(verifierPackageToken); 23167 } 23168 23169 dumpSharedLibrariesProto(proto); 23170 dumpFeaturesProto(proto); 23171 mSettings.dumpPackagesProto(proto); 23172 mSettings.dumpSharedUsersProto(proto); 23173 dumpMessagesProto(proto); 23174 } 23175 proto.flush(); 23176 } 23177 23178 private void dumpMessagesProto(ProtoOutputStream proto) { 23179 BufferedReader in = null; 23180 String line = null; 23181 try { 23182 in = new BufferedReader(new FileReader(getSettingsProblemFile())); 23183 while ((line = in.readLine()) != null) { 23184 if (line.contains("ignored: updated version")) continue; 23185 proto.write(PackageServiceDumpProto.MESSAGES, line); 23186 } 23187 } catch (IOException ignored) { 23188 } finally { 23189 IoUtils.closeQuietly(in); 23190 } 23191 } 23192 23193 private void dumpFeaturesProto(ProtoOutputStream proto) { 23194 synchronized (mAvailableFeatures) { 23195 final int count = mAvailableFeatures.size(); 23196 for (int i = 0; i < count; i++) { 23197 final FeatureInfo feat = mAvailableFeatures.valueAt(i); 23198 final long featureToken = proto.start(PackageServiceDumpProto.FEATURES); 23199 proto.write(PackageServiceDumpProto.FeatureProto.NAME, feat.name); 23200 proto.write(PackageServiceDumpProto.FeatureProto.VERSION, feat.version); 23201 proto.end(featureToken); 23202 } 23203 } 23204 } 23205 23206 private void dumpSharedLibrariesProto(ProtoOutputStream proto) { 23207 final int count = mSharedLibraries.size(); 23208 for (int i = 0; i < count; i++) { 23209 final String libName = mSharedLibraries.keyAt(i); 23210 SparseArray<SharedLibraryEntry> versionedLib = mSharedLibraries.get(libName); 23211 if (versionedLib == null) { 23212 continue; 23213 } 23214 final int versionCount = versionedLib.size(); 23215 for (int j = 0; j < versionCount; j++) { 23216 final SharedLibraryEntry libEntry = versionedLib.valueAt(j); 23217 final long sharedLibraryToken = 23218 proto.start(PackageServiceDumpProto.SHARED_LIBRARIES); 23219 proto.write(PackageServiceDumpProto.SharedLibraryProto.NAME, libEntry.info.getName()); 23220 final boolean isJar = (libEntry.path != null); 23221 proto.write(PackageServiceDumpProto.SharedLibraryProto.IS_JAR, isJar); 23222 if (isJar) { 23223 proto.write(PackageServiceDumpProto.SharedLibraryProto.PATH, libEntry.path); 23224 } else { 23225 proto.write(PackageServiceDumpProto.SharedLibraryProto.APK, libEntry.apk); 23226 } 23227 proto.end(sharedLibraryToken); 23228 } 23229 } 23230 } 23231 23232 private void dumpDexoptStateLPr(PrintWriter pw, String packageName) { 23233 final IndentingPrintWriter ipw = new IndentingPrintWriter(pw, " ", 120); 23234 ipw.println(); 23235 ipw.println("Dexopt state:"); 23236 ipw.increaseIndent(); 23237 Collection<PackageParser.Package> packages = null; 23238 if (packageName != null) { 23239 PackageParser.Package targetPackage = mPackages.get(packageName); 23240 if (targetPackage != null) { 23241 packages = Collections.singletonList(targetPackage); 23242 } else { 23243 ipw.println("Unable to find package: " + packageName); 23244 return; 23245 } 23246 } else { 23247 packages = mPackages.values(); 23248 } 23249 23250 for (PackageParser.Package pkg : packages) { 23251 ipw.println("[" + pkg.packageName + "]"); 23252 ipw.increaseIndent(); 23253 mPackageDexOptimizer.dumpDexoptState(ipw, pkg, 23254 mDexManager.getPackageUseInfoOrDefault(pkg.packageName)); 23255 ipw.decreaseIndent(); 23256 } 23257 } 23258 23259 private void dumpCompilerStatsLPr(PrintWriter pw, String packageName) { 23260 final IndentingPrintWriter ipw = new IndentingPrintWriter(pw, " ", 120); 23261 ipw.println(); 23262 ipw.println("Compiler stats:"); 23263 ipw.increaseIndent(); 23264 Collection<PackageParser.Package> packages = null; 23265 if (packageName != null) { 23266 PackageParser.Package targetPackage = mPackages.get(packageName); 23267 if (targetPackage != null) { 23268 packages = Collections.singletonList(targetPackage); 23269 } else { 23270 ipw.println("Unable to find package: " + packageName); 23271 return; 23272 } 23273 } else { 23274 packages = mPackages.values(); 23275 } 23276 23277 for (PackageParser.Package pkg : packages) { 23278 ipw.println("[" + pkg.packageName + "]"); 23279 ipw.increaseIndent(); 23280 23281 CompilerStats.PackageStats stats = getCompilerPackageStats(pkg.packageName); 23282 if (stats == null) { 23283 ipw.println("(No recorded stats)"); 23284 } else { 23285 stats.dump(ipw); 23286 } 23287 ipw.decreaseIndent(); 23288 } 23289 } 23290 23291 private String dumpDomainString(String packageName) { 23292 List<IntentFilterVerificationInfo> iviList = getIntentFilterVerifications(packageName) 23293 .getList(); 23294 List<IntentFilter> filters = getAllIntentFilters(packageName).getList(); 23295 23296 ArraySet<String> result = new ArraySet<>(); 23297 if (iviList.size() > 0) { 23298 for (IntentFilterVerificationInfo ivi : iviList) { 23299 for (String host : ivi.getDomains()) { 23300 result.add(host); 23301 } 23302 } 23303 } 23304 if (filters != null && filters.size() > 0) { 23305 for (IntentFilter filter : filters) { 23306 if (filter.hasCategory(Intent.CATEGORY_BROWSABLE) 23307 && (filter.hasDataScheme(IntentFilter.SCHEME_HTTP) || 23308 filter.hasDataScheme(IntentFilter.SCHEME_HTTPS))) { 23309 result.addAll(filter.getHostsList()); 23310 } 23311 } 23312 } 23313 23314 StringBuilder sb = new StringBuilder(result.size() * 16); 23315 for (String domain : result) { 23316 if (sb.length() > 0) sb.append(" "); 23317 sb.append(domain); 23318 } 23319 return sb.toString(); 23320 } 23321 23322 // ------- apps on sdcard specific code ------- 23323 static final boolean DEBUG_SD_INSTALL = false; 23324 23325 private static final String SD_ENCRYPTION_KEYSTORE_NAME = "AppsOnSD"; 23326 23327 private static final String SD_ENCRYPTION_ALGORITHM = "AES"; 23328 23329 private boolean mMediaMounted = false; 23330 23331 static String getEncryptKey() { 23332 try { 23333 String sdEncKey = SystemKeyStore.getInstance().retrieveKeyHexString( 23334 SD_ENCRYPTION_KEYSTORE_NAME); 23335 if (sdEncKey == null) { 23336 sdEncKey = SystemKeyStore.getInstance().generateNewKeyHexString(128, 23337 SD_ENCRYPTION_ALGORITHM, SD_ENCRYPTION_KEYSTORE_NAME); 23338 if (sdEncKey == null) { 23339 Slog.e(TAG, "Failed to create encryption keys"); 23340 return null; 23341 } 23342 } 23343 return sdEncKey; 23344 } catch (NoSuchAlgorithmException nsae) { 23345 Slog.e(TAG, "Failed to create encryption keys with exception: " + nsae); 23346 return null; 23347 } catch (IOException ioe) { 23348 Slog.e(TAG, "Failed to retrieve encryption keys with exception: " + ioe); 23349 return null; 23350 } 23351 } 23352 23353 /* 23354 * Update media status on PackageManager. 23355 */ 23356 @Override 23357 public void updateExternalMediaStatus(final boolean mediaStatus, final boolean reportStatus) { 23358 enforceSystemOrRoot("Media status can only be updated by the system"); 23359 // reader; this apparently protects mMediaMounted, but should probably 23360 // be a different lock in that case. 23361 synchronized (mPackages) { 23362 Log.i(TAG, "Updating external media status from " 23363 + (mMediaMounted ? "mounted" : "unmounted") + " to " 23364 + (mediaStatus ? "mounted" : "unmounted")); 23365 if (DEBUG_SD_INSTALL) 23366 Log.i(TAG, "updateExternalMediaStatus:: mediaStatus=" + mediaStatus 23367 + ", mMediaMounted=" + mMediaMounted); 23368 if (mediaStatus == mMediaMounted) { 23369 final Message msg = mHandler.obtainMessage(UPDATED_MEDIA_STATUS, reportStatus ? 1 23370 : 0, -1); 23371 mHandler.sendMessage(msg); 23372 return; 23373 } 23374 mMediaMounted = mediaStatus; 23375 } 23376 // Queue up an async operation since the package installation may take a 23377 // little while. 23378 mHandler.post(new Runnable() { 23379 public void run() { 23380 updateExternalMediaStatusInner(mediaStatus, reportStatus, true); 23381 } 23382 }); 23383 } 23384 23385 /** 23386 * Called by StorageManagerService when the initial ASECs to scan are available. 23387 * Should block until all the ASEC containers are finished being scanned. 23388 */ 23389 public void scanAvailableAsecs() { 23390 updateExternalMediaStatusInner(true, false, false); 23391 } 23392 23393 /* 23394 * Collect information of applications on external media, map them against 23395 * existing containers and update information based on current mount status. 23396 * Please note that we always have to report status if reportStatus has been 23397 * set to true especially when unloading packages. 23398 */ 23399 private void updateExternalMediaStatusInner(boolean isMounted, boolean reportStatus, 23400 boolean externalStorage) { 23401 ArrayMap<AsecInstallArgs, String> processCids = new ArrayMap<>(); 23402 int[] uidArr = EmptyArray.INT; 23403 23404 final String[] list = PackageHelper.getSecureContainerList(); 23405 if (ArrayUtils.isEmpty(list)) { 23406 Log.i(TAG, "No secure containers found"); 23407 } else { 23408 // Process list of secure containers and categorize them 23409 // as active or stale based on their package internal state. 23410 23411 // reader 23412 synchronized (mPackages) { 23413 for (String cid : list) { 23414 // Leave stages untouched for now; installer service owns them 23415 if (PackageInstallerService.isStageName(cid)) continue; 23416 23417 if (DEBUG_SD_INSTALL) 23418 Log.i(TAG, "Processing container " + cid); 23419 String pkgName = getAsecPackageName(cid); 23420 if (pkgName == null) { 23421 Slog.i(TAG, "Found stale container " + cid + " with no package name"); 23422 continue; 23423 } 23424 if (DEBUG_SD_INSTALL) 23425 Log.i(TAG, "Looking for pkg : " + pkgName); 23426 23427 final PackageSetting ps = mSettings.mPackages.get(pkgName); 23428 if (ps == null) { 23429 Slog.i(TAG, "Found stale container " + cid + " with no matching settings"); 23430 continue; 23431 } 23432 23433 /* 23434 * Skip packages that are not external if we're unmounting 23435 * external storage. 23436 */ 23437 if (externalStorage && !isMounted && !isExternal(ps)) { 23438 continue; 23439 } 23440 23441 final AsecInstallArgs args = new AsecInstallArgs(cid, 23442 getAppDexInstructionSets(ps), ps.isForwardLocked()); 23443 // The package status is changed only if the code path 23444 // matches between settings and the container id. 23445 if (ps.codePathString != null 23446 && ps.codePathString.startsWith(args.getCodePath())) { 23447 if (DEBUG_SD_INSTALL) { 23448 Log.i(TAG, "Container : " + cid + " corresponds to pkg : " + pkgName 23449 + " at code path: " + ps.codePathString); 23450 } 23451 23452 // We do have a valid package installed on sdcard 23453 processCids.put(args, ps.codePathString); 23454 final int uid = ps.appId; 23455 if (uid != -1) { 23456 uidArr = ArrayUtils.appendInt(uidArr, uid); 23457 } 23458 } else { 23459 Slog.i(TAG, "Found stale container " + cid + ": expected codePath=" 23460 + ps.codePathString); 23461 } 23462 } 23463 } 23464 23465 Arrays.sort(uidArr); 23466 } 23467 23468 // Process packages with valid entries. 23469 if (isMounted) { 23470 if (DEBUG_SD_INSTALL) 23471 Log.i(TAG, "Loading packages"); 23472 loadMediaPackages(processCids, uidArr, externalStorage); 23473 startCleaningPackages(); 23474 mInstallerService.onSecureContainersAvailable(); 23475 } else { 23476 if (DEBUG_SD_INSTALL) 23477 Log.i(TAG, "Unloading packages"); 23478 unloadMediaPackages(processCids, uidArr, reportStatus); 23479 } 23480 } 23481 23482 private void sendResourcesChangedBroadcast(boolean mediaStatus, boolean replacing, 23483 ArrayList<ApplicationInfo> infos, IIntentReceiver finishedReceiver) { 23484 final int size = infos.size(); 23485 final String[] packageNames = new String[size]; 23486 final int[] packageUids = new int[size]; 23487 for (int i = 0; i < size; i++) { 23488 final ApplicationInfo info = infos.get(i); 23489 packageNames[i] = info.packageName; 23490 packageUids[i] = info.uid; 23491 } 23492 sendResourcesChangedBroadcast(mediaStatus, replacing, packageNames, packageUids, 23493 finishedReceiver); 23494 } 23495 23496 private void sendResourcesChangedBroadcast(boolean mediaStatus, boolean replacing, 23497 ArrayList<String> pkgList, int uidArr[], IIntentReceiver finishedReceiver) { 23498 sendResourcesChangedBroadcast(mediaStatus, replacing, 23499 pkgList.toArray(new String[pkgList.size()]), uidArr, finishedReceiver); 23500 } 23501 23502 private void sendResourcesChangedBroadcast(boolean mediaStatus, boolean replacing, 23503 String[] pkgList, int uidArr[], IIntentReceiver finishedReceiver) { 23504 int size = pkgList.length; 23505 if (size > 0) { 23506 // Send broadcasts here 23507 Bundle extras = new Bundle(); 23508 extras.putStringArray(Intent.EXTRA_CHANGED_PACKAGE_LIST, pkgList); 23509 if (uidArr != null) { 23510 extras.putIntArray(Intent.EXTRA_CHANGED_UID_LIST, uidArr); 23511 } 23512 if (replacing) { 23513 extras.putBoolean(Intent.EXTRA_REPLACING, replacing); 23514 } 23515 String action = mediaStatus ? Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE 23516 : Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE; 23517 sendPackageBroadcast(action, null, extras, 0, null, finishedReceiver, null); 23518 } 23519 } 23520 23521 /* 23522 * Look at potentially valid container ids from processCids If package 23523 * information doesn't match the one on record or package scanning fails, 23524 * the cid is added to list of removeCids. We currently don't delete stale 23525 * containers. 23526 */ 23527 private void loadMediaPackages(ArrayMap<AsecInstallArgs, String> processCids, int[] uidArr, 23528 boolean externalStorage) { 23529 ArrayList<String> pkgList = new ArrayList<String>(); 23530 Set<AsecInstallArgs> keys = processCids.keySet(); 23531 23532 for (AsecInstallArgs args : keys) { 23533 String codePath = processCids.get(args); 23534 if (DEBUG_SD_INSTALL) 23535 Log.i(TAG, "Loading container : " + args.cid); 23536 int retCode = PackageManager.INSTALL_FAILED_CONTAINER_ERROR; 23537 try { 23538 // Make sure there are no container errors first. 23539 if (args.doPreInstall(PackageManager.INSTALL_SUCCEEDED) != PackageManager.INSTALL_SUCCEEDED) { 23540 Slog.e(TAG, "Failed to mount cid : " + args.cid 23541 + " when installing from sdcard"); 23542 continue; 23543 } 23544 // Check code path here. 23545 if (codePath == null || !codePath.startsWith(args.getCodePath())) { 23546 Slog.e(TAG, "Container " + args.cid + " cachepath " + args.getCodePath() 23547 + " does not match one in settings " + codePath); 23548 continue; 23549 } 23550 // Parse package 23551 int parseFlags = mDefParseFlags; 23552 if (args.isExternalAsec()) { 23553 parseFlags |= PackageParser.PARSE_EXTERNAL_STORAGE; 23554 } 23555 if (args.isFwdLocked()) { 23556 parseFlags |= PackageParser.PARSE_FORWARD_LOCK; 23557 } 23558 23559 synchronized (mInstallLock) { 23560 PackageParser.Package pkg = null; 23561 try { 23562 // Sadly we don't know the package name yet to freeze it 23563 pkg = scanPackageTracedLI(new File(codePath), parseFlags, 23564 SCAN_IGNORE_FROZEN, 0, null); 23565 } catch (PackageManagerException e) { 23566 Slog.w(TAG, "Failed to scan " + codePath + ": " + e.getMessage()); 23567 } 23568 // Scan the package 23569 if (pkg != null) { 23570 /* 23571 * TODO why is the lock being held? doPostInstall is 23572 * called in other places without the lock. This needs 23573 * to be straightened out. 23574 */ 23575 // writer 23576 synchronized (mPackages) { 23577 retCode = PackageManager.INSTALL_SUCCEEDED; 23578 pkgList.add(pkg.packageName); 23579 // Post process args 23580 args.doPostInstall(PackageManager.INSTALL_SUCCEEDED, 23581 pkg.applicationInfo.uid); 23582 } 23583 } else { 23584 Slog.i(TAG, "Failed to install pkg from " + codePath + " from sdcard"); 23585 } 23586 } 23587 23588 } finally { 23589 if (retCode != PackageManager.INSTALL_SUCCEEDED) { 23590 Log.w(TAG, "Container " + args.cid + " is stale, retCode=" + retCode); 23591 } 23592 } 23593 } 23594 // writer 23595 synchronized (mPackages) { 23596 // If the platform SDK has changed since the last time we booted, 23597 // we need to re-grant app permission to catch any new ones that 23598 // appear. This is really a hack, and means that apps can in some 23599 // cases get permissions that the user didn't initially explicitly 23600 // allow... it would be nice to have some better way to handle 23601 // this situation. 23602 final VersionInfo ver = externalStorage ? mSettings.getExternalVersion() 23603 : mSettings.getInternalVersion(); 23604 final String volumeUuid = externalStorage ? StorageManager.UUID_PRIMARY_PHYSICAL 23605 : StorageManager.UUID_PRIVATE_INTERNAL; 23606 23607 int updateFlags = UPDATE_PERMISSIONS_ALL; 23608 if (ver.sdkVersion != mSdkVersion) { 23609 logCriticalInfo(Log.INFO, "Platform changed from " + ver.sdkVersion + " to " 23610 + mSdkVersion + "; regranting permissions for external"); 23611 updateFlags |= UPDATE_PERMISSIONS_REPLACE_PKG | UPDATE_PERMISSIONS_REPLACE_ALL; 23612 } 23613 updatePermissionsLPw(null, null, volumeUuid, updateFlags); 23614 23615 // Yay, everything is now upgraded 23616 ver.forceCurrent(); 23617 23618 // can downgrade to reader 23619 // Persist settings 23620 mSettings.writeLPr(); 23621 } 23622 // Send a broadcast to let everyone know we are done processing 23623 if (pkgList.size() > 0) { 23624 sendResourcesChangedBroadcast(true, false, pkgList, uidArr, null); 23625 } 23626 } 23627 23628 /* 23629 * Utility method to unload a list of specified containers 23630 */ 23631 private void unloadAllContainers(Set<AsecInstallArgs> cidArgs) { 23632 // Just unmount all valid containers. 23633 for (AsecInstallArgs arg : cidArgs) { 23634 synchronized (mInstallLock) { 23635 arg.doPostDeleteLI(false); 23636 } 23637 } 23638 } 23639 23640 /* 23641 * Unload packages mounted on external media. This involves deleting package 23642 * data from internal structures, sending broadcasts about disabled packages, 23643 * gc'ing to free up references, unmounting all secure containers 23644 * corresponding to packages on external media, and posting a 23645 * UPDATED_MEDIA_STATUS message if status has been requested. Please note 23646 * that we always have to post this message if status has been requested no 23647 * matter what. 23648 */ 23649 private void unloadMediaPackages(ArrayMap<AsecInstallArgs, String> processCids, int uidArr[], 23650 final boolean reportStatus) { 23651 if (DEBUG_SD_INSTALL) 23652 Log.i(TAG, "unloading media packages"); 23653 ArrayList<String> pkgList = new ArrayList<String>(); 23654 ArrayList<AsecInstallArgs> failedList = new ArrayList<AsecInstallArgs>(); 23655 final Set<AsecInstallArgs> keys = processCids.keySet(); 23656 for (AsecInstallArgs args : keys) { 23657 String pkgName = args.getPackageName(); 23658 if (DEBUG_SD_INSTALL) 23659 Log.i(TAG, "Trying to unload pkg : " + pkgName); 23660 // Delete package internally 23661 PackageRemovedInfo outInfo = new PackageRemovedInfo(this); 23662 synchronized (mInstallLock) { 23663 final int deleteFlags = PackageManager.DELETE_KEEP_DATA; 23664 final boolean res; 23665 try (PackageFreezer freezer = freezePackageForDelete(pkgName, deleteFlags, 23666 "unloadMediaPackages")) { 23667 res = deletePackageLIF(pkgName, null, false, null, deleteFlags, outInfo, false, 23668 null); 23669 } 23670 if (res) { 23671 pkgList.add(pkgName); 23672 } else { 23673 Slog.e(TAG, "Failed to delete pkg from sdcard : " + pkgName); 23674 failedList.add(args); 23675 } 23676 } 23677 } 23678 23679 // reader 23680 synchronized (mPackages) { 23681 // We didn't update the settings after removing each package; 23682 // write them now for all packages. 23683 mSettings.writeLPr(); 23684 } 23685 23686 // We have to absolutely send UPDATED_MEDIA_STATUS only 23687 // after confirming that all the receivers processed the ordered 23688 // broadcast when packages get disabled, force a gc to clean things up. 23689 // and unload all the containers. 23690 if (pkgList.size() > 0) { 23691 sendResourcesChangedBroadcast(false, false, pkgList, uidArr, 23692 new IIntentReceiver.Stub() { 23693 public void performReceive(Intent intent, int resultCode, String data, 23694 Bundle extras, boolean ordered, boolean sticky, 23695 int sendingUser) throws RemoteException { 23696 Message msg = mHandler.obtainMessage(UPDATED_MEDIA_STATUS, 23697 reportStatus ? 1 : 0, 1, keys); 23698 mHandler.sendMessage(msg); 23699 } 23700 }); 23701 } else { 23702 Message msg = mHandler.obtainMessage(UPDATED_MEDIA_STATUS, reportStatus ? 1 : 0, -1, 23703 keys); 23704 mHandler.sendMessage(msg); 23705 } 23706 } 23707 23708 private void loadPrivatePackages(final VolumeInfo vol) { 23709 mHandler.post(new Runnable() { 23710 @Override 23711 public void run() { 23712 loadPrivatePackagesInner(vol); 23713 } 23714 }); 23715 } 23716 23717 private void loadPrivatePackagesInner(VolumeInfo vol) { 23718 final String volumeUuid = vol.fsUuid; 23719 if (TextUtils.isEmpty(volumeUuid)) { 23720 Slog.e(TAG, "Loading internal storage is probably a mistake; ignoring"); 23721 return; 23722 } 23723 23724 final ArrayList<PackageFreezer> freezers = new ArrayList<>(); 23725 final ArrayList<ApplicationInfo> loaded = new ArrayList<>(); 23726 final int parseFlags = mDefParseFlags | PackageParser.PARSE_EXTERNAL_STORAGE; 23727 23728 final VersionInfo ver; 23729 final List<PackageSetting> packages; 23730 synchronized (mPackages) { 23731 ver = mSettings.findOrCreateVersion(volumeUuid); 23732 packages = mSettings.getVolumePackagesLPr(volumeUuid); 23733 } 23734 23735 for (PackageSetting ps : packages) { 23736 freezers.add(freezePackage(ps.name, "loadPrivatePackagesInner")); 23737 synchronized (mInstallLock) { 23738 final PackageParser.Package pkg; 23739 try { 23740 pkg = scanPackageTracedLI(ps.codePath, parseFlags, SCAN_INITIAL, 0, null); 23741 loaded.add(pkg.applicationInfo); 23742 23743 } catch (PackageManagerException e) { 23744 Slog.w(TAG, "Failed to scan " + ps.codePath + ": " + e.getMessage()); 23745 } 23746 23747 if (!Build.FINGERPRINT.equals(ver.fingerprint)) { 23748 clearAppDataLIF(ps.pkg, UserHandle.USER_ALL, 23749 StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE 23750 | Installer.FLAG_CLEAR_CODE_CACHE_ONLY); 23751 } 23752 } 23753 } 23754 23755 // Reconcile app data for all started/unlocked users 23756 final StorageManager sm = mContext.getSystemService(StorageManager.class); 23757 final UserManager um = mContext.getSystemService(UserManager.class); 23758 UserManagerInternal umInternal = getUserManagerInternal(); 23759 for (UserInfo user : um.getUsers()) { 23760 final int flags; 23761 if (umInternal.isUserUnlockingOrUnlocked(user.id)) { 23762 flags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE; 23763 } else if (umInternal.isUserRunning(user.id)) { 23764 flags = StorageManager.FLAG_STORAGE_DE; 23765 } else { 23766 continue; 23767 } 23768 23769 try { 23770 sm.prepareUserStorage(volumeUuid, user.id, user.serialNumber, flags); 23771 synchronized (mInstallLock) { 23772 reconcileAppsDataLI(volumeUuid, user.id, flags, true /* migrateAppData */); 23773 } 23774 } catch (IllegalStateException e) { 23775 // Device was probably ejected, and we'll process that event momentarily 23776 Slog.w(TAG, "Failed to prepare storage: " + e); 23777 } 23778 } 23779 23780 synchronized (mPackages) { 23781 int updateFlags = UPDATE_PERMISSIONS_ALL; 23782 if (ver.sdkVersion != mSdkVersion) { 23783 logCriticalInfo(Log.INFO, "Platform changed from " + ver.sdkVersion + " to " 23784 + mSdkVersion + "; regranting permissions for " + volumeUuid); 23785 updateFlags |= UPDATE_PERMISSIONS_REPLACE_PKG | UPDATE_PERMISSIONS_REPLACE_ALL; 23786 } 23787 updatePermissionsLPw(null, null, volumeUuid, updateFlags); 23788 23789 // Yay, everything is now upgraded 23790 ver.forceCurrent(); 23791 23792 mSettings.writeLPr(); 23793 } 23794 23795 for (PackageFreezer freezer : freezers) { 23796 freezer.close(); 23797 } 23798 23799 if (DEBUG_INSTALL) Slog.d(TAG, "Loaded packages " + loaded); 23800 sendResourcesChangedBroadcast(true, false, loaded, null); 23801 mLoadedVolumes.add(vol.getId()); 23802 } 23803 23804 private void unloadPrivatePackages(final VolumeInfo vol) { 23805 mHandler.post(new Runnable() { 23806 @Override 23807 public void run() { 23808 unloadPrivatePackagesInner(vol); 23809 } 23810 }); 23811 } 23812 23813 private void unloadPrivatePackagesInner(VolumeInfo vol) { 23814 final String volumeUuid = vol.fsUuid; 23815 if (TextUtils.isEmpty(volumeUuid)) { 23816 Slog.e(TAG, "Unloading internal storage is probably a mistake; ignoring"); 23817 return; 23818 } 23819 23820 final ArrayList<ApplicationInfo> unloaded = new ArrayList<>(); 23821 synchronized (mInstallLock) { 23822 synchronized (mPackages) { 23823 final List<PackageSetting> packages = mSettings.getVolumePackagesLPr(volumeUuid); 23824 for (PackageSetting ps : packages) { 23825 if (ps.pkg == null) continue; 23826 23827 final ApplicationInfo info = ps.pkg.applicationInfo; 23828 final int deleteFlags = PackageManager.DELETE_KEEP_DATA; 23829 final PackageRemovedInfo outInfo = new PackageRemovedInfo(this); 23830 23831 try (PackageFreezer freezer = freezePackageForDelete(ps.name, deleteFlags, 23832 "unloadPrivatePackagesInner")) { 23833 if (deletePackageLIF(ps.name, null, false, null, deleteFlags, outInfo, 23834 false, null)) { 23835 unloaded.add(info); 23836 } else { 23837 Slog.w(TAG, "Failed to unload " + ps.codePath); 23838 } 23839 } 23840 23841 // Try very hard to release any references to this package 23842 // so we don't risk the system server being killed due to 23843 // open FDs 23844 AttributeCache.instance().removePackage(ps.name); 23845 } 23846 23847 mSettings.writeLPr(); 23848 } 23849 } 23850 23851 if (DEBUG_INSTALL) Slog.d(TAG, "Unloaded packages " + unloaded); 23852 sendResourcesChangedBroadcast(false, false, unloaded, null); 23853 mLoadedVolumes.remove(vol.getId()); 23854 23855 // Try very hard to release any references to this path so we don't risk 23856 // the system server being killed due to open FDs 23857 ResourcesManager.getInstance().invalidatePath(vol.getPath().getAbsolutePath()); 23858 23859 for (int i = 0; i < 3; i++) { 23860 System.gc(); 23861 System.runFinalization(); 23862 } 23863 } 23864 23865 private void assertPackageKnown(String volumeUuid, String packageName) 23866 throws PackageManagerException { 23867 synchronized (mPackages) { 23868 // Normalize package name to handle renamed packages 23869 packageName = normalizePackageNameLPr(packageName); 23870 23871 final PackageSetting ps = mSettings.mPackages.get(packageName); 23872 if (ps == null) { 23873 throw new PackageManagerException("Package " + packageName + " is unknown"); 23874 } else if (!TextUtils.equals(volumeUuid, ps.volumeUuid)) { 23875 throw new PackageManagerException( 23876 "Package " + packageName + " found on unknown volume " + volumeUuid 23877 + "; expected volume " + ps.volumeUuid); 23878 } 23879 } 23880 } 23881 23882 private void assertPackageKnownAndInstalled(String volumeUuid, String packageName, int userId) 23883 throws PackageManagerException { 23884 synchronized (mPackages) { 23885 // Normalize package name to handle renamed packages 23886 packageName = normalizePackageNameLPr(packageName); 23887 23888 final PackageSetting ps = mSettings.mPackages.get(packageName); 23889 if (ps == null) { 23890 throw new PackageManagerException("Package " + packageName + " is unknown"); 23891 } else if (!TextUtils.equals(volumeUuid, ps.volumeUuid)) { 23892 throw new PackageManagerException( 23893 "Package " + packageName + " found on unknown volume " + volumeUuid 23894 + "; expected volume " + ps.volumeUuid); 23895 } else if (!ps.getInstalled(userId)) { 23896 throw new PackageManagerException( 23897 "Package " + packageName + " not installed for user " + userId); 23898 } 23899 } 23900 } 23901 23902 private List<String> collectAbsoluteCodePaths() { 23903 synchronized (mPackages) { 23904 List<String> codePaths = new ArrayList<>(); 23905 final int packageCount = mSettings.mPackages.size(); 23906 for (int i = 0; i < packageCount; i++) { 23907 final PackageSetting ps = mSettings.mPackages.valueAt(i); 23908 codePaths.add(ps.codePath.getAbsolutePath()); 23909 } 23910 return codePaths; 23911 } 23912 } 23913 23914 /** 23915 * Examine all apps present on given mounted volume, and destroy apps that 23916 * aren't expected, either due to uninstallation or reinstallation on 23917 * another volume. 23918 */ 23919 private void reconcileApps(String volumeUuid) { 23920 List<String> absoluteCodePaths = collectAbsoluteCodePaths(); 23921 List<File> filesToDelete = null; 23922 23923 final File[] files = FileUtils.listFilesOrEmpty( 23924 Environment.getDataAppDirectory(volumeUuid)); 23925 for (File file : files) { 23926 final boolean isPackage = (isApkFile(file) || file.isDirectory()) 23927 && !PackageInstallerService.isStageName(file.getName()); 23928 if (!isPackage) { 23929 // Ignore entries which are not packages 23930 continue; 23931 } 23932 23933 String absolutePath = file.getAbsolutePath(); 23934 23935 boolean pathValid = false; 23936 final int absoluteCodePathCount = absoluteCodePaths.size(); 23937 for (int i = 0; i < absoluteCodePathCount; i++) { 23938 String absoluteCodePath = absoluteCodePaths.get(i); 23939 if (absolutePath.startsWith(absoluteCodePath)) { 23940 pathValid = true; 23941 break; 23942 } 23943 } 23944 23945 if (!pathValid) { 23946 if (filesToDelete == null) { 23947 filesToDelete = new ArrayList<>(); 23948 } 23949 filesToDelete.add(file); 23950 } 23951 } 23952 23953 if (filesToDelete != null) { 23954 final int fileToDeleteCount = filesToDelete.size(); 23955 for (int i = 0; i < fileToDeleteCount; i++) { 23956 File fileToDelete = filesToDelete.get(i); 23957 logCriticalInfo(Log.WARN, "Destroying orphaned" + fileToDelete); 23958 synchronized (mInstallLock) { 23959 removeCodePathLI(fileToDelete); 23960 } 23961 } 23962 } 23963 } 23964 23965 /** 23966 * Reconcile all app data for the given user. 23967 * <p> 23968 * Verifies that directories exist and that ownership and labeling is 23969 * correct for all installed apps on all mounted volumes. 23970 */ 23971 void reconcileAppsData(int userId, int flags, boolean migrateAppsData) { 23972 final StorageManager storage = mContext.getSystemService(StorageManager.class); 23973 for (VolumeInfo vol : storage.getWritablePrivateVolumes()) { 23974 final String volumeUuid = vol.getFsUuid(); 23975 synchronized (mInstallLock) { 23976 reconcileAppsDataLI(volumeUuid, userId, flags, migrateAppsData); 23977 } 23978 } 23979 } 23980 23981 private void reconcileAppsDataLI(String volumeUuid, int userId, int flags, 23982 boolean migrateAppData) { 23983 reconcileAppsDataLI(volumeUuid, userId, flags, migrateAppData, false /* onlyCoreApps */); 23984 } 23985 23986 /** 23987 * Reconcile all app data on given mounted volume. 23988 * <p> 23989 * Destroys app data that isn't expected, either due to uninstallation or 23990 * reinstallation on another volume. 23991 * <p> 23992 * Verifies that directories exist and that ownership and labeling is 23993 * correct for all installed apps. 23994 * @returns list of skipped non-core packages (if {@code onlyCoreApps} is true) 23995 */ 23996 private List<String> reconcileAppsDataLI(String volumeUuid, int userId, int flags, 23997 boolean migrateAppData, boolean onlyCoreApps) { 23998 Slog.v(TAG, "reconcileAppsData for " + volumeUuid + " u" + userId + " 0x" 23999 + Integer.toHexString(flags) + " migrateAppData=" + migrateAppData); 24000 List<String> result = onlyCoreApps ? new ArrayList<>() : null; 24001 24002 final File ceDir = Environment.getDataUserCeDirectory(volumeUuid, userId); 24003 final File deDir = Environment.getDataUserDeDirectory(volumeUuid, userId); 24004 24005 // First look for stale data that doesn't belong, and check if things 24006 // have changed since we did our last restorecon 24007 if ((flags & StorageManager.FLAG_STORAGE_CE) != 0) { 24008 if (StorageManager.isFileEncryptedNativeOrEmulated() 24009 && !StorageManager.isUserKeyUnlocked(userId)) { 24010 throw new RuntimeException( 24011 "Yikes, someone asked us to reconcile CE storage while " + userId 24012 + " was still locked; this would have caused massive data loss!"); 24013 } 24014 24015 final File[] files = FileUtils.listFilesOrEmpty(ceDir); 24016 for (File file : files) { 24017 final String packageName = file.getName(); 24018 try { 24019 assertPackageKnownAndInstalled(volumeUuid, packageName, userId); 24020 } catch (PackageManagerException e) { 24021 logCriticalInfo(Log.WARN, "Destroying " + file + " due to: " + e); 24022 try { 24023 mInstaller.destroyAppData(volumeUuid, packageName, userId, 24024 StorageManager.FLAG_STORAGE_CE, 0); 24025 } catch (InstallerException e2) { 24026 logCriticalInfo(Log.WARN, "Failed to destroy: " + e2); 24027 } 24028 } 24029 } 24030 } 24031 if ((flags & StorageManager.FLAG_STORAGE_DE) != 0) { 24032 final File[] files = FileUtils.listFilesOrEmpty(deDir); 24033 for (File file : files) { 24034 final String packageName = file.getName(); 24035 try { 24036 assertPackageKnownAndInstalled(volumeUuid, packageName, userId); 24037 } catch (PackageManagerException e) { 24038 logCriticalInfo(Log.WARN, "Destroying " + file + " due to: " + e); 24039 try { 24040 mInstaller.destroyAppData(volumeUuid, packageName, userId, 24041 StorageManager.FLAG_STORAGE_DE, 0); 24042 } catch (InstallerException e2) { 24043 logCriticalInfo(Log.WARN, "Failed to destroy: " + e2); 24044 } 24045 } 24046 } 24047 } 24048 24049 // Ensure that data directories are ready to roll for all packages 24050 // installed for this volume and user 24051 final List<PackageSetting> packages; 24052 synchronized (mPackages) { 24053 packages = mSettings.getVolumePackagesLPr(volumeUuid); 24054 } 24055 int preparedCount = 0; 24056 for (PackageSetting ps : packages) { 24057 final String packageName = ps.name; 24058 if (ps.pkg == null) { 24059 Slog.w(TAG, "Odd, missing scanned package " + packageName); 24060 // TODO: might be due to legacy ASEC apps; we should circle back 24061 // and reconcile again once they're scanned 24062 continue; 24063 } 24064 // Skip non-core apps if requested 24065 if (onlyCoreApps && !ps.pkg.coreApp) { 24066 result.add(packageName); 24067 continue; 24068 } 24069 24070 if (ps.getInstalled(userId)) { 24071 prepareAppDataAndMigrateLIF(ps.pkg, userId, flags, migrateAppData); 24072 preparedCount++; 24073 } 24074 } 24075 24076 Slog.v(TAG, "reconcileAppsData finished " + preparedCount + " packages"); 24077 return result; 24078 } 24079 24080 /** 24081 * Prepare app data for the given app just after it was installed or 24082 * upgraded. This method carefully only touches users that it's installed 24083 * for, and it forces a restorecon to handle any seinfo changes. 24084 * <p> 24085 * Verifies that directories exist and that ownership and labeling is 24086 * correct for all installed apps. If there is an ownership mismatch, it 24087 * will try recovering system apps by wiping data; third-party app data is 24088 * left intact. 24089 * <p> 24090 * <em>Note: To avoid a deadlock, do not call this method with {@code mPackages} lock held</em> 24091 */ 24092 private void prepareAppDataAfterInstallLIF(PackageParser.Package pkg) { 24093 final PackageSetting ps; 24094 synchronized (mPackages) { 24095 ps = mSettings.mPackages.get(pkg.packageName); 24096 mSettings.writeKernelMappingLPr(ps); 24097 } 24098 24099 final UserManager um = mContext.getSystemService(UserManager.class); 24100 UserManagerInternal umInternal = getUserManagerInternal(); 24101 for (UserInfo user : um.getUsers()) { 24102 final int flags; 24103 if (umInternal.isUserUnlockingOrUnlocked(user.id)) { 24104 flags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE; 24105 } else if (umInternal.isUserRunning(user.id)) { 24106 flags = StorageManager.FLAG_STORAGE_DE; 24107 } else { 24108 continue; 24109 } 24110 24111 if (ps.getInstalled(user.id)) { 24112 // TODO: when user data is locked, mark that we're still dirty 24113 prepareAppDataLIF(pkg, user.id, flags); 24114 } 24115 } 24116 } 24117 24118 /** 24119 * Prepare app data for the given app. 24120 * <p> 24121 * Verifies that directories exist and that ownership and labeling is 24122 * correct for all installed apps. If there is an ownership mismatch, this 24123 * will try recovering system apps by wiping data; third-party app data is 24124 * left intact. 24125 */ 24126 private void prepareAppDataLIF(PackageParser.Package pkg, int userId, int flags) { 24127 if (pkg == null) { 24128 Slog.wtf(TAG, "Package was null!", new Throwable()); 24129 return; 24130 } 24131 prepareAppDataLeafLIF(pkg, userId, flags); 24132 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 24133 for (int i = 0; i < childCount; i++) { 24134 prepareAppDataLeafLIF(pkg.childPackages.get(i), userId, flags); 24135 } 24136 } 24137 24138 private void prepareAppDataAndMigrateLIF(PackageParser.Package pkg, int userId, int flags, 24139 boolean maybeMigrateAppData) { 24140 prepareAppDataLIF(pkg, userId, flags); 24141 24142 if (maybeMigrateAppData && maybeMigrateAppDataLIF(pkg, userId)) { 24143 // We may have just shuffled around app data directories, so 24144 // prepare them one more time 24145 prepareAppDataLIF(pkg, userId, flags); 24146 } 24147 } 24148 24149 private void prepareAppDataLeafLIF(PackageParser.Package pkg, int userId, int flags) { 24150 if (DEBUG_APP_DATA) { 24151 Slog.v(TAG, "prepareAppData for " + pkg.packageName + " u" + userId + " 0x" 24152 + Integer.toHexString(flags)); 24153 } 24154 24155 final String volumeUuid = pkg.volumeUuid; 24156 final String packageName = pkg.packageName; 24157 final ApplicationInfo app = pkg.applicationInfo; 24158 final int appId = UserHandle.getAppId(app.uid); 24159 24160 Preconditions.checkNotNull(app.seInfo); 24161 24162 long ceDataInode = -1; 24163 try { 24164 ceDataInode = mInstaller.createAppData(volumeUuid, packageName, userId, flags, 24165 appId, app.seInfo, app.targetSdkVersion); 24166 } catch (InstallerException e) { 24167 if (app.isSystemApp()) { 24168 logCriticalInfo(Log.ERROR, "Failed to create app data for " + packageName 24169 + ", but trying to recover: " + e); 24170 destroyAppDataLeafLIF(pkg, userId, flags); 24171 try { 24172 ceDataInode = mInstaller.createAppData(volumeUuid, packageName, userId, flags, 24173 appId, app.seInfo, app.targetSdkVersion); 24174 logCriticalInfo(Log.DEBUG, "Recovery succeeded!"); 24175 } catch (InstallerException e2) { 24176 logCriticalInfo(Log.DEBUG, "Recovery failed!"); 24177 } 24178 } else { 24179 Slog.e(TAG, "Failed to create app data for " + packageName + ": " + e); 24180 } 24181 } 24182 24183 if ((flags & StorageManager.FLAG_STORAGE_CE) != 0 && ceDataInode != -1) { 24184 // TODO: mark this structure as dirty so we persist it! 24185 synchronized (mPackages) { 24186 final PackageSetting ps = mSettings.mPackages.get(packageName); 24187 if (ps != null) { 24188 ps.setCeDataInode(ceDataInode, userId); 24189 } 24190 } 24191 } 24192 24193 prepareAppDataContentsLeafLIF(pkg, userId, flags); 24194 } 24195 24196 private void prepareAppDataContentsLIF(PackageParser.Package pkg, int userId, int flags) { 24197 if (pkg == null) { 24198 Slog.wtf(TAG, "Package was null!", new Throwable()); 24199 return; 24200 } 24201 prepareAppDataContentsLeafLIF(pkg, userId, flags); 24202 final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; 24203 for (int i = 0; i < childCount; i++) { 24204 prepareAppDataContentsLeafLIF(pkg.childPackages.get(i), userId, flags); 24205 } 24206 } 24207 24208 private void prepareAppDataContentsLeafLIF(PackageParser.Package pkg, int userId, int flags) { 24209 final String volumeUuid = pkg.volumeUuid; 24210 final String packageName = pkg.packageName; 24211 final ApplicationInfo app = pkg.applicationInfo; 24212 24213 if ((flags & StorageManager.FLAG_STORAGE_CE) != 0) { 24214 // Create a native library symlink only if we have native libraries 24215 // and if the native libraries are 32 bit libraries. We do not provide 24216 // this symlink for 64 bit libraries. 24217 if (app.primaryCpuAbi != null && !VMRuntime.is64BitAbi(app.primaryCpuAbi)) { 24218 final String nativeLibPath = app.nativeLibraryDir; 24219 try { 24220 mInstaller.linkNativeLibraryDirectory(volumeUuid, packageName, 24221 nativeLibPath, userId); 24222 } catch (InstallerException e) { 24223 Slog.e(TAG, "Failed to link native for " + packageName + ": " + e); 24224 } 24225 } 24226 } 24227 } 24228 24229 /** 24230 * For system apps on non-FBE devices, this method migrates any existing 24231 * CE/DE data to match the {@code defaultToDeviceProtectedStorage} flag 24232 * requested by the app. 24233 */ 24234 private boolean maybeMigrateAppDataLIF(PackageParser.Package pkg, int userId) { 24235 if (pkg.isSystemApp() && !StorageManager.isFileEncryptedNativeOrEmulated() 24236 && PackageManager.APPLY_DEFAULT_TO_DEVICE_PROTECTED_STORAGE) { 24237 final int storageTarget = pkg.applicationInfo.isDefaultToDeviceProtectedStorage() 24238 ? StorageManager.FLAG_STORAGE_DE : StorageManager.FLAG_STORAGE_CE; 24239 try { 24240 mInstaller.migrateAppData(pkg.volumeUuid, pkg.packageName, userId, 24241 storageTarget); 24242 } catch (InstallerException e) { 24243 logCriticalInfo(Log.WARN, 24244 "Failed to migrate " + pkg.packageName + ": " + e.getMessage()); 24245 } 24246 return true; 24247 } else { 24248 return false; 24249 } 24250 } 24251 24252 public PackageFreezer freezePackage(String packageName, String killReason) { 24253 return freezePackage(packageName, UserHandle.USER_ALL, killReason); 24254 } 24255 24256 public PackageFreezer freezePackage(String packageName, int userId, String killReason) { 24257 return new PackageFreezer(packageName, userId, killReason); 24258 } 24259 24260 public PackageFreezer freezePackageForInstall(String packageName, int installFlags, 24261 String killReason) { 24262 return freezePackageForInstall(packageName, UserHandle.USER_ALL, installFlags, killReason); 24263 } 24264 24265 public PackageFreezer freezePackageForInstall(String packageName, int userId, int installFlags, 24266 String killReason) { 24267 if ((installFlags & PackageManager.INSTALL_DONT_KILL_APP) != 0) { 24268 return new PackageFreezer(); 24269 } else { 24270 return freezePackage(packageName, userId, killReason); 24271 } 24272 } 24273 24274 public PackageFreezer freezePackageForDelete(String packageName, int deleteFlags, 24275 String killReason) { 24276 return freezePackageForDelete(packageName, UserHandle.USER_ALL, deleteFlags, killReason); 24277 } 24278 24279 public PackageFreezer freezePackageForDelete(String packageName, int userId, int deleteFlags, 24280 String killReason) { 24281 if ((deleteFlags & PackageManager.DELETE_DONT_KILL_APP) != 0) { 24282 return new PackageFreezer(); 24283 } else { 24284 return freezePackage(packageName, userId, killReason); 24285 } 24286 } 24287 24288 /** 24289 * Class that freezes and kills the given package upon creation, and 24290 * unfreezes it upon closing. This is typically used when doing surgery on 24291 * app code/data to prevent the app from running while you're working. 24292 */ 24293 private class PackageFreezer implements AutoCloseable { 24294 private final String mPackageName; 24295 private final PackageFreezer[] mChildren; 24296 24297 private final boolean mWeFroze; 24298 24299 private final AtomicBoolean mClosed = new AtomicBoolean(); 24300 private final CloseGuard mCloseGuard = CloseGuard.get(); 24301 24302 /** 24303 * Create and return a stub freezer that doesn't actually do anything, 24304 * typically used when someone requested 24305 * {@link PackageManager#INSTALL_DONT_KILL_APP} or 24306 * {@link PackageManager#DELETE_DONT_KILL_APP}. 24307 */ 24308 public PackageFreezer() { 24309 mPackageName = null; 24310 mChildren = null; 24311 mWeFroze = false; 24312 mCloseGuard.open("close"); 24313 } 24314 24315 public PackageFreezer(String packageName, int userId, String killReason) { 24316 synchronized (mPackages) { 24317 mPackageName = packageName; 24318 mWeFroze = mFrozenPackages.add(mPackageName); 24319 24320 final PackageSetting ps = mSettings.mPackages.get(mPackageName); 24321 if (ps != null) { 24322 killApplication(ps.name, ps.appId, userId, killReason); 24323 } 24324 24325 final PackageParser.Package p = mPackages.get(packageName); 24326 if (p != null && p.childPackages != null) { 24327 final int N = p.childPackages.size(); 24328 mChildren = new PackageFreezer[N]; 24329 for (int i = 0; i < N; i++) { 24330 mChildren[i] = new PackageFreezer(p.childPackages.get(i).packageName, 24331 userId, killReason); 24332 } 24333 } else { 24334 mChildren = null; 24335 } 24336 } 24337 mCloseGuard.open("close"); 24338 } 24339 24340 @Override 24341 protected void finalize() throws Throwable { 24342 try { 24343 if (mCloseGuard != null) { 24344 mCloseGuard.warnIfOpen(); 24345 } 24346 24347 close(); 24348 } finally { 24349 super.finalize(); 24350 } 24351 } 24352 24353 @Override 24354 public void close() { 24355 mCloseGuard.close(); 24356 if (mClosed.compareAndSet(false, true)) { 24357 synchronized (mPackages) { 24358 if (mWeFroze) { 24359 mFrozenPackages.remove(mPackageName); 24360 } 24361 24362 if (mChildren != null) { 24363 for (PackageFreezer freezer : mChildren) { 24364 freezer.close(); 24365 } 24366 } 24367 } 24368 } 24369 } 24370 } 24371 24372 /** 24373 * Verify that given package is currently frozen. 24374 */ 24375 private void checkPackageFrozen(String packageName) { 24376 synchronized (mPackages) { 24377 if (!mFrozenPackages.contains(packageName)) { 24378 Slog.wtf(TAG, "Expected " + packageName + " to be frozen!", new Throwable()); 24379 } 24380 } 24381 } 24382 24383 @Override 24384 public int movePackage(final String packageName, final String volumeUuid) { 24385 mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MOVE_PACKAGE, null); 24386 24387 final int callingUid = Binder.getCallingUid(); 24388 final UserHandle user = new UserHandle(UserHandle.getUserId(callingUid)); 24389 final int moveId = mNextMoveId.getAndIncrement(); 24390 mHandler.post(new Runnable() { 24391 @Override 24392 public void run() { 24393 try { 24394 movePackageInternal(packageName, volumeUuid, moveId, callingUid, user); 24395 } catch (PackageManagerException e) { 24396 Slog.w(TAG, "Failed to move " + packageName, e); 24397 mMoveCallbacks.notifyStatusChanged(moveId, e.error); 24398 } 24399 } 24400 }); 24401 return moveId; 24402 } 24403 24404 private void movePackageInternal(final String packageName, final String volumeUuid, 24405 final int moveId, final int callingUid, UserHandle user) 24406 throws PackageManagerException { 24407 final StorageManager storage = mContext.getSystemService(StorageManager.class); 24408 final PackageManager pm = mContext.getPackageManager(); 24409 24410 final boolean currentAsec; 24411 final String currentVolumeUuid; 24412 final File codeFile; 24413 final String installerPackageName; 24414 final String packageAbiOverride; 24415 final int appId; 24416 final String seinfo; 24417 final String label; 24418 final int targetSdkVersion; 24419 final PackageFreezer freezer; 24420 final int[] installedUserIds; 24421 24422 // reader 24423 synchronized (mPackages) { 24424 final PackageParser.Package pkg = mPackages.get(packageName); 24425 final PackageSetting ps = mSettings.mPackages.get(packageName); 24426 if (pkg == null 24427 || ps == null 24428 || filterAppAccessLPr(ps, callingUid, user.getIdentifier())) { 24429 throw new PackageManagerException(MOVE_FAILED_DOESNT_EXIST, "Missing package"); 24430 } 24431 if (pkg.applicationInfo.isSystemApp()) { 24432 throw new PackageManagerException(MOVE_FAILED_SYSTEM_PACKAGE, 24433 "Cannot move system application"); 24434 } 24435 24436 final boolean isInternalStorage = VolumeInfo.ID_PRIVATE_INTERNAL.equals(volumeUuid); 24437 final boolean allow3rdPartyOnInternal = mContext.getResources().getBoolean( 24438 com.android.internal.R.bool.config_allow3rdPartyAppOnInternal); 24439 if (isInternalStorage && !allow3rdPartyOnInternal) { 24440 throw new PackageManagerException(MOVE_FAILED_3RD_PARTY_NOT_ALLOWED_ON_INTERNAL, 24441 "3rd party apps are not allowed on internal storage"); 24442 } 24443 24444 if (pkg.applicationInfo.isExternalAsec()) { 24445 currentAsec = true; 24446 currentVolumeUuid = StorageManager.UUID_PRIMARY_PHYSICAL; 24447 } else if (pkg.applicationInfo.isForwardLocked()) { 24448 currentAsec = true; 24449 currentVolumeUuid = "forward_locked"; 24450 } else { 24451 currentAsec = false; 24452 currentVolumeUuid = ps.volumeUuid; 24453 24454 final File probe = new File(pkg.codePath); 24455 final File probeOat = new File(probe, "oat"); 24456 if (!probe.isDirectory() || !probeOat.isDirectory()) { 24457 throw new PackageManagerException(MOVE_FAILED_INTERNAL_ERROR, 24458 "Move only supported for modern cluster style installs"); 24459 } 24460 } 24461 24462 if (Objects.equals(currentVolumeUuid, volumeUuid)) { 24463 throw new PackageManagerException(MOVE_FAILED_INTERNAL_ERROR, 24464 "Package already moved to " + volumeUuid); 24465 } 24466 if (pkg.applicationInfo.isInternal() && isPackageDeviceAdminOnAnyUser(packageName)) { 24467 throw new PackageManagerException(MOVE_FAILED_DEVICE_ADMIN, 24468 "Device admin cannot be moved"); 24469 } 24470 24471 if (mFrozenPackages.contains(packageName)) { 24472 throw new PackageManagerException(MOVE_FAILED_OPERATION_PENDING, 24473 "Failed to move already frozen package"); 24474 } 24475 24476 codeFile = new File(pkg.codePath); 24477 installerPackageName = ps.installerPackageName; 24478 packageAbiOverride = ps.cpuAbiOverrideString; 24479 appId = UserHandle.getAppId(pkg.applicationInfo.uid); 24480 seinfo = pkg.applicationInfo.seInfo; 24481 label = String.valueOf(pm.getApplicationLabel(pkg.applicationInfo)); 24482 targetSdkVersion = pkg.applicationInfo.targetSdkVersion; 24483 freezer = freezePackage(packageName, "movePackageInternal"); 24484 installedUserIds = ps.queryInstalledUsers(sUserManager.getUserIds(), true); 24485 } 24486 24487 final Bundle extras = new Bundle(); 24488 extras.putString(Intent.EXTRA_PACKAGE_NAME, packageName); 24489 extras.putString(Intent.EXTRA_TITLE, label); 24490 mMoveCallbacks.notifyCreated(moveId, extras); 24491 24492 int installFlags; 24493 final boolean moveCompleteApp; 24494 final File measurePath; 24495 24496 if (Objects.equals(StorageManager.UUID_PRIVATE_INTERNAL, volumeUuid)) { 24497 installFlags = INSTALL_INTERNAL; 24498 moveCompleteApp = !currentAsec; 24499 measurePath = Environment.getDataAppDirectory(volumeUuid); 24500 } else if (Objects.equals(StorageManager.UUID_PRIMARY_PHYSICAL, volumeUuid)) { 24501 installFlags = INSTALL_EXTERNAL; 24502 moveCompleteApp = false; 24503 measurePath = storage.getPrimaryPhysicalVolume().getPath(); 24504 } else { 24505 final VolumeInfo volume = storage.findVolumeByUuid(volumeUuid); 24506 if (volume == null || volume.getType() != VolumeInfo.TYPE_PRIVATE 24507 || !volume.isMountedWritable()) { 24508 freezer.close(); 24509 throw new PackageManagerException(MOVE_FAILED_INTERNAL_ERROR, 24510 "Move location not mounted private volume"); 24511 } 24512 24513 Preconditions.checkState(!currentAsec); 24514 24515 installFlags = INSTALL_INTERNAL; 24516 moveCompleteApp = true; 24517 measurePath = Environment.getDataAppDirectory(volumeUuid); 24518 } 24519 24520 // If we're moving app data around, we need all the users unlocked 24521 if (moveCompleteApp) { 24522 for (int userId : installedUserIds) { 24523 if (StorageManager.isFileEncryptedNativeOrEmulated() 24524 && !StorageManager.isUserKeyUnlocked(userId)) { 24525 throw new PackageManagerException(MOVE_FAILED_LOCKED_USER, 24526 "User " + userId + " must be unlocked"); 24527 } 24528 } 24529 } 24530 24531 final PackageStats stats = new PackageStats(null, -1); 24532 synchronized (mInstaller) { 24533 for (int userId : installedUserIds) { 24534 if (!getPackageSizeInfoLI(packageName, userId, stats)) { 24535 freezer.close(); 24536 throw new PackageManagerException(MOVE_FAILED_INTERNAL_ERROR, 24537 "Failed to measure package size"); 24538 } 24539 } 24540 } 24541 24542 if (DEBUG_INSTALL) Slog.d(TAG, "Measured code size " + stats.codeSize + ", data size " 24543 + stats.dataSize); 24544 24545 final long startFreeBytes = measurePath.getUsableSpace(); 24546 final long sizeBytes; 24547 if (moveCompleteApp) { 24548 sizeBytes = stats.codeSize + stats.dataSize; 24549 } else { 24550 sizeBytes = stats.codeSize; 24551 } 24552 24553 if (sizeBytes > storage.getStorageBytesUntilLow(measurePath)) { 24554 freezer.close(); 24555 throw new PackageManagerException(MOVE_FAILED_INTERNAL_ERROR, 24556 "Not enough free space to move"); 24557 } 24558 24559 mMoveCallbacks.notifyStatusChanged(moveId, 10); 24560 24561 final CountDownLatch installedLatch = new CountDownLatch(1); 24562 final IPackageInstallObserver2 installObserver = new IPackageInstallObserver2.Stub() { 24563 @Override 24564 public void onUserActionRequired(Intent intent) throws RemoteException { 24565 throw new IllegalStateException(); 24566 } 24567 24568 @Override 24569 public void onPackageInstalled(String basePackageName, int returnCode, String msg, 24570 Bundle extras) throws RemoteException { 24571 if (DEBUG_INSTALL) Slog.d(TAG, "Install result for move: " 24572 + PackageManager.installStatusToString(returnCode, msg)); 24573 24574 installedLatch.countDown(); 24575 freezer.close(); 24576 24577 final int status = PackageManager.installStatusToPublicStatus(returnCode); 24578 switch (status) { 24579 case PackageInstaller.STATUS_SUCCESS: 24580 mMoveCallbacks.notifyStatusChanged(moveId, 24581 PackageManager.MOVE_SUCCEEDED); 24582 break; 24583 case PackageInstaller.STATUS_FAILURE_STORAGE: 24584 mMoveCallbacks.notifyStatusChanged(moveId, 24585 PackageManager.MOVE_FAILED_INSUFFICIENT_STORAGE); 24586 break; 24587 default: 24588 mMoveCallbacks.notifyStatusChanged(moveId, 24589 PackageManager.MOVE_FAILED_INTERNAL_ERROR); 24590 break; 24591 } 24592 } 24593 }; 24594 24595 final MoveInfo move; 24596 if (moveCompleteApp) { 24597 // Kick off a thread to report progress estimates 24598 new Thread() { 24599 @Override 24600 public void run() { 24601 while (true) { 24602 try { 24603 if (installedLatch.await(1, TimeUnit.SECONDS)) { 24604 break; 24605 } 24606 } catch (InterruptedException ignored) { 24607 } 24608 24609 final long deltaFreeBytes = startFreeBytes - measurePath.getUsableSpace(); 24610 final int progress = 10 + (int) MathUtils.constrain( 24611 ((deltaFreeBytes * 80) / sizeBytes), 0, 80); 24612 mMoveCallbacks.notifyStatusChanged(moveId, progress); 24613 } 24614 } 24615 }.start(); 24616 24617 final String dataAppName = codeFile.getName(); 24618 move = new MoveInfo(moveId, currentVolumeUuid, volumeUuid, packageName, 24619 dataAppName, appId, seinfo, targetSdkVersion); 24620 } else { 24621 move = null; 24622 } 24623 24624 installFlags |= PackageManager.INSTALL_REPLACE_EXISTING; 24625 24626 final Message msg = mHandler.obtainMessage(INIT_COPY); 24627 final OriginInfo origin = OriginInfo.fromExistingFile(codeFile); 24628 final InstallParams params = new InstallParams(origin, move, installObserver, installFlags, 24629 installerPackageName, volumeUuid, null /*verificationInfo*/, user, 24630 packageAbiOverride, null /*grantedPermissions*/, null /*certificates*/, 24631 PackageManager.INSTALL_REASON_UNKNOWN); 24632 params.setTraceMethod("movePackage").setTraceCookie(System.identityHashCode(params)); 24633 msg.obj = params; 24634 24635 Trace.asyncTraceBegin(TRACE_TAG_PACKAGE_MANAGER, "movePackage", 24636 System.identityHashCode(msg.obj)); 24637 Trace.asyncTraceBegin(TRACE_TAG_PACKAGE_MANAGER, "queueInstall", 24638 System.identityHashCode(msg.obj)); 24639 24640 mHandler.sendMessage(msg); 24641 } 24642 24643 @Override 24644 public int movePrimaryStorage(String volumeUuid) throws RemoteException { 24645 mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MOVE_PACKAGE, null); 24646 24647 final int realMoveId = mNextMoveId.getAndIncrement(); 24648 final Bundle extras = new Bundle(); 24649 extras.putString(VolumeRecord.EXTRA_FS_UUID, volumeUuid); 24650 mMoveCallbacks.notifyCreated(realMoveId, extras); 24651 24652 final IPackageMoveObserver callback = new IPackageMoveObserver.Stub() { 24653 @Override 24654 public void onCreated(int moveId, Bundle extras) { 24655 // Ignored 24656 } 24657 24658 @Override 24659 public void onStatusChanged(int moveId, int status, long estMillis) { 24660 mMoveCallbacks.notifyStatusChanged(realMoveId, status, estMillis); 24661 } 24662 }; 24663 24664 final StorageManager storage = mContext.getSystemService(StorageManager.class); 24665 storage.setPrimaryStorageUuid(volumeUuid, callback); 24666 return realMoveId; 24667 } 24668 24669 @Override 24670 public int getMoveStatus(int moveId) { 24671 mContext.enforceCallingOrSelfPermission( 24672 android.Manifest.permission.MOUNT_UNMOUNT_FILESYSTEMS, null); 24673 return mMoveCallbacks.mLastStatus.get(moveId); 24674 } 24675 24676 @Override 24677 public void registerMoveCallback(IPackageMoveObserver callback) { 24678 mContext.enforceCallingOrSelfPermission( 24679 android.Manifest.permission.MOUNT_UNMOUNT_FILESYSTEMS, null); 24680 mMoveCallbacks.register(callback); 24681 } 24682 24683 @Override 24684 public void unregisterMoveCallback(IPackageMoveObserver callback) { 24685 mContext.enforceCallingOrSelfPermission( 24686 android.Manifest.permission.MOUNT_UNMOUNT_FILESYSTEMS, null); 24687 mMoveCallbacks.unregister(callback); 24688 } 24689 24690 @Override 24691 public boolean setInstallLocation(int loc) { 24692 mContext.enforceCallingOrSelfPermission(android.Manifest.permission.WRITE_SECURE_SETTINGS, 24693 null); 24694 if (getInstallLocation() == loc) { 24695 return true; 24696 } 24697 if (loc == PackageHelper.APP_INSTALL_AUTO || loc == PackageHelper.APP_INSTALL_INTERNAL 24698 || loc == PackageHelper.APP_INSTALL_EXTERNAL) { 24699 android.provider.Settings.Global.putInt(mContext.getContentResolver(), 24700 android.provider.Settings.Global.DEFAULT_INSTALL_LOCATION, loc); 24701 return true; 24702 } 24703 return false; 24704 } 24705 24706 @Override 24707 public int getInstallLocation() { 24708 // allow instant app access 24709 return android.provider.Settings.Global.getInt(mContext.getContentResolver(), 24710 android.provider.Settings.Global.DEFAULT_INSTALL_LOCATION, 24711 PackageHelper.APP_INSTALL_AUTO); 24712 } 24713 24714 /** Called by UserManagerService */ 24715 void cleanUpUser(UserManagerService userManager, int userHandle) { 24716 synchronized (mPackages) { 24717 mDirtyUsers.remove(userHandle); 24718 mUserNeedsBadging.delete(userHandle); 24719 mSettings.removeUserLPw(userHandle); 24720 mPendingBroadcasts.remove(userHandle); 24721 mInstantAppRegistry.onUserRemovedLPw(userHandle); 24722 removeUnusedPackagesLPw(userManager, userHandle); 24723 } 24724 } 24725 24726 /** 24727 * We're removing userHandle and would like to remove any downloaded packages 24728 * that are no longer in use by any other user. 24729 * @param userHandle the user being removed 24730 */ 24731 private void removeUnusedPackagesLPw(UserManagerService userManager, final int userHandle) { 24732 final boolean DEBUG_CLEAN_APKS = false; 24733 int [] users = userManager.getUserIds(); 24734 Iterator<PackageSetting> psit = mSettings.mPackages.values().iterator(); 24735 while (psit.hasNext()) { 24736 PackageSetting ps = psit.next(); 24737 if (ps.pkg == null) { 24738 continue; 24739 } 24740 final String packageName = ps.pkg.packageName; 24741 // Skip over if system app 24742 if ((ps.pkgFlags & ApplicationInfo.FLAG_SYSTEM) != 0) { 24743 continue; 24744 } 24745 if (DEBUG_CLEAN_APKS) { 24746 Slog.i(TAG, "Checking package " + packageName); 24747 } 24748 boolean keep = shouldKeepUninstalledPackageLPr(packageName); 24749 if (keep) { 24750 if (DEBUG_CLEAN_APKS) { 24751 Slog.i(TAG, " Keeping package " + packageName + " - requested by DO"); 24752 } 24753 } else { 24754 for (int i = 0; i < users.length; i++) { 24755 if (users[i] != userHandle && ps.getInstalled(users[i])) { 24756 keep = true; 24757 if (DEBUG_CLEAN_APKS) { 24758 Slog.i(TAG, " Keeping package " + packageName + " for user " 24759 + users[i]); 24760 } 24761 break; 24762 } 24763 } 24764 } 24765 if (!keep) { 24766 if (DEBUG_CLEAN_APKS) { 24767 Slog.i(TAG, " Removing package " + packageName); 24768 } 24769 mHandler.post(new Runnable() { 24770 public void run() { 24771 deletePackageX(packageName, PackageManager.VERSION_CODE_HIGHEST, 24772 userHandle, 0); 24773 } //end run 24774 }); 24775 } 24776 } 24777 } 24778 24779 /** Called by UserManagerService */ 24780 void createNewUser(int userId, String[] disallowedPackages) { 24781 synchronized (mInstallLock) { 24782 mSettings.createNewUserLI(this, mInstaller, userId, disallowedPackages); 24783 } 24784 synchronized (mPackages) { 24785 scheduleWritePackageRestrictionsLocked(userId); 24786 scheduleWritePackageListLocked(userId); 24787 applyFactoryDefaultBrowserLPw(userId); 24788 primeDomainVerificationsLPw(userId); 24789 } 24790 } 24791 24792 void onNewUserCreated(final int userId) { 24793 mDefaultPermissionPolicy.grantDefaultPermissions(userId); 24794 // If permission review for legacy apps is required, we represent 24795 // dagerous permissions for such apps as always granted runtime 24796 // permissions to keep per user flag state whether review is needed. 24797 // Hence, if a new user is added we have to propagate dangerous 24798 // permission grants for these legacy apps. 24799 if (mPermissionReviewRequired) { 24800 updatePermissionsLPw(null, null, UPDATE_PERMISSIONS_ALL 24801 | UPDATE_PERMISSIONS_REPLACE_ALL); 24802 } 24803 } 24804 24805 @Override 24806 public VerifierDeviceIdentity getVerifierDeviceIdentity() throws RemoteException { 24807 mContext.enforceCallingOrSelfPermission( 24808 android.Manifest.permission.PACKAGE_VERIFICATION_AGENT, 24809 "Only package verification agents can read the verifier device identity"); 24810 24811 synchronized (mPackages) { 24812 return mSettings.getVerifierDeviceIdentityLPw(); 24813 } 24814 } 24815 24816 @Override 24817 public void setPermissionEnforced(String permission, boolean enforced) { 24818 // TODO: Now that we no longer change GID for storage, this should to away. 24819 mContext.enforceCallingOrSelfPermission(Manifest.permission.GRANT_RUNTIME_PERMISSIONS, 24820 "setPermissionEnforced"); 24821 if (READ_EXTERNAL_STORAGE.equals(permission)) { 24822 synchronized (mPackages) { 24823 if (mSettings.mReadExternalStorageEnforced == null 24824 || mSettings.mReadExternalStorageEnforced != enforced) { 24825 mSettings.mReadExternalStorageEnforced = enforced; 24826 mSettings.writeLPr(); 24827 } 24828 } 24829 // kill any non-foreground processes so we restart them and 24830 // grant/revoke the GID. 24831 final IActivityManager am = ActivityManager.getService(); 24832 if (am != null) { 24833 final long token = Binder.clearCallingIdentity(); 24834 try { 24835 am.killProcessesBelowForeground("setPermissionEnforcement"); 24836 } catch (RemoteException e) { 24837 } finally { 24838 Binder.restoreCallingIdentity(token); 24839 } 24840 } 24841 } else { 24842 throw new IllegalArgumentException("No selective enforcement for " + permission); 24843 } 24844 } 24845 24846 @Override 24847 @Deprecated 24848 public boolean isPermissionEnforced(String permission) { 24849 // allow instant applications 24850 return true; 24851 } 24852 24853 @Override 24854 public boolean isStorageLow() { 24855 // allow instant applications 24856 final long token = Binder.clearCallingIdentity(); 24857 try { 24858 final DeviceStorageMonitorInternal 24859 dsm = LocalServices.getService(DeviceStorageMonitorInternal.class); 24860 if (dsm != null) { 24861 return dsm.isMemoryLow(); 24862 } else { 24863 return false; 24864 } 24865 } finally { 24866 Binder.restoreCallingIdentity(token); 24867 } 24868 } 24869 24870 @Override 24871 public IPackageInstaller getPackageInstaller() { 24872 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 24873 return null; 24874 } 24875 return mInstallerService; 24876 } 24877 24878 private boolean userNeedsBadging(int userId) { 24879 int index = mUserNeedsBadging.indexOfKey(userId); 24880 if (index < 0) { 24881 final UserInfo userInfo; 24882 final long token = Binder.clearCallingIdentity(); 24883 try { 24884 userInfo = sUserManager.getUserInfo(userId); 24885 } finally { 24886 Binder.restoreCallingIdentity(token); 24887 } 24888 final boolean b; 24889 if (userInfo != null && userInfo.isManagedProfile()) { 24890 b = true; 24891 } else { 24892 b = false; 24893 } 24894 mUserNeedsBadging.put(userId, b); 24895 return b; 24896 } 24897 return mUserNeedsBadging.valueAt(index); 24898 } 24899 24900 @Override 24901 public KeySet getKeySetByAlias(String packageName, String alias) { 24902 if (packageName == null || alias == null) { 24903 return null; 24904 } 24905 synchronized(mPackages) { 24906 final PackageParser.Package pkg = mPackages.get(packageName); 24907 if (pkg == null) { 24908 Slog.w(TAG, "KeySet requested for unknown package: " + packageName); 24909 throw new IllegalArgumentException("Unknown package: " + packageName); 24910 } 24911 final PackageSetting ps = (PackageSetting) pkg.mExtras; 24912 if (filterAppAccessLPr(ps, Binder.getCallingUid(), UserHandle.getCallingUserId())) { 24913 Slog.w(TAG, "KeySet requested for filtered package: " + packageName); 24914 throw new IllegalArgumentException("Unknown package: " + packageName); 24915 } 24916 KeySetManagerService ksms = mSettings.mKeySetManagerService; 24917 return new KeySet(ksms.getKeySetByAliasAndPackageNameLPr(packageName, alias)); 24918 } 24919 } 24920 24921 @Override 24922 public KeySet getSigningKeySet(String packageName) { 24923 if (packageName == null) { 24924 return null; 24925 } 24926 synchronized(mPackages) { 24927 final int callingUid = Binder.getCallingUid(); 24928 final int callingUserId = UserHandle.getUserId(callingUid); 24929 final PackageParser.Package pkg = mPackages.get(packageName); 24930 if (pkg == null) { 24931 Slog.w(TAG, "KeySet requested for unknown package: " + packageName); 24932 throw new IllegalArgumentException("Unknown package: " + packageName); 24933 } 24934 final PackageSetting ps = (PackageSetting) pkg.mExtras; 24935 if (filterAppAccessLPr(ps, callingUid, callingUserId)) { 24936 // filter and pretend the package doesn't exist 24937 Slog.w(TAG, "KeySet requested for filtered package: " + packageName 24938 + ", uid:" + callingUid); 24939 throw new IllegalArgumentException("Unknown package: " + packageName); 24940 } 24941 if (pkg.applicationInfo.uid != callingUid 24942 && Process.SYSTEM_UID != callingUid) { 24943 throw new SecurityException("May not access signing KeySet of other apps."); 24944 } 24945 KeySetManagerService ksms = mSettings.mKeySetManagerService; 24946 return new KeySet(ksms.getSigningKeySetByPackageNameLPr(packageName)); 24947 } 24948 } 24949 24950 @Override 24951 public boolean isPackageSignedByKeySet(String packageName, KeySet ks) { 24952 final int callingUid = Binder.getCallingUid(); 24953 if (getInstantAppPackageName(callingUid) != null) { 24954 return false; 24955 } 24956 if (packageName == null || ks == null) { 24957 return false; 24958 } 24959 synchronized(mPackages) { 24960 final PackageParser.Package pkg = mPackages.get(packageName); 24961 if (pkg == null 24962 || filterAppAccessLPr((PackageSetting) pkg.mExtras, callingUid, 24963 UserHandle.getUserId(callingUid))) { 24964 Slog.w(TAG, "KeySet requested for unknown package: " + packageName); 24965 throw new IllegalArgumentException("Unknown package: " + packageName); 24966 } 24967 IBinder ksh = ks.getToken(); 24968 if (ksh instanceof KeySetHandle) { 24969 KeySetManagerService ksms = mSettings.mKeySetManagerService; 24970 return ksms.packageIsSignedByLPr(packageName, (KeySetHandle) ksh); 24971 } 24972 return false; 24973 } 24974 } 24975 24976 @Override 24977 public boolean isPackageSignedByKeySetExactly(String packageName, KeySet ks) { 24978 final int callingUid = Binder.getCallingUid(); 24979 if (getInstantAppPackageName(callingUid) != null) { 24980 return false; 24981 } 24982 if (packageName == null || ks == null) { 24983 return false; 24984 } 24985 synchronized(mPackages) { 24986 final PackageParser.Package pkg = mPackages.get(packageName); 24987 if (pkg == null 24988 || filterAppAccessLPr((PackageSetting) pkg.mExtras, callingUid, 24989 UserHandle.getUserId(callingUid))) { 24990 Slog.w(TAG, "KeySet requested for unknown package: " + packageName); 24991 throw new IllegalArgumentException("Unknown package: " + packageName); 24992 } 24993 IBinder ksh = ks.getToken(); 24994 if (ksh instanceof KeySetHandle) { 24995 KeySetManagerService ksms = mSettings.mKeySetManagerService; 24996 return ksms.packageIsSignedByExactlyLPr(packageName, (KeySetHandle) ksh); 24997 } 24998 return false; 24999 } 25000 } 25001 25002 private void deletePackageIfUnusedLPr(final String packageName) { 25003 PackageSetting ps = mSettings.mPackages.get(packageName); 25004 if (ps == null) { 25005 return; 25006 } 25007 if (!ps.isAnyInstalled(sUserManager.getUserIds())) { 25008 // TODO Implement atomic delete if package is unused 25009 // It is currently possible that the package will be deleted even if it is installed 25010 // after this method returns. 25011 mHandler.post(new Runnable() { 25012 public void run() { 25013 deletePackageX(packageName, PackageManager.VERSION_CODE_HIGHEST, 25014 0, PackageManager.DELETE_ALL_USERS); 25015 } 25016 }); 25017 } 25018 } 25019 25020 /** 25021 * Check and throw if the given before/after packages would be considered a 25022 * downgrade. 25023 */ 25024 private static void checkDowngrade(PackageParser.Package before, PackageInfoLite after) 25025 throws PackageManagerException { 25026 if (after.versionCode < before.mVersionCode) { 25027 throw new PackageManagerException(INSTALL_FAILED_VERSION_DOWNGRADE, 25028 "Update version code " + after.versionCode + " is older than current " 25029 + before.mVersionCode); 25030 } else if (after.versionCode == before.mVersionCode) { 25031 if (after.baseRevisionCode < before.baseRevisionCode) { 25032 throw new PackageManagerException(INSTALL_FAILED_VERSION_DOWNGRADE, 25033 "Update base revision code " + after.baseRevisionCode 25034 + " is older than current " + before.baseRevisionCode); 25035 } 25036 25037 if (!ArrayUtils.isEmpty(after.splitNames)) { 25038 for (int i = 0; i < after.splitNames.length; i++) { 25039 final String splitName = after.splitNames[i]; 25040 final int j = ArrayUtils.indexOf(before.splitNames, splitName); 25041 if (j != -1) { 25042 if (after.splitRevisionCodes[i] < before.splitRevisionCodes[j]) { 25043 throw new PackageManagerException(INSTALL_FAILED_VERSION_DOWNGRADE, 25044 "Update split " + splitName + " revision code " 25045 + after.splitRevisionCodes[i] + " is older than current " 25046 + before.splitRevisionCodes[j]); 25047 } 25048 } 25049 } 25050 } 25051 } 25052 } 25053 25054 private static class MoveCallbacks extends Handler { 25055 private static final int MSG_CREATED = 1; 25056 private static final int MSG_STATUS_CHANGED = 2; 25057 25058 private final RemoteCallbackList<IPackageMoveObserver> 25059 mCallbacks = new RemoteCallbackList<>(); 25060 25061 private final SparseIntArray mLastStatus = new SparseIntArray(); 25062 25063 public MoveCallbacks(Looper looper) { 25064 super(looper); 25065 } 25066 25067 public void register(IPackageMoveObserver callback) { 25068 mCallbacks.register(callback); 25069 } 25070 25071 public void unregister(IPackageMoveObserver callback) { 25072 mCallbacks.unregister(callback); 25073 } 25074 25075 @Override 25076 public void handleMessage(Message msg) { 25077 final SomeArgs args = (SomeArgs) msg.obj; 25078 final int n = mCallbacks.beginBroadcast(); 25079 for (int i = 0; i < n; i++) { 25080 final IPackageMoveObserver callback = mCallbacks.getBroadcastItem(i); 25081 try { 25082 invokeCallback(callback, msg.what, args); 25083 } catch (RemoteException ignored) { 25084 } 25085 } 25086 mCallbacks.finishBroadcast(); 25087 args.recycle(); 25088 } 25089 25090 private void invokeCallback(IPackageMoveObserver callback, int what, SomeArgs args) 25091 throws RemoteException { 25092 switch (what) { 25093 case MSG_CREATED: { 25094 callback.onCreated(args.argi1, (Bundle) args.arg2); 25095 break; 25096 } 25097 case MSG_STATUS_CHANGED: { 25098 callback.onStatusChanged(args.argi1, args.argi2, (long) args.arg3); 25099 break; 25100 } 25101 } 25102 } 25103 25104 private void notifyCreated(int moveId, Bundle extras) { 25105 Slog.v(TAG, "Move " + moveId + " created " + extras.toString()); 25106 25107 final SomeArgs args = SomeArgs.obtain(); 25108 args.argi1 = moveId; 25109 args.arg2 = extras; 25110 obtainMessage(MSG_CREATED, args).sendToTarget(); 25111 } 25112 25113 private void notifyStatusChanged(int moveId, int status) { 25114 notifyStatusChanged(moveId, status, -1); 25115 } 25116 25117 private void notifyStatusChanged(int moveId, int status, long estMillis) { 25118 Slog.v(TAG, "Move " + moveId + " status " + status); 25119 25120 final SomeArgs args = SomeArgs.obtain(); 25121 args.argi1 = moveId; 25122 args.argi2 = status; 25123 args.arg3 = estMillis; 25124 obtainMessage(MSG_STATUS_CHANGED, args).sendToTarget(); 25125 25126 synchronized (mLastStatus) { 25127 mLastStatus.put(moveId, status); 25128 } 25129 } 25130 } 25131 25132 private final static class OnPermissionChangeListeners extends Handler { 25133 private static final int MSG_ON_PERMISSIONS_CHANGED = 1; 25134 25135 private final RemoteCallbackList<IOnPermissionsChangeListener> mPermissionListeners = 25136 new RemoteCallbackList<>(); 25137 25138 public OnPermissionChangeListeners(Looper looper) { 25139 super(looper); 25140 } 25141 25142 @Override 25143 public void handleMessage(Message msg) { 25144 switch (msg.what) { 25145 case MSG_ON_PERMISSIONS_CHANGED: { 25146 final int uid = msg.arg1; 25147 handleOnPermissionsChanged(uid); 25148 } break; 25149 } 25150 } 25151 25152 public void addListenerLocked(IOnPermissionsChangeListener listener) { 25153 mPermissionListeners.register(listener); 25154 25155 } 25156 25157 public void removeListenerLocked(IOnPermissionsChangeListener listener) { 25158 mPermissionListeners.unregister(listener); 25159 } 25160 25161 public void onPermissionsChanged(int uid) { 25162 if (mPermissionListeners.getRegisteredCallbackCount() > 0) { 25163 obtainMessage(MSG_ON_PERMISSIONS_CHANGED, uid, 0).sendToTarget(); 25164 } 25165 } 25166 25167 private void handleOnPermissionsChanged(int uid) { 25168 final int count = mPermissionListeners.beginBroadcast(); 25169 try { 25170 for (int i = 0; i < count; i++) { 25171 IOnPermissionsChangeListener callback = mPermissionListeners 25172 .getBroadcastItem(i); 25173 try { 25174 callback.onPermissionsChanged(uid); 25175 } catch (RemoteException e) { 25176 Log.e(TAG, "Permission listener is dead", e); 25177 } 25178 } 25179 } finally { 25180 mPermissionListeners.finishBroadcast(); 25181 } 25182 } 25183 } 25184 25185 private class PackageManagerNative extends IPackageManagerNative.Stub { 25186 @Override 25187 public String[] getNamesForUids(int[] uids) throws RemoteException { 25188 final String[] results = PackageManagerService.this.getNamesForUids(uids); 25189 // massage results so they can be parsed by the native binder 25190 for (int i = results.length - 1; i >= 0; --i) { 25191 if (results[i] == null) { 25192 results[i] = ""; 25193 } 25194 } 25195 return results; 25196 } 25197 25198 // NB: this differentiates between preloads and sideloads 25199 @Override 25200 public String getInstallerForPackage(String packageName) throws RemoteException { 25201 final String installerName = getInstallerPackageName(packageName); 25202 if (!TextUtils.isEmpty(installerName)) { 25203 return installerName; 25204 } 25205 // differentiate between preload and sideload 25206 int callingUser = UserHandle.getUserId(Binder.getCallingUid()); 25207 ApplicationInfo appInfo = getApplicationInfo(packageName, 25208 /*flags*/ 0, 25209 /*userId*/ callingUser); 25210 if (appInfo != null && (appInfo.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 25211 return "preload"; 25212 } 25213 return ""; 25214 } 25215 25216 @Override 25217 public int getVersionCodeForPackage(String packageName) throws RemoteException { 25218 try { 25219 int callingUser = UserHandle.getUserId(Binder.getCallingUid()); 25220 PackageInfo pInfo = getPackageInfo(packageName, 0, callingUser); 25221 if (pInfo != null) { 25222 return pInfo.versionCode; 25223 } 25224 } catch (Exception e) { 25225 } 25226 return 0; 25227 } 25228 } 25229 25230 private class PackageManagerInternalImpl extends PackageManagerInternal { 25231 @Override 25232 public void setLocationPackagesProvider(PackagesProvider provider) { 25233 synchronized (mPackages) { 25234 mDefaultPermissionPolicy.setLocationPackagesProviderLPw(provider); 25235 } 25236 } 25237 25238 @Override 25239 public void setVoiceInteractionPackagesProvider(PackagesProvider provider) { 25240 synchronized (mPackages) { 25241 mDefaultPermissionPolicy.setVoiceInteractionPackagesProviderLPw(provider); 25242 } 25243 } 25244 25245 @Override 25246 public void setSmsAppPackagesProvider(PackagesProvider provider) { 25247 synchronized (mPackages) { 25248 mDefaultPermissionPolicy.setSmsAppPackagesProviderLPw(provider); 25249 } 25250 } 25251 25252 @Override 25253 public void setDialerAppPackagesProvider(PackagesProvider provider) { 25254 synchronized (mPackages) { 25255 mDefaultPermissionPolicy.setDialerAppPackagesProviderLPw(provider); 25256 } 25257 } 25258 25259 @Override 25260 public void setSimCallManagerPackagesProvider(PackagesProvider provider) { 25261 synchronized (mPackages) { 25262 mDefaultPermissionPolicy.setSimCallManagerPackagesProviderLPw(provider); 25263 } 25264 } 25265 25266 @Override 25267 public void setSyncAdapterPackagesprovider(SyncAdapterPackagesProvider provider) { 25268 synchronized (mPackages) { 25269 mDefaultPermissionPolicy.setSyncAdapterPackagesProviderLPw(provider); 25270 } 25271 } 25272 25273 @Override 25274 public void grantDefaultPermissionsToDefaultSmsApp(String packageName, int userId) { 25275 synchronized (mPackages) { 25276 mDefaultPermissionPolicy.grantDefaultPermissionsToDefaultSmsAppLPr( 25277 packageName, userId); 25278 } 25279 } 25280 25281 @Override 25282 public void grantDefaultPermissionsToDefaultDialerApp(String packageName, int userId) { 25283 synchronized (mPackages) { 25284 mSettings.setDefaultDialerPackageNameLPw(packageName, userId); 25285 mDefaultPermissionPolicy.grantDefaultPermissionsToDefaultDialerAppLPr( 25286 packageName, userId); 25287 } 25288 } 25289 25290 @Override 25291 public void grantDefaultPermissionsToDefaultSimCallManager(String packageName, int userId) { 25292 synchronized (mPackages) { 25293 mDefaultPermissionPolicy.grantDefaultPermissionsToDefaultSimCallManagerLPr( 25294 packageName, userId); 25295 } 25296 } 25297 25298 @Override 25299 public void setKeepUninstalledPackages(final List<String> packageList) { 25300 Preconditions.checkNotNull(packageList); 25301 List<String> removedFromList = null; 25302 synchronized (mPackages) { 25303 if (mKeepUninstalledPackages != null) { 25304 final int packagesCount = mKeepUninstalledPackages.size(); 25305 for (int i = 0; i < packagesCount; i++) { 25306 String oldPackage = mKeepUninstalledPackages.get(i); 25307 if (packageList != null && packageList.contains(oldPackage)) { 25308 continue; 25309 } 25310 if (removedFromList == null) { 25311 removedFromList = new ArrayList<>(); 25312 } 25313 removedFromList.add(oldPackage); 25314 } 25315 } 25316 mKeepUninstalledPackages = new ArrayList<>(packageList); 25317 if (removedFromList != null) { 25318 final int removedCount = removedFromList.size(); 25319 for (int i = 0; i < removedCount; i++) { 25320 deletePackageIfUnusedLPr(removedFromList.get(i)); 25321 } 25322 } 25323 } 25324 } 25325 25326 @Override 25327 public boolean isPermissionsReviewRequired(String packageName, int userId) { 25328 synchronized (mPackages) { 25329 // If we do not support permission review, done. 25330 if (!mPermissionReviewRequired) { 25331 return false; 25332 } 25333 25334 PackageSetting packageSetting = mSettings.mPackages.get(packageName); 25335 if (packageSetting == null) { 25336 return false; 25337 } 25338 25339 // Permission review applies only to apps not supporting the new permission model. 25340 if (packageSetting.pkg.applicationInfo.targetSdkVersion >= Build.VERSION_CODES.M) { 25341 return false; 25342 } 25343 25344 // Legacy apps have the permission and get user consent on launch. 25345 PermissionsState permissionsState = packageSetting.getPermissionsState(); 25346 return permissionsState.isPermissionReviewRequired(userId); 25347 } 25348 } 25349 25350 @Override 25351 public PackageInfo getPackageInfo( 25352 String packageName, int flags, int filterCallingUid, int userId) { 25353 return PackageManagerService.this 25354 .getPackageInfoInternal(packageName, PackageManager.VERSION_CODE_HIGHEST, 25355 flags, filterCallingUid, userId); 25356 } 25357 25358 @Override 25359 public ApplicationInfo getApplicationInfo( 25360 String packageName, int flags, int filterCallingUid, int userId) { 25361 return PackageManagerService.this 25362 .getApplicationInfoInternal(packageName, flags, filterCallingUid, userId); 25363 } 25364 25365 @Override 25366 public ActivityInfo getActivityInfo( 25367 ComponentName component, int flags, int filterCallingUid, int userId) { 25368 return PackageManagerService.this 25369 .getActivityInfoInternal(component, flags, filterCallingUid, userId); 25370 } 25371 25372 @Override 25373 public List<ResolveInfo> queryIntentActivities( 25374 Intent intent, int flags, int filterCallingUid, int userId) { 25375 final String resolvedType = intent.resolveTypeIfNeeded(mContext.getContentResolver()); 25376 return PackageManagerService.this 25377 .queryIntentActivitiesInternal(intent, resolvedType, flags, filterCallingUid, 25378 userId, false /*resolveForStart*/, true /*allowDynamicSplits*/); 25379 } 25380 25381 @Override 25382 public ComponentName getHomeActivitiesAsUser(List<ResolveInfo> allHomeCandidates, 25383 int userId) { 25384 return PackageManagerService.this.getHomeActivitiesAsUser(allHomeCandidates, userId); 25385 } 25386 25387 @Override 25388 public void setDeviceAndProfileOwnerPackages( 25389 int deviceOwnerUserId, String deviceOwnerPackage, 25390 SparseArray<String> profileOwnerPackages) { 25391 mProtectedPackages.setDeviceAndProfileOwnerPackages( 25392 deviceOwnerUserId, deviceOwnerPackage, profileOwnerPackages); 25393 } 25394 25395 @Override 25396 public boolean isPackageDataProtected(int userId, String packageName) { 25397 return mProtectedPackages.isPackageDataProtected(userId, packageName); 25398 } 25399 25400 @Override 25401 public boolean isPackageEphemeral(int userId, String packageName) { 25402 synchronized (mPackages) { 25403 final PackageSetting ps = mSettings.mPackages.get(packageName); 25404 return ps != null ? ps.getInstantApp(userId) : false; 25405 } 25406 } 25407 25408 @Override 25409 public boolean wasPackageEverLaunched(String packageName, int userId) { 25410 synchronized (mPackages) { 25411 return mSettings.wasPackageEverLaunchedLPr(packageName, userId); 25412 } 25413 } 25414 25415 @Override 25416 public void grantRuntimePermission(String packageName, String name, int userId, 25417 boolean overridePolicy) { 25418 PackageManagerService.this.grantRuntimePermission(packageName, name, userId, 25419 overridePolicy); 25420 } 25421 25422 @Override 25423 public void revokeRuntimePermission(String packageName, String name, int userId, 25424 boolean overridePolicy) { 25425 PackageManagerService.this.revokeRuntimePermission(packageName, name, userId, 25426 overridePolicy); 25427 } 25428 25429 @Override 25430 public String getNameForUid(int uid) { 25431 return PackageManagerService.this.getNameForUid(uid); 25432 } 25433 25434 @Override 25435 public void requestInstantAppResolutionPhaseTwo(AuxiliaryResolveInfo responseObj, 25436 Intent origIntent, String resolvedType, String callingPackage, 25437 Bundle verificationBundle, int userId) { 25438 PackageManagerService.this.requestInstantAppResolutionPhaseTwo( 25439 responseObj, origIntent, resolvedType, callingPackage, verificationBundle, 25440 userId); 25441 } 25442 25443 @Override 25444 public void grantEphemeralAccess(int userId, Intent intent, 25445 int targetAppId, int ephemeralAppId) { 25446 synchronized (mPackages) { 25447 mInstantAppRegistry.grantInstantAccessLPw(userId, intent, 25448 targetAppId, ephemeralAppId); 25449 } 25450 } 25451 25452 @Override 25453 public boolean isInstantAppInstallerComponent(ComponentName component) { 25454 synchronized (mPackages) { 25455 return mInstantAppInstallerActivity != null 25456 && mInstantAppInstallerActivity.getComponentName().equals(component); 25457 } 25458 } 25459 25460 @Override 25461 public void pruneInstantApps() { 25462 mInstantAppRegistry.pruneInstantApps(); 25463 } 25464 25465 @Override 25466 public String getSetupWizardPackageName() { 25467 return mSetupWizardPackage; 25468 } 25469 25470 public void setExternalSourcesPolicy(ExternalSourcesPolicy policy) { 25471 if (policy != null) { 25472 mExternalSourcesPolicy = policy; 25473 } 25474 } 25475 25476 @Override 25477 public boolean isPackagePersistent(String packageName) { 25478 synchronized (mPackages) { 25479 PackageParser.Package pkg = mPackages.get(packageName); 25480 return pkg != null 25481 ? ((pkg.applicationInfo.flags&(ApplicationInfo.FLAG_SYSTEM 25482 | ApplicationInfo.FLAG_PERSISTENT)) == 25483 (ApplicationInfo.FLAG_SYSTEM | ApplicationInfo.FLAG_PERSISTENT)) 25484 : false; 25485 } 25486 } 25487 25488 @Override 25489 public List<PackageInfo> getOverlayPackages(int userId) { 25490 final ArrayList<PackageInfo> overlayPackages = new ArrayList<PackageInfo>(); 25491 synchronized (mPackages) { 25492 for (PackageParser.Package p : mPackages.values()) { 25493 if (p.mOverlayTarget != null) { 25494 PackageInfo pkg = generatePackageInfo((PackageSetting)p.mExtras, 0, userId); 25495 if (pkg != null) { 25496 overlayPackages.add(pkg); 25497 } 25498 } 25499 } 25500 } 25501 return overlayPackages; 25502 } 25503 25504 @Override 25505 public List<String> getTargetPackageNames(int userId) { 25506 List<String> targetPackages = new ArrayList<>(); 25507 synchronized (mPackages) { 25508 for (PackageParser.Package p : mPackages.values()) { 25509 if (p.mOverlayTarget == null) { 25510 targetPackages.add(p.packageName); 25511 } 25512 } 25513 } 25514 return targetPackages; 25515 } 25516 25517 @Override 25518 public boolean setEnabledOverlayPackages(int userId, @NonNull String targetPackageName, 25519 @Nullable List<String> overlayPackageNames) { 25520 synchronized (mPackages) { 25521 if (targetPackageName == null || mPackages.get(targetPackageName) == null) { 25522 Slog.e(TAG, "failed to find package " + targetPackageName); 25523 return false; 25524 } 25525 ArrayList<String> overlayPaths = null; 25526 if (overlayPackageNames != null && overlayPackageNames.size() > 0) { 25527 final int N = overlayPackageNames.size(); 25528 overlayPaths = new ArrayList<>(N); 25529 for (int i = 0; i < N; i++) { 25530 final String packageName = overlayPackageNames.get(i); 25531 final PackageParser.Package pkg = mPackages.get(packageName); 25532 if (pkg == null) { 25533 Slog.e(TAG, "failed to find package " + packageName); 25534 return false; 25535 } 25536 overlayPaths.add(pkg.baseCodePath); 25537 } 25538 } 25539 25540 final PackageSetting ps = mSettings.mPackages.get(targetPackageName); 25541 ps.setOverlayPaths(overlayPaths, userId); 25542 return true; 25543 } 25544 } 25545 25546 @Override 25547 public ResolveInfo resolveIntent(Intent intent, String resolvedType, 25548 int flags, int userId) { 25549 return resolveIntentInternal( 25550 intent, resolvedType, flags, userId, true /*resolveForStart*/); 25551 } 25552 25553 @Override 25554 public ResolveInfo resolveService(Intent intent, String resolvedType, 25555 int flags, int userId, int callingUid) { 25556 return resolveServiceInternal(intent, resolvedType, flags, userId, callingUid); 25557 } 25558 25559 @Override 25560 public void addIsolatedUid(int isolatedUid, int ownerUid) { 25561 synchronized (mPackages) { 25562 mIsolatedOwners.put(isolatedUid, ownerUid); 25563 } 25564 } 25565 25566 @Override 25567 public void removeIsolatedUid(int isolatedUid) { 25568 synchronized (mPackages) { 25569 mIsolatedOwners.delete(isolatedUid); 25570 } 25571 } 25572 25573 @Override 25574 public int getUidTargetSdkVersion(int uid) { 25575 synchronized (mPackages) { 25576 return getUidTargetSdkVersionLockedLPr(uid); 25577 } 25578 } 25579 25580 @Override 25581 public boolean canAccessInstantApps(int callingUid, int userId) { 25582 return PackageManagerService.this.canViewInstantApps(callingUid, userId); 25583 } 25584 25585 @Override 25586 public boolean hasInstantApplicationMetadata(String packageName, int userId) { 25587 synchronized (mPackages) { 25588 return mInstantAppRegistry.hasInstantApplicationMetadataLPr(packageName, userId); 25589 } 25590 } 25591 25592 @Override 25593 public void notifyPackageUse(String packageName, int reason) { 25594 synchronized (mPackages) { 25595 PackageManagerService.this.notifyPackageUseLocked(packageName, reason); 25596 } 25597 } 25598 } 25599 25600 @Override 25601 public void grantDefaultPermissionsToEnabledCarrierApps(String[] packageNames, int userId) { 25602 enforceSystemOrPhoneCaller("grantPermissionsToEnabledCarrierApps"); 25603 synchronized (mPackages) { 25604 final long identity = Binder.clearCallingIdentity(); 25605 try { 25606 mDefaultPermissionPolicy.grantDefaultPermissionsToEnabledCarrierAppsLPr( 25607 packageNames, userId); 25608 } finally { 25609 Binder.restoreCallingIdentity(identity); 25610 } 25611 } 25612 } 25613 25614 @Override 25615 public void grantDefaultPermissionsToEnabledImsServices(String[] packageNames, int userId) { 25616 enforceSystemOrPhoneCaller("grantDefaultPermissionsToEnabledImsServices"); 25617 synchronized (mPackages) { 25618 final long identity = Binder.clearCallingIdentity(); 25619 try { 25620 mDefaultPermissionPolicy.grantDefaultPermissionsToEnabledImsServicesLPr( 25621 packageNames, userId); 25622 } finally { 25623 Binder.restoreCallingIdentity(identity); 25624 } 25625 } 25626 } 25627 25628 private static void enforceSystemOrPhoneCaller(String tag) { 25629 int callingUid = Binder.getCallingUid(); 25630 if (callingUid != Process.PHONE_UID && callingUid != Process.SYSTEM_UID) { 25631 throw new SecurityException( 25632 "Cannot call " + tag + " from UID " + callingUid); 25633 } 25634 } 25635 25636 boolean isHistoricalPackageUsageAvailable() { 25637 return mPackageUsage.isHistoricalPackageUsageAvailable(); 25638 } 25639 25640 /** 25641 * Return a <b>copy</b> of the collection of packages known to the package manager. 25642 * @return A copy of the values of mPackages. 25643 */ 25644 Collection<PackageParser.Package> getPackages() { 25645 synchronized (mPackages) { 25646 return new ArrayList<>(mPackages.values()); 25647 } 25648 } 25649 25650 /** 25651 * Logs process start information (including base APK hash) to the security log. 25652 * @hide 25653 */ 25654 @Override 25655 public void logAppProcessStartIfNeeded(String processName, int uid, String seinfo, 25656 String apkFile, int pid) { 25657 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 25658 return; 25659 } 25660 if (!SecurityLog.isLoggingEnabled()) { 25661 return; 25662 } 25663 Bundle data = new Bundle(); 25664 data.putLong("startTimestamp", System.currentTimeMillis()); 25665 data.putString("processName", processName); 25666 data.putInt("uid", uid); 25667 data.putString("seinfo", seinfo); 25668 data.putString("apkFile", apkFile); 25669 data.putInt("pid", pid); 25670 Message msg = mProcessLoggingHandler.obtainMessage( 25671 ProcessLoggingHandler.LOG_APP_PROCESS_START_MSG); 25672 msg.setData(data); 25673 mProcessLoggingHandler.sendMessage(msg); 25674 } 25675 25676 public CompilerStats.PackageStats getCompilerPackageStats(String pkgName) { 25677 return mCompilerStats.getPackageStats(pkgName); 25678 } 25679 25680 public CompilerStats.PackageStats getOrCreateCompilerPackageStats(PackageParser.Package pkg) { 25681 return getOrCreateCompilerPackageStats(pkg.packageName); 25682 } 25683 25684 public CompilerStats.PackageStats getOrCreateCompilerPackageStats(String pkgName) { 25685 return mCompilerStats.getOrCreatePackageStats(pkgName); 25686 } 25687 25688 public void deleteCompilerPackageStats(String pkgName) { 25689 mCompilerStats.deletePackageStats(pkgName); 25690 } 25691 25692 @Override 25693 public int getInstallReason(String packageName, int userId) { 25694 final int callingUid = Binder.getCallingUid(); 25695 enforceCrossUserPermission(callingUid, userId, 25696 true /* requireFullPermission */, false /* checkShell */, 25697 "get install reason"); 25698 synchronized (mPackages) { 25699 final PackageSetting ps = mSettings.mPackages.get(packageName); 25700 if (filterAppAccessLPr(ps, callingUid, userId)) { 25701 return PackageManager.INSTALL_REASON_UNKNOWN; 25702 } 25703 if (ps != null) { 25704 return ps.getInstallReason(userId); 25705 } 25706 } 25707 return PackageManager.INSTALL_REASON_UNKNOWN; 25708 } 25709 25710 @Override 25711 public boolean canRequestPackageInstalls(String packageName, int userId) { 25712 return canRequestPackageInstallsInternal(packageName, 0, userId, 25713 true /* throwIfPermNotDeclared*/); 25714 } 25715 25716 private boolean canRequestPackageInstallsInternal(String packageName, int flags, int userId, 25717 boolean throwIfPermNotDeclared) { 25718 int callingUid = Binder.getCallingUid(); 25719 int uid = getPackageUid(packageName, 0, userId); 25720 if (callingUid != uid && callingUid != Process.ROOT_UID 25721 && callingUid != Process.SYSTEM_UID) { 25722 throw new SecurityException( 25723 "Caller uid " + callingUid + " does not own package " + packageName); 25724 } 25725 ApplicationInfo info = getApplicationInfo(packageName, flags, userId); 25726 if (info == null) { 25727 return false; 25728 } 25729 if (info.targetSdkVersion < Build.VERSION_CODES.O) { 25730 return false; 25731 } 25732 String appOpPermission = Manifest.permission.REQUEST_INSTALL_PACKAGES; 25733 String[] packagesDeclaringPermission = getAppOpPermissionPackages(appOpPermission); 25734 if (!ArrayUtils.contains(packagesDeclaringPermission, packageName)) { 25735 if (throwIfPermNotDeclared) { 25736 throw new SecurityException("Need to declare " + appOpPermission 25737 + " to call this api"); 25738 } else { 25739 Slog.e(TAG, "Need to declare " + appOpPermission + " to call this api"); 25740 return false; 25741 } 25742 } 25743 if (sUserManager.hasUserRestriction(UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES, userId)) { 25744 return false; 25745 } 25746 if (mExternalSourcesPolicy != null) { 25747 int isTrusted = mExternalSourcesPolicy.getPackageTrustedToInstallApps(packageName, uid); 25748 if (isTrusted != PackageManagerInternal.ExternalSourcesPolicy.USER_DEFAULT) { 25749 return isTrusted == PackageManagerInternal.ExternalSourcesPolicy.USER_TRUSTED; 25750 } 25751 } 25752 return checkUidPermission(appOpPermission, uid) == PERMISSION_GRANTED; 25753 } 25754 25755 @Override 25756 public ComponentName getInstantAppResolverSettingsComponent() { 25757 return mInstantAppResolverSettingsComponent; 25758 } 25759 25760 @Override 25761 public ComponentName getInstantAppInstallerComponent() { 25762 if (getInstantAppPackageName(Binder.getCallingUid()) != null) { 25763 return null; 25764 } 25765 return mInstantAppInstallerActivity == null 25766 ? null : mInstantAppInstallerActivity.getComponentName(); 25767 } 25768 25769 @Override 25770 public String getInstantAppAndroidId(String packageName, int userId) { 25771 mContext.enforceCallingOrSelfPermission(android.Manifest.permission.ACCESS_INSTANT_APPS, 25772 "getInstantAppAndroidId"); 25773 enforceCrossUserPermission(Binder.getCallingUid(), userId, 25774 true /* requireFullPermission */, false /* checkShell */, 25775 "getInstantAppAndroidId"); 25776 // Make sure the target is an Instant App. 25777 if (!isInstantApp(packageName, userId)) { 25778 return null; 25779 } 25780 synchronized (mPackages) { 25781 return mInstantAppRegistry.getInstantAppAndroidIdLPw(packageName, userId); 25782 } 25783 } 25784 25785 boolean canHaveOatDir(String packageName) { 25786 synchronized (mPackages) { 25787 PackageParser.Package p = mPackages.get(packageName); 25788 if (p == null) { 25789 return false; 25790 } 25791 return p.canHaveOatDir(); 25792 } 25793 } 25794 25795 private String getOatDir(PackageParser.Package pkg) { 25796 if (!pkg.canHaveOatDir()) { 25797 return null; 25798 } 25799 File codePath = new File(pkg.codePath); 25800 if (codePath.isDirectory()) { 25801 return PackageDexOptimizer.getOatDir(codePath).getAbsolutePath(); 25802 } 25803 return null; 25804 } 25805 25806 void deleteOatArtifactsOfPackage(String packageName) { 25807 final String[] instructionSets; 25808 final List<String> codePaths; 25809 final String oatDir; 25810 final PackageParser.Package pkg; 25811 synchronized (mPackages) { 25812 pkg = mPackages.get(packageName); 25813 } 25814 instructionSets = getAppDexInstructionSets(pkg.applicationInfo); 25815 codePaths = pkg.getAllCodePaths(); 25816 oatDir = getOatDir(pkg); 25817 25818 for (String codePath : codePaths) { 25819 for (String isa : instructionSets) { 25820 try { 25821 mInstaller.deleteOdex(codePath, isa, oatDir); 25822 } catch (InstallerException e) { 25823 Log.e(TAG, "Failed deleting oat files for " + codePath, e); 25824 } 25825 } 25826 } 25827 } 25828 25829 Set<String> getUnusedPackages(long downgradeTimeThresholdMillis) { 25830 Set<String> unusedPackages = new HashSet<>(); 25831 long currentTimeInMillis = System.currentTimeMillis(); 25832 synchronized (mPackages) { 25833 for (PackageParser.Package pkg : mPackages.values()) { 25834 PackageSetting ps = mSettings.mPackages.get(pkg.packageName); 25835 if (ps == null) { 25836 continue; 25837 } 25838 PackageDexUsage.PackageUseInfo packageUseInfo = 25839 getDexManager().getPackageUseInfoOrDefault(pkg.packageName); 25840 if (PackageManagerServiceUtils 25841 .isUnusedSinceTimeInMillis(ps.firstInstallTime, currentTimeInMillis, 25842 downgradeTimeThresholdMillis, packageUseInfo, 25843 pkg.getLatestPackageUseTimeInMills(), 25844 pkg.getLatestForegroundPackageUseTimeInMills())) { 25845 unusedPackages.add(pkg.packageName); 25846 } 25847 } 25848 } 25849 return unusedPackages; 25850 } 25851} 25852 25853interface PackageSender { 25854 void sendPackageBroadcast(final String action, final String pkg, 25855 final Bundle extras, final int flags, final String targetPkg, 25856 final IIntentReceiver finishedReceiver, final int[] userIds); 25857 void sendPackageAddedForNewUsers(String packageName, boolean sendBootCompleted, 25858 boolean includeStopped, int appId, int... userIds); 25859} 25860