[libvirt] [PATCH 20/27] Add API for issuing 'pci_add storage' monitor command

Daniel P. Berrange berrange at redhat.com
Thu Sep 24 15:00:22 UTC 2009


* src/qemu/qemu_monitor.c, src/qemu/qemu_monitor.h: Add new
  API qemuMonitorAddPCIDisk()
* src/qemu/qemu_driver.c: Convert over to using the new
  qemuMonitorAddPCIDisk() method, and remove now obsolete
  qemudEscape() method
---
 src/qemu/qemu_driver.c       |  130 ++---------------------------------------
 src/qemu/qemu_monitor_text.c |   55 ++++++++++++++++++
 src/qemu/qemu_monitor_text.h |   13 ++++
 3 files changed, 75 insertions(+), 123 deletions(-)

diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 10fc09a..b447a87 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -3093,83 +3093,6 @@ cleanup:
 }
 
 
-static char *qemudEscape(const char *in, int shell)
-{
-    int len = 0;
-    int i, j;
-    char *out;
-
-    /* To pass through the QEMU monitor, we need to use escape
-       sequences: \r, \n, \", \\
-
-       To pass through both QEMU + the shell, we need to escape
-       the single character ' as the five characters '\\''
-    */
-
-    for (i = 0; in[i] != '\0'; i++) {
-        switch(in[i]) {
-        case '\r':
-        case '\n':
-        case '"':
-        case '\\':
-            len += 2;
-            break;
-        case '\'':
-            if (shell)
-                len += 5;
-            else
-                len += 1;
-            break;
-        default:
-            len += 1;
-            break;
-        }
-    }
-
-    if (VIR_ALLOC_N(out, len + 1) < 0)
-        return NULL;
-
-    for (i = j = 0; in[i] != '\0'; i++) {
-        switch(in[i]) {
-        case '\r':
-            out[j++] = '\\';
-            out[j++] = 'r';
-            break;
-        case '\n':
-            out[j++] = '\\';
-            out[j++] = 'n';
-            break;
-        case '"':
-        case '\\':
-            out[j++] = '\\';
-            out[j++] = in[i];
-            break;
-        case '\'':
-            if (shell) {
-                out[j++] = '\'';
-                out[j++] = '\\';
-                out[j++] = '\\';
-                out[j++] = '\'';
-                out[j++] = '\'';
-            } else {
-                out[j++] = in[i];
-            }
-            break;
-        default:
-            out[j++] = in[i];
-            break;
-        }
-    }
-    out[j] = '\0';
-
-    return out;
-}
-
-static char *qemudEscapeMonitorArg(const char *in)
-{
-    return qemudEscape(in, 0);
-}
-
 #define QEMUD_SAVE_MAGIC "LibvirtQemudSave"
 #define QEMUD_SAVE_VERSION 2
 
