// SPDX-License-Identifier: GPL-2.0-only
/* Copyright(c) 2021 Intel Corporation. All rights reserved. */
#include <linux/platform_device.h>
#include <linux/module.h>
#include <linux/device.h>
#include <linux/kernel.h>
#include <linux/acpi.h>
#include <linux/pci.h>
#include <asm/div64.h>
#include "cxlpci.h"
#include "cxl.h"

#define CXL_RCRB_SIZE	SZ_8K

struct cxl_cxims_data {
	int nr_maps;
	u64 xormaps[];
};

/*
 * Find a targets entry (n) in the host bridge interleave list.
 * CXL Specification 3.0 Table 9-22
 */
static int cxl_xor_calc_n(u64 hpa, struct cxl_cxims_data *cximsd, int iw,
			  int ig)
{
	int i = 0, n = 0;
	u8 eiw;

	/* IW: 2,4,6,8,12,16 begin building 'n' using xormaps */
	if (iw != 3) {
		for (i = 0; i < cximsd->nr_maps; i++)
			n |= (hweight64(hpa & cximsd->xormaps[i]) & 1) << i;
	}
	/* IW: 3,6,12 add a modulo calculation to 'n' */
	if (!is_power_of_2(iw)) {
		if (ways_to_eiw(iw, &eiw))
			return -1;
		hpa &= GENMASK_ULL(51, eiw + ig);
		n |= do_div(hpa, 3) << i;
	}
	return n;
}

static struct cxl_dport *cxl_hb_xor(struct cxl_root_decoder *cxlrd, int pos)
{
	struct cxl_cxims_data *cximsd = cxlrd->platform_data;
	struct cxl_switch_decoder *cxlsd = &cxlrd->cxlsd;
	struct cxl_decoder *cxld = &cxlsd->cxld;
	int ig = cxld->interleave_granularity;
	int iw = cxld->interleave_ways;
	int n = 0;
	u64 hpa;

	if (dev_WARN_ONCE(&cxld->dev,
			  cxld->interleave_ways != cxlsd->nr_targets,
			  "misconfigured root decoder\n"))
		return NULL;

	hpa = cxlrd->res->start + pos * ig;

	/* Entry (n) is 0 for no interleave (iw == 1) */
	if (iw != 1)
		n = cxl_xor_calc_n(hpa, cximsd, iw, ig);

	if (n < 0)
		return NULL;

	return cxlrd->cxlsd.target[n];
}

struct cxl_cxims_context {
	struct device *dev;
	struct cxl_root_decoder *cxlrd;
};

static int cxl_parse_cxims(union acpi_subtable_headers *header, void *arg,
			   const unsigned long end)
{
	struct acpi_cedt_cxims *cxims = (struct acpi_cedt_cxims *)header;
	struct cxl_cxims_context *ctx = arg;
	struct cxl_root_decoder *cxlrd = ctx->cxlrd;
	struct cxl_decoder *cxld = &cxlrd->cxlsd.cxld;
	struct device *dev = ctx->dev;
	struct cxl_cxims_data *cximsd;
	unsigned int hbig, nr_maps;
	int rc;

	rc = eig_to_granularity(cxims->hbig, &hbig);
	if (rc)
		return rc;

	/* Does this CXIMS entry apply to the given CXL Window? */
	if (hbig != cxld->interleave_granularity)
		return 0;

	/* IW 1,3 do not use xormaps and skip this parsing entirely */
	if (is_power_of_2(cxld->interleave_ways))
		/* 2, 4, 8, 16 way */
		nr_maps = ilog2(cxld->interleave_ways);
	else
		/* 6, 12 way */
		nr_maps = ilog2(cxld->interleave_ways / 3);

	if (cxims->nr_xormaps < nr_maps) {
		dev_dbg(dev, "CXIMS nr_xormaps[%d] expected[%d]\n",
			cxims->nr_xormaps, nr_maps);
		return -ENXIO;
	}

	cximsd = devm_kzalloc(dev, struct_size(cximsd, xormaps, nr_maps),
			      GFP_KERNEL);
	if (!cximsd)
		return -ENOMEM;
	memcpy(cximsd->xormaps, cxims->xormap_list,
	       nr_maps * sizeof(*cximsd->xormaps));
	cximsd->nr_maps = nr_maps;
	cxlrd->platform_data = cximsd;

	return 0;
}

