Signed-off-by: Chunyan Liu <cyliu(a)suse.com>
---
src/libvirt_private.syms | 1 +
src/qemu/qemu_hostdev.c | 111 -----------------------------------------------
src/util/virhostdev.c | 111 +++++++++++++++++++++++++++++++++++++++++++++++
src/util/virhostdev.h | 6 +++
4 files changed, 118 insertions(+), 111 deletions(-)
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
index 04694d8..f3cd7a0 100644
--- a/src/libvirt_private.syms
+++ b/src/libvirt_private.syms
@@ -1295,6 +1295,7 @@ virHookPresent;
#util/virhostdev.h
virHostdevManagerGetDefault;
virHostdevPreparePCIDevices;
+virHostdevPrepareSCSIDevices;
virHostdevPrepareUSBDevices;
virHostdevReAttachPCIDevices;
virHostdevUpdateActivePciHostdevs;
diff --git a/src/qemu/qemu_hostdev.c b/src/qemu/qemu_hostdev.c
index 41ee32f..32825a4 100644
--- a/src/qemu/qemu_hostdev.c
+++ b/src/qemu/qemu_hostdev.c
@@ -245,117 +245,6 @@ qemuPrepareHostUSBDevices(virQEMUDriverPtr driver,
hostdevs, nhostdevs, flags);
}
-static int
-virHostdevPrepareSCSIDevices(virHostdevManagerPtr hostdev_mgr,
- const char *drv_name,
- const char *name,
- virDomainHostdevDefPtr *hostdevs,
- int nhostdevs)
-{
- size_t i, j;
- int count;
- virSCSIDeviceListPtr list;
- virSCSIDevicePtr tmp;
-
- /* To prevent situation where SCSI device is assigned to two domains
- * we need to keep a list of currently assigned SCSI devices.
- * This is done in several loops which cannot be joined into one big
- * loop. See virHostdevPreparePCIDevices()
- */
- if (!(list = virSCSIDeviceListNew()))
- goto cleanup;
-
- /* Loop 1: build temporary list */
- for (i = 0; i < nhostdevs; i++) {
- virDomainHostdevDefPtr hostdev = hostdevs[i];
- virSCSIDevicePtr scsi;
-
- if (hostdev->mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS ||
- hostdev->source.subsys.type != VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI)
- continue;
-
- if (hostdev->managed) {
- virReportError(VIR_ERR_XML_ERROR, "%s",
- _("SCSI host device doesn't support managed
mode"));
- goto cleanup;
- }
-
- if (!(scsi = virSCSIDeviceNew(NULL,
- hostdev->source.subsys.u.scsi.adapter,
- hostdev->source.subsys.u.scsi.bus,
- hostdev->source.subsys.u.scsi.target,
- hostdev->source.subsys.u.scsi.unit,
- hostdev->readonly,
- hostdev->shareable)))
- goto cleanup;
-
- if (scsi && virSCSIDeviceListAdd(list, scsi) < 0) {
- virSCSIDeviceFree(scsi);
- goto cleanup;
- }
- }
-
- /* Loop 2: Mark devices in temporary list as used by @name
- * and add them to driver list. However, if something goes
- * wrong, perform rollback.
- */
- virObjectLock(hostdev_mgr->activeScsiHostdevs);
- count = virSCSIDeviceListCount(list);
-
- for (i = 0; i < count; i++) {
- virSCSIDevicePtr scsi = virSCSIDeviceListGet(list, i);
- if ((tmp = virSCSIDeviceListFind(hostdev_mgr->activeScsiHostdevs,
- scsi))) {
- bool scsi_shareable = virSCSIDeviceGetShareable(scsi);
- bool tmp_shareable = virSCSIDeviceGetShareable(tmp);
-
- if (!(scsi_shareable && tmp_shareable)) {
- virReportError(VIR_ERR_OPERATION_INVALID,
- _("SCSI device %s is already in use by "
- "other domain(s) as '%s'"),
- virSCSIDeviceGetName(tmp),
- tmp_shareable ? "shareable" :
"non-shareable");
- goto error;
- }
-
- if (virSCSIDeviceSetUsedBy(tmp, drv_name, name) < 0)
- goto error;
- } else {
- if (virSCSIDeviceSetUsedBy(scsi, drv_name, name) < 0)
- goto error;
-
- VIR_DEBUG("Adding %s to activeScsiHostdevs",
virSCSIDeviceGetName(scsi));
-
- if (virSCSIDeviceListAdd(hostdev_mgr->activeScsiHostdevs, scsi) < 0)
- goto error;
- }
- }
-
- virObjectUnlock(hostdev_mgr->activeScsiHostdevs);
-
- /* Loop 3: Temporary list was successfully merged with
- * driver list, so steal all items to avoid freeing them
- * when freeing temporary list.
- */
- while (virSCSIDeviceListCount(list) > 0) {
- tmp = virSCSIDeviceListGet(list, 0);
- virSCSIDeviceListSteal(list, tmp);
- }
-
- virObjectUnref(list);
- return 0;
-
-error:
- for (j = 0; j < i; j++) {
- tmp = virSCSIDeviceListGet(list, i);
- virSCSIDeviceListSteal(hostdev_mgr->activeScsiHostdevs, tmp);
- }
- virObjectUnlock(hostdev_mgr->activeScsiHostdevs);
-cleanup:
- virObjectUnref(list);
- return -1;
-}
-
int
qemuPrepareHostdevSCSIDevices(virQEMUDriverPtr driver,
const char *name,
diff --git a/src/util/virhostdev.c b/src/util/virhostdev.c
index a55480c..87b7368 100644
--- a/src/util/virhostdev.c
+++ b/src/util/virhostdev.c
@@ -1143,3 +1143,114 @@ cleanup:
virObjectUnref(list);
return ret;
}
+
+int
+virHostdevPrepareSCSIDevices(virHostdevManagerPtr hostdev_mgr,
+ const char *drv_name,
+ const char *name,
+ virDomainHostdevDefPtr *hostdevs,
+ int nhostdevs)
+{
+ size_t i, j;
+ int count;
+ virSCSIDeviceListPtr list;
+ virSCSIDevicePtr tmp;
+
+ /* To prevent situation where SCSI device is assigned to two domains
+ * we need to keep a list of currently assigned SCSI devices.
+ * This is done in several loops which cannot be joined into one big
+ * loop. See virHostdevPreparePCIDevices()
+ */
+ if (!(list = virSCSIDeviceListNew()))
+ goto cleanup;
+
+ /* Loop 1: build temporary list */
+ for (i = 0; i < nhostdevs; i++) {
+ virDomainHostdevDefPtr hostdev = hostdevs[i];
+ virSCSIDevicePtr scsi;
+
+ if (hostdev->mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS ||
+ hostdev->source.subsys.type != VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI)
+ continue;
+
+ if (hostdev->managed) {
+ virReportError(VIR_ERR_XML_ERROR, "%s",
+ _("SCSI host device doesn't support managed
mode"));
+ goto cleanup;
+ }
+
+ if (!(scsi = virSCSIDeviceNew(NULL,
+ hostdev->source.subsys.u.scsi.adapter,
+ hostdev->source.subsys.u.scsi.bus,
+ hostdev->source.subsys.u.scsi.target,
+ hostdev->source.subsys.u.scsi.unit,
+ hostdev->readonly,
+ hostdev->shareable)))
+ goto cleanup;
+
+ if (scsi && virSCSIDeviceListAdd(list, scsi) < 0) {
+ virSCSIDeviceFree(scsi);
+ goto cleanup;
+ }
+ }
+
+ /* Loop 2: Mark devices in temporary list as used by @name
+ * and add them to driver list. However, if something goes
+ * wrong, perform rollback.
+ */
+ virObjectLock(hostdev_mgr->activeScsiHostdevs);
+ count = virSCSIDeviceListCount(list);
+
+ for (i = 0; i < count; i++) {
+ virSCSIDevicePtr scsi = virSCSIDeviceListGet(list, i);
+ if ((tmp = virSCSIDeviceListFind(hostdev_mgr->activeScsiHostdevs,
+ scsi))) {
+ bool scsi_shareable = virSCSIDeviceGetShareable(scsi);
+ bool tmp_shareable = virSCSIDeviceGetShareable(tmp);
+
+ if (!(scsi_shareable && tmp_shareable)) {
+ virReportError(VIR_ERR_OPERATION_INVALID,
+ _("SCSI device %s is already in use by "
+ "other domain(s) as '%s'"),
+ virSCSIDeviceGetName(tmp),
+ tmp_shareable ? "shareable" :
"non-shareable");
+ goto error;
+ }
+
+ if (virSCSIDeviceSetUsedBy(tmp, drv_name, name) < 0)
+ goto error;
+ } else {
+ if (virSCSIDeviceSetUsedBy(scsi, drv_name, name) < 0)
+ goto error;
+
+ VIR_DEBUG("Adding %s to activeScsiHostdevs",
virSCSIDeviceGetName(scsi));
+
+ if (virSCSIDeviceListAdd(hostdev_mgr->activeScsiHostdevs, scsi) < 0)
+ goto error;
+ }
+ }
+
+ virObjectUnlock(hostdev_mgr->activeScsiHostdevs);
+
+ /* Loop 3: Temporary list was successfully merged with
+ * driver list, so steal all items to avoid freeing them
+ * when freeing temporary list.
+ */
+ while (virSCSIDeviceListCount(list) > 0) {
+ tmp = virSCSIDeviceListGet(list, 0);
+ virSCSIDeviceListSteal(list, tmp);
+ }
+
+ virObjectUnref(list);
+ return 0;
+
+error:
+ for (j = 0; j < i; j++) {
+ tmp = virSCSIDeviceListGet(list, i);
+ virSCSIDeviceListSteal(hostdev_mgr->activeScsiHostdevs, tmp);
+ }
+ virObjectUnlock(hostdev_mgr->activeScsiHostdevs);
+cleanup:
+ virObjectUnref(list);
+ return -1;
+}
diff --git a/src/util/virhostdev.h b/src/util/virhostdev.h
index 83ebefc..c149603 100644
--- a/src/util/virhostdev.h
+++ b/src/util/virhostdev.h
@@ -65,6 +65,12 @@ virHostdevPrepareUSBDevices(virHostdevManagerPtr hostdev_mgr,
virDomainHostdevDefPtr *hostdevs,
int nhostdevs,
unsigned int flags);
+int
+virHostdevPrepareSCSIDevices(virHostdevManagerPtr hostdev_mgr,
+ const char *drv_name,
+ const char *name,
+ virDomainHostdevDefPtr *hostdevs,
+ int nhostdevs);
void
virHostdevReAttachPCIDevices(virHostdevManagerPtr hostdev_mgr,
const char *drv_name,
--
1.9.0