// SPDX-License-Identifier: GPL-2.0+
/*
 * Ingenic JZ47xx remoteproc driver
 * Copyright 2019, Paul Cercueil <paul@crapouillou.net>
 */

#include <linux/bitops.h>
#include <linux/clk.h>
#include <linux/err.h>
#include <linux/interrupt.h>
#include <linux/io.h>
#include <linux/module.h>
#include <linux/platform_device.h>
#include <linux/pm_runtime.h>
#include <linux/remoteproc.h>

#include "remoteproc_internal.h"

#define REG_AUX_CTRL		0x0
#define REG_AUX_MSG_ACK		0x10
#define REG_AUX_MSG		0x14
#define REG_CORE_MSG_ACK	0x18
#define REG_CORE_MSG		0x1C

#define AUX_CTRL_SLEEP		BIT(31)
#define AUX_CTRL_MSG_IRQ_EN	BIT(3)
#define AUX_CTRL_NMI_RESETS	BIT(2)
#define AUX_CTRL_NMI		BIT(1)
#define AUX_CTRL_SW_RESET	BIT(0)

struct vpu_mem_map {
	const char *name;
	unsigned int da;
};

struct vpu_mem_info {
	const struct vpu_mem_map *map;
	unsigned long len;
	void __iomem *base;
};

static const struct vpu_mem_map vpu_mem_map[] = {
	{ "tcsm0", 0x132b0000 },
	{ "tcsm1", 0xf4000000 },
	{ "sram",  0x132f0000 },
};

/**
 * struct vpu - Ingenic VPU remoteproc private structure
 * @irq: interrupt number
 * @clks: pointers to the VPU and AUX clocks
 * @aux_base: raw pointer to the AUX interface registers
 * @mem_info: array of struct vpu_mem_info, which contain the mapping info of
 *            each of the external memories
 * @dev: private pointer to the device
 */
struct vpu {
	int irq;
	struct clk_bulk_data clks[2];
	void __iomem *aux_base;
	struct vpu_mem_info mem_info[ARRAY_SIZE(vpu_mem_map)];
	struct device *dev;
};

static int ingenic_rproc_start(struct rproc *rproc)
{
	struct vpu *vpu = rproc->priv;
	u32 ctrl;

	enable_irq(vpu->irq);

	/* Reset the AUX and enable message IRQ */
	ctrl = AUX_CTRL_NMI_RESETS | AUX_CTRL_NMI | AUX_CTRL_MSG_IRQ_EN;
	writel(ctrl, vpu->aux_base + REG_AUX_CTRL);

	return 0;
}

static int ingenic_rproc_stop(struct rproc *rproc)
{
	struct vpu *vpu = rproc->priv;

	disable_irq(vpu->irq);

	/* Keep AUX in reset mode */
	writel(AUX_CTRL_SW_RESET, vpu->aux_base + REG_AUX_CTRL);

	return 0;
}

static void ingenic_rproc_kick(struct rproc *rproc, int vqid)
{
	struct vpu *vpu = rproc->priv;

	writel(vqid, vpu->aux_base + REG_CORE_MSG);
}

static void *ingenic_rproc_da_to_va(struct rproc *rproc, u64 da, size_t len)
{
	struct vpu *vpu = rproc->priv;
	void __iomem *va = NULL;
	unsigned int i;

	for (i = 0; i < ARRAY_SIZE(vpu_mem_map); i++) {
		const struct vpu_mem_info *info = &vpu->mem_info[i];
		const struct vpu_mem_map *map = info->map;

		if (da >= map->da && (da + len) < (map->da + info->len)) {
			va = info->base + (da - map->da);
			break;
		}
	}

	return (__force void *)va;
}

static struct rproc_ops ingenic_rproc_ops = {
	.start = ingenic_rproc_start,
	.stop = ingenic_rproc_stop,
	.kick = ingenic_rproc_kick,
	.da_to_va = ingenic_rproc_da_to_va,
};

static irqreturn_t vpu_interrupt(int irq, void *data)
{
	struct rproc *rproc = data;
	struct vpu *vpu = rproc->priv;
	u32 vring;

	vring = readl(vpu->aux_base + REG_AUX_MSG);

	/* Ack the interrupt */
	writel(0, vpu->aux_base + REG_AUX_MSG_ACK);

	return rproc_vq_interrupt(rproc, vring);
}

static void ingenic_rproc_disable_clks(void *data)
{
	struct vpu *vpu = data;

	pm_runtime_resume(vpu->dev);
	pm_runtime_disable(vpu->dev);

	clk_bulk_disable_unprepare(ARRAY_SIZE(vpu->clks), vpu->clks);
}

