[Qemu-devel] Welcome to Homerun!

2011-01-17 Thread HomeRun
Welcome to HomeRun!

Thanks for joining the HomeRun community. Are you ready to have fun? Give us a 
few minutes and you'll see how we make buying more fun, social, and rewarding 
than anywhere else. And, oh yeah, we forgot to mention that the prices are 
pretty unbelievable too :)

What should you do now? Here's a few things to get you started:

(1) Find your real friends already on HomeRun. Connect with Facebook or add 
them via email.
(2) Check out our City Samplers. They're great, inexpensive, one-time deals all 
around your city.
(3) Find The Daily Steal. It might be an "Avalanche" where the price drops as 
more members buy. So fun.
(4) See what's in The Private Reserve. When you get enough Points you'll 
qualify to buy these deals.
(5) Explore. Meet. Discuss. Buy. Enjoy. Win. There's so much to do, see, and 
experience on HomeRun.

Take me over to HomeRun: http://homerun.com/?_e=3b792c11

Go ahead and dive right in,

The HomeRun Team


Brought to you by HomeRun, PO Box 26049, San Francisco, CA, 94126, USA



Re: [Qemu-devel] paravirtual mouse/tablet

2011-01-17 Thread Gerd Hoffmann

  Hi,


I was just talking to Chase Douglas here at the ubuntu sprint about this, and
he pointed me at https://launchpad.net/rinput which is a program which
can forward remote events including multitouch over the network (including
forwarding from both Linux and MacOS X clients). Maybe that would be
worth looking at since it's a working implementation of forwarding
multitouch events between systems?


Looks like they are basically using the linux input layer protocol.

cheers,
  Gerd



Re: [Qemu-devel] paravirtual tablet v3

2011-01-17 Thread Gerd Hoffmann

On 01/14/11 21:48, Anthony Liguori wrote:

On 01/14/2011 10:35 AM, Gerd Hoffmann wrote:

Hi,

Now v3 featuring multitouch ;)

cheers,
Gerd


I really think multitouch needs to be a feature such that the guest can
nack it and the host can adjust accordingly. If it's there from day 1,
that's fine, but it still should be a feature.

There are a lot of non-multitouch aware guests out there and I don't
think we want the driver to be the one deciding how to map a multitouch
device to something that doesn't support mulitouch.


Sure, someone needs to map multitouch to non-multitouch.  I'd leave that 
job to the guest driver tough.  Why do you think doing it in the host is 
better?


cheers,
  Gerd



Re: [Qemu-devel] [PATCH 2/3] block: tell drivers about an image resize

2011-01-17 Thread Christoph Hellwig
> Do we want to check to ensure the size_changed flag isn't set before
> doing a second resize event?  I'm wondering if the truncate takes
> $longtime and user gets impatient and issues a second resize command.
> How should we respond?  Ignore it?  queue it up? 

The truncate is synchronous and the monitor command won't return before
it's done.  The interfact might be a bit cleaner if we'd just pass the
reason for the change callback as another argument.  I'll do that for
the next respin.

> Is there any other path that invokes bdrv_truncate?  If so, do we want
> invoke the call back in those scenarios or only if the truncate is
> initiated from the monitor invocation?

Currently only the qemu-img and qemu-io tools invooke bdrv_truncate.
But if we grow new users we should always tell the driver/guest about it
so that it knows about the size change.




[Qemu-devel] Re: [PATCH] usb-msd: Add usb-storage, removable=on|off property

2011-01-17 Thread Christoph Hellwig
The actual removable bit looks fine, but I don't think the connection of
the change callback looks sane.  What's the rationale for it?




Re: [Qemu-devel] [PATCH] pci: Remove unneeded null pointer check

2011-01-17 Thread Kevin Wolf
Am 15.01.2011 19:01, schrieb Stefan Weil:
> With bm == NULL, other code in the same function would crash.
> 
> This bug was reported by cppcheck:
> hw/ide/pci.c:280: error: Possible null pointer dereference: bm
> 
> Cc: Michael S. Tsirkin 
> Signed-off-by: Stefan Weil 

Thanks, applied to the block branch.

Kevin



[Qemu-devel] Re: [PATCH uq/master 2/2] MCE, unpoison memory address across reboot

2011-01-17 Thread Jan Kiszka
On 2011-01-17 03:08, Huang Ying wrote:
 As indicated, I'm sitting on lots of fixes and refactorings of the MCE
 user space code. How do you test your patches? Any suggestions how to do
 this efficiently would be warmly welcome.
>>>
>>> We use a self-made test script to test.  Repository is at:
>>>
>>> git://git.kernel.org/pub/scm/utils/cpu/mce/mce-test.git
>>>
>>> The kvm test script is in kvm sub-directory.
>>>
>>> The qemu patch attached is need by the test script.
>>>
>>
>> Yeah, I already found this yesterday and started reading. I was just
>> searching for p2v in qemu, but now it's clear where it comes from. Will
>> have a look (if you want to preview my changes:
>> git://git.kiszka.org/qemu-kvm.git queues/kvm-upstream).
>>
>> I was almost about to use MADV_HWPOISON instead of the injection module.
>> Is there a way to recover the fake corruption afterward? I think that
>> would allow to move some of the test logic into qemu and avoid p2v which
>> - IIRC - was disliked upstream.
> 
> I don't know how to fully recover from  MADV_HWPOISON.  You can recover
> the virtual address space via qemu_ram_remap() introduced in 1/2 of this
> patchset.  But you will lose one or several physical pages for each
> testing.  I think that may be not a big issue for a testing machine.
> 
> Ccing Andi and Fengguang, they know more than me about MADV_HWPOISON.

"page-types -b hwpoison -x" does the trick of unpoisoning for me. It can
be found at linux/Documentation/vm/page-types.c. So it's quite easy to
set up and clean up a test case based on MADV_HWPOISON IMO. Not sure,
though, if that can simulate all of what you currently do via mce-inject.

> 
>> Also, is there a way to simulate corrected errors (BUS_MCEERR_AO)?
> 
> BUS_MCEERR_AO is recoverable uncorrected error instead of corrected
> error.
> 
> The test script is for BUS_MCEERR_AO and BUS_MCEERR_AR.  To see the
> effect of pure BUS_MCEERR_AO, just remove the memory accessing loop
> (memset) in tools/simple_process/simple_process.c.

Yeah, that question was based on lacking knowledge about the different
error types. Meanwhile, I was able to trigger BUS_MCEERR_AO via
MADV_HWPOISON - and also BUS_MCEERR_AR by accessing that page. However,
I did not succeed with using mce-inject so far, thus with mce-test. But
I need to check this again.

Jan

-- 
Siemens AG, Corporate Technology, CT T DE IT 1
Corporate Competence Center Embedded Linux



Re: [Qemu-devel] [PATCH 08/12] Threadlet: Add aio_signal_handler threadlet API

2011-01-17 Thread Stefan Hajnoczi
On Thu, Jan 13, 2011 at 12:14 PM, Arun R Bharadwaj
 wrote:
> +static void threadlet_io_completion_signal_handler(int signum)
> +{
> +    qemu_service_io();
> +}
> +
> +static void threadlet_register_signal_handler(void)
> +{
> +    struct sigaction act;
> +    sigfillset(&act.sa_mask);
> +    act.sa_flags = 0; /* do not restart syscalls to interrupt select() */
> +    act.sa_handler = threadlet_io_completion_signal_handler;
> +    sigaction(SIGUSR2, &act, NULL);
> +}
> +
> +void threadlet_init(void)
> +{
> +    threadlet_register_signal_handler();
> +}

This would be the right place to create qemu-threadlet.c, instead of
adding the thread_init() prototype to qemu-thread.h and then including
that in vl.c.

Stefan



Re: [Qemu-devel] [PATCH 10/12] Move threadlet code to qemu-threadlets.c

2011-01-17 Thread Stefan Hajnoczi
On Thu, Jan 13, 2011 at 12:15 PM, Arun R Bharadwaj
 wrote:
> This patch moves the threadlet queue API code to
> qemu-threadlets.c where these APIs can be used by
> other subsystems.

qemu-threadlet.c would be consistent with qemu-thread.c (not qemu-threads.c).

Stefan



[Qemu-devel] MIPS, io-thread, icount and wfi

2011-01-17 Thread Edgar E. Iglesias
Hi,

I'm running an io-thread enabled qemu-system-mipsel with icount.
When the guest (linux) goes to sleep through the wait insn (waiting
to be woken up by future timer interrupts), the thing deadlocks.

IIUC, this is because vm timers are driven by icount, but the CPU is
halted so icount makes no progress and time stands still.

I've locally disabled vcpu halting when icount is enabled, that
works around my problem but of course makes qemu consume 100% host cpu.

I don't know why I only see this problem with io-thread builds?
Could be related timing and luck.

Would be interesting to know if someone has any info on how this was
intended to work (if it was)? And if there are ideas for better
workarounds or fixes that don't disable vcpu halting entirely.

Cheers



Re: [Qemu-devel] Re: [PATCH] usb-msd: Add usb-storage, removable=on|off property

2011-01-17 Thread Stefan Hajnoczi
On Mon, Jan 17, 2011 at 10:21:26AM +0100, Christoph Hellwig wrote:
> The actual removable bit looks fine, but I don't think the connection of
> the change callback looks sane.  What's the rationale for it?

Since we're using bdrv_set_removable(), the user may try to eject the
block device from the QEMU monitor.  At that point we have a closed
BlockDriverState and all operations will (at best) error since there is
no medium.

The callback removes the USB MSD so that eject is equivalent to removing
the device.  It's a hack and we could remove it, but then we're left
with a weird guest-visible state that you can't get into with a physical
USB thumbdrive.

I was considering not using bdrv_set_removable() and instead adding a
hint to the BlockDriverState which gets checked when constructing the
SCSI INQUIRY response.  If we take that approach, then QEMU doesn't
consider the block device removable in the eject/change medium sense.

Stefan



[Qemu-devel] Re: [PATCH v2 0/5] iohandlers: Add support for enabling/disabling individual handlers

2011-01-17 Thread Amit Shah
On (Thu) Jan 13 2011 [13:17:22], Anthony Liguori wrote:
> On 01/13/2011 09:00 AM, Amit Shah wrote:
> >Hi,
> >
> >This patchset adds new interfaces to work with iohandlers.  It adds:
> >
> >int assign_fd_handlers(int fd, IOHandlerOps *ops, void *opaque)
> >-- Specify io handlers for an fd
> >int remove_fd_handlers(int fd)
> >-- Remove fd handlers for fd (mark ioh for deletion)
> >int set_read_poll_fd_action(int fd, bool enable)
> >-- Enable or disable the fd_read_poll fd handler
> >int set_read_fd_action(int fd, bool enable)
> >-- Enable or disable the fd_read fd handler
> >int set_write_fd_action(int fd, bool enable)
> >-- Enable or disable the fd_read fd handler
> >
> >A new struct, IOHandlerOps, is added, to collect all the ops together
> >instead of passing individual ones to functions.
> 
> Instead of inventing new interfaces, I think we should steal^Wlearn
> from established interfaces.

Agreed.

I do also think it'll be worthwhile pulling in one of the libraries to
reduce the amount of qemu-specific code we have in the other cases as
well.

>  Both libevent and glib have interfaces
> that essentially boil down to:
> 
> handle add_fd_event(loop, fd, ConditionMask, callback, opaque)
> remove_event(loop, handle)

This is quite similar to the Linux polling API.

I don't know what the 'loop' parameter would do, though.

> I think that's what we should move to.  All the stuff in our current
> loop around allowing suppressing of read events is terrible as it
> forces the main loop to poll.  That makes it impossible to use other
> main loops because it's completely unusual.

While setting new APIs possibly requires more discussion if we want to
do it once and right, since it's also an internal API, we can keep
evolving them.

So what's the accepted course of action now - take this new API, rework
it to look like that of some other library's and then rework the
main_loop, keep developing something in parallel till it satisfies
everyone, etc.?

Also -- this patchset was prompted by a bug in qemu chardevs that
freezes guests if they write faster than the chardevs can consume.
What should the strategy on fixing that bug be?

Amit



Re: [Qemu-devel] [PATCH 00/12] Threadlets Infrastructure.

2011-01-17 Thread Stefan Hajnoczi
This series needs a new pair of eyes for review.  I'm probably missing
things here after seeing it many times.

posix-aio-compat.c:handle_work() doesn't need to take aiocb_mutex for
container_of(), which just calculates an address but doesn't actually
access the aiocb.

dequeue_work_on_queue() is incorrect because a threadlet_worker() may
remove the work item from the request_list just before we remove it
again.  That double-remove is wrong and by not detecting this case we
return success even though the work function may be running
concurrently (and it's not safe to do anything with the work item at
this time!).  Dequeue needs to lock the request_list, test if the item
is still
on the list, remove it if necessary, and return whether or not it was removed.

Stefan



Re: [Qemu-devel] [RFC] Propose the Fast Virtual Disk (FVD) image format that outperforms QCOW2 by 249%

2011-01-17 Thread Stefan Hajnoczi
Resend because qemu-devel was dropped from CC.  Thanks for pointing it
out Kevin.

On Sat, Jan 15, 2011 at 12:25 PM, Stefan Hajnoczi  wrote:
> On Sat, Jan 15, 2011 at 3:28 AM, Chunqiang Tang  wrote:
>> T1) To address the problems of B1- B3, I implemented an emulated disk in
>> block/sim.c, which allows a full control of event timings, either manually
>> or automatically. Given the three concurrent writes example above, their 9
>> events (Pa, Pb, Pc, Wa, Wb, Wc, Va, Vb, and Vc) can be precisely
>> controlled to be executed in any given order. Moreover, the emulated disk
>> can inject disk I/O errors in a controlled manner. For example, it can
>> fail a specific read or write to test how the code handles that, or it can
>> even fail as many as 90% of the reads/writes to test if the code has
>> resource leaks. qemu-io is extended with a module qemu-io-sim.c to work
>> with the emulated disk block/sim.c, so that the tester can use the qemu-io
>> console to manually control the order of events or fail disk reads or
>> writes.
>
> block/blkdebug.c already provides fault injection and is used in
> qemu-iotests test 026.  Using blkdebug it is possible to test specific
> error paths in image formats.  We should look at merging random
> failures ("fail as many as 90% of the reads/writes") into blkdebug.
>
>> T2) The solution in T1 still does not address the problem of B3), i.e.,
>> manually generating test cases is time consuming and has a low coverage.
>> This problem is solved by a new testing tool called qemu-test. qemu-test
>> can 1) automatically generate an unlimited number of randomized test cases
>> that, e.g., execute 1,000 concurrent disk reads or writes on overlapping
>> disk regions; 2) automatically generate the corresponding anticipated
>> correct results, automatically run the tests, and automatically compare
>> the actual test results with the anticipated correct results. Once it
>> discovers a difference, which indicates a bug, it halts testing and waits
>> for the developer to debug.  The randomized test cases created by
>> qemu-test are controlled by a pseudo random number generator, and hence
>> the behavior is completely repeatable. Therefore, once a bug is triggered,
>> it can be precisely repeated for an unlimited number of times to
>> facilitate debugging, even if this bug happens extremely rare in real runs
>> of a VM. qemu-test is fully automated. Once started, it can continuously
>> run, e.g., for months to test an enormous number of test cases.
>>
>> The implementation of qemu-test is actually not that complicated. It opens
>> two virtual disks, the so-called truth image and test image, respectively.
>> The truth image is served by a trivial synchronous block device driver so
>> that its behavior is guaranteed to be correct. The test image is served a
>> real block device driver (e.g., FVD or QCOW2) that we want to test.
>> qemu-test submits the same sequence of disk I/O requests (which is
>> randomly generated) to the truth image and the test image, and expect that
>> the two images’ contents never diverge. Otherwise, it indicates a bug in
>> the test image’s block device driver. qemu-test works with the emulated
>> disk block/sim.c so that it can randomize event timings in a controlled
>> manner and can inject disk I/O errors randomly.
>
> block/blkverify.c already provides I/O verification.  It mirrors
> writes to a raw file and compares the contents of read blocks to
> detect data integrity issues.  That's the same approach you have
> described.
>
>> I found qemu-test extremely powerful in discovering elusive bugs that I
>> never anticipated, and using qemu-test is effortless. Whenever I completed
>> some major code upgrade, I simply started qemu-test in the evening and
>> came back in the morning to collect bugs, if any. Debugging them is also
>> easy because the bugs are precisely repeatable even if they are hard to
>> trigger.
>
> Here are the unique features you've described beyond what qemu-io,
> blkdebug, and blkverify do:
>
> 1. New functionality
>  * Control over ordering of I/O request submission and completion.
>  * Random I/O generator (probably as new qemu-io command).
>
> 2. Enhancements to existing code:
>  * Random chance of failing I/O in blkdebug.
>
> Do you agree with this or are there other unique features which are
> beyond small enhancements to existing code?
>
> I think the best strategy is to consolidate these as incremental
> patches that can be reviewed and merged independently.
>
>> As for the FVD patch that includes the new testing framework, I tried to
>> post it on the mailing list twice but it always got bounced back, either
>> because the message is too big or because of a Notes client configuration
>> issue. Until I figure it out, please down the FVD patch from
>> https://researcher.ibm.com/researcher/files/us-ctang/FVD-01-14-2011.patch
>
> I'll send you my git-send-email config off-list.
>
> Stefan
>



[Qemu-devel] [PATCH v2 1/3] qcow2: Add QcowCache

2011-01-17 Thread Kevin Wolf
This adds some new cache functions to qcow2 which can be used for caching
refcount blocks and L2 tables. When used with cache=writethrough they work
like the old caching code which is spread all over qcow2, so for this case we
have merely a cleanup.

The interesting case is with writeback caching (this includes cache=none) where
data isn't written to disk immediately but only kept in cache initially. This
leads to some form of metadata write batching which avoids the current "write
to refcount block, flush, write to L2 table" pattern for each single request
when a lot of cluster allocations happen. Instead, cache entries are only
written out if its required to maintain the right order. In the pure cluster
allocation case this means that all metadata updates for requests are done in
memory initially and on sync, first the refcount blocks are written to disk,
then fsync, then L2 tables.

This improves performance of scenarios with lots of cluster allocations
noticably (e.g. installation or after taking a snapshot).

Signed-off-by: Kevin Wolf 
---
 Makefile.objs   |2 +-
 block/qcow2-cache.c |  293 +++
 block/qcow2.h   |   19 
 3 files changed, 313 insertions(+), 1 deletions(-)
 create mode 100644 block/qcow2-cache.c

diff --git a/Makefile.objs b/Makefile.objs
index c3e52c5..65889c9 100644
--- a/Makefile.objs
+++ b/Makefile.objs
@@ -19,7 +19,7 @@ block-obj-$(CONFIG_POSIX) += posix-aio-compat.o
 block-obj-$(CONFIG_LINUX_AIO) += linux-aio.o
 
 block-nested-y += raw.o cow.o qcow.o vdi.o vmdk.o cloop.o dmg.o bochs.o vpc.o 
vvfat.o
-block-nested-y += qcow2.o qcow2-refcount.o qcow2-cluster.o qcow2-snapshot.o
+block-nested-y += qcow2.o qcow2-refcount.o qcow2-cluster.o qcow2-snapshot.o 
qcow2-cache.o
 block-nested-y += qed.o qed-gencb.o qed-l2-cache.o qed-table.o qed-cluster.o
 block-nested-y += qed-check.o
 block-nested-y += parallels.o nbd.o blkdebug.o sheepdog.o blkverify.o
diff --git a/block/qcow2-cache.c b/block/qcow2-cache.c
new file mode 100644
index 000..200a98c
--- /dev/null
+++ b/block/qcow2-cache.c
@@ -0,0 +1,293 @@
+/*
+ * L2/refcount table cache for the QCOW2 format
+ *
+ * Copyright (c) 2010 Kevin Wolf 
+ *
+ * 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 "block_int.h"
+#include "qemu-common.h"
+#include "qcow2.h"
+
+typedef struct Qcow2CachedTable {
+void*   table;
+int64_t offset;
+booldirty;
+int cache_hits;
+int ref;
+} Qcow2CachedTable;
+
+struct Qcow2Cache {
+int size;
+Qcow2CachedTable*   entries;
+struct Qcow2Cache*  depends;
+boolwritethrough;
+};
+
+Qcow2Cache *qcow2_cache_create(BlockDriverState *bs, int num_tables,
+bool writethrough)
+{
+BDRVQcowState *s = bs->opaque;
+Qcow2Cache *c;
+int i;
+
+c = qemu_mallocz(sizeof(*c));
+c->size = num_tables;
+c->entries = qemu_mallocz(sizeof(*c->entries) * num_tables);
+c->writethrough = writethrough;
+
+for (i = 0; i < c->size; i++) {
+c->entries[i].table = qemu_blockalign(bs, s->cluster_size);
+}
+
+return c;
+}
+
+int qcow2_cache_destroy(BlockDriverState* bs, Qcow2Cache *c)
+{
+int i;
+int ret;
+
+ret = qcow2_cache_flush(bs, c);
+
+for (i = 0; i < c->size; i++) {
+assert(c->entries[i].ref == 0);
+qemu_vfree(c->entries[i].table);
+}
+
+qemu_free(c->entries);
+qemu_free(c);
+
+bdrv_flush(bs->file);
+
+return ret;
+}
+
+static int qcow2_cache_flush_dependency(BlockDriverState *bs, Qcow2Cache *c)
+{
+int ret;
+
+ret = qcow2_cache_flush(bs, c->depends);
+if (ret < 0) {
+return ret;
+}
+
+c->depends = NULL;
+return 0;
+}
+
+static int qcow2_cache_entry_flush(BlockDriverState *bs, Qcow2Cache *c, int i)
+{
+BDRVQcowState *s = bs->opaque;
+int ret;
+
+if (!c->entries[i].dirty || !c->entries[i].offset) {
+re

[Qemu-devel] [PATCH v2 3/3] qcow2: Batch flushes for COW

2011-01-17 Thread Kevin Wolf
qcow2 calls bdrv_flush() after performing COW in order to ensure that the
L2 table change is never written before the copy is safe on disk. Now that the
L2 table is cached, we can wait with flushing until we write out the next L2
table.

Signed-off-by: Kevin Wolf 
---
 block/qcow2-cache.c   |   20 +---
 block/qcow2-cluster.c |2 +-
 block/qcow2.h |1 +
 3 files changed, 19 insertions(+), 4 deletions(-)

diff --git a/block/qcow2-cache.c b/block/qcow2-cache.c
index 200a98c..ba17020 100644
--- a/block/qcow2-cache.c
+++ b/block/qcow2-cache.c
@@ -38,6 +38,7 @@ struct Qcow2Cache {
 int size;
 Qcow2CachedTable*   entries;
 struct Qcow2Cache*  depends;
+booldepends_on_flush;
 boolwritethrough;
 };
 
@@ -90,13 +91,15 @@ static int qcow2_cache_flush_dependency(BlockDriverState 
*bs, Qcow2Cache *c)
 }
 
 c->depends = NULL;
+c->depends_on_flush = false;
+
 return 0;
 }
 
 static int qcow2_cache_entry_flush(BlockDriverState *bs, Qcow2Cache *c, int i)
 {
 BDRVQcowState *s = bs->opaque;
-int ret;
+int ret = 0;
 
 if (!c->entries[i].dirty || !c->entries[i].offset) {
 return 0;
@@ -104,11 +107,17 @@ static int qcow2_cache_entry_flush(BlockDriverState *bs, 
Qcow2Cache *c, int i)
 
 if (c->depends) {
 ret = qcow2_cache_flush_dependency(bs, c);
-if (ret < 0) {
-return ret;
+} else if (c->depends_on_flush) {
+ret = bdrv_flush(bs->file);
+if (ret >= 0) {
+c->depends_on_flush = false;
 }
 }
 
+if (ret < 0) {
+return ret;
+}
+
 ret = bdrv_pwrite(bs->file, c->entries[i].offset, c->entries[i].table,
 s->cluster_size);
 if (ret < 0) {
@@ -166,6 +175,11 @@ int qcow2_cache_set_dependency(BlockDriverState *bs, 
Qcow2Cache *c,
 return 0;
 }
 
+void qcow2_cache_depends_on_flush(Qcow2Cache *c)
+{
+c->depends_on_flush = true;
+}
+
 static int qcow2_cache_find_entry_to_replace(Qcow2Cache *c)
 {
 int i;
diff --git a/block/qcow2-cluster.c b/block/qcow2-cluster.c
index f6dd09e..c06ac46 100644
--- a/block/qcow2-cluster.c
+++ b/block/qcow2-cluster.c
@@ -638,7 +638,7 @@ int qcow2_alloc_cluster_link_l2(BlockDriverState *bs, 
QCowL2Meta *m)
  * handled.
  */
 if (cow) {
-bdrv_flush(bs->file);
+qcow2_cache_depends_on_flush(s->l2_table_cache);
 }
 
 qcow2_cache_set_dependency(bs, s->l2_table_cache, s->refcount_block_cache);
diff --git a/block/qcow2.h b/block/qcow2.h
index 8302bbb..59810a5 100644
--- a/block/qcow2.h
+++ b/block/qcow2.h
@@ -229,6 +229,7 @@ void qcow2_cache_entry_mark_dirty(Qcow2Cache *c, void 
*table);
 int qcow2_cache_flush(BlockDriverState *bs, Qcow2Cache *c);
 int qcow2_cache_set_dependency(BlockDriverState *bs, Qcow2Cache *c,
 Qcow2Cache *dependency);
+void qcow2_cache_depends_on_flush(Qcow2Cache *c);
 
 int qcow2_cache_get(BlockDriverState *bs, Qcow2Cache *c, uint64_t offset,
 void **table);
-- 
1.7.2.3




[Qemu-devel] [PATCH v2 2/3] qcow2: Use QcowCache

2011-01-17 Thread Kevin Wolf
Use the new functions of qcow2-cache.c for everything that works on refcount
block and L2 tables.

Signed-off-by: Kevin Wolf 
---
 block/qcow2-cluster.c  |  206 ++--
 block/qcow2-refcount.c |  249 +++-
 block/qcow2.c  |   43 -
 block/qcow2.h  |   12 ++-
 4 files changed, 216 insertions(+), 294 deletions(-)

diff --git a/block/qcow2-cluster.c b/block/qcow2-cluster.c
index c3ef550..f6dd09e 100644
--- a/block/qcow2-cluster.c
+++ b/block/qcow2-cluster.c
@@ -67,7 +67,11 @@ int qcow2_grow_l1_table(BlockDriverState *bs, int min_size, 
bool exact_size)
 qemu_free(new_l1_table);
 return new_l1_table_offset;
 }
-bdrv_flush(bs->file);
+
+ret = qcow2_cache_flush(bs, s->refcount_block_cache);
+if (ret < 0) {
+return ret;
+}
 
 BLKDBG_EVENT(bs->file, BLKDBG_L1_GROW_WRITE_TABLE);
 for(i = 0; i < s->l1_size; i++)
@@ -98,63 +102,6 @@ int qcow2_grow_l1_table(BlockDriverState *bs, int min_size, 
bool exact_size)
 return ret;
 }
 
