diff mbox series

[6/6] tests/libqos: add riscv/virt machine nodes

Message ID 20240213191736.733334-7-dbarboza@ventanamicro.com
State New
Headers show
Series libqos, riscv: libqos fixes, add riscv machine | expand

Commit Message

Daniel Henrique Barboza Feb. 13, 2024, 7:17 p.m. UTC
Add a RISC-V 'virt' machine to the graph. This implementation is a
modified copy of the existing arm machine in arm-virt-machine.c

It contains a virtio-mmio and a generic-pcihost controller. The
generic-pcihost controller hardcodes assumptions from the ARM 'virt'
machine, like ecam and pio_base addresses, so we'll add an extra step to
set its parameters after creating it.

Our command line is incremented with 'aclint' parameters to allow the
machine to run MSI tests.

Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
---
 tests/qtest/libqos/meson.build          |   1 +
 tests/qtest/libqos/riscv-virt-machine.c | 137 ++++++++++++++++++++++++
 2 files changed, 138 insertions(+)
 create mode 100644 tests/qtest/libqos/riscv-virt-machine.c

Comments

Alistair Francis Feb. 15, 2024, 5:35 a.m. UTC | #1
On Wed, Feb 14, 2024 at 5:18 AM Daniel Henrique Barboza
<dbarboza@ventanamicro.com> wrote:
>
> Add a RISC-V 'virt' machine to the graph. This implementation is a
> modified copy of the existing arm machine in arm-virt-machine.c
>
> It contains a virtio-mmio and a generic-pcihost controller. The
> generic-pcihost controller hardcodes assumptions from the ARM 'virt'
> machine, like ecam and pio_base addresses, so we'll add an extra step to
> set its parameters after creating it.
>
> Our command line is incremented with 'aclint' parameters to allow the
> machine to run MSI tests.
>
> Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>

Acked-by: Alistair Francis <alistair.francis@wdc.com>

Alistair

