Compare commits
28
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
efdae0e168 | ||
|
|
e942243cd0 | ||
|
|
4f371cb8c3 | ||
|
|
29768222f1 | ||
|
|
68c271bad8 | ||
|
|
21a9f1ec41 | ||
|
|
39bacac57d | ||
|
|
7d9775ba12 | ||
|
|
3cfccddffa | ||
|
|
1bc3776fdb | ||
|
|
3a44160f46 | ||
|
|
5e8ea6c64c | ||
|
|
00ce651fb8 | ||
|
|
3c684a55ed | ||
|
|
b1ea570e48 | ||
|
|
6ccf4c1a0c | ||
|
|
dbaa6786af | ||
|
|
288291b795 | ||
|
|
7c2073faca | ||
|
|
5b528ba717 | ||
|
|
4f731a7250 | ||
|
|
f1ac0031f5 | ||
|
|
e45b9c9030 | ||
|
|
3cf75c269d | ||
|
|
585033f372 | ||
|
|
897506e66a | ||
|
|
e4bf8ffa42 | ||
|
|
20367a58a6 |
+1
-2
@@ -9,6 +9,5 @@ libvirt-0.6.2.tar.gz
|
||||
libvirt-0.6.3.tar.gz
|
||||
libvirt-0.6.4.tar.gz
|
||||
libvirt-0.6.5.tar.gz
|
||||
libvirt-0.7.0-0.1.gitf055724.tar.gz
|
||||
libvirt-0.7.0-0.6.gite195b43.tar.gz
|
||||
libvirt-0.7.0.tar.gz
|
||||
libvirt-0.7.1.tar.gz
|
||||
|
||||
@@ -4,7 +4,7 @@ NAME := libvirt
|
||||
SPECFILE = $(firstword $(wildcard *.spec))
|
||||
|
||||
define find-makefile-common
|
||||
for d in common ../common ../../common ; do if [ -f $$d/Makefile.common ] ; then if [ -f $$d/CVS/Root -a -w $$/Makefile.common ] ; then cd $$d ; cvs -Q update ; fi ; echo "$$d/Makefile.common" ; break ; fi ; done
|
||||
for d in common ../common ../../common ; do if [ -f $$d/Makefile.common ] ; then if [ -f $$d/CVS/Root -a -w $$d/Makefile.common ] ; then cd $$d ; cvs -Q update ; fi ; echo "$$d/Makefile.common" ; break ; fi ; done
|
||||
endef
|
||||
|
||||
MAKEFILE_COMMON := $(shell $(find-makefile-common))
|
||||
|
||||
@@ -1,51 +0,0 @@
|
||||
From 5f8d720b5f1393ee333a5fa8375ffe9ac954d48b Mon Sep 17 00:00:00 2001
|
||||
From: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Mon, 17 Aug 2009 08:32:08 +0100
|
||||
Subject: [PATCH] Disable sound cards when running sVirt
|
||||
|
||||
Temporary hack till PulseAudio autostart problems are sorted out when
|
||||
SELinux enforcing (bz 486112)
|
||||
|
||||
Fedora-patch: libvirt-0.6.4-svirt-sound.patch
|
||||
---
|
||||
src/qemu_conf.c | 17 ++++++++++++++++-
|
||||
1 files changed, 16 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_conf.c b/src/qemu_conf.c
|
||||
index 6b0b404..53186e0 100644
|
||||
--- a/src/qemu_conf.c
|
||||
+++ b/src/qemu_conf.c
|
||||
@@ -1384,6 +1384,20 @@ int qemudBuildCommandLine(virConnectPtr conn,
|
||||
char uuid[VIR_UUID_STRING_BUFLEN];
|
||||
char domid[50];
|
||||
const char *cpu = NULL;
|
||||
+ int skipSound = 0;
|
||||
+
|
||||
+ if (driver->securityDriver &&
|
||||
+ driver->securityDriver->name &&
|
||||
+ STREQ(driver->securityDriver->name, "selinux") &&
|
||||
+ getuid() == 0) {
|
||||
+ static int soundWarned = 0;
|
||||
+ skipSound = 1;
|
||||
+ if (def->nsounds &&
|
||||
+ !soundWarned) {
|
||||
+ soundWarned = 1;
|
||||
+ VIR_WARN0("Sound cards for VMs are disabled while SELinux security model is active");
|
||||
+ }
|
||||
+ }
|
||||
|
||||
uname_normalize(&ut);
|
||||
|
||||
@@ -2015,7 +2029,8 @@ int qemudBuildCommandLine(virConnectPtr conn,
|
||||
}
|
||||
|
||||
/* Add sound hardware */
|
||||
- if (def->nsounds) {
|
||||
+ if (def->nsounds &&
|
||||
+ !skipSound) {
|
||||
int size = 100;
|
||||
char *modstr;
|
||||
if (VIR_ALLOC_N(modstr, size+1) < 0)
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,79 +0,0 @@
|
||||
From 541cfdf5465ac3bba2c0c0901950547bc6638e47 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Thu, 6 Aug 2009 15:14:19 +0100
|
||||
Subject: [PATCH] chown kernel/initrd before spawning qemu
|
||||
|
||||
If we're running qemu unprivileged, we need to chown any supplied kernel
|
||||
or initrd before spawning it.
|
||||
|
||||
* src/qemu_driver.c: rename qemuDomainSetDiskOwnership() to
|
||||
qemuDomainSetFileOwnership(), pass it a path string instead of a disk
|
||||
definition and use it for chowning the kernel/initrd in
|
||||
qemuDomainSetAllDeviceOwnership()
|
||||
|
||||
(cherry picked from commit c42b39784534930791d1feb3de859d85a7848168)
|
||||
|
||||
Fedora-patch: libvirt-0.7.0-chown-kernel-initrd-before-spawning-qemu.patch
|
||||
---
|
||||
src/qemu_driver.c | 20 ++++++++++++--------
|
||||
1 files changed, 12 insertions(+), 8 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 412b68d..bd58435 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -1684,18 +1684,18 @@ static int qemuDomainSetHostdevOwnership(virConnectPtr conn,
|
||||
|
||||
}
|
||||
|
||||
-static int qemuDomainSetDiskOwnership(virConnectPtr conn,
|
||||
- virDomainDiskDefPtr def,
|
||||
+static int qemuDomainSetFileOwnership(virConnectPtr conn,
|
||||
+ const char *path,
|
||||
uid_t uid, gid_t gid)
|
||||
{
|
||||
|
||||
- if (!def->src)
|
||||
+ if (!path)
|
||||
return 0;
|
||||
|
||||
- VIR_DEBUG("Setting ownership on %s to %d:%d", def->src, uid, gid);
|
||||
- if (chown(def->src, uid, gid) < 0) {
|
||||
+ VIR_DEBUG("Setting ownership on %s to %d:%d", path, uid, gid);
|
||||
+ if (chown(path, uid, gid) < 0) {
|
||||
virReportSystemError(conn, errno, _("cannot set ownership on %s"),
|
||||
- def->src);
|
||||
+ path);
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
@@ -1725,7 +1725,7 @@ static int qemuDomainSetDeviceOwnership(virConnectPtr conn,
|
||||
(def->data.disk->readonly || def->data.disk->shared))
|
||||
return 0;
|
||||
|
||||
- return qemuDomainSetDiskOwnership(conn, def->data.disk, uid, gid);
|
||||
+ return qemuDomainSetFileOwnership(conn, def->data.disk->src, uid, gid);
|
||||
|
||||
case VIR_DOMAIN_DEVICE_HOSTDEV:
|
||||
return qemuDomainSetHostdevOwnership(conn, def->data.hostdev, uid, gid);
|
||||
@@ -1753,12 +1753,16 @@ static int qemuDomainSetAllDeviceOwnership(virConnectPtr conn,
|
||||
uid = restore ? 0 : driver->user;
|
||||
gid = restore ? 0 : driver->group;
|
||||
|
||||
+ if (qemuDomainSetFileOwnership(conn, def->os.kernel, uid, gid) < 0 ||
|
||||
+ qemuDomainSetFileOwnership(conn, def->os.initrd, uid, gid) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
for (i = 0 ; i < def->ndisks ; i++) {
|
||||
if (restore &&
|
||||
(def->disks[i]->readonly || def->disks[i]->shared))
|
||||
continue;
|
||||
|
||||
- if (qemuDomainSetDiskOwnership(conn, def->disks[i], uid, gid) < 0)
|
||||
+ if (qemuDomainSetFileOwnership(conn, def->disks[i]->src, uid, gid) < 0)
|
||||
return -1;
|
||||
}
|
||||
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,45 +0,0 @@
|
||||
From ddf0a7cb04debe60825d11186e68cc6de6fd1dd2 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Mon, 10 Aug 2009 11:16:37 +0100
|
||||
Subject: [PATCH] Handle kernels with no ipv6 support
|
||||
|
||||
If the ipv6 kernel module is not loaded, then we get this when starting
|
||||
a virtual network:
|
||||
|
||||
libvir: Network Config error :
|
||||
cannot enable /proc/sys/net/ipv6/conf/virbr0/disable_ipv6:
|
||||
No such file or directory
|
||||
|
||||
If disable_ipv6 is not present, we should just merrily continue on our
|
||||
way.
|
||||
|
||||
* src/network_driver.c: make networkDisableIPV6() not fail if the kernel
|
||||
has no ipv6 support
|
||||
|
||||
(cherry picked from commit f5a8f969dd92ec2744e1eec5d35288d5fbcded22)
|
||||
|
||||
Fedora-patch: libvirt-0.7.0-handle-kernels-with-no-ipv6-support.patch
|
||||
---
|
||||
src/network_driver.c | 6 ++++++
|
||||
1 files changed, 6 insertions(+), 0 deletions(-)
|
||||
|
||||
diff --git a/src/network_driver.c b/src/network_driver.c
|
||||
index eaea454..84910ab 100644
|
||||
--- a/src/network_driver.c
|
||||
+++ b/src/network_driver.c
|
||||
@@ -801,6 +801,12 @@ static int networkDisableIPV6(virConnectPtr conn,
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
+ if (access(field, W_OK) < 0 && errno == ENOENT) {
|
||||
+ VIR_DEBUG("ipv6 appears to already be disabled on %s", network->def->bridge);
|
||||
+ ret = 0;
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
if (virFileWriteStr(field, "1") < 0) {
|
||||
virReportSystemError(conn, errno,
|
||||
_("cannot enable %s"), field);
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,96 +0,0 @@
|
||||
From 663bf081dc6737c7fcc68a7ca1169aca60fbf8e5 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Thu, 13 Aug 2009 11:56:31 +0100
|
||||
Subject: [PATCH] Make LXC / UML drivers robust against NUMA topology brokenness
|
||||
|
||||
Some kernel versions expose broken NUMA topology for some machines.
|
||||
This causes the LXC/UML drivers to fail to start. QEMU driver was
|
||||
already fixed for this problem
|
||||
|
||||
* src/lxc_conf.c: Log and ignore failure to populate NUMA info
|
||||
* src/uml_conf.c: Log and ignore failure to populate NUMA info
|
||||
* src/capabilities.c: Reset nnumaCell to 0 after freeing
|
||||
|
||||
(cherry picked from commit 19bac57b26c2d46ac8a7601158f210f34acdceac)
|
||||
|
||||
Fedora-patch: libvirt-0.7.0-numa-ignore-fail.patch
|
||||
---
|
||||
src/capabilities.c | 1 +
|
||||
src/lxc_conf.c | 12 ++++++++++--
|
||||
src/uml_conf.c | 11 +++++++++--
|
||||
3 files changed, 20 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/src/capabilities.c b/src/capabilities.c
|
||||
index c6766b6..193a9fe 100644
|
||||
--- a/src/capabilities.c
|
||||
+++ b/src/capabilities.c
|
||||
@@ -139,6 +139,7 @@ virCapabilitiesFreeNUMAInfo(virCapsPtr caps)
|
||||
for (i = 0 ; i < caps->host.nnumaCell ; i++)
|
||||
virCapabilitiesFreeHostNUMACell(caps->host.numaCell[i]);
|
||||
VIR_FREE(caps->host.numaCell);
|
||||
+ caps->host.nnumaCell = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
diff --git a/src/lxc_conf.c b/src/lxc_conf.c
|
||||
index d06a024..fef60ba 100644
|
||||
--- a/src/lxc_conf.c
|
||||
+++ b/src/lxc_conf.c
|
||||
@@ -30,6 +30,8 @@
|
||||
#include "lxc_conf.h"
|
||||
#include "nodeinfo.h"
|
||||
#include "virterror_internal.h"
|
||||
+#include "logging.h"
|
||||
+
|
||||
|
||||
#define VIR_FROM_THIS VIR_FROM_LXC
|
||||
|
||||
@@ -46,8 +48,14 @@ virCapsPtr lxcCapsInit(void)
|
||||
0, 0)) == NULL)
|
||||
goto no_memory;
|
||||
|
||||
- if (nodeCapsInitNUMA(caps) < 0)
|
||||
- goto no_memory;
|
||||
+ /* Some machines have problematic NUMA toplogy causing
|
||||
+ * unexpected failures. We don't want to break the QEMU
|
||||
+ * driver in this scenario, so log errors & carry on
|
||||
+ */
|
||||
+ if (nodeCapsInitNUMA(caps) < 0) {
|
||||
+ virCapabilitiesFreeNUMAInfo(caps);
|
||||
+ VIR_WARN0("Failed to query host NUMA topology, disabling NUMA capabilities");
|
||||
+ }
|
||||
|
||||
/* XXX shouldn't 'borrow' KVM's prefix */
|
||||
virCapabilitiesSetMacPrefix(caps, (unsigned char []){ 0x52, 0x54, 0x00 });
|
||||
diff --git a/src/uml_conf.c b/src/uml_conf.c
|
||||
index 48e05a8..4f756d4 100644
|
||||
--- a/src/uml_conf.c
|
||||
+++ b/src/uml_conf.c
|
||||
@@ -45,6 +45,7 @@
|
||||
#include "nodeinfo.h"
|
||||
#include "verify.h"
|
||||
#include "bridge.h"
|
||||
+#include "logging.h"
|
||||
|
||||
#define VIR_FROM_THIS VIR_FROM_UML
|
||||
|
||||
@@ -63,8 +64,14 @@ virCapsPtr umlCapsInit(void) {
|
||||
0, 0)) == NULL)
|
||||
goto no_memory;
|
||||
|
||||
- if (nodeCapsInitNUMA(caps) < 0)
|
||||
- goto no_memory;
|
||||
+ /* Some machines have problematic NUMA toplogy causing
|
||||
+ * unexpected failures. We don't want to break the QEMU
|
||||
+ * driver in this scenario, so log errors & carry on
|
||||
+ */
|
||||
+ if (nodeCapsInitNUMA(caps) < 0) {
|
||||
+ virCapabilitiesFreeNUMAInfo(caps);
|
||||
+ VIR_WARN0("Failed to query host NUMA topology, disabling NUMA capabilities");
|
||||
+ }
|
||||
|
||||
if ((guest = virCapabilitiesAddGuest(caps,
|
||||
"uml",
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,505 +0,0 @@
|
||||
From d54fc5008d465d192101a0cb78fd02c437dff736 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Mon, 17 Aug 2009 08:32:08 +0100
|
||||
Subject: [PATCH] Policykit rewrite (bug #499970)
|
||||
|
||||
Fedora-patch: libvirt-0.7.0-policy-kit-rewrite.patch
|
||||
---
|
||||
configure.in | 73 ++++++++++++++++++++++++++++--------------
|
||||
qemud/Makefile.am | 11 +++++-
|
||||
qemud/libvirtd.policy | 42 ------------------------
|
||||
qemud/libvirtd.policy-0 | 42 ++++++++++++++++++++++++
|
||||
qemud/libvirtd.policy-1 | 42 ++++++++++++++++++++++++
|
||||
qemud/qemud.c | 4 +-
|
||||
qemud/qemud.h | 4 +-
|
||||
qemud/remote.c | 81 ++++++++++++++++++++++++++++++++++++++++++++--
|
||||
src/remote_internal.c | 7 ++++
|
||||
9 files changed, 230 insertions(+), 76 deletions(-)
|
||||
delete mode 100644 qemud/libvirtd.policy
|
||||
create mode 100644 qemud/libvirtd.policy-0
|
||||
create mode 100644 qemud/libvirtd.policy-1
|
||||
|
||||
diff --git a/configure.in b/configure.in
|
||||
index 45fa9ed..d28c44a 100644
|
||||
--- a/configure.in
|
||||
+++ b/configure.in
|
||||
@@ -641,40 +641,61 @@ AC_SUBST([SASL_LIBS])
|
||||
dnl PolicyKit library
|
||||
POLKIT_CFLAGS=
|
||||
POLKIT_LIBS=
|
||||
+PKCHECK_PATH=
|
||||
AC_ARG_WITH([polkit],
|
||||
[ --with-polkit use PolicyKit for UNIX socket access checks],
|
||||
[],
|
||||
[with_polkit=check])
|
||||
|
||||
+with_polkit0=no
|
||||
+with_polkit1=no
|
||||
if test "x$with_polkit" = "xyes" -o "x$with_polkit" = "xcheck"; then
|
||||
- PKG_CHECK_MODULES(POLKIT, polkit-dbus >= $POLKIT_REQUIRED,
|
||||
- [with_polkit=yes], [
|
||||
- if test "x$with_polkit" = "xcheck" ; then
|
||||
- with_polkit=no
|
||||
- else
|
||||
- AC_MSG_ERROR(
|
||||
- [You must install PolicyKit >= $POLKIT_REQUIRED to compile libvirt])
|
||||
- fi
|
||||
- ])
|
||||
- if test "x$with_polkit" = "xyes" ; then
|
||||
+ dnl Check for new polkit first - just a binary
|
||||
+ AC_PATH_PROG([PKCHECK_PATH],[pkcheck], [], [/usr/sbin:$PATH])
|
||||
+ if test "x$PKCHECK_PATH" != "x" ; then
|
||||
+ AC_DEFINE_UNQUOTED([PKCHECK_PATH],["$PKCHECK_PATH"],[Location of pkcheck program])
|
||||
AC_DEFINE_UNQUOTED([HAVE_POLKIT], 1,
|
||||
- [use PolicyKit for UNIX socket access checks])
|
||||
-
|
||||
- old_CFLAGS=$CFLAGS
|
||||
- old_LDFLAGS=$LDFLAGS
|
||||
- CFLAGS="$CFLAGS $POLKIT_CFLAGS"
|
||||
- LDFLAGS="$LDFLAGS $POLKIT_LIBS"
|
||||
- AC_CHECK_FUNCS([polkit_context_is_caller_authorized])
|
||||
- CFLAGS="$old_CFLAGS"
|
||||
- LDFLAGS="$old_LDFLAGS"
|
||||
-
|
||||
- AC_PATH_PROG([POLKIT_AUTH], [polkit-auth])
|
||||
- if test "x$POLKIT_AUTH" != "x"; then
|
||||
- AC_DEFINE_UNQUOTED([POLKIT_AUTH],["$POLKIT_AUTH"],[Location of polkit-auth program])
|
||||
+ [use PolicyKit for UNIX socket access checks])
|
||||
+ AC_DEFINE_UNQUOTED([HAVE_POLKIT1], 1,
|
||||
+ [use PolicyKit for UNIX socket access checks])
|
||||
+ with_polkit="yes"
|
||||
+ with_polkit1="yes"
|
||||
+ else
|
||||
+ dnl Check for old polkit second - library + binary
|
||||
+ PKG_CHECK_MODULES(POLKIT, polkit-dbus >= $POLKIT_REQUIRED,
|
||||
+ [with_polkit=yes], [
|
||||
+ if test "x$with_polkit" = "xcheck" ; then
|
||||
+ with_polkit=no
|
||||
+ else
|
||||
+ AC_MSG_ERROR(
|
||||
+ [You must install PolicyKit >= $POLKIT_REQUIRED to compile libvirt])
|
||||
+ fi
|
||||
+ ])
|
||||
+ if test "x$with_polkit" = "xyes" ; then
|
||||
+ AC_DEFINE_UNQUOTED([HAVE_POLKIT], 1,
|
||||
+ [use PolicyKit for UNIX socket access checks])
|
||||
+ AC_DEFINE_UNQUOTED([HAVE_POLKIT0], 1,
|
||||
+ [use PolicyKit for UNIX socket access checks])
|
||||
+
|
||||
+ old_CFLAGS=$CFLAGS
|
||||
+ old_LDFLAGS=$LDFLAGS
|
||||
+ CFLAGS="$CFLAGS $POLKIT_CFLAGS"
|
||||
+ LDFLAGS="$LDFLAGS $POLKIT_LIBS"
|
||||
+ AC_CHECK_FUNCS([polkit_context_is_caller_authorized])
|
||||
+ CFLAGS="$old_CFLAGS"
|
||||
+ LDFLAGS="$old_LDFLAGS"
|
||||
+
|
||||
+ AC_PATH_PROG([POLKIT_AUTH], [polkit-auth])
|
||||
+ if test "x$POLKIT_AUTH" != "x"; then
|
||||
+ AC_DEFINE_UNQUOTED([POLKIT_AUTH],["$POLKIT_AUTH"],[Location of polkit-auth program])
|
||||
+ fi
|
||||
+ with_polkit0="yes"
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
AM_CONDITIONAL([HAVE_POLKIT], [test "x$with_polkit" = "xyes"])
|
||||
+AM_CONDITIONAL([HAVE_POLKIT0], [test "x$with_polkit0" = "xyes"])
|
||||
+AM_CONDITIONAL([HAVE_POLKIT1], [test "x$with_polkit1" = "xyes"])
|
||||
AC_SUBST([POLKIT_CFLAGS])
|
||||
AC_SUBST([POLKIT_LIBS])
|
||||
|
||||
@@ -1695,7 +1716,11 @@ else
|
||||
AC_MSG_NOTICE([ avahi: no])
|
||||
fi
|
||||
if test "$with_polkit" = "yes" ; then
|
||||
-AC_MSG_NOTICE([ polkit: $POLKIT_CFLAGS $POLKIT_LIBS])
|
||||
+if test "$with_polkit0" = "yes" ; then
|
||||
+AC_MSG_NOTICE([ polkit: $POLKIT_CFLAGS $POLKIT_LIBS (version 0)])
|
||||
+else
|
||||
+AC_MSG_NOTICE([ polkit: $PKCHECK_PATH (version 1)])
|
||||
+fi
|
||||
else
|
||||
AC_MSG_NOTICE([ polkit: no])
|
||||
fi
|
||||
diff --git a/qemud/Makefile.am b/qemud/Makefile.am
|
||||
index 959ff88..3d143da 100644
|
||||
--- a/qemud/Makefile.am
|
||||
+++ b/qemud/Makefile.am
|
||||
@@ -21,7 +21,8 @@ EXTRA_DIST = \
|
||||
remote_protocol.x \
|
||||
libvirtd.conf \
|
||||
libvirtd.init.in \
|
||||
- libvirtd.policy \
|
||||
+ libvirtd.policy-0 \
|
||||
+ libvirtd.policy-1 \
|
||||
libvirtd.sasl \
|
||||
libvirtd.sysconf \
|
||||
libvirtd.aug \
|
||||
@@ -147,7 +148,13 @@ endif
|
||||
libvirtd_LDADD += ../src/libvirt.la
|
||||
|
||||
if HAVE_POLKIT
|
||||
+if HAVE_POLKIT0
|
||||
policydir = $(datadir)/PolicyKit/policy
|
||||
+policyfile = libvirtd.policy-0
|
||||
+else
|
||||
+policydir = $(datadir)/polkit-1/actions
|
||||
+policyfile = libvirtd.policy-1
|
||||
+endif
|
||||
endif
|
||||
|
||||
if HAVE_AVAHI
|
||||
@@ -197,7 +204,7 @@ endif
|
||||
if HAVE_POLKIT
|
||||
install-data-polkit:: install-init
|
||||
mkdir -p $(DESTDIR)$(policydir)
|
||||
- $(INSTALL_DATA) $(srcdir)/libvirtd.policy $(DESTDIR)$(policydir)/org.libvirt.unix.policy
|
||||
+ $(INSTALL_DATA) $(srcdir)/$(policyfile) $(DESTDIR)$(policydir)/org.libvirt.unix.policy
|
||||
uninstall-data-polkit:: install-init
|
||||
rm -f $(DESTDIR)$(policydir)/org.libvirt.unix.policy
|
||||
else
|
||||
diff --git a/qemud/libvirtd.policy b/qemud/libvirtd.policy
|
||||
deleted file mode 100644
|
||||
index b6da946..0000000
|
||||
--- a/qemud/libvirtd.policy
|
||||
+++ /dev/null
|
||||
@@ -1,42 +0,0 @@
|
||||
-<!DOCTYPE policyconfig PUBLIC
|
||||
- "-//freedesktop//DTD PolicyKit Policy Configuration 1.0//EN"
|
||||
- "http://www.freedesktop.org/standards/PolicyKit/1.0/policyconfig.dtd">
|
||||
-
|
||||
-<!--
|
||||
-Policy definitions for libvirt daemon
|
||||
-
|
||||
-Copyright (c) 2007 Daniel P. Berrange <berrange redhat com>
|
||||
-
|
||||
-libvirt is licensed to you under the GNU Lesser General Public License
|
||||
-version 2. See COPYING for details.
|
||||
-
|
||||
-NOTE: If you make changes to this file, make sure to validate the file
|
||||
-using the polkit-policy-file-validate(1) tool. Changes made to this
|
||||
-file are instantly applied.
|
||||
--->
|
||||
-
|
||||
-<policyconfig>
|
||||
- <action id="org.libvirt.unix.monitor">
|
||||
- <description>Monitor local virtualized systems</description>
|
||||
- <message>System policy prevents monitoring of local virtualized systems</message>
|
||||
- <defaults>
|
||||
- <!-- Any program can use libvirt in read-only mode for monitoring,
|
||||
- even if not part of a session -->
|
||||
- <allow_any>yes</allow_any>
|
||||
- <allow_inactive>yes</allow_inactive>
|
||||
- <allow_active>yes</allow_active>
|
||||
- </defaults>
|
||||
- </action>
|
||||
-
|
||||
- <action id="org.libvirt.unix.manage">
|
||||
- <description>Manage local virtualized systems</description>
|
||||
- <message>System policy prevents management of local virtualized systems</message>
|
||||
- <defaults>
|
||||
- <!-- Only a program in the active host session can use libvirt in
|
||||
- read-write mode for management, and we require user password -->
|
||||
- <allow_any>no</allow_any>
|
||||
- <allow_inactive>no</allow_inactive>
|
||||
- <allow_active>auth_admin_keep_session</allow_active>
|
||||
- </defaults>
|
||||
- </action>
|
||||
-</policyconfig>
|
||||
diff --git a/qemud/libvirtd.policy-0 b/qemud/libvirtd.policy-0
|
||||
new file mode 100644
|
||||
index 0000000..b6da946
|
||||
--- /dev/null
|
||||
+++ b/qemud/libvirtd.policy-0
|
||||
@@ -0,0 +1,42 @@
|
||||
+<!DOCTYPE policyconfig PUBLIC
|
||||
+ "-//freedesktop//DTD PolicyKit Policy Configuration 1.0//EN"
|
||||
+ "http://www.freedesktop.org/standards/PolicyKit/1.0/policyconfig.dtd">
|
||||
+
|
||||
+<!--
|
||||
+Policy definitions for libvirt daemon
|
||||
+
|
||||
+Copyright (c) 2007 Daniel P. Berrange <berrange redhat com>
|
||||
+
|
||||
+libvirt is licensed to you under the GNU Lesser General Public License
|
||||
+version 2. See COPYING for details.
|
||||
+
|
||||
+NOTE: If you make changes to this file, make sure to validate the file
|
||||
+using the polkit-policy-file-validate(1) tool. Changes made to this
|
||||
+file are instantly applied.
|
||||
+-->
|
||||
+
|
||||
+<policyconfig>
|
||||
+ <action id="org.libvirt.unix.monitor">
|
||||
+ <description>Monitor local virtualized systems</description>
|
||||
+ <message>System policy prevents monitoring of local virtualized systems</message>
|
||||
+ <defaults>
|
||||
+ <!-- Any program can use libvirt in read-only mode for monitoring,
|
||||
+ even if not part of a session -->
|
||||
+ <allow_any>yes</allow_any>
|
||||
+ <allow_inactive>yes</allow_inactive>
|
||||
+ <allow_active>yes</allow_active>
|
||||
+ </defaults>
|
||||
+ </action>
|
||||
+
|
||||
+ <action id="org.libvirt.unix.manage">
|
||||
+ <description>Manage local virtualized systems</description>
|
||||
+ <message>System policy prevents management of local virtualized systems</message>
|
||||
+ <defaults>
|
||||
+ <!-- Only a program in the active host session can use libvirt in
|
||||
+ read-write mode for management, and we require user password -->
|
||||
+ <allow_any>no</allow_any>
|
||||
+ <allow_inactive>no</allow_inactive>
|
||||
+ <allow_active>auth_admin_keep_session</allow_active>
|
||||
+ </defaults>
|
||||
+ </action>
|
||||
+</policyconfig>
|
||||
diff --git a/qemud/libvirtd.policy-1 b/qemud/libvirtd.policy-1
|
||||
new file mode 100644
|
||||
index 0000000..6fa3a5e
|
||||
--- /dev/null
|
||||
+++ b/qemud/libvirtd.policy-1
|
||||
@@ -0,0 +1,42 @@
|
||||
+<!DOCTYPE policyconfig PUBLIC
|
||||
+ "-//freedesktop//DTD PolicyKit Policy Configuration 1.0//EN"
|
||||
+ "http://www.freedesktop.org/standards/PolicyKit/1.0/policyconfig.dtd">
|
||||
+
|
||||
+<!--
|
||||
+Policy definitions for libvirt daemon
|
||||
+
|
||||
+Copyright (c) 2007 Daniel P. Berrange <berrange redhat com>
|
||||
+
|
||||
+libvirt is licensed to you under the GNU Lesser General Public License
|
||||
+version 2. See COPYING for details.
|
||||
+
|
||||
+NOTE: If you make changes to this file, make sure to validate the file
|
||||
+using the polkit-policy-file-validate(1) tool. Changes made to this
|
||||
+file are instantly applied.
|
||||
+-->
|
||||
+
|
||||
+<policyconfig>
|
||||
+ <action id="org.libvirt.unix.monitor">
|
||||
+ <description>Monitor local virtualized systems</description>
|
||||
+ <message>System policy prevents monitoring of local virtualized systems</message>
|
||||
+ <defaults>
|
||||
+ <!-- Any program can use libvirt in read-only mode for monitoring,
|
||||
+ even if not part of a session -->
|
||||
+ <allow_any>yes</allow_any>
|
||||
+ <allow_inactive>yes</allow_inactive>
|
||||
+ <allow_active>yes</allow_active>
|
||||
+ </defaults>
|
||||
+ </action>
|
||||
+
|
||||
+ <action id="org.libvirt.unix.manage">
|
||||
+ <description>Manage local virtualized systems</description>
|
||||
+ <message>System policy prevents management of local virtualized systems</message>
|
||||
+ <defaults>
|
||||
+ <!-- Only a program in the active host session can use libvirt in
|
||||
+ read-write mode for management, and we require user password -->
|
||||
+ <allow_any>no</allow_any>
|
||||
+ <allow_inactive>no</allow_inactive>
|
||||
+ <allow_active>auth_admin_keep</allow_active>
|
||||
+ </defaults>
|
||||
+ </action>
|
||||
+</policyconfig>
|
||||
diff --git a/qemud/qemud.c b/qemud/qemud.c
|
||||
index 3e551ca..50b0cdd 100644
|
||||
--- a/qemud/qemud.c
|
||||
+++ b/qemud/qemud.c
|
||||
@@ -895,7 +895,7 @@ static struct qemud_server *qemudNetworkInit(struct qemud_server *server) {
|
||||
}
|
||||
#endif
|
||||
|
||||
-#ifdef HAVE_POLKIT
|
||||
+#if HAVE_POLKIT0
|
||||
if (auth_unix_rw == REMOTE_AUTH_POLKIT ||
|
||||
auth_unix_ro == REMOTE_AUTH_POLKIT) {
|
||||
DBusError derr;
|
||||
@@ -982,7 +982,7 @@ static struct qemud_server *qemudNetworkInit(struct qemud_server *server) {
|
||||
sock = sock->next;
|
||||
}
|
||||
|
||||
-#ifdef HAVE_POLKIT
|
||||
+#if HAVE_POLKIT0
|
||||
if (server->sysbus)
|
||||
dbus_connection_unref(server->sysbus);
|
||||
#endif
|
||||
diff --git a/qemud/qemud.h b/qemud/qemud.h
|
||||
index 254db44..e8ce209 100644
|
||||
--- a/qemud/qemud.h
|
||||
+++ b/qemud/qemud.h
|
||||
@@ -34,7 +34,7 @@
|
||||
#include <sasl/sasl.h>
|
||||
#endif
|
||||
|
||||
-#ifdef HAVE_POLKIT
|
||||
+#if HAVE_POLKIT0
|
||||
#include <dbus/dbus.h>
|
||||
#endif
|
||||
|
||||
@@ -253,7 +253,7 @@ struct qemud_server {
|
||||
#if HAVE_SASL
|
||||
char **saslUsernameWhitelist;
|
||||
#endif
|
||||
-#if HAVE_POLKIT
|
||||
+#if HAVE_POLKIT0
|
||||
DBusConnection *sysbus;
|
||||
#endif
|
||||
};
|
||||
diff --git a/qemud/remote.c b/qemud/remote.c
|
||||
index d32d513..490a807 100644
|
||||
--- a/qemud/remote.c
|
||||
+++ b/qemud/remote.c
|
||||
@@ -43,7 +43,7 @@
|
||||
#include <fnmatch.h>
|
||||
#include "virterror_internal.h"
|
||||
|
||||
-#ifdef HAVE_POLKIT
|
||||
+#if HAVE_POLKIT0
|
||||
#include <polkit/polkit.h>
|
||||
#include <polkit-dbus/polkit-dbus.h>
|
||||
#endif
|
||||
@@ -3106,7 +3106,80 @@ remoteDispatchAuthSaslStep (struct qemud_server *server ATTRIBUTE_UNUSED,
|
||||
#endif /* HAVE_SASL */
|
||||
|
||||
|
||||
-#if HAVE_POLKIT
|
||||
+#if HAVE_POLKIT1
|
||||
+static int
|
||||
+remoteDispatchAuthPolkit (struct qemud_server *server,
|
||||
+ struct qemud_client *client,
|
||||
+ virConnectPtr conn ATTRIBUTE_UNUSED,
|
||||
+ remote_error *rerr,
|
||||
+ void *args ATTRIBUTE_UNUSED,
|
||||
+ remote_auth_polkit_ret *ret)
|
||||
+{
|
||||
+ pid_t callerPid;
|
||||
+ uid_t callerUid;
|
||||
+ const char *action;
|
||||
+ int status = -1;
|
||||
+ char pidbuf[50];
|
||||
+ int rv;
|
||||
+
|
||||
+ virMutexLock(&server->lock);
|
||||
+ virMutexLock(&client->lock);
|
||||
+ virMutexUnlock(&server->lock);
|
||||
+
|
||||
+ action = client->readonly ?
|
||||
+ "org.libvirt.unix.monitor" :
|
||||
+ "org.libvirt.unix.manage";
|
||||
+
|
||||
+ const char * const pkcheck [] = {
|
||||
+ PKCHECK_PATH,
|
||||
+ "--action-id", action,
|
||||
+ "--process", pidbuf,
|
||||
+ "--allow-user-interaction",
|
||||
+ NULL
|
||||
+ };
|
||||
+
|
||||
+ REMOTE_DEBUG("Start PolicyKit auth %d", client->fd);
|
||||
+ if (client->auth != REMOTE_AUTH_POLKIT) {
|
||||
+ VIR_ERROR0(_("client tried invalid PolicyKit init request"));
|
||||
+ goto authfail;
|
||||
+ }
|
||||
+
|
||||
+ if (qemudGetSocketIdentity(client->fd, &callerUid, &callerPid) < 0) {
|
||||
+ VIR_ERROR0(_("cannot get peer socket identity"));
|
||||
+ goto authfail;
|
||||
+ }
|
||||
+
|
||||
+ VIR_INFO(_("Checking PID %d running as %d"), callerPid, callerUid);
|
||||
+
|
||||
+ rv = snprintf(pidbuf, sizeof pidbuf, "%d", callerPid);
|
||||
+ if (rv < 0 || rv >= sizeof pidbuf) {
|
||||
+ VIR_ERROR(_("Caller PID was too large %d"), callerPid);
|
||||
+ goto authfail;
|
||||
+ }
|
||||
+
|
||||
+ if (virRun(NULL, pkcheck, &status) < 0) {
|
||||
+ VIR_ERROR(_("Cannot invoke %s"), PKCHECK_PATH);
|
||||
+ goto authfail;
|
||||
+ }
|
||||
+ if (status != 0) {
|
||||
+ VIR_ERROR(_("Policy kit denied action %s from pid %d, uid %d, result: %d\n"),
|
||||
+ action, callerPid, callerUid, status);
|
||||
+ goto authfail;
|
||||
+ }
|
||||
+ VIR_INFO(_("Policy allowed action %s from pid %d, uid %d"),
|
||||
+ action, callerPid, callerUid);
|
||||
+ ret->complete = 1;
|
||||
+ client->auth = REMOTE_AUTH_NONE;
|
||||
+
|
||||
+ virMutexUnlock(&client->lock);
|
||||
+ return 0;
|
||||
+
|
||||
+authfail:
|
||||
+ remoteDispatchAuthError(rerr);
|
||||
+ virMutexUnlock(&client->lock);
|
||||
+ return -1;
|
||||
+}
|
||||
+#elif HAVE_POLKIT0
|
||||
static int
|
||||
remoteDispatchAuthPolkit (struct qemud_server *server,
|
||||
struct qemud_client *client,
|
||||
@@ -3217,7 +3290,7 @@ authfail:
|
||||
return -1;
|
||||
}
|
||||
|
||||
-#else /* HAVE_POLKIT */
|
||||
+#else /* !HAVE_POLKIT0 & !HAVE_POLKIT1*/
|
||||
|
||||
static int
|
||||
remoteDispatchAuthPolkit (struct qemud_server *server ATTRIBUTE_UNUSED,
|
||||
@@ -3231,7 +3304,7 @@ remoteDispatchAuthPolkit (struct qemud_server *server ATTRIBUTE_UNUSED,
|
||||
remoteDispatchAuthError(rerr);
|
||||
return -1;
|
||||
}
|
||||
-#endif /* HAVE_POLKIT */
|
||||
+#endif /* HAVE_POLKIT1 */
|
||||
|
||||
|
||||
/***************************************************************
|
||||
diff --git a/src/remote_internal.c b/src/remote_internal.c
|
||||
index a58b768..e98c99b 100644
|
||||
--- a/src/remote_internal.c
|
||||
+++ b/src/remote_internal.c
|
||||
@@ -6201,6 +6201,7 @@ remoteAuthPolkit (virConnectPtr conn, struct private_data *priv, int in_open,
|
||||
virConnectAuthPtr auth)
|
||||
{
|
||||
remote_auth_polkit_ret ret;
|
||||
+#if HAVE_POLKIT0
|
||||
int i, allowcb = 0;
|
||||
virConnectCredential cred = {
|
||||
VIR_CRED_EXTERNAL,
|
||||
@@ -6210,8 +6211,10 @@ remoteAuthPolkit (virConnectPtr conn, struct private_data *priv, int in_open,
|
||||
NULL,
|
||||
0,
|
||||
};
|
||||
+#endif
|
||||
DEBUG0("Client initialize PolicyKit authentication");
|
||||
|
||||
+#if HAVE_POLKIT0
|
||||
if (auth && auth->cb) {
|
||||
/* Check if the necessary credential type for PolicyKit is supported */
|
||||
for (i = 0 ; i < auth->ncredtype ; i++) {
|
||||
@@ -6220,6 +6223,7 @@ remoteAuthPolkit (virConnectPtr conn, struct private_data *priv, int in_open,
|
||||
}
|
||||
|
||||
if (allowcb) {
|
||||
+ DEBUG0("Client run callback for PolicyKit authentication");
|
||||
/* Run the authentication callback */
|
||||
if ((*(auth->cb))(&cred, 1, auth->cbdata) < 0) {
|
||||
virRaiseError (in_open ? NULL : conn, NULL, NULL, VIR_FROM_REMOTE,
|
||||
@@ -6233,6 +6237,9 @@ remoteAuthPolkit (virConnectPtr conn, struct private_data *priv, int in_open,
|
||||
} else {
|
||||
DEBUG0("No auth callback provided");
|
||||
}
|
||||
+#else
|
||||
+ DEBUG0("No auth callback required for PolicyKit-1");
|
||||
+#endif
|
||||
|
||||
memset (&ret, 0, sizeof ret);
|
||||
if (call (conn, priv, in_open, REMOTE_PROC_AUTH_POLKIT,
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,122 @@
|
||||
diff -rup libvirt-0.7.1/qemud/libvirtd.init.in audio/qemud/libvirtd.init.in
|
||||
--- libvirt-0.7.1/qemud/libvirtd.init.in 2009-07-22 09:37:32.000000000 -0400
|
||||
+++ audio/qemud/libvirtd.init.in 2010-05-26 12:05:50.584822000 -0400
|
||||
@@ -47,6 +47,9 @@ KRB5_KTNAME=/etc/libvirt/krb5.tab
|
||||
|
||||
test -f @sysconfdir@/sysconfig/libvirtd && . @sysconfdir@/sysconfig/libvirtd
|
||||
|
||||
+export QEMU_AUDIO_DRV
|
||||
+export SDL_AUDIODRIVER
|
||||
+
|
||||
LIBVIRTD_CONFIG_ARGS=
|
||||
if [ -n "$LIBVIRTD_CONFIG" ]
|
||||
then
|
||||
diff -rup libvirt-0.7.1/qemud/libvirtd_qemu.aug audio/qemud/libvirtd_qemu.aug
|
||||
--- libvirt-0.7.1/qemud/libvirtd_qemu.aug 2009-09-08 10:16:02.000000000 -0400
|
||||
+++ audio/qemud/libvirtd_qemu.aug 2010-05-26 12:07:24.169216000 -0400
|
||||
@@ -36,6 +36,7 @@ module Libvirtd_qemu =
|
||||
| str_array_entry "cgroup_device_acl"
|
||||
| str_entry "save_image_format"
|
||||
| str_entry "hugetlbfs_mount"
|
||||
+ | bool_entry "vnc_allow_host_audio"
|
||||
|
||||
(* Each enty in the config is one of the following three ... *)
|
||||
let entry = vnc_entry
|
||||
diff -rup libvirt-0.7.1/qemud/libvirtd.sysconf audio/qemud/libvirtd.sysconf
|
||||
--- libvirt-0.7.1/qemud/libvirtd.sysconf 2010-05-26 12:04:08.379130000 -0400
|
||||
+++ audio/qemud/libvirtd.sysconf 2010-05-26 12:10:28.263486000 -0400
|
||||
@@ -11,7 +11,8 @@
|
||||
# Override the QEMU/SDL default audio driver probing when
|
||||
# starting virtual machines using SDL graphics
|
||||
#
|
||||
-# NB these have no effect for VMs using VNC
|
||||
+# NB these have no effect for VMs using VNC, unless vnc_allow_host_audio
|
||||
+# is enabled in /etc/libvirt/qemu.conf
|
||||
#QEMU_AUDIO_DRV=sdl
|
||||
#
|
||||
#SDL_AUDIODRIVER=pulse
|
||||
diff -rup libvirt-0.7.1/qemud/test_libvirtd_qemu.aug audio/qemud/test_libvirtd_qemu.aug
|
||||
--- libvirt-0.7.1/qemud/test_libvirtd_qemu.aug 2009-09-08 10:16:02.000000000 -0400
|
||||
+++ audio/qemud/test_libvirtd_qemu.aug 2010-05-26 12:11:19.540907000 -0400
|
||||
@@ -92,6 +92,8 @@ cgroup_device_acl = [ \"/dev/null\", \"/
|
||||
|
||||
save_image_format = \"gzip\"
|
||||
|
||||
+vnc_allow_host_audio = 1
|
||||
+
|
||||
hugetlbfs_mount = \"/dev/hugepages\"
|
||||
"
|
||||
|
||||
@@ -195,4 +197,6 @@ hugetlbfs_mount = \"/dev/hugepages\"
|
||||
{ "#empty" }
|
||||
{ "save_image_format" = "gzip" }
|
||||
{ "#empty" }
|
||||
-{ "hugetlbfs_mount" = "/dev/hugepages" }
|
||||
\ No newline at end of file
|
||||
+{ "hugetlbfs_mount" = "/dev/hugepages" }
|
||||
+{ "#empty" }
|
||||
+{ "vnc_allow_host_audio" = "1" }
|
||||
diff -rup libvirt-0.7.1/src/qemu.conf audio/src/qemu.conf
|
||||
--- libvirt-0.7.1/src/qemu.conf 2009-09-10 05:15:56.000000000 -0400
|
||||
+++ audio/src/qemu.conf 2010-05-26 12:08:12.419811000 -0400
|
||||
@@ -152,3 +152,13 @@
|
||||
# in a location of $MOUNTPOINT/libvirt/qemu
|
||||
|
||||
# hugetlbfs_mount = "/dev/hugepages"
|
||||
+#
|
||||
+
|
||||
+# QEMU implements an extension for providing audio over a VNC connection,
|
||||
+# though if your VNC client does not support it, your only chance for getting
|
||||
+# sound output is through regular audio backends. By default, libvirt will
|
||||
+# disable all QEMU sound backends if using VNC, since they can cause
|
||||
+# permissions issues. Enabling this option will make libvirtd honor the
|
||||
+# QEMU_AUDIO_DRV environment variable when using VNC.
|
||||
+#
|
||||
+# vnc_allow_host_audio = 0
|
||||
diff -rup libvirt-0.7.1/src/qemu_conf.c audio/src/qemu_conf.c
|
||||
--- libvirt-0.7.1/src/qemu_conf.c 2010-05-26 12:04:08.578062000 -0400
|
||||
+++ audio/src/qemu_conf.c 2010-05-26 12:09:31.174206000 -0400
|
||||
@@ -318,6 +318,10 @@ int qemudLoadDriverConfig(struct qemud_d
|
||||
}
|
||||
}
|
||||
|
||||
+ p = virConfGetValue (conf, "vnc_allow_host_audio");
|
||||
+ CHECK_TYPE ("vnc_allow_host_audio", VIR_CONF_LONG);
|
||||
+ if (p) driver->vncAllowHostAudio = p->l;
|
||||
+
|
||||
virConfFree (conf);
|
||||
return 0;
|
||||
}
|
||||
@@ -2113,12 +2117,15 @@ int qemudBuildCommandLine(virConnectPtr
|
||||
ADD_ARG_LIT(def->graphics[0]->data.vnc.keymap);
|
||||
}
|
||||
|
||||
- /* QEMU implements a VNC extension for providing audio, so we
|
||||
- * set the audio backend to none, to prevent it opening the
|
||||
- * host OS audio devices since that causes security issues
|
||||
- * and is non-sensical when using VNC.
|
||||
+ /* Unless user requested it, set the audio backend to none, to
|
||||
+ * prevent it opening the host OS audio devices, since that causes
|
||||
+ * security issues and might not work when using VNC.
|
||||
*/
|
||||
- ADD_ENV_LIT("QEMU_AUDIO_DRV=none");
|
||||
+ if (driver->vncAllowHostAudio) {
|
||||
+ ADD_ENV_COPY("QEMU_AUDIO_DRV");
|
||||
+ } else {
|
||||
+ ADD_ENV_LIT("QEMU_AUDIO_DRV=none");
|
||||
+ }
|
||||
} else if ((def->ngraphics == 1) &&
|
||||
def->graphics[0]->type == VIR_DOMAIN_GRAPHICS_TYPE_SDL) {
|
||||
char *xauth = NULL;
|
||||
diff -rup libvirt-0.7.1/src/qemu_conf.h audio/src/qemu_conf.h
|
||||
--- libvirt-0.7.1/src/qemu_conf.h 2009-09-10 09:45:00.000000000 -0400
|
||||
+++ audio/src/qemu_conf.h 2010-05-26 12:10:07.196992000 -0400
|
||||
@@ -110,6 +110,8 @@ struct qemud_driver {
|
||||
char *hugetlbfs_mount;
|
||||
char *hugepage_path;
|
||||
|
||||
+ unsigned int vncAllowHostAudio : 1;
|
||||
+
|
||||
virCapsPtr caps;
|
||||
|
||||
/* An array of callbacks */
|
||||
@@ -0,0 +1,99 @@
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-06-17 11:30:54.501983000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-06-17 11:20:13.032900000 -0400
|
||||
@@ -69,7 +69,7 @@
|
||||
#include "hostusb.h"
|
||||
#include "security.h"
|
||||
#include "cgroup.h"
|
||||
-
|
||||
+#include "storage_file.h"
|
||||
|
||||
#define VIR_FROM_THIS VIR_FROM_QEMU
|
||||
|
||||
@@ -1895,6 +1895,7 @@ static int qemuDomainSetDeviceOwnership(
|
||||
{
|
||||
uid_t uid;
|
||||
gid_t gid;
|
||||
+ const char *path;
|
||||
|
||||
if (!driver->privileged)
|
||||
return 0;
|
||||
@@ -1912,6 +1913,35 @@ static int qemuDomainSetDeviceOwnership(
|
||||
(def->data.disk->readonly || def->data.disk->shared))
|
||||
return 0;
|
||||
|
||||
+ if (!def->data.disk->src)
|
||||
+ return 0;
|
||||
+
|
||||
+ path = def->data.disk->src;
|
||||
+ do {
|
||||
+ virStorageFileMetadata meta;
|
||||
+ int ret;
|
||||
+
|
||||
+ memset(&meta, 0, sizeof(meta));
|
||||
+
|
||||
+ ret = virStorageFileGetMetadata(conn, path, &meta);
|
||||
+
|
||||
+ if (path != def->data.disk->src)
|
||||
+ VIR_FREE(path);
|
||||
+ path = NULL;
|
||||
+
|
||||
+ if (ret < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ if (meta.backingStore != NULL &&
|
||||
+ qemuDomainSetFileOwnership(conn,
|
||||
+ meta.backingStore, uid, gid) < 0) {
|
||||
+ VIR_FREE(meta.backingStore);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ path = meta.backingStore;
|
||||
+ } while (path != NULL);
|
||||
+
|
||||
return qemuDomainSetFileOwnership(conn, def->data.disk->src, uid, gid);
|
||||
|
||||
case VIR_DOMAIN_DEVICE_HOSTDEV:
|
||||
@@ -1929,6 +1959,7 @@ static int qemuDomainSetAllDeviceOwnersh
|
||||
int i;
|
||||
uid_t uid;
|
||||
gid_t gid;
|
||||
+ const char *path;
|
||||
|
||||
if (!driver->privileged)
|
||||
return 0;
|
||||
@@ -1949,6 +1980,35 @@ static int qemuDomainSetAllDeviceOwnersh
|
||||
(def->disks[i]->readonly || def->disks[i]->shared))
|
||||
continue;
|
||||
|
||||
+ if (!def->disks[i]->src)
|
||||
+ continue;
|
||||
+
|
||||
+ path = def->disks[i]->src;
|
||||
+ do {
|
||||
+ virStorageFileMetadata meta;
|
||||
+ int ret;
|
||||
+
|
||||
+ memset(&meta, 0, sizeof(meta));
|
||||
+
|
||||
+ ret = virStorageFileGetMetadata(conn, path, &meta);
|
||||
+
|
||||
+ if (path != def->disks[i]->src)
|
||||
+ VIR_FREE(path);
|
||||
+ path = NULL;
|
||||
+
|
||||
+ if (ret < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ if (meta.backingStore != NULL &&
|
||||
+ qemuDomainSetFileOwnership(conn,
|
||||
+ meta.backingStore, uid, gid) < 0) {
|
||||
+ VIR_FREE(meta.backingStore);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ path = meta.backingStore;
|
||||
+ } while (path != NULL);
|
||||
+
|
||||
if (qemuDomainSetFileOwnership(conn, def->disks[i]->src, uid, gid) < 0)
|
||||
return -1;
|
||||
}
|
||||
@@ -0,0 +1,82 @@
|
||||
diff -rup libvirt-0.7.1/src/qemu.conf new/src/qemu.conf
|
||||
--- libvirt-0.7.1/src/qemu.conf 2010-06-03 15:01:14.288848000 -0400
|
||||
+++ new/src/qemu.conf 2010-06-03 15:04:05.062031000 -0400
|
||||
@@ -162,3 +162,12 @@
|
||||
# QEMU_AUDIO_DRV environment variable when using VNC.
|
||||
#
|
||||
# vnc_allow_host_audio = 0
|
||||
+
|
||||
+# If clear_emulator_capabilities is enabled, libvirt will drop all
|
||||
+# privileged capabilities of the QEmu/KVM emulator. This is enabled by
|
||||
+# default.
|
||||
+#
|
||||
+# Warning: Disabling this option means that a compromised guest can
|
||||
+# exploit the privileges and possibly do damage to the host.
|
||||
+#
|
||||
+# clear_emulator_capabilities = 1
|
||||
diff -rup libvirt-0.7.1/src/qemu_conf.c new/src/qemu_conf.c
|
||||
--- libvirt-0.7.1/src/qemu_conf.c 2010-06-03 15:01:14.302852000 -0400
|
||||
+++ new/src/qemu_conf.c 2010-06-03 15:05:09.755183000 -0400
|
||||
@@ -98,7 +98,9 @@ int qemudLoadDriverConfig(struct qemud_d
|
||||
char *group;
|
||||
int i;
|
||||
|
||||
- /* Setup 2 critical defaults */
|
||||
+ /* Setup critical defaults */
|
||||
+ driver->clearEmulatorCapabilities = 1;
|
||||
+
|
||||
if (!(driver->vncListen = strdup("127.0.0.1"))) {
|
||||
virReportOOMError(NULL);
|
||||
return -1;
|
||||
@@ -322,6 +324,10 @@ int qemudLoadDriverConfig(struct qemud_d
|
||||
CHECK_TYPE ("vnc_allow_host_audio", VIR_CONF_LONG);
|
||||
if (p) driver->vncAllowHostAudio = p->l;
|
||||
|
||||
+ p = virConfGetValue (conf, "clear_emulator_capabilities");
|
||||
+ CHECK_TYPE ("clear_emulator_capabilities", VIR_CONF_LONG);
|
||||
+ if (p) driver->clearEmulatorCapabilities = p->l;
|
||||
+
|
||||
virConfFree (conf);
|
||||
return 0;
|
||||
}
|
||||
diff -rup libvirt-0.7.1/src/qemu_conf.h new/src/qemu_conf.h
|
||||
--- libvirt-0.7.1/src/qemu_conf.h 2010-06-03 15:01:14.306860000 -0400
|
||||
+++ new/src/qemu_conf.h 2010-06-03 15:05:27.968796000 -0400
|
||||
@@ -111,6 +111,7 @@ struct qemud_driver {
|
||||
char *hugepage_path;
|
||||
|
||||
unsigned int vncAllowHostAudio : 1;
|
||||
+ unsigned int clearEmulatorCapabilities : 1;
|
||||
|
||||
virCapsPtr caps;
|
||||
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-06-03 15:01:14.413848000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-06-03 15:06:08.186798000 -0400
|
||||
@@ -2063,7 +2063,7 @@ static int qemudStartVMDaemon(virConnect
|
||||
int stdin_fd) {
|
||||
const char **argv = NULL, **tmp;
|
||||
const char **progenv = NULL;
|
||||
- int i, ret;
|
||||
+ int i, ret, runflags;
|
||||
struct stat sb;
|
||||
int *tapfds = NULL;
|
||||
int ntapfds = 0;
|
||||
@@ -2205,9 +2205,16 @@ static int qemudStartVMDaemon(virConnect
|
||||
for (i = 0 ; i < ntapfds ; i++)
|
||||
FD_SET(tapfds[i], &keepfd);
|
||||
|
||||
+ VIR_DEBUG("Clear emulator capabilities: %d",
|
||||
+ driver->clearEmulatorCapabilities);
|
||||
+ runflags = VIR_EXEC_NONBLOCK;
|
||||
+ if (driver->clearEmulatorCapabilities) {
|
||||
+ runflags |= VIR_EXEC_CLEAR_CAPS;
|
||||
+ }
|
||||
+
|
||||
ret = virExecDaemonize(conn, argv, progenv, &keepfd, &child,
|
||||
stdin_fd, &logfile, &logfile,
|
||||
- VIR_EXEC_NONBLOCK | VIR_EXEC_CLEAR_CAPS,
|
||||
+ runflags,
|
||||
qemudSecurityHook, &hookData,
|
||||
pidfile);
|
||||
VIR_FREE(pidfile);
|
||||
@@ -0,0 +1,12 @@
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-06-03 13:51:14.398483000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-06-03 13:56:05.667092000 -0400
|
||||
@@ -5988,7 +5988,7 @@ static int qemudDomainAttachDevice(virDo
|
||||
virDomainDiskDeviceTypeToString(dev->data.disk->device));
|
||||
/* Fallthrough */
|
||||
}
|
||||
- if (ret != 0) {
|
||||
+ if (ret != 0 && cgroup) {
|
||||
virCgroupDenyDevicePath(cgroup,
|
||||
dev->data.disk->src);
|
||||
}
|
||||
@@ -0,0 +1,267 @@
|
||||
commit bc0010b3d149df00406b82c37eb59874d8525af4
|
||||
Author: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Wed Nov 11 12:07:00 2009 +0000
|
||||
|
||||
Fix save and restore with non-privileged guests and SELinux
|
||||
|
||||
When running qemu:///system instance, libvirtd runs as root,
|
||||
but QEMU may optionally be configured to run non-root. When
|
||||
then saving a guest to a state file, the file is initially
|
||||
created as root, and thus QEMU cannot write to it. It is also
|
||||
missing labelling required to allow access via SELinux.
|
||||
|
||||
* src/qemu_driver.c: Set ownership on save image before
|
||||
running migrate command in virDomainSave impl. Call out to
|
||||
security driver to set save image labelling
|
||||
* src/security.h: Add driver APIs for setting
|
||||
and restoring saved state file labelling
|
||||
* src/security_selinux.c: Implement saved state file
|
||||
labelling for SELinux
|
||||
|
||||
diff --git a/src/security.h b/src/security.h
|
||||
index fde2978..5514962 100644
|
||||
--- a/src/security.h
|
||||
+++ b/src/security.h
|
||||
@@ -42,6 +42,11 @@ typedef int (*virSecurityDomainRestoreHostdevLabel) (virConnectPtr conn,
|
||||
typedef int (*virSecurityDomainSetHostdevLabel) (virConnectPtr conn,
|
||||
virDomainObjPtr vm,
|
||||
virDomainHostdevDefPtr dev);
|
||||
+typedef int (*virSecurityDomainSetSavedStateLabel) (virConnectPtr conn,
|
||||
+ virDomainObjPtr vm,
|
||||
+ const char *savefile);
|
||||
+typedef int (*virSecurityDomainRestoreSavedStateLabel) (virConnectPtr conn,
|
||||
+ const char *savefile);
|
||||
typedef int (*virSecurityDomainGenLabel) (virConnectPtr conn,
|
||||
virDomainObjPtr sec);
|
||||
typedef int (*virSecurityDomainReserveLabel) (virConnectPtr conn,
|
||||
@@ -71,6 +76,8 @@ struct _virSecurityDriver {
|
||||
virSecurityDomainRestoreLabel domainRestoreSecurityLabel;
|
||||
virSecurityDomainRestoreHostdevLabel domainRestoreSecurityHostdevLabel;
|
||||
virSecurityDomainSetHostdevLabel domainSetSecurityHostdevLabel;
|
||||
+ virSecurityDomainSetSavedStateLabel domainSetSavedStateLabel;
|
||||
+ virSecurityDomainRestoreSavedStateLabel domainRestoreSavedStateLabel;
|
||||
|
||||
/*
|
||||
* This is internally managed driver state and should only be accessed
|
||||
diff --git a/src/security_selinux.c b/src/security_selinux.c
|
||||
index 0e31077..bd838e6 100644
|
||||
--- a/src/security_selinux.c
|
||||
+++ b/src/security_selinux.c
|
||||
@@ -523,6 +523,7 @@ done:
|
||||
return ret;
|
||||
}
|
||||
|
||||
+
|
||||
static int
|
||||
SELinuxRestoreSecurityPCILabel(virConnectPtr conn,
|
||||
pciDevice *dev ATTRIBUTE_UNUSED,
|
||||
@@ -623,6 +624,26 @@ SELinuxRestoreSecurityLabel(virConnectPtr conn,
|
||||
return rc;
|
||||
}
|
||||
|
||||
+
|
||||
+static int
|
||||
+SELinuxSetSavedStateLabel(virConnectPtr conn,
|
||||
+ virDomainObjPtr vm,
|
||||
+ const char *savefile)
|
||||
+{
|
||||
+ const virSecurityLabelDefPtr secdef = &vm->def->seclabel;
|
||||
+
|
||||
+ return SELinuxSetFilecon(conn, savefile, secdef->imagelabel);
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static int
|
||||
+SELinuxRestoreSavedStateLabel(virConnectPtr conn,
|
||||
+ const char *savefile)
|
||||
+{
|
||||
+ return SELinuxRestoreSecurityFileLabel(conn, savefile);
|
||||
+}
|
||||
+
|
||||
+
|
||||
static int
|
||||
SELinuxSecurityVerify(virConnectPtr conn, virDomainDefPtr def)
|
||||
{
|
||||
@@ -692,4 +713,6 @@ virSecurityDriver virSELinuxSecurityDriver = {
|
||||
.domainSetSecurityLabel = SELinuxSetSecurityLabel,
|
||||
.domainSetSecurityHostdevLabel = SELinuxSetSecurityHostdevLabel,
|
||||
.domainRestoreSecurityHostdevLabel = SELinuxRestoreSecurityHostdevLabel,
|
||||
+ .domainSetSavedStateLabel = SELinuxSetSavedStateLabel,
|
||||
+ .domainRestoreSavedStateLabel = SELinuxRestoreSavedStateLabel,
|
||||
};
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-05-17 16:28:38.243890000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-05-17 16:36:28.035091000 -0400
|
||||
@@ -3907,6 +3907,20 @@ static int qemudDomainSave(virDomainPtr
|
||||
}
|
||||
fd = -1;
|
||||
|
||||
+ if (driver->privileged &&
|
||||
+ chown(path, driver->user, driver->group) < 0) {
|
||||
+ virReportSystemError(NULL, errno,
|
||||
+ _("unable to set ownership of '%s' to user %d:%d"),
|
||||
+ path, driver->user, driver->group);
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
+ if (driver->securityDriver &&
|
||||
+ driver->securityDriver->domainSetSavedStateLabel &&
|
||||
+ driver->securityDriver->domainSetSavedStateLabel(dom->conn, vm, path) == -1)
|
||||
+ goto cleanup;
|
||||
+
|
||||
+
|
||||
/* Migrate to file */
|
||||
safe_path = qemudEscapeShellArg(path);
|
||||
if (!safe_path) {
|
||||
@@ -3956,6 +3970,20 @@ static int qemudDomainSave(virDomainPtr
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
+ if (driver->privileged &&
|
||||
+ chown(path, 0, 0) < 0) {
|
||||
+ virReportSystemError(NULL, errno,
|
||||
+ _("unable to set ownership of '%s' to user %d:%d"),
|
||||
+ path, 0, 0);
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
+ if (driver->securityDriver &&
|
||||
+ driver->securityDriver->domainRestoreSavedStateLabel &&
|
||||
+ driver->securityDriver->domainRestoreSavedStateLabel(dom->conn, path) == -1)
|
||||
+ VIR_WARN("failed to restore save state label on %s", path);
|
||||
+
|
||||
+
|
||||
/* Shut it down */
|
||||
qemudShutdownVMDaemon(dom->conn, driver, vm);
|
||||
event = virDomainEventNewFromObj(vm,
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-05-17 17:55:34.000000000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-05-18 11:45:29.903145000 -0400
|
||||
@@ -4028,7 +4028,7 @@ static int qemudDomainSave(virDomainPtr
|
||||
|
||||
if (driver->securityDriver &&
|
||||
driver->securityDriver->domainRestoreSavedStateLabel &&
|
||||
- driver->securityDriver->domainRestoreSavedStateLabel(dom->conn, path) == -1)
|
||||
+ driver->securityDriver->domainRestoreSavedStateLabel(dom->conn, vm, path) == -1)
|
||||
VIR_WARN("failed to restore save state label on %s", path);
|
||||
|
||||
|
||||
@@ -4616,6 +4616,11 @@ static int qemudDomainRestore(virConnect
|
||||
}
|
||||
def = NULL;
|
||||
|
||||
+ if (driver->securityDriver &&
|
||||
+ driver->securityDriver->domainSetSavedStateLabelRO &&
|
||||
+ driver->securityDriver->domainSetSavedStateLabelRO(conn, vm, path) == -1)
|
||||
+ goto cleanup;
|
||||
+
|
||||
if (header.version == 2) {
|
||||
const char *intermediate_argv[3] = { NULL, "-dc", NULL };
|
||||
const char *prog = qemudSaveCompressionTypeToString(header.compressed);
|
||||
@@ -4651,11 +4656,6 @@ static int qemudDomainRestore(virConnect
|
||||
close(fd);
|
||||
fd = -1;
|
||||
if (ret < 0) {
|
||||
- if (!vm->persistent) {
|
||||
- virDomainRemoveInactive(&driver->domains,
|
||||
- vm);
|
||||
- vm = NULL;
|
||||
- }
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
@@ -4677,6 +4677,19 @@ static int qemudDomainRestore(virConnect
|
||||
ret = 0;
|
||||
|
||||
cleanup:
|
||||
+ if (ret < 0) {
|
||||
+ if (!vm->persistent) {
|
||||
+ virDomainRemoveInactive(&driver->domains,
|
||||
+ vm);
|
||||
+ vm = NULL;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ if (driver->securityDriver &&
|
||||
+ driver->securityDriver->domainRestoreSavedStateLabel &&
|
||||
+ driver->securityDriver->domainRestoreSavedStateLabel(conn, vm, path) == -1)
|
||||
+ VIR_WARN("Unable to restore labelling on %s", path);
|
||||
+
|
||||
virDomainDefFree(def);
|
||||
VIR_FREE(xml);
|
||||
if (fd != -1)
|
||||
diff -rup libvirt-0.7.1/src/security.h new/src/security.h
|
||||
--- libvirt-0.7.1/src/security.h 2010-05-17 17:55:34.000000000 -0400
|
||||
+++ new/src/security.h 2010-05-18 11:41:27.703746000 -0400
|
||||
@@ -44,7 +44,11 @@ typedef int (*virSecurityDomainSetHostde
|
||||
typedef int (*virSecurityDomainSetSavedStateLabel) (virConnectPtr conn,
|
||||
virDomainObjPtr vm,
|
||||
const char *savefile);
|
||||
+typedef int (*virSecurityDomainSetSavedStateLabelRO) (virConnectPtr conn,
|
||||
+ virDomainObjPtr vm,
|
||||
+ const char *savefile);
|
||||
typedef int (*virSecurityDomainRestoreSavedStateLabel) (virConnectPtr conn,
|
||||
+ virDomainObjPtr vm,
|
||||
const char *savefile);
|
||||
typedef int (*virSecurityDomainGenLabel) (virConnectPtr conn,
|
||||
virDomainObjPtr sec);
|
||||
@@ -76,6 +80,7 @@ struct _virSecurityDriver {
|
||||
virSecurityDomainRestoreHostdevLabel domainRestoreSecurityHostdevLabel;
|
||||
virSecurityDomainSetHostdevLabel domainSetSecurityHostdevLabel;
|
||||
virSecurityDomainSetSavedStateLabel domainSetSavedStateLabel;
|
||||
+ virSecurityDomainSetSavedStateLabelRO domainSetSavedStateLabelRO;
|
||||
virSecurityDomainRestoreSavedStateLabel domainRestoreSavedStateLabel;
|
||||
|
||||
/*
|
||||
diff -rup libvirt-0.7.1/src/security_selinux.c new/src/security_selinux.c
|
||||
--- libvirt-0.7.1/src/security_selinux.c 2010-05-17 17:55:34.000000000 -0400
|
||||
+++ new/src/security_selinux.c 2010-05-18 11:49:24.542106000 -0400
|
||||
@@ -364,12 +364,20 @@ SELinuxRestoreSecurityFileLabel(virConne
|
||||
goto err;
|
||||
}
|
||||
|
||||
- if (stat(newpath, &buf) != 0)
|
||||
+ if (stat(newpath, &buf) != 0) {
|
||||
+ virReportSystemError(conn, err,
|
||||
+ _("cannot stat %s"), newpath);
|
||||
goto err;
|
||||
+ }
|
||||
|
||||
- if (matchpathcon(newpath, buf.st_mode, &fcon) == 0) {
|
||||
- rc = SELinuxSetFilecon(conn, newpath, fcon);
|
||||
+ if (matchpathcon(newpath, buf.st_mode, &fcon) != 0) {
|
||||
+ virReportSystemError(conn, err,
|
||||
+ _("failed to determine default context for %s"), newpath);
|
||||
+ goto err;
|
||||
}
|
||||
+
|
||||
+ rc = SELinuxSetFilecon(conn, newpath, fcon);
|
||||
+
|
||||
err:
|
||||
VIR_FREE(fcon);
|
||||
VIR_FREE(newpath);
|
||||
@@ -632,7 +640,17 @@ SELinuxSetSavedStateLabel(virConnectPtr
|
||||
|
||||
|
||||
static int
|
||||
+SELinuxSetSavedStateLabelRO(virConnectPtr conn,
|
||||
+ virDomainObjPtr vm ATTRIBUTE_UNUSED,
|
||||
+ const char *savefile)
|
||||
+{
|
||||
+ return SELinuxSetFilecon(conn, savefile, default_content_context);
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static int
|
||||
SELinuxRestoreSavedStateLabel(virConnectPtr conn,
|
||||
+ virDomainObjPtr vm ATTRIBUTE_UNUSED,
|
||||
const char *savefile)
|
||||
{
|
||||
return SELinuxRestoreSecurityFileLabel(conn, savefile);
|
||||
@@ -709,5 +727,6 @@ virSecurityDriver virSELinuxSecurityDriv
|
||||
.domainSetSecurityHostdevLabel = SELinuxSetSecurityHostdevLabel,
|
||||
.domainRestoreSecurityHostdevLabel = SELinuxRestoreSecurityHostdevLabel,
|
||||
.domainSetSavedStateLabel = SELinuxSetSavedStateLabel,
|
||||
+ .domainSetSavedStateLabelRO = SELinuxSetSavedStateLabelRO,
|
||||
.domainRestoreSavedStateLabel = SELinuxRestoreSavedStateLabel,
|
||||
};
|
||||
@@ -0,0 +1,22 @@
|
||||
commit 823a684f8d0495bd5e7b413e1a81fd5a600abef7
|
||||
Author: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Thu Feb 11 14:39:13 2010 +0000
|
||||
|
||||
Fix USB device path formatting mixup
|
||||
|
||||
* src/util/hostusb.c: The device path for a USB device wants the
|
||||
bus/device IDs in decimal not octal
|
||||
|
||||
diff --git a/src/util/hostusb.c b/src/util/hostusb.c
|
||||
index 3cce66b..bf96539 100644
|
||||
--- a/src/hostusb.c
|
||||
+++ b/src/hostusb.c
|
||||
@@ -184,7 +184,7 @@ usbGetDevice(unsigned bus,
|
||||
snprintf(dev->name, sizeof(dev->name), "%.3o:%.3o",
|
||||
dev->bus, dev->dev);
|
||||
snprintf(dev->path, sizeof(dev->path),
|
||||
- USB_DEVFS "%03o/%03o", dev->bus, dev->dev);
|
||||
+ USB_DEVFS "%03d/%03d", dev->bus, dev->dev);
|
||||
|
||||
/* XXX fixme. this should be product/vendor */
|
||||
snprintf(dev->id, sizeof(dev->id), "%d %d", dev->bus, dev->dev);
|
||||
@@ -0,0 +1,13 @@
|
||||
Only in new: qemu_driver.c
|
||||
diff -rup libvirt-0.7.1/src/hostusb.c new/src/hostusb.c
|
||||
--- libvirt-0.7.1/src/hostusb.c 2010-06-03 13:51:14.392459000 -0400
|
||||
+++ new/src/hostusb.c 2010-06-03 14:49:11.763379000 -0400
|
||||
@@ -123,7 +123,7 @@ static int usbFindBusByVendor(virConnect
|
||||
char *tmpstr = de->d_name;
|
||||
unsigned found_bus, found_addr;
|
||||
|
||||
- if (STREQ(de->d_name, "usb"))
|
||||
+ if (STRPREFIX(de->d_name, "usb"))
|
||||
tmpstr += 3;
|
||||
|
||||
if (virStrToLong_ui(tmpstr, &ignore, 10, &found_bus) < 0) {
|
||||
@@ -0,0 +1,496 @@
|
||||
diff -rup libvirt-0.7.1/src/hostusb.c new/src/hostusb.c
|
||||
--- libvirt-0.7.1/src/hostusb.c 2010-05-17 16:53:48.740748000 -0400
|
||||
+++ new/src/hostusb.c 2010-05-17 16:57:19.294731000 -0400
|
||||
@@ -37,9 +37,10 @@
|
||||
#include "util.h"
|
||||
#include "virterror_internal.h"
|
||||
|
||||
+#define USB_SYSFS "/sys/bus/usb"
|
||||
#define USB_DEVFS "/dev/bus/usb/"
|
||||
-#define USB_ID_LEN 10 /* "XXXX XXXX" */
|
||||
-#define USB_ADDR_LEN 8 /* "XXX:XXX" */
|
||||
+#define USB_ID_LEN 10 /* "1234 5678" */
|
||||
+#define USB_ADDR_LEN 8 /* "123:456" */
|
||||
|
||||
struct _usbDevice {
|
||||
unsigned bus;
|
||||
@@ -57,6 +58,101 @@ struct _usbDevice {
|
||||
virReportErrorHelper(conn, VIR_FROM_NONE, code, __FILE__, \
|
||||
__FUNCTION__, __LINE__, fmt)
|
||||
|
||||
+static int usbSysReadFile(virConnectPtr conn,
|
||||
+ const char *f_name, const char *d_name,
|
||||
+ int base, unsigned *value)
|
||||
+{
|
||||
+ int ret = -1, tmp;
|
||||
+ char *buf = NULL;
|
||||
+ char *filename = NULL;
|
||||
+ char *ignore = NULL;
|
||||
+
|
||||
+ tmp = virAsprintf(&filename, USB_SYSFS "/devices/%s/%s", d_name, f_name);
|
||||
+ if (tmp < 0) {
|
||||
+ virReportOOMError(conn);
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ if (virFileReadAll(filename, 1024, &buf) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ if (virStrToLong_ui(buf, &ignore, base, value) < 0) {
|
||||
+ usbReportError(conn, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Could not parse usb file %s"), filename);
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ ret = 0;
|
||||
+error:
|
||||
+ VIR_FREE(filename);
|
||||
+ VIR_FREE(buf);
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
+static int usbFindBusByVendor(virConnectPtr conn,
|
||||
+ unsigned vendor, unsigned product,
|
||||
+ unsigned *bus, unsigned *devno)
|
||||
+{
|
||||
+ DIR *dir = NULL;
|
||||
+ int ret = -1, found = 0;
|
||||
+ char *ignore = NULL;
|
||||
+ struct dirent *de;
|
||||
+
|
||||
+ dir = opendir(USB_SYSFS "/devices");
|
||||
+ if (!dir) {
|
||||
+ virReportSystemError(conn, errno,
|
||||
+ _("Could not open directory %s"),
|
||||
+ USB_SYSFS "/devices");
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ while ((de = readdir(dir))) {
|
||||
+ unsigned found_prod, found_vend;
|
||||
+ if (de->d_name[0] == '.' || strchr(de->d_name, ':'))
|
||||
+ continue;
|
||||
+
|
||||
+ if (usbSysReadFile(conn, "idVendor", de->d_name,
|
||||
+ 16, &found_vend) < 0)
|
||||
+ goto error;
|
||||
+ if (usbSysReadFile(conn, "idProduct", de->d_name,
|
||||
+ 16, &found_prod) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ if (found_prod == product && found_vend == vendor) {
|
||||
+ /* Lookup bus.addr info */
|
||||
+ char *tmpstr = de->d_name;
|
||||
+ unsigned found_bus, found_addr;
|
||||
+
|
||||
+ if (STREQ(de->d_name, "usb"))
|
||||
+ tmpstr += 3;
|
||||
+
|
||||
+ if (virStrToLong_ui(tmpstr, &ignore, 10, &found_bus) < 0) {
|
||||
+ usbReportError(conn, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Failed to parse dir name '%s'"),
|
||||
+ de->d_name);
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ if (usbSysReadFile(conn, "devnum", de->d_name,
|
||||
+ 10, &found_addr) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ *bus = found_bus;
|
||||
+ *devno = found_addr;
|
||||
+ found = 1;
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ if (!found)
|
||||
+ usbReportError(conn, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Did not find USB device %x:%x"), vendor, product);
|
||||
+ else
|
||||
+ ret = 0;
|
||||
+
|
||||
+error:
|
||||
+ return ret;
|
||||
+}
|
||||
|
||||
usbDevice *
|
||||
usbGetDevice(virConnectPtr conn,
|
||||
@@ -86,6 +182,21 @@ usbGetDevice(virConnectPtr conn,
|
||||
return dev;
|
||||
}
|
||||
|
||||
+
|
||||
+usbDevice *
|
||||
+usbFindDevice(unsigned vendor,
|
||||
+ unsigned product)
|
||||
+{
|
||||
+ unsigned bus = 0, devno = 0;
|
||||
+
|
||||
+ if (usbFindBusByVendor(vendor, product, &bus, &devno) < 0) {
|
||||
+ return NULL;
|
||||
+ }
|
||||
+
|
||||
+ return usbGetDevice(bus, devno);
|
||||
+}
|
||||
+
|
||||
+
|
||||
void
|
||||
usbFreeDevice(virConnectPtr conn ATTRIBUTE_UNUSED, usbDevice *dev)
|
||||
{
|
||||
@@ -93,6 +204,18 @@ usbFreeDevice(virConnectPtr conn ATTRIBU
|
||||
VIR_FREE(dev);
|
||||
}
|
||||
|
||||
+unsigned usbDeviceGetBus(usbDevice *dev)
|
||||
+{
|
||||
+ return dev->bus;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+unsigned usbDeviceGetDevno(usbDevice *dev)
|
||||
+{
|
||||
+ return dev->dev;
|
||||
+}
|
||||
+
|
||||
+
|
||||
|
||||
int usbDeviceFileIterate(virConnectPtr conn,
|
||||
usbDevice *dev,
|
||||
diff -rup libvirt-0.7.1/src/hostusb.h new/src/hostusb.h
|
||||
--- libvirt-0.7.1/src/hostusb.h 2009-09-10 09:45:00.000000000 -0400
|
||||
+++ new/src/hostusb.h 2010-05-17 16:58:06.553924000 -0400
|
||||
@@ -27,11 +27,16 @@
|
||||
|
||||
typedef struct _usbDevice usbDevice;
|
||||
|
||||
-usbDevice *usbGetDevice (virConnectPtr conn,
|
||||
- unsigned bus,
|
||||
- unsigned devno);
|
||||
-void usbFreeDevice (virConnectPtr conn,
|
||||
- usbDevice *dev);
|
||||
+usbDevice *usbGetDevice(virConnectPtr conn,
|
||||
+ unsigned bus,
|
||||
+ unsigned devno);
|
||||
+usbDevice *usbFindDevice(virConnectPtr conn,
|
||||
+ unsigned vendor,
|
||||
+ unsigned product);
|
||||
+void usbFreeDevice (virConnectPtr conn, usbDevice *dev);
|
||||
+
|
||||
+unsigned usbDeviceGetBus(usbDevice *dev);
|
||||
+unsigned usbDeviceGetDevno(usbDevice *dev);
|
||||
|
||||
/*
|
||||
* Callback that will be invoked once for each file
|
||||
diff -rup libvirt-0.7.1/src/libvirt_private.syms new/src/libvirt_private.syms
|
||||
--- libvirt-0.7.1/src/libvirt_private.syms 2010-05-17 16:53:48.401831000 -0400
|
||||
+++ new/src/libvirt_private.syms 2010-05-17 16:55:03.001748000 -0400
|
||||
@@ -441,7 +441,10 @@ virFileMatchesNameSuffix;
|
||||
|
||||
# usb.h
|
||||
usbGetDevice;
|
||||
+usbFindDevice;
|
||||
usbFreeDevice;
|
||||
+usbDeviceGetBus;
|
||||
+usbDeviceGetDevno;
|
||||
usbDeviceFileIterate;
|
||||
|
||||
# uuid.h
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-05-17 16:53:48.785743000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-05-17 17:06:40.575145000 -0400
|
||||
@@ -1493,16 +1493,13 @@ qemuUpdateActivePciHostdevs(struct qemud
|
||||
}
|
||||
|
||||
static int
|
||||
-qemuPrepareHostDevices(virConnectPtr conn,
|
||||
- struct qemud_driver *driver,
|
||||
- virDomainDefPtr def)
|
||||
+qemuPrepareHostPCIDevices(virConnectPtr conn,
|
||||
+ struct qemud_driver *driver,
|
||||
+ virDomainDefPtr def)
|
||||
{
|
||||
pciDeviceList *pcidevs;
|
||||
int i;
|
||||
|
||||
- if (!def->nhostdevs)
|
||||
- return 0;
|
||||
-
|
||||
if (!(pcidevs = qemuGetPciHostDeviceList(conn, def)))
|
||||
return -1;
|
||||
|
||||
@@ -1792,14 +1789,11 @@ static int qemuDomainSetHostdevUSBOwners
|
||||
struct qemuFileOwner owner = { uid, gid };
|
||||
int ret = -1;
|
||||
|
||||
- /* XXX what todo for USB devs assigned based on product/vendor ? Doom :-( */
|
||||
- if (!def->source.subsys.u.usb.bus ||
|
||||
- !def->source.subsys.u.usb.device)
|
||||
- return 0;
|
||||
-
|
||||
usbDevice *dev = usbGetDevice(conn,
|
||||
def->source.subsys.u.usb.bus,
|
||||
- def->source.subsys.u.usb.device);
|
||||
+ def->source.subsys.u.usb.device,
|
||||
+ def->source.subsys.u.usb.vendor,
|
||||
+ def->source.subsys.u.usb.product);
|
||||
|
||||
if (!dev)
|
||||
goto cleanup;
|
||||
@@ -2065,13 +2059,17 @@ static int qemudStartVMDaemon(virConnect
|
||||
return -1;
|
||||
}
|
||||
|
||||
+ DEBUG0("Preparing host devices");
|
||||
+ if (qemuPrepareHostDevices(conn, driver, vm->def) < 0)
|
||||
+ goto cleanup;
|
||||
+
|
||||
/* If you are using a SecurityDriver with dynamic labelling,
|
||||
then generate a security label for isolation */
|
||||
if (vm->def->seclabel.type == VIR_DOMAIN_SECLABEL_DYNAMIC &&
|
||||
driver->securityDriver &&
|
||||
driver->securityDriver->domainGenSecurityLabel &&
|
||||
driver->securityDriver->domainGenSecurityLabel(conn, vm) < 0)
|
||||
- return -1;
|
||||
+ return cleanup;
|
||||
|
||||
/* Ensure no historical cgroup for this VM is lieing around bogus settings */
|
||||
qemuRemoveCgroup(conn, driver, vm);
|
||||
@@ -2119,9 +2117,6 @@ static int qemudStartVMDaemon(virConnect
|
||||
if (qemuSetupCgroup(conn, driver, vm) < 0)
|
||||
goto cleanup;
|
||||
|
||||
- if (qemuPrepareHostDevices(conn, driver, vm->def) < 0)
|
||||
- goto cleanup;
|
||||
-
|
||||
if (VIR_ALLOC(vm->monitor_chr) < 0) {
|
||||
virReportOOMError(conn);
|
||||
goto cleanup;
|
||||
@@ -2348,6 +2343,56 @@ retry:
|
||||
}
|
||||
|
||||
|
||||
+
|
||||
+static int
|
||||
+qemuPrepareHostUSBDevices(struct qemud_driver *driver ATTRIBUTE_UNUSED,
|
||||
+ virDomainDefPtr def)
|
||||
+{
|
||||
+ int i;
|
||||
+ for (i = 0 ; i < def->nhostdevs ; i++) {
|
||||
+ virDomainHostdevDefPtr hostdev = def->hostdevs[i];
|
||||
+
|
||||
+ if (hostdev->mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS)
|
||||
+ continue;
|
||||
+ if (hostdev->source.subsys.type != VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB)
|
||||
+ continue;
|
||||
+
|
||||
+ /* Resolve a vendor/product to bus/device */
|
||||
+ if (hostdev->source.subsys.u.usb.vendor) {
|
||||
+ usbDevice *usb
|
||||
+ = usbFindDevice(hostdev->source.subsys.u.usb.vendor,
|
||||
+ hostdev->source.subsys.u.usb.product);
|
||||
+
|
||||
+ if (!usb)
|
||||
+ return -1;
|
||||
+
|
||||
+ hostdev->source.subsys.u.usb.bus = usbDeviceGetBus(usb);
|
||||
+ hostdev->source.subsys.u.usb.device = usbDeviceGetDevno(usb);
|
||||
+
|
||||
+ usbFreeDevice(usb);
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int
|
||||
+qemuPrepareHostDevices(struct qemud_driver *driver,
|
||||
+ virDomainDefPtr def)
|
||||
+{
|
||||
+ if (!def->nhostdevs)
|
||||
+ return 0;
|
||||
+
|
||||
+ if (qemuPrepareHostPCIDevices(driver, def) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ if (qemuPrepareHostUSBDevices(driver, def) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+
|
||||
static void
|
||||
qemudDispatchVMEvent(int watch, int fd, int events, void *opaque) {
|
||||
struct qemud_driver *driver = opaque;
|
||||
@@ -6294,6 +6339,23 @@ static int qemudDomainDetachHostDevice(v
|
||||
return -1;
|
||||
}
|
||||
|
||||
+ /* Resolve USB product/vendor to bus/device */
|
||||
+ if (hostdev->source.subsys.type == VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB &&
|
||||
+ hostdev->source.subsys.u.usb.vendor) {
|
||||
+ usbDevice *usb
|
||||
+ = usbFindDevice(hostdev->source.subsys.u.usb.vendor,
|
||||
+ hostdev->source.subsys.u.usb.product);
|
||||
+
|
||||
+ if (!usb)
|
||||
+ return -1;
|
||||
+
|
||||
+ hostdev->source.subsys.u.usb.bus = usbDeviceGetBus(usb);
|
||||
+ hostdev->source.subsys.u.usb.device = usbDeviceGetDevno(usb);
|
||||
+
|
||||
+ usbFreeDevice(usb);
|
||||
+ }
|
||||
+
|
||||
+
|
||||
if (driver->securityDriver &&
|
||||
driver->securityDriver->domainSetSecurityHostdevLabel(conn, vm, dev->data.hostdev) < 0)
|
||||
VIR_WARN0("Failed to restore device labelling");
|
||||
diff -rup libvirt-0.7.1/src/security_selinux.c new/src/security_selinux.c
|
||||
--- libvirt-0.7.1/src/security_selinux.c 2010-05-17 16:53:48.775745000 -0400
|
||||
+++ new/src/security_selinux.c 2010-05-17 16:58:47.442604000 -0400
|
||||
@@ -482,20 +482,15 @@ SELinuxSetSecurityHostdevLabel(virConnec
|
||||
|
||||
switch (dev->source.subsys.type) {
|
||||
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB: {
|
||||
- if (dev->source.subsys.u.usb.bus && dev->source.subsys.u.usb.device) {
|
||||
- usbDevice *usb = usbGetDevice(conn,
|
||||
- dev->source.subsys.u.usb.bus,
|
||||
- dev->source.subsys.u.usb.device);
|
||||
-
|
||||
- if (!usb)
|
||||
- goto done;
|
||||
-
|
||||
- ret = usbDeviceFileIterate(conn, usb, SELinuxSetSecurityUSBLabel, vm);
|
||||
- usbFreeDevice(conn, usb);
|
||||
- } else {
|
||||
- /* XXX deal with product/vendor better */
|
||||
- ret = 0;
|
||||
- }
|
||||
+ usbDevice *usb = usbGetDevice(conn,
|
||||
+ dev->source.subsys.u.usb.bus,
|
||||
+ dev->source.subsys.u.usb.device);
|
||||
+
|
||||
+ if (!usb)
|
||||
+ goto done;
|
||||
+
|
||||
+ ret = usbDeviceFileIterate(conn, usb, SELinuxSetSecurityUSBLabel, vm);
|
||||
+ usbFreeDevice(conn, usb);
|
||||
break;
|
||||
}
|
||||
|
||||
diff -rup libvirt-0.7.1/src/hostusb.c new/src/hostusb.c
|
||||
--- libvirt-0.7.1/src/hostusb.c 2010-05-17 17:09:02.573638000 -0400
|
||||
+++ new/src/hostusb.c 2010-05-17 17:29:49.133509000 -0400
|
||||
@@ -184,16 +184,17 @@ usbGetDevice(virConnectPtr conn,
|
||||
|
||||
|
||||
usbDevice *
|
||||
-usbFindDevice(unsigned vendor,
|
||||
+usbFindDevice(virConnectPtr conn,
|
||||
+ unsigned vendor,
|
||||
unsigned product)
|
||||
{
|
||||
unsigned bus = 0, devno = 0;
|
||||
|
||||
- if (usbFindBusByVendor(vendor, product, &bus, &devno) < 0) {
|
||||
+ if (usbFindBusByVendor(conn, vendor, product, &bus, &devno) < 0) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
- return usbGetDevice(bus, devno);
|
||||
+ return usbGetDevice(conn, bus, devno);
|
||||
}
|
||||
|
||||
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-05-17 17:09:02.602638000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-05-17 17:36:10.066214000 -0400
|
||||
@@ -1791,9 +1791,7 @@ static int qemuDomainSetHostdevUSBOwners
|
||||
|
||||
usbDevice *dev = usbGetDevice(conn,
|
||||
def->source.subsys.u.usb.bus,
|
||||
- def->source.subsys.u.usb.device,
|
||||
- def->source.subsys.u.usb.vendor,
|
||||
- def->source.subsys.u.usb.product);
|
||||
+ def->source.subsys.u.usb.device);
|
||||
|
||||
if (!dev)
|
||||
goto cleanup;
|
||||
@@ -2026,6 +2024,10 @@ qemuPrepareMonitorChr(virConnectPtr conn
|
||||
return 0;
|
||||
}
|
||||
|
||||
+static int
|
||||
+qemuPrepareHostDevices(struct qemud_driver *driver,
|
||||
+ virDomainDefPtr def);
|
||||
+
|
||||
static int qemudStartVMDaemon(virConnectPtr conn,
|
||||
struct qemud_driver *driver,
|
||||
virDomainObjPtr vm,
|
||||
@@ -2060,7 +2062,7 @@ static int qemudStartVMDaemon(virConnect
|
||||
}
|
||||
|
||||
DEBUG0("Preparing host devices");
|
||||
- if (qemuPrepareHostDevices(conn, driver, vm->def) < 0)
|
||||
+ if (qemuPrepareHostDevices(driver, vm->def) < 0)
|
||||
goto cleanup;
|
||||
|
||||
/* If you are using a SecurityDriver with dynamic labelling,
|
||||
@@ -2069,7 +2071,7 @@ static int qemudStartVMDaemon(virConnect
|
||||
driver->securityDriver &&
|
||||
driver->securityDriver->domainGenSecurityLabel &&
|
||||
driver->securityDriver->domainGenSecurityLabel(conn, vm) < 0)
|
||||
- return cleanup;
|
||||
+ goto cleanup;
|
||||
|
||||
/* Ensure no historical cgroup for this VM is lieing around bogus settings */
|
||||
qemuRemoveCgroup(conn, driver, vm);
|
||||
@@ -2360,7 +2362,8 @@ qemuPrepareHostUSBDevices(struct qemud_d
|
||||
/* Resolve a vendor/product to bus/device */
|
||||
if (hostdev->source.subsys.u.usb.vendor) {
|
||||
usbDevice *usb
|
||||
- = usbFindDevice(hostdev->source.subsys.u.usb.vendor,
|
||||
+ = usbFindDevice(NULL,
|
||||
+ hostdev->source.subsys.u.usb.vendor,
|
||||
hostdev->source.subsys.u.usb.product);
|
||||
|
||||
if (!usb)
|
||||
@@ -2369,7 +2372,7 @@ qemuPrepareHostUSBDevices(struct qemud_d
|
||||
hostdev->source.subsys.u.usb.bus = usbDeviceGetBus(usb);
|
||||
hostdev->source.subsys.u.usb.device = usbDeviceGetDevno(usb);
|
||||
|
||||
- usbFreeDevice(usb);
|
||||
+ usbFreeDevice(NULL, usb);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2383,7 +2386,7 @@ qemuPrepareHostDevices(struct qemud_driv
|
||||
if (!def->nhostdevs)
|
||||
return 0;
|
||||
|
||||
- if (qemuPrepareHostPCIDevices(driver, def) < 0)
|
||||
+ if (qemuPrepareHostPCIDevices(NULL, driver, def) < 0)
|
||||
return -1;
|
||||
|
||||
if (qemuPrepareHostUSBDevices(driver, def) < 0)
|
||||
@@ -6343,7 +6346,8 @@ static int qemudDomainDetachHostDevice(v
|
||||
if (hostdev->source.subsys.type == VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB &&
|
||||
hostdev->source.subsys.u.usb.vendor) {
|
||||
usbDevice *usb
|
||||
- = usbFindDevice(hostdev->source.subsys.u.usb.vendor,
|
||||
+ = usbFindDevice(NULL,
|
||||
+ hostdev->source.subsys.u.usb.vendor,
|
||||
hostdev->source.subsys.u.usb.product);
|
||||
|
||||
if (!usb)
|
||||
@@ -6352,7 +6356,7 @@ static int qemudDomainDetachHostDevice(v
|
||||
hostdev->source.subsys.u.usb.bus = usbDeviceGetBus(usb);
|
||||
hostdev->source.subsys.u.usb.device = usbDeviceGetDevno(usb);
|
||||
|
||||
- usbFreeDevice(usb);
|
||||
+ usbFreeDevice(NULL, usb);
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,686 @@
|
||||
commit 33a198c1f6a4a1bc7f34d50a31032e03bec10fee
|
||||
Author: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Fri Jul 17 20:20:08 2009 +0100
|
||||
|
||||
Initialize gcrypt threading
|
||||
|
||||
GNUTLS uses gcrypt for its crypto functions. gcrypt requires
|
||||
that the app/library initializes threading before using it.
|
||||
We don't want to force apps using libvirt to know about
|
||||
gcrypt, so we make virInitialize init threading on their
|
||||
behalf. This location also ensures libvirtd has initialized
|
||||
it correctly. This initialization is required even if libvirt
|
||||
itself were only using one thread, since another non-libvirt
|
||||
library (eg GTK-VNC) could also be using gcrypt from another
|
||||
thread
|
||||
|
||||
* src/libvirt.c: Register thread functions for gcrypt
|
||||
* configure.in: Add -lgcrypt to linker flags
|
||||
|
||||
diff --git a/src/libvirt.c b/src/libvirt.c
|
||||
index 103b331..cad33c2 100644
|
||||
--- a/src/libvirt.c
|
||||
+++ b/src/libvirt.c
|
||||
@@ -22,6 +22,7 @@
|
||||
#include <sys/wait.h>
|
||||
#endif
|
||||
#include <time.h>
|
||||
+#include <gcrypt.h>
|
||||
|
||||
#include <libxml/parser.h>
|
||||
#include <libxml/xpath.h>
|
||||
@@ -251,6 +252,55 @@ winsock_init (void)
|
||||
}
|
||||
#endif
|
||||
|
||||
+static int virTLSMutexInit (void **priv)
|
||||
+{ \
|
||||
+ virMutexPtr lock = NULL;
|
||||
+
|
||||
+ if (VIR_ALLOC(lock) < 0)
|
||||
+ return ENOMEM;
|
||||
+
|
||||
+ if (virMutexInit(lock) < 0) {
|
||||
+ VIR_FREE(lock);
|
||||
+ return errno;
|
||||
+ }
|
||||
+
|
||||
+ *priv = lock;
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int virTLSMutexDestroy(void **priv)
|
||||
+{
|
||||
+ virMutexPtr lock = *priv;
|
||||
+ virMutexDestroy(lock);
|
||||
+ VIR_FREE(lock);
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int virTLSMutexLock(void **priv)
|
||||
+{
|
||||
+ virMutexPtr lock = *priv;
|
||||
+ virMutexLock(lock);
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int virTLSMutexUnlock(void **priv)
|
||||
+{
|
||||
+ virMutexPtr lock = *priv;
|
||||
+ virMutexUnlock(lock);
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static struct gcry_thread_cbs virTLSThreadImpl = {
|
||||
+ (GCRY_THREAD_OPTION_PTHREAD | (GCRY_THREAD_OPTION_VERSION << 8)),
|
||||
+ NULL,
|
||||
+ virTLSMutexInit,
|
||||
+ virTLSMutexDestroy,
|
||||
+ virTLSMutexLock,
|
||||
+ virTLSMutexUnlock,
|
||||
+ NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL
|
||||
+};
|
||||
+
|
||||
+
|
||||
/**
|
||||
* virInitialize:
|
||||
*
|
||||
@@ -273,6 +323,9 @@ virInitialize(void)
|
||||
virRandomInitialize(time(NULL) ^ getpid()))
|
||||
return -1;
|
||||
|
||||
+ gcry_control(GCRYCTL_SET_THREAD_CBS, &virTLSThreadImpl);
|
||||
+ gcry_check_version(NULL);
|
||||
+
|
||||
virLogSetFromEnv();
|
||||
|
||||
DEBUG0("register drivers");
|
||||
commit 1c5c63338c90f6e82731f6871901dc72732033ef
|
||||
Author: Matthias Bolte <matthias.bolte@googlemail.com>
|
||||
Date: Fri Dec 18 12:02:07 2009 +0100
|
||||
|
||||
Fix compilation with gcrypt < 1.4.2
|
||||
|
||||
Commit 33a198c1f6a4a1bc7f34d50a31032e03bec10fee increased the gcrypt
|
||||
version requirement to 1.4.2 because the GCRY_THREAD_OPTION_VERSION
|
||||
define was added in this version.
|
||||
|
||||
The configure script doesn't check for the gcrypt version. To support
|
||||
gcrypt versions < 1.4.2 change the virTLSThreadImpl initialization
|
||||
to use GCRY_THREAD_OPTION_VERSION only if it's defined.
|
||||
|
||||
diff --git a/src/libvirt.c b/src/libvirt.c
|
||||
index 5167bc2..16c851f 100644
|
||||
--- a/src/libvirt.c
|
||||
+++ b/src/libvirt.c
|
||||
@@ -291,7 +291,12 @@ static int virTLSMutexUnlock(void **priv)
|
||||
}
|
||||
|
||||
static struct gcry_thread_cbs virTLSThreadImpl = {
|
||||
+ /* GCRY_THREAD_OPTION_VERSION was added in gcrypt 1.4.2 */
|
||||
+#ifdef GCRY_THREAD_OPTION_VERSION
|
||||
(GCRY_THREAD_OPTION_PTHREAD | (GCRY_THREAD_OPTION_VERSION << 8)),
|
||||
+#else
|
||||
+ GCRY_THREAD_OPTION_PTHREAD,
|
||||
+#endif
|
||||
NULL,
|
||||
virTLSMutexInit,
|
||||
virTLSMutexDestroy,
|
||||
diff -rup libvirt-0.7.1/aclocal.m4 gcrypt-new/aclocal.m4
|
||||
--- libvirt-0.7.1/aclocal.m4 2009-09-15 08:35:04.000000000 -0400
|
||||
+++ gcrypt-new/aclocal.m4 2010-05-17 17:52:13.765215000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# generated automatically by aclocal 1.11 -*- Autoconf -*-
|
||||
+# generated automatically by aclocal 1.11.1 -*- Autoconf -*-
|
||||
|
||||
# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004,
|
||||
# 2005, 2006, 2007, 2008, 2009 Free Software Foundation, Inc.
|
||||
@@ -190,7 +190,7 @@ AC_DEFUN([AM_AUTOMAKE_VERSION],
|
||||
[am__api_version='1.11'
|
||||
dnl Some users find AM_AUTOMAKE_VERSION and mistake it for a way to
|
||||
dnl require some minimum version. Point them to the right macro.
|
||||
-m4_if([$1], [1.11], [],
|
||||
+m4_if([$1], [1.11.1], [],
|
||||
[AC_FATAL([Do not call $0, use AM_INIT_AUTOMAKE([$1]).])])dnl
|
||||
])
|
||||
|
||||
@@ -206,7 +206,7 @@ m4_define([_AM_AUTOCONF_VERSION], [])
|
||||
# Call AM_AUTOMAKE_VERSION and AM_AUTOMAKE_VERSION so they can be traced.
|
||||
# This function is AC_REQUIREd by AM_INIT_AUTOMAKE.
|
||||
AC_DEFUN([AM_SET_CURRENT_AUTOMAKE_VERSION],
|
||||
-[AM_AUTOMAKE_VERSION([1.11])dnl
|
||||
+[AM_AUTOMAKE_VERSION([1.11.1])dnl
|
||||
m4_ifndef([AC_AUTOCONF_VERSION],
|
||||
[m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl
|
||||
_AM_AUTOCONF_VERSION(m4_defn([AC_AUTOCONF_VERSION]))])
|
||||
diff -rup libvirt-0.7.1/configure gcrypt-new/configure
|
||||
--- libvirt-0.7.1/configure 2009-09-15 08:35:09.000000000 -0400
|
||||
+++ gcrypt-new/configure 2010-05-17 17:52:18.706838000 -0400
|
||||
@@ -43324,7 +43324,7 @@ fi
|
||||
$as_echo "$as_me: error: You must install the GnuTLS library in order to compile and run libvirt" >&2;}
|
||||
{ (exit 1); exit 1; }; }
|
||||
|
||||
- GNUTLS_LIBS=$LIBS
|
||||
+ GNUTLS_LIBS="$LIBS -lgcrypt"
|
||||
LIBS="$old_libs"
|
||||
fi
|
||||
|
||||
diff -rup libvirt-0.7.1/docs/devhelp/Makefile.in gcrypt-new/docs/devhelp/Makefile.in
|
||||
--- libvirt-0.7.1/docs/devhelp/Makefile.in 2009-09-15 08:35:13.000000000 -0400
|
||||
+++ gcrypt-new/docs/devhelp/Makefile.in 2010-05-17 17:52:23.305455000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/docs/examples/Makefile.in gcrypt-new/docs/examples/Makefile.in
|
||||
--- libvirt-0.7.1/docs/examples/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/docs/examples/Makefile.in 2010-05-17 17:52:23.492454000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -999,7 +999,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1024,7 +1024,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/docs/examples/python/Makefile.in gcrypt-new/docs/examples/python/Makefile.in
|
||||
--- libvirt-0.7.1/docs/examples/python/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/docs/examples/python/Makefile.in 2010-05-17 17:52:23.650454000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/docs/Makefile.in gcrypt-new/docs/Makefile.in
|
||||
--- libvirt-0.7.1/docs/Makefile.in 2009-09-15 08:35:13.000000000 -0400
|
||||
+++ gcrypt-new/docs/Makefile.in 2010-05-17 17:52:23.143456000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -966,7 +966,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -991,7 +991,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/docs/schemas/Makefile.in gcrypt-new/docs/schemas/Makefile.in
|
||||
--- libvirt-0.7.1/docs/schemas/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/docs/schemas/Makefile.in 2010-05-17 17:52:23.807456000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/examples/domain-events/events-c/Makefile.in gcrypt-new/examples/domain-events/events-c/Makefile.in
|
||||
--- libvirt-0.7.1/examples/domain-events/events-c/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/examples/domain-events/events-c/Makefile.in 2010-05-17 17:52:23.983380000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/examples/hellolibvirt/Makefile.in gcrypt-new/examples/hellolibvirt/Makefile.in
|
||||
--- libvirt-0.7.1/examples/hellolibvirt/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/examples/hellolibvirt/Makefile.in 2010-05-17 17:52:24.166378000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/gnulib/lib/Makefile.in gcrypt-new/gnulib/lib/Makefile.in
|
||||
--- libvirt-0.7.1/gnulib/lib/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/gnulib/lib/Makefile.in 2010-05-17 17:52:24.409381000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1128,7 +1128,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1153,7 +1153,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/gnulib/tests/Makefile.in gcrypt-new/gnulib/tests/Makefile.in
|
||||
--- libvirt-0.7.1/gnulib/tests/Makefile.in 2009-09-15 08:35:15.000000000 -0400
|
||||
+++ gcrypt-new/gnulib/tests/Makefile.in 2010-05-17 17:52:24.719382000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1501,7 +1501,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1526,7 +1526,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/include/libvirt/Makefile.in gcrypt-new/include/libvirt/Makefile.in
|
||||
--- libvirt-0.7.1/include/libvirt/Makefile.in 2009-09-15 08:35:15.000000000 -0400
|
||||
+++ gcrypt-new/include/libvirt/Makefile.in 2010-05-17 17:52:25.069302000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/include/Makefile.in gcrypt-new/include/Makefile.in
|
||||
--- libvirt-0.7.1/include/Makefile.in 2009-09-15 08:35:15.000000000 -0400
|
||||
+++ gcrypt-new/include/Makefile.in 2010-05-17 17:52:24.902313000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -896,7 +896,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -921,7 +921,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/Makefile.in gcrypt-new/Makefile.in
|
||||
--- libvirt-0.7.1/Makefile.in 2009-09-15 08:35:18.000000000 -0400
|
||||
+++ gcrypt-new/Makefile.in 2010-05-17 17:52:28.423082000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1060,7 +1060,7 @@ uninstall-pkgconfigDATA:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1085,7 +1085,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1265,7 +1265,8 @@ distdir: $(DISTFILES)
|
||||
top_distdir="$(top_distdir)" distdir="$(distdir)" \
|
||||
dist-hook
|
||||
-test -n "$(am__skip_mode_fix)" \
|
||||
- || find "$(distdir)" -type d ! -perm -777 -exec chmod a+rwx {} \; -o \
|
||||
+ || find "$(distdir)" -type d ! -perm -755 \
|
||||
+ -exec chmod u+rwx,go+rx {} \; -o \
|
||||
! -type d ! -perm -444 -links 1 -exec chmod a+r {} \; -o \
|
||||
! -type d ! -perm -400 -exec chmod a+r {} \; -o \
|
||||
! -type d ! -perm -444 -exec $(install_sh) -c -m a+r {} {} \; \
|
||||
@@ -1309,17 +1310,17 @@ dist dist-all: distdir
|
||||
distcheck: dist
|
||||
case '$(DIST_ARCHIVES)' in \
|
||||
*.tar.gz*) \
|
||||
- GZIP=$(GZIP_ENV) gunzip -c $(distdir).tar.gz | $(am__untar) ;;\
|
||||
+ GZIP=$(GZIP_ENV) gzip -dc $(distdir).tar.gz | $(am__untar) ;;\
|
||||
*.tar.bz2*) \
|
||||
- bunzip2 -c $(distdir).tar.bz2 | $(am__untar) ;;\
|
||||
+ bzip2 -dc $(distdir).tar.bz2 | $(am__untar) ;;\
|
||||
*.tar.lzma*) \
|
||||
- unlzma -c $(distdir).tar.lzma | $(am__untar) ;;\
|
||||
+ lzma -dc $(distdir).tar.lzma | $(am__untar) ;;\
|
||||
*.tar.xz*) \
|
||||
xz -dc $(distdir).tar.xz | $(am__untar) ;;\
|
||||
*.tar.Z*) \
|
||||
uncompress -c $(distdir).tar.Z | $(am__untar) ;;\
|
||||
*.shar.gz*) \
|
||||
- GZIP=$(GZIP_ENV) gunzip -c $(distdir).shar.gz | unshar ;;\
|
||||
+ GZIP=$(GZIP_ENV) gzip -dc $(distdir).shar.gz | unshar ;;\
|
||||
*.zip*) \
|
||||
unzip $(distdir).zip ;;\
|
||||
esac
|
||||
diff -rup libvirt-0.7.1/proxy/Makefile.in gcrypt-new/proxy/Makefile.in
|
||||
--- libvirt-0.7.1/proxy/Makefile.in 2009-09-15 08:35:15.000000000 -0400
|
||||
+++ gcrypt-new/proxy/Makefile.in 2010-05-17 17:52:25.334306000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/python/Makefile.in gcrypt-new/python/Makefile.in
|
||||
--- libvirt-0.7.1/python/Makefile.in 2009-09-15 08:35:16.000000000 -0400
|
||||
+++ gcrypt-new/python/Makefile.in 2010-05-17 17:52:25.538302000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1090,7 +1090,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1115,7 +1115,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/python/tests/Makefile.in gcrypt-new/python/tests/Makefile.in
|
||||
--- libvirt-0.7.1/python/tests/Makefile.in 2009-09-15 08:35:16.000000000 -0400
|
||||
+++ gcrypt-new/python/tests/Makefile.in 2010-05-17 17:52:25.702304000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/qemud/Makefile.in gcrypt-new/qemud/Makefile.in
|
||||
--- libvirt-0.7.1/qemud/Makefile.in 2009-09-15 08:35:16.000000000 -0400
|
||||
+++ gcrypt-new/qemud/Makefile.in 2010-05-17 17:52:25.997229000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1522,7 +1522,7 @@ remote_protocol.c: remote_protocol.h
|
||||
@WITH_LIBVIRTD_TRUE@ test -e $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml || \
|
||||
@WITH_LIBVIRTD_TRUE@ ln -s ../default.xml \
|
||||
@WITH_LIBVIRTD_TRUE@ $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml
|
||||
-@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/qemu
|
||||
+@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt
|
||||
@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/run/libvirt
|
||||
@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/lib/libvirt
|
||||
|
||||
@@ -1530,7 +1530,7 @@ remote_protocol.c: remote_protocol.h
|
||||
@WITH_LIBVIRTD_TRUE@ rm -f $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml
|
||||
@WITH_LIBVIRTD_TRUE@ rm -f $(DESTDIR)$(sysconfdir)/$(default_xml_dest)
|
||||
@WITH_LIBVIRTD_TRUE@ rmdir $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart || :
|
||||
-@WITH_LIBVIRTD_TRUE@ rmdir $(DESTDIR)$(localstatedir)/log/libvirt/qemu || :
|
||||
+@WITH_LIBVIRTD_TRUE@ rmdir $(DESTDIR)$(localstatedir)/log/libvirt || :
|
||||
@WITH_LIBVIRTD_TRUE@ rmdir $(DESTDIR)$(localstatedir)/run/libvirt || :
|
||||
@WITH_LIBVIRTD_TRUE@ rmdir $(DESTDIR)$(localstatedir)/lib/libvirt || :
|
||||
|
||||
@@ -1577,6 +1577,8 @@ remote_protocol.c: remote_protocol.h
|
||||
|
||||
@WITH_LIBVIRTD_TRUE@install-logrotate: libvirtd.logrotate
|
||||
@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/qemu/
|
||||
+@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/lxc/
|
||||
+@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/uml/
|
||||
@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(sysconfdir)/logrotate.d/
|
||||
@WITH_LIBVIRTD_TRUE@ $(INSTALL_DATA) $< $(DESTDIR)$(sysconfdir)/logrotate.d/libvirtd
|
||||
|
||||
diff -rup libvirt-0.7.1/src/Makefile.in gcrypt-new/src/Makefile.in
|
||||
--- libvirt-0.7.1/src/Makefile.in 2009-09-15 08:35:17.000000000 -0400
|
||||
+++ gcrypt-new/src/Makefile.in 2010-05-17 17:52:26.929151000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -598,9 +598,9 @@ am__objects_45 = libvirt_util_la-bridge.
|
||||
libvirt_util_la-pci.lo libvirt_util_la-hostusb.lo \
|
||||
libvirt_util_la-qparams.lo \
|
||||
libvirt_util_la-storage_encryption_conf.lo \
|
||||
- libvirt_util_la-threads.lo libvirt_util_la-uuid.lo \
|
||||
- libvirt_util_la-util.lo libvirt_util_la-virterror.lo \
|
||||
- libvirt_util_la-xml.lo
|
||||
+ libvirt_util_la-storage_file.lo libvirt_util_la-threads.lo \
|
||||
+ libvirt_util_la-uuid.lo libvirt_util_la-util.lo \
|
||||
+ libvirt_util_la-virterror.lo libvirt_util_la-xml.lo
|
||||
am_libvirt_util_la_OBJECTS = $(am__objects_45)
|
||||
libvirt_util_la_OBJECTS = $(am_libvirt_util_la_OBJECTS)
|
||||
libvirt_util_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \
|
||||
@@ -617,11 +617,11 @@ am__libvirt_lxc_SOURCES_DIST = lxc_conf.
|
||||
event.h hash.c hash.h iptables.c iptables.h logging.c \
|
||||
logging.h memory.c memory.h pci.c pci.h hostusb.c hostusb.h \
|
||||
qparams.c qparams.h storage_encryption_conf.h \
|
||||
- storage_encryption_conf.c threads.c threads.h \
|
||||
- threads-pthread.h threads-win32.h uuid.c uuid.h util.c util.h \
|
||||
- virterror.c virterror_internal.h xml.c xml.h capabilities.c \
|
||||
- capabilities.h domain_conf.c domain_conf.h nodeinfo.h \
|
||||
- nodeinfo.c
|
||||
+ storage_encryption_conf.c storage_file.c storage_file.h \
|
||||
+ threads.c threads.h threads-pthread.h threads-win32.h uuid.c \
|
||||
+ uuid.h util.c util.h virterror.c virterror_internal.h xml.c \
|
||||
+ xml.h capabilities.c capabilities.h domain_conf.c \
|
||||
+ domain_conf.h nodeinfo.h nodeinfo.c
|
||||
am__objects_46 = libvirt_lxc-lxc_conf.$(OBJEXT) \
|
||||
libvirt_lxc-lxc_container.$(OBJEXT) \
|
||||
libvirt_lxc-lxc_controller.$(OBJEXT) \
|
||||
@@ -633,6 +633,7 @@ am__objects_47 = libvirt_lxc-bridge.$(OB
|
||||
libvirt_lxc-memory.$(OBJEXT) libvirt_lxc-pci.$(OBJEXT) \
|
||||
libvirt_lxc-hostusb.$(OBJEXT) libvirt_lxc-qparams.$(OBJEXT) \
|
||||
libvirt_lxc-storage_encryption_conf.$(OBJEXT) \
|
||||
+ libvirt_lxc-storage_file.$(OBJEXT) \
|
||||
libvirt_lxc-threads.$(OBJEXT) libvirt_lxc-uuid.$(OBJEXT) \
|
||||
libvirt_lxc-util.$(OBJEXT) libvirt_lxc-virterror.$(OBJEXT) \
|
||||
libvirt_lxc-xml.$(OBJEXT)
|
||||
@@ -1485,6 +1486,7 @@ UTIL_SOURCES = \
|
||||
hostusb.c hostusb.h \
|
||||
qparams.c qparams.h \
|
||||
storage_encryption_conf.h storage_encryption_conf.c \
|
||||
+ storage_file.c storage_file.h \
|
||||
threads.c threads.h \
|
||||
threads-pthread.h \
|
||||
threads-win32.h \
|
||||
@@ -2151,6 +2153,7 @@ distclean-compile:
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-pci.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-qparams.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-storage_encryption_conf.Po@am__quote@
|
||||
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-storage_file.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-threads.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-util.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-uuid.Po@am__quote@
|
||||
@@ -2170,6 +2173,7 @@ distclean-compile:
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-pci.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-qparams.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-storage_encryption_conf.Plo@am__quote@
|
||||
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-storage_file.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-threads.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-util.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-uuid.Plo@am__quote@
|
||||
@@ -2753,6 +2757,14 @@ libvirt_util_la-storage_encryption_conf.
|
||||
@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_util_la_CFLAGS) $(CFLAGS) -c -o libvirt_util_la-storage_encryption_conf.lo `test -f 'storage_encryption_conf.c' || echo '$(srcdir)/'`storage_encryption_conf.c
|
||||
|
||||
+libvirt_util_la-storage_file.lo: storage_file.c
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_util_la_CFLAGS) $(CFLAGS) -MT libvirt_util_la-storage_file.lo -MD -MP -MF $(DEPDIR)/libvirt_util_la-storage_file.Tpo -c -o libvirt_util_la-storage_file.lo `test -f 'storage_file.c' || echo '$(srcdir)/'`storage_file.c
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libvirt_util_la-storage_file.Tpo $(DEPDIR)/libvirt_util_la-storage_file.Plo
|
||||
+@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='storage_file.c' object='libvirt_util_la-storage_file.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
+@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_util_la_CFLAGS) $(CFLAGS) -c -o libvirt_util_la-storage_file.lo `test -f 'storage_file.c' || echo '$(srcdir)/'`storage_file.c
|
||||
+
|
||||
libvirt_util_la-threads.lo: threads.c
|
||||
@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_util_la_CFLAGS) $(CFLAGS) -MT libvirt_util_la-threads.lo -MD -MP -MF $(DEPDIR)/libvirt_util_la-threads.Tpo -c -o libvirt_util_la-threads.lo `test -f 'threads.c' || echo '$(srcdir)/'`threads.c
|
||||
@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libvirt_util_la-threads.Tpo $(DEPDIR)/libvirt_util_la-threads.Plo
|
||||
@@ -3065,6 +3077,22 @@ libvirt_lxc-storage_encryption_conf.obj:
|
||||
@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -c -o libvirt_lxc-storage_encryption_conf.obj `if test -f 'storage_encryption_conf.c'; then $(CYGPATH_W) 'storage_encryption_conf.c'; else $(CYGPATH_W) '$(srcdir)/storage_encryption_conf.c'; fi`
|
||||
|
||||
+libvirt_lxc-storage_file.o: storage_file.c
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -MT libvirt_lxc-storage_file.o -MD -MP -MF $(DEPDIR)/libvirt_lxc-storage_file.Tpo -c -o libvirt_lxc-storage_file.o `test -f 'storage_file.c' || echo '$(srcdir)/'`storage_file.c
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libvirt_lxc-storage_file.Tpo $(DEPDIR)/libvirt_lxc-storage_file.Po
|
||||
+@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='storage_file.c' object='libvirt_lxc-storage_file.o' libtool=no @AMDEPBACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
+@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -c -o libvirt_lxc-storage_file.o `test -f 'storage_file.c' || echo '$(srcdir)/'`storage_file.c
|
||||
+
|
||||
+libvirt_lxc-storage_file.obj: storage_file.c
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -MT libvirt_lxc-storage_file.obj -MD -MP -MF $(DEPDIR)/libvirt_lxc-storage_file.Tpo -c -o libvirt_lxc-storage_file.obj `if test -f 'storage_file.c'; then $(CYGPATH_W) 'storage_file.c'; else $(CYGPATH_W) '$(srcdir)/storage_file.c'; fi`
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libvirt_lxc-storage_file.Tpo $(DEPDIR)/libvirt_lxc-storage_file.Po
|
||||
+@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='storage_file.c' object='libvirt_lxc-storage_file.obj' libtool=no @AMDEPBACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
+@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -c -o libvirt_lxc-storage_file.obj `if test -f 'storage_file.c'; then $(CYGPATH_W) 'storage_file.c'; else $(CYGPATH_W) '$(srcdir)/storage_file.c'; fi`
|
||||
+
|
||||
libvirt_lxc-threads.o: threads.c
|
||||
@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -MT libvirt_lxc-threads.o -MD -MP -MF $(DEPDIR)/libvirt_lxc-threads.Tpo -c -o libvirt_lxc-threads.o `test -f 'threads.c' || echo '$(srcdir)/'`threads.c
|
||||
@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libvirt_lxc-threads.Tpo $(DEPDIR)/libvirt_lxc-threads.Po
|
||||
diff -rup libvirt-0.7.1/tests/confdata/Makefile.in gcrypt-new/tests/confdata/Makefile.in
|
||||
--- libvirt-0.7.1/tests/confdata/Makefile.in 2009-09-15 08:35:17.000000000 -0400
|
||||
+++ gcrypt-new/tests/confdata/Makefile.in 2010-05-17 17:52:27.383154000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/tests/Makefile.in gcrypt-new/tests/Makefile.in
|
||||
--- libvirt-0.7.1/tests/Makefile.in 2009-09-15 08:35:17.000000000 -0400
|
||||
+++ gcrypt-new/tests/Makefile.in 2010-05-17 17:52:27.223153000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1401,7 +1401,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1426,7 +1426,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/tests/sexpr2xmldata/Makefile.in gcrypt-new/tests/sexpr2xmldata/Makefile.in
|
||||
--- libvirt-0.7.1/tests/sexpr2xmldata/Makefile.in 2009-09-15 08:35:17.000000000 -0400
|
||||
+++ gcrypt-new/tests/sexpr2xmldata/Makefile.in 2010-05-17 17:52:27.543159000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/tests/xencapsdata/Makefile.in gcrypt-new/tests/xencapsdata/Makefile.in
|
||||
--- libvirt-0.7.1/tests/xencapsdata/Makefile.in 2009-09-15 08:35:18.000000000 -0400
|
||||
+++ gcrypt-new/tests/xencapsdata/Makefile.in 2010-05-17 17:52:27.704150000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/tests/xmconfigdata/Makefile.in gcrypt-new/tests/xmconfigdata/Makefile.in
|
||||
--- libvirt-0.7.1/tests/xmconfigdata/Makefile.in 2009-09-15 08:35:18.000000000 -0400
|
||||
+++ gcrypt-new/tests/xmconfigdata/Makefile.in 2010-05-17 17:52:27.872118000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/tests/xml2sexprdata/Makefile.in gcrypt-new/tests/xml2sexprdata/Makefile.in
|
||||
--- libvirt-0.7.1/tests/xml2sexprdata/Makefile.in 2009-09-15 08:35:18.000000000 -0400
|
||||
+++ gcrypt-new/tests/xml2sexprdata/Makefile.in 2010-05-17 17:52:28.046074000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/tools/Makefile.in gcrypt-new/tools/Makefile.in
|
||||
--- libvirt-0.7.1/tools/Makefile.in 2009-09-15 08:35:18.000000000 -0400
|
||||
+++ gcrypt-new/tools/Makefile.in 2010-05-17 17:52:28.213075000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -0,0 +1,13 @@
|
||||
diff -rup libvirt-0.7.1/src/lxc_driver.c new/src/lxc_driver.c
|
||||
--- libvirt-0.7.1/src/lxc_driver.c 2009-09-10 09:45:00.000000000 -0400
|
||||
+++ new/src/lxc_driver.c 2010-06-03 15:03:11.524069000 -0400
|
||||
@@ -96,7 +96,8 @@ static virDrvOpenStatus lxcOpen(virConne
|
||||
return VIR_DRV_OPEN_DECLINED;
|
||||
|
||||
/* If path isn't '/' then they typoed, tell them correct path */
|
||||
- if (STRNEQ(conn->uri->path, "/")) {
|
||||
+ if (conn->uri->path != NULL &&
|
||||
+ STRNEQ(conn->uri->path, "/")) {
|
||||
lxcError(conn, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
_("unexpected LXC URI path '%s', try lxc:///"),
|
||||
conn->uri->path);
|
||||
@@ -0,0 +1,65 @@
|
||||
commit e5f31f461f63bbad211e84b810d6ba43a705f9dd
|
||||
Author: Justin Clift <justin@salasaga.org>
|
||||
Date: Sun May 30 13:28:42 2010 +1000
|
||||
|
||||
Trivial virsh.pod additions --all for "list" command and similar
|
||||
|
||||
This is just a trivial patch to virsh.pod (from git master). It adds the
|
||||
following pieces to the virsh man page:
|
||||
|
||||
+ Shows the --inactive and --all optional parameters for the list
|
||||
command.
|
||||
|
||||
Closes Bugzilla #575512, reported by Renich Bon Ciric
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=575512
|
||||
|
||||
+ Corrects the existing description of the list command, to now say
|
||||
that only running domains are listed if no domains are specified.
|
||||
|
||||
The man page up until this point has said all domains are listed if
|
||||
no domains are specified, which is incorrect.
|
||||
|
||||
+ Adds the "shut off" state to the list of states for the list
|
||||
command.
|
||||
|
||||
+ Adds a missing =back around line 755, that pod2man was complaining
|
||||
was missing.
|
||||
|
||||
diff --git a/tools/virsh.pod b/tools/virsh.pod
|
||||
index cf7585d..495bb46 100644
|
||||
--- a/docs/virsh.pod
|
||||
+++ b/docs/virsh.pod
|
||||
@@ -156,10 +156,10 @@ description see:
|
||||
L<http://libvirt.org/formatcaps.html>
|
||||
The XML also show the NUMA topology information if available.
|
||||
|
||||
-=item B<list>
|
||||
+=item B<list> optional I<--inactive> I<--all>
|
||||
|
||||
Prints information about one or more domains. If no domains are
|
||||
-specified it prints out information about all domains.
|
||||
+specified it prints out information about running domains.
|
||||
|
||||
An example format for the list is as follows:
|
||||
|
||||
@@ -177,7 +177,7 @@ State is the run state (see below).
|
||||
|
||||
B<STATES>
|
||||
|
||||
-The State field lists 6 states for a domain, and which ones the
|
||||
+The State field lists 7 states for a domain, and which ones the
|
||||
current domain is in.
|
||||
|
||||
=over 4
|
||||
@@ -205,6 +205,11 @@ The domain is in the process of shutting down, i.e. the guest operating system
|
||||
has been notified and should be in the process of stopping its operations
|
||||
gracefully.
|
||||
|
||||
+=item B<shut off>
|
||||
+
|
||||
+The domain is not running. Usually this indicates the domain has been
|
||||
+shut down completely, or has not been started.
|
||||
+
|
||||
=item B<crashed>
|
||||
|
||||
The domain has crashed, which is always a violent ending. Usually
|
||||
@@ -0,0 +1,401 @@
|
||||
diff -rup libvirt-0.7.1/src/libvirt.c new/src/libvirt.c
|
||||
--- libvirt-0.7.1/src/libvirt.c 2010-06-03 15:30:32.615164000 -0400
|
||||
+++ new/src/libvirt.c 2010-06-03 15:33:22.863409000 -0400
|
||||
@@ -3054,6 +3054,7 @@ virDomainMigrateVersion2 (virDomainPtr d
|
||||
char *cookie = NULL;
|
||||
char *dom_xml = NULL;
|
||||
int cookielen = 0, ret;
|
||||
+ virErrorPtr orig_err = NULL;
|
||||
|
||||
/* Prepare the migration.
|
||||
*
|
||||
@@ -3102,6 +3103,10 @@ virDomainMigrateVersion2 (virDomainPtr d
|
||||
ret = domain->conn->driver->domainMigratePerform
|
||||
(domain, cookie, cookielen, uri, flags, dname, bandwidth);
|
||||
|
||||
+ /* Perform failed. Make sure Finish doesn't overwrite the error */
|
||||
+ if (ret < 0)
|
||||
+ orig_err = virSaveLastError();
|
||||
+
|
||||
/* In version 2 of the migration protocol, we pass the
|
||||
* status code from the sender to the destination host,
|
||||
* so it can do any cleanup if the migration failed.
|
||||
@@ -3111,6 +3116,10 @@ virDomainMigrateVersion2 (virDomainPtr d
|
||||
(dconn, dname, cookie, cookielen, uri, flags, ret);
|
||||
|
||||
done:
|
||||
+ if (orig_err) {
|
||||
+ virSetError(orig_err);
|
||||
+ virFreeError(orig_err);
|
||||
+ }
|
||||
VIR_FREE (uri_out);
|
||||
VIR_FREE (cookie);
|
||||
return ddomain;
|
||||
@@ -3222,7 +3231,7 @@ virDomainMigrate (virDomainPtr domain,
|
||||
|
||||
error:
|
||||
/* Copy to connection error object for back compatability */
|
||||
- virSetConnError(domain->conn);
|
||||
+ virDispatchError(domain->conn);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -3269,8 +3278,7 @@ virDomainMigratePrepare (virConnectPtr d
|
||||
virLibConnError (dconn, VIR_ERR_NO_SUPPORT, __FUNCTION__);
|
||||
|
||||
error:
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(dconn);
|
||||
+ virDispatchError(dconn);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -3318,8 +3326,7 @@ virDomainMigratePerform (virDomainPtr do
|
||||
virLibDomainError (domain, VIR_ERR_NO_SUPPORT, __FUNCTION__);
|
||||
|
||||
error:
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(domain->conn);
|
||||
+ virDispatchError(domain->conn);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -3364,8 +3371,7 @@ virDomainMigrateFinish (virConnectPtr dc
|
||||
virLibConnError (dconn, VIR_ERR_NO_SUPPORT, __FUNCTION__);
|
||||
|
||||
error:
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(dconn);
|
||||
+ virDispatchError(dconn);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -3416,8 +3422,7 @@ virDomainMigratePrepare2 (virConnectPtr
|
||||
virLibConnError (dconn, VIR_ERR_NO_SUPPORT, __FUNCTION__);
|
||||
|
||||
error:
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(dconn);
|
||||
+ virDispatchError(dconn);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -3464,8 +3469,7 @@ virDomainMigrateFinish2 (virConnectPtr d
|
||||
virLibConnError (dconn, VIR_ERR_NO_SUPPORT, __FUNCTION__);
|
||||
|
||||
error:
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(dconn);
|
||||
+ virDispatchError(dconn);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
diff -rup libvirt-0.7.1/src/libvirt_private.syms new/src/libvirt_private.syms
|
||||
--- libvirt-0.7.1/src/libvirt_private.syms 2010-06-03 15:30:33.051186000 -0400
|
||||
+++ new/src/libvirt_private.syms 2010-06-03 15:33:22.869400000 -0400
|
||||
@@ -461,6 +461,7 @@ virRaiseErrorFull;
|
||||
virReportSystemErrorFull;
|
||||
virReportOOMErrorFull;
|
||||
virStrerror;
|
||||
+virSetError;
|
||||
|
||||
|
||||
# xml.h
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-06-03 15:30:33.111159000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-06-03 15:35:22.809404000 -0400
|
||||
@@ -2297,12 +2297,17 @@ static void qemudShutdownVMDaemon(virCon
|
||||
virDomainObjPtr vm) {
|
||||
int ret;
|
||||
int retries = 0;
|
||||
+ virErrorPtr orig_err;
|
||||
|
||||
if (!virDomainIsActive(vm))
|
||||
return;
|
||||
|
||||
VIR_DEBUG(_("Shutting down VM '%s'\n"), vm->def->name);
|
||||
|
||||
+ /* This method is routinely used in clean up paths. Disable error
|
||||
+ * reporting so we don't squash a legit error. */
|
||||
+ orig_err = virSaveLastError();
|
||||
+
|
||||
if (virKillProcess(vm->pid, 0) == 0 &&
|
||||
virKillProcess(vm->pid, SIGTERM) < 0)
|
||||
virReportSystemError(conn, errno,
|
||||
@@ -2377,6 +2382,11 @@ retry:
|
||||
vm->def->id = -1;
|
||||
vm->newDef = NULL;
|
||||
}
|
||||
+
|
||||
+ if (orig_err) {
|
||||
+ virSetError(orig_err);
|
||||
+ virFreeError(orig_err);
|
||||
+ }
|
||||
}
|
||||
|
||||
|
||||
@@ -7497,6 +7507,10 @@ qemudDomainMigrateFinish2 (virConnectPtr
|
||||
virDomainObjPtr vm;
|
||||
virDomainPtr dom = NULL;
|
||||
virDomainEventPtr event = NULL;
|
||||
+ virErrorPtr orig_err;
|
||||
+
|
||||
+ /* Migration failed. Save the current error so nothing squashes it */
|
||||
+ orig_err = virSaveLastError();
|
||||
|
||||
qemuDriverLock(driver);
|
||||
vm = virDomainFindByName(&driver->domains, dname);
|
||||
@@ -7540,6 +7554,10 @@ qemudDomainMigrateFinish2 (virConnectPtr
|
||||
}
|
||||
|
||||
cleanup:
|
||||
+ if (orig_err) {
|
||||
+ virSetError(orig_err);
|
||||
+ virFreeError(orig_err);
|
||||
+ }
|
||||
if (vm)
|
||||
virDomainObjUnlock(vm);
|
||||
if (event)
|
||||
diff -rup libvirt-0.7.1/src/util.c new/src/util.c
|
||||
--- libvirt-0.7.1/src/util.c 2010-06-03 15:30:33.064159000 -0400
|
||||
+++ new/src/util.c 2010-06-03 15:33:22.881417000 -0400
|
||||
@@ -1764,31 +1764,82 @@ int virDiskNameToIndex(const char *name)
|
||||
#define AI_CANONIDN 0
|
||||
#endif
|
||||
|
||||
-char *virGetHostname(void)
|
||||
+/* Who knew getting a hostname could be so delicate. In Linux (and Unices
|
||||
+ * in general), many things depend on "hostname" returning a value that will
|
||||
+ * resolve one way or another. In the modern world where networks frequently
|
||||
+ * come and go this is often being hard-coded to resolve to "localhost". If
|
||||
+ * it *doesn't* resolve to localhost, then we would prefer to have the FQDN.
|
||||
+ * That leads us to 3 possibilities:
|
||||
+ *
|
||||
+ * 1) gethostname() returns an FQDN (not localhost) - we return the string
|
||||
+ * as-is, it's all of the information we want
|
||||
+ * 2) gethostname() returns "localhost" - we return localhost; doing further
|
||||
+ * work to try to resolve it is pointless
|
||||
+ * 3) gethostname() returns a shortened hostname - in this case, we want to
|
||||
+ * try to resolve this to a fully-qualified name. Therefore we pass it
|
||||
+ * to getaddrinfo(). There are two possible responses:
|
||||
+ * a) getaddrinfo() resolves to a FQDN - return the FQDN
|
||||
+ * b) getaddrinfo() resolves to localhost - in this case, the data we got
|
||||
+ * from gethostname() is actually more useful than what we got from
|
||||
+ * getaddrinfo(). Return the value from gethostname() and hope for
|
||||
+ * the best.
|
||||
+ */
|
||||
+char *virGetHostname()
|
||||
{
|
||||
int r;
|
||||
char hostname[HOST_NAME_MAX+1], *result;
|
||||
struct addrinfo hints, *info;
|
||||
|
||||
r = gethostname (hostname, sizeof(hostname));
|
||||
- if (r == -1)
|
||||
+ if (r == -1) {
|
||||
+ virReportSystemError(NULL, errno,
|
||||
+ "%s", _("failed to determine host name"));
|
||||
return NULL;
|
||||
+ }
|
||||
NUL_TERMINATE(hostname);
|
||||
|
||||
+ if (STRPREFIX(hostname, "localhost") || strchr(hostname, '.')) {
|
||||
+ /* in this case, gethostname returned localhost (meaning we can't
|
||||
+ * do any further canonicalization), or it returned an FQDN (and
|
||||
+ * we don't need to do any further canonicalization). Return the
|
||||
+ * string as-is; it's up to callers to check whether "localhost"
|
||||
+ * is allowed.
|
||||
+ */
|
||||
+ result = strdup(hostname);
|
||||
+ goto check_and_return;
|
||||
+ }
|
||||
+
|
||||
+ /* otherwise, it's a shortened, non-localhost, hostname. Attempt to
|
||||
+ * canonicalize the hostname by running it through getaddrinfo
|
||||
+ */
|
||||
+
|
||||
memset(&hints, 0, sizeof(hints));
|
||||
hints.ai_flags = AI_CANONNAME|AI_CANONIDN;
|
||||
hints.ai_family = AF_UNSPEC;
|
||||
r = getaddrinfo(hostname, NULL, &hints, &info);
|
||||
- if (r != 0)
|
||||
- return NULL;
|
||||
- if (info->ai_canonname == NULL) {
|
||||
- freeaddrinfo(info);
|
||||
+ if (r != 0) {
|
||||
+ ReportError(NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("getaddrinfo failed for '%s': %s"),
|
||||
+ hostname, gai_strerror(r));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
- /* Caller frees this string. */
|
||||
- result = strdup (info->ai_canonname);
|
||||
+ if (info->ai_canonname == NULL ||
|
||||
+ STRPREFIX(info->ai_canonname, "localhost"))
|
||||
+ /* in this case, we tried to canonicalize and we ended up back with
|
||||
+ * localhost. Ignore the canonicalized name and just return the
|
||||
+ * original hostname
|
||||
+ */
|
||||
+ result = strdup(hostname);
|
||||
+ else
|
||||
+ /* Caller frees this string. */
|
||||
+ result = strdup (info->ai_canonname);
|
||||
+
|
||||
freeaddrinfo(info);
|
||||
+
|
||||
+check_and_return:
|
||||
+ if (result == NULL)
|
||||
+ virReportOOMError(NULL);
|
||||
return result;
|
||||
}
|
||||
|
||||
diff -rup libvirt-0.7.1/src/virterror.c new/src/virterror.c
|
||||
--- libvirt-0.7.1/src/virterror.c 2009-09-14 06:12:53.000000000 -0400
|
||||
+++ new/src/virterror.c 2010-06-03 15:33:22.886409000 -0400
|
||||
@@ -287,6 +287,28 @@ virGetLastError(void)
|
||||
}
|
||||
|
||||
/**
|
||||
+ * virSetError:
|
||||
+ *
|
||||
+ * Set the current error from a previously saved error object
|
||||
+ *
|
||||
+ * Can be used to re-set an old error, which may have been squashed by
|
||||
+ * other functions (like cleanup routines).
|
||||
+ *
|
||||
+ * Returns 0 on success, 1 on failure
|
||||
+ */
|
||||
+int
|
||||
+virSetError(virErrorPtr newerr)
|
||||
+{
|
||||
+ virErrorPtr err;
|
||||
+ err = virGetLastError();
|
||||
+ if (!err)
|
||||
+ return -1;
|
||||
+
|
||||
+ virResetError(err);
|
||||
+ return virCopyError(newerr, err);
|
||||
+}
|
||||
+
|
||||
+/**
|
||||
* virCopyLastError:
|
||||
* @to: target to receive the copy
|
||||
*
|
||||
@@ -596,6 +618,52 @@ virSetConnError(virConnectPtr conn)
|
||||
}
|
||||
}
|
||||
|
||||
+/**
|
||||
+ * virDispatchError:
|
||||
+ * @conn: pointer to the hypervisor connection
|
||||
+ *
|
||||
+ * Internal helper to do final stage of error
|
||||
+ * reporting in public APIs.
|
||||
+ *
|
||||
+ * - Copy the global error to per-connection error if needed
|
||||
+ * - Set a generic error message if none is already set
|
||||
+ * - Invoke the error callback functions
|
||||
+ */
|
||||
+void
|
||||
+virDispatchError(virConnectPtr conn)
|
||||
+{
|
||||
+ virErrorPtr err = virLastErrorObject();
|
||||
+ virErrorFunc handler = virErrorHandler;
|
||||
+ void *userData = virUserData;
|
||||
+
|
||||
+ /* Should never happen, but doesn't hurt to check */
|
||||
+ if (!err)
|
||||
+ return;
|
||||
+
|
||||
+ /* Set a generic error message if none is already set */
|
||||
+ if (err->code == VIR_ERR_OK)
|
||||
+ virErrorGenericFailure(err);
|
||||
+
|
||||
+ /* Copy the global error to per-connection error if needed */
|
||||
+ if (conn) {
|
||||
+ virMutexLock(&conn->lock);
|
||||
+ virCopyError(err, &conn->err);
|
||||
+
|
||||
+ if (conn->handler != NULL) {
|
||||
+ handler = conn->handler;
|
||||
+ userData = conn->userData;
|
||||
+ }
|
||||
+ virMutexUnlock(&conn->lock);
|
||||
+ }
|
||||
+
|
||||
+ /* Invoke the error callback functions */
|
||||
+ if (handler != NULL) {
|
||||
+ (handler)(userData, err);
|
||||
+ } else {
|
||||
+ virDefaultErrorFunc(err);
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
|
||||
|
||||
/**
|
||||
@@ -634,8 +702,6 @@ virRaiseErrorFull(virConnectPtr conn,
|
||||
const char *fmt, ...)
|
||||
{
|
||||
virErrorPtr to;
|
||||
- void *userData = virUserData;
|
||||
- virErrorFunc handler = virErrorHandler;
|
||||
char *str;
|
||||
|
||||
/*
|
||||
@@ -653,18 +719,6 @@ virRaiseErrorFull(virConnectPtr conn,
|
||||
return;
|
||||
|
||||
/*
|
||||
- * try to find the best place to save and report the error
|
||||
- */
|
||||
- if (conn != NULL) {
|
||||
- virMutexLock(&conn->lock);
|
||||
- if (conn->handler != NULL) {
|
||||
- handler = conn->handler;
|
||||
- userData = conn->userData;
|
||||
- }
|
||||
- virMutexUnlock(&conn->lock);
|
||||
- }
|
||||
-
|
||||
- /*
|
||||
* formats the message
|
||||
*/
|
||||
if (fmt == NULL) {
|
||||
@@ -683,7 +737,6 @@ virRaiseErrorFull(virConnectPtr conn,
|
||||
/*
|
||||
* Save the information about the error
|
||||
*/
|
||||
- virResetError(to);
|
||||
/*
|
||||
* Delibrately not setting conn, dom & net fields since
|
||||
* they're utterly unsafe
|
||||
@@ -701,14 +754,7 @@ virRaiseErrorFull(virConnectPtr conn,
|
||||
to->int1 = int1;
|
||||
to->int2 = int2;
|
||||
|
||||
- /*
|
||||
- * now, report it
|
||||
- */
|
||||
- if (handler != NULL) {
|
||||
- handler(userData, to);
|
||||
- } else {
|
||||
- virDefaultErrorFunc(to);
|
||||
- }
|
||||
+ virDispatchError(conn);
|
||||
}
|
||||
|
||||
/**
|
||||
diff -rup libvirt-0.7.1/src/virterror_internal.h new/src/virterror_internal.h
|
||||
--- libvirt-0.7.1/src/virterror_internal.h 2009-07-23 12:33:02.000000000 -0400
|
||||
+++ new/src/virterror_internal.h 2010-06-03 15:33:22.890402000 -0400
|
||||
@@ -89,6 +89,8 @@ void virReportOOMErrorFull(virConnectPtr
|
||||
|
||||
void virSetGlobalError(void);
|
||||
void virSetConnError(virConnectPtr conn);
|
||||
+int virSetError(virErrorPtr newerr);
|
||||
+void virDispatchError(virConnectPtr conn);
|
||||
const char *virStrerror(int theerrno, char *errBuf, size_t errBufLen);
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,126 @@
|
||||
diff -rup libvirt-0.7.1/src/network_driver.c new/src/network_driver.c
|
||||
--- libvirt-0.7.1/src/network_driver.c 2009-09-15 03:49:04.000000000 -0400
|
||||
+++ new/src/network_driver.c 2010-06-15 13:33:01.900912000 -0400
|
||||
@@ -43,6 +43,8 @@
|
||||
#include <stdio.h>
|
||||
#include <sys/wait.h>
|
||||
#include <sys/ioctl.h>
|
||||
+#include <netinet/in.h>
|
||||
+#include <arpa/inet.h>
|
||||
|
||||
#include "virterror_internal.h"
|
||||
#include "datatypes.h"
|
||||
@@ -843,6 +845,102 @@ cleanup:
|
||||
return ret;
|
||||
}
|
||||
|
||||
+#define PROC_NET_ROUTE "/proc/net/route"
|
||||
+
|
||||
+static int networkCheckRouteCollision(virNetworkObjPtr network)
|
||||
+{
|
||||
+ int ret = -1, len;
|
||||
+ char *cur, *buf = NULL;
|
||||
+ enum {MAX_ROUTE_SIZE = 1024*64};
|
||||
+ struct in_addr inaddress, innetmask;
|
||||
+ unsigned int net_dest;
|
||||
+
|
||||
+ if (!network->def->ipAddress || !network->def->netmask)
|
||||
+ return 0;
|
||||
+
|
||||
+ if (inet_pton(AF_INET, network->def->ipAddress, &inaddress) <= 0) {
|
||||
+ networkReportError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("cannot parse IP address '%s'"),
|
||||
+ network->def->ipAddress);
|
||||
+ goto error;
|
||||
+ }
|
||||
+ if (inet_pton(AF_INET, network->def->netmask, &innetmask) <= 0) {
|
||||
+ networkReportError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("cannot parse netmask '%s'"),
|
||||
+ network->def->netmask);
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ net_dest = (inaddress.s_addr & innetmask.s_addr);
|
||||
+
|
||||
+ /* Read whole routing table into memory */
|
||||
+ if ((len = virFileReadAll(PROC_NET_ROUTE, MAX_ROUTE_SIZE, &buf)) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ /* Dropping the last character shouldn't hurt */
|
||||
+ if (len > 0)
|
||||
+ buf[len-1] = '\0';
|
||||
+
|
||||
+ VIR_DEBUG("%s output:\n%s", PROC_NET_ROUTE, buf);
|
||||
+
|
||||
+ if (!STRPREFIX (buf, "Iface"))
|
||||
+ goto out;
|
||||
+
|
||||
+ /* First line is just headings, skip it */
|
||||
+ cur = strchr(buf, '\n');
|
||||
+ if (cur)
|
||||
+ cur++;
|
||||
+
|
||||
+ while (cur) {
|
||||
+ char iface[17], dest[128], mask[128];
|
||||
+ unsigned int addr_val, mask_val;
|
||||
+ int num;
|
||||
+
|
||||
+ /* NUL-terminate the line, so sscanf doesn't go beyond a newline. */
|
||||
+ char *nl = strchr(cur, '\n');
|
||||
+ if (nl) {
|
||||
+ *nl++ = '\0';
|
||||
+ }
|
||||
+
|
||||
+ num = sscanf(cur, "%16s %127s %*s %*s %*s %*s %*s %127s",
|
||||
+ iface, dest, mask);
|
||||
+ cur = nl;
|
||||
+
|
||||
+ if (num != 3) {
|
||||
+ VIR_DEBUG("Failed to parse %s", PROC_NET_ROUTE);
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
+ if (virStrToLong_ui(dest, NULL, 16, &addr_val) < 0) {
|
||||
+ VIR_DEBUG("Failed to convert network address %s to uint", dest);
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
+ if (virStrToLong_ui(mask, NULL, 16, &mask_val) < 0) {
|
||||
+ VIR_DEBUG("Failed to convert network mask %s to uint", mask);
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
+ addr_val &= mask_val;
|
||||
+
|
||||
+ if ((net_dest == addr_val) &&
|
||||
+ (innetmask.s_addr == mask_val)) {
|
||||
+ networkReportError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Network %s/%s is already in use by "
|
||||
+ "interface %s"),
|
||||
+ network->def->ipAddress,
|
||||
+ network->def->netmask, iface);
|
||||
+ goto error;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+out:
|
||||
+ ret = 0;
|
||||
+error:
|
||||
+ VIR_FREE(buf);
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
static int networkStartNetworkDaemon(virConnectPtr conn,
|
||||
struct network_driver *driver,
|
||||
virNetworkObjPtr network) {
|
||||
@@ -854,6 +952,10 @@ static int networkStartNetworkDaemon(vir
|
||||
return -1;
|
||||
}
|
||||
|
||||
+ /* Check to see if network collides with an existing route */
|
||||
+ if (networkCheckRouteCollision(network) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
if ((err = brAddBridge(driver->brctl, network->def->bridge))) {
|
||||
virReportSystemError(conn, err,
|
||||
_("cannot create bridge '%s'"),
|
||||
@@ -0,0 +1,29 @@
|
||||
commit c11a82b62aefc21e070c527f59a1f9c57a7b4f36
|
||||
Author: Richard Jones <rjones@redhat.com>
|
||||
Date: Thu Dec 10 16:39:07 2009 +0000
|
||||
|
||||
qemu driver: Fix segfault in libvirt/libvirtd when uri->path is NULL.
|
||||
|
||||
See also:
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=545400#c1
|
||||
|
||||
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
|
||||
index 2fb059d..e9cc8c3 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -2651,6 +2651,15 @@ static virDrvOpenStatus qemudOpen(virConnectPtr conn,
|
||||
return VIR_DRV_OPEN_ERROR;
|
||||
}
|
||||
|
||||
+ if (conn->uri->path == NULL) {
|
||||
+ qemudReportError(conn, NULL, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("no QEMU URI path given, try %s"),
|
||||
+ qemu_driver->privileged
|
||||
+ ? "qemu:///system"
|
||||
+ : "qemu:///session");
|
||||
+ return VIR_DRV_OPEN_ERROR;
|
||||
+ }
|
||||
+
|
||||
if (qemu_driver->privileged) {
|
||||
if (STRNEQ (conn->uri->path, "/system") &&
|
||||
STRNEQ (conn->uri->path, "/session")) {
|
||||
@@ -0,0 +1,143 @@
|
||||
diff -rup libvirt-0.7.1/src/libvirt_private.syms paths/src/libvirt_private.syms
|
||||
--- libvirt-0.7.1/src/libvirt_private.syms 2010-05-26 12:48:49.276277000 -0400
|
||||
+++ paths/src/libvirt_private.syms 2010-05-26 13:00:47.501023000 -0400
|
||||
@@ -417,6 +417,7 @@ virParseMacAddr;
|
||||
virFileDeletePid;
|
||||
virFindFileInPath;
|
||||
virFileExists;
|
||||
+virFileSanitizePath;
|
||||
virFileHasSuffix;
|
||||
virFileLinkPointsTo;
|
||||
virFileMakePath;
|
||||
diff -rup libvirt-0.7.1/src/storage_conf.c paths/src/storage_conf.c
|
||||
--- libvirt-0.7.1/src/storage_conf.c 2010-05-26 12:48:48.885306000 -0400
|
||||
+++ paths/src/storage_conf.c 2010-05-26 13:00:17.027330000 -0400
|
||||
@@ -463,6 +463,7 @@ virStoragePoolDefParseXML(virConnectPtr
|
||||
char *type = NULL;
|
||||
char *uuid = NULL;
|
||||
char *authType = NULL;
|
||||
+ char *tmppath;
|
||||
|
||||
if (VIR_ALLOC(ret) < 0) {
|
||||
virReportOOMError(conn);
|
||||
@@ -610,11 +611,15 @@ virStoragePoolDefParseXML(virConnectPtr
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
- if ((ret->target.path = virXPathString(conn, "string(./target/path)", ctxt)) == NULL) {
|
||||
+ if ((tmppath = virXPathString(conn, "string(./target/path)", ctxt)) == NULL) {
|
||||
virStorageReportError(conn, VIR_ERR_XML_ERROR,
|
||||
"%s", _("missing storage pool target path"));
|
||||
goto cleanup;
|
||||
}
|
||||
+ ret->target.path = virFileSanitizePath(tmppath);
|
||||
+ VIR_FREE(tmppath);
|
||||
+ if (!ret->target.path)
|
||||
+ goto cleanup;
|
||||
|
||||
if (virStorageDefParsePerms(conn, ctxt, &ret->target.perms,
|
||||
"./target/permissions", 0700) < 0)
|
||||
diff -rup libvirt-0.7.1/src/storage_driver.c paths/src/storage_driver.c
|
||||
--- libvirt-0.7.1/src/storage_driver.c 2009-09-10 09:45:00.000000000 -0400
|
||||
+++ paths/src/storage_driver.c 2010-05-26 12:59:14.815537000 -0400
|
||||
@@ -1152,6 +1152,11 @@ storageVolumeLookupByPath(virConnectPtr
|
||||
virStorageDriverStatePtr driver = conn->storagePrivateData;
|
||||
unsigned int i;
|
||||
virStorageVolPtr ret = NULL;
|
||||
+ char *cleanpath;
|
||||
+
|
||||
+ cleanpath = virFileSanitizePath(path);
|
||||
+ if (!cleanpath)
|
||||
+ return NULL;
|
||||
|
||||
storageDriverLock(driver);
|
||||
for (i = 0 ; i < driver->pools.count && !ret ; i++) {
|
||||
@@ -1162,7 +1167,7 @@ storageVolumeLookupByPath(virConnectPtr
|
||||
|
||||
stable_path = virStorageBackendStablePath(conn,
|
||||
driver->pools.objs[i],
|
||||
- path);
|
||||
+ cleanpath);
|
||||
/*
|
||||
* virStorageBackendStablePath already does
|
||||
* virStorageReportError if it fails; we just need to keep
|
||||
@@ -1191,6 +1196,7 @@ storageVolumeLookupByPath(virConnectPtr
|
||||
"%s", _("no storage vol with matching path"));
|
||||
|
||||
cleanup:
|
||||
+ VIR_FREE(cleanpath);
|
||||
storageDriverUnlock(driver);
|
||||
return ret;
|
||||
}
|
||||
diff -rup libvirt-0.7.1/src/util.c paths/src/util.c
|
||||
--- libvirt-0.7.1/src/util.c 2010-05-26 12:48:48.840341000 -0400
|
||||
+++ paths/src/util.c 2010-05-26 12:58:02.088721000 -0400
|
||||
@@ -1126,6 +1126,55 @@ int virFileExists(const char *path)
|
||||
return(0);
|
||||
}
|
||||
|
||||
+/* Remove spurious / characters from a path. The result must be freed */
|
||||
+char *
|
||||
+virFileSanitizePath(const char *path)
|
||||
+{
|
||||
+ const char *cur = path;
|
||||
+ char *cleanpath;
|
||||
+ int idx = 0;
|
||||
+
|
||||
+ cleanpath = strdup(path);
|
||||
+ if (!cleanpath) {
|
||||
+ virReportOOMError(NULL);
|
||||
+ return NULL;
|
||||
+ }
|
||||
+
|
||||
+ /* Need to sanitize:
|
||||
+ * // -> //
|
||||
+ * /// -> /
|
||||
+ * /../foo -> /../foo
|
||||
+ * /foo///bar/ -> /foo/bar
|
||||
+ */
|
||||
+
|
||||
+ /* Starting with // is valid posix, but ///foo == /foo */
|
||||
+ if (cur[0] == '/' && cur[1] == '/' && cur[2] != '/') {
|
||||
+ idx = 2;
|
||||
+ cur += 2;
|
||||
+ }
|
||||
+
|
||||
+ /* Sanitize path in place */
|
||||
+ while (*cur != '\0') {
|
||||
+ if (*cur != '/') {
|
||||
+ cleanpath[idx++] = *cur++;
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
+ /* Skip all extra / */
|
||||
+ while (*++cur == '/')
|
||||
+ continue;
|
||||
+
|
||||
+ /* Don't add a trailing / */
|
||||
+ if (idx != 0 && *cur == '\0')
|
||||
+ break;
|
||||
+
|
||||
+ cleanpath[idx++] = '/';
|
||||
+ }
|
||||
+ cleanpath[idx] = '\0';
|
||||
+
|
||||
+ return cleanpath;
|
||||
+}
|
||||
+
|
||||
int virFileMakePath(const char *path)
|
||||
{
|
||||
struct stat st;
|
||||
diff -rup libvirt-0.7.1/src/util.h paths/src/util.h
|
||||
--- libvirt-0.7.1/src/util.h 2010-05-26 12:48:48.749342000 -0400
|
||||
+++ paths/src/util.h 2010-05-26 12:56:57.494264000 -0400
|
||||
@@ -107,6 +107,9 @@ char *virFindFileInPath(const char *file
|
||||
|
||||
int virFileExists(const char *path);
|
||||
|
||||
+char *virFileSanitizePath(const char *path);
|
||||
+
|
||||
+
|
||||
int virFileMakePath(const char *path);
|
||||
|
||||
int virFileBuildPath(const char *dir,
|
||||
@@ -1,465 +0,0 @@
|
||||
From 332979bb680d833529ab9cecac6828c6ce54d731 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Fri, 14 Aug 2009 08:31:10 +0100
|
||||
Subject: [PATCH] Add host PCI device hotplug support
|
||||
|
||||
Attaching a host PCI device to a qemu guest is done with a
|
||||
straightforward 'pci_add pci_addr auto host host=XX:XX.X' command.
|
||||
|
||||
Like with NIC and disk hotplug, we need to retain the guest PCI address
|
||||
assigned by qemu so that we can use it for hot-unplug.
|
||||
|
||||
Identifying a device for detach is done using the host PCI address.
|
||||
|
||||
Managed mode is handled by detaching/resetting the device before
|
||||
attaching it to the guest and re-attaching it after detaching it from
|
||||
the guest.
|
||||
|
||||
(cherry picked from commit 7636ef4630fc15c3d559eceb5b5c4fb1524b7c5a)
|
||||
(cherry picked from commit 0c5b7b93a3cdb197c55d79c2605e9e19e3af43f5)
|
||||
(cherry picked from commit 60ff07585ca8f7e639fed477e2e2cf79ce1c5c21)
|
||||
(cherry picked from commit 4e12af5623e4a962a6bb911af06fa29aa85befba)
|
||||
(cherry picked from commit 4dbecff9fbd5b5d1154bc7a41a5d4dd00533b359)
|
||||
(cherry picked from commit 12edef9a6aca5bd9a2ea18b73ca862f615684d84)
|
||||
(cherry picked from commit 457e05062863a35c7efb35470886b9b83a49d04d)
|
||||
(cherry picked from commit e8ad33931296c67de0538e78d12e21706a826d37)
|
||||
|
||||
Fedora-patch: libvirt-add-pci-hostdev-hotplug-support.patch
|
||||
---
|
||||
src/domain_conf.c | 33 +++++-
|
||||
src/domain_conf.h | 13 +++
|
||||
src/libvirt_private.syms | 2 +
|
||||
src/qemu_driver.c | 266 ++++++++++++++++++++++++++++++++++++++++++++--
|
||||
4 files changed, 300 insertions(+), 14 deletions(-)
|
||||
|
||||
diff --git a/src/domain_conf.c b/src/domain_conf.c
|
||||
index 2301a96..bad53f7 100644
|
||||
--- a/src/domain_conf.c
|
||||
+++ b/src/domain_conf.c
|
||||
@@ -1977,7 +1977,8 @@ out:
|
||||
static int
|
||||
virDomainHostdevSubsysPciDefParseXML(virConnectPtr conn,
|
||||
const xmlNodePtr node,
|
||||
- virDomainHostdevDefPtr def) {
|
||||
+ virDomainHostdevDefPtr def,
|
||||
+ int flags) {
|
||||
|
||||
int ret = -1;
|
||||
xmlNodePtr cur;
|
||||
@@ -2049,6 +2050,20 @@ virDomainHostdevSubsysPciDefParseXML(virConnectPtr conn,
|
||||
_("pci address needs function id"));
|
||||
goto out;
|
||||
}
|
||||
+ } else if ((flags & VIR_DOMAIN_XML_INTERNAL_STATUS) &&
|
||||
+ xmlStrEqual(cur->name, BAD_CAST "state")) {
|
||||
+ char *devaddr = virXMLPropString(cur, "devaddr");
|
||||
+ if (devaddr &&
|
||||
+ sscanf(devaddr, "%x:%x:%x",
|
||||
+ &def->source.subsys.u.pci.guest_addr.domain,
|
||||
+ &def->source.subsys.u.pci.guest_addr.bus,
|
||||
+ &def->source.subsys.u.pci.guest_addr.slot) < 3) {
|
||||
+ virDomainReportError(conn, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Unable to parse devaddr parameter '%s'"),
|
||||
+ devaddr);
|
||||
+ VIR_FREE(devaddr);
|
||||
+ goto out;
|
||||
+ }
|
||||
} else {
|
||||
virDomainReportError(conn, VIR_ERR_INTERNAL_ERROR,
|
||||
_("unknown pci source type '%s'"),
|
||||
@@ -2123,7 +2138,7 @@ virDomainHostdevDefParseXML(virConnectPtr conn,
|
||||
}
|
||||
if (def->mode == VIR_DOMAIN_HOSTDEV_MODE_SUBSYS &&
|
||||
def->source.subsys.type == VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI) {
|
||||
- if (virDomainHostdevSubsysPciDefParseXML(conn, cur, def) < 0)
|
||||
+ if (virDomainHostdevSubsysPciDefParseXML(conn, cur, def, flags) < 0)
|
||||
goto error;
|
||||
}
|
||||
} else {
|
||||
@@ -3937,7 +3952,8 @@ virDomainGraphicsDefFormat(virConnectPtr conn,
|
||||
static int
|
||||
virDomainHostdevDefFormat(virConnectPtr conn,
|
||||
virBufferPtr buf,
|
||||
- virDomainHostdevDefPtr def)
|
||||
+ virDomainHostdevDefPtr def,
|
||||
+ int flags)
|
||||
{
|
||||
const char *mode = virDomainHostdevModeTypeToString(def->mode);
|
||||
const char *type;
|
||||
@@ -3978,6 +3994,15 @@ virDomainHostdevDefFormat(virConnectPtr conn,
|
||||
def->source.subsys.u.pci.bus,
|
||||
def->source.subsys.u.pci.slot,
|
||||
def->source.subsys.u.pci.function);
|
||||
+ if (flags & VIR_DOMAIN_XML_INTERNAL_STATUS) {
|
||||
+ virBufferAddLit(buf, " <state");
|
||||
+ if (virHostdevHasValidGuestAddr(def))
|
||||
+ virBufferVSprintf(buf, " devaddr='%.4x:%.2x:%.2x'",
|
||||
+ def->source.subsys.u.pci.guest_addr.domain,
|
||||
+ def->source.subsys.u.pci.guest_addr.bus,
|
||||
+ def->source.subsys.u.pci.guest_addr.slot);
|
||||
+ virBufferAddLit(buf, "/>\n");
|
||||
+ }
|
||||
}
|
||||
|
||||
virBufferAddLit(buf, " </source>\n");
|
||||
@@ -4192,7 +4217,7 @@ char *virDomainDefFormat(virConnectPtr conn,
|
||||
goto cleanup;
|
||||
|
||||
for (n = 0 ; n < def->nhostdevs ; n++)
|
||||
- if (virDomainHostdevDefFormat(conn, &buf, def->hostdevs[n]) < 0)
|
||||
+ if (virDomainHostdevDefFormat(conn, &buf, def->hostdevs[n], flags) < 0)
|
||||
goto cleanup;
|
||||
|
||||
virBufferAddLit(&buf, " </devices>\n");
|
||||
diff --git a/src/domain_conf.h b/src/domain_conf.h
|
||||
index 63fca76..44302be 100644
|
||||
--- a/src/domain_conf.h
|
||||
+++ b/src/domain_conf.h
|
||||
@@ -391,6 +391,11 @@ struct _virDomainHostdevDef {
|
||||
unsigned bus;
|
||||
unsigned slot;
|
||||
unsigned function;
|
||||
+ struct {
|
||||
+ unsigned domain;
|
||||
+ unsigned bus;
|
||||
+ unsigned slot;
|
||||
+ } guest_addr;
|
||||
} pci;
|
||||
} u;
|
||||
} subsys;
|
||||
@@ -404,6 +409,14 @@ struct _virDomainHostdevDef {
|
||||
char* target;
|
||||
};
|
||||
|
||||
+static inline int
|
||||
+virHostdevHasValidGuestAddr(virDomainHostdevDefPtr def)
|
||||
+{
|
||||
+ return def->source.subsys.u.pci.guest_addr.domain ||
|
||||
+ def->source.subsys.u.pci.guest_addr.bus ||
|
||||
+ def->source.subsys.u.pci.guest_addr.slot;
|
||||
+}
|
||||
+
|
||||
/* Flags for the 'type' field in next struct */
|
||||
enum virDomainDeviceType {
|
||||
VIR_DOMAIN_DEVICE_DISK,
|
||||
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
|
||||
index 4f1b01f..22131c4 100644
|
||||
--- a/src/libvirt_private.syms
|
||||
+++ b/src/libvirt_private.syms
|
||||
@@ -88,6 +88,8 @@ virDomainGetRootFilesystem;
|
||||
virDomainGraphicsTypeFromString;
|
||||
virDomainGraphicsDefFree;
|
||||
virDomainHostdevDefFree;
|
||||
+virDomainHostdevModeTypeToString;
|
||||
+virDomainHostdevSubsysTypeToString;
|
||||
virDomainInputDefFree;
|
||||
virDomainLifecycleTypeFromString;
|
||||
virDomainLifecycleTypeToString;
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index cbc27c4..99dac52 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -5258,9 +5258,91 @@ cleanup:
|
||||
return -1;
|
||||
}
|
||||
|
||||
-static int qemudDomainAttachHostDevice(virConnectPtr conn,
|
||||
- virDomainObjPtr vm,
|
||||
- virDomainDeviceDefPtr dev)
|
||||
+static int qemudDomainAttachHostPciDevice(virConnectPtr conn,
|
||||
+ struct qemud_driver *driver,
|
||||
+ virDomainObjPtr vm,
|
||||
+ virDomainDeviceDefPtr dev)
|
||||
+{
|
||||
+ virDomainHostdevDefPtr hostdev = dev->data.hostdev;
|
||||
+ char *cmd, *reply;
|
||||
+ unsigned domain, bus, slot;
|
||||
+ pciDevice *pci;
|
||||
+
|
||||
+ if (VIR_REALLOC_N(vm->def->hostdevs, vm->def->nhostdevs+1) < 0) {
|
||||
+ virReportOOMError(conn);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ pci = pciGetDevice(conn,
|
||||
+ hostdev->source.subsys.u.pci.domain,
|
||||
+ hostdev->source.subsys.u.pci.bus,
|
||||
+ hostdev->source.subsys.u.pci.slot,
|
||||
+ hostdev->source.subsys.u.pci.function);
|
||||
+ if (!dev)
|
||||
+ return -1;
|
||||
+
|
||||
+ if ((hostdev->managed && pciDettachDevice(conn, pci) < 0) ||
|
||||
+ pciResetDevice(conn, pci, driver->activePciHostdevs) < 0) {
|
||||
+ pciFreeDevice(conn, pci);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ if (pciDeviceListAdd(conn, driver->activePciHostdevs, pci) < 0) {
|
||||
+ pciFreeDevice(conn, pci);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ cmd = reply = NULL;
|
||||
+
|
||||
+ if (virAsprintf(&cmd, "pci_add pci_addr=auto host host=%.2x:%.2x.%.1x",
|
||||
+ hostdev->source.subsys.u.pci.bus,
|
||||
+ hostdev->source.subsys.u.pci.slot,
|
||||
+ hostdev->source.subsys.u.pci.function) < 0) {
|
||||
+ virReportOOMError(conn);
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ if (qemudMonitorCommand(vm, cmd, &reply) < 0) {
|
||||
+ qemudReportError(conn, dom, NULL, VIR_ERR_OPERATION_FAILED,
|
||||
+ "%s", _("cannot attach host pci device"));
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ if (strstr(reply, "invalid type: host")) {
|
||||
+ qemudReportError(conn, dom, NULL, VIR_ERR_NO_SUPPORT, "%s",
|
||||
+ _("PCI device assignment is not supported by this version of qemu"));
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ if (qemudParsePciAddReply(vm, reply, &domain, &bus, &slot) < 0) {
|
||||
+ qemudReportError(conn, dom, NULL, VIR_ERR_OPERATION_FAILED,
|
||||
+ _("parsing pci_add reply failed: %s"), reply);
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ hostdev->source.subsys.u.pci.guest_addr.domain = domain;
|
||||
+ hostdev->source.subsys.u.pci.guest_addr.bus = bus;
|
||||
+ hostdev->source.subsys.u.pci.guest_addr.slot = slot;
|
||||
+
|
||||
+ vm->def->hostdevs[vm->def->nhostdevs++] = hostdev;
|
||||
+
|
||||
+ VIR_FREE(reply);
|
||||
+ VIR_FREE(cmd);
|
||||
+
|
||||
+ return 0;
|
||||
+
|
||||
+error:
|
||||
+ pciDeviceListDel(conn, driver->activePciHostdevs, pci);
|
||||
+
|
||||
+ VIR_FREE(reply);
|
||||
+ VIR_FREE(cmd);
|
||||
+
|
||||
+ return -1;
|
||||
+}
|
||||
+
|
||||
+static int qemudDomainAttachHostUsbDevice(virConnectPtr conn,
|
||||
+ virDomainObjPtr vm,
|
||||
+ virDomainDeviceDefPtr dev)
|
||||
{
|
||||
int ret;
|
||||
char *cmd, *reply;
|
||||
@@ -5310,6 +5392,36 @@ static int qemudDomainAttachHostDevice(virConnectPtr conn,
|
||||
return 0;
|
||||
}
|
||||
|
||||
+static int qemudDomainAttachHostDevice(virConnectPtr conn,
|
||||
+ struct qemud_driver *driver,
|
||||
+ virDomainObjPtr vm,
|
||||
+ virDomainDeviceDefPtr dev)
|
||||
+{
|
||||
+ virDomainHostdevDefPtr hostdev = dev->data.hostdev;
|
||||
+
|
||||
+ if (hostdev->mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS) {
|
||||
+ qemudReportError(conn, dom, NULL, VIR_ERR_NO_SUPPORT,
|
||||
+ _("hostdev mode '%s' not supported"),
|
||||
+ virDomainHostdevModeTypeToString(hostdev->mode));
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ if (qemuDomainSetDeviceOwnership(conn, driver, dev, 0) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ switch (hostdev->source.subsys.type) {
|
||||
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI:
|
||||
+ return qemudDomainAttachHostPciDevice(conn, driver, vm, dev);
|
||||
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB:
|
||||
+ return qemudDomainAttachHostUsbDevice(conn, vm, dev);
|
||||
+ default:
|
||||
+ qemudReportError(conn, dom, NULL, VIR_ERR_NO_SUPPORT,
|
||||
+ _("hostdev subsys type '%s' not supported"),
|
||||
+ virDomainHostdevSubsysTypeToString(hostdev->source.subsys.type));
|
||||
+ return -1;
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
static int qemudDomainAttachDevice(virDomainPtr dom,
|
||||
const char *xml) {
|
||||
struct qemud_driver *driver = dom->conn->privateData;
|
||||
@@ -5411,13 +5523,8 @@ static int qemudDomainAttachDevice(virDomainPtr dom,
|
||||
}
|
||||
} else if (dev->type == VIR_DOMAIN_DEVICE_NET) {
|
||||
ret = qemudDomainAttachNetDevice(dom->conn, driver, vm, dev, qemuCmdFlags);
|
||||
- } else if (dev->type == VIR_DOMAIN_DEVICE_HOSTDEV &&
|
||||
- dev->data.hostdev->mode == VIR_DOMAIN_HOSTDEV_MODE_SUBSYS &&
|
||||
- dev->data.hostdev->source.subsys.type == VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB) {
|
||||
- if (qemuDomainSetDeviceOwnership(dom->conn, driver, dev, 0) < 0)
|
||||
- goto cleanup;
|
||||
-
|
||||
- ret = qemudDomainAttachHostDevice(dom->conn, vm, dev);
|
||||
+ } else if (dev->type == VIR_DOMAIN_DEVICE_HOSTDEV) {
|
||||
+ ret = qemudDomainAttachHostDevice(dom->conn, driver, vm, dev);
|
||||
} else {
|
||||
qemudReportError(dom->conn, dom, NULL, VIR_ERR_NO_SUPPORT,
|
||||
_("device type '%s' cannot be attached"),
|
||||
@@ -5630,6 +5737,143 @@ cleanup:
|
||||
return ret;
|
||||
}
|
||||
|
||||
+static int qemudDomainDetachHostPciDevice(virConnectPtr conn,
|
||||
+ struct qemud_driver *driver,
|
||||
+ virDomainObjPtr vm,
|
||||
+ virDomainDeviceDefPtr dev)
|
||||
+{
|
||||
+ virDomainHostdevDefPtr detach;
|
||||
+ char *cmd, *reply;
|
||||
+ int i, ret;
|
||||
+ pciDevice *pci;
|
||||
+
|
||||
+ for (i = 0 ; i < vm->def->nhostdevs ; i++) {
|
||||
+ unsigned domain = vm->def->hostdevs[i]->source.subsys.u.pci.domain;
|
||||
+ unsigned bus = vm->def->hostdevs[i]->source.subsys.u.pci.bus;
|
||||
+ unsigned slot = vm->def->hostdevs[i]->source.subsys.u.pci.slot;
|
||||
+ unsigned function = vm->def->hostdevs[i]->source.subsys.u.pci.function;
|
||||
+
|
||||
+ if (dev->data.hostdev->source.subsys.u.pci.domain == domain &&
|
||||
+ dev->data.hostdev->source.subsys.u.pci.bus == bus &&
|
||||
+ dev->data.hostdev->source.subsys.u.pci.slot == slot &&
|
||||
+ dev->data.hostdev->source.subsys.u.pci.function == function) {
|
||||
+ detach = vm->def->hostdevs[i];
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ if (!detach) {
|
||||
+ qemudReportError(conn, NULL, NULL, VIR_ERR_OPERATION_FAILED,
|
||||
+ _("host pci device %.4x:%.2x:%.2x.%.1x not found"),
|
||||
+ dev->data.hostdev->source.subsys.u.pci.domain,
|
||||
+ dev->data.hostdev->source.subsys.u.pci.bus,
|
||||
+ dev->data.hostdev->source.subsys.u.pci.slot,
|
||||
+ dev->data.hostdev->source.subsys.u.pci.function);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ if (!virHostdevHasValidGuestAddr(detach)) {
|
||||
+ qemudReportError(conn, NULL, NULL, VIR_ERR_OPERATION_FAILED,
|
||||
+ "%s", _("hostdev cannot be detached - device state missing"));
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ if (virAsprintf(&cmd, "pci_del pci_addr=%.4x:%.2x:%.2x",
|
||||
+ detach->source.subsys.u.pci.guest_addr.domain,
|
||||
+ detach->source.subsys.u.pci.guest_addr.bus,
|
||||
+ detach->source.subsys.u.pci.guest_addr.slot) < 0) {
|
||||
+ virReportOOMError(conn);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ if (qemudMonitorCommand(vm, cmd, &reply) < 0) {
|
||||
+ qemudReportError(conn, dom, NULL, VIR_ERR_OPERATION_FAILED,
|
||||
+ "%s", _("cannot detach host pci device"));
|
||||
+ VIR_FREE(cmd);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ DEBUG("%s: pci_del reply: %s", vm->def->name, reply);
|
||||
+
|
||||
+ /* If the command fails due to a wrong PCI address qemu prints
|
||||
+ * 'invalid pci address'; nothing is printed on success */
|
||||
+ if (strstr(reply, "Invalid pci address")) {
|
||||
+ qemudReportError(conn, NULL, NULL, VIR_ERR_OPERATION_FAILED,
|
||||
+ _("failed to detach host pci device: invalid PCI address %.4x:%.2x:%.2x: %s"),
|
||||
+ detach->source.subsys.u.pci.guest_addr.domain,
|
||||
+ detach->source.subsys.u.pci.guest_addr.bus,
|
||||
+ detach->source.subsys.u.pci.guest_addr.slot,
|
||||
+ reply);
|
||||
+ VIR_FREE(reply);
|
||||
+ VIR_FREE(cmd);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ VIR_FREE(reply);
|
||||
+ VIR_FREE(cmd);
|
||||
+
|
||||
+ ret = 0;
|
||||
+
|
||||
+ pci = pciGetDevice(conn,
|
||||
+ detach->source.subsys.u.pci.domain,
|
||||
+ detach->source.subsys.u.pci.bus,
|
||||
+ detach->source.subsys.u.pci.slot,
|
||||
+ detach->source.subsys.u.pci.function);
|
||||
+ if (!pci)
|
||||
+ ret = -1;
|
||||
+ else {
|
||||
+ pciDeviceListDel(conn, driver->activePciHostdevs, pci);
|
||||
+ if (pciResetDevice(conn, pci, driver->activePciHostdevs) < 0)
|
||||
+ ret = -1;
|
||||
+ if (detach->managed && pciReAttachDevice(conn, pci) < 0)
|
||||
+ ret = -1;
|
||||
+ pciFreeDevice(conn, pci);
|
||||
+ }
|
||||
+
|
||||
+ if (i != --vm->def->nhostdevs)
|
||||
+ memmove(&vm->def->hostdevs[i],
|
||||
+ &vm->def->hostdevs[i+1],
|
||||
+ sizeof(*vm->def->hostdevs) * (vm->def->nhostdevs-i));
|
||||
+ if (VIR_REALLOC_N(vm->def->hostdevs, vm->def->nhostdevs) < 0) {
|
||||
+ virReportOOMError(conn);
|
||||
+ ret = -1;
|
||||
+ }
|
||||
+
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
+static int qemudDomainDetachHostDevice(virConnectPtr conn,
|
||||
+ struct qemud_driver *driver,
|
||||
+ virDomainObjPtr vm,
|
||||
+ virDomainDeviceDefPtr dev)
|
||||
+{
|
||||
+ virDomainHostdevDefPtr hostdev = dev->data.hostdev;
|
||||
+ int ret;
|
||||
+
|
||||
+ if (hostdev->mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS) {
|
||||
+ qemudReportError(conn, dom, NULL, VIR_ERR_NO_SUPPORT,
|
||||
+ _("hostdev mode '%s' not supported"),
|
||||
+ virDomainHostdevModeTypeToString(hostdev->mode));
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ switch (hostdev->source.subsys.type) {
|
||||
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI:
|
||||
+ ret = qemudDomainDetachHostPciDevice(conn, driver, vm, dev);
|
||||
+ break;
|
||||
+ default:
|
||||
+ qemudReportError(conn, dom, NULL, VIR_ERR_NO_SUPPORT,
|
||||
+ _("hostdev subsys type '%s' not supported"),
|
||||
+ virDomainHostdevSubsysTypeToString(hostdev->source.subsys.type));
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ if (qemuDomainSetDeviceOwnership(conn, driver, dev, 1) < 0)
|
||||
+ VIR_WARN0("Fail to restore disk device ownership");
|
||||
+
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
static int qemudDomainDetachDevice(virDomainPtr dom,
|
||||
const char *xml) {
|
||||
struct qemud_driver *driver = dom->conn->privateData;
|
||||
@@ -5670,6 +5914,8 @@ static int qemudDomainDetachDevice(virDomainPtr dom,
|
||||
VIR_WARN0("Fail to restore disk device ownership");
|
||||
} else if (dev->type == VIR_DOMAIN_DEVICE_NET) {
|
||||
ret = qemudDomainDetachNetDevice(dom->conn, vm, dev);
|
||||
+ } else if (dev->type == VIR_DOMAIN_DEVICE_HOSTDEV) {
|
||||
+ ret = qemudDomainDetachHostDevice(dom->conn, driver, vm, dev);
|
||||
} else
|
||||
qemudReportError(dom->conn, dom, NULL, VIR_ERR_NO_SUPPORT,
|
||||
"%s", _("only SCSI or virtio disk device can be detached dynamically"));
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,43 +0,0 @@
|
||||
From 100eb35a80932cd9a162c38ecd2ab8b01894fb61 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Mon, 17 Aug 2009 15:05:22 +0100
|
||||
Subject: [PATCH] Cosmetic change to 'virsh nodedev-list --tree' output
|
||||
|
||||
Maybe it's just me, but I try to select an item from the tree using
|
||||
double-click and get annoyed when "+-" gets included in the selection.
|
||||
|
||||
* src/virsh.c: add a space between "+-" and the node device name
|
||||
in 'virsh nodedev-list --tree'
|
||||
|
||||
(cherry picked from commit 097c818bf00b3777778ffc32fea3a6ed1e741e2b)
|
||||
|
||||
Fedora-patch: libvirt-add-space-to-nodedev-list-tree.patch
|
||||
---
|
||||
src/virsh.c | 4 +++-
|
||||
1 files changed, 3 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/virsh.c b/src/virsh.c
|
||||
index 94c3c4e..2d0cf81 100644
|
||||
--- a/src/virsh.c
|
||||
+++ b/src/virsh.c
|
||||
@@ -5370,6 +5370,8 @@ cmdNodeListDevicesPrint(vshControl *ctl,
|
||||
if (depth && depth < MAX_DEPTH) {
|
||||
indentBuf[indentIdx] = '+';
|
||||
indentBuf[indentIdx+1] = '-';
|
||||
+ indentBuf[indentIdx+2] = ' ';
|
||||
+ indentBuf[indentIdx+3] = '\0';
|
||||
}
|
||||
|
||||
/* Print this device */
|
||||
@@ -5398,7 +5400,7 @@ cmdNodeListDevicesPrint(vshControl *ctl,
|
||||
/* If there is a child device, then print another blank line */
|
||||
if (nextlastdev != -1) {
|
||||
vshPrint(ctl, "%s", indentBuf);
|
||||
- vshPrint(ctl, " |\n");
|
||||
+ vshPrint(ctl, " |\n");
|
||||
}
|
||||
|
||||
/* Finally print all children */
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,812 +0,0 @@
|
||||
From 89eefbd116ae74c3a5cfcfc74a31a40b83c726c3 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Mon, 17 Aug 2009 15:05:23 +0100
|
||||
Subject: [PATCH] Maintain a list of active PCI hostdevs and use it in pciResetDevice()
|
||||
|
||||
https://bugzilla.redhat.com/499678
|
||||
|
||||
First we add a pciDeviceList type and add a qemuGetPciHostDeviceList()
|
||||
function to build a list from a domain definition. Use this in
|
||||
prepare/re-attach to simplify things and eliminate the multiple
|
||||
pciGetDevice() calls.
|
||||
|
||||
Then, as we start/shutdown guests we can add or delete devices as
|
||||
appropriate from a list of active devices.
|
||||
|
||||
Finally, in pciReset(), we can use this to determine whether its safe to
|
||||
reset a device as a side effect of resetting another device.
|
||||
|
||||
(cherry picked from commit 78675b228b76a83f83d64856bfb63b9e14c103a0)
|
||||
(cherry picked from commit e8ad33931296c67de0538e78d12e21706a826d37)
|
||||
|
||||
Fedora-patch: libvirt-allow-pci-hostdev-reset-to-reset-other-devices.patch
|
||||
---
|
||||
src/libvirt_private.syms | 7 +-
|
||||
src/pci.c | 211 +++++++++++++++++++++++++++++++++--------
|
||||
src/pci.h | 23 +++++-
|
||||
src/qemu_conf.h | 3 +
|
||||
src/qemu_driver.c | 237 +++++++++++++++++++++++++++-------------------
|
||||
src/xen_unified.c | 2 +-
|
||||
6 files changed, 339 insertions(+), 144 deletions(-)
|
||||
|
||||
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
|
||||
index bd63692..4f1b01f 100644
|
||||
--- a/src/libvirt_private.syms
|
||||
+++ b/src/libvirt_private.syms
|
||||
@@ -278,7 +278,12 @@ pciFreeDevice;
|
||||
pciDettachDevice;
|
||||
pciReAttachDevice;
|
||||
pciResetDevice;
|
||||
-
|
||||
+pciDeviceSetManaged;
|
||||
+pciDeviceGetManaged;
|
||||
+pciDeviceListNew;
|
||||
+pciDeviceListFree;
|
||||
+pciDeviceListAdd;
|
||||
+pciDeviceListDel;
|
||||
|
||||
# qparams.h
|
||||
qparam_get_query;
|
||||
diff --git a/src/pci.c b/src/pci.c
|
||||
index 74f7ef0..96e5d6d 100644
|
||||
--- a/src/pci.c
|
||||
+++ b/src/pci.c
|
||||
@@ -63,6 +63,7 @@ struct _pciDevice {
|
||||
unsigned pci_pm_cap_pos;
|
||||
unsigned has_flr : 1;
|
||||
unsigned has_pm_reset : 1;
|
||||
+ unsigned managed : 1;
|
||||
};
|
||||
|
||||
/* For virReportOOMError() and virReportSystemError() */
|
||||
@@ -225,7 +226,7 @@ pciWrite32(pciDevice *dev, unsigned pos, uint32_t val)
|
||||
pciWrite(dev, pos, &buf[0], sizeof(buf));
|
||||
}
|
||||
|
||||
-typedef int (*pciIterPredicate)(pciDevice *, pciDevice *);
|
||||
+typedef int (*pciIterPredicate)(pciDevice *, pciDevice *, void *);
|
||||
|
||||
/* Iterate over available PCI devices calling @predicate
|
||||
* to compare each one to @dev.
|
||||
@@ -236,7 +237,8 @@ static int
|
||||
pciIterDevices(virConnectPtr conn,
|
||||
pciIterPredicate predicate,
|
||||
pciDevice *dev,
|
||||
- pciDevice **matched)
|
||||
+ pciDevice **matched,
|
||||
+ void *data)
|
||||
{
|
||||
DIR *dir;
|
||||
struct dirent *entry;
|
||||
@@ -254,7 +256,7 @@ pciIterDevices(virConnectPtr conn,
|
||||
|
||||
while ((entry = readdir(dir))) {
|
||||
unsigned domain, bus, slot, function;
|
||||
- pciDevice *try;
|
||||
+ pciDevice *check;
|
||||
|
||||
/* Ignore '.' and '..' */
|
||||
if (entry->d_name[0] == '.')
|
||||
@@ -266,18 +268,18 @@ pciIterDevices(virConnectPtr conn,
|
||||
continue;
|
||||
}
|
||||
|
||||
- try = pciGetDevice(conn, domain, bus, slot, function);
|
||||
- if (!try) {
|
||||
+ check = pciGetDevice(conn, domain, bus, slot, function);
|
||||
+ if (!check) {
|
||||
ret = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
- if (predicate(try, dev)) {
|
||||
- VIR_DEBUG("%s %s: iter matched on %s", dev->id, dev->name, try->name);
|
||||
- *matched = try;
|
||||
+ if (predicate(dev, check, data)) {
|
||||
+ VIR_DEBUG("%s %s: iter matched on %s", dev->id, dev->name, check->name);
|
||||
+ *matched = check;
|
||||
break;
|
||||
}
|
||||
- pciFreeDevice(conn, try);
|
||||
+ pciFreeDevice(conn, check);
|
||||
}
|
||||
closedir(dir);
|
||||
return ret;
|
||||
@@ -379,63 +381,70 @@ pciDetectPowerManagementReset(pciDevice *dev)
|
||||
return 0;
|
||||
}
|
||||
|
||||
-/* Any devices other than the one supplied on the same domain/bus ? */
|
||||
+/* Any active devices other than the one supplied on the same domain/bus ? */
|
||||
static int
|
||||
-pciSharesBus(pciDevice *a, pciDevice *b)
|
||||
+pciSharesBusWithActive(pciDevice *dev, pciDevice *check, void *data)
|
||||
{
|
||||
- return
|
||||
- a->domain == b->domain &&
|
||||
- a->bus == b->bus &&
|
||||
- (a->slot != b->slot ||
|
||||
- a->function != b->function);
|
||||
-}
|
||||
+ pciDeviceList *activeDevs = data;
|
||||
|
||||
-static int
|
||||
-pciBusContainsOtherDevices(virConnectPtr conn, pciDevice *dev)
|
||||
-{
|
||||
- pciDevice *matched = NULL;
|
||||
- if (pciIterDevices(conn, pciSharesBus, dev, &matched) < 0)
|
||||
- return 1;
|
||||
- if (!matched)
|
||||
+ if (dev->domain != check->domain ||
|
||||
+ dev->bus != check->bus ||
|
||||
+ (check->slot == check->slot &&
|
||||
+ check->function == check->function))
|
||||
+ return 0;
|
||||
+
|
||||
+ if (activeDevs && !pciDeviceListFind(activeDevs, check))
|
||||
return 0;
|
||||
- pciFreeDevice(conn, matched);
|
||||
+
|
||||
return 1;
|
||||
}
|
||||
|
||||
-/* Is @a the parent of @b ? */
|
||||
+static pciDevice *
|
||||
+pciBusContainsActiveDevices(virConnectPtr conn,
|
||||
+ pciDevice *dev,
|
||||
+ pciDeviceList *activeDevs)
|
||||
+{
|
||||
+ pciDevice *active = NULL;
|
||||
+ if (pciIterDevices(conn, pciSharesBusWithActive,
|
||||
+ dev, &active, activeDevs) < 0)
|
||||
+ return NULL;
|
||||
+ return active;
|
||||
+}
|
||||
+
|
||||
+/* Is @check the parent of @dev ? */
|
||||
static int
|
||||
-pciIsParent(pciDevice *a, pciDevice *b)
|
||||
+pciIsParent(pciDevice *dev, pciDevice *check, void *data ATTRIBUTE_UNUSED)
|
||||
{
|
||||
uint16_t device_class;
|
||||
uint8_t header_type, secondary, subordinate;
|
||||
|
||||
- if (a->domain != b->domain)
|
||||
+ if (dev->domain != check->domain)
|
||||
return 0;
|
||||
|
||||
/* Is it a bridge? */
|
||||
- device_class = pciRead16(a, PCI_CLASS_DEVICE);
|
||||
+ device_class = pciRead16(check, PCI_CLASS_DEVICE);
|
||||
if (device_class != PCI_CLASS_BRIDGE_PCI)
|
||||
return 0;
|
||||
|
||||
/* Is it a plane? */
|
||||
- header_type = pciRead8(a, PCI_HEADER_TYPE);
|
||||
+ header_type = pciRead8(check, PCI_HEADER_TYPE);
|
||||
if ((header_type & PCI_HEADER_TYPE_MASK) != PCI_HEADER_TYPE_BRIDGE)
|
||||
return 0;
|
||||
|
||||
- secondary = pciRead8(a, PCI_SECONDARY_BUS);
|
||||
- subordinate = pciRead8(a, PCI_SUBORDINATE_BUS);
|
||||
+ secondary = pciRead8(check, PCI_SECONDARY_BUS);
|
||||
+ subordinate = pciRead8(check, PCI_SUBORDINATE_BUS);
|
||||
|
||||
- VIR_DEBUG("%s %s: found parent device %s\n", b->id, b->name, a->name);
|
||||
+ VIR_DEBUG("%s %s: found parent device %s\n", dev->id, dev->name, check->name);
|
||||
|
||||
/* No, it's superman! */
|
||||
- return (b->bus >= secondary && b->bus <= subordinate);
|
||||
+ return (dev->bus >= secondary && dev->bus <= subordinate);
|
||||
}
|
||||
|
||||
static pciDevice *
|
||||
pciGetParentDevice(virConnectPtr conn, pciDevice *dev)
|
||||
{
|
||||
pciDevice *parent = NULL;
|
||||
- pciIterDevices(conn, pciIsParent, dev, &parent);
|
||||
+ pciIterDevices(conn, pciIsParent, dev, &parent, NULL);
|
||||
return parent;
|
||||
}
|
||||
|
||||
@@ -443,9 +452,11 @@ pciGetParentDevice(virConnectPtr conn, pciDevice *dev)
|
||||
* devices behind a bus.
|
||||
*/
|
||||
static int
|
||||
-pciTrySecondaryBusReset(virConnectPtr conn, pciDevice *dev)
|
||||
+pciTrySecondaryBusReset(virConnectPtr conn,
|
||||
+ pciDevice *dev,
|
||||
+ pciDeviceList *activeDevs)
|
||||
{
|
||||
- pciDevice *parent;
|
||||
+ pciDevice *parent, *conflict;
|
||||
uint8_t config_space[PCI_CONF_LEN];
|
||||
uint16_t ctl;
|
||||
int ret = -1;
|
||||
@@ -455,10 +466,10 @@ pciTrySecondaryBusReset(virConnectPtr conn, pciDevice *dev)
|
||||
* In future, we could allow it so long as those devices
|
||||
* are not in use by the host or other guests.
|
||||
*/
|
||||
- if (pciBusContainsOtherDevices(conn, dev)) {
|
||||
+ if ((conflict = pciBusContainsActiveDevices(conn, dev, activeDevs))) {
|
||||
pciReportError(conn, VIR_ERR_NO_SUPPORT,
|
||||
- _("Other devices on bus with %s, not doing bus reset"),
|
||||
- dev->name);
|
||||
+ _("Active %s devices on bus with %s, not doing bus reset"),
|
||||
+ conflict->name, dev->name);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -572,10 +583,18 @@ pciInitDevice(virConnectPtr conn, pciDevice *dev)
|
||||
}
|
||||
|
||||
int
|
||||
-pciResetDevice(virConnectPtr conn, pciDevice *dev)
|
||||
+pciResetDevice(virConnectPtr conn,
|
||||
+ pciDevice *dev,
|
||||
+ pciDeviceList *activeDevs)
|
||||
{
|
||||
int ret = -1;
|
||||
|
||||
+ if (activeDevs && pciDeviceListFind(activeDevs, dev)) {
|
||||
+ pciReportError(conn, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Not resetting active device %s"), dev->name);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
if (!dev->initted && pciInitDevice(conn, dev) < 0)
|
||||
return -1;
|
||||
|
||||
@@ -594,7 +613,7 @@ pciResetDevice(virConnectPtr conn, pciDevice *dev)
|
||||
|
||||
/* Bus reset is not an option with the root bus */
|
||||
if (ret < 0 && dev->bus != 0)
|
||||
- ret = pciTrySecondaryBusReset(conn, dev);
|
||||
+ ret = pciTrySecondaryBusReset(conn, dev, activeDevs);
|
||||
|
||||
if (ret < 0) {
|
||||
virErrorPtr err = virGetLastError();
|
||||
@@ -890,8 +909,116 @@ pciGetDevice(virConnectPtr conn,
|
||||
void
|
||||
pciFreeDevice(virConnectPtr conn ATTRIBUTE_UNUSED, pciDevice *dev)
|
||||
{
|
||||
+ if (!dev)
|
||||
+ return;
|
||||
VIR_DEBUG("%s %s: freeing", dev->id, dev->name);
|
||||
if (dev->fd >= 0)
|
||||
close(dev->fd);
|
||||
VIR_FREE(dev);
|
||||
}
|
||||
+
|
||||
+void pciDeviceSetManaged(pciDevice *dev, unsigned managed)
|
||||
+{
|
||||
+ dev->managed = !!managed;
|
||||
+}
|
||||
+
|
||||
+unsigned pciDeviceGetManaged(pciDevice *dev)
|
||||
+{
|
||||
+ return dev->managed;
|
||||
+}
|
||||
+
|
||||
+pciDeviceList *
|
||||
+pciDeviceListNew(virConnectPtr conn)
|
||||
+{
|
||||
+ pciDeviceList *list;
|
||||
+
|
||||
+ if (VIR_ALLOC(list) < 0) {
|
||||
+ virReportOOMError(conn);
|
||||
+ return NULL;
|
||||
+ }
|
||||
+
|
||||
+ return list;
|
||||
+}
|
||||
+
|
||||
+void
|
||||
+pciDeviceListFree(virConnectPtr conn,
|
||||
+ pciDeviceList *list)
|
||||
+{
|
||||
+ int i;
|
||||
+
|
||||
+ if (!list)
|
||||
+ return;
|
||||
+
|
||||
+ for (i = 0; i < list->count; i++) {
|
||||
+ pciFreeDevice(conn, list->devs[i]);
|
||||
+ list->devs[i] = NULL;
|
||||
+ }
|
||||
+
|
||||
+ list->count = 0;
|
||||
+ VIR_FREE(list->devs);
|
||||
+ VIR_FREE(list);
|
||||
+}
|
||||
+
|
||||
+int
|
||||
+pciDeviceListAdd(virConnectPtr conn,
|
||||
+ pciDeviceList *list,
|
||||
+ pciDevice *dev)
|
||||
+{
|
||||
+ if (pciDeviceListFind(list, dev)) {
|
||||
+ pciReportError(conn, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Device %s is already in use"), dev->name);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ if (VIR_REALLOC_N(list->devs, list->count+1) < 0) {
|
||||
+ virReportOOMError(conn);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ list->devs[list->count++] = dev;
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+void
|
||||
+pciDeviceListDel(virConnectPtr conn ATTRIBUTE_UNUSED,
|
||||
+ pciDeviceList *list,
|
||||
+ pciDevice *dev)
|
||||
+{
|
||||
+ int i;
|
||||
+
|
||||
+ for (i = 0; i < list->count; i++) {
|
||||
+ if (list->devs[i]->domain != dev->domain ||
|
||||
+ list->devs[i]->bus != dev->bus ||
|
||||
+ list->devs[i]->slot != dev->slot ||
|
||||
+ list->devs[i]->function != dev->function)
|
||||
+ continue;
|
||||
+
|
||||
+ pciFreeDevice(conn, list->devs[i]);
|
||||
+
|
||||
+ if (i != --list->count)
|
||||
+ memmove(&list->devs[i],
|
||||
+ &list->devs[i+1],
|
||||
+ sizeof(*list->devs) * (list->count-i));
|
||||
+
|
||||
+ if (VIR_REALLOC_N(list->devs, list->count) < 0) {
|
||||
+ ; /* not fatal */
|
||||
+ }
|
||||
+
|
||||
+ break;
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
+pciDevice *
|
||||
+pciDeviceListFind(pciDeviceList *list, pciDevice *dev)
|
||||
+{
|
||||
+ int i;
|
||||
+
|
||||
+ for (i = 0; i < list->count; i++)
|
||||
+ if (list->devs[i]->domain == dev->domain &&
|
||||
+ list->devs[i]->bus == dev->bus &&
|
||||
+ list->devs[i]->slot == dev->slot &&
|
||||
+ list->devs[i]->function == dev->function)
|
||||
+ return list->devs[i];
|
||||
+ return NULL;
|
||||
+}
|
||||
diff --git a/src/pci.h b/src/pci.h
|
||||
index 47882ef..685b0af 100644
|
||||
--- a/src/pci.h
|
||||
+++ b/src/pci.h
|
||||
@@ -27,6 +27,11 @@
|
||||
|
||||
typedef struct _pciDevice pciDevice;
|
||||
|
||||
+typedef struct {
|
||||
+ unsigned count;
|
||||
+ pciDevice **devs;
|
||||
+} pciDeviceList;
|
||||
+
|
||||
pciDevice *pciGetDevice (virConnectPtr conn,
|
||||
unsigned domain,
|
||||
unsigned bus,
|
||||
@@ -39,6 +44,22 @@ int pciDettachDevice (virConnectPtr conn,
|
||||
int pciReAttachDevice (virConnectPtr conn,
|
||||
pciDevice *dev);
|
||||
int pciResetDevice (virConnectPtr conn,
|
||||
- pciDevice *dev);
|
||||
+ pciDevice *dev,
|
||||
+ pciDeviceList *activeDevs);
|
||||
+void pciDeviceSetManaged(pciDevice *dev,
|
||||
+ unsigned managed);
|
||||
+unsigned pciDeviceGetManaged(pciDevice *dev);
|
||||
+
|
||||
+pciDeviceList *pciDeviceListNew (virConnectPtr conn);
|
||||
+void pciDeviceListFree (virConnectPtr conn,
|
||||
+ pciDeviceList *list);
|
||||
+int pciDeviceListAdd (virConnectPtr conn,
|
||||
+ pciDeviceList *list,
|
||||
+ pciDevice *dev);
|
||||
+void pciDeviceListDel (virConnectPtr conn,
|
||||
+ pciDeviceList *list,
|
||||
+ pciDevice *dev);
|
||||
+pciDevice * pciDeviceListFind (pciDeviceList *list,
|
||||
+ pciDevice *dev);
|
||||
|
||||
#endif /* __VIR_PCI_H__ */
|
||||
diff --git a/src/qemu_conf.h b/src/qemu_conf.h
|
||||
index 517626a..ab9d5e1 100644
|
||||
--- a/src/qemu_conf.h
|
||||
+++ b/src/qemu_conf.h
|
||||
@@ -35,6 +35,7 @@
|
||||
#include "threads.h"
|
||||
#include "security.h"
|
||||
#include "cgroup.h"
|
||||
+#include "pci.h"
|
||||
|
||||
#define qemudDebug(fmt, ...) do {} while(0)
|
||||
|
||||
@@ -107,6 +108,8 @@ struct qemud_driver {
|
||||
|
||||
char *securityDriverName;
|
||||
virSecurityDriverPtr securityDriver;
|
||||
+
|
||||
+ pciDeviceList *activePciHostdevs;
|
||||
};
|
||||
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index fd39fc2..cbc27c4 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -128,6 +128,9 @@ static int qemudDomainSetMemoryBalloon(virConnectPtr conn,
|
||||
static int qemudDetectVcpuPIDs(virConnectPtr conn,
|
||||
virDomainObjPtr vm);
|
||||
|
||||
+static int qemuUpdateActivePciHostdevs(struct qemud_driver *driver,
|
||||
+ virDomainDefPtr def);
|
||||
+
|
||||
static struct qemud_driver *qemu_driver = NULL;
|
||||
|
||||
static int qemuCgroupControllerActive(struct qemud_driver *driver,
|
||||
@@ -320,6 +323,10 @@ qemuReconnectDomain(struct qemud_driver *driver,
|
||||
goto error;
|
||||
}
|
||||
|
||||
+ if (qemuUpdateActivePciHostdevs(driver, obj->def) < 0) {
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
if (obj->def->seclabel.type == VIR_DOMAIN_SECLABEL_DYNAMIC &&
|
||||
driver->securityDriver &&
|
||||
driver->securityDriver->domainReserveSecurityLabel &&
|
||||
@@ -524,6 +531,9 @@ qemudStartup(int privileged) {
|
||||
if ((qemu_driver->caps = qemudCapsInit(NULL)) == NULL)
|
||||
goto out_of_memory;
|
||||
|
||||
+ if ((qemu_driver->activePciHostdevs = pciDeviceListNew(NULL)) == NULL)
|
||||
+ goto error;
|
||||
+
|
||||
if (qemudLoadDriverConfig(qemu_driver, driverConf) < 0) {
|
||||
goto error;
|
||||
}
|
||||
@@ -648,6 +658,7 @@ qemudShutdown(void) {
|
||||
return -1;
|
||||
|
||||
qemuDriverLock(qemu_driver);
|
||||
+ pciDeviceListFree(NULL, qemu_driver->activePciHostdevs);
|
||||
virCapabilitiesFree(qemu_driver->caps);
|
||||
|
||||
virDomainObjListFree(&qemu_driver->domains);
|
||||
@@ -1329,48 +1340,16 @@ static int qemudNextFreeVNCPort(struct qemud_driver *driver ATTRIBUTE_UNUSED) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
-static int qemuPrepareHostDevices(virConnectPtr conn,
|
||||
- virDomainDefPtr def) {
|
||||
+static pciDeviceList *
|
||||
+qemuGetPciHostDeviceList(virConnectPtr conn,
|
||||
+ virDomainDefPtr def)
|
||||
+{
|
||||
+ pciDeviceList *list;
|
||||
int i;
|
||||
|
||||
- /* We have to use 2 loops here. *All* devices must
|
||||
- * be detached before we reset any of them, because
|
||||
- * in some cases you have to reset the whole PCI,
|
||||
- * which impacts all devices on it
|
||||
- */
|
||||
-
|
||||
- for (i = 0 ; i < def->nhostdevs ; i++) {
|
||||
- virDomainHostdevDefPtr hostdev = def->hostdevs[i];
|
||||
-
|
||||
- if (hostdev->mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS)
|
||||
- continue;
|
||||
- if (hostdev->source.subsys.type != VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI)
|
||||
- continue;
|
||||
-
|
||||
- if (hostdev->managed) {
|
||||
- pciDevice *dev = pciGetDevice(conn,
|
||||
- hostdev->source.subsys.u.pci.domain,
|
||||
- hostdev->source.subsys.u.pci.bus,
|
||||
- hostdev->source.subsys.u.pci.slot,
|
||||
- hostdev->source.subsys.u.pci.function);
|
||||
- if (!dev)
|
||||
- goto error;
|
||||
-
|
||||
- if (pciDettachDevice(conn, dev) < 0) {
|
||||
- pciFreeDevice(conn, dev);
|
||||
- goto error;
|
||||
- }
|
||||
-
|
||||
- pciFreeDevice(conn, dev);
|
||||
- } /* else {
|
||||
- XXX validate that non-managed device isn't in use, eg
|
||||
- by checking that device is either un-bound, or bound
|
||||
- to pci-stub.ko
|
||||
- } */
|
||||
- }
|
||||
+ if (!(list = pciDeviceListNew(conn)))
|
||||
+ return NULL;
|
||||
|
||||
- /* Now that all the PCI hostdevs have be dettached, we can safely
|
||||
- * reset them */
|
||||
for (i = 0 ; i < def->nhostdevs ; i++) {
|
||||
virDomainHostdevDefPtr hostdev = def->hostdevs[i];
|
||||
pciDevice *dev;
|
||||
@@ -1385,95 +1364,151 @@ static int qemuPrepareHostDevices(virConnectPtr conn,
|
||||
hostdev->source.subsys.u.pci.bus,
|
||||
hostdev->source.subsys.u.pci.slot,
|
||||
hostdev->source.subsys.u.pci.function);
|
||||
- if (!dev)
|
||||
- goto error;
|
||||
+ if (!dev) {
|
||||
+ pciDeviceListFree(conn, list);
|
||||
+ return NULL;
|
||||
+ }
|
||||
|
||||
- if (pciResetDevice(conn, dev) < 0) {
|
||||
+ if (pciDeviceListAdd(conn, list, dev) < 0) {
|
||||
pciFreeDevice(conn, dev);
|
||||
- goto error;
|
||||
+ pciDeviceListFree(conn, list);
|
||||
+ return NULL;
|
||||
}
|
||||
|
||||
- pciFreeDevice(conn, dev);
|
||||
+ pciDeviceSetManaged(dev, hostdev->managed);
|
||||
}
|
||||
|
||||
- return 0;
|
||||
+ return list;
|
||||
+}
|
||||
|
||||
-error:
|
||||
- return -1;
|
||||
+static int
|
||||
+qemuUpdateActivePciHostdevs(struct qemud_driver *driver,
|
||||
+ virDomainDefPtr def)
|
||||
+{
|
||||
+ pciDeviceList *pcidevs;
|
||||
+ int i, ret;
|
||||
+
|
||||
+ if (!def->nhostdevs)
|
||||
+ return 0;
|
||||
+
|
||||
+ if (!(pcidevs = qemuGetPciHostDeviceList(NULL, def)))
|
||||
+ return -1;
|
||||
+
|
||||
+ ret = 0;
|
||||
+
|
||||
+ for (i = 0; i < pcidevs->count; i++) {
|
||||
+ if (pciDeviceListAdd(NULL,
|
||||
+ driver->activePciHostdevs,
|
||||
+ pcidevs->devs[i]) < 0) {
|
||||
+ ret = -1;
|
||||
+ break;
|
||||
+ }
|
||||
+ pcidevs->devs[i] = NULL;
|
||||
+ }
|
||||
+
|
||||
+ pciDeviceListFree(NULL, pcidevs);
|
||||
+ return ret;
|
||||
}
|
||||
|
||||
-static void
|
||||
-qemuDomainReAttachHostDevices(virConnectPtr conn, virDomainDefPtr def)
|
||||
+static int
|
||||
+qemuPrepareHostDevices(virConnectPtr conn,
|
||||
+ struct qemud_driver *driver,
|
||||
+ virDomainDefPtr def)
|
||||
{
|
||||
+ pciDeviceList *pcidevs;
|
||||
int i;
|
||||
|
||||
- /* Again 2 loops; reset all the devices before re-attach */
|
||||
+ if (!def->nhostdevs)
|
||||
+ return 0;
|
||||
|
||||
- for (i = 0 ; i < def->nhostdevs ; i++) {
|
||||
- virDomainHostdevDefPtr hostdev = def->hostdevs[i];
|
||||
- pciDevice *dev;
|
||||
+ if (!(pcidevs = qemuGetPciHostDeviceList(conn, def)))
|
||||
+ return -1;
|
||||
|
||||
- if (hostdev->mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS)
|
||||
- continue;
|
||||
- if (hostdev->source.subsys.type != VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI)
|
||||
- continue;
|
||||
+ /* We have to use 3 loops here. *All* devices must
|
||||
+ * be detached before we reset any of them, because
|
||||
+ * in some cases you have to reset the whole PCI,
|
||||
+ * which impacts all devices on it. Also, all devices
|
||||
+ * must be reset before being marked as active.
|
||||
+ */
|
||||
|
||||
- dev = pciGetDevice(conn,
|
||||
- hostdev->source.subsys.u.pci.domain,
|
||||
- hostdev->source.subsys.u.pci.bus,
|
||||
- hostdev->source.subsys.u.pci.slot,
|
||||
- hostdev->source.subsys.u.pci.function);
|
||||
- if (!dev) {
|
||||
- virErrorPtr err = virGetLastError();
|
||||
- VIR_ERROR(_("Failed to allocate pciDevice: %s\n"),
|
||||
- err ? err->message : "");
|
||||
- virResetError(err);
|
||||
- continue;
|
||||
- }
|
||||
+ /* XXX validate that non-managed device isn't in use, eg
|
||||
+ * by checking that device is either un-bound, or bound
|
||||
+ * to pci-stub.ko
|
||||
+ */
|
||||
|
||||
- if (pciResetDevice(conn, dev) < 0) {
|
||||
- virErrorPtr err = virGetLastError();
|
||||
- VIR_ERROR(_("Failed to reset PCI device: %s\n"),
|
||||
- err ? err->message : "");
|
||||
- virResetError(err);
|
||||
- }
|
||||
+ for (i = 0; i < pcidevs->count; i++)
|
||||
+ if (pciDeviceGetManaged(pcidevs->devs[i]) &&
|
||||
+ pciDettachDevice(conn, pcidevs->devs[i]) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ /* Now that all the PCI hostdevs have be dettached, we can safely
|
||||
+ * reset them */
|
||||
+ for (i = 0; i < pcidevs->count; i++)
|
||||
+ if (pciResetDevice(conn, pcidevs->devs[i],
|
||||
+ driver->activePciHostdevs) < 0)
|
||||
+ goto error;
|
||||
|
||||
- pciFreeDevice(conn, dev);
|
||||
+ /* Now mark all the devices as active */
|
||||
+ for (i = 0; i < pcidevs->count; i++) {
|
||||
+ if (pciDeviceListAdd(conn,
|
||||
+ driver->activePciHostdevs,
|
||||
+ pcidevs->devs[i]) < 0)
|
||||
+ goto error;
|
||||
+ pcidevs->devs[i] = NULL;
|
||||
}
|
||||
|
||||
- for (i = 0 ; i < def->nhostdevs ; i++) {
|
||||
- virDomainHostdevDefPtr hostdev = def->hostdevs[i];
|
||||
- pciDevice *dev;
|
||||
+ pciDeviceListFree(conn, pcidevs);
|
||||
+ return 0;
|
||||
|
||||
- if (hostdev->mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS)
|
||||
- continue;
|
||||
- if (hostdev->source.subsys.type != VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI)
|
||||
- continue;
|
||||
- if (!hostdev->managed)
|
||||
- continue;
|
||||
+error:
|
||||
+ pciDeviceListFree(conn, pcidevs);
|
||||
+ return -1;
|
||||
+}
|
||||
|
||||
- dev = pciGetDevice(conn,
|
||||
- hostdev->source.subsys.u.pci.domain,
|
||||
- hostdev->source.subsys.u.pci.bus,
|
||||
- hostdev->source.subsys.u.pci.slot,
|
||||
- hostdev->source.subsys.u.pci.function);
|
||||
- if (!dev) {
|
||||
+static void
|
||||
+qemuDomainReAttachHostDevices(virConnectPtr conn,
|
||||
+ struct qemud_driver *driver,
|
||||
+ virDomainDefPtr def)
|
||||
+{
|
||||
+ pciDeviceList *pcidevs;
|
||||
+ int i;
|
||||
+
|
||||
+ if (!def->nhostdevs)
|
||||
+ return;
|
||||
+
|
||||
+ if (!(pcidevs = qemuGetPciHostDeviceList(conn, def))) {
|
||||
+ virErrorPtr err = virGetLastError();
|
||||
+ VIR_ERROR(_("Failed to allocate pciDeviceList: %s\n"),
|
||||
+ err ? err->message : "");
|
||||
+ virResetError(err);
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ /* Again 3 loops; mark all devices as inactive before reset
|
||||
+ * them and reset all the devices before re-attach */
|
||||
+
|
||||
+ for (i = 0; i < pcidevs->count; i++)
|
||||
+ pciDeviceListDel(conn, driver->activePciHostdevs, pcidevs->devs[i]);
|
||||
+
|
||||
+ for (i = 0; i < pcidevs->count; i++)
|
||||
+ if (pciResetDevice(conn, pcidevs->devs[i],
|
||||
+ driver->activePciHostdevs) < 0) {
|
||||
virErrorPtr err = virGetLastError();
|
||||
- VIR_ERROR(_("Failed to allocate pciDevice: %s\n"),
|
||||
+ VIR_ERROR(_("Failed to reset PCI device: %s\n"),
|
||||
err ? err->message : "");
|
||||
virResetError(err);
|
||||
- continue;
|
||||
}
|
||||
|
||||
- if (pciReAttachDevice(conn, dev) < 0) {
|
||||
+ for (i = 0; i < pcidevs->count; i++)
|
||||
+ if (pciDeviceGetManaged(pcidevs->devs[i]) &&
|
||||
+ pciReAttachDevice(conn, pcidevs->devs[i]) < 0) {
|
||||
virErrorPtr err = virGetLastError();
|
||||
VIR_ERROR(_("Failed to re-attach PCI device: %s\n"),
|
||||
err ? err->message : "");
|
||||
virResetError(err);
|
||||
}
|
||||
|
||||
- pciFreeDevice(conn, dev);
|
||||
- }
|
||||
+ pciDeviceListFree(conn, pcidevs);
|
||||
}
|
||||
|
||||
static const char *const defaultDeviceACL[] = {
|
||||
@@ -2001,7 +2036,7 @@ static int qemudStartVMDaemon(virConnectPtr conn,
|
||||
if (qemuSetupCgroup(conn, driver, vm) < 0)
|
||||
goto cleanup;
|
||||
|
||||
- if (qemuPrepareHostDevices(conn, vm->def) < 0)
|
||||
+ if (qemuPrepareHostDevices(conn, driver, vm->def) < 0)
|
||||
goto cleanup;
|
||||
|
||||
if (VIR_ALLOC(vm->monitor_chr) < 0) {
|
||||
@@ -2183,7 +2218,7 @@ static void qemudShutdownVMDaemon(virConnectPtr conn,
|
||||
VIR_WARN("Failed to restore all device ownership for %s",
|
||||
vm->def->name);
|
||||
|
||||
- qemuDomainReAttachHostDevices(conn, vm->def);
|
||||
+ qemuDomainReAttachHostDevices(conn, driver, vm->def);
|
||||
|
||||
retry:
|
||||
if ((ret = qemuRemoveCgroup(conn, driver, vm)) < 0) {
|
||||
@@ -6791,6 +6826,7 @@ out:
|
||||
static int
|
||||
qemudNodeDeviceReset (virNodeDevicePtr dev)
|
||||
{
|
||||
+ struct qemud_driver *driver = dev->conn->privateData;
|
||||
pciDevice *pci;
|
||||
unsigned domain, bus, slot, function;
|
||||
int ret = -1;
|
||||
@@ -6802,11 +6838,14 @@ qemudNodeDeviceReset (virNodeDevicePtr dev)
|
||||
if (!pci)
|
||||
return -1;
|
||||
|
||||
- if (pciResetDevice(dev->conn, pci) < 0)
|
||||
+ qemuDriverLock(driver);
|
||||
+
|
||||
+ if (pciResetDevice(dev->conn, pci, driver->activePciHostdevs) < 0)
|
||||
goto out;
|
||||
|
||||
ret = 0;
|
||||
out:
|
||||
+ qemuDriverUnlock(driver);
|
||||
pciFreeDevice(dev->conn, pci);
|
||||
return ret;
|
||||
}
|
||||
diff --git a/src/xen_unified.c b/src/xen_unified.c
|
||||
index f2ffc25..dfa9ca5 100644
|
||||
--- a/src/xen_unified.c
|
||||
+++ b/src/xen_unified.c
|
||||
@@ -1641,7 +1641,7 @@ xenUnifiedNodeDeviceReset (virNodeDevicePtr dev)
|
||||
if (!pci)
|
||||
return -1;
|
||||
|
||||
- if (pciResetDevice(dev->conn, pci) < 0)
|
||||
+ if (pciResetDevice(dev->conn, pci, NULL) < 0)
|
||||
goto out;
|
||||
|
||||
ret = 0;
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,121 +0,0 @@
|
||||
From 5aad00b08cadc4d9da8bffd3d255ffaac98d36dd Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Fri, 14 Aug 2009 08:31:11 +0100
|
||||
Subject: [PATCH] Allow PM reset on multi-function PCI devices
|
||||
|
||||
https://bugzilla.redhat.com/515689
|
||||
|
||||
It turns out that a PCI Power Management reset only affects individual
|
||||
functions, and not the whole device.
|
||||
|
||||
The PCI Power Management spec talks about resetting the 'device' rather
|
||||
than the 'function', but Intel's Dexuan Cui informs me that it is
|
||||
actually a per-function reset.
|
||||
|
||||
Also, Yu Zhao has added pci_pm_reset() to the kernel, and it doesn't
|
||||
reject multi-function devices, so it must be true! :-)
|
||||
|
||||
(A side issue is that we could defer the PM reset to the kernel if we
|
||||
could detect that the kernel has PM reset support, but barring version
|
||||
number checks we don't have a way to detect that support)
|
||||
|
||||
* src/pci.c: remove the pciDeviceContainsOtherFunctions() check from
|
||||
pciTryPowerManagementReset() and prefer PM reset over bus reset
|
||||
where both are available
|
||||
|
||||
Cc: Cui, Dexuan <dexuan.cui@intel.com>
|
||||
Cc: Yu Zhao <yu.zhao@intel.com>
|
||||
|
||||
(cherry picked from commit 64a6682b93a2a8aa38067a43979c9eaf993d2b41)
|
||||
|
||||
Fedora-patch: libvirt-allow-pm-reset-on-multi-function-pci-devices.patch
|
||||
---
|
||||
src/pci.c | 48 +++++++++---------------------------------------
|
||||
1 files changed, 9 insertions(+), 39 deletions(-)
|
||||
|
||||
diff --git a/src/pci.c b/src/pci.c
|
||||
index 2dc2e1c..11b3e8b 100644
|
||||
--- a/src/pci.c
|
||||
+++ b/src/pci.c
|
||||
@@ -402,29 +402,6 @@ pciBusContainsOtherDevices(virConnectPtr conn, pciDevice *dev)
|
||||
return 1;
|
||||
}
|
||||
|
||||
-/* Any other functions on this device ? */
|
||||
-static int
|
||||
-pciSharesDevice(pciDevice *a, pciDevice *b)
|
||||
-{
|
||||
- return
|
||||
- a->domain == b->domain &&
|
||||
- a->bus == b->bus &&
|
||||
- a->slot == b->slot &&
|
||||
- a->function != b->function;
|
||||
-}
|
||||
-
|
||||
-static int
|
||||
-pciDeviceContainsOtherFunctions(virConnectPtr conn, pciDevice *dev)
|
||||
-{
|
||||
- pciDevice *matched = NULL;
|
||||
- if (pciIterDevices(conn, pciSharesDevice, dev, &matched) < 0)
|
||||
- return 1;
|
||||
- if (!matched)
|
||||
- return 0;
|
||||
- pciFreeDevice(conn, matched);
|
||||
- return 1;
|
||||
-}
|
||||
-
|
||||
/* Is @a the parent of @b ? */
|
||||
static int
|
||||
pciIsParent(pciDevice *a, pciDevice *b)
|
||||
@@ -529,7 +506,7 @@ out:
|
||||
* above we require the device supports a full internal reset.
|
||||
*/
|
||||
static int
|
||||
-pciTryPowerManagementReset(virConnectPtr conn, pciDevice *dev)
|
||||
+pciTryPowerManagementReset(virConnectPtr conn ATTRIBUTE_UNUSED, pciDevice *dev)
|
||||
{
|
||||
uint8_t config_space[PCI_CONF_LEN];
|
||||
uint32_t ctl;
|
||||
@@ -537,16 +514,6 @@ pciTryPowerManagementReset(virConnectPtr conn, pciDevice *dev)
|
||||
if (!dev->pci_pm_cap_pos)
|
||||
return -1;
|
||||
|
||||
- /* For now, we just refuse to do a power management reset
|
||||
- * if there are other functions on this device.
|
||||
- * In future, we could allow it so long as those functions
|
||||
- * are not in use by the host or other guests.
|
||||
- */
|
||||
- if (pciDeviceContainsOtherFunctions(conn, dev)) {
|
||||
- VIR_WARN("%s contains other functions, not resetting", dev->name);
|
||||
- return -1;
|
||||
- }
|
||||
-
|
||||
/* Save and restore the device's config space. */
|
||||
if (pciRead(dev, 0, &config_space[0], PCI_CONF_LEN) < 0) {
|
||||
VIR_WARN("Failed to save PCI config space for %s", dev->name);
|
||||
@@ -604,14 +571,17 @@ pciResetDevice(virConnectPtr conn, pciDevice *dev)
|
||||
if (dev->has_flr)
|
||||
return 0;
|
||||
|
||||
+ /* If the device supports PCI power management reset,
|
||||
+ * that's the next best thing because it only resets
|
||||
+ * the function, not the whole device.
|
||||
+ */
|
||||
+ if (dev->has_pm_reset)
|
||||
+ ret = pciTryPowerManagementReset(conn, dev);
|
||||
+
|
||||
/* Bus reset is not an option with the root bus */
|
||||
- if (dev->bus != 0)
|
||||
+ if (ret < 0 && dev->bus != 0)
|
||||
ret = pciTrySecondaryBusReset(conn, dev);
|
||||
|
||||
- /* Next best option is a PCI power management reset */
|
||||
- if (ret < 0 && dev->has_pm_reset)
|
||||
- ret = pciTryPowerManagementReset(conn, dev);
|
||||
-
|
||||
if (ret < 0)
|
||||
pciReportError(conn, VIR_ERR_NO_SUPPORT,
|
||||
_("No PCI reset capability available for %s"),
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,34 @@
|
||||
From bcd4180124afa20580d720912e2179b3a2f9295a Mon Sep 17 00:00:00 2001
|
||||
From: Daniel Veillard <veillard@redhat.com>
|
||||
Date: Mon, 5 Oct 2009 17:03:14 +0200
|
||||
Subject: [PATCH] 526769 change logrotate config default to weekly
|
||||
|
||||
* daemon/libvirtd.logrotate.in: change to weekly rotation of logs,
|
||||
keep a month worth of data and also extend to cover LXC and UML
|
||||
domain logs
|
||||
|
||||
(cherry picked from commit 529325bbdd050af89bda5a5c1a01b5553c49a57e)
|
||||
|
||||
Fedora-patch: libvirt-change-logrotate-config-to-weekly.patch
|
||||
---
|
||||
qemud/libvirtd.logrotate.in | 6 +++---
|
||||
1 files changed, 3 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/qemud/libvirtd.logrotate.in b/qemud/libvirtd.logrotate.in
|
||||
index 9b42630..093651c 100644
|
||||
--- a/qemud/libvirtd.logrotate.in
|
||||
+++ b/qemud/libvirtd.logrotate.in
|
||||
@@ -1,7 +1,7 @@
|
||||
-@localstatedir@/log/libvirt/qemu/*.log {
|
||||
- daily
|
||||
+@localstatedir@/log/libvirt/qemu/*.log @localstatedir@/log/libvirt/uml/*.log @localstatedir@/log/libvirt/lxc/*.log {
|
||||
+ weekly
|
||||
missingok
|
||||
- rotate 7
|
||||
+ rotate 4
|
||||
compress
|
||||
delaycompress
|
||||
copytruncate
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,77 @@
|
||||
From 4721ceb9b85daabe53804627473b06ced821c695 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Mon, 14 Sep 2009 11:23:20 +0100
|
||||
Subject: [PATCH] Allow control over QEMU audio backend
|
||||
|
||||
When using VNC for graphics + keyboard + mouse, we shouldn't
|
||||
then use the host OS for audio. Audio should go back over
|
||||
VNC.
|
||||
|
||||
When using SDL for graphics, we should use the host OS for
|
||||
audio since that's where the display is. We need to allow
|
||||
certain QEMU env variables to be passed through to guest
|
||||
too to allow choice of QEMU audio backend.
|
||||
|
||||
* qemud/libvirtd.sysconf: Mention QEMU/SDL audio env vars
|
||||
* src/qemu_conf.c: Passthrough QEMU/SDL audio env for SDL display,
|
||||
disable host audio for VNC display
|
||||
|
||||
(cherry picked from commit b08e6d38ae7a0ed70300d7d82107f83fddb60f44)
|
||||
|
||||
Fedora-patch: libvirt-disable-audio-backend.patch
|
||||
---
|
||||
qemud/libvirtd.sysconf | 8 ++++++++
|
||||
src/qemu_conf.c | 14 ++++++++++++++
|
||||
2 files changed, 22 insertions(+), 0 deletions(-)
|
||||
|
||||
diff --git a/qemud/libvirtd.sysconf b/qemud/libvirtd.sysconf
|
||||
index fe4596a..28080a0 100644
|
||||
--- a/qemud/libvirtd.sysconf
|
||||
+++ b/qemud/libvirtd.sysconf
|
||||
@@ -7,3 +7,11 @@
|
||||
|
||||
# Override Kerberos service keytab for SASL/GSSAPI
|
||||
#KRB5_KTNAME=/etc/libvirt/krb5.tab
|
||||
+
|
||||
+# Override the QEMU/SDL default audio driver probing when
|
||||
+# starting virtual machines using SDL graphics
|
||||
+#
|
||||
+# NB these have no effect for VMs using VNC
|
||||
+#QEMU_AUDIO_DRV=sdl
|
||||
+#
|
||||
+#SDL_AUDIODRIVER=pulse
|
||||
diff --git a/src/qemu_conf.c b/src/qemu_conf.c
|
||||
index f92bcef..0dd0624 100644
|
||||
--- a/src/qemu_conf.c
|
||||
+++ b/src/qemu_conf.c
|
||||
@@ -2109,6 +2109,13 @@ int qemudBuildCommandLine(virConnectPtr conn,
|
||||
ADD_ARG_LIT("-k");
|
||||
ADD_ARG_LIT(def->graphics[0]->data.vnc.keymap);
|
||||
}
|
||||
+
|
||||
+ /* QEMU implements a VNC extension for providing audio, so we
|
||||
+ * set the audio backend to none, to prevent it opening the
|
||||
+ * host OS audio devices since that causes security issues
|
||||
+ * and is non-sensical when using VNC.
|
||||
+ */
|
||||
+ ADD_ENV_LIT("QEMU_AUDIO_DRV=none");
|
||||
} else if ((def->ngraphics == 1) &&
|
||||
def->graphics[0]->type == VIR_DOMAIN_GRAPHICS_TYPE_SDL) {
|
||||
char *xauth = NULL;
|
||||
@@ -2131,6 +2138,13 @@ int qemudBuildCommandLine(virConnectPtr conn,
|
||||
ADD_ENV(display);
|
||||
if (def->graphics[0]->data.sdl.fullscreen)
|
||||
ADD_ARG_LIT("-full-screen");
|
||||
+
|
||||
+ /* If using SDL for video, then we should just let it
|
||||
+ * use QEMU's host audio drivers, possibly SDL too
|
||||
+ * User can set these two before starting libvirtd
|
||||
+ */
|
||||
+ ADD_ENV_COPY("QEMU_AUDIO_DRV");
|
||||
+ ADD_ENV_COPY("SDL_AUDIODRIVER");
|
||||
}
|
||||
|
||||
if (def->nvideos) {
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,31 @@
|
||||
From a5fa9f63fcffbf70465386672f24edac439866b9 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Thu, 24 Sep 2009 15:42:25 +0100
|
||||
Subject: [PATCH] Fix crash in device hotplug cleanup code
|
||||
|
||||
* src/qemu/qemu_driver.c: Fix crash in scenario where XML
|
||||
parsing of hotplugged device failed & thus 'dev' is NULL
|
||||
|
||||
(cherry picked from commit 879cd8cc2ba00f795913f296556e05f25afa7877)
|
||||
|
||||
Fedora-patch: libvirt-fix-crash-on-device-hotplug-parse-error.patch
|
||||
---
|
||||
src/qemu_driver.c | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 0ce403c..c956258 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -5912,7 +5912,7 @@ cleanup:
|
||||
if (cgroup)
|
||||
virCgroupFree(&cgroup);
|
||||
|
||||
- if (ret < 0) {
|
||||
+ if (ret < 0 && dev != NULL) {
|
||||
if (qemuDomainSetDeviceOwnership(dom->conn, driver, dev, 1) < 0)
|
||||
VIR_WARN0("Fail to restore disk device ownership");
|
||||
virDomainDeviceDefFree(dev);
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
From 7bc1491deba6338e514504d1b68fe097e7f2bf19 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel Veillard <veillard@redhat.com>
|
||||
Date: Thu, 1 Oct 2009 11:54:38 +0200
|
||||
Subject: [PATCH] Avoid a libvirtd crash on broken input 523418
|
||||
|
||||
* src/conf/domain_conf.c: a simple typo in an XML domain file could lead
|
||||
to a crash, because we called STRPREFIX() on the looked up value without
|
||||
checking it was non-null.
|
||||
|
||||
(cherry picked from commit 79d233b5ca62f86ab22d271d1f08ec20060eee88)
|
||||
|
||||
Fedora-patch: libvirt-fix-crash-on-missing-iface-target-dev.patch
|
||||
---
|
||||
src/domain_conf.c | 3 ++-
|
||||
1 files changed, 2 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/domain_conf.c b/src/domain_conf.c
|
||||
index c424c67..476cdd7 100644
|
||||
--- a/src/domain_conf.c
|
||||
+++ b/src/domain_conf.c
|
||||
@@ -1031,7 +1031,8 @@ virDomainNetDefParseXML(virConnectPtr conn,
|
||||
} else if ((ifname == NULL) &&
|
||||
xmlStrEqual(cur->name, BAD_CAST "target")) {
|
||||
ifname = virXMLPropString(cur, "dev");
|
||||
- if (STRPREFIX((const char*)ifname, "vnet")) {
|
||||
+ if ((ifname != NULL) &&
|
||||
+ (STRPREFIX((const char*)ifname, "vnet"))) {
|
||||
/* An auto-generated target name, blank it out */
|
||||
VIR_FREE(ifname);
|
||||
}
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,29 @@
|
||||
From 58c38896a67c170063401d8091bae7dca8842923 Mon Sep 17 00:00:00 2001
|
||||
From: Jiri Denemark <jdenemar@redhat.com>
|
||||
Date: Wed, 23 Sep 2009 18:46:23 +0200
|
||||
Subject: [PATCH] Fix a typo in virDiskHasValidPciAddr()
|
||||
|
||||
(cherry-picked from commit 3620e3cdcfe56cc4475b5ef1a0a893757240b795)
|
||||
|
||||
Signed-off-by: Jiri Denemark <jdenemar@redhat.com>
|
||||
Fedora-patch: libvirt-fix-device-detach-typo1.patch
|
||||
---
|
||||
src/domain_conf.h | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/domain_conf.h b/src/domain_conf.h
|
||||
index 09368d9..d494e54 100644
|
||||
--- a/src/domain_conf.h
|
||||
+++ b/src/domain_conf.h
|
||||
@@ -125,7 +125,7 @@ struct _virDomainDiskDef {
|
||||
static inline int
|
||||
virDiskHasValidPciAddr(virDomainDiskDefPtr def)
|
||||
{
|
||||
- return def->pci_addr.domain || def->pci_addr.domain || def->pci_addr.slot;
|
||||
+ return def->pci_addr.domain || def->pci_addr.bus || def->pci_addr.slot;
|
||||
}
|
||||
|
||||
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
From 81e967c716ce8c085be8baad9169f7772452d187 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Thu, 24 Sep 2009 08:55:55 +0100
|
||||
Subject: [PATCH] Fix a typo in virNetHasValidPciAddr() too
|
||||
|
||||
* src/domain_conf.h: check domain/bus/slot, not domain/domain/slot
|
||||
|
||||
(cherry-picked from commit 6bfffce91635bb08de601747e94ed1182c0f47eb)
|
||||
|
||||
Fedora-patch: libvirt-fix-device-detach-typo2.patch
|
||||
---
|
||||
src/domain_conf.h | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/domain_conf.h b/src/domain_conf.h
|
||||
index d494e54..7c918a7 100644
|
||||
--- a/src/domain_conf.h
|
||||
+++ b/src/domain_conf.h
|
||||
@@ -207,7 +207,7 @@ struct _virDomainNetDef {
|
||||
static inline int
|
||||
virNetHasValidPciAddr(virDomainNetDefPtr def)
|
||||
{
|
||||
- return def->pci_addr.domain || def->pci_addr.domain || def->pci_addr.slot;
|
||||
+ return def->pci_addr.domain || def->pci_addr.bus || def->pci_addr.slot;
|
||||
}
|
||||
|
||||
enum virDomainChrSrcType {
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
From 3a64779ec5a89d38d64e07bca2b11b19e1882d7a Mon Sep 17 00:00:00 2001
|
||||
From: Charles Duffy <charles@dyfis.net>
|
||||
Date: Thu, 24 Sep 2009 09:00:24 +0100
|
||||
Subject: [PATCH] Fix unitialized variable in qemudDomainDetachHostPciDevice()
|
||||
|
||||
* src/qemu_driver.c: initialize detach var
|
||||
|
||||
(cherry-picked from commit 580ad29288751234bee47ac9f6c04dac1dc529ea)
|
||||
|
||||
Fedora-patch: libvirt-fix-device-detach-typo3.patch
|
||||
---
|
||||
src/qemu_driver.c | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 7c7b985..550a59c 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -6126,7 +6126,7 @@ static int qemudDomainDetachHostPciDevice(virConnectPtr conn,
|
||||
virDomainObjPtr vm,
|
||||
virDomainDeviceDefPtr dev)
|
||||
{
|
||||
- virDomainHostdevDefPtr detach;
|
||||
+ virDomainHostdevDefPtr detach = NULL;
|
||||
char *cmd, *reply;
|
||||
int i, ret;
|
||||
pciDevice *pci;
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,79 +0,0 @@
|
||||
From 165fb333c9d954fec636dc0f1917ba50417478c0 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Sat, 15 Aug 2009 19:38:15 +0100
|
||||
Subject: [PATCH] Fix list updating after disk/network hot-unplug
|
||||
|
||||
The current code makes a poor effort at updating the device arrays after
|
||||
hot-unplug. Fix that and combine the two code paths into one.
|
||||
|
||||
* src/qemu_driver.c: fix list updating in qemudDomainDetachNetDevice() and
|
||||
qemudDomainDetachPciDiskDevice()
|
||||
|
||||
(cherry picked from commit 4e12af5623e4a962a6bb911af06fa29aa85befba)
|
||||
|
||||
Fedora-patch: libvirt-fix-device-list-update-after-detach.patch
|
||||
---
|
||||
src/qemu_driver.c | 38 ++++++++++++++++++--------------------
|
||||
1 files changed, 18 insertions(+), 20 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index bd58435..2c4fd6f 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -5404,18 +5404,17 @@ try_command:
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
- if (vm->def->ndisks > 1) {
|
||||
- vm->def->disks[i] = vm->def->disks[--vm->def->ndisks];
|
||||
- if (VIR_REALLOC_N(vm->def->disks, vm->def->ndisks) < 0) {
|
||||
- virReportOOMError(conn);
|
||||
- goto cleanup;
|
||||
- }
|
||||
- qsort(vm->def->disks, vm->def->ndisks, sizeof(*vm->def->disks),
|
||||
- virDomainDiskQSort);
|
||||
- } else {
|
||||
- VIR_FREE(vm->def->disks[0]);
|
||||
- vm->def->ndisks = 0;
|
||||
+ if (i != --vm->def->ndisks)
|
||||
+ memmove(&vm->def->disks[i],
|
||||
+ &vm->def->disks[i+1],
|
||||
+ sizeof(*vm->def->disks) * (vm->def->ndisks-i));
|
||||
+ if (VIR_REALLOC_N(vm->def->disks, vm->def->ndisks) < 0) {
|
||||
+ virReportOOMError(conn);
|
||||
+ goto cleanup;
|
||||
}
|
||||
+ qsort(vm->def->disks, vm->def->ndisks, sizeof(*vm->def->disks),
|
||||
+ virDomainDiskQSort);
|
||||
+
|
||||
ret = 0;
|
||||
|
||||
cleanup:
|
||||
@@ -5503,16 +5502,15 @@ qemudDomainDetachNetDevice(virConnectPtr conn,
|
||||
|
||||
DEBUG("%s: host_net_remove reply: %s", vm->def->name, reply);
|
||||
|
||||
- if (vm->def->nnets > 1) {
|
||||
- vm->def->nets[i] = vm->def->nets[--vm->def->nnets];
|
||||
- if (VIR_REALLOC_N(vm->def->nets, vm->def->nnets) < 0) {
|
||||
- virReportOOMError(conn);
|
||||
- goto cleanup;
|
||||
- }
|
||||
- } else {
|
||||
- VIR_FREE(vm->def->nets[0]);
|
||||
- vm->def->nnets = 0;
|
||||
+ if (i != --vm->def->nnets)
|
||||
+ memmove(&vm->def->nets[i],
|
||||
+ &vm->def->nets[i+1],
|
||||
+ sizeof(*vm->def->nets) * (vm->def->nnets-i));
|
||||
+ if (VIR_REALLOC_N(vm->def->nets, vm->def->nnets) < 0) {
|
||||
+ virReportOOMError(conn);
|
||||
+ goto cleanup;
|
||||
}
|
||||
+
|
||||
ret = 0;
|
||||
|
||||
cleanup:
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,32 @@
|
||||
From 7692e1e19487c28454b1e5f6488d5574c70883f2 Mon Sep 17 00:00:00 2001
|
||||
From: Chris Lalancette <clalance@redhat.com>
|
||||
Date: Mon, 21 Sep 2009 14:53:31 +0200
|
||||
Subject: [PATCH] Don't do virSetConnError when virDrvSupportsFeature is successful.
|
||||
|
||||
Signed-off-by: Chris Lalancette <clalance@redhat.com>
|
||||
Fedora-patch: libvirt-fix-drv-supports-feature-bogus-error.patch
|
||||
---
|
||||
src/libvirt.c | 7 +++++--
|
||||
1 files changed, 5 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/libvirt.c b/src/libvirt.c
|
||||
index 4a11688..fa59dc7 100644
|
||||
--- a/src/libvirt.c
|
||||
+++ b/src/libvirt.c
|
||||
@@ -1349,8 +1349,11 @@ virDrvSupportsFeature (virConnectPtr conn, int feature)
|
||||
}
|
||||
|
||||
ret = VIR_DRV_SUPPORTS_FEATURE (conn->driver, conn, feature);
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(conn);
|
||||
+
|
||||
+ if (ret < 0)
|
||||
+ /* Copy to connection error object for back compatability */
|
||||
+ virSetConnError(conn);
|
||||
+
|
||||
return ret;
|
||||
}
|
||||
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,79 @@
|
||||
From 71de8d92f20a9a9ee76d4d5df77ff477f1b7d441 Mon Sep 17 00:00:00 2001
|
||||
From: Matthias Bolte <matthias.bolte@googlemail.com>
|
||||
Date: Wed, 30 Sep 2009 02:17:27 +0200
|
||||
Subject: [PATCH] Fix memory leaks in libvirtd's message processing
|
||||
|
||||
Commit 47cab734995fa9521b1df05d37e9978eedd8d3a2 changed the way how
|
||||
qemud_client_message objects were reused. Before this commit
|
||||
remoteDispatchClientRequest() reused the received message for normal responses
|
||||
and to report non-fatal errors. If a fatal error occurred qemudWorker() frees
|
||||
the message. After this commit non-fatal errors are reported by
|
||||
remoteSerializeReplyError() using a new qemud_client_message object and the
|
||||
original message leaks.
|
||||
|
||||
To fix this leak the original message has to be freed if
|
||||
remoteSerializeReplyError() succeeds. If remoteSerializeReplyError()
|
||||
fails the original message is freed in qemudWorker().
|
||||
|
||||
* daemon/dispatch.c: free qemud_client_message objects that will not be reused
|
||||
and would leak otherwise, also free the allocated qemud_client_message object
|
||||
in remoteSerializeError() if an error occurs
|
||||
|
||||
(cherry-picked from commit c6f1459eb998619ab21a92d9bb87341f26978181)
|
||||
|
||||
Fedora-patch: libvirt-fix-libvirtd-leak-in-error-reply.patch
|
||||
---
|
||||
qemud/dispatch.c | 15 +++++++++++++--
|
||||
1 files changed, 13 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/qemud/dispatch.c b/qemud/dispatch.c
|
||||
index a60f2f4..ddb3215 100644
|
||||
--- a/qemud/dispatch.c
|
||||
+++ b/qemud/dispatch.c
|
||||
@@ -191,6 +191,7 @@ remoteSerializeError(struct qemud_client *client,
|
||||
|
||||
xdr_error:
|
||||
xdr_destroy(&xdr);
|
||||
+ VIR_FREE(msg);
|
||||
fatal_error:
|
||||
xdr_free((xdrproc_t)xdr_remote_error, (char *)rerr);
|
||||
return -1;
|
||||
@@ -336,6 +337,7 @@ remoteDispatchClientRequest (struct qemud_server *server,
|
||||
struct qemud_client *client,
|
||||
struct qemud_client_message *msg)
|
||||
{
|
||||
+ int ret;
|
||||
remote_error rerr;
|
||||
|
||||
memset(&rerr, 0, sizeof rerr);
|
||||
@@ -364,7 +366,12 @@ remoteDispatchClientRequest (struct qemud_server *server,
|
||||
}
|
||||
|
||||
error:
|
||||
- return remoteSerializeReplyError(client, &rerr, &msg->hdr);
|
||||
+ ret = remoteSerializeReplyError(client, &rerr, &msg->hdr);
|
||||
+
|
||||
+ if (ret >= 0)
|
||||
+ VIR_FREE(msg);
|
||||
+
|
||||
+ return ret;
|
||||
}
|
||||
|
||||
|
||||
@@ -521,8 +528,12 @@ remoteDispatchClientCall (struct qemud_server *server,
|
||||
rpc_error:
|
||||
/* Semi-bad stuff happened, we can still try to send back
|
||||
* an RPC error message to client */
|
||||
- return remoteSerializeReplyError(client, &rerr, &msg->hdr);
|
||||
+ rv = remoteSerializeReplyError(client, &rerr, &msg->hdr);
|
||||
+
|
||||
+ if (rv >= 0)
|
||||
+ VIR_FREE(msg);
|
||||
|
||||
+ return rv;
|
||||
|
||||
xdr_error:
|
||||
/* Seriously bad stuff happened, so we'll kill off this client
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,45 +0,0 @@
|
||||
From f2eb2ad5163d5bae2392a8bfc6040c45426c9f5f Mon Sep 17 00:00:00 2001
|
||||
From: Chris Lalancette <clalance@redhat.com>
|
||||
Date: Wed, 5 Aug 2009 13:42:07 +0200
|
||||
Subject: [PATCH] Run 'cont' on successful migration finish.
|
||||
|
||||
https://bugzilla.redhat.com/516187
|
||||
|
||||
As of qemu 0.10.6, qemu now honors the -S flag on incoming migration.
|
||||
That means that when the migration completes, we have to issue a
|
||||
'cont' command to get the VM running again. We do it unconditionally
|
||||
since it won't hurt on older qemu.
|
||||
|
||||
(cherry picked from commit d1ec4d7a5a4f50c9492137eaab4f021caa075f95)
|
||||
|
||||
Fedora-patch: libvirt-fix-migration-completion-with-newer-qemu.patch
|
||||
---
|
||||
src/qemu_driver.c | 11 +++++++++++
|
||||
1 files changed, 11 insertions(+), 0 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 99dac52..bf9a0b2 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -6951,7 +6951,18 @@ qemudDomainMigrateFinish2 (virConnectPtr dconn,
|
||||
*/
|
||||
if (retcode == 0) {
|
||||
dom = virGetDomain (dconn, vm->def->name, vm->def->uuid);
|
||||
+
|
||||
+ /* run 'cont' on the destination, which allows migration on qemu
|
||||
+ * >= 0.10.6 to work properly. This isn't strictly necessary on
|
||||
+ * older qemu's, but it also doesn't hurt anything there
|
||||
+ */
|
||||
+ if (qemudMonitorCommand(vm, "cont", &info) < 0) {
|
||||
+ qemudReportError(dconn, NULL, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ "%s", _("resume operation failed"));
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
VIR_FREE(info);
|
||||
+
|
||||
vm->state = VIR_DOMAIN_RUNNING;
|
||||
event = virDomainEventNewFromObj(vm,
|
||||
VIR_DOMAIN_EVENT_RESUMED,
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,46 @@
|
||||
From ba585ed6cff624c6c0f1f9801382fd6846466ee0 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Thu, 17 Sep 2009 15:31:08 +0100
|
||||
Subject: [PATCH] Fix net/disk hot-unplug segfault
|
||||
|
||||
When we hot-unplug the last device, we're currently double-freeing
|
||||
the device definition.
|
||||
|
||||
Reported by Michal Nowak here:
|
||||
|
||||
https://bugzilla.redhat.com/523953
|
||||
|
||||
* src/qemu_driver.c: fix double free
|
||||
|
||||
(cherry-picked from commit 8881ae1bf8783006777429403cc543c33187175d)
|
||||
|
||||
Fedora-patch: libvirt-fix-net-hotunplug-double-free.patch
|
||||
---
|
||||
src/qemu_driver.c | 4 ++--
|
||||
1 files changed, 2 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index a65334f..de31581 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -5998,7 +5998,7 @@ try_command:
|
||||
/* ignore, harmless */
|
||||
}
|
||||
} else {
|
||||
- VIR_FREE(vm->def->disks[0]);
|
||||
+ VIR_FREE(vm->def->disks);
|
||||
vm->def->ndisks = 0;
|
||||
}
|
||||
virDomainDiskDefFree(detach);
|
||||
@@ -6100,7 +6100,7 @@ qemudDomainDetachNetDevice(virConnectPtr conn,
|
||||
/* ignore, harmless */
|
||||
}
|
||||
} else {
|
||||
- VIR_FREE(vm->def->nets[0]);
|
||||
+ VIR_FREE(vm->def->nets);
|
||||
vm->def->nnets = 0;
|
||||
}
|
||||
virDomainNetDefFree(detach);
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,50 @@
|
||||
From 17831d20051f8de8f1f7d661e8a23f4fe67c2153 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Thu, 17 Sep 2009 15:32:45 +0100
|
||||
Subject: [PATCH] Fix leak in PCI hostdev hot-unplug
|
||||
|
||||
* src/qemu_driver.c: sync the hostdev hot-unplug code with the disk/net
|
||||
code.
|
||||
|
||||
(cherry-picked from commit a70da51ff76ed860bfc0cdee2e1d556da997c557)
|
||||
|
||||
Fedora-patch: libvirt-fix-pci-hostdev-hotunplug-leak.patch
|
||||
---
|
||||
src/qemu_driver.c | 20 +++++++++++++-------
|
||||
1 files changed, 13 insertions(+), 7 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index de31581..2ddcdc0 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -6206,14 +6206,20 @@ static int qemudDomainDetachHostPciDevice(virConnectPtr conn,
|
||||
pciFreeDevice(conn, pci);
|
||||
}
|
||||
|
||||
- if (i != --vm->def->nhostdevs)
|
||||
- memmove(&vm->def->hostdevs[i],
|
||||
- &vm->def->hostdevs[i+1],
|
||||
- sizeof(*vm->def->hostdevs) * (vm->def->nhostdevs-i));
|
||||
- if (VIR_REALLOC_N(vm->def->hostdevs, vm->def->nhostdevs) < 0) {
|
||||
- virReportOOMError(conn);
|
||||
- ret = -1;
|
||||
+ if (vm->def->nhostdevs > 1) {
|
||||
+ memmove(vm->def->hostdevs + i,
|
||||
+ vm->def->hostdevs + i + 1,
|
||||
+ sizeof(*vm->def->hostdevs) *
|
||||
+ (vm->def->nhostdevs - (i + 1)));
|
||||
+ vm->def->nhostdevs--;
|
||||
+ if (VIR_REALLOC_N(vm->def->hostdevs, vm->def->nhostdevs) < 0) {
|
||||
+ /* ignore, harmless */
|
||||
+ }
|
||||
+ } else {
|
||||
+ VIR_FREE(vm->def->hostdevs);
|
||||
+ vm->def->nhostdevs = 0;
|
||||
}
|
||||
+ virDomainHostdevDefFree(detach);
|
||||
|
||||
return ret;
|
||||
}
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,53 @@
|
||||
From f1be5a4714e194a84840343e0937fe62463a18dc Mon Sep 17 00:00:00 2001
|
||||
From: Charles Duffy <Charles_Duffy@dell.com>
|
||||
Date: Fri, 18 Sep 2009 11:32:35 -0500
|
||||
Subject: [PATCH] Prevent attempt to call cat -c during virDomainSave to raw
|
||||
|
||||
Fedora-patch: libvirt-fix-qemu-raw-format-save.patch
|
||||
---
|
||||
src/qemu_driver.c | 28 ++++++++++++++++++----------
|
||||
1 files changed, 18 insertions(+), 10 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 2ddcdc0..7c7b985 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -3905,17 +3905,25 @@ static int qemudDomainSave(virDomainPtr dom,
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
- const char *prog = qemudSaveCompressionTypeToString(header.compressed);
|
||||
- if (prog == NULL) {
|
||||
- qemudReportError(dom->conn, dom, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
- _("Invalid compress format %d"), header.compressed);
|
||||
- goto cleanup;
|
||||
- }
|
||||
+ {
|
||||
+ const char *prog = qemudSaveCompressionTypeToString(header.compressed);
|
||||
+ const char *args;
|
||||
|
||||
- if (STREQ (prog, "raw"))
|
||||
- prog = "cat";
|
||||
- internalret = virAsprintf(&command, "migrate \"exec:"
|
||||
- "%s -c >> '%s' 2>/dev/null\"", prog, safe_path);
|
||||
+ if (prog == NULL) {
|
||||
+ qemudReportError(dom->conn, dom, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Invalid compress format %d"), header.compressed);
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
+ if (STREQ (prog, "raw")) {
|
||||
+ prog = "cat";
|
||||
+ args = "";
|
||||
+ } else {
|
||||
+ args = "-c";
|
||||
+ }
|
||||
+ internalret = virAsprintf(&command, "migrate \"exec:"
|
||||
+ "%s %s >> '%s' 2>/dev/null\"", prog, args, safe_path);
|
||||
+ }
|
||||
|
||||
if (internalret < 0) {
|
||||
virReportOOMError(dom->conn);
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,38 @@
|
||||
From 0b846a30468a6b4586407f020ccde7bb51afaf98 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Mon, 12 Oct 2009 20:03:50 +0100
|
||||
Subject: [PATCH] Fix QEMU restore from file in raw format
|
||||
|
||||
The logic for running the decompression programs was broken in
|
||||
commit f238709304f9f6c57204cdd943e542cbae38fa5f, so that for
|
||||
non-raw formats the decompression program was never run, and
|
||||
for raw formats, it tried to exec an argv[] with initial NULL
|
||||
in the program name.
|
||||
|
||||
* src/qemu/qemu_driver.c: Fix logic in runing decompression program
|
||||
|
||||
(cherry picked from commit 74b379cbd5ba9f472a3a2d5710e497966b1a3a37)
|
||||
|
||||
Fedora-patch: libvirt-fix-qemu-restore-from-raw1.patch
|
||||
---
|
||||
src/qemu_driver.c | 3 +--
|
||||
1 files changed, 1 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 550a59c..0ce403c 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -4541,9 +4541,8 @@ static int qemudDomainRestore(virConnectPtr conn,
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
- if (header.compressed != QEMUD_SAVE_FORMAT_RAW)
|
||||
+ if (header.compressed != QEMUD_SAVE_FORMAT_RAW) {
|
||||
intermediate_argv[0] = prog;
|
||||
- else {
|
||||
intermediatefd = fd;
|
||||
fd = -1;
|
||||
if (virExec(conn, intermediate_argv, NULL, NULL,
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,120 @@
|
||||
From 57d7cc602d14c6b50e2826e427a5de124e479f95 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Mon, 12 Oct 2009 20:32:33 +0100
|
||||
Subject: [PATCH] Fix virFileReadLimFD/virFileReadAll to handle EINTR
|
||||
|
||||
The fread_file_lim() function uses fread() but never handles
|
||||
EINTR results, causing unexpected failures when reading QEMU
|
||||
help arg info. It was unneccessarily using FILE * instead
|
||||
of plain UNIX file handles, which prevented use of saferead()
|
||||
|
||||
* src/util/util.c: Switch fread_file_lim over to use saferead
|
||||
instead of fread, remove FILE * use, and rename
|
||||
|
||||
(cherry picked from commit 11a36d956cb8a5e439e535bff3e0cfce50a64bca)
|
||||
|
||||
Fedora-patch: libvirt-fix-qemu-restore-from-raw2.patch
|
||||
---
|
||||
src/util.c | 45 ++++++++++++---------------------------------
|
||||
1 files changed, 12 insertions(+), 33 deletions(-)
|
||||
|
||||
diff --git a/src/util.c b/src/util.c
|
||||
index 1878e33..7bc3a66 100644
|
||||
--- a/src/util.c
|
||||
+++ b/src/util.c
|
||||
@@ -887,7 +887,7 @@ virExec(virConnectPtr conn,
|
||||
number of bytes. If the length of the input is <= max_len, and
|
||||
upon error while reading that data, it works just like fread_file. */
|
||||
static char *
|
||||
-fread_file_lim (FILE *stream, size_t max_len, size_t *length)
|
||||
+saferead_lim (int fd, size_t max_len, size_t *length)
|
||||
{
|
||||
char *buf = NULL;
|
||||
size_t alloc = 0;
|
||||
@@ -895,8 +895,8 @@ fread_file_lim (FILE *stream, size_t max_len, size_t *length)
|
||||
int save_errno;
|
||||
|
||||
for (;;) {
|
||||
- size_t count;
|
||||
- size_t requested;
|
||||
+ int count;
|
||||
+ int requested;
|
||||
|
||||
if (size + BUFSIZ + 1 > alloc) {
|
||||
alloc += alloc / 2;
|
||||
@@ -912,12 +912,12 @@ fread_file_lim (FILE *stream, size_t max_len, size_t *length)
|
||||
/* Ensure that (size + requested <= max_len); */
|
||||
requested = MIN (size < max_len ? max_len - size : 0,
|
||||
alloc - size - 1);
|
||||
- count = fread (buf + size, 1, requested, stream);
|
||||
+ count = saferead (fd, buf + size, requested);
|
||||
size += count;
|
||||
|
||||
if (count != requested || requested == 0) {
|
||||
save_errno = errno;
|
||||
- if (ferror (stream))
|
||||
+ if (count < 0)
|
||||
break;
|
||||
buf[size] = '\0';
|
||||
*length = size;
|
||||
@@ -930,12 +930,12 @@ fread_file_lim (FILE *stream, size_t max_len, size_t *length)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
-/* A wrapper around fread_file_lim that maps a failure due to
|
||||
+/* A wrapper around saferead_lim that maps a failure due to
|
||||
exceeding the maximum size limitation to EOVERFLOW. */
|
||||
-static int virFileReadLimFP(FILE *fp, int maxlen, char **buf)
|
||||
+int virFileReadLimFD(int fd, int maxlen, char **buf)
|
||||
{
|
||||
size_t len;
|
||||
- char *s = fread_file_lim (fp, maxlen+1, &len);
|
||||
+ char *s = saferead_lim (fd, maxlen+1, &len);
|
||||
if (s == NULL)
|
||||
return -1;
|
||||
if (len > maxlen || (int)len != len) {
|
||||
@@ -949,37 +949,16 @@ static int virFileReadLimFP(FILE *fp, int maxlen, char **buf)
|
||||
return len;
|
||||
}
|
||||
|
||||
-/* Like virFileReadLimFP, but use a file descriptor rather than a FILE*. */
|
||||
-int virFileReadLimFD(int fd_arg, int maxlen, char **buf)
|
||||
-{
|
||||
- int fd = dup (fd_arg);
|
||||
- if (fd >= 0) {
|
||||
- FILE *fp = fdopen (fd, "r");
|
||||
- if (fp) {
|
||||
- int len = virFileReadLimFP (fp, maxlen, buf);
|
||||
- int saved_errno = errno;
|
||||
- fclose (fp);
|
||||
- errno = saved_errno;
|
||||
- return len;
|
||||
- } else {
|
||||
- int saved_errno = errno;
|
||||
- close (fd);
|
||||
- errno = saved_errno;
|
||||
- }
|
||||
- }
|
||||
- return -1;
|
||||
-}
|
||||
-
|
||||
int virFileReadAll(const char *path, int maxlen, char **buf)
|
||||
{
|
||||
- FILE *fh = fopen(path, "r");
|
||||
- if (fh == NULL) {
|
||||
+ int fd = open(path, O_RDONLY);
|
||||
+ if (fd < 0) {
|
||||
virReportSystemError(NULL, errno, _("Failed to open file '%s'"), path);
|
||||
return -1;
|
||||
}
|
||||
|
||||
- int len = virFileReadLimFP (fh, maxlen, buf);
|
||||
- fclose(fh);
|
||||
+ int len = virFileReadLimFD(fd, maxlen, buf);
|
||||
+ close(fd);
|
||||
if (len < 0) {
|
||||
virReportSystemError(NULL, errno, _("Failed to read file '%s'"), path);
|
||||
return -1;
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,41 @@
|
||||
From 6b12148864cf6a1d22a2cf4e0e9c48e9946331cb Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Wed, 30 Sep 2009 18:37:03 +0100
|
||||
Subject: [PATCH] Fix USB device re-labelling
|
||||
|
||||
A simple misplaced break out of a switch results in:
|
||||
|
||||
libvir: error : Failed to open file '/sys/bus/pci/devices/0000:00:54c./vendor': No such file or directory
|
||||
libvir: error : Failed to open file '/sys/bus/pci/devices/0000:00:54c./device': No such file or directory
|
||||
libvir: error : this function is not supported by the hypervisor: Failed to read product/vendor ID for 0000:00:54c.
|
||||
|
||||
when trying to passthrough a USB host device to qemu.
|
||||
|
||||
* src/security_selinux.c: fix a switch/break thinko
|
||||
|
||||
Fedora-patch: libvirt-fix-usb-device-passthrough.patch
|
||||
---
|
||||
src/security_selinux.c | 3 +--
|
||||
1 files changed, 1 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/security_selinux.c b/src/security_selinux.c
|
||||
index bc295b1..b4dc153 100644
|
||||
--- a/src/security_selinux.c
|
||||
+++ b/src/security_selinux.c
|
||||
@@ -464,12 +464,11 @@ SELinuxSetSecurityHostdevLabel(virConnectPtr conn,
|
||||
|
||||
ret = usbDeviceFileIterate(conn, usb, SELinuxSetSecurityUSBLabel, vm);
|
||||
usbFreeDevice(conn, usb);
|
||||
-
|
||||
- break;
|
||||
} else {
|
||||
/* XXX deal with product/vendor better */
|
||||
ret = 0;
|
||||
}
|
||||
+ break;
|
||||
}
|
||||
|
||||
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI: {
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,103 @@
|
||||
From cab81502320d97dac4c5c12e7496f30896709c49 Mon Sep 17 00:00:00 2001
|
||||
From: Matthias Bolte <matthias.bolte@googlemail.com>
|
||||
Date: Tue, 22 Sep 2009 15:12:48 +0200
|
||||
Subject: [PATCH] Fix xen driver refcounting.
|
||||
|
||||
The commit cb51aa48a777ddae6997faa9f28350cb62655ffd "Fix up connection
|
||||
reference counting." changed the driver closing and virConnectPtr
|
||||
unref-logic in virConnectClose().
|
||||
|
||||
Before this commit virConnectClose() closed all drivers of the given
|
||||
virConnectPtr and virUnrefConnect()'ed it afterwards. After this
|
||||
commit the driver-closing is done in virUnrefConnect() if and only if
|
||||
the ref-count of the virConnectPtr dropped to zero.
|
||||
|
||||
This change in execution order leads to a virConnectPtr leak, at least
|
||||
for connections to Xen.
|
||||
|
||||
The relevant call sequences:
|
||||
|
||||
virConnectOpen() -> xenUnifiedOpen() ...
|
||||
|
||||
... xenInotifyOpen() -> virConnectRef(conn)
|
||||
|
||||
... xenStoreOpen() -> xenStoreAddWatch() -> conn->refs++
|
||||
|
||||
virConnectClose() -> xenUnifiedClose() ...
|
||||
|
||||
... xenInotifyClose() -> virUnrefConnect(conn)
|
||||
|
||||
... xenStoreClose() -> xenStoreRemoveWatch() -> virUnrefConnect(conn)
|
||||
|
||||
Before the commit this additional virConnectRef/virUnrefConnect calls
|
||||
where no problem, because virConnectClose() closed the drivers
|
||||
explicitly and the additional refs added by the Xen subdrivers were
|
||||
removed properly. After the commit this additional refs result in a
|
||||
virConnectPtr leak (including a leak of the hypercall file handle;
|
||||
that's how I noticed this problem), because now the drivers are only
|
||||
close if and only if the ref-count drops to zero, but this cannot
|
||||
happen anymore, because the additional refs from the Xen subdrivers
|
||||
would only be removed if the drivers get closed, but that doesn't
|
||||
happen because the ref-count cannot drop to zero.
|
||||
|
||||
The fix for this problem is simple: remove the
|
||||
virConnectRef/virUnrefConnect calls from the Xen subdrivers (see
|
||||
attached patch). Maybe someone could explain why the Xen Inotify and
|
||||
Xen Store driver do this extra ref-counting, but none of the other Xen
|
||||
subdrivers. It seems unnecessary to me and can be removed without
|
||||
problems.
|
||||
|
||||
Signed-off-by: Chris Lalancette <clalance@redhat.com>
|
||||
|
||||
(cherry picked from commit 6ed7374c5a6c6a2b1b1801d7d041dc7f09748592)
|
||||
|
||||
Fedora-patch: libvirt-fix-xen-driver-refcounting.patch
|
||||
---
|
||||
src/xen_inotify.c | 2 --
|
||||
src/xs_internal.c | 3 ---
|
||||
2 files changed, 0 insertions(+), 5 deletions(-)
|
||||
|
||||
diff --git a/src/xen_inotify.c b/src/xen_inotify.c
|
||||
index e312b9e..ecaefaf 100644
|
||||
--- a/src/xen_inotify.c
|
||||
+++ b/src/xen_inotify.c
|
||||
@@ -463,7 +463,6 @@ xenInotifyOpen(virConnectPtr conn ATTRIBUTE_UNUSED,
|
||||
DEBUG0("Failed to add inotify handle, disabling events");
|
||||
}
|
||||
|
||||
- virConnectRef(conn);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -486,7 +485,6 @@ xenInotifyClose(virConnectPtr conn)
|
||||
if (priv->inotifyWatch != -1)
|
||||
virEventRemoveHandle(priv->inotifyWatch);
|
||||
close(priv->inotifyFD);
|
||||
- virUnrefConnect(conn);
|
||||
|
||||
return 0;
|
||||
}
|
||||
diff --git a/src/xs_internal.c b/src/xs_internal.c
|
||||
index 1f54b1f..a18dcad 100644
|
||||
--- a/src/xs_internal.c
|
||||
+++ b/src/xs_internal.c
|
||||
@@ -1139,8 +1139,6 @@ int xenStoreAddWatch(virConnectPtr conn,
|
||||
list->watches[n] = watch;
|
||||
list->count++;
|
||||
|
||||
- conn->refs++;
|
||||
-
|
||||
return xs_watch(priv->xshandle, watch->path, watch->token);
|
||||
}
|
||||
|
||||
@@ -1190,7 +1188,6 @@ int xenStoreRemoveWatch(virConnectPtr conn,
|
||||
; /* Failure to reduce memory allocation isn't fatal */
|
||||
}
|
||||
list->count--;
|
||||
- virUnrefConnect(conn);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,141 +0,0 @@
|
||||
From c8a9dbe131713de83bdc67c563c4ab149e32c489 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Fri, 14 Aug 2009 08:31:11 +0100
|
||||
Subject: [PATCH] Improve PCI host device reset error message
|
||||
|
||||
https://bugzilla.redhat.com/499678
|
||||
|
||||
Currently, if we are unable to reset a PCI device we return a fairly
|
||||
generic 'No PCI reset capability available' error message.
|
||||
|
||||
Fix that by returning an error from the individual reset messages and
|
||||
using that error to construct the higher level error mesage.
|
||||
|
||||
* src/pci.c: set errors in pciTryPowerManagementReset() and
|
||||
pciTrySecondaryBusReset() on failure; use those error messages
|
||||
in pciResetDevice(), or explain that no reset support is available
|
||||
|
||||
(cherry picked from commit ebea34185612c3b96d7d3bbd8b7c2ce6c9f4fe6f)
|
||||
|
||||
Fedora-patch: libvirt-improve-pci-hostdev-reset-error-message.patch
|
||||
---
|
||||
src/pci.c | 44 +++++++++++++++++++++++++++++++-------------
|
||||
src/qemu_driver.c | 4 ++--
|
||||
2 files changed, 33 insertions(+), 15 deletions(-)
|
||||
|
||||
diff --git a/src/pci.c b/src/pci.c
|
||||
index 11b3e8b..74f7ef0 100644
|
||||
--- a/src/pci.c
|
||||
+++ b/src/pci.c
|
||||
@@ -456,15 +456,18 @@ pciTrySecondaryBusReset(virConnectPtr conn, pciDevice *dev)
|
||||
* are not in use by the host or other guests.
|
||||
*/
|
||||
if (pciBusContainsOtherDevices(conn, dev)) {
|
||||
- VIR_WARN("Other devices on bus with %s, not doing bus reset",
|
||||
- dev->name);
|
||||
+ pciReportError(conn, VIR_ERR_NO_SUPPORT,
|
||||
+ _("Other devices on bus with %s, not doing bus reset"),
|
||||
+ dev->name);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Find the parent bus */
|
||||
parent = pciGetParentDevice(conn, dev);
|
||||
if (!parent) {
|
||||
- VIR_WARN("Failed to find parent device for %s", dev->name);
|
||||
+ pciReportError(conn, VIR_ERR_NO_SUPPORT,
|
||||
+ _("Failed to find parent device for %s"),
|
||||
+ dev->name);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -475,7 +478,9 @@ pciTrySecondaryBusReset(virConnectPtr conn, pciDevice *dev)
|
||||
* are multiple devices/functions
|
||||
*/
|
||||
if (pciRead(dev, 0, config_space, PCI_CONF_LEN) < 0) {
|
||||
- VIR_WARN("Failed to save PCI config space for %s", dev->name);
|
||||
+ pciReportError(conn, VIR_ERR_NO_SUPPORT,
|
||||
+ _("Failed to save PCI config space for %s"),
|
||||
+ dev->name);
|
||||
goto out;
|
||||
}
|
||||
|
||||
@@ -492,9 +497,12 @@ pciTrySecondaryBusReset(virConnectPtr conn, pciDevice *dev)
|
||||
|
||||
usleep(200 * 1000); /* sleep 200ms */
|
||||
|
||||
- if (pciWrite(dev, 0, config_space, PCI_CONF_LEN) < 0)
|
||||
- VIR_WARN("Failed to restore PCI config space for %s", dev->name);
|
||||
-
|
||||
+ if (pciWrite(dev, 0, config_space, PCI_CONF_LEN) < 0) {
|
||||
+ pciReportError(conn, VIR_ERR_NO_SUPPORT,
|
||||
+ _("Failed to restore PCI config space for %s"),
|
||||
+ dev->name);
|
||||
+ goto out;
|
||||
+ }
|
||||
ret = 0;
|
||||
out:
|
||||
pciFreeDevice(conn, parent);
|
||||
@@ -516,7 +524,9 @@ pciTryPowerManagementReset(virConnectPtr conn ATTRIBUTE_UNUSED, pciDevice *dev)
|
||||
|
||||
/* Save and restore the device's config space. */
|
||||
if (pciRead(dev, 0, &config_space[0], PCI_CONF_LEN) < 0) {
|
||||
- VIR_WARN("Failed to save PCI config space for %s", dev->name);
|
||||
+ pciReportError(conn, VIR_ERR_NO_SUPPORT,
|
||||
+ _("Failed to save PCI config space for %s"),
|
||||
+ dev->name);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -533,8 +543,12 @@ pciTryPowerManagementReset(virConnectPtr conn ATTRIBUTE_UNUSED, pciDevice *dev)
|
||||
|
||||
usleep(10 * 1000); /* sleep 10ms */
|
||||
|
||||
- if (pciWrite(dev, 0, &config_space[0], PCI_CONF_LEN) < 0)
|
||||
- VIR_WARN("Failed to restore PCI config space for %s", dev->name);
|
||||
+ if (pciWrite(dev, 0, &config_space[0], PCI_CONF_LEN) < 0) {
|
||||
+ pciReportError(conn, VIR_ERR_NO_SUPPORT,
|
||||
+ _("Failed to restore PCI config space for %s"),
|
||||
+ dev->name);
|
||||
+ return -1;
|
||||
+ }
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -582,10 +596,14 @@ pciResetDevice(virConnectPtr conn, pciDevice *dev)
|
||||
if (ret < 0 && dev->bus != 0)
|
||||
ret = pciTrySecondaryBusReset(conn, dev);
|
||||
|
||||
- if (ret < 0)
|
||||
+ if (ret < 0) {
|
||||
+ virErrorPtr err = virGetLastError();
|
||||
pciReportError(conn, VIR_ERR_NO_SUPPORT,
|
||||
- _("No PCI reset capability available for %s"),
|
||||
- dev->name);
|
||||
+ _("Unable to reset PCI device %s: %s"),
|
||||
+ dev->name,
|
||||
+ err ? err->message : _("no FLR, PM reset or bus reset available"));
|
||||
+ }
|
||||
+
|
||||
return ret;
|
||||
}
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 4ce7a54..fd39fc2 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -1465,9 +1465,9 @@ qemuDomainReAttachHostDevices(virConnectPtr conn, virDomainDefPtr def)
|
||||
continue;
|
||||
}
|
||||
|
||||
- if (pciDettachDevice(conn, dev) < 0) {
|
||||
+ if (pciReAttachDevice(conn, dev) < 0) {
|
||||
virErrorPtr err = virGetLastError();
|
||||
- VIR_ERROR(_("Failed to reset PCI device: %s\n"),
|
||||
+ VIR_ERROR(_("Failed to re-attach PCI device: %s\n"),
|
||||
err ? err->message : "");
|
||||
virResetError(err);
|
||||
}
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,31 @@
|
||||
From 918724aa76982224437384d712c182c332fa5ef9 Mon Sep 17 00:00:00 2001
|
||||
From: Dan Kenigsberg <danken@redhat.com>
|
||||
Date: Wed, 21 Oct 2009 13:56:04 +0200
|
||||
Subject: [PATCH] Do not log rotate very small logs
|
||||
|
||||
Without this, after few weeks without use, each defined domain grows a
|
||||
tail of empty gzipped logs, instead of keeping just the last log of
|
||||
interest.
|
||||
|
||||
* daemon/libvirtd.logrotate.in: only rotate when the log is over 100 KBytes
|
||||
|
||||
(cherry picked from commit b03fe2d0aefb57a096a102bf23375f0a167ca189)
|
||||
|
||||
Fedora-patch: libvirt-logrotate-avoid-compressing-small-logs.patch
|
||||
---
|
||||
qemud/libvirtd.logrotate.in | 1 +
|
||||
1 files changed, 1 insertions(+), 0 deletions(-)
|
||||
|
||||
diff --git a/qemud/libvirtd.logrotate.in b/qemud/libvirtd.logrotate.in
|
||||
index 093651c..0c51fd3 100644
|
||||
--- a/qemud/libvirtd.logrotate.in
|
||||
+++ b/qemud/libvirtd.logrotate.in
|
||||
@@ -5,4 +5,5 @@
|
||||
compress
|
||||
delaycompress
|
||||
copytruncate
|
||||
+ minsize 100k
|
||||
}
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,54 @@
|
||||
From b7e3ac4f23befe67518b57e34691c301820a436c Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Tue, 6 Oct 2009 12:33:17 +0100
|
||||
Subject: [PATCH] Create /var/log/libvirt/{lxc,uml} dirs
|
||||
|
||||
Otherwise logrotate barfs:
|
||||
|
||||
error: error accessing /var/log/libvirt/uml: No such file or directory
|
||||
error: libvirtd:1 glob failed for /var/log/libvirt/uml/*.log
|
||||
error: found error in /var/log/libvirt/qemu/*.log /var/log/libvirt/uml/*.log /var/log/libvirt/lxc/*.log , skipping
|
||||
|
||||
* qemud/Makefile.am: always create /var/log/libvirt/{lxc,uml} when
|
||||
installing the logrotate conf; not ideal, but easier than making
|
||||
the logrotate conf depend on which drivers are enabled
|
||||
|
||||
Fedora-patch: libvirt-logrotate-create-lxc-uml-dirs.patch
|
||||
---
|
||||
qemud/Makefile.am | 6 ++++--
|
||||
1 files changed, 4 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/qemud/Makefile.am b/qemud/Makefile.am
|
||||
index 3d143da..a7f4bdf 100644
|
||||
--- a/qemud/Makefile.am
|
||||
+++ b/qemud/Makefile.am
|
||||
@@ -176,7 +176,7 @@ install-data-local: install-init install-data-sasl install-data-polkit \
|
||||
test -e $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml || \
|
||||
ln -s ../default.xml \
|
||||
$(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml
|
||||
- mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/qemu
|
||||
+ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt
|
||||
mkdir -p $(DESTDIR)$(localstatedir)/run/libvirt
|
||||
mkdir -p $(DESTDIR)$(localstatedir)/lib/libvirt
|
||||
|
||||
@@ -184,7 +184,7 @@ uninstall-local:: uninstall-init uninstall-data-sasl install-data-polkit
|
||||
rm -f $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml
|
||||
rm -f $(DESTDIR)$(sysconfdir)/$(default_xml_dest)
|
||||
rmdir $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart || :
|
||||
- rmdir $(DESTDIR)$(localstatedir)/log/libvirt/qemu || :
|
||||
+ rmdir $(DESTDIR)$(localstatedir)/log/libvirt || :
|
||||
rmdir $(DESTDIR)$(localstatedir)/run/libvirt || :
|
||||
rmdir $(DESTDIR)$(localstatedir)/lib/libvirt || :
|
||||
|
||||
@@ -240,6 +240,8 @@ libvirtd.logrotate: libvirtd.logrotate.in
|
||||
|
||||
install-logrotate: libvirtd.logrotate
|
||||
mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/qemu/
|
||||
+ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/lxc/
|
||||
+ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/uml/
|
||||
mkdir -p $(DESTDIR)$(sysconfdir)/logrotate.d/
|
||||
$(INSTALL_DATA) $< $(DESTDIR)$(sysconfdir)/logrotate.d/libvirtd
|
||||
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,32 @@
|
||||
From ba3bc9b22a21b8e9e110166c98be70e2ad6469cb Mon Sep 17 00:00:00 2001
|
||||
From: Cole Robinson <crobinso@redhat.com>
|
||||
Date: Tue, 13 Oct 2009 11:31:27 -0400
|
||||
Subject: [PATCH] network: Fix printing XML 'delay' attribute
|
||||
|
||||
When specifying bridge delay via network XML define, we were looking for
|
||||
the 'delay' attribute, but would dump the value as 'forwardDelay'. Have
|
||||
the output match the expected input (and schema).
|
||||
|
||||
(cherry picked from commit 3b13aa3db37bf5a692bccfa015a01999043e797b)
|
||||
|
||||
Fedora-patch: libvirt-network-delay-attribute-formatting.patch
|
||||
---
|
||||
src/network_conf.c | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/network_conf.c b/src/network_conf.c
|
||||
index 3764bb4..f75c457 100644
|
||||
--- a/src/network_conf.c
|
||||
+++ b/src/network_conf.c
|
||||
@@ -587,7 +587,7 @@ char *virNetworkDefFormat(virConnectPtr conn,
|
||||
virBufferAddLit(&buf, " <bridge");
|
||||
if (def->bridge)
|
||||
virBufferEscapeString(&buf, " name='%s'", def->bridge);
|
||||
- virBufferVSprintf(&buf, " stp='%s' forwardDelay='%ld' />\n",
|
||||
+ virBufferVSprintf(&buf, " stp='%s' delay='%ld' />\n",
|
||||
def->stp ? "on" : "off",
|
||||
def->delay);
|
||||
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,177 @@
|
||||
From d7722ed1cb04aa8a7b9fbf880882841867b69ab0 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Mon, 12 Oct 2009 10:52:13 +0100
|
||||
Subject: [PATCH] Take domain type into account when looking up default machine
|
||||
|
||||
If one has e.g.
|
||||
|
||||
<guest>
|
||||
<os_type>hvm</os_type>
|
||||
<arch name='x86_64'>
|
||||
<wordsize>64</wordsize>
|
||||
<emulator>/usr/bin/qemu-system-x86_64</emulator>
|
||||
<machine>pc-0.11</machine>
|
||||
<machine canonical='pc-0.11'>pc</machine>
|
||||
<machine>pc-0.10</machine>
|
||||
<machine>isapc</machine>
|
||||
<domain type='qemu'>
|
||||
</domain>
|
||||
<domain type='kvm'>
|
||||
<emulator>/usr/bin/kvm</emulator>
|
||||
<machine>pc</machine>
|
||||
<machine>isapc</machine>
|
||||
</domain>
|
||||
</arch>
|
||||
</guest>
|
||||
|
||||
and start a guest with:
|
||||
|
||||
<domain type='kvm'>
|
||||
...
|
||||
<os>
|
||||
<type arch='x86_64'>hvm</type>
|
||||
...
|
||||
</os>
|
||||
</domain>
|
||||
|
||||
then the default machine type should be 'pc' and not 'pc-0.11'
|
||||
|
||||
Issue was reported by Anton Protopopov.
|
||||
|
||||
* src/capabilities.[ch]: pass the domain type to
|
||||
virCapabilitiesDefaultGuestArch() and use it to look up the default
|
||||
machine type from a specific guest domain if needed.
|
||||
|
||||
* src/conf/domain_conf.c, src/xen/xm_internal.c: update
|
||||
|
||||
* tests/qemuxml2argvdata/qemuxml2argv-machine-aliases2.xml: update
|
||||
the domain type to 'kvm' and remove the machine type to check
|
||||
that the default gets looked up correctly
|
||||
|
||||
(cherry picked from commit 73c901a8075c09203545fc81164c1e5f11c67c89)
|
||||
|
||||
Fedora-patch: libvirt-qemu-machine-type-fixes1.patch
|
||||
---
|
||||
src/capabilities.c | 31 ++++++++++++++++---
|
||||
src/capabilities.h | 3 +-
|
||||
src/domain_conf.c | 3 +-
|
||||
src/xm_internal.c | 3 +-
|
||||
.../qemuxml2argv-machine-aliases2.xml | 4 +-
|
||||
5 files changed, 34 insertions(+), 10 deletions(-)
|
||||
|
||||
diff --git a/src/capabilities.c b/src/capabilities.c
|
||||
index 38fe7fc..6ebddf5 100644
|
||||
--- a/src/capabilities.c
|
||||
+++ b/src/capabilities.c
|
||||
@@ -549,22 +549,43 @@ virCapabilitiesDefaultGuestArch(virCapsPtr caps,
|
||||
* @caps: capabilities to query
|
||||
* @ostype: OS type to search for
|
||||
* @arch: architecture to search for
|
||||
+ * @domain: domain type to search for
|
||||
*
|
||||
* Returns the first machine variant associated with
|
||||
- * the requested operating system type and architecture
|
||||
+ * the requested operating system type, architecture
|
||||
+ * and domain type
|
||||
*/
|
||||
extern const char *
|
||||
virCapabilitiesDefaultGuestMachine(virCapsPtr caps,
|
||||
const char *ostype,
|
||||
- const char *arch)
|
||||
+ const char *arch,
|
||||
+ const char *domain)
|
||||
{
|
||||
int i;
|
||||
+
|
||||
for (i = 0 ; i < caps->nguests ; i++) {
|
||||
- if (STREQ(caps->guests[i]->ostype, ostype) &&
|
||||
- STREQ(caps->guests[i]->arch.name, arch) &&
|
||||
- caps->guests[i]->arch.defaultInfo.nmachines)
|
||||
+ virCapsGuestPtr guest = caps->guests[i];
|
||||
+ int j;
|
||||
+
|
||||
+ if (!STREQ(guest->ostype, ostype) || !STREQ(guest->arch.name, arch))
|
||||
+ continue;
|
||||
+
|
||||
+ for (j = 0; j < guest->arch.ndomains; j++) {
|
||||
+ virCapsGuestDomainPtr dom= guest->arch.domains[j];
|
||||
+
|
||||
+ if (!STREQ(dom->type, domain))
|
||||
+ continue;
|
||||
+
|
||||
+ if (!dom->info.nmachines)
|
||||
+ break;
|
||||
+
|
||||
+ return dom->info.machines[0]->name;
|
||||
+ }
|
||||
+
|
||||
+ if (guest->arch.defaultInfo.nmachines)
|
||||
return caps->guests[i]->arch.defaultInfo.machines[0]->name;
|
||||
}
|
||||
+
|
||||
return NULL;
|
||||
}
|
||||
|
||||
diff --git a/src/capabilities.h b/src/capabilities.h
|
||||
index b958d95..2f24605 100644
|
||||
--- a/src/capabilities.h
|
||||
+++ b/src/capabilities.h
|
||||
@@ -207,7 +207,8 @@ virCapabilitiesDefaultGuestArch(virCapsPtr caps,
|
||||
extern const char *
|
||||
virCapabilitiesDefaultGuestMachine(virCapsPtr caps,
|
||||
const char *ostype,
|
||||
- const char *arch);
|
||||
+ const char *arch,
|
||||
+ const char *domain);
|
||||
extern const char *
|
||||
virCapabilitiesDefaultGuestEmulator(virCapsPtr caps,
|
||||
const char *ostype,
|
||||
diff --git a/src/domain_conf.c b/src/domain_conf.c
|
||||
index 5ae0775..c424c67 100644
|
||||
--- a/src/domain_conf.c
|
||||
+++ b/src/domain_conf.c
|
||||
@@ -2664,7 +2664,8 @@ static virDomainDefPtr virDomainDefParseXML(virConnectPtr conn,
|
||||
if (!def->os.machine) {
|
||||
const char *defaultMachine = virCapabilitiesDefaultGuestMachine(caps,
|
||||
def->os.type,
|
||||
- def->os.arch);
|
||||
+ def->os.arch,
|
||||
+ virDomainVirtTypeToString(def->virtType));
|
||||
if (defaultMachine != NULL) {
|
||||
if (!(def->os.machine = strdup(defaultMachine))) {
|
||||
virReportOOMError(conn);
|
||||
diff --git a/src/xm_internal.c b/src/xm_internal.c
|
||||
index de3aca9..6d351d4 100644
|
||||
--- a/src/xm_internal.c
|
||||
+++ b/src/xm_internal.c
|
||||
@@ -720,7 +720,8 @@ xenXMDomainConfigParse(virConnectPtr conn, virConfPtr conf) {
|
||||
|
||||
defaultMachine = virCapabilitiesDefaultGuestMachine(priv->caps,
|
||||
def->os.type,
|
||||
- def->os.arch);
|
||||
+ def->os.arch,
|
||||
+ virDomainVirtTypeToString(def->virtType));
|
||||
if (defaultMachine != NULL) {
|
||||
if (!(def->os.machine = strdup(defaultMachine)))
|
||||
goto no_memory;
|
||||
diff --git a/tests/qemuxml2argvdata/qemuxml2argv-machine-aliases2.xml b/tests/qemuxml2argvdata/qemuxml2argv-machine-aliases2.xml
|
||||
index 6f62243..a2c6254 100644
|
||||
--- a/tests/qemuxml2argvdata/qemuxml2argv-machine-aliases2.xml
|
||||
+++ b/tests/qemuxml2argvdata/qemuxml2argv-machine-aliases2.xml
|
||||
@@ -1,11 +1,11 @@
|
||||
-<domain type='qemu'>
|
||||
+<domain type='kvm'>
|
||||
<name>QEMUGuest1</name>
|
||||
<uuid>c7a5fdbd-edaf-9455-926a-d65c16db1809</uuid>
|
||||
<memory>219200</memory>
|
||||
<currentMemory>219200</currentMemory>
|
||||
<vcpu>1</vcpu>
|
||||
<os>
|
||||
- <type arch='x86_64' machine='pc'>hvm</type>
|
||||
+ <type arch='x86_64'>hvm</type>
|
||||
<boot dev='hd'/>
|
||||
</os>
|
||||
<clock offset='utc'/>
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,42 @@
|
||||
From bb64cc4cbe5d3c69057f63be2c1acaca72038e5a Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Thu, 15 Oct 2009 12:09:17 +0100
|
||||
Subject: [PATCH] Don't copy old machines from a domain which has none
|
||||
|
||||
If the the qemu and kvm binaries are the same, we don't include machine
|
||||
types in the kvm domain info.
|
||||
|
||||
However, the code which refreshes the machine types info from the
|
||||
previous capabilities structure first looks at the kvm domain's info,
|
||||
finds it matches and then copies the empty machine types list over
|
||||
for the top-level qemu domain.
|
||||
|
||||
That doesn't make sense, we shouldn't copy an empty machin types list.
|
||||
|
||||
* src/qemu/qemu_conf.c: qemudGetOldMachinesFromInfo(): don't copy an
|
||||
empty machine types list.
|
||||
|
||||
(cherry picked from commit 2210f8a3a8e2774ca4fb8b42e21899e5b85ca913)
|
||||
|
||||
Fedora-patch: libvirt-qemu-machine-type-fixes2.patch
|
||||
---
|
||||
src/qemu_conf.c | 3 +++
|
||||
1 files changed, 3 insertions(+), 0 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_conf.c b/src/qemu_conf.c
|
||||
index 0dd0624..34a7fe1 100644
|
||||
--- a/src/qemu_conf.c
|
||||
+++ b/src/qemu_conf.c
|
||||
@@ -505,6 +505,9 @@ qemudGetOldMachinesFromInfo(virCapsGuestDomainInfoPtr info,
|
||||
virCapsGuestMachinePtr *list;
|
||||
int i;
|
||||
|
||||
+ if (!info->nmachines)
|
||||
+ return 0;
|
||||
+
|
||||
if (!info->emulator || !STREQ(emulator, info->emulator))
|
||||
return 0;
|
||||
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,124 +0,0 @@
|
||||
From 8f26acc66ca90eea67fd5e84be5a76e3b8aa7fbf Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Fri, 14 Aug 2009 08:31:11 +0100
|
||||
Subject: [PATCH] Reset and re-attach PCI host devices on guest shutdown
|
||||
|
||||
https://bugzilla.redhat.com/499561
|
||||
|
||||
When the guest shuts down, we should attempt to restore all PCI host
|
||||
devices to a sane state.
|
||||
|
||||
In the case of managed hostdevs, we should reset and re-attach the
|
||||
devices. In the case of unmanaged hostdevs, we should just reset them.
|
||||
|
||||
Note, KVM will already reset assigned devices when the guest shuts
|
||||
down using whatever means it can, so we are only doing it to cover the
|
||||
cases the kernel can't handle.
|
||||
|
||||
* src/qemu_driver.c: add qemuDomainReAttachHostDevices() and call
|
||||
it from qemudShutdownVMDaemon()
|
||||
|
||||
(cherry picked from commit 4035152a8767e72fd4e26a91cb4d5afa75b72e61)
|
||||
|
||||
Fedora-patch: libvirt-reattach-pci-hostdevs-after-guest-shutdown.patch
|
||||
---
|
||||
src/qemu_driver.c | 76 +++++++++++++++++++++++++++++++++++++++++++++++++++++
|
||||
1 files changed, 76 insertions(+), 0 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 2c4fd6f..4ce7a54 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -1402,6 +1402,80 @@ error:
|
||||
return -1;
|
||||
}
|
||||
|
||||
+static void
|
||||
+qemuDomainReAttachHostDevices(virConnectPtr conn, virDomainDefPtr def)
|
||||
+{
|
||||
+ int i;
|
||||
+
|
||||
+ /* Again 2 loops; reset all the devices before re-attach */
|
||||
+
|
||||
+ for (i = 0 ; i < def->nhostdevs ; i++) {
|
||||
+ virDomainHostdevDefPtr hostdev = def->hostdevs[i];
|
||||
+ pciDevice *dev;
|
||||
+
|
||||
+ if (hostdev->mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS)
|
||||
+ continue;
|
||||
+ if (hostdev->source.subsys.type != VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI)
|
||||
+ continue;
|
||||
+
|
||||
+ dev = pciGetDevice(conn,
|
||||
+ hostdev->source.subsys.u.pci.domain,
|
||||
+ hostdev->source.subsys.u.pci.bus,
|
||||
+ hostdev->source.subsys.u.pci.slot,
|
||||
+ hostdev->source.subsys.u.pci.function);
|
||||
+ if (!dev) {
|
||||
+ virErrorPtr err = virGetLastError();
|
||||
+ VIR_ERROR(_("Failed to allocate pciDevice: %s\n"),
|
||||
+ err ? err->message : "");
|
||||
+ virResetError(err);
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
+ if (pciResetDevice(conn, dev) < 0) {
|
||||
+ virErrorPtr err = virGetLastError();
|
||||
+ VIR_ERROR(_("Failed to reset PCI device: %s\n"),
|
||||
+ err ? err->message : "");
|
||||
+ virResetError(err);
|
||||
+ }
|
||||
+
|
||||
+ pciFreeDevice(conn, dev);
|
||||
+ }
|
||||
+
|
||||
+ for (i = 0 ; i < def->nhostdevs ; i++) {
|
||||
+ virDomainHostdevDefPtr hostdev = def->hostdevs[i];
|
||||
+ pciDevice *dev;
|
||||
+
|
||||
+ if (hostdev->mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS)
|
||||
+ continue;
|
||||
+ if (hostdev->source.subsys.type != VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI)
|
||||
+ continue;
|
||||
+ if (!hostdev->managed)
|
||||
+ continue;
|
||||
+
|
||||
+ dev = pciGetDevice(conn,
|
||||
+ hostdev->source.subsys.u.pci.domain,
|
||||
+ hostdev->source.subsys.u.pci.bus,
|
||||
+ hostdev->source.subsys.u.pci.slot,
|
||||
+ hostdev->source.subsys.u.pci.function);
|
||||
+ if (!dev) {
|
||||
+ virErrorPtr err = virGetLastError();
|
||||
+ VIR_ERROR(_("Failed to allocate pciDevice: %s\n"),
|
||||
+ err ? err->message : "");
|
||||
+ virResetError(err);
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
+ if (pciDettachDevice(conn, dev) < 0) {
|
||||
+ virErrorPtr err = virGetLastError();
|
||||
+ VIR_ERROR(_("Failed to reset PCI device: %s\n"),
|
||||
+ err ? err->message : "");
|
||||
+ virResetError(err);
|
||||
+ }
|
||||
+
|
||||
+ pciFreeDevice(conn, dev);
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
static const char *const defaultDeviceACL[] = {
|
||||
"/dev/null", "/dev/full", "/dev/zero",
|
||||
"/dev/random", "/dev/urandom",
|
||||
@@ -2109,6 +2183,8 @@ static void qemudShutdownVMDaemon(virConnectPtr conn,
|
||||
VIR_WARN("Failed to restore all device ownership for %s",
|
||||
vm->def->name);
|
||||
|
||||
+ qemuDomainReAttachHostDevices(conn, vm->def);
|
||||
+
|
||||
retry:
|
||||
if ((ret = qemuRemoveCgroup(conn, driver, vm)) < 0) {
|
||||
if (ret == -EBUSY && (retries++ < 5)) {
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
From a44bce591a8d746a4a00c8609cb0111c76271cab Mon Sep 17 00:00:00 2001
|
||||
From: Cole Robinson <crobinso@redhat.com>
|
||||
Date: Thu, 8 Oct 2009 18:05:36 -0400
|
||||
Subject: [PATCH] storage: Fix generating iscsi 'auth' xml
|
||||
|
||||
We were missing a closing tag, so the XML wasn't proper.
|
||||
|
||||
(cherry picked from commit 826cbac4591fd5929b497299a90d3a65226b2825)
|
||||
|
||||
Fedora-patch: libvirt-storage-iscsi-auth-xml-formatting.patch
|
||||
---
|
||||
src/storage_conf.c | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/storage_conf.c b/src/storage_conf.c
|
||||
index 788de15..1633aac 100644
|
||||
--- a/src/storage_conf.c
|
||||
+++ b/src/storage_conf.c
|
||||
@@ -799,7 +799,7 @@ virStoragePoolSourceFormat(virConnectPtr conn,
|
||||
|
||||
|
||||
if (src->authType == VIR_STORAGE_POOL_AUTH_CHAP)
|
||||
- virBufferVSprintf(buf," <auth type='chap' login='%s' passwd='%s'>\n",
|
||||
+ virBufferVSprintf(buf," <auth type='chap' login='%s' passwd='%s'/>\n",
|
||||
src->auth.chap.login,
|
||||
src->auth.chap.passwd);
|
||||
virBufferAddLit(buf," </source>\n");
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
+432
-390
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user