Add new function to manage adding the disk -drive options to the
command line removing that task from the mainline qemuBuildCommandLine.
Also since using const virDomainDef in new function, that means other
functions called needed to change their usage.
Signed-off-by: John Ferlan <jferlan(a)redhat.com>
---
src/conf/domain_conf.c | 4 +-
src/conf/domain_conf.h | 4 +-
src/qemu/qemu_command.c | 317 +++++++++++++++++++++++++-----------------------
src/qemu/qemu_command.h | 2 +-
4 files changed, 173 insertions(+), 154 deletions(-)
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 11ac707..4b2633a 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -5746,7 +5746,7 @@ virDomainHostdevDefParseXMLCaps(xmlNodePtr node ATTRIBUTE_UNUSED,
}
int
-virDomainDeviceFindControllerModel(virDomainDefPtr def,
+virDomainDeviceFindControllerModel(const virDomainDef *def,
virDomainDeviceInfoPtr info,
int controllerType)
{
@@ -18327,7 +18327,7 @@ virDomainDefAddImplicitControllers(virDomainDefPtr def)
}
virDomainIOThreadIDDefPtr
-virDomainIOThreadIDFind(virDomainDefPtr def,
+virDomainIOThreadIDFind(const virDomainDef *def,
unsigned int iothread_id)
{
size_t i;
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
index 8af3c64..468b759 100644
--- a/src/conf/domain_conf.h
+++ b/src/conf/domain_conf.h
@@ -2516,7 +2516,7 @@ int virDomainDiskSetDriver(virDomainDiskDefPtr def, const char
*name)
ATTRIBUTE_RETURN_CHECK;
int virDomainDiskGetFormat(virDomainDiskDefPtr def);
void virDomainDiskSetFormat(virDomainDiskDefPtr def, int format);
-int virDomainDeviceFindControllerModel(virDomainDefPtr def,
+int virDomainDeviceFindControllerModel(const virDomainDef *def,
virDomainDeviceInfoPtr info,
int controllerType);
virDomainDiskDefPtr virDomainDiskFindByBusAndDst(virDomainDefPtr def,
@@ -2699,7 +2699,7 @@ bool virDomainDefCheckABIStability(virDomainDefPtr src,
int virDomainDefAddImplicitControllers(virDomainDefPtr def);
-virDomainIOThreadIDDefPtr virDomainIOThreadIDFind(virDomainDefPtr def,
+virDomainIOThreadIDDefPtr virDomainIOThreadIDFind(const virDomainDef *def,
unsigned int iothread_id);
virDomainIOThreadIDDefPtr virDomainIOThreadIDAdd(virDomainDefPtr def,
unsigned int iothread_id);
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index ef94af8..372f84f 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -1443,7 +1443,7 @@ qemuBuildDriveStr(virConnectPtr conn,
static bool
-qemuCheckIOThreads(virDomainDefPtr def,
+qemuCheckIOThreads(const virDomainDef *def,
virDomainDiskDefPtr disk)
{
/* Right "type" of disk" */
@@ -1469,7 +1469,7 @@ qemuCheckIOThreads(virDomainDefPtr def,
char *
-qemuBuildDriveDevStr(virDomainDefPtr def,
+qemuBuildDriveDevStr(const virDomainDef *def,
virDomainDiskDefPtr disk,
int bootindex,
virQEMUCapsPtr qemuCaps)
@@ -1766,6 +1766,168 @@ qemuBuildDriveDevStr(virDomainDefPtr def,
}
+static int
+qemuBuildDiskDriveCommandLine(virCommandPtr cmd,
+ virConnectPtr conn,
+ const virDomainDef *def,
+ virQEMUCapsPtr qemuCaps,
+ bool emitBootindex)
+{
+ size_t i;
+ int bootCD = 0, bootFloppy = 0, bootDisk = 0;
+ virBuffer fdc_opts = VIR_BUFFER_INITIALIZER;
+ char *fdc_opts_str = NULL;
+
+ if ((virQEMUCapsGet(qemuCaps, QEMU_CAPS_DRIVE_BOOT) || emitBootindex)) {
+ /* bootDevs will get translated into either bootindex=N or boot=on
+ * depending on what qemu supports */
+ for (i = 0; i < def->os.nBootDevs; i++) {
+ switch (def->os.bootDevs[i]) {
+ case VIR_DOMAIN_BOOT_CDROM:
+ bootCD = i + 1;
+ break;
+ case VIR_DOMAIN_BOOT_FLOPPY:
+ bootFloppy = i + 1;
+ break;
+ case VIR_DOMAIN_BOOT_DISK:
+ bootDisk = i + 1;
+ break;
+ }
+ }
+ }
+
+ for (i = 0; i < def->ndisks; i++) {
+ char *optstr;
+ int bootindex = 0;
+ virDomainDiskDefPtr disk = def->disks[i];
+ bool withDeviceArg = false;
+ bool deviceFlagMasked = false;
+
+ /* Unless we have -device, then USB disks need special
+ handling */
+ if ((disk->bus == VIR_DOMAIN_DISK_BUS_USB) &&
+ !virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE)) {
+ if (disk->device == VIR_DOMAIN_DISK_DEVICE_DISK) {
+ virCommandAddArg(cmd, "-usbdevice");
+ virCommandAddArgFormat(cmd, "disk:%s", disk->src->path);
+ } else {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("unsupported usb disk type for
'%s'"),
+ disk->src->path);
+ return -1;
+ }
+ continue;
+ }
+
+ /* PowerPC pseries based VMs do not support floppy device */
+ if ((disk->device == VIR_DOMAIN_DISK_DEVICE_FLOPPY) &&
+ ARCH_IS_PPC64(def->os.arch) &&
+ STRPREFIX(def->os.machine, "pseries")) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("PowerPC pseries machines do not support floppy
device"));
+ return -1;
+ }
+
+ switch (disk->device) {
+ case VIR_DOMAIN_DISK_DEVICE_CDROM:
+ bootindex = bootCD;
+ bootCD = 0;
+ break;
+ case VIR_DOMAIN_DISK_DEVICE_FLOPPY:
+ bootindex = bootFloppy;
+ bootFloppy = 0;
+ break;
+ case VIR_DOMAIN_DISK_DEVICE_DISK:
+ case VIR_DOMAIN_DISK_DEVICE_LUN:
+ bootindex = bootDisk;
+ bootDisk = 0;
+ break;
+ }
+
+ virCommandAddArg(cmd, "-drive");
+
+ /* Unfortunately it is not possible to use
+ -device for floppies, xen PV, or SD
+ devices. Fortunately, those don't need
+ static PCI addresses, so we don't really
+ care that we can't use -device */
+ if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE)) {
+ if (disk->bus != VIR_DOMAIN_DISK_BUS_XEN &&
+ disk->bus != VIR_DOMAIN_DISK_BUS_SD) {
+ withDeviceArg = true;
+ } else {
+ virQEMUCapsClear(qemuCaps, QEMU_CAPS_DEVICE);
+ deviceFlagMasked = true;
+ }
+ }
+ optstr = qemuBuildDriveStr(conn, disk,
+ emitBootindex ? false : !!bootindex,
+ qemuCaps);
+ if (deviceFlagMasked)
+ virQEMUCapsSet(qemuCaps, QEMU_CAPS_DEVICE);
+ if (!optstr)
+ return -1;
+ virCommandAddArg(cmd, optstr);
+ VIR_FREE(optstr);
+
+ if (!emitBootindex)
+ bootindex = 0;
+ else if (disk->info.bootIndex)
+ bootindex = disk->info.bootIndex;
+
+ if (withDeviceArg) {
+ if (disk->bus == VIR_DOMAIN_DISK_BUS_FDC) {
+ if (virAsprintf(&optstr, "drive%c=drive-%s",
+ disk->info.addr.drive.unit ? 'B' :
'A',
+ disk->info.alias) < 0)
+ return -1;
+
+ if (!qemuDomainMachineNeedsFDC(def)) {
+ virCommandAddArg(cmd, "-global");
+ virCommandAddArgFormat(cmd, "isa-fdc.%s", optstr);
+ } else {
+ virBufferAsprintf(&fdc_opts, "%s,", optstr);
+ }
+ VIR_FREE(optstr);
+
+ if (bootindex) {
+ if (virAsprintf(&optstr, "bootindex%c=%d",
+ disk->info.addr.drive.unit
+ ? 'B' : 'A',
+ bootindex) < 0)
+ return -1;
+
+ if (!qemuDomainMachineNeedsFDC(def)) {
+ virCommandAddArg(cmd, "-global");
+ virCommandAddArgFormat(cmd, "isa-fdc.%s", optstr);
+ } else {
+ virBufferAsprintf(&fdc_opts, "%s,", optstr);
+ }
+ VIR_FREE(optstr);
+ }
+ } else {
+ virCommandAddArg(cmd, "-device");
+
+ if (!(optstr = qemuBuildDriveDevStr(def, disk, bootindex,
+ qemuCaps)))
+ return -1;
+ virCommandAddArg(cmd, optstr);
+ VIR_FREE(optstr);
+ }
+ }
+ }
+ /* Newer Q35 machine types require an explicit FDC controller */
+ virBufferTrim(&fdc_opts, ",", -1);
+ if ((fdc_opts_str = virBufferContentAndReset(&fdc_opts))) {
+ virCommandAddArg(cmd, "-device");
+ virCommandAddArgFormat(cmd, "isa-fdc,%s", fdc_opts_str);
+ VIR_FREE(fdc_opts_str);
+ }
+
+ return 0;
+}
+
+
char *qemuBuildFSStr(virDomainFSDefPtr fs,
virQEMUCapsPtr qemuCaps ATTRIBUTE_UNUSED)
{
@@ -7623,9 +7785,7 @@ qemuBuildCommandLine(virConnectPtr conn,
bool emitBootindex = false;
int actualSerials = 0;
virQEMUDriverConfigPtr cfg = virQEMUDriverGetConfig(driver);
- virBuffer fdc_opts = VIR_BUFFER_INITIALIZER;
- char *fdc_opts_str = NULL;
- int bootCD = 0, bootFloppy = 0, bootDisk = 0, bootHostdevNet = 0;
+ int bootHostdevNet = 0;
VIR_DEBUG("conn=%p driver=%p def=%p mon=%p json=%d "
@@ -7743,150 +7903,9 @@ qemuBuildCommandLine(virConnectPtr conn,
if (qemuBuildHubCommandLine(cmd, def, qemuCaps) < 0)
goto error;
- if ((virQEMUCapsGet(qemuCaps, QEMU_CAPS_DRIVE_BOOT) || emitBootindex)) {
- /* bootDevs will get translated into either bootindex=N or boot=on
- * depending on what qemu supports */
- for (i = 0; i < def->os.nBootDevs; i++) {
- switch (def->os.bootDevs[i]) {
- case VIR_DOMAIN_BOOT_CDROM:
- bootCD = i + 1;
- break;
- case VIR_DOMAIN_BOOT_FLOPPY:
- bootFloppy = i + 1;
- break;
- case VIR_DOMAIN_BOOT_DISK:
- bootDisk = i + 1;
- break;
- }
- }
- }
-
- for (i = 0; i < def->ndisks; i++) {
- char *optstr;
- int bootindex = 0;
- virDomainDiskDefPtr disk = def->disks[i];
- bool withDeviceArg = false;
- bool deviceFlagMasked = false;
-
- /* Unless we have -device, then USB disks need special
- handling */
- if ((disk->bus == VIR_DOMAIN_DISK_BUS_USB) &&
- !virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE)) {
- if (disk->device == VIR_DOMAIN_DISK_DEVICE_DISK) {
- virCommandAddArg(cmd, "-usbdevice");
- virCommandAddArgFormat(cmd, "disk:%s", disk->src->path);
- } else {
- virReportError(VIR_ERR_INTERNAL_ERROR,
- _("unsupported usb disk type for
'%s'"),
- disk->src->path);
- goto error;
- }
- continue;
- }
-
- /* PowerPC pseries based VMs do not support floppy device */
- if ((disk->device == VIR_DOMAIN_DISK_DEVICE_FLOPPY) &&
- ARCH_IS_PPC64(def->os.arch) && STRPREFIX(def->os.machine,
"pseries")) {
- virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
- _("PowerPC pseries machines do not support floppy
device"));
- goto error;
- }
-
- switch (disk->device) {
- case VIR_DOMAIN_DISK_DEVICE_CDROM:
- bootindex = bootCD;
- bootCD = 0;
- break;
- case VIR_DOMAIN_DISK_DEVICE_FLOPPY:
- bootindex = bootFloppy;
- bootFloppy = 0;
- break;
- case VIR_DOMAIN_DISK_DEVICE_DISK:
- case VIR_DOMAIN_DISK_DEVICE_LUN:
- bootindex = bootDisk;
- bootDisk = 0;
- break;
- }
-
- virCommandAddArg(cmd, "-drive");
-
- /* Unfortunately it is not possible to use
- -device for floppies, xen PV, or SD
- devices. Fortunately, those don't need
- static PCI addresses, so we don't really
- care that we can't use -device */
- if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE)) {
- if (disk->bus != VIR_DOMAIN_DISK_BUS_XEN &&
- disk->bus != VIR_DOMAIN_DISK_BUS_SD) {
- withDeviceArg = true;
- } else {
- virQEMUCapsClear(qemuCaps, QEMU_CAPS_DEVICE);
- deviceFlagMasked = true;
- }
- }
- optstr = qemuBuildDriveStr(conn, disk,
- emitBootindex ? false : !!bootindex,
- qemuCaps);
- if (deviceFlagMasked)
- virQEMUCapsSet(qemuCaps, QEMU_CAPS_DEVICE);
- if (!optstr)
- goto error;
- virCommandAddArg(cmd, optstr);
- VIR_FREE(optstr);
-
- if (!emitBootindex)
- bootindex = 0;
- else if (disk->info.bootIndex)
- bootindex = disk->info.bootIndex;
-
- if (withDeviceArg) {
- if (disk->bus == VIR_DOMAIN_DISK_BUS_FDC) {
- if (virAsprintf(&optstr, "drive%c=drive-%s",
- disk->info.addr.drive.unit ? 'B' :
'A',
- disk->info.alias) < 0)
- goto error;
-
- if (!qemuDomainMachineNeedsFDC(def)) {
- virCommandAddArg(cmd, "-global");
- virCommandAddArgFormat(cmd, "isa-fdc.%s", optstr);
- } else {
- virBufferAsprintf(&fdc_opts, "%s,", optstr);
- }
- VIR_FREE(optstr);
-
- if (bootindex) {
- if (virAsprintf(&optstr, "bootindex%c=%d",
- disk->info.addr.drive.unit
- ? 'B' : 'A',
- bootindex) < 0)
- goto error;
-
- if (!qemuDomainMachineNeedsFDC(def)) {
- virCommandAddArg(cmd, "-global");
- virCommandAddArgFormat(cmd, "isa-fdc.%s", optstr);
- } else {
- virBufferAsprintf(&fdc_opts, "%s,", optstr);
- }
- VIR_FREE(optstr);
- }
- } else {
- virCommandAddArg(cmd, "-device");
-
- if (!(optstr = qemuBuildDriveDevStr(def, disk, bootindex,
- qemuCaps)))
- goto error;
- virCommandAddArg(cmd, optstr);
- VIR_FREE(optstr);
- }
- }
- }
- /* Newer Q35 machine types require an explicit FDC controller */
- virBufferTrim(&fdc_opts, ",", -1);
- if ((fdc_opts_str = virBufferContentAndReset(&fdc_opts))) {
- virCommandAddArg(cmd, "-device");
- virCommandAddArgFormat(cmd, "isa-fdc,%s", fdc_opts_str);
- VIR_FREE(fdc_opts_str);
- }
+ if (qemuBuildDiskDriveCommandLine(cmd, conn, def, qemuCaps,
+ emitBootindex) < 0)
+ goto error;
if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_FSDEV)) {
for (i = 0; i < def->nfss; i++) {
diff --git a/src/qemu/qemu_command.h b/src/qemu/qemu_command.h
index ed4f5bd..b10fc29 100644
--- a/src/qemu/qemu_command.h
+++ b/src/qemu/qemu_command.h
@@ -119,7 +119,7 @@ char *qemuBuildFSStr(virDomainFSDefPtr fs,
virQEMUCapsPtr qemuCaps);
/* Current, best practice */
-char *qemuBuildDriveDevStr(virDomainDefPtr def,
+char *qemuBuildDriveDevStr(const virDomainDef *def,
virDomainDiskDefPtr disk,
int bootindex,
virQEMUCapsPtr qemuCaps);
--
2.5.0