From 4e204196ebc4038eface8f90ac4e73049f085ebf Mon Sep 17 00:00:00 2001 From: Unsung Lee Date: Fri, 10 Nov 2023 16:46:29 +0900 Subject: lowmem-governor: Remove app with LmkKillException from the LMK victim list Remove app with LmkKillException configuration property (yes|1|ok|on|) from the LMK victim list during LMK. If LmkKillException is not declared in limiter.conf.d, then the process can be included in LMK victim list during LMK (default is no|0|off). Change-Id: I8aa5903850438952a6f2f9e024eba1bb4f7ccd43 Signed-off-by: Unsung Lee --- src/resource-limiter/memory/lowmem.c | 94 ++++++++++++++++++++++++++++++++++++ 1 file changed, 94 insertions(+) diff --git a/src/resource-limiter/memory/lowmem.c b/src/resource-limiter/memory/lowmem.c index 2c7d6114..9d5e62a5 100644 --- a/src/resource-limiter/memory/lowmem.c +++ b/src/resource-limiter/memory/lowmem.c @@ -193,6 +193,9 @@ static GArray *lowmem_kill_candidates = NULL; static GArray *lowmem_task_info_app_array = NULL; static GArray *lowmem_task_info_proc_array = NULL; +static GHashTable *g_lmk_kill_exception_pid_list; +static bool is_lmk_kill_exception_pid(pid_t pid); + //static int memlog_enabled; //static int memlog_nr_max = DEFAULT_MEMLOG_NR_MAX; /* remove logfiles to reduce to this threshold. @@ -593,6 +596,7 @@ static GArray *lowmem_get_task_info_app(int killer_flags, int start_oom, int end { GSList *iter = NULL; GSList *proc_app_list = proc_app_list_open(); + GSList *iterchild; if (!lowmem_task_info_app_array) lowmem_task_info_app_array = g_array_new(false, false, sizeof(struct task_info)); @@ -600,6 +604,7 @@ static GArray *lowmem_get_task_info_app(int killer_flags, int start_oom, int end gslist_for_each_item(iter, proc_app_list) { struct proc_app_info *pai = (struct proc_app_info *)(iter->data); struct task_info task; + bool found = false; if (!pai->appid) continue; @@ -619,6 +624,25 @@ static GArray *lowmem_get_task_info_app(int killer_flags, int start_oom, int end continue; } + if (is_lmk_kill_exception_pid(pai->main_pid)) { + _D("[LMK] Don't kill %s, (pid = %d) is lmk kill exception pid", + pai->appid, pai->main_pid); + continue; + } + + gslist_for_each_item(iterchild, pai->childs) { + pid_t child = GPOINTER_TO_PID(iterchild->data); + if (is_lmk_kill_exception_pid(child)) { + _D("[LMK] Don't kill %s, (pid = %d) is lmk kill exception pid", + pai->appid, child); + found = true; + break; + } + } + + if (found) + continue; + memset(&task, 0, sizeof(struct task_info)); task.pid = pai->main_pid; @@ -684,6 +708,7 @@ static GArray *lowmem_get_task_info_proc() struct task_info task; pid_t pid, pgid; int oom_score_adj = 0; + char *appid; if (!isdigit(dentry->d_name[0])) continue; @@ -713,6 +738,13 @@ static GArray *lowmem_get_task_info_proc() if (oom_score_adj > OOMADJ_SU && oom_score_adj <= OOMADJ_APP_MAX) continue; + appid = (char *)g_hash_table_lookup(g_lmk_kill_exception_pid_list, &pid); + if (appid) { + _D("[LMK] Don't kill %s, (pid = %d) is lmk kill exception pid", + appid, pid); + continue; + } + memset(&task, 0, sizeof(struct task_info)); /** @@ -1634,6 +1666,56 @@ static void print_mem_configs(void) _I("Background reclaim enabled = %d", g_bg_reclaim); } +static bool is_lmk_kill_exception_pid(pid_t pid) +{ + if (g_hash_table_contains(g_lmk_kill_exception_pid_list, &pid)) + return true; + + return false; +} + +static int lowmem_governor_add_exception_pid(void *data) +{ + struct proc_status *ps = (struct proc_status *)data; + struct proc_conf_info *pci; + gint *pid; + + if (!ps) + return RESOURCED_ERROR_INVALID_PARAMETER; + + if (ps->pid < 0) + return RESOURCED_ERROR_INVALID_PARAMETER; + + if (!ps->pai) + return RESOURCED_ERROR_INVALID_PARAMETER; + + pci = fixed_app_and_service_exist_check(ps->pai->appid, APP_TYPE); + if (!pci || !(pci->is_lmk_kill_exception)) + return RESOURCED_ERROR_NONE; + + _D("%s (pid = %d) is registered as LMK kill exception pid", + ps->pai->appid, ps->pid); + pid = g_new(gint, 1); + *pid = ps->pid; + g_hash_table_insert(g_lmk_kill_exception_pid_list, (gpointer)pid, pci->name); + + return RESOURCED_ERROR_NONE; +} + +static int lowmem_governor_remove_exception_pid(void *data) +{ + struct proc_status *ps = (struct proc_status *)data; + int pid = ps->pid; + + if (g_hash_table_contains(g_lmk_kill_exception_pid_list, &pid)) { + _D("%s (pid = %d) is unregistered as LMK kill exceptoin pid", + ps->pai->appid, ps->pid); + g_hash_table_remove(g_lmk_kill_exception_pid_list, &pid); + } + + return RESOURCED_ERROR_NONE; +} + /* To Do: should we need lowmem_fd_start, lowmem_fd_stop ?? */ static int lowmem_init(void) { @@ -1666,7 +1748,14 @@ static int lowmem_init(void) lowmem_limit_init(); lowmem_system_init(); + g_lmk_kill_exception_pid_list = g_hash_table_new_full(g_int_hash, + g_int_equal, g_free, NULL); + g_assert(g_lmk_kill_exception_pid_list); + register_notifier(RESOURCED_NOTIFIER_APP_PRELAUNCH, lowmem_prelaunch_handler); + register_notifier(RESOURCED_NOTIFIER_APP_LAUNCH, lowmem_governor_add_exception_pid); + register_notifier(RESOURCED_NOTIFIER_SERVICE_LAUNCH, lowmem_governor_add_exception_pid); + register_notifier(RESOURCED_NOTIFIER_APP_TERMINATED, lowmem_governor_remove_exception_pid); return ret; } @@ -1677,7 +1766,12 @@ static int lowmem_exit(void) lowmem_limit_exit(); lowmem_system_exit(); + g_hash_table_destroy(g_lmk_kill_exception_pid_list); + unregister_notifier(RESOURCED_NOTIFIER_APP_PRELAUNCH, lowmem_prelaunch_handler); + unregister_notifier(RESOURCED_NOTIFIER_APP_LAUNCH, lowmem_governor_add_exception_pid); + unregister_notifier(RESOURCED_NOTIFIER_SERVICE_LAUNCH, lowmem_governor_add_exception_pid); + unregister_notifier(RESOURCED_NOTIFIER_APP_TERMINATED, lowmem_governor_remove_exception_pid); return RESOURCED_ERROR_NONE; } -- cgit v1.2.3