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

Commit cf2ec150 authored by Linus Torvalds's avatar Linus Torvalds
Browse files

Merge branch 'for-linus' of git://linux-nfs.org/~bfields/linux

* 'for-linus' of git://linux-nfs.org/~bfields/linux:
  nfsd: don't allow setting ctime over v4
  Update to NFS/RDMA documentation
  locks: don't call ->copy_lock methods on return of conflicting locks
  lockd: unlock lockd locks held for a certain filesystem
  lockd: unlock lockd locks associated with a given server ip
  leases: remove unneeded variable from fcntl_setlease().
  leases: move lock allocation earlier in generic_setlease()
  leases: when unlocking, skip locking-related steps
  leases: fix a return-value mixup
parents 9f4def9a e36cd4a2
Loading
Loading
Loading
Loading
+9 −5
Original line number Original line Diff line number Diff line
@@ -5,7 +5,7 @@
################################################################################
################################################################################


 Author: NetApp and Open Grid Computing
 Author: NetApp and Open Grid Computing
 Date: February 25, 2008
 Date: April 15, 2008


Table of Contents
Table of Contents
~~~~~~~~~~~~~~~~~
~~~~~~~~~~~~~~~~~
@@ -197,12 +197,16 @@ NFS/RDMA Setup
  - On the server system, configure the /etc/exports file and
  - On the server system, configure the /etc/exports file and
    start the NFS/RDMA server.
    start the NFS/RDMA server.


    Exports entries with the following format have been tested:
    Exports entries with the following formats have been tested:


    /vol0   10.97.103.47(rw,async) 192.168.0.47(rw,async,insecure,no_root_squash)
    /vol0   192.168.0.47(fsid=0,rw,async,insecure,no_root_squash)
    /vol0   192.168.0.0/255.255.255.0(fsid=0,rw,async,insecure,no_root_squash)


    Here the first IP address is the client's Ethernet address and the second
    The IP address(es) is(are) the client's IPoIB address for an InfiniBand HCA or the
    IP address is the clients IPoIB address.
    cleint's iWARP address(es) for an RNIC.

    NOTE: The "insecure" option must be used because the NFS/RDMA client does not
    use a reserved port.


 Each time a machine boots:
 Each time a machine boots:


+1 −1
Original line number Original line Diff line number Diff line
@@ -632,7 +632,7 @@ nlmsvc_update_deferred_block(struct nlm_block *block, struct file_lock *conf,
		block->b_flags |= B_TIMED_OUT;
		block->b_flags |= B_TIMED_OUT;
	if (conf) {
	if (conf) {
		if (block->b_fl)
		if (block->b_fl)
			locks_copy_lock(block->b_fl, conf);
			__locks_copy_lock(block->b_fl, conf);
	}
	}
}
}


+61 −8
Original line number Original line Diff line number Diff line
@@ -18,6 +18,8 @@
#include <linux/lockd/lockd.h>
#include <linux/lockd/lockd.h>
#include <linux/lockd/share.h>
#include <linux/lockd/share.h>
#include <linux/lockd/sm_inter.h>
#include <linux/lockd/sm_inter.h>
#include <linux/module.h>
#include <linux/mount.h>


#define NLMDBG_FACILITY		NLMDBG_SVCSUBS
#define NLMDBG_FACILITY		NLMDBG_SVCSUBS


@@ -194,6 +196,12 @@ nlm_traverse_locks(struct nlm_host *host, struct nlm_file *file,
	return 0;
	return 0;
}
}


static int
nlmsvc_always_match(void *dummy1, struct nlm_host *dummy2)
{
	return 1;
}

/*
/*
 * Inspect a single file
 * Inspect a single file
 */
 */
@@ -230,7 +238,8 @@ nlm_file_inuse(struct nlm_file *file)
 * Loop over all files in the file table.
 * Loop over all files in the file table.
 */
 */
