1
0
mirror of git://sourceware.org/git/lvm2.git synced 2024-10-27 18:55:19 +03:00

raid: conditionally reject convert to striped/raid0*

If SubLVs to be removed still exist after an image removing
conversion (i.e. "lvconvert --yes --force --stripes N "
with N < total stripes) any request to convert to a different
striped/raid* level has to be rejected until after those freed
SubLVs got removed by running the aforementioned lvconvert again.

Add tests to check conversion to striped/raid* gets rejected.
Enhance a test comment.

Related: rhbz1191935
Related: rhbz1366296
This commit is contained in:
Heinz Mauelshagen 2017-03-17 13:58:54 +01:00
parent 5e7bc8d854
commit 17bee733d1
2 changed files with 53 additions and 15 deletions

View File

@ -171,6 +171,33 @@ char *top_level_lv_name(struct volume_group *vg, const char *lv_name)
return new_lv_name;
}
/* Get available and removed SubLVs for @lv */
static int _get_available_removed_sublvs(const struct logical_volume *lv, uint32_t *available_slvs, uint32_t *removed_slvs)
{
uint32_t s;
struct lv_segment *seg = first_seg(lv);
*available_slvs = 0;
*removed_slvs = 0;
if (!lv_is_raid(lv))
return 1;
for (s = 0; s < seg->area_count; s++) {
struct logical_volume *slv;
if (seg_type(seg, s) != AREA_LV || !(slv = seg_lv(seg, s))) {
log_error(INTERNAL_ERROR "Missing image sub lv in area %" PRIu32 " of LV %s.",
s, display_lvname(lv));
return_0;
}
(slv->status & LV_REMOVE_AFTER_RESHAPE) ? (*removed_slvs)++ : (*available_slvs)++;
}
return 1;
}
static int _lv_is_raid_with_tracking(const struct logical_volume *lv,
struct logical_volume **tracking)
{
@ -1916,19 +1943,8 @@ static int _raid_reshape_remove_images(struct logical_volume *lv,
* -> remove the freed up images and reduce LV size
*
*/
for (active_lvs = removed_lvs = s = 0; s < seg->area_count; s++) {
struct logical_volume *slv;
if (!seg_lv(seg, s) || !(slv = seg_lv(seg, s))) {
log_error("Missing image sub lv off LV %s.", display_lvname(lv));
return 0;
}
if (slv->status & LV_REMOVE_AFTER_RESHAPE)
removed_lvs++;
else
active_lvs++;
}
if (!_get_available_removed_sublvs(lv, &active_lvs, &removed_lvs))
return_0;
if (devs_in_sync != new_image_count) {
log_error("No correct kernel/lvm active LV count on %s.", display_lvname(lv));
@ -5965,6 +5981,7 @@ int lv_raid_convert(struct logical_volume *lv,
uint32_t new_image_count = seg->area_count;
uint32_t region_size = new_region_size;
uint32_t data_copies = seg->data_copies;
uint32_t available_slvs, removed_slvs;
takeover_fn_t takeover_fn;
new_segtype = new_segtype ? : seg->segtype;
@ -6016,6 +6033,17 @@ int lv_raid_convert(struct logical_volume *lv,
return 0;
}
/* Prohibit any takeover in case sub LVs to be removed still exist after a previous reshape */
if (_get_available_removed_sublvs(lv, &available_slvs, &removed_slvs))
return 0;
if (removed_slvs) {
log_error("Can't convert %s LV %s to %s containing sub LVs to remove after a reshape.",
lvseg_name(seg), display_lvname(lv), new_segtype->name);
log_error("Run \"lvconvert --stripes %" PRIu32 " %s\" first.",
seg->area_count - removed_slvs - 1, display_lvname(lv));
return 0;
}
/*
* Check acceptible options mirrors, region_size,
* stripes and/or stripe_size have been provided.

View File

@ -110,7 +110,7 @@ aux wait_for_sync $vg $lv1
_reshape_layout raid5_ls 3 4 $vg $lv1 --stripesize 256K
check lv_first_seg_field $vg/$lv1 stripesize "256.00k"
# Convert raid5(_n) -> striped
# Convert raid5(_n) -> striped testing raid5_ls gets rejected
not _lvconvert striped striped 3 3 $vg $lv1 512k
_reshape_layout raid5_n 3 4 $vg $lv1
_lvconvert striped striped 3 3 $vg $lv1
@ -144,8 +144,18 @@ _reshape_layout raid5_ls 63 64 $vg $lv1 --stripes 63
_reshape_layout raid5_ls 27 64 $vg $lv1 --stripes 27 --force
_reshape_layout raid5_ls 27 28 $vg $lv1 --stripes 27
# Convert raid5_ls back to 4 stripes
# Convert raid5_ls back to 4 stripes checking
# conversion to striped/raid* gets rejected
# with existing LVs to be removed afer reshape
_reshape_layout raid5_ls 4 28 $vg $lv1 --stripes 4 --force
# No we got the data reshaped and the freed SubLVs still present
# -> check takeover request gets rejected
not lvconvert --yes --type striped $vg/$lv1
not lvconvert --yes --type raid0 $vg/$lv1
not lvconvert --yes --type raid0_meta $vg/$lv1
not lvconvert --yes --type raid6 $vg/$lv1
# Remove the freed SubLVs
_reshape_layout raid5_ls 4 5 $vg $lv1 --stripes 4
# Convert raid5_ls back to 3 stripes