aa-120-try_to_free_pages_nozone
Subsystems (4)
The page reclaiming logic operates on a per-zone basis. This patch introduces a general try_to_free_pages_nozone() which just tries to free 32 pages from *every* zone.
This function is only used from free_more_memory() in fs/buffer.c. When we're trying to grow buffers against a device for filesystem metadata.
It seems to me that free_more_memory() simply is not needed - we're already retrying the allocation over in buffer.c, and it seems that this will do most everything which the call to try_to_free_pages() would do?
=====================================
fs/buffer.c renamed from fs/buffer.c~aa-120-try_to_free_pages_nozone +1 -5
@@ -731,12 +731,8 @@ void __invalidate_buffers(kdev_t dev, instatic void free_more_memory (void ) { -zone_t * zone = contig_page_data.node_zonelists[GFP_NOFS &GFP_ZONEMASK ].zones[0 ]; - -balance_dirty ();wakeup_bdflush (); -try_to_free_pages (zone,GFP_NOFS ,0 ); -run_task_queue (&tq_disk); +try_to_free_pages_nozone (GFP_NOIO ); current->policy |=SCHED_YIELD ;__set_current_state (TASK_RUNNING );schedule ();
include/linux/swap.h renamed from include/linux/swap.h~aa-120-try_to_free_pages_nozone +1 -0
@@ -113,6 +113,7 @@ extern void swap_setup(void);extern wait_queue_head_t kswapd_wait;extern int FASTCALL (try_to_free_pages (zone_t *,unsigned int ,unsigned int ));extern int vm_vfs_scan_ratio, vm_cache_scan_ratio, vm_lru_balance_ratio, vm_passes, vm_gfp_debug, vm_mapped_ratio; +extern int FASTCALL (try_to_free_pages_nozone (unsigned int ));/* linux/mm/page_io.c */ extern void rw_swap_page (int ,struct page *);
mm/page_alloc.c renamed from mm/page_alloc.c~aa-120-try_to_free_pages_nozone +24 -0
@@ -510,6 +510,30 @@ unsigned int nr_free_highpages (void) }#endif +int try_to_free_pages_nozone (unsigned int gfp_mask) +{ +pg_data_t *pgdat = pgdat_list; +zonelist_t *zonelist; +zone_t **zonep; +int ret =0 ; +unsigned long pf_free_pages; + + pf_free_pages = current->flags &PF_FREE_PAGES ; + current->flags &= ~PF_FREE_PAGES ; + +do { + zonelist = pgdat->node_zonelists + (gfp_mask &GFP_ZONEMASK ); + zonep = zonelist->zones; + + ret |=try_to_free_pages (*zonep, gfp_mask,0 ); + + pgdat = pgdat->node_next; + }while (pgdat); + + current->flags |= pf_free_pages; +return ret; +} +#define K (x) ((x) << (PAGE_SHIFT-10))/*
-