All of lore.kernel.org
 help / color / mirror / Atom feed
From: Jun'ichi Nomura <j-nomura@ce.jp.nec.com>
To: lvm-devel@redhat.com
Subject: [PATCH vgsplit 2/4] Update vgsplit to allow a list of LVs or PVs on the commandline.
Date: Mon, 24 Mar 2008 21:11:23 -0400	[thread overview]
Message-ID: <47E8513B.1000502@ce.jp.nec.com> (raw)
In-Reply-To: <20080324202437.539525068@redhat.com>

Hi Dave,

I quickly looked through the patch.
Please see comments below.

> Add some helper functions to allow vgsplit to continue in more cases.
> Introduce "related volumes" concept, as defined in the comments below.
> 
> 
> --- a/lib/metadata/metadata-exported.h
> +++ b/lib/metadata/metadata-exported.h
> @@ -151,6 +151,9 @@ struct pv_segment {
>  	uint32_t lv_area;	/* Index to area in LV segment */
>  };
>  
> +#define pvseg_is_allocated(pvseg) (pvseg->lvseg)
> +#define pvseg_is_free(pvseg) (!pvseg_is_allocated(pvseg))

Macro parameters should be surrounded by ().
#define pvseg_is_allocated(pvseg) ((pvseg)->lvseg)
#define pvseg_is_free(pvseg) (!pvseg_is_allocated((pvseg)))

> +struct related_volumes {
> +	struct volume_group *vg;
> +	struct list ll; /* struct lv_list */
> +	struct list pl; /* struct pv_list */
> +};

I think 'lvs' and 'pvs' are more descriptive.

struct related_volumes {
	struct volume_group *vg;
	struct list lvs; /* struct lv_list */
	struct list pvs; /* struct pv_list */
};

> +void pv_add_related_volume(struct related_volumes *rvs, struct pv_list *pvl);
> +void lv_add_related_volume(struct related_volumes *rvs, struct lv_list *lvl);

On the analogy of other function names in LVM2,
these sound like 'adding "related volume" to pv/lv'.

What these functions actually do is collecting related volumes for
given LV/PV and adding them to rvs.
How about collect_related_volumes_for_{pv,lv} or collect_rvs_for_{pv,lv}?

Or IOW, the functions add given PV/LV (and its relatives) to rvs.
So add_{pv,lv}_to_related_volumes() might be good as well.


> +static void _move_pv(struct volume_group *vg_from, struct volume_group *vg_to,
> +		     struct pv_list *pvl)
> +{
> +	struct physical_volume *pv;
> +
> +	list_del(&pvl->list);
> +	list_add(&vg_to->pvs, &pvl->list);

Since this del-and-add logic appears many times through this patch,
how about adding list_move() to lib/datastruct/list.h?

static inline list_move(struct list *item, struct list *head)
{
	list_del(item);
	list_add(head, item);
}

> +	pv = list_item(pvl, struct pv_list)->pv;

This is a bug, though it works with luck by struct pv_list layout.
It should be:
  pv = pvl->pv;

Not a problem of this patch, as it exists in the original code.

> +static int find_in_pv_list(const struct list *pl,
> +			   const struct physical_volume *pv)

I think other find_* functions in LVM2 returns what it finds.
Also, names of static functions tend to start with '_'.

So how about _find_pv_in_pv_list() and return a pointer to
the matched pvl otherwise NULL?
Or _pv_is_in_pv_list(), if the matched pvl has no use.

> +{
> +	const struct pv_list *pvl;
> +
> +	list_iterate_items(pvl, pl)
> +		if (pvl->pv == pv)
> +			return 1;
> +	return 0;
> +}

_add_pvs() in lib/metadata/lv_manip.c can use this function, too.


> +static int find_in_lv_list(const struct list *ll,
> +			   const struct logical_volume *lv)

Ditto about the naming.

> +static void add_related_pv(struct related_volumes *rvs,
> +			   const struct physical_volume *pv)
...
> +static void add_related_lv(struct related_volumes *rvs,
> +			   const struct logical_volume *lv)
...
> +static void add_related_segment(struct related_volumes *rvs,
> +				const struct lv_segment *lvseg)

These names sound like 'adding given pv/lv/lvseg to rvs'.
but actually are 'adding related volumes for pv/lv/lvseg to rvs'.
So similar renaming as pv_add_related_volume() would be nice, IMO.

> +	if (!list_empty(&lvseg->lv->segs_using_this_lv)) {
> +		lvseg2 = get_only_segment_using_this_lv(lvseg->lv);
> +		if (lvseg2)
> +			add_related_segment(rvs, lvseg2);
> +	}

First, I think this part should be moved to lv_find_related_volumes()
because segs_using_this_lv is a property of lv, not lvseg.

Second, you should walk through segs_using_this_lv, instead of
using get_only_segment_using_this_lv(). e.g. "pvmove" LV may be used by
multiple lvsegs.

> @@ -302,28 +146,64 @@ int vgsplit(struct cmd_context *cmd, int argc, char **argv)
...
> +	init_related_volumes(&rvs, vg_from);
> +	lv_count_cmdline = 0;
> +	pv_count_cmdline = 0;
> +	for (opt = 0; opt < argc; opt++) {
> +		/* FIXME: handle tags */
> +		if ((lvl = find_lv_in_vg(vg_from, argv[opt]))) {
> +			lv_count_cmdline++;
> +			lv_add_related_volume(&rvs, lvl);
> +		} else if ((pvl = find_pv_in_vg(vg_from, argv[opt]))) {
> +			pv_count_cmdline++;
> +			pv_add_related_volume(&rvs, pvl);
> +		}
>  	}
>  
> -	/* Move required LVs across, checking consistency */
> -	if (!(_move_lvs(vg_from, vg_to)))
> -		goto error;
> +	/*
> +	 * Now that we have the lists of all PVs and LVs involved in the
> +	 * split, check if this list contains PVs or LVs above what the user
> +	 * requested.  If so, ask for confirmation before continuing, as this
> +	 * is most likely what the user would expect.
> +	 */
> +	if ( ((pv_count_cmdline && list_size(&rvs.pl) > pv_count_cmdline) ||
> +	      (lv_count_cmdline && list_size(&rvs.ll) > lv_count_cmdline)) &&
> +	     !arg_count(cmd, force_ARG) ) {
> +		if (!confirm_vgsplit(&rvs.ll, &rvs.pl))
> +			goto error;
> +	}

The above condition won't work as expected if specified LV is composed
of some hidden LVs, e.g. mirror?

Thanks,
-- 
Jun'ichi Nomura, NEC Corporation of America




  reply	other threads:[~2008-03-25  1:11 UTC|newest]

Thread overview: 7+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2008-03-24 20:23 [PATCH vgsplit 0/4] bz#251990: Move logical volume from one VG to another dwysocha
2008-03-24 20:23 ` [PATCH vgsplit 1/4] Add is_reserved_name() helper function dwysocha
2008-03-25  1:18   ` Jun'ichi Nomura
2008-03-24 20:23 ` [PATCH vgsplit 2/4] Update vgsplit to allow a list of LVs or PVs on the commandline dwysocha
2008-03-25  1:11   ` Jun'ichi Nomura [this message]
2008-03-24 20:23 ` [PATCH vgsplit 3/4] Update vgsplit man page to allow LVs or PVs on the cmdline dwysocha
2008-03-24 20:23 ` [PATCH vgsplit 4/4] Update vgsplit tests to cover LVs " dwysocha

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=47E8513B.1000502@ce.jp.nec.com \
    --to=j-nomura@ce.jp.nec.com \
    --cc=lvm-devel@redhat.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.