summaryrefslogtreecommitdiff
path: root/tools/testing/cxl
diff options
context:
space:
mode:
authorDan Williams <dan.j.williams@intel.com>2022-02-01 12:24:30 -0800
committerDan Williams <dan.j.williams@intel.com>2022-02-08 22:57:30 -0800
commitd17d0540a0dbf109210f7b57a37571e2978da0fa (patch)
treed7f969f8c73c1134c480484ebb13a72a2950769e /tools/testing/cxl
parent98d2d3a264543680281fd8a4e6ae490ca26b4f85 (diff)
cxl/core/hdm: Add CXL standard decoder enumeration to the core
Unlike the decoder enumeration for "root decoders" described by platform firmware, standard decoders can be enumerated from the component registers space once the base address has been identified (via PCI, ACPI, or another mechanism). Add common infrastructure for HDM (Host-managed-Device-Memory) Decoder enumeration and share it between host-bridge, upstream switch port, and cxl_test defined decoders. The locking model for switch level decoders is to hold the port lock over the enumeration. This facilitates moving the dport and decoder enumeration to a 'port' driver. For now, the only enumerator of decoder resources is the cxl_acpi root driver. Co-developed-by: Ben Widawsky <ben.widawsky@intel.com> Signed-off-by: Ben Widawsky <ben.widawsky@intel.com> Reviewed-by: Jonathan Cameron <Jonathan.Cameron@huawei.com> Link: https://lore.kernel.org/r/164374688404.395335.9239248252443123526.stgit@dwillia2-desk3.amr.corp.intel.com Signed-off-by: Dan Williams <dan.j.williams@intel.com>
Diffstat (limited to 'tools/testing/cxl')
-rw-r--r--tools/testing/cxl/Kbuild4
-rw-r--r--tools/testing/cxl/test/cxl.c29
-rw-r--r--tools/testing/cxl/test/mock.c50
-rw-r--r--tools/testing/cxl/test/mock.h3
4 files changed, 86 insertions, 0 deletions
diff --git a/tools/testing/cxl/Kbuild b/tools/testing/cxl/Kbuild
index 61123544aa49..3045d7cba0db 100644
--- a/tools/testing/cxl/Kbuild
+++ b/tools/testing/cxl/Kbuild
@@ -5,6 +5,9 @@ ldflags-y += --wrap=acpi_evaluate_integer
ldflags-y += --wrap=acpi_pci_find_root
ldflags-y += --wrap=nvdimm_bus_register
ldflags-y += --wrap=devm_cxl_port_enumerate_dports
+ldflags-y += --wrap=devm_cxl_setup_hdm
+ldflags-y += --wrap=devm_cxl_add_passthrough_decoder
+ldflags-y += --wrap=devm_cxl_enumerate_decoders
DRIVERS := ../../../drivers
CXL_SRC := $(DRIVERS)/cxl
@@ -31,6 +34,7 @@ cxl_core-y += $(CXL_CORE_SRC)/regs.o
cxl_core-y += $(CXL_CORE_SRC)/memdev.o
cxl_core-y += $(CXL_CORE_SRC)/mbox.o
cxl_core-y += $(CXL_CORE_SRC)/pci.o
+cxl_core-y += $(CXL_CORE_SRC)/hdm.o
cxl_core-y += config_check.o
obj-m += test/
diff --git a/tools/testing/cxl/test/cxl.c b/tools/testing/cxl/test/cxl.c
index ef002e909d38..81c09380c537 100644
--- a/tools/testing/cxl/test/cxl.c
+++ b/tools/testing/cxl/test/cxl.c
@@ -8,6 +8,7 @@
#include <linux/acpi.h>
#include <linux/pci.h>
#include <linux/mm.h>
+#include <cxlmem.h>
#include "mock.h"
#define NR_CXL_HOST_BRIDGES 4
@@ -398,6 +399,31 @@ static struct acpi_pci_root *mock_acpi_pci_find_root(acpi_handle handle)
return &mock_pci_root[host_bridge_index(adev)];
}
+static struct cxl_hdm *mock_cxl_setup_hdm(struct device *host,
+ struct cxl_port *port)
+{
+ struct cxl_hdm *cxlhdm = devm_kzalloc(&port->dev, sizeof(*cxlhdm), GFP_KERNEL);
+
+ if (!cxlhdm)
+ return ERR_PTR(-ENOMEM);
+
+ cxlhdm->port = port;
+ return cxlhdm;
+}
+
+static int mock_cxl_add_passthrough_decoder(struct device *host,
+ struct cxl_port *port)
+{
+ dev_err(&port->dev, "unexpected passthrough decoder for cxl_test\n");
+ return -EOPNOTSUPP;
+}
+
+static int mock_cxl_enumerate_decoders(struct device *host,
+ struct cxl_hdm *cxlhdm)
+{
+ return 0;
+}
+
static int mock_cxl_port_enumerate_dports(struct device *host,
struct cxl_port *port)
{
@@ -439,6 +465,9 @@ static struct cxl_mock_ops cxl_mock_ops = {
.acpi_evaluate_integer = mock_acpi_evaluate_integer,
.acpi_pci_find_root = mock_acpi_pci_find_root,
.devm_cxl_port_enumerate_dports = mock_cxl_port_enumerate_dports,
+ .devm_cxl_setup_hdm = mock_cxl_setup_hdm,
+ .devm_cxl_add_passthrough_decoder = mock_cxl_add_passthrough_decoder,
+ .devm_cxl_enumerate_decoders = mock_cxl_enumerate_decoders,
.list = LIST_HEAD_INIT(cxl_mock_ops.list),
};
diff --git a/tools/testing/cxl/test/mock.c b/tools/testing/cxl/test/mock.c
index 56b4b7d734bc..18d3b65e2a9b 100644
--- a/tools/testing/cxl/test/mock.c
+++ b/tools/testing/cxl/test/mock.c
@@ -131,6 +131,56 @@ __wrap_nvdimm_bus_register(struct device *dev,
}
EXPORT_SYMBOL_GPL(__wrap_nvdimm_bus_register);
+struct cxl_hdm *__wrap_devm_cxl_setup_hdm(struct device *host,
+ struct cxl_port *port)
+{
+ int index;
+ struct cxl_hdm *cxlhdm;
+ struct cxl_mock_ops *ops = get_cxl_mock_ops(&index);
+
+ if (ops && ops->is_mock_port(port->uport))
+ cxlhdm = ops->devm_cxl_setup_hdm(host, port);
+ else
+ cxlhdm = devm_cxl_setup_hdm(host, port);
+ put_cxl_mock_ops(index);
+
+ return cxlhdm;
+}
+EXPORT_SYMBOL_NS_GPL(__wrap_devm_cxl_setup_hdm, CXL);
+
+int __wrap_devm_cxl_add_passthrough_decoder(struct device *host,
+ struct cxl_port *port)
+{
+ int rc, index;
+ struct cxl_mock_ops *ops = get_cxl_mock_ops(&index);
+
+ if (ops && ops->is_mock_port(port->uport))
+ rc = ops->devm_cxl_add_passthrough_decoder(host, port);
+ else
+ rc = devm_cxl_add_passthrough_decoder(host, port);
+ put_cxl_mock_ops(index);
+
+ return rc;
+}
+EXPORT_SYMBOL_NS_GPL(__wrap_devm_cxl_add_passthrough_decoder, CXL);
+
+int __wrap_devm_cxl_enumerate_decoders(struct device *host,
+ struct cxl_hdm *cxlhdm)
+{
+ int rc, index;
+ struct cxl_port *port = cxlhdm->port;
+ struct cxl_mock_ops *ops = get_cxl_mock_ops(&index);
+
+ if (ops && ops->is_mock_port(port->uport))
+ rc = ops->devm_cxl_enumerate_decoders(host, cxlhdm);
+ else
+ rc = devm_cxl_enumerate_decoders(host, cxlhdm);
+ put_cxl_mock_ops(index);
+
+ return rc;
+}
+EXPORT_SYMBOL_NS_GPL(__wrap_devm_cxl_enumerate_decoders, CXL);
+
int __wrap_devm_cxl_port_enumerate_dports(struct device *host,
struct cxl_port *port)
{
diff --git a/tools/testing/cxl/test/mock.h b/tools/testing/cxl/test/mock.h
index 99e7ff38090d..15e48063ea4b 100644
--- a/tools/testing/cxl/test/mock.h
+++ b/tools/testing/cxl/test/mock.h
@@ -21,6 +21,9 @@ struct cxl_mock_ops {
bool (*is_mock_dev)(struct device *dev);
int (*devm_cxl_port_enumerate_dports)(struct device *host,
struct cxl_port *port);
+ struct cxl_hdm *(*devm_cxl_setup_hdm)(struct device *host, struct cxl_port *port);
+ int (*devm_cxl_add_passthrough_decoder)(struct device *host, struct cxl_port *port);
+ int (*devm_cxl_enumerate_decoders)(struct device *host, struct cxl_hdm *hdm);
};
void register_cxl_mock_ops(struct cxl_mock_ops *ops);