From nobody Sun Nov 24 09:06:14 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=pass(p=none dis=none) header.from=gmail.com ARC-Seal: i=1; a=rsa-sha256; t=1726119676; cv=none; d=zohomail.com; s=zohoarc; b=jcOCDD1K1kO9sn4/gNXFA0OzjhHBwcegpehDdalBktbNSCo8FbAaCyNAV2eAP21TgGbGx+qNwhxUI8dXztMeMnDPN0L91S8GZUGLcwHIc4VYin423DIVamLYxvi1oSiaw1JnWSNsfIh5OaArfj+Yt2AHZS4XWjhMOcguf3mIwtU= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1726119676; h=Content-Transfer-Encoding:Cc:Cc:Date:Date:From:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:Subject:To:To:Message-Id:Reply-To; bh=2ByTGLA2ohy+rmq/nypuCycWKA7WUf0mVlcyTFolxao=; b=UQf7vXgeVPefRRthBdtsQICdb+h3MBQ/V0GgJ4+O+4DhQG2N0VHPUj/Rmlv2zf1hDSN3VA4kuY76dISaMiIJeT3/iwb6fnVJGnMvJvMVJtz6xcqePH/PSZc66kbotnUVrjCxkCM54haF1xVfouc311KBYcFOBr6jT0sMfUgqp8I= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=pass header.from= (p=none dis=none) Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1726119676110966.7129590190773; Wed, 11 Sep 2024 22:41:16 -0700 (PDT) Received: from localhost ([::1] helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1socQC-0003IG-Uj; Thu, 12 Sep 2024 01:31:12 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1socQ6-0002vJ-Dm for qemu-devel@nongnu.org; Thu, 12 Sep 2024 01:31:06 -0400 Received: from mail-pf1-x432.google.com ([2607:f8b0:4864:20::432]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1socQ4-00034f-2Q for qemu-devel@nongnu.org; Thu, 12 Sep 2024 01:31:05 -0400 Received: by mail-pf1-x432.google.com with SMTP id d2e1a72fcca58-71798a15ce5so1208996b3a.0 for ; Wed, 11 Sep 2024 22:31:03 -0700 (PDT) Received: from toolbox.alistair23.me (2403-580b-97e8-0-82ce-f179-8a79-69f4.ip6.aussiebb.net. [2403:580b:97e8:0:82ce:f179:8a79:69f4]) by smtp.gmail.com with ESMTPSA id d2e1a72fcca58-71908fc8fdesm3833034b3a.1.2024.09.11.22.30.59 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 11 Sep 2024 22:31:01 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1726119062; x=1726723862; darn=nongnu.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=2ByTGLA2ohy+rmq/nypuCycWKA7WUf0mVlcyTFolxao=; b=XxKmvz+MSFqZOyQRPIujsiGZzycOGGfJvkJ0MRLrb/qZL5sqQZZVSeRmvEvvmQrZy8 WSyTA1gX/NpyFGy7RpJFATof4m3rInPWjcLdbByA/uG2NNBWFTFOujlIlgSee+X8UnHh 5zJa4uRi+GVjNldn12ig65froSq87chaySj5it83HU+Dof/fSsfLrtQJnBWNkgaj3U6m 6RJe2dFXl5GBHNEJZl9drMJ26vf2EmOA408BKvrCqzRxxMaMtnHc8yqWGFL4dYz6A/q+ wKHZDWNP4ys1dIRwVJMxxy5ZHgCDZfwRVIMdv+r82wo5oEhP97o8WTu8qXqjMUZcehAQ vxMA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1726119062; x=1726723862; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=2ByTGLA2ohy+rmq/nypuCycWKA7WUf0mVlcyTFolxao=; b=oxRG6aV3RVMFZzyvOUN7Gy7+3H8cSQnOYxcaAB8QAh7DxTtDYsndbEzXTMsPNV0BBk c4tILBHGPL0v5U8EaDyfRQxSTGB+D1PV6tRFZsftNlDNvTpcJuCSXAXdHSF1nAHFpI4l 6Gmib3rduLTkO0r1fW0Jhmxdv7+M7B8RoWuktQVR6XkxyePinWlJ9m5BSza/U9uHQRqH VxXdCYCewifS2Tkf+5s/HmKCxSHp+BxUwB9DYL/jTfZxMLN4JrE/WEXiMw6omo0wIuRs HgiU0a/GAP3ChmdC9agLdb1rAkPh+JN6cuddkm2hjLQk6XzpcOykA0/v/mkKJyEbSO1p cZeg== X-Gm-Message-State: AOJu0YxYoJJGP1GEHdxZECqTUKgFYLAaFxl0+R9msqUcIaxcGl9p/7Bv I+DoCkxUaPZsI2UQWcRQr5Av2DnwfAQUdPJ0l99cXPmPybPjyx7BvETVQA== X-Google-Smtp-Source: AGHT+IGDeCbrQl5kIBITEnZGe7uvQeJZXD38N102Q8/sBgtv0UdDFql8WIguiFBU6B3OMeLhgqBdig== X-Received: by 2002:a05:6a00:18a3:b0:717:9896:fb03 with SMTP id d2e1a72fcca58-719263cbe2emr2546728b3a.6.1726119062150; Wed, 11 Sep 2024 22:31:02 -0700 (PDT) From: Alistair Francis X-Google-Original-From: Alistair Francis To: qemu-devel@nongnu.org Cc: alistair23@gmail.com, Daniel Henrique Barboza , Frank Chang , Alistair Francis Subject: [PULL 20/47] test/qtest: add riscv-iommu-pci tests Date: Thu, 12 Sep 2024 15:29:25 +1000 Message-ID: <20240912052953.2552501-21-alistair.francis@wdc.com> X-Mailer: git-send-email 2.46.0 In-Reply-To: <20240912052953.2552501-1-alistair.francis@wdc.com> References: <20240912052953.2552501-1-alistair.francis@wdc.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=2607:f8b0:4864:20::432; envelope-from=alistair23@gmail.com; helo=mail-pf1-x432.google.com X-Spam_score_int: -17 X-Spam_score: -1.8 X-Spam_bar: - X-Spam_report: (-1.8 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, FREEMAIL_ENVFROM_END_DIGIT=0.25, FREEMAIL_FROM=0.001, RCVD_IN_DNSWL_NONE=-0.0001, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: qemu-devel-bounces+importer=patchew.org@nongnu.org X-ZohoMail-DKIM: pass (identity @gmail.com) X-ZM-MESSAGEID: 1726119677629116600 Content-Type: text/plain; charset="utf-8" From: Daniel Henrique Barboza To test the RISC-V IOMMU emulation we'll use its PCI representation. Create a new 'riscv-iommu-pci' libqos device that will be present with CONFIG_RISCV_IOMMU. This config is only available for RISC-V, so this device will only be consumed by the RISC-V libqos machine. Start with basic tests: a PCI sanity check and a reset state register test. The reset test was taken from the RISC-V IOMMU spec chapter 5.2, "Reset behavior". More tests will be added later. Signed-off-by: Daniel Henrique Barboza Reviewed-by: Frank Chang Acked-by: Alistair Francis Message-ID: <20240903201633.93182-8-dbarboza@ventanamicro.com> Signed-off-by: Alistair Francis --- tests/qtest/libqos/riscv-iommu.h | 71 ++++++++++++++++++++++++ tests/qtest/libqos/riscv-iommu.c | 76 ++++++++++++++++++++++++++ tests/qtest/riscv-iommu-test.c | 93 ++++++++++++++++++++++++++++++++ tests/qtest/libqos/meson.build | 4 ++ tests/qtest/meson.build | 1 + 5 files changed, 245 insertions(+) create mode 100644 tests/qtest/libqos/riscv-iommu.h create mode 100644 tests/qtest/libqos/riscv-iommu.c create mode 100644 tests/qtest/riscv-iommu-test.c diff --git a/tests/qtest/libqos/riscv-iommu.h b/tests/qtest/libqos/riscv-io= mmu.h new file mode 100644 index 0000000000..d123efb41f --- /dev/null +++ b/tests/qtest/libqos/riscv-iommu.h @@ -0,0 +1,71 @@ +/* + * libqos driver riscv-iommu-pci framework + * + * Copyright (c) 2024 Ventana Micro Systems Inc. + * + * This work is licensed under the terms of the GNU GPL, version 2 or (at = your + * option) any later version. See the COPYING file in the top-level direc= tory. + * + */ + +#ifndef TESTS_LIBQOS_RISCV_IOMMU_H +#define TESTS_LIBQOS_RISCV_IOMMU_H + +#include "qgraph.h" +#include "pci.h" +#include "qemu/bitops.h" + +#ifndef GENMASK_ULL +#define GENMASK_ULL(h, l) (((~0ULL) >> (63 - (h) + (l))) << (l)) +#endif + +/* + * RISC-V IOMMU uses PCI_VENDOR_ID_REDHAT 0x1b36 and + * PCI_DEVICE_ID_REDHAT_RISCV_IOMMU 0x0014. + */ +#define RISCV_IOMMU_PCI_VENDOR_ID 0x1b36 +#define RISCV_IOMMU_PCI_DEVICE_ID 0x0014 +#define RISCV_IOMMU_PCI_DEVICE_CLASS 0x0806 + +/* Common field positions */ +#define RISCV_IOMMU_QUEUE_ENABLE BIT(0) +#define RISCV_IOMMU_QUEUE_INTR_ENABLE BIT(1) +#define RISCV_IOMMU_QUEUE_MEM_FAULT BIT(8) +#define RISCV_IOMMU_QUEUE_ACTIVE BIT(16) +#define RISCV_IOMMU_QUEUE_BUSY BIT(17) + +#define RISCV_IOMMU_REG_CAP 0x0000 +#define RISCV_IOMMU_CAP_VERSION GENMASK_ULL(7, 0) + +#define RISCV_IOMMU_REG_DDTP 0x0010 +#define RISCV_IOMMU_DDTP_BUSY BIT_ULL(4) +#define RISCV_IOMMU_DDTP_MODE GENMASK_ULL(3, 0) +#define RISCV_IOMMU_DDTP_MODE_OFF 0 + +#define RISCV_IOMMU_REG_CQCSR 0x0048 +#define RISCV_IOMMU_CQCSR_CQEN RISCV_IOMMU_QUEUE_ENABLE +#define RISCV_IOMMU_CQCSR_CIE RISCV_IOMMU_QUEUE_INTR_ENABLE +#define RISCV_IOMMU_CQCSR_CQON RISCV_IOMMU_QUEUE_ACTIVE +#define RISCV_IOMMU_CQCSR_BUSY RISCV_IOMMU_QUEUE_BUSY + +#define RISCV_IOMMU_REG_FQCSR 0x004C +#define RISCV_IOMMU_FQCSR_FQEN RISCV_IOMMU_QUEUE_ENABLE +#define RISCV_IOMMU_FQCSR_FIE RISCV_IOMMU_QUEUE_INTR_ENABLE +#define RISCV_IOMMU_FQCSR_FQON RISCV_IOMMU_QUEUE_ACTIVE +#define RISCV_IOMMU_FQCSR_BUSY RISCV_IOMMU_QUEUE_BUSY + +#define RISCV_IOMMU_REG_PQCSR 0x0050 +#define RISCV_IOMMU_PQCSR_PQEN RISCV_IOMMU_QUEUE_ENABLE +#define RISCV_IOMMU_PQCSR_PIE RISCV_IOMMU_QUEUE_INTR_ENABLE +#define RISCV_IOMMU_PQCSR_PQON RISCV_IOMMU_QUEUE_ACTIVE +#define RISCV_IOMMU_PQCSR_BUSY RISCV_IOMMU_QUEUE_BUSY + +#define RISCV_IOMMU_REG_IPSR 0x0054 + +typedef struct QRISCVIOMMU { + QOSGraphObject obj; + QPCIDevice dev; + QPCIBar reg_bar; +} QRISCVIOMMU; + +#endif diff --git a/tests/qtest/libqos/riscv-iommu.c b/tests/qtest/libqos/riscv-io= mmu.c new file mode 100644 index 0000000000..01e3b31c0b --- /dev/null +++ b/tests/qtest/libqos/riscv-iommu.c @@ -0,0 +1,76 @@ +/* + * libqos driver riscv-iommu-pci framework + * + * Copyright (c) 2024 Ventana Micro Systems Inc. + * + * This work is licensed under the terms of the GNU GPL, version 2 or (at = your + * option) any later version. See the COPYING file in the top-level direc= tory. + * + */ + +#include "qemu/osdep.h" +#include "../libqtest.h" +#include "qemu/module.h" +#include "qgraph.h" +#include "pci.h" +#include "riscv-iommu.h" + +static void *riscv_iommu_pci_get_driver(void *obj, const char *interface) +{ + QRISCVIOMMU *r_iommu_pci =3D obj; + + if (!g_strcmp0(interface, "pci-device")) { + return &r_iommu_pci->dev; + } + + fprintf(stderr, "%s not present in riscv_iommu_pci\n", interface); + g_assert_not_reached(); +} + +static void riscv_iommu_pci_start_hw(QOSGraphObject *obj) +{ + QRISCVIOMMU *pci =3D (QRISCVIOMMU *)obj; + qpci_device_enable(&pci->dev); +} + +static void riscv_iommu_pci_destructor(QOSGraphObject *obj) +{ + QRISCVIOMMU *pci =3D (QRISCVIOMMU *)obj; + qpci_iounmap(&pci->dev, pci->reg_bar); +} + +static void *riscv_iommu_pci_create(void *pci_bus, QGuestAllocator *alloc, + void *addr) +{ + QRISCVIOMMU *r_iommu_pci =3D g_new0(QRISCVIOMMU, 1); + QPCIBus *bus =3D pci_bus; + + qpci_device_init(&r_iommu_pci->dev, bus, addr); + r_iommu_pci->reg_bar =3D qpci_iomap(&r_iommu_pci->dev, 0, NULL); + + r_iommu_pci->obj.get_driver =3D riscv_iommu_pci_get_driver; + r_iommu_pci->obj.start_hw =3D riscv_iommu_pci_start_hw; + r_iommu_pci->obj.destructor =3D riscv_iommu_pci_destructor; + return &r_iommu_pci->obj; +} + +static void riscv_iommu_pci_register_nodes(void) +{ + QPCIAddress addr =3D { + .vendor_id =3D RISCV_IOMMU_PCI_VENDOR_ID, + .device_id =3D RISCV_IOMMU_PCI_DEVICE_ID, + .devfn =3D QPCI_DEVFN(1, 0), + }; + + QOSGraphEdgeOptions opts =3D { + .extra_device_opts =3D "addr=3D01.0", + }; + + add_qpci_address(&opts, &addr); + + qos_node_create_driver("riscv-iommu-pci", riscv_iommu_pci_create); + qos_node_produces("riscv-iommu-pci", "pci-device"); + qos_node_consumes("riscv-iommu-pci", "pci-bus", &opts); +} + +libqos_init(riscv_iommu_pci_register_nodes); diff --git a/tests/qtest/riscv-iommu-test.c b/tests/qtest/riscv-iommu-test.c new file mode 100644 index 0000000000..7f0dbd0211 --- /dev/null +++ b/tests/qtest/riscv-iommu-test.c @@ -0,0 +1,93 @@ +/* + * QTest testcase for RISC-V IOMMU + * + * Copyright (c) 2024 Ventana Micro Systems Inc. + * + * This work is licensed under the terms of the GNU GPL, version 2 or (at = your + * option) any later version. See the COPYING file in the top-level direc= tory. + * + */ + +#include "qemu/osdep.h" +#include "libqtest-single.h" +#include "qemu/module.h" +#include "libqos/qgraph.h" +#include "libqos/riscv-iommu.h" +#include "hw/pci/pci_regs.h" + +static uint32_t riscv_iommu_read_reg32(QRISCVIOMMU *r_iommu, int reg_offse= t) +{ + uint32_t reg; + + qpci_memread(&r_iommu->dev, r_iommu->reg_bar, reg_offset, + ®, sizeof(reg)); + return reg; +} + +static uint64_t riscv_iommu_read_reg64(QRISCVIOMMU *r_iommu, int reg_offse= t) +{ + uint64_t reg; + + qpci_memread(&r_iommu->dev, r_iommu->reg_bar, reg_offset, + ®, sizeof(reg)); + return reg; +} + +static void test_pci_config(void *obj, void *data, QGuestAllocator *t_allo= c) +{ + QRISCVIOMMU *r_iommu =3D obj; + QPCIDevice *dev =3D &r_iommu->dev; + uint16_t vendorid, deviceid, classid; + + vendorid =3D qpci_config_readw(dev, PCI_VENDOR_ID); + deviceid =3D qpci_config_readw(dev, PCI_DEVICE_ID); + classid =3D qpci_config_readw(dev, PCI_CLASS_DEVICE); + + g_assert_cmpuint(vendorid, =3D=3D, RISCV_IOMMU_PCI_VENDOR_ID); + g_assert_cmpuint(deviceid, =3D=3D, RISCV_IOMMU_PCI_DEVICE_ID); + g_assert_cmpuint(classid, =3D=3D, RISCV_IOMMU_PCI_DEVICE_CLASS); +} + +static void test_reg_reset(void *obj, void *data, QGuestAllocator *t_alloc) +{ + QRISCVIOMMU *r_iommu =3D obj; + uint64_t cap; + uint32_t reg; + + cap =3D riscv_iommu_read_reg64(r_iommu, RISCV_IOMMU_REG_CAP); + g_assert_cmpuint(cap & RISCV_IOMMU_CAP_VERSION, =3D=3D, 0x10); + + reg =3D riscv_iommu_read_reg32(r_iommu, RISCV_IOMMU_REG_CQCSR); + g_assert_cmpuint(reg & RISCV_IOMMU_CQCSR_CQEN, =3D=3D, 0); + g_assert_cmpuint(reg & RISCV_IOMMU_CQCSR_CIE, =3D=3D, 0); + g_assert_cmpuint(reg & RISCV_IOMMU_CQCSR_CQON, =3D=3D, 0); + g_assert_cmpuint(reg & RISCV_IOMMU_CQCSR_BUSY, =3D=3D, 0); + + reg =3D riscv_iommu_read_reg32(r_iommu, RISCV_IOMMU_REG_FQCSR); + g_assert_cmpuint(reg & RISCV_IOMMU_FQCSR_FQEN, =3D=3D, 0); + g_assert_cmpuint(reg & RISCV_IOMMU_FQCSR_FIE, =3D=3D, 0); + g_assert_cmpuint(reg & RISCV_IOMMU_FQCSR_FQON, =3D=3D, 0); + g_assert_cmpuint(reg & RISCV_IOMMU_FQCSR_BUSY, =3D=3D, 0); + + reg =3D riscv_iommu_read_reg32(r_iommu, RISCV_IOMMU_REG_PQCSR); + g_assert_cmpuint(reg & RISCV_IOMMU_PQCSR_PQEN, =3D=3D, 0); + g_assert_cmpuint(reg & RISCV_IOMMU_PQCSR_PIE, =3D=3D, 0); + g_assert_cmpuint(reg & RISCV_IOMMU_PQCSR_PQON, =3D=3D, 0); + g_assert_cmpuint(reg & RISCV_IOMMU_PQCSR_BUSY, =3D=3D, 0); + + reg =3D riscv_iommu_read_reg32(r_iommu, RISCV_IOMMU_REG_DDTP); + g_assert_cmpuint(reg & RISCV_IOMMU_DDTP_BUSY, =3D=3D, 0); + g_assert_cmpuint(reg & RISCV_IOMMU_DDTP_MODE, =3D=3D, + RISCV_IOMMU_DDTP_MODE_OFF); + + reg =3D riscv_iommu_read_reg32(r_iommu, RISCV_IOMMU_REG_IPSR); + g_assert_cmpuint(reg, =3D=3D, 0); +} + +static void register_riscv_iommu_test(void) +{ + qos_add_test("pci_config", "riscv-iommu-pci", test_pci_config, NULL); + qos_add_test("reg_reset", "riscv-iommu-pci", test_reg_reset, NULL); +} + +libqos_init(register_riscv_iommu_test); diff --git a/tests/qtest/libqos/meson.build b/tests/qtest/libqos/meson.build index 1b2b2dbb22..586fcacdc8 100644 --- a/tests/qtest/libqos/meson.build +++ b/tests/qtest/libqos/meson.build @@ -68,6 +68,10 @@ if have_virtfs libqos_srcs +=3D files('virtio-9p.c', 'virtio-9p-client.c') endif =20 +if config_all_devices.has_key('CONFIG_RISCV_IOMMU') + libqos_srcs +=3D files('riscv-iommu.c') +endif + libqos =3D static_library('qos', libqos_srcs + genh, build_by_default: false) =20 diff --git a/tests/qtest/meson.build b/tests/qtest/meson.build index fc852f3d8b..68cb7615a5 100644 --- a/tests/qtest/meson.build +++ b/tests/qtest/meson.build @@ -298,6 +298,7 @@ qos_test_ss.add( 'vmxnet3-test.c', 'igb-test.c', 'ufs-test.c', + 'riscv-iommu-test.c', ) =20 if config_all_devices.has_key('CONFIG_VIRTIO_SERIAL') --=20 2.46.0