// SPDX-License-Identifier: GPL-2.0+
/*
 * Take drivers/gpio/gpio-74x164.c as reference.
 *
 * 74Hx164 - Generic serial-in/parallel-out 8-bits shift register GPIO driver
 *
 * Copyright (C) 2016 Peng Fan <van.freenix@gmail.com>
 *
 */

#include <common.h>
#include <errno.h>
#include <dm.h>
#include <fdtdec.h>
#include <malloc.h>
#include <asm/global_data.h>
#include <asm/gpio.h>
#include <asm/io.h>
#include <dm/device_compat.h>
#include <dt-bindings/gpio/gpio.h>
#include <spi.h>

DECLARE_GLOBAL_DATA_PTR;

/*
 * struct gen_74x164_chip - Data for 74Hx164
 *
 * @oe: OE pin
 * @nregs: number of registers
 * @buffer: buffer for chained chips
 */
#define GEN_74X164_NUMBER_GPIOS 8

struct gen_74x164_priv {
	struct gpio_desc oe;
	u32 nregs;
	/*
	 * Since the nregs are chained, every byte sent will make
	 * the previous byte shift to the next register in the
	 * chain. Thus, the first byte sent will end up in the last
	 * register at the end of the transfer. So, to have a logical
	 * numbering, store the bytes in reverse order.
	 */
	u8 *buffer;
};

static int gen_74x164_write_conf(struct udevice *dev)
{
	struct gen_74x164_priv *priv = dev_get_priv(dev);
	int ret;

	ret = dm_spi_claim_bus(dev);
	if (ret)
		return ret;

	ret = dm_spi_xfer(dev, priv->nregs * 8, priv->buffer, NULL,
			  SPI_XFER_BEGIN | SPI_XFER_END);

	dm_spi_release_bus(dev);

	return ret;
}

static int gen_74x164_get_value(struct udevice *dev, unsigned offset)
{
	struct gen_74x164_priv *priv = dev_get_priv(dev);
	uint bank = priv->nregs - 1 - offset / 8;
	uint pin = offset % 8;

	return (priv->buffer[bank] >> pin) & 0x1;
}

static int gen_74x164_set_value(struct udevice *dev, unsigned offset,
				int value)
{
	struct gen_74x164_priv *priv = dev_get_priv(dev);
	uint bank = priv->nregs - 1 - offset / 8;
	uint pin = offset % 8;
	int ret;

	if (value)
		priv->buffer[bank] |= 1 << pin;
	else
		priv->buffer[bank] &= ~(1 << pin);

	ret = gen_74x164_write_conf(dev);
	if (ret)
		return ret;

	return 0;
}

static int gen_74x164_direction_input(struct udevice *dev, unsigned offset)
{
	return -ENOSYS;
}

static int gen_74x164_direction_output(struct udevice *dev, unsigned offset,
				      int value)
{
	return gen_74x164_set_value(dev, offset, value);
}

static int gen_74x164_get_function(struct udevice *dev, unsigned offset)
{
	return GPIOF_OUTPUT;
}

static int gen_74x164_xlate(struct udevice *dev, struct gpio_desc *desc,
			    struct ofnode_phandle_args *args)
{
	desc->offset = args->args[0];
	desc->flags = args->args[1] & GPIO_ACTIVE_LOW ? GPIOD_ACTIVE_LOW : 0;

	return 0;
}

static const struct dm_gpio_ops gen_74x164_ops = {
	.direction_input	= gen_74x164_direction_input,
	.direction_output	= gen_74x164_direction_output,
	.get_value		= gen_74x164_get_value,
	.set_value		= gen_74x164_set_value,
	.get_function		= gen_74x164_get_function,
	.xlate			= gen_74x164_xlate,
};

static int gen_74x164_probe(struct udevice *dev)
{
	struct gen_74x164_priv *priv = dev_get_priv(dev);
	struct gpio_dev_priv *uc_priv = dev_get_uclass_priv(dev);
	char *str, name[32];
	int ret;
	const void *fdt = gd->fdt_blob;
	int node = dev_of_offset(dev);

	snprintf(name, sizeof(name), "%s_", dev->name);
	str = strdup(name);
	if (!str)
		return -ENOMEM;

	/*
	 * See Linux kernel:
	 * Documentation/devicetree/bindings/gpio/gpio-74x164.txt
	 */
	priv->nregs = fdtdec_get_int(fdt, node, "registers-number", 1);
	priv->buffer = calloc(priv->nregs, sizeof(u8));
	if (!priv->buffer) {
		ret = -ENOMEM;
		goto free_str;
	}

	ret = fdtdec_get_byte_array(fdt, node, "registers-default",
				    priv->buffer, priv->nregs);
	if (ret)
		dev_dbg(dev, "No registers-default property\n");

	ret = gpio_request_by_name(dev, "oe-gpios", 0, &priv->oe,
				   GPIOD_IS_OUT | GPIOD_IS_OUT_ACTIVE);
	if (ret) {
		dev_dbg(dev, "No oe-pins property\n");
	}

	uc_priv->bank_name = str;
	uc_priv->gpio_count = priv->nregs * 8;

	ret = gen_74x164_write_conf(dev);
	if (ret)
		goto free_buf;

	dev_dbg(dev, "%s is ready\n", dev->name);

	return 0;

free_buf:
	free(priv->buffer);
free_str:
	free(str);
	return ret;
}

static const struct udevice_id gen_74x164_ids[] = {
	{ .compatible = "fairchild,74hc595" },
	{ }
};

U_BOOT_DRIVER(74x164) = {
	.name		= "74x164",
	.id		= UCLASS_GPIO,
	.ops		= &gen_74x164_ops,
	.probe		= gen_74x164_probe,
	.priv_auto	= sizeof(struct gen_74x164_priv),
	.of_match	= gen_74x164_ids,
};
