From 04ed6500833373b8a544f161113871e5dc5c867c Mon Sep 17 00:00:00 2001 From: Hiroshi Yamauchi Date: Thu, 2 Mar 2017 13:39:07 -0800 Subject: [PATCH] Fix the reset of boosted zygote thread priority. This fixes the unexpected priority 112 of the daemon threads (eg. HeapTaskDaemon). The problem was that when the zygote main thread's priority is reset, it directly calls setpriority() and fails to update the priority value in java.lang.Thread, which in turn causes any threads created by the thread to unexpectedly inherit the boosted priority. Calling java.lang.Thread.setPriority instead fixes. (cherry picked from commit 1e3db871e52e59c69edb1843df7f4aecb030bc6f) Bug: 35801778 Bug: 28866384 Test: angler master userdebug boots and thread priorities checked. Change-Id: I68a6ed7244a9067acc2749feca7f88422bf44b02 --- core/java/com/android/internal/os/Zygote.java | 12 +++++++++++ core/jni/com_android_internal_os_Zygote.cpp | 20 ------------------- 2 files changed, 12 insertions(+), 20 deletions(-) diff --git a/core/java/com/android/internal/os/Zygote.java b/core/java/com/android/internal/os/Zygote.java index 59416dd06cdc4..e065843a39614 100644 --- a/core/java/com/android/internal/os/Zygote.java +++ b/core/java/com/android/internal/os/Zygote.java @@ -100,6 +100,8 @@ public final class Zygote { int[][] rlimits, int mountExternal, String seInfo, String niceName, int[] fdsToClose, int[] fdsToIgnore, String instructionSet, String appDataDir) { VM_HOOKS.preFork(); + // Resets nice priority for zygote process. + resetNicePriority(); int pid = nativeForkAndSpecialize( uid, gid, gids, debugFlags, rlimits, mountExternal, seInfo, niceName, fdsToClose, fdsToIgnore, instructionSet, appDataDir); @@ -144,6 +146,8 @@ public final class Zygote { public static int forkSystemServer(int uid, int gid, int[] gids, int debugFlags, int[][] rlimits, long permittedCapabilities, long effectiveCapabilities) { VM_HOOKS.preFork(); + // Resets nice priority for zygote process. + resetNicePriority(); int pid = nativeForkSystemServer( uid, gid, gids, debugFlags, rlimits, permittedCapabilities, effectiveCapabilities); // Enable tracing as soon as we enter the system_server. @@ -173,6 +177,14 @@ public final class Zygote { VM_HOOKS.postForkChild(debugFlags, isSystemServer, instructionSet); } + /** + * Resets the calling thread priority to the default value (Thread.NORM_PRIORITY + * or nice value 0). This updates both the priority value in java.lang.Thread and + * the nice value (setpriority). + */ + static void resetNicePriority() { + Thread.currentThread().setPriority(Thread.NORM_PRIORITY); + } /** * Executes "/system/bin/sh -c <command>" using the exec() system call. diff --git a/core/jni/com_android_internal_os_Zygote.cpp b/core/jni/com_android_internal_os_Zygote.cpp index 3498108991fa1..90ad2da6fb184 100644 --- a/core/jni/com_android_internal_os_Zygote.cpp +++ b/core/jni/com_android_internal_os_Zygote.cpp @@ -155,24 +155,6 @@ static void SetSigChldHandler() { } } -// Resets nice priority for zygote process. Zygote priority can be set -// to high value during boot phase to speed it up. We want to ensure -// zygote is running at normal priority before childs are forked from it. -// -// This ends up being called repeatedly before each fork(), but there's -// no real harm in that. -static void ResetNicePriority(JNIEnv* env) { - errno = 0; - int prio = getpriority(PRIO_PROCESS, 0); - if (prio == -1 && errno != 0) { - ALOGW("getpriority failed: %s\n", strerror(errno)); - } - if (prio != 0 && setpriority(PRIO_PROCESS, 0, 0) != 0) { - ALOGE("setpriority(%d, 0, 0) failed: %s", PRIO_PROCESS, strerror(errno)); - RuntimeAbort(env, __LINE__, "setpriority failed"); - } -} - // Sets the SIGCHLD handler back to default behavior in zygote children. static void UnsetSigChldHandler() { struct sigaction sa; @@ -512,8 +494,6 @@ static pid_t ForkAndSpecializeCommon(JNIEnv* env, uid_t uid, gid_t gid, jintArra RuntimeAbort(env, __LINE__, "Unable to restat file descriptor table."); } - ResetNicePriority(env); - pid_t pid = fork(); if (pid == 0) {