// SPDX-License-Identifier: GPL-2.0
/*
 * LiteX LiteSDCard driver
 *
 * Copyright (C) 2019-2020 Antmicro <contact@antmicro.com>
 * Copyright (C) 2019-2020 Kamil Rakoczy <krakoczy@antmicro.com>
 * Copyright (C) 2019-2020 Maciej Dudek <mdudek@internships.antmicro.com>
 * Copyright (C) 2020 Paul Mackerras <paulus@ozlabs.org>
 * Copyright (C) 2020-2022 Gabriel Somlo <gsomlo@gmail.com>
 */

#include <linux/bits.h>
#include <linux/clk.h>
#include <linux/delay.h>
#include <linux/dma-mapping.h>
#include <linux/interrupt.h>
#include <linux/iopoll.h>
#include <linux/litex.h>
#include <linux/mod_devicetable.h>
#include <linux/module.h>
#include <linux/platform_device.h>

#include <linux/mmc/host.h>
#include <linux/mmc/mmc.h>
#include <linux/mmc/sd.h>

#define LITEX_PHY_CARDDETECT  0x00
#define LITEX_PHY_CLOCKERDIV  0x04
#define LITEX_PHY_INITIALIZE  0x08
#define LITEX_PHY_WRITESTATUS 0x0C
#define LITEX_CORE_CMDARG     0x00
#define LITEX_CORE_CMDCMD     0x04
#define LITEX_CORE_CMDSND     0x08
#define LITEX_CORE_CMDRSP     0x0C
#define LITEX_CORE_CMDEVT     0x1C
#define LITEX_CORE_DATEVT     0x20
#define LITEX_CORE_BLKLEN     0x24
#define LITEX_CORE_BLKCNT     0x28
#define LITEX_BLK2MEM_BASE    0x00
#define LITEX_BLK2MEM_LEN     0x08
#define LITEX_BLK2MEM_ENA     0x0C
#define LITEX_BLK2MEM_DONE    0x10
#define LITEX_BLK2MEM_LOOP    0x14
#define LITEX_MEM2BLK_BASE    0x00
#define LITEX_MEM2BLK_LEN     0x08
#define LITEX_MEM2BLK_ENA     0x0C
#define LITEX_MEM2BLK_DONE    0x10
#define LITEX_MEM2BLK_LOOP    0x14
#define LITEX_MEM2BLK         0x18
#define LITEX_IRQ_STATUS      0x00
#define LITEX_IRQ_PENDING     0x04
#define LITEX_IRQ_ENABLE      0x08

#define SD_CTL_DATA_XFER_NONE  0
#define SD_CTL_DATA_XFER_READ  1
#define SD_CTL_DATA_XFER_WRITE 2

#define SD_CTL_RESP_NONE       0
#define SD_CTL_RESP_SHORT      1
#define SD_CTL_RESP_LONG       2
#define SD_CTL_RESP_SHORT_BUSY 3

#define SD_BIT_DONE    BIT(0)
#define SD_BIT_WR_ERR  BIT(1)
#define SD_BIT_TIMEOUT BIT(2)
#define SD_BIT_CRC_ERR BIT(3)

#define SD_SLEEP_US       5
#define SD_TIMEOUT_US 20000

#define SDIRQ_CARD_DETECT    1
#define SDIRQ_SD_TO_MEM_DONE 2
#define SDIRQ_MEM_TO_SD_DONE 4
#define SDIRQ_CMD_DONE       8

struct litex_mmc_host {
	struct mmc_host *mmc;

	void __iomem *sdphy;
	void __iomem *sdcore;
	void __iomem *sdreader;
	void __iomem *sdwriter;
	void __iomem *sdirq;

	void *buffer;
	size_t buf_size;
	dma_addr_t dma;

	struct completion cmd_done;
	int irq;

	unsigned int ref_clk;
	unsigned int sd_clk;

	u32 resp[4];
	u16 rca;

	bool is_bus_width_set;
	bool app_cmd;
};

