]> xenbits.xensource.com Git - libvirt.git/commitdiff
Re-arrange QEMU device alias assignment code
authorDaniel P. Berrange <berrange@redhat.com>
Mon, 1 Feb 2010 15:58:38 +0000 (15:58 +0000)
committerDaniel P. Berrange <berrange@redhat.com>
Tue, 2 Feb 2010 16:31:47 +0000 (16:31 +0000)
This patch re-arranges the QEMU device alias assignment code to
make it easier to call into the same codeblock when performing
device hotplug. The new code has the ability to skip over already
assigned names to facilitate hotplug

* src/qemu/qemu_driver.c: Call qemuAssignDeviceNetAlias()
  instead of qemuAssignNetNames
* src/qemu/qemu_conf.h: Export qemuAssignDeviceNetAlias()
  instead of qemuAssignNetNames
* src/qemu/qemu_driver.c: Merge the legacy disk/network alias
  assignment code into the main methods

src/qemu/qemu_conf.c
src/qemu/qemu_conf.h
src/qemu/qemu_driver.c

index 862be1ec311ab497025471ad4bf2f0e09d41f090..f30dba72684f6925b6d88a5a67bf443835c78012 100644 (file)
@@ -1537,30 +1537,166 @@ int qemuDomainNetVLAN(virDomainNetDefPtr def)
     return qemuDomainDeviceAliasIndex(&def->info, "net");
 }
 
+
+/* Names used before -drive existed */
+static int qemuAssignDeviceDiskAliasLegacy(virDomainDiskDefPtr disk)
+{
+    char *devname;
+
+    if (disk->device == VIR_DOMAIN_DISK_DEVICE_CDROM &&
+        STREQ(disk->dst, "hdc"))
+        devname = strdup("cdrom");
+    else
+        devname = strdup(disk->dst);
+
+    if (!devname) {
+        virReportOOMError(NULL);
+        return -1;
+    }
+
+    disk->info.alias = devname;
+    return 0;
+}
+
+
+/* Names used before -drive supported the id= option */
+static int qemuAssignDeviceDiskAliasFixed(virDomainDiskDefPtr disk)
+{
+    int busid, devid;
+    int ret;
+    char *devname;
+
+    if (virDiskNameToBusDeviceIndex(disk, &busid, &devid) < 0) {
+        qemudReportError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR,
+                         _("cannot convert disk '%s' to bus/device index"),
+                         disk->dst);
+        return -1;
+    }
+
+    switch (disk->bus) {
+    case VIR_DOMAIN_DISK_BUS_IDE:
+        if (disk->device== VIR_DOMAIN_DISK_DEVICE_DISK)
+            ret = virAsprintf(&devname, "ide%d-hd%d", busid, devid);
+        else
+            ret = virAsprintf(&devname, "ide%d-cd%d", busid, devid);
+        break;
+    case VIR_DOMAIN_DISK_BUS_SCSI:
+        if (disk->device == VIR_DOMAIN_DISK_DEVICE_DISK)
+            ret = virAsprintf(&devname, "scsi%d-hd%d", busid, devid);
+        else
+            ret = virAsprintf(&devname, "scsi%d-cd%d", busid, devid);
+        break;
+    case VIR_DOMAIN_DISK_BUS_FDC:
+        ret = virAsprintf(&devname, "floppy%d", devid);
+        break;
+    case VIR_DOMAIN_DISK_BUS_VIRTIO:
+        ret = virAsprintf(&devname, "virtio%d", devid);
+        break;
+    case VIR_DOMAIN_DISK_BUS_XEN:
+        ret = virAsprintf(&devname, "xenblk%d", devid);
+        break;
+    default:
+        qemudReportError(NULL, NULL, NULL, VIR_ERR_NO_SUPPORT,
+                         _("Unsupported disk name mapping for bus '%s'"),
+                         virDomainDiskBusTypeToString(disk->bus));
+        return -1;
+    }
+
+    if (ret == -1) {
+        virReportOOMError(NULL);
+        return -1;
+    }
+
+    disk->info.alias = devname;
+
+    return 0;
+}
+
+
+/* Our custom -drive naming scheme used with id= */
+static int qemuAssignDeviceDiskAliasCustom(virDomainDiskDefPtr disk)
+{
+    const char *prefix = virDomainDiskBusTypeToString(disk->bus);
+    if (disk->info.type == VIR_DOMAIN_DEVICE_ADDRESS_TYPE_DRIVE) {
+        if (virAsprintf(&disk->info.alias, "%s%d-%d-%d", prefix,
+                        disk->info.addr.drive.controller,
+                        disk->info.addr.drive.bus,
+                        disk->info.addr.drive.unit) < 0)
+            goto no_memory;
+    } else {
+        int idx = virDiskNameToIndex(disk->dst);
+        if (virAsprintf(&disk->info.alias, "%s-disk%d", prefix, idx) < 0)
+            goto no_memory;
+    }
+
+    return 0;
+
+no_memory:
+    virReportOOMError(NULL);
+    return -1;
+}
+
+
 static int
