snapshot: merge count and name collection

Another case where we can do the same amount of work with fewer
lines of redundant code, which will make adding new filters easier.

* src/conf/domain_conf.c (virDomainSnapshotNameData): Adjust
struct.
(virDomainSnapshotObjListCount): Delete, now taken care of...
(virDomainSnapshotObjListCopyNames): ...here.
(virDomainSnapshotObjListGetNames): Adjust caller to handle
counting.
(virDomainSnapshotObjListNum): Simplify.
This commit is contained in:
Eric Blake 2012-06-14 07:33:37 -06:00
parent 7e111c6fe6
commit ec83c7163e

View File

@ -14256,11 +14256,11 @@ virDomainSnapshotObjListDeinit(virDomainSnapshotObjListPtr snapshots)
} }
struct virDomainSnapshotNameData { struct virDomainSnapshotNameData {
int oom;
int numnames;
int maxnames;
char **const names; char **const names;
int maxnames;
unsigned int flags; unsigned int flags;
int count;
bool error;
}; };
static void virDomainSnapshotObjListCopyNames(void *payload, static void virDomainSnapshotObjListCopyNames(void *payload,
@ -14270,7 +14270,7 @@ static void virDomainSnapshotObjListCopyNames(void *payload,
virDomainSnapshotObjPtr obj = payload; virDomainSnapshotObjPtr obj = payload;
struct virDomainSnapshotNameData *data = opaque; struct virDomainSnapshotNameData *data = opaque;
if (data->oom) if (data->error)
return; return;
/* LIST_ROOTS/LIST_DESCENDANTS was handled by the choice of /* LIST_ROOTS/LIST_DESCENDANTS was handled by the choice of
* iteration made in the caller, and LIST_METADATA is a no-op if * iteration made in the caller, and LIST_METADATA is a no-op if
@ -14278,12 +14278,13 @@ static void virDomainSnapshotObjListCopyNames(void *payload,
if ((data->flags & VIR_DOMAIN_SNAPSHOT_LIST_LEAVES) && obj->nchildren) if ((data->flags & VIR_DOMAIN_SNAPSHOT_LIST_LEAVES) && obj->nchildren)
return; return;
if (data->numnames < data->maxnames) { if (data->names && data->count < data->maxnames &&
if (!(data->names[data->numnames] = strdup(obj->def->name))) !(data->names[data->count] = strdup(obj->def->name))) {
data->oom = 1; data->error = true;
else virReportOOMError();
data->numnames++; return;
} }
data->count++;
} }
int int
@ -14292,7 +14293,8 @@ virDomainSnapshotObjListGetNames(virDomainSnapshotObjListPtr snapshots,
char **const names, int maxnames, char **const names, int maxnames,
unsigned int flags) unsigned int flags)
{ {
struct virDomainSnapshotNameData data = { 0, 0, maxnames, names, 0 }; struct virDomainSnapshotNameData data = { names, maxnames, flags, 0,
false };
int i; int i;
if (!from) { if (!from) {
@ -14303,52 +14305,32 @@ virDomainSnapshotObjListGetNames(virDomainSnapshotObjListPtr snapshots,
from = &snapshots->metaroot; from = &snapshots->metaroot;
} }
data.flags = flags & ~VIR_DOMAIN_SNAPSHOT_LIST_DESCENDANTS; data.flags &= ~VIR_DOMAIN_SNAPSHOT_LIST_DESCENDANTS;
if (flags & VIR_DOMAIN_SNAPSHOT_LIST_DESCENDANTS) { if (flags & VIR_DOMAIN_SNAPSHOT_LIST_DESCENDANTS) {
if (from->def) if (from->def)
virDomainSnapshotForEachDescendant(from, virDomainSnapshotForEachDescendant(from,
virDomainSnapshotObjListCopyNames, virDomainSnapshotObjListCopyNames,
&data); &data);
else else if (names || data.flags)
virHashForEach(snapshots->objs, virDomainSnapshotObjListCopyNames, virHashForEach(snapshots->objs, virDomainSnapshotObjListCopyNames,
&data); &data);
} else { else
data.count = virHashSize(snapshots->objs);
} else if (names || data.flags) {
virDomainSnapshotForEachChild(from, virDomainSnapshotForEachChild(from,
virDomainSnapshotObjListCopyNames, &data); virDomainSnapshotObjListCopyNames, &data);
} else {
data.count = from->nchildren;
} }
if (data.oom) { if (data.error) {
virReportOOMError(); for (i = 0; i < data.count; i++)
goto cleanup; VIR_FREE(names[i]);
return -1;
} }
return data.numnames; return data.count;
cleanup:
for (i = 0; i < data.numnames; i++)
VIR_FREE(data.names[i]);
return -1;
}
struct virDomainSnapshotNumData {
int count;
unsigned int flags;
};
static void virDomainSnapshotObjListCount(void *payload,
const void *name ATTRIBUTE_UNUSED,
void *opaque)
{
virDomainSnapshotObjPtr obj = payload;
struct virDomainSnapshotNumData *data = opaque;
/* LIST_ROOTS/LIST_DESCENDANTS was handled by the choice of
* iteration made in the caller, and LIST_METADATA is a no-op if
* we get this far. */
if ((data->flags & VIR_DOMAIN_SNAPSHOT_LIST_LEAVES) && obj->nchildren)
return;
data->count++;
} }
int int
@ -14356,33 +14338,7 @@ virDomainSnapshotObjListNum(virDomainSnapshotObjListPtr snapshots,
virDomainSnapshotObjPtr from, virDomainSnapshotObjPtr from,
unsigned int flags) unsigned int flags)
{ {
struct virDomainSnapshotNumData data = { 0, 0 }; return virDomainSnapshotObjListGetNames(snapshots, from, NULL, 0, flags);
if (!from) {
/* LIST_ROOTS and LIST_DESCENDANTS have the same bit value,
* but opposite semantics. Toggle here to get the correct
* traversal on the metaroot. */
flags ^= VIR_DOMAIN_SNAPSHOT_LIST_ROOTS;
from = &snapshots->metaroot;
}
data.flags = flags & ~VIR_DOMAIN_SNAPSHOT_LIST_DESCENDANTS;
if (flags & VIR_DOMAIN_SNAPSHOT_LIST_DESCENDANTS) {
if (data.flags || from->def)
virDomainSnapshotForEachDescendant(from,
virDomainSnapshotObjListCount,
&data);
else
data.count = virHashSize(snapshots->objs);
} else if (data.flags) {
virDomainSnapshotForEachChild(from,
virDomainSnapshotObjListCount, &data);
} else {
data.count = from->nchildren;
}
return data.count;
} }
virDomainSnapshotObjPtr virDomainSnapshotObjPtr