}
static int
-qemuDefaultScsiControllerModel(virDomainDefPtr def) {
- if (STREQ(def->os.arch, "ppc64") &&
- STREQ(def->os.machine, "pseries")) {
- return VIR_DOMAIN_CONTROLLER_MODEL_SCSI_IBMVSCSI;
+qemuCheckScsiControllerModel(virDomainDefPtr def,
+ virBitmapPtr qemuCaps,
+ int *model)
+{
+ if (*model > 0) {
+ switch (*model) {
+ case VIR_DOMAIN_CONTROLLER_MODEL_SCSI_LSILOGIC:
+ if (!qemuCapsGet(qemuCaps, QEMU_CAPS_SCSI_LSI)) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("This QEMU doesn't support "
+ "lsi scsi controller"));
+ return -1;
+ }
+ break;
+ case VIR_DOMAIN_CONTROLLER_MODEL_SCSI_VIRTIO_SCSI:
+ if (!qemuCapsGet(qemuCaps, QEMU_CAPS_VIRTIO_SCSI_PCI)) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("This QEMU doesn't support "
+ "virtio scsi controller"));
+ return -1;
+ }
+ break;
+ case VIR_DOMAIN_CONTROLLER_MODEL_SCSI_IBMVSCSI:
+ /*TODO: need checking work here if necessary */
+ break;
+ default:
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
+ _("Unsupported controller model: %s"),
+ virDomainControllerModelSCSITypeToString(*model));
+ return -1;
+ }
} else {
- return VIR_DOMAIN_CONTROLLER_MODEL_SCSI_LSILOGIC;
+ if (STREQ(def->os.arch, "ppc64") &&
+ STREQ(def->os.machine, "pseries")) {
+ *model = VIR_DOMAIN_CONTROLLER_MODEL_SCSI_IBMVSCSI;
+ } else if (qemuCapsGet(qemuCaps, QEMU_CAPS_SCSI_LSI)) {
+ *model = VIR_DOMAIN_CONTROLLER_MODEL_SCSI_LSILOGIC;
+ } else {
+ virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("Unable to determine model for scsi controller"));
+ return -1;
+ }
}
+
+ return 0;
}
/* Our custom -drive naming scheme used with id= */
static int
qemuAssignDeviceDiskAliasCustom(virDomainDefPtr def,
- virDomainDiskDefPtr disk)
+ virDomainDiskDefPtr disk,
+ virBitmapPtr qemuCaps)
{
const char *prefix = virDomainDiskBusTypeToString(disk->bus);
int controllerModel = -1;
controllerModel =
virDomainDiskFindControllerModel(def, disk,
VIR_DOMAIN_CONTROLLER_TYPE_SCSI);
- }
- if (controllerModel == -1 ||
- controllerModel == VIR_DOMAIN_CONTROLLER_MODEL_SCSI_AUTO)
- controllerModel = qemuDefaultScsiControllerModel(def);
+ if ((qemuCheckScsiControllerModel(def, qemuCaps, &controllerModel)) < 0)
+ return -1;
+ }
if (disk->bus != VIR_DOMAIN_DISK_BUS_SCSI ||
controllerModel == VIR_DOMAIN_CONTROLLER_MODEL_SCSI_LSILOGIC) {
{
if (qemuCapsGet(qemuCaps, QEMU_CAPS_DRIVE)) {
if (qemuCapsGet(qemuCaps, QEMU_CAPS_DEVICE))
- return qemuAssignDeviceDiskAliasCustom(vmdef, def);
+ return qemuAssignDeviceDiskAliasCustom(vmdef, def, qemuCaps);
else
return qemuAssignDeviceDiskAliasFixed(def);
} else {
return 0;
}
-int qemuDomainAssignSpaprVIOAddresses(virDomainDefPtr def)
+int qemuDomainAssignSpaprVIOAddresses(virDomainDefPtr def,
+ virBitmapPtr qemuCaps)
{
- int i, rc;
+ int i, rc = -1;
int model;
+ virBitmapPtr localCaps = NULL;
/* Default values match QEMU. See spapr_(llan|vscsi|vty).c */
+ if (!qemuCaps) {
+ /* need to get information from real environment */
+ if (qemuCapsExtractVersionInfo(def->emulator, def->os.arch,
+ false, NULL,
+ &localCaps) < 0)
+ goto cleanup;
+ qemuCaps = localCaps;
+ }
+
for (i = 0 ; i < def->nnets; i++) {
if (def->nets[i]->model &&
STREQ(def->nets[i]->model, "spapr-vlan"))
rc = qemuAssignSpaprVIOAddress(def, &def->nets[i]->info,
0x1000ul);
if (rc)
- return rc;
+ goto cleanup;
}
for (i = 0 ; i < def->ncontrollers; i++) {
model = def->controllers[i]->model;
- if (model == -1 &&
- def->controllers[i]->type == VIR_DOMAIN_CONTROLLER_TYPE_SCSI)
- model = qemuDefaultScsiControllerModel(def);
+ if (def->controllers[i]->type == VIR_DOMAIN_CONTROLLER_TYPE_SCSI) {
+ rc = qemuCheckScsiControllerModel(def, qemuCaps, &model);
+ if (rc)
+ goto cleanup;
+ }
+
if (model == VIR_DOMAIN_CONTROLLER_MODEL_SCSI_IBMVSCSI &&
def->controllers[i]->type == VIR_DOMAIN_CONTROLLER_TYPE_SCSI)
def->controllers[i]->info.type = VIR_DOMAIN_DEVICE_ADDRESS_TYPE_SPAPRVIO;
rc = qemuAssignSpaprVIOAddress(def, &def->controllers[i]->info,
0x2000ul);
if (rc)
- return rc;
+ goto cleanup;
}
for (i = 0 ; i < def->nserials; i++) {
rc = qemuAssignSpaprVIOAddress(def, &def->serials[i]->info,
0x30000000ul);
if (rc)
- return rc;
+ goto cleanup;
}
/* No other devices are currently supported on spapr-vio */
- return 0;
+ rc = 0;
+
+cleanup:
+ qemuCapsFree(localCaps);
+ return rc;
}
#define QEMU_PCI_ADDRESS_LAST_SLOT 31
{
int rc;
- rc = qemuDomainAssignSpaprVIOAddresses(def);
+ rc = qemuDomainAssignSpaprVIOAddresses(def, qemuCaps);
if (rc)
return rc;
controllerModel =
virDomainDiskFindControllerModel(def, disk,
VIR_DOMAIN_CONTROLLER_TYPE_SCSI);
- if (controllerModel == -1 ||
- controllerModel == VIR_DOMAIN_CONTROLLER_MODEL_SCSI_AUTO)
- controllerModel = qemuDefaultScsiControllerModel(def);
+ if ((qemuCheckScsiControllerModel(def, qemuCaps, &controllerModel)) < 0)
+ goto error;
if (controllerModel == VIR_DOMAIN_CONTROLLER_MODEL_SCSI_LSILOGIC) {
if (disk->info.addr.drive.target != 0) {
switch (def->type) {
case VIR_DOMAIN_CONTROLLER_TYPE_SCSI:
model = def->model;
- if (model == -1 ||
- model == VIR_DOMAIN_CONTROLLER_MODEL_SCSI_AUTO) {
- model = qemuDefaultScsiControllerModel(domainDef);
- }
+ if ((qemuCheckScsiControllerModel(domainDef, qemuCaps, &model)) < 0)
+ return NULL;
+
switch (model) {
case VIR_DOMAIN_CONTROLLER_MODEL_SCSI_VIRTIO_SCSI:
virBufferAddLit(&buf, "virtio-scsi-pci");
}
if (qemuCapsGet(priv->qemuCaps, QEMU_CAPS_DEVICE))
- qemuDomainAssignAddresses(obj->def, priv->qemuCaps, obj);
+ if ((qemuDomainAssignAddresses(obj->def, priv->qemuCaps, obj)) < 0)
+ goto error;
if (virSecurityManagerReserveLabel(driver->securityManager, obj->def, obj->pid) < 0)
goto error;
*/
if (qemuCapsGet(priv->qemuCaps, QEMU_CAPS_DEVICE)) {
VIR_DEBUG("Assigning domain PCI addresses");
- qemuDomainAssignAddresses(vm->def, priv->qemuCaps, vm);
+ if ((qemuDomainAssignAddresses(vm->def, priv->qemuCaps, vm)) < 0)
+ goto cleanup;
}
VIR_DEBUG("Building emulator command line");
*/
if (qemuCapsGet(priv->qemuCaps, QEMU_CAPS_DEVICE)) {
VIR_DEBUG("Assigning domain PCI addresses");
- qemuDomainAssignAddresses(vm->def, priv->qemuCaps, vm);
+ if ((qemuDomainAssignAddresses(vm->def, priv->qemuCaps, vm)) < 0)
+ goto cleanup;
}
if ((timestamp = virTimeStringNow()) == NULL) {
DO_TEST("disk-usb-device",
QEMU_CAPS_DRIVE, QEMU_CAPS_DEVICE, QEMU_CAPS_NODEFCONFIG);
DO_TEST("disk-scsi-device",
- QEMU_CAPS_DRIVE, QEMU_CAPS_DEVICE, QEMU_CAPS_NODEFCONFIG);
+ QEMU_CAPS_DRIVE, QEMU_CAPS_DEVICE, QEMU_CAPS_NODEFCONFIG,
+ QEMU_CAPS_SCSI_LSI);
DO_TEST("disk-scsi-device-auto",
- QEMU_CAPS_DRIVE, QEMU_CAPS_DEVICE, QEMU_CAPS_NODEFCONFIG);
+ QEMU_CAPS_DRIVE, QEMU_CAPS_DEVICE, QEMU_CAPS_NODEFCONFIG,
+ QEMU_CAPS_SCSI_LSI);
DO_TEST("disk-scsi-disk-split",
QEMU_CAPS_DRIVE, QEMU_CAPS_DEVICE, QEMU_CAPS_NODEFCONFIG,
- QEMU_CAPS_SCSI_CD);
+ QEMU_CAPS_SCSI_CD, QEMU_CAPS_SCSI_LSI, QEMU_CAPS_VIRTIO_SCSI_PCI);
DO_TEST("disk-scsi-vscsi",
QEMU_CAPS_DRIVE, QEMU_CAPS_DEVICE, QEMU_CAPS_NODEFCONFIG);
DO_TEST("disk-scsi-virtio-scsi",
- QEMU_CAPS_DRIVE, QEMU_CAPS_DEVICE, QEMU_CAPS_NODEFCONFIG);
+ QEMU_CAPS_DRIVE, QEMU_CAPS_DEVICE, QEMU_CAPS_NODEFCONFIG,
+ QEMU_CAPS_VIRTIO_SCSI_PCI);
DO_TEST("disk-sata-device",
QEMU_CAPS_DRIVE, QEMU_CAPS_DEVICE,
QEMU_CAPS_NODEFCONFIG, QEMU_CAPS_ICH9_AHCI);
DO_TEST("disk-scsi-lun-passthrough",
QEMU_CAPS_DRIVE,
QEMU_CAPS_DEVICE,
- QEMU_CAPS_SCSI_BLOCK, QEMU_CAPS_VIRTIO_BLK_SG_IO);
+ QEMU_CAPS_SCSI_BLOCK, QEMU_CAPS_VIRTIO_BLK_SG_IO,
+ QEMU_CAPS_SCSI_LSI, QEMU_CAPS_VIRTIO_SCSI_PCI);
DO_TEST("graphics-vnc", NONE);
DO_TEST("graphics-vnc-socket", NONE);
DO_TEST("multifunction-pci-device",
QEMU_CAPS_DRIVE, QEMU_CAPS_DEVICE, QEMU_CAPS_NODEFCONFIG,
- QEMU_CAPS_PCI_MULTIFUNCTION);
+ QEMU_CAPS_PCI_MULTIFUNCTION, QEMU_CAPS_SCSI_LSI);
DO_TEST("monitor-json", QEMU_CAPS_DEVICE,
QEMU_CAPS_CHARDEV, QEMU_CAPS_MONITOR_JSON, QEMU_CAPS_NODEFCONFIG);