-qemuAssignDeviceAliases(virDomainDefPtr def)
+qemuAssignDeviceDiskAlias(virDomainDiskDefPtr def, int qemuCmdFlags)
+{
+    if (qemuCmdFlags & QEMUD_CMD_FLAG_DRIVE) {
+        if (qemuCmdFlags & QEMUD_CMD_FLAG_DEVICE)
+            return qemuAssignDeviceDiskAliasCustom(def);
+        else
+            return qemuAssignDeviceDiskAliasFixed(def);
+    } else {
+        return qemuAssignDeviceDiskAliasLegacy(def);
+    }
+}
+
+
+int
+qemuAssignDeviceNetAlias(virDomainDefPtr def, virDomainNetDefPtr net, int idx)
+{
+    if (idx == -1) {
+        int i;
+        idx = 0;
+        for (i = 0 ; i < def->nnets ; i++) {
+            int thisidx;
+            if ((thisidx = qemuDomainDeviceAliasIndex(&def->nets[i]->info, "net")) < 0) {
+                qemudReportError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR, "%s",
+                                 _("Unable to determine device index for network device"));
+                return -1;
+            }
+            if (thisidx >= idx)
+                idx = thisidx + 1;
+        }
+    }
+
+    if (virAsprintf(&net->info.alias, "net%d", idx) < 0) {
+        virReportOOMError(NULL);
+        return -1;
+    }
+
+    return 0;
+}
+
+static int
+qemuAssignDeviceAliases(virDomainDefPtr def, int qemuCmdFlags)
 {
     int i;
 
     for (i = 0; i < def->ndisks ; i++) {
-        const char *prefix = virDomainDiskBusTypeToString(def->disks[i]->bus);
-        if (def->disks[i]->info.type == VIR_DOMAIN_DEVICE_ADDRESS_TYPE_DRIVE) {
-            if (virAsprintf(&def->disks[i]->info.alias, "%s%d-%d-%d", prefix,
-                            def->disks[i]->info.addr.drive.controller,
-                            def->disks[i]->info.addr.drive.bus,
-                            def->disks[i]->info.addr.drive.unit) < 0)
-                goto no_memory;
-        } else {
-            int idx = virDiskNameToIndex(def->disks[i]->dst);
-            if (virAsprintf(&def->disks[i]->info.alias, "%s-disk%d", prefix, idx) < 0)
-                goto no_memory;
-        }
+        if (qemuAssignDeviceDiskAlias(def->disks[i], qemuCmdFlags) < 0)
+            return -1;
     }
-    for (i = 0; i < def->nnets ; i++) {
-        if (virAsprintf(&def->nets[i]->info.alias, "net%d", i) < 0)
-            goto no_memory;
+    if ((qemuCmdFlags & QEMUD_CMD_FLAG_NET_NAME) ||
+        (qemuCmdFlags & QEMUD_CMD_FLAG_DEVICE)) {
+        for (i = 0; i < def->nnets ; i++) {
+            if (qemuAssignDeviceNetAlias(def, def->nets[i], i) < 0)
+                return -1;
+        }
     }
 
+    if (!(qemuCmdFlags & QEMUD_CMD_FLAG_DEVICE))
+        return 0;
+
     for (i = 0; i < def->nsounds ; i++) {
         if (virAsprintf(&def->sounds[i]->info.alias, "sound%d", i) < 0)
             goto no_memory;
@@ -1922,92 +2058,6 @@ error:
 }
 
 
-static char *qemuDiskLegacyName(const virDomainDiskDefPtr disk)
-{
-    char *devname;
-
-    if (disk->device == VIR_DOMAIN_DISK_DEVICE_CDROM &&
-        STREQ(disk->dst, "hdc"))
-        devname = strdup("cdrom");
-    else
-        devname = strdup(disk->dst);
-
-    if (!devname)
-        virReportOOMError(NULL);
-
-    return NULL;
-}
-
-/* Return the -drive QEMU disk name for use in monitor commands */
-static char *qemuDiskDriveName(const virDomainDiskDefPtr disk)
-{
-    int busid, devid;
-    int ret;
-    char *devname;
-
-    if (virDiskNameToBusDeviceIndex(disk, &busid, &devid) < 0) {
-        qemudReportError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR,
-                         _("cannot convert disk '%s' to bus/device index"),
-                         disk->dst);
-        return NULL;
-    }
-
-    switch (disk->bus) {
-    case VIR_DOMAIN_DISK_BUS_IDE:
-        if (disk->device== VIR_DOMAIN_DISK_DEVICE_DISK)
-            ret = virAsprintf(&devname, "ide%d-hd%d", busid, devid);
-        else
-            ret = virAsprintf(&devname, "ide%d-cd%d", busid, devid);
-        break;
-    case VIR_DOMAIN_DISK_BUS_SCSI:
-        if (disk->device == VIR_DOMAIN_DISK_DEVICE_DISK)
-            ret = virAsprintf(&devname, "scsi%d-hd%d", busid, devid);
-        else
-            ret = virAsprintf(&devname, "scsi%d-cd%d", busid, devid);
-        break;
-    case VIR_DOMAIN_DISK_BUS_FDC:
-        ret = virAsprintf(&devname, "floppy%d", devid);
-        break;
-    case VIR_DOMAIN_DISK_BUS_VIRTIO:
-        ret = virAsprintf(&devname, "virtio%d", devid);
-        break;
-    case VIR_DOMAIN_DISK_BUS_XEN:
-        ret = virAsprintf(&devname, "xenblk%d", devid);
-        break;
-    default:
-        qemudReportError(NULL, NULL, NULL, VIR_ERR_NO_SUPPORT,
-                         _("Unsupported disk name mapping for bus '%s'"),
-                         virDomainDiskBusTypeToString(disk->bus));
-        return NULL;
-    }
-
-    if (ret == -1) {
-        virReportOOMError(NULL);
-        return NULL;
-    }
-
-    return devname;
-}
-
-static int
-qemuAssignDiskAliases(virDomainDefPtr def, int qemuCmdFlags)
-{
-    int i;
-
-    for (i = 0 ; i < def->ndisks ; i++) {
-        if (qemuCmdFlags & QEMUD_CMD_FLAG_DRIVE)
-            def->disks[i]->info.alias =
-                qemuDiskDriveName(def->disks[i]);
-        else
-            def->disks[i]->info.alias =
-                qemuDiskLegacyName(def->disks[i]);
-
-        if (!def->disks[i]->info.alias)
-            return -1;
-    }
-    return 0;
-}
-
 static int
 qemuBuildDeviceAddressStr(virBufferPtr buf,
                           virDomainDeviceInfoPtr info)
@@ -2041,34 +2091,6 @@ qemuBuildDeviceAddressStr(virBufferPtr buf,
 }
 
 
-int
-qemuAssignNetNames(virDomainDefPtr def,
-                   virDomainNetDefPtr net)
-{
-    int i;
-    int lastidx = -1;
-
-    for (i = 0; i < def->nnets && def->nets[i] != net ; i++) {
-        int idx;
-
-        if ((idx = qemuDomainDeviceAliasIndex(&def->nets[i]->info, "net")) < 0) {
-            qemudReportError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR, "%s",
-                             _("Unable to determine device index for network device"));
-            return -1;
-        }
-
-        if (idx > lastidx)
-            lastidx = idx;
-    }
-
-    if (virAsprintf(&net->info.alias, "net%d", lastidx + 1) < 0) {
-        virReportOOMError(NULL);
-        return -1;
-    }
-
-    return 0;
-}
-
 #define QEMU_SERIAL_PARAM_ACCEPTED_CHARS \
   "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789-_"
 
