From 44f1b306663f2b9b04934c05dc35640821419c59 Mon Sep 17 00:00:00 2001 From: Todd Kennedy Date: Tue, 10 Jan 2017 10:10:04 -0800 Subject: [PATCH] Allow starting ephemeral apps from 'am' We previously filtered any ephemeral app if either startActivity or queryIntentActivities was called from a non-ephemeral app. However, the system should have access to all activities [ephemeral or not] Bug: 33458220 Test: cts-tradefed run commandAndExit cts-dev -m CtsAppSecurityHostTestCases -t android.appsecurity.cts.EphemeralTest Change-Id: I381862e3848b2e6f7f7b2612e9cc8977a1e132ab --- .../server/pm/PackageManagerService.java | 21 ++++++++++++++----- 1 file changed, 16 insertions(+), 5 deletions(-) diff --git a/services/core/java/com/android/server/pm/PackageManagerService.java b/services/core/java/com/android/server/pm/PackageManagerService.java index 2dd95038e4580..50c0c28d3ff36 100644 --- a/services/core/java/com/android/server/pm/PackageManagerService.java +++ b/services/core/java/com/android/server/pm/PackageManagerService.java @@ -3663,12 +3663,19 @@ public class PackageManagerService extends IPackageManager.Stub { if (mSafeMode) { flags |= PackageManager.MATCH_SYSTEM_ONLY; } - final String ephemeralPkgName = getEphemeralPackageName(Binder.getCallingUid()); - if (ephemeralPkgName != null) { + final int callingUid = Binder.getCallingUid(); + if (callingUid == Process.SYSTEM_UID || callingUid == 0) { + // The system sees all components + flags |= PackageManager.MATCH_EPHEMERAL; + } else if (getEphemeralPackageName(callingUid) != null) { + // But, ephemeral apps see both ephemeral and exposed, non-ephemeral components flags |= PackageManager.MATCH_VISIBLE_TO_EPHEMERAL_ONLY; flags |= PackageManager.MATCH_EPHEMERAL; + } else { + // Otherwise, prevent leaking ephemeral components + flags &= ~PackageManager.MATCH_VISIBLE_TO_EPHEMERAL_ONLY; + flags &= ~PackageManager.MATCH_EPHEMERAL; } - return updateFlagsForComponent(flags, userId, cookie); } @@ -5550,11 +5557,15 @@ public class PackageManagerService extends IPackageManager.Stub { // used when either 1) the calling package is normal and the activity is within // an ephemeral application or 2) the calling package is ephemeral and the // activity is not visible to ephemeral applications. + boolean matchEphemeral = + (flags & PackageManager.MATCH_EPHEMERAL) != 0; + boolean ephemeralVisibleOnly = + (flags & PackageManager.MATCH_VISIBLE_TO_EPHEMERAL_ONLY) != 0; boolean blockResolution = - (ephemeralPkgName == null + (!matchEphemeral && ephemeralPkgName == null && (ai.applicationInfo.privateFlags & ApplicationInfo.PRIVATE_FLAG_EPHEMERAL) != 0) - || (ephemeralPkgName != null + || (ephemeralVisibleOnly && ephemeralPkgName != null && (ai.flags & ActivityInfo.FLAG_VISIBLE_TO_EPHEMERAL) == 0); if (!blockResolution) { final ResolveInfo ri = new ResolveInfo();