static unsigned long cfmws_to_decoder_flags(int restrictions)
{
	unsigned long flags = CXL_DECODER_F_ENABLE;

	if (restrictions & ACPI_CEDT_CFMWS_RESTRICT_TYPE2)
		flags |= CXL_DECODER_F_TYPE2;
	if (restrictions & ACPI_CEDT_CFMWS_RESTRICT_TYPE3)
		flags |= CXL_DECODER_F_TYPE3;
	if (restrictions & ACPI_CEDT_CFMWS_RESTRICT_VOLATILE)
		flags |= CXL_DECODER_F_RAM;
	if (restrictions & ACPI_CEDT_CFMWS_RESTRICT_PMEM)
		flags |= CXL_DECODER_F_PMEM;
	if (restrictions & ACPI_CEDT_CFMWS_RESTRICT_FIXED)
		flags |= CXL_DECODER_F_LOCK;

	return flags;
}

static int cxl_acpi_cfmws_verify(struct device *dev,
				 struct acpi_cedt_cfmws *cfmws)
{
	int rc, expected_len;
	unsigned int ways;

	if (cfmws->interleave_arithmetic != ACPI_CEDT_CFMWS_ARITHMETIC_MODULO &&
	    cfmws->interleave_arithmetic != ACPI_CEDT_CFMWS_ARITHMETIC_XOR) {
		dev_err(dev, "CFMWS Unknown Interleave Arithmetic: %d\n",
			cfmws->interleave_arithmetic);
		return -EINVAL;
	}

	if (!IS_ALIGNED(cfmws->base_hpa, SZ_256M)) {
		dev_err(dev, "CFMWS Base HPA not 256MB aligned\n");
		return -EINVAL;
	}

	if (!IS_ALIGNED(cfmws->window_size, SZ_256M)) {
		dev_err(dev, "CFMWS Window Size not 256MB aligned\n");
		return -EINVAL;
	}

	rc = eiw_to_ways(cfmws->interleave_ways, &ways);
	if (rc) {
		dev_err(dev, "CFMWS Interleave Ways (%d) invalid\n",
			cfmws->interleave_ways);
		return -EINVAL;
	}

	expected_len = struct_size(cfmws, interleave_targets, ways);

	if (cfmws->header.length < expected_len) {
		dev_err(dev, "CFMWS length %d less than expected %d\n",
			cfmws->header.length, expected_len);
		return -EINVAL;
	}

	if (cfmws->header.length > expected_len)
		dev_dbg(dev, "CFMWS length %d greater than expected %d\n",
			cfmws->header.length, expected_len);

	return 0;
}

/*
 * Note, @dev must be the first member, see 'struct cxl_chbs_context'
 * and mock_acpi_table_parse_cedt()
 */
struct cxl_cfmws_context {
	struct device *dev;
	struct cxl_port *root_port;
	struct resource *cxl_res;
	int id;
};

