All of lore.kernel.org
 help / color / mirror / Atom feed
From: Michael Roth <mdroth@linux.vnet.ibm.com>
To: marcandre.lureau@redhat.com, peter.maydell@linaro.org
Cc: "Cam Macdonell" <cam@cs.ualberta.ca>,
	qemu-devel@nongnu.org, "Andreas Färber" <afaerber@suse.de>
Subject: Re: [Qemu-devel] [PULL 41/48] tests: add ivshmem qtest
Date: Sat, 10 Oct 2015 16:29:00 -0500	[thread overview]
Message-ID: <20151010212900.22227.62062@loki> (raw)
In-Reply-To: <1444159184-18153-42-git-send-email-marcandre.lureau@redhat.com>

Quoting marcandre.lureau@redhat.com (2015-10-06 14:19:37)
> From: Marc-André Lureau <marcandre.lureau@redhat.com>
> 
> Adds 4 ivshmemtests:
> - single qemu instance and basic IO
> - pair of instances, check memory sharing
> - pair of instances with server, and MSIX
> - hot plug/unplug
> 
> A temporary shm is created as well as a directory to place server
> socket, both should be clear on exit and abort.
> 
> Cc: Cam Macdonell <cam@cs.ualberta.ca>
> CC: Andreas Färber <afaerber@suse.de>
> Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
> Reviewed-by: Claudio Fontana <claudio.fontana@huawei.com>
> ---
>  tests/Makefile       |   3 +
>  tests/ivshmem-test.c | 484 +++++++++++++++++++++++++++++++++++++++++++++++++++
>  2 files changed, 487 insertions(+)
>  create mode 100644 tests/ivshmem-test.c
> 
> diff --git a/tests/Makefile b/tests/Makefile
> index e6474ba..4f78ea4 100644
> --- a/tests/Makefile
> +++ b/tests/Makefile
> @@ -146,6 +146,8 @@ gcov-files-pci-y += hw/display/virtio-gpu-pci.c
>  gcov-files-pci-$(CONFIG_VIRTIO_VGA) += hw/display/virtio-vga.c
>  check-qtest-pci-y += tests/intel-hda-test$(EXESUF)
>  gcov-files-pci-y += hw/audio/intel-hda.c hw/audio/hda-codec.c
> +check-qtest-pci-$(CONFIG_LINUX) += tests/ivshmem-test$(EXESUF)
> +gcov-files-pci-y += hw/misc/ivshmem.c
> 
>  check-qtest-i386-y = tests/endianness-test$(EXESUF)
>  check-qtest-i386-y += tests/fdc-test$(EXESUF)
> @@ -437,6 +439,7 @@ tests/vhost-user-test$(EXESUF): tests/vhost-user-test.o qemu-char.o qemu-timer.o
>  tests/qemu-iotests/socket_scm_helper$(EXESUF): tests/qemu-iotests/socket_scm_helper.o
>  tests/test-qemu-opts$(EXESUF): tests/test-qemu-opts.o $(test-util-obj-y)
>  tests/test-write-threshold$(EXESUF): tests/test-write-threshold.o $(test-block-obj-y)
> +tests/ivshmem-test$(EXESUF): tests/ivshmem-test.o contrib/ivshmem-server/ivshmem-server.o $(libqos-pc-obj-y)
> 
>  ifeq ($(CONFIG_POSIX),y)
>  LIBS += -lutil
> diff --git a/tests/ivshmem-test.c b/tests/ivshmem-test.c
> new file mode 100644
> index 0000000..f872592
> --- /dev/null
> +++ b/tests/ivshmem-test.c
> @@ -0,0 +1,484 @@
> +/*
> + * QTest testcase for ivshmem
> + *
> + * Copyright (c) 2015 Red Hat, Inc.
> + *
> + * 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 <errno.h>
> +#include <fcntl.h>
> +#include <glib.h>
> +#include <glib/gstdio.h>
> +#include <string.h>
> +#include <sys/mman.h>
> +#include <unistd.h>
> +#include "contrib/ivshmem-server/ivshmem-server.h"
> +#include "libqos/pci-pc.h"
> +#include "libqtest.h"
> +#include "qemu/osdep.h"
> +#include "qemu-common.h"
> +
> +#if GLIB_CHECK_VERSION(2, 32, 0)
> +#define HAVE_THREAD_NEW
> +#endif
> +
> +#define TMPSHMSIZE (1 << 20)
> +static char *tmpshm;
> +static void *tmpshmem;
> +static char *tmpdir;
> +static char *tmpserver;
> +
> +static void save_fn(QPCIDevice *dev, int devfn, void *data)
> +{
> +    QPCIDevice **pdev = (QPCIDevice **) data;
> +
> +    *pdev = dev;
> +}
> +
> +static QPCIDevice *get_device(void)
> +{
> +    QPCIDevice *dev;
> +    QPCIBus *pcibus;
> +
> +    pcibus = qpci_init_pc();
> +    qpci_device_foreach(pcibus, 0x1af4, 0x1110, save_fn, &dev);
> +    g_assert(dev != NULL);
> +
> +    return dev;
> +}
> +
> +typedef struct _IVState {
> +    QTestState *qtest;
> +    void *reg_base, *mem_base;
> +    QPCIDevice *dev;
> +} IVState;
> +
> +enum Reg {
> +    INTRMASK = 0,
> +    INTRSTATUS = 4,
> +    IVPOSITION = 8,
> +    DOORBELL = 12,
> +};
> +
> +static const char* reg2str(enum Reg reg) {
> +    switch (reg) {
> +    case INTRMASK:
> +        return "IntrMask";
> +    case INTRSTATUS:
> +        return "IntrStatus";
> +    case IVPOSITION:
> +        return "IVPosition";
> +    case DOORBELL:
> +        return "DoorBell";
> +    default:
> +        return NULL;
> +    }
> +}
> +
> +static inline unsigned in_reg(IVState *s, enum Reg reg)
> +{
> +    const char *name = reg2str(reg);
> +    QTestState *qtest = global_qtest;
> +    unsigned res;
> +
> +    global_qtest = s->qtest;
> +    res = qpci_io_readl(s->dev, s->reg_base + reg);
> +    g_test_message("*%s -> %x\n", name, res);
> +    global_qtest = qtest;
> +
> +    return res;
> +}
> +
> +static inline void out_reg(IVState *s, enum Reg reg, unsigned v)
> +{
> +    const char *name = reg2str(reg);
> +    QTestState *qtest = global_qtest;
> +
> +    global_qtest = s->qtest;
> +    g_test_message("%x -> *%s\n", v, name);
> +    qpci_io_writel(s->dev, s->reg_base + reg, v);
> +    global_qtest = qtest;
> +}
> +
> +static void setup_vm_cmd(IVState *s, const char *cmd, bool msix)
> +{
> +    uint64_t barsize;
> +
> +    s->qtest = qtest_start(cmd);
> +
> +    s->dev = get_device();
> +
> +    /* FIXME: other bar order fails, mappings changes */
> +    s->mem_base = qpci_iomap(s->dev, 2, &barsize);
> +    g_assert_nonnull(s->mem_base);
> +    g_assert_cmpuint(barsize, ==, TMPSHMSIZE);
> +
> +    if (msix) {
> +        qpci_msix_enable(s->dev);
> +    }
> +
> +    s->reg_base = qpci_iomap(s->dev, 0, &barsize);
> +    g_assert_nonnull(s->reg_base);
> +    g_assert_cmpuint(barsize, ==, 256);
> +
> +    qpci_device_enable(s->dev);
> +}
> +
> +static void setup_vm(IVState *s)
> +{
> +    char *cmd = g_strdup_printf("-device ivshmem,shm=%s,size=1M", tmpshm);
> +
> +    setup_vm_cmd(s, cmd, false);
> +
> +    g_free(cmd);
> +}
> +
> +static void test_ivshmem_single(void)
> +{
> +    IVState state, *s;
> +    uint32_t data[1024];
> +    int i;
> +
> +    setup_vm(&state);
> +    s = &state;
> +
> +    /* valid io */
> +    out_reg(s, INTRMASK, 0);
> +    in_reg(s, INTRSTATUS);
> +    in_reg(s, IVPOSITION);
> +
> +    out_reg(s, INTRMASK, 0xffffffff);
> +    g_assert_cmpuint(in_reg(s, INTRMASK), ==, 0xffffffff);
> +    out_reg(s, INTRSTATUS, 1);
> +    /* XXX: intercept IRQ, not seen in resp */
> +    g_assert_cmpuint(in_reg(s, INTRSTATUS), ==, 1);
> +
> +    /* invalid io */
> +    out_reg(s, IVPOSITION, 1);
> +    out_reg(s, DOORBELL, 8 << 16);
> +
> +    for (i = 0; i < G_N_ELEMENTS(data); i++) {
> +        data[i] = i;
> +    }
> +    qtest_memwrite(s->qtest, (uintptr_t)s->mem_base, data, sizeof(data));
> +
> +    for (i = 0; i < G_N_ELEMENTS(data); i++) {
> +        g_assert_cmpuint(((uint32_t *)tmpshmem)[i], ==, i);
> +    }
> +
> +    memset(data, 0, sizeof(data));
> +
> +    qtest_memread(s->qtest, (uintptr_t)s->mem_base, data, sizeof(data));
> +    for (i = 0; i < G_N_ELEMENTS(data); i++) {
> +        g_assert_cmpuint(data[i], ==, i);
> +    }
> +
> +    qtest_quit(s->qtest);
> +}
> +
> +static void test_ivshmem_pair(void)
> +{
> +    IVState state1, state2, *s1, *s2;
> +    char *data;
> +    int i;
> +
> +    setup_vm(&state1);
> +    s1 = &state1;
> +    setup_vm(&state2);
> +    s2 = &state2;
> +
> +    data = g_malloc0(TMPSHMSIZE);
> +
> +    /* host write, guest 1 & 2 read */
> +    memset(tmpshmem, 0x42, TMPSHMSIZE);
> +    qtest_memread(s1->qtest, (uintptr_t)s1->mem_base, data, TMPSHMSIZE);
> +    for (i = 0; i < TMPSHMSIZE; i++) {
> +        g_assert_cmpuint(data[i], ==, 0x42);
> +    }
> +    qtest_memread(s2->qtest, (uintptr_t)s2->mem_base, data, TMPSHMSIZE);
> +    for (i = 0; i < TMPSHMSIZE; i++) {
> +        g_assert_cmpuint(data[i], ==, 0x42);
> +    }
> +
> +    /* guest 1 write, guest 2 read */
> +    memset(data, 0x43, TMPSHMSIZE);
> +    qtest_memwrite(s1->qtest, (uintptr_t)s1->mem_base, data, TMPSHMSIZE);
> +    memset(data, 0, TMPSHMSIZE);
> +    qtest_memread(s2->qtest, (uintptr_t)s2->mem_base, data, TMPSHMSIZE);
> +    for (i = 0; i < TMPSHMSIZE; i++) {
> +        g_assert_cmpuint(data[i], ==, 0x43);
> +    }
> +
> +    /* guest 2 write, guest 1 read */
> +    memset(data, 0x44, TMPSHMSIZE);
> +    qtest_memwrite(s2->qtest, (uintptr_t)s2->mem_base, data, TMPSHMSIZE);
> +    memset(data, 0, TMPSHMSIZE);
> +    qtest_memread(s1->qtest, (uintptr_t)s2->mem_base, data, TMPSHMSIZE);
> +    for (i = 0; i < TMPSHMSIZE; i++) {
> +        g_assert_cmpuint(data[i], ==, 0x44);
> +    }
> +
> +    qtest_quit(s1->qtest);
> +    qtest_quit(s2->qtest);
> +    g_free(data);
> +}
> +
> +typedef struct ServerThread {
> +    GThread *thread;
> +    IvshmemServer *server;
> +    int pipe[2]; /* to handle quit */
> +} ServerThread;
> +
> +static void *server_thread(void *data)
> +{
> +    ServerThread *t = data;
> +    IvshmemServer *server = t->server;
> +
> +    while (true) {
> +        fd_set fds;
> +        int maxfd, ret;
> +
> +        FD_ZERO(&fds);
> +        FD_SET(t->pipe[0], &fds);
> +        maxfd = t->pipe[0] + 1;
> +
> +        ivshmem_server_get_fds(server, &fds, &maxfd);
> +
> +        ret = select(maxfd, &fds, NULL, NULL, NULL);
> +
> +        if (ret < 0) {
> +            if (errno == EINTR) {
> +                continue;
> +            }
> +
> +            g_critical("select error: %s\n", strerror(errno));
> +            break;
> +        }
> +        if (ret == 0) {
> +            continue;
> +        }
> +
> +        if (FD_ISSET(t->pipe[0], &fds)) {
> +            break;
> +        }
> +
> +        if (ivshmem_server_handle_fds(server, &fds, maxfd) < 0) {
> +            g_critical("ivshmem_server_handle_fds() failed\n");
> +            break;
> +        }
> +    }
> +
> +    return NULL;
> +}
> +
> +static void setup_vm_with_server(IVState *s, int nvectors)
> +{
> +    char *cmd = g_strdup_printf("-chardev socket,id=chr0,path=%s,nowait "
> +                                "-device ivshmem,size=1M,chardev=chr0,vectors=%d",
> +                                tmpserver, nvectors);
> +
> +    setup_vm_cmd(s, cmd, true);
> +
> +    g_free(cmd);
> +}
> +
> +static GThread *thread_new(const gchar *name, GThreadFunc func, gpointer data)
> +{
> +    GThread *thread = NULL;
> +    GError *error = NULL;
> +#ifdef HAVE_THREAD_NEW
> +    thread = g_thread_try_new(name, func, data, &error);
> +#else
> +    thread = g_thread_create(func, data, TRUE, &error);
> +#endif
> +    g_assert_no_error(error);
> +    return thread;
> +}
> +
> +static void test_ivshmem_server(void)
> +{
> +    IVState state1, state2, *s1, *s2;
> +    ServerThread thread;
> +    IvshmemServer server;
> +    int ret, vm1, vm2;
> +    int nvectors = 2;
> +
> +    memset(tmpshmem, 0x42, TMPSHMSIZE);
> +    ret = ivshmem_server_init(&server, tmpserver, tmpshm,
> +                              TMPSHMSIZE, nvectors,
> +                              getenv("QTEST_LOG") != NULL);
> +    g_assert_cmpint(ret, ==, 0);
> +
> +    ret = ivshmem_server_start(&server);
> +    g_assert_cmpint(ret, ==, 0);
> +
> +    setup_vm_with_server(&state1, nvectors);
> +    s1 = &state1;
> +    setup_vm_with_server(&state2, nvectors);
> +    s2 = &state2;
> +
> +    g_assert_cmpuint(in_reg(s1, IVPOSITION), ==, 0xffffffff);
> +    g_assert_cmpuint(in_reg(s2, IVPOSITION), ==, 0xffffffff);
> +
> +    g_assert_cmpuint(qtest_readb(s1->qtest, (uintptr_t)s1->mem_base), ==, 0x00);
> +
> +    thread.server = &server;
> +    ret = pipe(thread.pipe);
> +    g_assert_cmpint(ret, ==, 0);
> +    thread.thread = thread_new("ivshmem-server", server_thread, &thread);
> +
> +    /* waiting until mapping is done */
> +    while (true) {
> +        g_usleep(1000);
> +
> +        if (qtest_readb(s1->qtest, (uintptr_t)s1->mem_base) == 0x42 &&
> +            qtest_readb(s2->qtest, (uintptr_t)s2->mem_base) == 0x42) {
> +            break;
> +        }
> +    }
> +
> +    /* check got different VM ids */
> +    vm1 = in_reg(s1, IVPOSITION);
> +    vm2 = in_reg(s2, IVPOSITION);
> +    g_assert_cmpuint(vm1, !=, vm2);
> +
> +    global_qtest = s1->qtest;
> +    ret = qpci_msix_table_size(s1->dev);
> +    g_assert_cmpuint(ret, ==, nvectors);
> +
> +    /* ping vm2 -> vm1 */
> +    ret = qpci_msix_pending(s1->dev, 0);
> +    g_assert_cmpuint(ret, ==, 0);
> +    out_reg(s2, DOORBELL, vm1 << 16);
> +    g_usleep(10000);
> +    ret = qpci_msix_pending(s1->dev, 0);
> +    g_assert_cmpuint(ret, !=, 0);
> +
> +    /* ping vm1 -> vm2 */
> +    global_qtest = s2->qtest;
> +    ret = qpci_msix_pending(s2->dev, 0);
> +    g_assert_cmpuint(ret, ==, 0);
> +    out_reg(s1, DOORBELL, vm2 << 16);
> +    g_usleep(10000);
> +    ret = qpci_msix_pending(s2->dev, 0);
> +    g_assert_cmpuint(ret, !=, 0);
> +
> +    /* remove vm2 */
> +    qtest_quit(s2->qtest);
> +    /* XXX wait enough time for vm1 to be notified */
> +    g_usleep(1000);
> +
> +    qtest_quit(s1->qtest);
> +
> +    if (qemu_write_full(thread.pipe[1], "q", 1) != 1) {
> +        g_error("qemu_write_full: %s", g_strerror(errno));
> +    }
> +
> +    g_thread_join(thread.thread);
> +
> +    ivshmem_server_close(&server);
> +    close(thread.pipe[1]);
> +    close(thread.pipe[0]);
> +}
> +
> +#define PCI_SLOT_HP             0x06
> +
> +static void test_ivshmem_hotplug(void)
> +{
> +    gchar *opts;
> +
> +    qtest_start("");
> +
> +    opts = g_strdup_printf("'shm': '%s', 'size': '1M'", tmpshm);
> +
> +    qpci_plug_device_test("ivshmem", "iv1", PCI_SLOT_HP, opts);
> +    qpci_unplug_acpi_device_test("iv1", PCI_SLOT_HP);
> +
> +    qtest_end();
> +    g_free(opts);
> +}
> +
> +static void cleanup(void)
> +{
> +    if (tmpshmem) {
> +        munmap(tmpshmem, TMPSHMSIZE);
> +        tmpshmem = NULL;
> +    }
> +
> +    if (tmpshm) {
> +        shm_unlink(tmpshm);
> +        g_free(tmpshm);
> +        tmpshm = NULL;
> +    }
> +
> +    if (tmpserver) {
> +        g_unlink(tmpserver);
> +        g_free(tmpserver);
> +        tmpserver = NULL;
> +    }
> +
> +    if (tmpdir) {
> +        g_rmdir(tmpdir);
> +        tmpdir = NULL;
> +    }
> +}
> +
> +static void abrt_handler(void *data)
> +{
> +    cleanup();
> +}
> +
> +static gchar *mktempshm(int size, int *fd)
> +{
> +    while (true) {
> +        gchar *name;
> +
> +        name = g_strdup_printf("/qtest-%u-%u", getpid(), g_random_int());
> +        *fd = shm_open(name, O_CREAT|O_RDWR|O_EXCL,
> +                       S_IRWXU|S_IRWXG|S_IRWXO);
> +        if (*fd > 0) {
> +            g_assert(ftruncate(*fd, size) == 0);
> +            return name;
> +        }
> +
> +        g_free(name);
> +    }
> +}
> +
> +int main(int argc, char **argv)
> +{
> +    int ret, fd;
> +    static gchar dir[] = "/tmp/ivshmem-test.XXXXXX";
> +
> +#if !GLIB_CHECK_VERSION(2, 31, 0)
> +    if (!g_thread_supported()) {
> +        g_thread_init(NULL);
> +    }
> +#endif
> +
> +    g_test_init(&argc, &argv, NULL);
> +
> +    qtest_add_abrt_handler(abrt_handler, NULL);
> +    /* shm */
> +    tmpshm = mktempshm(TMPSHMSIZE, &fd);
> +    tmpshmem = mmap(0, TMPSHMSIZE, PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0);
> +    g_assert(tmpshmem != MAP_FAILED);
> +    /* server */
> +    if (g_mkdtemp_full(dir, 0700) == NULL) {

Noticed this while processing tests/test-qga.c series: g_mkdtemp*() are
glib 2.30 and newer so we need something for 2.22 compat. Since it's a
linux-only test, mkdtemp()+chmod() should probably cut it. For qga
series one I'll fix it up in my tree.

I tried to scan for other instances in this series, it looks like you
might have issue with g_thread_try_new() (glib 2.32, but we have compat
definitions for g_thread_new() at least).

Others glib functions look okay, from what I can tell.

> +        g_error("g_mkdtemp_full: %s", g_strerror(errno));
> +    }
> +    tmpdir = dir;
> +    tmpserver = g_strconcat(tmpdir, "/server", NULL);
> +
> +    qtest_add_func("/ivshmem/single", test_ivshmem_single);
> +    qtest_add_func("/ivshmem/pair", test_ivshmem_pair);
> +    qtest_add_func("/ivshmem/server", test_ivshmem_server);
> +    qtest_add_func("/ivshmem/hotplug", test_ivshmem_hotplug);
> +
> +    ret = g_test_run();
> +
> +    cleanup();
> +    return ret;
> +}
> -- 
> 2.4.3
> 
> 

  reply	other threads:[~2015-10-10 21:29 UTC|newest]

