diff options
Diffstat (limited to 'fs/file.c')
| -rw-r--r-- | fs/file.c | 18 | 
1 files changed, 11 insertions, 7 deletions
diff --git a/fs/file.c b/fs/file.c index 0be344755c02..4c6992d8f3ba 100644 --- a/fs/file.c +++ b/fs/file.c @@ -9,6 +9,7 @@  #include <linux/module.h>  #include <linux/fs.h>  #include <linux/mm.h> +#include <linux/mmzone.h>  #include <linux/time.h>  #include <linux/sched.h>  #include <linux/slab.h> @@ -39,14 +40,17 @@ int sysctl_nr_open_max = 1024 * 1024; /* raised later */   */  static DEFINE_PER_CPU(struct fdtable_defer, fdtable_defer_list); -static inline void *alloc_fdmem(unsigned int size) +static void *alloc_fdmem(unsigned int size)  { -	void *data; - -	data = kmalloc(size, GFP_KERNEL|__GFP_NOWARN); -	if (data != NULL) -		return data; - +	/* +	 * Very large allocations can stress page reclaim, so fall back to +	 * vmalloc() if the allocation size will be considered "large" by the VM. +	 */ +	if (size <= (PAGE_SIZE << PAGE_ALLOC_COSTLY_ORDER)) { +		void *data = kmalloc(size, GFP_KERNEL|__GFP_NOWARN); +		if (data != NULL) +			return data; +	}  	return vmalloc(size);  }  | 
