aboutsummaryrefslogtreecommitdiffstats
path: root/mm/page_alloc.c
diff options
context:
space:
mode:
authorDave Hansen <dave@linux.vnet.ibm.com>2011-05-24 20:12:16 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2011-05-25 11:39:21 -0400
commita238ab5b0239575c179f4976064192c3f7409dad (patch)
treebed3d186bee49318e1984eeac489a614ad6acb1b /mm/page_alloc.c
parentde03c72cfce5b263a674d04348b58475ec50163c (diff)
mm: break out page allocation warning code
This originally started as a simple patch to give vmalloc() some more verbose output on failure on top of the plain page allocator messages. Johannes suggested that it might be nicer to lead with the vmalloc() info _before_ the page allocator messages. But, I do think there's a lot of value in what __alloc_pages_slowpath() does with its filtering and so forth. This patch creates a new function which other allocators can call instead of relying on the internal page allocator warnings. It also gives this function private rate-limiting which separates it from other printk_ratelimit() users. Signed-off-by: Dave Hansen <dave@linux.vnet.ibm.com> Cc: Johannes Weiner <hannes@cmpxchg.org> Cc: David Rientjes <rientjes@google.com> Cc: Michal Nazarewicz <mina86@mina86.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'mm/page_alloc.c')
-rw-r--r--mm/page_alloc.c62
1 files changed, 41 insertions, 21 deletions
diff --git a/mm/page_alloc.c b/mm/page_alloc.c
index 83eaa2eb72f8..44019da9632e 100644
--- a/mm/page_alloc.c
+++ b/mm/page_alloc.c
@@ -30,6 +30,7 @@
30#include <linux/pagevec.h> 30#include <linux/pagevec.h>
31#include <linux/blkdev.h> 31#include <linux/blkdev.h>
32#include <linux/slab.h> 32#include <linux/slab.h>
33#include <linux/ratelimit.h>
33#include <linux/oom.h> 34#include <linux/oom.h>
34#include <linux/notifier.h> 35#include <linux/notifier.h>
35#include <linux/topology.h> 36#include <linux/topology.h>
@@ -1736,6 +1737,45 @@ static inline bool should_suppress_show_mem(void)
1736 return ret; 1737 return ret;
1737} 1738}
1738 1739
1740static DEFINE_RATELIMIT_STATE(nopage_rs,
1741 DEFAULT_RATELIMIT_INTERVAL,
1742 DEFAULT_RATELIMIT_BURST);
1743
1744void warn_alloc_failed(gfp_t gfp_mask, int order, const char *fmt, ...)
1745{
1746 va_list args;
1747 unsigned int filter = SHOW_MEM_FILTER_NODES;
1748
1749 if ((gfp_mask & __GFP_NOWARN) || !__ratelimit(&nopage_rs))
1750 return;
1751
1752 /*
1753 * This documents exceptions given to allocations in certain
1754 * contexts that are allowed to allocate outside current's set
1755 * of allowed nodes.
1756 */
1757 if (!(gfp_mask & __GFP_NOMEMALLOC))
1758 if (test_thread_flag(TIF_MEMDIE) ||
1759 (current->flags & (PF_MEMALLOC | PF_EXITING)))
1760 filter &= ~SHOW_MEM_FILTER_NODES;
1761 if (in_interrupt() || !(gfp_mask & __GFP_WAIT))
1762 filter &= ~SHOW_MEM_FILTER_NODES;
1763
1764 if (fmt) {
1765 printk(KERN_WARNING);
1766 va_start(args, fmt);
1767 vprintk(fmt, args);
1768 va_end(args);
1769 }
1770
1771 pr_warning("%s: page allocation failure: order:%d, mode:0x%x\n",
1772 current->comm, order, gfp_mask);
1773
1774 dump_stack();
1775 if (!should_suppress_show_mem())
1776 show_mem(filter);
1777}
1778
1739static inline int 1779static inline int
1740should_alloc_retry(gfp_t gfp_mask, unsigned int order, 1780should_alloc_retry(gfp_t gfp_mask, unsigned int order,
1741 unsigned long pages_reclaimed) 1781 unsigned long pages_reclaimed)
@@ -2178,27 +2218,7 @@ rebalance:
2178 } 2218 }
2179 2219
2180nopage: 2220nopage:
2181 if (!(gfp_mask & __GFP_NOWARN) && printk_ratelimit()) { 2221 warn_alloc_failed(gfp_mask, order, NULL);
2182 unsigned int filter = SHOW_MEM_FILTER_NODES;
2183
2184 /*
2185 * This documents exceptions given to allocations in certain
2186 * contexts that are allowed to allocate outside current's set
2187 * of allowed nodes.
2188 */
2189 if (!(gfp_mask & __GFP_NOMEMALLOC))
2190 if (test_thread_flag(TIF_MEMDIE) ||
2191 (current->flags & (PF_MEMALLOC | PF_EXITING)))
2192 filter &= ~SHOW_MEM_FILTER_NODES;
2193 if (in_interrupt() || !wait)
2194 filter &= ~SHOW_MEM_FILTER_NODES;
2195
2196 pr_warning("%s: page allocation failure. order:%d, mode:0x%x\n",
2197 current->comm, order, gfp_mask);
2198 dump_stack();
2199 if (!should_suppress_show_mem())
2200 show_mem(filter);
2201 }
2202 return page; 2222 return page;
2203got_pg: 2223got_pg:
2204 if (kmemcheck_enabled) 2224 if (kmemcheck_enabled)