Thread overview: 72+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2015-10-06 19:18 [Qemu-devel] [PULL 00/48] ivshmem series marcandre.lureau
2015-10-06 19:18 ` [Qemu-devel] [PULL 01/48] char: add qemu_chr_free() marcandre.lureau
2015-10-06 19:18 ` [Qemu-devel] [PULL 02/48] msix: add VMSTATE_MSIX_TEST marcandre.lureau
2015-10-06 19:18 ` [Qemu-devel] [PULL 03/48] ivhsmem: read do not accept more than sizeof(long) marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 04/48] ivshmem: fix number of bytes to push to fifo marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 05/48] ivshmem: factor out the incoming fifo handling marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 06/48] ivshmem: remove unnecessary dup() marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 07/48] ivshmem: remove superflous ivshmem_attr field marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 08/48] ivshmem: remove useless doorbell field marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 09/48] ivshmem: more qdev conversion marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 10/48] ivshmem: remove last exit(1) marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 11/48] ivshmem: limit maximum number of peers to G_MAXUINT16 marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 12/48] ivshmem: simplify around increase_dynamic_storage() marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 13/48] ivshmem: allocate eventfds in resize_peers() marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 14/48] ivshmem: remove useless ivshmem_update_irq() val argument marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 15/48] ivshmem: initialize max_peer to -1 marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 16/48] ivshmem: remove max_peer field marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 17/48] ivshmem: improve debug messages marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 18/48] ivshmem: improve error handling marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 19/48] ivshmem: print error on invalid peer id marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 20/48] ivshmem: simplify a bit the code marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 21/48] ivshmem: use common return marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 22/48] ivshmem: use common is_power_of_2() marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 23/48] ivshmem: migrate with VMStateDescription marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 24/48] ivshmem: shmfd can be 0 marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 25/48] ivshmem: check shm isn't already initialized marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 26/48] ivshmem: add device description marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 27/48] ivshmem: fix pci_ivshmem_exit() marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 28/48] ivshmem: replace 'guest' for 'peer' appropriately marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 29/48] ivshmem: error on too many eventfd received marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 30/48] ivshmem: reset mask on device reset marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 31/48] contrib: add ivshmem client and server marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 32/48] ivshmem-client: check the number of vectors marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 33/48] ivshmem-server: use a uint16 for client ID marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 34/48] ivshmem-server: fix hugetlbfs support marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 35/48] docs: update ivshmem device spec marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 36/48] ivshmem: add check on protocol version in QEMU marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 37/48] contrib: remove unnecessary strdup() marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 38/48] msix: implement pba write (but read-only) marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 39/48] qtest: add qtest_add_abrt_handler() marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 40/48] glib-compat: add 2.38/2.40/2.46 asserts marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 41/48] tests: add ivshmem qtest marcandre.lureau
2015-10-10 21:29   ` Michael Roth [this message]
2015-10-12 13:53     ` Marc-André Lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 42/48] ivshmem: do not keep shm_fd open marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 43/48] ivshmem: use qemu_strtosz() marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 44/48] ivshmem: add hostmem backend marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 45/48] ivshmem: remove EventfdEntry.vector marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 46/48] ivshmem: rename MSI eventfd_table marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 47/48] ivshmem: use kvm irqfd for msi notifications marcandre.lureau
2015-10-06 19:19 ` [Qemu-devel] [PULL 48/48] ivshmem: use little-endian int64_t for the protocol marcandre.lureau
2015-10-07 12:11 ` [Qemu-devel] [PULL 00/48] ivshmem series Andreas Färber
2015-10-07 12:16   ` Marc-André Lureau
2015-10-07 12:31     ` Andreas Färber
2015-10-07 12:44       ` Marc-André Lureau
2015-10-10 22:18         ` [Qemu-devel] [PATCH 1/2] tests: Add ivshmem qtest Andreas Färber
2015-10-10 22:18           ` [Qemu-devel] [PATCH 2/2] ivshmem-test: Implement tests Andreas Färber
2015-10-10 22:28             ` Andreas Färber
2015-10-10 23:10           ` [Qemu-devel] [PATCH 1/2] tests: Add ivshmem qtest Marc-André Lureau
2015-10-07 22:24       ` [Qemu-devel] [PULL 00/48] ivshmem series Paolo Bonzini
2015-10-07 12:42     ` Andrew Jones
2015-10-07 13:05       ` Andreas Färber
2015-10-07 13:26         ` Marc-André Lureau
2015-10-07 22:00         ` Peter Maydell
2015-10-09 11:55 ` Pavel Fedin
2015-10-09 12:12   ` Marc-André Lureau
2015-10-09 12:29     ` Pavel Fedin
2015-10-09 12:45       ` Marc-André Lureau
2015-10-09 12:47         ` Paolo Bonzini
2015-10-09 13:02           ` Pavel Fedin
2015-10-09 13:07             ` Paolo Bonzini
2015-10-09 12:51         ` Pavel Fedin

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20151010212900.22227.62062@loki \
    --to=mdroth@linux.vnet.ibm.com \
    --cc=afaerber@suse.de \
    --cc=cam@cs.ualberta.ca \
    --cc=marcandre.lureau@redhat.com \
    --cc=peter.maydell@linaro.org \
    --cc=qemu-devel@nongnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.