qemu/tests/virtio-9p-test.c
<<
>>
Prefs
   1/*
   2 * QTest testcase for VirtIO 9P
   3 *
   4 * Copyright (c) 2014 SUSE LINUX Products GmbH
   5 *
   6 * This work is licensed under the terms of the GNU GPL, version 2 or later.
   7 * See the COPYING file in the top-level directory.
   8 */
   9
  10#include "qemu/osdep.h"
  11#include "libqtest.h"
  12#include "qemu-common.h"
  13#include "libqos/libqos-pc.h"
  14#include "libqos/libqos-spapr.h"
  15#include "libqos/virtio.h"
  16#include "libqos/virtio-pci.h"
  17#include "standard-headers/linux/virtio_ids.h"
  18#include "standard-headers/linux/virtio_pci.h"
  19
  20static const char mount_tag[] = "qtest";
  21static char *test_share;
  22
  23
  24static QOSState *qvirtio_9p_start(void)
  25{
  26    const char *arch = qtest_get_arch();
  27    const char *cmd = "-fsdev local,id=fsdev0,security_model=none,path=%s "
  28                      "-device virtio-9p-pci,fsdev=fsdev0,mount_tag=%s";
  29
  30    test_share = g_strdup("/tmp/qtest.XXXXXX");
  31    g_assert_nonnull(mkdtemp(test_share));
  32
  33    if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) {
  34        return qtest_pc_boot(cmd, test_share, mount_tag);
  35    }
  36    if (strcmp(arch, "ppc64") == 0) {
  37        return qtest_spapr_boot(cmd, test_share, mount_tag);
  38    }
  39
  40    g_printerr("virtio-9p tests are only available on x86 or ppc64\n");
  41    exit(EXIT_FAILURE);
  42}
  43
  44static void qvirtio_9p_stop(QOSState *qs)
  45{
  46    qtest_shutdown(qs);
  47    rmdir(test_share);
  48    g_free(test_share);
  49}
  50
  51static void pci_nop(void)
  52{
  53    QOSState *qs;
  54
  55    qs = qvirtio_9p_start();
  56    qvirtio_9p_stop(qs);
  57}
  58
  59typedef struct {
  60    QVirtioDevice *dev;
  61    QOSState *qs;
  62    QVirtQueue *vq;
  63} QVirtIO9P;
  64
  65static QVirtIO9P *qvirtio_9p_pci_init(QOSState *qs)
  66{
  67    QVirtIO9P *v9p;
  68    QVirtioPCIDevice *dev;
  69
  70    v9p = g_new0(QVirtIO9P, 1);
  71
  72    v9p->qs = qs;
  73    dev = qvirtio_pci_device_find(v9p->qs->pcibus, VIRTIO_ID_9P);
  74    g_assert_nonnull(dev);
  75    g_assert_cmphex(dev->vdev.device_type, ==, VIRTIO_ID_9P);
  76    v9p->dev = (QVirtioDevice *) dev;
  77
  78    qvirtio_pci_device_enable(dev);
  79    qvirtio_reset(v9p->dev);
  80    qvirtio_set_acknowledge(v9p->dev);
  81    qvirtio_set_driver(v9p->dev);
  82
  83    v9p->vq = qvirtqueue_setup(v9p->dev, v9p->qs->alloc, 0);
  84    return v9p;
  85}
  86
  87static void qvirtio_9p_pci_free(QVirtIO9P *v9p)
  88{
  89    qvirtqueue_cleanup(v9p->dev->bus, v9p->vq, v9p->qs->alloc);
  90    qvirtio_pci_device_disable(container_of(v9p->dev, QVirtioPCIDevice, vdev));
  91    g_free(v9p->dev);
  92    g_free(v9p);
  93}
  94
  95static void pci_basic_config(void)
  96{
  97    QVirtIO9P *v9p;
  98    size_t tag_len;
  99    char *tag;
 100    int i;
 101    QOSState *qs;
 102
 103    qs = qvirtio_9p_start();
 104    v9p = qvirtio_9p_pci_init(qs);
 105
 106    tag_len = qvirtio_config_readw(v9p->dev, 0);
 107    g_assert_cmpint(tag_len, ==, strlen(mount_tag));
 108
 109    tag = g_malloc(tag_len);
 110    for (i = 0; i < tag_len; i++) {
 111        tag[i] = qvirtio_config_readb(v9p->dev, i + 2);
 112    }
 113    g_assert_cmpmem(tag, tag_len, mount_tag, tag_len);
 114    g_free(tag);
 115
 116    qvirtio_9p_pci_free(v9p);
 117    qvirtio_9p_stop(qs);
 118}
 119
 120int main(int argc, char **argv)
 121{
 122    g_test_init(&argc, &argv, NULL);
 123    qtest_add_func("/virtio/9p/pci/nop", pci_nop);
 124    qtest_add_func("/virtio/9p/pci/basic/configuration", pci_basic_config);
 125
 126    return g_test_run();
 127}
 128