diff options
author | Alasdair Kergon <agk@redhat.com> | 2004-05-18 22:12:53 +0000 |
---|---|---|
committer | Alasdair Kergon <agk@redhat.com> | 2004-05-18 22:12:53 +0000 |
commit | fdf15caaffa2e8ea8a70e629f0255407241d6077 (patch) | |
tree | 8c67a5c599ba6fdb54955e0c8f9c4c75dc76cb61 | |
parent | c7b4a53c0b75057cd1949b790edd62968496e2ea (diff) | |
download | lvm2-fdf15caaffa2e8ea8a70e629f0255407241d6077.tar.gz |
Rename allocation policies; add --alloc to cmdline; LV inherits from VG.
-rw-r--r-- | WHATS_NEW | 5 | ||||
-rw-r--r-- | lib/display/display.c | 13 | ||||
-rw-r--r-- | lib/format1/import-export.c | 3 | ||||
-rw-r--r-- | lib/format_text/export.c | 10 | ||||
-rw-r--r-- | lib/format_text/import_vsn1.c | 21 | ||||
-rw-r--r-- | lib/metadata/lv_manip.c | 10 | ||||
-rw-r--r-- | lib/metadata/metadata.c | 5 | ||||
-rw-r--r-- | lib/metadata/metadata.h | 12 | ||||
-rw-r--r-- | lib/report/columns.h | 2 | ||||
-rw-r--r-- | lib/report/report.c | 33 | ||||
-rw-r--r-- | tools/args.h | 1 | ||||
-rw-r--r-- | tools/commands.h | 33 | ||||
-rw-r--r-- | tools/lvchange.c | 62 | ||||
-rw-r--r-- | tools/lvcreate.c | 25 | ||||
-rw-r--r-- | tools/lvmcmdline.c | 15 | ||||
-rw-r--r-- | tools/lvresize.c | 5 | ||||
-rw-r--r-- | tools/tools.h | 1 | ||||
-rw-r--r-- | tools/vgchange.c | 52 | ||||
-rw-r--r-- | tools/vgcreate.c | 10 | ||||
-rw-r--r-- | tools/vgsplit.c | 3 |
20 files changed, 229 insertions, 92 deletions
@@ -1,5 +1,10 @@ Version 2.00.16 - ============================= + Add --alloc argument to tools. + Rename allocation policies to contiguous, normal, anywhere, inherit. + nextfree becomes normal; anywhere isn't implemented yet. + LV inherits allocation policy from VG. Defaults: LV - inherit; VG - normal + Additional status character added to vgs to indicate allocation policy. Add reset_fn to external_locking. Ensure presence of virtual targets before attempting activating. Attempt to fix resizing of snapshot origins. diff --git a/lib/display/display.c b/lib/display/display.c index 4a1aa921e..5e5012f6e 100644 --- a/lib/display/display.c +++ b/lib/display/display.c @@ -27,9 +27,10 @@ static struct { const char *str; } _policies[] = { { - ALLOC_NEXT_FREE, "next free"}, { ALLOC_CONTIGUOUS, "contiguous"}, { - ALLOC_DEFAULT, "next free (default)"} + ALLOC_NORMAL, "normal"}, { + ALLOC_ANYWHERE, "anywhere"}, { + ALLOC_INHERIT, "inherit"} }; static int _num_policies = sizeof(_policies) / sizeof(*_policies); @@ -122,8 +123,12 @@ alloc_policy_t get_alloc_from_string(const char *str) if (!strcmp(_policies[i].str, str)) return _policies[i].alloc; - log_error("Unrecognised allocation policy - using default"); - return ALLOC_DEFAULT; + /* Special case for old metadata */ + if(!strcmp("next free", str)) + return ALLOC_NORMAL; + + log_error("Unrecognised allocation policy %s", str); + return ALLOC_INVALID; } const char *display_size(struct cmd_context *cmd, uint64_t size, size_len_t sl) diff --git a/lib/format1/import-export.c b/lib/format1/import-export.c index 297056a5f..7217794a1 100644 --- a/lib/format1/import-export.c +++ b/lib/format1/import-export.c @@ -237,6 +237,7 @@ int import_vg(struct pool *mem, vg->free_count = vgd->pe_total - vgd->pe_allocated; vg->max_lv = vgd->lv_max; vg->max_pv = vgd->pv_max; + vg->alloc = ALLOC_NORMAL; if (partial) vg->status |= PARTIAL_VG; @@ -316,7 +317,7 @@ int import_lv(struct pool *mem, struct logical_volume *lv, struct lv_disk *lvd) if (lvd->lv_allocation & LV_CONTIGUOUS) lv->alloc = ALLOC_CONTIGUOUS; else - lv->alloc = ALLOC_NEXT_FREE; + lv->alloc = ALLOC_NORMAL; lv->read_ahead = lvd->lv_read_ahead; lv->size = lvd->lv_size; diff --git a/lib/format_text/export.c b/lib/format_text/export.c index 283fee29d..2bc168c8d 100644 --- a/lib/format_text/export.c +++ b/lib/format_text/export.c @@ -307,6 +307,13 @@ static int _print_vg(struct formatter *f, struct volume_group *vg) outf(f, "max_lv = %u", vg->max_lv); outf(f, "max_pv = %u", vg->max_pv); + /* Default policy is NORMAL; INHERIT is meaningless */ + if (vg->alloc != ALLOC_NORMAL && vg->alloc != ALLOC_INHERIT) { + f->nl(f); + outf(f, "allocation_policy = \"%s\"", + get_alloc_string(vg->alloc)); + } + return 1; } @@ -597,9 +604,10 @@ static int _print_lvs(struct formatter *f, struct volume_group *vg) outf(f, "tags = %s", buffer); } - if (lv->alloc != ALLOC_DEFAULT) + if (lv->alloc != ALLOC_INHERIT) outf(f, "allocation_policy = \"%s\"", get_alloc_string(lv->alloc)); + if (lv->read_ahead) outf(f, "read_ahead = %u", lv->read_ahead); if (lv->major >= 0) diff --git a/lib/format_text/import_vsn1.c b/lib/format_text/import_vsn1.c index f18d2eba8..a84848114 100644 --- a/lib/format_text/import_vsn1.c +++ b/lib/format_text/import_vsn1.c @@ -490,7 +490,7 @@ static int _read_lvnames(struct format_instance *fid, struct pool *mem, return 0; } - lv->alloc = ALLOC_DEFAULT; + lv->alloc = ALLOC_INHERIT; if ((cn = find_config_node(lvn, "allocation_policy"))) { struct config_value *cv = cn->v; if (!cv || !cv->v.str) { @@ -499,6 +499,10 @@ static int _read_lvnames(struct format_instance *fid, struct pool *mem, } lv->alloc = get_alloc_from_string(cv->v.str); + if (lv->alloc == ALLOC_INVALID) { + stack; + return 0; + } } /* read_ahead defaults to 0 */ @@ -700,6 +704,21 @@ static struct volume_group *_read_vg(struct format_instance *fid, goto bad; } + vg->alloc = ALLOC_NORMAL; + if ((cn = find_config_node(vgn, "allocation_policy"))) { + struct config_value *cv = cn->v; + if (!cv || !cv->v.str) { + log_error("allocation_policy must be a string."); + return 0; + } + + vg->alloc = get_alloc_from_string(cv->v.str); + if (vg->alloc == ALLOC_INVALID) { + stack; + return 0; + } + } + /* * The pv hash memoises the pv section names -> pv * structures. diff --git a/lib/metadata/lv_manip.c b/lib/metadata/lv_manip.c index 0dcf27ff1..9c70dcdc9 100644 --- a/lib/metadata/lv_manip.c +++ b/lib/metadata/lv_manip.c @@ -466,6 +466,9 @@ static int _allocate(struct volume_group *vg, struct logical_volume *lv, return 0; } + if (alloc == ALLOC_INHERIT) + alloc = vg->alloc; + /* * Build the sets of available areas on the pv's. */ @@ -479,15 +482,16 @@ static int _allocate(struct volume_group *vg, struct logical_volume *lv, else if (mirrored_pv) r = _alloc_mirrored(lv, pvms, allocated, segtype, mirrored_pv, mirrored_pe); + else if (alloc == ALLOC_CONTIGUOUS) r = _alloc_contiguous(lv, pvms, allocated); - else if (alloc == ALLOC_NEXT_FREE || alloc == ALLOC_DEFAULT) + else if (alloc == ALLOC_NORMAL || alloc == ALLOC_ANYWHERE) r = _alloc_next_free(lv, pvms, allocated); else { - log_error("Unknown allocation policy: " - "unable to setup logical volume."); + log_error("Unrecognised allocation policy: " + "unable to set up logical volume."); goto out; } diff --git a/lib/metadata/metadata.c b/lib/metadata/metadata.c index ccc1c4cbd..2f7175ecf 100644 --- a/lib/metadata/metadata.c +++ b/lib/metadata/metadata.c @@ -162,7 +162,8 @@ const char *strip_dir(const char *vg_name, const char *dev_dir) struct volume_group *vg_create(struct cmd_context *cmd, const char *vg_name, uint32_t extent_size, uint32_t max_pv, - uint32_t max_lv, int pv_count, char **pv_names) + uint32_t max_lv, alloc_policy_t alloc, + int pv_count, char **pv_names) { struct volume_group *vg; struct pool *mem = cmd->mem; @@ -211,6 +212,8 @@ struct volume_group *vg_create(struct cmd_context *cmd, const char *vg_name, vg->max_lv = max_lv; vg->max_pv = max_pv; + vg->alloc = alloc; + vg->pv_count = 0; list_init(&vg->pvs); diff --git a/lib/metadata/metadata.h b/lib/metadata/metadata.h index e9380da02..0fb27c9c3 100644 --- a/lib/metadata/metadata.h +++ b/lib/metadata/metadata.h @@ -70,9 +70,11 @@ #define FMT_ORPHAN_ALLOCATABLE 0x00000020 /* Orphan PV allocatable? */ typedef enum { - ALLOC_DEFAULT, - ALLOC_NEXT_FREE, - ALLOC_CONTIGUOUS + ALLOC_INVALID, + ALLOC_INHERIT, + ALLOC_CONTIGUOUS, + ALLOC_NORMAL, + ALLOC_ANYWHERE } alloc_policy_t; typedef enum { @@ -167,6 +169,7 @@ struct volume_group { char *system_id; uint32_t status; + alloc_policy_t alloc; uint32_t extent_size; uint32_t extent_count; @@ -389,7 +392,8 @@ struct physical_volume *pv_create(const struct format_type *fmt, struct volume_group *vg_create(struct cmd_context *cmd, const char *name, uint32_t extent_size, uint32_t max_pv, - uint32_t max_lv, int pv_count, char **pv_names); + uint32_t max_lv, alloc_policy_t alloc, + int pv_count, char **pv_names); int vg_remove(struct volume_group *vg); int vg_rename(struct cmd_context *cmd, struct volume_group *vg, const char *new_name); diff --git a/lib/report/columns.h b/lib/report/columns.h index 85787bd84..182cc3c18 100644 --- a/lib/report/columns.h +++ b/lib/report/columns.h @@ -45,7 +45,7 @@ FIELD(PVS, pv, STR, "PV Tags", tags, 7, tags, "pv_tags") FIELD(VGS, vg, STR, "Fmt", cmd, 3, vgfmt, "vg_fmt") FIELD(VGS, vg, STR, "VG UUID", id, 38, uuid, "vg_uuid") FIELD(VGS, vg, STR, "VG", name, 4, string, "vg_name") -FIELD(VGS, vg, STR, "Attr", status, 4, vgstatus, "vg_attr") +FIELD(VGS, vg, STR, "Attr", cmd, 5, vgstatus, "vg_attr") FIELD(VGS, vg, NUM, "VSize", cmd, 5, vgsize, "vg_size") FIELD(VGS, vg, NUM, "VFree", cmd, 5, vgfree, "vg_free") FIELD(VGS, vg, STR, "SYS ID", system_id, 6, string, "vg_sysid") diff --git a/lib/report/report.c b/lib/report/report.c index 955366fd9..f38539418 100644 --- a/lib/report/report.c +++ b/lib/report/report.c @@ -98,6 +98,20 @@ struct row { struct field *(*sort_fields)[]; /* Fields in sort order */ }; +static char _alloc_policy_char(alloc_policy_t alloc) +{ + switch (alloc) { + case ALLOC_CONTIGUOUS: + return 'c'; + case ALLOC_NORMAL: + return 'n'; + case ALLOC_ANYWHERE: + return 'a'; + default: + return 'i'; + } +} + /* * Data-munging functions to prepare each data type for display and sorting */ @@ -279,10 +293,7 @@ static int _lvstatus_disp(struct report_handle *rh, struct field *field, else repstr[1] = 'r'; - if (lv->alloc == ALLOC_CONTIGUOUS) - repstr[2] = 'c'; - else - repstr[2] = 'n'; + repstr[2] = _alloc_policy_char(lv->alloc); if (lv->status & LOCKED) repstr[2] = toupper(repstr[2]); @@ -354,34 +365,36 @@ static int _pvstatus_disp(struct report_handle *rh, struct field *field, static int _vgstatus_disp(struct report_handle *rh, struct field *field, const void *data) { - const uint32_t status = *(const uint32_t *) data; + const struct volume_group *vg = (const struct volume_group *) data; char *repstr; - if (!(repstr = pool_zalloc(rh->mem, 5))) { + if (!(repstr = pool_zalloc(rh->mem, 6))) { log_error("pool_alloc failed"); return 0; } - if (status & LVM_WRITE) + if (vg->status & LVM_WRITE) repstr[0] = 'w'; else repstr[0] = 'r'; - if (status & RESIZEABLE_VG) + if (vg->status & RESIZEABLE_VG) repstr[1] = 'z'; else repstr[1] = '-'; - if (status & EXPORTED_VG) + if (vg->status & EXPORTED_VG) repstr[2] = 'x'; else repstr[2] = '-'; - if (status & PARTIAL_VG) + if (vg->status & PARTIAL_VG) repstr[3] = 'p'; else repstr[3] = '-'; + repstr[4] = _alloc_policy_char(vg->alloc); + field->report_string = repstr; field->sort_value = (const void *) field->report_string; diff --git a/tools/args.h b/tools/args.h index ee0439bc9..7cc63dbd5 100644 --- a/tools/args.h +++ b/tools/args.h @@ -42,6 +42,7 @@ arg(refresh_ARG, '\0', "refresh", NULL) arg(mknodes_ARG, '\0', "mknodes", NULL) arg(minor_ARG, '\0', "minor", minor_arg) arg(type_ARG, '\0', "type", segtype_arg) +arg(alloc_ARG, '\0', "alloc", alloc_arg) /* Allow some variations */ arg(resizable_ARG, '\0', "resizable", yes_no_arg) diff --git a/tools/commands.h b/tools/commands.h index 2afccc67f..823626468 100644 --- a/tools/commands.h +++ b/tools/commands.h @@ -52,6 +52,7 @@ xx(lvchange, "\t[-A|--autobackup y|n]\n" "\t[-a|--available y|n]\n" "\t[--addtag Tag]\n" + "\t[--alloc AllocationType]\n" "\t[-C|--contiguous y|n]\n" "\t[-d|--debug]\n" "\t[--deltag Tag]\n" @@ -68,7 +69,7 @@ xx(lvchange, "\t[--version]" "\n" "\tLogicalVolume[Path] [LogicalVolume[Path]...]\n", - autobackup_ARG, available_ARG, contiguous_ARG, force_ARG, + alloc_ARG, autobackup_ARG, available_ARG, contiguous_ARG, force_ARG, ignorelockingfailure_ARG, major_ARG, minor_ARG, partial_ARG, permission_ARG, persistent_ARG, readahead_ARG, refresh_ARG, addtag_ARG, deltag_ARG, test_ARG) @@ -78,6 +79,7 @@ xx(lvcreate, "lvcreate " "\n" "\t[-A|--autobackup {y|n}]\n" "\t[--addtag Tag]\n" + "\t[--alloc AllocationType]\n" "\t[-C|--contiguous {y|n}]\n" "\t[-d|--debug]\n" "\t[-h|-?|--help]\n" @@ -99,6 +101,7 @@ xx(lvcreate, "\t[-c|--chunksize]\n" "\t[-A|--autobackup {y|n}]\n" "\t[--addtag Tag]\n" + "\t[--alloc AllocationType]\n" "\t[-C|--contiguous {y|n}]\n" "\t[-d|--debug]\n" "\t[-h|-?|--help]\n" @@ -114,10 +117,10 @@ xx(lvcreate, "\t[--version]\n" "\tOriginalLogicalVolume[Path] [PhysicalVolumePath...]\n\n", - autobackup_ARG, chunksize_ARG, contiguous_ARG, extents_ARG, major_ARG, - minor_ARG, name_ARG, permission_ARG, persistent_ARG, readahead_ARG, size_ARG, - snapshot_ARG, stripes_ARG, stripesize_ARG, addtag_ARG, test_ARG, type_ARG, - zero_ARG) + addtag_ARG, alloc_ARG, autobackup_ARG, chunksize_ARG, contiguous_ARG, + extents_ARG, major_ARG, minor_ARG, name_ARG, permission_ARG, + persistent_ARG, readahead_ARG, size_ARG, snapshot_ARG, stripes_ARG, + stripesize_ARG, test_ARG, type_ARG, zero_ARG) xx(lvdisplay, "Display information about a logical volume", @@ -160,6 +163,7 @@ xx(lvextend, "Add space to a logical volume", "lvextend\n" "\t[-A|--autobackup y|n]\n" + "\t[--alloc AllocationType]\n" "\t[-d|--debug]\n" "\t[-h|--help]\n" "\t[-i|--stripes Stripes [-I|--stripesize StripeSize]]\n" @@ -171,7 +175,7 @@ xx(lvextend, "\t[--version]" "\n" "\tLogicalVolume[Path] [ PhysicalVolumePath... ]\n", - autobackup_ARG, extents_ARG, size_ARG, stripes_ARG, + alloc_ARG, autobackup_ARG, extents_ARG, size_ARG, stripes_ARG, stripesize_ARG, test_ARG, type_ARG) xx(lvmchange, @@ -266,6 +270,7 @@ xx(lvresize, "Resize a logical volume", "lvresize\n" "\t[-A|--autobackup y|n]\n" + "\t[--alloc AllocationType]\n" "\t[-d|--debug]\n" "\t[-h|--help]\n" "\t[-i|--stripes Stripes [-I|--stripesize StripeSize]]\n" @@ -277,8 +282,8 @@ xx(lvresize, "\t[--version]" "\n" "\tLogicalVolume[Path] [ PhysicalVolumePath... ]\n", - autobackup_ARG, extents_ARG, size_ARG, stripes_ARG, stripesize_ARG, - test_ARG, type_ARG) + alloc_ARG, autobackup_ARG, extents_ARG, size_ARG, stripes_ARG, + stripesize_ARG, test_ARG, type_ARG) xx(lvs, "Display information about logical volumes", @@ -536,6 +541,7 @@ xx(vgchange, "Change volume group attributes", "vgchange" "\n" "\t[-A|--autobackup {y|n}] " "\n" + "\t[--alloc AllocationType] " "\n" "\t[-P|--partial] " "\n" "\t[-d|--debug] " "\n" "\t[-h|--help] " "\n" @@ -551,9 +557,9 @@ xx(vgchange, "\t --deltag Tag}\n" "\t[VolumeGroupName...]\n", - allocation_ARG, autobackup_ARG, available_ARG, ignorelockingfailure_ARG, - logicalvolume_ARG, partial_ARG, resizeable_ARG, resizable_ARG, deltag_ARG, - addtag_ARG, test_ARG, uuid_ARG) + addtag_ARG, alloc_ARG, allocation_ARG, autobackup_ARG, available_ARG, + deltag_ARG, ignorelockingfailure_ARG, logicalvolume_ARG, partial_ARG, + resizeable_ARG, resizable_ARG, test_ARG, uuid_ARG) xx(vgck, "Check the consistency of volume group(s)", @@ -586,6 +592,7 @@ xx(vgcreate, "vgcreate" "\n" "\t[-A|--autobackup {y|n}] " "\n" "\t[--addtag Tag] " "\n" + "\t[--alloc AllocationType] " "\n" "\t[-d|--debug]" "\n" "\t[-h|--help]" "\n" "\t[-l|--maxlogicalvolumes MaxLogicalVolumes]" "\n" @@ -597,8 +604,8 @@ xx(vgcreate, "\t[--version] " "\n" "\tVolumeGroupName PhysicalVolume [PhysicalVolume...]\n", - autobackup_ARG, maxlogicalvolumes_ARG, maxphysicalvolumes_ARG, - metadatatype_ARG, physicalextentsize_ARG, addtag_ARG, test_ARG) + addtag_ARG, alloc_ARG, autobackup_ARG, maxlogicalvolumes_ARG, + maxphysicalvolumes_ARG, metadatatype_ARG, physicalextentsize_ARG, test_ARG) xx(vgdisplay, "Display volume group information", diff --git a/tools/lvchange.c b/tools/lvchange.c index a80b043eb..df81e3651 100644 --- a/tools/lvchange.c +++ b/tools/lvchange.c @@ -117,45 +117,30 @@ static int lvchange_refresh(struct cmd_context *cmd, struct logical_volume *lv) return 1; } -static int lvchange_contiguous(struct cmd_context *cmd, - struct logical_volume *lv) +static int lvchange_alloc(struct cmd_context *cmd, struct logical_volume *lv) { int want_contiguous = 0; + alloc_policy_t alloc; - if (strcmp(arg_str_value(cmd, contiguous_ARG, "n"), "n")) - want_contiguous = 1; + want_contiguous = strcmp(arg_str_value(cmd, contiguous_ARG, "n"), "n"); + alloc = want_contiguous ? ALLOC_CONTIGUOUS : ALLOC_INHERIT; + alloc = (alloc_policy_t) arg_uint_value(cmd, alloc_ARG, alloc); - if (want_contiguous && lv->alloc == ALLOC_CONTIGUOUS) { + if (alloc == lv->alloc) { log_error("Allocation policy of logical volume \"%s\" is " - "already contiguous", lv->name); + "already %s", lv->name, get_alloc_string(alloc)); return 0; } - if (!want_contiguous && lv->alloc != ALLOC_CONTIGUOUS) { - log_error - ("Allocation policy of logical volume \"%s\" is already" - " not contiguous", lv->name); - return 0; - } + lv->alloc = alloc; -/******** FIXME lv_check_contiguous? - if (want_contiguous) - && (ret = lv_check_contiguous(vg, lv_index + 1)) == FALSE) { - log_error("No contiguous logical volume \"%s\"", lv->name); - return 0; -*********/ + /* FIXME If contiguous, check existing extents already are */ - if (want_contiguous) { - lv->alloc = ALLOC_CONTIGUOUS; - log_verbose("Setting contiguous allocation policy for \"%s\"", - lv->name); - } else { - lv->alloc = ALLOC_DEFAULT; - log_verbose("Reverting to default allocation policy for \"%s\"", - lv->name); - } + log_verbose("Setting contiguous allocation policy for \"%s\" to %s", + lv->name, get_alloc_string(alloc)); log_very_verbose("Updating logical volume \"%s\" on disk(s)", lv->name); + if (!vg_write(lv->vg)) { stack; return 0; @@ -170,7 +155,6 @@ static int lvchange_contiguous(struct cmd_context *cmd, } return 1; - } static int lvchange_readahead(struct cmd_context *cmd, @@ -365,7 +349,8 @@ static int lvchange_single(struct cmd_context *cmd, struct logical_volume *lv, if (!(lv->vg->status & LVM_WRITE) && (arg_count(cmd, contiguous_ARG) || arg_count(cmd, permission_ARG) || - arg_count(cmd, readahead_ARG) || arg_count(cmd, persistent_ARG))) { + arg_count(cmd, readahead_ARG) || arg_count(cmd, persistent_ARG) || + arg_count(cmd, alloc_ARG))) { log_error("Only -a permitted with read-only volume " "group \"%s\"", lv->vg->name); return EINVALID_CMD_LINE; @@ -373,7 +358,8 @@ static int lvchange_single(struct cmd_context *cmd, struct logical_volume *lv, if (lv_is_origin(lv) && (arg_count(cmd, contiguous_ARG) || arg_count(cmd, permission_ARG) || - arg_count(cmd, readahead_ARG) || arg_count(cmd, persistent_ARG))) { + arg_count(cmd, readahead_ARG) || arg_count(cmd, persistent_ARG) || + arg_count(cmd, alloc_ARG))) { log_error("Can't change logical volume \"%s\" under snapshot", lv->name); return ECMD_FAILED; @@ -401,11 +387,11 @@ static int lvchange_single(struct cmd_context *cmd, struct logical_volume *lv, } /* allocation policy change */ - if (arg_count(cmd, contiguous_ARG)) { + if (arg_count(cmd, contiguous_ARG) || arg_count(cmd, alloc_ARG)) { if (!archived && !archive(lv->vg)) return ECMD_FAILED; archived = 1; - doit += lvchange_contiguous(cmd, lv); + doit += lvchange_alloc(cmd, lv); } /* read ahead sector change */ @@ -461,9 +447,10 @@ int lvchange(struct cmd_context *cmd, int argc, char **argv) && !arg_count(cmd, permission_ARG) && !arg_count(cmd, readahead_ARG) && !arg_count(cmd, minor_ARG) && !arg_count(cmd, major_ARG) && !arg_count(cmd, persistent_ARG) && !arg_count(cmd, addtag_ARG) - && !arg_count(cmd, deltag_ARG) && !arg_count(cmd, refresh_ARG)) { + && !arg_count(cmd, deltag_ARG) && !arg_count(cmd, refresh_ARG) + && !arg_count(cmd, alloc_ARG)) { log_error("One or more of -a, -C, -j, -m, -M, -p, -r, " - "--refresh, --addtag or --deltag required"); + "--refresh, --alloc, --addtag or --deltag required"); return EINVALID_CMD_LINE; } @@ -471,7 +458,7 @@ int lvchange(struct cmd_context *cmd, int argc, char **argv) (arg_count(cmd, contiguous_ARG) || arg_count(cmd, permission_ARG) || arg_count(cmd, readahead_ARG) || arg_count(cmd, persistent_ARG) || arg_count(cmd, addtag_ARG) || arg_count(cmd, deltag_ARG) || - arg_count(cmd, refresh_ARG))) { + arg_count(cmd, refresh_ARG) || arg_count(cmd, alloc_ARG))) { log_error("Only -a permitted with --ignorelockingfailure"); return EINVALID_CMD_LINE; } @@ -492,6 +479,11 @@ int lvchange(struct cmd_context *cmd, int argc, char **argv) return EINVALID_CMD_LINE; } + if (arg_count(cmd, contiguous_ARG) && arg_count(cmd, alloc_ARG)) { + log_error("Only one of --alloc and --contiguous permitted"); + return EINVALID_CMD_LINE; + } + return process_each_lv(cmd, argc, argv, LCK_VG_WRITE, NULL, &lvchange_single); } diff --git a/tools/lvcreate.c b/tools/lvcreate.c index 3e00509dc..10ff466b8 100644 --- a/tools/lvcreate.c +++ b/tools/lvcreate.c @@ -21,7 +21,6 @@ struct lvcreate_params { /* flags */ int snapshot; int zero; - int contiguous; int major; int minor; @@ -43,6 +42,7 @@ struct lvcreate_params { uint32_t permission; uint32_t read_ahead; + alloc_policy_t alloc; int pv_count; char **pvs; @@ -217,6 +217,8 @@ static int _read_stripe_params(struct lvcreate_params *lp, static int _read_params(struct lvcreate_params *lp, struct cmd_context *cmd, int argc, char **argv) { + int contiguous; + memset(lp, 0, sizeof(*lp)); /* @@ -269,9 +271,18 @@ static int _read_params(struct lvcreate_params *lp, struct cmd_context *cmd, lp->zero = strcmp(arg_str_value(cmd, zero_ARG, "y"), "n"); /* - * Contiguous ? + * Alloc policy */ - lp->contiguous = strcmp(arg_str_value(cmd, contiguous_ARG, "n"), "n"); + contiguous = strcmp(arg_str_value(cmd, contiguous_ARG, "n"), "n"); + + lp->alloc = contiguous ? ALLOC_CONTIGUOUS : ALLOC_INHERIT; + + lp->alloc = (alloc_policy_t) arg_uint_value(cmd, alloc_ARG, lp->alloc); + + if (contiguous && (lp->alloc != ALLOC_CONTIGUOUS)) { + log_error("Conflicting contiguous and alloc arguments"); + return 0; + } /* * Read ahead. @@ -365,16 +376,12 @@ static int _lvcreate(struct cmd_context *cmd, struct lvcreate_params *lp) uint32_t size_rest; uint32_t status = 0; uint64_t tmp_size; - alloc_policy_t alloc = ALLOC_DEFAULT; struct volume_group *vg; struct logical_volume *lv, *org = NULL; struct list *pvh; const char *tag; int consistent = 1; - if (lp->contiguous) - alloc = ALLOC_CONTIGUOUS; - status |= lp->permission | VISIBLE_LV; /* does VG exist? */ @@ -487,13 +494,13 @@ static int _lvcreate(struct cmd_context *cmd, struct lvcreate_params *lp) } if (!(lv = lv_create_empty(vg->fid, lp->lv_name, "lvol%d", - status, alloc, vg))) { + status, lp->alloc, vg))) { stack; return 0; } if (!lv_extend(vg->fid, lv, lp->segtype, lp->stripes, lp->stripe_size, - lp->mirrors, lp->extents, NULL, 0u, 0u, pvh, alloc)) { + lp->mirrors, lp->extents, NULL, 0u, 0u, pvh, lp->alloc)) { stack; return 0; } diff --git a/tools/lvmcmdline.c b/tools/lvmcmdline.c index 010131f01..4117be64b 100644 --- a/tools/lvmcmdline.c +++ b/tools/lvmcmdline.c @@ -287,6 +287,21 @@ int permission_arg(struct cmd_context *cmd, struct arg *a) return 1; } +int alloc_arg(struct cmd_context *cmd, struct arg *a) +{ + alloc_policy_t alloc; + + a->sign = SIGN_NONE; + + alloc = get_alloc_from_string(a->value); + if (alloc == ALLOC_INVALID) + return 0; + + a->ui_value = (uint32_t) alloc; + + return 1; +} + int segtype_arg(struct cmd_context *cmd, struct arg *a) { if (!(a->ptr = (void *) get_segtype_from_string(cmd, a->value))) diff --git a/tools/lvresize.c b/tools/lvresize.c index 7ac448727..32c923048 100644 --- a/tools/lvresize.c +++ b/tools/lvresize.c @@ -115,6 +115,7 @@ static int _lvresize(struct cmd_context *cmd, struct lvresize_params *lp) uint32_t seg_stripes = 0, seg_stripesize = 0, seg_size = 0; uint32_t extents_used = 0; uint32_t size_rest; + alloc_policy_t alloc; char *lock_lvid; struct lv_list *lvl; int consistent = 1; @@ -170,6 +171,8 @@ static int _lvresize(struct cmd_context *cmd, struct lvresize_params *lp) goto error; } + alloc = (alloc_policy_t) arg_uint_value(cmd, alloc_ARG, lv->alloc); + if (lp->size) { if (lp->size % vg->extent_size) { if (lp->sign == SIGN_MINUS) @@ -393,7 +396,7 @@ static int _lvresize(struct cmd_context *cmd, struct lvresize_params *lp) if (!lv_extend(vg->fid, lv, lp->segtype, lp->stripes, lp->stripe_size, 0u, lp->extents - lv->le_count, - NULL, 0u, 0u, lp->pvh, lv->alloc)) { + NULL, 0u, 0u, lp->pvh, alloc)) { goto error; } } diff --git a/tools/tools.h b/tools/tools.h index 0cd9b244d..6433dae5b 100644 --- a/tools/tools.h +++ b/tools/tools.h @@ -121,6 +121,7 @@ int permission_arg(struct cmd_context *cmd, struct arg *a); int metadatatype_arg(struct cmd_context *cmd, struct arg *a); int units_arg(struct cmd_context *cmd, struct arg *a); int segtype_arg(struct cmd_context *cmd, struct arg *a); +int alloc_arg(struct cmd_context *cmd, struct arg *a); char yes_no_prompt(const char *prompt, ...); diff --git a/tools/vgchange.c b/tools/vgchange.c index 940bd6d0c..8f9f99bb6 100644 --- a/tools/vgchange.c +++ b/tools/vgchange.c @@ -86,6 +86,40 @@ static int _vgchange_available(struct cmd_context *cmd, struct volume_group *vg) return ECMD_PROCESSED; } +static int _vgchange_alloc(struct cmd_context *cmd, struct volume_group *vg) +{ + alloc_policy_t alloc; + + alloc = (alloc_policy_t) arg_uint_value(cmd, alloc_ARG, ALLOC_NORMAL); + + if (alloc == ALLOC_INHERIT) { + log_error("Volume Group allocation policy cannot inherit " + "from anything"); + return EINVALID_CMD_LINE; + } + + if (alloc == vg->alloc) { + log_error("Volume group allocation policy is already %s", + get_alloc_string(vg->alloc)); + return ECMD_FAILED; + } + + if (!archive(vg)) + return ECMD_FAILED; + + vg->alloc = alloc; + + if (!vg_write(vg) || !vg_commit(vg)) + return ECMD_FAILED; + + backup(vg); + + log_print("Volume group \"%s\" successfully changed", vg->name); + + return ECMD_PROCESSED; +} + + static int _vgchange_resizeable(struct cmd_context *cmd, struct volume_group *vg) { @@ -280,6 +314,9 @@ static int vgchange_single(struct cmd_context *cmd, const char *vg_name, else if (arg_count(cmd, uuid_ARG)) r = _vgchange_uuid(cmd, vg); + else if (arg_count(cmd, alloc_ARG)) + r = _vgchange_alloc(cmd, vg); + return r; } @@ -288,17 +325,20 @@ int vgchange(struct cmd_context *cmd, int argc, char **argv) if (! (arg_count(cmd, available_ARG) + arg_count(cmd, logicalvolume_ARG) + arg_count(cmd, resizeable_ARG) + arg_count(cmd, deltag_ARG) + - arg_count(cmd, addtag_ARG) + arg_count(cmd, uuid_ARG))) { - log_error("One of -a, -l, -x, --addtag, --deltag or --uuid " - "options required"); + arg_count(cmd, addtag_ARG) + arg_count(cmd, uuid_ARG) + + arg_count(cmd, alloc_ARG))) { + log_error("One of -a, -l, -x, --alloc, --addtag, --deltag " + "or --uuid required"); return EINVALID_CMD_LINE; } + /* FIXME Cope with several changes at once! */ if (arg_count(cmd, available_ARG) + arg_count(cmd, logicalvolume_ARG) + arg_count(cmd, resizeable_ARG) + arg_count(cmd, deltag_ARG) + - arg_count(cmd, addtag_ARG) + arg_count(cmd, uuid_ARG) > 1) { - log_error("Only one of -a, -l, -x, --addtag, --deltag or --uuid" - " options allowed"); + arg_count(cmd, addtag_ARG) + arg_count(cmd, alloc_ARG) + + arg_count(cmd, uuid_ARG) > 1) { + log_error("Only one of -a, -l, -x, --alloc, --addtag, --deltag " + "or --uuid allowed"); return EINVALID_CMD_LINE; } diff --git a/tools/vgcreate.c b/tools/vgcreate.c index ca44a7c9d..e073e4a45 100644 --- a/tools/vgcreate.c +++ b/tools/vgcreate.c @@ -25,6 +25,7 @@ int vgcreate(struct cmd_context *cmd, int argc, char **argv) char vg_path[PATH_MAX]; struct volume_group *vg; const char *tag; + alloc_policy_t alloc; if (!argc) { log_error("Please provide volume group name and " @@ -40,6 +41,13 @@ int vgcreate(struct cmd_context *cmd, int argc, char **argv) vg_name = argv[0]; max_lv = arg_uint_value(cmd, maxlogicalvolumes_ARG, 0); max_pv = arg_uint_value(cmd, maxphysicalvolumes_ARG, 0); + alloc = (alloc_policy_t) arg_uint_value(cmd, alloc_ARG, ALLOC_NORMAL); + + if (alloc == ALLOC_INHERIT) { + log_error("Volume Group allocation policy cannot inherit " + "from anything"); + return EINVALID_CMD_LINE; + } if (!(cmd->fmt->features & FMT_UNLIMITED_VOLS)) { if (!max_lv) @@ -92,7 +100,7 @@ int vgcreate(struct cmd_context *cmd, int argc, char **argv) } /* Create the new VG */ - if (!(vg = vg_create(cmd, vg_name, extent_size, max_pv, max_lv, + if (!(vg = vg_create(cmd, vg_name, extent_size, max_pv, max_lv, alloc, argc - 1, argv + 1))) return ECMD_FAILED; diff --git a/tools/vgsplit.c b/tools/vgsplit.c index 692d0a7c2..2ff4e93dd 100644 --- a/tools/vgsplit.c +++ b/tools/vgsplit.c @@ -215,7 +215,8 @@ int vgsplit(struct cmd_context *cmd, int argc, char **argv) /* Create new VG structure */ if (!(vg_to = vg_create(cmd, vg_name_to, vg_from->extent_size, - vg_from->max_pv, vg_from->max_lv, 0, NULL))) + vg_from->max_pv, vg_from->max_lv, + vg_from->alloc, 0, NULL))) goto error; /* Archive vg_from before changing it */ |