summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author Makoto Onuki <omakoto@google.com> 2021-11-17 17:52:56 +0000
committer Android (Google) Code Review <android-gerrit@google.com> 2021-11-17 17:52:56 +0000
commit5dcf36ad8d4569b51f0641cee092bf8e35795db8 (patch)
treeaeeda914c68b0f7d6d557ef285aea2cd113d082e
parent7b5857e2e372861a10751fa5b4d42e5dece5fc5d (diff)
parentb20c14d2af6caabbc16b286c5cebca4829eb8efd (diff)
Merge "Use different exceptions for different crash reasons" into sc-v2-dev
-rw-r--r--core/java/android/app/ActivityThread.java28
-rw-r--r--core/java/android/app/ForegroundServiceDidNotStartInTimeException.java33
-rw-r--r--core/java/android/app/IActivityManager.aidl2
-rw-r--r--core/java/android/app/RemoteServiceException.java103
-rw-r--r--services/core/java/com/android/server/am/ActiveServices.java8
-rw-r--r--services/core/java/com/android/server/am/ActivityManagerService.java8
-rw-r--r--services/core/java/com/android/server/am/ActivityManagerShellCommand.java4
-rw-r--r--services/core/java/com/android/server/am/BroadcastQueue.java12
-rw-r--r--services/core/java/com/android/server/am/ProcessRecord.java6
-rw-r--r--services/core/java/com/android/server/am/ServiceRecord.java4
-rwxr-xr-xservices/core/java/com/android/server/notification/NotificationManagerService.java6
11 files changed, 145 insertions, 69 deletions
diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java
index 431755e092e3..17bb797bf8c5 100644
--- a/core/java/android/app/ActivityThread.java
+++ b/core/java/android/app/ActivityThread.java
@@ -39,6 +39,12 @@ import static com.android.internal.annotations.VisibleForTesting.Visibility.PACK
import android.annotation.NonNull;
import android.annotation.Nullable;
+import android.app.RemoteServiceException.BadForegroundServiceNotificationException;
+import android.app.RemoteServiceException.CannotDeliverBroadcastException;
+import android.app.RemoteServiceException.CannotPostForegroundServiceNotificationException;
+import android.app.RemoteServiceException.CrashedByAdbException;
+import android.app.RemoteServiceException.ForegroundServiceDidNotStartInTimeException;
+import android.app.RemoteServiceException.MissingRequestPasswordComplexityPermissionException;
import android.app.assist.AssistContent;
import android.app.assist.AssistStructure;
import android.app.backup.BackupAgent;
@@ -1921,11 +1927,27 @@ public final class ActivityThread extends ClientTransactionHandler
private void throwRemoteServiceException(String message, int typeId) {
// Use a switch to ensure all the type IDs are unique.
switch (typeId) {
- case ForegroundServiceDidNotStartInTimeException.TYPE_ID: // 1
+ case ForegroundServiceDidNotStartInTimeException.TYPE_ID:
throw new ForegroundServiceDidNotStartInTimeException(message);
- case RemoteServiceException.TYPE_ID: // 0
+
+ case CannotDeliverBroadcastException.TYPE_ID:
+ throw new CannotDeliverBroadcastException(message);
+
+ case CannotPostForegroundServiceNotificationException.TYPE_ID:
+ throw new CannotPostForegroundServiceNotificationException(message);
+
+ case BadForegroundServiceNotificationException.TYPE_ID:
+ throw new BadForegroundServiceNotificationException(message);
+
+ case MissingRequestPasswordComplexityPermissionException.TYPE_ID:
+ throw new MissingRequestPasswordComplexityPermissionException(message);
+
+ case CrashedByAdbException.TYPE_ID:
+ throw new CrashedByAdbException(message);
+
default:
- throw new RemoteServiceException(message);
+ throw new RemoteServiceException(message
+ + " (with unwknown typeId:" + typeId + ")");
}
}
diff --git a/core/java/android/app/ForegroundServiceDidNotStartInTimeException.java b/core/java/android/app/ForegroundServiceDidNotStartInTimeException.java
deleted file mode 100644
index 364291e69ad6..000000000000
--- a/core/java/android/app/ForegroundServiceDidNotStartInTimeException.java
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * Copyright (C) 2021 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.app;
-
-/**
- * Exception used to crash an app process when it didn't call {@link Service#startForeground}
- * in time after the service was started with
- * {@link android.content.Context#startForegroundService}.
- *
- * @hide
- */
-public class ForegroundServiceDidNotStartInTimeException extends RemoteServiceException {
- /** The type ID passed to {@link IApplicationThread#scheduleCrash}. */
- public static final int TYPE_ID = 1;
-
- public ForegroundServiceDidNotStartInTimeException(String msg) {
- super(msg);
- }
-}
diff --git a/core/java/android/app/IActivityManager.aidl b/core/java/android/app/IActivityManager.aidl
index 0210a94eafcc..9e9e28b8bd4c 100644
--- a/core/java/android/app/IActivityManager.aidl
+++ b/core/java/android/app/IActivityManager.aidl
@@ -319,8 +319,6 @@ interface IActivityManager {
void handleApplicationStrictModeViolation(in IBinder app, int penaltyMask,
in StrictMode.ViolationInfo crashInfo);
boolean isTopActivityImmersive();
- void crashApplication(int uid, int initialPid, in String packageName, int userId,
- in String message, boolean force);
void crashApplicationWithType(int uid, int initialPid, in String packageName, int userId,
in String message, boolean force, int exceptionTypeId);
/** @deprecated -- use getProviderMimeTypeAsync */
diff --git a/core/java/android/app/RemoteServiceException.java b/core/java/android/app/RemoteServiceException.java
index 4b32463e2996..1038530d92d3 100644
--- a/core/java/android/app/RemoteServiceException.java
+++ b/core/java/android/app/RemoteServiceException.java
@@ -19,20 +19,109 @@ package android.app;
import android.util.AndroidRuntimeException;
/**
- * Exception used by {@link ActivityThread} to crash an app process.
+ * Exception used by {@link ActivityThread} to crash an app process for an unknown cause.
+ * An exception of this class is no longer supposed to be thrown. Instead, we use fine-grained
+ * sub-exceptions.
+ *
+ * Subclasses must be registered in
+ * {@link android.app.ActivityThread#throwRemoteServiceException(java.lang.String, int)}.
*
* @hide
*/
public class RemoteServiceException extends AndroidRuntimeException {
+ public RemoteServiceException(String msg) {
+ super(msg);
+ }
+
/**
- * The type ID passed to {@link IApplicationThread#scheduleCrash}.
+ * Exception used to crash an app process when it didn't call {@link Service#startForeground}
+ * in time after the service was started with
+ * {@link android.content.Context#startForegroundService}.
*
- * Assign a unique ID to each subclass. See the above method for the numbers that are already
- * taken.
+ * @hide
*/
- public static final int TYPE_ID = 0;
+ public static class ForegroundServiceDidNotStartInTimeException extends RemoteServiceException {
+ /** The type ID passed to {@link IApplicationThread#scheduleCrash}. */
+ public static final int TYPE_ID = 1;
- public RemoteServiceException(String msg) {
- super(msg);
+ public ForegroundServiceDidNotStartInTimeException(String msg) {
+ super(msg);
+ }
+ }
+
+ /**
+ * Exception used to crash an app process when the system received a RemoteException
+ * while delivering a broadcast to an app process.
+ *
+ * @hide
+ */
+ public static class CannotDeliverBroadcastException extends RemoteServiceException {
+ /** The type ID passed to {@link IApplicationThread#scheduleCrash}. */
+ public static final int TYPE_ID = 2;
+
+ public CannotDeliverBroadcastException(String msg) {
+ super(msg);
+ }
+ }
+
+ /**
+ * Exception used to crash an app process when the system received a RemoteException
+ * while posting a notification of a foreground service.
+ *
+ * @hide
+ */
+ public static class CannotPostForegroundServiceNotificationException
+ extends RemoteServiceException {
+ /** The type ID passed to {@link IApplicationThread#scheduleCrash}. */
+ public static final int TYPE_ID = 3;
+
+ public CannotPostForegroundServiceNotificationException(String msg) {
+ super(msg);
+ }
+ }
+
+ /**
+ * Exception used to crash an app process when the system finds an error in a foreground service
+ * notification.
+ *
+ * @hide
+ */
+ public static class BadForegroundServiceNotificationException extends RemoteServiceException {
+ /** The type ID passed to {@link IApplicationThread#scheduleCrash}. */
+ public static final int TYPE_ID = 4;
+
+ public BadForegroundServiceNotificationException(String msg) {
+ super(msg);
+ }
+ }
+
+ /**
+ * Exception used to crash an app process when it calls a setting activity that requires
+ * the {@code REQUEST_PASSWORD_COMPLEXITY} permission.
+ *
+ * @hide
+ */
+ public static class MissingRequestPasswordComplexityPermissionException
+ extends RemoteServiceException {
+ /** The type ID passed to {@link IApplicationThread#scheduleCrash}. */
+ public static final int TYPE_ID = 5;
+
+ public MissingRequestPasswordComplexityPermissionException(String msg) {
+ super(msg);
+ }
+ }
+
+ /**
+ * Exception used to crash an app process by {@code adb shell am crash}.
+ *
+ * @hide
+ */
+ public static class CrashedByAdbException extends RemoteServiceException {
+ /** The type ID passed to {@link IApplicationThread#scheduleCrash}. */
+ public static final int TYPE_ID = 6;
+
+ public CrashedByAdbException(String msg) {
+ super(msg);
+ }
}
}
diff --git a/services/core/java/com/android/server/am/ActiveServices.java b/services/core/java/com/android/server/am/ActiveServices.java
index a2fec2753340..df2ae987f8cb 100644
--- a/services/core/java/com/android/server/am/ActiveServices.java
+++ b/services/core/java/com/android/server/am/ActiveServices.java
@@ -87,13 +87,13 @@ import android.app.ActivityManagerInternal.ServiceNotificationPolicy;
import android.app.ActivityThread;
import android.app.AppGlobals;
import android.app.AppOpsManager;
-import android.app.ForegroundServiceDidNotStartInTimeException;
import android.app.ForegroundServiceStartNotAllowedException;
import android.app.IApplicationThread;
import android.app.IServiceConnection;
import android.app.Notification;
import android.app.NotificationManager;
import android.app.PendingIntent;
+import android.app.RemoteServiceException.ForegroundServiceDidNotStartInTimeException;
import android.app.Service;
import android.app.ServiceStartArgs;
import android.app.admin.DevicePolicyEventLogger;
@@ -1243,7 +1243,7 @@ public final class ActiveServices {
}
void killMisbehavingService(ServiceRecord r,
- int appUid, int appPid, String localPackageName) {
+ int appUid, int appPid, String localPackageName, int exceptionTypeId) {
synchronized (mAm) {
if (!r.destroying) {
// This service is still alive, stop it.
@@ -1257,8 +1257,8 @@ public final class ActiveServices {
stopServiceLocked(found, false);
}
}
- mAm.crashApplication(appUid, appPid, localPackageName, -1,
- "Bad notification for startForeground", true /*force*/);
+ mAm.crashApplicationWithType(appUid, appPid, localPackageName, -1,
+ "Bad notification for startForeground", true /*force*/, exceptionTypeId);
}
}
diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java
index b5f3389c50e0..5cd66aabbf2e 100644
--- a/services/core/java/com/android/server/am/ActivityManagerService.java
+++ b/services/core/java/com/android/server/am/ActivityManagerService.java
@@ -183,7 +183,6 @@ import android.app.PendingIntent;
import android.app.ProcessMemoryState;
import android.app.ProfilerInfo;
import android.app.PropertyInvalidatedCache;
-import android.app.RemoteServiceException;
import android.app.SyncNotedAppOp;
import android.app.WaitResult;
import android.app.backup.BackupManager.OperationType;
@@ -3000,13 +2999,6 @@ public class ActivityManagerService extends IActivityManager.Stub
}
@Override
- public void crashApplication(int uid, int initialPid, String packageName, int userId,
- String message, boolean force) {
- crashApplicationWithType(uid, initialPid, packageName, userId, message, force,
- RemoteServiceException.TYPE_ID);
- }
-
- @Override
public void crashApplicationWithType(int uid, int initialPid, String packageName, int userId,
String message, boolean force, int exceptionTypeId) {
if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES)
diff --git a/services/core/java/com/android/server/am/ActivityManagerShellCommand.java b/services/core/java/com/android/server/am/ActivityManagerShellCommand.java
index 31e48fb0837f..ea28117a6a3d 100644
--- a/services/core/java/com/android/server/am/ActivityManagerShellCommand.java
+++ b/services/core/java/com/android/server/am/ActivityManagerShellCommand.java
@@ -46,6 +46,7 @@ import android.app.IStopUserCallback;
import android.app.IUidObserver;
import android.app.KeyguardManager;
import android.app.ProfilerInfo;
+import android.app.RemoteServiceException.CrashedByAdbException;
import android.app.UserSwitchObserver;
import android.app.WaitResult;
import android.app.usage.AppStandbyInfo;
@@ -1154,7 +1155,8 @@ final class ActivityManagerShellCommand extends ShellCommand {
} catch (NumberFormatException e) {
packageName = arg;
}
- mInterface.crashApplication(-1, pid, packageName, userId, "shell-induced crash", false);
+ mInterface.crashApplicationWithType(-1, pid, packageName, userId, "shell-induced crash",
+ false, CrashedByAdbException.TYPE_ID);
return 0;
}
diff --git a/services/core/java/com/android/server/am/BroadcastQueue.java b/services/core/java/com/android/server/am/BroadcastQueue.java
index 94bf62f8b9b7..487101b7eac4 100644
--- a/services/core/java/com/android/server/am/BroadcastQueue.java
+++ b/services/core/java/com/android/server/am/BroadcastQueue.java
@@ -20,7 +20,13 @@ import static android.os.Process.ZYGOTE_POLICY_FLAG_EMPTY;
import static android.os.Process.ZYGOTE_POLICY_FLAG_LATENCY_SENSITIVE;
import static android.text.TextUtils.formatSimple;
-import static com.android.server.am.ActivityManagerDebugConfig.*;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST_DEFERRAL;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST_LIGHT;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_MU;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PERMISSIONS_REVIEW;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_BROADCAST;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_MU;
import android.annotation.Nullable;
import android.app.ActivityManager;
@@ -29,6 +35,7 @@ import android.app.AppOpsManager;
import android.app.BroadcastOptions;
import android.app.IApplicationThread;
import android.app.PendingIntent;
+import android.app.RemoteServiceException.CannotDeliverBroadcastException;
import android.app.usage.UsageEvents.Event;
import android.content.ComponentName;
import android.content.ContentResolver;
@@ -603,7 +610,8 @@ public final class BroadcastQueue {
synchronized (mService) {
Slog.w(TAG, "Can't deliver broadcast to " + app.processName
+ " (pid " + app.getPid() + "). Crashing it.");
- app.scheduleCrashLocked("can't deliver broadcast");
+ app.scheduleCrashLocked("can't deliver broadcast",
+ CannotDeliverBroadcastException.TYPE_ID);
}
throw ex;
}
diff --git a/services/core/java/com/android/server/am/ProcessRecord.java b/services/core/java/com/android/server/am/ProcessRecord.java
index 9e94d4aa2c0f..14ba7167f529 100644
--- a/services/core/java/com/android/server/am/ProcessRecord.java
+++ b/services/core/java/com/android/server/am/ProcessRecord.java
@@ -26,7 +26,6 @@ import android.app.ApplicationExitInfo;
import android.app.ApplicationExitInfo.Reason;
import android.app.ApplicationExitInfo.SubReason;
import android.app.IApplicationThread;
-import android.app.RemoteServiceException;
import android.content.pm.ApplicationInfo;
import android.content.pm.ProcessInfo;
import android.content.pm.VersionedPackage;
@@ -948,11 +947,6 @@ class ProcessRecord implements WindowProcessListener {
return mServices.hasForegroundServices();
}
- @GuardedBy("mService")
- void scheduleCrashLocked(String message) {
- scheduleCrashLocked(message, RemoteServiceException.TYPE_ID);
- }
-
/**
* Let an app process throw an exception on a binder thread, which typically crashes the
* process, unless it has an unhandled exception handler.
diff --git a/services/core/java/com/android/server/am/ServiceRecord.java b/services/core/java/com/android/server/am/ServiceRecord.java
index 17930ea9c93c..e36898fee387 100644
--- a/services/core/java/com/android/server/am/ServiceRecord.java
+++ b/services/core/java/com/android/server/am/ServiceRecord.java
@@ -28,6 +28,7 @@ import android.annotation.Nullable;
import android.app.IApplicationThread;
import android.app.Notification;
import android.app.PendingIntent;
+import android.app.RemoteServiceException.CannotPostForegroundServiceNotificationException;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
@@ -1039,7 +1040,8 @@ final class ServiceRecord extends Binder implements ComponentName.WithComponentN
// If it gave us a garbage notification, it doesn't
// get to be foreground.
ams.mServices.killMisbehavingService(record,
- appUid, appPid, localPackageName);
+ appUid, appPid, localPackageName,
+ CannotPostForegroundServiceNotificationException.TYPE_ID);
}
}
});
diff --git a/services/core/java/com/android/server/notification/NotificationManagerService.java b/services/core/java/com/android/server/notification/NotificationManagerService.java
index 47d8022a5acc..e597972a540b 100755
--- a/services/core/java/com/android/server/notification/NotificationManagerService.java
+++ b/services/core/java/com/android/server/notification/NotificationManagerService.java
@@ -149,6 +149,7 @@ import android.app.NotificationHistory.HistoricalNotification;
import android.app.NotificationManager;
import android.app.NotificationManager.Policy;
import android.app.PendingIntent;
+import android.app.RemoteServiceException.BadForegroundServiceNotificationException;
import android.app.StatsManager;
import android.app.StatusBarManager;
import android.app.UriGrantsManager;
@@ -1256,10 +1257,11 @@ public class NotificationManagerService extends SystemService {
// Still crash for foreground services, preventing the not-crash behaviour abused
// by apps to give us a garbage notification and silently start a fg service.
Binder.withCleanCallingIdentity(
- () -> mAm.crashApplication(uid, initialPid, pkg, -1,
+ () -> mAm.crashApplicationWithType(uid, initialPid, pkg, -1,
"Bad notification(tag=" + tag + ", id=" + id + ") posted from package "
+ pkg + ", crashing app(uid=" + uid + ", pid=" + initialPid + "): "
- + message, true /* force */));
+ + message, true /* force */,
+ BadForegroundServiceNotificationException.TYPE_ID));
}
}