-void qcow2_l2_cache_reset(BlockDriverState *bs)
-{
-BDRVQcowState *s = bs->opaque;
-
-memset(s->l2_cache, 0, s->l2_size * L2_CACHE_SIZE * sizeof(uint64_t));
-memset(s->l2_cache_offsets, 0, L2_CACHE_SIZE * sizeof(uint64_t));
-memset(s->l2_cache_counts, 0, L2_CACHE_SIZE * sizeof(uint32_t));
-}
-
-static inline int l2_cache_new_entry(BlockDriverState *bs)
-{
-BDRVQcowState *s = bs->opaque;
-uint32_t min_count;
-int min_index, i;
-
-/* find a new entry in the least used one */
-min_index = 0;
-min_count = 0x;
-for(i = 0; i < L2_CACHE_SIZE; i++) {
-if (s->l2_cache_counts[i] < min_count) {
-min_count = s->l2_cache_counts[i];
-min_index = i;
-}
-}
-return min_index;
-}
-
-/*
- * seek_l2_table
- *
- * seek l2_offset in the l2_cache table
- * if not found, return NULL,
- * if found,
- *   increments the l2 cache hit count of the entry,
- *   if counter overflow, divide by two all counters
- *   return the pointer to the l2 cache entry
- *
- */
-
-static uint64_t *seek_l2_table(BDRVQcowState *s, uint64_t l2_offset)
-{
-int i, j;
-
-for(i = 0; i < L2_CACHE_SIZE; i++) {
-if (l2_offset == s->l2_cache_offsets[i]) {
-/* increment the hit count */
-if (++s->l2_cache_counts[i] == 0x) {
-for(j = 0; j < L2_CACHE_SIZE; j++) {
-s->l2_cache_counts[j] >>= 1;
-}
-}
-return s->l2_cache + (i << s->l2_bits);
-}
-}
-return NULL;
-}
-
 /*
  * l2_load
  *
@@ -169,33 +116,12 @@ static int l2_load(BlockDriverState *bs, uint64_t 
l2_offset,
 uint64_t **l2_table)
 {
 BDRVQcowState *s = bs->opaque;
-int min_index;
 int ret;
 
-/* seek if the table for the given offset is in the cache */
-
-*l2_table = seek_l2_table(s, l2_offset);
-if (*l2_table != NULL) {
-return 0;
-}
-
-/* not found: load a new entry in the least used one */
-
-min_index = l2_cache_new_entry(bs);
-*l2_table = s->l2_cache + (min_index << s->l2_bits);
-
 BLKDBG_EVENT(bs->file, BLKDBG_L2_LOAD);
-ret = bdrv_pread(bs->file, l2_offset, *l2_table,
-s->l2_size * sizeof(uint64_t));
-if (ret < 0) {
-qcow2_l2_cache_reset(bs);
-return ret;
-}
+ret = qcow2_cache_get(bs, s->l2_table_cache, l2_offset, (void**) l2_table);
 
-s->l2_cache_offsets[min_index] = l2_offset;
-s->l2_cache_counts[min_index] = 1;
-
-return 0;
+return ret;
 }
 
 /*
@@ -238,7 +164,6 @@ static int write_l1_entry(BlockDriverState *bs, int 
l1_index)
 static int l2_allocate(BlockDriverState *bs, int l1_index, uint64_t **table)
 {
 BDRVQcowState *s = bs->opaque;
-int min_index;
 uint64_t old_l2_offset;
 uint64_t *l2_table;
 int64_t l2_offset;
@@ -252,29 +177,48 @@ static int l2_allocate(BlockDriverState *bs, int 
l1_index, uint64_t **table)
 if (l2_offset < 0) {
 return l2_offset;
 }
-bdrv_flush(bs->file);
+
+ret = qcow2_cache_flush(bs, s->refcount_block_cache);
+if (ret < 0) {
+goto fail;
+}
 
 /* allocate a new entry in the l2 cache */
 
-min_index = l2_cache_new_entry(bs);
-l2_table = s->l2_cache + (min_index << s->l2_bits);
+ret = qcow2_cache_get_empty(bs, s->l2_table_cache, l2_offset, (void**) 
table);
+if (ret < 0) {
+return ret;
+}
+
+l2_table = *table;
 
 if (old_l2_offset == 0) {
 /* if there was no old l2 table, clear the new table */
 memset(l2_table, 0, s->l2_size * sizeof(uint64_t));
 } else {
+uint64_t* old_table;
+
 /* if there was an old l2 table, read it from the disk */
 BLKDBG_EVENT(bs->file, BLKDBG_L2_ALLOC_COW_READ);
-ret = bdrv_pread(bs->file, old_l2_offset, l2_table,
-s->l2_size * sizeof(uint64_t));
+ret = qcow2_cache_

[Qemu-devel] [PATCH v2 0/3] qcow2 metadata cache

2011-01-17 Thread Kevin Wolf
block-queue turned out to be too big effort to be useful for quickly fixing the
performance problems that qcow2 got since we introduced the metadata flushes.
While I still think the idea is right, it needs more time and qcow2 doesn't
have more time. Let's come back to block-queue later when the most urgent qcow2
problems are fixed.

So this is the idea of block-queue applied to the very specific case of qcow2.
Whereas block-queue tried to be a generic solution for all kind of things and
tried to make all writes asynchronous at the same time, this is only about
batching writes to refcount blocks and L2 tables in qcow2 and getting the
dependencies right. (Yes, the L1 table and refcount table is left alone. They
are almost never written to anyway.)

This should be much easier to understand and review, and I myself feel a bit
more confident about it than with block-queue, too.

v1:
- Don't read newly allocated tables from the disk before memsetting them to
  zero

v2:
- Addressed Stefan's review comments
- Added patch 3 to avoid an unnecessary bdrv_flush after COW

Kevin Wolf (3):
  qcow2: Add QcowCache
  qcow2: Use QcowCache
  qcow2: Batch flushes for COW

 Makefile.objs  |2 +-
 block/qcow2-cache.c|  307 
 block/qcow2-cluster.c  |  206 +++-
 block/qcow2-refcount.c |  249 +++
 block/qcow2.c  |   43 ++-
 block/qcow2.h  |   32 -
 6 files changed, 544 insertions(+), 295 deletions(-)
 create mode 100644 block/qcow2-cache.c

-- 
1.7.2.3




Re: [Qemu-devel] [PATCH 1/3] block: add resize monitor command

2011-01-17 Thread Stefan Hajnoczi
On Fri, Jan 14, 2011 at 4:20 PM, Christoph Hellwig  wrote:
> +STEXI
> +@item resize
> +@findex resize
> +Resize a block image while a guest is running.  Usuaully requires guest

s/Usuaully/Usually/

> +action to see the updated size.  Resize to a lower size is supported,
> +but should be used with extreme caution.

This resizes the image files.  Resizing an LVM volume is a useful case
too.  One way to integrate that feature is to implement a host_device
.bdrv_truncate() that checks the underlying device size and returns
success if it matches the new value and failure otherwise.  Or perhaps
allow the QEMU resize command without an argument to fetch the size
from the underlying device (aka refresh the size).

> +    if (bdrv_get_type_hint(bs) == BDRV_TYPE_CDROM) {
> +        error_report("Can not resize CDROM devices\n");
> +        return -1;
> +    }

Hrm...BDRV_TYPE_FLOPPY probably too?

Stefan



Re: [Qemu-devel] [PATCH v2 1/6] Emulation of GRLIB GPTimer as defined in GRLIB IP Core User's Manual.

2011-01-17 Thread Fabien Chouteau

On 01/04/2011 07:46 PM, Blue Swirl wrote:

On Mon, Jan 3, 2011 at 2:07 PM, Fabien Chouteau  wrote:+}

+static uint32_t grlib_gptimer_readl(void *opaque, target_phys_addr_t addr)
+{
+GPTimerUnit *unit  = opaque;
+uint32_t value = 0;
+
+addr&= 0xff;


Not needed.



When io-memory starts at 0x8000300 and its size is 48 bytes, Qemu gives me
address like this one (for example):

0x320

But only the last two bytes of the address are significant, that's why I use
this bit-mask.

Maybe I do not initialize io-memory in a proper way...

--
Fabien Chouteau




Re: [Qemu-devel] TCG flow vs dyngen

2011-01-17 Thread Lluís
Stefano Bonifazi writes:

> Hi!
>  In case you are interested in helping me, I'll give you a big piece of news
> I've just got (even my teacher is not informed yet! :) )

I still don't understand what is your high-level objective...


Lluis

-- 
 "And it's much the same thing with knowledge, for whenever you learn
 something new, the whole world becomes that much richer."
 -- The Princess of Pure Reason, as told by Norton Juster in The Phantom
 Tollbooth



[Qemu-devel] [RFC][PATCH v6 00/23] virtagent: host/guest RPC communication agent

2011-01-17 Thread Michael Roth
These patches apply to master (1-14-2011), and can also be obtained from:
git://repo.or.cz/qemu/mdroth.git virtagent_v6

CHANGES IN V6:

 - Added a sentinel value to reliably detect the start of an "http" hdr. Used 
to skip past partially sent http content from previous "sessions"
 - Added http hdr tag (currently hardcoded for testing, will switch to uuid) to 
filter out valid-but-unexpected content in channel from previous "sessions"
 - Added timeout mechanism to avoid hanging monitor when agent isn't running
 - Added timed back-off on read's from a virtio-serial that result in ret=0 to 
avoid spinning if host isn't connected. 
 - Added daemonize flags to qemu-va
 - Added sane defaults for channel type and virtio-serial port path
 - Various bug fixes for state machine/job handling logic

CHANGES IN V5:

 - Dependency on virtproxy dropped, virtagent now handles transport and 
multiplexing of bi-directional RPCs internally
 - Removed duplification of qemu_set_fd_handler()-centered i/o code. Support 
for interacting with objects that use qemu_set_fd_handler() now available to 
tools via qemu-tools.c and a set of generalized utility functions
 - Fixed memory leaks in client/monitor functions
 - Various cleanups

CHANGES IN V4:

 - Added guest agent capabilities negotiation
 - Added RPC/monitor command to invoke guest shutdown/reboot/powerdown
 - Added RPC/monitor command to the guest agent
 - Added guest startup notification ("hello")
 - Added syslog()'ing of guest agent RPCs
 - Various cleanups

CHANGES IN V3:

 - Integrated virtagent server into virtproxy chardev. Usage examples below.
 - Consolidated RPC server/client setup into a pair of init routines
 - Fixed buffer overflow in agent_viewfile() and various memory leaks

CHANGES IN V2:

 - All RPC communication is now done using asynchronous/non-blocking read/write 
handlers
 - Previously fork()'d RPC server loop is now integrated into qemu-vp/virtproxy 
i/o loop
 - Cleanups/suggestions from previous RFC

OVERVIEW:

There are a wide range of use cases motivating the need for a guest agent of 
some sort to extend the functionality/usability/control offered by QEMU. Some 
examples include graceful guest shutdown/reboot and notifications thereof, 
copy/paste syncing between host/guest, guest statistics gathering, file access, 
etc.

Ideally these would all be served by a single, easilly extensible agent that 
can be deployed in a wide range of guests. Virtagent is an XMLRPC server, 
integrated into QEMU and a simple guest daemon, aimed at providing this type of 
functionality.

DESIGN:

There are actually 2 RPC servers:

1) a server in the guest agent which handles RPC requests from QEMU
2) a server in the host, integrated into the virtagent chardev, to handle RPC 
requests sent by the guest agent (mainly for handling asynchronous events 
reported by the agent).

Communication is done via RPCs (XMLRPC/HTTP between host and guest), albeit 
with a non-standard implementation that allows for multiplexing server/client 
RPC over a single virtio/isa serial channel.

EXAMPLE USAGE:

 - Configure guest agent to talk to host via virtio-serial
# start guest with virtio-serial/virtagent. for example (RHEL6):
qemu \
-chardev virtagent,id=test0 \
-device virtio-serial \
-device virtserialport,chardev=test0,name=virtagent0 \
-monitor stdio
...
# in the guest:
./qemu-va -c virtio-serial -p /dev/virtio-ports/virtagent0
...
# monitor commands
(qemu) agent_viewdmesg
[139311.710326] wlan0: deauthenticating from 00:30:bd:f7:12:d5 by local 
choice (reason=3)
[139323.469857] wlan0: deauthenticating from 00:21:29:cd:41:ee by local 
choice (reason=3)
...
[257683.375646] wlan0: authenticated
[257683.375684] wlan0: associate with AP 00:30:bd:f7:12:d5 (try 1)
[257683.377932] wlan0: RX AssocResp from 00:30:bd:f7:12:d5 (capab=0x411 
status=0 aid=4)
[257683.377940] wlan0: associated

(qemu) agent_viewfile /proc/meminfo
MemTotal:3985488 kB
MemFree:  400524 kB
Buffers:  220556 kB
Cached:  2073160 kB
SwapCached:0 kB
...
Hugepagesize:   2048 kB
DirectMap4k:8896 kB
DirectMap2M: 4110336 kB
(qemu) agent_shutdown powerdown
(qemu)

KNOWN ISSUES/PLANS:
 - Implement RPC for guest script/command execution
 - Use UUIDs for generating unique tags for each http request/response
 - Scan for sentinel value while reading http content as well to immediately 
detect truncated requests/responses and avoid accidentally consuming new ones
 - switch to standard logging/trace mechanisms
 - outstanding requests should be reset if we get a hello notification (this 
implies guest/guest agent restart)
 - the client socket that qemu connects to send RPCs is a hardcoded filepath. 
This is unacceptable as the socket is channel/process specific and things will 
break when multiple guests are started.

[RFC][PATCH v6 01/23] Move code r

[Qemu-devel] [RFC][PATCH v6 02/23] Add qemu_set_fd_handler() wrappers to qemu-tools.c

2011-01-17 Thread Michael Roth
This adds state information for managing fd handlers to qemu-tools.c so
that tools that build against it can implement an I/O loop for
interacting with objects that use qemu_set_fd_handler()

Signed-off-by: Michael Roth 
---
 qemu-tool.c |   25 -
 1 files changed, 24 insertions(+), 1 deletions(-)

diff --git a/qemu-tool.c b/qemu-tool.c
index 392e1c9..78d3532 100644
--- a/qemu-tool.c
+++ b/qemu-tool.c
@@ -22,6 +22,8 @@
 QEMUClock *rt_clock;
 
 FILE *logfile;
+static QLIST_HEAD(, IOHandlerRecord) io_handlers =
+QLIST_HEAD_INITIALIZER(io_handlers);
 
 struct QEMUBH
 {
@@ -103,11 +105,32 @@ void qemu_bh_delete(QEMUBH *bh)
 qemu_free(bh);
 }
 
+/* definitions to implement i/o loop for fd handlers in tools */
 int qemu_set_fd_handler2(int fd,
  IOCanReadHandler *fd_read_poll,
  IOHandler *fd_read,
  IOHandler *fd_write,
  void *opaque)
 {
-return 0;
+return qemu_set_fd_handler3(&io_handlers, fd, fd_read_poll, fd_read,
+fd_write, opaque);
+}
+
+int qemu_set_fd_handler(int fd,
+IOHandler *fd_read,
+IOHandler *fd_write,
+void *opaque)
+{
+return qemu_set_fd_handler2(fd, NULL, fd_read, fd_write, opaque);
+}
+
+void qemu_get_fdset(int *nfds, fd_set *rfds, fd_set *wfds, fd_set *xfds)
+{
+return qemu_get_fdset2(&io_handlers, nfds, rfds, wfds, xfds);
+}
+
+void qemu_process_fd_handlers(const fd_set *rfds, const fd_set *wfds,
+  const fd_set *xfds)
+{
+return qemu_process_fd_handlers2(&io_handlers, rfds, wfds, xfds);
 }
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 01/23] Move code related to fd handlers into utility functions

2011-01-17 Thread Michael Roth
This allows us to implement an i/o loop outside of vl.c that can
interact with objects that use qemu_set_fd_handler()

Signed-off-by: Michael Roth 
---
 Makefile.objs |2 +-
 qemu-char.h   |4 ++
 qemu-ioh.c|  115 +
 qemu-ioh.h|   34 +
 vl.c  |   86 --
 5 files changed, 170 insertions(+), 71 deletions(-)
 create mode 100644 qemu-ioh.c
 create mode 100644 qemu-ioh.h

diff --git a/Makefile.objs b/Makefile.objs
index c3e52c5..0078921 100644
--- a/Makefile.objs
+++ b/Makefile.objs
@@ -14,7 +14,7 @@ oslib-obj-$(CONFIG_POSIX) += oslib-posix.o
 # block-obj-y is code used by both qemu system emulation and qemu-img
 
 block-obj-y = cutils.o cache-utils.o qemu-malloc.o qemu-option.o module.o
-block-obj-y += nbd.o block.o aio.o aes.o qemu-config.o
+block-obj-y += nbd.o block.o aio.o aes.o qemu-config.o qemu-ioh.o
 block-obj-$(CONFIG_POSIX) += posix-aio-compat.o
 block-obj-$(CONFIG_LINUX_AIO) += linux-aio.o
 
diff --git a/qemu-char.h b/qemu-char.h
index e6ee6c4..7d0794a 100644
--- a/qemu-char.h
+++ b/qemu-char.h
@@ -7,6 +7,7 @@
 #include "qemu-config.h"
 #include "qobject.h"
 #include "qstring.h"
+#include "qemu-ioh.h"
 
 /* character device */
 
@@ -118,4 +119,7 @@ int qemu_set_fd_handler(int fd,
 IOHandler *fd_read,
 IOHandler *fd_write,
 void *opaque);
+void qemu_get_fdset(int *nfds, fd_set *rfds, fd_set *wfds, fd_set *xfds);
+void qemu_process_fd_handlers(const fd_set *rfds, const fd_set *wfds,
+  const fd_set *xfds);
 #endif
diff --git a/qemu-ioh.c b/qemu-ioh.c
new file mode 100644
index 000..cc71470
--- /dev/null
+++ b/qemu-ioh.c
@@ -0,0 +1,115 @@
+/*
+ * QEMU System Emulator
+ *
+ * Copyright (c) 2003-2008 Fabrice Bellard
+ *
+ * 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-ioh.h"
+#include "qlist.h"
+
+/* XXX: fd_read_poll should be suppressed, but an API change is
+   necessary in the character devices to suppress fd_can_read(). */
+int qemu_set_fd_handler3(void *ioh_record_list,
+ int fd,
+ IOCanReadHandler *fd_read_poll,
+ IOHandler *fd_read,
+ IOHandler *fd_write,
+ void *opaque)
+{
+QLIST_HEAD(, IOHandlerRecord) *io_handlers_ptr = ioh_record_list;
+IOHandlerRecord *ioh;
+
+if (!fd_read && !fd_write) {
+QLIST_FOREACH(ioh, io_handlers_ptr, next) {
+if (ioh->fd == fd) {
+ioh->deleted = 1;
+break;
+}
+}
+} else {
+QLIST_FOREACH(ioh, io_handlers_ptr, next) {
+if (ioh->fd == fd)
+goto found;
+}
+ioh = qemu_mallocz(sizeof(IOHandlerRecord));
+QLIST_INSERT_HEAD(io_handlers_ptr, ioh, next);
+found:
+ioh->fd = fd;
+ioh->fd_read_poll = fd_read_poll;
+ioh->fd_read = fd_read;
+ioh->fd_write = fd_write;
+ioh->opaque = opaque;
+ioh->deleted = 0;
+}
+return 0;
+}
+
+/* add entries from ioh record list to fd sets. nfds and fd sets
+ * should be cleared/reset by caller if desired. set a particular
+ * fdset to NULL to ignore fd events of that type
+ */
+void qemu_get_fdset2(void *ioh_record_list, int *nfds, fd_set *rfds,
+ fd_set *wfds, fd_set *xfds)
+{
+QLIST_HEAD(, IOHandlerRecord) *io_handlers = ioh_record_list;
+IOHandlerRecord *ioh;
+
+QLIST_FOREACH(ioh, io_handlers, next) {
+if (ioh->deleted)
+continue;
+if ((rfds != NULL && ioh->fd_read) &&
+(!ioh->fd_read_poll ||
+ ioh->fd_read_poll(ioh->opaque) != 0)) {
+FD_SET(ioh->fd, rfds);
+if (ioh->fd > *nfds)
+*nfds = ioh->fd;
+}
+if (wfds !

[Qemu-devel] [RFC][PATCH v6 11/23] virtagent: add agent_viewdmesg qmp/hmp commands

2011-01-17 Thread Michael Roth
Add commands to view guest dmesg output. Currently it is a 16K buffer.

Signed-off-by: Michael Roth 
---
 hmp-commands.hx |   16 +
 qmp-commands.hx |   35 +
 virtagent.c |   92 +++
 virtagent.h |3 ++
 4 files changed, 146 insertions(+), 0 deletions(-)

diff --git a/hmp-commands.hx b/hmp-commands.hx
index a3e5e27..f60c64f 100644
--- a/hmp-commands.hx
+++ b/hmp-commands.hx
@@ -1344,6 +1344,22 @@ STEXI
 Echo the file identified by @var{filepath} on the guest filesystem
 ETEXI
 
+{
+.name   = "agent_viewdmesg",
+.args_type  = "",
+.params = "",
+.help   = "View guest dmesg output",
+.user_print = do_agent_viewdmesg_print,
+.mhandler.cmd_async = do_agent_viewdmesg,
+.flags  = MONITOR_CMD_ASYNC,
+},
+
+STEXI
+@item agent_viewdmesg
+@findex agent_viewdmesg
+View guest dmesg output
+ETEXI
+
 STEXI
 @end table
 ETEXI
diff --git a/qmp-commands.hx b/qmp-commands.hx
index 9dca7b9..0db38bd 100644
--- a/qmp-commands.hx
+++ b/qmp-commands.hx
@@ -828,6 +828,41 @@ Example:
 EQMP
 
 {
+.name   = "agent_viewdmesg",
+.args_type  = "",
+.params = "",
+.help   = "View guest dmesg output",
+.user_print = do_agent_viewdmesg_print,
+.mhandler.cmd_async = do_agent_viewdmesg,
+.flags  = MONITOR_CMD_ASYNC,
+},
+
+STEXI
+@item agent_viewdmesg
+@findex agent_viewdmesg
+View guest dmesg output
+ETEXI
+SQMP
+agent_viewdmesg
+
+
+View guest dmesg output
+
+Arguments:
+
+(none)
+
+Example:
+
+-> { "execute": "agent_viewdmesg" }
+<- { "return": {
+   "contents": "[353487.942215] usb 1-4: USB disconnect, address 9\n..."
+ }
+   }
+
+EQMP
+
+{
 .name   = "qmp_capabilities",
 .args_type  = "",
 .params = "",
diff --git a/virtagent.c b/virtagent.c
index cd5caf1..0976afe 100644
--- a/virtagent.c
+++ b/virtagent.c
@@ -252,3 +252,95 @@ int do_agent_viewfile(Monitor *mon, const QDict 
*mon_params,
 xmlrpc_DECREF(params);
 return ret;
 }
+
+void do_agent_viewdmesg_print(Monitor *mon, const QObject *data)
+{
+QDict *qdict;
+const char *contents = NULL;
+int i;
+
+qdict = qobject_to_qdict(data);
+if (!qdict_haskey(qdict, "contents")) {
+goto out;
+}
+
+contents = qdict_get_str(qdict, "contents");
+if (contents != NULL) {
+ /* monitor_printf truncates so do it in chunks. also, file_contents
+  * may not be null-termed at proper location so explicitly calc
+  * last chunk sizes */
+for (i = 0; i < strlen(contents); i += 1024) {
+monitor_printf(mon, "%.1024s", contents + i);
+}
+}
+
+out:
+monitor_printf(mon, "\n");
+}
+
+static void do_agent_viewdmesg_cb(const char *resp_data,
+  size_t resp_data_len,
+  MonitorCompletion *mon_cb,
+  void *mon_data)
+{
+xmlrpc_value *resp = NULL;
+char *dmesg = NULL;
+int ret;
+xmlrpc_env env;
+QDict *qdict = qdict_new();
+
+if (resp_data == NULL) {
+LOG("error handling RPC request");
+goto out_no_resp;
+}
+
+xmlrpc_env_init(&env);
+resp = xmlrpc_parse_response(&env, resp_data, resp_data_len);
+if (va_rpc_has_error(&env)) {
+ret = -1;
+goto out_no_resp;
+}
+
+xmlrpc_parse_value(&env, resp, "s", &dmesg);
+if (va_rpc_has_error(&env)) {
+ret = -1;
+goto out;
+}
+
+if (dmesg != NULL) {
+qdict_put(qdict, "contents", qstring_from_str(dmesg));
+}
+
+out:
+xmlrpc_DECREF(resp);
+out_no_resp:
+if (mon_cb) {
+mon_cb(mon_data, QOBJECT(qdict));
+}
+}
+
+/*
+ * do_agent_viewdmesg(): View guest dmesg output
+ */
+int do_agent_viewdmesg(Monitor *mon, const QDict *mon_params,
+  MonitorCompletion cb, void *opaque)
+{
+xmlrpc_env env;
+xmlrpc_value *params;
+int ret;
+
+xmlrpc_env_init(&env);
+
+params = xmlrpc_build_value(&env, "()");
+if (va_rpc_has_error(&env)) {
+return -1;
+}
+
+ret = va_do_rpc(&env, "va.getdmesg", params, do_agent_viewdmesg_cb, cb,
+opaque);
+if (ret) {
+qerror_report(QERR_VA_FAILED, ret, strerror(ret));
+}
+xmlrpc_DECREF(params);
+return ret;
+}
diff --git a/virtagent.h b/virtagent.h
index 1bd7595..b67abc3 100644
--- a/virtagent.h
+++ b/virtagent.h
@@ -33,5 +33,8 @@ int va_client_close(void);
 void do_agent_viewfile_print(Monitor *mon, const QObject *qobject);
 int do_agent_viewfile(Monitor *mon, const QDict *mon_params,
   MonitorCompletion cb, void *opaque);
+void do_agent_viewdmesg_print(Monitor *mon, const QObject *qobject);
+int do_agent_viewdmesg(Monitor *mon, const QDict *mon_params,
+  MonitorCompletion cb, void *opaque);
 
 #end

[Qemu-devel] [RFC][PATCH v6 03/23] Make qemu timers available for tools

2011-01-17 Thread Michael Roth
To be able to use qemu_mod_timer() and friends to register timeout
events for virtagent's qemu-va tool, we need to do the following:

Move several blocks of code out of cpus.c that handle initialization
of qemu's io_thread_fd and working with it via
qemu_notify_event()/qemu_event_read()/etc, and make them accessible
as backend functions to both the emulator code and qemu-tool.c via
wrapper functions within cpus.c and qemu-tool.c, respectively. These
have been added to qemu-ioh.c, where similar treatment was given to
qemu_set_fd_handler() and friends.

Some of these wrapper functions lack declarations when being
built into tools, so we add those via qemu-tool.h, which can be included
by a tool to access them. With these changes we can drive timers in a
tool linking it against qemu-timer.o and then implementing something
similar to the main i/o loop in vl.c:

init_clocks();
configure_alarms("dynticks");
if (init_timer_alarm() < 0) {
errx(EXIT_FAILURE, "could not initialize alarm timer");
}

while (running) {
//do work
qemu_run_all_timers();
}

Signed-off-by: Michael Roth 
---
 cpus.c  |   83 +++-
 qemu-ioh.c  |   93 +++
 qemu-ioh.h  |9 ++
 qemu-tool.c |   92 +-
 qemu-tool.h |   26 
 5 files changed, 229 insertions(+), 74 deletions(-)
 create mode 100644 qemu-tool.h

diff --git a/cpus.c b/cpus.c
index 0309189..2f1adf6 100644
--- a/cpus.c
+++ b/cpus.c
@@ -163,90 +163,24 @@ static int io_thread_fd = -1;
 
 static void qemu_event_increment(void)
 {
-/* Write 8 bytes to be compatible with eventfd.  */
-static const uint64_t val = 1;
-ssize_t ret;
-
-if (io_thread_fd == -1)
-return;
-
-do {
-ret = write(io_thread_fd, &val, sizeof(val));
-} while (ret < 0 && errno == EINTR);
-
-/* EAGAIN is fine, a read must be pending.  */
-if (ret < 0 && errno != EAGAIN) {
-fprintf(stderr, "qemu_event_increment: write() filed: %s\n",
-strerror(errno));
-exit (1);
-}
-}
-
-static void qemu_event_read(void *opaque)
-{
-int fd = (unsigned long)opaque;
-ssize_t len;
-char buffer[512];
-
-/* Drain the notify pipe.  For eventfd, only 8 bytes will be read.  */
-do {
-len = read(fd, buffer, sizeof(buffer));
-} while ((len == -1 && errno == EINTR) || len == sizeof(buffer));
+return iothread_event_increment(&io_thread_fd);
 }
 
 static int qemu_event_init(void)
 {
-int err;
-int fds[2];
-
-err = qemu_eventfd(fds);
-if (err == -1)
-return -errno;
-
-err = fcntl_setfl(fds[0], O_NONBLOCK);
-if (err < 0)
-goto fail;
-
-err = fcntl_setfl(fds[1], O_NONBLOCK);
-if (err < 0)
-goto fail;
-
-qemu_set_fd_handler2(fds[0], NULL, qemu_event_read, NULL,
- (void *)(unsigned long)fds[0]);
-
-io_thread_fd = fds[1];
-return 0;
-
-fail:
-close(fds[0]);
-close(fds[1]);
-return err;
+return iothread_event_init(&io_thread_fd);
 }
 #else
 HANDLE qemu_event_handle;
 
-static void dummy_event_handler(void *opaque)
-{
-}
-
 static int qemu_event_init(void)
 {
-qemu_event_handle = CreateEvent(NULL, FALSE, FALSE, NULL);
-if (!qemu_event_handle) {
-fprintf(stderr, "Failed CreateEvent: %ld\n", GetLastError());
-return -1;
-}
-qemu_add_wait_object(qemu_event_handle, dummy_event_handler, NULL);
-return 0;
+return win32_event_init(&qemu_event_handle);
 }
 
 static void qemu_event_increment(void)
 {
-if (!SetEvent(qemu_event_handle)) {
-fprintf(stderr, "qemu_event_increment: SetEvent failed: %ld\n",
-GetLastError());
-exit (1);
-}
+win32_event_increment(&qemu_event_handle);
 }
 #endif
 
@@ -296,11 +230,10 @@ void qemu_cpu_kick(void *env)
 return;
 }
 
-void qemu_notify_event(void)
+static void qemu_stop_all_vcpus(void)
 {
 CPUState *env = cpu_single_env;
 
-qemu_event_increment ();
 if (env) {
 cpu_exit(env);
 }
@@ -309,6 +242,12 @@ void qemu_notify_event(void)
 }
 }
 
+void qemu_notify_event(void)
+{
+qemu_event_increment();
+qemu_stop_all_vcpus();
+}
+
 void qemu_mutex_lock_iothread(void) {}
 void qemu_mutex_unlock_iothread(void) {}
 
diff --git a/qemu-ioh.c b/qemu-ioh.c
index cc71470..001e7a2 100644
--- a/qemu-ioh.c
+++ b/qemu-ioh.c
@@ -22,7 +22,11 @@
  * THE SOFTWARE.
  */
 #include "qemu-ioh.h"
+#include "qemu-char.h"
 #include "qlist.h"
+#ifdef CONFIG_EVENTFD
+#include 
+#endif
 
 /* XXX: fd_read_poll should be suppressed, but an API change is
necessary in the character devices to suppress fd_can_read(). */
@@ -113,3 +117,92 @@ void qemu_process_fd_handlers2(void *ioh_record_list, 
const fd_set *rfds,
 }
 }
 }