static int litex_mmc_sdcard_wait_done(void __iomem *reg, struct device *dev)
{
	u8 evt;
	int ret;

	ret = readx_poll_timeout(litex_read8, reg, evt, evt & SD_BIT_DONE,
				 SD_SLEEP_US, SD_TIMEOUT_US);
	if (ret)
		return ret;
	if (evt == SD_BIT_DONE)
		return 0;
	if (evt & SD_BIT_WR_ERR)
		return -EIO;
	if (evt & SD_BIT_TIMEOUT)
		return -ETIMEDOUT;
	if (evt & SD_BIT_CRC_ERR)
		return -EILSEQ;
	dev_err(dev, "%s: unknown error (evt=%x)\n", __func__, evt);
	return -EINVAL;
}

static int litex_mmc_send_cmd(struct litex_mmc_host *host,
			      u8 cmd, u32 arg, u8 response_len, u8 transfer)
{
	struct device *dev = mmc_dev(host->mmc);
	void __iomem *reg;
	int ret;
	u8 evt;

	litex_write32(host->sdcore + LITEX_CORE_CMDARG, arg);
	litex_write32(host->sdcore + LITEX_CORE_CMDCMD,
		      cmd << 8 | transfer << 5 | response_len);
	litex_write8(host->sdcore + LITEX_CORE_CMDSND, 1);

	/*
	 * Wait for an interrupt if we have an interrupt and either there is
	 * data to be transferred, or if the card can report busy via DAT0.
	 */
	if (host->irq > 0 &&
	    (transfer != SD_CTL_DATA_XFER_NONE ||
	     response_len == SD_CTL_RESP_SHORT_BUSY)) {
		reinit_completion(&host->cmd_done);
		litex_write32(host->sdirq + LITEX_IRQ_ENABLE,
			      SDIRQ_CMD_DONE | SDIRQ_CARD_DETECT);
		wait_for_completion(&host->cmd_done);
	}

	ret = litex_mmc_sdcard_wait_done(host->sdcore + LITEX_CORE_CMDEVT, dev);
	if (ret) {
		dev_err(dev, "Command (cmd %d) error, status %d\n", cmd, ret);
		return ret;
	}

	if (response_len != SD_CTL_RESP_NONE) {
		/*
		 * NOTE: this matches the semantics of litex_read32()
		 * regardless of underlying arch endianness!
		 */
		memcpy_fromio(host->resp,
			      host->sdcore + LITEX_CORE_CMDRSP, 0x10);
	}

	if (!host->app_cmd && cmd == SD_SEND_RELATIVE_ADDR)
		host->rca = (host->resp[3] >> 16);

	host->app_cmd = (cmd == MMC_APP_CMD);

	if (transfer == SD_CTL_DATA_XFER_NONE)
		return ret; /* OK from prior litex_mmc_sdcard_wait_done() */

	ret = litex_mmc_sdcard_wait_done(host->sdcore + LITEX_CORE_DATEVT, dev);
	if (ret) {
		dev_err(dev, "Data xfer (cmd %d) error, status %d\n", cmd, ret);
		return ret;
	}

	/* Wait for completion of (read or write) DMA transfer */
	reg = (transfer == SD_CTL_DATA_XFER_READ) ?
		host->sdreader + LITEX_BLK2MEM_DONE :
		host->sdwriter + LITEX_MEM2BLK_DONE;
	ret = readx_poll_timeout(litex_read8, reg, evt, evt & SD_BIT_DONE,
				 SD_SLEEP_US, SD_TIMEOUT_US);
	if (ret)
		dev_err(dev, "DMA timeout (cmd %d)\n", cmd);

	return ret;
}

static int litex_mmc_send_app_cmd(struct litex_mmc_host *host)
{
	return litex_mmc_send_cmd(host, MMC_APP_CMD, host->rca << 16,
				  SD_CTL_RESP_SHORT, SD_CTL_DATA_XFER_NONE);
}

static int litex_mmc_send_set_bus_w_cmd(struct litex_mmc_host *host, u32 width)
{
	return litex_mmc_send_cmd(host, SD_APP_SET_BUS_WIDTH, width,
				  SD_CTL_RESP_SHORT, SD_CTL_DATA_XFER_NONE);
}

