diff options
Diffstat (limited to 'fs/nfsd/nfsproc.c')
| -rw-r--r-- | fs/nfsd/nfsproc.c | 27 | 
1 files changed, 14 insertions, 13 deletions
diff --git a/fs/nfsd/nfsproc.c b/fs/nfsd/nfsproc.c index 08e17264784..54c6b3d3cc7 100644 --- a/fs/nfsd/nfsproc.c +++ b/fs/nfsd/nfsproc.c @@ -26,17 +26,13 @@ static __be32  nfsd_return_attrs(__be32 err, struct nfsd_attrstat *resp)  {  	if (err) return err; -	return nfserrno(vfs_getattr(resp->fh.fh_export->ex_path.mnt, -				    resp->fh.fh_dentry, -				    &resp->stat)); +	return fh_getattr(&resp->fh, &resp->stat);  }  static __be32  nfsd_return_dirop(__be32 err, struct nfsd_diropres *resp)  {  	if (err) return err; -	return nfserrno(vfs_getattr(resp->fh.fh_export->ex_path.mnt, -				    resp->fh.fh_dentry, -				    &resp->stat)); +	return fh_getattr(&resp->fh, &resp->stat);  }  /*   * Get a file's attributes @@ -150,9 +146,7 @@ nfsd_proc_read(struct svc_rqst *rqstp, struct nfsd_readargs *argp,  				  &resp->count);  	if (nfserr) return nfserr; -	return nfserrno(vfs_getattr(resp->fh.fh_export->ex_path.mnt, -				    resp->fh.fh_dentry, -				    &resp->stat)); +	return fh_getattr(&resp->fh, &resp->stat);  }  /* @@ -196,6 +190,7 @@ nfsd_proc_create(struct svc_rqst *rqstp, struct nfsd_createargs *argp,  	struct dentry	*dchild;  	int		type, mode;  	__be32		nfserr; +	int		hosterr;  	dev_t		rdev = 0, wanted = new_decode_dev(attr->ia_size);  	dprintk("nfsd: CREATE   %s %.*s\n", @@ -214,6 +209,12 @@ nfsd_proc_create(struct svc_rqst *rqstp, struct nfsd_createargs *argp,  	nfserr = nfserr_exist;  	if (isdotent(argp->name, argp->len))  		goto done; +	hosterr = fh_want_write(dirfhp); +	if (hosterr) { +		nfserr = nfserrno(hosterr); +		goto done; +	} +  	fh_lock_nested(dirfhp, I_MUTEX_PARENT);  	dchild = lookup_one_len(argp->name, dirfhp->fh_dentry, argp->len);  	if (IS_ERR(dchild)) { @@ -330,7 +331,7 @@ nfsd_proc_create(struct svc_rqst *rqstp, struct nfsd_createargs *argp,  out_unlock:  	/* We don't really need to unlock, as fh_put does it. */  	fh_unlock(dirfhp); - +	fh_drop_write(dirfhp);  done:  	fh_put(dirfhp);  	return nfsd_return_dirop(nfserr, resp); @@ -735,9 +736,9 @@ nfserrno (int errno)  		{ nfserr_stale, -ESTALE },  		{ nfserr_jukebox, -ETIMEDOUT },  		{ nfserr_jukebox, -ERESTARTSYS }, -		{ nfserr_dropit, -EAGAIN }, -		{ nfserr_dropit, -ENOMEM }, -		{ nfserr_badname, -ESRCH }, +		{ nfserr_jukebox, -EAGAIN }, +		{ nfserr_jukebox, -EWOULDBLOCK }, +		{ nfserr_jukebox, -ENOMEM },  		{ nfserr_io, -ETXTBSY },  		{ nfserr_notsupp, -EOPNOTSUPP },  		{ nfserr_toosmall, -ETOOSMALL },  | 
