Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit ead13aee authored by Linus Torvalds's avatar Linus Torvalds
Browse files
Pull NFS client updates from Trond Myklebust:
 "Highlights include:

  Stable fixes:
   - fix an uninitialised pointer Oops in the writeback error path
   - fix a bogus warning (and early exit from the loop) in nfs_generic_pgio()

  Features:
   - Add NFSv4.2 SEEK feature and client support for lseek(SEEK_HOLE/SEEK_DATA)

  Other fixes:
   - pnfs: replace broken pnfs_put_lseg_async
   - Remove dead prototype for nfs4_insert_deviceid_node"

* tag 'nfs-for-3.18-2' of git://git.linux-nfs.org/projects/trondmy/linux-nfs:
  NFS: Fix a bogus warning in nfs_generic_pgio
  NFS: Fix an uninitialised pointer Oops in the writeback error path
  NFSv4.1/pnfs: replace broken pnfs_put_lseg_async
  NFSv4: Remove dead prototype for nfs4_insert_deviceid_node()
  NFS: Implement SEEK
parents 929254d8 b8fb9c30
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -28,6 +28,7 @@ nfsv4-y := nfs4proc.o nfs4xdr.o nfs4state.o nfs4renewd.o nfs4super.o nfs4file.o
nfsv4-$(CONFIG_NFS_USE_LEGACY_DNS) += cache_lib.o
nfsv4-$(CONFIG_SYSCTL)	+= nfs4sysctl.o
nfsv4-$(CONFIG_NFS_V4_1)	+= pnfs.o pnfs_dev.o
nfsv4-$(CONFIG_NFS_V4_2)	+= nfs42proc.o

obj-$(CONFIG_PNFS_FILE_LAYOUT) += filelayout/
obj-$(CONFIG_PNFS_OBJLAYOUT) += objlayout/
+1 −1
Original line number Diff line number Diff line
@@ -1031,7 +1031,7 @@ filelayout_clear_request_commit(struct nfs_page *req,
	}
out:
	nfs_request_remove_commit_list(req, cinfo);
	pnfs_put_lseg_async(freeme);
	pnfs_put_lseg_locked(freeme);
}

static void
+2 −0
Original line number Diff line number Diff line
@@ -718,6 +718,7 @@ struct nfs_lock_context *nfs_get_lock_context(struct nfs_open_context *ctx)
	kfree(new);
	return res;
}
EXPORT_SYMBOL_GPL(nfs_get_lock_context);

void nfs_put_lock_context(struct nfs_lock_context *l_ctx)
{
@@ -730,6 +731,7 @@ void nfs_put_lock_context(struct nfs_lock_context *l_ctx)
	spin_unlock(&inode->i_lock);
	kfree(l_ctx);
}
EXPORT_SYMBOL_GPL(nfs_put_lock_context);

/**
 * nfs_close_context - Common close_context() routine NFSv2/v3

fs/nfs/nfs42.h

0 → 100644
+14 −0
Original line number Diff line number Diff line
/*
 * Copyright (c) 2014 Anna Schumaker <Anna.Schumaker@Netapp.com>
 */

#ifndef __LINUX_FS_NFS_NFS4_2_H
#define __LINUX_FS_NFS_NFS4_2_H

/* nfs4.2proc.c */
loff_t nfs42_proc_llseek(struct file *, loff_t, int);

/* nfs4.2xdr.h */
extern struct rpc_procinfo nfs4_2_procedures[];

#endif /* __LINUX_FS_NFS_NFS4_2_H */

fs/nfs/nfs42proc.c

0 → 100644
+69 −0
Original line number Diff line number Diff line
/*
 * Copyright (c) 2014 Anna Schumaker <Anna.Schumaker@Netapp.com>
 */
#include <linux/fs.h>
#include <linux/sunrpc/sched.h>
#include <linux/nfs.h>
#include <linux/nfs3.h>
#include <linux/nfs4.h>
#include <linux/nfs_xdr.h>
#include <linux/nfs_fs.h>
#include "nfs4_fs.h"
#include "nfs42.h"

static int nfs42_set_rw_stateid(nfs4_stateid *dst, struct file *file,
				fmode_t fmode)
{
	struct nfs_open_context *open;
	struct nfs_lock_context *lock;
	int ret;

	open = get_nfs_open_context(nfs_file_open_context(file));
	lock = nfs_get_lock_context(open);
	if (IS_ERR(lock)) {
		put_nfs_open_context(open);
		return PTR_ERR(lock);
	}

	ret = nfs4_set_rw_stateid(dst, open, lock, fmode);

	nfs_put_lock_context(lock);
	put_nfs_open_context(open);
	return ret;
}

loff_t nfs42_proc_llseek(struct file *filep, loff_t offset, int whence)
{
	struct inode *inode = file_inode(filep);
	struct nfs42_seek_args args = {
		.sa_fh		= NFS_FH(inode),
		.sa_offset	= offset,
		.sa_what	= (whence == SEEK_HOLE) ?
					NFS4_CONTENT_HOLE : NFS4_CONTENT_DATA,
	};
	struct nfs42_seek_res res;
	struct rpc_message msg = {
		.rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_SEEK],
		.rpc_argp = &args,
		.rpc_resp = &res,
	};
	struct nfs_server *server = NFS_SERVER(inode);
	int status;

	if (!(server->caps & NFS_CAP_SEEK))
		return -ENOTSUPP;

	status = nfs42_set_rw_stateid(&args.sa_stateid, filep, FMODE_READ);
	if (status)
		return status;

	nfs_wb_all(inode);
	status = nfs4_call_sync(server->client, server, &msg,
				&args.seq_args, &res.seq_res, 0);
	if (status == -ENOTSUPP)
		server->caps &= ~NFS_CAP_SEEK;
	if (status)
		return status;

	return vfs_setpos(filep, res.sr_offset, inode->i_sb->s_maxbytes);
}
Loading