static int litex_mmc_set_bus_width(struct litex_mmc_host *host)
{
	bool app_cmd_sent;
	int ret;

	if (host->is_bus_width_set)
		return 0;

	/* Ensure 'app_cmd' precedes 'app_set_bus_width_cmd' */
	app_cmd_sent = host->app_cmd; /* was preceding command app_cmd? */
	if (!app_cmd_sent) {
		ret = litex_mmc_send_app_cmd(host);
		if (ret)
			return ret;
	}

	/* LiteSDCard only supports 4-bit bus width */
	ret = litex_mmc_send_set_bus_w_cmd(host, MMC_BUS_WIDTH_4);
	if (ret)
		return ret;

	/* Re-send 'app_cmd' if necessary */
	if (app_cmd_sent) {
		ret = litex_mmc_send_app_cmd(host);
		if (ret)
			return ret;
	}

	host->is_bus_width_set = true;

	return 0;
}

static int litex_mmc_get_cd(struct mmc_host *mmc)
{
	struct litex_mmc_host *host = mmc_priv(mmc);
	int ret;

	if (!mmc_card_is_removable(mmc))
		return 1;

	ret = !litex_read8(host->sdphy + LITEX_PHY_CARDDETECT);
	if (ret)
		return ret;

	/* Ensure bus width will be set (again) upon card (re)insertion */
	host->is_bus_width_set = false;

	return 0;
}

static irqreturn_t litex_mmc_interrupt(int irq, void *arg)
{
	struct mmc_host *mmc = arg;
	struct litex_mmc_host *host = mmc_priv(mmc);
	u32 pending = litex_read32(host->sdirq + LITEX_IRQ_PENDING);
	irqreturn_t ret = IRQ_NONE;

	/* Check for card change interrupt */
	if (pending & SDIRQ_CARD_DETECT) {
		litex_write32(host->sdirq + LITEX_IRQ_PENDING,
			      SDIRQ_CARD_DETECT);
		mmc_detect_change(mmc, msecs_to_jiffies(10));
		ret = IRQ_HANDLED;
	}

	/* Check for command completed */
	if (pending & SDIRQ_CMD_DONE) {
		/* Disable it so it doesn't keep interrupting */
		litex_write32(host->sdirq + LITEX_IRQ_ENABLE,
			      SDIRQ_CARD_DETECT);
		complete(&host->cmd_done);
		ret = IRQ_HANDLED;
	}

	return ret;
}

static u32 litex_mmc_response_len(struct mmc_command *cmd)
{
	if (cmd->flags & MMC_RSP_136)
		return SD_CTL_RESP_LONG;
	if (!(cmd->flags & MMC_RSP_PRESENT))
		return SD_CTL_RESP_NONE;
	if (cmd->flags & MMC_RSP_BUSY)
		return SD_CTL_RESP_SHORT_BUSY;
	return SD_CTL_RESP_SHORT;
}

static void litex_mmc_do_dma(struct litex_mmc_host *host, struct mmc_data *data,
			     unsigned int *len, bool *direct, u8 *transfer)
{
	struct device *dev = mmc_dev(host->mmc);
	dma_addr_t dma;
	int sg_count;

	/*
	 * Try to DMA directly to/from the data buffer.
	 * We can do that if the buffer can be mapped for DMA
	 * in one contiguous chunk.
	 */
	dma = host->dma;
	*len = data->blksz * data->blocks;
	sg_count = dma_map_sg(dev, data->sg, data->sg_len,
			      mmc_get_dma_dir(data));
	if (sg_count == 1) {
		dma = sg_dma_address(data->sg);
		*len = sg_dma_len(data->sg);
		*direct = true;
	} else if (*len > host->buf_size)
		*len = host->buf_size;

	if (data->flags & MMC_DATA_READ) {
		litex_write8(host->sdreader + LITEX_BLK2MEM_ENA, 0);
		litex_write64(host->sdreader + LITEX_BLK2MEM_BASE, dma);
		litex_write32(host->sdreader + LITEX_BLK2MEM_LEN, *len);
		litex_write8(host->sdreader + LITEX_BLK2MEM_ENA, 1);
		*transfer = SD_CTL_DATA_XFER_READ;
	} else if (data->flags & MMC_DATA_WRITE) {
		if (!*direct)
			sg_copy_to_buffer(data->sg, data->sg_len,
					  host->buffer, *len);
		litex_write8(host->sdwriter + LITEX_MEM2BLK_ENA, 0);
		litex_write64(host->sdwriter + LITEX_MEM2BLK_BASE, dma);
		litex_write32(host->sdwriter + LITEX_MEM2BLK_LEN, *len);
		litex_write8(host->sdwriter + LITEX_MEM2BLK_ENA, 1);
		*transfer = SD_CTL_DATA_XFER_WRITE;
	} else {
		dev_warn(dev, "Data present w/o read or write flag.\n");
		/* Continue: set cmd status, mark req done */
	}

	litex_write16(host->sdcore + LITEX_CORE_BLKLEN, data->blksz);
	litex_write32(host->sdcore + LITEX_CORE_BLKCNT, data->blocks);
}

