// SPDX-License-Identifier: GPL-2.0-only
/*
 * Copyright (c) 2017, 2020 The Linux Foundation. All rights reserved.
 */

#include <linux/device.h>
#include <linux/module.h>
#include <linux/of.h>
#include <linux/of_platform.h>
#include <linux/nvmem-provider.h>
#include <linux/regmap.h>

#define SDAM_MEM_START			0x40
#define REGISTER_MAP_ID			0x40
#define REGISTER_MAP_VERSION		0x41
#define SDAM_SIZE			0x44
#define SDAM_PBS_TRIG_SET		0xE5
#define SDAM_PBS_TRIG_CLR		0xE6

struct sdam_chip {
	struct platform_device		*pdev;
	struct regmap			*regmap;
	struct nvmem_config		sdam_config;
	unsigned int			base;
	unsigned int			size;
};

/* read only register offsets */
static const u8 sdam_ro_map[] = {
	REGISTER_MAP_ID,
	REGISTER_MAP_VERSION,
	SDAM_SIZE
};

static bool sdam_is_valid(struct sdam_chip *sdam, unsigned int offset,
				size_t len)
{
	unsigned int sdam_mem_end = SDAM_MEM_START + sdam->size - 1;

	if (!len)
		return false;

	if (offset >= SDAM_MEM_START && offset <= sdam_mem_end
				&& (offset + len - 1) <= sdam_mem_end)
		return true;
	else if ((offset == SDAM_PBS_TRIG_SET || offset == SDAM_PBS_TRIG_CLR)
				&& (len == 1))
		return true;

	return false;
}

static bool sdam_is_ro(unsigned int offset, size_t len)
{
	int i;

	for (i = 0; i < ARRAY_SIZE(sdam_ro_map); i++)
		if (offset <= sdam_ro_map[i] && (offset + len) > sdam_ro_map[i])
			return true;

	return false;
}

static int sdam_read(void *priv, unsigned int offset, void *val,
				size_t bytes)
{
	struct sdam_chip *sdam = priv;
	struct device *dev = &sdam->pdev->dev;
	int rc;

	if (!sdam_is_valid(sdam, offset, bytes)) {
		dev_err(dev, "Invalid SDAM offset %#x len=%zd\n",
			offset, bytes);
		return -EINVAL;
	}

	rc = regmap_bulk_read(sdam->regmap, sdam->base + offset, val, bytes);
	if (rc < 0)
		dev_err(dev, "Failed to read SDAM offset %#x len=%zd, rc=%d\n",
						offset, bytes, rc);

	return rc;
}

static int sdam_write(void *priv, unsigned int offset, void *val,
				size_t bytes)
{
	struct sdam_chip *sdam = priv;
	struct device *dev = &sdam->pdev->dev;
	int rc;

	if (!sdam_is_valid(sdam, offset, bytes)) {
		dev_err(dev, "Invalid SDAM offset %#x len=%zd\n",
			offset, bytes);
		return -EINVAL;
	}

	if (sdam_is_ro(offset, bytes)) {
		dev_err(dev, "Invalid write offset %#x len=%zd\n",
			offset, bytes);
		return -EINVAL;
	}

	rc = regmap_bulk_write(sdam->regmap, sdam->base + offset, val, bytes);
	if (rc < 0)
		dev_err(dev, "Failed to write SDAM offset %#x len=%zd, rc=%d\n",
						offset, bytes, rc);

	return rc;
}

static int sdam_probe(struct platform_device *pdev)
{
	struct sdam_chip *sdam;
	struct nvmem_device *nvmem;
	unsigned int val;
	int rc;

	sdam = devm_kzalloc(&pdev->dev, sizeof(*sdam), GFP_KERNEL);
	if (!sdam)
		return -ENOMEM;

	sdam->regmap = dev_get_regmap(pdev->dev.parent, NULL);
	if (!sdam->regmap) {
		dev_err(&pdev->dev, "Failed to get regmap handle\n");
		return -ENXIO;
	}

	rc = of_property_read_u32(pdev->dev.of_node, "reg", &sdam->base);
	if (rc < 0) {
		dev_err(&pdev->dev, "Failed to get SDAM base, rc=%d\n", rc);
		return -EINVAL;
	}

	rc = regmap_read(sdam->regmap, sdam->base + SDAM_SIZE, &val);
	if (rc < 0) {
		dev_err(&pdev->dev, "Failed to read SDAM_SIZE rc=%d\n", rc);
		return -EINVAL;
	}
	sdam->size = val * 32;

	sdam->sdam_config.dev = &pdev->dev;
	sdam->sdam_config.name = "spmi_sdam";
	sdam->sdam_config.id = NVMEM_DEVID_AUTO;
	sdam->sdam_config.owner = THIS_MODULE,
	sdam->sdam_config.stride = 1;
	sdam->sdam_config.word_size = 1;
	sdam->sdam_config.reg_read = sdam_read;
	sdam->sdam_config.reg_write = sdam_write;
	sdam->sdam_config.priv = sdam;

	nvmem = devm_nvmem_register(&pdev->dev, &sdam->sdam_config);
	if (IS_ERR(nvmem)) {
		dev_err(&pdev->dev,
			"Failed to register SDAM nvmem device rc=%ld\n",
			PTR_ERR(nvmem));
		return -ENXIO;
	}
	dev_dbg(&pdev->dev,
		"SDAM base=%#x size=%u registered successfully\n",
		sdam->base, sdam->size);

	return 0;
}

static const struct of_device_id sdam_match_table[] = {
	{ .compatible = "qcom,spmi-sdam" },
	{},
};

static struct platform_driver sdam_driver = {
	.driver = {
		.name = "qcom,spmi-sdam",
		.of_match_table = sdam_match_table,
	},
	.probe		= sdam_probe,
};

static int __init sdam_init(void)
{
	return platform_driver_register(&sdam_driver);
}
subsys_initcall(sdam_init);

static void __exit sdam_exit(void)
{
	return platform_driver_unregister(&sdam_driver);
}
module_exit(sdam_exit);

MODULE_DESCRIPTION("QCOM SPMI SDAM driver");
MODULE_LICENSE("GPL v2");
