// SPDX-License-Identifier: GPL-2.0
/*
 * Copyright (c) 2016, NVIDIA CORPORATION.
 */

#include <common.h>
#include <log.h>
#include <malloc.h>
#include <asm/io.h>
#include <dm.h>
#include <mailbox-uclass.h>
#include <dt-bindings/mailbox/tegra186-hsp.h>
#include <linux/bitops.h>

#define TEGRA_HSP_INT_DIMENSIONING		0x380
#define TEGRA_HSP_INT_DIMENSIONING_NSI_SHIFT	16
#define TEGRA_HSP_INT_DIMENSIONING_NSI_MASK	0xf
#define TEGRA_HSP_INT_DIMENSIONING_NDB_SHIFT	12
#define TEGRA_HSP_INT_DIMENSIONING_NDB_MASK	0xf
#define TEGRA_HSP_INT_DIMENSIONING_NAS_SHIFT	8
#define TEGRA_HSP_INT_DIMENSIONING_NAS_MASK	0xf
#define TEGRA_HSP_INT_DIMENSIONING_NSS_SHIFT	4
#define TEGRA_HSP_INT_DIMENSIONING_NSS_MASK	0xf
#define TEGRA_HSP_INT_DIMENSIONING_NSM_SHIFT	0
#define TEGRA_HSP_INT_DIMENSIONING_NSM_MASK	0xf

#define TEGRA_HSP_DB_REG_TRIGGER	0x0
#define TEGRA_HSP_DB_REG_ENABLE		0x4
#define TEGRA_HSP_DB_REG_RAW		0x8
#define TEGRA_HSP_DB_REG_PENDING	0xc

#define TEGRA_HSP_DB_ID_CCPLEX		1
#define TEGRA_HSP_DB_ID_BPMP		3
#define TEGRA_HSP_DB_ID_NUM		7

struct tegra_hsp {
	fdt_addr_t regs;
	uint32_t db_base;
};

static uint32_t *tegra_hsp_reg(struct tegra_hsp *thsp, uint32_t db_id,
			       uint32_t reg)
{
	return (uint32_t *)(thsp->regs + thsp->db_base + (db_id * 0x100) + reg);
}

static uint32_t tegra_hsp_readl(struct tegra_hsp *thsp, uint32_t db_id,
				uint32_t reg)
{
	uint32_t *r = tegra_hsp_reg(thsp, db_id, reg);
	return readl(r);
}

static void tegra_hsp_writel(struct tegra_hsp *thsp, uint32_t val,
			     uint32_t db_id, uint32_t reg)
{
	uint32_t *r = tegra_hsp_reg(thsp, db_id, reg);

	writel(val, r);
	readl(r);
}

static int tegra_hsp_db_id(ulong chan_id)
{
	switch (chan_id) {
	case (HSP_MBOX_TYPE_DB << 16) | HSP_DB_MASTER_BPMP:
		return TEGRA_HSP_DB_ID_BPMP;
	default:
		debug("Invalid channel ID\n");
		return -EINVAL;
	}
}

static int tegra_hsp_of_xlate(struct mbox_chan *chan,
			      struct ofnode_phandle_args *args)
{
	debug("%s(chan=%p)\n", __func__, chan);

	if (args->args_count != 2) {
		debug("Invaild args_count: %d\n", args->args_count);
		return -EINVAL;
	}

	chan->id = (args->args[0] << 16) | args->args[1];

	return 0;
}

static int tegra_hsp_request(struct mbox_chan *chan)
{
	int db_id;

	debug("%s(chan=%p)\n", __func__, chan);

	db_id = tegra_hsp_db_id(chan->id);
	if (db_id < 0) {
		debug("tegra_hsp_db_id() failed: %d\n", db_id);
		return -EINVAL;
	}

	return 0;
}

static int tegra_hsp_free(struct mbox_chan *chan)
{
	debug("%s(chan=%p)\n", __func__, chan);

	return 0;
}

static int tegra_hsp_send(struct mbox_chan *chan, const void *data)
{
	struct tegra_hsp *thsp = dev_get_priv(chan->dev);
	int db_id;

	debug("%s(chan=%p, data=%p)\n", __func__, chan, data);

	db_id = tegra_hsp_db_id(chan->id);
	tegra_hsp_writel(thsp, 1, db_id, TEGRA_HSP_DB_REG_TRIGGER);

	return 0;
}

static int tegra_hsp_recv(struct mbox_chan *chan, void *data)
{
	struct tegra_hsp *thsp = dev_get_priv(chan->dev);
	uint32_t db_id = TEGRA_HSP_DB_ID_CCPLEX;
	uint32_t val;

	debug("%s(chan=%p, data=%p)\n", __func__, chan, data);

	val = tegra_hsp_readl(thsp, db_id, TEGRA_HSP_DB_REG_RAW);
	if (!(val & BIT(chan->id)))
		return -ENODATA;

	tegra_hsp_writel(thsp, BIT(chan->id), db_id, TEGRA_HSP_DB_REG_RAW);

	return 0;
}

static int tegra_hsp_bind(struct udevice *dev)
{
	debug("%s(dev=%p)\n", __func__, dev);

	return 0;
}

static int tegra_hsp_probe(struct udevice *dev)
{
	struct tegra_hsp *thsp = dev_get_priv(dev);
	u32 val;
	int nr_sm, nr_ss, nr_as;

	debug("%s(dev=%p)\n", __func__, dev);

	thsp->regs = dev_read_addr(dev);
	if (thsp->regs == FDT_ADDR_T_NONE)
		return -ENODEV;

	val = readl(thsp->regs + TEGRA_HSP_INT_DIMENSIONING);
	nr_sm = (val >> TEGRA_HSP_INT_DIMENSIONING_NSM_SHIFT) &
		TEGRA_HSP_INT_DIMENSIONING_NSM_MASK;
	nr_ss = (val >> TEGRA_HSP_INT_DIMENSIONING_NSS_SHIFT) &
		TEGRA_HSP_INT_DIMENSIONING_NSS_MASK;
	nr_as = (val >> TEGRA_HSP_INT_DIMENSIONING_NAS_SHIFT) &
		TEGRA_HSP_INT_DIMENSIONING_NAS_MASK;

	thsp->db_base = (1 + (nr_sm >> 1) + nr_ss + nr_as) << 16;

	return 0;
}

static const struct udevice_id tegra_hsp_ids[] = {
	{ .compatible = "nvidia,tegra186-hsp" },
	{ }
};

struct mbox_ops tegra_hsp_mbox_ops = {
	.of_xlate = tegra_hsp_of_xlate,
	.request = tegra_hsp_request,
	.rfree = tegra_hsp_free,
	.send = tegra_hsp_send,
	.recv = tegra_hsp_recv,
};

U_BOOT_DRIVER(tegra_hsp) = {
	.name = "tegra-hsp",
	.id = UCLASS_MAILBOX,
	.of_match = tegra_hsp_ids,
	.bind = tegra_hsp_bind,
	.probe = tegra_hsp_probe,
	.priv_auto_alloc_size = sizeof(struct tegra_hsp),
	.ops = &tegra_hsp_mbox_ops,
};
