// SPDX-License-Identifier: GPL-2.0+
/*
 * Copyright (c) 2014 Google, Inc
 */

#include <common.h>
#include <eeprom.h>
#include <linux/err.h>
#include <linux/kernel.h>
#include <dm.h>
#include <dm/device-internal.h>
#include <i2c.h>
#include <i2c_eeprom.h>

struct i2c_eeprom_drv_data {
	u32 size; /* size in bytes */
	u32 pagewidth; /* pagesize = 2^pagewidth */
};

int i2c_eeprom_read(struct udevice *dev, int offset, uint8_t *buf, int size)
{
	const struct i2c_eeprom_ops *ops = device_get_ops(dev);

	if (!ops->read)
		return -ENOSYS;

	return ops->read(dev, offset, buf, size);
}

int i2c_eeprom_write(struct udevice *dev, int offset, uint8_t *buf, int size)
{
	const struct i2c_eeprom_ops *ops = device_get_ops(dev);

	if (!ops->write)
		return -ENOSYS;

	return ops->write(dev, offset, buf, size);
}

int i2c_eeprom_size(struct udevice *dev)
{
	const struct i2c_eeprom_ops *ops = device_get_ops(dev);

	if (!ops->size)
		return -ENOSYS;

	return ops->size(dev);
}

static int i2c_eeprom_std_read(struct udevice *dev, int offset, uint8_t *buf,
			       int size)
{
	return dm_i2c_read(dev, offset, buf, size);
}

static int i2c_eeprom_std_write(struct udevice *dev, int offset,
				const uint8_t *buf, int size)
{
	struct i2c_eeprom *priv = dev_get_priv(dev);
	int ret;

	while (size > 0) {
		int write_size = min_t(int, size, priv->pagesize);

		ret = dm_i2c_write(dev, offset, buf, write_size);
		if (ret)
			return ret;

		offset += write_size;
		buf += write_size;
		size -= write_size;

		udelay(10000);
	}

	return 0;
}

static int i2c_eeprom_std_size(struct udevice *dev)
{
	struct i2c_eeprom *priv = dev_get_priv(dev);

	return priv->size;
}

static const struct i2c_eeprom_ops i2c_eeprom_std_ops = {
	.read	= i2c_eeprom_std_read,
	.write	= i2c_eeprom_std_write,
	.size	= i2c_eeprom_std_size,
};

static int i2c_eeprom_std_ofdata_to_platdata(struct udevice *dev)
{
	struct i2c_eeprom *priv = dev_get_priv(dev);
	struct i2c_eeprom_drv_data *data =
		(struct i2c_eeprom_drv_data *)dev_get_driver_data(dev);
	u32 pagesize;
	u32 size;

	if (dev_read_u32(dev, "pagesize", &pagesize) == 0) {
		priv->pagesize = pagesize;
	} else {
		/* 6 bit -> page size of up to 2^63 (should be sufficient) */
		priv->pagewidth = data->pagewidth;
		priv->pagesize = (1 << priv->pagewidth);
	}

	if (dev_read_u32(dev, "size", &size) == 0)
		priv->size = size;
	else
		priv->size = data->size;

	return 0;
}

static int i2c_eeprom_std_bind(struct udevice *dev)
{
	ofnode partitions = ofnode_find_subnode(dev_ofnode(dev), "partitions");
	ofnode partition;
	const char *name;

	if (!ofnode_valid(partitions))
		return 0;
	if (!ofnode_device_is_compatible(partitions, "fixed-partitions"))
		return -ENOTSUPP;

	ofnode_for_each_subnode(partition, partitions) {
		name = ofnode_get_name(partition);
		if (!name)
			continue;

		device_bind_ofnode(dev, DM_GET_DRIVER(i2c_eeprom_partition),
				   name, NULL, partition, NULL);
	}

	return 0;
}

static int i2c_eeprom_std_probe(struct udevice *dev)
{
	u8 test_byte;
	int ret;

	/* Verify that the chip is functional */
	ret = i2c_eeprom_read(dev, 0, &test_byte, 1);
	if (ret)
		return -ENODEV;

	return 0;
}

static const struct i2c_eeprom_drv_data eeprom_data = {
	.size = 0,
	.pagewidth = 0,
};

static const struct i2c_eeprom_drv_data mc24aa02e48_data = {
	.size = 256,
	.pagewidth = 3,
};

static const struct i2c_eeprom_drv_data atmel24c01a_data = {
	.size = 128,
	.pagewidth = 3,
};

static const struct i2c_eeprom_drv_data atmel24c02_data = {
	.size = 256,
	.pagewidth = 3,
};

static const struct i2c_eeprom_drv_data atmel24c04_data = {
	.size = 512,
	.pagewidth = 4,
};

static const struct i2c_eeprom_drv_data atmel24c08_data = {
	.size = 1024,
	.pagewidth = 4,
};

static const struct i2c_eeprom_drv_data atmel24c08a_data = {
	.size = 1024,
	.pagewidth = 4,
};

static const struct i2c_eeprom_drv_data atmel24c16a_data = {
	.size = 2048,
	.pagewidth = 4,
};