+
+#ifndef _WIN32
+void iothread_event_increment(int *io_thread_fd)
+{
+/* Write 8 bytes to be com

[Qemu-devel] [RFC][PATCH v6 06/23] virtagent: base client definitions

2011-01-17 Thread Michael Roth
Functions for managing client capabilities and creating client RPC jobs.

Signed-off-by: Michael Roth 
---
 qerror.c |8 +++
 qerror.h |6 ++
 roms/seabios |2 +-
 virtagent.c  |  158 ++
 virtagent.h  |   34 
 5 files changed, 207 insertions(+), 1 deletions(-)
 create mode 100644 virtagent.c
 create mode 100644 virtagent.h

diff --git a/qerror.c b/qerror.c
index ac2cdaf..dea8c5f 100644
--- a/qerror.c
+++ b/qerror.c
@@ -200,6 +200,14 @@ static const QErrorStringTable qerror_table[] = {
 .error_fmt = QERR_VNC_SERVER_FAILED,
 .desc  = "Could not start VNC server on %(target)",
 },
+{
+.error_fmt = QERR_RPC_FAILED,
+.desc  = "An RPC error has occurred: %(message)",
+},
+{
+.error_fmt = QERR_VA_FAILED,
+.desc  = "An error was reported by virtagent: %(message)",
+},
 {}
 };
 
diff --git a/qerror.h b/qerror.h
index 943a24b..059c0dc 100644
--- a/qerror.h
+++ b/qerror.h
@@ -165,4 +165,10 @@ QError *qobject_to_qerror(const QObject *obj);
 #define QERR_VNC_SERVER_FAILED \
 "{ 'class': 'VNCServerFailed', 'data': { 'target': %s } }"
 
+#define QERR_RPC_FAILED \
+"{ 'class': 'RPCFailed', 'data': { 'code': %i, 'message': %s } }"
+
+#define QERR_VA_FAILED \
+"{ 'class': 'VirtagentFailed', 'data': { 'code': %i, 'message': %s } }"
+
 #endif /* QERROR_H */
diff --git a/roms/seabios b/roms/seabios
index 0ff9051..17d3e46 16
--- a/roms/seabios
+++ b/roms/seabios
@@ -1 +1 @@
-Subproject commit 0ff9051f756ba739bc2edca77925191c3c6cbc2f
+Subproject commit 17d3e46511aeedc9f09a8216d194d749187b80aa
diff --git a/virtagent.c b/virtagent.c
new file mode 100644
index 000..00eccb5
--- /dev/null
+++ b/virtagent.c
@@ -0,0 +1,158 @@
+/*
+ * virtagent - host/guest RPC client functions
+ *
+ * Copyright IBM Corp. 2010
+ *
+ * Authors:
+ *  Adam Litke
+ *  Michael Roth  
+ *
+ * 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 "qemu_socket.h"
+#include "virtagent-common.h"
+
+static VAClientData *va_client_data;
+
+static void va_set_capabilities(QList *qlist)
+{
+TRACE("called");
+
+if (va_client_data == NULL) {
+LOG("client is uninitialized, unable to set capabilities");
+return;
+}
+
+if (va_client_data->supported_methods != NULL) {
+qobject_decref(QOBJECT(va_client_data->supported_methods));
+va_client_data->supported_methods = NULL;
+TRACE("capabilities reset");
+}
+
+if (qlist != NULL) {
+va_client_data->supported_methods = qlist_copy(qlist);
+TRACE("capabilities set");
+}
+}
+
+typedef struct VACmpState {
+const char *method;
+bool found;
+} VACmpState;
+
+static void va_cmp_capability_iter(QObject *obj, void *opaque)
+{
+QString *method = qobject_to_qstring(obj);
+const char *method_str = NULL;
+VACmpState *cmp_state = opaque;
+
+if (method) {
+method_str = qstring_get_str(method);
+}
+
+if (method_str && opaque) {
+if (strcmp(method_str, cmp_state->method) == 0) {
+cmp_state->found = 1;
+}
+}
+}
+
+static bool va_has_capability(const char *method)
+{
+VACmpState cmp_state;
+
+if (method == NULL) {
+return false;
+}
+
+/* we can assume method introspection is available */
+if (strcmp(method, "system.listMethods") == 0) {
+return true;
+}
+/* assume hello is available to we can probe for/notify the host
+ * rpc server
+ */
+if (strcmp(method, "va.hello") == 0) {
+return true;
+}
+
+/* compare method against the last retrieved supported method list */
+cmp_state.method = method;
+cmp_state.found = false;
+if (va_client_data->supported_methods) {
+qlist_iter(va_client_data->supported_methods,
+   va_cmp_capability_iter,
+   (void *)&cmp_state);
+}
+
+return cmp_state.found;
+}
+
+int va_client_init(VAClientData *client_data)
+{
+client_data->supported_methods = NULL;
+client_data->enabled = true;
+va_client_data = client_data;
+
+return 0;
+}
+
+int va_client_close(void)
+{
+va_client_data = NULL;
+return 0;
+}
+
+static int va_rpc_has_error(xmlrpc_env *env)
+{
+if (env->fault_occurred) {
+qerror_report(QERR_RPC_FAILED, env->fault_code, env->fault_string);
+return -1;
+}
+return 0;
+}
+
+static bool va_is_enabled(void)
+{
+return va_client_data && va_client_data->enabled;
+}
+
+static int va_do_rpc(xmlrpc_env *const env, const char *function,
+ xmlrpc_value *params, VAClientCallback *cb,
+ MonitorCompletion *mon_cb, void *mon_data)
+{
+xmlrpc_mem_block *req_xml;
+int ret;
+
+if (!va_is_enabled()) {
+LOG("virtagent not initialized");
+ret = -E

[Qemu-devel] [RFC][PATCH v6 05/23] virtagent: transport definitions read/send callback functions

2011-01-17 Thread Michael Roth

Signed-off-by: Michael Roth 
---
 virtagent-common.c |  415 
 virtagent-common.h |1 +
 2 files changed, 416 insertions(+), 0 deletions(-)

diff --git a/virtagent-common.c b/virtagent-common.c
index c487252..f8b7d74 100644
--- a/virtagent-common.c
+++ b/virtagent-common.c
@@ -177,6 +177,421 @@ static void va_unset_server_timeout(void)
 }
 
 /***/
+/* callbacks for read/send handlers */
+
+static void va_client_send_cb(enum va_http_status http_status,
+  const char *content, size_t content_len)
+{
+VAClientJob *client_job = va_current_client_job();
+
+TRACE("called");
+assert(client_job != NULL);
+
+if (http_status != VA_HTTP_STATUS_OK) {
+/* TODO: we should reset everything at this point...guest/host will
+ * be out of whack with each other since there's no way to let the
+ * other know job failed (server or client job) if the send channel
+ * is down. But how do we induce the other side to do the same?
+ */
+LOG("error sending http request");
+}
+
+/* request sent ok. free up request xml, then move to
+ * wait (for response) state
+ */
+XMLRPC_MEMBLOCK_FREE(char, client_job->req_data);
+assert(va_set_client_state(VA_CLIENT_WAIT));
+}
+
+static void va_server_send_cb(enum va_http_status http_status,
+  const char *content, size_t content_len)
+{
+VAServerJob *server_job = va_pop_server_job();
+
+TRACE("called");
+assert(server_job != NULL);
+va_unset_server_timeout();
+
+if (http_status != VA_HTTP_STATUS_OK) {
+/* TODO: we should reset everything at this point...guest/host will
+ * be out of whack with each other since there's no way to let the
+ * other know job failed (server or client job) if the send channel
+ * is down
+ */
+LOG("error sending http response");
+return;
+}
+
+/* response sent ok, cleanup server job and kick off the next one */
+XMLRPC_MEMBLOCK_FREE(char, server_job->resp_data);
+qemu_free(server_job);
+va_kick();
+}
+
+static void va_client_read_cb(const char *content, size_t content_len,
+  const char client_tag[64])
+{
+VAClientJob *client_job;
+
+TRACE("called");
+client_job = va_pop_client_job();
+assert(client_job != NULL);
+if (--va_state->client_jobs_in_flight == 0) {
+va_unset_client_timeout();
+}
+if (strncmp(client_job->client_tag, client_tag, 64)) {
+LOG("http client tag mismatch");
+} else {
+TRACE("tag matched: %s", client_tag);
+}
+
+client_job->cb(content, content_len, client_job->mon_cb,
+   client_job->mon_data);
+va_kick();
+}
+
+static void va_server_read_cb(const char *content, size_t content_len,
+  const char client_tag[64])
+{
+int ret;
+
+TRACE("called");
+/* generate response and queue it up for sending */
+ret = va_do_server_rpc(content, content_len, client_tag);
+if (ret != 0) {
+LOG("error creating handling remote rpc request: %s", strerror(ret));
+}
+
+return;
+}
+
+static void va_http_read_cb(enum va_http_status http_status,
+const char *content, size_t content_len,
+const char client_tag[64],
+enum va_http_type http_type)
+{
+TRACE("called");
+if (http_status != VA_HTTP_STATUS_OK) {
+LOG("error reading http stream (type %d)", http_type);
+va_cancel_jobs();
+return;
+}
+
+if (http_type == VA_HTTP_TYPE_REQUEST) {
+TRACE("read request: %s", content);
+va_server_read_cb(content, content_len, client_tag);
+} else if (http_type == VA_HTTP_TYPE_RESPONSE) {
+TRACE("read response: %s", content);
+va_client_read_cb(content, content_len, client_tag);
+} else {
+LOG("unknown http response/request type");
+va_cancel_jobs();
+}
+
+return;
+}
+
+/***/
+/* utility functions for handling http calls */
+
+static void va_http_hdr_init(VAHTState *s, enum va_http_type http_type) {
+const char *preamble;
+
+TRACE("called");
+/* essentially ignored in the context of virtagent, but might as well */
+if (http_type == VA_HTTP_TYPE_REQUEST) {
+preamble = "POST /RPC2 HTTP/1.1";
+} else if (http_type == VA_HTTP_TYPE_RESPONSE) {
+preamble = "HTTP/1.1 200 OK";
+} else {
+s->hdr_len = 0;
+return;
+}
+memset(s->hdr, 0, VA_HDR_LEN_MAX);
+s->hdr_len = sprintf(s->hdr,
+ "%c%s" EOL
+ "Content-Type: text/xml" EOL
+ "Content-Length: %u" EOL
+ "X-Virtagent-Client-Tag: %s" EOL 

[Qemu-devel] [RFC][PATCH v6 08/23] virtagent: add va.getfile RPC

2011-01-17 Thread Michael Roth
Add RPC to retrieve a guest file. This interface is intended
for smaller reads like peeking at logs and /proc and such.

Signed-off-by: Michael Roth 
---
 virtagent-server.c |   59 
 1 files changed, 59 insertions(+), 0 deletions(-)

diff --git a/virtagent-server.c b/virtagent-server.c
index c38a9e0..af4b940 100644
--- a/virtagent-server.c
+++ b/virtagent-server.c
@@ -62,12 +62,71 @@ out:
 return ret;
 }
 
+/* RPC functions common to guest/host daemons */
+
+/* va_getfile(): return file contents
+ * rpc return values:
+ *   - base64-encoded file contents
+ */
+static xmlrpc_value *va_getfile(xmlrpc_env *env,
+xmlrpc_value *params,
+void *user_data)
+{
+const char *path;
+char *file_contents = NULL;
+char buf[VA_FILEBUF_LEN];
+int fd, ret, count = 0;
+xmlrpc_value *result = NULL;
+
+/* parse argument array */
+xmlrpc_decompose_value(env, params, "(s)", &path);
+if (env->fault_occurred) {
+return NULL;
+}
+
+SLOG("va_getfile(), path:%s", path);
+
+fd = open(path, O_RDONLY);
+if (fd == -1) {
+LOG("open failed: %s", strerror(errno));
+xmlrpc_faultf(env, "open failed: %s", strerror(errno));
+return NULL;
+}
+
+while ((ret = read(fd, buf, VA_FILEBUF_LEN)) > 0) {
+file_contents = qemu_realloc(file_contents, count + VA_FILEBUF_LEN);
+memcpy(file_contents + count, buf, ret);
+count += ret;
+if (count > VA_GETFILE_MAX) {
+xmlrpc_faultf(env, "max file size (%d bytes) exceeded",
+  VA_GETFILE_MAX);
+goto EXIT_CLOSE_BAD;
+}
+}
+if (ret == -1) {
+LOG("read failed: %s", strerror(errno));
+xmlrpc_faultf(env, "read failed: %s", strerror(errno));
+goto EXIT_CLOSE_BAD;
+}
+
+result = xmlrpc_build_value(env, "6", file_contents, count);
+
+EXIT_CLOSE_BAD:
+if (file_contents) {
+qemu_free(file_contents);
+}
+close(fd);
+return result;
+}
+
 typedef struct RPCFunction {
 xmlrpc_value *(*func)(xmlrpc_env *env, xmlrpc_value *param, void *unused);
 const char *func_name;
 } RPCFunction;
 
 static RPCFunction guest_functions[] = {
+{ .func = va_getfile,
+  .func_name = "va.getfile" },
 { NULL, NULL }
 };
 static RPCFunction host_functions[] = {
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 04/23] virtagent: common code for managing client/server rpc jobs

2011-01-17 Thread Michael Roth
This implements a simple state machine to manage client/server rpc
jobs being multiplexed over a single channel.

A client job consists of sending an rpc request, reading an
rpc response, then making the appropriate callbacks. We allow one
client job to be processed at a time, which will make the following
state transitions:

VA_CLIENT_IDLE -> VA_CLIENT_SEND (job queued, send channel open)
VA_CLIENT_SEND -> VA_CLIENT_WAIT (request sent, awaiting response)
VA_CLIENT_WAIT -> VA_CLIENT_IDLE (response recieved, callbacks made)

A server job consists of recieving an rpc request, generating a
response, then sending the response. We expect to receive one server
request at a time due to the 1 at a time restriction for client jobs.
Server jobs make the following transitions:

VA_SERVER_IDLE -> VA_SERVER_WAIT (recieved/executed request, send
channel busy, response deferred)
VA_SERVER_IDLE -> VA_SERVER_SEND (recieved/executed request, send
channel open, sending response)
VA_SERVER_WAIT -> VA_SERVER_SEND (send channel now open, sending
response)
VA_SERVER_SEND -> VA_SERVER_IDLE (response sent)

Signed-off-by: Michael Roth 
---
 virtagent-common.c |  613 
 virtagent-common.h |   71 ++
 2 files changed, 684 insertions(+), 0 deletions(-)
 create mode 100644 virtagent-common.c
 create mode 100644 virtagent-common.h

diff --git a/virtagent-common.c b/virtagent-common.c
new file mode 100644
index 000..c487252
--- /dev/null
+++ b/virtagent-common.c
@@ -0,0 +1,613 @@
+/*
+ * virtagent - common host/guest RPC functions
+ *
+ * Copyright IBM Corp. 2010
+ *
+ * Authors:
+ *  Adam Litke
+ *  Michael Roth  
+ *
+ * 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 "virtagent-common.h"
+
+typedef struct VAClientJob {
+char client_tag[64];
+xmlrpc_mem_block *req_data;
+char *resp_data;
+size_t resp_data_len;
+VAClientCallback *cb;
+QTAILQ_ENTRY(VAClientJob) next;
+/* for use by QMP functions */
+MonitorCompletion *mon_cb;
+void *mon_data;
+} VAClientJob;
+
+typedef struct VAServerJob {
+char client_tag[64];
+xmlrpc_mem_block *resp_data;
+char *req_data;
+size_t req_data_len;
+void *opaque;
+QTAILQ_ENTRY(VAServerJob) next;
+} VAServerJob;
+
+enum va_http_status {
+VA_HTTP_STATUS_NEW,
+VA_HTTP_STATUS_OK,
+VA_HTTP_STATUS_ERROR,
+};
+
+enum va_http_type {
+VA_HTTP_TYPE_UNKNOWN = 1,
+VA_HTTP_TYPE_REQUEST,
+VA_HTTP_TYPE_RESPONSE,
+} va_http_type;
+
+typedef void (VAHTSendCallback)(enum va_http_status http_status,
+const char *content, size_t content_len);
+typedef void (VAHTReadCallback)(enum va_http_status http_status,
+const char *content, size_t content_len,
+const char client_tag[64],
+enum va_http_type http_type);
+typedef struct VAHTState {
+enum {
+VA_SEND_START,
+VA_SEND_HDR,
+VA_SEND_BODY,
+VA_READ_START,
+VA_READ_HDR,
+VA_READ_BODY,
+} state;
+char hdr[VA_HDR_LEN_MAX];
+char hdr_client_tag[64];
+size_t hdr_len;
+size_t hdr_pos;
+char *content;
+size_t content_len;
+size_t content_pos;
+VAHTSendCallback *send_cb;
+VAHTReadCallback *read_cb;
+enum va_http_type http_type;
+} VAHTState;
+
+typedef struct VAState {
+bool is_host;
+const char *channel_method;
+const char *channel_path;
+int fd;
+QEMUTimer *client_timer;
+QEMUTimer *server_timer;
+enum va_client_state {
+VA_CLIENT_IDLE = 0,
+VA_CLIENT_SEND, /* sending rpc request */
+VA_CLIENT_WAIT, /* waiting for rpc response */
+} client_state;
+enum va_server_state {
+VA_SERVER_IDLE = 0,
+VA_SERVER_WAIT, /* waiting to send rpc response */
+VA_SERVER_SEND, /* sending rpc response */
+} server_state;
+VAClientData client_data;
+VAServerData server_data;
+int client_job_count;
+int client_jobs_in_flight;
+QTAILQ_HEAD(, VAClientJob) client_jobs;
+int server_job_count;
+QTAILQ_HEAD(, VAServerJob) server_jobs;
+/* for use by async send/read handlers for fd */
+VAHTState send_state;
+VAHTState read_state;
+} VAState;
+
+static VAState *va_state;
+
+static bool va_set_client_state(enum va_client_state client_state);
+static VAServerJob *va_pop_server_job(void);
+static VAClientJob *va_pop_client_job(void);
+static int va_kick(void);
+static int va_connect(void);
+static void va_http_read_handler(void *opaque);
+static void va_http_read_handler_reset(void);
+
+static VAClientJob *va_current_client_job(void)
+{
+TRACE("called");
+return QTAILQ_FIRST(&va_state->client_jobs);
+}
+
+static void va_cancel_jobs(void)
+{
+VAClientJob *cj, *cj_tmp;
+VAServerJob *sj, *sj_tmp

[Qemu-devel] [RFC][PATCH v6 14/23] virtagent: add va.ping RPC

2011-01-17 Thread Michael Roth
Do-nothing RPC that can be used to "ping" the RPC server

Signed-off-by: Michael Roth 
---
 virtagent-server.c |   17 +
 1 files changed, 17 insertions(+), 0 deletions(-)

diff --git a/virtagent-server.c b/virtagent-server.c
index d48c61e..ab8994b 100644
--- a/virtagent-server.c
+++ b/virtagent-server.c
@@ -219,6 +219,19 @@ out_bad:
 return NULL;
 }
 
+/* va_ping(): respond to client. response without error in env
+ *   variable indicates successful response
+ * rpc return values: none
+ */
+static xmlrpc_value *va_ping(xmlrpc_env *env,
+ xmlrpc_value *params,
+ void *user_data)
+{
+xmlrpc_value *result = xmlrpc_build_value(env, "s", "dummy");
+SLOG("va_ping()");
+return result;
+}
+
 typedef struct RPCFunction {
 xmlrpc_value *(*func)(xmlrpc_env *env, xmlrpc_value *param, void *unused);
 const char *func_name;
@@ -231,9 +244,13 @@ static RPCFunction guest_functions[] = {
   .func_name = "va.getdmesg" },
 { .func = va_shutdown,
   .func_name = "va.shutdown" },
+{ .func = va_ping,
+  .func_name = "va.ping" },
 { NULL, NULL }
 };
 static RPCFunction host_functions[] = {
+{ .func = va_ping,
+  .func_name = "va.ping" },
 { NULL, NULL }
 };
 
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 15/23] virtagent: add agent_ping qmp/hmp commands

2011-01-17 Thread Michael Roth
Monitor command to ping the RPC server.

Signed-off-by: Michael Roth 
---
 hmp-commands.hx |   16 
 qmp-commands.hx |   32 +++
 virtagent.c |   74 +++
 virtagent.h |3 ++
 4 files changed, 125 insertions(+), 0 deletions(-)

diff --git a/hmp-commands.hx b/hmp-commands.hx
index 0a8c500..6679771 100644
--- a/hmp-commands.hx
+++ b/hmp-commands.hx
@@ -1376,6 +1376,22 @@ STEXI
 Shutdown/reboot a guest locally
 ETEXI
 
+{
+.name   = "agent_ping",
+.args_type  = "",
+.params = "",
+.help   = "Ping a guest",
+.user_print = do_agent_ping_print,
+.mhandler.cmd_async = do_agent_ping,
+.flags  = MONITOR_CMD_ASYNC,
+},
+
+STEXI
+@item agent_ping
+@findex agent_ping
+Ping a guest
+ETEXI
+
 STEXI
 @end table
 ETEXI
diff --git a/qmp-commands.hx b/qmp-commands.hx
index 98d7270..be6f485 100644
--- a/qmp-commands.hx
+++ b/qmp-commands.hx
@@ -895,6 +895,38 @@ Example:
 EQMP
 
 {
+.name   = "agent_ping",
+.args_type  = "",
+.params = "",
+.help   = "Ping a guest",
+.user_print = do_agent_ping_print,
+.mhandler.cmd_async = do_agent_ping,
+.flags  = MONITOR_CMD_ASYNC,
+},
+
+STEXI
+@item agent_ping
+@findex agent_ping
+Ping a guest
+ETEXI
+SQMP
+agent_ping
+
+
+Ping a guest
+
+Arguments:
+
+(none)
+
+Example:
+
+-> { "execute": "agent_ping" }
+<- { "return": { "response":"ok" } }
+
+EQMP
+
+{
 .name   = "qmp_capabilities",
 .args_type  = "",
 .params = "",
diff --git a/virtagent.c b/virtagent.c
index 27700fb..4b6b7d1 100644
--- a/virtagent.c
+++ b/virtagent.c
@@ -403,3 +403,77 @@ int do_agent_shutdown(Monitor *mon, const QDict 
*mon_params,
 xmlrpc_DECREF(params);
 return ret;
 }
+
+void do_agent_ping_print(Monitor *mon, const QObject *data)
+{
+QDict *qdict;
+const char *response;
+
+TRACE("called");
+
+qdict = qobject_to_qdict(data);
+response = qdict_get_str(qdict, "response");
+if (qdict_haskey(qdict, "response")) {
+monitor_printf(mon, "%s", response);
+}
+
+monitor_printf(mon, "\n");
+}
+
+static void do_agent_ping_cb(const char *resp_data,
+ size_t resp_data_len,
+ MonitorCompletion *mon_cb,
+ void *mon_data)
+{
+xmlrpc_value *resp = NULL;
+xmlrpc_env env;
+QDict *qdict = qdict_new();
+
+TRACE("called");
+
+if (resp_data == NULL) {
+LOG("error handling RPC request");
+qdict_put(qdict, "response", qstring_from_str("error"));
+goto out_no_resp;
+}
+
+xmlrpc_env_init(&env);
+resp = xmlrpc_parse_response(&env, resp_data, resp_data_len);
+if (va_rpc_has_error(&env)) {
+qdict_put(qdict, "response", qstring_from_str("error"));
+goto out_no_resp;
+}
+qdict_put(qdict, "response", qstring_from_str("ok"));
+
+xmlrpc_DECREF(resp);
+out_no_resp:
+if (mon_cb) {
+mon_cb(mon_data, QOBJECT(qdict));
+}
+qobject_decref(QOBJECT(qdict));
+}
+
+/*
+ * do_agent_ping(): Ping a guest
+ */
+int do_agent_ping(Monitor *mon, const QDict *mon_params,
+  MonitorCompletion cb, void *opaque)
+{
+xmlrpc_env env;
+xmlrpc_value *params;
+int ret;
+
+xmlrpc_env_init(&env);
+
+params = xmlrpc_build_value(&env, "(n)");
+if (va_rpc_has_error(&env)) {
+return -1;
+}
+
+ret = va_do_rpc(&env, "va.ping", params, do_agent_ping_cb, cb, opaque);
+if (ret) {
+qerror_report(QERR_VA_FAILED, ret, strerror(ret));
+}
+xmlrpc_DECREF(params);
+return ret;
+}
diff --git a/virtagent.h b/virtagent.h
index 8281b90..7d3a122 100644
--- a/virtagent.h
+++ b/virtagent.h
@@ -38,5 +38,8 @@ int do_agent_viewdmesg(Monitor *mon, const QDict *mon_params,
   MonitorCompletion cb, void *opaque);
 int do_agent_shutdown(Monitor *mon, const QDict *mon_params,
   MonitorCompletion cb, void *opaque);
+void do_agent_ping_print(Monitor *mon, const QObject *qobject);
+int do_agent_ping(Monitor *mon, const QDict *mon_params,
+  MonitorCompletion cb, void *opaque);
 
 #endif /* VIRTAGENT_H */
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 07/23] virtagent: base server definitions

