Re: [Qemu-devel] [PATCH 1/2] hw/pflash_cfi01.c: Make read after byte-write or erase return status
No breakages for Microblaze test cases and series looks good. On Tue, Jan 22, 2013 at 12:08 AM, Peter Maydell peter.mayd...@linaro.org wrote: The Intel flash command set requires that a read operation after doing a 'single byte write' command returns the status register; add this case to pflash_read() so we return the correct information. Similarly, the case for the 0x28 flavour of block erase was missing. Signed-off-by: Peter Maydell peter.mayd...@linaro.org Reviewed-by: Peter Crosthwaite peter.crosthwa...@xilinx.com Tested-by: Peter Crosthwaite peter.crosthwa...@xilinx.com --- hw/pflash_cfi01.c |3 +++ 1 file changed, 3 insertions(+) diff --git a/hw/pflash_cfi01.c b/hw/pflash_cfi01.c index aadedef..310c716 100644 --- a/hw/pflash_cfi01.c +++ b/hw/pflash_cfi01.c @@ -162,7 +162,10 @@ static uint32_t pflash_read (pflash_t *pfl, hwaddr offset, } break; +case 0x10: /* Single byte program */ case 0x20: /* Block erase */ +case 0x28: /* Block erase */ +case 0x40: /* single byte program */ case 0x50: /* Clear status register */ case 0x60: /* Block /un)lock */ case 0x70: /* Status Register */ -- 1.7.9.5
Re: [Qemu-devel] [PATCH 2/2] hw/pflash_cfi01: Treat read in unknown command state as read
On Tue, Jan 22, 2013 at 12:08 AM, Peter Maydell peter.mayd...@linaro.org wrote: The code for handling the default unknown command state case in pflash_read in pflash_cfi01.c comments reset state treat it as a read. However the code doesn't actually do this. Moving the default case to the top of the switch so it can fall through into the read case brings this file into line with pflash_cfi02 and makes the code behave as the comments suggest. The pflash_cfi01 code has always had this bug -- it was presumably introduced when the original author copied the cfi02 code and rearranged the order of the switch statement without noticing that the default case relied on the fall-through. Signed-off-by: Peter Maydell peter.mayd...@linaro.org Reviewed-by: Peter Crosthwaite peter.crosthwa...@xilinx.com Tested-by: Peter Crosthwaite peter.crosthwa...@xilinx.com --- hw/pflash_cfi01.c | 11 ++- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/hw/pflash_cfi01.c b/hw/pflash_cfi01.c index 310c716..b30cac6 100644 --- a/hw/pflash_cfi01.c +++ b/hw/pflash_cfi01.c @@ -122,6 +122,12 @@ static uint32_t pflash_read (pflash_t *pfl, hwaddr offset, __func__, offset, pfl-cmd, width); #endif switch (pfl-cmd) { +default: +/* This should never happen : reset state treat it as a read */ +DPRINTF(%s: unknown command state: %x\n, __func__, pfl-cmd); +pfl-wcycle = 0; +pfl-cmd = 0; +/* fall through to read code */ case 0x00: /* Flash area read */ p = pfl-storage; @@ -197,11 +203,6 @@ static uint32_t pflash_read (pflash_t *pfl, hwaddr offset, else ret = pfl-cfi_table[boff]; break; -default: -/* This should never happen : reset state treat it as a read */ -DPRINTF(%s: unknown command state: %x\n, __func__, pfl-cmd); -pfl-wcycle = 0; -pfl-cmd = 0; } return ret; } -- 1.7.9.5
Re: [Qemu-devel] [PATCH 32/41] qemu-file: add writable socket QEMUFile
On 02/15/2013 07:47 PM, Paolo Bonzini wrote: Signed-off-by: Paolo Bonzini pbonz...@redhat.com --- include/migration/qemu-file.h |2 +- migration-tcp.c |2 +- migration-unix.c |2 +- savevm.c | 33 +++-- util/osdep.c |6 +- 5 files changed, 39 insertions(+), 6 deletions(-) diff --git a/include/migration/qemu-file.h b/include/migration/qemu-file.h index 987e719..25e8461 100644 --- a/include/migration/qemu-file.h +++ b/include/migration/qemu-file.h @@ -76,7 +76,7 @@ typedef struct QEMUFileOps { QEMUFile *qemu_fopen_ops(void *opaque, const QEMUFileOps *ops); QEMUFile *qemu_fopen(const char *filename, const char *mode); QEMUFile *qemu_fdopen(int fd, const char *mode); -QEMUFile *qemu_fopen_socket(int fd); +QEMUFile *qemu_fopen_socket(int fd, const char *mode); QEMUFile *qemu_popen_cmd(const char *command, const char *mode); int qemu_get_fd(QEMUFile *f); int qemu_fclose(QEMUFile *f); diff --git a/migration-tcp.c b/migration-tcp.c index e78a296..7d975b5 100644 --- a/migration-tcp.c +++ b/migration-tcp.c @@ -95,7 +95,7 @@ static void tcp_accept_incoming_migration(void *opaque) goto out; } -f = qemu_fopen_socket(c); +f = qemu_fopen_socket(c, rb); if (f == NULL) { fprintf(stderr, could not qemu_fopen socket\n); goto out; diff --git a/migration-unix.c b/migration-unix.c index 218835a..4693b43 100644 --- a/migration-unix.c +++ b/migration-unix.c @@ -95,7 +95,7 @@ static void unix_accept_incoming_migration(void *opaque) goto out; } -f = qemu_fopen_socket(c); +f = qemu_fopen_socket(c, rb); if (f == NULL) { fprintf(stderr, could not qemu_fopen socket\n); goto out; diff --git a/savevm.c b/savevm.c index f593acd..b6cf415 100644 --- a/savevm.c +++ b/savevm.c @@ -198,6 +198,18 @@ static int socket_get_buffer(void *opaque, uint8_t *buf, int64_t pos, int size) return len; } +static int socket_put_buffer(void *opaque, const uint8_t *buf, int64_t pos, int size) +{ +QEMUFileSocket *s = opaque; +ssize_t len; + +len = qemu_send_full(s-fd, buf, size, 0); +if (len == -1) { +len = -socket_error(); +} We won't always detect partial buffer write here Why not check len size? this way you won't need to change qemu_send_full +return len; +} + static int socket_close(void *opaque) { QEMUFileSocket *s = opaque; @@ -369,12 +381,29 @@ static const QEMUFileOps socket_read_ops = { .close = socket_close }; -QEMUFile *qemu_fopen_socket(int fd) +static const QEMUFileOps socket_write_ops = { +.get_fd = socket_get_fd, +.put_buffer = socket_put_buffer, +.close = socket_close +}; + +QEMUFile *qemu_fopen_socket(int fd, const char *mode) { QEMUFileSocket *s = g_malloc0(sizeof(QEMUFileSocket)); +if (mode == NULL || + (mode[0] != 'r' mode[0] != 'w') || + mode[1] != 'b' || mode[2] != 0) { +fprintf(stderr, qemu_fopen: Argument validity check failed\n); +return NULL; +} + s-fd = fd; -s-file = qemu_fopen_ops(s, socket_read_ops); +if (mode[0] == 'w') { +s-file = qemu_fopen_ops(s, socket_write_ops); +} else { +s-file = qemu_fopen_ops(s, socket_read_ops); +} return s-file; } diff --git a/util/osdep.c b/util/osdep.c index 5b51a03..be168e5 100644 --- a/util/osdep.c +++ b/util/osdep.c @@ -243,8 +243,12 @@ ssize_t qemu_write_full(int fd, const void *buf, size_t count) while (count) { ret = write(fd, buf, count); if (ret 0) { -if (errno == EINTR) +if (errno == EINTR) { continue; +} +if (total == 0) { +total = ret; +} I don't like it, first it only detect the first write failure (if the error happens when total !=0 the function won't return -1). Secondly this behavior is different from the function documentation. Regards, Orit break; }
Re: [Qemu-devel] [PATCH v2 2/2] qom/object.c: Allow itf cast with num_itfs = 0
Hi Paolo, On Tue, Feb 19, 2013 at 7:07 PM, Paolo Bonzini pbonz...@redhat.com wrote: Il 19/02/2013 05:02, Peter Crosthwaite ha scritto: num_interfaces only tells you how many interfaces the concrete child class has (as defined in the TypeInfo). This means if you have a child class which defines no interfaces of its own, but its parent has interfaces you cannot cast to those parent interfaces. Fixed changing the guard to check the class-interfaces list instead (which is a complete flattened list of implemented interfaces). Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com --- changed from v1: Change guard implementation rather than removed it (Paolo review) qom/object.c |3 ++- 1 files changed, 2 insertions(+), 1 deletions(-) diff --git a/qom/object.c b/qom/object.c index 4b72a64..3d638ff 100644 --- a/qom/object.c +++ b/qom/object.c @@ -449,7 +449,8 @@ ObjectClass *object_class_dynamic_cast(ObjectClass *class, TypeImpl *type = class-type; ObjectClass *ret = NULL; -if (type-num_interfaces type_is_ancestor(target_type, type_interface)) { +if (type-class-interfaces +type_is_ancestor(target_type, type_interface)) { int found = 0; GSList *i; Series looks good, thanks! Can I take that as an RB or acked-by? :-) Regards, Peter Paolo
Re: [Qemu-devel] [RESEND PATCH v2 0/2] seabios q35: Fix seabios IRQ mapping and setup
On 02/15/13 22:11, Alex Williamson wrote: This enables interrupts to work pre-boot for assigned devices. I had self nak'd and resent a v2 patch for 2/2, but there were never any comments, so resending the whole series as v2. Thanks, btw: With all the reorg going on in master atm I think it would be good to open a 1.7.2.x bugfix branch so we can make a bugfix release for qemu 1.4.1. These two patches are hot candidates to be cherry-picked into the bugfix branch IMHO. cheers, Gerd
Re: [Qemu-devel] Block I/O optimizations
On Mon, Feb 18, 2013 at 7:19 PM, Loic Dachary l...@dachary.org wrote: I recently tried to figure out the best and easiest ways to increase block I/O performances with qemu. Not being a qemu expert, I expected to find a few optimization tricks. Much to my surprise, it appears that there are many significant improvements being worked on. This is excellent news :-) However, I'm not sure I understand how they all fit together. It's probably quite obvious from the developer point of view but I would very much appreciate an overview of how dataplane, vhost-blk, ELVIS etc. should be used or developed to maximize I/O performances. Are there documents I should read ? If not, would someone be willing to share bits of wisdom ? Hi Loic, There will be more information on dataplane shortly. I'll write up a blog post and share the link with you. Stefan
Re: [Qemu-devel] [PATCH 33/41] qemu-file: simplify and export qemu_ftell
On 02/15/2013 07:47 PM, Paolo Bonzini wrote: Force a flush when qemu_ftell is called. This simplifies the buffer magic (it also breaks qemu_ftell for input QEMUFiles, but we never use it). Signed-off-by: Paolo Bonzini pbonz...@redhat.com --- savevm.c | 20 1 files changed, 8 insertions(+), 12 deletions(-) diff --git a/savevm.c b/savevm.c index b6cf415..e4dc01d 100644 --- a/savevm.c +++ b/savevm.c @@ -119,8 +119,8 @@ struct QEMUFile { void *opaque; int is_write; -int64_t buf_offset; /* start of buffer when writing, end of buffer - when reading */ +int64_t pos; /* start of buffer when writing, end of buffer +when reading */ int buf_index; int buf_size; /* 0 when writing */ uint8_t buf[IO_BUF_SIZE]; @@ -505,9 +505,9 @@ static void qemu_fflush(QEMUFile *f) return; } if (f-is_write f-buf_index 0) { -ret = f-ops-put_buffer(f-opaque, f-buf, f-buf_offset, f-buf_index); +ret = f-ops-put_buffer(f-opaque, f-buf, f-pos, f-buf_index); if (ret = 0) { -f-buf_offset += f-buf_index; +f-pos += f-buf_index; } f-buf_index = 0; } @@ -534,11 +534,11 @@ static void qemu_fill_buffer(QEMUFile *f) f-buf_index = 0; f-buf_size = pending; -len = f-ops-get_buffer(f-opaque, f-buf + pending, f-buf_offset, +len = f-ops-get_buffer(f-opaque, f-buf + pending, f-pos, IO_BUF_SIZE - pending); if (len 0) { f-buf_size += len; -f-buf_offset += len; +f-pos += len; } else if (len == 0) { qemu_file_set_error(f, -EIO); } else if (len != -EAGAIN) @@ -718,12 +718,8 @@ int qemu_get_byte(QEMUFile *f) int64_t qemu_ftell(QEMUFile *f) { -/* buf_offset excludes buffer for writing but includes it for reading */ -if (f-is_write) { -return f-buf_offset + f-buf_index; -} else { -return f-buf_offset - f-buf_size + f-buf_index; -} +qemu_fflush(f); +return f-pos; } int qemu_file_rate_limit(QEMUFile *f) Reviewed-by: Orit Wasserman owass...@redhat.com
Re: [Qemu-devel] [PATCH 1/2] win32: do not set CPU affinity
2013/2/21 Roy Tam roy...@gmail.com: 2013/2/21 Paolo Bonzini pbonz...@redhat.com: Il 21/02/2013 01:35, Roy Tam ha scritto: QEMU system emulation has been thread-safe for a long time, and setting the CPU affinity is hurting performance badly. Remove the bogus code. Jacob Kroon reports that the time to boot his VxWorks image goes from 3 minutes passed and I still haven't made it that far to ~140s. Yes it does work better for fdostest.img, but when I tried to boot ttylinux-i686-14.0.iso, qemu freezes after showing loading vmlinuz ... Did it work without the patch? Yes, at least linux kernel starts but stalls when hitting IO-APIC thingy, with noapic boot switch it stalls after detecting ttyS0 With patch, QEMU is unresponsive when loading vmlinuz (not even showing Decompressing Linux message) Clarify that it boots fine sometimes, but when QEMU freezes, there is a thread busy-waiting(seems so): http://i.imgur.com/LUJjd8r.png Paolo
Re: [Qemu-devel] [Bug 1130533] Re: Documentation cannot be build since commit c70a01e449536c616c85ab820c6fbad7d7e9cf39
FredBezies fredbez...@gmail.com writes: Could be also a bug related to texinfo 5.0 upgrade, indeed ! Anyway, besides removing this patch, which are the options ? Wait for Cole's fix to be committed, or apply it locally, or downgrade texinfo.
Re: [Qemu-devel] [PATCH v4 4/6] introduce new vma archive format
+This format contains a header which includes the VM configuration as +binary blobs, and a list of devices (dev_id, name). Is there a magic number, for quickly identifying whether a file is likely to be a vma? Yes ('VMA') What endianness are multi-byte numbers interpreted with? BE Does the overall header file leave ample room for adding later extensions in a manner that is reliably detected as an unsupported feature in older tools? yes +The actual VM image data is stored inside extents. An extent contains +up to 64 clusters, and start with a 512 byte header containing +additional information for those clusters. Doesn't this create alignment slowdowns on modern disks that prefer 4k alignment? No, because it is meant to be read sequentially. Direct access to specific blocks is not needed. Wouldn't it be better to have the header be 4096 bytes, so that each of the 64 clusters in an extent is also 4096-aligned? If you _do_ go with a 4096 header per extent, then it might be better to go with 16 bytes per cluster and 256 clusters per extent, instead of 8 bytes per cluster and 512 clusters per extent. That would increase extend size to 16MB, and would increase memory footprint because we need to have at least 2 extends in RAM. But again, there is no need to align to 4096 bytes. +We use a cluster size of 65536, and use 8 bytes for each cluster in +the header to store the following information: + +* 1 byte dev_id (to identity the drive) +* 2 bytes zero indicator (mark zero regions (16x4096)) +* 4 bytes cluster number Is that sufficient, or are we artificially limiting the maximum size of a disk image that can be stored to 64k*4G = 128T? Again, going with 16-bytes per cluster instead of 8 bytes per cluster, to get up to a 4096-byte header alignment so that all clusters fall on nice alignment boundaries, would leave you room to supply a 64-bit offset instead of a 32-bit cluster number. Don't know if that would be helpful or not, but food for thought. Honestly, 64k*4G = 128T is not a limit for me. And we still have one byte reserved, so we can have up to 1P per image, and up to 253 images. For now I have no plans to backup such large VMs. +* 1 byte not used (reserved) Can these be rearranged to 'dev_id, reserved, zero indicator, cluster number' to achieve natural alignment when reading the cluster number? It is already ordered that way in the code. I will fix the order in the text. +We only store non-zero blocks (such block is 4096 bytes). So if I understand correctly, your current layout is divided into extents of up to 4194816 bytes each (512 header, then 4M divided into 64 clusters of 64k each). Then, if the zero indicator is all 0, then the corresponding cluster will be 64k bytes on the wire; if it is 0x0001, then the first 4096 bytes of the corresponding cluster will be all zeros, and the cluster itself will occupy only 60k of the vma file? yes +Each archive is marked with a uuid. The archive header and all extent +headers includes that uuid and a MD5 checksum (over header data). Layout of this header? see vma.h Hint - look at how the qcow2 file format is specified. You need a lot more details - enough that someone could independently implement a program to read and create vma images that would be compatible with what your implementation produces. The format is really simple, you have the definitions in the header file, and a reference implementation. I am quite sure any experienced developer can write an implementation in a few hours. We do not talk about an extremely complex format like 'qcow2' here. +++ b/vma-reader.c @@ -0,0 +1,799 @@ +/* + * VMA: Virtual Machine Archive + * + * Copyright (C) 2012 Proxmox Server Solutions It's 2013. + +#define BITS_PER_LONG (sizeof(unsigned long) * 8) 8 is a magic number; you should be using CHAR_BIT from limits.h instead. Ok, will change that.
Re: [Qemu-devel] [PATCH 30/41] qemu-file: fsync a writable stdio QEMUFile
On 02/15/2013 07:47 PM, Paolo Bonzini wrote: This is what fd_close does. Prepare for switching to a QEMUFile. Signed-off-by: Paolo Bonzini pbonz...@redhat.com --- savevm.c | 18 ++ 1 files changed, 18 insertions(+), 0 deletions(-) diff --git a/savevm.c b/savevm.c index d7c2559..261d17a 100644 --- a/savevm.c +++ b/savevm.c @@ -256,6 +256,24 @@ static int stdio_fclose(void *opaque) { QEMUFileStdio *s = opaque; int ret = 0; + +if (s-file-ops-put_buffer) { +int fd = fileno(s-stdio_file); +struct stat st; + +ret = fstat(fd, st); +if (ret == 0 S_ISREG(st.st_mode)) { +/* + * If the file handle is a regular file make sure the + * data is flushed to disk before signaling success. + */ +ret = fsync(fd); +if (ret != 0) { +ret = -errno; +return ret; +} +} +} if (fclose(s-stdio_file) == EOF) { ret = -errno; } Reviewed-by: Orit Wasserman owass...@redhat.com
Re: [Qemu-devel] [PATCH] doc: document -netdev hubport
On Wed, Feb 20, 2013 at 05:21:24PM +0100, Laszlo Ersek wrote: On 02/20/13 11:03, Stefan Hajnoczi wrote: Signed-off-by: Stefan Hajnoczi stefa...@redhat.com --- qemu-options.hx | 11 ++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/qemu-options.hx b/qemu-options.hx index 4bc9c85..c77c43e 100644 --- a/qemu-options.hx +++ b/qemu-options.hx @@ -1404,7 +1404,8 @@ DEF(netdev, HAS_ARG, QEMU_OPTION_netdev, #ifdef CONFIG_VDE vde| #endif -socket],id=str[,option][,option][,...]\n, QEMU_ARCH_ALL) +socket| +hubport],id=str[,option][,option][,...]\n, QEMU_ARCH_ALL) STEXI @item -net nic[,vlan=@var{n}][,macaddr=@var{mac}][,model=@var{type}] [,name=@var{name}][,addr=@var{addr}][,vectors=@var{v}] @findex -net @@ -1726,6 +1727,14 @@ vde_switch -F -sock /tmp/myswitch qemu-system-i386 linux.img -net nic -net vde,sock=/tmp/myswitch @end example +@item -netdev hubport,id=@var{id},hubid=@var{hubid} + +Create a hub port on QEMU vlan @var{hubid}. This syntax is an alterative to Typo: - alterative - alternative +the -net @option{vlan} argument and can be used to connect a NIC specified with +-device to a QEMU vlan. Can we say [...] with -device netdev=@var{id} to a QEMU vlan or is the netdev= optarg obvious? (It's just the generic dev - netdev reference.) Good points, thanks. I'll send a v2. Stefan
[Qemu-devel] [PATCH v2] doc: document -netdev hubport
Signed-off-by: Stefan Hajnoczi stefa...@redhat.com --- qemu-options.hx | 11 ++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/qemu-options.hx b/qemu-options.hx index 4bc9c85..cd18ad1 100644 --- a/qemu-options.hx +++ b/qemu-options.hx @@ -1404,7 +1404,8 @@ DEF(netdev, HAS_ARG, QEMU_OPTION_netdev, #ifdef CONFIG_VDE vde| #endif -socket],id=str[,option][,option][,...]\n, QEMU_ARCH_ALL) +socket| +hubport],id=str[,option][,option][,...]\n, QEMU_ARCH_ALL) STEXI @item -net nic[,vlan=@var{n}][,macaddr=@var{mac}][,model=@var{type}] [,name=@var{name}][,addr=@var{addr}][,vectors=@var{v}] @findex -net @@ -1726,6 +1727,14 @@ vde_switch -F -sock /tmp/myswitch qemu-system-i386 linux.img -net nic -net vde,sock=/tmp/myswitch @end example +@item -netdev hubport,id=@var{id},hubid=@var{hubid} + +Create a hub port on QEMU vlan @var{hubid}. This syntax is an alternative to +the @code{-net @option{vlan}} argument and can be used to connect a NIC +specified with @code{-device ...,netdev=@var{id}} to a QEMU vlan. + +Note that only NICs can be connected to a hubport, other -netdevs cannot. + @item -net dump[,vlan=@var{n}][,file=@var{file}][,len=@var{len}] Dump network traffic on VLAN @var{n} to file @var{file} (@file{qemu-vlan0.pcap} by default). At most @var{len} bytes (64k by default) per packet are stored. The file format is -- 1.8.1.2
Re: [Qemu-devel] [edk2] [RFC PATCH] Distinguish between reset types
Il 21/02/2013 02:10, Laszlo Ersek ha scritto: OTOH if the keyboard reset gets soft in qemu, then OVMF's hard reset (the above code) will break. Maybe I could cycle between 0xCF9 and 0x64 in ResetCold(), starting with 0xCF9. Yes, that's the right thing to do. Also, in QEMU you're doing: if (val 4) { qemu_system_reset_request(); return; } d-rcr = val 2; /* keep System Reset type only */ It looks like d-rcr should be set first to match what hardware does (writing 0x6 causes a cold reset, and that's what you usually find in the ACPI tables). Paolo
Re: [Qemu-devel] [PATCH 7/9] gtk: add translation support (v5)
On Wed, Feb 20, 2013 at 06:26:55PM +0100, Andreas Färber wrote: Am 20.02.2013 18:05, schrieb Anthony Liguori: Andreas Färber afaer...@suse.de writes: Am 20.02.2013 14:43, schrieb Anthony Liguori: This includes a de_DE translation from Kevin Wolf and an it translation from Paolo Bonzini. Cc: Paolo Bonzini pbonz...@redhat.com Cc: Kevin Wolf kw...@redhat.com Cc: Stefan Hajnoczi stefa...@redhat.com Signed-off-by: Anthony Liguori aligu...@us.ibm.com --- v1 - v4 - Don't use '|| exit 1' with sub-invocation of make - Actually include Kevin's translation v4 - v5 - Update translations (Kevin and Paolo) - Fix 'make update' for it.po --- Makefile | 3 +++ configure | 4 +++- po/Makefile| 46 ++ po/de_DE.po| 45 + po/it.po | 45 + po/messages.po | 45 + ui/gtk.c | 22 +++--- 7 files changed, 202 insertions(+), 8 deletions(-) create mode 100644 po/Makefile create mode 100644 po/de_DE.po create mode 100644 po/it.po create mode 100644 po/messages.po IIUC this uses the English texts as key for lookup of translations. Experience shows that while that is most convenient for the English it leads to grammatical mistakes in other languages due to text reuse in wrong contexts. A prominent example is Server being translated as Kellner (which is waiter) in some early Windows NT version. :) More recent examples commonly found are ambiguities of, e.g., Update as noun vs. imperative - happens if the same wording is used in a menu and in some options dialog or status text. Similar for ing-forms translated as noun vs. infinitive vs. first-person present. Right or wrong, this is how GTK apps are written. If you disagree with it, take it up with the Gnome folks. Consistency trumps rightness here. You don't translate error_setg() et al., so translating a few UI items is in fact inconsistent here. I think the plan with error messages was to have them translated eventually, which is one of the reasons why clients may not parse them (and strerror() results are already translated today). But since we're using some standard GTK menu entries, not translating would actually give you the much bigger inconsistency: In the same menu, you would have both English and translated entries. This is what the first version of this patch series had, and which I really hated. As long as there is a logical separation between translated and untranslated strings (e.g. menus are translated, the monitor is English) I don't see a problem with it. A more critical issue would be distro packaging though. An alternative idea would be to separate the _L() text from the English text if that is possible through some macro, cmp. reply to Daniel. You want qemu to be usable with LANG=C, so using identifiers instead of English texts doesn't really work. The gettext functions that allow specifying a context look like a better solution to solve the problem if it ever comes up. Kevin
Re: [Qemu-devel] [PATCH v3 2/6] add basic backup support to block driver
This should call bdrv_is_allocated_above like the other block jobs do. It would be needed later anyway to backup only the topmost image. I do not need that information now, so why do you want that I add dead code? I think you do. You're wasting time reading unallocated clusters and checking that they are zero. bdrv_is_allocated_above gives you the same information much more efficiently. I thought that just returns information if the data is allocated, or if data is on backing file? Or is data guaranteed to be zero if bdrv_is_allocated_above() return 0? Do VMA files have to store all the blocks of the source file? I only use it for full backups currently. If you want incremental backups, you need to store information about the base image, and this is not the scope of this patch. IMHO incremental backup which references to other images are a mess. They are difficult to generate and difficult to maintain. I would prefer to use some kind of Content Addressable Storage, using hashes. That way you have advantages of full backups and incremental backups (deduplication). Having the additional advantage that we can easily rsync that data to another site.
Re: [Qemu-devel] [PATCH V2] tap: forbid creating multiqueue tap when hub is used
On Thu, Feb 21, 2013 at 11:05:56AM +0800, Jason Wang wrote: Obviously, hub does not support multiqueue tap. So this patch forbids creating multiple queue tap when hub is used to prevent the crash when command line such as -net tap,queues=2 is used. Cc: qemu-sta...@nongnu.org Signed-off-by: Jason Wang jasow...@redhat.com --- Changes from V1: - Add a comment to explain the reason. (Stefan) - Use a more specific message. (Stefan) --- net/tap.c |7 +++ 1 files changed, 7 insertions(+), 0 deletions(-) Thanks, applied to my net tree: https://github.com/stefanha/qemu/commits/net Stefan
Re: [Qemu-devel] [PATCH 2/5] blockdev: add discard suboption to -drive
On Wed, Feb 20, 2013 at 03:09:51PM +0100, Paolo Bonzini wrote: Il 13/02/2013 11:39, Stefan Hajnoczi ha scritto: .type = QEMU_OPT_STRING, .help = disk image, },{ +.name = discard, +.type = QEMU_OPT_STRING, +.help = discard operation (ignore/off, unmap/on), off/on aliases will be confusing when we plan to add anchor in the future, making this non-boolean. Please support ignore/unmap only. My problem here is that unmap will not be the default but at the same time it will be what people want to use. Hence, it is important to have an easy to remember and discover option; discard=on is immediately understandable, while discard=unmap is not. I understand. The risk is that we end up confusing users rather than helping, because the actual ignore/anchor/unmap modes need to be understood to use this feature properly. If you and Kevin like the off/on alias, go ahead. It's not critical. Stefan
Re: [Qemu-devel] Online resize of virtio-blk device does not emit udev event
On Wed, Feb 20, 2013 at 09:34:45PM +0100, Milos Vyletel wrote: It looks like none of the block drivers handle this. drivers/md/dm*.c is a block driver and you showed that LVM (device-mapper) does raise a uevent when the device is resized. That would be the place to look. Stefan
Re: [Qemu-devel] [PATCH 34/41] migration: use QEMUFile for migration channel lifetime
On 02/15/2013 07:47 PM, Paolo Bonzini wrote: As a start, use QEMUFile to store the destination and close it. qemu_get_fd gets a file descriptor that will be used by the write callbacks. Signed-off-by: Paolo Bonzini pbonz...@redhat.com --- include/migration/migration.h |7 --- migration-exec.c | 21 ++--- migration-fd.c| 35 +++ migration-tcp.c | 19 +++ migration-unix.c | 19 +++ migration.c |8 +--- savevm.c |1 + 7 files changed, 21 insertions(+), 89 deletions(-) diff --git a/include/migration/migration.h b/include/migration/migration.h index 172ef95..cf3e81c 100644 --- a/include/migration/migration.h +++ b/include/migration/migration.h @@ -38,12 +38,13 @@ struct MigrationState QEMUBH *cleanup_bh; QEMUFile *file; +QEMUFile *migration_file; + int fd; -int state; int (*get_error)(MigrationState *s); -int (*close)(MigrationState *s); int (*write)(MigrationState *s, const void *buff, size_t size); -void *opaque; + +int state; MigrationParams params; int64_t total_time; int64_t downtime; diff --git a/migration-exec.c b/migration-exec.c index a2b5f8d..8c3f720 100644 --- a/migration-exec.c +++ b/migration-exec.c @@ -43,33 +43,16 @@ static int file_write(MigrationState *s, const void * buf, size_t size) return write(s-fd, buf, size); } -static int exec_close(MigrationState *s) -{ -int ret = 0; -DPRINTF(exec_close\n); -ret = qemu_fclose(s-opaque); -s-opaque = NULL; -s-fd = -1; -return ret; -} - void exec_start_outgoing_migration(MigrationState *s, const char *command, Error **errp) { -QEMUFile *f; -f = qemu_popen_cmd(command, w); -if (f == NULL) { +s-migration_file = qemu_popen_cmd(command, w); +if (s-migration_file == NULL) { error_setg_errno(errp, errno, failed to popen the migration target); return; } -s-opaque = f; -s-fd = qemu_get_fd(f); -assert(s-fd != -1); - -s-close = exec_close; s-get_error = file_errno; s-write = file_write; - migrate_fd_connect(s); } diff --git a/migration-fd.c b/migration-fd.c index a99e0e3..4636457 100644 --- a/migration-fd.c +++ b/migration-fd.c @@ -40,45 +40,16 @@ static int fd_write(MigrationState *s, const void * buf, size_t size) return write(s-fd, buf, size); } -static int fd_close(MigrationState *s) -{ -struct stat st; -int ret; - -DPRINTF(fd_close\n); -ret = fstat(s-fd, st); -if (ret == 0 S_ISREG(st.st_mode)) { -/* - * If the file handle is a regular file make sure the - * data is flushed to disk before signaling success. - */ -ret = fsync(s-fd); -if (ret != 0) { -ret = -errno; -perror(migration-fd: fsync); -return ret; -} -} -ret = close(s-fd); -s-fd = -1; -if (ret != 0) { -ret = -errno; -perror(migration-fd: close); -} -return ret; -} - void fd_start_outgoing_migration(MigrationState *s, const char *fdname, Error **errp) { -s-fd = monitor_get_fd(cur_mon, fdname, errp); -if (s-fd == -1) { +int fd = monitor_get_fd(cur_mon, fdname, errp); +if (fd == -1) { return; } +s-migration_file = qemu_fdopen(fd, wb); s-get_error = fd_errno; s-write = fd_write; -s-close = fd_close; - migrate_fd_connect(s); } diff --git a/migration-tcp.c b/migration-tcp.c index 7d975b5..1e8e004 100644 --- a/migration-tcp.c +++ b/migration-tcp.c @@ -39,28 +39,17 @@ static int socket_write(MigrationState *s, const void * buf, size_t size) return send(s-fd, buf, size, 0); } -static int tcp_close(MigrationState *s) -{ -int r = 0; -DPRINTF(tcp_close\n); -if (closesocket(s-fd) 0) { -r = -socket_error(); -} -return r; -} - static void tcp_wait_for_connect(int fd, void *opaque) { MigrationState *s = opaque; if (fd 0) { DPRINTF(migrate connect error\n); -s-fd = -1; +s-migration_file = NULL; migrate_fd_error(s); } else { DPRINTF(migrate connect success\n); -s-fd = fd; -socket_set_block(s-fd); +s-migration_file = qemu_fopen_socket(fd, wb); migrate_fd_connect(s); } } @@ -69,9 +58,7 @@ void tcp_start_outgoing_migration(MigrationState *s, const char *host_port, Erro { s-get_error = socket_errno; s-write = socket_write; -s-close = tcp_close; - -s-fd = inet_nonblocking_connect(host_port, tcp_wait_for_connect, s, errp); +inet_nonblocking_connect(host_port, tcp_wait_for_connect, s, errp);
Re: [Qemu-devel] [PATCH v3 2/6] add basic backup support to block driver
This should call bdrv_is_allocated_above like the other block jobs do. It would be needed later anyway to backup only the topmost image. I do not need that information now, so why do you want that I add dead code? I think you do. You're wasting time reading unallocated clusters and checking that they are zero. bdrv_is_allocated_above gives you the same information much more efficiently. I thought that just returns information if the data is allocated, or if data is on backing file? Or is data guaranteed to be zero if bdrv_is_allocated_above() return 0? Oh, I need to pass NULL for base to get that information?
Re: [Qemu-devel] [PATCH 35/41] migration: use QEMUFile for writing outgoing migration data
On 02/15/2013 07:47 PM, Paolo Bonzini wrote: Second, drop the file descriptor indirection, and write directly to the QEMUFile. Signed-off-by: Paolo Bonzini pbonz...@redhat.com --- include/migration/migration.h |4 --- migration-exec.c | 12 --- migration-fd.c| 12 --- migration-tcp.c | 12 --- migration-unix.c | 12 --- migration.c | 44 +--- 6 files changed, 6 insertions(+), 90 deletions(-) diff --git a/include/migration/migration.h b/include/migration/migration.h index cf3e81c..bde13c2 100644 --- a/include/migration/migration.h +++ b/include/migration/migration.h @@ -40,10 +40,6 @@ struct MigrationState QEMUFile *file; QEMUFile *migration_file; -int fd; -int (*get_error)(MigrationState *s); -int (*write)(MigrationState *s, const void *buff, size_t size); - int state; MigrationParams params; int64_t total_time; diff --git a/migration-exec.c b/migration-exec.c index 8c3f720..1c539de 100644 --- a/migration-exec.c +++ b/migration-exec.c @@ -33,16 +33,6 @@ do { } while (0) #endif -static int file_errno(MigrationState *s) -{ -return errno; -} - -static int file_write(MigrationState *s, const void * buf, size_t size) -{ -return write(s-fd, buf, size); -} - void exec_start_outgoing_migration(MigrationState *s, const char *command, Error **errp) { s-migration_file = qemu_popen_cmd(command, w); @@ -51,8 +41,6 @@ void exec_start_outgoing_migration(MigrationState *s, const char *command, Error return; } -s-get_error = file_errno; -s-write = file_write; migrate_fd_connect(s); } diff --git a/migration-fd.c b/migration-fd.c index 4636457..07c758a 100644 --- a/migration-fd.c +++ b/migration-fd.c @@ -30,16 +30,6 @@ do { } while (0) #endif -static int fd_errno(MigrationState *s) -{ -return errno; -} - -static int fd_write(MigrationState *s, const void * buf, size_t size) -{ -return write(s-fd, buf, size); -} - void fd_start_outgoing_migration(MigrationState *s, const char *fdname, Error **errp) { int fd = monitor_get_fd(cur_mon, fdname, errp); @@ -48,8 +38,6 @@ void fd_start_outgoing_migration(MigrationState *s, const char *fdname, Error ** } s-migration_file = qemu_fdopen(fd, wb); -s-get_error = fd_errno; -s-write = fd_write; migrate_fd_connect(s); } diff --git a/migration-tcp.c b/migration-tcp.c index 1e8e004..5ea4f3d 100644 --- a/migration-tcp.c +++ b/migration-tcp.c @@ -29,16 +29,6 @@ do { } while (0) #endif -static int socket_errno(MigrationState *s) -{ -return socket_error(); -} - -static int socket_write(MigrationState *s, const void * buf, size_t size) -{ -return send(s-fd, buf, size, 0); -} - static void tcp_wait_for_connect(int fd, void *opaque) { MigrationState *s = opaque; @@ -56,8 +46,6 @@ static void tcp_wait_for_connect(int fd, void *opaque) void tcp_start_outgoing_migration(MigrationState *s, const char *host_port, Error **errp) { -s-get_error = socket_errno; -s-write = socket_write; inet_nonblocking_connect(host_port, tcp_wait_for_connect, s, errp); } diff --git a/migration-unix.c b/migration-unix.c index 11917f4..64bfa31 100644 --- a/migration-unix.c +++ b/migration-unix.c @@ -29,16 +29,6 @@ do { } while (0) #endif -static int unix_errno(MigrationState *s) -{ -return errno; -} - -static int unix_write(MigrationState *s, const void * buf, size_t size) -{ -return write(s-fd, buf, size); -} - static void unix_wait_for_connect(int fd, void *opaque) { MigrationState *s = opaque; @@ -56,8 +46,6 @@ static void unix_wait_for_connect(int fd, void *opaque) void unix_start_outgoing_migration(MigrationState *s, const char *path, Error **errp) { -s-get_error = unix_errno; -s-write = unix_write; unix_nonblocking_connect(path, unix_wait_for_connect, s, errp); } diff --git a/migration.c b/migration.c index 9cffdd4..68d47cd 100644 --- a/migration.c +++ b/migration.c @@ -291,25 +291,6 @@ void migrate_fd_error(MigrationState *s) notifier_list_notify(migration_state_notifiers, s); } -static ssize_t migrate_fd_put_buffer(MigrationState *s, const void *data, - size_t size) -{ -ssize_t ret; - -if (s-state != MIG_STATE_ACTIVE) { -return -EIO; -} - -do { -ret = s-write(s, data, size); -} while (ret == -1 ((s-get_error(s)) == EINTR)); - -if (ret == -1) -ret = -(s-get_error(s)); - -return ret; -} - static void migrate_fd_cancel(MigrationState *s) { DPRINTF(cancelling migration\n); @@ -323,7 +304,6 @@ int migrate_fd_close(MigrationState *s) if
[Qemu-devel] Build failure with -werror on i386
Configuring QEMU as ./configure --target-list=i386-softmmu --cpu=i386 --enable-werror results in following error cc1: warnings being treated as errors qemu-char.c: In function 'qmp_ringbuf_write': qemu-char.c:2764: error: passing argument 2 of 'g_base64_decode' from incompatible pointer type /usr/include/glib-2.0/glib/gbase64.h:49: note: expected 'gsize *' but argument is of type 'size_t *' A git-blame (not a bisect) seems to indicate this was introduced with the following commit. commit 1f590cf9455c571799d1bfc0777255fa0796d4da Author: Lei Li li...@linux.vnet.ibm.com Date: Fri Jan 25 00:03:20 2013 +0800 QAPI: Introduce memchar-write QMP command Signed-off-by: Lei Li li...@linux.vnet.ibm.com Signed-off-by: Luiz Capitulino lcapitul...@redhat.com This was produced on an Ubuntu 10.04 x86_64 machine. regards, David This email and any attachments are intended for the sole use of the named recipient(s) and contain(s) confidential information that may be proprietary, privileged or copyrighted under applicable law. If you are not the intended recipient, do not read, copy, or forward this email message or any attachments. Delete this email message and any attachments immediately.
Re: [Qemu-devel] [PATCH 2/5] blockdev: add discard suboption to -drive
On Thu, Feb 21, 2013 at 09:48:56AM +0100, Stefan Hajnoczi wrote: On Wed, Feb 20, 2013 at 03:09:51PM +0100, Paolo Bonzini wrote: Il 13/02/2013 11:39, Stefan Hajnoczi ha scritto: .type = QEMU_OPT_STRING, .help = disk image, },{ +.name = discard, +.type = QEMU_OPT_STRING, +.help = discard operation (ignore/off, unmap/on), off/on aliases will be confusing when we plan to add anchor in the future, making this non-boolean. Please support ignore/unmap only. My problem here is that unmap will not be the default but at the same time it will be what people want to use. Hence, it is important to have an easy to remember and discover option; discard=on is immediately understandable, while discard=unmap is not. I understand. The risk is that we end up confusing users rather than helping, because the actual ignore/anchor/unmap modes need to be understood to use this feature properly. If you and Kevin like the off/on alias, go ahead. It's not critical. I actually think both are good points and am not sure which one is more important. In such cases I tend to just accept whatever a proposed patch contains. Kevin
Re: [Qemu-devel] [edk2] [RFC PATCH] Distinguish between reset types
On Thu, 2013-02-21 at 09:36 +0100, Paolo Bonzini wrote: Il 21/02/2013 02:10, Laszlo Ersek ha scritto: OTOH if the keyboard reset gets soft in qemu, then OVMF's hard reset (the above code) will break. Maybe I could cycle between 0xCF9 and 0x64 in ResetCold(), starting with 0xCF9. Yes, that's the right thing to do. Also, in QEMU you're doing: if (val 4) { qemu_system_reset_request(); return; } d-rcr = val 2; /* keep System Reset type only */ It looks like d-rcr should be set first to match what hardware does (writing 0x6 causes a cold reset, and that's what you usually find in the ACPI tables). What Laszlo implemented (above) is fairly much as the data sheet describes it. You're supposed to write 0x02 to set the reset type, and *then* write 0x06 to actually trigger the reset. However, in practice on real hardware that isn't necessary. Just writing 0x06 once will do the trick. Which is just as well, because otherwise the ACPI RESET_REG wouldn't be able to represent it; that only describes *one* write, not two. So yes, you're right. Once qemu starts to distinguish properly between hard and soft reset, it should honour the value of bit 1 in the write which actually triggers the reset. Anthony's patch set did that.. albeit backwards, doing hard and soft reset the wrong way round. -- dwmw2 smime.p7s Description: S/MIME cryptographic signature
[Qemu-devel] [PATCH] doc: fix sheepdog invalid texi @table @list syntax
Some versions of texinfo are not happy with @table @list: ./qemu-options.texi:1526: unknown command `list' ./qemu-options.texi:1526: table requires an argument: the formatter for @item ./qemu-options.texi:1526: warning: @table has text but no @item Use @table @code instead and mark each line with @item. Reported-by: Fred Bezies fredbez...@gmail.com Signed-off-by: Stefan Hajnoczi stefa...@redhat.com --- Fred: Please test this patch to confirm it fixes the issue for you. qemu-options.hx | 19 +++ 1 file changed, 7 insertions(+), 12 deletions(-) diff --git a/qemu-options.hx b/qemu-options.hx index 4bc9c85..3af60bf 100644 --- a/qemu-options.hx +++ b/qemu-options.hx @@ -2095,18 +2095,13 @@ QEMU supports using either local sheepdog devices or remote networked devices. Syntax for specifying a sheepdog device -@table @list -``sheepdog:vdiname'' - -``sheepdog:vdiname:snapid'' - -``sheepdog:vdiname:tag'' - -``sheepdog:host:port:vdiname'' - -``sheepdog:host:port:vdiname:snapid'' - -``sheepdog:host:port:vdiname:tag'' +@table @code +@item sheepdog:vdiname +@item sheepdog:vdiname:snapid +@item sheepdog:vdiname:tag +@item sheepdog:host:port:vdiname +@item sheepdog:host:port:vdiname:snapid +@item sheepdog:host:port:vdiname:tag @end table Example -- 1.8.1.2
Re: [Qemu-devel] [edk2] [RFC PATCH] Distinguish between reset types
On Thu, 2013-02-21 at 02:10 +0100, Laszlo Ersek wrote: On 02/21/13 00:55, David Woodhouse wrote: Well... your test now works because of the bug that Anthony is trying to fix :) I don't believe so, Ok, for the *specific* variant of the test that you did. But there are many tests you could have done which *do* only work because of the bug that Anthony is trying to fix. From what you say, it looks like if the kernel had used the EFI runtime services 'ResetSystem' call, that should have failed too since it only does a KBC soft reset. We might want to discuss two things here: (1) The reset capability that OVMF exports via ACPI -- I agree that I should be effecting the 0xCF9 thing in the appropriate table. Right. When doing that, we should bear in mind your observation (which I can confirm here) that boards in the field tend to have the RESET_REG filled in to point at 0xcf9, but *without* the corresponding flag set in the FADT flags to say that it's supported. It would be interesting to know if there's a *reason* for that, or if it's just the typical failure of BIOS engineers to actually read a specification or care about quality any further than it boots one version of Windows when the wind is in an easterly direction. (2) There's also one point (that I've ever seen) where OVMF itself resets the platform. It is on the initial config TUI; there's a Reset System option somewhere. It's a runtime services call. The kernel can use it too, and perhaps one might even argue that the kernel *should* use it by default, in preference to anything else? But again I suppose that's only true if Windows uses it; if Windows doesn't then we can expect that nobody out there bothers to *test* its implementation on real hardware :( OTOH if the keyboard reset gets soft in qemu, then OVMF's hard reset (the above code) will break. Maybe I could cycle between 0xCF9 and 0x64 in ResetCold(), starting with 0xCF9. (The full logic in the Linux kernel seems a bit too much, see the list of source files in http://thread.gmane.org/gmane.comp.bios.tianocore.devel/2093/focus=195441.) Just cf9, kbc, cf9, kbc perhaps? http://mjg59.dreamwidth.org/3561.html -- dwmw2 smime.p7s Description: S/MIME cryptographic signature
Re: [Qemu-devel] [PATCH 4/4] piix_pci: Implement reset for i440FX PAM configuration
On Thu, 2013-02-21 at 08:46 +0100, Paolo Bonzini wrote: You may go ahead and send a pull request (note that we do send the other patches together with a pull request, just the cover letter has [PULL 0/4] and the git request-pull output). Thanks. I suppose I'd better test that I haven't broken suspend/resume first. I don't care about OS/2 or VDISK, but it's vaguely possible that suspend/resume might be another reset user which actually *would* be offended if the PAM configuration got reset, causing the BIOS to do a complete reinit. If that breaks, this will have to wait for the 'soft-reset' bits that Anthony is looking at. -- dwmw2 smime.p7s Description: S/MIME cryptographic signature
Re: [Qemu-devel] scp during migration with vhost fails
On 02/20/2013 10:23 PM, Michael S. Tsirkin wrote: On Fri, Feb 01, 2013 at 06:03:32PM +0800, Jason Wang wrote: Hello all: During testing, I find doing scp during migration with vhost fails with warnings in guest like: Corrupted MAC on input. Disconnecting: Packet corrupt. lost connection Here's the bisect result: Commit a01672d3968cf91208666d371784110bfde9d4f8 kvm: convert to MemoryListener API is the last commit that works well. With commit 04097f7c5957273c578f72b9bd603ba6b1d69e33 vhost: convert to MemoryListener API, guest network is unusable with warning of bad gso type With commit d743c382861eaa1e13f503b05aba5a382a7e7f7c vhost: fix incorrect userspace address, guest network is available, but scp during migration may fail. Looks like the issue is related to memory api, any thoughts? Thanks Tried to reproduce this for a while without success. Which command line was used? I use this simple cli, sometimes, it's not easy to be reproduced. qemu-system-x86_64 /home/kvm_autotest_root/images/mq.qcow2 -netdev tap,id=hn0,vhost=on -device virtio-net-pci,netdev=hn0,mac=00:00:05:00:00:06 -m 2G -enable-kvm -cpu host -smp 2 -monitor tcp:0:5000,server,nowait -daemonize
Re: [Qemu-devel] [PATCH] docs: Fix generating qemu-doc.html with texinfo 5
On Wed, Feb 20, 2013 at 12:20:31PM -0500, Cole Robinson wrote: LC_ALL=C makeinfo --no-headers --no-split --number-sections --html qemu-doc.texi -o qemu-doc.html ./qemu-options.texi:1521: unknown command `list' ./qemu-options.texi:1521: table requires an argument: the formatter for @item ./qemu-options.texi:1521: warning: @table has text but no @item CC: qemu-sta...@nongnu.org Signed-off-by: Cole Robinson crobi...@redhat.com --- qemu-options.hx | 19 +++ 1 file changed, 7 insertions(+), 12 deletions(-) I just sent a duplicate patch. Please ignore mine. Stefan
Re: [Qemu-devel] [PATCH] doc: fix sheepdog invalid texi @table @list syntax
On Thu, Feb 21, 2013 at 10:13:33AM +0100, Stefan Hajnoczi wrote: Some versions of texinfo are not happy with @table @list: ./qemu-options.texi:1526: unknown command `list' ./qemu-options.texi:1526: table requires an argument: the formatter for @item ./qemu-options.texi:1526: warning: @table has text but no @item Use @table @code instead and mark each line with @item. Reported-by: Fred Bezies fredbez...@gmail.com Signed-off-by: Stefan Hajnoczi stefa...@redhat.com --- Fred: Please test this patch to confirm it fixes the issue for you. qemu-options.hx | 19 +++ 1 file changed, 7 insertions(+), 12 deletions(-) Please ignore this patch, Cole Robinson already submitted an equivalent fix: http://patchwork.ozlabs.org/patch/222131/ Stefan
Re: [Qemu-devel] [PATCH] doc: fix sheepdog invalid texi @table @list syntax
On Thu, Feb 21, 2013 at 10:13:33AM +0100, Stefan Hajnoczi wrote: Some versions of texinfo are not happy with @table @list: ./qemu-options.texi:1526: unknown command `list' ./qemu-options.texi:1526: table requires an argument: the formatter for @item ./qemu-options.texi:1526: warning: @table has text but no @item Use @table @code instead and mark each line with @item. Reported-by: Fred Bezies fredbez...@gmail.com Signed-off-by: Stefan Hajnoczi stefa...@redhat.com --- Fred: Please test this patch to confirm it fixes the issue for you. qemu-options.hx | 19 +++ 1 file changed, 7 insertions(+), 12 deletions(-) NACK (For the patch tracking scripts) Stefan
Re: [Qemu-devel] [PATCH 1/2] win32: do not set CPU affinity
Il 21/02/2013 09:13, Roy Tam ha scritto: Yes, at least linux kernel starts but stalls when hitting IO-APIC thingy, with noapic boot switch it stalls after detecting ttyS0 With patch, QEMU is unresponsive when loading vmlinuz (not even showing Decompressing Linux message) Clarify that it boots fine sometimes, but when QEMU freezes, there is a thread busy-waiting(seems so): http://i.imgur.com/LUJjd8r.png Do you have an image I can try on Linux or Wine? Paolo
Re: [Qemu-devel] [Qemu-trivial] [PATCH] ppc: fixed RAM initialization bug in hw/ppc4xx_devs.c, can now use memory larger than 256MB in bamboo PPC machines
On Wed, Feb 20, 2013 at 09:36:09PM -0500, Alin Tomescu wrote: I hope this is the right way of submitting QEMU patches. I was trying to launch a PowerPC bamboo machine with more than 256MB of RAM with qemu-system-ppc -M bamboo -kernel $kernel -initrd $ramdisk -m 512, but QEMU would just hang. However, when I used -m 256, the machine would boot. I looked through the code in hw/ and it seems there is an error when the RAM memory is setup (if my understanding is correct). After patching it, the machine launched and booted successfully with 512MB of RAM. Signed-off-by: Alin Tomescu tomescu.a...@gmail.com --- hw/ppc4xx_devs.c |2 +- 1 file changed, 1 insertion(+), 1 deletion(-) I shortened the commit message and dropped the first line of commit description (I hope this is the right way of submitting QEMU patches.). Thanks, applied to the trivial patches tree: https://github.com/stefanha/qemu/commits/trivial-patches Stefan
Re: [Qemu-devel] [PATCH] .gitignore: Ignore optionrom/*.asm
On Tue, Feb 19, 2013 at 05:41:28PM -0500, Cole Robinson wrote: Signed-off-by: Cole Robinson crobi...@redhat.com --- .gitignore | 3 +++ 1 file changed, 3 insertions(+) Thanks, applied to the trivial patches tree: https://github.com/stefanha/qemu/commits/trivial-patches Stefan
Re: [Qemu-devel] [PATCH] Add some missing qtest binaries to .gitignore
On Thu, Feb 21, 2013 at 01:34:40PM +1100, David Gibson wrote: These binaries are generated during make check on at least some configurations, so att them to .gitignore. Signed-off-by: David Gibson da...@gibson.dropbear.id.au --- tests/.gitignore |7 +++ 1 file changed, 7 insertions(+) Thanks, applied to the trivial patches tree: https://github.com/stefanha/qemu/commits/trivial-patches Stefan
Re: [Qemu-devel] [RFC PATCH v2 19/23] qcow2: Add error handling to the l2meta coroutine
On Mon, Feb 18, 2013 at 04:42:55PM +0100, Stefan Hajnoczi wrote: On Wed, Feb 13, 2013 at 02:22:09PM +0100, Kevin Wolf wrote: diff --git a/block/qcow2.c b/block/qcow2.c index 57552aa..2819336 100644 --- a/block/qcow2.c +++ b/block/qcow2.c @@ -774,11 +774,33 @@ static void coroutine_fn process_l2meta(void *opaque) m-sleeping = false; } +again: qemu_co_mutex_lock(s-lock); ret = qcow2_alloc_cluster_link_l2(bs, m); if (ret 0) { -/* FIXME */ +/* + * This is a nasty situation: We have already completed the allocation + * write request and returned success, so just failing it isn't + * possible. We need to make sure to return an error during the next + * flush. + * + * However, we still can't drop the l2meta because we want I/O errors + * to be recoverable e.g. after the block device has been grown or the + * network connection restored. Sleep until the next flush comes and + * then retry. + */ A failed flush is live migrated by hw/virtio-blk.c but what happens when we fail during drain? That's a very good questions. Looks like things become rather hairy... This would be a case where we really need a VMState for block drivers (which is in fact how the whole rerror/werror handling would have been implemented best). Juan, any chance to introduce such a thing without breaking everything? Is there something like optional top-level sections? Kevin
Re: [Qemu-devel] [RFC PATCH v2 20/23] qcow2: Cancel COW when overwritten
On Mon, Feb 18, 2013 at 04:46:49PM +0100, Stefan Hajnoczi wrote: On Wed, Feb 13, 2013 at 02:22:10PM +0100, Kevin Wolf wrote: @@ -707,6 +710,16 @@ int qcow2_alloc_cluster_link_l2(BlockDriverState *bs, QCowL2Meta *m) } /* Update L2 table. */ +qemu_co_mutex_unlock(s-lock); +qemu_co_rwlock_wrlock(m-l2_writeback_lock); +has_wr_lock = true; +qemu_co_mutex_lock(s-lock); + +if (m-no_l2_update) { QcowL2Meta now has a no_l2_update field. A sign that we're abusing the QcowL2Meta struct and really need a different abstraction? I think the abstraction is the right one, even though maybe it could use a rename. Maybe QcowL2Meta - QcowCOWRequest or something. The comment in qcow2.h correctly describes what it's meant for. /** * Describes an in-flight (part of a) write request that writes to clusters * that are not referenced in their L2 table yet. */ typedef struct QCowL2Meta However, I think m-no_l2_update is actually redundant: The goal is that only one request that touches a cluster should be responsible for updating the L2 table, and it makes sense to choose the first one to do that. We already have this information in m-parent: The first one is the root of the tree described by these parent links. So if I'm not mistaken, m-no_l2_update == (m-parent != NULL). Kevin
[Qemu-devel] [PULL 0/5] Trivial patches for 6 to 21 February 2013
The 1.5 merge window is open, let's get patches moving again! The following changes since commit 7d2a929feba319c18603e324b1750830d6c8b7a1: vnc-tls: Fix compilation with newer versions of GNU-TLS (2013-02-18 08:40:20 -0600) are available in the git repository at: git://github.com/stefanha/qemu.git trivial-patches for you to fetch changes up to 159c9836d057d8990e71399e8a431b2b911e2885: .gitignore: Ignore optionrom/*.asm (2013-02-21 10:38:07 +0100) Alin Tomescu (1): ppc: fix bamboo 256MB RAM initialization in hw/ppc4xx_devs.c Cole Robinson (1): .gitignore: Ignore optionrom/*.asm David Gibson (1): Add some missing qtest binaries to .gitignore Hervé Poussineau (1): Remove forward declaration of non-existant variable Peter Crosthwaite (1): xilinx_axienet.c: Assert no error when making link .gitignore | 3 +++ hw/ppc4xx_devs.c| 2 +- hw/xilinx_axienet.c | 4 +++- include/sysemu/sysemu.h | 1 - tests/.gitignore| 7 +++ 5 files changed, 14 insertions(+), 3 deletions(-) -- 1.8.1.2
[Qemu-devel] [PATCH 2/5] xilinx_axienet.c: Assert no error when making link
From: Peter Crosthwaite peter.crosthwa...@xilinx.com This gives an awful silent failure when it doesn't work. Assert against link creation failure. Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com Signed-off-by: Stefan Hajnoczi stefa...@redhat.com --- hw/xilinx_axienet.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/hw/xilinx_axienet.c b/hw/xilinx_axienet.c index 34e344c..e5d9251 100644 --- a/hw/xilinx_axienet.c +++ b/hw/xilinx_axienet.c @@ -869,9 +869,11 @@ static int xilinx_enet_init(SysBusDevice *dev) static void xilinx_enet_initfn(Object *obj) { struct XilinxAXIEnet *s = FROM_SYSBUS(typeof(*s), SYS_BUS_DEVICE(obj)); +Error *errp = NULL; object_property_add_link(obj, axistream-connected, TYPE_STREAM_SLAVE, - (Object **) s-tx_dev, NULL); + (Object **) s-tx_dev, errp); +assert_no_error(errp); } static Property xilinx_enet_properties[] = { -- 1.8.1.2
[Qemu-devel] [PATCH 5/5] .gitignore: Ignore optionrom/*.asm
From: Cole Robinson crobi...@redhat.com Signed-off-by: Cole Robinson crobi...@redhat.com Signed-off-by: Stefan Hajnoczi stefa...@redhat.com --- .gitignore | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.gitignore b/.gitignore index 53fe9c3..27ad002 100644 --- a/.gitignore +++ b/.gitignore @@ -83,12 +83,15 @@ fsdev/virtfs-proxy-helper.pod patches pc-bios/bios-pq/status pc-bios/vgabios-pq/status +pc-bios/optionrom/linuxboot.asm pc-bios/optionrom/linuxboot.bin pc-bios/optionrom/linuxboot.raw pc-bios/optionrom/linuxboot.img +pc-bios/optionrom/multiboot.asm pc-bios/optionrom/multiboot.bin pc-bios/optionrom/multiboot.raw pc-bios/optionrom/multiboot.img +pc-bios/optionrom/kvmvapic.asm pc-bios/optionrom/kvmvapic.bin pc-bios/optionrom/kvmvapic.raw pc-bios/optionrom/kvmvapic.img -- 1.8.1.2
Re: [Qemu-devel] [PATCH] Remove elderly top level TODO file
On Wed, Feb 20, 2013 at 04:24:22PM +, Peter Maydell wrote: The top level TODO file hasn't been touched since 2008, so it's now an unhelpful and out of date mix of things that have already been done, things that don't make sense any more and things which could in theory be done but are not in practice important enough (or we'd have done them some time in the last five years). Remove it. The bug tracking system is probably a better place to track TODO items if we want to do so. Signed-off-by: Peter Maydell peter.mayd...@linaro.org --- TODO | 37 - 1 file changed, 37 deletions(-) delete mode 100644 TODO Reviewed-by: Stefan Hajnoczi stefa...@redhat.com
[Qemu-devel] [PATCH] net: reduce the unnecessary memory allocation of multiqueue
Edivaldo reports a problem that the array of NetClientState in NICState is too large - MAX_QUEUE_NUM(1024) which will wastes memory even if multiqueue is not used. Instead of static arrays, solving this issue by allocating the queues on demand for both the NetClientState array in NICState and VirtIONetQueue array in VirtIONet. Tested by myself, with single virtio-net-pci device. The memory allocation is almost the same as when multiqueue is not merged. Cc: Edivaldo de Araujo Pereira edivaldoapere...@yahoo.com.br Cc: qemu-sta...@nongnu.org Signed-off-by: Jason Wang jasow...@redhat.com --- hw/virtio-net.c |6 -- include/net/net.h |2 +- net/net.c | 19 +-- 3 files changed, 14 insertions(+), 13 deletions(-) diff --git a/hw/virtio-net.c b/hw/virtio-net.c index 573c669..70ab641 100644 --- a/hw/virtio-net.c +++ b/hw/virtio-net.c @@ -44,7 +44,7 @@ typedef struct VirtIONet VirtIODevice vdev; uint8_t mac[ETH_ALEN]; uint16_t status; -VirtIONetQueue vqs[MAX_QUEUE_NUM]; +VirtIONetQueue *vqs; VirtQueue *ctrl_vq; NICState *nic; uint32_t tx_timeout; @@ -1326,8 +1326,9 @@ VirtIODevice *virtio_net_init(DeviceState *dev, NICConf *conf, n-vdev.set_status = virtio_net_set_status; n-vdev.guest_notifier_mask = virtio_net_guest_notifier_mask; n-vdev.guest_notifier_pending = virtio_net_guest_notifier_pending; +n-max_queues = MAX(conf-queues, 1); +n-vqs = g_malloc0(sizeof(VirtIONetQueue) * n-max_queues); n-vqs[0].rx_vq = virtio_add_queue(n-vdev, 256, virtio_net_handle_rx); -n-max_queues = conf-queues; n-curr_queues = 1; n-vqs[0].n = n; n-tx_timeout = net-txtimer; @@ -1397,6 +1398,7 @@ void virtio_net_exit(VirtIODevice *vdev) g_free(n-mac_table.macs); g_free(n-vlans); +g_free(n-vqs); for (i = 0; i n-max_queues; i++) { VirtIONetQueue *q = n-vqs[i]; diff --git a/include/net/net.h b/include/net/net.h index 43a045e..cb049a1 100644 --- a/include/net/net.h +++ b/include/net/net.h @@ -72,7 +72,7 @@ struct NetClientState { }; typedef struct NICState { -NetClientState ncs[MAX_QUEUE_NUM]; +NetClientState *ncs; NICConf *conf; void *opaque; bool peer_deleted; diff --git a/net/net.c b/net/net.c index be03a8d..6262ed0 100644 --- a/net/net.c +++ b/net/net.c @@ -235,23 +235,20 @@ NICState *qemu_new_nic(NetClientInfo *info, const char *name, void *opaque) { -NetClientState *nc; NetClientState **peers = conf-peers.ncs; NICState *nic; -int i; +int i, queues = MAX(1, conf-queues); assert(info-type == NET_CLIENT_OPTIONS_KIND_NIC); assert(info-size = sizeof(NICState)); -nc = qemu_new_net_client(info, peers[0], model, name); -nc-queue_index = 0; - -nic = qemu_get_nic(nc); +nic = g_malloc0(info-size + sizeof(NetClientState) * queues); +nic-ncs = (void *)nic + info-size; nic-conf = conf; nic-opaque = opaque; -for (i = 1; i conf-queues; i++) { -qemu_net_client_setup(nic-ncs[i], info, peers[i], model, nc-name, +for (i = 0; i queues; i++) { +qemu_net_client_setup(nic-ncs[i], info, peers[i], model, name, NULL); nic-ncs[i].queue_index = i; } @@ -261,7 +258,7 @@ NICState *qemu_new_nic(NetClientInfo *info, NetClientState *qemu_get_subqueue(NICState *nic, int queue_index) { -return nic-ncs[queue_index]; +return nic-ncs + queue_index; } NetClientState *qemu_get_queue(NICState *nic) @@ -273,7 +270,7 @@ NICState *qemu_get_nic(NetClientState *nc) { NetClientState *nc0 = nc - nc-queue_index; -return DO_UPCAST(NICState, ncs[0], nc0); +return (NICState *)((void *)nc0 - nc-info-size); } void *qemu_get_nic_opaque(NetClientState *nc) @@ -368,6 +365,8 @@ void qemu_del_nic(NICState *nic) qemu_cleanup_net_client(nc); qemu_free_net_client(nc); } + +g_free(nic); } void qemu_foreach_nic(qemu_nic_foreach func, void *opaque) -- 1.7.1
Re: [Qemu-devel] scp during migration with vhost fails
On 02/21/2013 12:48 AM, Michael S. Tsirkin wrote: On Wed, Feb 20, 2013 at 04:23:52PM +0200, Michael S. Tsirkin wrote: On Fri, Feb 01, 2013 at 06:03:32PM +0800, Jason Wang wrote: Hello all: During testing, I find doing scp during migration with vhost fails with warnings in guest like: Corrupted MAC on input. Disconnecting: Packet corrupt. lost connection Here's the bisect result: Commit a01672d3968cf91208666d371784110bfde9d4f8 kvm: convert to MemoryListener API is the last commit that works well. With commit 04097f7c5957273c578f72b9bd603ba6b1d69e33 vhost: convert to MemoryListener API, guest network is unusable with warning of bad gso type With commit d743c382861eaa1e13f503b05aba5a382a7e7f7c vhost: fix incorrect userspace address, guest network is available, but scp during migration may fail. Looks like the issue is related to memory api, any thoughts? Thanks Tried to reproduce this for a while without success. Which command line was used? -- MST Could be we are not syncing all that we should? Does the following hack make the problem go away? diff --git a/hw/vhost.c b/hw/vhost.c index 8d41fdb..a7a0412 100644 --- a/hw/vhost.c +++ b/hw/vhost.c @@ -69,6 +69,8 @@ static int vhost_sync_dirty_bitmap(struct vhost_dev *dev, hwaddr end_addr) { int i; +start_addr = 0x0; +end_addr = ~0x0ull; if (!dev-log_enabled || !dev-started) { return 0; Still can reproduce with this. From the bisect result, the vhost dirty bitmap sync itself looks ok but something wrong when converting to memory listener.
[Qemu-devel] [PATCH 10/14] usb-redir: simplify packet copy
usb_packet_copy can handle combined packets now, so it isn't needed to special-case them any more. Also use the new usb_packet_size() function. Signed-off-by: Gerd Hoffmann kra...@redhat.com --- hw/usb/redirect.c | 18 -- 1 file changed, 4 insertions(+), 14 deletions(-) diff --git a/hw/usb/redirect.c b/hw/usb/redirect.c index 8c0ead0..7078403 100644 --- a/hw/usb/redirect.c +++ b/hw/usb/redirect.c @@ -737,7 +737,7 @@ static void usbredir_handle_bulk_data(USBRedirDevice *dev, USBPacket *p, uint8_t ep) { struct usb_redir_bulk_packet_header bulk_packet; -size_t size = (p-combined) ? p-combined-iov.size : p-iov.size; +size_t size = usb_packet_size(p); const int maxp = dev-endpoint[EP2I(ep)].max_packet_size; if (usbredir_already_in_flight(dev, p-id)) { @@ -771,12 +771,7 @@ static void usbredir_handle_bulk_data(USBRedirDevice *dev, USBPacket *p, bulk_packet, NULL, 0); } else { uint8_t buf[size]; -if (p-combined) { -iov_to_buf(p-combined-iov.iov, p-combined-iov.niov, - 0, buf, size); -} else { -usb_packet_copy(p, buf, size); -} +usb_packet_copy(p, buf, size); usbredir_log_data(dev, bulk data out:, buf, size); usbredirparser_send_bulk_packet(dev-parser, p-id, bulk_packet, buf, size); @@ -1830,7 +1825,7 @@ static void usbredir_bulk_packet(void *priv, uint64_t id, p = usbredir_find_packet_by_id(dev, ep, id); if (p) { -size_t size = (p-combined) ? p-combined-iov.size : p-iov.size; +size_t size = usb_packet_size(p); usbredir_handle_status(dev, p, bulk_packet-status); if (data_len 0) { usbredir_log_data(dev, bulk data in:, data, data_len); @@ -1840,12 +1835,7 @@ static void usbredir_bulk_packet(void *priv, uint64_t id, p-status = USB_RET_BABBLE; data_len = len = size; } -if (p-combined) { -iov_from_buf(p-combined-iov.iov, p-combined-iov.niov, - 0, data, data_len); -} else { -usb_packet_copy(p, data, data_len); -} +usb_packet_copy(p, data, data_len); } p-actual_length = len; if (p-pid == USB_TOKEN_IN p-ep-pipeline) { -- 1.7.9.7
[Qemu-devel] [PATCH 13/14] usb-xhci: usb3 streams
Add streams support to the xhci emulation. No secondary streams yet, only linear stream arays are supported for now. Signed-off-by: Gerd Hoffmann kra...@redhat.com --- hw/usb/hcd-xhci.c | 268 - trace-events |6 +- 2 files changed, 226 insertions(+), 48 deletions(-) diff --git a/hw/usb/hcd-xhci.c b/hw/usb/hcd-xhci.c index b8247f3..5796102 100644 --- a/hw/usb/hcd-xhci.c +++ b/hw/usb/hcd-xhci.c @@ -34,8 +34,8 @@ #else #define DPRINTF(...) do {} while (0) #endif -#define FIXME() do { fprintf(stderr, FIXME %s:%d\n, \ - __func__, __LINE__); abort(); } while (0) +#define FIXME(_msg) do { fprintf(stderr, FIXME %s:%d %s\n, \ + __func__, __LINE__, _msg); abort(); } while (0) #define MAXPORTS_2 15 #define MAXPORTS_3 15 @@ -301,6 +301,8 @@ typedef enum TRBCCode { #define SLOT_CONTEXT_ENTRIES_SHIFT 27 typedef struct XHCIState XHCIState; +typedef struct XHCIStreamContext XHCIStreamContext; +typedef struct XHCIEPContext XHCIEPContext; #define get_field(data, field) \ (((data) field##_SHIFT) field##_MASK) @@ -351,6 +353,7 @@ typedef struct XHCITransfer { unsigned int iso_pkts; unsigned int slotid; unsigned int epid; +unsigned int streamid; bool in_xfer; bool iso_xfer; @@ -367,7 +370,14 @@ typedef struct XHCITransfer { uint64_t mfindex_kick; } XHCITransfer; -typedef struct XHCIEPContext { +struct XHCIStreamContext { +dma_addr_t pctx; +unsigned int sct; +XHCIRing ring; +XHCIStreamContext *sstreams; +}; + +struct XHCIEPContext { XHCIState *xhci; unsigned int slotid; unsigned int epid; @@ -382,11 +392,17 @@ typedef struct XHCIEPContext { unsigned int max_psize; uint32_t state; +/* streams */ +unsigned int max_pstreams; +bool lsa; +unsigned int nr_pstreams; +XHCIStreamContext *pstreams; + /* iso xfer scheduling */ unsigned int interval; int64_t mfindex_last; QEMUTimer *kick_timer; -} XHCIEPContext; +}; typedef struct XHCISlot { bool enabled; @@ -482,7 +498,7 @@ enum xhci_flags { }; static void xhci_kick_ep(XHCIState *xhci, unsigned int slotid, - unsigned int epid); + unsigned int epid, unsigned int streamid); static TRBCCode xhci_disable_ep(XHCIState *xhci, unsigned int slotid, unsigned int epid); static void xhci_event(XHCIState *xhci, XHCIEvent *event, int v); @@ -1068,18 +1084,116 @@ static void xhci_stop(XHCIState *xhci) xhci-crcr_low = ~CRCR_CRR; } +static XHCIStreamContext *xhci_alloc_stream_contexts(unsigned count, + dma_addr_t base) +{ +XHCIStreamContext *stctx; +unsigned int i; + +stctx = g_new0(XHCIStreamContext, count); +for (i = 0; i count; i++) { +stctx[i].pctx = base + i * 16; +stctx[i].sct = -1; +} +return stctx; +} + +static void xhci_reset_streams(XHCIEPContext *epctx) +{ +unsigned int i; + +for (i = 0; i epctx-nr_pstreams; i++) { +epctx-pstreams[i].sct = -1; +g_free(epctx-pstreams[i].sstreams); +} +} + +static void xhci_alloc_streams(XHCIEPContext *epctx, dma_addr_t base) +{ +assert(epctx-pstreams == NULL); +epctx-nr_pstreams = 2 epctx-max_pstreams; +epctx-pstreams = xhci_alloc_stream_contexts(epctx-nr_pstreams, base); +} + +static void xhci_free_streams(XHCIEPContext *epctx) +{ +int i; + +assert(epctx-pstreams != NULL); + +if (!epctx-lsa) { +for (i = 0; i epctx-nr_pstreams; i++) { +g_free(epctx-pstreams[i].sstreams); +} +} +g_free(epctx-pstreams); +epctx-pstreams = NULL; +epctx-nr_pstreams = 0; +} + +static XHCIStreamContext *xhci_find_stream(XHCIEPContext *epctx, + unsigned int streamid, + uint32_t *cc_error) +{ +XHCIStreamContext *sctx; +dma_addr_t base; +uint32_t ctx[2], sct; + +assert(streamid != 0); +if (epctx-lsa) { +if (streamid = epctx-nr_pstreams) { +*cc_error = CC_INVALID_STREAM_ID_ERROR; +return NULL; +} +sctx = epctx-pstreams + streamid; +} else { +FIXME(secondary streams not implemented yet); +} + +if (sctx-sct == -1) { +xhci_dma_read_u32s(epctx-xhci, sctx-pctx, ctx, sizeof(ctx)); +fprintf(stderr, %s: init sctx #%d @ %lx: %08x %08x\n, __func__, +streamid, sctx-pctx, ctx[0], ctx[1]); +sct = (ctx[0] 1) 0x07; +if (epctx-lsa sct != 1) { +*cc_error = CC_INVALID_STREAM_TYPE_ERROR; +return NULL; +} +sctx-sct = sct; +base = xhci_addr64(ctx[0] ~0xf, ctx[1]); +xhci_ring_init(epctx-xhci, sctx-ring, base); +} +return sctx; +} + static void
[Qemu-devel] [PATCH 14/14] uas-uas: usb3 streams
Add usb3 streams support to the uas (usb attached scsi) emulation. Signed-off-by: Gerd Hoffmann kra...@redhat.com --- hw/usb/dev-uas.c | 247 -- 1 file changed, 205 insertions(+), 42 deletions(-) diff --git a/hw/usb/dev-uas.c b/hw/usb/dev-uas.c index 316c388..1ac5117 100644 --- a/hw/usb/dev-uas.c +++ b/hw/usb/dev-uas.c @@ -99,6 +99,9 @@ typedef struct { /* - */ +#define UAS_STREAM_BM_ATTR 4 +#define UAS_MAX_STREAMS (1 UAS_STREAM_BM_ATTR) + typedef struct UASDevice UASDevice; typedef struct UASRequest UASRequest; typedef struct UASStatus UASStatus; @@ -106,12 +109,18 @@ typedef struct UASStatus UASStatus; struct UASDevice { USBDevice dev; SCSIBus bus; -UASRequest*datain; -UASRequest*dataout; -USBPacket *status; QEMUBH*status_bh; QTAILQ_HEAD(, UASStatus) results; QTAILQ_HEAD(, UASRequest) requests; + +/* usb 2.0 only */ +USBPacket *status2; +UASRequest*datain2; +UASRequest*dataout2; + +/* usb 3.0 only */ +USBPacket *data3[UAS_MAX_STREAMS]; +USBPacket *status3[UAS_MAX_STREAMS]; }; struct UASRequest { @@ -132,6 +141,7 @@ struct UASRequest { }; struct UASStatus { +uint32_t stream; uas_uistatus; uint32_t length; QTAILQ_ENTRY(UASStatus) next; @@ -144,6 +154,7 @@ enum { STR_PRODUCT, STR_SERIALNUMBER, STR_CONFIG_HIGH, +STR_CONFIG_SUPER, }; static const USBDescStrings desc_strings = { @@ -151,6 +162,7 @@ static const USBDescStrings desc_strings = { [STR_PRODUCT] = USB Attached SCSI HBA, [STR_SERIALNUMBER] = 27842, [STR_CONFIG_HIGH] = High speed config (usb 2.0), +[STR_CONFIG_SUPER] = Super speed config (usb 3.0), }; static const USBDescIface desc_iface_high = { @@ -204,6 +216,64 @@ static const USBDescIface desc_iface_high = { } }; +static const USBDescIface desc_iface_super = { +.bInterfaceNumber = 0, +.bNumEndpoints = 4, +.bInterfaceClass = USB_CLASS_MASS_STORAGE, +.bInterfaceSubClass= 0x06, /* SCSI */ +.bInterfaceProtocol= 0x62, /* UAS */ +.eps = (USBDescEndpoint[]) { +{ +.bEndpointAddress = USB_DIR_OUT | UAS_PIPE_ID_COMMAND, +.bmAttributes = USB_ENDPOINT_XFER_BULK, +.wMaxPacketSize= 1024, +.bMaxBurst = 15, +.extra = (uint8_t[]) { +0x04, /* u8 bLength */ +0x24, /* u8 bDescriptorType */ +UAS_PIPE_ID_COMMAND, +0x00, /* u8 bReserved */ +}, +},{ +.bEndpointAddress = USB_DIR_IN | UAS_PIPE_ID_STATUS, +.bmAttributes = USB_ENDPOINT_XFER_BULK, +.wMaxPacketSize= 1024, +.bMaxBurst = 15, +.bmAttributes_super= UAS_STREAM_BM_ATTR, +.extra = (uint8_t[]) { +0x04, /* u8 bLength */ +0x24, /* u8 bDescriptorType */ +UAS_PIPE_ID_STATUS, +0x00, /* u8 bReserved */ +}, +},{ +.bEndpointAddress = USB_DIR_IN | UAS_PIPE_ID_DATA_IN, +.bmAttributes = USB_ENDPOINT_XFER_BULK, +.wMaxPacketSize= 1024, +.bMaxBurst = 15, +.bmAttributes_super= UAS_STREAM_BM_ATTR, +.extra = (uint8_t[]) { +0x04, /* u8 bLength */ +0x24, /* u8 bDescriptorType */ +UAS_PIPE_ID_DATA_IN, +0x00, /* u8 bReserved */ +}, +},{ +.bEndpointAddress = USB_DIR_OUT | UAS_PIPE_ID_DATA_OUT, +.bmAttributes = USB_ENDPOINT_XFER_BULK, +.wMaxPacketSize= 1024, +.bMaxBurst = 15, +.bmAttributes_super= UAS_STREAM_BM_ATTR, +.extra = (uint8_t[]) { +0x04, /* u8 bLength */ +0x24, /* u8 bDescriptorType */ +UAS_PIPE_ID_DATA_OUT, +0x00, /* u8 bReserved */ +}, +}, +} +}; + static const USBDescDevice desc_device_high = { .bcdUSB= 0x0200, .bMaxPacketSize0 = 64, @@ -220,6 +290,22 @@ static const USBDescDevice desc_device_high = { }, }; +static const USBDescDevice desc_device_super = { +.bcdUSB= 0x0300, +.bMaxPacketSize0 = 64, +.bNumConfigurations= 1, +.confs = (USBDescConfig[]) { +
[Qemu-devel] [PATCH 06/14] usb-host: move legacy cmd line bits
The code handling the -usbdevice host:... legacy command line syntax is moved to the new hw/usb/host-legacy.c file. Signed-off-by: Gerd Hoffmann kra...@redhat.com --- configure|2 +- hw/usb/Makefile.objs |2 +- hw/usb/host-legacy.c | 144 ++ hw/usb/host-linux.c | 101 +-- hw/usb/host.h| 44 +++ 5 files changed, 191 insertions(+), 102 deletions(-) create mode 100644 hw/usb/host-legacy.c create mode 100644 hw/usb/host.h diff --git a/configure b/configure index bf5970f..42cb314 100755 --- a/configure +++ b/configure @@ -3723,7 +3723,7 @@ fi # USB host support case $usb in linux) - echo HOST_USB=linux $config_host_mak + echo HOST_USB=linux legacy $config_host_mak ;; bsd) echo HOST_USB=bsd $config_host_mak diff --git a/hw/usb/Makefile.objs b/hw/usb/Makefile.objs index c1e40d7..e63e287 100644 --- a/hw/usb/Makefile.objs +++ b/hw/usb/Makefile.objs @@ -27,4 +27,4 @@ common-obj-$(CONFIG_USB_SMARTCARD)+= dev-smartcard-reader.o common-obj-$(CONFIG_USB_REDIR) += redirect.o quirks.o # usb pass-through -common-obj-y += host-$(HOST_USB).o +common-obj-y += $(patsubst %,host-%.o,$(HOST_USB)) diff --git a/hw/usb/host-legacy.c b/hw/usb/host-legacy.c new file mode 100644 index 000..3a5f705 --- /dev/null +++ b/hw/usb/host-legacy.c @@ -0,0 +1,144 @@ +/* + * Linux host USB redirector + * + * Copyright (c) 2005 Fabrice Bellard + * + * Copyright (c) 2008 Max Krasnyansky + * Support for host device auto connect disconnect + * Major rewrite to support fully async operation + * + * Copyright 2008 TJ li...@tjworld.net + * Added flexible support for /dev/bus/usb /sys/bus/usb/devices in addition + * to the legacy /proc/bus/usb USB device discovery and handling + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the Software), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED AS IS, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +#include qemu-common.h +#include hw/usb.h +#include hw/usb/host.h + +/* + * Autoconnect filter + * Format: + *auto:bus:dev[:vid:pid] + *auto:bus.dev[:vid:pid] + * + *bus - bus number(dec, * means any) + *dev - device number (dec, * means any) + *vid - vendor id (hex, * means any) + *pid - product id(hex, * means any) + * + *See 'lsusb' output. + */ +static int parse_filter(const char *spec, struct USBAutoFilter *f) +{ +enum { BUS, DEV, VID, PID, DONE }; +const char *p = spec; +int i; + +f-bus_num= 0; +f-addr = 0; +f-vendor_id = 0; +f-product_id = 0; + +for (i = BUS; i DONE; i++) { +p = strpbrk(p, :.); +if (!p) { +break; +} +p++; + +if (*p == '*') { +continue; +} +switch (i) { +case BUS: +f-bus_num = strtol(p, NULL, 10); +break; +case DEV: +f-addr= strtol(p, NULL, 10); +break; +case VID: +f-vendor_id = strtol(p, NULL, 16); +break; +case PID: +f-product_id = strtol(p, NULL, 16); +break; +} +} + +if (i DEV) { +fprintf(stderr, husb: invalid auto filter spec %s\n, spec); +return -1; +} + +return 0; +} + +USBDevice *usb_host_device_open(USBBus *bus, const char *devname) +{ +struct USBAutoFilter filter; +USBDevice *dev; +char *p; + +dev = usb_create(bus, usb-host); + +if (strstr(devname, auto:)) { +if (parse_filter(devname, filter) 0) { +goto fail; +} +} else { +p = strchr(devname, '.'); +if (p) { +filter.bus_num= strtoul(devname, NULL, 0); +filter.addr = strtoul(p + 1, NULL, 0); +filter.vendor_id = 0; +filter.product_id = 0; +} else { +p = strchr(devname, ':'); +if (p) { +filter.bus_num= 0; +filter.addr
[Qemu-devel] [PATCH 1/5] Remove forward declaration of non-existant variable
From: Hervé Poussineau hpous...@reactos.org This variable has been removed 5 years ago in 970ac5a3082428dca91171f270dcd95d6f4b2636. Signed-off-by: Hervé Poussineau hpous...@reactos.org Signed-off-by: Stefan Hajnoczi stefa...@redhat.com --- include/sysemu/sysemu.h | 1 - 1 file changed, 1 deletion(-) diff --git a/include/sysemu/sysemu.h b/include/sysemu/sysemu.h index 1d9599e..ae49088 100644 --- a/include/sysemu/sysemu.h +++ b/include/sysemu/sysemu.h @@ -94,7 +94,6 @@ typedef enum DisplayType } DisplayType; extern int autostart; -extern int bios_size; typedef enum { VGA_NONE, VGA_STD, VGA_CIRRUS, VGA_VMWARE, VGA_XENFB, VGA_QXL, -- 1.8.1.2
[Qemu-devel] [PATCH 12/14] usb-core: usb3 streams
This patch adds support for usb3 streams to the usb subsystem core. This is just adding a streams field / parameter in a number of places. Signed-off-by: Gerd Hoffmann kra...@redhat.com --- hw/usb.h | 10 ++ hw/usb/core.c | 10 ++ hw/usb/dev-bluetooth.c|2 +- hw/usb/dev-hid.c |2 +- hw/usb/dev-hub.c | 10 +- hw/usb/dev-network.c |2 +- hw/usb/dev-smartcard-reader.c |2 +- hw/usb/dev-uas.c |2 +- hw/usb/dev-wacom.c|4 ++-- hw/usb/hcd-ehci.c |7 --- hw/usb/hcd-musb.c |2 +- hw/usb/hcd-ohci.c |4 ++-- hw/usb/hcd-uhci.c |2 +- hw/usb/hcd-xhci.c |9 + 14 files changed, 37 insertions(+), 31 deletions(-) diff --git a/hw/usb.h b/hw/usb.h index 0d09e02..382496c 100644 --- a/hw/usb.h +++ b/hw/usb.h @@ -361,6 +361,7 @@ struct USBPacket { int pid; uint64_t id; USBEndpoint *ep; +unsigned int stream; QEMUIOVector iov; uint64_t parameter; /* control transfers */ bool short_not_ok; @@ -383,8 +384,9 @@ struct USBCombinedPacket { void usb_packet_init(USBPacket *p); void usb_packet_set_state(USBPacket *p, USBPacketState state); void usb_packet_check_state(USBPacket *p, USBPacketState expected); -void usb_packet_setup(USBPacket *p, int pid, USBEndpoint *ep, uint64_t id, - bool short_not_ok, bool int_req); +void usb_packet_setup(USBPacket *p, int pid, + USBEndpoint *ep, unsigned int stream, + uint64_t id, bool short_not_ok, bool int_req); void usb_packet_addbuf(USBPacket *p, void *ptr, size_t len); int usb_packet_map(USBPacket *p, QEMUSGList *sgl); void usb_packet_unmap(USBPacket *p, QEMUSGList *sgl); @@ -430,7 +432,7 @@ void usb_attach(USBPort *port); void usb_detach(USBPort *port); void usb_port_reset(USBPort *port); void usb_device_reset(USBDevice *dev); -void usb_wakeup(USBEndpoint *ep); +void usb_wakeup(USBEndpoint *ep, unsigned int stream); void usb_generic_async_ctrl_complete(USBDevice *s, USBPacket *p); int set_usb_string(uint8_t *buf, const char *str); @@ -489,7 +491,7 @@ struct USBBus { struct USBBusOps { int (*register_companion)(USBBus *bus, USBPort *ports[], uint32_t portcount, uint32_t firstport); -void (*wakeup_endpoint)(USBBus *bus, USBEndpoint *ep); +void (*wakeup_endpoint)(USBBus *bus, USBEndpoint *ep, unsigned int stream); }; void usb_bus_new(USBBus *bus, USBBusOps *ops, DeviceState *host); diff --git a/hw/usb/core.c b/hw/usb/core.c index 674fef8..15a150a 100644 --- a/hw/usb/core.c +++ b/hw/usb/core.c @@ -71,7 +71,7 @@ void usb_device_reset(USBDevice *dev) usb_device_handle_reset(dev); } -void usb_wakeup(USBEndpoint *ep) +void usb_wakeup(USBEndpoint *ep, unsigned int stream) { USBDevice *dev = ep-dev; USBBus *bus = usb_bus_from_device(dev); @@ -80,7 +80,7 @@ void usb_wakeup(USBEndpoint *ep) dev-port-ops-wakeup(dev-port); } if (bus-ops-wakeup_endpoint) { -bus-ops-wakeup_endpoint(bus, ep); +bus-ops-wakeup_endpoint(bus, ep, stream); } } @@ -545,14 +545,16 @@ void usb_packet_set_state(USBPacket *p, USBPacketState state) p-state = state; } -void usb_packet_setup(USBPacket *p, int pid, USBEndpoint *ep, uint64_t id, - bool short_not_ok, bool int_req) +void usb_packet_setup(USBPacket *p, int pid, + USBEndpoint *ep, unsigned int stream, + uint64_t id, bool short_not_ok, bool int_req) { assert(!usb_packet_is_inflight(p)); assert(p-iov.iov != NULL); p-id = id; p-pid = pid; p-ep = ep; +p-stream = stream; p-status = USB_RET_SUCCESS; p-actual_length = 0; p-parameter = 0; diff --git a/hw/usb/dev-bluetooth.c b/hw/usb/dev-bluetooth.c index adbf9d4..0f8aa48 100644 --- a/hw/usb/dev-bluetooth.c +++ b/hw/usb/dev-bluetooth.c @@ -478,7 +478,7 @@ static void usb_bt_out_hci_packet_event(void *opaque, struct USBBtState *s = (struct USBBtState *) opaque; if (s-evt.len == 0) { -usb_wakeup(s-intr); +usb_wakeup(s-intr, 0); } usb_bt_fifo_enqueue(s-evt, data, len); } diff --git a/hw/usb/dev-hid.c b/hw/usb/dev-hid.c index 29b6481..9701048 100644 --- a/hw/usb/dev-hid.c +++ b/hw/usb/dev-hid.c @@ -423,7 +423,7 @@ static void usb_hid_changed(HIDState *hs) { USBHIDState *us = container_of(hs, USBHIDState, hid); -usb_wakeup(us-intr); +usb_wakeup(us-intr, 0); } static void usb_hid_handle_reset(USBDevice *dev) diff --git a/hw/usb/dev-hub.c b/hw/usb/dev-hub.c index 79f2f46..504c98c 100644 --- a/hw/usb/dev-hub.c +++ b/hw/usb/dev-hub.c @@ -164,7 +164,7 @@ static void usb_hub_attach(USBPort *port1) } else { port-wPortStatus = ~PORT_STAT_LOW_SPEED; } -usb_wakeup(s-intr); +
[Qemu-devel] [PULL 00/14] usb patch queue
Hi, master is open again, time to push the bits piled up in the usb queue during the freeze. Most significant change is the usb3 streams support. Other than that there are a bunch of little fixes and some preparation for switch usb-host over to libusb. pleaase pull, Gerd The following changes since commit 7d2a929feba319c18603e324b1750830d6c8b7a1: vnc-tls: Fix compilation with newer versions of GNU-TLS (2013-02-18 08:40:20 -0600) are available in the git repository at: git://git.kraxel.org/qemu usb.78 for you to fetch changes up to 89a453d4a5c195e6d0a3c3d4fcaacb447447115f: uas-uas: usb3 streams (2013-02-19 13:18:00 +0100) Gerd Hoffmann (14): usb: Makefile cleanup fix scripts/make_device_config.sh make usb devices configurable allow disabling usb smartcard support usb-storage: use scsi_req_enqueue return value usb-host: move legacy cmd line bits usb-host: remove usb_host_device_close usb: add usb_ep_set_halted usb: make usb_packet_copy operate on combined packets usb-redir: simplify packet copy usb: fix endpoint descriptor ordering usb-core: usb3 streams usb-xhci: usb3 streams uas-uas: usb3 streams configure|2 +- default-configs/alpha-softmmu.mak|1 + default-configs/arm-softmmu.mak |1 + default-configs/i386-softmmu.mak |1 + default-configs/m68k-softmmu.mak |1 + default-configs/mips-softmmu.mak |1 + default-configs/mips64-softmmu.mak |1 + default-configs/mips64el-softmmu.mak |1 + default-configs/mipsel-softmmu.mak |1 + default-configs/ppc-softmmu.mak |1 + default-configs/ppc64-softmmu.mak|1 + default-configs/ppcemb-softmmu.mak |1 + default-configs/sh4-softmmu.mak |1 + default-configs/sh4eb-softmmu.mak|1 + default-configs/sparc64-softmmu.mak |1 + default-configs/usb.mak |8 + default-configs/x86_64-softmmu.mak |1 + hw/Makefile.objs |2 + hw/usb.h | 13 +- hw/usb/Makefile.objs | 30 +++- hw/usb/core.c| 35 +++-- hw/usb/desc.c|9 +- hw/usb/dev-bluetooth.c |2 +- hw/usb/dev-hid.c |2 +- hw/usb/dev-hub.c | 10 +- hw/usb/dev-network.c |2 +- hw/usb/dev-smartcard-reader.c|2 +- hw/usb/dev-storage.c |5 +- hw/usb/dev-uas.c | 247 -- hw/usb/dev-wacom.c |4 +- hw/usb/hcd-ehci.c|7 +- hw/usb/hcd-musb.c|2 +- hw/usb/hcd-ohci.c|4 +- hw/usb/hcd-uhci.c|2 +- hw/usb/hcd-xhci.c| 275 -- hw/usb/host-bsd.c|6 - hw/usb/host-legacy.c | 144 ++ hw/usb/host-linux.c | 125 +--- hw/usb/host-stub.c |5 - hw/usb/host.h| 44 ++ hw/usb/redirect.c| 18 +-- scripts/make_device_config.sh|2 +- trace-events |6 +- vl.c |5 +- 44 files changed, 742 insertions(+), 291 deletions(-) create mode 100644 default-configs/usb.mak create mode 100644 hw/usb/host-legacy.c create mode 100644 hw/usb/host.h
Re: [Qemu-devel] [PATCH 1/2] win32: do not set CPU affinity
2013/2/21 Paolo Bonzini pbonz...@redhat.com: Il 21/02/2013 09:13, Roy Tam ha scritto: Yes, at least linux kernel starts but stalls when hitting IO-APIC thingy, with noapic boot switch it stalls after detecting ttyS0 With patch, QEMU is unresponsive when loading vmlinuz (not even showing Decompressing Linux message) Clarify that it boots fine sometimes, but when QEMU freezes, there is a thread busy-waiting(seems so): http://i.imgur.com/LUJjd8r.png Do you have an image I can try on Linux or Wine? even fdostest.img can trigger this situation in WinXP. Paolo
[Qemu-devel] [PATCH 3/5] Add some missing qtest binaries to .gitignore
From: David Gibson da...@gibson.dropbear.id.au These binaries are generated during make check on at least some configurations, so att them to .gitignore. Signed-off-by: David Gibson da...@gibson.dropbear.id.au Signed-off-by: Stefan Hajnoczi stefa...@redhat.com --- tests/.gitignore | 7 +++ 1 file changed, 7 insertions(+) diff --git a/tests/.gitignore b/tests/.gitignore index 38c94ef..fb05c2a 100644 --- a/tests/.gitignore +++ b/tests/.gitignore @@ -4,11 +4,18 @@ check-qint check-qjson check-qlist check-qstring +test-aio +test-cutils +test-hbitmap +test-iov +test-mul64 test-qapi-types.[ch] test-qapi-visit.[ch] test-qmp-commands.h test-qmp-commands test-qmp-input-strict test-qmp-marshal.c +test-thread-pool test-x86-cpuid +test-xbzrle *-test -- 1.8.1.2
[Qemu-devel] [PATCH 09/14] usb: make usb_packet_copy operate on combined packets
Likewise usb_packet_skip. Also usb_packet_size. Signed-off-by: Gerd Hoffmann kra...@redhat.com --- hw/usb.h |1 + hw/usb/core.c | 19 ++- 2 files changed, 15 insertions(+), 5 deletions(-) diff --git a/hw/usb.h b/hw/usb.h index af86fbd..0d09e02 100644 --- a/hw/usb.h +++ b/hw/usb.h @@ -390,6 +390,7 @@ int usb_packet_map(USBPacket *p, QEMUSGList *sgl); void usb_packet_unmap(USBPacket *p, QEMUSGList *sgl); void usb_packet_copy(USBPacket *p, void *ptr, size_t bytes); void usb_packet_skip(USBPacket *p, size_t bytes); +size_t usb_packet_size(USBPacket *p); void usb_packet_cleanup(USBPacket *p); static inline bool usb_packet_is_inflight(USBPacket *p) diff --git a/hw/usb/core.c b/hw/usb/core.c index 5517797..674fef8 100644 --- a/hw/usb/core.c +++ b/hw/usb/core.c @@ -570,15 +570,17 @@ void usb_packet_addbuf(USBPacket *p, void *ptr, size_t len) void usb_packet_copy(USBPacket *p, void *ptr, size_t bytes) { +QEMUIOVector *iov = p-combined ? p-combined-iov : p-iov; + assert(p-actual_length = 0); -assert(p-actual_length + bytes = p-iov.size); +assert(p-actual_length + bytes = iov-size); switch (p-pid) { case USB_TOKEN_SETUP: case USB_TOKEN_OUT: -iov_to_buf(p-iov.iov, p-iov.niov, p-actual_length, ptr, bytes); +iov_to_buf(iov-iov, iov-niov, p-actual_length, ptr, bytes); break; case USB_TOKEN_IN: -iov_from_buf(p-iov.iov, p-iov.niov, p-actual_length, ptr, bytes); +iov_from_buf(iov-iov, iov-niov, p-actual_length, ptr, bytes); break; default: fprintf(stderr, %s: invalid pid: %x\n, __func__, p-pid); @@ -589,14 +591,21 @@ void usb_packet_copy(USBPacket *p, void *ptr, size_t bytes) void usb_packet_skip(USBPacket *p, size_t bytes) { +QEMUIOVector *iov = p-combined ? p-combined-iov : p-iov; + assert(p-actual_length = 0); -assert(p-actual_length + bytes = p-iov.size); +assert(p-actual_length + bytes = iov-size); if (p-pid == USB_TOKEN_IN) { -iov_memset(p-iov.iov, p-iov.niov, p-actual_length, 0, bytes); +iov_memset(iov-iov, iov-niov, p-actual_length, 0, bytes); } p-actual_length += bytes; } +size_t usb_packet_size(USBPacket *p) +{ +return p-combined ? p-combined-iov.size : p-iov.size; +} + void usb_packet_cleanup(USBPacket *p) { assert(!usb_packet_is_inflight(p)); -- 1.7.9.7
[Qemu-devel] [PATCH 03/14] make usb devices configurable
Leave the core usb devices (usb hub, tablet, mouse, keyboard) enabled unconditionally. Make the other ones configurable. Exceptions: - bluetooth: not qdevified yet, has a vl.c dependency because of that, thus disabling isn't as easy as not linking the object file. - smardcard: ccid-card-emulated depends on that one *and* CONFIG_SMARTCARD_NSS. So it isn't a one-liner and comes as separate patch because of that. Signed-off-by: Gerd Hoffmann kra...@redhat.com --- default-configs/alpha-softmmu.mak|1 + default-configs/arm-softmmu.mak |1 + default-configs/i386-softmmu.mak |1 + default-configs/m68k-softmmu.mak |1 + default-configs/mips-softmmu.mak |1 + default-configs/mips64-softmmu.mak |1 + default-configs/mips64el-softmmu.mak |1 + default-configs/mipsel-softmmu.mak |1 + default-configs/ppc-softmmu.mak |1 + default-configs/ppc64-softmmu.mak|1 + default-configs/ppcemb-softmmu.mak |1 + default-configs/sh4-softmmu.mak |1 + default-configs/sh4eb-softmmu.mak|1 + default-configs/sparc64-softmmu.mak |1 + default-configs/usb.mak |8 default-configs/x86_64-softmmu.mak |1 + hw/usb/Makefile.objs | 20 17 files changed, 35 insertions(+), 8 deletions(-) create mode 100644 default-configs/usb.mak diff --git a/default-configs/alpha-softmmu.mak b/default-configs/alpha-softmmu.mak index 501dd41..2dbee94 100644 --- a/default-configs/alpha-softmmu.mak +++ b/default-configs/alpha-softmmu.mak @@ -1,6 +1,7 @@ # Default configuration for alpha-softmmu include pci.mak +include usb.mak CONFIG_SERIAL=y CONFIG_I8254=y CONFIG_PCKBD=y diff --git a/default-configs/arm-softmmu.mak b/default-configs/arm-softmmu.mak index 2f1a5c9..b40f7b0 100644 --- a/default-configs/arm-softmmu.mak +++ b/default-configs/arm-softmmu.mak @@ -1,6 +1,7 @@ # Default configuration for arm-softmmu include pci.mak +include usb.mak CONFIG_GDBSTUB_XML=y CONFIG_VGA=y CONFIG_ISA_MMIO=y diff --git a/default-configs/i386-softmmu.mak b/default-configs/i386-softmmu.mak index 2c78175..1b23025 100644 --- a/default-configs/i386-softmmu.mak +++ b/default-configs/i386-softmmu.mak @@ -1,6 +1,7 @@ # Default configuration for i386-softmmu include pci.mak +include usb.mak CONFIG_VGA=y CONFIG_VGA_PCI=y CONFIG_VGA_ISA=y diff --git a/default-configs/m68k-softmmu.mak b/default-configs/m68k-softmmu.mak index 3e2ec37..778ea82 100644 --- a/default-configs/m68k-softmmu.mak +++ b/default-configs/m68k-softmmu.mak @@ -1,5 +1,6 @@ # Default configuration for m68k-softmmu include pci.mak +include usb.mak CONFIG_GDBSTUB_XML=y CONFIG_PTIMER=y diff --git a/default-configs/mips-softmmu.mak b/default-configs/mips-softmmu.mak index a271b1c..4f04a33 100644 --- a/default-configs/mips-softmmu.mak +++ b/default-configs/mips-softmmu.mak @@ -1,6 +1,7 @@ # Default configuration for mips-softmmu include pci.mak +include usb.mak CONFIG_ISA_MMIO=y CONFIG_ESP=y CONFIG_VGA=y diff --git a/default-configs/mips64-softmmu.mak b/default-configs/mips64-softmmu.mak index 0510bb6..a5b6c3c 100644 --- a/default-configs/mips64-softmmu.mak +++ b/default-configs/mips64-softmmu.mak @@ -1,6 +1,7 @@ # Default configuration for mips64-softmmu include pci.mak +include usb.mak CONFIG_ISA_MMIO=y CONFIG_ESP=y CONFIG_VGA=y diff --git a/default-configs/mips64el-softmmu.mak b/default-configs/mips64el-softmmu.mak index ed3bed3..a0e6de8 100644 --- a/default-configs/mips64el-softmmu.mak +++ b/default-configs/mips64el-softmmu.mak @@ -1,6 +1,7 @@ # Default configuration for mips64el-softmmu include pci.mak +include usb.mak CONFIG_ISA_MMIO=y CONFIG_ESP=y CONFIG_VGA=y diff --git a/default-configs/mipsel-softmmu.mak b/default-configs/mipsel-softmmu.mak index fa3a2ca..753dd76 100644 --- a/default-configs/mipsel-softmmu.mak +++ b/default-configs/mipsel-softmmu.mak @@ -1,6 +1,7 @@ # Default configuration for mipsel-softmmu include pci.mak +include usb.mak CONFIG_ISA_MMIO=y CONFIG_ESP=y CONFIG_VGA=y diff --git a/default-configs/ppc-softmmu.mak b/default-configs/ppc-softmmu.mak index 1f4a1cf..f9f8a81 100644 --- a/default-configs/ppc-softmmu.mak +++ b/default-configs/ppc-softmmu.mak @@ -1,6 +1,7 @@ # Default configuration for ppc-softmmu include pci.mak +include usb.mak CONFIG_GDBSTUB_XML=y CONFIG_ISA_MMIO=y CONFIG_ESCC=y diff --git a/default-configs/ppc64-softmmu.mak b/default-configs/ppc64-softmmu.mak index 5ff406c..dc44294 100644 --- a/default-configs/ppc64-softmmu.mak +++ b/default-configs/ppc64-softmmu.mak @@ -1,6 +1,7 @@ # Default configuration for ppc64-softmmu include pci.mak +include usb.mak CONFIG_GDBSTUB_XML=y CONFIG_ISA_MMIO=y CONFIG_ESCC=y diff --git a/default-configs/ppcemb-softmmu.mak b/default-configs/ppcemb-softmmu.mak index aaa9cdc..1c6bcf9 100644 --- a/default-configs/ppcemb-softmmu.mak +++ b/default-configs/ppcemb-softmmu.mak @@ -1,6 +1,7 @@ #
[Qemu-devel] [PATCH 07/14] usb-host: remove usb_host_device_close
Nobody implements that anyway. Signed-off-by: Gerd Hoffmann kra...@redhat.com --- hw/usb.h|1 - hw/usb/host-bsd.c |6 -- hw/usb/host-linux.c | 24 hw/usb/host-stub.c |5 - vl.c|5 +++-- 5 files changed, 3 insertions(+), 38 deletions(-) diff --git a/hw/usb.h b/hw/usb.h index bc42639..90024a4 100644 --- a/hw/usb.h +++ b/hw/usb.h @@ -434,7 +434,6 @@ int set_usb_string(uint8_t *buf, const char *str); /* usb-linux.c */ USBDevice *usb_host_device_open(USBBus *bus, const char *devname); -int usb_host_device_close(const char *devname); void usb_host_info(Monitor *mon, const QDict *qdict); /* usb-bt.c */ diff --git a/hw/usb/host-bsd.c b/hw/usb/host-bsd.c index 07f0e01..39f2281 100644 --- a/hw/usb/host-bsd.c +++ b/hw/usb/host-bsd.c @@ -637,9 +637,3 @@ void usb_host_info(Monitor *mon, const QDict *qdict) { usb_host_scan(mon, usb_host_info_device); } - -/* XXX add this */ -int usb_host_device_close(const char *devname) -{ -return 0; -} diff --git a/hw/usb/host-linux.c b/hw/usb/host-linux.c index c18a6c8..b67aeba 100644 --- a/hw/usb/host-linux.c +++ b/hw/usb/host-linux.c @@ -1540,30 +1540,6 @@ static void usb_host_register_types(void) type_init(usb_host_register_types) -int usb_host_device_close(const char *devname) -{ -#if 0 -char product_name[PRODUCT_NAME_SZ]; -int bus_num, addr; -USBHostDevice *s; - -if (strstr(devname, auto:)) { -return usb_host_auto_del(devname); -} -if (usb_host_find_device(bus_num, addr, product_name, -sizeof(product_name), devname) 0) { -return -1; -} -s = hostdev_find(bus_num, addr); -if (s) { -usb_device_delete_addr(s-bus_num, s-dev.addr); -return 0; -} -#endif - -return -1; -} - /* * Read sys file-system device file * diff --git a/hw/usb/host-stub.c b/hw/usb/host-stub.c index 8affba7..28d8032 100644 --- a/hw/usb/host-stub.c +++ b/hw/usb/host-stub.c @@ -45,8 +45,3 @@ USBDevice *usb_host_device_open(USBBus *bus, const char *devname) { return NULL; } - -int usb_host_device_close(const char *devname) -{ -return 0; -} diff --git a/vl.c b/vl.c index c5b0eea..955d2ff 100644 --- a/vl.c +++ b/vl.c @@ -1427,8 +1427,9 @@ static int usb_device_del(const char *devname) int bus_num, addr; const char *p; -if (strstart(devname, host:, p)) -return usb_host_device_close(p); +if (strstart(devname, host:, p)) { +return -1; +} if (!usb_enabled(false)) { return -1; -- 1.7.9.7
Re: [Qemu-devel] [RFC PATCH v2 19/23] qcow2: Add error handling to the l2meta coroutine
On Thu, Feb 21, 2013 at 10:35:42AM +0100, Kevin Wolf wrote: On Mon, Feb 18, 2013 at 04:42:55PM +0100, Stefan Hajnoczi wrote: On Wed, Feb 13, 2013 at 02:22:09PM +0100, Kevin Wolf wrote: diff --git a/block/qcow2.c b/block/qcow2.c index 57552aa..2819336 100644 --- a/block/qcow2.c +++ b/block/qcow2.c @@ -774,11 +774,33 @@ static void coroutine_fn process_l2meta(void *opaque) m-sleeping = false; } +again: qemu_co_mutex_lock(s-lock); ret = qcow2_alloc_cluster_link_l2(bs, m); if (ret 0) { -/* FIXME */ +/* + * This is a nasty situation: We have already completed the allocation + * write request and returned success, so just failing it isn't + * possible. We need to make sure to return an error during the next + * flush. + * + * However, we still can't drop the l2meta because we want I/O errors + * to be recoverable e.g. after the block device has been grown or the + * network connection restored. Sleep until the next flush comes and + * then retry. + */ A failed flush is live migrated by hw/virtio-blk.c but what happens when we fail during drain? That's a very good questions. Looks like things become rather hairy... This would be a case where we really need a VMState for block drivers (which is in fact how the whole rerror/werror handling would have been implemented best). Juan, any chance to introduce such a thing without breaking everything? Is there something like optional top-level sections? In fact, don't we have the same problem today, when flushing the image on the source fails during completion of the migration? With this series it just becomes much more likely to happen in practice. Kevin
[Qemu-devel] [PATCH 02/14] fix scripts/make_device_config.sh
Make it handle multiple include statements in a file: (1) The printf needs a space so the include files will be separated. (2) Also $f can contain multiple failes, so redirection will not work and we have to use cat to process all files. Signed-off-by: Gerd Hoffmann kra...@redhat.com --- scripts/make_device_config.sh |2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/scripts/make_device_config.sh b/scripts/make_device_config.sh index 0778fe2..81fe942 100644 --- a/scripts/make_device_config.sh +++ b/scripts/make_device_config.sh @@ -18,7 +18,7 @@ process_includes () { f=$src while [ -n $f ] ; do - f=`tr -d '\r' $f | awk '/^include / {printf '$src_dir'/%s, $2}'` + f=`cat $f | tr -d '\r' | awk '/^include / {printf '$src_dir'/%s , $2}'` [ $? = 0 ] || exit 1 all_includes=$all_includes $f done -- 1.7.9.7
[Qemu-devel] [PATCH 05/14] usb-storage: use scsi_req_enqueue return value
Signed-off-by: Gerd Hoffmann kra...@redhat.com --- hw/usb/dev-storage.c |5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/hw/usb/dev-storage.c b/hw/usb/dev-storage.c index b89d00f..d3f01aa 100644 --- a/hw/usb/dev-storage.c +++ b/hw/usb/dev-storage.c @@ -400,6 +400,7 @@ static void usb_msd_handle_data(USBDevice *dev, USBPacket *p) struct usb_msd_cbw cbw; uint8_t devep = p-ep-nr; SCSIDevice *scsi_dev; +uint32_t len; switch (p-pid) { case USB_TOKEN_OUT: @@ -441,8 +442,8 @@ static void usb_msd_handle_data(USBDevice *dev, USBPacket *p) #ifdef DEBUG_MSD scsi_req_print(s-req); #endif -scsi_req_enqueue(s-req); -if (s-req s-req-cmd.xfer != SCSI_XFER_NONE) { +len = scsi_req_enqueue(s-req); +if (len) { scsi_req_continue(s-req); } break; -- 1.7.9.7
[Qemu-devel] [PATCH 11/14] usb: fix endpoint descriptor ordering
Fix the ordering of the endpoint descriptors for superspeed endpoints: The superspeed companion must come first, possible additional descriptors for the endpoint after that. Signed-off-by: Gerd Hoffmann kra...@redhat.com --- hw/usb/desc.c |9 + 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/hw/usb/desc.c b/hw/usb/desc.c index b7c3233..b389381 100644 --- a/hw/usb/desc.c +++ b/hw/usb/desc.c @@ -225,12 +225,9 @@ int usb_desc_endpoint(const USBDescEndpoint *ep, int flags, d-u.endpoint.bRefresh = ep-bRefresh; d-u.endpoint.bSynchAddress = ep-bSynchAddress; } -if (ep-extra) { -memcpy(dest + bLength, ep-extra, extralen); -} if (superlen) { -USBDescriptor *d = (void *)(dest + bLength + extralen); +USBDescriptor *d = (void *)(dest + bLength); d-bLength = 0x06; d-bDescriptorType = USB_DT_ENDPOINT_COMPANION; @@ -243,6 +240,10 @@ int usb_desc_endpoint(const USBDescEndpoint *ep, int flags, usb_hi(ep-wBytesPerInterval); } +if (ep-extra) { +memcpy(dest + bLength + superlen, ep-extra, extralen); +} + return bLength + extralen + superlen; } -- 1.7.9.7
[Qemu-devel] [PATCH 4/5] ppc: fix bamboo 256MB RAM initialization in hw/ppc4xx_devs.c
From: Alin Tomescu tomescu.a...@gmail.com I was trying to launch a PowerPC bamboo machine with more than 256MB of RAM with qemu-system-ppc -M bamboo -kernel $kernel -initrd $ramdisk -m 512, but QEMU would just hang. However, when I used -m 256, the machine would boot. I looked through the code in hw/ and it seems there is an error when the RAM memory is setup (if my understanding is correct). After patching it, the machine launched and booted successfully with 512MB of RAM. Signed-off-by: Alin Tomescu tomescu.a...@gmail.com Signed-off-by: Stefan Hajnoczi stefa...@redhat.com --- hw/ppc4xx_devs.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/hw/ppc4xx_devs.c b/hw/ppc4xx_devs.c index 5e491bc..b6bb0e1 100644 --- a/hw/ppc4xx_devs.c +++ b/hw/ppc4xx_devs.c @@ -700,7 +700,7 @@ ram_addr_t ppc4xx_sdram_adjust(ram_addr_t ram_size, int nr_banks, vmstate_register_ram_global(ram_memories[i]); ram_bases[i] = base; ram_sizes[i] = bank_size; -base += ram_size; +base += bank_size; size_left -= bank_size; break; } -- 1.8.1.2
[Qemu-devel] [PATCH 08/14] usb: add usb_ep_set_halted
Signed-off-by: Gerd Hoffmann kra...@redhat.com --- hw/usb.h |1 + hw/usb/core.c |6 ++ 2 files changed, 7 insertions(+) diff --git a/hw/usb.h b/hw/usb.h index 90024a4..af86fbd 100644 --- a/hw/usb.h +++ b/hw/usb.h @@ -417,6 +417,7 @@ void usb_ep_set_max_packet_size(USBDevice *dev, int pid, int ep, uint16_t raw); int usb_ep_get_max_packet_size(USBDevice *dev, int pid, int ep); void usb_ep_set_pipeline(USBDevice *dev, int pid, int ep, bool enabled); +void usb_ep_set_halted(USBDevice *dev, int pid, int ep, bool halted); USBPacket *usb_ep_find_packet_by_id(USBDevice *dev, int pid, int ep, uint64_t id); diff --git a/hw/usb/core.c b/hw/usb/core.c index d057aab..5517797 100644 --- a/hw/usb/core.c +++ b/hw/usb/core.c @@ -755,6 +755,12 @@ void usb_ep_set_pipeline(USBDevice *dev, int pid, int ep, bool enabled) uep-pipeline = enabled; } +void usb_ep_set_halted(USBDevice *dev, int pid, int ep, bool halted) +{ +struct USBEndpoint *uep = usb_ep_get(dev, pid, ep); +uep-halted = halted; +} + USBPacket *usb_ep_find_packet_by_id(USBDevice *dev, int pid, int ep, uint64_t id) { -- 1.7.9.7
Re: [Qemu-devel] [PATCH V10 0/5] VMXNET3 paravirtual NIC device implementation
Hi Dmitry, The net multiqueue feature went into QEMU 1.4 and conflicts with vmxnet3.c. Please post a rebased version onto qemu.git/master so vmxnet3 can be merged. I'm currently getting the following compiler errors with these patches: hw/vmxnet3.c: In function ‘vmxnet3_set_variable_mac’: hw/vmxnet3.c:438:37: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c: In function ‘vmxnet3_send_packet’: hw/vmxnet3.c:680:47: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c: In function ‘vmxnet3_update_features’: hw/vmxnet3.c:1285:31: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c: In function ‘vmxnet3_can_receive’: hw/vmxnet3.c:1715:94: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1715:162: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1715:178: error: initialization from incompatible pointer type [-Werror] hw/vmxnet3.c:1715:178: error: (near initialization for ‘s’) [-Werror] hw/vmxnet3.c:1715:216: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1715:72: error: unused variable ‘offset_must_be_zero’ [-Werror=unused-variable] hw/vmxnet3.c: In function ‘vmxnet3_receive’: hw/vmxnet3.c:1795:94: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1795:162: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1795:178: error: initialization from incompatible pointer type [-Werror] hw/vmxnet3.c:1795:178: error: (near initialization for ‘s’) [-Werror] hw/vmxnet3.c:1795:216: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1795:72: error: unused variable ‘offset_must_be_zero’ [-Werror=unused-variable] hw/vmxnet3.c:1798:37: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c: In function ‘vmxnet3_cleanup’: hw/vmxnet3.c:1830:94: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1830:162: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1830:178: error: initialization from incompatible pointer type [-Werror] hw/vmxnet3.c:1830:178: error: (near initialization for ‘s’) [-Werror] hw/vmxnet3.c:1830:216: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1830:72: error: unused variable ‘offset_must_be_zero’ [-Werror=unused-variable] hw/vmxnet3.c: In function ‘vmxnet3_set_link_status’: hw/vmxnet3.c:1836:94: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1836:162: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1836:178: error: initialization from incompatible pointer type [-Werror] hw/vmxnet3.c:1836:178: error: (near initialization for ‘s’) [-Werror] hw/vmxnet3.c:1836:216: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1836:72: error: unused variable ‘offset_must_be_zero’ [-Werror=unused-variable] hw/vmxnet3.c: In function ‘vmxnet3_peer_has_vnet_hdr’: hw/vmxnet3.c:1859:34: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c: In function ‘vmxnet3_net_uninit’: hw/vmxnet3.c:1877:32: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c: In function ‘vmxnet3_net_init’: hw/vmxnet3.c:1909:36: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1910:34: error: ‘NICState’ has no member named ‘nc’ hw/vmxnet3.c:1913:37: error: ‘NICState’ has no member named ‘nc’
[Qemu-devel] [PATCH 04/14] allow disabling usb smartcard support
Signed-off-by: Gerd Hoffmann kra...@redhat.com --- hw/Makefile.objs |2 ++ hw/usb/Makefile.objs |1 - 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/hw/Makefile.objs b/hw/Makefile.objs index 447e32a..a1f3a80 100644 --- a/hw/Makefile.objs +++ b/hw/Makefile.objs @@ -38,8 +38,10 @@ common-obj-$(CONFIG_DMA) += dma.o common-obj-$(CONFIG_I82374) += i82374.o common-obj-$(CONFIG_HPET) += hpet.o common-obj-$(CONFIG_APPLESMC) += applesmc.o +ifeq ($(CONFIG_USB_SMARTCARD),y) common-obj-y += ccid-card-passthru.o common-obj-$(CONFIG_SMARTCARD_NSS) += ccid-card-emulated.o +endif common-obj-$(CONFIG_I8259) += i8259_common.o i8259.o common-obj-y += fifo.o common-obj-y += pam.o diff --git a/hw/usb/Makefile.objs b/hw/usb/Makefile.objs index 00998b5..c1e40d7 100644 --- a/hw/usb/Makefile.objs +++ b/hw/usb/Makefile.objs @@ -20,7 +20,6 @@ common-obj-$(CONFIG_USB_NETWORK) += dev-network.o # FIXME: make configurable too CONFIG_USB_BLUETOOTH := y -CONFIG_USB_SMARTCARD := y common-obj-$(CONFIG_USB_BLUETOOTH)+= dev-bluetooth.o common-obj-$(CONFIG_USB_SMARTCARD)+= dev-smartcard-reader.o -- 1.7.9.7
[Qemu-devel] [PATCH 01/14] usb: Makefile cleanup
Group files, sprinkle in some comments. Signed-off-by: Gerd Hoffmann kra...@redhat.com --- hw/usb/Makefile.objs | 27 --- 1 file changed, 20 insertions(+), 7 deletions(-) diff --git a/hw/usb/Makefile.objs b/hw/usb/Makefile.objs index d1bbbc0..bfe5e5f 100644 --- a/hw/usb/Makefile.objs +++ b/hw/usb/Makefile.objs @@ -1,14 +1,27 @@ +# usb subsystem core +common-obj-y += core.o combined-packet.o bus.o desc.o +common-obj-y += libhw.o + +# usb host adapters common-obj-$(CONFIG_USB_UHCI) += hcd-uhci.o common-obj-$(CONFIG_USB_OHCI) += hcd-ohci.o common-obj-$(CONFIG_USB_EHCI) += hcd-ehci.o hcd-ehci-pci.o hcd-ehci-sysbus.o common-obj-$(CONFIG_USB_XHCI) += hcd-xhci.o -common-obj-y += libhw.o +# emulated usb devices +common-obj-y += dev-hub.o +common-obj-y += dev-hid.o +common-obj-y += dev-wacom.o +common-obj-y += dev-storage.o +common-obj-y += dev-uas.o +common-obj-y += dev-smartcard-reader.o +common-obj-y += dev-audio.o +common-obj-y += dev-serial.o +common-obj-y += dev-network.o +common-obj-y += dev-bluetooth.o + +# usb redirection common-obj-$(CONFIG_USB_REDIR) += redirect.o quirks.o -common-obj-y += core.o combined-packet.o bus.o desc.o dev-hub.o -common-obj-y += host-$(HOST_USB).o dev-bluetooth.o -common-obj-y += dev-hid.o dev-storage.o dev-wacom.o -common-obj-y += dev-serial.o dev-network.o dev-audio.o -common-obj-y += dev-smartcard-reader.o -common-obj-y += dev-uas.o +# usb pass-through +common-obj-y += host-$(HOST_USB).o -- 1.7.9.7
Re: [Qemu-devel] [PATCH 4/4] piix_pci: Implement reset for i440FX PAM configuration
On Thu, 2013-02-21 at 09:17 +, David Woodhouse wrote: Thanks. I suppose I'd better test that I haven't broken suspend/resume first. I don't care about OS/2 or VDISK, but it's vaguely possible that suspend/resume might be another reset user which actually *would* be offended if the PAM configuration got reset, causing the BIOS to do a complete reinit. If that breaks, this will have to wait for the 'soft-reset' bits that Anthony is looking at. Ah crap, it breaks. Suspend/resume now does a full PAM reset, so SeaBIOS doesn't see that it's a resume and goes through a full hardware init and reboot. -- dwmw2 smime.p7s Description: S/MIME cryptographic signature
[Qemu-devel] [PATCH v5 0/6] Efficient VM backup for qemu
This series provides a way to efficiently backup VMs. * Backup to a single archive file * Backup contain all data to restore VM (full backup) * Do not depend on storage type or image format * Avoid use of temporary storage * store sparse images efficiently The file docs/backup.txt contains more details. Changes since v1: * fix spelling errors * move BackupInfo from BDS to BackupBlockJob * introduce BackupDriver to allow more than one backup format * vma: add suport to store vmstate (size is not known in advance) * add ability to store VM state Changes since v2: * BackupDriver: remove cancel_cb * use enum for BackupFormat * vma: use bdrv_open instead of bdrv_file_open * vma: fix aio, use O_DIRECT * backup one drive after another (try to avoid high load) Changes since v3: * move reviewer info from commit messages to cover-letter * remove 'RFC' from log headers and file names * removed comment about slow qcow2 snapshot bug * fix spelling errors * fixed copyright * change 'backupfile' parameter name to 'backup-file' * change 'config-filename' parameter name to 'config-file' * add documentation for 'devlist' parameter. * rename backup_cancel to backup-cancel Changes since v4: * vma create: write verbose output to stderr (not stdout) * backup.c: use rwlock instead of sleep, remove backup_in_progress_count * BackupDriver: remove '_cb' suffix * include cleanups suggested by Stefan * use CHAR_BIT instead of magic number '8' * implemented bdrv_co_is_allocated_above() - disabled for now because it actually slows down backup speed by 15% * extend regression tests to test unallocated regions Dietmar Maurer (6): add documenation for new backup framework add basic backup support to block driver add backup related monitor commands introduce new vma archive format add regression tests for backup add vm state to backups Makefile |3 +- Makefile.objs|1 + backup.c | 355 + backup.h | 45 +++ block.c | 71 - blockdev.c | 617 ++ docs/backup.txt | 116 ++ docs/specs/vma_spec.txt | 24 ++ hmp-commands.hx | 31 ++ hmp.c| 64 hmp.h|3 + include/block/block.h|2 + include/block/blockjob.h | 10 + monitor.c|7 + qapi-schema.json | 98 + qmp-commands.hx | 27 ++ tests/Makefile | 11 +- tests/backup-test.c | 529 ++ vma-reader.c | 799 +++ vma-writer.c | 940 ++ vma.c| 561 +++ vma.h| 145 +++ 22 files changed, 4450 insertions(+), 9 deletions(-) create mode 100644 backup.c create mode 100644 backup.h create mode 100644 docs/backup.txt create mode 100644 docs/specs/vma_spec.txt create mode 100644 tests/backup-test.c create mode 100644 vma-reader.c create mode 100644 vma-writer.c create mode 100644 vma.c create mode 100644 vma.h -- 1.7.2.5
[Qemu-devel] [PATCH v5 3/6] add backup related monitor commands
We use a generic BackupDriver struct to encapsulate all archive format related function. Another option would be to simply dump devid,cluster_num,cluster_data to the output fh (pipe), and an external binary saves the data. That way we could move the whole archive format related code out of qemu. Signed-off-by: Dietmar Maurer diet...@proxmox.com --- backup.h | 15 ++ blockdev.c | 423 ++ hmp-commands.hx | 31 hmp.c| 63 hmp.h|3 + monitor.c|7 + qapi-schema.json | 95 qmp-commands.hx | 27 8 files changed, 664 insertions(+), 0 deletions(-) diff --git a/backup.h b/backup.h index 9b1ea1c..22598a6 100644 --- a/backup.h +++ b/backup.h @@ -14,6 +14,9 @@ #ifndef QEMU_BACKUP_H #define QEMU_BACKUP_H +#include uuid/uuid.h +#include block/block.h + #define BACKUP_CLUSTER_BITS 16 #define BACKUP_CLUSTER_SIZE (1BACKUP_CLUSTER_BITS) #define BACKUP_BLOCKS_PER_CLUSTER (BACKUP_CLUSTER_SIZE/BDRV_SECTOR_SIZE) @@ -27,4 +30,16 @@ int backup_job_create(BlockDriverState *bs, BackupDumpFunc *backup_dump_cb, BlockDriverCompletionFunc *backup_complete_cb, void *opaque, int64_t speed); +typedef struct BackupDriver { +const char *format; +void *(*open)(const char *filename, uuid_t uuid, Error **errp); +int (*close)(void *opaque, Error **errp); +int (*register_config)(void *opaque, const char *name, gpointer data, + size_t data_len); +int (*register_stream)(void *opaque, const char *devname, size_t size); +int (*dump)(void *opaque, uint8_t dev_id, int64_t cluster_num, + unsigned char *buf, size_t *zero_bytes); +int (*complete)(void *opaque, uint8_t dev_id, int ret); +} BackupDriver; + #endif /* QEMU_BACKUP_H */ diff --git a/blockdev.c b/blockdev.c index 63e6f1e..84f598d 100644 --- a/blockdev.c +++ b/blockdev.c @@ -20,6 +20,7 @@ #include qmp-commands.h #include trace.h #include sysemu/arch_init.h +#include backup.h static QTAILQ_HEAD(drivelist, DriveInfo) drives = QTAILQ_HEAD_INITIALIZER(drives); @@ -1334,6 +1335,428 @@ void qmp_drive_mirror(const char *device, const char *target, drive_get_ref(drive_get_by_blockdev(bs)); } +/* Backup related function */ + +static void backup_run_next_job(void); + +static struct GenericBackupState { +Error *error; +bool cancel; +uuid_t uuid; +char uuid_str[37]; +int64_t speed; +time_t start_time; +time_t end_time; +char *backup_file; +const BackupDriver *driver; +void *writer; +GList *bcb_list; +size_t total; +size_t transferred; +size_t zero_bytes; +} backup_state; + +typedef struct BackupCB { +BlockDriverState *bs; +uint8_t dev_id; +bool started; +bool completed; +size_t size; +size_t transferred; +size_t zero_bytes; +} BackupCB; + +static int backup_dump_cb(void *opaque, BlockDriverState *bs, + int64_t cluster_num, unsigned char *buf) +{ +BackupCB *bcb = opaque; + +assert(backup_state.driver); +assert(backup_state.writer); +assert(backup_state.driver-dump); + +size_t zero_bytes = 0; +int bytes = backup_state.driver-dump(backup_state.writer, + bcb-dev_id, cluster_num, + buf, zero_bytes); + +if (bytes 0) { +bcb-transferred += bytes; +backup_state.transferred += bytes; +if (zero_bytes) { +bcb-zero_bytes += bytes; +backup_state.zero_bytes += zero_bytes; +} +} + +return bytes; +} + +static void backup_cleanup(void) +{ +if (backup_state.writer backup_state.driver) { +backup_state.end_time = time(NULL); +Error *local_err = NULL; +backup_state.driver-close(backup_state.writer, local_err); +error_propagate(backup_state.error, local_err); +backup_state.writer = NULL; +} + +if (backup_state.bcb_list) { +GList *l = backup_state.bcb_list; +while (l) { +BackupCB *bcb = l-data; +l = g_list_next(l); +drive_put_ref_bh_schedule(drive_get_by_blockdev(bcb-bs)); +g_free(bcb); +} +g_list_free(backup_state.bcb_list); +backup_state.bcb_list = NULL; +} +} + +static void backup_complete_cb(void *opaque, int ret) +{ +BackupCB *bcb = opaque; + +assert(backup_state.driver); +assert(backup_state.writer); +assert(backup_state.driver-complete); +assert(backup_state.driver-close); + +bcb-completed = true; + +backup_state.driver-complete(backup_state.writer, bcb-dev_id, ret); + +if (!backup_state.cancel) { +backup_run_next_job(); +} +} + +static void backup_cancel(void) +{ +backup_state.cancel = true; + +if (!backup_state.error) { +
[Qemu-devel] [PATCH v5 5/6] add regression tests for backup
Simple regression tests using vma-reader and vma-writer. Signed-off-by: Dietmar Maurer diet...@proxmox.com --- tests/Makefile | 11 +- tests/backup-test.c | 529 +++ 2 files changed, 538 insertions(+), 2 deletions(-) create mode 100644 tests/backup-test.c diff --git a/tests/Makefile b/tests/Makefile index 567e36e..136be84 100644 --- a/tests/Makefile +++ b/tests/Makefile @@ -59,6 +59,8 @@ gcov-files-test-mul64-y = util/host-utils.c check-block-$(CONFIG_POSIX) += tests/qemu-iotests-quick.sh +check-backup-y = tests/backup-test$(EXESUF) + # All QTests for now are POSIX-only, but the dependencies are # really in libqtest, not in the testcases themselves. check-qtest-i386-y = tests/fdc-test$(EXESUF) @@ -102,6 +104,7 @@ tests/test-coroutine$(EXESUF): tests/test-coroutine.o $(block-obj-y) libqemuutil tests/test-aio$(EXESUF): tests/test-aio.o $(block-obj-y) libqemuutil.a libqemustub.a tests/test-thread-pool$(EXESUF): tests/test-thread-pool.o $(block-obj-y) libqemuutil.a libqemustub.a tests/test-iov$(EXESUF): tests/test-iov.o libqemuutil.a +tests/backup-test$(EXESUF): tests/backup-test.o vma-reader.o $(block-obj-y) libqemuutil.a libqemustub.a tests/test-hbitmap$(EXESUF): tests/test-hbitmap.o libqemuutil.a libqemustub.a tests/test-x86-cpuid$(EXESUF): tests/test-x86-cpuid.o tests/test-xbzrle$(EXESUF): tests/test-xbzrle.o xbzrle.o page_cache.o libqemuutil.a @@ -213,10 +216,14 @@ check-tests/qemu-iotests-quick.sh: tests/qemu-iotests-quick.sh qemu-img$(EXESUF) # Consolidated targets -.PHONY: check-qtest check-unit check +.PHONY: check-backup check-qtest check-unit check check-qtest: $(patsubst %,check-qtest-%, $(QTEST_TARGETS)) check-unit: $(patsubst %,check-%, $(check-unit-y)) check-block: $(patsubst %,check-%, $(check-block-y)) -check: check-unit check-qtest + +check-backup: tests/backup-test$(EXESUF) + $ + +check: check-unit check-qtest check-backup -include $(wildcard tests/*.d) diff --git a/tests/backup-test.c b/tests/backup-test.c new file mode 100644 index 000..039ac1d --- /dev/null +++ b/tests/backup-test.c @@ -0,0 +1,529 @@ +/* + * QEMU backup test suit + * + * Copyright (C) 2013 Proxmox Server Solutions + * + * Authors: + * Dietmar Maurer (diet...@proxmox.com) + * + * This work is licensed under the terms of the GNU GPL, version 2. See + * the COPYING file in the top-level directory. + * + */ + +#include sys/time.h +#include sys/types.h +#include stdarg.h +#include stdio.h +#include getopt.h +#include libgen.h + +#include qemu-common.h +#include block/block.h + +#include vma.h + +static int opt_debug; +static int opt_loop; + +#define DPRINTF(fmt, ...) \ +do { if (opt_debug) { printf(fmt, ## __VA_ARGS__); } } while (0) + +#define CLUSTER(x) (x*BACKUP_CLUSTER_SIZE) + +#define RUN_TEST(testfunc, speed) \ +backup_test(#testfunc speed #speed, speed, testfunc); + + +static unsigned char buf_sec_pattern_cd[BDRV_SECTOR_SIZE]; +static unsigned char buf_sec_pattern_32[BDRV_SECTOR_SIZE]; + +#define TEST_IMG_SIZE (6*1024*1024+BDRV_SECTOR_SIZE) +#define TEST_IMG_NAME backuptest.raw +#define TEST_IMG_RESTORE_NAME backuptest.raw.restore +#define TEST_VMA_NAME backuptest.vma + +typedef struct BackupCB { +VmaWriter *vmaw; +uint8_t dev_id; +} BackupCB; + +static int backup_dump_cb(void *opaque, BlockDriverState *bs, + int64_t cluster_num, unsigned char *buf) +{ +BackupCB *bcb = opaque; + +DPRINTF(backup_dump_cb C% PRId64 %d\n, cluster_num, bcb-dev_id); + +size_t zb = 0; +if (vma_writer_write(bcb-vmaw, bcb-dev_id, cluster_num, buf, zb) 0) { +printf(backup_dump_cb vma_writer_write failed\n); +return -1; +} + +return 0; +} + +static void backup_complete_cb(void *opaque, int ret) +{ +BackupCB *bcb = opaque; + +DPRINTF(backup_complete_cb %d %d\n, bcb-dev_id, ret); + +if (ret 0) { +vma_writer_set_error(bcb-vmaw, backup_complete_cb %d, ret); +} + +if (vma_writer_close_stream(bcb-vmaw, bcb-dev_id) = 0) { +Error *err = NULL; +if (vma_writer_close(bcb-vmaw, err) != 0) { +g_error(vma_writer_close failed %s, error_get_pretty(err)); +} +} +DPRINTF(backup_complete_cb finish\n); +} + +static void write_sec_pattern_cd(BlockDriverState *bs, int64_t offset) +{ +int ret; + +DPRINTF(write_sec_pattern_cd % PRId64 \n, offset); + +if (offset 0x1ff) { +g_error(write_sec_pattern_cd offset % PRId64 + is not sector aligned\n, offset); +} + +ret = bdrv_write(bs, offset 9, buf_sec_pattern_cd, 1); +if (ret 0) { +g_error(write_sec_pattern_cd % PRId64 failed, offset); +} + +} + +static void read_sec(BlockDriverState *bs, int64_t offset, unsigned char *buf) +{ +DPRINTF(read_sec C% PRId64 start % PRId64 \n, +offsetVMA_CLUSTER_BITS, offset); + +if (offset 0x1ff) { +g_error(read_sec offset % PRId64 is not sector
[Qemu-devel] [PATCH v5 6/6] add vm state to backups
Signed-off-by: Dietmar Maurer diet...@proxmox.com --- blockdev.c | 196 +- hmp.c|3 +- qapi-schema.json |5 +- 3 files changed, 200 insertions(+), 4 deletions(-) diff --git a/blockdev.c b/blockdev.c index 683f7da..dd20631 100644 --- a/blockdev.c +++ b/blockdev.c @@ -22,6 +22,8 @@ #include sysemu/arch_init.h #include backup.h #include vma.h +#include migration/qemu-file.h +#include migration/migration.h static QTAILQ_HEAD(drivelist, DriveInfo) drives = QTAILQ_HEAD_INITIALIZER(drives); @@ -1355,6 +1357,10 @@ static struct GenericBackupState { size_t total; size_t transferred; size_t zero_bytes; +unsigned char buf[BACKUP_CLUSTER_SIZE]; +int buf_index; +size_t buf_cluster_num; +guint8 vmstate_dev_id; } backup_state; typedef struct BackupCB { @@ -1510,10 +1516,170 @@ static void backup_start_jobs(void) backup_run_next_job(); } +static int backup_state_close(void *opaque) +{ +if (!backup_state.buf_index) { +return 0; +} + +size_t zero_bytes = 0; +if (backup_state.buf_index BACKUP_CLUSTER_SIZE) { +memset(backup_state.buf + backup_state.buf_index, 0, + BACKUP_CLUSTER_SIZE - backup_state.buf_index); +} +int bytes = backup_state.driver-dump( +backup_state.writer, backup_state.vmstate_dev_id, +backup_state.buf_cluster_num, +backup_state.buf, zero_bytes); +backup_state.buf_index = 0; + +return bytes 0 ? -1 : 0; +} + +static int backup_state_put_buffer(void *opaque, const uint8_t *buf, + int64_t pos, int size) +{ +assert(backup_state.driver); +assert(backup_state.writer); +assert(backup_state.driver-dump); + +/* Note: our backup driver expects to get whole clusters (64KB) */ + +int ret = size; + +while (size 0) { +int l = BACKUP_CLUSTER_SIZE - backup_state.buf_index; +l = l size ? size : l; +memcpy(backup_state.buf + backup_state.buf_index, buf, l); +backup_state.buf_index += l; +buf += l; +size -= l; +if (backup_state.buf_index == BACKUP_CLUSTER_SIZE) { +size_t zero_bytes = 0; +int bytes = backup_state.driver-dump( +backup_state.writer, backup_state.vmstate_dev_id, +backup_state.buf_cluster_num++, +backup_state.buf, zero_bytes); +backup_state.buf_index = 0; +if (bytes 0) { +return -1; +} +} +} + +return ret; +} + +static const QEMUFileOps backup_file_ops = { +.put_buffer = backup_state_put_buffer, +.close = backup_state_close, +}; + +static void coroutine_fn backup_start_savevm(void *opaque) +{ +assert(backup_state.driver); +assert(backup_state.writer); +int ret; +char *err = NULL; +uint64_t remaining; +int64_t maxlen; +MigrationParams params = { +.blk = 0, +.shared = 0 +}; + +int restart = 0; + +QEMUFile *file = qemu_fopen_ops(NULL, backup_file_ops); + +ret = qemu_savevm_state_begin(file, params); +if (ret 0) { +qemu_fclose(file); +err = g_strdup(qemu_savevm_state_begin failed); +goto abort; +} + +while (1) { +ret = qemu_savevm_state_iterate(file); +remaining = ram_bytes_remaining(); + +if (ret 0) { +qemu_fclose(file); +err = g_strdup_printf(qemu_savevm_state_iterate error %d, ret); +goto abort; +} + +/* stop the VM if we use too much space, + * or if remaining is just a few MB + */ +maxlen = ram_bytes_total(); +size_t cpos = backup_state.buf_cluster_num * BACKUP_CLUSTER_SIZE; +if ((remaining 10) || ((cpos + remaining) = maxlen)) { +if (runstate_is_running()) { +restart = 1; +vm_stop(RUN_STATE_SAVE_VM); + } +} + +if (ret == 1) { /* finished */ +if (runstate_is_running()) { +restart = 1; +vm_stop(RUN_STATE_SAVE_VM); +} + +ret = qemu_savevm_state_complete(file); +if (ret 0) { +qemu_fclose(file); +err = g_strdup(qemu_savevm_state_complete error); +goto abort; + +} else { +if (qemu_fclose(file) 0) { +error_setg(backup_state.error, + backup_start_savevm: qemu_fclose failed); +goto abort; +} +if (backup_state.driver-complete(backup_state.writer, +backup_state.vmstate_dev_id, 0) 0) { +err = g_strdup(backup_start_savevm: complete failed); +goto abort; +} +backup_run_next_job(); +goto out; +
[Qemu-devel] [PATCH v5 2/6] add basic backup support to block driver
Function backup_job_create() creates a block job to backup a block device. The coroutine is started with backup_job_start(). We call backup_do_cow() for each write during backup. That function reads the original data and pass it to backup_dump_cb(). The tracked_request infrastructure is used to serialize access. Currently backup cluster size is hardcoded to 65536 bytes. Signed-off-by: Dietmar Maurer diet...@proxmox.com --- Makefile.objs|1 + backup.c | 355 ++ backup.h | 30 block.c | 71 +- include/block/block.h|2 + include/block/blockjob.h | 10 ++ 6 files changed, 463 insertions(+), 6 deletions(-) create mode 100644 backup.c create mode 100644 backup.h diff --git a/Makefile.objs b/Makefile.objs index a68cdac..df64f70 100644 --- a/Makefile.objs +++ b/Makefile.objs @@ -13,6 +13,7 @@ block-obj-$(CONFIG_POSIX) += aio-posix.o block-obj-$(CONFIG_WIN32) += aio-win32.o block-obj-y += block/ block-obj-y += qapi-types.o qapi-visit.o +block-obj-y += backup.o block-obj-y += qemu-coroutine.o qemu-coroutine-lock.o qemu-coroutine-io.o block-obj-y += qemu-coroutine-sleep.o diff --git a/backup.c b/backup.c new file mode 100644 index 000..8955e1a --- /dev/null +++ b/backup.c @@ -0,0 +1,355 @@ +/* + * QEMU backup + * + * Copyright (C) 2013 Proxmox Server Solutions + * + * Authors: + * Dietmar Maurer (diet...@proxmox.com) + * + * This work is licensed under the terms of the GNU GPL, version 2 or later. + * See the COPYING file in the top-level directory. + * + */ + +#include stdio.h +#include errno.h +#include unistd.h + +#include block/block.h +#include block/block_int.h +#include block/blockjob.h +#include qemu/ratelimit.h +#include backup.h + +#define DEBUG_BACKUP 0 + +#define USE_ALLOCATION_CHECK 0 + +#define DPRINTF(fmt, ...) \ +do { if (DEBUG_BACKUP) { printf(backup: fmt, ## __VA_ARGS__); } } \ +while (0) + + +#define SLICE_TIME 1ULL /* ns */ + +typedef struct BackupBlockJob { +BlockJob common; +RateLimit limit; +CoRwlock rwlock; +uint64_t sectors_read; +unsigned long *bitmap; +int bitmap_size; +BackupDumpFunc *backup_dump_cb; +BlockDriverCompletionFunc *backup_complete_cb; +void *opaque; +} BackupBlockJob; + +static bool backup_get_bitmap(BackupBlockJob *job, int64_t cluster_num) +{ +assert(job); +assert(job-bitmap); + +unsigned long val, idx, bit; + +idx = cluster_num / BITS_PER_LONG; + +assert(job-bitmap_size idx); + +bit = cluster_num % BITS_PER_LONG; +val = job-bitmap[idx]; + +return !!(val (1UL bit)); +} + +static void backup_set_bitmap(BackupBlockJob *job, int64_t cluster_num, + bool dirty) +{ +assert(job); +assert(job-bitmap); + +unsigned long val, idx, bit; + +idx = cluster_num / BITS_PER_LONG; + +assert(job-bitmap_size idx); + +bit = cluster_num % BITS_PER_LONG; +val = job-bitmap[idx]; +if (dirty) { +val |= 1UL bit; +} else { +val = ~(1UL bit); +} +job-bitmap[idx] = val; +} + +static int coroutine_fn backup_do_cow(BlockDriverState *bs, + int64_t sector_num, int nb_sectors) +{ +assert(bs); +BackupBlockJob *job = (BackupBlockJob *)bs-job; +assert(job); + +BlockDriver *drv = bs-drv; +struct iovec iov; +QEMUIOVector bounce_qiov; +void *bounce_buffer = NULL; +int ret = 0; + +qemu_co_rwlock_rdlock(job-rwlock); + +int64_t start, end; + +start = sector_num / BACKUP_BLOCKS_PER_CLUSTER; +end = (sector_num + nb_sectors + BACKUP_BLOCKS_PER_CLUSTER - 1) / +BACKUP_BLOCKS_PER_CLUSTER; + +DPRINTF(brdv_co_backup_cow enter %s C% PRId64 % PRId64 %d\n, +bdrv_get_device_name(bs), start, sector_num, nb_sectors); + +for (; start end; start++) { +bool zero = 0; + +if (backup_get_bitmap(job, start)) { +DPRINTF(brdv_co_backup_cow skip C% PRId64 \n, start); +continue; /* already copied */ +} + +/* immediately set bitmap (avoid coroutine race) */ +backup_set_bitmap(job, start, 1); + +DPRINTF(brdv_co_backup_cow C% PRId64 \n, start); + +if (!bounce_buffer) { +iov.iov_len = BACKUP_CLUSTER_SIZE; +iov.iov_base = bounce_buffer = qemu_blockalign(bs, iov.iov_len); +qemu_iovec_init_external(bounce_qiov, iov, 1); +} + +#if USE_ALLOCATION_CHECK +int n = 0; +ret = bdrv_co_is_allocated_above(bs, NULL, + start * BACKUP_BLOCKS_PER_CLUSTER, + BACKUP_BLOCKS_PER_CLUSTER, n); +if (ret 0) { +DPRINTF(brdv_co_backup_cow is_allocated C% PRId64 failed\n, +start); +goto out; +} + +zero = (ret == 0) (n ==
[Qemu-devel] [PATCH v5 1/6] add documenation for new backup framework
Signed-off-by: Dietmar Maurer diet...@proxmox.com --- docs/backup.txt | 116 +++ 1 files changed, 116 insertions(+), 0 deletions(-) create mode 100644 docs/backup.txt diff --git a/docs/backup.txt b/docs/backup.txt new file mode 100644 index 000..927d787 --- /dev/null +++ b/docs/backup.txt @@ -0,0 +1,116 @@ +Efficient VM backup for qemu + +=Requirements= + +* Backup to a single archive file +* Backup needs to contain all data to restore VM (full backup) +* Do not depend on storage type or image format +* Avoid use of temporary storage +* store sparse images efficiently + +=Introduction= + +Most VM backup solutions use some kind of snapshot to get a consistent +VM view at a specific point in time. For example, we previously used +LVM to create a snapshot of all used VM images, which are then copied +into a tar file. + +That basically means that any data written during backup involve +considerable overhead. For LVM we get the following steps: + +1.) read original data (VM write) +2.) write original data into snapshot (VM write) +3.) write new data (VM write) +4.) read data from snapshot (backup) +5.) write data from snapshot into tar file (backup) + +Another approach to backup VM images is to create a new qcow2 image +which use the old image as base. During backup, writes are redirected +to the new image, so the old image represents a 'snapshot'. After +backup, data need to be copied back from new image into the old +one (commit). So a simple write during backup triggers the following +steps: + +1.) write new data to new image (VM write) +2.) read data from old image (backup) +3.) write data from old image into tar file (backup) + +4.) read data from new image (commit) +5.) write data to old image (commit) + +This is in fact the same overhead as before. Other tools like qemu +livebackup produces similar overhead (2 reads, 3 writes). + +Some storage types/formats supports internal snapshots using some kind +of reference counting (rados, sheepdog, dm-thin, qcow2). It would be possible +to use that for backups, but for now we want to be storage-independent. + +=Make it more efficient= + +The be more efficient, we simply need to avoid unnecessary steps. The +following steps are always required: + +1.) read old data before it gets overwritten +2.) write that data into the backup archive +3.) write new data (VM write) + +As you can see, this involves only one read, and two writes. + +To make that work, our backup archive need to be able to store image +data 'out of order'. It is important to notice that this will not work +with traditional archive formats like tar. + +During backup we simply intercept writes, then read existing data and +store that directly into the archive. After that we can continue the +write. + +==Advantages== + +* very good performance (1 read, 2 writes) +* works on any storage type and image format. +* avoid usage of temporary storage +* we can define a new and simple archive format, which is able to + store sparse files efficiently. + +Note: Storing sparse files is a mess with existing archive +formats. For example, tar requires information about holes at the +beginning of the archive. + +==Disadvantages== + +* we need to define a new archive format + +Note: Most existing archive formats are optimized to store small files +including file attributes. We simply do not need that for VM archives. + +* archive contains data 'out of order' + +If you want to access image data in sequential order, you need to +re-order archive data. It would be possible to to that on the fly, +using temporary files. + +Fortunately, a normal restore/extract works perfectly with 'out of +order' data, because the target files are seekable. + +* slow backup storage can slow down VM during backup + +It is important to note that we only do sequential writes to the +backup storage. Furthermore one can compress the backup stream. IMHO, +it is better to slow down the VM a bit. All other solutions creates +large amounts of temporary data during backup. + +=Archive format requirements= + +The basic requirement for such new format is that we can store image +date 'out of order'. It is also very likely that we have less than 256 +drives/images per VM, and we want to be able to store VM configuration +files. + +We have defined a very simply format with those properties, see: + +docs/specs/vma_spec.txt + +Please let us know if you know an existing format which provides the +same functionality. + + -- 1.7.2.5
Re: [Qemu-devel] [PATCH v3 2/6] add basic backup support to block driver
I think you do. You're wasting time reading unallocated clusters and checking that they are zero. bdrv_is_allocated_above gives you the same information much more efficiently. I thought that just returns information if the data is allocated, or if data is on backing file? Or is data guaranteed to be zero if bdrv_is_allocated_above() return 0? Oh, I need to pass NULL for base to get that information? I just posted v5 of the patch. But I get a slow down of 15% if I use bdrv_is_allocated_above. (tested with empty qcow2 files.) Please can you take a look at the code - maybe I am doing something wrong?
Re: [Qemu-devel] scp during migration with vhost fails
On Thu, Feb 21, 2013 at 05:57:04PM +0800, Jason Wang wrote: On 02/21/2013 12:48 AM, Michael S. Tsirkin wrote: On Wed, Feb 20, 2013 at 04:23:52PM +0200, Michael S. Tsirkin wrote: On Fri, Feb 01, 2013 at 06:03:32PM +0800, Jason Wang wrote: Hello all: During testing, I find doing scp during migration with vhost fails with warnings in guest like: Corrupted MAC on input. Disconnecting: Packet corrupt. lost connection Here's the bisect result: Commit a01672d3968cf91208666d371784110bfde9d4f8 kvm: convert to MemoryListener API is the last commit that works well. With commit 04097f7c5957273c578f72b9bd603ba6b1d69e33 vhost: convert to MemoryListener API, guest network is unusable with warning of bad gso type With commit d743c382861eaa1e13f503b05aba5a382a7e7f7c vhost: fix incorrect userspace address, guest network is available, but scp during migration may fail. Looks like the issue is related to memory api, any thoughts? Thanks Tried to reproduce this for a while without success. Which command line was used? -- MST Could be we are not syncing all that we should? Does the following hack make the problem go away? diff --git a/hw/vhost.c b/hw/vhost.c index 8d41fdb..a7a0412 100644 --- a/hw/vhost.c +++ b/hw/vhost.c @@ -69,6 +69,8 @@ static int vhost_sync_dirty_bitmap(struct vhost_dev *dev, hwaddr end_addr) { int i; +start_addr = 0x0; +end_addr = ~0x0ull; if (!dev-log_enabled || !dev-started) { return 0; Still can reproduce with this. From the bisect result, the vhost dirty bitmap sync itself looks ok but something wrong when converting to memory listener. Reading the code carefully, I found two bugs introduced during this conversion. Patch below, could you please try? vhost: memory sync fixes This fixes two bugs related to memory sync during migration: - ram address calculation was missing the chunk address, so the wrong page was dirtied - one after last was used instead of the end address of a region, which might overflow to 0 and cause us to skip the region when the region ends at ~0x0ull. Signed-off-by: Michael S. Tsirkin m...@redhat.com --- diff --git a/hw/vhost.c b/hw/vhost.c index 8d41fdb..dbf6b46 100644 --- a/hw/vhost.c +++ b/hw/vhost.c @@ -55,7 +55,7 @@ static void vhost_dev_sync_region(struct vhost_dev *dev, ffsll(log) : ffs(log))) { ram_addr_t ram_addr; bit -= 1; -ram_addr = section-offset_within_region + bit * VHOST_LOG_PAGE; +ram_addr = section-offset_within_region + addr + bit * VHOST_LOG_PAGE; memory_region_set_dirty(section-mr, ram_addr, VHOST_LOG_PAGE); log = ~(0x1ull bit); } @@ -94,7 +94,7 @@ static void vhost_log_sync(MemoryListener *listener, struct vhost_dev *dev = container_of(listener, struct vhost_dev, memory_listener); hwaddr start_addr = section-offset_within_address_space; -hwaddr end_addr = start_addr + section-size; +hwaddr end_addr = start_addr + section-size - 1; vhost_sync_dirty_bitmap(dev, section, start_addr, end_addr); }
Re: [Qemu-devel] [PATCHv2] NVMe: Initial commit for NVM Express device
On Fri, Dec 14, 2012 at 05:44:37PM -0700, Keith Busch wrote: NVM Express is an open standard for PCI-e attached Non-Volatile Memory storage. This commit adds an emulated device that supports the register interface and command set defined by this standard. The standard can be viewed at nvmexpress.org. Cc: Michael S. Tsirkin m...@redhat.com Cc: Keith Busch keith.bu...@gmail.com Signed-off-by: Keith Busch keith.bu...@intel.com --- Thanks to everyone I've received comments from first attempt. Apparently there are _rules_ my emulated device needs to follow in order to run correctly in this environment. :) The most major change is none of the routines run in their own threads anymore. They are all timer callbacks that take the BQL. This single threads processes I was trying to parallelize before, so some of the code is simpler, albiet runs a little slower. The device uses the qemu block interface to communicate with the backing storage that represents the non-volatile memory of the nvme device. I split the code into a header and c file. I know this is fairly large, but I don't see a nice way to significantly split this into multiple commits without crippling the functionality. There are some optional features here that could potenetially be removed from the initial commmit, but they don't take an appreciable amount of code space. A lot had to change from the first revision, so my apologies if I missed or misunderstood something from the previous comments. First of all, sorry for not commenting on this patch earlier. I was planning to have a look since I saw the mail in early January, but I never actually got around to doing it. The patch didn't even compile since I first applied to my working copy; I suspect the include file reorganisation is to blame, so this should be enough to fix. I didn't review much of it in great detail, but I have taken a look at the parts interfacing with the block layer. I'll add some comments inline: +#define min(x, y) ((x) (y) ? (x) : (y)) qemu-common.h already has MIN(). +static uint16_t nvme_map_prp(NvmeRequest *req, uint64_t prp1, uint64_t prp2, +uint32_t len, int data_dir, NvmeCtrl *n) +{ +hwaddr req_len, trans_len = n-page_size - (prp1 % n-page_size); +req_len = trans_len = min(len, trans_len); +int num_prps = (len n-page_bits) + 1; +void *addr; + +if (!prp1) { +NVME_LOG(ERR, null prp1); +return NVME_INVALID_FIELD | NVME_DNR; +} + +NVME_LOG(IO_DBG, +ctrl:%u page size:%u prp1:%PRIx64 prp2:%PRIx64 len:%u dir:%d, +n-instance, n-page_size, prp1, prp2, len, data_dir); + +qemu_iovec_init(req-qiov, num_prps); +addr = cpu_physical_memory_map(prp1, trans_len, data_dir); +if (!addr || req_len != trans_len) { +NVME_LOG(ERR, +unable to map data bytes:%PRIu64 from address:%PRIx64, +trans_len, prp1); +return NVME_INTERNAL_DEV_ERROR; +} +NVME_LOG(IO_DBG, mapped prp1:%PRIx64 to %p len:%PRIu64, prp1, addr, +trans_len); +qemu_iovec_add(req-qiov, addr, trans_len); + +len -= trans_len; +if (len) { +if (!prp2) { +NVME_LOG(ERR, null prp2); +return NVME_INVALID_FIELD | NVME_DNR; +} +if (len n-page_size) { +uint64_t prp_list[n-max_prp_ents], nents, prp_trans; +int i = 0; + +nents = (uint64_t)((len + n-page_size - 1) n-page_bits); +prp_trans = min(n-max_prp_ents, nents) * sizeof(uint64_t); +cpu_physical_memory_rw(prp2, (uint8_t *)prp_list, prp_trans, 0); + +while (len != 0) { +if (i == n-max_prp_ents - 1 len n-page_size) { +if (!prp_list[i] || prp_list[i] (n-page_size - 1)) { +NVME_LOG(ERR, +null or unaligned prp chain:%u entry %PRIx64, i, +prp_list[i]); +return NVME_INVALID_FIELD | NVME_DNR; +} +nents = (uint64_t)((len + n-page_size - 1) +n-page_bits); +prp_trans = min(n-max_prp_ents, nents) * sizeof(uint64_t); +cpu_physical_memory_rw(prp_list[i], (uint8_t *)prp_list, +prp_trans, 0); +i = 0; +} +if (!prp_list[i] || prp_list[i] (n-page_size - 1)) { +NVME_LOG(ERR, +null or unaligned prp list:%u entry %PRIx64, +i, prp_list[i]); +return NVME_INVALID_FIELD | NVME_DNR; +} + +req_len = trans_len = min(len, n-page_size); +addr = cpu_physical_memory_map(prp_list[i], trans_len, +data_dir); +if (!addr || req_len != trans_len) { +
Re: [Qemu-devel] Live migration using qcow2
The problem is about cache coherency. Local files work just fine with cache=writeback, but if you migrate to a different host, you get the problem that the destination kernel may cache some parts of the image while the source is still writing to it. When you do the actual switch to the destination host and the backend doesn't take care of invalidating that cache, you might (partially) read outdated data. Isn't there a way to force a cache flush?
Re: [Qemu-devel] [PATCH 32/41] qemu-file: add writable socket QEMUFile
+static int socket_put_buffer(void *opaque, const uint8_t *buf, int64_t pos, int size) +{ +QEMUFileSocket *s = opaque; +ssize_t len; + +len = qemu_send_full(s-fd, buf, size, 0); +if (len == -1) { +len = -socket_error(); +} We won't always detect partial buffer write here Why not check len size? this way you won't need to change qemu_send_full Ok. Paolo +return len; +} + static int socket_close(void *opaque) { QEMUFileSocket *s = opaque; @@ -369,12 +381,29 @@ static const QEMUFileOps socket_read_ops = { .close = socket_close }; -QEMUFile *qemu_fopen_socket(int fd) +static const QEMUFileOps socket_write_ops = { +.get_fd = socket_get_fd, +.put_buffer = socket_put_buffer, +.close = socket_close +}; + +QEMUFile *qemu_fopen_socket(int fd, const char *mode) { QEMUFileSocket *s = g_malloc0(sizeof(QEMUFileSocket)); +if (mode == NULL || + (mode[0] != 'r' mode[0] != 'w') || + mode[1] != 'b' || mode[2] != 0) { +fprintf(stderr, qemu_fopen: Argument validity check failed\n); +return NULL; +} + s-fd = fd; -s-file = qemu_fopen_ops(s, socket_read_ops); +if (mode[0] == 'w') { +s-file = qemu_fopen_ops(s, socket_write_ops); +} else { +s-file = qemu_fopen_ops(s, socket_read_ops); +} return s-file; } diff --git a/util/osdep.c b/util/osdep.c index 5b51a03..be168e5 100644 --- a/util/osdep.c +++ b/util/osdep.c @@ -243,8 +243,12 @@ ssize_t qemu_write_full(int fd, const void *buf, size_t count) while (count) { ret = write(fd, buf, count); if (ret 0) { -if (errno == EINTR) +if (errno == EINTR) { continue; +} +if (total == 0) { +total = ret; +} I don't like it, first it only detect the first write failure (if the error happens when total !=0 the function won't return -1). Secondly this behavior is different from the function documentation. Regards, Orit break; }
Re: [Qemu-devel] [PATCH v2 2/2] qom/object.c: Allow itf cast with num_itfs = 0
diff --git a/qom/object.c b/qom/object.c index 4b72a64..3d638ff 100644 --- a/qom/object.c +++ b/qom/object.c @@ -449,7 +449,8 @@ ObjectClass *object_class_dynamic_cast(ObjectClass *class, TypeImpl *type = class-type; ObjectClass *ret = NULL; -if (type-num_interfaces type_is_ancestor(target_type, type_interface)) { +if (type-class-interfaces +type_is_ancestor(target_type, type_interface)) { int found = 0; GSList *i; Series looks good, thanks! Can I take that as an RB or acked-by? :-) I try to stay as far as possible from QOM these days, but people don't let me... :) Yes, it is a Reviewed-by. Paolo
Re: [Qemu-devel] [RFC PATCH v2 20/23] qcow2: Cancel COW when overwritten
On Thu, Feb 21, 2013 at 10:47:05AM +0100, Kevin Wolf wrote: On Mon, Feb 18, 2013 at 04:46:49PM +0100, Stefan Hajnoczi wrote: On Wed, Feb 13, 2013 at 02:22:10PM +0100, Kevin Wolf wrote: @@ -707,6 +710,16 @@ int qcow2_alloc_cluster_link_l2(BlockDriverState *bs, QCowL2Meta *m) } /* Update L2 table. */ +qemu_co_mutex_unlock(s-lock); +qemu_co_rwlock_wrlock(m-l2_writeback_lock); +has_wr_lock = true; +qemu_co_mutex_lock(s-lock); + +if (m-no_l2_update) { QcowL2Meta now has a no_l2_update field. A sign that we're abusing the QcowL2Meta struct and really need a different abstraction? I think the abstraction is the right one, even though maybe it could use a rename. Maybe QcowL2Meta - QcowCOWRequest or something. The comment in qcow2.h correctly describes what it's meant for. /** * Describes an in-flight (part of a) write request that writes to clusters * that are not referenced in their L2 table yet. */ typedef struct QCowL2Meta However, I think m-no_l2_update is actually redundant: The goal is that only one request that touches a cluster should be responsible for updating the L2 table, and it makes sense to choose the first one to do that. We already have this information in m-parent: The first one is the root of the tree described by these parent links. So if I'm not mistaken, m-no_l2_update == (m-parent != NULL). Okay, that makes sense. Stefan
Re: [Qemu-devel] [PATCH RESEND for-1.4] make_device_config.sh: Fix target path in generated dependency file
On 24 January 2013 15:47, Andreas Färber afaer...@suse.de wrote: config-devices.mak.d is included from Makefile.target, i.e. from inside the *-softmmu/ directory. It included the directory path, so never applied to the actual ./config-devices.mak. Symptoms were spurious build failures due to missing dependency on default-configs/pci.mak. Fix this by using `basename` to strip the directory path. This patch seems to break the case it claims to be fixing: (1) touching arm-softmmu.mak correctly provokes us to rebuild: cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. cam-vm-266:precise:qemu$ touch default-configs/arm-softmmu.mak cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak /bin/sh /home/petmay01/linaro/qemu-from-laptop/qemu/scripts/make_device_config.sh arm-softmmu/config-devices.mak default-configs/arm-softmmu.mak cat arm-softmmu/config-devices.mak | grep =y | sort -u config-all-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. (2) but touching pci.mak does not: cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. cam-vm-266:precise:qemu$ touch default-configs/pci.mak cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. (3) git revert 23bf49b5ec and rm arm-softmmu/config-devices.mak* and then things work: cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. cam-vm-266:precise:qemu$ touch default-configs/arm-softmmu.mak cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak /bin/sh /home/petmay01/linaro/qemu-from-laptop/qemu/scripts/make_device_config.sh arm-softmmu/config-devices.mak default-configs/arm-softmmu.mak cat arm-softmmu/config-devices.mak | grep =y | sort -u config-all-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. cam-vm-266:precise:qemu$ touch default-configs/pci.mak cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak /bin/sh /home/petmay01/linaro/qemu-from-laptop/qemu/scripts/make_device_config.sh arm-softmmu/config-devices.mak default-configs/arm-softmmu.mak cat arm-softmmu/config-devices.mak | grep =y | sort -u config-all-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. In particular the commit message claims config-devices.mak.d is included from Makefile.target but this is wrong -- this is done from the top level Makefile via the line -include $(SUBDIR_DEVICES_MAK_DEP). This is why you need to have the full path in the emitted dependency line. -- PMM
Re: [Qemu-devel] [PATCH v4 1/6] add documenation for new backup framework
On Thu, Feb 21, 2013 at 05:14:04AM +, Dietmar Maurer wrote: Thanks for writing this up. I don't think docs/backup.txt should be committed as-is though because it refers to you proposing this patch series. Once merged some of this document will no longer be relevant. Why will it be no longer relevant? It explain the basic idea. You could include this in the patch series cover letter instead. I use 'git' to have a versioning system. using cover-lettter instead defeats that purpose. It's a statement about the patch series at a given point in time. It will quickly become outdated on the code is extended/modified. I guess the cover letter is the wrong place, but commit messages would be the right place. Then it is versioned by git but refers to a specific tree so it doesn't become outdated like a file in the source tree would. Also, Please let us know if you know an existing format which provides the same functionality sounds like you are addressing patch reviewers. Stefan
Re: [Qemu-devel] [PATCH v4 2/6] add basic backup support to block driver
On Thu, Feb 21, 2013 at 05:23:30AM +, Dietmar Maurer wrote: +static void coroutine_fn backup_run(void *opaque) { +BackupBlockJob *job = opaque; +BlockDriverState *bs = job-common.bs; +assert(bs); + +int64_t start, end; + +start = 0; +end = (bs-total_sectors + BACKUP_BLOCKS_PER_CLUSTER - 1) / +BACKUP_BLOCKS_PER_CLUSTER; + +DPRINTF(backup_run start %s %zd %zd\n, bdrv_get_device_name(bs), +start, end); + +int ret = 0; + +for (; start end; start++) { +if (block_job_is_cancelled(job-common)) { +ret = -1; +break; +} + +/* we need to yield so that qemu_aio_flush() returns. + * (without, VM does not reboot) +* Note: use 1000 instead of 0 (0 prioritize this task too + much) indentation What does 0 prioritize this task too much mean? If no rate limit has been set the job should run at full speed. We should not hardcode arbitrary delays like 1000. The VM itself gets somehow slower during backup - do not know why. As workaround sleep 1000 works. Please find out why, it's a bug that an arbitrary sleep hides but doesn't fix (plus the sleep makes backup less efficient). If the VM becomes slow this loop is probably spinning without doing blocking I/O and only doing sleep 0. I guess that can happen when you loop over blocks that have already been backed up (bit has been set)? Stefan
Re: [Qemu-devel] [PATCH] move qemu-ga from bin to libexec dir, use $HELPERS
Ping? I received no answer neither to my original question (why qemu-ga is in /usr/bin) nor to this patch. Thanks, /mjt 16.02.2013 22:28, Michael Tokarev wrote: This patch does 3 things: 1. Renames HELPERS-y Makefile variable to HELPERS 2. Moves its definition from Makefile to configure 3. Moves qemu-ga binary from TOOLS to HELPERS. The effects are: 1. qemu-ga binary is now installed into libexecdir, not bindir. This is the main effect/motivation of this patch, -- this binary has no business being in a public binary directory, it is a system helper which must be run by a system startup script or some event daemon. 2. Another helper, qemu-bridge-helper, which is already installed in libexecdir, is built only when we're building one of softmmu targets on linux (initially it was just linux-specific, but not softmmu-specific). Signed-off-by: Michael Tokarev m...@tls.msk.ru --- Makefile | 10 -- configure |7 ++- 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/Makefile b/Makefile index 0d9099a..ba0cd98 100644 --- a/Makefile +++ b/Makefile @@ -53,8 +53,6 @@ $(call set-vpath, $(SRC_PATH)) LIBS+=-lz $(LIBS_TOOLS) -HELPERS-$(CONFIG_LINUX) = qemu-bridge-helper$(EXESUF) - ifdef BUILD_DOCS DOCS=qemu-doc.html qemu-tech.html qemu.1 qemu-img.1 qemu-nbd.8 QMP/qmp-commands.txt ifdef CONFIG_VIRTFS @@ -115,7 +113,7 @@ ifeq ($(CONFIG_SMARTCARD_NSS),y) include $(SRC_PATH)/libcacard/Makefile endif -all: $(DOCS) $(TOOLS) $(HELPERS-y) recurse-all +all: $(DOCS) $(TOOLS) $(HELPERS) recurse-all config-host.h: config-host.h-timestamp config-host.h-timestamp: config-host.mak @@ -215,7 +213,7 @@ clean: rm -f qemu-options.def find . -name '*.[oda]' -type f -exec rm -f {} + find . -name '*.l[oa]' -type f -exec rm -f {} + - rm -f $(TOOLS) $(HELPERS-y) qemu-ga TAGS cscope.* *.pod *~ */*~ + rm -f $(TOOLS) $(HELPERS) qemu-ga TAGS cscope.* *.pod *~ */*~ rm -Rf .libs rm -f qemu-img-cmds.h @# May not be present in GENERATED_HEADERS @@ -305,9 +303,9 @@ install: all $(if $(BUILD_DOCS),install-doc) install-sysconfig install-datadir ifneq ($(TOOLS),) $(INSTALL_PROG) $(STRIP_OPT) $(TOOLS) $(DESTDIR)$(bindir) endif -ifneq ($(HELPERS-y),) +ifneq ($(HELPERS),) $(INSTALL_DIR) $(DESTDIR)$(libexecdir) - $(INSTALL_PROG) $(STRIP_OPT) $(HELPERS-y) $(DESTDIR)$(libexecdir) + $(INSTALL_PROG) $(STRIP_OPT) $(HELPERS) $(DESTDIR)$(libexecdir) endif ifneq ($(BLOBS),) set -e; for x in $(BLOBS); do \ diff --git a/configure b/configure index 8789324..304c648 100755 --- a/configure +++ b/configure @@ -3204,6 +3204,7 @@ qemu_confdir=$sysconfdir$confsuffix qemu_datadir=$datadir$confsuffix tools= +helpers= if test $want_tools = yes ; then tools=qemu-img\$(EXESUF) qemu-io\$(EXESUF) $tools if [ $linux = yes -o $bsd = yes -o $solaris = yes ] ; then @@ -3225,9 +3226,12 @@ if test $softmmu = yes ; then fi if [ $linux = yes -o $bsd = yes -o $solaris = yes ] ; then if [ $guest_agent = yes ]; then - tools=qemu-ga\$(EXESUF) $tools + helpers=qemu-ga\$(EXESUF) $helpers fi fi + if [ $linux = yes ] ; then + helpers=qemu-bridge-helper\$(EXESUF) $helpers + fi fi # Mac OS X ships with a broken assembler @@ -3744,6 +3748,7 @@ if test $trace_default = yes; then fi echo TOOLS=$tools $config_host_mak +echo HELPERS=$helpers $config_host_mak echo ROMS=$roms $config_host_mak echo MAKE=$make $config_host_mak echo INSTALL=$install $config_host_mak
Re: [Qemu-devel] [PATCH v3 2/6] add basic backup support to block driver
- Messaggio originale - Da: Dietmar Maurer diet...@proxmox.com A: Paolo Bonzini pbonz...@redhat.com Cc: qemu-devel@nongnu.org Inviato: Giovedì, 21 febbraio 2013 12:40:52 Oggetto: RE: [PATCH v3 2/6] add basic backup support to block driver I think you do. You're wasting time reading unallocated clusters and checking that they are zero. bdrv_is_allocated_above gives you the same information much more efficiently. I thought that just returns information if the data is allocated, or if data is on backing file? Or is data guaranteed to be zero if bdrv_is_allocated_above() return 0? Oh, I need to pass NULL for base to get that information? I just posted v5 of the patch. But I get a slow down of 15% if I use bdrv_is_allocated_above. (tested with empty qcow2 files.) Strange, for an unallocated area bdrv_is_allocated_above and bdrv_read really do the same thing apart from writing the zeroes to the buffer. The code looks okay, does a profile say where the time is being spent? Or does the is_allocated_above ever trigger (are you using metadata preallocation)? BTW, any reason why BACKUP_BLOCKS_PER_CLUSTER is hardcoded and you're not using the cluster size from bdrv_get_info? Paolo
Re: [Qemu-devel] [PATCH RESEND for-1.4] make_device_config.sh: Fix target path in generated dependency file
Am 21.02.2013 13:34, schrieb Peter Maydell: On 24 January 2013 15:47, Andreas Färber afaer...@suse.de wrote: config-devices.mak.d is included from Makefile.target, i.e. from inside the *-softmmu/ directory. It included the directory path, so never applied to the actual ./config-devices.mak. Symptoms were spurious build failures due to missing dependency on default-configs/pci.mak. Fix this by using `basename` to strip the directory path. This patch seems to break the case it claims to be fixing: (1) touching arm-softmmu.mak correctly provokes us to rebuild: cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. cam-vm-266:precise:qemu$ touch default-configs/arm-softmmu.mak cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak /bin/sh /home/petmay01/linaro/qemu-from-laptop/qemu/scripts/make_device_config.sh arm-softmmu/config-devices.mak default-configs/arm-softmmu.mak cat arm-softmmu/config-devices.mak | grep =y | sort -u config-all-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. (2) but touching pci.mak does not: cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. cam-vm-266:precise:qemu$ touch default-configs/pci.mak cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. (3) git revert 23bf49b5ec and rm arm-softmmu/config-devices.mak* and then things work: cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. cam-vm-266:precise:qemu$ touch default-configs/arm-softmmu.mak cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak /bin/sh /home/petmay01/linaro/qemu-from-laptop/qemu/scripts/make_device_config.sh arm-softmmu/config-devices.mak default-configs/arm-softmmu.mak cat arm-softmmu/config-devices.mak | grep =y | sort -u config-all-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. cam-vm-266:precise:qemu$ touch default-configs/pci.mak cam-vm-266:precise:qemu$ make V=1 arm-softmmu/config-devices.mak /bin/sh /home/petmay01/linaro/qemu-from-laptop/qemu/scripts/make_device_config.sh arm-softmmu/config-devices.mak default-configs/arm-softmmu.mak cat arm-softmmu/config-devices.mak | grep =y | sort -u config-all-devices.mak make: `arm-softmmu/config-devices.mak' is up to date. In particular the commit message claims config-devices.mak.d is included from Makefile.target but this is wrong -- this is done from the top level Makefile via the line -include $(SUBDIR_DEVICES_MAK_DEP). This is why you need to have the full path in the emitted dependency line. As discussed on IRC, what happened here it seems is that at the time of writing the patch (two releases ago) we had -include *.d in Makefile.target, so the generated .mak.d files were effectively included from two Makefiles, working for one but not for the other. So effectively we were observing race conditions between Makefile and x86_64-softmmu/Makefile a.k.a. Makefile.target. This seems to have gotten fixed through Paolo's nested-vars handling in rules.mak, which only does -include *.d for directories listed in obj-y etc. So my patch was broken and is now completely broken. :( However I don't see in the curent Makefile.target and rules.mak where the *.d files are being included today, so we may have discovered a different issue that if fixed may reintroduce the original bug again... Paolo? Andreas -- SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg, Germany GF: Jeff Hawn, Jennifer Guild, Felix Imendörffer; HRB 16746 AG Nürnberg
[Qemu-devel] [PATCH 2/9] vring: introduce vring_restore() to restore from img
From: Liu Ping Fan pingf...@linux.vnet.ibm.com Re-initialize the members of vring correctly is required when restored from img. Signed-off-by: Liu Ping Fan pingf...@linux.vnet.ibm.com --- hw/dataplane/vring.c |6 ++ hw/dataplane/vring.h |1 + 2 files changed, 7 insertions(+), 0 deletions(-) diff --git a/hw/dataplane/vring.c b/hw/dataplane/vring.c index 865bd4d..0a540b4 100644 --- a/hw/dataplane/vring.c +++ b/hw/dataplane/vring.c @@ -48,6 +48,12 @@ bool vring_setup(Vring *vring, VirtIODevice *vdev, int n) return true; } +void vring_restore(Vring *vring, uint16_t last_avail_idx) +{ +vring-last_avail_idx = last_avail_idx; +vring-last_used_idx = vring-vr.used-idx; +} + void vring_teardown(Vring *vring) { hostmem_finalize(vring-hostmem); diff --git a/hw/dataplane/vring.h b/hw/dataplane/vring.h index 0d00500..9938bf9 100644 --- a/hw/dataplane/vring.h +++ b/hw/dataplane/vring.h @@ -49,6 +49,7 @@ static inline void vring_set_broken(Vring *vring) vring-broken = true; } +void vring_restore(Vring *vring, uint16_t last_avail_idx); bool vring_setup(Vring *vring, VirtIODevice *vdev, int n); void vring_teardown(Vring *vring); void vring_disable_notification(VirtIODevice *vdev, Vring *vring); -- 1.7.4.4
[Qemu-devel] [PATCH 3/9] event poll: make epoll work for normal fd
From: Liu Ping Fan pingf...@linux.vnet.ibm.com When event poll can work with normal fd, we can port them onto the event loop. Signed-off-by: Liu Ping Fan pingf...@linux.vnet.ibm.com --- hw/dataplane/event-poll.c | 36 hw/dataplane/event-poll.h |8 2 files changed, 44 insertions(+), 0 deletions(-) diff --git a/hw/dataplane/event-poll.c b/hw/dataplane/event-poll.c index 2b55c6e..b7dea53 100644 --- a/hw/dataplane/event-poll.c +++ b/hw/dataplane/event-poll.c @@ -32,6 +32,42 @@ void event_poll_add(EventPoll *poll, EventHandler *handler, } } +void event_poll_add_fd(EventPoll *poll, int fd, uint32_t type, +EventHandler *handler) +{ +struct epoll_event event = { +.events = type, +.data.ptr = handler, +}; + +if (epoll_ctl(poll-epoll_fd, EPOLL_CTL_ADD, fd, event) != 0) { +fprintf(stderr, failed to add event fd handler to epoll: %m\n); +exit(1); +} + +} +void event_poll_del_fd(EventPoll *poll, int fd) +{ +if (epoll_ctl(poll-epoll_fd, EPOLL_CTL_DEL, fd, NULL) != 0) { +fprintf(stderr, failed to del event handler to epoll: %m\n); +exit(1); +} +} + + +void event_poll_modify_fd(EventPoll *poll, int fd, uint32_t type, +EventHandler *handler) +{ +struct epoll_event event = { +.events = type, +.data.ptr = handler, +}; +if (epoll_ctl(poll-epoll_fd, EPOLL_CTL_MOD, fd, event) != 0) { +fprintf(stderr, failed to modify event handler to epoll: %m\n); +exit(1); +} +} + /* Event callback for stopping event_poll() */ static void handle_stop(EventHandler *handler) { diff --git a/hw/dataplane/event-poll.h b/hw/dataplane/event-poll.h index 3e8d3ec..606138c 100644 --- a/hw/dataplane/event-poll.h +++ b/hw/dataplane/event-poll.h @@ -22,6 +22,8 @@ typedef void EventCallback(EventHandler *handler); struct EventHandler { EventNotifier *notifier;/* eventfd */ EventCallback *callback;/* callback function */ +void *opaque; +int fd; /* normal fd*/ }; typedef struct { @@ -32,6 +34,12 @@ typedef struct { void event_poll_add(EventPoll *poll, EventHandler *handler, EventNotifier *notifier, EventCallback *callback); +void event_poll_add_fd(EventPoll *poll, int fd, uint32_t type, +EventHandler *handler); +void event_poll_del_fd(EventPoll *poll, int fd); +void event_poll_modify_fd(EventPoll *poll, int fd, uint32_t type, +EventHandler *handler); + void event_poll_init(EventPoll *poll); void event_poll_cleanup(EventPoll *poll); void event_poll(EventPoll *poll); -- 1.7.4.4
[Qemu-devel] [PATCH 4/9] event poll: pass event type to event callback
From: Liu Ping Fan pingf...@linux.vnet.ibm.com With this extra arg -- event type, we can support the standard events dispatched by epoll_wait() Signed-off-by: Liu Ping Fan pingf...@linux.vnet.ibm.com --- hw/dataplane/event-poll.c |4 ++-- hw/dataplane/event-poll.h |2 +- hw/dataplane/virtio-blk.c |6 +++--- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/hw/dataplane/event-poll.c b/hw/dataplane/event-poll.c index b7dea53..e19f3f3 100644 --- a/hw/dataplane/event-poll.c +++ b/hw/dataplane/event-poll.c @@ -69,7 +69,7 @@ void event_poll_modify_fd(EventPoll *poll, int fd, uint32_t type, } /* Event callback for stopping event_poll() */ -static void handle_stop(EventHandler *handler) +static void handle_stop(EventHandler *handler, uint32_t events) { /* Do nothing */ } @@ -123,7 +123,7 @@ void event_poll(EventPoll *poll) event_notifier_test_and_clear(handler-notifier); /* Handle the event */ -handler-callback(handler); +handler-callback(handler, event.events); } /* Stop event_poll() diff --git a/hw/dataplane/event-poll.h b/hw/dataplane/event-poll.h index 606138c..ff9712b 100644 --- a/hw/dataplane/event-poll.h +++ b/hw/dataplane/event-poll.h @@ -18,7 +18,7 @@ #include qemu/event_notifier.h typedef struct EventHandler EventHandler; -typedef void EventCallback(EventHandler *handler); +typedef void EventCallback(EventHandler *handler, uint32_t events); struct EventHandler { EventNotifier *notifier;/* eventfd */ EventCallback *callback;/* callback function */ diff --git a/hw/dataplane/virtio-blk.c b/hw/dataplane/virtio-blk.c index 4c4ad84..b60211a 100644 --- a/hw/dataplane/virtio-blk.c +++ b/hw/dataplane/virtio-blk.c @@ -206,7 +206,7 @@ static int process_request(IOQueue *ioq, struct iovec iov[], return 0; } -static void handle_notify(EventHandler *handler) +static void handle_notify(EventHandler *handler, uint32_t type) { VirtIOBlockDataPlane *s = container_of(handler, VirtIOBlockDataPlane, notify_handler); @@ -284,7 +284,7 @@ static void handle_notify(EventHandler *handler) } } -static void handle_io(EventHandler *handler) +static void handle_io(EventHandler *handler, uint32_t type) { VirtIOBlockDataPlane *s = container_of(handler, VirtIOBlockDataPlane, io_handler); @@ -298,7 +298,7 @@ static void handle_io(EventHandler *handler) * requests. */ if (unlikely(vring_more_avail(s-vring))) { -handle_notify(s-notify_handler); +handle_notify(s-notify_handler, type); } } -- 1.7.4.4
[Qemu-devel] [PATCH 6/9] virtio net: introduce dataplane for virtio net
From: Liu Ping Fan pingf...@linux.vnet.ibm.com This is a emulation to virtio-blk dataplane, which push the data handling out of biglock. And it is a try to implement this process in userspace, while vhost-net in kernel. Signed-off-by: Liu Ping Fan pingf...@linux.vnet.ibm.com --- hw/dataplane/virtio-net.c | 422 + hw/dataplane/virtio-net.h | 26 +++ hw/virtio-net.c | 56 +- hw/virtio-net.h | 61 +++ 4 files changed, 517 insertions(+), 48 deletions(-) create mode 100644 hw/dataplane/virtio-net.c create mode 100644 hw/dataplane/virtio-net.h diff --git a/hw/dataplane/virtio-net.c b/hw/dataplane/virtio-net.c new file mode 100644 index 000..9a1795d --- /dev/null +++ b/hw/dataplane/virtio-net.c @@ -0,0 +1,422 @@ +/* Copyright IBM, Corp. 2013 + * + * Based on vhost-net and virtio-blk dataplane code + * + * This work is licensed under the terms of the GNU GPL, version 2. + */ +#include hw/virtio.h +#include qemu/iov.h +#include vring.h +#include linux/virtio_ring.h +#include net/net.h +#include net/checksum.h +#include net/tap.h +#include virtio-net.h +#include qemu/error-report.h + +typedef struct VirtIONetDataPlane { +int async_tx_head; +Vring *rx_vring; +Vring *tx_vring; +EventHandler *rx_handler; +EventHandler *tx_handler; +bool stop; +} VirtIONetDataPlane; + +WorkThread virt_net_thread; + +#define VRING_MAX 128 + +static int32_t virtnet_tx(VirtIONet *n, VirtQueue *vq); + +static void virtnet_tx_complete(struct NetClientState *nc, ssize_t sz) +{ +int ret; +VirtIONet *n = DO_UPCAST(NICState, nc, nc)-opaque; + +vring_push(n-dp-tx_vring, n-dp-async_tx_head, 0); +ret = virtnet_tx(n, n-tx_vq); +if (ret != -EBUSY) { +vring_enable_notification(n-vdev, n-dp-tx_vring); +} +} + +static int virtnet_tx(VirtIONet *n, VirtQueue *vq) +{ +struct iovec out_iov[VRING_MAX], sg[VRING_MAX]; +struct iovec *snd, *end = out_iov[VRING_MAX]; +int head; +unsigned int out_num, in_num, sg_num; +int ret; +int num_packets = 0; + +if (!(n-vdev.status VIRTIO_CONFIG_S_DRIVER_OK)) { +return num_packets; +} + +assert(n-vdev.vm_running); + +if (n-async_tx.elem.out_num) { +return num_packets; +} + +while (true) { +head = vring_pop(n-vdev, n-dp-tx_vring, out_iov, end, out_num, +in_num); +if (head 0) { +break; +} +snd = out_iov; +assert(n-host_hdr_len = n-guest_hdr_len); +if (n-host_hdr_len != n-guest_hdr_len) { +sg_num = iov_copy(sg, ARRAY_SIZE(sg), + out_iov, out_num, + 0, n-host_hdr_len); +sg_num += iov_copy(sg + sg_num, ARRAY_SIZE(sg) - sg_num, + out_iov, out_num, + n-guest_hdr_len, -1); +out_num = sg_num; +snd = sg; +} + +ret = qemu_sendv_packet_async(n-nic-nc, snd, out_num, +virtnet_tx_complete); +if (ret == 0) { +n-dp-async_tx_head = head; +return -EBUSY; +} +vring_push(n-dp-tx_vring, head, 0); +if (num_packets++ n-tx_burst) { +break; +} +} + +return num_packets; +} + +static void virtnet_handle_tx(VirtIODevice *vdev, VirtQueue *vq) +{ +int32 ret; +VirtIONet *n = (VirtIONet *)vdev; + +/* This happens when device was stopped but VCPU wasn't. */ +if (!n-vdev.vm_running) { +return; +} +vring_disable_notification(vdev, n-dp-tx_vring); +ret = virtnet_tx(n, vq); +if (ret != -EBUSY) { +vring_enable_notification(vdev, n-dp-tx_vring); +} +} + + +static int virtio_net_can_receive(NetClientState *nc) +{ +VirtIONet *n = DO_UPCAST(NICState, nc, nc)-opaque; +if (!n-vdev.vm_running) { +return 0; +} +if (!(n-vdev.status VIRTIO_CONFIG_S_DRIVER_OK)) { +return 0; +} + +return 1; +} + +/* peek but not use */ +static int rx_mergeable_buf_sz(VirtIONet *n) +{ +uint16_t start, idx, head; +int total = 0; +Vring *vring = n-dp-rx_vring; +struct vring_desc *dsc; +struct vring_desc *base; + +for (start = vring-last_avail_idx; start != vring-vr.avail-idx; +start++) { +head = start%vring-vr.num; +idx = vring-vr.avail-ring[head]; +if (vring-vr.desc[idx].flags VRING_DESC_F_INDIRECT) { +base = hostmem_lookup(vring-hostmem, vring-vr.desc[idx].addr, +vring-vr.desc[idx].len, 0); +} else { +base = vring-vr.desc; +} +dsc = base; +do { +total += dsc-len; +if (!(dsc-flags VRING_DESC_F_NEXT)) { +break; +} +dsc = base[dsc-next]; +} while (true); +} +return total; +} + +static bool
[Qemu-devel] [PATCH 8/9] virtio net: enable dataplane for virtio net
From: Liu Ping Fan pingf...@linux.vnet.ibm.com Signed-off-by: Liu Ping Fan pingf...@linux.vnet.ibm.com --- hw/virtio-net.c | 38 ++ hw/virtio-net.h |3 +++ hw/virtio-pci.c |2 +- 3 files changed, 42 insertions(+), 1 deletions(-) diff --git a/hw/virtio-net.c b/hw/virtio-net.c index 6bf4a40..d9d6c10 100644 --- a/hw/virtio-net.c +++ b/hw/virtio-net.c @@ -98,10 +98,32 @@ static void virtio_net_vhost_status(VirtIONet *n, uint8_t status) } } +#ifdef CONFIG_VIRTIO_NET_DATA_PLANE +static void virtio_net_dataplane_status(VirtIONet *n, uint8_t status) +{ +if (!!n-dp_start == virtio_net_started(n, status) + !n-nic-nc.peer-link_down) { +return; +} + +if (!n-dp_start) { +virtnet_dataplane_start(n); +n-dp_start = true; +} else { +virtnet_dataplane_stop(n); +n-dp_start = false; +} +} +#endif + static void virtio_net_set_status(struct VirtIODevice *vdev, uint8_t status) { VirtIONet *n = to_virtio_net(vdev); +#ifdef CONFIG_VIRTIO_NET_DATA_PLANE +virtio_net_dataplane_status(n, status); +#endif + virtio_net_vhost_status(n, status); if (!n-tx_waiting) { @@ -422,6 +444,11 @@ static void virtio_net_handle_rx(VirtIODevice *vdev, VirtQueue *vq) { VirtIONet *n = to_virtio_net(vdev); +#ifdef CONFIG_VIRTIO_NET_DATA_PLANE +if (n-dp_start) { +return; +} +#endif qemu_flush_queued_packets(n-nic-nc); } @@ -762,6 +789,11 @@ static void virtio_net_handle_tx_bh(VirtIODevice *vdev, VirtQueue *vq) { VirtIONet *n = to_virtio_net(vdev); +#ifdef CONFIG_VIRTIO_NET_DATA_PLANE +if (n-dp_start) { +return; +} +#endif if (unlikely(n-tx_waiting)) { return; } @@ -1034,6 +1066,9 @@ VirtIODevice *virtio_net_init(DeviceState *dev, NICConf *conf, add_boot_device_path(conf-bootindex, dev, /ethernet-phy@0); +#ifdef CONFIG_VIRTIO_NET_DATA_PLANE +virtnet_dataplane_create(n); +#endif return n-vdev; } @@ -1060,4 +1095,7 @@ void virtio_net_exit(VirtIODevice *vdev) qemu_del_net_client(n-nic-nc); virtio_cleanup(n-vdev); +#ifdef CONFIG_VIRTIO_NET_DATA_PLANE +virtnet_dataplane_destroy(n); +#endif } diff --git a/hw/virtio-net.h b/hw/virtio-net.h index ed91a02..4370ed3 100644 --- a/hw/virtio-net.h +++ b/hw/virtio-net.h @@ -218,6 +218,9 @@ void virtio_net_cleanup(NetClientState *nc); #ifdef CONFIG_VIRTIO_NET_DATA_PLANE void virtnet_dataplane_create(VirtIONet *n); +void virtnet_dataplane_start(VirtIONet *n); +void virtnet_dataplane_stop(VirtIONet *n); +void virtnet_dataplane_destroy(VirtIONet *n); #endif #endif diff --git a/hw/virtio-pci.c b/hw/virtio-pci.c index c7f0c4d..3c478d7 100644 --- a/hw/virtio-pci.c +++ b/hw/virtio-pci.c @@ -969,7 +969,7 @@ static TypeInfo virtio_blk_info = { }; static Property virtio_net_properties[] = { -DEFINE_PROP_BIT(ioeventfd, VirtIOPCIProxy, flags, VIRTIO_PCI_FLAG_USE_IOEVENTFD_BIT, false), +DEFINE_PROP_BIT(ioeventfd, VirtIOPCIProxy, flags, VIRTIO_PCI_FLAG_USE_IOEVENTFD_BIT, true), DEFINE_PROP_UINT32(vectors, VirtIOPCIProxy, nvectors, 3), DEFINE_VIRTIO_NET_FEATURES(VirtIOPCIProxy, host_features), DEFINE_NIC_PROPERTIES(VirtIOPCIProxy, nic), -- 1.7.4.4
[Qemu-devel] [PATCH 0/9] introduce virtio net dataplane
This is a emulation to virtio-blk dataplane, which push the data handling out of biglock. And it is a try to implement this process in userspace, while vhost-net in kernel. The iperf's result show it improving the perfermance of base line, but still slower than vhost-net (maybe the rx path need optimized). Todo: implement fine lock for net-subsystem Liu Ping Fan (9): vring: split the modification and publish of used ring vring: introduce vring_restore() to restore from img event poll: make epoll work for normal fd event poll: pass event type to event callback event poll: enable event poll handle more than one event each time virtio net: introduce dataplane for virtio net tap: make tap peer work on dedicated data-plane thread virtio net: enable dataplane for virtio net configure: make virtio net dataplane configurable configure | 12 ++ hw/dataplane/Makefile.objs |4 +- hw/dataplane/event-poll.c | 69 +-- hw/dataplane/event-poll.h | 14 ++- hw/dataplane/virtio-blk.c |8 +- hw/dataplane/virtio-net.c | 444 hw/dataplane/virtio-net.h | 32 hw/dataplane/vring.c | 37 hw/dataplane/vring.h |3 + hw/virtio-net.c| 94 +- hw/virtio-net.h| 64 +++ hw/virtio-pci.c|2 +- include/net/tap.h |6 + net/tap.c | 92 +- 14 files changed, 806 insertions(+), 75 deletions(-) create mode 100644 hw/dataplane/virtio-net.c create mode 100644 hw/dataplane/virtio-net.h -- 1.7.4.4
[Qemu-devel] [PATCH 7/9] tap: make tap peer work on dedicated data-plane thread
From: Liu Ping Fan pingf...@linux.vnet.ibm.com Signed-off-by: Liu Ping Fan pingf...@linux.vnet.ibm.com --- hw/dataplane/virtio-net.c | 22 +++ hw/dataplane/virtio-net.h |6 +++ include/net/tap.h |6 +++ net/tap.c | 92 - 4 files changed, 125 insertions(+), 1 deletions(-) diff --git a/hw/dataplane/virtio-net.c b/hw/dataplane/virtio-net.c index 9a1795d..c3aac08 100644 --- a/hw/dataplane/virtio-net.c +++ b/hw/dataplane/virtio-net.c @@ -246,6 +246,7 @@ static void rx_cb(EventHandler *handler, uint32_t events) { VirtIONet *n = handler-opaque; +tap_enable_read(n-nic-nc.peer); event_notifier_test_and_clear(handler-notifier); qemu_flush_queued_packets(n-nic-nc); } @@ -388,6 +389,7 @@ void virtnet_dataplane_start(VirtIONet *n) event_poll_add(t-polltbl, n-dp-rx_handler, rx_e, rx_cb); event_poll_add(t-polltbl, n-dp-tx_handler, tx_e, tx_cb); +tap_create_epoll_event(n-nic-nc.peer); } void virtnet_dataplane_stop(VirtIONet *n) @@ -398,6 +400,7 @@ void virtnet_dataplane_stop(VirtIONet *n) event_poll_del_fd(t-polltbl, event_notifier_get_fd(rx_e)); event_poll_del_fd(t-polltbl, event_notifier_get_fd(tx_e)); +tap_del_epoll_event(n-nic-nc.peer); t-state = THREAD_EXIT; event_notifier_set(t-e); @@ -420,3 +423,22 @@ void virtnet_dataplane_destroy(VirtIONet *n) g_free(n-dp-tx_handler); g_free(n-dp); } + +void thread_add_event(WorkThread *t, uint32_t event_type, EventHandler *handler) +{ +event_poll_add_fd(t-polltbl, handler-fd, event_type, handler); +event_notifier_set(t-e); +} + +void thread_del_event(WorkThread *t, EventHandler *handler) +{ +event_poll_del_fd(t-polltbl, handler-fd); +event_notifier_set(t-e); +} + +void thread_modify_event(WorkThread *t, uint32_t event_type, +EventHandler *handler) +{ +event_poll_modify_fd(t-polltbl, handler-fd, event_type, handler); +event_notifier_set(t-e); +} diff --git a/hw/dataplane/virtio-net.h b/hw/dataplane/virtio-net.h index e50b2de..5d6bd34 100644 --- a/hw/dataplane/virtio-net.h +++ b/hw/dataplane/virtio-net.h @@ -23,4 +23,10 @@ typedef struct WorkThread { } WorkThread; extern WorkThread virt_net_thread; + +void thread_add_event(WorkThread *t, uint32_t event_type, +EventHandler *handler); +void thread_del_event(WorkThread *t, EventHandler *handler); +void thread_modify_event(WorkThread *t, uint32_t event_type, +EventHandler *handler); #endif diff --git a/include/net/tap.h b/include/net/tap.h index bb7efb5..3f78d15 100644 --- a/include/net/tap.h +++ b/include/net/tap.h @@ -29,6 +29,12 @@ #include qemu-common.h #include qapi-types.h +#ifdef CONFIG_VIRTIO_NET_DATA_PLANE +int tap_create_epoll_event(NetClientState *nc); +int tap_del_epoll_event(NetClientState *nc); +void tap_enable_read(NetClientState *nc); +#endif + int tap_has_ufo(NetClientState *nc); int tap_has_vnet_hdr(NetClientState *nc); int tap_has_vnet_hdr_len(NetClientState *nc, int len); diff --git a/net/tap.c b/net/tap.c index eb40c42..b6bfed4 100644 --- a/net/tap.c +++ b/net/tap.c @@ -27,6 +27,7 @@ #include config-host.h +#include sys/epoll.h #include sys/ioctl.h #include sys/stat.h #include sys/wait.h @@ -43,6 +44,7 @@ #include net/tap.h #include hw/vhost_net.h +#include hw/dataplane/virtio-net.h /* Maximum GSO packet size (64k) plus plenty of room for * the ethernet and virtio_net headers @@ -61,14 +63,22 @@ typedef struct TAPState { unsigned int has_ufo: 1; VHostNetState *vhost_net; unsigned host_vnet_hdr_len; + +#ifdef CONFIG_VIRTIO_NET_DATA_PLANE +EventHandler tap_evt; +uint32_t tap_events; +bool start; +#endif } TAPState; static int launch_script(const char *setup_script, const char *ifname, int fd); - +#ifndef CONFIG_VIRTIO_NET_DATA_PLANE static int tap_can_send(void *opaque); +#endif static void tap_send(void *opaque); static void tap_writable(void *opaque); +#ifndef CONFIG_VIRTIO_NET_DATA_PLANE static void tap_update_fd_handler(TAPState *s) { qemu_set_fd_handler2(s-fd, @@ -77,18 +87,96 @@ static void tap_update_fd_handler(TAPState *s) s-write_poll ? tap_writable : NULL, s); } +#endif static void tap_read_poll(TAPState *s, int enable) { +#ifdef CONFIG_VIRTIO_NET_DATA_PLANE +if (!s-start) { +return; +} +if (s-read_poll == !!enable) { +return; +} + +s-read_poll = !!enable; +if (enable) { +s-tap_events |= EPOLLIN; +} else { +s-tap_events = ~EPOLLIN; +} +thread_modify_event(virt_net_thread, s-tap_events, s-tap_evt); +#else s-read_poll = !!enable; tap_update_fd_handler(s); +#endif } static void tap_write_poll(TAPState *s, int enable) { +#ifdef CONFIG_VIRTIO_NET_DATA_PLANE +if (!s-start) { +return; +} +if (s-write_poll == !!enable) { +return; +} +s-write_poll = !!enable; +
Re: [Qemu-devel] [PATCH v4 4/6] introduce new vma archive format
On Thu, Feb 21, 2013 at 08:20:28AM +, Dietmar Maurer wrote: Honestly, 64k*4G = 128T is not a limit for me. And we still have one byte reserved, so we can have up to 1P per image, and up to 253 images. For now I have no plans to backup such large VMs. 640k ought to be enough for anybody? Code is easy enough to change that works for now can be good enough. Changing file formats and external interfaces is hard, though, so better get it right the first time. I don't want to get patches for a new format in a year or two just because 128T was enough for the first few users. Hint - look at how the qcow2 file format is specified. You need a lot more details - enough that someone could independently implement a program to read and create vma images that would be compatible with what your implementation produces. The format is really simple, you have the definitions in the header file, and a reference implementation. I am quite sure any experienced developer can write an implementation in a few hours. We do not talk about an extremely complex format like 'qcow2' here. This is not an excuse for lacking details in the spec. Quite the opposite. If someone has to look at your code in order to implement the format, you have failed as a spec writer. Kevin
Re: [Qemu-devel] [PATCH v4 3/6] add backup related monitor commands
On Thu, Feb 21, 2013 at 06:21:32AM +, Dietmar Maurer wrote: +/* add configuration file to archive */ +if (has_config_file) { +char *cdata = NULL; +gsize clen = 0; +GError *err = NULL; +if (!g_file_get_contents(config_file, cdata, clen, err)) { +error_setg(errp, unable to read file '%s', config_file); +goto err; +} + +const char *basename = g_path_get_basename(config_file); +if (driver-register_config_cb(writer, basename, cdata, clen) 0) { +error_setg(errp, register_config failed); +g_free(cdata); +goto err; +} +g_free(cdata); +} This is doing too much inside QEMU. First off, when QEMU is sandboxed or run with SELinux, we cannot expect to be able to access arbitrary files. This is why new QMP commands of this sort usually support file descriptor passing - then a more privileged component can give QEMU access. We can allow to pass fd for that later (if someone really uses it that way). g_file_get_contents() hangs the VM if the file is over NFS while the server is down. This is bad for reliability. The solution is to not pass a path which is on NFS. But that is up to the management tool. Management tools (proxmox, libvirt, or something else) handle the VM configuration. It may not be a single file. Saving external VM configuration is out of scope for QEMU. Backup includes configuration, so you need a way to save that. But I do not really get your suggestion - creating a backup without configuration does not make much sense? In future, we can allow to pass multiple config files - the vma archive format can already handle that. My point is that QEMU has no business dealing with the management tool's VM configuration file. And I think the management tool-specific archive format also shouldn't be in QEMU. How will a proxmox user restore a VMA file generated with oVirt since the configuration file comes from the management layer? They can't because the VMA is specific to the management layer and should be handled there, not inside QEMU. QEMU must provide the mechanism for point-in-time backups of block devices - your backup block job implements this. Where I disagree with this patch series is that you put the management tool-specific archive format writer into QEMU. That is outside the scope of QEMU. The management tool should tell QEMU to take the backups of block devices and do a live migration to file. The management tool can use a NBD server if it wants to capture all the block device backups into a single archive. And the management tool can bundle the VM configuration into that archive too. But those steps are beyond the scope of QEMU. The approach I'm suggesting is more modular. For example, the backup block job can also be used to copy out the state of a disk into a new qcow2 file. +## +# @backup: +# +# Starts a VM backup. +# +# @backup-file: the backup file name +# +# @format: format of the backup file +# +# @config-filename: #optional name of a configuration file to include +into # the backup archive. +# +# @speed: #optional the maximum speed, in bytes per second # # +@devlist: #optional list of block device names (separated by ',', ';' +# or ':'). By default the backup includes all writable block devices. +# +# Returns: the uuid of the backup job # # Since: 1.5.0 ## { +'command': 'backup', 'data': { 'backup-file': 'str', + '*format': 'BackupFormat', + '*config-file': 'str', + '*devlist': 'str', '*speed': 'int' +}, devlist should be ['String']. I want to be able to use that command on the human monitor. That is no longer possible if I use ['String']? Good question. I don't know the answer but perhaps Luiz or Anthony do (CCed)? diff --git a/qmp-commands.hx b/qmp-commands.hx index 799adea..17e381b 100644 --- a/qmp-commands.hx +++ b/qmp-commands.hx @@ -889,6 +889,18 @@ EQMP }, { +.name = backup, +.args_type = backup-file:s,format:s?,config-file:F?,speed:o?,devlist:s?, +.mhandler.cmd_new = qmp_marshal_input_backup, +}, + +{ +.name = backup-cancel, +.args_type = , +.mhandler.cmd_new = qmp_marshal_input_backup_cancel, +}, We might want to more than one backup if the guest has multiple disks. For example, the database disk is backed up independently of the main OS disk. This API only allows one backup to run at a time. I do not want multiple backup jobs. You can easily run 2 jobs in sequence to solve above use case. Why do you not want multiple backup jobs? It makes perfect sense to separate
[Qemu-devel] [PATCH 1/9] vring: split the modification and publish of used ring
From: Liu Ping Fan pingf...@linux.vnet.ibm.com Currently, vring_push() modify used ring and publish it, but sometime, we need to gather the changes and publish them all at once. So introduce vring_fill(), vring_flush(). Signed-off-by: Liu Ping Fan pingf...@linux.vnet.ibm.com --- hw/dataplane/vring.c | 31 +++ hw/dataplane/vring.h |2 ++ 2 files changed, 33 insertions(+), 0 deletions(-) diff --git a/hw/dataplane/vring.c b/hw/dataplane/vring.c index d5d4ef4..865bd4d 100644 --- a/hw/dataplane/vring.c +++ b/hw/dataplane/vring.c @@ -332,6 +332,37 @@ int vring_pop(VirtIODevice *vdev, Vring *vring, return head; } +/* Same as vring_push, but delay update used-idx, until ready */ +void vring_fill(Vring *vring, unsigned int head, int len) +{ +struct vring_used_elem *used; + +/* Don't touch vring if a fatal error occurred */ +if (vring-broken) { +return; +} + +/* The virtqueue contains a ring of used buffers. Get a pointer to the + * next entry in that used ring. */ +used = vring-vr.used-ring[vring-last_used_idx % vring-vr.num]; +used-id = head; +used-len = len; +vring-last_used_idx++; +} + +void vring_flush(Vring *vring) +{ +uint16_t new; + +/* Make sure buffer is written before we update index. */ +smp_wmb(); + +new = vring-vr.used-idx = vring-last_used_idx; +if (unlikely((int16_t)(new - vring-signalled_used) (uint16_t)1)) { +vring-signalled_used_valid = false; +} +} + /* After we've used one of their buffers, we tell them about it. * * Stolen from linux/drivers/vhost/vhost.c. diff --git a/hw/dataplane/vring.h b/hw/dataplane/vring.h index 3274f62..0d00500 100644 --- a/hw/dataplane/vring.h +++ b/hw/dataplane/vring.h @@ -57,6 +57,8 @@ bool vring_should_notify(VirtIODevice *vdev, Vring *vring); int vring_pop(VirtIODevice *vdev, Vring *vring, struct iovec iov[], struct iovec *iov_end, unsigned int *out_num, unsigned int *in_num); +void vring_fill(Vring *vring, unsigned int head, int len); +void vring_flush(Vring *vring); void vring_push(Vring *vring, unsigned int head, int len); #endif /* VRING_H */ -- 1.7.4.4
Re: [Qemu-devel] [PATCH v4 0/6] Efficient VM backup for qemu
On Thu, Feb 21, 2013 at 06:53:24AM +, Dietmar Maurer wrote: Interesting series, the backup block job makes sense to me. Regarding efficiency, I think incremental backup is a must, One can easily implement incremental backup on top of this patches. That is why I introduced the BackupDriver abstraction. otherwise regular backups using this approach won't really be a win over backing files. The backup writer abstraction is a special case interface somewhere between an image format and live migration. I'd prefer it if the backup block job stuck to BlockDriverState as the destination for backup data. Then you could save a point-in-time copy of a disk to a raw or even qcow2 image. The vmstate feature looks like vmsave duplication. The problem with vmsave is that it doesn't compose nicely with block jobs or the QMP transaction command, which would allow you to snapshot the disks and then capture the VM state. How would VMA fit in if the backup block job took a BlockDriverState destination and vmsave worked atomically with backup block jobs? You could have QEMU write to NBD server ports that a VMA writer process has open. VMA would happen outside the QEMU process. The benefit of doing this is that the backup block job becomes a general-purpose command and QEMU is not directly involved in capturing guest configuration. IMO the management tool is the correct place to orchestrate guest restore. I am still not sure what you describe here exactly. But this looks like you want to have an external backup server (NBD), and move the code out of qemu. But NBD is not the only option. There are many backup tool/servers out there, and you can easily write a BackupDriver for any of them. Using a fixed protocol like NBD does not really have an advantage for me, as you can write a BackupDriver for that. There is more discussion on this in the patch where a VM configuration file gets saved. I posted more concrete explanations of how it works and why it's a good idea. Stefan
Re: [Qemu-devel] [PATCH v4 0/6] Efficient VM backup for qemu
On Wed, Feb 20, 2013 at 04:04:49PM +, Dietmar Maurer wrote: Interesting series, the backup block job makes sense to me. Regarding efficiency, I think incremental backup is a must, otherwise regular backups using this approach won't really be a win over backing files. Incremental backup is something different, not touched by this code. You can add that later if needed. The backup writer abstraction is a special case interface somewhere between an image format and live migration. I'd prefer it if the backup block job stuck to BlockDriverState as the destination for backup data. Then you could save a point-in-time copy of a disk to a raw or even qcow2 image. backup needs to work on non-seekable pipes. The vmstate feature looks like vmsave duplication. The problem with vmsave is that it doesn't compose nicely with block jobs or the QMP transaction command, which would allow you to snapshot the disks and then capture the VM state. How would VMA fit in if the backup block job took a BlockDriverState destination and vmsave worked atomically with backup block jobs? You could have QEMU write to NBD server ports that a VMA writer process has open. VMA would happen outside the QEMU process. We want to write to pipes, so what you suggest simply does not work? Writing to pipes still works, the data is just passed first to a process on the host which writes the archive to the pipe. The archive write process writes to the pipe, not QEMU. Stefan
Re: [Qemu-devel] [PATCH v4 0/6] Efficient VM backup for qemu
On Thu, Feb 21, 2013 at 06:53:24AM +, Dietmar Maurer wrote: How would VMA fit in if the backup block job took a BlockDriverState destination and vmsave worked atomically with backup block jobs? You could have QEMU write to NBD server ports that a VMA writer process has open. VMA would happen outside the QEMU process. The benefit of doing this is that the backup block job becomes a general-purpose command and QEMU is not directly involved in capturing guest configuration. IMO the management tool is the correct place to orchestrate guest restore. I am still not sure what you describe here exactly. But this looks like you want to have an external backup server (NBD), and move the code out of qemu. But NBD is not the only option. There are many backup tool/servers out there, and you can easily write a BackupDriver for any of them. Using a fixed protocol like NBD does not really have an advantage for me, as you can write a BackupDriver for that. I think the reason why Stefan mentioned NBD is that qemu already has an NBD block driver, so if you can backup to a BlockDriverState, you get this for free. However, I don't think there's any reason why we couldn't have a regular (write-only?) VMA block driver inside qemu that can be used for the target BlockDriverState if you want to backup into a VMA. Kevin
Re: [Qemu-devel] [PATCH v4 0/6] Efficient VM backup for qemu
On Wed, Feb 20, 2013 at 04:04:49PM +, Dietmar Maurer wrote: The backup writer abstraction is a special case interface somewhere between an image format and live migration. I'd prefer it if the backup block job stuck to BlockDriverState as the destination for backup data. Then you could save a point-in-time copy of a disk to a raw or even qcow2 image. backup needs to work on non-seekable pipes. In _your_ use case. That means that we should support using non-seekable pipes, but it doesn't mean that any other use case is irrelevant. In fact I think backing up to a normal raw or qcow2 image file is the interesting case for the majority of people. Kevin
[Qemu-devel] [RFC PATCH 3/3] KVM: s390: Hook up ioeventfds.
As s390 doesn't use memory writes for virtio notifcations, create a special kind of ioeventfd instead that hooks up into diagnose 0x500 (kvm hypercall) with function code 3 (virtio-ccw notification). Signed-off-by: Cornelia Huck cornelia.h...@de.ibm.com --- arch/s390/include/asm/kvm_host.h | 23 ++ arch/s390/kvm/Kconfig| 1 + arch/s390/kvm/Makefile | 2 +- arch/s390/kvm/diag.c | 23 ++ arch/s390/kvm/kvm-s390.c | 165 +++ arch/s390/kvm/kvm-s390.h | 3 + 6 files changed, 216 insertions(+), 1 deletion(-) diff --git a/arch/s390/include/asm/kvm_host.h b/arch/s390/include/asm/kvm_host.h index 16bd5d1..8dad9dc 100644 --- a/arch/s390/include/asm/kvm_host.h +++ b/arch/s390/include/asm/kvm_host.h @@ -18,6 +18,7 @@ #include linux/kvm_host.h #include asm/debug.h #include asm/cpu.h +#include asm/schid.h #define KVM_MAX_VCPUS 64 #define KVM_USER_MEM_SLOTS 32 @@ -262,8 +263,30 @@ struct kvm_arch{ debug_info_t *dbf; struct kvm_s390_float_interrupt float_int; struct gmap *gmap; + struct list_head sch_fds; + struct rw_semaphore sch_fds_sem; int css_support; }; extern int sie64a(struct kvm_s390_sie_block *, u64 *); +#define __KVM_HAVE_ARCH_IOEVENTFD + +#define KVM_S390_IOEVENTFD_VIRTIO_CCW_NOTIFY 1 + +struct kvm_s390_ioeventfd_data { + __u8 type; + union { + /* VIRTIO_CCW_NOTIFY */ + struct { + __u64 vq; + struct subchannel_id schid; + } virtio_ccw_vq; + char padding[35]; + }; +} __packed; + +struct kvm_arch_ioeventfd { + struct list_head entry; + struct kvm_s390_ioeventfd_data data; +}; #endif diff --git a/arch/s390/kvm/Kconfig b/arch/s390/kvm/Kconfig index b58dd86..3c43e30 100644 --- a/arch/s390/kvm/Kconfig +++ b/arch/s390/kvm/Kconfig @@ -22,6 +22,7 @@ config KVM select PREEMPT_NOTIFIERS select ANON_INODES select HAVE_KVM_CPU_RELAX_INTERCEPT + select HAVE_KVM_EVENTFD ---help--- Support hosting paravirtualized guest machines using the SIE virtualization capability on the mainframe. This should work diff --git a/arch/s390/kvm/Makefile b/arch/s390/kvm/Makefile index 2441ffd..dbd8cc9 100644 --- a/arch/s390/kvm/Makefile +++ b/arch/s390/kvm/Makefile @@ -6,7 +6,7 @@ # it under the terms of the GNU General Public License (version 2 only) # as published by the Free Software Foundation. -common-objs = $(addprefix ../../../virt/kvm/, kvm_main.o) +common-objs = $(addprefix ../../../virt/kvm/, kvm_main.o eventfd.o) ccflags-y := -Ivirt/kvm -Iarch/s390/kvm diff --git a/arch/s390/kvm/diag.c b/arch/s390/kvm/diag.c index a390687..51ea66f 100644 --- a/arch/s390/kvm/diag.c +++ b/arch/s390/kvm/diag.c @@ -104,6 +104,27 @@ static int __diag_ipl_functions(struct kvm_vcpu *vcpu) return -EREMOTE; } +static int __diag_virtio_hypercall(struct kvm_vcpu *vcpu) +{ + struct kvm_s390_ioeventfd_data data; + u32 tmp; + + /* No channel I/O? Get out quickly. */ + if (!vcpu-kvm-arch.css_support || + (vcpu-run-s.regs.gprs[1] != 3)) + return -EOPNOTSUPP; + + /* subchannel id is in gpr 2, queue in gpr 3 */ + tmp = vcpu-run-s.regs.gprs[2] 0x; + memcpy(data.virtio_ccw_vq.schid, tmp, + sizeof(data.virtio_ccw_vq.schid)); + data.virtio_ccw_vq.vq = vcpu-run-s.regs.gprs[3]; + data.type = KVM_S390_IOEVENTFD_VIRTIO_CCW_NOTIFY; + + /* If signalling via eventfd fails, we want to drop to userspace. */ + return kvm_s390_ioeventfd_signal(vcpu-kvm, data) ? -EOPNOTSUPP : 0; +} + int kvm_s390_handle_diag(struct kvm_vcpu *vcpu) { int code = (vcpu-arch.sie_block-ipb 0xfff) 16; @@ -118,6 +139,8 @@ int kvm_s390_handle_diag(struct kvm_vcpu *vcpu) return __diag_time_slice_end_directed(vcpu); case 0x308: return __diag_ipl_functions(vcpu); + case 0x500: + return __diag_virtio_hypercall(vcpu); default: return -EOPNOTSUPP; } diff --git a/arch/s390/kvm/kvm-s390.c b/arch/s390/kvm/kvm-s390.c index 58a5f03..cd9eb0e 100644 --- a/arch/s390/kvm/kvm-s390.c +++ b/arch/s390/kvm/kvm-s390.c @@ -15,6 +15,7 @@ #include linux/compiler.h #include linux/err.h +#include linux/eventfd.h #include linux/fs.h #include linux/hrtimer.h #include linux/init.h @@ -143,6 +144,7 @@ int kvm_dev_ioctl_check_extension(long ext) case KVM_CAP_ONE_REG: case KVM_CAP_ENABLE_CAP: case KVM_CAP_S390_CSS_SUPPORT: + case KVM_CAP_IOEVENTFD: r = 1; break; case KVM_CAP_NR_VCPUS: @@ -237,6 +239,8 @@ int kvm_arch_init_vm(struct kvm *kvm, unsigned long type) if (!kvm-arch.gmap) goto out_nogmap; } +