|
|
7a3408 |
From a9dc408532244f476ace6ca0d524ca7e99324507 Mon Sep 17 00:00:00 2001
|
|
|
7a3408 |
Message-Id: <a9dc408532244f476ace6ca0d524ca7e99324507@dist-git>
|
|
|
7a3408 |
From: John Ferlan <jferlan@redhat.com>
|
|
|
7a3408 |
Date: Thu, 9 Jul 2015 08:28:53 -0400
|
|
|
7a3408 |
Subject: [PATCH] qemu: Refactor qemuCheckSharedDisk to create
|
|
|
7a3408 |
qemuCheckUnprivSGIO
|
|
|
7a3408 |
|
|
|
7a3408 |
https://bugzilla.redhat.com/show_bug.cgi?id=1072736
|
|
|
7a3408 |
|
|
|
7a3408 |
Split out the current function in order to share the code with hostdev
|
|
|
7a3408 |
in a future patch. Failure to match the expected sgio value against what
|
|
|
7a3408 |
is stored will cause an error which the caller would need to handle since
|
|
|
7a3408 |
only the caller has the disk (or eventually hostdev) specific data in
|
|
|
7a3408 |
order to uniquely identify the disk in an error message.
|
|
|
7a3408 |
|
|
|
7a3408 |
Signed-off-by: John Ferlan <jferlan@redhat.com>
|
|
|
7a3408 |
(cherry picked from commit f6a5cbbfdcd1cd5354de40c923968235951dc879)
|
|
|
7a3408 |
Signed-off-by: Jiri Denemark <jdenemar@redhat.com>
|
|
|
7a3408 |
---
|
|
|
7a3408 |
src/qemu/qemu_conf.c | 130 ++++++++++++++++++++++++++++++++-------------------
|
|
|
7a3408 |
1 file changed, 81 insertions(+), 49 deletions(-)
|
|
|
7a3408 |
|
|
|
7a3408 |
diff --git a/src/qemu/qemu_conf.c b/src/qemu/qemu_conf.c
|
|
|
7a3408 |
index a761ec5..bf2ec1e 100644
|
|
|
7a3408 |
--- a/src/qemu/qemu_conf.c
|
|
|
7a3408 |
+++ b/src/qemu/qemu_conf.c
|
|
|
7a3408 |
@@ -1018,6 +1018,69 @@ qemuGetSharedDeviceKey(const char *device_path)
|
|
|
7a3408 |
return key;
|
|
|
7a3408 |
}
|
|
|
7a3408 |
|
|
|
7a3408 |
+/*
|
|
|
7a3408 |
+ * Make necessary checks for the need to check and for the current setting
|
|
|
7a3408 |
+ * of the 'unpriv_sgio' value for the device_path passed.
|
|
|
7a3408 |
+ *
|
|
|
7a3408 |
+ * Returns:
|
|
|
7a3408 |
+ * 0 - Success
|
|
|
7a3408 |
+ * -1 - Some failure which would already have been messaged
|
|
|
7a3408 |
+ * -2 - Mismatch with the "shared" sgio setting - needs to be messaged
|
|
|
7a3408 |
+ * by caller since it has context of which type of disk resource is
|
|
|
7a3408 |
+ * being used and in the future the hostdev information.
|
|
|
7a3408 |
+ */
|
|
|
7a3408 |
+static int
|
|
|
7a3408 |
+qemuCheckUnprivSGIO(virHashTablePtr sharedDevices,
|
|
|
7a3408 |
+ const char *device_path,
|
|
|
7a3408 |
+ int sgio)
|
|
|
7a3408 |
+{
|
|
|
7a3408 |
+ char *sysfs_path = NULL;
|
|
|
7a3408 |
+ char *key = NULL;
|
|
|
7a3408 |
+ int val;
|
|
|
7a3408 |
+ int ret = -1;
|
|
|
7a3408 |
+
|
|
|
7a3408 |
+ if (!(sysfs_path = virGetUnprivSGIOSysfsPath(device_path, NULL)))
|
|
|
7a3408 |
+ goto cleanup;
|
|
|
7a3408 |
+
|
|
|
7a3408 |
+ /* It can't be conflict if unpriv_sgio is not supported by kernel. */
|
|
|
7a3408 |
+ if (!virFileExists(sysfs_path)) {
|
|
|
7a3408 |
+ ret = 0;
|
|
|
7a3408 |
+ goto cleanup;
|
|
|
7a3408 |
+ }
|
|
|
7a3408 |
+
|
|
|
7a3408 |
+ if (!(key = qemuGetSharedDeviceKey(device_path)))
|
|
|
7a3408 |
+ goto cleanup;
|
|
|
7a3408 |
+
|
|
|
7a3408 |
+ /* It can't be conflict if no other domain is sharing it. */
|
|
|
7a3408 |
+ if (!(virHashLookup(sharedDevices, key))) {
|
|
|
7a3408 |
+ ret = 0;
|
|
|
7a3408 |
+ goto cleanup;
|
|
|
7a3408 |
+ }
|
|
|
7a3408 |
+
|
|
|
7a3408 |
+ if (virGetDeviceUnprivSGIO(device_path, NULL, &val) < 0)
|
|
|
7a3408 |
+ goto cleanup;
|
|
|
7a3408 |
+
|
|
|
7a3408 |
+ /* Error message on failure needs to be handled in caller
|
|
|
7a3408 |
+ * since there is more specific knowledge of device
|
|
|
7a3408 |
+ */
|
|
|
7a3408 |
+ if (!((val == 0 &&
|
|
|
7a3408 |
+ (sgio == VIR_DOMAIN_DEVICE_SGIO_FILTERED ||
|
|
|
7a3408 |
+ sgio == VIR_DOMAIN_DEVICE_SGIO_DEFAULT)) ||
|
|
|
7a3408 |
+ (val == 1 &&
|
|
|
7a3408 |
+ sgio == VIR_DOMAIN_DEVICE_SGIO_UNFILTERED))) {
|
|
|
7a3408 |
+ ret = -2;
|
|
|
7a3408 |
+ goto cleanup;
|
|
|
7a3408 |
+ }
|
|
|
7a3408 |
+
|
|
|
7a3408 |
+ ret = 0;
|
|
|
7a3408 |
+
|
|
|
7a3408 |
+ cleanup:
|
|
|
7a3408 |
+ VIR_FREE(sysfs_path);
|
|
|
7a3408 |
+ VIR_FREE(key);
|
|
|
7a3408 |
+ return ret;
|
|
|
7a3408 |
+}
|
|
|
7a3408 |
+
|
|
|
7a3408 |
+
|
|
|
7a3408 |
/* Check if a shared device's setting conflicts with the conf
|
|
|
7a3408 |
* used by other domain(s). Currently only checks the sgio
|
|
|
7a3408 |
* setting. Note that this should only be called for disk with
|
|
|
7a3408 |
@@ -1029,62 +1092,31 @@ static int
|
|
|
7a3408 |
qemuCheckSharedDisk(virHashTablePtr sharedDevices,
|
|
|
7a3408 |
virDomainDiskDefPtr disk)
|
|
|
7a3408 |
{
|
|
|
7a3408 |
- char *sysfs_path = NULL;
|
|
|
7a3408 |
- char *key = NULL;
|
|
|
7a3408 |
- int val;
|
|
|
7a3408 |
- int ret = -1;
|
|
|
7a3408 |
+ int ret;
|
|
|
7a3408 |
|
|
|
7a3408 |
if (disk->device != VIR_DOMAIN_DISK_DEVICE_LUN)
|
|
|
7a3408 |
return 0;
|
|
|
7a3408 |
|
|
|
7a3408 |
- if (!(sysfs_path = virGetUnprivSGIOSysfsPath(disk->src->path, NULL)))
|
|
|
7a3408 |
- goto cleanup;
|
|
|
7a3408 |
-
|
|
|
7a3408 |
- /* It can't be conflict if unpriv_sgio is not supported by kernel. */
|
|
|
7a3408 |
- if (!virFileExists(sysfs_path)) {
|
|
|
7a3408 |
- ret = 0;
|
|
|
7a3408 |
- goto cleanup;
|
|
|
7a3408 |
- }
|
|
|
7a3408 |
-
|
|
|
7a3408 |
- if (!(key = qemuGetSharedDeviceKey(disk->src->path)))
|
|
|
7a3408 |
- goto cleanup;
|
|
|
7a3408 |
-
|
|
|
7a3408 |
- /* It can't be conflict if no other domain is sharing it. */
|
|
|
7a3408 |
- if (!(virHashLookup(sharedDevices, key))) {
|
|
|
7a3408 |
- ret = 0;
|
|
|
7a3408 |
- goto cleanup;
|
|
|
7a3408 |
- }
|
|
|
7a3408 |
-
|
|
|
7a3408 |
- if (virGetDeviceUnprivSGIO(disk->src->path, NULL, &val) < 0)
|
|
|
7a3408 |
- goto cleanup;
|
|
|
7a3408 |
-
|
|
|
7a3408 |
- if (!((val == 0 &&
|
|
|
7a3408 |
- (disk->sgio == VIR_DOMAIN_DEVICE_SGIO_FILTERED ||
|
|
|
7a3408 |
- disk->sgio == VIR_DOMAIN_DEVICE_SGIO_DEFAULT)) ||
|
|
|
7a3408 |
- (val == 1 &&
|
|
|
7a3408 |
- disk->sgio == VIR_DOMAIN_DEVICE_SGIO_UNFILTERED))) {
|
|
|
7a3408 |
-
|
|
|
7a3408 |
- if (virDomainDiskGetType(disk) == VIR_STORAGE_TYPE_VOLUME) {
|
|
|
7a3408 |
- virReportError(VIR_ERR_OPERATION_INVALID,
|
|
|
7a3408 |
- _("sgio of shared disk 'pool=%s' 'volume=%s' conflicts "
|
|
|
7a3408 |
- "with other active domains"),
|
|
|
7a3408 |
- disk->src->srcpool->pool,
|
|
|
7a3408 |
- disk->src->srcpool->volume);
|
|
|
7a3408 |
- } else {
|
|
|
7a3408 |
- virReportError(VIR_ERR_OPERATION_INVALID,
|
|
|
7a3408 |
- _("sgio of shared disk '%s' conflicts with other "
|
|
|
7a3408 |
- "active domains"), disk->src->path);
|
|
|
7a3408 |
+ if ((ret = qemuCheckUnprivSGIO(sharedDevices, disk->src->path,
|
|
|
7a3408 |
+ disk->sgio)) < 0) {
|
|
|
7a3408 |
+ if (ret == -2) {
|
|
|
7a3408 |
+ if (virDomainDiskGetType(disk) == VIR_STORAGE_TYPE_VOLUME) {
|
|
|
7a3408 |
+ virReportError(VIR_ERR_OPERATION_INVALID,
|
|
|
7a3408 |
+ _("sgio of shared disk 'pool=%s' 'volume=%s' "
|
|
|
7a3408 |
+ "conflicts with other active domains"),
|
|
|
7a3408 |
+ disk->src->srcpool->pool,
|
|
|
7a3408 |
+ disk->src->srcpool->volume);
|
|
|
7a3408 |
+ } else {
|
|
|
7a3408 |
+ virReportError(VIR_ERR_OPERATION_INVALID,
|
|
|
7a3408 |
+ _("sgio of shared disk '%s' conflicts with "
|
|
|
7a3408 |
+ "other active domains"),
|
|
|
7a3408 |
+ disk->src->path);
|
|
|
7a3408 |
+ }
|
|
|
7a3408 |
}
|
|
|
7a3408 |
-
|
|
|
7a3408 |
- goto cleanup;
|
|
|
7a3408 |
+ return -1;
|
|
|
7a3408 |
}
|
|
|
7a3408 |
|
|
|
7a3408 |
- ret = 0;
|
|
|
7a3408 |
-
|
|
|
7a3408 |
- cleanup:
|
|
|
7a3408 |
- VIR_FREE(sysfs_path);
|
|
|
7a3408 |
- VIR_FREE(key);
|
|
|
7a3408 |
- return ret;
|
|
|
7a3408 |
+ return 0;
|
|
|
7a3408 |
}
|
|
|
7a3408 |
|
|
|
7a3408 |
|
|
|
7a3408 |
--
|
|
|
7a3408 |
2.5.1
|
|
|
7a3408 |
|