[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]

[Libvir] [PATCH] Allow virDomainDefine to overwrite existing inactive domains for xen 3.0.3 userspace installations



virDomainDefineXML should overwrite an existing inactive domain config if it finds one; it does this successfully for later (post 3.0.3) xen versions. However on xen 3.0.3 overwriting an existing config would fail with a name conflict. This patch allows the overwrite, removing the prior config from the config hashes.

If someone more familiar than I with libvirt error handling and style could look at this and tell me if I've done something horribly wrong, I'd appreciate it.

Signed-off-by: Hugh Brock <hbrock redhat com>


--
Red Hat Virtualization Group http://redhat.com/virtualization
Hugh Brock           | virt-manager http://virt-manager.org
hbrock redhat com    | virtualization library http://libvirt.org
Index: src/xm_internal.c
===================================================================
RCS file: /data/cvs/libvirt/src/xm_internal.c,v
retrieving revision 1.23
diff -u -r1.23 xm_internal.c
--- src/xm_internal.c	4 Apr 2007 14:19:49 -0000	1.23
+++ src/xm_internal.c	1 May 2007 17:23:05 -0000
@@ -2072,7 +2072,9 @@
  */
 virDomainPtr xenXMDomainDefineXML(virConnectPtr conn, const char *xml) {
     virDomainPtr ret;
+    virDomainPtr olddomain;
     char filename[PATH_MAX];
+    const char * oldfilename;
     unsigned char uuid[VIR_UUID_BUFLEN];
     virConfPtr conf = NULL;
     xenXMConfCachePtr entry = NULL;
@@ -2103,8 +2105,44 @@
     }
 
     if (virHashLookup(nameConfigMap, value->str)) {
-        xenXMError(conn, VIR_ERR_INTERNAL_ERROR, "domain with name already exists");
-        goto error;
+        /* domain exists, we will overwrite it */
+
+        if (!(oldfilename = (char *)virHashLookup(nameConfigMap, value->str))) {
+            xenXMError(conn, VIR_ERR_INTERNAL_ERROR, "can't retrieve config filename for domain to overwrite");
+            goto error;
+        }
+
+        if (!(entry = virHashLookup(configCache, oldfilename))) {
+            xenXMError(conn, VIR_ERR_INTERNAL_ERROR, "can't retrieve config entry for domain to overwrite");
+            goto error;
+        }
+
+        if (xenXMConfigGetUUID(entry->conf, "uuid", uuid) < 0) {
+            xenXMError(conn, VIR_ERR_INTERNAL_ERROR, "uuid config parameter is missing");
+            goto error;
+        }
+        
+        if (!(olddomain = virGetDomain(conn, value->str, uuid)))
+            goto error;
+
+        if (olddomain->id != -1) {
+            xenXMError(conn, VIR_ERR_INTERNAL_ERROR, "can't overwrite an active domain");
+            goto error;
+        }
+
+        /* Remove the name -> filename mapping */
+        if (virHashRemoveEntry(nameConfigMap, value->str, NULL) < 0) {
+            xenXMError(conn, VIR_ERR_INTERNAL_ERROR, "failed to remove old domain from config map");
+            goto error;
+        }
+
+        /* Remove the config record itself */
+        if (virHashRemoveEntry(configCache, oldfilename, xenXMConfigFree) < 0) {
+            xenXMError(conn, VIR_ERR_INTERNAL_ERROR, "failed to remove old domain from config map");
+            goto error;
+        }
+
+        entry = NULL;
     }
 
     if ((strlen(configDir) + 1 + strlen(value->str) + 1) > PATH_MAX) {

[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]