2011-01-17 Thread Michael Roth

Signed-off-by: Michael Roth 
---
 virtagent-server.c |  111 
 virtagent-server.h |   34 
 2 files changed, 145 insertions(+), 0 deletions(-)
 create mode 100644 virtagent-server.c
 create mode 100644 virtagent-server.h

diff --git a/virtagent-server.c b/virtagent-server.c
new file mode 100644
index 000..c38a9e0
--- /dev/null
+++ b/virtagent-server.c
@@ -0,0 +1,111 @@
+/*
+ * virtagent - host/guest RPC server functions
+ *
+ * Copyright IBM Corp. 2010
+ *
+ * Authors:
+ *  Adam Litke
+ *  Michael Roth  
+ *
+ * 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 
+#include "qemu_socket.h"
+#include "virtagent-common.h"
+
+static bool va_enable_syslog = false; /* enable syslog'ing of RPCs */
+
+#define SLOG(msg, ...) do { \
+char msg_buf[1024]; \
+if (!va_enable_syslog) { \
+break; \
+} \
+snprintf(msg_buf, 1024, msg, ## __VA_ARGS__); \
+syslog(LOG_INFO, "virtagent, %s", msg_buf); \
+} while(0)
+
+static VAServerData *va_server_data;
+
+static bool va_server_is_enabled(void)
+{
+return va_server_data && va_server_data->enabled;
+}
+
+int va_do_server_rpc(const char *content, size_t content_len, const char *tag)
+{
+xmlrpc_mem_block *resp_xml;
+int ret;
+
+TRACE("called");
+
+if (!va_server_is_enabled()) {
+ret = -EBUSY;
+goto out;
+}
+resp_xml = xmlrpc_registry_process_call(&va_server_data->env,
+va_server_data->registry,
+NULL, content, content_len);
+if (resp_xml == NULL) {
+LOG("error processing RPC request");
+ret = -EINVAL;
+goto out;
+}
+
+ret = va_server_job_add(resp_xml, tag);
+if (ret != 0) {
+LOG("error adding server job: %s", strerror(ret));
+}
+
+out:
+return ret;
+}
+
+typedef struct RPCFunction {
+xmlrpc_value *(*func)(xmlrpc_env *env, xmlrpc_value *param, void *unused);
+const char *func_name;
+} RPCFunction;
+
+static RPCFunction guest_functions[] = {
+{ NULL, NULL }
+};
+static RPCFunction host_functions[] = {
+{ NULL, NULL }
+};
+
+static void va_register_functions(xmlrpc_env *env, xmlrpc_registry *registry,
+  RPCFunction *list)
+{
+int i;
+for (i = 0; list[i].func != NULL; ++i) {
+TRACE("adding func: %s", list[i].func_name);
+xmlrpc_registry_add_method(env, registry, NULL, list[i].func_name,
+   list[i].func, NULL);
+}
+}
+
+int va_server_init(VAServerData *server_data, bool is_host)
+{
+RPCFunction *func_list = is_host ? host_functions : guest_functions;
+
+va_enable_syslog = !is_host; /* enable logging for guest agent */
+xmlrpc_env_init(&server_data->env);
+server_data->registry = xmlrpc_registry_new(&server_data->env);
+va_register_functions(&server_data->env, server_data->registry, func_list);
+server_data->enabled = true;
+server_data->is_host = true;
+va_server_data = server_data;
+
+return 0;
+}
+
+int va_server_close(void)
+{
+if (va_server_data != NULL) {
+xmlrpc_registry_free(va_server_data->registry);
+xmlrpc_env_clean(&va_server_data->env);
+va_server_data = NULL;
+}
+return 0;
+}
diff --git a/virtagent-server.h b/virtagent-server.h
new file mode 100644
index 000..9f68921
--- /dev/null
+++ b/virtagent-server.h
@@ -0,0 +1,34 @@
+/*
+ * virt-agent - host/guest RPC daemon functions
+ *
+ * Copyright IBM Corp. 2010
+ *
+ * Authors:
+ *  Michael Roth  
+ *
+ * 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 
+#include 
+
+#define GUEST_AGENT_SERVICE_ID "virtagent"
+#define GUEST_AGENT_PATH "/tmp/virtagent-guest.sock"
+#define HOST_AGENT_SERVICE_ID "virtagent-host"
+#define HOST_AGENT_PATH "/tmp/virtagent-host.sock"
+#define VA_GETFILE_MAX 1 << 30
+#define VA_FILEBUF_LEN 16384
+#define VA_DMESG_LEN 16384
+
+typedef struct VAServerData {
+xmlrpc_env env;
+xmlrpc_registry *registry;
+bool enabled;
+bool is_host;
+} VAServerData;
+
+int va_server_init(VAServerData *server_data, bool is_host);
+int va_server_close(void);
+int va_do_server_rpc(const char *content, size_t content_len, const char 
tag[64]);
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 09/23] virtagent: add agent_viewfile qmp/hmp command

2011-01-17 Thread Michael Roth
Utilize the getfile RPC to provide a means to view text files in the
guest. Getfile can handle binary files as well but we don't advertise
that here due to the special handling requiring to store it and provide
it back to the user (base64 encoding it for instance). Hence the
otherwise confusing "viewfile" as opposed to "getfile".

Signed-off-by: Michael Roth 
---
 hmp-commands.hx |   16 +
 monitor.c   |1 +
 qmp-commands.hx |   33 +++
 virtagent.c |   96 +++
 virtagent.h |3 ++
 5 files changed, 149 insertions(+), 0 deletions(-)

diff --git a/hmp-commands.hx b/hmp-commands.hx
index 1cea572..a3e5e27 100644
--- a/hmp-commands.hx
+++ b/hmp-commands.hx
@@ -1328,6 +1328,22 @@ show available trace events and their state
 ETEXI
 #endif
 
+{
+.name   = "agent_viewfile",
+.args_type  = "filepath:s",
+.params = "filepath",
+.help   = "Echo a file from the guest filesystem",
+.user_print = do_agent_viewfile_print,
+.mhandler.cmd_async = do_agent_viewfile,
+.flags  = MONITOR_CMD_ASYNC,
+},
+
+STEXI
+@item agent_viewfile @var{filepath}
+@findex agent_viewfile
+Echo the file identified by @var{filepath} on the guest filesystem
+ETEXI
+
 STEXI
 @end table
 ETEXI
diff --git a/monitor.c b/monitor.c
index f258000..cd015aa 100644
--- a/monitor.c
+++ b/monitor.c
@@ -57,6 +57,7 @@
 #include "json-parser.h"
 #include "osdep.h"
 #include "exec-all.h"
+#include "virtagent.h"
 #ifdef CONFIG_SIMPLE_TRACE
 #include "trace.h"
 #endif
diff --git a/qmp-commands.hx b/qmp-commands.hx
index 56c4d8b..9dca7b9 100644
--- a/qmp-commands.hx
+++ b/qmp-commands.hx
@@ -795,6 +795,39 @@ Example:
 EQMP
 
 {
+.name   = "agent_viewfile",
+.args_type  = "filepath:s",
+.params = "filepath",
+.help   = "Echo a file from the guest filesystem",
+.user_print = monitor_user_noop,
+.mhandler.cmd_async = do_agent_viewfile,
+.flags  = MONITOR_CMD_ASYNC,
+},
+
+STEXI
+@item agent_viewfile @var{filepath}
+@findex agent_viewfile
+Echo the file identified by @var{filepath} on the guest filesystem
+ETEXI
+SQMP
+agent_viewfile
+
+
+Echo the file identified by @var{filepath} from the guest filesystem.
+
+Arguments:
+
+- "filepath": Full guest path of the desired file
+
+Example:
+
+-> { "execute": "agent_viewfile",
+"arguments": { "filepath": "/sys/kernel/kexec_loaded" } }
+<- { "return": { "contents": "0" } }
+
+EQMP
+
+{
 .name   = "qmp_capabilities",
 .args_type  = "",
 .params = "",
diff --git a/virtagent.c b/virtagent.c
index 00eccb5..cd5caf1 100644
--- a/virtagent.c
+++ b/virtagent.c
@@ -156,3 +156,99 @@ out_free:
 out:
 return ret;
 }
+
+/* QMP/HMP RPC client functions */
+
+void do_agent_viewfile_print(Monitor *mon, const QObject *data)
+{
+QDict *qdict;
+const char *contents = NULL;
+int i;
+
+qdict = qobject_to_qdict(data);
+if (!qdict_haskey(qdict, "contents")) {
+return;
+}
+
+contents = qdict_get_str(qdict, "contents");
+if (contents != NULL) {
+ /* monitor_printf truncates so do it in chunks. also, file_contents
+  * may not be null-termed at proper location so explicitly calc
+  * last chunk sizes */
+for (i = 0; i < strlen(contents); i += 1024) {
+monitor_printf(mon, "%.1024s", contents + i);
+}
+}
+monitor_printf(mon, "\n");
+}
+
+static void do_agent_viewfile_cb(const char *resp_data,
+ size_t resp_data_len,
+ MonitorCompletion *mon_cb,
+ void *mon_data)
+{
+xmlrpc_value *resp = NULL;
+char *file_contents = NULL;
+size_t file_size;
+int ret;
+xmlrpc_env env;
+QDict *qdict = qdict_new();
+
+if (resp_data == NULL) {
+LOG("error handling RPC request");
+goto out_no_resp;
+}
+
+xmlrpc_env_init(&env);
+resp = xmlrpc_parse_response(&env, resp_data, resp_data_len);
+if (va_rpc_has_error(&env)) {
+ret = -1;
+goto out_no_resp;
+}
+
+xmlrpc_parse_value(&env, resp, "6", &file_contents, &file_size);
+if (va_rpc_has_error(&env)) {
+ret = -1;
+goto out;
+}
+
+if (file_contents != NULL) {
+qdict_put(qdict, "contents",
+  qstring_from_substr(file_contents, 0, file_size-1));
+}
+
+out:
+xmlrpc_DECREF(resp);
+out_no_resp:
+if (mon_cb) {
+mon_cb(mon_data, QOBJECT(qdict));
+}
+qobject_decref(QOBJECT(qdict));
+}
+
+/*
+ * do_agent_viewfile(): View a text file in the guest
+ */
+int do_agent_viewfile(Monitor *mon, const QDict *mon_params,
+  MonitorCompletion cb, void *opaque)
+{
+xmlrpc_env env;
+xmlrpc_value *params;
+const char *filepath;
+int ret;
+
+filepath = q

[Qemu-devel] [RFC][PATCH v6 18/23] virtagent: add va.hello RPC

2011-01-17 Thread Michael Roth
This RPC tells us the guest agent is up and ready, and invokes guest
agent capability negotiation

Signed-off-by: Michael Roth 
---
 virtagent-server.c |   22 ++
 1 files changed, 22 insertions(+), 0 deletions(-)

diff --git a/virtagent-server.c b/virtagent-server.c
index ab8994b..b7e51ed 100644
--- a/virtagent-server.c
+++ b/virtagent-server.c
@@ -232,6 +232,26 @@ static xmlrpc_value *va_ping(xmlrpc_env *env,
 return result;
 }
 
+/* va_hello(): handle client startup notification
+ * rpc return values: none
+ */
+
+static xmlrpc_value *va_hello(xmlrpc_env *env,
+   xmlrpc_value *params,
+   void *user_data)
+{
+xmlrpc_value *result;
+int ret;
+TRACE("called");
+SLOG("va_hello()");
+result = xmlrpc_build_value(env, "s", "dummy");
+ret = va_client_init_capabilities();
+if (ret < 0) {
+LOG("error setting initializing client capabilities");
+}
+return result;
+}
+
 typedef struct RPCFunction {
 xmlrpc_value *(*func)(xmlrpc_env *env, xmlrpc_value *param, void *unused);
 const char *func_name;
@@ -251,6 +271,8 @@ static RPCFunction guest_functions[] = {
 static RPCFunction host_functions[] = {
 { .func = va_ping,
   .func_name = "va.ping" },
+{ .func = va_hello,
+  .func_name = "va.hello" },
 { NULL, NULL }
 };
 
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 12/23] virtagent: add va.shutdown RPC

2011-01-17 Thread Michael Roth
RPC to initiate guest reboot/halt/powerdown

Signed-off-by: Michael Roth 
---
 virtagent-server.c |   58 
 1 files changed, 58 insertions(+), 0 deletions(-)

diff --git a/virtagent-server.c b/virtagent-server.c
index f97e4b1..d48c61e 100644
--- a/virtagent-server.c
+++ b/virtagent-server.c
@@ -163,6 +163,62 @@ EXIT_NOCLOSE:
 return result;
 }
 
+/* va_shutdown(): initiate guest shutdown
+ * rpc return values: none
+ */
+static xmlrpc_value *va_shutdown(xmlrpc_env *env,
+xmlrpc_value *params,
+void *user_data)
+{
+int ret;
+const char *shutdown_type, *shutdown_flag;
+xmlrpc_value *result = xmlrpc_build_value(env, "s", "dummy");
+
+TRACE("called");
+xmlrpc_decompose_value(env, params, "(s)", &shutdown_type);
+if (env->fault_occurred) {
+goto out_bad;
+}
+
+if (strcmp(shutdown_type, "halt") == 0) {
+shutdown_flag = "-H";
+} else if (strcmp(shutdown_type, "powerdown") == 0) {
+shutdown_flag = "-P";
+} else if (strcmp(shutdown_type, "reboot") == 0) {
+shutdown_flag = "-r";
+} else {
+xmlrpc_faultf(env, "invalid shutdown type: %s", shutdown_type);
+goto out_bad;
+}
+
+SLOG("va_shutdown(), shutdown_type:%s", shutdown_type);
+
+ret = fork();
+if (ret == 0) {
+/* child, start the shutdown */
+setsid();
+fclose(stdin);
+fclose(stdout);
+fclose(stderr);
+
+sleep(5);
+ret = execl("/sbin/shutdown", "shutdown", shutdown_flag, "+0",
+"hypervisor initiated shutdown", (char*)NULL);
+if (ret < 0) {
+LOG("execl() failed: %s", strerror(errno));
+exit(1);
+}
+TRACE("shouldn't be here");
+exit(0);
+} else if (ret < 0) {
+xmlrpc_faultf(env, "fork() failed: %s", strerror(errno));
+}
+
+return result;
+out_bad:
+return NULL;
+}
+
 typedef struct RPCFunction {
 xmlrpc_value *(*func)(xmlrpc_env *env, xmlrpc_value *param, void *unused);
 const char *func_name;
@@ -173,6 +229,8 @@ static RPCFunction guest_functions[] = {
   .func_name = "va.getfile" },
 { .func = va_getdmesg,
   .func_name = "va.getdmesg" },
+{ .func = va_shutdown,
+  .func_name = "va.shutdown" },
 { NULL, NULL }
 };
 static RPCFunction host_functions[] = {
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 13/23] virtagent: add agent_shutdown qmp/hmp commands

2011-01-17 Thread Michael Roth
Provide monitor command to initiate guest reboot/halt/powerdown

Signed-off-by: Michael Roth 
---
 hmp-commands.hx |   16 ++
 qmp-commands.hx |   32 +
 virtagent.c |   59 +++
 virtagent.h |2 +
 4 files changed, 109 insertions(+), 0 deletions(-)

diff --git a/hmp-commands.hx b/hmp-commands.hx
index f60c64f..0a8c500 100644
--- a/hmp-commands.hx
+++ b/hmp-commands.hx
@@ -1360,6 +1360,22 @@ STEXI
 View guest dmesg output
 ETEXI
 
+{
+.name   = "agent_shutdown",
+.args_type  = "shutdown_type:s",
+.params = "[reboot|shutdown|poweroff]",
+.help   = "Shutdown/reboot a guest locally",
+.user_print = monitor_user_noop,
+.mhandler.cmd_async = do_agent_shutdown,
+.flags  = MONITOR_CMD_ASYNC,
+},
+
+STEXI
+@item agent_shutdown
+@findex agent_shutdown
+Shutdown/reboot a guest locally
+ETEXI
+
 STEXI
 @end table
 ETEXI
diff --git a/qmp-commands.hx b/qmp-commands.hx
index 0db38bd..98d7270 100644
--- a/qmp-commands.hx
+++ b/qmp-commands.hx
@@ -863,6 +863,38 @@ Example:
 EQMP
 
 {
+.name   = "agent_shutdown",
+.args_type  = "shutdown_type:s",
+.params = "[reboot|shutdown|poweroff]",
+.help   = "Shutdown/reboot the guest locally",
+.user_print = monitor_user_noop,
+.mhandler.cmd_async = do_agent_shutdown,
+.flags  = MONITOR_CMD_ASYNC,
+},
+
+STEXI
+@item agent_shutdown
+@findex agent_shutdown
+Shutdown/reboot the guest locally
+ETEXI
+SQMP
+agent_shutdown
+
+
+Shutdown the guest locally
+
+Arguments:
+
+(none)
+
+Example:
+
+-> { "execute": "agent_shutdown" }
+<- { "return": {} }
+
+EQMP
+
+{
 .name   = "qmp_capabilities",
 .args_type  = "",
 .params = "",
diff --git a/virtagent.c b/virtagent.c
index 0976afe..27700fb 100644
--- a/virtagent.c
+++ b/virtagent.c
@@ -344,3 +344,62 @@ int do_agent_viewdmesg(Monitor *mon, const QDict 
*mon_params,
 xmlrpc_DECREF(params);
 return ret;
 }
+
+static void do_agent_shutdown_cb(const char *resp_data,
+ size_t resp_data_len,
+ MonitorCompletion *mon_cb,
+ void *mon_data)
+{
+xmlrpc_value *resp = NULL;
+xmlrpc_env env;
+
+TRACE("called");
+
+if (resp_data == NULL) {
+LOG("error handling RPC request");
+goto out_no_resp;
+}
+
+xmlrpc_env_init(&env);
+resp = xmlrpc_parse_response(&env, resp_data, resp_data_len);
+if (va_rpc_has_error(&env)) {
+LOG("RPC Failed (%i): %s\n", env.fault_code,
+env.fault_string);
+goto out_no_resp;
+}
+
+xmlrpc_DECREF(resp);
+out_no_resp:
+if (mon_cb) {
+mon_cb(mon_data, NULL);
+}
+}
+
+/*
+ * do_agent_shutdown(): Shutdown a guest
+ */
+int do_agent_shutdown(Monitor *mon, const QDict *mon_params,
+  MonitorCompletion cb, void *opaque)
+{
+xmlrpc_env env;
+xmlrpc_value *params;
+const char *shutdown_type;
+int ret;
+
+TRACE("called");
+
+xmlrpc_env_init(&env);
+shutdown_type = qdict_get_str(mon_params, "shutdown_type");
+params = xmlrpc_build_value(&env, "(s)", shutdown_type);
+if (va_rpc_has_error(&env)) {
+return -1;
+}
+
+ret = va_do_rpc(&env, "va.shutdown", params, do_agent_shutdown_cb, cb,
+opaque);
+if (ret) {
+qerror_report(QERR_VA_FAILED, ret, strerror(ret));
+}
+xmlrpc_DECREF(params);
+return ret;
+}
diff --git a/virtagent.h b/virtagent.h
index b67abc3..8281b90 100644
--- a/virtagent.h
+++ b/virtagent.h
@@ -36,5 +36,7 @@ int do_agent_viewfile(Monitor *mon, const QDict *mon_params,
 void do_agent_viewdmesg_print(Monitor *mon, const QObject *qobject);
 int do_agent_viewdmesg(Monitor *mon, const QDict *mon_params,
   MonitorCompletion cb, void *opaque);
+int do_agent_shutdown(Monitor *mon, const QDict *mon_params,
+  MonitorCompletion cb, void *opaque);
 
 #endif /* VIRTAGENT_H */
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 10/23] virtagent: add va.getdmesg RPC

2011-01-17 Thread Michael Roth
Add RPC to view guest dmesg output.

Signed-off-by: Michael Roth 
---
 virtagent-server.c |   46 ++
 1 files changed, 46 insertions(+), 0 deletions(-)

diff --git a/virtagent-server.c b/virtagent-server.c
index af4b940..f97e4b1 100644
--- a/virtagent-server.c
+++ b/virtagent-server.c
@@ -119,6 +119,50 @@ EXIT_CLOSE_BAD:
 return result;
 }
 
+/* va_getdmesg(): return dmesg output
+ * rpc return values:
+ *   - dmesg output as a string
+ */
+static xmlrpc_value *va_getdmesg(xmlrpc_env *env,
+  xmlrpc_value *params,
+  void *user_data)
+{
+char *dmesg_buf = NULL, cmd[256];
+int ret;
+xmlrpc_value *result = NULL;
+FILE *pipe;
+
+SLOG("va_getdmesg()");
+
+dmesg_buf = qemu_mallocz(VA_DMESG_LEN + 2048);
+sprintf(cmd, "dmesg -s %d", VA_DMESG_LEN);
+
+pipe = popen(cmd, "r");
+if (pipe == NULL) {
+LOG("popen failed: %s", strerror(errno));
+xmlrpc_faultf(env, "popen failed: %s", strerror(errno));
+goto EXIT_NOCLOSE;
+}
+
+ret = fread(dmesg_buf, sizeof(char), VA_DMESG_LEN, pipe);
+if (!ferror(pipe)) {
+dmesg_buf[ret] = '\0';
+TRACE("dmesg:\n%s", dmesg_buf);
+result = xmlrpc_build_value(env, "s", dmesg_buf);
+} else {
+LOG("fread failed");
+xmlrpc_faultf(env, "popen failed: %s", strerror(errno));
+}
+
+pclose(pipe);
+EXIT_NOCLOSE:
+if (dmesg_buf) {
+qemu_free(dmesg_buf);
+}
+
+return result;
+}
+
 typedef struct RPCFunction {
 xmlrpc_value *(*func)(xmlrpc_env *env, xmlrpc_value *param, void *unused);
 const char *func_name;
@@ -127,6 +171,8 @@ typedef struct RPCFunction {
 static RPCFunction guest_functions[] = {
 { .func = va_getfile,
   .func_name = "va.getfile" },
+{ .func = va_getdmesg,
+  .func_name = "va.getdmesg" },
 { NULL, NULL }
 };
 static RPCFunction host_functions[] = {
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 16/23] virtagent: add agent_capabilities qmp/hmp commands

2011-01-17 Thread Michael Roth
Call guest agent's built-in introspection functions to get a list of
supported RPCs, and re-negotiate guest agent capabilities to determine
what agent_* commands are supported.

Signed-off-by: Michael Roth 
---
 hmp-commands.hx |   16 +
 qmp-commands.hx |   32 ++
 virtagent.c |   98 +++
 virtagent.h |3 ++
 4 files changed, 149 insertions(+), 0 deletions(-)

diff --git a/hmp-commands.hx b/hmp-commands.hx
index 6679771..52d4821 100644
--- a/hmp-commands.hx
+++ b/hmp-commands.hx
@@ -1392,6 +1392,22 @@ STEXI
 Ping a guest
 ETEXI
 
+{
+.name   = "agent_capabilities",
+.args_type  = "",
+.params = "",
+.help   = "Fetch and re-negotiate guest agent capabilities",
+.user_print = do_agent_capabilities_print,
+.mhandler.cmd_async = do_agent_capabilities,
+.flags  = MONITOR_CMD_ASYNC,
+},
+
+STEXI
+@item agent_capabilities
+@findex agent_capabilities
+Fetch and re-negotiate guest agent capabilties
+ETEXI
+
 STEXI
 @end table
 ETEXI
diff --git a/qmp-commands.hx b/qmp-commands.hx
index be6f485..5a14191 100644
--- a/qmp-commands.hx
+++ b/qmp-commands.hx
@@ -927,6 +927,38 @@ Example:
 EQMP
 
 {
+.name   = "agent_capabilities",
+.args_type  = "",
+.params = "",
+.help   = "Fetch and re-negotiate guest agent capabilities",
+.user_print = do_agent_capabilities_print,
+.mhandler.cmd_async = do_agent_capabilities,
+.flags  = MONITOR_CMD_ASYNC,
+},
+
+STEXI
+@item agent_capabilities
+@findex agent_capabilities
+Fetch and re-negotiate guest agent capabilties
+ETEXI
+SQMP
+agent_capabilities
+
+
+Fetch and re-negotiate guest agent capabilities
+
+Arguments:
+
+(none)
+
+Example:
+
+-> { "execute": "agent_capabilities" }
+<- { "return":["va.shutdown", "va.getdmesg", "va.getfile", ... ] }
+
+EQMP
+
+{
 .name   = "qmp_capabilities",
 .args_type  = "",
 .params = "",
diff --git a/virtagent.c b/virtagent.c
index 4b6b7d1..99efe2b 100644
--- a/virtagent.c
+++ b/virtagent.c
@@ -477,3 +477,101 @@ int do_agent_ping(Monitor *mon, const QDict *mon_params,
 xmlrpc_DECREF(params);
 return ret;
 }
+
+static void va_print_capability_iter(QObject *obj, void *opaque)
+{
+Monitor *mon = opaque;
+QString *method = qobject_to_qstring(obj);
+const char *method_str;
+
+if (method) {
+method_str = qstring_get_str(method);
+monitor_printf(mon, "%s\n", method_str); 
+}
+}
+
+void do_agent_capabilities_print(Monitor *mon, const QObject *data)
+{
+QList *qlist;
+
+TRACE("called");
+
+monitor_printf(mon, "the following RPC methods are supported by the guest 
agent:\n");
+qlist = qobject_to_qlist(data);
+qlist_iter(qlist, va_print_capability_iter, mon);
+}
+
+static void do_agent_capabilities_cb(const char *resp_data,
+ size_t resp_data_len,
+ MonitorCompletion *mon_cb,
+ void *mon_data)
+{
+xmlrpc_value *resp = NULL;
+xmlrpc_value *cur_val = NULL;
+const char *cur_method = NULL;
+xmlrpc_env env;
+QList *qlist = qlist_new();
+int i;
+
+TRACE("called");
+
+if (resp_data == NULL) {
+LOG("error handling RPC request");
+goto out_no_resp;
+}
+
+TRACE("resp = %s\n", resp_data);
+
+xmlrpc_env_init(&env);
+resp = xmlrpc_parse_response(&env, resp_data, resp_data_len);
+if (va_rpc_has_error(&env)) {
+goto out_no_resp;
+}
+
+/* extract the list of supported RPCs */
+for (i = 0; i < xmlrpc_array_size(&env, resp); i++) {
+xmlrpc_array_read_item(&env, resp, i, &cur_val);
+xmlrpc_read_string(&env, cur_val, &cur_method);
+if (cur_method) {
+TRACE("cur_method: %s", cur_method);
+qlist_append_obj(qlist, QOBJECT(qstring_from_str(cur_method)));
+}
+xmlrpc_DECREF(cur_val);
+}
+
+/* set our client capabilities accordingly */
+va_set_capabilities(qlist);
+
+xmlrpc_DECREF(resp);
+out_no_resp:
+if (mon_cb) {
+mon_cb(mon_data, QOBJECT(qlist));
+}
+qobject_decref(QOBJECT(qlist));
+}
+
+/*
+ * do_agent_capabilities(): Fetch/re-negotiate guest agent capabilities
+ */
+int do_agent_capabilities(Monitor *mon, const QDict *mon_params,
+  MonitorCompletion cb, void *opaque)
+{
+xmlrpc_env env;
+xmlrpc_value *params;
+int ret;
+
+xmlrpc_env_init(&env);
+
+params = xmlrpc_build_value(&env, "()");
+if (va_rpc_has_error(&env)) {
+return -1;
+}
+
+ret = va_do_rpc(&env, "system.listMethods", params,
+do_agent_capabilities_cb, cb, opaque);
+if (ret) {
+qerror_report(QERR_VA_FAILED, ret, strerror(ret));
+}
+xmlrpc_DECREF(params);
+return ret;
+}
diff --

Re: [Qemu-devel] [PATCH 0/8] Some more AHCI work

2011-01-17 Thread Gerd Hoffmann

On 12/20/10 22:13, Alexander Graf wrote:

Clearly, AHCI as is is not perfect yet (intentionally, release early,
release often, remember?). This patch set makes it work with SeaBIOS
so booting Windows 7 works flawlessly for me.


Confirmed.  Had to reinstall my win7 test vm today, tried with this 
patch series applied (still applies fine to master btw) and using AHCI 
for both cdrom and hard disk -- worked just fine.


Acked-by: Gerd Hoffmann 

cheers,
  Gerd




[Qemu-devel] [RFC][PATCH v6 17/23] virtagent: add client capabilities init function

2011-01-17 Thread Michael Roth
Non-monitor version of agent_capabilities monitor function. This is
called by the local RPC server when it gets a "hello" from the guest
agent to re-negotiate guest agent capabilities.

Signed-off-by: Michael Roth 
---
 virtagent.c |   18 ++
 virtagent.h |1 +
 2 files changed, 19 insertions(+), 0 deletions(-)

diff --git a/virtagent.c b/virtagent.c
index 99efe2b..3ea6b85 100644
--- a/virtagent.c
+++ b/virtagent.c
@@ -575,3 +575,21 @@ int do_agent_capabilities(Monitor *mon, const QDict 
*mon_params,
 xmlrpc_DECREF(params);
 return ret;
 }
+
+/* non-HMP/QMP RPC client functions */
+
+int va_client_init_capabilities(void)
+{
+xmlrpc_env env;
+xmlrpc_value *params;
+
+xmlrpc_env_init(&env);
+
+params = xmlrpc_build_value(&env, "()");
+if (va_rpc_has_error(&env)) {
+return -1;
+}
+
+return va_do_rpc(&env, "system.listMethods", params,
+ do_agent_capabilities_cb, NULL, NULL);
+}
diff --git a/virtagent.h b/virtagent.h
index da70317..127585b 100644
--- a/virtagent.h
+++ b/virtagent.h
@@ -44,5 +44,6 @@ int do_agent_ping(Monitor *mon, const QDict *mon_params,
 void do_agent_capabilities_print(Monitor *mon, const QObject *qobject);
 int do_agent_capabilities(Monitor *mon, const QDict *mon_params,
   MonitorCompletion cb, void *opaque);
+int va_client_init_capabilities(void);
 
 #endif /* VIRTAGENT_H */
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 19/23] virtagent: add "hello" notification function for guest agent

2011-01-17 Thread Michael Roth
This tells the host RPC server (QEMU) that we're up and running

Signed-off-by: Michael Roth 
---
 virtagent.c |   47 +++
 virtagent.h |1 +
 2 files changed, 48 insertions(+), 0 deletions(-)

diff --git a/virtagent.c b/virtagent.c
index 3ea6b85..b5e7944 100644
--- a/virtagent.c
+++ b/virtagent.c
@@ -593,3 +593,50 @@ int va_client_init_capabilities(void)
 return va_do_rpc(&env, "system.listMethods", params,
  do_agent_capabilities_cb, NULL, NULL);
 }
+
+static void va_send_hello_cb(const char *resp_data,
+ size_t resp_data_len,
+ MonitorCompletion *mon_cb,
+ void *mon_data)
+{
+xmlrpc_value *resp = NULL;
+xmlrpc_env env;
+
+TRACE("called");
+
+if (resp_data == NULL) {
+LOG("error handling RPC request");
+return;
+}
+
+xmlrpc_env_init(&env);
+resp = xmlrpc_parse_response(&env, resp_data, resp_data_len);
+if (va_rpc_has_error(&env)) {
+LOG("error parsing RPC response");
+return;
+}
+
+xmlrpc_DECREF(resp);
+}
+
+int va_send_hello(void)
+{
+xmlrpc_env env;
+xmlrpc_value *params;
+int ret;
+
+TRACE("called");
+
+xmlrpc_env_init(&env);
+params = xmlrpc_build_value(&env, "()");
+if (va_rpc_has_error(&env)) {
+return -1;
+}
+
+ret = va_do_rpc(&env, "va.hello", params, va_send_hello_cb, NULL, NULL);
+if (ret) {
+qerror_report(QERR_VA_FAILED, ret, strerror(ret));
+}
+xmlrpc_DECREF(params);
+return ret;
+}
diff --git a/virtagent.h b/virtagent.h
index 127585b..dba90d0 100644
--- a/virtagent.h
+++ b/virtagent.h
@@ -45,5 +45,6 @@ void do_agent_capabilities_print(Monitor *mon, const QObject 
*qobject);
 int do_agent_capabilities(Monitor *mon, const QDict *mon_params,
   MonitorCompletion cb, void *opaque);
 int va_client_init_capabilities(void);
+int va_send_hello(void);
 
 #endif /* VIRTAGENT_H */
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 20/23] virtagent: add va.capabilities RPC

2011-01-17 Thread Michael Roth

Signed-off-by: Michael Roth 
---
 virtagent-server.c |   37 +
 1 files changed, 37 insertions(+), 0 deletions(-)

diff --git a/virtagent-server.c b/virtagent-server.c
index b7e51ed..5961905 100644
--- a/virtagent-server.c
+++ b/virtagent-server.c
@@ -252,6 +252,10 @@ static xmlrpc_value *va_hello(xmlrpc_env *env,
 return result;
 }
 
+static xmlrpc_value *va_capabilities(xmlrpc_env *env,
+ xmlrpc_value *params,
+ void *user_data);
+
 typedef struct RPCFunction {
 xmlrpc_value *(*func)(xmlrpc_env *env, xmlrpc_value *param, void *unused);
 const char *func_name;
@@ -266,6 +270,8 @@ static RPCFunction guest_functions[] = {
   .func_name = "va.shutdown" },
 { .func = va_ping,
   .func_name = "va.ping" },
+{ .func = va_capabilities,
+  .func_name = "va.capabilities" },
 { NULL, NULL }
 };
 static RPCFunction host_functions[] = {
@@ -273,6 +279,8 @@ static RPCFunction host_functions[] = {
   .func_name = "va.ping" },
 { .func = va_hello,
   .func_name = "va.hello" },
+{ .func = va_capabilities,
+  .func_name = "va.capabilities" },
 { NULL, NULL }
 };
 
@@ -287,6 +295,35 @@ static void va_register_functions(xmlrpc_env *env, 
xmlrpc_registry *registry,
 }
 }
 
+/* va_capabilities(): return server capabilities
+ * rpc return values:
+ *   - version: virtagent version
+ *   - methods: list of supported RPCs
+ */
+static xmlrpc_value *va_capabilities(xmlrpc_env *env,
+ xmlrpc_value *params,
+ void *user_data)
+{
+int i;
+xmlrpc_value *result = NULL, *methods;
+RPCFunction *func_list = va_server_data->is_host ?
+ host_functions : guest_functions;
+
+/* provide a list of supported RPCs. we don't want to rely on
+ * system.methodList since introspection methods won't support
+ * client metadata, which we may eventually come to rely upon
+ */
+methods = xmlrpc_array_new(env);
+for (i = 0; func_list[i].func != NULL; ++i) {
+xmlrpc_array_append_item(env, methods,
+ xmlrpc_string_new(env, 
func_list[i].func_name));
+}
+
+result = xmlrpc_build_value(env, "{s:s,s:A}", "version", VA_VERSION,
+"methods", methods);
+return result;
+}
+
 int va_server_init(VAServerData *server_data, bool is_host)
 {
 RPCFunction *func_list = is_host ? host_functions : guest_functions;
-- 
1.7.0.4




[Qemu-devel] [RFC][PATCH v6 21/23] virtagent: add virtagent guest daemon

2011-01-17 Thread Michael Roth

Signed-off-by: Michael Roth 
---
 Makefile   |4 +-
 qemu-va.c  |  238 
 virtagent-common.h |1 +
 3 files changed, 242 insertions(+), 1 deletions(-)
 create mode 100644 qemu-va.c

diff --git a/Makefile b/Makefile
index 6d601ee..f1f4d18 100644
--- a/Makefile
+++ b/Makefile
@@ -151,7 +151,7 @@ version-obj-$(CONFIG_WIN32) += version.o
 ##
 
 qemu-img.o: qemu-img-cmds.h
-qemu-img.o qemu-tool.o qemu-nbd.o qemu-io.o cmd.o: $(GENERATED_HEADERS)
+qemu-img.o qemu-tool.o qemu-nbd.o qemu-io.o cmd.o qemu-va.o: 
$(GENERATED_HEADERS)
 
 qemu-img$(EXESUF): qemu-img.o qemu-tool.o qemu-error.o $(oslib-obj-y) 
$(trace-obj-y) $(block-obj-y) $(qobject-obj-y) $(version-obj-y) 
qemu-timer-common.o
 
@@ -159,6 +159,8 @@ qemu-nbd$(EXESUF): qemu-nbd.o qemu-tool.o qemu-error.o 
$(oslib-obj-y) $(trace-ob
 
 qemu-io$(EXESUF): qemu-io.o cmd.o qemu-tool.o qemu-error.o $(oslib-obj-y) 
$(trace-obj-y) $(block-obj-y) $(qobject-obj-y) $(version-obj-y) 
qemu-timer-common.o
 
+qemu-va$(EXESUF): qemu-va.o virtagent.o virtagent-server.o virtagent-common.o 
qemu-tool.o qemu-error.o qemu-sockets.c $(oslib-obj-y) $(trace-obj-y) 
$(block-obj-y) $(qobject-obj-y) $(version-obj-y) qemu-timer-common.o 
qemu-timer.o
+
 qemu-img-cmds.h: $(SRC_PATH)/qemu-img-cmds.hx
$(call quiet-command,sh $(SRC_PATH)/hxtool -h < $< > $@,"  GEN   $@")
 
diff --git a/qemu-va.c b/qemu-va.c
new file mode 100644
index 000..5f1e2ab
--- /dev/null
+++ b/qemu-va.c
@@ -0,0 +1,238 @@
+/*
+ * virtagent - QEMU guest agent
+ *
+ * Copyright IBM Corp. 2010
+ *
+ * Authors:
+ *  Michael Roth  
+ *
+ * This work is licensed under the terms of the GNU GPL, version 2 or later.
+ * See the COPYING file in the top-level directory.
+ *
+ * QEMU System Emulator
+ *
+ * Copyright (c) 2003-2008 Fabrice Bellard
+ *
+ * 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 
+#include 
+#include "qemu-ioh.h"
+#include "qemu-tool.h"
+#include "virtagent-common.h"
+
+static bool verbose_enabled;
+#define DEBUG_ENABLED
+
+#ifdef DEBUG_ENABLED
+#define DEBUG(msg, ...) do { \
+fprintf(stderr, "%s:%s():L%d: " msg "\n", \
+__FILE__, __FUNCTION__, __LINE__, ## __VA_ARGS__); \
+} while(0)
+#else
+#define DEBUG(msg, ...) do {} while (0)
+#endif
+
+#define INFO(msg, ...) do { \
+if (!verbose_enabled) { \
+break; \
+} \
+warnx(msg, ## __VA_ARGS__); \
+} while(0)
+
+/* mirror qemu I/O loop for standalone daemon */
+static void main_loop_wait(int nonblocking)
+{
+fd_set rfds, wfds, xfds;
+int ret, nfds;
+struct timeval tv;
+int timeout = 10;
+
+if (nonblocking) {
+timeout = 0;
+}
+
+/* poll any events */
+nfds = -1;
+FD_ZERO(&rfds);
+FD_ZERO(&wfds);
+FD_ZERO(&xfds);
+qemu_get_fdset(&nfds, &rfds, &wfds, &xfds);
+
+tv.tv_sec = timeout / 1000;
+tv.tv_usec = (timeout % 1000) * 1000;
+
+ret = select(nfds + 1, &rfds, &wfds, &xfds, &tv);
+
+if (ret > 0) {
+qemu_process_fd_handlers(&rfds, &wfds, &xfds);
+}
+
+DEBUG("running timers...");
+qemu_run_all_timers();
+}
+
+static void usage(const char *cmd)
+{
+printf(
+"Usage: %s -c \n"
+"QEMU virtagent guest agent %s\n"
+"\n"
+"  -c, --channel channel method: one of unix-connect, virtio-serial, or\n"
+"isa-serial\n"
+"  -p, --pathchannel path\n"
+"  -v, --verbose display extra debugging information\n"
+"  -d, --daemonize   become a daemon\n"
+"  -h, --helpdisplay this help and exit\n"
+"\n"
+"Report bugs to \n"
+, cmd, VA_VERSION);
+}
+
+static int init_virtagent(const char *method, const char *path) {
+VAContext ctx;
+int ret;
+
+INFO("initializing agent...");
+
+if (method == NULL) {
+/* try virtio-serial as our default */
+method = "virtio-serial";
+}
+
+if (path ==

[Qemu-devel] [RFC][PATCH v6 22/23] virtagent: integrate virtagent server/client via chardev

2011-01-17 Thread Michael Roth
This adds a new chardev, virtagent, which actually just passes back a
socket chardev after connecting to it and initializing the agent.

Signed-off-by: Michael Roth 
---
 qemu-char.c |   44 
 1 files changed, 44 insertions(+), 0 deletions(-)

diff --git a/qemu-char.c b/qemu-char.c
index edc9ad6..eae49c1 100644
--- a/qemu-char.c
+++ b/qemu-char.c
@@ -2463,6 +2463,49 @@ fail:
 return NULL;
 }
 
+#include "virtagent-common.h"
+
+static CharDriverState *qemu_chr_open_virtagent(QemuOpts *opts)
+{
+CharDriverState *chr;
+const char *path;
+VAContext ctx;
+int ret;
+
+/* revert to/enforce default socket chardev options for virtagent */
+path = qemu_opt_get(opts, "path");
+if (path == NULL) {
+path = VA_HOST_PATH_DEFAULT;
+}
+qemu_opt_set(opts, "path", path);
+qemu_opt_set(opts, "server", "on");
+qemu_opt_set(opts, "wait", "off");
+qemu_opt_set(opts, "telnet", "off");
+
+chr = qemu_chr_open_socket(opts);
+if (chr == NULL) {
+goto err;
+}
+
+/* initialize virtagent using the socket we just set up */
+ctx.channel_method = "unix-connect";
+ctx.channel_path = path;
+ctx.is_host = true;
+ret = va_init(ctx);
+ret = 0;
+if (ret != 0) {
+fprintf(stderr, "error initializing virtagent");
+goto err;
+}
+
+return chr;
+err:
+if (chr) {
+qemu_free(chr);
+}
+return NULL;
+}
+
 static const struct {
 const char *name;
 CharDriverState *(*open)(QemuOpts *opts);
@@ -2472,6 +2515,7 @@ static const struct {
 { .name = "udp",   .open = qemu_chr_open_udp },
 { .name = "msmouse",   .open = qemu_chr_open_msmouse },
 { .name = "vc",.open = text_console_init },
+{ .name = "virtagent", .open = qemu_chr_open_virtagent },
 #ifdef _WIN32
 { .name = "file",  .open = qemu_chr_open_win_file_out },
 { .name = "pipe",  .open = qemu_chr_open_win_pipe },
-- 
1.7.0.4




Re: [Qemu-devel] [RFC][PATCH v6 00/23] virtagent: host/guest RPC communication agent

2011-01-17 Thread Gerd Hoffmann

  Hi,


OVERVIEW:

There are a wide range of use cases motivating the need for a guest
agent of some sort to extend the functionality/usability/control
offered by QEMU. Some examples include graceful guest shutdown/reboot
and notifications thereof, copy/paste syncing between host/guest,
guest statistics gathering, file access, etc.


What is your plan to handle system-level queries+actions (such as 
reboot) vs. per-user stuff (such as cut+paste)?


cheers,
  Gerd




Re: [Qemu-devel] [RFC][PATCH v6 01/23] Move code related to fd handlers into utility functions

2011-01-17 Thread Gerd Hoffmann

  Hi,


+/* XXX: fd_read_poll should be suppressed, but an API change is
+   necessary in the character devices to suppress fd_can_read(). */


FYI: Amit (Cc'ed) looks at this api issue too for other reasons.

cheers,
  Gerd




[Qemu-devel] [RFC][PATCH v6 23/23] virtagent: various bits to build QEMU with virtagent

2011-01-17 Thread Michael Roth

Signed-off-by: Michael Roth 
---
 Makefile.target |2 +-
 configure   |   32 
 2 files changed, 33 insertions(+), 1 deletions(-)

diff --git a/Makefile.target b/Makefile.target
index e15b1c4..8564a8f 100644
--- a/Makefile.target
+++ b/Makefile.target
@@ -186,7 +186,7 @@ endif #CONFIG_BSD_USER
 # System emulator target
 ifdef CONFIG_SOFTMMU
 
-obj-y = arch_init.o cpus.o monitor.o machine.o gdbstub.o balloon.o
+obj-y = arch_init.o cpus.o monitor.o machine.o gdbstub.o balloon.o virtagent.o 
virtagent-server.o virtagent-common.o
 # virtio has to be here due to weird dependency between PCI and virtio-net.
 # need to fix this properly
 obj-$(CONFIG_NO_PCI) += pci-stub.o
diff --git a/configure b/configure
index 438219b..4814351 100755
--- a/configure
+++ b/configure
@@ -1271,6 +1271,37 @@ EOF
 fi
 
 ##
+# xmlrpc-c probe
+
+discard_cmake_vars() {
+echo "$@" | sed 's/@.*@//g'
+}
+
+# Look for the xmlrpc-c config program
+if test -n "$cross_prefix" && has ${cross_prefix}xmlrpc-c-config; then
+  xmlrpccconfig=${cross_prefix}xmlrpc-c-config
+elif has xmlrpc-c-config; then
+  xmlrpccconfig=xmlrpc-c-config
+else
+  feature_not_found "xmlrpc-c"
+fi
+
+cat > $TMPC << EOF
+#include 
+int main(void) { xmlrpc_env env; xmlrpc_env_init(&env); return 0; }
+EOF
+xmlrpc_cflags=`$xmlrpccconfig --cflags 2> /dev/null`
+xmlrpc_cflags=`discard_cmake_vars $xmlrpc_cflags`
+xmlrpc_libs=`$xmlrpccconfig client server-util --libs 2> /dev/null`
+xmlrpc_libs=`discard_cmake_vars $xmlrpc_libs`
+if compile_prog "$xmlrpc_cflags" "$xmlrpc_libs"; then
+  libs_softmmu="$xmlrpc_libs $libs_softmmu"
+  libs_tools="$xmlrpc_libs $libs_tools"
+else
+  feature_not_found "xmlrpc-c"
+fi
+
+##
 # VNC TLS detection
 if test "$vnc_tls" != "no" ; then
   cat > $TMPC <

[Qemu-devel] Re: [patch 1/2] document QEMU<->ACPIBIOS PCI hotplug interface

2011-01-17 Thread Michael S. Tsirkin
On Tue, Jan 11, 2011 at 02:20:38PM -0200, Marcelo Tosatti wrote:
> Document how QEMU communicates with ACPI BIOS for PCI hotplug.
> 
> Signed-off-by: Marcelo Tosatti 

This one seems to add whitespae errors:
/scm/qemu/.git/rebase-apply/patch:5: new blank line at EOF.
+
warning: 1 line adds whitespace errors.

> Index: qemu/docs/specs/acpi_pci_hotplug.txt
> ===
> --- /dev/null
> +++ qemu/docs/specs/acpi_pci_hotplug.txt
> @@ -0,0 +1,39 @@
> +QEMU<->ACPI BIOS PCI hotplug interface
> +--
> +
> +QEMU supports PCI hotplug via ACPI, for PCI bus 0. This document
> +describes the interface between QEMU and the ACPI BIOS.
> +
> +ACPI GPE block (IO ports 0xafe0-0xafe3, byte access):
> +-
> +
> +Generic ACPI GPE block. Bit 1 (GPE.1) used to notify PCI hotplug/eject
> +event to ACPI BIOS, via SCI interrupt.
> +
> +PCI slot injection notification pending (IO port 0xae00-0xae03, 4-byte 
> access):
> +---
> +Slot injection notification pending. One bit per slot.
> +
> +Read by ACPI BIOS GPE.1 handler to notify OS of injection
> +events.
> +
> +PCI slot removal notification (IO port 0xae04-0xae07, 4-byte access):
> +-
> +Slot removal notification pending. One bit per slot.
> +
> +Read by ACPI BIOS GPE.1 handler to notify OS of removal
> +events.
> +
> +PCI device eject (IO port 0xae08-0xae0b, 4-byte access):
> +
> +
> +Used by ACPI BIOS _EJ0 method to request device removal. One bit per slot.
> +Reads return 0.
> +
> +PCI removability status (IO port 0xae0c-0xae0f, 4-byte access):
> +---
> +
> +Used by ACPI BIOS _RMV method to indicate removability status to OS. One
> +bit per slot.
> +
> +
> 



[Qemu-devel] Re: [PATCH 8/8] ahci: fix !msi interrupts

2011-01-17 Thread Jan Kiszka
On 2010-12-20 22:13, Alexander Graf wrote:
> When not using MSI, receiving an interrupt while the interrupt line is active
> pulses the interrupt line. Without this, guests don't realize that a new
> interrupt occured.

This doesn't look OK. The device model should look at the currently used
mode and switch between edge and level triggering accordingly. As it
appears like this is what it already does, this change may just paper
over the real issue.

Jan

> 
> Signed-off-by: Alexander Graf 
> ---
>  hw/ide/ahci.c |3 +--
>  1 files changed, 1 insertions(+), 2 deletions(-)
> 
> diff --git a/hw/ide/ahci.c b/hw/ide/ahci.c
> index 97aef68..4c920da 100644
> --- a/hw/ide/ahci.c
> +++ b/hw/ide/ahci.c
> @@ -153,11 +153,10 @@ static void ahci_check_irq(AHCIState *s)
>  }
>  }
>  
> +ahci_irq_lower(s, NULL);
>  if (s->control_regs.irqstatus &&
>  (s->control_regs.ghc & HOST_CTL_IRQ_EN)) {
>  ahci_irq_raise(s, NULL);
> -} else {
> -ahci_irq_lower(s, NULL);
>  }
>  }
>  

-- 
Siemens AG, Corporate Technology, CT T DE IT 1
Corporate Competence Center Embedded Linux



[Qemu-devel] [PATCH] Documentation: Add qemu-img check/rebase

2011-01-17 Thread Kevin Wolf
Signed-off-by: Kevin Wolf 
---
 qemu-img.texi |   41 +
 1 files changed, 41 insertions(+), 0 deletions(-)

diff --git a/qemu-img.texi b/qemu-img.texi
index 1b90ddb..ced64a4 100644
--- a/qemu-img.texi
+++ b/qemu-img.texi
@@ -59,6 +59,13 @@ lists all snapshots in the given image
 Command description:
 
 @table @option
+@item check [-f @var{fmt}] @var{filename}
+
+Perform a consistency check on the disk image @var{filename}.
+
+Only the formats @code{qcow2}, @code{qed} and @code{vdi} support
+consistency checks.
+
 @item create [-f @var{fmt}] [-o @var{options}] @var{filename} [@var{size}]
 
 Create the new disk image @var{filename} of size @var{size} and format
@@ -107,6 +114,40 @@ they are displayed too.
 
 List, apply, create or delete snapshots in image @var{filename}.
 
+@item rebase [-f @var{fmt}] [-u] -b @var{backing_file} [-F @var{backing_fmt}] 
@var{filename}
+
+Changes the backing file of an image. Only the formats @code{qcow2} and
+@code{qed} support changing the backing file.
+
+The backing file is changed to @var{backing_file} and (if the image format of
+@var{filename} supports this) the backing file format is changed to
+@var{backing_fmt}.
+
+There are two different modes in which @code{rebase} can operate:
+@table @option
+@item Safe mode
+This is the default mode and performs a real rebase operation. The new backing
+file may differ from the old one and qemu-img rebase will take care of keeping
+the guest-visible content of @var{filename} unchanged.
+
+In order to achieve this, any clusters that differ between @var{backing_file}
+and the old backing file of @var{filename} are merged into @var{filename}
+before actually changing the backing file.
+
+Note that the safe mode is an expensive operation, comparable to converting
+an image. It only works if the old backing file still exists.
+
+@item Unsafe mode
+qemu-img uses the unsafe mode if @code{-u} is specified. In this mode, only the
+backing file name and format of @var{filename} is changed without any checks
+on the file contents. The user must take care of specifying the correct new
+backing file, or the guest-visible content of the image will be corrupted.
+
+This mode is useful for renaming or moving the backing file to somewhere else.
+It can be used without an accessible old backing file, i.e. you can use it to
+fix an image whose backing file has already been moved/renamed.
+@end table
+
 @item resize @var{filename} [+ | -]@var{size}
 
 Change the disk image as if it had been created with @var{size}.
-- 
1.7.2.3




Re: [Qemu-devel] [RFC][PATCH v6 00/23] virtagent: host/guest RPC communication agent

2011-01-17 Thread Michael Roth

On 01/17/2011 07:53 AM, Gerd Hoffmann wrote:

Hi,


OVERVIEW:

There are a wide range of use cases motivating the need for a guest
agent of some sort to extend the functionality/usability/control
offered by QEMU. Some examples include graceful guest shutdown/reboot
and notifications thereof, copy/paste syncing between host/guest,
guest statistics gathering, file access, etc.


What is your plan to handle system-level queries+actions (such as
reboot) vs. per-user stuff (such as cut+paste)?


This is an area that hasn't been well-defined yet and is definitely open 
for suggestions.


For host->guest RPCs the current plan is to always have the RPC executed 
at the system level, but for situations involving a specific user we 
fork and drop privileges with the RPC, and report back the status of the 
fork/exec. The fork'd process would then do what it needs to do, then if 
needed, communicate status back to the system-level daemon via some IPC 
mechanism (most likely a socket we listen to in addition to the serial 
channel) that can be used to send an event. The system-level daemon then 
communicates these events back to the host with a guest->host RPC.


Processes created independently of the system-level daemon could report 
events in the same manner, via this socket. I think this might suit the 
vdagent client model for Spice as well, things like resolutions changes 
and clipboard contents could be communicated as asynchronous events to 
virtagent via this socket, in place of a separate daemon, and virtagent 
could have RPCs that can route/translate host->guest calls to the 
user-level daemons.


Depending on the event, event-handling would either get consumed within 
virtagent, or punted to qemu's QMP event layer, which may need to be 
extended depending on the types of events we want to handle. The events 
would terminate within QEMU, but handlers could hook into external services.


So that's the rough plan, but would be happy to hear any other thoughts 
on how we might approach this.




cheers,
Gerd







[Qemu-devel] [PATCH 1/2] strtosz() use unsigned char as isspace() is not defined for signed char

2011-01-17 Thread Jes . Sorensen
From: Jes Sorensen 

Bug pointed out by Erik Blake, thanks!

Signed-off-by: Jes Sorensen 
---
 cutils.c |3 ++-
 1 files changed, 2 insertions(+), 1 deletions(-)

diff --git a/cutils.c b/cutils.c
index 7984bc1..f97ef39 100644
--- a/cutils.c
+++ b/cutils.c
@@ -294,7 +294,8 @@ int fcntl_setfl(int fd, int flag)
 ssize_t strtosz_suffix(const char *nptr, char **end, const char default_suffix)
 {
 ssize_t retval = -1;
-char *endptr, c, d;
+char *endptr;
+unsigned char c, d;
 int mul_required = 0;
 double val, mul, integral, fraction;
 
-- 
1.7.3.4




[Qemu-devel] [PATCH 2/2] strtosz() use toupper() to simply switch statement

2011-01-17 Thread Jes . Sorensen
From: Jes Sorensen 

Signed-off-by: Jes Sorensen 
---
 cutils.c |7 +--
 1 files changed, 1 insertions(+), 6 deletions(-)

diff --git a/cutils.c b/cutils.c
index f97ef39..f7aa90c 100644
--- a/cutils.c
+++ b/cutils.c
@@ -323,16 +323,14 @@ ssize_t strtosz_suffix(const char *nptr, char **end, 
const char default_suffix)
 d = c;
 }
 }
-switch (d) {
+switch (toupper(d)) {
 case 'B':
-case 'b':
 mul = 1;
 if (mul_required) {
 goto fail;
 }
 break;
 case 'K':
-case 'k':
 mul = 1 << 10;
 break;
 case 0:
@@ -340,15 +338,12 @@ ssize_t strtosz_suffix(const char *nptr, char **end, 
const char default_suffix)
 goto fail;
 }
 case 'M':
-case 'm':
 mul = 1ULL << 20;
 break;
 case 'G':
-case 'g':
 mul = 1ULL << 30;
 break;
 case 'T':
-case 't':
 mul = 1ULL << 40;
 break;
 default:
-- 
1.7.3.4




[Qemu-devel] Re: [PATCH v2 0/5] iohandlers: Add support for enabling/disabling individual handlers

2011-01-17 Thread Anthony Liguori

On 01/17/2011 04:18 AM, Amit Shah wrote:

On (Thu) Jan 13 2011 [13:17:22], Anthony Liguori wrote:
   

On 01/13/2011 09:00 AM, Amit Shah wrote:
 

Hi,

This patchset adds new interfaces to work with iohandlers.  It adds:

int assign_fd_handlers(int fd, IOHandlerOps *ops, void *opaque)
-- Specify io handlers for an fd
int remove_fd_handlers(int fd)
-- Remove fd handlers for fd (mark ioh for deletion)
int set_read_poll_fd_action(int fd, bool enable)
-- Enable or disable the fd_read_poll fd handler
int set_read_fd_action(int fd, bool enable)
-- Enable or disable the fd_read fd handler
int set_write_fd_action(int fd, bool enable)
-- Enable or disable the fd_read fd handler

A new struct, IOHandlerOps, is added, to collect all the ops together
instead of passing individual ones to functions.
   

Instead of inventing new interfaces, I think we should steal^Wlearn
from established interfaces.
 

Agreed.

I do also think it'll be worthwhile pulling in one of the libraries to
reduce the amount of qemu-specific code we have in the other cases as
well.

   

  Both libevent and glib have interfaces
that essentially boil down to:

handle add_fd_event(loop, fd, ConditionMask, callback, opaque)
remove_event(loop, handle)
 

This is quite similar to the Linux polling API.

I don't know what the 'loop' parameter would do, though.
   


It's to allow for multiple I/O threads.  There's one loop context per 
thread and you can register events specifically to a thread.



I think that's what we should move to.  All the stuff in our current
loop around allowing suppressing of read events is terrible as it
forces the main loop to poll.  That makes it impossible to use other
main loops because it's completely unusual.
 

While setting new APIs possibly requires more discussion if we want to
do it once and right, since it's also an internal API, we can keep
evolving them.
   


Yeah, but we should avoid unnecessary churn.  If we're going to do a 
major refactoring of an internal API, we should try to make the 
refactoring make sense as much as possible.


Eliminating the polling callbacks has been on the TODO for years now.  I 
don't think it make sense to refactor the API without at least doing this.



So what's the accepted course of action now - take this new API, rework
it to look like that of some other library's and then rework the
main_loop, keep developing something in parallel till it satisfies
everyone, etc.?

Also -- this patchset was prompted by a bug in qemu chardevs that
freezes guests if they write faster than the chardevs can consume.
What should the strategy on fixing that bug be?
   


Fix the loop API such that we're not just fixing one bug but that we can 
address a bunch of other bugs that are out there.


Regards,

Anthony Liguori


Amit
   





Re: [Qemu-devel] paravirtual tablet v3

2011-01-17 Thread Anthony Liguori

On 01/17/2011 02:19 AM, Gerd Hoffmann wrote:

On 01/14/11 21:48, Anthony Liguori wrote:

On 01/14/2011 10:35 AM, Gerd Hoffmann wrote:

Hi,

Now v3 featuring multitouch ;)

cheers,
Gerd


I really think multitouch needs to be a feature such that the guest can
nack it and the host can adjust accordingly. If it's there from day 1,
that's fine, but it still should be a feature.

There are a lot of non-multitouch aware guests out there and I don't
think we want the driver to be the one deciding how to map a multitouch
device to something that doesn't support mulitouch.


Sure, someone needs to map multitouch to non-multitouch.  I'd leave 
that job to the guest driver tough.  Why do you think doing it in the 
host is better?


My assumptions are 1) the host is capable of doing the mapping just as 
easily as the guest 2) the host can do something useful with the 
information that the guest is not multitouch capable.


Regards,

Anthony Liguori



cheers,
  Gerd






Re: [Qemu-devel] RFC: mass comment conversion from C99 to C89

2011-01-17 Thread Anthony Liguori

On 01/16/2011 06:12 PM, Peter Maydell wrote:

On 15 January 2011 16:02, Blue Swirl  wrote:
   

With the sed script below (my first I think), I'm able to convert most
files in QEMU from C99 comment style to C89. When successive line with
C99 comments are converted, the comments are merged. Two files
(hw/rtl8139.c and microblaze-dis.c) still fail.

Is this a good idea?
 

I'm a bit wary of this kind of wide-scale no-semantic-change commit
(and more so for things like indent, brace and whitespace fixes
which can affect large chunks of actual code), because it makes
it harder to deal with qemu forks (especially if you were hoping to
be able to periodically rebase with an eye to eventually getting
changes back into mainline qemu).
   


Yeah, I'm equally wary of such changes unless they have a very clear 
value (e.g. changing an API definition to accommodate an extra parameter).


Regards,

Anthony Liguori


This particular changeset doesn't touch target-arm so
it doesn't affect me personally, though.

-- PMM

   





[Qemu-devel] Re: [Xen-devel] [PATCH V2 3/3] xen: Introduce VGA sync dirty bitmap support

2011-01-17 Thread Stefano Stabellini
On Fri, 14 Jan 2011, anthony.per...@citrix.com wrote:
> From: Anthony PERARD 
> 
> This patch introduces phys memory client for Xen.
> 
> Only sync dirty_bitmap and set_memory are actually implemented.
> migration_log will stay empty for the moment.
> 
> Xen can only log one range for bit change, so only the range in the
> first call will be synced.
> 

I think the patch is OK now.




[Qemu-devel] [PATCH v2 0/2] strtosz() cleanup

2011-01-17 Thread Jes . Sorensen
From: Jes Sorensen 

Fix issue with signed char and isspace() as well as clean up switch
statement using toupper().

V2 of the patch fixes some types in the commit messages and spells
Eric correctly. My apologies for getting it wrong.

Jes Sorensen (2):
  strtosz() use unsigned char as isspace() is not defined for signed
char
  strtosz() use toupper() to simplify switch statement

 cutils.c |   10 +++---
 1 files changed, 3 insertions(+), 7 deletions(-)

-- 
1.7.3.4




[Qemu-devel] [PATCH 2/2] strtosz() use toupper() to simplify switch statement

2011-01-17 Thread Jes . Sorensen
From: Jes Sorensen 

Signed-off-by: Jes Sorensen 
---
 cutils.c |7 +--
 1 files changed, 1 insertions(+), 6 deletions(-)

diff --git a/cutils.c b/cutils.c
index f97ef39..f7aa90c 100644
--- a/cutils.c
+++ b/cutils.c
@@ -323,16 +323,14 @@ ssize_t strtosz_suffix(const char *nptr, char **end, 
const char default_suffix)
 d = c;
 }
 }
