lvcreate.c revision 1.1 1 /* $NetBSD: lvcreate.c,v 1.1 2008/12/22 00:19:02 haad Exp $ */
2
3 /*
4 * Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
5 * Copyright (C) 2004-2007 Red Hat, Inc. All rights reserved.
6 *
7 * This file is part of LVM2.
8 *
9 * This copyrighted material is made available to anyone wishing to use,
10 * modify, copy, or redistribute it subject to the terms and conditions
11 * of the GNU Lesser General Public License v.2.1.
12 *
13 * You should have received a copy of the GNU Lesser General Public License
14 * along with this program; if not, write to the Free Software Foundation,
15 * Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
16 */
17
18 #include "tools.h"
19 #include "lv_alloc.h"
20
21 #include <fcntl.h>
22
23 struct lvcreate_params {
24 /* flags */
25 int snapshot;
26 int zero;
27 int major;
28 int minor;
29 int corelog;
30 int nosync;
31
32 char *origin;
33 const char *vg_name;
34 const char *lv_name;
35
36 uint32_t stripes;
37 uint32_t stripe_size;
38 uint32_t chunk_size;
39 uint32_t region_size;
40
41 uint32_t mirrors;
42
43 const struct segment_type *segtype;
44
45 /* size */
46 uint32_t extents;
47 uint64_t size;
48 percent_t percent;
49
50 uint32_t permission;
51 uint32_t read_ahead;
52 alloc_policy_t alloc;
53
54 int pv_count;
55 char **pvs;
56 };
57
58 static int _lvcreate_name_params(struct lvcreate_params *lp,
59 struct cmd_context *cmd,
60 int *pargc, char ***pargv)
61 {
62 int argc = *pargc;
63 char **argv = *pargv, *ptr;
64 char *vg_name;
65
66 if (arg_count(cmd, name_ARG))
67 lp->lv_name = arg_value(cmd, name_ARG);
68
69 if (lp->snapshot) {
70 if (!argc) {
71 log_err("Please specify a logical volume to act as "
72 "the snapshot origin.");
73 return 0;
74 }
75
76 lp->origin = argv[0];
77 (*pargv)++, (*pargc)--;
78 if (!(lp->vg_name = extract_vgname(cmd, lp->origin))) {
79 log_err("The origin name should include the "
80 "volume group.");
81 return 0;
82 }
83
84 /* Strip the volume group from the origin */
85 if ((ptr = strrchr(lp->origin, (int) '/')))
86 lp->origin = ptr + 1;
87
88 } else {
89 /*
90 * If VG not on command line, try -n arg and then
91 * environment.
92 */
93 if (!argc) {
94 if (!(lp->vg_name = extract_vgname(cmd, lp->lv_name))) {
95 log_err("Please provide a volume group name");
96 return 0;
97 }
98
99 } else {
100 vg_name = skip_dev_dir(cmd, argv[0], NULL);
101 if (strrchr(vg_name, '/')) {
102 log_error("Volume group name expected "
103 "(no slash)");
104 return 0;
105 }
106
107 /*
108 * Ensure lv_name doesn't contain a
109 * different VG.
110 */
111 if (lp->lv_name && strchr(lp->lv_name, '/')) {
112 if (!(lp->vg_name =
113 extract_vgname(cmd, lp->lv_name)))
114 return 0;
115
116 if (strcmp(lp->vg_name, vg_name)) {
117 log_error("Inconsistent volume group "
118 "names "
119 "given: \"%s\" and \"%s\"",
120 lp->vg_name, vg_name);
121 return 0;
122 }
123 }
124
125 lp->vg_name = vg_name;
126 (*pargv)++, (*pargc)--;
127 }
128 }
129
130 if (!validate_name(lp->vg_name)) {
131 log_error("Volume group name %s has invalid characters",
132 lp->vg_name);
133 return 0;
134 }
135
136 if (lp->lv_name) {
137 if ((ptr = strrchr(lp->lv_name, '/')))
138 lp->lv_name = ptr + 1;
139
140 if (!apply_lvname_restrictions(lp->lv_name))
141 return_0;
142
143 if (!validate_name(lp->lv_name)) {
144 log_error("Logical volume name \"%s\" is invalid",
145 lp->lv_name);
146 return 0;
147 }
148 }
149
150 return 1;
151 }
152
153 static int _read_size_params(struct lvcreate_params *lp,
154 struct cmd_context *cmd)
155 {
156 if (arg_count(cmd, extents_ARG) + arg_count(cmd, size_ARG) != 1) {
157 log_error("Please specify either size or extents (not both)");
158 return 0;
159 }
160
161 if (arg_count(cmd, extents_ARG)) {
162 if (arg_sign_value(cmd, extents_ARG, 0) == SIGN_MINUS) {
163 log_error("Negative number of extents is invalid");
164 return 0;
165 }
166 lp->extents = arg_uint_value(cmd, extents_ARG, 0);
167 lp->percent = arg_percent_value(cmd, extents_ARG, PERCENT_NONE);
168 }
169
170 /* Size returned in kilobyte units; held in sectors */
171 if (arg_count(cmd, size_ARG)) {
172 if (arg_sign_value(cmd, size_ARG, 0) == SIGN_MINUS) {
173 log_error("Negative size is invalid");
174 return 0;
175 }
176 lp->size = arg_uint64_value(cmd, size_ARG, UINT64_C(0));
177 lp->percent = PERCENT_NONE;
178 }
179
180 return 1;
181 }
182
183 /*
184 * Generic stripe parameter checks.
185 * FIXME: Should eventually be moved into lvm library.
186 */
187 static int _validate_stripe_params(struct cmd_context *cmd,
188 struct lvcreate_params *lp)
189 {
190 if (lp->stripes == 1 && lp->stripe_size) {
191 log_print("Ignoring stripesize argument with single stripe");
192 lp->stripe_size = 0;
193 }
194
195 if (lp->stripes > 1 && !lp->stripe_size) {
196 lp->stripe_size = find_config_tree_int(cmd,
197 "metadata/stripesize",
198 DEFAULT_STRIPESIZE) * 2;
199 log_print("Using default stripesize %s",
200 display_size(cmd, (uint64_t) lp->stripe_size));
201 }
202
203 if (lp->stripes < 1 || lp->stripes > MAX_STRIPES) {
204 log_error("Number of stripes (%d) must be between %d and %d",
205 lp->stripes, 1, MAX_STRIPES);
206 return 0;
207 }
208
209 /* MAX size check is in _lvcreate */
210 if (lp->stripes > 1 && (lp->stripe_size < STRIPE_SIZE_MIN ||
211 lp->stripe_size & (lp->stripe_size - 1))) {
212 log_error("Invalid stripe size %s",
213 display_size(cmd, (uint64_t) lp->stripe_size));
214 return 0;
215 }
216
217 return 1;
218 }
219
220 /* The stripe size is limited by the size of a uint32_t, but since the
221 * value given by the user is doubled, and the final result must be a
222 * power of 2, we must divide UINT_MAX by four and add 1 (to round it
223 * up to the power of 2) */
224 static int _read_stripe_params(struct lvcreate_params *lp,
225 struct cmd_context *cmd)
226 {
227 if (arg_count(cmd, stripesize_ARG)) {
228 if (arg_sign_value(cmd, stripesize_ARG, 0) == SIGN_MINUS) {
229 log_error("Negative stripesize is invalid");
230 return 0;
231 }
232 /* Check to make sure we won't overflow lp->stripe_size */
233 if(arg_uint_value(cmd, stripesize_ARG, 0) > STRIPE_SIZE_LIMIT * 2) {
234 log_error("Stripe size cannot be larger than %s",
235 display_size(cmd, (uint64_t) STRIPE_SIZE_LIMIT));
236 return 0;
237 }
238 lp->stripe_size = arg_uint_value(cmd, stripesize_ARG, 0);
239 }
240
241
242 if (!_validate_stripe_params(cmd, lp))
243 return 0;
244
245 return 1;
246 }
247
248 /*
249 * Generic mirror parameter checks.
250 * FIXME: Should eventually be moved into lvm library.
251 */
252 static int _validate_mirror_params(const struct cmd_context *cmd __attribute((unused)),
253 const struct lvcreate_params *lp)
254 {
255 int pagesize = lvm_getpagesize();
256
257 if (lp->region_size & (lp->region_size - 1)) {
258 log_error("Region size (%" PRIu32 ") must be a power of 2",
259 lp->region_size);
260 return 0;
261 }
262
263 if (lp->region_size % (pagesize >> SECTOR_SHIFT)) {
264 log_error("Region size (%" PRIu32 ") must be a multiple of "
265 "machine memory page size (%d)",
266 lp->region_size, pagesize >> SECTOR_SHIFT);
267 return 0;
268 }
269
270 if (!lp->region_size) {
271 log_error("Non-zero region size must be supplied.");
272 return 0;
273 }
274
275 return 1;
276 }
277
278 static int _read_mirror_params(struct lvcreate_params *lp,
279 struct cmd_context *cmd)
280 {
281 int region_size;
282 const char *mirrorlog;
283
284 if (arg_count(cmd, corelog_ARG))
285 lp->corelog = 1;
286
287 mirrorlog = arg_str_value(cmd, mirrorlog_ARG,
288 lp->corelog ? "core" : DEFAULT_MIRRORLOG);
289
290 if (!strcmp("disk", mirrorlog)) {
291 if (lp->corelog) {
292 log_error("--mirrorlog disk and --corelog "
293 "are incompatible");
294 return 0;
295 }
296 lp->corelog = 0;
297 } else if (!strcmp("core", mirrorlog))
298 lp->corelog = 1;
299 else {
300 log_error("Unknown mirrorlog type: %s", mirrorlog);
301 return 0;
302 }
303
304 log_verbose("Setting logging type to %s", mirrorlog);
305
306 lp->nosync = arg_count(cmd, nosync_ARG) ? 1 : 0;
307
308 if (arg_count(cmd, regionsize_ARG)) {
309 if (arg_sign_value(cmd, regionsize_ARG, 0) == SIGN_MINUS) {
310 log_error("Negative regionsize is invalid");
311 return 0;
312 }
313 lp->region_size = arg_uint_value(cmd, regionsize_ARG, 0);
314 } else {
315 region_size = 2 * find_config_tree_int(cmd,
316 "activation/mirror_region_size",
317 DEFAULT_MIRROR_REGION_SIZE);
318 if (region_size < 0) {
319 log_error("Negative regionsize in configuration file "
320 "is invalid");
321 return 0;
322 }
323 lp->region_size = region_size;
324 }
325
326 if (!_validate_mirror_params(cmd, lp))
327 return 0;
328
329 return 1;
330 }
331
332 static int _lvcreate_params(struct lvcreate_params *lp, struct cmd_context *cmd,
333 int argc, char **argv)
334 {
335 int contiguous;
336 unsigned pagesize;
337
338 memset(lp, 0, sizeof(*lp));
339
340 /*
341 * Check selected options are compatible and determine segtype
342 */
343 lp->segtype = (const struct segment_type *)
344 arg_ptr_value(cmd, type_ARG,
345 get_segtype_from_string(cmd, "striped"));
346
347 lp->stripes = arg_uint_value(cmd, stripes_ARG, 1);
348 if (arg_count(cmd, stripes_ARG) && lp->stripes == 1)
349 log_print("Redundant stripes argument: default is 1");
350
351 if (arg_count(cmd, snapshot_ARG) || seg_is_snapshot(lp))
352 lp->snapshot = 1;
353
354 lp->mirrors = 1;
355
356 /* Default to 2 mirrored areas if --type mirror */
357 if (seg_is_mirrored(lp))
358 lp->mirrors = 2;
359
360 if (arg_count(cmd, mirrors_ARG)) {
361 lp->mirrors = arg_uint_value(cmd, mirrors_ARG, 0) + 1;
362 if (lp->mirrors == 1)
363 log_print("Redundant mirrors argument: default is 0");
364 if (arg_sign_value(cmd, mirrors_ARG, 0) == SIGN_MINUS) {
365 log_error("Mirrors argument may not be negative");
366 return 0;
367 }
368 }
369
370 if (lp->snapshot) {
371 if (arg_count(cmd, zero_ARG)) {
372 log_error("-Z is incompatible with snapshots");
373 return 0;
374 }
375 if (arg_sign_value(cmd, chunksize_ARG, 0) == SIGN_MINUS) {
376 log_error("Negative chunk size is invalid");
377 return 0;
378 }
379 lp->chunk_size = arg_uint_value(cmd, chunksize_ARG, 8);
380 if (lp->chunk_size < 8 || lp->chunk_size > 1024 ||
381 (lp->chunk_size & (lp->chunk_size - 1))) {
382 log_error("Chunk size must be a power of 2 in the "
383 "range 4K to 512K");
384 return 0;
385 }
386 log_verbose("Setting chunksize to %d sectors.", lp->chunk_size);
387
388 if (!(lp->segtype = get_segtype_from_string(cmd, "snapshot")))
389 return_0;
390 } else {
391 if (arg_count(cmd, chunksize_ARG)) {
392 log_error("-c is only available with snapshots");
393 return 0;
394 }
395 }
396
397 if (lp->mirrors > 1) {
398 if (lp->snapshot) {
399 log_error("mirrors and snapshots are currently "
400 "incompatible");
401 return 0;
402 }
403
404 if (lp->stripes > 1) {
405 log_error("mirrors and stripes are currently "
406 "incompatible");
407 return 0;
408 }
409
410 if (!(lp->segtype = get_segtype_from_string(cmd, "striped")))
411 return_0;
412 } else {
413 if (arg_count(cmd, corelog_ARG)) {
414 log_error("--corelog is only available with mirrors");
415 return 0;
416 }
417
418 if (arg_count(cmd, nosync_ARG)) {
419 log_error("--nosync is only available with mirrors");
420 return 0;
421 }
422 }
423
424 if (activation() && lp->segtype->ops->target_present &&
425 !lp->segtype->ops->target_present(NULL, NULL)) {
426 log_error("%s: Required device-mapper target(s) not "
427 "detected in your kernel", lp->segtype->name);
428 return 0;
429 }
430
431 if (!_lvcreate_name_params(lp, cmd, &argc, &argv) ||
432 !_read_size_params(lp, cmd) ||
433 !_read_stripe_params(lp, cmd) ||
434 !_read_mirror_params(lp, cmd))
435 return_0;
436
437 /*
438 * Should we zero the lv.
439 */
440 lp->zero = strcmp(arg_str_value(cmd, zero_ARG,
441 (lp->segtype->flags & SEG_CANNOT_BE_ZEROED) ? "n" : "y"), "n");
442
443 /*
444 * Alloc policy
445 */
446 contiguous = strcmp(arg_str_value(cmd, contiguous_ARG, "n"), "n");
447
448 lp->alloc = contiguous ? ALLOC_CONTIGUOUS : ALLOC_INHERIT;
449
450 lp->alloc = arg_uint_value(cmd, alloc_ARG, lp->alloc);
451
452 if (contiguous && (lp->alloc != ALLOC_CONTIGUOUS)) {
453 log_error("Conflicting contiguous and alloc arguments");
454 return 0;
455 }
456
457 /*
458 * Read ahead.
459 */
460 lp->read_ahead = arg_uint_value(cmd, readahead_ARG, DM_READ_AHEAD_NONE);
461 pagesize = lvm_getpagesize() >> SECTOR_SHIFT;
462 if (lp->read_ahead != DM_READ_AHEAD_AUTO &&
463 lp->read_ahead != DM_READ_AHEAD_NONE &&
464 lp->read_ahead % pagesize) {
465 lp->read_ahead = (lp->read_ahead / pagesize) * pagesize;
466 log_verbose("Rounding down readahead to %u sectors, a multiple "
467 "of page size %u.", lp->read_ahead, pagesize);
468 }
469
470 /*
471 * Permissions.
472 */
473 if (arg_count(cmd, permission_ARG))
474 lp->permission = arg_uint_value(cmd, permission_ARG, 0);
475 else
476 lp->permission = LVM_READ | LVM_WRITE;
477
478 /* Must not zero read only volume */
479 if (!(lp->permission & LVM_WRITE))
480 lp->zero = 0;
481
482 lp->minor = arg_int_value(cmd, minor_ARG, -1);
483 lp->major = arg_int_value(cmd, major_ARG, -1);
484
485 /* Persistent minor */
486 if (arg_count(cmd, persistent_ARG)) {
487 if (!strcmp(arg_str_value(cmd, persistent_ARG, "n"), "y")) {
488 if (lp->minor == -1) {
489 log_error("Please specify minor number with "
490 "--minor when using -My");
491 return 0;
492 }
493 if (lp->major == -1) {
494 log_error("Please specify major number with "
495 "--major when using -My");
496 return 0;
497 }
498 } else {
499 if ((lp->minor != -1) || (lp->major != -1)) {
500 log_error("--major and --minor incompatible "
501 "with -Mn");
502 return 0;
503 }
504 }
505 } else if (arg_count(cmd, minor_ARG) || arg_count(cmd, major_ARG)) {
506 log_error("--major and --minor require -My");
507 return 0;
508 }
509
510 lp->pv_count = argc;
511 lp->pvs = argv;
512
513 return 1;
514 }
515
516 static int _lvcreate(struct cmd_context *cmd, struct volume_group *vg,
517 struct lvcreate_params *lp)
518 {
519 uint32_t size_rest;
520 uint32_t status = 0;
521 uint64_t tmp_size;
522 struct logical_volume *lv, *org = NULL;
523 struct dm_list *pvh;
524 const char *tag = NULL;
525 int origin_active = 0;
526 char lv_name_buf[128];
527 const char *lv_name;
528 struct lvinfo info;
529 uint32_t pv_extent_count;
530
531 if (lp->lv_name && find_lv_in_vg(vg, lp->lv_name)) {
532 log_error("Logical volume \"%s\" already exists in "
533 "volume group \"%s\"", lp->lv_name, lp->vg_name);
534 return 0;
535 }
536
537 if (lp->mirrors > 1 && !(vg->fid->fmt->features & FMT_SEGMENTS)) {
538 log_error("Metadata does not support mirroring.");
539 return 0;
540 }
541
542 if (lp->read_ahead != DM_READ_AHEAD_AUTO &&
543 lp->read_ahead != DM_READ_AHEAD_NONE &&
544 (vg->fid->fmt->features & FMT_RESTRICTED_READAHEAD) &&
545 (lp->read_ahead < 2 || lp->read_ahead > 120)) {
546 log_error("Metadata only supports readahead values between 2 and 120.");
547 return 0;
548 }
549
550 if (lp->stripe_size > vg->extent_size) {
551 log_error("Reducing requested stripe size %s to maximum, "
552 "physical extent size %s",
553 display_size(cmd, (uint64_t) lp->stripe_size),
554 display_size(cmd, (uint64_t) vg->extent_size));
555 lp->stripe_size = vg->extent_size;
556 }
557
558 /* Need to check the vg's format to verify this - the cmd format isn't setup properly yet */
559 if (lp->stripes > 1 &&
560 !(vg->fid->fmt->features & FMT_UNLIMITED_STRIPESIZE) &&
561 (lp->stripe_size > STRIPE_SIZE_MAX)) {
562 log_error("Stripe size may not exceed %s",
563 display_size(cmd, (uint64_t) STRIPE_SIZE_MAX));
564 return 0;
565 }
566
567 if (lp->size) {
568 /* No of 512-byte sectors */
569 tmp_size = lp->size;
570
571 if (tmp_size % vg->extent_size) {
572 tmp_size += vg->extent_size - tmp_size %
573 vg->extent_size;
574 log_print("Rounding up size to full physical extent %s",
575 display_size(cmd, tmp_size));
576 }
577
578 if (tmp_size > (uint64_t) UINT32_MAX * vg->extent_size) {
579 log_error("Volume too large (%s) for extent size %s. "
580 "Upper limit is %s.",
581 display_size(cmd, tmp_size),
582 display_size(cmd, (uint64_t) vg->extent_size),
583 display_size(cmd, (uint64_t) UINT32_MAX *
584 vg->extent_size));
585 return 0;
586 }
587 lp->extents = (uint64_t) tmp_size / vg->extent_size;
588 }
589
590 /*
591 * Create the pv list.
592 */
593 if (lp->pv_count) {
594 if (!(pvh = create_pv_list(cmd->mem, vg,
595 lp->pv_count, lp->pvs, 1)))
596 return_0;
597 } else
598 pvh = &vg->pvs;
599
600 switch(lp->percent) {
601 case PERCENT_VG:
602 lp->extents = lp->extents * vg->extent_count / 100;
603 break;
604 case PERCENT_FREE:
605 lp->extents = lp->extents * vg->free_count / 100;
606 break;
607 case PERCENT_PVS:
608 if (!lp->pv_count) {
609 log_error("Please specify physical volume(s) "
610 "with %%PVS");
611 return 0;
612 }
613 pv_extent_count = pv_list_extents_free(pvh);
614 lp->extents = lp->extents * pv_extent_count / 100;
615 break;
616 case PERCENT_LV:
617 log_error("Please express size as %%VG, %%PVS, or "
618 "%%FREE.");
619 return 0;
620 case PERCENT_NONE:
621 break;
622 }
623
624 if ((size_rest = lp->extents % lp->stripes)) {
625 log_print("Rounding size (%d extents) up to stripe boundary "
626 "size (%d extents)", lp->extents,
627 lp->extents - size_rest + lp->stripes);
628 lp->extents = lp->extents - size_rest + lp->stripes;
629 }
630
631 if (lp->zero && !activation()) {
632 log_error("Can't wipe start of new LV without using "
633 "device-mapper kernel driver");
634 return 0;
635 }
636
637 status |= lp->permission | VISIBLE_LV;
638
639 if (lp->snapshot) {
640 if (!activation()) {
641 log_error("Can't create snapshot without using "
642 "device-mapper kernel driver");
643 return 0;
644 }
645 /* FIXME Allow exclusive activation. */
646 if (vg_is_clustered(vg)) {
647 log_error("Clustered snapshots are not yet supported.");
648 return 0;
649 }
650 if (!(org = find_lv(vg, lp->origin))) {
651 log_err("Couldn't find origin volume '%s'.",
652 lp->origin);
653 return 0;
654 }
655 if (lv_is_cow(org)) {
656 log_error("Snapshots of snapshots are not supported "
657 "yet.");
658 return 0;
659 }
660 if (org->status & LOCKED) {
661 log_error("Snapshots of locked devices are not "
662 "supported yet");
663 return 0;
664 }
665 if (org->status & MIRROR_IMAGE ||
666 org->status & MIRROR_LOG ||
667 org->status & MIRRORED) {
668 log_error("Snapshots and mirrors may not yet be mixed.");
669 return 0;
670 }
671
672 /* Must zero cow */
673 status |= LVM_WRITE;
674
675 if (!lv_info(cmd, org, &info, 0, 0)) {
676 log_error("Check for existence of snapshot origin "
677 "'%s' failed.", org->name);
678 return 0;
679 }
680 origin_active = info.exists;
681 }
682
683 if (!lp->extents) {
684 log_error("Unable to create new logical volume with no extents");
685 return 0;
686 }
687
688 if (!seg_is_virtual(lp) &&
689 vg->free_count < lp->extents) {
690 log_error("Insufficient free extents (%u) in volume group %s: "
691 "%u required", vg->free_count, vg->name, lp->extents);
692 return 0;
693 }
694
695 if (lp->stripes > dm_list_size(pvh) && lp->alloc != ALLOC_ANYWHERE) {
696 log_error("Number of stripes (%u) must not exceed "
697 "number of physical volumes (%d)", lp->stripes,
698 dm_list_size(pvh));
699 return 0;
700 }
701
702 if (lp->mirrors > 1 && !activation()) {
703 log_error("Can't create mirror without using "
704 "device-mapper kernel driver.");
705 return 0;
706 }
707
708 /* The snapshot segment gets created later */
709 if (lp->snapshot &&
710 !(lp->segtype = get_segtype_from_string(cmd, "striped")))
711 return_0;
712
713 if (!archive(vg))
714 return 0;
715
716 if (lp->lv_name)
717 lv_name = lp->lv_name;
718 else {
719 if (!generate_lv_name(vg, "lvol%d", lv_name_buf, sizeof(lv_name_buf))) {
720 log_error("Failed to generate LV name.");
721 return 0;
722 }
723 lv_name = &lv_name_buf[0];
724 }
725
726 if (arg_count(cmd, addtag_ARG)) {
727 if (!(tag = arg_str_value(cmd, addtag_ARG, NULL))) {
728 log_error("Failed to get tag");
729 return 0;
730 }
731
732 if (!(vg->fid->fmt->features & FMT_TAGS)) {
733 log_error("Volume group %s does not support tags",
734 vg->name);
735 return 0;
736 }
737 }
738
739 if (lp->mirrors > 1) {
740 init_mirror_in_sync(lp->nosync);
741
742 if (lp->nosync) {
743 log_warn("WARNING: New mirror won't be synchronised. "
744 "Don't read what you didn't write!");
745 status |= MIRROR_NOTSYNCED;
746 }
747 }
748
749 if (!(lv = lv_create_empty(lv_name ? lv_name : "lvol%d", NULL,
750 status, lp->alloc, 0, vg)))
751 return_0;
752
753 if (lp->read_ahead) {
754 log_verbose("Setting read ahead sectors");
755 lv->read_ahead = lp->read_ahead;
756 }
757
758 if (lp->minor >= 0) {
759 lv->major = lp->major;
760 lv->minor = lp->minor;
761 lv->status |= FIXED_MINOR;
762 log_verbose("Setting device number to (%d, %d)", lv->major,
763 lv->minor);
764 }
765
766 if (tag && !str_list_add(cmd->mem, &lv->tags, tag)) {
767 log_error("Failed to add tag %s to %s/%s",
768 tag, lv->vg->name, lv->name);
769 return 0;
770 }
771
772 if (!lv_extend(lv, lp->segtype, lp->stripes, lp->stripe_size,
773 1, lp->extents, NULL, 0u, 0u, pvh, lp->alloc))
774 return_0;
775
776 if (lp->mirrors > 1) {
777 if (!lv_add_mirrors(cmd, lv, lp->mirrors - 1, lp->stripes,
778 adjusted_mirror_region_size(
779 vg->extent_size,
780 lv->le_count,
781 lp->region_size),
782 lp->corelog ? 0U : 1U, pvh, lp->alloc,
783 MIRROR_BY_LV |
784 (lp->nosync ? MIRROR_SKIP_INIT_SYNC : 0))) {
785 stack;
786 goto revert_new_lv;
787 }
788 }
789
790 /* store vg on disk(s) */
791 if (!vg_write(vg))
792 return_0;
793
794 backup(vg);
795
796 if (!vg_commit(vg))
797 return_0;
798
799 if (lp->snapshot) {
800 if (!activate_lv_excl(cmd, lv)) {
801 log_error("Aborting. Failed to activate snapshot "
802 "exception store.");
803 goto revert_new_lv;
804 }
805 } else if (!activate_lv(cmd, lv)) {
806 if (lp->zero) {
807 log_error("Aborting. Failed to activate new LV to wipe "
808 "the start of it.");
809 goto deactivate_and_revert_new_lv;
810 }
811 log_error("Failed to activate new LV.");
812 return 0;
813 }
814
815 if (!lp->zero && !lp->snapshot)
816 log_error("WARNING: \"%s\" not zeroed", lv->name);
817 else if (!set_lv(cmd, lv, UINT64_C(0), 0)) {
818 log_error("Aborting. Failed to wipe %s.",
819 lp->snapshot ? "snapshot exception store" :
820 "start of new LV");
821 goto deactivate_and_revert_new_lv;
822 }
823
824 if (lp->snapshot) {
825 /* Reset permission after zeroing */
826 if (!(lp->permission & LVM_WRITE))
827 lv->status &= ~LVM_WRITE;
828
829 /* COW area must be deactivated if origin is not active */
830 if (!origin_active && !deactivate_lv(cmd, lv)) {
831 log_error("Aborting. Couldn't deactivate snapshot "
832 "COW area. Manual intervention required.");
833 return 0;
834 }
835
836 /* cow LV remains active and becomes snapshot LV */
837
838 if (!vg_add_snapshot(NULL, org, lv, NULL,
839 org->le_count, lp->chunk_size)) {
840 log_error("Couldn't create snapshot.");
841 return 0;
842 }
843
844 /* store vg on disk(s) */
845 if (!vg_write(vg))
846 return_0;
847
848 if (!suspend_lv(cmd, org)) {
849 log_error("Failed to suspend origin %s", org->name);
850 vg_revert(vg);
851 return 0;
852 }
853
854 if (!vg_commit(vg))
855 return_0;
856
857 if (!resume_lv(cmd, org)) {
858 log_error("Problem reactivating origin %s", org->name);
859 return 0;
860 }
861 }
862 /* FIXME out of sequence */
863 backup(vg);
864
865 log_print("Logical volume \"%s\" created", lv->name);
866
867 /*
868 * FIXME: as a sanity check we could try reading the
869 * last block of the device ?
870 */
871
872 return 1;
873
874 deactivate_and_revert_new_lv:
875 if (!deactivate_lv(cmd, lv)) {
876 log_error("Unable to deactivate failed new LV. "
877 "Manual intervention required.");
878 return 0;
879 }
880
881 revert_new_lv:
882 /* FIXME Better to revert to backup of metadata? */
883 if (!lv_remove(lv) || !vg_write(vg) || (backup(vg), !vg_commit(vg)))
884 log_error("Manual intervention may be required to remove "
885 "abandoned LV(s) before retrying.");
886 return 0;
887 }
888
889 int lvcreate(struct cmd_context *cmd, int argc, char **argv)
890 {
891 int r = ECMD_PROCESSED;
892 struct lvcreate_params lp;
893 struct volume_group *vg;
894
895 memset(&lp, 0, sizeof(lp));
896
897 if (!_lvcreate_params(&lp, cmd, argc, argv))
898 return EINVALID_CMD_LINE;
899
900 log_verbose("Finding volume group \"%s\"", lp.vg_name);
901 if (!(vg = vg_lock_and_read(cmd, lp.vg_name, NULL, LCK_VG_WRITE,
902 CLUSTERED | EXPORTED_VG | LVM_WRITE,
903 CORRECT_INCONSISTENT)))
904 return ECMD_FAILED;
905
906 if (!_lvcreate(cmd, vg, &lp))
907 r = ECMD_FAILED;
908
909 unlock_vg(cmd, lp.vg_name);
910 return r;
911 }
912