static int cxl_parse_cfmws(union acpi_subtable_headers *header, void *arg,
			   const unsigned long end)
{
	int target_map[CXL_DECODER_MAX_INTERLEAVE];
	struct cxl_cfmws_context *ctx = arg;
	struct cxl_port *root_port = ctx->root_port;
	struct resource *cxl_res = ctx->cxl_res;
	struct cxl_cxims_context cxims_ctx;
	struct cxl_root_decoder *cxlrd;
	struct device *dev = ctx->dev;
	struct acpi_cedt_cfmws *cfmws;
	cxl_calc_hb_fn cxl_calc_hb;
	struct cxl_decoder *cxld;
	unsigned int ways, i, ig;
	struct resource *res;
	int rc;

	cfmws = (struct acpi_cedt_cfmws *) header;

	rc = cxl_acpi_cfmws_verify(dev, cfmws);
	if (rc) {
		dev_err(dev, "CFMWS range %#llx-%#llx not registered\n",
			cfmws->base_hpa,
			cfmws->base_hpa + cfmws->window_size - 1);
		return 0;
	}

	rc = eiw_to_ways(cfmws->interleave_ways, &ways);
	if (rc)
		return rc;
	rc = eig_to_granularity(cfmws->granularity, &ig);
	if (rc)
		return rc;
	for (i = 0; i < ways; i++)
		target_map[i] = cfmws->interleave_targets[i];

	res = kzalloc(sizeof(*res), GFP_KERNEL);
	if (!res)
		return -ENOMEM;

	res->name = kasprintf(GFP_KERNEL, "CXL Window %d", ctx->id++);
	if (!res->name)
		goto err_name;

	res->start = cfmws->base_hpa;
	res->end = cfmws->base_hpa + cfmws->window_size - 1;
	res->flags = IORESOURCE_MEM;

	/* add to the local resource tracking to establish a sort order */
	rc = insert_resource(cxl_res, res);
	if (rc)
		goto err_insert;

	if (cfmws->interleave_arithmetic == ACPI_CEDT_CFMWS_ARITHMETIC_MODULO)
		cxl_calc_hb = cxl_hb_modulo;
	else
		cxl_calc_hb = cxl_hb_xor;

	cxlrd = cxl_root_decoder_alloc(root_port, ways, cxl_calc_hb);
	if (IS_ERR(cxlrd))
		return 0;

	cxld = &cxlrd->cxlsd.cxld;
	cxld->flags = cfmws_to_decoder_flags(cfmws->restrictions);
	cxld->target_type = CXL_DECODER_EXPANDER;
	cxld->hpa_range = (struct range) {
		.start = res->start,
		.end = res->end,
	};
	cxld->interleave_ways = ways;
	/*
	 * Minimize the x1 granularity to advertise support for any
	 * valid region granularity
	 */
	if (ways == 1)
		ig = CXL_DECODER_MIN_GRANULARITY;
	cxld->interleave_granularity = ig;

	if (cfmws->interleave_arithmetic == ACPI_CEDT_CFMWS_ARITHMETIC_XOR) {
		if (ways != 1 && ways != 3) {
			cxims_ctx = (struct cxl_cxims_context) {
				.dev = dev,
				.cxlrd = cxlrd,
			};
			rc = acpi_table_parse_cedt(ACPI_CEDT_TYPE_CXIMS,
						   cxl_parse_cxims, &cxims_ctx);
			if (rc < 0)
				goto err_xormap;
			if (!cxlrd->platform_data) {
				dev_err(dev, "No CXIMS for HBIG %u\n", ig);
				rc = -EINVAL;
				goto err_xormap;
			}
		}
	}
	rc = cxl_decoder_add(cxld, target_map);
err_xormap:
	if (rc)
		put_device(&cxld->dev);
	else
		rc = cxl_decoder_autoremove(dev, cxld);
	if (rc) {
		dev_err(dev, "Failed to add decode range [%#llx - %#llx]\n",
			cxld->hpa_range.start, cxld->hpa_range.end);
		return 0;
	}
	dev_dbg(dev, "add: %s node: %d range [%#llx - %#llx]\n",
		dev_name(&cxld->dev),
		phys_to_target_node(cxld->hpa_range.start),
		cxld->hpa_range.start, cxld->hpa_range.end);

	return 0;

err_insert:
	kfree(res->name);
err_name:
	kfree(res);
	return -ENOMEM;
}

__mock struct acpi_device *to_cxl_host_bridge(struct device *host,
					      struct device *dev)
{
	struct acpi_device *adev = to_acpi_device(dev);

	if (!acpi_pci_find_root(adev->handle))
		return NULL;

	if (strcmp(acpi_device_hid(adev), "ACPI0016") == 0)
		return adev;
	return NULL;
}

/*
 * A host bridge is a dport to a CFMWS decode and it is a uport to the
 * dport (PCIe Root Ports) in the host bridge.
 */
