From 2107f482080b9d7bdf63e5c98016b1aa48cba282 Mon Sep 17 00:00:00 2001 From: Joe Thornber Date: Mon, 12 Nov 2001 12:16:57 +0000 Subject: [PATCH] o Split struct io_space into: struct format_handler - format methods struct format_instance - links instance data, methods, and cmd struct cmd_context - dev_dir, memory allocator, device filter --- lib/format1/format1.c | 119 +++++++++++++++----------------- lib/format1/format1.h | 3 +- lib/format1/import-export.c | 19 +---- lib/metadata/lv_manip.c | 54 ++++++++------- lib/metadata/metadata.c | 64 ++++++++++------- lib/metadata/metadata.h | 134 +++++++++++++++++++----------------- 6 files changed, 193 insertions(+), 200 deletions(-) diff --git a/lib/format1/format1.c b/lib/format1/format1.c index 57766fc81..be93d737f 100644 --- a/lib/format1/format1.c +++ b/lib/format1/format1.c @@ -27,6 +27,7 @@ static int _check_vgs(struct list *pvs) if (!first) first = dl; + else if (memcmp(&first->vgd, &dl->vgd, sizeof(first->vgd))) { log_err("VG data differs between PVs %s and %s", dev_name(first->dev), dev_name(dl->dev)); @@ -86,7 +87,8 @@ static struct volume_group *_build_vg(struct pool *mem, struct list *pvs) return NULL; } -static struct volume_group *_vg_read(struct io_space *is, const char *vg_name) +static struct volume_group *_vg_read(struct format_instance *fi, + const char *vg_name) { struct pool *mem = pool_create(1024 * 10); struct list pvs; @@ -99,15 +101,14 @@ static struct volume_group *_vg_read(struct io_space *is, const char *vg_name) } /* Strip prefix if present */ - if (!strncmp(vg_name, is->prefix, strlen(is->prefix))) - vg_name += strlen(is->prefix); + vg_name = strip_dir(vg_name, fi->cmd->dev_dir); - if (!read_pvs_in_vg(vg_name, is->filter, mem, &pvs)) { + if (!read_pvs_in_vg(vg_name, fi->cmd->filter, mem, &pvs)) { stack; return NULL; } - if (!(vg = _build_vg(is->mem, &pvs))) + if (!(vg = _build_vg(fi->cmd->mem, &pvs))) stack; pool_destroy(mem); @@ -174,7 +175,7 @@ static int _flatten_vg(struct pool *mem, struct volume_group *vg, return 1; } -static int _vg_write(struct io_space *is, struct volume_group *vg) +static int _vg_write(struct format_instance *fi, struct volume_group *vg) { struct pool *mem = pool_create(1024 * 10); struct list pvs; @@ -187,17 +188,17 @@ static int _vg_write(struct io_space *is, struct volume_group *vg) list_init(&pvs); - r = (_flatten_vg(mem, vg, &pvs, is->prefix, is->filter) && + r = (_flatten_vg(mem, vg, &pvs, fi->cmd->dev_dir, fi->cmd->filter) && write_pvds(&pvs)); pool_destroy(mem); return r; } -static struct physical_volume *_pv_read(struct io_space *is, +static struct physical_volume *_pv_read(struct format_instance *fi, const char *name) { struct pool *mem = pool_create(1024); - struct physical_volume *pv; + struct physical_volume *pv = NULL; struct disk_list *dl; struct device *dev; @@ -208,35 +209,33 @@ static struct physical_volume *_pv_read(struct io_space *is, return NULL; } - if (!(dev = dev_cache_get(name, is->filter))) { + if (!(dev = dev_cache_get(name, fi->cmd->filter))) { stack; - goto bad; + goto out; } if (!(dl = read_disk(dev, mem, NULL))) { stack; - goto bad; + goto out; } - if (!(pv = pool_alloc(is->mem, sizeof(*pv)))) { + if (!(pv = pool_alloc(fi->cmd->mem, sizeof(*pv)))) { stack; - goto bad; + goto out; } - if (!import_pv(is->mem, dl->dev, pv, &dl->pvd)) { + if (!import_pv(fi->cmd->mem, dl->dev, pv, &dl->pvd)) { stack; - goto bad; + pool_free(fi->cmd->mem, pv); + pv = NULL; } + out: pool_destroy(mem); return pv; - - bad: - pool_destroy(mem); - return NULL; } -static struct list *_get_pvs(struct io_space *is) +static struct list *_get_pvs(struct format_instance *fi) { struct pool *mem = pool_create(1024 * 10); struct list pvs, *results; @@ -247,7 +246,7 @@ static struct list *_get_pvs(struct io_space *is) return NULL; } - if (!(results = pool_alloc(is->mem, sizeof(*results)))) { + if (!(results = pool_alloc(fi->cmd->mem, sizeof(*results)))) { stack; pool_destroy(mem); return NULL; @@ -256,12 +255,12 @@ static struct list *_get_pvs(struct io_space *is) list_init(&pvs); list_init(results); - if (!read_pvs_in_vg(NULL, is->filter, mem, &pvs)) { + if (!read_pvs_in_vg(NULL, fi->cmd->filter, mem, &pvs)) { stack; goto bad; } - if (!import_pvs(is->mem, &pvs, results, &count)) { + if (!import_pvs(fi->cmd->mem, &pvs, results, &count)) { stack; goto bad; } @@ -270,7 +269,7 @@ static struct list *_get_pvs(struct io_space *is) return results; bad: - pool_free(is->mem, results); + pool_free(fi->cmd->mem, results); pool_destroy(mem); return NULL; } @@ -289,10 +288,10 @@ static int _find_vg_name(struct list *names, const char *vg) return 0; } -static struct list *_get_vgs(struct io_space *is) +static struct list *_get_vgs(struct format_instance *fi) { struct list *pvh; - struct list *pvs, *names = pool_alloc(is->mem, sizeof(*names)); + struct list *pvs, *names = pool_alloc(fi->cmd->mem, sizeof(*names)); struct name_list *nl; if (!names) { @@ -302,7 +301,7 @@ static struct list *_get_vgs(struct io_space *is) list_init(names); - if (!(pvs = _get_pvs(is))) { + if (!(pvs = _get_pvs(fi))) { stack; goto bad; } @@ -314,12 +313,12 @@ static struct list *_get_vgs(struct io_space *is) _find_vg_name(names, pvl->pv.vg_name)) continue; - if (!(nl = pool_alloc(is->mem, sizeof(*nl)))) { + if (!(nl = pool_alloc(fi->cmd->mem, sizeof(*nl)))) { stack; goto bad; } - if (!(nl->name = pool_strdup(is->mem, pvl->pv.vg_name))) { + if (!(nl->name = pool_strdup(fi->cmd->mem, pvl->pv.vg_name))) { stack; goto bad; } @@ -333,11 +332,11 @@ static struct list *_get_vgs(struct io_space *is) return names; bad: - pool_free(is->mem, names); + pool_free(fi->cmd->mem, names); return NULL; } -static int _pv_setup(struct io_space *is, struct physical_volume *pv, +static int _pv_setup(struct format_instance *fi, struct physical_volume *pv, struct volume_group *vg) { /* @@ -351,7 +350,7 @@ static int _pv_setup(struct io_space *is, struct physical_volume *pv, return 1; } -static int _pv_write(struct io_space *is, struct physical_volume *pv) +static int _pv_write(struct format_instance *fi, struct physical_volume *pv) { struct pool *mem; struct disk_list *dl; @@ -401,7 +400,7 @@ static int _pv_write(struct io_space *is, struct physical_volume *pv) return 0; } -int _vg_setup(struct io_space *is, struct volume_group *vg) +int _vg_setup(struct format_instance *fi, struct volume_group *vg) { /* just check max_pv and max_lv */ if (vg->max_lv >= MAX_LV) @@ -439,44 +438,36 @@ int _vg_setup(struct io_space *is, struct volume_group *vg) return 1; } -void _destroy(struct io_space *ios) +void _destroy(struct format_instance *fi) { - dbg_free(ios->prefix); - pool_destroy(ios->mem); - dbg_free(ios); + dbg_free(fi); } -struct io_space *create_lvm1_format(const char *prefix, struct pool *mem, - struct dev_filter *filter) -{ - struct io_space *ios = dbg_malloc(sizeof(*ios)); - if (!ios) { - stack; - return NULL; - } +static struct format_handler _format1_ops = { + get_vgs: _get_vgs, + get_pvs: _get_pvs, + pv_read: _pv_read, + pv_setup: _pv_setup, + pv_write: _pv_write, + vg_read: _vg_read, + vg_setup: _vg_setup, + vg_write: _vg_write, + destroy: _destroy, +}; - ios->get_vgs = _get_vgs; - ios->get_pvs = _get_pvs; - ios->pv_read = _pv_read; - ios->pv_setup = _pv_setup; - ios->pv_write = _pv_write; - ios->vg_read = _vg_read; - ios->vg_setup = _vg_setup; - ios->vg_write = _vg_write; - ios->destroy = _destroy; +struct format_instance *create_lvm1_format(struct cmd_context *cmd) +{ + struct format_instance *fi = dbg_malloc(sizeof(*fi)); - ios->prefix = dbg_malloc(strlen(prefix) + 1); - if (!ios->prefix) { + if (!fi) { stack; - dbg_free(ios); - return 0; + return NULL; } - strcpy(ios->prefix, prefix); - ios->mem = mem; - ios->filter = filter; - ios->private = NULL; + fi->cmd = cmd; + fi->ops = &_format1_ops; + fi->private = NULL; - return ios; + return fi; } diff --git a/lib/format1/format1.h b/lib/format1/format1.h index d20b6b123..625612b92 100644 --- a/lib/format1/format1.h +++ b/lib/format1/format1.h @@ -9,7 +9,6 @@ #include "metadata.h" -struct io_space *create_lvm1_format(const char *prefix, struct pool *mem, - struct dev_filter *filter); +struct filter_instance *create_lvm1_format(struct cmd_context *cmd); #endif diff --git a/lib/format1/import-export.c b/lib/format1/import-export.c index 23c3d7655..cb8964008 100644 --- a/lib/format1/import-export.c +++ b/lib/format1/import-export.c @@ -526,22 +526,6 @@ int export_uuids(struct disk_list *dl, struct volume_group *vg) return 1; } -static int _get_lv_number(struct volume_group *vg, const char *name) -{ - /* FIXME: inefficient */ - int r = 0; - struct list *lvh; - - list_iterate(lvh, &vg->lvs) { - struct lv_list *ll = list_item(lvh, struct lv_list); - if (!strcmp(ll->lv.name, name)) - break; - r++; - } - - return r; -} - /* * This calculates the nasty pv_number and * lv_number fields used by LVM1. Very @@ -549,9 +533,8 @@ static int _get_lv_number(struct volume_group *vg, const char *name) */ void export_numbers(struct list *pvs, struct volume_group *vg) { - struct list *pvh, *lvh; + struct list *pvh; struct disk_list *dl; - struct lvd_list *ll; int pv_num = 1; list_iterate(pvh, pvs) { diff --git a/lib/metadata/lv_manip.c b/lib/metadata/lv_manip.c index c4070ae82..c410506b1 100644 --- a/lib/metadata/lv_manip.c +++ b/lib/metadata/lv_manip.c @@ -112,13 +112,11 @@ static int _alloc_simple(struct logical_volume *lv, allocated += _alloc_area(lv, allocated, pvm->pv, pva); if (allocated == lv->le_count) - break; + goto done; } - - if (allocated == lv->le_count) /* FIXME: yuck, repeated test */ - break; } + done: if (allocated != lv->le_count) { log_error("Insufficient free logical extents to " "allocate logical volume %s: %u required", @@ -165,13 +163,12 @@ static int _allocate(struct volume_group *vg, struct logical_volume *lv, vg->free_count -= lv->le_count - allocated; } - out: + out: pool_destroy(scratch); return r; } -struct logical_volume *lv_create(struct io_space *ios, - const char *name, +struct logical_volume *lv_create(const char *name, uint32_t status, uint32_t stripes, uint32_t stripe_size, @@ -179,6 +176,7 @@ struct logical_volume *lv_create(struct io_space *ios, struct volume_group *vg, struct list *acceptable_pvs) { + struct cmd_context *cmd = vg->cmd; struct lv_list *ll = NULL; struct logical_volume *lv; int i; @@ -201,7 +199,7 @@ struct logical_volume *lv_create(struct io_space *ios, return NULL; } - if (!(ll = pool_zalloc(ios->mem, sizeof(*ll)))) { + if (!(ll = pool_zalloc(cmd->mem, sizeof(*ll)))) { stack; return NULL; } @@ -212,7 +210,7 @@ struct logical_volume *lv_create(struct io_space *ios, strcpy(lv->id.uuid, ""); - if (!(lv->name = pool_strdup(ios->mem, name))) { + if (!(lv->name = pool_strdup(cmd->mem, name))) { stack; goto bad; } @@ -223,7 +221,8 @@ struct logical_volume *lv_create(struct io_space *ios, lv->size = extents * vg->extent_size; lv->le_count = extents; - if (!(lv->map = pool_zalloc(ios->mem, sizeof(*lv->map) * extents))) { + if (!(lv->map = pool_zalloc(cmd->mem, + sizeof(*lv->map) * extents))) { stack; goto bad; } @@ -233,9 +232,8 @@ struct logical_volume *lv_create(struct io_space *ios, goto bad; } - for (i = 0; i < lv->le_count; i++) { + for (i = 0; i < lv->le_count; i++) lv->map[i].pv->pe_allocated++; - } vg->lv_count++; list_add(&vg->lvs, &ll->list); @@ -243,15 +241,16 @@ struct logical_volume *lv_create(struct io_space *ios, return lv; - bad: + bad: if (ll) - pool_free(ios->mem, ll); + pool_free(cmd->mem, ll); return NULL; } -int lv_reduce(struct io_space *ios, struct logical_volume *lv, uint32_t extents) +int lv_reduce(struct logical_volume *lv, uint32_t extents) { + // FIXME: merge with Alasdair's version in tools if (extents % lv->stripes) { log_error("For a striped volume you must reduce by a " "multiple of the number of stripes"); @@ -269,15 +268,15 @@ int lv_reduce(struct io_space *ios, struct logical_volume *lv, uint32_t extents) return 1; } -int lv_extend(struct io_space *ios, - struct logical_volume *lv, uint32_t extents, +int lv_extend(struct logical_volume *lv, uint32_t extents, struct list *acceptable_pvs) { + struct cmd_context *cmd = lv->vg->cmd; struct pe_specifier *new_map; struct logical_volume *new_lv; int i; - if (!(new_map = pool_zalloc(ios->mem, sizeof(*new_map) * + if (!(new_map = pool_zalloc(cmd->mem, sizeof(*new_map) * (extents + lv->le_count)))) { stack; return 0; @@ -285,8 +284,8 @@ int lv_extend(struct io_space *ios, memcpy(new_map, lv->map, sizeof(*new_map) * lv->le_count); - if (!(new_lv = pool_alloc(ios->mem, sizeof(*new_lv)))) { - pool_free(ios->mem, new_map); + if (!(new_lv = pool_alloc(cmd->mem, sizeof(*new_lv)))) { + pool_free(cmd->mem, new_map); stack; return 0; } @@ -300,17 +299,20 @@ int lv_extend(struct io_space *ios, goto bad; } - for (i = lv->le_count; i < new_lv->le_count; i++) { + for (i = lv->le_count; i < new_lv->le_count; i++) new_lv->map[i].pv->pe_allocated++; - } memcpy(lv, new_lv, sizeof(*lv)); - /* now you see why new_lv had to be allocated last */ - pool_free(ios->mem, new_lv); + /* + * new_lv had to be allocated last so we + * could free it without touching the new + * map + */ + pool_free(cmd->mem, new_lv); return 1; - bad: - pool_free(ios->mem, new_map); + bad: + pool_free(cmd->mem, new_map); return 0; } diff --git a/lib/metadata/metadata.c b/lib/metadata/metadata.c index 24a8eacd0..ee5023589 100644 --- a/lib/metadata/metadata.c +++ b/lib/metadata/metadata.c @@ -12,21 +12,22 @@ #include -int _add_pv_to_vg(struct io_space *ios, struct volume_group *vg, +int _add_pv_to_vg(struct format_instance *fi, struct volume_group *vg, const char *pv_name) { struct pv_list *pvl; struct physical_volume *pv; + struct pool *mem = fi->cmd->mem; log_verbose("Adding physical volume '%s' to volume group '%s'", pv_name, vg->name); - if (!(pvl = pool_alloc(ios->mem, sizeof (*pvl)))) { + if (!(pvl = pool_alloc(mem, sizeof (*pvl)))) { log_error("pv_list allocation for '%s' failed", pv_name); return 0; } - if (!(pv = ios->pv_read(ios, pv_name))) { + if (!(pv = fi->ops->pv_read(fi, pv_name))) { log_error("Failed to read existing physical volume '%s'", pv_name); return 0; @@ -44,7 +45,7 @@ int _add_pv_to_vg(struct io_space *ios, struct volume_group *vg, /* FIXME check this */ pv->exported = NULL; - if (!(pv->vg_name = pool_strdup(ios->mem, vg->name))) { + if (!(pv->vg_name = pool_strdup(mem, vg->name))) { log_error("vg->name allocation failed for '%s'", pv_name); return 0; } @@ -63,14 +64,14 @@ int _add_pv_to_vg(struct io_space *ios, struct volume_group *vg, /* * The next two fields should be corrected - * by ios->pv_setup. + * by fi->pv_setup. */ pv->pe_start = 0; pv->pe_count = pv->size / pv->pe_size; pv->pe_allocated = 0; - if (!ios->pv_setup(ios, pv, vg)) { + if (!fi->ops->pv_setup(fi, pv, vg)) { log_debug("Format-specific setup of physical volume '%s' " "failed.", pv_name); return 0; @@ -89,7 +90,7 @@ int _add_pv_to_vg(struct io_space *ios, struct volume_group *vg, return 0; } - memcpy(&pvl->pv, pv, sizeof (struct physical_volume)); + memcpy(&pvl->pv, pv, sizeof(*pv)); list_add(&vg->pvs, &pvl->list); vg->pv_count++; @@ -99,14 +100,14 @@ int _add_pv_to_vg(struct io_space *ios, struct volume_group *vg, return 1; } -int vg_extend(struct io_space *ios, struct volume_group *vg, int pv_count, - char **pv_names) +int vg_extend(struct format_instance *fi, + struct volume_group *vg, int pv_count, char **pv_names) { int i; /* attach each pv */ for (i = 0; i < pv_count; i++) - if (!_add_pv_to_vg(ios, vg, pv_names[i])) { + if (!_add_pv_to_vg(fi, vg, pv_names[i])) { log_error("Unable to add physical volume '%s' to " "volume group '%s'.", pv_names[i], vg->name); return 0; @@ -115,33 +116,43 @@ int vg_extend(struct io_space *ios, struct volume_group *vg, int pv_count, return 1; } -struct volume_group *vg_create(struct io_space *ios, const char *vg_name, +const char *strip_prefix(const char *vg_name, const char *dev_dir) +{ + int len = strlen(dev_dir); + if (!strncmp(vg_name, dev_dir, len)) + vg_name += len; + + return vg_name; +} + +struct volume_group *vg_create(struct format_instance *fi, const char *vg_name, uint32_t extent_size, int max_pv, int max_lv, int pv_count, char **pv_names) { struct volume_group *vg; + struct pool *mem = fi->cmd->mem; - if (!(vg = pool_alloc(ios->mem, sizeof (*vg)))) { + if (!(vg = pool_alloc(mem, sizeof (*vg)))) { stack; return NULL; } /* is this vg name already in use ? */ - if (ios->vg_read(ios, vg_name)) { + if (fi->ops->vg_read(fi, vg_name)) { log_err("A volume group called '%s' already exists.", vg_name); goto bad; } if (!id_create(&vg->id)) { - log_err("Couldn't create uuid for volume group '%s'.", vg_name); + log_err("Couldn't create uuid for volume group '%s'.", + vg_name); goto bad; } /* Strip prefix if present */ - if (!strncmp(vg_name, ios->prefix, strlen(ios->prefix))) - vg_name += strlen(ios->prefix); + vg_name = strip_dir(vg_name, fi->cmd->dev_dir); - if (!(vg->name = pool_strdup(ios->mem, vg_name))) { + if (!(vg->name = pool_strdup(mem, vg_name))) { stack; goto bad; } @@ -161,26 +172,27 @@ struct volume_group *vg_create(struct io_space *ios, const char *vg_name, vg->lv_count = 0; list_init(&vg->lvs); - if (!ios->vg_setup(ios, vg)) { + if (!fi->ops->vg_setup(fi, vg)) { log_error("Format specific setup of volume group '%s' failed.", vg_name); goto bad; } /* attach the pv's */ - if (!vg_extend(ios, vg, pv_count, pv_names)) + if (!vg_extend(fi, vg, pv_count, pv_names)) goto bad; return vg; - bad: - pool_free(ios->mem, vg); + bad: + pool_free(mem, vg); return NULL; } -struct physical_volume *pv_create(struct io_space *ios, const char *name) +struct physical_volume *pv_create(struct format_instance *fi, const char *name) { - struct physical_volume *pv = pool_alloc(ios->mem, sizeof (*pv)); + struct pool *mem = fi->cmd->mem; + struct physical_volume *pv = pool_alloc(mem, sizeof (*pv)); if (!pv) { stack; @@ -188,12 +200,12 @@ struct physical_volume *pv_create(struct io_space *ios, const char *name) } id_create(&pv->id); - if (!(pv->dev = dev_cache_get(name, ios->filter))) { + if (!(pv->dev = dev_cache_get(name, fi->cmd->filter))) { log_err("Couldn't find device '%s'", name); goto bad; } - if (!(pv->vg_name = pool_alloc(ios->mem, NAME_LEN))) { + if (!(pv->vg_name = pool_alloc(mem, NAME_LEN))) { stack; goto bad; } @@ -214,7 +226,7 @@ struct physical_volume *pv_create(struct io_space *ios, const char *name) return pv; bad: - pool_free(ios->mem, pv); + pool_free(mem, pv); return NULL; } diff --git a/lib/metadata/metadata.h b/lib/metadata/metadata.h index 1d4d9e362..9dfe55574 100644 --- a/lib/metadata/metadata.h +++ b/lib/metadata/metadata.h @@ -64,7 +64,11 @@ struct pe_specifier { uint32_t pe; }; +struct cmd_context; + struct volume_group { + struct cmd_context *cmd; + struct id id; char *name; @@ -119,101 +123,114 @@ struct lv_list { struct logical_volume lv; }; +struct cmd_context { + /* format handler allocates all objects from here */ + struct pool *mem; + + /* misc. vars needed by format handler */ + char *dev_dir; + struct dev_filter *filter; +}; + +struct format_instance { + struct cmd_context *cmd; + struct format_handler *ops; + void *private; +}; + + /* * Ownership of objects passes to caller. */ -struct io_space { +struct format_handler { /* * Returns a name_list of vg's. */ - struct list *(*get_vgs)(struct io_space *is); + struct list *(*get_vgs)(struct format_instance *fi); /* * Returns pv_list of fully-populated pv structures. */ - struct list *(*get_pvs)(struct io_space *is); + struct list *(*get_pvs)(struct format_instance *fi); /* * Return PV with given path. */ - struct physical_volume *(*pv_read)(struct io_space *is, + struct physical_volume *(*pv_read)(struct format_instance *fi, const char *pv_name); /* - * Tweak an already filled out a pv ready - * for importing into a vg. eg. pe_count - * is format specific. + * Tweak an already filled out a pv ready for importing into a + * vg. eg. pe_count is format specific. */ - int (*pv_setup)(struct io_space *is, struct physical_volume *pv, + int (*pv_setup)(struct format_instance *fi, struct physical_volume *pv, struct volume_group *vg); /* - * Write a PV structure to disk. Fails if - * the PV is in a VG ie pv->vg_name must - * be null. + * Write a PV structure to disk. Fails if the PV is in a VG ie + * pv->vg_name must be null. */ - int (*pv_write)(struct io_space *is, struct physical_volume *pv); + int (*pv_write)(struct format_instance *fi, + struct physical_volume *pv); /* - * Tweak an already filled out vg. eg, - * max_pv is format specific. + * Tweak an already filled out vg. eg, max_pv is format + * specific. */ - int (*vg_setup)(struct io_space *is, struct volume_group *vg); + int (*vg_setup)(struct format_instance *fi, struct volume_group *vg); /* - * If vg_name doesn't contain any slash, - * this function adds prefix. + * The name may be prefixed with the dev_dir from the + * job_context. */ - struct volume_group *(*vg_read)(struct io_space *is, + struct volume_group *(*vg_read)(struct format_instance *fi, const char *vg_name); /* - * Write out complete VG metadata. Ensure - * *internal* consistency before writing - * anything. eg. PEs can't refer to PVs - * not part of the VG. Order write sequence - * to aid recovery if process is aborted - * (eg flush entire set of changes to each - * disk in turn) It is the responsibility - * of the caller to ensure external - * consistency, eg by calling pv_write() - * if removing PVs from a VG or calling - * vg_write() a second time if splitting a - * VG into two. vg_write() must not read - * or write from any PVs not included in - * the volume_group structure it is - * handed. + * Write out complete VG metadata. You must ensure internal + * consistency before calling. eg. PEs can't refer to PVs not + * part of the VG. + * + * It is also the responsibility of the caller to ensure external + * consistency, eg by calling pv_write() if removing PVs from + * a VG or calling vg_write() a second time if splitting a VG + * into two. + * + * vg_write() must not read or write from any PVs not included + * in the volume_group structure it is handed. Note: format1 + * does read all pv's currently. */ - int (*vg_write)(struct io_space *is, struct volume_group *vg); + int (*vg_write)(struct format_instance *fi, struct volume_group *vg); /* * Destructor for this object. */ - void (*destroy)(struct io_space *is); - - /* - * Current volume group prefix. - */ - char *prefix; - struct pool *mem; - struct dev_filter *filter; - void *private; + void (*destroy)(struct format_instance *fi); }; /* * Utility functions */ -struct volume_group *vg_create(struct io_space *ios, const char *name, +struct physical_volume *pv_create(struct format_instance *fi, + const char *name); + +struct volume_group *vg_create(struct format_instance *fi, const char *name, uint32_t extent_size, int max_pv, int max_lv, int pv_count, char **pv_names); -struct physical_volume *pv_create(struct io_space *ios, const char *name); + +/* + * This needs the format instance to check the + * pv's are orphaned. + */ +int vg_extend(struct format_instance *fi, + struct volume_group *vg, int pv_count, char **pv_names); + /* * Create a new LV within a given volume group. * */ -struct logical_volume *lv_create(struct io_space *ios, - const char *name, +struct logical_volume *lv_create(const char *name, uint32_t status, uint32_t stripes, uint32_t stripe_size, @@ -221,30 +238,15 @@ struct logical_volume *lv_create(struct io_space *ios, struct volume_group *vg, struct list *acceptable_pvs); -int lv_reduce(struct io_space *ios, - struct logical_volume *lv, - uint32_t extents); +int lv_reduce(struct logical_volume *lv, uint32_t extents); -int lv_extend(struct io_space *ios, struct logical_volume *lv, +int lv_extend(struct logical_volume *lv, uint32_t extents, struct list *allocatable_pvs); -int vg_extend(struct io_space *ios, struct volume_group *vg, int pv_count, - char **pv_names); - - - /* FIXME: Move to other files */ -struct io_space *create_text_format(struct dev_filter *filter, - const char *text_file); - int id_eq(struct id *op1, struct id *op2); -/* Create consistent new empty structures, populated with defaults */ -struct volume_group *vg_create(); - -int vg_destroy(struct volume_group *vg); - /* Manipulate PV structures */ int pv_add(struct volume_group *vg, struct physical_volume *pv); int pv_remove(struct volume_group *vg, struct physical_volume *pv); @@ -269,5 +271,9 @@ struct volume_group *find_vg_with_lv(const char *lv_name); struct physical_volume *_find_pv(struct volume_group *vg, struct device *dev); struct logical_volume *find_lv(struct volume_group *vg, const char *lv_name); +/* + * Remove a prefix directory if present. + */ +const char *strip_dir(const char *vg_name, const char *dir); #endif -- 2.43.5