@@ -4626,12 +4549,8 @@ static int qemudDomainAttachPciDiskDevice(virConnectPtr conn,
                                           virDomainObjPtr vm,
                                           virDomainDeviceDefPtr dev)
 {
-    int ret, i;
-    char *cmd, *reply;
-    char *safe_path;
+    int i;
     const char* type = virDomainDiskBusTypeToString(dev->data.disk->bus);
-    int tryOldSyntax = 0;
-    unsigned domain, bus, slot;
 
     for (i = 0 ; i < vm->def->ndisks ; i++) {
         if (STREQ(vm->def->disks[i]->dst, dev->data.disk->dst)) {
@@ -4646,48 +4565,13 @@ static int qemudDomainAttachPciDiskDevice(virConnectPtr conn,
         return -1;
     }
 
-try_command:
-    safe_path = qemudEscapeMonitorArg(dev->data.disk->src);
-    if (!safe_path) {
-        virReportOOMError(conn);
-        return -1;
-    }
-
-    ret = virAsprintf(&cmd, "pci_add %s storage file=%s,if=%s",
-                      (tryOldSyntax ? "0": "pci_addr=auto"), safe_path, type);
-    VIR_FREE(safe_path);
-    if (ret == -1) {
-        virReportOOMError(conn);
-        return ret;
-    }
-
-    if (qemudMonitorCommand(vm, cmd, &reply) < 0) {
-        qemudReportError(conn, dom, NULL, VIR_ERR_OPERATION_FAILED,
-                         _("cannot attach %s disk"), type);
-        VIR_FREE(cmd);
+    if (qemuMonitorAddPCIDisk(vm,
+                              dev->data.disk->src,
+                              type,
+                              &dev->data.disk->pci_addr.domain,
+                              &dev->data.disk->pci_addr.bus,
+                              &dev->data.disk->pci_addr.slot) < 0)
         return -1;
-    }
-
-    VIR_FREE(cmd);
-
-    if (qemudParsePciAddReply(vm, reply, &domain, &bus, &slot) < 0) {
-        if (!tryOldSyntax && strstr(reply, "invalid char in expression")) {
-            VIR_FREE(reply);
-            tryOldSyntax = 1;
-            goto try_command;
-        }
-
-        qemudReportError (conn, dom, NULL, VIR_ERR_OPERATION_FAILED,
-                          _("adding %s disk failed: %s"), type, reply);
-        VIR_FREE(reply);
-        return -1;
-    }
-
-    VIR_FREE(reply);
-
-    dev->data.disk->pci_addr.domain = domain;
-    dev->data.disk->pci_addr.bus    = bus;
-    dev->data.disk->pci_addr.slot   = slot;
 
     virDomainDiskInsertPreAlloced(vm->def, dev->data.disk);
 
diff --git a/src/qemu/qemu_monitor_text.c b/src/qemu/qemu_monitor_text.c
index 290dcce..765a482 100644
--- a/src/qemu/qemu_monitor_text.c
+++ b/src/qemu/qemu_monitor_text.c
@@ -1437,6 +1437,61 @@ cleanup:
 }
 
 
+int qemuMonitorAddPCIDisk(const virDomainObjPtr vm,
+                          const char *path,
+                          const char *bus,
+                          unsigned *guestDomain,
+                          unsigned *guestBus,
+                          unsigned *guestSlot) {
+    char *cmd = NULL;
+    char *reply = NULL;
+    char *safe_path = NULL;
+    int tryOldSyntax = 0;
+    int ret = -1;
+
+    safe_path = qemudEscapeMonitorArg(path);
+    if (!safe_path) {
+        virReportOOMError(NULL);
+        return -1;
+    }
+
+try_command:
+    if (virAsprintf(&cmd, "pci_add %s storage file=%s,if=%s",
+                    (tryOldSyntax ? "0": "pci_addr=auto"), safe_path, bus) < 0) {
+        virReportOOMError(NULL);
+        goto cleanup;
+    }
+
+    if (qemudMonitorCommand(vm, cmd, &reply) < 0) {
+        qemudReportError(NULL, NULL, NULL, VIR_ERR_OPERATION_FAILED,
+                         _("cannot attach %s disk %s"), bus, path);
+        goto cleanup;
+    }
+
+    if (qemuMonitorParsePciAddReply(vm, reply,
+                                    guestDomain, guestBus, guestSlot) < 0) {
+        if (!tryOldSyntax && strstr(reply, "invalid char in expression")) {
+            VIR_FREE(reply);
+            VIR_FREE(cmd);
+            tryOldSyntax = 1;
+            goto try_command;
+        }
+
+        qemudReportError (NULL, NULL, NULL, VIR_ERR_OPERATION_FAILED,
+                          _("adding %s disk failed %s: %s"), bus, path, reply);
+        goto cleanup;
+    }
+
+    ret = 0;
+
+cleanup:
+    VIR_FREE(cmd);
+    VIR_FREE(reply);
+    return ret;
+}
+
+
+
 int qemuMonitorRemovePCIDevice(const virDomainObjPtr vm,
                                unsigned guestDomain,
                                unsigned guestBus,
diff --git a/src/qemu/qemu_monitor_text.h b/src/qemu/qemu_monitor_text.h
index 342e71e..f3c1e62 100644
--- a/src/qemu/qemu_monitor_text.h
+++ b/src/qemu/qemu_monitor_text.h
@@ -137,6 +137,9 @@ int qemuMonitorMigrateToCommand(const virDomainObjPtr vm,
                                 const char *target);
 
 
+/* XXX disk driver type eg,  qcow/etc.
+ * XXX cache mode
+ */
 int qemuMonitorAddUSBDisk(const virDomainObjPtr vm,
                           const char *path);
 
@@ -157,6 +160,16 @@ int qemuMonitorAddPCIHostDevice(const virDomainObjPtr vm,
                                 unsigned *guestBus,
                                 unsigned *guestSlot);
 
+/* XXX disk driver type eg,  qcow/etc.
+ * XXX cache mode
+ */
+int qemuMonitorAddPCIDisk(const virDomainObjPtr vm,
+                          const char *path,
+                          const char *bus,
+                          unsigned *guestDomain,
+                          unsigned *guestBus,
+                          unsigned *guestSlot);
+
 int qemuMonitorRemovePCIDevice(const virDomainObjPtr vm,
                                unsigned guestDomain,
                                unsigned guestBus,
-- 
1.6.2.5




More information about the libvir-list mailing list