-switch (d) {
+switch (toupper(d)) {
 case 'B':
-case 'b':
 mul = 1;
 if (mul_required) {
 goto fail;
 }
 break;
 case 'K':
-case 'k':
 mul = 1 << 10;
 break;
 case 0:
@@ -340,15 +338,12 @@ ssize_t strtosz_suffix(const char *nptr, char **end, 
const char default_suffix)
 goto fail;
 }
 case 'M':
-case 'm':
 mul = 1ULL << 20;
 break;
 case 'G':
-case 'g':
 mul = 1ULL << 30;
 break;
 case 'T':
-case 't':
 mul = 1ULL << 40;
 break;
 default:
-- 
1.7.3.4




[Qemu-devel] [PATCH 1/2] strtosz() use unsigned char as isspace() is not defined for signed char

2011-01-17 Thread Jes . Sorensen
From: Jes Sorensen 

Bug pointed out by Eric Blake, thanks!

Signed-off-by: Jes Sorensen 
---
 cutils.c |3 ++-
 1 files changed, 2 insertions(+), 1 deletions(-)

diff --git a/cutils.c b/cutils.c
index 7984bc1..f97ef39 100644
--- a/cutils.c
+++ b/cutils.c
@@ -294,7 +294,8 @@ int fcntl_setfl(int fd, int flag)
 ssize_t strtosz_suffix(const char *nptr, char **end, const char default_suffix)
 {
 ssize_t retval = -1;
-char *endptr, c, d;
+char *endptr;
+unsigned char c, d;
 int mul_required = 0;
 double val, mul, integral, fraction;
 
-- 
1.7.3.4




[Qemu-devel] Re: [PATCH v2 0/2] strtosz() cleanup

2011-01-17 Thread Alex Williamson
On Mon, 2011-01-17 at 16:14 +0100, jes.soren...@redhat.com wrote:
> From: Jes Sorensen 
> 
> Fix issue with signed char and isspace() as well as clean up switch
> statement using toupper().
> 
> V2 of the patch fixes some types in the commit messages and spells
> Eric correctly. My apologies for getting it wrong.
> 
> Jes Sorensen (2):
>   strtosz() use unsigned char as isspace() is not defined for signed
> char
>   strtosz() use toupper() to simplify switch statement
> 
>  cutils.c |   10 +++---
>  1 files changed, 3 insertions(+), 7 deletions(-)
> 

And the modf() usage?  Or using STRTOSZ_DEFSUFFIX_* in the switch?  Or
avoiding the extra variable in 13/18?  Thanks,

Alex




Re: [Qemu-devel] [PATCH] Documentation: Add qemu-img check/rebase

2011-01-17 Thread Stefan Hajnoczi
On Mon, Jan 17, 2011 at 2:39 PM, Kevin Wolf  wrote:
> Signed-off-by: Kevin Wolf 
> ---
>  qemu-img.texi |   41 +
>  1 files changed, 41 insertions(+), 0 deletions(-)

Reviewed-by: Stefan Hajnoczi 



[Qemu-devel] Re: [PATCH 08/12] Threadlet: Add aio_signal_handler threadlet API

2011-01-17 Thread Paolo Bonzini

On 01/17/2011 10:56 AM, Stefan Hajnoczi wrote:

This would be the right place to create qemu-threadlet.c,


You mean .h?

Paolo



[Qemu-devel] Re: [PATCH V2 1/3] Introduce log_start/log_stop in CPUPhysMemoryClient

2011-01-17 Thread Jan Kiszka
On 2011-01-14 19:10, anthony.per...@citrix.com wrote:
> From: Anthony PERARD 
> 
> In order to use log_start/log_stop with Xen as well in the vga code,
> this two operations have been put in CPUPhysMemoryClient.
> 
> The two new functions cpu_physical_log_start,cpu_physical_log_stop are
> used in hw/vga.c and replace the kvm_log_start/stop. With this, vga does
> no longer depends on kvm header.

Basically, this looks good to me. Two remarks below.

> 
> Signed-off-by: Anthony PERARD 
> ---
>  cpu-all.h|6 ++
>  cpu-common.h |4 
>  exec.c   |   42 ++
>  hw/vga.c |   31 ---
>  hw/vhost.c   |   16 
>  kvm-all.c|8 ++--
>  kvm-stub.c   |   10 --
>  kvm.h|3 ---
>  8 files changed, 90 insertions(+), 30 deletions(-)
> 
> diff --git a/cpu-all.h b/cpu-all.h
> index 30ae17d..aaf5442 100644
> --- a/cpu-all.h
> +++ b/cpu-all.h
> @@ -957,6 +957,12 @@ int cpu_physical_memory_get_dirty_tracking(void);
>  int cpu_physical_sync_dirty_bitmap(target_phys_addr_t start_addr,
> target_phys_addr_t end_addr);
>  
> +int cpu_physical_log_start(target_phys_addr_t start_addr,
> +   ram_addr_t size);
> +
> +int cpu_physical_log_stop(target_phys_addr_t start_addr,
> +   ram_addr_t size);
> +
>  void dump_exec_info(FILE *f, fprintf_function cpu_fprintf);
>  #endif /* !CONFIG_USER_ONLY */
>  
> diff --git a/cpu-common.h b/cpu-common.h
> index 8ec01f4..2344842 100644
> --- a/cpu-common.h
> +++ b/cpu-common.h
> @@ -88,6 +88,10 @@ struct CPUPhysMemoryClient {
>   target_phys_addr_t end_addr);
>  int (*migration_log)(struct CPUPhysMemoryClient *client,
>   int enable);
> +int (*log_start)(struct CPUPhysMemoryClient *client,
> + target_phys_addr_t phys_addr, ram_addr_t size);
> +int (*log_stop)(struct CPUPhysMemoryClient *client,
> +target_phys_addr_t phys_addr, ram_addr_t size);
>  QLIST_ENTRY(CPUPhysMemoryClient) list;
>  };
>  
> diff --git a/exec.c b/exec.c
> index c6ed96d..609ec88 100644
> --- a/exec.c
> +++ b/exec.c
> @@ -1734,6 +1734,30 @@ static int cpu_notify_migration_log(int enable)
>  return 0;
>  }
>  
> +static int cpu_notify_log_start(target_phys_addr_t start,
> +ram_addr_t size)
> +{
> +CPUPhysMemoryClient *client;
> +QLIST_FOREACH(client, &memory_client_list, list) {
> +int r = client->log_start(client, start, size);
> +if (r < 0)
> +return r;
> +}
> +return 0;
> +}
> +
> +static int cpu_notify_log_stop(target_phys_addr_t start,
> +   ram_addr_t size)
> +{
> +CPUPhysMemoryClient *client;
> +QLIST_FOREACH(client, &memory_client_list, list) {
> +int r = client->log_stop(client, start, size);
> +if (r < 0)
> +return r;
> +}
> +return 0;
> +}
> +

