forked from pool/libvirt
Accepting request 408966 from home:jfehlig:branches:Virtualization
Add some SLE12 SP2 fixes to the Factory/Tumbleweed libvirt package. - BuildRequires: use librbd-devel instead of ceph-devel - Enable rbd support for aarch64 bsc#979473 - Use driver_override sysfs interface for binding/unbinding PCI stub drivers pci-simplify-stub.patch, pci-use-driver-override-sysfs.patch bsc#986718 OBS-URL: https://build.opensuse.org/request/show/408966 OBS-URL: https://build.opensuse.org/package/show/Virtualization/libvirt?expand=0&rev=551
This commit is contained in:
parent
b527b0e7f8
commit
91a43d315c
@ -1,3 +1,18 @@
|
||||
-------------------------------------------------------------------
|
||||
Fri Jul 15 14:57:40 UTC 2016 - jfehlig@suse.com
|
||||
|
||||
- BuildRequires: use librbd-devel instead of ceph-devel
|
||||
- Enable rbd support for aarch64
|
||||
bsc#979473
|
||||
|
||||
-------------------------------------------------------------------
|
||||
Thu Jul 14 22:39:08 UTC 2016 - jfehlig@suse.com
|
||||
|
||||
- Use driver_override sysfs interface for binding/unbinding
|
||||
PCI stub drivers
|
||||
pci-simplify-stub.patch, pci-use-driver-override-sysfs.patch
|
||||
bsc#986718
|
||||
|
||||
-------------------------------------------------------------------
|
||||
Tue Jul 12 19:57:40 UTC 2016 - jfehlig@suse.com
|
||||
|
||||
|
35
libvirt.spec
35
libvirt.spec
@ -102,11 +102,30 @@
|
||||
%define with_phyp 1
|
||||
%endif
|
||||
|
||||
# For now, only enable rbd storage backend on x86_64 SLE
|
||||
%if %{with_sle_build}
|
||||
%ifarch x86_64
|
||||
%define with_storage_rbd 1
|
||||
%endif
|
||||
# rbd enablement is a bit tricky. For x86_64
|
||||
%ifarch x86_64
|
||||
# enable on anything newer than 1320, or SLE12 family newer than 120100
|
||||
# use librbd-devel as build dependency
|
||||
%if 0%{?suse_version} > 1320 || ( 0%{?suse_version} == 1315 && ( 0%{?sle_version} > 120100 ) )
|
||||
%define with_storage_rbd 1
|
||||
%define with_rbd_lib librbd-devel
|
||||
%endif
|
||||
# enable for SLE12 family <= 120100 (SLE12ga/sp1, Leap 42.1)
|
||||
# use ceph-devel as build dependency
|
||||
%if 0%{?suse_version} == 1315 && 0%{?sle_version} <= 120100
|
||||
%define with_storage_rbd 1
|
||||
%define with_rbd_lib ceph-devel
|
||||
%endif
|
||||
%endif
|
||||
|
||||
# For arm
|
||||
%ifarch aarch64
|
||||
# enable on anything newer than 1320, or SLE12 family newer than 120100
|
||||
# use librbd-devel as build dependency
|
||||
%if 0%{?suse_version} > 1320 || ( 0%{?is_opensuse} == 0 && 0%{?sle_version} > 120100 )
|
||||
%define with_storage_rbd 1
|
||||
%define with_rbd_lib librbd-devel
|
||||
%endif
|
||||
%endif
|
||||
|
||||
# Support systemd on 12.1 and later
|
||||
@ -240,7 +259,7 @@ BuildRequires: parted-devel
|
||||
# For Multipath support
|
||||
BuildRequires: device-mapper-devel
|
||||
%if %{with_storage_rbd}
|
||||
BuildRequires: ceph-devel
|
||||
BuildRequires: %{with_rbd_lib}
|
||||
%endif
|
||||
%if %{with_numactl}
|
||||
# For QEMU/LXC numa info
|
||||
@ -282,6 +301,8 @@ Source100: %{name}-rpmlintrc
|
||||
Patch0: c8f08e48-systemd-notify-fix.patch
|
||||
# Patches pending upstream review
|
||||
Patch100: libxl-dom-reset.patch
|
||||
Patch101: pci-simplify-stub.patch
|
||||
Patch102: pci-use-driver-override-sysfs.patch
|
||||
# Need to go upstream
|
||||
Patch150: xen-pv-cdrom.patch
|
||||
Patch151: blockcopy-check-dst-identical-device.patch
|
||||
@ -733,6 +754,8 @@ libvirt plugin for NSS for translating domain names into IP addresses.
|
||||
%setup -q
|
||||
%patch0 -p1
|
||||
%patch100 -p1
|
||||
%patch101 -p1
|
||||
%patch102 -p1
|
||||
%patch150 -p1
|
||||
%patch151 -p1
|
||||
%patch152 -p1
|
||||
|
118
pci-simplify-stub.patch
Normal file
118
pci-simplify-stub.patch
Normal file
@ -0,0 +1,118 @@
|
||||
commit caba00f00fb18d8ffc388f4fc8b82527ef98d3b0
|
||||
Author: Jim Fehlig <jfehlig@suse.com>
|
||||
Date: Wed Jul 6 14:06:37 2016 -0600
|
||||
|
||||
virpci: simplify virPCIDeviceBindToStub
|
||||
|
||||
Early in virPCIDeviceBindToStub, there is a check to see if the
|
||||
stub is already bound to the device, returning success with no
|
||||
further actions if that is the case.
|
||||
|
||||
The same condition is unnecessarily checked later in the function.
|
||||
Remove the unneeded checks to simplify the logic a bit.
|
||||
|
||||
Signed-off-by: Jim Fehlig <jfehlig@suse.com>
|
||||
|
||||
Index: libvirt-2.0.0/src/util/virpci.c
|
||||
===================================================================
|
||||
--- libvirt-2.0.0.orig/src/util/virpci.c
|
||||
+++ libvirt-2.0.0/src/util/virpci.c
|
||||
@@ -1196,7 +1196,6 @@ static int
|
||||
virPCIDeviceBindToStub(virPCIDevicePtr dev)
|
||||
{
|
||||
int result = -1;
|
||||
- bool reprobe = false;
|
||||
char *stubDriverPath = NULL;
|
||||
char *driverLink = NULL;
|
||||
char *path = NULL; /* reused for different purposes */
|
||||
@@ -1225,10 +1224,16 @@ virPCIDeviceBindToStub(virPCIDevicePtr d
|
||||
/* The device is already bound to the correct driver */
|
||||
VIR_DEBUG("Device %s is already bound to %s",
|
||||
dev->name, stubDriverName);
|
||||
+ dev->unbind_from_stub = true;
|
||||
+ dev->remove_slot = true;
|
||||
result = 0;
|
||||
goto cleanup;
|
||||
}
|
||||
- reprobe = true;
|
||||
+ /*
|
||||
+ * If the device is bound to a driver that is not the stub, we'll
|
||||
+ * need to reprobe later
|
||||
+ */
|
||||
+ dev->reprobe = true;
|
||||
}
|
||||
|
||||
/* Add the PCI device ID to the stub's dynamic ID table;
|
||||
@@ -1249,51 +1254,34 @@ virPCIDeviceBindToStub(virPCIDevicePtr d
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
- /* check whether the device is bound to pci-stub when we write dev->id to
|
||||
- * ${stubDriver}/new_id.
|
||||
- */
|
||||
- if (virFileLinkPointsTo(driverLink, stubDriverPath)) {
|
||||
- dev->unbind_from_stub = true;
|
||||
- dev->remove_slot = true;
|
||||
- result = 0;
|
||||
+ if (virPCIDeviceUnbind(dev) < 0)
|
||||
goto remove_id;
|
||||
- }
|
||||
|
||||
- if (virPCIDeviceUnbind(dev) < 0)
|
||||
+ /* Xen's pciback.ko wants you to use new_slot first */
|
||||
+ VIR_FREE(path);
|
||||
+ if (!(path = virPCIDriverFile(stubDriverName, "new_slot")))
|
||||
goto remove_id;
|
||||
|
||||
- /* If the device was bound to a driver we'll need to reprobe later */
|
||||
- dev->reprobe = reprobe;
|
||||
+ if (virFileExists(path) && virFileWriteStr(path, dev->name, 0) < 0) {
|
||||
+ virReportSystemError(errno,
|
||||
+ _("Failed to add slot for "
|
||||
+ "PCI device '%s' to %s"),
|
||||
+ dev->name, stubDriverName);
|
||||
+ goto remove_id;
|
||||
+ }
|
||||
+ dev->remove_slot = true;
|
||||
|
||||
- /* If the device isn't already bound to pci-stub, try binding it now.
|
||||
- */
|
||||
- if (!virFileLinkPointsTo(driverLink, stubDriverPath)) {
|
||||
- /* Xen's pciback.ko wants you to use new_slot first */
|
||||
- VIR_FREE(path);
|
||||
- if (!(path = virPCIDriverFile(stubDriverName, "new_slot")))
|
||||
- goto remove_id;
|
||||
-
|
||||
- if (virFileExists(path) && virFileWriteStr(path, dev->name, 0) < 0) {
|
||||
- virReportSystemError(errno,
|
||||
- _("Failed to add slot for "
|
||||
- "PCI device '%s' to %s"),
|
||||
- dev->name, stubDriverName);
|
||||
- goto remove_id;
|
||||
- }
|
||||
- dev->remove_slot = true;
|
||||
+ VIR_FREE(path);
|
||||
+ if (!(path = virPCIDriverFile(stubDriverName, "bind")))
|
||||
+ goto remove_id;
|
||||
|
||||
- VIR_FREE(path);
|
||||
- if (!(path = virPCIDriverFile(stubDriverName, "bind")))
|
||||
- goto remove_id;
|
||||
-
|
||||
- if (virFileWriteStr(path, dev->name, 0) < 0) {
|
||||
- virReportSystemError(errno,
|
||||
- _("Failed to bind PCI device '%s' to %s"),
|
||||
- dev->name, stubDriverName);
|
||||
- goto remove_id;
|
||||
- }
|
||||
- dev->unbind_from_stub = true;
|
||||
+ if (virFileWriteStr(path, dev->name, 0) < 0) {
|
||||
+ virReportSystemError(errno,
|
||||
+ _("Failed to bind PCI device '%s' to %s"),
|
||||
+ dev->name, stubDriverName);
|
||||
+ goto remove_id;
|
||||
}
|
||||
+ dev->unbind_from_stub = true;
|
||||
|
||||
result = 0;
|
||||
|
271
pci-use-driver-override-sysfs.patch
Normal file
271
pci-use-driver-override-sysfs.patch
Normal file
@ -0,0 +1,271 @@
|
||||
commit 1de627810eaba897705cf32c9f025023e34ce73a
|
||||
Author: Jim Fehlig <jfehlig@suse.com>
|
||||
Date: Fri Jul 8 16:25:03 2016 -0600
|
||||
|
||||
virpci: support driver_override sysfs interface
|
||||
|
||||
Currently, libvirt uses the new_id PCI sysfs interface to bind a PCI
|
||||
stub driver to a PCI device. The new_id interface is known to be
|
||||
buggy and racey, hence a more deterministic interface was introduced
|
||||
in the 3.12 kernel - driver_override. For more details see
|
||||
|
||||
https://www.redhat.com/archives/libvir-list/2016-June/msg02124.html
|
||||
|
||||
This patch changes the stub binding/unbinding code to use the
|
||||
driver_override interface if present. If not present, the new_id
|
||||
interface will be used to provide compatibility with older kernels
|
||||
lacking driver_override.
|
||||
|
||||
Signed-off-by: Jim Fehlig <jfehlig@suse.com>
|
||||
|
||||
Index: libvirt-2.0.0/src/util/virpci.c
|
||||
===================================================================
|
||||
--- libvirt-2.0.0.orig/src/util/virpci.c
|
||||
+++ libvirt-2.0.0/src/util/virpci.c
|
||||
@@ -1158,6 +1158,19 @@ virPCIDeviceUnbindFromStub(virPCIDeviceP
|
||||
|
||||
VIR_DEBUG("Reprobing for PCI device %s", dev->name);
|
||||
|
||||
+ /* Remove driver_override if it exists */
|
||||
+ VIR_FREE(path);
|
||||
+ if (!(path = virPCIFile(dev->name, "driver_override")))
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ if (virFileExists(path) && virFileWriteStr(path, "\n", 0) < 0) {
|
||||
+ virReportSystemError(errno,
|
||||
+ _("Failed to remove stub driver from "
|
||||
+ "driver_override interface of PCI device '%s'"),
|
||||
+ dev->name);
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
/* Trigger a re-probe of the device is not in the stub's dynamic
|
||||
* ID table. If the stub is available, but 'remove_id' isn't
|
||||
* available, then re-probing would just cause the device to be
|
||||
@@ -1193,49 +1206,13 @@ virPCIDeviceUnbindFromStub(virPCIDeviceP
|
||||
|
||||
|
||||
static int
|
||||
-virPCIDeviceBindToStub(virPCIDevicePtr dev)
|
||||
+virPCIDeviceBindToStubWithNewid(virPCIDevicePtr dev,
|
||||
+ const char *stubDriverName)
|
||||
{
|
||||
- int result = -1;
|
||||
- char *stubDriverPath = NULL;
|
||||
- char *driverLink = NULL;
|
||||
- char *path = NULL; /* reused for different purposes */
|
||||
- const char *stubDriverName = NULL;
|
||||
+ int ret = -1;
|
||||
+ char *path = NULL;
|
||||
virErrorPtr err = NULL;
|
||||
|
||||
- /* Check the device is configured to use one of the known stub drivers */
|
||||
- if (dev->stubDriver == VIR_PCI_STUB_DRIVER_NONE) {
|
||||
- virReportError(VIR_ERR_INTERNAL_ERROR,
|
||||
- _("No stub driver configured for PCI device %s"),
|
||||
- dev->name);
|
||||
- return -1;
|
||||
- } else if (!(stubDriverName = virPCIStubDriverTypeToString(dev->stubDriver))) {
|
||||
- virReportError(VIR_ERR_INTERNAL_ERROR,
|
||||
- _("Unknown stub driver configured for PCI device %s"),
|
||||
- dev->name);
|
||||
- return -1;
|
||||
- }
|
||||
-
|
||||
- if (!(stubDriverPath = virPCIDriverDir(stubDriverName)) ||
|
||||
- !(driverLink = virPCIFile(dev->name, "driver")))
|
||||
- goto cleanup;
|
||||
-
|
||||
- if (virFileExists(driverLink)) {
|
||||
- if (virFileLinkPointsTo(driverLink, stubDriverPath)) {
|
||||
- /* The device is already bound to the correct driver */
|
||||
- VIR_DEBUG("Device %s is already bound to %s",
|
||||
- dev->name, stubDriverName);
|
||||
- dev->unbind_from_stub = true;
|
||||
- dev->remove_slot = true;
|
||||
- result = 0;
|
||||
- goto cleanup;
|
||||
- }
|
||||
- /*
|
||||
- * If the device is bound to a driver that is not the stub, we'll
|
||||
- * need to reprobe later
|
||||
- */
|
||||
- dev->reprobe = true;
|
||||
- }
|
||||
-
|
||||
/* Add the PCI device ID to the stub's dynamic ID table;
|
||||
* this is needed to allow us to bind the device to the stub.
|
||||
* Note: if the device is not currently bound to any driver,
|
||||
@@ -1283,7 +1260,7 @@ virPCIDeviceBindToStub(virPCIDevicePtr d
|
||||
}
|
||||
dev->unbind_from_stub = true;
|
||||
|
||||
- result = 0;
|
||||
+ ret = 0;
|
||||
|
||||
remove_id:
|
||||
err = virSaveLastError();
|
||||
@@ -1299,7 +1276,7 @@ virPCIDeviceBindToStub(virPCIDevicePtr d
|
||||
"cannot be probed again.", dev->id, stubDriverName);
|
||||
}
|
||||
dev->reprobe = false;
|
||||
- result = -1;
|
||||
+ ret = -1;
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
@@ -1314,10 +1291,142 @@ virPCIDeviceBindToStub(virPCIDevicePtr d
|
||||
"cannot be probed again.", dev->id, stubDriverName);
|
||||
}
|
||||
dev->reprobe = false;
|
||||
- result = -1;
|
||||
+ ret = -1;
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
+ cleanup:
|
||||
+ VIR_FREE(path);
|
||||
+
|
||||
+ if (err)
|
||||
+ virSetError(err);
|
||||
+ virFreeError(err);
|
||||
+
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static int
|
||||
+virPCIDeviceBindToStubWithOverride(virPCIDevicePtr dev,
|
||||
+ const char *stubDriverName)
|
||||
+{
|
||||
+ int ret = -1;
|
||||
+ char *path = NULL;
|
||||
+
|
||||
+ /*
|
||||
+ * Add stub to the device's driver_override, falling back to
|
||||
+ * adding the device ID to the stub's dynamic ID table.
|
||||
+ */
|
||||
+ if (!(path = virPCIFile(dev->name, "driver_override")))
|
||||
+ return -1;
|
||||
+
|
||||
+ if (virFileWriteStr(path, stubDriverName, 0) < 0) {
|
||||
+ virReportSystemError(errno,
|
||||
+ _("Failed to add stub driver '%s' to "
|
||||
+ "driver_override interface of PCI device '%s'"),
|
||||
+ stubDriverName, dev->name);
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
+ if (virPCIDeviceUnbind(dev) < 0)
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ /* Xen's pciback.ko wants you to use new_slot first */
|
||||
+ VIR_FREE(path);
|
||||
+ if (!(path = virPCIDriverFile(stubDriverName, "new_slot")))
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ if (virFileExists(path) && virFileWriteStr(path, dev->name, 0) < 0) {
|
||||
+ virReportSystemError(errno,
|
||||
+ _("Failed to add slot for "
|
||||
+ "PCI device '%s' to %s"),
|
||||
+ dev->name, stubDriverName);
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+ dev->remove_slot = true;
|
||||
+
|
||||
+ if (virFileWriteStr(PCI_SYSFS "drivers_probe", dev->name, 0) < 0) {
|
||||
+ virReportSystemError(errno,
|
||||
+ _("Failed to trigger a re-probe for PCI device '%s'"),
|
||||
+ dev->name);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
+ /*
|
||||
+ * Device is now bound to the stub. Set reprobe so it will be re-bound
|
||||
+ * when unbinding from the stub.
|
||||
+ */
|
||||
+ dev->reprobe = true;
|
||||
+ dev->unbind_from_stub = true;
|
||||
+
|
||||
+ ret = 0;
|
||||
+
|
||||
+ cleanup:
|
||||
+ VIR_FREE(path);
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static int
|
||||
+virPCIDeviceBindToStub(virPCIDevicePtr dev)
|
||||
+{
|
||||
+ int result = -1;
|
||||
+ char *stubDriverPath = NULL;
|
||||
+ char *driverLink = NULL;
|
||||
+ char *path = NULL; /* reused for different purposes */
|
||||
+ const char *stubDriverName = NULL;
|
||||
+
|
||||
+ /* Check the device is configured to use one of the known stub drivers */
|
||||
+ if (dev->stubDriver == VIR_PCI_STUB_DRIVER_NONE) {
|
||||
+ virReportError(VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("No stub driver configured for PCI device %s"),
|
||||
+ dev->name);
|
||||
+ return -1;
|
||||
+ } else if (!(stubDriverName = virPCIStubDriverTypeToString(dev->stubDriver))) {
|
||||
+ virReportError(VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Unknown stub driver configured for PCI device %s"),
|
||||
+ dev->name);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ if (!(stubDriverPath = virPCIDriverDir(stubDriverName)) ||
|
||||
+ !(driverLink = virPCIFile(dev->name, "driver")))
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ if (virFileExists(driverLink)) {
|
||||
+ if (virFileLinkPointsTo(driverLink, stubDriverPath)) {
|
||||
+ /* The device is already bound to the correct driver */
|
||||
+ VIR_DEBUG("Device %s is already bound to %s",
|
||||
+ dev->name, stubDriverName);
|
||||
+ dev->unbind_from_stub = true;
|
||||
+ dev->remove_slot = true;
|
||||
+ result = 0;
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+ /*
|
||||
+ * If the device is bound to a driver that is not the stub, we'll
|
||||
+ * need to reprobe later
|
||||
+ */
|
||||
+ dev->reprobe = true;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
+ * Add stub to the device's driver_override, falling back to
|
||||
+ * adding the device ID to the stub's dynamic ID table.
|
||||
+ */
|
||||
+ if (!(path = virPCIFile(dev->name, "driver_override")))
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ if (virFileExists(path)) {
|
||||
+ if (virPCIDeviceBindToStubWithOverride(dev, stubDriverName) < 0)
|
||||
+ goto cleanup;
|
||||
+ } else {
|
||||
+ if (virPCIDeviceBindToStubWithNewid(dev, stubDriverName) < 0)
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
+ result = 0;
|
||||
+
|
||||
cleanup:
|
||||
VIR_FREE(stubDriverPath);
|
||||
VIR_FREE(driverLink);
|
||||
@@ -1326,10 +1435,6 @@ virPCIDeviceBindToStub(virPCIDevicePtr d
|
||||
if (result < 0)
|
||||
virPCIDeviceUnbindFromStub(dev);
|
||||
|
||||
- if (err)
|
||||
- virSetError(err);
|
||||
- virFreeError(err);
|
||||
-
|
||||
return result;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user