Commit 4b4b90a7 authored by Andrew Morton's avatar Andrew Morton Committed by Linus Torvalds

[PATCH] discontigmem fixes and cleanups

From Martin Bligh

This patch fixes a nasty bug that wli found in buffer.c which
cause an oops - we were using contig_page_data on a discontigmem
machine. It's a slightly modified version of the fix wli suggested,
tested on NUMA-Q.

I've also added code to not define contig_page_data for discontigmem
systems, to stop this from happening again. I wrapped a couple of
bootmem functions that were using it in #ifndef CONFIG_DISCONTIGMEM.
I suppose it's possible (though unlikely) that some other discontig
arch might need to wrap a couple of functions in their tree similarly,
but any borkage will just give a simple clear compiler error telling
them exactly where the problem is.
parent 168973c5
...@@ -462,12 +462,17 @@ void __invalidate_buffers(kdev_t dev, int destroy_dirty_buffers) ...@@ -462,12 +462,17 @@ void __invalidate_buffers(kdev_t dev, int destroy_dirty_buffers)
static void free_more_memory(void) static void free_more_memory(void)
{ {
struct zone *zone; struct zone *zone;
pg_data_t *pgdat;
zone = contig_page_data.node_zonelists[GFP_NOFS&GFP_ZONEMASK].zones[0];
wakeup_bdflush(1024); wakeup_bdflush(1024);
blk_run_queues(); blk_run_queues();
yield(); yield();
try_to_free_pages(zone, GFP_NOFS, 0);
for_each_pgdat(pgdat) {
zone = pgdat->node_zonelists[GFP_NOFS&GFP_ZONEMASK].zones[0];
if (zone)
try_to_free_pages(zone, GFP_NOFS, 0);
}
} }
/* /*
......
...@@ -311,6 +311,7 @@ unsigned long __init free_all_bootmem_node (pg_data_t *pgdat) ...@@ -311,6 +311,7 @@ unsigned long __init free_all_bootmem_node (pg_data_t *pgdat)
return(free_all_bootmem_core(pgdat)); return(free_all_bootmem_core(pgdat));
} }
#ifndef CONFIG_DISCONTIGMEM
unsigned long __init init_bootmem (unsigned long start, unsigned long pages) unsigned long __init init_bootmem (unsigned long start, unsigned long pages)
{ {
max_low_pfn = pages; max_low_pfn = pages;
...@@ -334,6 +335,7 @@ unsigned long __init free_all_bootmem (void) ...@@ -334,6 +335,7 @@ unsigned long __init free_all_bootmem (void)
{ {
return(free_all_bootmem_core(&contig_page_data)); return(free_all_bootmem_core(&contig_page_data));
} }
#endif /* !CONFIG_DISCONTIGMEM */
void * __init __alloc_bootmem (unsigned long size, unsigned long align, unsigned long goal) void * __init __alloc_bootmem (unsigned long size, unsigned long align, unsigned long goal)
{ {
......
...@@ -11,11 +11,11 @@ ...@@ -11,11 +11,11 @@
int numnodes = 1; /* Initialized for UMA platforms */ int numnodes = 1; /* Initialized for UMA platforms */
#ifndef CONFIG_DISCONTIGMEM
static bootmem_data_t contig_bootmem_data; static bootmem_data_t contig_bootmem_data;
pg_data_t contig_page_data = { .bdata = &contig_bootmem_data }; pg_data_t contig_page_data = { .bdata = &contig_bootmem_data };
#ifndef CONFIG_DISCONTIGMEM
/* /*
* This is meant to be invoked by platforms whose physical memory starts * This is meant to be invoked by platforms whose physical memory starts
* at a considerably higher value than 0. Examples are Super-H, ARM, m68k. * at a considerably higher value than 0. Examples are Super-H, ARM, m68k.
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment