设为首页 加入收藏

TOP

oom killer(四)
2019-09-01 23:08:40 】 浏览:116
Tags:oom killer
), letting the system crash (worse) * OR try to be smart about which process to kill. Note that we * don't have to be perfect here, we just have to be good. */ void out_of_memory(struct zonelist *zonelist, gfp_t gfp_mask, int order, nodemask_t *nodemask, bool force_kill) { const nodemask_t *mpol_mask; struct task_struct *p; unsigned long totalpages; unsigned long freed = 0; unsigned int uninitialized_var(points); enum oom_constraint constraint = CONSTRAINT_NONE; int killed = 0; blocking_notifier_call_chain(&oom_notify_list, 0, &freed); if (freed > 0) /* Got some memory back in the last second. */ return; /* * If current has a pending SIGKILL or is exiting, then automatically * select it. The goal is to allow it to allocate so that it may * quickly exit and free its memory. */ if (fatal_signal_pending(current) || current->flags & PF_EXITING) { set_thread_flag(TIF_MEMDIE); return; } /* * Check if there were limitations on the allocation (only relevant for * NUMA) that may require different handling. */ constraint = constrained_alloc(zonelist, gfp_mask, nodemask, &totalpages); mpol_mask = (constraint == CONSTRAINT_MEMORY_POLICY) ? nodemask : NULL; check_panic_on_oom(constraint, gfp_mask, order, mpol_mask); if (sysctl_oom_kill_allocating_task && current->mm && !oom_unkillable_task(current, NULL, nodemask) && current->signal->oom_score_adj != OOM_SCORE_ADJ_MIN) { get_task_struct(current); oom_kill_process(current, gfp_mask, order, 0, totalpages, NULL, nodemask, "Out of memory (oom_kill_allocating_task)"); goto out; } p = select_bad_process(&points, totalpages, mpol_mask, force_kill); /* Found nothing?!?! Either we hang forever, or we panic. */ if (!p) { dump_header(NULL, gfp_mask, order, NULL, mpol_mask); panic("Out of memory and no killable processes...\n"); } if (p != (void *)-1UL) { oom_kill_process(p, gfp_mask, order, points, totalpages, NULL, nodemask, "Out of memory"); killed = 1; } out: /* * Give the killed threads a good chance of exiting before trying to * allocate memory again. */ if (killed) schedule_timeout_killable(1); }

该函数首先调用blocking_notifier_call_chain()进行OOM的内核通知链回调处理;接着的if (fatal_signal_pending(current) || current->flags & PF_EXITING)判断则是用于检查是否有SIGKILL信号挂起或者正在信号处理中,如果有则退出;再接着通过constrained_alloc()检查内存分配限制以及check_panic_on_oom()检查是否报linux内核panic;继而判断sysctl_oom_kill_allocating_task变量及进程检查,如果符合条件判断,则将当前分配的内存kill掉;否则最后,将通过select_bad_process()选出最佳的进程,进而调用oom_kill_process()对其进行kill操作。

最后分析一下select_bad_process()和oom_kill_process(),其中select_bad_process()的实现:

【file:/ mm/oom_kill.c】
/*
 * Simple selection loop. We chose the process with the highest
 * number of 'points'. Returns -1 on scan abort.
 *
 * (not docbooked, we don't want this one cluttering up the manual)
 */
static struct task_struct *select_bad_process(unsigned int *ppoints,
        unsigned long totalpages, const nodemask_t *nodemask,
        bool force_kill)
{
    struct task_struct *g, *p;
    struct task_struct *chosen = NULL;
    unsigned long chosen_points = 0;
 
    rcu_read_lock();
    for_each_process_thread(g, p) {
        unsigned int points;
 
        switch (oom_scan_process_thread(p, totalpages, nodemask,
                        force_kill)) {
        case OOM_SCAN_SELECT:
            chosen = p;
            chosen_points = ULONG_MAX;
            /* fall through */
        case OOM_SCAN_C
首页 上一页 1 2 3 4 5 6 下一页 尾页 4/6/6
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
上一篇Linux 匿名页的反向映射 下一篇在keil中添加stc系列单片机型号(..

最新文章

热门文章

Hot 文章

Python

C 语言

C++基础

大数据基础

linux编程基础

C/C++面试题目