diff options
-rw-r--r-- | core/java/android/os/Process.java | 44 | ||||
-rw-r--r-- | core/jni/android_util_Process.cpp | 40 |
2 files changed, 60 insertions, 24 deletions
diff --git a/core/java/android/os/Process.java b/core/java/android/os/Process.java index 770bf1c..8e041bb 100644 --- a/core/java/android/os/Process.java +++ b/core/java/android/os/Process.java @@ -266,25 +266,38 @@ public class Process { */ public static final int SCHED_IDLE = 5; + // Keep in sync with SP_* constants of enum type SchedPolicy + // declared in system/core/include/cutils/sched_policy.h, + // except THREAD_GROUP_DEFAULT does not correspond to any SP_* value. + /** - * Default thread group - gets a 'normal' share of the CPU + * Default thread group - + * has meaning with setProcessGroup() only, cannot be used with setThreadGroup(). + * When used with setProcessGroup(), the group of each thread in the process + * is conditionally changed based on that thread's current priority, as follows: + * threads with priority numerically less than THREAD_PRIORITY_BACKGROUND + * are moved to foreground thread group. All other threads are left unchanged. * @hide */ - public static final int THREAD_GROUP_DEFAULT = 0; + public static final int THREAD_GROUP_DEFAULT = -1; /** - * Background non-interactive thread group - All threads in + * Background thread group - All threads in * this group are scheduled with a reduced share of the CPU. + * Value is same as constant SP_BACKGROUND of enum SchedPolicy. + * FIXME rename to THREAD_GROUP_BACKGROUND. * @hide */ - public static final int THREAD_GROUP_BG_NONINTERACTIVE = 1; + public static final int THREAD_GROUP_BG_NONINTERACTIVE = 0; /** - * Foreground 'boost' thread group - All threads in - * this group are scheduled with an increased share of the CPU + * Foreground thread group - All threads in + * this group are scheduled with a normal share of the CPU. + * Value is same as constant SP_FOREGROUND of enum SchedPolicy. + * Not used at this level. * @hide **/ - public static final int THREAD_GROUP_FG_BOOST = 2; + private static final int THREAD_GROUP_FOREGROUND = 1; public static final int SIGNAL_QUIT = 3; public static final int SIGNAL_KILL = 9; @@ -672,28 +685,37 @@ public class Process { /** * Sets the scheduling group for a thread. * @hide - * @param tid The indentifier of the thread/process to change. - * @param group The target group for this thread/process. + * @param tid The identifier of the thread to change. + * @param group The target group for this thread from THREAD_GROUP_*. * * @throws IllegalArgumentException Throws IllegalArgumentException if * <var>tid</var> does not exist. * @throws SecurityException Throws SecurityException if your process does * not have permission to modify the given thread, or to use the given * priority. + * If the thread is a thread group leader, that is it's gettid() == getpid(), + * then the other threads in the same thread group are _not_ affected. */ public static final native void setThreadGroup(int tid, int group) throws IllegalArgumentException, SecurityException; + /** * Sets the scheduling group for a process and all child threads * @hide - * @param pid The indentifier of the process to change. - * @param group The target group for this process. + * @param pid The identifier of the process to change. + * @param group The target group for this process from THREAD_GROUP_*. * * @throws IllegalArgumentException Throws IllegalArgumentException if * <var>tid</var> does not exist. * @throws SecurityException Throws SecurityException if your process does * not have permission to modify the given thread, or to use the given * priority. + * + * group == THREAD_GROUP_DEFAULT means to move all non-background priority + * threads to the foreground scheduling group, but to leave background + * priority threads alone. group == THREAD_GROUP_BG_NONINTERACTIVE moves all + * threads, regardless of priority, to the background scheduling group. + * group == THREAD_GROUP_FOREGROUND is not allowed. */ public static final native void setProcessGroup(int pid, int group) throws IllegalArgumentException, SecurityException; diff --git a/core/jni/android_util_Process.cpp b/core/jni/android_util_Process.cpp index 41cc203..93be342 100644 --- a/core/jni/android_util_Process.cpp +++ b/core/jni/android_util_Process.cpp @@ -21,6 +21,7 @@ #include <binder/IPCThreadState.h> #include <binder/ProcessState.h> #include <binder/IServiceManager.h> +#include <cutils/sched_policy.h> #include <utils/String8.h> #include <utils/Vector.h> @@ -49,6 +50,8 @@ Mutex gKeyCreateMutex; static pthread_key_t gBgKey = -1; #endif +// For both of these, err should be in the errno range (positive), not a status_t (negative) + static void signalExceptionForPriorityError(JNIEnv* env, int err) { switch (err) { @@ -168,27 +171,36 @@ jint android_os_Process_getGidForName(JNIEnv* env, jobject clazz, jstring name) return -1; } -void android_os_Process_setThreadGroup(JNIEnv* env, jobject clazz, int pid, jint grp) +void android_os_Process_setThreadGroup(JNIEnv* env, jobject clazz, int tid, jint grp) { - int res = androidSetThreadSchedulingGroup(pid, grp); + ALOGV("%s tid=%d grp=%d", __func__, tid, grp); + SchedPolicy sp = (SchedPolicy) grp; + int res = set_sched_policy(tid, sp); if (res != NO_ERROR) { - signalExceptionForGroupError(env, res == BAD_VALUE ? EINVAL : errno); - return; + signalExceptionForGroupError(env, -res); } } void android_os_Process_setProcessGroup(JNIEnv* env, jobject clazz, int pid, jint grp) { + ALOGV("%s pid=%d grp=%d", __func__, pid, grp); DIR *d; FILE *fp; char proc_path[255]; struct dirent *de; - if (grp > ANDROID_TGROUP_MAX || grp < 0) { + if ((grp == SP_FOREGROUND) || (grp > SP_MAX)) { signalExceptionForGroupError(env, EINVAL); return; } + bool isDefault = false; + if (grp < 0) { + grp = SP_FOREGROUND; + isDefault = true; + } + SchedPolicy sp = (SchedPolicy) grp; + #if POLICY_DEBUG char cmdline[32]; int fd; @@ -203,7 +215,7 @@ void android_os_Process_setProcessGroup(JNIEnv* env, jobject clazz, int pid, jin close(fd); } - if (grp == ANDROID_TGROUP_BG_NONINTERACT) { + if (sp == SP_BACKGROUND) { ALOGD("setProcessGroup: vvv pid %d (%s)", pid, cmdline); } else { ALOGD("setProcessGroup: ^^^ pid %d (%s)", pid, cmdline); @@ -230,16 +242,18 @@ void android_os_Process_setProcessGroup(JNIEnv* env, jobject clazz, int pid, jin continue; } - t_pri = getpriority(PRIO_PROCESS, t_pid); + if (isDefault) { + t_pri = getpriority(PRIO_PROCESS, t_pid); - if (grp == ANDROID_TGROUP_DEFAULT && - t_pri >= ANDROID_PRIORITY_BACKGROUND) { - // This task wants to stay at background - continue; + if (t_pri >= ANDROID_PRIORITY_BACKGROUND) { + // This task wants to stay at background + continue; + } } - if (androidSetThreadSchedulingGroup(t_pid, grp) != NO_ERROR) { - signalExceptionForGroupError(env, errno); + int err = set_sched_policy(t_pid, sp); + if (err != NO_ERROR) { + signalExceptionForGroupError(env, -err); break; } } |