I would make the new callbacks optional, i.e. only invoke them if the
handler is non-NULL. Avoids stubs and branching to vhost.

>  static void phys_page_for_each_1(CPUPhysMemoryClient *client,
>   int level, void **lp)
>  {
> @@ -2073,6 +2097,24 @@ int cpu_physical_sync_dirty_bitmap(target_phys_addr_t 
> start_addr,
>  return ret;
>  }
>  
> +int cpu_physical_log_start(target_phys_addr_t start_addr,
> +   ram_addr_t size)
> +{
> +int ret;
> +
> +ret = cpu_notify_log_start(start_addr, size);
> +return ret;
> +}
> +
> +int cpu_physical_log_stop(target_phys_addr_t start_addr,
> +  ram_addr_t size)
> +{
> +int ret;
> +
> +ret = cpu_notify_log_stop(start_addr, size);
> +return ret;
> +}
> +

I consider this split-up between API frontend and cpu_notify_* backend
as unneeded. But that's not your fault, you just follow the pre-existing
pattern. Unless someone feels strong about this, you may just keep it.

Jan

-- 
Siemens AG, Corporate Technology, CT T DE IT 1
Corporate Competence Center Embedded Linux



Re: [Qemu-devel] [PATCH 0/7] usb-ccid (v15)

2011-01-17 Thread Alon Levy
Ping

On Tue, Jan 11, 2011 at 10:42:31AM +0200, Alon Levy wrote:
> This patchset adds three new devices, usb-ccid, ccid-card-passthru and
> ccid-card-emulated, providing a CCID bus, a simple passthru protocol
> implementing card requiring a client, and a standalone emulated card.
> 
> It also introduces a new directory libcaccard with CAC card emulation,
> CAC is a type of ISO 7816 smart card.
> 
> Tree for pull: git://anongit.freedesktop.org/~alon/qemu usb_ccid.v15
> 
> v14-v15 changes:
>  * add patch with --enable-smartcard and --disable-smartcard and only
>   disable ccid-card-emulated if nss not found.
>  * add patch with description strings
>  * s/libcaccard/libcacard/ in docs/ccid.txt
> 
> v13-v14 changes:
>  - support device_del/device_add on ccid-card-* and usb-ccid
>  * usb-ccid:
>   * lose card reference when card device deleted
>   * check slot number and deny adding a slot if one is already added.
>  * ccid-card-*: use qdev_simple_unplug_cb in both emulated and passthru ccid 
> cards,
>the exitfn already takes care of triggering card removal in the usb dev.
>  * libcacard:
>   * remove double include of config-host.mak
>   * add replay of card events to libcacard to support second and more 
> emulation
>   * don't initialize more then once (doesn't support it right now, so one
>thread, NSS thread, is left when device_del is done)
>   * add VCARD_EMUL_INIT_ALREADY_INITED
>  * ccid-card-emulated:
>   * take correct mutexes on signaling to fix deadlocks on device_del
>   * allow card insertion/removal event without proper reader insertion event
> 
> v12-v13 changes:
>  * libcacard:
>   * fix Makefile clean to remove vscclient
>   * fix double include of config-host in Makefile
>  * usb-ccid: remove attach/detach logic, usb is always attached. Guest
>   doesn't care if there is a reader attached with no card anyway.
>  * ccid-card-passthru: don't close chr_dev on removal, makes it possible
>   to use device_del/device_add to create remove/insertion for debugging.
> 
> v11-v12 changes:
>  * fix out of tree build
> 
> v10-v11 changes:
>  * fix last patch that removed one of the doc files.
>  * updated flow table in docs/ccid.txt
> 
> v8-v10 changes:
>  * usb-ccid:
>   * add slot for future use (Gerd)
>   * ifdef ENABLE_MIGRATION for migration support on account of usb
>migration not being ready in general. (Gerd)
>  * verbosified commit messages. (Gerd)
>  * put libcacard docs in libcacard commit. (Gerd)
> 
> v8-v9 changes:
>  * Blue Swirl comments:
>   * white space fixes
>   * enabled by default, disabled only if missing nss
>   * forgotten fix from v8 (don't build libcacard.so)
>  * added a note about device being little endian
>  * library renamed from libcaccard to libcacard
>  * squashed both of libcacard patches, they touched different files anyway.
> 
> v7-v8 changes:
>  * Blue Swirl comments:
>   * usb-ccid: deannonymize some structs
>   * usb-ccid: coding style change - answer_t and bulk_in_t fixed
>   * usb-ccid: handle endianess conversion between guest and host
>  * usb-ccid: s/ccid_bulk_in_copy_out/ccid_bulk_in_copy_to_guest/
>  * ccid-card-emulated: fix segfault if backend not specified
>  * ccid-card-emulated: let last reader inserted win
>  * libcaccard: remove double vscard_common.h
> 
> v6->v7 changes:
>  * external libcaccard became internal directory libcaccard
>   * statically link object files into qemu
>   * produce libcaccard.so for usage by external projects
>   * applied coding style to new code (please check me)
>   - did not use the qemu options parsing for libcaccard, since
>it seems to draw large amounts of qemu code (monitor for instance).
> 
> v5->v6 changes:
>  * really remove static debug (I apologize for claiming to have done so 
> before)
> 
> v4->v5 changes:
>  * rebased to latest
>  * remove static debug in card devices
>  * fix --enable-smartcard to link
>  * stall instead of assert when exceeding BULK_OUT_DATA_SIZE
>  * make ccid_reserve_recv_buf for too large len discard message, not exit
>  * make ccid_reserve_recv_buf return void*
>  * fix typo
>  * remove commented code in VMState
> 
> v3->v4:
>  * remove ccid field in CCIDBus
>  * remove static debug in bus
>  * add back docs
> 
> v2->v3:
>  * split into bus (usb-ccid.c, uses ccid.h) and card (ccid-card-passthru.c).
>  * removed documentation (being revised).
> 
> v1->v2:
>  * all QSIMPLEQ turned into fixed sized rings
>  * all allocated buffers turned into fixed size buffers
>  * added migration support
>  * added a message to tell client qemu has migrated to ip:port
>   * for lack of monitor commands ip:port are 0:0, which causes the updated
>vscclient to connect to one port higher on the same host. will add monitor
>commands in a separate patch. tested with current setup.
> 
> Alon Levy (6):
>   usb-ccid: add CCID bus
>   ccid: add passthru card device
>   ccid: add ccid-card-emulated device (v2)
>   ccid: add docs
>   ccid: configure: add --enable/disable and nss only disable
>

Re: [Qemu-devel] [PATCH 1/3] block: add resize monitor command

2011-01-17 Thread Christoph Hellwig
On Mon, Jan 17, 2011 at 11:28:47AM +, Stefan Hajnoczi wrote:
> > + ? ?if (bdrv_get_type_hint(bs) == BDRV_TYPE_CDROM) {
> > + ? ? ? ?error_report("Can not resize CDROM devices\n");
> > + ? ? ? ?return -1;
> > + ? ?}
> 
> Hrm...BDRV_TYPE_FLOPPY probably too?

If we want to be consistent, yes.  Or we could remove the CDROM check
and let people shoot themselves in the foot as much as they want.




[Qemu-devel] Re: [PATCH 8/8] ahci: fix !msi interrupts

2011-01-17 Thread Alexander Graf
Jan Kiszka wrote:
> On 2010-12-20 22:13, Alexander Graf wrote:
>   
>> When not using MSI, receiving an interrupt while the interrupt line is active
>> pulses the interrupt line. Without this, guests don't realize that a new
>> interrupt occured.
>> 
>
> This doesn't look OK. The device model should look at the currently used
> mode and switch between edge and level triggering accordingly. As it
> appears like this is what it already does, this change may just paper
> over the real issue.
>   

Well, I have this internal abstraction to make edge and level triggered
interrupt triggering easier. irq_lower is a simple nop for the edge case.


Alex




Re: [Qemu-devel] [PATCH v2 5/6] Emulation of Leon3.

2011-01-17 Thread Fabien Chouteau

On 01/04/2011 07:56 PM, Blue Swirl wrote:

On Mon, Jan 3, 2011 at 2:07 PM, Fabien Chouteau  wrote:

diff --git a/hw/leon3.c b/hw/leon3.c
new file mode 100644
index 000..d5fe863
--- /dev/null
+++ b/hw/leon3.c
@@ -0,0 +1,202 @@
+/*
+ * QEMU Leon3 System Emulator
+ *
+ * Copyright (c) 2010-2011 AdaCore
+ *
+ * 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 "hw.h"
+#include "qemu-timer.h"
+#include "qemu-char.h"
+#include "sysemu.h"
+#include "boards.h"
+#include "loader.h"
+#include "elf.h"
+
+#include "grlib.h"
+
+//#define DEBUG_LEON3
+
+#ifdef DEBUG_LEON3
+#define DPRINTF(fmt, ...)   \
+do { printf("Leon3: " fmt , ## __VA_ARGS__); } while (0)
+#else
+#define DPRINTF(fmt, ...)
+#endif
+
+/* Default system clock.  */
+#define CPU_CLK (40 * 1000 * 1000)
+
+#define PROM_FILENAME"u-boot.bin"
+
+#define MAX_PILS 16
+
+typedef struct ResetData {
+CPUState *env;
+uint64_t  entry;/* save kernel entry in case of reset */


uint32_t should be enough.


+} ResetData;
+
+static void main_cpu_reset(void *opaque)
+{
+ResetData *s = (ResetData *)opaque;
+assert(s != NULL);
+CPUState *env = s->env;
+assert(env != NULL);


These asserts won't ever trigger.


+
+cpu_reset(env);
+
+env->halted = 0;
+env->pc = s->entry;
+env->npc= s->entry + 4;
+}
+
+static void leon3_irq_ack(void *irq_manager, int intno)
+{
+grlib_irqmp_ack((DeviceState *)irq_manager, intno);
+leon3_cache_control_int();
+}
+
+static void leon3_generic_hw_init(ram_addr_t  ram_size,
+  const char *boot_device,
+  const char *kernel_filename,
+  const char *kernel_cmdline,
+  const char *initrd_filename,
+  const char *cpu_model)
+{
+CPUState   *env;
+ram_addr_t  ram_offset, prom_offset;
+int ret;
+char   *filename;
+qemu_irq   *cpu_irqs = NULL;
+int bios_size;
+int prom_size;
+int aligned_bios_size;
+ResetData  *reset_info;
+
+/* Init CPU */
+if (!cpu_model) {
+cpu_model = "LEON3";
+}
+
+env = cpu_init(cpu_model);
+if (!env) {
+fprintf(stderr, "qemu: Unable to find Sparc CPU definition\n");
+exit(1);
+}
+
+cpu_sparc_set_id(env, 0);
+
+/* Reset data */
+reset_info= qemu_mallocz(sizeof(ResetData));
+reset_info->env   = env;
+qemu_register_reset(main_cpu_reset, reset_info);
+
+/* Allocate IRQ manager */
+grlib_irqmp_create(0x8200, env,&cpu_irqs, MAX_PILS);
+
+env->qemu_irq_ack = leon3_irq_ack;
+
+/* Allocate RAM */
+if ((uint64_t)ram_size>  (1UL<<  30)) {
+fprintf(stderr,
+"qemu: Too much memory for this machine: %d, maximum 1G\n",
+(unsigned int)(ram_size / (1024 * 1024)));
+exit(1);
+}
+
+ram_offset = qemu_ram_alloc(NULL, "leon3.ram", ram_size);
+cpu_register_physical_memory(0x4000, ram_size, ram_offset | 
IO_MEM_RAM);
+
+/* Allocate BIOS */
+prom_size = 8 * 1024 * 1024; /* 8Mb */
+prom_offset = qemu_ram_alloc(NULL, "Leon3.bios", prom_size);
+cpu_register_physical_memory(0x, prom_size,
+ prom_offset | IO_MEM_ROM);
+
+/* Load boot prom */
+if (bios_name == NULL) {
+bios_name = PROM_FILENAME;
+}
+filename = qemu_find_file(QEMU_FILE_TYPE_BIOS, bios_name);
+
+bios_size = get_image_size(filename);
+
+if (bios_size>  prom_size) {
+fprintf(stderr, "qemu: could not load prom '%s': file too big \n",
+filename);
+exit(1);
+}
+
+if (bios_size>  0) {
+aligned_bios_size =
+(bios_size + TARGET_PAGE_SIZE - 1)&  TARGET_PAGE_MASK;
+
+ret = load_image_targphys(filename, 0x, bio

[Qemu-devel] Re: [PATCH 8/8] ahci: fix !msi interrupts

2011-01-17 Thread Jan Kiszka
On 2011-01-17 17:00, Alexander Graf wrote:
> Jan Kiszka wrote:
>> On 2010-12-20 22:13, Alexander Graf wrote:
>>   
>>> When not using MSI, receiving an interrupt while the interrupt line is 
>>> active
>>> pulses the interrupt line. Without this, guests don't realize that a new
>>> interrupt occured.
>>> 
>>
>> This doesn't look OK. The device model should look at the currently used
>> mode and switch between edge and level triggering accordingly. As it
>> appears like this is what it already does, this change may just paper
>> over the real issue.
>>   
> 
> Well, I have this internal abstraction to make edge and level triggered
> interrupt triggering easier. irq_lower is a simple nop for the edge case.
> 

I'm concerned about the artificial edge you generate for the level
triggered case. That's not like real hw behaves. If you need it,
something else might still be broken.

Jan

-- 
Siemens AG, Corporate Technology, CT T DE IT 1
Corporate Competence Center Embedded Linux



Re: [Qemu-devel] Re: [PATCH] usb-msd: Add usb-storage, removable=on|off property

2011-01-17 Thread Christoph Hellwig
On Mon, Jan 17, 2011 at 10:04:05AM +, Stefan Hajnoczi wrote:
> I was considering not using bdrv_set_removable() and instead adding a
> hint to the BlockDriverState which gets checked when constructing the
> SCSI INQUIRY response.  If we take that approach, then QEMU doesn't
> consider the block device removable in the eject/change medium sense.

I think that's the better approach.  What about moving the removable
qdev property up from the usb driver into the scsi-disk driver?  That's
where it logically belongs, and avoids the need to add another hint.



[Qemu-devel] Re: [PATCH 8/8] ahci: fix !msi interrupts

2011-01-17 Thread Alexander Graf
Jan Kiszka wrote:
> On 2011-01-17 17:00, Alexander Graf wrote:
>   
>> Jan Kiszka wrote:
>> 
>>> On 2010-12-20 22:13, Alexander Graf wrote:
>>>   
>>>   
 When not using MSI, receiving an interrupt while the interrupt line is 
 active
 pulses the interrupt line. Without this, guests don't realize that a new
 interrupt occured.
 
 
>>> This doesn't look OK. The device model should look at the currently used
>>> mode and switch between edge and level triggering accordingly. As it
>>> appears like this is what it already does, this change may just paper
>>> over the real issue.
>>>   
>>>   
>> Well, I have this internal abstraction to make edge and level triggered
>> interrupt triggering easier. irq_lower is a simple nop for the edge case.
>>
>> 
>
> I'm concerned about the artificial edge you generate for the level
> triggered case. That's not like real hw behaves. If you need it,
> something else might still be broken.
>   

Hrm. So worst case we generate a spurious interrupt?


Alex




Re: [Qemu-devel] [PULL] rtl8139, pci, ioeventfd

2011-01-17 Thread Anthony Liguori

On 01/11/2011 04:42 PM, Michael S. Tsirkin wrote:

The following changes since commit 05bf441eb69a813d3893174d54faa6afa8c0d39b:

   cris: Remove unused orig_flags (2011-01-10 23:28:08 +0100)

are available in the git repository at:
   git://git.kernel.org/pub/scm/linux/kernel/git/mst/qemu.git for_anthony
   


Pulled.  Thanks.

Regards,

Anthony Liguori


Alex Williamson (2):
   qdev: Track runtime machine modifications
   rtl8139: Use subsection to restrict migration after hotplug

Gerd Hoffmann (4):
   pci: allow devices being tagged as not hotpluggable.
   piix: tag as not hotpluggable.
   vga: tag as not hotplugable.
   qxl: tag as not hotpluggable

Michael S. Tsirkin (3):
   Merge remote branch 'origin/master' into pci
   virtio: move vmstate change tracking to core
   ioeventfd: error handling cleanup

Stefan Hajnoczi (4):
   virtio-pci: Rename bugs field to flags
   kvm: test for ioeventfd support on old kernels
   virtio-pci: Use ioeventfd for virtqueue notify
   docs: Document virtio PCI -device ioeventfd=on|off

  Makefile.objs|4 +-
  Makefile.target  |2 +
  docs/qdev-device-use.txt |8 ++-
  hmp-commands.hx  |   25 +
  hw/acpi_piix4.c  |2 +
  hw/cirrus_vga.c  |1 +
  hw/ide/piix.c|2 +
  hw/pc_piix.c |   12 +--
  hw/pci-stub.c|   50 ++
  hw/pci.c |   92 ++--
  hw/pci.h |5 +
  hw/pcie.c|   11 +--
  hw/pcie.h|2 -
  hw/pcie_aer.c|  223 ++
  hw/piix4.c   |1 +
  hw/piix_pci.c|2 +
  hw/qdev.c|   23 -
  hw/qdev.h|6 +-
  hw/qxl.c |1 +
  hw/rtl8139.c |   28 ++-
  hw/vga-pci.c |1 +
  hw/virtio-net.c  |   28 ++-
  hw/virtio-pci.c  |  213 ++--
  hw/virtio.c  |   36 +++-
  hw/virtio.h  |4 +
  hw/vmware_vga.c  |1 +
  hw/xio3130_downstream.c  |2 +-
  hw/xio3130_upstream.c|3 -
  kvm-all.c|   49 ++
  kvm-stub.c   |5 +
  kvm.h|1 +
  qerror.c |4 +
  qerror.h |3 +
  sysemu.h |5 +
  vl.c |4 +-
  35 files changed, 769 insertions(+), 90 deletions(-)
  create mode 100644 hw/pci-stub.c


   





[Qemu-devel] Re: [PATCH 8/8] ahci: fix !msi interrupts

2011-01-17 Thread Jan Kiszka
On 2011-01-17 17:04, Alexander Graf wrote:
> Jan Kiszka wrote:
>> On 2011-01-17 17:00, Alexander Graf wrote:
>>   
>>> Jan Kiszka wrote:
>>> 
 On 2010-12-20 22:13, Alexander Graf wrote:
   
   
> When not using MSI, receiving an interrupt while the interrupt line is 
> active
> pulses the interrupt line. Without this, guests don't realize that a new
> interrupt occured.
> 
> 
 This doesn't look OK. The device model should look at the currently used
 mode and switch between edge and level triggering accordingly. As it
 appears like this is what it already does, this change may just paper
 over the real issue.
   
   
>>> Well, I have this internal abstraction to make edge and level triggered
>>> interrupt triggering easier. irq_lower is a simple nop for the edge case.
>>>
>>> 
>>
>> I'm concerned about the artificial edge you generate for the level
>> triggered case. That's not like real hw behaves. If you need it,
>> something else might still be broken.
>>   
> 
> Hrm. So worst case we generate a spurious interrupt?
> 

Worse might also be that unknown issue that force you to inject an IRQ
here. We don't know. That's probably worst.

Jan

-- 
Siemens AG, Corporate Technology, CT T DE IT 1
Corporate Competence Center Embedded Linux



[Qemu-devel] Re: [PATCH 8/8] ahci: fix !msi interrupts

2011-01-17 Thread Alexander Graf
Jan Kiszka wrote:
> On 2011-01-17 17:04, Alexander Graf wrote:
>   
>> Jan Kiszka wrote:
>> 
>>> On 2011-01-17 17:00, Alexander Graf wrote:
>>>   
>>>   
 Jan Kiszka wrote:
 
 
> On 2010-12-20 22:13, Alexander Graf wrote:
>   
>   
>   
>> When not using MSI, receiving an interrupt while the interrupt line is 
>> active
>> pulses the interrupt line. Without this, guests don't realize that a new
>> interrupt occured.
>> 
>> 
>> 
> This doesn't look OK. The device model should look at the currently used
> mode and switch between edge and level triggering accordingly. As it
> appears like this is what it already does, this change may just paper
> over the real issue.
>   
>   
>   
 Well, I have this internal abstraction to make edge and level triggered
 interrupt triggering easier. irq_lower is a simple nop for the edge case.

 
 
>>> I'm concerned about the artificial edge you generate for the level
>>> triggered case. That's not like real hw behaves. If you need it,
>>> something else might still be broken.
>>>   
>>>   
>> Hrm. So worst case we generate a spurious interrupt?
>>
>> 
>
> Worse might also be that unknown issue that force you to inject an IRQ
> here. We don't know. That's probably worst.
>   

Well, IIRC the issue was that usually a level high interrupt line would
simply retrigger an interrupt after enabling the interrupt line in the
APIC again. Unless my memory completely fails on me, that didn't happen,
so I added the manual retrigger on a partial command ACK in ahci code.


Alex




[Qemu-devel] Re: [PATCH 8/8] ahci: fix !msi interrupts

2011-01-17 Thread Jan Kiszka
On 2011-01-17 17:33, Alexander Graf wrote:
> Jan Kiszka wrote:
>> On 2011-01-17 17:04, Alexander Graf wrote:
>>   
>>> Jan Kiszka wrote:
>>> 
 On 2011-01-17 17:00, Alexander Graf wrote:
   
   
> Jan Kiszka wrote:
> 
> 
>> On 2010-12-20 22:13, Alexander Graf wrote:
>>   
>>   
>>   
>>> When not using MSI, receiving an interrupt while the interrupt line is 
>>> active
>>> pulses the interrupt line. Without this, guests don't realize that a new
>>> interrupt occured.
>>> 
>>> 
>>> 
>> This doesn't look OK. The device model should look at the currently used
>> mode and switch between edge and level triggering accordingly. As it
>> appears like this is what it already does, this change may just paper
>> over the real issue.
>>   
>>   
>>   
> Well, I have this internal abstraction to make edge and level triggered
> interrupt triggering easier. irq_lower is a simple nop for the edge case.
>
> 
> 
 I'm concerned about the artificial edge you generate for the level
 triggered case. That's not like real hw behaves. If you need it,
 something else might still be broken.
   
   
>>> Hrm. So worst case we generate a spurious interrupt?
>>>
>>> 
>>
>> Worse might also be that unknown issue that force you to inject an IRQ
>> here. We don't know. That's probably worst.
>>   
> 
> Well, IIRC the issue was that usually a level high interrupt line would
> simply retrigger an interrupt after enabling the interrupt line in the
> APIC again. Unless my memory completely fails on me, that didn't happen,
> so I added the manual retrigger on a partial command ACK in ahci code.
> 

How many other device models require this workaround? And is this a
limitation of a specific irqchip model or of the irq layer (I can't
believe it's the latter though)? All fairly suspicious...

Jan

-- 
Siemens AG, Corporate Technology, CT T DE IT 1
Corporate Competence Center Embedded Linux



[Qemu-devel] Re: [PATCH 8/8] ahci: fix !msi interrupts

2011-01-17 Thread Alexander Graf
Jan Kiszka wrote:
> On 2011-01-17 17:33, Alexander Graf wrote:
>   
>> Jan Kiszka wrote:
>> 
>>> On 2011-01-17 17:04, Alexander Graf wrote:
>>>   
>>>   
 Jan Kiszka wrote:
 
 
> On 2011-01-17 17:00, Alexander Graf wrote:
>   
>   
>   
>> Jan Kiszka wrote:
>> 
>> 
>> 
>>> On 2010-12-20 22:13, Alexander Graf wrote:
>>>   
>>>   
>>>   
>>>   
 When not using MSI, receiving an interrupt while the interrupt line is 
 active
 pulses the interrupt line. Without this, guests don't realize that a 
 new
 interrupt occured.
 
 
 
 
>>> This doesn't look OK. The device model should look at the currently used
>>> mode and switch between edge and level triggering accordingly. As it
>>> appears like this is what it already does, this change may just paper
>>> over the real issue.
>>>   
>>>   
>>>   
>>>   
>> Well, I have this internal abstraction to make edge and level triggered
>> interrupt triggering easier. irq_lower is a simple nop for the edge case.
>>
>> 
>> 
>> 
> I'm concerned about the artificial edge you generate for the level
> triggered case. That's not like real hw behaves. If you need it,
> something else might still be broken.
>   
>   
>   
 Hrm. So worst case we generate a spurious interrupt?

 
 
>>> Worse might also be that unknown issue that force you to inject an IRQ
>>> here. We don't know. That's probably worst.
>>>   
>>>   
>> Well, IIRC the issue was that usually a level high interrupt line would
>> simply retrigger an interrupt after enabling the interrupt line in the
>> APIC again. Unless my memory completely fails on me, that didn't happen,
>> so I added the manual retrigger on a partial command ACK in ahci code.
>>
>> 
>
> How many other device models require this workaround? And is this a
> limitation of a specific irqchip model or of the irq layer (I can't
> believe it's the latter though)? All fairly suspicious...
>   

I don't know :).


Alex




[Qemu-devel] [PATCH][qemu-iotests] add support for rbd and sheepdog protocols

2011-01-17 Thread MORITA Kazutaka
This patch introduces tests for protocols other than file, and
initially supports rbd and sheepdog.

Signed-off-by: MORITA Kazutaka 
---
 001   |1 +
 002   |1 +
 003   |1 +
 004   |1 +
 005   |6 ++
 006   |1 +
 007   |1 +
 008   |1 +
 009   |1 +
 010   |1 +
 011   |1 +
 012   |1 +
 013   |1 +
 014   |1 +
 015   |1 +
 016   |1 +
 017   |1 +
 018   |1 +
 019   |1 +
 020   |1 +
 021   |1 +
 022   |1 +
 023   |1 +
 024   |1 +
 025   |1 +
 026   |1 +
 027   |1 +
 028   |1 +
 check |2 ++
 common|   13 +
 common.rc |   45 +
 31 files changed, 89 insertions(+), 4 deletions(-)

diff --git a/001 b/001
index fe66a8e..bd88dde 100755
--- a/001
+++ b/001
@@ -39,6 +39,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 . ./common.filter
 
 _supported_fmt generic
+_supported_proto generic
 _supported_os Linux
 
 
diff --git a/002 b/002
index 57af974..bebed84 100755
--- a/002
+++ b/002
@@ -39,6 +39,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 . ./common.filter
 
 _supported_fmt generic
+_supported_proto generic
 _supported_os Linux
 
 
diff --git a/003 b/003
index 656da99..ee25fb8 100755
--- a/003
+++ b/003
@@ -39,6 +39,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 . ./common.filter
 
 _supported_fmt generic
+_supported_proto generic
 _supported_os Linux
 
 size=128M
diff --git a/004 b/004
index 3de7ed8..c76451c 100755
--- a/004
+++ b/004
@@ -39,6 +39,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 . ./common.filter
 
 _supported_fmt generic
+_supported_proto generic
 _supported_os Linux
 
 
diff --git a/005 b/005
index 480276b..74537db 100755
--- a/005
+++ b/005
@@ -42,6 +42,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 . ./common.filter
 
 _supported_fmt generic
+_supported_proto generic
 _supported_os Linux
 
 # vpc is limited to 127GB, so we can't test it here
@@ -49,6 +50,11 @@ if [ "$IMGFMT" = "vpc" ]; then
 _notrun "image format $IMGFMT does not support large image sizes"
 fi
 
+# sheepdog image is limited to 4TB, so we can't test it here
+if [ "$IMGPROTO" = "sheepdog" ]; then
+_notrun "image protocol $IMGPROTO does not support large image sizes"
+fi
+
 echo
 echo "creating large image"
 _make_test_img 5000G
diff --git a/006 b/006
index 98ef4ea..0c0cf5d 100755
--- a/006
+++ b/006
@@ -40,6 +40,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 . ./common.filter
 
 _supported_fmt vpc
+_supported_proto generic
 _supported_os Linux
 
 
diff --git a/007 b/007
index 2de1aa4..0139264 100755
--- a/007
+++ b/007
@@ -41,6 +41,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 
 # currently only qcow2 allows for consistency checks using qemu-img
 _supported_fmt qcow2
+_supported_proto generic
 _supported_os Linux
 
 echo
diff --git a/008 b/008
index b697deb..2c53bac 100755
--- a/008
+++ b/008
@@ -39,6 +39,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 . ./common.filter
 
 _supported_fmt generic
+_supported_proto generic
 _supported_os Linux
 
 
diff --git a/009 b/009
index 1499b77..f7262b5 100755
--- a/009
+++ b/009
@@ -39,6 +39,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 . ./common.filter
 
 _supported_fmt generic
+_supported_proto generic
 _supported_os Linux
 
 
diff --git a/010 b/010
index 440e9f6..e3205aa 100755
--- a/010
+++ b/010
@@ -39,6 +39,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 . ./common.filter
 
 _supported_fmt generic
+_supported_proto generic
 _supported_os Linux
 
 
diff --git a/011 b/011
index 87b4082..59df1ae 100755
--- a/011
+++ b/011
@@ -39,6 +39,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 . ./common.filter
 
 _supported_fmt generic
+_supported_proto generic
 _supported_os Linux
 
 
diff --git a/012 b/012
index 32a2647..4052956 100755
--- a/012
+++ b/012
@@ -41,6 +41,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 . ./common.filter
 
 _supported_fmt generic
+_supported_proto file
 _supported_os Linux
 
 
diff --git a/013 b/013
index 0671bf6..ce40d5c 100755
--- a/013
+++ b/013
@@ -41,6 +41,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 
 # much of this could be generic for any format supporting compression.
 _supported_fmt qcow qcow2
+_supported_proto generic
 _supported_os Linux
 
 TEST_OFFSETS="0 4294967296"
diff --git a/014 b/014
index f38af43..a6d0aea 100755
--- a/014
+++ b/014
@@ -43,6 +43,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 
 # much of this could be generic for any format supporting snapshots
 _supported_fmt qcow2
+_supported_proto generic
 _supported_os Linux
 
 TEST_OFFSETS="0 4294967296"
diff --git a/015 b/015
index f3b0acc..bdafd26 100755
--- a/015
+++ b/015
@@ -41,6 +41,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15
 
 # actually any format that supports snapshots
 _supported_fmt qcow2
+_supported_proto generic
 _supported_os Linux
 
 echo
diff --git a/016 b/016
index e09a

[Qemu-devel] Re: [PATCH v2 0/2] strtosz() cleanup

2011-01-17 Thread Alex Williamson
On Mon, 2011-01-17 at 08:24 -0700, Alex Williamson wrote:
> On Mon, 2011-01-17 at 16:14 +0100, jes.soren...@redhat.com wrote:
> > From: Jes Sorensen 
> > 
> > Fix issue with signed char and isspace() as well as clean up switch
> > statement using toupper().
> > 
> > V2 of the patch fixes some types in the commit messages and spells
> > Eric correctly. My apologies for getting it wrong.
> > 
> > Jes Sorensen (2):
> >   strtosz() use unsigned char as isspace() is not defined for signed
> > char
> >   strtosz() use toupper() to simplify switch statement
> > 
> >  cutils.c |   10 +++---
> >  1 files changed, 3 insertions(+), 7 deletions(-)
> > 
> 
> And the modf() usage?  Or using STRTOSZ_DEFSUFFIX_* in the switch?  Or
> avoiding the extra variable in 13/18?  Thanks,

Sorry, I'm crossing my mailing lists.  These are a fine first step.

Acked-by: Alex Williamson 




[Qemu-devel] [PATCH 1/2] strtosz(): Fix name confusion in use of modf()

2011-01-17 Thread Jes . Sorensen
From: Jes Sorensen 

Signed-off-by: Jes Sorensen 
---
 cutils.c |4 ++--
 1 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/cutils.c b/cutils.c
index f7aa90c..328738c 100644
--- a/cutils.c
+++ b/cutils.c
@@ -304,8 +304,8 @@ ssize_t strtosz_suffix(const char *nptr, char **end, const 
char default_suffix)
 if (isnan(val) || endptr == nptr || errno != 0) {
 goto fail;
 }
-integral = modf(val, &fraction);
-if (integral != 0) {
+fraction = modf(val, &integral);
+if (fraction != 0) {
 mul_required = 1;
 }
 /*
-- 
1.7.3.4




[Qemu-devel] [PATCH 0/2] strtosz() more cleanups

2011-01-17 Thread Jes . Sorensen
From: Jes Sorensen 

Another two cleanups to strtosz() suggested by Alex Williamson.

I had reversed the use of the names of the return arguments to modf(),
and use the STRTOSZ_DESUFFIX_ macros in the switch() statement.

Cheers,
Jes


Jes Sorensen (2):
  strtosz(): Fix name confusion in use of modf()
  strtosz(): Use suffix macros in switch() statement

 cutils.c |   14 +++---
 1 files changed, 7 insertions(+), 7 deletions(-)

-- 
1.7.3.4




[Qemu-devel] Re: [PATCH 0/2] strtosz() more cleanups

2011-01-17 Thread Alex Williamson
On Mon, 2011-01-17 at 18:12 +0100, jes.soren...@redhat.com wrote:
> From: Jes Sorensen 
> 
> Another two cleanups to strtosz() suggested by Alex Williamson.
> 
> I had reversed the use of the names of the return arguments to modf(),
> and use the STRTOSZ_DESUFFIX_ macros in the switch() statement.
> 
> Cheers,
> Jes
> 
> 
> Jes Sorensen (2):
>   strtosz(): Fix name confusion in use of modf()
>   strtosz(): Use suffix macros in switch() statement
> 
>  cutils.c |   14 +++---
>  1 files changed, 7 insertions(+), 7 deletions(-)
> 

Acked-by: Alex Williamson 




[Qemu-devel] [PATCH 2/2] strtosz(): Use suffix macros in switch() statement

2011-01-17 Thread Jes . Sorensen
From: Jes Sorensen 

Signed-off-by: Jes Sorensen 
---
 cutils.c |   10 +-
 1 files changed, 5 insertions(+), 5 deletions(-)

diff --git a/cutils.c b/cutils.c
index 328738c..f2c8bbd 100644
--- a/cutils.c
+++ b/cutils.c
@@ -324,26 +324,26 @@ ssize_t strtosz_suffix(const char *nptr, char **end, 
const char default_suffix)
 }
 }
 switch (toupper(d)) {
-case 'B':
+case STRTOSZ_DEFSUFFIX_B:
 mul = 1;
 if (mul_required) {
 goto fail;
 }
 break;
-case 'K':
+case STRTOSZ_DEFSUFFIX_KB:
 mul = 1 << 10;
 break;
 case 0:
 if (mul_required) {
 goto fail;
 }
-case 'M':
+case STRTOSZ_DEFSUFFIX_MB:
 mul = 1ULL << 20;
 break;
-case 'G':
+case STRTOSZ_DEFSUFFIX_GB:
 mul = 1ULL << 30;
 break;
-case 'T':
+case STRTOSZ_DEFSUFFIX_TB:
 mul = 1ULL << 40;
 break;
 default:
-- 
1.7.3.4




Re: [Qemu-devel] [PATCH 1/3] block: add resize monitor command

2011-01-17 Thread Kevin Wolf
Am 14.01.2011 17:20, schrieb Christoph Hellwig:
> Add a monitor command that allows resizing of block devices while
> qemu is running.  It uses the existing bdrv_truncate method already
> used by qemu-img to do it's work.  Compared to qemu-img the size
> parsing is very simplicistic, but I think having a properly numering
> object is more useful for non-humand monitor users than having
> the units and relative resize parsing.
> 
> For SCSI devices the new size can be updated in Linux guests by
> doing the following shell command:
> 
>   echo > /sys/class/scsi_device/0:0:0:0/device/rescan
> 
> For ATA devices I don't know of a way to update the block device
> size in Linux system, and for virtio-blk the next two patches
> will provide an automatic update of the size when this command
> is issued on the host.
> 
> Signed-off-by: Christoph Hellwig 
> 
> Index: qemu/hmp-commands.hx
> ===
> --- qemu.orig/hmp-commands.hx 2011-01-14 15:11:48.527004132 +0100
> +++ qemu/hmp-commands.hx  2011-01-14 15:40:14.407006506 +0100
> @@ -53,6 +53,24 @@ Quit the emulator.
>  ETEXI
>  
>  {
> +.name   = "resize",
> +.args_type  = "id:s,size:l",

size should be 'o' instead of 'l'. The latter may be too small on 32 bit
hosts and doesn't support convenient suffixes:

 * 'l'  target long (32 or 64 bit)

 * 'o'  octets (aka bytes)
 *  user mode accepts an optional T, t, G, g, M, m, K, k
 *  suffix, which multiplies the value by 2^40 for
 *  suffixes T and t, 2^30 for suffixes G and g, 2^20 for
 *  M and m, 2^10 for K and k

> +.params = "device size",
> +.help   = "resize a block image",
> +.user_print = monitor_user_noop,
> +.mhandler.cmd_new = do_resize,
> +},
> +
> +STEXI
> +@item resize
> +@findex resize
> +Resize a block image while a guest is running.  Usuaully requires guest
> +action to see the updated size.  Resize to a lower size is supported,
> +but should be used with extreme caution.
> +ETEXI
> +
> +
> +{
>  .name   = "eject",
>  .args_type  = "force:-f,device:B",
>  .params = "[-f] device",
> Index: qemu/blockdev.c
> ===
> --- qemu.orig/blockdev.c  2011-01-14 15:11:48.539261151 +0100
> +++ qemu/blockdev.c   2011-01-14 15:50:35.604293558 +0100
> @@ -700,3 +700,41 @@ int do_drive_del(Monitor *mon, const QDi
>  
>  return 0;
>  }
> +
> +int do_resize(Monitor *mon, const QDict *qdict, QObject **ret_data)
> +{
> +const char *id = qdict_get_str(qdict, "id");
> +int64_t size = qdict_get_int(qdict, "size");
> +BlockDriverState *bs;
> +
> +bs = bdrv_find(id);
> +if (!bs) {
> +qerror_report(QERR_DEVICE_NOT_FOUND, id);
> +return -1;
> +}
> +
> +if (bdrv_get_type_hint(bs) == BDRV_TYPE_CDROM) {
> +error_report("Can not resize CDROM devices\n");
> +return -1;
> +}

Hm, is there a real reason except that CD-ROMs are read-only? The code
below seems to take read-only devices into account.

Kevin



[Qemu-devel] Re: [PATCH 08/12] Threadlet: Add aio_signal_handler threadlet API

2011-01-17 Thread Stefan Hajnoczi
On Mon, Jan 17, 2011 at 3:54 PM, Paolo Bonzini  wrote:
> On 01/17/2011 10:56 AM, Stefan Hajnoczi wrote:
>>
>> This would be the right place to create qemu-threadlet.c,
>
> You mean .h?

We need both qemu-threadlet.c and qemu-threadlet.h.

Stefan



Re: [Qemu-devel] [PATCH] qed: Refuse to create images on block devices

2011-01-17 Thread Kevin Wolf
Am 14.01.2011 23:44, schrieb Stefan Hajnoczi:
> QED relies on the underlying filesystem to extend the file and maintain
> its size.  Check that images are not created on a block device.
> 
> Signed-off-by: Stefan Hajnoczi 

Thanks, applied to the block branch.

Kevin



Re: [Qemu-devel] Re: [PATCH] usb-msd: Add usb-storage, removable=on|off property

2011-01-17 Thread Stefan Hajnoczi
On Mon, Jan 17, 2011 at 4:01 PM, Christoph Hellwig  wrote:
> On Mon, Jan 17, 2011 at 10:04:05AM +, Stefan Hajnoczi wrote:
>> I was considering not using bdrv_set_removable() and instead adding a
>> hint to the BlockDriverState which gets checked when constructing the
>> SCSI INQUIRY response.  If we take that approach, then QEMU doesn't
>> consider the block device removable in the eject/change medium sense.
>
> I think that's the better approach.  What about moving the removable
> qdev property up from the usb driver into the scsi-disk driver?  That's
> where it logically belongs, and avoids the need to add another hint.

That could work although the plumbing to get us to the point where a
scsi-disk qdev is created isn't very pretty either.  I'll try adding a
removable property and setting it in a sane way.

Stefan



[Qemu-devel] Re: [PATCH V2 1/3] Introduce log_start/log_stop in CPUPhysMemoryClient

2011-01-17 Thread Anthony PERARD
On Mon, 17 Jan 2011, Jan Kiszka wrote:

> On 2011-01-14 19:10, anthony.per...@citrix.com wrote:
> > From: Anthony PERARD 
> >
> > In order to use log_start/log_stop with Xen as well in the vga code,
> > this two operations have been put in CPUPhysMemoryClient.
> >
> > The two new functions cpu_physical_log_start,cpu_physical_log_stop are
> > used in hw/vga.c and replace the kvm_log_start/stop. With this, vga does
> > no longer depends on kvm header.
>
> Basically, this looks good to me. Two remarks below.
>
> >
> > Signed-off-by: Anthony PERARD 
> > ---
> >  cpu-all.h|6 ++
> >  cpu-common.h |4 
> >  exec.c   |   42 ++
> >  hw/vga.c |   31 ---
> >  hw/vhost.c   |   16 
> >  kvm-all.c|8 ++--
> >  kvm-stub.c   |   10 --
> >  kvm.h|3 ---
> >  8 files changed, 90 insertions(+), 30 deletions(-)
> >
> > diff --git a/exec.c b/exec.c
> > index c6ed96d..609ec88 100644
> > --- a/exec.c
> > +++ b/exec.c
> > @@ -1734,6 +1734,30 @@ static int cpu_notify_migration_log(int enable)
> >  return 0;
> >  }
> >
> > +static int cpu_notify_log_start(target_phys_addr_t start,
> > +ram_addr_t size)
> > +{
> > +CPUPhysMemoryClient *client;
> > +QLIST_FOREACH(client, &memory_client_list, list) {
> > +int r = client->log_start(client, start, size);
> > +if (r < 0)
> > +return r;
> > +}
> > +return 0;
> > +}
> > +
> > +static int cpu_notify_log_stop(target_phys_addr_t start,
> > +   ram_addr_t size)
> > +{
> > +CPUPhysMemoryClient *client;
> > +QLIST_FOREACH(client, &memory_client_list, list) {
> > +int r = client->log_stop(client, start, size);
> > +if (r < 0)
> > +return r;
> > +}
> > +return 0;
> > +}
> > +
>
> I would make the new callbacks optional, i.e. only invoke them if the
> handler is non-NULL. Avoids stubs and branching to vhost.

Ok, I will do that.

> >  static void phys_page_for_each_1(CPUPhysMemoryClient *client,
> >   int level, void **lp)
> >  {
> > @@ -2073,6 +2097,24 @@ int 
> > cpu_physical_sync_dirty_bitmap(target_phys_addr_t start_addr,
> >  return ret;
> >  }
> >
> > +int cpu_physical_log_start(target_phys_addr_t start_addr,
> > +   ram_addr_t size)
> > +{
> > +int ret;
> > +
> > +ret = cpu_notify_log_start(start_addr, size);
> > +return ret;
> > +}
> > +
> > +int cpu_physical_log_stop(target_phys_addr_t start_addr,
> > +  ram_addr_t size)
> > +{
> > +int ret;
> > +
> > +ret = cpu_notify_log_stop(start_addr, size);
> > +return ret;
> > +}
> > +
>
> I consider this split-up between API frontend and cpu_notify_* backend
> as unneeded. But that's not your fault, you just follow the pre-existing
> pattern. Unless someone feels strong about this, you may just keep it.

Actually, I will remove it, and keep only the frontend fonction.

Thanks,

-- 
Anthony PERARD



[Qemu-devel] [PATCH 4/5] blockdev: Fix drive_del not to crash when drive is not in use

2011-01-17 Thread Markus Armbruster
Watch this:

(qemu) drive_add 0 if=none,file=tmp.img
OK
(qemu) info block
none0: type=hd removable=0 file=tmp.img ro=0 drv=raw encrypted=0
(qemu) drive_del none0
Segmentation fault (core dumped)

do_drive_del()'s code to clean up the pointer from a qdev using the
drive back to the drive needs to check whether such a device exists.

Signed-off-by: Markus Armbruster 
---
 blockdev.c |   16 +---
 1 files changed, 9 insertions(+), 7 deletions(-)

diff --git a/blockdev.c b/blockdev.c
index 04a0e84..51a2da3 100644
--- a/blockdev.c
+++ b/blockdev.c
@@ -682,13 +682,15 @@ int do_drive_del(Monitor *mon, const QDict *qdict, 
QObject **ret_data)
 
 /* clean up guest state from pointing to host resource by
  * finding and removing DeviceState "drive" property */
-for (prop = bs->peer->info->props; prop && prop->name; prop++) {
-if (prop->info->type == PROP_TYPE_DRIVE) {
-ptr = qdev_get_prop_ptr(bs->peer, prop);
-if ((*ptr) == bs) {
-bdrv_detach(bs, bs->peer);
-*ptr = NULL;
-break;
+if (bs->peer) {
+for (prop = bs->peer->info->props; prop && prop->name; prop++) {
+if (prop->info->type == PROP_TYPE_DRIVE) {
+ptr = qdev_get_prop_ptr(bs->peer, prop);
+if (*ptr == bs) {
+bdrv_detach(bs, bs->peer);
+*ptr = NULL;
+break;
+}
 }
 }
 }
-- 
1.7.2.3




[Qemu-devel] [PATCH 0/5] -drive/drive_add fixes

2011-01-17 Thread Markus Armbruster
Note: PATCH 3/5 makes -drive reject duplicate definitions instead of
ignoring all but the first silently.  If this isn't sufficiently
bug-compatible for you, we need to talk.

Markus Armbruster (5):
  blockdev: Fix error message for invalid -drive CHS
  blockdev: Make drive_init() use error_report()
  blockdev: Reject multiple definitions for the same drive
  blockdev: Fix drive_del not to crash when drive is not in use
  blockdev: Fix drive_add for drives without media

 blockdev.c  |   88 --
 blockdev.h  |2 +-
 hw/device-hotplug.c |3 +-
 hw/usb-msd.c|3 +-
 vl.c|6 +--
 5 files changed, 47 insertions(+), 55 deletions(-)

-- 
1.7.2.3




Re: [Qemu-devel] Re: [PATCH v2 0/5] iohandlers: Add support for enabling/disabling individual handlers

2011-01-17 Thread Michael Roth

On 01/17/2011 08:57 AM, Anthony Liguori wrote:

On 01/17/2011 04:18 AM, Amit Shah wrote:

On (Thu) Jan 13 2011 [13:17:22], Anthony Liguori wrote:

On 01/13/2011 09:00 AM, Amit Shah wrote:

Hi,

This patchset adds new interfaces to work with iohandlers. It adds:

int assign_fd_handlers(int fd, IOHandlerOps *ops, void *opaque)
-- Specify io handlers for an fd
int remove_fd_handlers(int fd)
-- Remove fd handlers for fd (mark ioh for deletion)
int set_read_poll_fd_action(int fd, bool enable)
-- Enable or disable the fd_read_poll fd handler
int set_read_fd_action(int fd, bool enable)
-- Enable or disable the fd_read fd handler
int set_write_fd_action(int fd, bool enable)
-- Enable or disable the fd_read fd handler

A new struct, IOHandlerOps, is added, to collect all the ops together
instead of passing individual ones to functions.

Instead of inventing new interfaces, I think we should steal^Wlearn
from established interfaces.

Agreed.

I do also think it'll be worthwhile pulling in one of the libraries to
reduce the amount of qemu-specific code we have in the other cases as
well.


Both libevent and glib have interfaces
that essentially boil down to:

handle add_fd_event(loop, fd, ConditionMask, callback, opaque)
remove_event(loop, handle)

This is quite similar to the Linux polling API.

I don't know what the 'loop' parameter would do, though.


It's to allow for multiple I/O threads. There's one loop context per
thread and you can register events specifically to a thread.



In case you're interested, to make the fd handler stuff accessible to 
qemu tools I have some code that moves these interfaces into backend 
functions in another file, qemu-ioh.c, where the IOHandlerRecord list is 
supplied by the caller to track state.


This would extend naturally to threads by just having them maintain 
their own IOHandlerRecord lists as well, and stuff that is meant to 
interact with vl.c:io_handlers can be done via wrapper functions for 
backward-compatibility.


If that seems like a reasonable approach maybe you could leverage these 
patches remove some of the scope for your proposed changes:


http://repo.or.cz/w/qemu/mdroth.git/patch/56a391e85124382ddcbdb64dcc05aadfc965f000

http://repo.or.cz/w/qemu/mdroth.git/patch/f4428e2cdf5da231bb30ce1ed9eb5ce567a9dc55




[Qemu-devel] [PATCH 1/5] blockdev: Fix error message for invalid -drive CHS

2011-01-17 Thread Markus Armbruster
When cyls, heads or secs are out of range, the error message prints
buf, which points to the value of option "if".  Bogus, may even be
null.  Drop that.

Signed-off-by: Markus Armbruster 
---
 blockdev.c |6 +++---
 1 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/blockdev.c b/blockdev.c
index d7add36..b01a87c 100644
--- a/blockdev.c
+++ b/blockdev.c
@@ -224,15 +224,15 @@ DriveInfo *drive_init(QemuOpts *opts, int 
default_to_scsi, int *fatal_error)
 
 if (cyls || heads || secs) {
 if (cyls < 1 || (type == IF_IDE && cyls > 16383)) {
-fprintf(stderr, "qemu: '%s' invalid physical cyls number\n", buf);
+fprintf(stderr, "qemu: invalid physical cyls number\n");
return NULL;
}
 if (heads < 1 || (type == IF_IDE && heads > 16)) {
-fprintf(stderr, "qemu: '%s' invalid physical heads number\n", buf);
+fprintf(stderr, "qemu: invalid physical heads number\n");
return NULL;
}
 if (secs < 1 || (type == IF_IDE && secs > 63)) {
-fprintf(stderr, "qemu: '%s' invalid physical secs number\n", buf);
+fprintf(stderr, "qemu: invalid physical secs number\n");
return NULL;
}
 }
-- 
1.7.2.3




[Qemu-devel] [PATCH 2/5] blockdev: Make drive_init() use error_report()

2011-01-17 Thread Markus Armbruster
This makes the errors point to the error location, and fixes drive_add
to report errors in the monitor instead of stderr.

While there, tweak a few error messages for consistency.

Signed-off-by: Markus Armbruster 
---
 blockdev.c |   59 ---
 1 files changed, 28 insertions(+), 31 deletions(-)

diff --git a/blockdev.c b/blockdev.c
index b01a87c..127c919 100644
--- a/blockdev.c
+++ b/blockdev.c
@@ -107,7 +107,7 @@ DriveInfo *drive_get_by_blockdev(BlockDriverState *bs)
 
 static void bdrv_format_print(void *opaque, const char *name)
 {
-fprintf(stderr, " %s", name);
+error_printf(" %s", name);
 }
 
 void drive_uninit(DriveInfo *dinfo)
@@ -129,8 +129,8 @@ static int parse_block_error_action(const char *buf, int 
is_read)
 } else if (!strcmp(buf, "report")) {
 return BLOCK_ERR_REPORT;
 } else {
-fprintf(stderr, "qemu: '%s' invalid %s error action\n",
-buf, is_read ? "read" : "write");
+error_report("'%s' invalid %s error action",
+ buf, is_read ? "read" : "write");
 return -1;
 }
 }
@@ -217,31 +217,30 @@ DriveInfo *drive_init(QemuOpts *opts, int 
default_to_scsi, int *fatal_error)
type = IF_NONE;
 max_devs = 0;
} else {
-fprintf(stderr, "qemu: unsupported bus type '%s'\n", buf);
+error_report("unsupported bus type '%s'", buf);
 return NULL;
}
 }
 
 if (cyls || heads || secs) {
 if (cyls < 1 || (type == IF_IDE && cyls > 16383)) {
-fprintf(stderr, "qemu: invalid physical cyls number\n");
+error_report("invalid physical cyls number");
return NULL;
}
 if (heads < 1 || (type == IF_IDE && heads > 16)) {
-fprintf(stderr, "qemu: invalid physical heads number\n");
+error_report("invalid physical heads number");
return NULL;
}
 if (secs < 1 || (type == IF_IDE && secs > 63)) {
-fprintf(stderr, "qemu: invalid physical secs number\n");
+error_report("invalid physical secs number");
return NULL;
}
 }
 
 if ((buf = qemu_opt_get(opts, "trans")) != NULL) {
 if (!cyls) {
-fprintf(stderr,
-"qemu: '%s' trans must be used with cyls,heads and secs\n",
-buf);
+error_report("'%s' trans must be used with cyls,heads and secs",
+ buf);
 return NULL;
 }
 if (!strcmp(buf, "none"))
@@ -251,7 +250,7 @@ DriveInfo *drive_init(QemuOpts *opts, int default_to_scsi, 
int *fatal_error)
 else if (!strcmp(buf, "auto"))
 translation = BIOS_ATA_TRANSLATION_AUTO;
else {
-fprintf(stderr, "qemu: '%s' invalid translation type\n", buf);
+error_report("'%s' invalid translation type", buf);
return NULL;
}
 }
@@ -261,13 +260,12 @@ DriveInfo *drive_init(QemuOpts *opts, int 
default_to_scsi, int *fatal_error)
media = MEDIA_DISK;
} else if (!strcmp(buf, "cdrom")) {
 if (cyls || secs || heads) {
-fprintf(stderr,
-"qemu: '%s' invalid physical CHS format\n", buf);
+error_report("'%s' invalid physical CHS format", buf);
return NULL;
 }
media = MEDIA_CDROM;
} else {
-   fprintf(stderr, "qemu: '%s' invalid media\n", buf);
+   error_report("'%s' invalid media", buf);
return NULL;
}
 }
@@ -283,7 +281,7 @@ DriveInfo *drive_init(QemuOpts *opts, int default_to_scsi, 
int *fatal_error)
 } else if (!strcmp(buf, "writethrough")) {
 /* this is the default */
 } else {
-   fprintf(stderr, "qemu: invalid cache option\n");
+   error_report("invalid cache option");
return NULL;
 }
 }
@@ -295,7 +293,7 @@ DriveInfo *drive_init(QemuOpts *opts, int default_to_scsi, 
int *fatal_error)
 } else if (!strcmp(buf, "threads")) {
 /* this is the default */
 } else {
-   fprintf(stderr, "qemu: invalid aio option\n");
+   error_report("invalid aio option");
return NULL;
 }
 }
