aboutsummaryrefslogtreecommitdiffstats
path: root/fs/nfs/nfs4state.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2015-02-10 18:34:42 -0500
committerLinus Torvalds <torvalds@linux-foundation.org>2015-02-10 18:34:42 -0500
commit4b4f8580a4b77126733db8072862793d4deae66a (patch)
tree0d6ab49f4fe61ca96fd513b6dfae8be541796320 /fs/nfs/nfs4state.c
parent872912352c5be930e9568e5f3b6d73107d9f278d (diff)
parent8116bf4cb62d337c953cfa5369ef4cf83e73140c (diff)
Merge tag 'locks-v3.20-1' of git://git.samba.org/jlayton/linux
Pull file locking related changes #1 from Jeff Layton: "This patchset contains a fairly major overhaul of how file locks are tracked within the inode. Rather than a single list, we now create a per-inode "lock context" that contains individual lists for the file locks, and a new dedicated spinlock for them. There are changes in other trees that are based on top of this set so it may be easiest to pull this in early" * tag 'locks-v3.20-1' of git://git.samba.org/jlayton/linux: locks: update comments that refer to inode->i_flock locks: consolidate NULL i_flctx checks in locks_remove_file locks: keep a count of locks on the flctx lists locks: clean up the lm_change prototype locks: add a dedicated spinlock to protect i_flctx lists locks: remove i_flock field from struct inode locks: convert lease handling to file_lock_context locks: convert posix locks to file_lock_context locks: move flock locks to file_lock_context ceph: move spinlocking into ceph_encode_locks_to_buffer and ceph_count_locks locks: add a new struct file_locking_context pointer to struct inode locks: have locks_release_file use flock_lock_file to release generic flock locks locks: add new struct list_head to struct file_lock
Diffstat (limited to 'fs/nfs/nfs4state.c')
-rw-r--r--fs/nfs/nfs4state.c70
1 files changed, 38 insertions, 32 deletions
diff --git a/fs/nfs/nfs4state.c b/fs/nfs/nfs4state.c
index 5194933ed419..a3bb22ab68c5 100644
--- a/fs/nfs/nfs4state.c
+++ b/fs/nfs/nfs4state.c
@@ -1366,49 +1366,55 @@ static int nfs4_reclaim_locks(struct nfs4_state *state, const struct nfs4_state_
1366 struct nfs_inode *nfsi = NFS_I(inode); 1366 struct nfs_inode *nfsi = NFS_I(inode);
1367 struct file_lock *fl; 1367 struct file_lock *fl;
1368 int status = 0; 1368 int status = 0;
1369 struct file_lock_context *flctx = inode->i_flctx;
1370 struct list_head *list;
1369 1371
1370 if (inode->i_flock == NULL) 1372 if (flctx == NULL)
1371 return 0; 1373 return 0;
1372 1374
1375 list = &flctx->flc_posix;
1376
1373 /* Guard against delegation returns and new lock/unlock calls */ 1377 /* Guard against delegation returns and new lock/unlock calls */
1374 down_write(&nfsi->rwsem); 1378 down_write(&nfsi->rwsem);
1375 /* Protect inode->i_flock using the BKL */ 1379 spin_lock(&flctx->flc_lock);
1376 spin_lock(&inode->i_lock); 1380restart:
1377 for (fl = inode->i_flock; fl != NULL; fl = fl->fl_next) { 1381 list_for_each_entry(fl, list, fl_list) {
1378 if (!(fl->fl_flags & (FL_POSIX|FL_FLOCK)))
1379 continue;
1380 if (nfs_file_open_context(fl->fl_file)->state != state) 1382 if (nfs_file_open_context(fl->fl_file)->state != state)
1381 continue; 1383 continue;
1382 spin_unlock(&inode->i_lock); 1384 spin_unlock(&flctx->flc_lock);
1383 status = ops->recover_lock(state, fl); 1385 status = ops->recover_lock(state, fl);
1384 switch (status) { 1386 switch (status) {
1385 case 0: 1387 case 0:
1386 break; 1388 break;
1387 case -ESTALE: 1389 case -ESTALE:
1388 case -NFS4ERR_ADMIN_REVOKED: 1390 case -NFS4ERR_ADMIN_REVOKED:
1389 case -NFS4ERR_STALE_STATEID: 1391 case -NFS4ERR_STALE_STATEID:
1390 case -NFS4ERR_BAD_STATEID: 1392 case -NFS4ERR_BAD_STATEID:
1391 case -NFS4ERR_EXPIRED: 1393 case -NFS4ERR_EXPIRED:
1392 case -NFS4ERR_NO_GRACE: 1394 case -NFS4ERR_NO_GRACE:
1393 case -NFS4ERR_STALE_CLIENTID: 1395 case -NFS4ERR_STALE_CLIENTID:
1394 case -NFS4ERR_BADSESSION: 1396 case -NFS4ERR_BADSESSION:
1395 case -NFS4ERR_BADSLOT: 1397 case -NFS4ERR_BADSLOT:
1396 case -NFS4ERR_BAD_HIGH_SLOT: 1398 case -NFS4ERR_BAD_HIGH_SLOT:
1397 case -NFS4ERR_CONN_NOT_BOUND_TO_SESSION: 1399 case -NFS4ERR_CONN_NOT_BOUND_TO_SESSION:
1398 goto out; 1400 goto out;
1399 default: 1401 default:
1400 printk(KERN_ERR "NFS: %s: unhandled error %d\n", 1402 pr_err("NFS: %s: unhandled error %d\n",
1401 __func__, status); 1403 __func__, status);
1402 case -ENOMEM: 1404 case -ENOMEM:
1403 case -NFS4ERR_DENIED: 1405 case -NFS4ERR_DENIED:
1404 case -NFS4ERR_RECLAIM_BAD: 1406 case -NFS4ERR_RECLAIM_BAD:
1405 case -NFS4ERR_RECLAIM_CONFLICT: 1407 case -NFS4ERR_RECLAIM_CONFLICT:
1406 /* kill_proc(fl->fl_pid, SIGLOST, 1); */ 1408 /* kill_proc(fl->fl_pid, SIGLOST, 1); */
1407 status = 0; 1409 status = 0;
1408 } 1410 }
1409 spin_lock(&inode->i_lock); 1411 spin_lock(&flctx->flc_lock);
1410 } 1412 }
1411 spin_unlock(&inode->i_lock); 1413 if (list == &flctx->flc_posix) {
1414 list = &flctx->flc_flock;
1415 goto restart;
1416 }
1417 spin_unlock(&flctx->flc_lock);
1412out: 1418out:
1413 up_write(&nfsi->rwsem); 1419 up_write(&nfsi->rwsem);
1414 return status; 1420 return status;