Home | History | Annotate | Line # | Download | only in tools
lvconvert.c revision 1.1
      1 /*	$NetBSD: lvconvert.c,v 1.1 2008/12/22 00:19:01 haad Exp $	*/
      2 
      3 /*
      4  * Copyright (C) 2005-2007 Red Hat, Inc. All rights reserved.
      5  *
      6  * This file is part of LVM2.
      7  *
      8  * This copyrighted material is made available to anyone wishing to use,
      9  * modify, copy, or redistribute it subject to the terms and conditions
     10  * of the GNU Lesser General Public License v.2.1.
     11  *
     12  * You should have received a copy of the GNU Lesser General Public License
     13  * along with this program; if not, write to the Free Software Foundation,
     14  * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
     15  */
     16 
     17 #include "tools.h"
     18 #include "polldaemon.h"
     19 #include "lv_alloc.h"
     20 
     21 struct lvconvert_params {
     22 	int snapshot;
     23 	int zero;
     24 
     25 	const char *origin;
     26 	const char *lv_name;
     27 	const char *lv_name_full;
     28 	const char *vg_name;
     29 	int wait_completion;
     30 	int need_polling;
     31 
     32 	uint32_t chunk_size;
     33 	uint32_t region_size;
     34 
     35 	uint32_t mirrors;
     36 	sign_t mirrors_sign;
     37 
     38 	struct segment_type *segtype;
     39 
     40 	alloc_policy_t alloc;
     41 
     42 	int pv_count;
     43 	char **pvs;
     44 	struct dm_list *pvh;
     45 };
     46 
     47 static int _lvconvert_name_params(struct lvconvert_params *lp,
     48 				  struct cmd_context *cmd,
     49 				  int *pargc, char ***pargv)
     50 {
     51 	char *ptr;
     52 	const char *vg_name = NULL;
     53 
     54 	if (lp->snapshot) {
     55 		if (!*pargc) {
     56 			log_error("Please specify a logical volume to act as "
     57 				  "the snapshot origin.");
     58 			return 0;
     59 		}
     60 
     61 		lp->origin = *pargv[0];
     62 		(*pargv)++, (*pargc)--;
     63 		if (!(lp->vg_name = extract_vgname(cmd, lp->origin))) {
     64 			log_error("The origin name should include the "
     65 				  "volume group.");
     66 			return 0;
     67 		}
     68 
     69 		/* Strip the volume group from the origin */
     70 		if ((ptr = strrchr(lp->origin, (int) '/')))
     71 			lp->origin = ptr + 1;
     72 	}
     73 
     74 	if (!*pargc) {
     75 		log_error("Please provide logical volume path");
     76 		return 0;
     77 	}
     78 
     79 	lp->lv_name = lp->lv_name_full = (*pargv)[0];
     80 	(*pargv)++, (*pargc)--;
     81 
     82 	if (strchr(lp->lv_name_full, '/') &&
     83 	    (vg_name = extract_vgname(cmd, lp->lv_name_full)) &&
     84 	    lp->vg_name && strcmp(vg_name, lp->vg_name)) {
     85 		log_error("Please use a single volume group name "
     86 			  "(\"%s\" or \"%s\")", vg_name, lp->vg_name);
     87 		return 0;
     88 	}
     89 
     90 	if (!lp->vg_name)
     91 		lp->vg_name = vg_name;
     92 
     93 	if (!validate_name(lp->vg_name)) {
     94 		log_error("Please provide a valid volume group name");
     95 		return 0;
     96 	}
     97 
     98 	if ((ptr = strrchr(lp->lv_name_full, '/')))
     99 		lp->lv_name = ptr + 1;
    100 
    101 	if (!apply_lvname_restrictions(lp->lv_name))
    102 		return_0;
    103 
    104 	return 1;
    105 }
    106 
    107 static int _read_params(struct lvconvert_params *lp, struct cmd_context *cmd,
    108 			int argc, char **argv)
    109 {
    110 	int region_size;
    111 	int pagesize = lvm_getpagesize();
    112 
    113 	memset(lp, 0, sizeof(*lp));
    114 
    115 	if (arg_count(cmd, snapshot_ARG) &&
    116 	    (arg_count(cmd, mirrorlog_ARG) || arg_count(cmd, mirrors_ARG))) {
    117 		log_error("--snapshots argument cannot be mixed "
    118 			  "with --mirrors or --log");
    119 		return 0;
    120 	}
    121 
    122 	if (!arg_count(cmd, background_ARG))
    123 		lp->wait_completion = 1;
    124 
    125 	if (arg_count(cmd, snapshot_ARG))
    126 		lp->snapshot = 1;
    127 
    128 	if (arg_count(cmd, mirrors_ARG)) {
    129 		lp->mirrors = arg_uint_value(cmd, mirrors_ARG, 0);
    130 		lp->mirrors_sign = arg_sign_value(cmd, mirrors_ARG, 0);
    131 	}
    132 
    133 	lp->alloc = ALLOC_INHERIT;
    134 	if (arg_count(cmd, alloc_ARG))
    135 		lp->alloc = arg_uint_value(cmd, alloc_ARG, lp->alloc);
    136 
    137 	if (lp->snapshot) {
    138 		if (arg_count(cmd, regionsize_ARG)) {
    139 			log_error("--regionsize is only available with mirrors");
    140 			return 0;
    141 		}
    142 
    143 		if (arg_sign_value(cmd, chunksize_ARG, 0) == SIGN_MINUS) {
    144 			log_error("Negative chunk size is invalid");
    145 			return 0;
    146 		}
    147 		lp->chunk_size = arg_uint_value(cmd, chunksize_ARG, 8);
    148 		if (lp->chunk_size < 8 || lp->chunk_size > 1024 ||
    149 		    (lp->chunk_size & (lp->chunk_size - 1))) {
    150 			log_error("Chunk size must be a power of 2 in the "
    151 				  "range 4K to 512K");
    152 			return 0;
    153 		}
    154 		log_verbose("Setting chunksize to %d sectors.", lp->chunk_size);
    155 
    156 		if (!(lp->segtype = get_segtype_from_string(cmd, "snapshot")))
    157 			return_0;
    158 
    159 		lp->zero = strcmp(arg_str_value(cmd, zero_ARG,
    160 						(lp->segtype->flags &
    161 						 SEG_CANNOT_BE_ZEROED) ?
    162 						"n" : "y"), "n");
    163 
    164 	} else {	/* Mirrors */
    165 		if (arg_count(cmd, chunksize_ARG)) {
    166 			log_error("--chunksize is only available with "
    167 				  "snapshots");
    168 			return 0;
    169 		}
    170 
    171 		if (arg_count(cmd, zero_ARG)) {
    172 			log_error("--zero is only available with snapshots");
    173 			return 0;
    174 		}
    175 
    176 		/*
    177 	 	 * --regionsize is only valid if converting an LV into a mirror.
    178 	 	 * Checked when we know the state of the LV being converted.
    179 	 	 */
    180 
    181 		if (arg_count(cmd, regionsize_ARG)) {
    182 			if (arg_sign_value(cmd, regionsize_ARG, 0) ==
    183 				    SIGN_MINUS) {
    184 				log_error("Negative regionsize is invalid");
    185 				return 0;
    186 			}
    187 			lp->region_size = arg_uint_value(cmd, regionsize_ARG, 0);
    188 		} else {
    189 			region_size = 2 * find_config_tree_int(cmd,
    190 						"activation/mirror_region_size",
    191 						DEFAULT_MIRROR_REGION_SIZE);
    192 			if (region_size < 0) {
    193 				log_error("Negative regionsize in "
    194 					  "configuration file is invalid");
    195 				return 0;
    196 			}
    197 			lp->region_size = region_size;
    198 		}
    199 
    200 		if (lp->region_size % (pagesize >> SECTOR_SHIFT)) {
    201 			log_error("Region size (%" PRIu32 ") must be "
    202 				  "a multiple of machine memory "
    203 				  "page size (%d)",
    204 				  lp->region_size, pagesize >> SECTOR_SHIFT);
    205 			return 0;
    206 		}
    207 
    208 		if (lp->region_size & (lp->region_size - 1)) {
    209 			log_error("Region size (%" PRIu32
    210 				  ") must be a power of 2", lp->region_size);
    211 			return 0;
    212 		}
    213 
    214 		if (!lp->region_size) {
    215 			log_error("Non-zero region size must be supplied.");
    216 			return 0;
    217 		}
    218 
    219 		if (!(lp->segtype = get_segtype_from_string(cmd, "mirror")))
    220 			return_0;
    221 	}
    222 
    223 	if (activation() && lp->segtype->ops->target_present &&
    224 	    !lp->segtype->ops->target_present(NULL, NULL)) {
    225 		log_error("%s: Required device-mapper target(s) not "
    226 			  "detected in your kernel", lp->segtype->name);
    227 		return 0;
    228 	}
    229 
    230 	if (!_lvconvert_name_params(lp, cmd, &argc, &argv))
    231 		return_0;
    232 
    233 	lp->pv_count = argc;
    234 	lp->pvs = argv;
    235 
    236 	return 1;
    237 }
    238 
    239 
    240 static struct volume_group *_get_lvconvert_vg(struct cmd_context *cmd,
    241 					      const char *lv_name)
    242 {
    243 	dev_close_all();
    244 
    245         return vg_lock_and_read(cmd, extract_vgname(cmd, lv_name),
    246 				NULL, LCK_VG_WRITE,
    247  				CLUSTERED | EXPORTED_VG | LVM_WRITE,
    248 				CORRECT_INCONSISTENT | FAIL_INCONSISTENT);
    249 }
    250 
    251 static struct logical_volume *_get_lvconvert_lv(struct cmd_context *cmd __attribute((unused)),
    252 						struct volume_group *vg,
    253 						const char *name,
    254 						uint32_t lv_type __attribute((unused)))
    255 {
    256 	return find_lv(vg, name);
    257 }
    258 
    259 static int _update_lvconvert_mirror(struct cmd_context *cmd __attribute((unused)),
    260 				    struct volume_group *vg __attribute((unused)),
    261 				    struct logical_volume *lv __attribute((unused)),
    262 				    struct dm_list *lvs_changed __attribute((unused)),
    263 				    unsigned flags __attribute((unused)))
    264 {
    265 	/* lvconvert mirror doesn't require periodical metadata update */
    266 	return 1;
    267 }
    268 
    269 static int _finish_lvconvert_mirror(struct cmd_context *cmd,
    270 				    struct volume_group *vg,
    271 				    struct logical_volume *lv,
    272 				    struct dm_list *lvs_changed __attribute((unused)))
    273 {
    274 	if (!collapse_mirrored_lv(lv)) {
    275 		log_error("Failed to remove temporary sync layer.");
    276 		return 0;
    277 	}
    278 
    279 	lv->status &= ~CONVERTING;
    280 
    281 	log_very_verbose("Updating logical volume \"%s\" on disk(s)", lv->name);
    282 
    283 	if (!vg_write(vg))
    284 		return_0;
    285 
    286 	backup(vg);
    287 
    288 	if (!suspend_lv(cmd, lv)) {
    289 		log_error("Failed to lock %s", lv->name);
    290 		vg_revert(vg);
    291 		return 0;
    292 	}
    293 
    294 	if (!vg_commit(vg)) {
    295 		resume_lv(cmd, lv);
    296 		return 0;
    297 	}
    298 
    299 	log_very_verbose("Updating \"%s\" in kernel", lv->name);
    300 
    301 	if (!resume_lv(cmd, lv)) {
    302 		log_error("Problem reactivating %s", lv->name);
    303 		return 0;
    304 	}
    305 
    306 	log_print("Logical volume %s converted.", lv->name);
    307 
    308 	return 1;
    309 }
    310 
    311 static struct poll_functions _lvconvert_mirror_fns = {
    312 	.get_copy_vg = _get_lvconvert_vg,
    313 	.get_copy_lv = _get_lvconvert_lv,
    314 	.update_metadata = _update_lvconvert_mirror,
    315 	.finish_copy = _finish_lvconvert_mirror,
    316 };
    317 
    318 int lvconvert_poll(struct cmd_context *cmd, const char *lv_name,
    319 		   unsigned background)
    320 {
    321 	return poll_daemon(cmd, lv_name, background, 0, &_lvconvert_mirror_fns,
    322 			   "Converted");
    323 }
    324 
    325 static int _insert_lvconvert_layer(struct cmd_context *cmd,
    326 				   struct logical_volume *lv)
    327 {
    328 	char *format, *layer_name;
    329 	size_t len;
    330 	int i;
    331 
    332 	/*
    333  	 * We would like to give the same number for this layer
    334  	 * and the newly added mimage.
    335  	 * However, LV name of newly added mimage is determined *after*
    336 	 * the LV name of this layer is determined.
    337 	 *
    338 	 * So, use generate_lv_name() to generate mimage name first
    339 	 * and take the number from it.
    340 	 */
    341 
    342 	len = strlen(lv->name) + 32;
    343 	if (!(format = alloca(len)) ||
    344 	    !(layer_name = alloca(len)) ||
    345 	    dm_snprintf(format, len, "%s_mimage_%%d", lv->name) < 0) {
    346 		log_error("lvconvert: layer name allocation failed.");
    347 		return 0;
    348 	}
    349 
    350 	if (!generate_lv_name(lv->vg, format, layer_name, len) ||
    351 	    sscanf(layer_name, format, &i) != 1) {
    352 		log_error("lvconvert: layer name generation failed.");
    353 		return 0;
    354 	}
    355 
    356 	if (dm_snprintf(layer_name, len, MIRROR_SYNC_LAYER "_%d", i) < 0) {
    357 		log_error("layer name allocation failed.");
    358 		return 0;
    359 	}
    360 
    361 	if (!insert_layer_for_lv(cmd, lv, 0, layer_name)) {
    362 		log_error("Failed to insert resync layer");
    363 		return 0;
    364 	}
    365 
    366 	return 1;
    367 }
    368 
    369 /* walk down the stacked mirror LV to the original mirror LV */
    370 static struct logical_volume *_original_lv(struct logical_volume *lv)
    371 {
    372 	struct logical_volume *next_lv = lv, *tmp_lv;
    373 
    374 	while ((tmp_lv = find_temporary_mirror(next_lv)))
    375 		next_lv = tmp_lv;
    376 
    377 	return next_lv;
    378 }
    379 
    380 static int lvconvert_mirrors(struct cmd_context * cmd, struct logical_volume * lv,
    381 			     struct lvconvert_params *lp)
    382 {
    383 	struct lv_segment *seg;
    384 	uint32_t existing_mirrors;
    385 	const char *mirrorlog;
    386 	unsigned corelog = 0;
    387 	struct logical_volume *original_lv;
    388 
    389 	seg = first_seg(lv);
    390 	existing_mirrors = lv_mirror_count(lv);
    391 
    392 	/* If called with no argument, try collapsing the resync layers */
    393 	if (!arg_count(cmd, mirrors_ARG) && !arg_count(cmd, mirrorlog_ARG) &&
    394 	    !arg_count(cmd, corelog_ARG) && !arg_count(cmd, regionsize_ARG)) {
    395 		lp->need_polling = 1;
    396 		return 1;
    397 	}
    398 
    399 	/*
    400 	 * Adjust required number of mirrors
    401 	 *
    402 	 * We check mirrors_ARG again to see if it
    403 	 * was supplied.  If not, they want the mirror
    404 	 * count to remain the same.  They may be changing
    405 	 * the logging type.
    406 	 */
    407 	if (!arg_count(cmd, mirrors_ARG))
    408 		lp->mirrors = existing_mirrors;
    409 	else if (lp->mirrors_sign == SIGN_PLUS)
    410 		lp->mirrors = existing_mirrors + lp->mirrors;
    411 	else if (lp->mirrors_sign == SIGN_MINUS)
    412 		lp->mirrors = existing_mirrors - lp->mirrors;
    413 	else
    414 		lp->mirrors += 1;
    415 
    416 	/*
    417 	 * Did the user try to subtract more legs than available?
    418 	 */
    419 	if (lp->mirrors < 1) {
    420 		log_error("Logical volume %s only has %" PRIu32 " mirrors.",
    421 			  lv->name, existing_mirrors);
    422 		return 0;
    423 	}
    424 
    425 	/*
    426 	 * Adjust log type
    427 	 */
    428 	if (arg_count(cmd, corelog_ARG))
    429 		corelog = 1;
    430 
    431 	mirrorlog = arg_str_value(cmd, mirrorlog_ARG,
    432 				  corelog ? "core" : DEFAULT_MIRRORLOG);
    433 	if (!strcmp("disk", mirrorlog)) {
    434 		if (corelog) {
    435 			log_error("--mirrorlog disk and --corelog "
    436 				  "are incompatible");
    437 			return 0;
    438 		}
    439 		corelog = 0;
    440 	} else if (!strcmp("core", mirrorlog))
    441 		corelog = 1;
    442 	else {
    443 		log_error("Unknown mirrorlog type: %s", mirrorlog);
    444 		return 0;
    445 	}
    446 
    447 	log_verbose("Setting logging type to %s", mirrorlog);
    448 
    449 	/*
    450 	 * Region size must not change on existing mirrors
    451 	 */
    452 	if (arg_count(cmd, regionsize_ARG) && (lv->status & MIRRORED) &&
    453 	    (lp->region_size != seg->region_size)) {
    454 		log_error("Mirror log region size cannot be changed on "
    455 			  "an existing mirror.");
    456 		return 0;
    457 	}
    458 
    459 	/*
    460 	 * Converting from mirror to linear
    461 	 */
    462 	if ((lp->mirrors == 1)) {
    463 		if (!(lv->status & MIRRORED)) {
    464 			log_error("Logical volume %s is already not mirrored.",
    465 				  lv->name);
    466 			return 1;
    467 		}
    468 
    469 		if (!lv_remove_mirrors(cmd, lv, existing_mirrors - 1, 1,
    470 				       lp->pv_count ? lp->pvh : NULL, 0))
    471 			return_0;
    472 		goto commit_changes;
    473 	}
    474 
    475 	/*
    476 	 * Converting from linear to mirror
    477 	 */
    478 	if (!(lv->status & MIRRORED)) {
    479 		/* FIXME Share code with lvcreate */
    480 
    481 		/* FIXME Why is this restriction here?  Fix it! */
    482 		dm_list_iterate_items(seg, &lv->segments) {
    483 			if (seg_is_striped(seg) && seg->area_count > 1) {
    484 				log_error("Mirrors of striped volumes are not yet supported.");
    485 				return 0;
    486 			}
    487 		}
    488 
    489 		if (!lv_add_mirrors(cmd, lv, lp->mirrors - 1, 1,
    490 				    adjusted_mirror_region_size(
    491 						lv->vg->extent_size,
    492 						lv->le_count,
    493 						lp->region_size),
    494 				    corelog ? 0U : 1U, lp->pvh, lp->alloc,
    495 				    MIRROR_BY_LV))
    496 			return_0;
    497 		if (lp->wait_completion)
    498 			lp->need_polling = 1;
    499 		goto commit_changes;
    500 	}
    501 
    502 	/*
    503 	 * Converting from mirror to mirror with different leg count,
    504 	 * or different log type.
    505 	 */
    506 	if (dm_list_size(&lv->segments) != 1) {
    507 		log_error("Logical volume %s has multiple "
    508 			  "mirror segments.", lv->name);
    509 		return 0;
    510 	}
    511 
    512 	if (lp->mirrors == existing_mirrors) {
    513 		/*
    514 		 * Convert Mirror log type
    515 		 */
    516 		original_lv = _original_lv(lv);
    517 		if (!first_seg(original_lv)->log_lv && !corelog) {
    518 			if (!add_mirror_log(cmd, original_lv, 1,
    519 					    adjusted_mirror_region_size(
    520 							lv->vg->extent_size,
    521 							lv->le_count,
    522 							lp->region_size),
    523 					    lp->pvh, lp->alloc))
    524 				return_0;
    525 		} else if (first_seg(original_lv)->log_lv && corelog) {
    526 			if (!remove_mirror_log(cmd, original_lv,
    527 					       lp->pv_count ? lp->pvh : NULL))
    528 				return_0;
    529 		} else {
    530 			/* No change */
    531 			log_error("Logical volume %s already has %"
    532 				  PRIu32 " mirror(s).", lv->name,
    533 				  lp->mirrors - 1);
    534 			if (lv->status & CONVERTING)
    535 				lp->need_polling = 1;
    536 			return 1;
    537 		}
    538 	} else if (lp->mirrors > existing_mirrors) {
    539 		if (lv->status & MIRROR_NOTSYNCED) {
    540 			log_error("Not adding mirror to mirrored LV "
    541 				  "without initial resync");
    542 			return 0;
    543 		}
    544 		/*
    545 		 * Log addition/removal should be done before the layer
    546 		 * insertion to make the end result consistent with
    547 		 * linear-to-mirror conversion.
    548 		 */
    549 		original_lv = _original_lv(lv);
    550 		if (!first_seg(original_lv)->log_lv && !corelog) {
    551 			if (!add_mirror_log(cmd, original_lv, 1,
    552 					    adjusted_mirror_region_size(
    553 							lv->vg->extent_size,
    554 							lv->le_count,
    555 							lp->region_size),
    556 					    lp->pvh, lp->alloc))
    557 				return_0;
    558 		} else if (first_seg(original_lv)->log_lv && corelog) {
    559 			if (!remove_mirror_log(cmd, original_lv,
    560 					       lp->pv_count ? lp->pvh : NULL))
    561 				return_0;
    562 		}
    563 		/* Insert a temporary layer for syncing,
    564 		 * only if the original lv is using disk log. */
    565 		if (seg->log_lv && !_insert_lvconvert_layer(cmd, lv)) {
    566 			log_error("Failed to insert resync layer");
    567 			return 0;
    568 		}
    569 		/* FIXME: can't have multiple mlogs. force corelog. */
    570 		if (!lv_add_mirrors(cmd, lv, lp->mirrors - existing_mirrors, 1,
    571 				    adjusted_mirror_region_size(
    572 						lv->vg->extent_size,
    573 						lv->le_count,
    574 						lp->region_size),
    575 				    0U, lp->pvh, lp->alloc,
    576 				    MIRROR_BY_LV))
    577 			return_0;
    578 		lv->status |= CONVERTING;
    579 		lp->need_polling = 1;
    580 	} else {
    581 		/* Reduce number of mirrors */
    582 		if (!lv_remove_mirrors(cmd, lv, existing_mirrors - lp->mirrors,
    583 				       corelog ? 1U : 0U,
    584 				       lp->pv_count ? lp->pvh : NULL, 0))
    585 			return_0;
    586 	}
    587 
    588 commit_changes:
    589 	log_very_verbose("Updating logical volume \"%s\" on disk(s)", lv->name);
    590 
    591 	if (!vg_write(lv->vg))
    592 		return_0;
    593 
    594 	backup(lv->vg);
    595 
    596 	if (!suspend_lv(cmd, lv)) {
    597 		log_error("Failed to lock %s", lv->name);
    598 		vg_revert(lv->vg);
    599 		return 0;
    600 	}
    601 
    602 	if (!vg_commit(lv->vg)) {
    603 		resume_lv(cmd, lv);
    604 		return 0;
    605 	}
    606 
    607 	log_very_verbose("Updating \"%s\" in kernel", lv->name);
    608 
    609 	if (!resume_lv(cmd, lv)) {
    610 		log_error("Problem reactivating %s", lv->name);
    611 		return 0;
    612 	}
    613 
    614 	if (!lp->need_polling)
    615 		log_print("Logical volume %s converted.", lv->name);
    616 
    617 	return 1;
    618 }
    619 
    620 static int lvconvert_snapshot(struct cmd_context *cmd,
    621 			      struct logical_volume *lv,
    622 			      struct lvconvert_params *lp)
    623 {
    624 	struct logical_volume *org;
    625 
    626 	if (!(org = find_lv(lv->vg, lp->origin))) {
    627 		log_error("Couldn't find origin volume '%s'.", lp->origin);
    628 		return 0;
    629 	}
    630 
    631 	if (org == lv) {
    632 		log_error("Unable to use \"%s\" as both snapshot and origin.",
    633 			  lv->name);
    634 		return 0;
    635 	}
    636 
    637 	if (org->status & (LOCKED|PVMOVE|MIRRORED) || lv_is_cow(org)) {
    638 		log_error("Unable to create a snapshot of a %s LV.",
    639 			  org->status & LOCKED ? "locked" :
    640 			  org->status & PVMOVE ? "pvmove" :
    641 			  org->status & MIRRORED ? "mirrored" :
    642 			  "snapshot");
    643 		return 0;
    644 	}
    645 
    646 	if (!lp->zero || !(lv->status & LVM_WRITE))
    647 		log_warn("WARNING: \"%s\" not zeroed", lv->name);
    648 	else if (!set_lv(cmd, lv, UINT64_C(0), 0)) {
    649 		log_error("Aborting. Failed to wipe snapshot "
    650 			  "exception store.");
    651 		return 0;
    652 	}
    653 
    654 	if (!deactivate_lv(cmd, lv)) {
    655 		log_error("Couldn't deactivate LV %s.", lv->name);
    656 		return 0;
    657 	}
    658 
    659 	if (!vg_add_snapshot(NULL, org, lv, NULL, org->le_count,
    660 			     lp->chunk_size)) {
    661 		log_error("Couldn't create snapshot.");
    662 		return 0;
    663 	}
    664 
    665 	/* store vg on disk(s) */
    666 	if (!vg_write(lv->vg))
    667 		return_0;
    668 
    669 	backup(lv->vg);
    670 
    671 	if (!suspend_lv(cmd, org)) {
    672 		log_error("Failed to suspend origin %s", org->name);
    673 		vg_revert(lv->vg);
    674 		return 0;
    675 	}
    676 
    677 	if (!vg_commit(lv->vg))
    678 		return_0;
    679 
    680 	if (!resume_lv(cmd, org)) {
    681 		log_error("Problem reactivating origin %s", org->name);
    682 		return 0;
    683 	}
    684 
    685 	log_print("Logical volume %s converted to snapshot.", lv->name);
    686 
    687 	return 1;
    688 }
    689 
    690 static int lvconvert_single(struct cmd_context *cmd, struct logical_volume *lv,
    691 			    void *handle)
    692 {
    693 	struct lvconvert_params *lp = handle;
    694 
    695 	if (lv->status & LOCKED) {
    696 		log_error("Cannot convert locked LV %s", lv->name);
    697 		return ECMD_FAILED;
    698 	}
    699 
    700 	if (lv_is_origin(lv)) {
    701 		log_error("Can't convert logical volume \"%s\" under snapshot",
    702 			  lv->name);
    703 		return ECMD_FAILED;
    704 	}
    705 
    706 	if (lv_is_cow(lv)) {
    707 		log_error("Can't convert snapshot logical volume \"%s\"",
    708 			  lv->name);
    709 		return ECMD_FAILED;
    710 	}
    711 
    712 	if (lv->status & PVMOVE) {
    713 		log_error("Unable to convert pvmove LV %s", lv->name);
    714 		return ECMD_FAILED;
    715 	}
    716 
    717 	if (lp->snapshot) {
    718 		if (lv->status & MIRRORED) {
    719 			log_error("Unable to convert mirrored LV \"%s\" into a snapshot.", lv->name);
    720 			return ECMD_FAILED;
    721 		}
    722 		if (!archive(lv->vg))
    723 			return ECMD_FAILED;
    724 		if (!lvconvert_snapshot(cmd, lv, lp))
    725 			return ECMD_FAILED;
    726 	} else if (arg_count(cmd, mirrors_ARG) || (lv->status & MIRRORED)) {
    727 		if (!archive(lv->vg))
    728 			return ECMD_FAILED;
    729 		if (!lvconvert_mirrors(cmd, lv, lp))
    730 			return ECMD_FAILED;
    731 	}
    732 
    733 	return ECMD_PROCESSED;
    734 }
    735 
    736 int lvconvert(struct cmd_context * cmd, int argc, char **argv)
    737 {
    738 	struct volume_group *vg;
    739 	struct lv_list *lvl;
    740 	struct lvconvert_params lp;
    741 	int ret = ECMD_FAILED;
    742 	struct lvinfo info;
    743 
    744 	if (!_read_params(&lp, cmd, argc, argv)) {
    745 		stack;
    746 		return EINVALID_CMD_LINE;
    747 	}
    748 
    749 	log_verbose("Checking for existing volume group \"%s\"", lp.vg_name);
    750 
    751 	if (!(vg = vg_lock_and_read(cmd, lp.vg_name, NULL, LCK_VG_WRITE,
    752 				    CLUSTERED | EXPORTED_VG | LVM_WRITE,
    753 				    CORRECT_INCONSISTENT)))
    754 		return ECMD_FAILED;
    755 
    756 	if (!(lvl = find_lv_in_vg(vg, lp.lv_name))) {
    757 		log_error("Logical volume \"%s\" not found in "
    758 			  "volume group \"%s\"", lp.lv_name, lp.vg_name);
    759 		goto bad;
    760 	}
    761 
    762 	if (lp.pv_count) {
    763 		if (!(lp.pvh = create_pv_list(cmd->mem, vg, lp.pv_count,
    764 					      lp.pvs, 0)))
    765 			goto_bad;
    766 	} else
    767 		lp.pvh = &vg->pvs;
    768 
    769 	ret = lvconvert_single(cmd, lvl->lv, &lp);
    770 
    771 bad:
    772 	unlock_vg(cmd, lp.vg_name);
    773 
    774 	if (ret == ECMD_PROCESSED && lp.need_polling) {
    775 		if (!lv_info(cmd, lvl->lv, &info, 1, 0) || !info.exists) {
    776 			log_print("Conversion starts after activation");
    777 			return ret;
    778 		}
    779 		ret = lvconvert_poll(cmd, lp.lv_name_full,
    780 				     lp.wait_completion ? 0 : 1U);
    781 	}
    782 
    783 	return ret;
    784 }
    785