提交 2e53a991 编写于 作者: D Daniel P. Berrange

Switch storage objects to array instead of linked list

上级 dd48e929
Fri Oct 10 15:39:00 BST 2008 Daniel P. Berrange <berrange@redhat.com>
* src/storage_conf.c, src/storage_conf.h, src/storage_driver.c,
src/storage_backend_disk.c, src/storage_backend_fs.c,
src/storage_backend_iscsi.c, src/storage_backend_logical.c:
Switch storage objects to array instead of linked list
Fri Oct 10 15:39:00 BST 2008 Daniel P. Berrange <berrange@redhat.com>
* src/network_conf.c, src/network_conf.h, src/network_driver.c,
......
......@@ -182,9 +182,13 @@ virStorageBackendDiskMakeDataVol(virConnectPtr conn,
return -1;
}
vol->next = pool->volumes;
pool->volumes = vol;
pool->nvolumes++;
if (VIR_REALLOC_N(pool->volumes.objs,
pool->volumes.count+1) < 0) {
virStorageReportError(conn, VIR_ERR_NO_MEMORY, _("volume"));
virStorageVolDefFree(vol);
return -1;
}
pool->volumes.objs[pool->volumes.count++] = vol;
/* Prepended path will be same for all partitions, so we can
* strip the path to form a reasonable pool-unique name
......
......@@ -822,6 +822,7 @@ virStorageBackendFileSystemRefresh(virConnectPtr conn,
DIR *dir;
struct dirent *ent;
struct statvfs sb;
virStorageVolDefPtr vol = NULL;
if (!(dir = opendir(pool->def->target.path))) {
virStorageReportError(conn, VIR_ERR_INTERNAL_ERROR,
......@@ -831,61 +832,42 @@ virStorageBackendFileSystemRefresh(virConnectPtr conn,
}
while ((ent = readdir(dir)) != NULL) {
virStorageVolDefPtr vol;
int ret;
if (VIR_ALLOC(vol) < 0) {
virStorageReportError(conn, VIR_ERR_NO_MEMORY,
"%s", _("volume"));
goto cleanup;
}
if (VIR_ALLOC(vol) < 0)
goto no_memory;
vol->name = strdup(ent->d_name);
if (vol->name == NULL) {
VIR_FREE(vol);
virStorageReportError(conn, VIR_ERR_NO_MEMORY,
"%s", _("volume name"));
goto cleanup;
}
if ((vol->name = strdup(ent->d_name)) == NULL)
goto no_memory;
vol->target.format = VIR_STORAGE_VOL_RAW; /* Real value is filled in during probe */
if (VIR_ALLOC_N(vol->target.path, strlen(pool->def->target.path) +
1 + strlen(vol->name) + 1) < 0) {
VIR_FREE(vol->target.path);
VIR_FREE(vol);
virStorageReportError(conn, VIR_ERR_NO_MEMORY,
"%s", _("volume name"));
goto cleanup;
}
1 + strlen(vol->name) + 1) < 0)
goto no_memory;
strcpy(vol->target.path, pool->def->target.path);
strcat(vol->target.path, "/");
strcat(vol->target.path, vol->name);
if ((vol->key = strdup(vol->target.path)) == NULL) {
VIR_FREE(vol->name);
VIR_FREE(vol->target.path);
VIR_FREE(vol);
virStorageReportError(conn, VIR_ERR_NO_MEMORY,
"%s", _("volume key"));
goto cleanup;
}
if ((vol->key = strdup(vol->target.path)) == NULL)
goto no_memory;
if ((ret = virStorageBackendProbeFile(conn, vol) < 0)) {
VIR_FREE(vol->key);
VIR_FREE(vol->name);
VIR_FREE(vol->target.path);
VIR_FREE(vol);
if (ret == -1)
goto cleanup;
else
goto no_memory;
else {
/* Silently ignore non-regular files,
* eg '.' '..', 'lost+found' */
virStorageVolDefFree(vol);
vol = NULL;
continue;
}
}
vol->next = pool->volumes;
pool->volumes = vol;
pool->nvolumes++;
continue;
if (VIR_REALLOC_N(pool->volumes.objs,
pool->volumes.count+1) < 0)
goto no_memory;
pool->volumes.objs[pool->volumes.count++] = vol;
vol = NULL;
}
closedir(dir);
......@@ -904,8 +886,13 @@ virStorageBackendFileSystemRefresh(virConnectPtr conn,
return 0;
no_memory:
virStorageReportError(conn, VIR_ERR_NO_MEMORY, NULL);
/* fallthrough */
cleanup:
closedir(dir);
virStorageVolDefFree(vol);
virStoragePoolObjClearVols(pool);
return -1;
}
......
......@@ -236,9 +236,12 @@ virStorageBackendISCSINewLun(virConnectPtr conn, virStoragePoolObjPtr pool,
pool->def->capacity += vol->capacity;
pool->def->allocation += vol->allocation;
vol->next = pool->volumes;
pool->volumes = vol;
pool->nvolumes++;
if (VIR_REALLOC_N(pool->volumes.objs,
pool->volumes.count+1) < 0) {
virStorageReportError(conn, VIR_ERR_NO_MEMORY, NULL);
goto cleanup;
}
pool->volumes.objs[pool->volumes.count++] = vol;
close(fd);
......
......@@ -119,12 +119,17 @@ virStorageBackendLogicalMakeVol(virConnectPtr conn,
if ((vol->name = strdup(groups[0])) == NULL) {
virStorageReportError(conn, VIR_ERR_NO_MEMORY, "%s", _("volume"));
virStorageVolDefFree(vol);
return -1;
}
vol->next = pool->volumes;
pool->volumes = vol;
pool->nvolumes++;
if (VIR_REALLOC_N(pool->volumes.objs,
pool->volumes.count + 1)) {
virStorageReportError(conn, VIR_ERR_NO_MEMORY, NULL);
virStorageVolDefFree(vol);
return -1;
}
pool->volumes.objs[pool->volumes.count++] = vol;
}
if (vol->target.path == NULL) {
......
......@@ -52,6 +52,10 @@
void
virStorageVolDefFree(virStorageVolDefPtr def) {
int i;
if (!def)
return;
VIR_FREE(def->name);
VIR_FREE(def->key);
......@@ -69,6 +73,9 @@ void
virStoragePoolDefFree(virStoragePoolDefPtr def) {
int i;
if (!def)
return;
VIR_FREE(def->name);
VIR_FREE(def->source.host.name);
for (i = 0 ; i < def->source.ndevice ; i++) {
......@@ -92,9 +99,10 @@ virStoragePoolDefFree(virStoragePoolDefPtr def) {
void
virStoragePoolObjFree(virStoragePoolObjPtr obj) {
if (obj->def)
if (!obj)
return;
virStoragePoolDefFree(obj->def);
if (obj->newDef)
virStoragePoolDefFree(obj->newDef);
VIR_FREE(obj->configFile);
......@@ -102,28 +110,37 @@ virStoragePoolObjFree(virStoragePoolObjPtr obj) {
VIR_FREE(obj);
}
void virStoragePoolObjListFree(virStoragePoolObjListPtr pools)
{
unsigned int i;
for (i = 0 ; i < pools->count ; i++)
virStoragePoolObjFree(pools->objs[i]);
VIR_FREE(pools->objs);
pools->count = 0;
}
void
virStoragePoolObjRemove(virStorageDriverStatePtr driver,
virStoragePoolObjRemove(virStoragePoolObjListPtr pools,
virStoragePoolObjPtr pool)
{
virStoragePoolObjPtr prev = NULL, curr;
unsigned int i;
curr = driver->pools;
while (curr != pool) {
prev = curr;
curr = curr->next;
}
for (i = 0 ; i < pools->count ; i++) {
if (pools->objs[i] == pool) {
virStoragePoolObjFree(pools->objs[i]);
if (curr) {
if (prev)
prev->next = curr->next;
else
driver->pools = curr->next;
if (i < (pools->count - 1))
memmove(pools->objs + i, pools->objs + i + 1,
sizeof(*(pools->objs)) * (pools->count - (i + 1)));
driver->ninactivePools--;
if (VIR_REALLOC_N(pools->objs, pools->count - 1) < 0) {
; /* Failure to reduce memory allocation isn't fatal */
}
pools->count--;
virStoragePoolObjFree(pool);
break;
}
}
}
......@@ -906,29 +923,25 @@ virStorageVolDefFormat(virConnectPtr conn,
virStoragePoolObjPtr
virStoragePoolObjFindByUUID(virStorageDriverStatePtr driver,
virStoragePoolObjFindByUUID(virStoragePoolObjListPtr pools,
const unsigned char *uuid) {
virStoragePoolObjPtr pool = driver->pools;
unsigned int i;
while (pool) {
if (!memcmp(pool->def->uuid, uuid, VIR_UUID_BUFLEN))
return pool;
pool = pool->next;
}
for (i = 0 ; i < pools->count ; i++)
if (!memcmp(pools->objs[i]->def->uuid, uuid, VIR_UUID_BUFLEN))
return pools->objs[i];
return NULL;
}
virStoragePoolObjPtr
virStoragePoolObjFindByName(virStorageDriverStatePtr driver,
virStoragePoolObjFindByName(virStoragePoolObjListPtr pools,
const char *name) {
virStoragePoolObjPtr pool = driver->pools;
unsigned int i;
while (pool) {
if (STREQ(pool->def->name, name))
return pool;
pool = pool->next;
}
for (i = 0 ; i < pools->count ; i++)
if (STREQ(pools->objs[i]->def->name, name))
return pools->objs[i];
return NULL;
}
......@@ -936,26 +949,22 @@ virStoragePoolObjFindByName(virStorageDriverStatePtr driver,
void
virStoragePoolObjClearVols(virStoragePoolObjPtr pool)
{
virStorageVolDefPtr vol = pool->volumes;
while (vol) {
virStorageVolDefPtr next = vol->next;
virStorageVolDefFree(vol);
vol = next;
}
pool->volumes = NULL;
pool->nvolumes = 0;
unsigned int i;
for (i = 0 ; i < pool->volumes.count ; i++)
virStorageVolDefFree(pool->volumes.objs[i]);
VIR_FREE(pool->volumes.objs);
pool->volumes.count = 0;
}
virStorageVolDefPtr
virStorageVolDefFindByKey(virStoragePoolObjPtr pool,
const char *key) {
virStorageVolDefPtr vol = pool->volumes;
unsigned int i;
while (vol) {
if (STREQ(vol->key, key))
return vol;
vol = vol->next;
}
for (i = 0 ; i < pool->volumes.count ; i++)
if (STREQ(pool->volumes.objs[i]->key, key))
return pool->volumes.objs[i];
return NULL;
}
......@@ -963,13 +972,11 @@ virStorageVolDefFindByKey(virStoragePoolObjPtr pool,
virStorageVolDefPtr
virStorageVolDefFindByPath(virStoragePoolObjPtr pool,
const char *path) {
virStorageVolDefPtr vol = pool->volumes;
unsigned int i;
while (vol) {
if (STREQ(vol->target.path, path))
return vol;
vol = vol->next;
}
for (i = 0 ; i < pool->volumes.count ; i++)
if (STREQ(pool->volumes.objs[i]->target.path, path))
return pool->volumes.objs[i];
return NULL;
}
......@@ -977,24 +984,22 @@ virStorageVolDefFindByPath(virStoragePoolObjPtr pool,
virStorageVolDefPtr
virStorageVolDefFindByName(virStoragePoolObjPtr pool,
const char *name) {
virStorageVolDefPtr vol = pool->volumes;
unsigned int i;
while (vol) {
if (STREQ(vol->name, name))
return vol;
vol = vol->next;
}
for (i = 0 ; i < pool->volumes.count ; i++)
if (STREQ(pool->volumes.objs[i]->name, name))
return pool->volumes.objs[i];
return NULL;
}
virStoragePoolObjPtr
virStoragePoolObjAssignDef(virConnectPtr conn,
virStorageDriverStatePtr driver,
virStoragePoolObjListPtr pools,
virStoragePoolDefPtr def) {
virStoragePoolObjPtr pool;
if ((pool = virStoragePoolObjFindByName(driver, def->name))) {
if ((pool = virStoragePoolObjFindByName(pools, def->name))) {
if (!virStoragePoolObjIsActive(pool)) {
virStoragePoolDefFree(pool->def);
pool->def = def;
......@@ -1014,16 +1019,21 @@ virStoragePoolObjAssignDef(virConnectPtr conn,
pool->active = 0;
pool->def = def;
pool->next = driver->pools;
driver->pools = pool;
driver->ninactivePools++;
if (VIR_REALLOC_N(pools->objs, pools->count+1) < 0) {
pool->def = NULL;
virStoragePoolObjFree(pool);
virStorageReportError(conn, VIR_ERR_NO_MEMORY, NULL);
return NULL;
}
pools->objs[pools->count++] = pool;
return pool;
}
static virStoragePoolObjPtr
virStoragePoolObjLoad(virStorageDriverStatePtr driver,
virStoragePoolObjLoad(virConnectPtr conn,
virStoragePoolObjListPtr pools,
const char *file,
const char *path,
const char *xml,
......@@ -1045,7 +1055,7 @@ virStoragePoolObjLoad(virStorageDriverStatePtr driver,
return NULL;
}
if (!(pool = virStoragePoolObjAssignDef(NULL, driver, def))) {
if (!(pool = virStoragePoolObjAssignDef(conn, pools, def))) {
virStorageLog("Failed to load storage pool config '%s': out of memory", path);
virStoragePoolDefFree(def);
return NULL;
......@@ -1072,15 +1082,18 @@ virStoragePoolObjLoad(virStorageDriverStatePtr driver,
int
virStoragePoolObjScanConfigs(virStorageDriverStatePtr driver) {
virStoragePoolLoadAllConfigs(virConnectPtr conn,
virStoragePoolObjListPtr pools,
const char *configDir,
const char *autostartDir) {
DIR *dir;
struct dirent *entry;
if (!(dir = opendir(driver->configDir))) {
if (!(dir = opendir(configDir))) {
if (errno == ENOENT)
return 0;
virStorageLog("Failed to open dir '%s': %s",
driver->configDir, strerror(errno));
configDir, strerror(errno));
return -1;
}
......@@ -1095,24 +1108,24 @@ virStoragePoolObjScanConfigs(virStorageDriverStatePtr driver) {
if (!virFileHasSuffix(entry->d_name, ".xml"))
continue;
if (virFileBuildPath(driver->configDir, entry->d_name,
if (virFileBuildPath(configDir, entry->d_name,
NULL, path, PATH_MAX) < 0) {
virStorageLog("Config filename '%s/%s' is too long",
driver->configDir, entry->d_name);
configDir, entry->d_name);
continue;
}
if (virFileBuildPath(driver->autostartDir, entry->d_name,
if (virFileBuildPath(autostartDir, entry->d_name,
NULL, autostartLink, PATH_MAX) < 0) {
virStorageLog("Autostart link path '%s/%s' is too long",
driver->autostartDir, entry->d_name);
autostartDir, entry->d_name);
continue;
}
if (virFileReadAll(path, 8192, &xml) < 0)
continue;
virStoragePoolObjLoad(driver, entry->d_name, path, xml, autostartLink);
virStoragePoolObjLoad(conn, pools, entry->d_name, path, xml, autostartLink);
VIR_FREE(xml);
}
......
......@@ -87,10 +87,14 @@ struct _virStorageVolDef {
virStorageVolSource source;
virStorageVolTarget target;
virStorageVolDefPtr next;
};
typedef struct _virStorageVolDefList virStorageVolDefList;
typedef virStorageVolDefList *virStorageVolDefListPtr;
struct _virStorageVolDefList {
unsigned int count;
virStorageVolDefPtr *objs;
};
......@@ -222,10 +226,14 @@ struct _virStoragePoolObj {
virStoragePoolDefPtr def;
virStoragePoolDefPtr newDef;
int nvolumes;
virStorageVolDefPtr volumes;
virStorageVolDefList volumes;
};
virStoragePoolObjPtr next;
typedef struct _virStoragePoolObjList virStoragePoolObjList;
typedef virStoragePoolObjList *virStoragePoolObjListPtr;
struct _virStoragePoolObjList {
unsigned int count;
virStoragePoolObjPtr *objs;
};
......@@ -235,9 +243,8 @@ typedef struct _virStorageDriverState virStorageDriverState;
typedef virStorageDriverState *virStorageDriverStatePtr;
struct _virStorageDriverState {
int nactivePools;
int ninactivePools;
virStoragePoolObjPtr pools;
virStoragePoolObjList pools;
char *configDir;
char *autostartDir;
};
......@@ -251,11 +258,14 @@ static inline int virStoragePoolObjIsActive(virStoragePoolObjPtr pool) {
__virReportErrorHelper(conn, VIR_FROM_STORAGE, code, __FILE__, \
__FUNCTION__, __LINE__, fmt)
int virStoragePoolObjScanConfigs(virStorageDriverStatePtr driver);
int virStoragePoolLoadAllConfigs(virConnectPtr conn,
virStoragePoolObjListPtr pools,
const char *configDir,
const char *autostartDir);
virStoragePoolObjPtr virStoragePoolObjFindByUUID(virStorageDriverStatePtr driver,
virStoragePoolObjPtr virStoragePoolObjFindByUUID(virStoragePoolObjListPtr pools,
const unsigned char *uuid);
virStoragePoolObjPtr virStoragePoolObjFindByName(virStorageDriverStatePtr driver,
virStoragePoolObjPtr virStoragePoolObjFindByName(virStoragePoolObjListPtr pools,
const char *name);
virStorageVolDefPtr virStorageVolDefFindByKey(virStoragePoolObjPtr pool,
......@@ -282,7 +292,7 @@ char *virStorageVolDefFormat(virConnectPtr conn,
virStorageVolDefPtr def);
virStoragePoolObjPtr virStoragePoolObjAssignDef(virConnectPtr conn,
virStorageDriverStatePtr driver,
virStoragePoolObjListPtr pools,
virStoragePoolDefPtr def);
int virStoragePoolObjSaveDef(virConnectPtr conn,
......@@ -295,7 +305,8 @@ int virStoragePoolObjDeleteDef(virConnectPtr conn,
void virStorageVolDefFree(virStorageVolDefPtr def);
void virStoragePoolDefFree(virStoragePoolDefPtr def);
void virStoragePoolObjFree(virStoragePoolObjPtr pool);
void virStoragePoolObjRemove(virStorageDriverStatePtr driver,
void virStoragePoolObjListFree(virStoragePoolObjListPtr pools);
void virStoragePoolObjRemove(virStoragePoolObjListPtr pools,
virStoragePoolObjPtr pool);
#endif /* __VIR_STORAGE_DRIVER_H__ */
此差异已折叠。
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册