[pnfs] [PATCH 19/37] pnfs: client layout cache: allow waiting for alloc_layout

Dean Hildebrand seattleplus at gmail.com
Wed Jan 2 18:54:34 EST 2008


>  /*
>   * get, possibly allocate current_layout
>   */
> @@ -442,14 +450,32 @@ get_alloc_layout(struct inode *ino,
>  {
>  	struct nfs_inode *nfsi = NFS_I(ino);
>  	struct pnfs_layout_type *lo;
> +	int res;
>  
>  	dprintk("%s Begin\n", __FUNCTION__);
>  
> +retry:
>  	lo = nfsi->current_layout;
>  	if (lo)
>  		goto out;
>  
> +	res = wait_on_bit_lock(&nfsi->pnfs_layout_state, NFS_INO_LAYOUT_ALLOC,
> +			       pnfs_wait_schedule, TASK_INTERRUPTIBLE);
> +	if (res) {
> +		lo = ERR_PTR(res);
> +		goto err;
> +	}
> +
> +	if (nfsi->current_layout) {
> +		clear_bit_unlock(NFS_INO_LAYOUT_ALLOC,
> +				 &nfsi->pnfs_layout_state);
> +		goto retry;
> +	}
> +
>  	lo = nfsi->current_layout = alloc_init_layout(ino, io_ops);
> +	clear_bit_unlock(NFS_INO_LAYOUT_ALLOC, &nfsi->pnfs_layout_state);
> +	wake_up_bit(&nfsi->pnfs_layout_state, NFS_INO_LAYOUT_ALLOC);
> +
>   
This function seems a little muddled (or maybe some comments would 
help).  I've never been a fan of backward gotos.  Would something like 
the following be any less correct or inefficient?  Actually, if the 
following code works, could we just use a spinlock instead?  Are we just 
protecting nfsi->current_layout?

	res = wait_on_bit_lock(&nfsi->pnfs_layout_state, NFS_INO_LAYOUT_ALLOC,
			       pnfs_wait_schedule, TASK_INTERRUPTIBLE);

	if (res) {
		lo = ERR_PTR(res);
		goto err;
	}

	if (nfsi->current_layout) {
		clear_bit_unlock(NFS_INO_LAYOUT_ALLOC,
				 &nfsi->pnfs_layout_state);
		wake_up_bit(&nfsi->pnfs_layout_state, NFS_INO_LAYOUT_ALLOC);

		goto out;
	}

 	lo = nfsi->current_layout = alloc_init_layout(ino, io_ops);
	clear_bit_unlock(NFS_INO_LAYOUT_ALLOC, &nfsi->pnfs_layout_state);
	wake_up_bit(&nfsi->pnfs_layout_state, NFS_INO_LAYOUT_ALLOC);


Dean
>  	if (!lo) {
>  		lo = ERR_PTR(-ENOMEM);
>  		goto err;
> diff --git a/include/linux/nfs_fs.h b/include/linux/nfs_fs.h
> index 3d6bfbf..1a093b1 100644
> --- a/include/linux/nfs_fs.h
> +++ b/include/linux/nfs_fs.h
> @@ -178,7 +178,9 @@ struct nfs_inode {
>  #if defined(CONFIG_PNFS)
>  	unsigned long pnfs_layout_state;
>  #define NFS_INO_LAYOUT_FAILED	0x0001	/* get layout failed, stop trying */
> +#define NFS_INO_LAYOUT_ALLOC	0x0002	/* get layout failed, stop trying */
>  	time_t pnfs_layout_suspend;
> +	wait_queue_head_t lo_waitq;
>  	struct pnfs_layout_type *current_layout;
>  	/* use rpc_creds in this open_context to send LAYOUTCOMMIT to MDS */
>  	struct nfs_open_context *layoutcommit_ctx;
>   


More information about the pNFS mailing list