diff --git a/lmkd/lmkd.c b/lmkd/lmkd.c index 7794f81fa..ca78c38c3 100644 --- a/lmkd/lmkd.c +++ b/lmkd/lmkd.c @@ -16,6 +16,7 @@ #define LOG_TAG "lowmemorykiller" +#include #include #include #include @@ -28,18 +29,22 @@ #include #include #include +#include #include #include +#include #include #include #include #include +#include #include #include #include #include #include +#include #ifdef LMKD_LOG_STATS #include "statslog.h" @@ -1261,6 +1266,41 @@ static struct proc *proc_get_heaviest(int oomadj) { return maxprocp; } +static void set_process_group_and_prio(int pid, SchedPolicy sp, int prio) { + DIR* d; + char proc_path[PATH_MAX]; + struct dirent* de; + + snprintf(proc_path, sizeof(proc_path), "/proc/%d/task", pid); + if (!(d = opendir(proc_path))) { + ALOGW("Failed to open %s; errno=%d: process pid(%d) might have died", proc_path, errno, + pid); + return; + } + + while ((de = readdir(d))) { + int t_pid; + + if (de->d_name[0] == '.') continue; + t_pid = atoi(de->d_name); + + if (!t_pid) { + ALOGW("Failed to get t_pid for '%s' of pid(%d)", de->d_name, pid); + continue; + } + + if (setpriority(PRIO_PROCESS, t_pid, prio) && errno != ESRCH) { + ALOGW("Unable to raise priority of killing t_pid (%d): errno=%d", t_pid, errno); + } + + if (set_cpuset_policy(t_pid, sp)) { + ALOGW("Failed to set_cpuset_policy on pid(%d) t_pid(%d) to %d", pid, t_pid, (int)sp); + continue; + } + } + closedir(d); +} + static int last_killed_pid = -1; /* Kill one process specified by procp. Returns the size of the process killed */ @@ -1301,6 +1341,9 @@ static int kill_one_process(struct proc* procp) { /* CAP_KILL required */ r = kill(pid, SIGKILL); + + set_process_group_and_prio(pid, SP_FOREGROUND, ANDROID_PRIORITY_HIGHEST); + inc_killcnt(procp->oomadj); ALOGI("Kill '%s' (%d), uid %d, oom_adj %d to free %ldkB", taskname, pid, uid, procp->oomadj, tasksize * page_k);