[libvirt] [PATCHv4 0/3] Xen: Fix <clock> handling
by Philipp Hahn
Before version 3.1 xen only implemented clock/@offset='utc' and 'localtime'.
With the introduction of managed domains in 3.1 xend keeps track of the
rtc_timeoffset, even over reboots. This translates to libvirts
clock/@offset='variable' variant. Be advised that only HV domains have a RTC.
In addition xen also supports a variant where the offset is tracked to
'localtime', which is currently not supported by libvirt. To make matters
worse, this was somehow broken in some versions of xen and was finally fixed
with version xen-3.4.
The following patch set ...
* adds support for handling variable offsets relative to localtime,
* fixes libvirt to use clock/@offset='variable' for newer xen versions,
* adapts the test suit accordingly
I've tested this on CenOS5 (xend-3.0.3 + 3.1.2 hypervisor?), UCS-2.3
(xen-3.2.1), UCS-2.4 (xen-3.4.3) and UCS-3.0 (xen-4.1.2).
Since v1:
+ fix handling of direct-PV-domains
+ added handling of localtime=1 + rtc_timeoffset
+ fixed test suite
Since v2: (on feedback by Eric)
+ add the adjustment='reset' attribute to force the old behaviour
+ handle adjustment='$timeDelta' as a short-cut for the conversion to variable.
+ simplify error path handling
+ update version numbers to 0.9.11
Since v3:
+ Add missing offset=VARIALE for adjustment='$timeDelta' conversion.
Philipp Hahn (3):
Support clock=variable relative to localtime
Xen: Fix <clock> handling
Xen: Adapt <clock> tests
docs/formatdomain.html.in | 18 ++-
docs/schemas/domaincommon.rng | 30 +++-
src/conf/domain_conf.c | 61 +++++++-
src/conf/domain_conf.h | 17 ++-
src/libvirt_private.syms | 1 +
src/qemu/qemu_command.c | 8 +-
src/qemu/qemu_process.c | 2 +-
src/xenxs/xen_sxpr.c | 167 +++++++++++++++-----
src/xenxs/xen_xm.c | 123 ++++++++++++---
.../qemuxml2argv-clock-variable.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-boot-grub.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-bridge-ipaddr.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-curmem.xml | 2 +-
.../sexpr2xml-disk-block-shareable.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-disk-block.xml | 2 +-
.../sexpr2xml-disk-drv-blktap-qcow.xml | 2 +-
.../sexpr2xml-disk-drv-blktap-raw.xml | 2 +-
.../sexpr2xml-disk-drv-blktap2-raw.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-disk-file.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-autoport.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-empty-kernel.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-force-hpet.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-force-nohpet.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-kernel.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-legacy-vfb.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-localtime.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-net-ioemu.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-net-netfront.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-parallel-tcp.xml | 2 +-
.../sexpr2xml-fv-serial-dev-2-ports.xml | 2 +-
.../sexpr2xml-fv-serial-dev-2nd-port.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-serial-file.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-serial-null.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-serial-pipe.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-serial-pty.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-serial-stdio.xml | 2 +-
.../sexpr2xml-fv-serial-tcp-telnet.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-serial-tcp.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-serial-udp.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-serial-unix.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-sound-all.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-sound.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-usbmouse.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-usbtablet.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-utc.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv-v2.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-fv.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-net-bridged.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-net-e1000.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-net-routed.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-no-source-cdrom.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-pci-devs.xml | 2 +-
.../sexpr2xml-pv-bootloader-cmdline.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-pv-bootloader.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-pv-localtime.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-pv-vcpus.xml | 2 +-
.../sexpr2xml-pv-vfb-new-vncdisplay.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-pv-vfb-new.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-pv-vfb-orig.xml | 2 +-
.../sexpr2xmldata/sexpr2xml-pv-vfb-type-crash.xml | 2 +-
tests/sexpr2xmldata/sexpr2xml-pv.xml | 2 +-
tests/xmconfigdata/sexpr2xml-pv-bootloader.cfg | 1 +
tests/xmconfigdata/test-escape-paths.xml | 2 +-
tests/xmconfigdata/test-fullvirt-force-hpet.cfg | 2 +-
tests/xmconfigdata/test-fullvirt-force-hpet.xml | 2 +-
tests/xmconfigdata/test-fullvirt-force-nohpet.cfg | 2 +-
tests/xmconfigdata/test-fullvirt-force-nohpet.xml | 2 +-
tests/xmconfigdata/test-fullvirt-localtime.xml | 2 +-
tests/xmconfigdata/test-fullvirt-net-ioemu.xml | 2 +-
tests/xmconfigdata/test-fullvirt-net-netfront.xml | 2 +-
tests/xmconfigdata/test-fullvirt-new-cdrom.xml | 2 +-
tests/xmconfigdata/test-fullvirt-old-cdrom.cfg | 2 +-
tests/xmconfigdata/test-fullvirt-old-cdrom.xml | 2 +-
tests/xmconfigdata/test-fullvirt-parallel-tcp.xml | 2 +-
.../test-fullvirt-serial-dev-2-ports.xml | 2 +-
.../test-fullvirt-serial-dev-2nd-port.xml | 2 +-
tests/xmconfigdata/test-fullvirt-serial-file.xml | 2 +-
tests/xmconfigdata/test-fullvirt-serial-null.xml | 2 +-
tests/xmconfigdata/test-fullvirt-serial-pipe.xml | 2 +-
tests/xmconfigdata/test-fullvirt-serial-pty.xml | 2 +-
tests/xmconfigdata/test-fullvirt-serial-stdio.xml | 2 +-
.../test-fullvirt-serial-tcp-telnet.xml | 2 +-
tests/xmconfigdata/test-fullvirt-serial-tcp.xml | 2 +-
tests/xmconfigdata/test-fullvirt-serial-udp.xml | 2 +-
tests/xmconfigdata/test-fullvirt-serial-unix.xml | 2 +-
tests/xmconfigdata/test-fullvirt-sound.xml | 2 +-
tests/xmconfigdata/test-fullvirt-usbmouse.xml | 2 +-
.../test-fullvirt-usbtablet-no-bus.xml | 2 +-
tests/xmconfigdata/test-fullvirt-usbtablet.xml | 2 +-
tests/xmconfigdata/test-fullvirt-utc.xml | 2 +-
tests/xmconfigdata/test-no-source-cdrom.xml | 2 +-
tests/xmconfigdata/test-paravirt-net-e1000.cfg | 1 +
tests/xmconfigdata/test-paravirt-net-e1000.xml | 2 +-
tests/xmconfigdata/test-paravirt-net-vifname.cfg | 1 +
tests/xmconfigdata/test-paravirt-net-vifname.xml | 2 +-
.../test-paravirt-new-pvfb-vncdisplay.cfg | 1 +
.../test-paravirt-new-pvfb-vncdisplay.xml | 2 +-
tests/xmconfigdata/test-paravirt-new-pvfb.cfg | 1 +
tests/xmconfigdata/test-paravirt-new-pvfb.xml | 2 +-
.../test-paravirt-old-pvfb-vncdisplay.cfg | 1 +
.../test-paravirt-old-pvfb-vncdisplay.xml | 2 +-
tests/xmconfigdata/test-paravirt-old-pvfb.cfg | 1 +
tests/xmconfigdata/test-paravirt-old-pvfb.xml | 2 +-
tests/xmconfigdata/test-paravirt-vcpu.cfg | 1 +
tests/xmconfigdata/test-paravirt-vcpu.xml | 2 +-
tests/xmconfigdata/test-pci-devs.xml | 2 +-
tests/xml2sexprdata/xml2sexpr-boot-grub.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-bridge-ipaddr.sexpr | 4 +-
tests/xml2sexprdata/xml2sexpr-curmem.sexpr | 1 +
.../xml2sexpr-disk-block-shareable.sexpr | 4 +-
tests/xml2sexprdata/xml2sexpr-disk-block.sexpr | 4 +-
.../xml2sexprdata/xml2sexpr-disk-drv-blkback.sexpr | 4 +-
.../xml2sexpr-disk-drv-blktap-qcow.sexpr | 4 +-
.../xml2sexpr-disk-drv-blktap-raw.sexpr | 4 +-
.../xml2sexprdata/xml2sexpr-disk-drv-blktap.sexpr | 4 +-
.../xml2sexpr-disk-drv-blktap2-raw.sexpr | 4 +-
.../xml2sexprdata/xml2sexpr-disk-drv-blktap2.sexpr | 4 +-
tests/xml2sexprdata/xml2sexpr-disk-drv-loop.sexpr | 4 +-
tests/xml2sexprdata/xml2sexpr-disk-file.sexpr | 4 +-
tests/xml2sexprdata/xml2sexpr-escape.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-force-hpet.sexpr | 1 +
.../xml2sexprdata/xml2sexpr-fv-force-nohpet.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-kernel.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-localtime.sexpr | 5 +-
tests/xml2sexprdata/xml2sexpr-fv-net-ioemu.sexpr | 3 +-
.../xml2sexprdata/xml2sexpr-fv-net-netfront.sexpr | 3 +-
.../xml2sexprdata/xml2sexpr-fv-parallel-tcp.sexpr | 1 +
.../xml2sexpr-fv-serial-dev-2-ports.sexpr | 3 +-
.../xml2sexpr-fv-serial-dev-2nd-port.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-serial-file.sexpr | 3 +-
tests/xml2sexprdata/xml2sexpr-fv-serial-null.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-serial-pipe.sexpr | 3 +-
tests/xml2sexprdata/xml2sexpr-fv-serial-pty.sexpr | 1 +
.../xml2sexprdata/xml2sexpr-fv-serial-stdio.sexpr | 1 +
.../xml2sexpr-fv-serial-tcp-telnet.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-serial-tcp.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-serial-udp.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-serial-unix.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-sound.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-usbmouse.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-usbtablet.sexpr | 3 +-
tests/xml2sexprdata/xml2sexpr-fv-utc.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-v2.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-fv-vncunused.sexpr | 3 +-
tests/xml2sexprdata/xml2sexpr-fv.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-net-bridged.sexpr | 2 +-
tests/xml2sexprdata/xml2sexpr-net-e1000.sexpr | 2 +-
tests/xml2sexprdata/xml2sexpr-net-routed.sexpr | 2 +-
.../xml2sexprdata/xml2sexpr-no-source-cdrom.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-pci-devs.sexpr | 2 +-
.../xml2sexpr-pv-bootloader-cmdline.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-pv-bootloader.sexpr | 4 +-
tests/xml2sexprdata/xml2sexpr-pv-vcpus.sexpr | 2 +-
.../xml2sexprdata/xml2sexpr-pv-vfb-new-auto.sexpr | 2 +-
tests/xml2sexprdata/xml2sexpr-pv-vfb-new.sexpr | 2 +-
tests/xml2sexprdata/xml2sexpr-pv-vfb-orig.sexpr | 1 +
tests/xml2sexprdata/xml2sexpr-pv.sexpr | 2 +-
157 files changed, 526 insertions(+), 200 deletions(-)
12 years, 8 months
[libvirt] [PATCH] libvirt: xen: do not use ioemu type for any emulated NIC
by Stefan Bader
-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA512
When using the xm/xend stack to manage instances there is a bug that causes
the emulated interfaces to be unusable when the vif config contains type=ioemu.
The current code already has a special quirk to not use this keyword if no
specific model is given for the emulated NIC (defaulting to rtl8139).
Essentially it works because regardless of the type argument, the Xen stack
always creates emulated and paravirt interfaces and lets the guest decide
which one to use. So neither xl nor xm stack actually require the type keyword
for emulated NICs.
- ---
/*
* apparently type ioemu breaks paravirt drivers on HVM so skip this
* from XEND_CONFIG_MAX_VERS_NET_TYPE_IOEMU
*/
if (xendConfigVersion <= XEND_CONFIG_MAX_VERS_NET_TYPE_IOEMU)
virBufferAddLit(&buf, ",type=ioemu");
- ---
This is still broken when a different emulated NIC (eg. e1000 is enforced),
but the same fix solves that problem. Which is what the attached patch does.
I have been testing with this change applied and was able to change between
various emulated NIC models successfully. I believe it would be applicable
to libvirt upstream, too.
- -Stefan
PS: Please cc: me directly on replies as I am not subscribed to this list. Thanks.
diff -Nurp libvirt.old/src/xenxs/xen_sxpr.c libvirt-0.9.8/src/xenxs/xen_sxpr.c
- --- libvirt.old/src/xenxs/xen_sxpr.c 2012-03-16 11:17:02.685042296 +0100
+++ libvirt-0.9.8/src/xenxs/xen_sxpr.c 2012-03-15 18:43:32.000000000 +0100
@@ -1873,7 +1873,9 @@ xenFormatSxprNet(virConnectPtr conn,
}
else {
virBufferEscapeSexpr(buf, "(model '%s')", def->model);
- - virBufferAddLit(buf, "(type ioemu)");
+ /* See above. Also needed when model is specified. */
+ if (xendConfigVersion <= XEND_CONFIG_MAX_VERS_NET_TYPE_IOEMU)
+ virBufferAddLit(buf, "(type ioemu)");
}
if (!isAttach)
diff -Nurp libvirt.old/src/xenxs/xen_xm.c libvirt-0.9.8/src/xenxs/xen_xm.c
- --- libvirt.old/src/xenxs/xen_xm.c 2012-03-16 11:17:02.645042103 +0100
+++ libvirt-0.9.8/src/xenxs/xen_xm.c 2012-03-15 18:43:32.000000000 +0100
@@ -1335,7 +1335,9 @@ static int xenFormatXMNet(virConnectPtr
}
else {
virBufferAsprintf(&buf, ",model=%s", net->model);
- - virBufferAddLit(&buf, ",type=ioemu");
+ /* See above. Also needed if model is specified. */
+ if (xendConfigVersion <= XEND_CONFIG_MAX_VERS_NET_TYPE_IOEMU)
+ virBufferAddLit(&buf, ",type=ioemu");
}
if (net->ifname)
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.11 (GNU/Linux)
Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org/
iQIcBAEBCgAGBQJPYxc9AAoJEOhnXe7L7s6j3f8P/3nyZUh5dY8vVcGsRX9mkoX5
DwioJfLit8wjNUX3iJciPnTCUprJeiOpev/dKuuIaUfSEOP+xzHKcAbSVdyXhlME
R5n+EbBI6WBDbVT/rbV+Mp52bVoe3vb8LgT2dc1KzYYpcMjlzAzUd56IdJ64YQaS
r9o6ps279jY6AeDEEnz0TTajKdNbMBt578kwmsES/1rHMVLT2wLrnQp6Kc9ECQ5o
YjpOAU55Bl8OP+1DK0SFSyRl1gesrUXCN1g6QsWiiaeq0OpO8TDxfpxoBKwV19cO
kFHoZ8UR4XyaDosVg0S2+WaOn7o8B7r1k+biD23L4QaADcsN+l4uuDHaHYX4nd/L
PpbUpZY8+KjTny6H/khqYYJR/G9Wl7L6GMlGLJLihlue3/iIfrHJZdF1+dFgo9uZ
vaYgjZWe1ak9vQIUfxa4enxdadBYS7Xy1JP9egA87DACnpzOEWgZ6Qadhcj0cewm
MHfEmFWnaHHLI+TqaLSwN3XeTsbZ2GP8ixlW+ewNyAPd76g3uYFVTxDOd9a+r301
C+jtgwDcG1aciXR/diR/Dnr7JZ3Y9Fgu/gt/n0Pr4tIgiYF8+T4WG0osXssiiqbc
3p92VzkEl3P/g5QRdeB/+XxGz9IfAikALyNO4ztFSxk4JIh1ix/OIoaucNSc7XFl
boPeTDnZLrdIVncDmJ5c
=RhMW
-----END PGP SIGNATURE-----
12 years, 8 months
[libvirt] booting a snapshot
by Pankaj Rawat
Hi all
I have created a snapshot of qcow2 image as
qemu-img create -f qcow2 -b guestqcow2 snapshot1
now I want to boot from this snapshot but I don't know how
can any one tell me ?
DISCLAIMER:
-----------------------------------------------------------------------------------------------------------------------
The contents of this e-mail and any attachment(s) are confidential and
intended
for the named recipient(s) only.
It shall not attach any liability on the originator or NECHCL or its
affiliates. Any views or opinions presented in
this email are solely those of the author and may not necessarily reflect the
opinions of NECHCL or its affiliates.
Any form of reproduction, dissemination, copying, disclosure, modification,
distribution and / or publication of
this message without the prior written consent of the author of this e-mail is
strictly prohibited. If you have
received this email in error please delete it and notify the sender
immediately. .
-----------------------------------------------------------------------------------------------------------------------
12 years, 8 months
[libvirt] [PATCH libvirt-glib] Fix generation of docs in a VPATH builder
by Daniel P. Berrange
From: "Daniel P. Berrange" <berrange(a)redhat.com>
The DOC_SOURCE_DIR variable was missing the $(top_srcdir) variable
so it could not find the source files when run from a VPATH build.
Empirically the previous comment saying that $(top_srcdir) was not
needed is wrong.
---
docs/libvirt-gconfig/Makefile.am | 4 +---
docs/libvirt-glib/Makefile.am | 4 +---
docs/libvirt-gobject/Makefile.am | 4 +---
3 files changed, 3 insertions(+), 9 deletions(-)
diff --git a/docs/libvirt-gconfig/Makefile.am b/docs/libvirt-gconfig/Makefile.am
index 2af0d90..6a3df37 100644
--- a/docs/libvirt-gconfig/Makefile.am
+++ b/docs/libvirt-gconfig/Makefile.am
@@ -3,9 +3,7 @@ DOC_MODULE=Libvirt-gconfig
DOC_MAIN_SGML_FILE=$(DOC_MODULE)-docs.xml
-# Must not use $(top_srcdir) since gtkdoc-scan runs
-# from the srcdir already, not the builddir
-DOC_SOURCE_DIR=../../libvirt-gconfig
+DOC_SOURCE_DIR=$(top_srcdir)/libvirt-gconfig
SCANGOBJ_OPTIONS=
diff --git a/docs/libvirt-glib/Makefile.am b/docs/libvirt-glib/Makefile.am
index 81e9671..e45f4e2 100644
--- a/docs/libvirt-glib/Makefile.am
+++ b/docs/libvirt-glib/Makefile.am
@@ -3,9 +3,7 @@ DOC_MODULE=Libvirt-glib
DOC_MAIN_SGML_FILE=$(DOC_MODULE)-docs.xml
-# Must not use $(top_srcdir) since gtkdoc-scan runs
-# from the srcdir already, not the builddir
-DOC_SOURCE_DIR=../../libvirt-glib
+DOC_SOURCE_DIR=$(top_srcdir)/libvirt-glib
SCANGOBJ_OPTIONS=
diff --git a/docs/libvirt-gobject/Makefile.am b/docs/libvirt-gobject/Makefile.am
index 6eb3553..c068a96 100644
--- a/docs/libvirt-gobject/Makefile.am
+++ b/docs/libvirt-gobject/Makefile.am
@@ -3,9 +3,7 @@ DOC_MODULE=Libvirt-gobject
DOC_MAIN_SGML_FILE=$(DOC_MODULE)-docs.xml
-# Must not use $(top_srcdir) since gtkdoc-scan runs
-# from the srcdir already, not the builddir
-DOC_SOURCE_DIR=../../libvirt-gobject
+DOC_SOURCE_DIR=$(top_srcdir)/libvirt-gobject
SCANGOBJ_OPTIONS=
--
1.7.7.6
12 years, 8 months
[libvirt] [libvirt-glib] Remove unneeded call in libvirt-gconfig test
by Christophe Fergeau
Because of a copy and paste error, the test program is making an
unneeded call to gvir_config_domain_channel_set_target_type
when setting up its USB redirection device.
---
libvirt-gconfig/tests/test-domain-create.c | 2 --
1 files changed, 0 insertions(+), 2 deletions(-)
diff --git a/libvirt-gconfig/tests/test-domain-create.c b/libvirt-gconfig/tests/test-domain-create.c
index 88c887d..4ee33aa 100644
--- a/libvirt-gconfig/tests/test-domain-create.c
+++ b/libvirt-gconfig/tests/test-domain-create.c
@@ -204,8 +204,6 @@ int main(int argc, char **argv)
redirdev = gvir_config_domain_redirdev_new();
gvir_config_domain_redirdev_set_bus(redirdev,
GVIR_CONFIG_DOMAIN_REDIRDEV_BUS_USB);
- gvir_config_domain_channel_set_target_type(channel,
- GVIR_CONFIG_DOMAIN_CHANNEL_TARGET_VIRTIO);
spicevmc = gvir_config_domain_chardev_source_spicevmc_new();
gvir_config_domain_chardev_set_source(GVIR_CONFIG_DOMAIN_CHARDEV(redirdev),
GVIR_CONFIG_DOMAIN_CHARDEV_SOURCE(spicevmc));
--
1.7.7.6
12 years, 8 months
[libvirt] [PATCH] python: always include config.h first
by Eric Blake
On RHEL 5.7, I got this compilation failure:
In file included from /usr/include/python2.4/pyport.h:98,
from /usr/include/python2.4/Python.h:55,
from libvirt.c:3:
../gnulib/lib/time.h:468: error: expected ';', ',' or ')' before '__timer'
Turns out that our '#define restrict __restrict' from config.h wasn't
being picked up. Gnulib _requires_ that all .c files include <config.h>
first, otherwise the gnulib header overrides tend to misbehave.
* python/generator.py (buildStubs): Include <config.h> first.
---
Pushing under the build-breaker rule.
python/generator.py | 3 ++-
1 files changed, 2 insertions(+), 1 deletions(-)
diff --git a/python/generator.py b/python/generator.py
index 98072f0..e641c31 100755
--- a/python/generator.py
+++ b/python/generator.py
@@ -757,7 +757,8 @@ def buildStubs(module):
export.write("/* Generated */\n\n")
wrapper = open(wrapper_file, "w")
- wrapper.write("/* Generated */\n\n")
+ wrapper.write("/* Generated by generator.py */\n\n")
+ wrapper.write("#include <config.h>\n")
wrapper.write("#include <Python.h>\n")
wrapper.write("#include <libvirt/" + module + ".h>\n")
wrapper.write("#include \"typewrappers.h\"\n")
--
1.7.7.6
12 years, 8 months
Re: [libvirt] Unknown KVM internal error on 3.2.1
by Doug Goldstein
On Wed, Mar 7, 2012 at 8:19 AM, Avi Kivity <avi(a)redhat.com> wrote:
> On 03/07/2012 01:00 PM, Gleb Natapov wrote:
>> >
>> > > KVM internal error. Suberror: 1
>> > > emulation failure
>> > > EAX=8004003b EBX=38d54633 ECX=c0460a7e EDX=8005003b
>> > > ESI=e49329a8 EDI=f7c98d60 EBP=00000286 ESP=f7fecf68
>> > > EIP=f91d1778 EFL=00000282 [--S----] CPL=0 II=0 A20=1 SMM=0 HLT=0
>> > > ES =007b 00000000 ffffffff 00c0f300 DPL=3 DS [-WA]
>> > > CS =0060 00000000 ffffffff 00c09b00 DPL=0 CS32 [-RA]
>> > > SS =0068 00000000 ffffffff 00c09300 DPL=0 DS [-WA]
>> > > DS =007b 00000000 ffffffff 00c0f300 DPL=3 DS [-WA]
>> > > FS =0000 00000000 ffffffff 00000000
>> > > GS =0000 b7f526c0 ffffffff 00000000
>> > > LDT=0088 c074a020 00000027 00008200 DPL=0 LDT
>> > > TR =0080 c180a7c4 00002073 00008b00 DPL=0 TSS32-busy
>> > > GDT= f7c9f000 000000ff
>> > > IDT= c06fa000 000007ff
>> > > CR0=8005003b CR2=0046b044 CR3=3100d000 CR4=000006d0
>> > > DR0=0000000000000000 DR1=0000000000000000 DR2=0000000000000000
>> > > DR3=0000000000000000
>> > > DR6=00000000ffff0ff0 DR7=0000000000000400
>> > > EFER=0000000000000000
>> > > Code=?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? <??>
>> > > ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ??
>> > > ?? ?? ?? ?? ?? ??
>> >
>> > What are all these ?? doing here? Usually they indicate the bad code,
>> > but here they don't, this is strange.
>> >
>> I think it tries to execute code from mmio.
>>
>
> Likely. But let's be sure.
>
> When it happens again, please keep the guest alive so we can examine it
> via qemu monitor commands.
>
> --
> error compiling committee.c: too many arguments to function
>
Shortly after I sent the original e-mail I told libvirt to use the
host CPU. As discussed in another thread since libvirt uses
-nodefconfig, it doesn't really have the correct CPU. I believe the
original issue is from the fact that I had an AMD K10 based processor
with the errata that was previously causing some issues when it wasn't
respected. The default qemu64 processor that libvirt had the guest use
did not take into account this errata and causes this issue.
I have reverted these CPU settings and will get the monitor
information as soon as it occurs again.
Providing all the background just to be sure.
The host is:
processor : 63
vendor_id : AuthenticAMD
cpu family : 21
model : 1
model name : AMD Opteron(TM) Processor 6272
stepping : 2
microcode : 0x6000613
cpu MHz : 2099.875
cache size : 2048 KB
physical id : 2
siblings : 16
core id : 7
cpu cores : 8
apicid : 79
initial apicid : 79
fpu : yes
fpu_exception : yes
cpuid level : 13
wp : yes
flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov
pat pse36 clflush mmx fxsr sse sse2 ht syscall nx mmxext fxsr_opt
pdpe1gb rdtscp lm constant_tsc rep_good nopl nonstop_tsc extd_apicid
amd_dcm aperfmperf pni pclmulqdq monitor ssse3 cx16 sse4_1 sse4_2
popcnt aes xsave avx lahf_lm cmp_legacy svm extapic cr8_legacy abm
sse4a misalignsse 3dnowprefetch osvw ibs xop skinit wdt lwp fma4
nodeid_msr topoext perfctr_core arat cpb npt lbrv svm_lock nrip_save
tsc_scale vmcb_clean flushbyasid decodeassists pausefilter pfthreshold
bogomips : 4200.08
TLB size : 1536 4K pages
clflush size : 64
cache_alignment : 64
address sizes : 48 bits physical, 48 bits virtual
power management: ts ttp tm 100mhzsteps hwpstate [9]
The guest is:
processor : 1
vendor_id : AuthenticAMD
cpu family : 6
model : 15
model name : Intel(R) Core(TM)2 Duo CPU T7700 @ 2.40GHz
stepping : 11
cpu MHz : 2100.397
cache size : 512 KB
fdiv_bug : no
hlt_bug : no
f00f_bug : no
coma_bug : no
fpu : yes
fpu_exception : yes
cpuid level : 10
wp : yes
flags : fpu vme de pse tsc msr pae mce cx8 apic mtrr pge mca cmov pat
pse36 clflush mmx fxsr sse sse2 syscall nx mmxext fxsr_opt pdpe1gb lm
pni cx16 popcnt lahf_lm cmp_legacy svm cr8legacy abm sse4a misalignsse
3dnowprefetch
bogomips : 4200.01
The QEMU command line contains the following:
-cpu core2duo,+wdt,+skinit,+osvw,+3dnowprefetch,+misalignsse,+sse4a,+abm,+cr8legacy,+extapic,+svm,+cmp_legacy,+lahf_lm,+rdtscp,+pdpe1gb,+fxsr_opt,+mmxext,+aes,+popcnt,+sse4.2,+sse4.1,+cx16,+ht
While libvirt's XML contains:
<cpu match='exact'>
<model>Opteron_G3</model>
<vendor>AMD</vendor>
<feature policy='require' name='aes'/>
<feature policy='require' name='skinit'/>
<feature policy='require' name='vme'/>
<feature policy='require' name='mmxext'/>
<feature policy='require' name='fxsr_opt'/>
<feature policy='require' name='cr8legacy'/>
<feature policy='require' name='ht'/>
<feature policy='require' name='3dnowprefetch'/>
<feature policy='require' name='ssse3'/>
<feature policy='require' name='wdt'/>
<feature policy='require' name='extapic'/>
<feature policy='require' name='pdpe1gb'/>
<feature policy='require' name='osvw'/>
<feature policy='require' name='sse4.1'/>
<feature policy='require' name='cmp_legacy'/>
<feature policy='require' name='sse4.2'/>
</cpu>
What the guest used to be with qemu64 CPU:
processor : 1
vendor_id : AuthenticAMD
cpu family : 6
model : 3
model name : QEMU Virtual CPU version 0.15.1
stepping : 3
cpu MHz : 2100.026
fdiv_bug : no
hlt_bug : no
f00f_bug : no
coma_bug : no
fpu : yes
fpu_exception : yes
cpuid level : 4
wp : yes
flags : fpu de pse tsc msr pae mce cx8 apic pge cmov pat mmx fxsr sse
sse2 pni popcnt
bogomips : 4199.33
I also find it odd that the CPU says its 0.15.1 when -M pc-0.13 is
explicitly passed in via the command line.
--
Doug Goldstein
12 years, 8 months
[libvirt] [RFC][PATCH] nwfilter: Add support for ipset
by Stefan Berger
Sending this as an RFC for now...
This patch adds support for the recent ipset iptables extension
to libvirt's nwfilter subsystem. Ipset allows to maintain 'sets'
of IP addresses, ports and other packet parameters and allows for
faster lookup and ('chunked') rule evaluation to achieve higher
throughput than what can be achieved with individual iptables rules.
On the command line iptables supports ipset using
iptables ... -m set --match-set <ipset name> <flags> -j ...
where 'ipset name' is the name of a previously created ipset and
flags is a comma-separated list of up to 6 flags. Flags use 'src' and 'dst'
for selecting IP addresses, ports etc. from the source or
destination part of a packet. So a concrete example may look like this:
iptables -A INPUT -m set --match-set test src,src -j ACCEPT
Since ipset management is quite complex, the idea was to leave ipset
management outside of libvirt but still allow users to reference an ipset.
The user would have to make sure the ipset is available once the VM is
started so that the iptables rules can be created.
Using XML to describe an ipset in an nwfilter rule would then look as
follows:
<rule action='accept' direction='in'>
<all ipset='test:src,src'/>
</rule>
The two parameters on the command line become one parameter in the XML
attribute 'ipset' and are separated by a colon (':').
FYI: Here is the man page for ipset:
https://ipset.netfilter.org/ipset.man.html
If you have any comments, please let me know.
Regards,
Stefan
---
docs/formatnwfilter.html.in | 34 ++++++++++
docs/schemas/nwfilter.rng | 11 +++
src/conf/nwfilter_conf.c | 98
++++++++++++++++++++++++++++++
src/conf/nwfilter_conf.h | 11 +++
src/nwfilter/nwfilter_ebiptables_driver.c | 64 ++++++++++++++++++-
tests/nwfilterxml2xmlin/ipset-test.xml | 12 +++
tests/nwfilterxml2xmlout/ipset-test.xml | 12 +++
tests/nwfilterxml2xmltest.c | 2
8 files changed, 240 insertions(+), 4 deletions(-)
Index: libvirt/src/conf/nwfilter_conf.c
===================================================================
--- libvirt.orig/src/conf/nwfilter_conf.c
+++ libvirt/src/conf/nwfilter_conf.c
@@ -183,6 +183,7 @@ static const char dstportstart_str[] = "
static const char dstportend_str[] = "dstportend";
static const char dscp_str[] = "dscp";
static const char state_str[] = "state";
+static const char ipset_str[] = "ipset";
#define SRCMACADDR srcmacaddr_str
#define SRCMACMASK srcmacmask_str
@@ -206,6 +207,7 @@ static const char state_str[] = "
#define DSTPORTEND dstportend_str
#define DSCP dscp_str
#define STATE state_str
+#define IPSET ipset_str
/**
@@ -980,6 +982,94 @@ tcpFlagsFormatter(virBufferPtr buf,
return true;
}
+static bool
+ipsetValidator(enum attrDatatype datatype ATTRIBUTE_UNUSED, union data
*val,
+ virNWFilterRuleDefPtr nwf ATTRIBUTE_UNUSED,
+ nwItemDesc *item)
+{
+ unsigned int idx;
+ const char *errmsg = NULL;
+ char *col = strrchr(val->c, ':');
+ size_t pos = col - val->c;
+
+ if (!col || pos == 0) {
+ errmsg = _("malformed ipset description");
+ goto arg_err_exit;
+ }
+
+ if (pos > sizeof(item->u.ipset.setname) - 1) {
+ errmsg = _("ipset name exceeds 31 characters");
+ goto arg_err_exit;
+ }
+
+ if (virStrncpy(item->u.ipset.setname, val->c, pos,
+ sizeof(item->u.ipset.setname)) == NULL) {
+ errmsg = _("could not copy ipset name");
+ goto err_exit;
+ }
+
+ if (item->u.ipset.setname[strspn(item->u.ipset.setname,
+ VALID_IPSETNAME)] != 0) {
+ errmsg = _("ipset name contains invalid characters");
+ goto arg_err_exit;
+ }
+
+ idx = pos + 1;
+ item->u.ipset.numFlags = 0;
+ item->u.ipset.flags = 0;
+
+ errmsg = _("malformed ipset flags");
+
+ while (item->u.ipset.numFlags < 6) {
+ if (STRCASEEQLEN(&val->c[idx], "src", 3)) {
+ item->u.ipset.flags |= (1 << item->u.ipset.numFlags);
+ } else if (!STRCASEEQLEN(&val->c[idx], "dst", 3)) {
+ goto arg_err_exit;
+ }
+ item->u.ipset.numFlags++;
+ idx += 3;
+ if (val->c[idx] != ',')
+ break;
+ idx++;
+ }
+
+ if (val->c[idx] != '\0')
+ goto arg_err_exit;
+
+ return true;
+
+arg_err_exit:
+ virNWFilterReportError(VIR_ERR_INVALID_ARG,
+ "%s", errmsg);
+ return false;
+
+err_exit:
+ virNWFilterReportError(VIR_ERR_INTERNAL_ERROR,
+ "%s", errmsg);
+ return false;
+}
+
+static bool
+ipsetFormatter(virBufferPtr buf,
+ virNWFilterRuleDefPtr nwf ATTRIBUTE_UNUSED,
+ nwItemDesc *item)
+{
+ uint8_t ctr;
+
+ virBufferAdd(buf, item->u.ipset.setname, -1);
+ virBufferAddLit(buf, ":");
+
+ for (ctr = 0; ctr < item->u.ipset.numFlags; ctr++) {
+ if (ctr != 0)
+ virBufferAddLit(buf, ",");
+ if ((item->u.ipset.flags & (1 << ctr)))
+ virBufferAddLit(buf, "src");
+ else
+ virBufferAddLit(buf, "dst");
+ }
+
+ return true;
+}
#define COMMON_MAC_PROPS(STRUCT) \
{\
@@ -1411,6 +1501,13 @@ static const virXMLAttr2Struct ipv6Attri
.dataIdx = offsetof(virNWFilterRuleDef,
p.STRUCT.ipHdr.dataState),\
.validator = stateValidator,\
.formatter = stateFormatter,\
+ },\
+ {\
+ .name = IPSET,\
+ .datatype = DATATYPE_IPSET,\
+ .dataIdx = offsetof(virNWFilterRuleDef, p.STRUCT.ipHdr.dataIPSet),\
+ .validator = ipsetValidator,\
+ .formatter = ipsetFormatter,\
}
#define COMMON_PORT_PROPS(STRUCT) \
@@ -1853,6 +1950,7 @@ virNWFilterRuleDetailsParse(xmlNodePtr n
break;
case DATATYPE_STRING:
+ case DATATYPE_IPSET:
if (!validator) {
/* not supported */
rc = -1;
Index: libvirt/src/conf/nwfilter_conf.h
===================================================================
--- libvirt.orig/src/conf/nwfilter_conf.h
+++ libvirt/src/conf/nwfilter_conf.h
@@ -103,8 +103,9 @@ enum attrDatatype {
DATATYPE_BOOLEAN = (1 << 12),
DATATYPE_UINT32 = (1 << 13),
DATATYPE_UINT32_HEX = (1 << 14),
+ DATATYPE_IPSET = (1 << 15),
- DATATYPE_LAST = (1 << 15),
+ DATATYPE_LAST = (1 << 16),
};
# define NWFILTER_MAC_BGA "01:80:c2:00:00:00"
@@ -136,9 +137,16 @@ struct _nwItemDesc {
uint8_t mask;
uint8_t flags;
} tcpFlags;
+ struct {
+ char setname[32];
+ uint8_t numFlags;
+ uint8_t flags;
+ } ipset;
} u;
};
+# define VALID_IPSETNAME \
+ "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_.:-+ "
typedef struct _ethHdrDataDef ethHdrDataDef;
typedef ethHdrDataDef *ethHdrDataDefPtr;
@@ -232,6 +240,7 @@ struct _ipHdrDataDef {
nwItemDesc dataState;
nwItemDesc dataConnlimitAbove;
nwItemDesc dataComment;
+ nwItemDesc dataIPSet;
};
Index: libvirt/src/nwfilter/nwfilter_ebiptables_driver.c
===================================================================
--- libvirt.orig/src/nwfilter/nwfilter_ebiptables_driver.c
+++ libvirt/src/nwfilter/nwfilter_ebiptables_driver.c
@@ -256,10 +256,13 @@ static int
_printDataType(virNWFilterVarCombIterPtr vars,
char *buf, int bufsize,
nwItemDescPtr item,
- bool asHex)
+ bool asHex, bool directionIn)
{
int done;
char *data;
+ uint8_t ctr;
+ virBuffer vb = VIR_BUFFER_INITIALIZER;
+ char *flags;
if (printVar(vars, buf, bufsize, item, &done) < 0)
return -1;
@@ -346,6 +349,41 @@ _printDataType(virNWFilterVarCombIterPtr
}
break;
+ case DATATYPE_IPSET:
+ for (ctr = 0; ctr < item->u.ipset.numFlags; ctr++) {
+ if (ctr != 0)
+ virBufferAddLit(&vb, ",");
+ if ((item->u.ipset.flags & (1 << ctr))) {
+ if (directionIn)
+ virBufferAddLit(&vb, "dst");
+ else
+ virBufferAddLit(&vb, "src");
+ } else {
+ if (directionIn)
+ virBufferAddLit(&vb, "src");
+ else
+ virBufferAddLit(&vb, "dst");
+ }
+ }
+
+ if (virBufferError(&vb)) {
+ virReportOOMError();
+ virBufferFreeAndReset(&vb);
+ return -1;
+ }
+
+ flags = virBufferContentAndReset(&vb);
+
+ if (snprintf(buf, bufsize, "\"%s\" %s",
+ item->u.ipset.setname, flags) >= bufsize) {
+ virNWFilterReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("Buffer too small for stringcopy
type"));
+ VIR_FREE(flags);
+ return -1;
+ }
+ VIR_FREE(flags);
+ break;
+
default:
virNWFilterReportError(VIR_ERR_INTERNAL_ERROR,
_("Unhandled datatype %x"),
item->datatype);
@@ -362,16 +400,23 @@ printDataType(virNWFilterVarCombIterPtr
char *buf, int bufsize,
nwItemDescPtr item)
{
- return _printDataType(vars, buf, bufsize, item, 0);
+ return _printDataType(vars, buf, bufsize, item, 0, 0);
}
+static int
+printDataTypeDirection(virNWFilterVarCombIterPtr vars,
+ char *buf, int bufsize,
+ nwItemDescPtr item, bool directionIn)
+{
+ return _printDataType(vars, buf, bufsize, item, 0, directionIn);
+}
static int
printDataTypeAsHex(virNWFilterVarCombIterPtr vars,
char *buf, int bufsize,
nwItemDescPtr item)
{
- return _printDataType(vars, buf, bufsize, item, 1);
+ return _printDataType(vars, buf, bufsize, item, 1, 0);
}
@@ -927,6 +972,7 @@ iptablesHandleIpHdr(virBufferPtr buf,
char ipaddr[INET6_ADDRSTRLEN],
number[MAX(INT_BUFSIZE_BOUND(uint32_t),
INT_BUFSIZE_BOUND(int))];
+ char str[200];
const char *src = "--source";
const char *dst = "--destination";
const char *srcrange = "--src-range";
@@ -938,6 +984,18 @@ iptablesHandleIpHdr(virBufferPtr buf,
dstrange = "--src-range";
}
+ if (HAS_ENTRY_ITEM(&ipHdr->dataIPSet)) {
+
+ if (printDataTypeDirection(vars,
+ str, sizeof(str),
+ &ipHdr->dataIPSet, directionIn) < 0)
+ goto err_exit;
+
+ virBufferAsprintf(afterStateMatch,
+ " -m set --match-set %s",
+ str);
+ }
+
if (HAS_ENTRY_ITEM(&ipHdr->dataSrcIPAddr)) {
if (printDataType(vars,
Index: libvirt/docs/schemas/nwfilter.rng
===================================================================
--- libvirt.orig/docs/schemas/nwfilter.rng
+++ libvirt/docs/schemas/nwfilter.rng
@@ -485,6 +485,11 @@
<ref name="stateflags-type"/>
</attribute>
</optional>
+ <optional>
+ <attribute name="ipset">
+ <ref name="ipset-type"/>
+ </attribute>
+ </optional>
</interleave>
</define>
@@ -1060,4 +1065,10 @@
<param
name="pattern">((SYN|ACK|URG|PSH|FIN|RST)(,(SYN|ACK|URG|PSH|FIN|RST))*|ALL|NONE)/((SYN|ACK|URG|PSH|FIN|RST)(,(SYN|ACK|URG|PSH|FIN|RST))*|ALL|NONE)</param>
</data>
</define>
+
+ <define name='ipset-type'>
+ <data type="string">
+ <param
name="pattern">[a-zA-Z0-9_\.:\-\+]{1,31}:(src|dst)(,(src|dst)){0,5}</param>
+ </data>
+ </define>
</grammar>
Index: libvirt/tests/nwfilterxml2xmlin/ipset-test.xml
===================================================================
--- /dev/null
+++ libvirt/tests/nwfilterxml2xmlin/ipset-test.xml
@@ -0,0 +1,12 @@
+<filter name='testcase' chain='root'>
+ <uuid>5c6d49af-b071-6127-b4ec-6f8ed4b55335</uuid>
+ <rule action='accept' direction='out'>
+ <all ipset='test:src,dst' />
+ </rule>
+ <rule action='accept' direction='in'>
+ <all ipset='test:SRC,DST,SRC' />
+ </rule>
+ <rule action='accept' direction='in'>
+ <all ipset='test:_.-+:SRC,dSt,SRC' />
+ </rule>
+</filter>
Index: libvirt/tests/nwfilterxml2xmlout/ipset-test.xml
===================================================================
--- /dev/null
+++ libvirt/tests/nwfilterxml2xmlout/ipset-test.xml
@@ -0,0 +1,12 @@
+<filter name='testcase' chain='root'>
+ <uuid>5c6d49af-b071-6127-b4ec-6f8ed4b55335</uuid>
+ <rule action='accept' direction='out' priority='500'>
+ <all ipset='test:src,dst'/>
+ </rule>
+ <rule action='accept' direction='in' priority='500'>
+ <all ipset='test:src,dst,src'/>
+ </rule>
+ <rule action='accept' direction='in' priority='500'>
+ <all ipset='test:_.-+:src,dst,src'/>
+ </rule>
+</filter>
Index: libvirt/tests/nwfilterxml2xmltest.c
===================================================================
--- libvirt.orig/tests/nwfilterxml2xmltest.c
+++ libvirt/tests/nwfilterxml2xmltest.c
@@ -157,6 +157,8 @@ mymain(void)
DO_TEST("iter-test2", false);
DO_TEST("iter-test3", false);
+ DO_TEST("ipset-test", false);
+
return (ret==0 ? EXIT_SUCCESS : EXIT_FAILURE);
}
Index: libvirt/docs/formatnwfilter.html.in
===================================================================
--- libvirt.orig/docs/formatnwfilter.html.in
+++ libvirt/docs/formatnwfilter.html.in
@@ -528,6 +528,10 @@
<li>IPV6_MASK: IPv6 mask in numbers format (FFFF:FFFF:FC00::) or CIDR
mask (0-128)</li>
<li>STRING: A string</li>
<li>BOOLEAN: 'true', 'yes', '1' or 'false', 'no', '0'</li>
+ <li>IPSET: The name of the ipset followed by a colon (':') followed
+ by up to 6 'src' or 'dst' elements selecting features from either
+ the source or destination part of the packet header; example:
+ myipset:src,src,dst</li>
</ul>
<p>
<br/><br/>
@@ -1169,6 +1173,11 @@
<td>STRING</td>
<td>TCP-only: format of mask/flags with mask and flags each being a
comma separated list of SYN,ACK,URG,PSH,FIN,RST or NONE or ALL</td>
</tr>
+ <tr>
+ <td>ipset <span class="since">(Since 0.9.10)</span></td>
+ <td>IPSET</td>
+ <td>References an IPset managed outside of libvirt</td>
+ </tr>
</table>
<p>
<br/><br/>
@@ -1269,6 +1278,11 @@
<td>STRING</td>
<td>comma separated list of NEW,ESTABLISHED,RELATED,INVALID or NONE</td>
</tr>
+ <tr>
+ <td>ipset <span class="since">(Since 0.9.10)</span></td>
+ <td>IPSET</td>
+ <td>References an IP set managed outside of libvirt</td>
+ </tr>
</table>
<p>
<br/><br/>
@@ -1358,6 +1372,11 @@
<td>STRING</td>
<td>comma separated list of NEW,ESTABLISHED,RELATED,INVALID or NONE</td>
</tr>
+ <tr>
+ <td>ipset <span class="since">(Since 0.9.10)</span></td>
+ <td>IPSET</td>
+ <td>References an IP set managed outside of libvirt</td>
+ </tr>
</table>
<p>
<br/><br/>
@@ -1459,6 +1478,11 @@
<td>STRING</td>
<td>TCP-only: format of mask/flags with mask and flags each being a
comma separated list of SYN,ACK,URG,PSH,FIN,RST or NONE or ALL</td>
</tr>
+ <tr>
+ <td>ipset <span class="since">(Since 0.9.10)</span></td>
+ <td>IPSET</td>
+ <td>References an IP set managed outside of libvirt</td>
+ </tr>
</table>
<p>
<br/><br/>
@@ -1545,6 +1569,11 @@
<td>STRING</td>
<td>comma separated list of NEW,ESTABLISHED,RELATED,INVALID or NONE</td>
</tr>
+ <tr>
+ <td>ipset <span class="since">(Since 0.9.10)</span></td>
+ <td>IPSET</td>
+ <td>References an IP set managed outside of libvirt</td>
+ </tr>
</table>
<p>
<br/><br/>
@@ -1619,6 +1648,11 @@
<td>STRING</td>
<td>comma separated list of NEW,ESTABLISHED,RELATED,INVALID or NONE</td>
</tr>
+ <tr>
+ <td>ipset <span class="since">(Since 0.9.10)</span></td>
+ <td>IPSET</td>
+ <td>References an IP set managed outside of libvirt</td>
+ </tr>
</table>
<p>
<br/><br/>
12 years, 8 months
[libvirt] [PATCH v3] python: add virDomainGetCPUStats python binding API
by Guannan Ren
dom.getCPUStats(True, 0)
[{'cpu_time': 24699446159L, 'system_time': 10870000000L, 'user_time': 950000000L}]
dom.getCPUStats(False, 0)
[{'cpu_time': 8535292289L}, {'cpu_time': 1005395355L}, {'cpu_time': 9351766377L}, {'cpu_time': 5813545649L}]
*generator.py Add a new naming rule
*libvirt-override-api.xml The API function description
*libvirt-override.c Implement it.
---
python/generator.py | 5 +-
python/libvirt-override-api.xml | 13 ++++
python/libvirt-override.c | 147 +++++++++++++++++++++++++++++++++++++++
3 files changed, 164 insertions(+), 1 deletions(-)
diff --git a/python/generator.py b/python/generator.py
index 98072f0..4f95cc9 100755
--- a/python/generator.py
+++ b/python/generator.py
@@ -423,7 +423,7 @@ skip_impl = (
'virDomainGetBlockIoTune',
'virDomainSetInterfaceParameters',
'virDomainGetInterfaceParameters',
- 'virDomainGetCPUStats', # not implemented now.
+ 'virDomainGetCPUStats',
'virDomainGetDiskErrors',
)
@@ -966,6 +966,9 @@ def nameFixup(name, classe, type, file):
elif name[0:19] == "virStorageVolLookup":
func = name[3:]
func = string.lower(func[0:1]) + func[1:]
+ elif name[0:20] == "virDomainGetCPUStats":
+ func = name[9:]
+ func = string.lower(func[0:1]) + func[1:]
elif name[0:12] == "virDomainGet":
func = name[12:]
func = string.lower(func[0:1]) + func[1:]
diff --git a/python/libvirt-override-api.xml b/python/libvirt-override-api.xml
index ab8f33a..26d9902 100644
--- a/python/libvirt-override-api.xml
+++ b/python/libvirt-override-api.xml
@@ -149,6 +149,19 @@
<arg name='path' type='char *' info='the path for the block device'/>
<arg name='flags' type='int' info='flags (unused; pass 0)'/>
</function>
+ <function name='virDomainGetCPUStats' file='python'>
+ <info>Extracts CPU statistics for a running domain. On success it will
+ return a list of data of dictionary type. If boolean total is False, the
+ first element of the list refers to CPU0 on the host, second element is
+ CPU1, and so on. The format of data struct is as follows:
+ [{cpu_time:xxx}, {cpu_time:xxx}, ...]
+ If it is True, it returns total domain CPU statistics in the format of
+ [{cpu_time:xxx, user_time:xxx, system_time:xxx}]</info>
+ <return type='str *' info='returns a list of dictionary in case of success, None in case of error'/>
+ <arg name='domain' type='virDomainPtr' info='pointer to domain object'/>
+ <arg name='total' type='bool' info='on true, return total domain CPU statistics, false return per-cpu info'/>
+ <arg name='flags' type='int' info='flags (unused; pass 0)'/>
+ </function>
<function name='virDomainInterfaceStats' file='python'>
<info>Extracts interface device statistics for a domain</info>
<return type='virDomainInterfaceStats' info='a tuple of statistics'/>
diff --git a/python/libvirt-override.c b/python/libvirt-override.c
index 792cfa3..5920456 100644
--- a/python/libvirt-override.c
+++ b/python/libvirt-override.c
@@ -378,6 +378,152 @@ cleanup:
}
static PyObject *
+libvirt_virDomainGetCPUStats(PyObject *self ATTRIBUTE_UNUSED, PyObject *args)
+{
+ virDomainPtr domain;
+ PyObject *pyobj_domain, *totalbool;
+ PyObject *cpu, *total;
+ PyObject *ret = NULL;
+ PyObject *error = NULL;
+ int ncpus = -1, start_cpu = 0;
+ int sumparams = 0, nparams = -1;
+ int i, i_retval;
+ unsigned int flags, totalflag;
+ virTypedParameterPtr params = NULL, cpuparams;
+
+ if (!PyArg_ParseTuple(args, (char *)"OOi:virDomainGetCPUStats",
+ &pyobj_domain, &totalbool, &flags))
+ return NULL;
+ domain = (virDomainPtr) PyvirDomain_Get(pyobj_domain);
+
+ if (!PyBool_Check(totalbool)) {
+ PyErr_Format(PyExc_TypeError,
+ "The \"total\" attribute must be bool");
+ return NULL;
+ } else {
+ /* Hack - Python's definition of Py_True breaks strict
+ * aliasing rules, so can't directly compare
+ */
+ PyObject *hacktrue = PyBool_FromLong(1);
+ totalflag = hacktrue == totalbool ? 1 : 0;
+ Py_DECREF(hacktrue);
+ }
+
+ if ((ret = PyList_New(0)) == NULL)
+ return NULL;
+
+ if (!totalflag) {
+ LIBVIRT_BEGIN_ALLOW_THREADS;
+ ncpus = virDomainGetCPUStats(domain, NULL, 0, 0, 0, flags);
+ LIBVIRT_END_ALLOW_THREADS;
+
+ if (ncpus < 0) {
+ error = VIR_PY_NONE;
+ goto error;
+ }
+
+ LIBVIRT_BEGIN_ALLOW_THREADS;
+ nparams = virDomainGetCPUStats(domain, NULL, 0, 0, 1, flags);
+ LIBVIRT_END_ALLOW_THREADS;
+
+ if (nparams < 0) {
+ error = VIR_PY_NONE;
+ goto error;
+ }
+
+ sumparams = nparams * MIN(ncpus, 128);
+
+ if (VIR_ALLOC_N(params, sumparams) < 0) {
+ error = PyErr_NoMemory();
+ goto error;
+ }
+
+ while (ncpus) {
+ int queried_ncpus = MIN(ncpus, 128);
+ if (nparams) {
+
+ LIBVIRT_BEGIN_ALLOW_THREADS;
+ i_retval = virDomainGetCPUStats(domain, params,
+ nparams, start_cpu, queried_ncpus, flags);
+ LIBVIRT_END_ALLOW_THREADS;
+
+ if (i_retval < 0) {
+ error = VIR_PY_NONE;
+ goto error;
+ }
+ } else {
+ i_retval = 0;
+ }
+
+ for (i = 0; i < queried_ncpus; i++) {
+ cpuparams = ¶ms[i * i_retval];
+ if ((cpu = getPyVirTypedParameter(cpuparams, i_retval)) == NULL) {
+ goto error;
+ }
+
+ if (PyList_Append(ret, cpu) < 0) {
+ Py_DECREF(cpu);
+ goto error;
+ }
+ Py_DECREF(cpu);
+ }
+
+ start_cpu += queried_ncpus;
+ ncpus -= queried_ncpus;
+ virTypedParameterArrayClear(params, sumparams);
+ }
+ } else {
+ LIBVIRT_BEGIN_ALLOW_THREADS;
+ nparams = virDomainGetCPUStats(domain, NULL, 0, -1, 1, flags);
+ LIBVIRT_END_ALLOW_THREADS;
+
+ if (nparams < 0) {
+ error = VIR_PY_NONE;
+ goto error;
+ }
+
+ if (nparams) {
+ sumparams = nparams;
+
+ if (VIR_ALLOC_N(params, nparams) < 0) {
+ error = PyErr_NoMemory();
+ goto error;
+ }
+
+ LIBVIRT_BEGIN_ALLOW_THREADS;
+ i_retval = virDomainGetCPUStats(domain, params, nparams, -1, 1, flags);
+ LIBVIRT_END_ALLOW_THREADS;
+
+ if (i_retval < 0) {
+ error = VIR_PY_NONE;
+ goto error;
+ }
+ } else {
+ i_retval = 0;
+ }
+
+ if ((total = getPyVirTypedParameter(params, i_retval)) == NULL) {
+ goto error;
+ }
+ if (PyList_Append(ret, total) < 0) {
+ Py_DECREF(total);
+ goto error;
+ }
+ Py_DECREF(total);
+ }
+
+ virTypedParameterArrayClear(params, sumparams);
+ VIR_FREE(params);
+ return ret;
+
+error:
+ virTypedParameterArrayClear(params, sumparams);
+ VIR_FREE(params);
+ Py_DECREF(ret);
+ return error;
+}
+
+static PyObject *
libvirt_virDomainInterfaceStats(PyObject *self ATTRIBUTE_UNUSED, PyObject *args) {
virDomainPtr domain;
PyObject *pyobj_domain;
@@ -5366,6 +5512,7 @@ static PyMethodDef libvirtMethods[] = {
{(char *) "virNetworkGetAutostart", libvirt_virNetworkGetAutostart, METH_VARARGS, NULL},
{(char *) "virDomainBlockStats", libvirt_virDomainBlockStats, METH_VARARGS, NULL},
{(char *) "virDomainBlockStatsFlags", libvirt_virDomainBlockStatsFlags, METH_VARARGS, NULL},
+ {(char *) "virDomainGetCPUStats", libvirt_virDomainGetCPUStats, METH_VARARGS, NULL},
{(char *) "virDomainInterfaceStats", libvirt_virDomainInterfaceStats, METH_VARARGS, NULL},
{(char *) "virDomainMemoryStats", libvirt_virDomainMemoryStats, METH_VARARGS, NULL},
{(char *) "virNodeGetCellsFreeMemory", libvirt_virNodeGetCellsFreeMemory, METH_VARARGS, NULL},
--
1.7.7.5
12 years, 8 months
[libvirt] [PATCH] python: make virDomainSetSchedulerParameters accpet integer argument
by Guannan Ren
When sending a Python integer as an argument to
PyLong_AsUnsignedLong or PyLong_AsUnsignedLongLong,
the following error occurs
SystemError: Objects/longobject.c:980:
bad argument to internal function
This error comes from the fact that
PyLong_AsUnsignedLong and PyLong_AsUnsignedLongLong,
unlike PyLong_AsLong or PyLong_AsLongLong, does not check
to see if the number is a long or integer, but only a long.
The regression is introduced by
9c8466daac19379c41be39ec8f18db36c9573c02
>>> dom.setSchedulerParameters({'cpu_shares': 1024})
0
dom.schedulerParameters()
{'cpu_shares': 1024L}
>>> dom.setSchedulerParameters({'cpu_shares': 1024L})
0
>>> dom.schedulerParameters()
{'cpu_shares': 1024L}
---
python/libvirt-override.c | 9 ++++++++-
1 files changed, 8 insertions(+), 1 deletions(-)
diff --git a/python/libvirt-override.c b/python/libvirt-override.c
index 792cfa3..aec8f5a 100644
--- a/python/libvirt-override.c
+++ b/python/libvirt-override.c
@@ -233,7 +233,14 @@ setPyVirTypedParameter(PyObject *info,
break;
case VIR_TYPED_PARAM_ULLONG:
{
- unsigned long long ullong_val = PyLong_AsUnsignedLongLong(value);
+ unsigned long long ullong_val;
+ if (PyInt_Check(value))
+ ullong_val = (unsigned long long)PyInt_AsLong(value);
+ else if (PyLong_Check(value))
+ ullong_val = PyLong_AsUnsignedLongLong(value);
+ else
+ PyErr_SetString(PyExc_TypeError, "an integer is required");
+
if ((ullong_val == -1) && PyErr_Occurred())
goto cleanup;
temp->value.ul = ullong_val;
--
1.7.7.5
12 years, 8 months