summaryrefslogtreecommitdiff
path: root/android/content
diff options
context:
space:
mode:
Diffstat (limited to 'android/content')
-rw-r--r--android/content/ContentResolver.java84
-rw-r--r--android/content/Context.java2
-rw-r--r--android/content/Intent.java42
-rw-r--r--android/content/QuickViewConstants.java4
-rw-r--r--android/content/pm/ApplicationInfo.java102
-rw-r--r--android/content/pm/LauncherApps.java24
-rw-r--r--android/content/pm/PackageInfo.java55
-rw-r--r--android/content/pm/PackageManager.java89
-rw-r--r--android/content/pm/PackageManagerInternal.java38
-rw-r--r--android/content/pm/PackageParser.java24
-rw-r--r--android/content/pm/PackageSharedLibraryUpdater.java2
-rw-r--r--android/content/pm/PackageUserState.java6
-rw-r--r--android/content/pm/SigningInfo.java139
13 files changed, 426 insertions, 185 deletions
diff --git a/android/content/ContentResolver.java b/android/content/ContentResolver.java
index 9f3df377..f7908b69 100644
--- a/android/content/ContentResolver.java
+++ b/android/content/ContentResolver.java
@@ -51,7 +51,6 @@ import android.text.TextUtils;
import android.util.EventLog;
import android.util.Log;
-import com.android.internal.util.ArrayUtils;
import com.android.internal.util.MimeIconUtils;
import com.android.internal.util.Preconditions;
@@ -602,6 +601,8 @@ public abstract class ContentResolver {
try {
return provider.getType(url);
} catch (RemoteException e) {
+ // Arbitrary and not worth documenting, as Activity
+ // Manager will kill this process shortly anyway.
return null;
} catch (java.lang.Exception e) {
Log.w(TAG, "Failed to get type for: " + url + " (" + e.getMessage() + ")");
@@ -620,9 +621,7 @@ public abstract class ContentResolver {
ContentProvider.getUriWithoutUserId(url), resolveUserId(url));
return type;
} catch (RemoteException e) {
- // Arbitrary and not worth documenting, as Activity
- // Manager will kill this process shortly anyway.
- return null;
+ throw e.rethrowFromSystemServer();
} catch (java.lang.Exception e) {
Log.w(TAG, "Failed to get type for: " + url + " (" + e.getMessage() + ")");
return null;
@@ -1964,6 +1963,7 @@ public abstract class ContentResolver {
getContentService().registerContentObserver(uri, notifyForDescendents,
observer.getContentObserver(), userHandle, mTargetSdkVersion);
} catch (RemoteException e) {
+ throw e.rethrowFromSystemServer();
}
}
@@ -1982,6 +1982,7 @@ public abstract class ContentResolver {
contentObserver);
}
} catch (RemoteException e) {
+ throw e.rethrowFromSystemServer();
}
}
@@ -2089,6 +2090,7 @@ public abstract class ContentResolver {
syncToNetwork ? NOTIFY_SYNC_TO_NETWORK : 0,
userHandle, mTargetSdkVersion);
} catch (RemoteException e) {
+ throw e.rethrowFromSystemServer();
}
}
@@ -2105,6 +2107,7 @@ public abstract class ContentResolver {
observer != null && observer.deliverSelfNotifications(), flags,
userHandle, mTargetSdkVersion);
} catch (RemoteException e) {
+ throw e.rethrowFromSystemServer();
}
}
@@ -2126,6 +2129,7 @@ public abstract class ContentResolver {
ContentProvider.getUriWithoutUserId(uri), modeFlags, /* toPackage= */ null,
resolveUserId(uri));
} catch (RemoteException e) {
+ throw e.rethrowFromSystemServer();
}
}
@@ -2141,6 +2145,7 @@ public abstract class ContentResolver {
ContentProvider.getUriWithoutUserId(uri), modeFlags, toPackage,
resolveUserId(uri));
} catch (RemoteException e) {
+ throw e.rethrowFromSystemServer();
}
}
@@ -2160,6 +2165,7 @@ public abstract class ContentResolver {
ContentProvider.getUriWithoutUserId(uri), modeFlags, /* toPackage= */ null,
resolveUserId(uri));
} catch (RemoteException e) {
+ throw e.rethrowFromSystemServer();
}
}
@@ -2178,7 +2184,7 @@ public abstract class ContentResolver {
return ActivityManager.getService()
.getPersistedUriPermissions(mPackageName, true).getList();
} catch (RemoteException e) {
- throw new RuntimeException("Activity manager has died", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2194,7 +2200,7 @@ public abstract class ContentResolver {
return ActivityManager.getService()
.getPersistedUriPermissions(mPackageName, false).getList();
} catch (RemoteException e) {
- throw new RuntimeException("Activity manager has died", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2273,7 +2279,7 @@ public abstract class ContentResolver {
try {
getContentService().syncAsUser(request, userId);
} catch(RemoteException e) {
- // Shouldn't happen.
+ throw e.rethrowFromSystemServer();
}
}
@@ -2285,7 +2291,7 @@ public abstract class ContentResolver {
try {
getContentService().sync(request);
} catch(RemoteException e) {
- // Shouldn't happen.
+ throw e.rethrowFromSystemServer();
}
}
@@ -2349,6 +2355,7 @@ public abstract class ContentResolver {
try {
getContentService().cancelSync(account, authority, null);
} catch (RemoteException e) {
+ throw e.rethrowFromSystemServer();
}
}
@@ -2360,6 +2367,7 @@ public abstract class ContentResolver {
try {
getContentService().cancelSyncAsUser(account, authority, null, userId);
} catch (RemoteException e) {
+ throw e.rethrowFromSystemServer();
}
}
@@ -2371,7 +2379,7 @@ public abstract class ContentResolver {
try {
return getContentService().getSyncAdapterTypes();
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2383,7 +2391,7 @@ public abstract class ContentResolver {
try {
return getContentService().getSyncAdapterTypesAsUser(userId);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2397,8 +2405,8 @@ public abstract class ContentResolver {
try {
return getContentService().getSyncAdapterPackagesForAuthorityAsUser(authority, userId);
} catch (RemoteException e) {
+ throw e.rethrowFromSystemServer();
}
- return ArrayUtils.emptyArray(String.class);
}
/**
@@ -2414,7 +2422,7 @@ public abstract class ContentResolver {
try {
return getContentService().getSyncAutomatically(account, authority);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2427,7 +2435,7 @@ public abstract class ContentResolver {
try {
return getContentService().getSyncAutomaticallyAsUser(account, authority, userId);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2453,8 +2461,7 @@ public abstract class ContentResolver {
try {
getContentService().setSyncAutomaticallyAsUser(account, authority, sync, userId);
} catch (RemoteException e) {
- // exception ignored; if this is thrown then it means the runtime is in the midst of
- // being restarted
+ throw e.rethrowFromSystemServer();
}
}
@@ -2500,8 +2507,7 @@ public abstract class ContentResolver {
try {
getContentService().addPeriodicSync(account, authority, extras, pollFrequency);
} catch (RemoteException e) {
- // exception ignored; if this is thrown then it means the runtime is in the midst of
- // being restarted
+ throw e.rethrowFromSystemServer();
}
}
@@ -2540,7 +2546,7 @@ public abstract class ContentResolver {
try {
getContentService().removePeriodicSync(account, authority, extras);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2564,8 +2570,7 @@ public abstract class ContentResolver {
try {
getContentService().cancelRequest(request);
} catch (RemoteException e) {
- // exception ignored; if this is thrown then it means the runtime is in the midst of
- // being restarted
+ throw e.rethrowFromSystemServer();
}
}
@@ -2582,7 +2587,7 @@ public abstract class ContentResolver {
try {
return getContentService().getPeriodicSyncs(account, authority, null);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2596,7 +2601,7 @@ public abstract class ContentResolver {
try {
return getContentService().getIsSyncable(account, authority);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2609,7 +2614,7 @@ public abstract class ContentResolver {
try {
return getContentService().getIsSyncableAsUser(account, authority, userId);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2623,8 +2628,7 @@ public abstract class ContentResolver {
try {
getContentService().setIsSyncable(account, authority, syncable);
} catch (RemoteException e) {
- // exception ignored; if this is thrown then it means the runtime is in the midst of
- // being restarted
+ throw e.rethrowFromSystemServer();
}
}
@@ -2640,7 +2644,7 @@ public abstract class ContentResolver {
try {
return getContentService().getMasterSyncAutomatically();
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2652,7 +2656,7 @@ public abstract class ContentResolver {
try {
return getContentService().getMasterSyncAutomaticallyAsUser(userId);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2676,8 +2680,7 @@ public abstract class ContentResolver {
try {
getContentService().setMasterSyncAutomaticallyAsUser(sync, userId);
} catch (RemoteException e) {
- // exception ignored; if this is thrown then it means the runtime is in the midst of
- // being restarted
+ throw e.rethrowFromSystemServer();
}
}
@@ -2701,7 +2704,7 @@ public abstract class ContentResolver {
try {
return getContentService().isSyncActive(account, authority, null);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2727,7 +2730,7 @@ public abstract class ContentResolver {
}
return syncs.get(0);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2744,7 +2747,7 @@ public abstract class ContentResolver {
try {
return getContentService().getCurrentSyncs();
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2756,7 +2759,7 @@ public abstract class ContentResolver {
try {
return getContentService().getCurrentSyncsAsUser(userId);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2771,7 +2774,7 @@ public abstract class ContentResolver {
try {
return getContentService().getSyncStatus(account, authority, null);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2784,7 +2787,7 @@ public abstract class ContentResolver {
try {
return getContentService().getSyncStatusAsUser(account, authority, null, userId);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2809,7 +2812,7 @@ public abstract class ContentResolver {
try {
return getContentService().isSyncPendingAsUser(account, authority, null, userId);
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2841,7 +2844,7 @@ public abstract class ContentResolver {
getContentService().addStatusChangeListener(mask, observer);
return observer;
} catch (RemoteException e) {
- throw new RuntimeException("the ContentService should always be reachable", e);
+ throw e.rethrowFromSystemServer();
}
}
@@ -2856,8 +2859,7 @@ public abstract class ContentResolver {
try {
getContentService().removeStatusChangeListener((ISyncStatusObserver.Stub) handle);
} catch (RemoteException e) {
- // exception ignored; if this is thrown then it means the runtime is in the midst of
- // being restarted
+ throw e.rethrowFromSystemServer();
}
}
@@ -3027,9 +3029,7 @@ public abstract class ContentResolver {
return sContentService;
}
IBinder b = ServiceManager.getService(CONTENT_SERVICE_NAME);
- if (false) Log.v("ContentService", "default service binder = " + b);
sContentService = IContentService.Stub.asInterface(b);
- if (false) Log.v("ContentService", "default service = " + sContentService);
return sContentService;
}
@@ -3038,7 +3038,7 @@ public abstract class ContentResolver {
return mPackageName;
}
- private static IContentService sContentService;
+ private static volatile IContentService sContentService;
private final Context mContext;
final String mPackageName;
diff --git a/android/content/Context.java b/android/content/Context.java
index 920056a8..ede7ee4b 100644
--- a/android/content/Context.java
+++ b/android/content/Context.java
@@ -3780,7 +3780,7 @@ public abstract class Context {
public static final String DROPBOX_SERVICE = "dropbox";
/**
- * System service name for the DeviceIdleController. There is no Java API for this.
+ * System service name for the DeviceIdleManager.
* @see #getSystemService(String)
* @hide
*/
diff --git a/android/content/Intent.java b/android/content/Intent.java
index 000912cd..f608fcb1 100644
--- a/android/content/Intent.java
+++ b/android/content/Intent.java
@@ -40,6 +40,7 @@ import android.os.Bundle;
import android.os.IBinder;
import android.os.Parcel;
import android.os.Parcelable;
+import android.os.PersistableBundle;
import android.os.Process;
import android.os.ResultReceiver;
import android.os.ShellCommand;
@@ -1814,8 +1815,12 @@ public class Intent implements Parcelable, Cloneable {
public static final String EXTRA_PACKAGE_NAME = "android.intent.extra.PACKAGE_NAME";
/**
- * Intent extra: A {@link Bundle} of extras for a package being suspended. Will be sent with
- * {@link #ACTION_MY_PACKAGE_SUSPENDED}.
+ * Intent extra: A {@link Bundle} of extras for a package being suspended. Will be sent as an
+ * extra with {@link #ACTION_MY_PACKAGE_SUSPENDED}.
+ *
+ * <p>The contents of this {@link Bundle} are a contract between the suspended app and the
+ * suspending app, i.e. any app with the permission {@code android.permission.SUSPEND_APPS}.
+ * This is meant to enable the suspended app to better handle the state of being suspended.
*
* @see #ACTION_MY_PACKAGE_SUSPENDED
* @see #ACTION_MY_PACKAGE_UNSUSPENDED
@@ -2282,6 +2287,34 @@ public class Intent implements Parcelable, Cloneable {
public static final String ACTION_MY_PACKAGE_SUSPENDED = "android.intent.action.MY_PACKAGE_SUSPENDED";
/**
+ * Activity Action: Started to show more details about why an application was suspended.
+ *
+ * <p>Whenever the system detects an activity launch for a suspended app, it shows a dialog to
+ * the user to inform them of the state and present them an affordance to start this activity
+ * action to show more details about the reason for suspension.
+ *
+ * <p>Apps holding {@link android.Manifest.permission#SUSPEND_APPS} must declare an activity
+ * handling this intent and protect it with
+ * {@link android.Manifest.permission#SEND_SHOW_SUSPENDED_APP_DETAILS}.
+ *
+ * <p>Includes an extra {@link #EXTRA_PACKAGE_NAME} which is the name of the suspended package.
+ *
+ * <p class="note">This is a protected intent that can only be sent
+ * by the system.
+ *
+ * @see PackageManager#setPackagesSuspended(String[], boolean, PersistableBundle,
+ * PersistableBundle, String)
+ * @see PackageManager#isPackageSuspended()
+ * @see #ACTION_PACKAGES_SUSPENDED
+ *
+ * @hide
+ */
+ @SystemApi
+ @SdkConstant(SdkConstantType.ACTIVITY_INTENT_ACTION)
+ public static final String ACTION_SHOW_SUSPENDED_APP_DETAILS =
+ "android.intent.action.SHOW_SUSPENDED_APP_DETAILS";
+
+ /**
* Broadcast Action: Sent to a package that has been unsuspended.
*
* <p class="note">This is a protected intent that can only be sent
@@ -6788,6 +6821,9 @@ public class Intent implements Parcelable, Cloneable {
case "--activity-task-on-home":
intent.addFlags(Intent.FLAG_ACTIVITY_TASK_ON_HOME);
break;
+ case "--activity-match-external":
+ intent.addFlags(Intent.FLAG_ACTIVITY_MATCH_EXTERNAL);
+ break;
case "--receiver-registered-only":
intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
break;
@@ -6924,7 +6960,7 @@ public class Intent implements Parcelable, Cloneable {
" [--activity-no-user-action] [--activity-previous-is-top]",
" [--activity-reorder-to-front] [--activity-reset-task-if-needed]",
" [--activity-single-top] [--activity-clear-task]",
- " [--activity-task-on-home]",
+ " [--activity-task-on-home] [--activity-match-external]",
" [--receiver-registered-only] [--receiver-replace-pending]",
" [--receiver-foreground] [--receiver-no-abort]",
" [--receiver-include-background]",
diff --git a/android/content/QuickViewConstants.java b/android/content/QuickViewConstants.java
index a25513de..132d43f2 100644
--- a/android/content/QuickViewConstants.java
+++ b/android/content/QuickViewConstants.java
@@ -45,8 +45,8 @@ public class QuickViewConstants {
* Feature to delete an individual document. Quick viewer implementations must use
* Storage Access Framework to both verify delete permission and to delete content.
*
- * @see DocumentsContract#Document#FLAG_SUPPORTS_DELETE
- * @see DocumentsContract#deleteDocument(ContentResolver resolver, Uri documentUri)
+ * @see DocumentsContract.Document#FLAG_SUPPORTS_DELETE
+ * @see DocumentsContract#deleteDocument(ContentResolver, Uri)
*/
public static final String FEATURE_DELETE = "android:delete";
diff --git a/android/content/pm/ApplicationInfo.java b/android/content/pm/ApplicationInfo.java
index e85058df..d65e051b 100644
--- a/android/content/pm/ApplicationInfo.java
+++ b/android/content/pm/ApplicationInfo.java
@@ -26,6 +26,7 @@ import android.content.Context;
import android.content.pm.PackageManager.NameNotFoundException;
import android.content.res.Resources;
import android.graphics.drawable.Drawable;
+import android.os.Build;
import android.os.Environment;
import android.os.Parcel;
import android.os.Parcelable;
@@ -590,26 +591,33 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
public static final int PRIVATE_FLAG_VIRTUAL_PRELOAD = 1 << 16;
/**
- * Value for {@linl #privateFlags}: whether this app is pre-installed on the
+ * Value for {@link #privateFlags}: whether this app is pre-installed on the
* OEM partition of the system image.
* @hide
*/
public static final int PRIVATE_FLAG_OEM = 1 << 17;
/**
- * Value for {@linl #privateFlags}: whether this app is pre-installed on the
+ * Value for {@link #privateFlags}: whether this app is pre-installed on the
* vendor partition of the system image.
* @hide
*/
public static final int PRIVATE_FLAG_VENDOR = 1 << 18;
/**
- * Value for {@linl #privateFlags}: whether this app is pre-installed on the
+ * Value for {@link #privateFlags}: whether this app is pre-installed on the
* product partition of the system image.
* @hide
*/
public static final int PRIVATE_FLAG_PRODUCT = 1 << 19;
+ /**
+ * Value for {@link #privateFlags}: whether this app is signed with the
+ * platform key.
+ * @hide
+ */
+ public static final int PRIVATE_FLAG_SIGNED_WITH_PLATFORM_KEY = 1 << 20;
+
/** @hide */
@IntDef(flag = true, prefix = { "PRIVATE_FLAG_" }, value = {
PRIVATE_FLAG_ACTIVITIES_RESIZE_MODE_RESIZEABLE,
@@ -629,6 +637,7 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
PRIVATE_FLAG_PRIVILEGED,
PRIVATE_FLAG_PRODUCT,
PRIVATE_FLAG_REQUIRED_FOR_SYSTEM_USER,
+ PRIVATE_FLAG_SIGNED_WITH_PLATFORM_KEY,
PRIVATE_FLAG_STATIC_SHARED_LIBRARY,
PRIVATE_FLAG_VENDOR,
PRIVATE_FLAG_VIRTUAL_PRELOAD,
@@ -904,7 +913,17 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
* The app's declared version code.
* @hide
*/
- public long versionCode;
+ public long longVersionCode;
+
+ /**
+ * An integer representation of the app's declared version code. This is being left in place as
+ * some apps were using reflection to access it before the move to long in
+ * {@link android.os.Build.VERSION_CODES#P}
+ * @deprecated Use {@link #longVersionCode} instead.
+ * @hide
+ */
+ @Deprecated
+ public int versionCode;
/**
* The user-visible SDK version (ex. 26) of the framework against which the application claims
@@ -1114,11 +1133,12 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
*/
public static final int HIDDEN_API_ENFORCEMENT_NONE = 0;
/**
- * Light grey list enforcement, the strictest option. Enforces the light grey, dark grey and
- * black lists.
+ * No API enforcement, but enable the detection logic and warnings. Observed behaviour is the
+ * same as {@link #HIDDEN_API_ENFORCEMENT_NONE} but you may see warnings in the log when APIs
+ * are accessed.
* @hide
* */
- public static final int HIDDEN_API_ENFORCEMENT_ALL_LISTS = 1;
+ public static final int HIDDEN_API_ENFORCEMENT_JUST_WARN = 1;
/**
* Dark grey list enforcement. Enforces the dark grey and black lists
* @hide
@@ -1140,14 +1160,15 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
@IntDef(prefix = { "HIDDEN_API_ENFORCEMENT_" }, value = {
HIDDEN_API_ENFORCEMENT_DEFAULT,
HIDDEN_API_ENFORCEMENT_NONE,
- HIDDEN_API_ENFORCEMENT_ALL_LISTS,
+ HIDDEN_API_ENFORCEMENT_JUST_WARN,
HIDDEN_API_ENFORCEMENT_DARK_GREY_AND_BLACK,
HIDDEN_API_ENFORCEMENT_BLACK,
})
@Retention(RetentionPolicy.SOURCE)
public @interface HiddenApiEnforcementPolicy {}
- private boolean isValidHiddenApiEnforcementPolicy(int policy) {
+ /** @hide */
+ public static boolean isValidHiddenApiEnforcementPolicy(int policy) {
return policy >= HIDDEN_API_ENFORCEMENT_DEFAULT && policy <= HIDDEN_API_ENFORCEMENT_MAX;
}
@@ -1214,7 +1235,7 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
pw.println(prefix + "enabled=" + enabled
+ " minSdkVersion=" + minSdkVersion
+ " targetSdkVersion=" + targetSdkVersion
- + " versionCode=" + versionCode
+ + " versionCode=" + longVersionCode
+ " targetSandboxVersion=" + targetSandboxVersion);
if ((dumpFlags & DUMP_FLAG_DETAILS) != 0) {
if (manageSpaceActivityName != null) {
@@ -1287,7 +1308,7 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
proto.write(ApplicationInfoProto.Version.ENABLED, enabled);
proto.write(ApplicationInfoProto.Version.MIN_SDK_VERSION, minSdkVersion);
proto.write(ApplicationInfoProto.Version.TARGET_SDK_VERSION, targetSdkVersion);
- proto.write(ApplicationInfoProto.Version.VERSION_CODE, versionCode);
+ proto.write(ApplicationInfoProto.Version.VERSION_CODE, longVersionCode);
proto.write(ApplicationInfoProto.Version.TARGET_SANDBOX_VERSION, targetSandboxVersion);
proto.end(versionToken);
@@ -1421,7 +1442,7 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
uid = orig.uid;
minSdkVersion = orig.minSdkVersion;
targetSdkVersion = orig.targetSdkVersion;
- versionCode = orig.versionCode;
+ setVersionCode(orig.longVersionCode);
enabled = orig.enabled;
enabledSetting = orig.enabledSetting;
installLocation = orig.installLocation;
@@ -1495,7 +1516,7 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
dest.writeInt(uid);
dest.writeInt(minSdkVersion);
dest.writeInt(targetSdkVersion);
- dest.writeLong(versionCode);
+ dest.writeLong(longVersionCode);
dest.writeInt(enabled ? 1 : 0);
dest.writeInt(enabledSetting);
dest.writeInt(installLocation);
@@ -1566,7 +1587,7 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
uid = source.readInt();
minSdkVersion = source.readInt();
targetSdkVersion = source.readInt();
- versionCode = source.readLong();
+ setVersionCode(source.readLong());
enabled = source.readInt() != 0;
enabledSetting = source.readInt();
installLocation = source.readInt();
@@ -1658,17 +1679,26 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
return SystemConfig.getInstance().getHiddenApiWhitelistedApps().contains(packageName);
}
+ private boolean isAllowedToUseHiddenApis() {
+ return isSignedWithPlatformKey()
+ || (isPackageWhitelistedForHiddenApis() && (isSystemApp() || isUpdatedSystemApp()));
+ }
+
/**
* @hide
*/
public @HiddenApiEnforcementPolicy int getHiddenApiEnforcementPolicy() {
+ if (isAllowedToUseHiddenApis()) {
+ return HIDDEN_API_ENFORCEMENT_NONE;
+ }
if (mHiddenApiPolicy != HIDDEN_API_ENFORCEMENT_DEFAULT) {
return mHiddenApiPolicy;
}
- if (isPackageWhitelistedForHiddenApis() && (isSystemApp() || isUpdatedSystemApp())) {
- return HIDDEN_API_ENFORCEMENT_NONE;
+ if (targetSdkVersion < Build.VERSION_CODES.P) {
+ return HIDDEN_API_ENFORCEMENT_BLACK;
+ } else {
+ return HIDDEN_API_ENFORCEMENT_DARK_GREY_AND_BLACK;
}
- return HIDDEN_API_ENFORCEMENT_BLACK;
}
/**
@@ -1682,6 +1712,39 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
}
/**
+ * Updates the hidden API enforcement policy for this app from the given values, if appropriate.
+ *
+ * This will have no effect if this app is not subject to hidden API enforcement, i.e. if it
+ * is on the package whitelist.
+ *
+ * @param policyPreP configured policy for pre-P apps, or {@link
+ * #HIDDEN_API_ENFORCEMENT_DEFAULT} if nothing configured.
+ * @param policyP configured policy for apps targeting P or later, or {@link
+ * #HIDDEN_API_ENFORCEMENT_DEFAULT} if nothing configured.
+ * @hide
+ */
+ public void maybeUpdateHiddenApiEnforcementPolicy(
+ @HiddenApiEnforcementPolicy int policyPreP, @HiddenApiEnforcementPolicy int policyP) {
+ if (isPackageWhitelistedForHiddenApis()) {
+ return;
+ }
+ if (targetSdkVersion < Build.VERSION_CODES.P) {
+ setHiddenApiEnforcementPolicy(policyPreP);
+ } else if (targetSdkVersion >= Build.VERSION_CODES.P) {
+ setHiddenApiEnforcementPolicy(policyP);
+ }
+
+ }
+
+ /**
+ * @hide
+ */
+ public void setVersionCode(long newVersionCode) {
+ longVersionCode = newVersionCode;
+ versionCode = (int) newVersionCode;
+ }
+
+ /**
* @hide
*/
@Override
@@ -1758,6 +1821,11 @@ public class ApplicationInfo extends PackageItemInfo implements Parcelable {
}
/** @hide */
+ public boolean isSignedWithPlatformKey() {
+ return (privateFlags & ApplicationInfo.PRIVATE_FLAG_SIGNED_WITH_PLATFORM_KEY) != 0;
+ }
+
+ /** @hide */
@TestApi
public boolean isPrivilegedApp() {
return (privateFlags & ApplicationInfo.PRIVATE_FLAG_PRIVILEGED) != 0;
diff --git a/android/content/pm/LauncherApps.java b/android/content/pm/LauncherApps.java
index 9aace2e7..8223363a 100644
--- a/android/content/pm/LauncherApps.java
+++ b/android/content/pm/LauncherApps.java
@@ -212,7 +212,7 @@ public class LauncherApps {
* an applicaton.
*
* <p>Note: On devices running {@link android.os.Build.VERSION_CODES#P Android P} or higher,
- * any apps that override {@link #onPackagesSuspended(String[], Bundle, UserHandle)} will
+ * any apps that override {@link #onPackagesSuspended(String[], UserHandle, Bundle)} will
* not receive this callback.
*
* @param packageNames The names of the packages that have just been
@@ -226,15 +226,20 @@ public class LauncherApps {
* Indicates that one or more packages have been suspended. A device administrator or an app
* with {@code android.permission.SUSPEND_APPS} can do this.
*
+ * <p>A suspending app with the permission {@code android.permission.SUSPEND_APPS} can
+ * optionally provide a {@link Bundle} of extra information that it deems helpful for the
+ * launcher to handle the suspended state of these packages. The contents of this
+ * {@link Bundle} supposed to be a contract between the suspending app and the launcher.
+ *
* @param packageNames The names of the packages that have just been suspended.
- * @param launcherExtras A {@link Bundle} of extras for the launcher.
* @param user the user for which the given packages were suspended.
- *
+ * @param launcherExtras A {@link Bundle} of extras for the launcher, if provided to the
+ * system, {@code null} otherwise.
* @see PackageManager#isPackageSuspended()
* @see #getSuspendedPackageLauncherExtras(String, UserHandle)
*/
- public void onPackagesSuspended(String[] packageNames, @Nullable Bundle launcherExtras,
- UserHandle user) {
+ public void onPackagesSuspended(String[] packageNames, UserHandle user,
+ @Nullable Bundle launcherExtras) {
onPackagesSuspended(packageNames, user);
}
@@ -662,6 +667,9 @@ public class LauncherApps {
* {@code PackageManager#setPackagesSuspended(String[], boolean, PersistableBundle,
* PersistableBundle, String)}.
*
+ * <p>The contents of this {@link Bundle} are supposed to be a contract between the suspending
+ * app and the launcher.
+ *
* <p>Note: This just returns whatever extras were provided to the system, <em>which might
* even be {@code null}.</em>
*
@@ -670,7 +678,7 @@ public class LauncherApps {
* @return A {@link Bundle} of launcher extras. Or {@code null} if the package is not currently
* suspended.
*
- * @see Callback#onPackagesSuspended(String[], Bundle, UserHandle)
+ * @see Callback#onPackagesSuspended(String[], UserHandle, Bundle)
* @see PackageManager#isPackageSuspended()
*/
public @Nullable Bundle getSuspendedPackageLauncherExtras(String packageName, UserHandle user) {
@@ -1298,8 +1306,8 @@ public class LauncherApps {
mCallback.onPackagesUnavailable(info.packageNames, info.user, info.replacing);
break;
case MSG_SUSPENDED:
- mCallback.onPackagesSuspended(info.packageNames, info.launcherExtras,
- info.user);
+ mCallback.onPackagesSuspended(info.packageNames, info.user, info.launcherExtras
+ );
break;
case MSG_UNSUSPENDED:
mCallback.onPackagesUnsuspended(info.packageNames, info.user);
diff --git a/android/content/pm/PackageInfo.java b/android/content/pm/PackageInfo.java
index 627ceb78..5f9f8f1f 100644
--- a/android/content/pm/PackageInfo.java
+++ b/android/content/pm/PackageInfo.java
@@ -244,7 +244,7 @@ public class PackageInfo implements Parcelable {
* the first position to be the same across updates.
*
* <strong>Deprecated</strong> This has been replaced by the
- * {@link PackageInfo#signingCertificateHistory} field, which takes into
+ * {@link PackageInfo#signingInfo} field, which takes into
* account signing certificate rotation. For backwards compatibility in
* the event of signing certificate rotation, this will return the oldest
* reported signing certificate, so that an application will appear to
@@ -256,29 +256,15 @@ public class PackageInfo implements Parcelable {
public Signature[] signatures;
/**
- * Array of all signatures arrays read from the package file, potentially
+ * Signing information read from the package file, potentially
* including past signing certificates no longer used after signing
- * certificate rotation. Though signing certificate rotation is only
- * available for apps with a single signing certificate, this provides an
- * array of arrays so that packages signed with multiple signing
- * certificates can still return all signers. This is only filled in if
+ * certificate rotation. This is only filled in if
* the flag {@link PackageManager#GET_SIGNING_CERTIFICATES} was set.
*
- * A package must be singed with at least one certificate, which is at
- * position zero in the array. An application may be signed by multiple
- * certificates, which would be in the array at position zero in an
- * indeterminate order. A package may also have a history of certificates
- * due to signing certificate rotation. In this case, the array will be
- * populated by a series of single-entry arrays corresponding to a signing
- * certificate of the package.
- *
- * <strong>Note:</strong> Signature ordering is not guaranteed to be
- * stable which means that a package signed with certificates A and B is
- * equivalent to being signed with certificates B and A. This means that
- * in case multiple signatures are reported you cannot assume the one at
- * the first position will be the same across updates.
+ * Use this field instead of the deprecated {@code signatures} field.
+ * See {@link SigningInfo} for more information on its contents.
*/
- public Signature[][] signingCertificateHistory;
+ public SigningInfo signingInfo;
/**
* Application specified preferred configuration
@@ -476,17 +462,11 @@ public class PackageInfo implements Parcelable {
dest.writeBoolean(mOverlayIsStatic);
dest.writeInt(compileSdkVersion);
dest.writeString(compileSdkVersionCodename);
- writeSigningCertificateHistoryToParcel(dest, parcelableFlags);
- }
-
- private void writeSigningCertificateHistoryToParcel(Parcel dest, int parcelableFlags) {
- if (signingCertificateHistory != null) {
- dest.writeInt(signingCertificateHistory.length);
- for (int i = 0; i < signingCertificateHistory.length; i++) {
- dest.writeTypedArray(signingCertificateHistory[i], parcelableFlags);
- }
+ if (signingInfo != null) {
+ dest.writeInt(1);
+ signingInfo.writeToParcel(dest, parcelableFlags);
} else {
- dest.writeInt(-1);
+ dest.writeInt(0);
}
}
@@ -544,7 +524,10 @@ public class PackageInfo implements Parcelable {
mOverlayIsStatic = source.readBoolean();
compileSdkVersion = source.readInt();
compileSdkVersionCodename = source.readString();
- readSigningCertificateHistoryFromParcel(source);
+ int hasSigningInfo = source.readInt();
+ if (hasSigningInfo != 0) {
+ signingInfo = SigningInfo.CREATOR.createFromParcel(source);
+ }
// The component lists were flattened with the redundant ApplicationInfo
// instances omitted. Distribute the canonical one here as appropriate.
@@ -556,16 +539,6 @@ public class PackageInfo implements Parcelable {
}
}
- private void readSigningCertificateHistoryFromParcel(Parcel source) {
- int len = source.readInt();
- if (len != -1) {
- signingCertificateHistory = new Signature[len][];
- for (int i = 0; i < len; i++) {
- signingCertificateHistory[i] = source.createTypedArray(Signature.CREATOR);
- }
- }
- }
-
private void propagateApplicationInfo(ApplicationInfo appInfo, ComponentInfo[] components) {
if (components != null) {
for (ComponentInfo ci : components) {
diff --git a/android/content/pm/PackageManager.java b/android/content/pm/PackageManager.java
index 491f0af2..9d3b53f2 100644
--- a/android/content/pm/PackageManager.java
+++ b/android/content/pm/PackageManager.java
@@ -2629,6 +2629,17 @@ public abstract class PackageManager {
"android.hardware.strongbox_keystore";
/**
+ * Feature for {@link #getSystemAvailableFeatures} and {@link #hasSystemFeature}:
+ * The device has a Keymaster implementation that supports Device ID attestation.
+ *
+ * @see DevicePolicyManager#isDeviceIdAttestationSupported
+ * @hide
+ */
+ @SdkConstant(SdkConstantType.FEATURE)
+ public static final String FEATURE_DEVICE_ID_ATTESTATION =
+ "android.software.device_id_attestation";
+
+ /**
* Action to external storage service to clean out removed apps.
* @hide
*/
@@ -3941,6 +3952,7 @@ public abstract class PackageManager {
*
* @hide
*/
+ @TestApi
public abstract @NonNull String getServicesSystemSharedLibraryPackageName();
/**
@@ -3950,6 +3962,7 @@ public abstract class PackageManager {
*
* @hide
*/
+ @TestApi
public abstract @NonNull String getSharedSystemSharedLibraryPackageName();
/**
@@ -5558,7 +5571,8 @@ public abstract class PackageManager {
* @param packageName The name of the package to get the suspended status of.
* @param userId The user id.
* @return {@code true} if the package is suspended or {@code false} if the package is not
- * suspended or could not be found.
+ * suspended.
+ * @throws IllegalArgumentException if the package was not found.
* @hide
*/
public abstract boolean isPackageSuspendedForUser(String packageName, int userId);
@@ -5567,12 +5581,13 @@ public abstract class PackageManager {
* Query if an app is currently suspended.
*
* @return {@code true} if the given package is suspended, {@code false} otherwise
+ * @throws NameNotFoundException if the package could not be found.
*
* @see #setPackagesSuspended(String[], boolean, PersistableBundle, PersistableBundle, String)
* @hide
*/
@SystemApi
- public boolean isPackageSuspended(String packageName) {
+ public boolean isPackageSuspended(String packageName) throws NameNotFoundException {
throw new UnsupportedOperationException("isPackageSuspended not implemented");
}
@@ -5603,51 +5618,16 @@ public abstract class PackageManager {
}
/**
- * Retrieve the {@link PersistableBundle} that was passed as {@code appExtras} when the given
- * package was suspended.
- *
- * <p> The caller must hold permission {@link Manifest.permission#SUSPEND_APPS} to use this
- * api.</p>
- *
- * @param packageName The package to retrieve extras for.
- * @return The {@code appExtras} for the suspended package.
- *
- * @see #setPackagesSuspended(String[], boolean, PersistableBundle, PersistableBundle, String)
- * @hide
- */
- @SystemApi
- @RequiresPermission(Manifest.permission.SUSPEND_APPS)
- public @Nullable PersistableBundle getSuspendedPackageAppExtras(String packageName) {
- throw new UnsupportedOperationException("getSuspendedPackageAppExtras not implemented");
- }
-
- /**
- * Set the app extras for a suspended package. This method can be used to update the appExtras
- * for a package that was earlier suspended using
- * {@link #setPackagesSuspended(String[], boolean, PersistableBundle, PersistableBundle,
- * String)}
- * Does nothing if the given package is not already in a suspended state.
+ * Returns a {@link Bundle} of extras that was meant to be sent to the calling app when it was
+ * suspended. An app with the permission {@code android.permission.SUSPEND_APPS} can supply this
+ * to the system at the time of suspending an app.
*
- * @param packageName The package for which the appExtras need to be updated
- * @param appExtras The new appExtras for the given package
+ * <p>This is the same {@link Bundle} that is sent along with the broadcast
+ * {@link Intent#ACTION_MY_PACKAGE_SUSPENDED}, whenever the app is suspended. The contents of
+ * this {@link Bundle} are a contract between the suspended app and the suspending app.
*
- * @see #setPackagesSuspended(String[], boolean, PersistableBundle, PersistableBundle, String)
- *
- * @hide
- */
- @SystemApi
- @RequiresPermission(Manifest.permission.SUSPEND_APPS)
- public void setSuspendedPackageAppExtras(String packageName,
- @Nullable PersistableBundle appExtras) {
- throw new UnsupportedOperationException("setSuspendedPackageAppExtras not implemented");
- }
-
- /**
- * Returns any extra information supplied as {@code appExtras} to the system when the calling
- * app was suspended.
- *
- * <p>Note: If no extras were supplied to the system, this method will return {@code null}, even
- * when the calling app has been suspended.</p>
+ * <p>Note: These extras are optional, so if no extras were supplied to the system, this method
+ * will return {@code null}, even when the calling app has been suspended.
*
* @return A {@link Bundle} containing the extras for the app, or {@code null} if the
* package is not currently suspended.
@@ -5655,6 +5635,7 @@ public abstract class PackageManager {
* @see #isPackageSuspended()
* @see Intent#ACTION_MY_PACKAGE_UNSUSPENDED
* @see Intent#ACTION_MY_PACKAGE_SUSPENDED
+ * @see Intent#EXTRA_SUSPENDED_PACKAGE_EXTRAS
*/
public @Nullable Bundle getSuspendedPackageAppExtras() {
throw new UnsupportedOperationException("getSuspendedPackageAppExtras not implemented");
@@ -6118,7 +6099,9 @@ public abstract class PackageManager {
* signed. This should be used instead of {@code getPackageInfo} with {@code GET_SIGNATURES}
* since it takes into account the possibility of signing certificate rotation, except in the
* case of packages that are signed by multiple certificates, for which signing certificate
- * rotation is not supported.
+ * rotation is not supported. This method is analogous to using {@code getPackageInfo} with
+ * {@code GET_SIGNING_CERTIFICATES} and then searching through the resulting {@code
+ * signingCertificateHistory} field to see if the desired certificate is present.
*
* @param packageName package whose signing certificates to check
* @param certificate signing certificate for which to search
@@ -6132,13 +6115,19 @@ public abstract class PackageManager {
}
/**
- * Searches the set of signing certificates by which the given uid has proven to have been
- * signed. This should be used instead of {@code getPackageInfo} with {@code GET_SIGNATURES}
+ * Searches the set of signing certificates by which the package(s) for the given uid has proven
+ * to have been signed. For multiple packages sharing the same uid, this will return the
+ * signing certificates found in the signing history of the "newest" package, where "newest"
+ * indicates the package with the newest signing certificate in the shared uid group. This
+ * method should be used instead of {@code getPackageInfo} with {@code GET_SIGNATURES}
* since it takes into account the possibility of signing certificate rotation, except in the
* case of packages that are signed by multiple certificates, for which signing certificate
- * rotation is not supported.
+ * rotation is not supported. This method is analogous to using {@code getPackagesForUid}
+ * followed by {@code getPackageInfo} with {@code GET_SIGNING_CERTIFICATES}, selecting the
+ * {@code PackageInfo} of the newest-signed bpackage , and finally searching through the
+ * resulting {@code signingCertificateHistory} field to see if the desired certificate is there.
*
- * @param uid package whose signing certificates to check
+ * @param uid uid whose signing certificates to check
* @param certificate signing certificate for which to search
* @param type representation of the {@code certificate}
* @return true if this package was or is signed by exactly the certificate {@code certificate}
diff --git a/android/content/pm/PackageManagerInternal.java b/android/content/pm/PackageManagerInternal.java
index c9b78c08..a9d09110 100644
--- a/android/content/pm/PackageManagerInternal.java
+++ b/android/content/pm/PackageManagerInternal.java
@@ -191,10 +191,10 @@ public abstract class PackageManagerInternal {
/**
* Retrieve launcher extras for a suspended package provided to the system in
* {@link PackageManager#setPackagesSuspended(String[], boolean, PersistableBundle,
- * PersistableBundle, String)}
+ * PersistableBundle, String)}.
*
* @param packageName The package for which to return launcher extras.
- * @param userId The user for which to check,
+ * @param userId The user for which to check.
* @return The launcher extras.
*
* @see PackageManager#setPackagesSuspended(String[], boolean, PersistableBundle,
@@ -205,6 +205,38 @@ public abstract class PackageManagerInternal {
int userId);
/**
+ * Internal api to query the suspended state of a package.
+ * @param packageName The package to check.
+ * @param userId The user id to check for.
+ * @return {@code true} if the package is suspended, {@code false} otherwise.
+ * @see PackageManager#isPackageSuspended(String)
+ */
+ public abstract boolean isPackageSuspended(String packageName, int userId);
+
+ /**
+ * Get the name of the package that suspended the given package. Packages can be suspended by
+ * device administrators or apps holding {@link android.Manifest.permission#MANAGE_USERS} or
+ * {@link android.Manifest.permission#SUSPEND_APPS}.
+ *
+ * @param suspendedPackage The package that has been suspended.
+ * @param userId The user for which to check.
+ * @return Name of the package that suspended the given package. Returns {@code null} if the
+ * given package is not currently suspended and the platform package name - i.e.
+ * {@code "android"} - if the package was suspended by a device admin.
+ */
+ public abstract String getSuspendingPackage(String suspendedPackage, int userId);
+
+ /**
+ * Get the dialog message to be shown to the user when they try to launch a suspended
+ * application.
+ *
+ * @param suspendedPackage The package that has been suspended.
+ * @param userId The user for which to check.
+ * @return The dialog message to be shown to the user.
+ */
+ public abstract String getSuspendedDialogMessage(String suspendedPackage, int userId);
+
+ /**
* Do a straight uid lookup for the given package/application in the given user.
* @see PackageManager#getPackageUidAsUser(String, int, int)
* @return The app's uid, or < 0 if the package was not found in that user
@@ -429,7 +461,7 @@ public abstract class PackageManagerInternal {
* Resolves an activity intent, allowing instant apps to be resolved.
*/
public abstract ResolveInfo resolveIntent(Intent intent, String resolvedType,
- int flags, int userId, boolean resolveForStart);
+ int flags, int userId, boolean resolveForStart, int filterCallingUid);
/**
* Resolves a service intent, allowing instant apps to be resolved.
diff --git a/android/content/pm/PackageParser.java b/android/content/pm/PackageParser.java
index 2f0faf25..453a74aa 100644
--- a/android/content/pm/PackageParser.java
+++ b/android/content/pm/PackageParser.java
@@ -810,21 +810,11 @@ public class PackageParser {
// replacement for GET_SIGNATURES
if ((flags & PackageManager.GET_SIGNING_CERTIFICATES) != 0) {
- if (p.mSigningDetails.hasPastSigningCertificates()) {
- // Package has included signing certificate rotation information. Convert each
- // entry to an array
- int numberOfSigs = p.mSigningDetails.pastSigningCertificates.length;
- pi.signingCertificateHistory = new Signature[numberOfSigs][];
- for (int i = 0; i < numberOfSigs; i++) {
- pi.signingCertificateHistory[i] =
- new Signature[] { p.mSigningDetails.pastSigningCertificates[i] };
- }
- } else if (p.mSigningDetails.hasSignatures()) {
- // otherwise keep old behavior
- int numberOfSigs = p.mSigningDetails.signatures.length;
- pi.signingCertificateHistory = new Signature[1][numberOfSigs];
- System.arraycopy(p.mSigningDetails.signatures, 0,
- pi.signingCertificateHistory[0], 0, numberOfSigs);
+ if (p.mSigningDetails != SigningDetails.UNKNOWN) {
+ // only return a valid SigningInfo if there is signing information to report
+ pi.signingInfo = new SigningInfo(p.mSigningDetails);
+ } else {
+ pi.signingInfo = null;
}
}
return pi;
@@ -1918,7 +1908,7 @@ public class PackageParser {
com.android.internal.R.styleable.AndroidManifest_versionCode, 0);
pkg.mVersionCodeMajor = sa.getInteger(
com.android.internal.R.styleable.AndroidManifest_versionCodeMajor, 0);
- pkg.applicationInfo.versionCode = pkg.getLongVersionCode();
+ pkg.applicationInfo.setVersionCode(pkg.getLongVersionCode());
pkg.baseRevisionCode = sa.getInteger(
com.android.internal.R.styleable.AndroidManifest_revisionCode, 0);
pkg.mVersionName = sa.getNonConfigurationString(
@@ -2726,7 +2716,7 @@ public class PackageParser {
// Fot apps targeting O-MR1 we require explicit enumeration of all certs.
String[] additionalCertSha256Digests = EmptyArray.STRING;
- if (pkg.applicationInfo.targetSdkVersion > Build.VERSION_CODES.O) {
+ if (pkg.applicationInfo.targetSdkVersion >= Build.VERSION_CODES.O_MR1) {
additionalCertSha256Digests = parseAdditionalCertificates(res, parser, outError);
if (additionalCertSha256Digests == null) {
return false;
diff --git a/android/content/pm/PackageSharedLibraryUpdater.java b/android/content/pm/PackageSharedLibraryUpdater.java
index fa894320..b14b321a 100644
--- a/android/content/pm/PackageSharedLibraryUpdater.java
+++ b/android/content/pm/PackageSharedLibraryUpdater.java
@@ -62,7 +62,7 @@ public abstract class PackageSharedLibraryUpdater {
static boolean apkTargetsApiLevelLessThanOrEqualToOMR1(PackageParser.Package pkg) {
int targetSdkVersion = pkg.applicationInfo.targetSdkVersion;
- return targetSdkVersion <= Build.VERSION_CODES.O_MR1;
+ return targetSdkVersion < Build.VERSION_CODES.P;
}
/**
diff --git a/android/content/pm/PackageUserState.java b/android/content/pm/PackageUserState.java
index f7b6e091..f471a1d9 100644
--- a/android/content/pm/PackageUserState.java
+++ b/android/content/pm/PackageUserState.java
@@ -34,6 +34,7 @@ import android.util.ArraySet;
import com.android.internal.util.ArrayUtils;
import java.util.Arrays;
+import java.util.Objects;
/**
* Per-user state information about a package.
@@ -47,6 +48,7 @@ public class PackageUserState {
public boolean hidden; // Is the app restricted by owner / admin
public boolean suspended;
public String suspendingPackage;
+ public String dialogMessage; // Message to show when a suspended package launch attempt is made
public PersistableBundle suspendedAppExtras;
public PersistableBundle suspendedLauncherExtras;
public boolean instantApp;
@@ -82,6 +84,7 @@ public class PackageUserState {
hidden = o.hidden;
suspended = o.suspended;
suspendingPackage = o.suspendingPackage;
+ dialogMessage = o.dialogMessage;
suspendedAppExtras = o.suspendedAppExtras;
suspendedLauncherExtras = o.suspendedLauncherExtras;
instantApp = o.instantApp;
@@ -208,6 +211,9 @@ public class PackageUserState {
|| !suspendingPackage.equals(oldState.suspendingPackage)) {
return false;
}
+ if (!Objects.equals(dialogMessage, oldState.dialogMessage)) {
+ return false;
+ }
if (!BaseBundle.kindofEquals(suspendedAppExtras,
oldState.suspendedAppExtras)) {
return false;
diff --git a/android/content/pm/SigningInfo.java b/android/content/pm/SigningInfo.java
new file mode 100644
index 00000000..ef874035
--- /dev/null
+++ b/android/content/pm/SigningInfo.java
@@ -0,0 +1,139 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.content.pm;
+
+
+import android.annotation.NonNull;
+import android.os.Parcel;
+import android.os.Parcelable;
+
+/**
+ * Information pertaining to the signing certificates used to sign a package.
+ */
+public final class SigningInfo implements Parcelable {
+
+ @NonNull
+ private final PackageParser.SigningDetails mSigningDetails;
+
+ public SigningInfo() {
+ mSigningDetails = PackageParser.SigningDetails.UNKNOWN;
+ }
+
+ /**
+ * @hide only packagemanager should be populating this
+ */
+ public SigningInfo(PackageParser.SigningDetails signingDetails) {
+ mSigningDetails = new PackageParser.SigningDetails(signingDetails);
+ }
+
+ public SigningInfo(SigningInfo orig) {
+ mSigningDetails = new PackageParser.SigningDetails(orig.mSigningDetails);
+ }
+
+ private SigningInfo(Parcel source) {
+ mSigningDetails = PackageParser.SigningDetails.CREATOR.createFromParcel(source);
+ }
+
+ /**
+ * Although relatively uncommon, packages may be signed by more than one signer, in which case
+ * their identity is viewed as being the set of all signers, not just any one.
+ */
+ public boolean hasMultipleSigners() {
+ return mSigningDetails.signatures != null && mSigningDetails.signatures.length > 1;
+ }
+
+ /**
+ * APK Signature Scheme v3 enables packages to provide a proof-of-rotation record that the
+ * platform verifies, and uses, to allow the use of new signing certificates. This is only
+ * available to packages that are not signed by multiple signers. In the event of a change to a
+ * new signing certificate, the package's past signing certificates are presented as well. Any
+ * check of a package's signing certificate should also include a search through its entire
+ * signing history, since it could change to a new signing certificate at any time.
+ */
+ public boolean hasPastSigningCertificates() {
+ return mSigningDetails.signatures != null
+ && mSigningDetails.pastSigningCertificates != null;
+ }
+
+ /**
+ * Returns the signing certificates this package has proven it is authorized to use. This
+ * includes both the signing certificate associated with the signer of the package and the past
+ * signing certificates it included as its proof of signing certificate rotation. This method
+ * is the preferred replacement for the {@code GET_SIGNATURES} flag used with {@link
+ * PackageManager#getPackageInfo(String, int)}. When determining if a package is signed by a
+ * desired certificate, the returned array should be checked to determine if it is one of the
+ * entries.
+ *
+ * <note>
+ * This method returns null if the package is signed by multiple signing certificates, as
+ * opposed to being signed by one current signer and also providing the history of past
+ * signing certificates. {@link #hasMultipleSigners()} may be used to determine if this
+ * package is signed by multiple signers. Packages which are signed by multiple signers
+ * cannot change their signing certificates and their {@code Signature} array should be
+ * checked to make sure that every entry matches the looked-for signing certificates.
+ * </note>
+ */
+ public Signature[] getSigningCertificateHistory() {
+ if (hasMultipleSigners()) {
+ return null;
+ } else if (!hasPastSigningCertificates()) {
+
+ // this package is only signed by one signer with no history, return it
+ return mSigningDetails.signatures;
+ } else {
+
+ // this package has provided proof of past signing certificates, include them
+ return mSigningDetails.pastSigningCertificates;
+ }
+ }
+
+ /**
+ * Returns the signing certificates used to sign the APK contents of this application. Not
+ * including any past signing certificates the package proved it is authorized to use.
+ * <note>
+ * This method should not be used unless {@link #hasMultipleSigners()} returns true,
+ * indicating that {@link #getSigningCertificateHistory()} cannot be used, otherwise {@link
+ * #getSigningCertificateHistory()} should be preferred.
+ * </note>
+ */
+ public Signature[] getApkContentsSigners() {
+ return mSigningDetails.signatures;
+ }
+
+ @Override
+ public int describeContents() {
+ return 0;
+ }
+
+ @Override
+ public void writeToParcel(Parcel dest, int parcelableFlags) {
+ mSigningDetails.writeToParcel(dest, parcelableFlags);
+ }
+
+ public static final Parcelable.Creator<SigningInfo> CREATOR =
+ new Parcelable.Creator<SigningInfo>() {
+ @Override
+ public SigningInfo createFromParcel(Parcel source) {
+ return new SigningInfo(source);
+ }
+
+ @Override
+ public SigningInfo[] newArray(int size) {
+ return new SigningInfo[size];
+ }
+ };
+}