/*
 * Driver for the Diolan DLN-2 USB-GPIO adapter
 *
 * Copyright (c) 2014 Intel Corporation
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License as
 * published by the Free Software Foundation, version 2.
 */

#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/slab.h>
#include <linux/types.h>
#include <linux/irqdomain.h>
#include <linux/irq.h>
#include <linux/irqchip/chained_irq.h>
#include <linux/gpio.h>
#include <linux/gpio/driver.h>
#include <linux/platform_device.h>
#include <linux/mfd/dln2.h>

#define DLN2_GPIO_ID			0x01

#define DLN2_GPIO_GET_PIN_COUNT		DLN2_CMD(0x01, DLN2_GPIO_ID)
#define DLN2_GPIO_SET_DEBOUNCE		DLN2_CMD(0x04, DLN2_GPIO_ID)
#define DLN2_GPIO_GET_DEBOUNCE		DLN2_CMD(0x05, DLN2_GPIO_ID)
#define DLN2_GPIO_PORT_GET_VAL		DLN2_CMD(0x06, DLN2_GPIO_ID)
#define DLN2_GPIO_PIN_GET_VAL		DLN2_CMD(0x0B, DLN2_GPIO_ID)
#define DLN2_GPIO_PIN_SET_OUT_VAL	DLN2_CMD(0x0C, DLN2_GPIO_ID)
#define DLN2_GPIO_PIN_GET_OUT_VAL	DLN2_CMD(0x0D, DLN2_GPIO_ID)
#define DLN2_GPIO_CONDITION_MET_EV	DLN2_CMD(0x0F, DLN2_GPIO_ID)
#define DLN2_GPIO_PIN_ENABLE		DLN2_CMD(0x10, DLN2_GPIO_ID)
#define DLN2_GPIO_PIN_DISABLE		DLN2_CMD(0x11, DLN2_GPIO_ID)
#define DLN2_GPIO_PIN_SET_DIRECTION	DLN2_CMD(0x13, DLN2_GPIO_ID)
#define DLN2_GPIO_PIN_GET_DIRECTION	DLN2_CMD(0x14, DLN2_GPIO_ID)
#define DLN2_GPIO_PIN_SET_EVENT_CFG	DLN2_CMD(0x1E, DLN2_GPIO_ID)
#define DLN2_GPIO_PIN_GET_EVENT_CFG	DLN2_CMD(0x1F, DLN2_GPIO_ID)

#define DLN2_GPIO_EVENT_NONE		0
#define DLN2_GPIO_EVENT_CHANGE		1
#define DLN2_GPIO_EVENT_LVL_HIGH	2
#define DLN2_GPIO_EVENT_LVL_LOW		3
#define DLN2_GPIO_EVENT_CHANGE_RISING	0x11
#define DLN2_GPIO_EVENT_CHANGE_FALLING  0x21
#define DLN2_GPIO_EVENT_MASK		0x0F

#define DLN2_GPIO_MAX_PINS 32

struct dln2_gpio {
	struct platform_device *pdev;
	struct gpio_chip gpio;

	/*
	 * Cache pin direction to save us one transfer, since the hardware has
	 * separate commands to read the in and out values.
	 */
	DECLARE_BITMAP(output_enabled, DLN2_GPIO_MAX_PINS);

	/* active IRQs - not synced to hardware */
	DECLARE_BITMAP(unmasked_irqs, DLN2_GPIO_MAX_PINS);
	/* active IRQS - synced to hardware */
	DECLARE_BITMAP(enabled_irqs, DLN2_GPIO_MAX_PINS);
	int irq_type[DLN2_GPIO_MAX_PINS];
	struct mutex irq_lock;
};

struct dln2_gpio_pin {
	__le16 pin;
};

struct dln2_gpio_pin_val {
	__le16 pin __packed;
	u8 value;
};