> ---
>  tests/qtest/libqos/meson.build          |   1 +
>  tests/qtest/libqos/riscv-virt-machine.c | 137 ++++++++++++++++++++++++
>  2 files changed, 138 insertions(+)
>  create mode 100644 tests/qtest/libqos/riscv-virt-machine.c
>
> diff --git a/tests/qtest/libqos/meson.build b/tests/qtest/libqos/meson.build
> index 90aae42a22..3aed6efcb8 100644
> --- a/tests/qtest/libqos/meson.build
> +++ b/tests/qtest/libqos/meson.build
> @@ -60,6 +60,7 @@ libqos_srcs = files(
>          'arm-xilinx-zynq-a9-machine.c',
>          'ppc64_pseries-machine.c',
>          'x86_64_pc-machine.c',
> +        'riscv-virt-machine.c',
>  )
>
>  if have_virtfs
> diff --git a/tests/qtest/libqos/riscv-virt-machine.c b/tests/qtest/libqos/riscv-virt-machine.c
> new file mode 100644
> index 0000000000..c4364c9c5d
> --- /dev/null
> +++ b/tests/qtest/libqos/riscv-virt-machine.c
> @@ -0,0 +1,137 @@
> +/*
> + * libqos driver framework for risc-v
> + *
> + * Initial version based on arm-virt-machine.c
> + *
> + * Copyright (c) 2024 Ventana Micro
> + *
> + * This library is free software; you can redistribute it and/or
> + * modify it under the terms of the GNU Lesser General Public
> + * License version 2.1 as published by the Free Software Foundation.
> + *
> + * This library is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
> + * Lesser General Public License for more details.
> + *
> + * You should have received a copy of the GNU Lesser General Public
> + * License along with this library; if not, see <http://www.gnu.org/licenses/>
> + */
> +
> +#include "qemu/osdep.h"
> +#include "../libqtest.h"
> +#include "qemu/module.h"
> +#include "libqos-malloc.h"
> +#include "qgraph.h"
> +#include "virtio-mmio.h"
> +#include "generic-pcihost.h"
> +#include "hw/pci/pci_regs.h"
> +
> +#define RISCV_PAGE_SIZE            4096
> +
> +/* VIRT_DRAM */
> +#define RISCV_VIRT_RAM_ADDR        0x80000000
> +#define RISCV_VIRT_RAM_SIZE        0x20000000
> +
> +/*
> + * VIRT_VIRTIO. BASE_ADDR  points to the last
> + * virtio_mmio device.
> + */
> +#define VIRTIO_MMIO_BASE_ADDR      0x10008000
> +#define VIRTIO_MMIO_SIZE           0x00001000
> +
> +/* VIRT_PCIE_PIO  */
> +#define RISCV_GPEX_PIO_BASE        0x3000000
> +#define RISCV_BUS_PIO_LIMIT        0x10000
> +
> +/* VIRT_PCIE_MMIO */
> +#define RISCV_BUS_MMIO_ALLOC_PTR   0x40000000
> +#define RISCV_BUS_MMIO_LIMIT       0x80000000
> +
> +/* VIRT_PCIE_ECAM */
> +#define RISCV_ECAM_ALLOC_PTR   0x30000000
> +
> +typedef struct QVirtMachine QVirtMachine;
> +
> +struct QVirtMachine {
> +    QOSGraphObject obj;
> +    QGuestAllocator alloc;
> +    QVirtioMMIODevice virtio_mmio;
> +    QGenericPCIHost bridge;
> +};
> +
> +static void virt_destructor(QOSGraphObject *obj)
> +{
> +    QVirtMachine *machine = (QVirtMachine *) obj;
> +    alloc_destroy(&machine->alloc);
> +}
> +
> +static void *virt_get_driver(void *object, const char *interface)
> +{
> +    QVirtMachine *machine = object;
> +    if (!g_strcmp0(interface, "memory")) {
> +        return &machine->alloc;
> +    }
> +
> +    fprintf(stderr, "%s not present in riscv/virtio\n", interface);
> +    g_assert_not_reached();
> +}
> +
> +static QOSGraphObject *virt_get_device(void *obj, const char *device)
> +{
> +    QVirtMachine *machine = obj;
> +    if (!g_strcmp0(device, "generic-pcihost")) {
> +        return &machine->bridge.obj;
> +    } else if (!g_strcmp0(device, "virtio-mmio")) {
> +        return &machine->virtio_mmio.obj;
> +    }
> +
> +    fprintf(stderr, "%s not present in riscv/virt\n", device);
> +    g_assert_not_reached();
> +}
> +
> +static void riscv_config_qpci_bus(QGenericPCIBus *qpci)
> +{
> +    qpci->gpex_pio_base = RISCV_GPEX_PIO_BASE;
> +    qpci->bus.pio_limit = RISCV_BUS_PIO_LIMIT;
> +
> +    qpci->bus.mmio_alloc_ptr = RISCV_BUS_MMIO_ALLOC_PTR;
> +    qpci->bus.mmio_limit = RISCV_BUS_MMIO_LIMIT;
> +
> +    qpci->ecam_alloc_ptr = RISCV_ECAM_ALLOC_PTR;
> +}
> +
> +static void *qos_create_machine_riscv_virt(QTestState *qts)
> +{
> +    QVirtMachine *machine = g_new0(QVirtMachine, 1);
> +
> +    alloc_init(&machine->alloc, 0,
> +               RISCV_VIRT_RAM_ADDR,
> +               RISCV_VIRT_RAM_ADDR + RISCV_VIRT_RAM_SIZE,
> +               RISCV_PAGE_SIZE);
> +    qvirtio_mmio_init_device(&machine->virtio_mmio, qts, VIRTIO_MMIO_BASE_ADDR,
> +                              VIRTIO_MMIO_SIZE);
> +
> +    qos_create_generic_pcihost(&machine->bridge, qts, &machine->alloc);
> +    riscv_config_qpci_bus(&machine->bridge.pci);
> +
> +    machine->obj.get_device = virt_get_device;
> +    machine->obj.get_driver = virt_get_driver;
> +    machine->obj.destructor = virt_destructor;
> +    return machine;
> +}
> +
> +static void virt_machine_register_nodes(void)
> +{
> +    qos_node_create_machine_args("riscv32/virt", qos_create_machine_riscv_virt,
> +                                 "aclint=on,aia=aplic-imsic");
> +    qos_node_contains("riscv32/virt", "virtio-mmio", NULL);
> +    qos_node_contains("riscv32/virt", "generic-pcihost", NULL);
> +
> +    qos_node_create_machine_args("riscv64/virt", qos_create_machine_riscv_virt,
> +                                 "aclint=on,aia=aplic-imsic");
> +    qos_node_contains("riscv64/virt", "virtio-mmio", NULL);
> +    qos_node_contains("riscv64/virt", "generic-pcihost", NULL);
> +}
> +
> +libqos_init(virt_machine_register_nodes);
> --
> 2.43.0
>
>
Thomas Huth Feb. 16, 2024, 10:58 a.m. UTC | #2
On 13/02/2024 20.17, Daniel Henrique Barboza wrote:
> Add a RISC-V 'virt' machine to the graph. This implementation is a
> modified copy of the existing arm machine in arm-virt-machine.c
> 
> It contains a virtio-mmio and a generic-pcihost controller. The
> generic-pcihost controller hardcodes assumptions from the ARM 'virt'
> machine, like ecam and pio_base addresses, so we'll add an extra step to
> set its parameters after creating it.
> 
> Our command line is incremented with 'aclint' parameters to allow the
> machine to run MSI tests.
> 
> Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
> ---
>   tests/qtest/libqos/meson.build          |   1 +
>   tests/qtest/libqos/riscv-virt-machine.c | 137 ++++++++++++++++++++++++
>   2 files changed, 138 insertions(+)
>   create mode 100644 tests/qtest/libqos/riscv-virt-machine.c