@@ -2984,11 +3006,8 @@ int qemudBuildCommandLine(virConnectPtr conn,
 
     uname_normalize(&ut);
 
-    if (qemuCmdFlags & QEMUD_CMD_FLAG_DEVICE) {
-        qemuAssignDeviceAliases(def);
-    } else {
-        qemuAssignDiskAliases(def, qemuCmdFlags);
-    }
+    if (qemuAssignDeviceAliases(def, qemuCmdFlags) < 0)
+        return -1;
 
     virUUIDFormat(def->uuid, uuid);
 
@@ -3541,12 +3560,6 @@ int qemudBuildCommandLine(virConnectPtr conn,
                     goto no_memory;
             }
 
-            if ((qemuCmdFlags & QEMUD_CMD_FLAG_NET_NAME) &&
-                !(qemuCmdFlags & QEMUD_CMD_FLAG_DEVICE)) {
-                if (qemuAssignNetNames(def, net) < 0)
-                    goto no_memory;
-            }
-
             /* Possible combinations:
              *
              *  1. Old way:   -net nic,model=e1000,vlan=1 -net tap,vlan=1
index 98b9bbba99f6091498bf161fa96e9dae56b48eb3..d85be8f07b11b38bb8c854a403fa10325f2163f1 100644 (file)
@@ -247,9 +247,6 @@ int         qemudNetworkIfaceConnect    (virConnectPtr conn,
                                          virDomainNetDefPtr net,
                                          int qemuCmdFlags);
 
-int         qemuAssignNetNames          (virDomainDefPtr def,
-                                         virDomainNetDefPtr net);
-
 int         qemudProbeMachineTypes      (const char *binary,
                                          virCapsGuestMachinePtr **machines,
                                          int *nmachines);
@@ -286,6 +283,7 @@ void qemuDomainPCIAddressSetFree(qemuDomainPCIAddressSetPtr addrs);
 int  qemuAssignDevicePCISlots(virDomainDefPtr def, qemuDomainPCIAddressSetPtr addrs);
 
 int qemuDomainNetVLAN(virDomainNetDefPtr def);
+int qemuAssignDeviceNetAlias(virDomainDefPtr def, virDomainNetDefPtr net, int idx);
 
 
 #endif /* __QEMUD_CONF_H */
index 9d96ec62e236083c61dfe9b0651e6e94bbdf2c6b..d47ef10980557bc3601306e4bc09900fe3788e09 100644 (file)
@@ -5625,9 +5625,11 @@ static int qemudDomainAttachNetDevice(virConnectPtr conn,
     if (VIR_REALLOC_N(vm->def->nets, vm->def->nnets+1) < 0)
         goto no_memory;
 
-    if ((qemuCmdFlags & QEMUD_CMD_FLAG_NET_NAME) &&
-        qemuAssignNetNames(vm->def, net) < 0)
-        goto cleanup;
+    if ((qemuCmdFlags & QEMUD_CMD_FLAG_NET_NAME) ||
+        (qemuCmdFlags & QEMUD_CMD_FLAG_DEVICE)) {
+        if (qemuAssignDeviceNetAlias(vm->def, net, -1) < 0)
+            goto cleanup;
+    }
 
     if ((qemuCmdFlags & QEMUD_CMD_FLAG_DEVICE) &&
         qemuDomainPCIAddressEnsureAddr(priv->pciaddrs, &net->info) < 0)
@@ -5635,6 +5637,12 @@ static int qemudDomainAttachNetDevice(virConnectPtr conn,
 
     vlan = qemuDomainNetVLAN(net);
 
+    if (vlan < 0) {
+        qemudReportError(conn, NULL, NULL, VIR_ERR_NO_SUPPORT, "%s",
+                         _("Unable to attach network devices without vlan"));
+        goto cleanup;
+    }
+
     if (tapfd != -1) {
         if (virAsprintf(&tapfd_name, "fd-%s", net->info.alias) < 0)
             goto no_memory;