static int dln2_gpio_get_pin_count(struct platform_device *pdev)
{
	int ret;
	__le16 count;
	int len = sizeof(count);

	ret = dln2_transfer_rx(pdev, DLN2_GPIO_GET_PIN_COUNT, &count, &len);
	if (ret < 0)
		return ret;
	if (len < sizeof(count))
		return -EPROTO;

	return le16_to_cpu(count);
}

static int dln2_gpio_pin_cmd(struct dln2_gpio *dln2, int cmd, unsigned pin)
{
	struct dln2_gpio_pin req = {
		.pin = cpu_to_le16(pin),
	};

	return dln2_transfer_tx(dln2->pdev, cmd, &req, sizeof(req));
}

static int dln2_gpio_pin_val(struct dln2_gpio *dln2, int cmd, unsigned int pin)
{
	int ret;
	struct dln2_gpio_pin req = {
		.pin = cpu_to_le16(pin),
	};
	struct dln2_gpio_pin_val rsp;
	int len = sizeof(rsp);

	ret = dln2_transfer(dln2->pdev, cmd, &req, sizeof(req), &rsp, &len);
	if (ret < 0)
		return ret;
	if (len < sizeof(rsp) || req.pin != rsp.pin)
		return -EPROTO;

	return rsp.value;
}

static int dln2_gpio_pin_get_in_val(struct dln2_gpio *dln2, unsigned int pin)
{
	int ret;

	ret = dln2_gpio_pin_val(dln2, DLN2_GPIO_PIN_GET_VAL, pin);
	if (ret < 0)
		return ret;
	return !!ret;
}

static int dln2_gpio_pin_get_out_val(struct dln2_gpio *dln2, unsigned int pin)
{
	int ret;

	ret = dln2_gpio_pin_val(dln2, DLN2_GPIO_PIN_GET_OUT_VAL, pin);
	if (ret < 0)
		return ret;
	return !!ret;
}

static int dln2_gpio_pin_set_out_val(struct dln2_gpio *dln2,
				     unsigned int pin, int value)
{
	struct dln2_gpio_pin_val req = {
		.pin = cpu_to_le16(pin),
		.value = value,
	};

	return dln2_transfer_tx(dln2->pdev, DLN2_GPIO_PIN_SET_OUT_VAL, &req,
				sizeof(req));
}

#define DLN2_GPIO_DIRECTION_IN		0
#define DLN2_GPIO_DIRECTION_OUT		1

static int dln2_gpio_request(struct gpio_chip *chip, unsigned offset)
{
	struct dln2_gpio *dln2 = container_of(chip, struct dln2_gpio, gpio);
	struct dln2_gpio_pin req = {
		.pin = cpu_to_le16(offset),
	};
	struct dln2_gpio_pin_val rsp;
	int len = sizeof(rsp);
	int ret;

	ret = dln2_gpio_pin_cmd(dln2, DLN2_GPIO_PIN_ENABLE, offset);
	if (ret < 0)
		return ret;

	/* cache the pin direction */
	ret = dln2_transfer(dln2->pdev, DLN2_GPIO_PIN_GET_DIRECTION,
			    &req, sizeof(req), &rsp, &len);
	if (ret < 0)
		return ret;
	if (len < sizeof(rsp) || req.pin != rsp.pin) {
		ret = -EPROTO;
		goto out_disable;
	}

	switch (rsp.value) {
	case DLN2_GPIO_DIRECTION_IN:
		clear_bit(offset, dln2->output_enabled);
		return 0;
	case DLN2_GPIO_DIRECTION_OUT:
		set_bit(offset, dln2->output_enabled);
		return 0;
	default:
		ret = -EPROTO;
		goto out_disable;
	}

out_disable:
	dln2_gpio_pin_cmd(dln2, DLN2_GPIO_PIN_DISABLE, offset);
	return ret;
}

static void dln2_gpio_free(struct gpio_chip *chip, unsigned offset)
{
	struct dln2_gpio *dln2 = container_of(chip, struct dln2_gpio, gpio);

	dln2_gpio_pin_cmd(dln2, DLN2_GPIO_PIN_DISABLE, offset);
}

static int dln2_gpio_get_direction(struct gpio_chip *chip, unsigned offset)
{
	struct dln2_gpio *dln2 = container_of(chip, struct dln2_gpio, gpio);

	if (test_bit(offset, dln2->output_enabled))
		return GPIOF_DIR_OUT;

	return GPIOF_DIR_IN;
}

static int dln2_gpio_get(struct gpio_chip *chip, unsigned int offset)
{
	struct dln2_gpio *dln2 = container_of(chip, struct dln2_gpio, gpio);
	int dir;

	dir = dln2_gpio_get_direction(chip, offset);
	if (dir < 0)
		return dir;

	if (dir == GPIOF_DIR_IN)
		return dln2_gpio_pin_get_in_val(dln2, offset);

	return dln2_gpio_pin_get_out_val(dln2, offset);
}

static void dln2_gpio_set(struct gpio_chip *chip, unsigned offset, int value)
{
	struct dln2_gpio *dln2 = container_of(chip, struct dln2_gpio, gpio);

	dln2_gpio_pin_set_out_val(dln2, offset, value);
}

static int dln2_gpio_set_direction(struct gpio_chip *chip, unsigned offset,
				   unsigned dir)
{
	struct dln2_gpio *dln2 = container_of(chip, struct dln2_gpio, gpio);
	struct dln2_gpio_pin_val req = {
		.pin = cpu_to_le16(offset),
		.value = dir,
	};
	int ret;

	ret = dln2_transfer_tx(dln2->pdev, DLN2_GPIO_PIN_SET_DIRECTION,
			       &req, sizeof(req));
	if (ret < 0)
		return ret;

	if (dir == DLN2_GPIO_DIRECTION_OUT)
		set_bit(offset, dln2->output_enabled);
	else
		clear_bit(offset, dln2->output_enabled);

	return ret;
}

static int dln2_gpio_direction_input(struct gpio_chip *chip, unsigned offset)
{
	return dln2_gpio_set_direction(chip, offset, DLN2_GPIO_DIRECTION_IN);
}

static int dln2_gpio_direction_output(struct gpio_chip *chip, unsigned offset,
				      int value)
{
	struct dln2_gpio *dln2 = container_of(chip, struct dln2_gpio, gpio);
	int ret;

	ret = dln2_gpio_pin_set_out_val(dln2, offset, value);
	if (ret < 0)
		return ret;

	return dln2_gpio_set_direction(chip, offset, DLN2_GPIO_DIRECTION_OUT);
}

static int dln2_gpio_set_debounce(struct gpio_chip *chip, unsigned offset,
				  unsigned debounce)
{
	struct dln2_gpio *dln2 = container_of(chip, struct dln2_gpio, gpio);
	__le32 duration = cpu_to_le32(debounce);

	return dln2_transfer_tx(dln2->pdev, DLN2_GPIO_SET_DEBOUNCE,
				&duration, sizeof(duration));
}

static int dln2_gpio_set_event_cfg(struct dln2_gpio *dln2, unsigned pin,
				   unsigned type, unsigned period)
{
	struct {
		__le16 pin;
		u8 type;
		__le16 period;
	} __packed req = {
		.pin = cpu_to_le16(pin),
		.type = type,
		.period = cpu_to_le16(period),
	};

	return dln2_transfer_tx(dln2->pdev, DLN2_GPIO_PIN_SET_EVENT_CFG,
				&req, sizeof(req));
}

static void dln2_irq_unmask(struct irq_data *irqd)
{
	struct gpio_chip *gc = irq_data_get_irq_chip_data(irqd);
	struct dln2_gpio *dln2 = container_of(gc, struct dln2_gpio, gpio);
	int pin = irqd_to_hwirq(irqd);

	set_bit(pin, dln2->unmasked_irqs);
}

static void dln2_irq_mask(struct irq_data *irqd)
{
	struct gpio_chip *gc = irq_data_get_irq_chip_data(irqd);
	struct dln2_gpio *dln2 = container_of(gc, struct dln2_gpio, gpio);
	int pin = irqd_to_hwirq(irqd);

	clear_bit(pin, dln2->unmasked_irqs);
}

static int dln2_irq_set_type(struct irq_data *irqd, unsigned type)
{
	struct gpio_chip *gc = irq_data_get_irq_chip_data(irqd);
	struct dln2_gpio *dln2 = container_of(gc, struct dln2_gpio, gpio);
	int pin = irqd_to_hwirq(irqd);

	switch (type) {
	case IRQ_TYPE_LEVEL_HIGH:
		dln2->irq_type[pin] = DLN2_GPIO_EVENT_LVL_HIGH;
		break;
	case IRQ_TYPE_LEVEL_LOW:
		dln2->irq_type[pin] = DLN2_GPIO_EVENT_LVL_LOW;
		break;
	case IRQ_TYPE_EDGE_BOTH:
		dln2->irq_type[pin] = DLN2_GPIO_EVENT_CHANGE;
		break;
	case IRQ_TYPE_EDGE_RISING:
		dln2->irq_type[pin] = DLN2_GPIO_EVENT_CHANGE_RISING;
		break;
	case IRQ_TYPE_EDGE_FALLING:
		dln2->irq_type[pin] = DLN2_GPIO_EVENT_CHANGE_FALLING;
		break;
	default:
		return -EINVAL;
	}

	return 0;
}

static void dln2_irq_bus_lock(struct irq_data *irqd)
{
	struct gpio_chip *gc = irq_data_get_irq_chip_data(irqd);
	struct dln2_gpio *dln2 = container_of(gc, struct dln2_gpio, gpio);

	mutex_lock(&dln2->irq_lock);
}

static void dln2_irq_bus_unlock(struct irq_data *irqd)
{
	struct gpio_chip *gc = irq_data_get_irq_chip_data(irqd);
	struct dln2_gpio *dln2 = container_of(gc, struct dln2_gpio, gpio);
	int pin = irqd_to_hwirq(irqd);
	int enabled, unmasked;
	unsigned type;
	int ret;

	enabled = test_bit(pin, dln2->enabled_irqs);
	unmasked = test_bit(pin, dln2->unmasked_irqs);

	if (enabled != unmasked) {
		if (unmasked) {
			type = dln2->irq_type[pin] & DLN2_GPIO_EVENT_MASK;
			set_bit(pin, dln2->enabled_irqs);
		} else {
			type = DLN2_GPIO_EVENT_NONE;
			clear_bit(pin, dln2->enabled_irqs);
		}

		ret = dln2_gpio_set_event_cfg(dln2, pin, type, 0);
		if (ret)
			dev_err(dln2->gpio.dev, "failed to set event\n");
	}

	mutex_unlock(&dln2->irq_lock);
}

static struct irq_chip dln2_gpio_irqchip = {
	.name = "dln2-irq",
	.irq_mask = dln2_irq_mask,
	.irq_unmask = dln2_irq_unmask,
	.irq_set_type = dln2_irq_set_type,
	.irq_bus_lock = dln2_irq_bus_lock,
	.irq_bus_sync_unlock = dln2_irq_bus_unlock,
};

static void dln2_gpio_event(struct platform_device *pdev, u16 echo,
			    const void *data, int len)
{
	int pin, irq;

	const struct {
		__le16 count;
		__u8 type;
		__le16 pin;
		__u8 value;
	} __packed *event = data;
	struct dln2_gpio *dln2 = platform_get_drvdata(pdev);

	if (len < sizeof(*event)) {
		dev_err(dln2->gpio.dev, "short event message\n");
		return;
	}

	pin = le16_to_cpu(event->pin);
	if (pin >= dln2->gpio.ngpio) {
		dev_err(dln2->gpio.dev, "out of bounds pin %d\n", pin);
		return;
	}

	irq = irq_find_mapping(dln2->gpio.irqdomain, pin);
	if (!irq) {
		dev_err(dln2->gpio.dev, "pin %d not mapped to IRQ\n", pin);
		return;
	}

	switch (dln2->irq_type[pin]) {
	case DLN2_GPIO_EVENT_CHANGE_RISING:
		if (event->value)
			generic_handle_irq(irq);
		break;
	case DLN2_GPIO_EVENT_CHANGE_FALLING:
		if (!event->value)
			generic_handle_irq(irq);
		break;
	default:
		generic_handle_irq(irq);
	}
}

static int dln2_gpio_probe(struct platform_device *pdev)
{
	struct dln2_gpio *dln2;
	struct device *dev = &pdev->dev;
	int pins;
	int ret;

	pins = dln2_gpio_get_pin_count(pdev);
	if (pins < 0) {
		dev_err(dev, "failed to get pin count: %d\n", pins);
		return pins;
	}
	if (pins > DLN2_GPIO_MAX_PINS) {
		pins = DLN2_GPIO_MAX_PINS;
		dev_warn(dev, "clamping pins to %d\n", DLN2_GPIO_MAX_PINS);
	}

	dln2 = devm_kzalloc(&pdev->dev, sizeof(*dln2), GFP_KERNEL);
	if (!dln2)
		return -ENOMEM;

	mutex_init(&dln2->irq_lock);

	dln2->pdev = pdev;

	dln2->gpio.label = "dln2";
	dln2->gpio.dev = dev;
	dln2->gpio.owner = THIS_MODULE;
	dln2->gpio.base = -1;
	dln2->gpio.ngpio = pins;
	dln2->gpio.can_sleep = true;
	dln2->gpio.irq_not_threaded = true;
	dln2->gpio.set = dln2_gpio_set;
	dln2->gpio.get = dln2_gpio_get;
	dln2->gpio.request = dln2_gpio_request;
	dln2->gpio.free = dln2_gpio_free;
	dln2->gpio.get_direction = dln2_gpio_get_direction;
	dln2->gpio.direction_input = dln2_gpio_direction_input;
	dln2->gpio.direction_output = dln2_gpio_direction_output;
	dln2->gpio.set_debounce = dln2_gpio_set_debounce;

	platform_set_drvdata(pdev, dln2);

	ret = gpiochip_add(&dln2->gpio);
	if (ret < 0) {
		dev_err(dev, "failed to add gpio chip: %d\n", ret);
		goto out;
	}

	ret = gpiochip_irqchip_add(&dln2->gpio, &dln2_gpio_irqchip, 0,
				   handle_simple_irq, IRQ_TYPE_NONE);
	if (ret < 0) {
		dev_err(dev, "failed to add irq chip: %d\n", ret);
		goto out_gpiochip_remove;
	}

	ret = dln2_register_event_cb(pdev, DLN2_GPIO_CONDITION_MET_EV,
				     dln2_gpio_event);
	if (ret) {
		dev_err(dev, "failed to register event cb: %d\n", ret);
		goto out_gpiochip_remove;
	}

	return 0;

out_gpiochip_remove:
	gpiochip_remove(&dln2->gpio);
out:
	return ret;
}

static int dln2_gpio_remove(struct platform_device *pdev)
{
	struct dln2_gpio *dln2 = platform_get_drvdata(pdev);

	dln2_unregister_event_cb(pdev, DLN2_GPIO_CONDITION_MET_EV);
	gpiochip_remove(&dln2->gpio);

	return 0;
}

static struct platform_driver dln2_gpio_driver = {
	.driver.name	= "dln2-gpio",
	.probe		= dln2_gpio_probe,
	.remove		= dln2_gpio_remove,
};

module_platform_driver(dln2_gpio_driver);

MODULE_AUTHOR("Daniel Baluta <daniel.baluta@intel.com");
MODULE_DESCRIPTION("Driver for the Diolan DLN2 GPIO interface");
MODULE_LICENSE("GPL v2");
MODULE_ALIAS("platform:dln2-gpio");