static void litex_mmc_request(struct mmc_host *mmc, struct mmc_request *mrq)
{
	struct litex_mmc_host *host = mmc_priv(mmc);
	struct device *dev = mmc_dev(mmc);
	struct mmc_command *cmd = mrq->cmd;
	struct mmc_command *sbc = mrq->sbc;
	struct mmc_data *data = mrq->data;
	struct mmc_command *stop = mrq->stop;
	unsigned int retries = cmd->retries;
	unsigned int len = 0;
	bool direct = false;
	u32 response_len = litex_mmc_response_len(cmd);
	u8 transfer = SD_CTL_DATA_XFER_NONE;

	/* First check that the card is still there */
	if (!litex_mmc_get_cd(mmc)) {
		cmd->error = -ENOMEDIUM;
		mmc_request_done(mmc, mrq);
		return;
	}

	/* Send set-block-count command if needed */
	if (sbc) {
		sbc->error = litex_mmc_send_cmd(host, sbc->opcode, sbc->arg,
						litex_mmc_response_len(sbc),
						SD_CTL_DATA_XFER_NONE);
		if (sbc->error) {
			host->is_bus_width_set = false;
			mmc_request_done(mmc, mrq);
			return;
		}
	}

	if (data) {
		/*
		 * LiteSDCard only supports 4-bit bus width; therefore, we MUST
		 * inject a SET_BUS_WIDTH (acmd6) before the very first data
		 * transfer, earlier than when the mmc subsystem would normally
		 * get around to it!
		 */
		cmd->error = litex_mmc_set_bus_width(host);
		if (cmd->error) {
			dev_err(dev, "Can't set bus width!\n");
			mmc_request_done(mmc, mrq);
			return;
		}

		litex_mmc_do_dma(host, data, &len, &direct, &transfer);
	}

	do {
		cmd->error = litex_mmc_send_cmd(host, cmd->opcode, cmd->arg,
						response_len, transfer);
	} while (cmd->error && retries-- > 0);

	if (cmd->error) {
		/* Card may be gone; don't assume bus width is still set */
		host->is_bus_width_set = false;
	}

	if (response_len == SD_CTL_RESP_SHORT) {
		/* Pull short response fields from appropriate host registers */
		cmd->resp[0] = host->resp[3];
		cmd->resp[1] = host->resp[2] & 0xFF;
	} else if (response_len == SD_CTL_RESP_LONG) {
		cmd->resp[0] = host->resp[0];
		cmd->resp[1] = host->resp[1];
		cmd->resp[2] = host->resp[2];
		cmd->resp[3] = host->resp[3];
	}

	/* Send stop-transmission command if required */
	if (stop && (cmd->error || !sbc)) {
		stop->error = litex_mmc_send_cmd(host, stop->opcode, stop->arg,
						 litex_mmc_response_len(stop),
						 SD_CTL_DATA_XFER_NONE);
		if (stop->error)
			host->is_bus_width_set = false;
	}

	if (data) {
		dma_unmap_sg(dev, data->sg, data->sg_len,
			     mmc_get_dma_dir(data));
	}

	if (!cmd->error && transfer != SD_CTL_DATA_XFER_NONE) {
		data->bytes_xfered = min(len, mmc->max_req_size);
		if (transfer == SD_CTL_DATA_XFER_READ && !direct) {
			sg_copy_from_buffer(data->sg, sg_nents(data->sg),
					    host->buffer, data->bytes_xfered);
		}
	}

	mmc_request_done(mmc, mrq);
}

