Loading include/linux/sunrpc/cache.h +13 −0 Original line number Diff line number Diff line Loading @@ -64,6 +64,10 @@ struct cache_detail_procfs { struct proc_dir_entry *flush_ent, *channel_ent, *content_ent; }; struct cache_detail_pipefs { struct dentry *dir; }; struct cache_detail { struct module * owner; int hash_size; Loading Loading @@ -110,6 +114,7 @@ struct cache_detail { union { struct cache_detail_procfs procfs; struct cache_detail_pipefs pipefs; } u; }; Loading @@ -135,6 +140,10 @@ struct cache_deferred_req { }; extern const struct file_operations cache_file_operations_pipefs; extern const struct file_operations content_file_operations_pipefs; extern const struct file_operations cache_flush_operations_pipefs; extern struct cache_head * sunrpc_cache_lookup(struct cache_detail *detail, struct cache_head *key, int hash); Loading Loading @@ -186,6 +195,10 @@ extern void cache_purge(struct cache_detail *detail); extern int cache_register(struct cache_detail *cd); extern void cache_unregister(struct cache_detail *cd); extern int sunrpc_cache_register_pipefs(struct dentry *parent, const char *, mode_t, struct cache_detail *); extern void sunrpc_cache_unregister_pipefs(struct cache_detail *); extern void qword_add(char **bpp, int *lp, char *str); extern void qword_addhex(char **bpp, int *lp, char *buf, int blen); extern int qword_get(char **bpp, char *dest, int bufsize); Loading include/linux/sunrpc/rpc_pipe_fs.h +8 −0 Original line number Diff line number Diff line Loading @@ -47,6 +47,14 @@ extern int rpc_queue_upcall(struct inode *, struct rpc_pipe_msg *); struct rpc_clnt; extern struct dentry *rpc_create_client_dir(struct dentry *, struct qstr *, struct rpc_clnt *); extern int rpc_remove_client_dir(struct dentry *); struct cache_detail; extern struct dentry *rpc_create_cache_dir(struct dentry *, struct qstr *, mode_t umode, struct cache_detail *); extern void rpc_remove_cache_dir(struct dentry *); extern struct dentry *rpc_mkpipe(struct dentry *, const char *, void *, const struct rpc_pipe_ops *, int flags); extern int rpc_unlink(struct dentry *); Loading net/sunrpc/cache.c +126 −0 Original line number Diff line number Diff line Loading @@ -32,6 +32,7 @@ #include <linux/sunrpc/types.h> #include <linux/sunrpc/cache.h> #include <linux/sunrpc/stats.h> #include <linux/sunrpc/rpc_pipe_fs.h> #define RPCDBG_FACILITY RPCDBG_CACHE Loading Loading @@ -1438,3 +1439,128 @@ void cache_unregister(struct cache_detail *cd) sunrpc_destroy_cache_detail(cd); } EXPORT_SYMBOL_GPL(cache_unregister); static ssize_t cache_read_pipefs(struct file *filp, char __user *buf, size_t count, loff_t *ppos) { struct cache_detail *cd = RPC_I(filp->f_path.dentry->d_inode)->private; return cache_read(filp, buf, count, ppos, cd); } static ssize_t cache_write_pipefs(struct file *filp, const char __user *buf, size_t count, loff_t *ppos) { struct cache_detail *cd = RPC_I(filp->f_path.dentry->d_inode)->private; return cache_write(filp, buf, count, ppos, cd); } static unsigned int cache_poll_pipefs(struct file *filp, poll_table *wait) { struct cache_detail *cd = RPC_I(filp->f_path.dentry->d_inode)->private; return cache_poll(filp, wait, cd); } static int cache_ioctl_pipefs(struct inode *inode, struct file *filp, unsigned int cmd, unsigned long arg) { struct cache_detail *cd = RPC_I(inode)->private; return cache_ioctl(inode, filp, cmd, arg, cd); } static int cache_open_pipefs(struct inode *inode, struct file *filp) { struct cache_detail *cd = RPC_I(inode)->private; return cache_open(inode, filp, cd); } static int cache_release_pipefs(struct inode *inode, struct file *filp) { struct cache_detail *cd = RPC_I(inode)->private; return cache_release(inode, filp, cd); } const struct file_operations cache_file_operations_pipefs = { .owner = THIS_MODULE, .llseek = no_llseek, .read = cache_read_pipefs, .write = cache_write_pipefs, .poll = cache_poll_pipefs, .ioctl = cache_ioctl_pipefs, /* for FIONREAD */ .open = cache_open_pipefs, .release = cache_release_pipefs, }; static int content_open_pipefs(struct inode *inode, struct file *filp) { struct cache_detail *cd = RPC_I(inode)->private; return content_open(inode, filp, cd); } const struct file_operations content_file_operations_pipefs = { .open = content_open_pipefs, .read = seq_read, .llseek = seq_lseek, .release = seq_release_private, }; static ssize_t read_flush_pipefs(struct file *filp, char __user *buf, size_t count, loff_t *ppos) { struct cache_detail *cd = RPC_I(filp->f_path.dentry->d_inode)->private; return read_flush(filp, buf, count, ppos, cd); } static ssize_t write_flush_pipefs(struct file *filp, const char __user *buf, size_t count, loff_t *ppos) { struct cache_detail *cd = RPC_I(filp->f_path.dentry->d_inode)->private; return write_flush(filp, buf, count, ppos, cd); } const struct file_operations cache_flush_operations_pipefs = { .open = nonseekable_open, .read = read_flush_pipefs, .write = write_flush_pipefs, }; int sunrpc_cache_register_pipefs(struct dentry *parent, const char *name, mode_t umode, struct cache_detail *cd) { struct qstr q; struct dentry *dir; int ret = 0; sunrpc_init_cache_detail(cd); q.name = name; q.len = strlen(name); q.hash = full_name_hash(q.name, q.len); dir = rpc_create_cache_dir(parent, &q, umode, cd); if (!IS_ERR(dir)) cd->u.pipefs.dir = dir; else { sunrpc_destroy_cache_detail(cd); ret = PTR_ERR(dir); } return ret; } EXPORT_SYMBOL_GPL(sunrpc_cache_register_pipefs); void sunrpc_cache_unregister_pipefs(struct cache_detail *cd) { rpc_remove_cache_dir(cd->u.pipefs.dir); cd->u.pipefs.dir = NULL; sunrpc_destroy_cache_detail(cd); } EXPORT_SYMBOL_GPL(sunrpc_cache_unregister_pipefs); net/sunrpc/rpc_pipe.c +43 −0 Original line number Diff line number Diff line Loading @@ -26,6 +26,7 @@ #include <linux/sunrpc/clnt.h> #include <linux/workqueue.h> #include <linux/sunrpc/rpc_pipe_fs.h> #include <linux/sunrpc/cache.h> static struct vfsmount *rpc_mount __read_mostly; static int rpc_mount_count; Loading Loading @@ -882,6 +883,48 @@ int rpc_remove_client_dir(struct dentry *dentry) return rpc_rmdir_depopulate(dentry, rpc_clntdir_depopulate); } static const struct rpc_filelist cache_pipefs_files[3] = { [0] = { .name = "channel", .i_fop = &cache_file_operations_pipefs, .mode = S_IFIFO|S_IRUSR|S_IWUSR, }, [1] = { .name = "content", .i_fop = &content_file_operations_pipefs, .mode = S_IFREG|S_IRUSR, }, [2] = { .name = "flush", .i_fop = &cache_flush_operations_pipefs, .mode = S_IFREG|S_IRUSR|S_IWUSR, }, }; static int rpc_cachedir_populate(struct dentry *dentry, void *private) { return rpc_populate(dentry, cache_pipefs_files, 0, 3, private); } static void rpc_cachedir_depopulate(struct dentry *dentry) { rpc_depopulate(dentry, cache_pipefs_files, 0, 3); } struct dentry *rpc_create_cache_dir(struct dentry *parent, struct qstr *name, mode_t umode, struct cache_detail *cd) { return rpc_mkdir_populate(parent, name, umode, NULL, rpc_cachedir_populate, cd); } void rpc_remove_cache_dir(struct dentry *dentry) { rpc_rmdir_depopulate(dentry, rpc_cachedir_depopulate); } /* * populate the filesystem */ Loading Loading
include/linux/sunrpc/cache.h +13 −0 Original line number Diff line number Diff line Loading @@ -64,6 +64,10 @@ struct cache_detail_procfs { struct proc_dir_entry *flush_ent, *channel_ent, *content_ent; }; struct cache_detail_pipefs { struct dentry *dir; }; struct cache_detail { struct module * owner; int hash_size; Loading Loading @@ -110,6 +114,7 @@ struct cache_detail { union { struct cache_detail_procfs procfs; struct cache_detail_pipefs pipefs; } u; }; Loading @@ -135,6 +140,10 @@ struct cache_deferred_req { }; extern const struct file_operations cache_file_operations_pipefs; extern const struct file_operations content_file_operations_pipefs; extern const struct file_operations cache_flush_operations_pipefs; extern struct cache_head * sunrpc_cache_lookup(struct cache_detail *detail, struct cache_head *key, int hash); Loading Loading @@ -186,6 +195,10 @@ extern void cache_purge(struct cache_detail *detail); extern int cache_register(struct cache_detail *cd); extern void cache_unregister(struct cache_detail *cd); extern int sunrpc_cache_register_pipefs(struct dentry *parent, const char *, mode_t, struct cache_detail *); extern void sunrpc_cache_unregister_pipefs(struct cache_detail *); extern void qword_add(char **bpp, int *lp, char *str); extern void qword_addhex(char **bpp, int *lp, char *buf, int blen); extern int qword_get(char **bpp, char *dest, int bufsize); Loading
include/linux/sunrpc/rpc_pipe_fs.h +8 −0 Original line number Diff line number Diff line Loading @@ -47,6 +47,14 @@ extern int rpc_queue_upcall(struct inode *, struct rpc_pipe_msg *); struct rpc_clnt; extern struct dentry *rpc_create_client_dir(struct dentry *, struct qstr *, struct rpc_clnt *); extern int rpc_remove_client_dir(struct dentry *); struct cache_detail; extern struct dentry *rpc_create_cache_dir(struct dentry *, struct qstr *, mode_t umode, struct cache_detail *); extern void rpc_remove_cache_dir(struct dentry *); extern struct dentry *rpc_mkpipe(struct dentry *, const char *, void *, const struct rpc_pipe_ops *, int flags); extern int rpc_unlink(struct dentry *); Loading
net/sunrpc/cache.c +126 −0 Original line number Diff line number Diff line Loading @@ -32,6 +32,7 @@ #include <linux/sunrpc/types.h> #include <linux/sunrpc/cache.h> #include <linux/sunrpc/stats.h> #include <linux/sunrpc/rpc_pipe_fs.h> #define RPCDBG_FACILITY RPCDBG_CACHE Loading Loading @@ -1438,3 +1439,128 @@ void cache_unregister(struct cache_detail *cd) sunrpc_destroy_cache_detail(cd); } EXPORT_SYMBOL_GPL(cache_unregister); static ssize_t cache_read_pipefs(struct file *filp, char __user *buf, size_t count, loff_t *ppos) { struct cache_detail *cd = RPC_I(filp->f_path.dentry->d_inode)->private; return cache_read(filp, buf, count, ppos, cd); } static ssize_t cache_write_pipefs(struct file *filp, const char __user *buf, size_t count, loff_t *ppos) { struct cache_detail *cd = RPC_I(filp->f_path.dentry->d_inode)->private; return cache_write(filp, buf, count, ppos, cd); } static unsigned int cache_poll_pipefs(struct file *filp, poll_table *wait) { struct cache_detail *cd = RPC_I(filp->f_path.dentry->d_inode)->private; return cache_poll(filp, wait, cd); } static int cache_ioctl_pipefs(struct inode *inode, struct file *filp, unsigned int cmd, unsigned long arg) { struct cache_detail *cd = RPC_I(inode)->private; return cache_ioctl(inode, filp, cmd, arg, cd); } static int cache_open_pipefs(struct inode *inode, struct file *filp) { struct cache_detail *cd = RPC_I(inode)->private; return cache_open(inode, filp, cd); } static int cache_release_pipefs(struct inode *inode, struct file *filp) { struct cache_detail *cd = RPC_I(inode)->private; return cache_release(inode, filp, cd); } const struct file_operations cache_file_operations_pipefs = { .owner = THIS_MODULE, .llseek = no_llseek, .read = cache_read_pipefs, .write = cache_write_pipefs, .poll = cache_poll_pipefs, .ioctl = cache_ioctl_pipefs, /* for FIONREAD */ .open = cache_open_pipefs, .release = cache_release_pipefs, }; static int content_open_pipefs(struct inode *inode, struct file *filp) { struct cache_detail *cd = RPC_I(inode)->private; return content_open(inode, filp, cd); } const struct file_operations content_file_operations_pipefs = { .open = content_open_pipefs, .read = seq_read, .llseek = seq_lseek, .release = seq_release_private, }; static ssize_t read_flush_pipefs(struct file *filp, char __user *buf, size_t count, loff_t *ppos) { struct cache_detail *cd = RPC_I(filp->f_path.dentry->d_inode)->private; return read_flush(filp, buf, count, ppos, cd); } static ssize_t write_flush_pipefs(struct file *filp, const char __user *buf, size_t count, loff_t *ppos) { struct cache_detail *cd = RPC_I(filp->f_path.dentry->d_inode)->private; return write_flush(filp, buf, count, ppos, cd); } const struct file_operations cache_flush_operations_pipefs = { .open = nonseekable_open, .read = read_flush_pipefs, .write = write_flush_pipefs, }; int sunrpc_cache_register_pipefs(struct dentry *parent, const char *name, mode_t umode, struct cache_detail *cd) { struct qstr q; struct dentry *dir; int ret = 0; sunrpc_init_cache_detail(cd); q.name = name; q.len = strlen(name); q.hash = full_name_hash(q.name, q.len); dir = rpc_create_cache_dir(parent, &q, umode, cd); if (!IS_ERR(dir)) cd->u.pipefs.dir = dir; else { sunrpc_destroy_cache_detail(cd); ret = PTR_ERR(dir); } return ret; } EXPORT_SYMBOL_GPL(sunrpc_cache_register_pipefs); void sunrpc_cache_unregister_pipefs(struct cache_detail *cd) { rpc_remove_cache_dir(cd->u.pipefs.dir); cd->u.pipefs.dir = NULL; sunrpc_destroy_cache_detail(cd); } EXPORT_SYMBOL_GPL(sunrpc_cache_unregister_pipefs);
net/sunrpc/rpc_pipe.c +43 −0 Original line number Diff line number Diff line Loading @@ -26,6 +26,7 @@ #include <linux/sunrpc/clnt.h> #include <linux/workqueue.h> #include <linux/sunrpc/rpc_pipe_fs.h> #include <linux/sunrpc/cache.h> static struct vfsmount *rpc_mount __read_mostly; static int rpc_mount_count; Loading Loading @@ -882,6 +883,48 @@ int rpc_remove_client_dir(struct dentry *dentry) return rpc_rmdir_depopulate(dentry, rpc_clntdir_depopulate); } static const struct rpc_filelist cache_pipefs_files[3] = { [0] = { .name = "channel", .i_fop = &cache_file_operations_pipefs, .mode = S_IFIFO|S_IRUSR|S_IWUSR, }, [1] = { .name = "content", .i_fop = &content_file_operations_pipefs, .mode = S_IFREG|S_IRUSR, }, [2] = { .name = "flush", .i_fop = &cache_flush_operations_pipefs, .mode = S_IFREG|S_IRUSR|S_IWUSR, }, }; static int rpc_cachedir_populate(struct dentry *dentry, void *private) { return rpc_populate(dentry, cache_pipefs_files, 0, 3, private); } static void rpc_cachedir_depopulate(struct dentry *dentry) { rpc_depopulate(dentry, cache_pipefs_files, 0, 3); } struct dentry *rpc_create_cache_dir(struct dentry *parent, struct qstr *name, mode_t umode, struct cache_detail *cd) { return rpc_mkdir_populate(parent, name, umode, NULL, rpc_cachedir_populate, cd); } void rpc_remove_cache_dir(struct dentry *dentry) { rpc_rmdir_depopulate(dentry, rpc_cachedir_depopulate); } /* * populate the filesystem */ Loading