summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid Teigland <teigland@redhat.com>2020-02-18 16:09:34 -0600
committerDavid Teigland <teigland@redhat.com>2020-02-18 16:09:34 -0600
commit1da3fa71fcdf58f9de5249655a41cf0897d5ac23 (patch)
treec35503fd682985599bb6cd7c82248911bbdd76d0
parent449187f18a61576abe13c36016908d509bf9aac1 (diff)
downloadlvm2-dev-dct-integrity24.tar.gz
integrity: convert linear+integrity to raid1+integritydev-dct-integrity24
-rwxr-xr-xconfigure27
-rw-r--r--lib/metadata/integrity_manip.c30
-rw-r--r--lib/metadata/lv_manip.c6
-rw-r--r--lib/metadata/metadata-exported.h9
-rw-r--r--tools/lvconvert.c47
5 files changed, 95 insertions, 24 deletions
diff --git a/configure b/configure
index 6dd7edac3..716ee9ca7 100755
--- a/configure
+++ b/configure
@@ -918,6 +918,7 @@ enable_cache_check_needs_check
with_vdo
with_vdo_format
with_writecache
+with_integrity
enable_readline
enable_realtime
enable_ocf
@@ -1716,6 +1717,7 @@ Optional Packages:
--with-vdo=TYPE vdo support: internal/none [internal]
--with-vdo-format=PATH vdoformat tool: [autodetect]
--with-writecache=TYPE writecache support: internal/none [none]
+ --with-integrity=TYPE integrity support: internal/none [none]
--with-ocfdir=DIR install OCF files in
[PREFIX/lib/ocf/resource.d/lvm2]
--with-default-pid-dir=PID_DIR
@@ -9762,6 +9764,31 @@ $as_echo "#define WRITECACHE_INTERNAL 1" >>confdefs.h
esac
################################################################################
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to include integrity" >&5
+$as_echo_n "checking whether to include integrity... " >&6; }
+
+# Check whether --with-integrity was given.
+if test "${with_integrity+set}" = set; then :
+ withval=$with_integrity; INTEGRITY=$withval
+else
+ INTEGRITY="none"
+fi
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $INTEGRITY" >&5
+$as_echo "$INTEGRITY" >&6; }
+
+case "$INTEGRITY" in
+ none) ;;
+ internal)
+
+$as_echo "#define INTEGRITY_INTERNAL 1" >>confdefs.h
+
+ ;;
+ *) as_fn_error $? "--with-integrity parameter invalid" "$LINENO" 5 ;;
+esac
+
+################################################################################
# Check whether --enable-readline was given.
if test "${enable_readline+set}" = set; then :
enableval=$enable_readline; READLINE=$enableval
diff --git a/lib/metadata/integrity_manip.c b/lib/metadata/integrity_manip.c
index df734d95c..f83b9c8c8 100644
--- a/lib/metadata/integrity_manip.c
+++ b/lib/metadata/integrity_manip.c
@@ -336,7 +336,7 @@ int lv_remove_integrity_from_raid(struct logical_volume *lv)
return 1;
}
-int lv_remove_integrity(struct logical_volume *lv)
+int lv_remove_integrity(struct logical_volume *lv, struct logical_volume **keep_lv_imeta)
{
struct cmd_context *cmd = lv->vg->cmd;
struct volume_group *vg = lv->vg;
@@ -394,7 +394,9 @@ int lv_remove_integrity(struct logical_volume *lv)
if (!lv_remove(lv_iorig))
log_error("Failed to remove unused iorig LV %s.", lv_iorig->name);
- if (!lv_remove(lv_imeta))
+ if (keep_lv_imeta)
+ *keep_lv_imeta = lv_imeta;
+ else if (!lv_remove(lv_imeta))
log_error("Failed to remove unused imeta LV %s.", lv_imeta->name);
if (!vg_write(vg) || !vg_commit(vg))
@@ -434,10 +436,10 @@ int lv_remove_integrity(struct logical_volume *lv)
*
*/
-int lv_add_integrity_to_raid(struct logical_volume *lv, const char *arg,
- struct integrity_settings *settings,
- struct dm_list *pvh)
+int lv_add_integrity_to_raid(struct logical_volume *lv, struct integrity_settings *settings,
+ struct dm_list *pvh, struct logical_volume *lv_imeta_0)
{
+ char imeta0_name[NAME_LEN];
struct lvcreate_params lp;
struct dm_list allocatable_pvs;
struct logical_volume *imeta_lvs[DEFAULT_RAID_MAX_IMAGES];
@@ -495,6 +497,21 @@ int lv_add_integrity_to_raid(struct logical_volume *lv, const char *arg,
goto_bad;
}
+ /*
+ * Use an existing lv_imeta from previous linear+integrity LV.
+ * FIXME: is it guaranteed that lv_image_0 is the existing?
+ */
+ if (!s && lv_imeta_0) {
+ if (dm_snprintf(imeta0_name, sizeof(imeta0_name), "%s_imeta", lv_image->name) < 0) {
+ /* fixme */
+ }
+ if (!lv_rename_update(cmd, lv_imeta_0, imeta0_name, 0)) {
+ /* fixme */
+ }
+ imeta_lvs[0] = lv_imeta_0;
+ continue;
+ }
+
dm_list_init(&allocatable_pvs);
if (!get_pv_list_for_lv(cmd->mem, lv_image, &allocatable_pvs)) {
@@ -659,8 +676,7 @@ bad:
return 0;
}
-int lv_add_integrity(struct logical_volume *lv, const char *arg,
- struct integrity_settings *settings,
+int lv_add_integrity(struct logical_volume *lv, struct integrity_settings *settings,
struct dm_list *pvh)
{
struct lvcreate_params lp = { 0 };
diff --git a/lib/metadata/lv_manip.c b/lib/metadata/lv_manip.c
index 30ab7f145..989c9486b 100644
--- a/lib/metadata/lv_manip.c
+++ b/lib/metadata/lv_manip.c
@@ -8340,12 +8340,10 @@ static struct logical_volume *_lv_create_an_lv(struct volume_group *vg,
log_debug("Adding integrity to new LV");
if (seg_is_raid(lp)) {
- if (!lv_add_integrity_to_raid(lv, lp->integrity_arg,
- &lp->integrity_settings, lp->pvh))
+ if (!lv_add_integrity_to_raid(lv, &lp->integrity_settings, lp->pvh, NULL))
goto revert_new_lv;
} else {
- if (!lv_add_integrity(lv, lp->integrity_arg,
- &lp->integrity_settings, lp->pvh))
+ if (!lv_add_integrity(lv, &lp->integrity_settings, lp->pvh))
goto revert_new_lv;
}
diff --git a/lib/metadata/metadata-exported.h b/lib/metadata/metadata-exported.h
index 954d494f2..d96eec101 100644
--- a/lib/metadata/metadata-exported.h
+++ b/lib/metadata/metadata-exported.h
@@ -1406,11 +1406,10 @@ struct dm_list *create_pv_list(struct dm_pool *mem, struct volume_group *vg, int
char **argv, int allocatable_only);
struct dm_list *clone_pv_list(struct dm_pool *mem, struct dm_list *pvsl);
-int lv_add_integrity(struct logical_volume *lv, const char *arg,
- struct integrity_settings *settings, struct dm_list *pvh);
-int lv_add_integrity_to_raid(struct logical_volume *lv, const char *arg,
- struct integrity_settings *settings, struct dm_list *pvh);
-int lv_remove_integrity(struct logical_volume *lv);
+int lv_add_integrity(struct logical_volume *lv, struct integrity_settings *settings, struct dm_list *pvh);
+int lv_add_integrity_to_raid(struct logical_volume *lv, struct integrity_settings *settings, struct dm_list *pvh,
+ struct logical_volume *lv_imeta_0);
+int lv_remove_integrity(struct logical_volume *lv, struct logical_volume **keep_lv_imeta);
int lv_remove_integrity_from_raid(struct logical_volume *lv);
void lv_clear_integrity_recalculate_metadata(struct logical_volume *lv);
int lv_has_integrity_recalculate_metadata(struct logical_volume *lv);
diff --git a/tools/lvconvert.c b/tools/lvconvert.c
index 8dfa9db5d..e27516231 100644
--- a/tools/lvconvert.c
+++ b/tools/lvconvert.c
@@ -85,6 +85,8 @@ struct lvconvert_params {
struct dm_list idls;
const char *origin_name;
+
+ struct logical_volume *prev_lv_imeta;
};
struct convert_poll_id_list {
@@ -1400,7 +1402,7 @@ static int _lvconvert_raid(struct logical_volume *lv, struct lvconvert_params *l
struct integrity_settings *isettings = NULL;
if (!lv_get_raid_integrity_settings(lv, &isettings))
return_0;
- if (!lv_add_integrity_to_raid(lv, "external", isettings, lp->pvh))
+ if (!lv_add_integrity_to_raid(lv, isettings, lp->pvh, NULL))
return_0;
}
@@ -1450,7 +1452,7 @@ static int _lvconvert_raid(struct logical_volume *lv, struct lvconvert_params *l
struct integrity_settings *isettings = NULL;
if (!lv_get_raid_integrity_settings(lv, &isettings))
return_0;
- if (!lv_add_integrity_to_raid(lv, "external", isettings, lp->pvh))
+ if (!lv_add_integrity_to_raid(lv, isettings, lp->pvh, NULL))
return_0;
}
@@ -1479,7 +1481,7 @@ try_new_takeover_or_reshape:
struct integrity_settings *isettings = NULL;
if (!lv_get_raid_integrity_settings(lv, &isettings))
return_0;
- if (!lv_add_integrity_to_raid(lv, "external", isettings, lp->pvh))
+ if (!lv_add_integrity_to_raid(lv, isettings, lp->pvh, NULL))
return_0;
}
@@ -1736,12 +1738,36 @@ static int _lvconvert_raid_types(struct cmd_context *cmd, struct logical_volume
struct lvconvert_params *lp)
{
struct lv_segment *seg = first_seg(lv);
+ struct integrity_settings isettings;
+ int add_integrity = 0;
int ret = 0;
/* If LV is inactive here, ensure it's not active elsewhere. */
if (!lockd_lv(cmd, lv, "ex", 0))
return_ECMD_FAILED;
+ /*
+ * Converting integrity+linear to raid+integrity. The imeta
+ * used for the linear LV can be used for that same linear LV
+ * in its new position as a raid image.
+ *
+ * Remove the top integrity layer (saving the detached imeta LV),
+ * do the raid conversion on the linear LV, which makes the new
+ * top LV a raid LV. When integrity is added to the raid images,
+ * use the saved imeta LV and reattach it to the same linear LV
+ * that is now a raid image.
+ */
+ if (lv_is_integrity(lv)) {
+ struct lv_segment *iseg = first_seg(lv);
+
+ memcpy(&isettings, &iseg->integrity_settings, sizeof(isettings));
+ add_integrity = 1;
+
+ if (!lv_remove_integrity(lv, &lp->prev_lv_imeta))
+ goto_out;
+ seg = first_seg(lv);
+ }
+
/* Set up segtype either from type_str or else to match the existing one. */
if (!*lp->type_str)
lp->segtype = seg->segtype;
@@ -1799,8 +1825,13 @@ static int _lvconvert_raid_types(struct cmd_context *cmd, struct logical_volume
* If operations differ between striped and linear, split this case.
*/
if (segtype_is_striped(seg->segtype) || segtype_is_linear(seg->segtype)) {
- ret = _convert_striped(cmd, lv, lp);
- goto out;
+ if (!_convert_striped(cmd, lv, lp))
+ goto_out;
+
+ if (add_integrity) {
+ if (!lv_add_integrity_to_raid(lv, &isettings, lp->pvh, lp->prev_lv_imeta))
+ goto_out;
+ }
}
/*
@@ -5795,7 +5826,7 @@ static int _lvconvert_integrity_remove(struct cmd_context *cmd,
if (lv_is_raid(lv))
ret = lv_remove_integrity_from_raid(lv);
else
- ret = lv_remove_integrity(lv);
+ ret = lv_remove_integrity(lv, NULL);
if (!ret)
return 0;
@@ -5829,9 +5860,9 @@ static int _lvconvert_integrity_add(struct cmd_context *cmd,
return_0;
if (lv_is_raid(lv))
- ret = lv_add_integrity_to_raid(lv, "external", set, use_pvh);
+ ret = lv_add_integrity_to_raid(lv, set, use_pvh, NULL);
else
- ret = lv_add_integrity(lv, "external", set, use_pvh);
+ ret = lv_add_integrity(lv, set, use_pvh);
if (!ret)
return 0;