* [PATCH 0/6] More layoutreturn nits @ 2016-07-22 19:33 Trond Myklebust 2016-07-22 19:33 ` [PATCH 1/6] pNFS: Clear the layout return tracking on layout reinitialisation Trond Myklebust 0 siblings, 1 reply; 7+ messages in thread From: Trond Myklebust @ 2016-07-22 19:33 UTC (permalink / raw) To: linux-nfs Various non-critical bugfixes and cleanups targeting layoutreturn. Trond Myklebust (6): pNFS: Clear the layout return tracking on layout reinitialisation pNFS: Ensure layoutreturn acts as a completion for layout callbacks pNFS: Do not set plh_return_seq for non-callback related layoutreturns pNFS: Remove redundant stateid invalidation NFS: pnfs_mark_matching_lsegs_return() should match the layout sequence id pNFS: Cleanup - don't open code pnfs_mark_layout_stateid_invalid() fs/nfs/nfs42proc.c | 3 +- fs/nfs/nfs4proc.c | 3 +- fs/nfs/pnfs.c | 108 +++++++++++++++++++++++++++++++++-------------------- fs/nfs/pnfs.h | 2 + 4 files changed, 71 insertions(+), 45 deletions(-) -- 2.7.4 ^ permalink raw reply [flat|nested] 7+ messages in thread
* [PATCH 1/6] pNFS: Clear the layout return tracking on layout reinitialisation 2016-07-22 19:33 [PATCH 0/6] More layoutreturn nits Trond Myklebust @ 2016-07-22 19:33 ` Trond Myklebust 2016-07-22 19:33 ` [PATCH 2/6] pNFS: Ensure layoutreturn acts as a completion for layout callbacks Trond Myklebust 0 siblings, 1 reply; 7+ messages in thread From: Trond Myklebust @ 2016-07-22 19:33 UTC (permalink / raw) To: linux-nfs Ensure that we don't carry over layoutreturn info from a previous incarnation of this layout. Signed-off-by: Trond Myklebust <trond.myklebust@primarydata.com> --- fs/nfs/pnfs.c | 17 +++++++++++++---- 1 file changed, 13 insertions(+), 4 deletions(-) diff --git a/fs/nfs/pnfs.c b/fs/nfs/pnfs.c index 0c7e0d45a4de..27052d4b46ef 100644 --- a/fs/nfs/pnfs.c +++ b/fs/nfs/pnfs.c @@ -871,15 +871,21 @@ void pnfs_clear_layoutreturn_waitbit(struct pnfs_layout_hdr *lo) rpc_wake_up(&NFS_SERVER(lo->plh_inode)->roc_rpcwaitq); } +static void +pnfs_clear_layoutreturn_info(struct pnfs_layout_hdr *lo) +{ + lo->plh_return_iomode = 0; + lo->plh_return_seq = 0; + clear_bit(NFS_LAYOUT_RETURN_REQUESTED, &lo->plh_flags); +} + static bool pnfs_prepare_layoutreturn(struct pnfs_layout_hdr *lo) { if (test_and_set_bit(NFS_LAYOUT_RETURN, &lo->plh_flags)) return false; - lo->plh_return_iomode = 0; - lo->plh_return_seq = 0; pnfs_get_layout_hdr(lo); - clear_bit(NFS_LAYOUT_RETURN_REQUESTED, &lo->plh_flags); + pnfs_clear_layoutreturn_info(lo); return true; } @@ -1760,7 +1766,10 @@ pnfs_layout_process(struct nfs4_layoutget *lgp) lo->plh_barrier = be32_to_cpu(res->stateid.seqid); } - clear_bit(NFS_LAYOUT_INVALID_STID, &lo->plh_flags); + if (test_bit(NFS_LAYOUT_INVALID_STID, &lo->plh_flags)) { + pnfs_clear_layoutreturn_info(lo); + clear_bit(NFS_LAYOUT_INVALID_STID, &lo->plh_flags); + } pnfs_get_lseg(lseg); pnfs_layout_insert_lseg(lo, lseg, &free_me); -- 2.7.4 ^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 2/6] pNFS: Ensure layoutreturn acts as a completion for layout callbacks 2016-07-22 19:33 ` [PATCH 1/6] pNFS: Clear the layout return tracking on layout reinitialisation Trond Myklebust @ 2016-07-22 19:33 ` Trond Myklebust 2016-07-22 19:33 ` [PATCH 3/6] pNFS: Do not set plh_return_seq for non-callback related layoutreturns Trond Myklebust 0 siblings, 1 reply; 7+ messages in thread From: Trond Myklebust @ 2016-07-22 19:33 UTC (permalink / raw) To: linux-nfs When we return NFS_OK to the CB_LAYOUTRECALL, we are required to send a layoutreturn that "completes" that layout recall request, using the correct stateid. Signed-off-by: Trond Myklebust <trond.myklebust@primarydata.com> --- fs/nfs/pnfs.c | 40 +++++++++++++++++++++++++--------------- 1 file changed, 25 insertions(+), 15 deletions(-) diff --git a/fs/nfs/pnfs.c b/fs/nfs/pnfs.c index 27052d4b46ef..7a29598d8ab0 100644 --- a/fs/nfs/pnfs.c +++ b/fs/nfs/pnfs.c @@ -880,12 +880,28 @@ pnfs_clear_layoutreturn_info(struct pnfs_layout_hdr *lo) } static bool -pnfs_prepare_layoutreturn(struct pnfs_layout_hdr *lo) +pnfs_prepare_layoutreturn(struct pnfs_layout_hdr *lo, + nfs4_stateid *stateid, + enum pnfs_iomode *iomode) { if (test_and_set_bit(NFS_LAYOUT_RETURN, &lo->plh_flags)) return false; pnfs_get_layout_hdr(lo); - pnfs_clear_layoutreturn_info(lo); + if (test_bit(NFS_LAYOUT_RETURN_REQUESTED, &lo->plh_flags)) { + if (stateid != NULL) { + nfs4_stateid_copy(stateid, &lo->plh_stateid); + if (lo->plh_return_seq != 0) + stateid->seqid = cpu_to_be32(lo->plh_return_seq); + } + if (iomode != NULL) + *iomode = lo->plh_return_iomode; + pnfs_clear_layoutreturn_info(lo); + return true; + } + if (stateid != NULL) + nfs4_stateid_copy(stateid, &lo->plh_stateid); + if (iomode != NULL) + *iomode = IOMODE_ANY; return true; } @@ -953,10 +969,7 @@ static void pnfs_layoutreturn_before_put_layout_hdr(struct pnfs_layout_hdr *lo) enum pnfs_iomode iomode; bool send; - nfs4_stateid_copy(&stateid, &lo->plh_stateid); - stateid.seqid = cpu_to_be32(lo->plh_return_seq); - iomode = lo->plh_return_iomode; - send = pnfs_prepare_layoutreturn(lo); + send = pnfs_prepare_layoutreturn(lo, &stateid, &iomode); spin_unlock(&inode->i_lock); if (send) { /* Send an async layoutreturn so we dont deadlock */ @@ -993,7 +1006,6 @@ _pnfs_return_layout(struct inode *ino) dprintk("NFS: %s no layout to return\n", __func__); goto out; } - nfs4_stateid_copy(&stateid, &nfsi->layout->plh_stateid); /* Reference matched in nfs4_layoutreturn_release */ pnfs_get_layout_hdr(lo); empty = list_empty(&lo->plh_segs); @@ -1017,7 +1029,7 @@ _pnfs_return_layout(struct inode *ino) } set_bit(NFS_LAYOUT_INVALID_STID, &lo->plh_flags); - send = pnfs_prepare_layoutreturn(lo); + send = pnfs_prepare_layoutreturn(lo, &stateid, NULL); spin_unlock(&ino->i_lock); pnfs_free_lseg_list(&tmp_list); if (send) @@ -1084,11 +1096,10 @@ bool pnfs_roc(struct inode *ino) goto out_noroc; } - nfs4_stateid_copy(&stateid, &lo->plh_stateid); /* always send layoutreturn if being marked so */ - if (test_and_clear_bit(NFS_LAYOUT_RETURN_REQUESTED, - &lo->plh_flags)) - layoutreturn = pnfs_prepare_layoutreturn(lo); + if (test_bit(NFS_LAYOUT_RETURN_REQUESTED, &lo->plh_flags)) + layoutreturn = pnfs_prepare_layoutreturn(lo, + &stateid, NULL); list_for_each_entry_safe(lseg, tmp, &lo->plh_segs, pls_list) /* If we are sending layoutreturn, invalidate all valid lsegs */ @@ -1869,10 +1880,9 @@ void pnfs_error_mark_layout_for_return(struct inode *inode, if (!pnfs_mark_matching_lsegs_return(lo, &free_me, &range, lseg->pls_seq)) { nfs4_stateid stateid; - enum pnfs_iomode iomode = lo->plh_return_iomode; + enum pnfs_iomode iomode; - nfs4_stateid_copy(&stateid, &lo->plh_stateid); - return_now = pnfs_prepare_layoutreturn(lo); + return_now = pnfs_prepare_layoutreturn(lo, &stateid, &iomode); spin_unlock(&inode->i_lock); if (return_now) pnfs_send_layoutreturn(lo, &stateid, iomode, false); -- 2.7.4 ^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 3/6] pNFS: Do not set plh_return_seq for non-callback related layoutreturns 2016-07-22 19:33 ` [PATCH 2/6] pNFS: Ensure layoutreturn acts as a completion for layout callbacks Trond Myklebust @ 2016-07-22 19:33 ` Trond Myklebust 2016-07-22 19:33 ` [PATCH 4/6] pNFS: Remove redundant stateid invalidation Trond Myklebust 0 siblings, 1 reply; 7+ messages in thread From: Trond Myklebust @ 2016-07-22 19:33 UTC (permalink / raw) To: linux-nfs In cases where we need to send a layoutreturn in order to propagate an error, we should not tie that to a specific layout stateid. Signed-off-by: Trond Myklebust <trond.myklebust@primarydata.com> --- fs/nfs/pnfs.c | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/fs/nfs/pnfs.c b/fs/nfs/pnfs.c index 7a29598d8ab0..12d4d1b55dd1 100644 --- a/fs/nfs/pnfs.c +++ b/fs/nfs/pnfs.c @@ -1803,14 +1803,14 @@ static void pnfs_set_plh_return_info(struct pnfs_layout_hdr *lo, enum pnfs_iomode iomode, u32 seq) { - if (lo->plh_return_iomode == iomode) - return; - if (lo->plh_return_iomode != 0) + if (lo->plh_return_iomode != 0 && lo->plh_return_iomode != iomode) iomode = IOMODE_ANY; lo->plh_return_iomode = iomode; set_bit(NFS_LAYOUT_RETURN_REQUESTED, &lo->plh_flags); - if (!lo->plh_return_seq || pnfs_seqid_is_newer(seq, lo->plh_return_seq)) + if (seq != 0) { + WARN_ON_ONCE(lo->plh_return_seq != 0 && lo->plh_return_seq != seq); lo->plh_return_seq = seq; + } } /** @@ -1871,14 +1871,13 @@ void pnfs_error_mark_layout_for_return(struct inode *inode, bool return_now = false; spin_lock(&inode->i_lock); - pnfs_set_plh_return_info(lo, range.iomode, lseg->pls_seq); + pnfs_set_plh_return_info(lo, range.iomode, 0); /* * mark all matching lsegs so that we are sure to have no live * segments at hand when sending layoutreturn. See pnfs_put_lseg() * for how it works. */ - if (!pnfs_mark_matching_lsegs_return(lo, &free_me, - &range, lseg->pls_seq)) { + if (!pnfs_mark_matching_lsegs_return(lo, &free_me, &range, 0)) { nfs4_stateid stateid; enum pnfs_iomode iomode; -- 2.7.4 ^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 4/6] pNFS: Remove redundant stateid invalidation 2016-07-22 19:33 ` [PATCH 3/6] pNFS: Do not set plh_return_seq for non-callback related layoutreturns Trond Myklebust @ 2016-07-22 19:33 ` Trond Myklebust 2016-07-22 19:33 ` [PATCH 5/6] NFS: pnfs_mark_matching_lsegs_return() should match the layout sequence id Trond Myklebust 0 siblings, 1 reply; 7+ messages in thread From: Trond Myklebust @ 2016-07-22 19:33 UTC (permalink / raw) To: linux-nfs The layout stateid will be invalidated once it holds no more layout segments anyway. Signed-off-by: Trond Myklebust <trond.myklebust@primarydata.com> --- fs/nfs/pnfs.c | 1 - 1 file changed, 1 deletion(-) diff --git a/fs/nfs/pnfs.c b/fs/nfs/pnfs.c index 12d4d1b55dd1..010f8803090b 100644 --- a/fs/nfs/pnfs.c +++ b/fs/nfs/pnfs.c @@ -1028,7 +1028,6 @@ _pnfs_return_layout(struct inode *ino) goto out_put_layout_hdr; } - set_bit(NFS_LAYOUT_INVALID_STID, &lo->plh_flags); send = pnfs_prepare_layoutreturn(lo, &stateid, NULL); spin_unlock(&ino->i_lock); pnfs_free_lseg_list(&tmp_list); -- 2.7.4 ^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 5/6] NFS: pnfs_mark_matching_lsegs_return() should match the layout sequence id 2016-07-22 19:33 ` [PATCH 4/6] pNFS: Remove redundant stateid invalidation Trond Myklebust @ 2016-07-22 19:33 ` Trond Myklebust 2016-07-22 19:33 ` [PATCH 6/6] pNFS: Cleanup - don't open code pnfs_mark_layout_stateid_invalid() Trond Myklebust 0 siblings, 1 reply; 7+ messages in thread From: Trond Myklebust @ 2016-07-22 19:33 UTC (permalink / raw) To: linux-nfs When determining which layout segments to return, we do want pnfs_mark_matching_lsegs_return to check that they match the layout sequence id. This ensures that we don't waste time if the server is replaying a layout recall that has already been satisfied. Signed-off-by: Trond Myklebust <trond.myklebust@primarydata.com> --- fs/nfs/pnfs.c | 37 +++++++++++++++++++++++-------------- 1 file changed, 23 insertions(+), 14 deletions(-) diff --git a/fs/nfs/pnfs.c b/fs/nfs/pnfs.c index 010f8803090b..0d68768e7afe 100644 --- a/fs/nfs/pnfs.c +++ b/fs/nfs/pnfs.c @@ -484,15 +484,6 @@ pnfs_lseg_range_intersecting(const struct pnfs_layout_range *l1, (end2 == NFS4_MAX_UINT64 || end2 > start1); } -static bool -should_free_lseg(const struct pnfs_layout_range *lseg_range, - const struct pnfs_layout_range *recall_range) -{ - return (recall_range->iomode == IOMODE_ANY || - lseg_range->iomode == recall_range->iomode) && - pnfs_lseg_range_intersecting(lseg_range, recall_range); -} - static bool pnfs_lseg_dec_and_remove_zero(struct pnfs_layout_segment *lseg, struct list_head *tmp_list) { @@ -531,6 +522,27 @@ static bool pnfs_seqid_is_newer(u32 s1, u32 s2) return (s32)(s1 - s2) > 0; } +static bool +pnfs_should_free_range(const struct pnfs_layout_range *lseg_range, + const struct pnfs_layout_range *recall_range) +{ + return (recall_range->iomode == IOMODE_ANY || + lseg_range->iomode == recall_range->iomode) && + pnfs_lseg_range_intersecting(lseg_range, recall_range); +} + +static bool +pnfs_match_lseg_recall(const struct pnfs_layout_segment *lseg, + const struct pnfs_layout_range *recall_range, + u32 seq) +{ + if (seq != 0 && pnfs_seqid_is_newer(lseg->pls_seq, seq)) + return false; + if (recall_range == NULL) + return true; + return pnfs_should_free_range(&lseg->pls_range, recall_range); +} + /** * pnfs_mark_matching_lsegs_invalid - tear down lsegs or mark them for later * @lo: layout header containing the lsegs @@ -560,10 +572,7 @@ pnfs_mark_matching_lsegs_invalid(struct pnfs_layout_hdr *lo, if (list_empty(&lo->plh_segs)) return 0; list_for_each_entry_safe(lseg, next, &lo->plh_segs, pls_list) - if (!recall_range || - should_free_lseg(&lseg->pls_range, recall_range)) { - if (seq && pnfs_seqid_is_newer(lseg->pls_seq, seq)) - continue; + if (pnfs_match_lseg_recall(lseg, recall_range, seq)) { dprintk("%s: freeing lseg %p iomode %d seq %u" "offset %llu length %llu\n", __func__, lseg, lseg->pls_range.iomode, lseg->pls_seq, @@ -1839,7 +1848,7 @@ pnfs_mark_matching_lsegs_return(struct pnfs_layout_hdr *lo, assert_spin_locked(&lo->plh_inode->i_lock); list_for_each_entry_safe(lseg, next, &lo->plh_segs, pls_list) - if (should_free_lseg(&lseg->pls_range, return_range)) { + if (pnfs_match_lseg_recall(lseg, return_range, seq)) { dprintk("%s: marking lseg %p iomode %d " "offset %llu length %llu\n", __func__, lseg, lseg->pls_range.iomode, -- 2.7.4 ^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 6/6] pNFS: Cleanup - don't open code pnfs_mark_layout_stateid_invalid() 2016-07-22 19:33 ` [PATCH 5/6] NFS: pnfs_mark_matching_lsegs_return() should match the layout sequence id Trond Myklebust @ 2016-07-22 19:33 ` Trond Myklebust 0 siblings, 0 replies; 7+ messages in thread From: Trond Myklebust @ 2016-07-22 19:33 UTC (permalink / raw) To: linux-nfs Ensure nfs42_layoutstat_done() layoutget don't open code layout stateid invalidation. Signed-off-by: Trond Myklebust <trond.myklebust@primarydata.com> --- fs/nfs/nfs42proc.c | 3 +-- fs/nfs/nfs4proc.c | 3 +-- fs/nfs/pnfs.c | 2 +- fs/nfs/pnfs.h | 2 ++ 4 files changed, 5 insertions(+), 5 deletions(-) diff --git a/fs/nfs/nfs42proc.c b/fs/nfs/nfs42proc.c index aa03ed09ba06..6ea5ad6f0d44 100644 --- a/fs/nfs/nfs42proc.c +++ b/fs/nfs/nfs42proc.c @@ -336,8 +336,7 @@ nfs42_layoutstat_done(struct rpc_task *task, void *calldata) * Mark the bad layout state as invalid, then retry * with the current stateid. */ - set_bit(NFS_LAYOUT_INVALID_STID, &lo->plh_flags); - pnfs_mark_matching_lsegs_invalid(lo, &head, NULL, 0); + pnfs_mark_layout_stateid_invalid(lo, &head); spin_unlock(&inode->i_lock); pnfs_free_lseg_list(&head); } else diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index de97567795a5..676d0e5392c7 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c @@ -7932,8 +7932,7 @@ nfs4_layoutget_handle_exception(struct rpc_task *task, * Mark the bad layout state as invalid, then retry * with the current stateid. */ - set_bit(NFS_LAYOUT_INVALID_STID, &lo->plh_flags); - pnfs_mark_matching_lsegs_invalid(lo, &head, NULL, 0); + pnfs_mark_layout_stateid_invalid(lo, &head); spin_unlock(&inode->i_lock); pnfs_free_lseg_list(&head); } else diff --git a/fs/nfs/pnfs.c b/fs/nfs/pnfs.c index 0d68768e7afe..7ac0eaa97a89 100644 --- a/fs/nfs/pnfs.c +++ b/fs/nfs/pnfs.c @@ -259,7 +259,7 @@ pnfs_put_layout_hdr(struct pnfs_layout_hdr *lo) * is required. * Note that caller must hold inode->i_lock. */ -static int +int pnfs_mark_layout_stateid_invalid(struct pnfs_layout_hdr *lo, struct list_head *lseg_list) { diff --git a/fs/nfs/pnfs.h b/fs/nfs/pnfs.h index b21bd0bee784..4a7ab14900d9 100644 --- a/fs/nfs/pnfs.h +++ b/fs/nfs/pnfs.h @@ -268,6 +268,8 @@ int pnfs_mark_matching_lsegs_return(struct pnfs_layout_hdr *lo, struct list_head *tmp_list, const struct pnfs_layout_range *recall_range, u32 seq); +int pnfs_mark_layout_stateid_invalid(struct pnfs_layout_hdr *lo, + struct list_head *lseg_list); bool pnfs_roc(struct inode *ino); void pnfs_roc_release(struct inode *ino); void pnfs_roc_set_barrier(struct inode *ino, u32 barrier); -- 2.7.4 ^ permalink raw reply related [flat|nested] 7+ messages in thread
end of thread, other threads:[~2016-07-22 19:34 UTC | newest] Thread overview: 7+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2016-07-22 19:33 [PATCH 0/6] More layoutreturn nits Trond Myklebust 2016-07-22 19:33 ` [PATCH 1/6] pNFS: Clear the layout return tracking on layout reinitialisation Trond Myklebust 2016-07-22 19:33 ` [PATCH 2/6] pNFS: Ensure layoutreturn acts as a completion for layout callbacks Trond Myklebust 2016-07-22 19:33 ` [PATCH 3/6] pNFS: Do not set plh_return_seq for non-callback related layoutreturns Trond Myklebust 2016-07-22 19:33 ` [PATCH 4/6] pNFS: Remove redundant stateid invalidation Trond Myklebust 2016-07-22 19:33 ` [PATCH 5/6] NFS: pnfs_mark_matching_lsegs_return() should match the layout sequence id Trond Myklebust 2016-07-22 19:33 ` [PATCH 6/6] pNFS: Cleanup - don't open code pnfs_mark_layout_stateid_invalid() Trond Myklebust
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for NNTP newsgroup(s).