From 3c7aa15d2073d81e56e8ba8771a4ab6f23be7ae2 Mon Sep 17 00:00:00 2001 From: Kinglong Mee Date: Tue, 10 Jun 2014 18:08:19 +0800 Subject: NFSD: Using min/max/min_t/max_t for calculate Signed-off-by: Kinglong Mee Signed-off-by: J. Bruce Fields --- fs/nfsd/vfs.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) (limited to 'fs/nfsd/vfs.c') diff --git a/fs/nfsd/vfs.c b/fs/nfsd/vfs.c index 140c496f612c..7498099b382f 100644 --- a/fs/nfsd/vfs.c +++ b/fs/nfsd/vfs.c @@ -2093,8 +2093,7 @@ nfsd_racache_init(int cache_size) if (raparm_hash[0].pb_head) return 0; nperbucket = DIV_ROUND_UP(cache_size, RAPARM_HASH_SIZE); - if (nperbucket < 2) - nperbucket = 2; + nperbucket = max(2, nperbucket); cache_size = nperbucket * RAPARM_HASH_SIZE; dprintk("nfsd: allocating %d readahead buffers.\n", cache_size); -- cgit v1.2.3 From bf18f163e89c52e09c96534db45c4274273a0b34 Mon Sep 17 00:00:00 2001 From: Kinglong Mee Date: Tue, 10 Jun 2014 22:06:44 +0800 Subject: NFSD: Using exp_get for export getting Don't using cache_get besides export.h, using exp_get for export. Signed-off-by: Kinglong Mee Signed-off-by: J. Bruce Fields --- fs/nfsd/export.c | 2 +- fs/nfsd/export.h | 3 ++- fs/nfsd/nfs4proc.c | 6 +++--- fs/nfsd/nfsfh.c | 3 +-- fs/nfsd/vfs.c | 3 +-- 5 files changed, 8 insertions(+), 9 deletions(-) (limited to 'fs/nfsd/vfs.c') diff --git a/fs/nfsd/export.c b/fs/nfsd/export.c index ef2d9d62ce2b..72ffd7cce3c3 100644 --- a/fs/nfsd/export.c +++ b/fs/nfsd/export.c @@ -1253,7 +1253,7 @@ static int e_show(struct seq_file *m, void *p) return 0; } - cache_get(&exp->h); + exp_get(exp); if (cache_check(cd, &exp->h, NULL)) return 0; exp_put(exp); diff --git a/fs/nfsd/export.h b/fs/nfsd/export.h index cfeea85c5bed..04dc8c167b0c 100644 --- a/fs/nfsd/export.h +++ b/fs/nfsd/export.h @@ -101,9 +101,10 @@ static inline void exp_put(struct svc_export *exp) cache_put(&exp->h, exp->cd); } -static inline void exp_get(struct svc_export *exp) +static inline struct svc_export *exp_get(struct svc_export *exp) { cache_get(&exp->h); + return exp; } struct svc_export * rqst_exp_find(struct svc_rqst *, int, u32 *); diff --git a/fs/nfsd/nfs4proc.c b/fs/nfsd/nfs4proc.c index be6734060d2a..f3f048724ac7 100644 --- a/fs/nfsd/nfs4proc.c +++ b/fs/nfsd/nfs4proc.c @@ -177,7 +177,7 @@ fh_dup2(struct svc_fh *dst, struct svc_fh *src) fh_put(dst); dget(src->fh_dentry); if (src->fh_export) - cache_get(&src->fh_export->h); + exp_get(src->fh_export); *dst = *src; } @@ -918,8 +918,8 @@ nfsd4_secinfo_no_name(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstat default: return nfserr_inval; } - exp_get(cstate->current_fh.fh_export); - sin->sin_exp = cstate->current_fh.fh_export; + + sin->sin_exp = exp_get(cstate->current_fh.fh_export); fh_put(&cstate->current_fh); return nfs_ok; } diff --git a/fs/nfsd/nfsfh.c b/fs/nfsd/nfsfh.c index ec8393418154..6f5cc76a6c6e 100644 --- a/fs/nfsd/nfsfh.c +++ b/fs/nfsd/nfsfh.c @@ -539,8 +539,7 @@ fh_compose(struct svc_fh *fhp, struct svc_export *exp, struct dentry *dentry, dentry); fhp->fh_dentry = dget(dentry); /* our internal copy */ - fhp->fh_export = exp; - cache_get(&exp->h); + fhp->fh_export = exp_get(exp); if (fhp->fh_handle.fh_version == 0xca) { /* old style filehandle please */ diff --git a/fs/nfsd/vfs.c b/fs/nfsd/vfs.c index 7498099b382f..df7cf61f2cd3 100644 --- a/fs/nfsd/vfs.c +++ b/fs/nfsd/vfs.c @@ -189,8 +189,7 @@ nfsd_lookup_dentry(struct svc_rqst *rqstp, struct svc_fh *fhp, dprintk("nfsd: nfsd_lookup(fh %s, %.*s)\n", SVCFH_fmt(fhp), len,name); dparent = fhp->fh_dentry; - exp = fhp->fh_export; - exp_get(exp); + exp = exp_get(fhp->fh_export); /* Lookup the name, but don't follow links */ if (isdotent(name, len)) { -- cgit v1.2.3 From e2afc81919400505481a985fb389475707195c3c Mon Sep 17 00:00:00 2001 From: Jeff Layton Date: Tue, 17 Jun 2014 07:44:13 -0400 Subject: nfsd: nfsd_splice_read and nfsd_readv should return __be32 The callers expect a __be32 return and the functions they call return __be32, so having these return int is just wrong. Also, nfsd_finish_read can be made static. Signed-off-by: Jeff Layton Reviewed-by: Christoph Hellwig Signed-off-by: J. Bruce Fields --- fs/nfsd/vfs.c | 7 ++++--- fs/nfsd/vfs.h | 4 ++-- 2 files changed, 6 insertions(+), 5 deletions(-) (limited to 'fs/nfsd/vfs.c') diff --git a/fs/nfsd/vfs.c b/fs/nfsd/vfs.c index df7cf61f2cd3..6ffaa70300ed 100644 --- a/fs/nfsd/vfs.c +++ b/fs/nfsd/vfs.c @@ -819,7 +819,8 @@ static int nfsd_direct_splice_actor(struct pipe_inode_info *pipe, return __splice_from_pipe(pipe, sd, nfsd_splice_actor); } -__be32 nfsd_finish_read(struct file *file, unsigned long *count, int host_err) +static __be32 +nfsd_finish_read(struct file *file, unsigned long *count, int host_err) { if (host_err >= 0) { nfsdstats.io_read += host_err; @@ -830,7 +831,7 @@ __be32 nfsd_finish_read(struct file *file, unsigned long *count, int host_err) return nfserrno(host_err); } -int nfsd_splice_read(struct svc_rqst *rqstp, +__be32 nfsd_splice_read(struct svc_rqst *rqstp, struct file *file, loff_t offset, unsigned long *count) { struct splice_desc sd = { @@ -846,7 +847,7 @@ int nfsd_splice_read(struct svc_rqst *rqstp, return nfsd_finish_read(file, count, host_err); } -int nfsd_readv(struct file *file, loff_t offset, struct kvec *vec, int vlen, +__be32 nfsd_readv(struct file *file, loff_t offset, struct kvec *vec, int vlen, unsigned long *count) { mm_segment_t oldfs; diff --git a/fs/nfsd/vfs.h b/fs/nfsd/vfs.h index 91b6ae3f658b..b84aef50f55d 100644 --- a/fs/nfsd/vfs.h +++ b/fs/nfsd/vfs.h @@ -74,9 +74,9 @@ struct raparms; __be32 nfsd_get_tmp_read_open(struct svc_rqst *, struct svc_fh *, struct file **, struct raparms **); void nfsd_put_tmp_read_open(struct file *, struct raparms *); -int nfsd_splice_read(struct svc_rqst *, +__be32 nfsd_splice_read(struct svc_rqst *, struct file *, loff_t, unsigned long *); -int nfsd_readv(struct file *, loff_t, struct kvec *, int, +__be32 nfsd_readv(struct file *, loff_t, struct kvec *, int, unsigned long *); __be32 nfsd_read(struct svc_rqst *, struct svc_fh *, loff_t, struct kvec *, int, unsigned long *); -- cgit v1.2.3 From 52ee04330f585d1b5bc40442f07df07248fa3aee Mon Sep 17 00:00:00 2001 From: "J. Bruce Fields" Date: Fri, 20 Jun 2014 11:52:21 -0400 Subject: nfsd: let nfsd_symlink assume null-terminated data Currently nfsd_symlink has a weird hack to serve callers who don't null-terminate symlink data: it looks ahead at the next byte to see if it's zero, and copies it to a new buffer to null-terminate if not. That means callers don't have to null-terminate, but they *do* have to ensure that the byte following the end of the data is theirs to read. That's a bit subtle, and the NFSv4 code actually got this wrong. So let's just throw out that code and let callers pass null-terminated strings; we've already fixed them to do that. Signed-off-by: J. Bruce Fields --- fs/nfsd/nfs3proc.c | 2 +- fs/nfsd/nfs4proc.c | 2 +- fs/nfsd/nfsproc.c | 2 +- fs/nfsd/vfs.c | 17 +++-------------- fs/nfsd/vfs.h | 2 +- 5 files changed, 7 insertions(+), 18 deletions(-) (limited to 'fs/nfsd/vfs.c') diff --git a/fs/nfsd/nfs3proc.c b/fs/nfsd/nfs3proc.c index 61ef42c7b0a6..19ba233cf006 100644 --- a/fs/nfsd/nfs3proc.c +++ b/fs/nfsd/nfs3proc.c @@ -282,7 +282,7 @@ nfsd3_proc_symlink(struct svc_rqst *rqstp, struct nfsd3_symlinkargs *argp, fh_copy(&resp->dirfh, &argp->ffh); fh_init(&resp->fh, NFS3_FHSIZE); nfserr = nfsd_symlink(rqstp, &resp->dirfh, argp->fname, argp->flen, - argp->tname, argp->tlen, + argp->tname, &resp->fh, &argp->attrs); RETURN_STATUS(nfserr); } diff --git a/fs/nfsd/nfs4proc.c b/fs/nfsd/nfs4proc.c index 2b3795a135e8..7aa83bf34fa9 100644 --- a/fs/nfsd/nfs4proc.c +++ b/fs/nfsd/nfs4proc.c @@ -623,7 +623,7 @@ nfsd4_create(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, case NF4LNK: status = nfsd_symlink(rqstp, &cstate->current_fh, create->cr_name, create->cr_namelen, - create->cr_linkname, create->cr_linklen, + create->cr_linkname, &resfh, &create->cr_iattr); break; diff --git a/fs/nfsd/nfsproc.c b/fs/nfsd/nfsproc.c index aebe23c45cbe..583ed03877e4 100644 --- a/fs/nfsd/nfsproc.c +++ b/fs/nfsd/nfsproc.c @@ -409,7 +409,7 @@ nfsd_proc_symlink(struct svc_rqst *rqstp, struct nfsd_symlinkargs *argp, */ argp->tname[argp->tlen] = '\0'; nfserr = nfsd_symlink(rqstp, &argp->ffh, argp->fname, argp->flen, - argp->tname, argp->tlen, + argp->tname, &newfh, &argp->attrs); diff --git a/fs/nfsd/vfs.c b/fs/nfsd/vfs.c index 6ffaa70300ed..7518c65f9a5a 100644 --- a/fs/nfsd/vfs.c +++ b/fs/nfsd/vfs.c @@ -1504,7 +1504,7 @@ out_nfserr: __be32 nfsd_symlink(struct svc_rqst *rqstp, struct svc_fh *fhp, char *fname, int flen, - char *path, int plen, + char *path, struct svc_fh *resfhp, struct iattr *iap) { @@ -1513,7 +1513,7 @@ nfsd_symlink(struct svc_rqst *rqstp, struct svc_fh *fhp, int host_err; err = nfserr_noent; - if (!flen || !plen) + if (!flen || path[0] == '\0') goto out; err = nfserr_exist; if (isdotent(fname, flen)) @@ -1534,18 +1534,7 @@ nfsd_symlink(struct svc_rqst *rqstp, struct svc_fh *fhp, if (IS_ERR(dnew)) goto out_nfserr; - if (unlikely(path[plen] != 0)) { - char *path_alloced = kmalloc(plen+1, GFP_KERNEL); - if (path_alloced == NULL) - host_err = -ENOMEM; - else { - strncpy(path_alloced, path, plen); - path_alloced[plen] = 0; - host_err = vfs_symlink(dentry->d_inode, dnew, path_alloced); - kfree(path_alloced); - } - } else - host_err = vfs_symlink(dentry->d_inode, dnew, path); + host_err = vfs_symlink(dentry->d_inode, dnew, path); err = nfserrno(host_err); if (!err) err = nfserrno(commit_metadata(fhp)); diff --git a/fs/nfsd/vfs.h b/fs/nfsd/vfs.h index b84aef50f55d..20e4b6679e46 100644 --- a/fs/nfsd/vfs.h +++ b/fs/nfsd/vfs.h @@ -85,7 +85,7 @@ __be32 nfsd_write(struct svc_rqst *, struct svc_fh *,struct file *, __be32 nfsd_readlink(struct svc_rqst *, struct svc_fh *, char *, int *); __be32 nfsd_symlink(struct svc_rqst *, struct svc_fh *, - char *name, int len, char *path, int plen, + char *name, int len, char *path, struct svc_fh *res, struct iattr *); __be32 nfsd_link(struct svc_rqst *, struct svc_fh *, char *, int, struct svc_fh *); -- cgit v1.2.3 From 1e444f5bc0c468e244ee601b7acbd87f0b6ee7e2 Mon Sep 17 00:00:00 2001 From: Kinglong Mee Date: Tue, 1 Jul 2014 17:48:02 +0800 Subject: NFSD: Remove iattr parameter from nfsd_symlink() Commit db2e747b1499 (vfs: remove mode parameter from vfs_symlink()) have remove mode parameter from vfs_symlink. So that, iattr isn't needed by nfsd_symlink now, just remove it. Signed-off-by: Kinglong Mee Signed-off-by: J. Bruce Fields --- fs/nfsd/nfs3proc.c | 3 +-- fs/nfsd/nfs4proc.c | 3 +-- fs/nfsd/nfsproc.c | 4 +--- fs/nfsd/vfs.c | 3 +-- fs/nfsd/vfs.h | 2 +- 5 files changed, 5 insertions(+), 10 deletions(-) (limited to 'fs/nfsd/vfs.c') diff --git a/fs/nfsd/nfs3proc.c b/fs/nfsd/nfs3proc.c index 19ba233cf006..fa2525b2e9d7 100644 --- a/fs/nfsd/nfs3proc.c +++ b/fs/nfsd/nfs3proc.c @@ -282,8 +282,7 @@ nfsd3_proc_symlink(struct svc_rqst *rqstp, struct nfsd3_symlinkargs *argp, fh_copy(&resp->dirfh, &argp->ffh); fh_init(&resp->fh, NFS3_FHSIZE); nfserr = nfsd_symlink(rqstp, &resp->dirfh, argp->fname, argp->flen, - argp->tname, - &resp->fh, &argp->attrs); + argp->tname, &resp->fh); RETURN_STATUS(nfserr); } diff --git a/fs/nfsd/nfs4proc.c b/fs/nfsd/nfs4proc.c index b57c8826ce08..9425ffc48809 100644 --- a/fs/nfsd/nfs4proc.c +++ b/fs/nfsd/nfs4proc.c @@ -623,8 +623,7 @@ nfsd4_create(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, case NF4LNK: status = nfsd_symlink(rqstp, &cstate->current_fh, create->cr_name, create->cr_namelen, - create->cr_data, - &resfh, &create->cr_iattr); + create->cr_data, &resfh); break; case NF4BLK: diff --git a/fs/nfsd/nfsproc.c b/fs/nfsd/nfsproc.c index 583ed03877e4..eff49552cdc8 100644 --- a/fs/nfsd/nfsproc.c +++ b/fs/nfsd/nfsproc.c @@ -409,9 +409,7 @@ nfsd_proc_symlink(struct svc_rqst *rqstp, struct nfsd_symlinkargs *argp, */ argp->tname[argp->tlen] = '\0'; nfserr = nfsd_symlink(rqstp, &argp->ffh, argp->fname, argp->flen, - argp->tname, - &newfh, &argp->attrs); - + argp->tname, &newfh); fh_put(&argp->ffh); fh_put(&newfh); diff --git a/fs/nfsd/vfs.c b/fs/nfsd/vfs.c index 7518c65f9a5a..730f31964597 100644 --- a/fs/nfsd/vfs.c +++ b/fs/nfsd/vfs.c @@ -1505,8 +1505,7 @@ __be32 nfsd_symlink(struct svc_rqst *rqstp, struct svc_fh *fhp, char *fname, int flen, char *path, - struct svc_fh *resfhp, - struct iattr *iap) + struct svc_fh *resfhp) { struct dentry *dentry, *dnew; __be32 err, cerr; diff --git a/fs/nfsd/vfs.h b/fs/nfsd/vfs.h index 20e4b6679e46..c2ff3f14e5f6 100644 --- a/fs/nfsd/vfs.h +++ b/fs/nfsd/vfs.h @@ -86,7 +86,7 @@ __be32 nfsd_readlink(struct svc_rqst *, struct svc_fh *, char *, int *); __be32 nfsd_symlink(struct svc_rqst *, struct svc_fh *, char *name, int len, char *path, - struct svc_fh *res, struct iattr *); + struct svc_fh *res); __be32 nfsd_link(struct svc_rqst *, struct svc_fh *, char *, int, struct svc_fh *); __be32 nfsd_rename(struct svc_rqst *, -- cgit v1.2.3 From 0f3a24b43bf75adf67df188a85594a8f43b9ee93 Mon Sep 17 00:00:00 2001 From: Trond Myklebust Date: Tue, 1 Jul 2014 18:27:53 -0400 Subject: nfsd: Ensure that nfsd_create_setattr commits files to stable storage Since nfsd_create_setattr strips the mode from the struct iattr, it is quite possible that it will optimise away the call to nfsd_setattr altogether. If this is the case, then we never call commit_metadata() on the newly created file. Also ensure that both nfsd_setattr() and nfsd_create_setattr() fail when the call to commit_metadata fails. Signed-off-by: Trond Myklebust Signed-off-by: J. Bruce Fields --- fs/nfsd/vfs.c | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) (limited to 'fs/nfsd/vfs.c') diff --git a/fs/nfsd/vfs.c b/fs/nfsd/vfs.c index 730f31964597..e1b792ada45b 100644 --- a/fs/nfsd/vfs.c +++ b/fs/nfsd/vfs.c @@ -463,7 +463,7 @@ out_put_write_access: if (size_change) put_write_access(inode); if (!err) - commit_metadata(fhp); + err = commit_metadata(fhp); out: return err; } @@ -1121,7 +1121,8 @@ nfsd_create_setattr(struct svc_rqst *rqstp, struct svc_fh *resfhp, iap->ia_valid &= ~(ATTR_UID|ATTR_GID); if (iap->ia_valid) return nfsd_setattr(rqstp, resfhp, iap, 0, (time_t)0); - return 0; + /* Callers expect file metadata to be committed here */ + return commit_metadata(resfhp); } /* HPUX client sometimes creates a file in mode 000, and sets size to 0. @@ -1253,9 +1254,10 @@ nfsd_create(struct svc_rqst *rqstp, struct svc_fh *fhp, err = nfsd_create_setattr(rqstp, resfhp, iap); /* - * nfsd_setattr already committed the child. Transactional filesystems - * had a chance to commit changes for both parent and child - * simultaneously making the following commit_metadata a noop. + * nfsd_create_setattr already committed the child. Transactional + * filesystems had a chance to commit changes for both parent and + * child * simultaneously making the following commit_metadata a + * noop. */ err2 = nfserrno(commit_metadata(fhp)); if (err2) @@ -1426,7 +1428,8 @@ do_nfsd_create(struct svc_rqst *rqstp, struct svc_fh *fhp, err = nfsd_create_setattr(rqstp, resfhp, iap); /* - * nfsd_setattr already committed the child (and possibly also the parent). + * nfsd_create_setattr already committed the child + * (and possibly also the parent). */ if (!err) err = nfserrno(commit_metadata(fhp)); -- cgit v1.2.3 From 722b620d1830fce69367b099ef6a83f41a4b9d72 Mon Sep 17 00:00:00 2001 From: Jeff Layton Date: Thu, 3 Jul 2014 07:54:19 -0400 Subject: nfsd: properly convert return from commit_metadata to __be32 Commit 2a7420c03e504 (nfsd: Ensure that nfsd_create_setattr commits files to stable storage), added a couple of calls to commit_metadata, but doesn't convert their return codes to __be32 in the appropriate places. Cc: Trond Myklebust Signed-off-by: Jeff Layton Signed-off-by: J. Bruce Fields --- fs/nfsd/vfs.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'fs/nfsd/vfs.c') diff --git a/fs/nfsd/vfs.c b/fs/nfsd/vfs.c index e1b792ada45b..f501a9b5c9df 100644 --- a/fs/nfsd/vfs.c +++ b/fs/nfsd/vfs.c @@ -463,7 +463,7 @@ out_put_write_access: if (size_change) put_write_access(inode); if (!err) - err = commit_metadata(fhp); + err = nfserrno(commit_metadata(fhp)); out: return err; } @@ -1122,7 +1122,7 @@ nfsd_create_setattr(struct svc_rqst *rqstp, struct svc_fh *resfhp, if (iap->ia_valid) return nfsd_setattr(rqstp, resfhp, iap, 0, (time_t)0); /* Callers expect file metadata to be committed here */ - return commit_metadata(resfhp); + return nfserrno(commit_metadata(resfhp)); } /* HPUX client sometimes creates a file in mode 000, and sets size to 0. -- cgit v1.2.3