diff options
author | Jeff Layton <jlayton@poochiereds.net> | 2016-05-17 12:28:48 -0400 |
---|---|---|
committer | Anna Schumaker <Anna.Schumaker@Netapp.com> | 2016-05-17 15:48:13 -0400 |
commit | 1b3c6d07e29515064aca8a9f86efaea7da4da027 (patch) | |
tree | 9bff3d864babadc95af859903a2b16fd888c0f36 | |
parent | 183d9e7b112aaed0d19c16ffcf0f8c3a86dc71e0 (diff) |
pnfs: make pnfs_layout_process more robust
It can return NULL if layoutgets are blocked currently. Fix it to return
-EAGAIN in that case, so we can properly handle it in pnfs_update_layout.
Also, clean up and simplify the error handling -- eliminate "status" and
just use "lseg".
Signed-off-by: Jeff Layton <jeff.layton@primarydata.com>
Signed-off-by: Anna Schumaker <Anna.Schumaker@Netapp.com>
-rw-r--r-- | fs/nfs/pnfs.c | 27 |
1 files changed, 11 insertions, 16 deletions
diff --git a/fs/nfs/pnfs.c b/fs/nfs/pnfs.c index 46339a7fb191..79ae3049608d 100644 --- a/fs/nfs/pnfs.c +++ b/fs/nfs/pnfs.c | |||
@@ -1708,21 +1708,19 @@ pnfs_layout_process(struct nfs4_layoutget *lgp) | |||
1708 | struct pnfs_layout_segment *lseg; | 1708 | struct pnfs_layout_segment *lseg; |
1709 | struct inode *ino = lo->plh_inode; | 1709 | struct inode *ino = lo->plh_inode; |
1710 | LIST_HEAD(free_me); | 1710 | LIST_HEAD(free_me); |
1711 | int status = -EINVAL; | ||
1712 | 1711 | ||
1713 | if (!pnfs_sanity_check_layout_range(&res->range)) | 1712 | if (!pnfs_sanity_check_layout_range(&res->range)) |
1714 | goto out; | 1713 | return ERR_PTR(-EINVAL); |
1715 | 1714 | ||
1716 | /* Inject layout blob into I/O device driver */ | 1715 | /* Inject layout blob into I/O device driver */ |
1717 | lseg = NFS_SERVER(ino)->pnfs_curr_ld->alloc_lseg(lo, res, lgp->gfp_flags); | 1716 | lseg = NFS_SERVER(ino)->pnfs_curr_ld->alloc_lseg(lo, res, lgp->gfp_flags); |
1718 | if (!lseg || IS_ERR(lseg)) { | 1717 | if (IS_ERR_OR_NULL(lseg)) { |
1719 | if (!lseg) | 1718 | if (!lseg) |
1720 | status = -ENOMEM; | 1719 | lseg = ERR_PTR(-ENOMEM); |
1721 | else | 1720 | |
1722 | status = PTR_ERR(lseg); | 1721 | dprintk("%s: Could not allocate layout: error %ld\n", |
1723 | dprintk("%s: Could not allocate layout: error %d\n", | 1722 | __func__, PTR_ERR(lseg)); |
1724 | __func__, status); | 1723 | return lseg; |
1725 | goto out; | ||
1726 | } | 1724 | } |
1727 | 1725 | ||
1728 | init_lseg(lo, lseg); | 1726 | init_lseg(lo, lseg); |
@@ -1732,15 +1730,14 @@ pnfs_layout_process(struct nfs4_layoutget *lgp) | |||
1732 | spin_lock(&ino->i_lock); | 1730 | spin_lock(&ino->i_lock); |
1733 | if (pnfs_layoutgets_blocked(lo)) { | 1731 | if (pnfs_layoutgets_blocked(lo)) { |
1734 | dprintk("%s forget reply due to state\n", __func__); | 1732 | dprintk("%s forget reply due to state\n", __func__); |
1735 | goto out_forget_reply; | 1733 | goto out_forget; |
1736 | } | 1734 | } |
1737 | 1735 | ||
1738 | if (nfs4_stateid_match_other(&lo->plh_stateid, &res->stateid)) { | 1736 | if (nfs4_stateid_match_other(&lo->plh_stateid, &res->stateid)) { |
1739 | /* existing state ID, make sure the sequence number matches. */ | 1737 | /* existing state ID, make sure the sequence number matches. */ |
1740 | if (pnfs_layout_stateid_blocked(lo, &res->stateid)) { | 1738 | if (pnfs_layout_stateid_blocked(lo, &res->stateid)) { |
1741 | dprintk("%s forget reply due to sequence\n", __func__); | 1739 | dprintk("%s forget reply due to sequence\n", __func__); |
1742 | status = -EAGAIN; | 1740 | goto out_forget; |
1743 | goto out_forget_reply; | ||
1744 | } | 1741 | } |
1745 | pnfs_set_layout_stateid(lo, &res->stateid, false); | 1742 | pnfs_set_layout_stateid(lo, &res->stateid, false); |
1746 | } else { | 1743 | } else { |
@@ -1766,14 +1763,12 @@ pnfs_layout_process(struct nfs4_layoutget *lgp) | |||
1766 | spin_unlock(&ino->i_lock); | 1763 | spin_unlock(&ino->i_lock); |
1767 | pnfs_free_lseg_list(&free_me); | 1764 | pnfs_free_lseg_list(&free_me); |
1768 | return lseg; | 1765 | return lseg; |
1769 | out: | ||
1770 | return ERR_PTR(status); | ||
1771 | 1766 | ||
1772 | out_forget_reply: | 1767 | out_forget: |
1773 | spin_unlock(&ino->i_lock); | 1768 | spin_unlock(&ino->i_lock); |
1774 | lseg->pls_layout = lo; | 1769 | lseg->pls_layout = lo; |
1775 | NFS_SERVER(ino)->pnfs_curr_ld->free_lseg(lseg); | 1770 | NFS_SERVER(ino)->pnfs_curr_ld->free_lseg(lseg); |
1776 | goto out; | 1771 | return ERR_PTR(-EAGAIN); |
1777 | } | 1772 | } |
1778 | 1773 | ||
1779 | static void | 1774 | static void |