Acked-by: Thomas Huth <thuth@redhat.com>
diff mbox series

Patch

diff --git a/tests/qtest/libqos/meson.build b/tests/qtest/libqos/meson.build
index 90aae42a22..3aed6efcb8 100644
--- a/tests/qtest/libqos/meson.build
+++ b/tests/qtest/libqos/meson.build
@@ -60,6 +60,7 @@  libqos_srcs = files(
         'arm-xilinx-zynq-a9-machine.c',
         'ppc64_pseries-machine.c',
         'x86_64_pc-machine.c',
+        'riscv-virt-machine.c',
 )
 
 if have_virtfs
diff --git a/tests/qtest/libqos/riscv-virt-machine.c b/tests/qtest/libqos/riscv-virt-machine.c
new file mode 100644
index 0000000000..c4364c9c5d
--- /dev/null
+++ b/tests/qtest/libqos/riscv-virt-machine.c
@@ -0,0 +1,137 @@ 
+/*
+ * libqos driver framework for risc-v
+ *
+ * Initial version based on arm-virt-machine.c
+ *
+ * Copyright (c) 2024 Ventana Micro
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License version 2.1 as published by the Free Software Foundation.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, see <http://www.gnu.org/licenses/>
+ */
+
+#include "qemu/osdep.h"
+#include "../libqtest.h"
+#include "qemu/module.h"
+#include "libqos-malloc.h"
+#include "qgraph.h"
+#include "virtio-mmio.h"
+#include "generic-pcihost.h"
+#include "hw/pci/pci_regs.h"
+
+#define RISCV_PAGE_SIZE            4096
+
+/* VIRT_DRAM */
+#define RISCV_VIRT_RAM_ADDR        0x80000000
+#define RISCV_VIRT_RAM_SIZE        0x20000000
+
+/*
+ * VIRT_VIRTIO. BASE_ADDR  points to the last
+ * virtio_mmio device.
+ */
+#define VIRTIO_MMIO_BASE_ADDR      0x10008000
+#define VIRTIO_MMIO_SIZE           0x00001000
+
+/* VIRT_PCIE_PIO  */
+#define RISCV_GPEX_PIO_BASE        0x3000000
+#define RISCV_BUS_PIO_LIMIT        0x10000
+
+/* VIRT_PCIE_MMIO */
+#define RISCV_BUS_MMIO_ALLOC_PTR   0x40000000
+#define RISCV_BUS_MMIO_LIMIT       0x80000000
+
+/* VIRT_PCIE_ECAM */
+#define RISCV_ECAM_ALLOC_PTR   0x30000000
+
+typedef struct QVirtMachine QVirtMachine;
+
+struct QVirtMachine {
+    QOSGraphObject obj;
+    QGuestAllocator alloc;
+    QVirtioMMIODevice virtio_mmio;
+    QGenericPCIHost bridge;
+};
+
+static void virt_destructor(QOSGraphObject *obj)
+{
+    QVirtMachine *machine = (QVirtMachine *) obj;
+    alloc_destroy(&machine->alloc);
+}
+
+static void *virt_get_driver(void *object, const char *interface)
+{
+    QVirtMachine *machine = object;
+    if (!g_strcmp0(interface, "memory")) {
+        return &machine->alloc;
+    }
+
+    fprintf(stderr, "%s not present in riscv/virtio\n", interface);
+    g_assert_not_reached();
+}
+
+static QOSGraphObject *virt_get_device(void *obj, const char *device)
+{
+    QVirtMachine *machine = obj;
+    if (!g_strcmp0(device, "generic-pcihost")) {
+        return &machine->bridge.obj;
+    } else if (!g_strcmp0(device, "virtio-mmio")) {
+        return &machine->virtio_mmio.obj;
+    }
+
+    fprintf(stderr, "%s not present in riscv/virt\n", device);
+    g_assert_not_reached();
+}
+
+static void riscv_config_qpci_bus(QGenericPCIBus *qpci)
+{
+    qpci->gpex_pio_base = RISCV_GPEX_PIO_BASE;
+    qpci->bus.pio_limit = RISCV_BUS_PIO_LIMIT;
+
+    qpci->bus.mmio_alloc_ptr = RISCV_BUS_MMIO_ALLOC_PTR;
+    qpci->bus.mmio_limit = RISCV_BUS_MMIO_LIMIT;
+
+    qpci->ecam_alloc_ptr = RISCV_ECAM_ALLOC_PTR;
+}
+
+static void *qos_create_machine_riscv_virt(QTestState *qts)
+{
+    QVirtMachine *machine = g_new0(QVirtMachine, 1);
+
+    alloc_init(&machine->alloc, 0,
+               RISCV_VIRT_RAM_ADDR,
+               RISCV_VIRT_RAM_ADDR + RISCV_VIRT_RAM_SIZE,
+               RISCV_PAGE_SIZE);
+    qvirtio_mmio_init_device(&machine->virtio_mmio, qts, VIRTIO_MMIO_BASE_ADDR,
+                              VIRTIO_MMIO_SIZE);
+
+    qos_create_generic_pcihost(&machine->bridge, qts, &machine->alloc);
+    riscv_config_qpci_bus(&machine->bridge.pci);
+
+    machine->obj.get_device = virt_get_device;
+    machine->obj.get_driver = virt_get_driver;
+    machine->obj.destructor = virt_destructor;
+    return machine;
+}
+
+static void virt_machine_register_nodes(void)
+{
+    qos_node_create_machine_args("riscv32/virt", qos_create_machine_riscv_virt,
+                                 "aclint=on,aia=aplic-imsic");
+    qos_node_contains("riscv32/virt", "virtio-mmio", NULL);
+    qos_node_contains("riscv32/virt", "generic-pcihost", NULL);
+
+    qos_node_create_machine_args("riscv64/virt", qos_create_machine_riscv_virt,
+                                 "aclint=on,aia=aplic-imsic");
+    qos_node_contains("riscv64/virt", "virtio-mmio", NULL);
+    qos_node_contains("riscv64/virt", "generic-pcihost", NULL);
+}
+
+libqos_init(virt_machine_register_nodes);