static void litex_mmc_setclk(struct litex_mmc_host *host, unsigned int freq)
{
	struct device *dev = mmc_dev(host->mmc);
	u32 div;

	div = freq ? host->ref_clk / freq : 256U;
	div = roundup_pow_of_two(div);
	div = clamp(div, 2U, 256U);
	dev_dbg(dev, "sd_clk_freq=%d: set to %d via div=%d\n",
		freq, host->ref_clk / div, div);
	litex_write16(host->sdphy + LITEX_PHY_CLOCKERDIV, div);
	host->sd_clk = freq;
}

static void litex_mmc_set_ios(struct mmc_host *mmc, struct mmc_ios *ios)
{
	struct litex_mmc_host *host = mmc_priv(mmc);

	/*
	 * NOTE: Ignore any ios->bus_width updates; they occur right after
	 * the mmc core sends its own acmd6 bus-width change notification,
	 * which is redundant since we snoop on the command flow and inject
	 * an early acmd6 before the first data transfer command is sent!
	 */

	/* Update sd_clk */
	if (ios->clock != host->sd_clk)
		litex_mmc_setclk(host, ios->clock);
}

static const struct mmc_host_ops litex_mmc_ops = {
	.get_cd = litex_mmc_get_cd,
	.request = litex_mmc_request,
	.set_ios = litex_mmc_set_ios,
};

static int litex_mmc_irq_init(struct platform_device *pdev,
			      struct litex_mmc_host *host)
{
	struct device *dev = mmc_dev(host->mmc);
	int ret;

	ret = platform_get_irq_optional(pdev, 0);
	if (ret < 0 && ret != -ENXIO)
		return ret;
	if (ret > 0)
		host->irq = ret;
	else {
		dev_warn(dev, "Failed to get IRQ, using polling\n");
		goto use_polling;
	}

	host->sdirq = devm_platform_ioremap_resource_byname(pdev, "irq");
	if (IS_ERR(host->sdirq))
		return PTR_ERR(host->sdirq);

	ret = devm_request_irq(dev, host->irq, litex_mmc_interrupt, 0,
			       "litex-mmc", host->mmc);
	if (ret < 0) {
		dev_warn(dev, "IRQ request error %d, using polling\n", ret);
		goto use_polling;
	}

	/* Clear & enable card-change interrupts */
	litex_write32(host->sdirq + LITEX_IRQ_PENDING, SDIRQ_CARD_DETECT);
	litex_write32(host->sdirq + LITEX_IRQ_ENABLE, SDIRQ_CARD_DETECT);

	return 0;

use_polling:
	host->mmc->caps |= MMC_CAP_NEEDS_POLL;
	return 0;
}

static void litex_mmc_free_host_wrapper(void *mmc)
{
	mmc_free_host(mmc);
}

