Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'nfs-for-4.5-3' of git://git.linux-nfs.org/projects/trondmy/linux-nfs

Pull NFS client bugfix and cleanup from Trond Myklebust:
"Bugfix:
- pNFS: Fix for missing layoutreturn calls

Cleanup:
- pNFS: rename NFS_LAYOUT_RETURN_BEFORE_CLOSE for code clarity"

* tag 'nfs-for-4.5-3' of git://git.linux-nfs.org/projects/trondmy/linux-nfs:
NFS: Cleanup - rename NFS_LAYOUT_RETURN_BEFORE_CLOSE
pNFS: Fix missing layoutreturn calls

+62 -68
+1 -1
fs/nfs/flexfilelayout/flexfilelayout.c
··· 1215 1215 hdr->pgio_mirror_idx + 1, 1216 1216 &hdr->pgio_mirror_idx)) 1217 1217 goto out_eagain; 1218 - set_bit(NFS_LAYOUT_RETURN_BEFORE_CLOSE, 1218 + set_bit(NFS_LAYOUT_RETURN_REQUESTED, 1219 1219 &hdr->lseg->pls_layout->plh_flags); 1220 1220 pnfs_read_resend_pnfs(hdr); 1221 1221 return task->tk_status;
+1 -1
fs/nfs/flexfilelayout/flexfilelayoutdev.c
··· 412 412 OP_ILLEGAL, GFP_NOIO); 413 413 if (!fail_return) { 414 414 if (ff_layout_has_available_ds(lseg)) 415 - set_bit(NFS_LAYOUT_RETURN_BEFORE_CLOSE, 415 + set_bit(NFS_LAYOUT_RETURN_REQUESTED, 416 416 &lseg->pls_layout->plh_flags); 417 417 else 418 418 pnfs_error_mark_layout_for_return(ino, lseg);
+58 -64
fs/nfs/pnfs.c
··· 52 52 */ 53 53 static LIST_HEAD(pnfs_modules_tbl); 54 54 55 - static int 56 - pnfs_send_layoutreturn(struct pnfs_layout_hdr *lo, const nfs4_stateid *stateid, 57 - enum pnfs_iomode iomode, bool sync); 55 + static void pnfs_layoutreturn_before_put_layout_hdr(struct pnfs_layout_hdr *lo); 58 56 59 57 /* Return the registered pnfs layout driver module matching given id */ 60 58 static struct pnfs_layoutdriver_type * ··· 241 243 { 242 244 struct inode *inode = lo->plh_inode; 243 245 246 + pnfs_layoutreturn_before_put_layout_hdr(lo); 247 + 244 248 if (atomic_dec_and_lock(&lo->plh_refcount, &inode->i_lock)) { 245 249 if (!list_empty(&lo->plh_segs)) 246 250 WARN_ONCE(1, "NFS: BUG unfreed layout segments.\n"); ··· 345 345 rpc_wake_up(&NFS_SERVER(inode)->roc_rpcwaitq); 346 346 } 347 347 348 - /* Return true if layoutreturn is needed */ 349 - static bool 350 - pnfs_layout_need_return(struct pnfs_layout_hdr *lo, 351 - struct pnfs_layout_segment *lseg) 352 - { 353 - struct pnfs_layout_segment *s; 354 - 355 - if (!test_and_clear_bit(NFS_LSEG_LAYOUTRETURN, &lseg->pls_flags)) 356 - return false; 357 - 358 - list_for_each_entry(s, &lo->plh_segs, pls_list) 359 - if (s != lseg && test_bit(NFS_LSEG_LAYOUTRETURN, &s->pls_flags)) 360 - return false; 361 - 362 - return true; 363 - } 364 - 365 - static bool 366 - pnfs_prepare_layoutreturn(struct pnfs_layout_hdr *lo) 367 - { 368 - if (test_and_set_bit(NFS_LAYOUT_RETURN, &lo->plh_flags)) 369 - return false; 370 - lo->plh_return_iomode = 0; 371 - pnfs_get_layout_hdr(lo); 372 - clear_bit(NFS_LAYOUT_RETURN_BEFORE_CLOSE, &lo->plh_flags); 373 - return true; 374 - } 375 - 376 - static void pnfs_layoutreturn_before_put_lseg(struct pnfs_layout_segment *lseg, 377 - struct pnfs_layout_hdr *lo, struct inode *inode) 378 - { 379 - lo = lseg->pls_layout; 380 - inode = lo->plh_inode; 381 - 382 - spin_lock(&inode->i_lock); 383 - if (pnfs_layout_need_return(lo, lseg)) { 384 - nfs4_stateid stateid; 385 - enum pnfs_iomode iomode; 386 - bool send; 387 - 388 - nfs4_stateid_copy(&stateid, &lo->plh_stateid); 389 - iomode = lo->plh_return_iomode; 390 - send = pnfs_prepare_layoutreturn(lo); 391 - spin_unlock(&inode->i_lock); 392 - if (send) { 393 - /* Send an async layoutreturn so we dont deadlock */ 394 - pnfs_send_layoutreturn(lo, &stateid, iomode, false); 395 - } 396 - } else 397 - spin_unlock(&inode->i_lock); 398 - } 399 - 400 348 void 401 349 pnfs_put_lseg(struct pnfs_layout_segment *lseg) 402 350 { ··· 358 410 atomic_read(&lseg->pls_refcount), 359 411 test_bit(NFS_LSEG_VALID, &lseg->pls_flags)); 360 412 361 - /* Handle the case where refcount != 1 */ 362 - if (atomic_add_unless(&lseg->pls_refcount, -1, 1)) 363 - return; 364 - 365 413 lo = lseg->pls_layout; 366 414 inode = lo->plh_inode; 367 - /* Do we need a layoutreturn? */ 368 - if (test_bit(NFS_LSEG_LAYOUTRETURN, &lseg->pls_flags)) 369 - pnfs_layoutreturn_before_put_lseg(lseg, lo, inode); 370 415 371 416 if (atomic_dec_and_lock(&lseg->pls_refcount, &inode->i_lock)) { 372 417 if (test_bit(NFS_LSEG_VALID, &lseg->pls_flags)) { ··· 878 937 rpc_wake_up(&NFS_SERVER(lo->plh_inode)->roc_rpcwaitq); 879 938 } 880 939 940 + static bool 941 + pnfs_prepare_layoutreturn(struct pnfs_layout_hdr *lo) 942 + { 943 + if (test_and_set_bit(NFS_LAYOUT_RETURN, &lo->plh_flags)) 944 + return false; 945 + lo->plh_return_iomode = 0; 946 + pnfs_get_layout_hdr(lo); 947 + clear_bit(NFS_LAYOUT_RETURN_REQUESTED, &lo->plh_flags); 948 + return true; 949 + } 950 + 881 951 static int 882 952 pnfs_send_layoutreturn(struct pnfs_layout_hdr *lo, const nfs4_stateid *stateid, 883 953 enum pnfs_iomode iomode, bool sync) ··· 921 969 out: 922 970 dprintk("<-- %s status: %d\n", __func__, status); 923 971 return status; 972 + } 973 + 974 + /* Return true if layoutreturn is needed */ 975 + static bool 976 + pnfs_layout_need_return(struct pnfs_layout_hdr *lo) 977 + { 978 + struct pnfs_layout_segment *s; 979 + 980 + if (!test_bit(NFS_LAYOUT_RETURN_REQUESTED, &lo->plh_flags)) 981 + return false; 982 + 983 + /* Defer layoutreturn until all lsegs are done */ 984 + list_for_each_entry(s, &lo->plh_segs, pls_list) { 985 + if (test_bit(NFS_LSEG_LAYOUTRETURN, &s->pls_flags)) 986 + return false; 987 + } 988 + 989 + return true; 990 + } 991 + 992 + static void pnfs_layoutreturn_before_put_layout_hdr(struct pnfs_layout_hdr *lo) 993 + { 994 + struct inode *inode= lo->plh_inode; 995 + 996 + if (!test_bit(NFS_LAYOUT_RETURN_REQUESTED, &lo->plh_flags)) 997 + return; 998 + spin_lock(&inode->i_lock); 999 + if (pnfs_layout_need_return(lo)) { 1000 + nfs4_stateid stateid; 1001 + enum pnfs_iomode iomode; 1002 + bool send; 1003 + 1004 + nfs4_stateid_copy(&stateid, &lo->plh_stateid); 1005 + iomode = lo->plh_return_iomode; 1006 + send = pnfs_prepare_layoutreturn(lo); 1007 + spin_unlock(&inode->i_lock); 1008 + if (send) { 1009 + /* Send an async layoutreturn so we dont deadlock */ 1010 + pnfs_send_layoutreturn(lo, &stateid, iomode, false); 1011 + } 1012 + } else 1013 + spin_unlock(&inode->i_lock); 924 1014 } 925 1015 926 1016 /* ··· 1085 1091 1086 1092 nfs4_stateid_copy(&stateid, &lo->plh_stateid); 1087 1093 /* always send layoutreturn if being marked so */ 1088 - if (test_and_clear_bit(NFS_LAYOUT_RETURN_BEFORE_CLOSE, 1094 + if (test_and_clear_bit(NFS_LAYOUT_RETURN_REQUESTED, 1089 1095 &lo->plh_flags)) 1090 1096 layoutreturn = pnfs_prepare_layoutreturn(lo); 1091 1097 ··· 1766 1772 pnfs_set_plh_return_iomode(lo, return_range->iomode); 1767 1773 if (!mark_lseg_invalid(lseg, tmp_list)) 1768 1774 remaining++; 1769 - set_bit(NFS_LAYOUT_RETURN_BEFORE_CLOSE, 1775 + set_bit(NFS_LAYOUT_RETURN_REQUESTED, 1770 1776 &lo->plh_flags); 1771 1777 } 1772 1778 return remaining;
+2 -2
fs/nfs/pnfs.h
··· 94 94 NFS_LAYOUT_RO_FAILED = 0, /* get ro layout failed stop trying */ 95 95 NFS_LAYOUT_RW_FAILED, /* get rw layout failed stop trying */ 96 96 NFS_LAYOUT_BULK_RECALL, /* bulk recall affecting layout */ 97 - NFS_LAYOUT_RETURN, /* Return this layout ASAP */ 98 - NFS_LAYOUT_RETURN_BEFORE_CLOSE, /* Return this layout before close */ 97 + NFS_LAYOUT_RETURN, /* layoutreturn in progress */ 98 + NFS_LAYOUT_RETURN_REQUESTED, /* Return this layout ASAP */ 99 99 NFS_LAYOUT_INVALID_STID, /* layout stateid id is invalid */ 100 100 NFS_LAYOUT_FIRST_LAYOUTGET, /* Serialize first layoutget */ 101 101 };