static int
static int
nlm_traverse_files(struct nlm_host *host, nlm_host_match_fn_t match)
nlm_traverse_files(void *data, nlm_host_match_fn_t match,
		int (*is_failover_file)(void *data, struct nlm_file *file))
{
{
	struct hlist_node *pos, *next;
	struct hlist_node *pos, *next;
	struct nlm_file	*file;
	struct nlm_file	*file;
@@ -239,12 +248,14 @@ nlm_traverse_files(struct nlm_host *host, nlm_host_match_fn_t match)
	mutex_lock(&nlm_file_mutex);
	mutex_lock(&nlm_file_mutex);
	for (i = 0; i < FILE_NRHASH; i++) {
	for (i = 0; i < FILE_NRHASH; i++) {
		hlist_for_each_entry_safe(file, pos, next, &nlm_files[i], f_list) {
		hlist_for_each_entry_safe(file, pos, next, &nlm_files[i], f_list) {
			if (is_failover_file && !is_failover_file(data, file))
				continue;
			file->f_count++;
			file->f_count++;
			mutex_unlock(&nlm_file_mutex);
			mutex_unlock(&nlm_file_mutex);


			/* Traverse locks, blocks and shares of this file
			/* Traverse locks, blocks and shares of this file
			 * and update file->f_locks count */
			 * and update file->f_locks count */
			if (nlm_inspect_file(host, file, match))
			if (nlm_inspect_file(data, file, match))
				ret = 1;
				ret = 1;


			mutex_lock(&nlm_file_mutex);
			mutex_lock(&nlm_file_mutex);
@@ -303,21 +314,27 @@ nlm_release_file(struct nlm_file *file)
 *	Used by nlmsvc_invalidate_all
 *	Used by nlmsvc_invalidate_all
 */
 */
static int
static int
nlmsvc_mark_host(struct nlm_host *host, struct nlm_host *dummy)
nlmsvc_mark_host(void *data, struct nlm_host *dummy)
{
{
	struct nlm_host *host = data;

	host->h_inuse = 1;
	host->h_inuse = 1;
	return 0;
	return 0;
}
}


static int
static int
nlmsvc_same_host(struct nlm_host *host, struct nlm_host *other)
nlmsvc_same_host(void *data, struct nlm_host *other)
{
{
	struct nlm_host *host = data;

	return host == other;
	return host == other;
}
}


static int
static int
nlmsvc_is_client(struct nlm_host *host, struct nlm_host *dummy)
nlmsvc_is_client(void *data, struct nlm_host *dummy)
{
{
	struct nlm_host *host = data;

	if (host->h_server) {
	if (host->h_server) {
		/* we are destroying locks even though the client
		/* we are destroying locks even though the client
		 * hasn't asked us too, so don't unmonitor the
		 * hasn't asked us too, so don't unmonitor the
@@ -337,7 +354,7 @@ void
nlmsvc_mark_resources(void)
nlmsvc_mark_resources(void)
{
{
	dprintk("lockd: nlmsvc_mark_resources\n");
	dprintk("lockd: nlmsvc_mark_resources\n");
	nlm_traverse_files(NULL, nlmsvc_mark_host);
	nlm_traverse_files(NULL, nlmsvc_mark_host, NULL);
}
}


/*
/*
@@ -348,7 +365,7 @@ nlmsvc_free_host_resources(struct nlm_host *host)
{
{
	dprintk("lockd: nlmsvc_free_host_resources\n");
	dprintk("lockd: nlmsvc_free_host_resources\n");


	if (nlm_traverse_files(host, nlmsvc_same_host)) {
	if (nlm_traverse_files(host, nlmsvc_same_host, NULL)) {
		printk(KERN_WARNING
		printk(KERN_WARNING
			"lockd: couldn't remove all locks held by %s\n",
			"lockd: couldn't remove all locks held by %s\n",
			host->h_name);
			host->h_name);
@@ -368,5 +385,41 @@ nlmsvc_invalidate_all(void)
	 * turn, which is about as inefficient as it gets.
	 * turn, which is about as inefficient as it gets.
	 * Now we just do it once in nlm_traverse_files.
	 * Now we just do it once in nlm_traverse_files.
	 */
	 */
	nlm_traverse_files(NULL, nlmsvc_is_client);
	nlm_traverse_files(NULL, nlmsvc_is_client, NULL);
}

static int
nlmsvc_match_sb(void *datap, struct nlm_file *file)
{
	struct super_block *sb = datap;

	return sb == file->f_file->f_path.mnt->mnt_sb;
}

int
nlmsvc_unlock_all_by_sb(struct super_block *sb)
{
	int ret;

	ret = nlm_traverse_files(sb, nlmsvc_always_match, nlmsvc_match_sb);
	return ret ? -EIO : 0;
}
EXPORT_SYMBOL_GPL(nlmsvc_unlock_all_by_sb);

static int
nlmsvc_match_ip(void *datap, struct nlm_host *host)
{
	__be32 *server_addr = datap;

	return host->h_saddr.sin_addr.s_addr == *server_addr;
}

int
nlmsvc_unlock_all_by_ip(__be32 server_addr)
{
	int ret;
	ret = nlm_traverse_files(&server_addr, nlmsvc_match_ip, NULL);
	return ret ? -EIO : 0;

}
}
EXPORT_SYMBOL_GPL(nlmsvc_unlock_all_by_ip);
+17 −15
Original line number Original line Diff line number Diff line
@@ -224,7 +224,7 @@ static void locks_copy_private(struct file_lock *new, struct file_lock *fl)
/*
/*
 * Initialize a new lock from an existing file_lock structure.
 * Initialize a new lock from an existing file_lock structure.
 */
 */
static void __locks_copy_lock(struct file_lock *new, const struct file_lock *fl)
void __locks_copy_lock(struct file_lock *new, const struct file_lock *fl)
{
{
	new->fl_owner = fl->fl_owner;
	new->fl_owner = fl->fl_owner;
	new->fl_pid = fl->fl_pid;
	new->fl_pid = fl->fl_pid;
@@ -833,7 +833,7 @@ static int __posix_lock_file(struct inode *inode, struct file_lock *request, str
			if (!posix_locks_conflict(request, fl))
			if (!posix_locks_conflict(request, fl))
				continue;
				continue;
			if (conflock)
			if (conflock)
				locks_copy_lock(conflock, fl);
				__locks_copy_lock(conflock, fl);
			error = -EAGAIN;
			error = -EAGAIN;
			if (!(request->fl_flags & FL_SLEEP))
			if (!(request->fl_flags & FL_SLEEP))
				goto out;
				goto out;
@@ -1367,6 +1367,12 @@ int generic_setlease(struct file *filp, long arg, struct file_lock **flp)


	lease = *flp;
	lease = *flp;


	if (arg != F_UNLCK) {
		error = -ENOMEM;
		new_fl = locks_alloc_lock();
		if (new_fl == NULL)
			goto out;

		error = -EAGAIN;
		error = -EAGAIN;
		if ((arg == F_RDLCK) && (atomic_read(&inode->i_writecount) > 0))
		if ((arg == F_RDLCK) && (atomic_read(&inode->i_writecount) > 0))
			goto out;
			goto out;
@@ -1374,11 +1380,7 @@ int generic_setlease(struct file *filp, long arg, struct file_lock **flp)
		    && ((atomic_read(&dentry->d_count) > 1)
		    && ((atomic_read(&dentry->d_count) > 1)
			|| (atomic_read(&inode->i_count) > 1)))
			|| (atomic_read(&inode->i_count) > 1)))
			goto out;
			goto out;

	}
	error = -ENOMEM;
	new_fl = locks_alloc_lock();
	if (new_fl == NULL)
		goto out;


	/*
	/*
	 * At this point, we know that if there is an exclusive
	 * At this point, we know that if there is an exclusive
@@ -1404,6 +1406,7 @@ int generic_setlease(struct file *filp, long arg, struct file_lock **flp)
			rdlease_count++;
			rdlease_count++;
	}
	}


	error = -EAGAIN;
	if ((arg == F_RDLCK && (wrlease_count > 0)) ||
	if ((arg == F_RDLCK && (wrlease_count > 0)) ||
	    (arg == F_WRLCK && ((rdlease_count + wrlease_count) > 0)))
	    (arg == F_WRLCK && ((rdlease_count + wrlease_count) > 0)))
		goto out;
		goto out;
@@ -1490,8 +1493,7 @@ EXPORT_SYMBOL_GPL(vfs_setlease);
int fcntl_setlease(unsigned int fd, struct file *filp, long arg)
int fcntl_setlease(unsigned int fd, struct file *filp, long arg)
{
{
	struct file_lock fl, *flp = &fl;
	struct file_lock fl, *flp = &fl;
	struct dentry *dentry = filp->f_path.dentry;
	struct inode *inode = filp->f_path.dentry->d_inode;
	struct inode *inode = dentry->d_inode;
	int error;
	int error;


	locks_init_lock(&fl);
	locks_init_lock(&fl);
+0 −3
Original line number Original line Diff line number Diff line
@@ -2712,9 +2712,6 @@ nfsd4_lock(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate,
	* Note: locks.c uses the BKL to protect the inode's lock list.
	* Note: locks.c uses the BKL to protect the inode's lock list.
	*/
	*/


	/* XXX?: Just to divert the locks_release_private at the start of
	 * locks_copy_lock: */
	locks_init_lock(&conflock);
	err = vfs_lock_file(filp, cmd, &file_lock, &conflock);
	err = vfs_lock_file(filp, cmd, &file_lock, &conflock);
	switch (-err) {
	switch (-err) {
	case 0: /* success! */
	case 0: /* success! */
Loading