]> xenbits.xensource.com Git - libvirt.git/commitdiff
Storage pool duplicate UUID/name checking
authorDaniel P. Berrange <berrange@redhat.com>
Thu, 27 May 2010 11:41:30 +0000 (12:41 +0100)
committerDaniel P. Berrange <berrange@redhat.com>
Tue, 8 Jun 2010 14:11:08 +0000 (15:11 +0100)
The storage pool driver is not doing correct checking for
duplicate UUID/name values. This introduces a new method
virStoragePoolObjIsDuplicate, based on the previously
written virDomainObjIsDuplicate.

* src/conf/storage_conf.c, src/conf/storage_conf.c,
  src/libvirt_private.syms: Add virStoragePoolObjIsDuplicate,
* src/storage/storage_driver.c: Call virStoragePoolObjIsDuplicate
  for checking uniqueness of uuid/names

src/conf/storage_conf.c
src/conf/storage_conf.h
src/libvirt_private.syms
src/storage/storage_driver.c

index 422e76acc9753a9c81158eb7efc12a34cc3424d1..9ae1a89a8a9dcb1c5ca73c0fd8a392eec7433386 100644 (file)
@@ -1628,6 +1628,69 @@ char *virStoragePoolSourceListFormat(virStoragePoolSourceListPtr def)
 }
 
 
+/*
+ * virStoragePoolObjIsDuplicate:
+ * @doms : virStoragePoolObjListPtr to search
+ * @def  : virStoragePoolDefPtr definition of pool to lookup
+ * @check_active: If true, ensure that pool is not active
+ *
+ * Returns: -1 on error
+ *          0 if pool is new
+ *          1 if pool is a duplicate
+ */
+int virStoragePoolObjIsDuplicate(virStoragePoolObjListPtr pools,
+                                 virStoragePoolDefPtr def,
+                                 unsigned int check_active)
+{
+    int ret = -1;
+    int dupPool = 0;
+    virStoragePoolObjPtr pool = NULL;
+
+    /* See if a Pool with matching UUID already exists */
+    pool = virStoragePoolObjFindByUUID(pools, def->uuid);
+    if (pool) {
+        /* UUID matches, but if names don't match, refuse it */
+        if (STRNEQ(pool->def->name, def->name)) {
+            char uuidstr[VIR_UUID_STRING_BUFLEN];
+            virUUIDFormat(pool->def->uuid, uuidstr);
+            virStorageReportError(VIR_ERR_OPERATION_FAILED,
+                                  _("pool '%s' is already defined with uuid %s"),
+                                  pool->def->name, uuidstr);
+            goto cleanup;
+        }
+
+        if (check_active) {
+            /* UUID & name match, but if Pool is already active, refuse it */
+            if (virStoragePoolObjIsActive(pool)) {
+                virStorageReportError(VIR_ERR_OPERATION_INVALID,
+                                      _("pool is already active as '%s'"),
+                                      pool->def->name);
+                goto cleanup;
+            }
+        }
+
+        dupPool = 1;
+    } else {
+        /* UUID does not match, but if a name matches, refuse it */
+        pool = virStoragePoolObjFindByName(pools, def->name);
+        if (pool) {
+            char uuidstr[VIR_UUID_STRING_BUFLEN];
+            virUUIDFormat(pool->def->uuid, uuidstr);
+            virStorageReportError(VIR_ERR_OPERATION_FAILED,
+                                  _("pool '%s' already exists with uuid %s"),
+                                  def->name, uuidstr);
+            goto cleanup;
+        }
+    }
+
+    ret = dupPool;
+cleanup:
+    if (pool)
+        virStoragePoolObjUnlock(pool);
+    return ret;
+}
+
+
 void virStoragePoolObjLock(virStoragePoolObjPtr obj)
 {
     virMutexLock(&obj->lock);
index 5813489db44dc9d0c855ecf08c986706d6707139..bedee9efeeed99b3e4fe82014d51b309cfc53e32 100644 (file)
@@ -379,6 +379,10 @@ virStoragePoolSourcePtr
 virStoragePoolSourceListNewSource(virStoragePoolSourceListPtr list);
 char *virStoragePoolSourceListFormat(virStoragePoolSourceListPtr def);
 
+int virStoragePoolObjIsDuplicate(virStoragePoolObjListPtr pools,
+                                 virStoragePoolDefPtr def,
+                                 unsigned int check_active);
+
 void virStoragePoolObjLock(virStoragePoolObjPtr obj);
 void virStoragePoolObjUnlock(virStoragePoolObjPtr obj);
 
index 4f44064928a832577968232f473ed7a98784824f..4b1276aa01047532b529731c1ee5f1b42b9369d8 100644 (file)
@@ -610,6 +610,7 @@ virStoragePoolTypeFromString;
 virStoragePartedFsTypeTypeToString;
 virStoragePoolObjLock;
 virStoragePoolObjUnlock;
+virStoragePoolObjIsDuplicate;
 
 # storage_encryption_conf.h
 virStorageEncryptionFree;
index 0870f74a3daa7d42eaec4ed48b1c7d91e0ab6abe..e53317a67630752c0cf3eaf1b68d82093d89753a 100644 (file)
@@ -521,17 +521,8 @@ storagePoolCreate(virConnectPtr conn,
     if (!(def = virStoragePoolDefParseString(xml)))
         goto cleanup;
 
-    pool = virStoragePoolObjFindByUUID(&driver->pools, def->uuid);
-    if (!pool)
-        pool = virStoragePoolObjFindByName(&driver->pools, def->name);
-
-    if (pool) {
-        virStorageReportError(VIR_ERR_INTERNAL_ERROR,
-                              "%s", _("storage pool already exists"));
-        virStoragePoolObjUnlock(pool);
-        pool = NULL;
+    if (virStoragePoolObjIsDuplicate(&driver->pools, def, 1) < 0)
         goto cleanup;
-    }
 
     if ((backend = virStorageBackendForType(def->type)) == NULL)
         goto cleanup;
@@ -579,6 +570,9 @@ storagePoolDefine(virConnectPtr conn,
     if (!(def = virStoragePoolDefParseString(xml)))
         goto cleanup;
 
+    if (virStoragePoolObjIsDuplicate(&driver->pools, def, 0) < 0)
+        goto cleanup;
+
     if (virStorageBackendForType(def->type) == NULL)
         goto cleanup;