static int add_host_bridge_uport(struct device *match, void *arg)
{
	struct cxl_port *root_port = arg;
	struct device *host = root_port->dev.parent;
	struct acpi_device *hb = to_cxl_host_bridge(host, match);
	struct acpi_pci_root *pci_root;
	struct cxl_dport *dport;
	struct cxl_port *port;
	struct device *bridge;
	int rc;

	if (!hb)
		return 0;

	pci_root = acpi_pci_find_root(hb->handle);
	bridge = pci_root->bus->bridge;
	dport = cxl_find_dport_by_dev(root_port, bridge);
	if (!dport) {
		dev_dbg(host, "host bridge expected and not found\n");
		return 0;
	}

	if (dport->rch) {
		dev_info(bridge, "host supports CXL (restricted)\n");
		return 0;
	}

	rc = devm_cxl_register_pci_bus(host, bridge, pci_root->bus);
	if (rc)
		return rc;

	port = devm_cxl_add_port(host, bridge, dport->component_reg_phys,
				 dport);
	if (IS_ERR(port))
		return PTR_ERR(port);

	dev_info(bridge, "host supports CXL\n");

	return 0;
}

struct cxl_chbs_context {
	struct device *dev;
	unsigned long long uid;
	resource_size_t rcrb;
	resource_size_t chbcr;
	u32 cxl_version;
};

static int cxl_get_chbcr(union acpi_subtable_headers *header, void *arg,
			 const unsigned long end)
{
	struct cxl_chbs_context *ctx = arg;
	struct acpi_cedt_chbs *chbs;

	if (ctx->chbcr)
		return 0;

	chbs = (struct acpi_cedt_chbs *) header;

	if (ctx->uid != chbs->uid)
		return 0;

	ctx->cxl_version = chbs->cxl_version;
	ctx->rcrb = CXL_RESOURCE_NONE;
	ctx->chbcr = CXL_RESOURCE_NONE;

	if (!chbs->base)
		return 0;

	if (chbs->cxl_version != ACPI_CEDT_CHBS_VERSION_CXL11) {
		ctx->chbcr = chbs->base;
		return 0;
	}

	if (chbs->length != CXL_RCRB_SIZE)
		return 0;

	ctx->rcrb = chbs->base;
	ctx->chbcr = cxl_rcrb_to_component(ctx->dev, chbs->base,
					   CXL_RCRB_DOWNSTREAM);

	return 0;
}

static int add_host_bridge_dport(struct device *match, void *arg)
{
	acpi_status rc;
	struct device *bridge;
	unsigned long long uid;
	struct cxl_dport *dport;
	struct cxl_chbs_context ctx;
	struct acpi_pci_root *pci_root;
	struct cxl_port *root_port = arg;
	struct device *host = root_port->dev.parent;
	struct acpi_device *hb = to_cxl_host_bridge(host, match);

	if (!hb)
		return 0;

	rc = acpi_evaluate_integer(hb->handle, METHOD_NAME__UID, NULL, &uid);
	if (rc != AE_OK) {
		dev_err(match, "unable to retrieve _UID\n");
		return -ENODEV;
	}

	dev_dbg(match, "UID found: %lld\n", uid);

	ctx = (struct cxl_chbs_context) {
		.dev = match,
		.uid = uid,
	};
	acpi_table_parse_cedt(ACPI_CEDT_TYPE_CHBS, cxl_get_chbcr, &ctx);

	if (!ctx.chbcr) {
		dev_warn(match, "No CHBS found for Host Bridge (UID %lld)\n",
			 uid);
		return 0;
	}

	if (ctx.rcrb != CXL_RESOURCE_NONE)
		dev_dbg(match, "RCRB found for UID %lld: %pa\n", uid, &ctx.rcrb);

	if (ctx.chbcr == CXL_RESOURCE_NONE) {
		dev_warn(match, "CHBCR invalid for Host Bridge (UID %lld)\n",
			 uid);
		return 0;
	}

	dev_dbg(match, "CHBCR found: %pa\n", &ctx.chbcr);

	pci_root = acpi_pci_find_root(hb->handle);
	bridge = pci_root->bus->bridge;
	if (ctx.cxl_version == ACPI_CEDT_CHBS_VERSION_CXL11)
		dport = devm_cxl_add_rch_dport(root_port, bridge, uid,
					       ctx.chbcr, ctx.rcrb);
	else
		dport = devm_cxl_add_dport(root_port, bridge, uid,
					   ctx.chbcr);
	if (IS_ERR(dport))
		return PTR_ERR(dport);

	return 0;
}