@@ -303,14 +301,14 @@ DriveInfo *drive_init(QemuOpts *opts, int 
default_to_scsi, int *fatal_error)
 
 if ((buf = qemu_opt_get(opts, "format")) != NULL) {
if (strcmp(buf, "?") == 0) {
-fprintf(stderr, "qemu: Supported formats:");
-bdrv_iterate_format(bdrv_format_print, NULL);
-fprintf(stderr, "\n");
-   return NULL;
+   error_printf("Supported formats:");
+   bdrv_iterate_format(bdrv_format_print, NULL);
+   error_printf("\n");
+   return NULL;
 }
 drv = bdrv_find_whitelisted_format(buf);
 if (!drv) {
-fprintf(stderr, "

[Qemu-devel] [PATCH 5/5] blockdev: Fix drive_add for drives without media

2011-01-17 Thread Markus Armbruster
Watch this:

(qemu) drive_add 0 if=none
(qemu) info block
none0: type=hd removable=0 [not inserted]
(qemu) drive_del none0
Segmentation fault (core dumped)

add_init_drive() is confused about drive_init()'s failure modes, and
cleans up when it shouldn't.  This leaves the DriveInfo with member
opts dangling.  drive_del attempts to free it, and dies.

drive_init() behaves as follows:

* If it created a drive with media, it returns its DriveInfo.

* If it created a drive without media, it clears *fatal_error and
  returns NULL.

* If it couldn't create a drive, it sets *fatal_error and returns
  NULL.

Of its three callers:

* drive_init_func() is correct.

* usb_msd_init() assumes drive_init() failed when it returns NULL.
  This is correct only because it always passes option "file", and
  "drive without media" can't happen then.

* add_init_drive() assumes drive_init() failed when it returns NULL.
  This is incorrect.

Clean up drive_init() to return NULL on failure and only on failure.
Drop its parameter fatal_error.

Signed-off-by: Markus Armbruster 
---
 blockdev.c  |8 ++--
 blockdev.h  |2 +-
 hw/device-hotplug.c |3 +--
 hw/usb-msd.c|3 +--
 vl.c|6 ++
 5 files changed, 7 insertions(+), 15 deletions(-)

diff --git a/blockdev.c b/blockdev.c
index 51a2da3..8a74bf3 100644
--- a/blockdev.c
+++ b/blockdev.c
@@ -135,7 +135,7 @@ static int parse_block_error_action(const char *buf, int 
is_read)
 }
 }
 
-DriveInfo *drive_init(QemuOpts *opts, int default_to_scsi, int *fatal_error)
+DriveInfo *drive_init(QemuOpts *opts, int default_to_scsi)
 {
 const char *buf;
 const char *file = NULL;
@@ -157,8 +157,6 @@ DriveInfo *drive_init(QemuOpts *opts, int default_to_scsi, 
int *fatal_error)
 int snapshot = 0;
 int ret;
 
-*fatal_error = 1;
-
 translation = BIOS_ATA_TRANSLATION_AUTO;
 
 if (default_to_scsi) {
@@ -463,8 +461,7 @@ DriveInfo *drive_init(QemuOpts *opts, int default_to_scsi, 
int *fatal_error)
 abort();
 }
 if (!file || !*file) {
-*fatal_error = 0;
-return NULL;
+return dinfo;
 }
 if (snapshot) {
 /* always use cache=unsafe with snapshot */
@@ -493,7 +490,6 @@ DriveInfo *drive_init(QemuOpts *opts, int default_to_scsi, 
int *fatal_error)
 
 if (bdrv_key_required(dinfo->bdrv))
 autostart = 0;
-*fatal_error = 0;
 return dinfo;
 }
 
diff --git a/blockdev.h b/blockdev.h
index 4536b5c..38ee5d2 100644
--- a/blockdev.h
+++ b/blockdev.h
@@ -40,7 +40,7 @@ void drive_uninit(DriveInfo *dinfo);
 DriveInfo *drive_get_by_blockdev(BlockDriverState *bs);
 
 QemuOpts *drive_add(const char *file, const char *fmt, ...) GCC_FMT_ATTR(2, 3);
-DriveInfo *drive_init(QemuOpts *arg, int default_to_scsi, int *fatal_error);
+DriveInfo *drive_init(QemuOpts *arg, int default_to_scsi);
 
 /* device-hotplug */
 
diff --git a/hw/device-hotplug.c b/hw/device-hotplug.c
index 9704e2f..c310cb8 100644
--- a/hw/device-hotplug.c
+++ b/hw/device-hotplug.c
@@ -29,7 +29,6 @@
 
 DriveInfo *add_init_drive(const char *optstr)
 {
-int fatal_error;
 DriveInfo *dinfo;
 QemuOpts *opts;
 
@@ -37,7 +36,7 @@ DriveInfo *add_init_drive(const char *optstr)
 if (!opts)
 return NULL;
 
-dinfo = drive_init(opts, current_machine->use_scsi, &fatal_error);
+dinfo = drive_init(opts, current_machine->use_scsi);
 if (!dinfo) {
 qemu_opts_del(opts);
 return NULL;
diff --git a/hw/usb-msd.c b/hw/usb-msd.c
index 0a95d8d..00f64b0 100644
--- a/hw/usb-msd.c
+++ b/hw/usb-msd.c
@@ -570,7 +570,6 @@ static USBDevice *usb_msd_init(const char *filename)
 QemuOpts *opts;
 DriveInfo *dinfo;
 USBDevice *dev;
-int fatal_error;
 const char *p1;
 char fmt[32];
 
@@ -600,7 +599,7 @@ static USBDevice *usb_msd_init(const char *filename)
 qemu_opt_set(opts, "if", "none");
 
 /* create host drive */
-dinfo = drive_init(opts, 0, &fatal_error);
+dinfo = drive_init(opts, 0);
 if (!dinfo) {
 qemu_opts_del(opts);
 return NULL;
diff --git a/vl.c b/vl.c
index 0292184..5ffa12b 100644
--- a/vl.c
+++ b/vl.c
@@ -631,11 +631,9 @@ static int bt_parse(const char *opt)
 static int drive_init_func(QemuOpts *opts, void *opaque)
 {
 int *use_scsi = opaque;
-int fatal_error = 0;
 
-if (drive_init(opts, *use_scsi, &fatal_error) == NULL) {
-if (fatal_error)
-return 1;
+if (drive_init(opts, *use_scsi) == NULL) {
+return 1;
 }
 return 0;
 }
-- 
1.7.2.3




[Qemu-devel] [PATCH 3/5] blockdev: Reject multiple definitions for the same drive

2011-01-17 Thread Markus Armbruster
For reasons lost in the mist of time, we silently ignore multiple
definitions for the same drive:

$ qemu-system-x86_64 -nodefaults -vnc :1 -S -monitor stdio -drive 
if=ide,index=1,file=tmp.qcow2 -drive if=ide,index=1,file=nonexistant
QEMU 0.13.50 monitor - type 'help' for more information
(qemu) info block
ide0-hd1: type=hd removable=0 file=tmp.qcow2 backing_file=tmp.img ro=0 
drv=qcow2 encrypted=0

With if=none, this can become quite confusing:

$ qemu-system-x86_64 -nodefaults -vnc :1 -S -monitor stdio -drive 
if=none,index=1,file=tmp.qcow2,id=eins -drive 
if=none,index=1,file=nonexistant,id=zwei -device ide-drive,drive=eins -device 
ide-drive,drive=zwei
qemu-system-x86_64: -device ide-drive,drive=zwei: Property 
'ide-drive.drive' can't find value 'zwei'

The second -device fails, because it refers to drive zwei, which got
silently ignored.

Make multiple drive definitions fail cleanly.

Signed-off-by: Markus Armbruster 
---
 blockdev.c |5 +++--
 1 files changed, 3 insertions(+), 2 deletions(-)

diff --git a/blockdev.c b/blockdev.c
index 127c919..04a0e84 100644
--- a/blockdev.c
+++ b/blockdev.c
@@ -387,11 +387,12 @@ DriveInfo *drive_init(QemuOpts *opts, int 
default_to_scsi, int *fatal_error)
 }
 
 /*
- * ignore multiple definitions
+ * catch multiple definitions
  */
 
 if (drive_get(type, bus_id, unit_id) != NULL) {
-*fatal_error = 0;
+error_report("drive with bus=%d, unit=%d (index=%d) exists",
+ bus_id, unit_id, index);
 return NULL;
 }
 
-- 
1.7.2.3




[Qemu-devel] Error running qemu on powerpc

2011-01-17 Thread Dushyant Bansal

Hi,
I have installed qemu on x86 system. I downloaded debian-powerpc image 
from http://people.debian.org/~aurel32/qemu/powerpc/ and used it with 
"qemu-system-ppc".

This is the cpuinfo of the guest os (debian-507-powerpc (2.6.26-1-powerpc) )

processor: 0
cpu: 740/750
temperature : 62-64 C (uncalibrated)
clock: 1000.00MHz
revision: 3.1 (pvr 0008 0301)
bogomips: 33.02
timebase: 16600733
platform: PowerMac
model: Power Macintosh
machine: Power Macintosh
motherboard: AAPL,PowerMac G3 MacRISC
detected as: 49 (PowerMac G3 (Silk))
pmac flags: 
pmac-generation: OldWorld

Now, I installed qemu on that guest os , and tried to run the same 
debian-powerpc image using "qemu-system-ppc -nographic" on it. After 
giving some messages about building device tree strings and structure, 
the boot process got stuck at:


"Calling quiesce
Returning from prom init"


Thanks,
Dushyant




[Qemu-devel] KVM call agenda for Jan 18

2011-01-17 Thread Chris Wright
Please send in any agenda items you are interested in covering.

thanks,
-chris



[Qemu-devel] Re: [PATCH v2 3/3] checkpatch: adjust to QEMUisms

2011-01-17 Thread Blue Swirl
On Mon, Jan 17, 2011 at 7:40 AM, Paolo Bonzini  wrote:
> On 01/15/2011 06:45 PM, Blue Swirl wrote:
>>
>> +                       if ($level == 0 && !$block =~ /^\s*\{/ &&
>> !$allowed) {
>
> I'm not a Perl expert at all, but I think you need parentheses for the
> argument of "!":

! has higher precedence than =~:
http://perldoc.perl.org/perlop.html#Operator-Precedence-and-Associativity

>  if ($level == 0 && !($block =~ /^\s*\{/) && !$allowed) {

Maybe instead:
if ($level == 0 && $block !~ /^\s*\{/ && !$allowed) {



Re: [Qemu-devel] [PATCH v2 1/6] Emulation of GRLIB GPTimer as defined in GRLIB IP Core User's Manual.

2011-01-17 Thread Blue Swirl
On Mon, Jan 17, 2011 at 11:43 AM, Fabien Chouteau  wrote:
> On 01/04/2011 07:46 PM, Blue Swirl wrote:
>>
>> On Mon, Jan 3, 2011 at 2:07 PM, Fabien Chouteau
>>  wrote:+}
>>>
>>> +static uint32_t grlib_gptimer_readl(void *opaque, target_phys_addr_t
>>> addr)
>>> +{
>>> +    GPTimerUnit *unit  = opaque;
>>> +    uint32_t     value = 0;
>>> +
>>> +    addr&= 0xff;
>>
>> Not needed.
>>
>
> When io-memory starts at 0x8000300 and its size is 48 bytes, Qemu gives me
> address like this one (for example):
>
> 0x320

Sorry, I was confused. This part is OK (except for the spacing).



Re: [Qemu-devel] [PATCH 1/2] strtosz() use unsigned char as isspace() is not defined for signed char

2011-01-17 Thread Blue Swirl
On Mon, Jan 17, 2011 at 3:14 PM,   wrote:
> From: Jes Sorensen 

This is exactly why we have qemu_isspace().



  1   2   >