static int ingenic_rproc_probe(struct platform_device *pdev)
{
	struct device *dev = &pdev->dev;
	struct resource *mem;
	struct rproc *rproc;
	struct vpu *vpu;
	unsigned int i;
	int ret;

	rproc = devm_rproc_alloc(dev, "ingenic-vpu",
				 &ingenic_rproc_ops, NULL, sizeof(*vpu));
	if (!rproc)
		return -ENOMEM;

	vpu = rproc->priv;
	vpu->dev = &pdev->dev;
	platform_set_drvdata(pdev, vpu);

	mem = platform_get_resource_byname(pdev, IORESOURCE_MEM, "aux");
	vpu->aux_base = devm_ioremap_resource(dev, mem);
	if (IS_ERR(vpu->aux_base)) {
		dev_err(dev, "Failed to ioremap\n");
		return PTR_ERR(vpu->aux_base);
	}

	for (i = 0; i < ARRAY_SIZE(vpu_mem_map); i++) {
		mem = platform_get_resource_byname(pdev, IORESOURCE_MEM,
						   vpu_mem_map[i].name);

		vpu->mem_info[i].base = devm_ioremap_resource(dev, mem);
		if (IS_ERR(vpu->mem_info[i].base)) {
			ret = PTR_ERR(vpu->mem_info[i].base);
			dev_err(dev, "Failed to ioremap\n");
			return ret;
		}

		vpu->mem_info[i].len = resource_size(mem);
		vpu->mem_info[i].map = &vpu_mem_map[i];
	}

	vpu->clks[0].id = "vpu";
	vpu->clks[1].id = "aux";

	ret = devm_clk_bulk_get(dev, ARRAY_SIZE(vpu->clks), vpu->clks);
	if (ret) {
		dev_err(dev, "Failed to get clocks\n");
		return ret;
	}

	vpu->irq = platform_get_irq(pdev, 0);
	if (vpu->irq < 0)
		return vpu->irq;

	ret = devm_request_irq(dev, vpu->irq, vpu_interrupt, 0, "VPU", rproc);
	if (ret < 0) {
		dev_err(dev, "Failed to request IRQ\n");
		return ret;
	}

	disable_irq(vpu->irq);

	/* The clocks must be enabled for the firmware to be loaded in TCSM */
	ret = clk_bulk_prepare_enable(ARRAY_SIZE(vpu->clks), vpu->clks);
	if (ret) {
		dev_err(dev, "Unable to start clocks\n");
		return ret;
	}

	pm_runtime_irq_safe(dev);
	pm_runtime_set_active(dev);
	pm_runtime_enable(dev);
	pm_runtime_get_sync(dev);
	pm_runtime_use_autosuspend(dev);

	ret = devm_add_action_or_reset(dev, ingenic_rproc_disable_clks, vpu);
	if (ret) {
		dev_err(dev, "Unable to register action\n");
		goto out_pm_put;
	}

	ret = devm_rproc_add(dev, rproc);
	if (ret) {
		dev_err(dev, "Failed to register remote processor\n");
		goto out_pm_put;
	}

out_pm_put:
	pm_runtime_put_autosuspend(dev);

	return ret;
}

static const struct of_device_id ingenic_rproc_of_matches[] = {
	{ .compatible = "ingenic,jz4770-vpu-rproc", },
	{}
};
MODULE_DEVICE_TABLE(of, ingenic_rproc_of_matches);

static int __maybe_unused ingenic_rproc_suspend(struct device *dev)
{
	struct vpu *vpu = dev_get_drvdata(dev);

	clk_bulk_disable(ARRAY_SIZE(vpu->clks), vpu->clks);

	return 0;
}

static int __maybe_unused ingenic_rproc_resume(struct device *dev)
{
	struct vpu *vpu = dev_get_drvdata(dev);

	return clk_bulk_enable(ARRAY_SIZE(vpu->clks), vpu->clks);
}

static const struct dev_pm_ops __maybe_unused ingenic_rproc_pm = {
	SET_RUNTIME_PM_OPS(ingenic_rproc_suspend, ingenic_rproc_resume, NULL)
};

static struct platform_driver ingenic_rproc_driver = {
	.probe = ingenic_rproc_probe,
	.driver = {
		.name = "ingenic-vpu",
#ifdef CONFIG_PM
		.pm = &ingenic_rproc_pm,
#endif
		.of_match_table = ingenic_rproc_of_matches,
	},
};
module_platform_driver(ingenic_rproc_driver);

MODULE_LICENSE("GPL");
MODULE_AUTHOR("Paul Cercueil <paul@crapouillou.net>");
MODULE_DESCRIPTION("Ingenic JZ47xx Remote Processor control driver");