static int add_root_nvdimm_bridge(struct device *match, void *data)
{
	struct cxl_decoder *cxld;
	struct cxl_port *root_port = data;
	struct cxl_nvdimm_bridge *cxl_nvb;
	struct device *host = root_port->dev.parent;

	if (!is_root_decoder(match))
		return 0;

	cxld = to_cxl_decoder(match);
	if (!(cxld->flags & CXL_DECODER_F_PMEM))
		return 0;

	cxl_nvb = devm_cxl_add_nvdimm_bridge(host, root_port);
	if (IS_ERR(cxl_nvb)) {
		dev_dbg(host, "failed to register pmem\n");
		return PTR_ERR(cxl_nvb);
	}
	dev_dbg(host, "%s: add: %s\n", dev_name(&root_port->dev),
		dev_name(&cxl_nvb->dev));
	return 1;
}

static struct lock_class_key cxl_root_key;

static void cxl_acpi_lock_reset_class(void *dev)
{
	device_lock_reset_class(dev);
}

static void del_cxl_resource(struct resource *res)
{
	kfree(res->name);
	kfree(res);
}

static void cxl_set_public_resource(struct resource *priv, struct resource *pub)
{
	priv->desc = (unsigned long) pub;
}

static struct resource *cxl_get_public_resource(struct resource *priv)
{
	return (struct resource *) priv->desc;
}

static void remove_cxl_resources(void *data)
{
	struct resource *res, *next, *cxl = data;

	for (res = cxl->child; res; res = next) {
		struct resource *victim = cxl_get_public_resource(res);

		next = res->sibling;
		remove_resource(res);

		if (victim) {
			remove_resource(victim);
			kfree(victim);
		}

		del_cxl_resource(res);
	}
}

/**
 * add_cxl_resources() - reflect CXL fixed memory windows in iomem_resource
 * @cxl_res: A standalone resource tree where each CXL window is a sibling
 *
 * Walk each CXL window in @cxl_res and add it to iomem_resource potentially
 * expanding its boundaries to ensure that any conflicting resources become
 * children. If a window is expanded it may then conflict with a another window
 * entry and require the window to be truncated or trimmed. Consider this
 * situation:
 *
 * |-- "CXL Window 0" --||----- "CXL Window 1" -----|
 * |--------------- "System RAM" -------------|
 *
 * ...where platform firmware has established as System RAM resource across 2
 * windows, but has left some portion of window 1 for dynamic CXL region
 * provisioning. In this case "Window 0" will span the entirety of the "System
 * RAM" span, and "CXL Window 1" is truncated to the remaining tail past the end
 * of that "System RAM" resource.
 */
static int add_cxl_resources(struct resource *cxl_res)
{
	struct resource *res, *new, *next;

	for (res = cxl_res->child; res; res = next) {
		new = kzalloc(sizeof(*new), GFP_KERNEL);
		if (!new)
			return -ENOMEM;
		new->name = res->name;
		new->start = res->start;
		new->end = res->end;
		new->flags = IORESOURCE_MEM;
		new->desc = IORES_DESC_CXL;

		/*
		 * Record the public resource in the private cxl_res tree for
		 * later removal.
		 */
		cxl_set_public_resource(res, new);

		insert_resource_expand_to_fit(&iomem_resource, new);

		next = res->sibling;
		while (next && resource_overlaps(new, next)) {
			if (resource_contains(new, next)) {
				struct resource *_next = next->sibling;

				remove_resource(next);
				del_cxl_resource(next);
				next = _next;
			} else
				next->start = new->end + 1;
		}
	}
	return 0;
}

static int pair_cxl_resource(struct device *dev, void *data)
{
	struct resource *cxl_res = data;
	struct resource *p;

	if (!is_root_decoder(dev))
		return 0;

	for (p = cxl_res->child; p; p = p->sibling) {
		struct cxl_root_decoder *cxlrd = to_cxl_root_decoder(dev);
		struct cxl_decoder *cxld = &cxlrd->cxlsd.cxld;
		struct resource res = {
			.start = cxld->hpa_range.start,
			.end = cxld->hpa_range.end,
			.flags = IORESOURCE_MEM,
		};

		if (resource_contains(p, &res)) {
			cxlrd->res = cxl_get_public_resource(p);
			break;
		}
	}

	return 0;
}

