[libvirt] [PATCH 0/2] about Virsh Command Reference
by Hu Tao
Hi,
We now have libvirt advanced at 0.9.3, but there is almost no
progress has been made on Virsh Command Reference. I'm now
starting on updating Virsh Command Reference to get it synced
with libvirt/virsh, but since I'm not a native-English speaker,
there must be grammers, typos, etc. in the documents written
by me, so any comments on these are appreciated. Besides,
comments on other errors, such as example usages, are also
welcome.
In this series, docs for two cmmands are updated. I'll post more
patches for other commands subsequently.
Hu Tao (2):
update documentation for command attach-disk
update documentation for command detach-disk
source/attach-disk.xml | 292 +++++++++++++++++++++++++++++++++++++++++++++++-
source/detach-disk.xml | 233 +++++++++++++++++++++++++++++++++++++-
2 files changed, 517 insertions(+), 8 deletions(-)
--
1.7.3.1
13 years, 3 months
[libvirt] snapshots += domain description?
by Philipp Hahn
Hello,
I just encountered a problem with the current snapshot implementation for
qemu/kvm: To revert back to a snapshot, the domain description must closely
match the domain description when the snapshot was created. If the ram-size
doesn't match or the VM now contains fewer CPUs or contains additional disks,
kvm will either not load the snapshot or the machine will be broken
afterwarts.
Is this a known problem?
Without looking into the implementation details I think saving the full domain
description instead of just a reference to the domain uuid as part of the
snapshot description would work better. Or am I supposed to save the domain
description myself in addition the the data saved
in /var/lib/libvirt/qemu/snapshot/$DOMAIN_NAME/$SNAPSHOT_NAME.xml. I think
this is very important feature, because when you - for example - notice that
you need additional disk space and would like to include an additional block
device, this is your ideal time to take a snapshot you can revert to when you
do something wrong.
Looking at VMware I see that reverting a VM there will not only revert the
disks and ram back to the saved state, but also the description including
name, ram size, etc.
Any comment or advise is appreciated.
Sincerely
Philipp Hahn
--
Philipp Hahn Open Source Software Engineer hahn(a)univention.de
Univention GmbH Linux for Your Business fon: +49 421 22 232- 0
Mary-Somerville-Str.1 28359 Bremen fax: +49 421 22 232-99
http://www.univention.de
13 years, 3 months
[libvirt] [PATCH v3] Add support for fd: protocol
by Corey Bryant
sVirt provides SELinux MAC isolation for Qemu guest processes and their
corresponding resources (image files). sVirt provides this support
by labeling guests and resources with security labels that are stored
in file system extended attributes. Some file systems, such as NFS, do
not support the extended attribute security namespace, which is needed
for image file isolation when using the sVirt SELinux security driver
in libvirt.
The proposed solution entails a combination of Qemu, libvirt, and
SELinux patches that work together to isolate multiple guests' images
when they're stored in the same NFS mount. This results in an
environment where sVirt isolation and NFS image file isolation can both
be provided.
This patch contains the Qemu code to support this solution. I would
like to solicit input from the libvirt community prior to starting
the libvirt patch.
Currently, Qemu opens an image file in addition to performing the
necessary read and write operations. The proposed solution will move
the open out of Qemu and into libvirt. Once libvirt opens an image
file for the guest, it will pass the file descriptor to Qemu via a
new fd: protocol.
If the image file resides in an NFS mount, the following SELinux policy
changes will provide image isolation:
- A new SELinux boolean is created (e.g. virt_read_write_nfs) to
allow Qemu (svirt_t) to only have SELinux read and write
permissions on nfs_t files
- Qemu (svirt_t) also gets SELinux use permissions on libvirt
(virtd_t) file descriptors
Following is a sample invocation of Qemu using the fd: protocol on
the command line:
qemu -drive file=fd:4,format=qcow2
The fd: protocol is also supported by the drive_add monitor command.
This requires that the specified file descriptor is passed to the
monitor alongside a prior getfd monitor command.
There are some additional features provided by certain image types
where Qemu reopens the image file. All of these scenarios will be
unsupported for the fd: protocol, at least for this patch:
- The -snapshot command line option
- The savevm monitor command
- The snapshot_blkdev monitor command
- Use of copy-on-write image files
- The -cdrom command line option
- The -drive command line option with media=cdrom
- The change monitor command
The thought is that this support can be added in the future, but is
not required for the initial fd: support.
This patch was tested with the following formats: raw, cow, qcow,
qcow2, qed, and vmdk, using the fd: protocol from the command line
and the monitor. Tests were also run to verify existing file name
support and qemu-img were not regressed. Non-valid file descriptors,
fd: without format, snapshot and backing files, and cdrom were also
tested.
v2:
- Add drive_add monitor command support
- Fence off unsupported features that re-open image file
v3:
- Fence off cdrom and change monitor command support
Signed-off-by: Corey Bryant <coreyb(a)linux.vnet.ibm.com>
---
block.c | 16 ++++++++++
block.h | 1 +
block/cow.c | 5 +++
block/qcow.c | 5 +++
block/qcow2.c | 5 +++
block/qed.c | 4 ++
block/raw-posix.c | 81 +++++++++++++++++++++++++++++++++++++++++++++++------
block/vmdk.c | 5 +++
block_int.h | 1 +
blockdev.c | 19 ++++++++++++
monitor.c | 5 +++
monitor.h | 1 +
qemu-options.hx | 8 +++--
qemu-tool.c | 5 +++
14 files changed, 149 insertions(+), 12 deletions(-)
diff --git a/block.c b/block.c
index 24a25d5..500db84 100644
--- a/block.c
+++ b/block.c
@@ -536,6 +536,10 @@ int bdrv_open(BlockDriverState *bs, const char *filename, int flags,
char tmp_filename[PATH_MAX];
char backing_filename[PATH_MAX];
+ if (bdrv_is_fd_protocol(bs)) {
+ return -ENOTSUP;
+ }
+
/* if snapshot, we create a temporary backing file and open it
instead of opening 'filename' directly */
@@ -585,6 +589,10 @@ int bdrv_open(BlockDriverState *bs, const char *filename, int flags,
/* Find the right image format driver */
if (!drv) {
+ /* format must be specified for fd: protocol */
+ if (bdrv_is_fd_protocol(bs)) {
+ return -ENOTSUP;
+ }
ret = find_image_format(filename, &drv);
}
@@ -1460,6 +1468,11 @@ int bdrv_enable_write_cache(BlockDriverState *bs)
return bs->enable_write_cache;
}
+int bdrv_is_fd_protocol(BlockDriverState *bs)
+{
+ return bs->fd_protocol;
+}
+
/* XXX: no longer used */
void bdrv_set_change_cb(BlockDriverState *bs,
void (*change_cb)(void *opaque, int reason),
@@ -1964,6 +1977,9 @@ int bdrv_snapshot_create(BlockDriverState *bs,
BlockDriver *drv = bs->drv;
if (!drv)
return -ENOMEDIUM;
+ if (bdrv_is_fd_protocol(bs)) {
+ return -ENOTSUP;
+ }
if (drv->bdrv_snapshot_create)
return drv->bdrv_snapshot_create(bs, sn_info);
if (bs->file)
diff --git a/block.h b/block.h
index 859d1d9..0417b69 100644
--- a/block.h
+++ b/block.h
@@ -182,6 +182,7 @@ int bdrv_is_removable(BlockDriverState *bs);
int bdrv_is_read_only(BlockDriverState *bs);
int bdrv_is_sg(BlockDriverState *bs);
int bdrv_enable_write_cache(BlockDriverState *bs);
+int bdrv_is_fd_protocol(BlockDriverState *bs);
int bdrv_is_inserted(BlockDriverState *bs);
int bdrv_media_changed(BlockDriverState *bs);
int bdrv_is_locked(BlockDriverState *bs);
diff --git a/block/cow.c b/block/cow.c
index 4cf543c..e17f8e7 100644
--- a/block/cow.c
+++ b/block/cow.c
@@ -82,6 +82,11 @@ static int cow_open(BlockDriverState *bs, int flags)
pstrcpy(bs->backing_file, sizeof(bs->backing_file),
cow_header.backing_file);
+ if (bs->backing_file[0] != '\0' && bdrv_is_fd_protocol(bs)) {
+ /* backing file currently not supported by fd: protocol */
+ goto fail;
+ }
+
bitmap_size = ((bs->total_sectors + 7) >> 3) + sizeof(cow_header);
s->cow_sectors_offset = (bitmap_size + 511) & ~511;
return 0;
diff --git a/block/qcow.c b/block/qcow.c
index 227b104..964d411 100644
--- a/block/qcow.c
+++ b/block/qcow.c
@@ -157,6 +157,11 @@ static int qcow_open(BlockDriverState *bs, int flags)
if (bdrv_pread(bs->file, header.backing_file_offset, bs->backing_file, len) != len)
goto fail;
bs->backing_file[len] = '\0';
+
+ if (bs->backing_file[0] != '\0' && bdrv_is_fd_protocol(bs)) {
+ /* backing file currently not supported by fd: protocol */
+ goto fail;
+ }
}
return 0;
diff --git a/block/qcow2.c b/block/qcow2.c
index 48e1b95..7f6a4fa 100644
--- a/block/qcow2.c
+++ b/block/qcow2.c
@@ -270,6 +270,11 @@ static int qcow2_open(BlockDriverState *bs, int flags)
goto fail;
}
bs->backing_file[len] = '\0';
+
+ if (bs->backing_file[0] != '\0' && bdrv_is_fd_protocol(bs)) {
+ ret = -ENOTSUP;
+ goto fail;
+ }
}
if (qcow2_read_snapshots(bs) < 0) {
ret = -EINVAL;
diff --git a/block/qed.c b/block/qed.c
index 3970379..5028897 100644
--- a/block/qed.c
+++ b/block/qed.c
@@ -446,6 +446,10 @@ static int bdrv_qed_open(BlockDriverState *bs, int flags)
return ret;
}
+ if (bs->backing_file[0] != '\0' && bdrv_is_fd_protocol(bs)) {
+ return -ENOTSUP;
+ }
+
if (s->header.features & QED_F_BACKING_FORMAT_NO_PROBE) {
pstrcpy(bs->backing_format, sizeof(bs->backing_format), "raw");
}
diff --git a/block/raw-posix.c b/block/raw-posix.c
index 34b64aa..cec4d36 100644
--- a/block/raw-posix.c
+++ b/block/raw-posix.c
@@ -28,6 +28,7 @@
#include "block_int.h"
#include "module.h"
#include "block/raw-posix-aio.h"
+#include "monitor.h"
#ifdef CONFIG_COCOA
#include <paths.h>
@@ -185,7 +186,8 @@ static int raw_open_common(BlockDriverState *bs, const char *filename,
int bdrv_flags, int open_flags)
{
BDRVRawState *s = bs->opaque;
- int fd, ret;
+ int fd = -1;
+ int ret;
ret = raw_normalize_devicepath(&filename);
if (ret != 0) {
@@ -207,15 +209,17 @@ static int raw_open_common(BlockDriverState *bs, const char *filename,
if (!(bdrv_flags & BDRV_O_CACHE_WB))
s->open_flags |= O_DSYNC;
- s->fd = -1;
- fd = qemu_open(filename, s->open_flags, 0644);
- if (fd < 0) {
- ret = -errno;
- if (ret == -EROFS)
- ret = -EACCES;
- return ret;
+ if (s->fd == -1) {
+ fd = qemu_open(filename, s->open_flags, 0644);
+ if (fd < 0) {
+ ret = -errno;
+ if (ret == -EROFS) {
+ ret = -EACCES;
+ }
+ return ret;
+ }
+ s->fd = fd;
}
- s->fd = fd;
s->aligned_buf = NULL;
if ((bdrv_flags & BDRV_O_NOCACHE)) {
@@ -272,6 +276,7 @@ static int raw_open(BlockDriverState *bs, const char *filename, int flags)
{
BDRVRawState *s = bs->opaque;
+ s->fd = -1;
s->type = FTYPE_FILE;
return raw_open_common(bs, filename, flags, 0);
}
@@ -892,6 +897,60 @@ static BlockDriver bdrv_file = {
.create_options = raw_create_options,
};
+static int raw_open_fd(BlockDriverState *bs, const char *filename, int flags)
+{
+ BDRVRawState *s = bs->opaque;
+ const char *fd_str;
+ int fd;
+
+ /* extract the file descriptor - fail if it's not fd: */
+ if (!strstart(filename, "fd:", &fd_str)) {
+ return -EINVAL;
+ }
+
+ if (!qemu_isdigit(fd_str[0])) {
+ /* get fd from monitor */
+ fd = qemu_get_fd(fd_str);
+ if (fd == -1) {
+ return -EBADF;
+ }
+ } else {
+ char *endptr = NULL;
+
+ fd = strtol(fd_str, &endptr, 10);
+ if (*endptr || (fd == 0 && fd_str == endptr)) {
+ return -EBADF;
+ }
+ }
+
+ s->fd = fd;
+ s->type = FTYPE_FILE;
+
+ return raw_open_common(bs, filename, flags, 0);
+}
+
+static BlockDriver bdrv_file_fd = {
+ .format_name = "file",
+ .protocol_name = "fd",
+ .instance_size = sizeof(BDRVRawState),
+ .bdrv_probe = NULL, /* no probe for protocols */
+ .bdrv_file_open = raw_open_fd,
+ .bdrv_read = raw_read,
+ .bdrv_write = raw_write,
+ .bdrv_close = raw_close,
+ .bdrv_flush = raw_flush,
+ .bdrv_discard = raw_discard,
+
+ .bdrv_aio_readv = raw_aio_readv,
+ .bdrv_aio_writev = raw_aio_writev,
+ .bdrv_aio_flush = raw_aio_flush,
+
+ .bdrv_truncate = raw_truncate,
+ .bdrv_getlength = raw_getlength,
+
+ .create_options = raw_create_options,
+};
+
/***********************************************/
/* host device */
@@ -1000,6 +1059,7 @@ static int hdev_open(BlockDriverState *bs, const char *filename, int flags)
}
#endif
+ s->fd = -1;
s->type = FTYPE_FILE;
#if defined(__linux__)
{
@@ -1170,6 +1230,7 @@ static int floppy_open(BlockDriverState *bs, const char *filename, int flags)
BDRVRawState *s = bs->opaque;
int ret;
+ s->fd = -1;
s->type = FTYPE_FD;
/* open will not fail even if no floppy is inserted, so add O_NONBLOCK */
@@ -1288,6 +1349,7 @@ static int cdrom_open(BlockDriverState *bs, const char *filename, int flags)
{
BDRVRawState *s = bs->opaque;
+ s->fd = -1;
s->type = FTYPE_CD;
/* open will not fail even if no CD is inserted, so add O_NONBLOCK */
@@ -1517,6 +1579,7 @@ static void bdrv_file_init(void)
* Register all the drivers. Note that order is important, the driver
* registered last will get probed first.
*/
+ bdrv_register(&bdrv_file_fd);
bdrv_register(&bdrv_file);
bdrv_register(&bdrv_host_device);
#ifdef __linux__
diff --git a/block/vmdk.c b/block/vmdk.c
index 922b23d..2ea808e 100644
--- a/block/vmdk.c
+++ b/block/vmdk.c
@@ -353,6 +353,11 @@ static int vmdk_parent_open(BlockDriverState *bs)
return -1;
pstrcpy(bs->backing_file, end_name - p_name + 1, p_name);
+
+ if (bs->backing_file[0] != '\0' && bdrv_is_fd_protocol(bs)) {
+ /* backing file currently not supported by fd: protocol */
+ return -1;
+ }
}
return 0;
diff --git a/block_int.h b/block_int.h
index 1e265d2..441049c 100644
--- a/block_int.h
+++ b/block_int.h
@@ -152,6 +152,7 @@ struct BlockDriverState {
int encrypted; /* if true, the media is encrypted */
int valid_key; /* if true, a valid encryption key has been set */
int sg; /* if true, the device is a /dev/sg* */
+ int fd_protocol; /* if true, the fd: protocol was specified */
/* event callback when inserting/removing */
void (*change_cb)(void *opaque, int reason);
void *change_opaque;
diff --git a/blockdev.c b/blockdev.c
index c263663..5cb7b56 100644
--- a/blockdev.c
+++ b/blockdev.c
@@ -542,6 +542,14 @@ DriveInfo *drive_init(QemuOpts *opts, int default_to_scsi)
bdrv_flags |= ro ? 0 : BDRV_O_RDWR;
+ if (strncmp(file, "fd:", 3) == 0) {
+ if (media == MEDIA_CDROM) {
+ error_report("CD-ROM not supported by fd: protocol");
+ goto err;
+ }
+ dinfo->bdrv->fd_protocol = 1;
+ }
+
ret = bdrv_open(dinfo->bdrv, file, bdrv_flags, drv);
if (ret < 0) {
error_report("could not open disk image %s: %s",
@@ -602,6 +610,12 @@ int do_snapshot_blkdev(Monitor *mon, const QDict *qdict, QObject **ret_data)
goto out;
}
+ if (bdrv_is_fd_protocol(bs)) {
+ qerror_report(QERR_UNSUPPORTED);
+ ret = -1;
+ goto out;
+ }
+
pstrcpy(old_filename, sizeof(old_filename), bs->filename);
old_drv = bs->drv;
@@ -719,6 +733,11 @@ int do_change_block(Monitor *mon, const char *device,
BlockDriver *drv = NULL;
int bdrv_flags;
+ if (strncmp(filename, "fd:", 3) == 0) {
+ qerror_report(QERR_UNSUPPORTED);
+ return -1;
+ }
+
bs = bdrv_find(device);
if (!bs) {
qerror_report(QERR_DEVICE_NOT_FOUND, device);
diff --git a/monitor.c b/monitor.c
index a6388a9..e521b60 100644
--- a/monitor.c
+++ b/monitor.c
@@ -2832,6 +2832,11 @@ int monitor_get_fd(Monitor *mon, const char *fdname)
return -1;
}
+int qemu_get_fd(const char *fdname)
+{
+ return cur_mon ? monitor_get_fd(cur_mon, fdname) : -1;
+}
+
static const mon_cmd_t mon_cmds[] = {
#include "hmp-commands.h"
{ NULL, NULL, },
diff --git a/monitor.h b/monitor.h
index 4f2d328..de5b987 100644
--- a/monitor.h
+++ b/monitor.h
@@ -51,6 +51,7 @@ int monitor_read_bdrv_key_start(Monitor *mon, BlockDriverState *bs,
void *opaque);
int monitor_get_fd(Monitor *mon, const char *fdname);
+int qemu_get_fd(const char *fdname);
void monitor_vprintf(Monitor *mon, const char *fmt, va_list ap)
GCC_FMT_ATTR(2, 0);
diff --git a/qemu-options.hx b/qemu-options.hx
index cb3347e..ab28541 100644
--- a/qemu-options.hx
+++ b/qemu-options.hx
@@ -116,7 +116,7 @@ using @file{/dev/cdrom} as filename (@pxref{host_drives}).
ETEXI
DEF("drive", HAS_ARG, QEMU_OPTION_drive,
- "-drive [file=file][,if=type][,bus=n][,unit=m][,media=d][,index=i]\n"
+ "-drive [file=[fd:]file][,if=type][,bus=n][,unit=m][,media=d][,index=i]\n"
" [,cyls=c,heads=h,secs=s[,trans=t]][,snapshot=on|off]\n"
" [,cache=writethrough|writeback|none|unsafe][,format=f]\n"
" [,serial=s][,addr=A][,id=name][,aio=threads|native]\n"
@@ -129,10 +129,12 @@ STEXI
Define a new drive. Valid options are:
@table @option
-@item file=@var{file}
+@item file=[fd:]@var{file}
This option defines which disk image (@pxref{disk_images}) to use with
this drive. If the filename contains comma, you must double it
-(for instance, "file=my,,file" to use file "my,file").
+(for instance, "file=my,,file" to use file "my,file"). @option{fd:}@var{file}
+specifies the file descriptor of an already open disk image.
+@option{format=}@var{format} is required by @option{fd:}@var{file}.
@item if=@var{interface}
This option defines on which type on interface the drive is connected.
Available types are: ide, scsi, sd, mtd, floppy, pflash, virtio.
diff --git a/qemu-tool.c b/qemu-tool.c
index 41e5c41..8fe6b8c 100644
--- a/qemu-tool.c
+++ b/qemu-tool.c
@@ -96,3 +96,8 @@ int64_t qemu_get_clock_ns(QEMUClock *clock)
{
return 0;
}
+
+int qemu_get_fd(const char *fdname)
+{
+ return -1;
+}
--
1.7.3.4
13 years, 3 months
[libvirt] Is there smt missing at Java bindings?
by kadir yüceer
Hello all,
I've been posting questions about my issue to the user list but it seems
nobody can answer, so I had to try this list, sorry if there is any
disturbance.
Here is the case:
I've been trying to develop a java app that can register callbacks for
domain lifecycle events(suspend,resume,etc.). Only method that I've seen is
Connect.VirDomainEventRegisterAny, and there is an abstract callback method
inside VirConnectDomainEventGenericCallback. I implement the callback, and
register it for all the domains by passing the domain pointer as NULL.
Additionally for testing, I've added a println into the suspend function in
org.libvirt.Domain.java, and compiled the java bindings and used the new jar
file, and I was successful, I can see the message whenever I suspend the
domain either by clicking *pause* or by writing dom.suspend() in my java
app.
However, when I try to register a callback as I mentioned in the beginning
(with eventID 0, which is life_cycle ID), after the suspend operation, I get
the error that you can see at the end of the mail.
But before you check it out, I have to ask, are some of the event-related
features of libvirt missing in java bindings? For example;
VirEventAddHandleFunc, VirEventAddHandleCallback, and their derivatives. Is
this a problem or the only Connect.VirDomainEventRegisterAny method of java
binding suffice for providing callbacks for domain events?
Thanks in advance for your responses. The error is below.
Kind Regards
Kadir
#
# A fatal error has been detected by the Java Runtime Environment:
#
# SIGSEGV (0xb) at pc=0x00000000, pid=5692, tid=3077520240
#
# JRE version: 6.0_20-b20
# Java VM: OpenJDK Server VM (19.0-b09 mixed mode linux-x86 )
# Derivative: IcedTea6 1.9.7
# Distribution: Ubuntu 10.10, package 6b20-1.9.7-0ubuntu1
# Problematic frame:
# C 0x00000000
#
# An error report file with more information is saved as:
# /root/NetBeansProjects/NovaTest_v0.3/hs_err_pid5692.log
#
# If you would like to submit a bug report, please include
# instructions how to reproduce the bug and visit:
# https://bugs.launchpad.net/ubuntu/+source/openjdk-6/
# The crash happened outside the Java Virtual Machine in native code.
# See problematic frame for where to report the bug.
#
Java Result: 134
13 years, 3 months
[libvirt] [PATCH] qemu: Fix -chardev udp if parameters are omitted
by Cole Robinson
The following XML:
<serial type='udp'>
<source mode='connect' service='9999'/>
</serial>
is accepted by domain_conf.c but maps to the qemu command line:
-chardev udp,host=127.0.0.1,port=2222,localaddr=(null),localport=(null)
qemu can cope with everything omitting except the connection port, which
seems to also be the intent of domain_conf validation, so let's not
generate bogus command lines for that case.
Additionally, tweak the qemu cli parsing to handle omitted host parameters
for -serial udp
---
src/qemu/qemu_command.c | 48 +++++++++++---------
.../qemuxml2argv-serial-udp-chardev.args | 6 ++-
.../qemuxml2argv-serial-udp-chardev.xml | 4 ++
.../qemuxml2argvdata/qemuxml2argv-serial-udp.args | 2 +-
tests/qemuxml2argvdata/qemuxml2argv-serial-udp.xml | 4 ++
5 files changed, 39 insertions(+), 25 deletions(-)
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index c9b9850..231d7c3 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -2119,14 +2119,17 @@ qemuBuildChrChardevStr(virDomainChrSourceDefPtr dev, const char *alias,
break;
case VIR_DOMAIN_CHR_TYPE_UDP:
- virBufferVSprintf(&buf,
- "udp,id=char%s,host=%s,port=%s,localaddr=%s,"
- "localport=%s",
+ virBufferVSprintf(&buf, "udp,id=char%s,port=%s",
alias,
- dev->data.udp.connectHost,
- dev->data.udp.connectService,
- dev->data.udp.bindHost,
- dev->data.udp.bindService);
+ dev->data.udp.connectService);
+
+ if (dev->data.udp.connectHost)
+ virBufferVSprintf(&buf, ",host=%s", dev->data.udp.connectHost);
+ if (dev->data.udp.bindHost)
+ virBufferVSprintf(&buf, ",localaddr=%s", dev->data.udp.bindHost);
+ if (dev->data.udp.bindService)
+ virBufferVSprintf(&buf, ",localport=%s",
+ dev->data.udp.bindService);
break;
case VIR_DOMAIN_CHR_TYPE_TCP:
@@ -2216,11 +2219,13 @@ qemuBuildChrArgStr(virDomainChrSourceDefPtr dev, const char *prefix)
break;
case VIR_DOMAIN_CHR_TYPE_UDP:
- virBufferVSprintf(&buf, "udp:%s:%s@%s:%s",
- dev->data.udp.connectHost,
- dev->data.udp.connectService,
- dev->data.udp.bindHost,
- dev->data.udp.bindService);
+ virBufferVSprintf(&buf, "udp:%s:%s",
+ dev->data.udp.connectHost ?: "",
+ dev->data.udp.connectService);
+ if (dev->data.udp.bindService)
+ virBufferVSprintf(&buf, "@%s:%s",
+ dev->data.udp.bindHost ?: "",
+ dev->data.udp.bindService);
break;
case VIR_DOMAIN_CHR_TYPE_TCP:
@@ -5302,13 +5307,12 @@ qemuParseCommandLineChr(const char *val)
host2 = svc1 ? strchr(svc1, '@') : NULL;
svc2 = host2 ? strchr(host2, ':') : NULL;
- if (svc1)
+ if (svc1 && (svc1 != val)) {
def->source.data.udp.connectHost = strndup(val, svc1-val);
- else
- def->source.data.udp.connectHost = strdup(val);
- if (!def->source.data.udp.connectHost)
- goto no_memory;
+ if (!def->source.data.udp.connectHost)
+ goto no_memory;
+ }
if (svc1) {
svc1++;
@@ -5323,14 +5327,14 @@ qemuParseCommandLineChr(const char *val)
if (host2) {
host2++;
- if (svc2)
+ if (svc2 && (svc2 != host2)) {
def->source.data.udp.bindHost = strndup(host2, svc2-host2);
- else
- def->source.data.udp.bindHost = strdup(host2);
- if (!def->source.data.udp.bindHost)
- goto no_memory;
+ if (!def->source.data.udp.bindHost)
+ goto no_memory;
+ }
}
+
if (svc2) {
svc2++;
def->source.data.udp.bindService = strdup(svc2);
diff --git a/tests/qemuxml2argvdata/qemuxml2argv-serial-udp-chardev.args b/tests/qemuxml2argvdata/qemuxml2argv-serial-udp-chardev.args
index 7525110..8c6a6d5 100644
--- a/tests/qemuxml2argvdata/qemuxml2argv-serial-udp-chardev.args
+++ b/tests/qemuxml2argvdata/qemuxml2argv-serial-udp-chardev.args
@@ -2,6 +2,8 @@ LC_ALL=C PATH=/bin HOME=/home/test USER=test LOGNAME=test /usr/bin/qemu -S -M \
pc -m 214 -smp 1 -nographic -nodefconfig -nodefaults -chardev socket,\
id=charmonitor,path=/tmp/test-monitor,server,nowait -mon chardev=charmonitor,\
id=monitor,mode=readline -no-acpi -boot c -hda /dev/HostVG/QEMUGuest1 -chardev \
-udp,id=charserial0,host=127.0.0.1,port=9998,localaddr=127.0.0.1,localport=9999 \
--device isa-serial,chardev=charserial0,id=serial0 -usb -device \
+udp,id=charserial0,port=9998,host=127.0.0.1,localaddr=127.0.0.1,localport=9999 \
+-device isa-serial,chardev=charserial0,id=serial0 \
+-chardev udp,id=charserial1,port=9999 \
+-device isa-serial,chardev=charserial1,id=serial1 -usb -device \
virtio-balloon-pci,id=balloon0,bus=pci.0,addr=0x2
diff --git a/tests/qemuxml2argvdata/qemuxml2argv-serial-udp-chardev.xml b/tests/qemuxml2argvdata/qemuxml2argv-serial-udp-chardev.xml
index 12622d4..9627c67 100644
--- a/tests/qemuxml2argvdata/qemuxml2argv-serial-udp-chardev.xml
+++ b/tests/qemuxml2argvdata/qemuxml2argv-serial-udp-chardev.xml
@@ -25,6 +25,10 @@
<source mode='connect' host='127.0.0.1' service='9998'/>
<target port='0'/>
</serial>
+ <serial type='udp'>
+ <source mode='connect' service='9999'/>
+ <target port='1'/>
+ </serial>
<console type='udp'>
<source mode='bind' host='127.0.0.1' service='9999'/>
<source mode='connect' host='127.0.0.1' service='9998'/>
diff --git a/tests/qemuxml2argvdata/qemuxml2argv-serial-udp.args b/tests/qemuxml2argvdata/qemuxml2argv-serial-udp.args
index 53c69bc..cf25fe0 100644
--- a/tests/qemuxml2argvdata/qemuxml2argv-serial-udp.args
+++ b/tests/qemuxml2argvdata/qemuxml2argv-serial-udp.args
@@ -1,4 +1,4 @@
LC_ALL=C PATH=/bin HOME=/home/test USER=test LOGNAME=test /usr/bin/qemu -S -M \
pc -m 214 -smp 1 -nographic -monitor unix:/tmp/test-monitor,server,nowait \
-no-acpi -boot c -hda /dev/HostVG/QEMUGuest1 -net none -serial \
-udp:127.0.0.1:9998@127.0.0.1:9999 -parallel none -usb
+udp:127.0.0.1:9998@127.0.0.1:9999 -serial udp::9999 -parallel none -usb
diff --git a/tests/qemuxml2argvdata/qemuxml2argv-serial-udp.xml b/tests/qemuxml2argvdata/qemuxml2argv-serial-udp.xml
index 8697f5a..f606ea4 100644
--- a/tests/qemuxml2argvdata/qemuxml2argv-serial-udp.xml
+++ b/tests/qemuxml2argvdata/qemuxml2argv-serial-udp.xml
@@ -25,6 +25,10 @@
<source mode='connect' host='127.0.0.1' service='9998'/>
<target port='0'/>
</serial>
+ <serial type='udp'>
+ <source mode='connect' service='9999'/>
+ <target port='1'/>
+ </serial>
<console type='udp'>
<source mode='bind' host='127.0.0.1' service='9999'/>
<source mode='connect' host='127.0.0.1' service='9998'/>
--
1.7.4
13 years, 3 months
[libvirt] [BUG] Re: [2/6] loadvm: improve tests before bdrv_snapshot_goto()
by Philipp Hahn
Hello,
Am Dienstag 03 August 2010 06:44:26 schrieb Kevin Wolf:
> From: Miguel Di Ciurcio Filho <miguel.filho(a)gmail.com>
>
> This patch improves the resilience of the load_vmstate() function, doing
> further and better ordered tests.
This patch broke restoring not-running VMs using libvirt-0.8.7 with qemu-0.14:
When the domain is not running while taking a snpshot, the sn.vm_state_size
== 0:
2021 } else if (sn.vm_state_size == 0) {
(gdb) print sn
$6 = {id_str = "1", '\0' <repeats 126 times>, name = "pre-update-flash", '\0'
<repeats 239 times>, vm_state_size = 0, date_sec = 1302698007, date_nsec =
711909000,
vm_clock_nsec = 0}
> The [old] process:
...
> - run bdrv_snapshot_goto() on devices
> - if fails, give an warning and goes to the next (not good!)
> - if fails on the VM state device, return zero (not good!)
> - check if the requested snapshot exists on the device that saves the VM
> state and the state is not zero
> - if fails return -error
Previously the qcow2 image was still reverted to the old state, so on the next
start of the domain the qcow2 image would be in the state of the snapshot
> New behavior:
...
> - check if the requested snapshot exists on the device that saves the VM
> state and the state is not zero
> - if fails return -error
...
> - run snapshot_goto() on devices
Now the qcow2 image is not reverted and when the domain is started, it is NOT
in the state of the snapshot.
I can't decide if this regression is an Qemu bug or libvirt should be adapted
to this new behavior.
I found the Bug also reported with Ubuntu and created a Bug in our own German
bugtracker:
<https://bugs.launchpad.net/qemu/+bug/726619>
<https://forge.univention.org/bugzilla/show_bug.cgi?id=22221>
Sincerely
Philipp Hahn
--
Philipp Hahn Open Source Software Engineer hahn(a)univention.de
Univention GmbH Linux for Your Business fon: +49 421 22 232- 0
Mary-Somerville-Str.1 D-28359 Bremen fax: +49 421 22 232-99
http://www.univention.de/
13 years, 3 months
[libvirt] libvirt-0.9.1 to 0.9.3-r1: managedsave/save won't start/restore at saved state
by Nicolas Sebrecht
I'm seeing strange behaviour, here. Any guests saved using both
managedsave and save commands from virsh won't restore at saved state. A
new full boot sequence happen.
- Tested against libvirt v0.9.1, v0.9.2, v0.9.3-r1 (Gentoo)
- Confirmed on three different hosts Gentoo amd64 systems.
- Tested with gentoo and ubuntu guests.
- Nothing relevant in /var/log/libvirt/libvirt.log or
/var/log/libvirt/qemu/<dom>.log
The "state file" /var/lib/libvirt/qemu/save/<dom>.save exists and is
deleted when 'virsh start' is called.
The new boot sequence is confirmed by :
- VNC console checks
- previous screen sessions lost
- uptime
I've open a bug at https://bugs.gentoo.org/show_bug.cgi?id=376333 but
had no answer.
Any idea on what could happen or how to inspect it?
--
Nicolas Sebrecht
13 years, 3 months
[libvirt] Disk snapshot mode proposal: patch for storing the snapshot mode from .vmx to .xml
by computernews@rambler.ru
Hello,
Few days ago I have proposed to implement the snapshot mode
functionality for esx/vpx:
|Mail subject: "[libvirt] VMWare "independent disk" processing needed"
Sent: "04.07.2011"
Sender: "computernews(a)rambler.ru"
|
What I meant is to allow "libvirt" to handle (see full .vmx attached) :
|vmx: scsi0:1.mode = "independent-persistent"
vmx: scsi0:2.mode = "independent-nonpersistent"|
As none has responded I decided to start implementing that myself.
By now I have the managed to implement the .vmx -> .xml part. According
to "General tips for contributing patches"
(http://libvirt.org/hacking.html#patches) I am sending the patch back to
the community as early as it has sense as I still hope to contribute
this feature to the community. It builds and has been functionally
tested. I also tried my best to stick to coding conventions applied on
the project. So I hope my patch will not take long time to analyze for
someone experienced enough.
I saw someone already has started (put few comments about snapshot modes
in src/vmx/vmx.c). So tried to undestand an original idea and keep up
with it. I hope I was not wrong there.
I am willing to keep working in this direction. So if someone would be
so kind to take a look at my efforts and provide a feedback - it would
be very nice and, I hope, useful for the rest of the project.
Attached are:
1. patch itself
2. ".vmx" file I am testing on
3. ".xml" file produced by my changes
Looking forward to hear any feedback/criticism/advices. Thanks in advance.
Best regards
Oleh Paliy
13 years, 3 months
[libvirt] PCI devices passthough to LXC containers using libvirt
by Devendra K. Modium
Hi All
Please let me know if anyone have given access to
PCI devices for a LXC container.
I have tried getting the xml from
"virsh nodedev-dumpxml pci_device" and
added to the libvirt xml file as shown below
<device>
<name>pci_0000_03_00_0</name>
<parent>pci_0000_00_03_0</parent>
<driver>
<name>nvidia</name>
</driver>
<capability type='pci'>
<domain>0</domain>
<bus>3</bus>
<slot>0</slot>
<function>0</function>
<product id='0x06fd' />
<vendor id='0x10de'>nVidia Corporation</vendor>
</capability>
</device>
But it didn't work. I see the logs and it says
couldn't get physical and virtual functions of these devices with error
get_physical_function_linux:323 : Attempting to get SR IOV physical function for device with sysfs path '/sys/devices/pci0000:00/0000:00:00.0'
16:48:34.033: 13802: debug : get_sriov_function:270 : Attempting to resolve device path from device link '/sys/devices/pci0000:00/0000:00:00.0/physfn'
16:48:34.033: 13802: debug : get_sriov_function:274 : SR IOV function link '/sys/devices/pci0000:00/0000:00:00.0/physfn' does not exist
16:48:34.033: 13802: debug : get_virtual_functions_linux:348 : Attempting to get SR IOV virtual functions for devicewith sysfs path '/sys/devices/pci0000:00/0000:00:00.0'
If anyone got some guidelines how to debug, please let me know.
Thanks in advance
Regards
Devendra
13 years, 3 months
[libvirt] virNetClientPtr leak in remote driver
by Matthias Bolte
doRemoteClose doesn't free the virNetClientPtr and this creates a
260kb leak per remote connection. This happens because
virNetClientFree doesn't remove the last ref, because virNetClientNew
creates the virNetClientPtr with a refcount of 2.
static virNetClientPtr virNetClientNew(virNetSocketPtr sock,
const char *hostname)
{
[...]
client->refs = 1;
[...]
/* Set up a callback to listen on the socket data */
client->refs++;
if (virNetSocketAddIOCallback(client->sock,
VIR_EVENT_HANDLE_READABLE,
virNetClientIncomingEvent,
client,
virNetClientEventFree) < 0) {
client->refs--;
VIR_DEBUG("Failed to add event watch, disabling events");
}
[...]
}
virNetClientNew adds a ref before calling virNetSocketAddIOCallback
but only removes it when virNetSocketAddIOCallback fails. This seems
wrong too me and the ref should be removed in the success case too.
The same pattern was added in 0302391ee643ad91fdc6d2ecf7e4cf0fc9724516
(Fix race in ref counting when handling RPC jobs)
--- a/src/rpc/virnetserverclient.c
+++ b/src/rpc/virnetserverclient.c
@@ -763,10 +763,12 @@ readmore:
/* Send off to for normal dispatch to workers */
if (msg) {
+ client->refs++;
if (!client->dispatchFunc ||
client->dispatchFunc(client, msg,
client->dispatchOpaque) < 0) {
virNetMessageFree(msg);
client->wantClose = true;
+ client->refs--;
return;
}
}
Again, this seems wrong and the ref should be removed in the success
case here too. Before I spent time to figure out how the refcounting
is supposed to work here I just report it and hope that Dan can easily
fix this.
--
Matthias Bolte
http://photron.blogspot.com
13 years, 3 months