static int
-virStorageBackendLogicalFindPoolSourcesFunc(virConnectPtr conn ATTRIBUTE_UNUSED,
+virStorageBackendLogicalFindPoolSourcesFunc(virConnectPtr conn,
virStoragePoolObjPtr pool ATTRIBUTE_UNUSED,
char **const groups,
void *data)
{
- virStringList **rest = data;
- virStringList *newItem;
- const char *name = groups[0];
+ virStoragePoolSourceListPtr sourceList = data;
+ char *pvname = NULL;
+ char *vgname = NULL;
+ int i;
+ virStoragePoolSourceDevicePtr dev;
+ virStoragePoolSource *thisSource;
+
+ pvname = strdup(groups[0]);
+ vgname = strdup(groups[1]);
+
+ if (pvname == NULL || vgname == NULL) {
+ virStorageReportError(conn, VIR_ERR_NO_MEMORY, "%s",
+ _("allocating pvname or vgname"));
+ goto err_no_memory;
+ }
+
+ thisSource = NULL;
+ for (i = 0 ; i < sourceList->nsources; i++) {
+ if (STREQ(sourceList->sources[i].name, vgname)) {
+ thisSource = &sourceList->sources[i];
+ break;
+ }
+ }
+
+ if (thisSource == NULL) {
+ if (VIR_REALLOC_N(sourceList->sources, sourceList->nsources + 1) != 0) {
+ virStorageReportError(conn, VIR_ERR_NO_MEMORY, "%s",
+ _("allocating new source"));
+ goto err_no_memory;
+ }
- /* Append new XML desc to list */
+ thisSource = &sourceList->sources[sourceList->nsources];
+ sourceList->nsources++;
- if (VIR_ALLOC(newItem) != 0) {
- virStorageReportError(conn, VIR_ERR_NO_MEMORY, "%s", _("new xml desc"));
- return -1;
+ memset(thisSource, 0, sizeof(*thisSource));
+ thisSource->name = vgname;
}
+ else
+ VIR_FREE(vgname);
- if (asprintf(&newItem->val, "<source><name>%s</name></source>", name) <= 0) {
- virStorageReportError(conn, VIR_ERR_INTERNAL_ERROR, "%s", _("asprintf failed"));
- VIR_FREE(newItem);
- return -1;
+ if (VIR_REALLOC_N(thisSource->devices, thisSource->ndevice + 1) != 0) {
+ virStorageReportError(conn, VIR_ERR_NO_MEMORY, "%s",
+ _("allocating new device"));
+ goto err_no_memory;
}
- newItem->len = strlen(newItem->val);
- newItem->next = *rest;
- *rest = newItem;
+ dev = &thisSource->devices[thisSource->ndevice];
+ thisSource->ndevice++;
+
+ memset(dev, 0, sizeof(*dev));
+ dev->path = pvname;
return 0;
+
+ err_no_memory:
+ VIR_FREE(pvname);
+ VIR_FREE(vgname);
+
+ return -1;
}
static char *
unsigned int flags ATTRIBUTE_UNUSED)
{
/*
- * # vgs --noheadings -o vg_name
- * VolGroup00
- * VolGroup01
+ * # pvs --noheadings -o pv_name,vg_name
+ * /dev/sdb
+ * /dev/sdc VolGroup00
*/
const char *regexes[] = {
- "^\\s*(\\S+)\\s*$"
+ "^\\s*(\\S+)\\s+(\\S+)\\s*$"
};
int vars[] = {
- 1
+ 2
};
- virStringList *descs = NULL;
- const char *prog[] = { VGS, "--noheadings", "-o", "vg_name", NULL };
+ const char *const prog[] = { PVS, "--noheadings", "-o", "pv_name,vg_name", NULL };
int exitstatus;
char *retval = NULL;
+ virStoragePoolSourceList sourceList;
+ int i;
+ memset(&sourceList, 0, sizeof(sourceList));
if (virStorageBackendRunProgRegex(conn, NULL, prog, 1, regexes, vars,
virStorageBackendLogicalFindPoolSourcesFunc,
- &descs, &exitstatus) < 0)
+ &sourceList, &exitstatus) < 0)
return NULL;
- retval = virStringListJoin(descs, SOURCES_START_TAG, SOURCES_END_TAG, "\n");
+ retval = virStoragePoolSourceListFormat(conn, &sourceList);
if (retval == NULL) {
- virStorageReportError(conn, VIR_ERR_NO_MEMORY, "%s", _("retval"));
+ virStorageReportError(conn, VIR_ERR_INTERNAL_ERROR, "%s",
+ _("failed to get source from sourceList"));
goto cleanup;
}
cleanup:
- virStringListFree(descs);
+ for (i = 0; i < sourceList.nsources; i++)
+ virStoragePoolSourceFree(&sourceList.sources[i]);
+
+ VIR_FREE(sourceList.sources);
return retval;
}
}
void
-virStoragePoolDefFree(virStoragePoolDefPtr def) {
+virStoragePoolSourceFree(virStoragePoolSourcePtr source) {
int i;
- if (!def)
+ if (!source)
return;
- VIR_FREE(def->name);
- VIR_FREE(def->source.host.name);
- for (i = 0 ; i < def->source.ndevice ; i++) {
- VIR_FREE(def->source.devices[i].freeExtents);
- VIR_FREE(def->source.devices[i].path);
+ VIR_FREE(source->host.name);
+ for (i = 0 ; i < source->ndevice ; i++) {
+ VIR_FREE(source->devices[i].freeExtents);
+ VIR_FREE(source->devices[i].path);
}
- VIR_FREE(def->source.devices);
- VIR_FREE(def->source.dir);
- VIR_FREE(def->source.name);
+ VIR_FREE(source->devices);
+ VIR_FREE(source->dir);
+ VIR_FREE(source->name);
- if (def->source.authType == VIR_STORAGE_POOL_AUTH_CHAP) {
- VIR_FREE(def->source.auth.chap.login);
- VIR_FREE(def->source.auth.chap.passwd);
+ if (source->authType == VIR_STORAGE_POOL_AUTH_CHAP) {
+ VIR_FREE(source->auth.chap.login);
+ VIR_FREE(source->auth.chap.passwd);
}
+}
+
+void
+virStoragePoolDefFree(virStoragePoolDefPtr def) {
+ if (!def)
+ return;
+
+ VIR_FREE(def->name);
+
+ virStoragePoolSourceFree(&def->source);
VIR_FREE(def->target.path);
VIR_FREE(def->target.perms.label);
return 0;
}
+
+char *virStoragePoolSourceListFormat(virConnectPtr conn ATTRIBUTE_UNUSED,
+ virStoragePoolSourceListPtr def)
+{
+ int i, j;
+ virBuffer buf = VIR_BUFFER_INITIALIZER;
+
+ virBufferAddLit(&buf, "<source>");
+
+ for (i = 0; i < def->nsources; i++) {
+ virBufferVSprintf(&buf, "<name>%s</name>", def->sources[i].name);
+ for (j = 0; j < def->sources[i].ndevice; j++)
+ virBufferVSprintf(&buf, "<device path='%s'/>", def->sources[i].devices[j].path);
+ }
+
+ virBufferAddLit(&buf, "</source>");
+
+ return virBufferContentAndReset(&buf);
+}
char *autostartDir;
};
+typedef struct _virStoragePoolSourceList virStoragePoolSourceList;
+typedef virStoragePoolSourceList *virStoragePoolSourceListPtr;
+struct _virStoragePoolSourceList {
+ unsigned int nsources;
+ virStoragePoolSourcePtr sources;
+};
static inline int virStoragePoolObjIsActive(virStoragePoolObjPtr pool) {
return pool->active;
virStoragePoolObjPtr pool);
void virStorageVolDefFree(virStorageVolDefPtr def);
+void virStoragePoolSourceFree(virStoragePoolSourcePtr source);
void virStoragePoolDefFree(virStoragePoolDefPtr def);
void virStoragePoolObjFree(virStoragePoolObjPtr pool);
void virStoragePoolObjListFree(virStoragePoolObjListPtr pools);
void virStoragePoolObjRemove(virStoragePoolObjListPtr pools,
virStoragePoolObjPtr pool);
-#endif /* __VIR_STORAGE_DRIVER_H__ */
+char *virStoragePoolSourceListFormat(virConnectPtr conn,
+ virStoragePoolSourceListPtr def);
+#endif /* __VIR_STORAGE_CONF_H__ */