diff options
Diffstat (limited to 'fs/netfs/main.c')
| -rw-r--r-- | fs/netfs/main.c | 55 | 
1 files changed, 47 insertions, 8 deletions
diff --git a/fs/netfs/main.c b/fs/netfs/main.c index 5e77618a7940..5f0f438e5d21 100644 --- a/fs/netfs/main.c +++ b/fs/netfs/main.c @@ -7,6 +7,7 @@  #include <linux/module.h>  #include <linux/export.h> +#include <linux/mempool.h>  #include <linux/proc_fs.h>  #include <linux/seq_file.h>  #include "internal.h" @@ -23,6 +24,11 @@ unsigned netfs_debug;  module_param_named(debug, netfs_debug, uint, S_IWUSR | S_IRUGO);  MODULE_PARM_DESC(netfs_debug, "Netfs support debugging mask"); +static struct kmem_cache *netfs_request_slab; +static struct kmem_cache *netfs_subrequest_slab; +mempool_t netfs_request_pool; +mempool_t netfs_subrequest_pool; +  #ifdef CONFIG_PROC_FS  LIST_HEAD(netfs_io_requests);  DEFINE_SPINLOCK(netfs_proc_lock); @@ -31,9 +37,9 @@ static const char *netfs_origins[nr__netfs_io_origin] = {  	[NETFS_READAHEAD]		= "RA",  	[NETFS_READPAGE]		= "RP",  	[NETFS_READ_FOR_WRITE]		= "RW", +	[NETFS_COPY_TO_CACHE]		= "CC",  	[NETFS_WRITEBACK]		= "WB",  	[NETFS_WRITETHROUGH]		= "WT", -	[NETFS_LAUNDER_WRITE]		= "LW",  	[NETFS_UNBUFFERED_WRITE]	= "UW",  	[NETFS_DIO_READ]		= "DR",  	[NETFS_DIO_WRITE]		= "DW", @@ -56,7 +62,7 @@ static int netfs_requests_seq_show(struct seq_file *m, void *v)  	rreq = list_entry(v, struct netfs_io_request, proc_link);  	seq_printf(m, -		   "%08x %s %3d %2lx %4d %3d @%04llx %zx/%zx", +		   "%08x %s %3d %2lx %4d %3d @%04llx %llx/%llx",  		   rreq->debug_id,  		   netfs_origins[rreq->origin],  		   refcount_read(&rreq->ref), @@ -98,25 +104,54 @@ static int __init netfs_init(void)  {  	int ret = -ENOMEM; +	netfs_request_slab = kmem_cache_create("netfs_request", +					       sizeof(struct netfs_io_request), 0, +					       SLAB_HWCACHE_ALIGN | SLAB_ACCOUNT, +					       NULL); +	if (!netfs_request_slab) +		goto error_req; + +	if (mempool_init_slab_pool(&netfs_request_pool, 100, netfs_request_slab) < 0) +		goto error_reqpool; + +	netfs_subrequest_slab = kmem_cache_create("netfs_subrequest", +						  sizeof(struct netfs_io_subrequest), 0, +						  SLAB_HWCACHE_ALIGN | SLAB_ACCOUNT, +						  NULL); +	if (!netfs_subrequest_slab) +		goto error_subreq; + +	if (mempool_init_slab_pool(&netfs_subrequest_pool, 100, netfs_subrequest_slab) < 0) +		goto error_subreqpool; +  	if (!proc_mkdir("fs/netfs", NULL)) -		goto error; +		goto error_proc;  	if (!proc_create_seq("fs/netfs/requests", S_IFREG | 0444, NULL,  			     &netfs_requests_seq_ops)) -		goto error_proc; +		goto error_procfile;  #ifdef CONFIG_FSCACHE_STATS  	if (!proc_create_single("fs/netfs/stats", S_IFREG | 0444, NULL,  				netfs_stats_show)) -		goto error_proc; +		goto error_procfile;  #endif  	ret = fscache_init();  	if (ret < 0) -		goto error_proc; +		goto error_fscache;  	return 0; -error_proc: +error_fscache: +error_procfile:  	remove_proc_entry("fs/netfs", NULL); -error: +error_proc: +	mempool_exit(&netfs_subrequest_pool); +error_subreqpool: +	kmem_cache_destroy(netfs_subrequest_slab); +error_subreq: +	mempool_exit(&netfs_request_pool); +error_reqpool: +	kmem_cache_destroy(netfs_request_slab); +error_req:  	return ret;  }  fs_initcall(netfs_init); @@ -125,5 +160,9 @@ static void __exit netfs_exit(void)  {  	fscache_exit();  	remove_proc_entry("fs/netfs", NULL); +	mempool_exit(&netfs_subrequest_pool); +	kmem_cache_destroy(netfs_subrequest_slab); +	mempool_exit(&netfs_request_pool); +	kmem_cache_destroy(netfs_request_slab);  }  module_exit(netfs_exit);  |