mirror of https://gitee.com/openkylin/libvirt.git
Add a new controller type 'usb' with optionnal 'model'
The model by default is piix3-uchi. Example: <controller type='usb' index='0' model='ich9-ehci'/>
This commit is contained in:
parent
2e4b5243b2
commit
d6d54cd19e
|
@ -1219,17 +1219,22 @@
|
|||
|
||||
<p>
|
||||
Each controller has a mandatory attribute <code>type</code>,
|
||||
which must be one of "ide", "fdc", "scsi", "sata", "ccid", or
|
||||
"virtio-serial", and a mandatory attribute <code>index</code>
|
||||
which is the decimal integer describing in which order the bus
|
||||
controller is encountered (for use in <code>controller</code>
|
||||
attributes of <code><address></code> elements). The
|
||||
"virtio-serial" controller has two additional optional
|
||||
which must be one of "ide", "fdc", "scsi", "sata", "usb",
|
||||
"ccid", or "virtio-serial", and a mandatory
|
||||
attribute <code>index</code> which is the decimal integer
|
||||
describing in which order the bus controller is encountered (for
|
||||
use in <code>controller</code> attributes
|
||||
of <code><address></code> elements). The "virtio-serial"
|
||||
controller has two additional optional
|
||||
attributes <code>ports</code> and <code>vectors</code>, which
|
||||
control how many devices can be connected through the
|
||||
controller. A "scsi" controller has an optional
|
||||
attribute <code>model</code>, which is one of "auto",
|
||||
"buslogic", "lsilogic", "lsias1068", or "vmpvscsi".
|
||||
A "usb" controller has an optional attribute <code>model</code>,
|
||||
which is one of "piix3-uhci", "piix4-uhci", "ehci",
|
||||
"ich9-ehci1", "ich9-uhci1", "ich9-uhci2", "ich9-uhci3",
|
||||
"vt82c686b-uhci" or "pci-ohci".
|
||||
</p>
|
||||
|
||||
<p>
|
||||
|
|
|
@ -878,6 +878,7 @@
|
|||
<value>scsi</value>
|
||||
<value>sata</value>
|
||||
<value>ccid</value>
|
||||
<value>usb</value>
|
||||
</choice>
|
||||
</attribute>
|
||||
</optional>
|
||||
|
|
|
@ -194,7 +194,8 @@ VIR_ENUM_IMPL(virDomainController, VIR_DOMAIN_CONTROLLER_TYPE_LAST,
|
|||
"scsi",
|
||||
"sata",
|
||||
"virtio-serial",
|
||||
"ccid")
|
||||
"ccid",
|
||||
"usb")
|
||||
|
||||
VIR_ENUM_IMPL(virDomainControllerModelSCSI, VIR_DOMAIN_CONTROLLER_MODEL_SCSI_LAST,
|
||||
"auto",
|
||||
|
@ -2473,6 +2474,8 @@ virDomainControllerModelTypeFromString(const virDomainControllerDefPtr def,
|
|||
{
|
||||
if (def->type == VIR_DOMAIN_CONTROLLER_TYPE_SCSI)
|
||||
return virDomainControllerModelSCSITypeFromString(model);
|
||||
else if (def->type == VIR_DOMAIN_CONTROLLER_TYPE_USB)
|
||||
return virDomainControllerModelUSBTypeFromString(model);
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
@ -8756,6 +8759,8 @@ virDomainControllerModelTypeToString(virDomainControllerDefPtr def,
|
|||
{
|
||||
if (def->type == VIR_DOMAIN_CONTROLLER_TYPE_SCSI)
|
||||
return virDomainControllerModelSCSITypeToString(model);
|
||||
else if (def->type == VIR_DOMAIN_CONTROLLER_TYPE_USB)
|
||||
return virDomainControllerModelUSBTypeToString(model);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
|
|
@ -253,6 +253,7 @@ enum virDomainControllerType {
|
|||
VIR_DOMAIN_CONTROLLER_TYPE_SATA,
|
||||
VIR_DOMAIN_CONTROLLER_TYPE_VIRTIO_SERIAL,
|
||||
VIR_DOMAIN_CONTROLLER_TYPE_CCID,
|
||||
VIR_DOMAIN_CONTROLLER_TYPE_USB,
|
||||
|
||||
VIR_DOMAIN_CONTROLLER_TYPE_LAST
|
||||
};
|
||||
|
|
|
@ -85,6 +85,20 @@ VIR_ENUM_IMPL(qemuVideo, VIR_DOMAIN_VIDEO_TYPE_LAST,
|
|||
"", /* don't support vbox */
|
||||
"qxl");
|
||||
|
||||
VIR_ENUM_DECL(qemuControllerModelUSB)
|
||||
|
||||
VIR_ENUM_IMPL(qemuControllerModelUSB, VIR_DOMAIN_CONTROLLER_MODEL_USB_LAST,
|
||||
"piix3-usb-uhci",
|
||||
"piix4-usb-uhci",
|
||||
"usb-ehci",
|
||||
"ich9-usb-ehci1",
|
||||
"ich9-usb-uhci1",
|
||||
"ich9-usb-uhci2",
|
||||
"ich9-usb-uhci3",
|
||||
"vt82c686b-usb-uhci",
|
||||
"pci-ohci");
|
||||
|
||||
|
||||
static void
|
||||
uname_normalize (struct utsname *ut)
|
||||
{
|
||||
|
@ -1703,9 +1717,60 @@ error:
|
|||
}
|
||||
|
||||
|
||||
static int
|
||||
qemuControllerModelUSBToCaps(int model)
|
||||
{
|
||||
switch (model) {
|
||||
case VIR_DOMAIN_CONTROLLER_MODEL_USB_PIIX3_UHCI:
|
||||
return QEMU_CAPS_PIIX3_USB_UHCI;
|
||||
case VIR_DOMAIN_CONTROLLER_MODEL_USB_PIIX4_UHCI:
|
||||
return QEMU_CAPS_PIIX4_USB_UHCI;
|
||||
case VIR_DOMAIN_CONTROLLER_MODEL_USB_EHCI:
|
||||
return QEMU_CAPS_USB_EHCI;
|
||||
case VIR_DOMAIN_CONTROLLER_MODEL_USB_ICH9_EHCI1:
|
||||
case VIR_DOMAIN_CONTROLLER_MODEL_USB_ICH9_UHCI1:
|
||||
case VIR_DOMAIN_CONTROLLER_MODEL_USB_ICH9_UHCI2:
|
||||
case VIR_DOMAIN_CONTROLLER_MODEL_USB_ICH9_UHCI3:
|
||||
return QEMU_CAPS_ICH9_USB_EHCI1;
|
||||
case VIR_DOMAIN_CONTROLLER_MODEL_USB_VT82C686B_UHCI:
|
||||
return QEMU_CAPS_VT82C686B_USB_UHCI;
|
||||
case VIR_DOMAIN_CONTROLLER_MODEL_USB_PCI_OHCI:
|
||||
return QEMU_CAPS_PCI_OHCI;
|
||||
default:
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static int
|
||||
qemuBuildUSBControllerDevStr(virDomainControllerDefPtr def,
|
||||
virBitmapPtr qemuCaps,
|
||||
virBuffer *buf)
|
||||
{
|
||||
const char *smodel;
|
||||
int model, caps;
|
||||
|
||||
model = def->model;
|
||||
if (model == -1)
|
||||
model = VIR_DOMAIN_CONTROLLER_MODEL_USB_PIIX3_UHCI;
|
||||
|
||||
smodel = qemuControllerModelUSBTypeToString(model);
|
||||
caps = qemuControllerModelUSBToCaps(model);
|
||||
|
||||
if (caps == -1 || !qemuCapsGet(qemuCaps, caps)) {
|
||||
qemuReportError(VIR_ERR_CONFIG_UNSUPPORTED,
|
||||
_("%s not supported in this QEMU binary"), smodel);
|
||||
return -1;
|
||||
}
|
||||
|
||||
virBufferAsprintf(buf, "%s,id=usb%d", smodel, def->idx);
|
||||
return 0;
|
||||
}
|
||||
|
||||
char *
|
||||
qemuBuildControllerDevStr(virDomainControllerDefPtr def,
|
||||
virBitmapPtr qemuCaps)
|
||||
virBitmapPtr qemuCaps,
|
||||
int *nusbcontroller)
|
||||
{
|
||||
virBuffer buf = VIR_BUFFER_INITIALIZER;
|
||||
|
||||
|
@ -1737,6 +1802,15 @@ qemuBuildControllerDevStr(virDomainControllerDefPtr def,
|
|||
virBufferAsprintf(&buf, "usb-ccid,id=ccid%d", def->idx);
|
||||
break;
|
||||
|
||||
case VIR_DOMAIN_CONTROLLER_TYPE_USB:
|
||||
if (qemuBuildUSBControllerDevStr(def, qemuCaps, &buf) == -1)
|
||||
goto error;
|
||||
|
||||
if (nusbcontroller)
|
||||
*nusbcontroller += 1;
|
||||
|
||||
break;
|
||||
|
||||
/* We always get an IDE controller, whether we want it or not. */
|
||||
case VIR_DOMAIN_CONTROLLER_TYPE_IDE:
|
||||
default:
|
||||
|
@ -2904,7 +2978,8 @@ qemuBuildCommandLine(virConnectPtr conn,
|
|||
bool has_rbd_hosts = false;
|
||||
virBuffer rbd_hosts = VIR_BUFFER_INITIALIZER;
|
||||
bool emitBootindex = false;
|
||||
|
||||
int usbcontroller = 0;
|
||||
bool usblegacy = false;
|
||||
uname_normalize(&ut);
|
||||
|
||||
if (qemuAssignDeviceAliases(def, qemuCaps) < 0)
|
||||
|
@ -3423,14 +3498,26 @@ qemuBuildCommandLine(virConnectPtr conn,
|
|||
goto error;
|
||||
}
|
||||
|
||||
virCommandAddArg(cmd, "-device");
|
||||
if (def->controllers[i]->type == VIR_DOMAIN_CONTROLLER_TYPE_USB &&
|
||||
def->controllers[i]->model == -1 &&
|
||||
!qemuCapsGet(qemuCaps, QEMU_CAPS_PIIX3_USB_UHCI)) {
|
||||
if (usblegacy) {
|
||||
qemuReportError(VIR_ERR_CONFIG_UNSUPPORTED,
|
||||
_("Multiple legacy USB controller not supported"));
|
||||
goto error;
|
||||
}
|
||||
usblegacy = true;
|
||||
} else {
|
||||
virCommandAddArg(cmd, "-device");
|
||||
|
||||
char *devstr;
|
||||
if (!(devstr = qemuBuildControllerDevStr(def->controllers[i], qemuCaps)))
|
||||
goto error;
|
||||
char *devstr;
|
||||
if (!(devstr = qemuBuildControllerDevStr(def->controllers[i], qemuCaps,
|
||||
&usbcontroller)))
|
||||
goto error;
|
||||
|
||||
virCommandAddArg(cmd, devstr);
|
||||
VIR_FREE(devstr);
|
||||
virCommandAddArg(cmd, devstr);
|
||||
VIR_FREE(devstr);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -4135,7 +4222,9 @@ qemuBuildCommandLine(virConnectPtr conn,
|
|||
}
|
||||
}
|
||||
|
||||
virCommandAddArg(cmd, "-usb");
|
||||
if (usbcontroller == 0)
|
||||
virCommandAddArg(cmd, "-usb");
|
||||
|
||||
for (i = 0 ; i < def->ninputs ; i++) {
|
||||
virDomainInputDefPtr input = def->inputs[i];
|
||||
|
||||
|
|
|
@ -89,7 +89,8 @@ char * qemuBuildFSDevStr(virDomainFSDefPtr fs,
|
|||
virBitmapPtr qemuCaps);
|
||||
/* Current, best practice */
|
||||
char * qemuBuildControllerDevStr(virDomainControllerDefPtr def,
|
||||
virBitmapPtr qemuCaps);
|
||||
virBitmapPtr qemuCaps,
|
||||
int *nusbcontroller);
|
||||
|
||||
char * qemuBuildWatchdogDevStr(virDomainWatchdogDefPtr dev,
|
||||
virBitmapPtr qemuCaps);
|
||||
|
|
|
@ -286,7 +286,15 @@ int qemuDomainAttachPciControllerDevice(struct qemud_driver *driver,
|
|||
if (qemuAssignDeviceControllerAlias(controller) < 0)
|
||||
goto cleanup;
|
||||
|
||||
if (!(devstr = qemuBuildControllerDevStr(controller, priv->qemuCaps))) {
|
||||
if (controller->type == VIR_DOMAIN_CONTROLLER_TYPE_USB &&
|
||||
controller->model == -1 &&
|
||||
!qemuCapsGet(priv->qemuCaps, QEMU_CAPS_PIIX3_USB_UHCI)) {
|
||||
qemuReportError(VIR_ERR_OPERATION_FAILED,
|
||||
_("USB controller hotplug unsupported in this QEMU binary"));
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
if (!(devstr = qemuBuildControllerDevStr(controller, priv->qemuCaps, NULL))) {
|
||||
goto cleanup;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -487,6 +487,13 @@ mymain(void)
|
|||
QEMU_CAPS_CHARDEV, QEMU_CAPS_DEVICE,
|
||||
QEMU_CAPS_NODEFCONFIG, QEMU_CAPS_CCID_EMULATED);
|
||||
|
||||
DO_TEST("usb-controller", false,
|
||||
QEMU_CAPS_CHARDEV, QEMU_CAPS_DEVICE,
|
||||
QEMU_CAPS_NODEFCONFIG);
|
||||
DO_TEST("usb-piix3-controller", false,
|
||||
QEMU_CAPS_CHARDEV, QEMU_CAPS_DEVICE, QEMU_CAPS_PIIX3_USB_UHCI,
|
||||
QEMU_CAPS_NODEFCONFIG);
|
||||
|
||||
DO_TEST("smbios", false, QEMU_CAPS_SMBIOS_TYPE);
|
||||
|
||||
DO_TEST("watchdog", false, NONE);
|
||||
|
|
Loading…
Reference in New Issue