static int litex_mmc_probe(struct platform_device *pdev)
{
	struct device *dev = &pdev->dev;
	struct litex_mmc_host *host;
	struct mmc_host *mmc;
	struct clk *clk;
	int ret;

	/*
	 * NOTE: defaults to max_[req,seg]_size=PAGE_SIZE, max_blk_size=512,
	 * and max_blk_count accordingly set to 8;
	 * If for some reason we need to modify max_blk_count, we must also
	 * re-calculate `max_[req,seg]_size = max_blk_size * max_blk_count;`
	 */
	mmc = mmc_alloc_host(sizeof(struct litex_mmc_host), dev);
	if (!mmc)
		return -ENOMEM;

	ret = devm_add_action_or_reset(dev, litex_mmc_free_host_wrapper, mmc);
	if (ret)
		return dev_err_probe(dev, ret,
				     "Can't register mmc_free_host action\n");

	host = mmc_priv(mmc);
	host->mmc = mmc;

	/* Initialize clock source */
	clk = devm_clk_get(dev, NULL);
	if (IS_ERR(clk))
		return dev_err_probe(dev, PTR_ERR(clk), "can't get clock\n");
	host->ref_clk = clk_get_rate(clk);
	host->sd_clk = 0;

	/*
	 * LiteSDCard only supports 4-bit bus width; therefore, we MUST inject
	 * a SET_BUS_WIDTH (acmd6) before the very first data transfer, earlier
	 * than when the mmc subsystem would normally get around to it!
	 */
	host->is_bus_width_set = false;
	host->app_cmd = false;

	/* LiteSDCard can support 64-bit DMA addressing */
	ret = dma_set_mask_and_coherent(dev, DMA_BIT_MASK(64));
	if (ret)
		return ret;

	host->buf_size = mmc->max_req_size * 2;
	host->buffer = dmam_alloc_coherent(dev, host->buf_size,
					   &host->dma, GFP_KERNEL);
	if (host->buffer == NULL)
		return -ENOMEM;

	host->sdphy = devm_platform_ioremap_resource_byname(pdev, "phy");
	if (IS_ERR(host->sdphy))
		return PTR_ERR(host->sdphy);

	host->sdcore = devm_platform_ioremap_resource_byname(pdev, "core");
	if (IS_ERR(host->sdcore))
		return PTR_ERR(host->sdcore);

	host->sdreader = devm_platform_ioremap_resource_byname(pdev, "reader");
	if (IS_ERR(host->sdreader))
		return PTR_ERR(host->sdreader);

	host->sdwriter = devm_platform_ioremap_resource_byname(pdev, "writer");
	if (IS_ERR(host->sdwriter))
		return PTR_ERR(host->sdwriter);

	/* Ensure DMA bus masters are disabled */
	litex_write8(host->sdreader + LITEX_BLK2MEM_ENA, 0);
	litex_write8(host->sdwriter + LITEX_MEM2BLK_ENA, 0);

	init_completion(&host->cmd_done);
	ret = litex_mmc_irq_init(pdev, host);
	if (ret)
		return ret;

	mmc->ops = &litex_mmc_ops;

	ret = mmc_regulator_get_supply(mmc);
	if (ret || mmc->ocr_avail == 0) {
		dev_warn(dev, "can't get voltage, defaulting to 3.3V\n");
		mmc->ocr_avail = MMC_VDD_32_33 | MMC_VDD_33_34;
	}

	/*
	 * Set default sd_clk frequency range based on empirical observations
	 * of LiteSDCard gateware behavior on typical SDCard media
	 */
	mmc->f_min = 12.5e6;
	mmc->f_max = 50e6;

	ret = mmc_of_parse(mmc);
	if (ret)
		return ret;

	/* Force 4-bit bus_width (only width supported by hardware) */
	mmc->caps &= ~MMC_CAP_8_BIT_DATA;
	mmc->caps |= MMC_CAP_4_BIT_DATA;

	/* Set default capabilities */
	mmc->caps |= MMC_CAP_WAIT_WHILE_BUSY |
		     MMC_CAP_DRIVER_TYPE_D |
		     MMC_CAP_CMD23;
	mmc->caps2 |= MMC_CAP2_NO_WRITE_PROTECT |
		      MMC_CAP2_NO_SDIO |
		      MMC_CAP2_NO_MMC;

	platform_set_drvdata(pdev, host);

	ret = mmc_add_host(mmc);
	if (ret)
		return ret;

	dev_info(dev, "LiteX MMC controller initialized.\n");
	return 0;
}

static int litex_mmc_remove(struct platform_device *pdev)
{
	struct litex_mmc_host *host = platform_get_drvdata(pdev);

	mmc_remove_host(host->mmc);
	return 0;
}

static const struct of_device_id litex_match[] = {
	{ .compatible = "litex,mmc" },
	{ }
};
MODULE_DEVICE_TABLE(of, litex_match);

static struct platform_driver litex_mmc_driver = {
	.probe = litex_mmc_probe,
	.remove = litex_mmc_remove,
	.driver = {
		.name = "litex-mmc",
		.of_match_table = litex_match,
	},
};
module_platform_driver(litex_mmc_driver);

MODULE_DESCRIPTION("LiteX SDCard driver");
MODULE_AUTHOR("Antmicro <contact@antmicro.com>");
MODULE_AUTHOR("Kamil Rakoczy <krakoczy@antmicro.com>");
MODULE_AUTHOR("Maciej Dudek <mdudek@internships.antmicro.com>");
MODULE_AUTHOR("Paul Mackerras <paulus@ozlabs.org>");
MODULE_AUTHOR("Gabriel Somlo <gsomlo@gmail.com>");
MODULE_LICENSE("GPL v2");
