From 5ba372306a42eb56355f92af1ad2322f26049d9d Mon Sep 17 00:00:00 2001 From: Daniel Veillard Date: Fri, 8 Aug 2008 15:03:00 +0000 Subject: [PATCH] =?UTF-8?q?llow=20to=20add=20a=20disk=20as=20an=20USB=20de?= =?UTF-8?q?vice=20(QEmu/KVM)=20*=20src/domain=5Fconf.c=20src/domain=5Fconf?= =?UTF-8?q?.h=20src/qemu=5Fconf.c=20=20=20src/qemu=5Fdriver.c:=20patch=20f?= =?UTF-8?q?rom=20Guido=20G=C3=BCnther=20allowing=20to=20add=20=20=20disk?= =?UTF-8?q?=20as=20USB=20devices=20*=20docs/libvirt.rng:=20extend=20the=20?= =?UTF-8?q?schemas=20for=20the=20new=20value=20*=20tests/qemuxml2argvdata/?= =?UTF-8?q?qemuxml2argv-disk-usb.args=20=20=20tests/qemuxml2argvdata/qemux?= =?UTF-8?q?ml2argv-disk-usb.xml=20=20=20tests/qemuxml2argvtest.c=20tests/q?= =?UTF-8?q?emuxml2xmltest.c:=20add=20a=20specific=20=20=20test=20to=20the?= =?UTF-8?q?=20regression=20suite=20Daniel?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ChangeLog | 11 +++++ docs/libvirt.rng | 1 + src/domain_conf.c | 3 +- src/domain_conf.h | 1 + src/qemu_conf.c | 37 ++++++++++++++- src/qemu_driver.c | 46 +++++++++++++++++++ .../qemuxml2argv-disk-usb.args | 1 + .../qemuxml2argv-disk-usb.xml | 26 +++++++++++ tests/qemuxml2argvtest.c | 1 + tests/qemuxml2xmltest.c | 1 + 10 files changed, 126 insertions(+), 2 deletions(-) create mode 100644 tests/qemuxml2argvdata/qemuxml2argv-disk-usb.args create mode 100644 tests/qemuxml2argvdata/qemuxml2argv-disk-usb.xml diff --git a/ChangeLog b/ChangeLog index bed00cd7e2..740b98ccf8 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,14 @@ +Fri Aug 8 16:53:24 CEST 2008 Daniel Veillard + + * src/domain_conf.c src/domain_conf.h src/qemu_conf.c + src/qemu_driver.c: patch from Guido Günther allowing to add + disk as USB devices + * docs/libvirt.rng: extend the schemas for the new value + * tests/qemuxml2argvdata/qemuxml2argv-disk-usb.args + tests/qemuxml2argvdata/qemuxml2argv-disk-usb.xml + tests/qemuxml2argvtest.c tests/qemuxml2xmltest.c: add a specific + test to the regression suite + Fri Aug 8 16:15:55 CEST 2008 Daniel Veillard * src/domain_conf.c src/domain_conf.h src/qemu_conf.c diff --git a/docs/libvirt.rng b/docs/libvirt.rng index 60e181f41e..81ec33babc 100644 --- a/docs/libvirt.rng +++ b/docs/libvirt.rng @@ -412,6 +412,7 @@ virtio fdc xen + usb diff --git a/src/domain_conf.c b/src/domain_conf.c index 922cf76d4c..237579ff15 100644 --- a/src/domain_conf.c +++ b/src/domain_conf.c @@ -84,7 +84,8 @@ VIR_ENUM_IMPL(virDomainDiskBus, VIR_DOMAIN_DISK_BUS_LAST, "fdc", "scsi", "virtio", - "xen") + "xen", + "usb") VIR_ENUM_IMPL(virDomainFS, VIR_DOMAIN_FS_TYPE_LAST, "mount", diff --git a/src/domain_conf.h b/src/domain_conf.h index 8a9d1db0f7..9e7c524b75 100644 --- a/src/domain_conf.h +++ b/src/domain_conf.h @@ -72,6 +72,7 @@ enum virDomainDiskBus { VIR_DOMAIN_DISK_BUS_SCSI, VIR_DOMAIN_DISK_BUS_VIRTIO, VIR_DOMAIN_DISK_BUS_XEN, + VIR_DOMAIN_DISK_BUS_USB, VIR_DOMAIN_DISK_BUS_LAST }; diff --git a/src/qemu_conf.c b/src/qemu_conf.c index 46bb9f4c86..3ffabcce14 100644 --- a/src/qemu_conf.c +++ b/src/qemu_conf.c @@ -55,7 +55,8 @@ VIR_ENUM_IMPL(virDomainDiskQEMUBus, VIR_DOMAIN_DISK_BUS_LAST, "floppy", "scsi", "virtio", - "xen") + "xen", + "usb") #define qemudLog(level, msg...) fprintf(stderr, msg) @@ -772,6 +773,16 @@ int qemudBuildCommandLine(virConnectPtr conn, goto no_memory; \ } while (0) +#define ADD_USBDISK(thisarg) \ + do { \ + ADD_ARG_LIT("-usbdevice"); \ + ADD_ARG_SPACE; \ + if ((asprintf(&qargv[qargc++], "disk:%s", thisarg)) == -1) { \ + qargv[qargc-1] = NULL; \ + goto no_memory; \ + } \ + } while (0) + snprintf(memory, sizeof(memory), "%lu", vm->def->memory/1024); snprintf(vcpus, sizeof(vcpus), "%lu", vm->def->vcpus); @@ -883,6 +894,18 @@ int qemudBuildCommandLine(virConnectPtr conn, int idx = virDiskNameToIndex(disk->dst); const char *bus = virDomainDiskQEMUBusTypeToString(disk->bus); + if (disk->bus == VIR_DOMAIN_DISK_BUS_USB) { + if (disk->device == VIR_DOMAIN_DISK_DEVICE_DISK) { + ADD_USBDISK(disk->src); + } else { + qemudReportError(conn, NULL, NULL, VIR_ERR_INTERNAL_ERROR, + _("unsupported usb disk type for '%s'"), disk->src); + goto error; + } + disk = disk->next; + continue; + } + if (idx < 0) { qemudReportError(conn, NULL, NULL, VIR_ERR_INTERNAL_ERROR, _("unsupported disk type '%s'"), disk->dst); @@ -922,6 +945,18 @@ int qemudBuildCommandLine(virConnectPtr conn, char dev[NAME_MAX]; char file[PATH_MAX]; + if (disk->bus == VIR_DOMAIN_DISK_BUS_USB) { + if (disk->device == VIR_DOMAIN_DISK_DEVICE_DISK) { + ADD_USBDISK(disk->src); + } else { + qemudReportError(conn, NULL, NULL, VIR_ERR_INTERNAL_ERROR, + _("unsupported usb disk type for '%s'"), disk->src); + goto error; + } + disk = disk->next; + continue; + } + if (STREQ(disk->dst, "hdc") && disk->device == VIR_DOMAIN_DISK_DEVICE_CDROM) { if (disk->src) { diff --git a/src/qemu_driver.c b/src/qemu_driver.c index 3c6d7c0346..a432e79a2d 100644 --- a/src/qemu_driver.c +++ b/src/qemu_driver.c @@ -2984,6 +2984,48 @@ static int qemudDomainAttachCdromDevice(virDomainPtr dom, return 0; } +static int qemudDomainAttachUsbMassstorageDevice(virDomainPtr dom, virDomainDeviceDefPtr dev) +{ + struct qemud_driver *driver = (struct qemud_driver *)dom->conn->privateData; + virDomainObjPtr vm = virDomainFindByUUID(driver->domains, dom->uuid); + int ret; + char *cmd, *reply; + + if (!vm) { + qemudReportError(dom->conn, dom, NULL, VIR_ERR_INVALID_DOMAIN, + "%s", _("no domain with matching uuid")); + return -1; + } + + ret = asprintf(&cmd, "usb_add disk:%s", dev->data.disk->src); + if (ret == -1) { + qemudReportError(dom->conn, NULL, NULL, VIR_ERR_NO_MEMORY, NULL); + return ret; + } + + if (qemudMonitorCommand(driver, vm, cmd, &reply) < 0) { + qemudReportError(dom->conn, dom, NULL, VIR_ERR_OPERATION_FAILED, + "%s", _("cannot attach usb device")); + VIR_FREE(cmd); + return -1; + } + + DEBUG ("attach_usb reply: %s", reply); + /* If the command failed qemu prints: + * Could not add ... */ + if (strstr(reply, "Could not add ")) { + qemudReportError (dom->conn, dom, NULL, VIR_ERR_OPERATION_FAILED, + "%s", + _("adding usb device failed")); + VIR_FREE(reply); + VIR_FREE(cmd); + return -1; + } + VIR_FREE(reply); + VIR_FREE(cmd); + return 0; +} + static int qemudDomainAttachHostDevice(virDomainPtr dom, virDomainDeviceDefPtr dev) { struct qemud_driver *driver = (struct qemud_driver *)dom->conn->privateData; @@ -3061,6 +3103,10 @@ static int qemudDomainAttachDevice(virDomainPtr dom, if (dev->type == VIR_DOMAIN_DEVICE_DISK && dev->data.disk->device == VIR_DOMAIN_DISK_DEVICE_CDROM) { ret = qemudDomainAttachCdromDevice(dom, dev); + } else if (dev->type == VIR_DOMAIN_DEVICE_DISK && + dev->data.disk->device == VIR_DOMAIN_DEVICE_DISK && + dev->data.disk->bus == VIR_DOMAIN_DISK_BUS_USB) { + ret = qemudDomainAttachUsbMassstorageDevice(dom, dev); } else if (dev->type == VIR_DOMAIN_DEVICE_HOSTDEV && dev->data.hostdev->mode == VIR_DOMAIN_HOSTDEV_MODE_SUBSYS && dev->data.hostdev->source.subsys.type == VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB) { diff --git a/tests/qemuxml2argvdata/qemuxml2argv-disk-usb.args b/tests/qemuxml2argvdata/qemuxml2argv-disk-usb.args new file mode 100644 index 0000000000..60a8317562 --- /dev/null +++ b/tests/qemuxml2argvdata/qemuxml2argv-disk-usb.args @@ -0,0 +1 @@ +/usr/bin/qemu -S -M pc -m 214 -smp 1 -nographic -monitor pty -no-acpi -boot c -hda /dev/HostVG/QEMUGuest1 -usbdevice disk:/tmp/usbdisk.img -net none -serial none -parallel none -usb \ No newline at end of file diff --git a/tests/qemuxml2argvdata/qemuxml2argv-disk-usb.xml b/tests/qemuxml2argvdata/qemuxml2argv-disk-usb.xml new file mode 100644 index 0000000000..d59e1c0a27 --- /dev/null +++ b/tests/qemuxml2argvdata/qemuxml2argv-disk-usb.xml @@ -0,0 +1,26 @@ + + QEMUGuest1 + c7a5fdbd-edaf-9455-926a-d65c16db1809 + 219200 + 219200 + 1 + + hvm + + + + destroy + restart + destroy + + /usr/bin/qemu + + + + + + + + + + diff --git a/tests/qemuxml2argvtest.c b/tests/qemuxml2argvtest.c index 458201b9cd..757d80440d 100644 --- a/tests/qemuxml2argvtest.c +++ b/tests/qemuxml2argvtest.c @@ -156,6 +156,7 @@ mymain(int argc, char **argv) QEMUD_CMD_FLAG_DRIVE_BOOT); DO_TEST("disk-drive-boot-cdrom", QEMUD_CMD_FLAG_DRIVE | QEMUD_CMD_FLAG_DRIVE_BOOT); + DO_TEST("disk-usb", 0); DO_TEST("graphics-vnc", 0); DO_TEST("graphics-sdl", 0); DO_TEST("input-usbmouse", 0); diff --git a/tests/qemuxml2xmltest.c b/tests/qemuxml2xmltest.c index 536c9bd876..c810f78339 100644 --- a/tests/qemuxml2xmltest.c +++ b/tests/qemuxml2xmltest.c @@ -95,6 +95,7 @@ mymain(int argc, char **argv) DO_TEST("disk-floppy"); DO_TEST("disk-many"); DO_TEST("disk-xenvbd"); + DO_TEST("disk-usb"); DO_TEST("graphics-vnc"); DO_TEST("graphics-sdl"); DO_TEST("input-usbmouse");