static int cxl_acpi_probe(struct platform_device *pdev)
{
	int rc;
	struct resource *cxl_res;
	struct cxl_port *root_port;
	struct device *host = &pdev->dev;
	struct acpi_device *adev = ACPI_COMPANION(host);
	struct cxl_cfmws_context ctx;

	device_lock_set_class(&pdev->dev, &cxl_root_key);
	rc = devm_add_action_or_reset(&pdev->dev, cxl_acpi_lock_reset_class,
				      &pdev->dev);
	if (rc)
		return rc;

	cxl_res = devm_kzalloc(host, sizeof(*cxl_res), GFP_KERNEL);
	if (!cxl_res)
		return -ENOMEM;
	cxl_res->name = "CXL mem";
	cxl_res->start = 0;
	cxl_res->end = -1;
	cxl_res->flags = IORESOURCE_MEM;

	root_port = devm_cxl_add_port(host, host, CXL_RESOURCE_NONE, NULL);
	if (IS_ERR(root_port))
		return PTR_ERR(root_port);

	rc = bus_for_each_dev(adev->dev.bus, NULL, root_port,
			      add_host_bridge_dport);
	if (rc < 0)
		return rc;

	rc = devm_add_action_or_reset(host, remove_cxl_resources, cxl_res);
	if (rc)
		return rc;

	ctx = (struct cxl_cfmws_context) {
		.dev = host,
		.root_port = root_port,
		.cxl_res = cxl_res,
	};
	rc = acpi_table_parse_cedt(ACPI_CEDT_TYPE_CFMWS, cxl_parse_cfmws, &ctx);
	if (rc < 0)
		return -ENXIO;

	rc = add_cxl_resources(cxl_res);
	if (rc)
		return rc;

	/*
	 * Populate the root decoders with their related iomem resource,
	 * if present
	 */
	device_for_each_child(&root_port->dev, cxl_res, pair_cxl_resource);

	/*
	 * Root level scanned with host-bridge as dports, now scan host-bridges
	 * for their role as CXL uports to their CXL-capable PCIe Root Ports.
	 */
	rc = bus_for_each_dev(adev->dev.bus, NULL, root_port,
			      add_host_bridge_uport);
	if (rc < 0)
		return rc;

	if (IS_ENABLED(CONFIG_CXL_PMEM))
		rc = device_for_each_child(&root_port->dev, root_port,
					   add_root_nvdimm_bridge);
	if (rc < 0)
		return rc;

	/* In case PCI is scanned before ACPI re-trigger memdev attach */
	cxl_bus_rescan();
	return 0;
}

static const struct acpi_device_id cxl_acpi_ids[] = {
	{ "ACPI0017" },
	{ },
};
MODULE_DEVICE_TABLE(acpi, cxl_acpi_ids);

static const struct platform_device_id cxl_test_ids[] = {
	{ "cxl_acpi" },
	{ },
};
MODULE_DEVICE_TABLE(platform, cxl_test_ids);

static struct platform_driver cxl_acpi_driver = {
	.probe = cxl_acpi_probe,
	.driver = {
		.name = KBUILD_MODNAME,
		.acpi_match_table = cxl_acpi_ids,
	},
	.id_table = cxl_test_ids,
};

static int __init cxl_acpi_init(void)
{
	return platform_driver_register(&cxl_acpi_driver);
}

static void __exit cxl_acpi_exit(void)
{
	platform_driver_unregister(&cxl_acpi_driver);
	cxl_bus_drain();
}

/* load before dax_hmem sees 'Soft Reserved' CXL ranges */
subsys_initcall(cxl_acpi_init);
module_exit(cxl_acpi_exit);
MODULE_LICENSE("GPL v2");
MODULE_IMPORT_NS(CXL);
MODULE_IMPORT_NS(ACPI);
