Rebased to version 1.2.13.2
disk backend is not removed properly when disk frontent hotplug fails (bz #1265968) Fix TPM cancel path on newer kernels (bz #1244895) Remove timeout for libvirt-guests.service (bz #1195544) CVE-2015-5313 libvirt: filesystem storage volume names path traversal flaw (bz #1291433) Fix VM names with non-ascii (bz #1062943) Fix backwards migration with graphics listen address (bz #1276883)remotes/origin/f22
parent
1b23098699
commit
43c932192d
|
@ -1,40 +0,0 @@
|
||||||
From: Eric Blake <eblake@redhat.com>
|
|
||||||
Date: Tue, 14 Apr 2015 13:53:04 -0600
|
|
||||||
Subject: [PATCH] build: provide virNetDevSysfsFile on non-Linux
|
|
||||||
|
|
||||||
Commit 49ed6cff is broken on mingw and other non-linux platforms:
|
|
||||||
|
|
||||||
CCLD libvirt.la
|
|
||||||
Cannot export virNetDevSysfsFile: symbol not defined
|
|
||||||
collect2: error: ld returned 1 exit status
|
|
||||||
|
|
||||||
* src/util/virnetdev.c: Provide virNetDevSysfsFile fallback.
|
|
||||||
|
|
||||||
Signed-off-by: Eric Blake <eblake@redhat.com>
|
|
||||||
(cherry picked from commit 58dfc5341432e5b510c441457a524b9d818ad63c)
|
|
||||||
---
|
|
||||||
src/util/virnetdev.c | 11 +++++++++++
|
|
||||||
1 file changed, 11 insertions(+)
|
|
||||||
|
|
||||||
diff --git a/src/util/virnetdev.c b/src/util/virnetdev.c
|
|
||||||
index 309fbb8..ebb4c5c 100644
|
|
||||||
--- a/src/util/virnetdev.c
|
|
||||||
+++ b/src/util/virnetdev.c
|
|
||||||
@@ -1777,6 +1777,17 @@ virNetDevGetVirtualFunctionInfo(const char *vfname ATTRIBUTE_UNUSED,
|
|
||||||
_("Unable to get virtual function info on this platform"));
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
+
|
|
||||||
+int
|
|
||||||
+virNetDevSysfsFile(char **pf_sysfs_device_link ATTRIBUTE_UNUSED,
|
|
||||||
+ const char *ifname ATTRIBUTE_UNUSED,
|
|
||||||
+ const char *file ATTRIBUTE_UNUSED)
|
|
||||||
+{
|
|
||||||
+ virReportSystemError(ENOSYS, "%s",
|
|
||||||
+ _("Unable to get sysfs info on this platform"));
|
|
||||||
+ return -1;
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
#endif /* !__linux__ */
|
|
||||||
#if defined(__linux__) && defined(HAVE_LIBNL) && defined(IFLA_VF_MAX)
|
|
||||||
|
|
|
@ -79,10 +79,10 @@ index 0000000..01a15fa
|
||||||
+ }
|
+ }
|
||||||
+});
|
+});
|
||||||
diff --git a/libvirt.spec.in b/libvirt.spec.in
|
diff --git a/libvirt.spec.in b/libvirt.spec.in
|
||||||
index f25b710..766bd08 100644
|
index dc327a2..a23629d 100644
|
||||||
--- a/libvirt.spec.in
|
--- a/libvirt.spec.in
|
||||||
+++ b/libvirt.spec.in
|
+++ b/libvirt.spec.in
|
||||||
@@ -1628,9 +1628,9 @@ then
|
@@ -1631,9 +1631,9 @@ then
|
||||||
fi
|
fi
|
||||||
|
|
||||||
%if %{with_libvirtd}
|
%if %{with_libvirtd}
|
||||||
|
@ -93,7 +93,7 @@ index f25b710..766bd08 100644
|
||||||
%if 0%{?fedora} || 0%{?rhel} >= 6
|
%if 0%{?fedora} || 0%{?rhel} >= 6
|
||||||
# We want soft static allocation of well-known ids, as disk images
|
# We want soft static allocation of well-known ids, as disk images
|
||||||
# are commonly shared across NFS mounts by id rather than name; see
|
# are commonly shared across NFS mounts by id rather than name; see
|
||||||
@@ -1644,11 +1644,21 @@ if ! getent passwd qemu >/dev/null; then
|
@@ -1647,11 +1647,21 @@ if ! getent passwd qemu >/dev/null; then
|
||||||
useradd -r -g qemu -G kvm -d / -s /sbin/nologin -c "qemu user" qemu
|
useradd -r -g qemu -G kvm -d / -s /sbin/nologin -c "qemu user" qemu
|
||||||
fi
|
fi
|
||||||
fi
|
fi
|
||||||
|
@ -116,7 +116,7 @@ index f25b710..766bd08 100644
|
||||||
%post daemon
|
%post daemon
|
||||||
|
|
||||||
%if %{with_systemd}
|
%if %{with_systemd}
|
||||||
@@ -1922,6 +1932,7 @@ exit 0
|
@@ -1925,6 +1935,7 @@ exit 0
|
||||||
%if 0%{?fedora} || 0%{?rhel} >= 6
|
%if 0%{?fedora} || 0%{?rhel} >= 6
|
||||||
%{_datadir}/polkit-1/actions/org.libvirt.unix.policy
|
%{_datadir}/polkit-1/actions/org.libvirt.unix.policy
|
||||||
%{_datadir}/polkit-1/actions/org.libvirt.api.policy
|
%{_datadir}/polkit-1/actions/org.libvirt.api.policy
|
|
@ -1,310 +0,0 @@
|
||||||
From: Michal Privoznik <mprivozn@redhat.com>
|
|
||||||
Date: Wed, 11 Jun 2014 15:05:00 +0200
|
|
||||||
Subject: [PATCH] Introduce virnetdevtest
|
|
||||||
|
|
||||||
This is yet another test for check of basic functionality of our
|
|
||||||
NIC state handling code.
|
|
||||||
|
|
||||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
|
||||||
(cherry picked from commit 49ed6cff997bb893dafc805c868c9e772a04696d)
|
|
||||||
---
|
|
||||||
src/libvirt_private.syms | 1 +
|
|
||||||
src/util/virnetdev.c | 4 +-
|
|
||||||
src/util/virnetdev.h | 5 ++
|
|
||||||
tests/Makefile.am | 15 ++++
|
|
||||||
tests/virnetdevmock.c | 48 +++++++++++
|
|
||||||
tests/virnetdevtest.c | 94 ++++++++++++++++++++++
|
|
||||||
.../sys/class/net/eth0-broken/operstate | 1 +
|
|
||||||
.../sys/class/net/eth0-broken/speed | 1 +
|
|
||||||
.../virnetdevtestdata/sys/class/net/eth0/operstate | 1 +
|
|
||||||
tests/virnetdevtestdata/sys/class/net/eth0/speed | 1 +
|
|
||||||
tests/virnetdevtestdata/sys/class/net/lo/operstate | 1 +
|
|
||||||
tests/virnetdevtestdata/sys/class/net/lo/speed | 1 +
|
|
||||||
12 files changed, 171 insertions(+), 2 deletions(-)
|
|
||||||
create mode 100644 tests/virnetdevmock.c
|
|
||||||
create mode 100644 tests/virnetdevtest.c
|
|
||||||
create mode 100644 tests/virnetdevtestdata/sys/class/net/eth0-broken/operstate
|
|
||||||
create mode 100644 tests/virnetdevtestdata/sys/class/net/eth0-broken/speed
|
|
||||||
create mode 100644 tests/virnetdevtestdata/sys/class/net/eth0/operstate
|
|
||||||
create mode 100644 tests/virnetdevtestdata/sys/class/net/eth0/speed
|
|
||||||
create mode 100644 tests/virnetdevtestdata/sys/class/net/lo/operstate
|
|
||||||
create mode 100644 tests/virnetdevtestdata/sys/class/net/lo/speed
|
|
||||||
|
|
||||||
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
|
|
||||||
index 8653727..9cda39c 100644
|
|
||||||
--- a/src/libvirt_private.syms
|
|
||||||
+++ b/src/libvirt_private.syms
|
|
||||||
@@ -1702,6 +1702,7 @@ virNetDevSetPromiscuous;
|
|
||||||
virNetDevSetRcvAllMulti;
|
|
||||||
virNetDevSetRcvMulti;
|
|
||||||
virNetDevSetupControl;
|
|
||||||
+virNetDevSysfsFile;
|
|
||||||
virNetDevValidateConfig;
|
|
||||||
|
|
||||||
|
|
||||||
diff --git a/src/util/virnetdev.c b/src/util/virnetdev.c
|
|
||||||
index ebb4c5c..c196d98 100644
|
|
||||||
--- a/src/util/virnetdev.c
|
|
||||||
+++ b/src/util/virnetdev.c
|
|
||||||
@@ -1514,9 +1514,9 @@ int virNetDevValidateConfig(const char *ifname ATTRIBUTE_UNUSED,
|
|
||||||
#ifdef __linux__
|
|
||||||
# define NET_SYSFS "/sys/class/net/"
|
|
||||||
|
|
||||||
-static int
|
|
||||||
+int
|
|
||||||
virNetDevSysfsFile(char **pf_sysfs_device_link, const char *ifname,
|
|
||||||
- const char *file)
|
|
||||||
+ const char *file)
|
|
||||||
{
|
|
||||||
|
|
||||||
if (virAsprintf(pf_sysfs_device_link, NET_SYSFS "%s/%s", ifname, file) < 0)
|
|
||||||
diff --git a/src/util/virnetdev.h b/src/util/virnetdev.h
|
|
||||||
index 0c0f666..d692f94 100644
|
|
||||||
--- a/src/util/virnetdev.h
|
|
||||||
+++ b/src/util/virnetdev.h
|
|
||||||
@@ -203,4 +203,9 @@ int virNetDevSetRcvAllMulti(const char *ifname, bool receive)
|
|
||||||
ATTRIBUTE_NONNULL(1) ATTRIBUTE_RETURN_CHECK;
|
|
||||||
int virNetDevGetRcvAllMulti(const char *ifname, bool *receive)
|
|
||||||
ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2) ATTRIBUTE_RETURN_CHECK;
|
|
||||||
+int virNetDevSysfsFile(char **pf_sysfs_device_link,
|
|
||||||
+ const char *ifname,
|
|
||||||
+ const char *file)
|
|
||||||
+ ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2) ATTRIBUTE_NONNULL(3)
|
|
||||||
+ ATTRIBUTE_RETURN_CHECK;
|
|
||||||
#endif /* __VIR_NETDEV_H__ */
|
|
||||||
diff --git a/tests/Makefile.am b/tests/Makefile.am
|
|
||||||
index 938270c..2dd0088 100644
|
|
||||||
--- a/tests/Makefile.am
|
|
||||||
+++ b/tests/Makefile.am
|
|
||||||
@@ -175,6 +175,7 @@ test_programs = virshtest sockettest \
|
|
||||||
domainconftest \
|
|
||||||
virhostdevtest \
|
|
||||||
vircaps2xmltest \
|
|
||||||
+ virnetdevtest \
|
|
||||||
$(NULL)
|
|
||||||
|
|
||||||
if WITH_REMOTE
|
|
||||||
@@ -401,6 +402,7 @@ test_libraries = libshunload.la \
|
|
||||||
virnetserverclientmock.la \
|
|
||||||
vircgroupmock.la \
|
|
||||||
virpcimock.la \
|
|
||||||
+ virnetdevmock.la \
|
|
||||||
$(NULL)
|
|
||||||
if WITH_QEMU
|
|
||||||
test_libraries += libqemumonitortestutils.la \
|
|
||||||
@@ -1017,6 +1019,19 @@ virpcimock_la_LIBADD = $(GNULIB_LIBS) \
|
|
||||||
virpcimock_la_LDFLAGS = -module -avoid-version \
|
|
||||||
-rpath /evil/libtool/hack/to/force/shared/lib/creation
|
|
||||||
|
|
||||||
+virnetdevtest_SOURCES = \
|
|
||||||
+ virnetdevtest.c testutils.h testutils.c
|
|
||||||
+virnetdevtest_CFLAGS = $(AM_CFLAGS) $(LIBNL_CFLAGS)
|
|
||||||
+virnetdevtest_LDADD = $(LDADDS)
|
|
||||||
+
|
|
||||||
+virnetdevmock_la_SOURCES = \
|
|
||||||
+ virnetdevmock.c
|
|
||||||
+virnetdevmock_la_CFLAGS = $(AM_CFLAGS) $(LIBNL_CFLAGS)
|
|
||||||
+virnetdevmock_la_LIBADD = $(GNULIB_LIBS) \
|
|
||||||
+ ../src/libvirt.la
|
|
||||||
+virnetdevmock_la_LDFLAGS = -module -avoid-version \
|
|
||||||
+ -rpath /evil/libtool/hack/to/force/shared/lib/creation
|
|
||||||
+
|
|
||||||
if WITH_LINUX
|
|
||||||
virusbtest_SOURCES = \
|
|
||||||
virusbtest.c testutils.h testutils.c
|
|
||||||
diff --git a/tests/virnetdevmock.c b/tests/virnetdevmock.c
|
|
||||||
new file mode 100644
|
|
||||||
index 0000000..a9967b7
|
|
||||||
--- /dev/null
|
|
||||||
+++ b/tests/virnetdevmock.c
|
|
||||||
@@ -0,0 +1,48 @@
|
|
||||||
+/*
|
|
||||||
+ * Copyright (C) 2015 Red Hat, Inc.
|
|
||||||
+ *
|
|
||||||
+ * This library is free software; you can redistribute it and/or
|
|
||||||
+ * modify it under the terms of the GNU Lesser General Public
|
|
||||||
+ * License as published by the Free Software Foundation; either
|
|
||||||
+ * version 2.1 of the License, or (at your option) any later version.
|
|
||||||
+ *
|
|
||||||
+ * This library is distributed in the hope that it will be useful,
|
|
||||||
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
+ * Lesser General Public License for more details.
|
|
||||||
+ *
|
|
||||||
+ * You should have received a copy of the GNU Lesser General Public
|
|
||||||
+ * License along with this library. If not, see
|
|
||||||
+ * <http://www.gnu.org/licenses/>.
|
|
||||||
+ *
|
|
||||||
+ * Author: Michal Privoznik <mprivozn@redhat.com>
|
|
||||||
+ */
|
|
||||||
+
|
|
||||||
+#include <config.h>
|
|
||||||
+
|
|
||||||
+#ifdef __linux__
|
|
||||||
+# include "internal.h"
|
|
||||||
+# include <stdlib.h>
|
|
||||||
+# include <stdio.h>
|
|
||||||
+# include "virstring.h"
|
|
||||||
+# include "virnetdev.h"
|
|
||||||
+
|
|
||||||
+# define NET_DEV_TEST_DATA_PREFIX abs_srcdir "/virnetdevtestdata/sys/class/net"
|
|
||||||
+
|
|
||||||
+int
|
|
||||||
+virNetDevSysfsFile(char **pf_sysfs_device_link,
|
|
||||||
+ const char *ifname,
|
|
||||||
+ const char *file)
|
|
||||||
+{
|
|
||||||
+
|
|
||||||
+ if (virAsprintfQuiet(pf_sysfs_device_link, "%s/%s/%s",
|
|
||||||
+ NET_DEV_TEST_DATA_PREFIX, ifname, file) < 0) {
|
|
||||||
+ fprintf(stderr, "Out of memory\n");
|
|
||||||
+ abort();
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ return 0;
|
|
||||||
+}
|
|
||||||
+#else
|
|
||||||
+/* Nothing to override on non-__linux__ platforms */
|
|
||||||
+#endif
|
|
||||||
diff --git a/tests/virnetdevtest.c b/tests/virnetdevtest.c
|
|
||||||
new file mode 100644
|
|
||||||
index 0000000..c31543e
|
|
||||||
--- /dev/null
|
|
||||||
+++ b/tests/virnetdevtest.c
|
|
||||||
@@ -0,0 +1,94 @@
|
|
||||||
+/*
|
|
||||||
+ * Copyright (C) 2015 Red Hat, Inc.
|
|
||||||
+ *
|
|
||||||
+ * This library is free software; you can redistribute it and/or
|
|
||||||
+ * modify it under the terms of the GNU Lesser General Public
|
|
||||||
+ * License as published by the Free Software Foundation; either
|
|
||||||
+ * version 2.1 of the License, or (at your option) any later version.
|
|
||||||
+ *
|
|
||||||
+ * This library is distributed in the hope that it will be useful,
|
|
||||||
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
+ * Lesser General Public License for more details.
|
|
||||||
+ *
|
|
||||||
+ * You should have received a copy of the GNU Lesser General Public
|
|
||||||
+ * License along with this library. If not, see
|
|
||||||
+ * <http://www.gnu.org/licenses/>.
|
|
||||||
+ *
|
|
||||||
+ * Author: Michal Privoznik <mprivozn@redhat.com>
|
|
||||||
+ */
|
|
||||||
+
|
|
||||||
+#include <config.h>
|
|
||||||
+
|
|
||||||
+#include "testutils.h"
|
|
||||||
+
|
|
||||||
+#ifdef __linux__
|
|
||||||
+
|
|
||||||
+# include "virnetdev.h"
|
|
||||||
+
|
|
||||||
+# define VIR_FROM_THIS VIR_FROM_NONE
|
|
||||||
+
|
|
||||||
+struct testVirNetDevGetLinkInfoData {
|
|
||||||
+ const char *ifname; /* ifname to get info on */
|
|
||||||
+ virInterfaceState state; /* expected state */
|
|
||||||
+ unsigned int speed; /* expected speed */
|
|
||||||
+};
|
|
||||||
+
|
|
||||||
+static int
|
|
||||||
+testVirNetDevGetLinkInfo(const void *opaque)
|
|
||||||
+{
|
|
||||||
+ int ret = -1;
|
|
||||||
+ const struct testVirNetDevGetLinkInfoData *data = opaque;
|
|
||||||
+ virInterfaceLink lnk;
|
|
||||||
+
|
|
||||||
+ if (virNetDevGetLinkInfo(data->ifname, &lnk) < 0)
|
|
||||||
+ goto cleanup;
|
|
||||||
+
|
|
||||||
+ if (lnk.state != data->state) {
|
|
||||||
+ fprintf(stderr,
|
|
||||||
+ "Fetched link state (%s) doesn't match the expected one (%s)",
|
|
||||||
+ virInterfaceStateTypeToString(lnk.state),
|
|
||||||
+ virInterfaceStateTypeToString(data->state));
|
|
||||||
+ goto cleanup;
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ if (lnk.speed != data->speed) {
|
|
||||||
+ fprintf(stderr,
|
|
||||||
+ "Fetched link speed (%u) doesn't match the expected one (%u)",
|
|
||||||
+ lnk.speed, data->speed);
|
|
||||||
+ goto cleanup;
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ ret = 0;
|
|
||||||
+ cleanup:
|
|
||||||
+ return ret;
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+static int
|
|
||||||
+mymain(void)
|
|
||||||
+{
|
|
||||||
+ int ret = 0;
|
|
||||||
+
|
|
||||||
+# define DO_TEST_LINK(ifname, state, speed) \
|
|
||||||
+ do { \
|
|
||||||
+ struct testVirNetDevGetLinkInfoData data = {ifname, state, speed}; \
|
|
||||||
+ if (virtTestRun("Link info: " # ifname, \
|
|
||||||
+ testVirNetDevGetLinkInfo, &data) < 0) \
|
|
||||||
+ ret = -1; \
|
|
||||||
+ } while (0)
|
|
||||||
+
|
|
||||||
+ DO_TEST_LINK("eth0", VIR_INTERFACE_STATE_UP, 1000);
|
|
||||||
+ DO_TEST_LINK("lo", VIR_INTERFACE_STATE_UNKNOWN, 0);
|
|
||||||
+ DO_TEST_LINK("eth0-broken", VIR_INTERFACE_STATE_DOWN, 0);
|
|
||||||
+
|
|
||||||
+ return ret == 0 ? EXIT_SUCCESS : EXIT_FAILURE;
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+VIRT_TEST_MAIN_PRELOAD(mymain, abs_builddir "/.libs/virnetdevmock.so")
|
|
||||||
+#else
|
|
||||||
+int
|
|
||||||
+main(void)
|
|
||||||
+{
|
|
||||||
+ return EXIT_AM_SKIP;
|
|
||||||
+}
|
|
||||||
+#endif
|
|
||||||
diff --git a/tests/virnetdevtestdata/sys/class/net/eth0-broken/operstate b/tests/virnetdevtestdata/sys/class/net/eth0-broken/operstate
|
|
||||||
new file mode 100644
|
|
||||||
index 0000000..eb0e904
|
|
||||||
--- /dev/null
|
|
||||||
+++ b/tests/virnetdevtestdata/sys/class/net/eth0-broken/operstate
|
|
||||||
@@ -0,0 +1 @@
|
|
||||||
+down
|
|
||||||
diff --git a/tests/virnetdevtestdata/sys/class/net/eth0-broken/speed b/tests/virnetdevtestdata/sys/class/net/eth0-broken/speed
|
|
||||||
new file mode 100644
|
|
||||||
index 0000000..4f6ff86
|
|
||||||
--- /dev/null
|
|
||||||
+++ b/tests/virnetdevtestdata/sys/class/net/eth0-broken/speed
|
|
||||||
@@ -0,0 +1 @@
|
|
||||||
+4294967295
|
|
||||||
diff --git a/tests/virnetdevtestdata/sys/class/net/eth0/operstate b/tests/virnetdevtestdata/sys/class/net/eth0/operstate
|
|
||||||
new file mode 100644
|
|
||||||
index 0000000..e31ee94
|
|
||||||
--- /dev/null
|
|
||||||
+++ b/tests/virnetdevtestdata/sys/class/net/eth0/operstate
|
|
||||||
@@ -0,0 +1 @@
|
|
||||||
+up
|
|
||||||
diff --git a/tests/virnetdevtestdata/sys/class/net/eth0/speed b/tests/virnetdevtestdata/sys/class/net/eth0/speed
|
|
||||||
new file mode 100644
|
|
||||||
index 0000000..83b33d2
|
|
||||||
--- /dev/null
|
|
||||||
+++ b/tests/virnetdevtestdata/sys/class/net/eth0/speed
|
|
||||||
@@ -0,0 +1 @@
|
|
||||||
+1000
|
|
||||||
diff --git a/tests/virnetdevtestdata/sys/class/net/lo/operstate b/tests/virnetdevtestdata/sys/class/net/lo/operstate
|
|
||||||
new file mode 100644
|
|
||||||
index 0000000..3546645
|
|
||||||
--- /dev/null
|
|
||||||
+++ b/tests/virnetdevtestdata/sys/class/net/lo/operstate
|
|
||||||
@@ -0,0 +1 @@
|
|
||||||
+unknown
|
|
||||||
diff --git a/tests/virnetdevtestdata/sys/class/net/lo/speed b/tests/virnetdevtestdata/sys/class/net/lo/speed
|
|
||||||
new file mode 100644
|
|
||||||
index 0000000..573541a
|
|
||||||
--- /dev/null
|
|
||||||
+++ b/tests/virnetdevtestdata/sys/class/net/lo/speed
|
|
||||||
@@ -0,0 +1 @@
|
|
||||||
+0
|
|
|
@ -1,265 +0,0 @@
|
||||||
From: Michal Privoznik <mprivozn@redhat.com>
|
|
||||||
Date: Wed, 15 Apr 2015 11:45:47 +0200
|
|
||||||
Subject: [PATCH] Cleanup "/sys/class/net" usage
|
|
||||||
|
|
||||||
Throughout the code, we have several places need to construct a path
|
|
||||||
somewhere in /sys/class/net/... They are not consistent and nearly
|
|
||||||
each code piece invents its own way how to do it. So unify this by:
|
|
||||||
|
|
||||||
1) use virNetDevSysfsFile() wherever possible
|
|
||||||
|
|
||||||
2) At least use common macro SYSFS_NET_DIR declared in virnetdev.h at
|
|
||||||
the rest of places which can't go with 1)
|
|
||||||
|
|
||||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
|
||||||
(cherry picked from commit 96a21e975f4b9d2f66a6aee1a16188837c98f82c)
|
|
||||||
---
|
|
||||||
src/Makefile.am | 4 ++--
|
|
||||||
src/parallels/parallels_network.c | 10 ++++------
|
|
||||||
src/util/virnetdev.c | 5 ++---
|
|
||||||
src/util/virnetdev.h | 2 ++
|
|
||||||
src/util/virnetdevbridge.c | 13 ++++++-------
|
|
||||||
src/util/virnetdevmacvlan.c | 30 +++++++++++++++---------------
|
|
||||||
src/util/virnetdevveth.c | 2 +-
|
|
||||||
7 files changed, 32 insertions(+), 34 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/src/Makefile.am b/src/Makefile.am
|
|
||||||
index c2e1947..a900303 100644
|
|
||||||
--- a/src/Makefile.am
|
|
||||||
+++ b/src/Makefile.am
|
|
||||||
@@ -1381,8 +1381,8 @@ noinst_LTLIBRARIES += libvirt_driver_parallels.la
|
|
||||||
libvirt_la_BUILT_LIBADD += libvirt_driver_parallels.la
|
|
||||||
libvirt_driver_parallels_la_CFLAGS = \
|
|
||||||
-I$(srcdir)/conf $(AM_CFLAGS) \
|
|
||||||
- $(PARALLELS_SDK_CFLAGS)
|
|
||||||
-libvirt_driver_parallels_la_LIBADD = $(PARALLELS_SDK_LIBS)
|
|
||||||
+ $(PARALLELS_SDK_CFLAGS) $(LIBNL_CFLAGS)
|
|
||||||
+libvirt_driver_parallels_la_LIBADD = $(PARALLELS_SDK_LIBS) $(LIBNL_LIBS)
|
|
||||||
libvirt_driver_parallels_la_SOURCES = $(PARALLELS_DRIVER_SOURCES)
|
|
||||||
endif WITH_PARALLELS
|
|
||||||
|
|
||||||
diff --git a/src/parallels/parallels_network.c b/src/parallels/parallels_network.c
|
|
||||||
index 3e7087d..b4ae737 100644
|
|
||||||
--- a/src/parallels/parallels_network.c
|
|
||||||
+++ b/src/parallels/parallels_network.c
|
|
||||||
@@ -28,6 +28,7 @@
|
|
||||||
#include "viralloc.h"
|
|
||||||
#include "virerror.h"
|
|
||||||
#include "virfile.h"
|
|
||||||
+#include "virnetdev.h"
|
|
||||||
#include "md5.h"
|
|
||||||
#include "parallels_utils.h"
|
|
||||||
#include "virstring.h"
|
|
||||||
@@ -39,8 +40,6 @@
|
|
||||||
virReportErrorHelper(VIR_FROM_TEST, VIR_ERR_OPERATION_FAILED, __FILE__, \
|
|
||||||
__FUNCTION__, __LINE__, _("Can't parse prlctl output"))
|
|
||||||
|
|
||||||
-#define SYSFS_NET_DIR "/sys/class/net"
|
|
||||||
-
|
|
||||||
static int parallelsGetBridgedNetInfo(virNetworkDefPtr def, virJSONValuePtr jobj)
|
|
||||||
{
|
|
||||||
const char *ifname;
|
|
||||||
@@ -56,8 +55,7 @@ static int parallelsGetBridgedNetInfo(virNetworkDefPtr def, virJSONValuePtr jobj
|
|
||||||
goto cleanup;
|
|
||||||
}
|
|
||||||
|
|
||||||
- if (virAsprintf(&bridgeLink, "%s/%s/brport/bridge",
|
|
||||||
- SYSFS_NET_DIR, ifname) < 0)
|
|
||||||
+ if (virAsprintf(&bridgeLink, SYSFS_NET_DIR "%s/brport/bridge", ifname) < 0)
|
|
||||||
goto cleanup;
|
|
||||||
|
|
||||||
if (virFileResolveLink(bridgeLink, &bridgePath) < 0) {
|
|
||||||
@@ -68,8 +66,8 @@ static int parallelsGetBridgedNetInfo(virNetworkDefPtr def, virJSONValuePtr jobj
|
|
||||||
if (VIR_STRDUP(def->bridge, last_component(bridgePath)) < 0)
|
|
||||||
goto cleanup;
|
|
||||||
|
|
||||||
- if (virAsprintf(&bridgeAddressPath, "%s/%s/brport/bridge/address",
|
|
||||||
- SYSFS_NET_DIR, ifname) < 0)
|
|
||||||
+ if (virAsprintf(&bridgeAddressPath, SYSFS_NET_DIR "%s/brport/bridge/address",
|
|
||||||
+ ifname) < 0)
|
|
||||||
goto cleanup;
|
|
||||||
|
|
||||||
if ((len = virFileReadAll(bridgeAddressPath, 18, &bridgeAddress)) < 0) {
|
|
||||||
diff --git a/src/util/virnetdev.c b/src/util/virnetdev.c
|
|
||||||
index c196d98..93f6715 100644
|
|
||||||
--- a/src/util/virnetdev.c
|
|
||||||
+++ b/src/util/virnetdev.c
|
|
||||||
@@ -1512,14 +1512,13 @@ int virNetDevValidateConfig(const char *ifname ATTRIBUTE_UNUSED,
|
|
||||||
|
|
||||||
|
|
||||||
#ifdef __linux__
|
|
||||||
-# define NET_SYSFS "/sys/class/net/"
|
|
||||||
|
|
||||||
int
|
|
||||||
virNetDevSysfsFile(char **pf_sysfs_device_link, const char *ifname,
|
|
||||||
const char *file)
|
|
||||||
{
|
|
||||||
|
|
||||||
- if (virAsprintf(pf_sysfs_device_link, NET_SYSFS "%s/%s", ifname, file) < 0)
|
|
||||||
+ if (virAsprintf(pf_sysfs_device_link, SYSFS_NET_DIR "%s/%s", ifname, file) < 0)
|
|
||||||
return -1;
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
@@ -1529,7 +1528,7 @@ virNetDevSysfsDeviceFile(char **pf_sysfs_device_link, const char *ifname,
|
|
||||||
const char *file)
|
|
||||||
{
|
|
||||||
|
|
||||||
- if (virAsprintf(pf_sysfs_device_link, NET_SYSFS "%s/device/%s", ifname,
|
|
||||||
+ if (virAsprintf(pf_sysfs_device_link, SYSFS_NET_DIR "%s/device/%s", ifname,
|
|
||||||
file) < 0)
|
|
||||||
return -1;
|
|
||||||
return 0;
|
|
||||||
diff --git a/src/util/virnetdev.h b/src/util/virnetdev.h
|
|
||||||
index d692f94..83868d4 100644
|
|
||||||
--- a/src/util/virnetdev.h
|
|
||||||
+++ b/src/util/virnetdev.h
|
|
||||||
@@ -203,6 +203,8 @@ int virNetDevSetRcvAllMulti(const char *ifname, bool receive)
|
|
||||||
ATTRIBUTE_NONNULL(1) ATTRIBUTE_RETURN_CHECK;
|
|
||||||
int virNetDevGetRcvAllMulti(const char *ifname, bool *receive)
|
|
||||||
ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2) ATTRIBUTE_RETURN_CHECK;
|
|
||||||
+
|
|
||||||
+# define SYSFS_NET_DIR "/sys/class/net/"
|
|
||||||
int virNetDevSysfsFile(char **pf_sysfs_device_link,
|
|
||||||
const char *ifname,
|
|
||||||
const char *file)
|
|
||||||
diff --git a/src/util/virnetdevbridge.c b/src/util/virnetdevbridge.c
|
|
||||||
index d9dcc39..282746b 100644
|
|
||||||
--- a/src/util/virnetdevbridge.c
|
|
||||||
+++ b/src/util/virnetdevbridge.c
|
|
||||||
@@ -114,7 +114,6 @@ static int virNetDevBridgeCmd(const char *brname,
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if defined(HAVE_STRUCT_IFREQ) && defined(__linux__)
|
|
||||||
-# define SYSFS_NET_DIR "/sys/class/net"
|
|
||||||
/*
|
|
||||||
* Bridge parameters can be set via sysfs on newish kernels,
|
|
||||||
* or by ioctl on older kernels. Perhaps we could just use
|
|
||||||
@@ -130,7 +129,7 @@ static int virNetDevBridgeSet(const char *brname,
|
|
||||||
char *path = NULL;
|
|
||||||
int ret = -1;
|
|
||||||
|
|
||||||
- if (virAsprintf(&path, "%s/%s/bridge/%s", SYSFS_NET_DIR, brname, paramname) < 0)
|
|
||||||
+ if (virAsprintf(&path, SYSFS_NET_DIR "%s/bridge/%s", brname, paramname) < 0)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
if (virFileExists(path)) {
|
|
||||||
@@ -177,7 +176,7 @@ static int virNetDevBridgeGet(const char *brname,
|
|
||||||
char *path = NULL;
|
|
||||||
int ret = -1;
|
|
||||||
|
|
||||||
- if (virAsprintf(&path, "%s/%s/bridge/%s", SYSFS_NET_DIR, brname, paramname) < 0)
|
|
||||||
+ if (virAsprintf(&path, SYSFS_NET_DIR "%s/bridge/%s", brname, paramname) < 0)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
if (virFileExists(path)) {
|
|
||||||
@@ -235,8 +234,8 @@ virNetDevBridgePortSet(const char *brname,
|
|
||||||
|
|
||||||
snprintf(valuestr, sizeof(valuestr), "%lu", value);
|
|
||||||
|
|
||||||
- if (virAsprintf(&path, "%s/%s/brif/%s/%s",
|
|
||||||
- SYSFS_NET_DIR, brname, ifname, paramname) < 0)
|
|
||||||
+ if (virAsprintf(&path, SYSFS_NET_DIR "%s/brif/%s/%s",
|
|
||||||
+ brname, ifname, paramname) < 0)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
if (!virFileExists(path))
|
|
||||||
@@ -265,8 +264,8 @@ virNetDevBridgePortGet(const char *brname,
|
|
||||||
char *valuestr = NULL;
|
|
||||||
int ret = -1;
|
|
||||||
|
|
||||||
- if (virAsprintf(&path, "%s/%s/brif/%s/%s",
|
|
||||||
- SYSFS_NET_DIR, brname, ifname, paramname) < 0)
|
|
||||||
+ if (virAsprintf(&path, SYSFS_NET_DIR "%s/brif/%s/%s",
|
|
||||||
+ brname, ifname, paramname) < 0)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
if (virFileReadAll(path, INT_BUFSIZE_BOUND(unsigned long), &valuestr) < 0)
|
|
||||||
diff --git a/src/util/virnetdevmacvlan.c b/src/util/virnetdevmacvlan.c
|
|
||||||
index b5ee2f1..955d90d 100644
|
|
||||||
--- a/src/util/virnetdevmacvlan.c
|
|
||||||
+++ b/src/util/virnetdevmacvlan.c
|
|
||||||
@@ -299,19 +299,15 @@ static
|
|
||||||
int virNetDevMacVLanTapOpen(const char *ifname,
|
|
||||||
int retries)
|
|
||||||
{
|
|
||||||
- FILE *file;
|
|
||||||
- char path[64];
|
|
||||||
+ int ret = -1;
|
|
||||||
+ FILE *file = NULL;
|
|
||||||
+ char *path;
|
|
||||||
int ifindex;
|
|
||||||
char tapname[50];
|
|
||||||
int tapfd;
|
|
||||||
|
|
||||||
- if (snprintf(path, sizeof(path),
|
|
||||||
- "/sys/class/net/%s/ifindex", ifname) >= sizeof(path)) {
|
|
||||||
- virReportSystemError(errno,
|
|
||||||
- "%s",
|
|
||||||
- _("buffer for ifindex path is too small"));
|
|
||||||
+ if (virNetDevSysfsFile(&path, ifname, "ifindex") < 0)
|
|
||||||
return -1;
|
|
||||||
- }
|
|
||||||
|
|
||||||
file = fopen(path, "r");
|
|
||||||
|
|
||||||
@@ -319,15 +315,14 @@ int virNetDevMacVLanTapOpen(const char *ifname,
|
|
||||||
virReportSystemError(errno,
|
|
||||||
_("cannot open macvtap file %s to determine "
|
|
||||||
"interface index"), path);
|
|
||||||
- return -1;
|
|
||||||
+ goto cleanup;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (fscanf(file, "%d", &ifindex) != 1) {
|
|
||||||
virReportSystemError(errno,
|
|
||||||
"%s", _("cannot determine macvtap's tap device "
|
|
||||||
"interface index"));
|
|
||||||
- VIR_FORCE_FCLOSE(file);
|
|
||||||
- return -1;
|
|
||||||
+ goto cleanup;
|
|
||||||
}
|
|
||||||
|
|
||||||
VIR_FORCE_FCLOSE(file);
|
|
||||||
@@ -337,7 +332,7 @@ int virNetDevMacVLanTapOpen(const char *ifname,
|
|
||||||
virReportSystemError(errno,
|
|
||||||
"%s",
|
|
||||||
_("internal buffer for tap device is too small"));
|
|
||||||
- return -1;
|
|
||||||
+ goto cleanup;
|
|
||||||
}
|
|
||||||
|
|
||||||
while (1) {
|
|
||||||
@@ -351,12 +346,17 @@ int virNetDevMacVLanTapOpen(const char *ifname,
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
- if (tapfd < 0)
|
|
||||||
+ if (tapfd < 0) {
|
|
||||||
virReportSystemError(errno,
|
|
||||||
_("cannot open macvtap tap device %s"),
|
|
||||||
tapname);
|
|
||||||
-
|
|
||||||
- return tapfd;
|
|
||||||
+ goto cleanup;
|
|
||||||
+ }
|
|
||||||
+ ret = tapfd;
|
|
||||||
+ cleanup:
|
|
||||||
+ VIR_FREE(path);
|
|
||||||
+ VIR_FORCE_FCLOSE(file);
|
|
||||||
+ return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
diff --git a/src/util/virnetdevveth.c b/src/util/virnetdevveth.c
|
|
||||||
index e9d6f9c..6905168 100644
|
|
||||||
--- a/src/util/virnetdevveth.c
|
|
||||||
+++ b/src/util/virnetdevveth.c
|
|
||||||
@@ -47,7 +47,7 @@ static int virNetDevVethExists(int devNum)
|
|
||||||
{
|
|
||||||
int ret;
|
|
||||||
char *path = NULL;
|
|
||||||
- if (virAsprintf(&path, "/sys/class/net/vnet%d/", devNum) < 0)
|
|
||||||
+ if (virAsprintf(&path, SYSFS_NET_DIR "vnet%d/", devNum) < 0)
|
|
||||||
return -1;
|
|
||||||
ret = virFileExists(path) ? 1 : 0;
|
|
||||||
VIR_DEBUG("Checked dev vnet%d usage: %d", devNum, ret);
|
|
|
@ -1,77 +0,0 @@
|
||||||
From: Lubomir Rintel <lkundrak@v3.sk>
|
|
||||||
Date: Tue, 14 Apr 2015 18:21:44 +0200
|
|
||||||
Subject: [PATCH] lxc: move wireless PHYs to a network namespace
|
|
||||||
|
|
||||||
The 802.11 interfaces can not be moved by themselves, their Phy has to move too.
|
|
||||||
|
|
||||||
If there are other interfaces, they have to move too -- hopefully it's not too
|
|
||||||
confusing. This is a less-invasive alternative to defining a new hostdev type
|
|
||||||
for PHYs.
|
|
||||||
|
|
||||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
|
||||||
(cherry picked from commit 3a495948b97770b026afab1ccaac560a9669a36e)
|
|
||||||
---
|
|
||||||
src/util/virnetdev.c | 39 ++++++++++++++++++++++++++++++++++++---
|
|
||||||
1 file changed, 36 insertions(+), 3 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/src/util/virnetdev.c b/src/util/virnetdev.c
|
|
||||||
index 93f6715..e111a07 100644
|
|
||||||
--- a/src/util/virnetdev.c
|
|
||||||
+++ b/src/util/virnetdev.c
|
|
||||||
@@ -551,20 +551,53 @@ int virNetDevSetMTUFromDevice(const char *ifname,
|
|
||||||
*/
|
|
||||||
int virNetDevSetNamespace(const char *ifname, pid_t pidInNs)
|
|
||||||
{
|
|
||||||
- int rc;
|
|
||||||
+ int ret = -1;
|
|
||||||
char *pid = NULL;
|
|
||||||
+ char *phy = NULL;
|
|
||||||
+ char *phy_path = NULL;
|
|
||||||
+ int len;
|
|
||||||
+
|
|
||||||
const char *argv[] = {
|
|
||||||
"ip", "link", "set", ifname, "netns", NULL, NULL
|
|
||||||
};
|
|
||||||
|
|
||||||
+ const char *iwargv[] = {
|
|
||||||
+ "iw", "phy", NULL, "set", "netns", NULL, NULL
|
|
||||||
+ };
|
|
||||||
+
|
|
||||||
if (virAsprintf(&pid, "%lld", (long long) pidInNs) == -1)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
argv[5] = pid;
|
|
||||||
- rc = virRun(argv, NULL);
|
|
||||||
+ if (virRun(argv, NULL) < 0)
|
|
||||||
+ goto cleanup;
|
|
||||||
+
|
|
||||||
+ /* The 802.11 wireless devices only move together with their PHY. */
|
|
||||||
+ if (virNetDevSysfsFile(&phy_path, ifname, "phy80211/name") < 0)
|
|
||||||
+ goto cleanup;
|
|
||||||
+
|
|
||||||
+ if ((len = virFileReadAllQuiet(phy_path, 1024, &phy) < 0)) {
|
|
||||||
+ if (errno == ENOENT) {
|
|
||||||
+ /* Okay, this is not a wireless card. Claim success. */
|
|
||||||
+ ret = 0;
|
|
||||||
+ }
|
|
||||||
+ goto cleanup;
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ /* Remove a line break. */
|
|
||||||
+ phy[len - 1] = '\0';
|
|
||||||
+
|
|
||||||
+ iwargv[2] = phy;
|
|
||||||
+ iwargv[5] = pid;
|
|
||||||
+ if (virRun(iwargv, NULL) < 0)
|
|
||||||
+ goto cleanup;
|
|
||||||
|
|
||||||
+ ret = 0;
|
|
||||||
+ cleanup:
|
|
||||||
+ VIR_FREE(phy_path);
|
|
||||||
+ VIR_FREE(phy);
|
|
||||||
VIR_FREE(pid);
|
|
||||||
- return rc;
|
|
||||||
+ return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
#if defined(SIOCSIFNAME) && defined(HAVE_STRUCT_IFREQ)
|
|
|
@ -1,27 +0,0 @@
|
||||||
From: Michal Privoznik <mprivozn@redhat.com>
|
|
||||||
Date: Wed, 15 Apr 2015 10:09:52 +0200
|
|
||||||
Subject: [PATCH] tests: Add virnetdevtestdata to EXTRA_DIST
|
|
||||||
|
|
||||||
In one of my previous commits (49ed6cff9) I've introduced a test
|
|
||||||
among with some files stored under virnetdevtestdata folder.
|
|
||||||
While this works perfectly within a git tree, the folder was not
|
|
||||||
getting into .tar.gz and therefore the dist-check would fail.
|
|
||||||
|
|
||||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
|
||||||
(cherry picked from commit 598f3fddbc0a9e9c16bb0554ff1481d3250c7d00)
|
|
||||||
---
|
|
||||||
tests/Makefile.am | 1 +
|
|
||||||
1 file changed, 1 insertion(+)
|
|
||||||
|
|
||||||
diff --git a/tests/Makefile.am b/tests/Makefile.am
|
|
||||||
index 2dd0088..3af12b6 100644
|
|
||||||
--- a/tests/Makefile.am
|
|
||||||
+++ b/tests/Makefile.am
|
|
||||||
@@ -132,6 +132,7 @@ EXTRA_DIST = \
|
|
||||||
vboxsnapshotxmldata \
|
|
||||||
virsh-uriprecedence \
|
|
||||||
virfiledata \
|
|
||||||
+ virnetdevtestdata \
|
|
||||||
virpcitestdata \
|
|
||||||
virscsidata \
|
|
||||||
virusbtestdata \
|
|
|
@ -1,55 +0,0 @@
|
||||||
From: Lubomir Rintel <lkundrak@v3.sk>
|
|
||||||
Date: Fri, 24 Apr 2015 15:52:56 +0200
|
|
||||||
Subject: [PATCH] lxc: don't up the veth interfaces unless explicitly asked to
|
|
||||||
|
|
||||||
Upping an interface for no reason and not configuring it is a cardinal sin.
|
|
||||||
|
|
||||||
With the default addrgenmode if eui64 it sticks a link-local address to the
|
|
||||||
interface. That is not good, as NetworkManager would see an address configured,
|
|
||||||
assume the interface is already configured and won't touch it iself and the
|
|
||||||
interface might stay unconfigured until the end of the days.
|
|
||||||
|
|
||||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1124721
|
|
||||||
|
|
||||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
|
||||||
(cherry picked from commit c3cf3c43a0bb2e0e4909c32821e20f607635ec85)
|
|
||||||
---
|
|
||||||
src/lxc/lxc_container.c | 3 ++-
|
|
||||||
src/lxc/lxc_native.c | 10 ++++------
|
|
||||||
2 files changed, 6 insertions(+), 7 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/src/lxc/lxc_container.c b/src/lxc/lxc_container.c
|
|
||||||
index cc20b6d..9a9ae5c 100644
|
|
||||||
--- a/src/lxc/lxc_container.c
|
|
||||||
+++ b/src/lxc/lxc_container.c
|
|
||||||
@@ -541,7 +541,8 @@ static int lxcContainerRenameAndEnableInterfaces(virDomainDefPtr vmDef,
|
|
||||||
VIR_FREE(ipStr);
|
|
||||||
}
|
|
||||||
|
|
||||||
- if (netDef->linkstate != VIR_DOMAIN_NET_INTERFACE_LINK_STATE_DOWN) {
|
|
||||||
+ if (netDef->nips ||
|
|
||||||
+ netDef->linkstate == VIR_DOMAIN_NET_INTERFACE_LINK_STATE_UP) {
|
|
||||||
VIR_DEBUG("Enabling %s", newname);
|
|
||||||
rc = virNetDevSetOnline(newname, true);
|
|
||||||
if (rc < 0)
|
|
||||||
diff --git a/src/lxc/lxc_native.c b/src/lxc/lxc_native.c
|
|
||||||
index abf07ce..434523a 100644
|
|
||||||
--- a/src/lxc/lxc_native.c
|
|
||||||
+++ b/src/lxc/lxc_native.c
|
|
||||||
@@ -348,12 +348,10 @@ lxcCreateNetDef(const char *type,
|
|
||||||
if (VIR_ALLOC(net) < 0)
|
|
||||||
goto error;
|
|
||||||
|
|
||||||
- if (flag) {
|
|
||||||
- if (STREQ(flag, "up"))
|
|
||||||
- net->linkstate = VIR_DOMAIN_NET_INTERFACE_LINK_STATE_UP;
|
|
||||||
- else
|
|
||||||
- net->linkstate = VIR_DOMAIN_NET_INTERFACE_LINK_STATE_DOWN;
|
|
||||||
- }
|
|
||||||
+ if (STREQ_NULLABLE(flag, "up"))
|
|
||||||
+ net->linkstate = VIR_DOMAIN_NET_INTERFACE_LINK_STATE_UP;
|
|
||||||
+ else
|
|
||||||
+ net->linkstate = VIR_DOMAIN_NET_INTERFACE_LINK_STATE_DOWN;
|
|
||||||
|
|
||||||
if (VIR_STRDUP(net->ifname_guest, name) < 0)
|
|
||||||
goto error;
|
|
|
@ -1,80 +0,0 @@
|
||||||
From: Lubomir Rintel <lkundrak@v3.sk>
|
|
||||||
Date: Wed, 27 May 2015 19:30:50 +0200
|
|
||||||
Subject: [PATCH] interface: don't error out if a bond has no interfaces
|
|
||||||
|
|
||||||
It's not a problem at all and causes virt-manager to break down.
|
|
||||||
|
|
||||||
Note: netcf 0.2.8 and earlier generates invalid XML for a bond with no
|
|
||||||
interfaces anyway, so in that case this error in libvirt is never
|
|
||||||
reached since we fail earlier.
|
|
||||||
|
|
||||||
Signed-off-by: Lubomir Rintel <lkundrak@v3.sk>
|
|
||||||
(cherry picked from commit efc68de5cd70d62b1941a707d22299422f1962f9)
|
|
||||||
---
|
|
||||||
src/conf/interface_conf.c | 29 ++++++++++++-----------------
|
|
||||||
1 file changed, 12 insertions(+), 17 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/src/conf/interface_conf.c b/src/conf/interface_conf.c
|
|
||||||
index c2eb945..26e55cc 100644
|
|
||||||
--- a/src/conf/interface_conf.c
|
|
||||||
+++ b/src/conf/interface_conf.c
|
|
||||||
@@ -1,7 +1,7 @@
|
|
||||||
/*
|
|
||||||
* interface_conf.c: interfaces XML handling
|
|
||||||
*
|
|
||||||
- * Copyright (C) 2006-2010, 2013, 2014 Red Hat, Inc.
|
|
||||||
+ * Copyright (C) 2006-2010, 2013-2015 Red Hat, Inc.
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
@@ -548,39 +548,34 @@ virInterfaceDefParseBondItfs(virInterfaceDefPtr def,
|
|
||||||
virInterfaceDefPtr itf;
|
|
||||||
int nbItf;
|
|
||||||
size_t i;
|
|
||||||
- int ret = 0;
|
|
||||||
+ int ret = -1;
|
|
||||||
|
|
||||||
nbItf = virXPathNodeSet("./interface", ctxt, &interfaces);
|
|
||||||
- if (nbItf < 0) {
|
|
||||||
- ret = -1;
|
|
||||||
- goto error;
|
|
||||||
- }
|
|
||||||
+ if (nbItf < 0)
|
|
||||||
+ goto cleanup;
|
|
||||||
|
|
||||||
if (nbItf == 0) {
|
|
||||||
- virReportError(VIR_ERR_XML_ERROR,
|
|
||||||
- "%s", _("bond has no interfaces"));
|
|
||||||
- ret = -1;
|
|
||||||
- goto error;
|
|
||||||
+ ret = 0;
|
|
||||||
+ goto cleanup;
|
|
||||||
}
|
|
||||||
|
|
||||||
- if (VIR_ALLOC_N(def->data.bond.itf, nbItf) < 0) {
|
|
||||||
- ret = -1;
|
|
||||||
- goto error;
|
|
||||||
- }
|
|
||||||
+ if (VIR_ALLOC_N(def->data.bond.itf, nbItf) < 0)
|
|
||||||
+ goto cleanup;
|
|
||||||
+
|
|
||||||
def->data.bond.nbItf = nbItf;
|
|
||||||
|
|
||||||
for (i = 0; i < nbItf; i++) {
|
|
||||||
ctxt->node = interfaces[i];
|
|
||||||
itf = virInterfaceDefParseXML(ctxt, VIR_INTERFACE_TYPE_BOND);
|
|
||||||
if (itf == NULL) {
|
|
||||||
- ret = -1;
|
|
||||||
def->data.bond.nbItf = i;
|
|
||||||
- goto error;
|
|
||||||
+ goto cleanup;
|
|
||||||
}
|
|
||||||
def->data.bond.itf[i] = itf;
|
|
||||||
}
|
|
||||||
|
|
||||||
- error:
|
|
||||||
+ ret = 0;
|
|
||||||
+ cleanup:
|
|
||||||
VIR_FREE(interfaces);
|
|
||||||
ctxt->node = bond;
|
|
||||||
return ret;
|
|
|
@ -1,88 +0,0 @@
|
||||||
From: Lubomir Rintel <lkundrak@v3.sk>
|
|
||||||
Date: Mon, 1 Jun 2015 20:40:23 +0200
|
|
||||||
Subject: [PATCH] virnetdev: fix moving of 802.11 phys
|
|
||||||
|
|
||||||
There was a couple of problems with the style fixes applied to the original
|
|
||||||
patch:
|
|
||||||
|
|
||||||
1.) virFileReadAllQuiet comparison was incorrectly parenthesized when moved
|
|
||||||
into a condition, causing the len to be set to the result of comparison. This,
|
|
||||||
together with the removed underflow check would underflow the phy buffer.
|
|
||||||
|
|
||||||
2.) The logic was broken. Failure to call "ip" would abort the function, thus
|
|
||||||
the "iw" branch would never be reached.
|
|
||||||
|
|
||||||
This aims to fix the issues and work around possible style complains :)
|
|
||||||
|
|
||||||
Signed-off-by: Lubomir Rintel <lkundrak@v3.sk>
|
|
||||||
(cherry picked from commit 81b19ce46a9a65a00481403b8c0b15a8ac1367f2)
|
|
||||||
---
|
|
||||||
src/util/virnetdev.c | 46 +++++++++++++++++++++-------------------------
|
|
||||||
1 file changed, 21 insertions(+), 25 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/src/util/virnetdev.c b/src/util/virnetdev.c
|
|
||||||
index e111a07..e2c9f9d 100644
|
|
||||||
--- a/src/util/virnetdev.c
|
|
||||||
+++ b/src/util/virnetdev.c
|
|
||||||
@@ -557,40 +557,36 @@ int virNetDevSetNamespace(const char *ifname, pid_t pidInNs)
|
|
||||||
char *phy_path = NULL;
|
|
||||||
int len;
|
|
||||||
|
|
||||||
- const char *argv[] = {
|
|
||||||
- "ip", "link", "set", ifname, "netns", NULL, NULL
|
|
||||||
- };
|
|
||||||
-
|
|
||||||
- const char *iwargv[] = {
|
|
||||||
- "iw", "phy", NULL, "set", "netns", NULL, NULL
|
|
||||||
- };
|
|
||||||
-
|
|
||||||
if (virAsprintf(&pid, "%lld", (long long) pidInNs) == -1)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
- argv[5] = pid;
|
|
||||||
- if (virRun(argv, NULL) < 0)
|
|
||||||
- goto cleanup;
|
|
||||||
-
|
|
||||||
/* The 802.11 wireless devices only move together with their PHY. */
|
|
||||||
if (virNetDevSysfsFile(&phy_path, ifname, "phy80211/name") < 0)
|
|
||||||
goto cleanup;
|
|
||||||
|
|
||||||
- if ((len = virFileReadAllQuiet(phy_path, 1024, &phy) < 0)) {
|
|
||||||
- if (errno == ENOENT) {
|
|
||||||
- /* Okay, this is not a wireless card. Claim success. */
|
|
||||||
- ret = 0;
|
|
||||||
- }
|
|
||||||
- goto cleanup;
|
|
||||||
- }
|
|
||||||
+ if ((len = virFileReadAllQuiet(phy_path, 1024, &phy)) <= 0) {
|
|
||||||
+ /* Not a wireless device. */
|
|
||||||
+ const char *argv[] = {
|
|
||||||
+ "ip", "link", "set", ifname, "netns", NULL, NULL
|
|
||||||
+ };
|
|
||||||
|
|
||||||
- /* Remove a line break. */
|
|
||||||
- phy[len - 1] = '\0';
|
|
||||||
+ argv[5] = pid;
|
|
||||||
+ if (virRun(argv, NULL) < 0)
|
|
||||||
+ goto cleanup;
|
|
||||||
|
|
||||||
- iwargv[2] = phy;
|
|
||||||
- iwargv[5] = pid;
|
|
||||||
- if (virRun(iwargv, NULL) < 0)
|
|
||||||
- goto cleanup;
|
|
||||||
+ } else {
|
|
||||||
+ const char *argv[] = {
|
|
||||||
+ "iw", "phy", NULL, "set", "netns", NULL, NULL
|
|
||||||
+ };
|
|
||||||
+
|
|
||||||
+ /* Remove a line break. */
|
|
||||||
+ phy[len - 1] = '\0';
|
|
||||||
+
|
|
||||||
+ argv[2] = phy;
|
|
||||||
+ argv[5] = pid;
|
|
||||||
+ if (virRun(argv, NULL) < 0)
|
|
||||||
+ goto cleanup;
|
|
||||||
+ }
|
|
||||||
|
|
||||||
ret = 0;
|
|
||||||
cleanup:
|
|
|
@ -1,35 +0,0 @@
|
||||||
From: Peter Krempa <pkrempa@redhat.com>
|
|
||||||
Date: Fri, 13 Mar 2015 16:59:26 +0100
|
|
||||||
Subject: [PATCH] qemu: process: Export qemuProcessFindDomainDiskByAlias
|
|
||||||
|
|
||||||
(cherry picked from commit 5c634730b99b53afd6e2cea4b7d2fc2dfc2ee630)
|
|
||||||
---
|
|
||||||
src/qemu/qemu_process.c | 2 +-
|
|
||||||
src/qemu/qemu_process.h | 3 +++
|
|
||||||
2 files changed, 4 insertions(+), 1 deletion(-)
|
|
||||||
|
|
||||||
diff --git a/src/qemu/qemu_process.c b/src/qemu/qemu_process.c
|
|
||||||
index 46f02b5..1994027 100644
|
|
||||||
--- a/src/qemu/qemu_process.c
|
|
||||||
+++ b/src/qemu/qemu_process.c
|
|
||||||
@@ -390,7 +390,7 @@ qemuProcessFindDomainDiskByPath(virDomainObjPtr vm,
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
-static virDomainDiskDefPtr
|
|
||||||
+virDomainDiskDefPtr
|
|
||||||
qemuProcessFindDomainDiskByAlias(virDomainObjPtr vm,
|
|
||||||
const char *alias)
|
|
||||||
{
|
|
||||||
diff --git a/src/qemu/qemu_process.h b/src/qemu/qemu_process.h
|
|
||||||
index 2e1d393..fffc926 100644
|
|
||||||
--- a/src/qemu/qemu_process.h
|
|
||||||
+++ b/src/qemu/qemu_process.h
|
|
||||||
@@ -107,4 +107,7 @@ int qemuProcessReadLog(int fd, char *buf, int buflen, int off, bool skipchar);
|
|
||||||
int qemuProcessSetSchedParams(int id, pid_t pid, size_t nsp,
|
|
||||||
virDomainThreadSchedParamPtr sp);
|
|
||||||
|
|
||||||
+virDomainDiskDefPtr qemuProcessFindDomainDiskByAlias(virDomainObjPtr vm,
|
|
||||||
+ const char *alias);
|
|
||||||
+
|
|
||||||
#endif /* __QEMU_PROCESS_H__ */
|
|
|
@ -1,351 +0,0 @@
|
||||||
From: Peter Krempa <pkrempa@redhat.com>
|
|
||||||
Date: Fri, 13 Mar 2015 17:00:03 +0100
|
|
||||||
Subject: [PATCH] qemu: event: Don't fiddle with disk backing trees without a
|
|
||||||
job
|
|
||||||
|
|
||||||
Surprisingly we did not grab a VM job when a block job finished and we'd
|
|
||||||
happily rewrite the backing chain data. This made it possible to crash
|
|
||||||
libvirt when queueing two backing chains tightly and other badness.
|
|
||||||
|
|
||||||
To fix it, add yet another handler to the helper thread that handles
|
|
||||||
monitor events that require a job.
|
|
||||||
|
|
||||||
(cherry picked from commit 1a92c719101e5bfa6fe2b78006ad04c7f075ea28)
|
|
||||||
---
|
|
||||||
src/qemu/qemu_domain.h | 2 +
|
|
||||||
src/qemu/qemu_driver.c | 142 ++++++++++++++++++++++++++++++++++++++++++++++++
|
|
||||||
src/qemu/qemu_process.c | 129 ++++++++-----------------------------------
|
|
||||||
3 files changed, 168 insertions(+), 105 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/src/qemu/qemu_domain.h b/src/qemu/qemu_domain.h
|
|
||||||
index fe3e2b1..a7ebb47 100644
|
|
||||||
--- a/src/qemu/qemu_domain.h
|
|
||||||
+++ b/src/qemu/qemu_domain.h
|
|
||||||
@@ -196,6 +196,7 @@ typedef enum {
|
|
||||||
QEMU_PROCESS_EVENT_DEVICE_DELETED,
|
|
||||||
QEMU_PROCESS_EVENT_NIC_RX_FILTER_CHANGED,
|
|
||||||
QEMU_PROCESS_EVENT_SERIAL_CHANGED,
|
|
||||||
+ QEMU_PROCESS_EVENT_BLOCK_JOB,
|
|
||||||
|
|
||||||
QEMU_PROCESS_EVENT_LAST
|
|
||||||
} qemuProcessEventType;
|
|
||||||
@@ -204,6 +205,7 @@ struct qemuProcessEvent {
|
|
||||||
virDomainObjPtr vm;
|
|
||||||
qemuProcessEventType eventType;
|
|
||||||
int action;
|
|
||||||
+ int status;
|
|
||||||
void *data;
|
|
||||||
};
|
|
||||||
|
|
||||||
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
|
|
||||||
index 1009497..2e8c9d8 100644
|
|
||||||
--- a/src/qemu/qemu_driver.c
|
|
||||||
+++ b/src/qemu/qemu_driver.c
|
|
||||||
@@ -4480,6 +4480,141 @@ processSerialChangedEvent(virQEMUDriverPtr driver,
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
+static void
|
|
||||||
+processBlockJobEvent(virQEMUDriverPtr driver,
|
|
||||||
+ virDomainObjPtr vm,
|
|
||||||
+ char *diskAlias,
|
|
||||||
+ int type,
|
|
||||||
+ int status)
|
|
||||||
+{
|
|
||||||
+ virObjectEventPtr event = NULL;
|
|
||||||
+ virObjectEventPtr event2 = NULL;
|
|
||||||
+ const char *path;
|
|
||||||
+ virDomainDiskDefPtr disk;
|
|
||||||
+ virQEMUDriverConfigPtr cfg = virQEMUDriverGetConfig(driver);
|
|
||||||
+ virDomainDiskDefPtr persistDisk = NULL;
|
|
||||||
+ bool save = false;
|
|
||||||
+
|
|
||||||
+ if (qemuDomainObjBeginJob(driver, vm, QEMU_JOB_MODIFY) < 0)
|
|
||||||
+ goto cleanup;
|
|
||||||
+
|
|
||||||
+ if (!virDomainObjIsActive(vm)) {
|
|
||||||
+ VIR_DEBUG("Domain is not running");
|
|
||||||
+ goto endjob;
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ disk = qemuProcessFindDomainDiskByAlias(vm, diskAlias);
|
|
||||||
+
|
|
||||||
+ if (disk) {
|
|
||||||
+ /* Have to generate two variants of the event for old vs. new
|
|
||||||
+ * client callbacks */
|
|
||||||
+ if (type == VIR_DOMAIN_BLOCK_JOB_TYPE_COMMIT &&
|
|
||||||
+ disk->mirrorJob == VIR_DOMAIN_BLOCK_JOB_TYPE_ACTIVE_COMMIT)
|
|
||||||
+ type = disk->mirrorJob;
|
|
||||||
+ path = virDomainDiskGetSource(disk);
|
|
||||||
+ event = virDomainEventBlockJobNewFromObj(vm, path, type, status);
|
|
||||||
+ event2 = virDomainEventBlockJob2NewFromObj(vm, disk->dst, type,
|
|
||||||
+ status);
|
|
||||||
+
|
|
||||||
+ /* If we completed a block pull or commit, then update the XML
|
|
||||||
+ * to match. */
|
|
||||||
+ switch ((virConnectDomainEventBlockJobStatus) status) {
|
|
||||||
+ case VIR_DOMAIN_BLOCK_JOB_COMPLETED:
|
|
||||||
+ if (disk->mirrorState == VIR_DOMAIN_DISK_MIRROR_STATE_PIVOT) {
|
|
||||||
+ if (vm->newDef) {
|
|
||||||
+ int indx = virDomainDiskIndexByName(vm->newDef, disk->dst,
|
|
||||||
+ false);
|
|
||||||
+ virStorageSourcePtr copy = NULL;
|
|
||||||
+
|
|
||||||
+ if (indx >= 0) {
|
|
||||||
+ persistDisk = vm->newDef->disks[indx];
|
|
||||||
+ copy = virStorageSourceCopy(disk->mirror, false);
|
|
||||||
+ if (virStorageSourceInitChainElement(copy,
|
|
||||||
+ persistDisk->src,
|
|
||||||
+ true) < 0) {
|
|
||||||
+ VIR_WARN("Unable to update persistent definition "
|
|
||||||
+ "on vm %s after block job",
|
|
||||||
+ vm->def->name);
|
|
||||||
+ virStorageSourceFree(copy);
|
|
||||||
+ copy = NULL;
|
|
||||||
+ persistDisk = NULL;
|
|
||||||
+ }
|
|
||||||
+ }
|
|
||||||
+ if (copy) {
|
|
||||||
+ virStorageSourceFree(persistDisk->src);
|
|
||||||
+ persistDisk->src = copy;
|
|
||||||
+ }
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ /* XXX We want to revoke security labels and disk
|
|
||||||
+ * lease, as well as audit that revocation, before
|
|
||||||
+ * dropping the original source. But it gets tricky
|
|
||||||
+ * if both source and mirror share common backing
|
|
||||||
+ * files (we want to only revoke the non-shared
|
|
||||||
+ * portion of the chain); so for now, we leak the
|
|
||||||
+ * access to the original. */
|
|
||||||
+ virStorageSourceFree(disk->src);
|
|
||||||
+ disk->src = disk->mirror;
|
|
||||||
+ } else {
|
|
||||||
+ virStorageSourceFree(disk->mirror);
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ /* Recompute the cached backing chain to match our
|
|
||||||
+ * updates. Better would be storing the chain ourselves
|
|
||||||
+ * rather than reprobing, but we haven't quite completed
|
|
||||||
+ * that conversion to use our XML tracking. */
|
|
||||||
+ disk->mirror = NULL;
|
|
||||||
+ save = disk->mirrorState != VIR_DOMAIN_DISK_MIRROR_STATE_NONE;
|
|
||||||
+ disk->mirrorState = VIR_DOMAIN_DISK_MIRROR_STATE_NONE;
|
|
||||||
+ disk->mirrorJob = VIR_DOMAIN_BLOCK_JOB_TYPE_UNKNOWN;
|
|
||||||
+ ignore_value(qemuDomainDetermineDiskChain(driver, vm, disk,
|
|
||||||
+ true, true));
|
|
||||||
+ break;
|
|
||||||
+
|
|
||||||
+ case VIR_DOMAIN_BLOCK_JOB_READY:
|
|
||||||
+ disk->mirrorState = VIR_DOMAIN_DISK_MIRROR_STATE_READY;
|
|
||||||
+ save = true;
|
|
||||||
+ break;
|
|
||||||
+
|
|
||||||
+ case VIR_DOMAIN_BLOCK_JOB_FAILED:
|
|
||||||
+ case VIR_DOMAIN_BLOCK_JOB_CANCELED:
|
|
||||||
+ virStorageSourceFree(disk->mirror);
|
|
||||||
+ disk->mirror = NULL;
|
|
||||||
+ disk->mirrorState = status == VIR_DOMAIN_BLOCK_JOB_FAILED ?
|
|
||||||
+ VIR_DOMAIN_DISK_MIRROR_STATE_ABORT : VIR_DOMAIN_DISK_MIRROR_STATE_NONE;
|
|
||||||
+ disk->mirrorJob = VIR_DOMAIN_BLOCK_JOB_TYPE_UNKNOWN;
|
|
||||||
+ save = true;
|
|
||||||
+ break;
|
|
||||||
+
|
|
||||||
+ case VIR_DOMAIN_BLOCK_JOB_LAST:
|
|
||||||
+ break;
|
|
||||||
+ }
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ if (save) {
|
|
||||||
+ if (virDomainSaveStatus(driver->xmlopt, cfg->stateDir, vm) < 0)
|
|
||||||
+ VIR_WARN("Unable to save status on vm %s after block job",
|
|
||||||
+ vm->def->name);
|
|
||||||
+ if (persistDisk && virDomainSaveConfig(cfg->configDir,
|
|
||||||
+ vm->newDef) < 0)
|
|
||||||
+ VIR_WARN("Unable to update persistent definition on vm %s "
|
|
||||||
+ "after block job", vm->def->name);
|
|
||||||
+ }
|
|
||||||
+ virObjectUnlock(vm);
|
|
||||||
+ virObjectUnref(cfg);
|
|
||||||
+
|
|
||||||
+ if (event)
|
|
||||||
+ qemuDomainEventQueue(driver, event);
|
|
||||||
+ if (event2)
|
|
||||||
+ qemuDomainEventQueue(driver, event2);
|
|
||||||
+
|
|
||||||
+ endjob:
|
|
||||||
+ qemuDomainObjEndJob(driver, vm);
|
|
||||||
+ cleanup:
|
|
||||||
+ VIR_FREE(diskAlias);
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+
|
|
||||||
static void qemuProcessEventHandler(void *data, void *opaque)
|
|
||||||
{
|
|
||||||
struct qemuProcessEvent *processEvent = data;
|
|
||||||
@@ -4506,6 +4641,13 @@ static void qemuProcessEventHandler(void *data, void *opaque)
|
|
||||||
case QEMU_PROCESS_EVENT_SERIAL_CHANGED:
|
|
||||||
processSerialChangedEvent(driver, vm, processEvent->data,
|
|
||||||
processEvent->action);
|
|
||||||
+ break;
|
|
||||||
+ case QEMU_PROCESS_EVENT_BLOCK_JOB:
|
|
||||||
+ processBlockJobEvent(driver, vm,
|
|
||||||
+ processEvent->data,
|
|
||||||
+ processEvent->action,
|
|
||||||
+ processEvent->status);
|
|
||||||
+ break;
|
|
||||||
case QEMU_PROCESS_EVENT_LAST:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
diff --git a/src/qemu/qemu_process.c b/src/qemu/qemu_process.c
|
|
||||||
index 1994027..685cec6 100644
|
|
||||||
--- a/src/qemu/qemu_process.c
|
|
||||||
+++ b/src/qemu/qemu_process.c
|
|
||||||
@@ -1017,123 +1017,42 @@ qemuProcessHandleBlockJob(qemuMonitorPtr mon ATTRIBUTE_UNUSED,
|
|
||||||
void *opaque)
|
|
||||||
{
|
|
||||||
virQEMUDriverPtr driver = opaque;
|
|
||||||
- virObjectEventPtr event = NULL;
|
|
||||||
- virObjectEventPtr event2 = NULL;
|
|
||||||
- const char *path;
|
|
||||||
- virDomainDiskDefPtr disk;
|
|
||||||
- virQEMUDriverConfigPtr cfg = virQEMUDriverGetConfig(driver);
|
|
||||||
- virDomainDiskDefPtr persistDisk = NULL;
|
|
||||||
- bool save = false;
|
|
||||||
+ struct qemuProcessEvent *processEvent = NULL;
|
|
||||||
+ char *data;
|
|
||||||
|
|
||||||
virObjectLock(vm);
|
|
||||||
- disk = qemuProcessFindDomainDiskByAlias(vm, diskAlias);
|
|
||||||
|
|
||||||
- if (disk) {
|
|
||||||
- /* Have to generate two variants of the event for old vs. new
|
|
||||||
- * client callbacks */
|
|
||||||
- if (type == VIR_DOMAIN_BLOCK_JOB_TYPE_COMMIT &&
|
|
||||||
- disk->mirrorJob == VIR_DOMAIN_BLOCK_JOB_TYPE_ACTIVE_COMMIT)
|
|
||||||
- type = disk->mirrorJob;
|
|
||||||
- path = virDomainDiskGetSource(disk);
|
|
||||||
- event = virDomainEventBlockJobNewFromObj(vm, path, type, status);
|
|
||||||
- event2 = virDomainEventBlockJob2NewFromObj(vm, disk->dst, type,
|
|
||||||
- status);
|
|
||||||
-
|
|
||||||
- /* If we completed a block pull or commit, then update the XML
|
|
||||||
- * to match. */
|
|
||||||
- switch ((virConnectDomainEventBlockJobStatus) status) {
|
|
||||||
- case VIR_DOMAIN_BLOCK_JOB_COMPLETED:
|
|
||||||
- if (disk->mirrorState == VIR_DOMAIN_DISK_MIRROR_STATE_PIVOT) {
|
|
||||||
- if (vm->newDef) {
|
|
||||||
- int indx = virDomainDiskIndexByName(vm->newDef, disk->dst,
|
|
||||||
- false);
|
|
||||||
- virStorageSourcePtr copy = NULL;
|
|
||||||
-
|
|
||||||
- if (indx >= 0) {
|
|
||||||
- persistDisk = vm->newDef->disks[indx];
|
|
||||||
- copy = virStorageSourceCopy(disk->mirror, false);
|
|
||||||
- if (virStorageSourceInitChainElement(copy,
|
|
||||||
- persistDisk->src,
|
|
||||||
- true) < 0) {
|
|
||||||
- VIR_WARN("Unable to update persistent definition "
|
|
||||||
- "on vm %s after block job",
|
|
||||||
- vm->def->name);
|
|
||||||
- virStorageSourceFree(copy);
|
|
||||||
- copy = NULL;
|
|
||||||
- persistDisk = NULL;
|
|
||||||
- }
|
|
||||||
- }
|
|
||||||
- if (copy) {
|
|
||||||
- virStorageSourceFree(persistDisk->src);
|
|
||||||
- persistDisk->src = copy;
|
|
||||||
- }
|
|
||||||
- }
|
|
||||||
-
|
|
||||||
- /* XXX We want to revoke security labels and disk
|
|
||||||
- * lease, as well as audit that revocation, before
|
|
||||||
- * dropping the original source. But it gets tricky
|
|
||||||
- * if both source and mirror share common backing
|
|
||||||
- * files (we want to only revoke the non-shared
|
|
||||||
- * portion of the chain); so for now, we leak the
|
|
||||||
- * access to the original. */
|
|
||||||
- virStorageSourceFree(disk->src);
|
|
||||||
- disk->src = disk->mirror;
|
|
||||||
- } else {
|
|
||||||
- virStorageSourceFree(disk->mirror);
|
|
||||||
- }
|
|
||||||
+ VIR_DEBUG("Block job for device %s (domain: %p,%s) type %d status %d",
|
|
||||||
+ diskAlias, vm, vm->def->name, type, status);
|
|
||||||
|
|
||||||
- /* Recompute the cached backing chain to match our
|
|
||||||
- * updates. Better would be storing the chain ourselves
|
|
||||||
- * rather than reprobing, but we haven't quite completed
|
|
||||||
- * that conversion to use our XML tracking. */
|
|
||||||
- disk->mirror = NULL;
|
|
||||||
- save = disk->mirrorState != VIR_DOMAIN_DISK_MIRROR_STATE_NONE;
|
|
||||||
- disk->mirrorState = VIR_DOMAIN_DISK_MIRROR_STATE_NONE;
|
|
||||||
- disk->mirrorJob = VIR_DOMAIN_BLOCK_JOB_TYPE_UNKNOWN;
|
|
||||||
- ignore_value(qemuDomainDetermineDiskChain(driver, vm, disk,
|
|
||||||
- true, true));
|
|
||||||
- break;
|
|
||||||
-
|
|
||||||
- case VIR_DOMAIN_BLOCK_JOB_READY:
|
|
||||||
- disk->mirrorState = VIR_DOMAIN_DISK_MIRROR_STATE_READY;
|
|
||||||
- save = true;
|
|
||||||
- break;
|
|
||||||
+ if (VIR_ALLOC(processEvent) < 0)
|
|
||||||
+ goto error;
|
|
||||||
|
|
||||||
- case VIR_DOMAIN_BLOCK_JOB_FAILED:
|
|
||||||
- case VIR_DOMAIN_BLOCK_JOB_CANCELED:
|
|
||||||
- virStorageSourceFree(disk->mirror);
|
|
||||||
- disk->mirror = NULL;
|
|
||||||
- disk->mirrorState = status == VIR_DOMAIN_BLOCK_JOB_FAILED ?
|
|
||||||
- VIR_DOMAIN_DISK_MIRROR_STATE_ABORT : VIR_DOMAIN_DISK_MIRROR_STATE_NONE;
|
|
||||||
- disk->mirrorJob = VIR_DOMAIN_BLOCK_JOB_TYPE_UNKNOWN;
|
|
||||||
- save = true;
|
|
||||||
- break;
|
|
||||||
+ processEvent->eventType = QEMU_PROCESS_EVENT_BLOCK_JOB;
|
|
||||||
+ if (VIR_STRDUP(data, diskAlias) < 0)
|
|
||||||
+ goto error;
|
|
||||||
+ processEvent->data = data;
|
|
||||||
+ processEvent->vm = vm;
|
|
||||||
+ processEvent->action = type;
|
|
||||||
+ processEvent->status = status;
|
|
||||||
|
|
||||||
- case VIR_DOMAIN_BLOCK_JOB_LAST:
|
|
||||||
- break;
|
|
||||||
- }
|
|
||||||
+ virObjectRef(vm);
|
|
||||||
+ if (virThreadPoolSendJob(driver->workerPool, 0, processEvent) < 0) {
|
|
||||||
+ ignore_value(virObjectUnref(vm));
|
|
||||||
+ goto error;
|
|
||||||
}
|
|
||||||
|
|
||||||
- if (save) {
|
|
||||||
- if (virDomainSaveStatus(driver->xmlopt, cfg->stateDir, vm) < 0)
|
|
||||||
- VIR_WARN("Unable to save status on vm %s after block job",
|
|
||||||
- vm->def->name);
|
|
||||||
- if (persistDisk && virDomainSaveConfig(cfg->configDir,
|
|
||||||
- vm->newDef) < 0)
|
|
||||||
- VIR_WARN("Unable to update persistent definition on vm %s "
|
|
||||||
- "after block job", vm->def->name);
|
|
||||||
- }
|
|
||||||
+ cleanup:
|
|
||||||
virObjectUnlock(vm);
|
|
||||||
- virObjectUnref(cfg);
|
|
||||||
-
|
|
||||||
- if (event)
|
|
||||||
- qemuDomainEventQueue(driver, event);
|
|
||||||
- if (event2)
|
|
||||||
- qemuDomainEventQueue(driver, event2);
|
|
||||||
-
|
|
||||||
return 0;
|
|
||||||
+ error:
|
|
||||||
+ if (processEvent)
|
|
||||||
+ VIR_FREE(processEvent->data);
|
|
||||||
+ VIR_FREE(processEvent);
|
|
||||||
+ goto cleanup;
|
|
||||||
}
|
|
||||||
|
|
||||||
+
|
|
||||||
static int
|
|
||||||
qemuProcessHandleGraphics(qemuMonitorPtr mon ATTRIBUTE_UNUSED,
|
|
||||||
virDomainObjPtr vm,
|
|
|
@ -1,175 +0,0 @@
|
||||||
From: Peter Krempa <pkrempa@redhat.com>
|
|
||||||
Date: Fri, 13 Mar 2015 17:22:04 +0100
|
|
||||||
Subject: [PATCH] qemu: Disallow concurrent block jobs on a single disk
|
|
||||||
|
|
||||||
While qemu may be prepared to do this libvirt is not. Forbid the block
|
|
||||||
ops until we fix our code.
|
|
||||||
|
|
||||||
(cherry picked from commit 51f9f03a4ca50b070c0fbfb29748d49f583e15e1)
|
|
||||||
---
|
|
||||||
src/conf/domain_conf.h | 4 ++++
|
|
||||||
src/qemu/qemu_domain.c | 23 +++++++++++++++++++++++
|
|
||||||
src/qemu/qemu_domain.h | 2 ++
|
|
||||||
src/qemu/qemu_driver.c | 28 +++++++++++++---------------
|
|
||||||
4 files changed, 42 insertions(+), 15 deletions(-)
|
|
||||||
|
|
||||||
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
|
|
||||||
index bca1b94..47bdb61 100644
|
|
||||||
--- a/src/conf/domain_conf.h
|
|
||||||
+++ b/src/conf/domain_conf.h
|
|
||||||
@@ -664,6 +664,10 @@ struct _virDomainDiskDef {
|
|
||||||
int tray_status; /* enum virDomainDiskTray */
|
|
||||||
int removable; /* enum virTristateSwitch */
|
|
||||||
|
|
||||||
+ /* ideally we want a smarter way to interlock block jobs on single qemu disk
|
|
||||||
+ * in the future, but for now we just disallow any concurrent job on a
|
|
||||||
+ * single disk */
|
|
||||||
+ bool blockjob;
|
|
||||||
virStorageSourcePtr mirror;
|
|
||||||
int mirrorState; /* enum virDomainDiskMirrorState */
|
|
||||||
int mirrorJob; /* virDomainBlockJobType */
|
|
||||||
diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
|
|
||||||
index bd7d8a4..7c2d046 100644
|
|
||||||
--- a/src/qemu/qemu_domain.c
|
|
||||||
+++ b/src/qemu/qemu_domain.c
|
|
||||||
@@ -2757,6 +2757,29 @@ qemuDomainDetermineDiskChain(virQEMUDriverPtr driver,
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
+
|
|
||||||
+bool
|
|
||||||
+qemuDomainDiskBlockJobIsActive(virDomainDiskDefPtr disk)
|
|
||||||
+{
|
|
||||||
+ if (disk->mirror) {
|
|
||||||
+ virReportError(VIR_ERR_BLOCK_COPY_ACTIVE,
|
|
||||||
+ _("disk '%s' already in active block job"),
|
|
||||||
+ disk->dst);
|
|
||||||
+
|
|
||||||
+ return true;
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ if (disk->blockjob) {
|
|
||||||
+ virReportError(VIR_ERR_OPERATION_UNSUPPORTED,
|
|
||||||
+ _("disk '%s' already in active block job"),
|
|
||||||
+ disk->dst);
|
|
||||||
+ return true;
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ return false;
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+
|
|
||||||
int
|
|
||||||
qemuDomainUpdateDeviceList(virQEMUDriverPtr driver,
|
|
||||||
virDomainObjPtr vm,
|
|
||||||
diff --git a/src/qemu/qemu_domain.h b/src/qemu/qemu_domain.h
|
|
||||||
index a7ebb47..41e075b 100644
|
|
||||||
--- a/src/qemu/qemu_domain.h
|
|
||||||
+++ b/src/qemu/qemu_domain.h
|
|
||||||
@@ -414,6 +414,8 @@ int qemuDomainJobInfoToParams(qemuDomainJobInfoPtr jobInfo,
|
|
||||||
ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2)
|
|
||||||
ATTRIBUTE_NONNULL(3) ATTRIBUTE_NONNULL(4);
|
|
||||||
|
|
||||||
+bool qemuDomainDiskBlockJobIsActive(virDomainDiskDefPtr disk);
|
|
||||||
+
|
|
||||||
void qemuDomObjEndAPI(virDomainObjPtr *vm);
|
|
||||||
|
|
||||||
#endif /* __QEMU_DOMAIN_H__ */
|
|
||||||
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
|
|
||||||
index 2e8c9d8..3ec057b 100644
|
|
||||||
--- a/src/qemu/qemu_driver.c
|
|
||||||
+++ b/src/qemu/qemu_driver.c
|
|
||||||
@@ -4569,6 +4569,7 @@ processBlockJobEvent(virQEMUDriverPtr driver,
|
|
||||||
disk->mirrorJob = VIR_DOMAIN_BLOCK_JOB_TYPE_UNKNOWN;
|
|
||||||
ignore_value(qemuDomainDetermineDiskChain(driver, vm, disk,
|
|
||||||
true, true));
|
|
||||||
+ disk->blockjob = false;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case VIR_DOMAIN_BLOCK_JOB_READY:
|
|
||||||
@@ -4584,6 +4585,7 @@ processBlockJobEvent(virQEMUDriverPtr driver,
|
|
||||||
VIR_DOMAIN_DISK_MIRROR_STATE_ABORT : VIR_DOMAIN_DISK_MIRROR_STATE_NONE;
|
|
||||||
disk->mirrorJob = VIR_DOMAIN_BLOCK_JOB_TYPE_UNKNOWN;
|
|
||||||
save = true;
|
|
||||||
+ disk->blockjob = false;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case VIR_DOMAIN_BLOCK_JOB_LAST:
|
|
||||||
@@ -15827,6 +15829,7 @@ qemuDomainBlockPivot(virConnectPtr conn,
|
|
||||||
disk->mirror = NULL;
|
|
||||||
disk->mirrorState = VIR_DOMAIN_DISK_MIRROR_STATE_NONE;
|
|
||||||
disk->mirrorJob = VIR_DOMAIN_BLOCK_JOB_TYPE_UNKNOWN;
|
|
||||||
+ disk->blockjob = false;
|
|
||||||
}
|
|
||||||
if (virDomainSaveStatus(driver->xmlopt, cfg->stateDir, vm) < 0)
|
|
||||||
ret = -1;
|
|
||||||
@@ -15927,12 +15930,9 @@ qemuDomainBlockJobImpl(virDomainObjPtr vm,
|
|
||||||
goto endjob;
|
|
||||||
disk = vm->def->disks[idx];
|
|
||||||
|
|
||||||
- if (mode == BLOCK_JOB_PULL && disk->mirror) {
|
|
||||||
- virReportError(VIR_ERR_BLOCK_COPY_ACTIVE,
|
|
||||||
- _("disk '%s' already in active block job"),
|
|
||||||
- disk->dst);
|
|
||||||
+ if (mode == BLOCK_JOB_PULL && qemuDomainDiskBlockJobIsActive(disk))
|
|
||||||
goto endjob;
|
|
||||||
- }
|
|
||||||
+
|
|
||||||
if (mode == BLOCK_JOB_ABORT) {
|
|
||||||
if ((flags & VIR_DOMAIN_BLOCK_JOB_ABORT_PIVOT) &&
|
|
||||||
!(async && disk->mirror)) {
|
|
||||||
@@ -16017,6 +16017,8 @@ qemuDomainBlockJobImpl(virDomainObjPtr vm,
|
|
||||||
if (mode == BLOCK_JOB_ABORT && disk->mirror)
|
|
||||||
disk->mirrorState = VIR_DOMAIN_DISK_MIRROR_STATE_NONE;
|
|
||||||
goto endjob;
|
|
||||||
+ } else if (mode == BLOCK_JOB_PULL) {
|
|
||||||
+ disk->blockjob = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
waitjob:
|
|
||||||
@@ -16269,12 +16271,8 @@ qemuDomainBlockCopyCommon(virDomainObjPtr vm,
|
|
||||||
if (!device)
|
|
||||||
goto endjob;
|
|
||||||
disk = vm->def->disks[idx];
|
|
||||||
- if (disk->mirror) {
|
|
||||||
- virReportError(VIR_ERR_BLOCK_COPY_ACTIVE,
|
|
||||||
- _("disk '%s' already in active block job"),
|
|
||||||
- disk->dst);
|
|
||||||
+ if (qemuDomainDiskBlockJobIsActive(disk))
|
|
||||||
goto endjob;
|
|
||||||
- }
|
|
||||||
|
|
||||||
if (!(virQEMUCapsGet(priv->qemuCaps, QEMU_CAPS_DRIVE_MIRROR) &&
|
|
||||||
virQEMUCapsGet(priv->qemuCaps, QEMU_CAPS_BLOCKJOB_ASYNC))) {
|
|
||||||
@@ -16396,6 +16394,7 @@ qemuDomainBlockCopyCommon(virDomainObjPtr vm,
|
|
||||||
disk->mirror = mirror;
|
|
||||||
mirror = NULL;
|
|
||||||
disk->mirrorJob = VIR_DOMAIN_BLOCK_JOB_TYPE_COPY;
|
|
||||||
+ disk->blockjob = true;
|
|
||||||
|
|
||||||
if (virDomainSaveStatus(driver->xmlopt, cfg->stateDir, vm) < 0)
|
|
||||||
VIR_WARN("Unable to save status on vm %s after state change",
|
|
||||||
@@ -16657,12 +16656,9 @@ qemuDomainBlockCommit(virDomainPtr dom,
|
|
||||||
disk->dst);
|
|
||||||
goto endjob;
|
|
||||||
}
|
|
||||||
- if (disk->mirror) {
|
|
||||||
- virReportError(VIR_ERR_BLOCK_COPY_ACTIVE,
|
|
||||||
- _("disk '%s' already in active block job"),
|
|
||||||
- disk->dst);
|
|
||||||
+
|
|
||||||
+ if (qemuDomainDiskBlockJobIsActive(disk))
|
|
||||||
goto endjob;
|
|
||||||
- }
|
|
||||||
if (qemuDomainDetermineDiskChain(driver, vm, disk, false, true) < 0)
|
|
||||||
goto endjob;
|
|
||||||
|
|
||||||
@@ -16785,6 +16781,8 @@ qemuDomainBlockCommit(virDomainPtr dom,
|
|
||||||
goto endjob;
|
|
||||||
}
|
|
||||||
|
|
||||||
+ disk->blockjob = true;
|
|
||||||
+
|
|
||||||
if (mirror) {
|
|
||||||
if (ret == 0) {
|
|
||||||
virQEMUDriverConfigPtr cfg = virQEMUDriverGetConfig(driver);
|
|
|
@ -1,28 +0,0 @@
|
||||||
From: Peter Krempa <pkrempa@redhat.com>
|
|
||||||
Date: Mon, 16 Mar 2015 16:52:44 +0100
|
|
||||||
Subject: [PATCH] qemu: block-commit: Mark disk in block jobs only on
|
|
||||||
successful command
|
|
||||||
|
|
||||||
Patch 51f9f03a4ca50b070c0fbfb29748d49f583e15e1 introduces a regression
|
|
||||||
where if a blockCommit operation fails the disk is still marked as being
|
|
||||||
part of a block job but can't be unmarked later.
|
|
||||||
|
|
||||||
(cherry picked from commit ee744b5b387b5123ee40683c52ab40783ffc3020)
|
|
||||||
---
|
|
||||||
src/qemu/qemu_driver.c | 3 ++-
|
|
||||||
1 file changed, 2 insertions(+), 1 deletion(-)
|
|
||||||
|
|
||||||
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
|
|
||||||
index 3ec057b..4817e06 100644
|
|
||||||
--- a/src/qemu/qemu_driver.c
|
|
||||||
+++ b/src/qemu/qemu_driver.c
|
|
||||||
@@ -16781,7 +16781,8 @@ qemuDomainBlockCommit(virDomainPtr dom,
|
|
||||||
goto endjob;
|
|
||||||
}
|
|
||||||
|
|
||||||
- disk->blockjob = true;
|
|
||||||
+ if (ret == 0)
|
|
||||||
+ disk->blockjob = true;
|
|
||||||
|
|
||||||
if (mirror) {
|
|
||||||
if (ret == 0) {
|
|
33
libvirt.spec
33
libvirt.spec
|
@ -370,8 +370,8 @@
|
||||||
|
|
||||||
Summary: Library providing a simple virtualization API
|
Summary: Library providing a simple virtualization API
|
||||||
Name: libvirt
|
Name: libvirt
|
||||||
Version: 1.2.13.1
|
Version: 1.2.13.2
|
||||||
Release: 3%{?dist}%{?extra_release}
|
Release: 1%{?dist}%{?extra_release}
|
||||||
License: LGPLv2+
|
License: LGPLv2+
|
||||||
Group: Development/Libraries
|
Group: Development/Libraries
|
||||||
BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root
|
BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root
|
||||||
|
@ -382,23 +382,8 @@ URL: http://libvirt.org/
|
||||||
%endif
|
%endif
|
||||||
Source: http://libvirt.org/sources/%{?mainturl}libvirt-%{version}.tar.gz
|
Source: http://libvirt.org/sources/%{?mainturl}libvirt-%{version}.tar.gz
|
||||||
|
|
||||||
# lxc network fixes (bz #1225591, bz #1225593, bz #1225594)
|
|
||||||
Patch0001: 0001-build-provide-virNetDevSysfsFile-on-non-Linux.patch
|
|
||||||
Patch0002: 0002-Introduce-virnetdevtest.patch
|
|
||||||
Patch0003: 0003-Cleanup-sys-class-net-usage.patch
|
|
||||||
Patch0004: 0004-lxc-move-wireless-PHYs-to-a-network-namespace.patch
|
|
||||||
Patch0005: 0005-tests-Add-virnetdevtestdata-to-EXTRA_DIST.patch
|
|
||||||
Patch0006: 0006-lxc-don-t-up-the-veth-interfaces-unless-explicitly-a.patch
|
|
||||||
Patch0007: 0007-interface-don-t-error-out-if-a-bond-has-no-interface.patch
|
|
||||||
Patch0008: 0008-virnetdev-fix-moving-of-802.11-phys.patch
|
|
||||||
|
|
||||||
# polkit: Allow password-less access for 'libvirt' group (bz #957300)
|
# polkit: Allow password-less access for 'libvirt' group (bz #957300)
|
||||||
Patch0101: 0101-polkit-Allow-password-less-access-for-libvirt-group.patch
|
Patch0001: 0001-polkit-Allow-password-less-access-for-libvirt-group.patch
|
||||||
# Add sanity checks for drive mirroring (bz #1263438)
|
|
||||||
Patch0102: 0102-qemu-process-Export-qemuProcessFindDomainDiskByAlias.patch
|
|
||||||
Patch0103: 0103-qemu-event-Don-t-fiddle-with-disk-backing-trees-with.patch
|
|
||||||
Patch0104: 0104-qemu-Disallow-concurrent-block-jobs-on-a-single-disk.patch
|
|
||||||
Patch0105: 0105-qemu-block-commit-Mark-disk-in-block-jobs-only-on-su.patch
|
|
||||||
|
|
||||||
%if %{with_libvirtd}
|
%if %{with_libvirtd}
|
||||||
Requires: libvirt-daemon = %{version}-%{release}
|
Requires: libvirt-daemon = %{version}-%{release}
|
||||||
|
@ -1261,6 +1246,7 @@ if [ $COUNT -gt 0 ]; then
|
||||||
fi
|
fi
|
||||||
echo "Applied $COUNT patches"
|
echo "Applied $COUNT patches"
|
||||||
rm -f $PATCHLIST
|
rm -f $PATCHLIST
|
||||||
|
rm -rf .git
|
||||||
|
|
||||||
%build
|
%build
|
||||||
%if ! %{with_xen}
|
%if ! %{with_xen}
|
||||||
|
@ -2311,6 +2297,17 @@ exit 0
|
||||||
%doc examples/systemtap
|
%doc examples/systemtap
|
||||||
|
|
||||||
%changelog
|
%changelog
|
||||||
|
* Wed Dec 23 2015 Cole Robinson <crobinso@redhat.com> - 1.2.13.2-1
|
||||||
|
- Rebased to version 1.2.13.2
|
||||||
|
- disk backend is not removed properly when disk frontent hotplug fails (bz
|
||||||
|
#1265968)
|
||||||
|
- Fix TPM cancel path on newer kernels (bz #1244895)
|
||||||
|
- Remove timeout for libvirt-guests.service (bz #1195544)
|
||||||
|
- CVE-2015-5313 libvirt: filesystem storage volume names path traversal flaw
|
||||||
|
(bz #1291433)
|
||||||
|
- Fix VM names with non-ascii (bz #1062943)
|
||||||
|
- Fix backwards migration with graphics listen address (bz #1276883)
|
||||||
|
|
||||||
* Mon Sep 21 2015 Cole Robinson <crobinso@redhat.com> - 1.2.13.1-3
|
* Mon Sep 21 2015 Cole Robinson <crobinso@redhat.com> - 1.2.13.1-3
|
||||||
- Add sanity checks for drive mirroring (bz #1263438)
|
- Add sanity checks for drive mirroring (bz #1263438)
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue