/*
 * Base driver for Dialog Semiconductor DA9030/DA9034
 *
 * Copyright (C) 2008 Compulab, Ltd.
 * 	Mike Rapoport <mike@compulab.co.il>
 *
 * Copyright (C) 2006-2008 Marvell International Ltd.
 * 	Eric Miao <eric.miao@marvell.com>
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 as
 * published by the Free Software Foundation.
 */

#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/interrupt.h>
#include <linux/platform_device.h>
#include <linux/i2c.h>
#include <linux/mfd/da903x.h>

#define DA9030_CHIP_ID		0x00
#define DA9030_EVENT_A		0x01
#define DA9030_EVENT_B		0x02
#define DA9030_EVENT_C		0x03
#define DA9030_STATUS		0x04
#define DA9030_IRQ_MASK_A	0x05
#define DA9030_IRQ_MASK_B	0x06
#define DA9030_IRQ_MASK_C	0x07
#define DA9030_SYS_CTRL_A	0x08
#define DA9030_SYS_CTRL_B	0x09
#define DA9030_FAULT_LOG	0x0a

#define DA9034_CHIP_ID		0x00
#define DA9034_EVENT_A		0x01
#define DA9034_EVENT_B		0x02
#define DA9034_EVENT_C		0x03
#define DA9034_EVENT_D		0x04
#define DA9034_STATUS_A		0x05
#define DA9034_STATUS_B		0x06
#define DA9034_IRQ_MASK_A	0x07
#define DA9034_IRQ_MASK_B	0x08
#define DA9034_IRQ_MASK_C	0x09
#define DA9034_IRQ_MASK_D	0x0a
#define DA9034_SYS_CTRL_A	0x0b
#define DA9034_SYS_CTRL_B	0x0c
#define DA9034_FAULT_LOG	0x0d

struct da903x_chip;

struct da903x_chip_ops {
	int	(*init_chip)(struct da903x_chip *);
	int	(*unmask_events)(struct da903x_chip *, unsigned int events);
	int	(*mask_events)(struct da903x_chip *, unsigned int events);
	int	(*read_events)(struct da903x_chip *, unsigned int *events);
	int	(*read_status)(struct da903x_chip *, unsigned int *status);
};

struct da903x_chip {
	struct i2c_client	*client;
	struct device		*dev;
	struct da903x_chip_ops	*ops;

	int			type;
	uint32_t		events_mask;

	struct mutex		lock;
	struct work_struct	irq_work;

	struct blocking_notifier_head notifier_list;
};

static inline int __da903x_read(struct i2c_client *client,
				int reg, uint8_t *val)
{
	int ret;

	ret = i2c_smbus_read_byte_data(client, reg);
	if (ret < 0) {
		dev_err(&client->dev, "failed reading at 0x%02x\n", reg);
		return ret;
	}

	*val = (uint8_t)ret;
	return 0;
}

static inline int __da903x_reads(struct i2c_client *client, int reg,
				 int len, uint8_t *val)
{
	int ret;

	ret = i2c_smbus_read_i2c_block_data(client, reg, len, val);
	if (ret < 0) {
		dev_err(&client->dev, "failed reading from 0x%02x\n", reg);
		return ret;
	}
	return 0;
}

static inline int __da903x_write(struct i2c_client *client,
				 int reg, uint8_t val)
{
	int ret;

	ret = i2c_smbus_write_byte_data(client, reg, val);
	if (ret < 0) {
		dev_err(&client->dev, "failed writing 0x%02x to 0x%02x\n",
				val, reg);
		return ret;
	}
	return 0;
}

static inline int __da903x_writes(struct i2c_client *client, int reg,
				  int len, uint8_t *val)
{
	int ret;

	ret = i2c_smbus_write_i2c_block_data(client, reg, len, val);
	if (ret < 0) {
		dev_err(&client->dev, "failed writings to 0x%02x\n", reg);
		return ret;
	}
	return 0;
}

int da903x_register_notifier(struct device *dev, struct notifier_block *nb,
				unsigned int events)
{
	struct da903x_chip *chip = dev_get_drvdata(dev);

	chip->ops->unmask_events(chip, events);
	return blocking_notifier_chain_register(&chip->notifier_list, nb);
}
EXPORT_SYMBOL_GPL(da903x_register_notifier);

int da903x_unregister_notifier(struct device *dev, struct notifier_block *nb,
				unsigned int events)
{
	struct da903x_chip *chip = dev_get_drvdata(dev);

	chip->ops->mask_events(chip, events);
	return blocking_notifier_chain_unregister(&chip->notifier_list, nb);
}
EXPORT_SYMBOL_GPL(da903x_unregister_notifier);

int da903x_write(struct device *dev, int reg, uint8_t val)
{
	return __da903x_write(to_i2c_client(dev), reg, val);
}
EXPORT_SYMBOL_GPL(da903x_write);

int da903x_read(struct device *dev, int reg, uint8_t *val)
{
	return __da903x_read(to_i2c_client(dev), reg, val);
}
EXPORT_SYMBOL_GPL(da903x_read);

int da903x_set_bits(struct device *dev, int reg, uint8_t bit_mask)
{
	struct da903x_chip *chip = dev_get_drvdata(dev);
	uint8_t reg_val;
	int ret = 0;

	mutex_lock(&chip->lock);

	ret = __da903x_read(chip->client, reg, &reg_val);
	if (ret)
		goto out;

	if ((reg_val & bit_mask) == 0) {
		reg_val |= bit_mask;
		ret = __da903x_write(chip->client, reg, reg_val);
	}
out:
	mutex_unlock(&chip->lock);
	return ret;
}
EXPORT_SYMBOL_GPL(da903x_set_bits);

int da903x_clr_bits(struct device *dev, int reg, uint8_t bit_mask)
{
	struct da903x_chip *chip = dev_get_drvdata(dev);
	uint8_t reg_val;
	int ret = 0;

	mutex_lock(&chip->lock);

	ret = __da903x_read(chip->client, reg, &reg_val);
	if (ret)
		goto out;

	if (reg_val & bit_mask) {
		reg_val &= ~bit_mask;
		ret = __da903x_write(chip->client, reg, reg_val);
	}
out:
	mutex_unlock(&chip->lock);
	return ret;
}
EXPORT_SYMBOL_GPL(da903x_clr_bits);

int da903x_update(struct device *dev, int reg, uint8_t val, uint8_t mask)
{
	struct da903x_chip *chip = dev_get_drvdata(dev);
	uint8_t reg_val;
	int ret = 0;

	mutex_lock(&chip->lock);

	ret = __da903x_read(chip->client, reg, &reg_val);
	if (ret)
		goto out;

	if ((reg_val & mask) != val) {
		reg_val = (reg_val & ~mask) | val;
		ret = __da903x_write(chip->client, reg, reg_val);
	}
out:
	mutex_unlock(&chip->lock);
	return ret;
}
EXPORT_SYMBOL_GPL(da903x_update);

int da903x_query_status(struct device *dev, unsigned int sbits)
{
	struct da903x_chip *chip = dev_get_drvdata(dev);
	unsigned int status = 0;

	chip->ops->read_status(chip, &status);
	return ((status & sbits) == sbits);
}
EXPORT_SYMBOL(da903x_query_status);

static int __devinit da9030_init_chip(struct da903x_chip *chip)
{
	uint8_t chip_id;
	int err;

	err = __da903x_read(chip->client, DA9030_CHIP_ID, &chip_id);
	if (err)
		return err;

	err = __da903x_write(chip->client, DA9030_SYS_CTRL_A, 0xE8);
	if (err)
		return err;

	dev_info(chip->dev, "DA9030 (CHIP ID: 0x%02x) detected\n", chip_id);
	return 0;
}

static int da9030_unmask_events(struct da903x_chip *chip, unsigned int events)
{
	uint8_t v[3];

	chip->events_mask &= ~events;

	v[0] = (chip->events_mask & 0xff);
	v[1] = (chip->events_mask >> 8) & 0xff;
	v[2] = (chip->events_mask >> 16) & 0xff;

	return __da903x_writes(chip->client, DA9030_IRQ_MASK_A, 3, v);
}

static int da9030_mask_events(struct da903x_chip *chip, unsigned int events)
{
	uint8_t v[3];

	chip->events_mask |= events;

	v[0] = (chip->events_mask & 0xff);
	v[1] = (chip->events_mask >> 8) & 0xff;
	v[2] = (chip->events_mask >> 16) & 0xff;

	return __da903x_writes(chip->client, DA9030_IRQ_MASK_A, 3, v);
}

static int da9030_read_events(struct da903x_chip *chip, unsigned int *events)
{
	uint8_t v[3] = {0, 0, 0};
	int ret;

	ret = __da903x_reads(chip->client, DA9030_EVENT_A, 3, v);
	if (ret < 0)
		return ret;

	*events = (v[2] << 16) | (v[1] << 8) | v[0];
	return 0;
}

static int da9030_read_status(struct da903x_chip *chip, unsigned int *status)
{
	return __da903x_read(chip->client, DA9030_STATUS, (uint8_t *)status);
}

static int da9034_init_chip(struct da903x_chip *chip)
{
	uint8_t chip_id;
	int err;

	err = __da903x_read(chip->client, DA9034_CHIP_ID, &chip_id);
	if (err)
		return err;

	err = __da903x_write(chip->client, DA9034_SYS_CTRL_A, 0xE8);
	if (err)
		return err;

	/* avoid SRAM power off during sleep*/
	__da903x_write(chip->client, 0x10, 0x07);
	__da903x_write(chip->client, 0x11, 0xff);
	__da903x_write(chip->client, 0x12, 0xff);

	/* Enable the ONKEY power down functionality */
	__da903x_write(chip->client, DA9034_SYS_CTRL_B, 0x20);
	__da903x_write(chip->client, DA9034_SYS_CTRL_A, 0x60);

	/* workaround to make LEDs work */
	__da903x_write(chip->client, 0x90, 0x01);
	__da903x_write(chip->client, 0xB0, 0x08);

	/* make ADTV1 and SDTV1 effective */
	__da903x_write(chip->client, 0x20, 0x00);

	dev_info(chip->dev, "DA9034 (CHIP ID: 0x%02x) detected\n", chip_id);
	return 0;
}

static int da9034_unmask_events(struct da903x_chip *chip, unsigned int events)
{
	uint8_t v[4];

	chip->events_mask &= ~events;

	v[0] = (chip->events_mask & 0xff);
	v[1] = (chip->events_mask >> 8) & 0xff;
	v[2] = (chip->events_mask >> 16) & 0xff;
	v[3] = (chip->events_mask >> 24) & 0xff;

	return __da903x_writes(chip->client, DA9034_IRQ_MASK_A, 4, v);
}

static int da9034_mask_events(struct da903x_chip *chip, unsigned int events)
{
	uint8_t v[4];

	chip->events_mask |= events;

	v[0] = (chip->events_mask & 0xff);
	v[1] = (chip->events_mask >> 8) & 0xff;
	v[2] = (chip->events_mask >> 16) & 0xff;
	v[3] = (chip->events_mask >> 24) & 0xff;

	return __da903x_writes(chip->client, DA9034_IRQ_MASK_A, 4, v);
}

static int da9034_read_events(struct da903x_chip *chip, unsigned int *events)
{
	uint8_t v[4] = {0, 0, 0, 0};
	int ret;

	ret = __da903x_reads(chip->client, DA9034_EVENT_A, 4, v);
	if (ret < 0)
		return ret;

	*events = (v[3] << 24) | (v[2] << 16) | (v[1] << 8) | v[0];
	return 0;
}

static int da9034_read_status(struct da903x_chip *chip, unsigned int *status)
{
	uint8_t v[2] = {0, 0};
	int ret = 0;

	ret = __da903x_reads(chip->client, DA9034_STATUS_A, 2, v);
	if (ret)
		return ret;

	*status = (v[1] << 8) | v[0];
	return 0;
}

static void da903x_irq_work(struct work_struct *work)
{
	struct da903x_chip *chip =
		container_of(work, struct da903x_chip, irq_work);
	unsigned int events = 0;

	while (1) {
		if (chip->ops->read_events(chip, &events))
			break;

		events &= ~chip->events_mask;
		if (events == 0)
			break;

		blocking_notifier_call_chain(
				&chip->notifier_list, events, NULL);
	}
	enable_irq(chip->client->irq);
}

static int da903x_irq_handler(int irq, void *data)
{
	struct da903x_chip *chip = data;

	disable_irq_nosync(irq);
	(void)schedule_work(&chip->irq_work);

	return IRQ_HANDLED;
}

static struct da903x_chip_ops da903x_ops[] = {
	[0] = {
		.init_chip	= da9030_init_chip,
		.unmask_events	= da9030_unmask_events,
		.mask_events	= da9030_mask_events,
		.read_events	= da9030_read_events,
		.read_status	= da9030_read_status,
	},
	[1] = {
		.init_chip	= da9034_init_chip,
		.unmask_events	= da9034_unmask_events,
		.mask_events	= da9034_mask_events,
		.read_events	= da9034_read_events,
		.read_status	= da9034_read_status,
	}
};

static const struct i2c_device_id da903x_id_table[] = {
	{ "da9030", 0 },
	{ "da9034", 1 },
	{ },
};
MODULE_DEVICE_TABLE(i2c, da903x_id_table);

static int __devexit __remove_subdev(struct device *dev, void *unused)
{
	platform_device_unregister(to_platform_device(dev));
	return 0;
}

static int __devexit da903x_remove_subdevs(struct da903x_chip *chip)
{
	return device_for_each_child(chip->dev, NULL, __remove_subdev);
}

static int __devinit da903x_add_subdevs(struct da903x_chip *chip,
					struct da903x_platform_data *pdata)
{
	struct da903x_subdev_info *subdev;
	struct platform_device *pdev;
	int i, ret = 0;

	for (i = 0; i < pdata->num_subdevs; i++) {
		subdev = &pdata->subdevs[i];

		pdev = platform_device_alloc(subdev->name, subdev->id);

		pdev->dev.parent = chip->dev;
		pdev->dev.platform_data = subdev->platform_data;

		ret = platform_device_add(pdev);
		if (ret)
			goto failed;
	}
	return 0;

failed:
	da903x_remove_subdevs(chip);
	return ret;
}

static int __devinit da903x_probe(struct i2c_client *client,
				  const struct i2c_device_id *id)
{
	struct da903x_platform_data *pdata = client->dev.platform_data;
	struct da903x_chip *chip;
	unsigned int tmp;
	int ret;

	chip = kzalloc(sizeof(struct da903x_chip), GFP_KERNEL);
	if (chip == NULL)
		return -ENOMEM;

	chip->client = client;
	chip->dev = &client->dev;
	chip->ops = &da903x_ops[id->driver_data];

	mutex_init(&chip->lock);
	INIT_WORK(&chip->irq_work, da903x_irq_work);
	BLOCKING_INIT_NOTIFIER_HEAD(&chip->notifier_list);

	i2c_set_clientdata(client, chip);

	ret = chip->ops->init_chip(chip);
	if (ret)
		goto out_free_chip;

	/* mask and clear all IRQs */
	chip->events_mask = 0xffffffff;
	chip->ops->mask_events(chip, chip->events_mask);
	chip->ops->read_events(chip, &tmp);

	ret = request_irq(client->irq, da903x_irq_handler,
			IRQF_DISABLED | IRQF_TRIGGER_FALLING,
			"da903x", chip);
	if (ret) {
		dev_err(&client->dev, "failed to request irq %d\n",
				client->irq);
		goto out_free_chip;
	}

	ret = da903x_add_subdevs(chip, pdata);
	if (ret)
		goto out_free_irq;

	return 0;

out_free_irq:
	free_irq(client->irq, chip);
out_free_chip:
	i2c_set_clientdata(client, NULL);
	kfree(chip);
	return ret;
}

static int __devexit da903x_remove(struct i2c_client *client)
{
	struct da903x_chip *chip = i2c_get_clientdata(client);

	da903x_remove_subdevs(chip);
	kfree(chip);
	return 0;
}

static struct i2c_driver da903x_driver = {
	.driver	= {
		.name	= "da903x",
		.owner	= THIS_MODULE,
	},
	.probe		= da903x_probe,
	.remove		= __devexit_p(da903x_remove),
	.id_table	= da903x_id_table,
};

static int __init da903x_init(void)
{
	return i2c_add_driver(&da903x_driver);
}
module_init(da903x_init);

static void __exit da903x_exit(void)
{
	i2c_del_driver(&da903x_driver);
}
module_exit(da903x_exit);

MODULE_DESCRIPTION("PMIC Driver for Dialog Semiconductor DA9034");
MODULE_AUTHOR("Eric Miao <eric.miao@marvell.com>"
	      "Mike Rapoport <mike@compulab.co.il>");
MODULE_LICENSE("GPL");
