diff options
author | 2024-10-17 17:13:49 +0000 | |
---|---|---|
committer | 2024-10-17 17:13:49 +0000 | |
commit | e2360277f4bfd07cb8eaf72421cba854b7acd752 (patch) | |
tree | b9affd2a340b03cbbfc420b524ab95574b499d17 | |
parent | 947a9aeb7bd8bf28fedca4ce4bcc9c709f36309a (diff) | |
parent | 6303779886bed25e5f4f7b5a086e6b398d2208e3 (diff) |
Merge "Decrease the app zygote preload timeout." into main
-rw-r--r-- | core/java/android/os/ZygoteProcess.java | 52 | ||||
-rw-r--r-- | services/core/java/com/android/server/am/ActivityManagerShellCommand.java | 14 |
2 files changed, 52 insertions, 14 deletions
diff --git a/core/java/android/os/ZygoteProcess.java b/core/java/android/os/ZygoteProcess.java index b1ef05a6f00c..6c99bd1272a4 100644 --- a/core/java/android/os/ZygoteProcess.java +++ b/core/java/android/os/ZygoteProcess.java @@ -73,6 +73,9 @@ public class ZygoteProcess { private static final int ZYGOTE_CONNECT_TIMEOUT_MS = 60000; + // How long we wait for an AppZygote to complete pre-loading; this is a pretty conservative + // value that we can probably decrease over time, but we want to be careful here. + public static volatile int sAppZygotePreloadTimeoutMs = 15000; /** * Use a relatively short delay, because for app zygote, this is in the critical path of * service launch. @@ -1100,6 +1103,17 @@ public class ZygoteProcess { } /** + * Updates the timeout used when preloading code in the app-zygote + * + * @param timeoutMs timeout in milliseconds + */ + public static void setAppZygotePreloadTimeout(int timeoutMs) { + Slog.i(LOG_TAG, "Changing app-zygote preload timeout to " + timeoutMs + " ms."); + + sAppZygotePreloadTimeoutMs = timeoutMs; + } + + /** * Instructs the zygote to pre-load the application code for the given Application. * Only the app zygote supports this function. * TODO preloadPackageForAbi() can probably be removed and the callers an use this instead. @@ -1107,25 +1121,35 @@ public class ZygoteProcess { public boolean preloadApp(ApplicationInfo appInfo, String abi) throws ZygoteStartFailedEx, IOException { synchronized (mLock) { + int ret; ZygoteState state = openZygoteSocketIfNeeded(abi); - state.mZygoteOutputWriter.write("2"); - state.mZygoteOutputWriter.newLine(); + int previousSocketTimeout = state.mZygoteSessionSocket.getSoTimeout(); - state.mZygoteOutputWriter.write("--preload-app"); - state.mZygoteOutputWriter.newLine(); + try { + state.mZygoteSessionSocket.setSoTimeout(sAppZygotePreloadTimeoutMs); - // Zygote args needs to be strings, so in order to pass ApplicationInfo, - // write it to a Parcel, and base64 the raw Parcel bytes to the other side. - Parcel parcel = Parcel.obtain(); - appInfo.writeToParcel(parcel, 0 /* flags */); - String encodedParcelData = Base64.getEncoder().encodeToString(parcel.marshall()); - parcel.recycle(); - state.mZygoteOutputWriter.write(encodedParcelData); - state.mZygoteOutputWriter.newLine(); + state.mZygoteOutputWriter.write("2"); + state.mZygoteOutputWriter.newLine(); - state.mZygoteOutputWriter.flush(); + state.mZygoteOutputWriter.write("--preload-app"); + state.mZygoteOutputWriter.newLine(); - return (state.mZygoteInputStream.readInt() == 0); + // Zygote args needs to be strings, so in order to pass ApplicationInfo, + // write it to a Parcel, and base64 the raw Parcel bytes to the other side. + Parcel parcel = Parcel.obtain(); + appInfo.writeToParcel(parcel, 0 /* flags */); + String encodedParcelData = Base64.getEncoder().encodeToString(parcel.marshall()); + parcel.recycle(); + state.mZygoteOutputWriter.write(encodedParcelData); + state.mZygoteOutputWriter.newLine(); + + state.mZygoteOutputWriter.flush(); + + ret = state.mZygoteInputStream.readInt(); + } finally { + state.mZygoteSessionSocket.setSoTimeout(previousSocketTimeout); + } + return ret == 0; } } diff --git a/services/core/java/com/android/server/am/ActivityManagerShellCommand.java b/services/core/java/com/android/server/am/ActivityManagerShellCommand.java index bbd432340e8f..3a3f041c4189 100644 --- a/services/core/java/com/android/server/am/ActivityManagerShellCommand.java +++ b/services/core/java/com/android/server/am/ActivityManagerShellCommand.java @@ -110,6 +110,7 @@ import android.os.SystemClock; import android.os.Trace; import android.os.UserHandle; import android.os.UserManager; +import android.os.ZygoteProcess; import android.text.TextUtils; import android.util.ArrayMap; import android.util.ArraySet; @@ -439,6 +440,8 @@ final class ActivityManagerShellCommand extends ShellCommand { return runSetForegroundServiceDelegate(pw); case "capabilities": return runCapabilities(pw); + case "set-app-zygote-preload-timeout": + return runSetAppZygotePreloadTimeout(pw); default: return handleDefaultCommands(cmd); } @@ -448,6 +451,15 @@ final class ActivityManagerShellCommand extends ShellCommand { return -1; } + int runSetAppZygotePreloadTimeout(PrintWriter pw) throws RemoteException { + final String timeout = getNextArgRequired(); + final int timeoutMs = Integer.parseInt(timeout); + + ZygoteProcess.setAppZygotePreloadTimeout(timeoutMs); + + return 0; + } + int runCapabilities(PrintWriter pw) throws RemoteException { final PrintWriter err = getErrPrintWriter(); boolean outputAsProtobuf = false; @@ -4603,6 +4615,8 @@ final class ActivityManagerShellCommand extends ShellCommand { pw.println(" capabilities [--protobuf]"); pw.println(" Output am supported features (text format). Options are:"); pw.println(" --protobuf: format output using protobuffer"); + pw.println(" set-app-zygote-preload-timeout <TIMEOUT_IN_MS>"); + pw.println(" Set the timeout for preloading code in the app-zygote"); Intent.printIntentArgsHelp(pw, ""); } } |