static const struct i2c_eeprom_drv_data atmel24mac402_data = {
	.size = 256,
	.pagewidth = 4,
};

static const struct i2c_eeprom_drv_data atmel24c32_data = {
	.size = 4096,
	.pagewidth = 5,
};

static const struct i2c_eeprom_drv_data atmel24c64_data = {
	.size = 8192,
	.pagewidth = 5,
};

static const struct i2c_eeprom_drv_data atmel24c128_data = {
	.size = 16384,
	.pagewidth = 6,
};

static const struct i2c_eeprom_drv_data atmel24c256_data = {
	.size = 32768,
	.pagewidth = 6,
};

static const struct i2c_eeprom_drv_data atmel24c512_data = {
	.size = 65536,
	.pagewidth = 6,
};

static const struct udevice_id i2c_eeprom_std_ids[] = {
	{ .compatible = "i2c-eeprom", (ulong)&eeprom_data },
	{ .compatible = "microchip,24aa02e48", (ulong)&mc24aa02e48_data },
	{ .compatible = "atmel,24c01a", (ulong)&atmel24c01a_data },
	{ .compatible = "atmel,24c02", (ulong)&atmel24c02_data },
	{ .compatible = "atmel,24c04", (ulong)&atmel24c04_data },
	{ .compatible = "atmel,24c08", (ulong)&atmel24c08_data },
	{ .compatible = "atmel,24c08a", (ulong)&atmel24c08a_data },
	{ .compatible = "atmel,24c16a", (ulong)&atmel24c16a_data },
	{ .compatible = "atmel,24mac402", (ulong)&atmel24mac402_data },
	{ .compatible = "atmel,24c32", (ulong)&atmel24c32_data },
	{ .compatible = "atmel,24c64", (ulong)&atmel24c64_data },
	{ .compatible = "atmel,24c128", (ulong)&atmel24c128_data },
	{ .compatible = "atmel,24c256", (ulong)&atmel24c256_data },
	{ .compatible = "atmel,24c512", (ulong)&atmel24c512_data },
	{ }
};

U_BOOT_DRIVER(i2c_eeprom_std) = {
	.name			= "i2c_eeprom",
	.id			= UCLASS_I2C_EEPROM,
	.of_match		= i2c_eeprom_std_ids,
	.bind			= i2c_eeprom_std_bind,
	.probe			= i2c_eeprom_std_probe,
	.ofdata_to_platdata	= i2c_eeprom_std_ofdata_to_platdata,
	.priv_auto_alloc_size	= sizeof(struct i2c_eeprom),
	.ops			= &i2c_eeprom_std_ops,
};

struct i2c_eeprom_partition {
	u32 offset;
	u32 size;
};

static int i2c_eeprom_partition_probe(struct udevice *dev)
{
	return 0;
}

static int i2c_eeprom_partition_ofdata_to_platdata(struct udevice *dev)
{
	struct i2c_eeprom_partition *priv = dev_get_priv(dev);
	u32 offset, size;
	int ret;

	ret = dev_read_u32(dev, "offset", &offset);
	if (ret)
		return ret;

	ret = dev_read_u32(dev, "size", &size);
	if (ret)
		return ret;

	priv->offset = offset;
	priv->size = size;

	return 0;
}

static int i2c_eeprom_partition_read(struct udevice *dev, int offset,
				     u8 *buf, int size)
{
	struct i2c_eeprom_partition *priv = dev_get_priv(dev);
	struct udevice *parent = dev_get_parent(dev);

	if (!parent)
		return -ENODEV;
	if (offset + size > priv->size)
		return -EINVAL;

	return i2c_eeprom_read(parent, offset + priv->offset, buf, size);
}

static int i2c_eeprom_partition_write(struct udevice *dev, int offset,
				      const u8 *buf, int size)
{
	struct i2c_eeprom_partition *priv = dev_get_priv(dev);
	struct udevice *parent = dev_get_parent(dev);

	if (!parent)
		return -ENODEV;
	if (offset + size > priv->size)
		return -EINVAL;

	return i2c_eeprom_write(parent, offset + priv->offset, (uint8_t *)buf,
				size);
}

static int i2c_eeprom_partition_size(struct udevice *dev)
{
	struct i2c_eeprom_partition *priv = dev_get_priv(dev);

	return priv->size;
}

static const struct i2c_eeprom_ops i2c_eeprom_partition_ops = {
	.read	= i2c_eeprom_partition_read,
	.write	= i2c_eeprom_partition_write,
	.size	= i2c_eeprom_partition_size,
};

U_BOOT_DRIVER(i2c_eeprom_partition) = {
	.name			= "i2c_eeprom_partition",
	.id			= UCLASS_I2C_EEPROM,
	.probe			= i2c_eeprom_partition_probe,
	.ofdata_to_platdata	= i2c_eeprom_partition_ofdata_to_platdata,
	.priv_auto_alloc_size	= sizeof(struct i2c_eeprom_partition),
	.ops			= &i2c_eeprom_partition_ops,
};

UCLASS_DRIVER(i2c_eeprom) = {
	.id		= UCLASS_I2C_EEPROM,
	.name		= "i2c_eeprom",
};
