Re: [PATCH] pnfs/blocklayout: put deviceid node after releasing bl_ext_lock

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hi Ben,

> On Jun 10, 2016, at 16:37, Benjamin Coddington <bcodding@xxxxxxxxxx> wrote:
> 
> The last put of deviceid nodes for SCSI layouts may sleep, so we shouldn't
> hold any spinlocks.  Make sure we put them outside the bl_ext_lock.
> 
> Signed-off-by: Benjamin Coddington <bcodding@xxxxxxxxxx>
> ---
> fs/nfs/blocklayout/extent_tree.c | 27 +++++++++++++++++++++------
> 1 file changed, 21 insertions(+), 6 deletions(-)
> 
> diff --git a/fs/nfs/blocklayout/extent_tree.c b/fs/nfs/blocklayout/extent_tree.c
> index 720b3ff55fa9..992bcb19c11e 100644
> --- a/fs/nfs/blocklayout/extent_tree.c
> +++ b/fs/nfs/blocklayout/extent_tree.c
> @@ -121,6 +121,16 @@ ext_try_to_merge_right(struct rb_root *root, struct pnfs_block_extent *be)
> 	return be;
> }
> 
> +static void __ext_put_deviceids(struct list_head *head)
> +{
> +	struct pnfs_block_extent *be, *tmp;
> +
> +	list_for_each_entry_safe(be, tmp, head, be_list) {
> +		nfs4_put_deviceid_node(be->be_device);
> +		kfree(be);
> +	}

This definitely needs a list_del()… I only noticed this morning after hunting for the OOM that Christoph says turned up after this weekend.

> +}
> +
> static void
> __ext_tree_insert(struct rb_root *root,
> 		struct pnfs_block_extent *new, bool merge_ok)
> @@ -163,7 +173,8 @@ free_new:
> }
> 
> static int
> -__ext_tree_remove(struct rb_root *root, sector_t start, sector_t end)
> +__ext_tree_remove(struct rb_root *root,
> +		sector_t start, sector_t end, struct list_head *tmp)
> {
> 	struct pnfs_block_extent *be;
> 	sector_t len1 = 0, len2 = 0;
> @@ -223,8 +234,7 @@ __ext_tree_remove(struct rb_root *root, sector_t start, sector_t end)
> 			struct pnfs_block_extent *next = ext_tree_next(be);
> 
> 			rb_erase(&be->be_node, root);
> -			nfs4_put_deviceid_node(be->be_device);
> -			kfree(be);
> +			list_add_tail(&be->be_list, tmp);
> 			be = next;
> 		}
> 
> @@ -350,16 +360,18 @@ int ext_tree_remove(struct pnfs_block_layout *bl, bool rw,
> 		sector_t start, sector_t end)
> {
> 	int err, err2;
> +	LIST_HEAD(tmp);
> 
> 	spin_lock(&bl->bl_ext_lock);
> -	err = __ext_tree_remove(&bl->bl_ext_ro, start, end);
> +	err = __ext_tree_remove(&bl->bl_ext_ro, start, end, &tmp);
> 	if (rw) {
> -		err2 = __ext_tree_remove(&bl->bl_ext_rw, start, end);
> +		err2 = __ext_tree_remove(&bl->bl_ext_rw, start, end, &tmp);
> 		if (!err)
> 			err = err2;
> 	}
> 	spin_unlock(&bl->bl_ext_lock);
> 
> +	__ext_put_deviceids(&tmp);
> 	return err;
> }
> 
> @@ -396,12 +408,13 @@ ext_tree_mark_written(struct pnfs_block_layout *bl, sector_t start,
> 	sector_t end = start + len;
> 	struct pnfs_block_extent *be;
> 	int err = 0;
> +	LIST_HEAD(tmp);
> 
> 	spin_lock(&bl->bl_ext_lock);
> 	/*
> 	 * First remove all COW extents or holes from written to range.
> 	 */
> -	err = __ext_tree_remove(&bl->bl_ext_ro, start, end);
> +	err = __ext_tree_remove(&bl->bl_ext_ro, start, end, &tmp);
> 	if (err)
> 		goto out;
> 
> @@ -459,6 +472,8 @@ ext_tree_mark_written(struct pnfs_block_layout *bl, sector_t start,
> 	}
> out:
> 	spin_unlock(&bl->bl_ext_lock);
> +
> +	__ext_put_deviceids(&tmp);
> 	return err;
> }
> 
> -- 
> 2.5.5
> 
> --
> To unsubscribe from this list: send the line "unsubscribe linux-nfs" in
> the body of a message to majordomo@xxxxxxxxxxxxxxx
> More majordomo info at  http://vger.kernel.org/majordomo-info.html
> 

--
To unsubscribe from this list: send the line "unsubscribe linux-nfs" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html



[Index of Archives]     [Linux Filesystem Development]     [Linux USB Development]     [Linux Media Development]     [Video for Linux]     [Linux NILFS]     [Linux Audio Users]     [Yosemite Info]     [Linux SCSI]

  Powered by Linux