1
0
mirror of git://sourceware.org/git/lvm2.git synced 2024-12-21 13:34:40 +03:00

Allow mirror images to be resized.

This commit is contained in:
Alasdair Kergon 2005-06-03 19:48:19 +00:00
parent c77de77790
commit ffb0e5387b
5 changed files with 79 additions and 10 deletions

View File

@ -1,5 +1,6 @@
Version 2.01.11 - Version 2.01.11 -
============================== ==============================
Allow mirror images to be resized.
Allow mirror images to have more than one segment. Allow mirror images to have more than one segment.
Centralise restrictions on LV names. Centralise restrictions on LV names.
Always insert an intermediate layer for mirrors. Always insert an intermediate layer for mirrors.

View File

@ -300,7 +300,7 @@ static struct alloc_handle *_alloc_init(struct pool *mem,
uint32_t s, area_count; uint32_t s, area_count;
if (stripes > 1 && mirrors > 1) { if (stripes > 1 && mirrors > 1) {
log_error("striped mirrors are not supported yet"); log_error("Striped mirrors are not supported yet");
return NULL; return NULL;
} }
@ -980,7 +980,9 @@ int lv_extend(struct logical_volume *lv,
alloc_policy_t alloc) alloc_policy_t alloc)
{ {
int r = 1; int r = 1;
uint32_t m;
struct alloc_handle *ah; struct alloc_handle *ah;
struct lv_segment *first_seg;
if (segtype_is_virtual(segtype)) if (segtype_is_virtual(segtype))
return lv_add_virtual_segment(lv, status, extents, segtype); return lv_add_virtual_segment(lv, status, extents, segtype);
@ -992,11 +994,30 @@ int lv_extend(struct logical_volume *lv,
return 0; return 0;
} }
if (!mirrors) {
if (!lv_add_segment(ah, 0, ah->area_count, lv, segtype, stripe_size, if (!lv_add_segment(ah, 0, ah->area_count, lv, segtype, stripe_size,
mirrored_pv, mirrored_pe, status, 0, NULL)) { mirrored_pv, mirrored_pe, status, 0, NULL)) {
stack; stack;
goto out; goto out;
} }
} else {
list_iterate_items(first_seg, &lv->segments)
break;
for (m = 0; m < mirrors; m++) {
if (!lv_add_segment(ah, m, 1, seg_lv(first_seg, m),
get_segtype_from_string(lv->vg->cmd,
"striped"),
0, NULL, 0, 0, 0, NULL)) {
log_error("Aborting. Failed to extend %s.",
seg_lv(first_seg, m)->name);
return 0;
}
}
first_seg->area_len += extents;
first_seg->len += extents;
lv->le_count += extents;
lv->size += (uint64_t) extents *lv->vg->extent_size;
}
out: out:
alloc_destroy(ah); alloc_destroy(ah);

View File

@ -178,6 +178,7 @@ xx(lvextend,
"\t[-i|--stripes Stripes [-I|--stripesize StripeSize]]\n" "\t[-i|--stripes Stripes [-I|--stripesize StripeSize]]\n"
"\t{-l|--extents [+]LogicalExtentsNumber |\n" "\t{-l|--extents [+]LogicalExtentsNumber |\n"
"\t -L|--size [+]LogicalVolumeSize[kKmMgGtT]}\n" "\t -L|--size [+]LogicalVolumeSize[kKmMgGtT]}\n"
"\t[-m|--mirrors Mirrors]\n"
"\t[-n|--nofsck]\n" "\t[-n|--nofsck]\n"
"\t[-r|--resizefs]\n" "\t[-r|--resizefs]\n"
"\t[-t|--test]\n" "\t[-t|--test]\n"
@ -186,8 +187,9 @@ xx(lvextend,
"\t[--version]" "\n" "\t[--version]" "\n"
"\tLogicalVolume[Path] [ PhysicalVolumePath... ]\n", "\tLogicalVolume[Path] [ PhysicalVolumePath... ]\n",
alloc_ARG, autobackup_ARG, extents_ARG, nofsck_ARG, resizefs_ARG, alloc_ARG, autobackup_ARG, extents_ARG, mirrors_ARG, nofsck_ARG,
size_ARG, stripes_ARG, stripesize_ARG, test_ARG, type_ARG) resizefs_ARG, size_ARG, stripes_ARG, stripesize_ARG, test_ARG,
type_ARG)
xx(lvmchange, xx(lvmchange,
"With the device mapper, this is obsolete and does nothing.", "With the device mapper, this is obsolete and does nothing.",

View File

@ -497,6 +497,11 @@ static int _lvcreate(struct cmd_context *cmd, struct lvcreate_params *lp)
return 0; return 0;
} }
if (lp->mirrors && !(vg->fid->fmt->features & FMT_SEGMENTS)) {
log_error("Metadata does not support mirroring.");
return 0;
}
/* /*
* Create the pv list. * Create the pv list.
*/ */

View File

@ -23,6 +23,7 @@ struct lvresize_params {
uint32_t stripes; uint32_t stripes;
uint32_t stripe_size; uint32_t stripe_size;
uint32_t mirrors;
struct segment_type *segtype; struct segment_type *segtype;
@ -119,6 +120,7 @@ static int _lvresize(struct cmd_context *cmd, struct lvresize_params *lp)
struct lvinfo info; struct lvinfo info;
uint32_t stripesize_extents = 0; uint32_t stripesize_extents = 0;
uint32_t seg_stripes = 0, seg_stripesize = 0, seg_size = 0; uint32_t seg_stripes = 0, seg_stripesize = 0, seg_size = 0;
uint32_t seg_mirrors = 0;
uint32_t extents_used = 0; uint32_t extents_used = 0;
uint32_t size_rest; uint32_t size_rest;
alloc_policy_t alloc; alloc_policy_t alloc;
@ -161,6 +163,13 @@ static int _lvresize(struct cmd_context *cmd, struct lvresize_params *lp)
log_print("Varied striping not supported. Ignoring."); log_print("Varied striping not supported. Ignoring.");
} }
if (arg_count(cmd, mirrors_ARG)) {
if (vg->fid->fmt->features & FMT_SEGMENTS)
lp->mirrors = arg_uint_value(cmd, mirrors_ARG, 1) + 1;
else
log_print("Mirrors not supported. Ignoring.");
}
if (arg_count(cmd, stripesize_ARG)) { if (arg_count(cmd, stripesize_ARG)) {
if (arg_sign_value(cmd, stripesize_ARG, 0) == SIGN_MINUS) { if (arg_sign_value(cmd, stripesize_ARG, 0) == SIGN_MINUS) {
log_error("Stripesize may not be negative."); log_error("Stripesize may not be negative.");
@ -171,6 +180,10 @@ static int _lvresize(struct cmd_context *cmd, struct lvresize_params *lp)
stripesize_ARG, 0); stripesize_ARG, 0);
else else
log_print("Varied stripesize not supported. Ignoring."); log_print("Varied stripesize not supported. Ignoring.");
if (lp->mirrors) {
log_error("Mirrors and striping cannot be combined yet.");
return ECMD_FAILED;
}
} }
lv = lvl->lv; lv = lvl->lv;
@ -277,13 +290,34 @@ static int _lvresize(struct cmd_context *cmd, struct lvresize_params *lp)
} }
} }
/* If extending, find mirrors of last segment */
if ((lp->extents > lv->le_count)) {
list_iterate_back_items(seg, &lv->segments) {
if (seg_is_mirrored(seg))
seg_mirrors = seg->area_count;
else
seg_mirrors = 0;
break;
}
if (!arg_count(cmd, mirrors_ARG) && seg_mirrors) {
log_print("Extending %" PRIu32 " mirror images.",
seg_mirrors);
lp->mirrors = seg_mirrors;
}
if ((arg_count(cmd, mirrors_ARG) || seg_mirrors) &&
(lp->mirrors != seg_mirrors)) {
log_error("Cannot vary number of mirrors in LV yet.");
return EINVALID_CMD_LINE;
}
}
/* If reducing, find stripes, stripesize & size of last segment */ /* If reducing, find stripes, stripesize & size of last segment */
if (lp->extents < lv->le_count) { if (lp->extents < lv->le_count) {
extents_used = 0; extents_used = 0;
if (lp->stripes || lp->stripe_size) if (lp->stripes || lp->stripe_size || lp->mirrors)
log_error("Ignoring stripes and stripesize arguments " log_error("Ignoring stripes, stripesize and mirrors "
"when reducing"); "arguments when reducing");
list_iterate_items(seg, &lv->segments) { list_iterate_items(seg, &lv->segments) {
seg_extents = seg->len; seg_extents = seg->len;
@ -293,6 +327,11 @@ static int _lvresize(struct cmd_context *cmd, struct lvresize_params *lp)
seg_stripes = seg->area_count; seg_stripes = seg->area_count;
} }
if (seg_is_mirrored(seg))
seg_mirrors = seg->area_count;
else
seg_mirrors = 0;
if (lp->extents <= extents_used + seg_extents) if (lp->extents <= extents_used + seg_extents)
break; break;
@ -302,6 +341,7 @@ static int _lvresize(struct cmd_context *cmd, struct lvresize_params *lp)
seg_size = lp->extents - extents_used; seg_size = lp->extents - extents_used;
lp->stripe_size = seg_stripesize; lp->stripe_size = seg_stripesize;
lp->stripes = seg_stripes; lp->stripes = seg_stripes;
lp->mirrors = seg_mirrors;
} }
if (lp->stripes > 1 && !lp->stripe_size) { if (lp->stripes > 1 && !lp->stripe_size) {
@ -456,7 +496,7 @@ static int _lvresize(struct cmd_context *cmd, struct lvresize_params *lp)
return ECMD_FAILED; return ECMD_FAILED;
} }
} else if (!lv_extend(lv, lp->segtype, lp->stripes, } else if (!lv_extend(lv, lp->segtype, lp->stripes,
lp->stripe_size, 0u, lp->stripe_size, lp->mirrors,
lp->extents - lv->le_count, lp->extents - lv->le_count,
NULL, 0u, 0u, pvh, alloc)) { NULL, 0u, 0u, pvh, alloc)) {
stack; stack;