[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for GFP_THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists consume memory and occupy cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman <[EMAIL PROTECTED]> Acked-by: Christoph Lameter <[EMAIL PROTECTED]> --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 17 +--- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 20 ++--- 10 files changed, 159 insertions(+), 161 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.24-rc1-mm-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.24-rc1-mm-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.24-rc1-mm-007_node_zonelist/arch/parisc/mm/init.c 2007-11-08 19:04:11.0 + +++ linux-2.6.24-rc1-mm-010_use_two_zonelists/arch/parisc/mm/init.c 2007-11-08 19:11:18.0 + @@ -603,15 +603,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i < npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j < MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)->node_zonelists + j; + struct zone **z; + struct zone *zone; printk("Zone list for zone %d on node %d: ", j, i); - for (k = 0; zl->zones[k] != NULL; k++) - printk("[%d/%s] ", zone_to_nid(zl->zones[k]), zl->zones[k]->name); + for_each_zone_zonelist(zone, z, zl, j) + printk("[%d/%s] ", zone_to_nid(zone), + zone->name); printk("\n"); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.24-rc1-mm-007_node_zonelist/fs/buffer.c linux-2.6.24-rc1-mm-010_use_two_zonelists/fs/buffer.c --- linux-2.6.24-rc1-mm-007_node_zonelist/fs/buffer.c 2007-11-08 19:08:12.0 + +++ linux-2.6.24-rc1-mm-010_use_two_zonelists/fs/buffer.c 2007-11-08 19:11:18.0 + @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.24-rc1-mm-007_node_zonelist/include/linux/gfp.h linux-2.6.24-rc1-mm-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.24-rc1-mm-007_node_zonelist/include/linux/gfp.h 2007-11-08 19:08:12.0 + +++ linux-2.6.24-rc1-mm-010_use_two_zonelists/include/linux/gfp.h 2007-11-08 19:11:18.0 + @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags & __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags & __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags & __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags & (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags & __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff
[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for GFP_THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists consume memory and occupy cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman [EMAIL PROTECTED] Acked-by: Christoph Lameter [EMAIL PROTECTED] --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 17 +--- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 20 ++--- 10 files changed, 159 insertions(+), 161 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.24-rc1-mm-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.24-rc1-mm-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.24-rc1-mm-007_node_zonelist/arch/parisc/mm/init.c 2007-11-08 19:04:11.0 + +++ linux-2.6.24-rc1-mm-010_use_two_zonelists/arch/parisc/mm/init.c 2007-11-08 19:11:18.0 + @@ -603,15 +603,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)-node_zonelists + j; + struct zone **z; + struct zone *zone; printk(Zone list for zone %d on node %d: , j, i); - for (k = 0; zl-zones[k] != NULL; k++) - printk([%d/%s] , zone_to_nid(zl-zones[k]), zl-zones[k]-name); + for_each_zone_zonelist(zone, z, zl, j) + printk([%d/%s] , zone_to_nid(zone), + zone-name); printk(\n); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.24-rc1-mm-007_node_zonelist/fs/buffer.c linux-2.6.24-rc1-mm-010_use_two_zonelists/fs/buffer.c --- linux-2.6.24-rc1-mm-007_node_zonelist/fs/buffer.c 2007-11-08 19:08:12.0 + +++ linux-2.6.24-rc1-mm-010_use_two_zonelists/fs/buffer.c 2007-11-08 19:11:18.0 + @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.24-rc1-mm-007_node_zonelist/include/linux/gfp.h linux-2.6.24-rc1-mm-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.24-rc1-mm-007_node_zonelist/include/linux/gfp.h 2007-11-08 19:08:12.0 + +++ linux-2.6.24-rc1-mm-010_use_two_zonelists/include/linux/gfp.h 2007-11-08 19:11:18.0 + @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff
[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for GFP_THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists consume memory and occupy cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman <[EMAIL PROTECTED]> Acked-by: Christoph Lameter <[EMAIL PROTECTED]> --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 17 +--- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 21 ++--- 10 files changed, 159 insertions(+), 162 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc8-mm2-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.23-rc8-mm2-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.23-rc8-mm2-007_node_zonelist/arch/parisc/mm/init.c 2007-09-25 01:33:10.0 +0100 +++ linux-2.6.23-rc8-mm2-010_use_two_zonelists/arch/parisc/mm/init.c 2007-09-28 15:49:16.0 +0100 @@ -599,15 +599,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i < npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j < MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)->node_zonelists + j; + struct zone **z; + struct zone *zone; printk("Zone list for zone %d on node %d: ", j, i); - for (k = 0; zl->zones[k] != NULL; k++) - printk("[%ld/%s] ", zone_to_nid(zl->zones[k]), zl->zones[k]->name); + for_each_zone_zonelist(zone, z, zl, j) + printk("[%d/%s] ", zone_to_nid(zone), + zone->name); printk("\n"); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc8-mm2-007_node_zonelist/fs/buffer.c linux-2.6.23-rc8-mm2-010_use_two_zonelists/fs/buffer.c --- linux-2.6.23-rc8-mm2-007_node_zonelist/fs/buffer.c 2007-09-28 15:48:55.0 +0100 +++ linux-2.6.23-rc8-mm2-010_use_two_zonelists/fs/buffer.c 2007-09-28 15:49:16.0 +0100 @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc8-mm2-007_node_zonelist/include/linux/gfp.h linux-2.6.23-rc8-mm2-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.23-rc8-mm2-007_node_zonelist/include/linux/gfp.h 2007-09-28 15:48:55.0 +0100 +++ linux-2.6.23-rc8-mm2-010_use_two_zonelists/include/linux/gfp.h 2007-09-28 15:49:16.0 +0100 @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags & __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags & __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags & __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags & (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags & __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) diff -rup -X
[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for GFP_THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists consume memory and occupy cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman [EMAIL PROTECTED] Acked-by: Christoph Lameter [EMAIL PROTECTED] --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 17 +--- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 21 ++--- 10 files changed, 159 insertions(+), 162 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc8-mm2-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.23-rc8-mm2-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.23-rc8-mm2-007_node_zonelist/arch/parisc/mm/init.c 2007-09-25 01:33:10.0 +0100 +++ linux-2.6.23-rc8-mm2-010_use_two_zonelists/arch/parisc/mm/init.c 2007-09-28 15:49:16.0 +0100 @@ -599,15 +599,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)-node_zonelists + j; + struct zone **z; + struct zone *zone; printk(Zone list for zone %d on node %d: , j, i); - for (k = 0; zl-zones[k] != NULL; k++) - printk([%ld/%s] , zone_to_nid(zl-zones[k]), zl-zones[k]-name); + for_each_zone_zonelist(zone, z, zl, j) + printk([%d/%s] , zone_to_nid(zone), + zone-name); printk(\n); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc8-mm2-007_node_zonelist/fs/buffer.c linux-2.6.23-rc8-mm2-010_use_two_zonelists/fs/buffer.c --- linux-2.6.23-rc8-mm2-007_node_zonelist/fs/buffer.c 2007-09-28 15:48:55.0 +0100 +++ linux-2.6.23-rc8-mm2-010_use_two_zonelists/fs/buffer.c 2007-09-28 15:49:16.0 +0100 @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc8-mm2-007_node_zonelist/include/linux/gfp.h linux-2.6.23-rc8-mm2-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.23-rc8-mm2-007_node_zonelist/include/linux/gfp.h 2007-09-28 15:48:55.0 +0100 +++ linux-2.6.23-rc8-mm2-010_use_two_zonelists/include/linux/gfp.h 2007-09-28 15:49:16.0 +0100 @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff
[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists occupy memory and consume cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman <[EMAIL PROTECTED]> Acked-by: Christoph Lameter <[EMAIL PROTECTED]> --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 17 +--- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 22 ++--- 10 files changed, 160 insertions(+), 162 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c 2007-08-28 02:32:35.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c 2007-09-13 11:57:36.0 +0100 @@ -599,15 +599,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i < npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j < MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)->node_zonelists + j; + struct zone **z; + struct zone *zone; printk("Zone list for zone %d on node %d: ", j, i); - for (k = 0; zl->zones[k] != NULL; k++) - printk("[%ld/%s] ", zone_to_nid(zl->zones[k]), zl->zones[k]->name); + for_each_zone_zonelist(zone, z, zl, j) + printk("[%d/%s] ", zone_to_nid(zone), + zone->name); printk("\n"); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c 2007-09-13 11:57:27.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c 2007-09-13 11:57:36.0 +0100 @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h 2007-09-13 11:57:27.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h 2007-09-13 11:57:36.0 +0100 @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags & __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags & __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags & __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags & (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags & __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) diff -rup -X
[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists occupy memory and consume cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman [EMAIL PROTECTED] Acked-by: Christoph Lameter [EMAIL PROTECTED] --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 17 +--- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 22 ++--- 10 files changed, 160 insertions(+), 162 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c 2007-08-28 02:32:35.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c 2007-09-13 11:57:36.0 +0100 @@ -599,15 +599,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)-node_zonelists + j; + struct zone **z; + struct zone *zone; printk(Zone list for zone %d on node %d: , j, i); - for (k = 0; zl-zones[k] != NULL; k++) - printk([%ld/%s] , zone_to_nid(zl-zones[k]), zl-zones[k]-name); + for_each_zone_zonelist(zone, z, zl, j) + printk([%d/%s] , zone_to_nid(zone), + zone-name); printk(\n); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c 2007-09-13 11:57:27.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c 2007-09-13 11:57:36.0 +0100 @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h 2007-09-13 11:57:27.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h 2007-09-13 11:57:36.0 +0100 @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff
[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists occupy memory and consume cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman <[EMAIL PROTECTED]> Acked-by: Christoph Lameter <[EMAIL PROTECTED]> --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 29 --- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 20 ++--- 10 files changed, 171 insertions(+), 161 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c 2007-08-28 02:32:35.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c 2007-09-12 16:05:27.0 +0100 @@ -599,15 +599,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i < npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j < MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)->node_zonelists + j; + struct zone **z; + struct zone *zone; printk("Zone list for zone %d on node %d: ", j, i); - for (k = 0; zl->zones[k] != NULL; k++) - printk("[%ld/%s] ", zone_to_nid(zl->zones[k]), zl->zones[k]->name); + for_each_zone_zonelist(zone, z, zl, j) + printk("[%d/%s] ", zone_to_nid(zone), + zone->name); printk("\n"); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c 2007-09-12 16:05:18.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c 2007-09-12 16:05:27.0 +0100 @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h 2007-09-12 16:05:18.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h 2007-09-12 16:05:27.0 +0100 @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags & __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags & __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags & __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags & (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags & __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) @@ -157,6 +150,18 @@ static inline gfp_t
[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists occupy memory and consume cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman [EMAIL PROTECTED] Acked-by: Christoph Lameter [EMAIL PROTECTED] --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 29 --- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 20 ++--- 10 files changed, 171 insertions(+), 161 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c 2007-08-28 02:32:35.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c 2007-09-12 16:05:27.0 +0100 @@ -599,15 +599,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)-node_zonelists + j; + struct zone **z; + struct zone *zone; printk(Zone list for zone %d on node %d: , j, i); - for (k = 0; zl-zones[k] != NULL; k++) - printk([%ld/%s] , zone_to_nid(zl-zones[k]), zl-zones[k]-name); + for_each_zone_zonelist(zone, z, zl, j) + printk([%d/%s] , zone_to_nid(zone), + zone-name); printk(\n); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c 2007-09-12 16:05:18.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c 2007-09-12 16:05:27.0 +0100 @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h 2007-09-12 16:05:18.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h 2007-09-12 16:05:27.0 +0100 @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) @@ -157,6 +150,18 @@ static inline gfp_t set_migrateflags(gfp *
[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists occupy memory and consume cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman <[EMAIL PROTECTED]> Acked-by: Christoph Lameter <[EMAIL PROTECTED]> --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 29 --- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 20 ++--- 10 files changed, 171 insertions(+), 161 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c 2007-08-28 02:32:35.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c 2007-09-10 16:06:22.0 +0100 @@ -599,15 +599,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i < npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j < MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)->node_zonelists + j; + struct zone **z; + struct zone *zone; printk("Zone list for zone %d on node %d: ", j, i); - for (k = 0; zl->zones[k] != NULL; k++) - printk("[%ld/%s] ", zone_to_nid(zl->zones[k]), zl->zones[k]->name); + for_each_zone_zonelist(zone, z, zl, j) + printk("[%d/%s] ", zone_to_nid(zone), + zone->name); printk("\n"); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c 2007-09-10 16:06:13.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c 2007-09-10 16:06:22.0 +0100 @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h 2007-09-10 16:06:13.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h 2007-09-10 16:06:22.0 +0100 @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags & __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags & __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags & __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags & (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags & __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) @@ -157,6 +150,18 @@ static inline gfp_t
[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists occupy memory and consume cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman <[EMAIL PROTECTED]> Acked-by: Christoph Lameter <[EMAIL PROTECTED]> --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 29 --- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 20 ++--- 10 files changed, 171 insertions(+), 161 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c 2007-08-28 02:32:35.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c 2007-09-10 16:06:22.0 +0100 @@ -599,15 +599,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i < npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j < MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)->node_zonelists + j; + struct zone **z; + struct zone *zone; printk("Zone list for zone %d on node %d: ", j, i); - for (k = 0; zl->zones[k] != NULL; k++) - printk("[%ld/%s] ", zone_to_nid(zl->zones[k]), zl->zones[k]->name); + for_each_zone_zonelist(zone, z, zl, j) + printk("[%d/%s] ", zone_to_nid(zone), + zone->name); printk("\n"); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c 2007-09-10 16:06:13.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c 2007-09-10 16:06:22.0 +0100 @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h 2007-09-10 16:06:13.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h 2007-09-10 16:06:22.0 +0100 @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags & __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags & __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags & __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags & (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags & __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) @@ -157,6 +150,18 @@ static inline gfp_t
[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists occupy memory and consume cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman [EMAIL PROTECTED] Acked-by: Christoph Lameter [EMAIL PROTECTED] --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 29 --- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 20 ++--- 10 files changed, 171 insertions(+), 161 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c 2007-08-28 02:32:35.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c 2007-09-10 16:06:22.0 +0100 @@ -599,15 +599,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)-node_zonelists + j; + struct zone **z; + struct zone *zone; printk(Zone list for zone %d on node %d: , j, i); - for (k = 0; zl-zones[k] != NULL; k++) - printk([%ld/%s] , zone_to_nid(zl-zones[k]), zl-zones[k]-name); + for_each_zone_zonelist(zone, z, zl, j) + printk([%d/%s] , zone_to_nid(zone), + zone-name); printk(\n); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c 2007-09-10 16:06:13.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c 2007-09-10 16:06:22.0 +0100 @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h 2007-09-10 16:06:13.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h 2007-09-10 16:06:22.0 +0100 @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) @@ -157,6 +150,18 @@ static inline gfp_t set_migrateflags(gfp *
[PATCH 3/6] Use two zonelist that are filtered by GFP mask
Currently a node has a number of zonelists, one for each zone type in the system and a second set for THISNODE allocations. Based on the zones allowed by a gfp mask, one of these zonelists is selected. All of these zonelists occupy memory and consume cache lines. This patch replaces the multiple zonelists per-node with two zonelists. The first contains all populated zones in the system and the second contains all populated zones in node suitable for GFP_THISNODE allocations. An iterator macro is introduced called for_each_zone_zonelist() interates through each zone in the zonelist that is allowed by the GFP flags. Signed-off-by: Mel Gorman [EMAIL PROTECTED] Acked-by: Christoph Lameter [EMAIL PROTECTED] --- arch/parisc/mm/init.c | 11 +- fs/buffer.c|6 + include/linux/gfp.h| 29 --- include/linux/mmzone.h | 65 +++- mm/hugetlb.c |8 +- mm/oom_kill.c |8 +- mm/page_alloc.c| 169 +++- mm/slab.c |8 +- mm/slub.c |8 +- mm/vmscan.c| 20 ++--- 10 files changed, 171 insertions(+), 161 deletions(-) diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/arch/parisc/mm/init.c 2007-08-28 02:32:35.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/arch/parisc/mm/init.c 2007-09-10 16:06:22.0 +0100 @@ -599,15 +599,18 @@ void show_mem(void) #ifdef CONFIG_DISCONTIGMEM { struct zonelist *zl; - int i, j, k; + int i, j; for (i = 0; i npmem_ranges; i++) { + zl = node_zonelist(i); for (j = 0; j MAX_NR_ZONES; j++) { - zl = NODE_DATA(i)-node_zonelists + j; + struct zone **z; + struct zone *zone; printk(Zone list for zone %d on node %d: , j, i); - for (k = 0; zl-zones[k] != NULL; k++) - printk([%ld/%s] , zone_to_nid(zl-zones[k]), zl-zones[k]-name); + for_each_zone_zonelist(zone, z, zl, j) + printk([%d/%s] , zone_to_nid(zone), + zone-name); printk(\n); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c --- linux-2.6.23-rc4-mm1-007_node_zonelist/fs/buffer.c 2007-09-10 16:06:13.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/fs/buffer.c 2007-09-10 16:06:22.0 +0100 @@ -375,9 +375,11 @@ static void free_more_memory(void) yield(); for_each_online_node(nid) { - zones = node_zonelist(nid, GFP_NOFS); + zones = first_zones_zonelist(node_zonelist(nid, GFP_NOFS), + gfp_zone(GFP_NOFS)); if (*zones) - try_to_free_pages(zones, 0, GFP_NOFS); + try_to_free_pages(node_zonelist(nid, GFP_NOFS), 0, + GFP_NOFS); } } diff -rup -X /usr/src/patchset-0.6/bin//dontdiff linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h --- linux-2.6.23-rc4-mm1-007_node_zonelist/include/linux/gfp.h 2007-09-10 16:06:13.0 +0100 +++ linux-2.6.23-rc4-mm1-010_use_two_zonelists/include/linux/gfp.h 2007-09-10 16:06:22.0 +0100 @@ -119,29 +119,22 @@ static inline int allocflags_to_migratet static inline enum zone_type gfp_zone(gfp_t flags) { - int base = 0; - -#ifdef CONFIG_NUMA - if (flags __GFP_THISNODE) - base = MAX_NR_ZONES; -#endif - #ifdef CONFIG_ZONE_DMA if (flags __GFP_DMA) - return base + ZONE_DMA; + return ZONE_DMA; #endif #ifdef CONFIG_ZONE_DMA32 if (flags __GFP_DMA32) - return base + ZONE_DMA32; + return ZONE_DMA32; #endif if ((flags (__GFP_HIGHMEM | __GFP_MOVABLE)) == (__GFP_HIGHMEM | __GFP_MOVABLE)) - return base + ZONE_MOVABLE; + return ZONE_MOVABLE; #ifdef CONFIG_HIGHMEM if (flags __GFP_HIGHMEM) - return base + ZONE_HIGHMEM; + return ZONE_HIGHMEM; #endif - return base + ZONE_NORMAL; + return ZONE_NORMAL; } static inline gfp_t set_migrateflags(gfp_t gfp, gfp_t migrate_flags) @@ -157,6 +150,18 @@ static inline gfp_t set_migrateflags(gfp *