Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 207216
b: refs/heads/master
c: e365893
h: refs/heads/master
v: v3
  • Loading branch information
David Rientjes authored and Linus Torvalds committed Aug 10, 2010
1 parent f2a7a3f commit c0f9851
Show file tree
Hide file tree
Showing 2 changed files with 58 additions and 30 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 309ed882508cc471320ff79265e7340774d6746c
refs/heads/master: e365893236ca78fa1fe2482ccbdc30e9abde6027
86 changes: 57 additions & 29 deletions trunk/mm/oom_kill.c
Original file line number Diff line number Diff line change
Expand Up @@ -630,6 +630,44 @@ void clear_zonelist_oom(struct zonelist *zonelist, gfp_t gfp_mask)
spin_unlock(&zone_scan_lock);
}

/*
* Try to acquire the oom killer lock for all system zones. Returns zero if a
* parallel oom killing is taking place, otherwise locks all zones and returns
* non-zero.
*/
static int try_set_system_oom(void)
{
struct zone *zone;
int ret = 1;

spin_lock(&zone_scan_lock);
for_each_populated_zone(zone)
if (zone_is_oom_locked(zone)) {
ret = 0;
goto out;
}
for_each_populated_zone(zone)
zone_set_flag(zone, ZONE_OOM_LOCKED);
out:
spin_unlock(&zone_scan_lock);
return ret;
}

/*
* Clears ZONE_OOM_LOCKED for all system zones so that failed allocation
* attempts or page faults may now recall the oom killer, if necessary.
*/
static void clear_system_oom(void)
{
struct zone *zone;

spin_lock(&zone_scan_lock);
for_each_populated_zone(zone)
zone_clear_flag(zone, ZONE_OOM_LOCKED);
spin_unlock(&zone_scan_lock);
}


/*
* Must be called with tasklist_lock held for read.
*/
Expand Down Expand Up @@ -665,33 +703,6 @@ static void __out_of_memory(gfp_t gfp_mask, int order,
goto retry;
}

/*
* pagefault handler calls into here because it is out of memory but
* doesn't know exactly how or why.
*/
void pagefault_out_of_memory(void)
{
unsigned long freed = 0;

blocking_notifier_call_chain(&oom_notify_list, 0, &freed);
if (freed > 0)
/* Got some memory back in the last second. */
return;

check_panic_on_oom(CONSTRAINT_NONE, 0, 0);
read_lock(&tasklist_lock);
/* unknown gfp_mask and order */
__out_of_memory(0, 0, CONSTRAINT_NONE, NULL);
read_unlock(&tasklist_lock);

/*
* Give "p" a good chance of killing itself before we
* retry to allocate memory.
*/
if (!test_thread_flag(TIF_MEMDIE))
schedule_timeout_uninterruptible(1);
}

/**
* out_of_memory - kill the "best" process when we run out of memory
* @zonelist: zonelist pointer
Expand All @@ -708,7 +719,7 @@ void out_of_memory(struct zonelist *zonelist, gfp_t gfp_mask,
int order, nodemask_t *nodemask)
{
unsigned long freed = 0;
enum oom_constraint constraint;
enum oom_constraint constraint = CONSTRAINT_NONE;

blocking_notifier_call_chain(&oom_notify_list, 0, &freed);
if (freed > 0)
Expand All @@ -729,7 +740,8 @@ void out_of_memory(struct zonelist *zonelist, gfp_t gfp_mask,
* Check if there were limitations on the allocation (only relevant for
* NUMA) that may require different handling.
*/
constraint = constrained_alloc(zonelist, gfp_mask, nodemask);
if (zonelist)
constraint = constrained_alloc(zonelist, gfp_mask, nodemask);
check_panic_on_oom(constraint, gfp_mask, order);
read_lock(&tasklist_lock);
__out_of_memory(gfp_mask, order, constraint, nodemask);
Expand All @@ -742,3 +754,19 @@ void out_of_memory(struct zonelist *zonelist, gfp_t gfp_mask,
if (!test_thread_flag(TIF_MEMDIE))
schedule_timeout_uninterruptible(1);
}

/*
* The pagefault handler calls here because it is out of memory, so kill a
* memory-hogging task. If a populated zone has ZONE_OOM_LOCKED set, a parallel
* oom killing is already in progress so do nothing. If a task is found with
* TIF_MEMDIE set, it has been killed so do nothing and allow it to exit.
*/
void pagefault_out_of_memory(void)
{
if (try_set_system_oom()) {
out_of_memory(NULL, 0, 0, NULL);
clear_system_oom();
}
if (!test_thread_flag(TIF_MEMDIE))
schedule_timeout_uninterruptible(1);
}

0 comments on commit c0f9851

Please sign in to comment.